{"version":3,"file":"salaxy-lib-ng1.umd.cjs","sources":["../../../@salaxy/ng1/ts/ajax/AjaxNg1.ts","../../../@salaxy/ng1/ts/controllers/bases/WizardController.ts","../../../@salaxy/ng1/ts/controllers/account/onboarding/CustomerOnboardingController.ts","../../../@salaxy/ng1/ts/controllers/account/onboarding/WorkerOnboardingController.ts","../../../@salaxy/ng1/ts/controllers/account/onboarding/HouseholdOnboardingController.ts","../../../@salaxy/ng1/ts/controllers/account/onboarding/CompanyOnboardingController.ts","../../../@salaxy/ng1/ts/controllers/account/onboarding/SigningController.ts","../../../@salaxy/ng1/ts/controllers/account/onboarding/SignatureController.ts","../../../@salaxy/ng1/ts/controllers/bases/CrudControllerBase.ts","../../../@salaxy/ng1/ts/controllers/account/AccountAuthorizationController.ts","../../../@salaxy/ng1/ts/controllers/account/CertificateController.ts","../../../node_modules/.pnpm/angular@1.8.3/node_modules/angular/angular.js","../../../node_modules/.pnpm/angular@1.8.3/node_modules/angular/index.js","../../../@salaxy/ng1/ts/controllers/bases/ApiCrudObjectController.ts","../../../@salaxy/ng1/ts/controllers/bases/ApiCrudObjectControllerBindings.ts","../../../@salaxy/ng1/ts/controllers/bases/ListControllerBase.ts","../../../@salaxy/ng1/ts/controllers/bases/ListControllerBaseBindings.ts","../../../@salaxy/ng1/ts/controllers/bases/ODataHelperController.ts","../../../@salaxy/ng1/ts/controllers/bases/ODataQueryController.ts","../../../@salaxy/ng1/ts/controllers/account/CertificateCrudController.ts","../../../@salaxy/ng1/ts/services/ui/model/EditDialogKnownActions.ts","../../../@salaxy/ng1/ts/services/ui/model/EditDialogParameters.ts","../../../@salaxy/ng1/ts/services/ui/model/EditDialogResult.ts","../../../@salaxy/ng1/ts/services/ui/AlertService.ts","../../../node_modules/.pnpm/@progress+pako-esm@1.0.1/node_modules/@progress/pako-esm/dist/pako-esm5.js","../../../node_modules/.pnpm/@progress+jszip-esm@1.0.3/node_modules/@progress/jszip-esm/dist/jszip-esm5.js","../../../node_modules/.pnpm/file-saver@2.0.5/node_modules/file-saver/dist/FileSaver.min.js","../../../@salaxy/ng1/ts/services/ui/ExcelHelpers.ts","../../../@salaxy/ng1/ts/services/ui/FileService.ts","../../../@salaxy/ng1/ts/services/ui/GravatarHelpers.ts","../../../@salaxy/ng1/ts/services/ui/JsonSchemaService.ts","../../../@salaxy/ng1/ts/helpers/AppInsightExceptionTracking.ts","../../../@salaxy/ng1/ts/helpers/CalendarHelper.ts","../../../@salaxy/ng1/ts/helpers/sitemap_PersonLeafs.ts","../../../@salaxy/ng1/ts/helpers/sitemap_Company.ts","../../../@salaxy/ng1/ts/helpers/SitemapHelper.ts","../../../@salaxy/ng1/ts/helpers/CurrentRoute.ts","../../../@salaxy/ng1/ts/helpers/PromisePolyfill.ts","../../../@salaxy/ng1/ts/helpers/RouteHelperProvider.ts","../../../@salaxy/ng1/ts/helpers/RRuleFinnish.ts","../../../@salaxy/ng1/ts/services/ui/NaviService.ts","../../../@salaxy/ng1/ts/services/ui/UiCrudHelpers.ts","../../../@salaxy/ng1/ts/services/ui/UiHelpers.ts","../../../@salaxy/ng1/ts/services/ui/WizardService.ts","../../../@salaxy/ng1/ts/services/BaseService.ts","../../../@salaxy/ng1/ts/services/AuthorizedAccountService.ts","../../../@salaxy/ng1/ts/services/CacheService.ts","../../../@salaxy/ng1/ts/services/CertificateService.ts","../../../@salaxy/ng1/ts/services/CredentialService.ts","../../../@salaxy/ng1/ts/controllers/calc/PayrollLogic.ts","../../../@salaxy/ng1/ts/services/InvoicesService.ts","../../../@salaxy/ng1/ts/services/OnboardingService.ts","../../../@salaxy/ng1/ts/services/PartnerService.ts","../../../@salaxy/ng1/ts/services/ReportsService.ts","../../../@salaxy/ng1/ts/services/RowTypeService.ts","../../../@salaxy/ng1/ts/services/SessionService.ts","../../../@salaxy/ng1/ts/services/SettingsService.ts","../../../@salaxy/ng1/ts/services/SignatureService.ts","../../../@salaxy/ng1/ts/services/UiTranslatorService.ts","../../../@salaxy/ng1/ts/services/UploadService.ts","../../../@salaxy/ng1/ts/services/UsecasesService.ts","../../../@salaxy/ng1/ts/services/UserSettingsService.ts","../../../@salaxy/ng1/ts/services/VarmaPensionService.ts","../../../@salaxy/ng1/ts/services/WorkflowService.ts","../../../@salaxy/ng1/ts/controllers/account/CredentialController.ts","../../../@salaxy/ng1/ts/controllers/account/EmbeddedUiController.ts","../../../@salaxy/ng1/ts/controllers/account/PartnerController.ts","../../../@salaxy/ng1/ts/controllers/account/SessionController.ts","../../../@salaxy/ng1/ts/controllers/account/CompanyAccountController.ts","../../../@salaxy/ng1/ts/controllers/calc/2022/CalcEmploymentController.ts","../../../@salaxy/ng1/ts/controllers/calc/CalculationCrudController.ts","../../../@salaxy/ng1/ts/controllers/calc/2022/Calculator2022Controller.ts","../../../@salaxy/ng1/ts/controllers/calc/salary-bases/SalaryBasesController.ts","../../../node_modules/.pnpm/@kurkle+color@0.3.2/node_modules/@kurkle/color/dist/color.esm.js","../../../node_modules/.pnpm/chart.js@4.4.2/node_modules/chart.js/dist/chunks/helpers.segment.js","../../../node_modules/.pnpm/chart.js@4.4.2/node_modules/chart.js/dist/chart.js","../../../@salaxy/ng1/ts/controllers/calc/CalcChartController.ts","../../../@salaxy/ng1/ts/controllers/calc/CalcHouseholdUsecaseController.ts","../../../@salaxy/ng1/ts/controllers/calc/CalculatorSection.ts","../../../@salaxy/ng1/ts/controllers/calc/CalculatorSections.ts","../../../@salaxy/ng1/ts/controllers/calc/Calculator2019Controller.ts","../../../@salaxy/ng1/ts/controllers/calc/CalcIrRowsController.ts","../../../@salaxy/ng1/ts/controllers/calc/CalcReportController.ts","../../../@salaxy/ng1/ts/controllers/calc/CalcReportsController.ts","../../../@salaxy/ng1/ts/controllers/calc/CalcReportsDisplayController.ts","../../../@salaxy/ng1/ts/controllers/calc/CalcRowTypeController.ts","../../../@salaxy/ng1/ts/controllers/calc/CalcRowFormulaController.ts","../../../@salaxy/ng1/ts/controllers/calc/CalcWorktimeController.ts","../../../@salaxy/ng1/ts/controllers/calc/CalcRowDimensionInputController.ts","../../../@salaxy/ng1/ts/controllers/calc/CalcRowDocumentationController.ts","../../../@salaxy/ng1/ts/controllers/calc/CalcRows2019Controller.ts","../../../@salaxy/ng1/ts/controllers/calc/CalcSharingReceiptActionController.ts","../../../@salaxy/ng1/ts/controllers/calc/CalcsIrRowsController.ts","../../../@salaxy/ng1/ts/controllers/calc/CalculatorPanels.ts","../../../@salaxy/ng1/ts/controllers/calc/CreditTransferController.ts","../../../@salaxy/ng1/ts/controllers/calc/PayrollCrudController.ts","../../../@salaxy/ng1/ts/controllers/calc/Payroll4CrudController.ts","../../../@salaxy/ng1/ts/controllers/calc/PaymentController.ts","../../../@salaxy/ng1/ts/controllers/calc/CalculationEditorController.ts","../../../@salaxy/ng1/ts/controllers/calc/CostAccountingController.ts","../../../@salaxy/ng1/ts/controllers/calc/CalcCostAccountingController.ts","../../../@salaxy/ng1/ts/controllers/calc/CalcRowCostAccountingController.ts","../../../@salaxy/ng1/ts/controllers/calc/PalkkausPersonalPaymentOverviewController.ts","../../../@salaxy/ng1/ts/controllers/calc/SalaryDateKindController.ts","../../../@salaxy/ng1/ts/controllers/calc/CalcLeavesController.ts","../../../@salaxy/ng1/ts/controllers/calc/CalcRepairController.ts","../../../node_modules/.pnpm/xlsx@0.18.5/node_modules/xlsx/xlsx.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/internal/qs/formats.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/internal/qs/utils.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/internal/qs/stringify.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/version.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/_shims/registry.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/_shims/MultipartBody.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/_shims/web-runtime.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/_shims/index.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/error.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/internal/decoders/line.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/internal/stream-utils.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/streaming.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/uploads.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/core.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/pagination.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resource.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/chat/completions/messages.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/chat/completions/completions.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/chat/chat.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/audio/speech.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/audio/transcriptions.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/audio/translations.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/audio/audio.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/batches.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/beta/assistants.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/lib/RunnableFunction.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/lib/chatCompletionUtils.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/lib/EventStream.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/lib/parser.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/lib/AbstractChatCompletionRunner.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/lib/ChatCompletionRunner.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/_vendor/partial-json-parser/parser.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/lib/ChatCompletionStream.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/lib/ChatCompletionStreamingRunner.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/beta/chat/completions.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/beta/chat/chat.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/beta/realtime/sessions.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/beta/realtime/realtime.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/lib/AssistantStream.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/beta/threads/messages.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/beta/threads/runs/steps.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/beta/threads/runs/runs.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/beta/threads/threads.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/lib/Util.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/beta/vector-stores/files.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/beta/vector-stores/file-batches.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/beta/vector-stores/vector-stores.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/beta/beta.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/completions.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/embeddings.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/files.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/fine-tuning/jobs/checkpoints.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/fine-tuning/jobs/jobs.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/fine-tuning/fine-tuning.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/images.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/models.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/moderations.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/uploads/parts.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/resources/uploads/uploads.mjs","../../../node_modules/.pnpm/openai@4.86.2_encoding@0.1.13_ws@8.18.3_bufferutil@4.0.8_utf-8-validate@5.0.10_/node_modules/openai/index.mjs","../../../@salaxy/ng1/ts/controllers/calc/Payroll4AssistantController.ts","../../../@salaxy/ng1/ts/controllers/calc/CalcRepairInfoController.ts","../../../@salaxy/ng1/ts/controllers/calc/NewPaymentController.ts","../../../@salaxy/ng1/ts/controllers/communications/ContactInfoController.ts","../../../@salaxy/ng1/ts/controllers/communications/MessageThreadCrudController.ts","../../../@salaxy/ng1/ts/controllers/communications/OmapalkkaController.ts","../../../@salaxy/ng1/ts/controllers/communications/VarmaBannerController.ts","../../../@salaxy/ng1/ts/controllers/communications/WelcomeController.ts","../../../@salaxy/ng1/ts/controllers/form-controls/_InputBase.ts","../../../node_modules/.pnpm/air-datepicker@3.5.3/node_modules/air-datepicker/air-datepicker.js","../../../node_modules/.pnpm/air-datepicker@3.5.3/node_modules/air-datepicker/locale/en.js","../../../node_modules/.pnpm/air-datepicker@3.5.3/node_modules/air-datepicker/locale/fi.js","../../../node_modules/.pnpm/air-datepicker@3.5.3/node_modules/air-datepicker/locale/sv.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/enums.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/dom-utils/getNodeName.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/dom-utils/getWindow.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/dom-utils/instanceOf.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/modifiers/applyStyles.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/utils/getBasePlacement.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/utils/math.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/utils/userAgent.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/dom-utils/isLayoutViewport.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/dom-utils/getBoundingClientRect.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/dom-utils/getLayoutRect.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/dom-utils/contains.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/dom-utils/getComputedStyle.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/dom-utils/isTableElement.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/dom-utils/getDocumentElement.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/dom-utils/getParentNode.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/dom-utils/getOffsetParent.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/utils/getMainAxisFromPlacement.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/utils/within.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/utils/getFreshSideObject.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/utils/mergePaddingObject.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/utils/expandToHashMap.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/modifiers/arrow.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/utils/getVariation.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/modifiers/computeStyles.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/modifiers/eventListeners.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/utils/getOppositePlacement.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/utils/getOppositeVariationPlacement.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/dom-utils/getWindowScroll.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/dom-utils/getWindowScrollBarX.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/dom-utils/getViewportRect.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/dom-utils/getDocumentRect.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/dom-utils/isScrollParent.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/dom-utils/getScrollParent.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/dom-utils/listScrollParents.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/utils/rectToClientRect.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/dom-utils/getClippingRect.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/utils/computeOffsets.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/utils/detectOverflow.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/utils/computeAutoPlacement.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/modifiers/flip.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/modifiers/hide.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/modifiers/offset.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/modifiers/popperOffsets.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/utils/getAltAxis.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/modifiers/preventOverflow.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/dom-utils/getHTMLElementScroll.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/dom-utils/getNodeScroll.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/dom-utils/getCompositeRect.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/utils/orderModifiers.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/utils/debounce.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/utils/mergeByName.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/createPopper.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/popper-lite.js","../../../node_modules/.pnpm/@popperjs+core@2.11.8/node_modules/@popperjs/core/lib/popper.js","../../../@salaxy/ng1/ts/controllers/form-controls/DatepickerController.ts","../../../@salaxy/ng1/ts/controllers/form-controls/DatepickerPopupController.ts","../../../@salaxy/ng1/ts/controllers/form-controls/DateRangeController.ts","../../../@salaxy/ng1/ts/controllers/form-controls/FormGroupController.ts","../../../@salaxy/ng1/ts/controllers/form-controls/InputController.ts","../../../@salaxy/ng1/ts/controllers/form-controls/InputAccountingTargetController.ts","../../../@salaxy/ng1/ts/controllers/form-controls/InputBooleanController.ts","../../../@salaxy/ng1/ts/controllers/form-controls/InputCollectiveBargainAgreementController.ts","../../../@salaxy/ng1/ts/controllers/form-controls/InputEnumController.ts","../../../@salaxy/ng1/ts/controllers/form-controls/InputCredentialController.ts","../../../@salaxy/ng1/ts/controllers/form-controls/InputDurationController.ts","../../../@salaxy/ng1/ts/controllers/form-controls/InputIncomeTypeController.ts","../../../@salaxy/ng1/ts/controllers/form-controls/InputNumberController.ts","../../../@salaxy/ng1/ts/controllers/form-controls/InputOccupationTypeController.ts","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/weekday.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/helpers.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/dateutil.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/iterresult.js","../../../node_modules/.pnpm/tslib@2.6.2/node_modules/tslib/tslib.es6.mjs","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/callbackiterresult.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/nlp/i18n.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/nlp/totext.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/nlp/parsetext.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/types.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/nlp/index.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/datetime.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/parseoptions.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/parsestring.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/datewithzone.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/optionstostring.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/cache.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/masks.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/iterinfo/yearinfo.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/iterinfo/monthinfo.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/iterinfo/easter.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/iterinfo/index.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/iter/poslist.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/iter/index.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/rrule.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/iterset.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/rrulestr.js","../../../node_modules/.pnpm/rrule@2.8.1/node_modules/rrule/dist/esm/rruleset.js","../../../@salaxy/ng1/ts/controllers/form-controls/InputRruleController.ts","../../../@salaxy/ng1/ts/controllers/form-controls/InputTimeController.ts","../../../@salaxy/ng1/ts/controllers/form-controls/InputTypeaheadController.ts","../../../@salaxy/ng1/ts/controllers/form-controls/ToggleButtonsController.ts","../../../@salaxy/ng1/ts/controllers/form-controls/ValidationSummaryController.ts","../../../@salaxy/ng1/ts/controllers/form-controls/InputHolidayMultipliersController.ts","../../../@salaxy/ng1/ts/controllers/form-controls/InputPayStatsRowTypeController.ts","../../../@salaxy/ng1/ts/controllers/form-controls/InputEmployeeGroupController.ts","../../../@salaxy/ng1/ts/controllers/form-controls/MarkdownEditorController.ts","../../../@salaxy/ng1/ts/controllers/form-controls/MarkdownViewerController.ts","../../../@salaxy/ng1/ts/controllers/helpers/ActionButtonController.ts","../../../@salaxy/ng1/ts/controllers/helpers/AlertController.ts","../../../@salaxy/ng1/ts/controllers/helpers/AvatarController.ts","../../../@salaxy/ng1/ts/controllers/helpers/BatchProcessController.ts","../../../@salaxy/ng1/ts/controllers/helpers/CalendarController.ts","../../../node_modules/.pnpm/chartjs-plugin-annotation@3.0.1_chart.js@4.4.2/node_modules/chartjs-plugin-annotation/dist/chartjs-plugin-annotation.esm.js","../../../node_modules/.pnpm/dayjs@1.11.10/node_modules/dayjs/dayjs.min.js","../../../node_modules/.pnpm/dayjs@1.11.10/node_modules/dayjs/plugin/customParseFormat.js","../../../node_modules/.pnpm/dayjs@1.11.10/node_modules/dayjs/plugin/advancedFormat.js","../../../node_modules/.pnpm/dayjs@1.11.10/node_modules/dayjs/plugin/quarterOfYear.js","../../../node_modules/.pnpm/dayjs@1.11.10/node_modules/dayjs/plugin/localizedFormat.js","../../../node_modules/.pnpm/dayjs@1.11.10/node_modules/dayjs/plugin/isoWeek.js","../../../node_modules/.pnpm/chartjs-adapter-dayjs-4@1.0.4_chart.js@4.4.2_dayjs@1.11.10/node_modules/chartjs-adapter-dayjs-4/dist/chartjs-adapter-dayjs-4.esm.js","../../../@salaxy/ng1/ts/controllers/helpers/ChartController.ts","../../../@salaxy/ng1/ts/controllers/helpers/JsonFormatterController.ts","../../../node_modules/.pnpm/json-diff-ts@4.8.2/node_modules/json-diff-ts/dist/index.js","../../../@salaxy/ng1/ts/controllers/helpers/JsonDiffController.ts","../../../@salaxy/ng1/ts/controllers/helpers/NaviController.ts","../../../@salaxy/ng1/ts/controllers/helpers/SpinnerController.ts","../../../@salaxy/ng1/ts/controllers/helpers/TabController.ts","../../../@salaxy/ng1/ts/controllers/helpers/TabsController.ts","../../../@salaxy/ng1/ts/controllers/helpers/TabButtonsController.ts","../../../@salaxy/ng1/ts/controllers/helpers/UiTranslatorController.ts","../../../@salaxy/ng1/ts/controllers/helpers/ODataActionsController.ts","../../../@salaxy/ng1/ts/controllers/helpers/ImportController.ts","../../../@salaxy/ng1/ts/controllers/helpers/ExportController.ts","../../../node_modules/.pnpm/tabulator-tables@5.6.1/node_modules/tabulator-tables/dist/js/tabulator_esm.js","../../../@salaxy/ng1/ts/controllers/helpers/import/DataImportControllerBase.ts","../../../@salaxy/ng1/ts/controllers/helpers/import/CompanyImportController.ts","../../../@salaxy/ng1/ts/controllers/helpers/import/CalcImportController.ts","../../../@salaxy/ng1/ts/controllers/helpers/import/ImportStagingController.ts","../../../@salaxy/ng1/ts/controllers/helpers/import/WorkerImportController.ts","../../../@salaxy/ng1/ts/controllers/invoices/CustomerInvoiceCrudController.ts","../../../@salaxy/ng1/ts/controllers/invoices/InvoiceCrudController.ts","../../../@salaxy/ng1/ts/controllers/invoices/InvoicePaymentListController.ts","../../../@salaxy/ng1/ts/controllers/invoices/InvoicesCreateController.ts","../../../@salaxy/ng1/ts/controllers/invoices/PaymentChannelController.ts","../../../@salaxy/ng1/ts/controllers/invoices/InvoiceToolsController.ts","../../../@salaxy/ng1/ts/controllers/invoices/InvoiceSepaController.ts","../../../@salaxy/ng1/ts/controllers/invoices/InvoiceReportController.ts","../../../@salaxy/ng1/ts/controllers/invoices/CompanyInvoicesController.ts","../../../@salaxy/ng1/ts/controllers/invoices/InvoiceAlertsController.ts","../../../@salaxy/ng1/ts/controllers/modals/EditDialogController.ts","../../../@salaxy/ng1/ts/controllers/modals/ModalGenericDialogController.ts","../../../@salaxy/ng1/ts/controllers/personal/CalcSharingController.ts","../../../@salaxy/ng1/ts/controllers/personal/EmployerListController.ts","../../../@salaxy/ng1/ts/controllers/personal/EmployerReportController.ts","../../../@salaxy/ng1/ts/controllers/personal/EmployerSelectController.ts","../../../@salaxy/ng1/ts/controllers/personal/HouseholdDeductionReportController.ts","../../../@salaxy/ng1/ts/controllers/personal/HouseholdYearCrudController.ts","../../../@salaxy/ng1/ts/controllers/personal/PersonAccountController.ts","../../../@salaxy/ng1/ts/controllers/personal/WorkerReportController.ts","../../../@salaxy/ng1/ts/controllers/personal/TimesheetWorkerDemoController.ts","../../../@salaxy/ng1/ts/controllers/personal/WorkerTimerController.ts","../../../@salaxy/ng1/ts/controllers/personal/WorkerHourlyReportController.ts","../../../@salaxy/ng1/ts/controllers/personal/WorkerExpenseReportController.ts","../../../@salaxy/ng1/ts/controllers/pro/AccountantWizardController.ts","../../../@salaxy/ng1/ts/controllers/records/RecordsController.ts","../../../@salaxy/ng1/ts/controllers/report/AccountingReportCrudController.ts","../../../@salaxy/ng1/ts/controllers/report/AccountingReportQueryController.ts","../../../@salaxy/ng1/ts/controllers/report/AccountingReportRowsController.ts","../../../@salaxy/ng1/ts/controllers/report/AccountingReportToolsController.ts","../../../@salaxy/ng1/ts/controllers/report/IrEarningsPaymentCrudController.ts","../../../@salaxy/ng1/ts/controllers/report/IrPayerSummaryCrudController.ts","../../../@salaxy/ng1/ts/controllers/report/ReportsController.ts","../../../@salaxy/ng1/ts/controllers/report/SalaryReportCrudController.ts","../../../@salaxy/ng1/ts/controllers/report/PayCertificateController.ts","../../../@salaxy/ng1/ts/controllers/report/ConfigurableGridReportControllerBase.ts","../../../@salaxy/ng1/ts/controllers/report/CalculationReportController.ts","../../../@salaxy/ng1/ts/controllers/report/AccountingRowReportController.ts","../../../@salaxy/ng1/ts/controllers/report/SummaryReportDisplayController.ts","../../../@salaxy/ng1/ts/controllers/report/SummaryReportController.ts","../../../@salaxy/ng1/ts/controllers/report/AccountingReportDisplayController.ts","../../../@salaxy/ng1/ts/controllers/report/WorkerSummaryReportController.ts","../../../@salaxy/ng1/ts/controllers/report/WorkerSummaryReportDisplayController.ts","../../../@salaxy/ng1/ts/controllers/report/HolidayReportController.ts","../../../@salaxy/ng1/ts/controllers/report/SalarySlipDownloadController.ts","../../../@salaxy/ng1/ts/controllers/report/AccountingHolidayPayDebtReportQueryController.ts","../../../@salaxy/ng1/ts/controllers/report/HolidayPayReportQueryController.ts","../../../@salaxy/ng1/ts/controllers/report/SummaryReportQueryController.ts","../../../@salaxy/ng1/ts/controllers/report/PayStatsReportQueryController.ts","../../../@salaxy/ng1/ts/controllers/settings/AccountantController.ts","../../../@salaxy/ng1/ts/controllers/settings/AccountingChannelSettingsController.ts","../../../@salaxy/ng1/ts/controllers/settings/AccountingTargetCrudController.ts","../../../@salaxy/ng1/ts/controllers/settings/CompanySettingsController.ts","../../../@salaxy/ng1/ts/controllers/settings/InsuranceWizardController.ts","../../../@salaxy/ng1/ts/controllers/settings/OwnerSettingsController.ts","../../../@salaxy/ng1/ts/controllers/settings/PaymentChannelSettingsController.ts","../../../@salaxy/ng1/ts/controllers/settings/RowTypesSettingsController.ts","../../../@salaxy/ng1/ts/controllers/settings/ServiceModelCrudController.ts","../../../@salaxy/ng1/ts/controllers/sxy-form/SxyCodeEditorController.ts","../../../@salaxy/ng1/ts/controllers/sxy-form/SxyFormController.ts","../../../@salaxy/ng1/ts/controllers/sxy-form/SxyFormElementController.ts","../../../@salaxy/ng1/ts/controllers/sxy-form/SxyGridController.ts","../../../@salaxy/ng1/ts/controllers/sxy-form/SxyInputController.ts","../../../@salaxy/ng1/ts/controllers/sxy-form/SxySchemaEditorController.ts","../../../@salaxy/ng1/ts/controllers/sxy-table/SxyTableController.ts","../../../@salaxy/ng1/ts/controllers/test/AccountResetController.ts","../../../@salaxy/ng1/ts/controllers/test/SmokeTestController.ts","../../../@salaxy/ng1/ts/controllers/test/ReferenceObjectCrudController.ts","../../../@salaxy/ng1/ts/controllers/worker/AbsencePeriodsController.ts","../../../@salaxy/ng1/ts/controllers/worker/EmploymentCrudController.ts","../../../@salaxy/ng1/ts/controllers/worker/EmploymentTaxcardsController.ts","../../../@salaxy/ng1/ts/controllers/worker/EmploymentWizardController.ts","../../../@salaxy/ng1/ts/controllers/worker/HolidayYearAccrualController.ts","../../../@salaxy/ng1/ts/controllers/worker/HolidayYearCrudController.ts","../../../@salaxy/ng1/ts/controllers/worker/HolidayYearHolidaysController.ts","../../../@salaxy/ng1/ts/controllers/worker/HolidayYearPaidController.ts","../../../@salaxy/ng1/ts/controllers/worker/MyTaxcardsController.ts","../../../@salaxy/ng1/ts/controllers/worker/TaxcardManualEditController.ts","../../../@salaxy/ng1/ts/controllers/worker/TaxcardCrudController.ts","../../../@salaxy/ng1/ts/controllers/worker/TaxcardIncomeLogController.ts","../../../@salaxy/ng1/ts/controllers/worker/WorkerAbsencesCrudController.ts","../../../@salaxy/ng1/ts/controllers/worker/WorkerAccountCrudController.ts","../../../@salaxy/ng1/ts/controllers/worker/WorkerAssureController.ts","../../../@salaxy/ng1/ts/controllers/workflow/CalendarEventsCrudController.ts","../../../@salaxy/ng1/ts/controllers/workflow/DatasetsCrudController.ts","../../../@salaxy/ng1/ts/controllers/workflow/UsecasesCrudController.ts","../../../@salaxy/ng1/ts/controllers/workflow/WorkflowController.ts","../../../@salaxy/ng1/ts/controllers/workflow/WorkflowBadgeController.ts","../../../@salaxy/ng1/ts/controllers/templates/TemplateCrudController.ts","../../../@salaxy/ng1/ts/components/_ComponentBase.ts","../../../@salaxy/ng1/ts/components/account/AccountInfo.ts","../../../@salaxy/ng1/ts/components/account/AssurePartner.ts","../../../@salaxy/ng1/ts/components/account/AuthCard.ts","../../../@salaxy/ng1/ts/components/account/AuthorizedAccounts.ts","../../../@salaxy/ng1/ts/components/account/AuthorizingAccounts.ts","../../../@salaxy/ng1/ts/components/account/Certificates.ts","../../../@salaxy/ng1/ts/components/account/Credentials.ts","../../../@salaxy/ng1/ts/components/account/LanguageSelector.ts","../../../@salaxy/ng1/ts/components/account/LoginButton.ts","../../../@salaxy/ng1/ts/components/account/Signing.ts","../../../@salaxy/ng1/ts/components/account/UserInfo.ts","../../../@salaxy/ng1/ts/components/account/AccountAvatarEdit.ts","../../../@salaxy/ng1/ts/components/account/AccountContactEdit.ts","../../../@salaxy/ng1/ts/components/calc/2022/CalcEmployment.ts","../../../@salaxy/ng1/ts/components/calc/2022/CalcRowsEditor.ts","../../../@salaxy/ng1/ts/components/calc/2022/CalcUsecase.ts","../../../@salaxy/ng1/ts/components/calc/payroll/PayrollDetails.ts","../../../@salaxy/ng1/ts/components/calc/payroll/PayrollDetailsList.ts","../../../@salaxy/ng1/ts/components/calc/payroll/PayrollEdit.ts","../../../@salaxy/ng1/ts/components/calc/payroll/PayrollList.ts","../../../@salaxy/ng1/ts/components/calc/payroll/PayrollSelectList.ts","../../../@salaxy/ng1/ts/components/calc/payroll/PayrollDetailsSelectList.ts","../../../@salaxy/ng1/ts/components/calc/payroll/PayrollAssistant.ts","../../../@salaxy/ng1/ts/components/calc/rows/CalcIrRows.ts","../../../@salaxy/ng1/ts/components/calc/rows/CalcRows2019Editor.ts","../../../@salaxy/ng1/ts/components/calc/rows/CalcRowCostAccounting.ts","../../../@salaxy/ng1/ts/components/calc/rows/CalcRowDimensionInput.ts","../../../@salaxy/ng1/ts/components/calc/rows/CalcsIrRows.ts","../../../@salaxy/ng1/ts/components/calc/rows/CalcRowDocumentation.ts","../../../@salaxy/ng1/ts/components/calc/rows/CalcRowFormula.ts","../../../@salaxy/ng1/ts/components/calc/Calc.ts","../../../@salaxy/ng1/ts/components/calc/CalcChart.ts","../../../@salaxy/ng1/ts/components/calc/CalcDashboard.ts","../../../@salaxy/ng1/ts/components/calc/CalcList.ts","../../../@salaxy/ng1/ts/components/calc/CalcNewIntro.ts","../../../@salaxy/ng1/ts/components/calc/CalcReport.ts","../../../@salaxy/ng1/ts/components/calc/CalcReports.ts","../../../@salaxy/ng1/ts/components/calc/CalcResults.ts","../../../@salaxy/ng1/ts/components/calc/CalcRowType.ts","../../../@salaxy/ng1/ts/components/calc/CalcSharingReceiptAction.ts","../../../@salaxy/ng1/ts/components/calc/CalcLeaves.ts","../../../@salaxy/ng1/ts/components/calc/CalcWorkerInfo.ts","../../../@salaxy/ng1/ts/components/calc/CalcWorktime.ts","../../../@salaxy/ng1/ts/components/calc/PayButton.ts","../../../@salaxy/ng1/ts/components/calc/CalcEditor.ts","../../../@salaxy/ng1/ts/components/calc/CalcCostAccounting.ts","../../../@salaxy/ng1/ts/components/calc/CostAccounting.ts","../../../@salaxy/ng1/ts/components/calc/SalaryDateKindButton.ts","../../../@salaxy/ng1/ts/components/calc/CalcRepair.ts","../../../@salaxy/ng1/ts/components/calc/CalcRepairInfo.ts","../../../@salaxy/ng1/ts/components/communications/ContactInfo.ts","../../../@salaxy/ng1/ts/components/communications/MessageThread.ts","../../../@salaxy/ng1/ts/components/communications/VarmaBanner.ts","../../../@salaxy/ng1/ts/components/communications/Welcome.ts","../../../@salaxy/ng1/ts/components/communications/workerMessages/HourlyReport.ts","../../../@salaxy/ng1/ts/components/communications/workerMessages/Timer.ts","../../../@salaxy/ng1/ts/components/communications/workerMessages/ExpenseReport.ts","../../../@salaxy/ng1/ts/components/communications/MessageThreadList.ts","../../../@salaxy/ng1/ts/components/form-controls/Datepicker.ts","../../../@salaxy/ng1/ts/components/form-controls/DatepickerPopup.ts","../../../@salaxy/ng1/ts/components/form-controls/DateRange.ts","../../../@salaxy/ng1/ts/components/form-controls/FormGroup.ts","../../../@salaxy/ng1/ts/components/form-controls/Input.ts","../../../@salaxy/ng1/ts/components/form-controls/InputAccountingTarget.ts","../../../@salaxy/ng1/ts/components/form-controls/InputBoolean.ts","../../../@salaxy/ng1/ts/components/form-controls/InputCollectiveBargainAgreement.ts","../../../@salaxy/ng1/ts/components/form-controls/InputEnum.ts","../../../@salaxy/ng1/ts/components/form-controls/InputCredential.ts","../../../@salaxy/ng1/ts/components/form-controls/InputDuration.ts","../../../@salaxy/ng1/ts/components/form-controls/InputIncomeType.ts","../../../@salaxy/ng1/ts/components/form-controls/InputNumber.ts","../../../@salaxy/ng1/ts/components/form-controls/InputOccupationType.ts","../../../@salaxy/ng1/ts/components/form-controls/InputRrule.ts","../../../@salaxy/ng1/ts/components/form-controls/InputTime.ts","../../../@salaxy/ng1/ts/components/form-controls/ToggleButtons.ts","../../../@salaxy/ng1/ts/components/form-controls/Textarea.ts","../../../@salaxy/ng1/ts/components/form-controls/ValidationSummary.ts","../../../@salaxy/ng1/ts/components/form-controls/InputTypeahead.ts","../../../@salaxy/ng1/ts/components/form-controls/InputPayStatsRowType.ts","../../../@salaxy/ng1/ts/components/form-controls/InputHolidayMultipliers.ts","../../../@salaxy/ng1/ts/components/form-controls/InputEmployeeGroup.ts","../../../@salaxy/ng1/ts/components/form-controls/InputMarkdown.ts","../../../@salaxy/ng1/ts/components/form-controls/MarkdownEditor.ts","../../../@salaxy/ng1/ts/components/form-controls/MarkdownViewer.ts","../../../@salaxy/ng1/ts/components/helpers/ActionButton.ts","../../../@salaxy/ng1/ts/components/helpers/Alert.ts","../../../@salaxy/ng1/ts/components/helpers/Avatar.ts","../../../@salaxy/ng1/ts/components/helpers/Calendar.ts","../../../@salaxy/ng1/ts/components/helpers/Chart.ts","../../../@salaxy/ng1/ts/components/helpers/DataMapper.ts","../../../@salaxy/ng1/ts/components/helpers/JsonFormatter.ts","../../../@salaxy/ng1/ts/components/helpers/NaviSitemap.ts","../../../@salaxy/ng1/ts/components/helpers/NaviStarterLayout.ts","../../../@salaxy/ng1/ts/components/helpers/Spinner.ts","../../../@salaxy/ng1/ts/components/helpers/Tab.ts","../../../@salaxy/ng1/ts/components/helpers/Tabs.ts","../../../@salaxy/ng1/ts/components/helpers/TabButtons.ts","../../../@salaxy/ng1/ts/components/helpers/UiTranslator.ts","../../../@salaxy/ng1/ts/components/helpers/import/DataImportComponentBase.ts","../../../@salaxy/ng1/ts/components/helpers/import/CalcImport.ts","../../../@salaxy/ng1/ts/components/helpers/import/CompanyImport.ts","../../../@salaxy/ng1/ts/components/helpers/import/ImportStaging.ts","../../../@salaxy/ng1/ts/components/helpers/import/WorkerImport.ts","../../../@salaxy/ng1/ts/components/helpers/JsonDiff.ts","../../../@salaxy/ng1/ts/components/invoices/CreditTransfer.ts","../../../@salaxy/ng1/ts/components/invoices/InvoiceEdit.ts","../../../@salaxy/ng1/ts/components/invoices/InvoiceList.ts","../../../@salaxy/ng1/ts/components/invoices/InvoicePaymentList.ts","../../../@salaxy/ng1/ts/components/invoices/InvoicePreview.ts","../../../@salaxy/ng1/ts/components/invoices/InvoicesCreate.ts","../../../@salaxy/ng1/ts/components/invoices/PaymentChannelInvoicePreview.ts","../../../@salaxy/ng1/ts/components/invoices/InvoiceTools.ts","../../../@salaxy/ng1/ts/components/invoices/InvoiceReport.ts","../../../@salaxy/ng1/ts/components/invoices/CompanyInvoices.ts","../../../@salaxy/ng1/ts/components/invoices/InvoiceAlerts.ts","../../../@salaxy/ng1/ts/components/obsolete/WorkerAssure.ts","../../../@salaxy/ng1/ts/components/odata/OdataFooter.ts","../../../@salaxy/ng1/ts/components/odata/OdataTable.ts","../../../@salaxy/ng1/ts/components/odata/OdataActions.ts","../../../@salaxy/ng1/ts/components/personal/AccountAuthorizationPerson.ts","../../../@salaxy/ng1/ts/components/personal/AccountAvatarEditPerson.ts","../../../@salaxy/ng1/ts/components/personal/AccountContactEditPerson.ts","../../../@salaxy/ng1/ts/components/personal/AccountDetailsPerson.ts","../../../@salaxy/ng1/ts/components/personal/AccountDetailsEditPerson.ts","../../../@salaxy/ng1/ts/components/personal/AccountInfoPerson.ts","../../../@salaxy/ng1/ts/components/personal/AccountInsuranceEditPerson.ts","../../../@salaxy/ng1/ts/components/personal/EmployerList.ts","../../../@salaxy/ng1/ts/components/personal/EmployerReport.ts","../../../@salaxy/ng1/ts/components/personal/EmployerSelect.ts","../../../@salaxy/ng1/ts/components/personal/CalcHouseholdUsecase.ts","../../../@salaxy/ng1/ts/components/personal/CalcSharing.ts","../../../@salaxy/ng1/ts/components/personal/CalcSharingInfo.ts","../../../@salaxy/ng1/ts/components/personal/HouseholdDeductionReport.ts","../../../@salaxy/ng1/ts/components/personal/WorkerReport.ts","../../../@salaxy/ng1/ts/components/personal/HouseholdYearList.ts","../../../@salaxy/ng1/ts/components/personal/HouseholdYearDetails.ts","../../../@salaxy/ng1/ts/components/report/AccountingReportList.ts","../../../@salaxy/ng1/ts/components/report/AccountingReportQuery.ts","../../../@salaxy/ng1/ts/components/report/AccountingReportRows.ts","../../../@salaxy/ng1/ts/components/report/AccountingReportTools.ts","../../../@salaxy/ng1/ts/components/report/AccountingReportViewer.ts","../../../@salaxy/ng1/ts/components/report/CalculationReport.ts","../../../@salaxy/ng1/ts/components/report/HolidayReport.ts","../../../@salaxy/ng1/ts/components/report/IrEarningsPayment.ts","../../../@salaxy/ng1/ts/components/report/IrEarningsPaymentList.ts","../../../@salaxy/ng1/ts/components/report/IrPayerSummary.ts","../../../@salaxy/ng1/ts/components/report/IrPayerSummaryList.ts","../../../@salaxy/ng1/ts/components/report/PayCertificate.ts","../../../@salaxy/ng1/ts/components/report/ReportList.ts","../../../@salaxy/ng1/ts/components/report/SalaryReportList.ts","../../../@salaxy/ng1/ts/components/report/AccountingRowReport.ts","../../../@salaxy/ng1/ts/components/report/SummaryReport.ts","../../../@salaxy/ng1/ts/components/report/WorkerSummaryReport.ts","../../../@salaxy/ng1/ts/components/report/AccountingHolidayPayDebtReportQuery.ts","../../../@salaxy/ng1/ts/components/report/HolidayPayReportQuery.ts","../../../@salaxy/ng1/ts/components/report/SummaryReportQuery.ts","../../../@salaxy/ng1/ts/components/report/PayStatsReportQuery.ts","../../../@salaxy/ng1/ts/components/settings/Accountant.ts","../../../@salaxy/ng1/ts/components/settings/AccountingSettings.ts","../../../@salaxy/ng1/ts/components/settings/AccountingTargetDetails.ts","../../../@salaxy/ng1/ts/components/settings/AccountingTargetSettings.ts","../../../@salaxy/ng1/ts/components/settings/CostAccountingSettings.ts","../../../@salaxy/ng1/ts/components/settings/HolidaySettings.ts","../../../@salaxy/ng1/ts/components/settings/Insurance.ts","../../../@salaxy/ng1/ts/components/settings/InsuranceSettings.ts","../../../@salaxy/ng1/ts/components/settings/OwnerSettings.ts","../../../@salaxy/ng1/ts/components/settings/PaymentChannelSettings.ts","../../../@salaxy/ng1/ts/components/settings/PaymentSettings.ts","../../../@salaxy/ng1/ts/components/settings/ProSettings.ts","../../../@salaxy/ng1/ts/components/settings/RowTypesSettings.ts","../../../@salaxy/ng1/ts/components/settings/ServiceModelDetails.ts","../../../@salaxy/ng1/ts/components/settings/IrDeliverySettings.ts","../../../@salaxy/ng1/ts/components/settings/PayStatsSettings.ts","../../../@salaxy/ng1/ts/components/sxy-form/SxyAlert.ts","../../../@salaxy/ng1/ts/components/sxy-form/SxyCodeEditor.ts","../../../@salaxy/ng1/ts/components/sxy-form/SxyFieldset.ts","../../../@salaxy/ng1/ts/components/sxy-form/SxyForm.ts","../../../@salaxy/ng1/ts/components/sxy-form/SxyGrid.ts","../../../@salaxy/ng1/ts/components/sxy-form/SxyInput.ts","../../../@salaxy/ng1/ts/components/sxy-form/SxySchemaEditor.ts","../../../@salaxy/ng1/ts/components/sxy-table/SxyTable.ts","../../../@salaxy/ng1/ts/components/test/AccountReset.ts","../../../@salaxy/ng1/ts/components/test/SmokeTest.ts","../../../@salaxy/ng1/ts/components/worker/holidays/HolidayYearAccrual.ts","../../../@salaxy/ng1/ts/components/worker/holidays/HolidayYearHolidays.ts","../../../@salaxy/ng1/ts/components/worker/holidays/HolidayYearPaid.ts","../../../@salaxy/ng1/ts/components/worker/holidays/WorkerHolidays.ts","../../../@salaxy/ng1/ts/components/worker/taxcard/EmploymentTaxcards.ts","../../../@salaxy/ng1/ts/components/worker/taxcard/TaxcardDetails.ts","../../../@salaxy/ng1/ts/components/worker/taxcard/TaxcardIncomeLog.ts","../../../@salaxy/ng1/ts/components/worker/taxcard/TaxcardManualEdit.ts","../../../@salaxy/ng1/ts/components/worker/taxcard/TaxCardsList.ts","../../../@salaxy/ng1/ts/components/worker/taxcard/TaxcardList.ts","../../../@salaxy/ng1/ts/components/worker/AbsencePeriods.ts","../../../@salaxy/ng1/ts/components/worker/EmploymentDetails.ts","../../../@salaxy/ng1/ts/components/worker/WorkerAbsences.ts","../../../@salaxy/ng1/ts/components/worker/WorkerDetails.ts","../../../@salaxy/ng1/ts/components/worker/EmploymentList.ts","../../../@salaxy/ng1/ts/components/workflow/CalendarEventDetails.ts","../../../@salaxy/ng1/ts/components/workflow/DatasetDetails.ts","../../../@salaxy/ng1/ts/components/workflow/UsecaseDetails.ts","../../../@salaxy/ng1/ts/components/workflow/Records.ts","../../../@salaxy/ng1/ts/components/workflow/WorkflowButtons.ts","../../../@salaxy/ng1/ts/components/workflow/WorkflowReopen.ts","../../../@salaxy/ng1/ts/components/workflow/WorkflowBadge.ts","../../../@salaxy/ng1/ts/components/_ComponentsRegistration.ts","../../../node_modules/.pnpm/angular-route@1.8.3/node_modules/angular-route/angular-route.js","../../../node_modules/.pnpm/angular-route@1.8.3/node_modules/angular-route/index.js","../../../node_modules/.pnpm/angular-i18n@1.8.3/node_modules/angular-i18n/angular-locale_fi.js","../../../node_modules/.pnpm/angular-ui-bootstrap@2.5.6/node_modules/angular-ui-bootstrap/dist/ui-bootstrap-tpls.js","../../../node_modules/.pnpm/angular-ui-bootstrap@2.5.6/node_modules/angular-ui-bootstrap/index.js","../../../node_modules/.pnpm/angular-sanitize@1.8.3/node_modules/angular-sanitize/angular-sanitize.js","../../../node_modules/.pnpm/angular-sanitize@1.8.3/node_modules/angular-sanitize/index.js","../../../node_modules/.pnpm/ng-file-upload@12.2.13/node_modules/ng-file-upload/dist/ng-file-upload-all.js","../../../node_modules/.pnpm/ng-file-upload@12.2.13/node_modules/ng-file-upload/index.js","../../../node_modules/.pnpm/angular-translate@2.19.1/node_modules/angular-translate/dist/angular-translate.js","../../../@salaxy/ng1/ts/controllers/_ControllersRegistration.ts","../../../@salaxy/ng1/ts/directives/AppendNodeDirective.ts","../../../node_modules/.pnpm/bootstrap@5.3.3_@popperjs+core@2.11.8/node_modules/bootstrap/dist/js/bootstrap.esm.js","../../../@salaxy/ng1/ts/directives/Bs5Tooltip.ts","../../../@salaxy/ng1/ts/directives/Bs5Popover.ts","../../../@salaxy/ng1/ts/directives/EnumParserFunctions.ts","../../../@salaxy/ng1/ts/directives/IfRoleDirective.ts","../../../@salaxy/ng1/ts/directives/IfSitemapDirective.ts","../../../@salaxy/ng1/ts/directives/LoaderDirective.ts","../../../@salaxy/ng1/ts/directives/OrderbyDirective.ts","../../../@salaxy/ng1/ts/directives/ValidatorFunctions.ts","../../../@salaxy/ng1/ts/directives/DatepickerInputValidationDirective.ts","../../../node_modules/.pnpm/marked@12.0.2/node_modules/marked/lib/marked.esm.js","../../../@salaxy/ng1/ts/directives/HtmlDirective.ts","../../../@salaxy/ng1/ts/directives/TextDirective.ts","../../../@salaxy/ng1/ts/directives/_DirectivesRegistration.ts","../../../@salaxy/ng1/ts/filters/FilterFunctions.ts","../../../@salaxy/ng1/ts/filters/_FiltersRegistration.ts","../../../@salaxy/ng1/ts/interceptors/LoaderInterceptor.ts","../../../@salaxy/ng1/ts/interceptors/TemplateInterceptor.ts","../../../@salaxy/ng1/ts/services/_ServicesRegistration.ts","../../../@salaxy/ng1/ts/components/_NgComponents.ts","../../../@salaxy/ng1/ts/templates/bootstrap.ts","../../../@salaxy/ng1/ts/web-personal/PersonalWebLegacyController.ts","../../../@salaxy/ng1/ts/web-personal/PersonalWebSiteMap.ts","../../../@salaxy/ng1/ts/web-personal/module-registration.ts"],"sourcesContent":["import { IQService } from \"angular\";\r\n\r\nimport { Ajax, Config, Configs, Cookies, Token } from \"@salaxy/core\";\r\n\r\n/**\r\n * The $http access to the server methods: GET, POST and DELETE\r\n * with different return types and authentication / error events.\r\n */\r\nexport class AjaxNg1 implements Ajax {\r\n\r\n    /**\r\n     * For NG-dependency injection\r\n     * @ignore\r\n     */\r\n    public static $inject = [\"$http\", \"$q\"];\r\n\r\n    /** Alert service for ajax. */\r\n    public static alertService: any;\r\n\r\n   /**\r\n    * By default (true) the token is set to salaxy-token -cookie.\r\n    * Disable cookies with this flag.\r\n    */\r\n    public useCookie = true;\r\n\r\n    /**\r\n     * By default credentials are not used in http-calls.\r\n     * Enable credentials with this flag.\r\n     */\r\n    public useCredentials = false;\r\n\r\n    /**\r\n     * The server address - root of the server\r\n     * This is settable field. Will probably be changed to a configuration object in the final version.\r\n     */\r\n    public serverAddress = \"https://test-api.salaxy.com\";\r\n\r\n    private token: string;\r\n\r\n    /**\r\n     * Creates a new instance of AjaxNg1\r\n     * @param $http - Angular http\r\n     * @param $q - Angular q\r\n     * @param config - Optional config containing keys which override the corresponding global Config keys.\r\n     */\r\n    constructor(private $http: angular.IHttpService, private $q: IQService, config: Config = null) {\r\n\r\n      const globalConfig = Configs.current;\r\n\r\n      if (globalConfig || config) {\r\n        // apiServer\r\n        const apiServer = config?.apiServer ?? globalConfig.apiServer;\r\n        if (apiServer) {\r\n          this.serverAddress = apiServer;\r\n        }\r\n\r\n        // useCredentials\r\n        const useCredentials = config?.useCredentials ?? globalConfig.useCredentials;\r\n        if (useCredentials != null) {\r\n          this.useCredentials = useCredentials;\r\n        }\r\n\r\n        // useCookie\r\n        const useCookie = config?.useCookie ?? globalConfig.useCookie;\r\n        if (useCookie != null) {\r\n          this.useCookie = useCookie;\r\n        }\r\n      }\r\n    }\r\n\r\n    /**\r\n     * Gets the API address with version information. E.g. 'https://test-api.salaxy.com/v03/api'.\r\n     * Default version, as of writing 2.0\r\n     */\r\n    public getApiAddress(): string {\r\n        return this.serverAddress + \"/v03/api\";\r\n    }\r\n\r\n    /** Gets the Server address that is used as bases to the HTML queries. E.g. 'https://test-api.salaxy.com' */\r\n    public getServerAddress(): string {\r\n        return this.serverAddress;\r\n    }\r\n\r\n    /**\r\n     * Gets a JSON-message from server using the API\r\n     * @param method The API method is the url path after the api version segments (e.g. '/v03/api')\r\n     * and starts with a forward slash, e.g. '/calculator/new'.\r\n     * @returns A Promise with result data. Standard Promise rejection to be used for error handling.\r\n     */\r\n    public getJSON(method: string): Promise<any> {\r\n\r\n        const request: any = {}; // angular.IRequestConfig\r\n\r\n        const token: string = this.getCurrentToken();\r\n        if (token) {\r\n            request.headers = { Authorization: \"Bearer \" + token };\r\n        }\r\n\r\n        request.url = this.getUrl(method);\r\n        request.method = \"GET\";\r\n        request.responseType = \"json\";\r\n        request.withCredentials = (token) ? false : this.useCredentials;\r\n\r\n        return this.$http(request).then(\r\n            (response) => response.data,\r\n            (error: any) => {\r\n                return this.handleError(error);\r\n            }) as any;\r\n    }\r\n\r\n    /**\r\n     * Gets a HTML-message from server using the API\r\n     * @param method - The API method is the url path after the api version segments (e.g. '/v03/api')\r\n     * and starts with a forward slash, e.g. '/calculator/new'.\r\n     * @returns A Promise with result data. Standard Promise rejection to be used for error handling.\r\n     */\r\n    public getHTML(method: string): Promise<string> {\r\n\r\n        const request: any = {}; // angular.IRequestConfig\r\n\r\n        const token: string = this.getCurrentToken();\r\n        if (token) {\r\n            request.headers = { Authorization: \"Bearer \" + token };\r\n        }\r\n\r\n        request.url = this.getUrl(method);\r\n        request.method = \"GET\";\r\n        request.responseType = \"text\";\r\n        request.withCredentials = (token) ? false : this.useCredentials;\r\n\r\n        return (this.$http(request).then(\r\n            (response) => {\r\n                return response.data;\r\n            },\r\n            (error: any) => {\r\n                return this.handleError(error);\r\n            }) as any\r\n        );\r\n    }\r\n\r\n    /**\r\n     * Gets a blob (binary data) from the server using the API.\r\n     * @param method - The API method is the url path after the api version segments (e.g. '/v03/api')\r\n     * and starts with a forward slash, e.g. '/calculator/new'.\r\n     * @returns A Promise that resolves to an object containing:\r\n     * - data: The blob data from the response\r\n     * - headers: An object containing the response headers as key-value pairs\r\n     */\r\n    public getBlob(method: string): Promise<{data: Blob, headers: {[key: string]: string}}> {\r\n      const request: any = {}; // angular.IRequestConfig\r\n\r\n        const token: string = this.getCurrentToken();\r\n        if (token) {\r\n            request.headers = { Authorization: \"Bearer \" + token };\r\n        }\r\n\r\n        request.url = this.getUrl(method);\r\n        request.method = \"GET\";\r\n        request.responseType = \"blob\";\r\n        request.withCredentials = (token) ? false : this.useCredentials;\r\n\r\n        return (this.$http(request).then(\r\n            (response) => {\r\n              const headers: {[key: string]: string} = {};\r\n              const headersObject = response.headers();\r\n              Object.keys(headersObject).forEach((key) => {\r\n                headers[key] = headersObject[key];\r\n              });\r\n              return {data: response.data, headers};\r\n            },\r\n            (error: any) => {\r\n                return this.handleError(error);\r\n            }) as any\r\n        );\r\n    }\r\n\r\n    /**\r\n     * POSTS data to server and receives back a blob (binary data).\r\n     * @param method - The API method is the url path after the api version segments (e.g. '/v03/api')\r\n     * and starts with a forward slash, e.g. '/calculator/new'.\r\n     * @param data - The data that is posted to the server.\r\n     * @returns A Promise that resolves to an object containing:\r\n     * - data: The blob data from the response\r\n     * - headers: An object containing the response headers as key-value pairs\r\n     */\r\n    public postBlob(method: string, data: any): Promise<{data: Blob, headers: {[key: string]: string}}> {\r\n      const request: any = {}; // angular.IRequestConfig\r\n\r\n      const token: string = this.getCurrentToken();\r\n      if (token) {\r\n          request.headers = { Authorization: \"Bearer \" + token };\r\n      }\r\n\r\n      request.url = this.getUrl(method);\r\n      request.method = \"POST\";\r\n      request.data = data;\r\n      request.responseType = \"blob\";\r\n      request.withCredentials = (token) ? false : this.useCredentials;\r\n\r\n      return (this.$http(request).then(\r\n        (response) => {\r\n          const headers: {[key: string]: string} = {};\r\n          const headersObject = response.headers();\r\n          Object.keys(headersObject).forEach((key) => {\r\n            headers[key] = headersObject[key];\r\n          });\r\n          return {data: response.data, headers};\r\n        },\r\n        (error: any) => {\r\n            return this.handleError(error);\r\n        }) as any\r\n      );\r\n    }\r\n\r\n    /**\r\n     * POSTS data to server and receives back a JSON-message.\r\n     * @param method - The API method is the url path after the api version segments (e.g. '/v03/api')\r\n     * and starts with a forward slash, e.g. '/calculator/new'.\r\n     * @param data - The data that is posted to the server.\r\n     * @returns A Promise with result data. Standard Promise rejection to be used for error handling.\r\n     */\r\n    public postJSON(method: string, data: any): Promise<any> {\r\n\r\n        const request: any = {}; // angular.IRequestConfig\r\n\r\n        const token: string = this.getCurrentToken();\r\n        if (token) {\r\n            request.headers = { Authorization: \"Bearer \" + token };\r\n        }\r\n\r\n        request.url = this.getUrl(method);\r\n        request.method = \"POST\";\r\n        request.data = data;\r\n        request.responseType = \"json\";\r\n        request.withCredentials = (token) ? false : this.useCredentials;\r\n\r\n        return (this.$http(request).then(\r\n            (response) => response.data,\r\n            (error: any) => {\r\n                return this.handleError(error);\r\n            }) as any\r\n        );\r\n    }\r\n\r\n    /**\r\n     * POSTS data to server and receives back HTML.\r\n     * @param method - The API method is the url path after the api version segments (e.g. '/v03/api')\r\n     * and starts with a forward slash, e.g. '/calculator/new'.\r\n     * @param data - The data that is posted to the server.\r\n     * @returns A Promise with result data. Standard Promise rejection to be used for error handling.\r\n     */\r\n    public postHTML(method: string, data: any): Promise<string> {\r\n\r\n        const request: any = {}; // angular.IRequestConfig\r\n\r\n        const token: string = this.getCurrentToken();\r\n        if (token) {\r\n            request.headers = { Authorization: \"Bearer \" + token };\r\n        }\r\n\r\n        request.url = this.getUrl(method);\r\n        request.method = \"POST\";\r\n        request.data = data;\r\n        request.responseType = \"text\";\r\n        request.withCredentials = (token) ? false : this.useCredentials;\r\n\r\n        return (this.$http(request).then(\r\n            (response) => response.data,\r\n            (error: any) => {\r\n                return this.handleError(error);\r\n            }) as any\r\n        );\r\n    }\r\n\r\n    /**\r\n     * Sends a DELETE-message to server using the API\r\n     * @param method - The API method is the url path after the api version segments (e.g. '/v03/api')\r\n     * and starts with a forward slash, e.g. '/calculator/new'.\r\n     * @returns A Promise with result data. Standard Promise rejection to be used for error handling.\r\n     */\r\n    public remove(method: string): Promise<any> {\r\n\r\n        const request: any = {}; // angular.IRequestConfig\r\n\r\n        const token: string = this.getCurrentToken();\r\n        if (token) {\r\n            request.headers = { Authorization: \"Bearer \" + token };\r\n        }\r\n\r\n        request.url = this.getUrl(method);\r\n        request.method = \"DELETE\";\r\n        request.responseType = \"json\";\r\n        request.withCredentials = (token) ? false : this.useCredentials;\r\n\r\n        return (this.$http(request).then(\r\n            (response) => {\r\n                return response.data;\r\n            },\r\n            (error: any) => {\r\n                return this.handleError(error);\r\n            }) as any\r\n        );\r\n    }\r\n\r\n    /**\r\n     * Gets the current token.\r\n     * Will check the salaxy-token cookie if the token is persisted there\r\n     */\r\n    public getCurrentToken(): string {\r\n        if (!this.token && this.useCookie) {\r\n            this.token = new Cookies().get(\"salaxy-token\") || \"\";\r\n        }\r\n        return this.token;\r\n    }\r\n\r\n    /** Gets the status of the current token. */\r\n    public getTokenStatus(): \"noToken\" | \"ok\" | \"expired\" | \"invalid\" {\r\n      const token = this.getCurrentToken();\r\n      return Token.validate(token);\r\n    }\r\n\r\n    /**\r\n     * Sets the current token. Persists it to cookie until the browser window\r\n     * @param token - the authentication token to persist.\r\n     */\r\n    public setCurrentToken(token: string | null): void {\r\n        const isStronglyAuthorizedPayer = !!Token.parsePayload(token ?? \"\")?.act;\r\n        if (this.useCookie && !isStronglyAuthorizedPayer) {\r\n            new Cookies().setCookie(\"salaxy-token\", token || \"\");\r\n        }\r\n        this.token = token;\r\n    }\r\n\r\n    /** If missing, append the API server address to the given url method string */\r\n    private getUrl(method: string): string {\r\n      if (!method || method.trim() === \"\") {\r\n        return null;\r\n      }\r\n      if (method.toLowerCase().startsWith(\"http\")) {\r\n        return method;\r\n      }\r\n      if (method.toLowerCase().startsWith(\"/v\")) {\r\n        return this.getServerAddress() + method;\r\n      }\r\n      return this.getApiAddress() + method;\r\n    }\r\n\r\n    private handleError(errorThrown: any): Promise<any> {\r\n        let msg: string;\r\n        if (errorThrown) {\r\n            if (errorThrown.data && errorThrown.data.messageHtml) {\r\n                msg = `<b>${errorThrown.data.error}:</b><br/>${errorThrown.data.messageHtml}`;\r\n            } else if (errorThrown.data && errorThrown.data.message) {\r\n                msg = errorThrown.data.message;\r\n            } else {\r\n                msg = `HTTP error: ${errorThrown.statusText} (${errorThrown.status})`;\r\n            }\r\n        } else {\r\n            msg = \"Unexpected error in HTTP request\";\r\n        }\r\n        if (AjaxNg1.alertService) {\r\n            if (AjaxNg1.alertService.catchError) {\r\n                return AjaxNg1.alertService.catchError(errorThrown);\r\n            } else {\r\n                AjaxNg1.alertService.addError(msg);\r\n            }\r\n        }\r\n        return this.$q.reject(errorThrown) as any;\r\n    }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { WizardService, WizardStep } from \"../../services\";\r\n\r\n/**\r\n * A generic Wizard controller for rendering the Wizard UI\r\n */\r\nexport class WizardController implements angular.IController {\r\n\r\n    /**\r\n     * For NG-dependency injection\r\n     * @ignore\r\n     */\r\n    public static $inject = [\"$scope\", \"WizardService\", \"data\"];\r\n\r\n    /** Styling classes for columns. */\r\n    public colWidthClasses = [\"col-sm-12\", \"col-sm-12\", \"col-sm-6\", \"col-sm-4\", \"col-sm-3\", \"col-sm-fifth\", \"col-sm-2\"];\r\n\r\n    /** Path for the view that is shown in the wizard */\r\n    public viewPath: string;\r\n\r\n    /** Path to the buttons view that is shown in the footer of the wizard */\r\n    public buttonsView?: string;\r\n\r\n    /**\r\n     * Creates a new WizardController\r\n     * @param $scope - The Angular scope\r\n     * @param wizardService - Maintains the state of the wizard\r\n     * @param data - Any data to the controller\r\n     * @ignore\r\n     */\r\n    constructor(\r\n        protected $scope: angular.IScope,\r\n        protected wizardService: WizardService,\r\n        protected data: any = null,\r\n    ) {\r\n    }\r\n\r\n    /**\r\n     * Implement IController\r\n     */\r\n    public $onInit() {\r\n        //\r\n    }\r\n\r\n    /** Gets all the steps in the Wizard */\r\n    public get steps(): WizardStep[] {\r\n        return this.wizardService.getSteps();\r\n    }\r\n\r\n    /** Gets the number of the currently active step */\r\n    public get step(): number {\r\n        return this.wizardService.activeStepNumber;\r\n    }\r\n    /** Sets the number of the currently active step */\r\n    public set step(stepNumber: number) {\r\n        this.wizardService.activeStepNumber = stepNumber;\r\n    }\r\n\r\n    /** The currently selected step object */\r\n    public get currentStep(): WizardStep {\r\n        return this.wizardService.getCurrentStepObject();\r\n    }\r\n\r\n    /** Active styling properties */\r\n    public get style() {\r\n        return {\r\n            colWidthClass: this.colWidthClasses[this.steps.length],\r\n        };\r\n    }\r\n\r\n    /** Returns true if goNext is enabled  */\r\n    public get canGoNext(): boolean {\r\n        if (this.steps.length > this.step) {\r\n            if (this.steps[this.step] && !this.steps[this.step].disabled) {\r\n                return true;\r\n            }\r\n        }\r\n        return false;\r\n    }\r\n\r\n    /** Returns true if goNext is enabled  */\r\n    public get canGoPrevious(): boolean {\r\n        if (this.step > 1 && !this.steps[this.step - 2].disabled) {\r\n            return true;\r\n        }\r\n        return false;\r\n    }\r\n\r\n    /**\r\n     * Navigates to the next step if possible\r\n     */\r\n    public goNext() {\r\n        if (this.canGoNext) {\r\n            this.step++;\r\n        }\r\n    }\r\n\r\n    /** Navigates to the previous step if possible */\r\n    public goPrevious() {\r\n        if (this.canGoPrevious) {\r\n            this.step--;\r\n        }\r\n    }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Ajax, Configs, Onboarding, PensionCompany,  SettingsLogic} from \"@salaxy/core\";\r\n\r\nimport { WizardController } from \"../../bases/WizardController\";\r\n\r\nimport { AuthorizedAccountService, OnboardingService, SessionService, WizardService, WizardStep } from \"../../../services\";\r\n\r\n/**\r\n * Wizard for Creating a new Palkkaus.fi company account by accountant\r\n */\r\nexport class CustomerOnboardingController extends WizardController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$scope\", \"WizardService\", \"OnboardingService\", \"SessionService\", \"AuthorizedAccountService\", \"AjaxNg1\", \"$location\", \"data\"];\r\n\r\n  /** Form data validity */\r\n  public formDataValidity: boolean;\r\n\r\n  /** If true, step is proceeding */\r\n  public isStepProceeding = false;\r\n\r\n  /** Copy indicator */\r\n  public linkCopied = false;\r\n  constructor(\r\n    $scope: angular.IScope,\r\n    wizardService: WizardService,\r\n    private onboardingService: OnboardingService,\r\n    private sessionService: SessionService,\r\n    private authorizedAccountService: AuthorizedAccountService,\r\n    private ajax: Ajax,\r\n    private $location: angular.ILocationService,\r\n    data: any,\r\n  ) {\r\n    super($scope, wizardService, data);\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    this.wizardService.setSteps(this.getWizardSteps());\r\n    if (this.model &&\r\n      this.model.company.resolvedId &&\r\n      this.model.signature.personalId != null) {\r\n      this.wizardService.activeStepNumber = this.wizardService.getSteps().length;\r\n      // suomi.fi-->\r\n      // } else if (this.model && this.model.signature.isProcura) {\r\n      //   this.wizardService.activeStepNumber = 2;\r\n      // <--suomi.fi\r\n    } else {\r\n      this.wizardService.activeStepNumber = 1;\r\n    }\r\n  }\r\n\r\n  /** Company wizard configuration */\r\n  public getWizardSteps(): WizardStep[] {\r\n    const steps: WizardStep[] = [];\r\n    steps.push(\r\n      {\r\n        title: \"SALAXY.NG1.CustomerOnboardingComponent.stepUserInfo.title\",\r\n        heading: \"\",\r\n        intro: \"\",\r\n        view: \"salaxy-components/modals/onboarding/customer/user.html\",\r\n        buttonsView: \"salaxy-components/modals/onboarding/customer/user-buttons.html\",\r\n      },\r\n      {\r\n        title: \"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyInfo.title\",\r\n        heading: \"\",\r\n        intro: \"\",\r\n        view: \"salaxy-components/modals/onboarding/customer/company.html\",\r\n        buttonsView: \"salaxy-components/modals/onboarding/customer/buttons.html\",\r\n      },\r\n      {\r\n        title: \"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyLegal.title\",\r\n        heading: \"\",\r\n        intro: \"\",\r\n        view: \"salaxy-components/modals/onboarding/customer/company-legal.html\",\r\n        buttonsView: \"salaxy-components/modals/onboarding/customer/buttons.html\",\r\n      },\r\n      {\r\n        title: \"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.title\",\r\n        heading: \"\",\r\n        intro: \"\",\r\n        view: \"salaxy-components/modals/onboarding/customer/insurance.html\",\r\n        buttonsView: \"salaxy-components/modals/onboarding/customer/commit-buttons.html\",\r\n      },\r\n      {\r\n        title: \"SALAXY.NG1.CustomerOnboardingComponent.stepInviteCompany.title\",\r\n        heading: \"\",\r\n        intro: \"\",\r\n        view: \"salaxy-components/modals/onboarding/customer/finish.html\",\r\n        buttonsView: \"salaxy-components/modals/onboarding/customer/finish-buttons.html\",\r\n      });\r\n    return steps;\r\n  }\r\n\r\n  /**\r\n   * The onboarding model is provided by the onboarding service.\r\n   *\r\n   */\r\n  public get model(): Onboarding {\r\n    return this.onboardingService.model;\r\n  }\r\n\r\n  /**\r\n   * Navigates to the next step if possible and saves the data.\r\n   */\r\n  public goNext() {\r\n    if (this.isStepProceeding) {\r\n      return;\r\n    }\r\n    this.isStepProceeding = true;\r\n    this.save().then(() => {\r\n      super.goNext();\r\n      this.isStepProceeding = false;\r\n    })\r\n      .catch((reason) => {\r\n        this.isStepProceeding = false;\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Navigates to the previous step if possible and saves the data.\r\n   */\r\n  public goPrevious() {\r\n    if (this.isStepProceeding) {\r\n      return;\r\n    }\r\n    this.isStepProceeding = true;\r\n    this.save().then(() => {\r\n      super.goPrevious();\r\n      this.isStepProceeding = false;\r\n    })\r\n      .catch((reason) => {\r\n        this.isStepProceeding = false;\r\n      });\r\n  }\r\n\r\n  /** Returns true if user can go forward in wizard  */\r\n  public get canGoNext(): boolean {\r\n    if (this.steps.length > this.step) {\r\n      if (this.steps[this.step] && !this.steps[this.step].disabled) {\r\n        if (this.formDataValidity) {\r\n          return true;\r\n        }\r\n      }\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /** Sharing link for singing. */\r\n  public get signingLink(): string {\r\n    if (!this.model) {\r\n      return \"\";\r\n    }\r\n    return Configs.current.wwwServer + \"/share/signing/\" + encodeURIComponent(this.model.owner) + \"/\" + this.model.id;\r\n  }\r\n\r\n  /** Sharing link for authorization mail. */\r\n  public get sharingLink(): string {\r\n    if (!this.model) {\r\n      return \"\";\r\n    }\r\n    return Configs.current.wwwServer + \"/share/authorization/\" + encodeURIComponent(this.model.owner) + \"/\" + this.model.id;\r\n  }\r\n\r\n  /** Copies link to clipboard */\r\n  public copyLink(link: string) {\r\n    (navigator as any).clipboard.writeText(link);\r\n    this.linkCopied = true;\r\n  }\r\n\r\n  /** Mailto-link with sharing link. */\r\n  public get mailtoLink(): string {\r\n    if (!this.model || !this.model.person) {\r\n      return \"\";\r\n    }\r\n    let link = \"mailto:\";\r\n    link += this.model.person.contact.email;\r\n    link += \"?subject=\" + encodeURIComponent(\"Palkkaus.fi-palvelun valtakirjan allekirjoitus\");\r\n\r\n    let body = \"Hei \" + this.model.person.firstName + \" \" + this.model.person.lastName + \",\\n\\n\";\r\n    body += \"Olemme ottamassa käyttöön Palkkaus.fi-palvelun yrityksesi palkanmaksuun.\";\r\n    body += \" Jotta he voivat hoitaa kaikki viranomaisvelvoitteet, tarvitaan allekirjoitus sinulta.\";\r\n    body += \" Se hoituu helposti pankkitunnuksilla seuraamalla tätä linkkiä: \";\r\n    body += this.sharingLink + \". \\n\\n\";\r\n    body += \"Ystävällisin terveisin, \\n\";\r\n    body += this.sessionService.getAvatar().displayName;\r\n    link += \"&body=\" + encodeURIComponent(body);\r\n    return link;\r\n  }\r\n\r\n  /**\r\n   * Existing company alert.\r\n   */\r\n  public get existingCompanyAlert(): boolean {\r\n    const currentAccountId = this.sessionService.session?.currentAccount?.id;\r\n    // existing account in the system and is different than current account\r\n    return this.model?.company?.resolvedId &&\r\n           this.model.company.resolvedId != currentAccountId;\r\n  }\r\n\r\n  /**\r\n   * Proceeds to company selection in e-authorization service.\r\n   */\r\n  public goToCompanySelection(): void {\r\n\r\n    /*  suomi.fi-->\r\n    const rawUrl = this.$location.url();\r\n    let baseUrl = this.$location.absUrl();\r\n    if (rawUrl.length > 1) {\r\n      baseUrl = baseUrl.substring(0, baseUrl.indexOf(rawUrl));\r\n    }\r\n    baseUrl = baseUrl.replace(/\\/$/, \"\");\r\n    const accessToken = this.ajax.getCurrentToken();\r\n    const token = accessToken ? `${encodeURIComponent(accessToken)}` : \"\";\r\n    const cancelUrl = `${baseUrl}/onboarding/customer/${this.model.id}${token ? \"&ob_token=\" + token : \"\"}`;\r\n    const successUrl = `${baseUrl}/onboarding/customer/${this.model.id}${token ? \"&ob_token=\" + token : \"\"}`;\r\n    this.save().then(() => {\r\n      window.location.assign(`${this.ajax.getServerAddress()}/Onboarding/CompanySelection?OnboardingId=${encodeURIComponent(this.model.id)}&SuccessUrl=${encodeURIComponent(successUrl)}&CancelUrl=${encodeURIComponent(cancelUrl)}${token ? \"&access_token=\" + token : \"\"}`);\r\n    });\r\n     <--suomi.fi*/\r\n    this.model.company.doYtjUpdate = true;\r\n    this.goNext();\r\n  }\r\n\r\n  /** Commit onboarding */\r\n  public commit(): void {\r\n    if (this.isStepProceeding) {\r\n      return;\r\n    }\r\n    this.isStepProceeding = true;\r\n    this.model.signature.email = this.model.person.contact.email;\r\n    this.model.signature.telephone = this.model.person.contact.telephone;\r\n    this.model.signature.personName = (this.model.person.firstName + \" \" + this.model.person.lastName).trim();\r\n\r\n    this.onboardingService.commit().then(() => {\r\n      // refresh authorizing accounts\r\n      this.authorizedAccountService.reloadAuthorizingAccounts();\r\n      super.goNext();\r\n      this.isStepProceeding = false;\r\n    })\r\n      .catch((reason) => {\r\n        this.isStepProceeding = false;\r\n      });\r\n  }\r\n\r\n  /** Sets pension fields (defaults) after user input. */\r\n  public checkPensionCompanySelection() {\r\n\r\n    if (!this.model.products.pension.isPensionContractDone) {\r\n      this.model.products.pension.pensionCompany = PensionCompany.None;\r\n      this.model.products.pension.pensionContractNumber = null;\r\n    }\r\n    const pensionCompany = this.model.products.pension.pensionCompany;\r\n    if (this.model.products.pension.isPensionContractDone && pensionCompany === PensionCompany.Varma) {\r\n      this.model.products.pension.isPendingContract = false;\r\n    }\r\n    // If the company is one that Palkkaus.fi/Salaxy does not have a process with, user is forced to take care of pension themselves\r\n    if (pensionCompany === PensionCompany.Veritas ||\r\n      pensionCompany === PensionCompany.Apteekkien ||\r\n      pensionCompany === PensionCompany.Verso ||\r\n      pensionCompany === PensionCompany.Valio ||\r\n      (pensionCompany ?? \"\").startsWith(\"keva\") ||\r\n      pensionCompany === PensionCompany.Other) {\r\n      this.model.products.pension.isPensionSelfHandling = true;\r\n    }\r\n    // Check if pending contract\r\n    if (this.model.products.pension.isPendingContract) {\r\n      this.model.products.pension.isPensionSelfHandling = false;\r\n    }\r\n  }\r\n\r\n  /** Sets insurance fields (defaults) after user input. */\r\n  public checkInsuranceCompanySelection() {\r\n    if (!this.model.products.insurance.isInsuranceContractDone) {\r\n      this.model.products.insurance.insuranceCompany = null;\r\n      this.model.products.insurance.insuranceContractNumber = null;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Saves the data to server\r\n   */\r\n  public save(): Promise<Onboarding> {\r\n    return this.onboardingService.save();\r\n  }\r\n\r\n  /**\r\n   * Sets the pension contract number as a test number according to the selected company.\r\n   */\r\n  public setPensionNumberForTest() {\r\n    this.model.products.pension.pensionContractNumber = SettingsLogic.getPensionNumberForTest(this.model.products.pension.pensionCompany);\r\n  }\r\n\r\n  /**\r\n   * Launches the wizard.\r\n   * @param accountId Optional account id.\r\n   */\r\n  public launch(accountId: string = null): Promise<any> {\r\n    return this.onboardingService.launchCustomerOnboarding(accountId);\r\n  }\r\n\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { ApiValidationError, Onboarding } from \"@salaxy/core\";\r\n\r\nimport { OnboardingService, SessionService, UiHelpers, WizardService, WizardStep, SignatureService } from \"../../../services\";\r\n\r\nimport { WizardController } from \"../../bases/WizardController\";\r\n\r\n/**\r\n * Wizard for Creating a new Palkkaus.fi-account (worker)\r\n */\r\nexport class WorkerOnboardingController extends WizardController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$scope\", \"WizardService\", \"OnboardingService\", \"SessionService\", \"UiHelpers\", \"SignatureService\"];\r\n\r\n  /** Worker wizard configuration */\r\n  public wizardSteps: WizardStep[] = [\r\n    {\r\n      title: \"SALAXY.NG1.WorkerOnboardingComponent.stepUserInfo.title\",\r\n      heading: \"SALAXY.NG1.WorkerOnboardingComponent.stepUserInfo.heading\",\r\n      intro: \"\",\r\n      active: true,\r\n      view: \"salaxy-components/modals/onboarding/worker/user-info.html\",\r\n      buttonsView: \"salaxy-components/modals/onboarding/worker/firstPageButtons.html\",\r\n    },\r\n    /*\r\n    {\r\n      title: \"SALAXY.NG1.WorkerOnboardingComponent.stepPhoneNumberVerify.title\",\r\n      heading: \"SALAXY.NG1.WorkerOnboardingComponent.stepPhoneNumberVerify.heading\",\r\n      intro: \"SALAXY.NG1.WorkerOnboardingComponent.stepPhoneNumberVerify.intro\",\r\n      view: \"salaxy-components/modals/onboarding/worker/phonenumber-verify.html\",\r\n      buttonsView: \"salaxy-components/modals/onboarding/worker/phoneNumberVerifyButtons.html\",\r\n    },\r\n    */\r\n    {\r\n      title: \"SALAXY.NG1.WorkerOnboardingComponent.stepContract.stepTitle\",\r\n      heading: \"SALAXY.NG1.WorkerOnboardingComponent.stepContract.heading\",\r\n      intro: \"SALAXY.NG1.WorkerOnboardingComponent.stepContract.intro\",\r\n      view: \"salaxy-components/modals/onboarding/worker/contract-worker.html\",\r\n      buttonsView: \"salaxy-components/modals/onboarding/worker/contractButtons.html\",\r\n    },\r\n  ];\r\n\r\n  /**\r\n   * Field to expose forms validity state.\r\n   */\r\n  public formDataValidity: boolean;\r\n\r\n  /** If true, step is proceeding */\r\n  public isStepProceeding = false;\r\n\r\n  public signatureMethods: any[];\r\n\r\n  constructor(\r\n    $scope: angular.IScope,\r\n    wizardService: WizardService,\r\n    private onboardingService: OnboardingService,\r\n    private sessionService: SessionService,\r\n    private uiHelpers: UiHelpers,\r\n    private signatureService: SignatureService\r\n  ) {\r\n    super($scope, wizardService);\r\n  }\r\n\r\n   /**\r\n    * Implement IController\r\n    */\r\n   public $onInit() {\r\n    this.wizardService.setSteps(this.wizardSteps);\r\n    this.wizardService.activeStepNumber = 1;\r\n    this.getSignatureMethods();\r\n  }\r\n\r\n  /**\r\n   * Navigates to the next step if possible and saves the data.\r\n   */\r\n  public goNext(): Promise<boolean> {\r\n    if (this.isStepProceeding) {\r\n      return Promise.resolve(false);\r\n    }\r\n    this.isStepProceeding = true;\r\n    return this.save().then(() => {\r\n      super.goNext();\r\n      this.isStepProceeding = false;\r\n      return true;\r\n    }).catch((reason) => {\r\n      this.isStepProceeding = false;\r\n      return false;\r\n    });\r\n  }\r\n\r\n  /** Returns true if user can go forward in wizard  */\r\n  public get canGoNext(): boolean {\r\n    if (this.steps.length > this.step) {\r\n      if (this.steps[this.step] && !this.steps[this.step].disabled) {\r\n        if (this.formDataValidity) {\r\n          /* if (this.model.validation.isOfficialIdUnique == true){ */\r\n          return true;\r\n          /* } */\r\n        }\r\n      }\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /** Runs a check function before going forward */\r\n\r\n  public goNextIf(checkFunction: (goNext: () => Promise<boolean>) => void) {\r\n    checkFunction(() => this.goNext());\r\n  }\r\n\r\n  /**\r\n   * Navigates to the previous step if possible and saves the data.\r\n   */\r\n  public goPrevious() {\r\n    if (this.isStepProceeding) {\r\n      return;\r\n    }\r\n    this.isStepProceeding = true;\r\n    this.save().then(() => {\r\n      super.goPrevious();\r\n      this.isStepProceeding = false;\r\n    })\r\n      .catch((reason) => {\r\n        this.isStepProceeding = false;\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Saves the data to server\r\n   */\r\n  public save(): Promise<Onboarding> {\r\n    this.model.signature.email = this.model.person.contact.email;\r\n    this.model.signature.telephone = this.model.person.contact.telephone;\r\n    this.model.signature.personName = (this.model.person.firstName + \" \" + this.model.person.lastName).trim();\r\n    return this.onboardingService.save();\r\n  }\r\n\r\n  /**\r\n   * Returns signing url.\r\n   */\r\n  public get vismaSignUrl(): string {\r\n    // HACK: Get rid of this: Use this.model.signature.digitalSignature.auth_service instead.\r\n    const method = (this.model.signature as any).method;\r\n    return this.onboardingService.getDigitalSignUrl(method);\r\n  }\r\n\r\n  /**\r\n   * The onboarding model is provided by the onboarding service.\r\n   */\r\n  public get model(): Onboarding {\r\n    return this.onboardingService.model;\r\n  }\r\n\r\n  /** Returns the PDF preview address for the authorization pdf. */\r\n  public getPdfPreviewAddress() {\r\n    return this.onboardingService.getPdfPreviewAddress();\r\n  }\r\n\r\n  /**\r\n   * Returns validation error for key if exists.\r\n   * @param key - Validation error key.\r\n   */\r\n  public getValidationError(key: string): ApiValidationError {\r\n    if (this.model && this.model.validation) {\r\n      return this.model.validation.errors.find((x) => x.key === key);\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /**\r\n   * Resets validation error for key if exists.\r\n   * @param key - Validation error key.\r\n   */\r\n  public removeValidationError(key: string): void {\r\n    if (this.model && this.model.validation) {\r\n      (this.model.validation as any).errors = this.model.validation.errors.filter((x) => x.key !== key);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Checks if the given string is other identifier than Finnish Personal Identification Number\r\n   * @param ssn given social security number\r\n   */\r\n  public isOtherIdentifier(ssn: string){\r\n\r\n    /** 8th character is 9 */\r\n    const regex = /^.{7}[9]/;\r\n    return regex.test((ssn || \"\").trim());\r\n  }\r\n\r\n  /**\r\n   * Launches the wizard.\r\n   * @param id Optional onboarding id.\r\n   */\r\n  public launch(id: string = null): Promise<any> {\r\n    return this.onboardingService.launchWorkerOnboarding(id);\r\n  }\r\n\r\n  private getSignatureMethods(): void {\r\n    const signatureMethods = this.signatureService.getMethods(\"telia\");\r\n\r\n    this.signatureMethods = signatureMethods\r\n      .map(method => ({\r\n        value: method.value,\r\n        label: method.title,\r\n        imgSrc: method.img,\r\n      }));\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { ApiValidationError, Onboarding } from \"@salaxy/core\";\r\n\r\nimport { OnboardingService, SessionService, SignatureService, WizardService, WizardStep } from \"../../../services\";\r\nimport { WizardController } from \"../../bases/WizardController\";\r\n\r\n/**\r\n * Wizard for Creating a new Palkkaus.fi-account for a household.\r\n */\r\nexport class HouseholdOnboardingController extends WizardController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$scope\", \"WizardService\", \"OnboardingService\", \"SessionService\", \"SignatureService\", \"data\"];\r\n\r\n  /** Household wizard configuration */\r\n  public wizardSteps: WizardStep[] = [\r\n    {\r\n      title: \"Käyttäjän tiedot\",\r\n      heading: \"Tervetuloa, Palkkamyllyyn!\",\r\n      intro: `Palkkamyllyn tarjoaa Rakennusliitto ry, joka toimii henkilötietojen käsittelijänä ja vastaa myös asiakaspalvelusta.\\n\\nPalvelun tuottajana, teknisenä toteuttajana ja myös henkilötietojen käsittelijä toimii Suomen Palkanlaskenta Oy (Palkkaus.fi).`,\r\n      active: true,\r\n      view: \"salaxy-components/modals/onboarding/household/wizard_index.html\",\r\n      buttonsView: \"salaxy-components/modals/onboarding/household/firstPageButtons.html\",\r\n    },\r\n    /*\r\n    {\r\n      title: \"Puhelinnumero\",\r\n      heading: \"Puhelinnumero\",\r\n      intro: \"Puhelinnumeroa tarvitsemme yhteydenpitoa varten. Jos rekisteröit Siirto-palvelussa olevan puhelinnumeron, voit maksaa ja vastaanottaa palkkoja mobiilimaksuilla. Vahvistamme antamasi numeron.\",\r\n      view: \"salaxy-components/modals/onboarding/household/phoneNumber.html\",\r\n      buttonsView: \"salaxy-components/modals/onboarding/household/phoneNumberButtons.html\",\r\n    },\r\n    {\r\n      title: \"Puhelinnumeron vahvistaminen\",\r\n      heading: \"Puhelinnumeron vahvistaminen\",\r\n      intro: \"Olemme lähettäneet sinulle SMS-viestin varmistaaksemme numerosi. Syötä viestissä oleva vahvistuskoodi tähän.\",\r\n      view: \"salaxy-components/modals/onboarding/household/phoneNumberVerify.html\",\r\n      buttonsView: \"salaxy-components/modals/onboarding/household/phoneNumberVerifyButtons.html\",\r\n    },\r\n    */\r\n    {\r\n      title: \"Palkanmaksun tiedot\",\r\n      heading: \"Palkanmaksun tiedot\",\r\n      view: \"salaxy-components/modals/onboarding/household/household.html\",\r\n      buttonsView: \"salaxy-components/modals/onboarding/household/householdButtons.html\",\r\n    },\r\n    {\r\n      title: \"Palvelusopimus\",\r\n      heading: \"Palvelusopimus ja valtuutus\",\r\n      view: \"salaxy-components/modals/onboarding/household/contract.html\",\r\n      buttonsView: \"salaxy-components/modals/onboarding/household/contractButtons.html\",\r\n    },\r\n  ];\r\n\r\n  /**\r\n   * Field to expose forms validity state.\r\n   */\r\n  public formDataValidity: boolean;\r\n\r\n  /** If true, step is proceeding */\r\n  public isStepProceeding = false;\r\n\r\n  public visibleSignatureMethods: object;\r\n\r\n  constructor(\r\n    $scope: angular.IScope,\r\n    wizardService: WizardService,\r\n    private onboardingService: OnboardingService,\r\n    private sessionService: SessionService,\r\n    private signatureService: SignatureService,\r\n    data: any,\r\n  ) {\r\n    super($scope, wizardService, data);\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    this.wizardService.setSteps(this.wizardSteps);\r\n    this.wizardService.activeStepNumber = 1;\r\n    const signatureMethods = this.signatureService.getMethods(\"telia\");\r\n\r\n    this.visibleSignatureMethods = signatureMethods\r\n      .filter(method => method.isPopular)\r\n      .map(method => ({\r\n        value: method.value,\r\n        label: method.title,\r\n        imgSrc: method.img,\r\n      }));\r\n  }\r\n\r\n  /**\r\n   * Navigates to the next step if possible and saves the data.\r\n   */\r\n  public goNext(): Promise<boolean> {\r\n    if (this.isStepProceeding) {\r\n      return Promise.resolve(false);\r\n    }\r\n    this.isStepProceeding = true;\r\n    return this.save().then(() => {\r\n      super.goNext();\r\n      this.isStepProceeding = false;\r\n      return true;\r\n    }).catch((reason) => {\r\n      this.isStepProceeding = false;\r\n      return false;\r\n    });\r\n  }\r\n\r\n  /** Returns true if user can go forward in wizard  */\r\n  public get canGoNext(): boolean {\r\n    if (this.steps.length > this.step) {\r\n      if (this.steps[this.step] && !this.steps[this.step].disabled) {\r\n        if (this.formDataValidity) {\r\n          /* if (this.model.validation.isOfficialIdUnique == true){ */\r\n          return true;\r\n          /* } */\r\n        }\r\n      }\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /** Runs a check function before going forward */\r\n\r\n  public goNextIf(checkFunction: (goNext: () => Promise<boolean>) => void) {\r\n    checkFunction(() => this.goNext());\r\n  }\r\n\r\n  /**\r\n   * Navigates to the previous step if possible and saves the data.\r\n   */\r\n  public goPrevious() {\r\n    if (this.isStepProceeding) {\r\n      return;\r\n    }\r\n    this.isStepProceeding = true;\r\n    this.save().then(() => {\r\n      super.goPrevious();\r\n      this.isStepProceeding = false;\r\n    })\r\n      .catch((reason) => {\r\n        this.isStepProceeding = false;\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Saves the data to server\r\n   */\r\n  public save(): Promise<Onboarding> {\r\n    this.model.signature.email = this.model.person.contact.email;\r\n    this.model.signature.telephone = this.model.person.contact.telephone;\r\n    this.model.signature.personName = (this.model.person.firstName + \" \" + this.model.person.lastName).trim();\r\n    return this.onboardingService.save();\r\n  }\r\n\r\n  /**\r\n   * Returns signing url.\r\n   */\r\n  public get vismaSignUrl(): string {\r\n    // HACK: Get rid of this: Use this.model.signature.digitalSignature.auth_service instead.\r\n    const method = (this.model.signature as any).method;\r\n    return this.onboardingService.getDigitalSignUrl(method);\r\n  }\r\n\r\n  /**\r\n   * The onboarding model is provided by the onboarding service.\r\n   */\r\n  public get model(): Onboarding {\r\n    return this.onboardingService.model;\r\n  }\r\n\r\n  /** Returns the PDF preview address for the authorization pdf. */\r\n  public getPdfPreviewAddress() {\r\n    return this.onboardingService.getPdfPreviewAddress();\r\n  }\r\n\r\n  /**\r\n   * Returns validation error for key if exists.\r\n   * @param key - Validation error key.\r\n   */\r\n  public getValidationError(key: string): ApiValidationError {\r\n    if (this.model && this.model.validation) {\r\n      return this.model.validation.errors.find((x) => x.key === key);\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /**\r\n   * Resets validation error for key if exists.\r\n   * @param key - Validation error key.\r\n   */\r\n  public removeValidationError(key: string): void {\r\n    if (this.model && this.model.validation) {\r\n      (this.model.validation as any).errors = this.model.validation.errors.filter((x) => x.key !== key);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Launches the wizard.\r\n   * @param id Optional onboarding id.\r\n   */\r\n  public launch(id: string = null): Promise<any> {\r\n    return this.onboardingService.launchHouseholdOnboarding(id);\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Ajax, ApiValidationError, Onboarding, Role, Translations } from \"@salaxy/core\";\r\n\r\nimport { OnboardingService, SessionService, WizardService, WizardStep, UiHelpers } from \"../../../services\";\r\nimport { WizardController } from \"../../bases/WizardController\";\r\n\r\n/**\r\n * Wizard for creating a new Palkkaus.fi-account for a company.\r\n */\r\nexport class CompanyOnboardingController extends WizardController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$scope\", \"WizardService\", \"OnboardingService\", \"SessionService\", \"AjaxNg1\", \"$location\", \"data\", \"UiHelpers\"];\r\n\r\n  /**\r\n   * Field to expose forms validity state.\r\n   */\r\n  public formDataValidity: boolean;\r\n\r\n  /** If true, step is proceeding */\r\n  public isStepProceeding = false;\r\n\r\n  constructor(\r\n    $scope: angular.IScope,\r\n    wizardService: WizardService,\r\n    private onboardingService: OnboardingService,\r\n    private sessionService: SessionService,\r\n    private ajax: Ajax,\r\n    private $location: angular.ILocationService,\r\n    data: any,\r\n    private uiHelpers: UiHelpers,\r\n  ) {\r\n    super($scope, wizardService, data);\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n\r\n    this.wizardService.setSteps(this.getWizardSteps());\r\n    if (this.model && this.model.signature.isProcura) {\r\n      this.wizardService.activeStepNumber = 3;\r\n    } else {\r\n      this.wizardService.activeStepNumber = 1;\r\n    }\r\n  }\r\n\r\n  /** Company wizard configuration */\r\n  public getWizardSteps(): WizardStep[] {\r\n    const steps: WizardStep[] = [];\r\n    steps.push(\r\n      {\r\n        title: \"SALAXY.NG1.CompanyOnboardingComponent.step1.title\",\r\n        intro: \"SALAXY.NG1.CompanyOnboardingComponent.step1.intro\",\r\n        active: true,\r\n        view: \"salaxy-components/modals/onboarding/company/wizard_index.html\",\r\n        buttonsView: \"salaxy-components/modals/onboarding/company/firstPageButtons.html\",\r\n      });\r\n    if (this.showCompanySelection) {\r\n      steps.push(\r\n        {\r\n          title: \"SALAXY.NG1.CompanyOnboardingComponent.stepSuomiFi.title\",\r\n          intro: \"SALAXY.NG1.CompanyOnboardingComponent.stepSuomiFi.intro\",\r\n          view: \"salaxy-components/modals/onboarding/company/suomifi.html\",\r\n          buttonsView: \"salaxy-components/modals/onboarding/company/suomifiButtons.html\",\r\n        });\r\n    }\r\n    steps.push(\r\n      {\r\n        title: \"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.title\",\r\n        intro: \"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.intro\",\r\n        view: \"salaxy-components/modals/onboarding/company/company.html\",\r\n        buttonsView: \"salaxy-components/modals/onboarding/company/defaultWizardButtons.html\",\r\n      },\r\n      /*\r\n      {\r\n        title: \"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyLegal.title\",\r\n        view: \"salaxy-components/modals/onboarding/company/company-legal.html\",\r\n        buttonsView: \"salaxy-components/modals/onboarding/company/defaultWizardButtons.html\",\r\n      },\r\n      */\r\n      {\r\n        title: \"SALAXY.NG1.CompanyOnboardingComponent.stepContract.title\",\r\n        view: \"salaxy-components/modals/onboarding/company/contract.html\",\r\n        buttonsView: \"salaxy-components/modals/onboarding/company/contractButtons.html\",\r\n      },\r\n    );\r\n    return steps;\r\n  }\r\n\r\n  /**\r\n   * Navigates to the next step if possible and saves the data.\r\n   */\r\n  public goNext(): Promise<boolean> {\r\n    if (this.isStepProceeding) {\r\n      return Promise.resolve(false);\r\n    }\r\n    this.isStepProceeding = true;\r\n    return this.save().then(() => {\r\n      super.goNext();\r\n      this.isStepProceeding = false;\r\n      return true;\r\n    }).catch((reason) => {\r\n      this.isStepProceeding = false;\r\n      return false;\r\n    });\r\n  }\r\n\r\n  /** Returns true if user can go forward in wizard  */\r\n  public get canGoNext(): boolean {\r\n    if (this.steps.length > this.step) {\r\n      if (this.steps[this.step] && !this.steps[this.step].disabled) {\r\n        if (this.formDataValidity) {\r\n          /* if (this.model.validation.isOfficialIdUnique == true){ */\r\n          return true;\r\n          /* } */\r\n        }\r\n      }\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /**\r\n   * Navigates to the previous step if possible and saves the data.\r\n   */\r\n  public goPrevious() {\r\n    if (this.isStepProceeding) {\r\n      return;\r\n    }\r\n    this.isStepProceeding = true;\r\n    this.save().then(() => {\r\n      super.goPrevious();\r\n      this.isStepProceeding = false;\r\n    })\r\n      .catch((reason) => {\r\n        this.isStepProceeding = false;\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Saves the data to server\r\n   */\r\n  public save(): Promise<Onboarding> {\r\n    this.model.signature.email = this.model.person.contact.email;\r\n    this.model.signature.telephone = this.model.person.contact.telephone;\r\n    this.model.signature.personName = (this.model.person.firstName + \" \" + this.model.person.lastName).trim();\r\n    return this.onboardingService.save();\r\n  }\r\n\r\n  /**\r\n   * Returns signing url.\r\n   */\r\n  public get vismaSignUrl(): string {\r\n    return this.onboardingService.getDigitalSignUrl();\r\n  }\r\n\r\n  /**\r\n   * The onboarding model is provided by the onboarding service.\r\n   */\r\n  public get model(): Onboarding {\r\n    return this.onboardingService.model;\r\n  }\r\n\r\n  /** IF true, the Suomi.fi company selection is used. */\r\n  public get showCompanySelection(): boolean {\r\n\r\n    const isAccountant = this.model &&\r\n    this.model.company &&\r\n     this.model.company.roles &&\r\n     this.model.company.roles.some( (r) => ( r === Role.Accountant || r === Role.AccountantCandidate));\r\n\r\n    return isAccountant;\r\n  }\r\n\r\n  /** Returns the PDF preview address for the authorization pdf. */\r\n  public getPdfPreviewAddress() {\r\n    return this.onboardingService.getPdfPreviewAddress();\r\n  }\r\n\r\n  /**\r\n   * Existing company alert.\r\n   */\r\n  public get existingCompanyAlert(): boolean {\r\n    const currentAccountId = this.sessionService.session?.currentAccount?.id;\r\n    // existing account in the system and is different than current account\r\n    return this.model?.company?.resolvedId &&\r\n           this.model.company.resolvedId != currentAccountId;\r\n  }\r\n\r\n  /** Go to suomi fi ypa */\r\n  public goToSuomifi() {\r\n\r\n    const rawUrl = this.$location.url();\r\n    let baseUrl = this.$location.absUrl();\r\n    if (rawUrl.length > 1) {\r\n      baseUrl = baseUrl.substring(0, baseUrl.indexOf(rawUrl));\r\n    }\r\n    baseUrl = baseUrl.replace(/\\/$/, \"\").trim();\r\n\r\n    const accessToken = this.ajax.getCurrentToken();\r\n    const token = accessToken ? `${encodeURIComponent(accessToken)}` : \"\";\r\n    const urlParam = ( baseUrl.indexOf(\"&\") >= 0 || baseUrl.indexOf(\"?\") >= 0) ? \"&url=\" : \"\";\r\n    const cancelUrl = `${baseUrl}${urlParam}/onboarding/company/${this.model.id}${token ? \"&ob_token=\" + token : \"\"}`;\r\n    const successUrl = `${baseUrl}${urlParam}/onboarding/company/${this.model.id}${token ? \"&ob_token=\" + token : \"\"}`;\r\n    this.save().then(() => {\r\n      window.location.assign(`${this.ajax.getServerAddress()}/Onboarding/CompanySelection?OnboardingId=${encodeURIComponent(this.model.id)}&Language=${encodeURIComponent(Translations.getLanguage())}&SuccessUrl=${encodeURIComponent(successUrl)}&CancelUrl=${encodeURIComponent(cancelUrl)}${token ? \"&access_token=\" + token : \"\"}`);\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Launches the wizard.\r\n   * @param id Optional onboarding id.\r\n   */\r\n  public launch(id: string = null): Promise<any> {\r\n    return this.onboardingService.launchCompanyOnboarding(id);\r\n  }\r\n\r\n  /**\r\n   * Sets the company's business id, clears the YTJ search results fetches other company info's via YTJ search and saves\r\n   * @param businessId The business id that is set as the company's business id\r\n   */\r\n  public chooseBusinessId(businessId) {\r\n    this.model.company.businessId = businessId;\r\n    this.model.company.ytjSearch = null;\r\n    this.searchYtj();\r\n  }\r\n\r\n  /**\r\n   * Sets the DoYtjUpdate flag to true and saves.\r\n   * @param searchType - If true, sets the business ID to null\r\n   * Use this option to force a YTJ name search, even if there already is something written in business ID field.\r\n   */\r\n  public searchYtj(searchType?: \"businessId\" | \"name\") {\r\n    // Clear company's type and address\r\n    this.model.company.companyType = null;\r\n    this.model.company.contact.street = null;\r\n    this.model.company.contact.city = null;\r\n    this.model.company.contact.postalCode = null;\r\n    // Clear previous YTJ search results\r\n    this.model.company.ytjSearch = null;\r\n    // Prepare for YTJ search\r\n    this.model.company.doYtjUpdate = true;\r\n    if (searchType === \"name\") {\r\n      this.model.company.businessId = null;\r\n    }\r\n    if (searchType === \"businessId\") {\r\n\r\n      this.model.company.name = null;\r\n    }\r\n\r\n    this.save();\r\n  }\r\n\r\n  /**\r\n   * Returns validation error for key if exists.\r\n   * @param key - Validation error key.\r\n   */\r\n  public getValidationError(key: string): ApiValidationError {\r\n    if (this.model && this.model.validation) {\r\n      return this.model.validation.errors.find((x) => x.key === key);\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /** Opens wizard as modal dialog */\r\n  public openSigningWizardDialog(onBoardingId = null): Promise<any> {\r\n    const skin = this.sessionService.getCurrentCss();\r\n    const origin = this.sessionService.getOrigin();\r\n    const url =  origin + (skin ?\r\n      `popup.html#settings/signing?skin=${skin}&lang=${Translations.getLanguage()}&id=${this.onboardingService.model?.id ?? \"\"}#access_token=${this.ajax.getCurrentToken()}` :\r\n      `popup.html#settings/signing?lang=${Translations.getLanguage()}&id=${this.onboardingService.model?.id ?? \"\"}#access_token=${this.ajax.getCurrentToken()}`);\r\n    return this.uiHelpers.showExternalDialog(onBoardingId, url , { id: onBoardingId, origin }, {width: 1080, height: 800}).then( (result) => {\r\n      if (result?.action != \"cancel\") {\r\n        return this.checkSession();\r\n      } else {\r\n        return;\r\n      }\r\n    });\r\n  }\r\n\r\n  /** Launches company wizard. */\r\n  public launchSigningWizard() {\r\n    const data =  this.readTokenFromUrl(this.$location.absUrl(), \"data=\");\r\n    const id = JSON.parse(atob(decodeURIComponent(data)))?.id;\r\n    const origin = JSON.parse(atob(decodeURIComponent(data)))?.origin;\r\n    return this.onboardingService.getOnboardingData(id).then( () => {\r\n      const skin = this.sessionService.getCurrentCss();\r\n      this.onboardingService.model.ui.successUrl = origin + (skin ?\r\n        `popup.html#settings/signing-success?skin=${skin}&lang=${Translations.getLanguage()}&id=${this.onboardingService.model?.id ?? \"\"}#access_token=${this.ajax.getCurrentToken()}` :\r\n        `popup.html#settings/signing-success?lang=${Translations.getLanguage()}&id=${this.onboardingService.model?.id ?? \"\"}#access_token=${this.ajax.getCurrentToken()}`);\r\n      this.onboardingService.model.ui.cancelUrl = this.onboardingService.model.ui.successUrl.replace(\"/signing-success?\", \"/signing-cancel?\");\r\n      return this.onboardingService.save().then( () => {\r\n        return this.onboardingService.launchCompanyOnboarding(this.onboardingService.model.id);\r\n      });\r\n    });\r\n  }\r\n\r\n  /** Reloads the current session*/\r\n  public checkSession(): Promise<any> {\r\n    return this.sessionService.checkSession();\r\n  }\r\n\r\n  private readTokenFromUrl(url: string, key: string): string {\r\n    // shoud use regex...\r\n    const start = url.toLowerCase().indexOf(key);\r\n    if (start >= 0) {\r\n      const end = url.indexOf(\"&\", start);\r\n      return end >= 0\r\n        ? url.substring(start + key.length, end)\r\n        : url.substring(start + key.length);\r\n    }\r\n    return null;\r\n  }\r\n\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Ajax, Language, Onboarding, Translations, WebSiteUserRole, AuthorizationContract, AuthorizationType } from \"@salaxy/core\";\r\n\r\nimport { OnboardingService, SessionService, SignatureMethod, SignatureService, UiHelpers } from \"../../../services\";\r\n\r\n/**\r\n * Controller for showing the signing user interface for unsigned account.\r\n */\r\nexport class SigningController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$scope\", \"OnboardingService\", \"SessionService\", \"SignatureService\", \"$sce\", \"UiHelpers\", \"AjaxNg1\", \"$timeout\"];\r\n\r\n  /** If true (typically default), the signing person is also the contact person for the company */\r\n  public isContactPersonSigner: boolean;\r\n\r\n  /** If true, shows the component even if the Signing is already OK. Typically used only in test. */\r\n  public showAlways: boolean;\r\n\r\n  /** If true, component shows success popup */\r\n  public showInPopup = false;\r\n\r\n  /**\r\n   * Will be true if the component has done authentication and determines that signature is already OK\r\n   * If true, the component is not shown to the end user unless showAlways is set true.\r\n   */\r\n  public isSigningOk: boolean;\r\n\r\n  /** True when the session is available (auth) AND the signature is required. */\r\n  public isSigningRequired: boolean;\r\n\r\n  /** URL for the PDF preview. Changes when saved, to assure that PDF is not cached.  */\r\n  public pdfPreviewUrl: string;\r\n\r\n  /** Binding for button, which calls startDigitalSignature(). */\r\n  public isSigninStarted = false;\r\n\r\n  constructor(\r\n    private $scope: angular.IScope,\r\n    private onboardingService: OnboardingService,\r\n    private sessionService: SessionService,\r\n    private signatureService: SignatureService,\r\n    private $sce: angular.ISCEService,\r\n    private uiHelpers: UiHelpers,\r\n    private ajax: Ajax,\r\n    private $timeout: angular.ITimeoutService,\r\n  ) {\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit = () => {\r\n    this.init();\r\n\r\n    this.sessionService.subscribe(this.$scope, () => {\r\n      this.init();\r\n    });\r\n    this.isContactPersonSigner = true;\r\n  };\r\n\r\n  /** Saves the current onboarding model. */\r\n  public save(): Promise<Onboarding> {\r\n    if (this.isContactPersonSigner) {\r\n      this.model.company.contact.email = this.model.signature.email;\r\n      this.model.company.contact.telephone = this.model.signature.telephone;\r\n    }\r\n    return this.onboardingService.save()\r\n      .then((onboarding) => {\r\n        this.pdfPreviewUrl = null;\r\n        return onboarding;\r\n      });\r\n  }\r\n\r\n  /**\r\n   * The onboarding model is provided by the onboarding service.\r\n   */\r\n  public get model(): Onboarding {\r\n    if (this.onboardingService.model?.company) {\r\n      this.onboardingService.model.company.language = Translations.getLanguage() as Language;\r\n    }\r\n    if (this.onboardingService.model?.person) {\r\n      this.onboardingService.model.person.language = Translations.getLanguage() as Language;\r\n    }\r\n    return this.onboardingService.model;\r\n  }\r\n\r\n  /** Returns the PDF preview address for the authorization pdf. */\r\n  public getPdfPreviewAddress() {\r\n    if (!this.pdfPreviewUrl && this.model?.id) {\r\n      this.pdfPreviewUrl = this.$sce.trustAsResourceUrl(this.onboardingService.getPdfPreviewAddress(true) + \"&t=\" + new Date().getTime() + \"&language=\" + this.model.company.language);\r\n    }\r\n    return this.pdfPreviewUrl;\r\n  }\r\n\r\n  /**\r\n   * Starts Visma sign\r\n   * If this.showInPopup is false, saves the model and starts the signature.\r\n   * If this.showInPopup is true, saves the model, starts the signature and then opens success dialog.\r\n   * @param authMethod Method of authentication (bank selection).\r\n   * Only used for Persons (Telia methods), ignored for companies.\r\n   */\r\n  public startDigitalSignature(authMethod: string) {\r\n    this.isSigninStarted = true;\r\n    if (this.showInPopup) {\r\n      this.save().then(() => {\r\n        let skin = this.sessionService.getCurrentCss() || \"\";\r\n        if (skin) {\r\n          skin = `skin=${skin}&`;\r\n        }\r\n\r\n        const successUrl = this.sessionService.getOrigin() +\r\n          `popup.html#settings/signing-success?${skin}lang=${Translations.getLanguage()}&id=${this.onboardingService.model?.id ?? \"\"}#access_token=${this.ajax.getCurrentToken()}`;\r\n        const url = this.onboardingService.getDigitalSignUrl(authMethod, null, null, successUrl, successUrl.replace(\"/signing-success?\", \"/signing-cancel?\") );\r\n        // To prevent double-clicking\r\n        this.$timeout(() => this.isSigninStarted = false, 2000);\r\n        return this.uiHelpers.showExternalDialog(\"vismaSignPopup\", url, {}, { width: 1080, height: 800 })\r\n          .then((result) => {\r\n            if (result?.action != \"cancel\") {\r\n              return this.sessionService.checkSession();\r\n            } else {\r\n              return;\r\n            }\r\n          });\r\n      });\r\n    } else {\r\n      this.uiHelpers.showLoading(\"SALAXY.NG1.SigningComponent.dialog.header\", `Siirrytään allekirjoitukseen (${authMethod})`);\r\n      // Saving is needed mainly for potential changes in name, e-mail and phone. AuthService, signerPersonalId and successUrl are passed in URL.\r\n      this.save().then(() => {\r\n        window.top.location.href = this.onboardingService.getDigitalSignUrl(authMethod);\r\n      });\r\n    }\r\n  }\r\n\r\n  /** List of supported Signature methods */\r\n  public get methods() {\r\n    return this.signatureService.getMethods();\r\n  }\r\n\r\n  /**\r\n   * Returns the SignatureMethod for given value.\r\n   * @param value - value for SignatureMethod, e.g. tupas-nordea.\r\n   */\r\n  public getMethod(value: string): SignatureMethod {\r\n    const arr = this.methods.filter((x) => x.value === value);\r\n    if (arr.length > 0) {\r\n      return arr[0];\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /**\r\n   * Signs the authorization contract for the current user.\r\n   * Creates a partner contract authorization and updates the session.\r\n   * @returns Promise that resolves when the contract is signed and session is updated\r\n   * @throws Error if the contract signing fails\r\n   */\r\n  public async signPartnerContract(): Promise<void> {\r\n    const data: AuthorizationContract = {\r\n      authorizationType: AuthorizationType.PartnerContract\r\n    };\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    try {\r\n      await this.ajax.postJSON(\"/onboarding/contract\", data);\r\n      await this.sessionService.checkSession();\r\n    } catch (error) {\r\n      console.error(\"Failed to sign partner contract:\", error);\r\n    } finally {\r\n      loading.dismiss();\r\n    }\r\n  }\r\n\r\n  private init() {\r\n    this.isSigningOk = this.sessionService.isSigningOk();\r\n    this.pdfPreviewUrl = null;\r\n    this.isSigningRequired = !this.sessionService.isSigningOk();\r\n    if (this.sessionService.isSessionChecked && this.sessionService.isAuthenticated) {\r\n      const accountId = this.sessionService.session.currentAccount.id;\r\n      if (this.onboardingService.model && this.onboardingService.model.company.resolvedId === accountId) {\r\n        return;\r\n      }\r\n\r\n      // reset before get\r\n      this.onboardingService.model = null;\r\n      this.onboardingService.id = null;\r\n      this.onboardingService.getOnboardingDataForAccount(this.sessionService.session.currentAccount.id).then(() => {\r\n        if (this.onboardingService.model) {\r\n          this.onboardingService.model.signature.isPep = null;\r\n          this.onboardingService.model.company.ownership.isRequiredTracking = null;\r\n          if (!this.onboardingService.model.id) {\r\n            this.onboardingService.save();\r\n          }\r\n          return;\r\n        } else {\r\n          this.onboardingService.model = {\r\n            accountType: WebSiteUserRole.Company,\r\n            signature: {},\r\n          };\r\n          this.onboardingService.save();\r\n        }\r\n      });\r\n    }\r\n  }\r\n}\r\n\r\n","import angular from \"angular\";\r\n\r\nimport { SignatureMethod, SignatureService } from \"../../../services\";\r\n\r\n/**\r\n * Handles user interaction for Digital Signature\r\n */\r\nexport class SignatureController implements angular.IController {\r\n\r\n    /**\r\n     * For NG-dependency injection\r\n     * @ignore\r\n     */\r\n    public static $inject = [\r\n        \"SignatureService\",\r\n    ];\r\n\r\n    /**\r\n     * Creates a new SignatureController\r\n     * @param signatureService - Service that handles the communication to the server\r\n     * @ignore\r\n     */\r\n    constructor(private signatureService: SignatureService) {\r\n    }\r\n\r\n    /**\r\n     * Implement IController\r\n     */\r\n    public $onInit = () => {\r\n        //\r\n    };\r\n\r\n    /**\r\n     * Legacy list of supported Visma Sign Signature methods.\r\n     */\r\n    public get methods() {\r\n        return this.getMethods(\"tupas\");\r\n    }\r\n\r\n    /**\r\n     * List of supported Signature methods\r\n     * @param methodGroup - Method group \"telia\" for Telia Tunnistus and \"tupas\" for Visma Sign. Default is \"tupas\".\r\n     */\r\n    public getMethods(methodGroup: \"tupas\" | \"telia\" = \"tupas\") {\r\n        return this.signatureService.getMethods(methodGroup);\r\n    }\r\n\r\n    /**\r\n     * Returns the SignatureMethod for given value.\r\n     * @param value - value for SignatureMethod, e.g. tupas-nordea.\r\n     */\r\n    public getMethod(value: string): SignatureMethod {\r\n        return this.signatureService.getMethods(\"tupas\").find( (x) => x.value === value)\r\n        ?? this.signatureService.getMethods(\"telia\").find( (x) => x.value === value);\r\n    }\r\n}\r\n","import { IService, UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Base class for CRUD controllers of legacy service model: BaseService<T> / IService<T>.\r\n * Most new implementations should use the new API CRUD model instead.\r\n * However, this service model may still be the right choice in certain circumstances where the editable data should be\r\n * cached or is already in session (like account data).\r\n */\r\nexport class CrudControllerBase<T> implements angular.IController {\r\n\r\n    /**\r\n     * Bindings for the component which uses CRUD controller.\r\n     */\r\n    public static crudBindings = {\r\n\r\n        /**\r\n         * Function that is called when user selects an item in the list.\r\n         * The selected item is the parameter of the function call.\r\n         * @example <salaxy-payroll-list on-list-select=\"$ctrl.myCustomSelectFunc(item)\"></salaxy-payroll-list>\r\n         */\r\n        onListSelect: \"&\",\r\n\r\n        /**\r\n         * Function that is called when an item is deleted.\r\n         * The event is intended for user interface logic after delete (promise resolve)\r\n         * and potentially when waiting for server to respond (from function call until promise resolve).\r\n         * It is not meant for delete validation and/or for preventing deletion.\r\n         * If onDelete is not specified, the browser is redirected to listUrl if specified.\r\n         * @example <salaxy-payroll-list on-delete=\"$ctrl.resetUiAfterDeleteFunc\"></salaxy-payroll-list>\r\n         */\r\n        onDelete: \"&\",\r\n\r\n        /**\r\n         * Function that is called after a new item has been created.\r\n         * At this point, the item has been created, but not yet selected as current.\r\n         * If onCreateNew is not specified the browser is redirected to detailsUrl if specified and if not, only current item is set.\r\n         * @example <salaxy-payroll-list on-create-new=\"$ctrl.startMyCustomWizardFunc\"></salaxy-payroll-list>\r\n         */\r\n        onCreateNew: \"&\",\r\n\r\n        /**\r\n         * URL to which the component navigates when an item is clicked.\r\n         * The \"id\" or \"rowIndex\" property of the selected item is added to the URL.\r\n         * URL is ignored if onListSelect is set. In this case, you may navigate yourself in that method.\r\n         * @example <salaxy-payroll-list details-url=\"/myCustomRoute/\"></salaxy-payroll-list>\r\n         */\r\n        detailsUrl: \"@\",\r\n\r\n        /**\r\n         * URL for the list view. At the moment, if specified, the browser is redirected here after delete.\r\n         * @example\r\n         * <!-- Main worker list is in the front page in this case -->\r\n         * <salaxy-employment-details list-url=\"/home\"></salaxy-employment-details>\r\n         */\r\n        listUrl: \"@\",\r\n    };\r\n\r\n    /**\r\n     * For list-controls, this is the URL for item select event\r\n     * as well as the URL where a new item is edited. Basically showing the Details view.\r\n     * For more control, use onListSelect or onCreateNew events.\r\n     * @example <salaxy-payroll-list details-url=\"/myCustomRoute/\"></salaxy-payroll-list>\r\n     */\r\n    public detailsUrl: string;\r\n\r\n    /**\r\n     * URL for the list view. At the moment, if specified, the browser is redirected here after delete.\r\n     * @example\r\n     * <!-- Main worker list is in the front page in this case -->\r\n     * <salaxy-employment-details list-url=\"/home\"></salaxy-employment-details>\r\n     */\r\n    public listUrl: string;\r\n\r\n    /**\r\n     * Angular ng-model **if** the controller is bound to model using ng-model attribute.\r\n     */\r\n    public model: angular.INgModelController;\r\n\r\n    /**\r\n     * Function that is called when an item is deleted.\r\n     * The event is intended for user interface logic after delete (promise resolve)\r\n     * and potentially when waiting for server to respond (from function call until promise resolve).\r\n     * It is not meant for delete validation and/or for preventing deletion.\r\n     * If onDelete is not specified, the browser is redirected to listUrl if specified.\r\n     * NOTE: the deleteResult should basically always be  Promise<true> or promise failure. Promise<false> does not really make sense here.\r\n     * @example <salaxy-payroll-list on-delete=\"$ctrl.resetUiAfterDeleteFunc(deleteResult)\"></salaxy-payroll-list>\r\n     */\r\n    public onDelete: (eventData: {\r\n      /** The deleteResult should basically always be  Promise<true> or promise failure. Promise<false> does not really make sense here. */\r\n      deleteResult: Promise<boolean>,\r\n    }) => Promise<boolean>;\r\n\r\n    /**\r\n     * Function that is called after a new item has been created.\r\n     * At this point, the item has been created, but not yet selected as current.\r\n     * If onCreateNew is not specified the browser is redirected to detailsUrl if specified and if not, only current item is set.\r\n     * @example <salaxy-payroll-list on-create-new=\"$ctrl.startMyCustomWizardFunc(item)\"></salaxy-payroll-list>\r\n     */\r\n    public onCreateNew: (eventData: {\r\n      /** New item which was created. */\r\n       item: T,\r\n      }) => void;\r\n\r\n    /**\r\n     * For list-controls, this is the function of on-list-select event.\r\n     * If onListSelect is not specified, the browser is redirected to detailsUrl if specified.\r\n     * If detailsUrl is not specified, only current item is set.\r\n     * @example <salaxy-payroll-list on-list-select=\"$ctrl.myCustomSelectFunc(item)\"></salaxy-payroll-list>\r\n     */\r\n    public onListSelect: (eventData: {\r\n      /** The selected item. */\r\n      item: T,\r\n    }) => void;\r\n\r\n    /**\r\n     * Creates a new CrudControllerBase.\r\n     * @param crudService The the BaseService instance that is used for communicating to server.\r\n     * @param $location Angular.js Location service that is used for navigation. Especially the list views.\r\n     * @param $attrs Angular.js Attisbutes for determining whether events have been bound to.\r\n     * @param uiHelpers - Salaxy ui helpers service.\r\n     */\r\n    constructor(\r\n        protected crudService: IService<T>,\r\n        protected $location: angular.ILocationService,\r\n        protected $attrs: angular.IAttributes,\r\n        protected uiHelpers: UiHelpers,\r\n    ) {\r\n        if (!crudService) {\r\n            throw new Error(\"crudService is undefined in CrudControllerBase\");\r\n        }\r\n        if (!$location) {\r\n            throw new Error(\"$location is undefined in CrudControllerBase\");\r\n        }\r\n        if (!uiHelpers) {\r\n            throw new Error(\"uiHelpers is undefined in CrudControllerBase\");\r\n        }\r\n        if (!$attrs) {\r\n            throw new Error(\"$attrs is undefined in CrudControllerBase\");\r\n        }\r\n    }\r\n\r\n    /**\r\n     * Implement IController by providing onInit method.\r\n     * We currently do nothing here, but if you override this function,\r\n     * you should call this method in base class for future compatibility.\r\n     */\r\n    public $onInit() {\r\n        // No init code at the moment, we may add later if necessary.\r\n    }\r\n\r\n    /** Gets the Current selected item. */\r\n    public get current(): T {\r\n      if (this.getBindingMode() === \"model\") {\r\n        return this.model.$viewValue;\r\n      }\r\n      return this.crudService.current;\r\n    }\r\n\r\n    /** Gets the list of all CRUD objects listed. */\r\n    public get list(): T[] {\r\n        return this.crudService.list;\r\n    }\r\n\r\n    /**\r\n     * Creates a new item. The item is not saved in this process yet.\r\n     * Item is set as current unless onCreateNew is specified => Then you are responsible for doing it yourself.\r\n     * If detailsUrl is specified, the browser is redirectedted there.\r\n     * Current item is set also in this case (as opposed to listSelect) because the new item does not yet have an id\r\n     * and passing it in current item is the only way using router.\r\n     * Use onCreateNew event or crudService.getBlank() if you do not want to set the current item.\r\n     * @param newItem Specify the new item if you want to initialize it with specific values.\r\n     * In most cases, you should let the system create it with defaults.\r\n     */\r\n    public createNew(newItem: T = null): T {\r\n        if (!newItem) {\r\n            newItem = this.crudService.getBlank();\r\n        }\r\n        if (this.$attrs.onCreateNew) {\r\n            this.onCreateNew({ item: newItem });\r\n        } else {\r\n            this.setCurrent(newItem);\r\n            if (this.detailsUrl) {\r\n                // unique fraction is required for page refresh, if the list and details are in the same page.\r\n                this.$location.url(this.detailsUrl + \"new#\" + (new Date()).getTime());\r\n            }\r\n        }\r\n        return newItem;\r\n    }\r\n\r\n    /** Copies the current item and sets it as the new current */\r\n    public copyCurrent(): void {\r\n        if (this.current) {\r\n            this.setCurrent(this.crudService.copyAsNew(this.current));\r\n        }\r\n    }\r\n\r\n    /**\r\n     * Creates a copy of a given item and sets it as current\r\n     * unless onCreateNew is specified => Then you are responsible for doing it yourself.\r\n     * If detailsUrl is specified, the browser is redirectedted there.\r\n     * Current item is set also in this case (as opposed to listSelect) because the new item does not yet have an id\r\n     * and passing it in current item is the only way using router.\r\n     * Use onCreateNew event or crudService.copyAsNew() if you do not want to set the current item.\r\n     * @param copySource The item to copy as new.\r\n     * @returns The new item that is created.\r\n     */\r\n    public copyAsNew(copySource: T): T {\r\n        const copy = this.crudService.copyAsNew(copySource);\r\n        return this.createNew(copy);\r\n    }\r\n\r\n    /**\r\n     * Creates a copy of a given item and sets it as current\r\n     * unless onCreateNew is specified => Then you are responsible for doing it yourself.\r\n     * If detailsUrl is specified, the browser is redirectedted there.\r\n     * Current item is set also in this case (as opposed to listSelect) because the new item does not yet have an id\r\n     * and passing it in current item is the only way using router.\r\n     * Use onCreateNew event or crudService.copyAsNew() if you do not want to set the current item.\r\n     * @param copySourceId The id of the item to copy as new.\r\n     * @returns The new item that is created.\r\n     */\r\n    public copyIdAsNew = (copySourceId: string): T => {\r\n      const copySource = this.list.find( (x) => (x as any).id === copySourceId);\r\n      if (copySource) {\r\n        return this.copyAsNew(copySource);\r\n      }\r\n      return null;\r\n    };\r\n\r\n    /**\r\n     * Mode for data binding is \"singleton\" by default.\r\n     * This means that this.current is bound to crudService.current.\r\n     * If ng-model is defined for the component (this.ngModelController),\r\n     * this.current is bound to ngModelController view value (as with form controls).\r\n     */\r\n    public getBindingMode(): \"model\" | \"singleton\" {\r\n      return this.model ? \"model\" : \"singleton\";\r\n    }\r\n\r\n    /** Called by the view when the item is clicked. */\r\n    public listSelect = (selectedItem: T) => {\r\n        if (this.$attrs.onListSelect) {\r\n            this.onListSelect({ item: selectedItem });\r\n        } else if (this.detailsUrl) {\r\n            this.$location.url(this.detailsUrl + ((selectedItem as any).id || (selectedItem as any).rowIndex));\r\n        } else {\r\n            this.setCurrent(selectedItem);\r\n        }\r\n    };\r\n\r\n    /** Called by the view when the item (id) is clicked. */\r\n    public listSelectId = (selectedItemId: string) => {\r\n      const selectedItem = this.list.find( (x) => (x as any).id === selectedItemId );\r\n      if (selectedItem) {\r\n        this.listSelect(selectedItem);\r\n      }\r\n    };\r\n\r\n    /** Saves the current item. */\r\n    public saveCurrent(): Promise<T> {\r\n      return this.crudService.saveCurrent();\r\n    }\r\n\r\n    /**\r\n     * Sets the current item: Either to ng-model view value or crudService.setCurrent().\r\n     * @param item The item to set as Current.\r\n     */\r\n    public setCurrent(item: T) {\r\n      if (this.getBindingMode() === \"model\") {\r\n        this.model.$setViewValue(item);\r\n      } else {\r\n        this.crudService.setCurrent(item);\r\n      }\r\n    }\r\n\r\n    /**\r\n     * Shows the \"Are you sure?\" dialog and if user clicks OK, deletes the item.\r\n     * Cancels the started payment for the payroll too.\r\n     * @param id Identifier of the item to be deleted.\r\n     * @param confirmMessage Optional custom message for the confirm dialog.\r\n     * If not specified, a generic message is shown.\r\n     * If set to boolean false, the confirm message is not shown at all.\r\n     * @returns Promise that resolves to true if the item is deleted.\r\n     * False, if user cancels and fails if the deletion fails.\r\n     */\r\n    public delete = (id: string, confirmMessage?: string): Promise<boolean> => {\r\n      return this.uiHelpers.showConfirm(confirmMessage || \"SALAXY.NG1.ApiCrudObjectComponent.deleteDialog\")\r\n          .then((result: boolean) => {\r\n              if (result) {\r\n                  if (this.$attrs.onDelete) {\r\n                      return this.onDelete({ deleteResult: this.deleteNoConfirm(id)});\r\n                  }\r\n                  if (this.listUrl) {\r\n                      this.$location.url(this.listUrl);\r\n                  }\r\n                  return this.deleteNoConfirm(id);\r\n              } else {\r\n                  return Promise.resolve(false);\r\n              }\r\n          });\r\n    };\r\n\r\n    /**\r\n     * Deletes an item without showing the confirm dialog.\r\n     * The method shows the \"Please wait...\" loader, but does not call onDelete\r\n     * or move the browser to listUrl. The caller should take care\r\n     * of the UX actions after delete if necessary.\r\n     * @param id Identifier of the item to be deleted.\r\n     * @returns Promise that resolves to true (never false). Fails if the deletion fails.\r\n     */\r\n    public deleteNoConfirm(id: string): Promise<boolean> {\r\n        const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n        return this.crudService.delete(id).then(() => {\r\n            loading.dismiss();\r\n            return true;\r\n        });\r\n    }\r\n\r\n}\r\n","import { Ajax, AuthorizedAvatar, CompanyAccount, PersonAccount } from \"@salaxy/core\";\r\n\r\nimport { AuthorizedAccountService, SessionService, UiHelpers } from \"../../services\";\r\nimport { CrudControllerBase } from \"../bases/CrudControllerBase\";\r\n\r\n/**\r\n * Handles user interaction for viewing and modifying authorized and authorizing accounts.\r\n */\r\nexport class AccountAuthorizationController extends CrudControllerBase<AuthorizedAvatar> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"AuthorizedAccountService\",\r\n    \"$location\",\r\n    \"$attrs\",\r\n    \"UiHelpers\",\r\n    \"SessionService\",\r\n    \"AjaxNg1\",\r\n  ];\r\n\r\n   /** If true, the switch will be disabled and its value cannot be changed by clicking/toggling it */\r\n   public disabled: boolean;\r\n\r\n  constructor(\r\n    private authorizedAccountService: AuthorizedAccountService,\r\n    $location: angular.ILocationService,\r\n    $attrs: angular.IAttributes,\r\n    uiHelpers: UiHelpers,\r\n    private sessionService: SessionService,\r\n    private ajax: Ajax,\r\n  ) {\r\n    super(authorizedAccountService, $location, $attrs, uiHelpers);\r\n  }\r\n\r\n\r\n\r\n  /**\r\n   * Returns the list of Integration partner sites available and the status of each partner.\r\n   */\r\n  public get partnerIntegrationSites() {\r\n    return this.authorizedAccountService.getPartnerIntegrationSiteList();\r\n  }\r\n\r\n  /**\r\n   * Gets a specific partner site for the current user\r\n   * @param id Identifier of the site\r\n   */\r\n  public getPartnerSite(id: string) {\r\n\r\n    return this.authorizedAccountService.getPartnerSite(id);\r\n  }\r\n\r\n  /**\r\n   * Returns the current partner site\r\n   */\r\n  public get currentPartnerSite() {\r\n    return this.authorizedAccountService.getCurrentPartnerSite();\r\n  }\r\n\r\n  /**\r\n   * Shows a dialog for adding / removing authorizations from known partners that\r\n   * frequently require authorizations. These are typically integrated software\r\n   * that are added without Primary Partner flag.\r\n   * @param id - The id of the partner site for which the dialog is shown.\r\n   */\r\n  public showPartnerSiteDialog(id: string) {\r\n    const partnerSite = this.getPartnerSite(id);\r\n    this.authorizedAccountService.setCurrentPartnerSite(partnerSite);\r\n    this.uiHelpers.showDialog(\"salaxy-components/modals/account/Authorization.html\", \"AccountAuthorizationController\");\r\n  }\r\n\r\n    /** Toggles the authorization option and makes the corresponding api call. */\r\n    public switchAuthorization() {\r\n      const partnerSite =  this.currentPartnerSite;\r\n      if (this.disabled !== true && !partnerSite.disabled) {\r\n        if (partnerSite.enabled == false && partnerSite.accountId) {\r\n          this.authorizedAccountService.delete(partnerSite.accountId);\r\n        } else if (partnerSite.enabled == true && partnerSite.accountId) {\r\n          const authorizedAccount = this.authorizedAccountService.getBlank();\r\n          authorizedAccount.id = partnerSite.accountId;\r\n          this.authorizedAccountService.save(authorizedAccount);\r\n        }\r\n      }\r\n    }\r\n  /**\r\n   * Returns the authorizing accounts for the current account\r\n   */\r\n  public get authorizingAccounts(): (PersonAccount | CompanyAccount)[] {\r\n    return this.authorizedAccountService.getAuthorizingAccounts();\r\n  }\r\n\r\n  /** Deletes the account. Only in test. */\r\n  public deleteAccount(accountId: string) {\r\n    this.uiHelpers.showConfirm(\"Haluatko varmasti poistaa tilin, tiliä ei voi palauttaa?\")\r\n      .then((result: boolean) => {\r\n        if (result) {\r\n          const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n          this.ajax.remove(\"/accounts/authorizingAccount/\" + accountId).then(() => {\r\n            this.authorizedAccountService.reloadAuthorizingAccounts().then(() => {\r\n              loading.dismiss();\r\n            });\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Shows a dialog for adding any new authorized account.\r\n   */\r\n  public showAuthorizedAccountAddDialog() {\r\n    super.createNew();\r\n    this.uiHelpers.showDialog(\"salaxy-components/modals/account/AuthorizedAccountAdd.html\", \"AccountAuthorizationController\");\r\n  }\r\n\r\n  /** Adds authorized account */\r\n  public saveCurrent(callback: (avatar: AuthorizedAvatar) => void = null): Promise<AuthorizedAvatar> {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    return super.saveCurrent().then((avatar: AuthorizedAvatar) => {\r\n      loading.dismiss();\r\n      if (callback) {\r\n        callback(avatar);\r\n      }\r\n      return avatar;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Adds access token to url.\r\n   * @param accountId - Account id to login as.\r\n   */\r\n  public getLoginAsUrl(accountId): string {\r\n\r\n    let url = this.ajax.getServerAddress() + \"/Security/LoginAs/\" + accountId;\r\n    url = url + \"?access_token=\" + encodeURIComponent(this.ajax.getCurrentToken());\r\n    return url;\r\n  }\r\n\r\n  /**\r\n   * Checks whether the user is in a given role\r\n   * @param role - One of the known roles\r\n   */\r\n  public isInRole(role: any): boolean {\r\n    return this.sessionService.isInRole(role);\r\n  }\r\n\r\n}\r\n","import { Certificate, Certificates, InputEnumOption, IssuedCertificate, Translations } from \"@salaxy/core\";\r\n\r\nimport { CertificateService, UiHelpers } from \"../../services\";\r\nimport { CrudControllerBase } from \"../bases/CrudControllerBase\";\r\n\r\n/** Certificate controller for listing certificate, revoking and requesting a new certificate. */\r\nexport class CertificateController extends CrudControllerBase<Certificate> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"CertificateService\", \"$location\", \"$attrs\", \"UiHelpers\", \"Certificates\"];\r\n\r\n  constructor(\r\n    private certificateService: CertificateService,\r\n    $location: angular.ILocationService,\r\n    $attrs: angular.IAttributes,\r\n    uiHelpers: UiHelpers,\r\n    private certificateApi: Certificates,\r\n  ) {\r\n    super(certificateService, $location, $attrs, uiHelpers);\r\n  }\r\n\r\n  /** Creates a new certificate */\r\n  public createNew(): Certificate {\r\n    super.createNew();\r\n    this.current.title = Translations.get(\"SALAXY.NG1.CertificatesComponent.newCertificate\");\r\n    return this.current;\r\n  }\r\n\r\n  public result: {\r\n    /** Certificate file as blob. */\r\n    blob: Blob;\r\n    /** Certificate file as text. */\r\n    text: string;\r\n    /** Certificate thumbprint. */\r\n    thumbprint: string;\r\n  } = undefined;\r\n\r\n  /** Certificate format (id) */\r\n  public certFormat: \"pfx\" | \"pem\" = \"pfx\";\r\n\r\n  /** Returns the metadata for the certFrmat */\r\n  public get currentCertFormat() {\r\n    return this.certFormats.find((f) => f.value === this.certFormat) || this.certFormats[0];\r\n  }\r\n\r\n  /** Avilabe certificate formats */\r\n  public certFormats: InputEnumOption[] = [\r\n    {\r\n      value: \"pfx\",\r\n      text: \"Windows-sertifikaatti (pfx / pkcs12)\",\r\n      ui: {\r\n        mime: \"application/x-pkcs12\",\r\n        suffix: \"pfx\",\r\n      }\r\n    }, {\r\n      value: \"pem\",\r\n      text: \"Yleinen sertifikaatti (zip / pem)\",\r\n      ui: {\r\n        mime: \"application/zip\",\r\n        suffix: \"zip\",\r\n      },\r\n    },\r\n  ];\r\n\r\n  /**\r\n   * Shows a dialog for adding nw certificate.\r\n   */\r\n  public showCertificateAddDialog() {\r\n    this.createNew();\r\n    this.uiHelpers.showDialog(\"salaxy-components/modals/account/CertificateAdd.html\", \"CertificateController\");\r\n  }\r\n\r\n  /** Creates a new certificate */\r\n  public createCert(): void {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    if (this.certFormat === \"pem\") {\r\n      this.certificateApi.issuePemCertificate(this.current).then((certificate: IssuedCertificate) => {\r\n        this.result = {\r\n          blob: this.uiHelpers.bytes2Blob(certificate.bytes, this.currentCertFormat.ui.mime),\r\n          text: certificate.cert + \"\\n\\n\" + certificate.key,\r\n          thumbprint: certificate.thumbprint,\r\n        };\r\n        loading.dismiss();\r\n      });\r\n    } else {\r\n      super.saveCurrent().then((certificate: Certificate) => {\r\n        this.result = {\r\n          blob: this.uiHelpers.bytes2Blob(certificate.bytes, this.currentCertFormat.ui.mime),\r\n          text: certificate.bytes,\r\n          thumbprint: certificate.thumbprint,\r\n        };\r\n        loading.dismiss();\r\n      });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Downloads current.blob as pfx and sets current.id as name\r\n   */\r\n  public downloadCertFile() {\r\n    this.uiHelpers.downloadFile(this.result.blob, `${this.result.thumbprint}.${this.currentCertFormat.ui.suffix}`);\r\n  }\r\n}\r\n","/**\n * @license AngularJS v1.8.3\n * (c) 2010-2020 Google LLC. http://angularjs.org\n * License: MIT\n */\n(function(window) {'use strict';\n\n/* exported\n  minErrConfig,\n  errorHandlingConfig,\n  isValidObjectMaxDepth\n*/\n\nvar minErrConfig = {\n  objectMaxDepth: 5,\n  urlErrorParamsEnabled: true\n};\n\n/**\n * @ngdoc function\n * @name angular.errorHandlingConfig\n * @module ng\n * @kind function\n *\n * @description\n * Configure several aspects of error handling in AngularJS if used as a setter or return the\n * current configuration if used as a getter. The following options are supported:\n *\n * - **objectMaxDepth**: The maximum depth to which objects are traversed when stringified for error messages.\n *\n * Omitted or undefined options will leave the corresponding configuration values unchanged.\n *\n * @param {Object=} config - The configuration object. May only contain the options that need to be\n *     updated. Supported keys:\n *\n * * `objectMaxDepth`  **{Number}** - The max depth for stringifying objects. Setting to a\n *   non-positive or non-numeric value, removes the max depth limit.\n *   Default: 5\n *\n * * `urlErrorParamsEnabled`  **{Boolean}** - Specifies whether the generated error url will\n *   contain the parameters of the thrown error. Disabling the parameters can be useful if the\n *   generated error url is very long.\n *\n *   Default: true. When used without argument, it returns the current value.\n */\nfunction errorHandlingConfig(config) {\n  if (isObject(config)) {\n    if (isDefined(config.objectMaxDepth)) {\n      minErrConfig.objectMaxDepth = isValidObjectMaxDepth(config.objectMaxDepth) ? config.objectMaxDepth : NaN;\n    }\n    if (isDefined(config.urlErrorParamsEnabled) && isBoolean(config.urlErrorParamsEnabled)) {\n      minErrConfig.urlErrorParamsEnabled = config.urlErrorParamsEnabled;\n    }\n  } else {\n    return minErrConfig;\n  }\n}\n\n/**\n * @private\n * @param {Number} maxDepth\n * @return {boolean}\n */\nfunction isValidObjectMaxDepth(maxDepth) {\n  return isNumber(maxDepth) && maxDepth > 0;\n}\n\n\n/**\n * @description\n *\n * This object provides a utility for producing rich Error messages within\n * AngularJS. It can be called as follows:\n *\n * var exampleMinErr = minErr('example');\n * throw exampleMinErr('one', 'This {0} is {1}', foo, bar);\n *\n * The above creates an instance of minErr in the example namespace. The\n * resulting error will have a namespaced error code of example.one.  The\n * resulting error will replace {0} with the value of foo, and {1} with the\n * value of bar. The object is not restricted in the number of arguments it can\n * take.\n *\n * If fewer arguments are specified than necessary for interpolation, the extra\n * interpolation markers will be preserved in the final string.\n *\n * Since data will be parsed statically during a build step, some restrictions\n * are applied with respect to how minErr instances are created and called.\n * Instances should have names of the form namespaceMinErr for a minErr created\n * using minErr('namespace'). Error codes, namespaces and template strings\n * should all be static strings, not variables or general expressions.\n *\n * @param {string} module The namespace to use for the new minErr instance.\n * @param {function} ErrorConstructor Custom error constructor to be instantiated when returning\n *   error from returned function, for cases when a particular type of error is useful.\n * @returns {function(code:string, template:string, ...templateArgs): Error} minErr instance\n */\n\nfunction minErr(module, ErrorConstructor) {\n  ErrorConstructor = ErrorConstructor || Error;\n\n  var url = 'https://errors.angularjs.org/1.8.3/';\n  var regex = url.replace('.', '\\\\.') + '[\\\\s\\\\S]*';\n  var errRegExp = new RegExp(regex, 'g');\n\n  return function() {\n    var code = arguments[0],\n      template = arguments[1],\n      message = '[' + (module ? module + ':' : '') + code + '] ',\n      templateArgs = sliceArgs(arguments, 2).map(function(arg) {\n        return toDebugString(arg, minErrConfig.objectMaxDepth);\n      }),\n      paramPrefix, i;\n\n    // A minErr message has two parts: the message itself and the url that contains the\n    // encoded message.\n    // The message's parameters can contain other error messages which also include error urls.\n    // To prevent the messages from getting too long, we strip the error urls from the parameters.\n\n    message += template.replace(/\\{\\d+\\}/g, function(match) {\n      var index = +match.slice(1, -1);\n\n      if (index < templateArgs.length) {\n        return templateArgs[index].replace(errRegExp, '');\n      }\n\n      return match;\n    });\n\n    message += '\\n' + url + (module ? module + '/' : '') + code;\n\n    if (minErrConfig.urlErrorParamsEnabled) {\n      for (i = 0, paramPrefix = '?'; i < templateArgs.length; i++, paramPrefix = '&') {\n        message += paramPrefix + 'p' + i + '=' + encodeURIComponent(templateArgs[i]);\n      }\n    }\n\n    return new ErrorConstructor(message);\n  };\n}\n\n/* We need to tell ESLint what variables are being exported */\n/* exported\n  angular,\n  msie,\n  jqLite,\n  jQuery,\n  slice,\n  splice,\n  push,\n  toString,\n  minErrConfig,\n  errorHandlingConfig,\n  isValidObjectMaxDepth,\n  ngMinErr,\n  angularModule,\n  uid,\n  REGEX_STRING_REGEXP,\n  VALIDITY_STATE_PROPERTY,\n\n  lowercase,\n  uppercase,\n  nodeName_,\n  isArrayLike,\n  forEach,\n  forEachSorted,\n  reverseParams,\n  nextUid,\n  setHashKey,\n  extend,\n  toInt,\n  inherit,\n  merge,\n  noop,\n  identity,\n  valueFn,\n  isUndefined,\n  isDefined,\n  isObject,\n  isBlankObject,\n  isString,\n  isNumber,\n  isNumberNaN,\n  isDate,\n  isError,\n  isArray,\n  isFunction,\n  isRegExp,\n  isWindow,\n  isScope,\n  isFile,\n  isFormData,\n  isBlob,\n  isBoolean,\n  isPromiseLike,\n  trim,\n  escapeForRegexp,\n  isElement,\n  makeMap,\n  includes,\n  arrayRemove,\n  copy,\n  simpleCompare,\n  equals,\n  csp,\n  jq,\n  concat,\n  sliceArgs,\n  bind,\n  toJsonReplacer,\n  toJson,\n  fromJson,\n  convertTimezoneToLocal,\n  timezoneToOffset,\n  addDateMinutes,\n  startingTag,\n  tryDecodeURIComponent,\n  parseKeyValue,\n  toKeyValue,\n  encodeUriSegment,\n  encodeUriQuery,\n  angularInit,\n  bootstrap,\n  getTestability,\n  snake_case,\n  bindJQuery,\n  assertArg,\n  assertArgFn,\n  assertNotHasOwnProperty,\n  getter,\n  getBlockNodes,\n  hasOwnProperty,\n  createMap,\n  stringify,\n  UNSAFE_restoreLegacyJqLiteXHTMLReplacement,\n\n  NODE_TYPE_ELEMENT,\n  NODE_TYPE_ATTRIBUTE,\n  NODE_TYPE_TEXT,\n  NODE_TYPE_COMMENT,\n  NODE_TYPE_DOCUMENT,\n  NODE_TYPE_DOCUMENT_FRAGMENT\n*/\n\n////////////////////////////////////\n\n/**\n * @ngdoc module\n * @name ng\n * @module ng\n * @installation\n * @description\n *\n * The ng module is loaded by default when an AngularJS application is started. The module itself\n * contains the essential components for an AngularJS application to function. The table below\n * lists a high level breakdown of each of the services/factories, filters, directives and testing\n * components available within this core module.\n *\n */\n\nvar REGEX_STRING_REGEXP = /^\\/(.+)\\/([a-z]*)$/;\n\n// The name of a form control's ValidityState property.\n// This is used so that it's possible for internal tests to create mock ValidityStates.\nvar VALIDITY_STATE_PROPERTY = 'validity';\n\n\nvar hasOwnProperty = Object.prototype.hasOwnProperty;\n\n/**\n * @private\n *\n * @description Converts the specified string to lowercase.\n * @param {string} string String to be converted to lowercase.\n * @returns {string} Lowercased string.\n */\nvar lowercase = function(string) {return isString(string) ? string.toLowerCase() : string;};\n\n/**\n * @private\n *\n * @description Converts the specified string to uppercase.\n * @param {string} string String to be converted to uppercase.\n * @returns {string} Uppercased string.\n */\nvar uppercase = function(string) {return isString(string) ? string.toUpperCase() : string;};\n\n\nvar\n    msie,             // holds major version number for IE, or NaN if UA is not IE.\n    jqLite,           // delay binding since jQuery could be loaded after us.\n    jQuery,           // delay binding\n    slice             = [].slice,\n    splice            = [].splice,\n    push              = [].push,\n    toString          = Object.prototype.toString,\n    getPrototypeOf    = Object.getPrototypeOf,\n    ngMinErr          = minErr('ng'),\n\n    /** @name angular */\n    angular           = window.angular || (window.angular = {}),\n    angularModule,\n    uid               = 0;\n\n// Support: IE 9-11 only\n/**\n * documentMode is an IE-only property\n * http://msdn.microsoft.com/en-us/library/ie/cc196988(v=vs.85).aspx\n */\nmsie = window.document.documentMode;\n\n\n/**\n * @private\n * @param {*} obj\n * @return {boolean} Returns true if `obj` is an array or array-like object (NodeList, Arguments,\n *                   String ...)\n */\nfunction isArrayLike(obj) {\n\n  // `null`, `undefined` and `window` are not array-like\n  if (obj == null || isWindow(obj)) return false;\n\n  // arrays, strings and jQuery/jqLite objects are array like\n  // * jqLite is either the jQuery or jqLite constructor function\n  // * we have to check the existence of jqLite first as this method is called\n  //   via the forEach method when constructing the jqLite object in the first place\n  if (isArray(obj) || isString(obj) || (jqLite && obj instanceof jqLite)) return true;\n\n  // Support: iOS 8.2 (not reproducible in simulator)\n  // \"length\" in obj used to prevent JIT error (gh-11508)\n  var length = 'length' in Object(obj) && obj.length;\n\n  // NodeList objects (with `item` method) and\n  // other objects with suitable length characteristics are array-like\n  return isNumber(length) && (length >= 0 && (length - 1) in obj || typeof obj.item === 'function');\n\n}\n\n/**\n * @ngdoc function\n * @name angular.forEach\n * @module ng\n * @kind function\n *\n * @description\n * Invokes the `iterator` function once for each item in `obj` collection, which can be either an\n * object or an array. The `iterator` function is invoked with `iterator(value, key, obj)`, where `value`\n * is the value of an object property or an array element, `key` is the object property key or\n * array element index and obj is the `obj` itself. Specifying a `context` for the function is optional.\n *\n * It is worth noting that `.forEach` does not iterate over inherited properties because it filters\n * using the `hasOwnProperty` method.\n *\n * Unlike ES262's\n * [Array.prototype.forEach](http://www.ecma-international.org/ecma-262/5.1/#sec-15.4.4.18),\n * providing 'undefined' or 'null' values for `obj` will not throw a TypeError, but rather just\n * return the value provided.\n *\n   ```js\n     var values = {name: 'misko', gender: 'male'};\n     var log = [];\n     angular.forEach(values, function(value, key) {\n       this.push(key + ': ' + value);\n     }, log);\n     expect(log).toEqual(['name: misko', 'gender: male']);\n   ```\n *\n * @param {Object|Array} obj Object to iterate over.\n * @param {Function} iterator Iterator function.\n * @param {Object=} context Object to become context (`this`) for the iterator function.\n * @returns {Object|Array} Reference to `obj`.\n */\n\nfunction forEach(obj, iterator, context) {\n  var key, length;\n  if (obj) {\n    if (isFunction(obj)) {\n      for (key in obj) {\n        if (key !== 'prototype' && key !== 'length' && key !== 'name' && obj.hasOwnProperty(key)) {\n          iterator.call(context, obj[key], key, obj);\n        }\n      }\n    } else if (isArray(obj) || isArrayLike(obj)) {\n      var isPrimitive = typeof obj !== 'object';\n      for (key = 0, length = obj.length; key < length; key++) {\n        if (isPrimitive || key in obj) {\n          iterator.call(context, obj[key], key, obj);\n        }\n      }\n    } else if (obj.forEach && obj.forEach !== forEach) {\n        obj.forEach(iterator, context, obj);\n    } else if (isBlankObject(obj)) {\n      // createMap() fast path --- Safe to avoid hasOwnProperty check because prototype chain is empty\n      for (key in obj) {\n        iterator.call(context, obj[key], key, obj);\n      }\n    } else if (typeof obj.hasOwnProperty === 'function') {\n      // Slow path for objects inheriting Object.prototype, hasOwnProperty check needed\n      for (key in obj) {\n        if (obj.hasOwnProperty(key)) {\n          iterator.call(context, obj[key], key, obj);\n        }\n      }\n    } else {\n      // Slow path for objects which do not have a method `hasOwnProperty`\n      for (key in obj) {\n        if (hasOwnProperty.call(obj, key)) {\n          iterator.call(context, obj[key], key, obj);\n        }\n      }\n    }\n  }\n  return obj;\n}\n\nfunction forEachSorted(obj, iterator, context) {\n  var keys = Object.keys(obj).sort();\n  for (var i = 0; i < keys.length; i++) {\n    iterator.call(context, obj[keys[i]], keys[i]);\n  }\n  return keys;\n}\n\n\n/**\n * when using forEach the params are value, key, but it is often useful to have key, value.\n * @param {function(string, *)} iteratorFn\n * @returns {function(*, string)}\n */\nfunction reverseParams(iteratorFn) {\n  return function(value, key) {iteratorFn(key, value);};\n}\n\n/**\n * A consistent way of creating unique IDs in angular.\n *\n * Using simple numbers allows us to generate 28.6 million unique ids per second for 10 years before\n * we hit number precision issues in JavaScript.\n *\n * Math.pow(2,53) / 60 / 60 / 24 / 365 / 10 = 28.6M\n *\n * @returns {number} an unique alpha-numeric string\n */\nfunction nextUid() {\n  return ++uid;\n}\n\n\n/**\n * Set or clear the hashkey for an object.\n * @param obj object\n * @param h the hashkey (!truthy to delete the hashkey)\n */\nfunction setHashKey(obj, h) {\n  if (h) {\n    obj.$$hashKey = h;\n  } else {\n    delete obj.$$hashKey;\n  }\n}\n\n\nfunction baseExtend(dst, objs, deep) {\n  var h = dst.$$hashKey;\n\n  for (var i = 0, ii = objs.length; i < ii; ++i) {\n    var obj = objs[i];\n    if (!isObject(obj) && !isFunction(obj)) continue;\n    var keys = Object.keys(obj);\n    for (var j = 0, jj = keys.length; j < jj; j++) {\n      var key = keys[j];\n      var src = obj[key];\n\n      if (deep && isObject(src)) {\n        if (isDate(src)) {\n          dst[key] = new Date(src.valueOf());\n        } else if (isRegExp(src)) {\n          dst[key] = new RegExp(src);\n        } else if (src.nodeName) {\n          dst[key] = src.cloneNode(true);\n        } else if (isElement(src)) {\n          dst[key] = src.clone();\n        } else {\n          if (key !== '__proto__') {\n            if (!isObject(dst[key])) dst[key] = isArray(src) ? [] : {};\n            baseExtend(dst[key], [src], true);\n          }\n        }\n      } else {\n        dst[key] = src;\n      }\n    }\n  }\n\n  setHashKey(dst, h);\n  return dst;\n}\n\n/**\n * @ngdoc function\n * @name angular.extend\n * @module ng\n * @kind function\n *\n * @description\n * Extends the destination object `dst` by copying own enumerable properties from the `src` object(s)\n * to `dst`. You can specify multiple `src` objects. If you want to preserve original objects, you can do so\n * by passing an empty object as the target: `var object = angular.extend({}, object1, object2)`.\n *\n * **Note:** Keep in mind that `angular.extend` does not support recursive merge (deep copy). Use\n * {@link angular.merge} for this.\n *\n * @param {Object} dst Destination object.\n * @param {...Object} src Source object(s).\n * @returns {Object} Reference to `dst`.\n */\nfunction extend(dst) {\n  return baseExtend(dst, slice.call(arguments, 1), false);\n}\n\n\n/**\n* @ngdoc function\n* @name angular.merge\n* @module ng\n* @kind function\n*\n* @description\n* Deeply extends the destination object `dst` by copying own enumerable properties from the `src` object(s)\n* to `dst`. You can specify multiple `src` objects. If you want to preserve original objects, you can do so\n* by passing an empty object as the target: `var object = angular.merge({}, object1, object2)`.\n*\n* Unlike {@link angular.extend extend()}, `merge()` recursively descends into object properties of source\n* objects, performing a deep copy.\n*\n* @deprecated\n* sinceVersion=\"1.6.5\"\n* This function is deprecated, but will not be removed in the 1.x lifecycle.\n* There are edge cases (see {@link angular.merge#known-issues known issues}) that are not\n* supported by this function. We suggest using another, similar library for all-purpose merging,\n* such as [lodash's merge()](https://lodash.com/docs/4.17.4#merge).\n*\n* @knownIssue\n* This is a list of (known) object types that are not handled correctly by this function:\n* - [`Blob`](https://developer.mozilla.org/docs/Web/API/Blob)\n* - [`MediaStream`](https://developer.mozilla.org/docs/Web/API/MediaStream)\n* - [`CanvasGradient`](https://developer.mozilla.org/docs/Web/API/CanvasGradient)\n* - AngularJS {@link $rootScope.Scope scopes};\n*\n* `angular.merge` also does not support merging objects with circular references.\n*\n* @param {Object} dst Destination object.\n* @param {...Object} src Source object(s).\n* @returns {Object} Reference to `dst`.\n*/\nfunction merge(dst) {\n  return baseExtend(dst, slice.call(arguments, 1), true);\n}\n\n\n\nfunction toInt(str) {\n  return parseInt(str, 10);\n}\n\nvar isNumberNaN = Number.isNaN || function isNumberNaN(num) {\n  // eslint-disable-next-line no-self-compare\n  return num !== num;\n};\n\n\nfunction inherit(parent, extra) {\n  return extend(Object.create(parent), extra);\n}\n\n/**\n * @ngdoc function\n * @name angular.noop\n * @module ng\n * @kind function\n *\n * @description\n * A function that performs no operations. This function can be useful when writing code in the\n * functional style.\n   ```js\n     function foo(callback) {\n       var result = calculateResult();\n       (callback || angular.noop)(result);\n     }\n   ```\n */\nfunction noop() {}\nnoop.$inject = [];\n\n\n/**\n * @ngdoc function\n * @name angular.identity\n * @module ng\n * @kind function\n *\n * @description\n * A function that returns its first argument. This function is useful when writing code in the\n * functional style.\n *\n   ```js\n   function transformer(transformationFn, value) {\n     return (transformationFn || angular.identity)(value);\n   };\n\n   // E.g.\n   function getResult(fn, input) {\n     return (fn || angular.identity)(input);\n   };\n\n   getResult(function(n) { return n * 2; }, 21);   // returns 42\n   getResult(null, 21);                            // returns 21\n   getResult(undefined, 21);                       // returns 21\n   ```\n *\n * @param {*} value to be returned.\n * @returns {*} the value passed in.\n */\nfunction identity($) {return $;}\nidentity.$inject = [];\n\n\nfunction valueFn(value) {return function valueRef() {return value;};}\n\nfunction hasCustomToString(obj) {\n  return isFunction(obj.toString) && obj.toString !== toString;\n}\n\n\n/**\n * @ngdoc function\n * @name angular.isUndefined\n * @module ng\n * @kind function\n *\n * @description\n * Determines if a reference is undefined.\n *\n * @param {*} value Reference to check.\n * @returns {boolean} True if `value` is undefined.\n */\nfunction isUndefined(value) {return typeof value === 'undefined';}\n\n\n/**\n * @ngdoc function\n * @name angular.isDefined\n * @module ng\n * @kind function\n *\n * @description\n * Determines if a reference is defined.\n *\n * @param {*} value Reference to check.\n * @returns {boolean} True if `value` is defined.\n */\nfunction isDefined(value) {return typeof value !== 'undefined';}\n\n\n/**\n * @ngdoc function\n * @name angular.isObject\n * @module ng\n * @kind function\n *\n * @description\n * Determines if a reference is an `Object`. Unlike `typeof` in JavaScript, `null`s are not\n * considered to be objects. Note that JavaScript arrays are objects.\n *\n * @param {*} value Reference to check.\n * @returns {boolean} True if `value` is an `Object` but not `null`.\n */\nfunction isObject(value) {\n  // http://jsperf.com/isobject4\n  return value !== null && typeof value === 'object';\n}\n\n\n/**\n * Determine if a value is an object with a null prototype\n *\n * @returns {boolean} True if `value` is an `Object` with a null prototype\n */\nfunction isBlankObject(value) {\n  return value !== null && typeof value === 'object' && !getPrototypeOf(value);\n}\n\n\n/**\n * @ngdoc function\n * @name angular.isString\n * @module ng\n * @kind function\n *\n * @description\n * Determines if a reference is a `String`.\n *\n * @param {*} value Reference to check.\n * @returns {boolean} True if `value` is a `String`.\n */\nfunction isString(value) {return typeof value === 'string';}\n\n\n/**\n * @ngdoc function\n * @name angular.isNumber\n * @module ng\n * @kind function\n *\n * @description\n * Determines if a reference is a `Number`.\n *\n * This includes the \"special\" numbers `NaN`, `+Infinity` and `-Infinity`.\n *\n * If you wish to exclude these then you can use the native\n * [`isFinite'](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/isFinite)\n * method.\n *\n * @param {*} value Reference to check.\n * @returns {boolean} True if `value` is a `Number`.\n */\nfunction isNumber(value) {return typeof value === 'number';}\n\n\n/**\n * @ngdoc function\n * @name angular.isDate\n * @module ng\n * @kind function\n *\n * @description\n * Determines if a value is a date.\n *\n * @param {*} value Reference to check.\n * @returns {boolean} True if `value` is a `Date`.\n */\nfunction isDate(value) {\n  return toString.call(value) === '[object Date]';\n}\n\n\n/**\n * @ngdoc function\n * @name angular.isArray\n * @module ng\n * @kind function\n *\n * @description\n * Determines if a reference is an `Array`.\n *\n * @param {*} value Reference to check.\n * @returns {boolean} True if `value` is an `Array`.\n */\nfunction isArray(arr) {\n  return Array.isArray(arr) || arr instanceof Array;\n}\n\n/**\n * @description\n * Determines if a reference is an `Error`.\n * Loosely based on https://www.npmjs.com/package/iserror\n *\n * @param {*} value Reference to check.\n * @returns {boolean} True if `value` is an `Error`.\n */\nfunction isError(value) {\n  var tag = toString.call(value);\n  switch (tag) {\n    case '[object Error]': return true;\n    case '[object Exception]': return true;\n    case '[object DOMException]': return true;\n    default: return value instanceof Error;\n  }\n}\n\n/**\n * @ngdoc function\n * @name angular.isFunction\n * @module ng\n * @kind function\n *\n * @description\n * Determines if a reference is a `Function`.\n *\n * @param {*} value Reference to check.\n * @returns {boolean} True if `value` is a `Function`.\n */\nfunction isFunction(value) {return typeof value === 'function';}\n\n\n/**\n * Determines if a value is a regular expression object.\n *\n * @private\n * @param {*} value Reference to check.\n * @returns {boolean} True if `value` is a `RegExp`.\n */\nfunction isRegExp(value) {\n  return toString.call(value) === '[object RegExp]';\n}\n\n\n/**\n * Checks if `obj` is a window object.\n *\n * @private\n * @param {*} obj Object to check\n * @returns {boolean} True if `obj` is a window obj.\n */\nfunction isWindow(obj) {\n  return obj && obj.window === obj;\n}\n\n\nfunction isScope(obj) {\n  return obj && obj.$evalAsync && obj.$watch;\n}\n\n\nfunction isFile(obj) {\n  return toString.call(obj) === '[object File]';\n}\n\n\nfunction isFormData(obj) {\n  return toString.call(obj) === '[object FormData]';\n}\n\n\nfunction isBlob(obj) {\n  return toString.call(obj) === '[object Blob]';\n}\n\n\nfunction isBoolean(value) {\n  return typeof value === 'boolean';\n}\n\n\nfunction isPromiseLike(obj) {\n  return obj && isFunction(obj.then);\n}\n\n\nvar TYPED_ARRAY_REGEXP = /^\\[object (?:Uint8|Uint8Clamped|Uint16|Uint32|Int8|Int16|Int32|Float32|Float64)Array]$/;\nfunction isTypedArray(value) {\n  return value && isNumber(value.length) && TYPED_ARRAY_REGEXP.test(toString.call(value));\n}\n\nfunction isArrayBuffer(obj) {\n  return toString.call(obj) === '[object ArrayBuffer]';\n}\n\n\nvar trim = function(value) {\n  return isString(value) ? value.trim() : value;\n};\n\n// Copied from:\n// http://docs.closure-library.googlecode.com/git/local_closure_goog_string_string.js.source.html#line1021\n// Prereq: s is a string.\nvar escapeForRegexp = function(s) {\n  return s\n    .replace(/([-()[\\]{}+?*.$^|,:#<!\\\\])/g, '\\\\$1')\n    // eslint-disable-next-line no-control-regex\n    .replace(/\\x08/g, '\\\\x08');\n};\n\n\n/**\n * @ngdoc function\n * @name angular.isElement\n * @module ng\n * @kind function\n *\n * @description\n * Determines if a reference is a DOM element (or wrapped jQuery element).\n *\n * @param {*} value Reference to check.\n * @returns {boolean} True if `value` is a DOM element (or wrapped jQuery element).\n */\nfunction isElement(node) {\n  return !!(node &&\n    (node.nodeName  // We are a direct element.\n    || (node.prop && node.attr && node.find)));  // We have an on and find method part of jQuery API.\n}\n\n/**\n * @param str 'key1,key2,...'\n * @returns {object} in the form of {key1:true, key2:true, ...}\n */\nfunction makeMap(str) {\n  var obj = {}, items = str.split(','), i;\n  for (i = 0; i < items.length; i++) {\n    obj[items[i]] = true;\n  }\n  return obj;\n}\n\n\nfunction nodeName_(element) {\n  return lowercase(element.nodeName || (element[0] && element[0].nodeName));\n}\n\nfunction includes(array, obj) {\n  return Array.prototype.indexOf.call(array, obj) !== -1;\n}\n\nfunction arrayRemove(array, value) {\n  var index = array.indexOf(value);\n  if (index >= 0) {\n    array.splice(index, 1);\n  }\n  return index;\n}\n\n/**\n * @ngdoc function\n * @name angular.copy\n * @module ng\n * @kind function\n *\n * @description\n * Creates a deep copy of `source`, which should be an object or an array. This functions is used\n * internally, mostly in the change-detection code. It is not intended as an all-purpose copy\n * function, and has several limitations (see below).\n *\n * * If no destination is supplied, a copy of the object or array is created.\n * * If a destination is provided, all of its elements (for arrays) or properties (for objects)\n *   are deleted and then all elements/properties from the source are copied to it.\n * * If `source` is not an object or array (inc. `null` and `undefined`), `source` is returned.\n * * If `source` is identical to `destination` an exception will be thrown.\n *\n * <br />\n *\n * <div class=\"alert alert-warning\">\n *   Only enumerable properties are taken into account. Non-enumerable properties (both on `source`\n *   and on `destination`) will be ignored.\n * </div>\n *\n * <div class=\"alert alert-warning\">\n *   `angular.copy` does not check if destination and source are of the same type. It's the\n *   developer's responsibility to make sure they are compatible.\n * </div>\n *\n * @knownIssue\n * This is a non-exhaustive list of object types / features that are not handled correctly by\n * `angular.copy`. Note that since this functions is used by the change detection code, this\n * means binding or watching objects of these types (or that include these types) might not work\n * correctly.\n * - [`File`](https://developer.mozilla.org/docs/Web/API/File)\n * - [`Map`](https://developer.mozilla.org/docs/Web/JavaScript/Reference/Global_Objects/Map)\n * - [`ImageData`](https://developer.mozilla.org/docs/Web/API/ImageData)\n * - [`MediaStream`](https://developer.mozilla.org/docs/Web/API/MediaStream)\n * - [`Set`](https://developer.mozilla.org/docs/Web/JavaScript/Reference/Global_Objects/Set)\n * - [`WeakMap`](https://developer.mozilla.org/docs/Web/JavaScript/Reference/Global_Objects/WeakMap)\n * - [`getter`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Functions/get)/\n *   [`setter`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Functions/set)\n *\n * @param {*} source The source that will be used to make a copy. Can be any type, including\n *     primitives, `null`, and `undefined`.\n * @param {(Object|Array)=} destination Destination into which the source is copied. If provided,\n *     must be of the same type as `source`.\n * @returns {*} The copy or updated `destination`, if `destination` was specified.\n *\n * @example\n  <example module=\"copyExample\" name=\"angular-copy\">\n    <file name=\"index.html\">\n      <div ng-controller=\"ExampleController\">\n        <form novalidate class=\"simple-form\">\n          <label>Name: <input type=\"text\" ng-model=\"user.name\" /></label><br />\n          <label>Age:  <input type=\"number\" ng-model=\"user.age\" /></label><br />\n          Gender: <label><input type=\"radio\" ng-model=\"user.gender\" value=\"male\" />male</label>\n                  <label><input type=\"radio\" ng-model=\"user.gender\" value=\"female\" />female</label><br />\n          <button ng-click=\"reset()\">RESET</button>\n          <button ng-click=\"update(user)\">SAVE</button>\n        </form>\n        <pre>form = {{user | json}}</pre>\n        <pre>leader = {{leader | json}}</pre>\n      </div>\n    </file>\n    <file name=\"script.js\">\n      // Module: copyExample\n      angular.\n        module('copyExample', []).\n        controller('ExampleController', ['$scope', function($scope) {\n          $scope.leader = {};\n\n          $scope.reset = function() {\n            // Example with 1 argument\n            $scope.user = angular.copy($scope.leader);\n          };\n\n          $scope.update = function(user) {\n            // Example with 2 arguments\n            angular.copy(user, $scope.leader);\n          };\n\n          $scope.reset();\n        }]);\n    </file>\n  </example>\n */\nfunction copy(source, destination, maxDepth) {\n  var stackSource = [];\n  var stackDest = [];\n  maxDepth = isValidObjectMaxDepth(maxDepth) ? maxDepth : NaN;\n\n  if (destination) {\n    if (isTypedArray(destination) || isArrayBuffer(destination)) {\n      throw ngMinErr('cpta', 'Can\\'t copy! TypedArray destination cannot be mutated.');\n    }\n    if (source === destination) {\n      throw ngMinErr('cpi', 'Can\\'t copy! Source and destination are identical.');\n    }\n\n    // Empty the destination object\n    if (isArray(destination)) {\n      destination.length = 0;\n    } else {\n      forEach(destination, function(value, key) {\n        if (key !== '$$hashKey') {\n          delete destination[key];\n        }\n      });\n    }\n\n    stackSource.push(source);\n    stackDest.push(destination);\n    return copyRecurse(source, destination, maxDepth);\n  }\n\n  return copyElement(source, maxDepth);\n\n  function copyRecurse(source, destination, maxDepth) {\n    maxDepth--;\n    if (maxDepth < 0) {\n      return '...';\n    }\n    var h = destination.$$hashKey;\n    var key;\n    if (isArray(source)) {\n      for (var i = 0, ii = source.length; i < ii; i++) {\n        destination.push(copyElement(source[i], maxDepth));\n      }\n    } else if (isBlankObject(source)) {\n      // createMap() fast path --- Safe to avoid hasOwnProperty check because prototype chain is empty\n      for (key in source) {\n        destination[key] = copyElement(source[key], maxDepth);\n      }\n    } else if (source && typeof source.hasOwnProperty === 'function') {\n      // Slow path, which must rely on hasOwnProperty\n      for (key in source) {\n        if (source.hasOwnProperty(key)) {\n          destination[key] = copyElement(source[key], maxDepth);\n        }\n      }\n    } else {\n      // Slowest path --- hasOwnProperty can't be called as a method\n      for (key in source) {\n        if (hasOwnProperty.call(source, key)) {\n          destination[key] = copyElement(source[key], maxDepth);\n        }\n      }\n    }\n    setHashKey(destination, h);\n    return destination;\n  }\n\n  function copyElement(source, maxDepth) {\n    // Simple values\n    if (!isObject(source)) {\n      return source;\n    }\n\n    // Already copied values\n    var index = stackSource.indexOf(source);\n    if (index !== -1) {\n      return stackDest[index];\n    }\n\n    if (isWindow(source) || isScope(source)) {\n      throw ngMinErr('cpws',\n        'Can\\'t copy! Making copies of Window or Scope instances is not supported.');\n    }\n\n    var needsRecurse = false;\n    var destination = copyType(source);\n\n    if (destination === undefined) {\n      destination = isArray(source) ? [] : Object.create(getPrototypeOf(source));\n      needsRecurse = true;\n    }\n\n    stackSource.push(source);\n    stackDest.push(destination);\n\n    return needsRecurse\n      ? copyRecurse(source, destination, maxDepth)\n      : destination;\n  }\n\n  function copyType(source) {\n    switch (toString.call(source)) {\n      case '[object Int8Array]':\n      case '[object Int16Array]':\n      case '[object Int32Array]':\n      case '[object Float32Array]':\n      case '[object Float64Array]':\n      case '[object Uint8Array]':\n      case '[object Uint8ClampedArray]':\n      case '[object Uint16Array]':\n      case '[object Uint32Array]':\n        return new source.constructor(copyElement(source.buffer), source.byteOffset, source.length);\n\n      case '[object ArrayBuffer]':\n        // Support: IE10\n        if (!source.slice) {\n          // If we're in this case we know the environment supports ArrayBuffer\n          /* eslint-disable no-undef */\n          var copied = new ArrayBuffer(source.byteLength);\n          new Uint8Array(copied).set(new Uint8Array(source));\n          /* eslint-enable */\n          return copied;\n        }\n        return source.slice(0);\n\n      case '[object Boolean]':\n      case '[object Number]':\n      case '[object String]':\n      case '[object Date]':\n        return new source.constructor(source.valueOf());\n\n      case '[object RegExp]':\n        var re = new RegExp(source.source, source.toString().match(/[^/]*$/)[0]);\n        re.lastIndex = source.lastIndex;\n        return re;\n\n      case '[object Blob]':\n        return new source.constructor([source], {type: source.type});\n    }\n\n    if (isFunction(source.cloneNode)) {\n      return source.cloneNode(true);\n    }\n  }\n}\n\n\n// eslint-disable-next-line no-self-compare\nfunction simpleCompare(a, b) { return a === b || (a !== a && b !== b); }\n\n\n/**\n * @ngdoc function\n * @name angular.equals\n * @module ng\n * @kind function\n *\n * @description\n * Determines if two objects or two values are equivalent. Supports value types, regular\n * expressions, arrays and objects.\n *\n * Two objects or values are considered equivalent if at least one of the following is true:\n *\n * * Both objects or values pass `===` comparison.\n * * Both objects or values are of the same type and all of their properties are equal by\n *   comparing them with `angular.equals`.\n * * Both values are NaN. (In JavaScript, NaN == NaN => false. But we consider two NaN as equal)\n * * Both values represent the same regular expression (In JavaScript,\n *   /abc/ == /abc/ => false. But we consider two regular expressions as equal when their textual\n *   representation matches).\n *\n * During a property comparison, properties of `function` type and properties with names\n * that begin with `$` are ignored.\n *\n * Scope and DOMWindow objects are being compared only by identify (`===`).\n *\n * @param {*} o1 Object or value to compare.\n * @param {*} o2 Object or value to compare.\n * @returns {boolean} True if arguments are equal.\n *\n * @example\n   <example module=\"equalsExample\" name=\"equalsExample\">\n     <file name=\"index.html\">\n      <div ng-controller=\"ExampleController\">\n        <form novalidate>\n          <h3>User 1</h3>\n          Name: <input type=\"text\" ng-model=\"user1.name\">\n          Age: <input type=\"number\" ng-model=\"user1.age\">\n\n          <h3>User 2</h3>\n          Name: <input type=\"text\" ng-model=\"user2.name\">\n          Age: <input type=\"number\" ng-model=\"user2.age\">\n\n          <div>\n            <br/>\n            <input type=\"button\" value=\"Compare\" ng-click=\"compare()\">\n          </div>\n          User 1: <pre>{{user1 | json}}</pre>\n          User 2: <pre>{{user2 | json}}</pre>\n          Equal: <pre>{{result}}</pre>\n        </form>\n      </div>\n    </file>\n    <file name=\"script.js\">\n        angular.module('equalsExample', []).controller('ExampleController', ['$scope', function($scope) {\n          $scope.user1 = {};\n          $scope.user2 = {};\n          $scope.compare = function() {\n            $scope.result = angular.equals($scope.user1, $scope.user2);\n          };\n        }]);\n    </file>\n  </example>\n */\nfunction equals(o1, o2) {\n  if (o1 === o2) return true;\n  if (o1 === null || o2 === null) return false;\n  // eslint-disable-next-line no-self-compare\n  if (o1 !== o1 && o2 !== o2) return true; // NaN === NaN\n  var t1 = typeof o1, t2 = typeof o2, length, key, keySet;\n  if (t1 === t2 && t1 === 'object') {\n    if (isArray(o1)) {\n      if (!isArray(o2)) return false;\n      if ((length = o1.length) === o2.length) {\n        for (key = 0; key < length; key++) {\n          if (!equals(o1[key], o2[key])) return false;\n        }\n        return true;\n      }\n    } else if (isDate(o1)) {\n      if (!isDate(o2)) return false;\n      return simpleCompare(o1.getTime(), o2.getTime());\n    } else if (isRegExp(o1)) {\n      if (!isRegExp(o2)) return false;\n      return o1.toString() === o2.toString();\n    } else {\n      if (isScope(o1) || isScope(o2) || isWindow(o1) || isWindow(o2) ||\n        isArray(o2) || isDate(o2) || isRegExp(o2)) return false;\n      keySet = createMap();\n      for (key in o1) {\n        if (key.charAt(0) === '$' || isFunction(o1[key])) continue;\n        if (!equals(o1[key], o2[key])) return false;\n        keySet[key] = true;\n      }\n      for (key in o2) {\n        if (!(key in keySet) &&\n            key.charAt(0) !== '$' &&\n            isDefined(o2[key]) &&\n            !isFunction(o2[key])) return false;\n      }\n      return true;\n    }\n  }\n  return false;\n}\n\nvar csp = function() {\n  if (!isDefined(csp.rules)) {\n\n\n    var ngCspElement = (window.document.querySelector('[ng-csp]') ||\n                    window.document.querySelector('[data-ng-csp]'));\n\n    if (ngCspElement) {\n      var ngCspAttribute = ngCspElement.getAttribute('ng-csp') ||\n                    ngCspElement.getAttribute('data-ng-csp');\n      csp.rules = {\n        noUnsafeEval: !ngCspAttribute || (ngCspAttribute.indexOf('no-unsafe-eval') !== -1),\n        noInlineStyle: !ngCspAttribute || (ngCspAttribute.indexOf('no-inline-style') !== -1)\n      };\n    } else {\n      csp.rules = {\n        noUnsafeEval: noUnsafeEval(),\n        noInlineStyle: false\n      };\n    }\n  }\n\n  return csp.rules;\n\n  function noUnsafeEval() {\n    try {\n      // eslint-disable-next-line no-new, no-new-func\n      new Function('');\n      return false;\n    } catch (e) {\n      return true;\n    }\n  }\n};\n\n/**\n * @ngdoc directive\n * @module ng\n * @name ngJq\n *\n * @element ANY\n * @param {string=} ngJq the name of the library available under `window`\n * to be used for angular.element\n * @description\n * Use this directive to force the angular.element library.  This should be\n * used to force either jqLite by leaving ng-jq blank or setting the name of\n * the jquery variable under window (eg. jQuery).\n *\n * Since AngularJS looks for this directive when it is loaded (doesn't wait for the\n * DOMContentLoaded event), it must be placed on an element that comes before the script\n * which loads angular. Also, only the first instance of `ng-jq` will be used and all\n * others ignored.\n *\n * @example\n * This example shows how to force jqLite using the `ngJq` directive to the `html` tag.\n ```html\n <!doctype html>\n <html ng-app ng-jq>\n ...\n ...\n </html>\n ```\n * @example\n * This example shows how to use a jQuery based library of a different name.\n * The library name must be available at the top most 'window'.\n ```html\n <!doctype html>\n <html ng-app ng-jq=\"jQueryLib\">\n ...\n ...\n </html>\n ```\n */\nvar jq = function() {\n  if (isDefined(jq.name_)) return jq.name_;\n  var el;\n  var i, ii = ngAttrPrefixes.length, prefix, name;\n  for (i = 0; i < ii; ++i) {\n    prefix = ngAttrPrefixes[i];\n    el = window.document.querySelector('[' + prefix.replace(':', '\\\\:') + 'jq]');\n    if (el) {\n      name = el.getAttribute(prefix + 'jq');\n      break;\n    }\n  }\n\n  return (jq.name_ = name);\n};\n\nfunction concat(array1, array2, index) {\n  return array1.concat(slice.call(array2, index));\n}\n\nfunction sliceArgs(args, startIndex) {\n  return slice.call(args, startIndex || 0);\n}\n\n\n/**\n * @ngdoc function\n * @name angular.bind\n * @module ng\n * @kind function\n *\n * @description\n * Returns a function which calls function `fn` bound to `self` (`self` becomes the `this` for\n * `fn`). You can supply optional `args` that are prebound to the function. This feature is also\n * known as [partial application](http://en.wikipedia.org/wiki/Partial_application), as\n * distinguished from [function currying](http://en.wikipedia.org/wiki/Currying#Contrast_with_partial_function_application).\n *\n * @param {Object} self Context which `fn` should be evaluated in.\n * @param {function()} fn Function to be bound.\n * @param {...*} args Optional arguments to be prebound to the `fn` function call.\n * @returns {function()} Function that wraps the `fn` with all the specified bindings.\n */\nfunction bind(self, fn) {\n  var curryArgs = arguments.length > 2 ? sliceArgs(arguments, 2) : [];\n  if (isFunction(fn) && !(fn instanceof RegExp)) {\n    return curryArgs.length\n      ? function() {\n          return arguments.length\n            ? fn.apply(self, concat(curryArgs, arguments, 0))\n            : fn.apply(self, curryArgs);\n        }\n      : function() {\n          return arguments.length\n            ? fn.apply(self, arguments)\n            : fn.call(self);\n        };\n  } else {\n    // In IE, native methods are not functions so they cannot be bound (note: they don't need to be).\n    return fn;\n  }\n}\n\n\nfunction toJsonReplacer(key, value) {\n  var val = value;\n\n  if (typeof key === 'string' && key.charAt(0) === '$' && key.charAt(1) === '$') {\n    val = undefined;\n  } else if (isWindow(value)) {\n    val = '$WINDOW';\n  } else if (value &&  window.document === value) {\n    val = '$DOCUMENT';\n  } else if (isScope(value)) {\n    val = '$SCOPE';\n  }\n\n  return val;\n}\n\n\n/**\n * @ngdoc function\n * @name angular.toJson\n * @module ng\n * @kind function\n *\n * @description\n * Serializes input into a JSON-formatted string. Properties with leading $$ characters will be\n * stripped since AngularJS uses this notation internally.\n *\n * @param {Object|Array|Date|string|number|boolean} obj Input to be serialized into JSON.\n * @param {boolean|number} [pretty=2] If set to true, the JSON output will contain newlines and whitespace.\n *    If set to an integer, the JSON output will contain that many spaces per indentation.\n * @returns {string|undefined} JSON-ified string representing `obj`.\n * @knownIssue\n *\n * The Safari browser throws a `RangeError` instead of returning `null` when it tries to stringify a `Date`\n * object with an invalid date value. The only reliable way to prevent this is to monkeypatch the\n * `Date.prototype.toJSON` method as follows:\n *\n * ```\n * var _DatetoJSON = Date.prototype.toJSON;\n * Date.prototype.toJSON = function() {\n *   try {\n *     return _DatetoJSON.call(this);\n *   } catch(e) {\n *     if (e instanceof RangeError) {\n *       return null;\n *     }\n *     throw e;\n *   }\n * };\n * ```\n *\n * See https://github.com/angular/angular.js/pull/14221 for more information.\n */\nfunction toJson(obj, pretty) {\n  if (isUndefined(obj)) return undefined;\n  if (!isNumber(pretty)) {\n    pretty = pretty ? 2 : null;\n  }\n  return JSON.stringify(obj, toJsonReplacer, pretty);\n}\n\n\n/**\n * @ngdoc function\n * @name angular.fromJson\n * @module ng\n * @kind function\n *\n * @description\n * Deserializes a JSON string.\n *\n * @param {string} json JSON string to deserialize.\n * @returns {Object|Array|string|number} Deserialized JSON string.\n */\nfunction fromJson(json) {\n  return isString(json)\n      ? JSON.parse(json)\n      : json;\n}\n\n\nvar ALL_COLONS = /:/g;\nfunction timezoneToOffset(timezone, fallback) {\n  // Support: IE 9-11 only, Edge 13-15+\n  // IE/Edge do not \"understand\" colon (`:`) in timezone\n  timezone = timezone.replace(ALL_COLONS, '');\n  var requestedTimezoneOffset = Date.parse('Jan 01, 1970 00:00:00 ' + timezone) / 60000;\n  return isNumberNaN(requestedTimezoneOffset) ? fallback : requestedTimezoneOffset;\n}\n\n\nfunction addDateMinutes(date, minutes) {\n  date = new Date(date.getTime());\n  date.setMinutes(date.getMinutes() + minutes);\n  return date;\n}\n\n\nfunction convertTimezoneToLocal(date, timezone, reverse) {\n  reverse = reverse ? -1 : 1;\n  var dateTimezoneOffset = date.getTimezoneOffset();\n  var timezoneOffset = timezoneToOffset(timezone, dateTimezoneOffset);\n  return addDateMinutes(date, reverse * (timezoneOffset - dateTimezoneOffset));\n}\n\n\n/**\n * @returns {string} Returns the string representation of the element.\n */\nfunction startingTag(element) {\n  element = jqLite(element).clone().empty();\n  var elemHtml = jqLite('<div></div>').append(element).html();\n  try {\n    return element[0].nodeType === NODE_TYPE_TEXT ? lowercase(elemHtml) :\n        elemHtml.\n          match(/^(<[^>]+>)/)[1].\n          replace(/^<([\\w-]+)/, function(match, nodeName) {return '<' + lowercase(nodeName);});\n  } catch (e) {\n    return lowercase(elemHtml);\n  }\n\n}\n\n\n/////////////////////////////////////////////////\n\n/**\n * Tries to decode the URI component without throwing an exception.\n *\n * @private\n * @param str value potential URI component to check.\n * @returns {boolean} True if `value` can be decoded\n * with the decodeURIComponent function.\n */\nfunction tryDecodeURIComponent(value) {\n  try {\n    return decodeURIComponent(value);\n  } catch (e) {\n    // Ignore any invalid uri component.\n  }\n}\n\n\n/**\n * Parses an escaped url query string into key-value pairs.\n * @returns {Object.<string,boolean|Array>}\n */\nfunction parseKeyValue(/**string*/keyValue) {\n  var obj = {};\n  forEach((keyValue || '').split('&'), function(keyValue) {\n    var splitPoint, key, val;\n    if (keyValue) {\n      key = keyValue = keyValue.replace(/\\+/g,'%20');\n      splitPoint = keyValue.indexOf('=');\n      if (splitPoint !== -1) {\n        key = keyValue.substring(0, splitPoint);\n        val = keyValue.substring(splitPoint + 1);\n      }\n      key = tryDecodeURIComponent(key);\n      if (isDefined(key)) {\n        val = isDefined(val) ? tryDecodeURIComponent(val) : true;\n        if (!hasOwnProperty.call(obj, key)) {\n          obj[key] = val;\n        } else if (isArray(obj[key])) {\n          obj[key].push(val);\n        } else {\n          obj[key] = [obj[key],val];\n        }\n      }\n    }\n  });\n  return obj;\n}\n\nfunction toKeyValue(obj) {\n  var parts = [];\n  forEach(obj, function(value, key) {\n    if (isArray(value)) {\n      forEach(value, function(arrayValue) {\n        parts.push(encodeUriQuery(key, true) +\n                   (arrayValue === true ? '' : '=' + encodeUriQuery(arrayValue, true)));\n      });\n    } else {\n    parts.push(encodeUriQuery(key, true) +\n               (value === true ? '' : '=' + encodeUriQuery(value, true)));\n    }\n  });\n  return parts.length ? parts.join('&') : '';\n}\n\n\n/**\n * We need our custom method because encodeURIComponent is too aggressive and doesn't follow\n * http://www.ietf.org/rfc/rfc3986.txt with regards to the character set (pchar) allowed in path\n * segments:\n *    segment       = *pchar\n *    pchar         = unreserved / pct-encoded / sub-delims / \":\" / \"@\"\n *    pct-encoded   = \"%\" HEXDIG HEXDIG\n *    unreserved    = ALPHA / DIGIT / \"-\" / \".\" / \"_\" / \"~\"\n *    sub-delims    = \"!\" / \"$\" / \"&\" / \"'\" / \"(\" / \")\"\n *                     / \"*\" / \"+\" / \",\" / \";\" / \"=\"\n */\nfunction encodeUriSegment(val) {\n  return encodeUriQuery(val, true).\n             replace(/%26/gi, '&').\n             replace(/%3D/gi, '=').\n             replace(/%2B/gi, '+');\n}\n\n\n/**\n * This method is intended for encoding *key* or *value* parts of query component. We need a custom\n * method because encodeURIComponent is too aggressive and encodes stuff that doesn't have to be\n * encoded per http://tools.ietf.org/html/rfc3986:\n *    query         = *( pchar / \"/\" / \"?\" )\n *    pchar         = unreserved / pct-encoded / sub-delims / \":\" / \"@\"\n *    unreserved    = ALPHA / DIGIT / \"-\" / \".\" / \"_\" / \"~\"\n *    pct-encoded   = \"%\" HEXDIG HEXDIG\n *    sub-delims    = \"!\" / \"$\" / \"&\" / \"'\" / \"(\" / \")\"\n *                     / \"*\" / \"+\" / \",\" / \";\" / \"=\"\n */\nfunction encodeUriQuery(val, pctEncodeSpaces) {\n  return encodeURIComponent(val).\n             replace(/%40/gi, '@').\n             replace(/%3A/gi, ':').\n             replace(/%24/g, '$').\n             replace(/%2C/gi, ',').\n             replace(/%3B/gi, ';').\n             replace(/%20/g, (pctEncodeSpaces ? '%20' : '+'));\n}\n\nvar ngAttrPrefixes = ['ng-', 'data-ng-', 'ng:', 'x-ng-'];\n\nfunction getNgAttribute(element, ngAttr) {\n  var attr, i, ii = ngAttrPrefixes.length;\n  for (i = 0; i < ii; ++i) {\n    attr = ngAttrPrefixes[i] + ngAttr;\n    if (isString(attr = element.getAttribute(attr))) {\n      return attr;\n    }\n  }\n  return null;\n}\n\nfunction allowAutoBootstrap(document) {\n  var script = document.currentScript;\n\n  if (!script) {\n    // Support: IE 9-11 only\n    // IE does not have `document.currentScript`\n    return true;\n  }\n\n  // If the `currentScript` property has been clobbered just return false, since this indicates a probable attack\n  if (!(script instanceof window.HTMLScriptElement || script instanceof window.SVGScriptElement)) {\n    return false;\n  }\n\n  var attributes = script.attributes;\n  var srcs = [attributes.getNamedItem('src'), attributes.getNamedItem('href'), attributes.getNamedItem('xlink:href')];\n\n  return srcs.every(function(src) {\n    if (!src) {\n      return true;\n    }\n    if (!src.value) {\n      return false;\n    }\n\n    var link = document.createElement('a');\n    link.href = src.value;\n\n    if (document.location.origin === link.origin) {\n      // Same-origin resources are always allowed, even for banned URL schemes.\n      return true;\n    }\n    // Disabled bootstrapping unless angular.js was loaded from a known scheme used on the web.\n    // This is to prevent angular.js bundled with browser extensions from being used to bypass the\n    // content security policy in web pages and other browser extensions.\n    switch (link.protocol) {\n      case 'http:':\n      case 'https:':\n      case 'ftp:':\n      case 'blob:':\n      case 'file:':\n      case 'data:':\n        return true;\n      default:\n        return false;\n    }\n  });\n}\n\n// Cached as it has to run during loading so that document.currentScript is available.\nvar isAutoBootstrapAllowed = allowAutoBootstrap(window.document);\n\n/**\n * @ngdoc directive\n * @name ngApp\n * @module ng\n *\n * @element ANY\n * @param {angular.Module} ngApp an optional application\n *   {@link angular.module module} name to load.\n * @param {boolean=} ngStrictDi if this attribute is present on the app element, the injector will be\n *   created in \"strict-di\" mode. This means that the application will fail to invoke functions which\n *   do not use explicit function annotation (and are thus unsuitable for minification), as described\n *   in {@link guide/di the Dependency Injection guide}, and useful debugging info will assist in\n *   tracking down the root of these bugs.\n *\n * @description\n *\n * Use this directive to **auto-bootstrap** an AngularJS application. The `ngApp` directive\n * designates the **root element** of the application and is typically placed near the root element\n * of the page - e.g. on the `<body>` or `<html>` tags.\n *\n * There are a few things to keep in mind when using `ngApp`:\n * - only one AngularJS application can be auto-bootstrapped per HTML document. The first `ngApp`\n *   found in the document will be used to define the root element to auto-bootstrap as an\n *   application. To run multiple applications in an HTML document you must manually bootstrap them using\n *   {@link angular.bootstrap} instead.\n * - AngularJS applications cannot be nested within each other.\n * - Do not use a directive that uses {@link ng.$compile#transclusion transclusion} on the same element as `ngApp`.\n *   This includes directives such as {@link ng.ngIf `ngIf`}, {@link ng.ngInclude `ngInclude`} and\n *   {@link ngRoute.ngView `ngView`}.\n *   Doing this misplaces the app {@link ng.$rootElement `$rootElement`} and the app's {@link auto.$injector injector},\n *   causing animations to stop working and making the injector inaccessible from outside the app.\n *\n * You can specify an **AngularJS module** to be used as the root module for the application.  This\n * module will be loaded into the {@link auto.$injector} when the application is bootstrapped. It\n * should contain the application code needed or have dependencies on other modules that will\n * contain the code. See {@link angular.module} for more information.\n *\n * In the example below if the `ngApp` directive were not placed on the `html` element then the\n * document would not be compiled, the `AppController` would not be instantiated and the `{{ a+b }}`\n * would not be resolved to `3`.\n *\n * @example\n *\n * ### Simple Usage\n *\n * `ngApp` is the easiest, and most common way to bootstrap an application.\n *\n <example module=\"ngAppDemo\" name=\"ng-app\">\n   <file name=\"index.html\">\n   <div ng-controller=\"ngAppDemoController\">\n     I can add: {{a}} + {{b}} =  {{ a+b }}\n   </div>\n   </file>\n   <file name=\"script.js\">\n   angular.module('ngAppDemo', []).controller('ngAppDemoController', function($scope) {\n     $scope.a = 1;\n     $scope.b = 2;\n   });\n   </file>\n </example>\n *\n * @example\n *\n * ### With `ngStrictDi`\n *\n * Using `ngStrictDi`, you would see something like this:\n *\n <example ng-app-included=\"true\" name=\"strict-di\">\n   <file name=\"index.html\">\n   <div ng-app=\"ngAppStrictDemo\" ng-strict-di>\n       <div ng-controller=\"GoodController1\">\n           I can add: {{a}} + {{b}} =  {{ a+b }}\n\n           <p>This renders because the controller does not fail to\n              instantiate, by using explicit annotation style (see\n              script.js for details)\n           </p>\n       </div>\n\n       <div ng-controller=\"GoodController2\">\n           Name: <input ng-model=\"name\"><br />\n           Hello, {{name}}!\n\n           <p>This renders because the controller does not fail to\n              instantiate, by using explicit annotation style\n              (see script.js for details)\n           </p>\n       </div>\n\n       <div ng-controller=\"BadController\">\n           I can add: {{a}} + {{b}} =  {{ a+b }}\n\n           <p>The controller could not be instantiated, due to relying\n              on automatic function annotations (which are disabled in\n              strict mode). As such, the content of this section is not\n              interpolated, and there should be an error in your web console.\n           </p>\n       </div>\n   </div>\n   </file>\n   <file name=\"script.js\">\n   angular.module('ngAppStrictDemo', [])\n     // BadController will fail to instantiate, due to relying on automatic function annotation,\n     // rather than an explicit annotation\n     .controller('BadController', function($scope) {\n       $scope.a = 1;\n       $scope.b = 2;\n     })\n     // Unlike BadController, GoodController1 and GoodController2 will not fail to be instantiated,\n     // due to using explicit annotations using the array style and $inject property, respectively.\n     .controller('GoodController1', ['$scope', function($scope) {\n       $scope.a = 1;\n       $scope.b = 2;\n     }])\n     .controller('GoodController2', GoodController2);\n     function GoodController2($scope) {\n       $scope.name = 'World';\n     }\n     GoodController2.$inject = ['$scope'];\n   </file>\n   <file name=\"style.css\">\n   div[ng-controller] {\n       margin-bottom: 1em;\n       -webkit-border-radius: 4px;\n       border-radius: 4px;\n       border: 1px solid;\n       padding: .5em;\n   }\n   div[ng-controller^=Good] {\n       border-color: #d6e9c6;\n       background-color: #dff0d8;\n       color: #3c763d;\n   }\n   div[ng-controller^=Bad] {\n       border-color: #ebccd1;\n       background-color: #f2dede;\n       color: #a94442;\n       margin-bottom: 0;\n   }\n   </file>\n </example>\n */\nfunction angularInit(element, bootstrap) {\n  var appElement,\n      module,\n      config = {};\n\n  // The element `element` has priority over any other element.\n  forEach(ngAttrPrefixes, function(prefix) {\n    var name = prefix + 'app';\n\n    if (!appElement && element.hasAttribute && element.hasAttribute(name)) {\n      appElement = element;\n      module = element.getAttribute(name);\n    }\n  });\n  forEach(ngAttrPrefixes, function(prefix) {\n    var name = prefix + 'app';\n    var candidate;\n\n    if (!appElement && (candidate = element.querySelector('[' + name.replace(':', '\\\\:') + ']'))) {\n      appElement = candidate;\n      module = candidate.getAttribute(name);\n    }\n  });\n  if (appElement) {\n    if (!isAutoBootstrapAllowed) {\n      window.console.error('AngularJS: disabling automatic bootstrap. <script> protocol indicates ' +\n          'an extension, document.location.href does not match.');\n      return;\n    }\n    config.strictDi = getNgAttribute(appElement, 'strict-di') !== null;\n    bootstrap(appElement, module ? [module] : [], config);\n  }\n}\n\n/**\n * @ngdoc function\n * @name angular.bootstrap\n * @module ng\n * @description\n * Use this function to manually start up AngularJS application.\n *\n * For more information, see the {@link guide/bootstrap Bootstrap guide}.\n *\n * AngularJS will detect if it has been loaded into the browser more than once and only allow the\n * first loaded script to be bootstrapped and will report a warning to the browser console for\n * each of the subsequent scripts. This prevents strange results in applications, where otherwise\n * multiple instances of AngularJS try to work on the DOM.\n *\n * <div class=\"alert alert-warning\">\n * **Note:** Protractor based end-to-end tests cannot use this function to bootstrap manually.\n * They must use {@link ng.directive:ngApp ngApp}.\n * </div>\n *\n * <div class=\"alert alert-warning\">\n * **Note:** Do not bootstrap the app on an element with a directive that uses {@link ng.$compile#transclusion transclusion},\n * such as {@link ng.ngIf `ngIf`}, {@link ng.ngInclude `ngInclude`} and {@link ngRoute.ngView `ngView`}.\n * Doing this misplaces the app {@link ng.$rootElement `$rootElement`} and the app's {@link auto.$injector injector},\n * causing animations to stop working and making the injector inaccessible from outside the app.\n * </div>\n *\n * ```html\n * <!doctype html>\n * <html>\n * <body>\n * <div ng-controller=\"WelcomeController\">\n *   {{greeting}}\n * </div>\n *\n * <script src=\"angular.js\"></script>\n * <script>\n *   var app = angular.module('demo', [])\n *   .controller('WelcomeController', function($scope) {\n *       $scope.greeting = 'Welcome!';\n *   });\n *   angular.bootstrap(document, ['demo']);\n * </script>\n * </body>\n * </html>\n * ```\n *\n * @param {DOMElement} element DOM element which is the root of AngularJS application.\n * @param {Array<String|Function|Array>=} modules an array of modules to load into the application.\n *     Each item in the array should be the name of a predefined module or a (DI annotated)\n *     function that will be invoked by the injector as a `config` block.\n *     See: {@link angular.module modules}\n * @param {Object=} config an object for defining configuration options for the application. The\n *     following keys are supported:\n *\n * * `strictDi` - disable automatic function annotation for the application. This is meant to\n *   assist in finding bugs which break minified code. Defaults to `false`.\n *\n * @returns {auto.$injector} Returns the newly created injector for this app.\n */\nfunction bootstrap(element, modules, config) {\n  if (!isObject(config)) config = {};\n  var defaultConfig = {\n    strictDi: false\n  };\n  config = extend(defaultConfig, config);\n  var doBootstrap = function() {\n    element = jqLite(element);\n\n    if (element.injector()) {\n      var tag = (element[0] === window.document) ? 'document' : startingTag(element);\n      // Encode angle brackets to prevent input from being sanitized to empty string #8683.\n      throw ngMinErr(\n          'btstrpd',\n          'App already bootstrapped with this element \\'{0}\\'',\n          tag.replace(/</,'&lt;').replace(/>/,'&gt;'));\n    }\n\n    modules = modules || [];\n    modules.unshift(['$provide', function($provide) {\n      $provide.value('$rootElement', element);\n    }]);\n\n    if (config.debugInfoEnabled) {\n      // Pushing so that this overrides `debugInfoEnabled` setting defined in user's `modules`.\n      modules.push(['$compileProvider', function($compileProvider) {\n        $compileProvider.debugInfoEnabled(true);\n      }]);\n    }\n\n    modules.unshift('ng');\n    var injector = createInjector(modules, config.strictDi);\n    injector.invoke(['$rootScope', '$rootElement', '$compile', '$injector',\n       function bootstrapApply(scope, element, compile, injector) {\n        scope.$apply(function() {\n          element.data('$injector', injector);\n          compile(element)(scope);\n        });\n      }]\n    );\n    return injector;\n  };\n\n  var NG_ENABLE_DEBUG_INFO = /^NG_ENABLE_DEBUG_INFO!/;\n  var NG_DEFER_BOOTSTRAP = /^NG_DEFER_BOOTSTRAP!/;\n\n  if (window && NG_ENABLE_DEBUG_INFO.test(window.name)) {\n    config.debugInfoEnabled = true;\n    window.name = window.name.replace(NG_ENABLE_DEBUG_INFO, '');\n  }\n\n  if (window && !NG_DEFER_BOOTSTRAP.test(window.name)) {\n    return doBootstrap();\n  }\n\n  window.name = window.name.replace(NG_DEFER_BOOTSTRAP, '');\n  angular.resumeBootstrap = function(extraModules) {\n    forEach(extraModules, function(module) {\n      modules.push(module);\n    });\n    return doBootstrap();\n  };\n\n  if (isFunction(angular.resumeDeferredBootstrap)) {\n    angular.resumeDeferredBootstrap();\n  }\n}\n\n/**\n * @ngdoc function\n * @name angular.reloadWithDebugInfo\n * @module ng\n * @description\n * Use this function to reload the current application with debug information turned on.\n * This takes precedence over a call to `$compileProvider.debugInfoEnabled(false)`.\n *\n * See {@link ng.$compileProvider#debugInfoEnabled} for more.\n */\nfunction reloadWithDebugInfo() {\n  window.name = 'NG_ENABLE_DEBUG_INFO!' + window.name;\n  window.location.reload();\n}\n\n/**\n * @name angular.getTestability\n * @module ng\n * @description\n * Get the testability service for the instance of AngularJS on the given\n * element.\n * @param {DOMElement} element DOM element which is the root of AngularJS application.\n */\nfunction getTestability(rootElement) {\n  var injector = angular.element(rootElement).injector();\n  if (!injector) {\n    throw ngMinErr('test',\n      'no injector found for element argument to getTestability');\n  }\n  return injector.get('$$testability');\n}\n\nvar SNAKE_CASE_REGEXP = /[A-Z]/g;\nfunction snake_case(name, separator) {\n  separator = separator || '_';\n  return name.replace(SNAKE_CASE_REGEXP, function(letter, pos) {\n    return (pos ? separator : '') + letter.toLowerCase();\n  });\n}\n\nvar bindJQueryFired = false;\nfunction bindJQuery() {\n  var originalCleanData;\n\n  if (bindJQueryFired) {\n    return;\n  }\n\n  // bind to jQuery if present;\n  var jqName = jq();\n  jQuery = isUndefined(jqName) ? window.jQuery :   // use jQuery (if present)\n           !jqName             ? undefined     :   // use jqLite\n                                 window[jqName];   // use jQuery specified by `ngJq`\n\n  // Use jQuery if it exists with proper functionality, otherwise default to us.\n  // AngularJS 1.2+ requires jQuery 1.7+ for on()/off() support.\n  // AngularJS 1.3+ technically requires at least jQuery 2.1+ but it may work with older\n  // versions. It will not work for sure with jQuery <1.7, though.\n  if (jQuery && jQuery.fn.on) {\n    jqLite = jQuery;\n    extend(jQuery.fn, {\n      scope: JQLitePrototype.scope,\n      isolateScope: JQLitePrototype.isolateScope,\n      controller: /** @type {?} */ (JQLitePrototype).controller,\n      injector: JQLitePrototype.injector,\n      inheritedData: JQLitePrototype.inheritedData\n    });\n  } else {\n    jqLite = JQLite;\n  }\n\n  // All nodes removed from the DOM via various jqLite/jQuery APIs like .remove()\n  // are passed through jqLite/jQuery.cleanData. Monkey-patch this method to fire\n  // the $destroy event on all removed nodes.\n  originalCleanData = jqLite.cleanData;\n  jqLite.cleanData = function(elems) {\n    var events;\n    for (var i = 0, elem; (elem = elems[i]) != null; i++) {\n      events = (jqLite._data(elem) || {}).events;\n      if (events && events.$destroy) {\n        jqLite(elem).triggerHandler('$destroy');\n      }\n    }\n    originalCleanData(elems);\n  };\n\n  angular.element = jqLite;\n\n  // Prevent double-proxying.\n  bindJQueryFired = true;\n}\n\n/**\n * @ngdoc function\n * @name angular.UNSAFE_restoreLegacyJqLiteXHTMLReplacement\n * @module ng\n * @kind function\n *\n * @description\n * Restores the pre-1.8 behavior of jqLite that turns XHTML-like strings like\n * `<div /><span />` to `<div></div><span></span>` instead of `<div><span></span></div>`.\n * The new behavior is a security fix. Thus, if you need to call this function, please try to adjust\n * your code for this change and remove your use of this function as soon as possible.\n\n * Note that this only patches jqLite. If you use jQuery 3.5.0 or newer, please read the\n * [jQuery 3.5 upgrade guide](https://jquery.com/upgrade-guide/3.5/) for more details\n * about the workarounds.\n */\nfunction UNSAFE_restoreLegacyJqLiteXHTMLReplacement() {\n  JQLite.legacyXHTMLReplacement = true;\n}\n\n/**\n * throw error if the argument is falsy.\n */\nfunction assertArg(arg, name, reason) {\n  if (!arg) {\n    throw ngMinErr('areq', 'Argument \\'{0}\\' is {1}', (name || '?'), (reason || 'required'));\n  }\n  return arg;\n}\n\nfunction assertArgFn(arg, name, acceptArrayAnnotation) {\n  if (acceptArrayAnnotation && isArray(arg)) {\n      arg = arg[arg.length - 1];\n  }\n\n  assertArg(isFunction(arg), name, 'not a function, got ' +\n      (arg && typeof arg === 'object' ? arg.constructor.name || 'Object' : typeof arg));\n  return arg;\n}\n\n/**\n * throw error if the name given is hasOwnProperty\n * @param  {String} name    the name to test\n * @param  {String} context the context in which the name is used, such as module or directive\n */\nfunction assertNotHasOwnProperty(name, context) {\n  if (name === 'hasOwnProperty') {\n    throw ngMinErr('badname', 'hasOwnProperty is not a valid {0} name', context);\n  }\n}\n\n/**\n * Return the value accessible from the object by path. Any undefined traversals are ignored\n * @param {Object} obj starting object\n * @param {String} path path to traverse\n * @param {boolean} [bindFnToScope=true]\n * @returns {Object} value as accessible by path\n */\n//TODO(misko): this function needs to be removed\nfunction getter(obj, path, bindFnToScope) {\n  if (!path) return obj;\n  var keys = path.split('.');\n  var key;\n  var lastInstance = obj;\n  var len = keys.length;\n\n  for (var i = 0; i < len; i++) {\n    key = keys[i];\n    if (obj) {\n      obj = (lastInstance = obj)[key];\n    }\n  }\n  if (!bindFnToScope && isFunction(obj)) {\n    return bind(lastInstance, obj);\n  }\n  return obj;\n}\n\n/**\n * Return the DOM siblings between the first and last node in the given array.\n * @param {Array} array like object\n * @returns {Array} the inputted object or a jqLite collection containing the nodes\n */\nfunction getBlockNodes(nodes) {\n  // TODO(perf): update `nodes` instead of creating a new object?\n  var node = nodes[0];\n  var endNode = nodes[nodes.length - 1];\n  var blockNodes;\n\n  for (var i = 1; node !== endNode && (node = node.nextSibling); i++) {\n    if (blockNodes || nodes[i] !== node) {\n      if (!blockNodes) {\n        blockNodes = jqLite(slice.call(nodes, 0, i));\n      }\n      blockNodes.push(node);\n    }\n  }\n\n  return blockNodes || nodes;\n}\n\n\n/**\n * Creates a new object without a prototype. This object is useful for lookup without having to\n * guard against prototypically inherited properties via hasOwnProperty.\n *\n * Related micro-benchmarks:\n * - http://jsperf.com/object-create2\n * - http://jsperf.com/proto-map-lookup/2\n * - http://jsperf.com/for-in-vs-object-keys2\n *\n * @returns {Object}\n */\nfunction createMap() {\n  return Object.create(null);\n}\n\nfunction stringify(value) {\n  if (value == null) { // null || undefined\n    return '';\n  }\n  switch (typeof value) {\n    case 'string':\n      break;\n    case 'number':\n      value = '' + value;\n      break;\n    default:\n      if (hasCustomToString(value) && !isArray(value) && !isDate(value)) {\n        value = value.toString();\n      } else {\n        value = toJson(value);\n      }\n  }\n\n  return value;\n}\n\nvar NODE_TYPE_ELEMENT = 1;\nvar NODE_TYPE_ATTRIBUTE = 2;\nvar NODE_TYPE_TEXT = 3;\nvar NODE_TYPE_COMMENT = 8;\nvar NODE_TYPE_DOCUMENT = 9;\nvar NODE_TYPE_DOCUMENT_FRAGMENT = 11;\n\n/**\n * @ngdoc type\n * @name angular.Module\n * @module ng\n * @description\n *\n * Interface for configuring AngularJS {@link angular.module modules}.\n */\n\nfunction setupModuleLoader(window) {\n\n  var $injectorMinErr = minErr('$injector');\n  var ngMinErr = minErr('ng');\n\n  function ensure(obj, name, factory) {\n    return obj[name] || (obj[name] = factory());\n  }\n\n  var angular = ensure(window, 'angular', Object);\n\n  // We need to expose `angular.$$minErr` to modules such as `ngResource` that reference it during bootstrap\n  angular.$$minErr = angular.$$minErr || minErr;\n\n  return ensure(angular, 'module', function() {\n    /** @type {Object.<string, angular.Module>} */\n    var modules = {};\n\n    /**\n     * @ngdoc function\n     * @name angular.module\n     * @module ng\n     * @description\n     *\n     * The `angular.module` is a global place for creating, registering and retrieving AngularJS\n     * modules.\n     * All modules (AngularJS core or 3rd party) that should be available to an application must be\n     * registered using this mechanism.\n     *\n     * Passing one argument retrieves an existing {@link angular.Module},\n     * whereas passing more than one argument creates a new {@link angular.Module}\n     *\n     *\n     * # Module\n     *\n     * A module is a collection of services, directives, controllers, filters, and configuration information.\n     * `angular.module` is used to configure the {@link auto.$injector $injector}.\n     *\n     * ```js\n     * // Create a new module\n     * var myModule = angular.module('myModule', []);\n     *\n     * // register a new service\n     * myModule.value('appName', 'MyCoolApp');\n     *\n     * // configure existing services inside initialization blocks.\n     * myModule.config(['$locationProvider', function($locationProvider) {\n     *   // Configure existing providers\n     *   $locationProvider.hashPrefix('!');\n     * }]);\n     * ```\n     *\n     * Then you can create an injector and load your modules like this:\n     *\n     * ```js\n     * var injector = angular.injector(['ng', 'myModule'])\n     * ```\n     *\n     * However it's more likely that you'll just use\n     * {@link ng.directive:ngApp ngApp} or\n     * {@link angular.bootstrap} to simplify this process for you.\n     *\n     * @param {!string} name The name of the module to create or retrieve.\n     * @param {!Array.<string>=} requires If specified then new module is being created. If\n     *        unspecified then the module is being retrieved for further configuration.\n     * @param {Function=} configFn Optional configuration function for the module. Same as\n     *        {@link angular.Module#config Module#config()}.\n     * @returns {angular.Module} new module with the {@link angular.Module} api.\n     */\n    return function module(name, requires, configFn) {\n\n      var info = {};\n\n      var assertNotHasOwnProperty = function(name, context) {\n        if (name === 'hasOwnProperty') {\n          throw ngMinErr('badname', 'hasOwnProperty is not a valid {0} name', context);\n        }\n      };\n\n      assertNotHasOwnProperty(name, 'module');\n      if (requires && modules.hasOwnProperty(name)) {\n        modules[name] = null;\n      }\n      return ensure(modules, name, function() {\n        if (!requires) {\n          throw $injectorMinErr('nomod', 'Module \\'{0}\\' is not available! You either misspelled ' +\n             'the module name or forgot to load it. If registering a module ensure that you ' +\n             'specify the dependencies as the second argument.', name);\n        }\n\n        /** @type {!Array.<Array.<*>>} */\n        var invokeQueue = [];\n\n        /** @type {!Array.<Function>} */\n        var configBlocks = [];\n\n        /** @type {!Array.<Function>} */\n        var runBlocks = [];\n\n        var config = invokeLater('$injector', 'invoke', 'push', configBlocks);\n\n        /** @type {angular.Module} */\n        var moduleInstance = {\n          // Private state\n          _invokeQueue: invokeQueue,\n          _configBlocks: configBlocks,\n          _runBlocks: runBlocks,\n\n          /**\n           * @ngdoc method\n           * @name angular.Module#info\n           * @module ng\n           *\n           * @param {Object=} info Information about the module\n           * @returns {Object|Module} The current info object for this module if called as a getter,\n           *                          or `this` if called as a setter.\n           *\n           * @description\n           * Read and write custom information about this module.\n           * For example you could put the version of the module in here.\n           *\n           * ```js\n           * angular.module('myModule', []).info({ version: '1.0.0' });\n           * ```\n           *\n           * The version could then be read back out by accessing the module elsewhere:\n           *\n           * ```\n           * var version = angular.module('myModule').info().version;\n           * ```\n           *\n           * You can also retrieve this information during runtime via the\n           * {@link $injector#modules `$injector.modules`} property:\n           *\n           * ```js\n           * var version = $injector.modules['myModule'].info().version;\n           * ```\n           */\n          info: function(value) {\n            if (isDefined(value)) {\n              if (!isObject(value)) throw ngMinErr('aobj', 'Argument \\'{0}\\' must be an object', 'value');\n              info = value;\n              return this;\n            }\n            return info;\n          },\n\n          /**\n           * @ngdoc property\n           * @name angular.Module#requires\n           * @module ng\n           *\n           * @description\n           * Holds the list of modules which the injector will load before the current module is\n           * loaded.\n           */\n          requires: requires,\n\n          /**\n           * @ngdoc property\n           * @name angular.Module#name\n           * @module ng\n           *\n           * @description\n           * Name of the module.\n           */\n          name: name,\n\n\n          /**\n           * @ngdoc method\n           * @name angular.Module#provider\n           * @module ng\n           * @param {string} name service name\n           * @param {Function} providerType Construction function for creating new instance of the\n           *                                service.\n           * @description\n           * See {@link auto.$provide#provider $provide.provider()}.\n           */\n          provider: invokeLaterAndSetModuleName('$provide', 'provider'),\n\n          /**\n           * @ngdoc method\n           * @name angular.Module#factory\n           * @module ng\n           * @param {string} name service name\n           * @param {Function} providerFunction Function for creating new instance of the service.\n           * @description\n           * See {@link auto.$provide#factory $provide.factory()}.\n           */\n          factory: invokeLaterAndSetModuleName('$provide', 'factory'),\n\n          /**\n           * @ngdoc method\n           * @name angular.Module#service\n           * @module ng\n           * @param {string} name service name\n           * @param {Function} constructor A constructor function that will be instantiated.\n           * @description\n           * See {@link auto.$provide#service $provide.service()}.\n           */\n          service: invokeLaterAndSetModuleName('$provide', 'service'),\n\n          /**\n           * @ngdoc method\n           * @name angular.Module#value\n           * @module ng\n           * @param {string} name service name\n           * @param {*} object Service instance object.\n           * @description\n           * See {@link auto.$provide#value $provide.value()}.\n           */\n          value: invokeLater('$provide', 'value'),\n\n          /**\n           * @ngdoc method\n           * @name angular.Module#constant\n           * @module ng\n           * @param {string} name constant name\n           * @param {*} object Constant value.\n           * @description\n           * Because the constants are fixed, they get applied before other provide methods.\n           * See {@link auto.$provide#constant $provide.constant()}.\n           */\n          constant: invokeLater('$provide', 'constant', 'unshift'),\n\n           /**\n           * @ngdoc method\n           * @name angular.Module#decorator\n           * @module ng\n           * @param {string} name The name of the service to decorate.\n           * @param {Function} decorFn This function will be invoked when the service needs to be\n           *                           instantiated and should return the decorated service instance.\n           * @description\n           * See {@link auto.$provide#decorator $provide.decorator()}.\n           */\n          decorator: invokeLaterAndSetModuleName('$provide', 'decorator', configBlocks),\n\n          /**\n           * @ngdoc method\n           * @name angular.Module#animation\n           * @module ng\n           * @param {string} name animation name\n           * @param {Function} animationFactory Factory function for creating new instance of an\n           *                                    animation.\n           * @description\n           *\n           * **NOTE**: animations take effect only if the **ngAnimate** module is loaded.\n           *\n           *\n           * Defines an animation hook that can be later used with\n           * {@link $animate $animate} service and directives that use this service.\n           *\n           * ```js\n           * module.animation('.animation-name', function($inject1, $inject2) {\n           *   return {\n           *     eventName : function(element, done) {\n           *       //code to run the animation\n           *       //once complete, then run done()\n           *       return function cancellationFunction(element) {\n           *         //code to cancel the animation\n           *       }\n           *     }\n           *   }\n           * })\n           * ```\n           *\n           * See {@link ng.$animateProvider#register $animateProvider.register()} and\n           * {@link ngAnimate ngAnimate module} for more information.\n           */\n          animation: invokeLaterAndSetModuleName('$animateProvider', 'register'),\n\n          /**\n           * @ngdoc method\n           * @name angular.Module#filter\n           * @module ng\n           * @param {string} name Filter name - this must be a valid AngularJS expression identifier\n           * @param {Function} filterFactory Factory function for creating new instance of filter.\n           * @description\n           * See {@link ng.$filterProvider#register $filterProvider.register()}.\n           *\n           * <div class=\"alert alert-warning\">\n           * **Note:** Filter names must be valid AngularJS {@link expression} identifiers, such as `uppercase` or `orderBy`.\n           * Names with special characters, such as hyphens and dots, are not allowed. If you wish to namespace\n           * your filters, then you can use capitalization (`myappSubsectionFilterx`) or underscores\n           * (`myapp_subsection_filterx`).\n           * </div>\n           */\n          filter: invokeLaterAndSetModuleName('$filterProvider', 'register'),\n\n          /**\n           * @ngdoc method\n           * @name angular.Module#controller\n           * @module ng\n           * @param {string|Object} name Controller name, or an object map of controllers where the\n           *    keys are the names and the values are the constructors.\n           * @param {Function} constructor Controller constructor function.\n           * @description\n           * See {@link ng.$controllerProvider#register $controllerProvider.register()}.\n           */\n          controller: invokeLaterAndSetModuleName('$controllerProvider', 'register'),\n\n          /**\n           * @ngdoc method\n           * @name angular.Module#directive\n           * @module ng\n           * @param {string|Object} name Directive name, or an object map of directives where the\n           *    keys are the names and the values are the factories.\n           * @param {Function} directiveFactory Factory function for creating new instance of\n           * directives.\n           * @description\n           * See {@link ng.$compileProvider#directive $compileProvider.directive()}.\n           */\n          directive: invokeLaterAndSetModuleName('$compileProvider', 'directive'),\n\n          /**\n           * @ngdoc method\n           * @name angular.Module#component\n           * @module ng\n           * @param {string|Object} name Name of the component in camelCase (i.e. `myComp` which will match `<my-comp>`),\n           *    or an object map of components where the keys are the names and the values are the component definition objects.\n           * @param {Object} options Component definition object (a simplified\n           *    {@link ng.$compile#directive-definition-object directive definition object})\n           *\n           * @description\n           * See {@link ng.$compileProvider#component $compileProvider.component()}.\n           */\n          component: invokeLaterAndSetModuleName('$compileProvider', 'component'),\n\n          /**\n           * @ngdoc method\n           * @name angular.Module#config\n           * @module ng\n           * @param {Function} configFn Execute this function on module load. Useful for service\n           *    configuration.\n           * @description\n           * Use this method to configure services by injecting their\n           * {@link angular.Module#provider `providers`}, e.g. for adding routes to the\n           * {@link ngRoute.$routeProvider $routeProvider}.\n           *\n           * Note that you can only inject {@link angular.Module#provider `providers`} and\n           * {@link angular.Module#constant `constants`} into this function.\n           *\n           * For more about how to configure services, see\n           * {@link providers#provider-recipe Provider Recipe}.\n           */\n          config: config,\n\n          /**\n           * @ngdoc method\n           * @name angular.Module#run\n           * @module ng\n           * @param {Function} initializationFn Execute this function after injector creation.\n           *    Useful for application initialization.\n           * @description\n           * Use this method to register work which should be performed when the injector is done\n           * loading all modules.\n           */\n          run: function(block) {\n            runBlocks.push(block);\n            return this;\n          }\n        };\n\n        if (configFn) {\n          config(configFn);\n        }\n\n        return moduleInstance;\n\n        /**\n         * @param {string} provider\n         * @param {string} method\n         * @param {String=} insertMethod\n         * @returns {angular.Module}\n         */\n        function invokeLater(provider, method, insertMethod, queue) {\n          if (!queue) queue = invokeQueue;\n          return function() {\n            queue[insertMethod || 'push']([provider, method, arguments]);\n            return moduleInstance;\n          };\n        }\n\n        /**\n         * @param {string} provider\n         * @param {string} method\n         * @returns {angular.Module}\n         */\n        function invokeLaterAndSetModuleName(provider, method, queue) {\n          if (!queue) queue = invokeQueue;\n          return function(recipeName, factoryFunction) {\n            if (factoryFunction && isFunction(factoryFunction)) factoryFunction.$$moduleName = name;\n            queue.push([provider, method, arguments]);\n            return moduleInstance;\n          };\n        }\n      });\n    };\n  });\n\n}\n\n/* global shallowCopy: true */\n\n/**\n * Creates a shallow copy of an object, an array or a primitive.\n *\n * Assumes that there are no proto properties for objects.\n */\nfunction shallowCopy(src, dst) {\n  if (isArray(src)) {\n    dst = dst || [];\n\n    for (var i = 0, ii = src.length; i < ii; i++) {\n      dst[i] = src[i];\n    }\n  } else if (isObject(src)) {\n    dst = dst || {};\n\n    for (var key in src) {\n      if (!(key.charAt(0) === '$' && key.charAt(1) === '$')) {\n        dst[key] = src[key];\n      }\n    }\n  }\n\n  return dst || src;\n}\n\n/* exported toDebugString */\n\nfunction serializeObject(obj, maxDepth) {\n  var seen = [];\n\n  // There is no direct way to stringify object until reaching a specific depth\n  // and a very deep object can cause a performance issue, so we copy the object\n  // based on this specific depth and then stringify it.\n  if (isValidObjectMaxDepth(maxDepth)) {\n    // This file is also included in `angular-loader`, so `copy()` might not always be available in\n    // the closure. Therefore, it is lazily retrieved as `angular.copy()` when needed.\n    obj = angular.copy(obj, null, maxDepth);\n  }\n  return JSON.stringify(obj, function(key, val) {\n    val = toJsonReplacer(key, val);\n    if (isObject(val)) {\n\n      if (seen.indexOf(val) >= 0) return '...';\n\n      seen.push(val);\n    }\n    return val;\n  });\n}\n\nfunction toDebugString(obj, maxDepth) {\n  if (typeof obj === 'function') {\n    return obj.toString().replace(/ \\{[\\s\\S]*$/, '');\n  } else if (isUndefined(obj)) {\n    return 'undefined';\n  } else if (typeof obj !== 'string') {\n    return serializeObject(obj, maxDepth);\n  }\n  return obj;\n}\n\n/* global angularModule: true,\n  version: true,\n\n  $CompileProvider,\n\n  htmlAnchorDirective,\n  inputDirective,\n  hiddenInputBrowserCacheDirective,\n  formDirective,\n  scriptDirective,\n  selectDirective,\n  optionDirective,\n  ngBindDirective,\n  ngBindHtmlDirective,\n  ngBindTemplateDirective,\n  ngClassDirective,\n  ngClassEvenDirective,\n  ngClassOddDirective,\n  ngCloakDirective,\n  ngControllerDirective,\n  ngFormDirective,\n  ngHideDirective,\n  ngIfDirective,\n  ngIncludeDirective,\n  ngIncludeFillContentDirective,\n  ngInitDirective,\n  ngNonBindableDirective,\n  ngPluralizeDirective,\n  ngRefDirective,\n  ngRepeatDirective,\n  ngShowDirective,\n  ngStyleDirective,\n  ngSwitchDirective,\n  ngSwitchWhenDirective,\n  ngSwitchDefaultDirective,\n  ngOptionsDirective,\n  ngTranscludeDirective,\n  ngModelDirective,\n  ngListDirective,\n  ngChangeDirective,\n  patternDirective,\n  patternDirective,\n  requiredDirective,\n  requiredDirective,\n  minlengthDirective,\n  minlengthDirective,\n  maxlengthDirective,\n  maxlengthDirective,\n  ngValueDirective,\n  ngModelOptionsDirective,\n  ngAttributeAliasDirectives,\n  ngEventDirectives,\n\n  $AnchorScrollProvider,\n  $AnimateProvider,\n  $CoreAnimateCssProvider,\n  $$CoreAnimateJsProvider,\n  $$CoreAnimateQueueProvider,\n  $$AnimateRunnerFactoryProvider,\n  $$AnimateAsyncRunFactoryProvider,\n  $BrowserProvider,\n  $CacheFactoryProvider,\n  $ControllerProvider,\n  $DateProvider,\n  $DocumentProvider,\n  $$IsDocumentHiddenProvider,\n  $ExceptionHandlerProvider,\n  $FilterProvider,\n  $$ForceReflowProvider,\n  $InterpolateProvider,\n  $$IntervalFactoryProvider,\n  $IntervalProvider,\n  $HttpProvider,\n  $HttpParamSerializerProvider,\n  $HttpParamSerializerJQLikeProvider,\n  $HttpBackendProvider,\n  $xhrFactoryProvider,\n  $jsonpCallbacksProvider,\n  $LocationProvider,\n  $LogProvider,\n  $$MapProvider,\n  $ParseProvider,\n  $RootScopeProvider,\n  $QProvider,\n  $$QProvider,\n  $$SanitizeUriProvider,\n  $SceProvider,\n  $SceDelegateProvider,\n  $SnifferProvider,\n  $$TaskTrackerFactoryProvider,\n  $TemplateCacheProvider,\n  $TemplateRequestProvider,\n  $$TestabilityProvider,\n  $TimeoutProvider,\n  $$RAFProvider,\n  $WindowProvider,\n  $$jqLiteProvider,\n  $$CookieReaderProvider\n*/\n\n\n/**\n * @ngdoc object\n * @name angular.version\n * @module ng\n * @description\n * An object that contains information about the current AngularJS version.\n *\n * This object has the following properties:\n *\n * - `full` – `{string}` – Full version string, such as \"0.9.18\".\n * - `major` – `{number}` – Major version number, such as \"0\".\n * - `minor` – `{number}` – Minor version number, such as \"9\".\n * - `dot` – `{number}` – Dot version number, such as \"18\".\n * - `codeName` – `{string}` – Code name of the release, such as \"jiggling-armfat\".\n */\nvar version = {\n  // These placeholder strings will be replaced by grunt's `build` task.\n  // They need to be double- or single-quoted.\n  full: '1.8.3',\n  major: 1,\n  minor: 8,\n  dot: 3,\n  codeName: 'ultimate-farewell'\n};\n\n\nfunction publishExternalAPI(angular) {\n  extend(angular, {\n    'errorHandlingConfig': errorHandlingConfig,\n    'bootstrap': bootstrap,\n    'copy': copy,\n    'extend': extend,\n    'merge': merge,\n    'equals': equals,\n    'element': jqLite,\n    'forEach': forEach,\n    'injector': createInjector,\n    'noop': noop,\n    'bind': bind,\n    'toJson': toJson,\n    'fromJson': fromJson,\n    'identity': identity,\n    'isUndefined': isUndefined,\n    'isDefined': isDefined,\n    'isString': isString,\n    'isFunction': isFunction,\n    'isObject': isObject,\n    'isNumber': isNumber,\n    'isElement': isElement,\n    'isArray': isArray,\n    'version': version,\n    'isDate': isDate,\n    'callbacks': {$$counter: 0},\n    'getTestability': getTestability,\n    'reloadWithDebugInfo': reloadWithDebugInfo,\n    'UNSAFE_restoreLegacyJqLiteXHTMLReplacement': UNSAFE_restoreLegacyJqLiteXHTMLReplacement,\n    '$$minErr': minErr,\n    '$$csp': csp,\n    '$$encodeUriSegment': encodeUriSegment,\n    '$$encodeUriQuery': encodeUriQuery,\n    '$$lowercase': lowercase,\n    '$$stringify': stringify,\n    '$$uppercase': uppercase\n  });\n\n  angularModule = setupModuleLoader(window);\n\n  angularModule('ng', ['ngLocale'], ['$provide',\n    function ngModule($provide) {\n      // $$sanitizeUriProvider needs to be before $compileProvider as it is used by it.\n      $provide.provider({\n        $$sanitizeUri: $$SanitizeUriProvider\n      });\n      $provide.provider('$compile', $CompileProvider).\n        directive({\n            a: htmlAnchorDirective,\n            input: inputDirective,\n            textarea: inputDirective,\n            form: formDirective,\n            script: scriptDirective,\n            select: selectDirective,\n            option: optionDirective,\n            ngBind: ngBindDirective,\n            ngBindHtml: ngBindHtmlDirective,\n            ngBindTemplate: ngBindTemplateDirective,\n            ngClass: ngClassDirective,\n            ngClassEven: ngClassEvenDirective,\n            ngClassOdd: ngClassOddDirective,\n            ngCloak: ngCloakDirective,\n            ngController: ngControllerDirective,\n            ngForm: ngFormDirective,\n            ngHide: ngHideDirective,\n            ngIf: ngIfDirective,\n            ngInclude: ngIncludeDirective,\n            ngInit: ngInitDirective,\n            ngNonBindable: ngNonBindableDirective,\n            ngPluralize: ngPluralizeDirective,\n            ngRef: ngRefDirective,\n            ngRepeat: ngRepeatDirective,\n            ngShow: ngShowDirective,\n            ngStyle: ngStyleDirective,\n            ngSwitch: ngSwitchDirective,\n            ngSwitchWhen: ngSwitchWhenDirective,\n            ngSwitchDefault: ngSwitchDefaultDirective,\n            ngOptions: ngOptionsDirective,\n            ngTransclude: ngTranscludeDirective,\n            ngModel: ngModelDirective,\n            ngList: ngListDirective,\n            ngChange: ngChangeDirective,\n            pattern: patternDirective,\n            ngPattern: patternDirective,\n            required: requiredDirective,\n            ngRequired: requiredDirective,\n            minlength: minlengthDirective,\n            ngMinlength: minlengthDirective,\n            maxlength: maxlengthDirective,\n            ngMaxlength: maxlengthDirective,\n            ngValue: ngValueDirective,\n            ngModelOptions: ngModelOptionsDirective\n        }).\n        directive({\n          ngInclude: ngIncludeFillContentDirective,\n          input: hiddenInputBrowserCacheDirective\n        }).\n        directive(ngAttributeAliasDirectives).\n        directive(ngEventDirectives);\n      $provide.provider({\n        $anchorScroll: $AnchorScrollProvider,\n        $animate: $AnimateProvider,\n        $animateCss: $CoreAnimateCssProvider,\n        $$animateJs: $$CoreAnimateJsProvider,\n        $$animateQueue: $$CoreAnimateQueueProvider,\n        $$AnimateRunner: $$AnimateRunnerFactoryProvider,\n        $$animateAsyncRun: $$AnimateAsyncRunFactoryProvider,\n        $browser: $BrowserProvider,\n        $cacheFactory: $CacheFactoryProvider,\n        $controller: $ControllerProvider,\n        $document: $DocumentProvider,\n        $$isDocumentHidden: $$IsDocumentHiddenProvider,\n        $exceptionHandler: $ExceptionHandlerProvider,\n        $filter: $FilterProvider,\n        $$forceReflow: $$ForceReflowProvider,\n        $interpolate: $InterpolateProvider,\n        $interval: $IntervalProvider,\n        $$intervalFactory: $$IntervalFactoryProvider,\n        $http: $HttpProvider,\n        $httpParamSerializer: $HttpParamSerializerProvider,\n        $httpParamSerializerJQLike: $HttpParamSerializerJQLikeProvider,\n        $httpBackend: $HttpBackendProvider,\n        $xhrFactory: $xhrFactoryProvider,\n        $jsonpCallbacks: $jsonpCallbacksProvider,\n        $location: $LocationProvider,\n        $log: $LogProvider,\n        $parse: $ParseProvider,\n        $rootScope: $RootScopeProvider,\n        $q: $QProvider,\n        $$q: $$QProvider,\n        $sce: $SceProvider,\n        $sceDelegate: $SceDelegateProvider,\n        $sniffer: $SnifferProvider,\n        $$taskTrackerFactory: $$TaskTrackerFactoryProvider,\n        $templateCache: $TemplateCacheProvider,\n        $templateRequest: $TemplateRequestProvider,\n        $$testability: $$TestabilityProvider,\n        $timeout: $TimeoutProvider,\n        $window: $WindowProvider,\n        $$rAF: $$RAFProvider,\n        $$jqLite: $$jqLiteProvider,\n        $$Map: $$MapProvider,\n        $$cookieReader: $$CookieReaderProvider\n      });\n    }\n  ])\n  .info({ angularVersion: '1.8.3' });\n}\n\n/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *\n *     Any commits to this file should be reviewed with security in mind.  *\n *   Changes to this file can potentially create security vulnerabilities. *\n *          An approval from 2 Core members with history of modifying      *\n *                         this file is required.                          *\n *                                                                         *\n *  Does the change somehow allow for arbitrary javascript to be executed? *\n *    Or allows for someone to change the prototype of built-in objects?   *\n *     Or gives undesired access to variables likes document or window?    *\n * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */\n\n/* global\n  JQLitePrototype: true,\n  BOOLEAN_ATTR: true,\n  ALIASED_ATTR: true\n*/\n\n//////////////////////////////////\n//JQLite\n//////////////////////////////////\n\n/**\n * @ngdoc function\n * @name angular.element\n * @module ng\n * @kind function\n *\n * @description\n * Wraps a raw DOM element or HTML string as a [jQuery](http://jquery.com) element.\n *\n * If jQuery is available, `angular.element` is an alias for the\n * [jQuery](http://api.jquery.com/jQuery/) function. If jQuery is not available, `angular.element`\n * delegates to AngularJS's built-in subset of jQuery, called \"jQuery lite\" or **jqLite**.\n *\n * jqLite is a tiny, API-compatible subset of jQuery that allows\n * AngularJS to manipulate the DOM in a cross-browser compatible way. jqLite implements only the most\n * commonly needed functionality with the goal of having a very small footprint.\n *\n * To use `jQuery`, simply ensure it is loaded before the `angular.js` file. You can also use the\n * {@link ngJq `ngJq`} directive to specify that jqlite should be used over jQuery, or to use a\n * specific version of jQuery if multiple versions exist on the page.\n *\n * <div class=\"alert alert-info\">**Note:** All element references in AngularJS are always wrapped with jQuery or\n * jqLite (such as the element argument in a directive's compile / link function). They are never raw DOM references.</div>\n *\n * <div class=\"alert alert-warning\">**Note:** Keep in mind that this function will not find elements\n * by tag name / CSS selector. For lookups by tag name, try instead `angular.element(document).find(...)`\n * or `$document.find()`, or use the standard DOM APIs, e.g. `document.querySelectorAll()`.</div>\n *\n * ## AngularJS's jqLite\n * jqLite provides only the following jQuery methods:\n *\n * - [`addClass()`](http://api.jquery.com/addClass/) - Does not support a function as first argument\n * - [`after()`](http://api.jquery.com/after/)\n * - [`append()`](http://api.jquery.com/append/) - Contrary to jQuery, this doesn't clone elements\n *   so will not work correctly when invoked on a jqLite object containing more than one DOM node\n * - [`attr()`](http://api.jquery.com/attr/) - Does not support functions as parameters\n * - [`bind()`](http://api.jquery.com/bind/) (_deprecated_, use [`on()`](http://api.jquery.com/on/)) - Does not support namespaces, selectors or eventData\n * - [`children()`](http://api.jquery.com/children/) - Does not support selectors\n * - [`clone()`](http://api.jquery.com/clone/)\n * - [`contents()`](http://api.jquery.com/contents/)\n * - [`css()`](http://api.jquery.com/css/) - Only retrieves inline-styles, does not call `getComputedStyle()`.\n *   As a setter, does not convert numbers to strings or append 'px', and also does not have automatic property prefixing.\n * - [`data()`](http://api.jquery.com/data/)\n * - [`detach()`](http://api.jquery.com/detach/)\n * - [`empty()`](http://api.jquery.com/empty/)\n * - [`eq()`](http://api.jquery.com/eq/)\n * - [`find()`](http://api.jquery.com/find/) - Limited to lookups by tag name\n * - [`hasClass()`](http://api.jquery.com/hasClass/)\n * - [`html()`](http://api.jquery.com/html/)\n * - [`next()`](http://api.jquery.com/next/) - Does not support selectors\n * - [`on()`](http://api.jquery.com/on/) - Does not support namespaces, selectors or eventData\n * - [`off()`](http://api.jquery.com/off/) - Does not support namespaces, selectors or event object as parameter\n * - [`one()`](http://api.jquery.com/one/) - Does not support namespaces or selectors\n * - [`parent()`](http://api.jquery.com/parent/) - Does not support selectors\n * - [`prepend()`](http://api.jquery.com/prepend/)\n * - [`prop()`](http://api.jquery.com/prop/)\n * - [`ready()`](http://api.jquery.com/ready/) (_deprecated_, use `angular.element(callback)` instead of `angular.element(document).ready(callback)`)\n * - [`remove()`](http://api.jquery.com/remove/)\n * - [`removeAttr()`](http://api.jquery.com/removeAttr/) - Does not support multiple attributes\n * - [`removeClass()`](http://api.jquery.com/removeClass/) - Does not support a function as first argument\n * - [`removeData()`](http://api.jquery.com/removeData/)\n * - [`replaceWith()`](http://api.jquery.com/replaceWith/)\n * - [`text()`](http://api.jquery.com/text/)\n * - [`toggleClass()`](http://api.jquery.com/toggleClass/) - Does not support a function as first argument\n * - [`triggerHandler()`](http://api.jquery.com/triggerHandler/) - Passes a dummy event object to handlers\n * - [`unbind()`](http://api.jquery.com/unbind/) (_deprecated_, use [`off()`](http://api.jquery.com/off/)) - Does not support namespaces or event object as parameter\n * - [`val()`](http://api.jquery.com/val/)\n * - [`wrap()`](http://api.jquery.com/wrap/)\n *\n * jqLite also provides a method restoring pre-1.8 insecure treatment of XHTML-like tags.\n * This legacy behavior turns input like `<div /><span />` to `<div></div><span></span>`\n * instead of `<div><span></span></div>` like version 1.8 & newer do. To restore it, invoke:\n * ```js\n * angular.UNSAFE_restoreLegacyJqLiteXHTMLReplacement();\n * ```\n * Note that this only patches jqLite. If you use jQuery 3.5.0 or newer, please read the\n * [jQuery 3.5 upgrade guide](https://jquery.com/upgrade-guide/3.5/) for more details\n * about the workarounds.\n *\n * ## jQuery/jqLite Extras\n * AngularJS also provides the following additional methods and events to both jQuery and jqLite:\n *\n * ### Events\n * - `$destroy` - AngularJS intercepts all jqLite/jQuery's DOM destruction apis and fires this event\n *    on all DOM nodes being removed.  This can be used to clean up any 3rd party bindings to the DOM\n *    element before it is removed.\n *\n * ### Methods\n * - `controller(name)` - retrieves the controller of the current element or its parent. By default\n *   retrieves controller associated with the `ngController` directive. If `name` is provided as\n *   camelCase directive name, then the controller for this directive will be retrieved (e.g.\n *   `'ngModel'`).\n * - `injector()` - retrieves the injector of the current element or its parent.\n * - `scope()` - retrieves the {@link ng.$rootScope.Scope scope} of the current\n *   element or its parent. Requires {@link guide/production#disabling-debug-data Debug Data} to\n *   be enabled.\n * - `isolateScope()` - retrieves an isolate {@link ng.$rootScope.Scope scope} if one is attached directly to the\n *   current element. This getter should be used only on elements that contain a directive which starts a new isolate\n *   scope. Calling `scope()` on this element always returns the original non-isolate scope.\n *   Requires {@link guide/production#disabling-debug-data Debug Data} to be enabled.\n * - `inheritedData()` - same as `data()`, but walks up the DOM until a value is found or the top\n *   parent element is reached.\n *\n * @knownIssue You cannot spy on `angular.element` if you are using Jasmine version 1.x. See\n * https://github.com/angular/angular.js/issues/14251 for more information.\n *\n * @param {string|DOMElement} element HTML string or DOMElement to be wrapped into jQuery.\n * @returns {Object} jQuery object.\n */\n\nJQLite.expando = 'ng339';\n\nvar jqCache = JQLite.cache = {},\n    jqId = 1;\n\n/*\n * !!! This is an undocumented \"private\" function !!!\n */\nJQLite._data = function(node) {\n  //jQuery always returns an object on cache miss\n  return this.cache[node[this.expando]] || {};\n};\n\nfunction jqNextId() { return ++jqId; }\n\n\nvar DASH_LOWERCASE_REGEXP = /-([a-z])/g;\nvar MS_HACK_REGEXP = /^-ms-/;\nvar MOUSE_EVENT_MAP = { mouseleave: 'mouseout', mouseenter: 'mouseover' };\nvar jqLiteMinErr = minErr('jqLite');\n\n/**\n * Converts kebab-case to camelCase.\n * There is also a special case for the ms prefix starting with a lowercase letter.\n * @param name Name to normalize\n */\nfunction cssKebabToCamel(name) {\n    return kebabToCamel(name.replace(MS_HACK_REGEXP, 'ms-'));\n}\n\nfunction fnCamelCaseReplace(all, letter) {\n  return letter.toUpperCase();\n}\n\n/**\n * Converts kebab-case to camelCase.\n * @param name Name to normalize\n */\nfunction kebabToCamel(name) {\n  return name\n    .replace(DASH_LOWERCASE_REGEXP, fnCamelCaseReplace);\n}\n\nvar SINGLE_TAG_REGEXP = /^<([\\w-]+)\\s*\\/?>(?:<\\/\\1>|)$/;\nvar HTML_REGEXP = /<|&#?\\w+;/;\nvar TAG_NAME_REGEXP = /<([\\w:-]+)/;\nvar XHTML_TAG_REGEXP = /<(?!area|br|col|embed|hr|img|input|link|meta|param)(([\\w:-]+)[^>]*)\\/>/gi;\n\n// Table parts need to be wrapped with `<table>` or they're\n// stripped to their contents when put in a div.\n// XHTML parsers do not magically insert elements in the\n// same way that tag soup parsers do, so we cannot shorten\n// this by omitting <tbody> or other required elements.\nvar wrapMap = {\n  thead: ['table'],\n  col: ['colgroup', 'table'],\n  tr: ['tbody', 'table'],\n  td: ['tr', 'tbody', 'table']\n};\n\nwrapMap.tbody = wrapMap.tfoot = wrapMap.colgroup = wrapMap.caption = wrapMap.thead;\nwrapMap.th = wrapMap.td;\n\n// Support: IE <10 only\n// IE 9 requires an option wrapper & it needs to have the whole table structure\n// set up in advance; assigning `\"<td></td>\"` to `tr.innerHTML` doesn't work, etc.\nvar wrapMapIE9 = {\n  option: [1, '<select multiple=\"multiple\">', '</select>'],\n  _default: [0, '', '']\n};\n\nfor (var key in wrapMap) {\n  var wrapMapValueClosing = wrapMap[key];\n  var wrapMapValue = wrapMapValueClosing.slice().reverse();\n  wrapMapIE9[key] = [wrapMapValue.length, '<' + wrapMapValue.join('><') + '>', '</' + wrapMapValueClosing.join('></') + '>'];\n}\n\nwrapMapIE9.optgroup = wrapMapIE9.option;\n\nfunction jqLiteIsTextNode(html) {\n  return !HTML_REGEXP.test(html);\n}\n\nfunction jqLiteAcceptsData(node) {\n  // The window object can accept data but has no nodeType\n  // Otherwise we are only interested in elements (1) and documents (9)\n  var nodeType = node.nodeType;\n  return nodeType === NODE_TYPE_ELEMENT || !nodeType || nodeType === NODE_TYPE_DOCUMENT;\n}\n\nfunction jqLiteHasData(node) {\n  for (var key in jqCache[node.ng339]) {\n    return true;\n  }\n  return false;\n}\n\nfunction jqLiteBuildFragment(html, context) {\n  var tmp, tag, wrap, finalHtml,\n      fragment = context.createDocumentFragment(),\n      nodes = [], i;\n\n  if (jqLiteIsTextNode(html)) {\n    // Convert non-html into a text node\n    nodes.push(context.createTextNode(html));\n  } else {\n    // Convert html into DOM nodes\n    tmp = fragment.appendChild(context.createElement('div'));\n    tag = (TAG_NAME_REGEXP.exec(html) || ['', ''])[1].toLowerCase();\n    finalHtml = JQLite.legacyXHTMLReplacement ?\n      html.replace(XHTML_TAG_REGEXP, '<$1></$2>') :\n      html;\n\n    if (msie < 10) {\n      wrap = wrapMapIE9[tag] || wrapMapIE9._default;\n      tmp.innerHTML = wrap[1] + finalHtml + wrap[2];\n\n      // Descend through wrappers to the right content\n      i = wrap[0];\n      while (i--) {\n        tmp = tmp.firstChild;\n      }\n    } else {\n      wrap = wrapMap[tag] || [];\n\n      // Create wrappers & descend into them\n      i = wrap.length;\n      while (--i > -1) {\n        tmp.appendChild(window.document.createElement(wrap[i]));\n        tmp = tmp.firstChild;\n      }\n\n      tmp.innerHTML = finalHtml;\n    }\n\n    nodes = concat(nodes, tmp.childNodes);\n\n    tmp = fragment.firstChild;\n    tmp.textContent = '';\n  }\n\n  // Remove wrapper from fragment\n  fragment.textContent = '';\n  fragment.innerHTML = ''; // Clear inner HTML\n  forEach(nodes, function(node) {\n    fragment.appendChild(node);\n  });\n\n  return fragment;\n}\n\nfunction jqLiteParseHTML(html, context) {\n  context = context || window.document;\n  var parsed;\n\n  if ((parsed = SINGLE_TAG_REGEXP.exec(html))) {\n    return [context.createElement(parsed[1])];\n  }\n\n  if ((parsed = jqLiteBuildFragment(html, context))) {\n    return parsed.childNodes;\n  }\n\n  return [];\n}\n\nfunction jqLiteWrapNode(node, wrapper) {\n  var parent = node.parentNode;\n\n  if (parent) {\n    parent.replaceChild(wrapper, node);\n  }\n\n  wrapper.appendChild(node);\n}\n\n\n// IE9-11 has no method \"contains\" in SVG element and in Node.prototype. Bug #10259.\nvar jqLiteContains = window.Node.prototype.contains || /** @this */ function(arg) {\n  // eslint-disable-next-line no-bitwise\n  return !!(this.compareDocumentPosition(arg) & 16);\n};\n\n/////////////////////////////////////////////\nfunction JQLite(element) {\n  if (element instanceof JQLite) {\n    return element;\n  }\n\n  var argIsString;\n\n  if (isString(element)) {\n    element = trim(element);\n    argIsString = true;\n  }\n  if (!(this instanceof JQLite)) {\n    if (argIsString && element.charAt(0) !== '<') {\n      throw jqLiteMinErr('nosel', 'Looking up elements via selectors is not supported by jqLite! See: http://docs.angularjs.org/api/angular.element');\n    }\n    return new JQLite(element);\n  }\n\n  if (argIsString) {\n    jqLiteAddNodes(this, jqLiteParseHTML(element));\n  } else if (isFunction(element)) {\n    jqLiteReady(element);\n  } else {\n    jqLiteAddNodes(this, element);\n  }\n}\n\nfunction jqLiteClone(element) {\n  return element.cloneNode(true);\n}\n\nfunction jqLiteDealoc(element, onlyDescendants) {\n  if (!onlyDescendants && jqLiteAcceptsData(element)) jqLite.cleanData([element]);\n\n  if (element.querySelectorAll) {\n    jqLite.cleanData(element.querySelectorAll('*'));\n  }\n}\n\nfunction isEmptyObject(obj) {\n  var name;\n\n  for (name in obj) {\n    return false;\n  }\n  return true;\n}\n\nfunction removeIfEmptyData(element) {\n  var expandoId = element.ng339;\n  var expandoStore = expandoId && jqCache[expandoId];\n\n  var events = expandoStore && expandoStore.events;\n  var data = expandoStore && expandoStore.data;\n\n  if ((!data || isEmptyObject(data)) && (!events || isEmptyObject(events))) {\n    delete jqCache[expandoId];\n    element.ng339 = undefined; // don't delete DOM expandos. IE and Chrome don't like it\n  }\n}\n\nfunction jqLiteOff(element, type, fn, unsupported) {\n  if (isDefined(unsupported)) throw jqLiteMinErr('offargs', 'jqLite#off() does not support the `selector` argument');\n\n  var expandoStore = jqLiteExpandoStore(element);\n  var events = expandoStore && expandoStore.events;\n  var handle = expandoStore && expandoStore.handle;\n\n  if (!handle) return; //no listeners registered\n\n  if (!type) {\n    for (type in events) {\n      if (type !== '$destroy') {\n        element.removeEventListener(type, handle);\n      }\n      delete events[type];\n    }\n  } else {\n\n    var removeHandler = function(type) {\n      var listenerFns = events[type];\n      if (isDefined(fn)) {\n        arrayRemove(listenerFns || [], fn);\n      }\n      if (!(isDefined(fn) && listenerFns && listenerFns.length > 0)) {\n        element.removeEventListener(type, handle);\n        delete events[type];\n      }\n    };\n\n    forEach(type.split(' '), function(type) {\n      removeHandler(type);\n      if (MOUSE_EVENT_MAP[type]) {\n        removeHandler(MOUSE_EVENT_MAP[type]);\n      }\n    });\n  }\n\n  removeIfEmptyData(element);\n}\n\nfunction jqLiteRemoveData(element, name) {\n  var expandoId = element.ng339;\n  var expandoStore = expandoId && jqCache[expandoId];\n\n  if (expandoStore) {\n    if (name) {\n      delete expandoStore.data[name];\n    } else {\n      expandoStore.data = {};\n    }\n\n    removeIfEmptyData(element);\n  }\n}\n\n\nfunction jqLiteExpandoStore(element, createIfNecessary) {\n  var expandoId = element.ng339,\n      expandoStore = expandoId && jqCache[expandoId];\n\n  if (createIfNecessary && !expandoStore) {\n    element.ng339 = expandoId = jqNextId();\n    expandoStore = jqCache[expandoId] = {events: {}, data: {}, handle: undefined};\n  }\n\n  return expandoStore;\n}\n\n\nfunction jqLiteData(element, key, value) {\n  if (jqLiteAcceptsData(element)) {\n    var prop;\n\n    var isSimpleSetter = isDefined(value);\n    var isSimpleGetter = !isSimpleSetter && key && !isObject(key);\n    var massGetter = !key;\n    var expandoStore = jqLiteExpandoStore(element, !isSimpleGetter);\n    var data = expandoStore && expandoStore.data;\n\n    if (isSimpleSetter) { // data('key', value)\n      data[kebabToCamel(key)] = value;\n    } else {\n      if (massGetter) {  // data()\n        return data;\n      } else {\n        if (isSimpleGetter) { // data('key')\n          // don't force creation of expandoStore if it doesn't exist yet\n          return data && data[kebabToCamel(key)];\n        } else { // mass-setter: data({key1: val1, key2: val2})\n          for (prop in key) {\n            data[kebabToCamel(prop)] = key[prop];\n          }\n        }\n      }\n    }\n  }\n}\n\nfunction jqLiteHasClass(element, selector) {\n  if (!element.getAttribute) return false;\n  return ((' ' + (element.getAttribute('class') || '') + ' ').replace(/[\\n\\t]/g, ' ').\n      indexOf(' ' + selector + ' ') > -1);\n}\n\nfunction jqLiteRemoveClass(element, cssClasses) {\n  if (cssClasses && element.setAttribute) {\n    var existingClasses = (' ' + (element.getAttribute('class') || '') + ' ')\n                            .replace(/[\\n\\t]/g, ' ');\n    var newClasses = existingClasses;\n\n    forEach(cssClasses.split(' '), function(cssClass) {\n      cssClass = trim(cssClass);\n      newClasses = newClasses.replace(' ' + cssClass + ' ', ' ');\n    });\n\n    if (newClasses !== existingClasses) {\n      element.setAttribute('class', trim(newClasses));\n    }\n  }\n}\n\nfunction jqLiteAddClass(element, cssClasses) {\n  if (cssClasses && element.setAttribute) {\n    var existingClasses = (' ' + (element.getAttribute('class') || '') + ' ')\n                            .replace(/[\\n\\t]/g, ' ');\n    var newClasses = existingClasses;\n\n    forEach(cssClasses.split(' '), function(cssClass) {\n      cssClass = trim(cssClass);\n      if (newClasses.indexOf(' ' + cssClass + ' ') === -1) {\n        newClasses += cssClass + ' ';\n      }\n    });\n\n    if (newClasses !== existingClasses) {\n      element.setAttribute('class', trim(newClasses));\n    }\n  }\n}\n\n\nfunction jqLiteAddNodes(root, elements) {\n  // THIS CODE IS VERY HOT. Don't make changes without benchmarking.\n\n  if (elements) {\n\n    // if a Node (the most common case)\n    if (elements.nodeType) {\n      root[root.length++] = elements;\n    } else {\n      var length = elements.length;\n\n      // if an Array or NodeList and not a Window\n      if (typeof length === 'number' && elements.window !== elements) {\n        if (length) {\n          for (var i = 0; i < length; i++) {\n            root[root.length++] = elements[i];\n          }\n        }\n      } else {\n        root[root.length++] = elements;\n      }\n    }\n  }\n}\n\n\nfunction jqLiteController(element, name) {\n  return jqLiteInheritedData(element, '$' + (name || 'ngController') + 'Controller');\n}\n\nfunction jqLiteInheritedData(element, name, value) {\n  // if element is the document object work with the html element instead\n  // this makes $(document).scope() possible\n  if (element.nodeType === NODE_TYPE_DOCUMENT) {\n    element = element.documentElement;\n  }\n  var names = isArray(name) ? name : [name];\n\n  while (element) {\n    for (var i = 0, ii = names.length; i < ii; i++) {\n      if (isDefined(value = jqLite.data(element, names[i]))) return value;\n    }\n\n    // If dealing with a document fragment node with a host element, and no parent, use the host\n    // element as the parent. This enables directives within a Shadow DOM or polyfilled Shadow DOM\n    // to lookup parent controllers.\n    element = element.parentNode || (element.nodeType === NODE_TYPE_DOCUMENT_FRAGMENT && element.host);\n  }\n}\n\nfunction jqLiteEmpty(element) {\n  jqLiteDealoc(element, true);\n  while (element.firstChild) {\n    element.removeChild(element.firstChild);\n  }\n}\n\nfunction jqLiteRemove(element, keepData) {\n  if (!keepData) jqLiteDealoc(element);\n  var parent = element.parentNode;\n  if (parent) parent.removeChild(element);\n}\n\n\nfunction jqLiteDocumentLoaded(action, win) {\n  win = win || window;\n  if (win.document.readyState === 'complete') {\n    // Force the action to be run async for consistent behavior\n    // from the action's point of view\n    // i.e. it will definitely not be in a $apply\n    win.setTimeout(action);\n  } else {\n    // No need to unbind this handler as load is only ever called once\n    jqLite(win).on('load', action);\n  }\n}\n\nfunction jqLiteReady(fn) {\n  function trigger() {\n    window.document.removeEventListener('DOMContentLoaded', trigger);\n    window.removeEventListener('load', trigger);\n    fn();\n  }\n\n  // check if document is already loaded\n  if (window.document.readyState === 'complete') {\n    window.setTimeout(fn);\n  } else {\n    // We can not use jqLite since we are not done loading and jQuery could be loaded later.\n\n    // Works for modern browsers and IE9\n    window.document.addEventListener('DOMContentLoaded', trigger);\n\n    // Fallback to window.onload for others\n    window.addEventListener('load', trigger);\n  }\n}\n\n//////////////////////////////////////////\n// Functions which are declared directly.\n//////////////////////////////////////////\nvar JQLitePrototype = JQLite.prototype = {\n  ready: jqLiteReady,\n  toString: function() {\n    var value = [];\n    forEach(this, function(e) { value.push('' + e);});\n    return '[' + value.join(', ') + ']';\n  },\n\n  eq: function(index) {\n      return (index >= 0) ? jqLite(this[index]) : jqLite(this[this.length + index]);\n  },\n\n  length: 0,\n  push: push,\n  sort: [].sort,\n  splice: [].splice\n};\n\n//////////////////////////////////////////\n// Functions iterating getter/setters.\n// these functions return self on setter and\n// value on get.\n//////////////////////////////////////////\nvar BOOLEAN_ATTR = {};\nforEach('multiple,selected,checked,disabled,readOnly,required,open'.split(','), function(value) {\n  BOOLEAN_ATTR[lowercase(value)] = value;\n});\nvar BOOLEAN_ELEMENTS = {};\nforEach('input,select,option,textarea,button,form,details'.split(','), function(value) {\n  BOOLEAN_ELEMENTS[value] = true;\n});\nvar ALIASED_ATTR = {\n  'ngMinlength': 'minlength',\n  'ngMaxlength': 'maxlength',\n  'ngMin': 'min',\n  'ngMax': 'max',\n  'ngPattern': 'pattern',\n  'ngStep': 'step'\n};\n\nfunction getBooleanAttrName(element, name) {\n  // check dom last since we will most likely fail on name\n  var booleanAttr = BOOLEAN_ATTR[name.toLowerCase()];\n\n  // booleanAttr is here twice to minimize DOM access\n  return booleanAttr && BOOLEAN_ELEMENTS[nodeName_(element)] && booleanAttr;\n}\n\nfunction getAliasedAttrName(name) {\n  return ALIASED_ATTR[name];\n}\n\nforEach({\n  data: jqLiteData,\n  removeData: jqLiteRemoveData,\n  hasData: jqLiteHasData,\n  cleanData: function jqLiteCleanData(nodes) {\n    for (var i = 0, ii = nodes.length; i < ii; i++) {\n      jqLiteRemoveData(nodes[i]);\n      jqLiteOff(nodes[i]);\n    }\n  }\n}, function(fn, name) {\n  JQLite[name] = fn;\n});\n\nforEach({\n  data: jqLiteData,\n  inheritedData: jqLiteInheritedData,\n\n  scope: function(element) {\n    // Can't use jqLiteData here directly so we stay compatible with jQuery!\n    return jqLite.data(element, '$scope') || jqLiteInheritedData(element.parentNode || element, ['$isolateScope', '$scope']);\n  },\n\n  isolateScope: function(element) {\n    // Can't use jqLiteData here directly so we stay compatible with jQuery!\n    return jqLite.data(element, '$isolateScope') || jqLite.data(element, '$isolateScopeNoTemplate');\n  },\n\n  controller: jqLiteController,\n\n  injector: function(element) {\n    return jqLiteInheritedData(element, '$injector');\n  },\n\n  removeAttr: function(element, name) {\n    element.removeAttribute(name);\n  },\n\n  hasClass: jqLiteHasClass,\n\n  css: function(element, name, value) {\n    name = cssKebabToCamel(name);\n\n    if (isDefined(value)) {\n      element.style[name] = value;\n    } else {\n      return element.style[name];\n    }\n  },\n\n  attr: function(element, name, value) {\n    var ret;\n    var nodeType = element.nodeType;\n    if (nodeType === NODE_TYPE_TEXT || nodeType === NODE_TYPE_ATTRIBUTE || nodeType === NODE_TYPE_COMMENT ||\n      !element.getAttribute) {\n      return;\n    }\n\n    var lowercasedName = lowercase(name);\n    var isBooleanAttr = BOOLEAN_ATTR[lowercasedName];\n\n    if (isDefined(value)) {\n      // setter\n\n      if (value === null || (value === false && isBooleanAttr)) {\n        element.removeAttribute(name);\n      } else {\n        element.setAttribute(name, isBooleanAttr ? lowercasedName : value);\n      }\n    } else {\n      // getter\n\n      ret = element.getAttribute(name);\n\n      if (isBooleanAttr && ret !== null) {\n        ret = lowercasedName;\n      }\n      // Normalize non-existing attributes to undefined (as jQuery).\n      return ret === null ? undefined : ret;\n    }\n  },\n\n  prop: function(element, name, value) {\n    if (isDefined(value)) {\n      element[name] = value;\n    } else {\n      return element[name];\n    }\n  },\n\n  text: (function() {\n    getText.$dv = '';\n    return getText;\n\n    function getText(element, value) {\n      if (isUndefined(value)) {\n        var nodeType = element.nodeType;\n        return (nodeType === NODE_TYPE_ELEMENT || nodeType === NODE_TYPE_TEXT) ? element.textContent : '';\n      }\n      element.textContent = value;\n    }\n  })(),\n\n  val: function(element, value) {\n    if (isUndefined(value)) {\n      if (element.multiple && nodeName_(element) === 'select') {\n        var result = [];\n        forEach(element.options, function(option) {\n          if (option.selected) {\n            result.push(option.value || option.text);\n          }\n        });\n        return result;\n      }\n      return element.value;\n    }\n    element.value = value;\n  },\n\n  html: function(element, value) {\n    if (isUndefined(value)) {\n      return element.innerHTML;\n    }\n    jqLiteDealoc(element, true);\n    element.innerHTML = value;\n  },\n\n  empty: jqLiteEmpty\n}, function(fn, name) {\n  /**\n   * Properties: writes return selection, reads return first value\n   */\n  JQLite.prototype[name] = function(arg1, arg2) {\n    var i, key;\n    var nodeCount = this.length;\n\n    // jqLiteHasClass has only two arguments, but is a getter-only fn, so we need to special-case it\n    // in a way that survives minification.\n    // jqLiteEmpty takes no arguments but is a setter.\n    if (fn !== jqLiteEmpty &&\n        (isUndefined((fn.length === 2 && (fn !== jqLiteHasClass && fn !== jqLiteController)) ? arg1 : arg2))) {\n      if (isObject(arg1)) {\n\n        // we are a write, but the object properties are the key/values\n        for (i = 0; i < nodeCount; i++) {\n          if (fn === jqLiteData) {\n            // data() takes the whole object in jQuery\n            fn(this[i], arg1);\n          } else {\n            for (key in arg1) {\n              fn(this[i], key, arg1[key]);\n            }\n          }\n        }\n        // return self for chaining\n        return this;\n      } else {\n        // we are a read, so read the first child.\n        // TODO: do we still need this?\n        var value = fn.$dv;\n        // Only if we have $dv do we iterate over all, otherwise it is just the first element.\n        var jj = (isUndefined(value)) ? Math.min(nodeCount, 1) : nodeCount;\n        for (var j = 0; j < jj; j++) {\n          var nodeValue = fn(this[j], arg1, arg2);\n          value = value ? value + nodeValue : nodeValue;\n        }\n        return value;\n      }\n    } else {\n      // we are a write, so apply to all children\n      for (i = 0; i < nodeCount; i++) {\n        fn(this[i], arg1, arg2);\n      }\n      // return self for chaining\n      return this;\n    }\n  };\n});\n\nfunction createEventHandler(element, events) {\n  var eventHandler = function(event, type) {\n    // jQuery specific api\n    event.isDefaultPrevented = function() {\n      return event.defaultPrevented;\n    };\n\n    var eventFns = events[type || event.type];\n    var eventFnsLength = eventFns ? eventFns.length : 0;\n\n    if (!eventFnsLength) return;\n\n    if (isUndefined(event.immediatePropagationStopped)) {\n      var originalStopImmediatePropagation = event.stopImmediatePropagation;\n      event.stopImmediatePropagation = function() {\n        event.immediatePropagationStopped = true;\n\n        if (event.stopPropagation) {\n          event.stopPropagation();\n        }\n\n        if (originalStopImmediatePropagation) {\n          originalStopImmediatePropagation.call(event);\n        }\n      };\n    }\n\n    event.isImmediatePropagationStopped = function() {\n      return event.immediatePropagationStopped === true;\n    };\n\n    // Some events have special handlers that wrap the real handler\n    var handlerWrapper = eventFns.specialHandlerWrapper || defaultHandlerWrapper;\n\n    // Copy event handlers in case event handlers array is modified during execution.\n    if ((eventFnsLength > 1)) {\n      eventFns = shallowCopy(eventFns);\n    }\n\n    for (var i = 0; i < eventFnsLength; i++) {\n      if (!event.isImmediatePropagationStopped()) {\n        handlerWrapper(element, event, eventFns[i]);\n      }\n    }\n  };\n\n  // TODO: this is a hack for angularMocks/clearDataCache that makes it possible to deregister all\n  //       events on `element`\n  eventHandler.elem = element;\n  return eventHandler;\n}\n\nfunction defaultHandlerWrapper(element, event, handler) {\n  handler.call(element, event);\n}\n\nfunction specialMouseHandlerWrapper(target, event, handler) {\n  // Refer to jQuery's implementation of mouseenter & mouseleave\n  // Read about mouseenter and mouseleave:\n  // http://www.quirksmode.org/js/events_mouse.html#link8\n  var related = event.relatedTarget;\n  // For mousenter/leave call the handler if related is outside the target.\n  // NB: No relatedTarget if the mouse left/entered the browser window\n  if (!related || (related !== target && !jqLiteContains.call(target, related))) {\n    handler.call(target, event);\n  }\n}\n\n//////////////////////////////////////////\n// Functions iterating traversal.\n// These functions chain results into a single\n// selector.\n//////////////////////////////////////////\nforEach({\n  removeData: jqLiteRemoveData,\n\n  on: function jqLiteOn(element, type, fn, unsupported) {\n    if (isDefined(unsupported)) throw jqLiteMinErr('onargs', 'jqLite#on() does not support the `selector` or `eventData` parameters');\n\n    // Do not add event handlers to non-elements because they will not be cleaned up.\n    if (!jqLiteAcceptsData(element)) {\n      return;\n    }\n\n    var expandoStore = jqLiteExpandoStore(element, true);\n    var events = expandoStore.events;\n    var handle = expandoStore.handle;\n\n    if (!handle) {\n      handle = expandoStore.handle = createEventHandler(element, events);\n    }\n\n    // http://jsperf.com/string-indexof-vs-split\n    var types = type.indexOf(' ') >= 0 ? type.split(' ') : [type];\n    var i = types.length;\n\n    var addHandler = function(type, specialHandlerWrapper, noEventListener) {\n      var eventFns = events[type];\n\n      if (!eventFns) {\n        eventFns = events[type] = [];\n        eventFns.specialHandlerWrapper = specialHandlerWrapper;\n        if (type !== '$destroy' && !noEventListener) {\n          element.addEventListener(type, handle);\n        }\n      }\n\n      eventFns.push(fn);\n    };\n\n    while (i--) {\n      type = types[i];\n      if (MOUSE_EVENT_MAP[type]) {\n        addHandler(MOUSE_EVENT_MAP[type], specialMouseHandlerWrapper);\n        addHandler(type, undefined, true);\n      } else {\n        addHandler(type);\n      }\n    }\n  },\n\n  off: jqLiteOff,\n\n  one: function(element, type, fn) {\n    element = jqLite(element);\n\n    //add the listener twice so that when it is called\n    //you can remove the original function and still be\n    //able to call element.off(ev, fn) normally\n    element.on(type, function onFn() {\n      element.off(type, fn);\n      element.off(type, onFn);\n    });\n    element.on(type, fn);\n  },\n\n  replaceWith: function(element, replaceNode) {\n    var index, parent = element.parentNode;\n    jqLiteDealoc(element);\n    forEach(new JQLite(replaceNode), function(node) {\n      if (index) {\n        parent.insertBefore(node, index.nextSibling);\n      } else {\n        parent.replaceChild(node, element);\n      }\n      index = node;\n    });\n  },\n\n  children: function(element) {\n    var children = [];\n    forEach(element.childNodes, function(element) {\n      if (element.nodeType === NODE_TYPE_ELEMENT) {\n        children.push(element);\n      }\n    });\n    return children;\n  },\n\n  contents: function(element) {\n    return element.contentDocument || element.childNodes || [];\n  },\n\n  append: function(element, node) {\n    var nodeType = element.nodeType;\n    if (nodeType !== NODE_TYPE_ELEMENT && nodeType !== NODE_TYPE_DOCUMENT_FRAGMENT) return;\n\n    node = new JQLite(node);\n\n    for (var i = 0, ii = node.length; i < ii; i++) {\n      var child = node[i];\n      element.appendChild(child);\n    }\n  },\n\n  prepend: function(element, node) {\n    if (element.nodeType === NODE_TYPE_ELEMENT) {\n      var index = element.firstChild;\n      forEach(new JQLite(node), function(child) {\n        element.insertBefore(child, index);\n      });\n    }\n  },\n\n  wrap: function(element, wrapNode) {\n    jqLiteWrapNode(element, jqLite(wrapNode).eq(0).clone()[0]);\n  },\n\n  remove: jqLiteRemove,\n\n  detach: function(element) {\n    jqLiteRemove(element, true);\n  },\n\n  after: function(element, newElement) {\n    var index = element, parent = element.parentNode;\n\n    if (parent) {\n      newElement = new JQLite(newElement);\n\n      for (var i = 0, ii = newElement.length; i < ii; i++) {\n        var node = newElement[i];\n        parent.insertBefore(node, index.nextSibling);\n        index = node;\n      }\n    }\n  },\n\n  addClass: jqLiteAddClass,\n  removeClass: jqLiteRemoveClass,\n\n  toggleClass: function(element, selector, condition) {\n    if (selector) {\n      forEach(selector.split(' '), function(className) {\n        var classCondition = condition;\n        if (isUndefined(classCondition)) {\n          classCondition = !jqLiteHasClass(element, className);\n        }\n        (classCondition ? jqLiteAddClass : jqLiteRemoveClass)(element, className);\n      });\n    }\n  },\n\n  parent: function(element) {\n    var parent = element.parentNode;\n    return parent && parent.nodeType !== NODE_TYPE_DOCUMENT_FRAGMENT ? parent : null;\n  },\n\n  next: function(element) {\n    return element.nextElementSibling;\n  },\n\n  find: function(element, selector) {\n    if (element.getElementsByTagName) {\n      return element.getElementsByTagName(selector);\n    } else {\n      return [];\n    }\n  },\n\n  clone: jqLiteClone,\n\n  triggerHandler: function(element, event, extraParameters) {\n\n    var dummyEvent, eventFnsCopy, handlerArgs;\n    var eventName = event.type || event;\n    var expandoStore = jqLiteExpandoStore(element);\n    var events = expandoStore && expandoStore.events;\n    var eventFns = events && events[eventName];\n\n    if (eventFns) {\n      // Create a dummy event to pass to the handlers\n      dummyEvent = {\n        preventDefault: function() { this.defaultPrevented = true; },\n        isDefaultPrevented: function() { return this.defaultPrevented === true; },\n        stopImmediatePropagation: function() { this.immediatePropagationStopped = true; },\n        isImmediatePropagationStopped: function() { return this.immediatePropagationStopped === true; },\n        stopPropagation: noop,\n        type: eventName,\n        target: element\n      };\n\n      // If a custom event was provided then extend our dummy event with it\n      if (event.type) {\n        dummyEvent = extend(dummyEvent, event);\n      }\n\n      // Copy event handlers in case event handlers array is modified during execution.\n      eventFnsCopy = shallowCopy(eventFns);\n      handlerArgs = extraParameters ? [dummyEvent].concat(extraParameters) : [dummyEvent];\n\n      forEach(eventFnsCopy, function(fn) {\n        if (!dummyEvent.isImmediatePropagationStopped()) {\n          fn.apply(element, handlerArgs);\n        }\n      });\n    }\n  }\n}, function(fn, name) {\n  /**\n   * chaining functions\n   */\n  JQLite.prototype[name] = function(arg1, arg2, arg3) {\n    var value;\n\n    for (var i = 0, ii = this.length; i < ii; i++) {\n      if (isUndefined(value)) {\n        value = fn(this[i], arg1, arg2, arg3);\n        if (isDefined(value)) {\n          // any function which returns a value needs to be wrapped\n          value = jqLite(value);\n        }\n      } else {\n        jqLiteAddNodes(value, fn(this[i], arg1, arg2, arg3));\n      }\n    }\n    return isDefined(value) ? value : this;\n  };\n});\n\n// bind legacy bind/unbind to on/off\nJQLite.prototype.bind = JQLite.prototype.on;\nJQLite.prototype.unbind = JQLite.prototype.off;\n\n\n// Provider for private $$jqLite service\n/** @this */\nfunction $$jqLiteProvider() {\n  this.$get = function $$jqLite() {\n    return extend(JQLite, {\n      hasClass: function(node, classes) {\n        if (node.attr) node = node[0];\n        return jqLiteHasClass(node, classes);\n      },\n      addClass: function(node, classes) {\n        if (node.attr) node = node[0];\n        return jqLiteAddClass(node, classes);\n      },\n      removeClass: function(node, classes) {\n        if (node.attr) node = node[0];\n        return jqLiteRemoveClass(node, classes);\n      }\n    });\n  };\n}\n\n/**\n * Computes a hash of an 'obj'.\n * Hash of a:\n *  string is string\n *  number is number as string\n *  object is either result of calling $$hashKey function on the object or uniquely generated id,\n *         that is also assigned to the $$hashKey property of the object.\n *\n * @param obj\n * @returns {string} hash string such that the same input will have the same hash string.\n *         The resulting string key is in 'type:hashKey' format.\n */\nfunction hashKey(obj, nextUidFn) {\n  var key = obj && obj.$$hashKey;\n\n  if (key) {\n    if (typeof key === 'function') {\n      key = obj.$$hashKey();\n    }\n    return key;\n  }\n\n  var objType = typeof obj;\n  if (objType === 'function' || (objType === 'object' && obj !== null)) {\n    key = obj.$$hashKey = objType + ':' + (nextUidFn || nextUid)();\n  } else {\n    key = objType + ':' + obj;\n  }\n\n  return key;\n}\n\n// A minimal ES2015 Map implementation.\n// Should be bug/feature equivalent to the native implementations of supported browsers\n// (for the features required in Angular).\n// See https://kangax.github.io/compat-table/es6/#test-Map\nvar nanKey = Object.create(null);\nfunction NgMapShim() {\n  this._keys = [];\n  this._values = [];\n  this._lastKey = NaN;\n  this._lastIndex = -1;\n}\nNgMapShim.prototype = {\n  _idx: function(key) {\n    if (key !== this._lastKey) {\n      this._lastKey = key;\n      this._lastIndex = this._keys.indexOf(key);\n    }\n    return this._lastIndex;\n  },\n  _transformKey: function(key) {\n    return isNumberNaN(key) ? nanKey : key;\n  },\n  get: function(key) {\n    key = this._transformKey(key);\n    var idx = this._idx(key);\n    if (idx !== -1) {\n      return this._values[idx];\n    }\n  },\n  has: function(key) {\n    key = this._transformKey(key);\n    var idx = this._idx(key);\n    return idx !== -1;\n  },\n  set: function(key, value) {\n    key = this._transformKey(key);\n    var idx = this._idx(key);\n    if (idx === -1) {\n      idx = this._lastIndex = this._keys.length;\n    }\n    this._keys[idx] = key;\n    this._values[idx] = value;\n\n    // Support: IE11\n    // Do not `return this` to simulate the partial IE11 implementation\n  },\n  delete: function(key) {\n    key = this._transformKey(key);\n    var idx = this._idx(key);\n    if (idx === -1) {\n      return false;\n    }\n    this._keys.splice(idx, 1);\n    this._values.splice(idx, 1);\n    this._lastKey = NaN;\n    this._lastIndex = -1;\n    return true;\n  }\n};\n\n// For now, always use `NgMapShim`, even if `window.Map` is available. Some native implementations\n// are still buggy (often in subtle ways) and can cause hard-to-debug failures. When native `Map`\n// implementations get more stable, we can reconsider switching to `window.Map` (when available).\nvar NgMap = NgMapShim;\n\nvar $$MapProvider = [/** @this */function() {\n  this.$get = [function() {\n    return NgMap;\n  }];\n}];\n\n/**\n * @ngdoc function\n * @module ng\n * @name angular.injector\n * @kind function\n *\n * @description\n * Creates an injector object that can be used for retrieving services as well as for\n * dependency injection (see {@link guide/di dependency injection}).\n *\n * @param {Array.<string|Function>} modules A list of module functions or their aliases. See\n *     {@link angular.module}. The `ng` module must be explicitly added.\n * @param {boolean=} [strictDi=false] Whether the injector should be in strict mode, which\n *     disallows argument name annotation inference.\n * @returns {injector} Injector object. See {@link auto.$injector $injector}.\n *\n * @example\n * Typical usage\n * ```js\n *   // create an injector\n *   var $injector = angular.injector(['ng']);\n *\n *   // use the injector to kick off your application\n *   // use the type inference to auto inject arguments, or use implicit injection\n *   $injector.invoke(function($rootScope, $compile, $document) {\n *     $compile($document)($rootScope);\n *     $rootScope.$digest();\n *   });\n * ```\n *\n * Sometimes you want to get access to the injector of a currently running AngularJS app\n * from outside AngularJS. Perhaps, you want to inject and compile some markup after the\n * application has been bootstrapped. You can do this using the extra `injector()` added\n * to JQuery/jqLite elements. See {@link angular.element}.\n *\n * *This is fairly rare but could be the case if a third party library is injecting the\n * markup.*\n *\n * In the following example a new block of HTML containing a `ng-controller`\n * directive is added to the end of the document body by JQuery. We then compile and link\n * it into the current AngularJS scope.\n *\n * ```js\n * var $div = $('<div ng-controller=\"MyCtrl\">{{content.label}}</div>');\n * $(document.body).append($div);\n *\n * angular.element(document).injector().invoke(function($compile) {\n *   var scope = angular.element($div).scope();\n *   $compile($div)(scope);\n * });\n * ```\n */\n\n\n/**\n * @ngdoc module\n * @name auto\n * @installation\n * @description\n *\n * Implicit module which gets automatically added to each {@link auto.$injector $injector}.\n */\n\nvar ARROW_ARG = /^([^(]+?)=>/;\nvar FN_ARGS = /^[^(]*\\(\\s*([^)]*)\\)/m;\nvar FN_ARG_SPLIT = /,/;\nvar FN_ARG = /^\\s*(_?)(\\S+?)\\1\\s*$/;\nvar STRIP_COMMENTS = /((\\/\\/.*$)|(\\/\\*[\\s\\S]*?\\*\\/))/mg;\nvar $injectorMinErr = minErr('$injector');\n\nfunction stringifyFn(fn) {\n  return Function.prototype.toString.call(fn);\n}\n\nfunction extractArgs(fn) {\n  var fnText = stringifyFn(fn).replace(STRIP_COMMENTS, ''),\n      args = fnText.match(ARROW_ARG) || fnText.match(FN_ARGS);\n  return args;\n}\n\nfunction anonFn(fn) {\n  // For anonymous functions, showing at the very least the function signature can help in\n  // debugging.\n  var args = extractArgs(fn);\n  if (args) {\n    return 'function(' + (args[1] || '').replace(/[\\s\\r\\n]+/, ' ') + ')';\n  }\n  return 'fn';\n}\n\nfunction annotate(fn, strictDi, name) {\n  var $inject,\n      argDecl,\n      last;\n\n  if (typeof fn === 'function') {\n    if (!($inject = fn.$inject)) {\n      $inject = [];\n      if (fn.length) {\n        if (strictDi) {\n          if (!isString(name) || !name) {\n            name = fn.name || anonFn(fn);\n          }\n          throw $injectorMinErr('strictdi',\n            '{0} is not using explicit annotation and cannot be invoked in strict mode', name);\n        }\n        argDecl = extractArgs(fn);\n        forEach(argDecl[1].split(FN_ARG_SPLIT), function(arg) {\n          arg.replace(FN_ARG, function(all, underscore, name) {\n            $inject.push(name);\n          });\n        });\n      }\n      fn.$inject = $inject;\n    }\n  } else if (isArray(fn)) {\n    last = fn.length - 1;\n    assertArgFn(fn[last], 'fn');\n    $inject = fn.slice(0, last);\n  } else {\n    assertArgFn(fn, 'fn', true);\n  }\n  return $inject;\n}\n\n///////////////////////////////////////\n\n/**\n * @ngdoc service\n * @name $injector\n *\n * @description\n *\n * `$injector` is used to retrieve object instances as defined by\n * {@link auto.$provide provider}, instantiate types, invoke methods,\n * and load modules.\n *\n * The following always holds true:\n *\n * ```js\n *   var $injector = angular.injector();\n *   expect($injector.get('$injector')).toBe($injector);\n *   expect($injector.invoke(function($injector) {\n *     return $injector;\n *   })).toBe($injector);\n * ```\n *\n * ## Injection Function Annotation\n *\n * JavaScript does not have annotations, and annotations are needed for dependency injection. The\n * following are all valid ways of annotating function with injection arguments and are equivalent.\n *\n * ```js\n *   // inferred (only works if code not minified/obfuscated)\n *   $injector.invoke(function(serviceA){});\n *\n *   // annotated\n *   function explicit(serviceA) {};\n *   explicit.$inject = ['serviceA'];\n *   $injector.invoke(explicit);\n *\n *   // inline\n *   $injector.invoke(['serviceA', function(serviceA){}]);\n * ```\n *\n * ### Inference\n *\n * In JavaScript calling `toString()` on a function returns the function definition. The definition\n * can then be parsed and the function arguments can be extracted. This method of discovering\n * annotations is disallowed when the injector is in strict mode.\n * *NOTE:* This does not work with minification, and obfuscation tools since these tools change the\n * argument names.\n *\n * ### `$inject` Annotation\n * By adding an `$inject` property onto a function the injection parameters can be specified.\n *\n * ### Inline\n * As an array of injection names, where the last item in the array is the function to call.\n */\n\n/**\n * @ngdoc property\n * @name $injector#modules\n * @type {Object}\n * @description\n * A hash containing all the modules that have been loaded into the\n * $injector.\n *\n * You can use this property to find out information about a module via the\n * {@link angular.Module#info `myModule.info(...)`} method.\n *\n * For example:\n *\n * ```\n * var info = $injector.modules['ngAnimate'].info();\n * ```\n *\n * **Do not use this property to attempt to modify the modules after the application\n * has been bootstrapped.**\n */\n\n\n/**\n * @ngdoc method\n * @name $injector#get\n *\n * @description\n * Return an instance of the service.\n *\n * @param {string} name The name of the instance to retrieve.\n * @param {string=} caller An optional string to provide the origin of the function call for error messages.\n * @return {*} The instance.\n */\n\n/**\n * @ngdoc method\n * @name $injector#invoke\n *\n * @description\n * Invoke the method and supply the method arguments from the `$injector`.\n *\n * @param {Function|Array.<string|Function>} fn The injectable function to invoke. Function parameters are\n *   injected according to the {@link guide/di $inject Annotation} rules.\n * @param {Object=} self The `this` for the invoked method.\n * @param {Object=} locals Optional object. If preset then any argument names are read from this\n *                         object first, before the `$injector` is consulted.\n * @returns {*} the value returned by the invoked `fn` function.\n */\n\n/**\n * @ngdoc method\n * @name $injector#has\n *\n * @description\n * Allows the user to query if the particular service exists.\n *\n * @param {string} name Name of the service to query.\n * @returns {boolean} `true` if injector has given service.\n */\n\n/**\n * @ngdoc method\n * @name $injector#instantiate\n * @description\n * Create a new instance of JS type. The method takes a constructor function, invokes the new\n * operator, and supplies all of the arguments to the constructor function as specified by the\n * constructor annotation.\n *\n * @param {Function} Type Annotated constructor function.\n * @param {Object=} locals Optional object. If preset then any argument names are read from this\n * object first, before the `$injector` is consulted.\n * @returns {Object} new instance of `Type`.\n */\n\n/**\n * @ngdoc method\n * @name $injector#annotate\n *\n * @description\n * Returns an array of service names which the function is requesting for injection. This API is\n * used by the injector to determine which services need to be injected into the function when the\n * function is invoked. There are three ways in which the function can be annotated with the needed\n * dependencies.\n *\n * #### Argument names\n *\n * The simplest form is to extract the dependencies from the arguments of the function. This is done\n * by converting the function into a string using `toString()` method and extracting the argument\n * names.\n * ```js\n *   // Given\n *   function MyController($scope, $route) {\n *     // ...\n *   }\n *\n *   // Then\n *   expect(injector.annotate(MyController)).toEqual(['$scope', '$route']);\n * ```\n *\n * You can disallow this method by using strict injection mode.\n *\n * This method does not work with code minification / obfuscation. For this reason the following\n * annotation strategies are supported.\n *\n * #### The `$inject` property\n *\n * If a function has an `$inject` property and its value is an array of strings, then the strings\n * represent names of services to be injected into the function.\n * ```js\n *   // Given\n *   var MyController = function(obfuscatedScope, obfuscatedRoute) {\n *     // ...\n *   }\n *   // Define function dependencies\n *   MyController['$inject'] = ['$scope', '$route'];\n *\n *   // Then\n *   expect(injector.annotate(MyController)).toEqual(['$scope', '$route']);\n * ```\n *\n * #### The array notation\n *\n * It is often desirable to inline Injected functions and that's when setting the `$inject` property\n * is very inconvenient. In these situations using the array notation to specify the dependencies in\n * a way that survives minification is a better choice:\n *\n * ```js\n *   // We wish to write this (not minification / obfuscation safe)\n *   injector.invoke(function($compile, $rootScope) {\n *     // ...\n *   });\n *\n *   // We are forced to write break inlining\n *   var tmpFn = function(obfuscatedCompile, obfuscatedRootScope) {\n *     // ...\n *   };\n *   tmpFn.$inject = ['$compile', '$rootScope'];\n *   injector.invoke(tmpFn);\n *\n *   // To better support inline function the inline annotation is supported\n *   injector.invoke(['$compile', '$rootScope', function(obfCompile, obfRootScope) {\n *     // ...\n *   }]);\n *\n *   // Therefore\n *   expect(injector.annotate(\n *      ['$compile', '$rootScope', function(obfus_$compile, obfus_$rootScope) {}])\n *    ).toEqual(['$compile', '$rootScope']);\n * ```\n *\n * @param {Function|Array.<string|Function>} fn Function for which dependent service names need to\n * be retrieved as described above.\n *\n * @param {boolean=} [strictDi=false] Disallow argument name annotation inference.\n *\n * @returns {Array.<string>} The names of the services which the function requires.\n */\n/**\n * @ngdoc method\n * @name $injector#loadNewModules\n *\n * @description\n *\n * **This is a dangerous API, which you use at your own risk!**\n *\n * Add the specified modules to the current injector.\n *\n * This method will add each of the injectables to the injector and execute all of the config and run\n * blocks for each module passed to the method.\n *\n * If a module has already been loaded into the injector then it will not be loaded again.\n *\n * * The application developer is responsible for loading the code containing the modules; and for\n * ensuring that lazy scripts are not downloaded and executed more often that desired.\n * * Previously compiled HTML will not be affected by newly loaded directives, filters and components.\n * * Modules cannot be unloaded.\n *\n * You can use {@link $injector#modules `$injector.modules`} to check whether a module has been loaded\n * into the injector, which may indicate whether the script has been executed already.\n *\n * @example\n * Here is an example of loading a bundle of modules, with a utility method called `getScript`:\n *\n * ```javascript\n * app.factory('loadModule', function($injector) {\n *   return function loadModule(moduleName, bundleUrl) {\n *     return getScript(bundleUrl).then(function() { $injector.loadNewModules([moduleName]); });\n *   };\n * })\n * ```\n *\n * @param {Array<String|Function|Array>=} mods an array of modules to load into the application.\n *     Each item in the array should be the name of a predefined module or a (DI annotated)\n *     function that will be invoked by the injector as a `config` block.\n *     See: {@link angular.module modules}\n */\n\n\n/**\n * @ngdoc service\n * @name $provide\n *\n * @description\n *\n * The {@link auto.$provide $provide} service has a number of methods for registering components\n * with the {@link auto.$injector $injector}. Many of these functions are also exposed on\n * {@link angular.Module}.\n *\n * An AngularJS **service** is a singleton object created by a **service factory**.  These **service\n * factories** are functions which, in turn, are created by a **service provider**.\n * The **service providers** are constructor functions. When instantiated they must contain a\n * property called `$get`, which holds the **service factory** function.\n *\n * When you request a service, the {@link auto.$injector $injector} is responsible for finding the\n * correct **service provider**, instantiating it and then calling its `$get` **service factory**\n * function to get the instance of the **service**.\n *\n * Often services have no configuration options and there is no need to add methods to the service\n * provider.  The provider will be no more than a constructor function with a `$get` property. For\n * these cases the {@link auto.$provide $provide} service has additional helper methods to register\n * services without specifying a provider.\n *\n * * {@link auto.$provide#provider provider(name, provider)} - registers a **service provider** with the\n *     {@link auto.$injector $injector}\n * * {@link auto.$provide#constant constant(name, obj)} - registers a value/object that can be accessed by\n *     providers and services.\n * * {@link auto.$provide#value value(name, obj)} - registers a value/object that can only be accessed by\n *     services, not providers.\n * * {@link auto.$provide#factory factory(name, fn)} - registers a service **factory function**\n *     that will be wrapped in a **service provider** object, whose `$get` property will contain the\n *     given factory function.\n * * {@link auto.$provide#service service(name, Fn)} - registers a **constructor function**\n *     that will be wrapped in a **service provider** object, whose `$get` property will instantiate\n *      a new object using the given constructor function.\n * * {@link auto.$provide#decorator decorator(name, decorFn)} - registers a **decorator function** that\n *      will be able to modify or replace the implementation of another service.\n *\n * See the individual methods for more information and examples.\n */\n\n/**\n * @ngdoc method\n * @name $provide#provider\n * @description\n *\n * Register a **provider function** with the {@link auto.$injector $injector}. Provider functions\n * are constructor functions, whose instances are responsible for \"providing\" a factory for a\n * service.\n *\n * Service provider names start with the name of the service they provide followed by `Provider`.\n * For example, the {@link ng.$log $log} service has a provider called\n * {@link ng.$logProvider $logProvider}.\n *\n * Service provider objects can have additional methods which allow configuration of the provider\n * and its service. Importantly, you can configure what kind of service is created by the `$get`\n * method, or how that service will act. For example, the {@link ng.$logProvider $logProvider} has a\n * method {@link ng.$logProvider#debugEnabled debugEnabled}\n * which lets you specify whether the {@link ng.$log $log} service will log debug messages to the\n * console or not.\n *\n * It is possible to inject other providers into the provider function,\n * but the injected provider must have been defined before the one that requires it.\n *\n * @param {string} name The name of the instance. NOTE: the provider will be available under `name +\n                        'Provider'` key.\n * @param {(Object|function())} provider If the provider is:\n *\n *   - `Object`: then it should have a `$get` method. The `$get` method will be invoked using\n *     {@link auto.$injector#invoke $injector.invoke()} when an instance needs to be created.\n *   - `Constructor`: a new instance of the provider will be created using\n *     {@link auto.$injector#instantiate $injector.instantiate()}, then treated as `object`.\n *\n * @returns {Object} registered provider instance\n\n * @example\n *\n * The following example shows how to create a simple event tracking service and register it using\n * {@link auto.$provide#provider $provide.provider()}.\n *\n * ```js\n *  // Define the eventTracker provider\n *  function EventTrackerProvider() {\n *    var trackingUrl = '/track';\n *\n *    // A provider method for configuring where the tracked events should been saved\n *    this.setTrackingUrl = function(url) {\n *      trackingUrl = url;\n *    };\n *\n *    // The service factory function\n *    this.$get = ['$http', function($http) {\n *      var trackedEvents = {};\n *      return {\n *        // Call this to track an event\n *        event: function(event) {\n *          var count = trackedEvents[event] || 0;\n *          count += 1;\n *          trackedEvents[event] = count;\n *          return count;\n *        },\n *        // Call this to save the tracked events to the trackingUrl\n *        save: function() {\n *          $http.post(trackingUrl, trackedEvents);\n *        }\n *      };\n *    }];\n *  }\n *\n *  describe('eventTracker', function() {\n *    var postSpy;\n *\n *    beforeEach(module(function($provide) {\n *      // Register the eventTracker provider\n *      $provide.provider('eventTracker', EventTrackerProvider);\n *    }));\n *\n *    beforeEach(module(function(eventTrackerProvider) {\n *      // Configure eventTracker provider\n *      eventTrackerProvider.setTrackingUrl('/custom-track');\n *    }));\n *\n *    it('tracks events', inject(function(eventTracker) {\n *      expect(eventTracker.event('login')).toEqual(1);\n *      expect(eventTracker.event('login')).toEqual(2);\n *    }));\n *\n *    it('saves to the tracking url', inject(function(eventTracker, $http) {\n *      postSpy = spyOn($http, 'post');\n *      eventTracker.event('login');\n *      eventTracker.save();\n *      expect(postSpy).toHaveBeenCalled();\n *      expect(postSpy.mostRecentCall.args[0]).not.toEqual('/track');\n *      expect(postSpy.mostRecentCall.args[0]).toEqual('/custom-track');\n *      expect(postSpy.mostRecentCall.args[1]).toEqual({ 'login': 1 });\n *    }));\n *  });\n * ```\n */\n\n/**\n * @ngdoc method\n * @name $provide#factory\n * @description\n *\n * Register a **service factory**, which will be called to return the service instance.\n * This is short for registering a service where its provider consists of only a `$get` property,\n * which is the given service factory function.\n * You should use {@link auto.$provide#factory $provide.factory(getFn)} if you do not need to\n * configure your service in a provider.\n *\n * @param {string} name The name of the instance.\n * @param {Function|Array.<string|Function>} $getFn The injectable $getFn for the instance creation.\n *                      Internally this is a short hand for `$provide.provider(name, {$get: $getFn})`.\n * @returns {Object} registered provider instance\n *\n * @example\n * Here is an example of registering a service\n * ```js\n *   $provide.factory('ping', ['$http', function($http) {\n *     return function ping() {\n *       return $http.send('/ping');\n *     };\n *   }]);\n * ```\n * You would then inject and use this service like this:\n * ```js\n *   someModule.controller('Ctrl', ['ping', function(ping) {\n *     ping();\n *   }]);\n * ```\n */\n\n\n/**\n * @ngdoc method\n * @name $provide#service\n * @description\n *\n * Register a **service constructor**, which will be invoked with `new` to create the service\n * instance.\n * This is short for registering a service where its provider's `$get` property is a factory\n * function that returns an instance instantiated by the injector from the service constructor\n * function.\n *\n * Internally it looks a bit like this:\n *\n * ```\n * {\n *   $get: function() {\n *     return $injector.instantiate(constructor);\n *   }\n * }\n * ```\n *\n *\n * You should use {@link auto.$provide#service $provide.service(class)} if you define your service\n * as a type/class.\n *\n * @param {string} name The name of the instance.\n * @param {Function|Array.<string|Function>} constructor An injectable class (constructor function)\n *     that will be instantiated.\n * @returns {Object} registered provider instance\n *\n * @example\n * Here is an example of registering a service using\n * {@link auto.$provide#service $provide.service(class)}.\n * ```js\n *   var Ping = function($http) {\n *     this.$http = $http;\n *   };\n *\n *   Ping.$inject = ['$http'];\n *\n *   Ping.prototype.send = function() {\n *     return this.$http.get('/ping');\n *   };\n *   $provide.service('ping', Ping);\n * ```\n * You would then inject and use this service like this:\n * ```js\n *   someModule.controller('Ctrl', ['ping', function(ping) {\n *     ping.send();\n *   }]);\n * ```\n */\n\n\n/**\n * @ngdoc method\n * @name $provide#value\n * @description\n *\n * Register a **value service** with the {@link auto.$injector $injector}, such as a string, a\n * number, an array, an object or a function. This is short for registering a service where its\n * provider's `$get` property is a factory function that takes no arguments and returns the **value\n * service**. That also means it is not possible to inject other services into a value service.\n *\n * Value services are similar to constant services, except that they cannot be injected into a\n * module configuration function (see {@link angular.Module#config}) but they can be overridden by\n * an AngularJS {@link auto.$provide#decorator decorator}.\n *\n * @param {string} name The name of the instance.\n * @param {*} value The value.\n * @returns {Object} registered provider instance\n *\n * @example\n * Here are some examples of creating value services.\n * ```js\n *   $provide.value('ADMIN_USER', 'admin');\n *\n *   $provide.value('RoleLookup', { admin: 0, writer: 1, reader: 2 });\n *\n *   $provide.value('halfOf', function(value) {\n *     return value / 2;\n *   });\n * ```\n */\n\n\n/**\n * @ngdoc method\n * @name $provide#constant\n * @description\n *\n * Register a **constant service** with the {@link auto.$injector $injector}, such as a string,\n * a number, an array, an object or a function. Like the {@link auto.$provide#value value}, it is not\n * possible to inject other services into a constant.\n *\n * But unlike {@link auto.$provide#value value}, a constant can be\n * injected into a module configuration function (see {@link angular.Module#config}) and it cannot\n * be overridden by an AngularJS {@link auto.$provide#decorator decorator}.\n *\n * @param {string} name The name of the constant.\n * @param {*} value The constant value.\n * @returns {Object} registered instance\n *\n * @example\n * Here a some examples of creating constants:\n * ```js\n *   $provide.constant('SHARD_HEIGHT', 306);\n *\n *   $provide.constant('MY_COLOURS', ['red', 'blue', 'grey']);\n *\n *   $provide.constant('double', function(value) {\n *     return value * 2;\n *   });\n * ```\n */\n\n\n/**\n * @ngdoc method\n * @name $provide#decorator\n * @description\n *\n * Register a **decorator function** with the {@link auto.$injector $injector}. A decorator function\n * intercepts the creation of a service, allowing it to override or modify the behavior of the\n * service. The return value of the decorator function may be the original service, or a new service\n * that replaces (or wraps and delegates to) the original service.\n *\n * You can find out more about using decorators in the {@link guide/decorators} guide.\n *\n * @param {string} name The name of the service to decorate.\n * @param {Function|Array.<string|Function>} decorator This function will be invoked when the service needs to be\n *    provided and should return the decorated service instance. The function is called using\n *    the {@link auto.$injector#invoke injector.invoke} method and is therefore fully injectable.\n *    Local injection arguments:\n *\n *    * `$delegate` - The original service instance, which can be replaced, monkey patched, configured,\n *      decorated or delegated to.\n *\n * @example\n * Here we decorate the {@link ng.$log $log} service to convert warnings to errors by intercepting\n * calls to {@link ng.$log#error $log.warn()}.\n * ```js\n *   $provide.decorator('$log', ['$delegate', function($delegate) {\n *     $delegate.warn = $delegate.error;\n *     return $delegate;\n *   }]);\n * ```\n */\n\n\nfunction createInjector(modulesToLoad, strictDi) {\n  strictDi = (strictDi === true);\n  var INSTANTIATING = {},\n      providerSuffix = 'Provider',\n      path = [],\n      loadedModules = new NgMap(),\n      providerCache = {\n        $provide: {\n            provider: supportObject(provider),\n            factory: supportObject(factory),\n            service: supportObject(service),\n            value: supportObject(value),\n            constant: supportObject(constant),\n            decorator: decorator\n          }\n      },\n      providerInjector = (providerCache.$injector =\n          createInternalInjector(providerCache, function(serviceName, caller) {\n            if (angular.isString(caller)) {\n              path.push(caller);\n            }\n            throw $injectorMinErr('unpr', 'Unknown provider: {0}', path.join(' <- '));\n          })),\n      instanceCache = {},\n      protoInstanceInjector =\n          createInternalInjector(instanceCache, function(serviceName, caller) {\n            var provider = providerInjector.get(serviceName + providerSuffix, caller);\n            return instanceInjector.invoke(\n                provider.$get, provider, undefined, serviceName);\n          }),\n      instanceInjector = protoInstanceInjector;\n\n  providerCache['$injector' + providerSuffix] = { $get: valueFn(protoInstanceInjector) };\n  instanceInjector.modules = providerInjector.modules = createMap();\n  var runBlocks = loadModules(modulesToLoad);\n  instanceInjector = protoInstanceInjector.get('$injector');\n  instanceInjector.strictDi = strictDi;\n  forEach(runBlocks, function(fn) { if (fn) instanceInjector.invoke(fn); });\n\n  instanceInjector.loadNewModules = function(mods) {\n    forEach(loadModules(mods), function(fn) { if (fn) instanceInjector.invoke(fn); });\n  };\n\n\n  return instanceInjector;\n\n  ////////////////////////////////////\n  // $provider\n  ////////////////////////////////////\n\n  function supportObject(delegate) {\n    return function(key, value) {\n      if (isObject(key)) {\n        forEach(key, reverseParams(delegate));\n      } else {\n        return delegate(key, value);\n      }\n    };\n  }\n\n  function provider(name, provider_) {\n    assertNotHasOwnProperty(name, 'service');\n    if (isFunction(provider_) || isArray(provider_)) {\n      provider_ = providerInjector.instantiate(provider_);\n    }\n    if (!provider_.$get) {\n      throw $injectorMinErr('pget', 'Provider \\'{0}\\' must define $get factory method.', name);\n    }\n    return (providerCache[name + providerSuffix] = provider_);\n  }\n\n  function enforceReturnValue(name, factory) {\n    return /** @this */ function enforcedReturnValue() {\n      var result = instanceInjector.invoke(factory, this);\n      if (isUndefined(result)) {\n        throw $injectorMinErr('undef', 'Provider \\'{0}\\' must return a value from $get factory method.', name);\n      }\n      return result;\n    };\n  }\n\n  function factory(name, factoryFn, enforce) {\n    return provider(name, {\n      $get: enforce !== false ? enforceReturnValue(name, factoryFn) : factoryFn\n    });\n  }\n\n  function service(name, constructor) {\n    return factory(name, ['$injector', function($injector) {\n      return $injector.instantiate(constructor);\n    }]);\n  }\n\n  function value(name, val) { return factory(name, valueFn(val), false); }\n\n  function constant(name, value) {\n    assertNotHasOwnProperty(name, 'constant');\n    providerCache[name] = value;\n    instanceCache[name] = value;\n  }\n\n  function decorator(serviceName, decorFn) {\n    var origProvider = providerInjector.get(serviceName + providerSuffix),\n        orig$get = origProvider.$get;\n\n    origProvider.$get = function() {\n      var origInstance = instanceInjector.invoke(orig$get, origProvider);\n      return instanceInjector.invoke(decorFn, null, {$delegate: origInstance});\n    };\n  }\n\n  ////////////////////////////////////\n  // Module Loading\n  ////////////////////////////////////\n  function loadModules(modulesToLoad) {\n    assertArg(isUndefined(modulesToLoad) || isArray(modulesToLoad), 'modulesToLoad', 'not an array');\n    var runBlocks = [], moduleFn;\n    forEach(modulesToLoad, function(module) {\n      if (loadedModules.get(module)) return;\n      loadedModules.set(module, true);\n\n      function runInvokeQueue(queue) {\n        var i, ii;\n        for (i = 0, ii = queue.length; i < ii; i++) {\n          var invokeArgs = queue[i],\n              provider = providerInjector.get(invokeArgs[0]);\n\n          provider[invokeArgs[1]].apply(provider, invokeArgs[2]);\n        }\n      }\n\n      try {\n        if (isString(module)) {\n          moduleFn = angularModule(module);\n          instanceInjector.modules[module] = moduleFn;\n          runBlocks = runBlocks.concat(loadModules(moduleFn.requires)).concat(moduleFn._runBlocks);\n          runInvokeQueue(moduleFn._invokeQueue);\n          runInvokeQueue(moduleFn._configBlocks);\n        } else if (isFunction(module)) {\n            runBlocks.push(providerInjector.invoke(module));\n        } else if (isArray(module)) {\n            runBlocks.push(providerInjector.invoke(module));\n        } else {\n          assertArgFn(module, 'module');\n        }\n      } catch (e) {\n        if (isArray(module)) {\n          module = module[module.length - 1];\n        }\n        if (e.message && e.stack && e.stack.indexOf(e.message) === -1) {\n          // Safari & FF's stack traces don't contain error.message content\n          // unlike those of Chrome and IE\n          // So if stack doesn't contain message, we create a new string that contains both.\n          // Since error.stack is read-only in Safari, I'm overriding e and not e.stack here.\n          // eslint-disable-next-line no-ex-assign\n          e = e.message + '\\n' + e.stack;\n        }\n        throw $injectorMinErr('modulerr', 'Failed to instantiate module {0} due to:\\n{1}',\n                  module, e.stack || e.message || e);\n      }\n    });\n    return runBlocks;\n  }\n\n  ////////////////////////////////////\n  // internal Injector\n  ////////////////////////////////////\n\n  function createInternalInjector(cache, factory) {\n\n    function getService(serviceName, caller) {\n      if (cache.hasOwnProperty(serviceName)) {\n        if (cache[serviceName] === INSTANTIATING) {\n          throw $injectorMinErr('cdep', 'Circular dependency found: {0}',\n                    serviceName + ' <- ' + path.join(' <- '));\n        }\n        return cache[serviceName];\n      } else {\n        try {\n          path.unshift(serviceName);\n          cache[serviceName] = INSTANTIATING;\n          cache[serviceName] = factory(serviceName, caller);\n          return cache[serviceName];\n        } catch (err) {\n          if (cache[serviceName] === INSTANTIATING) {\n            delete cache[serviceName];\n          }\n          throw err;\n        } finally {\n          path.shift();\n        }\n      }\n    }\n\n\n    function injectionArgs(fn, locals, serviceName) {\n      var args = [],\n          $inject = createInjector.$$annotate(fn, strictDi, serviceName);\n\n      for (var i = 0, length = $inject.length; i < length; i++) {\n        var key = $inject[i];\n        if (typeof key !== 'string') {\n          throw $injectorMinErr('itkn',\n                  'Incorrect injection token! Expected service name as string, got {0}', key);\n        }\n        args.push(locals && locals.hasOwnProperty(key) ? locals[key] :\n                                                         getService(key, serviceName));\n      }\n      return args;\n    }\n\n    function isClass(func) {\n      // Support: IE 9-11 only\n      // IE 9-11 do not support classes and IE9 leaks with the code below.\n      if (msie || typeof func !== 'function') {\n        return false;\n      }\n      var result = func.$$ngIsClass;\n      if (!isBoolean(result)) {\n        result = func.$$ngIsClass = /^class\\b/.test(stringifyFn(func));\n      }\n      return result;\n    }\n\n    function invoke(fn, self, locals, serviceName) {\n      if (typeof locals === 'string') {\n        serviceName = locals;\n        locals = null;\n      }\n\n      var args = injectionArgs(fn, locals, serviceName);\n      if (isArray(fn)) {\n        fn = fn[fn.length - 1];\n      }\n\n      if (!isClass(fn)) {\n        // http://jsperf.com/angularjs-invoke-apply-vs-switch\n        // #5388\n        return fn.apply(self, args);\n      } else {\n        args.unshift(null);\n        return new (Function.prototype.bind.apply(fn, args))();\n      }\n    }\n\n\n    function instantiate(Type, locals, serviceName) {\n      // Check if Type is annotated and use just the given function at n-1 as parameter\n      // e.g. someModule.factory('greeter', ['$window', function(renamed$window) {}]);\n      var ctor = (isArray(Type) ? Type[Type.length - 1] : Type);\n      var args = injectionArgs(Type, locals, serviceName);\n      // Empty object at position 0 is ignored for invocation with `new`, but required.\n      args.unshift(null);\n      return new (Function.prototype.bind.apply(ctor, args))();\n    }\n\n\n    return {\n      invoke: invoke,\n      instantiate: instantiate,\n      get: getService,\n      annotate: createInjector.$$annotate,\n      has: function(name) {\n        return providerCache.hasOwnProperty(name + providerSuffix) || cache.hasOwnProperty(name);\n      }\n    };\n  }\n}\n\ncreateInjector.$$annotate = annotate;\n\n/**\n * @ngdoc provider\n * @name $anchorScrollProvider\n * @this\n *\n * @description\n * Use `$anchorScrollProvider` to disable automatic scrolling whenever\n * {@link ng.$location#hash $location.hash()} changes.\n */\nfunction $AnchorScrollProvider() {\n\n  var autoScrollingEnabled = true;\n\n  /**\n   * @ngdoc method\n   * @name $anchorScrollProvider#disableAutoScrolling\n   *\n   * @description\n   * By default, {@link ng.$anchorScroll $anchorScroll()} will automatically detect changes to\n   * {@link ng.$location#hash $location.hash()} and scroll to the element matching the new hash.<br />\n   * Use this method to disable automatic scrolling.\n   *\n   * If automatic scrolling is disabled, one must explicitly call\n   * {@link ng.$anchorScroll $anchorScroll()} in order to scroll to the element related to the\n   * current hash.\n   */\n  this.disableAutoScrolling = function() {\n    autoScrollingEnabled = false;\n  };\n\n  /**\n   * @ngdoc service\n   * @name $anchorScroll\n   * @kind function\n   * @requires $window\n   * @requires $location\n   * @requires $rootScope\n   *\n   * @description\n   * When called, it scrolls to the element related to the specified `hash` or (if omitted) to the\n   * current value of {@link ng.$location#hash $location.hash()}, according to the rules specified\n   * in the\n   * [HTML5 spec](http://www.w3.org/html/wg/drafts/html/master/browsers.html#an-indicated-part-of-the-document).\n   *\n   * It also watches the {@link ng.$location#hash $location.hash()} and automatically scrolls to\n   * match any anchor whenever it changes. This can be disabled by calling\n   * {@link ng.$anchorScrollProvider#disableAutoScrolling $anchorScrollProvider.disableAutoScrolling()}.\n   *\n   * Additionally, you can use its {@link ng.$anchorScroll#yOffset yOffset} property to specify a\n   * vertical scroll-offset (either fixed or dynamic).\n   *\n   * @param {string=} hash The hash specifying the element to scroll to. If omitted, the value of\n   *                       {@link ng.$location#hash $location.hash()} will be used.\n   *\n   * @property {(number|function|jqLite)} yOffset\n   * If set, specifies a vertical scroll-offset. This is often useful when there are fixed\n   * positioned elements at the top of the page, such as navbars, headers etc.\n   *\n   * `yOffset` can be specified in various ways:\n   * - **number**: A fixed number of pixels to be used as offset.<br /><br />\n   * - **function**: A getter function called everytime `$anchorScroll()` is executed. Must return\n   *   a number representing the offset (in pixels).<br /><br />\n   * - **jqLite**: A jqLite/jQuery element to be used for specifying the offset. The distance from\n   *   the top of the page to the element's bottom will be used as offset.<br />\n   *   **Note**: The element will be taken into account only as long as its `position` is set to\n   *   `fixed`. This option is useful, when dealing with responsive navbars/headers that adjust\n   *   their height and/or positioning according to the viewport's size.\n   *\n   * <br />\n   * <div class=\"alert alert-warning\">\n   * In order for `yOffset` to work properly, scrolling should take place on the document's root and\n   * not some child element.\n   * </div>\n   *\n   * @example\n     <example module=\"anchorScrollExample\" name=\"anchor-scroll\">\n       <file name=\"index.html\">\n         <div id=\"scrollArea\" ng-controller=\"ScrollController\">\n           <a ng-click=\"gotoBottom()\">Go to bottom</a>\n           <a id=\"bottom\"></a> You're at the bottom!\n         </div>\n       </file>\n       <file name=\"script.js\">\n         angular.module('anchorScrollExample', [])\n           .controller('ScrollController', ['$scope', '$location', '$anchorScroll',\n             function($scope, $location, $anchorScroll) {\n               $scope.gotoBottom = function() {\n                 // set the location.hash to the id of\n                 // the element you wish to scroll to.\n                 $location.hash('bottom');\n\n                 // call $anchorScroll()\n                 $anchorScroll();\n               };\n             }]);\n       </file>\n       <file name=\"style.css\">\n         #scrollArea {\n           height: 280px;\n           overflow: auto;\n         }\n\n         #bottom {\n           display: block;\n           margin-top: 2000px;\n         }\n       </file>\n     </example>\n   *\n   * <hr />\n   * The example below illustrates the use of a vertical scroll-offset (specified as a fixed value).\n   * See {@link ng.$anchorScroll#yOffset $anchorScroll.yOffset} for more details.\n   *\n   * @example\n     <example module=\"anchorScrollOffsetExample\" name=\"anchor-scroll-offset\">\n       <file name=\"index.html\">\n         <div class=\"fixed-header\" ng-controller=\"headerCtrl\">\n           <a href=\"\" ng-click=\"gotoAnchor(x)\" ng-repeat=\"x in [1,2,3,4,5]\">\n             Go to anchor {{x}}\n           </a>\n         </div>\n         <div id=\"anchor{{x}}\" class=\"anchor\" ng-repeat=\"x in [1,2,3,4,5]\">\n           Anchor {{x}} of 5\n         </div>\n       </file>\n       <file name=\"script.js\">\n         angular.module('anchorScrollOffsetExample', [])\n           .run(['$anchorScroll', function($anchorScroll) {\n             $anchorScroll.yOffset = 50;   // always scroll by 50 extra pixels\n           }])\n           .controller('headerCtrl', ['$anchorScroll', '$location', '$scope',\n             function($anchorScroll, $location, $scope) {\n               $scope.gotoAnchor = function(x) {\n                 var newHash = 'anchor' + x;\n                 if ($location.hash() !== newHash) {\n                   // set the $location.hash to `newHash` and\n                   // $anchorScroll will automatically scroll to it\n                   $location.hash('anchor' + x);\n                 } else {\n                   // call $anchorScroll() explicitly,\n                   // since $location.hash hasn't changed\n                   $anchorScroll();\n                 }\n               };\n             }\n           ]);\n       </file>\n       <file name=\"style.css\">\n         body {\n           padding-top: 50px;\n         }\n\n         .anchor {\n           border: 2px dashed DarkOrchid;\n           padding: 10px 10px 200px 10px;\n         }\n\n         .fixed-header {\n           background-color: rgba(0, 0, 0, 0.2);\n           height: 50px;\n           position: fixed;\n           top: 0; left: 0; right: 0;\n         }\n\n         .fixed-header > a {\n           display: inline-block;\n           margin: 5px 15px;\n         }\n       </file>\n     </example>\n   */\n  this.$get = ['$window', '$location', '$rootScope', function($window, $location, $rootScope) {\n    var document = $window.document;\n\n    // Helper function to get first anchor from a NodeList\n    // (using `Array#some()` instead of `angular#forEach()` since it's more performant\n    //  and working in all supported browsers.)\n    function getFirstAnchor(list) {\n      var result = null;\n      Array.prototype.some.call(list, function(element) {\n        if (nodeName_(element) === 'a') {\n          result = element;\n          return true;\n        }\n      });\n      return result;\n    }\n\n    function getYOffset() {\n\n      var offset = scroll.yOffset;\n\n      if (isFunction(offset)) {\n        offset = offset();\n      } else if (isElement(offset)) {\n        var elem = offset[0];\n        var style = $window.getComputedStyle(elem);\n        if (style.position !== 'fixed') {\n          offset = 0;\n        } else {\n          offset = elem.getBoundingClientRect().bottom;\n        }\n      } else if (!isNumber(offset)) {\n        offset = 0;\n      }\n\n      return offset;\n    }\n\n    function scrollTo(elem) {\n      if (elem) {\n        elem.scrollIntoView();\n\n        var offset = getYOffset();\n\n        if (offset) {\n          // `offset` is the number of pixels we should scroll UP in order to align `elem` properly.\n          // This is true ONLY if the call to `elem.scrollIntoView()` initially aligns `elem` at the\n          // top of the viewport.\n          //\n          // IF the number of pixels from the top of `elem` to the end of the page's content is less\n          // than the height of the viewport, then `elem.scrollIntoView()` will align the `elem` some\n          // way down the page.\n          //\n          // This is often the case for elements near the bottom of the page.\n          //\n          // In such cases we do not need to scroll the whole `offset` up, just the difference between\n          // the top of the element and the offset, which is enough to align the top of `elem` at the\n          // desired position.\n          var elemTop = elem.getBoundingClientRect().top;\n          $window.scrollBy(0, elemTop - offset);\n        }\n      } else {\n        $window.scrollTo(0, 0);\n      }\n    }\n\n    function scroll(hash) {\n      // Allow numeric hashes\n      hash = isString(hash) ? hash : isNumber(hash) ? hash.toString() : $location.hash();\n      var elm;\n\n      // empty hash, scroll to the top of the page\n      if (!hash) scrollTo(null);\n\n      // element with given id\n      else if ((elm = document.getElementById(hash))) scrollTo(elm);\n\n      // first anchor with given name :-D\n      else if ((elm = getFirstAnchor(document.getElementsByName(hash)))) scrollTo(elm);\n\n      // no element and hash === 'top', scroll to the top of the page\n      else if (hash === 'top') scrollTo(null);\n    }\n\n    // does not scroll when user clicks on anchor link that is currently on\n    // (no url change, no $location.hash() change), browser native does scroll\n    if (autoScrollingEnabled) {\n      $rootScope.$watch(function autoScrollWatch() {return $location.hash();},\n        function autoScrollWatchAction(newVal, oldVal) {\n          // skip the initial scroll if $location.hash is empty\n          if (newVal === oldVal && newVal === '') return;\n\n          jqLiteDocumentLoaded(function() {\n            $rootScope.$evalAsync(scroll);\n          });\n        });\n    }\n\n    return scroll;\n  }];\n}\n\nvar $animateMinErr = minErr('$animate');\nvar ELEMENT_NODE = 1;\nvar NG_ANIMATE_CLASSNAME = 'ng-animate';\n\nfunction mergeClasses(a,b) {\n  if (!a && !b) return '';\n  if (!a) return b;\n  if (!b) return a;\n  if (isArray(a)) a = a.join(' ');\n  if (isArray(b)) b = b.join(' ');\n  return a + ' ' + b;\n}\n\nfunction extractElementNode(element) {\n  for (var i = 0; i < element.length; i++) {\n    var elm = element[i];\n    if (elm.nodeType === ELEMENT_NODE) {\n      return elm;\n    }\n  }\n}\n\nfunction splitClasses(classes) {\n  if (isString(classes)) {\n    classes = classes.split(' ');\n  }\n\n  // Use createMap() to prevent class assumptions involving property names in\n  // Object.prototype\n  var obj = createMap();\n  forEach(classes, function(klass) {\n    // sometimes the split leaves empty string values\n    // incase extra spaces were applied to the options\n    if (klass.length) {\n      obj[klass] = true;\n    }\n  });\n  return obj;\n}\n\n// if any other type of options value besides an Object value is\n// passed into the $animate.method() animation then this helper code\n// will be run which will ignore it. While this patch is not the\n// greatest solution to this, a lot of existing plugins depend on\n// $animate to either call the callback (< 1.2) or return a promise\n// that can be changed. This helper function ensures that the options\n// are wiped clean incase a callback function is provided.\nfunction prepareAnimateOptions(options) {\n  return isObject(options)\n      ? options\n      : {};\n}\n\nvar $$CoreAnimateJsProvider = /** @this */ function() {\n  this.$get = noop;\n};\n\n// this is prefixed with Core since it conflicts with\n// the animateQueueProvider defined in ngAnimate/animateQueue.js\nvar $$CoreAnimateQueueProvider = /** @this */ function() {\n  var postDigestQueue = new NgMap();\n  var postDigestElements = [];\n\n  this.$get = ['$$AnimateRunner', '$rootScope',\n       function($$AnimateRunner,   $rootScope) {\n    return {\n      enabled: noop,\n      on: noop,\n      off: noop,\n      pin: noop,\n\n      push: function(element, event, options, domOperation) {\n        if (domOperation) {\n          domOperation();\n        }\n\n        options = options || {};\n        if (options.from) {\n          element.css(options.from);\n        }\n        if (options.to) {\n          element.css(options.to);\n        }\n\n        if (options.addClass || options.removeClass) {\n          addRemoveClassesPostDigest(element, options.addClass, options.removeClass);\n        }\n\n        var runner = new $$AnimateRunner();\n\n        // since there are no animations to run the runner needs to be\n        // notified that the animation call is complete.\n        runner.complete();\n        return runner;\n      }\n    };\n\n\n    function updateData(data, classes, value) {\n      var changed = false;\n      if (classes) {\n        classes = isString(classes) ? classes.split(' ') :\n                  isArray(classes) ? classes : [];\n        forEach(classes, function(className) {\n          if (className) {\n            changed = true;\n            data[className] = value;\n          }\n        });\n      }\n      return changed;\n    }\n\n    function handleCSSClassChanges() {\n      forEach(postDigestElements, function(element) {\n        var data = postDigestQueue.get(element);\n        if (data) {\n          var existing = splitClasses(element.attr('class'));\n          var toAdd = '';\n          var toRemove = '';\n          forEach(data, function(status, className) {\n            var hasClass = !!existing[className];\n            if (status !== hasClass) {\n              if (status) {\n                toAdd += (toAdd.length ? ' ' : '') + className;\n              } else {\n                toRemove += (toRemove.length ? ' ' : '') + className;\n              }\n            }\n          });\n\n          forEach(element, function(elm) {\n            if (toAdd) {\n              jqLiteAddClass(elm, toAdd);\n            }\n            if (toRemove) {\n              jqLiteRemoveClass(elm, toRemove);\n            }\n          });\n          postDigestQueue.delete(element);\n        }\n      });\n      postDigestElements.length = 0;\n    }\n\n\n    function addRemoveClassesPostDigest(element, add, remove) {\n      var data = postDigestQueue.get(element) || {};\n\n      var classesAdded = updateData(data, add, true);\n      var classesRemoved = updateData(data, remove, false);\n\n      if (classesAdded || classesRemoved) {\n\n        postDigestQueue.set(element, data);\n        postDigestElements.push(element);\n\n        if (postDigestElements.length === 1) {\n          $rootScope.$$postDigest(handleCSSClassChanges);\n        }\n      }\n    }\n  }];\n};\n\n/**\n * @ngdoc provider\n * @name $animateProvider\n *\n * @description\n * Default implementation of $animate that doesn't perform any animations, instead just\n * synchronously performs DOM updates and resolves the returned runner promise.\n *\n * In order to enable animations the `ngAnimate` module has to be loaded.\n *\n * To see the functional implementation check out `src/ngAnimate/animate.js`.\n */\nvar $AnimateProvider = ['$provide', /** @this */ function($provide) {\n  var provider = this;\n  var classNameFilter = null;\n  var customFilter = null;\n\n  this.$$registeredAnimations = Object.create(null);\n\n   /**\n   * @ngdoc method\n   * @name $animateProvider#register\n   *\n   * @description\n   * Registers a new injectable animation factory function. The factory function produces the\n   * animation object which contains callback functions for each event that is expected to be\n   * animated.\n   *\n   *   * `eventFn`: `function(element, ... , doneFunction, options)`\n   *   The element to animate, the `doneFunction` and the options fed into the animation. Depending\n   *   on the type of animation additional arguments will be injected into the animation function. The\n   *   list below explains the function signatures for the different animation methods:\n   *\n   *   - setClass: function(element, addedClasses, removedClasses, doneFunction, options)\n   *   - addClass: function(element, addedClasses, doneFunction, options)\n   *   - removeClass: function(element, removedClasses, doneFunction, options)\n   *   - enter, leave, move: function(element, doneFunction, options)\n   *   - animate: function(element, fromStyles, toStyles, doneFunction, options)\n   *\n   *   Make sure to trigger the `doneFunction` once the animation is fully complete.\n   *\n   * ```js\n   *   return {\n   *     //enter, leave, move signature\n   *     eventFn : function(element, done, options) {\n   *       //code to run the animation\n   *       //once complete, then run done()\n   *       return function endFunction(wasCancelled) {\n   *         //code to cancel the animation\n   *       }\n   *     }\n   *   }\n   * ```\n   *\n   * @param {string} name The name of the animation (this is what the class-based CSS value will be compared to).\n   * @param {Function} factory The factory function that will be executed to return the animation\n   *                           object.\n   */\n  this.register = function(name, factory) {\n    if (name && name.charAt(0) !== '.') {\n      throw $animateMinErr('notcsel', 'Expecting class selector starting with \\'.\\' got \\'{0}\\'.', name);\n    }\n\n    var key = name + '-animation';\n    provider.$$registeredAnimations[name.substr(1)] = key;\n    $provide.factory(key, factory);\n  };\n\n  /**\n   * @ngdoc method\n   * @name $animateProvider#customFilter\n   *\n   * @description\n   * Sets and/or returns the custom filter function that is used to \"filter\" animations, i.e.\n   * determine if an animation is allowed or not. When no filter is specified (the default), no\n   * animation will be blocked. Setting the `customFilter` value will only allow animations for\n   * which the filter function's return value is truthy.\n   *\n   * This allows to easily create arbitrarily complex rules for filtering animations, such as\n   * allowing specific events only, or enabling animations on specific subtrees of the DOM, etc.\n   * Filtering animations can also boost performance for low-powered devices, as well as\n   * applications containing a lot of structural operations.\n   *\n   * <div class=\"alert alert-success\">\n   *   **Best Practice:**\n   *   Keep the filtering function as lean as possible, because it will be called for each DOM\n   *   action (e.g. insertion, removal, class change) performed by \"animation-aware\" directives.\n   *   See {@link guide/animations#which-directives-support-animations- here} for a list of built-in\n   *   directives that support animations.\n   *   Performing computationally expensive or time-consuming operations on each call of the\n   *   filtering function can make your animations sluggish.\n   * </div>\n   *\n   * **Note:** If present, `customFilter` will be checked before\n   * {@link $animateProvider#classNameFilter classNameFilter}.\n   *\n   * @param {Function=} filterFn - The filter function which will be used to filter all animations.\n   *   If a falsy value is returned, no animation will be performed. The function will be called\n   *   with the following arguments:\n   *   - **node** `{DOMElement}` - The DOM element to be animated.\n   *   - **event** `{String}` - The name of the animation event (e.g. `enter`, `leave`, `addClass`\n   *     etc).\n   *   - **options** `{Object}` - A collection of options/styles used for the animation.\n   * @return {Function} The current filter function or `null` if there is none set.\n   */\n  this.customFilter = function(filterFn) {\n    if (arguments.length === 1) {\n      customFilter = isFunction(filterFn) ? filterFn : null;\n    }\n\n    return customFilter;\n  };\n\n  /**\n   * @ngdoc method\n   * @name $animateProvider#classNameFilter\n   *\n   * @description\n   * Sets and/or returns the CSS class regular expression that is checked when performing\n   * an animation. Upon bootstrap the classNameFilter value is not set at all and will\n   * therefore enable $animate to attempt to perform an animation on any element that is triggered.\n   * When setting the `classNameFilter` value, animations will only be performed on elements\n   * that successfully match the filter expression. This in turn can boost performance\n   * for low-powered devices as well as applications containing a lot of structural operations.\n   *\n   * **Note:** If present, `classNameFilter` will be checked after\n   * {@link $animateProvider#customFilter customFilter}. If `customFilter` is present and returns\n   * false, `classNameFilter` will not be checked.\n   *\n   * @param {RegExp=} expression The className expression which will be checked against all animations\n   * @return {RegExp} The current CSS className expression value. If null then there is no expression value\n   */\n  this.classNameFilter = function(expression) {\n    if (arguments.length === 1) {\n      classNameFilter = (expression instanceof RegExp) ? expression : null;\n      if (classNameFilter) {\n        var reservedRegex = new RegExp('[(\\\\s|\\\\/)]' + NG_ANIMATE_CLASSNAME + '[(\\\\s|\\\\/)]');\n        if (reservedRegex.test(classNameFilter.toString())) {\n          classNameFilter = null;\n          throw $animateMinErr('nongcls', '$animateProvider.classNameFilter(regex) prohibits accepting a regex value which matches/contains the \"{0}\" CSS class.', NG_ANIMATE_CLASSNAME);\n        }\n      }\n    }\n    return classNameFilter;\n  };\n\n  this.$get = ['$$animateQueue', function($$animateQueue) {\n    function domInsert(element, parentElement, afterElement) {\n      // if for some reason the previous element was removed\n      // from the dom sometime before this code runs then let's\n      // just stick to using the parent element as the anchor\n      if (afterElement) {\n        var afterNode = extractElementNode(afterElement);\n        if (afterNode && !afterNode.parentNode && !afterNode.previousElementSibling) {\n          afterElement = null;\n        }\n      }\n      if (afterElement) {\n        afterElement.after(element);\n      } else {\n        parentElement.prepend(element);\n      }\n    }\n\n    /**\n     * @ngdoc service\n     * @name $animate\n     * @description The $animate service exposes a series of DOM utility methods that provide support\n     * for animation hooks. The default behavior is the application of DOM operations, however,\n     * when an animation is detected (and animations are enabled), $animate will do the heavy lifting\n     * to ensure that animation runs with the triggered DOM operation.\n     *\n     * By default $animate doesn't trigger any animations. This is because the `ngAnimate` module isn't\n     * included and only when it is active then the animation hooks that `$animate` triggers will be\n     * functional. Once active then all structural `ng-` directives will trigger animations as they perform\n     * their DOM-related operations (enter, leave and move). Other directives such as `ngClass`,\n     * `ngShow`, `ngHide` and `ngMessages` also provide support for animations.\n     *\n     * It is recommended that the`$animate` service is always used when executing DOM-related procedures within directives.\n     *\n     * To learn more about enabling animation support, click here to visit the\n     * {@link ngAnimate ngAnimate module page}.\n     */\n    return {\n      // we don't call it directly since non-existant arguments may\n      // be interpreted as null within the sub enabled function\n\n      /**\n       *\n       * @ngdoc method\n       * @name $animate#on\n       * @kind function\n       * @description Sets up an event listener to fire whenever the animation event (enter, leave, move, etc...)\n       *    has fired on the given element or among any of its children. Once the listener is fired, the provided callback\n       *    is fired with the following params:\n       *\n       * ```js\n       * $animate.on('enter', container,\n       *    function callback(element, phase) {\n       *      // cool we detected an enter animation within the container\n       *    }\n       * );\n       * ```\n       *\n       * <div class=\"alert alert-warning\">\n       * **Note**: Generally, the events that are fired correspond 1:1 to `$animate` method names,\n       * e.g. {@link ng.$animate#addClass addClass()} will fire `addClass`, and {@link ng.ngClass}\n       * will fire `addClass` if classes are added, and `removeClass` if classes are removed.\n       * However, there are two exceptions:\n       *\n       * <ul>\n       *   <li>if both an {@link ng.$animate#addClass addClass()} and a\n       *   {@link ng.$animate#removeClass removeClass()} action are performed during the same\n       *   animation, the event fired will be `setClass`. This is true even for `ngClass`.</li>\n       *   <li>an {@link ng.$animate#animate animate()} call that adds and removes classes will fire\n       *   the `setClass` event, but if it either removes or adds classes,\n       *   it will fire `animate` instead.</li>\n       * </ul>\n       *\n       * </div>\n       *\n       * @param {string} event the animation event that will be captured (e.g. enter, leave, move, addClass, removeClass, etc...)\n       * @param {DOMElement} container the container element that will capture each of the animation events that are fired on itself\n       *     as well as among its children\n       * @param {Function} callback the callback function that will be fired when the listener is triggered.\n       *\n       * The arguments present in the callback function are:\n       * * `element` - The captured DOM element that the animation was fired on.\n       * * `phase` - The phase of the animation. The two possible phases are **start** (when the animation starts) and **close** (when it ends).\n       * * `data` - an object with these properties:\n       *     * addClass - `{string|null}` - space-separated CSS classes to add to the element\n       *     * removeClass - `{string|null}` - space-separated CSS classes to remove from the element\n       *     * from - `{Object|null}` - CSS properties & values at the beginning of the animation\n       *     * to - `{Object|null}` - CSS properties & values at the end of the animation\n       *\n       * Note that the callback does not trigger a scope digest. Wrap your call into a\n       * {@link $rootScope.Scope#$apply scope.$apply} to propagate changes to the scope.\n       */\n      on: $$animateQueue.on,\n\n      /**\n       *\n       * @ngdoc method\n       * @name $animate#off\n       * @kind function\n       * @description Deregisters an event listener based on the event which has been associated with the provided element. This method\n       * can be used in three different ways depending on the arguments:\n       *\n       * ```js\n       * // remove all the animation event listeners listening for `enter`\n       * $animate.off('enter');\n       *\n       * // remove listeners for all animation events from the container element\n       * $animate.off(container);\n       *\n       * // remove all the animation event listeners listening for `enter` on the given element and its children\n       * $animate.off('enter', container);\n       *\n       * // remove the event listener function provided by `callback` that is set\n       * // to listen for `enter` on the given `container` as well as its children\n       * $animate.off('enter', container, callback);\n       * ```\n       *\n       * @param {string|DOMElement} event|container the animation event (e.g. enter, leave, move,\n       * addClass, removeClass, etc...), or the container element. If it is the element, all other\n       * arguments are ignored.\n       * @param {DOMElement=} container the container element the event listener was placed on\n       * @param {Function=} callback the callback function that was registered as the listener\n       */\n      off: $$animateQueue.off,\n\n      /**\n       * @ngdoc method\n       * @name $animate#pin\n       * @kind function\n       * @description Associates the provided element with a host parent element to allow the element to be animated even if it exists\n       *    outside of the DOM structure of the AngularJS application. By doing so, any animation triggered via `$animate` can be issued on the\n       *    element despite being outside the realm of the application or within another application. Say for example if the application\n       *    was bootstrapped on an element that is somewhere inside of the `<body>` tag, but we wanted to allow for an element to be situated\n       *    as a direct child of `document.body`, then this can be achieved by pinning the element via `$animate.pin(element)`. Keep in mind\n       *    that calling `$animate.pin(element, parentElement)` will not actually insert into the DOM anywhere; it will just create the association.\n       *\n       *    Note that this feature is only active when the `ngAnimate` module is used.\n       *\n       * @param {DOMElement} element the external element that will be pinned\n       * @param {DOMElement} parentElement the host parent element that will be associated with the external element\n       */\n      pin: $$animateQueue.pin,\n\n      /**\n       *\n       * @ngdoc method\n       * @name $animate#enabled\n       * @kind function\n       * @description Used to get and set whether animations are enabled or not on the entire application or on an element and its children. This\n       * function can be called in four ways:\n       *\n       * ```js\n       * // returns true or false\n       * $animate.enabled();\n       *\n       * // changes the enabled state for all animations\n       * $animate.enabled(false);\n       * $animate.enabled(true);\n       *\n       * // returns true or false if animations are enabled for an element\n       * $animate.enabled(element);\n       *\n       * // changes the enabled state for an element and its children\n       * $animate.enabled(element, true);\n       * $animate.enabled(element, false);\n       * ```\n       *\n       * @param {DOMElement=} element the element that will be considered for checking/setting the enabled state\n       * @param {boolean=} enabled whether or not the animations will be enabled for the element\n       *\n       * @return {boolean} whether or not animations are enabled\n       */\n      enabled: $$animateQueue.enabled,\n\n      /**\n       * @ngdoc method\n       * @name $animate#cancel\n       * @kind function\n       * @description Cancels the provided animation and applies the end state of the animation.\n       * Note that this does not cancel the underlying operation, e.g. the setting of classes or\n       * adding the element to the DOM.\n       *\n       * @param {animationRunner} animationRunner An animation runner returned by an $animate function.\n       *\n       * @example\n        <example module=\"animationExample\" deps=\"angular-animate.js\" animations=\"true\" name=\"animate-cancel\">\n          <file name=\"app.js\">\n            angular.module('animationExample', ['ngAnimate']).component('cancelExample', {\n              templateUrl: 'template.html',\n              controller: function($element, $animate) {\n                this.runner = null;\n\n                this.addClass = function() {\n                  this.runner = $animate.addClass($element.find('div'), 'red');\n                  var ctrl = this;\n                  this.runner.finally(function() {\n                    ctrl.runner = null;\n                  });\n                };\n\n                this.removeClass = function() {\n                  this.runner = $animate.removeClass($element.find('div'), 'red');\n                  var ctrl = this;\n                  this.runner.finally(function() {\n                    ctrl.runner = null;\n                  });\n                };\n\n                this.cancel = function() {\n                  $animate.cancel(this.runner);\n                };\n              }\n            });\n          </file>\n          <file name=\"template.html\">\n            <p>\n              <button id=\"add\" ng-click=\"$ctrl.addClass()\">Add</button>\n              <button ng-click=\"$ctrl.removeClass()\">Remove</button>\n              <br>\n              <button id=\"cancel\" ng-click=\"$ctrl.cancel()\" ng-disabled=\"!$ctrl.runner\">Cancel</button>\n              <br>\n              <div id=\"target\">CSS-Animated Text</div>\n            </p>\n          </file>\n          <file name=\"index.html\">\n            <cancel-example></cancel-example>\n          </file>\n          <file name=\"style.css\">\n            .red-add, .red-remove {\n              transition: all 4s cubic-bezier(0.250, 0.460, 0.450, 0.940);\n            }\n\n            .red,\n            .red-add.red-add-active {\n              color: #FF0000;\n              font-size: 40px;\n            }\n\n            .red-remove.red-remove-active {\n              font-size: 10px;\n              color: black;\n            }\n\n          </file>\n        </example>\n       */\n      cancel: function(runner) {\n        if (runner.cancel) {\n          runner.cancel();\n        }\n      },\n\n      /**\n       *\n       * @ngdoc method\n       * @name $animate#enter\n       * @kind function\n       * @description Inserts the element into the DOM either after the `after` element (if provided) or\n       *   as the first child within the `parent` element and then triggers an animation.\n       *   A promise is returned that will be resolved during the next digest once the animation\n       *   has completed.\n       *\n       * @param {DOMElement} element the element which will be inserted into the DOM\n       * @param {DOMElement} parent the parent element which will append the element as\n       *   a child (so long as the after element is not present)\n       * @param {DOMElement=} after the sibling element after which the element will be appended\n       * @param {object=} options an optional collection of options/styles that will be applied to the element.\n       *   The object can have the following properties:\n       *\n       *   - **addClass** - `{string}` - space-separated CSS classes to add to element\n       *   - **from** - `{Object}` - CSS properties & values at the beginning of animation. Must have matching `to`\n       *   - **removeClass** - `{string}` - space-separated CSS classes to remove from element\n       *   - **to** - `{Object}` - CSS properties & values at end of animation. Must have matching `from`\n       *\n       * @return {Runner} the animation runner\n       */\n      enter: function(element, parent, after, options) {\n        parent = parent && jqLite(parent);\n        after = after && jqLite(after);\n        parent = parent || after.parent();\n        domInsert(element, parent, after);\n        return $$animateQueue.push(element, 'enter', prepareAnimateOptions(options));\n      },\n\n      /**\n       *\n       * @ngdoc method\n       * @name $animate#move\n       * @kind function\n       * @description Inserts (moves) the element into its new position in the DOM either after\n       *   the `after` element (if provided) or as the first child within the `parent` element\n       *   and then triggers an animation. A promise is returned that will be resolved\n       *   during the next digest once the animation has completed.\n       *\n       * @param {DOMElement} element the element which will be moved into the new DOM position\n       * @param {DOMElement} parent the parent element which will append the element as\n       *   a child (so long as the after element is not present)\n       * @param {DOMElement=} after the sibling element after which the element will be appended\n       * @param {object=} options an optional collection of options/styles that will be applied to the element.\n       *   The object can have the following properties:\n       *\n       *   - **addClass** - `{string}` - space-separated CSS classes to add to element\n       *   - **from** - `{Object}` - CSS properties & values at the beginning of animation. Must have matching `to`\n       *   - **removeClass** - `{string}` - space-separated CSS classes to remove from element\n       *   - **to** - `{Object}` - CSS properties & values at end of animation. Must have matching `from`\n       *\n       * @return {Runner} the animation runner\n       */\n      move: function(element, parent, after, options) {\n        parent = parent && jqLite(parent);\n        after = after && jqLite(after);\n        parent = parent || after.parent();\n        domInsert(element, parent, after);\n        return $$animateQueue.push(element, 'move', prepareAnimateOptions(options));\n      },\n\n      /**\n       * @ngdoc method\n       * @name $animate#leave\n       * @kind function\n       * @description Triggers an animation and then removes the element from the DOM.\n       * When the function is called a promise is returned that will be resolved during the next\n       * digest once the animation has completed.\n       *\n       * @param {DOMElement} element the element which will be removed from the DOM\n       * @param {object=} options an optional collection of options/styles that will be applied to the element.\n       *   The object can have the following properties:\n       *\n       *   - **addClass** - `{string}` - space-separated CSS classes to add to element\n       *   - **from** - `{Object}` - CSS properties & values at the beginning of animation. Must have matching `to`\n       *   - **removeClass** - `{string}` - space-separated CSS classes to remove from element\n       *   - **to** - `{Object}` - CSS properties & values at end of animation. Must have matching `from`\n       *\n       * @return {Runner} the animation runner\n       */\n      leave: function(element, options) {\n        return $$animateQueue.push(element, 'leave', prepareAnimateOptions(options), function() {\n          element.remove();\n        });\n      },\n\n      /**\n       * @ngdoc method\n       * @name $animate#addClass\n       * @kind function\n       *\n       * @description Triggers an addClass animation surrounding the addition of the provided CSS class(es). Upon\n       *   execution, the addClass operation will only be handled after the next digest and it will not trigger an\n       *   animation if element already contains the CSS class or if the class is removed at a later step.\n       *   Note that class-based animations are treated differently compared to structural animations\n       *   (like enter, move and leave) since the CSS classes may be added/removed at different points\n       *   depending if CSS or JavaScript animations are used.\n       *\n       * @param {DOMElement} element the element which the CSS classes will be applied to\n       * @param {string} className the CSS class(es) that will be added (multiple classes are separated via spaces)\n       * @param {object=} options an optional collection of options/styles that will be applied to the element.\n       *   The object can have the following properties:\n       *\n       *   - **removeClass** - `{string}` - space-separated CSS classes to remove from element\n       *   - **from** - `{Object}` - CSS properties & values at the beginning of animation. Must have matching `to`\n       *   - **to** - `{Object}` - CSS properties & values at end of animation. Must have matching `from`\n       *\n       * @return {Runner} animationRunner the animation runner\n       */\n      addClass: function(element, className, options) {\n        options = prepareAnimateOptions(options);\n        options.addClass = mergeClasses(options.addclass, className);\n        return $$animateQueue.push(element, 'addClass', options);\n      },\n\n      /**\n       * @ngdoc method\n       * @name $animate#removeClass\n       * @kind function\n       *\n       * @description Triggers a removeClass animation surrounding the removal of the provided CSS class(es). Upon\n       *   execution, the removeClass operation will only be handled after the next digest and it will not trigger an\n       *   animation if element does not contain the CSS class or if the class is added at a later step.\n       *   Note that class-based animations are treated differently compared to structural animations\n       *   (like enter, move and leave) since the CSS classes may be added/removed at different points\n       *   depending if CSS or JavaScript animations are used.\n       *\n       * @param {DOMElement} element the element which the CSS classes will be applied to\n       * @param {string} className the CSS class(es) that will be removed (multiple classes are separated via spaces)\n       * @param {object=} options an optional collection of options/styles that will be applied to the element.\n       *   The object can have the following properties:\n       *\n       *   - **addClass** - `{string}` - space-separated CSS classes to add to element\n       *   - **from** - `{Object}` - CSS properties & values at the beginning of animation. Must have matching `to`\n       *   - **to** - `{Object}` - CSS properties & values at end of animation. Must have matching `from`\n       *\n       * @return {Runner} the animation runner\n       */\n      removeClass: function(element, className, options) {\n        options = prepareAnimateOptions(options);\n        options.removeClass = mergeClasses(options.removeClass, className);\n        return $$animateQueue.push(element, 'removeClass', options);\n      },\n\n      /**\n       * @ngdoc method\n       * @name $animate#setClass\n       * @kind function\n       *\n       * @description Performs both the addition and removal of a CSS classes on an element and (during the process)\n       *    triggers an animation surrounding the class addition/removal. Much like `$animate.addClass` and\n       *    `$animate.removeClass`, `setClass` will only evaluate the classes being added/removed once a digest has\n       *    passed. Note that class-based animations are treated differently compared to structural animations\n       *    (like enter, move and leave) since the CSS classes may be added/removed at different points\n       *    depending if CSS or JavaScript animations are used.\n       *\n       * @param {DOMElement} element the element which the CSS classes will be applied to\n       * @param {string} add the CSS class(es) that will be added (multiple classes are separated via spaces)\n       * @param {string} remove the CSS class(es) that will be removed (multiple classes are separated via spaces)\n       * @param {object=} options an optional collection of options/styles that will be applied to the element.\n       *   The object can have the following properties:\n       *\n       *   - **addClass** - `{string}` - space-separated CSS classes to add to element\n       *   - **removeClass** - `{string}` - space-separated CSS classes to remove from element\n       *   - **from** - `{Object}` - CSS properties & values at the beginning of animation. Must have matching `to`\n       *   - **to** - `{Object}` - CSS properties & values at end of animation. Must have matching `from`\n       *\n       * @return {Runner} the animation runner\n       */\n      setClass: function(element, add, remove, options) {\n        options = prepareAnimateOptions(options);\n        options.addClass = mergeClasses(options.addClass, add);\n        options.removeClass = mergeClasses(options.removeClass, remove);\n        return $$animateQueue.push(element, 'setClass', options);\n      },\n\n      /**\n       * @ngdoc method\n       * @name $animate#animate\n       * @kind function\n       *\n       * @description Performs an inline animation on the element which applies the provided to and from CSS styles to the element.\n       * If any detected CSS transition, keyframe or JavaScript matches the provided className value, then the animation will take\n       * on the provided styles. For example, if a transition animation is set for the given className, then the provided `from` and\n       * `to` styles will be applied alongside the given transition. If the CSS style provided in `from` does not have a corresponding\n       * style in `to`, the style in `from` is applied immediately, and no animation is run.\n       * If a JavaScript animation is detected then the provided styles will be given in as function parameters into the `animate`\n       * method (or as part of the `options` parameter):\n       *\n       * ```js\n       * ngModule.animation('.my-inline-animation', function() {\n       *   return {\n       *     animate : function(element, from, to, done, options) {\n       *       //animation\n       *       done();\n       *     }\n       *   }\n       * });\n       * ```\n       *\n       * @param {DOMElement} element the element which the CSS styles will be applied to\n       * @param {object} from the from (starting) CSS styles that will be applied to the element and across the animation.\n       * @param {object} to the to (destination) CSS styles that will be applied to the element and across the animation.\n       * @param {string=} className an optional CSS class that will be applied to the element for the duration of the animation. If\n       *    this value is left as empty then a CSS class of `ng-inline-animate` will be applied to the element.\n       *    (Note that if no animation is detected then this value will not be applied to the element.)\n       * @param {object=} options an optional collection of options/styles that will be applied to the element.\n       *   The object can have the following properties:\n       *\n       *   - **addClass** - `{string}` - space-separated CSS classes to add to element\n       *   - **from** - `{Object}` - CSS properties & values at the beginning of animation. Must have matching `to`\n       *   - **removeClass** - `{string}` - space-separated CSS classes to remove from element\n       *   - **to** - `{Object}` - CSS properties & values at end of animation. Must have matching `from`\n       *\n       * @return {Runner} the animation runner\n       */\n      animate: function(element, from, to, className, options) {\n        options = prepareAnimateOptions(options);\n        options.from = options.from ? extend(options.from, from) : from;\n        options.to   = options.to   ? extend(options.to, to)     : to;\n\n        className = className || 'ng-inline-animate';\n        options.tempClasses = mergeClasses(options.tempClasses, className);\n        return $$animateQueue.push(element, 'animate', options);\n      }\n    };\n  }];\n}];\n\nvar $$AnimateAsyncRunFactoryProvider = /** @this */ function() {\n  this.$get = ['$$rAF', function($$rAF) {\n    var waitQueue = [];\n\n    function waitForTick(fn) {\n      waitQueue.push(fn);\n      if (waitQueue.length > 1) return;\n      $$rAF(function() {\n        for (var i = 0; i < waitQueue.length; i++) {\n          waitQueue[i]();\n        }\n        waitQueue = [];\n      });\n    }\n\n    return function() {\n      var passed = false;\n      waitForTick(function() {\n        passed = true;\n      });\n      return function(callback) {\n        if (passed) {\n          callback();\n        } else {\n          waitForTick(callback);\n        }\n      };\n    };\n  }];\n};\n\nvar $$AnimateRunnerFactoryProvider = /** @this */ function() {\n  this.$get = ['$q', '$sniffer', '$$animateAsyncRun', '$$isDocumentHidden', '$timeout',\n       function($q,   $sniffer,   $$animateAsyncRun,   $$isDocumentHidden,   $timeout) {\n\n    var INITIAL_STATE = 0;\n    var DONE_PENDING_STATE = 1;\n    var DONE_COMPLETE_STATE = 2;\n\n    AnimateRunner.chain = function(chain, callback) {\n      var index = 0;\n\n      next();\n      function next() {\n        if (index === chain.length) {\n          callback(true);\n          return;\n        }\n\n        chain[index](function(response) {\n          if (response === false) {\n            callback(false);\n            return;\n          }\n          index++;\n          next();\n        });\n      }\n    };\n\n    AnimateRunner.all = function(runners, callback) {\n      var count = 0;\n      var status = true;\n      forEach(runners, function(runner) {\n        runner.done(onProgress);\n      });\n\n      function onProgress(response) {\n        status = status && response;\n        if (++count === runners.length) {\n          callback(status);\n        }\n      }\n    };\n\n    function AnimateRunner(host) {\n      this.setHost(host);\n\n      var rafTick = $$animateAsyncRun();\n      var timeoutTick = function(fn) {\n        $timeout(fn, 0, false);\n      };\n\n      this._doneCallbacks = [];\n      this._tick = function(fn) {\n        if ($$isDocumentHidden()) {\n          timeoutTick(fn);\n        } else {\n          rafTick(fn);\n        }\n      };\n      this._state = 0;\n    }\n\n    AnimateRunner.prototype = {\n      setHost: function(host) {\n        this.host = host || {};\n      },\n\n      done: function(fn) {\n        if (this._state === DONE_COMPLETE_STATE) {\n          fn();\n        } else {\n          this._doneCallbacks.push(fn);\n        }\n      },\n\n      progress: noop,\n\n      getPromise: function() {\n        if (!this.promise) {\n          var self = this;\n          this.promise = $q(function(resolve, reject) {\n            self.done(function(status) {\n              if (status === false) {\n                reject();\n              } else {\n                resolve();\n              }\n            });\n          });\n        }\n        return this.promise;\n      },\n\n      then: function(resolveHandler, rejectHandler) {\n        return this.getPromise().then(resolveHandler, rejectHandler);\n      },\n\n      'catch': function(handler) {\n        return this.getPromise()['catch'](handler);\n      },\n\n      'finally': function(handler) {\n        return this.getPromise()['finally'](handler);\n      },\n\n      pause: function() {\n        if (this.host.pause) {\n          this.host.pause();\n        }\n      },\n\n      resume: function() {\n        if (this.host.resume) {\n          this.host.resume();\n        }\n      },\n\n      end: function() {\n        if (this.host.end) {\n          this.host.end();\n        }\n        this._resolve(true);\n      },\n\n      cancel: function() {\n        if (this.host.cancel) {\n          this.host.cancel();\n        }\n        this._resolve(false);\n      },\n\n      complete: function(response) {\n        var self = this;\n        if (self._state === INITIAL_STATE) {\n          self._state = DONE_PENDING_STATE;\n          self._tick(function() {\n            self._resolve(response);\n          });\n        }\n      },\n\n      _resolve: function(response) {\n        if (this._state !== DONE_COMPLETE_STATE) {\n          forEach(this._doneCallbacks, function(fn) {\n            fn(response);\n          });\n          this._doneCallbacks.length = 0;\n          this._state = DONE_COMPLETE_STATE;\n        }\n      }\n    };\n\n    return AnimateRunner;\n  }];\n};\n\n/* exported $CoreAnimateCssProvider */\n\n/**\n * @ngdoc service\n * @name $animateCss\n * @kind object\n * @this\n *\n * @description\n * This is the core version of `$animateCss`. By default, only when the `ngAnimate` is included,\n * then the `$animateCss` service will actually perform animations.\n *\n * Click here {@link ngAnimate.$animateCss to read the documentation for $animateCss}.\n */\nvar $CoreAnimateCssProvider = function() {\n  this.$get = ['$$rAF', '$q', '$$AnimateRunner', function($$rAF, $q, $$AnimateRunner) {\n\n    return function(element, initialOptions) {\n      // all of the animation functions should create\n      // a copy of the options data, however, if a\n      // parent service has already created a copy then\n      // we should stick to using that\n      var options = initialOptions || {};\n      if (!options.$$prepared) {\n        options = copy(options);\n      }\n\n      // there is no point in applying the styles since\n      // there is no animation that goes on at all in\n      // this version of $animateCss.\n      if (options.cleanupStyles) {\n        options.from = options.to = null;\n      }\n\n      if (options.from) {\n        element.css(options.from);\n        options.from = null;\n      }\n\n      var closed, runner = new $$AnimateRunner();\n      return {\n        start: run,\n        end: run\n      };\n\n      function run() {\n        $$rAF(function() {\n          applyAnimationContents();\n          if (!closed) {\n            runner.complete();\n          }\n          closed = true;\n        });\n        return runner;\n      }\n\n      function applyAnimationContents() {\n        if (options.addClass) {\n          element.addClass(options.addClass);\n          options.addClass = null;\n        }\n        if (options.removeClass) {\n          element.removeClass(options.removeClass);\n          options.removeClass = null;\n        }\n        if (options.to) {\n          element.css(options.to);\n          options.to = null;\n        }\n      }\n    };\n  }];\n};\n\n/* global getHash: true, stripHash: false */\n\nfunction getHash(url) {\n  var index = url.indexOf('#');\n  return index === -1 ? '' : url.substr(index);\n}\n\nfunction trimEmptyHash(url) {\n  return url.replace(/#$/, '');\n}\n\n/**\n * ! This is a private undocumented service !\n *\n * @name $browser\n * @requires $log\n * @description\n * This object has two goals:\n *\n * - hide all the global state in the browser caused by the window object\n * - abstract away all the browser specific features and inconsistencies\n *\n * For tests we provide {@link ngMock.$browser mock implementation} of the `$browser`\n * service, which can be used for convenient testing of the application without the interaction with\n * the real browser apis.\n */\n/**\n * @param {object} window The global window object.\n * @param {object} document jQuery wrapped document.\n * @param {object} $log window.console or an object with the same interface.\n * @param {object} $sniffer $sniffer service\n */\nfunction Browser(window, document, $log, $sniffer, $$taskTrackerFactory) {\n  var self = this,\n      location = window.location,\n      history = window.history,\n      setTimeout = window.setTimeout,\n      clearTimeout = window.clearTimeout,\n      pendingDeferIds = {},\n      taskTracker = $$taskTrackerFactory($log);\n\n  self.isMock = false;\n\n  //////////////////////////////////////////////////////////////\n  // Task-tracking API\n  //////////////////////////////////////////////////////////////\n\n  // TODO(vojta): remove this temporary api\n  self.$$completeOutstandingRequest = taskTracker.completeTask;\n  self.$$incOutstandingRequestCount = taskTracker.incTaskCount;\n\n  // TODO(vojta): prefix this method with $$ ?\n  self.notifyWhenNoOutstandingRequests = taskTracker.notifyWhenNoPendingTasks;\n\n  //////////////////////////////////////////////////////////////\n  // URL API\n  //////////////////////////////////////////////////////////////\n\n  var cachedState, lastHistoryState,\n      lastBrowserUrl = location.href,\n      baseElement = document.find('base'),\n      pendingLocation = null,\n      getCurrentState = !$sniffer.history ? noop : function getCurrentState() {\n        try {\n          return history.state;\n        } catch (e) {\n          // MSIE can reportedly throw when there is no state (UNCONFIRMED).\n        }\n      };\n\n  cacheState();\n\n  /**\n   * @name $browser#url\n   *\n   * @description\n   * GETTER:\n   * Without any argument, this method just returns current value of `location.href` (with a\n   * trailing `#` stripped of if the hash is empty).\n   *\n   * SETTER:\n   * With at least one argument, this method sets url to new value.\n   * If html5 history api supported, `pushState`/`replaceState` is used, otherwise\n   * `location.href`/`location.replace` is used.\n   * Returns its own instance to allow chaining.\n   *\n   * NOTE: this api is intended for use only by the `$location` service. Please use the\n   * {@link ng.$location $location service} to change url.\n   *\n   * @param {string} url New url (when used as setter)\n   * @param {boolean=} replace Should new url replace current history record?\n   * @param {object=} state State object to use with `pushState`/`replaceState`\n   */\n  self.url = function(url, replace, state) {\n    // In modern browsers `history.state` is `null` by default; treating it separately\n    // from `undefined` would cause `$browser.url('/foo')` to change `history.state`\n    // to undefined via `pushState`. Instead, let's change `undefined` to `null` here.\n    if (isUndefined(state)) {\n      state = null;\n    }\n\n    // Android Browser BFCache causes location, history reference to become stale.\n    if (location !== window.location) location = window.location;\n    if (history !== window.history) history = window.history;\n\n    // setter\n    if (url) {\n      var sameState = lastHistoryState === state;\n\n      // Normalize the inputted URL\n      url = urlResolve(url).href;\n\n      // Don't change anything if previous and current URLs and states match. This also prevents\n      // IE<10 from getting into redirect loop when in LocationHashbangInHtml5Url mode.\n      // See https://github.com/angular/angular.js/commit/ffb2701\n      if (lastBrowserUrl === url && (!$sniffer.history || sameState)) {\n        return self;\n      }\n      var sameBase = lastBrowserUrl && stripHash(lastBrowserUrl) === stripHash(url);\n      lastBrowserUrl = url;\n      lastHistoryState = state;\n      // Don't use history API if only the hash changed\n      // due to a bug in IE10/IE11 which leads\n      // to not firing a `hashchange` nor `popstate` event\n      // in some cases (see #9143).\n      if ($sniffer.history && (!sameBase || !sameState)) {\n        history[replace ? 'replaceState' : 'pushState'](state, '', url);\n        cacheState();\n      } else {\n        if (!sameBase) {\n          pendingLocation = url;\n        }\n        if (replace) {\n          location.replace(url);\n        } else if (!sameBase) {\n          location.href = url;\n        } else {\n          location.hash = getHash(url);\n        }\n        if (location.href !== url) {\n          pendingLocation = url;\n        }\n      }\n      if (pendingLocation) {\n        pendingLocation = url;\n      }\n      return self;\n    // getter\n    } else {\n      // - pendingLocation is needed as browsers don't allow to read out\n      //   the new location.href if a reload happened or if there is a bug like in iOS 9 (see\n      //   https://openradar.appspot.com/22186109).\n      return trimEmptyHash(pendingLocation || location.href);\n    }\n  };\n\n  /**\n   * @name $browser#state\n   *\n   * @description\n   * This method is a getter.\n   *\n   * Return history.state or null if history.state is undefined.\n   *\n   * @returns {object} state\n   */\n  self.state = function() {\n    return cachedState;\n  };\n\n  var urlChangeListeners = [],\n      urlChangeInit = false;\n\n  function cacheStateAndFireUrlChange() {\n    pendingLocation = null;\n    fireStateOrUrlChange();\n  }\n\n  // This variable should be used *only* inside the cacheState function.\n  var lastCachedState = null;\n  function cacheState() {\n    // This should be the only place in $browser where `history.state` is read.\n    cachedState = getCurrentState();\n    cachedState = isUndefined(cachedState) ? null : cachedState;\n\n    // Prevent callbacks fo fire twice if both hashchange & popstate were fired.\n    if (equals(cachedState, lastCachedState)) {\n      cachedState = lastCachedState;\n    }\n\n    lastCachedState = cachedState;\n    lastHistoryState = cachedState;\n  }\n\n  function fireStateOrUrlChange() {\n    var prevLastHistoryState = lastHistoryState;\n    cacheState();\n\n    if (lastBrowserUrl === self.url() && prevLastHistoryState === cachedState) {\n      return;\n    }\n\n    lastBrowserUrl = self.url();\n    lastHistoryState = cachedState;\n    forEach(urlChangeListeners, function(listener) {\n      listener(self.url(), cachedState);\n    });\n  }\n\n  /**\n   * @name $browser#onUrlChange\n   *\n   * @description\n   * Register callback function that will be called, when url changes.\n   *\n   * It's only called when the url is changed from outside of AngularJS:\n   * - user types different url into address bar\n   * - user clicks on history (forward/back) button\n   * - user clicks on a link\n   *\n   * It's not called when url is changed by $browser.url() method\n   *\n   * The listener gets called with new url as parameter.\n   *\n   * NOTE: this api is intended for use only by the $location service. Please use the\n   * {@link ng.$location $location service} to monitor url changes in AngularJS apps.\n   *\n   * @param {function(string)} listener Listener function to be called when url changes.\n   * @return {function(string)} Returns the registered listener fn - handy if the fn is anonymous.\n   */\n  self.onUrlChange = function(callback) {\n    // TODO(vojta): refactor to use node's syntax for events\n    if (!urlChangeInit) {\n      // We listen on both (hashchange/popstate) when available, as some browsers don't\n      // fire popstate when user changes the address bar and don't fire hashchange when url\n      // changed by push/replaceState\n\n      // html5 history api - popstate event\n      if ($sniffer.history) jqLite(window).on('popstate', cacheStateAndFireUrlChange);\n      // hashchange event\n      jqLite(window).on('hashchange', cacheStateAndFireUrlChange);\n\n      urlChangeInit = true;\n    }\n\n    urlChangeListeners.push(callback);\n    return callback;\n  };\n\n  /**\n   * @private\n   * Remove popstate and hashchange handler from window.\n   *\n   * NOTE: this api is intended for use only by $rootScope.\n   */\n  self.$$applicationDestroyed = function() {\n    jqLite(window).off('hashchange popstate', cacheStateAndFireUrlChange);\n  };\n\n  /**\n   * Checks whether the url has changed outside of AngularJS.\n   * Needs to be exported to be able to check for changes that have been done in sync,\n   * as hashchange/popstate events fire in async.\n   */\n  self.$$checkUrlChange = fireStateOrUrlChange;\n\n  //////////////////////////////////////////////////////////////\n  // Misc API\n  //////////////////////////////////////////////////////////////\n\n  /**\n   * @name $browser#baseHref\n   *\n   * @description\n   * Returns current <base href>\n   * (always relative - without domain)\n   *\n   * @returns {string} The current base href\n   */\n  self.baseHref = function() {\n    var href = baseElement.attr('href');\n    return href ? href.replace(/^(https?:)?\\/\\/[^/]*/, '') : '';\n  };\n\n  /**\n   * @name $browser#defer\n   * @param {function()} fn A function, who's execution should be deferred.\n   * @param {number=} [delay=0] Number of milliseconds to defer the function execution.\n   * @param {string=} [taskType=DEFAULT_TASK_TYPE] The type of task that is deferred.\n   * @returns {*} DeferId that can be used to cancel the task via `$browser.defer.cancel()`.\n   *\n   * @description\n   * Executes a fn asynchronously via `setTimeout(fn, delay)`.\n   *\n   * Unlike when calling `setTimeout` directly, in test this function is mocked and instead of using\n   * `setTimeout` in tests, the fns are queued in an array, which can be programmatically flushed\n   * via `$browser.defer.flush()`.\n   *\n   */\n  self.defer = function(fn, delay, taskType) {\n    var timeoutId;\n\n    delay = delay || 0;\n    taskType = taskType || taskTracker.DEFAULT_TASK_TYPE;\n\n    taskTracker.incTaskCount(taskType);\n    timeoutId = setTimeout(function() {\n      delete pendingDeferIds[timeoutId];\n      taskTracker.completeTask(fn, taskType);\n    }, delay);\n    pendingDeferIds[timeoutId] = taskType;\n\n    return timeoutId;\n  };\n\n\n  /**\n   * @name $browser#defer.cancel\n   *\n   * @description\n   * Cancels a deferred task identified with `deferId`.\n   *\n   * @param {*} deferId Token returned by the `$browser.defer` function.\n   * @returns {boolean} Returns `true` if the task hasn't executed yet and was successfully\n   *                    canceled.\n   */\n  self.defer.cancel = function(deferId) {\n    if (pendingDeferIds.hasOwnProperty(deferId)) {\n      var taskType = pendingDeferIds[deferId];\n      delete pendingDeferIds[deferId];\n      clearTimeout(deferId);\n      taskTracker.completeTask(noop, taskType);\n      return true;\n    }\n    return false;\n  };\n\n}\n\n/** @this */\nfunction $BrowserProvider() {\n  this.$get = ['$window', '$log', '$sniffer', '$document', '$$taskTrackerFactory',\n       function($window,   $log,   $sniffer,   $document,   $$taskTrackerFactory) {\n    return new Browser($window, $document, $log, $sniffer, $$taskTrackerFactory);\n  }];\n}\n\n/**\n * @ngdoc service\n * @name $cacheFactory\n * @this\n *\n * @description\n * Factory that constructs {@link $cacheFactory.Cache Cache} objects and gives access to\n * them.\n *\n * ```js\n *\n *  var cache = $cacheFactory('cacheId');\n *  expect($cacheFactory.get('cacheId')).toBe(cache);\n *  expect($cacheFactory.get('noSuchCacheId')).not.toBeDefined();\n *\n *  cache.put(\"key\", \"value\");\n *  cache.put(\"another key\", \"another value\");\n *\n *  // We've specified no options on creation\n *  expect(cache.info()).toEqual({id: 'cacheId', size: 2});\n *\n * ```\n *\n *\n * @param {string} cacheId Name or id of the newly created cache.\n * @param {object=} options Options object that specifies the cache behavior. Properties:\n *\n *   - `{number=}` `capacity` — turns the cache into LRU cache.\n *\n * @returns {object} Newly created cache object with the following set of methods:\n *\n * - `{object}` `info()` — Returns id, size, and options of cache.\n * - `{{*}}` `put({string} key, {*} value)` — Puts a new key-value pair into the cache and returns\n *   it.\n * - `{{*}}` `get({string} key)` — Returns cached value for `key` or undefined for cache miss.\n * - `{void}` `remove({string} key)` — Removes a key-value pair from the cache.\n * - `{void}` `removeAll()` — Removes all cached values.\n * - `{void}` `destroy()` — Removes references to this cache from $cacheFactory.\n *\n * @example\n   <example module=\"cacheExampleApp\" name=\"cache-factory\">\n     <file name=\"index.html\">\n       <div ng-controller=\"CacheController\">\n         <input ng-model=\"newCacheKey\" placeholder=\"Key\">\n         <input ng-model=\"newCacheValue\" placeholder=\"Value\">\n         <button ng-click=\"put(newCacheKey, newCacheValue)\">Cache</button>\n\n         <p ng-if=\"keys.length\">Cached Values</p>\n         <div ng-repeat=\"key in keys\">\n           <span ng-bind=\"key\"></span>\n           <span>: </span>\n           <b ng-bind=\"cache.get(key)\"></b>\n         </div>\n\n         <p>Cache Info</p>\n         <div ng-repeat=\"(key, value) in cache.info()\">\n           <span ng-bind=\"key\"></span>\n           <span>: </span>\n           <b ng-bind=\"value\"></b>\n         </div>\n       </div>\n     </file>\n     <file name=\"script.js\">\n       angular.module('cacheExampleApp', []).\n         controller('CacheController', ['$scope', '$cacheFactory', function($scope, $cacheFactory) {\n           $scope.keys = [];\n           $scope.cache = $cacheFactory('cacheId');\n           $scope.put = function(key, value) {\n             if (angular.isUndefined($scope.cache.get(key))) {\n               $scope.keys.push(key);\n             }\n             $scope.cache.put(key, angular.isUndefined(value) ? null : value);\n           };\n         }]);\n     </file>\n     <file name=\"style.css\">\n       p {\n         margin: 10px 0 3px;\n       }\n     </file>\n   </example>\n */\nfunction $CacheFactoryProvider() {\n\n  this.$get = function() {\n    var caches = {};\n\n    function cacheFactory(cacheId, options) {\n      if (cacheId in caches) {\n        throw minErr('$cacheFactory')('iid', 'CacheId \\'{0}\\' is already taken!', cacheId);\n      }\n\n      var size = 0,\n          stats = extend({}, options, {id: cacheId}),\n          data = createMap(),\n          capacity = (options && options.capacity) || Number.MAX_VALUE,\n          lruHash = createMap(),\n          freshEnd = null,\n          staleEnd = null;\n\n      /**\n       * @ngdoc type\n       * @name $cacheFactory.Cache\n       *\n       * @description\n       * A cache object used to store and retrieve data, primarily used by\n       * {@link $templateRequest $templateRequest} and the {@link ng.directive:script script}\n       * directive to cache templates and other data.\n       *\n       * ```js\n       *  angular.module('superCache')\n       *    .factory('superCache', ['$cacheFactory', function($cacheFactory) {\n       *      return $cacheFactory('super-cache');\n       *    }]);\n       * ```\n       *\n       * Example test:\n       *\n       * ```js\n       *  it('should behave like a cache', inject(function(superCache) {\n       *    superCache.put('key', 'value');\n       *    superCache.put('another key', 'another value');\n       *\n       *    expect(superCache.info()).toEqual({\n       *      id: 'super-cache',\n       *      size: 2\n       *    });\n       *\n       *    superCache.remove('another key');\n       *    expect(superCache.get('another key')).toBeUndefined();\n       *\n       *    superCache.removeAll();\n       *    expect(superCache.info()).toEqual({\n       *      id: 'super-cache',\n       *      size: 0\n       *    });\n       *  }));\n       * ```\n       */\n      return (caches[cacheId] = {\n\n        /**\n         * @ngdoc method\n         * @name $cacheFactory.Cache#put\n         * @kind function\n         *\n         * @description\n         * Inserts a named entry into the {@link $cacheFactory.Cache Cache} object to be\n         * retrieved later, and incrementing the size of the cache if the key was not already\n         * present in the cache. If behaving like an LRU cache, it will also remove stale\n         * entries from the set.\n         *\n         * It will not insert undefined values into the cache.\n         *\n         * @param {string} key the key under which the cached data is stored.\n         * @param {*} value the value to store alongside the key. If it is undefined, the key\n         *    will not be stored.\n         * @returns {*} the value stored.\n         */\n        put: function(key, value) {\n          if (isUndefined(value)) return;\n          if (capacity < Number.MAX_VALUE) {\n            var lruEntry = lruHash[key] || (lruHash[key] = {key: key});\n\n            refresh(lruEntry);\n          }\n\n          if (!(key in data)) size++;\n          data[key] = value;\n\n          if (size > capacity) {\n            this.remove(staleEnd.key);\n          }\n\n          return value;\n        },\n\n        /**\n         * @ngdoc method\n         * @name $cacheFactory.Cache#get\n         * @kind function\n         *\n         * @description\n         * Retrieves named data stored in the {@link $cacheFactory.Cache Cache} object.\n         *\n         * @param {string} key the key of the data to be retrieved\n         * @returns {*} the value stored.\n         */\n        get: function(key) {\n          if (capacity < Number.MAX_VALUE) {\n            var lruEntry = lruHash[key];\n\n            if (!lruEntry) return;\n\n            refresh(lruEntry);\n          }\n\n          return data[key];\n        },\n\n\n        /**\n         * @ngdoc method\n         * @name $cacheFactory.Cache#remove\n         * @kind function\n         *\n         * @description\n         * Removes an entry from the {@link $cacheFactory.Cache Cache} object.\n         *\n         * @param {string} key the key of the entry to be removed\n         */\n        remove: function(key) {\n          if (capacity < Number.MAX_VALUE) {\n            var lruEntry = lruHash[key];\n\n            if (!lruEntry) return;\n\n            if (lruEntry === freshEnd) freshEnd = lruEntry.p;\n            if (lruEntry === staleEnd) staleEnd = lruEntry.n;\n            link(lruEntry.n,lruEntry.p);\n\n            delete lruHash[key];\n          }\n\n          if (!(key in data)) return;\n\n          delete data[key];\n          size--;\n        },\n\n\n        /**\n         * @ngdoc method\n         * @name $cacheFactory.Cache#removeAll\n         * @kind function\n         *\n         * @description\n         * Clears the cache object of any entries.\n         */\n        removeAll: function() {\n          data = createMap();\n          size = 0;\n          lruHash = createMap();\n          freshEnd = staleEnd = null;\n        },\n\n\n        /**\n         * @ngdoc method\n         * @name $cacheFactory.Cache#destroy\n         * @kind function\n         *\n         * @description\n         * Destroys the {@link $cacheFactory.Cache Cache} object entirely,\n         * removing it from the {@link $cacheFactory $cacheFactory} set.\n         */\n        destroy: function() {\n          data = null;\n          stats = null;\n          lruHash = null;\n          delete caches[cacheId];\n        },\n\n\n        /**\n         * @ngdoc method\n         * @name $cacheFactory.Cache#info\n         * @kind function\n         *\n         * @description\n         * Retrieve information regarding a particular {@link $cacheFactory.Cache Cache}.\n         *\n         * @returns {object} an object with the following properties:\n         *   <ul>\n         *     <li>**id**: the id of the cache instance</li>\n         *     <li>**size**: the number of entries kept in the cache instance</li>\n         *     <li>**...**: any additional properties from the options object when creating the\n         *       cache.</li>\n         *   </ul>\n         */\n        info: function() {\n          return extend({}, stats, {size: size});\n        }\n      });\n\n\n      /**\n       * makes the `entry` the freshEnd of the LRU linked list\n       */\n      function refresh(entry) {\n        if (entry !== freshEnd) {\n          if (!staleEnd) {\n            staleEnd = entry;\n          } else if (staleEnd === entry) {\n            staleEnd = entry.n;\n          }\n\n          link(entry.n, entry.p);\n          link(entry, freshEnd);\n          freshEnd = entry;\n          freshEnd.n = null;\n        }\n      }\n\n\n      /**\n       * bidirectionally links two entries of the LRU linked list\n       */\n      function link(nextEntry, prevEntry) {\n        if (nextEntry !== prevEntry) {\n          if (nextEntry) nextEntry.p = prevEntry; //p stands for previous, 'prev' didn't minify\n          if (prevEntry) prevEntry.n = nextEntry; //n stands for next, 'next' didn't minify\n        }\n      }\n    }\n\n\n  /**\n   * @ngdoc method\n   * @name $cacheFactory#info\n   *\n   * @description\n   * Get information about all the caches that have been created\n   *\n   * @returns {Object} - key-value map of `cacheId` to the result of calling `cache#info`\n   */\n    cacheFactory.info = function() {\n      var info = {};\n      forEach(caches, function(cache, cacheId) {\n        info[cacheId] = cache.info();\n      });\n      return info;\n    };\n\n\n  /**\n   * @ngdoc method\n   * @name $cacheFactory#get\n   *\n   * @description\n   * Get access to a cache object by the `cacheId` used when it was created.\n   *\n   * @param {string} cacheId Name or id of a cache to access.\n   * @returns {object} Cache object identified by the cacheId or undefined if no such cache.\n   */\n    cacheFactory.get = function(cacheId) {\n      return caches[cacheId];\n    };\n\n\n    return cacheFactory;\n  };\n}\n\n/**\n * @ngdoc service\n * @name $templateCache\n * @this\n *\n * @description\n * `$templateCache` is a {@link $cacheFactory.Cache Cache object} created by the\n * {@link ng.$cacheFactory $cacheFactory}.\n *\n * The first time a template is used, it is loaded in the template cache for quick retrieval. You\n * can load templates directly into the cache in a `script` tag, by using {@link $templateRequest},\n * or by consuming the `$templateCache` service directly.\n *\n * Adding via the `script` tag:\n *\n * ```html\n *   <script type=\"text/ng-template\" id=\"templateId.html\">\n *     <p>This is the content of the template</p>\n *   </script>\n * ```\n *\n * **Note:** the `script` tag containing the template does not need to be included in the `head` of\n * the document, but it must be a descendent of the {@link ng.$rootElement $rootElement} (e.g.\n * element with {@link ngApp} attribute), otherwise the template will be ignored.\n *\n * Adding via the `$templateCache` service:\n *\n * ```js\n * var myApp = angular.module('myApp', []);\n * myApp.run(function($templateCache) {\n *   $templateCache.put('templateId.html', 'This is the content of the template');\n * });\n * ```\n *\n * To retrieve the template later, simply use it in your component:\n * ```js\n * myApp.component('myComponent', {\n *    templateUrl: 'templateId.html'\n * });\n * ```\n *\n * or get it via the `$templateCache` service:\n * ```js\n * $templateCache.get('templateId.html')\n * ```\n *\n */\nfunction $TemplateCacheProvider() {\n  this.$get = ['$cacheFactory', function($cacheFactory) {\n    return $cacheFactory('templates');\n  }];\n}\n\n/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *\n *     Any commits to this file should be reviewed with security in mind.  *\n *   Changes to this file can potentially create security vulnerabilities. *\n *          An approval from 2 Core members with history of modifying      *\n *                         this file is required.                          *\n *                                                                         *\n *  Does the change somehow allow for arbitrary javascript to be executed? *\n *    Or allows for someone to change the prototype of built-in objects?   *\n *     Or gives undesired access to variables like document or window?    *\n * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */\n\n/* ! VARIABLE/FUNCTION NAMING CONVENTIONS THAT APPLY TO THIS FILE!\n *\n * DOM-related variables:\n *\n * - \"node\" - DOM Node\n * - \"element\" - DOM Element or Node\n * - \"$node\" or \"$element\" - jqLite-wrapped node or element\n *\n *\n * Compiler related stuff:\n *\n * - \"linkFn\" - linking fn of a single directive\n * - \"nodeLinkFn\" - function that aggregates all linking fns for a particular node\n * - \"childLinkFn\" -  function that aggregates all linking fns for child nodes of a particular node\n * - \"compositeLinkFn\" - function that aggregates all linking fns for a compilation root (nodeList)\n */\n\n\n/**\n * @ngdoc service\n * @name $compile\n * @kind function\n *\n * @description\n * Compiles an HTML string or DOM into a template and produces a template function, which\n * can then be used to link {@link ng.$rootScope.Scope `scope`} and the template together.\n *\n * The compilation is a process of walking the DOM tree and matching DOM elements to\n * {@link ng.$compileProvider#directive directives}.\n *\n * <div class=\"alert alert-warning\">\n * **Note:** This document is an in-depth reference of all directive options.\n * For a gentle introduction to directives with examples of common use cases,\n * see the {@link guide/directive directive guide}.\n * </div>\n *\n * ## Comprehensive Directive API\n *\n * There are many different options for a directive.\n *\n * The difference resides in the return value of the factory function.\n * You can either return a {@link $compile#directive-definition-object Directive Definition Object (see below)}\n * that defines the directive properties, or just the `postLink` function (all other properties will have\n * the default values).\n *\n * <div class=\"alert alert-success\">\n * **Best Practice:** It's recommended to use the \"directive definition object\" form.\n * </div>\n *\n * Here's an example directive declared with a Directive Definition Object:\n *\n * ```js\n *   var myModule = angular.module(...);\n *\n *   myModule.directive('directiveName', function factory(injectables) {\n *     var directiveDefinitionObject = {\n *       {@link $compile#-priority- priority}: 0,\n *       {@link $compile#-template- template}: '<div></div>', // or // function(tElement, tAttrs) { ... },\n *       // or\n *       // {@link $compile#-templateurl- templateUrl}: 'directive.html', // or // function(tElement, tAttrs) { ... },\n *       {@link $compile#-transclude- transclude}: false,\n *       {@link $compile#-restrict- restrict}: 'A',\n *       {@link $compile#-templatenamespace- templateNamespace}: 'html',\n *       {@link $compile#-scope- scope}: false,\n *       {@link $compile#-controller- controller}: function($scope, $element, $attrs, $transclude, otherInjectables) { ... },\n *       {@link $compile#-controlleras- controllerAs}: 'stringIdentifier',\n *       {@link $compile#-bindtocontroller- bindToController}: false,\n *       {@link $compile#-require- require}: 'siblingDirectiveName', // or // ['^parentDirectiveName', '?optionalDirectiveName', '?^optionalParent'],\n *       {@link $compile#-multielement- multiElement}: false,\n *       {@link $compile#-compile- compile}: function compile(tElement, tAttrs, transclude) {\n *         return {\n *            {@link $compile#pre-linking-function pre}: function preLink(scope, iElement, iAttrs, controller) { ... },\n *            {@link $compile#post-linking-function post}: function postLink(scope, iElement, iAttrs, controller) { ... }\n *         }\n *         // or\n *         // return function postLink( ... ) { ... }\n *       },\n *       // or\n *       // {@link $compile#-link- link}: {\n *       //  {@link $compile#pre-linking-function pre}: function preLink(scope, iElement, iAttrs, controller) { ... },\n *       //  {@link $compile#post-linking-function post}: function postLink(scope, iElement, iAttrs, controller) { ... }\n *       // }\n *       // or\n *       // {@link $compile#-link- link}: function postLink( ... ) { ... }\n *     };\n *     return directiveDefinitionObject;\n *   });\n * ```\n *\n * <div class=\"alert alert-warning\">\n * **Note:** Any unspecified options will use the default value. You can see the default values below.\n * </div>\n *\n * Therefore the above can be simplified as:\n *\n * ```js\n *   var myModule = angular.module(...);\n *\n *   myModule.directive('directiveName', function factory(injectables) {\n *     var directiveDefinitionObject = {\n *       link: function postLink(scope, iElement, iAttrs) { ... }\n *     };\n *     return directiveDefinitionObject;\n *     // or\n *     // return function postLink(scope, iElement, iAttrs) { ... }\n *   });\n * ```\n *\n * ### Life-cycle hooks\n * Directive controllers can provide the following methods that are called by AngularJS at points in the life-cycle of the\n * directive:\n * * `$onInit()` - Called on each controller after all the controllers on an element have been constructed and\n *   had their bindings initialized (and before the pre &amp; post linking functions for the directives on\n *   this element). This is a good place to put initialization code for your controller.\n * * `$onChanges(changesObj)` - Called whenever one-way (`<`) or interpolation (`@`) bindings are updated. The\n *   `changesObj` is a hash whose keys are the names of the bound properties that have changed, and the values are an\n *   object of the form `{ currentValue, previousValue, isFirstChange() }`. Use this hook to trigger updates within a\n *   component such as cloning the bound value to prevent accidental mutation of the outer value. Note that this will\n *   also be called when your bindings are initialized.\n * * `$doCheck()` - Called on each turn of the digest cycle. Provides an opportunity to detect and act on\n *   changes. Any actions that you wish to take in response to the changes that you detect must be\n *   invoked from this hook; implementing this has no effect on when `$onChanges` is called. For example, this hook\n *   could be useful if you wish to perform a deep equality check, or to check a Date object, changes to which would not\n *   be detected by AngularJS's change detector and thus not trigger `$onChanges`. This hook is invoked with no arguments;\n *   if detecting changes, you must store the previous value(s) for comparison to the current values.\n * * `$onDestroy()` - Called on a controller when its containing scope is destroyed. Use this hook for releasing\n *   external resources, watches and event handlers. Note that components have their `$onDestroy()` hooks called in\n *   the same order as the `$scope.$broadcast` events are triggered, which is top down. This means that parent\n *   components will have their `$onDestroy()` hook called before child components.\n * * `$postLink()` - Called after this controller's element and its children have been linked. Similar to the post-link\n *   function this hook can be used to set up DOM event handlers and do direct DOM manipulation.\n *   Note that child elements that contain `templateUrl` directives will not have been compiled and linked since\n *   they are waiting for their template to load asynchronously and their own compilation and linking has been\n *   suspended until that occurs.\n *\n * #### Comparison with life-cycle hooks in the new Angular\n * The new Angular also uses life-cycle hooks for its components. While the AngularJS life-cycle hooks are similar there are\n * some differences that you should be aware of, especially when it comes to moving your code from AngularJS to Angular:\n *\n * * AngularJS hooks are prefixed with `$`, such as `$onInit`. Angular hooks are prefixed with `ng`, such as `ngOnInit`.\n * * AngularJS hooks can be defined on the controller prototype or added to the controller inside its constructor.\n *   In Angular you can only define hooks on the prototype of the Component class.\n * * Due to the differences in change-detection, you may get many more calls to `$doCheck` in AngularJS than you would to\n *   `ngDoCheck` in Angular.\n * * Changes to the model inside `$doCheck` will trigger new turns of the digest loop, which will cause the changes to be\n *   propagated throughout the application.\n *   Angular does not allow the `ngDoCheck` hook to trigger a change outside of the component. It will either throw an\n *   error or do nothing depending upon the state of `enableProdMode()`.\n *\n * #### Life-cycle hook examples\n *\n * This example shows how you can check for mutations to a Date object even though the identity of the object\n * has not changed.\n *\n * <example name=\"doCheckDateExample\" module=\"do-check-module\">\n *   <file name=\"app.js\">\n *     angular.module('do-check-module', [])\n *       .component('app', {\n *         template:\n *           'Month: <input ng-model=\"$ctrl.month\" ng-change=\"$ctrl.updateDate()\">' +\n *           'Date: {{ $ctrl.date }}' +\n *           '<test date=\"$ctrl.date\"></test>',\n *         controller: function() {\n *           this.date = new Date();\n *           this.month = this.date.getMonth();\n *           this.updateDate = function() {\n *             this.date.setMonth(this.month);\n *           };\n *         }\n *       })\n *       .component('test', {\n *         bindings: { date: '<' },\n *         template:\n *           '<pre>{{ $ctrl.log | json }}</pre>',\n *         controller: function() {\n *           var previousValue;\n *           this.log = [];\n *           this.$doCheck = function() {\n *             var currentValue = this.date && this.date.valueOf();\n *             if (previousValue !== currentValue) {\n *               this.log.push('doCheck: date mutated: ' + this.date);\n *               previousValue = currentValue;\n *             }\n *           };\n *         }\n *       });\n *   </file>\n *   <file name=\"index.html\">\n *     <app></app>\n *   </file>\n * </example>\n *\n * This example show how you might use `$doCheck` to trigger changes in your component's inputs even if the\n * actual identity of the component doesn't change. (Be aware that cloning and deep equality checks on large\n * arrays or objects can have a negative impact on your application performance.)\n *\n * <example name=\"doCheckArrayExample\" module=\"do-check-module\">\n *   <file name=\"index.html\">\n *     <div ng-init=\"items = []\">\n *       <button ng-click=\"items.push(items.length)\">Add Item</button>\n *       <button ng-click=\"items = []\">Reset Items</button>\n *       <pre>{{ items }}</pre>\n *       <test items=\"items\"></test>\n *     </div>\n *   </file>\n *   <file name=\"app.js\">\n *      angular.module('do-check-module', [])\n *        .component('test', {\n *          bindings: { items: '<' },\n *          template:\n *            '<pre>{{ $ctrl.log | json }}</pre>',\n *          controller: function() {\n *            this.log = [];\n *\n *            this.$doCheck = function() {\n *              if (this.items_ref !== this.items) {\n *                this.log.push('doCheck: items changed');\n *                this.items_ref = this.items;\n *              }\n *              if (!angular.equals(this.items_clone, this.items)) {\n *                this.log.push('doCheck: items mutated');\n *                this.items_clone = angular.copy(this.items);\n *              }\n *            };\n *          }\n *        });\n *   </file>\n * </example>\n *\n *\n * ### Directive Definition Object\n *\n * The directive definition object provides instructions to the {@link ng.$compile\n * compiler}. The attributes are:\n *\n * #### `multiElement`\n * When this property is set to true (default is `false`), the HTML compiler will collect DOM nodes between\n * nodes with the attributes `directive-name-start` and `directive-name-end`, and group them\n * together as the directive elements. It is recommended that this feature be used on directives\n * which are not strictly behavioral (such as {@link ngClick}), and which\n * do not manipulate or replace child nodes (such as {@link ngInclude}).\n *\n * #### `priority`\n * When there are multiple directives defined on a single DOM element, sometimes it\n * is necessary to specify the order in which the directives are applied. The `priority` is used\n * to sort the directives before their `compile` functions get called. Priority is defined as a\n * number. Directives with greater numerical `priority` are compiled first. Pre-link functions\n * are also run in priority order, but post-link functions are run in reverse order. The order\n * of directives with the same priority is undefined. The default priority is `0`.\n *\n * #### `terminal`\n * If set to true then the current `priority` will be the last set of directives\n * which will execute (any directives at the current priority will still execute\n * as the order of execution on same `priority` is undefined). Note that expressions\n * and other directives used in the directive's template will also be excluded from execution.\n *\n * #### `scope`\n * The scope property can be `false`, `true`, or an object:\n *\n * * **`false` (default):** No scope will be created for the directive. The directive will use its\n * parent's scope.\n *\n * * **`true`:** A new child scope that prototypically inherits from its parent will be created for\n * the directive's element. If multiple directives on the same element request a new scope,\n * only one new scope is created.\n *\n * * **`{...}` (an object hash):** A new \"isolate\" scope is created for the directive's template.\n * The 'isolate' scope differs from normal scope in that it does not prototypically\n * inherit from its parent scope. This is useful when creating reusable components, which should not\n * accidentally read or modify data in the parent scope. Note that an isolate scope\n * directive without a `template` or `templateUrl` will not apply the isolate scope\n * to its children elements.\n *\n * The 'isolate' scope object hash defines a set of local scope properties derived from attributes on the\n * directive's element. These local properties are useful for aliasing values for templates. The keys in\n * the object hash map to the name of the property on the isolate scope; the values define how the property\n * is bound to the parent scope, via matching attributes on the directive's element:\n *\n * * `@` or `@attr` - bind a local scope property to the value of DOM attribute. The result is\n *   always a string since DOM attributes are strings. If no `attr` name is specified then the\n *   attribute name is assumed to be the same as the local name. Given `<my-component\n *   my-attr=\"hello {{name}}\">` and the isolate scope definition `scope: { localName:'@myAttr' }`,\n *   the directive's scope property `localName` will reflect the interpolated value of `hello\n *   {{name}}`. As the `name` attribute changes so will the `localName` property on the directive's\n *   scope. The `name` is read from the parent scope (not the directive's scope).\n *\n * * `=` or `=attr` - set up a bidirectional binding between a local scope property and an expression\n *   passed via the attribute `attr`. The expression is evaluated in the context of the parent scope.\n *   If no `attr` name is specified then the attribute name is assumed to be the same as the local\n *   name. Given `<my-component my-attr=\"parentModel\">` and the isolate scope definition `scope: {\n *   localModel: '=myAttr' }`, the property `localModel` on the directive's scope will reflect the\n *   value of `parentModel` on the parent scope. Changes to `parentModel` will be reflected in\n *   `localModel` and vice versa. If the binding expression is non-assignable, or if the attribute\n *   isn't  optional and doesn't exist, an exception\n *   ({@link error/$compile/nonassign `$compile:nonassign`}) will be thrown upon discovering changes\n *   to the local value, since it will be impossible to sync them back to the parent scope.\n *\n *   By default, the {@link ng.$rootScope.Scope#$watch `$watch`}\n *   method is used for tracking changes, and the equality check is based on object identity.\n *   However, if an object literal or an array literal is passed as the binding expression, the\n *   equality check is done by value (using the {@link angular.equals} function). It's also possible\n *   to watch the evaluated value shallowly with {@link ng.$rootScope.Scope#$watchCollection\n *   `$watchCollection`}: use `=*` or `=*attr`\n *\n  * * `<` or `<attr` - set up a one-way (one-directional) binding between a local scope property and an\n *   expression passed via the attribute `attr`. The expression is evaluated in the context of the\n *   parent scope. If no `attr` name is specified then the attribute name is assumed to be the same as the\n *   local name.\n *\n *   For example, given `<my-component my-attr=\"parentModel\">` and directive definition of\n *   `scope: { localModel:'<myAttr' }`, then the isolated scope property `localModel` will reflect the\n *   value of `parentModel` on the parent scope. Any changes to `parentModel` will be reflected\n *   in `localModel`, but changes in `localModel` will not reflect in `parentModel`. There are however\n *   two caveats:\n *     1. one-way binding does not copy the value from the parent to the isolate scope, it simply\n *     sets the same value. That means if your bound value is an object, changes to its properties\n *     in the isolated scope will be reflected in the parent scope (because both reference the same object).\n *     2. one-way binding watches changes to the **identity** of the parent value. That means the\n *     {@link ng.$rootScope.Scope#$watch `$watch`} on the parent value only fires if the reference\n *     to the value has changed. In most cases, this should not be of concern, but can be important\n *     to know if you one-way bind to an object, and then replace that object in the isolated scope.\n *     If you now change a property of the object in your parent scope, the change will not be\n *     propagated to the isolated scope, because the identity of the object on the parent scope\n *     has not changed. Instead you must assign a new object.\n *\n *   One-way binding is useful if you do not plan to propagate changes to your isolated scope bindings\n *   back to the parent. However, it does not make this completely impossible.\n *\n *   By default, the {@link ng.$rootScope.Scope#$watch `$watch`}\n *   method is used for tracking changes, and the equality check is based on object identity.\n *   It's also possible to watch the evaluated value shallowly with\n *   {@link ng.$rootScope.Scope#$watchCollection `$watchCollection`}: use `<*` or `<*attr`\n *\n * * `&` or `&attr` - provides a way to execute an expression in the context of the parent scope. If\n *   no `attr` name is specified then the attribute name is assumed to be the same as the local name.\n *   Given `<my-component my-attr=\"count = count + value\">` and the isolate scope definition `scope: {\n *   localFn:'&myAttr' }`, the isolate scope property `localFn` will point to a function wrapper for\n *   the `count = count + value` expression. Often it's desirable to pass data from the isolated scope\n *   via an expression to the parent scope. This can be done by passing a map of local variable names\n *   and values into the expression wrapper fn. For example, if the expression is `increment(amount)`\n *   then we can specify the amount value by calling the `localFn` as `localFn({amount: 22})`.\n *\n * All 4 kinds of bindings (`@`, `=`, `<`, and `&`) can be made optional by adding `?` to the expression.\n * The marker must come after the mode and before the attribute name.\n * See the {@link error/$compile/iscp Invalid Isolate Scope Definition error} for definition examples.\n * This is useful to refine the interface directives provide.\n * One subtle difference between optional and non-optional happens **when the binding attribute is not\n * set**:\n * - the binding is optional: the property will not be defined\n * - the binding is not optional: the property is defined\n *\n * ```js\n *app.directive('testDir', function() {\n    return {\n      scope: {\n        notoptional: '=',\n        optional: '=?',\n      },\n      bindToController: true,\n      controller: function() {\n        this.$onInit = function() {\n          console.log(this.hasOwnProperty('notoptional')) // true\n          console.log(this.hasOwnProperty('optional')) // false\n        }\n      }\n    }\n  })\n *```\n *\n *\n * ##### Combining directives with different scope defintions\n *\n * In general it's possible to apply more than one directive to one element, but there might be limitations\n * depending on the type of scope required by the directives. The following points will help explain these limitations.\n * For simplicity only two directives are taken into account, but it is also applicable for several directives:\n *\n * * **no scope** + **no scope** => Two directives which don't require their own scope will use their parent's scope\n * * **child scope** + **no scope** =>  Both directives will share one single child scope\n * * **child scope** + **child scope** =>  Both directives will share one single child scope\n * * **isolated scope** + **no scope** =>  The isolated directive will use it's own created isolated scope. The other directive will use\n * its parent's scope\n * * **isolated scope** + **child scope** =>  **Won't work!** Only one scope can be related to one element. Therefore these directives cannot\n * be applied to the same element.\n * * **isolated scope** + **isolated scope**  =>  **Won't work!** Only one scope can be related to one element. Therefore these directives\n * cannot be applied to the same element.\n *\n *\n * #### `bindToController`\n * This property is used to bind scope properties directly to the controller. It can be either\n * `true` or an object hash with the same format as the `scope` property.\n *\n * When an isolate scope is used for a directive (see above), `bindToController: true` will\n * allow a component to have its properties bound to the controller, rather than to scope.\n *\n * After the controller is instantiated, the initial values of the isolate scope bindings will be bound to the controller\n * properties. You can access these bindings once they have been initialized by providing a controller method called\n * `$onInit`, which is called after all the controllers on an element have been constructed and had their bindings\n * initialized.\n *\n * It is also possible to set `bindToController` to an object hash with the same format as the `scope` property.\n * This will set up the scope bindings to the controller directly. Note that `scope` can still be used\n * to define which kind of scope is created. By default, no scope is created. Use `scope: {}` to create an isolate\n * scope (useful for component directives).\n *\n * If both `bindToController` and `scope` are defined and have object hashes, `bindToController` overrides `scope`.\n *\n *\n * #### `controller`\n * Controller constructor function. The controller is instantiated before the\n * pre-linking phase and can be accessed by other directives (see\n * `require` attribute). This allows the directives to communicate with each other and augment\n * each other's behavior. The controller is injectable (and supports bracket notation) with the following locals:\n *\n * * `$scope` - Current scope associated with the element\n * * `$element` - Current element\n * * `$attrs` - Current attributes object for the element\n * * `$transclude` - A transclude linking function pre-bound to the correct transclusion scope:\n *   `function([scope], cloneLinkingFn, futureParentElement, slotName)`:\n *    * `scope`: (optional) override the scope.\n *    * `cloneLinkingFn`: (optional) argument to create clones of the original transcluded content.\n *    * `futureParentElement` (optional):\n *        * defines the parent to which the `cloneLinkingFn` will add the cloned elements.\n *        * default: `$element.parent()` resp. `$element` for `transclude:'element'` resp. `transclude:true`.\n *        * only needed for transcludes that are allowed to contain non html elements (e.g. SVG elements)\n *          and when the `cloneLinkingFn` is passed,\n *          as those elements need to created and cloned in a special way when they are defined outside their\n *          usual containers (e.g. like `<svg>`).\n *        * See also the `directive.templateNamespace` property.\n *    * `slotName`: (optional) the name of the slot to transclude. If falsy (e.g. `null`, `undefined` or `''`)\n *      then the default transclusion is provided.\n *    The `$transclude` function also has a method on it, `$transclude.isSlotFilled(slotName)`, which returns\n *    `true` if the specified slot contains content (i.e. one or more DOM nodes).\n *\n * #### `require`\n * Require another directive and inject its controller as the fourth argument to the linking function. The\n * `require` property can be a string, an array or an object:\n * * a **string** containing the name of the directive to pass to the linking function\n * * an **array** containing the names of directives to pass to the linking function. The argument passed to the\n * linking function will be an array of controllers in the same order as the names in the `require` property\n * * an **object** whose property values are the names of the directives to pass to the linking function. The argument\n * passed to the linking function will also be an object with matching keys, whose values will hold the corresponding\n * controllers.\n *\n * If the `require` property is an object and `bindToController` is truthy, then the required controllers are\n * bound to the controller using the keys of the `require` property. This binding occurs after all the controllers\n * have been constructed but before `$onInit` is called.\n * If the name of the required controller is the same as the local name (the key), the name can be\n * omitted. For example, `{parentDir: '^^'}` is equivalent to `{parentDir: '^^parentDir'}`.\n * See the {@link $compileProvider#component} helper for an example of how this can be used.\n * If no such required directive(s) can be found, or if the directive does not have a controller, then an error is\n * raised (unless no link function is specified and the required controllers are not being bound to the directive\n * controller, in which case error checking is skipped). The name can be prefixed with:\n *\n * * (no prefix) - Locate the required controller on the current element. Throw an error if not found.\n * * `?` - Attempt to locate the required controller or pass `null` to the `link` fn if not found.\n * * `^` - Locate the required controller by searching the element and its parents. Throw an error if not found.\n * * `^^` - Locate the required controller by searching the element's parents. Throw an error if not found.\n * * `?^` - Attempt to locate the required controller by searching the element and its parents or pass\n *   `null` to the `link` fn if not found.\n * * `?^^` - Attempt to locate the required controller by searching the element's parents, or pass\n *   `null` to the `link` fn if not found.\n *\n *\n * #### `controllerAs`\n * Identifier name for a reference to the controller in the directive's scope.\n * This allows the controller to be referenced from the directive template. This is especially\n * useful when a directive is used as component, i.e. with an `isolate` scope. It's also possible\n * to use it in a directive without an `isolate` / `new` scope, but you need to be aware that the\n * `controllerAs` reference might overwrite a property that already exists on the parent scope.\n *\n *\n * #### `restrict`\n * String of subset of `EACM` which restricts the directive to a specific directive\n * declaration style. If omitted, the defaults (elements and attributes) are used.\n *\n * * `E` - Element name (default): `<my-directive></my-directive>`\n * * `A` - Attribute (default): `<div my-directive=\"exp\"></div>`\n * * `C` - Class: `<div class=\"my-directive: exp;\"></div>`\n * * `M` - Comment: `<!-- directive: my-directive exp -->`\n *\n *\n * #### `templateNamespace`\n * String representing the document type used by the markup in the template.\n * AngularJS needs this information as those elements need to be created and cloned\n * in a special way when they are defined outside their usual containers like `<svg>` and `<math>`.\n *\n * * `html` - All root nodes in the template are HTML. Root nodes may also be\n *   top-level elements such as `<svg>` or `<math>`.\n * * `svg` - The root nodes in the template are SVG elements (excluding `<math>`).\n * * `math` - The root nodes in the template are MathML elements (excluding `<svg>`).\n *\n * If no `templateNamespace` is specified, then the namespace is considered to be `html`.\n *\n * #### `template`\n * HTML markup that may:\n * * Replace the contents of the directive's element (default).\n * * Replace the directive's element itself (if `replace` is true - DEPRECATED).\n * * Wrap the contents of the directive's element (if `transclude` is true).\n *\n * Value may be:\n *\n * * A string. For example `<div red-on-hover>{{delete_str}}</div>`.\n * * A function which takes two arguments `tElement` and `tAttrs` (described in the `compile`\n *   function api below) and returns a string value.\n *\n *\n * #### `templateUrl`\n * This is similar to `template` but the template is loaded from the specified URL, asynchronously.\n *\n * Because template loading is asynchronous the compiler will suspend compilation of directives on that element\n * for later when the template has been resolved.  In the meantime it will continue to compile and link\n * sibling and parent elements as though this element had not contained any directives.\n *\n * The compiler does not suspend the entire compilation to wait for templates to be loaded because this\n * would result in the whole app \"stalling\" until all templates are loaded asynchronously - even in the\n * case when only one deeply nested directive has `templateUrl`.\n *\n * Template loading is asynchronous even if the template has been preloaded into the {@link $templateCache}.\n *\n * You can specify `templateUrl` as a string representing the URL or as a function which takes two\n * arguments `tElement` and `tAttrs` (described in the `compile` function api below) and returns\n * a string value representing the url.  In either case, the template URL is passed through {@link\n * $sce#getTrustedResourceUrl $sce.getTrustedResourceUrl}.\n *\n *\n * #### `replace`\n * <div class=\"alert alert-danger\">\n * **Note:** `replace` is deprecated in AngularJS and has been removed in the new Angular (v2+).\n * </div>\n *\n * Specifies what the template should replace. Defaults to `false`.\n *\n * * `true` - the template will replace the directive's element.\n * * `false` - the template will replace the contents of the directive's element.\n *\n * The replacement process migrates all of the attributes / classes from the old element to the new\n * one. See the {@link guide/directive#template-expanding-directive\n * Directives Guide} for an example.\n *\n * There are very few scenarios where element replacement is required for the application function,\n * the main one being reusable custom components that are used within SVG contexts\n * (because SVG doesn't work with custom elements in the DOM tree).\n *\n * #### `transclude`\n * Extract the contents of the element where the directive appears and make it available to the directive.\n * The contents are compiled and provided to the directive as a **transclusion function**. See the\n * {@link $compile#transclusion Transclusion} section below.\n *\n *\n * #### `compile`\n *\n * ```js\n *   function compile(tElement, tAttrs, transclude) { ... }\n * ```\n *\n * The compile function deals with transforming the template DOM. Since most directives do not do\n * template transformation, it is not used often. The compile function takes the following arguments:\n *\n *   * `tElement` - template element - The element where the directive has been declared. It is\n *     safe to do template transformation on the element and child elements only.\n *\n *   * `tAttrs` - template attributes - Normalized list of attributes declared on this element shared\n *     between all directive compile functions.\n *\n *   * `transclude` -  [*DEPRECATED*!] A transclude linking function: `function(scope, cloneLinkingFn)`\n *\n * <div class=\"alert alert-warning\">\n * **Note:** The template instance and the link instance may be different objects if the template has\n * been cloned. For this reason it is **not** safe to do anything other than DOM transformations that\n * apply to all cloned DOM nodes within the compile function. Specifically, DOM listener registration\n * should be done in a linking function rather than in a compile function.\n * </div>\n\n * <div class=\"alert alert-warning\">\n * **Note:** The compile function cannot handle directives that recursively use themselves in their\n * own templates or compile functions. Compiling these directives results in an infinite loop and\n * stack overflow errors.\n *\n * This can be avoided by manually using `$compile` in the postLink function to imperatively compile\n * a directive's template instead of relying on automatic template compilation via `template` or\n * `templateUrl` declaration or manual compilation inside the compile function.\n * </div>\n *\n * <div class=\"alert alert-danger\">\n * **Note:** The `transclude` function that is passed to the compile function is deprecated, as it\n *   e.g. does not know about the right outer scope. Please use the transclude function that is passed\n *   to the link function instead.\n * </div>\n\n * A compile function can have a return value which can be either a function or an object.\n *\n * * returning a (post-link) function - is equivalent to registering the linking function via the\n *   `link` property of the config object when the compile function is empty.\n *\n * * returning an object with function(s) registered via `pre` and `post` properties - allows you to\n *   control when a linking function should be called during the linking phase. See info about\n *   pre-linking and post-linking functions below.\n *\n *\n * #### `link`\n * This property is used only if the `compile` property is not defined.\n *\n * ```js\n *   function link(scope, iElement, iAttrs, controller, transcludeFn) { ... }\n * ```\n *\n * The link function is responsible for registering DOM listeners as well as updating the DOM. It is\n * executed after the template has been cloned. This is where most of the directive logic will be\n * put.\n *\n *   * `scope` - {@link ng.$rootScope.Scope Scope} - The scope to be used by the\n *     directive for registering {@link ng.$rootScope.Scope#$watch watches}.\n *\n *   * `iElement` - instance element - The element where the directive is to be used. It is safe to\n *     manipulate the children of the element only in `postLink` function since the children have\n *     already been linked.\n *\n *   * `iAttrs` - instance attributes - Normalized list of attributes declared on this element shared\n *     between all directive linking functions.\n *\n *   * `controller` - the directive's required controller instance(s) - Instances are shared\n *     among all directives, which allows the directives to use the controllers as a communication\n *     channel. The exact value depends on the directive's `require` property:\n *       * no controller(s) required: the directive's own controller, or `undefined` if it doesn't have one\n *       * `string`: the controller instance\n *       * `array`: array of controller instances\n *\n *     If a required controller cannot be found, and it is optional, the instance is `null`,\n *     otherwise the {@link error:$compile:ctreq Missing Required Controller} error is thrown.\n *\n *     Note that you can also require the directive's own controller - it will be made available like\n *     any other controller.\n *\n *   * `transcludeFn` - A transclude linking function pre-bound to the correct transclusion scope.\n *     This is the same as the `$transclude` parameter of directive controllers,\n *     see {@link ng.$compile#-controller- the controller section for details}.\n *     `function([scope], cloneLinkingFn, futureParentElement)`.\n *\n * #### Pre-linking function\n *\n * Executed before the child elements are linked. Not safe to do DOM transformation since the\n * compiler linking function will fail to locate the correct elements for linking.\n *\n * #### Post-linking function\n *\n * Executed after the child elements are linked.\n *\n * Note that child elements that contain `templateUrl` directives will not have been compiled\n * and linked since they are waiting for their template to load asynchronously and their own\n * compilation and linking has been suspended until that occurs.\n *\n * It is safe to do DOM transformation in the post-linking function on elements that are not waiting\n * for their async templates to be resolved.\n *\n *\n * ### Transclusion\n *\n * Transclusion is the process of extracting a collection of DOM elements from one part of the DOM and\n * copying them to another part of the DOM, while maintaining their connection to the original AngularJS\n * scope from where they were taken.\n *\n * Transclusion is used (often with {@link ngTransclude}) to insert the\n * original contents of a directive's element into a specified place in the template of the directive.\n * The benefit of transclusion, over simply moving the DOM elements manually, is that the transcluded\n * content has access to the properties on the scope from which it was taken, even if the directive\n * has isolated scope.\n * See the {@link guide/directive#creating-a-directive-that-wraps-other-elements Directives Guide}.\n *\n * This makes it possible for the widget to have private state for its template, while the transcluded\n * content has access to its originating scope.\n *\n * <div class=\"alert alert-warning\">\n * **Note:** When testing an element transclude directive you must not place the directive at the root of the\n * DOM fragment that is being compiled. See {@link guide/unit-testing#testing-transclusion-directives\n * Testing Transclusion Directives}.\n * </div>\n *\n * There are three kinds of transclusion depending upon whether you want to transclude just the contents of the\n * directive's element, the entire element or multiple parts of the element contents:\n *\n * * `true` - transclude the content (i.e. the child nodes) of the directive's element.\n * * `'element'` - transclude the whole of the directive's element including any directives on this\n *   element that are defined at a lower priority than this directive. When used, the `template`\n *   property is ignored.\n * * **`{...}` (an object hash):** - map elements of the content onto transclusion \"slots\" in the template.\n *\n * **Multi-slot transclusion** is declared by providing an object for the `transclude` property.\n *\n * This object is a map where the keys are the name of the slot to fill and the value is an element selector\n * used to match the HTML to the slot. The element selector should be in normalized form (e.g. `myElement`)\n * and will match the standard element variants (e.g. `my-element`, `my:element`, `data-my-element`, etc).\n *\n * For further information check out the guide on {@link guide/directive#matching-directives Matching Directives}.\n *\n * If the element selector is prefixed with a `?` then that slot is optional.\n *\n * For example, the transclude object `{ slotA: '?myCustomElement' }` maps `<my-custom-element>` elements to\n * the `slotA` slot, which can be accessed via the `$transclude` function or via the {@link ngTransclude} directive.\n *\n * Slots that are not marked as optional (`?`) will trigger a compile time error if there are no matching elements\n * in the transclude content. If you wish to know if an optional slot was filled with content, then you can call\n * `$transclude.isSlotFilled(slotName)` on the transclude function passed to the directive's link function and\n * injectable into the directive's controller.\n *\n *\n * #### Transclusion Functions\n *\n * When a directive requests transclusion, the compiler extracts its contents and provides a **transclusion\n * function** to the directive's `link` function and `controller`. This transclusion function is a special\n * **linking function** that will return the compiled contents linked to a new transclusion scope.\n *\n * <div class=\"alert alert-info\">\n * If you are just using {@link ngTransclude} then you don't need to worry about this function, since\n * ngTransclude will deal with it for us.\n * </div>\n *\n * If you want to manually control the insertion and removal of the transcluded content in your directive\n * then you must use this transclude function. When you call a transclude function it returns a jqLite/JQuery\n * object that contains the compiled DOM, which is linked to the correct transclusion scope.\n *\n * When you call a transclusion function you can pass in a **clone attach function**. This function accepts\n * two parameters, `function(clone, scope) { ... }`, where the `clone` is a fresh compiled copy of your transcluded\n * content and the `scope` is the newly created transclusion scope, which the clone will be linked to.\n *\n * <div class=\"alert alert-info\">\n * **Best Practice**: Always provide a `cloneFn` (clone attach function) when you call a transclude function\n * since you then get a fresh clone of the original DOM and also have access to the new transclusion scope.\n * </div>\n *\n * It is normal practice to attach your transcluded content (`clone`) to the DOM inside your **clone\n * attach function**:\n *\n * ```js\n * var transcludedContent, transclusionScope;\n *\n * $transclude(function(clone, scope) {\n *   element.append(clone);\n *   transcludedContent = clone;\n *   transclusionScope = scope;\n * });\n * ```\n *\n * Later, if you want to remove the transcluded content from your DOM then you should also destroy the\n * associated transclusion scope:\n *\n * ```js\n * transcludedContent.remove();\n * transclusionScope.$destroy();\n * ```\n *\n * <div class=\"alert alert-info\">\n * **Best Practice**: if you intend to add and remove transcluded content manually in your directive\n * (by calling the transclude function to get the DOM and calling `element.remove()` to remove it),\n * then you are also responsible for calling `$destroy` on the transclusion scope.\n * </div>\n *\n * The built-in DOM manipulation directives, such as {@link ngIf}, {@link ngSwitch} and {@link ngRepeat}\n * automatically destroy their transcluded clones as necessary so you do not need to worry about this if\n * you are simply using {@link ngTransclude} to inject the transclusion into your directive.\n *\n *\n * #### Transclusion Scopes\n *\n * When you call a transclude function it returns a DOM fragment that is pre-bound to a **transclusion\n * scope**. This scope is special, in that it is a child of the directive's scope (and so gets destroyed\n * when the directive's scope gets destroyed) but it inherits the properties of the scope from which it\n * was taken.\n *\n * For example consider a directive that uses transclusion and isolated scope. The DOM hierarchy might look\n * like this:\n *\n * ```html\n * <div ng-app>\n *   <div isolate>\n *     <div transclusion>\n *     </div>\n *   </div>\n * </div>\n * ```\n *\n * The `$parent` scope hierarchy will look like this:\n *\n   ```\n   - $rootScope\n     - isolate\n       - transclusion\n   ```\n *\n * but the scopes will inherit prototypically from different scopes to their `$parent`.\n *\n   ```\n   - $rootScope\n     - transclusion\n   - isolate\n   ```\n *\n *\n * ### Attributes\n *\n * The {@link ng.$compile.directive.Attributes Attributes} object - passed as a parameter in the\n * `link()` or `compile()` functions. It has a variety of uses.\n *\n * * *Accessing normalized attribute names:* Directives like `ngBind` can be expressed in many ways:\n *   `ng:bind`, `data-ng-bind`, or `x-ng-bind`. The attributes object allows for normalized access\n *   to the attributes.\n *\n * * *Directive inter-communication:* All directives share the same instance of the attributes\n *   object which allows the directives to use the attributes object as inter directive\n *   communication.\n *\n * * *Supports interpolation:* Interpolation attributes are assigned to the attribute object\n *   allowing other directives to read the interpolated value.\n *\n * * *Observing interpolated attributes:* Use `$observe` to observe the value changes of attributes\n *   that contain interpolation (e.g. `src=\"{{bar}}\"`). Not only is this very efficient but it's also\n *   the only way to easily get the actual value because during the linking phase the interpolation\n *   hasn't been evaluated yet and so the value is at this time set to `undefined`.\n *\n * ```js\n * function linkingFn(scope, elm, attrs, ctrl) {\n *   // get the attribute value\n *   console.log(attrs.ngModel);\n *\n *   // change the attribute\n *   attrs.$set('ngModel', 'new value');\n *\n *   // observe changes to interpolated attribute\n *   attrs.$observe('ngModel', function(value) {\n *     console.log('ngModel has changed value to ' + value);\n *   });\n * }\n * ```\n *\n * ## Example\n *\n * <div class=\"alert alert-warning\">\n * **Note**: Typically directives are registered with `module.directive`. The example below is\n * to illustrate how `$compile` works.\n * </div>\n *\n <example module=\"compileExample\" name=\"compile\">\n   <file name=\"index.html\">\n    <script>\n      angular.module('compileExample', [], function($compileProvider) {\n        // Configure new 'compile' directive by passing a directive\n        // factory function. The factory function injects '$compile'.\n        $compileProvider.directive('compile', function($compile) {\n          // The directive factory creates a link function.\n          return function(scope, element, attrs) {\n            scope.$watch(\n              function(scope) {\n                // Watch the 'compile' expression for changes.\n                return scope.$eval(attrs.compile);\n              },\n              function(value) {\n                // When the 'compile' expression changes\n                // assign it into the current DOM.\n                element.html(value);\n\n                // Compile the new DOM and link it to the current scope.\n                // NOTE: we only compile '.childNodes' so that we\n                // don't get into an infinite loop compiling ourselves.\n                $compile(element.contents())(scope);\n              }\n            );\n          };\n        });\n      })\n      .controller('GreeterController', ['$scope', function($scope) {\n        $scope.name = 'AngularJS';\n        $scope.html = 'Hello {{name}}';\n      }]);\n    </script>\n    <div ng-controller=\"GreeterController\">\n      <input ng-model=\"name\"> <br/>\n      <textarea ng-model=\"html\"></textarea> <br/>\n      <div compile=\"html\"></div>\n    </div>\n   </file>\n   <file name=\"protractor.js\" type=\"protractor\">\n     it('should auto compile', function() {\n       var textarea = $('textarea');\n       var output = $('div[compile]');\n       // The initial state reads 'Hello AngularJS'.\n       expect(output.getText()).toBe('Hello AngularJS');\n       textarea.clear();\n       textarea.sendKeys('{{name}}!');\n       expect(output.getText()).toBe('AngularJS!');\n     });\n   </file>\n </example>\n\n *\n *\n * @param {string|DOMElement} element Element or HTML string to compile into a template function.\n * @param {function(angular.Scope, cloneAttachFn=)} transclude function available to directives - DEPRECATED.\n *\n * <div class=\"alert alert-danger\">\n * **Note:** Passing a `transclude` function to the $compile function is deprecated, as it\n *   e.g. will not use the right outer scope. Please pass the transclude function as a\n *   `parentBoundTranscludeFn` to the link function instead.\n * </div>\n *\n * @param {number} maxPriority only apply directives lower than given priority (Only effects the\n *                 root element(s), not their children)\n * @returns {function(scope, cloneAttachFn=, options=)} a link function which is used to bind template\n * (a DOM element/tree) to a scope. Where:\n *\n *  * `scope` - A {@link ng.$rootScope.Scope Scope} to bind to.\n *  * `cloneAttachFn` - If `cloneAttachFn` is provided, then the link function will clone the\n *  `template` and call the `cloneAttachFn` function allowing the caller to attach the\n *  cloned elements to the DOM document at the appropriate place. The `cloneAttachFn` is\n *  called as: <br/> `cloneAttachFn(clonedElement, scope)` where:\n *\n *      * `clonedElement` - is a clone of the original `element` passed into the compiler.\n *      * `scope` - is the current scope with which the linking function is working with.\n *\n *  * `options` - An optional object hash with linking options. If `options` is provided, then the following\n *  keys may be used to control linking behavior:\n *\n *      * `parentBoundTranscludeFn` - the transclude function made available to\n *        directives; if given, it will be passed through to the link functions of\n *        directives found in `element` during compilation.\n *      * `transcludeControllers` - an object hash with keys that map controller names\n *        to a hash with the key `instance`, which maps to the controller instance;\n *        if given, it will make the controllers available to directives on the compileNode:\n *        ```\n *        {\n *          parent: {\n *            instance: parentControllerInstance\n *          }\n *        }\n *        ```\n *      * `futureParentElement` - defines the parent to which the `cloneAttachFn` will add\n *        the cloned elements; only needed for transcludes that are allowed to contain non HTML\n *        elements (e.g. SVG elements). See also the `directive.controller` property.\n *\n * Calling the linking function returns the element of the template. It is either the original\n * element passed in, or the clone of the element if the `cloneAttachFn` is provided.\n *\n * After linking the view is not updated until after a call to `$digest`, which typically is done by\n * AngularJS automatically.\n *\n * If you need access to the bound view, there are two ways to do it:\n *\n * - If you are not asking the linking function to clone the template, create the DOM element(s)\n *   before you send them to the compiler and keep this reference around.\n *   ```js\n *     var element = angular.element('<p>{{total}}</p>');\n *     $compile(element)(scope);\n *   ```\n *\n * - if on the other hand, you need the element to be cloned, the view reference from the original\n *   example would not point to the clone, but rather to the original template that was cloned. In\n *   this case, you can access the clone either via the `cloneAttachFn` or the value returned by the\n *   linking function:\n *   ```js\n *     var templateElement = angular.element('<p>{{total}}</p>');\n *     var clonedElement = $compile(templateElement)(scope, function(clonedElement, scope) {\n *       // Attach the clone to DOM document at the right place.\n *     });\n *\n *     // Now we have reference to the cloned DOM via `clonedElement`.\n *     // NOTE: The `clonedElement` returned by the linking function is the same as the\n *     //       `clonedElement` passed to `cloneAttachFn`.\n *   ```\n *\n *\n * For information on how the compiler works, see the\n * {@link guide/compiler AngularJS HTML Compiler} section of the Developer Guide.\n *\n * @knownIssue\n *\n * ### Double Compilation\n *\n   Double compilation occurs when an already compiled part of the DOM gets\n   compiled again. This is an undesired effect and can lead to misbehaving directives, performance issues,\n   and memory leaks. Refer to the Compiler Guide {@link guide/compiler#double-compilation-and-how-to-avoid-it\n   section on double compilation} for an in-depth explanation and ways to avoid it.\n\n * @knownIssue\n\n   ### Issues with `replace: true`\n *\n * <div class=\"alert alert-danger\">\n *   **Note**: {@link $compile#-replace- `replace: true`} is deprecated and not recommended to use,\n *   mainly due to the issues listed here. It has been completely removed in the new Angular.\n * </div>\n *\n * #### Attribute values are not merged\n *\n * When a `replace` directive encounters the same attribute on the original and the replace node,\n * it will simply deduplicate the attribute and join the values with a space or with a `;` in case of\n * the `style` attribute.\n * ```html\n * Original Node: <span class=\"original\" style=\"color: red;\"></span>\n * Replace Template: <span class=\"replaced\" style=\"background: blue;\"></span>\n * Result: <span class=\"original replaced\" style=\"color: red; background: blue;\"></span>\n * ```\n *\n * That means attributes that contain AngularJS expressions will not be merged correctly, e.g.\n * {@link ngShow} or {@link ngClass} will cause a {@link $parse} error:\n *\n * ```html\n * Original Node: <span ng-class=\"{'something': something}\" ng-show=\"!condition\"></span>\n * Replace Template: <span ng-class=\"{'else': else}\" ng-show=\"otherCondition\"></span>\n * Result: <span ng-class=\"{'something': something} {'else': else}\" ng-show=\"!condition otherCondition\"></span>\n * ```\n *\n * See issue [#5695](https://github.com/angular/angular.js/issues/5695).\n *\n * #### Directives are not deduplicated before compilation\n *\n * When the original node and the replace template declare the same directive(s), they will be\n * {@link guide/compiler#double-compilation-and-how-to-avoid-it compiled twice} because the compiler\n * does not deduplicate them. In many cases, this is not noticeable, but e.g. {@link ngModel} will\n * attach `$formatters` and `$parsers` twice.\n *\n * See issue [#2573](https://github.com/angular/angular.js/issues/2573).\n *\n * #### `transclude: element` in the replace template root can have unexpected effects\n *\n * When the replace template has a directive at the root node that uses\n * {@link $compile#-transclude- `transclude: element`}, e.g.\n * {@link ngIf} or {@link ngRepeat}, the DOM structure or scope inheritance can be incorrect.\n * See the following issues:\n *\n * - Incorrect scope on replaced element:\n * [#9837](https://github.com/angular/angular.js/issues/9837)\n * - Different DOM between `template` and `templateUrl`:\n * [#10612](https://github.com/angular/angular.js/issues/14326)\n *\n */\n\n/**\n * @ngdoc directive\n * @name ngProp\n * @restrict A\n * @element ANY\n *\n * @usage\n *\n * ```html\n * <ANY ng-prop-propname=\"expression\">\n * </ANY>\n * ```\n *\n * or with uppercase letters in property (e.g. \"propName\"):\n *\n *\n * ```html\n * <ANY ng-prop-prop_name=\"expression\">\n * </ANY>\n * ```\n *\n *\n * @description\n * The `ngProp` directive binds an expression to a DOM element property.\n * `ngProp` allows writing to arbitrary properties by including\n * the property name in the attribute, e.g. `ng-prop-value=\"'my value'\"` binds 'my value' to\n * the `value` property.\n *\n * Usually, it's not necessary to write to properties in AngularJS, as the built-in directives\n * handle the most common use cases (instead of the above example, you would use {@link ngValue}).\n *\n * However, [custom elements](https://developer.mozilla.org/docs/Web/Web_Components/Using_custom_elements)\n * often use custom properties to hold data, and `ngProp` can be used to provide input to these\n * custom elements.\n *\n * ## Binding to camelCase properties\n *\n * Since HTML attributes are case-insensitive, camelCase properties like `innerHTML` must be escaped.\n * AngularJS uses the underscore (_) in front of a character to indicate that it is uppercase, so\n * `innerHTML`  must be written as `ng-prop-inner_h_t_m_l=\"expression\"` (Note that this is just an\n * example, and for binding HTML {@link ngBindHtml} should be used.\n *\n * ## Security\n *\n * Binding expressions to arbitrary properties poses a security risk, as  properties like `innerHTML`\n * can insert potentially dangerous HTML into the application, e.g. script tags that execute\n * malicious code.\n * For this reason, `ngProp` applies Strict Contextual Escaping with the {@link ng.$sce $sce service}.\n * This means vulnerable properties require their content to be \"trusted\", based on the\n * context of the property. For example, the `innerHTML` is in the `HTML` context, and the\n * `iframe.src` property is in the `RESOURCE_URL` context, which requires that values written to\n * this property are trusted as a `RESOURCE_URL`.\n *\n * This can be set explicitly by calling $sce.trustAs(type, value) on the value that is\n * trusted before passing it to the `ng-prop-*` directive. There are exist shorthand methods for\n * each context type in the form of {@link ng.$sce#trustAsResourceUrl $sce.trustAsResourceUrl()} et al.\n *\n * In some cases you can also rely upon automatic sanitization of untrusted values - see below.\n *\n * Based on the context, other options may exist to mark a value as trusted / configure the behavior\n * of {@link ng.$sce}. For example, to restrict the `RESOURCE_URL` context to specific origins, use\n * the {@link $sceDelegateProvider#trustedResourceUrlList trustedResourceUrlList()}\n * and {@link $sceDelegateProvider#bannedResourceUrlList bannedResourceUrlList()}.\n *\n * {@link ng.$sce#what-trusted-context-types-are-supported- Find out more about the different context types}.\n *\n * ### HTML Sanitization\n *\n * By default, `$sce` will throw an error if it detects untrusted HTML content, and will not bind the\n * content.\n * However, if you include the {@link ngSanitize ngSanitize module}, it will try to sanitize the\n * potentially dangerous HTML, e.g. strip non-trusted tags and attributes when binding to\n * `innerHTML`.\n *\n * @example\n * ### Binding to different contexts\n *\n * <example name=\"ngProp\" module=\"exampleNgProp\">\n *   <file name=\"app.js\">\n *     angular.module('exampleNgProp', [])\n *       .component('main', {\n *         templateUrl: 'main.html',\n *         controller: function($sce) {\n *           this.safeContent = '<strong>Safe content</strong>';\n *           this.unsafeContent = '<button onclick=\"alert(\\'Hello XSS!\\')\">Click for XSS</button>';\n *           this.trustedUnsafeContent = $sce.trustAsHtml(this.unsafeContent);\n *         }\n *       });\n *   </file>\n *   <file name=\"main.html\">\n *     <div>\n *       <div class=\"prop-unit\">\n *         Binding to a property without security context:\n *         <div class=\"prop-binding\" ng-prop-inner_text=\"$ctrl.safeContent\"></div>\n *         <span class=\"prop-note\">innerText</span> (safeContent)\n *       </div>\n *\n *       <div class=\"prop-unit\">\n *         \"Safe\" content that requires a security context will throw because the contents could potentially be dangerous ...\n *         <div class=\"prop-binding\" ng-prop-inner_h_t_m_l=\"$ctrl.safeContent\"></div>\n *         <span class=\"prop-note\">innerHTML</span> (safeContent)\n *       </div>\n *\n *       <div class=\"prop-unit\">\n *         ... so that actually dangerous content cannot be executed:\n *         <div class=\"prop-binding\" ng-prop-inner_h_t_m_l=\"$ctrl.unsafeContent\"></div>\n *         <span class=\"prop-note\">innerHTML</span> (unsafeContent)\n *       </div>\n *\n *       <div class=\"prop-unit\">\n *         ... but unsafe Content that has been trusted explicitly works - only do this if you are 100% sure!\n *         <div class=\"prop-binding\" ng-prop-inner_h_t_m_l=\"$ctrl.trustedUnsafeContent\"></div>\n *         <span class=\"prop-note\">innerHTML</span> (trustedUnsafeContent)\n *       </div>\n *     </div>\n *   </file>\n *   <file name=\"index.html\">\n *     <main></main>\n *   </file>\n *   <file name=\"styles.css\">\n *     .prop-unit {\n *       margin-bottom: 10px;\n *     }\n *\n *     .prop-binding {\n *       min-height: 30px;\n *       border: 1px solid blue;\n *     }\n *\n *     .prop-note {\n *       font-family: Monospace;\n *     }\n *   </file>\n * </example>\n *\n *\n * @example\n * ### Binding to innerHTML with ngSanitize\n *\n * <example name=\"ngProp\" module=\"exampleNgProp\" deps=\"angular-sanitize.js\">\n *   <file name=\"app.js\">\n *     angular.module('exampleNgProp', ['ngSanitize'])\n *       .component('main', {\n *         templateUrl: 'main.html',\n *         controller: function($sce) {\n *           this.safeContent = '<strong>Safe content</strong>';\n *           this.unsafeContent = '<button onclick=\"alert(\\'Hello XSS!\\')\">Click for XSS</button>';\n *           this.trustedUnsafeContent = $sce.trustAsHtml(this.unsafeContent);\n *         }\n *       });\n *   </file>\n *   <file name=\"main.html\">\n *     <div>\n *       <div class=\"prop-unit\">\n *         \"Safe\" content will be sanitized ...\n *         <div class=\"prop-binding\" ng-prop-inner_h_t_m_l=\"$ctrl.safeContent\"></div>\n *         <span class=\"prop-note\">innerHTML</span> (safeContent)\n *       </div>\n *\n *       <div class=\"prop-unit\">\n *         ... as will dangerous content:\n *         <div class=\"prop-binding\" ng-prop-inner_h_t_m_l=\"$ctrl.unsafeContent\"></div>\n *         <span class=\"prop-note\">innerHTML</span> (unsafeContent)\n *       </div>\n *\n *       <div class=\"prop-unit\">\n *         ... and content that has been trusted explicitly works the same as without ngSanitize:\n *         <div class=\"prop-binding\" ng-prop-inner_h_t_m_l=\"$ctrl.trustedUnsafeContent\"></div>\n *         <span class=\"prop-note\">innerHTML</span> (trustedUnsafeContent)\n *       </div>\n *     </div>\n *   </file>\n *   <file name=\"index.html\">\n *     <main></main>\n *   </file>\n *   <file name=\"styles.css\">\n *     .prop-unit {\n *       margin-bottom: 10px;\n *     }\n *\n *     .prop-binding {\n *       min-height: 30px;\n *       border: 1px solid blue;\n *     }\n *\n *     .prop-note {\n *       font-family: Monospace;\n *     }\n *   </file>\n * </example>\n *\n */\n\n/** @ngdoc directive\n * @name ngOn\n * @restrict A\n * @element ANY\n *\n * @usage\n *\n * ```html\n * <ANY ng-on-eventname=\"expression\">\n * </ANY>\n * ```\n *\n * or with uppercase letters in property (e.g. \"eventName\"):\n *\n *\n * ```html\n * <ANY ng-on-event_name=\"expression\">\n * </ANY>\n * ```\n *\n * @description\n * The `ngOn` directive adds an event listener to a DOM element via\n * {@link angular.element angular.element().on()}, and evaluates an expression when the event is\n * fired.\n * `ngOn` allows adding listeners for arbitrary events by including\n * the event name in the attribute, e.g. `ng-on-drop=\"onDrop()\"` executes the 'onDrop()' expression\n * when the `drop` event is fired.\n *\n * AngularJS provides specific directives for many events, such as {@link ngClick}, so in most\n * cases it is not necessary to use `ngOn`. However, AngularJS does not support all events\n * (e.g. the `drop` event in the example above), and new events might be introduced in later DOM\n * standards.\n *\n * Another use-case for `ngOn` is listening to\n * [custom events](https://developer.mozilla.org/docs/Web/Guide/Events/Creating_and_triggering_events)\n * fired by\n * [custom elements](https://developer.mozilla.org/docs/Web/Web_Components/Using_custom_elements).\n *\n * ## Binding to camelCase properties\n *\n * Since HTML attributes are case-insensitive, camelCase properties like `myEvent` must be escaped.\n * AngularJS uses the underscore (_) in front of a character to indicate that it is uppercase, so\n * `myEvent` must be written as `ng-on-my_event=\"expression\"`.\n *\n * @example\n * ### Bind to built-in DOM events\n *\n * <example name=\"ngOn\" module=\"exampleNgOn\">\n *   <file name=\"app.js\">\n *     angular.module('exampleNgOn', [])\n *       .component('main', {\n *         templateUrl: 'main.html',\n *         controller: function() {\n *           this.clickCount = 0;\n *           this.mouseoverCount = 0;\n *\n *           this.loadingState = 0;\n *         }\n *       });\n *   </file>\n *   <file name=\"main.html\">\n *     <div>\n *       This is equivalent to `ngClick` and `ngMouseover`:<br>\n *       <button\n *         ng-on-click=\"$ctrl.clickCount = $ctrl.clickCount + 1\"\n *         ng-on-mouseover=\"$ctrl.mouseoverCount = $ctrl.mouseoverCount + 1\">Click or mouseover</button><br>\n *       clickCount: {{$ctrl.clickCount}}<br>\n *       mouseover: {{$ctrl.mouseoverCount}}\n *\n *       <hr>\n *\n *       For the `error` and `load` event on images no built-in AngularJS directives exist:<br>\n *       <img src=\"thisimagedoesnotexist.png\" ng-on-error=\"$ctrl.loadingState = -1\" ng-on-load=\"$ctrl.loadingState = 1\"><br>\n *       <div ng-switch=\"$ctrl.loadingState\">\n *         <span ng-switch-when=\"0\">Image is loading</span>\n *         <span ng-switch-when=\"-1\">Image load error</span>\n *         <span ng-switch-when=\"1\">Image loaded successfully</span>\n *       </div>\n *     </div>\n *   </file>\n *   <file name=\"index.html\">\n *     <main></main>\n *   </file>\n * </example>\n *\n *\n * @example\n * ### Bind to custom DOM events\n *\n * <example name=\"ngOnCustom\" module=\"exampleNgOn\">\n *   <file name=\"app.js\">\n *     angular.module('exampleNgOn', [])\n *       .component('main', {\n *         templateUrl: 'main.html',\n *         controller: function() {\n *           this.eventLog = '';\n *\n *           this.listener = function($event) {\n *             this.eventLog = 'Event with type \"' + $event.type + '\" fired at ' + $event.detail;\n *           };\n *         }\n *       })\n *       .component('childComponent', {\n *         templateUrl: 'child.html',\n *         controller: function($element) {\n *           this.fireEvent = function() {\n *             var event = new CustomEvent('customtype', { detail: new Date()});\n *\n *             $element[0].dispatchEvent(event);\n *           };\n *         }\n *       });\n *   </file>\n *   <file name=\"main.html\">\n *     <child-component ng-on-customtype=\"$ctrl.listener($event)\"></child-component><br>\n *     <span>Event log: {{$ctrl.eventLog}}</span>\n *   </file>\n *   <file name=\"child.html\">\n      <button ng-click=\"$ctrl.fireEvent()\">Fire custom event</button>\n *   </file>\n *   <file name=\"index.html\">\n *     <main></main>\n *   </file>\n * </example>\n */\n\nvar $compileMinErr = minErr('$compile');\n\nfunction UNINITIALIZED_VALUE() {}\nvar _UNINITIALIZED_VALUE = new UNINITIALIZED_VALUE();\n\n/**\n * @ngdoc provider\n * @name $compileProvider\n *\n * @description\n */\n$CompileProvider.$inject = ['$provide', '$$sanitizeUriProvider'];\n/** @this */\nfunction $CompileProvider($provide, $$sanitizeUriProvider) {\n  var hasDirectives = {},\n      Suffix = 'Directive',\n      COMMENT_DIRECTIVE_REGEXP = /^\\s*directive:\\s*([\\w-]+)\\s+(.*)$/,\n      CLASS_DIRECTIVE_REGEXP = /(([\\w-]+)(?::([^;]+))?;?)/,\n      ALL_OR_NOTHING_ATTRS = makeMap('ngSrc,ngSrcset,src,srcset'),\n      REQUIRE_PREFIX_REGEXP = /^(?:(\\^\\^?)?(\\?)?(\\^\\^?)?)?/;\n\n  // Ref: http://developers.whatwg.org/webappapis.html#event-handler-idl-attributes\n  // The assumption is that future DOM event attribute names will begin with\n  // 'on' and be composed of only English letters.\n  var EVENT_HANDLER_ATTR_REGEXP = /^(on[a-z]+|formaction)$/;\n  var bindingCache = createMap();\n\n  function parseIsolateBindings(scope, directiveName, isController) {\n    var LOCAL_REGEXP = /^([@&]|[=<](\\*?))(\\??)\\s*([\\w$]*)$/;\n\n    var bindings = createMap();\n\n    forEach(scope, function(definition, scopeName) {\n      definition = definition.trim();\n\n      if (definition in bindingCache) {\n        bindings[scopeName] = bindingCache[definition];\n        return;\n      }\n      var match = definition.match(LOCAL_REGEXP);\n\n      if (!match) {\n        throw $compileMinErr('iscp',\n            'Invalid {3} for directive \\'{0}\\'.' +\n            ' Definition: {... {1}: \\'{2}\\' ...}',\n            directiveName, scopeName, definition,\n            (isController ? 'controller bindings definition' :\n            'isolate scope definition'));\n      }\n\n      bindings[scopeName] = {\n        mode: match[1][0],\n        collection: match[2] === '*',\n        optional: match[3] === '?',\n        attrName: match[4] || scopeName\n      };\n      if (match[4]) {\n        bindingCache[definition] = bindings[scopeName];\n      }\n    });\n\n    return bindings;\n  }\n\n  function parseDirectiveBindings(directive, directiveName) {\n    var bindings = {\n      isolateScope: null,\n      bindToController: null\n    };\n    if (isObject(directive.scope)) {\n      if (directive.bindToController === true) {\n        bindings.bindToController = parseIsolateBindings(directive.scope,\n                                                         directiveName, true);\n        bindings.isolateScope = {};\n      } else {\n        bindings.isolateScope = parseIsolateBindings(directive.scope,\n                                                     directiveName, false);\n      }\n    }\n    if (isObject(directive.bindToController)) {\n      bindings.bindToController =\n          parseIsolateBindings(directive.bindToController, directiveName, true);\n    }\n    if (bindings.bindToController && !directive.controller) {\n      // There is no controller\n      throw $compileMinErr('noctrl',\n            'Cannot bind to controller without directive \\'{0}\\'s controller.',\n            directiveName);\n    }\n    return bindings;\n  }\n\n  function assertValidDirectiveName(name) {\n    var letter = name.charAt(0);\n    if (!letter || letter !== lowercase(letter)) {\n      throw $compileMinErr('baddir', 'Directive/Component name \\'{0}\\' is invalid. The first character must be a lowercase letter', name);\n    }\n    if (name !== name.trim()) {\n      throw $compileMinErr('baddir',\n            'Directive/Component name \\'{0}\\' is invalid. The name should not contain leading or trailing whitespaces',\n            name);\n    }\n  }\n\n  function getDirectiveRequire(directive) {\n    var require = directive.require || (directive.controller && directive.name);\n\n    if (!isArray(require) && isObject(require)) {\n      forEach(require, function(value, key) {\n        var match = value.match(REQUIRE_PREFIX_REGEXP);\n        var name = value.substring(match[0].length);\n        if (!name) require[key] = match[0] + key;\n      });\n    }\n\n    return require;\n  }\n\n  function getDirectiveRestrict(restrict, name) {\n    if (restrict && !(isString(restrict) && /[EACM]/.test(restrict))) {\n      throw $compileMinErr('badrestrict',\n          'Restrict property \\'{0}\\' of directive \\'{1}\\' is invalid',\n          restrict,\n          name);\n    }\n\n    return restrict || 'EA';\n  }\n\n  /**\n   * @ngdoc method\n   * @name $compileProvider#directive\n   * @kind function\n   *\n   * @description\n   * Register a new directive with the compiler.\n   *\n   * @param {string|Object} name Name of the directive in camel-case (i.e. `ngBind` which will match\n   *    as `ng-bind`), or an object map of directives where the keys are the names and the values\n   *    are the factories.\n   * @param {Function|Array} directiveFactory An injectable directive factory function. See the\n   *    {@link guide/directive directive guide} and the {@link $compile compile API} for more info.\n   * @returns {ng.$compileProvider} Self for chaining.\n   */\n  this.directive = function registerDirective(name, directiveFactory) {\n    assertArg(name, 'name');\n    assertNotHasOwnProperty(name, 'directive');\n    if (isString(name)) {\n      assertValidDirectiveName(name);\n      assertArg(directiveFactory, 'directiveFactory');\n      if (!hasDirectives.hasOwnProperty(name)) {\n        hasDirectives[name] = [];\n        $provide.factory(name + Suffix, ['$injector', '$exceptionHandler',\n          function($injector, $exceptionHandler) {\n            var directives = [];\n            forEach(hasDirectives[name], function(directiveFactory, index) {\n              try {\n                var directive = $injector.invoke(directiveFactory);\n                if (isFunction(directive)) {\n                  directive = { compile: valueFn(directive) };\n                } else if (!directive.compile && directive.link) {\n                  directive.compile = valueFn(directive.link);\n                }\n                directive.priority = directive.priority || 0;\n                directive.index = index;\n                directive.name = directive.name || name;\n                directive.require = getDirectiveRequire(directive);\n                directive.restrict = getDirectiveRestrict(directive.restrict, name);\n                directive.$$moduleName = directiveFactory.$$moduleName;\n                directives.push(directive);\n              } catch (e) {\n                $exceptionHandler(e);\n              }\n            });\n            return directives;\n          }]);\n      }\n      hasDirectives[name].push(directiveFactory);\n    } else {\n      forEach(name, reverseParams(registerDirective));\n    }\n    return this;\n  };\n\n  /**\n   * @ngdoc method\n   * @name $compileProvider#component\n   * @module ng\n   * @param {string|Object} name Name of the component in camelCase (i.e. `myComp` which will match `<my-comp>`),\n   *    or an object map of components where the keys are the names and the values are the component definition objects.\n   * @param {Object} options Component definition object (a simplified\n   *    {@link ng.$compile#directive-definition-object directive definition object}),\n   *    with the following properties (all optional):\n   *\n   *    - `controller` – `{(string|function()=}` – controller constructor function that should be\n   *      associated with newly created scope or the name of a {@link ng.$compile#-controller-\n   *      registered controller} if passed as a string. An empty `noop` function by default.\n   *    - `controllerAs` – `{string=}` – identifier name for to reference the controller in the component's scope.\n   *      If present, the controller will be published to scope under the `controllerAs` name.\n   *      If not present, this will default to be `$ctrl`.\n   *    - `template` – `{string=|function()=}` – html template as a string or a function that\n   *      returns an html template as a string which should be used as the contents of this component.\n   *      Empty string by default.\n   *\n   *      If `template` is a function, then it is {@link auto.$injector#invoke injected} with\n   *      the following locals:\n   *\n   *      - `$element` - Current element\n   *      - `$attrs` - Current attributes object for the element\n   *\n   *    - `templateUrl` – `{string=|function()=}` – path or function that returns a path to an html\n   *      template that should be used  as the contents of this component.\n   *\n   *      If `templateUrl` is a function, then it is {@link auto.$injector#invoke injected} with\n   *      the following locals:\n   *\n   *      - `$element` - Current element\n   *      - `$attrs` - Current attributes object for the element\n   *\n   *    - `bindings` – `{object=}` – defines bindings between DOM attributes and component properties.\n   *      Component properties are always bound to the component controller and not to the scope.\n   *      See {@link ng.$compile#-bindtocontroller- `bindToController`}.\n   *    - `transclude` – `{boolean=}` – whether {@link $compile#transclusion content transclusion} is enabled.\n   *      Disabled by default.\n   *    - `require` - `{Object<string, string>=}` - requires the controllers of other directives and binds them to\n   *      this component's controller. The object keys specify the property names under which the required\n   *      controllers (object values) will be bound. See {@link ng.$compile#-require- `require`}.\n   *    - `$...` – additional properties to attach to the directive factory function and the controller\n   *      constructor function. (This is used by the component router to annotate)\n   *\n   * @returns {ng.$compileProvider} the compile provider itself, for chaining of function calls.\n   * @description\n   * Register a **component definition** with the compiler. This is a shorthand for registering a special\n   * type of directive, which represents a self-contained UI component in your application. Such components\n   * are always isolated (i.e. `scope: {}`) and are always restricted to elements (i.e. `restrict: 'E'`).\n   *\n   * Component definitions are very simple and do not require as much configuration as defining general\n   * directives. Component definitions usually consist only of a template and a controller backing it.\n   *\n   * In order to make the definition easier, components enforce best practices like use of `controllerAs`,\n   * `bindToController`. They always have **isolate scope** and are restricted to elements.\n   *\n   * Here are a few examples of how you would usually define components:\n   *\n   * ```js\n   *   var myMod = angular.module(...);\n   *   myMod.component('myComp', {\n   *     template: '<div>My name is {{$ctrl.name}}</div>',\n   *     controller: function() {\n   *       this.name = 'shahar';\n   *     }\n   *   });\n   *\n   *   myMod.component('myComp', {\n   *     template: '<div>My name is {{$ctrl.name}}</div>',\n   *     bindings: {name: '@'}\n   *   });\n   *\n   *   myMod.component('myComp', {\n   *     templateUrl: 'views/my-comp.html',\n   *     controller: 'MyCtrl',\n   *     controllerAs: 'ctrl',\n   *     bindings: {name: '@'}\n   *   });\n   *\n   * ```\n   * For more examples, and an in-depth guide, see the {@link guide/component component guide}.\n   *\n   * <br />\n   * See also {@link ng.$compileProvider#directive $compileProvider.directive()}.\n   */\n  this.component = function registerComponent(name, options) {\n    if (!isString(name)) {\n      forEach(name, reverseParams(bind(this, registerComponent)));\n      return this;\n    }\n\n    var controller = options.controller || function() {};\n\n    function factory($injector) {\n      function makeInjectable(fn) {\n        if (isFunction(fn) || isArray(fn)) {\n          return /** @this */ function(tElement, tAttrs) {\n            return $injector.invoke(fn, this, {$element: tElement, $attrs: tAttrs});\n          };\n        } else {\n          return fn;\n        }\n      }\n\n      var template = (!options.template && !options.templateUrl ? '' : options.template);\n      var ddo = {\n        controller: controller,\n        controllerAs: identifierForController(options.controller) || options.controllerAs || '$ctrl',\n        template: makeInjectable(template),\n        templateUrl: makeInjectable(options.templateUrl),\n        transclude: options.transclude,\n        scope: {},\n        bindToController: options.bindings || {},\n        restrict: 'E',\n        require: options.require\n      };\n\n      // Copy annotations (starting with $) over to the DDO\n      forEach(options, function(val, key) {\n        if (key.charAt(0) === '$') ddo[key] = val;\n      });\n\n      return ddo;\n    }\n\n    // TODO(pete) remove the following `forEach` before we release 1.6.0\n    // The component-router@0.2.0 looks for the annotations on the controller constructor\n    // Nothing in AngularJS looks for annotations on the factory function but we can't remove\n    // it from 1.5.x yet.\n\n    // Copy any annotation properties (starting with $) over to the factory and controller constructor functions\n    // These could be used by libraries such as the new component router\n    forEach(options, function(val, key) {\n      if (key.charAt(0) === '$') {\n        factory[key] = val;\n        // Don't try to copy over annotations to named controller\n        if (isFunction(controller)) controller[key] = val;\n      }\n    });\n\n    factory.$inject = ['$injector'];\n\n    return this.directive(name, factory);\n  };\n\n\n  /**\n   * @ngdoc method\n   * @name $compileProvider#aHrefSanitizationTrustedUrlList\n   * @kind function\n   *\n   * @description\n   * Retrieves or overrides the default regular expression that is used for determining trusted safe\n   * urls during a[href] sanitization.\n   *\n   * The sanitization is a security measure aimed at preventing XSS attacks via html links.\n   *\n   * Any url about to be assigned to a[href] via data-binding is first normalized and turned into\n   * an absolute url. Afterwards, the url is matched against the `aHrefSanitizationTrustedUrlList`\n   * regular expression. If a match is found, the original url is written into the dom. Otherwise,\n   * the absolute url is prefixed with `'unsafe:'` string and only then is it written into the DOM.\n   *\n   * @param {RegExp=} regexp New regexp to trust urls with.\n   * @returns {RegExp|ng.$compileProvider} Current RegExp if called without value or self for\n   *    chaining otherwise.\n   */\n  this.aHrefSanitizationTrustedUrlList = function(regexp) {\n    if (isDefined(regexp)) {\n      $$sanitizeUriProvider.aHrefSanitizationTrustedUrlList(regexp);\n      return this;\n    } else {\n      return $$sanitizeUriProvider.aHrefSanitizationTrustedUrlList();\n    }\n  };\n\n\n  /**\n   * @ngdoc method\n   * @name $compileProvider#aHrefSanitizationWhitelist\n   * @kind function\n   *\n   * @deprecated\n   * sinceVersion=\"1.8.1\"\n   *\n   * This method is deprecated. Use {@link $compileProvider#aHrefSanitizationTrustedUrlList\n   * aHrefSanitizationTrustedUrlList} instead.\n   */\n  Object.defineProperty(this, 'aHrefSanitizationWhitelist', {\n    get: function() {\n      return this.aHrefSanitizationTrustedUrlList;\n    },\n    set: function(value) {\n      this.aHrefSanitizationTrustedUrlList = value;\n    }\n  });\n\n\n  /**\n   * @ngdoc method\n   * @name $compileProvider#imgSrcSanitizationTrustedUrlList\n   * @kind function\n   *\n   * @description\n   * Retrieves or overrides the default regular expression that is used for determining trusted safe\n   * urls during img[src] sanitization.\n   *\n   * The sanitization is a security measure aimed at prevent XSS attacks via html links.\n   *\n   * Any url about to be assigned to img[src] via data-binding is first normalized and turned into\n   * an absolute url. Afterwards, the url is matched against the `imgSrcSanitizationTrustedUrlList`\n   * regular expression. If a match is found, the original url is written into the dom. Otherwise,\n   * the absolute url is prefixed with `'unsafe:'` string and only then is it written into the DOM.\n   *\n   * @param {RegExp=} regexp New regexp to trust urls with.\n   * @returns {RegExp|ng.$compileProvider} Current RegExp if called without value or self for\n   *    chaining otherwise.\n   */\n  this.imgSrcSanitizationTrustedUrlList = function(regexp) {\n    if (isDefined(regexp)) {\n      $$sanitizeUriProvider.imgSrcSanitizationTrustedUrlList(regexp);\n      return this;\n    } else {\n      return $$sanitizeUriProvider.imgSrcSanitizationTrustedUrlList();\n    }\n  };\n\n\n  /**\n   * @ngdoc method\n   * @name $compileProvider#imgSrcSanitizationWhitelist\n   * @kind function\n   *\n   * @deprecated\n   * sinceVersion=\"1.8.1\"\n   *\n   * This method is deprecated. Use {@link $compileProvider#imgSrcSanitizationTrustedUrlList\n   * imgSrcSanitizationTrustedUrlList} instead.\n   */\n  Object.defineProperty(this, 'imgSrcSanitizationWhitelist', {\n    get: function() {\n      return this.imgSrcSanitizationTrustedUrlList;\n    },\n    set: function(value) {\n      this.imgSrcSanitizationTrustedUrlList = value;\n    }\n  });\n\n  /**\n   * @ngdoc method\n   * @name  $compileProvider#debugInfoEnabled\n   *\n   * @param {boolean=} enabled update the debugInfoEnabled state if provided, otherwise just return the\n   * current debugInfoEnabled state\n   * @returns {*} current value if used as getter or itself (chaining) if used as setter\n   *\n   * @kind function\n   *\n   * @description\n   * Call this method to enable/disable various debug runtime information in the compiler such as adding\n   * binding information and a reference to the current scope on to DOM elements.\n   * If enabled, the compiler will add the following to DOM elements that have been bound to the scope\n   * * `ng-binding` CSS class\n   * * `ng-scope` and `ng-isolated-scope` CSS classes\n   * * `$binding` data property containing an array of the binding expressions\n   * * Data properties used by the {@link angular.element#methods `scope()`/`isolateScope()` methods} to return\n   *   the element's scope.\n   * * Placeholder comments will contain information about what directive and binding caused the placeholder.\n   *   E.g. `<!-- ngIf: shouldShow() -->`.\n   *\n   * You may want to disable this in production for a significant performance boost. See\n   * {@link guide/production#disabling-debug-data Disabling Debug Data} for more.\n   *\n   * The default value is true.\n   */\n  var debugInfoEnabled = true;\n  this.debugInfoEnabled = function(enabled) {\n    if (isDefined(enabled)) {\n      debugInfoEnabled = enabled;\n      return this;\n    }\n    return debugInfoEnabled;\n  };\n\n  /**\n   * @ngdoc method\n   * @name  $compileProvider#strictComponentBindingsEnabled\n   *\n   * @param {boolean=} enabled update the strictComponentBindingsEnabled state if provided,\n   * otherwise return the current strictComponentBindingsEnabled state.\n   * @returns {*} current value if used as getter or itself (chaining) if used as setter\n   *\n   * @kind function\n   *\n   * @description\n   * Call this method to enable / disable the strict component bindings check. If enabled, the\n   * compiler will enforce that all scope / controller bindings of a\n   * {@link $compileProvider#directive directive} / {@link $compileProvider#component component}\n   * that are not set as optional with `?`, must be provided when the directive is instantiated.\n   * If not provided, the compiler will throw the\n   * {@link error/$compile/missingattr $compile:missingattr error}.\n   *\n   * The default value is false.\n   */\n  var strictComponentBindingsEnabled = false;\n  this.strictComponentBindingsEnabled = function(enabled) {\n    if (isDefined(enabled)) {\n      strictComponentBindingsEnabled = enabled;\n      return this;\n    }\n    return strictComponentBindingsEnabled;\n  };\n\n  var TTL = 10;\n  /**\n   * @ngdoc method\n   * @name $compileProvider#onChangesTtl\n   * @description\n   *\n   * Sets the number of times `$onChanges` hooks can trigger new changes before giving up and\n   * assuming that the model is unstable.\n   *\n   * The current default is 10 iterations.\n   *\n   * In complex applications it's possible that dependencies between `$onChanges` hooks and bindings will result\n   * in several iterations of calls to these hooks. However if an application needs more than the default 10\n   * iterations to stabilize then you should investigate what is causing the model to continuously change during\n   * the `$onChanges` hook execution.\n   *\n   * Increasing the TTL could have performance implications, so you should not change it without proper justification.\n   *\n   * @param {number} limit The number of `$onChanges` hook iterations.\n   * @returns {number|object} the current limit (or `this` if called as a setter for chaining)\n   */\n  this.onChangesTtl = function(value) {\n    if (arguments.length) {\n      TTL = value;\n      return this;\n    }\n    return TTL;\n  };\n\n  var commentDirectivesEnabledConfig = true;\n  /**\n   * @ngdoc method\n   * @name $compileProvider#commentDirectivesEnabled\n   * @description\n   *\n   * It indicates to the compiler\n   * whether or not directives on comments should be compiled.\n   * Defaults to `true`.\n   *\n   * Calling this function with false disables the compilation of directives\n   * on comments for the whole application.\n   * This results in a compilation performance gain,\n   * as the compiler doesn't have to check comments when looking for directives.\n   * This should however only be used if you are sure that no comment directives are used in\n   * the application (including any 3rd party directives).\n   *\n   * @param {boolean} enabled `false` if the compiler may ignore directives on comments\n   * @returns {boolean|object} the current value (or `this` if called as a setter for chaining)\n   */\n  this.commentDirectivesEnabled = function(value) {\n    if (arguments.length) {\n      commentDirectivesEnabledConfig = value;\n      return this;\n    }\n    return commentDirectivesEnabledConfig;\n  };\n\n\n  var cssClassDirectivesEnabledConfig = true;\n  /**\n   * @ngdoc method\n   * @name $compileProvider#cssClassDirectivesEnabled\n   * @description\n   *\n   * It indicates to the compiler\n   * whether or not directives on element classes should be compiled.\n   * Defaults to `true`.\n   *\n   * Calling this function with false disables the compilation of directives\n   * on element classes for the whole application.\n   * This results in a compilation performance gain,\n   * as the compiler doesn't have to check element classes when looking for directives.\n   * This should however only be used if you are sure that no class directives are used in\n   * the application (including any 3rd party directives).\n   *\n   * @param {boolean} enabled `false` if the compiler may ignore directives on element classes\n   * @returns {boolean|object} the current value (or `this` if called as a setter for chaining)\n   */\n  this.cssClassDirectivesEnabled = function(value) {\n    if (arguments.length) {\n      cssClassDirectivesEnabledConfig = value;\n      return this;\n    }\n    return cssClassDirectivesEnabledConfig;\n  };\n\n\n  /**\n   * The security context of DOM Properties.\n   * @private\n   */\n  var PROP_CONTEXTS = createMap();\n\n  /**\n   * @ngdoc method\n   * @name $compileProvider#addPropertySecurityContext\n   * @description\n   *\n   * Defines the security context for DOM properties bound by ng-prop-*.\n   *\n   * @param {string} elementName The element name or '*' to match any element.\n   * @param {string} propertyName The DOM property name.\n   * @param {string} ctx The {@link $sce} security context in which this value is safe for use, e.g. `$sce.URL`\n   * @returns {object} `this` for chaining\n   */\n  this.addPropertySecurityContext = function(elementName, propertyName, ctx) {\n    var key = (elementName.toLowerCase() + '|' + propertyName.toLowerCase());\n\n    if (key in PROP_CONTEXTS && PROP_CONTEXTS[key] !== ctx) {\n      throw $compileMinErr('ctxoverride', 'Property context \\'{0}.{1}\\' already set to \\'{2}\\', cannot override to \\'{3}\\'.', elementName, propertyName, PROP_CONTEXTS[key], ctx);\n    }\n\n    PROP_CONTEXTS[key] = ctx;\n    return this;\n  };\n\n  /* Default property contexts.\n   *\n   * Copy of https://github.com/angular/angular/blob/6.0.6/packages/compiler/src/schema/dom_security_schema.ts#L31-L58\n   * Changing:\n   * - SecurityContext.* => SCE_CONTEXTS/$sce.*\n   * - STYLE => CSS\n   * - various URL => MEDIA_URL\n   * - *|formAction, form|action URL => RESOURCE_URL (like the attribute)\n   */\n  (function registerNativePropertyContexts() {\n    function registerContext(ctx, values) {\n      forEach(values, function(v) { PROP_CONTEXTS[v.toLowerCase()] = ctx; });\n    }\n\n    registerContext(SCE_CONTEXTS.HTML, [\n      'iframe|srcdoc',\n      '*|innerHTML',\n      '*|outerHTML'\n    ]);\n    registerContext(SCE_CONTEXTS.CSS, ['*|style']);\n    registerContext(SCE_CONTEXTS.URL, [\n      'area|href',       'area|ping',\n      'a|href',          'a|ping',\n      'blockquote|cite',\n      'body|background',\n      'del|cite',\n      'input|src',\n      'ins|cite',\n      'q|cite'\n    ]);\n    registerContext(SCE_CONTEXTS.MEDIA_URL, [\n      'audio|src',\n      'img|src',    'img|srcset',\n      'source|src', 'source|srcset',\n      'track|src',\n      'video|src',  'video|poster'\n    ]);\n    registerContext(SCE_CONTEXTS.RESOURCE_URL, [\n      '*|formAction',\n      'applet|code',      'applet|codebase',\n      'base|href',\n      'embed|src',\n      'frame|src',\n      'form|action',\n      'head|profile',\n      'html|manifest',\n      'iframe|src',\n      'link|href',\n      'media|src',\n      'object|codebase',  'object|data',\n      'script|src'\n    ]);\n  })();\n\n\n  this.$get = [\n            '$injector', '$interpolate', '$exceptionHandler', '$templateRequest', '$parse',\n            '$controller', '$rootScope', '$sce', '$animate',\n    function($injector,   $interpolate,   $exceptionHandler,   $templateRequest,   $parse,\n             $controller,   $rootScope,   $sce,   $animate) {\n\n    var SIMPLE_ATTR_NAME = /^\\w/;\n    var specialAttrHolder = window.document.createElement('div');\n\n\n    var commentDirectivesEnabled = commentDirectivesEnabledConfig;\n    var cssClassDirectivesEnabled = cssClassDirectivesEnabledConfig;\n\n\n    var onChangesTtl = TTL;\n    // The onChanges hooks should all be run together in a single digest\n    // When changes occur, the call to trigger their hooks will be added to this queue\n    var onChangesQueue;\n\n    // This function is called in a $$postDigest to trigger all the onChanges hooks in a single digest\n    function flushOnChangesQueue() {\n      try {\n        if (!(--onChangesTtl)) {\n          // We have hit the TTL limit so reset everything\n          onChangesQueue = undefined;\n          throw $compileMinErr('infchng', '{0} $onChanges() iterations reached. Aborting!\\n', TTL);\n        }\n        // We must run this hook in an apply since the $$postDigest runs outside apply\n        $rootScope.$apply(function() {\n          for (var i = 0, ii = onChangesQueue.length; i < ii; ++i) {\n            try {\n              onChangesQueue[i]();\n            } catch (e) {\n              $exceptionHandler(e);\n            }\n          }\n          // Reset the queue to trigger a new schedule next time there is a change\n          onChangesQueue = undefined;\n        });\n      } finally {\n        onChangesTtl++;\n      }\n    }\n\n\n    function sanitizeSrcset(value, invokeType) {\n      if (!value) {\n        return value;\n      }\n      if (!isString(value)) {\n        throw $compileMinErr('srcset', 'Can\\'t pass trusted values to `{0}`: \"{1}\"', invokeType, value.toString());\n      }\n\n      // Such values are a bit too complex to handle automatically inside $sce.\n      // Instead, we sanitize each of the URIs individually, which works, even dynamically.\n\n      // It's not possible to work around this using `$sce.trustAsMediaUrl`.\n      // If you want to programmatically set explicitly trusted unsafe URLs, you should use\n      // `$sce.trustAsHtml` on the whole `img` tag and inject it into the DOM using the\n      // `ng-bind-html` directive.\n\n      var result = '';\n\n      // first check if there are spaces because it's not the same pattern\n      var trimmedSrcset = trim(value);\n      //                (   999x   ,|   999w   ,|   ,|,   )\n      var srcPattern = /(\\s+\\d+x\\s*,|\\s+\\d+w\\s*,|\\s+,|,\\s+)/;\n      var pattern = /\\s/.test(trimmedSrcset) ? srcPattern : /(,)/;\n\n      // split srcset into tuple of uri and descriptor except for the last item\n      var rawUris = trimmedSrcset.split(pattern);\n\n      // for each tuples\n      var nbrUrisWith2parts = Math.floor(rawUris.length / 2);\n      for (var i = 0; i < nbrUrisWith2parts; i++) {\n        var innerIdx = i * 2;\n        // sanitize the uri\n        result += $sce.getTrustedMediaUrl(trim(rawUris[innerIdx]));\n        // add the descriptor\n        result += ' ' + trim(rawUris[innerIdx + 1]);\n      }\n\n      // split the last item into uri and descriptor\n      var lastTuple = trim(rawUris[i * 2]).split(/\\s/);\n\n      // sanitize the last uri\n      result += $sce.getTrustedMediaUrl(trim(lastTuple[0]));\n\n      // and add the last descriptor if any\n      if (lastTuple.length === 2) {\n        result += (' ' + trim(lastTuple[1]));\n      }\n      return result;\n    }\n\n\n    function Attributes(element, attributesToCopy) {\n      if (attributesToCopy) {\n        var keys = Object.keys(attributesToCopy);\n        var i, l, key;\n\n        for (i = 0, l = keys.length; i < l; i++) {\n          key = keys[i];\n          this[key] = attributesToCopy[key];\n        }\n      } else {\n        this.$attr = {};\n      }\n\n      this.$$element = element;\n    }\n\n    Attributes.prototype = {\n      /**\n       * @ngdoc method\n       * @name $compile.directive.Attributes#$normalize\n       * @kind function\n       *\n       * @description\n       * Converts an attribute name (e.g. dash/colon/underscore-delimited string, optionally prefixed with `x-` or\n       * `data-`) to its normalized, camelCase form.\n       *\n       * Also there is special case for Moz prefix starting with upper case letter.\n       *\n       * For further information check out the guide on {@link guide/directive#matching-directives Matching Directives}\n       *\n       * @param {string} name Name to normalize\n       */\n      $normalize: directiveNormalize,\n\n\n      /**\n       * @ngdoc method\n       * @name $compile.directive.Attributes#$addClass\n       * @kind function\n       *\n       * @description\n       * Adds the CSS class value specified by the classVal parameter to the element. If animations\n       * are enabled then an animation will be triggered for the class addition.\n       *\n       * @param {string} classVal The className value that will be added to the element\n       */\n      $addClass: function(classVal) {\n        if (classVal && classVal.length > 0) {\n          $animate.addClass(this.$$element, classVal);\n        }\n      },\n\n      /**\n       * @ngdoc method\n       * @name $compile.directive.Attributes#$removeClass\n       * @kind function\n       *\n       * @description\n       * Removes the CSS class value specified by the classVal parameter from the element. If\n       * animations are enabled then an animation will be triggered for the class removal.\n       *\n       * @param {string} classVal The className value that will be removed from the element\n       */\n      $removeClass: function(classVal) {\n        if (classVal && classVal.length > 0) {\n          $animate.removeClass(this.$$element, classVal);\n        }\n      },\n\n      /**\n       * @ngdoc method\n       * @name $compile.directive.Attributes#$updateClass\n       * @kind function\n       *\n       * @description\n       * Adds and removes the appropriate CSS class values to the element based on the difference\n       * between the new and old CSS class values (specified as newClasses and oldClasses).\n       *\n       * @param {string} newClasses The current CSS className value\n       * @param {string} oldClasses The former CSS className value\n       */\n      $updateClass: function(newClasses, oldClasses) {\n        var toAdd = tokenDifference(newClasses, oldClasses);\n        if (toAdd && toAdd.length) {\n          $animate.addClass(this.$$element, toAdd);\n        }\n\n        var toRemove = tokenDifference(oldClasses, newClasses);\n        if (toRemove && toRemove.length) {\n          $animate.removeClass(this.$$element, toRemove);\n        }\n      },\n\n      /**\n       * Set a normalized attribute on the element in a way such that all directives\n       * can share the attribute. This function properly handles boolean attributes.\n       * @param {string} key Normalized key. (ie ngAttribute)\n       * @param {string|boolean} value The value to set. If `null` attribute will be deleted.\n       * @param {boolean=} writeAttr If false, does not write the value to DOM element attribute.\n       *     Defaults to true.\n       * @param {string=} attrName Optional none normalized name. Defaults to key.\n       */\n      $set: function(key, value, writeAttr, attrName) {\n        // TODO: decide whether or not to throw an error if \"class\"\n        // is set through this function since it may cause $updateClass to\n        // become unstable.\n\n        var node = this.$$element[0],\n            booleanKey = getBooleanAttrName(node, key),\n            aliasedKey = getAliasedAttrName(key),\n            observer = key,\n            nodeName;\n\n        if (booleanKey) {\n          this.$$element.prop(key, value);\n          attrName = booleanKey;\n        } else if (aliasedKey) {\n          this[aliasedKey] = value;\n          observer = aliasedKey;\n        }\n\n        this[key] = value;\n\n        // translate normalized key to actual key\n        if (attrName) {\n          this.$attr[key] = attrName;\n        } else {\n          attrName = this.$attr[key];\n          if (!attrName) {\n            this.$attr[key] = attrName = snake_case(key, '-');\n          }\n        }\n\n        nodeName = nodeName_(this.$$element);\n\n        // Sanitize img[srcset] values.\n        if (nodeName === 'img' && key === 'srcset') {\n          this[key] = value = sanitizeSrcset(value, '$set(\\'srcset\\', value)');\n        }\n\n        if (writeAttr !== false) {\n          if (value === null || isUndefined(value)) {\n            this.$$element.removeAttr(attrName);\n          } else {\n            if (SIMPLE_ATTR_NAME.test(attrName)) {\n              // jQuery skips special boolean attrs treatment in XML nodes for\n              // historical reasons and hence AngularJS cannot freely call\n              // `.attr(attrName, false) with such attributes. To avoid issues\n              // in XHTML, call `removeAttr` in such cases instead.\n              // See https://github.com/jquery/jquery/issues/4249\n              if (booleanKey && value === false) {\n                this.$$element.removeAttr(attrName);\n              } else {\n                this.$$element.attr(attrName, value);\n              }\n            } else {\n              setSpecialAttr(this.$$element[0], attrName, value);\n            }\n          }\n        }\n\n        // fire observers\n        var $$observers = this.$$observers;\n        if ($$observers) {\n          forEach($$observers[observer], function(fn) {\n            try {\n              fn(value);\n            } catch (e) {\n              $exceptionHandler(e);\n            }\n          });\n        }\n      },\n\n\n      /**\n       * @ngdoc method\n       * @name $compile.directive.Attributes#$observe\n       * @kind function\n       *\n       * @description\n       * Observes an interpolated attribute.\n       *\n       * The observer function will be invoked once during the next `$digest` following\n       * compilation. The observer is then invoked whenever the interpolated value\n       * changes.\n       *\n       * @param {string} key Normalized key. (ie ngAttribute) .\n       * @param {function(interpolatedValue)} fn Function that will be called whenever\n                the interpolated value of the attribute changes.\n       *        See the {@link guide/interpolation#how-text-and-attribute-bindings-work Interpolation\n       *        guide} for more info.\n       * @returns {function()} Returns a deregistration function for this observer.\n       */\n      $observe: function(key, fn) {\n        var attrs = this,\n            $$observers = (attrs.$$observers || (attrs.$$observers = createMap())),\n            listeners = ($$observers[key] || ($$observers[key] = []));\n\n        listeners.push(fn);\n        $rootScope.$evalAsync(function() {\n          if (!listeners.$$inter && attrs.hasOwnProperty(key) && !isUndefined(attrs[key])) {\n            // no one registered attribute interpolation function, so lets call it manually\n            fn(attrs[key]);\n          }\n        });\n\n        return function() {\n          arrayRemove(listeners, fn);\n        };\n      }\n    };\n\n    function setSpecialAttr(element, attrName, value) {\n      // Attributes names that do not start with letters (such as `(click)`) cannot be set using `setAttribute`\n      // so we have to jump through some hoops to get such an attribute\n      // https://github.com/angular/angular.js/pull/13318\n      specialAttrHolder.innerHTML = '<span ' + attrName + '>';\n      var attributes = specialAttrHolder.firstChild.attributes;\n      var attribute = attributes[0];\n      // We have to remove the attribute from its container element before we can add it to the destination element\n      attributes.removeNamedItem(attribute.name);\n      attribute.value = value;\n      element.attributes.setNamedItem(attribute);\n    }\n\n    function safeAddClass($element, className) {\n      try {\n        $element.addClass(className);\n      } catch (e) {\n        // ignore, since it means that we are trying to set class on\n        // SVG element, where class name is read-only.\n      }\n    }\n\n\n    var startSymbol = $interpolate.startSymbol(),\n        endSymbol = $interpolate.endSymbol(),\n        denormalizeTemplate = (startSymbol === '{{' && endSymbol  === '}}')\n            ? identity\n            : function denormalizeTemplate(template) {\n              return template.replace(/\\{\\{/g, startSymbol).replace(/}}/g, endSymbol);\n        },\n        NG_PREFIX_BINDING = /^ng(Attr|Prop|On)([A-Z].*)$/;\n    var MULTI_ELEMENT_DIR_RE = /^(.+)Start$/;\n\n    compile.$$addBindingInfo = debugInfoEnabled ? function $$addBindingInfo($element, binding) {\n      var bindings = $element.data('$binding') || [];\n\n      if (isArray(binding)) {\n        bindings = bindings.concat(binding);\n      } else {\n        bindings.push(binding);\n      }\n\n      $element.data('$binding', bindings);\n    } : noop;\n\n    compile.$$addBindingClass = debugInfoEnabled ? function $$addBindingClass($element) {\n      safeAddClass($element, 'ng-binding');\n    } : noop;\n\n    compile.$$addScopeInfo = debugInfoEnabled ? function $$addScopeInfo($element, scope, isolated, noTemplate) {\n      var dataName = isolated ? (noTemplate ? '$isolateScopeNoTemplate' : '$isolateScope') : '$scope';\n      $element.data(dataName, scope);\n    } : noop;\n\n    compile.$$addScopeClass = debugInfoEnabled ? function $$addScopeClass($element, isolated) {\n      safeAddClass($element, isolated ? 'ng-isolate-scope' : 'ng-scope');\n    } : noop;\n\n    compile.$$createComment = function(directiveName, comment) {\n      var content = '';\n      if (debugInfoEnabled) {\n        content = ' ' + (directiveName || '') + ': ';\n        if (comment) content += comment + ' ';\n      }\n      return window.document.createComment(content);\n    };\n\n    return compile;\n\n    //================================\n\n    function compile($compileNodes, transcludeFn, maxPriority, ignoreDirective,\n                        previousCompileContext) {\n      if (!($compileNodes instanceof jqLite)) {\n        // jquery always rewraps, whereas we need to preserve the original selector so that we can\n        // modify it.\n        $compileNodes = jqLite($compileNodes);\n      }\n      var compositeLinkFn =\n              compileNodes($compileNodes, transcludeFn, $compileNodes,\n                           maxPriority, ignoreDirective, previousCompileContext);\n      compile.$$addScopeClass($compileNodes);\n      var namespace = null;\n      return function publicLinkFn(scope, cloneConnectFn, options) {\n        if (!$compileNodes) {\n          throw $compileMinErr('multilink', 'This element has already been linked.');\n        }\n        assertArg(scope, 'scope');\n\n        if (previousCompileContext && previousCompileContext.needsNewScope) {\n          // A parent directive did a replace and a directive on this element asked\n          // for transclusion, which caused us to lose a layer of element on which\n          // we could hold the new transclusion scope, so we will create it manually\n          // here.\n          scope = scope.$parent.$new();\n        }\n\n        options = options || {};\n        var parentBoundTranscludeFn = options.parentBoundTranscludeFn,\n          transcludeControllers = options.transcludeControllers,\n          futureParentElement = options.futureParentElement;\n\n        // When `parentBoundTranscludeFn` is passed, it is a\n        // `controllersBoundTransclude` function (it was previously passed\n        // as `transclude` to directive.link) so we must unwrap it to get\n        // its `boundTranscludeFn`\n        if (parentBoundTranscludeFn && parentBoundTranscludeFn.$$boundTransclude) {\n          parentBoundTranscludeFn = parentBoundTranscludeFn.$$boundTransclude;\n        }\n\n        if (!namespace) {\n          namespace = detectNamespaceForChildElements(futureParentElement);\n        }\n        var $linkNode;\n        if (namespace !== 'html') {\n          // When using a directive with replace:true and templateUrl the $compileNodes\n          // (or a child element inside of them)\n          // might change, so we need to recreate the namespace adapted compileNodes\n          // for call to the link function.\n          // Note: This will already clone the nodes...\n          $linkNode = jqLite(\n            wrapTemplate(namespace, jqLite('<div></div>').append($compileNodes).html())\n          );\n        } else if (cloneConnectFn) {\n          // important!!: we must call our jqLite.clone() since the jQuery one is trying to be smart\n          // and sometimes changes the structure of the DOM.\n          $linkNode = JQLitePrototype.clone.call($compileNodes);\n        } else {\n          $linkNode = $compileNodes;\n        }\n\n        if (transcludeControllers) {\n          for (var controllerName in transcludeControllers) {\n            $linkNode.data('$' + controllerName + 'Controller', transcludeControllers[controllerName].instance);\n          }\n        }\n\n        compile.$$addScopeInfo($linkNode, scope);\n\n        if (cloneConnectFn) cloneConnectFn($linkNode, scope);\n        if (compositeLinkFn) compositeLinkFn(scope, $linkNode, $linkNode, parentBoundTranscludeFn);\n\n        if (!cloneConnectFn) {\n          $compileNodes = compositeLinkFn = null;\n        }\n        return $linkNode;\n      };\n    }\n\n    function detectNamespaceForChildElements(parentElement) {\n      // TODO: Make this detect MathML as well...\n      var node = parentElement && parentElement[0];\n      if (!node) {\n        return 'html';\n      } else {\n        return nodeName_(node) !== 'foreignobject' && toString.call(node).match(/SVG/) ? 'svg' : 'html';\n      }\n    }\n\n    /**\n     * Compile function matches each node in nodeList against the directives. Once all directives\n     * for a particular node are collected their compile functions are executed. The compile\n     * functions return values - the linking functions - are combined into a composite linking\n     * function, which is the a linking function for the node.\n     *\n     * @param {NodeList} nodeList an array of nodes or NodeList to compile\n     * @param {function(angular.Scope, cloneAttachFn=)} transcludeFn A linking function, where the\n     *        scope argument is auto-generated to the new child of the transcluded parent scope.\n     * @param {DOMElement=} $rootElement If the nodeList is the root of the compilation tree then\n     *        the rootElement must be set the jqLite collection of the compile root. This is\n     *        needed so that the jqLite collection items can be replaced with widgets.\n     * @param {number=} maxPriority Max directive priority.\n     * @returns {Function} A composite linking function of all of the matched directives or null.\n     */\n    function compileNodes(nodeList, transcludeFn, $rootElement, maxPriority, ignoreDirective,\n                            previousCompileContext) {\n      var linkFns = [],\n          // `nodeList` can be either an element's `.childNodes` (live NodeList)\n          // or a jqLite/jQuery collection or an array\n          notLiveList = isArray(nodeList) || (nodeList instanceof jqLite),\n          attrs, directives, nodeLinkFn, childNodes, childLinkFn, linkFnFound, nodeLinkFnFound;\n\n\n      for (var i = 0; i < nodeList.length; i++) {\n        attrs = new Attributes();\n\n        // Support: IE 11 only\n        // Workaround for #11781 and #14924\n        if (msie === 11) {\n          mergeConsecutiveTextNodes(nodeList, i, notLiveList);\n        }\n\n        // We must always refer to `nodeList[i]` hereafter,\n        // since the nodes can be replaced underneath us.\n        directives = collectDirectives(nodeList[i], [], attrs, i === 0 ? maxPriority : undefined,\n                                        ignoreDirective);\n\n        nodeLinkFn = (directives.length)\n            ? applyDirectivesToNode(directives, nodeList[i], attrs, transcludeFn, $rootElement,\n                                      null, [], [], previousCompileContext)\n            : null;\n\n        if (nodeLinkFn && nodeLinkFn.scope) {\n          compile.$$addScopeClass(attrs.$$element);\n        }\n\n        childLinkFn = (nodeLinkFn && nodeLinkFn.terminal ||\n                      !(childNodes = nodeList[i].childNodes) ||\n                      !childNodes.length)\n            ? null\n            : compileNodes(childNodes,\n                 nodeLinkFn ? (\n                  (nodeLinkFn.transcludeOnThisElement || !nodeLinkFn.templateOnThisElement)\n                     && nodeLinkFn.transclude) : transcludeFn);\n\n        if (nodeLinkFn || childLinkFn) {\n          linkFns.push(i, nodeLinkFn, childLinkFn);\n          linkFnFound = true;\n          nodeLinkFnFound = nodeLinkFnFound || nodeLinkFn;\n        }\n\n        //use the previous context only for the first element in the virtual group\n        previousCompileContext = null;\n      }\n\n      // return a linking function if we have found anything, null otherwise\n      return linkFnFound ? compositeLinkFn : null;\n\n      function compositeLinkFn(scope, nodeList, $rootElement, parentBoundTranscludeFn) {\n        var nodeLinkFn, childLinkFn, node, childScope, i, ii, idx, childBoundTranscludeFn;\n        var stableNodeList;\n\n\n        if (nodeLinkFnFound) {\n          // copy nodeList so that if a nodeLinkFn removes or adds an element at this DOM level our\n          // offsets don't get screwed up\n          var nodeListLength = nodeList.length;\n          stableNodeList = new Array(nodeListLength);\n\n          // create a sparse array by only copying the elements which have a linkFn\n          for (i = 0; i < linkFns.length; i += 3) {\n            idx = linkFns[i];\n            stableNodeList[idx] = nodeList[idx];\n          }\n        } else {\n          stableNodeList = nodeList;\n        }\n\n        for (i = 0, ii = linkFns.length; i < ii;) {\n          node = stableNodeList[linkFns[i++]];\n          nodeLinkFn = linkFns[i++];\n          childLinkFn = linkFns[i++];\n\n          if (nodeLinkFn) {\n            if (nodeLinkFn.scope) {\n              childScope = scope.$new();\n              compile.$$addScopeInfo(jqLite(node), childScope);\n            } else {\n              childScope = scope;\n            }\n\n            if (nodeLinkFn.transcludeOnThisElement) {\n              childBoundTranscludeFn = createBoundTranscludeFn(\n                  scope, nodeLinkFn.transclude, parentBoundTranscludeFn);\n\n            } else if (!nodeLinkFn.templateOnThisElement && parentBoundTranscludeFn) {\n              childBoundTranscludeFn = parentBoundTranscludeFn;\n\n            } else if (!parentBoundTranscludeFn && transcludeFn) {\n              childBoundTranscludeFn = createBoundTranscludeFn(scope, transcludeFn);\n\n            } else {\n              childBoundTranscludeFn = null;\n            }\n\n            nodeLinkFn(childLinkFn, childScope, node, $rootElement, childBoundTranscludeFn);\n\n          } else if (childLinkFn) {\n            childLinkFn(scope, node.childNodes, undefined, parentBoundTranscludeFn);\n          }\n        }\n      }\n    }\n\n    function mergeConsecutiveTextNodes(nodeList, idx, notLiveList) {\n      var node = nodeList[idx];\n      var parent = node.parentNode;\n      var sibling;\n\n      if (node.nodeType !== NODE_TYPE_TEXT) {\n        return;\n      }\n\n      while (true) {\n        sibling = parent ? node.nextSibling : nodeList[idx + 1];\n        if (!sibling || sibling.nodeType !== NODE_TYPE_TEXT) {\n          break;\n        }\n\n        node.nodeValue = node.nodeValue + sibling.nodeValue;\n\n        if (sibling.parentNode) {\n          sibling.parentNode.removeChild(sibling);\n        }\n        if (notLiveList && sibling === nodeList[idx + 1]) {\n          nodeList.splice(idx + 1, 1);\n        }\n      }\n    }\n\n    function createBoundTranscludeFn(scope, transcludeFn, previousBoundTranscludeFn) {\n      function boundTranscludeFn(transcludedScope, cloneFn, controllers, futureParentElement, containingScope) {\n\n        if (!transcludedScope) {\n          transcludedScope = scope.$new(false, containingScope);\n          transcludedScope.$$transcluded = true;\n        }\n\n        return transcludeFn(transcludedScope, cloneFn, {\n          parentBoundTranscludeFn: previousBoundTranscludeFn,\n          transcludeControllers: controllers,\n          futureParentElement: futureParentElement\n        });\n      }\n\n      // We need  to attach the transclusion slots onto the `boundTranscludeFn`\n      // so that they are available inside the `controllersBoundTransclude` function\n      var boundSlots = boundTranscludeFn.$$slots = createMap();\n      for (var slotName in transcludeFn.$$slots) {\n        if (transcludeFn.$$slots[slotName]) {\n          boundSlots[slotName] = createBoundTranscludeFn(scope, transcludeFn.$$slots[slotName], previousBoundTranscludeFn);\n        } else {\n          boundSlots[slotName] = null;\n        }\n      }\n\n      return boundTranscludeFn;\n    }\n\n    /**\n     * Looks for directives on the given node and adds them to the directive collection which is\n     * sorted.\n     *\n     * @param node Node to search.\n     * @param directives An array to which the directives are added to. This array is sorted before\n     *        the function returns.\n     * @param attrs The shared attrs object which is used to populate the normalized attributes.\n     * @param {number=} maxPriority Max directive priority.\n     */\n    function collectDirectives(node, directives, attrs, maxPriority, ignoreDirective) {\n      var nodeType = node.nodeType,\n          attrsMap = attrs.$attr,\n          match,\n          nodeName,\n          className;\n\n      switch (nodeType) {\n        case NODE_TYPE_ELEMENT: /* Element */\n\n          nodeName = nodeName_(node);\n\n          // use the node name: <directive>\n          addDirective(directives,\n              directiveNormalize(nodeName), 'E', maxPriority, ignoreDirective);\n\n          // iterate over the attributes\n          for (var attr, name, nName, value, ngPrefixMatch, nAttrs = node.attributes,\n                   j = 0, jj = nAttrs && nAttrs.length; j < jj; j++) {\n            var attrStartName = false;\n            var attrEndName = false;\n\n            var isNgAttr = false, isNgProp = false, isNgEvent = false;\n            var multiElementMatch;\n\n            attr = nAttrs[j];\n            name = attr.name;\n            value = attr.value;\n\n            nName = directiveNormalize(name.toLowerCase());\n\n            // Support ng-attr-*, ng-prop-* and ng-on-*\n            if ((ngPrefixMatch = nName.match(NG_PREFIX_BINDING))) {\n              isNgAttr = ngPrefixMatch[1] === 'Attr';\n              isNgProp = ngPrefixMatch[1] === 'Prop';\n              isNgEvent = ngPrefixMatch[1] === 'On';\n\n              // Normalize the non-prefixed name\n              name = name.replace(PREFIX_REGEXP, '')\n                .toLowerCase()\n                .substr(4 + ngPrefixMatch[1].length).replace(/_(.)/g, function(match, letter) {\n                  return letter.toUpperCase();\n                });\n\n            // Support *-start / *-end multi element directives\n            } else if ((multiElementMatch = nName.match(MULTI_ELEMENT_DIR_RE)) && directiveIsMultiElement(multiElementMatch[1])) {\n              attrStartName = name;\n              attrEndName = name.substr(0, name.length - 5) + 'end';\n              name = name.substr(0, name.length - 6);\n            }\n\n            if (isNgProp || isNgEvent) {\n              attrs[nName] = value;\n              attrsMap[nName] = attr.name;\n\n              if (isNgProp) {\n                addPropertyDirective(node, directives, nName, name);\n              } else {\n                addEventDirective(directives, nName, name);\n              }\n            } else {\n              // Update nName for cases where a prefix was removed\n              // NOTE: the .toLowerCase() is unnecessary and causes https://github.com/angular/angular.js/issues/16624 for ng-attr-*\n              nName = directiveNormalize(name.toLowerCase());\n              attrsMap[nName] = name;\n\n              if (isNgAttr || !attrs.hasOwnProperty(nName)) {\n                attrs[nName] = value;\n                if (getBooleanAttrName(node, nName)) {\n                  attrs[nName] = true; // presence means true\n                }\n              }\n\n              addAttrInterpolateDirective(node, directives, value, nName, isNgAttr);\n              addDirective(directives, nName, 'A', maxPriority, ignoreDirective, attrStartName,\n                            attrEndName);\n            }\n          }\n\n          if (nodeName === 'input' && node.getAttribute('type') === 'hidden') {\n            // Hidden input elements can have strange behaviour when navigating back to the page\n            // This tells the browser not to try to cache and reinstate previous values\n            node.setAttribute('autocomplete', 'off');\n          }\n\n          // use class as directive\n          if (!cssClassDirectivesEnabled) break;\n          className = node.className;\n          if (isObject(className)) {\n              // Maybe SVGAnimatedString\n              className = className.animVal;\n          }\n          if (isString(className) && className !== '') {\n            while ((match = CLASS_DIRECTIVE_REGEXP.exec(className))) {\n              nName = directiveNormalize(match[2]);\n              if (addDirective(directives, nName, 'C', maxPriority, ignoreDirective)) {\n                attrs[nName] = trim(match[3]);\n              }\n              className = className.substr(match.index + match[0].length);\n            }\n          }\n          break;\n        case NODE_TYPE_TEXT: /* Text Node */\n          addTextInterpolateDirective(directives, node.nodeValue);\n          break;\n        case NODE_TYPE_COMMENT: /* Comment */\n          if (!commentDirectivesEnabled) break;\n          collectCommentDirectives(node, directives, attrs, maxPriority, ignoreDirective);\n          break;\n      }\n\n      directives.sort(byPriority);\n      return directives;\n    }\n\n    function collectCommentDirectives(node, directives, attrs, maxPriority, ignoreDirective) {\n      // function created because of performance, try/catch disables\n      // the optimization of the whole function #14848\n      try {\n        var match = COMMENT_DIRECTIVE_REGEXP.exec(node.nodeValue);\n        if (match) {\n          var nName = directiveNormalize(match[1]);\n          if (addDirective(directives, nName, 'M', maxPriority, ignoreDirective)) {\n            attrs[nName] = trim(match[2]);\n          }\n        }\n      } catch (e) {\n        // turns out that under some circumstances IE9 throws errors when one attempts to read\n        // comment's node value.\n        // Just ignore it and continue. (Can't seem to reproduce in test case.)\n      }\n    }\n\n    /**\n     * Given a node with a directive-start it collects all of the siblings until it finds\n     * directive-end.\n     * @param node\n     * @param attrStart\n     * @param attrEnd\n     * @returns {*}\n     */\n    function groupScan(node, attrStart, attrEnd) {\n      var nodes = [];\n      var depth = 0;\n      if (attrStart && node.hasAttribute && node.hasAttribute(attrStart)) {\n        do {\n          if (!node) {\n            throw $compileMinErr('uterdir',\n                      'Unterminated attribute, found \\'{0}\\' but no matching \\'{1}\\' found.',\n                      attrStart, attrEnd);\n          }\n          if (node.nodeType === NODE_TYPE_ELEMENT) {\n            if (node.hasAttribute(attrStart)) depth++;\n            if (node.hasAttribute(attrEnd)) depth--;\n          }\n          nodes.push(node);\n          node = node.nextSibling;\n        } while (depth > 0);\n      } else {\n        nodes.push(node);\n      }\n\n      return jqLite(nodes);\n    }\n\n    /**\n     * Wrapper for linking function which converts normal linking function into a grouped\n     * linking function.\n     * @param linkFn\n     * @param attrStart\n     * @param attrEnd\n     * @returns {Function}\n     */\n    function groupElementsLinkFnWrapper(linkFn, attrStart, attrEnd) {\n      return function groupedElementsLink(scope, element, attrs, controllers, transcludeFn) {\n        element = groupScan(element[0], attrStart, attrEnd);\n        return linkFn(scope, element, attrs, controllers, transcludeFn);\n      };\n    }\n\n    /**\n     * A function generator that is used to support both eager and lazy compilation\n     * linking function.\n     * @param eager\n     * @param $compileNodes\n     * @param transcludeFn\n     * @param maxPriority\n     * @param ignoreDirective\n     * @param previousCompileContext\n     * @returns {Function}\n     */\n    function compilationGenerator(eager, $compileNodes, transcludeFn, maxPriority, ignoreDirective, previousCompileContext) {\n      var compiled;\n\n      if (eager) {\n        return compile($compileNodes, transcludeFn, maxPriority, ignoreDirective, previousCompileContext);\n      }\n      return /** @this */ function lazyCompilation() {\n        if (!compiled) {\n          compiled = compile($compileNodes, transcludeFn, maxPriority, ignoreDirective, previousCompileContext);\n\n          // Null out all of these references in order to make them eligible for garbage collection\n          // since this is a potentially long lived closure\n          $compileNodes = transcludeFn = previousCompileContext = null;\n        }\n        return compiled.apply(this, arguments);\n      };\n    }\n\n    /**\n     * Once the directives have been collected, their compile functions are executed. This method\n     * is responsible for inlining directive templates as well as terminating the application\n     * of the directives if the terminal directive has been reached.\n     *\n     * @param {Array} directives Array of collected directives to execute their compile function.\n     *        this needs to be pre-sorted by priority order.\n     * @param {Node} compileNode The raw DOM node to apply the compile functions to\n     * @param {Object} templateAttrs The shared attribute function\n     * @param {function(angular.Scope, cloneAttachFn=)} transcludeFn A linking function, where the\n     *                                                  scope argument is auto-generated to the new\n     *                                                  child of the transcluded parent scope.\n     * @param {JQLite} jqCollection If we are working on the root of the compile tree then this\n     *                              argument has the root jqLite array so that we can replace nodes\n     *                              on it.\n     * @param {Object=} originalReplaceDirective An optional directive that will be ignored when\n     *                                           compiling the transclusion.\n     * @param {Array.<Function>} preLinkFns\n     * @param {Array.<Function>} postLinkFns\n     * @param {Object} previousCompileContext Context used for previous compilation of the current\n     *                                        node\n     * @returns {Function} linkFn\n     */\n    function applyDirectivesToNode(directives, compileNode, templateAttrs, transcludeFn,\n                                   jqCollection, originalReplaceDirective, preLinkFns, postLinkFns,\n                                   previousCompileContext) {\n      previousCompileContext = previousCompileContext || {};\n\n      var terminalPriority = -Number.MAX_VALUE,\n          newScopeDirective = previousCompileContext.newScopeDirective,\n          controllerDirectives = previousCompileContext.controllerDirectives,\n          newIsolateScopeDirective = previousCompileContext.newIsolateScopeDirective,\n          templateDirective = previousCompileContext.templateDirective,\n          nonTlbTranscludeDirective = previousCompileContext.nonTlbTranscludeDirective,\n          hasTranscludeDirective = false,\n          hasTemplate = false,\n          hasElementTranscludeDirective = previousCompileContext.hasElementTranscludeDirective,\n          $compileNode = templateAttrs.$$element = jqLite(compileNode),\n          directive,\n          directiveName,\n          $template,\n          replaceDirective = originalReplaceDirective,\n          childTranscludeFn = transcludeFn,\n          linkFn,\n          didScanForMultipleTransclusion = false,\n          mightHaveMultipleTransclusionError = false,\n          directiveValue;\n\n      // executes all directives on the current element\n      for (var i = 0, ii = directives.length; i < ii; i++) {\n        directive = directives[i];\n        var attrStart = directive.$$start;\n        var attrEnd = directive.$$end;\n\n        // collect multiblock sections\n        if (attrStart) {\n          $compileNode = groupScan(compileNode, attrStart, attrEnd);\n        }\n        $template = undefined;\n\n        if (terminalPriority > directive.priority) {\n          break; // prevent further processing of directives\n        }\n\n        directiveValue = directive.scope;\n\n        if (directiveValue) {\n\n          // skip the check for directives with async templates, we'll check the derived sync\n          // directive when the template arrives\n          if (!directive.templateUrl) {\n            if (isObject(directiveValue)) {\n              // This directive is trying to add an isolated scope.\n              // Check that there is no scope of any kind already\n              assertNoDuplicate('new/isolated scope', newIsolateScopeDirective || newScopeDirective,\n                                directive, $compileNode);\n              newIsolateScopeDirective = directive;\n            } else {\n              // This directive is trying to add a child scope.\n              // Check that there is no isolated scope already\n              assertNoDuplicate('new/isolated scope', newIsolateScopeDirective, directive,\n                                $compileNode);\n            }\n          }\n\n          newScopeDirective = newScopeDirective || directive;\n        }\n\n        directiveName = directive.name;\n\n        // If we encounter a condition that can result in transclusion on the directive,\n        // then scan ahead in the remaining directives for others that may cause a multiple\n        // transclusion error to be thrown during the compilation process.  If a matching directive\n        // is found, then we know that when we encounter a transcluded directive, we need to eagerly\n        // compile the `transclude` function rather than doing it lazily in order to throw\n        // exceptions at the correct time\n        if (!didScanForMultipleTransclusion && ((directive.replace && (directive.templateUrl || directive.template))\n            || (directive.transclude && !directive.$$tlb))) {\n                var candidateDirective;\n\n                for (var scanningIndex = i + 1; (candidateDirective = directives[scanningIndex++]);) {\n                    if ((candidateDirective.transclude && !candidateDirective.$$tlb)\n                        || (candidateDirective.replace && (candidateDirective.templateUrl || candidateDirective.template))) {\n                        mightHaveMultipleTransclusionError = true;\n                        break;\n                    }\n                }\n\n                didScanForMultipleTransclusion = true;\n        }\n\n        if (!directive.templateUrl && directive.controller) {\n          controllerDirectives = controllerDirectives || createMap();\n          assertNoDuplicate('\\'' + directiveName + '\\' controller',\n              controllerDirectives[directiveName], directive, $compileNode);\n          controllerDirectives[directiveName] = directive;\n        }\n\n        directiveValue = directive.transclude;\n\n        if (directiveValue) {\n          hasTranscludeDirective = true;\n\n          // Special case ngIf and ngRepeat so that we don't complain about duplicate transclusion.\n          // This option should only be used by directives that know how to safely handle element transclusion,\n          // where the transcluded nodes are added or replaced after linking.\n          if (!directive.$$tlb) {\n            assertNoDuplicate('transclusion', nonTlbTranscludeDirective, directive, $compileNode);\n            nonTlbTranscludeDirective = directive;\n          }\n\n          if (directiveValue === 'element') {\n            hasElementTranscludeDirective = true;\n            terminalPriority = directive.priority;\n            $template = $compileNode;\n            $compileNode = templateAttrs.$$element =\n                jqLite(compile.$$createComment(directiveName, templateAttrs[directiveName]));\n            compileNode = $compileNode[0];\n            replaceWith(jqCollection, sliceArgs($template), compileNode);\n\n            childTranscludeFn = compilationGenerator(mightHaveMultipleTransclusionError, $template, transcludeFn, terminalPriority,\n                                        replaceDirective && replaceDirective.name, {\n                                          // Don't pass in:\n                                          // - controllerDirectives - otherwise we'll create duplicates controllers\n                                          // - newIsolateScopeDirective or templateDirective - combining templates with\n                                          //   element transclusion doesn't make sense.\n                                          //\n                                          // We need only nonTlbTranscludeDirective so that we prevent putting transclusion\n                                          // on the same element more than once.\n                                          nonTlbTranscludeDirective: nonTlbTranscludeDirective\n                                        });\n          } else {\n\n            var slots = createMap();\n\n            if (!isObject(directiveValue)) {\n              $template = jqLite(jqLiteClone(compileNode)).contents();\n            } else {\n\n              // We have transclusion slots,\n              // collect them up, compile them and store their transclusion functions\n              $template = window.document.createDocumentFragment();\n\n              var slotMap = createMap();\n              var filledSlots = createMap();\n\n              // Parse the element selectors\n              forEach(directiveValue, function(elementSelector, slotName) {\n                // If an element selector starts with a ? then it is optional\n                var optional = (elementSelector.charAt(0) === '?');\n                elementSelector = optional ? elementSelector.substring(1) : elementSelector;\n\n                slotMap[elementSelector] = slotName;\n\n                // We explicitly assign `null` since this implies that a slot was defined but not filled.\n                // Later when calling boundTransclusion functions with a slot name we only error if the\n                // slot is `undefined`\n                slots[slotName] = null;\n\n                // filledSlots contains `true` for all slots that are either optional or have been\n                // filled. This is used to check that we have not missed any required slots\n                filledSlots[slotName] = optional;\n              });\n\n              // Add the matching elements into their slot\n              forEach($compileNode.contents(), function(node) {\n                var slotName = slotMap[directiveNormalize(nodeName_(node))];\n                if (slotName) {\n                  filledSlots[slotName] = true;\n                  slots[slotName] = slots[slotName] || window.document.createDocumentFragment();\n                  slots[slotName].appendChild(node);\n                } else {\n                  $template.appendChild(node);\n                }\n              });\n\n              // Check for required slots that were not filled\n              forEach(filledSlots, function(filled, slotName) {\n                if (!filled) {\n                  throw $compileMinErr('reqslot', 'Required transclusion slot `{0}` was not filled.', slotName);\n                }\n              });\n\n              for (var slotName in slots) {\n                if (slots[slotName]) {\n                  // Only define a transclusion function if the slot was filled\n                  var slotCompileNodes = jqLite(slots[slotName].childNodes);\n                  slots[slotName] = compilationGenerator(mightHaveMultipleTransclusionError, slotCompileNodes, transcludeFn);\n                }\n              }\n\n              $template = jqLite($template.childNodes);\n            }\n\n            $compileNode.empty(); // clear contents\n            childTranscludeFn = compilationGenerator(mightHaveMultipleTransclusionError, $template, transcludeFn, undefined,\n                undefined, { needsNewScope: directive.$$isolateScope || directive.$$newScope});\n            childTranscludeFn.$$slots = slots;\n          }\n        }\n\n        if (directive.template) {\n          hasTemplate = true;\n          assertNoDuplicate('template', templateDirective, directive, $compileNode);\n          templateDirective = directive;\n\n          directiveValue = (isFunction(directive.template))\n              ? directive.template($compileNode, templateAttrs)\n              : directive.template;\n\n          directiveValue = denormalizeTemplate(directiveValue);\n\n          if (directive.replace) {\n            replaceDirective = directive;\n            if (jqLiteIsTextNode(directiveValue)) {\n              $template = [];\n            } else {\n              $template = removeComments(wrapTemplate(directive.templateNamespace, trim(directiveValue)));\n            }\n            compileNode = $template[0];\n\n            if ($template.length !== 1 || compileNode.nodeType !== NODE_TYPE_ELEMENT) {\n              throw $compileMinErr('tplrt',\n                  'Template for directive \\'{0}\\' must have exactly one root element. {1}',\n                  directiveName, '');\n            }\n\n            replaceWith(jqCollection, $compileNode, compileNode);\n\n            var newTemplateAttrs = {$attr: {}};\n\n            // combine directives from the original node and from the template:\n            // - take the array of directives for this element\n            // - split it into two parts, those that already applied (processed) and those that weren't (unprocessed)\n            // - collect directives from the template and sort them by priority\n            // - combine directives as: processed + template + unprocessed\n            var templateDirectives = collectDirectives(compileNode, [], newTemplateAttrs);\n            var unprocessedDirectives = directives.splice(i + 1, directives.length - (i + 1));\n\n            if (newIsolateScopeDirective || newScopeDirective) {\n              // The original directive caused the current element to be replaced but this element\n              // also needs to have a new scope, so we need to tell the template directives\n              // that they would need to get their scope from further up, if they require transclusion\n              markDirectiveScope(templateDirectives, newIsolateScopeDirective, newScopeDirective);\n            }\n            directives = directives.concat(templateDirectives).concat(unprocessedDirectives);\n            mergeTemplateAttributes(templateAttrs, newTemplateAttrs);\n\n            ii = directives.length;\n          } else {\n            $compileNode.html(directiveValue);\n          }\n        }\n\n        if (directive.templateUrl) {\n          hasTemplate = true;\n          assertNoDuplicate('template', templateDirective, directive, $compileNode);\n          templateDirective = directive;\n\n          if (directive.replace) {\n            replaceDirective = directive;\n          }\n\n          // eslint-disable-next-line no-func-assign\n          nodeLinkFn = compileTemplateUrl(directives.splice(i, directives.length - i), $compileNode,\n              templateAttrs, jqCollection, hasTranscludeDirective && childTranscludeFn, preLinkFns, postLinkFns, {\n                controllerDirectives: controllerDirectives,\n                newScopeDirective: (newScopeDirective !== directive) && newScopeDirective,\n                newIsolateScopeDirective: newIsolateScopeDirective,\n                templateDirective: templateDirective,\n                nonTlbTranscludeDirective: nonTlbTranscludeDirective\n              });\n          ii = directives.length;\n        } else if (directive.compile) {\n          try {\n            linkFn = directive.compile($compileNode, templateAttrs, childTranscludeFn);\n            var context = directive.$$originalDirective || directive;\n            if (isFunction(linkFn)) {\n              addLinkFns(null, bind(context, linkFn), attrStart, attrEnd);\n            } else if (linkFn) {\n              addLinkFns(bind(context, linkFn.pre), bind(context, linkFn.post), attrStart, attrEnd);\n            }\n          } catch (e) {\n            $exceptionHandler(e, startingTag($compileNode));\n          }\n        }\n\n        if (directive.terminal) {\n          nodeLinkFn.terminal = true;\n          terminalPriority = Math.max(terminalPriority, directive.priority);\n        }\n\n      }\n\n      nodeLinkFn.scope = newScopeDirective && newScopeDirective.scope === true;\n      nodeLinkFn.transcludeOnThisElement = hasTranscludeDirective;\n      nodeLinkFn.templateOnThisElement = hasTemplate;\n      nodeLinkFn.transclude = childTranscludeFn;\n\n      previousCompileContext.hasElementTranscludeDirective = hasElementTranscludeDirective;\n\n      // might be normal or delayed nodeLinkFn depending on if templateUrl is present\n      return nodeLinkFn;\n\n      ////////////////////\n\n      function addLinkFns(pre, post, attrStart, attrEnd) {\n        if (pre) {\n          if (attrStart) pre = groupElementsLinkFnWrapper(pre, attrStart, attrEnd);\n          pre.require = directive.require;\n          pre.directiveName = directiveName;\n          if (newIsolateScopeDirective === directive || directive.$$isolateScope) {\n            pre = cloneAndAnnotateFn(pre, {isolateScope: true});\n          }\n          preLinkFns.push(pre);\n        }\n        if (post) {\n          if (attrStart) post = groupElementsLinkFnWrapper(post, attrStart, attrEnd);\n          post.require = directive.require;\n          post.directiveName = directiveName;\n          if (newIsolateScopeDirective === directive || directive.$$isolateScope) {\n            post = cloneAndAnnotateFn(post, {isolateScope: true});\n          }\n          postLinkFns.push(post);\n        }\n      }\n\n      function nodeLinkFn(childLinkFn, scope, linkNode, $rootElement, boundTranscludeFn) {\n        var i, ii, linkFn, isolateScope, controllerScope, elementControllers, transcludeFn, $element,\n            attrs, scopeBindingInfo;\n\n        if (compileNode === linkNode) {\n          attrs = templateAttrs;\n          $element = templateAttrs.$$element;\n        } else {\n          $element = jqLite(linkNode);\n          attrs = new Attributes($element, templateAttrs);\n        }\n\n        controllerScope = scope;\n        if (newIsolateScopeDirective) {\n          isolateScope = scope.$new(true);\n        } else if (newScopeDirective) {\n          controllerScope = scope.$parent;\n        }\n\n        if (boundTranscludeFn) {\n          // track `boundTranscludeFn` so it can be unwrapped if `transcludeFn`\n          // is later passed as `parentBoundTranscludeFn` to `publicLinkFn`\n          transcludeFn = controllersBoundTransclude;\n          transcludeFn.$$boundTransclude = boundTranscludeFn;\n          // expose the slots on the `$transclude` function\n          transcludeFn.isSlotFilled = function(slotName) {\n            return !!boundTranscludeFn.$$slots[slotName];\n          };\n        }\n\n        if (controllerDirectives) {\n          elementControllers = setupControllers($element, attrs, transcludeFn, controllerDirectives, isolateScope, scope, newIsolateScopeDirective);\n        }\n\n        if (newIsolateScopeDirective) {\n          // Initialize isolate scope bindings for new isolate scope directive.\n          compile.$$addScopeInfo($element, isolateScope, true, !(templateDirective && (templateDirective === newIsolateScopeDirective ||\n              templateDirective === newIsolateScopeDirective.$$originalDirective)));\n          compile.$$addScopeClass($element, true);\n          isolateScope.$$isolateBindings =\n              newIsolateScopeDirective.$$isolateBindings;\n          scopeBindingInfo = initializeDirectiveBindings(scope, attrs, isolateScope,\n                                        isolateScope.$$isolateBindings,\n                                        newIsolateScopeDirective);\n          if (scopeBindingInfo.removeWatches) {\n            isolateScope.$on('$destroy', scopeBindingInfo.removeWatches);\n          }\n        }\n\n        // Initialize bindToController bindings\n        for (var name in elementControllers) {\n          var controllerDirective = controllerDirectives[name];\n          var controller = elementControllers[name];\n          var bindings = controllerDirective.$$bindings.bindToController;\n\n          controller.instance = controller();\n          $element.data('$' + controllerDirective.name + 'Controller', controller.instance);\n          controller.bindingInfo =\n            initializeDirectiveBindings(controllerScope, attrs, controller.instance, bindings, controllerDirective);\n          }\n\n        // Bind the required controllers to the controller, if `require` is an object and `bindToController` is truthy\n        forEach(controllerDirectives, function(controllerDirective, name) {\n          var require = controllerDirective.require;\n          if (controllerDirective.bindToController && !isArray(require) && isObject(require)) {\n            extend(elementControllers[name].instance, getControllers(name, require, $element, elementControllers));\n          }\n        });\n\n        // Handle the init and destroy lifecycle hooks on all controllers that have them\n        forEach(elementControllers, function(controller) {\n          var controllerInstance = controller.instance;\n          if (isFunction(controllerInstance.$onChanges)) {\n            try {\n              controllerInstance.$onChanges(controller.bindingInfo.initialChanges);\n            } catch (e) {\n              $exceptionHandler(e);\n            }\n          }\n          if (isFunction(controllerInstance.$onInit)) {\n            try {\n              controllerInstance.$onInit();\n            } catch (e) {\n              $exceptionHandler(e);\n            }\n          }\n          if (isFunction(controllerInstance.$doCheck)) {\n            controllerScope.$watch(function() { controllerInstance.$doCheck(); });\n            controllerInstance.$doCheck();\n          }\n          if (isFunction(controllerInstance.$onDestroy)) {\n            controllerScope.$on('$destroy', function callOnDestroyHook() {\n              controllerInstance.$onDestroy();\n            });\n          }\n        });\n\n        // PRELINKING\n        for (i = 0, ii = preLinkFns.length; i < ii; i++) {\n          linkFn = preLinkFns[i];\n          invokeLinkFn(linkFn,\n              linkFn.isolateScope ? isolateScope : scope,\n              $element,\n              attrs,\n              linkFn.require && getControllers(linkFn.directiveName, linkFn.require, $element, elementControllers),\n              transcludeFn\n          );\n        }\n\n        // RECURSION\n        // We only pass the isolate scope, if the isolate directive has a template,\n        // otherwise the child elements do not belong to the isolate directive.\n        var scopeToChild = scope;\n        if (newIsolateScopeDirective && (newIsolateScopeDirective.template || newIsolateScopeDirective.templateUrl === null)) {\n          scopeToChild = isolateScope;\n        }\n        if (childLinkFn) {\n          childLinkFn(scopeToChild, linkNode.childNodes, undefined, boundTranscludeFn);\n        }\n\n        // POSTLINKING\n        for (i = postLinkFns.length - 1; i >= 0; i--) {\n          linkFn = postLinkFns[i];\n          invokeLinkFn(linkFn,\n              linkFn.isolateScope ? isolateScope : scope,\n              $element,\n              attrs,\n              linkFn.require && getControllers(linkFn.directiveName, linkFn.require, $element, elementControllers),\n              transcludeFn\n          );\n        }\n\n        // Trigger $postLink lifecycle hooks\n        forEach(elementControllers, function(controller) {\n          var controllerInstance = controller.instance;\n          if (isFunction(controllerInstance.$postLink)) {\n            controllerInstance.$postLink();\n          }\n        });\n\n        // This is the function that is injected as `$transclude`.\n        // Note: all arguments are optional!\n        function controllersBoundTransclude(scope, cloneAttachFn, futureParentElement, slotName) {\n          var transcludeControllers;\n          // No scope passed in:\n          if (!isScope(scope)) {\n            slotName = futureParentElement;\n            futureParentElement = cloneAttachFn;\n            cloneAttachFn = scope;\n            scope = undefined;\n          }\n\n          if (hasElementTranscludeDirective) {\n            transcludeControllers = elementControllers;\n          }\n          if (!futureParentElement) {\n            futureParentElement = hasElementTranscludeDirective ? $element.parent() : $element;\n          }\n          if (slotName) {\n            // slotTranscludeFn can be one of three things:\n            //  * a transclude function - a filled slot\n            //  * `null` - an optional slot that was not filled\n            //  * `undefined` - a slot that was not declared (i.e. invalid)\n            var slotTranscludeFn = boundTranscludeFn.$$slots[slotName];\n            if (slotTranscludeFn) {\n              return slotTranscludeFn(scope, cloneAttachFn, transcludeControllers, futureParentElement, scopeToChild);\n            } else if (isUndefined(slotTranscludeFn)) {\n              throw $compileMinErr('noslot',\n               'No parent directive that requires a transclusion with slot name \"{0}\". ' +\n               'Element: {1}',\n               slotName, startingTag($element));\n            }\n          } else {\n            return boundTranscludeFn(scope, cloneAttachFn, transcludeControllers, futureParentElement, scopeToChild);\n          }\n        }\n      }\n    }\n\n    function getControllers(directiveName, require, $element, elementControllers) {\n      var value;\n\n      if (isString(require)) {\n        var match = require.match(REQUIRE_PREFIX_REGEXP);\n        var name = require.substring(match[0].length);\n        var inheritType = match[1] || match[3];\n        var optional = match[2] === '?';\n\n        //If only parents then start at the parent element\n        if (inheritType === '^^') {\n          $element = $element.parent();\n        //Otherwise attempt getting the controller from elementControllers in case\n        //the element is transcluded (and has no data) and to avoid .data if possible\n        } else {\n          value = elementControllers && elementControllers[name];\n          value = value && value.instance;\n        }\n\n        if (!value) {\n          var dataName = '$' + name + 'Controller';\n\n          if (inheritType === '^^' && $element[0] && $element[0].nodeType === NODE_TYPE_DOCUMENT) {\n            // inheritedData() uses the documentElement when it finds the document, so we would\n            // require from the element itself.\n            value = null;\n          } else {\n            value = inheritType ? $element.inheritedData(dataName) : $element.data(dataName);\n          }\n        }\n\n        if (!value && !optional) {\n          throw $compileMinErr('ctreq',\n              'Controller \\'{0}\\', required by directive \\'{1}\\', can\\'t be found!',\n              name, directiveName);\n        }\n      } else if (isArray(require)) {\n        value = [];\n        for (var i = 0, ii = require.length; i < ii; i++) {\n          value[i] = getControllers(directiveName, require[i], $element, elementControllers);\n        }\n      } else if (isObject(require)) {\n        value = {};\n        forEach(require, function(controller, property) {\n          value[property] = getControllers(directiveName, controller, $element, elementControllers);\n        });\n      }\n\n      return value || null;\n    }\n\n    function setupControllers($element, attrs, transcludeFn, controllerDirectives, isolateScope, scope, newIsolateScopeDirective) {\n      var elementControllers = createMap();\n      for (var controllerKey in controllerDirectives) {\n        var directive = controllerDirectives[controllerKey];\n        var locals = {\n          $scope: directive === newIsolateScopeDirective || directive.$$isolateScope ? isolateScope : scope,\n          $element: $element,\n          $attrs: attrs,\n          $transclude: transcludeFn\n        };\n\n        var controller = directive.controller;\n        if (controller === '@') {\n          controller = attrs[directive.name];\n        }\n\n        var controllerInstance = $controller(controller, locals, true, directive.controllerAs);\n\n        // For directives with element transclusion the element is a comment.\n        // In this case .data will not attach any data.\n        // Instead, we save the controllers for the element in a local hash and attach to .data\n        // later, once we have the actual element.\n        elementControllers[directive.name] = controllerInstance;\n        $element.data('$' + directive.name + 'Controller', controllerInstance.instance);\n      }\n      return elementControllers;\n    }\n\n    // Depending upon the context in which a directive finds itself it might need to have a new isolated\n    // or child scope created. For instance:\n    // * if the directive has been pulled into a template because another directive with a higher priority\n    // asked for element transclusion\n    // * if the directive itself asks for transclusion but it is at the root of a template and the original\n    // element was replaced. See https://github.com/angular/angular.js/issues/12936\n    function markDirectiveScope(directives, isolateScope, newScope) {\n      for (var j = 0, jj = directives.length; j < jj; j++) {\n        directives[j] = inherit(directives[j], {$$isolateScope: isolateScope, $$newScope: newScope});\n      }\n    }\n\n    /**\n     * looks up the directive and decorates it with exception handling and proper parameters. We\n     * call this the boundDirective.\n     *\n     * @param {string} name name of the directive to look up.\n     * @param {string} location The directive must be found in specific format.\n     *   String containing any of theses characters:\n     *\n     *   * `E`: element name\n     *   * `A': attribute\n     *   * `C`: class\n     *   * `M`: comment\n     * @returns {boolean} true if directive was added.\n     */\n    function addDirective(tDirectives, name, location, maxPriority, ignoreDirective, startAttrName,\n                          endAttrName) {\n      if (name === ignoreDirective) return null;\n      var match = null;\n      if (hasDirectives.hasOwnProperty(name)) {\n        for (var directive, directives = $injector.get(name + Suffix),\n            i = 0, ii = directives.length; i < ii; i++) {\n          directive = directives[i];\n          if ((isUndefined(maxPriority) || maxPriority > directive.priority) &&\n               directive.restrict.indexOf(location) !== -1) {\n            if (startAttrName) {\n              directive = inherit(directive, {$$start: startAttrName, $$end: endAttrName});\n            }\n            if (!directive.$$bindings) {\n              var bindings = directive.$$bindings =\n                  parseDirectiveBindings(directive, directive.name);\n              if (isObject(bindings.isolateScope)) {\n                directive.$$isolateBindings = bindings.isolateScope;\n              }\n            }\n            tDirectives.push(directive);\n            match = directive;\n          }\n        }\n      }\n      return match;\n    }\n\n\n    /**\n     * looks up the directive and returns true if it is a multi-element directive,\n     * and therefore requires DOM nodes between -start and -end markers to be grouped\n     * together.\n     *\n     * @param {string} name name of the directive to look up.\n     * @returns true if directive was registered as multi-element.\n     */\n    function directiveIsMultiElement(name) {\n      if (hasDirectives.hasOwnProperty(name)) {\n        for (var directive, directives = $injector.get(name + Suffix),\n            i = 0, ii = directives.length; i < ii; i++) {\n          directive = directives[i];\n          if (directive.multiElement) {\n            return true;\n          }\n        }\n      }\n      return false;\n    }\n\n    /**\n     * When the element is replaced with HTML template then the new attributes\n     * on the template need to be merged with the existing attributes in the DOM.\n     * The desired effect is to have both of the attributes present.\n     *\n     * @param {object} dst destination attributes (original DOM)\n     * @param {object} src source attributes (from the directive template)\n     */\n    function mergeTemplateAttributes(dst, src) {\n      var srcAttr = src.$attr,\n          dstAttr = dst.$attr;\n\n      // reapply the old attributes to the new element\n      forEach(dst, function(value, key) {\n        if (key.charAt(0) !== '$') {\n          if (src[key] && src[key] !== value) {\n            if (value.length) {\n              value += (key === 'style' ? ';' : ' ') + src[key];\n            } else {\n              value = src[key];\n            }\n          }\n          dst.$set(key, value, true, srcAttr[key]);\n        }\n      });\n\n      // copy the new attributes on the old attrs object\n      forEach(src, function(value, key) {\n        // Check if we already set this attribute in the loop above.\n        // `dst` will never contain hasOwnProperty as DOM parser won't let it.\n        // You will get an \"InvalidCharacterError: DOM Exception 5\" error if you\n        // have an attribute like \"has-own-property\" or \"data-has-own-property\", etc.\n        if (!dst.hasOwnProperty(key) && key.charAt(0) !== '$') {\n          dst[key] = value;\n\n          if (key !== 'class' && key !== 'style') {\n            dstAttr[key] = srcAttr[key];\n          }\n        }\n      });\n    }\n\n\n    function compileTemplateUrl(directives, $compileNode, tAttrs,\n        $rootElement, childTranscludeFn, preLinkFns, postLinkFns, previousCompileContext) {\n      var linkQueue = [],\n          afterTemplateNodeLinkFn,\n          afterTemplateChildLinkFn,\n          beforeTemplateCompileNode = $compileNode[0],\n          origAsyncDirective = directives.shift(),\n          derivedSyncDirective = inherit(origAsyncDirective, {\n            templateUrl: null, transclude: null, replace: null, $$originalDirective: origAsyncDirective\n          }),\n          templateUrl = (isFunction(origAsyncDirective.templateUrl))\n              ? origAsyncDirective.templateUrl($compileNode, tAttrs)\n              : origAsyncDirective.templateUrl,\n          templateNamespace = origAsyncDirective.templateNamespace;\n\n      $compileNode.empty();\n\n      $templateRequest(templateUrl)\n        .then(function(content) {\n          var compileNode, tempTemplateAttrs, $template, childBoundTranscludeFn;\n\n          content = denormalizeTemplate(content);\n\n          if (origAsyncDirective.replace) {\n            if (jqLiteIsTextNode(content)) {\n              $template = [];\n            } else {\n              $template = removeComments(wrapTemplate(templateNamespace, trim(content)));\n            }\n            compileNode = $template[0];\n\n            if ($template.length !== 1 || compileNode.nodeType !== NODE_TYPE_ELEMENT) {\n              throw $compileMinErr('tplrt',\n                  'Template for directive \\'{0}\\' must have exactly one root element. {1}',\n                  origAsyncDirective.name, templateUrl);\n            }\n\n            tempTemplateAttrs = {$attr: {}};\n            replaceWith($rootElement, $compileNode, compileNode);\n            var templateDirectives = collectDirectives(compileNode, [], tempTemplateAttrs);\n\n            if (isObject(origAsyncDirective.scope)) {\n              // the original directive that caused the template to be loaded async required\n              // an isolate scope\n              markDirectiveScope(templateDirectives, true);\n            }\n            directives = templateDirectives.concat(directives);\n            mergeTemplateAttributes(tAttrs, tempTemplateAttrs);\n          } else {\n            compileNode = beforeTemplateCompileNode;\n            $compileNode.html(content);\n          }\n\n          directives.unshift(derivedSyncDirective);\n\n          afterTemplateNodeLinkFn = applyDirectivesToNode(directives, compileNode, tAttrs,\n              childTranscludeFn, $compileNode, origAsyncDirective, preLinkFns, postLinkFns,\n              previousCompileContext);\n          forEach($rootElement, function(node, i) {\n            if (node === compileNode) {\n              $rootElement[i] = $compileNode[0];\n            }\n          });\n          afterTemplateChildLinkFn = compileNodes($compileNode[0].childNodes, childTranscludeFn);\n\n          while (linkQueue.length) {\n            var scope = linkQueue.shift(),\n                beforeTemplateLinkNode = linkQueue.shift(),\n                linkRootElement = linkQueue.shift(),\n                boundTranscludeFn = linkQueue.shift(),\n                linkNode = $compileNode[0];\n\n            if (scope.$$destroyed) continue;\n\n            if (beforeTemplateLinkNode !== beforeTemplateCompileNode) {\n              var oldClasses = beforeTemplateLinkNode.className;\n\n              if (!(previousCompileContext.hasElementTranscludeDirective &&\n                  origAsyncDirective.replace)) {\n                // it was cloned therefore we have to clone as well.\n                linkNode = jqLiteClone(compileNode);\n              }\n              replaceWith(linkRootElement, jqLite(beforeTemplateLinkNode), linkNode);\n\n              // Copy in CSS classes from original node\n              safeAddClass(jqLite(linkNode), oldClasses);\n            }\n            if (afterTemplateNodeLinkFn.transcludeOnThisElement) {\n              childBoundTranscludeFn = createBoundTranscludeFn(scope, afterTemplateNodeLinkFn.transclude, boundTranscludeFn);\n            } else {\n              childBoundTranscludeFn = boundTranscludeFn;\n            }\n            afterTemplateNodeLinkFn(afterTemplateChildLinkFn, scope, linkNode, $rootElement,\n              childBoundTranscludeFn);\n          }\n          linkQueue = null;\n        }).catch(function(error) {\n          if (isError(error)) {\n            $exceptionHandler(error);\n          }\n        });\n\n      return function delayedNodeLinkFn(ignoreChildLinkFn, scope, node, rootElement, boundTranscludeFn) {\n        var childBoundTranscludeFn = boundTranscludeFn;\n        if (scope.$$destroyed) return;\n        if (linkQueue) {\n          linkQueue.push(scope,\n                         node,\n                         rootElement,\n                         childBoundTranscludeFn);\n        } else {\n          if (afterTemplateNodeLinkFn.transcludeOnThisElement) {\n            childBoundTranscludeFn = createBoundTranscludeFn(scope, afterTemplateNodeLinkFn.transclude, boundTranscludeFn);\n          }\n          afterTemplateNodeLinkFn(afterTemplateChildLinkFn, scope, node, rootElement, childBoundTranscludeFn);\n        }\n      };\n    }\n\n\n    /**\n     * Sorting function for bound directives.\n     */\n    function byPriority(a, b) {\n      var diff = b.priority - a.priority;\n      if (diff !== 0) return diff;\n      if (a.name !== b.name) return (a.name < b.name) ? -1 : 1;\n      return a.index - b.index;\n    }\n\n    function assertNoDuplicate(what, previousDirective, directive, element) {\n\n      function wrapModuleNameIfDefined(moduleName) {\n        return moduleName ?\n          (' (module: ' + moduleName + ')') :\n          '';\n      }\n\n      if (previousDirective) {\n        throw $compileMinErr('multidir', 'Multiple directives [{0}{1}, {2}{3}] asking for {4} on: {5}',\n            previousDirective.name, wrapModuleNameIfDefined(previousDirective.$$moduleName),\n            directive.name, wrapModuleNameIfDefined(directive.$$moduleName), what, startingTag(element));\n      }\n    }\n\n\n    function addTextInterpolateDirective(directives, text) {\n      var interpolateFn = $interpolate(text, true);\n      if (interpolateFn) {\n        directives.push({\n          priority: 0,\n          compile: function textInterpolateCompileFn(templateNode) {\n            var templateNodeParent = templateNode.parent(),\n                hasCompileParent = !!templateNodeParent.length;\n\n            // When transcluding a template that has bindings in the root\n            // we don't have a parent and thus need to add the class during linking fn.\n            if (hasCompileParent) compile.$$addBindingClass(templateNodeParent);\n\n            return function textInterpolateLinkFn(scope, node) {\n              var parent = node.parent();\n              if (!hasCompileParent) compile.$$addBindingClass(parent);\n              compile.$$addBindingInfo(parent, interpolateFn.expressions);\n              scope.$watch(interpolateFn, function interpolateFnWatchAction(value) {\n                node[0].nodeValue = value;\n              });\n            };\n          }\n        });\n      }\n    }\n\n\n    function wrapTemplate(type, template) {\n      type = lowercase(type || 'html');\n      switch (type) {\n      case 'svg':\n      case 'math':\n        var wrapper = window.document.createElement('div');\n        wrapper.innerHTML = '<' + type + '>' + template + '</' + type + '>';\n        return wrapper.childNodes[0].childNodes;\n      default:\n        return template;\n      }\n    }\n\n\n    function getTrustedAttrContext(nodeName, attrNormalizedName) {\n      if (attrNormalizedName === 'srcdoc') {\n        return $sce.HTML;\n      }\n      // All nodes with src attributes require a RESOURCE_URL value, except for\n      // img and various html5 media nodes, which require the MEDIA_URL context.\n      if (attrNormalizedName === 'src' || attrNormalizedName === 'ngSrc') {\n        if (['img', 'video', 'audio', 'source', 'track'].indexOf(nodeName) === -1) {\n          return $sce.RESOURCE_URL;\n        }\n        return $sce.MEDIA_URL;\n      } else if (attrNormalizedName === 'xlinkHref') {\n        // Some xlink:href are okay, most aren't\n        if (nodeName === 'image') return $sce.MEDIA_URL;\n        if (nodeName === 'a') return $sce.URL;\n        return $sce.RESOURCE_URL;\n      } else if (\n          // Formaction\n          (nodeName === 'form' && attrNormalizedName === 'action') ||\n          // If relative URLs can go where they are not expected to, then\n          // all sorts of trust issues can arise.\n          (nodeName === 'base' && attrNormalizedName === 'href') ||\n          // links can be stylesheets or imports, which can run script in the current origin\n          (nodeName === 'link' && attrNormalizedName === 'href')\n      ) {\n        return $sce.RESOURCE_URL;\n      } else if (nodeName === 'a' && (attrNormalizedName === 'href' ||\n                                 attrNormalizedName === 'ngHref')) {\n        return $sce.URL;\n      }\n    }\n\n    function getTrustedPropContext(nodeName, propNormalizedName) {\n      var prop = propNormalizedName.toLowerCase();\n      return PROP_CONTEXTS[nodeName + '|' + prop] || PROP_CONTEXTS['*|' + prop];\n    }\n\n    function sanitizeSrcsetPropertyValue(value) {\n      return sanitizeSrcset($sce.valueOf(value), 'ng-prop-srcset');\n    }\n    function addPropertyDirective(node, directives, attrName, propName) {\n      if (EVENT_HANDLER_ATTR_REGEXP.test(propName)) {\n        throw $compileMinErr('nodomevents', 'Property bindings for HTML DOM event properties are disallowed');\n      }\n\n      var nodeName = nodeName_(node);\n      var trustedContext = getTrustedPropContext(nodeName, propName);\n\n      var sanitizer = identity;\n      // Sanitize img[srcset] + source[srcset] values.\n      if (propName === 'srcset' && (nodeName === 'img' || nodeName === 'source')) {\n        sanitizer = sanitizeSrcsetPropertyValue;\n      } else if (trustedContext) {\n        sanitizer = $sce.getTrusted.bind($sce, trustedContext);\n      }\n\n      directives.push({\n        priority: 100,\n        compile: function ngPropCompileFn(_, attr) {\n          var ngPropGetter = $parse(attr[attrName]);\n          var ngPropWatch = $parse(attr[attrName], function sceValueOf(val) {\n            // Unwrap the value to compare the actual inner safe value, not the wrapper object.\n            return $sce.valueOf(val);\n          });\n\n          return {\n            pre: function ngPropPreLinkFn(scope, $element) {\n              function applyPropValue() {\n                var propValue = ngPropGetter(scope);\n                $element[0][propName] = sanitizer(propValue);\n              }\n\n              applyPropValue();\n              scope.$watch(ngPropWatch, applyPropValue);\n            }\n          };\n        }\n      });\n    }\n\n    function addEventDirective(directives, attrName, eventName) {\n      directives.push(\n        createEventDirective($parse, $rootScope, $exceptionHandler, attrName, eventName, /*forceAsync=*/false)\n      );\n    }\n\n    function addAttrInterpolateDirective(node, directives, value, name, isNgAttr) {\n      var nodeName = nodeName_(node);\n      var trustedContext = getTrustedAttrContext(nodeName, name);\n      var mustHaveExpression = !isNgAttr;\n      var allOrNothing = ALL_OR_NOTHING_ATTRS[name] || isNgAttr;\n\n      var interpolateFn = $interpolate(value, mustHaveExpression, trustedContext, allOrNothing);\n\n      // no interpolation found -> ignore\n      if (!interpolateFn) return;\n\n      if (name === 'multiple' && nodeName === 'select') {\n        throw $compileMinErr('selmulti',\n            'Binding to the \\'multiple\\' attribute is not supported. Element: {0}',\n            startingTag(node));\n      }\n\n      if (EVENT_HANDLER_ATTR_REGEXP.test(name)) {\n        throw $compileMinErr('nodomevents', 'Interpolations for HTML DOM event attributes are disallowed');\n      }\n\n      directives.push({\n        priority: 100,\n        compile: function() {\n            return {\n              pre: function attrInterpolatePreLinkFn(scope, element, attr) {\n                var $$observers = (attr.$$observers || (attr.$$observers = createMap()));\n\n                // If the attribute has changed since last $interpolate()ed\n                var newValue = attr[name];\n                if (newValue !== value) {\n                  // we need to interpolate again since the attribute value has been updated\n                  // (e.g. by another directive's compile function)\n                  // ensure unset/empty values make interpolateFn falsy\n                  interpolateFn = newValue && $interpolate(newValue, true, trustedContext, allOrNothing);\n                  value = newValue;\n                }\n\n                // if attribute was updated so that there is no interpolation going on we don't want to\n                // register any observers\n                if (!interpolateFn) return;\n\n                // initialize attr object so that it's ready in case we need the value for isolate\n                // scope initialization, otherwise the value would not be available from isolate\n                // directive's linking fn during linking phase\n                attr[name] = interpolateFn(scope);\n\n                ($$observers[name] || ($$observers[name] = [])).$$inter = true;\n                (attr.$$observers && attr.$$observers[name].$$scope || scope).\n                  $watch(interpolateFn, function interpolateFnWatchAction(newValue, oldValue) {\n                    //special case for class attribute addition + removal\n                    //so that class changes can tap into the animation\n                    //hooks provided by the $animate service. Be sure to\n                    //skip animations when the first digest occurs (when\n                    //both the new and the old values are the same) since\n                    //the CSS classes are the non-interpolated values\n                    if (name === 'class' && newValue !== oldValue) {\n                      attr.$updateClass(newValue, oldValue);\n                    } else {\n                      attr.$set(name, newValue);\n                    }\n                  });\n              }\n            };\n          }\n      });\n    }\n\n\n    /**\n     * This is a special jqLite.replaceWith, which can replace items which\n     * have no parents, provided that the containing jqLite collection is provided.\n     *\n     * @param {JqLite=} $rootElement The root of the compile tree. Used so that we can replace nodes\n     *                               in the root of the tree.\n     * @param {JqLite} elementsToRemove The jqLite element which we are going to replace. We keep\n     *                                  the shell, but replace its DOM node reference.\n     * @param {Node} newNode The new DOM node.\n     */\n    function replaceWith($rootElement, elementsToRemove, newNode) {\n      var firstElementToRemove = elementsToRemove[0],\n          removeCount = elementsToRemove.length,\n          parent = firstElementToRemove.parentNode,\n          i, ii;\n\n      if ($rootElement) {\n        for (i = 0, ii = $rootElement.length; i < ii; i++) {\n          if ($rootElement[i] === firstElementToRemove) {\n            $rootElement[i++] = newNode;\n            for (var j = i, j2 = j + removeCount - 1,\n                     jj = $rootElement.length;\n                 j < jj; j++, j2++) {\n              if (j2 < jj) {\n                $rootElement[j] = $rootElement[j2];\n              } else {\n                delete $rootElement[j];\n              }\n            }\n            $rootElement.length -= removeCount - 1;\n\n            // If the replaced element is also the jQuery .context then replace it\n            // .context is a deprecated jQuery api, so we should set it only when jQuery set it\n            // http://api.jquery.com/context/\n            if ($rootElement.context === firstElementToRemove) {\n              $rootElement.context = newNode;\n            }\n            break;\n          }\n        }\n      }\n\n      if (parent) {\n        parent.replaceChild(newNode, firstElementToRemove);\n      }\n\n      // Append all the `elementsToRemove` to a fragment. This will...\n      // - remove them from the DOM\n      // - allow them to still be traversed with .nextSibling\n      // - allow a single fragment.qSA to fetch all elements being removed\n      var fragment = window.document.createDocumentFragment();\n      for (i = 0; i < removeCount; i++) {\n        fragment.appendChild(elementsToRemove[i]);\n      }\n\n      if (jqLite.hasData(firstElementToRemove)) {\n        // Copy over user data (that includes AngularJS's $scope etc.). Don't copy private\n        // data here because there's no public interface in jQuery to do that and copying over\n        // event listeners (which is the main use of private data) wouldn't work anyway.\n        jqLite.data(newNode, jqLite.data(firstElementToRemove));\n\n        // Remove $destroy event listeners from `firstElementToRemove`\n        jqLite(firstElementToRemove).off('$destroy');\n      }\n\n      // Cleanup any data/listeners on the elements and children.\n      // This includes invoking the $destroy event on any elements with listeners.\n      jqLite.cleanData(fragment.querySelectorAll('*'));\n\n      // Update the jqLite collection to only contain the `newNode`\n      for (i = 1; i < removeCount; i++) {\n        delete elementsToRemove[i];\n      }\n      elementsToRemove[0] = newNode;\n      elementsToRemove.length = 1;\n    }\n\n\n    function cloneAndAnnotateFn(fn, annotation) {\n      return extend(function() { return fn.apply(null, arguments); }, fn, annotation);\n    }\n\n\n    function invokeLinkFn(linkFn, scope, $element, attrs, controllers, transcludeFn) {\n      try {\n        linkFn(scope, $element, attrs, controllers, transcludeFn);\n      } catch (e) {\n        $exceptionHandler(e, startingTag($element));\n      }\n    }\n\n    function strictBindingsCheck(attrName, directiveName) {\n      if (strictComponentBindingsEnabled) {\n        throw $compileMinErr('missingattr',\n          'Attribute \\'{0}\\' of \\'{1}\\' is non-optional and must be set!',\n          attrName, directiveName);\n      }\n    }\n\n    // Set up $watches for isolate scope and controller bindings.\n    function initializeDirectiveBindings(scope, attrs, destination, bindings, directive) {\n      var removeWatchCollection = [];\n      var initialChanges = {};\n      var changes;\n\n      forEach(bindings, function initializeBinding(definition, scopeName) {\n        var attrName = definition.attrName,\n        optional = definition.optional,\n        mode = definition.mode, // @, =, <, or &\n        lastValue,\n        parentGet, parentSet, compare, removeWatch;\n\n        switch (mode) {\n\n          case '@':\n            if (!optional && !hasOwnProperty.call(attrs, attrName)) {\n              strictBindingsCheck(attrName, directive.name);\n              destination[scopeName] = attrs[attrName] = undefined;\n\n            }\n            removeWatch = attrs.$observe(attrName, function(value) {\n              if (isString(value) || isBoolean(value)) {\n                var oldValue = destination[scopeName];\n                recordChanges(scopeName, value, oldValue);\n                destination[scopeName] = value;\n              }\n            });\n            attrs.$$observers[attrName].$$scope = scope;\n            lastValue = attrs[attrName];\n            if (isString(lastValue)) {\n              // If the attribute has been provided then we trigger an interpolation to ensure\n              // the value is there for use in the link fn\n              destination[scopeName] = $interpolate(lastValue)(scope);\n            } else if (isBoolean(lastValue)) {\n              // If the attributes is one of the BOOLEAN_ATTR then AngularJS will have converted\n              // the value to boolean rather than a string, so we special case this situation\n              destination[scopeName] = lastValue;\n            }\n            initialChanges[scopeName] = new SimpleChange(_UNINITIALIZED_VALUE, destination[scopeName]);\n            removeWatchCollection.push(removeWatch);\n            break;\n\n          case '=':\n            if (!hasOwnProperty.call(attrs, attrName)) {\n              if (optional) break;\n              strictBindingsCheck(attrName, directive.name);\n              attrs[attrName] = undefined;\n            }\n            if (optional && !attrs[attrName]) break;\n\n            parentGet = $parse(attrs[attrName]);\n            if (parentGet.literal) {\n              compare = equals;\n            } else {\n              compare = simpleCompare;\n            }\n            parentSet = parentGet.assign || function() {\n              // reset the change, or we will throw this exception on every $digest\n              lastValue = destination[scopeName] = parentGet(scope);\n              throw $compileMinErr('nonassign',\n                  'Expression \\'{0}\\' in attribute \\'{1}\\' used with directive \\'{2}\\' is non-assignable!',\n                  attrs[attrName], attrName, directive.name);\n            };\n            lastValue = destination[scopeName] = parentGet(scope);\n            var parentValueWatch = function parentValueWatch(parentValue) {\n              if (!compare(parentValue, destination[scopeName])) {\n                // we are out of sync and need to copy\n                if (!compare(parentValue, lastValue)) {\n                  // parent changed and it has precedence\n                  destination[scopeName] = parentValue;\n                } else {\n                  // if the parent can be assigned then do so\n                  parentSet(scope, parentValue = destination[scopeName]);\n                }\n              }\n              lastValue = parentValue;\n              return lastValue;\n            };\n            parentValueWatch.$stateful = true;\n            if (definition.collection) {\n              removeWatch = scope.$watchCollection(attrs[attrName], parentValueWatch);\n            } else {\n              removeWatch = scope.$watch($parse(attrs[attrName], parentValueWatch), null, parentGet.literal);\n            }\n            removeWatchCollection.push(removeWatch);\n            break;\n\n          case '<':\n            if (!hasOwnProperty.call(attrs, attrName)) {\n              if (optional) break;\n              strictBindingsCheck(attrName, directive.name);\n              attrs[attrName] = undefined;\n            }\n            if (optional && !attrs[attrName]) break;\n\n            parentGet = $parse(attrs[attrName]);\n            var isLiteral = parentGet.literal;\n\n            var initialValue = destination[scopeName] = parentGet(scope);\n            initialChanges[scopeName] = new SimpleChange(_UNINITIALIZED_VALUE, destination[scopeName]);\n\n            removeWatch = scope[definition.collection ? '$watchCollection' : '$watch'](parentGet, function parentValueWatchAction(newValue, oldValue) {\n              if (oldValue === newValue) {\n                if (oldValue === initialValue || (isLiteral && equals(oldValue, initialValue))) {\n                  return;\n                }\n                oldValue = initialValue;\n              }\n              recordChanges(scopeName, newValue, oldValue);\n              destination[scopeName] = newValue;\n            });\n\n            removeWatchCollection.push(removeWatch);\n            break;\n\n          case '&':\n            if (!optional && !hasOwnProperty.call(attrs, attrName)) {\n              strictBindingsCheck(attrName, directive.name);\n            }\n            // Don't assign Object.prototype method to scope\n            parentGet = attrs.hasOwnProperty(attrName) ? $parse(attrs[attrName]) : noop;\n\n            // Don't assign noop to destination if expression is not valid\n            if (parentGet === noop && optional) break;\n\n            destination[scopeName] = function(locals) {\n              return parentGet(scope, locals);\n            };\n            break;\n        }\n      });\n\n      function recordChanges(key, currentValue, previousValue) {\n        if (isFunction(destination.$onChanges) && !simpleCompare(currentValue, previousValue)) {\n          // If we have not already scheduled the top level onChangesQueue handler then do so now\n          if (!onChangesQueue) {\n            scope.$$postDigest(flushOnChangesQueue);\n            onChangesQueue = [];\n          }\n          // If we have not already queued a trigger of onChanges for this controller then do so now\n          if (!changes) {\n            changes = {};\n            onChangesQueue.push(triggerOnChangesHook);\n          }\n          // If the has been a change on this property already then we need to reuse the previous value\n          if (changes[key]) {\n            previousValue = changes[key].previousValue;\n          }\n          // Store this change\n          changes[key] = new SimpleChange(previousValue, currentValue);\n        }\n      }\n\n      function triggerOnChangesHook() {\n        destination.$onChanges(changes);\n        // Now clear the changes so that we schedule onChanges when more changes arrive\n        changes = undefined;\n      }\n\n      return {\n        initialChanges: initialChanges,\n        removeWatches: removeWatchCollection.length && function removeWatches() {\n          for (var i = 0, ii = removeWatchCollection.length; i < ii; ++i) {\n            removeWatchCollection[i]();\n          }\n        }\n      };\n    }\n  }];\n}\n\nfunction SimpleChange(previous, current) {\n  this.previousValue = previous;\n  this.currentValue = current;\n}\nSimpleChange.prototype.isFirstChange = function() { return this.previousValue === _UNINITIALIZED_VALUE; };\n\n\nvar PREFIX_REGEXP = /^((?:x|data)[:\\-_])/i;\nvar SPECIAL_CHARS_REGEXP = /[:\\-_]+(.)/g;\n\n/**\n * Converts all accepted directives format into proper directive name.\n * @param name Name to normalize\n */\nfunction directiveNormalize(name) {\n  return name\n    .replace(PREFIX_REGEXP, '')\n    .replace(SPECIAL_CHARS_REGEXP, function(_, letter, offset) {\n      return offset ? letter.toUpperCase() : letter;\n    });\n}\n\n/**\n * @ngdoc type\n * @name $compile.directive.Attributes\n *\n * @description\n * A shared object between directive compile / linking functions which contains normalized DOM\n * element attributes. The values reflect current binding state `{{ }}`. The normalization is\n * needed since all of these are treated as equivalent in AngularJS:\n *\n * ```\n *    <span ng:bind=\"a\" ng-bind=\"a\" data-ng-bind=\"a\" x-ng-bind=\"a\">\n * ```\n */\n\n/**\n * @ngdoc property\n * @name $compile.directive.Attributes#$attr\n *\n * @description\n * A map of DOM element attribute names to the normalized name. This is\n * needed to do reverse lookup from normalized name back to actual name.\n */\n\n\n/**\n * @ngdoc method\n * @name $compile.directive.Attributes#$set\n * @kind function\n *\n * @description\n * Set DOM element attribute value.\n *\n *\n * @param {string} name Normalized element attribute name of the property to modify. The name is\n *          reverse-translated using the {@link ng.$compile.directive.Attributes#$attr $attr}\n *          property to the original name.\n * @param {string} value Value to set the attribute to. The value can be an interpolated string.\n */\n\n\n\n/**\n * Closure compiler type information\n */\n\nfunction nodesetLinkingFn(\n  /* angular.Scope */ scope,\n  /* NodeList */ nodeList,\n  /* Element */ rootElement,\n  /* function(Function) */ boundTranscludeFn\n) {}\n\nfunction directiveLinkingFn(\n  /* nodesetLinkingFn */ nodesetLinkingFn,\n  /* angular.Scope */ scope,\n  /* Node */ node,\n  /* Element */ rootElement,\n  /* function(Function) */ boundTranscludeFn\n) {}\n\nfunction tokenDifference(str1, str2) {\n  var values = '',\n      tokens1 = str1.split(/\\s+/),\n      tokens2 = str2.split(/\\s+/);\n\n  outer:\n  for (var i = 0; i < tokens1.length; i++) {\n    var token = tokens1[i];\n    for (var j = 0; j < tokens2.length; j++) {\n      if (token === tokens2[j]) continue outer;\n    }\n    values += (values.length > 0 ? ' ' : '') + token;\n  }\n  return values;\n}\n\nfunction removeComments(jqNodes) {\n  jqNodes = jqLite(jqNodes);\n  var i = jqNodes.length;\n\n  if (i <= 1) {\n    return jqNodes;\n  }\n\n  while (i--) {\n    var node = jqNodes[i];\n    if (node.nodeType === NODE_TYPE_COMMENT ||\n       (node.nodeType === NODE_TYPE_TEXT && node.nodeValue.trim() === '')) {\n         splice.call(jqNodes, i, 1);\n    }\n  }\n  return jqNodes;\n}\n\nvar $controllerMinErr = minErr('$controller');\n\n\nvar CNTRL_REG = /^(\\S+)(\\s+as\\s+([\\w$]+))?$/;\nfunction identifierForController(controller, ident) {\n  if (ident && isString(ident)) return ident;\n  if (isString(controller)) {\n    var match = CNTRL_REG.exec(controller);\n    if (match) return match[3];\n  }\n}\n\n\n/**\n * @ngdoc provider\n * @name $controllerProvider\n * @this\n *\n * @description\n * The {@link ng.$controller $controller service} is used by AngularJS to create new\n * controllers.\n *\n * This provider allows controller registration via the\n * {@link ng.$controllerProvider#register register} method.\n */\nfunction $ControllerProvider() {\n  var controllers = {};\n\n  /**\n   * @ngdoc method\n   * @name $controllerProvider#has\n   * @param {string} name Controller name to check.\n   */\n  this.has = function(name) {\n    return controllers.hasOwnProperty(name);\n  };\n\n  /**\n   * @ngdoc method\n   * @name $controllerProvider#register\n   * @param {string|Object} name Controller name, or an object map of controllers where the keys are\n   *    the names and the values are the constructors.\n   * @param {Function|Array} constructor Controller constructor fn (optionally decorated with DI\n   *    annotations in the array notation).\n   */\n  this.register = function(name, constructor) {\n    assertNotHasOwnProperty(name, 'controller');\n    if (isObject(name)) {\n      extend(controllers, name);\n    } else {\n      controllers[name] = constructor;\n    }\n  };\n\n  this.$get = ['$injector', function($injector) {\n\n    /**\n     * @ngdoc service\n     * @name $controller\n     * @requires $injector\n     *\n     * @param {Function|string} constructor If called with a function then it's considered to be the\n     *    controller constructor function. Otherwise it's considered to be a string which is used\n     *    to retrieve the controller constructor using the following steps:\n     *\n     *    * check if a controller with given name is registered via `$controllerProvider`\n     *    * check if evaluating the string on the current scope returns a constructor\n     *\n     *    The string can use the `controller as property` syntax, where the controller instance is published\n     *    as the specified property on the `scope`; the `scope` must be injected into `locals` param for this\n     *    to work correctly.\n     *\n     * @param {Object} locals Injection locals for Controller.\n     * @return {Object} Instance of given controller.\n     *\n     * @description\n     * `$controller` service is responsible for instantiating controllers.\n     *\n     * It's just a simple call to {@link auto.$injector $injector}, but extracted into\n     * a service, so that one can override this service with [BC version](https://gist.github.com/1649788).\n     */\n    return function $controller(expression, locals, later, ident) {\n      // PRIVATE API:\n      //   param `later` --- indicates that the controller's constructor is invoked at a later time.\n      //                     If true, $controller will allocate the object with the correct\n      //                     prototype chain, but will not invoke the controller until a returned\n      //                     callback is invoked.\n      //   param `ident` --- An optional label which overrides the label parsed from the controller\n      //                     expression, if any.\n      var instance, match, constructor, identifier;\n      later = later === true;\n      if (ident && isString(ident)) {\n        identifier = ident;\n      }\n\n      if (isString(expression)) {\n        match = expression.match(CNTRL_REG);\n        if (!match) {\n          throw $controllerMinErr('ctrlfmt',\n            'Badly formed controller string \\'{0}\\'. ' +\n            'Must match `__name__ as __id__` or `__name__`.', expression);\n        }\n        constructor = match[1];\n        identifier = identifier || match[3];\n        expression = controllers.hasOwnProperty(constructor)\n            ? controllers[constructor]\n            : getter(locals.$scope, constructor, true);\n\n        if (!expression) {\n          throw $controllerMinErr('ctrlreg',\n            'The controller with the name \\'{0}\\' is not registered.', constructor);\n        }\n\n        assertArgFn(expression, constructor, true);\n      }\n\n      if (later) {\n        // Instantiate controller later:\n        // This machinery is used to create an instance of the object before calling the\n        // controller's constructor itself.\n        //\n        // This allows properties to be added to the controller before the constructor is\n        // invoked. Primarily, this is used for isolate scope bindings in $compile.\n        //\n        // This feature is not intended for use by applications, and is thus not documented\n        // publicly.\n        // Object creation: http://jsperf.com/create-constructor/2\n        var controllerPrototype = (isArray(expression) ?\n          expression[expression.length - 1] : expression).prototype;\n        instance = Object.create(controllerPrototype || null);\n\n        if (identifier) {\n          addIdentifier(locals, identifier, instance, constructor || expression.name);\n        }\n\n        return extend(function $controllerInit() {\n          var result = $injector.invoke(expression, instance, locals, constructor);\n          if (result !== instance && (isObject(result) || isFunction(result))) {\n            instance = result;\n            if (identifier) {\n              // If result changed, re-assign controllerAs value to scope.\n              addIdentifier(locals, identifier, instance, constructor || expression.name);\n            }\n          }\n          return instance;\n        }, {\n          instance: instance,\n          identifier: identifier\n        });\n      }\n\n      instance = $injector.instantiate(expression, locals, constructor);\n\n      if (identifier) {\n        addIdentifier(locals, identifier, instance, constructor || expression.name);\n      }\n\n      return instance;\n    };\n\n    function addIdentifier(locals, identifier, instance, name) {\n      if (!(locals && isObject(locals.$scope))) {\n        throw minErr('$controller')('noscp',\n          'Cannot export controller \\'{0}\\' as \\'{1}\\'! No $scope object provided via `locals`.',\n          name, identifier);\n      }\n\n      locals.$scope[identifier] = instance;\n    }\n  }];\n}\n\n/**\n * @ngdoc service\n * @name $document\n * @requires $window\n * @this\n *\n * @description\n * A {@link angular.element jQuery or jqLite} wrapper for the browser's `window.document` object.\n *\n * @example\n   <example module=\"documentExample\" name=\"document\">\n     <file name=\"index.html\">\n       <div ng-controller=\"ExampleController\">\n         <p>$document title: <b ng-bind=\"title\"></b></p>\n         <p>window.document title: <b ng-bind=\"windowTitle\"></b></p>\n       </div>\n     </file>\n     <file name=\"script.js\">\n       angular.module('documentExample', [])\n         .controller('ExampleController', ['$scope', '$document', function($scope, $document) {\n           $scope.title = $document[0].title;\n           $scope.windowTitle = angular.element(window.document)[0].title;\n         }]);\n     </file>\n   </example>\n */\nfunction $DocumentProvider() {\n  this.$get = ['$window', function(window) {\n    return jqLite(window.document);\n  }];\n}\n\n\n/**\n * @private\n * @this\n * Listens for document visibility change and makes the current status accessible.\n */\nfunction $$IsDocumentHiddenProvider() {\n  this.$get = ['$document', '$rootScope', function($document, $rootScope) {\n    var doc = $document[0];\n    var hidden = doc && doc.hidden;\n\n    $document.on('visibilitychange', changeListener);\n\n    $rootScope.$on('$destroy', function() {\n      $document.off('visibilitychange', changeListener);\n    });\n\n    function changeListener() {\n      hidden = doc.hidden;\n    }\n\n    return function() {\n      return hidden;\n    };\n  }];\n}\n\n/**\n * @ngdoc service\n * @name $exceptionHandler\n * @requires ng.$log\n * @this\n *\n * @description\n * Any uncaught exception in AngularJS expressions is delegated to this service.\n * The default implementation simply delegates to `$log.error` which logs it into\n * the browser console.\n *\n * In unit tests, if `angular-mocks.js` is loaded, this service is overridden by\n * {@link ngMock.$exceptionHandler mock $exceptionHandler} which aids in testing.\n *\n * ## Example:\n *\n * The example below will overwrite the default `$exceptionHandler` in order to (a) log uncaught\n * errors to the backend for later inspection by the developers and (b) to use `$log.warn()` instead\n * of `$log.error()`.\n *\n * ```js\n *   angular.\n *     module('exceptionOverwrite', []).\n *     factory('$exceptionHandler', ['$log', 'logErrorsToBackend', function($log, logErrorsToBackend) {\n *       return function myExceptionHandler(exception, cause) {\n *         logErrorsToBackend(exception, cause);\n *         $log.warn(exception, cause);\n *       };\n *     }]);\n * ```\n *\n * <hr />\n * Note, that code executed in event-listeners (even those registered using jqLite's `on`/`bind`\n * methods) does not delegate exceptions to the {@link ng.$exceptionHandler $exceptionHandler}\n * (unless executed during a digest).\n *\n * If you wish, you can manually delegate exceptions, e.g.\n * `try { ... } catch(e) { $exceptionHandler(e); }`\n *\n * @param {Error} exception Exception associated with the error.\n * @param {string=} cause Optional information about the context in which\n *       the error was thrown.\n *\n */\nfunction $ExceptionHandlerProvider() {\n  this.$get = ['$log', function($log) {\n    return function(exception, cause) {\n      $log.error.apply($log, arguments);\n    };\n  }];\n}\n\nvar $$ForceReflowProvider = /** @this */ function() {\n  this.$get = ['$document', function($document) {\n    return function(domNode) {\n      //the line below will force the browser to perform a repaint so\n      //that all the animated elements within the animation frame will\n      //be properly updated and drawn on screen. This is required to\n      //ensure that the preparation animation is properly flushed so that\n      //the active state picks up from there. DO NOT REMOVE THIS LINE.\n      //DO NOT OPTIMIZE THIS LINE. THE MINIFIER WILL REMOVE IT OTHERWISE WHICH\n      //WILL RESULT IN AN UNPREDICTABLE BUG THAT IS VERY HARD TO TRACK DOWN AND\n      //WILL TAKE YEARS AWAY FROM YOUR LIFE.\n      if (domNode) {\n        if (!domNode.nodeType && domNode instanceof jqLite) {\n          domNode = domNode[0];\n        }\n      } else {\n        domNode = $document[0].body;\n      }\n      return domNode.offsetWidth + 1;\n    };\n  }];\n};\n\nvar APPLICATION_JSON = 'application/json';\nvar CONTENT_TYPE_APPLICATION_JSON = {'Content-Type': APPLICATION_JSON + ';charset=utf-8'};\nvar JSON_START = /^\\[|^\\{(?!\\{)/;\nvar JSON_ENDS = {\n  '[': /]$/,\n  '{': /}$/\n};\nvar JSON_PROTECTION_PREFIX = /^\\)]\\}',?\\n/;\nvar $httpMinErr = minErr('$http');\n\nfunction serializeValue(v) {\n  if (isObject(v)) {\n    return isDate(v) ? v.toISOString() : toJson(v);\n  }\n  return v;\n}\n\n\n/** @this */\nfunction $HttpParamSerializerProvider() {\n  /**\n   * @ngdoc service\n   * @name $httpParamSerializer\n   * @description\n   *\n   * Default {@link $http `$http`} params serializer that converts objects to strings\n   * according to the following rules:\n   *\n   * * `{'foo': 'bar'}` results in `foo=bar`\n   * * `{'foo': Date.now()}` results in `foo=2015-04-01T09%3A50%3A49.262Z` (`toISOString()` and encoded representation of a Date object)\n   * * `{'foo': ['bar', 'baz']}` results in `foo=bar&foo=baz` (repeated key for each array element)\n   * * `{'foo': {'bar':'baz'}}` results in `foo=%7B%22bar%22%3A%22baz%22%7D` (stringified and encoded representation of an object)\n   *\n   * Note that serializer will sort the request parameters alphabetically.\n   */\n\n  this.$get = function() {\n    return function ngParamSerializer(params) {\n      if (!params) return '';\n      var parts = [];\n      forEachSorted(params, function(value, key) {\n        if (value === null || isUndefined(value) || isFunction(value)) return;\n        if (isArray(value)) {\n          forEach(value, function(v) {\n            parts.push(encodeUriQuery(key)  + '=' + encodeUriQuery(serializeValue(v)));\n          });\n        } else {\n          parts.push(encodeUriQuery(key) + '=' + encodeUriQuery(serializeValue(value)));\n        }\n      });\n\n      return parts.join('&');\n    };\n  };\n}\n\n/** @this */\nfunction $HttpParamSerializerJQLikeProvider() {\n  /**\n   * @ngdoc service\n   * @name $httpParamSerializerJQLike\n   *\n   * @description\n   *\n   * Alternative {@link $http `$http`} params serializer that follows\n   * jQuery's [`param()`](http://api.jquery.com/jquery.param/) method logic.\n   * The serializer will also sort the params alphabetically.\n   *\n   * To use it for serializing `$http` request parameters, set it as the `paramSerializer` property:\n   *\n   * ```js\n   * $http({\n   *   url: myUrl,\n   *   method: 'GET',\n   *   params: myParams,\n   *   paramSerializer: '$httpParamSerializerJQLike'\n   * });\n   * ```\n   *\n   * It is also possible to set it as the default `paramSerializer` in the\n   * {@link $httpProvider#defaults `$httpProvider`}.\n   *\n   * Additionally, you can inject the serializer and use it explicitly, for example to serialize\n   * form data for submission:\n   *\n   * ```js\n   * .controller(function($http, $httpParamSerializerJQLike) {\n   *   //...\n   *\n   *   $http({\n   *     url: myUrl,\n   *     method: 'POST',\n   *     data: $httpParamSerializerJQLike(myData),\n   *     headers: {\n   *       'Content-Type': 'application/x-www-form-urlencoded'\n   *     }\n   *   });\n   *\n   * });\n   * ```\n   *\n   */\n  this.$get = function() {\n    return function jQueryLikeParamSerializer(params) {\n      if (!params) return '';\n      var parts = [];\n      serialize(params, '', true);\n      return parts.join('&');\n\n      function serialize(toSerialize, prefix, topLevel) {\n        if (isArray(toSerialize)) {\n          forEach(toSerialize, function(value, index) {\n            serialize(value, prefix + '[' + (isObject(value) ? index : '') + ']');\n          });\n        } else if (isObject(toSerialize) && !isDate(toSerialize)) {\n          forEachSorted(toSerialize, function(value, key) {\n            serialize(value, prefix +\n                (topLevel ? '' : '[') +\n                key +\n                (topLevel ? '' : ']'));\n          });\n        } else {\n          if (isFunction(toSerialize)) {\n            toSerialize = toSerialize();\n          }\n          parts.push(encodeUriQuery(prefix) + '=' +\n              (toSerialize == null ? '' : encodeUriQuery(serializeValue(toSerialize))));\n        }\n      }\n    };\n  };\n}\n\nfunction defaultHttpResponseTransform(data, headers) {\n  if (isString(data)) {\n    // Strip json vulnerability protection prefix and trim whitespace\n    var tempData = data.replace(JSON_PROTECTION_PREFIX, '').trim();\n\n    if (tempData) {\n      var contentType = headers('Content-Type');\n      var hasJsonContentType = contentType && (contentType.indexOf(APPLICATION_JSON) === 0);\n\n      if (hasJsonContentType || isJsonLike(tempData)) {\n        try {\n          data = fromJson(tempData);\n        } catch (e) {\n          if (!hasJsonContentType) {\n            return data;\n          }\n          throw $httpMinErr('baddata', 'Data must be a valid JSON object. Received: \"{0}\". ' +\n          'Parse error: \"{1}\"', data, e);\n        }\n      }\n    }\n  }\n\n  return data;\n}\n\nfunction isJsonLike(str) {\n    var jsonStart = str.match(JSON_START);\n    return jsonStart && JSON_ENDS[jsonStart[0]].test(str);\n}\n\n/**\n * Parse headers into key value object\n *\n * @param {string} headers Raw headers as a string\n * @returns {Object} Parsed headers as key value object\n */\nfunction parseHeaders(headers) {\n  var parsed = createMap(), i;\n\n  function fillInParsed(key, val) {\n    if (key) {\n      parsed[key] = parsed[key] ? parsed[key] + ', ' + val : val;\n    }\n  }\n\n  if (isString(headers)) {\n    forEach(headers.split('\\n'), function(line) {\n      i = line.indexOf(':');\n      fillInParsed(lowercase(trim(line.substr(0, i))), trim(line.substr(i + 1)));\n    });\n  } else if (isObject(headers)) {\n    forEach(headers, function(headerVal, headerKey) {\n      fillInParsed(lowercase(headerKey), trim(headerVal));\n    });\n  }\n\n  return parsed;\n}\n\n\n/**\n * Returns a function that provides access to parsed headers.\n *\n * Headers are lazy parsed when first requested.\n * @see parseHeaders\n *\n * @param {(string|Object)} headers Headers to provide access to.\n * @returns {function(string=)} Returns a getter function which if called with:\n *\n *   - if called with an argument returns a single header value or null\n *   - if called with no arguments returns an object containing all headers.\n */\nfunction headersGetter(headers) {\n  var headersObj;\n\n  return function(name) {\n    if (!headersObj) headersObj =  parseHeaders(headers);\n\n    if (name) {\n      var value = headersObj[lowercase(name)];\n      if (value === undefined) {\n        value = null;\n      }\n      return value;\n    }\n\n    return headersObj;\n  };\n}\n\n\n/**\n * Chain all given functions\n *\n * This function is used for both request and response transforming\n *\n * @param {*} data Data to transform.\n * @param {function(string=)} headers HTTP headers getter fn.\n * @param {number} status HTTP status code of the response.\n * @param {(Function|Array.<Function>)} fns Function or an array of functions.\n * @returns {*} Transformed data.\n */\nfunction transformData(data, headers, status, fns) {\n  if (isFunction(fns)) {\n    return fns(data, headers, status);\n  }\n\n  forEach(fns, function(fn) {\n    data = fn(data, headers, status);\n  });\n\n  return data;\n}\n\n\nfunction isSuccess(status) {\n  return 200 <= status && status < 300;\n}\n\n\n/**\n * @ngdoc provider\n * @name $httpProvider\n * @this\n *\n * @description\n * Use `$httpProvider` to change the default behavior of the {@link ng.$http $http} service.\n */\nfunction $HttpProvider() {\n  /**\n   * @ngdoc property\n   * @name $httpProvider#defaults\n   * @description\n   *\n   * Object containing default values for all {@link ng.$http $http} requests.\n   *\n   * - **`defaults.cache`** - {boolean|Object} - A boolean value or object created with\n   * {@link ng.$cacheFactory `$cacheFactory`} to enable or disable caching of HTTP responses\n   * by default. See {@link $http#caching $http Caching} for more information.\n   *\n   * - **`defaults.headers`** - {Object} - Default headers for all $http requests.\n   * Refer to {@link ng.$http#setting-http-headers $http} for documentation on\n   * setting default headers.\n   *     - **`defaults.headers.common`**\n   *     - **`defaults.headers.post`**\n   *     - **`defaults.headers.put`**\n   *     - **`defaults.headers.patch`**\n   *\n   * - **`defaults.jsonpCallbackParam`** - `{string}` - the name of the query parameter that passes the name of the\n   * callback in a JSONP request. The value of this parameter will be replaced with the expression generated by the\n   * {@link $jsonpCallbacks} service. Defaults to `'callback'`.\n   *\n   * - **`defaults.paramSerializer`** - `{string|function(Object<string,string>):string}` - A function\n   *  used to the prepare string representation of request parameters (specified as an object).\n   *  If specified as string, it is interpreted as a function registered with the {@link auto.$injector $injector}.\n   *  Defaults to {@link ng.$httpParamSerializer $httpParamSerializer}.\n   *\n   * - **`defaults.transformRequest`** -\n   * `{Array<function(data, headersGetter)>|function(data, headersGetter)}` -\n   * An array of functions (or a single function) which are applied to the request data.\n   * By default, this is an array with one request transformation function:\n   *\n   *   - If the `data` property of the request configuration object contains an object, serialize it\n   *     into JSON format.\n   *\n   * - **`defaults.transformResponse`** -\n   * `{Array<function(data, headersGetter, status)>|function(data, headersGetter, status)}` -\n   * An array of functions (or a single function) which are applied to the response data. By default,\n   * this is an array which applies one response transformation function that does two things:\n   *\n   *  - If XSRF prefix is detected, strip it\n   *    (see {@link ng.$http#security-considerations Security Considerations in the $http docs}).\n   *  - If the `Content-Type` is `application/json` or the response looks like JSON,\n   *    deserialize it using a JSON parser.\n   *\n   * - **`defaults.xsrfCookieName`** - {string} - Name of cookie containing the XSRF token.\n   * Defaults value is `'XSRF-TOKEN'`.\n   *\n   * - **`defaults.xsrfHeaderName`** - {string} - Name of HTTP header to populate with the\n   * XSRF token. Defaults value is `'X-XSRF-TOKEN'`.\n   *\n   */\n  var defaults = this.defaults = {\n    // transform incoming response data\n    transformResponse: [defaultHttpResponseTransform],\n\n    // transform outgoing request data\n    transformRequest: [function(d) {\n      return isObject(d) && !isFile(d) && !isBlob(d) && !isFormData(d) ? toJson(d) : d;\n    }],\n\n    // default headers\n    headers: {\n      common: {\n        'Accept': 'application/json, text/plain, */*'\n      },\n      post:   shallowCopy(CONTENT_TYPE_APPLICATION_JSON),\n      put:    shallowCopy(CONTENT_TYPE_APPLICATION_JSON),\n      patch:  shallowCopy(CONTENT_TYPE_APPLICATION_JSON)\n    },\n\n    xsrfCookieName: 'XSRF-TOKEN',\n    xsrfHeaderName: 'X-XSRF-TOKEN',\n\n    paramSerializer: '$httpParamSerializer',\n\n    jsonpCallbackParam: 'callback'\n  };\n\n  var useApplyAsync = false;\n  /**\n   * @ngdoc method\n   * @name $httpProvider#useApplyAsync\n   * @description\n   *\n   * Configure $http service to combine processing of multiple http responses received at around\n   * the same time via {@link ng.$rootScope.Scope#$applyAsync $rootScope.$applyAsync}. This can result in\n   * significant performance improvement for bigger applications that make many HTTP requests\n   * concurrently (common during application bootstrap).\n   *\n   * Defaults to false. If no value is specified, returns the current configured value.\n   *\n   * @param {boolean=} value If true, when requests are loaded, they will schedule a deferred\n   *    \"apply\" on the next tick, giving time for subsequent requests in a roughly ~10ms window\n   *    to load and share the same digest cycle.\n   *\n   * @returns {boolean|Object} If a value is specified, returns the $httpProvider for chaining.\n   *    otherwise, returns the current configured value.\n   */\n  this.useApplyAsync = function(value) {\n    if (isDefined(value)) {\n      useApplyAsync = !!value;\n      return this;\n    }\n    return useApplyAsync;\n  };\n\n  /**\n   * @ngdoc property\n   * @name $httpProvider#interceptors\n   * @description\n   *\n   * Array containing service factories for all synchronous or asynchronous {@link ng.$http $http}\n   * pre-processing of request or postprocessing of responses.\n   *\n   * These service factories are ordered by request, i.e. they are applied in the same order as the\n   * array, on request, but reverse order, on response.\n   *\n   * {@link ng.$http#interceptors Interceptors detailed info}\n   */\n  var interceptorFactories = this.interceptors = [];\n\n  /**\n   * @ngdoc property\n   * @name $httpProvider#xsrfTrustedOrigins\n   * @description\n   *\n   * Array containing URLs whose origins are trusted to receive the XSRF token. See the\n   * {@link ng.$http#security-considerations Security Considerations} sections for more details on\n   * XSRF.\n   *\n   * **Note:** An \"origin\" consists of the [URI scheme](https://en.wikipedia.org/wiki/URI_scheme),\n   * the [hostname](https://en.wikipedia.org/wiki/Hostname) and the\n   * [port number](https://en.wikipedia.org/wiki/Port_(computer_networking). For `http:` and\n   * `https:`, the port number can be omitted if using th default ports (80 and 443 respectively).\n   * Examples: `http://example.com`, `https://api.example.com:9876`\n   *\n   * <div class=\"alert alert-warning\">\n   *   It is not possible to trust specific URLs/paths. The `path`, `query` and `fragment` parts\n   *   of a URL will be ignored. For example, `https://foo.com/path/bar?query=baz#fragment` will be\n   *   treated as `https://foo.com`, meaning that **all** requests to URLs starting with\n   *   `https://foo.com/` will include the XSRF token.\n   * </div>\n   *\n   * @example\n   *\n   * ```js\n   * // App served from `https://example.com/`.\n   * angular.\n   *   module('xsrfTrustedOriginsExample', []).\n   *   config(['$httpProvider', function($httpProvider) {\n   *     $httpProvider.xsrfTrustedOrigins.push('https://api.example.com');\n   *   }]).\n   *   run(['$http', function($http) {\n   *     // The XSRF token will be sent.\n   *     $http.get('https://api.example.com/preferences').then(...);\n   *\n   *     // The XSRF token will NOT be sent.\n   *     $http.get('https://stats.example.com/activity').then(...);\n   *   }]);\n   * ```\n   */\n  var xsrfTrustedOrigins = this.xsrfTrustedOrigins = [];\n\n  /**\n   * @ngdoc property\n   * @name $httpProvider#xsrfWhitelistedOrigins\n   * @description\n   *\n   * @deprecated\n   * sinceVersion=\"1.8.1\"\n   *\n   * This property is deprecated. Use {@link $httpProvider#xsrfTrustedOrigins xsrfTrustedOrigins}\n   * instead.\n   */\n  Object.defineProperty(this, 'xsrfWhitelistedOrigins', {\n    get: function() {\n      return this.xsrfTrustedOrigins;\n    },\n    set: function(origins) {\n      this.xsrfTrustedOrigins = origins;\n    }\n  });\n\n  this.$get = ['$browser', '$httpBackend', '$$cookieReader', '$cacheFactory', '$rootScope', '$q', '$injector', '$sce',\n      function($browser, $httpBackend, $$cookieReader, $cacheFactory, $rootScope, $q, $injector, $sce) {\n\n    var defaultCache = $cacheFactory('$http');\n\n    /**\n     * Make sure that default param serializer is exposed as a function\n     */\n    defaults.paramSerializer = isString(defaults.paramSerializer) ?\n      $injector.get(defaults.paramSerializer) : defaults.paramSerializer;\n\n    /**\n     * Interceptors stored in reverse order. Inner interceptors before outer interceptors.\n     * The reversal is needed so that we can build up the interception chain around the\n     * server request.\n     */\n    var reversedInterceptors = [];\n\n    forEach(interceptorFactories, function(interceptorFactory) {\n      reversedInterceptors.unshift(isString(interceptorFactory)\n          ? $injector.get(interceptorFactory) : $injector.invoke(interceptorFactory));\n    });\n\n    /**\n     * A function to check request URLs against a list of allowed origins.\n     */\n    var urlIsAllowedOrigin = urlIsAllowedOriginFactory(xsrfTrustedOrigins);\n\n    /**\n     * @ngdoc service\n     * @kind function\n     * @name $http\n     * @requires ng.$httpBackend\n     * @requires $cacheFactory\n     * @requires $rootScope\n     * @requires $q\n     * @requires $injector\n     *\n     * @description\n     * The `$http` service is a core AngularJS service that facilitates communication with the remote\n     * HTTP servers via the browser's [XMLHttpRequest](https://developer.mozilla.org/en/xmlhttprequest)\n     * object or via [JSONP](http://en.wikipedia.org/wiki/JSONP).\n     *\n     * For unit testing applications that use `$http` service, see\n     * {@link ngMock.$httpBackend $httpBackend mock}.\n     *\n     * For a higher level of abstraction, please check out the {@link ngResource.$resource\n     * $resource} service.\n     *\n     * The $http API is based on the {@link ng.$q deferred/promise APIs} exposed by\n     * the $q service. While for simple usage patterns this doesn't matter much, for advanced usage\n     * it is important to familiarize yourself with these APIs and the guarantees they provide.\n     *\n     *\n     * ## General usage\n     * The `$http` service is a function which takes a single argument — a {@link $http#usage configuration object} —\n     * that is used to generate an HTTP request and returns  a {@link ng.$q promise} that is\n     * resolved (request success) or rejected (request failure) with a\n     * {@link ng.$http#$http-returns response} object.\n     *\n     * ```js\n     *   // Simple GET request example:\n     *   $http({\n     *     method: 'GET',\n     *     url: '/someUrl'\n     *   }).then(function successCallback(response) {\n     *       // this callback will be called asynchronously\n     *       // when the response is available\n     *     }, function errorCallback(response) {\n     *       // called asynchronously if an error occurs\n     *       // or server returns response with an error status.\n     *     });\n     * ```\n     *\n     *\n     * ## Shortcut methods\n     *\n     * Shortcut methods are also available. All shortcut methods require passing in the URL, and\n     * request data must be passed in for POST/PUT requests. An optional config can be passed as the\n     * last argument.\n     *\n     * ```js\n     *   $http.get('/someUrl', config).then(successCallback, errorCallback);\n     *   $http.post('/someUrl', data, config).then(successCallback, errorCallback);\n     * ```\n     *\n     * Complete list of shortcut methods:\n     *\n     * - {@link ng.$http#get $http.get}\n     * - {@link ng.$http#head $http.head}\n     * - {@link ng.$http#post $http.post}\n     * - {@link ng.$http#put $http.put}\n     * - {@link ng.$http#delete $http.delete}\n     * - {@link ng.$http#jsonp $http.jsonp}\n     * - {@link ng.$http#patch $http.patch}\n     *\n     *\n     * ## Writing Unit Tests that use $http\n     * When unit testing (using {@link ngMock ngMock}), it is necessary to call\n     * {@link ngMock.$httpBackend#flush $httpBackend.flush()} to flush each pending\n     * request using trained responses.\n     *\n     * ```\n     * $httpBackend.expectGET(...);\n     * $http.get(...);\n     * $httpBackend.flush();\n     * ```\n     *\n     * ## Setting HTTP Headers\n     *\n     * The $http service will automatically add certain HTTP headers to all requests. These defaults\n     * can be fully configured by accessing the `$httpProvider.defaults.headers` configuration\n     * object, which currently contains this default configuration:\n     *\n     * - `$httpProvider.defaults.headers.common` (headers that are common for all requests):\n     *   - <code>Accept: application/json, text/plain, \\*&#65279;/&#65279;\\*</code>\n     * - `$httpProvider.defaults.headers.post`: (header defaults for POST requests)\n     *   - `Content-Type: application/json`\n     * - `$httpProvider.defaults.headers.put` (header defaults for PUT requests)\n     *   - `Content-Type: application/json`\n     *\n     * To add or overwrite these defaults, simply add or remove a property from these configuration\n     * objects. To add headers for an HTTP method other than POST or PUT, simply add a new object\n     * with the lowercased HTTP method name as the key, e.g.\n     * `$httpProvider.defaults.headers.get = { 'My-Header' : 'value' }`.\n     *\n     * The defaults can also be set at runtime via the `$http.defaults` object in the same\n     * fashion. For example:\n     *\n     * ```\n     * module.run(function($http) {\n     *   $http.defaults.headers.common.Authorization = 'Basic YmVlcDpib29w';\n     * });\n     * ```\n     *\n     * In addition, you can supply a `headers` property in the config object passed when\n     * calling `$http(config)`, which overrides the defaults without changing them globally.\n     *\n     * To explicitly remove a header automatically added via $httpProvider.defaults.headers on a per request basis,\n     * Use the `headers` property, setting the desired header to `undefined`. For example:\n     *\n     * ```js\n     * var req = {\n     *  method: 'POST',\n     *  url: 'http://example.com',\n     *  headers: {\n     *    'Content-Type': undefined\n     *  },\n     *  data: { test: 'test' }\n     * }\n     *\n     * $http(req).then(function(){...}, function(){...});\n     * ```\n     *\n     * ## Transforming Requests and Responses\n     *\n     * Both requests and responses can be transformed using transformation functions: `transformRequest`\n     * and `transformResponse`. These properties can be a single function that returns\n     * the transformed value (`function(data, headersGetter, status)`) or an array of such transformation functions,\n     * which allows you to `push` or `unshift` a new transformation function into the transformation chain.\n     *\n     * <div class=\"alert alert-warning\">\n     * **Note:** AngularJS does not make a copy of the `data` parameter before it is passed into the `transformRequest` pipeline.\n     * That means changes to the properties of `data` are not local to the transform function (since Javascript passes objects by reference).\n     * For example, when calling `$http.get(url, $scope.myObject)`, modifications to the object's properties in a transformRequest\n     * function will be reflected on the scope and in any templates where the object is data-bound.\n     * To prevent this, transform functions should have no side-effects.\n     * If you need to modify properties, it is recommended to make a copy of the data, or create new object to return.\n     * </div>\n     *\n     * ### Default Transformations\n     *\n     * The `$httpProvider` provider and `$http` service expose `defaults.transformRequest` and\n     * `defaults.transformResponse` properties. If a request does not provide its own transformations\n     * then these will be applied.\n     *\n     * You can augment or replace the default transformations by modifying these properties by adding to or\n     * replacing the array.\n     *\n     * AngularJS provides the following default transformations:\n     *\n     * Request transformations (`$httpProvider.defaults.transformRequest` and `$http.defaults.transformRequest`) is\n     * an array with one function that does the following:\n     *\n     * - If the `data` property of the request configuration object contains an object, serialize it\n     *   into JSON format.\n     *\n     * Response transformations (`$httpProvider.defaults.transformResponse` and `$http.defaults.transformResponse`) is\n     * an array with one function that does the following:\n     *\n     *  - If XSRF prefix is detected, strip it (see Security Considerations section below).\n     *  - If the `Content-Type` is `application/json` or the response looks like JSON,\n   *      deserialize it using a JSON parser.\n     *\n     *\n     * ### Overriding the Default Transformations Per Request\n     *\n     * If you wish to override the request/response transformations only for a single request then provide\n     * `transformRequest` and/or `transformResponse` properties on the configuration object passed\n     * into `$http`.\n     *\n     * Note that if you provide these properties on the config object the default transformations will be\n     * overwritten. If you wish to augment the default transformations then you must include them in your\n     * local transformation array.\n     *\n     * The following code demonstrates adding a new response transformation to be run after the default response\n     * transformations have been run.\n     *\n     * ```js\n     * function appendTransform(defaults, transform) {\n     *\n     *   // We can't guarantee that the default transformation is an array\n     *   defaults = angular.isArray(defaults) ? defaults : [defaults];\n     *\n     *   // Append the new transformation to the defaults\n     *   return defaults.concat(transform);\n     * }\n     *\n     * $http({\n     *   url: '...',\n     *   method: 'GET',\n     *   transformResponse: appendTransform($http.defaults.transformResponse, function(value) {\n     *     return doTransform(value);\n     *   })\n     * });\n     * ```\n     *\n     *\n     * ## Caching\n     *\n     * {@link ng.$http `$http`} responses are not cached by default. To enable caching, you must\n     * set the config.cache value or the default cache value to TRUE or to a cache object (created\n     * with {@link ng.$cacheFactory `$cacheFactory`}). If defined, the value of config.cache takes\n     * precedence over the default cache value.\n     *\n     * In order to:\n     *   * cache all responses - set the default cache value to TRUE or to a cache object\n     *   * cache a specific response - set config.cache value to TRUE or to a cache object\n     *\n     * If caching is enabled, but neither the default cache nor config.cache are set to a cache object,\n     * then the default `$cacheFactory(\"$http\")` object is used.\n     *\n     * The default cache value can be set by updating the\n     * {@link ng.$http#defaults `$http.defaults.cache`} property or the\n     * {@link $httpProvider#defaults `$httpProvider.defaults.cache`} property.\n     *\n     * When caching is enabled, {@link ng.$http `$http`} stores the response from the server using\n     * the relevant cache object. The next time the same request is made, the response is returned\n     * from the cache without sending a request to the server.\n     *\n     * Take note that:\n     *\n     *   * Only GET and JSONP requests are cached.\n     *   * The cache key is the request URL including search parameters; headers are not considered.\n     *   * Cached responses are returned asynchronously, in the same way as responses from the server.\n     *   * If multiple identical requests are made using the same cache, which is not yet populated,\n     *     one request will be made to the server and remaining requests will return the same response.\n     *   * A cache-control header on the response does not affect if or how responses are cached.\n     *\n     *\n     * ## Interceptors\n     *\n     * Before you start creating interceptors, be sure to understand the\n     * {@link ng.$q $q and deferred/promise APIs}.\n     *\n     * For purposes of global error handling, authentication, or any kind of synchronous or\n     * asynchronous pre-processing of request or postprocessing of responses, it is desirable to be\n     * able to intercept requests before they are handed to the server and\n     * responses before they are handed over to the application code that\n     * initiated these requests. The interceptors leverage the {@link ng.$q\n     * promise APIs} to fulfill this need for both synchronous and asynchronous pre-processing.\n     *\n     * The interceptors are service factories that are registered with the `$httpProvider` by\n     * adding them to the `$httpProvider.interceptors` array. The factory is called and\n     * injected with dependencies (if specified) and returns the interceptor.\n     *\n     * There are two kinds of interceptors (and two kinds of rejection interceptors):\n     *\n     *   * `request`: interceptors get called with a http {@link $http#usage config} object. The function is free to\n     *     modify the `config` object or create a new one. The function needs to return the `config`\n     *     object directly, or a promise containing the `config` or a new `config` object.\n     *   * `requestError`: interceptor gets called when a previous interceptor threw an error or\n     *     resolved with a rejection.\n     *   * `response`: interceptors get called with http `response` object. The function is free to\n     *     modify the `response` object or create a new one. The function needs to return the `response`\n     *     object directly, or as a promise containing the `response` or a new `response` object.\n     *   * `responseError`: interceptor gets called when a previous interceptor threw an error or\n     *     resolved with a rejection.\n     *\n     *\n     * ```js\n     *   // register the interceptor as a service\n     *   $provide.factory('myHttpInterceptor', function($q, dependency1, dependency2) {\n     *     return {\n     *       // optional method\n     *       'request': function(config) {\n     *         // do something on success\n     *         return config;\n     *       },\n     *\n     *       // optional method\n     *      'requestError': function(rejection) {\n     *         // do something on error\n     *         if (canRecover(rejection)) {\n     *           return responseOrNewPromise\n     *         }\n     *         return $q.reject(rejection);\n     *       },\n     *\n     *\n     *\n     *       // optional method\n     *       'response': function(response) {\n     *         // do something on success\n     *         return response;\n     *       },\n     *\n     *       // optional method\n     *      'responseError': function(rejection) {\n     *         // do something on error\n     *         if (canRecover(rejection)) {\n     *           return responseOrNewPromise\n     *         }\n     *         return $q.reject(rejection);\n     *       }\n     *     };\n     *   });\n     *\n     *   $httpProvider.interceptors.push('myHttpInterceptor');\n     *\n     *\n     *   // alternatively, register the interceptor via an anonymous factory\n     *   $httpProvider.interceptors.push(function($q, dependency1, dependency2) {\n     *     return {\n     *      'request': function(config) {\n     *          // same as above\n     *       },\n     *\n     *       'response': function(response) {\n     *          // same as above\n     *       }\n     *     };\n     *   });\n     * ```\n     *\n     * ## Security Considerations\n     *\n     * When designing web applications, consider security threats from:\n     *\n     * - [JSON vulnerability](http://haacked.com/archive/2008/11/20/anatomy-of-a-subtle-json-vulnerability.aspx)\n     * - [XSRF](http://en.wikipedia.org/wiki/Cross-site_request_forgery)\n     *\n     * Both server and the client must cooperate in order to eliminate these threats. AngularJS comes\n     * pre-configured with strategies that address these issues, but for this to work backend server\n     * cooperation is required.\n     *\n     * ### JSON Vulnerability Protection\n     *\n     * A [JSON vulnerability](http://haacked.com/archive/2008/11/20/anatomy-of-a-subtle-json-vulnerability.aspx)\n     * allows third party website to turn your JSON resource URL into\n     * [JSONP](http://en.wikipedia.org/wiki/JSONP) request under some conditions. To\n     * counter this your server can prefix all JSON requests with following string `\")]}',\\n\"`.\n     * AngularJS will automatically strip the prefix before processing it as JSON.\n     *\n     * For example if your server needs to return:\n     * ```js\n     * ['one','two']\n     * ```\n     *\n     * which is vulnerable to attack, your server can return:\n     * ```js\n     * )]}',\n     * ['one','two']\n     * ```\n     *\n     * AngularJS will strip the prefix, before processing the JSON.\n     *\n     *\n     * ### Cross Site Request Forgery (XSRF) Protection\n     *\n     * [XSRF](http://en.wikipedia.org/wiki/Cross-site_request_forgery) is an attack technique by\n     * which the attacker can trick an authenticated user into unknowingly executing actions on your\n     * website. AngularJS provides a mechanism to counter XSRF. When performing XHR requests, the\n     * $http service reads a token from a cookie (by default, `XSRF-TOKEN`) and sets it as an HTTP\n     * header (by default `X-XSRF-TOKEN`). Since only JavaScript that runs on your domain could read\n     * the cookie, your server can be assured that the XHR came from JavaScript running on your\n     * domain.\n     *\n     * To take advantage of this, your server needs to set a token in a JavaScript readable session\n     * cookie called `XSRF-TOKEN` on the first HTTP GET request. On subsequent XHR requests the\n     * server can verify that the cookie matches the `X-XSRF-TOKEN` HTTP header, and therefore be\n     * sure that only JavaScript running on your domain could have sent the request. The token must\n     * be unique for each user and must be verifiable by the server (to prevent the JavaScript from\n     * making up its own tokens). We recommend that the token is a digest of your site's\n     * authentication cookie with a [salt](https://en.wikipedia.org/wiki/Salt_(cryptography&#41;)\n     * for added security.\n     *\n     * The header will &mdash; by default &mdash; **not** be set for cross-domain requests. This\n     * prevents unauthorized servers (e.g. malicious or compromised 3rd-party APIs) from gaining\n     * access to your users' XSRF tokens and exposing them to Cross Site Request Forgery. If you\n     * want to, you can trust additional origins to also receive the XSRF token, by adding them\n     * to {@link ng.$httpProvider#xsrfTrustedOrigins xsrfTrustedOrigins}. This might be\n     * useful, for example, if your application, served from `example.com`, needs to access your API\n     * at `api.example.com`.\n     * See {@link ng.$httpProvider#xsrfTrustedOrigins $httpProvider.xsrfTrustedOrigins} for\n     * more details.\n     *\n     * <div class=\"alert alert-danger\">\n     *   **Warning**<br />\n     *   Only trusted origins that you have control over and make sure you understand the\n     *   implications of doing so.\n     * </div>\n     *\n     * The name of the cookie and the header can be specified using the `xsrfCookieName` and\n     * `xsrfHeaderName` properties of either `$httpProvider.defaults` at config-time,\n     * `$http.defaults` at run-time, or the per-request config object.\n     *\n     * In order to prevent collisions in environments where multiple AngularJS apps share the\n     * same domain or subdomain, we recommend that each application uses a unique cookie name.\n     *\n     *\n     * @param {object} config Object describing the request to be made and how it should be\n     *    processed. The object has following properties:\n     *\n     *    - **method** – `{string}` – HTTP method (e.g. 'GET', 'POST', etc)\n     *    - **url** – `{string|TrustedObject}` – Absolute or relative URL of the resource that is being requested;\n     *      or an object created by a call to `$sce.trustAsResourceUrl(url)`.\n     *    - **params** – `{Object.<string|Object>}` – Map of strings or objects which will be serialized\n     *      with the `paramSerializer` and appended as GET parameters.\n     *    - **data** – `{string|Object}` – Data to be sent as the request message data.\n     *    - **headers** – `{Object}` – Map of strings or functions which return strings representing\n     *      HTTP headers to send to the server. If the return value of a function is null, the\n     *      header will not be sent. Functions accept a config object as an argument.\n     *    - **eventHandlers** - `{Object}` - Event listeners to be bound to the XMLHttpRequest object.\n     *      To bind events to the XMLHttpRequest upload object, use `uploadEventHandlers`.\n     *      The handler will be called in the context of a `$apply` block.\n     *    - **uploadEventHandlers** - `{Object}` - Event listeners to be bound to the XMLHttpRequest upload\n     *      object. To bind events to the XMLHttpRequest object, use `eventHandlers`.\n     *      The handler will be called in the context of a `$apply` block.\n     *    - **xsrfHeaderName** – `{string}` – Name of HTTP header to populate with the XSRF token.\n     *    - **xsrfCookieName** – `{string}` – Name of cookie containing the XSRF token.\n     *    - **transformRequest** –\n     *      `{function(data, headersGetter)|Array.<function(data, headersGetter)>}` –\n     *      transform function or an array of such functions. The transform function takes the http\n     *      request body and headers and returns its transformed (typically serialized) version.\n     *      See {@link ng.$http#overriding-the-default-transformations-per-request\n     *      Overriding the Default Transformations}\n     *    - **transformResponse** –\n     *      `{function(data, headersGetter, status)|Array.<function(data, headersGetter, status)>}` –\n     *      transform function or an array of such functions. The transform function takes the http\n     *      response body, headers and status and returns its transformed (typically deserialized) version.\n     *      See {@link ng.$http#overriding-the-default-transformations-per-request\n     *      Overriding the Default Transformations}\n     *    - **paramSerializer** - `{string|function(Object<string,string>):string}` - A function used to\n     *      prepare the string representation of request parameters (specified as an object).\n     *      If specified as string, it is interpreted as function registered with the\n     *      {@link $injector $injector}, which means you can create your own serializer\n     *      by registering it as a {@link auto.$provide#service service}.\n     *      The default serializer is the {@link $httpParamSerializer $httpParamSerializer};\n     *      alternatively, you can use the {@link $httpParamSerializerJQLike $httpParamSerializerJQLike}\n     *    - **cache** – `{boolean|Object}` – A boolean value or object created with\n     *      {@link ng.$cacheFactory `$cacheFactory`} to enable or disable caching of the HTTP response.\n     *      See {@link $http#caching $http Caching} for more information.\n     *    - **timeout** – `{number|Promise}` – timeout in milliseconds, or {@link ng.$q promise}\n     *      that should abort the request when resolved.\n     *\n     *      A numerical timeout or a promise returned from {@link ng.$timeout $timeout}, will set\n     *      the `xhrStatus` in the {@link $http#$http-returns response} to \"timeout\", and any other\n     *      resolved promise will set it to \"abort\", following standard XMLHttpRequest behavior.\n     *\n     *    - **withCredentials** - `{boolean}` - whether to set the `withCredentials` flag on the\n     *      XHR object. See [requests with credentials](https://developer.mozilla.org/docs/Web/HTTP/Access_control_CORS#Requests_with_credentials)\n     *      for more information.\n     *    - **responseType** - `{string}` - see\n     *      [XMLHttpRequest.responseType](https://developer.mozilla.org/en-US/docs/Web/API/XMLHttpRequest#xmlhttprequest-responsetype).\n     *\n     * @returns {HttpPromise} A {@link ng.$q `Promise}` that will be resolved (request success)\n     *   or rejected (request failure) with a response object.\n     *\n     *   The response object has these properties:\n     *\n     *   - **data** – `{string|Object}` – The response body transformed with\n     *     the transform functions.\n     *   - **status** – `{number}` – HTTP status code of the response.\n     *   - **headers** – `{function([headerName])}` – Header getter function.\n     *   - **config** – `{Object}` – The configuration object that was used\n     *     to generate the request.\n     *   - **statusText** – `{string}` – HTTP status text of the response.\n     *   - **xhrStatus** – `{string}` – Status of the XMLHttpRequest\n     *     (`complete`, `error`, `timeout` or `abort`).\n     *\n     *\n     *   A response status code between 200 and 299 is considered a success status\n     *   and will result in the success callback being called. Any response status\n     *   code outside of that range is considered an error status and will result\n     *   in the error callback being called.\n     *   Also, status codes less than -1 are normalized to zero. -1 usually means\n     *   the request was aborted, e.g. using a `config.timeout`. More information\n     *   about the status might be available in the `xhrStatus` property.\n     *\n     *   Note that if the response is a redirect, XMLHttpRequest will transparently\n     *   follow it, meaning that the outcome (success or error) will be determined\n     *   by the final response status code.\n     *\n     *\n     * @property {Array.<Object>} pendingRequests Array of config objects for currently pending\n     *   requests. This is primarily meant to be used for debugging purposes.\n     *\n     *\n     * @example\n<example module=\"httpExample\" name=\"http-service\">\n<file name=\"index.html\">\n  <div ng-controller=\"FetchController\">\n    <select ng-model=\"method\" aria-label=\"Request method\">\n      <option>GET</option>\n      <option>JSONP</option>\n    </select>\n    <input type=\"text\" ng-model=\"url\" size=\"80\" aria-label=\"URL\" />\n    <button id=\"fetchbtn\" ng-click=\"fetch()\">fetch</button><br>\n    <button id=\"samplegetbtn\" ng-click=\"updateModel('GET', 'http-hello.html')\">Sample GET</button>\n    <button id=\"samplejsonpbtn\"\n      ng-click=\"updateModel('JSONP',\n                    'https://angularjs.org/greet.php?name=Super%20Hero')\">\n      Sample JSONP\n    </button>\n    <button id=\"invalidjsonpbtn\"\n      ng-click=\"updateModel('JSONP', 'https://angularjs.org/doesntexist')\">\n        Invalid JSONP\n      </button>\n    <pre>http status code: {{status}}</pre>\n    <pre>http response data: {{data}}</pre>\n  </div>\n</file>\n<file name=\"script.js\">\n  angular.module('httpExample', [])\n    .config(['$sceDelegateProvider', function($sceDelegateProvider) {\n      // We must add the JSONP endpoint that we are using to the trusted list to show that we trust it\n      $sceDelegateProvider.trustedResourceUrlList([\n        'self',\n        'https://angularjs.org/**'\n      ]);\n    }])\n    .controller('FetchController', ['$scope', '$http', '$templateCache',\n      function($scope, $http, $templateCache) {\n        $scope.method = 'GET';\n        $scope.url = 'http-hello.html';\n\n        $scope.fetch = function() {\n          $scope.code = null;\n          $scope.response = null;\n\n          $http({method: $scope.method, url: $scope.url, cache: $templateCache}).\n            then(function(response) {\n              $scope.status = response.status;\n              $scope.data = response.data;\n            }, function(response) {\n              $scope.data = response.data || 'Request failed';\n              $scope.status = response.status;\n          });\n        };\n\n        $scope.updateModel = function(method, url) {\n          $scope.method = method;\n          $scope.url = url;\n        };\n      }]);\n</file>\n<file name=\"http-hello.html\">\n  Hello, $http!\n</file>\n<file name=\"protractor.js\" type=\"protractor\">\n  var status = element(by.binding('status'));\n  var data = element(by.binding('data'));\n  var fetchBtn = element(by.id('fetchbtn'));\n  var sampleGetBtn = element(by.id('samplegetbtn'));\n  var invalidJsonpBtn = element(by.id('invalidjsonpbtn'));\n\n  it('should make an xhr GET request', function() {\n    sampleGetBtn.click();\n    fetchBtn.click();\n    expect(status.getText()).toMatch('200');\n    expect(data.getText()).toMatch(/Hello, \\$http!/);\n  });\n\n// Commented out due to flakes. See https://github.com/angular/angular.js/issues/9185\n// it('should make a JSONP request to angularjs.org', function() {\n//   var sampleJsonpBtn = element(by.id('samplejsonpbtn'));\n//   sampleJsonpBtn.click();\n//   fetchBtn.click();\n//   expect(status.getText()).toMatch('200');\n//   expect(data.getText()).toMatch(/Super Hero!/);\n// });\n\n  it('should make JSONP request to invalid URL and invoke the error handler',\n      function() {\n    invalidJsonpBtn.click();\n    fetchBtn.click();\n    expect(status.getText()).toMatch('0');\n    expect(data.getText()).toMatch('Request failed');\n  });\n</file>\n</example>\n     */\n    function $http(requestConfig) {\n\n      if (!isObject(requestConfig)) {\n        throw minErr('$http')('badreq', 'Http request configuration must be an object.  Received: {0}', requestConfig);\n      }\n\n      if (!isString($sce.valueOf(requestConfig.url))) {\n        throw minErr('$http')('badreq', 'Http request configuration url must be a string or a $sce trusted object.  Received: {0}', requestConfig.url);\n      }\n\n      var config = extend({\n        method: 'get',\n        transformRequest: defaults.transformRequest,\n        transformResponse: defaults.transformResponse,\n        paramSerializer: defaults.paramSerializer,\n        jsonpCallbackParam: defaults.jsonpCallbackParam\n      }, requestConfig);\n\n      config.headers = mergeHeaders(requestConfig);\n      config.method = uppercase(config.method);\n      config.paramSerializer = isString(config.paramSerializer) ?\n          $injector.get(config.paramSerializer) : config.paramSerializer;\n\n      $browser.$$incOutstandingRequestCount('$http');\n\n      var requestInterceptors = [];\n      var responseInterceptors = [];\n      var promise = $q.resolve(config);\n\n      // apply interceptors\n      forEach(reversedInterceptors, function(interceptor) {\n        if (interceptor.request || interceptor.requestError) {\n          requestInterceptors.unshift(interceptor.request, interceptor.requestError);\n        }\n        if (interceptor.response || interceptor.responseError) {\n          responseInterceptors.push(interceptor.response, interceptor.responseError);\n        }\n      });\n\n      promise = chainInterceptors(promise, requestInterceptors);\n      promise = promise.then(serverRequest);\n      promise = chainInterceptors(promise, responseInterceptors);\n      promise = promise.finally(completeOutstandingRequest);\n\n      return promise;\n\n\n      function chainInterceptors(promise, interceptors) {\n        for (var i = 0, ii = interceptors.length; i < ii;) {\n          var thenFn = interceptors[i++];\n          var rejectFn = interceptors[i++];\n\n          promise = promise.then(thenFn, rejectFn);\n        }\n\n        interceptors.length = 0;\n\n        return promise;\n      }\n\n      function completeOutstandingRequest() {\n        $browser.$$completeOutstandingRequest(noop, '$http');\n      }\n\n      function executeHeaderFns(headers, config) {\n        var headerContent, processedHeaders = {};\n\n        forEach(headers, function(headerFn, header) {\n          if (isFunction(headerFn)) {\n            headerContent = headerFn(config);\n            if (headerContent != null) {\n              processedHeaders[header] = headerContent;\n            }\n          } else {\n            processedHeaders[header] = headerFn;\n          }\n        });\n\n        return processedHeaders;\n      }\n\n      function mergeHeaders(config) {\n        var defHeaders = defaults.headers,\n            reqHeaders = extend({}, config.headers),\n            defHeaderName, lowercaseDefHeaderName, reqHeaderName;\n\n        defHeaders = extend({}, defHeaders.common, defHeaders[lowercase(config.method)]);\n\n        // using for-in instead of forEach to avoid unnecessary iteration after header has been found\n        defaultHeadersIteration:\n        for (defHeaderName in defHeaders) {\n          lowercaseDefHeaderName = lowercase(defHeaderName);\n\n          for (reqHeaderName in reqHeaders) {\n            if (lowercase(reqHeaderName) === lowercaseDefHeaderName) {\n              continue defaultHeadersIteration;\n            }\n          }\n\n          reqHeaders[defHeaderName] = defHeaders[defHeaderName];\n        }\n\n        // execute if header value is a function for merged headers\n        return executeHeaderFns(reqHeaders, shallowCopy(config));\n      }\n\n      function serverRequest(config) {\n        var headers = config.headers;\n        var reqData = transformData(config.data, headersGetter(headers), undefined, config.transformRequest);\n\n        // strip content-type if data is undefined\n        if (isUndefined(reqData)) {\n          forEach(headers, function(value, header) {\n            if (lowercase(header) === 'content-type') {\n              delete headers[header];\n            }\n          });\n        }\n\n        if (isUndefined(config.withCredentials) && !isUndefined(defaults.withCredentials)) {\n          config.withCredentials = defaults.withCredentials;\n        }\n\n        // send request\n        return sendReq(config, reqData).then(transformResponse, transformResponse);\n      }\n\n      function transformResponse(response) {\n        // make a copy since the response must be cacheable\n        var resp = extend({}, response);\n        resp.data = transformData(response.data, response.headers, response.status,\n                                  config.transformResponse);\n        return (isSuccess(response.status))\n          ? resp\n          : $q.reject(resp);\n      }\n    }\n\n    $http.pendingRequests = [];\n\n    /**\n     * @ngdoc method\n     * @name $http#get\n     *\n     * @description\n     * Shortcut method to perform `GET` request.\n     *\n     * @param {string|TrustedObject} url Absolute or relative URL of the resource that is being requested;\n     *                                   or an object created by a call to `$sce.trustAsResourceUrl(url)`.\n     * @param {Object=} config Optional configuration object. See {@link ng.$http#$http-arguments `$http()` arguments}.\n     * @returns {HttpPromise}  A Promise that will be resolved or rejected with a response object.\n     * See {@link ng.$http#$http-returns `$http()` return value}.\n     */\n\n    /**\n     * @ngdoc method\n     * @name $http#delete\n     *\n     * @description\n     * Shortcut method to perform `DELETE` request.\n     *\n     * @param {string|TrustedObject} url Absolute or relative URL of the resource that is being requested;\n     *                                   or an object created by a call to `$sce.trustAsResourceUrl(url)`.\n     * @param {Object=} config Optional configuration object. See {@link ng.$http#$http-arguments `$http()` arguments}.\n     * @returns {HttpPromise}  A Promise that will be resolved or rejected with a response object.\n     * See {@link ng.$http#$http-returns `$http()` return value}.\n     */\n\n    /**\n     * @ngdoc method\n     * @name $http#head\n     *\n     * @description\n     * Shortcut method to perform `HEAD` request.\n     *\n     * @param {string|TrustedObject} url Absolute or relative URL of the resource that is being requested;\n     *                                   or an object created by a call to `$sce.trustAsResourceUrl(url)`.\n     * @param {Object=} config Optional configuration object. See {@link ng.$http#$http-arguments `$http()` arguments}.\n     * @returns {HttpPromise}  A Promise that will be resolved or rejected with a response object.\n     * See {@link ng.$http#$http-returns `$http()` return value}.\n     */\n\n    /**\n     * @ngdoc method\n     * @name $http#jsonp\n     *\n     * @description\n     * Shortcut method to perform `JSONP` request.\n     *\n     * Note that, since JSONP requests are sensitive because the response is given full access to the browser,\n     * the url must be declared, via {@link $sce} as a trusted resource URL.\n     * You can trust a URL by adding it to the trusted resource URL list via\n     * {@link $sceDelegateProvider#trustedResourceUrlList  `$sceDelegateProvider.trustedResourceUrlList`} or\n     * by explicitly trusting the URL via {@link $sce#trustAsResourceUrl `$sce.trustAsResourceUrl(url)`}.\n     *\n     * You should avoid generating the URL for the JSONP request from user provided data.\n     * Provide additional query parameters via `params` property of the `config` parameter, rather than\n     * modifying the URL itself.\n     *\n     * JSONP requests must specify a callback to be used in the response from the server. This callback\n     * is passed as a query parameter in the request. You must specify the name of this parameter by\n     * setting the `jsonpCallbackParam` property on the request config object.\n     *\n     * ```\n     * $http.jsonp('some/trusted/url', {jsonpCallbackParam: 'callback'})\n     * ```\n     *\n     * You can also specify a default callback parameter name in `$http.defaults.jsonpCallbackParam`.\n     * Initially this is set to `'callback'`.\n     *\n     * <div class=\"alert alert-danger\">\n     * You can no longer use the `JSON_CALLBACK` string as a placeholder for specifying where the callback\n     * parameter value should go.\n     * </div>\n     *\n     * If you would like to customise where and how the callbacks are stored then try overriding\n     * or decorating the {@link $jsonpCallbacks} service.\n     *\n     * @param {string|TrustedObject} url Absolute or relative URL of the resource that is being requested;\n     *                                   or an object created by a call to `$sce.trustAsResourceUrl(url)`.\n     * @param {Object=} config Optional configuration object. See {@link ng.$http#$http-arguments `$http()` arguments}.\n     * @returns {HttpPromise}  A Promise that will be resolved or rejected with a response object.\n     * See {@link ng.$http#$http-returns `$http()` return value}.\n     */\n    createShortMethods('get', 'delete', 'head', 'jsonp');\n\n    /**\n     * @ngdoc method\n     * @name $http#post\n     *\n     * @description\n     * Shortcut method to perform `POST` request.\n     *\n     * @param {string} url Relative or absolute URL specifying the destination of the request\n     * @param {*} data Request content\n     * @param {Object=} config Optional configuration object. See {@link ng.$http#$http-arguments `$http()` arguments}.\n     * @returns {HttpPromise}  A Promise that will be resolved or rejected with a response object.\n     * See {@link ng.$http#$http-returns `$http()` return value}.\n     */\n\n    /**\n     * @ngdoc method\n     * @name $http#put\n     *\n     * @description\n     * Shortcut method to perform `PUT` request.\n     *\n     * @param {string} url Relative or absolute URL specifying the destination of the request\n     * @param {*} data Request content\n     * @param {Object=} config Optional configuration object. See {@link ng.$http#$http-arguments `$http()` arguments}.\n     * @returns {HttpPromise}  A Promise that will be resolved or rejected with a response object.\n     * See {@link ng.$http#$http-returns `$http()` return value}.\n     */\n\n     /**\n      * @ngdoc method\n      * @name $http#patch\n      *\n      * @description\n      * Shortcut method to perform `PATCH` request.\n      *\n      * @param {string} url Relative or absolute URL specifying the destination of the request\n      * @param {*} data Request content\n      * @param {Object=} config Optional configuration object. See {@link ng.$http#$http-arguments `$http()` arguments}.\n      * @returns {HttpPromise}  A Promise that will be resolved or rejected with a response object.\n      * See {@link ng.$http#$http-returns `$http()` return value}.\n      */\n    createShortMethodsWithData('post', 'put', 'patch');\n\n        /**\n         * @ngdoc property\n         * @name $http#defaults\n         *\n         * @description\n         * Runtime equivalent of the `$httpProvider.defaults` property. Allows configuration of\n         * default headers, withCredentials as well as request and response transformations.\n         *\n         * See \"Setting HTTP Headers\" and \"Transforming Requests and Responses\" sections above.\n         */\n    $http.defaults = defaults;\n\n\n    return $http;\n\n\n    function createShortMethods(names) {\n      forEach(arguments, function(name) {\n        $http[name] = function(url, config) {\n          return $http(extend({}, config || {}, {\n            method: name,\n            url: url\n          }));\n        };\n      });\n    }\n\n\n    function createShortMethodsWithData(name) {\n      forEach(arguments, function(name) {\n        $http[name] = function(url, data, config) {\n          return $http(extend({}, config || {}, {\n            method: name,\n            url: url,\n            data: data\n          }));\n        };\n      });\n    }\n\n\n    /**\n     * Makes the request.\n     *\n     * !!! ACCESSES CLOSURE VARS:\n     * $httpBackend, defaults, $log, $rootScope, defaultCache, $http.pendingRequests\n     */\n    function sendReq(config, reqData) {\n      var deferred = $q.defer(),\n          promise = deferred.promise,\n          cache,\n          cachedResp,\n          reqHeaders = config.headers,\n          isJsonp = lowercase(config.method) === 'jsonp',\n          url = config.url;\n\n      if (isJsonp) {\n        // JSONP is a pretty sensitive operation where we're allowing a script to have full access to\n        // our DOM and JS space.  So we require that the URL satisfies SCE.RESOURCE_URL.\n        url = $sce.getTrustedResourceUrl(url);\n      } else if (!isString(url)) {\n        // If it is not a string then the URL must be a $sce trusted object\n        url = $sce.valueOf(url);\n      }\n\n      url = buildUrl(url, config.paramSerializer(config.params));\n\n      if (isJsonp) {\n        // Check the url and add the JSONP callback placeholder\n        url = sanitizeJsonpCallbackParam(url, config.jsonpCallbackParam);\n      }\n\n      $http.pendingRequests.push(config);\n      promise.then(removePendingReq, removePendingReq);\n\n      if ((config.cache || defaults.cache) && config.cache !== false &&\n          (config.method === 'GET' || config.method === 'JSONP')) {\n        cache = isObject(config.cache) ? config.cache\n            : isObject(/** @type {?} */ (defaults).cache)\n              ? /** @type {?} */ (defaults).cache\n              : defaultCache;\n      }\n\n      if (cache) {\n        cachedResp = cache.get(url);\n        if (isDefined(cachedResp)) {\n          if (isPromiseLike(cachedResp)) {\n            // cached request has already been sent, but there is no response yet\n            cachedResp.then(resolvePromiseWithResult, resolvePromiseWithResult);\n          } else {\n            // serving from cache\n            if (isArray(cachedResp)) {\n              resolvePromise(cachedResp[1], cachedResp[0], shallowCopy(cachedResp[2]), cachedResp[3], cachedResp[4]);\n            } else {\n              resolvePromise(cachedResp, 200, {}, 'OK', 'complete');\n            }\n          }\n        } else {\n          // put the promise for the non-transformed response into cache as a placeholder\n          cache.put(url, promise);\n        }\n      }\n\n\n      // if we won't have the response in cache, set the xsrf headers and\n      // send the request to the backend\n      if (isUndefined(cachedResp)) {\n        var xsrfValue = urlIsAllowedOrigin(config.url)\n            ? $$cookieReader()[config.xsrfCookieName || defaults.xsrfCookieName]\n            : undefined;\n        if (xsrfValue) {\n          reqHeaders[(config.xsrfHeaderName || defaults.xsrfHeaderName)] = xsrfValue;\n        }\n\n        $httpBackend(config.method, url, reqData, done, reqHeaders, config.timeout,\n            config.withCredentials, config.responseType,\n            createApplyHandlers(config.eventHandlers),\n            createApplyHandlers(config.uploadEventHandlers));\n      }\n\n      return promise;\n\n      function createApplyHandlers(eventHandlers) {\n        if (eventHandlers) {\n          var applyHandlers = {};\n          forEach(eventHandlers, function(eventHandler, key) {\n            applyHandlers[key] = function(event) {\n              if (useApplyAsync) {\n                $rootScope.$applyAsync(callEventHandler);\n              } else if ($rootScope.$$phase) {\n                callEventHandler();\n              } else {\n                $rootScope.$apply(callEventHandler);\n              }\n\n              function callEventHandler() {\n                eventHandler(event);\n              }\n            };\n          });\n          return applyHandlers;\n        }\n      }\n\n\n      /**\n       * Callback registered to $httpBackend():\n       *  - caches the response if desired\n       *  - resolves the raw $http promise\n       *  - calls $apply\n       */\n      function done(status, response, headersString, statusText, xhrStatus) {\n        if (cache) {\n          if (isSuccess(status)) {\n            cache.put(url, [status, response, parseHeaders(headersString), statusText, xhrStatus]);\n          } else {\n            // remove promise from the cache\n            cache.remove(url);\n          }\n        }\n\n        function resolveHttpPromise() {\n          resolvePromise(response, status, headersString, statusText, xhrStatus);\n        }\n\n        if (useApplyAsync) {\n          $rootScope.$applyAsync(resolveHttpPromise);\n        } else {\n          resolveHttpPromise();\n          if (!$rootScope.$$phase) $rootScope.$apply();\n        }\n      }\n\n\n      /**\n       * Resolves the raw $http promise.\n       */\n      function resolvePromise(response, status, headers, statusText, xhrStatus) {\n        //status: HTTP response status code, 0, -1 (aborted by timeout / promise)\n        status = status >= -1 ? status : 0;\n\n        (isSuccess(status) ? deferred.resolve : deferred.reject)({\n          data: response,\n          status: status,\n          headers: headersGetter(headers),\n          config: config,\n          statusText: statusText,\n          xhrStatus: xhrStatus\n        });\n      }\n\n      function resolvePromiseWithResult(result) {\n        resolvePromise(result.data, result.status, shallowCopy(result.headers()), result.statusText, result.xhrStatus);\n      }\n\n      function removePendingReq() {\n        var idx = $http.pendingRequests.indexOf(config);\n        if (idx !== -1) $http.pendingRequests.splice(idx, 1);\n      }\n    }\n\n\n    function buildUrl(url, serializedParams) {\n      if (serializedParams.length > 0) {\n        url += ((url.indexOf('?') === -1) ? '?' : '&') + serializedParams;\n      }\n      return url;\n    }\n\n    function sanitizeJsonpCallbackParam(url, cbKey) {\n      var parts = url.split('?');\n      if (parts.length > 2) {\n        // Throw if the url contains more than one `?` query indicator\n        throw $httpMinErr('badjsonp', 'Illegal use more than one \"?\", in url, \"{1}\"', url);\n      }\n      var params = parseKeyValue(parts[1]);\n      forEach(params, function(value, key) {\n        if (value === 'JSON_CALLBACK') {\n          // Throw if the url already contains a reference to JSON_CALLBACK\n          throw $httpMinErr('badjsonp', 'Illegal use of JSON_CALLBACK in url, \"{0}\"', url);\n        }\n        if (key === cbKey) {\n          // Throw if the callback param was already provided\n          throw $httpMinErr('badjsonp', 'Illegal use of callback param, \"{0}\", in url, \"{1}\"', cbKey, url);\n        }\n      });\n\n      // Add in the JSON_CALLBACK callback param value\n      url += ((url.indexOf('?') === -1) ? '?' : '&') + cbKey + '=JSON_CALLBACK';\n\n      return url;\n    }\n  }];\n}\n\n/**\n * @ngdoc service\n * @name $xhrFactory\n * @this\n *\n * @description\n * Factory function used to create XMLHttpRequest objects.\n *\n * Replace or decorate this service to create your own custom XMLHttpRequest objects.\n *\n * ```\n * angular.module('myApp', [])\n * .factory('$xhrFactory', function() {\n *   return function createXhr(method, url) {\n *     return new window.XMLHttpRequest({mozSystem: true});\n *   };\n * });\n * ```\n *\n * @param {string} method HTTP method of the request (GET, POST, PUT, ..)\n * @param {string} url URL of the request.\n */\nfunction $xhrFactoryProvider() {\n  this.$get = function() {\n    return function createXhr() {\n      return new window.XMLHttpRequest();\n    };\n  };\n}\n\n/**\n * @ngdoc service\n * @name $httpBackend\n * @requires $jsonpCallbacks\n * @requires $document\n * @requires $xhrFactory\n * @this\n *\n * @description\n * HTTP backend used by the {@link ng.$http service} that delegates to\n * XMLHttpRequest object or JSONP and deals with browser incompatibilities.\n *\n * You should never need to use this service directly, instead use the higher-level abstractions:\n * {@link ng.$http $http} or {@link ngResource.$resource $resource}.\n *\n * During testing this implementation is swapped with {@link ngMock.$httpBackend mock\n * $httpBackend} which can be trained with responses.\n */\nfunction $HttpBackendProvider() {\n  this.$get = ['$browser', '$jsonpCallbacks', '$document', '$xhrFactory', function($browser, $jsonpCallbacks, $document, $xhrFactory) {\n    return createHttpBackend($browser, $xhrFactory, $browser.defer, $jsonpCallbacks, $document[0]);\n  }];\n}\n\nfunction createHttpBackend($browser, createXhr, $browserDefer, callbacks, rawDocument) {\n  // TODO(vojta): fix the signature\n  return function(method, url, post, callback, headers, timeout, withCredentials, responseType, eventHandlers, uploadEventHandlers) {\n    url = url || $browser.url();\n\n    if (lowercase(method) === 'jsonp') {\n      var callbackPath = callbacks.createCallback(url);\n      var jsonpDone = jsonpReq(url, callbackPath, function(status, text) {\n        // jsonpReq only ever sets status to 200 (OK), 404 (ERROR) or -1 (WAITING)\n        var response = (status === 200) && callbacks.getResponse(callbackPath);\n        completeRequest(callback, status, response, '', text, 'complete');\n        callbacks.removeCallback(callbackPath);\n      });\n    } else {\n\n      var xhr = createXhr(method, url);\n      var abortedByTimeout = false;\n\n      xhr.open(method, url, true);\n      forEach(headers, function(value, key) {\n        if (isDefined(value)) {\n            xhr.setRequestHeader(key, value);\n        }\n      });\n\n      xhr.onload = function requestLoaded() {\n        var statusText = xhr.statusText || '';\n\n        // responseText is the old-school way of retrieving response (supported by IE9)\n        // response/responseType properties were introduced in XHR Level2 spec (supported by IE10)\n        var response = ('response' in xhr) ? xhr.response : xhr.responseText;\n\n        // normalize IE9 bug (http://bugs.jquery.com/ticket/1450)\n        var status = xhr.status === 1223 ? 204 : xhr.status;\n\n        // fix status code when it is 0 (0 status is undocumented).\n        // Occurs when accessing file resources or on Android 4.1 stock browser\n        // while retrieving files from application cache.\n        if (status === 0) {\n          status = response ? 200 : urlResolve(url).protocol === 'file' ? 404 : 0;\n        }\n\n        completeRequest(callback,\n            status,\n            response,\n            xhr.getAllResponseHeaders(),\n            statusText,\n            'complete');\n      };\n\n      var requestError = function() {\n        // The response is always empty\n        // See https://xhr.spec.whatwg.org/#request-error-steps and https://fetch.spec.whatwg.org/#concept-network-error\n        completeRequest(callback, -1, null, null, '', 'error');\n      };\n\n      var requestAborted = function() {\n        completeRequest(callback, -1, null, null, '', abortedByTimeout ? 'timeout' : 'abort');\n      };\n\n      var requestTimeout = function() {\n        // The response is always empty\n        // See https://xhr.spec.whatwg.org/#request-error-steps and https://fetch.spec.whatwg.org/#concept-network-error\n        completeRequest(callback, -1, null, null, '', 'timeout');\n      };\n\n      xhr.onerror = requestError;\n      xhr.ontimeout = requestTimeout;\n      xhr.onabort = requestAborted;\n\n      forEach(eventHandlers, function(value, key) {\n        xhr.addEventListener(key, value);\n      });\n\n      forEach(uploadEventHandlers, function(value, key) {\n        xhr.upload.addEventListener(key, value);\n      });\n\n      if (withCredentials) {\n        xhr.withCredentials = true;\n      }\n\n      if (responseType) {\n        try {\n          xhr.responseType = responseType;\n        } catch (e) {\n          // WebKit added support for the json responseType value on 09/03/2013\n          // https://bugs.webkit.org/show_bug.cgi?id=73648. Versions of Safari prior to 7 are\n          // known to throw when setting the value \"json\" as the response type. Other older\n          // browsers implementing the responseType\n          //\n          // The json response type can be ignored if not supported, because JSON payloads are\n          // parsed on the client-side regardless.\n          if (responseType !== 'json') {\n            throw e;\n          }\n        }\n      }\n\n      xhr.send(isUndefined(post) ? null : post);\n    }\n\n    // Since we are using xhr.abort() when a request times out, we have to set a flag that\n    // indicates to requestAborted if the request timed out or was aborted.\n    //\n    // http.timeout = numerical timeout   timeout\n    // http.timeout = $timeout            timeout\n    // http.timeout = promise             abort\n    // xhr.abort()                        abort (The xhr object is normally inaccessible, but\n    //                                    can be exposed with the xhrFactory)\n    if (timeout > 0) {\n      var timeoutId = $browserDefer(function() {\n        timeoutRequest('timeout');\n      }, timeout);\n    } else if (isPromiseLike(timeout)) {\n      timeout.then(function() {\n        timeoutRequest(isDefined(timeout.$$timeoutId) ? 'timeout' : 'abort');\n      });\n    }\n\n    function timeoutRequest(reason) {\n      abortedByTimeout = reason === 'timeout';\n      if (jsonpDone) {\n        jsonpDone();\n      }\n      if (xhr) {\n        xhr.abort();\n      }\n    }\n\n    function completeRequest(callback, status, response, headersString, statusText, xhrStatus) {\n      // cancel timeout and subsequent timeout promise resolution\n      if (isDefined(timeoutId)) {\n        $browserDefer.cancel(timeoutId);\n      }\n      jsonpDone = xhr = null;\n\n      callback(status, response, headersString, statusText, xhrStatus);\n    }\n  };\n\n  function jsonpReq(url, callbackPath, done) {\n    url = url.replace('JSON_CALLBACK', callbackPath);\n    // we can't use jQuery/jqLite here because jQuery does crazy stuff with script elements, e.g.:\n    // - fetches local scripts via XHR and evals them\n    // - adds and immediately removes script elements from the document\n    var script = rawDocument.createElement('script'), callback = null;\n    script.type = 'text/javascript';\n    script.src = url;\n    script.async = true;\n\n    callback = function(event) {\n      script.removeEventListener('load', callback);\n      script.removeEventListener('error', callback);\n      rawDocument.body.removeChild(script);\n      script = null;\n      var status = -1;\n      var text = 'unknown';\n\n      if (event) {\n        if (event.type === 'load' && !callbacks.wasCalled(callbackPath)) {\n          event = { type: 'error' };\n        }\n        text = event.type;\n        status = event.type === 'error' ? 404 : 200;\n      }\n\n      if (done) {\n        done(status, text);\n      }\n    };\n\n    script.addEventListener('load', callback);\n    script.addEventListener('error', callback);\n    rawDocument.body.appendChild(script);\n    return callback;\n  }\n}\n\nvar $interpolateMinErr = angular.$interpolateMinErr = minErr('$interpolate');\n$interpolateMinErr.throwNoconcat = function(text) {\n  throw $interpolateMinErr('noconcat',\n      'Error while interpolating: {0}\\nStrict Contextual Escaping disallows ' +\n      'interpolations that concatenate multiple expressions when a trusted value is ' +\n      'required.  See http://docs.angularjs.org/api/ng.$sce', text);\n};\n\n$interpolateMinErr.interr = function(text, err) {\n  return $interpolateMinErr('interr', 'Can\\'t interpolate: {0}\\n{1}', text, err.toString());\n};\n\n/**\n * @ngdoc provider\n * @name $interpolateProvider\n * @this\n *\n * @description\n *\n * Used for configuring the interpolation markup. Defaults to `{{` and `}}`.\n *\n * <div class=\"alert alert-danger\">\n * This feature is sometimes used to mix different markup languages, e.g. to wrap an AngularJS\n * template within a Python Jinja template (or any other template language). Mixing templating\n * languages is **very dangerous**. The embedding template language will not safely escape AngularJS\n * expressions, so any user-controlled values in the template will cause Cross Site Scripting (XSS)\n * security bugs!\n * </div>\n *\n * @example\n<example name=\"custom-interpolation-markup\" module=\"customInterpolationApp\">\n<file name=\"index.html\">\n<script>\n  var customInterpolationApp = angular.module('customInterpolationApp', []);\n\n  customInterpolationApp.config(function($interpolateProvider) {\n    $interpolateProvider.startSymbol('//');\n    $interpolateProvider.endSymbol('//');\n  });\n\n\n  customInterpolationApp.controller('DemoController', function() {\n      this.label = \"This binding is brought you by // interpolation symbols.\";\n  });\n</script>\n<div ng-controller=\"DemoController as demo\">\n    //demo.label//\n</div>\n</file>\n<file name=\"protractor.js\" type=\"protractor\">\n  it('should interpolate binding with custom symbols', function() {\n    expect(element(by.binding('demo.label')).getText()).toBe('This binding is brought you by // interpolation symbols.');\n  });\n</file>\n</example>\n */\nfunction $InterpolateProvider() {\n  var startSymbol = '{{';\n  var endSymbol = '}}';\n\n  /**\n   * @ngdoc method\n   * @name $interpolateProvider#startSymbol\n   * @description\n   * Symbol to denote start of expression in the interpolated string. Defaults to `{{`.\n   *\n   * @param {string=} value new value to set the starting symbol to.\n   * @returns {string|self} Returns the symbol when used as getter and self if used as setter.\n   */\n  this.startSymbol = function(value) {\n    if (value) {\n      startSymbol = value;\n      return this;\n    }\n    return startSymbol;\n  };\n\n  /**\n   * @ngdoc method\n   * @name $interpolateProvider#endSymbol\n   * @description\n   * Symbol to denote the end of expression in the interpolated string. Defaults to `}}`.\n   *\n   * @param {string=} value new value to set the ending symbol to.\n   * @returns {string|self} Returns the symbol when used as getter and self if used as setter.\n   */\n  this.endSymbol = function(value) {\n    if (value) {\n      endSymbol = value;\n      return this;\n    }\n    return endSymbol;\n  };\n\n\n  this.$get = ['$parse', '$exceptionHandler', '$sce', function($parse, $exceptionHandler, $sce) {\n    var startSymbolLength = startSymbol.length,\n        endSymbolLength = endSymbol.length,\n        escapedStartRegexp = new RegExp(startSymbol.replace(/./g, escape), 'g'),\n        escapedEndRegexp = new RegExp(endSymbol.replace(/./g, escape), 'g');\n\n    function escape(ch) {\n      return '\\\\\\\\\\\\' + ch;\n    }\n\n    function unescapeText(text) {\n      return text.replace(escapedStartRegexp, startSymbol).\n        replace(escapedEndRegexp, endSymbol);\n    }\n\n    // TODO: this is the same as the constantWatchDelegate in parse.js\n    function constantWatchDelegate(scope, listener, objectEquality, constantInterp) {\n      var unwatch = scope.$watch(function constantInterpolateWatch(scope) {\n        unwatch();\n        return constantInterp(scope);\n      }, listener, objectEquality);\n      return unwatch;\n    }\n\n    /**\n     * @ngdoc service\n     * @name $interpolate\n     * @kind function\n     *\n     * @requires $parse\n     * @requires $sce\n     *\n     * @description\n     *\n     * Compiles a string with markup into an interpolation function. This service is used by the\n     * HTML {@link ng.$compile $compile} service for data binding. See\n     * {@link ng.$interpolateProvider $interpolateProvider} for configuring the\n     * interpolation markup.\n     *\n     *\n     * ```js\n     *   var $interpolate = ...; // injected\n     *   var exp = $interpolate('Hello {{name | uppercase}}!');\n     *   expect(exp({name:'AngularJS'})).toEqual('Hello ANGULARJS!');\n     * ```\n     *\n     * `$interpolate` takes an optional fourth argument, `allOrNothing`. If `allOrNothing` is\n     * `true`, the interpolation function will return `undefined` unless all embedded expressions\n     * evaluate to a value other than `undefined`.\n     *\n     * ```js\n     *   var $interpolate = ...; // injected\n     *   var context = {greeting: 'Hello', name: undefined };\n     *\n     *   // default \"forgiving\" mode\n     *   var exp = $interpolate('{{greeting}} {{name}}!');\n     *   expect(exp(context)).toEqual('Hello !');\n     *\n     *   // \"allOrNothing\" mode\n     *   exp = $interpolate('{{greeting}} {{name}}!', false, null, true);\n     *   expect(exp(context)).toBeUndefined();\n     *   context.name = 'AngularJS';\n     *   expect(exp(context)).toEqual('Hello AngularJS!');\n     * ```\n     *\n     * `allOrNothing` is useful for interpolating URLs. `ngSrc` and `ngSrcset` use this behavior.\n     *\n     * #### Escaped Interpolation\n     * $interpolate provides a mechanism for escaping interpolation markers. Start and end markers\n     * can be escaped by preceding each of their characters with a REVERSE SOLIDUS U+005C (backslash).\n     * It will be rendered as a regular start/end marker, and will not be interpreted as an expression\n     * or binding.\n     *\n     * This enables web-servers to prevent script injection attacks and defacing attacks, to some\n     * degree, while also enabling code examples to work without relying on the\n     * {@link ng.directive:ngNonBindable ngNonBindable} directive.\n     *\n     * **For security purposes, it is strongly encouraged that web servers escape user-supplied data,\n     * replacing angle brackets (&lt;, &gt;) with &amp;lt; and &amp;gt; respectively, and replacing all\n     * interpolation start/end markers with their escaped counterparts.**\n     *\n     * Escaped interpolation markers are only replaced with the actual interpolation markers in rendered\n     * output when the $interpolate service processes the text. So, for HTML elements interpolated\n     * by {@link ng.$compile $compile}, or otherwise interpolated with the `mustHaveExpression` parameter\n     * set to `true`, the interpolated text must contain an unescaped interpolation expression. As such,\n     * this is typically useful only when user-data is used in rendering a template from the server, or\n     * when otherwise untrusted data is used by a directive.\n     *\n     * <example name=\"interpolation\">\n     *  <file name=\"index.html\">\n     *    <div ng-init=\"username='A user'\">\n     *      <p ng-init=\"apptitle='Escaping demo'\">{{apptitle}}: \\{\\{ username = \"defaced value\"; \\}\\}\n     *        </p>\n     *      <p><strong>{{username}}</strong> attempts to inject code which will deface the\n     *        application, but fails to accomplish their task, because the server has correctly\n     *        escaped the interpolation start/end markers with REVERSE SOLIDUS U+005C (backslash)\n     *        characters.</p>\n     *      <p>Instead, the result of the attempted script injection is visible, and can be removed\n     *        from the database by an administrator.</p>\n     *    </div>\n     *  </file>\n     * </example>\n     *\n     * @knownIssue\n     * It is currently not possible for an interpolated expression to contain the interpolation end\n     * symbol. For example, `{{ '}}' }}` will be incorrectly interpreted as `{{ ' }}` + `' }}`, i.e.\n     * an interpolated expression consisting of a single-quote (`'`) and the `' }}` string.\n     *\n     * @knownIssue\n     * All directives and components must use the standard `{{` `}}` interpolation symbols\n     * in their templates. If you change the application interpolation symbols the {@link $compile}\n     * service will attempt to denormalize the standard symbols to the custom symbols.\n     * The denormalization process is not clever enough to know not to replace instances of the standard\n     * symbols where they would not normally be treated as interpolation symbols. For example in the following\n     * code snippet the closing braces of the literal object will get incorrectly denormalized:\n     *\n     * ```\n     * <div data-context='{\"context\":{\"id\":3,\"type\":\"page\"}}\">\n     * ```\n     *\n     * The workaround is to ensure that such instances are separated by whitespace:\n     * ```\n     * <div data-context='{\"context\":{\"id\":3,\"type\":\"page\"} }\">\n     * ```\n     *\n     * See https://github.com/angular/angular.js/pull/14610#issuecomment-219401099 for more information.\n     *\n     * @param {string} text The text with markup to interpolate.\n     * @param {boolean=} mustHaveExpression if set to true then the interpolation string must have\n     *    embedded expression in order to return an interpolation function. Strings with no\n     *    embedded expression will return null for the interpolation function.\n     * @param {string=} trustedContext when provided, the returned function passes the interpolated\n     *    result through {@link ng.$sce#getTrusted $sce.getTrusted(interpolatedResult,\n     *    trustedContext)} before returning it.  Refer to the {@link ng.$sce $sce} service that\n     *    provides Strict Contextual Escaping for details.\n     * @param {boolean=} allOrNothing if `true`, then the returned function returns undefined\n     *    unless all embedded expressions evaluate to a value other than `undefined`.\n     * @returns {function(context)} an interpolation function which is used to compute the\n     *    interpolated string. The function has these parameters:\n     *\n     * - `context`: evaluation context for all expressions embedded in the interpolated text\n     */\n    function $interpolate(text, mustHaveExpression, trustedContext, allOrNothing) {\n      var contextAllowsConcatenation = trustedContext === $sce.URL || trustedContext === $sce.MEDIA_URL;\n\n      // Provide a quick exit and simplified result function for text with no interpolation\n      if (!text.length || text.indexOf(startSymbol) === -1) {\n        if (mustHaveExpression) return;\n\n        var unescapedText = unescapeText(text);\n        if (contextAllowsConcatenation) {\n          unescapedText = $sce.getTrusted(trustedContext, unescapedText);\n        }\n        var constantInterp = valueFn(unescapedText);\n        constantInterp.exp = text;\n        constantInterp.expressions = [];\n        constantInterp.$$watchDelegate = constantWatchDelegate;\n\n        return constantInterp;\n      }\n\n      allOrNothing = !!allOrNothing;\n      var startIndex,\n          endIndex,\n          index = 0,\n          expressions = [],\n          parseFns,\n          textLength = text.length,\n          exp,\n          concat = [],\n          expressionPositions = [],\n          singleExpression;\n\n\n      while (index < textLength) {\n        if (((startIndex = text.indexOf(startSymbol, index)) !== -1) &&\n             ((endIndex = text.indexOf(endSymbol, startIndex + startSymbolLength)) !== -1)) {\n          if (index !== startIndex) {\n            concat.push(unescapeText(text.substring(index, startIndex)));\n          }\n          exp = text.substring(startIndex + startSymbolLength, endIndex);\n          expressions.push(exp);\n          index = endIndex + endSymbolLength;\n          expressionPositions.push(concat.length);\n          concat.push(''); // Placeholder that will get replaced with the evaluated expression.\n        } else {\n          // we did not find an interpolation, so we have to add the remainder to the separators array\n          if (index !== textLength) {\n            concat.push(unescapeText(text.substring(index)));\n          }\n          break;\n        }\n      }\n\n      singleExpression = concat.length === 1 && expressionPositions.length === 1;\n      // Intercept expression if we need to stringify concatenated inputs, which may be SCE trusted\n      // objects rather than simple strings\n      // (we don't modify the expression if the input consists of only a single trusted input)\n      var interceptor = contextAllowsConcatenation && singleExpression ? undefined : parseStringifyInterceptor;\n      parseFns = expressions.map(function(exp) { return $parse(exp, interceptor); });\n\n      // Concatenating expressions makes it hard to reason about whether some combination of\n      // concatenated values are unsafe to use and could easily lead to XSS.  By requiring that a\n      // single expression be used for some $sce-managed secure contexts (RESOURCE_URLs mostly),\n      // we ensure that the value that's used is assigned or constructed by some JS code somewhere\n      // that is more testable or make it obvious that you bound the value to some user controlled\n      // value.  This helps reduce the load when auditing for XSS issues.\n\n      // Note that URL and MEDIA_URL $sce contexts do not need this, since `$sce` can sanitize the values\n      // passed to it. In that case, `$sce.getTrusted` will be called on either the single expression\n      // or on the overall concatenated string (losing trusted types used in the mix, by design).\n      // Both these methods will sanitize plain strings. Also, HTML could be included, but since it's\n      // only used in srcdoc attributes, this would not be very useful.\n\n      if (!mustHaveExpression || expressions.length) {\n        var compute = function(values) {\n          for (var i = 0, ii = expressions.length; i < ii; i++) {\n            if (allOrNothing && isUndefined(values[i])) return;\n            concat[expressionPositions[i]] = values[i];\n          }\n\n          if (contextAllowsConcatenation) {\n            // If `singleExpression` then `concat[0]` might be a \"trusted\" value or `null`, rather than a string\n            return $sce.getTrusted(trustedContext, singleExpression ? concat[0] : concat.join(''));\n          } else if (trustedContext && concat.length > 1) {\n            // This context does not allow more than one part, e.g. expr + string or exp + exp.\n            $interpolateMinErr.throwNoconcat(text);\n          }\n          // In an unprivileged context or only one part: just concatenate and return.\n          return concat.join('');\n        };\n\n        return extend(function interpolationFn(context) {\n            var i = 0;\n            var ii = expressions.length;\n            var values = new Array(ii);\n\n            try {\n              for (; i < ii; i++) {\n                values[i] = parseFns[i](context);\n              }\n\n              return compute(values);\n            } catch (err) {\n              $exceptionHandler($interpolateMinErr.interr(text, err));\n            }\n\n          }, {\n          // all of these properties are undocumented for now\n          exp: text, //just for compatibility with regular watchers created via $watch\n          expressions: expressions,\n          $$watchDelegate: function(scope, listener) {\n            var lastValue;\n            return scope.$watchGroup(parseFns, /** @this */ function interpolateFnWatcher(values, oldValues) {\n              var currValue = compute(values);\n              listener.call(this, currValue, values !== oldValues ? lastValue : currValue, scope);\n              lastValue = currValue;\n            });\n          }\n        });\n      }\n\n      function parseStringifyInterceptor(value) {\n        try {\n          // In concatenable contexts, getTrusted comes at the end, to avoid sanitizing individual\n          // parts of a full URL. We don't care about losing the trustedness here.\n          // In non-concatenable contexts, where there is only one expression, this interceptor is\n          // not applied to the expression.\n          value = (trustedContext && !contextAllowsConcatenation) ?\n                    $sce.getTrusted(trustedContext, value) :\n                    $sce.valueOf(value);\n          return allOrNothing && !isDefined(value) ? value : stringify(value);\n        } catch (err) {\n          $exceptionHandler($interpolateMinErr.interr(text, err));\n        }\n      }\n    }\n\n\n    /**\n     * @ngdoc method\n     * @name $interpolate#startSymbol\n     * @description\n     * Symbol to denote the start of expression in the interpolated string. Defaults to `{{`.\n     *\n     * Use {@link ng.$interpolateProvider#startSymbol `$interpolateProvider.startSymbol`} to change\n     * the symbol.\n     *\n     * @returns {string} start symbol.\n     */\n    $interpolate.startSymbol = function() {\n      return startSymbol;\n    };\n\n\n    /**\n     * @ngdoc method\n     * @name $interpolate#endSymbol\n     * @description\n     * Symbol to denote the end of expression in the interpolated string. Defaults to `}}`.\n     *\n     * Use {@link ng.$interpolateProvider#endSymbol `$interpolateProvider.endSymbol`} to change\n     * the symbol.\n     *\n     * @returns {string} end symbol.\n     */\n    $interpolate.endSymbol = function() {\n      return endSymbol;\n    };\n\n    return $interpolate;\n  }];\n}\n\nvar $intervalMinErr = minErr('$interval');\n\n/** @this */\nfunction $IntervalProvider() {\n  this.$get = ['$$intervalFactory', '$window',\n       function($$intervalFactory,   $window) {\n    var intervals = {};\n    var setIntervalFn = function(tick, delay, deferred) {\n      var id = $window.setInterval(tick, delay);\n      intervals[id] = deferred;\n      return id;\n    };\n    var clearIntervalFn = function(id) {\n      $window.clearInterval(id);\n      delete intervals[id];\n    };\n\n    /**\n     * @ngdoc service\n     * @name $interval\n     *\n     * @description\n     * AngularJS's wrapper for `window.setInterval`. The `fn` function is executed every `delay`\n     * milliseconds.\n     *\n     * The return value of registering an interval function is a promise. This promise will be\n     * notified upon each tick of the interval, and will be resolved after `count` iterations, or\n     * run indefinitely if `count` is not defined. The value of the notification will be the\n     * number of iterations that have run.\n     * To cancel an interval, call `$interval.cancel(promise)`.\n     *\n     * In tests you can use {@link ngMock.$interval#flush `$interval.flush(millis)`} to\n     * move forward by `millis` milliseconds and trigger any functions scheduled to run in that\n     * time.\n     *\n     * <div class=\"alert alert-warning\">\n     * **Note**: Intervals created by this service must be explicitly destroyed when you are finished\n     * with them.  In particular they are not automatically destroyed when a controller's scope or a\n     * directive's element are destroyed.\n     * You should take this into consideration and make sure to always cancel the interval at the\n     * appropriate moment.  See the example below for more details on how and when to do this.\n     * </div>\n     *\n     * @param {function()} fn A function that should be called repeatedly. If no additional arguments\n     *   are passed (see below), the function is called with the current iteration count.\n     * @param {number} delay Number of milliseconds between each function call.\n     * @param {number=} [count=0] Number of times to repeat. If not set, or 0, will repeat\n     *   indefinitely.\n     * @param {boolean=} [invokeApply=true] If set to `false` skips model dirty checking, otherwise\n     *   will invoke `fn` within the {@link ng.$rootScope.Scope#$apply $apply} block.\n     * @param {...*=} Pass additional parameters to the executed function.\n     * @returns {promise} A promise which will be notified on each iteration. It will resolve once all iterations of the interval complete.\n     *\n     * @example\n     * <example module=\"intervalExample\" name=\"interval-service\">\n     * <file name=\"index.html\">\n     *   <script>\n     *     angular.module('intervalExample', [])\n     *       .controller('ExampleController', ['$scope', '$interval',\n     *         function($scope, $interval) {\n     *           $scope.format = 'M/d/yy h:mm:ss a';\n     *           $scope.blood_1 = 100;\n     *           $scope.blood_2 = 120;\n     *\n     *           var stop;\n     *           $scope.fight = function() {\n     *             // Don't start a new fight if we are already fighting\n     *             if ( angular.isDefined(stop) ) return;\n     *\n     *             stop = $interval(function() {\n     *               if ($scope.blood_1 > 0 && $scope.blood_2 > 0) {\n     *                 $scope.blood_1 = $scope.blood_1 - 3;\n     *                 $scope.blood_2 = $scope.blood_2 - 4;\n     *               } else {\n     *                 $scope.stopFight();\n     *               }\n     *             }, 100);\n     *           };\n     *\n     *           $scope.stopFight = function() {\n     *             if (angular.isDefined(stop)) {\n     *               $interval.cancel(stop);\n     *               stop = undefined;\n     *             }\n     *           };\n     *\n     *           $scope.resetFight = function() {\n     *             $scope.blood_1 = 100;\n     *             $scope.blood_2 = 120;\n     *           };\n     *\n     *           $scope.$on('$destroy', function() {\n     *             // Make sure that the interval is destroyed too\n     *             $scope.stopFight();\n     *           });\n     *         }])\n     *       // Register the 'myCurrentTime' directive factory method.\n     *       // We inject $interval and dateFilter service since the factory method is DI.\n     *       .directive('myCurrentTime', ['$interval', 'dateFilter',\n     *         function($interval, dateFilter) {\n     *           // return the directive link function. (compile function not needed)\n     *           return function(scope, element, attrs) {\n     *             var format,  // date format\n     *                 stopTime; // so that we can cancel the time updates\n     *\n     *             // used to update the UI\n     *             function updateTime() {\n     *               element.text(dateFilter(new Date(), format));\n     *             }\n     *\n     *             // watch the expression, and update the UI on change.\n     *             scope.$watch(attrs.myCurrentTime, function(value) {\n     *               format = value;\n     *               updateTime();\n     *             });\n     *\n     *             stopTime = $interval(updateTime, 1000);\n     *\n     *             // listen on DOM destroy (removal) event, and cancel the next UI update\n     *             // to prevent updating time after the DOM element was removed.\n     *             element.on('$destroy', function() {\n     *               $interval.cancel(stopTime);\n     *             });\n     *           }\n     *         }]);\n     *   </script>\n     *\n     *   <div>\n     *     <div ng-controller=\"ExampleController\">\n     *       <label>Date format: <input ng-model=\"format\"></label> <hr/>\n     *       Current time is: <span my-current-time=\"format\"></span>\n     *       <hr/>\n     *       Blood 1 : <font color='red'>{{blood_1}}</font>\n     *       Blood 2 : <font color='red'>{{blood_2}}</font>\n     *       <button type=\"button\" data-ng-click=\"fight()\">Fight</button>\n     *       <button type=\"button\" data-ng-click=\"stopFight()\">StopFight</button>\n     *       <button type=\"button\" data-ng-click=\"resetFight()\">resetFight</button>\n     *     </div>\n     *   </div>\n     *\n     * </file>\n     * </example>\n     */\n    var interval = $$intervalFactory(setIntervalFn, clearIntervalFn);\n\n    /**\n     * @ngdoc method\n     * @name $interval#cancel\n     *\n     * @description\n     * Cancels a task associated with the `promise`.\n     *\n     * @param {Promise=} promise returned by the `$interval` function.\n     * @returns {boolean} Returns `true` if the task was successfully canceled.\n     */\n    interval.cancel = function(promise) {\n      if (!promise) return false;\n\n      if (!promise.hasOwnProperty('$$intervalId')) {\n        throw $intervalMinErr('badprom',\n            '`$interval.cancel()` called with a promise that was not generated by `$interval()`.');\n      }\n\n      if (!intervals.hasOwnProperty(promise.$$intervalId)) return false;\n\n      var id = promise.$$intervalId;\n      var deferred = intervals[id];\n\n      // Interval cancels should not report an unhandled promise.\n      markQExceptionHandled(deferred.promise);\n      deferred.reject('canceled');\n      clearIntervalFn(id);\n\n      return true;\n    };\n\n    return interval;\n  }];\n}\n\n/** @this */\nfunction $$IntervalFactoryProvider() {\n  this.$get = ['$browser', '$q', '$$q', '$rootScope',\n       function($browser,   $q,   $$q,   $rootScope) {\n    return function intervalFactory(setIntervalFn, clearIntervalFn) {\n      return function intervalFn(fn, delay, count, invokeApply) {\n        var hasParams = arguments.length > 4,\n            args = hasParams ? sliceArgs(arguments, 4) : [],\n            iteration = 0,\n            skipApply = isDefined(invokeApply) && !invokeApply,\n            deferred = (skipApply ? $$q : $q).defer(),\n            promise = deferred.promise;\n\n        count = isDefined(count) ? count : 0;\n\n        function callback() {\n          if (!hasParams) {\n            fn(iteration);\n          } else {\n            fn.apply(null, args);\n          }\n        }\n\n        function tick() {\n          if (skipApply) {\n            $browser.defer(callback);\n          } else {\n            $rootScope.$evalAsync(callback);\n          }\n          deferred.notify(iteration++);\n\n          if (count > 0 && iteration >= count) {\n            deferred.resolve(iteration);\n            clearIntervalFn(promise.$$intervalId);\n          }\n\n          if (!skipApply) $rootScope.$apply();\n        }\n\n        promise.$$intervalId = setIntervalFn(tick, delay, deferred, skipApply);\n\n        return promise;\n      };\n    };\n  }];\n}\n\n/**\n * @ngdoc service\n * @name $jsonpCallbacks\n * @requires $window\n * @description\n * This service handles the lifecycle of callbacks to handle JSONP requests.\n * Override this service if you wish to customise where the callbacks are stored and\n * how they vary compared to the requested url.\n */\nvar $jsonpCallbacksProvider = /** @this */ function() {\n  this.$get = function() {\n    var callbacks = angular.callbacks;\n    var callbackMap = {};\n\n    function createCallback(callbackId) {\n      var callback = function(data) {\n        callback.data = data;\n        callback.called = true;\n      };\n      callback.id = callbackId;\n      return callback;\n    }\n\n    return {\n      /**\n       * @ngdoc method\n       * @name $jsonpCallbacks#createCallback\n       * @param {string} url the url of the JSONP request\n       * @returns {string} the callback path to send to the server as part of the JSONP request\n       * @description\n       * {@link $httpBackend} calls this method to create a callback and get hold of the path to the callback\n       * to pass to the server, which will be used to call the callback with its payload in the JSONP response.\n       */\n      createCallback: function(url) {\n        var callbackId = '_' + (callbacks.$$counter++).toString(36);\n        var callbackPath = 'angular.callbacks.' + callbackId;\n        var callback = createCallback(callbackId);\n        callbackMap[callbackPath] = callbacks[callbackId] = callback;\n        return callbackPath;\n      },\n      /**\n       * @ngdoc method\n       * @name $jsonpCallbacks#wasCalled\n       * @param {string} callbackPath the path to the callback that was sent in the JSONP request\n       * @returns {boolean} whether the callback has been called, as a result of the JSONP response\n       * @description\n       * {@link $httpBackend} calls this method to find out whether the JSONP response actually called the\n       * callback that was passed in the request.\n       */\n      wasCalled: function(callbackPath) {\n        return callbackMap[callbackPath].called;\n      },\n      /**\n       * @ngdoc method\n       * @name $jsonpCallbacks#getResponse\n       * @param {string} callbackPath the path to the callback that was sent in the JSONP request\n       * @returns {*} the data received from the response via the registered callback\n       * @description\n       * {@link $httpBackend} calls this method to get hold of the data that was provided to the callback\n       * in the JSONP response.\n       */\n      getResponse: function(callbackPath) {\n        return callbackMap[callbackPath].data;\n      },\n      /**\n       * @ngdoc method\n       * @name $jsonpCallbacks#removeCallback\n       * @param {string} callbackPath the path to the callback that was sent in the JSONP request\n       * @description\n       * {@link $httpBackend} calls this method to remove the callback after the JSONP request has\n       * completed or timed-out.\n       */\n      removeCallback: function(callbackPath) {\n        var callback = callbackMap[callbackPath];\n        delete callbacks[callback.id];\n        delete callbackMap[callbackPath];\n      }\n    };\n  };\n};\n\n/**\n * @ngdoc service\n * @name $locale\n *\n * @description\n * $locale service provides localization rules for various AngularJS components. As of right now the\n * only public api is:\n *\n * * `id` – `{string}` – locale id formatted as `languageId-countryId` (e.g. `en-us`)\n */\n\n/* global stripHash: true */\n\nvar PATH_MATCH = /^([^?#]*)(\\?([^#]*))?(#(.*))?$/,\n    DEFAULT_PORTS = {'http': 80, 'https': 443, 'ftp': 21};\nvar $locationMinErr = minErr('$location');\n\n\n/**\n * Encode path using encodeUriSegment, ignoring forward slashes\n *\n * @param {string} path Path to encode\n * @returns {string}\n */\nfunction encodePath(path) {\n  var segments = path.split('/'),\n      i = segments.length;\n\n  while (i--) {\n    // decode forward slashes to prevent them from being double encoded\n    segments[i] = encodeUriSegment(segments[i].replace(/%2F/g, '/'));\n  }\n\n  return segments.join('/');\n}\n\nfunction decodePath(path, html5Mode) {\n  var segments = path.split('/'),\n      i = segments.length;\n\n  while (i--) {\n    segments[i] = decodeURIComponent(segments[i]);\n    if (html5Mode) {\n      // encode forward slashes to prevent them from being mistaken for path separators\n      segments[i] = segments[i].replace(/\\//g, '%2F');\n    }\n  }\n\n  return segments.join('/');\n}\n\nfunction normalizePath(pathValue, searchValue, hashValue) {\n  var search = toKeyValue(searchValue),\n    hash = hashValue ? '#' + encodeUriSegment(hashValue) : '',\n    path = encodePath(pathValue);\n\n  return path + (search ? '?' + search : '') + hash;\n}\n\nfunction parseAbsoluteUrl(absoluteUrl, locationObj) {\n  var parsedUrl = urlResolve(absoluteUrl);\n\n  locationObj.$$protocol = parsedUrl.protocol;\n  locationObj.$$host = parsedUrl.hostname;\n  locationObj.$$port = toInt(parsedUrl.port) || DEFAULT_PORTS[parsedUrl.protocol] || null;\n}\n\nvar DOUBLE_SLASH_REGEX = /^\\s*[\\\\/]{2,}/;\nfunction parseAppUrl(url, locationObj, html5Mode) {\n\n  if (DOUBLE_SLASH_REGEX.test(url)) {\n    throw $locationMinErr('badpath', 'Invalid url \"{0}\".', url);\n  }\n\n  var prefixed = (url.charAt(0) !== '/');\n  if (prefixed) {\n    url = '/' + url;\n  }\n  var match = urlResolve(url);\n  var path = prefixed && match.pathname.charAt(0) === '/' ? match.pathname.substring(1) : match.pathname;\n  locationObj.$$path = decodePath(path, html5Mode);\n  locationObj.$$search = parseKeyValue(match.search);\n  locationObj.$$hash = decodeURIComponent(match.hash);\n\n  // make sure path starts with '/';\n  if (locationObj.$$path && locationObj.$$path.charAt(0) !== '/') {\n    locationObj.$$path = '/' + locationObj.$$path;\n  }\n}\n\nfunction startsWith(str, search) {\n  return str.slice(0, search.length) === search;\n}\n\n/**\n *\n * @param {string} base\n * @param {string} url\n * @returns {string} returns text from `url` after `base` or `undefined` if it does not begin with\n *                   the expected string.\n */\nfunction stripBaseUrl(base, url) {\n  if (startsWith(url, base)) {\n    return url.substr(base.length);\n  }\n}\n\nfunction stripHash(url) {\n  var index = url.indexOf('#');\n  return index === -1 ? url : url.substr(0, index);\n}\n\nfunction stripFile(url) {\n  return url.substr(0, stripHash(url).lastIndexOf('/') + 1);\n}\n\n/* return the server only (scheme://host:port) */\nfunction serverBase(url) {\n  return url.substring(0, url.indexOf('/', url.indexOf('//') + 2));\n}\n\n\n/**\n * LocationHtml5Url represents a URL\n * This object is exposed as $location service when HTML5 mode is enabled and supported\n *\n * @constructor\n * @param {string} appBase application base URL\n * @param {string} appBaseNoFile application base URL stripped of any filename\n * @param {string} basePrefix URL path prefix\n */\nfunction LocationHtml5Url(appBase, appBaseNoFile, basePrefix) {\n  this.$$html5 = true;\n  basePrefix = basePrefix || '';\n  parseAbsoluteUrl(appBase, this);\n\n\n  /**\n   * Parse given HTML5 (regular) URL string into properties\n   * @param {string} url HTML5 URL\n   * @private\n   */\n  this.$$parse = function(url) {\n    var pathUrl = stripBaseUrl(appBaseNoFile, url);\n    if (!isString(pathUrl)) {\n      throw $locationMinErr('ipthprfx', 'Invalid url \"{0}\", missing path prefix \"{1}\".', url,\n          appBaseNoFile);\n    }\n\n    parseAppUrl(pathUrl, this, true);\n\n    if (!this.$$path) {\n      this.$$path = '/';\n    }\n\n    this.$$compose();\n  };\n\n  this.$$normalizeUrl = function(url) {\n    return appBaseNoFile + url.substr(1); // first char is always '/'\n  };\n\n  this.$$parseLinkUrl = function(url, relHref) {\n    if (relHref && relHref[0] === '#') {\n      // special case for links to hash fragments:\n      // keep the old url and only replace the hash fragment\n      this.hash(relHref.slice(1));\n      return true;\n    }\n    var appUrl, prevAppUrl;\n    var rewrittenUrl;\n\n\n    if (isDefined(appUrl = stripBaseUrl(appBase, url))) {\n      prevAppUrl = appUrl;\n      if (basePrefix && isDefined(appUrl = stripBaseUrl(basePrefix, appUrl))) {\n        rewrittenUrl = appBaseNoFile + (stripBaseUrl('/', appUrl) || appUrl);\n      } else {\n        rewrittenUrl = appBase + prevAppUrl;\n      }\n    } else if (isDefined(appUrl = stripBaseUrl(appBaseNoFile, url))) {\n      rewrittenUrl = appBaseNoFile + appUrl;\n    } else if (appBaseNoFile === url + '/') {\n      rewrittenUrl = appBaseNoFile;\n    }\n    if (rewrittenUrl) {\n      this.$$parse(rewrittenUrl);\n    }\n    return !!rewrittenUrl;\n  };\n}\n\n\n/**\n * LocationHashbangUrl represents URL\n * This object is exposed as $location service when developer doesn't opt into html5 mode.\n * It also serves as the base class for html5 mode fallback on legacy browsers.\n *\n * @constructor\n * @param {string} appBase application base URL\n * @param {string} appBaseNoFile application base URL stripped of any filename\n * @param {string} hashPrefix hashbang prefix\n */\nfunction LocationHashbangUrl(appBase, appBaseNoFile, hashPrefix) {\n\n  parseAbsoluteUrl(appBase, this);\n\n\n  /**\n   * Parse given hashbang URL into properties\n   * @param {string} url Hashbang URL\n   * @private\n   */\n  this.$$parse = function(url) {\n    var withoutBaseUrl = stripBaseUrl(appBase, url) || stripBaseUrl(appBaseNoFile, url);\n    var withoutHashUrl;\n\n    if (!isUndefined(withoutBaseUrl) && withoutBaseUrl.charAt(0) === '#') {\n\n      // The rest of the URL starts with a hash so we have\n      // got either a hashbang path or a plain hash fragment\n      withoutHashUrl = stripBaseUrl(hashPrefix, withoutBaseUrl);\n      if (isUndefined(withoutHashUrl)) {\n        // There was no hashbang prefix so we just have a hash fragment\n        withoutHashUrl = withoutBaseUrl;\n      }\n\n    } else {\n      // There was no hashbang path nor hash fragment:\n      // If we are in HTML5 mode we use what is left as the path;\n      // Otherwise we ignore what is left\n      if (this.$$html5) {\n        withoutHashUrl = withoutBaseUrl;\n      } else {\n        withoutHashUrl = '';\n        if (isUndefined(withoutBaseUrl)) {\n          appBase = url;\n          /** @type {?} */ (this).replace();\n        }\n      }\n    }\n\n    parseAppUrl(withoutHashUrl, this, false);\n\n    this.$$path = removeWindowsDriveName(this.$$path, withoutHashUrl, appBase);\n\n    this.$$compose();\n\n    /*\n     * In Windows, on an anchor node on documents loaded from\n     * the filesystem, the browser will return a pathname\n     * prefixed with the drive name ('/C:/path') when a\n     * pathname without a drive is set:\n     *  * a.setAttribute('href', '/foo')\n     *   * a.pathname === '/C:/foo' //true\n     *\n     * Inside of AngularJS, we're always using pathnames that\n     * do not include drive names for routing.\n     */\n    function removeWindowsDriveName(path, url, base) {\n      /*\n      Matches paths for file protocol on windows,\n      such as /C:/foo/bar, and captures only /foo/bar.\n      */\n      var windowsFilePathExp = /^\\/[A-Z]:(\\/.*)/;\n\n      var firstPathSegmentMatch;\n\n      //Get the relative path from the input URL.\n      if (startsWith(url, base)) {\n        url = url.replace(base, '');\n      }\n\n      // The input URL intentionally contains a first path segment that ends with a colon.\n      if (windowsFilePathExp.exec(url)) {\n        return path;\n      }\n\n      firstPathSegmentMatch = windowsFilePathExp.exec(path);\n      return firstPathSegmentMatch ? firstPathSegmentMatch[1] : path;\n    }\n  };\n\n  this.$$normalizeUrl = function(url) {\n    return appBase + (url ? hashPrefix + url : '');\n  };\n\n  this.$$parseLinkUrl = function(url, relHref) {\n    if (stripHash(appBase) === stripHash(url)) {\n      this.$$parse(url);\n      return true;\n    }\n    return false;\n  };\n}\n\n\n/**\n * LocationHashbangUrl represents URL\n * This object is exposed as $location service when html5 history api is enabled but the browser\n * does not support it.\n *\n * @constructor\n * @param {string} appBase application base URL\n * @param {string} appBaseNoFile application base URL stripped of any filename\n * @param {string} hashPrefix hashbang prefix\n */\nfunction LocationHashbangInHtml5Url(appBase, appBaseNoFile, hashPrefix) {\n  this.$$html5 = true;\n  LocationHashbangUrl.apply(this, arguments);\n\n  this.$$parseLinkUrl = function(url, relHref) {\n    if (relHref && relHref[0] === '#') {\n      // special case for links to hash fragments:\n      // keep the old url and only replace the hash fragment\n      this.hash(relHref.slice(1));\n      return true;\n    }\n\n    var rewrittenUrl;\n    var appUrl;\n\n    if (appBase === stripHash(url)) {\n      rewrittenUrl = url;\n    } else if ((appUrl = stripBaseUrl(appBaseNoFile, url))) {\n      rewrittenUrl = appBase + hashPrefix + appUrl;\n    } else if (appBaseNoFile === url + '/') {\n      rewrittenUrl = appBaseNoFile;\n    }\n    if (rewrittenUrl) {\n      this.$$parse(rewrittenUrl);\n    }\n    return !!rewrittenUrl;\n  };\n\n  this.$$normalizeUrl = function(url) {\n    // include hashPrefix in $$absUrl when $$url is empty so IE9 does not reload page because of removal of '#'\n    return appBase + hashPrefix + url;\n  };\n}\n\n\nvar locationPrototype = {\n\n  /**\n   * Ensure absolute URL is initialized.\n   * @private\n   */\n  $$absUrl:'',\n\n  /**\n   * Are we in html5 mode?\n   * @private\n   */\n  $$html5: false,\n\n  /**\n   * Has any change been replacing?\n   * @private\n   */\n  $$replace: false,\n\n  /**\n   * Compose url and update `url` and `absUrl` property\n   * @private\n   */\n  $$compose: function() {\n    this.$$url = normalizePath(this.$$path, this.$$search, this.$$hash);\n    this.$$absUrl = this.$$normalizeUrl(this.$$url);\n    this.$$urlUpdatedByLocation = true;\n  },\n\n  /**\n   * @ngdoc method\n   * @name $location#absUrl\n   *\n   * @description\n   * This method is getter only.\n   *\n   * Return full URL representation with all segments encoded according to rules specified in\n   * [RFC 3986](http://www.ietf.org/rfc/rfc3986.txt).\n   *\n   *\n   * ```js\n   * // given URL http://example.com/#/some/path?foo=bar&baz=xoxo\n   * var absUrl = $location.absUrl();\n   * // => \"http://example.com/#/some/path?foo=bar&baz=xoxo\"\n   * ```\n   *\n   * @return {string} full URL\n   */\n  absUrl: locationGetter('$$absUrl'),\n\n  /**\n   * @ngdoc method\n   * @name $location#url\n   *\n   * @description\n   * This method is getter / setter.\n   *\n   * Return URL (e.g. `/path?a=b#hash`) when called without any parameter.\n   *\n   * Change path, search and hash, when called with parameter and return `$location`.\n   *\n   *\n   * ```js\n   * // given URL http://example.com/#/some/path?foo=bar&baz=xoxo\n   * var url = $location.url();\n   * // => \"/some/path?foo=bar&baz=xoxo\"\n   * ```\n   *\n   * @param {string=} url New URL without base prefix (e.g. `/path?a=b#hash`)\n   * @return {string} url\n   */\n  url: function(url) {\n    if (isUndefined(url)) {\n      return this.$$url;\n    }\n\n    var match = PATH_MATCH.exec(url);\n    if (match[1] || url === '') this.path(decodeURIComponent(match[1]));\n    if (match[2] || match[1] || url === '') this.search(match[3] || '');\n    this.hash(match[5] || '');\n\n    return this;\n  },\n\n  /**\n   * @ngdoc method\n   * @name $location#protocol\n   *\n   * @description\n   * This method is getter only.\n   *\n   * Return protocol of current URL.\n   *\n   *\n   * ```js\n   * // given URL http://example.com/#/some/path?foo=bar&baz=xoxo\n   * var protocol = $location.protocol();\n   * // => \"http\"\n   * ```\n   *\n   * @return {string} protocol of current URL\n   */\n  protocol: locationGetter('$$protocol'),\n\n  /**\n   * @ngdoc method\n   * @name $location#host\n   *\n   * @description\n   * This method is getter only.\n   *\n   * Return host of current URL.\n   *\n   * Note: compared to the non-AngularJS version `location.host` which returns `hostname:port`, this returns the `hostname` portion only.\n   *\n   *\n   * ```js\n   * // given URL http://example.com/#/some/path?foo=bar&baz=xoxo\n   * var host = $location.host();\n   * // => \"example.com\"\n   *\n   * // given URL http://user:password@example.com:8080/#/some/path?foo=bar&baz=xoxo\n   * host = $location.host();\n   * // => \"example.com\"\n   * host = location.host;\n   * // => \"example.com:8080\"\n   * ```\n   *\n   * @return {string} host of current URL.\n   */\n  host: locationGetter('$$host'),\n\n  /**\n   * @ngdoc method\n   * @name $location#port\n   *\n   * @description\n   * This method is getter only.\n   *\n   * Return port of current URL.\n   *\n   *\n   * ```js\n   * // given URL http://example.com/#/some/path?foo=bar&baz=xoxo\n   * var port = $location.port();\n   * // => 80\n   * ```\n   *\n   * @return {Number} port\n   */\n  port: locationGetter('$$port'),\n\n  /**\n   * @ngdoc method\n   * @name $location#path\n   *\n   * @description\n   * This method is getter / setter.\n   *\n   * Return path of current URL when called without any parameter.\n   *\n   * Change path when called with parameter and return `$location`.\n   *\n   * Note: Path should always begin with forward slash (/), this method will add the forward slash\n   * if it is missing.\n   *\n   *\n   * ```js\n   * // given URL http://example.com/#/some/path?foo=bar&baz=xoxo\n   * var path = $location.path();\n   * // => \"/some/path\"\n   * ```\n   *\n   * @param {(string|number)=} path New path\n   * @return {(string|object)} path if called with no parameters, or `$location` if called with a parameter\n   */\n  path: locationGetterSetter('$$path', function(path) {\n    path = path !== null ? path.toString() : '';\n    return path.charAt(0) === '/' ? path : '/' + path;\n  }),\n\n  /**\n   * @ngdoc method\n   * @name $location#search\n   *\n   * @description\n   * This method is getter / setter.\n   *\n   * Return search part (as object) of current URL when called without any parameter.\n   *\n   * Change search part when called with parameter and return `$location`.\n   *\n   *\n   * ```js\n   * // given URL http://example.com/#/some/path?foo=bar&baz=xoxo\n   * var searchObject = $location.search();\n   * // => {foo: 'bar', baz: 'xoxo'}\n   *\n   * // set foo to 'yipee'\n   * $location.search('foo', 'yipee');\n   * // $location.search() => {foo: 'yipee', baz: 'xoxo'}\n   * ```\n   *\n   * @param {string|Object.<string>|Object.<Array.<string>>} search New search params - string or\n   * hash object.\n   *\n   * When called with a single argument the method acts as a setter, setting the `search` component\n   * of `$location` to the specified value.\n   *\n   * If the argument is a hash object containing an array of values, these values will be encoded\n   * as duplicate search parameters in the URL.\n   *\n   * @param {(string|Number|Array<string>|boolean)=} paramValue If `search` is a string or number, then `paramValue`\n   * will override only a single search property.\n   *\n   * If `paramValue` is an array, it will override the property of the `search` component of\n   * `$location` specified via the first argument.\n   *\n   * If `paramValue` is `null`, the property specified via the first argument will be deleted.\n   *\n   * If `paramValue` is `true`, the property specified via the first argument will be added with no\n   * value nor trailing equal sign.\n   *\n   * @return {Object} If called with no arguments returns the parsed `search` object. If called with\n   * one or more arguments returns `$location` object itself.\n   */\n  search: function(search, paramValue) {\n    switch (arguments.length) {\n      case 0:\n        return this.$$search;\n      case 1:\n        if (isString(search) || isNumber(search)) {\n          search = search.toString();\n          this.$$search = parseKeyValue(search);\n        } else if (isObject(search)) {\n          search = copy(search, {});\n          // remove object undefined or null properties\n          forEach(search, function(value, key) {\n            if (value == null) delete search[key];\n          });\n\n          this.$$search = search;\n        } else {\n          throw $locationMinErr('isrcharg',\n              'The first argument of the `$location#search()` call must be a string or an object.');\n        }\n        break;\n      default:\n        if (isUndefined(paramValue) || paramValue === null) {\n          delete this.$$search[search];\n        } else {\n          this.$$search[search] = paramValue;\n        }\n    }\n\n    this.$$compose();\n    return this;\n  },\n\n  /**\n   * @ngdoc method\n   * @name $location#hash\n   *\n   * @description\n   * This method is getter / setter.\n   *\n   * Returns the hash fragment when called without any parameters.\n   *\n   * Changes the hash fragment when called with a parameter and returns `$location`.\n   *\n   *\n   * ```js\n   * // given URL http://example.com/#/some/path?foo=bar&baz=xoxo#hashValue\n   * var hash = $location.hash();\n   * // => \"hashValue\"\n   * ```\n   *\n   * @param {(string|number)=} hash New hash fragment\n   * @return {string} hash\n   */\n  hash: locationGetterSetter('$$hash', function(hash) {\n    return hash !== null ? hash.toString() : '';\n  }),\n\n  /**\n   * @ngdoc method\n   * @name $location#replace\n   *\n   * @description\n   * If called, all changes to $location during the current `$digest` will replace the current history\n   * record, instead of adding a new one.\n   */\n  replace: function() {\n    this.$$replace = true;\n    return this;\n  }\n};\n\nforEach([LocationHashbangInHtml5Url, LocationHashbangUrl, LocationHtml5Url], function(Location) {\n  Location.prototype = Object.create(locationPrototype);\n\n  /**\n   * @ngdoc method\n   * @name $location#state\n   *\n   * @description\n   * This method is getter / setter.\n   *\n   * Return the history state object when called without any parameter.\n   *\n   * Change the history state object when called with one parameter and return `$location`.\n   * The state object is later passed to `pushState` or `replaceState`.\n   *\n   * NOTE: This method is supported only in HTML5 mode and only in browsers supporting\n   * the HTML5 History API (i.e. methods `pushState` and `replaceState`). If you need to support\n   * older browsers (like IE9 or Android < 4.0), don't use this method.\n   *\n   * @param {object=} state State object for pushState or replaceState\n   * @return {object} state\n   */\n  Location.prototype.state = function(state) {\n    if (!arguments.length) {\n      return this.$$state;\n    }\n\n    if (Location !== LocationHtml5Url || !this.$$html5) {\n      throw $locationMinErr('nostate', 'History API state support is available only ' +\n        'in HTML5 mode and only in browsers supporting HTML5 History API');\n    }\n    // The user might modify `stateObject` after invoking `$location.state(stateObject)`\n    // but we're changing the $$state reference to $browser.state() during the $digest\n    // so the modification window is narrow.\n    this.$$state = isUndefined(state) ? null : state;\n    this.$$urlUpdatedByLocation = true;\n\n    return this;\n  };\n});\n\n\nfunction locationGetter(property) {\n  return /** @this */ function() {\n    return this[property];\n  };\n}\n\n\nfunction locationGetterSetter(property, preprocess) {\n  return /** @this */ function(value) {\n    if (isUndefined(value)) {\n      return this[property];\n    }\n\n    this[property] = preprocess(value);\n    this.$$compose();\n\n    return this;\n  };\n}\n\n\n/**\n * @ngdoc service\n * @name $location\n *\n * @requires $rootElement\n *\n * @description\n * The $location service parses the URL in the browser address bar (based on the\n * [window.location](https://developer.mozilla.org/en/window.location)) and makes the URL\n * available to your application. Changes to the URL in the address bar are reflected into\n * $location service and changes to $location are reflected into the browser address bar.\n *\n * **The $location service:**\n *\n * - Exposes the current URL in the browser address bar, so you can\n *   - Watch and observe the URL.\n *   - Change the URL.\n * - Synchronizes the URL with the browser when the user\n *   - Changes the address bar.\n *   - Clicks the back or forward button (or clicks a History link).\n *   - Clicks on a link.\n * - Represents the URL object as a set of methods (protocol, host, port, path, search, hash).\n *\n * For more information see {@link guide/$location Developer Guide: Using $location}\n */\n\n/**\n * @ngdoc provider\n * @name $locationProvider\n * @this\n *\n * @description\n * Use the `$locationProvider` to configure how the application deep linking paths are stored.\n */\nfunction $LocationProvider() {\n  var hashPrefix = '!',\n      html5Mode = {\n        enabled: false,\n        requireBase: true,\n        rewriteLinks: true\n      };\n\n  /**\n   * @ngdoc method\n   * @name $locationProvider#hashPrefix\n   * @description\n   * The default value for the prefix is `'!'`.\n   * @param {string=} prefix Prefix for hash part (containing path and search)\n   * @returns {*} current value if used as getter or itself (chaining) if used as setter\n   */\n  this.hashPrefix = function(prefix) {\n    if (isDefined(prefix)) {\n      hashPrefix = prefix;\n      return this;\n    } else {\n      return hashPrefix;\n    }\n  };\n\n  /**\n   * @ngdoc method\n   * @name $locationProvider#html5Mode\n   * @description\n   * @param {(boolean|Object)=} mode If boolean, sets `html5Mode.enabled` to value.\n   *   If object, sets `enabled`, `requireBase` and `rewriteLinks` to respective values. Supported\n   *   properties:\n   *   - **enabled** – `{boolean}` – (default: false) If true, will rely on `history.pushState` to\n   *     change urls where supported. Will fall back to hash-prefixed paths in browsers that do not\n   *     support `pushState`.\n   *   - **requireBase** - `{boolean}` - (default: `true`) When html5Mode is enabled, specifies\n   *     whether or not a <base> tag is required to be present. If `enabled` and `requireBase` are\n   *     true, and a base tag is not present, an error will be thrown when `$location` is injected.\n   *     See the {@link guide/$location $location guide for more information}\n   *   - **rewriteLinks** - `{boolean|string}` - (default: `true`) When html5Mode is enabled,\n   *     enables/disables URL rewriting for relative links. If set to a string, URL rewriting will\n   *     only happen on links with an attribute that matches the given string. For example, if set\n   *     to `'internal-link'`, then the URL will only be rewritten for `<a internal-link>` links.\n   *     Note that [attribute name normalization](guide/directive#normalization) does not apply\n   *     here, so `'internalLink'` will **not** match `'internal-link'`.\n   *\n   * @returns {Object} html5Mode object if used as getter or itself (chaining) if used as setter\n   */\n  this.html5Mode = function(mode) {\n    if (isBoolean(mode)) {\n      html5Mode.enabled = mode;\n      return this;\n    } else if (isObject(mode)) {\n\n      if (isBoolean(mode.enabled)) {\n        html5Mode.enabled = mode.enabled;\n      }\n\n      if (isBoolean(mode.requireBase)) {\n        html5Mode.requireBase = mode.requireBase;\n      }\n\n      if (isBoolean(mode.rewriteLinks) || isString(mode.rewriteLinks)) {\n        html5Mode.rewriteLinks = mode.rewriteLinks;\n      }\n\n      return this;\n    } else {\n      return html5Mode;\n    }\n  };\n\n  /**\n   * @ngdoc event\n   * @name $location#$locationChangeStart\n   * @eventType broadcast on root scope\n   * @description\n   * Broadcasted before a URL will change.\n   *\n   * This change can be prevented by calling\n   * `preventDefault` method of the event. See {@link ng.$rootScope.Scope#$on} for more\n   * details about event object. Upon successful change\n   * {@link ng.$location#$locationChangeSuccess $locationChangeSuccess} is fired.\n   *\n   * The `newState` and `oldState` parameters may be defined only in HTML5 mode and when\n   * the browser supports the HTML5 History API.\n   *\n   * @param {Object} angularEvent Synthetic event object.\n   * @param {string} newUrl New URL\n   * @param {string=} oldUrl URL that was before it was changed.\n   * @param {string=} newState New history state object\n   * @param {string=} oldState History state object that was before it was changed.\n   */\n\n  /**\n   * @ngdoc event\n   * @name $location#$locationChangeSuccess\n   * @eventType broadcast on root scope\n   * @description\n   * Broadcasted after a URL was changed.\n   *\n   * The `newState` and `oldState` parameters may be defined only in HTML5 mode and when\n   * the browser supports the HTML5 History API.\n   *\n   * @param {Object} angularEvent Synthetic event object.\n   * @param {string} newUrl New URL\n   * @param {string=} oldUrl URL that was before it was changed.\n   * @param {string=} newState New history state object\n   * @param {string=} oldState History state object that was before it was changed.\n   */\n\n  this.$get = ['$rootScope', '$browser', '$sniffer', '$rootElement', '$window',\n      function($rootScope, $browser, $sniffer, $rootElement, $window) {\n    var $location,\n        LocationMode,\n        baseHref = $browser.baseHref(), // if base[href] is undefined, it defaults to ''\n        initialUrl = $browser.url(),\n        appBase;\n\n    if (html5Mode.enabled) {\n      if (!baseHref && html5Mode.requireBase) {\n        throw $locationMinErr('nobase',\n          '$location in HTML5 mode requires a <base> tag to be present!');\n      }\n      appBase = serverBase(initialUrl) + (baseHref || '/');\n      LocationMode = $sniffer.history ? LocationHtml5Url : LocationHashbangInHtml5Url;\n    } else {\n      appBase = stripHash(initialUrl);\n      LocationMode = LocationHashbangUrl;\n    }\n    var appBaseNoFile = stripFile(appBase);\n\n    $location = new LocationMode(appBase, appBaseNoFile, '#' + hashPrefix);\n    $location.$$parseLinkUrl(initialUrl, initialUrl);\n\n    $location.$$state = $browser.state();\n\n    var IGNORE_URI_REGEXP = /^\\s*(javascript|mailto):/i;\n\n    // Determine if two URLs are equal despite potentially having different encoding/normalizing\n    //  such as $location.absUrl() vs $browser.url()\n    // See https://github.com/angular/angular.js/issues/16592\n    function urlsEqual(a, b) {\n      return a === b || urlResolve(a).href === urlResolve(b).href;\n    }\n\n    function setBrowserUrlWithFallback(url, replace, state) {\n      var oldUrl = $location.url();\n      var oldState = $location.$$state;\n      try {\n        $browser.url(url, replace, state);\n\n        // Make sure $location.state() returns referentially identical (not just deeply equal)\n        // state object; this makes possible quick checking if the state changed in the digest\n        // loop. Checking deep equality would be too expensive.\n        $location.$$state = $browser.state();\n      } catch (e) {\n        // Restore old values if pushState fails\n        $location.url(oldUrl);\n        $location.$$state = oldState;\n\n        throw e;\n      }\n    }\n\n    $rootElement.on('click', function(event) {\n      var rewriteLinks = html5Mode.rewriteLinks;\n      // TODO(vojta): rewrite link when opening in new tab/window (in legacy browser)\n      // currently we open nice url link and redirect then\n\n      if (!rewriteLinks || event.ctrlKey || event.metaKey || event.shiftKey || event.which === 2 || event.button === 2) return;\n\n      var elm = jqLite(event.target);\n\n      // traverse the DOM up to find first A tag\n      while (nodeName_(elm[0]) !== 'a') {\n        // ignore rewriting if no A tag (reached root element, or no parent - removed from document)\n        if (elm[0] === $rootElement[0] || !(elm = elm.parent())[0]) return;\n      }\n\n      if (isString(rewriteLinks) && isUndefined(elm.attr(rewriteLinks))) return;\n\n      var absHref = elm.prop('href');\n      // get the actual href attribute - see\n      // http://msdn.microsoft.com/en-us/library/ie/dd347148(v=vs.85).aspx\n      var relHref = elm.attr('href') || elm.attr('xlink:href');\n\n      if (isObject(absHref) && absHref.toString() === '[object SVGAnimatedString]') {\n        // SVGAnimatedString.animVal should be identical to SVGAnimatedString.baseVal, unless during\n        // an animation.\n        absHref = urlResolve(absHref.animVal).href;\n      }\n\n      // Ignore when url is started with javascript: or mailto:\n      if (IGNORE_URI_REGEXP.test(absHref)) return;\n\n      if (absHref && !elm.attr('target') && !event.isDefaultPrevented()) {\n        if ($location.$$parseLinkUrl(absHref, relHref)) {\n          // We do a preventDefault for all urls that are part of the AngularJS application,\n          // in html5mode and also without, so that we are able to abort navigation without\n          // getting double entries in the location history.\n          event.preventDefault();\n          // update location manually\n          if ($location.absUrl() !== $browser.url()) {\n            $rootScope.$apply();\n          }\n        }\n      }\n    });\n\n\n    // rewrite hashbang url <> html5 url\n    if ($location.absUrl() !== initialUrl) {\n      $browser.url($location.absUrl(), true);\n    }\n\n    var initializing = true;\n\n    // update $location when $browser url changes\n    $browser.onUrlChange(function(newUrl, newState) {\n\n      if (!startsWith(newUrl, appBaseNoFile)) {\n        // If we are navigating outside of the app then force a reload\n        $window.location.href = newUrl;\n        return;\n      }\n\n      $rootScope.$evalAsync(function() {\n        var oldUrl = $location.absUrl();\n        var oldState = $location.$$state;\n        var defaultPrevented;\n        $location.$$parse(newUrl);\n        $location.$$state = newState;\n\n        defaultPrevented = $rootScope.$broadcast('$locationChangeStart', newUrl, oldUrl,\n            newState, oldState).defaultPrevented;\n\n        // if the location was changed by a `$locationChangeStart` handler then stop\n        // processing this location change\n        if ($location.absUrl() !== newUrl) return;\n\n        if (defaultPrevented) {\n          $location.$$parse(oldUrl);\n          $location.$$state = oldState;\n          setBrowserUrlWithFallback(oldUrl, false, oldState);\n        } else {\n          initializing = false;\n          afterLocationChange(oldUrl, oldState);\n        }\n      });\n      if (!$rootScope.$$phase) $rootScope.$digest();\n    });\n\n    // update browser\n    $rootScope.$watch(function $locationWatch() {\n      if (initializing || $location.$$urlUpdatedByLocation) {\n        $location.$$urlUpdatedByLocation = false;\n\n        var oldUrl = $browser.url();\n        var newUrl = $location.absUrl();\n        var oldState = $browser.state();\n        var currentReplace = $location.$$replace;\n        var urlOrStateChanged = !urlsEqual(oldUrl, newUrl) ||\n          ($location.$$html5 && $sniffer.history && oldState !== $location.$$state);\n\n        if (initializing || urlOrStateChanged) {\n          initializing = false;\n\n          $rootScope.$evalAsync(function() {\n            var newUrl = $location.absUrl();\n            var defaultPrevented = $rootScope.$broadcast('$locationChangeStart', newUrl, oldUrl,\n                $location.$$state, oldState).defaultPrevented;\n\n            // if the location was changed by a `$locationChangeStart` handler then stop\n            // processing this location change\n            if ($location.absUrl() !== newUrl) return;\n\n            if (defaultPrevented) {\n              $location.$$parse(oldUrl);\n              $location.$$state = oldState;\n            } else {\n              if (urlOrStateChanged) {\n                setBrowserUrlWithFallback(newUrl, currentReplace,\n                                          oldState === $location.$$state ? null : $location.$$state);\n              }\n              afterLocationChange(oldUrl, oldState);\n            }\n          });\n        }\n      }\n\n      $location.$$replace = false;\n\n      // we don't need to return anything because $evalAsync will make the digest loop dirty when\n      // there is a change\n    });\n\n    return $location;\n\n    function afterLocationChange(oldUrl, oldState) {\n      $rootScope.$broadcast('$locationChangeSuccess', $location.absUrl(), oldUrl,\n        $location.$$state, oldState);\n    }\n}];\n}\n\n/**\n * @ngdoc service\n * @name $log\n * @requires $window\n *\n * @description\n * Simple service for logging. Default implementation safely writes the message\n * into the browser's console (if present).\n *\n * The main purpose of this service is to simplify debugging and troubleshooting.\n *\n * To reveal the location of the calls to `$log` in the JavaScript console,\n * you can \"blackbox\" the AngularJS source in your browser:\n *\n * [Mozilla description of blackboxing](https://developer.mozilla.org/en-US/docs/Tools/Debugger/How_to/Black_box_a_source).\n * [Chrome description of blackboxing](https://developer.chrome.com/devtools/docs/blackboxing).\n *\n * Note: Not all browsers support blackboxing.\n *\n * The default is to log `debug` messages. You can use\n * {@link ng.$logProvider ng.$logProvider#debugEnabled} to change this.\n *\n * @example\n   <example module=\"logExample\" name=\"log-service\">\n     <file name=\"script.js\">\n       angular.module('logExample', [])\n         .controller('LogController', ['$scope', '$log', function($scope, $log) {\n           $scope.$log = $log;\n           $scope.message = 'Hello World!';\n         }]);\n     </file>\n     <file name=\"index.html\">\n       <div ng-controller=\"LogController\">\n         <p>Reload this page with open console, enter text and hit the log button...</p>\n         <label>Message:\n         <input type=\"text\" ng-model=\"message\" /></label>\n         <button ng-click=\"$log.log(message)\">log</button>\n         <button ng-click=\"$log.warn(message)\">warn</button>\n         <button ng-click=\"$log.info(message)\">info</button>\n         <button ng-click=\"$log.error(message)\">error</button>\n         <button ng-click=\"$log.debug(message)\">debug</button>\n       </div>\n     </file>\n   </example>\n */\n\n/**\n * @ngdoc provider\n * @name $logProvider\n * @this\n *\n * @description\n * Use the `$logProvider` to configure how the application logs messages\n */\nfunction $LogProvider() {\n  var debug = true,\n      self = this;\n\n  /**\n   * @ngdoc method\n   * @name $logProvider#debugEnabled\n   * @description\n   * @param {boolean=} flag enable or disable debug level messages\n   * @returns {*} current value if used as getter or itself (chaining) if used as setter\n   */\n  this.debugEnabled = function(flag) {\n    if (isDefined(flag)) {\n      debug = flag;\n      return this;\n    } else {\n      return debug;\n    }\n  };\n\n  this.$get = ['$window', function($window) {\n    // Support: IE 9-11, Edge 12-14+\n    // IE/Edge display errors in such a way that it requires the user to click in 4 places\n    // to see the stack trace. There is no way to feature-detect it so there's a chance\n    // of the user agent sniffing to go wrong but since it's only about logging, this shouldn't\n    // break apps. Other browsers display errors in a sensible way and some of them map stack\n    // traces along source maps if available so it makes sense to let browsers display it\n    // as they want.\n    var formatStackTrace = msie || /\\bEdge\\//.test($window.navigator && $window.navigator.userAgent);\n\n    return {\n      /**\n       * @ngdoc method\n       * @name $log#log\n       *\n       * @description\n       * Write a log message\n       */\n      log: consoleLog('log'),\n\n      /**\n       * @ngdoc method\n       * @name $log#info\n       *\n       * @description\n       * Write an information message\n       */\n      info: consoleLog('info'),\n\n      /**\n       * @ngdoc method\n       * @name $log#warn\n       *\n       * @description\n       * Write a warning message\n       */\n      warn: consoleLog('warn'),\n\n      /**\n       * @ngdoc method\n       * @name $log#error\n       *\n       * @description\n       * Write an error message\n       */\n      error: consoleLog('error'),\n\n      /**\n       * @ngdoc method\n       * @name $log#debug\n       *\n       * @description\n       * Write a debug message\n       */\n      debug: (function() {\n        var fn = consoleLog('debug');\n\n        return function() {\n          if (debug) {\n            fn.apply(self, arguments);\n          }\n        };\n      })()\n    };\n\n    function formatError(arg) {\n      if (isError(arg)) {\n        if (arg.stack && formatStackTrace) {\n          arg = (arg.message && arg.stack.indexOf(arg.message) === -1)\n              ? 'Error: ' + arg.message + '\\n' + arg.stack\n              : arg.stack;\n        } else if (arg.sourceURL) {\n          arg = arg.message + '\\n' + arg.sourceURL + ':' + arg.line;\n        }\n      }\n      return arg;\n    }\n\n    function consoleLog(type) {\n      var console = $window.console || {},\n          logFn = console[type] || console.log || noop;\n\n      return function() {\n        var args = [];\n        forEach(arguments, function(arg) {\n          args.push(formatError(arg));\n        });\n        // Support: IE 9 only\n        // console methods don't inherit from Function.prototype in IE 9 so we can't\n        // call `logFn.apply(console, args)` directly.\n        return Function.prototype.apply.call(logFn, console, args);\n      };\n    }\n  }];\n}\n\n/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *\n *     Any commits to this file should be reviewed with security in mind.  *\n *   Changes to this file can potentially create security vulnerabilities. *\n *          An approval from 2 Core members with history of modifying      *\n *                         this file is required.                          *\n *                                                                         *\n *  Does the change somehow allow for arbitrary javascript to be executed? *\n *    Or allows for someone to change the prototype of built-in objects?   *\n *     Or gives undesired access to variables likes document or window?    *\n * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */\n\nvar $parseMinErr = minErr('$parse');\n\nvar objectValueOf = {}.constructor.prototype.valueOf;\n\n// Sandboxing AngularJS Expressions\n// ------------------------------\n// AngularJS expressions are no longer sandboxed. So it is now even easier to access arbitrary JS code by\n// various means such as obtaining a reference to native JS functions like the Function constructor.\n//\n// As an example, consider the following AngularJS expression:\n//\n//   {}.toString.constructor('alert(\"evil JS code\")')\n//\n// It is important to realize that if you create an expression from a string that contains user provided\n// content then it is possible that your application contains a security vulnerability to an XSS style attack.\n//\n// See https://docs.angularjs.org/guide/security\n\n\nfunction getStringValue(name) {\n  // Property names must be strings. This means that non-string objects cannot be used\n  // as keys in an object. Any non-string object, including a number, is typecasted\n  // into a string via the toString method.\n  // -- MDN, https://developer.mozilla.org/en/docs/Web/JavaScript/Reference/Operators/Property_accessors#Property_names\n  //\n  // So, to ensure that we are checking the same `name` that JavaScript would use, we cast it\n  // to a string. It's not always possible. If `name` is an object and its `toString` method is\n  // 'broken' (doesn't return a string, isn't a function, etc.), an error will be thrown:\n  //\n  // TypeError: Cannot convert object to primitive value\n  //\n  // For performance reasons, we don't catch this error here and allow it to propagate up the call\n  // stack. Note that you'll get the same error in JavaScript if you try to access a property using\n  // such a 'broken' object as a key.\n  return name + '';\n}\n\n\nvar OPERATORS = createMap();\nforEach('+ - * / % === !== == != < > <= >= && || ! = |'.split(' '), function(operator) { OPERATORS[operator] = true; });\nvar ESCAPE = {'n':'\\n', 'f':'\\f', 'r':'\\r', 't':'\\t', 'v':'\\v', '\\'':'\\'', '\"':'\"'};\n\n\n/////////////////////////////////////////\n\n\n/**\n * @constructor\n */\nvar Lexer = function Lexer(options) {\n  this.options = options;\n};\n\nLexer.prototype = {\n  constructor: Lexer,\n\n  lex: function(text) {\n    this.text = text;\n    this.index = 0;\n    this.tokens = [];\n\n    while (this.index < this.text.length) {\n      var ch = this.text.charAt(this.index);\n      if (ch === '\"' || ch === '\\'') {\n        this.readString(ch);\n      } else if (this.isNumber(ch) || ch === '.' && this.isNumber(this.peek())) {\n        this.readNumber();\n      } else if (this.isIdentifierStart(this.peekMultichar())) {\n        this.readIdent();\n      } else if (this.is(ch, '(){}[].,;:?')) {\n        this.tokens.push({index: this.index, text: ch});\n        this.index++;\n      } else if (this.isWhitespace(ch)) {\n        this.index++;\n      } else {\n        var ch2 = ch + this.peek();\n        var ch3 = ch2 + this.peek(2);\n        var op1 = OPERATORS[ch];\n        var op2 = OPERATORS[ch2];\n        var op3 = OPERATORS[ch3];\n        if (op1 || op2 || op3) {\n          var token = op3 ? ch3 : (op2 ? ch2 : ch);\n          this.tokens.push({index: this.index, text: token, operator: true});\n          this.index += token.length;\n        } else {\n          this.throwError('Unexpected next character ', this.index, this.index + 1);\n        }\n      }\n    }\n    return this.tokens;\n  },\n\n  is: function(ch, chars) {\n    return chars.indexOf(ch) !== -1;\n  },\n\n  peek: function(i) {\n    var num = i || 1;\n    return (this.index + num < this.text.length) ? this.text.charAt(this.index + num) : false;\n  },\n\n  isNumber: function(ch) {\n    return ('0' <= ch && ch <= '9') && typeof ch === 'string';\n  },\n\n  isWhitespace: function(ch) {\n    // IE treats non-breaking space as \\u00A0\n    return (ch === ' ' || ch === '\\r' || ch === '\\t' ||\n            ch === '\\n' || ch === '\\v' || ch === '\\u00A0');\n  },\n\n  isIdentifierStart: function(ch) {\n    return this.options.isIdentifierStart ?\n        this.options.isIdentifierStart(ch, this.codePointAt(ch)) :\n        this.isValidIdentifierStart(ch);\n  },\n\n  isValidIdentifierStart: function(ch) {\n    return ('a' <= ch && ch <= 'z' ||\n            'A' <= ch && ch <= 'Z' ||\n            '_' === ch || ch === '$');\n  },\n\n  isIdentifierContinue: function(ch) {\n    return this.options.isIdentifierContinue ?\n        this.options.isIdentifierContinue(ch, this.codePointAt(ch)) :\n        this.isValidIdentifierContinue(ch);\n  },\n\n  isValidIdentifierContinue: function(ch, cp) {\n    return this.isValidIdentifierStart(ch, cp) || this.isNumber(ch);\n  },\n\n  codePointAt: function(ch) {\n    if (ch.length === 1) return ch.charCodeAt(0);\n    // eslint-disable-next-line no-bitwise\n    return (ch.charCodeAt(0) << 10) + ch.charCodeAt(1) - 0x35FDC00;\n  },\n\n  peekMultichar: function() {\n    var ch = this.text.charAt(this.index);\n    var peek = this.peek();\n    if (!peek) {\n      return ch;\n    }\n    var cp1 = ch.charCodeAt(0);\n    var cp2 = peek.charCodeAt(0);\n    if (cp1 >= 0xD800 && cp1 <= 0xDBFF && cp2 >= 0xDC00 && cp2 <= 0xDFFF) {\n      return ch + peek;\n    }\n    return ch;\n  },\n\n  isExpOperator: function(ch) {\n    return (ch === '-' || ch === '+' || this.isNumber(ch));\n  },\n\n  throwError: function(error, start, end) {\n    end = end || this.index;\n    var colStr = (isDefined(start)\n            ? 's ' + start +  '-' + this.index + ' [' + this.text.substring(start, end) + ']'\n            : ' ' + end);\n    throw $parseMinErr('lexerr', 'Lexer Error: {0} at column{1} in expression [{2}].',\n        error, colStr, this.text);\n  },\n\n  readNumber: function() {\n    var number = '';\n    var start = this.index;\n    while (this.index < this.text.length) {\n      var ch = lowercase(this.text.charAt(this.index));\n      if (ch === '.' || this.isNumber(ch)) {\n        number += ch;\n      } else {\n        var peekCh = this.peek();\n        if (ch === 'e' && this.isExpOperator(peekCh)) {\n          number += ch;\n        } else if (this.isExpOperator(ch) &&\n            peekCh && this.isNumber(peekCh) &&\n            number.charAt(number.length - 1) === 'e') {\n          number += ch;\n        } else if (this.isExpOperator(ch) &&\n            (!peekCh || !this.isNumber(peekCh)) &&\n            number.charAt(number.length - 1) === 'e') {\n          this.throwError('Invalid exponent');\n        } else {\n          break;\n        }\n      }\n      this.index++;\n    }\n    this.tokens.push({\n      index: start,\n      text: number,\n      constant: true,\n      value: Number(number)\n    });\n  },\n\n  readIdent: function() {\n    var start = this.index;\n    this.index += this.peekMultichar().length;\n    while (this.index < this.text.length) {\n      var ch = this.peekMultichar();\n      if (!this.isIdentifierContinue(ch)) {\n        break;\n      }\n      this.index += ch.length;\n    }\n    this.tokens.push({\n      index: start,\n      text: this.text.slice(start, this.index),\n      identifier: true\n    });\n  },\n\n  readString: function(quote) {\n    var start = this.index;\n    this.index++;\n    var string = '';\n    var rawString = quote;\n    var escape = false;\n    while (this.index < this.text.length) {\n      var ch = this.text.charAt(this.index);\n      rawString += ch;\n      if (escape) {\n        if (ch === 'u') {\n          var hex = this.text.substring(this.index + 1, this.index + 5);\n          if (!hex.match(/[\\da-f]{4}/i)) {\n            this.throwError('Invalid unicode escape [\\\\u' + hex + ']');\n          }\n          this.index += 4;\n          string += String.fromCharCode(parseInt(hex, 16));\n        } else {\n          var rep = ESCAPE[ch];\n          string = string + (rep || ch);\n        }\n        escape = false;\n      } else if (ch === '\\\\') {\n        escape = true;\n      } else if (ch === quote) {\n        this.index++;\n        this.tokens.push({\n          index: start,\n          text: rawString,\n          constant: true,\n          value: string\n        });\n        return;\n      } else {\n        string += ch;\n      }\n      this.index++;\n    }\n    this.throwError('Unterminated quote', start);\n  }\n};\n\nvar AST = function AST(lexer, options) {\n  this.lexer = lexer;\n  this.options = options;\n};\n\nAST.Program = 'Program';\nAST.ExpressionStatement = 'ExpressionStatement';\nAST.AssignmentExpression = 'AssignmentExpression';\nAST.ConditionalExpression = 'ConditionalExpression';\nAST.LogicalExpression = 'LogicalExpression';\nAST.BinaryExpression = 'BinaryExpression';\nAST.UnaryExpression = 'UnaryExpression';\nAST.CallExpression = 'CallExpression';\nAST.MemberExpression = 'MemberExpression';\nAST.Identifier = 'Identifier';\nAST.Literal = 'Literal';\nAST.ArrayExpression = 'ArrayExpression';\nAST.Property = 'Property';\nAST.ObjectExpression = 'ObjectExpression';\nAST.ThisExpression = 'ThisExpression';\nAST.LocalsExpression = 'LocalsExpression';\n\n// Internal use only\nAST.NGValueParameter = 'NGValueParameter';\n\nAST.prototype = {\n  ast: function(text) {\n    this.text = text;\n    this.tokens = this.lexer.lex(text);\n\n    var value = this.program();\n\n    if (this.tokens.length !== 0) {\n      this.throwError('is an unexpected token', this.tokens[0]);\n    }\n\n    return value;\n  },\n\n  program: function() {\n    var body = [];\n    while (true) {\n      if (this.tokens.length > 0 && !this.peek('}', ')', ';', ']'))\n        body.push(this.expressionStatement());\n      if (!this.expect(';')) {\n        return { type: AST.Program, body: body};\n      }\n    }\n  },\n\n  expressionStatement: function() {\n    return { type: AST.ExpressionStatement, expression: this.filterChain() };\n  },\n\n  filterChain: function() {\n    var left = this.expression();\n    while (this.expect('|')) {\n      left = this.filter(left);\n    }\n    return left;\n  },\n\n  expression: function() {\n    return this.assignment();\n  },\n\n  assignment: function() {\n    var result = this.ternary();\n    if (this.expect('=')) {\n      if (!isAssignable(result)) {\n        throw $parseMinErr('lval', 'Trying to assign a value to a non l-value');\n      }\n\n      result = { type: AST.AssignmentExpression, left: result, right: this.assignment(), operator: '='};\n    }\n    return result;\n  },\n\n  ternary: function() {\n    var test = this.logicalOR();\n    var alternate;\n    var consequent;\n    if (this.expect('?')) {\n      alternate = this.expression();\n      if (this.consume(':')) {\n        consequent = this.expression();\n        return { type: AST.ConditionalExpression, test: test, alternate: alternate, consequent: consequent};\n      }\n    }\n    return test;\n  },\n\n  logicalOR: function() {\n    var left = this.logicalAND();\n    while (this.expect('||')) {\n      left = { type: AST.LogicalExpression, operator: '||', left: left, right: this.logicalAND() };\n    }\n    return left;\n  },\n\n  logicalAND: function() {\n    var left = this.equality();\n    while (this.expect('&&')) {\n      left = { type: AST.LogicalExpression, operator: '&&', left: left, right: this.equality()};\n    }\n    return left;\n  },\n\n  equality: function() {\n    var left = this.relational();\n    var token;\n    while ((token = this.expect('==','!=','===','!=='))) {\n      left = { type: AST.BinaryExpression, operator: token.text, left: left, right: this.relational() };\n    }\n    return left;\n  },\n\n  relational: function() {\n    var left = this.additive();\n    var token;\n    while ((token = this.expect('<', '>', '<=', '>='))) {\n      left = { type: AST.BinaryExpression, operator: token.text, left: left, right: this.additive() };\n    }\n    return left;\n  },\n\n  additive: function() {\n    var left = this.multiplicative();\n    var token;\n    while ((token = this.expect('+','-'))) {\n      left = { type: AST.BinaryExpression, operator: token.text, left: left, right: this.multiplicative() };\n    }\n    return left;\n  },\n\n  multiplicative: function() {\n    var left = this.unary();\n    var token;\n    while ((token = this.expect('*','/','%'))) {\n      left = { type: AST.BinaryExpression, operator: token.text, left: left, right: this.unary() };\n    }\n    return left;\n  },\n\n  unary: function() {\n    var token;\n    if ((token = this.expect('+', '-', '!'))) {\n      return { type: AST.UnaryExpression, operator: token.text, prefix: true, argument: this.unary() };\n    } else {\n      return this.primary();\n    }\n  },\n\n  primary: function() {\n    var primary;\n    if (this.expect('(')) {\n      primary = this.filterChain();\n      this.consume(')');\n    } else if (this.expect('[')) {\n      primary = this.arrayDeclaration();\n    } else if (this.expect('{')) {\n      primary = this.object();\n    } else if (this.selfReferential.hasOwnProperty(this.peek().text)) {\n      primary = copy(this.selfReferential[this.consume().text]);\n    } else if (this.options.literals.hasOwnProperty(this.peek().text)) {\n      primary = { type: AST.Literal, value: this.options.literals[this.consume().text]};\n    } else if (this.peek().identifier) {\n      primary = this.identifier();\n    } else if (this.peek().constant) {\n      primary = this.constant();\n    } else {\n      this.throwError('not a primary expression', this.peek());\n    }\n\n    var next;\n    while ((next = this.expect('(', '[', '.'))) {\n      if (next.text === '(') {\n        primary = {type: AST.CallExpression, callee: primary, arguments: this.parseArguments() };\n        this.consume(')');\n      } else if (next.text === '[') {\n        primary = { type: AST.MemberExpression, object: primary, property: this.expression(), computed: true };\n        this.consume(']');\n      } else if (next.text === '.') {\n        primary = { type: AST.MemberExpression, object: primary, property: this.identifier(), computed: false };\n      } else {\n        this.throwError('IMPOSSIBLE');\n      }\n    }\n    return primary;\n  },\n\n  filter: function(baseExpression) {\n    var args = [baseExpression];\n    var result = {type: AST.CallExpression, callee: this.identifier(), arguments: args, filter: true};\n\n    while (this.expect(':')) {\n      args.push(this.expression());\n    }\n\n    return result;\n  },\n\n  parseArguments: function() {\n    var args = [];\n    if (this.peekToken().text !== ')') {\n      do {\n        args.push(this.filterChain());\n      } while (this.expect(','));\n    }\n    return args;\n  },\n\n  identifier: function() {\n    var token = this.consume();\n    if (!token.identifier) {\n      this.throwError('is not a valid identifier', token);\n    }\n    return { type: AST.Identifier, name: token.text };\n  },\n\n  constant: function() {\n    // TODO check that it is a constant\n    return { type: AST.Literal, value: this.consume().value };\n  },\n\n  arrayDeclaration: function() {\n    var elements = [];\n    if (this.peekToken().text !== ']') {\n      do {\n        if (this.peek(']')) {\n          // Support trailing commas per ES5.1.\n          break;\n        }\n        elements.push(this.expression());\n      } while (this.expect(','));\n    }\n    this.consume(']');\n\n    return { type: AST.ArrayExpression, elements: elements };\n  },\n\n  object: function() {\n    var properties = [], property;\n    if (this.peekToken().text !== '}') {\n      do {\n        if (this.peek('}')) {\n          // Support trailing commas per ES5.1.\n          break;\n        }\n        property = {type: AST.Property, kind: 'init'};\n        if (this.peek().constant) {\n          property.key = this.constant();\n          property.computed = false;\n          this.consume(':');\n          property.value = this.expression();\n        } else if (this.peek().identifier) {\n          property.key = this.identifier();\n          property.computed = false;\n          if (this.peek(':')) {\n            this.consume(':');\n            property.value = this.expression();\n          } else {\n            property.value = property.key;\n          }\n        } else if (this.peek('[')) {\n          this.consume('[');\n          property.key = this.expression();\n          this.consume(']');\n          property.computed = true;\n          this.consume(':');\n          property.value = this.expression();\n        } else {\n          this.throwError('invalid key', this.peek());\n        }\n        properties.push(property);\n      } while (this.expect(','));\n    }\n    this.consume('}');\n\n    return {type: AST.ObjectExpression, properties: properties };\n  },\n\n  throwError: function(msg, token) {\n    throw $parseMinErr('syntax',\n        'Syntax Error: Token \\'{0}\\' {1} at column {2} of the expression [{3}] starting at [{4}].',\n          token.text, msg, (token.index + 1), this.text, this.text.substring(token.index));\n  },\n\n  consume: function(e1) {\n    if (this.tokens.length === 0) {\n      throw $parseMinErr('ueoe', 'Unexpected end of expression: {0}', this.text);\n    }\n\n    var token = this.expect(e1);\n    if (!token) {\n      this.throwError('is unexpected, expecting [' + e1 + ']', this.peek());\n    }\n    return token;\n  },\n\n  peekToken: function() {\n    if (this.tokens.length === 0) {\n      throw $parseMinErr('ueoe', 'Unexpected end of expression: {0}', this.text);\n    }\n    return this.tokens[0];\n  },\n\n  peek: function(e1, e2, e3, e4) {\n    return this.peekAhead(0, e1, e2, e3, e4);\n  },\n\n  peekAhead: function(i, e1, e2, e3, e4) {\n    if (this.tokens.length > i) {\n      var token = this.tokens[i];\n      var t = token.text;\n      if (t === e1 || t === e2 || t === e3 || t === e4 ||\n          (!e1 && !e2 && !e3 && !e4)) {\n        return token;\n      }\n    }\n    return false;\n  },\n\n  expect: function(e1, e2, e3, e4) {\n    var token = this.peek(e1, e2, e3, e4);\n    if (token) {\n      this.tokens.shift();\n      return token;\n    }\n    return false;\n  },\n\n  selfReferential: {\n    'this': {type: AST.ThisExpression },\n    '$locals': {type: AST.LocalsExpression }\n  }\n};\n\nfunction ifDefined(v, d) {\n  return typeof v !== 'undefined' ? v : d;\n}\n\nfunction plusFn(l, r) {\n  if (typeof l === 'undefined') return r;\n  if (typeof r === 'undefined') return l;\n  return l + r;\n}\n\nfunction isStateless($filter, filterName) {\n  var fn = $filter(filterName);\n  return !fn.$stateful;\n}\n\nvar PURITY_ABSOLUTE = 1;\nvar PURITY_RELATIVE = 2;\n\n// Detect nodes which could depend on non-shallow state of objects\nfunction isPure(node, parentIsPure) {\n  switch (node.type) {\n    // Computed members might invoke a stateful toString()\n    case AST.MemberExpression:\n      if (node.computed) {\n        return false;\n      }\n      break;\n\n    // Unary always convert to primative\n    case AST.UnaryExpression:\n      return PURITY_ABSOLUTE;\n\n    // The binary + operator can invoke a stateful toString().\n    case AST.BinaryExpression:\n      return node.operator !== '+' ? PURITY_ABSOLUTE : false;\n\n    // Functions / filters probably read state from within objects\n    case AST.CallExpression:\n      return false;\n  }\n\n  return (undefined === parentIsPure) ? PURITY_RELATIVE : parentIsPure;\n}\n\nfunction findConstantAndWatchExpressions(ast, $filter, parentIsPure) {\n  var allConstants;\n  var argsToWatch;\n  var isStatelessFilter;\n\n  var astIsPure = ast.isPure = isPure(ast, parentIsPure);\n\n  switch (ast.type) {\n  case AST.Program:\n    allConstants = true;\n    forEach(ast.body, function(expr) {\n      findConstantAndWatchExpressions(expr.expression, $filter, astIsPure);\n      allConstants = allConstants && expr.expression.constant;\n    });\n    ast.constant = allConstants;\n    break;\n  case AST.Literal:\n    ast.constant = true;\n    ast.toWatch = [];\n    break;\n  case AST.UnaryExpression:\n    findConstantAndWatchExpressions(ast.argument, $filter, astIsPure);\n    ast.constant = ast.argument.constant;\n    ast.toWatch = ast.argument.toWatch;\n    break;\n  case AST.BinaryExpression:\n    findConstantAndWatchExpressions(ast.left, $filter, astIsPure);\n    findConstantAndWatchExpressions(ast.right, $filter, astIsPure);\n    ast.constant = ast.left.constant && ast.right.constant;\n    ast.toWatch = ast.left.toWatch.concat(ast.right.toWatch);\n    break;\n  case AST.LogicalExpression:\n    findConstantAndWatchExpressions(ast.left, $filter, astIsPure);\n    findConstantAndWatchExpressions(ast.right, $filter, astIsPure);\n    ast.constant = ast.left.constant && ast.right.constant;\n    ast.toWatch = ast.constant ? [] : [ast];\n    break;\n  case AST.ConditionalExpression:\n    findConstantAndWatchExpressions(ast.test, $filter, astIsPure);\n    findConstantAndWatchExpressions(ast.alternate, $filter, astIsPure);\n    findConstantAndWatchExpressions(ast.consequent, $filter, astIsPure);\n    ast.constant = ast.test.constant && ast.alternate.constant && ast.consequent.constant;\n    ast.toWatch = ast.constant ? [] : [ast];\n    break;\n  case AST.Identifier:\n    ast.constant = false;\n    ast.toWatch = [ast];\n    break;\n  case AST.MemberExpression:\n    findConstantAndWatchExpressions(ast.object, $filter, astIsPure);\n    if (ast.computed) {\n      findConstantAndWatchExpressions(ast.property, $filter, astIsPure);\n    }\n    ast.constant = ast.object.constant && (!ast.computed || ast.property.constant);\n    ast.toWatch = ast.constant ? [] : [ast];\n    break;\n  case AST.CallExpression:\n    isStatelessFilter = ast.filter ? isStateless($filter, ast.callee.name) : false;\n    allConstants = isStatelessFilter;\n    argsToWatch = [];\n    forEach(ast.arguments, function(expr) {\n      findConstantAndWatchExpressions(expr, $filter, astIsPure);\n      allConstants = allConstants && expr.constant;\n      argsToWatch.push.apply(argsToWatch, expr.toWatch);\n    });\n    ast.constant = allConstants;\n    ast.toWatch = isStatelessFilter ? argsToWatch : [ast];\n    break;\n  case AST.AssignmentExpression:\n    findConstantAndWatchExpressions(ast.left, $filter, astIsPure);\n    findConstantAndWatchExpressions(ast.right, $filter, astIsPure);\n    ast.constant = ast.left.constant && ast.right.constant;\n    ast.toWatch = [ast];\n    break;\n  case AST.ArrayExpression:\n    allConstants = true;\n    argsToWatch = [];\n    forEach(ast.elements, function(expr) {\n      findConstantAndWatchExpressions(expr, $filter, astIsPure);\n      allConstants = allConstants && expr.constant;\n      argsToWatch.push.apply(argsToWatch, expr.toWatch);\n    });\n    ast.constant = allConstants;\n    ast.toWatch = argsToWatch;\n    break;\n  case AST.ObjectExpression:\n    allConstants = true;\n    argsToWatch = [];\n    forEach(ast.properties, function(property) {\n      findConstantAndWatchExpressions(property.value, $filter, astIsPure);\n      allConstants = allConstants && property.value.constant;\n      argsToWatch.push.apply(argsToWatch, property.value.toWatch);\n      if (property.computed) {\n        //`{[key]: value}` implicitly does `key.toString()` which may be non-pure\n        findConstantAndWatchExpressions(property.key, $filter, /*parentIsPure=*/false);\n        allConstants = allConstants && property.key.constant;\n        argsToWatch.push.apply(argsToWatch, property.key.toWatch);\n      }\n    });\n    ast.constant = allConstants;\n    ast.toWatch = argsToWatch;\n    break;\n  case AST.ThisExpression:\n    ast.constant = false;\n    ast.toWatch = [];\n    break;\n  case AST.LocalsExpression:\n    ast.constant = false;\n    ast.toWatch = [];\n    break;\n  }\n}\n\nfunction getInputs(body) {\n  if (body.length !== 1) return;\n  var lastExpression = body[0].expression;\n  var candidate = lastExpression.toWatch;\n  if (candidate.length !== 1) return candidate;\n  return candidate[0] !== lastExpression ? candidate : undefined;\n}\n\nfunction isAssignable(ast) {\n  return ast.type === AST.Identifier || ast.type === AST.MemberExpression;\n}\n\nfunction assignableAST(ast) {\n  if (ast.body.length === 1 && isAssignable(ast.body[0].expression)) {\n    return {type: AST.AssignmentExpression, left: ast.body[0].expression, right: {type: AST.NGValueParameter}, operator: '='};\n  }\n}\n\nfunction isLiteral(ast) {\n  return ast.body.length === 0 ||\n      ast.body.length === 1 && (\n      ast.body[0].expression.type === AST.Literal ||\n      ast.body[0].expression.type === AST.ArrayExpression ||\n      ast.body[0].expression.type === AST.ObjectExpression);\n}\n\nfunction isConstant(ast) {\n  return ast.constant;\n}\n\nfunction ASTCompiler($filter) {\n  this.$filter = $filter;\n}\n\nASTCompiler.prototype = {\n  compile: function(ast) {\n    var self = this;\n    this.state = {\n      nextId: 0,\n      filters: {},\n      fn: {vars: [], body: [], own: {}},\n      assign: {vars: [], body: [], own: {}},\n      inputs: []\n    };\n    findConstantAndWatchExpressions(ast, self.$filter);\n    var extra = '';\n    var assignable;\n    this.stage = 'assign';\n    if ((assignable = assignableAST(ast))) {\n      this.state.computing = 'assign';\n      var result = this.nextId();\n      this.recurse(assignable, result);\n      this.return_(result);\n      extra = 'fn.assign=' + this.generateFunction('assign', 's,v,l');\n    }\n    var toWatch = getInputs(ast.body);\n    self.stage = 'inputs';\n    forEach(toWatch, function(watch, key) {\n      var fnKey = 'fn' + key;\n      self.state[fnKey] = {vars: [], body: [], own: {}};\n      self.state.computing = fnKey;\n      var intoId = self.nextId();\n      self.recurse(watch, intoId);\n      self.return_(intoId);\n      self.state.inputs.push({name: fnKey, isPure: watch.isPure});\n      watch.watchId = key;\n    });\n    this.state.computing = 'fn';\n    this.stage = 'main';\n    this.recurse(ast);\n    var fnString =\n      // The build and minification steps remove the string \"use strict\" from the code, but this is done using a regex.\n      // This is a workaround for this until we do a better job at only removing the prefix only when we should.\n      '\"' + this.USE + ' ' + this.STRICT + '\";\\n' +\n      this.filterPrefix() +\n      'var fn=' + this.generateFunction('fn', 's,l,a,i') +\n      extra +\n      this.watchFns() +\n      'return fn;';\n\n    // eslint-disable-next-line no-new-func\n    var fn = (new Function('$filter',\n        'getStringValue',\n        'ifDefined',\n        'plus',\n        fnString))(\n          this.$filter,\n          getStringValue,\n          ifDefined,\n          plusFn);\n    this.state = this.stage = undefined;\n    return fn;\n  },\n\n  USE: 'use',\n\n  STRICT: 'strict',\n\n  watchFns: function() {\n    var result = [];\n    var inputs = this.state.inputs;\n    var self = this;\n    forEach(inputs, function(input) {\n      result.push('var ' + input.name + '=' + self.generateFunction(input.name, 's'));\n      if (input.isPure) {\n        result.push(input.name, '.isPure=' + JSON.stringify(input.isPure) + ';');\n      }\n    });\n    if (inputs.length) {\n      result.push('fn.inputs=[' + inputs.map(function(i) { return i.name; }).join(',') + '];');\n    }\n    return result.join('');\n  },\n\n  generateFunction: function(name, params) {\n    return 'function(' + params + '){' +\n        this.varsPrefix(name) +\n        this.body(name) +\n        '};';\n  },\n\n  filterPrefix: function() {\n    var parts = [];\n    var self = this;\n    forEach(this.state.filters, function(id, filter) {\n      parts.push(id + '=$filter(' + self.escape(filter) + ')');\n    });\n    if (parts.length) return 'var ' + parts.join(',') + ';';\n    return '';\n  },\n\n  varsPrefix: function(section) {\n    return this.state[section].vars.length ? 'var ' + this.state[section].vars.join(',') + ';' : '';\n  },\n\n  body: function(section) {\n    return this.state[section].body.join('');\n  },\n\n  recurse: function(ast, intoId, nameId, recursionFn, create, skipWatchIdCheck) {\n    var left, right, self = this, args, expression, computed;\n    recursionFn = recursionFn || noop;\n    if (!skipWatchIdCheck && isDefined(ast.watchId)) {\n      intoId = intoId || this.nextId();\n      this.if_('i',\n        this.lazyAssign(intoId, this.computedMember('i', ast.watchId)),\n        this.lazyRecurse(ast, intoId, nameId, recursionFn, create, true)\n      );\n      return;\n    }\n    switch (ast.type) {\n    case AST.Program:\n      forEach(ast.body, function(expression, pos) {\n        self.recurse(expression.expression, undefined, undefined, function(expr) { right = expr; });\n        if (pos !== ast.body.length - 1) {\n          self.current().body.push(right, ';');\n        } else {\n          self.return_(right);\n        }\n      });\n      break;\n    case AST.Literal:\n      expression = this.escape(ast.value);\n      this.assign(intoId, expression);\n      recursionFn(intoId || expression);\n      break;\n    case AST.UnaryExpression:\n      this.recurse(ast.argument, undefined, undefined, function(expr) { right = expr; });\n      expression = ast.operator + '(' + this.ifDefined(right, 0) + ')';\n      this.assign(intoId, expression);\n      recursionFn(expression);\n      break;\n    case AST.BinaryExpression:\n      this.recurse(ast.left, undefined, undefined, function(expr) { left = expr; });\n      this.recurse(ast.right, undefined, undefined, function(expr) { right = expr; });\n      if (ast.operator === '+') {\n        expression = this.plus(left, right);\n      } else if (ast.operator === '-') {\n        expression = this.ifDefined(left, 0) + ast.operator + this.ifDefined(right, 0);\n      } else {\n        expression = '(' + left + ')' + ast.operator + '(' + right + ')';\n      }\n      this.assign(intoId, expression);\n      recursionFn(expression);\n      break;\n    case AST.LogicalExpression:\n      intoId = intoId || this.nextId();\n      self.recurse(ast.left, intoId);\n      self.if_(ast.operator === '&&' ? intoId : self.not(intoId), self.lazyRecurse(ast.right, intoId));\n      recursionFn(intoId);\n      break;\n    case AST.ConditionalExpression:\n      intoId = intoId || this.nextId();\n      self.recurse(ast.test, intoId);\n      self.if_(intoId, self.lazyRecurse(ast.alternate, intoId), self.lazyRecurse(ast.consequent, intoId));\n      recursionFn(intoId);\n      break;\n    case AST.Identifier:\n      intoId = intoId || this.nextId();\n      if (nameId) {\n        nameId.context = self.stage === 'inputs' ? 's' : this.assign(this.nextId(), this.getHasOwnProperty('l', ast.name) + '?l:s');\n        nameId.computed = false;\n        nameId.name = ast.name;\n      }\n      self.if_(self.stage === 'inputs' || self.not(self.getHasOwnProperty('l', ast.name)),\n        function() {\n          self.if_(self.stage === 'inputs' || 's', function() {\n            if (create && create !== 1) {\n              self.if_(\n                self.isNull(self.nonComputedMember('s', ast.name)),\n                self.lazyAssign(self.nonComputedMember('s', ast.name), '{}'));\n            }\n            self.assign(intoId, self.nonComputedMember('s', ast.name));\n          });\n        }, intoId && self.lazyAssign(intoId, self.nonComputedMember('l', ast.name))\n        );\n      recursionFn(intoId);\n      break;\n    case AST.MemberExpression:\n      left = nameId && (nameId.context = this.nextId()) || this.nextId();\n      intoId = intoId || this.nextId();\n      self.recurse(ast.object, left, undefined, function() {\n        self.if_(self.notNull(left), function() {\n          if (ast.computed) {\n            right = self.nextId();\n            self.recurse(ast.property, right);\n            self.getStringValue(right);\n            if (create && create !== 1) {\n              self.if_(self.not(self.computedMember(left, right)), self.lazyAssign(self.computedMember(left, right), '{}'));\n            }\n            expression = self.computedMember(left, right);\n            self.assign(intoId, expression);\n            if (nameId) {\n              nameId.computed = true;\n              nameId.name = right;\n            }\n          } else {\n            if (create && create !== 1) {\n              self.if_(self.isNull(self.nonComputedMember(left, ast.property.name)), self.lazyAssign(self.nonComputedMember(left, ast.property.name), '{}'));\n            }\n            expression = self.nonComputedMember(left, ast.property.name);\n            self.assign(intoId, expression);\n            if (nameId) {\n              nameId.computed = false;\n              nameId.name = ast.property.name;\n            }\n          }\n        }, function() {\n          self.assign(intoId, 'undefined');\n        });\n        recursionFn(intoId);\n      }, !!create);\n      break;\n    case AST.CallExpression:\n      intoId = intoId || this.nextId();\n      if (ast.filter) {\n        right = self.filter(ast.callee.name);\n        args = [];\n        forEach(ast.arguments, function(expr) {\n          var argument = self.nextId();\n          self.recurse(expr, argument);\n          args.push(argument);\n        });\n        expression = right + '(' + args.join(',') + ')';\n        self.assign(intoId, expression);\n        recursionFn(intoId);\n      } else {\n        right = self.nextId();\n        left = {};\n        args = [];\n        self.recurse(ast.callee, right, left, function() {\n          self.if_(self.notNull(right), function() {\n            forEach(ast.arguments, function(expr) {\n              self.recurse(expr, ast.constant ? undefined : self.nextId(), undefined, function(argument) {\n                args.push(argument);\n              });\n            });\n            if (left.name) {\n              expression = self.member(left.context, left.name, left.computed) + '(' + args.join(',') + ')';\n            } else {\n              expression = right + '(' + args.join(',') + ')';\n            }\n            self.assign(intoId, expression);\n          }, function() {\n            self.assign(intoId, 'undefined');\n          });\n          recursionFn(intoId);\n        });\n      }\n      break;\n    case AST.AssignmentExpression:\n      right = this.nextId();\n      left = {};\n      this.recurse(ast.left, undefined, left, function() {\n        self.if_(self.notNull(left.context), function() {\n          self.recurse(ast.right, right);\n          expression = self.member(left.context, left.name, left.computed) + ast.operator + right;\n          self.assign(intoId, expression);\n          recursionFn(intoId || expression);\n        });\n      }, 1);\n      break;\n    case AST.ArrayExpression:\n      args = [];\n      forEach(ast.elements, function(expr) {\n        self.recurse(expr, ast.constant ? undefined : self.nextId(), undefined, function(argument) {\n          args.push(argument);\n        });\n      });\n      expression = '[' + args.join(',') + ']';\n      this.assign(intoId, expression);\n      recursionFn(intoId || expression);\n      break;\n    case AST.ObjectExpression:\n      args = [];\n      computed = false;\n      forEach(ast.properties, function(property) {\n        if (property.computed) {\n          computed = true;\n        }\n      });\n      if (computed) {\n        intoId = intoId || this.nextId();\n        this.assign(intoId, '{}');\n        forEach(ast.properties, function(property) {\n          if (property.computed) {\n            left = self.nextId();\n            self.recurse(property.key, left);\n          } else {\n            left = property.key.type === AST.Identifier ?\n                       property.key.name :\n                       ('' + property.key.value);\n          }\n          right = self.nextId();\n          self.recurse(property.value, right);\n          self.assign(self.member(intoId, left, property.computed), right);\n        });\n      } else {\n        forEach(ast.properties, function(property) {\n          self.recurse(property.value, ast.constant ? undefined : self.nextId(), undefined, function(expr) {\n            args.push(self.escape(\n                property.key.type === AST.Identifier ? property.key.name :\n                  ('' + property.key.value)) +\n                ':' + expr);\n          });\n        });\n        expression = '{' + args.join(',') + '}';\n        this.assign(intoId, expression);\n      }\n      recursionFn(intoId || expression);\n      break;\n    case AST.ThisExpression:\n      this.assign(intoId, 's');\n      recursionFn(intoId || 's');\n      break;\n    case AST.LocalsExpression:\n      this.assign(intoId, 'l');\n      recursionFn(intoId || 'l');\n      break;\n    case AST.NGValueParameter:\n      this.assign(intoId, 'v');\n      recursionFn(intoId || 'v');\n      break;\n    }\n  },\n\n  getHasOwnProperty: function(element, property) {\n    var key = element + '.' + property;\n    var own = this.current().own;\n    if (!own.hasOwnProperty(key)) {\n      own[key] = this.nextId(false, element + '&&(' + this.escape(property) + ' in ' + element + ')');\n    }\n    return own[key];\n  },\n\n  assign: function(id, value) {\n    if (!id) return;\n    this.current().body.push(id, '=', value, ';');\n    return id;\n  },\n\n  filter: function(filterName) {\n    if (!this.state.filters.hasOwnProperty(filterName)) {\n      this.state.filters[filterName] = this.nextId(true);\n    }\n    return this.state.filters[filterName];\n  },\n\n  ifDefined: function(id, defaultValue) {\n    return 'ifDefined(' + id + ',' + this.escape(defaultValue) + ')';\n  },\n\n  plus: function(left, right) {\n    return 'plus(' + left + ',' + right + ')';\n  },\n\n  return_: function(id) {\n    this.current().body.push('return ', id, ';');\n  },\n\n  if_: function(test, alternate, consequent) {\n    if (test === true) {\n      alternate();\n    } else {\n      var body = this.current().body;\n      body.push('if(', test, '){');\n      alternate();\n      body.push('}');\n      if (consequent) {\n        body.push('else{');\n        consequent();\n        body.push('}');\n      }\n    }\n  },\n\n  not: function(expression) {\n    return '!(' + expression + ')';\n  },\n\n  isNull: function(expression) {\n    return expression + '==null';\n  },\n\n  notNull: function(expression) {\n    return expression + '!=null';\n  },\n\n  nonComputedMember: function(left, right) {\n    var SAFE_IDENTIFIER = /^[$_a-zA-Z][$_a-zA-Z0-9]*$/;\n    var UNSAFE_CHARACTERS = /[^$_a-zA-Z0-9]/g;\n    if (SAFE_IDENTIFIER.test(right)) {\n      return left + '.' + right;\n    } else {\n      return left  + '[\"' + right.replace(UNSAFE_CHARACTERS, this.stringEscapeFn) + '\"]';\n    }\n  },\n\n  computedMember: function(left, right) {\n    return left + '[' + right + ']';\n  },\n\n  member: function(left, right, computed) {\n    if (computed) return this.computedMember(left, right);\n    return this.nonComputedMember(left, right);\n  },\n\n  getStringValue: function(item) {\n    this.assign(item, 'getStringValue(' + item + ')');\n  },\n\n  lazyRecurse: function(ast, intoId, nameId, recursionFn, create, skipWatchIdCheck) {\n    var self = this;\n    return function() {\n      self.recurse(ast, intoId, nameId, recursionFn, create, skipWatchIdCheck);\n    };\n  },\n\n  lazyAssign: function(id, value) {\n    var self = this;\n    return function() {\n      self.assign(id, value);\n    };\n  },\n\n  stringEscapeRegex: /[^ a-zA-Z0-9]/g,\n\n  stringEscapeFn: function(c) {\n    return '\\\\u' + ('0000' + c.charCodeAt(0).toString(16)).slice(-4);\n  },\n\n  escape: function(value) {\n    if (isString(value)) return '\\'' + value.replace(this.stringEscapeRegex, this.stringEscapeFn) + '\\'';\n    if (isNumber(value)) return value.toString();\n    if (value === true) return 'true';\n    if (value === false) return 'false';\n    if (value === null) return 'null';\n    if (typeof value === 'undefined') return 'undefined';\n\n    throw $parseMinErr('esc', 'IMPOSSIBLE');\n  },\n\n  nextId: function(skip, init) {\n    var id = 'v' + (this.state.nextId++);\n    if (!skip) {\n      this.current().vars.push(id + (init ? '=' + init : ''));\n    }\n    return id;\n  },\n\n  current: function() {\n    return this.state[this.state.computing];\n  }\n};\n\n\nfunction ASTInterpreter($filter) {\n  this.$filter = $filter;\n}\n\nASTInterpreter.prototype = {\n  compile: function(ast) {\n    var self = this;\n    findConstantAndWatchExpressions(ast, self.$filter);\n    var assignable;\n    var assign;\n    if ((assignable = assignableAST(ast))) {\n      assign = this.recurse(assignable);\n    }\n    var toWatch = getInputs(ast.body);\n    var inputs;\n    if (toWatch) {\n      inputs = [];\n      forEach(toWatch, function(watch, key) {\n        var input = self.recurse(watch);\n        input.isPure = watch.isPure;\n        watch.input = input;\n        inputs.push(input);\n        watch.watchId = key;\n      });\n    }\n    var expressions = [];\n    forEach(ast.body, function(expression) {\n      expressions.push(self.recurse(expression.expression));\n    });\n    var fn = ast.body.length === 0 ? noop :\n             ast.body.length === 1 ? expressions[0] :\n             function(scope, locals) {\n               var lastValue;\n               forEach(expressions, function(exp) {\n                 lastValue = exp(scope, locals);\n               });\n               return lastValue;\n             };\n    if (assign) {\n      fn.assign = function(scope, value, locals) {\n        return assign(scope, locals, value);\n      };\n    }\n    if (inputs) {\n      fn.inputs = inputs;\n    }\n    return fn;\n  },\n\n  recurse: function(ast, context, create) {\n    var left, right, self = this, args;\n    if (ast.input) {\n      return this.inputs(ast.input, ast.watchId);\n    }\n    switch (ast.type) {\n    case AST.Literal:\n      return this.value(ast.value, context);\n    case AST.UnaryExpression:\n      right = this.recurse(ast.argument);\n      return this['unary' + ast.operator](right, context);\n    case AST.BinaryExpression:\n      left = this.recurse(ast.left);\n      right = this.recurse(ast.right);\n      return this['binary' + ast.operator](left, right, context);\n    case AST.LogicalExpression:\n      left = this.recurse(ast.left);\n      right = this.recurse(ast.right);\n      return this['binary' + ast.operator](left, right, context);\n    case AST.ConditionalExpression:\n      return this['ternary?:'](\n        this.recurse(ast.test),\n        this.recurse(ast.alternate),\n        this.recurse(ast.consequent),\n        context\n      );\n    case AST.Identifier:\n      return self.identifier(ast.name, context, create);\n    case AST.MemberExpression:\n      left = this.recurse(ast.object, false, !!create);\n      if (!ast.computed) {\n        right = ast.property.name;\n      }\n      if (ast.computed) right = this.recurse(ast.property);\n      return ast.computed ?\n        this.computedMember(left, right, context, create) :\n        this.nonComputedMember(left, right, context, create);\n    case AST.CallExpression:\n      args = [];\n      forEach(ast.arguments, function(expr) {\n        args.push(self.recurse(expr));\n      });\n      if (ast.filter) right = this.$filter(ast.callee.name);\n      if (!ast.filter) right = this.recurse(ast.callee, true);\n      return ast.filter ?\n        function(scope, locals, assign, inputs) {\n          var values = [];\n          for (var i = 0; i < args.length; ++i) {\n            values.push(args[i](scope, locals, assign, inputs));\n          }\n          var value = right.apply(undefined, values, inputs);\n          return context ? {context: undefined, name: undefined, value: value} : value;\n        } :\n        function(scope, locals, assign, inputs) {\n          var rhs = right(scope, locals, assign, inputs);\n          var value;\n          if (rhs.value != null) {\n            var values = [];\n            for (var i = 0; i < args.length; ++i) {\n              values.push(args[i](scope, locals, assign, inputs));\n            }\n            value = rhs.value.apply(rhs.context, values);\n          }\n          return context ? {value: value} : value;\n        };\n    case AST.AssignmentExpression:\n      left = this.recurse(ast.left, true, 1);\n      right = this.recurse(ast.right);\n      return function(scope, locals, assign, inputs) {\n        var lhs = left(scope, locals, assign, inputs);\n        var rhs = right(scope, locals, assign, inputs);\n        lhs.context[lhs.name] = rhs;\n        return context ? {value: rhs} : rhs;\n      };\n    case AST.ArrayExpression:\n      args = [];\n      forEach(ast.elements, function(expr) {\n        args.push(self.recurse(expr));\n      });\n      return function(scope, locals, assign, inputs) {\n        var value = [];\n        for (var i = 0; i < args.length; ++i) {\n          value.push(args[i](scope, locals, assign, inputs));\n        }\n        return context ? {value: value} : value;\n      };\n    case AST.ObjectExpression:\n      args = [];\n      forEach(ast.properties, function(property) {\n        if (property.computed) {\n          args.push({key: self.recurse(property.key),\n                     computed: true,\n                     value: self.recurse(property.value)\n          });\n        } else {\n          args.push({key: property.key.type === AST.Identifier ?\n                          property.key.name :\n                          ('' + property.key.value),\n                     computed: false,\n                     value: self.recurse(property.value)\n          });\n        }\n      });\n      return function(scope, locals, assign, inputs) {\n        var value = {};\n        for (var i = 0; i < args.length; ++i) {\n          if (args[i].computed) {\n            value[args[i].key(scope, locals, assign, inputs)] = args[i].value(scope, locals, assign, inputs);\n          } else {\n            value[args[i].key] = args[i].value(scope, locals, assign, inputs);\n          }\n        }\n        return context ? {value: value} : value;\n      };\n    case AST.ThisExpression:\n      return function(scope) {\n        return context ? {value: scope} : scope;\n      };\n    case AST.LocalsExpression:\n      return function(scope, locals) {\n        return context ? {value: locals} : locals;\n      };\n    case AST.NGValueParameter:\n      return function(scope, locals, assign) {\n        return context ? {value: assign} : assign;\n      };\n    }\n  },\n\n  'unary+': function(argument, context) {\n    return function(scope, locals, assign, inputs) {\n      var arg = argument(scope, locals, assign, inputs);\n      if (isDefined(arg)) {\n        arg = +arg;\n      } else {\n        arg = 0;\n      }\n      return context ? {value: arg} : arg;\n    };\n  },\n  'unary-': function(argument, context) {\n    return function(scope, locals, assign, inputs) {\n      var arg = argument(scope, locals, assign, inputs);\n      if (isDefined(arg)) {\n        arg = -arg;\n      } else {\n        arg = -0;\n      }\n      return context ? {value: arg} : arg;\n    };\n  },\n  'unary!': function(argument, context) {\n    return function(scope, locals, assign, inputs) {\n      var arg = !argument(scope, locals, assign, inputs);\n      return context ? {value: arg} : arg;\n    };\n  },\n  'binary+': function(left, right, context) {\n    return function(scope, locals, assign, inputs) {\n      var lhs = left(scope, locals, assign, inputs);\n      var rhs = right(scope, locals, assign, inputs);\n      var arg = plusFn(lhs, rhs);\n      return context ? {value: arg} : arg;\n    };\n  },\n  'binary-': function(left, right, context) {\n    return function(scope, locals, assign, inputs) {\n      var lhs = left(scope, locals, assign, inputs);\n      var rhs = right(scope, locals, assign, inputs);\n      var arg = (isDefined(lhs) ? lhs : 0) - (isDefined(rhs) ? rhs : 0);\n      return context ? {value: arg} : arg;\n    };\n  },\n  'binary*': function(left, right, context) {\n    return function(scope, locals, assign, inputs) {\n      var arg = left(scope, locals, assign, inputs) * right(scope, locals, assign, inputs);\n      return context ? {value: arg} : arg;\n    };\n  },\n  'binary/': function(left, right, context) {\n    return function(scope, locals, assign, inputs) {\n      var arg = left(scope, locals, assign, inputs) / right(scope, locals, assign, inputs);\n      return context ? {value: arg} : arg;\n    };\n  },\n  'binary%': function(left, right, context) {\n    return function(scope, locals, assign, inputs) {\n      var arg = left(scope, locals, assign, inputs) % right(scope, locals, assign, inputs);\n      return context ? {value: arg} : arg;\n    };\n  },\n  'binary===': function(left, right, context) {\n    return function(scope, locals, assign, inputs) {\n      var arg = left(scope, locals, assign, inputs) === right(scope, locals, assign, inputs);\n      return context ? {value: arg} : arg;\n    };\n  },\n  'binary!==': function(left, right, context) {\n    return function(scope, locals, assign, inputs) {\n      var arg = left(scope, locals, assign, inputs) !== right(scope, locals, assign, inputs);\n      return context ? {value: arg} : arg;\n    };\n  },\n  'binary==': function(left, right, context) {\n    return function(scope, locals, assign, inputs) {\n      // eslint-disable-next-line eqeqeq\n      var arg = left(scope, locals, assign, inputs) == right(scope, locals, assign, inputs);\n      return context ? {value: arg} : arg;\n    };\n  },\n  'binary!=': function(left, right, context) {\n    return function(scope, locals, assign, inputs) {\n      // eslint-disable-next-line eqeqeq\n      var arg = left(scope, locals, assign, inputs) != right(scope, locals, assign, inputs);\n      return context ? {value: arg} : arg;\n    };\n  },\n  'binary<': function(left, right, context) {\n    return function(scope, locals, assign, inputs) {\n      var arg = left(scope, locals, assign, inputs) < right(scope, locals, assign, inputs);\n      return context ? {value: arg} : arg;\n    };\n  },\n  'binary>': function(left, right, context) {\n    return function(scope, locals, assign, inputs) {\n      var arg = left(scope, locals, assign, inputs) > right(scope, locals, assign, inputs);\n      return context ? {value: arg} : arg;\n    };\n  },\n  'binary<=': function(left, right, context) {\n    return function(scope, locals, assign, inputs) {\n      var arg = left(scope, locals, assign, inputs) <= right(scope, locals, assign, inputs);\n      return context ? {value: arg} : arg;\n    };\n  },\n  'binary>=': function(left, right, context) {\n    return function(scope, locals, assign, inputs) {\n      var arg = left(scope, locals, assign, inputs) >= right(scope, locals, assign, inputs);\n      return context ? {value: arg} : arg;\n    };\n  },\n  'binary&&': function(left, right, context) {\n    return function(scope, locals, assign, inputs) {\n      var arg = left(scope, locals, assign, inputs) && right(scope, locals, assign, inputs);\n      return context ? {value: arg} : arg;\n    };\n  },\n  'binary||': function(left, right, context) {\n    return function(scope, locals, assign, inputs) {\n      var arg = left(scope, locals, assign, inputs) || right(scope, locals, assign, inputs);\n      return context ? {value: arg} : arg;\n    };\n  },\n  'ternary?:': function(test, alternate, consequent, context) {\n    return function(scope, locals, assign, inputs) {\n      var arg = test(scope, locals, assign, inputs) ? alternate(scope, locals, assign, inputs) : consequent(scope, locals, assign, inputs);\n      return context ? {value: arg} : arg;\n    };\n  },\n  value: function(value, context) {\n    return function() { return context ? {context: undefined, name: undefined, value: value} : value; };\n  },\n  identifier: function(name, context, create) {\n    return function(scope, locals, assign, inputs) {\n      var base = locals && (name in locals) ? locals : scope;\n      if (create && create !== 1 && base && base[name] == null) {\n        base[name] = {};\n      }\n      var value = base ? base[name] : undefined;\n      if (context) {\n        return {context: base, name: name, value: value};\n      } else {\n        return value;\n      }\n    };\n  },\n  computedMember: function(left, right, context, create) {\n    return function(scope, locals, assign, inputs) {\n      var lhs = left(scope, locals, assign, inputs);\n      var rhs;\n      var value;\n      if (lhs != null) {\n        rhs = right(scope, locals, assign, inputs);\n        rhs = getStringValue(rhs);\n        if (create && create !== 1) {\n          if (lhs && !(lhs[rhs])) {\n            lhs[rhs] = {};\n          }\n        }\n        value = lhs[rhs];\n      }\n      if (context) {\n        return {context: lhs, name: rhs, value: value};\n      } else {\n        return value;\n      }\n    };\n  },\n  nonComputedMember: function(left, right, context, create) {\n    return function(scope, locals, assign, inputs) {\n      var lhs = left(scope, locals, assign, inputs);\n      if (create && create !== 1) {\n        if (lhs && lhs[right] == null) {\n          lhs[right] = {};\n        }\n      }\n      var value = lhs != null ? lhs[right] : undefined;\n      if (context) {\n        return {context: lhs, name: right, value: value};\n      } else {\n        return value;\n      }\n    };\n  },\n  inputs: function(input, watchId) {\n    return function(scope, value, locals, inputs) {\n      if (inputs) return inputs[watchId];\n      return input(scope, value, locals);\n    };\n  }\n};\n\n/**\n * @constructor\n */\nfunction Parser(lexer, $filter, options) {\n  this.ast = new AST(lexer, options);\n  this.astCompiler = options.csp ? new ASTInterpreter($filter) :\n                                   new ASTCompiler($filter);\n}\n\nParser.prototype = {\n  constructor: Parser,\n\n  parse: function(text) {\n    var ast = this.getAst(text);\n    var fn = this.astCompiler.compile(ast.ast);\n    fn.literal = isLiteral(ast.ast);\n    fn.constant = isConstant(ast.ast);\n    fn.oneTime = ast.oneTime;\n    return fn;\n  },\n\n  getAst: function(exp) {\n    var oneTime = false;\n    exp = exp.trim();\n\n    if (exp.charAt(0) === ':' && exp.charAt(1) === ':') {\n      oneTime = true;\n      exp = exp.substring(2);\n    }\n    return {\n      ast: this.ast.ast(exp),\n      oneTime: oneTime\n    };\n  }\n};\n\nfunction getValueOf(value) {\n  return isFunction(value.valueOf) ? value.valueOf() : objectValueOf.call(value);\n}\n\n///////////////////////////////////\n\n/**\n * @ngdoc service\n * @name $parse\n * @kind function\n *\n * @description\n *\n * Converts AngularJS {@link guide/expression expression} into a function.\n *\n * ```js\n *   var getter = $parse('user.name');\n *   var setter = getter.assign;\n *   var context = {user:{name:'AngularJS'}};\n *   var locals = {user:{name:'local'}};\n *\n *   expect(getter(context)).toEqual('AngularJS');\n *   setter(context, 'newValue');\n *   expect(context.user.name).toEqual('newValue');\n *   expect(getter(context, locals)).toEqual('local');\n * ```\n *\n *\n * @param {string} expression String expression to compile.\n * @returns {function(context, locals)} a function which represents the compiled expression:\n *\n *    * `context` – `{object}` – an object against which any expressions embedded in the strings\n *      are evaluated against (typically a scope object).\n *    * `locals` – `{object=}` – local variables context object, useful for overriding values in\n *      `context`.\n *\n *    The returned function also has the following properties:\n *      * `literal` – `{boolean}` – whether the expression's top-level node is a JavaScript\n *        literal.\n *      * `constant` – `{boolean}` – whether the expression is made entirely of JavaScript\n *        constant literals.\n *      * `assign` – `{?function(context, value)}` – if the expression is assignable, this will be\n *        set to a function to change its value on the given context.\n *\n */\n\n\n/**\n * @ngdoc provider\n * @name $parseProvider\n * @this\n *\n * @description\n * `$parseProvider` can be used for configuring the default behavior of the {@link ng.$parse $parse}\n *  service.\n */\nfunction $ParseProvider() {\n  var cache = createMap();\n  var literals = {\n    'true': true,\n    'false': false,\n    'null': null,\n    'undefined': undefined\n  };\n  var identStart, identContinue;\n\n  /**\n   * @ngdoc method\n   * @name $parseProvider#addLiteral\n   * @description\n   *\n   * Configure $parse service to add literal values that will be present as literal at expressions.\n   *\n   * @param {string} literalName Token for the literal value. The literal name value must be a valid literal name.\n   * @param {*} literalValue Value for this literal. All literal values must be primitives or `undefined`.\n   *\n   **/\n  this.addLiteral = function(literalName, literalValue) {\n    literals[literalName] = literalValue;\n  };\n\n /**\n  * @ngdoc method\n  * @name $parseProvider#setIdentifierFns\n  *\n  * @description\n  *\n  * Allows defining the set of characters that are allowed in AngularJS expressions. The function\n  * `identifierStart` will get called to know if a given character is a valid character to be the\n  * first character for an identifier. The function `identifierContinue` will get called to know if\n  * a given character is a valid character to be a follow-up identifier character. The functions\n  * `identifierStart` and `identifierContinue` will receive as arguments the single character to be\n  * identifier and the character code point. These arguments will be `string` and `numeric`. Keep in\n  * mind that the `string` parameter can be two characters long depending on the character\n  * representation. It is expected for the function to return `true` or `false`, whether that\n  * character is allowed or not.\n  *\n  * Since this function will be called extensively, keep the implementation of these functions fast,\n  * as the performance of these functions have a direct impact on the expressions parsing speed.\n  *\n  * @param {function=} identifierStart The function that will decide whether the given character is\n  *   a valid identifier start character.\n  * @param {function=} identifierContinue The function that will decide whether the given character is\n  *   a valid identifier continue character.\n  */\n  this.setIdentifierFns = function(identifierStart, identifierContinue) {\n    identStart = identifierStart;\n    identContinue = identifierContinue;\n    return this;\n  };\n\n  this.$get = ['$filter', function($filter) {\n    var noUnsafeEval = csp().noUnsafeEval;\n    var $parseOptions = {\n          csp: noUnsafeEval,\n          literals: copy(literals),\n          isIdentifierStart: isFunction(identStart) && identStart,\n          isIdentifierContinue: isFunction(identContinue) && identContinue\n        };\n    $parse.$$getAst = $$getAst;\n    return $parse;\n\n    function $parse(exp, interceptorFn) {\n      var parsedExpression, cacheKey;\n\n      switch (typeof exp) {\n        case 'string':\n          exp = exp.trim();\n          cacheKey = exp;\n\n          parsedExpression = cache[cacheKey];\n\n          if (!parsedExpression) {\n            var lexer = new Lexer($parseOptions);\n            var parser = new Parser(lexer, $filter, $parseOptions);\n            parsedExpression = parser.parse(exp);\n\n            cache[cacheKey] = addWatchDelegate(parsedExpression);\n          }\n          return addInterceptor(parsedExpression, interceptorFn);\n\n        case 'function':\n          return addInterceptor(exp, interceptorFn);\n\n        default:\n          return addInterceptor(noop, interceptorFn);\n      }\n    }\n\n    function $$getAst(exp) {\n      var lexer = new Lexer($parseOptions);\n      var parser = new Parser(lexer, $filter, $parseOptions);\n      return parser.getAst(exp).ast;\n    }\n\n    function expressionInputDirtyCheck(newValue, oldValueOfValue, compareObjectIdentity) {\n\n      if (newValue == null || oldValueOfValue == null) { // null/undefined\n        return newValue === oldValueOfValue;\n      }\n\n      if (typeof newValue === 'object') {\n\n        // attempt to convert the value to a primitive type\n        // TODO(docs): add a note to docs that by implementing valueOf even objects and arrays can\n        //             be cheaply dirty-checked\n        newValue = getValueOf(newValue);\n\n        if (typeof newValue === 'object' && !compareObjectIdentity) {\n          // objects/arrays are not supported - deep-watching them would be too expensive\n          return false;\n        }\n\n        // fall-through to the primitive equality check\n      }\n\n      //Primitive or NaN\n      // eslint-disable-next-line no-self-compare\n      return newValue === oldValueOfValue || (newValue !== newValue && oldValueOfValue !== oldValueOfValue);\n    }\n\n    function inputsWatchDelegate(scope, listener, objectEquality, parsedExpression, prettyPrintExpression) {\n      var inputExpressions = parsedExpression.inputs;\n      var lastResult;\n\n      if (inputExpressions.length === 1) {\n        var oldInputValueOf = expressionInputDirtyCheck; // init to something unique so that equals check fails\n        inputExpressions = inputExpressions[0];\n        return scope.$watch(function expressionInputWatch(scope) {\n          var newInputValue = inputExpressions(scope);\n          if (!expressionInputDirtyCheck(newInputValue, oldInputValueOf, inputExpressions.isPure)) {\n            lastResult = parsedExpression(scope, undefined, undefined, [newInputValue]);\n            oldInputValueOf = newInputValue && getValueOf(newInputValue);\n          }\n          return lastResult;\n        }, listener, objectEquality, prettyPrintExpression);\n      }\n\n      var oldInputValueOfValues = [];\n      var oldInputValues = [];\n      for (var i = 0, ii = inputExpressions.length; i < ii; i++) {\n        oldInputValueOfValues[i] = expressionInputDirtyCheck; // init to something unique so that equals check fails\n        oldInputValues[i] = null;\n      }\n\n      return scope.$watch(function expressionInputsWatch(scope) {\n        var changed = false;\n\n        for (var i = 0, ii = inputExpressions.length; i < ii; i++) {\n          var newInputValue = inputExpressions[i](scope);\n          if (changed || (changed = !expressionInputDirtyCheck(newInputValue, oldInputValueOfValues[i], inputExpressions[i].isPure))) {\n            oldInputValues[i] = newInputValue;\n            oldInputValueOfValues[i] = newInputValue && getValueOf(newInputValue);\n          }\n        }\n\n        if (changed) {\n          lastResult = parsedExpression(scope, undefined, undefined, oldInputValues);\n        }\n\n        return lastResult;\n      }, listener, objectEquality, prettyPrintExpression);\n    }\n\n    function oneTimeWatchDelegate(scope, listener, objectEquality, parsedExpression, prettyPrintExpression) {\n      var isDone = parsedExpression.literal ? isAllDefined : isDefined;\n      var unwatch, lastValue;\n\n      var exp = parsedExpression.$$intercepted || parsedExpression;\n      var post = parsedExpression.$$interceptor || identity;\n\n      var useInputs = parsedExpression.inputs && !exp.inputs;\n\n      // Propagate the literal/inputs/constant attributes\n      // ... but not oneTime since we are handling it\n      oneTimeWatch.literal = parsedExpression.literal;\n      oneTimeWatch.constant = parsedExpression.constant;\n      oneTimeWatch.inputs = parsedExpression.inputs;\n\n      // Allow other delegates to run on this wrapped expression\n      addWatchDelegate(oneTimeWatch);\n\n      unwatch = scope.$watch(oneTimeWatch, listener, objectEquality, prettyPrintExpression);\n\n      return unwatch;\n\n      function unwatchIfDone() {\n        if (isDone(lastValue)) {\n          unwatch();\n        }\n      }\n\n      function oneTimeWatch(scope, locals, assign, inputs) {\n        lastValue = useInputs && inputs ? inputs[0] : exp(scope, locals, assign, inputs);\n        if (isDone(lastValue)) {\n          scope.$$postDigest(unwatchIfDone);\n        }\n        return post(lastValue);\n      }\n    }\n\n    function isAllDefined(value) {\n      var allDefined = true;\n      forEach(value, function(val) {\n        if (!isDefined(val)) allDefined = false;\n      });\n      return allDefined;\n    }\n\n    function constantWatchDelegate(scope, listener, objectEquality, parsedExpression) {\n      var unwatch = scope.$watch(function constantWatch(scope) {\n        unwatch();\n        return parsedExpression(scope);\n      }, listener, objectEquality);\n      return unwatch;\n    }\n\n    function addWatchDelegate(parsedExpression) {\n      if (parsedExpression.constant) {\n        parsedExpression.$$watchDelegate = constantWatchDelegate;\n      } else if (parsedExpression.oneTime) {\n        parsedExpression.$$watchDelegate = oneTimeWatchDelegate;\n      } else if (parsedExpression.inputs) {\n        parsedExpression.$$watchDelegate = inputsWatchDelegate;\n      }\n\n      return parsedExpression;\n    }\n\n    function chainInterceptors(first, second) {\n      function chainedInterceptor(value) {\n        return second(first(value));\n      }\n      chainedInterceptor.$stateful = first.$stateful || second.$stateful;\n      chainedInterceptor.$$pure = first.$$pure && second.$$pure;\n\n      return chainedInterceptor;\n    }\n\n    function addInterceptor(parsedExpression, interceptorFn) {\n      if (!interceptorFn) return parsedExpression;\n\n      // Extract any existing interceptors out of the parsedExpression\n      // to ensure the original parsedExpression is always the $$intercepted\n      if (parsedExpression.$$interceptor) {\n        interceptorFn = chainInterceptors(parsedExpression.$$interceptor, interceptorFn);\n        parsedExpression = parsedExpression.$$intercepted;\n      }\n\n      var useInputs = false;\n\n      var fn = function interceptedExpression(scope, locals, assign, inputs) {\n        var value = useInputs && inputs ? inputs[0] : parsedExpression(scope, locals, assign, inputs);\n        return interceptorFn(value);\n      };\n\n      // Maintain references to the interceptor/intercepted\n      fn.$$intercepted = parsedExpression;\n      fn.$$interceptor = interceptorFn;\n\n      // Propagate the literal/oneTime/constant attributes\n      fn.literal = parsedExpression.literal;\n      fn.oneTime = parsedExpression.oneTime;\n      fn.constant = parsedExpression.constant;\n\n      // Treat the interceptor like filters.\n      // If it is not $stateful then only watch its inputs.\n      // If the expression itself has no inputs then use the full expression as an input.\n      if (!interceptorFn.$stateful) {\n        useInputs = !parsedExpression.inputs;\n        fn.inputs = parsedExpression.inputs ? parsedExpression.inputs : [parsedExpression];\n\n        if (!interceptorFn.$$pure) {\n          fn.inputs = fn.inputs.map(function(e) {\n              // Remove the isPure flag of inputs when it is not absolute because they are now wrapped in a\n              // non-pure interceptor function.\n              if (e.isPure === PURITY_RELATIVE) {\n                return function depurifier(s) { return e(s); };\n              }\n              return e;\n            });\n        }\n      }\n\n      return addWatchDelegate(fn);\n    }\n  }];\n}\n\n/**\n * @ngdoc service\n * @name $q\n * @requires $rootScope\n *\n * @description\n * A service that helps you run functions asynchronously, and use their return values (or exceptions)\n * when they are done processing.\n *\n * This is a [Promises/A+](https://promisesaplus.com/)-compliant implementation of promises/deferred\n * objects inspired by [Kris Kowal's Q](https://github.com/kriskowal/q).\n *\n * $q can be used in two fashions --- one which is more similar to Kris Kowal's Q or jQuery's Deferred\n * implementations, and the other which resembles ES6 (ES2015) promises to some degree.\n *\n * ## $q constructor\n *\n * The streamlined ES6 style promise is essentially just using $q as a constructor which takes a `resolver`\n * function as the first argument. This is similar to the native Promise implementation from ES6,\n * see [MDN](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Promise).\n *\n * While the constructor-style use is supported, not all of the supporting methods from ES6 promises are\n * available yet.\n *\n * It can be used like so:\n *\n * ```js\n *   // for the purpose of this example let's assume that variables `$q` and `okToGreet`\n *   // are available in the current lexical scope (they could have been injected or passed in).\n *\n *   function asyncGreet(name) {\n *     // perform some asynchronous operation, resolve or reject the promise when appropriate.\n *     return $q(function(resolve, reject) {\n *       setTimeout(function() {\n *         if (okToGreet(name)) {\n *           resolve('Hello, ' + name + '!');\n *         } else {\n *           reject('Greeting ' + name + ' is not allowed.');\n *         }\n *       }, 1000);\n *     });\n *   }\n *\n *   var promise = asyncGreet('Robin Hood');\n *   promise.then(function(greeting) {\n *     alert('Success: ' + greeting);\n *   }, function(reason) {\n *     alert('Failed: ' + reason);\n *   });\n * ```\n *\n * Note: progress/notify callbacks are not currently supported via the ES6-style interface.\n *\n * Note: unlike ES6 behavior, an exception thrown in the constructor function will NOT implicitly reject the promise.\n *\n * However, the more traditional CommonJS-style usage is still available, and documented below.\n *\n * [The CommonJS Promise proposal](http://wiki.commonjs.org/wiki/Promises) describes a promise as an\n * interface for interacting with an object that represents the result of an action that is\n * performed asynchronously, and may or may not be finished at any given point in time.\n *\n * From the perspective of dealing with error handling, deferred and promise APIs are to\n * asynchronous programming what `try`, `catch` and `throw` keywords are to synchronous programming.\n *\n * ```js\n *   // for the purpose of this example let's assume that variables `$q` and `okToGreet`\n *   // are available in the current lexical scope (they could have been injected or passed in).\n *\n *   function asyncGreet(name) {\n *     var deferred = $q.defer();\n *\n *     setTimeout(function() {\n *       deferred.notify('About to greet ' + name + '.');\n *\n *       if (okToGreet(name)) {\n *         deferred.resolve('Hello, ' + name + '!');\n *       } else {\n *         deferred.reject('Greeting ' + name + ' is not allowed.');\n *       }\n *     }, 1000);\n *\n *     return deferred.promise;\n *   }\n *\n *   var promise = asyncGreet('Robin Hood');\n *   promise.then(function(greeting) {\n *     alert('Success: ' + greeting);\n *   }, function(reason) {\n *     alert('Failed: ' + reason);\n *   }, function(update) {\n *     alert('Got notification: ' + update);\n *   });\n * ```\n *\n * At first it might not be obvious why this extra complexity is worth the trouble. The payoff\n * comes in the way of guarantees that promise and deferred APIs make, see\n * https://github.com/kriskowal/uncommonjs/blob/master/promises/specification.md.\n *\n * Additionally the promise api allows for composition that is very hard to do with the\n * traditional callback ([CPS](http://en.wikipedia.org/wiki/Continuation-passing_style)) approach.\n * For more on this please see the [Q documentation](https://github.com/kriskowal/q) especially the\n * section on serial or parallel joining of promises.\n *\n * ## The Deferred API\n *\n * A new instance of deferred is constructed by calling `$q.defer()`.\n *\n * The purpose of the deferred object is to expose the associated Promise instance as well as APIs\n * that can be used for signaling the successful or unsuccessful completion, as well as the status\n * of the task.\n *\n * **Methods**\n *\n * - `resolve(value)` – resolves the derived promise with the `value`. If the value is a rejection\n *   constructed via `$q.reject`, the promise will be rejected instead.\n * - `reject(reason)` – rejects the derived promise with the `reason`. This is equivalent to\n *   resolving it with a rejection constructed via `$q.reject`.\n * - `notify(value)` - provides updates on the status of the promise's execution. This may be called\n *   multiple times before the promise is either resolved or rejected.\n *\n * **Properties**\n *\n * - promise – `{Promise}` – promise object associated with this deferred.\n *\n *\n * ## The Promise API\n *\n * A new promise instance is created when a deferred instance is created and can be retrieved by\n * calling `deferred.promise`.\n *\n * The purpose of the promise object is to allow for interested parties to get access to the result\n * of the deferred task when it completes.\n *\n * **Methods**\n *\n * - `then(successCallback, [errorCallback], [notifyCallback])` – regardless of when the promise was or\n *   will be resolved or rejected, `then` calls one of the success or error callbacks asynchronously\n *   as soon as the result is available. The callbacks are called with a single argument: the result\n *   or rejection reason. Additionally, the notify callback may be called zero or more times to\n *   provide a progress indication, before the promise is resolved or rejected.\n *\n *   This method *returns a new promise* which is resolved or rejected via the return value of the\n *   `successCallback`, `errorCallback` (unless that value is a promise, in which case it is resolved\n *   with the value which is resolved in that promise using\n *   [promise chaining](http://www.html5rocks.com/en/tutorials/es6/promises/#toc-promises-queues)).\n *   It also notifies via the return value of the `notifyCallback` method. The promise cannot be\n *   resolved or rejected from the notifyCallback method. The errorCallback and notifyCallback\n *   arguments are optional.\n *\n * - `catch(errorCallback)` – shorthand for `promise.then(null, errorCallback)`\n *\n * - `finally(callback, notifyCallback)` – allows you to observe either the fulfillment or rejection of a promise,\n *   but to do so without modifying the final value. This is useful to release resources or do some\n *   clean-up that needs to be done whether the promise was rejected or resolved. See the [full\n *   specification](https://github.com/kriskowal/q/wiki/API-Reference#promisefinallycallback) for\n *   more information.\n *\n * ## Chaining promises\n *\n * Because calling the `then` method of a promise returns a new derived promise, it is easily\n * possible to create a chain of promises:\n *\n * ```js\n *   promiseB = promiseA.then(function(result) {\n *     return result + 1;\n *   });\n *\n *   // promiseB will be resolved immediately after promiseA is resolved and its value\n *   // will be the result of promiseA incremented by 1\n * ```\n *\n * It is possible to create chains of any length and since a promise can be resolved with another\n * promise (which will defer its resolution further), it is possible to pause/defer resolution of\n * the promises at any point in the chain. This makes it possible to implement powerful APIs like\n * $http's response interceptors.\n *\n *\n * ## Differences between Kris Kowal's Q and $q\n *\n *  There are two main differences:\n *\n * - $q is integrated with the {@link ng.$rootScope.Scope} Scope model observation\n *   mechanism in AngularJS, which means faster propagation of resolution or rejection into your\n *   models and avoiding unnecessary browser repaints, which would result in flickering UI.\n * - Q has many more features than $q, but that comes at a cost of bytes. $q is tiny, but contains\n *   all the important functionality needed for common async tasks.\n *\n * ## Testing\n *\n *  ```js\n *    it('should simulate promise', inject(function($q, $rootScope) {\n *      var deferred = $q.defer();\n *      var promise = deferred.promise;\n *      var resolvedValue;\n *\n *      promise.then(function(value) { resolvedValue = value; });\n *      expect(resolvedValue).toBeUndefined();\n *\n *      // Simulate resolving of promise\n *      deferred.resolve(123);\n *      // Note that the 'then' function does not get called synchronously.\n *      // This is because we want the promise API to always be async, whether or not\n *      // it got called synchronously or asynchronously.\n *      expect(resolvedValue).toBeUndefined();\n *\n *      // Propagate promise resolution to 'then' functions using $apply().\n *      $rootScope.$apply();\n *      expect(resolvedValue).toEqual(123);\n *    }));\n *  ```\n *\n * @param {function(function, function)} resolver Function which is responsible for resolving or\n *   rejecting the newly created promise. The first parameter is a function which resolves the\n *   promise, the second parameter is a function which rejects the promise.\n *\n * @returns {Promise} The newly created promise.\n */\n/**\n * @ngdoc provider\n * @name $qProvider\n * @this\n *\n * @description\n */\nfunction $QProvider() {\n  var errorOnUnhandledRejections = true;\n  this.$get = ['$rootScope', '$exceptionHandler', function($rootScope, $exceptionHandler) {\n    return qFactory(function(callback) {\n      $rootScope.$evalAsync(callback);\n    }, $exceptionHandler, errorOnUnhandledRejections);\n  }];\n\n  /**\n   * @ngdoc method\n   * @name $qProvider#errorOnUnhandledRejections\n   * @kind function\n   *\n   * @description\n   * Retrieves or overrides whether to generate an error when a rejected promise is not handled.\n   * This feature is enabled by default.\n   *\n   * @param {boolean=} value Whether to generate an error when a rejected promise is not handled.\n   * @returns {boolean|ng.$qProvider} Current value when called without a new value or self for\n   *    chaining otherwise.\n   */\n  this.errorOnUnhandledRejections = function(value) {\n    if (isDefined(value)) {\n      errorOnUnhandledRejections = value;\n      return this;\n    } else {\n      return errorOnUnhandledRejections;\n    }\n  };\n}\n\n/** @this */\nfunction $$QProvider() {\n  var errorOnUnhandledRejections = true;\n  this.$get = ['$browser', '$exceptionHandler', function($browser, $exceptionHandler) {\n    return qFactory(function(callback) {\n      $browser.defer(callback);\n    }, $exceptionHandler, errorOnUnhandledRejections);\n  }];\n\n  this.errorOnUnhandledRejections = function(value) {\n    if (isDefined(value)) {\n      errorOnUnhandledRejections = value;\n      return this;\n    } else {\n      return errorOnUnhandledRejections;\n    }\n  };\n}\n\n/**\n * Constructs a promise manager.\n *\n * @param {function(function)} nextTick Function for executing functions in the next turn.\n * @param {function(...*)} exceptionHandler Function into which unexpected exceptions are passed for\n *     debugging purposes.\n * @param {boolean=} errorOnUnhandledRejections Whether an error should be generated on unhandled\n *     promises rejections.\n * @returns {object} Promise manager.\n */\nfunction qFactory(nextTick, exceptionHandler, errorOnUnhandledRejections) {\n  var $qMinErr = minErr('$q', TypeError);\n  var queueSize = 0;\n  var checkQueue = [];\n\n  /**\n   * @ngdoc method\n   * @name ng.$q#defer\n   * @kind function\n   *\n   * @description\n   * Creates a `Deferred` object which represents a task which will finish in the future.\n   *\n   * @returns {Deferred} Returns a new instance of deferred.\n   */\n  function defer() {\n    return new Deferred();\n  }\n\n  function Deferred() {\n    var promise = this.promise = new Promise();\n    //Non prototype methods necessary to support unbound execution :/\n    this.resolve = function(val) { resolvePromise(promise, val); };\n    this.reject = function(reason) { rejectPromise(promise, reason); };\n    this.notify = function(progress) { notifyPromise(promise, progress); };\n  }\n\n\n  function Promise() {\n    this.$$state = { status: 0 };\n  }\n\n  extend(Promise.prototype, {\n    then: function(onFulfilled, onRejected, progressBack) {\n      if (isUndefined(onFulfilled) && isUndefined(onRejected) && isUndefined(progressBack)) {\n        return this;\n      }\n      var result = new Promise();\n\n      this.$$state.pending = this.$$state.pending || [];\n      this.$$state.pending.push([result, onFulfilled, onRejected, progressBack]);\n      if (this.$$state.status > 0) scheduleProcessQueue(this.$$state);\n\n      return result;\n    },\n\n    'catch': function(callback) {\n      return this.then(null, callback);\n    },\n\n    'finally': function(callback, progressBack) {\n      return this.then(function(value) {\n        return handleCallback(value, resolve, callback);\n      }, function(error) {\n        return handleCallback(error, reject, callback);\n      }, progressBack);\n    }\n  });\n\n  function processQueue(state) {\n    var fn, promise, pending;\n\n    pending = state.pending;\n    state.processScheduled = false;\n    state.pending = undefined;\n    try {\n      for (var i = 0, ii = pending.length; i < ii; ++i) {\n        markQStateExceptionHandled(state);\n        promise = pending[i][0];\n        fn = pending[i][state.status];\n        try {\n          if (isFunction(fn)) {\n            resolvePromise(promise, fn(state.value));\n          } else if (state.status === 1) {\n            resolvePromise(promise, state.value);\n          } else {\n            rejectPromise(promise, state.value);\n          }\n        } catch (e) {\n          rejectPromise(promise, e);\n          // This error is explicitly marked for being passed to the $exceptionHandler\n          if (e && e.$$passToExceptionHandler === true) {\n            exceptionHandler(e);\n          }\n        }\n      }\n    } finally {\n      --queueSize;\n      if (errorOnUnhandledRejections && queueSize === 0) {\n        nextTick(processChecks);\n      }\n    }\n  }\n\n  function processChecks() {\n    // eslint-disable-next-line no-unmodified-loop-condition\n    while (!queueSize && checkQueue.length) {\n      var toCheck = checkQueue.shift();\n      if (!isStateExceptionHandled(toCheck)) {\n        markQStateExceptionHandled(toCheck);\n        var errorMessage = 'Possibly unhandled rejection: ' + toDebugString(toCheck.value);\n        if (isError(toCheck.value)) {\n          exceptionHandler(toCheck.value, errorMessage);\n        } else {\n          exceptionHandler(errorMessage);\n        }\n      }\n    }\n  }\n\n  function scheduleProcessQueue(state) {\n    if (errorOnUnhandledRejections && !state.pending && state.status === 2 && !isStateExceptionHandled(state)) {\n      if (queueSize === 0 && checkQueue.length === 0) {\n        nextTick(processChecks);\n      }\n      checkQueue.push(state);\n    }\n    if (state.processScheduled || !state.pending) return;\n    state.processScheduled = true;\n    ++queueSize;\n    nextTick(function() { processQueue(state); });\n  }\n\n  function resolvePromise(promise, val) {\n    if (promise.$$state.status) return;\n    if (val === promise) {\n      $$reject(promise, $qMinErr(\n        'qcycle',\n        'Expected promise to be resolved with value other than itself \\'{0}\\'',\n        val));\n    } else {\n      $$resolve(promise, val);\n    }\n\n  }\n\n  function $$resolve(promise, val) {\n    var then;\n    var done = false;\n    try {\n      if (isObject(val) || isFunction(val)) then = val.then;\n      if (isFunction(then)) {\n        promise.$$state.status = -1;\n        then.call(val, doResolve, doReject, doNotify);\n      } else {\n        promise.$$state.value = val;\n        promise.$$state.status = 1;\n        scheduleProcessQueue(promise.$$state);\n      }\n    } catch (e) {\n      doReject(e);\n    }\n\n    function doResolve(val) {\n      if (done) return;\n      done = true;\n      $$resolve(promise, val);\n    }\n    function doReject(val) {\n      if (done) return;\n      done = true;\n      $$reject(promise, val);\n    }\n    function doNotify(progress) {\n      notifyPromise(promise, progress);\n    }\n  }\n\n  function rejectPromise(promise, reason) {\n    if (promise.$$state.status) return;\n    $$reject(promise, reason);\n  }\n\n  function $$reject(promise, reason) {\n    promise.$$state.value = reason;\n    promise.$$state.status = 2;\n    scheduleProcessQueue(promise.$$state);\n  }\n\n  function notifyPromise(promise, progress) {\n    var callbacks = promise.$$state.pending;\n\n    if ((promise.$$state.status <= 0) && callbacks && callbacks.length) {\n      nextTick(function() {\n        var callback, result;\n        for (var i = 0, ii = callbacks.length; i < ii; i++) {\n          result = callbacks[i][0];\n          callback = callbacks[i][3];\n          try {\n            notifyPromise(result, isFunction(callback) ? callback(progress) : progress);\n          } catch (e) {\n            exceptionHandler(e);\n          }\n        }\n      });\n    }\n  }\n\n  /**\n   * @ngdoc method\n   * @name $q#reject\n   * @kind function\n   *\n   * @description\n   * Creates a promise that is resolved as rejected with the specified `reason`. This api should be\n   * used to forward rejection in a chain of promises. If you are dealing with the last promise in\n   * a promise chain, you don't need to worry about it.\n   *\n   * When comparing deferreds/promises to the familiar behavior of try/catch/throw, think of\n   * `reject` as the `throw` keyword in JavaScript. This also means that if you \"catch\" an error via\n   * a promise error callback and you want to forward the error to the promise derived from the\n   * current promise, you have to \"rethrow\" the error by returning a rejection constructed via\n   * `reject`.\n   *\n   * ```js\n   *   promiseB = promiseA.then(function(result) {\n   *     // success: do something and resolve promiseB\n   *     //          with the old or a new result\n   *     return result;\n   *   }, function(reason) {\n   *     // error: handle the error if possible and\n   *     //        resolve promiseB with newPromiseOrValue,\n   *     //        otherwise forward the rejection to promiseB\n   *     if (canHandle(reason)) {\n   *      // handle the error and recover\n   *      return newPromiseOrValue;\n   *     }\n   *     return $q.reject(reason);\n   *   });\n   * ```\n   *\n   * @param {*} reason Constant, message, exception or an object representing the rejection reason.\n   * @returns {Promise} Returns a promise that was already resolved as rejected with the `reason`.\n   */\n  function reject(reason) {\n    var result = new Promise();\n    rejectPromise(result, reason);\n    return result;\n  }\n\n  function handleCallback(value, resolver, callback) {\n    var callbackOutput = null;\n    try {\n      if (isFunction(callback)) callbackOutput = callback();\n    } catch (e) {\n      return reject(e);\n    }\n    if (isPromiseLike(callbackOutput)) {\n      return callbackOutput.then(function() {\n        return resolver(value);\n      }, reject);\n    } else {\n      return resolver(value);\n    }\n  }\n\n  /**\n   * @ngdoc method\n   * @name $q#when\n   * @kind function\n   *\n   * @description\n   * Wraps an object that might be a value or a (3rd party) then-able promise into a $q promise.\n   * This is useful when you are dealing with an object that might or might not be a promise, or if\n   * the promise comes from a source that can't be trusted.\n   *\n   * @param {*} value Value or a promise\n   * @param {Function=} successCallback\n   * @param {Function=} errorCallback\n   * @param {Function=} progressCallback\n   * @returns {Promise} Returns a promise of the passed value or promise\n   */\n\n\n  function when(value, callback, errback, progressBack) {\n    var result = new Promise();\n    resolvePromise(result, value);\n    return result.then(callback, errback, progressBack);\n  }\n\n  /**\n   * @ngdoc method\n   * @name $q#resolve\n   * @kind function\n   *\n   * @description\n   * Alias of {@link ng.$q#when when} to maintain naming consistency with ES6.\n   *\n   * @param {*} value Value or a promise\n   * @param {Function=} successCallback\n   * @param {Function=} errorCallback\n   * @param {Function=} progressCallback\n   * @returns {Promise} Returns a promise of the passed value or promise\n   */\n  var resolve = when;\n\n  /**\n   * @ngdoc method\n   * @name $q#all\n   * @kind function\n   *\n   * @description\n   * Combines multiple promises into a single promise that is resolved when all of the input\n   * promises are resolved.\n   *\n   * @param {Array.<Promise>|Object.<Promise>} promises An array or hash of promises.\n   * @returns {Promise} Returns a single promise that will be resolved with an array/hash of values,\n   *   each value corresponding to the promise at the same index/key in the `promises` array/hash.\n   *   If any of the promises is resolved with a rejection, this resulting promise will be rejected\n   *   with the same rejection value.\n   */\n\n  function all(promises) {\n    var result = new Promise(),\n        counter = 0,\n        results = isArray(promises) ? [] : {};\n\n    forEach(promises, function(promise, key) {\n      counter++;\n      when(promise).then(function(value) {\n        results[key] = value;\n        if (!(--counter)) resolvePromise(result, results);\n      }, function(reason) {\n        rejectPromise(result, reason);\n      });\n    });\n\n    if (counter === 0) {\n      resolvePromise(result, results);\n    }\n\n    return result;\n  }\n\n  /**\n   * @ngdoc method\n   * @name $q#race\n   * @kind function\n   *\n   * @description\n   * Returns a promise that resolves or rejects as soon as one of those promises\n   * resolves or rejects, with the value or reason from that promise.\n   *\n   * @param {Array.<Promise>|Object.<Promise>} promises An array or hash of promises.\n   * @returns {Promise} a promise that resolves or rejects as soon as one of the `promises`\n   * resolves or rejects, with the value or reason from that promise.\n   */\n\n  function race(promises) {\n    var deferred = defer();\n\n    forEach(promises, function(promise) {\n      when(promise).then(deferred.resolve, deferred.reject);\n    });\n\n    return deferred.promise;\n  }\n\n  function $Q(resolver) {\n    if (!isFunction(resolver)) {\n      throw $qMinErr('norslvr', 'Expected resolverFn, got \\'{0}\\'', resolver);\n    }\n\n    var promise = new Promise();\n\n    function resolveFn(value) {\n      resolvePromise(promise, value);\n    }\n\n    function rejectFn(reason) {\n      rejectPromise(promise, reason);\n    }\n\n    resolver(resolveFn, rejectFn);\n\n    return promise;\n  }\n\n  // Let's make the instanceof operator work for promises, so that\n  // `new $q(fn) instanceof $q` would evaluate to true.\n  $Q.prototype = Promise.prototype;\n\n  $Q.defer = defer;\n  $Q.reject = reject;\n  $Q.when = when;\n  $Q.resolve = resolve;\n  $Q.all = all;\n  $Q.race = race;\n\n  return $Q;\n}\n\nfunction isStateExceptionHandled(state) {\n  return !!state.pur;\n}\nfunction markQStateExceptionHandled(state) {\n  state.pur = true;\n}\nfunction markQExceptionHandled(q) {\n  // Built-in `$q` promises will always have a `$$state` property. This check is to allow\n  // overwriting `$q` with a different promise library (e.g. Bluebird + angular-bluebird-promises).\n  // (Currently, this is the only method that might be called with a promise, even if it is not\n  // created by the built-in `$q`.)\n  if (q.$$state) {\n    markQStateExceptionHandled(q.$$state);\n  }\n}\n\n/** @this */\nfunction $$RAFProvider() { //rAF\n  this.$get = ['$window', '$timeout', function($window, $timeout) {\n    var requestAnimationFrame = $window.requestAnimationFrame ||\n                                $window.webkitRequestAnimationFrame;\n\n    var cancelAnimationFrame = $window.cancelAnimationFrame ||\n                               $window.webkitCancelAnimationFrame ||\n                               $window.webkitCancelRequestAnimationFrame;\n\n    var rafSupported = !!requestAnimationFrame;\n    var raf = rafSupported\n      ? function(fn) {\n          var id = requestAnimationFrame(fn);\n          return function() {\n            cancelAnimationFrame(id);\n          };\n        }\n      : function(fn) {\n          var timer = $timeout(fn, 16.66, false); // 1000 / 60 = 16.666\n          return function() {\n            $timeout.cancel(timer);\n          };\n        };\n\n    raf.supported = rafSupported;\n\n    return raf;\n  }];\n}\n\n/**\n * DESIGN NOTES\n *\n * The design decisions behind the scope are heavily favored for speed and memory consumption.\n *\n * The typical use of scope is to watch the expressions, which most of the time return the same\n * value as last time so we optimize the operation.\n *\n * Closures construction is expensive in terms of speed as well as memory:\n *   - No closures, instead use prototypical inheritance for API\n *   - Internal state needs to be stored on scope directly, which means that private state is\n *     exposed as $$____ properties\n *\n * Loop operations are optimized by using while(count--) { ... }\n *   - This means that in order to keep the same order of execution as addition we have to add\n *     items to the array at the beginning (unshift) instead of at the end (push)\n *\n * Child scopes are created and removed often\n *   - Using an array would be slow since inserts in the middle are expensive; so we use linked lists\n *\n * There are fewer watches than observers. This is why you don't want the observer to be implemented\n * in the same way as watch. Watch requires return of the initialization function which is expensive\n * to construct.\n */\n\n\n/**\n * @ngdoc provider\n * @name $rootScopeProvider\n * @description\n *\n * Provider for the $rootScope service.\n */\n\n/**\n * @ngdoc method\n * @name $rootScopeProvider#digestTtl\n * @description\n *\n * Sets the number of `$digest` iterations the scope should attempt to execute before giving up and\n * assuming that the model is unstable.\n *\n * The current default is 10 iterations.\n *\n * In complex applications it's possible that the dependencies between `$watch`s will result in\n * several digest iterations. However if an application needs more than the default 10 digest\n * iterations for its model to stabilize then you should investigate what is causing the model to\n * continuously change during the digest.\n *\n * Increasing the TTL could have performance implications, so you should not change it without\n * proper justification.\n *\n * @param {number} limit The number of digest iterations.\n */\n\n\n/**\n * @ngdoc service\n * @name $rootScope\n * @this\n *\n * @description\n *\n * Every application has a single root {@link ng.$rootScope.Scope scope}.\n * All other scopes are descendant scopes of the root scope. Scopes provide separation\n * between the model and the view, via a mechanism for watching the model for changes.\n * They also provide event emission/broadcast and subscription facility. See the\n * {@link guide/scope developer guide on scopes}.\n */\nfunction $RootScopeProvider() {\n  var TTL = 10;\n  var $rootScopeMinErr = minErr('$rootScope');\n  var lastDirtyWatch = null;\n  var applyAsyncId = null;\n\n  this.digestTtl = function(value) {\n    if (arguments.length) {\n      TTL = value;\n    }\n    return TTL;\n  };\n\n  function createChildScopeClass(parent) {\n    function ChildScope() {\n      this.$$watchers = this.$$nextSibling =\n          this.$$childHead = this.$$childTail = null;\n      this.$$listeners = {};\n      this.$$listenerCount = {};\n      this.$$watchersCount = 0;\n      this.$id = nextUid();\n      this.$$ChildScope = null;\n      this.$$suspended = false;\n    }\n    ChildScope.prototype = parent;\n    return ChildScope;\n  }\n\n  this.$get = ['$exceptionHandler', '$parse', '$browser',\n      function($exceptionHandler, $parse, $browser) {\n\n    function destroyChildScope($event) {\n        $event.currentScope.$$destroyed = true;\n    }\n\n    function cleanUpScope($scope) {\n\n      // Support: IE 9 only\n      if (msie === 9) {\n        // There is a memory leak in IE9 if all child scopes are not disconnected\n        // completely when a scope is destroyed. So this code will recurse up through\n        // all this scopes children\n        //\n        // See issue https://github.com/angular/angular.js/issues/10706\n        if ($scope.$$childHead) {\n          cleanUpScope($scope.$$childHead);\n        }\n        if ($scope.$$nextSibling) {\n          cleanUpScope($scope.$$nextSibling);\n        }\n      }\n\n      // The code below works around IE9 and V8's memory leaks\n      //\n      // See:\n      // - https://code.google.com/p/v8/issues/detail?id=2073#c26\n      // - https://github.com/angular/angular.js/issues/6794#issuecomment-38648909\n      // - https://github.com/angular/angular.js/issues/1313#issuecomment-10378451\n\n      $scope.$parent = $scope.$$nextSibling = $scope.$$prevSibling = $scope.$$childHead =\n          $scope.$$childTail = $scope.$root = $scope.$$watchers = null;\n    }\n\n    /**\n     * @ngdoc type\n     * @name $rootScope.Scope\n     *\n     * @description\n     * A root scope can be retrieved using the {@link ng.$rootScope $rootScope} key from the\n     * {@link auto.$injector $injector}. Child scopes are created using the\n     * {@link ng.$rootScope.Scope#$new $new()} method. (Most scopes are created automatically when\n     * compiled HTML template is executed.) See also the {@link guide/scope Scopes guide} for\n     * an in-depth introduction and usage examples.\n     *\n     *\n     * ## Inheritance\n     * A scope can inherit from a parent scope, as in this example:\n     * ```js\n         var parent = $rootScope;\n         var child = parent.$new();\n\n         parent.salutation = \"Hello\";\n         expect(child.salutation).toEqual('Hello');\n\n         child.salutation = \"Welcome\";\n         expect(child.salutation).toEqual('Welcome');\n         expect(parent.salutation).toEqual('Hello');\n     * ```\n     *\n     * When interacting with `Scope` in tests, additional helper methods are available on the\n     * instances of `Scope` type. See {@link ngMock.$rootScope.Scope ngMock Scope} for additional\n     * details.\n     *\n     *\n     * @param {Object.<string, function()>=} providers Map of service factory which need to be\n     *                                       provided for the current scope. Defaults to {@link ng}.\n     * @param {Object.<string, *>=} instanceCache Provides pre-instantiated services which should\n     *                              append/override services provided by `providers`. This is handy\n     *                              when unit-testing and having the need to override a default\n     *                              service.\n     * @returns {Object} Newly created scope.\n     *\n     */\n    function Scope() {\n      this.$id = nextUid();\n      this.$$phase = this.$parent = this.$$watchers =\n                     this.$$nextSibling = this.$$prevSibling =\n                     this.$$childHead = this.$$childTail = null;\n      this.$root = this;\n      this.$$destroyed = false;\n      this.$$suspended = false;\n      this.$$listeners = {};\n      this.$$listenerCount = {};\n      this.$$watchersCount = 0;\n      this.$$isolateBindings = null;\n    }\n\n    /**\n     * @ngdoc property\n     * @name $rootScope.Scope#$id\n     *\n     * @description\n     * Unique scope ID (monotonically increasing) useful for debugging.\n     */\n\n     /**\n      * @ngdoc property\n      * @name $rootScope.Scope#$parent\n      *\n      * @description\n      * Reference to the parent scope.\n      */\n\n      /**\n       * @ngdoc property\n       * @name $rootScope.Scope#$root\n       *\n       * @description\n       * Reference to the root scope.\n       */\n\n    Scope.prototype = {\n      constructor: Scope,\n      /**\n       * @ngdoc method\n       * @name $rootScope.Scope#$new\n       * @kind function\n       *\n       * @description\n       * Creates a new child {@link ng.$rootScope.Scope scope}.\n       *\n       * The parent scope will propagate the {@link ng.$rootScope.Scope#$digest $digest()} event.\n       * The scope can be removed from the scope hierarchy using {@link ng.$rootScope.Scope#$destroy $destroy()}.\n       *\n       * {@link ng.$rootScope.Scope#$destroy $destroy()} must be called on a scope when it is\n       * desired for the scope and its child scopes to be permanently detached from the parent and\n       * thus stop participating in model change detection and listener notification by invoking.\n       *\n       * @param {boolean} isolate If true, then the scope does not prototypically inherit from the\n       *         parent scope. The scope is isolated, as it can not see parent scope properties.\n       *         When creating widgets, it is useful for the widget to not accidentally read parent\n       *         state.\n       *\n       * @param {Scope} [parent=this] The {@link ng.$rootScope.Scope `Scope`} that will be the `$parent`\n       *                              of the newly created scope. Defaults to `this` scope if not provided.\n       *                              This is used when creating a transclude scope to correctly place it\n       *                              in the scope hierarchy while maintaining the correct prototypical\n       *                              inheritance.\n       *\n       * @returns {Object} The newly created child scope.\n       *\n       */\n      $new: function(isolate, parent) {\n        var child;\n\n        parent = parent || this;\n\n        if (isolate) {\n          child = new Scope();\n          child.$root = this.$root;\n        } else {\n          // Only create a child scope class if somebody asks for one,\n          // but cache it to allow the VM to optimize lookups.\n          if (!this.$$ChildScope) {\n            this.$$ChildScope = createChildScopeClass(this);\n          }\n          child = new this.$$ChildScope();\n        }\n        child.$parent = parent;\n        child.$$prevSibling = parent.$$childTail;\n        if (parent.$$childHead) {\n          parent.$$childTail.$$nextSibling = child;\n          parent.$$childTail = child;\n        } else {\n          parent.$$childHead = parent.$$childTail = child;\n        }\n\n        // When the new scope is not isolated or we inherit from `this`, and\n        // the parent scope is destroyed, the property `$$destroyed` is inherited\n        // prototypically. In all other cases, this property needs to be set\n        // when the parent scope is destroyed.\n        // The listener needs to be added after the parent is set\n        if (isolate || parent !== this) child.$on('$destroy', destroyChildScope);\n\n        return child;\n      },\n\n      /**\n       * @ngdoc method\n       * @name $rootScope.Scope#$watch\n       * @kind function\n       *\n       * @description\n       * Registers a `listener` callback to be executed whenever the `watchExpression` changes.\n       *\n       * - The `watchExpression` is called on every call to {@link ng.$rootScope.Scope#$digest\n       *   $digest()} and should return the value that will be watched. (`watchExpression` should not change\n       *   its value when executed multiple times with the same input because it may be executed multiple\n       *   times by {@link ng.$rootScope.Scope#$digest $digest()}. That is, `watchExpression` should be\n       *   [idempotent](http://en.wikipedia.org/wiki/Idempotence).)\n       * - The `listener` is called only when the value from the current `watchExpression` and the\n       *   previous call to `watchExpression` are not equal (with the exception of the initial run,\n       *   see below). Inequality is determined according to reference inequality,\n       *   [strict comparison](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/Comparison_Operators)\n       *    via the `!==` Javascript operator, unless `objectEquality == true`\n       *   (see next point)\n       * - When `objectEquality == true`, inequality of the `watchExpression` is determined\n       *   according to the {@link angular.equals} function. To save the value of the object for\n       *   later comparison, the {@link angular.copy} function is used. This therefore means that\n       *   watching complex objects will have adverse memory and performance implications.\n       * - This should not be used to watch for changes in objects that are (or contain)\n       *   [File](https://developer.mozilla.org/docs/Web/API/File) objects due to limitations with {@link angular.copy `angular.copy`}.\n       * - The watch `listener` may change the model, which may trigger other `listener`s to fire.\n       *   This is achieved by rerunning the watchers until no changes are detected. The rerun\n       *   iteration limit is 10 to prevent an infinite loop deadlock.\n       *\n       *\n       * If you want to be notified whenever {@link ng.$rootScope.Scope#$digest $digest} is called,\n       * you can register a `watchExpression` function with no `listener`. (Be prepared for\n       * multiple calls to your `watchExpression` because it will execute multiple times in a\n       * single {@link ng.$rootScope.Scope#$digest $digest} cycle if a change is detected.)\n       *\n       * After a watcher is registered with the scope, the `listener` fn is called asynchronously\n       * (via {@link ng.$rootScope.Scope#$evalAsync $evalAsync}) to initialize the\n       * watcher. In rare cases, this is undesirable because the listener is called when the result\n       * of `watchExpression` didn't change. To detect this scenario within the `listener` fn, you\n       * can compare the `newVal` and `oldVal`. If these two values are identical (`===`) then the\n       * listener was called due to initialization.\n       *\n       *\n       *\n       * @example\n       * ```js\n           // let's assume that scope was dependency injected as the $rootScope\n           var scope = $rootScope;\n           scope.name = 'misko';\n           scope.counter = 0;\n\n           expect(scope.counter).toEqual(0);\n           scope.$watch('name', function(newValue, oldValue) {\n             scope.counter = scope.counter + 1;\n           });\n           expect(scope.counter).toEqual(0);\n\n           scope.$digest();\n           // the listener is always called during the first $digest loop after it was registered\n           expect(scope.counter).toEqual(1);\n\n           scope.$digest();\n           // but now it will not be called unless the value changes\n           expect(scope.counter).toEqual(1);\n\n           scope.name = 'adam';\n           scope.$digest();\n           expect(scope.counter).toEqual(2);\n\n\n\n           // Using a function as a watchExpression\n           var food;\n           scope.foodCounter = 0;\n           expect(scope.foodCounter).toEqual(0);\n           scope.$watch(\n             // This function returns the value being watched. It is called for each turn of the $digest loop\n             function() { return food; },\n             // This is the change listener, called when the value returned from the above function changes\n             function(newValue, oldValue) {\n               if ( newValue !== oldValue ) {\n                 // Only increment the counter if the value changed\n                 scope.foodCounter = scope.foodCounter + 1;\n               }\n             }\n           );\n           // No digest has been run so the counter will be zero\n           expect(scope.foodCounter).toEqual(0);\n\n           // Run the digest but since food has not changed count will still be zero\n           scope.$digest();\n           expect(scope.foodCounter).toEqual(0);\n\n           // Update food and run digest.  Now the counter will increment\n           food = 'cheeseburger';\n           scope.$digest();\n           expect(scope.foodCounter).toEqual(1);\n\n       * ```\n       *\n       *\n       *\n       * @param {(function()|string)} watchExpression Expression that is evaluated on each\n       *    {@link ng.$rootScope.Scope#$digest $digest} cycle. A change in the return value triggers\n       *    a call to the `listener`.\n       *\n       *    - `string`: Evaluated as {@link guide/expression expression}\n       *    - `function(scope)`: called with current `scope` as a parameter.\n       * @param {function(newVal, oldVal, scope)} listener Callback called whenever the value\n       *    of `watchExpression` changes.\n       *\n       *    - `newVal` contains the current value of the `watchExpression`\n       *    - `oldVal` contains the previous value of the `watchExpression`\n       *    - `scope` refers to the current scope\n       * @param {boolean=} [objectEquality=false] Compare for object equality using {@link angular.equals} instead of\n       *     comparing for reference equality.\n       * @returns {function()} Returns a deregistration function for this listener.\n       */\n      $watch: function(watchExp, listener, objectEquality, prettyPrintExpression) {\n        var get = $parse(watchExp);\n        var fn = isFunction(listener) ? listener : noop;\n\n        if (get.$$watchDelegate) {\n          return get.$$watchDelegate(this, fn, objectEquality, get, watchExp);\n        }\n        var scope = this,\n            array = scope.$$watchers,\n            watcher = {\n              fn: fn,\n              last: initWatchVal,\n              get: get,\n              exp: prettyPrintExpression || watchExp,\n              eq: !!objectEquality\n            };\n\n        lastDirtyWatch = null;\n\n        if (!array) {\n          array = scope.$$watchers = [];\n          array.$$digestWatchIndex = -1;\n        }\n        // we use unshift since we use a while loop in $digest for speed.\n        // the while loop reads in reverse order.\n        array.unshift(watcher);\n        array.$$digestWatchIndex++;\n        incrementWatchersCount(this, 1);\n\n        return function deregisterWatch() {\n          var index = arrayRemove(array, watcher);\n          if (index >= 0) {\n            incrementWatchersCount(scope, -1);\n            if (index < array.$$digestWatchIndex) {\n              array.$$digestWatchIndex--;\n            }\n          }\n          lastDirtyWatch = null;\n        };\n      },\n\n      /**\n       * @ngdoc method\n       * @name $rootScope.Scope#$watchGroup\n       * @kind function\n       *\n       * @description\n       * A variant of {@link ng.$rootScope.Scope#$watch $watch()} where it watches an array of `watchExpressions`.\n       * If any one expression in the collection changes the `listener` is executed.\n       *\n       * - The items in the `watchExpressions` array are observed via the standard `$watch` operation. Their return\n       *   values are examined for changes on every call to `$digest`.\n       * - The `listener` is called whenever any expression in the `watchExpressions` array changes.\n       *\n       * @param {Array.<string|Function(scope)>} watchExpressions Array of expressions that will be individually\n       * watched using {@link ng.$rootScope.Scope#$watch $watch()}\n       *\n       * @param {function(newValues, oldValues, scope)} listener Callback called whenever the return value of any\n       *    expression in `watchExpressions` changes\n       *    The `newValues` array contains the current values of the `watchExpressions`, with the indexes matching\n       *    those of `watchExpression`\n       *    and the `oldValues` array contains the previous values of the `watchExpressions`, with the indexes matching\n       *    those of `watchExpression`\n       *    The `scope` refers to the current scope.\n       * @returns {function()} Returns a de-registration function for all listeners.\n       */\n      $watchGroup: function(watchExpressions, listener) {\n        var oldValues = new Array(watchExpressions.length);\n        var newValues = new Array(watchExpressions.length);\n        var deregisterFns = [];\n        var self = this;\n        var changeReactionScheduled = false;\n        var firstRun = true;\n\n        if (!watchExpressions.length) {\n          // No expressions means we call the listener ASAP\n          var shouldCall = true;\n          self.$evalAsync(function() {\n            if (shouldCall) listener(newValues, newValues, self);\n          });\n          return function deregisterWatchGroup() {\n            shouldCall = false;\n          };\n        }\n\n        if (watchExpressions.length === 1) {\n          // Special case size of one\n          return this.$watch(watchExpressions[0], function watchGroupAction(value, oldValue, scope) {\n            newValues[0] = value;\n            oldValues[0] = oldValue;\n            listener(newValues, (value === oldValue) ? newValues : oldValues, scope);\n          });\n        }\n\n        forEach(watchExpressions, function(expr, i) {\n          var unwatchFn = self.$watch(expr, function watchGroupSubAction(value) {\n            newValues[i] = value;\n            if (!changeReactionScheduled) {\n              changeReactionScheduled = true;\n              self.$evalAsync(watchGroupAction);\n            }\n          });\n          deregisterFns.push(unwatchFn);\n        });\n\n        function watchGroupAction() {\n          changeReactionScheduled = false;\n\n          try {\n            if (firstRun) {\n              firstRun = false;\n              listener(newValues, newValues, self);\n            } else {\n              listener(newValues, oldValues, self);\n            }\n          } finally {\n            for (var i = 0; i < watchExpressions.length; i++) {\n              oldValues[i] = newValues[i];\n            }\n          }\n        }\n\n        return function deregisterWatchGroup() {\n          while (deregisterFns.length) {\n            deregisterFns.shift()();\n          }\n        };\n      },\n\n\n      /**\n       * @ngdoc method\n       * @name $rootScope.Scope#$watchCollection\n       * @kind function\n       *\n       * @description\n       * Shallow watches the properties of an object and fires whenever any of the properties change\n       * (for arrays, this implies watching the array items; for object maps, this implies watching\n       * the properties). If a change is detected, the `listener` callback is fired.\n       *\n       * - The `obj` collection is observed via standard $watch operation and is examined on every\n       *   call to $digest() to see if any items have been added, removed, or moved.\n       * - The `listener` is called whenever anything within the `obj` has changed. Examples include\n       *   adding, removing, and moving items belonging to an object or array.\n       *\n       *\n       * @example\n       * ```js\n          $scope.names = ['igor', 'matias', 'misko', 'james'];\n          $scope.dataCount = 4;\n\n          $scope.$watchCollection('names', function(newNames, oldNames) {\n            $scope.dataCount = newNames.length;\n          });\n\n          expect($scope.dataCount).toEqual(4);\n          $scope.$digest();\n\n          //still at 4 ... no changes\n          expect($scope.dataCount).toEqual(4);\n\n          $scope.names.pop();\n          $scope.$digest();\n\n          //now there's been a change\n          expect($scope.dataCount).toEqual(3);\n       * ```\n       *\n       *\n       * @param {string|function(scope)} obj Evaluated as {@link guide/expression expression}. The\n       *    expression value should evaluate to an object or an array which is observed on each\n       *    {@link ng.$rootScope.Scope#$digest $digest} cycle. Any shallow change within the\n       *    collection will trigger a call to the `listener`.\n       *\n       * @param {function(newCollection, oldCollection, scope)} listener a callback function called\n       *    when a change is detected.\n       *    - The `newCollection` object is the newly modified data obtained from the `obj` expression\n       *    - The `oldCollection` object is a copy of the former collection data.\n       *      Due to performance considerations, the`oldCollection` value is computed only if the\n       *      `listener` function declares two or more arguments.\n       *    - The `scope` argument refers to the current scope.\n       *\n       * @returns {function()} Returns a de-registration function for this listener. When the\n       *    de-registration function is executed, the internal watch operation is terminated.\n       */\n      $watchCollection: function(obj, listener) {\n        // Mark the interceptor as\n        // ... $$pure when literal since the instance will change when any input changes\n        $watchCollectionInterceptor.$$pure = $parse(obj).literal;\n        // ... $stateful when non-literal since we must read the state of the collection\n        $watchCollectionInterceptor.$stateful = !$watchCollectionInterceptor.$$pure;\n\n        var self = this;\n        // the current value, updated on each dirty-check run\n        var newValue;\n        // a shallow copy of the newValue from the last dirty-check run,\n        // updated to match newValue during dirty-check run\n        var oldValue;\n        // a shallow copy of the newValue from when the last change happened\n        var veryOldValue;\n        // only track veryOldValue if the listener is asking for it\n        var trackVeryOldValue = (listener.length > 1);\n        var changeDetected = 0;\n        var changeDetector = $parse(obj, $watchCollectionInterceptor);\n        var internalArray = [];\n        var internalObject = {};\n        var initRun = true;\n        var oldLength = 0;\n\n        function $watchCollectionInterceptor(_value) {\n          newValue = _value;\n          var newLength, key, bothNaN, newItem, oldItem;\n\n          // If the new value is undefined, then return undefined as the watch may be a one-time watch\n          if (isUndefined(newValue)) return;\n\n          if (!isObject(newValue)) { // if primitive\n            if (oldValue !== newValue) {\n              oldValue = newValue;\n              changeDetected++;\n            }\n          } else if (isArrayLike(newValue)) {\n            if (oldValue !== internalArray) {\n              // we are transitioning from something which was not an array into array.\n              oldValue = internalArray;\n              oldLength = oldValue.length = 0;\n              changeDetected++;\n            }\n\n            newLength = newValue.length;\n\n            if (oldLength !== newLength) {\n              // if lengths do not match we need to trigger change notification\n              changeDetected++;\n              oldValue.length = oldLength = newLength;\n            }\n            // copy the items to oldValue and look for changes.\n            for (var i = 0; i < newLength; i++) {\n              oldItem = oldValue[i];\n              newItem = newValue[i];\n\n              // eslint-disable-next-line no-self-compare\n              bothNaN = (oldItem !== oldItem) && (newItem !== newItem);\n              if (!bothNaN && (oldItem !== newItem)) {\n                changeDetected++;\n                oldValue[i] = newItem;\n              }\n            }\n          } else {\n            if (oldValue !== internalObject) {\n              // we are transitioning from something which was not an object into object.\n              oldValue = internalObject = {};\n              oldLength = 0;\n              changeDetected++;\n            }\n            // copy the items to oldValue and look for changes.\n            newLength = 0;\n            for (key in newValue) {\n              if (hasOwnProperty.call(newValue, key)) {\n                newLength++;\n                newItem = newValue[key];\n                oldItem = oldValue[key];\n\n                if (key in oldValue) {\n                  // eslint-disable-next-line no-self-compare\n                  bothNaN = (oldItem !== oldItem) && (newItem !== newItem);\n                  if (!bothNaN && (oldItem !== newItem)) {\n                    changeDetected++;\n                    oldValue[key] = newItem;\n                  }\n                } else {\n                  oldLength++;\n                  oldValue[key] = newItem;\n                  changeDetected++;\n                }\n              }\n            }\n            if (oldLength > newLength) {\n              // we used to have more keys, need to find them and destroy them.\n              changeDetected++;\n              for (key in oldValue) {\n                if (!hasOwnProperty.call(newValue, key)) {\n                  oldLength--;\n                  delete oldValue[key];\n                }\n              }\n            }\n          }\n          return changeDetected;\n        }\n\n        function $watchCollectionAction() {\n          if (initRun) {\n            initRun = false;\n            listener(newValue, newValue, self);\n          } else {\n            listener(newValue, veryOldValue, self);\n          }\n\n          // make a copy for the next time a collection is changed\n          if (trackVeryOldValue) {\n            if (!isObject(newValue)) {\n              //primitive\n              veryOldValue = newValue;\n            } else if (isArrayLike(newValue)) {\n              veryOldValue = new Array(newValue.length);\n              for (var i = 0; i < newValue.length; i++) {\n                veryOldValue[i] = newValue[i];\n              }\n            } else { // if object\n              veryOldValue = {};\n              for (var key in newValue) {\n                if (hasOwnProperty.call(newValue, key)) {\n                  veryOldValue[key] = newValue[key];\n                }\n              }\n            }\n          }\n        }\n\n        return this.$watch(changeDetector, $watchCollectionAction);\n      },\n\n      /**\n       * @ngdoc method\n       * @name $rootScope.Scope#$digest\n       * @kind function\n       *\n       * @description\n       * Processes all of the {@link ng.$rootScope.Scope#$watch watchers} of the current scope and\n       * its children. Because a {@link ng.$rootScope.Scope#$watch watcher}'s listener can change\n       * the model, the `$digest()` keeps calling the {@link ng.$rootScope.Scope#$watch watchers}\n       * until no more listeners are firing. This means that it is possible to get into an infinite\n       * loop. This function will throw `'Maximum iteration limit exceeded.'` if the number of\n       * iterations exceeds 10.\n       *\n       * Usually, you don't call `$digest()` directly in\n       * {@link ng.directive:ngController controllers} or in\n       * {@link ng.$compileProvider#directive directives}.\n       * Instead, you should call {@link ng.$rootScope.Scope#$apply $apply()} (typically from within\n       * a {@link ng.$compileProvider#directive directive}), which will force a `$digest()`.\n       *\n       * If you want to be notified whenever `$digest()` is called,\n       * you can register a `watchExpression` function with\n       * {@link ng.$rootScope.Scope#$watch $watch()} with no `listener`.\n       *\n       * In unit tests, you may need to call `$digest()` to simulate the scope life cycle.\n       *\n       * @example\n       * ```js\n           var scope = ...;\n           scope.name = 'misko';\n           scope.counter = 0;\n\n           expect(scope.counter).toEqual(0);\n           scope.$watch('name', function(newValue, oldValue) {\n             scope.counter = scope.counter + 1;\n           });\n           expect(scope.counter).toEqual(0);\n\n           scope.$digest();\n           // the listener is always called during the first $digest loop after it was registered\n           expect(scope.counter).toEqual(1);\n\n           scope.$digest();\n           // but now it will not be called unless the value changes\n           expect(scope.counter).toEqual(1);\n\n           scope.name = 'adam';\n           scope.$digest();\n           expect(scope.counter).toEqual(2);\n       * ```\n       *\n       */\n      $digest: function() {\n        var watch, value, last, fn, get,\n            watchers,\n            dirty, ttl = TTL,\n            next, current, target = asyncQueue.length ? $rootScope : this,\n            watchLog = [],\n            logIdx, asyncTask;\n\n        beginPhase('$digest');\n        // Check for changes to browser url that happened in sync before the call to $digest\n        $browser.$$checkUrlChange();\n\n        if (this === $rootScope && applyAsyncId !== null) {\n          // If this is the root scope, and $applyAsync has scheduled a deferred $apply(), then\n          // cancel the scheduled $apply and flush the queue of expressions to be evaluated.\n          $browser.defer.cancel(applyAsyncId);\n          flushApplyAsync();\n        }\n\n        lastDirtyWatch = null;\n\n        do { // \"while dirty\" loop\n          dirty = false;\n          current = target;\n\n          // It's safe for asyncQueuePosition to be a local variable here because this loop can't\n          // be reentered recursively. Calling $digest from a function passed to $evalAsync would\n          // lead to a '$digest already in progress' error.\n          for (var asyncQueuePosition = 0; asyncQueuePosition < asyncQueue.length; asyncQueuePosition++) {\n            try {\n              asyncTask = asyncQueue[asyncQueuePosition];\n              fn = asyncTask.fn;\n              fn(asyncTask.scope, asyncTask.locals);\n            } catch (e) {\n              $exceptionHandler(e);\n            }\n            lastDirtyWatch = null;\n          }\n          asyncQueue.length = 0;\n\n          traverseScopesLoop:\n          do { // \"traverse the scopes\" loop\n            if ((watchers = !current.$$suspended && current.$$watchers)) {\n              // process our watches\n              watchers.$$digestWatchIndex = watchers.length;\n              while (watchers.$$digestWatchIndex--) {\n                try {\n                  watch = watchers[watchers.$$digestWatchIndex];\n                  // Most common watches are on primitives, in which case we can short\n                  // circuit it with === operator, only when === fails do we use .equals\n                  if (watch) {\n                    get = watch.get;\n                    if ((value = get(current)) !== (last = watch.last) &&\n                        !(watch.eq\n                            ? equals(value, last)\n                            : (isNumberNaN(value) && isNumberNaN(last)))) {\n                      dirty = true;\n                      lastDirtyWatch = watch;\n                      watch.last = watch.eq ? copy(value, null) : value;\n                      fn = watch.fn;\n                      fn(value, ((last === initWatchVal) ? value : last), current);\n                      if (ttl < 5) {\n                        logIdx = 4 - ttl;\n                        if (!watchLog[logIdx]) watchLog[logIdx] = [];\n                        watchLog[logIdx].push({\n                          msg: isFunction(watch.exp) ? 'fn: ' + (watch.exp.name || watch.exp.toString()) : watch.exp,\n                          newVal: value,\n                          oldVal: last\n                        });\n                      }\n                    } else if (watch === lastDirtyWatch) {\n                      // If the most recently dirty watcher is now clean, short circuit since the remaining watchers\n                      // have already been tested.\n                      dirty = false;\n                      break traverseScopesLoop;\n                    }\n                  }\n                } catch (e) {\n                  $exceptionHandler(e);\n                }\n              }\n            }\n\n            // Insanity Warning: scope depth-first traversal\n            // yes, this code is a bit crazy, but it works and we have tests to prove it!\n            // this piece should be kept in sync with the traversal in $broadcast\n            // (though it differs due to having the extra check for $$suspended and does not\n            // check $$listenerCount)\n            if (!(next = ((!current.$$suspended && current.$$watchersCount && current.$$childHead) ||\n                (current !== target && current.$$nextSibling)))) {\n              while (current !== target && !(next = current.$$nextSibling)) {\n                current = current.$parent;\n              }\n            }\n          } while ((current = next));\n\n          // `break traverseScopesLoop;` takes us to here\n\n          if ((dirty || asyncQueue.length) && !(ttl--)) {\n            clearPhase();\n            throw $rootScopeMinErr('infdig',\n                '{0} $digest() iterations reached. Aborting!\\n' +\n                'Watchers fired in the last 5 iterations: {1}',\n                TTL, watchLog);\n          }\n\n        } while (dirty || asyncQueue.length);\n\n        clearPhase();\n\n        // postDigestQueuePosition isn't local here because this loop can be reentered recursively.\n        while (postDigestQueuePosition < postDigestQueue.length) {\n          try {\n            postDigestQueue[postDigestQueuePosition++]();\n          } catch (e) {\n            $exceptionHandler(e);\n          }\n        }\n        postDigestQueue.length = postDigestQueuePosition = 0;\n\n        // Check for changes to browser url that happened during the $digest\n        // (for which no event is fired; e.g. via `history.pushState()`)\n        $browser.$$checkUrlChange();\n      },\n\n      /**\n       * @ngdoc method\n       * @name $rootScope.Scope#$suspend\n       * @kind function\n       *\n       * @description\n       * Suspend watchers of this scope subtree so that they will not be invoked during digest.\n       *\n       * This can be used to optimize your application when you know that running those watchers\n       * is redundant.\n       *\n       * **Warning**\n       *\n       * Suspending scopes from the digest cycle can have unwanted and difficult to debug results.\n       * Only use this approach if you are confident that you know what you are doing and have\n       * ample tests to ensure that bindings get updated as you expect.\n       *\n       * Some of the things to consider are:\n       *\n       * * Any external event on a directive/component will not trigger a digest while the hosting\n       *   scope is suspended - even if the event handler calls `$apply()` or `$rootScope.$digest()`.\n       * * Transcluded content exists on a scope that inherits from outside a directive but exists\n       *   as a child of the directive's containing scope. If the containing scope is suspended the\n       *   transcluded scope will also be suspended, even if the scope from which the transcluded\n       *   scope inherits is not suspended.\n       * * Multiple directives trying to manage the suspended status of a scope can confuse each other:\n       *    * A call to `$suspend()` on an already suspended scope is a no-op.\n       *    * A call to `$resume()` on a non-suspended scope is a no-op.\n       *    * If two directives suspend a scope, then one of them resumes the scope, the scope will no\n       *      longer be suspended. This could result in the other directive believing a scope to be\n       *      suspended when it is not.\n       * * If a parent scope is suspended then all its descendants will be also excluded from future\n       *   digests whether or not they have been suspended themselves. Note that this also applies to\n       *   isolate child scopes.\n       * * Calling `$digest()` directly on a descendant of a suspended scope will still run the watchers\n       *   for that scope and its descendants. When digesting we only check whether the current scope is\n       *   locally suspended, rather than checking whether it has a suspended ancestor.\n       * * Calling `$resume()` on a scope that has a suspended ancestor will not cause the scope to be\n       *   included in future digests until all its ancestors have been resumed.\n       * * Resolved promises, e.g. from explicit `$q` deferreds and `$http` calls, trigger `$apply()`\n       *   against the `$rootScope` and so will still trigger a global digest even if the promise was\n       *   initiated by a component that lives on a suspended scope.\n       */\n      $suspend: function() {\n        this.$$suspended = true;\n      },\n\n      /**\n       * @ngdoc method\n       * @name $rootScope.Scope#$isSuspended\n       * @kind function\n       *\n       * @description\n       * Call this method to determine if this scope has been explicitly suspended. It will not\n       * tell you whether an ancestor has been suspended.\n       * To determine if this scope will be excluded from a digest triggered at the $rootScope,\n       * for example, you must check all its ancestors:\n       *\n       * ```\n       * function isExcludedFromDigest(scope) {\n       *   while(scope) {\n       *     if (scope.$isSuspended()) return true;\n       *     scope = scope.$parent;\n       *   }\n       *   return false;\n       * ```\n       *\n       * Be aware that a scope may not be included in digests if it has a suspended ancestor,\n       * even if `$isSuspended()` returns false.\n       *\n       * @returns true if the current scope has been suspended.\n       */\n      $isSuspended: function() {\n        return this.$$suspended;\n      },\n\n      /**\n       * @ngdoc method\n       * @name $rootScope.Scope#$resume\n       * @kind function\n       *\n       * @description\n       * Resume watchers of this scope subtree in case it was suspended.\n       *\n       * See {@link $rootScope.Scope#$suspend} for information about the dangers of using this approach.\n       */\n      $resume: function() {\n        this.$$suspended = false;\n      },\n\n      /**\n       * @ngdoc event\n       * @name $rootScope.Scope#$destroy\n       * @eventType broadcast on scope being destroyed\n       *\n       * @description\n       * Broadcasted when a scope and its children are being destroyed.\n       *\n       * Note that, in AngularJS, there is also a `$destroy` jQuery event, which can be used to\n       * clean up DOM bindings before an element is removed from the DOM.\n       */\n\n      /**\n       * @ngdoc method\n       * @name $rootScope.Scope#$destroy\n       * @kind function\n       *\n       * @description\n       * Removes the current scope (and all of its children) from the parent scope. Removal implies\n       * that calls to {@link ng.$rootScope.Scope#$digest $digest()} will no longer\n       * propagate to the current scope and its children. Removal also implies that the current\n       * scope is eligible for garbage collection.\n       *\n       * The `$destroy()` is usually used by directives such as\n       * {@link ng.directive:ngRepeat ngRepeat} for managing the\n       * unrolling of the loop.\n       *\n       * Just before a scope is destroyed, a `$destroy` event is broadcasted on this scope.\n       * Application code can register a `$destroy` event handler that will give it a chance to\n       * perform any necessary cleanup.\n       *\n       * Note that, in AngularJS, there is also a `$destroy` jQuery event, which can be used to\n       * clean up DOM bindings before an element is removed from the DOM.\n       */\n      $destroy: function() {\n        // We can't destroy a scope that has been already destroyed.\n        if (this.$$destroyed) return;\n        var parent = this.$parent;\n\n        this.$broadcast('$destroy');\n        this.$$destroyed = true;\n\n        if (this === $rootScope) {\n          //Remove handlers attached to window when $rootScope is removed\n          $browser.$$applicationDestroyed();\n        }\n\n        incrementWatchersCount(this, -this.$$watchersCount);\n        for (var eventName in this.$$listenerCount) {\n          decrementListenerCount(this, this.$$listenerCount[eventName], eventName);\n        }\n\n        // sever all the references to parent scopes (after this cleanup, the current scope should\n        // not be retained by any of our references and should be eligible for garbage collection)\n        if (parent && parent.$$childHead === this) parent.$$childHead = this.$$nextSibling;\n        if (parent && parent.$$childTail === this) parent.$$childTail = this.$$prevSibling;\n        if (this.$$prevSibling) this.$$prevSibling.$$nextSibling = this.$$nextSibling;\n        if (this.$$nextSibling) this.$$nextSibling.$$prevSibling = this.$$prevSibling;\n\n        // Disable listeners, watchers and apply/digest methods\n        this.$destroy = this.$digest = this.$apply = this.$evalAsync = this.$applyAsync = noop;\n        this.$on = this.$watch = this.$watchGroup = function() { return noop; };\n        this.$$listeners = {};\n\n        // Disconnect the next sibling to prevent `cleanUpScope` destroying those too\n        this.$$nextSibling = null;\n        cleanUpScope(this);\n      },\n\n      /**\n       * @ngdoc method\n       * @name $rootScope.Scope#$eval\n       * @kind function\n       *\n       * @description\n       * Executes the `expression` on the current scope and returns the result. Any exceptions in\n       * the expression are propagated (uncaught). This is useful when evaluating AngularJS\n       * expressions.\n       *\n       * @example\n       * ```js\n           var scope = ng.$rootScope.Scope();\n           scope.a = 1;\n           scope.b = 2;\n\n           expect(scope.$eval('a+b')).toEqual(3);\n           expect(scope.$eval(function(scope){ return scope.a + scope.b; })).toEqual(3);\n       * ```\n       *\n       * @param {(string|function())=} expression An AngularJS expression to be executed.\n       *\n       *    - `string`: execute using the rules as defined in  {@link guide/expression expression}.\n       *    - `function(scope)`: execute the function with the current `scope` parameter.\n       *\n       * @param {(object)=} locals Local variables object, useful for overriding values in scope.\n       * @returns {*} The result of evaluating the expression.\n       */\n      $eval: function(expr, locals) {\n        return $parse(expr)(this, locals);\n      },\n\n      /**\n       * @ngdoc method\n       * @name $rootScope.Scope#$evalAsync\n       * @kind function\n       *\n       * @description\n       * Executes the expression on the current scope at a later point in time.\n       *\n       * The `$evalAsync` makes no guarantees as to when the `expression` will be executed, only\n       * that:\n       *\n       *   - it will execute after the function that scheduled the evaluation (preferably before DOM\n       *     rendering).\n       *   - at least one {@link ng.$rootScope.Scope#$digest $digest cycle} will be performed after\n       *     `expression` execution.\n       *\n       * Any exceptions from the execution of the expression are forwarded to the\n       * {@link ng.$exceptionHandler $exceptionHandler} service.\n       *\n       * __Note:__ if this function is called outside of a `$digest` cycle, a new `$digest` cycle\n       * will be scheduled. However, it is encouraged to always call code that changes the model\n       * from within an `$apply` call. That includes code evaluated via `$evalAsync`.\n       *\n       * @param {(string|function())=} expression An AngularJS expression to be executed.\n       *\n       *    - `string`: execute using the rules as defined in {@link guide/expression expression}.\n       *    - `function(scope)`: execute the function with the current `scope` parameter.\n       *\n       * @param {(object)=} locals Local variables object, useful for overriding values in scope.\n       */\n      $evalAsync: function(expr, locals) {\n        // if we are outside of an $digest loop and this is the first time we are scheduling async\n        // task also schedule async auto-flush\n        if (!$rootScope.$$phase && !asyncQueue.length) {\n          $browser.defer(function() {\n            if (asyncQueue.length) {\n              $rootScope.$digest();\n            }\n          }, null, '$evalAsync');\n        }\n\n        asyncQueue.push({scope: this, fn: $parse(expr), locals: locals});\n      },\n\n      $$postDigest: function(fn) {\n        postDigestQueue.push(fn);\n      },\n\n      /**\n       * @ngdoc method\n       * @name $rootScope.Scope#$apply\n       * @kind function\n       *\n       * @description\n       * `$apply()` is used to execute an expression in AngularJS from outside of the AngularJS\n       * framework. (For example from browser DOM events, setTimeout, XHR or third party libraries).\n       * Because we are calling into the AngularJS framework we need to perform proper scope life\n       * cycle of {@link ng.$exceptionHandler exception handling},\n       * {@link ng.$rootScope.Scope#$digest executing watches}.\n       *\n       * **Life cycle: Pseudo-Code of `$apply()`**\n       *\n       * ```js\n           function $apply(expr) {\n             try {\n               return $eval(expr);\n             } catch (e) {\n               $exceptionHandler(e);\n             } finally {\n               $root.$digest();\n             }\n           }\n       * ```\n       *\n       *\n       * Scope's `$apply()` method transitions through the following stages:\n       *\n       * 1. The {@link guide/expression expression} is executed using the\n       *    {@link ng.$rootScope.Scope#$eval $eval()} method.\n       * 2. Any exceptions from the execution of the expression are forwarded to the\n       *    {@link ng.$exceptionHandler $exceptionHandler} service.\n       * 3. The {@link ng.$rootScope.Scope#$watch watch} listeners are fired immediately after the\n       *    expression was executed using the {@link ng.$rootScope.Scope#$digest $digest()} method.\n       *\n       *\n       * @param {(string|function())=} exp An AngularJS expression to be executed.\n       *\n       *    - `string`: execute using the rules as defined in {@link guide/expression expression}.\n       *    - `function(scope)`: execute the function with current `scope` parameter.\n       *\n       * @returns {*} The result of evaluating the expression.\n       */\n      $apply: function(expr) {\n        try {\n          beginPhase('$apply');\n          try {\n            return this.$eval(expr);\n          } finally {\n            clearPhase();\n          }\n        } catch (e) {\n          $exceptionHandler(e);\n        } finally {\n          try {\n            $rootScope.$digest();\n          } catch (e) {\n            $exceptionHandler(e);\n            // eslint-disable-next-line no-unsafe-finally\n            throw e;\n          }\n        }\n      },\n\n      /**\n       * @ngdoc method\n       * @name $rootScope.Scope#$applyAsync\n       * @kind function\n       *\n       * @description\n       * Schedule the invocation of $apply to occur at a later time. The actual time difference\n       * varies across browsers, but is typically around ~10 milliseconds.\n       *\n       * This can be used to queue up multiple expressions which need to be evaluated in the same\n       * digest.\n       *\n       * @param {(string|function())=} exp An AngularJS expression to be executed.\n       *\n       *    - `string`: execute using the rules as defined in {@link guide/expression expression}.\n       *    - `function(scope)`: execute the function with current `scope` parameter.\n       */\n      $applyAsync: function(expr) {\n        var scope = this;\n        if (expr) {\n          applyAsyncQueue.push($applyAsyncExpression);\n        }\n        expr = $parse(expr);\n        scheduleApplyAsync();\n\n        function $applyAsyncExpression() {\n          scope.$eval(expr);\n        }\n      },\n\n      /**\n       * @ngdoc method\n       * @name $rootScope.Scope#$on\n       * @kind function\n       *\n       * @description\n       * Listens on events of a given type. See {@link ng.$rootScope.Scope#$emit $emit} for\n       * discussion of event life cycle.\n       *\n       * The event listener function format is: `function(event, args...)`. The `event` object\n       * passed into the listener has the following attributes:\n       *\n       *   - `targetScope` - `{Scope}`: the scope on which the event was `$emit`-ed or\n       *     `$broadcast`-ed.\n       *   - `currentScope` - `{Scope}`: the scope that is currently handling the event. Once the\n       *     event propagates through the scope hierarchy, this property is set to null.\n       *   - `name` - `{string}`: name of the event.\n       *   - `stopPropagation` - `{function=}`: calling `stopPropagation` function will cancel\n       *     further event propagation (available only for events that were `$emit`-ed).\n       *   - `preventDefault` - `{function}`: calling `preventDefault` sets `defaultPrevented` flag\n       *     to true.\n       *   - `defaultPrevented` - `{boolean}`: true if `preventDefault` was called.\n       *\n       * @param {string} name Event name to listen on.\n       * @param {function(event, ...args)} listener Function to call when the event is emitted.\n       * @returns {function()} Returns a deregistration function for this listener.\n       */\n      $on: function(name, listener) {\n        var namedListeners = this.$$listeners[name];\n        if (!namedListeners) {\n          this.$$listeners[name] = namedListeners = [];\n        }\n        namedListeners.push(listener);\n\n        var current = this;\n        do {\n          if (!current.$$listenerCount[name]) {\n            current.$$listenerCount[name] = 0;\n          }\n          current.$$listenerCount[name]++;\n        } while ((current = current.$parent));\n\n        var self = this;\n        return function() {\n          var indexOfListener = namedListeners.indexOf(listener);\n          if (indexOfListener !== -1) {\n            // Use delete in the hope of the browser deallocating the memory for the array entry,\n            // while not shifting the array indexes of other listeners.\n            // See issue https://github.com/angular/angular.js/issues/16135\n            delete namedListeners[indexOfListener];\n            decrementListenerCount(self, 1, name);\n          }\n        };\n      },\n\n\n      /**\n       * @ngdoc method\n       * @name $rootScope.Scope#$emit\n       * @kind function\n       *\n       * @description\n       * Dispatches an event `name` upwards through the scope hierarchy notifying the\n       * registered {@link ng.$rootScope.Scope#$on} listeners.\n       *\n       * The event life cycle starts at the scope on which `$emit` was called. All\n       * {@link ng.$rootScope.Scope#$on listeners} listening for `name` event on this scope get\n       * notified. Afterwards, the event traverses upwards toward the root scope and calls all\n       * registered listeners along the way. The event will stop propagating if one of the listeners\n       * cancels it.\n       *\n       * Any exception emitted from the {@link ng.$rootScope.Scope#$on listeners} will be passed\n       * onto the {@link ng.$exceptionHandler $exceptionHandler} service.\n       *\n       * @param {string} name Event name to emit.\n       * @param {...*} args Optional one or more arguments which will be passed onto the event listeners.\n       * @return {Object} Event object (see {@link ng.$rootScope.Scope#$on}).\n       */\n      $emit: function(name, args) {\n        var empty = [],\n            namedListeners,\n            scope = this,\n            stopPropagation = false,\n            event = {\n              name: name,\n              targetScope: scope,\n              stopPropagation: function() {stopPropagation = true;},\n              preventDefault: function() {\n                event.defaultPrevented = true;\n              },\n              defaultPrevented: false\n            },\n            listenerArgs = concat([event], arguments, 1),\n            i, length;\n\n        do {\n          namedListeners = scope.$$listeners[name] || empty;\n          event.currentScope = scope;\n          for (i = 0, length = namedListeners.length; i < length; i++) {\n\n            // if listeners were deregistered, defragment the array\n            if (!namedListeners[i]) {\n              namedListeners.splice(i, 1);\n              i--;\n              length--;\n              continue;\n            }\n            try {\n              //allow all listeners attached to the current scope to run\n              namedListeners[i].apply(null, listenerArgs);\n            } catch (e) {\n              $exceptionHandler(e);\n            }\n          }\n          //if any listener on the current scope stops propagation, prevent bubbling\n          if (stopPropagation) {\n            break;\n          }\n          //traverse upwards\n          scope = scope.$parent;\n        } while (scope);\n\n        event.currentScope = null;\n\n        return event;\n      },\n\n\n      /**\n       * @ngdoc method\n       * @name $rootScope.Scope#$broadcast\n       * @kind function\n       *\n       * @description\n       * Dispatches an event `name` downwards to all child scopes (and their children) notifying the\n       * registered {@link ng.$rootScope.Scope#$on} listeners.\n       *\n       * The event life cycle starts at the scope on which `$broadcast` was called. All\n       * {@link ng.$rootScope.Scope#$on listeners} listening for `name` event on this scope get\n       * notified. Afterwards, the event propagates to all direct and indirect scopes of the current\n       * scope and calls all registered listeners along the way. The event cannot be canceled.\n       *\n       * Any exception emitted from the {@link ng.$rootScope.Scope#$on listeners} will be passed\n       * onto the {@link ng.$exceptionHandler $exceptionHandler} service.\n       *\n       * @param {string} name Event name to broadcast.\n       * @param {...*} args Optional one or more arguments which will be passed onto the event listeners.\n       * @return {Object} Event object, see {@link ng.$rootScope.Scope#$on}\n       */\n      $broadcast: function(name, args) {\n        var target = this,\n            current = target,\n            next = target,\n            event = {\n              name: name,\n              targetScope: target,\n              preventDefault: function() {\n                event.defaultPrevented = true;\n              },\n              defaultPrevented: false\n            };\n\n        if (!target.$$listenerCount[name]) return event;\n\n        var listenerArgs = concat([event], arguments, 1),\n            listeners, i, length;\n\n        //down while you can, then up and next sibling or up and next sibling until back at root\n        while ((current = next)) {\n          event.currentScope = current;\n          listeners = current.$$listeners[name] || [];\n          for (i = 0, length = listeners.length; i < length; i++) {\n            // if listeners were deregistered, defragment the array\n            if (!listeners[i]) {\n              listeners.splice(i, 1);\n              i--;\n              length--;\n              continue;\n            }\n\n            try {\n              listeners[i].apply(null, listenerArgs);\n            } catch (e) {\n              $exceptionHandler(e);\n            }\n          }\n\n          // Insanity Warning: scope depth-first traversal\n          // yes, this code is a bit crazy, but it works and we have tests to prove it!\n          // this piece should be kept in sync with the traversal in $digest\n          // (though it differs due to having the extra check for $$listenerCount and\n          // does not check $$suspended)\n          if (!(next = ((current.$$listenerCount[name] && current.$$childHead) ||\n              (current !== target && current.$$nextSibling)))) {\n            while (current !== target && !(next = current.$$nextSibling)) {\n              current = current.$parent;\n            }\n          }\n        }\n\n        event.currentScope = null;\n        return event;\n      }\n    };\n\n    var $rootScope = new Scope();\n\n    //The internal queues. Expose them on the $rootScope for debugging/testing purposes.\n    var asyncQueue = $rootScope.$$asyncQueue = [];\n    var postDigestQueue = $rootScope.$$postDigestQueue = [];\n    var applyAsyncQueue = $rootScope.$$applyAsyncQueue = [];\n\n    var postDigestQueuePosition = 0;\n\n    return $rootScope;\n\n\n    function beginPhase(phase) {\n      if ($rootScope.$$phase) {\n        throw $rootScopeMinErr('inprog', '{0} already in progress', $rootScope.$$phase);\n      }\n\n      $rootScope.$$phase = phase;\n    }\n\n    function clearPhase() {\n      $rootScope.$$phase = null;\n    }\n\n    function incrementWatchersCount(current, count) {\n      do {\n        current.$$watchersCount += count;\n      } while ((current = current.$parent));\n    }\n\n    function decrementListenerCount(current, count, name) {\n      do {\n        current.$$listenerCount[name] -= count;\n\n        if (current.$$listenerCount[name] === 0) {\n          delete current.$$listenerCount[name];\n        }\n      } while ((current = current.$parent));\n    }\n\n    /**\n     * function used as an initial value for watchers.\n     * because it's unique we can easily tell it apart from other values\n     */\n    function initWatchVal() {}\n\n    function flushApplyAsync() {\n      while (applyAsyncQueue.length) {\n        try {\n          applyAsyncQueue.shift()();\n        } catch (e) {\n          $exceptionHandler(e);\n        }\n      }\n      applyAsyncId = null;\n    }\n\n    function scheduleApplyAsync() {\n      if (applyAsyncId === null) {\n        applyAsyncId = $browser.defer(function() {\n          $rootScope.$apply(flushApplyAsync);\n        }, null, '$applyAsync');\n      }\n    }\n  }];\n}\n\n/**\n * @ngdoc service\n * @name $rootElement\n *\n * @description\n * The root element of AngularJS application. This is either the element where {@link\n * ng.directive:ngApp ngApp} was declared or the element passed into\n * {@link angular.bootstrap}. The element represents the root element of application. It is also the\n * location where the application's {@link auto.$injector $injector} service gets\n * published, and can be retrieved using `$rootElement.injector()`.\n */\n\n\n// the implementation is in angular.bootstrap\n\n/**\n * @this\n * @description\n * Private service to sanitize uris for links and images. Used by $compile and $sanitize.\n */\nfunction $$SanitizeUriProvider() {\n\n  var aHrefSanitizationTrustedUrlList = /^\\s*(https?|s?ftp|mailto|tel|file):/,\n    imgSrcSanitizationTrustedUrlList = /^\\s*((https?|ftp|file|blob):|data:image\\/)/;\n\n  /**\n   * @description\n   * Retrieves or overrides the default regular expression that is used for determining trusted safe\n   * urls during a[href] sanitization.\n   *\n   * The sanitization is a security measure aimed at prevent XSS attacks via HTML anchor links.\n   *\n   * Any url due to be assigned to an `a[href]` attribute via interpolation is marked as requiring\n   * the $sce.URL security context. When interpolation occurs a call is made to `$sce.trustAsUrl(url)`\n   * which in turn may call `$$sanitizeUri(url, isMedia)` to sanitize the potentially malicious URL.\n   *\n   * If the URL matches the `aHrefSanitizationTrustedUrlList` regular expression, it is returned unchanged.\n   *\n   * If there is no match the URL is returned prefixed with `'unsafe:'` to ensure that when it is written\n   * to the DOM it is inactive and potentially malicious code will not be executed.\n   *\n   * @param {RegExp=} regexp New regexp to trust urls with.\n   * @returns {RegExp|ng.$compileProvider} Current RegExp if called without value or self for\n   *    chaining otherwise.\n   */\n  this.aHrefSanitizationTrustedUrlList = function(regexp) {\n    if (isDefined(regexp)) {\n      aHrefSanitizationTrustedUrlList = regexp;\n      return this;\n    }\n    return aHrefSanitizationTrustedUrlList;\n  };\n\n\n  /**\n   * @description\n   * Retrieves or overrides the default regular expression that is used for determining trusted safe\n   * urls during img[src] sanitization.\n   *\n   * The sanitization is a security measure aimed at prevent XSS attacks via HTML image src links.\n   *\n   * Any URL due to be assigned to an `img[src]` attribute via interpolation is marked as requiring\n   * the $sce.MEDIA_URL security context. When interpolation occurs a call is made to\n   * `$sce.trustAsMediaUrl(url)` which in turn may call `$$sanitizeUri(url, isMedia)` to sanitize\n   * the potentially malicious URL.\n   *\n   * If the URL matches the `imgSrcSanitizationTrustedUrlList` regular expression, it is returned\n   * unchanged.\n   *\n   * If there is no match the URL is returned prefixed with `'unsafe:'` to ensure that when it is written\n   * to the DOM it is inactive and potentially malicious code will not be executed.\n   *\n   * @param {RegExp=} regexp New regexp to trust urls with.\n   * @returns {RegExp|ng.$compileProvider} Current RegExp if called without value or self for\n   *    chaining otherwise.\n   */\n  this.imgSrcSanitizationTrustedUrlList = function(regexp) {\n    if (isDefined(regexp)) {\n      imgSrcSanitizationTrustedUrlList = regexp;\n      return this;\n    }\n    return imgSrcSanitizationTrustedUrlList;\n  };\n\n  this.$get = function() {\n    return function sanitizeUri(uri, isMediaUrl) {\n      // if (!uri) return uri;\n      var regex = isMediaUrl ? imgSrcSanitizationTrustedUrlList : aHrefSanitizationTrustedUrlList;\n      var normalizedVal = urlResolve(uri && uri.trim()).href;\n      if (normalizedVal !== '' && !normalizedVal.match(regex)) {\n        return 'unsafe:' + normalizedVal;\n      }\n      return uri;\n    };\n  };\n}\n\n/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *\n *     Any commits to this file should be reviewed with security in mind.  *\n *   Changes to this file can potentially create security vulnerabilities. *\n *          An approval from 2 Core members with history of modifying      *\n *                         this file is required.                          *\n *                                                                         *\n *  Does the change somehow allow for arbitrary javascript to be executed? *\n *    Or allows for someone to change the prototype of built-in objects?   *\n *     Or gives undesired access to variables likes document or window?    *\n * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */\n\n/* exported $SceProvider, $SceDelegateProvider */\n\nvar $sceMinErr = minErr('$sce');\n\nvar SCE_CONTEXTS = {\n  // HTML is used when there's HTML rendered (e.g. ng-bind-html, iframe srcdoc binding).\n  HTML: 'html',\n\n  // Style statements or stylesheets. Currently unused in AngularJS.\n  CSS: 'css',\n\n  // An URL used in a context where it refers to the source of media, which are not expected to be run\n  // as scripts, such as an image, audio, video, etc.\n  MEDIA_URL: 'mediaUrl',\n\n  // An URL used in a context where it does not refer to a resource that loads code.\n  // A value that can be trusted as a URL can also trusted as a MEDIA_URL.\n  URL: 'url',\n\n  // RESOURCE_URL is a subtype of URL used where the referred-to resource could be interpreted as\n  // code. (e.g. ng-include, script src binding, templateUrl)\n  // A value that can be trusted as a RESOURCE_URL, can also trusted as a URL and a MEDIA_URL.\n  RESOURCE_URL: 'resourceUrl',\n\n  // Script. Currently unused in AngularJS.\n  JS: 'js'\n};\n\n// Helper functions follow.\n\nvar UNDERSCORE_LOWERCASE_REGEXP = /_([a-z])/g;\n\nfunction snakeToCamel(name) {\n  return name\n    .replace(UNDERSCORE_LOWERCASE_REGEXP, fnCamelCaseReplace);\n}\n\nfunction adjustMatcher(matcher) {\n  if (matcher === 'self') {\n    return matcher;\n  } else if (isString(matcher)) {\n    // Strings match exactly except for 2 wildcards - '*' and '**'.\n    // '*' matches any character except those from the set ':/.?&'.\n    // '**' matches any character (like .* in a RegExp).\n    // More than 2 *'s raises an error as it's ill defined.\n    if (matcher.indexOf('***') > -1) {\n      throw $sceMinErr('iwcard',\n          'Illegal sequence *** in string matcher.  String: {0}', matcher);\n    }\n    matcher = escapeForRegexp(matcher).\n                  replace(/\\\\\\*\\\\\\*/g, '.*').\n                  replace(/\\\\\\*/g, '[^:/.?&;]*');\n    return new RegExp('^' + matcher + '$');\n  } else if (isRegExp(matcher)) {\n    // The only other type of matcher allowed is a Regexp.\n    // Match entire URL / disallow partial matches.\n    // Flags are reset (i.e. no global, ignoreCase or multiline)\n    return new RegExp('^' + matcher.source + '$');\n  } else {\n    throw $sceMinErr('imatcher',\n        'Matchers may only be \"self\", string patterns or RegExp objects');\n  }\n}\n\n\nfunction adjustMatchers(matchers) {\n  var adjustedMatchers = [];\n  if (isDefined(matchers)) {\n    forEach(matchers, function(matcher) {\n      adjustedMatchers.push(adjustMatcher(matcher));\n    });\n  }\n  return adjustedMatchers;\n}\n\n\n/**\n * @ngdoc service\n * @name $sceDelegate\n * @kind function\n *\n * @description\n *\n * `$sceDelegate` is a service that is used by the `$sce` service to provide {@link ng.$sce Strict\n * Contextual Escaping (SCE)} services to AngularJS.\n *\n * For an overview of this service and the functionnality it provides in AngularJS, see the main\n * page for {@link ng.$sce SCE}. The current page is targeted for developers who need to alter how\n * SCE works in their application, which shouldn't be needed in most cases.\n *\n * <div class=\"alert alert-danger\">\n * AngularJS strongly relies on contextual escaping for the security of bindings: disabling or\n * modifying this might cause cross site scripting (XSS) vulnerabilities. For libraries owners,\n * changes to this service will also influence users, so be extra careful and document your changes.\n * </div>\n *\n * Typically, you would configure or override the {@link ng.$sceDelegate $sceDelegate} instead of\n * the `$sce` service to customize the way Strict Contextual Escaping works in AngularJS.  This is\n * because, while the `$sce` provides numerous shorthand methods, etc., you really only need to\n * override 3 core functions (`trustAs`, `getTrusted` and `valueOf`) to replace the way things\n * work because `$sce` delegates to `$sceDelegate` for these operations.\n *\n * Refer {@link ng.$sceDelegateProvider $sceDelegateProvider} to configure this service.\n *\n * The default instance of `$sceDelegate` should work out of the box with little pain.  While you\n * can override it completely to change the behavior of `$sce`, the common case would\n * involve configuring the {@link ng.$sceDelegateProvider $sceDelegateProvider} instead by setting\n * your own trusted and banned resource lists for trusting URLs used for loading AngularJS resources\n * such as templates.  Refer {@link ng.$sceDelegateProvider#trustedResourceUrlList\n * $sceDelegateProvider.trustedResourceUrlList} and {@link\n * ng.$sceDelegateProvider#bannedResourceUrlList $sceDelegateProvider.bannedResourceUrlList}\n */\n\n/**\n * @ngdoc provider\n * @name $sceDelegateProvider\n * @this\n *\n * @description\n *\n * The `$sceDelegateProvider` provider allows developers to configure the {@link ng.$sceDelegate\n * $sceDelegate service}, used as a delegate for {@link ng.$sce Strict Contextual Escaping (SCE)}.\n *\n * The `$sceDelegateProvider` allows one to get/set the `trustedResourceUrlList` and\n * `bannedResourceUrlList` used to ensure that the URLs used for sourcing AngularJS templates and\n * other script-running URLs are safe (all places that use the `$sce.RESOURCE_URL` context). See\n * {@link ng.$sceDelegateProvider#trustedResourceUrlList\n * $sceDelegateProvider.trustedResourceUrlList} and\n * {@link ng.$sceDelegateProvider#bannedResourceUrlList $sceDelegateProvider.bannedResourceUrlList},\n *\n * For the general details about this service in AngularJS, read the main page for {@link ng.$sce\n * Strict Contextual Escaping (SCE)}.\n *\n * **Example**:  Consider the following case. <a name=\"example\"></a>\n *\n * - your app is hosted at url `http://myapp.example.com/`\n * - but some of your templates are hosted on other domains you control such as\n *   `http://srv01.assets.example.com/`, `http://srv02.assets.example.com/`, etc.\n * - and you have an open redirect at `http://myapp.example.com/clickThru?...`.\n *\n * Here is what a secure configuration for this scenario might look like:\n *\n * ```\n *  angular.module('myApp', []).config(function($sceDelegateProvider) {\n *    $sceDelegateProvider.trustedResourceUrlList([\n *      // Allow same origin resource loads.\n *      'self',\n *      // Allow loading from our assets domain.  Notice the difference between * and **.\n *      'http://srv*.assets.example.com/**'\n *    ]);\n *\n *    // The banned resource URL list overrides the trusted resource URL list so the open redirect\n *    // here is blocked.\n *    $sceDelegateProvider.bannedResourceUrlList([\n *      'http://myapp.example.com/clickThru**'\n *    ]);\n *  });\n * ```\n * Note that an empty trusted resource URL list will block every resource URL from being loaded, and will require\n * you to manually mark each one as trusted with `$sce.trustAsResourceUrl`. However, templates\n * requested by {@link ng.$templateRequest $templateRequest} that are present in\n * {@link ng.$templateCache $templateCache} will not go through this check. If you have a mechanism\n * to populate your templates in that cache at config time, then it is a good idea to remove 'self'\n * from the trusted resource URL lsit. This helps to mitigate the security impact of certain types\n * of issues, like for instance attacker-controlled `ng-includes`.\n */\n\nfunction $SceDelegateProvider() {\n  this.SCE_CONTEXTS = SCE_CONTEXTS;\n\n  // Resource URLs can also be trusted by policy.\n  var trustedResourceUrlList = ['self'],\n      bannedResourceUrlList = [];\n\n  /**\n   * @ngdoc method\n   * @name $sceDelegateProvider#trustedResourceUrlList\n   * @kind function\n   *\n   * @param {Array=} trustedResourceUrlList When provided, replaces the trustedResourceUrlList with\n   *     the value provided.  This must be an array or null.  A snapshot of this array is used so\n   *     further changes to the array are ignored.\n   *     Follow {@link ng.$sce#resourceUrlPatternItem this link} for a description of the items\n   *     allowed in this array.\n   *\n   * @return {Array} The currently set trusted resource URL array.\n   *\n   * @description\n   * Sets/Gets the list trusted of resource URLs.\n   *\n   * The **default value** when no `trustedResourceUrlList` has been explicitly set is `['self']`\n   * allowing only same origin resource requests.\n   *\n   * <div class=\"alert alert-warning\">\n   * **Note:** the default `trustedResourceUrlList` of 'self' is not recommended if your app shares\n   * its origin with other apps! It is a good idea to limit it to only your application's directory.\n   * </div>\n   */\n  this.trustedResourceUrlList = function(value) {\n    if (arguments.length) {\n      trustedResourceUrlList = adjustMatchers(value);\n    }\n    return trustedResourceUrlList;\n  };\n\n  /**\n   * @ngdoc method\n   * @name $sceDelegateProvider#resourceUrlWhitelist\n   * @kind function\n   *\n   * @deprecated\n   * sinceVersion=\"1.8.1\"\n   *\n   * This method is deprecated. Use {@link $sceDelegateProvider#trustedResourceUrlList\n   * trustedResourceUrlList} instead.\n   */\n  Object.defineProperty(this, 'resourceUrlWhitelist', {\n    get: function() {\n      return this.trustedResourceUrlList;\n    },\n    set: function(value) {\n      this.trustedResourceUrlList = value;\n    }\n  });\n\n  /**\n   * @ngdoc method\n   * @name $sceDelegateProvider#bannedResourceUrlList\n   * @kind function\n   *\n   * @param {Array=} bannedResourceUrlList When provided, replaces the `bannedResourceUrlList` with\n   *     the value provided. This must be an array or null. A snapshot of this array is used so\n   *     further changes to the array are ignored.</p><p>\n   *     Follow {@link ng.$sce#resourceUrlPatternItem this link} for a description of the items\n   *     allowed in this array.</p><p>\n   *     The typical usage for the `bannedResourceUrlList` is to **block\n   *     [open redirects](http://cwe.mitre.org/data/definitions/601.html)** served by your domain as\n   *     these would otherwise be trusted but actually return content from the redirected domain.\n   *     </p><p>\n   *     Finally, **the banned resource URL list overrides the trusted resource URL list** and has\n   *     the final say.\n   *\n   * @return {Array} The currently set `bannedResourceUrlList` array.\n   *\n   * @description\n   * Sets/Gets the `bannedResourceUrlList` of trusted resource URLs.\n   *\n   * The **default value** when no trusted resource URL list has been explicitly set is the empty\n   * array (i.e. there is no `bannedResourceUrlList`.)\n   */\n  this.bannedResourceUrlList = function(value) {\n    if (arguments.length) {\n      bannedResourceUrlList = adjustMatchers(value);\n    }\n    return bannedResourceUrlList;\n  };\n\n  /**\n   * @ngdoc method\n   * @name $sceDelegateProvider#resourceUrlBlacklist\n   * @kind function\n   *\n   * @deprecated\n   * sinceVersion=\"1.8.1\"\n   *\n   * This method is deprecated. Use {@link $sceDelegateProvider#bannedResourceUrlList\n   * bannedResourceUrlList} instead.\n   */\n  Object.defineProperty(this, 'resourceUrlBlacklist', {\n    get: function() {\n      return this.bannedResourceUrlList;\n    },\n    set: function(value) {\n      this.bannedResourceUrlList = value;\n    }\n  });\n\n  this.$get = ['$injector', '$$sanitizeUri', function($injector, $$sanitizeUri) {\n\n    var htmlSanitizer = function htmlSanitizer(html) {\n      throw $sceMinErr('unsafe', 'Attempting to use an unsafe value in a safe context.');\n    };\n\n    if ($injector.has('$sanitize')) {\n      htmlSanitizer = $injector.get('$sanitize');\n    }\n\n\n    function matchUrl(matcher, parsedUrl) {\n      if (matcher === 'self') {\n        return urlIsSameOrigin(parsedUrl) || urlIsSameOriginAsBaseUrl(parsedUrl);\n      } else {\n        // definitely a regex.  See adjustMatchers()\n        return !!matcher.exec(parsedUrl.href);\n      }\n    }\n\n    function isResourceUrlAllowedByPolicy(url) {\n      var parsedUrl = urlResolve(url.toString());\n      var i, n, allowed = false;\n      // Ensure that at least one item from the trusted resource URL list allows this url.\n      for (i = 0, n = trustedResourceUrlList.length; i < n; i++) {\n        if (matchUrl(trustedResourceUrlList[i], parsedUrl)) {\n          allowed = true;\n          break;\n        }\n      }\n      if (allowed) {\n        // Ensure that no item from the banned resource URL list has blocked this url.\n        for (i = 0, n = bannedResourceUrlList.length; i < n; i++) {\n          if (matchUrl(bannedResourceUrlList[i], parsedUrl)) {\n            allowed = false;\n            break;\n          }\n        }\n      }\n      return allowed;\n    }\n\n    function generateHolderType(Base) {\n      var holderType = function TrustedValueHolderType(trustedValue) {\n        this.$$unwrapTrustedValue = function() {\n          return trustedValue;\n        };\n      };\n      if (Base) {\n        holderType.prototype = new Base();\n      }\n      holderType.prototype.valueOf = function sceValueOf() {\n        return this.$$unwrapTrustedValue();\n      };\n      holderType.prototype.toString = function sceToString() {\n        return this.$$unwrapTrustedValue().toString();\n      };\n      return holderType;\n    }\n\n    var trustedValueHolderBase = generateHolderType(),\n        byType = {};\n\n    byType[SCE_CONTEXTS.HTML] = generateHolderType(trustedValueHolderBase);\n    byType[SCE_CONTEXTS.CSS] = generateHolderType(trustedValueHolderBase);\n    byType[SCE_CONTEXTS.MEDIA_URL] = generateHolderType(trustedValueHolderBase);\n    byType[SCE_CONTEXTS.URL] = generateHolderType(byType[SCE_CONTEXTS.MEDIA_URL]);\n    byType[SCE_CONTEXTS.JS] = generateHolderType(trustedValueHolderBase);\n    byType[SCE_CONTEXTS.RESOURCE_URL] = generateHolderType(byType[SCE_CONTEXTS.URL]);\n\n    /**\n     * @ngdoc method\n     * @name $sceDelegate#trustAs\n     *\n     * @description\n     * Returns a trusted representation of the parameter for the specified context. This trusted\n     * object will later on be used as-is, without any security check, by bindings or directives\n     * that require this security context.\n     * For instance, marking a string as trusted for the `$sce.HTML` context will entirely bypass\n     * the potential `$sanitize` call in corresponding `$sce.HTML` bindings or directives, such as\n     * `ng-bind-html`. Note that in most cases you won't need to call this function: if you have the\n     * sanitizer loaded, passing the value itself will render all the HTML that does not pose a\n     * security risk.\n     *\n     * See {@link ng.$sceDelegate#getTrusted getTrusted} for the function that will consume those\n     * trusted values, and {@link ng.$sce $sce} for general documentation about strict contextual\n     * escaping.\n     *\n     * @param {string} type The context in which this value is safe for use, e.g. `$sce.URL`,\n     *     `$sce.RESOURCE_URL`, `$sce.HTML`, `$sce.JS` or `$sce.CSS`.\n     *\n     * @param {*} value The value that should be considered trusted.\n     * @return {*} A trusted representation of value, that can be used in the given context.\n     */\n    function trustAs(type, trustedValue) {\n      var Constructor = (byType.hasOwnProperty(type) ? byType[type] : null);\n      if (!Constructor) {\n        throw $sceMinErr('icontext',\n            'Attempted to trust a value in invalid context. Context: {0}; Value: {1}',\n            type, trustedValue);\n      }\n      if (trustedValue === null || isUndefined(trustedValue) || trustedValue === '') {\n        return trustedValue;\n      }\n      // All the current contexts in SCE_CONTEXTS happen to be strings.  In order to avoid trusting\n      // mutable objects, we ensure here that the value passed in is actually a string.\n      if (typeof trustedValue !== 'string') {\n        throw $sceMinErr('itype',\n            'Attempted to trust a non-string value in a content requiring a string: Context: {0}',\n            type);\n      }\n      return new Constructor(trustedValue);\n    }\n\n    /**\n     * @ngdoc method\n     * @name $sceDelegate#valueOf\n     *\n     * @description\n     * If the passed parameter had been returned by a prior call to {@link ng.$sceDelegate#trustAs\n     * `$sceDelegate.trustAs`}, returns the value that had been passed to {@link\n     * ng.$sceDelegate#trustAs `$sceDelegate.trustAs`}.\n     *\n     * If the passed parameter is not a value that had been returned by {@link\n     * ng.$sceDelegate#trustAs `$sceDelegate.trustAs`}, it must be returned as-is.\n     *\n     * @param {*} value The result of a prior {@link ng.$sceDelegate#trustAs `$sceDelegate.trustAs`}\n     *     call or anything else.\n     * @return {*} The `value` that was originally provided to {@link ng.$sceDelegate#trustAs\n     *     `$sceDelegate.trustAs`} if `value` is the result of such a call.  Otherwise, returns\n     *     `value` unchanged.\n     */\n    function valueOf(maybeTrusted) {\n      if (maybeTrusted instanceof trustedValueHolderBase) {\n        return maybeTrusted.$$unwrapTrustedValue();\n      } else {\n        return maybeTrusted;\n      }\n    }\n\n    /**\n     * @ngdoc method\n     * @name $sceDelegate#getTrusted\n     *\n     * @description\n     * Given an object and a security context in which to assign it, returns a value that's safe to\n     * use in this context, which was represented by the parameter. To do so, this function either\n     * unwraps the safe type it has been given (for instance, a {@link ng.$sceDelegate#trustAs\n     * `$sceDelegate.trustAs`} result), or it might try to sanitize the value given, depending on\n     * the context and sanitizer availablility.\n     *\n     * The contexts that can be sanitized are $sce.MEDIA_URL, $sce.URL and $sce.HTML. The first two are available\n     * by default, and the third one relies on the `$sanitize` service (which may be loaded through\n     * the `ngSanitize` module). Furthermore, for $sce.RESOURCE_URL context, a plain string may be\n     * accepted if the resource url policy defined by {@link ng.$sceDelegateProvider#trustedResourceUrlList\n     * `$sceDelegateProvider.trustedResourceUrlList`} and {@link ng.$sceDelegateProvider#bannedResourceUrlList\n     * `$sceDelegateProvider.bannedResourceUrlList`} accepts that resource.\n     *\n     * This function will throw if the safe type isn't appropriate for this context, or if the\n     * value given cannot be accepted in the context (which might be caused by sanitization not\n     * being available, or the value not being recognized as safe).\n     *\n     * <div class=\"alert alert-danger\">\n     * Disabling auto-escaping is extremely dangerous, it usually creates a Cross Site Scripting\n     * (XSS) vulnerability in your application.\n     * </div>\n     *\n     * @param {string} type The context in which this value is to be used (such as `$sce.HTML`).\n     * @param {*} maybeTrusted The result of a prior {@link ng.$sceDelegate#trustAs\n     *     `$sceDelegate.trustAs`} call, or anything else (which will not be considered trusted.)\n     * @return {*} A version of the value that's safe to use in the given context, or throws an\n     *     exception if this is impossible.\n     */\n    function getTrusted(type, maybeTrusted) {\n      if (maybeTrusted === null || isUndefined(maybeTrusted) || maybeTrusted === '') {\n        return maybeTrusted;\n      }\n      var constructor = (byType.hasOwnProperty(type) ? byType[type] : null);\n      // If maybeTrusted is a trusted class instance or subclass instance, then unwrap and return\n      // as-is.\n      if (constructor && maybeTrusted instanceof constructor) {\n        return maybeTrusted.$$unwrapTrustedValue();\n      }\n\n      // If maybeTrusted is a trusted class instance but not of the correct trusted type\n      // then unwrap it and allow it to pass through to the rest of the checks\n      if (isFunction(maybeTrusted.$$unwrapTrustedValue)) {\n        maybeTrusted = maybeTrusted.$$unwrapTrustedValue();\n      }\n\n      // If we get here, then we will either sanitize the value or throw an exception.\n      if (type === SCE_CONTEXTS.MEDIA_URL || type === SCE_CONTEXTS.URL) {\n        // we attempt to sanitize non-resource URLs\n        return $$sanitizeUri(maybeTrusted.toString(), type === SCE_CONTEXTS.MEDIA_URL);\n      } else if (type === SCE_CONTEXTS.RESOURCE_URL) {\n        if (isResourceUrlAllowedByPolicy(maybeTrusted)) {\n          return maybeTrusted;\n        } else {\n          throw $sceMinErr('insecurl',\n              'Blocked loading resource from url not allowed by $sceDelegate policy.  URL: {0}',\n              maybeTrusted.toString());\n        }\n      } else if (type === SCE_CONTEXTS.HTML) {\n        // htmlSanitizer throws its own error when no sanitizer is available.\n        return htmlSanitizer(maybeTrusted);\n      }\n      // Default error when the $sce service has no way to make the input safe.\n      throw $sceMinErr('unsafe', 'Attempting to use an unsafe value in a safe context.');\n    }\n\n    return { trustAs: trustAs,\n             getTrusted: getTrusted,\n             valueOf: valueOf };\n  }];\n}\n\n\n/**\n * @ngdoc provider\n * @name $sceProvider\n * @this\n *\n * @description\n *\n * The $sceProvider provider allows developers to configure the {@link ng.$sce $sce} service.\n * -   enable/disable Strict Contextual Escaping (SCE) in a module\n * -   override the default implementation with a custom delegate\n *\n * Read more about {@link ng.$sce Strict Contextual Escaping (SCE)}.\n */\n\n/**\n * @ngdoc service\n * @name $sce\n * @kind function\n *\n * @description\n *\n * `$sce` is a service that provides Strict Contextual Escaping services to AngularJS.\n *\n * ## Strict Contextual Escaping\n *\n * Strict Contextual Escaping (SCE) is a mode in which AngularJS constrains bindings to only render\n * trusted values. Its goal is to assist in writing code in a way that (a) is secure by default, and\n * (b) makes auditing for security vulnerabilities such as XSS, clickjacking, etc. a lot easier.\n *\n * ### Overview\n *\n * To systematically block XSS security bugs, AngularJS treats all values as untrusted by default in\n * HTML or sensitive URL bindings. When binding untrusted values, AngularJS will automatically\n * run security checks on them (sanitizations, trusted URL resource, depending on context), or throw\n * when it cannot guarantee the security of the result. That behavior depends strongly on contexts:\n * HTML can be sanitized, but template URLs cannot, for instance.\n *\n * To illustrate this, consider the `ng-bind-html` directive. It renders its value directly as HTML:\n * we call that the *context*. When given an untrusted input, AngularJS will attempt to sanitize it\n * before rendering if a sanitizer is available, and throw otherwise. To bypass sanitization and\n * render the input as-is, you will need to mark it as trusted for that context before attempting\n * to bind it.\n *\n * As of version 1.2, AngularJS ships with SCE enabled by default.\n *\n * ### In practice\n *\n * Here's an example of a binding in a privileged context:\n *\n * ```\n * <input ng-model=\"userHtml\" aria-label=\"User input\">\n * <div ng-bind-html=\"userHtml\"></div>\n * ```\n *\n * Notice that `ng-bind-html` is bound to `userHtml` controlled by the user.  With SCE\n * disabled, this application allows the user to render arbitrary HTML into the DIV, which would\n * be an XSS security bug. In a more realistic example, one may be rendering user comments, blog\n * articles, etc. via bindings. (HTML is just one example of a context where rendering user\n * controlled input creates security vulnerabilities.)\n *\n * For the case of HTML, you might use a library, either on the client side, or on the server side,\n * to sanitize unsafe HTML before binding to the value and rendering it in the document.\n *\n * How would you ensure that every place that used these types of bindings was bound to a value that\n * was sanitized by your library (or returned as safe for rendering by your server?)  How can you\n * ensure that you didn't accidentally delete the line that sanitized the value, or renamed some\n * properties/fields and forgot to update the binding to the sanitized value?\n *\n * To be secure by default, AngularJS makes sure bindings go through that sanitization, or\n * any similar validation process, unless there's a good reason to trust the given value in this\n * context.  That trust is formalized with a function call. This means that as a developer, you\n * can assume all untrusted bindings are safe. Then, to audit your code for binding security issues,\n * you just need to ensure the values you mark as trusted indeed are safe - because they were\n * received from your server, sanitized by your library, etc. You can organize your codebase to\n * help with this - perhaps allowing only the files in a specific directory to do this.\n * Ensuring that the internal API exposed by that code doesn't markup arbitrary values as safe then\n * becomes a more manageable task.\n *\n * In the case of AngularJS' SCE service, one uses {@link ng.$sce#trustAs $sce.trustAs}\n * (and shorthand methods such as {@link ng.$sce#trustAsHtml $sce.trustAsHtml}, etc.) to\n * build the trusted versions of your values.\n *\n * ### How does it work?\n *\n * In privileged contexts, directives and code will bind to the result of {@link ng.$sce#getTrusted\n * $sce.getTrusted(context, value)} rather than to the value directly.  Think of this function as\n * a way to enforce the required security context in your data sink. Directives use {@link\n * ng.$sce#parseAs $sce.parseAs} rather than `$parse` to watch attribute bindings, which performs\n * the {@link ng.$sce#getTrusted $sce.getTrusted} behind the scenes on non-constant literals. Also,\n * when binding without directives, AngularJS will understand the context of your bindings\n * automatically.\n *\n * As an example, {@link ng.directive:ngBindHtml ngBindHtml} uses {@link\n * ng.$sce#parseAsHtml $sce.parseAsHtml(binding expression)}.  Here's the actual code (slightly\n * simplified):\n *\n * ```\n * var ngBindHtmlDirective = ['$sce', function($sce) {\n *   return function(scope, element, attr) {\n *     scope.$watch($sce.parseAsHtml(attr.ngBindHtml), function(value) {\n *       element.html(value || '');\n *     });\n *   };\n * }];\n * ```\n *\n * ### Impact on loading templates\n *\n * This applies both to the {@link ng.directive:ngInclude `ng-include`} directive as well as\n * `templateUrl`'s specified by {@link guide/directive directives}.\n *\n * By default, AngularJS only loads templates from the same domain and protocol as the application\n * document.  This is done by calling {@link ng.$sce#getTrustedResourceUrl\n * $sce.getTrustedResourceUrl} on the template URL.  To load templates from other domains and/or\n * protocols, you may either add them to the {@link ng.$sceDelegateProvider#trustedResourceUrlList\n * trustedResourceUrlList} or {@link ng.$sce#trustAsResourceUrl wrap them} into trusted values.\n *\n * *Please note*:\n * The browser's\n * [Same Origin Policy](https://code.google.com/p/browsersec/wiki/Part2#Same-origin_policy_for_XMLHttpRequest)\n * and [Cross-Origin Resource Sharing (CORS)](http://www.w3.org/TR/cors/)\n * policy apply in addition to this and may further restrict whether the template is successfully\n * loaded.  This means that without the right CORS policy, loading templates from a different domain\n * won't work on all browsers.  Also, loading templates from `file://` URL does not work on some\n * browsers.\n *\n * ### This feels like too much overhead\n *\n * It's important to remember that SCE only applies to interpolation expressions.\n *\n * If your expressions are constant literals, they're automatically trusted and you don't need to\n * call `$sce.trustAs` on them (e.g.\n * `<div ng-bind-html=\"'<b>implicitly trusted</b>'\"></div>`) just works (remember to include the\n * `ngSanitize` module). The `$sceDelegate` will also use the `$sanitize` service if it is available\n * when binding untrusted values to `$sce.HTML` context.\n * AngularJS provides an implementation in `angular-sanitize.js`, and if you\n * wish to use it, you will also need to depend on the {@link ngSanitize `ngSanitize`} module in\n * your application.\n *\n * The included {@link ng.$sceDelegate $sceDelegate} comes with sane defaults to allow you to load\n * templates in `ng-include` from your application's domain without having to even know about SCE.\n * It blocks loading templates from other domains or loading templates over http from an https\n * served document.  You can change these by setting your own custom {@link\n * ng.$sceDelegateProvider#trustedResourceUrlList trusted resource URL list} and {@link\n * ng.$sceDelegateProvider#bannedResourceUrlList banned resource URL list} for matching such URLs.\n *\n * This significantly reduces the overhead.  It is far easier to pay the small overhead and have an\n * application that's secure and can be audited to verify that with much more ease than bolting\n * security onto an application later.\n *\n * <a name=\"contexts\"></a>\n * ### What trusted context types are supported?\n *\n * | Context             | Notes          |\n * |---------------------|----------------|\n * | `$sce.HTML`         | For HTML that's safe to source into the application.  The {@link ng.directive:ngBindHtml ngBindHtml} directive uses this context for bindings. If an unsafe value is encountered and the {@link ngSanitize $sanitize} module is present this will sanitize the value instead of throwing an error. |\n * | `$sce.CSS`          | For CSS that's safe to source into the application.  Currently unused.  Feel free to use it in your own directives. |\n * | `$sce.MEDIA_URL`    | For URLs that are safe to render as media. Is automatically converted from string by sanitizing when needed. |\n * | `$sce.URL`          | For URLs that are safe to follow as links. Is automatically converted from string by sanitizing when needed. Note that `$sce.URL` makes a stronger statement about the URL than `$sce.MEDIA_URL` does and therefore contexts requiring values trusted for `$sce.URL` can be used anywhere that values trusted for `$sce.MEDIA_URL` are required.|\n * | `$sce.RESOURCE_URL` | For URLs that are not only safe to follow as links, but whose contents are also safe to include in your application.  Examples include `ng-include`, `src` / `ngSrc` bindings for tags other than `IMG` (e.g. `IFRAME`, `OBJECT`, etc.)  <br><br>Note that `$sce.RESOURCE_URL` makes a stronger statement about the URL than `$sce.URL` or `$sce.MEDIA_URL` do and therefore contexts requiring values trusted for `$sce.RESOURCE_URL` can be used anywhere that values trusted for `$sce.URL` or `$sce.MEDIA_URL` are required. <br><br> The {@link $sceDelegateProvider#trustedResourceUrlList $sceDelegateProvider#trustedResourceUrlList()} and {@link $sceDelegateProvider#bannedResourceUrlList $sceDelegateProvider#bannedResourceUrlList()} can be used to restrict trusted origins for `RESOURCE_URL` |\n * | `$sce.JS`           | For JavaScript that is safe to execute in your application's context.  Currently unused.  Feel free to use it in your own directives. |\n *\n *\n * <div class=\"alert alert-warning\">\n * Be aware that, before AngularJS 1.7.0, `a[href]` and `img[src]` used to sanitize their\n * interpolated values directly rather than rely upon {@link ng.$sce#getTrusted `$sce.getTrusted`}.\n *\n * **As of 1.7.0, this is no longer the case.**\n *\n * Now such interpolations are marked as requiring `$sce.URL` (for `a[href]`) or `$sce.MEDIA_URL`\n * (for `img[src]`), so that the sanitization happens (via `$sce.getTrusted...`) when the `$interpolate`\n * service evaluates the expressions.\n * </div>\n *\n * There are no CSS or JS context bindings in AngularJS currently, so their corresponding `$sce.trustAs`\n * functions aren't useful yet. This might evolve.\n *\n * ### Format of items in {@link ng.$sceDelegateProvider#trustedResourceUrlList trustedResourceUrlList}/{@link ng.$sceDelegateProvider#bannedResourceUrlList bannedResourceUrlList} <a name=\"resourceUrlPatternItem\"></a>\n *\n *  Each element in these arrays must be one of the following:\n *\n *  - **'self'**\n *    - The special **string**, `'self'`, can be used to match against all URLs of the **same\n *      domain** as the application document using the **same protocol**.\n *  - **String** (except the special value `'self'`)\n *    - The string is matched against the full *normalized / absolute URL* of the resource\n *      being tested (substring matches are not good enough.)\n *    - There are exactly **two wildcard sequences** - `*` and `**`.  All other characters\n *      match themselves.\n *    - `*`: matches zero or more occurrences of any character other than one of the following 6\n *      characters: '`:`', '`/`', '`.`', '`?`', '`&`' and '`;`'.  It's a useful wildcard for use\n *      for matching resource URL lists.\n *    - `**`: matches zero or more occurrences of *any* character.  As such, it's not\n *      appropriate for use in a scheme, domain, etc. as it would match too much.  (e.g.\n *      http://**.example.com/ would match http://evil.com/?ignore=.example.com/ and that might\n *      not have been the intention.)  Its usage at the very end of the path is ok.  (e.g.\n *      http://foo.example.com/templates/**).\n *  - **RegExp** (*see caveat below*)\n *    - *Caveat*:  While regular expressions are powerful and offer great flexibility,  their syntax\n *      (and all the inevitable escaping) makes them *harder to maintain*.  It's easy to\n *      accidentally introduce a bug when one updates a complex expression (imho, all regexes should\n *      have good test coverage).  For instance, the use of `.` in the regex is correct only in a\n *      small number of cases.  A `.` character in the regex used when matching the scheme or a\n *      subdomain could be matched against a `:` or literal `.` that was likely not intended.   It\n *      is highly recommended to use the string patterns and only fall back to regular expressions\n *      as a last resort.\n *    - The regular expression must be an instance of RegExp (i.e. not a string.)  It is\n *      matched against the **entire** *normalized / absolute URL* of the resource being tested\n *      (even when the RegExp did not have the `^` and `$` codes.)  In addition, any flags\n *      present on the RegExp (such as multiline, global, ignoreCase) are ignored.\n *    - If you are generating your JavaScript from some other templating engine (not\n *      recommended, e.g. in issue [#4006](https://github.com/angular/angular.js/issues/4006)),\n *      remember to escape your regular expression (and be aware that you might need more than\n *      one level of escaping depending on your templating engine and the way you interpolated\n *      the value.)  Do make use of your platform's escaping mechanism as it might be good\n *      enough before coding your own.  E.g. Ruby has\n *      [Regexp.escape(str)](http://www.ruby-doc.org/core-2.0.0/Regexp.html#method-c-escape)\n *      and Python has [re.escape](http://docs.python.org/library/re.html#re.escape).\n *      Javascript lacks a similar built in function for escaping.  Take a look at Google\n *      Closure library's [goog.string.regExpEscape(s)](\n *      http://docs.closure-library.googlecode.com/git/closure_goog_string_string.js.source.html#line962).\n *\n * Refer {@link ng.$sceDelegateProvider $sceDelegateProvider} for an example.\n *\n * ### Show me an example using SCE.\n *\n * <example module=\"mySceApp\" deps=\"angular-sanitize.js\" name=\"sce-service\">\n * <file name=\"index.html\">\n *   <div ng-controller=\"AppController as myCtrl\">\n *     <i ng-bind-html=\"myCtrl.explicitlyTrustedHtml\" id=\"explicitlyTrustedHtml\"></i><br><br>\n *     <b>User comments</b><br>\n *     By default, HTML that isn't explicitly trusted (e.g. Alice's comment) is sanitized when\n *     $sanitize is available.  If $sanitize isn't available, this results in an error instead of an\n *     exploit.\n *     <div class=\"well\">\n *       <div ng-repeat=\"userComment in myCtrl.userComments\">\n *         <b>{{userComment.name}}</b>:\n *         <span ng-bind-html=\"userComment.htmlComment\" class=\"htmlComment\"></span>\n *         <br>\n *       </div>\n *     </div>\n *   </div>\n * </file>\n *\n * <file name=\"script.js\">\n *   angular.module('mySceApp', ['ngSanitize'])\n *     .controller('AppController', ['$http', '$templateCache', '$sce',\n *       function AppController($http, $templateCache, $sce) {\n *         var self = this;\n *         $http.get('test_data.json', {cache: $templateCache}).then(function(response) {\n *           self.userComments = response.data;\n *         });\n *         self.explicitlyTrustedHtml = $sce.trustAsHtml(\n *             '<span onmouseover=\"this.textContent=&quot;Explicitly trusted HTML bypasses ' +\n *             'sanitization.&quot;\">Hover over this text.</span>');\n *       }]);\n * </file>\n *\n * <file name=\"test_data.json\">\n * [\n *   { \"name\": \"Alice\",\n *     \"htmlComment\":\n *         \"<span onmouseover='this.textContent=\\\"PWN3D!\\\"'>Is <i>anyone</i> reading this?</span>\"\n *   },\n *   { \"name\": \"Bob\",\n *     \"htmlComment\": \"<i>Yes!</i>  Am I the only other one?\"\n *   }\n * ]\n * </file>\n *\n * <file name=\"protractor.js\" type=\"protractor\">\n *   describe('SCE doc demo', function() {\n *     it('should sanitize untrusted values', function() {\n *       expect(element.all(by.css('.htmlComment')).first().getAttribute('innerHTML'))\n *           .toBe('<span>Is <i>anyone</i> reading this?</span>');\n *     });\n *\n *     it('should NOT sanitize explicitly trusted values', function() {\n *       expect(element(by.id('explicitlyTrustedHtml')).getAttribute('innerHTML')).toBe(\n *           '<span onmouseover=\"this.textContent=&quot;Explicitly trusted HTML bypasses ' +\n *           'sanitization.&quot;\">Hover over this text.</span>');\n *     });\n *   });\n * </file>\n * </example>\n *\n *\n *\n * ## Can I disable SCE completely?\n *\n * Yes, you can.  However, this is strongly discouraged.  SCE gives you a lot of security benefits\n * for little coding overhead.  It will be much harder to take an SCE disabled application and\n * either secure it on your own or enable SCE at a later stage.  It might make sense to disable SCE\n * for cases where you have a lot of existing code that was written before SCE was introduced and\n * you're migrating them a module at a time. Also do note that this is an app-wide setting, so if\n * you are writing a library, you will cause security bugs applications using it.\n *\n * That said, here's how you can completely disable SCE:\n *\n * ```\n * angular.module('myAppWithSceDisabledmyApp', []).config(function($sceProvider) {\n *   // Completely disable SCE.  For demonstration purposes only!\n *   // Do not use in new projects or libraries.\n *   $sceProvider.enabled(false);\n * });\n * ```\n *\n */\n\nfunction $SceProvider() {\n  var enabled = true;\n\n  /**\n   * @ngdoc method\n   * @name $sceProvider#enabled\n   * @kind function\n   *\n   * @param {boolean=} value If provided, then enables/disables SCE application-wide.\n   * @return {boolean} True if SCE is enabled, false otherwise.\n   *\n   * @description\n   * Enables/disables SCE and returns the current value.\n   */\n  this.enabled = function(value) {\n    if (arguments.length) {\n      enabled = !!value;\n    }\n    return enabled;\n  };\n\n\n  /* Design notes on the default implementation for SCE.\n   *\n   * The API contract for the SCE delegate\n   * -------------------------------------\n   * The SCE delegate object must provide the following 3 methods:\n   *\n   * - trustAs(contextEnum, value)\n   *     This method is used to tell the SCE service that the provided value is OK to use in the\n   *     contexts specified by contextEnum.  It must return an object that will be accepted by\n   *     getTrusted() for a compatible contextEnum and return this value.\n   *\n   * - valueOf(value)\n   *     For values that were not produced by trustAs(), return them as is.  For values that were\n   *     produced by trustAs(), return the corresponding input value to trustAs.  Basically, if\n   *     trustAs is wrapping the given values into some type, this operation unwraps it when given\n   *     such a value.\n   *\n   * - getTrusted(contextEnum, value)\n   *     This function should return the value that is safe to use in the context specified by\n   *     contextEnum or throw and exception otherwise.\n   *\n   * NOTE: This contract deliberately does NOT state that values returned by trustAs() must be\n   * opaque or wrapped in some holder object.  That happens to be an implementation detail.  For\n   * instance, an implementation could maintain a registry of all trusted objects by context.  In\n   * such a case, trustAs() would return the same object that was passed in.  getTrusted() would\n   * return the same object passed in if it was found in the registry under a compatible context or\n   * throw an exception otherwise.  An implementation might only wrap values some of the time based\n   * on some criteria.  getTrusted() might return a value and not throw an exception for special\n   * constants or objects even if not wrapped.  All such implementations fulfill this contract.\n   *\n   *\n   * A note on the inheritance model for SCE contexts\n   * ------------------------------------------------\n   * I've used inheritance and made RESOURCE_URL wrapped types a subtype of URL wrapped types.  This\n   * is purely an implementation details.\n   *\n   * The contract is simply this:\n   *\n   *     getTrusted($sce.RESOURCE_URL, value) succeeding implies that getTrusted($sce.URL, value)\n   *     will also succeed.\n   *\n   * Inheritance happens to capture this in a natural way. In some future, we may not use\n   * inheritance anymore. That is OK because no code outside of sce.js and sceSpecs.js would need to\n   * be aware of this detail.\n   */\n\n  this.$get = ['$parse', '$sceDelegate', function(\n                $parse,   $sceDelegate) {\n    // Support: IE 9-11 only\n    // Prereq: Ensure that we're not running in IE<11 quirks mode.  In that mode, IE < 11 allow\n    // the \"expression(javascript expression)\" syntax which is insecure.\n    if (enabled && msie < 8) {\n      throw $sceMinErr('iequirks',\n        'Strict Contextual Escaping does not support Internet Explorer version < 11 in quirks ' +\n        'mode.  You can fix this by adding the text <!doctype html> to the top of your HTML ' +\n        'document.  See http://docs.angularjs.org/api/ng.$sce for more information.');\n    }\n\n    var sce = shallowCopy(SCE_CONTEXTS);\n\n    /**\n     * @ngdoc method\n     * @name $sce#isEnabled\n     * @kind function\n     *\n     * @return {Boolean} True if SCE is enabled, false otherwise.  If you want to set the value, you\n     *     have to do it at module config time on {@link ng.$sceProvider $sceProvider}.\n     *\n     * @description\n     * Returns a boolean indicating if SCE is enabled.\n     */\n    sce.isEnabled = function() {\n      return enabled;\n    };\n    sce.trustAs = $sceDelegate.trustAs;\n    sce.getTrusted = $sceDelegate.getTrusted;\n    sce.valueOf = $sceDelegate.valueOf;\n\n    if (!enabled) {\n      sce.trustAs = sce.getTrusted = function(type, value) { return value; };\n      sce.valueOf = identity;\n    }\n\n    /**\n     * @ngdoc method\n     * @name $sce#parseAs\n     *\n     * @description\n     * Converts AngularJS {@link guide/expression expression} into a function.  This is like {@link\n     * ng.$parse $parse} and is identical when the expression is a literal constant.  Otherwise, it\n     * wraps the expression in a call to {@link ng.$sce#getTrusted $sce.getTrusted(*type*,\n     * *result*)}\n     *\n     * @param {string} type The SCE context in which this result will be used.\n     * @param {string} expression String expression to compile.\n     * @return {function(context, locals)} A function which represents the compiled expression:\n     *\n     *    * `context` – `{object}` – an object against which any expressions embedded in the\n     *      strings are evaluated against (typically a scope object).\n     *    * `locals` – `{object=}` – local variables context object, useful for overriding values\n     *      in `context`.\n     */\n    sce.parseAs = function sceParseAs(type, expr) {\n      var parsed = $parse(expr);\n      if (parsed.literal && parsed.constant) {\n        return parsed;\n      } else {\n        return $parse(expr, function(value) {\n          return sce.getTrusted(type, value);\n        });\n      }\n    };\n\n    /**\n     * @ngdoc method\n     * @name $sce#trustAs\n     *\n     * @description\n     * Delegates to {@link ng.$sceDelegate#trustAs `$sceDelegate.trustAs`}. As such, returns a\n     * wrapped object that represents your value, and the trust you have in its safety for the given\n     * context. AngularJS can then use that value as-is in bindings of the specified secure context.\n     * This is used in bindings for `ng-bind-html`, `ng-include`, and most `src` attribute\n     * interpolations. See {@link ng.$sce $sce} for strict contextual escaping.\n     *\n     * @param {string} type The context in which this value is safe for use, e.g. `$sce.URL`,\n     *     `$sce.RESOURCE_URL`, `$sce.HTML`, `$sce.JS` or `$sce.CSS`.\n     *\n     * @param {*} value The value that that should be considered trusted.\n     * @return {*} A wrapped version of value that can be used as a trusted variant of your `value`\n     *     in the context you specified.\n     */\n\n    /**\n     * @ngdoc method\n     * @name $sce#trustAsHtml\n     *\n     * @description\n     * Shorthand method.  `$sce.trustAsHtml(value)` →\n     *     {@link ng.$sceDelegate#trustAs `$sceDelegate.trustAs($sce.HTML, value)`}\n     *\n     * @param {*} value The value to mark as trusted for `$sce.HTML` context.\n     * @return {*} A wrapped version of value that can be used as a trusted variant of your `value`\n     *     in `$sce.HTML` context (like `ng-bind-html`).\n     */\n\n    /**\n     * @ngdoc method\n     * @name $sce#trustAsCss\n     *\n     * @description\n     * Shorthand method.  `$sce.trustAsCss(value)` →\n     *     {@link ng.$sceDelegate#trustAs `$sceDelegate.trustAs($sce.CSS, value)`}\n     *\n     * @param {*} value The value to mark as trusted for `$sce.CSS` context.\n     * @return {*} A wrapped version of value that can be used as a trusted variant\n     *     of your `value` in `$sce.CSS` context. This context is currently unused, so there are\n     *     almost no reasons to use this function so far.\n     */\n\n    /**\n     * @ngdoc method\n     * @name $sce#trustAsUrl\n     *\n     * @description\n     * Shorthand method.  `$sce.trustAsUrl(value)` →\n     *     {@link ng.$sceDelegate#trustAs `$sceDelegate.trustAs($sce.URL, value)`}\n     *\n     * @param {*} value The value to mark as trusted for `$sce.URL` context.\n     * @return {*} A wrapped version of value that can be used as a trusted variant of your `value`\n     *     in `$sce.URL` context. That context is currently unused, so there are almost no reasons\n     *     to use this function so far.\n     */\n\n    /**\n     * @ngdoc method\n     * @name $sce#trustAsResourceUrl\n     *\n     * @description\n     * Shorthand method.  `$sce.trustAsResourceUrl(value)` →\n     *     {@link ng.$sceDelegate#trustAs `$sceDelegate.trustAs($sce.RESOURCE_URL, value)`}\n     *\n     * @param {*} value The value to mark as trusted for `$sce.RESOURCE_URL` context.\n     * @return {*} A wrapped version of value that can be used as a trusted variant of your `value`\n     *     in `$sce.RESOURCE_URL` context (template URLs in `ng-include`, most `src` attribute\n     *     bindings, ...)\n     */\n\n    /**\n     * @ngdoc method\n     * @name $sce#trustAsJs\n     *\n     * @description\n     * Shorthand method.  `$sce.trustAsJs(value)` →\n     *     {@link ng.$sceDelegate#trustAs `$sceDelegate.trustAs($sce.JS, value)`}\n     *\n     * @param {*} value The value to mark as trusted for `$sce.JS` context.\n     * @return {*} A wrapped version of value that can be used as a trusted variant of your `value`\n     *     in `$sce.JS` context. That context is currently unused, so there are almost no reasons to\n     *     use this function so far.\n     */\n\n    /**\n     * @ngdoc method\n     * @name $sce#getTrusted\n     *\n     * @description\n     * Delegates to {@link ng.$sceDelegate#getTrusted `$sceDelegate.getTrusted`}.  As such,\n     * takes any input, and either returns a value that's safe to use in the specified context,\n     * or throws an exception. This function is aware of trusted values created by the `trustAs`\n     * function and its shorthands, and when contexts are appropriate, returns the unwrapped value\n     * as-is. Finally, this function can also throw when there is no way to turn `maybeTrusted` in a\n     * safe value (e.g., no sanitization is available or possible.)\n     *\n     * @param {string} type The context in which this value is to be used.\n     * @param {*} maybeTrusted The result of a prior {@link ng.$sce#trustAs\n     *     `$sce.trustAs`} call, or anything else (which will not be considered trusted.)\n     * @return {*} A version of the value that's safe to use in the given context, or throws an\n     *     exception if this is impossible.\n     */\n\n    /**\n     * @ngdoc method\n     * @name $sce#getTrustedHtml\n     *\n     * @description\n     * Shorthand method.  `$sce.getTrustedHtml(value)` →\n     *     {@link ng.$sceDelegate#getTrusted `$sceDelegate.getTrusted($sce.HTML, value)`}\n     *\n     * @param {*} value The value to pass to `$sce.getTrusted`.\n     * @return {*} The return value of `$sce.getTrusted($sce.HTML, value)`\n     */\n\n    /**\n     * @ngdoc method\n     * @name $sce#getTrustedCss\n     *\n     * @description\n     * Shorthand method.  `$sce.getTrustedCss(value)` →\n     *     {@link ng.$sceDelegate#getTrusted `$sceDelegate.getTrusted($sce.CSS, value)`}\n     *\n     * @param {*} value The value to pass to `$sce.getTrusted`.\n     * @return {*} The return value of `$sce.getTrusted($sce.CSS, value)`\n     */\n\n    /**\n     * @ngdoc method\n     * @name $sce#getTrustedUrl\n     *\n     * @description\n     * Shorthand method.  `$sce.getTrustedUrl(value)` →\n     *     {@link ng.$sceDelegate#getTrusted `$sceDelegate.getTrusted($sce.URL, value)`}\n     *\n     * @param {*} value The value to pass to `$sce.getTrusted`.\n     * @return {*} The return value of `$sce.getTrusted($sce.URL, value)`\n     */\n\n    /**\n     * @ngdoc method\n     * @name $sce#getTrustedResourceUrl\n     *\n     * @description\n     * Shorthand method.  `$sce.getTrustedResourceUrl(value)` →\n     *     {@link ng.$sceDelegate#getTrusted `$sceDelegate.getTrusted($sce.RESOURCE_URL, value)`}\n     *\n     * @param {*} value The value to pass to `$sceDelegate.getTrusted`.\n     * @return {*} The return value of `$sce.getTrusted($sce.RESOURCE_URL, value)`\n     */\n\n    /**\n     * @ngdoc method\n     * @name $sce#getTrustedJs\n     *\n     * @description\n     * Shorthand method.  `$sce.getTrustedJs(value)` →\n     *     {@link ng.$sceDelegate#getTrusted `$sceDelegate.getTrusted($sce.JS, value)`}\n     *\n     * @param {*} value The value to pass to `$sce.getTrusted`.\n     * @return {*} The return value of `$sce.getTrusted($sce.JS, value)`\n     */\n\n    /**\n     * @ngdoc method\n     * @name $sce#parseAsHtml\n     *\n     * @description\n     * Shorthand method.  `$sce.parseAsHtml(expression string)` →\n     *     {@link ng.$sce#parseAs `$sce.parseAs($sce.HTML, value)`}\n     *\n     * @param {string} expression String expression to compile.\n     * @return {function(context, locals)} A function which represents the compiled expression:\n     *\n     *    * `context` – `{object}` – an object against which any expressions embedded in the\n     *      strings are evaluated against (typically a scope object).\n     *    * `locals` – `{object=}` – local variables context object, useful for overriding values\n     *      in `context`.\n     */\n\n    /**\n     * @ngdoc method\n     * @name $sce#parseAsCss\n     *\n     * @description\n     * Shorthand method.  `$sce.parseAsCss(value)` →\n     *     {@link ng.$sce#parseAs `$sce.parseAs($sce.CSS, value)`}\n     *\n     * @param {string} expression String expression to compile.\n     * @return {function(context, locals)} A function which represents the compiled expression:\n     *\n     *    * `context` – `{object}` – an object against which any expressions embedded in the\n     *      strings are evaluated against (typically a scope object).\n     *    * `locals` – `{object=}` – local variables context object, useful for overriding values\n     *      in `context`.\n     */\n\n    /**\n     * @ngdoc method\n     * @name $sce#parseAsUrl\n     *\n     * @description\n     * Shorthand method.  `$sce.parseAsUrl(value)` →\n     *     {@link ng.$sce#parseAs `$sce.parseAs($sce.URL, value)`}\n     *\n     * @param {string} expression String expression to compile.\n     * @return {function(context, locals)} A function which represents the compiled expression:\n     *\n     *    * `context` – `{object}` – an object against which any expressions embedded in the\n     *      strings are evaluated against (typically a scope object).\n     *    * `locals` – `{object=}` – local variables context object, useful for overriding values\n     *      in `context`.\n     */\n\n    /**\n     * @ngdoc method\n     * @name $sce#parseAsResourceUrl\n     *\n     * @description\n     * Shorthand method.  `$sce.parseAsResourceUrl(value)` →\n     *     {@link ng.$sce#parseAs `$sce.parseAs($sce.RESOURCE_URL, value)`}\n     *\n     * @param {string} expression String expression to compile.\n     * @return {function(context, locals)} A function which represents the compiled expression:\n     *\n     *    * `context` – `{object}` – an object against which any expressions embedded in the\n     *      strings are evaluated against (typically a scope object).\n     *    * `locals` – `{object=}` – local variables context object, useful for overriding values\n     *      in `context`.\n     */\n\n    /**\n     * @ngdoc method\n     * @name $sce#parseAsJs\n     *\n     * @description\n     * Shorthand method.  `$sce.parseAsJs(value)` →\n     *     {@link ng.$sce#parseAs `$sce.parseAs($sce.JS, value)`}\n     *\n     * @param {string} expression String expression to compile.\n     * @return {function(context, locals)} A function which represents the compiled expression:\n     *\n     *    * `context` – `{object}` – an object against which any expressions embedded in the\n     *      strings are evaluated against (typically a scope object).\n     *    * `locals` – `{object=}` – local variables context object, useful for overriding values\n     *      in `context`.\n     */\n\n    // Shorthand delegations.\n    var parse = sce.parseAs,\n        getTrusted = sce.getTrusted,\n        trustAs = sce.trustAs;\n\n    forEach(SCE_CONTEXTS, function(enumValue, name) {\n      var lName = lowercase(name);\n      sce[snakeToCamel('parse_as_' + lName)] = function(expr) {\n        return parse(enumValue, expr);\n      };\n      sce[snakeToCamel('get_trusted_' + lName)] = function(value) {\n        return getTrusted(enumValue, value);\n      };\n      sce[snakeToCamel('trust_as_' + lName)] = function(value) {\n        return trustAs(enumValue, value);\n      };\n    });\n\n    return sce;\n  }];\n}\n\n/* exported $SnifferProvider */\n\n/**\n * !!! This is an undocumented \"private\" service !!!\n *\n * @name $sniffer\n * @requires $window\n * @requires $document\n * @this\n *\n * @property {boolean} history Does the browser support html5 history api ?\n * @property {boolean} transitions Does the browser support CSS transition events ?\n * @property {boolean} animations Does the browser support CSS animation events ?\n *\n * @description\n * This is very simple implementation of testing browser's features.\n */\nfunction $SnifferProvider() {\n  this.$get = ['$window', '$document', function($window, $document) {\n    var eventSupport = {},\n        // Chrome Packaged Apps are not allowed to access `history.pushState`.\n        // If not sandboxed, they can be detected by the presence of `chrome.app.runtime`\n        // (see https://developer.chrome.com/apps/api_index). If sandboxed, they can be detected by\n        // the presence of an extension runtime ID and the absence of other Chrome runtime APIs\n        // (see https://developer.chrome.com/apps/manifest/sandbox).\n        // (NW.js apps have access to Chrome APIs, but do support `history`.)\n        isNw = $window.nw && $window.nw.process,\n        isChromePackagedApp =\n            !isNw &&\n            $window.chrome &&\n            ($window.chrome.app && $window.chrome.app.runtime ||\n                !$window.chrome.app && $window.chrome.runtime && $window.chrome.runtime.id),\n        hasHistoryPushState = !isChromePackagedApp && $window.history && $window.history.pushState,\n        android =\n          toInt((/android (\\d+)/.exec(lowercase(($window.navigator || {}).userAgent)) || [])[1]),\n        boxee = /Boxee/i.test(($window.navigator || {}).userAgent),\n        document = $document[0] || {},\n        bodyStyle = document.body && document.body.style,\n        transitions = false,\n        animations = false;\n\n    if (bodyStyle) {\n      // Support: Android <5, Blackberry Browser 10, default Chrome in Android 4.4.x\n      // Mentioned browsers need a -webkit- prefix for transitions & animations.\n      transitions = !!('transition' in bodyStyle || 'webkitTransition' in bodyStyle);\n      animations = !!('animation' in bodyStyle || 'webkitAnimation' in bodyStyle);\n    }\n\n\n    return {\n      // Android has history.pushState, but it does not update location correctly\n      // so let's not use the history API at all.\n      // http://code.google.com/p/android/issues/detail?id=17471\n      // https://github.com/angular/angular.js/issues/904\n\n      // older webkit browser (533.9) on Boxee box has exactly the same problem as Android has\n      // so let's not use the history API also\n      // We are purposefully using `!(android < 4)` to cover the case when `android` is undefined\n      history: !!(hasHistoryPushState && !(android < 4) && !boxee),\n      hasEvent: function(event) {\n        // Support: IE 9-11 only\n        // IE9 implements 'input' event it's so fubared that we rather pretend that it doesn't have\n        // it. In particular the event is not fired when backspace or delete key are pressed or\n        // when cut operation is performed.\n        // IE10+ implements 'input' event but it erroneously fires under various situations,\n        // e.g. when placeholder changes, or a form is focused.\n        if (event === 'input' && msie) return false;\n\n        if (isUndefined(eventSupport[event])) {\n          var divElm = document.createElement('div');\n          eventSupport[event] = 'on' + event in divElm;\n        }\n\n        return eventSupport[event];\n      },\n      csp: csp(),\n      transitions: transitions,\n      animations: animations,\n      android: android\n    };\n  }];\n}\n\n/**\n * ! This is a private undocumented service !\n *\n * @name $$taskTrackerFactory\n * @description\n * A function to create `TaskTracker` instances.\n *\n * A `TaskTracker` can keep track of pending tasks (grouped by type) and can notify interested\n * parties when all pending tasks (or tasks of a specific type) have been completed.\n *\n * @param {$log} log - A logger instance (such as `$log`). Used to log error during callback\n *     execution.\n *\n * @this\n */\nfunction $$TaskTrackerFactoryProvider() {\n  this.$get = valueFn(function(log) { return new TaskTracker(log); });\n}\n\nfunction TaskTracker(log) {\n  var self = this;\n  var taskCounts = {};\n  var taskCallbacks = [];\n\n  var ALL_TASKS_TYPE = self.ALL_TASKS_TYPE = '$$all$$';\n  var DEFAULT_TASK_TYPE = self.DEFAULT_TASK_TYPE = '$$default$$';\n\n  /**\n   * Execute the specified function and decrement the appropriate `taskCounts` counter.\n   * If the counter reaches 0, all corresponding `taskCallbacks` are executed.\n   *\n   * @param {Function} fn - The function to execute.\n   * @param {string=} [taskType=DEFAULT_TASK_TYPE] - The type of task that is being completed.\n   */\n  self.completeTask = completeTask;\n\n  /**\n   * Increase the task count for the specified task type (or the default task type if non is\n   * specified).\n   *\n   * @param {string=} [taskType=DEFAULT_TASK_TYPE] - The type of task whose count will be increased.\n   */\n  self.incTaskCount = incTaskCount;\n\n  /**\n   * Execute the specified callback when all pending tasks have been completed.\n   *\n   * If there are no pending tasks, the callback is executed immediately. You can optionally limit\n   * the tasks that will be waited for to a specific type, by passing a `taskType`.\n   *\n   * @param {function} callback - The function to call when there are no pending tasks.\n   * @param {string=} [taskType=ALL_TASKS_TYPE] - The type of tasks that will be waited for.\n   */\n  self.notifyWhenNoPendingTasks = notifyWhenNoPendingTasks;\n\n  function completeTask(fn, taskType) {\n    taskType = taskType || DEFAULT_TASK_TYPE;\n\n    try {\n      fn();\n    } finally {\n      decTaskCount(taskType);\n\n      var countForType = taskCounts[taskType];\n      var countForAll = taskCounts[ALL_TASKS_TYPE];\n\n      // If at least one of the queues (`ALL_TASKS_TYPE` or `taskType`) is empty, run callbacks.\n      if (!countForAll || !countForType) {\n        var getNextCallback = !countForAll ? getLastCallback : getLastCallbackForType;\n        var nextCb;\n\n        while ((nextCb = getNextCallback(taskType))) {\n          try {\n            nextCb();\n          } catch (e) {\n            log.error(e);\n          }\n        }\n      }\n    }\n  }\n\n  function decTaskCount(taskType) {\n    taskType = taskType || DEFAULT_TASK_TYPE;\n    if (taskCounts[taskType]) {\n      taskCounts[taskType]--;\n      taskCounts[ALL_TASKS_TYPE]--;\n    }\n  }\n\n  function getLastCallback() {\n    var cbInfo = taskCallbacks.pop();\n    return cbInfo && cbInfo.cb;\n  }\n\n  function getLastCallbackForType(taskType) {\n    for (var i = taskCallbacks.length - 1; i >= 0; --i) {\n      var cbInfo = taskCallbacks[i];\n      if (cbInfo.type === taskType) {\n        taskCallbacks.splice(i, 1);\n        return cbInfo.cb;\n      }\n    }\n  }\n\n  function incTaskCount(taskType) {\n    taskType = taskType || DEFAULT_TASK_TYPE;\n    taskCounts[taskType] = (taskCounts[taskType] || 0) + 1;\n    taskCounts[ALL_TASKS_TYPE] = (taskCounts[ALL_TASKS_TYPE] || 0) + 1;\n  }\n\n  function notifyWhenNoPendingTasks(callback, taskType) {\n    taskType = taskType || ALL_TASKS_TYPE;\n    if (!taskCounts[taskType]) {\n      callback();\n    } else {\n      taskCallbacks.push({type: taskType, cb: callback});\n    }\n  }\n}\n\nvar $templateRequestMinErr = minErr('$templateRequest');\n\n/**\n * @ngdoc provider\n * @name $templateRequestProvider\n * @this\n *\n * @description\n * Used to configure the options passed to the {@link $http} service when making a template request.\n *\n * For example, it can be used for specifying the \"Accept\" header that is sent to the server, when\n * requesting a template.\n */\nfunction $TemplateRequestProvider() {\n\n  var httpOptions;\n\n  /**\n   * @ngdoc method\n   * @name $templateRequestProvider#httpOptions\n   * @description\n   * The options to be passed to the {@link $http} service when making the request.\n   * You can use this to override options such as the \"Accept\" header for template requests.\n   *\n   * The {@link $templateRequest} will set the `cache` and the `transformResponse` properties of the\n   * options if not overridden here.\n   *\n   * @param {string=} value new value for the {@link $http} options.\n   * @returns {string|self} Returns the {@link $http} options when used as getter and self if used as setter.\n   */\n  this.httpOptions = function(val) {\n    if (val) {\n      httpOptions = val;\n      return this;\n    }\n    return httpOptions;\n  };\n\n  /**\n   * @ngdoc service\n   * @name $templateRequest\n   *\n   * @description\n   * The `$templateRequest` service runs security checks then downloads the provided template using\n   * `$http` and, upon success, stores the contents inside of `$templateCache`. If the HTTP request\n   * fails or the response data of the HTTP request is empty, a `$compile` error will be thrown (the\n   * exception can be thwarted by setting the 2nd parameter of the function to true). Note that the\n   * contents of `$templateCache` are trusted, so the call to `$sce.getTrustedUrl(tpl)` is omitted\n   * when `tpl` is of type string and `$templateCache` has the matching entry.\n   *\n   * If you want to pass custom options to the `$http` service, such as setting the Accept header you\n   * can configure this via {@link $templateRequestProvider#httpOptions}.\n   *\n   * `$templateRequest` is used internally by {@link $compile}, {@link ngRoute.$route}, and directives such\n   * as {@link ngInclude} to download and cache templates.\n   *\n   * 3rd party modules should use `$templateRequest` if their services or directives are loading\n   * templates.\n   *\n   * @param {string|TrustedResourceUrl} tpl The HTTP request template URL\n   * @param {boolean=} ignoreRequestError Whether or not to ignore the exception when the request fails or the template is empty\n   *\n   * @return {Promise} a promise for the HTTP response data of the given URL.\n   *\n   * @property {number} totalPendingRequests total amount of pending template requests being downloaded.\n   */\n  this.$get = ['$exceptionHandler', '$templateCache', '$http', '$q', '$sce',\n    function($exceptionHandler, $templateCache, $http, $q, $sce) {\n\n      function handleRequestFn(tpl, ignoreRequestError) {\n        handleRequestFn.totalPendingRequests++;\n\n        // We consider the template cache holds only trusted templates, so\n        // there's no need to go through adding the template again to the trusted\n        // resources for keys that already are included in there. This also makes\n        // AngularJS accept any script directive, no matter its name. However, we\n        // still need to unwrap trusted types.\n        if (!isString(tpl) || isUndefined($templateCache.get(tpl))) {\n          tpl = $sce.getTrustedResourceUrl(tpl);\n        }\n\n        var transformResponse = $http.defaults && $http.defaults.transformResponse;\n\n        if (isArray(transformResponse)) {\n          transformResponse = transformResponse.filter(function(transformer) {\n            return transformer !== defaultHttpResponseTransform;\n          });\n        } else if (transformResponse === defaultHttpResponseTransform) {\n          transformResponse = null;\n        }\n\n        return $http.get(tpl, extend({\n            cache: $templateCache,\n            transformResponse: transformResponse\n          }, httpOptions))\n          .finally(function() {\n            handleRequestFn.totalPendingRequests--;\n          })\n          .then(function(response) {\n            return $templateCache.put(tpl, response.data);\n          }, handleError);\n\n        function handleError(resp) {\n          if (!ignoreRequestError) {\n            resp = $templateRequestMinErr('tpload',\n                'Failed to load template: {0} (HTTP status: {1} {2})',\n                tpl, resp.status, resp.statusText);\n\n            $exceptionHandler(resp);\n          }\n\n          return $q.reject(resp);\n        }\n      }\n\n      handleRequestFn.totalPendingRequests = 0;\n\n      return handleRequestFn;\n    }\n  ];\n}\n\n/** @this */\nfunction $$TestabilityProvider() {\n  this.$get = ['$rootScope', '$browser', '$location',\n       function($rootScope,   $browser,   $location) {\n\n    /**\n     * @name $testability\n     *\n     * @description\n     * The private $$testability service provides a collection of methods for use when debugging\n     * or by automated test and debugging tools.\n     */\n    var testability = {};\n\n    /**\n     * @name $$testability#findBindings\n     *\n     * @description\n     * Returns an array of elements that are bound (via ng-bind or {{}})\n     * to expressions matching the input.\n     *\n     * @param {Element} element The element root to search from.\n     * @param {string} expression The binding expression to match.\n     * @param {boolean} opt_exactMatch If true, only returns exact matches\n     *     for the expression. Filters and whitespace are ignored.\n     */\n    testability.findBindings = function(element, expression, opt_exactMatch) {\n      var bindings = element.getElementsByClassName('ng-binding');\n      var matches = [];\n      forEach(bindings, function(binding) {\n        var dataBinding = angular.element(binding).data('$binding');\n        if (dataBinding) {\n          forEach(dataBinding, function(bindingName) {\n            if (opt_exactMatch) {\n              var matcher = new RegExp('(^|\\\\s)' + escapeForRegexp(expression) + '(\\\\s|\\\\||$)');\n              if (matcher.test(bindingName)) {\n                matches.push(binding);\n              }\n            } else {\n              if (bindingName.indexOf(expression) !== -1) {\n                matches.push(binding);\n              }\n            }\n          });\n        }\n      });\n      return matches;\n    };\n\n    /**\n     * @name $$testability#findModels\n     *\n     * @description\n     * Returns an array of elements that are two-way found via ng-model to\n     * expressions matching the input.\n     *\n     * @param {Element} element The element root to search from.\n     * @param {string} expression The model expression to match.\n     * @param {boolean} opt_exactMatch If true, only returns exact matches\n     *     for the expression.\n     */\n    testability.findModels = function(element, expression, opt_exactMatch) {\n      var prefixes = ['ng-', 'data-ng-', 'ng\\\\:'];\n      for (var p = 0; p < prefixes.length; ++p) {\n        var attributeEquals = opt_exactMatch ? '=' : '*=';\n        var selector = '[' + prefixes[p] + 'model' + attributeEquals + '\"' + expression + '\"]';\n        var elements = element.querySelectorAll(selector);\n        if (elements.length) {\n          return elements;\n        }\n      }\n    };\n\n    /**\n     * @name $$testability#getLocation\n     *\n     * @description\n     * Shortcut for getting the location in a browser agnostic way. Returns\n     *     the path, search, and hash. (e.g. /path?a=b#hash)\n     */\n    testability.getLocation = function() {\n      return $location.url();\n    };\n\n    /**\n     * @name $$testability#setLocation\n     *\n     * @description\n     * Shortcut for navigating to a location without doing a full page reload.\n     *\n     * @param {string} url The location url (path, search and hash,\n     *     e.g. /path?a=b#hash) to go to.\n     */\n    testability.setLocation = function(url) {\n      if (url !== $location.url()) {\n        $location.url(url);\n        $rootScope.$digest();\n      }\n    };\n\n    /**\n     * @name $$testability#whenStable\n     *\n     * @description\n     * Calls the callback when all pending tasks are completed.\n     *\n     * Types of tasks waited for include:\n     * - Pending timeouts (via {@link $timeout}).\n     * - Pending HTTP requests (via {@link $http}).\n     * - In-progress route transitions (via {@link $route}).\n     * - Pending tasks scheduled via {@link $rootScope#$applyAsync}.\n     * - Pending tasks scheduled via {@link $rootScope#$evalAsync}.\n     *   These include tasks scheduled via `$evalAsync()` indirectly (such as {@link $q} promises).\n     *\n     * @param {function} callback\n     */\n    testability.whenStable = function(callback) {\n      $browser.notifyWhenNoOutstandingRequests(callback);\n    };\n\n    return testability;\n  }];\n}\n\nvar $timeoutMinErr = minErr('$timeout');\n\n/** @this */\nfunction $TimeoutProvider() {\n  this.$get = ['$rootScope', '$browser', '$q', '$$q', '$exceptionHandler',\n       function($rootScope,   $browser,   $q,   $$q,   $exceptionHandler) {\n\n    var deferreds = {};\n\n\n    /**\n     * @ngdoc service\n     * @name $timeout\n     *\n     * @description\n     * AngularJS's wrapper for `window.setTimeout`. The `fn` function is wrapped into a try/catch\n     * block and delegates any exceptions to\n     * {@link ng.$exceptionHandler $exceptionHandler} service.\n     *\n     * The return value of calling `$timeout` is a promise, which will be resolved when\n     * the delay has passed and the timeout function, if provided, is executed.\n     *\n     * To cancel a timeout request, call `$timeout.cancel(promise)`.\n     *\n     * In tests you can use {@link ngMock.$timeout `$timeout.flush()`} to\n     * synchronously flush the queue of deferred functions.\n     *\n     * If you only want a promise that will be resolved after some specified delay\n     * then you can call `$timeout` without the `fn` function.\n     *\n     * @param {function()=} fn A function, whose execution should be delayed.\n     * @param {number=} [delay=0] Delay in milliseconds.\n     * @param {boolean=} [invokeApply=true] If set to `false` skips model dirty checking, otherwise\n     *   will invoke `fn` within the {@link ng.$rootScope.Scope#$apply $apply} block.\n     * @param {...*=} Pass additional parameters to the executed function.\n     * @returns {Promise} Promise that will be resolved when the timeout is reached. The promise\n     *   will be resolved with the return value of the `fn` function.\n     *\n     */\n    function timeout(fn, delay, invokeApply) {\n      if (!isFunction(fn)) {\n        invokeApply = delay;\n        delay = fn;\n        fn = noop;\n      }\n\n      var args = sliceArgs(arguments, 3),\n          skipApply = (isDefined(invokeApply) && !invokeApply),\n          deferred = (skipApply ? $$q : $q).defer(),\n          promise = deferred.promise,\n          timeoutId;\n\n      timeoutId = $browser.defer(function() {\n        try {\n          deferred.resolve(fn.apply(null, args));\n        } catch (e) {\n          deferred.reject(e);\n          $exceptionHandler(e);\n        } finally {\n          delete deferreds[promise.$$timeoutId];\n        }\n\n        if (!skipApply) $rootScope.$apply();\n      }, delay, '$timeout');\n\n      promise.$$timeoutId = timeoutId;\n      deferreds[timeoutId] = deferred;\n\n      return promise;\n    }\n\n\n    /**\n     * @ngdoc method\n     * @name $timeout#cancel\n     *\n     * @description\n     * Cancels a task associated with the `promise`. As a result of this, the promise will be\n     * resolved with a rejection.\n     *\n     * @param {Promise=} promise Promise returned by the `$timeout` function.\n     * @returns {boolean} Returns `true` if the task hasn't executed yet and was successfully\n     *   canceled.\n     */\n    timeout.cancel = function(promise) {\n      if (!promise) return false;\n\n      if (!promise.hasOwnProperty('$$timeoutId')) {\n        throw $timeoutMinErr('badprom',\n            '`$timeout.cancel()` called with a promise that was not generated by `$timeout()`.');\n      }\n\n      if (!deferreds.hasOwnProperty(promise.$$timeoutId)) return false;\n\n      var id = promise.$$timeoutId;\n      var deferred = deferreds[id];\n\n      // Timeout cancels should not report an unhandled promise.\n      markQExceptionHandled(deferred.promise);\n      deferred.reject('canceled');\n      delete deferreds[id];\n\n      return $browser.defer.cancel(id);\n    };\n\n    return timeout;\n  }];\n}\n\n// NOTE:  The usage of window and document instead of $window and $document here is\n// deliberate.  This service depends on the specific behavior of anchor nodes created by the\n// browser (resolving and parsing URLs) that is unlikely to be provided by mock objects and\n// cause us to break tests.  In addition, when the browser resolves a URL for XHR, it\n// doesn't know about mocked locations and resolves URLs to the real document - which is\n// exactly the behavior needed here.  There is little value is mocking these out for this\n// service.\nvar urlParsingNode = window.document.createElement('a');\nvar originUrl = urlResolve(window.location.href);\nvar baseUrlParsingNode;\n\nurlParsingNode.href = 'http://[::1]';\n\n// Support: IE 9-11 only, Edge 16-17 only (fixed in 18 Preview)\n// IE/Edge don't wrap IPv6 addresses' hostnames in square brackets\n// when parsed out of an anchor element.\nvar ipv6InBrackets = urlParsingNode.hostname === '[::1]';\n\n/**\n *\n * Implementation Notes for non-IE browsers\n * ----------------------------------------\n * Assigning a URL to the href property of an anchor DOM node, even one attached to the DOM,\n * results both in the normalizing and parsing of the URL.  Normalizing means that a relative\n * URL will be resolved into an absolute URL in the context of the application document.\n * Parsing means that the anchor node's host, hostname, protocol, port, pathname and related\n * properties are all populated to reflect the normalized URL.  This approach has wide\n * compatibility - Safari 1+, Mozilla 1+ etc.  See\n * http://www.aptana.com/reference/html/api/HTMLAnchorElement.html\n *\n * Implementation Notes for IE\n * ---------------------------\n * IE <= 10 normalizes the URL when assigned to the anchor node similar to the other\n * browsers.  However, the parsed components will not be set if the URL assigned did not specify\n * them.  (e.g. if you assign a.href = \"foo\", then a.protocol, a.host, etc. will be empty.)  We\n * work around that by performing the parsing in a 2nd step by taking a previously normalized\n * URL (e.g. by assigning to a.href) and assigning it a.href again.  This correctly populates the\n * properties such as protocol, hostname, port, etc.\n *\n * References:\n *   http://developer.mozilla.org/en-US/docs/Web/API/HTMLAnchorElement\n *   http://www.aptana.com/reference/html/api/HTMLAnchorElement.html\n *   http://url.spec.whatwg.org/#urlutils\n *   https://github.com/angular/angular.js/pull/2902\n *   http://james.padolsey.com/javascript/parsing-urls-with-the-dom/\n *\n * @kind function\n * @param {string|object} url The URL to be parsed. If `url` is not a string, it will be returned\n *     unchanged.\n * @description Normalizes and parses a URL.\n * @returns {object} Returns the normalized URL as a dictionary.\n *\n *   | member name   | Description                                                            |\n *   |---------------|------------------------------------------------------------------------|\n *   | href          | A normalized version of the provided URL if it was not an absolute URL |\n *   | protocol      | The protocol without the trailing colon                                |\n *   | host          | The host and port (if the port is non-default) of the normalizedUrl    |\n *   | search        | The search params, minus the question mark                             |\n *   | hash          | The hash string, minus the hash symbol                                 |\n *   | hostname      | The hostname                                                           |\n *   | port          | The port, without \":\"                                                  |\n *   | pathname      | The pathname, beginning with \"/\"                                       |\n *\n */\nfunction urlResolve(url) {\n  if (!isString(url)) return url;\n\n  var href = url;\n\n  // Support: IE 9-11 only\n  if (msie) {\n    // Normalize before parse.  Refer Implementation Notes on why this is\n    // done in two steps on IE.\n    urlParsingNode.setAttribute('href', href);\n    href = urlParsingNode.href;\n  }\n\n  urlParsingNode.setAttribute('href', href);\n\n  var hostname = urlParsingNode.hostname;\n\n  if (!ipv6InBrackets && hostname.indexOf(':') > -1) {\n    hostname = '[' + hostname + ']';\n  }\n\n  return {\n    href: urlParsingNode.href,\n    protocol: urlParsingNode.protocol ? urlParsingNode.protocol.replace(/:$/, '') : '',\n    host: urlParsingNode.host,\n    search: urlParsingNode.search ? urlParsingNode.search.replace(/^\\?/, '') : '',\n    hash: urlParsingNode.hash ? urlParsingNode.hash.replace(/^#/, '') : '',\n    hostname: hostname,\n    port: urlParsingNode.port,\n    pathname: (urlParsingNode.pathname.charAt(0) === '/')\n      ? urlParsingNode.pathname\n      : '/' + urlParsingNode.pathname\n  };\n}\n\n/**\n * Parse a request URL and determine whether this is a same-origin request as the application\n * document.\n *\n * @param {string|object} requestUrl The url of the request as a string that will be resolved\n * or a parsed URL object.\n * @returns {boolean} Whether the request is for the same origin as the application document.\n */\nfunction urlIsSameOrigin(requestUrl) {\n  return urlsAreSameOrigin(requestUrl, originUrl);\n}\n\n/**\n * Parse a request URL and determine whether it is same-origin as the current document base URL.\n *\n * Note: The base URL is usually the same as the document location (`location.href`) but can\n * be overriden by using the `<base>` tag.\n *\n * @param {string|object} requestUrl The url of the request as a string that will be resolved\n * or a parsed URL object.\n * @returns {boolean} Whether the URL is same-origin as the document base URL.\n */\nfunction urlIsSameOriginAsBaseUrl(requestUrl) {\n  return urlsAreSameOrigin(requestUrl, getBaseUrl());\n}\n\n/**\n * Create a function that can check a URL's origin against a list of allowed/trusted origins.\n * The current location's origin is implicitly trusted.\n *\n * @param {string[]} trustedOriginUrls - A list of URLs (strings), whose origins are trusted.\n *\n * @returns {Function} - A function that receives a URL (string or parsed URL object) and returns\n *     whether it is of an allowed origin.\n */\nfunction urlIsAllowedOriginFactory(trustedOriginUrls) {\n  var parsedAllowedOriginUrls = [originUrl].concat(trustedOriginUrls.map(urlResolve));\n\n  /**\n   * Check whether the specified URL (string or parsed URL object) has an origin that is allowed\n   * based on a list of trusted-origin URLs. The current location's origin is implicitly\n   * trusted.\n   *\n   * @param {string|Object} requestUrl - The URL to be checked (provided as a string that will be\n   *     resolved or a parsed URL object).\n   *\n   * @returns {boolean} - Whether the specified URL is of an allowed origin.\n   */\n  return function urlIsAllowedOrigin(requestUrl) {\n    var parsedUrl = urlResolve(requestUrl);\n    return parsedAllowedOriginUrls.some(urlsAreSameOrigin.bind(null, parsedUrl));\n  };\n}\n\n/**\n * Determine if two URLs share the same origin.\n *\n * @param {string|Object} url1 - First URL to compare as a string or a normalized URL in the form of\n *     a dictionary object returned by `urlResolve()`.\n * @param {string|object} url2 - Second URL to compare as a string or a normalized URL in the form\n *     of a dictionary object returned by `urlResolve()`.\n *\n * @returns {boolean} - True if both URLs have the same origin, and false otherwise.\n */\nfunction urlsAreSameOrigin(url1, url2) {\n  url1 = urlResolve(url1);\n  url2 = urlResolve(url2);\n\n  return (url1.protocol === url2.protocol &&\n          url1.host === url2.host);\n}\n\n/**\n * Returns the current document base URL.\n * @returns {string}\n */\nfunction getBaseUrl() {\n  if (window.document.baseURI) {\n    return window.document.baseURI;\n  }\n\n  // `document.baseURI` is available everywhere except IE\n  if (!baseUrlParsingNode) {\n    baseUrlParsingNode = window.document.createElement('a');\n    baseUrlParsingNode.href = '.';\n\n    // Work-around for IE bug described in Implementation Notes. The fix in `urlResolve()` is not\n    // suitable here because we need to track changes to the base URL.\n    baseUrlParsingNode = baseUrlParsingNode.cloneNode(false);\n  }\n  return baseUrlParsingNode.href;\n}\n\n/**\n * @ngdoc service\n * @name $window\n * @this\n *\n * @description\n * A reference to the browser's `window` object. While `window`\n * is globally available in JavaScript, it causes testability problems, because\n * it is a global variable. In AngularJS we always refer to it through the\n * `$window` service, so it may be overridden, removed or mocked for testing.\n *\n * Expressions, like the one defined for the `ngClick` directive in the example\n * below, are evaluated with respect to the current scope.  Therefore, there is\n * no risk of inadvertently coding in a dependency on a global value in such an\n * expression.\n *\n * @example\n   <example module=\"windowExample\" name=\"window-service\">\n     <file name=\"index.html\">\n       <script>\n         angular.module('windowExample', [])\n           .controller('ExampleController', ['$scope', '$window', function($scope, $window) {\n             $scope.greeting = 'Hello, World!';\n             $scope.doGreeting = function(greeting) {\n               $window.alert(greeting);\n             };\n           }]);\n       </script>\n       <div ng-controller=\"ExampleController\">\n         <input type=\"text\" ng-model=\"greeting\" aria-label=\"greeting\" />\n         <button ng-click=\"doGreeting(greeting)\">ALERT</button>\n       </div>\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n      it('should display the greeting in the input box', function() {\n       element(by.model('greeting')).sendKeys('Hello, E2E Tests');\n       // If we click the button it will block the test runner\n       // element(':button').click();\n      });\n     </file>\n   </example>\n */\nfunction $WindowProvider() {\n  this.$get = valueFn(window);\n}\n\n/**\n * @name $$cookieReader\n * @requires $document\n *\n * @description\n * This is a private service for reading cookies used by $http and ngCookies\n *\n * @return {Object} a key/value map of the current cookies\n */\nfunction $$CookieReader($document) {\n  var rawDocument = $document[0] || {};\n  var lastCookies = {};\n  var lastCookieString = '';\n\n  function safeGetCookie(rawDocument) {\n    try {\n      return rawDocument.cookie || '';\n    } catch (e) {\n      return '';\n    }\n  }\n\n  function safeDecodeURIComponent(str) {\n    try {\n      return decodeURIComponent(str);\n    } catch (e) {\n      return str;\n    }\n  }\n\n  return function() {\n    var cookieArray, cookie, i, index, name;\n    var currentCookieString = safeGetCookie(rawDocument);\n\n    if (currentCookieString !== lastCookieString) {\n      lastCookieString = currentCookieString;\n      cookieArray = lastCookieString.split('; ');\n      lastCookies = {};\n\n      for (i = 0; i < cookieArray.length; i++) {\n        cookie = cookieArray[i];\n        index = cookie.indexOf('=');\n        if (index > 0) { //ignore nameless cookies\n          name = safeDecodeURIComponent(cookie.substring(0, index));\n          // the first value that is seen for a cookie is the most\n          // specific one.  values for the same cookie name that\n          // follow are for less specific paths.\n          if (isUndefined(lastCookies[name])) {\n            lastCookies[name] = safeDecodeURIComponent(cookie.substring(index + 1));\n          }\n        }\n      }\n    }\n    return lastCookies;\n  };\n}\n\n$$CookieReader.$inject = ['$document'];\n\n/** @this */\nfunction $$CookieReaderProvider() {\n  this.$get = $$CookieReader;\n}\n\n/* global currencyFilter: true,\n dateFilter: true,\n filterFilter: true,\n jsonFilter: true,\n limitToFilter: true,\n lowercaseFilter: true,\n numberFilter: true,\n orderByFilter: true,\n uppercaseFilter: true,\n */\n\n/**\n * @ngdoc provider\n * @name $filterProvider\n * @description\n *\n * Filters are just functions which transform input to an output. However filters need to be\n * Dependency Injected. To achieve this a filter definition consists of a factory function which is\n * annotated with dependencies and is responsible for creating a filter function.\n *\n * <div class=\"alert alert-warning\">\n * **Note:** Filter names must be valid AngularJS {@link expression} identifiers, such as `uppercase` or `orderBy`.\n * Names with special characters, such as hyphens and dots, are not allowed. If you wish to namespace\n * your filters, then you can use capitalization (`myappSubsectionFilterx`) or underscores\n * (`myapp_subsection_filterx`).\n * </div>\n *\n * ```js\n *   // Filter registration\n *   function MyModule($provide, $filterProvider) {\n *     // create a service to demonstrate injection (not always needed)\n *     $provide.value('greet', function(name){\n *       return 'Hello ' + name + '!';\n *     });\n *\n *     // register a filter factory which uses the\n *     // greet service to demonstrate DI.\n *     $filterProvider.register('greet', function(greet){\n *       // return the filter function which uses the greet service\n *       // to generate salutation\n *       return function(text) {\n *         // filters need to be forgiving so check input validity\n *         return text && greet(text) || text;\n *       };\n *     });\n *   }\n * ```\n *\n * The filter function is registered with the `$injector` under the filter name suffix with\n * `Filter`.\n *\n * ```js\n *   it('should be the same instance', inject(\n *     function($filterProvider) {\n *       $filterProvider.register('reverse', function(){\n *         return ...;\n *       });\n *     },\n *     function($filter, reverseFilter) {\n *       expect($filter('reverse')).toBe(reverseFilter);\n *     });\n * ```\n *\n *\n * For more information about how AngularJS filters work, and how to create your own filters, see\n * {@link guide/filter Filters} in the AngularJS Developer Guide.\n */\n\n/**\n * @ngdoc service\n * @name $filter\n * @kind function\n * @description\n * Filters are used for formatting data displayed to the user.\n *\n * They can be used in view templates, controllers or services. AngularJS comes\n * with a collection of [built-in filters](api/ng/filter), but it is easy to\n * define your own as well.\n *\n * The general syntax in templates is as follows:\n *\n * ```html\n * {{ expression [| filter_name[:parameter_value] ... ] }}\n * ```\n *\n * @param {String} name Name of the filter function to retrieve\n * @return {Function} the filter function\n * @example\n   <example name=\"$filter\" module=\"filterExample\">\n     <file name=\"index.html\">\n       <div ng-controller=\"MainCtrl\">\n        <h3>{{ originalText }}</h3>\n        <h3>{{ filteredText }}</h3>\n       </div>\n     </file>\n\n     <file name=\"script.js\">\n      angular.module('filterExample', [])\n      .controller('MainCtrl', function($scope, $filter) {\n        $scope.originalText = 'hello';\n        $scope.filteredText = $filter('uppercase')($scope.originalText);\n      });\n     </file>\n   </example>\n  */\n$FilterProvider.$inject = ['$provide'];\n/** @this */\nfunction $FilterProvider($provide) {\n  var suffix = 'Filter';\n\n  /**\n   * @ngdoc method\n   * @name $filterProvider#register\n   * @param {string|Object} name Name of the filter function, or an object map of filters where\n   *    the keys are the filter names and the values are the filter factories.\n   *\n   *    <div class=\"alert alert-warning\">\n   *    **Note:** Filter names must be valid AngularJS {@link expression} identifiers, such as `uppercase` or `orderBy`.\n   *    Names with special characters, such as hyphens and dots, are not allowed. If you wish to namespace\n   *    your filters, then you can use capitalization (`myappSubsectionFilterx`) or underscores\n   *    (`myapp_subsection_filterx`).\n   *    </div>\n    * @param {Function} factory If the first argument was a string, a factory function for the filter to be registered.\n   * @returns {Object} Registered filter instance, or if a map of filters was provided then a map\n   *    of the registered filter instances.\n   */\n  function register(name, factory) {\n    if (isObject(name)) {\n      var filters = {};\n      forEach(name, function(filter, key) {\n        filters[key] = register(key, filter);\n      });\n      return filters;\n    } else {\n      return $provide.factory(name + suffix, factory);\n    }\n  }\n  this.register = register;\n\n  this.$get = ['$injector', function($injector) {\n    return function(name) {\n      return $injector.get(name + suffix);\n    };\n  }];\n\n  ////////////////////////////////////////\n\n  /* global\n    currencyFilter: false,\n    dateFilter: false,\n    filterFilter: false,\n    jsonFilter: false,\n    limitToFilter: false,\n    lowercaseFilter: false,\n    numberFilter: false,\n    orderByFilter: false,\n    uppercaseFilter: false\n  */\n\n  register('currency', currencyFilter);\n  register('date', dateFilter);\n  register('filter', filterFilter);\n  register('json', jsonFilter);\n  register('limitTo', limitToFilter);\n  register('lowercase', lowercaseFilter);\n  register('number', numberFilter);\n  register('orderBy', orderByFilter);\n  register('uppercase', uppercaseFilter);\n}\n\n/**\n * @ngdoc filter\n * @name filter\n * @kind function\n *\n * @description\n * Selects a subset of items from `array` and returns it as a new array.\n *\n * @param {Array} array The source array.\n * <div class=\"alert alert-info\">\n *   **Note**: If the array contains objects that reference themselves, filtering is not possible.\n * </div>\n * @param {string|Object|function()} expression The predicate to be used for selecting items from\n *   `array`.\n *\n *   Can be one of:\n *\n *   - `string`: The string is used for matching against the contents of the `array`. All strings or\n *     objects with string properties in `array` that match this string will be returned. This also\n *     applies to nested object properties.\n *     The predicate can be negated by prefixing the string with `!`.\n *\n *   - `Object`: A pattern object can be used to filter specific properties on objects contained\n *     by `array`. For example `{name:\"M\", phone:\"1\"}` predicate will return an array of items\n *     which have property `name` containing \"M\" and property `phone` containing \"1\". A special\n *     property name (`$` by default) can be used (e.g. as in `{$: \"text\"}`) to accept a match\n *     against any property of the object or its nested object properties. That's equivalent to the\n *     simple substring match with a `string` as described above. The special property name can be\n *     overwritten, using the `anyPropertyKey` parameter.\n *     The predicate can be negated by prefixing the string with `!`.\n *     For example `{name: \"!M\"}` predicate will return an array of items which have property `name`\n *     not containing \"M\".\n *\n *     Note that a named property will match properties on the same level only, while the special\n *     `$` property will match properties on the same level or deeper. E.g. an array item like\n *     `{name: {first: 'John', last: 'Doe'}}` will **not** be matched by `{name: 'John'}`, but\n *     **will** be matched by `{$: 'John'}`.\n *\n *   - `function(value, index, array)`: A predicate function can be used to write arbitrary filters.\n *     The function is called for each element of the array, with the element, its index, and\n *     the entire array itself as arguments.\n *\n *     The final result is an array of those elements that the predicate returned true for.\n *\n * @param {function(actual, expected)|true|false} [comparator] Comparator which is used in\n *     determining if values retrieved using `expression` (when it is not a function) should be\n *     considered a match based on the expected value (from the filter expression) and actual\n *     value (from the object in the array).\n *\n *   Can be one of:\n *\n *   - `function(actual, expected)`:\n *     The function will be given the object value and the predicate value to compare and\n *     should return true if both values should be considered equal.\n *\n *   - `true`: A shorthand for `function(actual, expected) { return angular.equals(actual, expected)}`.\n *     This is essentially strict comparison of expected and actual.\n *\n *   - `false`: A short hand for a function which will look for a substring match in a case\n *     insensitive way. Primitive values are converted to strings. Objects are not compared against\n *     primitives, unless they have a custom `toString` method (e.g. `Date` objects).\n *\n *\n *   Defaults to `false`.\n *\n * @param {string} [anyPropertyKey] The special property name that matches against any property.\n *     By default `$`.\n *\n * @example\n   <example name=\"filter-filter\">\n     <file name=\"index.html\">\n       <div ng-init=\"friends = [{name:'John', phone:'555-1276'},\n                                {name:'Mary', phone:'800-BIG-MARY'},\n                                {name:'Mike', phone:'555-4321'},\n                                {name:'Adam', phone:'555-5678'},\n                                {name:'Julie', phone:'555-8765'},\n                                {name:'Juliette', phone:'555-5678'}]\"></div>\n\n       <label>Search: <input ng-model=\"searchText\"></label>\n       <table id=\"searchTextResults\">\n         <tr><th>Name</th><th>Phone</th></tr>\n         <tr ng-repeat=\"friend in friends | filter:searchText\">\n           <td>{{friend.name}}</td>\n           <td>{{friend.phone}}</td>\n         </tr>\n       </table>\n       <hr>\n       <label>Any: <input ng-model=\"search.$\"></label> <br>\n       <label>Name only <input ng-model=\"search.name\"></label><br>\n       <label>Phone only <input ng-model=\"search.phone\"></label><br>\n       <label>Equality <input type=\"checkbox\" ng-model=\"strict\"></label><br>\n       <table id=\"searchObjResults\">\n         <tr><th>Name</th><th>Phone</th></tr>\n         <tr ng-repeat=\"friendObj in friends | filter:search:strict\">\n           <td>{{friendObj.name}}</td>\n           <td>{{friendObj.phone}}</td>\n         </tr>\n       </table>\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       var expectFriendNames = function(expectedNames, key) {\n         element.all(by.repeater(key + ' in friends').column(key + '.name')).then(function(arr) {\n           arr.forEach(function(wd, i) {\n             expect(wd.getText()).toMatch(expectedNames[i]);\n           });\n         });\n       };\n\n       it('should search across all fields when filtering with a string', function() {\n         var searchText = element(by.model('searchText'));\n         searchText.clear();\n         searchText.sendKeys('m');\n         expectFriendNames(['Mary', 'Mike', 'Adam'], 'friend');\n\n         searchText.clear();\n         searchText.sendKeys('76');\n         expectFriendNames(['John', 'Julie'], 'friend');\n       });\n\n       it('should search in specific fields when filtering with a predicate object', function() {\n         var searchAny = element(by.model('search.$'));\n         searchAny.clear();\n         searchAny.sendKeys('i');\n         expectFriendNames(['Mary', 'Mike', 'Julie', 'Juliette'], 'friendObj');\n       });\n       it('should use a equal comparison when comparator is true', function() {\n         var searchName = element(by.model('search.name'));\n         var strict = element(by.model('strict'));\n         searchName.clear();\n         searchName.sendKeys('Julie');\n         strict.click();\n         expectFriendNames(['Julie'], 'friendObj');\n       });\n     </file>\n   </example>\n */\n\nfunction filterFilter() {\n  return function(array, expression, comparator, anyPropertyKey) {\n    if (!isArrayLike(array)) {\n      if (array == null) {\n        return array;\n      } else {\n        throw minErr('filter')('notarray', 'Expected array but received: {0}', array);\n      }\n    }\n\n    anyPropertyKey = anyPropertyKey || '$';\n    var expressionType = getTypeForFilter(expression);\n    var predicateFn;\n    var matchAgainstAnyProp;\n\n    switch (expressionType) {\n      case 'function':\n        predicateFn = expression;\n        break;\n      case 'boolean':\n      case 'null':\n      case 'number':\n      case 'string':\n        matchAgainstAnyProp = true;\n        // falls through\n      case 'object':\n        predicateFn = createPredicateFn(expression, comparator, anyPropertyKey, matchAgainstAnyProp);\n        break;\n      default:\n        return array;\n    }\n\n    return Array.prototype.filter.call(array, predicateFn);\n  };\n}\n\n// Helper functions for `filterFilter`\nfunction createPredicateFn(expression, comparator, anyPropertyKey, matchAgainstAnyProp) {\n  var shouldMatchPrimitives = isObject(expression) && (anyPropertyKey in expression);\n  var predicateFn;\n\n  if (comparator === true) {\n    comparator = equals;\n  } else if (!isFunction(comparator)) {\n    comparator = function(actual, expected) {\n      if (isUndefined(actual)) {\n        // No substring matching against `undefined`\n        return false;\n      }\n      if ((actual === null) || (expected === null)) {\n        // No substring matching against `null`; only match against `null`\n        return actual === expected;\n      }\n      if (isObject(expected) || (isObject(actual) && !hasCustomToString(actual))) {\n        // Should not compare primitives against objects, unless they have custom `toString` method\n        return false;\n      }\n\n      actual = lowercase('' + actual);\n      expected = lowercase('' + expected);\n      return actual.indexOf(expected) !== -1;\n    };\n  }\n\n  predicateFn = function(item) {\n    if (shouldMatchPrimitives && !isObject(item)) {\n      return deepCompare(item, expression[anyPropertyKey], comparator, anyPropertyKey, false);\n    }\n    return deepCompare(item, expression, comparator, anyPropertyKey, matchAgainstAnyProp);\n  };\n\n  return predicateFn;\n}\n\nfunction deepCompare(actual, expected, comparator, anyPropertyKey, matchAgainstAnyProp, dontMatchWholeObject) {\n  var actualType = getTypeForFilter(actual);\n  var expectedType = getTypeForFilter(expected);\n\n  if ((expectedType === 'string') && (expected.charAt(0) === '!')) {\n    return !deepCompare(actual, expected.substring(1), comparator, anyPropertyKey, matchAgainstAnyProp);\n  } else if (isArray(actual)) {\n    // In case `actual` is an array, consider it a match\n    // if ANY of it's items matches `expected`\n    return actual.some(function(item) {\n      return deepCompare(item, expected, comparator, anyPropertyKey, matchAgainstAnyProp);\n    });\n  }\n\n  switch (actualType) {\n    case 'object':\n      var key;\n      if (matchAgainstAnyProp) {\n        for (key in actual) {\n          // Under certain, rare, circumstances, key may not be a string and `charAt` will be undefined\n          // See: https://github.com/angular/angular.js/issues/15644\n          if (key.charAt && (key.charAt(0) !== '$') &&\n              deepCompare(actual[key], expected, comparator, anyPropertyKey, true)) {\n            return true;\n          }\n        }\n        return dontMatchWholeObject ? false : deepCompare(actual, expected, comparator, anyPropertyKey, false);\n      } else if (expectedType === 'object') {\n        for (key in expected) {\n          var expectedVal = expected[key];\n          if (isFunction(expectedVal) || isUndefined(expectedVal)) {\n            continue;\n          }\n\n          var matchAnyProperty = key === anyPropertyKey;\n          var actualVal = matchAnyProperty ? actual : actual[key];\n          if (!deepCompare(actualVal, expectedVal, comparator, anyPropertyKey, matchAnyProperty, matchAnyProperty)) {\n            return false;\n          }\n        }\n        return true;\n      } else {\n        return comparator(actual, expected);\n      }\n    case 'function':\n      return false;\n    default:\n      return comparator(actual, expected);\n  }\n}\n\n// Used for easily differentiating between `null` and actual `object`\nfunction getTypeForFilter(val) {\n  return (val === null) ? 'null' : typeof val;\n}\n\nvar MAX_DIGITS = 22;\nvar DECIMAL_SEP = '.';\nvar ZERO_CHAR = '0';\n\n/**\n * @ngdoc filter\n * @name currency\n * @kind function\n *\n * @description\n * Formats a number as a currency (ie $1,234.56). When no currency symbol is provided, default\n * symbol for current locale is used.\n *\n * @param {number} amount Input to filter.\n * @param {string=} symbol Currency symbol or identifier to be displayed.\n * @param {number=} fractionSize Number of decimal places to round the amount to, defaults to default max fraction size for current locale\n * @returns {string} Formatted number.\n *\n *\n * @example\n   <example module=\"currencyExample\" name=\"currency-filter\">\n     <file name=\"index.html\">\n       <script>\n         angular.module('currencyExample', [])\n           .controller('ExampleController', ['$scope', function($scope) {\n             $scope.amount = 1234.56;\n           }]);\n       </script>\n       <div ng-controller=\"ExampleController\">\n         <input type=\"number\" ng-model=\"amount\" aria-label=\"amount\"> <br>\n         default currency symbol ($): <span id=\"currency-default\">{{amount | currency}}</span><br>\n         custom currency identifier (USD$): <span id=\"currency-custom\">{{amount | currency:\"USD$\"}}</span><br>\n         no fractions (0): <span id=\"currency-no-fractions\">{{amount | currency:\"USD$\":0}}</span>\n       </div>\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       it('should init with 1234.56', function() {\n         expect(element(by.id('currency-default')).getText()).toBe('$1,234.56');\n         expect(element(by.id('currency-custom')).getText()).toBe('USD$1,234.56');\n         expect(element(by.id('currency-no-fractions')).getText()).toBe('USD$1,235');\n       });\n       it('should update', function() {\n         if (browser.params.browser === 'safari') {\n           // Safari does not understand the minus key. See\n           // https://github.com/angular/protractor/issues/481\n           return;\n         }\n         element(by.model('amount')).clear();\n         element(by.model('amount')).sendKeys('-1234');\n         expect(element(by.id('currency-default')).getText()).toBe('-$1,234.00');\n         expect(element(by.id('currency-custom')).getText()).toBe('-USD$1,234.00');\n         expect(element(by.id('currency-no-fractions')).getText()).toBe('-USD$1,234');\n       });\n     </file>\n   </example>\n */\ncurrencyFilter.$inject = ['$locale'];\nfunction currencyFilter($locale) {\n  var formats = $locale.NUMBER_FORMATS;\n  return function(amount, currencySymbol, fractionSize) {\n    if (isUndefined(currencySymbol)) {\n      currencySymbol = formats.CURRENCY_SYM;\n    }\n\n    if (isUndefined(fractionSize)) {\n      fractionSize = formats.PATTERNS[1].maxFrac;\n    }\n\n    // If the currency symbol is empty, trim whitespace around the symbol\n    var currencySymbolRe = !currencySymbol ? /\\s*\\u00A4\\s*/g : /\\u00A4/g;\n\n    // if null or undefined pass it through\n    return (amount == null)\n        ? amount\n        : formatNumber(amount, formats.PATTERNS[1], formats.GROUP_SEP, formats.DECIMAL_SEP, fractionSize).\n            replace(currencySymbolRe, currencySymbol);\n  };\n}\n\n/**\n * @ngdoc filter\n * @name number\n * @kind function\n *\n * @description\n * Formats a number as text.\n *\n * If the input is null or undefined, it will just be returned.\n * If the input is infinite (Infinity or -Infinity), the Infinity symbol '∞' or '-∞' is returned, respectively.\n * If the input is not a number an empty string is returned.\n *\n *\n * @param {number|string} number Number to format.\n * @param {(number|string)=} fractionSize Number of decimal places to round the number to.\n * If this is not provided then the fraction size is computed from the current locale's number\n * formatting pattern. In the case of the default locale, it will be 3.\n * @returns {string} Number rounded to `fractionSize` appropriately formatted based on the current\n *                   locale (e.g., in the en_US locale it will have \".\" as the decimal separator and\n *                   include \",\" group separators after each third digit).\n *\n * @example\n   <example module=\"numberFilterExample\" name=\"number-filter\">\n     <file name=\"index.html\">\n       <script>\n         angular.module('numberFilterExample', [])\n           .controller('ExampleController', ['$scope', function($scope) {\n             $scope.val = 1234.56789;\n           }]);\n       </script>\n       <div ng-controller=\"ExampleController\">\n         <label>Enter number: <input ng-model='val'></label><br>\n         Default formatting: <span id='number-default'>{{val | number}}</span><br>\n         No fractions: <span>{{val | number:0}}</span><br>\n         Negative number: <span>{{-val | number:4}}</span>\n       </div>\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       it('should format numbers', function() {\n         expect(element(by.id('number-default')).getText()).toBe('1,234.568');\n         expect(element(by.binding('val | number:0')).getText()).toBe('1,235');\n         expect(element(by.binding('-val | number:4')).getText()).toBe('-1,234.5679');\n       });\n\n       it('should update', function() {\n         element(by.model('val')).clear();\n         element(by.model('val')).sendKeys('3374.333');\n         expect(element(by.id('number-default')).getText()).toBe('3,374.333');\n         expect(element(by.binding('val | number:0')).getText()).toBe('3,374');\n         expect(element(by.binding('-val | number:4')).getText()).toBe('-3,374.3330');\n      });\n     </file>\n   </example>\n */\nnumberFilter.$inject = ['$locale'];\nfunction numberFilter($locale) {\n  var formats = $locale.NUMBER_FORMATS;\n  return function(number, fractionSize) {\n\n    // if null or undefined pass it through\n    return (number == null)\n        ? number\n        : formatNumber(number, formats.PATTERNS[0], formats.GROUP_SEP, formats.DECIMAL_SEP,\n                       fractionSize);\n  };\n}\n\n/**\n * Parse a number (as a string) into three components that can be used\n * for formatting the number.\n *\n * (Significant bits of this parse algorithm came from https://github.com/MikeMcl/big.js/)\n *\n * @param  {string} numStr The number to parse\n * @return {object} An object describing this number, containing the following keys:\n *  - d : an array of digits containing leading zeros as necessary\n *  - i : the number of the digits in `d` that are to the left of the decimal point\n *  - e : the exponent for numbers that would need more than `MAX_DIGITS` digits in `d`\n *\n */\nfunction parse(numStr) {\n  var exponent = 0, digits, numberOfIntegerDigits;\n  var i, j, zeros;\n\n  // Decimal point?\n  if ((numberOfIntegerDigits = numStr.indexOf(DECIMAL_SEP)) > -1) {\n    numStr = numStr.replace(DECIMAL_SEP, '');\n  }\n\n  // Exponential form?\n  if ((i = numStr.search(/e/i)) > 0) {\n    // Work out the exponent.\n    if (numberOfIntegerDigits < 0) numberOfIntegerDigits = i;\n    numberOfIntegerDigits += +numStr.slice(i + 1);\n    numStr = numStr.substring(0, i);\n  } else if (numberOfIntegerDigits < 0) {\n    // There was no decimal point or exponent so it is an integer.\n    numberOfIntegerDigits = numStr.length;\n  }\n\n  // Count the number of leading zeros.\n  for (i = 0; numStr.charAt(i) === ZERO_CHAR; i++) { /* empty */ }\n\n  if (i === (zeros = numStr.length)) {\n    // The digits are all zero.\n    digits = [0];\n    numberOfIntegerDigits = 1;\n  } else {\n    // Count the number of trailing zeros\n    zeros--;\n    while (numStr.charAt(zeros) === ZERO_CHAR) zeros--;\n\n    // Trailing zeros are insignificant so ignore them\n    numberOfIntegerDigits -= i;\n    digits = [];\n    // Convert string to array of digits without leading/trailing zeros.\n    for (j = 0; i <= zeros; i++, j++) {\n      digits[j] = +numStr.charAt(i);\n    }\n  }\n\n  // If the number overflows the maximum allowed digits then use an exponent.\n  if (numberOfIntegerDigits > MAX_DIGITS) {\n    digits = digits.splice(0, MAX_DIGITS - 1);\n    exponent = numberOfIntegerDigits - 1;\n    numberOfIntegerDigits = 1;\n  }\n\n  return { d: digits, e: exponent, i: numberOfIntegerDigits };\n}\n\n/**\n * Round the parsed number to the specified number of decimal places\n * This function changed the parsedNumber in-place\n */\nfunction roundNumber(parsedNumber, fractionSize, minFrac, maxFrac) {\n    var digits = parsedNumber.d;\n    var fractionLen = digits.length - parsedNumber.i;\n\n    // determine fractionSize if it is not specified; `+fractionSize` converts it to a number\n    fractionSize = (isUndefined(fractionSize)) ? Math.min(Math.max(minFrac, fractionLen), maxFrac) : +fractionSize;\n\n    // The index of the digit to where rounding is to occur\n    var roundAt = fractionSize + parsedNumber.i;\n    var digit = digits[roundAt];\n\n    if (roundAt > 0) {\n      // Drop fractional digits beyond `roundAt`\n      digits.splice(Math.max(parsedNumber.i, roundAt));\n\n      // Set non-fractional digits beyond `roundAt` to 0\n      for (var j = roundAt; j < digits.length; j++) {\n        digits[j] = 0;\n      }\n    } else {\n      // We rounded to zero so reset the parsedNumber\n      fractionLen = Math.max(0, fractionLen);\n      parsedNumber.i = 1;\n      digits.length = Math.max(1, roundAt = fractionSize + 1);\n      digits[0] = 0;\n      for (var i = 1; i < roundAt; i++) digits[i] = 0;\n    }\n\n    if (digit >= 5) {\n      if (roundAt - 1 < 0) {\n        for (var k = 0; k > roundAt; k--) {\n          digits.unshift(0);\n          parsedNumber.i++;\n        }\n        digits.unshift(1);\n        parsedNumber.i++;\n      } else {\n        digits[roundAt - 1]++;\n      }\n    }\n\n    // Pad out with zeros to get the required fraction length\n    for (; fractionLen < Math.max(0, fractionSize); fractionLen++) digits.push(0);\n\n\n    // Do any carrying, e.g. a digit was rounded up to 10\n    var carry = digits.reduceRight(function(carry, d, i, digits) {\n      d = d + carry;\n      digits[i] = d % 10;\n      return Math.floor(d / 10);\n    }, 0);\n    if (carry) {\n      digits.unshift(carry);\n      parsedNumber.i++;\n    }\n}\n\n/**\n * Format a number into a string\n * @param  {number} number       The number to format\n * @param  {{\n *           minFrac, // the minimum number of digits required in the fraction part of the number\n *           maxFrac, // the maximum number of digits required in the fraction part of the number\n *           gSize,   // number of digits in each group of separated digits\n *           lgSize,  // number of digits in the last group of digits before the decimal separator\n *           negPre,  // the string to go in front of a negative number (e.g. `-` or `(`))\n *           posPre,  // the string to go in front of a positive number\n *           negSuf,  // the string to go after a negative number (e.g. `)`)\n *           posSuf   // the string to go after a positive number\n *         }} pattern\n * @param  {string} groupSep     The string to separate groups of number (e.g. `,`)\n * @param  {string} decimalSep   The string to act as the decimal separator (e.g. `.`)\n * @param  {[type]} fractionSize The size of the fractional part of the number\n * @return {string}              The number formatted as a string\n */\nfunction formatNumber(number, pattern, groupSep, decimalSep, fractionSize) {\n\n  if (!(isString(number) || isNumber(number)) || isNaN(number)) return '';\n\n  var isInfinity = !isFinite(number);\n  var isZero = false;\n  var numStr = Math.abs(number) + '',\n      formattedText = '',\n      parsedNumber;\n\n  if (isInfinity) {\n    formattedText = '\\u221e';\n  } else {\n    parsedNumber = parse(numStr);\n\n    roundNumber(parsedNumber, fractionSize, pattern.minFrac, pattern.maxFrac);\n\n    var digits = parsedNumber.d;\n    var integerLen = parsedNumber.i;\n    var exponent = parsedNumber.e;\n    var decimals = [];\n    isZero = digits.reduce(function(isZero, d) { return isZero && !d; }, true);\n\n    // pad zeros for small numbers\n    while (integerLen < 0) {\n      digits.unshift(0);\n      integerLen++;\n    }\n\n    // extract decimals digits\n    if (integerLen > 0) {\n      decimals = digits.splice(integerLen, digits.length);\n    } else {\n      decimals = digits;\n      digits = [0];\n    }\n\n    // format the integer digits with grouping separators\n    var groups = [];\n    if (digits.length >= pattern.lgSize) {\n      groups.unshift(digits.splice(-pattern.lgSize, digits.length).join(''));\n    }\n    while (digits.length > pattern.gSize) {\n      groups.unshift(digits.splice(-pattern.gSize, digits.length).join(''));\n    }\n    if (digits.length) {\n      groups.unshift(digits.join(''));\n    }\n    formattedText = groups.join(groupSep);\n\n    // append the decimal digits\n    if (decimals.length) {\n      formattedText += decimalSep + decimals.join('');\n    }\n\n    if (exponent) {\n      formattedText += 'e+' + exponent;\n    }\n  }\n  if (number < 0 && !isZero) {\n    return pattern.negPre + formattedText + pattern.negSuf;\n  } else {\n    return pattern.posPre + formattedText + pattern.posSuf;\n  }\n}\n\nfunction padNumber(num, digits, trim, negWrap) {\n  var neg = '';\n  if (num < 0 || (negWrap && num <= 0)) {\n    if (negWrap) {\n      num = -num + 1;\n    } else {\n      num = -num;\n      neg = '-';\n    }\n  }\n  num = '' + num;\n  while (num.length < digits) num = ZERO_CHAR + num;\n  if (trim) {\n    num = num.substr(num.length - digits);\n  }\n  return neg + num;\n}\n\n\nfunction dateGetter(name, size, offset, trim, negWrap) {\n  offset = offset || 0;\n  return function(date) {\n    var value = date['get' + name]();\n    if (offset > 0 || value > -offset) {\n      value += offset;\n    }\n    if (value === 0 && offset === -12) value = 12;\n    return padNumber(value, size, trim, negWrap);\n  };\n}\n\nfunction dateStrGetter(name, shortForm, standAlone) {\n  return function(date, formats) {\n    var value = date['get' + name]();\n    var propPrefix = (standAlone ? 'STANDALONE' : '') + (shortForm ? 'SHORT' : '');\n    var get = uppercase(propPrefix + name);\n\n    return formats[get][value];\n  };\n}\n\nfunction timeZoneGetter(date, formats, offset) {\n  var zone = -1 * offset;\n  var paddedZone = (zone >= 0) ? '+' : '';\n\n  paddedZone += padNumber(Math[zone > 0 ? 'floor' : 'ceil'](zone / 60), 2) +\n                padNumber(Math.abs(zone % 60), 2);\n\n  return paddedZone;\n}\n\nfunction getFirstThursdayOfYear(year) {\n    // 0 = index of January\n    var dayOfWeekOnFirst = (new Date(year, 0, 1)).getDay();\n    // 4 = index of Thursday (+1 to account for 1st = 5)\n    // 11 = index of *next* Thursday (+1 account for 1st = 12)\n    return new Date(year, 0, ((dayOfWeekOnFirst <= 4) ? 5 : 12) - dayOfWeekOnFirst);\n}\n\nfunction getThursdayThisWeek(datetime) {\n    return new Date(datetime.getFullYear(), datetime.getMonth(),\n      // 4 = index of Thursday\n      datetime.getDate() + (4 - datetime.getDay()));\n}\n\nfunction weekGetter(size) {\n   return function(date) {\n      var firstThurs = getFirstThursdayOfYear(date.getFullYear()),\n         thisThurs = getThursdayThisWeek(date);\n\n      var diff = +thisThurs - +firstThurs,\n         result = 1 + Math.round(diff / 6.048e8); // 6.048e8 ms per week\n\n      return padNumber(result, size);\n   };\n}\n\nfunction ampmGetter(date, formats) {\n  return date.getHours() < 12 ? formats.AMPMS[0] : formats.AMPMS[1];\n}\n\nfunction eraGetter(date, formats) {\n  return date.getFullYear() <= 0 ? formats.ERAS[0] : formats.ERAS[1];\n}\n\nfunction longEraGetter(date, formats) {\n  return date.getFullYear() <= 0 ? formats.ERANAMES[0] : formats.ERANAMES[1];\n}\n\nvar DATE_FORMATS = {\n  yyyy: dateGetter('FullYear', 4, 0, false, true),\n    yy: dateGetter('FullYear', 2, 0, true, true),\n     y: dateGetter('FullYear', 1, 0, false, true),\n  MMMM: dateStrGetter('Month'),\n   MMM: dateStrGetter('Month', true),\n    MM: dateGetter('Month', 2, 1),\n     M: dateGetter('Month', 1, 1),\n  LLLL: dateStrGetter('Month', false, true),\n    dd: dateGetter('Date', 2),\n     d: dateGetter('Date', 1),\n    HH: dateGetter('Hours', 2),\n     H: dateGetter('Hours', 1),\n    hh: dateGetter('Hours', 2, -12),\n     h: dateGetter('Hours', 1, -12),\n    mm: dateGetter('Minutes', 2),\n     m: dateGetter('Minutes', 1),\n    ss: dateGetter('Seconds', 2),\n     s: dateGetter('Seconds', 1),\n     // while ISO 8601 requires fractions to be prefixed with `.` or `,`\n     // we can be just safely rely on using `sss` since we currently don't support single or two digit fractions\n   sss: dateGetter('Milliseconds', 3),\n  EEEE: dateStrGetter('Day'),\n   EEE: dateStrGetter('Day', true),\n     a: ampmGetter,\n     Z: timeZoneGetter,\n    ww: weekGetter(2),\n     w: weekGetter(1),\n     G: eraGetter,\n     GG: eraGetter,\n     GGG: eraGetter,\n     GGGG: longEraGetter\n};\n\nvar DATE_FORMATS_SPLIT = /((?:[^yMLdHhmsaZEwG']+)|(?:'(?:[^']|'')*')|(?:E+|y+|M+|L+|d+|H+|h+|m+|s+|a|Z|G+|w+))([\\s\\S]*)/,\n    NUMBER_STRING = /^-?\\d+$/;\n\n/**\n * @ngdoc filter\n * @name date\n * @kind function\n *\n * @description\n *   Formats `date` to a string based on the requested `format`.\n *\n *   `format` string can be composed of the following elements:\n *\n *   * `'yyyy'`: 4 digit representation of year (e.g. AD 1 => 0001, AD 2010 => 2010)\n *   * `'yy'`: 2 digit representation of year, padded (00-99). (e.g. AD 2001 => 01, AD 2010 => 10)\n *   * `'y'`: 1 digit representation of year, e.g. (AD 1 => 1, AD 199 => 199)\n *   * `'MMMM'`: Month in year (January-December)\n *   * `'MMM'`: Month in year (Jan-Dec)\n *   * `'MM'`: Month in year, padded (01-12)\n *   * `'M'`: Month in year (1-12)\n *   * `'LLLL'`: Stand-alone month in year (January-December)\n *   * `'dd'`: Day in month, padded (01-31)\n *   * `'d'`: Day in month (1-31)\n *   * `'EEEE'`: Day in Week,(Sunday-Saturday)\n *   * `'EEE'`: Day in Week, (Sun-Sat)\n *   * `'HH'`: Hour in day, padded (00-23)\n *   * `'H'`: Hour in day (0-23)\n *   * `'hh'`: Hour in AM/PM, padded (01-12)\n *   * `'h'`: Hour in AM/PM, (1-12)\n *   * `'mm'`: Minute in hour, padded (00-59)\n *   * `'m'`: Minute in hour (0-59)\n *   * `'ss'`: Second in minute, padded (00-59)\n *   * `'s'`: Second in minute (0-59)\n *   * `'sss'`: Millisecond in second, padded (000-999)\n *   * `'a'`: AM/PM marker\n *   * `'Z'`: 4 digit (+sign) representation of the timezone offset (-1200-+1200)\n *   * `'ww'`: Week of year, padded (00-53). Week 01 is the week with the first Thursday of the year\n *   * `'w'`: Week of year (0-53). Week 1 is the week with the first Thursday of the year\n *   * `'G'`, `'GG'`, `'GGG'`: The abbreviated form of the era string (e.g. 'AD')\n *   * `'GGGG'`: The long form of the era string (e.g. 'Anno Domini')\n *\n *   `format` string can also be one of the following predefined\n *   {@link guide/i18n localizable formats}:\n *\n *   * `'medium'`: equivalent to `'MMM d, y h:mm:ss a'` for en_US locale\n *     (e.g. Sep 3, 2010 12:05:08 PM)\n *   * `'short'`: equivalent to `'M/d/yy h:mm a'` for en_US  locale (e.g. 9/3/10 12:05 PM)\n *   * `'fullDate'`: equivalent to `'EEEE, MMMM d, y'` for en_US  locale\n *     (e.g. Friday, September 3, 2010)\n *   * `'longDate'`: equivalent to `'MMMM d, y'` for en_US  locale (e.g. September 3, 2010)\n *   * `'mediumDate'`: equivalent to `'MMM d, y'` for en_US  locale (e.g. Sep 3, 2010)\n *   * `'shortDate'`: equivalent to `'M/d/yy'` for en_US locale (e.g. 9/3/10)\n *   * `'mediumTime'`: equivalent to `'h:mm:ss a'` for en_US locale (e.g. 12:05:08 PM)\n *   * `'shortTime'`: equivalent to `'h:mm a'` for en_US locale (e.g. 12:05 PM)\n *\n *   `format` string can contain literal values. These need to be escaped by surrounding with single quotes (e.g.\n *   `\"h 'in the morning'\"`). In order to output a single quote, escape it - i.e., two single quotes in a sequence\n *   (e.g. `\"h 'o''clock'\"`).\n *\n *   Any other characters in the `format` string will be output as-is.\n *\n * @param {(Date|number|string)} date Date to format either as Date object, milliseconds (string or\n *    number) or various ISO 8601 datetime string formats (e.g. yyyy-MM-ddTHH:mm:ss.sssZ and its\n *    shorter versions like yyyy-MM-ddTHH:mmZ, yyyy-MM-dd or yyyyMMddTHHmmssZ). If no timezone is\n *    specified in the string input, the time is considered to be in the local timezone.\n * @param {string=} format Formatting rules (see Description). If not specified,\n *    `mediumDate` is used.\n * @param {string=} timezone Timezone to be used for formatting. It understands UTC/GMT and the\n *    continental US time zone abbreviations, but for general use, use a time zone offset, for\n *    example, `'+0430'` (4 hours, 30 minutes east of the Greenwich meridian)\n *    If not specified, the timezone of the browser will be used.\n * @returns {string} Formatted string or the input if input is not recognized as date/millis.\n *\n * @example\n   <example name=\"filter-date\">\n     <file name=\"index.html\">\n       <span ng-non-bindable>{{1288323623006 | date:'medium'}}</span>:\n           <span>{{1288323623006 | date:'medium'}}</span><br>\n       <span ng-non-bindable>{{1288323623006 | date:'yyyy-MM-dd HH:mm:ss Z'}}</span>:\n          <span>{{1288323623006 | date:'yyyy-MM-dd HH:mm:ss Z'}}</span><br>\n       <span ng-non-bindable>{{1288323623006 | date:'MM/dd/yyyy @ h:mma'}}</span>:\n          <span>{{'1288323623006' | date:'MM/dd/yyyy @ h:mma'}}</span><br>\n       <span ng-non-bindable>{{1288323623006 | date:\"MM/dd/yyyy 'at' h:mma\"}}</span>:\n          <span>{{'1288323623006' | date:\"MM/dd/yyyy 'at' h:mma\"}}</span><br>\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       it('should format date', function() {\n         expect(element(by.binding(\"1288323623006 | date:'medium'\")).getText()).\n            toMatch(/Oct 2\\d, 2010 \\d{1,2}:\\d{2}:\\d{2} (AM|PM)/);\n         expect(element(by.binding(\"1288323623006 | date:'yyyy-MM-dd HH:mm:ss Z'\")).getText()).\n            toMatch(/2010-10-2\\d \\d{2}:\\d{2}:\\d{2} (-|\\+)?\\d{4}/);\n         expect(element(by.binding(\"'1288323623006' | date:'MM/dd/yyyy @ h:mma'\")).getText()).\n            toMatch(/10\\/2\\d\\/2010 @ \\d{1,2}:\\d{2}(AM|PM)/);\n         expect(element(by.binding(\"'1288323623006' | date:\\\"MM/dd/yyyy 'at' h:mma\\\"\")).getText()).\n            toMatch(/10\\/2\\d\\/2010 at \\d{1,2}:\\d{2}(AM|PM)/);\n       });\n     </file>\n   </example>\n */\ndateFilter.$inject = ['$locale'];\nfunction dateFilter($locale) {\n\n\n  var R_ISO8601_STR = /^(\\d{4})-?(\\d\\d)-?(\\d\\d)(?:T(\\d\\d)(?::?(\\d\\d)(?::?(\\d\\d)(?:\\.(\\d+))?)?)?(Z|([+-])(\\d\\d):?(\\d\\d))?)?$/;\n                     // 1        2       3         4          5          6          7          8  9     10      11\n  function jsonStringToDate(string) {\n    var match;\n    if ((match = string.match(R_ISO8601_STR))) {\n      var date = new Date(0),\n          tzHour = 0,\n          tzMin  = 0,\n          dateSetter = match[8] ? date.setUTCFullYear : date.setFullYear,\n          timeSetter = match[8] ? date.setUTCHours : date.setHours;\n\n      if (match[9]) {\n        tzHour = toInt(match[9] + match[10]);\n        tzMin = toInt(match[9] + match[11]);\n      }\n      dateSetter.call(date, toInt(match[1]), toInt(match[2]) - 1, toInt(match[3]));\n      var h = toInt(match[4] || 0) - tzHour;\n      var m = toInt(match[5] || 0) - tzMin;\n      var s = toInt(match[6] || 0);\n      var ms = Math.round(parseFloat('0.' + (match[7] || 0)) * 1000);\n      timeSetter.call(date, h, m, s, ms);\n      return date;\n    }\n    return string;\n  }\n\n\n  return function(date, format, timezone) {\n    var text = '',\n        parts = [],\n        fn, match;\n\n    format = format || 'mediumDate';\n    format = $locale.DATETIME_FORMATS[format] || format;\n    if (isString(date)) {\n      date = NUMBER_STRING.test(date) ? toInt(date) : jsonStringToDate(date);\n    }\n\n    if (isNumber(date)) {\n      date = new Date(date);\n    }\n\n    if (!isDate(date) || !isFinite(date.getTime())) {\n      return date;\n    }\n\n    while (format) {\n      match = DATE_FORMATS_SPLIT.exec(format);\n      if (match) {\n        parts = concat(parts, match, 1);\n        format = parts.pop();\n      } else {\n        parts.push(format);\n        format = null;\n      }\n    }\n\n    var dateTimezoneOffset = date.getTimezoneOffset();\n    if (timezone) {\n      dateTimezoneOffset = timezoneToOffset(timezone, dateTimezoneOffset);\n      date = convertTimezoneToLocal(date, timezone, true);\n    }\n    forEach(parts, function(value) {\n      fn = DATE_FORMATS[value];\n      text += fn ? fn(date, $locale.DATETIME_FORMATS, dateTimezoneOffset)\n                 : value === '\\'\\'' ? '\\'' : value.replace(/(^'|'$)/g, '').replace(/''/g, '\\'');\n    });\n\n    return text;\n  };\n}\n\n\n/**\n * @ngdoc filter\n * @name json\n * @kind function\n *\n * @description\n *   Allows you to convert a JavaScript object into JSON string.\n *\n *   This filter is mostly useful for debugging. When using the double curly {{value}} notation\n *   the binding is automatically converted to JSON.\n *\n * @param {*} object Any JavaScript object (including arrays and primitive types) to filter.\n * @param {number=} spacing The number of spaces to use per indentation, defaults to 2.\n * @returns {string} JSON string.\n *\n *\n * @example\n   <example name=\"filter-json\">\n     <file name=\"index.html\">\n       <pre id=\"default-spacing\">{{ {'name':'value'} | json }}</pre>\n       <pre id=\"custom-spacing\">{{ {'name':'value'} | json:4 }}</pre>\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       it('should jsonify filtered objects', function() {\n         expect(element(by.id('default-spacing')).getText()).toMatch(/\\{\\n {2}\"name\": ?\"value\"\\n}/);\n         expect(element(by.id('custom-spacing')).getText()).toMatch(/\\{\\n {4}\"name\": ?\"value\"\\n}/);\n       });\n     </file>\n   </example>\n *\n */\nfunction jsonFilter() {\n  return function(object, spacing) {\n    if (isUndefined(spacing)) {\n        spacing = 2;\n    }\n    return toJson(object, spacing);\n  };\n}\n\n\n/**\n * @ngdoc filter\n * @name lowercase\n * @kind function\n * @description\n * Converts string to lowercase.\n *\n * See the {@link ng.uppercase uppercase filter documentation} for a functionally identical example.\n *\n * @see angular.lowercase\n */\nvar lowercaseFilter = valueFn(lowercase);\n\n\n/**\n * @ngdoc filter\n * @name uppercase\n * @kind function\n * @description\n * Converts string to uppercase.\n * @example\n   <example module=\"uppercaseFilterExample\" name=\"filter-uppercase\">\n     <file name=\"index.html\">\n       <script>\n         angular.module('uppercaseFilterExample', [])\n           .controller('ExampleController', ['$scope', function($scope) {\n             $scope.title = 'This is a title';\n           }]);\n       </script>\n       <div ng-controller=\"ExampleController\">\n         <!-- This title should be formatted normally -->\n         <h1>{{title}}</h1>\n         <!-- This title should be capitalized -->\n         <h1>{{title | uppercase}}</h1>\n       </div>\n     </file>\n   </example>\n */\nvar uppercaseFilter = valueFn(uppercase);\n\n/**\n * @ngdoc filter\n * @name limitTo\n * @kind function\n *\n * @description\n * Creates a new array or string containing only a specified number of elements. The elements are\n * taken from either the beginning or the end of the source array, string or number, as specified by\n * the value and sign (positive or negative) of `limit`. Other array-like objects are also supported\n * (e.g. array subclasses, NodeLists, jqLite/jQuery collections etc). If a number is used as input,\n * it is converted to a string.\n *\n * @param {Array|ArrayLike|string|number} input - Array/array-like, string or number to be limited.\n * @param {string|number} limit - The length of the returned array or string. If the `limit` number\n *     is positive, `limit` number of items from the beginning of the source array/string are copied.\n *     If the number is negative, `limit` number  of items from the end of the source array/string\n *     are copied. The `limit` will be trimmed if it exceeds `array.length`. If `limit` is undefined,\n *     the input will be returned unchanged.\n * @param {(string|number)=} begin - Index at which to begin limitation. As a negative index,\n *     `begin` indicates an offset from the end of `input`. Defaults to `0`.\n * @returns {Array|string} A new sub-array or substring of length `limit` or less if the input had\n *     less than `limit` elements.\n *\n * @example\n   <example module=\"limitToExample\" name=\"limit-to-filter\">\n     <file name=\"index.html\">\n       <script>\n         angular.module('limitToExample', [])\n           .controller('ExampleController', ['$scope', function($scope) {\n             $scope.numbers = [1,2,3,4,5,6,7,8,9];\n             $scope.letters = \"abcdefghi\";\n             $scope.longNumber = 2345432342;\n             $scope.numLimit = 3;\n             $scope.letterLimit = 3;\n             $scope.longNumberLimit = 3;\n           }]);\n       </script>\n       <div ng-controller=\"ExampleController\">\n         <label>\n            Limit {{numbers}} to:\n            <input type=\"number\" step=\"1\" ng-model=\"numLimit\">\n         </label>\n         <p>Output numbers: {{ numbers | limitTo:numLimit }}</p>\n         <label>\n            Limit {{letters}} to:\n            <input type=\"number\" step=\"1\" ng-model=\"letterLimit\">\n         </label>\n         <p>Output letters: {{ letters | limitTo:letterLimit }}</p>\n         <label>\n            Limit {{longNumber}} to:\n            <input type=\"number\" step=\"1\" ng-model=\"longNumberLimit\">\n         </label>\n         <p>Output long number: {{ longNumber | limitTo:longNumberLimit }}</p>\n       </div>\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       var numLimitInput = element(by.model('numLimit'));\n       var letterLimitInput = element(by.model('letterLimit'));\n       var longNumberLimitInput = element(by.model('longNumberLimit'));\n       var limitedNumbers = element(by.binding('numbers | limitTo:numLimit'));\n       var limitedLetters = element(by.binding('letters | limitTo:letterLimit'));\n       var limitedLongNumber = element(by.binding('longNumber | limitTo:longNumberLimit'));\n\n       it('should limit the number array to first three items', function() {\n         expect(numLimitInput.getAttribute('value')).toBe('3');\n         expect(letterLimitInput.getAttribute('value')).toBe('3');\n         expect(longNumberLimitInput.getAttribute('value')).toBe('3');\n         expect(limitedNumbers.getText()).toEqual('Output numbers: [1,2,3]');\n         expect(limitedLetters.getText()).toEqual('Output letters: abc');\n         expect(limitedLongNumber.getText()).toEqual('Output long number: 234');\n       });\n\n       // There is a bug in safari and protractor that doesn't like the minus key\n       // it('should update the output when -3 is entered', function() {\n       //   numLimitInput.clear();\n       //   numLimitInput.sendKeys('-3');\n       //   letterLimitInput.clear();\n       //   letterLimitInput.sendKeys('-3');\n       //   longNumberLimitInput.clear();\n       //   longNumberLimitInput.sendKeys('-3');\n       //   expect(limitedNumbers.getText()).toEqual('Output numbers: [7,8,9]');\n       //   expect(limitedLetters.getText()).toEqual('Output letters: ghi');\n       //   expect(limitedLongNumber.getText()).toEqual('Output long number: 342');\n       // });\n\n       it('should not exceed the maximum size of input array', function() {\n         numLimitInput.clear();\n         numLimitInput.sendKeys('100');\n         letterLimitInput.clear();\n         letterLimitInput.sendKeys('100');\n         longNumberLimitInput.clear();\n         longNumberLimitInput.sendKeys('100');\n         expect(limitedNumbers.getText()).toEqual('Output numbers: [1,2,3,4,5,6,7,8,9]');\n         expect(limitedLetters.getText()).toEqual('Output letters: abcdefghi');\n         expect(limitedLongNumber.getText()).toEqual('Output long number: 2345432342');\n       });\n     </file>\n   </example>\n*/\nfunction limitToFilter() {\n  return function(input, limit, begin) {\n    if (Math.abs(Number(limit)) === Infinity) {\n      limit = Number(limit);\n    } else {\n      limit = toInt(limit);\n    }\n    if (isNumberNaN(limit)) return input;\n\n    if (isNumber(input)) input = input.toString();\n    if (!isArrayLike(input)) return input;\n\n    begin = (!begin || isNaN(begin)) ? 0 : toInt(begin);\n    begin = (begin < 0) ? Math.max(0, input.length + begin) : begin;\n\n    if (limit >= 0) {\n      return sliceFn(input, begin, begin + limit);\n    } else {\n      if (begin === 0) {\n        return sliceFn(input, limit, input.length);\n      } else {\n        return sliceFn(input, Math.max(0, begin + limit), begin);\n      }\n    }\n  };\n}\n\nfunction sliceFn(input, begin, end) {\n  if (isString(input)) return input.slice(begin, end);\n\n  return slice.call(input, begin, end);\n}\n\n/**\n * @ngdoc filter\n * @name orderBy\n * @kind function\n *\n * @description\n * Returns an array containing the items from the specified `collection`, ordered by a `comparator`\n * function based on the values computed using the `expression` predicate.\n *\n * For example, `[{id: 'foo'}, {id: 'bar'}] | orderBy:'id'` would result in\n * `[{id: 'bar'}, {id: 'foo'}]`.\n *\n * The `collection` can be an Array or array-like object (e.g. NodeList, jQuery object, TypedArray,\n * String, etc).\n *\n * The `expression` can be a single predicate, or a list of predicates each serving as a tie-breaker\n * for the preceding one. The `expression` is evaluated against each item and the output is used\n * for comparing with other items.\n *\n * You can change the sorting order by setting `reverse` to `true`. By default, items are sorted in\n * ascending order.\n *\n * The comparison is done using the `comparator` function. If none is specified, a default, built-in\n * comparator is used (see below for details - in a nutshell, it compares numbers numerically and\n * strings alphabetically).\n *\n * ### Under the hood\n *\n * Ordering the specified `collection` happens in two phases:\n *\n * 1. All items are passed through the predicate (or predicates), and the returned values are saved\n *    along with their type (`string`, `number` etc). For example, an item `{label: 'foo'}`, passed\n *    through a predicate that extracts the value of the `label` property, would be transformed to:\n *    ```\n *    {\n *      value: 'foo',\n *      type: 'string',\n *      index: ...\n *    }\n *    ```\n *    **Note:** `null` values use `'null'` as their type.\n * 2. The comparator function is used to sort the items, based on the derived values, types and\n *    indices.\n *\n * If you use a custom comparator, it will be called with pairs of objects of the form\n * `{value: ..., type: '...', index: ...}` and is expected to return `0` if the objects are equal\n * (as far as the comparator is concerned), `-1` if the 1st one should be ranked higher than the\n * second, or `1` otherwise.\n *\n * In order to ensure that the sorting will be deterministic across platforms, if none of the\n * specified predicates can distinguish between two items, `orderBy` will automatically introduce a\n * dummy predicate that returns the item's index as `value`.\n * (If you are using a custom comparator, make sure it can handle this predicate as well.)\n *\n * If a custom comparator still can't distinguish between two items, then they will be sorted based\n * on their index using the built-in comparator.\n *\n * Finally, in an attempt to simplify things, if a predicate returns an object as the extracted\n * value for an item, `orderBy` will try to convert that object to a primitive value, before passing\n * it to the comparator. The following rules govern the conversion:\n *\n * 1. If the object has a `valueOf()` method that returns a primitive, its return value will be\n *    used instead.<br />\n *    (If the object has a `valueOf()` method that returns another object, then the returned object\n *    will be used in subsequent steps.)\n * 2. If the object has a custom `toString()` method (i.e. not the one inherited from `Object`) that\n *    returns a primitive, its return value will be used instead.<br />\n *    (If the object has a `toString()` method that returns another object, then the returned object\n *    will be used in subsequent steps.)\n * 3. No conversion; the object itself is used.\n *\n * ### The default comparator\n *\n * The default, built-in comparator should be sufficient for most usecases. In short, it compares\n * numbers numerically, strings alphabetically (and case-insensitively), for objects falls back to\n * using their index in the original collection, sorts values of different types by type and puts\n * `undefined` and `null` values at the end of the sorted list.\n *\n * More specifically, it follows these steps to determine the relative order of items:\n *\n * 1. If the compared values are of different types:\n *    - If one of the values is undefined, consider it \"greater than\" the other.\n *    - Else if one of the values is null, consider it \"greater than\" the other.\n *    - Else compare the types themselves alphabetically.\n * 2. If both values are of type `string`, compare them alphabetically in a case- and\n *    locale-insensitive way.\n * 3. If both values are objects, compare their indices instead.\n * 4. Otherwise, return:\n *    -  `0`, if the values are equal (by strict equality comparison, i.e. using `===`).\n *    - `-1`, if the 1st value is \"less than\" the 2nd value (compared using the `<` operator).\n *    -  `1`, otherwise.\n *\n * **Note:** If you notice numbers not being sorted as expected, make sure they are actually being\n *           saved as numbers and not strings.\n * **Note:** For the purpose of sorting, `null` and `undefined` are considered \"greater than\"\n *           any other value (with undefined \"greater than\" null). This effectively means that `null`\n *           and `undefined` values end up at the end of a list sorted in ascending order.\n * **Note:** `null` values use `'null'` as their type to be able to distinguish them from objects.\n *\n * @param {Array|ArrayLike} collection - The collection (array or array-like object) to sort.\n * @param {(Function|string|Array.<Function|string>)=} expression - A predicate (or list of\n *    predicates) to be used by the comparator to determine the order of elements.\n *\n *    Can be one of:\n *\n *    - `Function`: A getter function. This function will be called with each item as argument and\n *      the return value will be used for sorting.\n *    - `string`: An AngularJS expression. This expression will be evaluated against each item and the\n *      result will be used for sorting. For example, use `'label'` to sort by a property called\n *      `label` or `'label.substring(0, 3)'` to sort by the first 3 characters of the `label`\n *      property.<br />\n *      (The result of a constant expression is interpreted as a property name to be used for\n *      comparison. For example, use `'\"special name\"'` (note the extra pair of quotes) to sort by a\n *      property called `special name`.)<br />\n *      An expression can be optionally prefixed with `+` or `-` to control the sorting direction,\n *      ascending or descending. For example, `'+label'` or `'-label'`. If no property is provided,\n *      (e.g. `'+'` or `'-'`), the collection element itself is used in comparisons.\n *    - `Array`: An array of function and/or string predicates. If a predicate cannot determine the\n *      relative order of two items, the next predicate is used as a tie-breaker.\n *\n * **Note:** If the predicate is missing or empty then it defaults to `'+'`.\n *\n * @param {boolean=} reverse - If `true`, reverse the sorting order.\n * @param {(Function)=} comparator - The comparator function used to determine the relative order of\n *    value pairs. If omitted, the built-in comparator will be used.\n *\n * @returns {Array} - The sorted array.\n *\n *\n * @example\n * ### Ordering a table with `ngRepeat`\n *\n * The example below demonstrates a simple {@link ngRepeat ngRepeat}, where the data is sorted by\n * age in descending order (expression is set to `'-age'`). The `comparator` is not set, which means\n * it defaults to the built-in comparator.\n *\n   <example name=\"orderBy-static\" module=\"orderByExample1\">\n     <file name=\"index.html\">\n       <div ng-controller=\"ExampleController\">\n         <table class=\"friends\">\n           <tr>\n             <th>Name</th>\n             <th>Phone Number</th>\n             <th>Age</th>\n           </tr>\n           <tr ng-repeat=\"friend in friends | orderBy:'-age'\">\n             <td>{{friend.name}}</td>\n             <td>{{friend.phone}}</td>\n             <td>{{friend.age}}</td>\n           </tr>\n         </table>\n       </div>\n     </file>\n     <file name=\"script.js\">\n       angular.module('orderByExample1', [])\n         .controller('ExampleController', ['$scope', function($scope) {\n           $scope.friends = [\n             {name: 'John',   phone: '555-1212',  age: 10},\n             {name: 'Mary',   phone: '555-9876',  age: 19},\n             {name: 'Mike',   phone: '555-4321',  age: 21},\n             {name: 'Adam',   phone: '555-5678',  age: 35},\n             {name: 'Julie',  phone: '555-8765',  age: 29}\n           ];\n         }]);\n     </file>\n     <file name=\"style.css\">\n       .friends {\n         border-collapse: collapse;\n       }\n\n       .friends th {\n         border-bottom: 1px solid;\n       }\n       .friends td, .friends th {\n         border-left: 1px solid;\n         padding: 5px 10px;\n       }\n       .friends td:first-child, .friends th:first-child {\n         border-left: none;\n       }\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       // Element locators\n       var names = element.all(by.repeater('friends').column('friend.name'));\n\n       it('should sort friends by age in reverse order', function() {\n         expect(names.get(0).getText()).toBe('Adam');\n         expect(names.get(1).getText()).toBe('Julie');\n         expect(names.get(2).getText()).toBe('Mike');\n         expect(names.get(3).getText()).toBe('Mary');\n         expect(names.get(4).getText()).toBe('John');\n       });\n     </file>\n   </example>\n * <hr />\n *\n * @example\n * ### Changing parameters dynamically\n *\n * All parameters can be changed dynamically. The next example shows how you can make the columns of\n * a table sortable, by binding the `expression` and `reverse` parameters to scope properties.\n *\n   <example name=\"orderBy-dynamic\" module=\"orderByExample2\">\n     <file name=\"index.html\">\n       <div ng-controller=\"ExampleController\">\n         <pre>Sort by = {{propertyName}}; reverse = {{reverse}}</pre>\n         <hr/>\n         <button ng-click=\"propertyName = null; reverse = false\">Set to unsorted</button>\n         <hr/>\n         <table class=\"friends\">\n           <tr>\n             <th>\n               <button ng-click=\"sortBy('name')\">Name</button>\n               <span class=\"sortorder\" ng-show=\"propertyName === 'name'\" ng-class=\"{reverse: reverse}\"></span>\n             </th>\n             <th>\n               <button ng-click=\"sortBy('phone')\">Phone Number</button>\n               <span class=\"sortorder\" ng-show=\"propertyName === 'phone'\" ng-class=\"{reverse: reverse}\"></span>\n             </th>\n             <th>\n               <button ng-click=\"sortBy('age')\">Age</button>\n               <span class=\"sortorder\" ng-show=\"propertyName === 'age'\" ng-class=\"{reverse: reverse}\"></span>\n             </th>\n           </tr>\n           <tr ng-repeat=\"friend in friends | orderBy:propertyName:reverse\">\n             <td>{{friend.name}}</td>\n             <td>{{friend.phone}}</td>\n             <td>{{friend.age}}</td>\n           </tr>\n         </table>\n       </div>\n     </file>\n     <file name=\"script.js\">\n       angular.module('orderByExample2', [])\n         .controller('ExampleController', ['$scope', function($scope) {\n           var friends = [\n             {name: 'John',   phone: '555-1212',  age: 10},\n             {name: 'Mary',   phone: '555-9876',  age: 19},\n             {name: 'Mike',   phone: '555-4321',  age: 21},\n             {name: 'Adam',   phone: '555-5678',  age: 35},\n             {name: 'Julie',  phone: '555-8765',  age: 29}\n           ];\n\n           $scope.propertyName = 'age';\n           $scope.reverse = true;\n           $scope.friends = friends;\n\n           $scope.sortBy = function(propertyName) {\n             $scope.reverse = ($scope.propertyName === propertyName) ? !$scope.reverse : false;\n             $scope.propertyName = propertyName;\n           };\n         }]);\n     </file>\n     <file name=\"style.css\">\n       .friends {\n         border-collapse: collapse;\n       }\n\n       .friends th {\n         border-bottom: 1px solid;\n       }\n       .friends td, .friends th {\n         border-left: 1px solid;\n         padding: 5px 10px;\n       }\n       .friends td:first-child, .friends th:first-child {\n         border-left: none;\n       }\n\n       .sortorder:after {\n         content: '\\25b2';   // BLACK UP-POINTING TRIANGLE\n       }\n       .sortorder.reverse:after {\n         content: '\\25bc';   // BLACK DOWN-POINTING TRIANGLE\n       }\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       // Element locators\n       var unsortButton = element(by.partialButtonText('unsorted'));\n       var nameHeader = element(by.partialButtonText('Name'));\n       var phoneHeader = element(by.partialButtonText('Phone'));\n       var ageHeader = element(by.partialButtonText('Age'));\n       var firstName = element(by.repeater('friends').column('friend.name').row(0));\n       var lastName = element(by.repeater('friends').column('friend.name').row(4));\n\n       it('should sort friends by some property, when clicking on the column header', function() {\n         expect(firstName.getText()).toBe('Adam');\n         expect(lastName.getText()).toBe('John');\n\n         phoneHeader.click();\n         expect(firstName.getText()).toBe('John');\n         expect(lastName.getText()).toBe('Mary');\n\n         nameHeader.click();\n         expect(firstName.getText()).toBe('Adam');\n         expect(lastName.getText()).toBe('Mike');\n\n         ageHeader.click();\n         expect(firstName.getText()).toBe('John');\n         expect(lastName.getText()).toBe('Adam');\n       });\n\n       it('should sort friends in reverse order, when clicking on the same column', function() {\n         expect(firstName.getText()).toBe('Adam');\n         expect(lastName.getText()).toBe('John');\n\n         ageHeader.click();\n         expect(firstName.getText()).toBe('John');\n         expect(lastName.getText()).toBe('Adam');\n\n         ageHeader.click();\n         expect(firstName.getText()).toBe('Adam');\n         expect(lastName.getText()).toBe('John');\n       });\n\n       it('should restore the original order, when clicking \"Set to unsorted\"', function() {\n         expect(firstName.getText()).toBe('Adam');\n         expect(lastName.getText()).toBe('John');\n\n         unsortButton.click();\n         expect(firstName.getText()).toBe('John');\n         expect(lastName.getText()).toBe('Julie');\n       });\n     </file>\n   </example>\n * <hr />\n *\n * @example\n * ### Using `orderBy` inside a controller\n *\n * It is also possible to call the `orderBy` filter manually, by injecting `orderByFilter`, and\n * calling it with the desired parameters. (Alternatively, you could inject the `$filter` factory\n * and retrieve the `orderBy` filter with `$filter('orderBy')`.)\n *\n   <example name=\"orderBy-call-manually\" module=\"orderByExample3\">\n     <file name=\"index.html\">\n       <div ng-controller=\"ExampleController\">\n         <pre>Sort by = {{propertyName}}; reverse = {{reverse}}</pre>\n         <hr/>\n         <button ng-click=\"sortBy(null)\">Set to unsorted</button>\n         <hr/>\n         <table class=\"friends\">\n           <tr>\n             <th>\n               <button ng-click=\"sortBy('name')\">Name</button>\n               <span class=\"sortorder\" ng-show=\"propertyName === 'name'\" ng-class=\"{reverse: reverse}\"></span>\n             </th>\n             <th>\n               <button ng-click=\"sortBy('phone')\">Phone Number</button>\n               <span class=\"sortorder\" ng-show=\"propertyName === 'phone'\" ng-class=\"{reverse: reverse}\"></span>\n             </th>\n             <th>\n               <button ng-click=\"sortBy('age')\">Age</button>\n               <span class=\"sortorder\" ng-show=\"propertyName === 'age'\" ng-class=\"{reverse: reverse}\"></span>\n             </th>\n           </tr>\n           <tr ng-repeat=\"friend in friends\">\n             <td>{{friend.name}}</td>\n             <td>{{friend.phone}}</td>\n             <td>{{friend.age}}</td>\n           </tr>\n         </table>\n       </div>\n     </file>\n     <file name=\"script.js\">\n       angular.module('orderByExample3', [])\n         .controller('ExampleController', ['$scope', 'orderByFilter', function($scope, orderBy) {\n           var friends = [\n             {name: 'John',   phone: '555-1212',  age: 10},\n             {name: 'Mary',   phone: '555-9876',  age: 19},\n             {name: 'Mike',   phone: '555-4321',  age: 21},\n             {name: 'Adam',   phone: '555-5678',  age: 35},\n             {name: 'Julie',  phone: '555-8765',  age: 29}\n           ];\n\n           $scope.propertyName = 'age';\n           $scope.reverse = true;\n           $scope.friends = orderBy(friends, $scope.propertyName, $scope.reverse);\n\n           $scope.sortBy = function(propertyName) {\n             $scope.reverse = (propertyName !== null && $scope.propertyName === propertyName)\n                 ? !$scope.reverse : false;\n             $scope.propertyName = propertyName;\n             $scope.friends = orderBy(friends, $scope.propertyName, $scope.reverse);\n           };\n         }]);\n     </file>\n     <file name=\"style.css\">\n       .friends {\n         border-collapse: collapse;\n       }\n\n       .friends th {\n         border-bottom: 1px solid;\n       }\n       .friends td, .friends th {\n         border-left: 1px solid;\n         padding: 5px 10px;\n       }\n       .friends td:first-child, .friends th:first-child {\n         border-left: none;\n       }\n\n       .sortorder:after {\n         content: '\\25b2';   // BLACK UP-POINTING TRIANGLE\n       }\n       .sortorder.reverse:after {\n         content: '\\25bc';   // BLACK DOWN-POINTING TRIANGLE\n       }\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       // Element locators\n       var unsortButton = element(by.partialButtonText('unsorted'));\n       var nameHeader = element(by.partialButtonText('Name'));\n       var phoneHeader = element(by.partialButtonText('Phone'));\n       var ageHeader = element(by.partialButtonText('Age'));\n       var firstName = element(by.repeater('friends').column('friend.name').row(0));\n       var lastName = element(by.repeater('friends').column('friend.name').row(4));\n\n       it('should sort friends by some property, when clicking on the column header', function() {\n         expect(firstName.getText()).toBe('Adam');\n         expect(lastName.getText()).toBe('John');\n\n         phoneHeader.click();\n         expect(firstName.getText()).toBe('John');\n         expect(lastName.getText()).toBe('Mary');\n\n         nameHeader.click();\n         expect(firstName.getText()).toBe('Adam');\n         expect(lastName.getText()).toBe('Mike');\n\n         ageHeader.click();\n         expect(firstName.getText()).toBe('John');\n         expect(lastName.getText()).toBe('Adam');\n       });\n\n       it('should sort friends in reverse order, when clicking on the same column', function() {\n         expect(firstName.getText()).toBe('Adam');\n         expect(lastName.getText()).toBe('John');\n\n         ageHeader.click();\n         expect(firstName.getText()).toBe('John');\n         expect(lastName.getText()).toBe('Adam');\n\n         ageHeader.click();\n         expect(firstName.getText()).toBe('Adam');\n         expect(lastName.getText()).toBe('John');\n       });\n\n       it('should restore the original order, when clicking \"Set to unsorted\"', function() {\n         expect(firstName.getText()).toBe('Adam');\n         expect(lastName.getText()).toBe('John');\n\n         unsortButton.click();\n         expect(firstName.getText()).toBe('John');\n         expect(lastName.getText()).toBe('Julie');\n       });\n     </file>\n   </example>\n * <hr />\n *\n * @example\n * ### Using a custom comparator\n *\n * If you have very specific requirements about the way items are sorted, you can pass your own\n * comparator function. For example, you might need to compare some strings in a locale-sensitive\n * way. (When specifying a custom comparator, you also need to pass a value for the `reverse`\n * argument - passing `false` retains the default sorting order, i.e. ascending.)\n *\n   <example name=\"orderBy-custom-comparator\" module=\"orderByExample4\">\n     <file name=\"index.html\">\n       <div ng-controller=\"ExampleController\">\n         <div class=\"friends-container custom-comparator\">\n           <h3>Locale-sensitive Comparator</h3>\n           <table class=\"friends\">\n             <tr>\n               <th>Name</th>\n               <th>Favorite Letter</th>\n             </tr>\n             <tr ng-repeat=\"friend in friends | orderBy:'favoriteLetter':false:localeSensitiveComparator\">\n               <td>{{friend.name}}</td>\n               <td>{{friend.favoriteLetter}}</td>\n             </tr>\n           </table>\n         </div>\n         <div class=\"friends-container default-comparator\">\n           <h3>Default Comparator</h3>\n           <table class=\"friends\">\n             <tr>\n               <th>Name</th>\n               <th>Favorite Letter</th>\n             </tr>\n             <tr ng-repeat=\"friend in friends | orderBy:'favoriteLetter'\">\n               <td>{{friend.name}}</td>\n               <td>{{friend.favoriteLetter}}</td>\n             </tr>\n           </table>\n         </div>\n       </div>\n     </file>\n     <file name=\"script.js\">\n       angular.module('orderByExample4', [])\n         .controller('ExampleController', ['$scope', function($scope) {\n           $scope.friends = [\n             {name: 'John',   favoriteLetter: 'Ä'},\n             {name: 'Mary',   favoriteLetter: 'Ü'},\n             {name: 'Mike',   favoriteLetter: 'Ö'},\n             {name: 'Adam',   favoriteLetter: 'H'},\n             {name: 'Julie',  favoriteLetter: 'Z'}\n           ];\n\n           $scope.localeSensitiveComparator = function(v1, v2) {\n             // If we don't get strings, just compare by index\n             if (v1.type !== 'string' || v2.type !== 'string') {\n               return (v1.index < v2.index) ? -1 : 1;\n             }\n\n             // Compare strings alphabetically, taking locale into account\n             return v1.value.localeCompare(v2.value);\n           };\n         }]);\n     </file>\n     <file name=\"style.css\">\n       .friends-container {\n         display: inline-block;\n         margin: 0 30px;\n       }\n\n       .friends {\n         border-collapse: collapse;\n       }\n\n       .friends th {\n         border-bottom: 1px solid;\n       }\n       .friends td, .friends th {\n         border-left: 1px solid;\n         padding: 5px 10px;\n       }\n       .friends td:first-child, .friends th:first-child {\n         border-left: none;\n       }\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       // Element locators\n       var container = element(by.css('.custom-comparator'));\n       var names = container.all(by.repeater('friends').column('friend.name'));\n\n       it('should sort friends by favorite letter (in correct alphabetical order)', function() {\n         expect(names.get(0).getText()).toBe('John');\n         expect(names.get(1).getText()).toBe('Adam');\n         expect(names.get(2).getText()).toBe('Mike');\n         expect(names.get(3).getText()).toBe('Mary');\n         expect(names.get(4).getText()).toBe('Julie');\n       });\n     </file>\n   </example>\n *\n */\norderByFilter.$inject = ['$parse'];\nfunction orderByFilter($parse) {\n  return function(array, sortPredicate, reverseOrder, compareFn) {\n\n    if (array == null) return array;\n    if (!isArrayLike(array)) {\n      throw minErr('orderBy')('notarray', 'Expected array but received: {0}', array);\n    }\n\n    if (!isArray(sortPredicate)) { sortPredicate = [sortPredicate]; }\n    if (sortPredicate.length === 0) { sortPredicate = ['+']; }\n\n    var predicates = processPredicates(sortPredicate);\n\n    var descending = reverseOrder ? -1 : 1;\n\n    // Define the `compare()` function. Use a default comparator if none is specified.\n    var compare = isFunction(compareFn) ? compareFn : defaultCompare;\n\n    // The next three lines are a version of a Swartzian Transform idiom from Perl\n    // (sometimes called the Decorate-Sort-Undecorate idiom)\n    // See https://en.wikipedia.org/wiki/Schwartzian_transform\n    var compareValues = Array.prototype.map.call(array, getComparisonObject);\n    compareValues.sort(doComparison);\n    array = compareValues.map(function(item) { return item.value; });\n\n    return array;\n\n    function getComparisonObject(value, index) {\n      // NOTE: We are adding an extra `tieBreaker` value based on the element's index.\n      // This will be used to keep the sort stable when none of the input predicates can\n      // distinguish between two elements.\n      return {\n        value: value,\n        tieBreaker: {value: index, type: 'number', index: index},\n        predicateValues: predicates.map(function(predicate) {\n          return getPredicateValue(predicate.get(value), index);\n        })\n      };\n    }\n\n    function doComparison(v1, v2) {\n      for (var i = 0, ii = predicates.length; i < ii; i++) {\n        var result = compare(v1.predicateValues[i], v2.predicateValues[i]);\n        if (result) {\n          return result * predicates[i].descending * descending;\n        }\n      }\n\n      return (compare(v1.tieBreaker, v2.tieBreaker) || defaultCompare(v1.tieBreaker, v2.tieBreaker)) * descending;\n    }\n  };\n\n  function processPredicates(sortPredicates) {\n    return sortPredicates.map(function(predicate) {\n      var descending = 1, get = identity;\n\n      if (isFunction(predicate)) {\n        get = predicate;\n      } else if (isString(predicate)) {\n        if ((predicate.charAt(0) === '+' || predicate.charAt(0) === '-')) {\n          descending = predicate.charAt(0) === '-' ? -1 : 1;\n          predicate = predicate.substring(1);\n        }\n        if (predicate !== '') {\n          get = $parse(predicate);\n          if (get.constant) {\n            var key = get();\n            get = function(value) { return value[key]; };\n          }\n        }\n      }\n      return {get: get, descending: descending};\n    });\n  }\n\n  function isPrimitive(value) {\n    switch (typeof value) {\n      case 'number': /* falls through */\n      case 'boolean': /* falls through */\n      case 'string':\n        return true;\n      default:\n        return false;\n    }\n  }\n\n  function objectValue(value) {\n    // If `valueOf` is a valid function use that\n    if (isFunction(value.valueOf)) {\n      value = value.valueOf();\n      if (isPrimitive(value)) return value;\n    }\n    // If `toString` is a valid function and not the one from `Object.prototype` use that\n    if (hasCustomToString(value)) {\n      value = value.toString();\n      if (isPrimitive(value)) return value;\n    }\n\n    return value;\n  }\n\n  function getPredicateValue(value, index) {\n    var type = typeof value;\n    if (value === null) {\n      type = 'null';\n    } else if (type === 'object') {\n      value = objectValue(value);\n    }\n    return {value: value, type: type, index: index};\n  }\n\n  function defaultCompare(v1, v2) {\n    var result = 0;\n    var type1 = v1.type;\n    var type2 = v2.type;\n\n    if (type1 === type2) {\n      var value1 = v1.value;\n      var value2 = v2.value;\n\n      if (type1 === 'string') {\n        // Compare strings case-insensitively\n        value1 = value1.toLowerCase();\n        value2 = value2.toLowerCase();\n      } else if (type1 === 'object') {\n        // For basic objects, use the position of the object\n        // in the collection instead of the value\n        if (isObject(value1)) value1 = v1.index;\n        if (isObject(value2)) value2 = v2.index;\n      }\n\n      if (value1 !== value2) {\n        result = value1 < value2 ? -1 : 1;\n      }\n    } else {\n      result = (type1 === 'undefined') ? 1 :\n        (type2 === 'undefined') ? -1 :\n        (type1 === 'null') ? 1 :\n        (type2 === 'null') ? -1 :\n        (type1 < type2) ? -1 : 1;\n    }\n\n    return result;\n  }\n}\n\nfunction ngDirective(directive) {\n  if (isFunction(directive)) {\n    directive = {\n      link: directive\n    };\n  }\n  directive.restrict = directive.restrict || 'AC';\n  return valueFn(directive);\n}\n\n/**\n * @ngdoc directive\n * @name a\n * @restrict E\n *\n * @description\n * Modifies the default behavior of the html a tag so that the default action is prevented when\n * the href attribute is empty.\n *\n * For dynamically creating `href` attributes for a tags, see the {@link ng.ngHref `ngHref`} directive.\n */\nvar htmlAnchorDirective = valueFn({\n  restrict: 'E',\n  compile: function(element, attr) {\n    if (!attr.href && !attr.xlinkHref) {\n      return function(scope, element) {\n        // If the linked element is not an anchor tag anymore, do nothing\n        if (element[0].nodeName.toLowerCase() !== 'a') return;\n\n        // SVGAElement does not use the href attribute, but rather the 'xlinkHref' attribute.\n        var href = toString.call(element.prop('href')) === '[object SVGAnimatedString]' ?\n                   'xlink:href' : 'href';\n        element.on('click', function(event) {\n          // if we have no href url, then don't navigate anywhere.\n          if (!element.attr(href)) {\n            event.preventDefault();\n          }\n        });\n      };\n    }\n  }\n});\n\n/**\n * @ngdoc directive\n * @name ngHref\n * @restrict A\n * @priority 99\n *\n * @description\n * Using AngularJS markup like `{{hash}}` in an href attribute will\n * make the link go to the wrong URL if the user clicks it before\n * AngularJS has a chance to replace the `{{hash}}` markup with its\n * value. Until AngularJS replaces the markup the link will be broken\n * and will most likely return a 404 error. The `ngHref` directive\n * solves this problem.\n *\n * The wrong way to write it:\n * ```html\n * <a href=\"http://www.gravatar.com/avatar/{{hash}}\">link1</a>\n * ```\n *\n * The correct way to write it:\n * ```html\n * <a ng-href=\"http://www.gravatar.com/avatar/{{hash}}\">link1</a>\n * ```\n *\n * @element A\n * @param {template} ngHref any string which can contain `{{}}` markup.\n *\n * @example\n * This example shows various combinations of `href`, `ng-href` and `ng-click` attributes\n * in links and their different behaviors:\n    <example name=\"ng-href\">\n      <file name=\"index.html\">\n        <input ng-model=\"value\" /><br />\n        <a id=\"link-1\" href ng-click=\"value = 1\">link 1</a> (link, don't reload)<br />\n        <a id=\"link-2\" href=\"\" ng-click=\"value = 2\">link 2</a> (link, don't reload)<br />\n        <a id=\"link-3\" ng-href=\"/{{'123'}}\">link 3</a> (link, reload!)<br />\n        <a id=\"link-4\" href=\"\" name=\"xx\" ng-click=\"value = 4\">anchor</a> (link, don't reload)<br />\n        <a id=\"link-5\" name=\"xxx\" ng-click=\"value = 5\">anchor</a> (no link)<br />\n        <a id=\"link-6\" ng-href=\"{{value}}\">link</a> (link, change location)\n      </file>\n      <file name=\"protractor.js\" type=\"protractor\">\n        it('should execute ng-click but not reload when href without value', function() {\n          element(by.id('link-1')).click();\n          expect(element(by.model('value')).getAttribute('value')).toEqual('1');\n          expect(element(by.id('link-1')).getAttribute('href')).toBe('');\n        });\n\n        it('should execute ng-click but not reload when href empty string', function() {\n          element(by.id('link-2')).click();\n          expect(element(by.model('value')).getAttribute('value')).toEqual('2');\n          expect(element(by.id('link-2')).getAttribute('href')).toBe('');\n        });\n\n        it('should execute ng-click and change url when ng-href specified', function() {\n          expect(element(by.id('link-3')).getAttribute('href')).toMatch(/\\/123$/);\n\n          element(by.id('link-3')).click();\n\n          // At this point, we navigate away from an AngularJS page, so we need\n          // to use browser.driver to get the base webdriver.\n\n          browser.wait(function() {\n            return browser.driver.getCurrentUrl().then(function(url) {\n              return url.match(/\\/123$/);\n            });\n          }, 5000, 'page should navigate to /123');\n        });\n\n        it('should execute ng-click but not reload when href empty string and name specified', function() {\n          element(by.id('link-4')).click();\n          expect(element(by.model('value')).getAttribute('value')).toEqual('4');\n          expect(element(by.id('link-4')).getAttribute('href')).toBe('');\n        });\n\n        it('should execute ng-click but not reload when no href but name specified', function() {\n          element(by.id('link-5')).click();\n          expect(element(by.model('value')).getAttribute('value')).toEqual('5');\n          expect(element(by.id('link-5')).getAttribute('href')).toBe(null);\n        });\n\n        it('should only change url when only ng-href', function() {\n          element(by.model('value')).clear();\n          element(by.model('value')).sendKeys('6');\n          expect(element(by.id('link-6')).getAttribute('href')).toMatch(/\\/6$/);\n\n          element(by.id('link-6')).click();\n\n          // At this point, we navigate away from an AngularJS page, so we need\n          // to use browser.driver to get the base webdriver.\n          browser.wait(function() {\n            return browser.driver.getCurrentUrl().then(function(url) {\n              return url.match(/\\/6$/);\n            });\n          }, 5000, 'page should navigate to /6');\n        });\n      </file>\n    </example>\n */\n\n/**\n * @ngdoc directive\n * @name ngSrc\n * @restrict A\n * @priority 99\n *\n * @description\n * Using AngularJS markup like `{{hash}}` in a `src` attribute doesn't\n * work right: The browser will fetch from the URL with the literal\n * text `{{hash}}` until AngularJS replaces the expression inside\n * `{{hash}}`. The `ngSrc` directive solves this problem.\n *\n * The buggy way to write it:\n * ```html\n * <img src=\"http://www.gravatar.com/avatar/{{hash}}\" alt=\"Description\"/>\n * ```\n *\n * The correct way to write it:\n * ```html\n * <img ng-src=\"http://www.gravatar.com/avatar/{{hash}}\" alt=\"Description\" />\n * ```\n *\n * @element IMG\n * @param {template} ngSrc any string which can contain `{{}}` markup.\n */\n\n/**\n * @ngdoc directive\n * @name ngSrcset\n * @restrict A\n * @priority 99\n *\n * @description\n * Using AngularJS markup like `{{hash}}` in a `srcset` attribute doesn't\n * work right: The browser will fetch from the URL with the literal\n * text `{{hash}}` until AngularJS replaces the expression inside\n * `{{hash}}`. The `ngSrcset` directive solves this problem.\n *\n * The buggy way to write it:\n * ```html\n * <img srcset=\"http://www.gravatar.com/avatar/{{hash}} 2x\" alt=\"Description\"/>\n * ```\n *\n * The correct way to write it:\n * ```html\n * <img ng-srcset=\"http://www.gravatar.com/avatar/{{hash}} 2x\" alt=\"Description\" />\n * ```\n *\n * @element IMG\n * @param {template} ngSrcset any string which can contain `{{}}` markup.\n */\n\n/**\n * @ngdoc directive\n * @name ngDisabled\n * @restrict A\n * @priority 100\n *\n * @description\n *\n * This directive sets the `disabled` attribute on the element (typically a form control,\n * e.g. `input`, `button`, `select` etc.) if the\n * {@link guide/expression expression} inside `ngDisabled` evaluates to truthy.\n *\n * A special directive is necessary because we cannot use interpolation inside the `disabled`\n * attribute. See the {@link guide/interpolation interpolation guide} for more info.\n *\n * @example\n    <example name=\"ng-disabled\">\n      <file name=\"index.html\">\n        <label>Click me to toggle: <input type=\"checkbox\" ng-model=\"checked\"></label><br/>\n        <button ng-model=\"button\" ng-disabled=\"checked\">Button</button>\n      </file>\n      <file name=\"protractor.js\" type=\"protractor\">\n        it('should toggle button', function() {\n          expect(element(by.css('button')).getAttribute('disabled')).toBeFalsy();\n          element(by.model('checked')).click();\n          expect(element(by.css('button')).getAttribute('disabled')).toBeTruthy();\n        });\n      </file>\n    </example>\n *\n * @param {expression} ngDisabled If the {@link guide/expression expression} is truthy,\n *     then the `disabled` attribute will be set on the element\n */\n\n\n/**\n * @ngdoc directive\n * @name ngChecked\n * @restrict A\n * @priority 100\n *\n * @description\n * Sets the `checked` attribute on the element, if the expression inside `ngChecked` is truthy.\n *\n * Note that this directive should not be used together with {@link ngModel `ngModel`},\n * as this can lead to unexpected behavior.\n *\n * A special directive is necessary because we cannot use interpolation inside the `checked`\n * attribute. See the {@link guide/interpolation interpolation guide} for more info.\n *\n * @example\n    <example name=\"ng-checked\">\n      <file name=\"index.html\">\n        <label>Check me to check both: <input type=\"checkbox\" ng-model=\"leader\"></label><br/>\n        <input id=\"checkFollower\" type=\"checkbox\" ng-checked=\"leader\" aria-label=\"Follower input\">\n      </file>\n      <file name=\"protractor.js\" type=\"protractor\">\n        it('should check both checkBoxes', function() {\n          expect(element(by.id('checkFollower')).getAttribute('checked')).toBeFalsy();\n          element(by.model('leader')).click();\n          expect(element(by.id('checkFollower')).getAttribute('checked')).toBeTruthy();\n        });\n      </file>\n    </example>\n *\n * @element INPUT\n * @param {expression} ngChecked If the {@link guide/expression expression} is truthy,\n *     then the `checked` attribute will be set on the element\n */\n\n\n/**\n * @ngdoc directive\n * @name ngReadonly\n * @restrict A\n * @priority 100\n *\n * @description\n *\n * Sets the `readonly` attribute on the element, if the expression inside `ngReadonly` is truthy.\n * Note that `readonly` applies only to `input` elements with specific types. [See the input docs on\n * MDN](https://developer.mozilla.org/en-US/docs/Web/HTML/Element/input#attr-readonly) for more information.\n *\n * A special directive is necessary because we cannot use interpolation inside the `readonly`\n * attribute. See the {@link guide/interpolation interpolation guide} for more info.\n *\n * @example\n    <example name=\"ng-readonly\">\n      <file name=\"index.html\">\n        <label>Check me to make text readonly: <input type=\"checkbox\" ng-model=\"checked\"></label><br/>\n        <input type=\"text\" ng-readonly=\"checked\" value=\"I'm AngularJS\" aria-label=\"Readonly field\" />\n      </file>\n      <file name=\"protractor.js\" type=\"protractor\">\n        it('should toggle readonly attr', function() {\n          expect(element(by.css('[type=\"text\"]')).getAttribute('readonly')).toBeFalsy();\n          element(by.model('checked')).click();\n          expect(element(by.css('[type=\"text\"]')).getAttribute('readonly')).toBeTruthy();\n        });\n      </file>\n    </example>\n *\n * @element INPUT\n * @param {expression} ngReadonly If the {@link guide/expression expression} is truthy,\n *     then special attribute \"readonly\" will be set on the element\n */\n\n\n/**\n * @ngdoc directive\n * @name ngSelected\n * @restrict A\n * @priority 100\n *\n * @description\n *\n * Sets the `selected` attribute on the element, if the expression inside `ngSelected` is truthy.\n *\n * A special directive is necessary because we cannot use interpolation inside the `selected`\n * attribute. See the {@link guide/interpolation interpolation guide} for more info.\n *\n * <div class=\"alert alert-warning\">\n *   **Note:** `ngSelected` does not interact with the `select` and `ngModel` directives, it only\n *   sets the `selected` attribute on the element. If you are using `ngModel` on the select, you\n *   should not use `ngSelected` on the options, as `ngModel` will set the select value and\n *   selected options.\n * </div>\n *\n * @example\n    <example name=\"ng-selected\">\n      <file name=\"index.html\">\n        <label>Check me to select: <input type=\"checkbox\" ng-model=\"selected\"></label><br/>\n        <select aria-label=\"ngSelected demo\">\n          <option>Hello!</option>\n          <option id=\"greet\" ng-selected=\"selected\">Greetings!</option>\n        </select>\n      </file>\n      <file name=\"protractor.js\" type=\"protractor\">\n        it('should select Greetings!', function() {\n          expect(element(by.id('greet')).getAttribute('selected')).toBeFalsy();\n          element(by.model('selected')).click();\n          expect(element(by.id('greet')).getAttribute('selected')).toBeTruthy();\n        });\n      </file>\n    </example>\n *\n * @element OPTION\n * @param {expression} ngSelected If the {@link guide/expression expression} is truthy,\n *     then special attribute \"selected\" will be set on the element\n */\n\n/**\n * @ngdoc directive\n * @name ngOpen\n * @restrict A\n * @priority 100\n *\n * @description\n *\n * Sets the `open` attribute on the element, if the expression inside `ngOpen` is truthy.\n *\n * A special directive is necessary because we cannot use interpolation inside the `open`\n * attribute. See the {@link guide/interpolation interpolation guide} for more info.\n *\n * ## A note about browser compatibility\n *\n * Internet Explorer and Edge do not support the `details` element, it is\n * recommended to use {@link ng.ngShow} and {@link ng.ngHide} instead.\n *\n * @example\n     <example name=\"ng-open\">\n       <file name=\"index.html\">\n         <label>Toggle details: <input type=\"checkbox\" ng-model=\"open\"></label><br/>\n         <details id=\"details\" ng-open=\"open\">\n            <summary>List</summary>\n            <ul>\n              <li>Apple</li>\n              <li>Orange</li>\n              <li>Durian</li>\n            </ul>\n         </details>\n       </file>\n       <file name=\"protractor.js\" type=\"protractor\">\n         it('should toggle open', function() {\n           expect(element(by.id('details')).getAttribute('open')).toBeFalsy();\n           element(by.model('open')).click();\n           expect(element(by.id('details')).getAttribute('open')).toBeTruthy();\n         });\n       </file>\n     </example>\n *\n * @element DETAILS\n * @param {expression} ngOpen If the {@link guide/expression expression} is truthy,\n *     then special attribute \"open\" will be set on the element\n */\n\nvar ngAttributeAliasDirectives = {};\n\n// boolean attrs are evaluated\nforEach(BOOLEAN_ATTR, function(propName, attrName) {\n  // binding to multiple is not supported\n  if (propName === 'multiple') return;\n\n  function defaultLinkFn(scope, element, attr) {\n    scope.$watch(attr[normalized], function ngBooleanAttrWatchAction(value) {\n      attr.$set(attrName, !!value);\n    });\n  }\n\n  var normalized = directiveNormalize('ng-' + attrName);\n  var linkFn = defaultLinkFn;\n\n  if (propName === 'checked') {\n    linkFn = function(scope, element, attr) {\n      // ensuring ngChecked doesn't interfere with ngModel when both are set on the same input\n      if (attr.ngModel !== attr[normalized]) {\n        defaultLinkFn(scope, element, attr);\n      }\n    };\n  }\n\n  ngAttributeAliasDirectives[normalized] = function() {\n    return {\n      restrict: 'A',\n      priority: 100,\n      link: linkFn\n    };\n  };\n});\n\n// aliased input attrs are evaluated\nforEach(ALIASED_ATTR, function(htmlAttr, ngAttr) {\n  ngAttributeAliasDirectives[ngAttr] = function() {\n    return {\n      priority: 100,\n      link: function(scope, element, attr) {\n        //special case ngPattern when a literal regular expression value\n        //is used as the expression (this way we don't have to watch anything).\n        if (ngAttr === 'ngPattern' && attr.ngPattern.charAt(0) === '/') {\n          var match = attr.ngPattern.match(REGEX_STRING_REGEXP);\n          if (match) {\n            attr.$set('ngPattern', new RegExp(match[1], match[2]));\n            return;\n          }\n        }\n\n        scope.$watch(attr[ngAttr], function ngAttrAliasWatchAction(value) {\n          attr.$set(ngAttr, value);\n        });\n      }\n    };\n  };\n});\n\n// ng-src, ng-srcset, ng-href are interpolated\nforEach(['src', 'srcset', 'href'], function(attrName) {\n  var normalized = directiveNormalize('ng-' + attrName);\n  ngAttributeAliasDirectives[normalized] = ['$sce', function($sce) {\n    return {\n      priority: 99, // it needs to run after the attributes are interpolated\n      link: function(scope, element, attr) {\n        var propName = attrName,\n            name = attrName;\n\n        if (attrName === 'href' &&\n            toString.call(element.prop('href')) === '[object SVGAnimatedString]') {\n          name = 'xlinkHref';\n          attr.$attr[name] = 'xlink:href';\n          propName = null;\n        }\n\n        // We need to sanitize the url at least once, in case it is a constant\n        // non-interpolated attribute.\n        attr.$set(normalized, $sce.getTrustedMediaUrl(attr[normalized]));\n\n        attr.$observe(normalized, function(value) {\n          if (!value) {\n            if (attrName === 'href') {\n              attr.$set(name, null);\n            }\n            return;\n          }\n\n          attr.$set(name, value);\n\n          // Support: IE 9-11 only\n          // On IE, if \"ng:src\" directive declaration is used and \"src\" attribute doesn't exist\n          // then calling element.setAttribute('src', 'foo') doesn't do anything, so we need\n          // to set the property as well to achieve the desired effect.\n          // We use attr[attrName] value since $set might have sanitized the url.\n          if (msie && propName) element.prop(propName, attr[name]);\n        });\n      }\n    };\n  }];\n});\n\n/* global -nullFormCtrl, -PENDING_CLASS, -SUBMITTED_CLASS\n */\nvar nullFormCtrl = {\n  $addControl: noop,\n  $getControls: valueFn([]),\n  $$renameControl: nullFormRenameControl,\n  $removeControl: noop,\n  $setValidity: noop,\n  $setDirty: noop,\n  $setPristine: noop,\n  $setSubmitted: noop,\n  $$setSubmitted: noop\n},\nPENDING_CLASS = 'ng-pending',\nSUBMITTED_CLASS = 'ng-submitted';\n\nfunction nullFormRenameControl(control, name) {\n  control.$name = name;\n}\n\n/**\n * @ngdoc type\n * @name form.FormController\n *\n * @property {boolean} $pristine True if user has not interacted with the form yet.\n * @property {boolean} $dirty True if user has already interacted with the form.\n * @property {boolean} $valid True if all of the containing forms and controls are valid.\n * @property {boolean} $invalid True if at least one containing control or form is invalid.\n * @property {boolean} $submitted True if user has submitted the form even if its invalid.\n *\n * @property {Object} $pending An object hash, containing references to controls or forms with\n *  pending validators, where:\n *\n *  - keys are validations tokens (error names).\n *  - values are arrays of controls or forms that have a pending validator for the given error name.\n *\n * See {@link form.FormController#$error $error} for a list of built-in validation tokens.\n *\n * @property {Object} $error An object hash, containing references to controls or forms with failing\n *  validators, where:\n *\n *  - keys are validation tokens (error names),\n *  - values are arrays of controls or forms that have a failing validator for the given error name.\n *\n *  Built-in validation tokens:\n *  - `email`\n *  - `max`\n *  - `maxlength`\n *  - `min`\n *  - `minlength`\n *  - `number`\n *  - `pattern`\n *  - `required`\n *  - `url`\n *  - `date`\n *  - `datetimelocal`\n *  - `time`\n *  - `week`\n *  - `month`\n *\n * @description\n * `FormController` keeps track of all its controls and nested forms as well as the state of them,\n * such as being valid/invalid or dirty/pristine.\n *\n * Each {@link ng.directive:form form} directive creates an instance\n * of `FormController`.\n *\n */\n//asks for $scope to fool the BC controller module\nFormController.$inject = ['$element', '$attrs', '$scope', '$animate', '$interpolate'];\nfunction FormController($element, $attrs, $scope, $animate, $interpolate) {\n  this.$$controls = [];\n\n  // init state\n  this.$error = {};\n  this.$$success = {};\n  this.$pending = undefined;\n  this.$name = $interpolate($attrs.name || $attrs.ngForm || '')($scope);\n  this.$dirty = false;\n  this.$pristine = true;\n  this.$valid = true;\n  this.$invalid = false;\n  this.$submitted = false;\n  this.$$parentForm = nullFormCtrl;\n\n  this.$$element = $element;\n  this.$$animate = $animate;\n\n  setupValidity(this);\n}\n\nFormController.prototype = {\n  /**\n   * @ngdoc method\n   * @name form.FormController#$rollbackViewValue\n   *\n   * @description\n   * Rollback all form controls pending updates to the `$modelValue`.\n   *\n   * Updates may be pending by a debounced event or because the input is waiting for a some future\n   * event defined in `ng-model-options`. This method is typically needed by the reset button of\n   * a form that uses `ng-model-options` to pend updates.\n   */\n  $rollbackViewValue: function() {\n    forEach(this.$$controls, function(control) {\n      control.$rollbackViewValue();\n    });\n  },\n\n  /**\n   * @ngdoc method\n   * @name form.FormController#$commitViewValue\n   *\n   * @description\n   * Commit all form controls pending updates to the `$modelValue`.\n   *\n   * Updates may be pending by a debounced event or because the input is waiting for a some future\n   * event defined in `ng-model-options`. This method is rarely needed as `NgModelController`\n   * usually handles calling this in response to input events.\n   */\n  $commitViewValue: function() {\n    forEach(this.$$controls, function(control) {\n      control.$commitViewValue();\n    });\n  },\n\n  /**\n   * @ngdoc method\n   * @name form.FormController#$addControl\n   * @param {object} control control object, either a {@link form.FormController} or an\n   * {@link ngModel.NgModelController}\n   *\n   * @description\n   * Register a control with the form. Input elements using ngModelController do this automatically\n   * when they are linked.\n   *\n   * Note that the current state of the control will not be reflected on the new parent form. This\n   * is not an issue with normal use, as freshly compiled and linked controls are in a `$pristine`\n   * state.\n   *\n   * However, if the method is used programmatically, for example by adding dynamically created controls,\n   * or controls that have been previously removed without destroying their corresponding DOM element,\n   * it's the developers responsibility to make sure the current state propagates to the parent form.\n   *\n   * For example, if an input control is added that is already `$dirty` and has `$error` properties,\n   * calling `$setDirty()` and `$validate()` afterwards will propagate the state to the parent form.\n   */\n  $addControl: function(control) {\n    // Breaking change - before, inputs whose name was \"hasOwnProperty\" were quietly ignored\n    // and not added to the scope.  Now we throw an error.\n    assertNotHasOwnProperty(control.$name, 'input');\n    this.$$controls.push(control);\n\n    if (control.$name) {\n      this[control.$name] = control;\n    }\n\n    control.$$parentForm = this;\n  },\n\n  /**\n   * @ngdoc method\n   * @name form.FormController#$getControls\n   * @returns {Array} the controls that are currently part of this form\n   *\n   * @description\n   * This method returns a **shallow copy** of the controls that are currently part of this form.\n   * The controls can be instances of {@link form.FormController `FormController`}\n   * ({@link ngForm \"child-forms\"}) and of {@link ngModel.NgModelController `NgModelController`}.\n   * If you need access to the controls of child-forms, you have to call `$getControls()`\n   * recursively on them.\n   * This can be used for example to iterate over all controls to validate them.\n   *\n   * The controls can be accessed normally, but adding to, or removing controls from the array has\n   * no effect on the form. Instead, use {@link form.FormController#$addControl `$addControl()`} and\n   * {@link form.FormController#$removeControl `$removeControl()`} for this use-case.\n   * Likewise, adding a control to, or removing a control from the form is not reflected\n   * in the shallow copy. That means you should get a fresh copy from `$getControls()` every time\n   * you need access to the controls.\n   */\n  $getControls: function() {\n    return shallowCopy(this.$$controls);\n  },\n\n  // Private API: rename a form control\n  $$renameControl: function(control, newName) {\n    var oldName = control.$name;\n\n    if (this[oldName] === control) {\n      delete this[oldName];\n    }\n    this[newName] = control;\n    control.$name = newName;\n  },\n\n  /**\n   * @ngdoc method\n   * @name form.FormController#$removeControl\n   * @param {object} control control object, either a {@link form.FormController} or an\n   * {@link ngModel.NgModelController}\n   *\n   * @description\n   * Deregister a control from the form.\n   *\n   * Input elements using ngModelController do this automatically when they are destroyed.\n   *\n   * Note that only the removed control's validation state (`$errors`etc.) will be removed from the\n   * form. `$dirty`, `$submitted` states will not be changed, because the expected behavior can be\n   * different from case to case. For example, removing the only `$dirty` control from a form may or\n   * may not mean that the form is still `$dirty`.\n   */\n  $removeControl: function(control) {\n    if (control.$name && this[control.$name] === control) {\n      delete this[control.$name];\n    }\n    forEach(this.$pending, function(value, name) {\n      // eslint-disable-next-line no-invalid-this\n      this.$setValidity(name, null, control);\n    }, this);\n    forEach(this.$error, function(value, name) {\n      // eslint-disable-next-line no-invalid-this\n      this.$setValidity(name, null, control);\n    }, this);\n    forEach(this.$$success, function(value, name) {\n      // eslint-disable-next-line no-invalid-this\n      this.$setValidity(name, null, control);\n    }, this);\n\n    arrayRemove(this.$$controls, control);\n    control.$$parentForm = nullFormCtrl;\n  },\n\n  /**\n   * @ngdoc method\n   * @name form.FormController#$setDirty\n   *\n   * @description\n   * Sets the form to a dirty state.\n   *\n   * This method can be called to add the 'ng-dirty' class and set the form to a dirty\n   * state (ng-dirty class). This method will also propagate to parent forms.\n   */\n  $setDirty: function() {\n    this.$$animate.removeClass(this.$$element, PRISTINE_CLASS);\n    this.$$animate.addClass(this.$$element, DIRTY_CLASS);\n    this.$dirty = true;\n    this.$pristine = false;\n    this.$$parentForm.$setDirty();\n  },\n\n  /**\n   * @ngdoc method\n   * @name form.FormController#$setPristine\n   *\n   * @description\n   * Sets the form to its pristine state.\n   *\n   * This method sets the form's `$pristine` state to true, the `$dirty` state to false, removes\n   * the `ng-dirty` class and adds the `ng-pristine` class. Additionally, it sets the `$submitted`\n   * state to false.\n   *\n   * This method will also propagate to all the controls contained in this form.\n   *\n   * Setting a form back to a pristine state is often useful when we want to 'reuse' a form after\n   * saving or resetting it.\n   */\n  $setPristine: function() {\n    this.$$animate.setClass(this.$$element, PRISTINE_CLASS, DIRTY_CLASS + ' ' + SUBMITTED_CLASS);\n    this.$dirty = false;\n    this.$pristine = true;\n    this.$submitted = false;\n    forEach(this.$$controls, function(control) {\n      control.$setPristine();\n    });\n  },\n\n  /**\n   * @ngdoc method\n   * @name form.FormController#$setUntouched\n   *\n   * @description\n   * Sets the form to its untouched state.\n   *\n   * This method can be called to remove the 'ng-touched' class and set the form controls to their\n   * untouched state (ng-untouched class).\n   *\n   * Setting a form controls back to their untouched state is often useful when setting the form\n   * back to its pristine state.\n   */\n  $setUntouched: function() {\n    forEach(this.$$controls, function(control) {\n      control.$setUntouched();\n    });\n  },\n\n  /**\n   * @ngdoc method\n   * @name form.FormController#$setSubmitted\n   *\n   * @description\n   * Sets the form to its `$submitted` state. This will also set `$submitted` on all child and\n   * parent forms of the form.\n   */\n  $setSubmitted: function() {\n    var rootForm = this;\n    while (rootForm.$$parentForm && (rootForm.$$parentForm !== nullFormCtrl)) {\n      rootForm = rootForm.$$parentForm;\n    }\n    rootForm.$$setSubmitted();\n  },\n\n  $$setSubmitted: function() {\n    this.$$animate.addClass(this.$$element, SUBMITTED_CLASS);\n    this.$submitted = true;\n    forEach(this.$$controls, function(control) {\n      if (control.$$setSubmitted) {\n        control.$$setSubmitted();\n      }\n    });\n  }\n};\n\n/**\n * @ngdoc method\n * @name form.FormController#$setValidity\n *\n * @description\n * Change the validity state of the form, and notify the parent form (if any).\n *\n * Application developers will rarely need to call this method directly. It is used internally, by\n * {@link ngModel.NgModelController#$setValidity NgModelController.$setValidity()}, to propagate a\n * control's validity state to the parent `FormController`.\n *\n * @param {string} validationErrorKey Name of the validator. The `validationErrorKey` will be\n *        assigned to either `$error[validationErrorKey]` or `$pending[validationErrorKey]` (for\n *        unfulfilled `$asyncValidators`), so that it is available for data-binding. The\n *        `validationErrorKey` should be in camelCase and will get converted into dash-case for\n *        class name. Example: `myError` will result in `ng-valid-my-error` and\n *        `ng-invalid-my-error` classes and can be bound to as `{{ someForm.$error.myError }}`.\n * @param {boolean} isValid Whether the current state is valid (true), invalid (false), pending\n *        (undefined),  or skipped (null). Pending is used for unfulfilled `$asyncValidators`.\n *        Skipped is used by AngularJS when validators do not run because of parse errors and when\n *        `$asyncValidators` do not run because any of the `$validators` failed.\n * @param {NgModelController | FormController} controller - The controller whose validity state is\n *        triggering the change.\n */\naddSetValidityMethod({\n  clazz: FormController,\n  set: function(object, property, controller) {\n    var list = object[property];\n    if (!list) {\n      object[property] = [controller];\n    } else {\n      var index = list.indexOf(controller);\n      if (index === -1) {\n        list.push(controller);\n      }\n    }\n  },\n  unset: function(object, property, controller) {\n    var list = object[property];\n    if (!list) {\n      return;\n    }\n    arrayRemove(list, controller);\n    if (list.length === 0) {\n      delete object[property];\n    }\n  }\n});\n\n/**\n * @ngdoc directive\n * @name ngForm\n * @restrict EAC\n *\n * @description\n * Helper directive that makes it possible to create control groups inside a\n * {@link ng.directive:form `form`} directive.\n * These \"child forms\" can be used, for example, to determine the validity of a sub-group of\n * controls.\n *\n * <div class=\"alert alert-danger\">\n * **Note**: `ngForm` cannot be used as a replacement for `<form>`, because it lacks its\n * [built-in HTML functionality](https://html.spec.whatwg.org/#the-form-element).\n * Specifically, you cannot submit `ngForm` like a `<form>` tag. That means,\n * you cannot send data to the server with `ngForm`, or integrate it with\n * {@link ng.directive:ngSubmit `ngSubmit`}.\n * </div>\n *\n * @param {string=} ngForm|name Name of the form. If specified, the form controller will\n *                              be published into the related scope, under this name.\n *\n */\n\n /**\n * @ngdoc directive\n * @name form\n * @restrict E\n *\n * @description\n * Directive that instantiates\n * {@link form.FormController FormController}.\n *\n * If the `name` attribute is specified, the form controller is published onto the current scope under\n * this name.\n *\n * ## Alias: {@link ng.directive:ngForm `ngForm`}\n *\n * In AngularJS, forms can be nested. This means that the outer form is valid when all of the child\n * forms are valid as well. However, browsers do not allow nesting of `<form>` elements, so\n * AngularJS provides the {@link ng.directive:ngForm `ngForm`} directive, which behaves identically to\n * `form` but can be nested. Nested forms can be useful, for example, if the validity of a sub-group\n * of controls needs to be determined.\n *\n * ## CSS classes\n *  - `ng-valid` is set if the form is valid.\n *  - `ng-invalid` is set if the form is invalid.\n *  - `ng-pending` is set if the form is pending.\n *  - `ng-pristine` is set if the form is pristine.\n *  - `ng-dirty` is set if the form is dirty.\n *  - `ng-submitted` is set if the form was submitted.\n *\n * Keep in mind that ngAnimate can detect each of these classes when added and removed.\n *\n *\n * ## Submitting a form and preventing the default action\n *\n * Since the role of forms in client-side AngularJS applications is different than in classical\n * roundtrip apps, it is desirable for the browser not to translate the form submission into a full\n * page reload that sends the data to the server. Instead some javascript logic should be triggered\n * to handle the form submission in an application-specific way.\n *\n * For this reason, AngularJS prevents the default action (form submission to the server) unless the\n * `<form>` element has an `action` attribute specified.\n *\n * You can use one of the following two ways to specify what javascript method should be called when\n * a form is submitted:\n *\n * - {@link ng.directive:ngSubmit ngSubmit} directive on the form element\n * - {@link ng.directive:ngClick ngClick} directive on the first\n  *  button or input field of type submit (input[type=submit])\n *\n * To prevent double execution of the handler, use only one of the {@link ng.directive:ngSubmit ngSubmit}\n * or {@link ng.directive:ngClick ngClick} directives.\n * This is because of the following form submission rules in the HTML specification:\n *\n * - If a form has only one input field then hitting enter in this field triggers form submit\n * (`ngSubmit`)\n * - if a form has 2+ input fields and no buttons or input[type=submit] then hitting enter\n * doesn't trigger submit\n * - if a form has one or more input fields and one or more buttons or input[type=submit] then\n * hitting enter in any of the input fields will trigger the click handler on the *first* button or\n * input[type=submit] (`ngClick`) *and* a submit handler on the enclosing form (`ngSubmit`)\n *\n * Any pending `ngModelOptions` changes will take place immediately when an enclosing form is\n * submitted. Note that `ngClick` events will occur before the model is updated. Use `ngSubmit`\n * to have access to the updated model.\n *\n * @animations\n * Animations in ngForm are triggered when any of the associated CSS classes are added and removed.\n * These classes are: `.ng-pristine`, `.ng-dirty`, `.ng-invalid` and `.ng-valid` as well as any\n * other validations that are performed within the form. Animations in ngForm are similar to how\n * they work in ngClass and animations can be hooked into using CSS transitions, keyframes as well\n * as JS animations.\n *\n * The following example shows a simple way to utilize CSS transitions to style a form element\n * that has been rendered as invalid after it has been validated:\n *\n * <pre>\n * //be sure to include ngAnimate as a module to hook into more\n * //advanced animations\n * .my-form {\n *   transition:0.5s linear all;\n *   background: white;\n * }\n * .my-form.ng-invalid {\n *   background: red;\n *   color:white;\n * }\n * </pre>\n *\n * @example\n    <example name=\"ng-form\" deps=\"angular-animate.js\" animations=\"true\" fixBase=\"true\" module=\"formExample\">\n      <file name=\"index.html\">\n       <script>\n         angular.module('formExample', [])\n           .controller('FormController', ['$scope', function($scope) {\n             $scope.userType = 'guest';\n           }]);\n       </script>\n       <style>\n        .my-form {\n          transition:all linear 0.5s;\n          background: transparent;\n        }\n        .my-form.ng-invalid {\n          background: red;\n        }\n       </style>\n       <form name=\"myForm\" ng-controller=\"FormController\" class=\"my-form\">\n         userType: <input name=\"input\" ng-model=\"userType\" required>\n         <span class=\"error\" ng-show=\"myForm.input.$error.required\">Required!</span><br>\n         <code>userType = {{userType}}</code><br>\n         <code>myForm.input.$valid = {{myForm.input.$valid}}</code><br>\n         <code>myForm.input.$error = {{myForm.input.$error}}</code><br>\n         <code>myForm.$valid = {{myForm.$valid}}</code><br>\n         <code>myForm.$error.required = {{!!myForm.$error.required}}</code><br>\n        </form>\n      </file>\n      <file name=\"protractor.js\" type=\"protractor\">\n        it('should initialize to model', function() {\n          var userType = element(by.binding('userType'));\n          var valid = element(by.binding('myForm.input.$valid'));\n\n          expect(userType.getText()).toContain('guest');\n          expect(valid.getText()).toContain('true');\n        });\n\n        it('should be invalid if empty', function() {\n          var userType = element(by.binding('userType'));\n          var valid = element(by.binding('myForm.input.$valid'));\n          var userInput = element(by.model('userType'));\n\n          userInput.clear();\n          userInput.sendKeys('');\n\n          expect(userType.getText()).toEqual('userType =');\n          expect(valid.getText()).toContain('false');\n        });\n      </file>\n    </example>\n *\n * @param {string=} name Name of the form. If specified, the form controller will be published into\n *                       related scope, under this name.\n */\nvar formDirectiveFactory = function(isNgForm) {\n  return ['$timeout', '$parse', function($timeout, $parse) {\n    var formDirective = {\n      name: 'form',\n      restrict: isNgForm ? 'EAC' : 'E',\n      require: ['form', '^^?form'], //first is the form's own ctrl, second is an optional parent form\n      controller: FormController,\n      compile: function ngFormCompile(formElement, attr) {\n        // Setup initial state of the control\n        formElement.addClass(PRISTINE_CLASS).addClass(VALID_CLASS);\n\n        var nameAttr = attr.name ? 'name' : (isNgForm && attr.ngForm ? 'ngForm' : false);\n\n        return {\n          pre: function ngFormPreLink(scope, formElement, attr, ctrls) {\n            var controller = ctrls[0];\n\n            // if `action` attr is not present on the form, prevent the default action (submission)\n            if (!('action' in attr)) {\n              // we can't use jq events because if a form is destroyed during submission the default\n              // action is not prevented. see #1238\n              //\n              // IE 9 is not affected because it doesn't fire a submit event and try to do a full\n              // page reload if the form was destroyed by submission of the form via a click handler\n              // on a button in the form. Looks like an IE9 specific bug.\n              var handleFormSubmission = function(event) {\n                scope.$apply(function() {\n                  controller.$commitViewValue();\n                  controller.$setSubmitted();\n                });\n\n                event.preventDefault();\n              };\n\n              formElement[0].addEventListener('submit', handleFormSubmission);\n\n              // unregister the preventDefault listener so that we don't not leak memory but in a\n              // way that will achieve the prevention of the default action.\n              formElement.on('$destroy', function() {\n                $timeout(function() {\n                  formElement[0].removeEventListener('submit', handleFormSubmission);\n                }, 0, false);\n              });\n            }\n\n            var parentFormCtrl = ctrls[1] || controller.$$parentForm;\n            parentFormCtrl.$addControl(controller);\n\n            var setter = nameAttr ? getSetter(controller.$name) : noop;\n\n            if (nameAttr) {\n              setter(scope, controller);\n              attr.$observe(nameAttr, function(newValue) {\n                if (controller.$name === newValue) return;\n                setter(scope, undefined);\n                controller.$$parentForm.$$renameControl(controller, newValue);\n                setter = getSetter(controller.$name);\n                setter(scope, controller);\n              });\n            }\n            formElement.on('$destroy', function() {\n              controller.$$parentForm.$removeControl(controller);\n              setter(scope, undefined);\n              extend(controller, nullFormCtrl); //stop propagating child destruction handlers upwards\n            });\n          }\n        };\n      }\n    };\n\n    return formDirective;\n\n    function getSetter(expression) {\n      if (expression === '') {\n        //create an assignable expression, so forms with an empty name can be renamed later\n        return $parse('this[\"\"]').assign;\n      }\n      return $parse(expression).assign || noop;\n    }\n  }];\n};\n\nvar formDirective = formDirectiveFactory();\nvar ngFormDirective = formDirectiveFactory(true);\n\n\n\n// helper methods\nfunction setupValidity(instance) {\n  instance.$$classCache = {};\n  instance.$$classCache[INVALID_CLASS] = !(instance.$$classCache[VALID_CLASS] = instance.$$element.hasClass(VALID_CLASS));\n}\nfunction addSetValidityMethod(context) {\n  var clazz = context.clazz,\n      set = context.set,\n      unset = context.unset;\n\n  clazz.prototype.$setValidity = function(validationErrorKey, state, controller) {\n    if (isUndefined(state)) {\n      createAndSet(this, '$pending', validationErrorKey, controller);\n    } else {\n      unsetAndCleanup(this, '$pending', validationErrorKey, controller);\n    }\n    if (!isBoolean(state)) {\n      unset(this.$error, validationErrorKey, controller);\n      unset(this.$$success, validationErrorKey, controller);\n    } else {\n      if (state) {\n        unset(this.$error, validationErrorKey, controller);\n        set(this.$$success, validationErrorKey, controller);\n      } else {\n        set(this.$error, validationErrorKey, controller);\n        unset(this.$$success, validationErrorKey, controller);\n      }\n    }\n    if (this.$pending) {\n      cachedToggleClass(this, PENDING_CLASS, true);\n      this.$valid = this.$invalid = undefined;\n      toggleValidationCss(this, '', null);\n    } else {\n      cachedToggleClass(this, PENDING_CLASS, false);\n      this.$valid = isObjectEmpty(this.$error);\n      this.$invalid = !this.$valid;\n      toggleValidationCss(this, '', this.$valid);\n    }\n\n    // re-read the state as the set/unset methods could have\n    // combined state in this.$error[validationError] (used for forms),\n    // where setting/unsetting only increments/decrements the value,\n    // and does not replace it.\n    var combinedState;\n    if (this.$pending && this.$pending[validationErrorKey]) {\n      combinedState = undefined;\n    } else if (this.$error[validationErrorKey]) {\n      combinedState = false;\n    } else if (this.$$success[validationErrorKey]) {\n      combinedState = true;\n    } else {\n      combinedState = null;\n    }\n\n    toggleValidationCss(this, validationErrorKey, combinedState);\n    this.$$parentForm.$setValidity(validationErrorKey, combinedState, this);\n  };\n\n  function createAndSet(ctrl, name, value, controller) {\n    if (!ctrl[name]) {\n      ctrl[name] = {};\n    }\n    set(ctrl[name], value, controller);\n  }\n\n  function unsetAndCleanup(ctrl, name, value, controller) {\n    if (ctrl[name]) {\n      unset(ctrl[name], value, controller);\n    }\n    if (isObjectEmpty(ctrl[name])) {\n      ctrl[name] = undefined;\n    }\n  }\n\n  function cachedToggleClass(ctrl, className, switchValue) {\n    if (switchValue && !ctrl.$$classCache[className]) {\n      ctrl.$$animate.addClass(ctrl.$$element, className);\n      ctrl.$$classCache[className] = true;\n    } else if (!switchValue && ctrl.$$classCache[className]) {\n      ctrl.$$animate.removeClass(ctrl.$$element, className);\n      ctrl.$$classCache[className] = false;\n    }\n  }\n\n  function toggleValidationCss(ctrl, validationErrorKey, isValid) {\n    validationErrorKey = validationErrorKey ? '-' + snake_case(validationErrorKey, '-') : '';\n\n    cachedToggleClass(ctrl, VALID_CLASS + validationErrorKey, isValid === true);\n    cachedToggleClass(ctrl, INVALID_CLASS + validationErrorKey, isValid === false);\n  }\n}\n\nfunction isObjectEmpty(obj) {\n  if (obj) {\n    for (var prop in obj) {\n      if (obj.hasOwnProperty(prop)) {\n        return false;\n      }\n    }\n  }\n  return true;\n}\n\n/* global\n  VALID_CLASS: false,\n  INVALID_CLASS: false,\n  PRISTINE_CLASS: false,\n  DIRTY_CLASS: false,\n  ngModelMinErr: false\n*/\n\n// Regex code was initially obtained from SO prior to modification: https://stackoverflow.com/questions/3143070/javascript-regex-iso-datetime#answer-3143231\nvar ISO_DATE_REGEXP = /^\\d{4,}-[01]\\d-[0-3]\\dT[0-2]\\d:[0-5]\\d:[0-5]\\d\\.\\d+(?:[+-][0-2]\\d:[0-5]\\d|Z)$/;\n// See valid URLs in RFC3987 (http://tools.ietf.org/html/rfc3987)\n// Note: We are being more lenient, because browsers are too.\n//   1. Scheme\n//   2. Slashes\n//   3. Username\n//   4. Password\n//   5. Hostname\n//   6. Port\n//   7. Path\n//   8. Query\n//   9. Fragment\n//                 1111111111111111 222   333333    44444        55555555555555555555555     666     77777777     8888888     999\nvar URL_REGEXP = /^[a-z][a-z\\d.+-]*:\\/*(?:[^:@]+(?::[^@]+)?@)?(?:[^\\s:/?#]+|\\[[a-f\\d:]+])(?::\\d+)?(?:\\/[^?#]*)?(?:\\?[^#]*)?(?:#.*)?$/i;\n// eslint-disable-next-line max-len\nvar EMAIL_REGEXP = /^(?=.{1,254}$)(?=.{1,64}@)[-!#$%&'*+/0-9=?A-Z^_`a-z{|}~]+(\\.[-!#$%&'*+/0-9=?A-Z^_`a-z{|}~]+)*@[A-Za-z0-9]([A-Za-z0-9-]{0,61}[A-Za-z0-9])?(\\.[A-Za-z0-9]([A-Za-z0-9-]{0,61}[A-Za-z0-9])?)*$/;\nvar NUMBER_REGEXP = /^\\s*(-|\\+)?(\\d+|(\\d*(\\.\\d*)))([eE][+-]?\\d+)?\\s*$/;\nvar DATE_REGEXP = /^(\\d{4,})-(\\d{2})-(\\d{2})$/;\nvar DATETIMELOCAL_REGEXP = /^(\\d{4,})-(\\d\\d)-(\\d\\d)T(\\d\\d):(\\d\\d)(?::(\\d\\d)(\\.\\d{1,3})?)?$/;\nvar WEEK_REGEXP = /^(\\d{4,})-W(\\d\\d)$/;\nvar MONTH_REGEXP = /^(\\d{4,})-(\\d\\d)$/;\nvar TIME_REGEXP = /^(\\d\\d):(\\d\\d)(?::(\\d\\d)(\\.\\d{1,3})?)?$/;\n\nvar PARTIAL_VALIDATION_EVENTS = 'keydown wheel mousedown';\nvar PARTIAL_VALIDATION_TYPES = createMap();\nforEach('date,datetime-local,month,time,week'.split(','), function(type) {\n  PARTIAL_VALIDATION_TYPES[type] = true;\n});\n\nvar inputType = {\n\n  /**\n   * @ngdoc input\n   * @name input[text]\n   *\n   * @description\n   * Standard HTML text input with AngularJS data binding, inherited by most of the `input` elements.\n   *\n   *\n   * @param {string} ngModel Assignable AngularJS expression to data-bind to.\n   * @param {string=} name Property name of the form under which the control is published.\n   * @param {string=} required Adds `required` validation error key if the value is not entered.\n   * @param {string=} ngRequired Adds `required` attribute and `required` validation constraint to\n   *    the element when the ngRequired expression evaluates to true. Use `ngRequired` instead of\n   *    `required` when you want to data-bind to the `required` attribute.\n   * @param {number=} ngMinlength Sets `minlength` validation error key if the value is shorter than\n   *    minlength.\n   * @param {number=} ngMaxlength Sets `maxlength` validation error key if the value is longer than\n   *    maxlength. Setting the attribute to a negative or non-numeric value, allows view values of\n   *    any length.\n   * @param {string=} pattern Similar to `ngPattern` except that the attribute value is the actual string\n   *    that contains the regular expression body that will be converted to a regular expression\n   *    as in the ngPattern directive.\n   * @param {string=} ngPattern Sets `pattern` validation error key if the ngModel {@link ngModel.NgModelController#$viewValue $viewValue}\n   *    does not match a RegExp found by evaluating the AngularJS expression given in the attribute value.\n   *    If the expression evaluates to a RegExp object, then this is used directly.\n   *    If the expression evaluates to a string, then it will be converted to a RegExp\n   *    after wrapping it in `^` and `$` characters. For instance, `\"abc\"` will be converted to\n   *    `new RegExp('^abc$')`.<br />\n   *    **Note:** Avoid using the `g` flag on the RegExp, as it will cause each successive search to\n   *    start at the index of the last search's match, thus not taking the whole input value into\n   *    account.\n   * @param {string=} ngChange AngularJS expression to be executed when input changes due to user\n   *    interaction with the input element.\n   * @param {boolean=} [ngTrim=true] If set to false AngularJS will not automatically trim the input.\n   *    This parameter is ignored for input[type=password] controls, which will never trim the\n   *    input.\n   *\n   * @example\n      <example name=\"text-input-directive\" module=\"textInputExample\">\n        <file name=\"index.html\">\n         <script>\n           angular.module('textInputExample', [])\n             .controller('ExampleController', ['$scope', function($scope) {\n               $scope.example = {\n                 text: 'guest',\n                 word: /^\\s*\\w*\\s*$/\n               };\n             }]);\n         </script>\n         <form name=\"myForm\" ng-controller=\"ExampleController\">\n           <label>Single word:\n             <input type=\"text\" name=\"input\" ng-model=\"example.text\"\n                    ng-pattern=\"example.word\" required ng-trim=\"false\">\n           </label>\n           <div role=\"alert\">\n             <span class=\"error\" ng-show=\"myForm.input.$error.required\">\n               Required!</span>\n             <span class=\"error\" ng-show=\"myForm.input.$error.pattern\">\n               Single word only!</span>\n           </div>\n           <code>text = {{example.text}}</code><br/>\n           <code>myForm.input.$valid = {{myForm.input.$valid}}</code><br/>\n           <code>myForm.input.$error = {{myForm.input.$error}}</code><br/>\n           <code>myForm.$valid = {{myForm.$valid}}</code><br/>\n           <code>myForm.$error.required = {{!!myForm.$error.required}}</code><br/>\n          </form>\n        </file>\n        <file name=\"protractor.js\" type=\"protractor\">\n          var text = element(by.binding('example.text'));\n          var valid = element(by.binding('myForm.input.$valid'));\n          var input = element(by.model('example.text'));\n\n          it('should initialize to model', function() {\n            expect(text.getText()).toContain('guest');\n            expect(valid.getText()).toContain('true');\n          });\n\n          it('should be invalid if empty', function() {\n            input.clear();\n            input.sendKeys('');\n\n            expect(text.getText()).toEqual('text =');\n            expect(valid.getText()).toContain('false');\n          });\n\n          it('should be invalid if multi word', function() {\n            input.clear();\n            input.sendKeys('hello world');\n\n            expect(valid.getText()).toContain('false');\n          });\n        </file>\n      </example>\n   */\n  'text': textInputType,\n\n    /**\n     * @ngdoc input\n     * @name input[date]\n     *\n     * @description\n     * Input with date validation and transformation. In browsers that do not yet support\n     * the HTML5 date input, a text element will be used. In that case, text must be entered in a valid ISO-8601\n     * date format (yyyy-MM-dd), for example: `2009-01-06`. Since many\n     * modern browsers do not yet support this input type, it is important to provide cues to users on the\n     * expected input format via a placeholder or label.\n     *\n     * The model must always be a Date object, otherwise AngularJS will throw an error.\n     * Invalid `Date` objects (dates whose `getTime()` is `NaN`) will be rendered as an empty string.\n     *\n     * The timezone to be used to read/write the `Date` instance in the model can be defined using\n     * {@link ng.directive:ngModelOptions ngModelOptions}. By default, this is the timezone of the browser.\n     *\n     * @param {string} ngModel Assignable AngularJS expression to data-bind to.\n     * @param {string=} name Property name of the form under which the control is published.\n     * @param {string=} min Sets the `min` validation error key if the value entered is less than `min`. This must be a\n     *   valid ISO date string (yyyy-MM-dd). You can also use interpolation inside this attribute\n     *   (e.g. `min=\"{{minDate | date:'yyyy-MM-dd'}}\"`). Note that `min` will also add native HTML5\n     *   constraint validation.\n     * @param {string=} max Sets the `max` validation error key if the value entered is greater than `max`. This must be\n     *   a valid ISO date string (yyyy-MM-dd). You can also use interpolation inside this attribute\n     *   (e.g. `max=\"{{maxDate | date:'yyyy-MM-dd'}}\"`). Note that `max` will also add native HTML5\n     *   constraint validation.\n     * @param {(date|string)=} ngMin Sets the `min` validation constraint to the Date / ISO date string\n     *   the `ngMin` expression evaluates to. Note that it does not set the `min` attribute.\n     * @param {(date|string)=} ngMax Sets the `max` validation constraint to the Date / ISO date string\n     *   the `ngMax` expression evaluates to. Note that it does not set the `max` attribute.\n     * @param {string=} required Sets `required` validation error key if the value is not entered.\n     * @param {string=} ngRequired Adds `required` attribute and `required` validation constraint to\n     *    the element when the ngRequired expression evaluates to true. Use `ngRequired` instead of\n     *    `required` when you want to data-bind to the `required` attribute.\n     * @param {string=} ngChange AngularJS expression to be executed when input changes due to user\n     *    interaction with the input element.\n     *\n     * @example\n     <example name=\"date-input-directive\" module=\"dateInputExample\">\n     <file name=\"index.html\">\n       <script>\n          angular.module('dateInputExample', [])\n            .controller('DateController', ['$scope', function($scope) {\n              $scope.example = {\n                value: new Date(2013, 9, 22)\n              };\n            }]);\n       </script>\n       <form name=\"myForm\" ng-controller=\"DateController as dateCtrl\">\n          <label for=\"exampleInput\">Pick a date in 2013:</label>\n          <input type=\"date\" id=\"exampleInput\" name=\"input\" ng-model=\"example.value\"\n              placeholder=\"yyyy-MM-dd\" min=\"2013-01-01\" max=\"2013-12-31\" required />\n          <div role=\"alert\">\n            <span class=\"error\" ng-show=\"myForm.input.$error.required\">\n                Required!</span>\n            <span class=\"error\" ng-show=\"myForm.input.$error.date\">\n                Not a valid date!</span>\n           </div>\n           <tt>value = {{example.value | date: \"yyyy-MM-dd\"}}</tt><br/>\n           <tt>myForm.input.$valid = {{myForm.input.$valid}}</tt><br/>\n           <tt>myForm.input.$error = {{myForm.input.$error}}</tt><br/>\n           <tt>myForm.$valid = {{myForm.$valid}}</tt><br/>\n           <tt>myForm.$error.required = {{!!myForm.$error.required}}</tt><br/>\n       </form>\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n        var value = element(by.binding('example.value | date: \"yyyy-MM-dd\"'));\n        var valid = element(by.binding('myForm.input.$valid'));\n\n        // currently protractor/webdriver does not support\n        // sending keys to all known HTML5 input controls\n        // for various browsers (see https://github.com/angular/protractor/issues/562).\n        function setInput(val) {\n          // set the value of the element and force validation.\n          var scr = \"var ipt = document.getElementById('exampleInput'); \" +\n          \"ipt.value = '\" + val + \"';\" +\n          \"angular.element(ipt).scope().$apply(function(s) { s.myForm[ipt.name].$setViewValue('\" + val + \"'); });\";\n          browser.executeScript(scr);\n        }\n\n        it('should initialize to model', function() {\n          expect(value.getText()).toContain('2013-10-22');\n          expect(valid.getText()).toContain('myForm.input.$valid = true');\n        });\n\n        it('should be invalid if empty', function() {\n          setInput('');\n          expect(value.getText()).toEqual('value =');\n          expect(valid.getText()).toContain('myForm.input.$valid = false');\n        });\n\n        it('should be invalid if over max', function() {\n          setInput('2015-01-01');\n          expect(value.getText()).toContain('');\n          expect(valid.getText()).toContain('myForm.input.$valid = false');\n        });\n     </file>\n     </example>\n     */\n  'date': createDateInputType('date', DATE_REGEXP,\n         createDateParser(DATE_REGEXP, ['yyyy', 'MM', 'dd']),\n         'yyyy-MM-dd'),\n\n   /**\n    * @ngdoc input\n    * @name input[datetime-local]\n    *\n    * @description\n    * Input with datetime validation and transformation. In browsers that do not yet support\n    * the HTML5 date input, a text element will be used. In that case, the text must be entered in a valid ISO-8601\n    * local datetime format (yyyy-MM-ddTHH:mm:ss), for example: `2010-12-28T14:57:00`.\n    *\n    * The model must always be a Date object, otherwise AngularJS will throw an error.\n    * Invalid `Date` objects (dates whose `getTime()` is `NaN`) will be rendered as an empty string.\n    *\n    * The timezone to be used to read/write the `Date` instance in the model can be defined using\n    * {@link ng.directive:ngModelOptions ngModelOptions}. By default, this is the timezone of the browser.\n    *\n    * The format of the displayed time can be adjusted with the\n    * {@link ng.directive:ngModelOptions#ngModelOptions-arguments ngModelOptions} `timeSecondsFormat`\n    * and `timeStripZeroSeconds`.\n    *\n    * @param {string} ngModel Assignable AngularJS expression to data-bind to.\n    * @param {string=} name Property name of the form under which the control is published.\n    * @param {string=} min Sets the `min` validation error key if the value entered is less than `min`.\n    *   This must be a valid ISO datetime format (yyyy-MM-ddTHH:mm:ss). You can also use interpolation\n    *   inside this attribute (e.g. `min=\"{{minDatetimeLocal | date:'yyyy-MM-ddTHH:mm:ss'}}\"`).\n    *   Note that `min` will also add native HTML5 constraint validation.\n    * @param {string=} max Sets the `max` validation error key if the value entered is greater than `max`.\n    *   This must be a valid ISO datetime format (yyyy-MM-ddTHH:mm:ss). You can also use interpolation\n    *   inside this attribute (e.g. `max=\"{{maxDatetimeLocal | date:'yyyy-MM-ddTHH:mm:ss'}}\"`).\n    *   Note that `max` will also add native HTML5 constraint validation.\n    * @param {(date|string)=} ngMin Sets the `min` validation error key to the Date / ISO datetime string\n    *   the `ngMin` expression evaluates to. Note that it does not set the `min` attribute.\n    * @param {(date|string)=} ngMax Sets the `max` validation error key to the Date / ISO datetime string\n    *   the `ngMax` expression evaluates to. Note that it does not set the `max` attribute.\n    * @param {string=} required Sets `required` validation error key if the value is not entered.\n    * @param {string=} ngRequired Adds `required` attribute and `required` validation constraint to\n    *    the element when the ngRequired expression evaluates to true. Use `ngRequired` instead of\n    *    `required` when you want to data-bind to the `required` attribute.\n    * @param {string=} ngChange AngularJS expression to be executed when input changes due to user\n    *    interaction with the input element.\n    *\n    * @example\n    <example name=\"datetimelocal-input-directive\" module=\"dateExample\">\n    <file name=\"index.html\">\n      <script>\n        angular.module('dateExample', [])\n          .controller('DateController', ['$scope', function($scope) {\n            $scope.example = {\n              value: new Date(2010, 11, 28, 14, 57)\n            };\n          }]);\n      </script>\n      <form name=\"myForm\" ng-controller=\"DateController as dateCtrl\">\n        <label for=\"exampleInput\">Pick a date between in 2013:</label>\n        <input type=\"datetime-local\" id=\"exampleInput\" name=\"input\" ng-model=\"example.value\"\n            placeholder=\"yyyy-MM-ddTHH:mm:ss\" min=\"2001-01-01T00:00:00\" max=\"2013-12-31T00:00:00\" required />\n        <div role=\"alert\">\n          <span class=\"error\" ng-show=\"myForm.input.$error.required\">\n              Required!</span>\n          <span class=\"error\" ng-show=\"myForm.input.$error.datetimelocal\">\n              Not a valid date!</span>\n        </div>\n        <tt>value = {{example.value | date: \"yyyy-MM-ddTHH:mm:ss\"}}</tt><br/>\n        <tt>myForm.input.$valid = {{myForm.input.$valid}}</tt><br/>\n        <tt>myForm.input.$error = {{myForm.input.$error}}</tt><br/>\n        <tt>myForm.$valid = {{myForm.$valid}}</tt><br/>\n        <tt>myForm.$error.required = {{!!myForm.$error.required}}</tt><br/>\n      </form>\n    </file>\n    <file name=\"protractor.js\" type=\"protractor\">\n      var value = element(by.binding('example.value | date: \"yyyy-MM-ddTHH:mm:ss\"'));\n      var valid = element(by.binding('myForm.input.$valid'));\n\n      // currently protractor/webdriver does not support\n      // sending keys to all known HTML5 input controls\n      // for various browsers (https://github.com/angular/protractor/issues/562).\n      function setInput(val) {\n        // set the value of the element and force validation.\n        var scr = \"var ipt = document.getElementById('exampleInput'); \" +\n        \"ipt.value = '\" + val + \"';\" +\n        \"angular.element(ipt).scope().$apply(function(s) { s.myForm[ipt.name].$setViewValue('\" + val + \"'); });\";\n        browser.executeScript(scr);\n      }\n\n      it('should initialize to model', function() {\n        expect(value.getText()).toContain('2010-12-28T14:57:00');\n        expect(valid.getText()).toContain('myForm.input.$valid = true');\n      });\n\n      it('should be invalid if empty', function() {\n        setInput('');\n        expect(value.getText()).toEqual('value =');\n        expect(valid.getText()).toContain('myForm.input.$valid = false');\n      });\n\n      it('should be invalid if over max', function() {\n        setInput('2015-01-01T23:59:00');\n        expect(value.getText()).toContain('');\n        expect(valid.getText()).toContain('myForm.input.$valid = false');\n      });\n    </file>\n    </example>\n    */\n  'datetime-local': createDateInputType('datetimelocal', DATETIMELOCAL_REGEXP,\n      createDateParser(DATETIMELOCAL_REGEXP, ['yyyy', 'MM', 'dd', 'HH', 'mm', 'ss', 'sss']),\n      'yyyy-MM-ddTHH:mm:ss.sss'),\n\n  /**\n   * @ngdoc input\n   * @name input[time]\n   *\n   * @description\n   * Input with time validation and transformation. In browsers that do not yet support\n   * the HTML5 time input, a text element will be used. In that case, the text must be entered in a valid ISO-8601\n   * local time format (HH:mm:ss), for example: `14:57:00`. Model must be a Date object. This binding will always output a\n   * Date object to the model of January 1, 1970, or local date `new Date(1970, 0, 1, HH, mm, ss)`.\n   *\n   * The model must always be a Date object, otherwise AngularJS will throw an error.\n   * Invalid `Date` objects (dates whose `getTime()` is `NaN`) will be rendered as an empty string.\n   *\n   * The timezone to be used to read/write the `Date` instance in the model can be defined using\n   * {@link ng.directive:ngModelOptions#ngModelOptions-arguments ngModelOptions}. By default,\n   * this is the timezone of the browser.\n   *\n   * The format of the displayed time can be adjusted with the\n   * {@link ng.directive:ngModelOptions#ngModelOptions-arguments ngModelOptions} `timeSecondsFormat`\n   * and `timeStripZeroSeconds`.\n   *\n   * @param {string} ngModel Assignable AngularJS expression to data-bind to.\n   * @param {string=} name Property name of the form under which the control is published.\n   * @param {string=} min Sets the `min` validation error key if the value entered is less than `min`.\n   *   This must be a valid ISO time format (HH:mm:ss). You can also use interpolation inside this\n   *   attribute (e.g. `min=\"{{minTime | date:'HH:mm:ss'}}\"`). Note that `min` will also add\n   *   native HTML5 constraint validation.\n   * @param {string=} max Sets the `max` validation error key if the value entered is greater than `max`.\n   *   This must be a valid ISO time format (HH:mm:ss). You can also use interpolation inside this\n   *   attribute (e.g. `max=\"{{maxTime | date:'HH:mm:ss'}}\"`). Note that `max` will also add\n   *   native HTML5 constraint validation.\n   * @param {(date|string)=} ngMin Sets the `min` validation constraint to the Date / ISO time string the\n   *   `ngMin` expression evaluates to. Note that it does not set the `min` attribute.\n   * @param {(date|string)=} ngMax Sets the `max` validation constraint to the Date / ISO time string the\n   *   `ngMax` expression evaluates to. Note that it does not set the `max` attribute.\n   * @param {string=} required Sets `required` validation error key if the value is not entered.\n   * @param {string=} ngRequired Adds `required` attribute and `required` validation constraint to\n   *    the element when the ngRequired expression evaluates to true. Use `ngRequired` instead of\n   *    `required` when you want to data-bind to the `required` attribute.\n   * @param {string=} ngChange AngularJS expression to be executed when input changes due to user\n   *    interaction with the input element.\n   *\n   * @example\n   <example name=\"time-input-directive\" module=\"timeExample\">\n   <file name=\"index.html\">\n     <script>\n      angular.module('timeExample', [])\n        .controller('DateController', ['$scope', function($scope) {\n          $scope.example = {\n            value: new Date(1970, 0, 1, 14, 57, 0)\n          };\n        }]);\n     </script>\n     <form name=\"myForm\" ng-controller=\"DateController as dateCtrl\">\n        <label for=\"exampleInput\">Pick a time between 8am and 5pm:</label>\n        <input type=\"time\" id=\"exampleInput\" name=\"input\" ng-model=\"example.value\"\n            placeholder=\"HH:mm:ss\" min=\"08:00:00\" max=\"17:00:00\" required />\n        <div role=\"alert\">\n          <span class=\"error\" ng-show=\"myForm.input.$error.required\">\n              Required!</span>\n          <span class=\"error\" ng-show=\"myForm.input.$error.time\">\n              Not a valid date!</span>\n        </div>\n        <tt>value = {{example.value | date: \"HH:mm:ss\"}}</tt><br/>\n        <tt>myForm.input.$valid = {{myForm.input.$valid}}</tt><br/>\n        <tt>myForm.input.$error = {{myForm.input.$error}}</tt><br/>\n        <tt>myForm.$valid = {{myForm.$valid}}</tt><br/>\n        <tt>myForm.$error.required = {{!!myForm.$error.required}}</tt><br/>\n     </form>\n   </file>\n   <file name=\"protractor.js\" type=\"protractor\">\n      var value = element(by.binding('example.value | date: \"HH:mm:ss\"'));\n      var valid = element(by.binding('myForm.input.$valid'));\n\n      // currently protractor/webdriver does not support\n      // sending keys to all known HTML5 input controls\n      // for various browsers (https://github.com/angular/protractor/issues/562).\n      function setInput(val) {\n        // set the value of the element and force validation.\n        var scr = \"var ipt = document.getElementById('exampleInput'); \" +\n        \"ipt.value = '\" + val + \"';\" +\n        \"angular.element(ipt).scope().$apply(function(s) { s.myForm[ipt.name].$setViewValue('\" + val + \"'); });\";\n        browser.executeScript(scr);\n      }\n\n      it('should initialize to model', function() {\n        expect(value.getText()).toContain('14:57:00');\n        expect(valid.getText()).toContain('myForm.input.$valid = true');\n      });\n\n      it('should be invalid if empty', function() {\n        setInput('');\n        expect(value.getText()).toEqual('value =');\n        expect(valid.getText()).toContain('myForm.input.$valid = false');\n      });\n\n      it('should be invalid if over max', function() {\n        setInput('23:59:00');\n        expect(value.getText()).toContain('');\n        expect(valid.getText()).toContain('myForm.input.$valid = false');\n      });\n   </file>\n   </example>\n   */\n  'time': createDateInputType('time', TIME_REGEXP,\n      createDateParser(TIME_REGEXP, ['HH', 'mm', 'ss', 'sss']),\n     'HH:mm:ss.sss'),\n\n   /**\n    * @ngdoc input\n    * @name input[week]\n    *\n    * @description\n    * Input with week-of-the-year validation and transformation to Date. In browsers that do not yet support\n    * the HTML5 week input, a text element will be used. In that case, the text must be entered in a valid ISO-8601\n    * week format (yyyy-W##), for example: `2013-W02`.\n    *\n    * The model must always be a Date object, otherwise AngularJS will throw an error.\n    * Invalid `Date` objects (dates whose `getTime()` is `NaN`) will be rendered as an empty string.\n    *\n    * The value of the resulting Date object will be set to Thursday at 00:00:00 of the requested week,\n    * due to ISO-8601 week numbering standards. Information on ISO's system for numbering the weeks of the\n    * year can be found at: https://en.wikipedia.org/wiki/ISO_8601#Week_dates\n    *\n    * The timezone to be used to read/write the `Date` instance in the model can be defined using\n    * {@link ng.directive:ngModelOptions ngModelOptions}. By default, this is the timezone of the browser.\n    *\n    * @param {string} ngModel Assignable AngularJS expression to data-bind to.\n    * @param {string=} name Property name of the form under which the control is published.\n    * @param {string=} min Sets the `min` validation error key if the value entered is less than `min`.\n    *   This must be a valid ISO week format (yyyy-W##). You can also use interpolation inside this\n    *   attribute (e.g. `min=\"{{minWeek | date:'yyyy-Www'}}\"`). Note that `min` will also add\n    *   native HTML5 constraint validation.\n    * @param {string=} max Sets the `max` validation error key if the value entered is greater than `max`.\n    *   This must be a valid ISO week format (yyyy-W##). You can also use interpolation inside this\n    *   attribute (e.g. `max=\"{{maxWeek | date:'yyyy-Www'}}\"`). Note that `max` will also add\n    *   native HTML5 constraint validation.\n    * @param {(date|string)=} ngMin Sets the `min` validation constraint to the Date / ISO week string\n    *   the `ngMin` expression evaluates to. Note that it does not set the `min` attribute.\n    * @param {(date|string)=} ngMax Sets the `max` validation constraint to the Date / ISO week string\n    *   the `ngMax` expression evaluates to. Note that it does not set the `max` attribute.\n    * @param {string=} required Sets `required` validation error key if the value is not entered.\n    * @param {string=} ngRequired Adds `required` attribute and `required` validation constraint to\n    *    the element when the ngRequired expression evaluates to true. Use `ngRequired` instead of\n    *    `required` when you want to data-bind to the `required` attribute.\n    * @param {string=} ngChange AngularJS expression to be executed when input changes due to user\n    *    interaction with the input element.\n    *\n    * @example\n    <example name=\"week-input-directive\" module=\"weekExample\">\n    <file name=\"index.html\">\n      <script>\n      angular.module('weekExample', [])\n        .controller('DateController', ['$scope', function($scope) {\n          $scope.example = {\n            value: new Date(2013, 0, 3)\n          };\n        }]);\n      </script>\n      <form name=\"myForm\" ng-controller=\"DateController as dateCtrl\">\n        <label>Pick a date between in 2013:\n          <input id=\"exampleInput\" type=\"week\" name=\"input\" ng-model=\"example.value\"\n                 placeholder=\"YYYY-W##\" min=\"2012-W32\"\n                 max=\"2013-W52\" required />\n        </label>\n        <div role=\"alert\">\n          <span class=\"error\" ng-show=\"myForm.input.$error.required\">\n              Required!</span>\n          <span class=\"error\" ng-show=\"myForm.input.$error.week\">\n              Not a valid date!</span>\n        </div>\n        <tt>value = {{example.value | date: \"yyyy-Www\"}}</tt><br/>\n        <tt>myForm.input.$valid = {{myForm.input.$valid}}</tt><br/>\n        <tt>myForm.input.$error = {{myForm.input.$error}}</tt><br/>\n        <tt>myForm.$valid = {{myForm.$valid}}</tt><br/>\n        <tt>myForm.$error.required = {{!!myForm.$error.required}}</tt><br/>\n      </form>\n    </file>\n    <file name=\"protractor.js\" type=\"protractor\">\n      var value = element(by.binding('example.value | date: \"yyyy-Www\"'));\n      var valid = element(by.binding('myForm.input.$valid'));\n\n      // currently protractor/webdriver does not support\n      // sending keys to all known HTML5 input controls\n      // for various browsers (https://github.com/angular/protractor/issues/562).\n      function setInput(val) {\n        // set the value of the element and force validation.\n        var scr = \"var ipt = document.getElementById('exampleInput'); \" +\n        \"ipt.value = '\" + val + \"';\" +\n        \"angular.element(ipt).scope().$apply(function(s) { s.myForm[ipt.name].$setViewValue('\" + val + \"'); });\";\n        browser.executeScript(scr);\n      }\n\n      it('should initialize to model', function() {\n        expect(value.getText()).toContain('2013-W01');\n        expect(valid.getText()).toContain('myForm.input.$valid = true');\n      });\n\n      it('should be invalid if empty', function() {\n        setInput('');\n        expect(value.getText()).toEqual('value =');\n        expect(valid.getText()).toContain('myForm.input.$valid = false');\n      });\n\n      it('should be invalid if over max', function() {\n        setInput('2015-W01');\n        expect(value.getText()).toContain('');\n        expect(valid.getText()).toContain('myForm.input.$valid = false');\n      });\n    </file>\n    </example>\n    */\n  'week': createDateInputType('week', WEEK_REGEXP, weekParser, 'yyyy-Www'),\n\n  /**\n   * @ngdoc input\n   * @name input[month]\n   *\n   * @description\n   * Input with month validation and transformation. In browsers that do not yet support\n   * the HTML5 month input, a text element will be used. In that case, the text must be entered in a valid ISO-8601\n   * month format (yyyy-MM), for example: `2009-01`.\n   *\n   * The model must always be a Date object, otherwise AngularJS will throw an error.\n   * Invalid `Date` objects (dates whose `getTime()` is `NaN`) will be rendered as an empty string.\n   * If the model is not set to the first of the month, the next view to model update will set it\n   * to the first of the month.\n   *\n   * The timezone to be used to read/write the `Date` instance in the model can be defined using\n   * {@link ng.directive:ngModelOptions ngModelOptions}. By default, this is the timezone of the browser.\n   *\n   * @param {string} ngModel Assignable AngularJS expression to data-bind to.\n   * @param {string=} name Property name of the form under which the control is published.\n   * @param {string=} min Sets the `min` validation error key if the value entered is less than `min`.\n   *   This must be a valid ISO month format (yyyy-MM). You can also use interpolation inside this\n   *   attribute (e.g. `min=\"{{minMonth | date:'yyyy-MM'}}\"`). Note that `min` will also add\n   *   native HTML5 constraint validation.\n   * @param {string=} max Sets the `max` validation error key if the value entered is greater than `max`.\n   *   This must be a valid ISO month format (yyyy-MM). You can also use interpolation inside this\n   *   attribute (e.g. `max=\"{{maxMonth | date:'yyyy-MM'}}\"`). Note that `max` will also add\n   *   native HTML5 constraint validation.\n   * @param {(date|string)=} ngMin Sets the `min` validation constraint to the Date / ISO week string\n   *   the `ngMin` expression evaluates to. Note that it does not set the `min` attribute.\n   * @param {(date|string)=} ngMax Sets the `max` validation constraint to the Date / ISO week string\n   *   the `ngMax` expression evaluates to. Note that it does not set the `max` attribute.\n\n   * @param {string=} required Sets `required` validation error key if the value is not entered.\n   * @param {string=} ngRequired Adds `required` attribute and `required` validation constraint to\n   *    the element when the ngRequired expression evaluates to true. Use `ngRequired` instead of\n   *    `required` when you want to data-bind to the `required` attribute.\n   * @param {string=} ngChange AngularJS expression to be executed when input changes due to user\n   *    interaction with the input element.\n   *\n   * @example\n   <example name=\"month-input-directive\" module=\"monthExample\">\n   <file name=\"index.html\">\n     <script>\n      angular.module('monthExample', [])\n        .controller('DateController', ['$scope', function($scope) {\n          $scope.example = {\n            value: new Date(2013, 9, 1)\n          };\n        }]);\n     </script>\n     <form name=\"myForm\" ng-controller=\"DateController as dateCtrl\">\n       <label for=\"exampleInput\">Pick a month in 2013:</label>\n       <input id=\"exampleInput\" type=\"month\" name=\"input\" ng-model=\"example.value\"\n          placeholder=\"yyyy-MM\" min=\"2013-01\" max=\"2013-12\" required />\n       <div role=\"alert\">\n         <span class=\"error\" ng-show=\"myForm.input.$error.required\">\n            Required!</span>\n         <span class=\"error\" ng-show=\"myForm.input.$error.month\">\n            Not a valid month!</span>\n       </div>\n       <tt>value = {{example.value | date: \"yyyy-MM\"}}</tt><br/>\n       <tt>myForm.input.$valid = {{myForm.input.$valid}}</tt><br/>\n       <tt>myForm.input.$error = {{myForm.input.$error}}</tt><br/>\n       <tt>myForm.$valid = {{myForm.$valid}}</tt><br/>\n       <tt>myForm.$error.required = {{!!myForm.$error.required}}</tt><br/>\n     </form>\n   </file>\n   <file name=\"protractor.js\" type=\"protractor\">\n      var value = element(by.binding('example.value | date: \"yyyy-MM\"'));\n      var valid = element(by.binding('myForm.input.$valid'));\n\n      // currently protractor/webdriver does not support\n      // sending keys to all known HTML5 input controls\n      // for various browsers (https://github.com/angular/protractor/issues/562).\n      function setInput(val) {\n        // set the value of the element and force validation.\n        var scr = \"var ipt = document.getElementById('exampleInput'); \" +\n        \"ipt.value = '\" + val + \"';\" +\n        \"angular.element(ipt).scope().$apply(function(s) { s.myForm[ipt.name].$setViewValue('\" + val + \"'); });\";\n        browser.executeScript(scr);\n      }\n\n      it('should initialize to model', function() {\n        expect(value.getText()).toContain('2013-10');\n        expect(valid.getText()).toContain('myForm.input.$valid = true');\n      });\n\n      it('should be invalid if empty', function() {\n        setInput('');\n        expect(value.getText()).toEqual('value =');\n        expect(valid.getText()).toContain('myForm.input.$valid = false');\n      });\n\n      it('should be invalid if over max', function() {\n        setInput('2015-01');\n        expect(value.getText()).toContain('');\n        expect(valid.getText()).toContain('myForm.input.$valid = false');\n      });\n   </file>\n   </example>\n   */\n  'month': createDateInputType('month', MONTH_REGEXP,\n     createDateParser(MONTH_REGEXP, ['yyyy', 'MM']),\n     'yyyy-MM'),\n\n  /**\n   * @ngdoc input\n   * @name input[number]\n   *\n   * @description\n   * Text input with number validation and transformation. Sets the `number` validation\n   * error if not a valid number.\n   *\n   * <div class=\"alert alert-warning\">\n   * The model must always be of type `number` otherwise AngularJS will throw an error.\n   * Be aware that a string containing a number is not enough. See the {@link ngModel:numfmt}\n   * error docs for more information and an example of how to convert your model if necessary.\n   * </div>\n   *\n   *\n   *\n   * @knownIssue\n   *\n   * ### HTML5 constraint validation and `allowInvalid`\n   *\n   * In browsers that follow the\n   * [HTML5 specification](https://html.spec.whatwg.org/multipage/forms.html#number-state-%28type=number%29),\n   * `input[number]` does not work as expected with {@link ngModelOptions `ngModelOptions.allowInvalid`}.\n   * If a non-number is entered in the input, the browser will report the value as an empty string,\n   * which means the view / model values in `ngModel` and subsequently the scope value\n   * will also be an empty string.\n   *\n   * @knownIssue\n   *\n   * ### Large numbers and `step` validation\n   *\n   * The `step` validation will not work correctly for very large numbers (e.g. 9999999999) due to\n   * Javascript's arithmetic limitations. If you need to handle large numbers, purpose-built\n   * libraries (e.g. https://github.com/MikeMcl/big.js/), can be included into AngularJS by\n   * {@link guide/forms#modifying-built-in-validators overwriting the validators}\n   * for `number` and / or `step`, or by {@link guide/forms#custom-validation applying custom validators}\n   * to an `input[text]` element. The source for `input[number]` type can be used as a starting\n   * point for both implementations.\n   *\n   * @param {string} ngModel Assignable AngularJS expression to data-bind to.\n   * @param {string=} name Property name of the form under which the control is published.\n   * @param {string=} min Sets the `min` validation error key if the value entered is less than `min`.\n   *    Can be interpolated.\n   * @param {string=} max Sets the `max` validation error key if the value entered is greater than `max`.\n   *    Can be interpolated.\n   * @param {string=} ngMin Like `min`, sets the `min` validation error key if the value entered is less than `ngMin`,\n   *    but does not trigger HTML5 native validation. Takes an expression.\n   * @param {string=} ngMax Like `max`, sets the `max` validation error key if the value entered is greater than `ngMax`,\n   *    but does not trigger HTML5 native validation. Takes an expression.\n   * @param {string=} step Sets the `step` validation error key if the value entered does not fit the `step` constraint.\n   *    Can be interpolated.\n   * @param {string=} ngStep Like `step`, sets the `step` validation error key if the value entered does not fit the `ngStep` constraint,\n   *    but does not trigger HTML5 native validation. Takes an expression.\n   * @param {string=} required Sets `required` validation error key if the value is not entered.\n   * @param {string=} ngRequired Adds `required` attribute and `required` validation constraint to\n   *    the element when the ngRequired expression evaluates to true. Use `ngRequired` instead of\n   *    `required` when you want to data-bind to the `required` attribute.\n   * @param {number=} ngMinlength Sets `minlength` validation error key if the value is shorter than\n   *    minlength.\n   * @param {number=} ngMaxlength Sets `maxlength` validation error key if the value is longer than\n   *    maxlength. Setting the attribute to a negative or non-numeric value, allows view values of\n   *    any length.\n   * @param {string=} pattern Similar to `ngPattern` except that the attribute value is the actual string\n   *    that contains the regular expression body that will be converted to a regular expression\n   *    as in the ngPattern directive.\n   * @param {string=} ngPattern Sets `pattern` validation error key if the ngModel {@link ngModel.NgModelController#$viewValue $viewValue}\n   *    does not match a RegExp found by evaluating the AngularJS expression given in the attribute value.\n   *    If the expression evaluates to a RegExp object, then this is used directly.\n   *    If the expression evaluates to a string, then it will be converted to a RegExp\n   *    after wrapping it in `^` and `$` characters. For instance, `\"abc\"` will be converted to\n   *    `new RegExp('^abc$')`.<br />\n   *    **Note:** Avoid using the `g` flag on the RegExp, as it will cause each successive search to\n   *    start at the index of the last search's match, thus not taking the whole input value into\n   *    account.\n   * @param {string=} ngChange AngularJS expression to be executed when input changes due to user\n   *    interaction with the input element.\n   *\n   * @example\n      <example name=\"number-input-directive\" module=\"numberExample\">\n        <file name=\"index.html\">\n         <script>\n           angular.module('numberExample', [])\n             .controller('ExampleController', ['$scope', function($scope) {\n               $scope.example = {\n                 value: 12\n               };\n             }]);\n         </script>\n         <form name=\"myForm\" ng-controller=\"ExampleController\">\n           <label>Number:\n             <input type=\"number\" name=\"input\" ng-model=\"example.value\"\n                    min=\"0\" max=\"99\" required>\n          </label>\n           <div role=\"alert\">\n             <span class=\"error\" ng-show=\"myForm.input.$error.required\">\n               Required!</span>\n             <span class=\"error\" ng-show=\"myForm.input.$error.number\">\n               Not valid number!</span>\n           </div>\n           <tt>value = {{example.value}}</tt><br/>\n           <tt>myForm.input.$valid = {{myForm.input.$valid}}</tt><br/>\n           <tt>myForm.input.$error = {{myForm.input.$error}}</tt><br/>\n           <tt>myForm.$valid = {{myForm.$valid}}</tt><br/>\n           <tt>myForm.$error.required = {{!!myForm.$error.required}}</tt><br/>\n          </form>\n        </file>\n        <file name=\"protractor.js\" type=\"protractor\">\n          var value = element(by.binding('example.value'));\n          var valid = element(by.binding('myForm.input.$valid'));\n          var input = element(by.model('example.value'));\n\n          it('should initialize to model', function() {\n            expect(value.getText()).toContain('12');\n            expect(valid.getText()).toContain('true');\n          });\n\n          it('should be invalid if empty', function() {\n            input.clear();\n            input.sendKeys('');\n            expect(value.getText()).toEqual('value =');\n            expect(valid.getText()).toContain('false');\n          });\n\n          it('should be invalid if over max', function() {\n            input.clear();\n            input.sendKeys('123');\n            expect(value.getText()).toEqual('value =');\n            expect(valid.getText()).toContain('false');\n          });\n        </file>\n      </example>\n   */\n  'number': numberInputType,\n\n\n  /**\n   * @ngdoc input\n   * @name input[url]\n   *\n   * @description\n   * Text input with URL validation. Sets the `url` validation error key if the content is not a\n   * valid URL.\n   *\n   * <div class=\"alert alert-warning\">\n   * **Note:** `input[url]` uses a regex to validate urls that is derived from the regex\n   * used in Chromium. If you need stricter validation, you can use `ng-pattern` or modify\n   * the built-in validators (see the {@link guide/forms Forms guide})\n   * </div>\n   *\n   * @param {string} ngModel Assignable AngularJS expression to data-bind to.\n   * @param {string=} name Property name of the form under which the control is published.\n   * @param {string=} required Sets `required` validation error key if the value is not entered.\n   * @param {string=} ngRequired Adds `required` attribute and `required` validation constraint to\n   *    the element when the ngRequired expression evaluates to true. Use `ngRequired` instead of\n   *    `required` when you want to data-bind to the `required` attribute.\n   * @param {number=} ngMinlength Sets `minlength` validation error key if the value is shorter than\n   *    minlength.\n   * @param {number=} ngMaxlength Sets `maxlength` validation error key if the value is longer than\n   *    maxlength. Setting the attribute to a negative or non-numeric value, allows view values of\n   *    any length.\n   * @param {string=} pattern Similar to `ngPattern` except that the attribute value is the actual string\n   *    that contains the regular expression body that will be converted to a regular expression\n   *    as in the ngPattern directive.\n   * @param {string=} ngPattern Sets `pattern` validation error key if the ngModel {@link ngModel.NgModelController#$viewValue $viewValue}\n   *    does not match a RegExp found by evaluating the AngularJS expression given in the attribute value.\n   *    If the expression evaluates to a RegExp object, then this is used directly.\n   *    If the expression evaluates to a string, then it will be converted to a RegExp\n   *    after wrapping it in `^` and `$` characters. For instance, `\"abc\"` will be converted to\n   *    `new RegExp('^abc$')`.<br />\n   *    **Note:** Avoid using the `g` flag on the RegExp, as it will cause each successive search to\n   *    start at the index of the last search's match, thus not taking the whole input value into\n   *    account.\n   * @param {string=} ngChange AngularJS expression to be executed when input changes due to user\n   *    interaction with the input element.\n   *\n   * @example\n      <example name=\"url-input-directive\" module=\"urlExample\">\n        <file name=\"index.html\">\n         <script>\n           angular.module('urlExample', [])\n             .controller('ExampleController', ['$scope', function($scope) {\n               $scope.url = {\n                 text: 'http://google.com'\n               };\n             }]);\n         </script>\n         <form name=\"myForm\" ng-controller=\"ExampleController\">\n           <label>URL:\n             <input type=\"url\" name=\"input\" ng-model=\"url.text\" required>\n           <label>\n           <div role=\"alert\">\n             <span class=\"error\" ng-show=\"myForm.input.$error.required\">\n               Required!</span>\n             <span class=\"error\" ng-show=\"myForm.input.$error.url\">\n               Not valid url!</span>\n           </div>\n           <tt>text = {{url.text}}</tt><br/>\n           <tt>myForm.input.$valid = {{myForm.input.$valid}}</tt><br/>\n           <tt>myForm.input.$error = {{myForm.input.$error}}</tt><br/>\n           <tt>myForm.$valid = {{myForm.$valid}}</tt><br/>\n           <tt>myForm.$error.required = {{!!myForm.$error.required}}</tt><br/>\n           <tt>myForm.$error.url = {{!!myForm.$error.url}}</tt><br/>\n          </form>\n        </file>\n        <file name=\"protractor.js\" type=\"protractor\">\n          var text = element(by.binding('url.text'));\n          var valid = element(by.binding('myForm.input.$valid'));\n          var input = element(by.model('url.text'));\n\n          it('should initialize to model', function() {\n            expect(text.getText()).toContain('http://google.com');\n            expect(valid.getText()).toContain('true');\n          });\n\n          it('should be invalid if empty', function() {\n            input.clear();\n            input.sendKeys('');\n\n            expect(text.getText()).toEqual('text =');\n            expect(valid.getText()).toContain('false');\n          });\n\n          it('should be invalid if not url', function() {\n            input.clear();\n            input.sendKeys('box');\n\n            expect(valid.getText()).toContain('false');\n          });\n        </file>\n      </example>\n   */\n  'url': urlInputType,\n\n\n  /**\n   * @ngdoc input\n   * @name input[email]\n   *\n   * @description\n   * Text input with email validation. Sets the `email` validation error key if not a valid email\n   * address.\n   *\n   * <div class=\"alert alert-warning\">\n   * **Note:** `input[email]` uses a regex to validate email addresses that is derived from the regex\n   * used in Chromium, which may not fulfill your app's requirements.\n   * If you need stricter (e.g. requiring a top-level domain), or more relaxed validation\n   * (e.g. allowing IPv6 address literals) you can use `ng-pattern` or\n   * modify the built-in validators (see the {@link guide/forms Forms guide}).\n   * </div>\n   *\n   * @param {string} ngModel Assignable AngularJS expression to data-bind to.\n   * @param {string=} name Property name of the form under which the control is published.\n   * @param {string=} required Sets `required` validation error key if the value is not entered.\n   * @param {string=} ngRequired Adds `required` attribute and `required` validation constraint to\n   *    the element when the ngRequired expression evaluates to true. Use `ngRequired` instead of\n   *    `required` when you want to data-bind to the `required` attribute.\n   * @param {number=} ngMinlength Sets `minlength` validation error key if the value is shorter than\n   *    minlength.\n   * @param {number=} ngMaxlength Sets `maxlength` validation error key if the value is longer than\n   *    maxlength. Setting the attribute to a negative or non-numeric value, allows view values of\n   *    any length.\n   * @param {string=} pattern Similar to `ngPattern` except that the attribute value is the actual string\n   *    that contains the regular expression body that will be converted to a regular expression\n   *    as in the ngPattern directive.\n   * @param {string=} ngPattern Sets `pattern` validation error key if the ngModel {@link ngModel.NgModelController#$viewValue $viewValue}\n   *    does not match a RegExp found by evaluating the AngularJS expression given in the attribute value.\n   *    If the expression evaluates to a RegExp object, then this is used directly.\n   *    If the expression evaluates to a string, then it will be converted to a RegExp\n   *    after wrapping it in `^` and `$` characters. For instance, `\"abc\"` will be converted to\n   *    `new RegExp('^abc$')`.<br />\n   *    **Note:** Avoid using the `g` flag on the RegExp, as it will cause each successive search to\n   *    start at the index of the last search's match, thus not taking the whole input value into\n   *    account.\n   * @param {string=} ngChange AngularJS expression to be executed when input changes due to user\n   *    interaction with the input element.\n   *\n   * @example\n      <example name=\"email-input-directive\" module=\"emailExample\">\n        <file name=\"index.html\">\n         <script>\n           angular.module('emailExample', [])\n             .controller('ExampleController', ['$scope', function($scope) {\n               $scope.email = {\n                 text: 'me@example.com'\n               };\n             }]);\n         </script>\n           <form name=\"myForm\" ng-controller=\"ExampleController\">\n             <label>Email:\n               <input type=\"email\" name=\"input\" ng-model=\"email.text\" required>\n             </label>\n             <div role=\"alert\">\n               <span class=\"error\" ng-show=\"myForm.input.$error.required\">\n                 Required!</span>\n               <span class=\"error\" ng-show=\"myForm.input.$error.email\">\n                 Not valid email!</span>\n             </div>\n             <tt>text = {{email.text}}</tt><br/>\n             <tt>myForm.input.$valid = {{myForm.input.$valid}}</tt><br/>\n             <tt>myForm.input.$error = {{myForm.input.$error}}</tt><br/>\n             <tt>myForm.$valid = {{myForm.$valid}}</tt><br/>\n             <tt>myForm.$error.required = {{!!myForm.$error.required}}</tt><br/>\n             <tt>myForm.$error.email = {{!!myForm.$error.email}}</tt><br/>\n           </form>\n         </file>\n        <file name=\"protractor.js\" type=\"protractor\">\n          var text = element(by.binding('email.text'));\n          var valid = element(by.binding('myForm.input.$valid'));\n          var input = element(by.model('email.text'));\n\n          it('should initialize to model', function() {\n            expect(text.getText()).toContain('me@example.com');\n            expect(valid.getText()).toContain('true');\n          });\n\n          it('should be invalid if empty', function() {\n            input.clear();\n            input.sendKeys('');\n            expect(text.getText()).toEqual('text =');\n            expect(valid.getText()).toContain('false');\n          });\n\n          it('should be invalid if not email', function() {\n            input.clear();\n            input.sendKeys('xxx');\n\n            expect(valid.getText()).toContain('false');\n          });\n        </file>\n      </example>\n   */\n  'email': emailInputType,\n\n\n  /**\n   * @ngdoc input\n   * @name input[radio]\n   *\n   * @description\n   * HTML radio button.\n   *\n   * **Note:**<br>\n   * All inputs controlled by {@link ngModel ngModel} (including those of type `radio`) will use the\n   * value of their `name` attribute to determine the property under which their\n   * {@link ngModel.NgModelController NgModelController} will be published on the parent\n   * {@link form.FormController FormController}. Thus, if you use the same `name` for multiple\n   * inputs of a form (e.g. a group of radio inputs), only _one_ `NgModelController` will be\n   * published on the parent `FormController` under that name. The rest of the controllers will\n   * continue to work as expected, but you won't be able to access them as properties on the parent\n   * `FormController`.\n   *\n   * <div class=\"alert alert-info\">\n   *   <p>\n   *     In plain HTML forms, the `name` attribute is used to identify groups of radio inputs, so\n   *     that the browser can manage their state (checked/unchecked) based on the state of other\n   *     inputs in the same group.\n   *   </p>\n   *   <p>\n   *     In AngularJS forms, this is not necessary. The input's state will be updated based on the\n   *     value of the underlying model data.\n   *   </p>\n   * </div>\n   *\n   * <div class=\"alert alert-success\">\n   *   If you omit the `name` attribute on a radio input, `ngModel` will automatically assign it a\n   *   unique name.\n   * </div>\n   *\n   * @param {string} ngModel Assignable AngularJS expression to data-bind to.\n   * @param {string} value The value to which the `ngModel` expression should be set when selected.\n   *    Note that `value` only supports `string` values, i.e. the scope model needs to be a string,\n   *    too. Use `ngValue` if you need complex models (`number`, `object`, ...).\n   * @param {string=} name Property name of the form under which the control is published.\n   * @param {string=} ngChange AngularJS expression to be executed when input changes due to user\n   *    interaction with the input element.\n   * @param {string} ngValue AngularJS expression to which `ngModel` will be be set when the radio\n   *    is selected. Should be used instead of the `value` attribute if you need\n   *    a non-string `ngModel` (`boolean`, `array`, ...).\n   *\n   * @example\n      <example name=\"radio-input-directive\" module=\"radioExample\">\n        <file name=\"index.html\">\n         <script>\n           angular.module('radioExample', [])\n             .controller('ExampleController', ['$scope', function($scope) {\n               $scope.color = {\n                 name: 'blue'\n               };\n               $scope.specialValue = {\n                 \"id\": \"12345\",\n                 \"value\": \"green\"\n               };\n             }]);\n         </script>\n         <form name=\"myForm\" ng-controller=\"ExampleController\">\n           <label>\n             <input type=\"radio\" ng-model=\"color.name\" value=\"red\">\n             Red\n           </label><br/>\n           <label>\n             <input type=\"radio\" ng-model=\"color.name\" ng-value=\"specialValue\">\n             Green\n           </label><br/>\n           <label>\n             <input type=\"radio\" ng-model=\"color.name\" value=\"blue\">\n             Blue\n           </label><br/>\n           <tt>color = {{color.name | json}}</tt><br/>\n          </form>\n          Note that `ng-value=\"specialValue\"` sets radio item's value to be the value of `$scope.specialValue`.\n        </file>\n        <file name=\"protractor.js\" type=\"protractor\">\n          it('should change state', function() {\n            var inputs = element.all(by.model('color.name'));\n            var color = element(by.binding('color.name'));\n\n            expect(color.getText()).toContain('blue');\n\n            inputs.get(0).click();\n            expect(color.getText()).toContain('red');\n\n            inputs.get(1).click();\n            expect(color.getText()).toContain('green');\n          });\n        </file>\n      </example>\n   */\n  'radio': radioInputType,\n\n  /**\n   * @ngdoc input\n   * @name input[range]\n   *\n   * @description\n   * Native range input with validation and transformation.\n   *\n   * The model for the range input must always be a `Number`.\n   *\n   * IE9 and other browsers that do not support the `range` type fall back\n   * to a text input without any default values for `min`, `max` and `step`. Model binding,\n   * validation and number parsing are nevertheless supported.\n   *\n   * Browsers that support range (latest Chrome, Safari, Firefox, Edge) treat `input[range]`\n   * in a way that never allows the input to hold an invalid value. That means:\n   * - any non-numerical value is set to `(max + min) / 2`.\n   * - any numerical value that is less than the current min val, or greater than the current max val\n   * is set to the min / max val respectively.\n   * - additionally, the current `step` is respected, so the nearest value that satisfies a step\n   * is used.\n   *\n   * See the [HTML Spec on input[type=range]](https://www.w3.org/TR/html5/forms.html#range-state-(type=range))\n   * for more info.\n   *\n   * This has the following consequences for AngularJS:\n   *\n   * Since the element value should always reflect the current model value, a range input\n   * will set the bound ngModel expression to the value that the browser has set for the\n   * input element. For example, in the following input `<input type=\"range\" ng-model=\"model.value\">`,\n   * if the application sets `model.value = null`, the browser will set the input to `'50'`.\n   * AngularJS will then set the model to `50`, to prevent input and model value being out of sync.\n   *\n   * That means the model for range will immediately be set to `50` after `ngModel` has been\n   * initialized. It also means a range input can never have the required error.\n   *\n   * This does not only affect changes to the model value, but also to the values of the `min`,\n   * `max`, and `step` attributes. When these change in a way that will cause the browser to modify\n   * the input value, AngularJS will also update the model value.\n   *\n   * Automatic value adjustment also means that a range input element can never have the `required`,\n   * `min`, or `max` errors.\n   *\n   * However, `step` is currently only fully implemented by Firefox. Other browsers have problems\n   * when the step value changes dynamically - they do not adjust the element value correctly, but\n   * instead may set the `stepMismatch` error. If that's the case, the AngularJS will set the `step`\n   * error on the input, and set the model to `undefined`.\n   *\n   * Note that `input[range]` is not compatible with`ngMax`, `ngMin`, and `ngStep`, because they do\n   * not set the `min` and `max` attributes, which means that the browser won't automatically adjust\n   * the input value based on their values, and will always assume min = 0, max = 100, and step = 1.\n   *\n   * @param {string}  ngModel Assignable AngularJS expression to data-bind to.\n   * @param {string=} name Property name of the form under which the control is published.\n   * @param {string=} min Sets the `min` validation to ensure that the value entered is greater\n   *                  than `min`. Can be interpolated.\n   * @param {string=} max Sets the `max` validation to ensure that the value entered is less than `max`.\n   *                  Can be interpolated.\n   * @param {string=} step Sets the `step` validation to ensure that the value entered matches the `step`\n   *                  Can be interpolated.\n   * @param {expression=} ngChange AngularJS expression to be executed when the ngModel value changes due\n   *                      to user interaction with the input element.\n   * @param {expression=} ngChecked If the expression is truthy, then the `checked` attribute will be set on the\n   *                      element. **Note** : `ngChecked` should not be used alongside `ngModel`.\n   *                      Checkout {@link ng.directive:ngChecked ngChecked} for usage.\n   *\n   * @example\n      <example name=\"range-input-directive\" module=\"rangeExample\">\n        <file name=\"index.html\">\n          <script>\n            angular.module('rangeExample', [])\n              .controller('ExampleController', ['$scope', function($scope) {\n                $scope.value = 75;\n                $scope.min = 10;\n                $scope.max = 90;\n              }]);\n          </script>\n          <form name=\"myForm\" ng-controller=\"ExampleController\">\n\n            Model as range: <input type=\"range\" name=\"range\" ng-model=\"value\" min=\"{{min}}\"  max=\"{{max}}\">\n            <hr>\n            Model as number: <input type=\"number\" ng-model=\"value\"><br>\n            Min: <input type=\"number\" ng-model=\"min\"><br>\n            Max: <input type=\"number\" ng-model=\"max\"><br>\n            value = <code>{{value}}</code><br/>\n            myForm.range.$valid = <code>{{myForm.range.$valid}}</code><br/>\n            myForm.range.$error = <code>{{myForm.range.$error}}</code>\n          </form>\n        </file>\n      </example>\n\n   * ## Range Input with ngMin & ngMax attributes\n\n   * @example\n      <example name=\"range-input-directive-ng\" module=\"rangeExample\">\n        <file name=\"index.html\">\n          <script>\n            angular.module('rangeExample', [])\n              .controller('ExampleController', ['$scope', function($scope) {\n                $scope.value = 75;\n                $scope.min = 10;\n                $scope.max = 90;\n              }]);\n          </script>\n          <form name=\"myForm\" ng-controller=\"ExampleController\">\n            Model as range: <input type=\"range\" name=\"range\" ng-model=\"value\" ng-min=\"min\" ng-max=\"max\">\n            <hr>\n            Model as number: <input type=\"number\" ng-model=\"value\"><br>\n            Min: <input type=\"number\" ng-model=\"min\"><br>\n            Max: <input type=\"number\" ng-model=\"max\"><br>\n            value = <code>{{value}}</code><br/>\n            myForm.range.$valid = <code>{{myForm.range.$valid}}</code><br/>\n            myForm.range.$error = <code>{{myForm.range.$error}}</code>\n          </form>\n        </file>\n      </example>\n\n   */\n  'range': rangeInputType,\n\n  /**\n   * @ngdoc input\n   * @name input[checkbox]\n   *\n   * @description\n   * HTML checkbox.\n   *\n   * @param {string} ngModel Assignable AngularJS expression to data-bind to.\n   * @param {string=} name Property name of the form under which the control is published.\n   * @param {expression=} ngTrueValue The value to which the expression should be set when selected.\n   * @param {expression=} ngFalseValue The value to which the expression should be set when not selected.\n   * @param {string=} ngChange AngularJS expression to be executed when input changes due to user\n   *    interaction with the input element.\n   *\n   * @example\n      <example name=\"checkbox-input-directive\" module=\"checkboxExample\">\n        <file name=\"index.html\">\n         <script>\n           angular.module('checkboxExample', [])\n             .controller('ExampleController', ['$scope', function($scope) {\n               $scope.checkboxModel = {\n                value1 : true,\n                value2 : 'YES'\n              };\n             }]);\n         </script>\n         <form name=\"myForm\" ng-controller=\"ExampleController\">\n           <label>Value1:\n             <input type=\"checkbox\" ng-model=\"checkboxModel.value1\">\n           </label><br/>\n           <label>Value2:\n             <input type=\"checkbox\" ng-model=\"checkboxModel.value2\"\n                    ng-true-value=\"'YES'\" ng-false-value=\"'NO'\">\n            </label><br/>\n           <tt>value1 = {{checkboxModel.value1}}</tt><br/>\n           <tt>value2 = {{checkboxModel.value2}}</tt><br/>\n          </form>\n        </file>\n        <file name=\"protractor.js\" type=\"protractor\">\n          it('should change state', function() {\n            var value1 = element(by.binding('checkboxModel.value1'));\n            var value2 = element(by.binding('checkboxModel.value2'));\n\n            expect(value1.getText()).toContain('true');\n            expect(value2.getText()).toContain('YES');\n\n            element(by.model('checkboxModel.value1')).click();\n            element(by.model('checkboxModel.value2')).click();\n\n            expect(value1.getText()).toContain('false');\n            expect(value2.getText()).toContain('NO');\n          });\n        </file>\n      </example>\n   */\n  'checkbox': checkboxInputType,\n\n  'hidden': noop,\n  'button': noop,\n  'submit': noop,\n  'reset': noop,\n  'file': noop\n};\n\nfunction stringBasedInputType(ctrl) {\n  ctrl.$formatters.push(function(value) {\n    return ctrl.$isEmpty(value) ? value : value.toString();\n  });\n}\n\nfunction textInputType(scope, element, attr, ctrl, $sniffer, $browser) {\n  baseInputType(scope, element, attr, ctrl, $sniffer, $browser);\n  stringBasedInputType(ctrl);\n}\n\nfunction baseInputType(scope, element, attr, ctrl, $sniffer, $browser) {\n  var type = lowercase(element[0].type);\n\n  // In composition mode, users are still inputting intermediate text buffer,\n  // hold the listener until composition is done.\n  // More about composition events: https://developer.mozilla.org/en-US/docs/Web/API/CompositionEvent\n  if (!$sniffer.android) {\n    var composing = false;\n\n    element.on('compositionstart', function() {\n      composing = true;\n    });\n\n    // Support: IE9+\n    element.on('compositionupdate', function(ev) {\n      // End composition when ev.data is empty string on 'compositionupdate' event.\n      // When the input de-focusses (e.g. by clicking away), IE triggers 'compositionupdate'\n      // instead of 'compositionend'.\n      if (isUndefined(ev.data) || ev.data === '') {\n        composing = false;\n      }\n    });\n\n    element.on('compositionend', function() {\n      composing = false;\n      listener();\n    });\n  }\n\n  var timeout;\n\n  var listener = function(ev) {\n    if (timeout) {\n      $browser.defer.cancel(timeout);\n      timeout = null;\n    }\n    if (composing) return;\n    var value = element.val(),\n        event = ev && ev.type;\n\n    // By default we will trim the value\n    // If the attribute ng-trim exists we will avoid trimming\n    // If input type is 'password', the value is never trimmed\n    if (type !== 'password' && (!attr.ngTrim || attr.ngTrim !== 'false')) {\n      value = trim(value);\n    }\n\n    // If a control is suffering from bad input (due to native validators), browsers discard its\n    // value, so it may be necessary to revalidate (by calling $setViewValue again) even if the\n    // control's value is the same empty value twice in a row.\n    if (ctrl.$viewValue !== value || (value === '' && ctrl.$$hasNativeValidators)) {\n      ctrl.$setViewValue(value, event);\n    }\n  };\n\n  // if the browser does support \"input\" event, we are fine - except on IE9 which doesn't fire the\n  // input event on backspace, delete or cut\n  if ($sniffer.hasEvent('input')) {\n    element.on('input', listener);\n  } else {\n    var deferListener = function(ev, input, origValue) {\n      if (!timeout) {\n        timeout = $browser.defer(function() {\n          timeout = null;\n          if (!input || input.value !== origValue) {\n            listener(ev);\n          }\n        });\n      }\n    };\n\n    element.on('keydown', /** @this */ function(event) {\n      var key = event.keyCode;\n\n      // ignore\n      //    command            modifiers                   arrows\n      if (key === 91 || (15 < key && key < 19) || (37 <= key && key <= 40)) return;\n\n      deferListener(event, this, this.value);\n    });\n\n    // if user modifies input value using context menu in IE, we need \"paste\", \"cut\" and \"drop\" events to catch it\n    if ($sniffer.hasEvent('paste')) {\n      element.on('paste cut drop', deferListener);\n    }\n  }\n\n  // if user paste into input using mouse on older browser\n  // or form autocomplete on newer browser, we need \"change\" event to catch it\n  element.on('change', listener);\n\n  // Some native input types (date-family) have the ability to change validity without\n  // firing any input/change events.\n  // For these event types, when native validators are present and the browser supports the type,\n  // check for validity changes on various DOM events.\n  if (PARTIAL_VALIDATION_TYPES[type] && ctrl.$$hasNativeValidators && type === attr.type) {\n    element.on(PARTIAL_VALIDATION_EVENTS, /** @this */ function(ev) {\n      if (!timeout) {\n        var validity = this[VALIDITY_STATE_PROPERTY];\n        var origBadInput = validity.badInput;\n        var origTypeMismatch = validity.typeMismatch;\n        timeout = $browser.defer(function() {\n          timeout = null;\n          if (validity.badInput !== origBadInput || validity.typeMismatch !== origTypeMismatch) {\n            listener(ev);\n          }\n        });\n      }\n    });\n  }\n\n  ctrl.$render = function() {\n    // Workaround for Firefox validation #12102.\n    var value = ctrl.$isEmpty(ctrl.$viewValue) ? '' : ctrl.$viewValue;\n    if (element.val() !== value) {\n      element.val(value);\n    }\n  };\n}\n\nfunction weekParser(isoWeek, existingDate) {\n  if (isDate(isoWeek)) {\n    return isoWeek;\n  }\n\n  if (isString(isoWeek)) {\n    WEEK_REGEXP.lastIndex = 0;\n    var parts = WEEK_REGEXP.exec(isoWeek);\n    if (parts) {\n      var year = +parts[1],\n          week = +parts[2],\n          hours = 0,\n          minutes = 0,\n          seconds = 0,\n          milliseconds = 0,\n          firstThurs = getFirstThursdayOfYear(year),\n          addDays = (week - 1) * 7;\n\n      if (existingDate) {\n        hours = existingDate.getHours();\n        minutes = existingDate.getMinutes();\n        seconds = existingDate.getSeconds();\n        milliseconds = existingDate.getMilliseconds();\n      }\n\n      return new Date(year, 0, firstThurs.getDate() + addDays, hours, minutes, seconds, milliseconds);\n    }\n  }\n\n  return NaN;\n}\n\nfunction createDateParser(regexp, mapping) {\n  return function(iso, previousDate) {\n    var parts, map;\n\n    if (isDate(iso)) {\n      return iso;\n    }\n\n    if (isString(iso)) {\n      // When a date is JSON'ified to wraps itself inside of an extra\n      // set of double quotes. This makes the date parsing code unable\n      // to match the date string and parse it as a date.\n      if (iso.charAt(0) === '\"' && iso.charAt(iso.length - 1) === '\"') {\n        iso = iso.substring(1, iso.length - 1);\n      }\n      if (ISO_DATE_REGEXP.test(iso)) {\n        return new Date(iso);\n      }\n      regexp.lastIndex = 0;\n      parts = regexp.exec(iso);\n\n      if (parts) {\n        parts.shift();\n        if (previousDate) {\n          map = {\n            yyyy: previousDate.getFullYear(),\n            MM: previousDate.getMonth() + 1,\n            dd: previousDate.getDate(),\n            HH: previousDate.getHours(),\n            mm: previousDate.getMinutes(),\n            ss: previousDate.getSeconds(),\n            sss: previousDate.getMilliseconds() / 1000\n          };\n        } else {\n          map = { yyyy: 1970, MM: 1, dd: 1, HH: 0, mm: 0, ss: 0, sss: 0 };\n        }\n\n        forEach(parts, function(part, index) {\n          if (index < mapping.length) {\n            map[mapping[index]] = +part;\n          }\n        });\n\n        var date = new Date(map.yyyy, map.MM - 1, map.dd, map.HH, map.mm, map.ss || 0, map.sss * 1000 || 0);\n        if (map.yyyy < 100) {\n          // In the constructor, 2-digit years map to 1900-1999.\n          // Use `setFullYear()` to set the correct year.\n          date.setFullYear(map.yyyy);\n        }\n\n        return date;\n      }\n    }\n\n    return NaN;\n  };\n}\n\nfunction createDateInputType(type, regexp, parseDate, format) {\n  return function dynamicDateInputType(scope, element, attr, ctrl, $sniffer, $browser, $filter, $parse) {\n    badInputChecker(scope, element, attr, ctrl, type);\n    baseInputType(scope, element, attr, ctrl, $sniffer, $browser);\n\n    var isTimeType = type === 'time' || type === 'datetimelocal';\n    var previousDate;\n    var previousTimezone;\n\n    ctrl.$parsers.push(function(value) {\n      if (ctrl.$isEmpty(value)) return null;\n\n      if (regexp.test(value)) {\n        // Note: We cannot read ctrl.$modelValue, as there might be a different\n        // parser/formatter in the processing chain so that the model\n        // contains some different data format!\n        return parseDateAndConvertTimeZoneToLocal(value, previousDate);\n      }\n      ctrl.$$parserName = type;\n      return undefined;\n    });\n\n    ctrl.$formatters.push(function(value) {\n      if (value && !isDate(value)) {\n        throw ngModelMinErr('datefmt', 'Expected `{0}` to be a date', value);\n      }\n      if (isValidDate(value)) {\n        previousDate = value;\n        var timezone = ctrl.$options.getOption('timezone');\n\n        if (timezone) {\n          previousTimezone = timezone;\n          previousDate = convertTimezoneToLocal(previousDate, timezone, true);\n        }\n\n        return formatter(value, timezone);\n      } else {\n        previousDate = null;\n        previousTimezone = null;\n        return '';\n      }\n    });\n\n    if (isDefined(attr.min) || attr.ngMin) {\n      var minVal = attr.min || $parse(attr.ngMin)(scope);\n      var parsedMinVal = parseObservedDateValue(minVal);\n\n      ctrl.$validators.min = function(value) {\n        return !isValidDate(value) || isUndefined(parsedMinVal) || parseDate(value) >= parsedMinVal;\n      };\n      attr.$observe('min', function(val) {\n        if (val !== minVal) {\n          parsedMinVal = parseObservedDateValue(val);\n          minVal = val;\n          ctrl.$validate();\n        }\n      });\n    }\n\n    if (isDefined(attr.max) || attr.ngMax) {\n      var maxVal = attr.max || $parse(attr.ngMax)(scope);\n      var parsedMaxVal = parseObservedDateValue(maxVal);\n\n      ctrl.$validators.max = function(value) {\n        return !isValidDate(value) || isUndefined(parsedMaxVal) || parseDate(value) <= parsedMaxVal;\n      };\n      attr.$observe('max', function(val) {\n        if (val !== maxVal) {\n          parsedMaxVal = parseObservedDateValue(val);\n          maxVal = val;\n          ctrl.$validate();\n        }\n      });\n    }\n\n    function isValidDate(value) {\n      // Invalid Date: getTime() returns NaN\n      return value && !(value.getTime && value.getTime() !== value.getTime());\n    }\n\n    function parseObservedDateValue(val) {\n      return isDefined(val) && !isDate(val) ? parseDateAndConvertTimeZoneToLocal(val) || undefined : val;\n    }\n\n    function parseDateAndConvertTimeZoneToLocal(value, previousDate) {\n      var timezone = ctrl.$options.getOption('timezone');\n\n      if (previousTimezone && previousTimezone !== timezone) {\n        // If the timezone has changed, adjust the previousDate to the default timezone\n        // so that the new date is converted with the correct timezone offset\n        previousDate = addDateMinutes(previousDate, timezoneToOffset(previousTimezone));\n      }\n\n      var parsedDate = parseDate(value, previousDate);\n\n      if (!isNaN(parsedDate) && timezone) {\n        parsedDate = convertTimezoneToLocal(parsedDate, timezone);\n      }\n      return parsedDate;\n    }\n\n    function formatter(value, timezone) {\n      var targetFormat = format;\n\n      if (isTimeType && isString(ctrl.$options.getOption('timeSecondsFormat'))) {\n        targetFormat = format\n          .replace('ss.sss', ctrl.$options.getOption('timeSecondsFormat'))\n          .replace(/:$/, '');\n      }\n\n      var formatted =  $filter('date')(value, targetFormat, timezone);\n\n      if (isTimeType && ctrl.$options.getOption('timeStripZeroSeconds')) {\n        formatted = formatted.replace(/(?::00)?(?:\\.000)?$/, '');\n      }\n\n      return formatted;\n    }\n  };\n}\n\nfunction badInputChecker(scope, element, attr, ctrl, parserName) {\n  var node = element[0];\n  var nativeValidation = ctrl.$$hasNativeValidators = isObject(node.validity);\n  if (nativeValidation) {\n    ctrl.$parsers.push(function(value) {\n      var validity = element.prop(VALIDITY_STATE_PROPERTY) || {};\n      if (validity.badInput || validity.typeMismatch) {\n        ctrl.$$parserName = parserName;\n        return undefined;\n      }\n\n      return value;\n    });\n  }\n}\n\nfunction numberFormatterParser(ctrl) {\n  ctrl.$parsers.push(function(value) {\n    if (ctrl.$isEmpty(value))      return null;\n    if (NUMBER_REGEXP.test(value)) return parseFloat(value);\n\n    ctrl.$$parserName = 'number';\n    return undefined;\n  });\n\n  ctrl.$formatters.push(function(value) {\n    if (!ctrl.$isEmpty(value)) {\n      if (!isNumber(value)) {\n        throw ngModelMinErr('numfmt', 'Expected `{0}` to be a number', value);\n      }\n      value = value.toString();\n    }\n    return value;\n  });\n}\n\nfunction parseNumberAttrVal(val) {\n  if (isDefined(val) && !isNumber(val)) {\n    val = parseFloat(val);\n  }\n  return !isNumberNaN(val) ? val : undefined;\n}\n\nfunction isNumberInteger(num) {\n  // See http://stackoverflow.com/questions/14636536/how-to-check-if-a-variable-is-an-integer-in-javascript#14794066\n  // (minus the assumption that `num` is a number)\n\n  // eslint-disable-next-line no-bitwise\n  return (num | 0) === num;\n}\n\nfunction countDecimals(num) {\n  var numString = num.toString();\n  var decimalSymbolIndex = numString.indexOf('.');\n\n  if (decimalSymbolIndex === -1) {\n    if (-1 < num && num < 1) {\n      // It may be in the exponential notation format (`1e-X`)\n      var match = /e-(\\d+)$/.exec(numString);\n\n      if (match) {\n        return Number(match[1]);\n      }\n    }\n\n    return 0;\n  }\n\n  return numString.length - decimalSymbolIndex - 1;\n}\n\nfunction isValidForStep(viewValue, stepBase, step) {\n  // At this point `stepBase` and `step` are expected to be non-NaN values\n  // and `viewValue` is expected to be a valid stringified number.\n  var value = Number(viewValue);\n\n  var isNonIntegerValue = !isNumberInteger(value);\n  var isNonIntegerStepBase = !isNumberInteger(stepBase);\n  var isNonIntegerStep = !isNumberInteger(step);\n\n  // Due to limitations in Floating Point Arithmetic (e.g. `0.3 - 0.2 !== 0.1` or\n  // `0.5 % 0.1 !== 0`), we need to convert all numbers to integers.\n  if (isNonIntegerValue || isNonIntegerStepBase || isNonIntegerStep) {\n    var valueDecimals = isNonIntegerValue ? countDecimals(value) : 0;\n    var stepBaseDecimals = isNonIntegerStepBase ? countDecimals(stepBase) : 0;\n    var stepDecimals = isNonIntegerStep ? countDecimals(step) : 0;\n\n    var decimalCount = Math.max(valueDecimals, stepBaseDecimals, stepDecimals);\n    var multiplier = Math.pow(10, decimalCount);\n\n    value = value * multiplier;\n    stepBase = stepBase * multiplier;\n    step = step * multiplier;\n\n    if (isNonIntegerValue) value = Math.round(value);\n    if (isNonIntegerStepBase) stepBase = Math.round(stepBase);\n    if (isNonIntegerStep) step = Math.round(step);\n  }\n\n  return (value - stepBase) % step === 0;\n}\n\nfunction numberInputType(scope, element, attr, ctrl, $sniffer, $browser, $filter, $parse) {\n  badInputChecker(scope, element, attr, ctrl, 'number');\n  numberFormatterParser(ctrl);\n  baseInputType(scope, element, attr, ctrl, $sniffer, $browser);\n\n  var parsedMinVal;\n\n  if (isDefined(attr.min) || attr.ngMin) {\n    var minVal = attr.min || $parse(attr.ngMin)(scope);\n    parsedMinVal = parseNumberAttrVal(minVal);\n\n    ctrl.$validators.min = function(modelValue, viewValue) {\n      return ctrl.$isEmpty(viewValue) || isUndefined(parsedMinVal) || viewValue >= parsedMinVal;\n    };\n\n    attr.$observe('min', function(val) {\n      if (val !== minVal) {\n        parsedMinVal = parseNumberAttrVal(val);\n        minVal = val;\n        // TODO(matsko): implement validateLater to reduce number of validations\n        ctrl.$validate();\n      }\n    });\n  }\n\n  if (isDefined(attr.max) || attr.ngMax) {\n    var maxVal = attr.max || $parse(attr.ngMax)(scope);\n    var parsedMaxVal = parseNumberAttrVal(maxVal);\n\n    ctrl.$validators.max = function(modelValue, viewValue) {\n      return ctrl.$isEmpty(viewValue) || isUndefined(parsedMaxVal) || viewValue <= parsedMaxVal;\n    };\n\n    attr.$observe('max', function(val) {\n      if (val !== maxVal) {\n        parsedMaxVal = parseNumberAttrVal(val);\n        maxVal = val;\n        // TODO(matsko): implement validateLater to reduce number of validations\n        ctrl.$validate();\n      }\n    });\n  }\n\n  if (isDefined(attr.step) || attr.ngStep) {\n    var stepVal = attr.step || $parse(attr.ngStep)(scope);\n    var parsedStepVal = parseNumberAttrVal(stepVal);\n\n    ctrl.$validators.step = function(modelValue, viewValue) {\n      return ctrl.$isEmpty(viewValue) || isUndefined(parsedStepVal) ||\n        isValidForStep(viewValue, parsedMinVal || 0, parsedStepVal);\n    };\n\n    attr.$observe('step', function(val) {\n      // TODO(matsko): implement validateLater to reduce number of validations\n      if (val !== stepVal) {\n        parsedStepVal = parseNumberAttrVal(val);\n        stepVal = val;\n        ctrl.$validate();\n      }\n\n    });\n\n  }\n}\n\nfunction rangeInputType(scope, element, attr, ctrl, $sniffer, $browser) {\n  badInputChecker(scope, element, attr, ctrl, 'range');\n  numberFormatterParser(ctrl);\n  baseInputType(scope, element, attr, ctrl, $sniffer, $browser);\n\n  var supportsRange = ctrl.$$hasNativeValidators && element[0].type === 'range',\n      minVal = supportsRange ? 0 : undefined,\n      maxVal = supportsRange ? 100 : undefined,\n      stepVal = supportsRange ? 1 : undefined,\n      validity = element[0].validity,\n      hasMinAttr = isDefined(attr.min),\n      hasMaxAttr = isDefined(attr.max),\n      hasStepAttr = isDefined(attr.step);\n\n  var originalRender = ctrl.$render;\n\n  ctrl.$render = supportsRange && isDefined(validity.rangeUnderflow) && isDefined(validity.rangeOverflow) ?\n    //Browsers that implement range will set these values automatically, but reading the adjusted values after\n    //$render would cause the min / max validators to be applied with the wrong value\n    function rangeRender() {\n      originalRender();\n      ctrl.$setViewValue(element.val());\n    } :\n    originalRender;\n\n  if (hasMinAttr) {\n    minVal = parseNumberAttrVal(attr.min);\n\n    ctrl.$validators.min = supportsRange ?\n      // Since all browsers set the input to a valid value, we don't need to check validity\n      function noopMinValidator() { return true; } :\n      // non-support browsers validate the min val\n      function minValidator(modelValue, viewValue) {\n        return ctrl.$isEmpty(viewValue) || isUndefined(minVal) || viewValue >= minVal;\n      };\n\n    setInitialValueAndObserver('min', minChange);\n  }\n\n  if (hasMaxAttr) {\n    maxVal = parseNumberAttrVal(attr.max);\n\n    ctrl.$validators.max = supportsRange ?\n      // Since all browsers set the input to a valid value, we don't need to check validity\n      function noopMaxValidator() { return true; } :\n      // non-support browsers validate the max val\n      function maxValidator(modelValue, viewValue) {\n        return ctrl.$isEmpty(viewValue) || isUndefined(maxVal) || viewValue <= maxVal;\n      };\n\n    setInitialValueAndObserver('max', maxChange);\n  }\n\n  if (hasStepAttr) {\n    stepVal = parseNumberAttrVal(attr.step);\n\n    ctrl.$validators.step = supportsRange ?\n      function nativeStepValidator() {\n        // Currently, only FF implements the spec on step change correctly (i.e. adjusting the\n        // input element value to a valid value). It's possible that other browsers set the stepMismatch\n        // validity error instead, so we can at least report an error in that case.\n        return !validity.stepMismatch;\n      } :\n      // ngStep doesn't set the setp attr, so the browser doesn't adjust the input value as setting step would\n      function stepValidator(modelValue, viewValue) {\n        return ctrl.$isEmpty(viewValue) || isUndefined(stepVal) ||\n               isValidForStep(viewValue, minVal || 0, stepVal);\n      };\n\n    setInitialValueAndObserver('step', stepChange);\n  }\n\n  function setInitialValueAndObserver(htmlAttrName, changeFn) {\n    // interpolated attributes set the attribute value only after a digest, but we need the\n    // attribute value when the input is first rendered, so that the browser can adjust the\n    // input value based on the min/max value\n    element.attr(htmlAttrName, attr[htmlAttrName]);\n    var oldVal = attr[htmlAttrName];\n    attr.$observe(htmlAttrName, function wrappedObserver(val) {\n      if (val !== oldVal) {\n        oldVal = val;\n        changeFn(val);\n      }\n    });\n  }\n\n  function minChange(val) {\n    minVal = parseNumberAttrVal(val);\n    // ignore changes before model is initialized\n    if (isNumberNaN(ctrl.$modelValue)) {\n      return;\n    }\n\n    if (supportsRange) {\n      var elVal = element.val();\n      // IE11 doesn't set the el val correctly if the minVal is greater than the element value\n      if (minVal > elVal) {\n        elVal = minVal;\n        element.val(elVal);\n      }\n      ctrl.$setViewValue(elVal);\n    } else {\n      // TODO(matsko): implement validateLater to reduce number of validations\n      ctrl.$validate();\n    }\n  }\n\n  function maxChange(val) {\n    maxVal = parseNumberAttrVal(val);\n    // ignore changes before model is initialized\n    if (isNumberNaN(ctrl.$modelValue)) {\n      return;\n    }\n\n    if (supportsRange) {\n      var elVal = element.val();\n      // IE11 doesn't set the el val correctly if the maxVal is less than the element value\n      if (maxVal < elVal) {\n        element.val(maxVal);\n        // IE11 and Chrome don't set the value to the minVal when max < min\n        elVal = maxVal < minVal ? minVal : maxVal;\n      }\n      ctrl.$setViewValue(elVal);\n    } else {\n      // TODO(matsko): implement validateLater to reduce number of validations\n      ctrl.$validate();\n    }\n  }\n\n  function stepChange(val) {\n    stepVal = parseNumberAttrVal(val);\n    // ignore changes before model is initialized\n    if (isNumberNaN(ctrl.$modelValue)) {\n      return;\n    }\n\n    // Some browsers don't adjust the input value correctly, but set the stepMismatch error\n    if (!supportsRange) {\n      // TODO(matsko): implement validateLater to reduce number of validations\n      ctrl.$validate();\n    } else if (ctrl.$viewValue !== element.val()) {\n      ctrl.$setViewValue(element.val());\n    }\n  }\n}\n\nfunction urlInputType(scope, element, attr, ctrl, $sniffer, $browser) {\n  // Note: no badInputChecker here by purpose as `url` is only a validation\n  // in browsers, i.e. we can always read out input.value even if it is not valid!\n  baseInputType(scope, element, attr, ctrl, $sniffer, $browser);\n  stringBasedInputType(ctrl);\n\n  ctrl.$validators.url = function(modelValue, viewValue) {\n    var value = modelValue || viewValue;\n    return ctrl.$isEmpty(value) || URL_REGEXP.test(value);\n  };\n}\n\nfunction emailInputType(scope, element, attr, ctrl, $sniffer, $browser) {\n  // Note: no badInputChecker here by purpose as `url` is only a validation\n  // in browsers, i.e. we can always read out input.value even if it is not valid!\n  baseInputType(scope, element, attr, ctrl, $sniffer, $browser);\n  stringBasedInputType(ctrl);\n\n  ctrl.$validators.email = function(modelValue, viewValue) {\n    var value = modelValue || viewValue;\n    return ctrl.$isEmpty(value) || EMAIL_REGEXP.test(value);\n  };\n}\n\nfunction radioInputType(scope, element, attr, ctrl) {\n  var doTrim = !attr.ngTrim || trim(attr.ngTrim) !== 'false';\n  // make the name unique, if not defined\n  if (isUndefined(attr.name)) {\n    element.attr('name', nextUid());\n  }\n\n  var listener = function(ev) {\n    var value;\n    if (element[0].checked) {\n      value = attr.value;\n      if (doTrim) {\n        value = trim(value);\n      }\n      ctrl.$setViewValue(value, ev && ev.type);\n    }\n  };\n\n  element.on('change', listener);\n\n  ctrl.$render = function() {\n    var value = attr.value;\n    if (doTrim) {\n      value = trim(value);\n    }\n    element[0].checked = (value === ctrl.$viewValue);\n  };\n\n  attr.$observe('value', ctrl.$render);\n}\n\nfunction parseConstantExpr($parse, context, name, expression, fallback) {\n  var parseFn;\n  if (isDefined(expression)) {\n    parseFn = $parse(expression);\n    if (!parseFn.constant) {\n      throw ngModelMinErr('constexpr', 'Expected constant expression for `{0}`, but saw ' +\n                                   '`{1}`.', name, expression);\n    }\n    return parseFn(context);\n  }\n  return fallback;\n}\n\nfunction checkboxInputType(scope, element, attr, ctrl, $sniffer, $browser, $filter, $parse) {\n  var trueValue = parseConstantExpr($parse, scope, 'ngTrueValue', attr.ngTrueValue, true);\n  var falseValue = parseConstantExpr($parse, scope, 'ngFalseValue', attr.ngFalseValue, false);\n\n  var listener = function(ev) {\n    ctrl.$setViewValue(element[0].checked, ev && ev.type);\n  };\n\n  element.on('change', listener);\n\n  ctrl.$render = function() {\n    element[0].checked = ctrl.$viewValue;\n  };\n\n  // Override the standard `$isEmpty` because the $viewValue of an empty checkbox is always set to `false`\n  // This is because of the parser below, which compares the `$modelValue` with `trueValue` to convert\n  // it to a boolean.\n  ctrl.$isEmpty = function(value) {\n    return value === false;\n  };\n\n  ctrl.$formatters.push(function(value) {\n    return equals(value, trueValue);\n  });\n\n  ctrl.$parsers.push(function(value) {\n    return value ? trueValue : falseValue;\n  });\n}\n\n\n/**\n * @ngdoc directive\n * @name textarea\n * @restrict E\n *\n * @description\n * HTML textarea element control with AngularJS data-binding. The data-binding and validation\n * properties of this element are exactly the same as those of the\n * {@link ng.directive:input input element}.\n *\n * @param {string} ngModel Assignable AngularJS expression to data-bind to.\n * @param {string=} name Property name of the form under which the control is published.\n * @param {string=} required Sets `required` validation error key if the value is not entered.\n * @param {string=} ngRequired Adds `required` attribute and `required` validation constraint to\n *    the element when the ngRequired expression evaluates to true. Use `ngRequired` instead of\n *    `required` when you want to data-bind to the `required` attribute.\n * @param {number=} ngMinlength Sets `minlength` validation error key if the value is shorter than\n *    minlength.\n * @param {number=} ngMaxlength Sets `maxlength` validation error key if the value is longer than\n *    maxlength. Setting the attribute to a negative or non-numeric value, allows view values of any\n *    length.\n * @param {string=} ngPattern Sets `pattern` validation error key if the ngModel {@link ngModel.NgModelController#$viewValue $viewValue}\n *    does not match a RegExp found by evaluating the AngularJS expression given in the attribute value.\n *    If the expression evaluates to a RegExp object, then this is used directly.\n *    If the expression evaluates to a string, then it will be converted to a RegExp\n *    after wrapping it in `^` and `$` characters. For instance, `\"abc\"` will be converted to\n *    `new RegExp('^abc$')`.<br />\n *    **Note:** Avoid using the `g` flag on the RegExp, as it will cause each successive search to\n *    start at the index of the last search's match, thus not taking the whole input value into\n *    account.\n * @param {string=} ngChange AngularJS expression to be executed when input changes due to user\n *    interaction with the input element.\n * @param {boolean=} [ngTrim=true] If set to false AngularJS will not automatically trim the input.\n *\n * @knownIssue\n *\n * When specifying the `placeholder` attribute of `<textarea>`, Internet Explorer will temporarily\n * insert the placeholder value as the textarea's content. If the placeholder value contains\n * interpolation (`{{ ... }}`), an error will be logged in the console when AngularJS tries to update\n * the value of the by-then-removed text node. This doesn't affect the functionality of the\n * textarea, but can be undesirable.\n *\n * You can work around this Internet Explorer issue by using `ng-attr-placeholder` instead of\n * `placeholder` on textareas, whenever you need interpolation in the placeholder value. You can\n * find more details on `ngAttr` in the\n * [Interpolation](guide/interpolation#-ngattr-for-binding-to-arbitrary-attributes) section of the\n * Developer Guide.\n */\n\n\n/**\n * @ngdoc directive\n * @name input\n * @restrict E\n *\n * @description\n * HTML input element control. When used together with {@link ngModel `ngModel`}, it provides data-binding,\n * input state control, and validation.\n * Input control follows HTML5 input types and polyfills the HTML5 validation behavior for older browsers.\n *\n * <div class=\"alert alert-warning\">\n * **Note:** Not every feature offered is available for all input types.\n * Specifically, data binding and event handling via `ng-model` is unsupported for `input[file]`.\n * </div>\n *\n * @param {string} ngModel Assignable AngularJS expression to data-bind to.\n * @param {string=} name Property name of the form under which the control is published.\n * @param {string=} required Sets `required` validation error key if the value is not entered.\n * @param {boolean=} ngRequired Sets `required` attribute if set to true\n * @param {number=} ngMinlength Sets `minlength` validation error key if the value is shorter than\n *    minlength.\n * @param {number=} ngMaxlength Sets `maxlength` validation error key if the value is longer than\n *    maxlength. Setting the attribute to a negative or non-numeric value, allows view values of any\n *    length.\n * @param {string=} ngPattern Sets `pattern` validation error key if the ngModel {@link ngModel.NgModelController#$viewValue $viewValue}\n *    value does not match a RegExp found by evaluating the AngularJS expression given in the attribute value.\n *    If the expression evaluates to a RegExp object, then this is used directly.\n *    If the expression evaluates to a string, then it will be converted to a RegExp\n *    after wrapping it in `^` and `$` characters. For instance, `\"abc\"` will be converted to\n *    `new RegExp('^abc$')`.<br />\n *    **Note:** Avoid using the `g` flag on the RegExp, as it will cause each successive search to\n *    start at the index of the last search's match, thus not taking the whole input value into\n *    account.\n * @param {string=} ngChange AngularJS expression to be executed when input changes due to user\n *    interaction with the input element.\n * @param {boolean=} [ngTrim=true] If set to false AngularJS will not automatically trim the input.\n *    This parameter is ignored for input[type=password] controls, which will never trim the\n *    input.\n *\n * @example\n    <example name=\"input-directive\" module=\"inputExample\">\n      <file name=\"index.html\">\n       <script>\n          angular.module('inputExample', [])\n            .controller('ExampleController', ['$scope', function($scope) {\n              $scope.user = {name: 'guest', last: 'visitor'};\n            }]);\n       </script>\n       <div ng-controller=\"ExampleController\">\n         <form name=\"myForm\">\n           <label>\n              User name:\n              <input type=\"text\" name=\"userName\" ng-model=\"user.name\" required>\n           </label>\n           <div role=\"alert\">\n             <span class=\"error\" ng-show=\"myForm.userName.$error.required\">\n              Required!</span>\n           </div>\n           <label>\n              Last name:\n              <input type=\"text\" name=\"lastName\" ng-model=\"user.last\"\n              ng-minlength=\"3\" ng-maxlength=\"10\">\n           </label>\n           <div role=\"alert\">\n             <span class=\"error\" ng-show=\"myForm.lastName.$error.minlength\">\n               Too short!</span>\n             <span class=\"error\" ng-show=\"myForm.lastName.$error.maxlength\">\n               Too long!</span>\n           </div>\n         </form>\n         <hr>\n         <tt>user = {{user}}</tt><br/>\n         <tt>myForm.userName.$valid = {{myForm.userName.$valid}}</tt><br/>\n         <tt>myForm.userName.$error = {{myForm.userName.$error}}</tt><br/>\n         <tt>myForm.lastName.$valid = {{myForm.lastName.$valid}}</tt><br/>\n         <tt>myForm.lastName.$error = {{myForm.lastName.$error}}</tt><br/>\n         <tt>myForm.$valid = {{myForm.$valid}}</tt><br/>\n         <tt>myForm.$error.required = {{!!myForm.$error.required}}</tt><br/>\n         <tt>myForm.$error.minlength = {{!!myForm.$error.minlength}}</tt><br/>\n         <tt>myForm.$error.maxlength = {{!!myForm.$error.maxlength}}</tt><br/>\n       </div>\n      </file>\n      <file name=\"protractor.js\" type=\"protractor\">\n        var user = element(by.exactBinding('user'));\n        var userNameValid = element(by.binding('myForm.userName.$valid'));\n        var lastNameValid = element(by.binding('myForm.lastName.$valid'));\n        var lastNameError = element(by.binding('myForm.lastName.$error'));\n        var formValid = element(by.binding('myForm.$valid'));\n        var userNameInput = element(by.model('user.name'));\n        var userLastInput = element(by.model('user.last'));\n\n        it('should initialize to model', function() {\n          expect(user.getText()).toContain('{\"name\":\"guest\",\"last\":\"visitor\"}');\n          expect(userNameValid.getText()).toContain('true');\n          expect(formValid.getText()).toContain('true');\n        });\n\n        it('should be invalid if empty when required', function() {\n          userNameInput.clear();\n          userNameInput.sendKeys('');\n\n          expect(user.getText()).toContain('{\"last\":\"visitor\"}');\n          expect(userNameValid.getText()).toContain('false');\n          expect(formValid.getText()).toContain('false');\n        });\n\n        it('should be valid if empty when min length is set', function() {\n          userLastInput.clear();\n          userLastInput.sendKeys('');\n\n          expect(user.getText()).toContain('{\"name\":\"guest\",\"last\":\"\"}');\n          expect(lastNameValid.getText()).toContain('true');\n          expect(formValid.getText()).toContain('true');\n        });\n\n        it('should be invalid if less than required min length', function() {\n          userLastInput.clear();\n          userLastInput.sendKeys('xx');\n\n          expect(user.getText()).toContain('{\"name\":\"guest\"}');\n          expect(lastNameValid.getText()).toContain('false');\n          expect(lastNameError.getText()).toContain('minlength');\n          expect(formValid.getText()).toContain('false');\n        });\n\n        it('should be invalid if longer than max length', function() {\n          userLastInput.clear();\n          userLastInput.sendKeys('some ridiculously long name');\n\n          expect(user.getText()).toContain('{\"name\":\"guest\"}');\n          expect(lastNameValid.getText()).toContain('false');\n          expect(lastNameError.getText()).toContain('maxlength');\n          expect(formValid.getText()).toContain('false');\n        });\n      </file>\n    </example>\n */\nvar inputDirective = ['$browser', '$sniffer', '$filter', '$parse',\n    function($browser, $sniffer, $filter, $parse) {\n  return {\n    restrict: 'E',\n    require: ['?ngModel'],\n    link: {\n      pre: function(scope, element, attr, ctrls) {\n        if (ctrls[0]) {\n          (inputType[lowercase(attr.type)] || inputType.text)(scope, element, attr, ctrls[0], $sniffer,\n                                                              $browser, $filter, $parse);\n        }\n      }\n    }\n  };\n}];\n\n\nvar hiddenInputBrowserCacheDirective = function() {\n  var valueProperty = {\n    configurable: true,\n    enumerable: false,\n    get: function() {\n      return this.getAttribute('value') || '';\n    },\n    set: function(val) {\n      this.setAttribute('value', val);\n    }\n  };\n\n  return {\n    restrict: 'E',\n    priority: 200,\n    compile: function(_, attr) {\n      if (lowercase(attr.type) !== 'hidden') {\n        return;\n      }\n\n      return {\n        pre: function(scope, element, attr, ctrls) {\n          var node = element[0];\n\n          // Support: Edge\n          // Moving the DOM around prevents autofillling\n          if (node.parentNode) {\n            node.parentNode.insertBefore(node, node.nextSibling);\n          }\n\n          // Support: FF, IE\n          // Avoiding direct assignment to .value prevents autofillling\n          if (Object.defineProperty) {\n            Object.defineProperty(node, 'value', valueProperty);\n          }\n        }\n      };\n    }\n  };\n};\n\n\n\nvar CONSTANT_VALUE_REGEXP = /^(true|false|\\d+)$/;\n/**\n * @ngdoc directive\n * @name ngValue\n * @restrict A\n * @priority 100\n *\n * @description\n * Binds the given expression to the value of the element.\n *\n * It is mainly used on {@link input[radio] `input[radio]`} and option elements,\n * so that when the element is selected, the {@link ngModel `ngModel`} of that element (or its\n * {@link select `select`} parent element) is set to the bound value. It is especially useful\n * for dynamically generated lists using {@link ngRepeat `ngRepeat`}, as shown below.\n *\n * It can also be used to achieve one-way binding of a given expression to an input element\n * such as an `input[text]` or a `textarea`, when that element does not use ngModel.\n *\n * @element ANY\n * @param {string=} ngValue AngularJS expression, whose value will be bound to the `value` attribute\n * and `value` property of the element.\n *\n * @example\n    <example name=\"ngValue-directive\" module=\"valueExample\">\n      <file name=\"index.html\">\n       <script>\n          angular.module('valueExample', [])\n            .controller('ExampleController', ['$scope', function($scope) {\n              $scope.names = ['pizza', 'unicorns', 'robots'];\n              $scope.my = { favorite: 'unicorns' };\n            }]);\n       </script>\n        <form ng-controller=\"ExampleController\">\n          <h2>Which is your favorite?</h2>\n            <label ng-repeat=\"name in names\" for=\"{{name}}\">\n              {{name}}\n              <input type=\"radio\"\n                     ng-model=\"my.favorite\"\n                     ng-value=\"name\"\n                     id=\"{{name}}\"\n                     name=\"favorite\">\n            </label>\n          <div>You chose {{my.favorite}}</div>\n        </form>\n      </file>\n      <file name=\"protractor.js\" type=\"protractor\">\n        var favorite = element(by.binding('my.favorite'));\n\n        it('should initialize to model', function() {\n          expect(favorite.getText()).toContain('unicorns');\n        });\n        it('should bind the values to the inputs', function() {\n          element.all(by.model('my.favorite')).get(0).click();\n          expect(favorite.getText()).toContain('pizza');\n        });\n      </file>\n    </example>\n */\nvar ngValueDirective = function() {\n  /**\n   *  inputs use the value attribute as their default value if the value property is not set.\n   *  Once the value property has been set (by adding input), it will not react to changes to\n   *  the value attribute anymore. Setting both attribute and property fixes this behavior, and\n   *  makes it possible to use ngValue as a sort of one-way bind.\n   */\n  function updateElementValue(element, attr, value) {\n    // Support: IE9 only\n    // In IE9 values are converted to string (e.g. `input.value = null` results in `input.value === 'null'`).\n    var propValue = isDefined(value) ? value : (msie === 9) ? '' : null;\n    element.prop('value', propValue);\n    attr.$set('value', value);\n  }\n\n  return {\n    restrict: 'A',\n    priority: 100,\n    compile: function(tpl, tplAttr) {\n      if (CONSTANT_VALUE_REGEXP.test(tplAttr.ngValue)) {\n        return function ngValueConstantLink(scope, elm, attr) {\n          var value = scope.$eval(attr.ngValue);\n          updateElementValue(elm, attr, value);\n        };\n      } else {\n        return function ngValueLink(scope, elm, attr) {\n          scope.$watch(attr.ngValue, function valueWatchAction(value) {\n            updateElementValue(elm, attr, value);\n          });\n        };\n      }\n    }\n  };\n};\n\n/**\n * @ngdoc directive\n * @name ngBind\n * @restrict AC\n *\n * @description\n * The `ngBind` attribute tells AngularJS to replace the text content of the specified HTML element\n * with the value of a given expression, and to update the text content when the value of that\n * expression changes.\n *\n * Typically, you don't use `ngBind` directly, but instead you use the double curly markup like\n * `{{ expression }}` which is similar but less verbose.\n *\n * It is preferable to use `ngBind` instead of `{{ expression }}` if a template is momentarily\n * displayed by the browser in its raw state before AngularJS compiles it. Since `ngBind` is an\n * element attribute, it makes the bindings invisible to the user while the page is loading.\n *\n * An alternative solution to this problem would be using the\n * {@link ng.directive:ngCloak ngCloak} directive.\n *\n *\n * @element ANY\n * @param {expression} ngBind {@link guide/expression Expression} to evaluate.\n *\n * @example\n * Enter a name in the Live Preview text box; the greeting below the text box changes instantly.\n   <example module=\"bindExample\" name=\"ng-bind\">\n     <file name=\"index.html\">\n       <script>\n         angular.module('bindExample', [])\n           .controller('ExampleController', ['$scope', function($scope) {\n             $scope.name = 'Whirled';\n           }]);\n       </script>\n       <div ng-controller=\"ExampleController\">\n         <label>Enter name: <input type=\"text\" ng-model=\"name\"></label><br>\n         Hello <span ng-bind=\"name\"></span>!\n       </div>\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       it('should check ng-bind', function() {\n         var nameInput = element(by.model('name'));\n\n         expect(element(by.binding('name')).getText()).toBe('Whirled');\n         nameInput.clear();\n         nameInput.sendKeys('world');\n         expect(element(by.binding('name')).getText()).toBe('world');\n       });\n     </file>\n   </example>\n */\nvar ngBindDirective = ['$compile', function($compile) {\n  return {\n    restrict: 'AC',\n    compile: function ngBindCompile(templateElement) {\n      $compile.$$addBindingClass(templateElement);\n      return function ngBindLink(scope, element, attr) {\n        $compile.$$addBindingInfo(element, attr.ngBind);\n        element = element[0];\n        scope.$watch(attr.ngBind, function ngBindWatchAction(value) {\n          element.textContent = stringify(value);\n        });\n      };\n    }\n  };\n}];\n\n\n/**\n * @ngdoc directive\n * @name ngBindTemplate\n *\n * @description\n * The `ngBindTemplate` directive specifies that the element\n * text content should be replaced with the interpolation of the template\n * in the `ngBindTemplate` attribute.\n * Unlike `ngBind`, the `ngBindTemplate` can contain multiple `{{` `}}`\n * expressions. This directive is needed since some HTML elements\n * (such as TITLE and OPTION) cannot contain SPAN elements.\n *\n * @element ANY\n * @param {string} ngBindTemplate template of form\n *   <tt>{{</tt> <tt>expression</tt> <tt>}}</tt> to eval.\n *\n * @example\n * Try it here: enter text in text box and watch the greeting change.\n   <example module=\"bindExample\" name=\"ng-bind-template\">\n     <file name=\"index.html\">\n       <script>\n         angular.module('bindExample', [])\n           .controller('ExampleController', ['$scope', function($scope) {\n             $scope.salutation = 'Hello';\n             $scope.name = 'World';\n           }]);\n       </script>\n       <div ng-controller=\"ExampleController\">\n        <label>Salutation: <input type=\"text\" ng-model=\"salutation\"></label><br>\n        <label>Name: <input type=\"text\" ng-model=\"name\"></label><br>\n        <pre ng-bind-template=\"{{salutation}} {{name}}!\"></pre>\n       </div>\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       it('should check ng-bind', function() {\n         var salutationElem = element(by.binding('salutation'));\n         var salutationInput = element(by.model('salutation'));\n         var nameInput = element(by.model('name'));\n\n         expect(salutationElem.getText()).toBe('Hello World!');\n\n         salutationInput.clear();\n         salutationInput.sendKeys('Greetings');\n         nameInput.clear();\n         nameInput.sendKeys('user');\n\n         expect(salutationElem.getText()).toBe('Greetings user!');\n       });\n     </file>\n   </example>\n */\nvar ngBindTemplateDirective = ['$interpolate', '$compile', function($interpolate, $compile) {\n  return {\n    compile: function ngBindTemplateCompile(templateElement) {\n      $compile.$$addBindingClass(templateElement);\n      return function ngBindTemplateLink(scope, element, attr) {\n        var interpolateFn = $interpolate(element.attr(attr.$attr.ngBindTemplate));\n        $compile.$$addBindingInfo(element, interpolateFn.expressions);\n        element = element[0];\n        attr.$observe('ngBindTemplate', function(value) {\n          element.textContent = isUndefined(value) ? '' : value;\n        });\n      };\n    }\n  };\n}];\n\n\n/**\n * @ngdoc directive\n * @name ngBindHtml\n *\n * @description\n * Evaluates the expression and inserts the resulting HTML into the element in a secure way. By default,\n * the resulting HTML content will be sanitized using the {@link ngSanitize.$sanitize $sanitize} service.\n * To utilize this functionality, ensure that `$sanitize` is available, for example, by including {@link\n * ngSanitize} in your module's dependencies (not in core AngularJS). In order to use {@link ngSanitize}\n * in your module's dependencies, you need to include \"angular-sanitize.js\" in your application.\n *\n * You may also bypass sanitization for values you know are safe. To do so, bind to\n * an explicitly trusted value via {@link ng.$sce#trustAsHtml $sce.trustAsHtml}.  See the example\n * under {@link ng.$sce#show-me-an-example-using-sce- Strict Contextual Escaping (SCE)}.\n *\n * Note: If a `$sanitize` service is unavailable and the bound value isn't explicitly trusted, you\n * will have an exception (instead of an exploit.)\n *\n * @element ANY\n * @param {expression} ngBindHtml {@link guide/expression Expression} to evaluate.\n *\n * @example\n\n   <example module=\"bindHtmlExample\" deps=\"angular-sanitize.js\" name=\"ng-bind-html\">\n     <file name=\"index.html\">\n       <div ng-controller=\"ExampleController\">\n        <p ng-bind-html=\"myHTML\"></p>\n       </div>\n     </file>\n\n     <file name=\"script.js\">\n       angular.module('bindHtmlExample', ['ngSanitize'])\n         .controller('ExampleController', ['$scope', function($scope) {\n           $scope.myHTML =\n              'I am an <code>HTML</code>string with ' +\n              '<a href=\"#\">links!</a> and other <em>stuff</em>';\n         }]);\n     </file>\n\n     <file name=\"protractor.js\" type=\"protractor\">\n       it('should check ng-bind-html', function() {\n         expect(element(by.binding('myHTML')).getText()).toBe(\n             'I am an HTMLstring with links! and other stuff');\n       });\n     </file>\n   </example>\n */\nvar ngBindHtmlDirective = ['$sce', '$parse', '$compile', function($sce, $parse, $compile) {\n  return {\n    restrict: 'A',\n    compile: function ngBindHtmlCompile(tElement, tAttrs) {\n      var ngBindHtmlGetter = $parse(tAttrs.ngBindHtml);\n      var ngBindHtmlWatch = $parse(tAttrs.ngBindHtml, function sceValueOf(val) {\n        // Unwrap the value to compare the actual inner safe value, not the wrapper object.\n        return $sce.valueOf(val);\n      });\n      $compile.$$addBindingClass(tElement);\n\n      return function ngBindHtmlLink(scope, element, attr) {\n        $compile.$$addBindingInfo(element, attr.ngBindHtml);\n\n        scope.$watch(ngBindHtmlWatch, function ngBindHtmlWatchAction() {\n          // The watched value is the unwrapped value. To avoid re-escaping, use the direct getter.\n          var value = ngBindHtmlGetter(scope);\n          element.html($sce.getTrustedHtml(value) || '');\n        });\n      };\n    }\n  };\n}];\n\n/**\n * @ngdoc directive\n * @name ngChange\n * @restrict A\n *\n * @description\n * Evaluate the given expression when the user changes the input.\n * The expression is evaluated immediately, unlike the JavaScript onchange event\n * which only triggers at the end of a change (usually, when the user leaves the\n * form element or presses the return key).\n *\n * The `ngChange` expression is only evaluated when a change in the input value causes\n * a new value to be committed to the model.\n *\n * It will not be evaluated:\n * * if the value returned from the `$parsers` transformation pipeline has not changed\n * * if the input has continued to be invalid since the model will stay `null`\n * * if the model is changed programmatically and not by a change to the input value\n *\n *\n * Note, this directive requires `ngModel` to be present.\n *\n * @element ANY\n * @param {expression} ngChange {@link guide/expression Expression} to evaluate upon change\n * in input value.\n *\n * @example\n * <example name=\"ngChange-directive\" module=\"changeExample\">\n *   <file name=\"index.html\">\n *     <script>\n *       angular.module('changeExample', [])\n *         .controller('ExampleController', ['$scope', function($scope) {\n *           $scope.counter = 0;\n *           $scope.change = function() {\n *             $scope.counter++;\n *           };\n *         }]);\n *     </script>\n *     <div ng-controller=\"ExampleController\">\n *       <input type=\"checkbox\" ng-model=\"confirmed\" ng-change=\"change()\" id=\"ng-change-example1\" />\n *       <input type=\"checkbox\" ng-model=\"confirmed\" id=\"ng-change-example2\" />\n *       <label for=\"ng-change-example2\">Confirmed</label><br />\n *       <tt>debug = {{confirmed}}</tt><br/>\n *       <tt>counter = {{counter}}</tt><br/>\n *     </div>\n *   </file>\n *   <file name=\"protractor.js\" type=\"protractor\">\n *     var counter = element(by.binding('counter'));\n *     var debug = element(by.binding('confirmed'));\n *\n *     it('should evaluate the expression if changing from view', function() {\n *       expect(counter.getText()).toContain('0');\n *\n *       element(by.id('ng-change-example1')).click();\n *\n *       expect(counter.getText()).toContain('1');\n *       expect(debug.getText()).toContain('true');\n *     });\n *\n *     it('should not evaluate the expression if changing from model', function() {\n *       element(by.id('ng-change-example2')).click();\n\n *       expect(counter.getText()).toContain('0');\n *       expect(debug.getText()).toContain('true');\n *     });\n *   </file>\n * </example>\n */\nvar ngChangeDirective = valueFn({\n  restrict: 'A',\n  require: 'ngModel',\n  link: function(scope, element, attr, ctrl) {\n    ctrl.$viewChangeListeners.push(function() {\n      scope.$eval(attr.ngChange);\n    });\n  }\n});\n\n/* exported\n  ngClassDirective,\n  ngClassEvenDirective,\n  ngClassOddDirective\n*/\n\nfunction classDirective(name, selector) {\n  name = 'ngClass' + name;\n  var indexWatchExpression;\n\n  return ['$parse', function($parse) {\n    return {\n      restrict: 'AC',\n      link: function(scope, element, attr) {\n        var classCounts = element.data('$classCounts');\n        var oldModulo = true;\n        var oldClassString;\n\n        if (!classCounts) {\n          // Use createMap() to prevent class assumptions involving property\n          // names in Object.prototype\n          classCounts = createMap();\n          element.data('$classCounts', classCounts);\n        }\n\n        if (name !== 'ngClass') {\n          if (!indexWatchExpression) {\n            indexWatchExpression = $parse('$index', function moduloTwo($index) {\n              // eslint-disable-next-line no-bitwise\n              return $index & 1;\n            });\n          }\n\n          scope.$watch(indexWatchExpression, ngClassIndexWatchAction);\n        }\n\n        scope.$watch($parse(attr[name], toClassString), ngClassWatchAction);\n\n        function addClasses(classString) {\n          classString = digestClassCounts(split(classString), 1);\n          attr.$addClass(classString);\n        }\n\n        function removeClasses(classString) {\n          classString = digestClassCounts(split(classString), -1);\n          attr.$removeClass(classString);\n        }\n\n        function updateClasses(oldClassString, newClassString) {\n          var oldClassArray = split(oldClassString);\n          var newClassArray = split(newClassString);\n\n          var toRemoveArray = arrayDifference(oldClassArray, newClassArray);\n          var toAddArray = arrayDifference(newClassArray, oldClassArray);\n\n          var toRemoveString = digestClassCounts(toRemoveArray, -1);\n          var toAddString = digestClassCounts(toAddArray, 1);\n\n          attr.$addClass(toAddString);\n          attr.$removeClass(toRemoveString);\n        }\n\n        function digestClassCounts(classArray, count) {\n          var classesToUpdate = [];\n\n          forEach(classArray, function(className) {\n            if (count > 0 || classCounts[className]) {\n              classCounts[className] = (classCounts[className] || 0) + count;\n              if (classCounts[className] === +(count > 0)) {\n                classesToUpdate.push(className);\n              }\n            }\n          });\n\n          return classesToUpdate.join(' ');\n        }\n\n        function ngClassIndexWatchAction(newModulo) {\n          // This watch-action should run before the `ngClassWatchAction()`, thus it\n          // adds/removes `oldClassString`. If the `ngClass` expression has changed as well, the\n          // `ngClassWatchAction()` will update the classes.\n          if (newModulo === selector) {\n            addClasses(oldClassString);\n          } else {\n            removeClasses(oldClassString);\n          }\n\n          oldModulo = newModulo;\n        }\n\n        function ngClassWatchAction(newClassString) {\n          if (oldModulo === selector) {\n            updateClasses(oldClassString, newClassString);\n          }\n\n          oldClassString = newClassString;\n        }\n      }\n    };\n  }];\n\n  // Helpers\n  function arrayDifference(tokens1, tokens2) {\n    if (!tokens1 || !tokens1.length) return [];\n    if (!tokens2 || !tokens2.length) return tokens1;\n\n    var values = [];\n\n    outer:\n    for (var i = 0; i < tokens1.length; i++) {\n      var token = tokens1[i];\n      for (var j = 0; j < tokens2.length; j++) {\n        if (token === tokens2[j]) continue outer;\n      }\n      values.push(token);\n    }\n\n    return values;\n  }\n\n  function split(classString) {\n    return classString && classString.split(' ');\n  }\n\n  function toClassString(classValue) {\n    if (!classValue) return classValue;\n\n    var classString = classValue;\n\n    if (isArray(classValue)) {\n      classString = classValue.map(toClassString).join(' ');\n    } else if (isObject(classValue)) {\n      classString = Object.keys(classValue).\n        filter(function(key) { return classValue[key]; }).\n        join(' ');\n    } else if (!isString(classValue)) {\n      classString = classValue + '';\n    }\n\n    return classString;\n  }\n}\n\n/**\n * @ngdoc directive\n * @name ngClass\n * @restrict AC\n * @element ANY\n *\n * @description\n * The `ngClass` directive allows you to dynamically set CSS classes on an HTML element by databinding\n * an expression that represents all classes to be added.\n *\n * The directive operates in three different ways, depending on which of three types the expression\n * evaluates to:\n *\n * 1. If the expression evaluates to a string, the string should be one or more space-delimited class\n * names.\n *\n * 2. If the expression evaluates to an object, then for each key-value pair of the\n * object with a truthy value the corresponding key is used as a class name.\n *\n * 3. If the expression evaluates to an array, each element of the array should either be a string as in\n * type 1 or an object as in type 2. This means that you can mix strings and objects together in an array\n * to give you more control over what CSS classes appear. See the code below for an example of this.\n *\n *\n * The directive won't add duplicate classes if a particular class was already set.\n *\n * When the expression changes, the previously added classes are removed and only then are the\n * new classes added.\n *\n * @knownIssue\n * You should not use {@link guide/interpolation interpolation} in the value of the `class`\n * attribute, when using the `ngClass` directive on the same element.\n * See {@link guide/interpolation#known-issues here} for more info.\n *\n * @animations\n * | Animation                        | Occurs                              |\n * |----------------------------------|-------------------------------------|\n * | {@link ng.$animate#addClass addClass}       | just before the class is applied to the element   |\n * | {@link ng.$animate#removeClass removeClass} | just before the class is removed from the element |\n * | {@link ng.$animate#setClass setClass} | just before classes are added and classes are removed from the element at the same time |\n *\n * ### ngClass and pre-existing CSS3 Transitions/Animations\n   The ngClass directive still supports CSS3 Transitions/Animations even if they do not follow the ngAnimate CSS naming structure.\n   Upon animation ngAnimate will apply supplementary CSS classes to track the start and end of an animation, but this will not hinder\n   any pre-existing CSS transitions already on the element. To get an idea of what happens during a class-based animation, be sure\n   to view the step by step details of {@link $animate#addClass $animate.addClass} and\n   {@link $animate#removeClass $animate.removeClass}.\n *\n * @param {expression} ngClass {@link guide/expression Expression} to eval. The result\n *   of the evaluation can be a string representing space delimited class\n *   names, an array, or a map of class names to boolean values. In the case of a map, the\n *   names of the properties whose values are truthy will be added as css classes to the\n *   element.\n *\n * @example\n * ### Basic\n   <example name=\"ng-class\">\n     <file name=\"index.html\">\n       <p ng-class=\"{strike: deleted, bold: important, 'has-error': error}\">Map Syntax Example</p>\n       <label>\n          <input type=\"checkbox\" ng-model=\"deleted\">\n          deleted (apply \"strike\" class)\n       </label><br>\n       <label>\n          <input type=\"checkbox\" ng-model=\"important\">\n          important (apply \"bold\" class)\n       </label><br>\n       <label>\n          <input type=\"checkbox\" ng-model=\"error\">\n          error (apply \"has-error\" class)\n       </label>\n       <hr>\n       <p ng-class=\"style\">Using String Syntax</p>\n       <input type=\"text\" ng-model=\"style\"\n              placeholder=\"Type: bold strike red\" aria-label=\"Type: bold strike red\">\n       <hr>\n       <p ng-class=\"[style1, style2, style3]\">Using Array Syntax</p>\n       <input ng-model=\"style1\"\n              placeholder=\"Type: bold, strike or red\" aria-label=\"Type: bold, strike or red\"><br>\n       <input ng-model=\"style2\"\n              placeholder=\"Type: bold, strike or red\" aria-label=\"Type: bold, strike or red 2\"><br>\n       <input ng-model=\"style3\"\n              placeholder=\"Type: bold, strike or red\" aria-label=\"Type: bold, strike or red 3\"><br>\n       <hr>\n       <p ng-class=\"[style4, {orange: warning}]\">Using Array and Map Syntax</p>\n       <input ng-model=\"style4\" placeholder=\"Type: bold, strike\" aria-label=\"Type: bold, strike\"><br>\n       <label><input type=\"checkbox\" ng-model=\"warning\"> warning (apply \"orange\" class)</label>\n     </file>\n     <file name=\"style.css\">\n       .strike {\n           text-decoration: line-through;\n       }\n       .bold {\n           font-weight: bold;\n       }\n       .red {\n           color: red;\n       }\n       .has-error {\n           color: red;\n           background-color: yellow;\n       }\n       .orange {\n           color: orange;\n       }\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       var ps = element.all(by.css('p'));\n\n       it('should let you toggle the class', function() {\n\n         expect(ps.first().getAttribute('class')).not.toMatch(/bold/);\n         expect(ps.first().getAttribute('class')).not.toMatch(/has-error/);\n\n         element(by.model('important')).click();\n         expect(ps.first().getAttribute('class')).toMatch(/bold/);\n\n         element(by.model('error')).click();\n         expect(ps.first().getAttribute('class')).toMatch(/has-error/);\n       });\n\n       it('should let you toggle string example', function() {\n         expect(ps.get(1).getAttribute('class')).toBe('');\n         element(by.model('style')).clear();\n         element(by.model('style')).sendKeys('red');\n         expect(ps.get(1).getAttribute('class')).toBe('red');\n       });\n\n       it('array example should have 3 classes', function() {\n         expect(ps.get(2).getAttribute('class')).toBe('');\n         element(by.model('style1')).sendKeys('bold');\n         element(by.model('style2')).sendKeys('strike');\n         element(by.model('style3')).sendKeys('red');\n         expect(ps.get(2).getAttribute('class')).toBe('bold strike red');\n       });\n\n       it('array with map example should have 2 classes', function() {\n         expect(ps.last().getAttribute('class')).toBe('');\n         element(by.model('style4')).sendKeys('bold');\n         element(by.model('warning')).click();\n         expect(ps.last().getAttribute('class')).toBe('bold orange');\n       });\n     </file>\n   </example>\n\n   @example\n   ### Animations\n\n   The example below demonstrates how to perform animations using ngClass.\n\n   <example module=\"ngAnimate\" deps=\"angular-animate.js\" animations=\"true\" name=\"ng-class\">\n     <file name=\"index.html\">\n      <input id=\"setbtn\" type=\"button\" value=\"set\" ng-click=\"myVar='my-class'\">\n      <input id=\"clearbtn\" type=\"button\" value=\"clear\" ng-click=\"myVar=''\">\n      <br>\n      <span class=\"base-class\" ng-class=\"myVar\">Sample Text</span>\n     </file>\n     <file name=\"style.css\">\n       .base-class {\n         transition:all cubic-bezier(0.250, 0.460, 0.450, 0.940) 0.5s;\n       }\n\n       .base-class.my-class {\n         color: red;\n         font-size:3em;\n       }\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       it('should check ng-class', function() {\n         expect(element(by.css('.base-class')).getAttribute('class')).not.\n           toMatch(/my-class/);\n\n         element(by.id('setbtn')).click();\n\n         expect(element(by.css('.base-class')).getAttribute('class')).\n           toMatch(/my-class/);\n\n         element(by.id('clearbtn')).click();\n\n         expect(element(by.css('.base-class')).getAttribute('class')).not.\n           toMatch(/my-class/);\n       });\n     </file>\n   </example>\n */\nvar ngClassDirective = classDirective('', true);\n\n/**\n * @ngdoc directive\n * @name ngClassOdd\n * @restrict AC\n *\n * @description\n * The `ngClassOdd` and `ngClassEven` directives work exactly as\n * {@link ng.directive:ngClass ngClass}, except they work in\n * conjunction with `ngRepeat` and take effect only on odd (even) rows.\n *\n * This directive can be applied only within the scope of an\n * {@link ng.directive:ngRepeat ngRepeat}.\n *\n * @animations\n * | Animation                        | Occurs                              |\n * |----------------------------------|-------------------------------------|\n * | {@link ng.$animate#addClass addClass}       | just before the class is applied to the element   |\n * | {@link ng.$animate#removeClass removeClass} | just before the class is removed from the element |\n *\n * @element ANY\n * @param {expression} ngClassOdd {@link guide/expression Expression} to eval. The result\n *   of the evaluation can be a string representing space delimited class names or an array.\n *\n * @example\n   <example name=\"ng-class-odd\">\n     <file name=\"index.html\">\n        <ol ng-init=\"names=['John', 'Mary', 'Cate', 'Suz']\">\n          <li ng-repeat=\"name in names\">\n           <span ng-class-odd=\"'odd'\" ng-class-even=\"'even'\">\n             {{name}}\n           </span>\n          </li>\n        </ol>\n     </file>\n     <file name=\"style.css\">\n       .odd {\n         color: red;\n       }\n       .even {\n         color: blue;\n       }\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       it('should check ng-class-odd and ng-class-even', function() {\n         expect(element(by.repeater('name in names').row(0).column('name')).getAttribute('class')).\n           toMatch(/odd/);\n         expect(element(by.repeater('name in names').row(1).column('name')).getAttribute('class')).\n           toMatch(/even/);\n       });\n     </file>\n   </example>\n *\n * <hr />\n * @example\n * An example on how to implement animations using `ngClassOdd`:\n *\n   <example module=\"ngAnimate\" deps=\"angular-animate.js\" animations=\"true\" name=\"ng-class-odd-animate\">\n     <file name=\"index.html\">\n       <div ng-init=\"items=['Item 3', 'Item 2', 'Item 1', 'Item 0']\">\n         <button ng-click=\"items.unshift('Item ' + items.length)\">Add item</button>\n         <hr />\n         <table>\n           <tr ng-repeat=\"item in items\" ng-class-odd=\"'odd'\">\n             <td>{{ item }}</td>\n           </tr>\n         </table>\n       </div>\n     </file>\n     <file name=\"style.css\">\n       .odd {\n         background: rgba(255, 255, 0, 0.25);\n       }\n\n       .odd-add, .odd-remove {\n         transition: 1.5s;\n       }\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       it('should add new entries to the beginning of the list', function() {\n         var button = element(by.buttonText('Add item'));\n         var rows = element.all(by.repeater('item in items'));\n\n         expect(rows.count()).toBe(4);\n         expect(rows.get(0).getText()).toBe('Item 3');\n         expect(rows.get(1).getText()).toBe('Item 2');\n\n         button.click();\n\n         expect(rows.count()).toBe(5);\n         expect(rows.get(0).getText()).toBe('Item 4');\n         expect(rows.get(1).getText()).toBe('Item 3');\n       });\n\n       it('should add odd class to odd entries', function() {\n         var button = element(by.buttonText('Add item'));\n         var rows = element.all(by.repeater('item in items'));\n\n         expect(rows.get(0).getAttribute('class')).toMatch(/odd/);\n         expect(rows.get(1).getAttribute('class')).not.toMatch(/odd/);\n\n         button.click();\n\n         expect(rows.get(0).getAttribute('class')).toMatch(/odd/);\n         expect(rows.get(1).getAttribute('class')).not.toMatch(/odd/);\n       });\n     </file>\n   </example>\n */\nvar ngClassOddDirective = classDirective('Odd', 0);\n\n/**\n * @ngdoc directive\n * @name ngClassEven\n * @restrict AC\n *\n * @description\n * The `ngClassOdd` and `ngClassEven` directives work exactly as\n * {@link ng.directive:ngClass ngClass}, except they work in\n * conjunction with `ngRepeat` and take effect only on odd (even) rows.\n *\n * This directive can be applied only within the scope of an\n * {@link ng.directive:ngRepeat ngRepeat}.\n *\n * @animations\n * | Animation                        | Occurs                              |\n * |----------------------------------|-------------------------------------|\n * | {@link ng.$animate#addClass addClass}       | just before the class is applied to the element   |\n * | {@link ng.$animate#removeClass removeClass} | just before the class is removed from the element |\n *\n * @element ANY\n * @param {expression} ngClassEven {@link guide/expression Expression} to eval. The\n *   result of the evaluation can be a string representing space delimited class names or an array.\n *\n * @example\n   <example name=\"ng-class-even\">\n     <file name=\"index.html\">\n        <ol ng-init=\"names=['John', 'Mary', 'Cate', 'Suz']\">\n          <li ng-repeat=\"name in names\">\n           <span ng-class-odd=\"'odd'\" ng-class-even=\"'even'\">\n             {{name}} &nbsp; &nbsp; &nbsp;\n           </span>\n          </li>\n        </ol>\n     </file>\n     <file name=\"style.css\">\n       .odd {\n         color: red;\n       }\n       .even {\n         color: blue;\n       }\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       it('should check ng-class-odd and ng-class-even', function() {\n         expect(element(by.repeater('name in names').row(0).column('name')).getAttribute('class')).\n           toMatch(/odd/);\n         expect(element(by.repeater('name in names').row(1).column('name')).getAttribute('class')).\n           toMatch(/even/);\n       });\n     </file>\n   </example>\n *\n * <hr />\n * @example\n * An example on how to implement animations using `ngClassEven`:\n *\n   <example module=\"ngAnimate\" deps=\"angular-animate.js\" animations=\"true\" name=\"ng-class-even-animate\">\n     <file name=\"index.html\">\n       <div ng-init=\"items=['Item 3', 'Item 2', 'Item 1', 'Item 0']\">\n         <button ng-click=\"items.unshift('Item ' + items.length)\">Add item</button>\n         <hr />\n         <table>\n           <tr ng-repeat=\"item in items\" ng-class-even=\"'even'\">\n             <td>{{ item }}</td>\n           </tr>\n         </table>\n       </div>\n     </file>\n     <file name=\"style.css\">\n       .even {\n         background: rgba(255, 255, 0, 0.25);\n       }\n\n       .even-add, .even-remove {\n         transition: 1.5s;\n       }\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       it('should add new entries to the beginning of the list', function() {\n         var button = element(by.buttonText('Add item'));\n         var rows = element.all(by.repeater('item in items'));\n\n         expect(rows.count()).toBe(4);\n         expect(rows.get(0).getText()).toBe('Item 3');\n         expect(rows.get(1).getText()).toBe('Item 2');\n\n         button.click();\n\n         expect(rows.count()).toBe(5);\n         expect(rows.get(0).getText()).toBe('Item 4');\n         expect(rows.get(1).getText()).toBe('Item 3');\n       });\n\n       it('should add even class to even entries', function() {\n         var button = element(by.buttonText('Add item'));\n         var rows = element.all(by.repeater('item in items'));\n\n         expect(rows.get(0).getAttribute('class')).not.toMatch(/even/);\n         expect(rows.get(1).getAttribute('class')).toMatch(/even/);\n\n         button.click();\n\n         expect(rows.get(0).getAttribute('class')).not.toMatch(/even/);\n         expect(rows.get(1).getAttribute('class')).toMatch(/even/);\n       });\n     </file>\n   </example>\n */\nvar ngClassEvenDirective = classDirective('Even', 1);\n\n/**\n * @ngdoc directive\n * @name ngCloak\n * @restrict AC\n *\n * @description\n * The `ngCloak` directive is used to prevent the AngularJS html template from being briefly\n * displayed by the browser in its raw (uncompiled) form while your application is loading. Use this\n * directive to avoid the undesirable flicker effect caused by the html template display.\n *\n * The directive can be applied to the `<body>` element, but the preferred usage is to apply\n * multiple `ngCloak` directives to small portions of the page to permit progressive rendering\n * of the browser view.\n *\n * `ngCloak` works in cooperation with the following css rule embedded within `angular.js` and\n * `angular.min.js`.\n * For CSP mode please add `angular-csp.css` to your html file (see {@link ng.directive:ngCsp ngCsp}).\n *\n * ```css\n * [ng\\:cloak], [ng-cloak], [data-ng-cloak], [x-ng-cloak], .ng-cloak, .x-ng-cloak {\n *   display: none !important;\n * }\n * ```\n *\n * When this css rule is loaded by the browser, all html elements (including their children) that\n * are tagged with the `ngCloak` directive are hidden. When AngularJS encounters this directive\n * during the compilation of the template it deletes the `ngCloak` element attribute, making\n * the compiled element visible.\n *\n * For the best result, the `angular.js` script must be loaded in the head section of the html\n * document; alternatively, the css rule above must be included in the external stylesheet of the\n * application.\n *\n * @element ANY\n *\n * @example\n   <example name=\"ng-cloak\">\n     <file name=\"index.html\">\n        <div id=\"template1\" ng-cloak>{{ 'hello' }}</div>\n        <div id=\"template2\" class=\"ng-cloak\">{{ 'world' }}</div>\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       it('should remove the template directive and css class', function() {\n         expect($('#template1').getAttribute('ng-cloak')).\n           toBeNull();\n         expect($('#template2').getAttribute('ng-cloak')).\n           toBeNull();\n       });\n     </file>\n   </example>\n *\n */\nvar ngCloakDirective = ngDirective({\n  compile: function(element, attr) {\n    attr.$set('ngCloak', undefined);\n    element.removeClass('ng-cloak');\n  }\n});\n\n/**\n * @ngdoc directive\n * @name ngController\n *\n * @description\n * The `ngController` directive attaches a controller class to the view. This is a key aspect of how angular\n * supports the principles behind the Model-View-Controller design pattern.\n *\n * MVC components in angular:\n *\n * * Model — Models are the properties of a scope; scopes are attached to the DOM where scope properties\n *   are accessed through bindings.\n * * View — The template (HTML with data bindings) that is rendered into the View.\n * * Controller — The `ngController` directive specifies a Controller class; the class contains business\n *   logic behind the application to decorate the scope with functions and values\n *\n * Note that you can also attach controllers to the DOM by declaring it in a route definition\n * via the {@link ngRoute.$route $route} service. A common mistake is to declare the controller\n * again using `ng-controller` in the template itself.  This will cause the controller to be attached\n * and executed twice.\n *\n * @element ANY\n * @scope\n * @priority 500\n * @param {expression} ngController Name of a constructor function registered with the current\n * {@link ng.$controllerProvider $controllerProvider} or an {@link guide/expression expression}\n * that on the current scope evaluates to a constructor function.\n *\n * The controller instance can be published into a scope property by specifying\n * `ng-controller=\"as propertyName\"`.\n *\n * @example\n * Here is a simple form for editing user contact information. Adding, removing, clearing, and\n * greeting are methods declared on the controller (see source tab). These methods can\n * easily be called from the AngularJS markup. Any changes to the data are automatically reflected\n * in the View without the need for a manual update.\n *\n * Two different declaration styles are included below:\n *\n * * one binds methods and properties directly onto the controller using `this`:\n * `ng-controller=\"SettingsController1 as settings\"`\n * * one injects `$scope` into the controller:\n * `ng-controller=\"SettingsController2\"`\n *\n * The second option is more common in the AngularJS community, and is generally used in boilerplates\n * and in this guide. However, there are advantages to binding properties directly to the controller\n * and avoiding scope.\n *\n * * Using `controller as` makes it obvious which controller you are accessing in the template when\n * multiple controllers apply to an element.\n * * If you are writing your controllers as classes you have easier access to the properties and\n * methods, which will appear on the scope, from inside the controller code.\n * * Since there is always a `.` in the bindings, you don't have to worry about prototypal\n * inheritance masking primitives.\n *\n * This example demonstrates the `controller as` syntax.\n *\n * <example name=\"ngControllerAs\" module=\"controllerAsExample\">\n *   <file name=\"index.html\">\n *    <div id=\"ctrl-as-exmpl\" ng-controller=\"SettingsController1 as settings\">\n *      <label>Name: <input type=\"text\" ng-model=\"settings.name\"/></label>\n *      <button ng-click=\"settings.greet()\">greet</button><br/>\n *      Contact:\n *      <ul>\n *        <li ng-repeat=\"contact in settings.contacts\">\n *          <select ng-model=\"contact.type\" aria-label=\"Contact method\" id=\"select_{{$index}}\">\n *             <option>phone</option>\n *             <option>email</option>\n *          </select>\n *          <input type=\"text\" ng-model=\"contact.value\" aria-labelledby=\"select_{{$index}}\" />\n *          <button ng-click=\"settings.clearContact(contact)\">clear</button>\n *          <button ng-click=\"settings.removeContact(contact)\" aria-label=\"Remove\">X</button>\n *        </li>\n *        <li><button ng-click=\"settings.addContact()\">add</button></li>\n *     </ul>\n *    </div>\n *   </file>\n *   <file name=\"app.js\">\n *    angular.module('controllerAsExample', [])\n *      .controller('SettingsController1', SettingsController1);\n *\n *    function SettingsController1() {\n *      this.name = 'John Smith';\n *      this.contacts = [\n *        {type: 'phone', value: '408 555 1212'},\n *        {type: 'email', value: 'john.smith@example.org'}\n *      ];\n *    }\n *\n *    SettingsController1.prototype.greet = function() {\n *      alert(this.name);\n *    };\n *\n *    SettingsController1.prototype.addContact = function() {\n *      this.contacts.push({type: 'email', value: 'yourname@example.org'});\n *    };\n *\n *    SettingsController1.prototype.removeContact = function(contactToRemove) {\n *     var index = this.contacts.indexOf(contactToRemove);\n *      this.contacts.splice(index, 1);\n *    };\n *\n *    SettingsController1.prototype.clearContact = function(contact) {\n *      contact.type = 'phone';\n *      contact.value = '';\n *    };\n *   </file>\n *   <file name=\"protractor.js\" type=\"protractor\">\n *     it('should check controller as', function() {\n *       var container = element(by.id('ctrl-as-exmpl'));\n *         expect(container.element(by.model('settings.name'))\n *           .getAttribute('value')).toBe('John Smith');\n *\n *       var firstRepeat =\n *           container.element(by.repeater('contact in settings.contacts').row(0));\n *       var secondRepeat =\n *           container.element(by.repeater('contact in settings.contacts').row(1));\n *\n *       expect(firstRepeat.element(by.model('contact.value')).getAttribute('value'))\n *           .toBe('408 555 1212');\n *\n *       expect(secondRepeat.element(by.model('contact.value')).getAttribute('value'))\n *           .toBe('john.smith@example.org');\n *\n *       firstRepeat.element(by.buttonText('clear')).click();\n *\n *       expect(firstRepeat.element(by.model('contact.value')).getAttribute('value'))\n *           .toBe('');\n *\n *       container.element(by.buttonText('add')).click();\n *\n *       expect(container.element(by.repeater('contact in settings.contacts').row(2))\n *           .element(by.model('contact.value'))\n *           .getAttribute('value'))\n *           .toBe('yourname@example.org');\n *     });\n *   </file>\n * </example>\n *\n * This example demonstrates the \"attach to `$scope`\" style of controller.\n *\n * <example name=\"ngController\" module=\"controllerExample\">\n *  <file name=\"index.html\">\n *   <div id=\"ctrl-exmpl\" ng-controller=\"SettingsController2\">\n *     <label>Name: <input type=\"text\" ng-model=\"name\"/></label>\n *     <button ng-click=\"greet()\">greet</button><br/>\n *     Contact:\n *     <ul>\n *       <li ng-repeat=\"contact in contacts\">\n *         <select ng-model=\"contact.type\" id=\"select_{{$index}}\">\n *            <option>phone</option>\n *            <option>email</option>\n *         </select>\n *         <input type=\"text\" ng-model=\"contact.value\" aria-labelledby=\"select_{{$index}}\" />\n *         <button ng-click=\"clearContact(contact)\">clear</button>\n *         <button ng-click=\"removeContact(contact)\">X</button>\n *       </li>\n *       <li>[ <button ng-click=\"addContact()\">add</button> ]</li>\n *    </ul>\n *   </div>\n *  </file>\n *  <file name=\"app.js\">\n *   angular.module('controllerExample', [])\n *     .controller('SettingsController2', ['$scope', SettingsController2]);\n *\n *   function SettingsController2($scope) {\n *     $scope.name = 'John Smith';\n *     $scope.contacts = [\n *       {type:'phone', value:'408 555 1212'},\n *       {type:'email', value:'john.smith@example.org'}\n *     ];\n *\n *     $scope.greet = function() {\n *       alert($scope.name);\n *     };\n *\n *     $scope.addContact = function() {\n *       $scope.contacts.push({type:'email', value:'yourname@example.org'});\n *     };\n *\n *     $scope.removeContact = function(contactToRemove) {\n *       var index = $scope.contacts.indexOf(contactToRemove);\n *       $scope.contacts.splice(index, 1);\n *     };\n *\n *     $scope.clearContact = function(contact) {\n *       contact.type = 'phone';\n *       contact.value = '';\n *     };\n *   }\n *  </file>\n *  <file name=\"protractor.js\" type=\"protractor\">\n *    it('should check controller', function() {\n *      var container = element(by.id('ctrl-exmpl'));\n *\n *      expect(container.element(by.model('name'))\n *          .getAttribute('value')).toBe('John Smith');\n *\n *      var firstRepeat =\n *          container.element(by.repeater('contact in contacts').row(0));\n *      var secondRepeat =\n *          container.element(by.repeater('contact in contacts').row(1));\n *\n *      expect(firstRepeat.element(by.model('contact.value')).getAttribute('value'))\n *          .toBe('408 555 1212');\n *      expect(secondRepeat.element(by.model('contact.value')).getAttribute('value'))\n *          .toBe('john.smith@example.org');\n *\n *      firstRepeat.element(by.buttonText('clear')).click();\n *\n *      expect(firstRepeat.element(by.model('contact.value')).getAttribute('value'))\n *          .toBe('');\n *\n *      container.element(by.buttonText('add')).click();\n *\n *      expect(container.element(by.repeater('contact in contacts').row(2))\n *          .element(by.model('contact.value'))\n *          .getAttribute('value'))\n *          .toBe('yourname@example.org');\n *    });\n *  </file>\n *</example>\n\n */\nvar ngControllerDirective = [function() {\n  return {\n    restrict: 'A',\n    scope: true,\n    controller: '@',\n    priority: 500\n  };\n}];\n\n/**\n * @ngdoc directive\n * @name ngCsp\n *\n * @restrict A\n * @element ANY\n * @description\n *\n * AngularJS has some features that can conflict with certain restrictions that are applied when using\n * [CSP (Content Security Policy)](https://developer.mozilla.org/en/Security/CSP) rules.\n *\n * If you intend to implement CSP with these rules then you must tell AngularJS not to use these\n * features.\n *\n * This is necessary when developing things like Google Chrome Extensions or Universal Windows Apps.\n *\n *\n * The following default rules in CSP affect AngularJS:\n *\n * * The use of `eval()`, `Function(string)` and similar functions to dynamically create and execute\n * code from strings is forbidden. AngularJS makes use of this in the {@link $parse} service to\n * provide a 30% increase in the speed of evaluating AngularJS expressions. (This CSP rule can be\n * disabled with the CSP keyword `unsafe-eval`, but it is generally not recommended as it would\n * weaken the protections offered by CSP.)\n *\n * * The use of inline resources, such as inline `<script>` and `<style>` elements, are forbidden.\n * This prevents apps from injecting custom styles directly into the document. AngularJS makes use of\n * this to include some CSS rules (e.g. {@link ngCloak} and {@link ngHide}). To make these\n * directives work when a CSP rule is blocking inline styles, you must link to the `angular-csp.css`\n * in your HTML manually. (This CSP rule can be disabled with the CSP keyword `unsafe-inline`, but\n * it is generally not recommended as it would weaken the protections offered by CSP.)\n *\n * If you do not provide `ngCsp` then AngularJS tries to autodetect if CSP is blocking dynamic code\n * creation from strings (e.g., `unsafe-eval` not specified in CSP header) and automatically\n * deactivates this feature in the {@link $parse} service. This autodetection, however, triggers a\n * CSP error to be logged in the console:\n *\n * ```\n * Refused to evaluate a string as JavaScript because 'unsafe-eval' is not an allowed source of\n * script in the following Content Security Policy directive: \"default-src 'self'\". Note that\n * 'script-src' was not explicitly set, so 'default-src' is used as a fallback.\n * ```\n *\n * This error is harmless but annoying. To prevent the error from showing up, put the `ngCsp`\n * directive on an element of the HTML document that appears before the `<script>` tag that loads\n * the `angular.js` file.\n *\n * *Note: This directive is only available in the `ng-csp` and `data-ng-csp` attribute form.*\n *\n * You can specify which of the CSP related AngularJS features should be deactivated by providing\n * a value for the `ng-csp` attribute. The options are as follows:\n *\n * * no-inline-style: this stops AngularJS from injecting CSS styles into the DOM\n *\n * * no-unsafe-eval: this stops AngularJS from optimizing $parse with unsafe eval of strings\n *\n * You can use these values in the following combinations:\n *\n *\n * * No declaration means that AngularJS will assume that you can do inline styles, but it will do\n * a runtime check for unsafe-eval. E.g. `<body>`. This is backwardly compatible with previous\n * versions of AngularJS.\n *\n * * A simple `ng-csp` (or `data-ng-csp`) attribute will tell AngularJS to deactivate both inline\n * styles and unsafe eval. E.g. `<body ng-csp>`. This is backwardly compatible with previous\n * versions of AngularJS.\n *\n * * Specifying only `no-unsafe-eval` tells AngularJS that we must not use eval, but that we can\n * inject inline styles. E.g. `<body ng-csp=\"no-unsafe-eval\">`.\n *\n * * Specifying only `no-inline-style` tells AngularJS that we must not inject styles, but that we can\n * run eval - no automatic check for unsafe eval will occur. E.g. `<body ng-csp=\"no-inline-style\">`\n *\n * * Specifying both `no-unsafe-eval` and `no-inline-style` tells AngularJS that we must not inject\n * styles nor use eval, which is the same as an empty: ng-csp.\n * E.g.`<body ng-csp=\"no-inline-style;no-unsafe-eval\">`\n *\n * @example\n *\n * This example shows how to apply the `ngCsp` directive to the `html` tag.\n   ```html\n     <!doctype html>\n     <html ng-app ng-csp>\n     ...\n     ...\n     </html>\n   ```\n\n  <!-- Note: the `.csp` suffix in the example name triggers CSP mode in our http server! -->\n  <example name=\"example.csp\" module=\"cspExample\" ng-csp=\"true\">\n    <file name=\"index.html\">\n      <div ng-controller=\"MainController as ctrl\">\n        <div>\n          <button ng-click=\"ctrl.inc()\" id=\"inc\">Increment</button>\n          <span id=\"counter\">\n            {{ctrl.counter}}\n          </span>\n        </div>\n\n        <div>\n          <button ng-click=\"ctrl.evil()\" id=\"evil\">Evil</button>\n          <span id=\"evilError\">\n            {{ctrl.evilError}}\n          </span>\n        </div>\n      </div>\n    </file>\n    <file name=\"script.js\">\n       angular.module('cspExample', [])\n         .controller('MainController', function MainController() {\n            this.counter = 0;\n            this.inc = function() {\n              this.counter++;\n            };\n            this.evil = function() {\n              try {\n                eval('1+2'); // eslint-disable-line no-eval\n              } catch (e) {\n                this.evilError = e.message;\n              }\n            };\n          });\n    </file>\n    <file name=\"protractor.js\" type=\"protractor\">\n      var util, webdriver;\n\n      var incBtn = element(by.id('inc'));\n      var counter = element(by.id('counter'));\n      var evilBtn = element(by.id('evil'));\n      var evilError = element(by.id('evilError'));\n\n      function getAndClearSevereErrors() {\n        return browser.manage().logs().get('browser').then(function(browserLog) {\n          return browserLog.filter(function(logEntry) {\n            return logEntry.level.value > webdriver.logging.Level.WARNING.value;\n          });\n        });\n      }\n\n      function clearErrors() {\n        getAndClearSevereErrors();\n      }\n\n      function expectNoErrors() {\n        getAndClearSevereErrors().then(function(filteredLog) {\n          expect(filteredLog.length).toEqual(0);\n          if (filteredLog.length) {\n            console.log('browser console errors: ' + util.inspect(filteredLog));\n          }\n        });\n      }\n\n      function expectError(regex) {\n        getAndClearSevereErrors().then(function(filteredLog) {\n          var found = false;\n          filteredLog.forEach(function(log) {\n            if (log.message.match(regex)) {\n              found = true;\n            }\n          });\n          if (!found) {\n            throw new Error('expected an error that matches ' + regex);\n          }\n        });\n      }\n\n      beforeEach(function() {\n        util = require('util');\n        webdriver = require('selenium-webdriver');\n      });\n\n      // For now, we only test on Chrome,\n      // as Safari does not load the page with Protractor's injected scripts,\n      // and Firefox webdriver always disables content security policy (#6358)\n      if (browser.params.browser !== 'chrome') {\n        return;\n      }\n\n      it('should not report errors when the page is loaded', function() {\n        // clear errors so we are not dependent on previous tests\n        clearErrors();\n        // Need to reload the page as the page is already loaded when\n        // we come here\n        browser.driver.getCurrentUrl().then(function(url) {\n          browser.get(url);\n        });\n        expectNoErrors();\n      });\n\n      it('should evaluate expressions', function() {\n        expect(counter.getText()).toEqual('0');\n        incBtn.click();\n        expect(counter.getText()).toEqual('1');\n        expectNoErrors();\n      });\n\n      it('should throw and report an error when using \"eval\"', function() {\n        evilBtn.click();\n        expect(evilError.getText()).toMatch(/Content Security Policy/);\n        expectError(/Content Security Policy/);\n      });\n    </file>\n  </example>\n  */\n\n// `ngCsp` is not implemented as a proper directive any more, because we need it be processed while\n// we bootstrap the app (before `$parse` is instantiated). For this reason, we just have the `csp()`\n// fn that looks for the `ng-csp` attribute anywhere in the current doc.\n\n/**\n * @ngdoc directive\n * @name ngClick\n * @restrict A\n * @element ANY\n * @priority 0\n *\n * @description\n * The ngClick directive allows you to specify custom behavior when\n * an element is clicked.\n *\n * @param {expression} ngClick {@link guide/expression Expression} to evaluate upon\n * click. ({@link guide/expression#-event- Event object is available as `$event`})\n *\n * @example\n   <example name=\"ng-click\">\n     <file name=\"index.html\">\n      <button ng-click=\"count = count + 1\" ng-init=\"count=0\">\n        Increment\n      </button>\n      <span>\n        count: {{count}}\n      </span>\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       it('should check ng-click', function() {\n         expect(element(by.binding('count')).getText()).toMatch('0');\n         element(by.css('button')).click();\n         expect(element(by.binding('count')).getText()).toMatch('1');\n       });\n     </file>\n   </example>\n */\n/*\n * A collection of directives that allows creation of custom event handlers that are defined as\n * AngularJS expressions and are compiled and executed within the current scope.\n */\nvar ngEventDirectives = {};\n\n// For events that might fire synchronously during DOM manipulation\n// we need to execute their event handlers asynchronously using $evalAsync,\n// so that they are not executed in an inconsistent state.\nvar forceAsyncEvents = {\n  'blur': true,\n  'focus': true\n};\nforEach(\n  'click dblclick mousedown mouseup mouseover mouseout mousemove mouseenter mouseleave keydown keyup keypress submit focus blur copy cut paste'.split(' '),\n  function(eventName) {\n    var directiveName = directiveNormalize('ng-' + eventName);\n    ngEventDirectives[directiveName] = ['$parse', '$rootScope', '$exceptionHandler', function($parse, $rootScope, $exceptionHandler) {\n      return createEventDirective($parse, $rootScope, $exceptionHandler, directiveName, eventName, forceAsyncEvents[eventName]);\n    }];\n  }\n);\n\nfunction createEventDirective($parse, $rootScope, $exceptionHandler, directiveName, eventName, forceAsync) {\n  return {\n    restrict: 'A',\n    compile: function($element, attr) {\n      // NOTE:\n      // We expose the powerful `$event` object on the scope that provides access to the Window,\n      // etc. This is OK, because expressions are not sandboxed any more (and the expression\n      // sandbox was never meant to be a security feature anyway).\n      var fn = $parse(attr[directiveName]);\n      return function ngEventHandler(scope, element) {\n        element.on(eventName, function(event) {\n          var callback = function() {\n            fn(scope, {$event: event});\n          };\n\n          if (!$rootScope.$$phase) {\n            scope.$apply(callback);\n          } else if (forceAsync) {\n            scope.$evalAsync(callback);\n          } else {\n            try {\n              callback();\n            } catch (error) {\n              $exceptionHandler(error);\n            }\n          }\n        });\n      };\n    }\n  };\n}\n\n/**\n * @ngdoc directive\n * @name ngDblclick\n * @restrict A\n * @element ANY\n * @priority 0\n *\n * @description\n * The `ngDblclick` directive allows you to specify custom behavior on a dblclick event.\n *\n * @param {expression} ngDblclick {@link guide/expression Expression} to evaluate upon\n * a dblclick. (The Event object is available as `$event`)\n *\n * @example\n   <example name=\"ng-dblclick\">\n     <file name=\"index.html\">\n      <button ng-dblclick=\"count = count + 1\" ng-init=\"count=0\">\n        Increment (on double click)\n      </button>\n      count: {{count}}\n     </file>\n   </example>\n */\n\n\n/**\n * @ngdoc directive\n * @name ngMousedown\n * @restrict A\n * @element ANY\n * @priority 0\n *\n * @description\n * The ngMousedown directive allows you to specify custom behavior on mousedown event.\n *\n * @param {expression} ngMousedown {@link guide/expression Expression} to evaluate upon\n * mousedown. ({@link guide/expression#-event- Event object is available as `$event`})\n *\n * @example\n   <example name=\"ng-mousedown\">\n     <file name=\"index.html\">\n      <button ng-mousedown=\"count = count + 1\" ng-init=\"count=0\">\n        Increment (on mouse down)\n      </button>\n      count: {{count}}\n     </file>\n   </example>\n */\n\n\n/**\n * @ngdoc directive\n * @name ngMouseup\n * @restrict A\n * @element ANY\n * @priority 0\n *\n * @description\n * Specify custom behavior on mouseup event.\n *\n * @param {expression} ngMouseup {@link guide/expression Expression} to evaluate upon\n * mouseup. ({@link guide/expression#-event- Event object is available as `$event`})\n *\n * @example\n   <example name=\"ng-mouseup\">\n     <file name=\"index.html\">\n      <button ng-mouseup=\"count = count + 1\" ng-init=\"count=0\">\n        Increment (on mouse up)\n      </button>\n      count: {{count}}\n     </file>\n   </example>\n */\n\n/**\n * @ngdoc directive\n * @name ngMouseover\n * @restrict A\n * @element ANY\n * @priority 0\n *\n * @description\n * Specify custom behavior on mouseover event.\n *\n * @param {expression} ngMouseover {@link guide/expression Expression} to evaluate upon\n * mouseover. ({@link guide/expression#-event- Event object is available as `$event`})\n *\n * @example\n   <example name=\"ng-mouseover\">\n     <file name=\"index.html\">\n      <button ng-mouseover=\"count = count + 1\" ng-init=\"count=0\">\n        Increment (when mouse is over)\n      </button>\n      count: {{count}}\n     </file>\n   </example>\n */\n\n\n/**\n * @ngdoc directive\n * @name ngMouseenter\n * @restrict A\n * @element ANY\n * @priority 0\n *\n * @description\n * Specify custom behavior on mouseenter event.\n *\n * @param {expression} ngMouseenter {@link guide/expression Expression} to evaluate upon\n * mouseenter. ({@link guide/expression#-event- Event object is available as `$event`})\n *\n * @example\n   <example name=\"ng-mouseenter\">\n     <file name=\"index.html\">\n      <button ng-mouseenter=\"count = count + 1\" ng-init=\"count=0\">\n        Increment (when mouse enters)\n      </button>\n      count: {{count}}\n     </file>\n   </example>\n */\n\n\n/**\n * @ngdoc directive\n * @name ngMouseleave\n * @restrict A\n * @element ANY\n * @priority 0\n *\n * @description\n * Specify custom behavior on mouseleave event.\n *\n * @param {expression} ngMouseleave {@link guide/expression Expression} to evaluate upon\n * mouseleave. ({@link guide/expression#-event- Event object is available as `$event`})\n *\n * @example\n   <example name=\"ng-mouseleave\">\n     <file name=\"index.html\">\n      <button ng-mouseleave=\"count = count + 1\" ng-init=\"count=0\">\n        Increment (when mouse leaves)\n      </button>\n      count: {{count}}\n     </file>\n   </example>\n */\n\n\n/**\n * @ngdoc directive\n * @name ngMousemove\n * @restrict A\n * @element ANY\n * @priority 0\n *\n * @description\n * Specify custom behavior on mousemove event.\n *\n * @param {expression} ngMousemove {@link guide/expression Expression} to evaluate upon\n * mousemove. ({@link guide/expression#-event- Event object is available as `$event`})\n *\n * @example\n   <example name=\"ng-mousemove\">\n     <file name=\"index.html\">\n      <button ng-mousemove=\"count = count + 1\" ng-init=\"count=0\">\n        Increment (when mouse moves)\n      </button>\n      count: {{count}}\n     </file>\n   </example>\n */\n\n\n/**\n * @ngdoc directive\n * @name ngKeydown\n * @restrict A\n * @element ANY\n * @priority 0\n *\n * @description\n * Specify custom behavior on keydown event.\n *\n * @param {expression} ngKeydown {@link guide/expression Expression} to evaluate upon\n * keydown. (Event object is available as `$event` and can be interrogated for keyCode, altKey, etc.)\n *\n * @example\n   <example name=\"ng-keydown\">\n     <file name=\"index.html\">\n      <input ng-keydown=\"count = count + 1\" ng-init=\"count=0\">\n      key down count: {{count}}\n     </file>\n   </example>\n */\n\n\n/**\n * @ngdoc directive\n * @name ngKeyup\n * @restrict A\n * @element ANY\n * @priority 0\n *\n * @description\n * Specify custom behavior on keyup event.\n *\n * @param {expression} ngKeyup {@link guide/expression Expression} to evaluate upon\n * keyup. (Event object is available as `$event` and can be interrogated for keyCode, altKey, etc.)\n *\n * @example\n   <example name=\"ng-keyup\">\n     <file name=\"index.html\">\n       <p>Typing in the input box below updates the key count</p>\n       <input ng-keyup=\"count = count + 1\" ng-init=\"count=0\"> key up count: {{count}}\n\n       <p>Typing in the input box below updates the keycode</p>\n       <input ng-keyup=\"event=$event\">\n       <p>event keyCode: {{ event.keyCode }}</p>\n       <p>event altKey: {{ event.altKey }}</p>\n     </file>\n   </example>\n */\n\n\n/**\n * @ngdoc directive\n * @name ngKeypress\n * @restrict A\n * @element ANY\n *\n * @description\n * Specify custom behavior on keypress event.\n *\n * @param {expression} ngKeypress {@link guide/expression Expression} to evaluate upon\n * keypress. ({@link guide/expression#-event- Event object is available as `$event`}\n * and can be interrogated for keyCode, altKey, etc.)\n *\n * @example\n   <example name=\"ng-keypress\">\n     <file name=\"index.html\">\n      <input ng-keypress=\"count = count + 1\" ng-init=\"count=0\">\n      key press count: {{count}}\n     </file>\n   </example>\n */\n\n\n/**\n * @ngdoc directive\n * @name ngSubmit\n * @restrict A\n * @element form\n * @priority 0\n *\n * @description\n * Enables binding AngularJS expressions to onsubmit events.\n *\n * Additionally it prevents the default action (which for form means sending the request to the\n * server and reloading the current page), but only if the form does not contain `action`,\n * `data-action`, or `x-action` attributes.\n *\n * <div class=\"alert alert-warning\">\n * **Warning:** Be careful not to cause \"double-submission\" by using both the `ngClick` and\n * `ngSubmit` handlers together. See the\n * {@link form#submitting-a-form-and-preventing-the-default-action `form` directive documentation}\n * for a detailed discussion of when `ngSubmit` may be triggered.\n * </div>\n *\n * @param {expression} ngSubmit {@link guide/expression Expression} to eval.\n * ({@link guide/expression#-event- Event object is available as `$event`})\n *\n * @example\n   <example module=\"submitExample\" name=\"ng-submit\">\n     <file name=\"index.html\">\n      <script>\n        angular.module('submitExample', [])\n          .controller('ExampleController', ['$scope', function($scope) {\n            $scope.list = [];\n            $scope.text = 'hello';\n            $scope.submit = function() {\n              if ($scope.text) {\n                $scope.list.push(this.text);\n                $scope.text = '';\n              }\n            };\n          }]);\n      </script>\n      <form ng-submit=\"submit()\" ng-controller=\"ExampleController\">\n        Enter text and hit enter:\n        <input type=\"text\" ng-model=\"text\" name=\"text\" />\n        <input type=\"submit\" id=\"submit\" value=\"Submit\" />\n        <pre>list={{list}}</pre>\n      </form>\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       it('should check ng-submit', function() {\n         expect(element(by.binding('list')).getText()).toBe('list=[]');\n         element(by.css('#submit')).click();\n         expect(element(by.binding('list')).getText()).toContain('hello');\n         expect(element(by.model('text')).getAttribute('value')).toBe('');\n       });\n       it('should ignore empty strings', function() {\n         expect(element(by.binding('list')).getText()).toBe('list=[]');\n         element(by.css('#submit')).click();\n         element(by.css('#submit')).click();\n         expect(element(by.binding('list')).getText()).toContain('hello');\n        });\n     </file>\n   </example>\n */\n\n/**\n * @ngdoc directive\n * @name ngFocus\n * @restrict A\n * @element window, input, select, textarea, a\n * @priority 0\n *\n * @description\n * Specify custom behavior on focus event.\n *\n * Note: As the `focus` event is executed synchronously when calling `input.focus()`\n * AngularJS executes the expression using `scope.$evalAsync` if the event is fired\n * during an `$apply` to ensure a consistent state.\n *\n * @param {expression} ngFocus {@link guide/expression Expression} to evaluate upon\n * focus. ({@link guide/expression#-event- Event object is available as `$event`})\n *\n * @example\n * See {@link ng.directive:ngClick ngClick}\n */\n\n/**\n * @ngdoc directive\n * @name ngBlur\n * @restrict A\n * @element window, input, select, textarea, a\n * @priority 0\n *\n * @description\n * Specify custom behavior on blur event.\n *\n * A [blur event](https://developer.mozilla.org/en-US/docs/Web/Events/blur) fires when\n * an element has lost focus.\n *\n * Note: As the `blur` event is executed synchronously also during DOM manipulations\n * (e.g. removing a focussed input),\n * AngularJS executes the expression using `scope.$evalAsync` if the event is fired\n * during an `$apply` to ensure a consistent state.\n *\n * @param {expression} ngBlur {@link guide/expression Expression} to evaluate upon\n * blur. ({@link guide/expression#-event- Event object is available as `$event`})\n *\n * @example\n * See {@link ng.directive:ngClick ngClick}\n */\n\n/**\n * @ngdoc directive\n * @name ngCopy\n * @restrict A\n * @element window, input, select, textarea, a\n * @priority 0\n *\n * @description\n * Specify custom behavior on copy event.\n *\n * @param {expression} ngCopy {@link guide/expression Expression} to evaluate upon\n * copy. ({@link guide/expression#-event- Event object is available as `$event`})\n *\n * @example\n   <example name=\"ng-copy\">\n     <file name=\"index.html\">\n      <input ng-copy=\"copied=true\" ng-init=\"copied=false; value='copy me'\" ng-model=\"value\">\n      copied: {{copied}}\n     </file>\n   </example>\n */\n\n/**\n * @ngdoc directive\n * @name ngCut\n * @restrict A\n * @element window, input, select, textarea, a\n * @priority 0\n *\n * @description\n * Specify custom behavior on cut event.\n *\n * @param {expression} ngCut {@link guide/expression Expression} to evaluate upon\n * cut. ({@link guide/expression#-event- Event object is available as `$event`})\n *\n * @example\n   <example name=\"ng-cut\">\n     <file name=\"index.html\">\n      <input ng-cut=\"cut=true\" ng-init=\"cut=false; value='cut me'\" ng-model=\"value\">\n      cut: {{cut}}\n     </file>\n   </example>\n */\n\n/**\n * @ngdoc directive\n * @name ngPaste\n * @restrict A\n * @element window, input, select, textarea, a\n * @priority 0\n *\n * @description\n * Specify custom behavior on paste event.\n *\n * @param {expression} ngPaste {@link guide/expression Expression} to evaluate upon\n * paste. ({@link guide/expression#-event- Event object is available as `$event`})\n *\n * @example\n   <example name=\"ng-paste\">\n     <file name=\"index.html\">\n      <input ng-paste=\"paste=true\" ng-init=\"paste=false\" placeholder='paste here'>\n      pasted: {{paste}}\n     </file>\n   </example>\n */\n\n/**\n * @ngdoc directive\n * @name ngIf\n * @restrict A\n * @multiElement\n *\n * @description\n * The `ngIf` directive removes or recreates a portion of the DOM tree based on an\n * {expression}. If the expression assigned to `ngIf` evaluates to a false\n * value then the element is removed from the DOM, otherwise a clone of the\n * element is reinserted into the DOM.\n *\n * `ngIf` differs from `ngShow` and `ngHide` in that `ngIf` completely removes and recreates the\n * element in the DOM rather than changing its visibility via the `display` css property.  A common\n * case when this difference is significant is when using css selectors that rely on an element's\n * position within the DOM, such as the `:first-child` or `:last-child` pseudo-classes.\n *\n * Note that when an element is removed using `ngIf` its scope is destroyed and a new scope\n * is created when the element is restored.  The scope created within `ngIf` inherits from\n * its parent scope using\n * [prototypal inheritance](https://github.com/angular/angular.js/wiki/Understanding-Scopes#javascript-prototypal-inheritance).\n * An important implication of this is if `ngModel` is used within `ngIf` to bind to\n * a javascript primitive defined in the parent scope. In this case any modifications made to the\n * variable within the child scope will override (hide) the value in the parent scope.\n *\n * Also, `ngIf` recreates elements using their compiled state. An example of this behavior\n * is if an element's class attribute is directly modified after it's compiled, using something like\n * jQuery's `.addClass()` method, and the element is later removed. When `ngIf` recreates the element\n * the added class will be lost because the original compiled state is used to regenerate the element.\n *\n * Additionally, you can provide animations via the `ngAnimate` module to animate the `enter`\n * and `leave` effects.\n *\n * @animations\n * | Animation                        | Occurs                               |\n * |----------------------------------|-------------------------------------|\n * | {@link ng.$animate#enter enter}  | just after the `ngIf` contents change and a new DOM element is created and injected into the `ngIf` container |\n * | {@link ng.$animate#leave leave}  | just before the `ngIf` contents are removed from the DOM |\n *\n * @element ANY\n * @scope\n * @priority 600\n * @param {expression} ngIf If the {@link guide/expression expression} is falsy then\n *     the element is removed from the DOM tree. If it is truthy a copy of the compiled\n *     element is added to the DOM tree.\n *\n * @example\n  <example module=\"ngAnimate\" deps=\"angular-animate.js\" animations=\"true\" name=\"ng-if\">\n    <file name=\"index.html\">\n      <label>Click me: <input type=\"checkbox\" ng-model=\"checked\" ng-init=\"checked=true\" /></label><br/>\n      Show when checked:\n      <span ng-if=\"checked\" class=\"animate-if\">\n        This is removed when the checkbox is unchecked.\n      </span>\n    </file>\n    <file name=\"animations.css\">\n      .animate-if {\n        background:white;\n        border:1px solid black;\n        padding:10px;\n      }\n\n      .animate-if.ng-enter, .animate-if.ng-leave {\n        transition:all cubic-bezier(0.250, 0.460, 0.450, 0.940) 0.5s;\n      }\n\n      .animate-if.ng-enter,\n      .animate-if.ng-leave.ng-leave-active {\n        opacity:0;\n      }\n\n      .animate-if.ng-leave,\n      .animate-if.ng-enter.ng-enter-active {\n        opacity:1;\n      }\n    </file>\n  </example>\n */\nvar ngIfDirective = ['$animate', '$compile', function($animate, $compile) {\n  return {\n    multiElement: true,\n    transclude: 'element',\n    priority: 600,\n    terminal: true,\n    restrict: 'A',\n    $$tlb: true,\n    link: function($scope, $element, $attr, ctrl, $transclude) {\n        var block, childScope, previousElements;\n        $scope.$watch($attr.ngIf, function ngIfWatchAction(value) {\n\n          if (value) {\n            if (!childScope) {\n              $transclude(function(clone, newScope) {\n                childScope = newScope;\n                clone[clone.length++] = $compile.$$createComment('end ngIf', $attr.ngIf);\n                // Note: We only need the first/last node of the cloned nodes.\n                // However, we need to keep the reference to the jqlite wrapper as it might be changed later\n                // by a directive with templateUrl when its template arrives.\n                block = {\n                  clone: clone\n                };\n                $animate.enter(clone, $element.parent(), $element);\n              });\n            }\n          } else {\n            if (previousElements) {\n              previousElements.remove();\n              previousElements = null;\n            }\n            if (childScope) {\n              childScope.$destroy();\n              childScope = null;\n            }\n            if (block) {\n              previousElements = getBlockNodes(block.clone);\n              $animate.leave(previousElements).done(function(response) {\n                if (response !== false) previousElements = null;\n              });\n              block = null;\n            }\n          }\n        });\n    }\n  };\n}];\n\n/**\n * @ngdoc directive\n * @name ngInclude\n * @restrict ECA\n * @scope\n * @priority -400\n *\n * @description\n * Fetches, compiles and includes an external HTML fragment.\n *\n * By default, the template URL is restricted to the same domain and protocol as the\n * application document. This is done by calling {@link $sce#getTrustedResourceUrl\n * $sce.getTrustedResourceUrl} on it. To load templates from other domains or protocols\n * you may either add them to your {@link ng.$sceDelegateProvider#trustedResourceUrlList trusted\n * resource URL list} or {@link $sce#trustAsResourceUrl wrap them} as trusted values. Refer to\n * AngularJS's {@link ng.$sce Strict Contextual Escaping}.\n *\n * In addition, the browser's\n * [Same Origin Policy](https://code.google.com/p/browsersec/wiki/Part2#Same-origin_policy_for_XMLHttpRequest)\n * and [Cross-Origin Resource Sharing (CORS)](http://www.w3.org/TR/cors/)\n * policy may further restrict whether the template is successfully loaded.\n * For example, `ngInclude` won't work for cross-domain requests on all browsers and for `file://`\n * access on some browsers.\n *\n * @animations\n * | Animation                        | Occurs                              |\n * |----------------------------------|-------------------------------------|\n * | {@link ng.$animate#enter enter}  | when the expression changes, on the new include |\n * | {@link ng.$animate#leave leave}  | when the expression changes, on the old include |\n *\n * The enter and leave animation occur concurrently.\n *\n * @param {string} ngInclude|src AngularJS expression evaluating to URL. If the source is a string constant,\n *                 make sure you wrap it in **single** quotes, e.g. `src=\"'myPartialTemplate.html'\"`.\n * @param {string=} onload Expression to evaluate when a new partial is loaded.\n *                  <div class=\"alert alert-warning\">\n *                  **Note:** When using onload on SVG elements in IE11, the browser will try to call\n *                  a function with the name on the window element, which will usually throw a\n *                  \"function is undefined\" error. To fix this, you can instead use `data-onload` or a\n *                  different form that {@link guide/directive#normalization matches} `onload`.\n *                  </div>\n   *\n * @param {string=} autoscroll Whether `ngInclude` should call {@link ng.$anchorScroll\n *                  $anchorScroll} to scroll the viewport after the content is loaded.\n *\n *                  - If the attribute is not set, disable scrolling.\n *                  - If the attribute is set without value, enable scrolling.\n *                  - Otherwise enable scrolling only if the expression evaluates to truthy value.\n *\n * @example\n  <example module=\"includeExample\" deps=\"angular-animate.js\" animations=\"true\" name=\"ng-include\">\n    <file name=\"index.html\">\n     <div ng-controller=\"ExampleController\">\n       <select ng-model=\"template\" ng-options=\"t.name for t in templates\">\n        <option value=\"\">(blank)</option>\n       </select>\n       url of the template: <code>{{template.url}}</code>\n       <hr/>\n       <div class=\"slide-animate-container\">\n         <div class=\"slide-animate\" ng-include=\"template.url\"></div>\n       </div>\n     </div>\n    </file>\n    <file name=\"script.js\">\n      angular.module('includeExample', ['ngAnimate'])\n        .controller('ExampleController', ['$scope', function($scope) {\n          $scope.templates =\n            [{ name: 'template1.html', url: 'template1.html'},\n             { name: 'template2.html', url: 'template2.html'}];\n          $scope.template = $scope.templates[0];\n        }]);\n     </file>\n    <file name=\"template1.html\">\n      Content of template1.html\n    </file>\n    <file name=\"template2.html\">\n      Content of template2.html\n    </file>\n    <file name=\"animations.css\">\n      .slide-animate-container {\n        position:relative;\n        background:white;\n        border:1px solid black;\n        height:40px;\n        overflow:hidden;\n      }\n\n      .slide-animate {\n        padding:10px;\n      }\n\n      .slide-animate.ng-enter, .slide-animate.ng-leave {\n        transition:all cubic-bezier(0.250, 0.460, 0.450, 0.940) 0.5s;\n\n        position:absolute;\n        top:0;\n        left:0;\n        right:0;\n        bottom:0;\n        display:block;\n        padding:10px;\n      }\n\n      .slide-animate.ng-enter {\n        top:-50px;\n      }\n      .slide-animate.ng-enter.ng-enter-active {\n        top:0;\n      }\n\n      .slide-animate.ng-leave {\n        top:0;\n      }\n      .slide-animate.ng-leave.ng-leave-active {\n        top:50px;\n      }\n    </file>\n    <file name=\"protractor.js\" type=\"protractor\">\n      var templateSelect = element(by.model('template'));\n      var includeElem = element(by.css('[ng-include]'));\n\n      it('should load template1.html', function() {\n        expect(includeElem.getText()).toMatch(/Content of template1.html/);\n      });\n\n      it('should load template2.html', function() {\n        if (browser.params.browser === 'firefox') {\n          // Firefox can't handle using selects\n          // See https://github.com/angular/protractor/issues/480\n          return;\n        }\n        templateSelect.click();\n        templateSelect.all(by.css('option')).get(2).click();\n        expect(includeElem.getText()).toMatch(/Content of template2.html/);\n      });\n\n      it('should change to blank', function() {\n        if (browser.params.browser === 'firefox') {\n          // Firefox can't handle using selects\n          return;\n        }\n        templateSelect.click();\n        templateSelect.all(by.css('option')).get(0).click();\n        expect(includeElem.isPresent()).toBe(false);\n      });\n    </file>\n  </example>\n */\n\n\n/**\n * @ngdoc event\n * @name ngInclude#$includeContentRequested\n * @eventType emit on the scope ngInclude was declared in\n * @description\n * Emitted every time the ngInclude content is requested.\n *\n * @param {Object} angularEvent Synthetic event object.\n * @param {String} src URL of content to load.\n */\n\n\n/**\n * @ngdoc event\n * @name ngInclude#$includeContentLoaded\n * @eventType emit on the current ngInclude scope\n * @description\n * Emitted every time the ngInclude content is reloaded.\n *\n * @param {Object} angularEvent Synthetic event object.\n * @param {String} src URL of content to load.\n */\n\n\n/**\n * @ngdoc event\n * @name ngInclude#$includeContentError\n * @eventType emit on the scope ngInclude was declared in\n * @description\n * Emitted when a template HTTP request yields an erroneous response (status < 200 || status > 299)\n *\n * @param {Object} angularEvent Synthetic event object.\n * @param {String} src URL of content to load.\n */\nvar ngIncludeDirective = ['$templateRequest', '$anchorScroll', '$animate',\n                  function($templateRequest,   $anchorScroll,   $animate) {\n  return {\n    restrict: 'ECA',\n    priority: 400,\n    terminal: true,\n    transclude: 'element',\n    controller: angular.noop,\n    compile: function(element, attr) {\n      var srcExp = attr.ngInclude || attr.src,\n          onloadExp = attr.onload || '',\n          autoScrollExp = attr.autoscroll;\n\n      return function(scope, $element, $attr, ctrl, $transclude) {\n        var changeCounter = 0,\n            currentScope,\n            previousElement,\n            currentElement;\n\n        var cleanupLastIncludeContent = function() {\n          if (previousElement) {\n            previousElement.remove();\n            previousElement = null;\n          }\n          if (currentScope) {\n            currentScope.$destroy();\n            currentScope = null;\n          }\n          if (currentElement) {\n            $animate.leave(currentElement).done(function(response) {\n              if (response !== false) previousElement = null;\n            });\n            previousElement = currentElement;\n            currentElement = null;\n          }\n        };\n\n        scope.$watch(srcExp, function ngIncludeWatchAction(src) {\n          var afterAnimation = function(response) {\n            if (response !== false && isDefined(autoScrollExp) &&\n              (!autoScrollExp || scope.$eval(autoScrollExp))) {\n                $anchorScroll();\n            }\n          };\n          var thisChangeId = ++changeCounter;\n\n          if (src) {\n            //set the 2nd param to true to ignore the template request error so that the inner\n            //contents and scope can be cleaned up.\n            $templateRequest(src, true).then(function(response) {\n              if (scope.$$destroyed) return;\n\n              if (thisChangeId !== changeCounter) return;\n              var newScope = scope.$new();\n              ctrl.template = response;\n\n              // Note: This will also link all children of ng-include that were contained in the original\n              // html. If that content contains controllers, ... they could pollute/change the scope.\n              // However, using ng-include on an element with additional content does not make sense...\n              // Note: We can't remove them in the cloneAttchFn of $transclude as that\n              // function is called before linking the content, which would apply child\n              // directives to non existing elements.\n              var clone = $transclude(newScope, function(clone) {\n                cleanupLastIncludeContent();\n                $animate.enter(clone, null, $element).done(afterAnimation);\n              });\n\n              currentScope = newScope;\n              currentElement = clone;\n\n              currentScope.$emit('$includeContentLoaded', src);\n              scope.$eval(onloadExp);\n            }, function() {\n              if (scope.$$destroyed) return;\n\n              if (thisChangeId === changeCounter) {\n                cleanupLastIncludeContent();\n                scope.$emit('$includeContentError', src);\n              }\n            });\n            scope.$emit('$includeContentRequested', src);\n          } else {\n            cleanupLastIncludeContent();\n            ctrl.template = null;\n          }\n        });\n      };\n    }\n  };\n}];\n\n// This directive is called during the $transclude call of the first `ngInclude` directive.\n// It will replace and compile the content of the element with the loaded template.\n// We need this directive so that the element content is already filled when\n// the link function of another directive on the same element as ngInclude\n// is called.\nvar ngIncludeFillContentDirective = ['$compile',\n  function($compile) {\n    return {\n      restrict: 'ECA',\n      priority: -400,\n      require: 'ngInclude',\n      link: function(scope, $element, $attr, ctrl) {\n        if (toString.call($element[0]).match(/SVG/)) {\n          // WebKit: https://bugs.webkit.org/show_bug.cgi?id=135698 --- SVG elements do not\n          // support innerHTML, so detect this here and try to generate the contents\n          // specially.\n          $element.empty();\n          $compile(jqLiteBuildFragment(ctrl.template, window.document).childNodes)(scope,\n              function namespaceAdaptedClone(clone) {\n            $element.append(clone);\n          }, {futureParentElement: $element});\n          return;\n        }\n\n        $element.html(ctrl.template);\n        $compile($element.contents())(scope);\n      }\n    };\n  }];\n\n/**\n * @ngdoc directive\n * @name ngInit\n * @restrict AC\n * @priority 450\n * @element ANY\n *\n * @param {expression} ngInit {@link guide/expression Expression} to eval.\n *\n * @description\n * The `ngInit` directive allows you to evaluate an expression in the\n * current scope.\n *\n * <div class=\"alert alert-danger\">\n * This directive can be abused to add unnecessary amounts of logic into your templates.\n * There are only a few appropriate uses of `ngInit`:\n * <ul>\n *   <li>aliasing special properties of {@link ng.directive:ngRepeat `ngRepeat`},\n *     as seen in the demo below.</li>\n *   <li>initializing data during development, or for examples, as seen throughout these docs.</li>\n *   <li>injecting data via server side scripting.</li>\n * </ul>\n *\n * Besides these few cases, you should use {@link guide/component Components} or\n * {@link guide/controller Controllers} rather than `ngInit` to initialize values on a scope.\n * </div>\n *\n * <div class=\"alert alert-warning\">\n * **Note**: If you have assignment in `ngInit` along with a {@link ng.$filter `filter`}, make\n * sure you have parentheses to ensure correct operator precedence:\n * <pre class=\"prettyprint\">\n * `<div ng-init=\"test1 = ($index | toString)\"></div>`\n * </pre>\n * </div>\n *\n * @example\n   <example module=\"initExample\" name=\"ng-init\">\n     <file name=\"index.html\">\n   <script>\n     angular.module('initExample', [])\n       .controller('ExampleController', ['$scope', function($scope) {\n         $scope.list = [['a', 'b'], ['c', 'd']];\n       }]);\n   </script>\n   <div ng-controller=\"ExampleController\">\n     <div ng-repeat=\"innerList in list\" ng-init=\"outerIndex = $index\">\n       <div ng-repeat=\"value in innerList\" ng-init=\"innerIndex = $index\">\n          <span class=\"example-init\">list[ {{outerIndex}} ][ {{innerIndex}} ] = {{value}};</span>\n       </div>\n     </div>\n   </div>\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       it('should alias index positions', function() {\n         var elements = element.all(by.css('.example-init'));\n         expect(elements.get(0).getText()).toBe('list[ 0 ][ 0 ] = a;');\n         expect(elements.get(1).getText()).toBe('list[ 0 ][ 1 ] = b;');\n         expect(elements.get(2).getText()).toBe('list[ 1 ][ 0 ] = c;');\n         expect(elements.get(3).getText()).toBe('list[ 1 ][ 1 ] = d;');\n       });\n     </file>\n   </example>\n */\nvar ngInitDirective = ngDirective({\n  priority: 450,\n  compile: function() {\n    return {\n      pre: function(scope, element, attrs) {\n        scope.$eval(attrs.ngInit);\n      }\n    };\n  }\n});\n\n/**\n * @ngdoc directive\n * @name ngList\n * @restrict A\n * @priority 100\n *\n * @param {string=} ngList optional delimiter that should be used to split the value.\n *\n * @description\n * Text input that converts between a delimited string and an array of strings. The default\n * delimiter is a comma followed by a space - equivalent to `ng-list=\", \"`. You can specify a custom\n * delimiter as the value of the `ngList` attribute - for example, `ng-list=\" | \"`.\n *\n * The behaviour of the directive is affected by the use of the `ngTrim` attribute.\n * * If `ngTrim` is set to `\"false\"` then whitespace around both the separator and each\n *   list item is respected. This implies that the user of the directive is responsible for\n *   dealing with whitespace but also allows you to use whitespace as a delimiter, such as a\n *   tab or newline character.\n * * Otherwise whitespace around the delimiter is ignored when splitting (although it is respected\n *   when joining the list items back together) and whitespace around each list item is stripped\n *   before it is added to the model.\n *\n * @example\n * ### Validation\n *\n * <example name=\"ngList-directive\" module=\"listExample\">\n *   <file name=\"app.js\">\n *      angular.module('listExample', [])\n *        .controller('ExampleController', ['$scope', function($scope) {\n *          $scope.names = ['morpheus', 'neo', 'trinity'];\n *        }]);\n *   </file>\n *   <file name=\"index.html\">\n *    <form name=\"myForm\" ng-controller=\"ExampleController\">\n *      <label>List: <input name=\"namesInput\" ng-model=\"names\" ng-list required></label>\n *      <span role=\"alert\">\n *        <span class=\"error\" ng-show=\"myForm.namesInput.$error.required\">\n *        Required!</span>\n *      </span>\n *      <br>\n *      <tt>names = {{names}}</tt><br/>\n *      <tt>myForm.namesInput.$valid = {{myForm.namesInput.$valid}}</tt><br/>\n *      <tt>myForm.namesInput.$error = {{myForm.namesInput.$error}}</tt><br/>\n *      <tt>myForm.$valid = {{myForm.$valid}}</tt><br/>\n *      <tt>myForm.$error.required = {{!!myForm.$error.required}}</tt><br/>\n *     </form>\n *   </file>\n *   <file name=\"protractor.js\" type=\"protractor\">\n *     var listInput = element(by.model('names'));\n *     var names = element(by.exactBinding('names'));\n *     var valid = element(by.binding('myForm.namesInput.$valid'));\n *     var error = element(by.css('span.error'));\n *\n *     it('should initialize to model', function() {\n *       expect(names.getText()).toContain('[\"morpheus\",\"neo\",\"trinity\"]');\n *       expect(valid.getText()).toContain('true');\n *       expect(error.getCssValue('display')).toBe('none');\n *     });\n *\n *     it('should be invalid if empty', function() {\n *       listInput.clear();\n *       listInput.sendKeys('');\n *\n *       expect(names.getText()).toContain('');\n *       expect(valid.getText()).toContain('false');\n *       expect(error.getCssValue('display')).not.toBe('none');\n *     });\n *   </file>\n * </example>\n *\n * @example\n * ### Splitting on newline\n *\n * <example name=\"ngList-directive-newlines\">\n *   <file name=\"index.html\">\n *    <textarea ng-model=\"list\" ng-list=\"&#10;\" ng-trim=\"false\"></textarea>\n *    <pre>{{ list | json }}</pre>\n *   </file>\n *   <file name=\"protractor.js\" type=\"protractor\">\n *     it(\"should split the text by newlines\", function() {\n *       var listInput = element(by.model('list'));\n *       var output = element(by.binding('list | json'));\n *       listInput.sendKeys('abc\\ndef\\nghi');\n *       expect(output.getText()).toContain('[\\n  \"abc\",\\n  \"def\",\\n  \"ghi\"\\n]');\n *     });\n *   </file>\n * </example>\n *\n */\nvar ngListDirective = function() {\n  return {\n    restrict: 'A',\n    priority: 100,\n    require: 'ngModel',\n    link: function(scope, element, attr, ctrl) {\n      var ngList = attr.ngList || ', ';\n      var trimValues = attr.ngTrim !== 'false';\n      var separator = trimValues ? trim(ngList) : ngList;\n\n      var parse = function(viewValue) {\n        // If the viewValue is invalid (say required but empty) it will be `undefined`\n        if (isUndefined(viewValue)) return;\n\n        var list = [];\n\n        if (viewValue) {\n          forEach(viewValue.split(separator), function(value) {\n            if (value) list.push(trimValues ? trim(value) : value);\n          });\n        }\n\n        return list;\n      };\n\n      ctrl.$parsers.push(parse);\n      ctrl.$formatters.push(function(value) {\n        if (isArray(value)) {\n          return value.join(ngList);\n        }\n\n        return undefined;\n      });\n\n      // Override the standard $isEmpty because an empty array means the input is empty.\n      ctrl.$isEmpty = function(value) {\n        return !value || !value.length;\n      };\n    }\n  };\n};\n\n/* global VALID_CLASS: true,\n  INVALID_CLASS: true,\n  PRISTINE_CLASS: true,\n  DIRTY_CLASS: true,\n  UNTOUCHED_CLASS: true,\n  TOUCHED_CLASS: true,\n  PENDING_CLASS: true,\n  addSetValidityMethod: true,\n  setupValidity: true,\n  defaultModelOptions: false\n*/\n\n\nvar VALID_CLASS = 'ng-valid',\n    INVALID_CLASS = 'ng-invalid',\n    PRISTINE_CLASS = 'ng-pristine',\n    DIRTY_CLASS = 'ng-dirty',\n    UNTOUCHED_CLASS = 'ng-untouched',\n    TOUCHED_CLASS = 'ng-touched',\n    EMPTY_CLASS = 'ng-empty',\n    NOT_EMPTY_CLASS = 'ng-not-empty';\n\nvar ngModelMinErr = minErr('ngModel');\n\n/**\n * @ngdoc type\n * @name ngModel.NgModelController\n * @property {*} $viewValue The actual value from the control's view. For `input` elements, this is a\n * String. See {@link ngModel.NgModelController#$setViewValue} for information about when the $viewValue\n * is set.\n *\n * @property {*} $modelValue The value in the model that the control is bound to.\n *\n * @property {Array.<Function>} $parsers Array of functions to execute, as a pipeline, whenever\n *  the control updates the ngModelController with a new {@link ngModel.NgModelController#$viewValue\n    `$viewValue`} from the DOM, usually via user input.\n    See {@link ngModel.NgModelController#$setViewValue `$setViewValue()`} for a detailed lifecycle explanation.\n    Note that the `$parsers` are not called when the bound ngModel expression changes programmatically.\n\n  The functions are called in array order, each passing\n    its return value through to the next. The last return value is forwarded to the\n    {@link ngModel.NgModelController#$validators `$validators`} collection.\n\n  Parsers are used to sanitize / convert the {@link ngModel.NgModelController#$viewValue\n    `$viewValue`}.\n\n  Returning `undefined` from a parser means a parse error occurred. In that case,\n    no {@link ngModel.NgModelController#$validators `$validators`} will run and the `ngModel`\n    will be set to `undefined` unless {@link ngModelOptions `ngModelOptions.allowInvalid`}\n    is set to `true`. The parse error is stored in `ngModel.$error.parse`.\n\n  This simple example shows a parser that would convert text input value to lowercase:\n * ```js\n * function parse(value) {\n *   if (value) {\n *     return value.toLowerCase();\n *   }\n * }\n * ngModelController.$parsers.push(parse);\n * ```\n\n *\n * @property {Array.<Function>} $formatters Array of functions to execute, as a pipeline, whenever\n    the bound ngModel expression changes programmatically. The `$formatters` are not called when the\n    value of the control is changed by user interaction.\n\n  Formatters are used to format / convert the {@link ngModel.NgModelController#$modelValue\n    `$modelValue`} for display in the control.\n\n  The functions are called in reverse array order, each passing the value through to the\n    next. The last return value is used as the actual DOM value.\n\n  This simple example shows a formatter that would convert the model value to uppercase:\n\n * ```js\n * function format(value) {\n *   if (value) {\n *     return value.toUpperCase();\n *   }\n * }\n * ngModel.$formatters.push(format);\n * ```\n *\n * @property {Object.<string, function>} $validators A collection of validators that are applied\n *      whenever the model value changes. The key value within the object refers to the name of the\n *      validator while the function refers to the validation operation. The validation operation is\n *      provided with the model value as an argument and must return a true or false value depending\n *      on the response of that validation.\n *\n * ```js\n * ngModel.$validators.validCharacters = function(modelValue, viewValue) {\n *   var value = modelValue || viewValue;\n *   return /[0-9]+/.test(value) &&\n *          /[a-z]+/.test(value) &&\n *          /[A-Z]+/.test(value) &&\n *          /\\W+/.test(value);\n * };\n * ```\n *\n * @property {Object.<string, function>} $asyncValidators A collection of validations that are expected to\n *      perform an asynchronous validation (e.g. a HTTP request). The validation function that is provided\n *      is expected to return a promise when it is run during the model validation process. Once the promise\n *      is delivered then the validation status will be set to true when fulfilled and false when rejected.\n *      When the asynchronous validators are triggered, each of the validators will run in parallel and the model\n *      value will only be updated once all validators have been fulfilled. As long as an asynchronous validator\n *      is unfulfilled, its key will be added to the controllers `$pending` property. Also, all asynchronous validators\n *      will only run once all synchronous validators have passed.\n *\n * Please note that if $http is used then it is important that the server returns a success HTTP response code\n * in order to fulfill the validation and a status level of `4xx` in order to reject the validation.\n *\n * ```js\n * ngModel.$asyncValidators.uniqueUsername = function(modelValue, viewValue) {\n *   var value = modelValue || viewValue;\n *\n *   // Lookup user by username\n *   return $http.get('/api/users/' + value).\n *      then(function resolved() {\n *        //username exists, this means validation fails\n *        return $q.reject('exists');\n *      }, function rejected() {\n *        //username does not exist, therefore this validation passes\n *        return true;\n *      });\n * };\n * ```\n *\n * @property {Array.<Function>} $viewChangeListeners Array of functions to execute whenever\n *     a change to {@link ngModel.NgModelController#$viewValue `$viewValue`} has caused a change\n *     to {@link ngModel.NgModelController#$modelValue `$modelValue`}.\n *     It is called with no arguments, and its return value is ignored.\n *     This can be used in place of additional $watches against the model value.\n *\n * @property {Object} $error An object hash with all failing validator ids as keys.\n * @property {Object} $pending An object hash with all pending validator ids as keys.\n *\n * @property {boolean} $untouched True if control has not lost focus yet.\n * @property {boolean} $touched True if control has lost focus.\n * @property {boolean} $pristine True if user has not interacted with the control yet.\n * @property {boolean} $dirty True if user has already interacted with the control.\n * @property {boolean} $valid True if there is no error.\n * @property {boolean} $invalid True if at least one error on the control.\n * @property {string} $name The name attribute of the control.\n *\n * @description\n *\n * `NgModelController` provides API for the {@link ngModel `ngModel`} directive.\n * The controller contains services for data-binding, validation, CSS updates, and value formatting\n * and parsing. It purposefully does not contain any logic which deals with DOM rendering or\n * listening to DOM events.\n * Such DOM related logic should be provided by other directives which make use of\n * `NgModelController` for data-binding to control elements.\n * AngularJS provides this DOM logic for most {@link input `input`} elements.\n * At the end of this page you can find a {@link ngModel.NgModelController#custom-control-example\n * custom control example} that uses `ngModelController` to bind to `contenteditable` elements.\n *\n * @example\n * ### Custom Control Example\n * This example shows how to use `NgModelController` with a custom control to achieve\n * data-binding. Notice how different directives (`contenteditable`, `ng-model`, and `required`)\n * collaborate together to achieve the desired result.\n *\n * `contenteditable` is an HTML5 attribute, which tells the browser to let the element\n * contents be edited in place by the user.\n *\n * We are using the {@link ng.service:$sce $sce} service here and include the {@link ngSanitize $sanitize}\n * module to automatically remove \"bad\" content like inline event listener (e.g. `<span onclick=\"...\">`).\n * However, as we are using `$sce` the model can still decide to provide unsafe content if it marks\n * that content using the `$sce` service.\n *\n * <example name=\"NgModelController\" module=\"customControl\" deps=\"angular-sanitize.js\">\n    <file name=\"style.css\">\n      [contenteditable] {\n        border: 1px solid black;\n        background-color: white;\n        min-height: 20px;\n      }\n\n      .ng-invalid {\n        border: 1px solid red;\n      }\n\n    </file>\n    <file name=\"script.js\">\n      angular.module('customControl', ['ngSanitize']).\n        directive('contenteditable', ['$sce', function($sce) {\n          return {\n            restrict: 'A', // only activate on element attribute\n            require: '?ngModel', // get a hold of NgModelController\n            link: function(scope, element, attrs, ngModel) {\n              if (!ngModel) return; // do nothing if no ng-model\n\n              // Specify how UI should be updated\n              ngModel.$render = function() {\n                element.html($sce.getTrustedHtml(ngModel.$viewValue || ''));\n              };\n\n              // Listen for change events to enable binding\n              element.on('blur keyup change', function() {\n                scope.$evalAsync(read);\n              });\n              read(); // initialize\n\n              // Write data to the model\n              function read() {\n                var html = element.html();\n                // When we clear the content editable the browser leaves a <br> behind\n                // If strip-br attribute is provided then we strip this out\n                if (attrs.stripBr && html === '<br>') {\n                  html = '';\n                }\n                ngModel.$setViewValue(html);\n              }\n            }\n          };\n        }]);\n    </file>\n    <file name=\"index.html\">\n      <form name=\"myForm\">\n       <div contenteditable\n            name=\"myWidget\" ng-model=\"userContent\"\n            strip-br=\"true\"\n            required>Change me!</div>\n        <span ng-show=\"myForm.myWidget.$error.required\">Required!</span>\n       <hr>\n       <textarea ng-model=\"userContent\" aria-label=\"Dynamic textarea\"></textarea>\n      </form>\n    </file>\n    <file name=\"protractor.js\" type=\"protractor\">\n    it('should data-bind and become invalid', function() {\n      if (browser.params.browser === 'safari' || browser.params.browser === 'firefox') {\n        // SafariDriver can't handle contenteditable\n        // and Firefox driver can't clear contenteditables very well\n        return;\n      }\n      var contentEditable = element(by.css('[contenteditable]'));\n      var content = 'Change me!';\n\n      expect(contentEditable.getText()).toEqual(content);\n\n      contentEditable.clear();\n      contentEditable.sendKeys(protractor.Key.BACK_SPACE);\n      expect(contentEditable.getText()).toEqual('');\n      expect(contentEditable.getAttribute('class')).toMatch(/ng-invalid-required/);\n    });\n    </file>\n * </example>\n *\n *\n */\nNgModelController.$inject = ['$scope', '$exceptionHandler', '$attrs', '$element', '$parse', '$animate', '$timeout', '$q', '$interpolate'];\nfunction NgModelController($scope, $exceptionHandler, $attr, $element, $parse, $animate, $timeout, $q, $interpolate) {\n  this.$viewValue = Number.NaN;\n  this.$modelValue = Number.NaN;\n  this.$$rawModelValue = undefined; // stores the parsed modelValue / model set from scope regardless of validity.\n  this.$validators = {};\n  this.$asyncValidators = {};\n  this.$parsers = [];\n  this.$formatters = [];\n  this.$viewChangeListeners = [];\n  this.$untouched = true;\n  this.$touched = false;\n  this.$pristine = true;\n  this.$dirty = false;\n  this.$valid = true;\n  this.$invalid = false;\n  this.$error = {}; // keep invalid keys here\n  this.$$success = {}; // keep valid keys here\n  this.$pending = undefined; // keep pending keys here\n  this.$name = $interpolate($attr.name || '', false)($scope);\n  this.$$parentForm = nullFormCtrl;\n  this.$options = defaultModelOptions;\n  this.$$updateEvents = '';\n  // Attach the correct context to the event handler function for updateOn\n  this.$$updateEventHandler = this.$$updateEventHandler.bind(this);\n\n  this.$$parsedNgModel = $parse($attr.ngModel);\n  this.$$parsedNgModelAssign = this.$$parsedNgModel.assign;\n  this.$$ngModelGet = this.$$parsedNgModel;\n  this.$$ngModelSet = this.$$parsedNgModelAssign;\n  this.$$pendingDebounce = null;\n  this.$$parserValid = undefined;\n  this.$$parserName = 'parse';\n\n  this.$$currentValidationRunId = 0;\n\n  this.$$scope = $scope;\n  this.$$rootScope = $scope.$root;\n  this.$$attr = $attr;\n  this.$$element = $element;\n  this.$$animate = $animate;\n  this.$$timeout = $timeout;\n  this.$$parse = $parse;\n  this.$$q = $q;\n  this.$$exceptionHandler = $exceptionHandler;\n\n  setupValidity(this);\n  setupModelWatcher(this);\n}\n\nNgModelController.prototype = {\n  $$initGetterSetters: function() {\n    if (this.$options.getOption('getterSetter')) {\n      var invokeModelGetter = this.$$parse(this.$$attr.ngModel + '()'),\n          invokeModelSetter = this.$$parse(this.$$attr.ngModel + '($$$p)');\n\n      this.$$ngModelGet = function($scope) {\n        var modelValue = this.$$parsedNgModel($scope);\n        if (isFunction(modelValue)) {\n          modelValue = invokeModelGetter($scope);\n        }\n        return modelValue;\n      };\n      this.$$ngModelSet = function($scope, newValue) {\n        if (isFunction(this.$$parsedNgModel($scope))) {\n          invokeModelSetter($scope, {$$$p: newValue});\n        } else {\n          this.$$parsedNgModelAssign($scope, newValue);\n        }\n      };\n    } else if (!this.$$parsedNgModel.assign) {\n      throw ngModelMinErr('nonassign', 'Expression \\'{0}\\' is non-assignable. Element: {1}',\n          this.$$attr.ngModel, startingTag(this.$$element));\n    }\n  },\n\n\n  /**\n   * @ngdoc method\n   * @name ngModel.NgModelController#$render\n   *\n   * @description\n   * Called when the view needs to be updated. It is expected that the user of the ng-model\n   * directive will implement this method.\n   *\n   * The `$render()` method is invoked in the following situations:\n   *\n   * * `$rollbackViewValue()` is called.  If we are rolling back the view value to the last\n   *   committed value then `$render()` is called to update the input control.\n   * * The value referenced by `ng-model` is changed programmatically and both the `$modelValue` and\n   *   the `$viewValue` are different from last time.\n   *\n   * Since `ng-model` does not do a deep watch, `$render()` is only invoked if the values of\n   * `$modelValue` and `$viewValue` are actually different from their previous values. If `$modelValue`\n   * or `$viewValue` are objects (rather than a string or number) then `$render()` will not be\n   * invoked if you only change a property on the objects.\n   */\n  $render: noop,\n\n  /**\n   * @ngdoc method\n   * @name ngModel.NgModelController#$isEmpty\n   *\n   * @description\n   * This is called when we need to determine if the value of an input is empty.\n   *\n   * For instance, the required directive does this to work out if the input has data or not.\n   *\n   * The default `$isEmpty` function checks whether the value is `undefined`, `''`, `null` or `NaN`.\n   *\n   * You can override this for input directives whose concept of being empty is different from the\n   * default. The `checkboxInputType` directive does this because in its case a value of `false`\n   * implies empty.\n   *\n   * @param {*} value The value of the input to check for emptiness.\n   * @returns {boolean} True if `value` is \"empty\".\n   */\n  $isEmpty: function(value) {\n    // eslint-disable-next-line no-self-compare\n    return isUndefined(value) || value === '' || value === null || value !== value;\n  },\n\n  $$updateEmptyClasses: function(value) {\n    if (this.$isEmpty(value)) {\n      this.$$animate.removeClass(this.$$element, NOT_EMPTY_CLASS);\n      this.$$animate.addClass(this.$$element, EMPTY_CLASS);\n    } else {\n      this.$$animate.removeClass(this.$$element, EMPTY_CLASS);\n      this.$$animate.addClass(this.$$element, NOT_EMPTY_CLASS);\n    }\n  },\n\n  /**\n   * @ngdoc method\n   * @name ngModel.NgModelController#$setPristine\n   *\n   * @description\n   * Sets the control to its pristine state.\n   *\n   * This method can be called to remove the `ng-dirty` class and set the control to its pristine\n   * state (`ng-pristine` class). A model is considered to be pristine when the control\n   * has not been changed from when first compiled.\n   */\n  $setPristine: function() {\n    this.$dirty = false;\n    this.$pristine = true;\n    this.$$animate.removeClass(this.$$element, DIRTY_CLASS);\n    this.$$animate.addClass(this.$$element, PRISTINE_CLASS);\n  },\n\n  /**\n   * @ngdoc method\n   * @name ngModel.NgModelController#$setDirty\n   *\n   * @description\n   * Sets the control to its dirty state.\n   *\n   * This method can be called to remove the `ng-pristine` class and set the control to its dirty\n   * state (`ng-dirty` class). A model is considered to be dirty when the control has been changed\n   * from when first compiled.\n   */\n  $setDirty: function() {\n    this.$dirty = true;\n    this.$pristine = false;\n    this.$$animate.removeClass(this.$$element, PRISTINE_CLASS);\n    this.$$animate.addClass(this.$$element, DIRTY_CLASS);\n    this.$$parentForm.$setDirty();\n  },\n\n  /**\n   * @ngdoc method\n   * @name ngModel.NgModelController#$setUntouched\n   *\n   * @description\n   * Sets the control to its untouched state.\n   *\n   * This method can be called to remove the `ng-touched` class and set the control to its\n   * untouched state (`ng-untouched` class). Upon compilation, a model is set as untouched\n   * by default, however this function can be used to restore that state if the model has\n   * already been touched by the user.\n   */\n  $setUntouched: function() {\n    this.$touched = false;\n    this.$untouched = true;\n    this.$$animate.setClass(this.$$element, UNTOUCHED_CLASS, TOUCHED_CLASS);\n  },\n\n  /**\n   * @ngdoc method\n   * @name ngModel.NgModelController#$setTouched\n   *\n   * @description\n   * Sets the control to its touched state.\n   *\n   * This method can be called to remove the `ng-untouched` class and set the control to its\n   * touched state (`ng-touched` class). A model is considered to be touched when the user has\n   * first focused the control element and then shifted focus away from the control (blur event).\n   */\n  $setTouched: function() {\n    this.$touched = true;\n    this.$untouched = false;\n    this.$$animate.setClass(this.$$element, TOUCHED_CLASS, UNTOUCHED_CLASS);\n  },\n\n  /**\n   * @ngdoc method\n   * @name ngModel.NgModelController#$rollbackViewValue\n   *\n   * @description\n   * Cancel an update and reset the input element's value to prevent an update to the `$modelValue`,\n   * which may be caused by a pending debounced event or because the input is waiting for some\n   * future event.\n   *\n   * If you have an input that uses `ng-model-options` to set up debounced updates or updates that\n   * depend on special events such as `blur`, there can be a period when the `$viewValue` is out of\n   * sync with the ngModel's `$modelValue`.\n   *\n   * In this case, you can use `$rollbackViewValue()` to manually cancel the debounced / future update\n   * and reset the input to the last committed view value.\n   *\n   * It is also possible that you run into difficulties if you try to update the ngModel's `$modelValue`\n   * programmatically before these debounced/future events have resolved/occurred, because AngularJS's\n   * dirty checking mechanism is not able to tell whether the model has actually changed or not.\n   *\n   * The `$rollbackViewValue()` method should be called before programmatically changing the model of an\n   * input which may have such events pending. This is important in order to make sure that the\n   * input field will be updated with the new model value and any pending operations are cancelled.\n   *\n   * @example\n   * <example name=\"ng-model-cancel-update\" module=\"cancel-update-example\">\n   *   <file name=\"app.js\">\n   *     angular.module('cancel-update-example', [])\n   *\n   *     .controller('CancelUpdateController', ['$scope', function($scope) {\n   *       $scope.model = {value1: '', value2: ''};\n   *\n   *       $scope.setEmpty = function(e, value, rollback) {\n   *         if (e.keyCode === 27) {\n   *           e.preventDefault();\n   *           if (rollback) {\n   *             $scope.myForm[value].$rollbackViewValue();\n   *           }\n   *           $scope.model[value] = '';\n   *         }\n   *       };\n   *     }]);\n   *   </file>\n   *   <file name=\"index.html\">\n   *     <div ng-controller=\"CancelUpdateController\">\n   *       <p>Both of these inputs are only updated if they are blurred. Hitting escape should\n   *       empty them. Follow these steps and observe the difference:</p>\n   *       <ol>\n   *         <li>Type something in the input. You will see that the model is not yet updated</li>\n   *         <li>Press the Escape key.\n   *           <ol>\n   *             <li> In the first example, nothing happens, because the model is already '', and no\n   *             update is detected. If you blur the input, the model will be set to the current view.\n   *             </li>\n   *             <li> In the second example, the pending update is cancelled, and the input is set back\n   *             to the last committed view value (''). Blurring the input does nothing.\n   *             </li>\n   *           </ol>\n   *         </li>\n   *       </ol>\n   *\n   *       <form name=\"myForm\" ng-model-options=\"{ updateOn: 'blur' }\">\n   *         <div>\n   *           <p id=\"inputDescription1\">Without $rollbackViewValue():</p>\n   *           <input name=\"value1\" aria-describedby=\"inputDescription1\" ng-model=\"model.value1\"\n   *                  ng-keydown=\"setEmpty($event, 'value1')\">\n   *           value1: \"{{ model.value1 }}\"\n   *         </div>\n   *\n   *         <div>\n   *           <p id=\"inputDescription2\">With $rollbackViewValue():</p>\n   *           <input name=\"value2\" aria-describedby=\"inputDescription2\" ng-model=\"model.value2\"\n   *                  ng-keydown=\"setEmpty($event, 'value2', true)\">\n   *           value2: \"{{ model.value2 }}\"\n   *         </div>\n   *       </form>\n   *     </div>\n   *   </file>\n       <file name=\"style.css\">\n          div {\n            display: table-cell;\n          }\n          div:nth-child(1) {\n            padding-right: 30px;\n          }\n\n        </file>\n   * </example>\n   */\n  $rollbackViewValue: function() {\n    this.$$timeout.cancel(this.$$pendingDebounce);\n    this.$viewValue = this.$$lastCommittedViewValue;\n    this.$render();\n  },\n\n  /**\n   * @ngdoc method\n   * @name ngModel.NgModelController#$validate\n   *\n   * @description\n   * Runs each of the registered validators (first synchronous validators and then\n   * asynchronous validators).\n   * If the validity changes to invalid, the model will be set to `undefined`,\n   * unless {@link ngModelOptions `ngModelOptions.allowInvalid`} is `true`.\n   * If the validity changes to valid, it will set the model to the last available valid\n   * `$modelValue`, i.e. either the last parsed value or the last value set from the scope.\n   */\n  $validate: function() {\n\n    // ignore $validate before model is initialized\n    if (isNumberNaN(this.$modelValue)) {\n      return;\n    }\n\n    var viewValue = this.$$lastCommittedViewValue;\n    // Note: we use the $$rawModelValue as $modelValue might have been\n    // set to undefined during a view -> model update that found validation\n    // errors. We can't parse the view here, since that could change\n    // the model although neither viewValue nor the model on the scope changed\n    var modelValue = this.$$rawModelValue;\n\n    var prevValid = this.$valid;\n    var prevModelValue = this.$modelValue;\n\n    var allowInvalid = this.$options.getOption('allowInvalid');\n\n    var that = this;\n    this.$$runValidators(modelValue, viewValue, function(allValid) {\n      // If there was no change in validity, don't update the model\n      // This prevents changing an invalid modelValue to undefined\n      if (!allowInvalid && prevValid !== allValid) {\n        // Note: Don't check this.$valid here, as we could have\n        // external validators (e.g. calculated on the server),\n        // that just call $setValidity and need the model value\n        // to calculate their validity.\n        that.$modelValue = allValid ? modelValue : undefined;\n\n        if (that.$modelValue !== prevModelValue) {\n          that.$$writeModelToScope();\n        }\n      }\n    });\n  },\n\n  $$runValidators: function(modelValue, viewValue, doneCallback) {\n    this.$$currentValidationRunId++;\n    var localValidationRunId = this.$$currentValidationRunId;\n    var that = this;\n\n    // check parser error\n    if (!processParseErrors()) {\n      validationDone(false);\n      return;\n    }\n    if (!processSyncValidators()) {\n      validationDone(false);\n      return;\n    }\n    processAsyncValidators();\n\n    function processParseErrors() {\n      var errorKey = that.$$parserName;\n\n      if (isUndefined(that.$$parserValid)) {\n        setValidity(errorKey, null);\n      } else {\n        if (!that.$$parserValid) {\n          forEach(that.$validators, function(v, name) {\n            setValidity(name, null);\n          });\n          forEach(that.$asyncValidators, function(v, name) {\n            setValidity(name, null);\n          });\n        }\n\n        // Set the parse error last, to prevent unsetting it, should a $validators key == parserName\n        setValidity(errorKey, that.$$parserValid);\n        return that.$$parserValid;\n      }\n      return true;\n    }\n\n    function processSyncValidators() {\n      var syncValidatorsValid = true;\n      forEach(that.$validators, function(validator, name) {\n        var result = Boolean(validator(modelValue, viewValue));\n        syncValidatorsValid = syncValidatorsValid && result;\n        setValidity(name, result);\n      });\n      if (!syncValidatorsValid) {\n        forEach(that.$asyncValidators, function(v, name) {\n          setValidity(name, null);\n        });\n        return false;\n      }\n      return true;\n    }\n\n    function processAsyncValidators() {\n      var validatorPromises = [];\n      var allValid = true;\n      forEach(that.$asyncValidators, function(validator, name) {\n        var promise = validator(modelValue, viewValue);\n        if (!isPromiseLike(promise)) {\n          throw ngModelMinErr('nopromise',\n            'Expected asynchronous validator to return a promise but got \\'{0}\\' instead.', promise);\n        }\n        setValidity(name, undefined);\n        validatorPromises.push(promise.then(function() {\n          setValidity(name, true);\n        }, function() {\n          allValid = false;\n          setValidity(name, false);\n        }));\n      });\n      if (!validatorPromises.length) {\n        validationDone(true);\n      } else {\n        that.$$q.all(validatorPromises).then(function() {\n          validationDone(allValid);\n        }, noop);\n      }\n    }\n\n    function setValidity(name, isValid) {\n      if (localValidationRunId === that.$$currentValidationRunId) {\n        that.$setValidity(name, isValid);\n      }\n    }\n\n    function validationDone(allValid) {\n      if (localValidationRunId === that.$$currentValidationRunId) {\n\n        doneCallback(allValid);\n      }\n    }\n  },\n\n  /**\n   * @ngdoc method\n   * @name ngModel.NgModelController#$commitViewValue\n   *\n   * @description\n   * Commit a pending update to the `$modelValue`.\n   *\n   * Updates may be pending by a debounced event or because the input is waiting for a some future\n   * event defined in `ng-model-options`. this method is rarely needed as `NgModelController`\n   * usually handles calling this in response to input events.\n   */\n  $commitViewValue: function() {\n    var viewValue = this.$viewValue;\n\n    this.$$timeout.cancel(this.$$pendingDebounce);\n\n    // If the view value has not changed then we should just exit, except in the case where there is\n    // a native validator on the element. In this case the validation state may have changed even though\n    // the viewValue has stayed empty.\n    if (this.$$lastCommittedViewValue === viewValue && (viewValue !== '' || !this.$$hasNativeValidators)) {\n      return;\n    }\n    this.$$updateEmptyClasses(viewValue);\n    this.$$lastCommittedViewValue = viewValue;\n\n    // change to dirty\n    if (this.$pristine) {\n      this.$setDirty();\n    }\n    this.$$parseAndValidate();\n  },\n\n  $$parseAndValidate: function() {\n    var viewValue = this.$$lastCommittedViewValue;\n    var modelValue = viewValue;\n    var that = this;\n\n    this.$$parserValid = isUndefined(modelValue) ? undefined : true;\n\n    // Reset any previous parse error\n    this.$setValidity(this.$$parserName, null);\n    this.$$parserName = 'parse';\n\n    if (this.$$parserValid) {\n      for (var i = 0; i < this.$parsers.length; i++) {\n        modelValue = this.$parsers[i](modelValue);\n        if (isUndefined(modelValue)) {\n          this.$$parserValid = false;\n          break;\n        }\n      }\n    }\n    if (isNumberNaN(this.$modelValue)) {\n      // this.$modelValue has not been touched yet...\n      this.$modelValue = this.$$ngModelGet(this.$$scope);\n    }\n    var prevModelValue = this.$modelValue;\n    var allowInvalid = this.$options.getOption('allowInvalid');\n    this.$$rawModelValue = modelValue;\n\n    if (allowInvalid) {\n      this.$modelValue = modelValue;\n      writeToModelIfNeeded();\n    }\n\n    // Pass the $$lastCommittedViewValue here, because the cached viewValue might be out of date.\n    // This can happen if e.g. $setViewValue is called from inside a parser\n    this.$$runValidators(modelValue, this.$$lastCommittedViewValue, function(allValid) {\n      if (!allowInvalid) {\n        // Note: Don't check this.$valid here, as we could have\n        // external validators (e.g. calculated on the server),\n        // that just call $setValidity and need the model value\n        // to calculate their validity.\n        that.$modelValue = allValid ? modelValue : undefined;\n        writeToModelIfNeeded();\n      }\n    });\n\n    function writeToModelIfNeeded() {\n      if (that.$modelValue !== prevModelValue) {\n        that.$$writeModelToScope();\n      }\n    }\n  },\n\n  $$writeModelToScope: function() {\n    this.$$ngModelSet(this.$$scope, this.$modelValue);\n    forEach(this.$viewChangeListeners, function(listener) {\n      try {\n        listener();\n      } catch (e) {\n        // eslint-disable-next-line no-invalid-this\n        this.$$exceptionHandler(e);\n      }\n    }, this);\n  },\n\n  /**\n   * @ngdoc method\n   * @name ngModel.NgModelController#$setViewValue\n   *\n   * @description\n   * Update the view value.\n   *\n   * This method should be called when a control wants to change the view value; typically,\n   * this is done from within a DOM event handler. For example, the {@link ng.directive:input input}\n   * directive calls it when the value of the input changes and {@link ng.directive:select select}\n   * calls it when an option is selected.\n   *\n   * When `$setViewValue` is called, the new `value` will be staged for committing through the `$parsers`\n   * and `$validators` pipelines. If there are no special {@link ngModelOptions} specified then the staged\n   * value is sent directly for processing through the `$parsers` pipeline. After this, the `$validators` and\n   * `$asyncValidators` are called and the value is applied to `$modelValue`.\n   * Finally, the value is set to the **expression** specified in the `ng-model` attribute and\n   * all the registered change listeners, in the `$viewChangeListeners` list are called.\n   *\n   * In case the {@link ng.directive:ngModelOptions ngModelOptions} directive is used with `updateOn`\n   * and the `default` trigger is not listed, all those actions will remain pending until one of the\n   * `updateOn` events is triggered on the DOM element.\n   * All these actions will be debounced if the {@link ng.directive:ngModelOptions ngModelOptions}\n   * directive is used with a custom debounce for this particular event.\n   * Note that a `$digest` is only triggered once the `updateOn` events are fired, or if `debounce`\n   * is specified, once the timer runs out.\n   *\n   * When used with standard inputs, the view value will always be a string (which is in some cases\n   * parsed into another type, such as a `Date` object for `input[date]`.)\n   * However, custom controls might also pass objects to this method. In this case, we should make\n   * a copy of the object before passing it to `$setViewValue`. This is because `ngModel` does not\n   * perform a deep watch of objects, it only looks for a change of identity. If you only change\n   * the property of the object then ngModel will not realize that the object has changed and\n   * will not invoke the `$parsers` and `$validators` pipelines. For this reason, you should\n   * not change properties of the copy once it has been passed to `$setViewValue`.\n   * Otherwise you may cause the model value on the scope to change incorrectly.\n   *\n   * <div class=\"alert alert-info\">\n   * In any case, the value passed to the method should always reflect the current value\n   * of the control. For example, if you are calling `$setViewValue` for an input element,\n   * you should pass the input DOM value. Otherwise, the control and the scope model become\n   * out of sync. It's also important to note that `$setViewValue` does not call `$render` or change\n   * the control's DOM value in any way. If we want to change the control's DOM value\n   * programmatically, we should update the `ngModel` scope expression. Its new value will be\n   * picked up by the model controller, which will run it through the `$formatters`, `$render` it\n   * to update the DOM, and finally call `$validate` on it.\n   * </div>\n   *\n   * @param {*} value value from the view.\n   * @param {string} trigger Event that triggered the update.\n   */\n  $setViewValue: function(value, trigger) {\n    this.$viewValue = value;\n    if (this.$options.getOption('updateOnDefault')) {\n      this.$$debounceViewValueCommit(trigger);\n    }\n  },\n\n  $$debounceViewValueCommit: function(trigger) {\n    var debounceDelay = this.$options.getOption('debounce');\n\n    if (isNumber(debounceDelay[trigger])) {\n      debounceDelay = debounceDelay[trigger];\n    } else if (isNumber(debounceDelay['default']) &&\n      this.$options.getOption('updateOn').indexOf(trigger) === -1\n    ) {\n      debounceDelay = debounceDelay['default'];\n    } else if (isNumber(debounceDelay['*'])) {\n      debounceDelay = debounceDelay['*'];\n    }\n\n    this.$$timeout.cancel(this.$$pendingDebounce);\n    var that = this;\n    if (debounceDelay > 0) { // this fails if debounceDelay is an object\n      this.$$pendingDebounce = this.$$timeout(function() {\n        that.$commitViewValue();\n      }, debounceDelay);\n    } else if (this.$$rootScope.$$phase) {\n      this.$commitViewValue();\n    } else {\n      this.$$scope.$apply(function() {\n        that.$commitViewValue();\n      });\n    }\n  },\n\n  /**\n   * @ngdoc method\n   *\n   * @name ngModel.NgModelController#$overrideModelOptions\n   *\n   * @description\n   *\n   * Override the current model options settings programmatically.\n   *\n   * The previous `ModelOptions` value will not be modified. Instead, a\n   * new `ModelOptions` object will inherit from the previous one overriding\n   * or inheriting settings that are defined in the given parameter.\n   *\n   * See {@link ngModelOptions} for information about what options can be specified\n   * and how model option inheritance works.\n   *\n   * <div class=\"alert alert-warning\">\n   * **Note:** this function only affects the options set on the `ngModelController`,\n   * and not the options on the {@link ngModelOptions} directive from which they might have been\n   * obtained initially.\n   * </div>\n   *\n   * <div class=\"alert alert-danger\">\n   * **Note:** it is not possible to override the `getterSetter` option.\n   * </div>\n   *\n   * @param {Object} options a hash of settings to override the previous options\n   *\n   */\n  $overrideModelOptions: function(options) {\n    this.$options = this.$options.createChild(options);\n    this.$$setUpdateOnEvents();\n  },\n\n  /**\n   * @ngdoc method\n   *\n   * @name  ngModel.NgModelController#$processModelValue\n\n   * @description\n   *\n   * Runs the model -> view pipeline on the current\n   * {@link ngModel.NgModelController#$modelValue $modelValue}.\n   *\n   * The following actions are performed by this method:\n   *\n   * - the `$modelValue` is run through the {@link ngModel.NgModelController#$formatters $formatters}\n   * and the result is set to the {@link ngModel.NgModelController#$viewValue $viewValue}\n   * - the `ng-empty` or `ng-not-empty` class is set on the element\n   * - if the `$viewValue` has changed:\n   *   - {@link ngModel.NgModelController#$render $render} is called on the control\n   *   - the {@link ngModel.NgModelController#$validators $validators} are run and\n   *   the validation status is set.\n   *\n   * This method is called by ngModel internally when the bound scope value changes.\n   * Application developers usually do not have to call this function themselves.\n   *\n   * This function can be used when the `$viewValue` or the rendered DOM value are not correctly\n   * formatted and the `$modelValue` must be run through the `$formatters` again.\n   *\n   * @example\n   * Consider a text input with an autocomplete list (for fruit), where the items are\n   * objects with a name and an id.\n   * A user enters `ap` and then selects `Apricot` from the list.\n   * Based on this, the autocomplete widget will call `$setViewValue({name: 'Apricot', id: 443})`,\n   * but the rendered value will still be `ap`.\n   * The widget can then call `ctrl.$processModelValue()` to run the model -> view\n   * pipeline again, which formats the object to the string `Apricot`,\n   * then updates the `$viewValue`, and finally renders it in the DOM.\n   *\n   * <example module=\"inputExample\" name=\"ng-model-process\">\n     <file name=\"index.html\">\n      <div ng-controller=\"inputController\" style=\"display: flex;\">\n        <div style=\"margin-right: 30px;\">\n          Search Fruit:\n          <basic-autocomplete items=\"items\" on-select=\"selectedFruit = item\"></basic-autocomplete>\n        </div>\n        <div>\n          Model:<br>\n          <pre>{{selectedFruit | json}}</pre>\n        </div>\n      </div>\n     </file>\n     <file name=\"app.js\">\n      angular.module('inputExample', [])\n        .controller('inputController', function($scope) {\n          $scope.items = [\n            {name: 'Apricot', id: 443},\n            {name: 'Clementine', id: 972},\n            {name: 'Durian', id: 169},\n            {name: 'Jackfruit', id: 982},\n            {name: 'Strawberry', id: 863}\n          ];\n        })\n        .component('basicAutocomplete', {\n          bindings: {\n            items: '<',\n            onSelect: '&'\n          },\n          templateUrl: 'autocomplete.html',\n          controller: function($element, $scope) {\n            var that = this;\n            var ngModel;\n\n            that.$postLink = function() {\n              ngModel = $element.find('input').controller('ngModel');\n\n              ngModel.$formatters.push(function(value) {\n                return (value && value.name) || value;\n              });\n\n              ngModel.$parsers.push(function(value) {\n                var match = value;\n                for (var i = 0; i < that.items.length; i++) {\n                  if (that.items[i].name === value) {\n                    match = that.items[i];\n                    break;\n                  }\n                }\n\n                return match;\n              });\n            };\n\n            that.selectItem = function(item) {\n              ngModel.$setViewValue(item);\n              ngModel.$processModelValue();\n              that.onSelect({item: item});\n            };\n          }\n        });\n     </file>\n     <file name=\"autocomplete.html\">\n       <div>\n         <input type=\"search\" ng-model=\"$ctrl.searchTerm\" />\n         <ul>\n           <li ng-repeat=\"item in $ctrl.items | filter:$ctrl.searchTerm\">\n             <button ng-click=\"$ctrl.selectItem(item)\">{{ item.name }}</button>\n           </li>\n         </ul>\n       </div>\n     </file>\n   * </example>\n   *\n   */\n  $processModelValue: function() {\n    var viewValue = this.$$format();\n\n    if (this.$viewValue !== viewValue) {\n      this.$$updateEmptyClasses(viewValue);\n      this.$viewValue = this.$$lastCommittedViewValue = viewValue;\n      this.$render();\n      // It is possible that model and view value have been updated during render\n      this.$$runValidators(this.$modelValue, this.$viewValue, noop);\n    }\n  },\n\n  /**\n   * This method is called internally to run the $formatters on the $modelValue\n   */\n  $$format: function() {\n    var formatters = this.$formatters,\n        idx = formatters.length;\n\n    var viewValue = this.$modelValue;\n    while (idx--) {\n      viewValue = formatters[idx](viewValue);\n    }\n\n    return viewValue;\n  },\n\n  /**\n   * This method is called internally when the bound scope value changes.\n   */\n  $$setModelValue: function(modelValue) {\n    this.$modelValue = this.$$rawModelValue = modelValue;\n    this.$$parserValid = undefined;\n    this.$processModelValue();\n  },\n\n  $$setUpdateOnEvents: function() {\n    if (this.$$updateEvents) {\n      this.$$element.off(this.$$updateEvents, this.$$updateEventHandler);\n    }\n\n    this.$$updateEvents = this.$options.getOption('updateOn');\n    if (this.$$updateEvents) {\n      this.$$element.on(this.$$updateEvents, this.$$updateEventHandler);\n    }\n  },\n\n  $$updateEventHandler: function(ev) {\n    this.$$debounceViewValueCommit(ev && ev.type);\n  }\n};\n\nfunction setupModelWatcher(ctrl) {\n  // model -> value\n  // Note: we cannot use a normal scope.$watch as we want to detect the following:\n  // 1. scope value is 'a'\n  // 2. user enters 'b'\n  // 3. ng-change kicks in and reverts scope value to 'a'\n  //    -> scope value did not change since the last digest as\n  //       ng-change executes in apply phase\n  // 4. view should be changed back to 'a'\n  ctrl.$$scope.$watch(function ngModelWatch(scope) {\n    var modelValue = ctrl.$$ngModelGet(scope);\n\n    // if scope model value and ngModel value are out of sync\n    // This cannot be moved to the action function, because it would not catch the\n    // case where the model is changed in the ngChange function or the model setter\n    if (modelValue !== ctrl.$modelValue &&\n      // checks for NaN is needed to allow setting the model to NaN when there's an asyncValidator\n      // eslint-disable-next-line no-self-compare\n      (ctrl.$modelValue === ctrl.$modelValue || modelValue === modelValue)\n    ) {\n      ctrl.$$setModelValue(modelValue);\n    }\n\n    return modelValue;\n  });\n}\n\n/**\n * @ngdoc method\n * @name ngModel.NgModelController#$setValidity\n *\n * @description\n * Change the validity state, and notify the form.\n *\n * This method can be called within $parsers/$formatters or a custom validation implementation.\n * However, in most cases it should be sufficient to use the `ngModel.$validators` and\n * `ngModel.$asyncValidators` collections which will call `$setValidity` automatically.\n *\n * @param {string} validationErrorKey Name of the validator. The `validationErrorKey` will be assigned\n *        to either `$error[validationErrorKey]` or `$pending[validationErrorKey]`\n *        (for unfulfilled `$asyncValidators`), so that it is available for data-binding.\n *        The `validationErrorKey` should be in camelCase and will get converted into dash-case\n *        for class name. Example: `myError` will result in `ng-valid-my-error` and `ng-invalid-my-error`\n *        classes and can be bound to as `{{ someForm.someControl.$error.myError }}`.\n * @param {boolean} isValid Whether the current state is valid (true), invalid (false), pending (undefined),\n *                          or skipped (null). Pending is used for unfulfilled `$asyncValidators`.\n *                          Skipped is used by AngularJS when validators do not run because of parse errors and\n *                          when `$asyncValidators` do not run because any of the `$validators` failed.\n */\naddSetValidityMethod({\n  clazz: NgModelController,\n  set: function(object, property) {\n    object[property] = true;\n  },\n  unset: function(object, property) {\n    delete object[property];\n  }\n});\n\n\n/**\n * @ngdoc directive\n * @name ngModel\n * @restrict A\n * @priority 1\n * @param {expression} ngModel assignable {@link guide/expression Expression} to bind to.\n *\n * @description\n * The `ngModel` directive binds an `input`,`select`, `textarea` (or custom form control) to a\n * property on the scope using {@link ngModel.NgModelController NgModelController},\n * which is created and exposed by this directive.\n *\n * `ngModel` is responsible for:\n *\n * - Binding the view into the model, which other directives such as `input`, `textarea` or `select`\n *   require.\n * - Providing validation behavior (i.e. required, number, email, url).\n * - Keeping the state of the control (valid/invalid, dirty/pristine, touched/untouched, validation errors).\n * - Setting related css classes on the element (`ng-valid`, `ng-invalid`, `ng-dirty`, `ng-pristine`, `ng-touched`,\n *   `ng-untouched`, `ng-empty`, `ng-not-empty`) including animations.\n * - Registering the control with its parent {@link ng.directive:form form}.\n *\n * Note: `ngModel` will try to bind to the property given by evaluating the expression on the\n * current scope. If the property doesn't already exist on this scope, it will be created\n * implicitly and added to the scope.\n *\n * For best practices on using `ngModel`, see:\n *\n *  - [Understanding Scopes](https://github.com/angular/angular.js/wiki/Understanding-Scopes)\n *\n * For basic examples, how to use `ngModel`, see:\n *\n *  - {@link ng.directive:input input}\n *    - {@link input[text] text}\n *    - {@link input[checkbox] checkbox}\n *    - {@link input[radio] radio}\n *    - {@link input[number] number}\n *    - {@link input[email] email}\n *    - {@link input[url] url}\n *    - {@link input[date] date}\n *    - {@link input[datetime-local] datetime-local}\n *    - {@link input[time] time}\n *    - {@link input[month] month}\n *    - {@link input[week] week}\n *  - {@link ng.directive:select select}\n *  - {@link ng.directive:textarea textarea}\n *\n * ## Complex Models (objects or collections)\n *\n * By default, `ngModel` watches the model by reference, not value. This is important to know when\n * binding inputs to models that are objects (e.g. `Date`) or collections (e.g. arrays). If only properties of the\n * object or collection change, `ngModel` will not be notified and so the input will not be  re-rendered.\n *\n * The model must be assigned an entirely new object or collection before a re-rendering will occur.\n *\n * Some directives have options that will cause them to use a custom `$watchCollection` on the model expression\n * - for example, `ngOptions` will do so when a `track by` clause is included in the comprehension expression or\n * if the select is given the `multiple` attribute.\n *\n * The `$watchCollection()` method only does a shallow comparison, meaning that changing properties deeper than the\n * first level of the object (or only changing the properties of an item in the collection if it's an array) will still\n * not trigger a re-rendering of the model.\n *\n * ## CSS classes\n * The following CSS classes are added and removed on the associated input/select/textarea element\n * depending on the validity of the model.\n *\n *  - `ng-valid`: the model is valid\n *  - `ng-invalid`: the model is invalid\n *  - `ng-valid-[key]`: for each valid key added by `$setValidity`\n *  - `ng-invalid-[key]`: for each invalid key added by `$setValidity`\n *  - `ng-pristine`: the control hasn't been interacted with yet\n *  - `ng-dirty`: the control has been interacted with\n *  - `ng-touched`: the control has been blurred\n *  - `ng-untouched`: the control hasn't been blurred\n *  - `ng-pending`: any `$asyncValidators` are unfulfilled\n *  - `ng-empty`: the view does not contain a value or the value is deemed \"empty\", as defined\n *     by the {@link ngModel.NgModelController#$isEmpty} method\n *  - `ng-not-empty`: the view contains a non-empty value\n *\n * Keep in mind that ngAnimate can detect each of these classes when added and removed.\n *\n * @animations\n * Animations within models are triggered when any of the associated CSS classes are added and removed\n * on the input element which is attached to the model. These classes include: `.ng-pristine`, `.ng-dirty`,\n * `.ng-invalid` and `.ng-valid` as well as any other validations that are performed on the model itself.\n * The animations that are triggered within ngModel are similar to how they work in ngClass and\n * animations can be hooked into using CSS transitions, keyframes as well as JS animations.\n *\n * The following example shows a simple way to utilize CSS transitions to style an input element\n * that has been rendered as invalid after it has been validated:\n *\n * <pre>\n * //be sure to include ngAnimate as a module to hook into more\n * //advanced animations\n * .my-input {\n *   transition:0.5s linear all;\n *   background: white;\n * }\n * .my-input.ng-invalid {\n *   background: red;\n *   color:white;\n * }\n * </pre>\n *\n * @example\n * ### Basic Usage\n * <example deps=\"angular-animate.js\" animations=\"true\" fixBase=\"true\" module=\"inputExample\" name=\"ng-model\">\n     <file name=\"index.html\">\n       <script>\n        angular.module('inputExample', [])\n          .controller('ExampleController', ['$scope', function($scope) {\n            $scope.val = '1';\n          }]);\n       </script>\n       <style>\n         .my-input {\n           transition:all linear 0.5s;\n           background: transparent;\n         }\n         .my-input.ng-invalid {\n           color:white;\n           background: red;\n         }\n       </style>\n       <p id=\"inputDescription\">\n        Update input to see transitions when valid/invalid.\n        Integer is a valid value.\n       </p>\n       <form name=\"testForm\" ng-controller=\"ExampleController\">\n         <input ng-model=\"val\" ng-pattern=\"/^\\d+$/\" name=\"anim\" class=\"my-input\"\n                aria-describedby=\"inputDescription\" />\n       </form>\n     </file>\n * </example>\n *\n * @example\n * ### Binding to a getter/setter\n *\n * Sometimes it's helpful to bind `ngModel` to a getter/setter function.  A getter/setter is a\n * function that returns a representation of the model when called with zero arguments, and sets\n * the internal state of a model when called with an argument. It's sometimes useful to use this\n * for models that have an internal representation that's different from what the model exposes\n * to the view.\n *\n * <div class=\"alert alert-success\">\n * **Best Practice:** It's best to keep getters fast because AngularJS is likely to call them more\n * frequently than other parts of your code.\n * </div>\n *\n * You use this behavior by adding `ng-model-options=\"{ getterSetter: true }\"` to an element that\n * has `ng-model` attached to it. You can also add `ng-model-options=\"{ getterSetter: true }\"` to\n * a `<form>`, which will enable this behavior for all `<input>`s within it. See\n * {@link ng.directive:ngModelOptions `ngModelOptions`} for more.\n *\n * The following example shows how to use `ngModel` with a getter/setter:\n *\n * @example\n * <example name=\"ngModel-getter-setter\" module=\"getterSetterExample\">\n     <file name=\"index.html\">\n       <div ng-controller=\"ExampleController\">\n         <form name=\"userForm\">\n           <label>Name:\n             <input type=\"text\" name=\"userName\"\n                    ng-model=\"user.name\"\n                    ng-model-options=\"{ getterSetter: true }\" />\n           </label>\n         </form>\n         <pre>user.name = <span ng-bind=\"user.name()\"></span></pre>\n       </div>\n     </file>\n     <file name=\"app.js\">\n       angular.module('getterSetterExample', [])\n         .controller('ExampleController', ['$scope', function($scope) {\n           var _name = 'Brian';\n           $scope.user = {\n             name: function(newName) {\n              // Note that newName can be undefined for two reasons:\n              // 1. Because it is called as a getter and thus called with no arguments\n              // 2. Because the property should actually be set to undefined. This happens e.g. if the\n              //    input is invalid\n              return arguments.length ? (_name = newName) : _name;\n             }\n           };\n         }]);\n     </file>\n * </example>\n */\nvar ngModelDirective = ['$rootScope', function($rootScope) {\n  return {\n    restrict: 'A',\n    require: ['ngModel', '^?form', '^?ngModelOptions'],\n    controller: NgModelController,\n    // Prelink needs to run before any input directive\n    // so that we can set the NgModelOptions in NgModelController\n    // before anyone else uses it.\n    priority: 1,\n    compile: function ngModelCompile(element) {\n      // Setup initial state of the control\n      element.addClass(PRISTINE_CLASS).addClass(UNTOUCHED_CLASS).addClass(VALID_CLASS);\n\n      return {\n        pre: function ngModelPreLink(scope, element, attr, ctrls) {\n          var modelCtrl = ctrls[0],\n              formCtrl = ctrls[1] || modelCtrl.$$parentForm,\n              optionsCtrl = ctrls[2];\n\n          if (optionsCtrl) {\n            modelCtrl.$options = optionsCtrl.$options;\n          }\n\n          modelCtrl.$$initGetterSetters();\n\n          // notify others, especially parent forms\n          formCtrl.$addControl(modelCtrl);\n\n          attr.$observe('name', function(newValue) {\n            if (modelCtrl.$name !== newValue) {\n              modelCtrl.$$parentForm.$$renameControl(modelCtrl, newValue);\n            }\n          });\n\n          scope.$on('$destroy', function() {\n            modelCtrl.$$parentForm.$removeControl(modelCtrl);\n          });\n        },\n        post: function ngModelPostLink(scope, element, attr, ctrls) {\n          var modelCtrl = ctrls[0];\n          modelCtrl.$$setUpdateOnEvents();\n\n          function setTouched() {\n            modelCtrl.$setTouched();\n          }\n\n          element.on('blur', function() {\n            if (modelCtrl.$touched) return;\n\n            if ($rootScope.$$phase) {\n              scope.$evalAsync(setTouched);\n            } else {\n              scope.$apply(setTouched);\n            }\n          });\n        }\n      };\n    }\n  };\n}];\n\n/* exported defaultModelOptions */\nvar defaultModelOptions;\nvar DEFAULT_REGEXP = /(\\s+|^)default(\\s+|$)/;\n\n/**\n * @ngdoc type\n * @name ModelOptions\n * @description\n * A container for the options set by the {@link ngModelOptions} directive\n */\nfunction ModelOptions(options) {\n  this.$$options = options;\n}\n\nModelOptions.prototype = {\n\n  /**\n   * @ngdoc method\n   * @name ModelOptions#getOption\n   * @param {string} name the name of the option to retrieve\n   * @returns {*} the value of the option\n   * @description\n   * Returns the value of the given option\n   */\n  getOption: function(name) {\n    return this.$$options[name];\n  },\n\n  /**\n   * @ngdoc method\n   * @name ModelOptions#createChild\n   * @param {Object} options a hash of options for the new child that will override the parent's options\n   * @return {ModelOptions} a new `ModelOptions` object initialized with the given options.\n   */\n  createChild: function(options) {\n    var inheritAll = false;\n\n    // make a shallow copy\n    options = extend({}, options);\n\n    // Inherit options from the parent if specified by the value `\"$inherit\"`\n    forEach(options, /** @this */ function(option, key) {\n      if (option === '$inherit') {\n        if (key === '*') {\n          inheritAll = true;\n        } else {\n          options[key] = this.$$options[key];\n          // `updateOn` is special so we must also inherit the `updateOnDefault` option\n          if (key === 'updateOn') {\n            options.updateOnDefault = this.$$options.updateOnDefault;\n          }\n        }\n      } else {\n        if (key === 'updateOn') {\n          // If the `updateOn` property contains the `default` event then we have to remove\n          // it from the event list and set the `updateOnDefault` flag.\n          options.updateOnDefault = false;\n          options[key] = trim(option.replace(DEFAULT_REGEXP, function() {\n            options.updateOnDefault = true;\n            return ' ';\n          }));\n        }\n      }\n    }, this);\n\n    if (inheritAll) {\n      // We have a property of the form: `\"*\": \"$inherit\"`\n      delete options['*'];\n      defaults(options, this.$$options);\n    }\n\n    // Finally add in any missing defaults\n    defaults(options, defaultModelOptions.$$options);\n\n    return new ModelOptions(options);\n  }\n};\n\n\ndefaultModelOptions = new ModelOptions({\n  updateOn: '',\n  updateOnDefault: true,\n  debounce: 0,\n  getterSetter: false,\n  allowInvalid: false,\n  timezone: null\n});\n\n\n/**\n * @ngdoc directive\n * @name ngModelOptions\n * @restrict A\n * @priority 10\n *\n * @description\n * This directive allows you to modify the behaviour of {@link ngModel} directives within your\n * application. You can specify an `ngModelOptions` directive on any element. All {@link ngModel}\n * directives will use the options of their nearest `ngModelOptions` ancestor.\n *\n * The `ngModelOptions` settings are found by evaluating the value of the attribute directive as\n * an AngularJS expression. This expression should evaluate to an object, whose properties contain\n * the settings. For example: `<div ng-model-options=\"{ debounce: 100 }\"`.\n *\n * ## Inheriting Options\n *\n * You can specify that an `ngModelOptions` setting should be inherited from a parent `ngModelOptions`\n * directive by giving it the value of `\"$inherit\"`.\n * Then it will inherit that setting from the first `ngModelOptions` directive found by traversing up the\n * DOM tree. If there is no ancestor element containing an `ngModelOptions` directive then default settings\n * will be used.\n *\n * For example given the following fragment of HTML\n *\n *\n * ```html\n * <div ng-model-options=\"{ allowInvalid: true, debounce: 200 }\">\n *   <form ng-model-options=\"{ updateOn: 'blur', allowInvalid: '$inherit' }\">\n *     <input ng-model-options=\"{ updateOn: 'default', allowInvalid: '$inherit' }\" />\n *   </form>\n * </div>\n * ```\n *\n * the `input` element will have the following settings\n *\n * ```js\n * { allowInvalid: true, updateOn: 'default', debounce: 0 }\n * ```\n *\n * Notice that the `debounce` setting was not inherited and used the default value instead.\n *\n * You can specify that all undefined settings are automatically inherited from an ancestor by\n * including a property with key of `\"*\"` and value of `\"$inherit\"`.\n *\n * For example given the following fragment of HTML\n *\n *\n * ```html\n * <div ng-model-options=\"{ allowInvalid: true, debounce: 200 }\">\n *   <form ng-model-options=\"{ updateOn: 'blur', \"*\": '$inherit' }\">\n *     <input ng-model-options=\"{ updateOn: 'default', \"*\": '$inherit' }\" />\n *   </form>\n * </div>\n * ```\n *\n * the `input` element will have the following settings\n *\n * ```js\n * { allowInvalid: true, updateOn: 'default', debounce: 200 }\n * ```\n *\n * Notice that the `debounce` setting now inherits the value from the outer `<div>` element.\n *\n * If you are creating a reusable component then you should be careful when using `\"*\": \"$inherit\"`\n * since you may inadvertently inherit a setting in the future that changes the behavior of your component.\n *\n *\n * ## Triggering and debouncing model updates\n *\n * The `updateOn` and `debounce` properties allow you to specify a custom list of events that will\n * trigger a model update and/or a debouncing delay so that the actual update only takes place when\n * a timer expires; this timer will be reset after another change takes place.\n *\n * Given the nature of `ngModelOptions`, the value displayed inside input fields in the view might\n * be different from the value in the actual model. This means that if you update the model you\n * should also invoke {@link ngModel.NgModelController#$rollbackViewValue} on the relevant input field in\n * order to make sure it is synchronized with the model and that any debounced action is canceled.\n *\n * The easiest way to reference the control's {@link ngModel.NgModelController#$rollbackViewValue}\n * method is by making sure the input is placed inside a form that has a `name` attribute. This is\n * important because `form` controllers are published to the related scope under the name in their\n * `name` attribute.\n *\n * Any pending changes will take place immediately when an enclosing form is submitted via the\n * `submit` event. Note that `ngClick` events will occur before the model is updated. Use `ngSubmit`\n * to have access to the updated model.\n *\n * ### Overriding immediate updates\n *\n * The following example shows how to override immediate updates. Changes on the inputs within the\n * form will update the model only when the control loses focus (blur event). If `escape` key is\n * pressed while the input field is focused, the value is reset to the value in the current model.\n *\n * <example name=\"ngModelOptions-directive-blur\" module=\"optionsExample\">\n *   <file name=\"index.html\">\n *     <div ng-controller=\"ExampleController\">\n *       <form name=\"userForm\">\n *         <label>\n *           Name:\n *           <input type=\"text\" name=\"userName\"\n *                  ng-model=\"user.name\"\n *                  ng-model-options=\"{ updateOn: 'blur' }\"\n *                  ng-keyup=\"cancel($event)\" />\n *         </label><br />\n *         <label>\n *           Other data:\n *           <input type=\"text\" ng-model=\"user.data\" />\n *         </label><br />\n *       </form>\n *       <pre>user.name = <span ng-bind=\"user.name\"></span></pre>\n *     </div>\n *   </file>\n *   <file name=\"app.js\">\n *     angular.module('optionsExample', [])\n *       .controller('ExampleController', ['$scope', function($scope) {\n *         $scope.user = { name: 'say', data: '' };\n *\n *         $scope.cancel = function(e) {\n *           if (e.keyCode === 27) {\n *             $scope.userForm.userName.$rollbackViewValue();\n *           }\n *         };\n *       }]);\n *   </file>\n *   <file name=\"protractor.js\" type=\"protractor\">\n *     var model = element(by.binding('user.name'));\n *     var input = element(by.model('user.name'));\n *     var other = element(by.model('user.data'));\n *\n *     it('should allow custom events', function() {\n *       input.sendKeys(' hello');\n *       input.click();\n *       expect(model.getText()).toEqual('say');\n *       other.click();\n *       expect(model.getText()).toEqual('say hello');\n *     });\n *\n *     it('should $rollbackViewValue when model changes', function() {\n *       input.sendKeys(' hello');\n *       expect(input.getAttribute('value')).toEqual('say hello');\n *       input.sendKeys(protractor.Key.ESCAPE);\n *       expect(input.getAttribute('value')).toEqual('say');\n *       other.click();\n *       expect(model.getText()).toEqual('say');\n *     });\n *   </file>\n * </example>\n *\n * ### Debouncing updates\n *\n * The next example shows how to debounce model changes. Model will be updated only 1 sec after last change.\n * If the `Clear` button is pressed, any debounced action is canceled and the value becomes empty.\n *\n * <example name=\"ngModelOptions-directive-debounce\" module=\"optionsExample\">\n *   <file name=\"index.html\">\n *     <div ng-controller=\"ExampleController\">\n *       <form name=\"userForm\">\n *         Name:\n *         <input type=\"text\" name=\"userName\"\n *                ng-model=\"user.name\"\n *                ng-model-options=\"{ debounce: 1000 }\" />\n *         <button ng-click=\"userForm.userName.$rollbackViewValue(); user.name=''\">Clear</button><br />\n *       </form>\n *       <pre>user.name = <span ng-bind=\"user.name\"></span></pre>\n *     </div>\n *   </file>\n *   <file name=\"app.js\">\n *     angular.module('optionsExample', [])\n *       .controller('ExampleController', ['$scope', function($scope) {\n *         $scope.user = { name: 'say' };\n *       }]);\n *   </file>\n * </example>\n *\n * ### Default events, extra triggers, and catch-all debounce values\n *\n * This example shows the relationship between \"default\" update events and\n * additional `updateOn` triggers.\n *\n * `default` events are those that are bound to the control, and when fired, update the `$viewValue`\n * via {@link ngModel.NgModelController#$setViewValue $setViewValue}. Every event that is not listed\n * in `updateOn` is considered a \"default\" event, since different control types have different\n * default events.\n *\n * The control in this example updates by \"default\", \"click\", and \"blur\", with different `debounce`\n * values. You can see that \"click\" doesn't have an individual `debounce` value -\n * therefore it uses the `*` debounce value.\n *\n * There is also a button that calls {@link ngModel.NgModelController#$setViewValue $setViewValue}\n * directly with a \"custom\" event. Since \"custom\" is not defined in the `updateOn` list,\n * it is considered a \"default\" event and will update the\n * control if \"default\" is defined in `updateOn`, and will receive the \"default\" debounce value.\n * Note that this is just to illustrate how custom controls would possibly call `$setViewValue`.\n *\n * You can change the `updateOn` and `debounce` configuration to test different scenarios. This\n * is done with {@link ngModel.NgModelController#$overrideModelOptions $overrideModelOptions}.\n *\n  <example name=\"ngModelOptions-advanced\" module=\"optionsExample\">\n    <file name=\"index.html\">\n       <model-update-demo></model-update-demo>\n    </file>\n    <file name=\"app.js\">\n      angular.module('optionsExample', [])\n        .component('modelUpdateDemo', {\n          templateUrl: 'template.html',\n          controller: function() {\n            this.name = 'Chinua';\n\n            this.options = {\n              updateOn: 'default blur click',\n              debounce: {\n                default: 2000,\n                blur: 0,\n                '*': 1000\n              }\n            };\n\n            this.updateEvents = function() {\n              var eventList = this.options.updateOn.split(' ');\n              eventList.push('*');\n              var events = {};\n\n              for (var i = 0; i < eventList.length; i++) {\n                events[eventList[i]] = this.options.debounce[eventList[i]];\n              }\n\n              this.events = events;\n            };\n\n            this.updateOptions = function() {\n              var options = angular.extend(this.options, {\n                updateOn: Object.keys(this.events).join(' ').replace('*', ''),\n                debounce: this.events\n              });\n\n              this.form.input.$overrideModelOptions(options);\n            };\n\n            // Initialize the event form\n            this.updateEvents();\n          }\n        });\n    </file>\n    <file name=\"template.html\">\n      <form name=\"$ctrl.form\">\n        Input: <input type=\"text\" name=\"input\" ng-model=\"$ctrl.name\" ng-model-options=\"$ctrl.options\" />\n      </form>\n      Model: <tt>{{$ctrl.name}}</tt>\n      <hr>\n      <button ng-click=\"$ctrl.form.input.$setViewValue('some value', 'custom')\">Trigger setViewValue with 'some value' and 'custom' event</button>\n\n      <hr>\n      <form ng-submit=\"$ctrl.updateOptions()\">\n        <b>updateOn</b><br>\n        <input type=\"text\" ng-model=\"$ctrl.options.updateOn\" ng-change=\"$ctrl.updateEvents()\" ng-model-options=\"{debounce: 500}\">\n\n        <table>\n          <tr>\n            <th>Option</th>\n            <th>Debounce value</th>\n          </tr>\n          <tr ng-repeat=\"(key, value) in $ctrl.events\">\n            <td>{{key}}</td>\n            <td><input type=\"number\" ng-model=\"$ctrl.events[key]\" /></td>\n          </tr>\n        </table>\n\n        <br>\n        <input type=\"submit\" value=\"Update options\">\n      </form>\n    </file>\n  </example>\n *\n *\n * ## Model updates and validation\n *\n * The default behaviour in `ngModel` is that the model value is set to `undefined` when the\n * validation determines that the value is invalid. By setting the `allowInvalid` property to true,\n * the model will still be updated even if the value is invalid.\n *\n *\n * ## Connecting to the scope\n *\n * By setting the `getterSetter` property to true you are telling ngModel that the `ngModel` expression\n * on the scope refers to a \"getter/setter\" function rather than the value itself.\n *\n * The following example shows how to bind to getter/setters:\n *\n * <example name=\"ngModelOptions-directive-getter-setter\" module=\"getterSetterExample\">\n *   <file name=\"index.html\">\n *     <div ng-controller=\"ExampleController\">\n *       <form name=\"userForm\">\n *         <label>\n *           Name:\n *           <input type=\"text\" name=\"userName\"\n *                  ng-model=\"user.name\"\n *                  ng-model-options=\"{ getterSetter: true }\" />\n *         </label>\n *       </form>\n *       <pre>user.name = <span ng-bind=\"user.name()\"></span></pre>\n *     </div>\n *   </file>\n *   <file name=\"app.js\">\n *     angular.module('getterSetterExample', [])\n *       .controller('ExampleController', ['$scope', function($scope) {\n *         var _name = 'Brian';\n *         $scope.user = {\n *           name: function(newName) {\n *             return angular.isDefined(newName) ? (_name = newName) : _name;\n *           }\n *         };\n *       }]);\n *   </file>\n * </example>\n *\n *\n * ## Programmatically changing options\n *\n * The `ngModelOptions` expression is only evaluated once when the directive is linked; it is not\n * watched for changes. However, it is possible to override the options on a single\n * {@link ngModel.NgModelController} instance with\n * {@link ngModel.NgModelController#$overrideModelOptions `NgModelController#$overrideModelOptions()`}.\n * See also the example for\n * {@link ngModelOptions#default-events-extra-triggers-and-catch-all-debounce-values\n * Default events, extra triggers, and catch-all debounce values}.\n *\n *\n * ## Specifying timezones\n *\n * You can specify the timezone that date/time input directives expect by providing its name in the\n * `timezone` property.\n *\n *\n * ## Formatting the value of `time` and `datetime-local`\n *\n * With the options `timeSecondsFormat` and `timeStripZeroSeconds` it is possible to adjust the value\n * that is displayed in the control. Note that browsers may apply their own formatting\n * in the user interface.\n *\n   <example name=\"ngModelOptions-time-format\" module=\"timeExample\">\n     <file name=\"index.html\">\n       <time-example></time-example>\n     </file>\n     <file name=\"script.js\">\n        angular.module('timeExample', [])\n          .component('timeExample', {\n            templateUrl: 'timeExample.html',\n            controller: function() {\n              this.time = new Date(1970, 0, 1, 14, 57, 0);\n\n              this.options = {\n                timeSecondsFormat: 'ss',\n                timeStripZeroSeconds: true\n              };\n\n              this.optionChange = function() {\n                this.timeForm.timeFormatted.$overrideModelOptions(this.options);\n                this.time = new Date(this.time);\n              };\n            }\n          });\n     </file>\n     <file name=\"timeExample.html\">\n       <form name=\"$ctrl.timeForm\">\n         <strong>Default</strong>:\n         <input type=\"time\" ng-model=\"$ctrl.time\" step=\"any\" /><br>\n         <strong>With options</strong>:\n         <input type=\"time\" name=\"timeFormatted\" ng-model=\"$ctrl.time\" step=\"any\" ng-model-options=\"$ctrl.options\" />\n         <br>\n\n         Options:<br>\n         <code>timeSecondsFormat</code>:\n         <input\n           type=\"text\"\n           ng-model=\"$ctrl.options.timeSecondsFormat\"\n           ng-change=\"$ctrl.optionChange()\">\n         <br>\n         <code>timeStripZeroSeconds</code>:\n         <input\n           type=\"checkbox\"\n           ng-model=\"$ctrl.options.timeStripZeroSeconds\"\n           ng-change=\"$ctrl.optionChange()\">\n        </form>\n      </file>\n *  </example>\n *\n * @param {Object} ngModelOptions options to apply to {@link ngModel} directives on this element and\n *   and its descendents.\n *\n * **General options**:\n *\n *   - `updateOn`: string specifying which event should the input be bound to. You can set several\n *     events using an space delimited list. There is a special event called `default` that\n *     matches the default events belonging to the control. These are the events that are bound to\n *     the control, and when fired, update the `$viewValue` via `$setViewValue`.\n *\n *     `ngModelOptions` considers every event that is not listed in `updateOn` a \"default\" event,\n *     since different control types use different default events.\n *\n *     See also the section {@link ngModelOptions#triggering-and-debouncing-model-updates\n *     Triggering and debouncing model updates}.\n *\n *   - `debounce`: integer value which contains the debounce model update value in milliseconds. A\n *     value of 0 triggers an immediate update. If an object is supplied instead, you can specify a\n *     custom value for each event. For example:\n *     ```\n *     ng-model-options=\"{\n *       updateOn: 'default blur',\n *       debounce: { 'default': 500, 'blur': 0 }\n *     }\"\n *     ```\n *     You can use the `*` key to specify a debounce value that applies to all events that are not\n *     specifically listed. In the following example, `mouseup` would have a debounce delay of 1000:\n *     ```\n *     ng-model-options=\"{\n *       updateOn: 'default blur mouseup',\n *       debounce: { 'default': 500, 'blur': 0, '*': 1000 }\n *     }\"\n *     ```\n *   - `allowInvalid`: boolean value which indicates that the model can be set with values that did\n *     not validate correctly instead of the default behavior of setting the model to undefined.\n *   - `getterSetter`: boolean value which determines whether or not to treat functions bound to\n *     `ngModel` as getters/setters.\n *\n *\n *  **Input-type specific options**:\n *\n *   - `timezone`: Defines the timezone to be used to read/write the `Date` instance in the model for\n *     `<input type=\"date\" />`, `<input type=\"time\" />`, ... . It understands UTC/GMT and the\n *     continental US time zone abbreviations, but for general use, use a time zone offset, for\n *     example, `'+0430'` (4 hours, 30 minutes east of the Greenwich meridian)\n *     If not specified, the timezone of the browser will be used.\n *     Note that changing the timezone will have no effect on the current date, and is only applied after\n *     the next input / model change.\n *\n *   - `timeSecondsFormat`: Defines if the `time` and `datetime-local` types should show seconds and\n *     milliseconds. The option follows the format string of {@link date date filter}.\n *     By default, the options is `undefined` which is equal to `'ss.sss'` (seconds and milliseconds).\n *     The other options are `'ss'` (strips milliseconds), and `''` (empty string), which strips both\n *     seconds and milliseconds.\n *     Note that browsers that support `time` and `datetime-local` require the hour and minutes\n *     part of the time string, and may show the value differently in the user interface.\n *     {@link ngModelOptions#formatting-the-value-of-time-and-datetime-local- See the example}.\n *\n *   - `timeStripZeroSeconds`: Defines if the `time` and `datetime-local` types should strip the\n *     seconds and milliseconds from the formatted value if they are zero. This option is applied\n *     after `timeSecondsFormat`.\n *     This option can be used to make the formatting consistent over different browsers, as some\n *     browsers with support for `time` will natively hide the milliseconds and\n *     seconds if they are zero, but others won't, and browsers that don't implement these input\n *     types will always show the full string.\n *     {@link ngModelOptions#formatting-the-value-of-time-and-datetime-local- See the example}.\n *\n */\nvar ngModelOptionsDirective = function() {\n  NgModelOptionsController.$inject = ['$attrs', '$scope'];\n  function NgModelOptionsController($attrs, $scope) {\n    this.$$attrs = $attrs;\n    this.$$scope = $scope;\n  }\n  NgModelOptionsController.prototype = {\n    $onInit: function() {\n      var parentOptions = this.parentCtrl ? this.parentCtrl.$options : defaultModelOptions;\n      var modelOptionsDefinition = this.$$scope.$eval(this.$$attrs.ngModelOptions);\n\n      this.$options = parentOptions.createChild(modelOptionsDefinition);\n    }\n  };\n\n  return {\n    restrict: 'A',\n    // ngModelOptions needs to run before ngModel and input directives\n    priority: 10,\n    require: {parentCtrl: '?^^ngModelOptions'},\n    bindToController: true,\n    controller: NgModelOptionsController\n  };\n};\n\n\n// shallow copy over values from `src` that are not already specified on `dst`\nfunction defaults(dst, src) {\n  forEach(src, function(value, key) {\n    if (!isDefined(dst[key])) {\n      dst[key] = value;\n    }\n  });\n}\n\n/**\n * @ngdoc directive\n * @name ngNonBindable\n * @restrict AC\n * @priority 1000\n * @element ANY\n *\n * @description\n * The `ngNonBindable` directive tells AngularJS not to compile or bind the contents of the current\n * DOM element, including directives on the element itself that have a lower priority than\n * `ngNonBindable`. This is useful if the element contains what appears to be AngularJS directives\n * and bindings but which should be ignored by AngularJS. This could be the case if you have a site\n * that displays snippets of code, for instance.\n *\n * @example\n * In this example there are two locations where a simple interpolation binding (`{{}}`) is present,\n * but the one wrapped in `ngNonBindable` is left alone.\n *\n  <example name=\"ng-non-bindable\">\n    <file name=\"index.html\">\n      <div>Normal: {{1 + 2}}</div>\n      <div ng-non-bindable>Ignored: {{1 + 2}}</div>\n    </file>\n    <file name=\"protractor.js\" type=\"protractor\">\n     it('should check ng-non-bindable', function() {\n       expect(element(by.binding('1 + 2')).getText()).toContain('3');\n       expect(element.all(by.css('div')).last().getText()).toMatch(/1 \\+ 2/);\n     });\n    </file>\n  </example>\n */\nvar ngNonBindableDirective = ngDirective({ terminal: true, priority: 1000 });\n\n/* exported ngOptionsDirective */\n\n/* global jqLiteRemove */\n\nvar ngOptionsMinErr = minErr('ngOptions');\n\n/**\n * @ngdoc directive\n * @name ngOptions\n * @restrict A\n *\n * @description\n *\n * The `ngOptions` attribute can be used to dynamically generate a list of `<option>`\n * elements for the `<select>` element using the array or object obtained by evaluating the\n * `ngOptions` comprehension expression.\n *\n * In many cases, {@link ng.directive:ngRepeat ngRepeat} can be used on `<option>` elements instead of\n * `ngOptions` to achieve a similar result. However, `ngOptions` provides some benefits:\n * - more flexibility in how the `<select>`'s model is assigned via the `select` **`as`** part of the\n * comprehension expression\n * - reduced memory consumption by not creating a new scope for each repeated instance\n * - increased render speed by creating the options in a documentFragment instead of individually\n *\n * When an item in the `<select>` menu is selected, the array element or object property\n * represented by the selected option will be bound to the model identified by the `ngModel`\n * directive.\n *\n * Optionally, a single hard-coded `<option>` element, with the value set to an empty string, can\n * be nested into the `<select>` element. This element will then represent the `null` or \"not selected\"\n * option. See example below for demonstration.\n *\n * ## Complex Models (objects or collections)\n *\n * By default, `ngModel` watches the model by reference, not value. This is important to know when\n * binding the select to a model that is an object or a collection.\n *\n * One issue occurs if you want to preselect an option. For example, if you set\n * the model to an object that is equal to an object in your collection, `ngOptions` won't be able to set the selection,\n * because the objects are not identical. So by default, you should always reference the item in your collection\n * for preselections, e.g.: `$scope.selected = $scope.collection[3]`.\n *\n * Another solution is to use a `track by` clause, because then `ngOptions` will track the identity\n * of the item not by reference, but by the result of the `track by` expression. For example, if your\n * collection items have an id property, you would `track by item.id`.\n *\n * A different issue with objects or collections is that ngModel won't detect if an object property or\n * a collection item changes. For that reason, `ngOptions` additionally watches the model using\n * `$watchCollection`, when the expression contains a `track by` clause or the the select has the `multiple` attribute.\n * This allows ngOptions to trigger a re-rendering of the options even if the actual object/collection\n * has not changed identity, but only a property on the object or an item in the collection changes.\n *\n * Note that `$watchCollection` does a shallow comparison of the properties of the object (or the items in the collection\n * if the model is an array). This means that changing a property deeper than the first level inside the\n * object/collection will not trigger a re-rendering.\n *\n * ## `select` **`as`**\n *\n * Using `select` **`as`** will bind the result of the `select` expression to the model, but\n * the value of the `<select>` and `<option>` html elements will be either the index (for array data sources)\n * or property name (for object data sources) of the value within the collection. If a **`track by`** expression\n * is used, the result of that expression will be set as the value of the `option` and `select` elements.\n *\n *\n * ### `select` **`as`** and **`track by`**\n *\n * <div class=\"alert alert-warning\">\n * Be careful when using `select` **`as`** and **`track by`** in the same expression.\n * </div>\n *\n * Given this array of items on the $scope:\n *\n * ```js\n * $scope.items = [{\n *   id: 1,\n *   label: 'aLabel',\n *   subItem: { name: 'aSubItem' }\n * }, {\n *   id: 2,\n *   label: 'bLabel',\n *   subItem: { name: 'bSubItem' }\n * }];\n * ```\n *\n * This will work:\n *\n * ```html\n * <select ng-options=\"item as item.label for item in items track by item.id\" ng-model=\"selected\"></select>\n * ```\n * ```js\n * $scope.selected = $scope.items[0];\n * ```\n *\n * but this will not work:\n *\n * ```html\n * <select ng-options=\"item.subItem as item.label for item in items track by item.id\" ng-model=\"selected\"></select>\n * ```\n * ```js\n * $scope.selected = $scope.items[0].subItem;\n * ```\n *\n * In both examples, the **`track by`** expression is applied successfully to each `item` in the\n * `items` array. Because the selected option has been set programmatically in the controller, the\n * **`track by`** expression is also applied to the `ngModel` value. In the first example, the\n * `ngModel` value is `items[0]` and the **`track by`** expression evaluates to `items[0].id` with\n * no issue. In the second example, the `ngModel` value is `items[0].subItem` and the **`track by`**\n * expression evaluates to `items[0].subItem.id` (which is undefined). As a result, the model value\n * is not matched against any `<option>` and the `<select>` appears as having no selected value.\n *\n *\n * @param {string} ngModel Assignable AngularJS expression to data-bind to.\n * @param {comprehension_expression} ngOptions in one of the following forms:\n *\n *   * for array data sources:\n *     * `label` **`for`** `value` **`in`** `array`\n *     * `select` **`as`** `label` **`for`** `value` **`in`** `array`\n *     * `label` **`group by`** `group` **`for`** `value` **`in`** `array`\n *     * `label` **`disable when`** `disable` **`for`** `value` **`in`** `array`\n *     * `label` **`group by`** `group` **`for`** `value` **`in`** `array` **`track by`** `trackexpr`\n *     * `label` **`disable when`** `disable` **`for`** `value` **`in`** `array` **`track by`** `trackexpr`\n *     * `label` **`for`** `value` **`in`** `array` | orderBy:`orderexpr` **`track by`** `trackexpr`\n *        (for including a filter with `track by`)\n *   * for object data sources:\n *     * `label` **`for (`**`key` **`,`** `value`**`) in`** `object`\n *     * `select` **`as`** `label` **`for (`**`key` **`,`** `value`**`) in`** `object`\n *     * `label` **`group by`** `group` **`for (`**`key`**`,`** `value`**`) in`** `object`\n *     * `label` **`disable when`** `disable` **`for (`**`key`**`,`** `value`**`) in`** `object`\n *     * `select` **`as`** `label` **`group by`** `group`\n *         **`for` `(`**`key`**`,`** `value`**`) in`** `object`\n *     * `select` **`as`** `label` **`disable when`** `disable`\n *         **`for` `(`**`key`**`,`** `value`**`) in`** `object`\n *\n * Where:\n *\n *   * `array` / `object`: an expression which evaluates to an array / object to iterate over.\n *   * `value`: local variable which will refer to each item in the `array` or each property value\n *      of `object` during iteration.\n *   * `key`: local variable which will refer to a property name in `object` during iteration.\n *   * `label`: The result of this expression will be the label for `<option>` element. The\n *     `expression` will most likely refer to the `value` variable (e.g. `value.propertyName`).\n *   * `select`: The result of this expression will be bound to the model of the parent `<select>`\n *      element. If not specified, `select` expression will default to `value`.\n *   * `group`: The result of this expression will be used to group options using the `<optgroup>`\n *      DOM element.\n *   * `disable`: The result of this expression will be used to disable the rendered `<option>`\n *      element. Return `true` to disable.\n *   * `trackexpr`: Used when working with an array of objects. The result of this expression will be\n *      used to identify the objects in the array. The `trackexpr` will most likely refer to the\n *     `value` variable (e.g. `value.propertyName`). With this the selection is preserved\n *      even when the options are recreated (e.g. reloaded from the server).\n * @param {string=} name Property name of the form under which the control is published.\n * @param {string=} required The control is considered valid only if value is entered.\n * @param {string=} ngRequired Adds `required` attribute and `required` validation constraint to\n *    the element when the ngRequired expression evaluates to true. Use `ngRequired` instead of\n *    `required` when you want to data-bind to the `required` attribute.\n * @param {string=} ngAttrSize sets the size of the select element dynamically. Uses the\n * {@link guide/interpolation#-ngattr-for-binding-to-arbitrary-attributes ngAttr} directive.\n *\n * @example\n    <example module=\"selectExample\" name=\"select\">\n      <file name=\"index.html\">\n        <script>\n        angular.module('selectExample', [])\n          .controller('ExampleController', ['$scope', function($scope) {\n            $scope.colors = [\n              {name:'black', shade:'dark'},\n              {name:'white', shade:'light', notAnOption: true},\n              {name:'red', shade:'dark'},\n              {name:'blue', shade:'dark', notAnOption: true},\n              {name:'yellow', shade:'light', notAnOption: false}\n            ];\n            $scope.myColor = $scope.colors[2]; // red\n          }]);\n        </script>\n        <div ng-controller=\"ExampleController\">\n          <ul>\n            <li ng-repeat=\"color in colors\">\n              <label>Name: <input ng-model=\"color.name\"></label>\n              <label><input type=\"checkbox\" ng-model=\"color.notAnOption\"> Disabled?</label>\n              <button ng-click=\"colors.splice($index, 1)\" aria-label=\"Remove\">X</button>\n            </li>\n            <li>\n              <button ng-click=\"colors.push({})\">add</button>\n            </li>\n          </ul>\n          <hr/>\n          <label>Color (null not allowed):\n            <select ng-model=\"myColor\" ng-options=\"color.name for color in colors\"></select>\n          </label><br/>\n          <label>Color (null allowed):\n          <span  class=\"nullable\">\n            <select ng-model=\"myColor\" ng-options=\"color.name for color in colors\">\n              <option value=\"\">-- choose color --</option>\n            </select>\n          </span></label><br/>\n\n          <label>Color grouped by shade:\n            <select ng-model=\"myColor\" ng-options=\"color.name group by color.shade for color in colors\">\n            </select>\n          </label><br/>\n\n          <label>Color grouped by shade, with some disabled:\n            <select ng-model=\"myColor\"\n                  ng-options=\"color.name group by color.shade disable when color.notAnOption for color in colors\">\n            </select>\n          </label><br/>\n\n\n\n          Select <button ng-click=\"myColor = { name:'not in list', shade: 'other' }\">bogus</button>.\n          <br/>\n          <hr/>\n          Currently selected: {{ {selected_color:myColor} }}\n          <div style=\"border:solid 1px black; height:20px\"\n               ng-style=\"{'background-color':myColor.name}\">\n          </div>\n        </div>\n      </file>\n      <file name=\"protractor.js\" type=\"protractor\">\n         it('should check ng-options', function() {\n           expect(element(by.binding('{selected_color:myColor}')).getText()).toMatch('red');\n           element.all(by.model('myColor')).first().click();\n           element.all(by.css('select[ng-model=\"myColor\"] option')).first().click();\n           expect(element(by.binding('{selected_color:myColor}')).getText()).toMatch('black');\n           element(by.css('.nullable select[ng-model=\"myColor\"]')).click();\n           element.all(by.css('.nullable select[ng-model=\"myColor\"] option')).first().click();\n           expect(element(by.binding('{selected_color:myColor}')).getText()).toMatch('null');\n         });\n      </file>\n    </example>\n */\n\n/* eslint-disable max-len */\n//                     //00001111111111000000000002222222222000000000000000000000333333333300000000000000000000000004444444444400000000000005555555555555000000000666666666666600000007777777777777000000000000000888888888800000000000000000009999999999\nvar NG_OPTIONS_REGEXP = /^\\s*([\\s\\S]+?)(?:\\s+as\\s+([\\s\\S]+?))?(?:\\s+group\\s+by\\s+([\\s\\S]+?))?(?:\\s+disable\\s+when\\s+([\\s\\S]+?))?\\s+for\\s+(?:([$\\w][$\\w]*)|(?:\\(\\s*([$\\w][$\\w]*)\\s*,\\s*([$\\w][$\\w]*)\\s*\\)))\\s+in\\s+([\\s\\S]+?)(?:\\s+track\\s+by\\s+([\\s\\S]+?))?$/;\n                        // 1: value expression (valueFn)\n                        // 2: label expression (displayFn)\n                        // 3: group by expression (groupByFn)\n                        // 4: disable when expression (disableWhenFn)\n                        // 5: array item variable name\n                        // 6: object item key variable name\n                        // 7: object item value variable name\n                        // 8: collection expression\n                        // 9: track by expression\n/* eslint-enable */\n\n\nvar ngOptionsDirective = ['$compile', '$document', '$parse', function($compile, $document, $parse) {\n\n  function parseOptionsExpression(optionsExp, selectElement, scope) {\n\n    var match = optionsExp.match(NG_OPTIONS_REGEXP);\n    if (!(match)) {\n      throw ngOptionsMinErr('iexp',\n        'Expected expression in form of ' +\n        '\\'_select_ (as _label_)? for (_key_,)?_value_ in _collection_\\'' +\n        ' but got \\'{0}\\'. Element: {1}',\n        optionsExp, startingTag(selectElement));\n    }\n\n    // Extract the parts from the ngOptions expression\n\n    // The variable name for the value of the item in the collection\n    var valueName = match[5] || match[7];\n    // The variable name for the key of the item in the collection\n    var keyName = match[6];\n\n    // An expression that generates the viewValue for an option if there is a label expression\n    var selectAs = / as /.test(match[0]) && match[1];\n    // An expression that is used to track the id of each object in the options collection\n    var trackBy = match[9];\n    // An expression that generates the viewValue for an option if there is no label expression\n    var valueFn = $parse(match[2] ? match[1] : valueName);\n    var selectAsFn = selectAs && $parse(selectAs);\n    var viewValueFn = selectAsFn || valueFn;\n    var trackByFn = trackBy && $parse(trackBy);\n\n    // Get the value by which we are going to track the option\n    // if we have a trackFn then use that (passing scope and locals)\n    // otherwise just hash the given viewValue\n    var getTrackByValueFn = trackBy ?\n                              function(value, locals) { return trackByFn(scope, locals); } :\n                              function getHashOfValue(value) { return hashKey(value); };\n    var getTrackByValue = function(value, key) {\n      return getTrackByValueFn(value, getLocals(value, key));\n    };\n\n    var displayFn = $parse(match[2] || match[1]);\n    var groupByFn = $parse(match[3] || '');\n    var disableWhenFn = $parse(match[4] || '');\n    var valuesFn = $parse(match[8]);\n\n    var locals = {};\n    var getLocals = keyName ? function(value, key) {\n      locals[keyName] = key;\n      locals[valueName] = value;\n      return locals;\n    } : function(value) {\n      locals[valueName] = value;\n      return locals;\n    };\n\n\n    function Option(selectValue, viewValue, label, group, disabled) {\n      this.selectValue = selectValue;\n      this.viewValue = viewValue;\n      this.label = label;\n      this.group = group;\n      this.disabled = disabled;\n    }\n\n    function getOptionValuesKeys(optionValues) {\n      var optionValuesKeys;\n\n      if (!keyName && isArrayLike(optionValues)) {\n        optionValuesKeys = optionValues;\n      } else {\n        // if object, extract keys, in enumeration order, unsorted\n        optionValuesKeys = [];\n        for (var itemKey in optionValues) {\n          if (optionValues.hasOwnProperty(itemKey) && itemKey.charAt(0) !== '$') {\n            optionValuesKeys.push(itemKey);\n          }\n        }\n      }\n      return optionValuesKeys;\n    }\n\n    return {\n      trackBy: trackBy,\n      getTrackByValue: getTrackByValue,\n      getWatchables: $parse(valuesFn, function(optionValues) {\n        // Create a collection of things that we would like to watch (watchedArray)\n        // so that they can all be watched using a single $watchCollection\n        // that only runs the handler once if anything changes\n        var watchedArray = [];\n        optionValues = optionValues || [];\n\n        var optionValuesKeys = getOptionValuesKeys(optionValues);\n        var optionValuesLength = optionValuesKeys.length;\n        for (var index = 0; index < optionValuesLength; index++) {\n          var key = (optionValues === optionValuesKeys) ? index : optionValuesKeys[index];\n          var value = optionValues[key];\n\n          var locals = getLocals(value, key);\n          var selectValue = getTrackByValueFn(value, locals);\n          watchedArray.push(selectValue);\n\n          // Only need to watch the displayFn if there is a specific label expression\n          if (match[2] || match[1]) {\n            var label = displayFn(scope, locals);\n            watchedArray.push(label);\n          }\n\n          // Only need to watch the disableWhenFn if there is a specific disable expression\n          if (match[4]) {\n            var disableWhen = disableWhenFn(scope, locals);\n            watchedArray.push(disableWhen);\n          }\n        }\n        return watchedArray;\n      }),\n\n      getOptions: function() {\n\n        var optionItems = [];\n        var selectValueMap = {};\n\n        // The option values were already computed in the `getWatchables` fn,\n        // which must have been called to trigger `getOptions`\n        var optionValues = valuesFn(scope) || [];\n        var optionValuesKeys = getOptionValuesKeys(optionValues);\n        var optionValuesLength = optionValuesKeys.length;\n\n        for (var index = 0; index < optionValuesLength; index++) {\n          var key = (optionValues === optionValuesKeys) ? index : optionValuesKeys[index];\n          var value = optionValues[key];\n          var locals = getLocals(value, key);\n          var viewValue = viewValueFn(scope, locals);\n          var selectValue = getTrackByValueFn(viewValue, locals);\n          var label = displayFn(scope, locals);\n          var group = groupByFn(scope, locals);\n          var disabled = disableWhenFn(scope, locals);\n          var optionItem = new Option(selectValue, viewValue, label, group, disabled);\n\n          optionItems.push(optionItem);\n          selectValueMap[selectValue] = optionItem;\n        }\n\n        return {\n          items: optionItems,\n          selectValueMap: selectValueMap,\n          getOptionFromViewValue: function(value) {\n            return selectValueMap[getTrackByValue(value)];\n          },\n          getViewValueFromOption: function(option) {\n            // If the viewValue could be an object that may be mutated by the application,\n            // we need to make a copy and not return the reference to the value on the option.\n            return trackBy ? copy(option.viewValue) : option.viewValue;\n          }\n        };\n      }\n    };\n  }\n\n\n  // Support: IE 9 only\n  // We can't just jqLite('<option>') since jqLite is not smart enough\n  // to create it in <select> and IE barfs otherwise.\n  var optionTemplate = window.document.createElement('option'),\n      optGroupTemplate = window.document.createElement('optgroup');\n\n    function ngOptionsPostLink(scope, selectElement, attr, ctrls) {\n\n      var selectCtrl = ctrls[0];\n      var ngModelCtrl = ctrls[1];\n      var multiple = attr.multiple;\n\n      // The emptyOption allows the application developer to provide their own custom \"empty\"\n      // option when the viewValue does not match any of the option values.\n      for (var i = 0, children = selectElement.children(), ii = children.length; i < ii; i++) {\n        if (children[i].value === '') {\n          selectCtrl.hasEmptyOption = true;\n          selectCtrl.emptyOption = children.eq(i);\n          break;\n        }\n      }\n\n      // The empty option will be compiled and rendered before we first generate the options\n      selectElement.empty();\n\n      var providedEmptyOption = !!selectCtrl.emptyOption;\n\n      var unknownOption = jqLite(optionTemplate.cloneNode(false));\n      unknownOption.val('?');\n\n      var options;\n      var ngOptions = parseOptionsExpression(attr.ngOptions, selectElement, scope);\n      // This stores the newly created options before they are appended to the select.\n      // Since the contents are removed from the fragment when it is appended,\n      // we only need to create it once.\n      var listFragment = $document[0].createDocumentFragment();\n\n      // Overwrite the implementation. ngOptions doesn't use hashes\n      selectCtrl.generateUnknownOptionValue = function(val) {\n        return '?';\n      };\n\n      // Update the controller methods for multiple selectable options\n      if (!multiple) {\n\n        selectCtrl.writeValue = function writeNgOptionsValue(value) {\n          // The options might not be defined yet when ngModel tries to render\n          if (!options) return;\n\n          var selectedOption = selectElement[0].options[selectElement[0].selectedIndex];\n          var option = options.getOptionFromViewValue(value);\n\n          // Make sure to remove the selected attribute from the previously selected option\n          // Otherwise, screen readers might get confused\n          if (selectedOption) selectedOption.removeAttribute('selected');\n\n          if (option) {\n            // Don't update the option when it is already selected.\n            // For example, the browser will select the first option by default. In that case,\n            // most properties are set automatically - except the `selected` attribute, which we\n            // set always\n\n            if (selectElement[0].value !== option.selectValue) {\n              selectCtrl.removeUnknownOption();\n\n              selectElement[0].value = option.selectValue;\n              option.element.selected = true;\n            }\n\n            option.element.setAttribute('selected', 'selected');\n          } else {\n            selectCtrl.selectUnknownOrEmptyOption(value);\n          }\n        };\n\n        selectCtrl.readValue = function readNgOptionsValue() {\n\n          var selectedOption = options.selectValueMap[selectElement.val()];\n\n          if (selectedOption && !selectedOption.disabled) {\n            selectCtrl.unselectEmptyOption();\n            selectCtrl.removeUnknownOption();\n            return options.getViewValueFromOption(selectedOption);\n          }\n          return null;\n        };\n\n        // If we are using `track by` then we must watch the tracked value on the model\n        // since ngModel only watches for object identity change\n        // FIXME: When a user selects an option, this watch will fire needlessly\n        if (ngOptions.trackBy) {\n          scope.$watch(\n            function() { return ngOptions.getTrackByValue(ngModelCtrl.$viewValue); },\n            function() { ngModelCtrl.$render(); }\n          );\n        }\n\n      } else {\n\n        selectCtrl.writeValue = function writeNgOptionsMultiple(values) {\n          // The options might not be defined yet when ngModel tries to render\n          if (!options) return;\n\n          // Only set `<option>.selected` if necessary, in order to prevent some browsers from\n          // scrolling to `<option>` elements that are outside the `<select>` element's viewport.\n          var selectedOptions = values && values.map(getAndUpdateSelectedOption) || [];\n\n          options.items.forEach(function(option) {\n            if (option.element.selected && !includes(selectedOptions, option)) {\n              option.element.selected = false;\n            }\n          });\n        };\n\n\n        selectCtrl.readValue = function readNgOptionsMultiple() {\n          var selectedValues = selectElement.val() || [],\n              selections = [];\n\n          forEach(selectedValues, function(value) {\n            var option = options.selectValueMap[value];\n            if (option && !option.disabled) selections.push(options.getViewValueFromOption(option));\n          });\n\n          return selections;\n        };\n\n        // If we are using `track by` then we must watch these tracked values on the model\n        // since ngModel only watches for object identity change\n        if (ngOptions.trackBy) {\n\n          scope.$watchCollection(function() {\n            if (isArray(ngModelCtrl.$viewValue)) {\n              return ngModelCtrl.$viewValue.map(function(value) {\n                return ngOptions.getTrackByValue(value);\n              });\n            }\n          }, function() {\n            ngModelCtrl.$render();\n          });\n\n        }\n      }\n\n      if (providedEmptyOption) {\n\n        // compile the element since there might be bindings in it\n        $compile(selectCtrl.emptyOption)(scope);\n\n        selectElement.prepend(selectCtrl.emptyOption);\n\n        if (selectCtrl.emptyOption[0].nodeType === NODE_TYPE_COMMENT) {\n          // This means the empty option has currently no actual DOM node, probably because\n          // it has been modified by a transclusion directive.\n          selectCtrl.hasEmptyOption = false;\n\n          // Redefine the registerOption function, which will catch\n          // options that are added by ngIf etc. (rendering of the node is async because of\n          // lazy transclusion)\n          selectCtrl.registerOption = function(optionScope, optionEl) {\n            if (optionEl.val() === '') {\n              selectCtrl.hasEmptyOption = true;\n              selectCtrl.emptyOption = optionEl;\n              selectCtrl.emptyOption.removeClass('ng-scope');\n              // This ensures the new empty option is selected if previously no option was selected\n              ngModelCtrl.$render();\n\n              optionEl.on('$destroy', function() {\n                var needsRerender = selectCtrl.$isEmptyOptionSelected();\n\n                selectCtrl.hasEmptyOption = false;\n                selectCtrl.emptyOption = undefined;\n\n                if (needsRerender) ngModelCtrl.$render();\n              });\n            }\n          };\n\n        } else {\n          // remove the class, which is added automatically because we recompile the element and it\n          // becomes the compilation root\n          selectCtrl.emptyOption.removeClass('ng-scope');\n        }\n\n      }\n\n      // We will re-render the option elements if the option values or labels change\n      scope.$watchCollection(ngOptions.getWatchables, updateOptions);\n\n      // ------------------------------------------------------------------ //\n\n      function addOptionElement(option, parent) {\n        var optionElement = optionTemplate.cloneNode(false);\n        parent.appendChild(optionElement);\n        updateOptionElement(option, optionElement);\n      }\n\n      function getAndUpdateSelectedOption(viewValue) {\n        var option = options.getOptionFromViewValue(viewValue);\n        var element = option && option.element;\n\n        if (element && !element.selected) element.selected = true;\n\n        return option;\n      }\n\n      function updateOptionElement(option, element) {\n        option.element = element;\n        element.disabled = option.disabled;\n        // Support: IE 11 only, Edge 12-13 only\n        // NOTE: The label must be set before the value, otherwise IE 11 & Edge create unresponsive\n        // selects in certain circumstances when multiple selects are next to each other and display\n        // the option list in listbox style, i.e. the select is [multiple], or specifies a [size].\n        // See https://github.com/angular/angular.js/issues/11314 for more info.\n        // This is unfortunately untestable with unit / e2e tests\n        if (option.label !== element.label) {\n          element.label = option.label;\n          element.textContent = option.label;\n        }\n        element.value = option.selectValue;\n      }\n\n      function updateOptions() {\n        var previousValue = options && selectCtrl.readValue();\n\n        // We must remove all current options, but cannot simply set innerHTML = null\n        // since the providedEmptyOption might have an ngIf on it that inserts comments which we\n        // must preserve.\n        // Instead, iterate over the current option elements and remove them or their optgroup\n        // parents\n        if (options) {\n\n          for (var i = options.items.length - 1; i >= 0; i--) {\n            var option = options.items[i];\n            if (isDefined(option.group)) {\n              jqLiteRemove(option.element.parentNode);\n            } else {\n              jqLiteRemove(option.element);\n            }\n          }\n        }\n\n        options = ngOptions.getOptions();\n\n        var groupElementMap = {};\n\n        options.items.forEach(function addOption(option) {\n          var groupElement;\n\n          if (isDefined(option.group)) {\n\n            // This option is to live in a group\n            // See if we have already created this group\n            groupElement = groupElementMap[option.group];\n\n            if (!groupElement) {\n\n              groupElement = optGroupTemplate.cloneNode(false);\n              listFragment.appendChild(groupElement);\n\n              // Update the label on the group element\n              // \"null\" is special cased because of Safari\n              groupElement.label = option.group === null ? 'null' : option.group;\n\n              // Store it for use later\n              groupElementMap[option.group] = groupElement;\n            }\n\n            addOptionElement(option, groupElement);\n\n          } else {\n\n            // This option is not in a group\n            addOptionElement(option, listFragment);\n          }\n        });\n\n        selectElement[0].appendChild(listFragment);\n\n        ngModelCtrl.$render();\n\n        // Check to see if the value has changed due to the update to the options\n        if (!ngModelCtrl.$isEmpty(previousValue)) {\n          var nextValue = selectCtrl.readValue();\n          var isNotPrimitive = ngOptions.trackBy || multiple;\n          if (isNotPrimitive ? !equals(previousValue, nextValue) : previousValue !== nextValue) {\n            ngModelCtrl.$setViewValue(nextValue);\n            ngModelCtrl.$render();\n          }\n        }\n      }\n  }\n\n  return {\n    restrict: 'A',\n    terminal: true,\n    require: ['select', 'ngModel'],\n    link: {\n      pre: function ngOptionsPreLink(scope, selectElement, attr, ctrls) {\n        // Deactivate the SelectController.register method to prevent\n        // option directives from accidentally registering themselves\n        // (and unwanted $destroy handlers etc.)\n        ctrls[0].registerOption = noop;\n      },\n      post: ngOptionsPostLink\n    }\n  };\n}];\n\n/**\n * @ngdoc directive\n * @name ngPluralize\n * @restrict EA\n *\n * @description\n * `ngPluralize` is a directive that displays messages according to en-US localization rules.\n * These rules are bundled with angular.js, but can be overridden\n * (see {@link guide/i18n AngularJS i18n} dev guide). You configure ngPluralize directive\n * by specifying the mappings between\n * [plural categories](http://unicode.org/repos/cldr-tmp/trunk/diff/supplemental/language_plural_rules.html)\n * and the strings to be displayed.\n *\n * ## Plural categories and explicit number rules\n * There are two\n * [plural categories](http://unicode.org/repos/cldr-tmp/trunk/diff/supplemental/language_plural_rules.html)\n * in AngularJS's default en-US locale: \"one\" and \"other\".\n *\n * While a plural category may match many numbers (for example, in en-US locale, \"other\" can match\n * any number that is not 1), an explicit number rule can only match one number. For example, the\n * explicit number rule for \"3\" matches the number 3. There are examples of plural categories\n * and explicit number rules throughout the rest of this documentation.\n *\n * ## Configuring ngPluralize\n * You configure ngPluralize by providing 2 attributes: `count` and `when`.\n * You can also provide an optional attribute, `offset`.\n *\n * The value of the `count` attribute can be either a string or an {@link guide/expression\n * AngularJS expression}; these are evaluated on the current scope for its bound value.\n *\n * The `when` attribute specifies the mappings between plural categories and the actual\n * string to be displayed. The value of the attribute should be a JSON object.\n *\n * The following example shows how to configure ngPluralize:\n *\n * ```html\n * <ng-pluralize count=\"personCount\"\n                 when=\"{'0': 'Nobody is viewing.',\n *                      'one': '1 person is viewing.',\n *                      'other': '{} people are viewing.'}\">\n * </ng-pluralize>\n *```\n *\n * In the example, `\"0: Nobody is viewing.\"` is an explicit number rule. If you did not\n * specify this rule, 0 would be matched to the \"other\" category and \"0 people are viewing\"\n * would be shown instead of \"Nobody is viewing\". You can specify an explicit number rule for\n * other numbers, for example 12, so that instead of showing \"12 people are viewing\", you can\n * show \"a dozen people are viewing\".\n *\n * You can use a set of closed braces (`{}`) as a placeholder for the number that you want substituted\n * into pluralized strings. In the previous example, AngularJS will replace `{}` with\n * <span ng-non-bindable>`{{personCount}}`</span>. The closed braces `{}` is a placeholder\n * for <span ng-non-bindable>{{numberExpression}}</span>.\n *\n * If no rule is defined for a category, then an empty string is displayed and a warning is generated.\n * Note that some locales define more categories than `one` and `other`. For example, fr-fr defines `few` and `many`.\n *\n * ## Configuring ngPluralize with offset\n * The `offset` attribute allows further customization of pluralized text, which can result in\n * a better user experience. For example, instead of the message \"4 people are viewing this document\",\n * you might display \"John, Kate and 2 others are viewing this document\".\n * The offset attribute allows you to offset a number by any desired value.\n * Let's take a look at an example:\n *\n * ```html\n * <ng-pluralize count=\"personCount\" offset=2\n *               when=\"{'0': 'Nobody is viewing.',\n *                      '1': '{{person1}} is viewing.',\n *                      '2': '{{person1}} and {{person2}} are viewing.',\n *                      'one': '{{person1}}, {{person2}} and one other person are viewing.',\n *                      'other': '{{person1}}, {{person2}} and {} other people are viewing.'}\">\n * </ng-pluralize>\n * ```\n *\n * Notice that we are still using two plural categories(one, other), but we added\n * three explicit number rules 0, 1 and 2.\n * When one person, perhaps John, views the document, \"John is viewing\" will be shown.\n * When three people view the document, no explicit number rule is found, so\n * an offset of 2 is taken off 3, and AngularJS uses 1 to decide the plural category.\n * In this case, plural category 'one' is matched and \"John, Mary and one other person are viewing\"\n * is shown.\n *\n * Note that when you specify offsets, you must provide explicit number rules for\n * numbers from 0 up to and including the offset. If you use an offset of 3, for example,\n * you must provide explicit number rules for 0, 1, 2 and 3. You must also provide plural strings for\n * plural categories \"one\" and \"other\".\n *\n * @param {string|expression} count The variable to be bound to.\n * @param {string} when The mapping between plural category to its corresponding strings.\n * @param {number=} offset Offset to deduct from the total number.\n *\n * @example\n    <example module=\"pluralizeExample\" name=\"ng-pluralize\">\n      <file name=\"index.html\">\n        <script>\n          angular.module('pluralizeExample', [])\n            .controller('ExampleController', ['$scope', function($scope) {\n              $scope.person1 = 'Igor';\n              $scope.person2 = 'Misko';\n              $scope.personCount = 1;\n            }]);\n        </script>\n        <div ng-controller=\"ExampleController\">\n          <label>Person 1:<input type=\"text\" ng-model=\"person1\" value=\"Igor\" /></label><br/>\n          <label>Person 2:<input type=\"text\" ng-model=\"person2\" value=\"Misko\" /></label><br/>\n          <label>Number of People:<input type=\"text\" ng-model=\"personCount\" value=\"1\" /></label><br/>\n\n          <!--- Example with simple pluralization rules for en locale --->\n          Without Offset:\n          <ng-pluralize count=\"personCount\"\n                        when=\"{'0': 'Nobody is viewing.',\n                               'one': '1 person is viewing.',\n                               'other': '{} people are viewing.'}\">\n          </ng-pluralize><br>\n\n          <!--- Example with offset --->\n          With Offset(2):\n          <ng-pluralize count=\"personCount\" offset=2\n                        when=\"{'0': 'Nobody is viewing.',\n                               '1': '{{person1}} is viewing.',\n                               '2': '{{person1}} and {{person2}} are viewing.',\n                               'one': '{{person1}}, {{person2}} and one other person are viewing.',\n                               'other': '{{person1}}, {{person2}} and {} other people are viewing.'}\">\n          </ng-pluralize>\n        </div>\n      </file>\n      <file name=\"protractor.js\" type=\"protractor\">\n        it('should show correct pluralized string', function() {\n          var withoutOffset = element.all(by.css('ng-pluralize')).get(0);\n          var withOffset = element.all(by.css('ng-pluralize')).get(1);\n          var countInput = element(by.model('personCount'));\n\n          expect(withoutOffset.getText()).toEqual('1 person is viewing.');\n          expect(withOffset.getText()).toEqual('Igor is viewing.');\n\n          countInput.clear();\n          countInput.sendKeys('0');\n\n          expect(withoutOffset.getText()).toEqual('Nobody is viewing.');\n          expect(withOffset.getText()).toEqual('Nobody is viewing.');\n\n          countInput.clear();\n          countInput.sendKeys('2');\n\n          expect(withoutOffset.getText()).toEqual('2 people are viewing.');\n          expect(withOffset.getText()).toEqual('Igor and Misko are viewing.');\n\n          countInput.clear();\n          countInput.sendKeys('3');\n\n          expect(withoutOffset.getText()).toEqual('3 people are viewing.');\n          expect(withOffset.getText()).toEqual('Igor, Misko and one other person are viewing.');\n\n          countInput.clear();\n          countInput.sendKeys('4');\n\n          expect(withoutOffset.getText()).toEqual('4 people are viewing.');\n          expect(withOffset.getText()).toEqual('Igor, Misko and 2 other people are viewing.');\n        });\n        it('should show data-bound names', function() {\n          var withOffset = element.all(by.css('ng-pluralize')).get(1);\n          var personCount = element(by.model('personCount'));\n          var person1 = element(by.model('person1'));\n          var person2 = element(by.model('person2'));\n          personCount.clear();\n          personCount.sendKeys('4');\n          person1.clear();\n          person1.sendKeys('Di');\n          person2.clear();\n          person2.sendKeys('Vojta');\n          expect(withOffset.getText()).toEqual('Di, Vojta and 2 other people are viewing.');\n        });\n      </file>\n    </example>\n */\nvar ngPluralizeDirective = ['$locale', '$interpolate', '$log', function($locale, $interpolate, $log) {\n  var BRACE = /{}/g,\n      IS_WHEN = /^when(Minus)?(.+)$/;\n\n  return {\n    link: function(scope, element, attr) {\n      var numberExp = attr.count,\n          whenExp = attr.$attr.when && element.attr(attr.$attr.when), // we have {{}} in attrs\n          offset = attr.offset || 0,\n          whens = scope.$eval(whenExp) || {},\n          whensExpFns = {},\n          startSymbol = $interpolate.startSymbol(),\n          endSymbol = $interpolate.endSymbol(),\n          braceReplacement = startSymbol + numberExp + '-' + offset + endSymbol,\n          watchRemover = angular.noop,\n          lastCount;\n\n      forEach(attr, function(expression, attributeName) {\n        var tmpMatch = IS_WHEN.exec(attributeName);\n        if (tmpMatch) {\n          var whenKey = (tmpMatch[1] ? '-' : '') + lowercase(tmpMatch[2]);\n          whens[whenKey] = element.attr(attr.$attr[attributeName]);\n        }\n      });\n      forEach(whens, function(expression, key) {\n        whensExpFns[key] = $interpolate(expression.replace(BRACE, braceReplacement));\n\n      });\n\n      scope.$watch(numberExp, function ngPluralizeWatchAction(newVal) {\n        var count = parseFloat(newVal);\n        var countIsNaN = isNumberNaN(count);\n\n        if (!countIsNaN && !(count in whens)) {\n          // If an explicit number rule such as 1, 2, 3... is defined, just use it.\n          // Otherwise, check it against pluralization rules in $locale service.\n          count = $locale.pluralCat(count - offset);\n        }\n\n        // If both `count` and `lastCount` are NaN, we don't need to re-register a watch.\n        // In JS `NaN !== NaN`, so we have to explicitly check.\n        if ((count !== lastCount) && !(countIsNaN && isNumberNaN(lastCount))) {\n          watchRemover();\n          var whenExpFn = whensExpFns[count];\n          if (isUndefined(whenExpFn)) {\n            if (newVal != null) {\n              $log.debug('ngPluralize: no rule defined for \\'' + count + '\\' in ' + whenExp);\n            }\n            watchRemover = noop;\n            updateElementText();\n          } else {\n            watchRemover = scope.$watch(whenExpFn, updateElementText);\n          }\n          lastCount = count;\n        }\n      });\n\n      function updateElementText(newText) {\n        element.text(newText || '');\n      }\n    }\n  };\n}];\n\n/**\n * @ngdoc directive\n * @name ngRef\n * @restrict A\n *\n * @description\n * The `ngRef` attribute tells AngularJS to assign the controller of a component (or a directive)\n * to the given property in the current scope. It is also possible to add the jqlite-wrapped DOM\n * element to the scope.\n *\n * If the element with `ngRef` is destroyed `null` is assigned to the property.\n *\n * Note that if you want to assign from a child into the parent scope, you must initialize the\n * target property on the parent scope, otherwise `ngRef` will assign on the child scope.\n * This commonly happens when assigning elements or components wrapped in {@link ngIf} or\n * {@link ngRepeat}. See the second example below.\n *\n *\n * @element ANY\n * @param {string} ngRef property name - A valid AngularJS expression identifier to which the\n *                       controller or jqlite-wrapped DOM element will be bound.\n * @param {string=} ngRefRead read value - The name of a directive (or component) on this element,\n *                            or the special string `$element`. If a name is provided, `ngRef` will\n *                            assign the matching controller. If `$element` is provided, the element\n *                            itself is assigned (even if a controller is available).\n *\n *\n * @example\n * ### Simple toggle\n * This example shows how the controller of the component toggle\n * is reused in the template through the scope to use its logic.\n * <example name=\"ng-ref-component\" module=\"myApp\">\n *   <file name=\"index.html\">\n *     <my-toggle ng-ref=\"myToggle\"></my-toggle>\n *     <button ng-click=\"myToggle.toggle()\">Toggle</button>\n *     <div ng-show=\"myToggle.isOpen()\">\n *       You are using a component in the same template to show it.\n *     </div>\n *   </file>\n *   <file name=\"index.js\">\n *     angular.module('myApp', [])\n *     .component('myToggle', {\n *       controller: function ToggleController() {\n *         var opened = false;\n *         this.isOpen = function() { return opened; };\n *         this.toggle = function() { opened = !opened; };\n *       }\n *     });\n *   </file>\n *   <file name=\"protractor.js\" type=\"protractor\">\n *      it('should publish the toggle into the scope', function() {\n *        var toggle = element(by.buttonText('Toggle'));\n *        expect(toggle.evaluate('myToggle.isOpen()')).toEqual(false);\n *        toggle.click();\n *        expect(toggle.evaluate('myToggle.isOpen()')).toEqual(true);\n *      });\n *   </file>\n * </example>\n *\n * @example\n * ### ngRef inside scopes\n * This example shows how `ngRef` works with child scopes. The `ngRepeat`-ed `myWrapper` components\n * are assigned to the scope of `myRoot`, because the `toggles` property has been initialized.\n * The repeated `myToggle` components are published to the child scopes created by `ngRepeat`.\n * `ngIf` behaves similarly - the assignment of `myToggle` happens in the `ngIf` child scope,\n * because the target property has not been initialized on the `myRoot` component controller.\n *\n * <example name=\"ng-ref-scopes\" module=\"myApp\">\n *   <file name=\"index.html\">\n *     <my-root></my-root>\n *   </file>\n *   <file name=\"index.js\">\n *     angular.module('myApp', [])\n *     .component('myRoot', {\n *       templateUrl: 'root.html',\n *       controller: function() {\n *         this.wrappers = []; // initialize the array so that the wrappers are assigned into the parent scope\n *       }\n *     })\n *     .component('myToggle', {\n *       template: '<strong>myToggle</strong><button ng-click=\"$ctrl.toggle()\" ng-transclude></button>',\n *       transclude: true,\n *       controller: function ToggleController() {\n *         var opened = false;\n *         this.isOpen = function() { return opened; };\n *         this.toggle = function() { opened = !opened; };\n *       }\n *     })\n *     .component('myWrapper', {\n *       transclude: true,\n *       template: '<strong>myWrapper</strong>' +\n *         '<div>ngRepeatToggle.isOpen(): {{$ctrl.ngRepeatToggle.isOpen() | json}}</div>' +\n *         '<my-toggle ng-ref=\"$ctrl.ngRepeatToggle\"><ng-transclude></ng-transclude></my-toggle>'\n *     });\n *   </file>\n *   <file name=\"root.html\">\n *     <strong>myRoot</strong>\n *     <my-toggle ng-ref=\"$ctrl.outerToggle\">Outer Toggle</my-toggle>\n *     <div>outerToggle.isOpen(): {{$ctrl.outerToggle.isOpen() | json}}</div>\n *     <div><em>wrappers assigned to root</em><br>\n *     <div ng-repeat=\"wrapper in $ctrl.wrappers\">\n *       wrapper.ngRepeatToggle.isOpen(): {{wrapper.ngRepeatToggle.isOpen() | json}}\n *     </div>\n *\n *     <ul>\n *       <li ng-repeat=\"(index, value) in [1,2,3]\">\n *         <strong>ngRepeat</strong>\n *         <div>outerToggle.isOpen(): {{$ctrl.outerToggle.isOpen() | json}}</div>\n *         <my-wrapper ng-ref=\"$ctrl.wrappers[index]\">ngRepeat Toggle {{$index + 1}}</my-wrapper>\n *       </li>\n *     </ul>\n *\n *     <div>ngIfToggle.isOpen(): {{ngIfToggle.isOpen()}} // This is always undefined because it's\n *       assigned to the child scope created by ngIf.\n *     </div>\n *     <div ng-if=\"true\">\n          <strong>ngIf</strong>\n *        <my-toggle ng-ref=\"ngIfToggle\">ngIf Toggle</my-toggle>\n *        <div>ngIfToggle.isOpen(): {{ngIfToggle.isOpen() | json}}</div>\n *        <div>outerToggle.isOpen(): {{$ctrl.outerToggle.isOpen() | json}}</div>\n *     </div>\n *   </file>\n *   <file name=\"styles.css\">\n *     ul {\n *       list-style: none;\n *       padding-left: 0;\n *     }\n *\n *     li[ng-repeat] {\n *       background: lightgreen;\n *       padding: 8px;\n *       margin: 8px;\n *     }\n *\n *     [ng-if] {\n *       background: lightgrey;\n *       padding: 8px;\n *     }\n *\n *     my-root {\n *       background: lightgoldenrodyellow;\n *       padding: 8px;\n *       display: block;\n *     }\n *\n *     my-wrapper {\n *       background: lightsalmon;\n *       padding: 8px;\n *       display: block;\n *     }\n *\n *     my-toggle {\n *       background: lightblue;\n *       padding: 8px;\n *       display: block;\n *     }\n *   </file>\n *   <file name=\"protractor.js\" type=\"protractor\">\n *      var OuterToggle = function() {\n *        this.toggle = function() {\n *          element(by.buttonText('Outer Toggle')).click();\n *        };\n *        this.isOpen = function() {\n *          return element.all(by.binding('outerToggle.isOpen()')).first().getText();\n *        };\n *      };\n *      var NgRepeatToggle = function(i) {\n *        var parent = element.all(by.repeater('(index, value) in [1,2,3]')).get(i - 1);\n *        this.toggle = function() {\n *          element(by.buttonText('ngRepeat Toggle ' + i)).click();\n *        };\n *        this.isOpen = function() {\n *          return parent.element(by.binding('ngRepeatToggle.isOpen() | json')).getText();\n *        };\n *        this.isOuterOpen = function() {\n *          return parent.element(by.binding('outerToggle.isOpen() | json')).getText();\n *        };\n *      };\n *      var NgRepeatToggles = function() {\n *        var toggles = [1,2,3].map(function(i) { return new NgRepeatToggle(i); });\n *        this.forEach = function(fn) {\n *          toggles.forEach(fn);\n *        };\n *        this.isOuterOpen = function(i) {\n *          return toggles[i - 1].isOuterOpen();\n *        };\n *      };\n *      var NgIfToggle = function() {\n *        var parent = element(by.css('[ng-if]'));\n *        this.toggle = function() {\n *          element(by.buttonText('ngIf Toggle')).click();\n *        };\n *        this.isOpen = function() {\n *          return by.binding('ngIfToggle.isOpen() | json').getText();\n *        };\n *        this.isOuterOpen = function() {\n *          return parent.element(by.binding('outerToggle.isOpen() | json')).getText();\n *        };\n *      };\n *\n *      it('should toggle the outer toggle', function() {\n *        var outerToggle = new OuterToggle();\n *        expect(outerToggle.isOpen()).toEqual('outerToggle.isOpen(): false');\n *        outerToggle.toggle();\n *        expect(outerToggle.isOpen()).toEqual('outerToggle.isOpen(): true');\n *      });\n *\n *      it('should toggle all outer toggles', function() {\n *        var outerToggle = new OuterToggle();\n *        var repeatToggles = new NgRepeatToggles();\n *        var ifToggle = new NgIfToggle();\n *        expect(outerToggle.isOpen()).toEqual('outerToggle.isOpen(): false');\n *        expect(repeatToggles.isOuterOpen(1)).toEqual('outerToggle.isOpen(): false');\n *        expect(repeatToggles.isOuterOpen(2)).toEqual('outerToggle.isOpen(): false');\n *        expect(repeatToggles.isOuterOpen(3)).toEqual('outerToggle.isOpen(): false');\n *        expect(ifToggle.isOuterOpen()).toEqual('outerToggle.isOpen(): false');\n *        outerToggle.toggle();\n *        expect(outerToggle.isOpen()).toEqual('outerToggle.isOpen(): true');\n *        expect(repeatToggles.isOuterOpen(1)).toEqual('outerToggle.isOpen(): true');\n *        expect(repeatToggles.isOuterOpen(2)).toEqual('outerToggle.isOpen(): true');\n *        expect(repeatToggles.isOuterOpen(3)).toEqual('outerToggle.isOpen(): true');\n *        expect(ifToggle.isOuterOpen()).toEqual('outerToggle.isOpen(): true');\n *      });\n *\n *      it('should toggle each repeat iteration separately', function() {\n *        var repeatToggles = new NgRepeatToggles();\n *\n *        repeatToggles.forEach(function(repeatToggle) {\n *          expect(repeatToggle.isOpen()).toEqual('ngRepeatToggle.isOpen(): false');\n *          expect(repeatToggle.isOuterOpen()).toEqual('outerToggle.isOpen(): false');\n *          repeatToggle.toggle();\n *          expect(repeatToggle.isOpen()).toEqual('ngRepeatToggle.isOpen(): true');\n *          expect(repeatToggle.isOuterOpen()).toEqual('outerToggle.isOpen(): false');\n *        });\n *      });\n *   </file>\n * </example>\n *\n */\n\nvar ngRefMinErr = minErr('ngRef');\n\nvar ngRefDirective = ['$parse', function($parse) {\n  return {\n    priority: -1, // Needed for compatibility with element transclusion on the same element\n    restrict: 'A',\n    compile: function(tElement, tAttrs) {\n      // Get the expected controller name, converts <data-some-thing> into \"someThing\"\n      var controllerName = directiveNormalize(nodeName_(tElement));\n\n      // Get the expression for value binding\n      var getter = $parse(tAttrs.ngRef);\n      var setter = getter.assign || function() {\n        throw ngRefMinErr('nonassign', 'Expression in ngRef=\"{0}\" is non-assignable!', tAttrs.ngRef);\n      };\n\n      return function(scope, element, attrs) {\n        var refValue;\n\n        if (attrs.hasOwnProperty('ngRefRead')) {\n          if (attrs.ngRefRead === '$element') {\n            refValue = element;\n          } else {\n            refValue = element.data('$' + attrs.ngRefRead + 'Controller');\n\n            if (!refValue) {\n              throw ngRefMinErr(\n                'noctrl',\n                'The controller for ngRefRead=\"{0}\" could not be found on ngRef=\"{1}\"',\n                attrs.ngRefRead,\n                tAttrs.ngRef\n              );\n            }\n          }\n        } else {\n          refValue = element.data('$' + controllerName + 'Controller');\n        }\n\n        refValue = refValue || element;\n\n        setter(scope, refValue);\n\n        // when the element is removed, remove it (nullify it)\n        element.on('$destroy', function() {\n          // only remove it if value has not changed,\n          // because animations (and other procedures) may duplicate elements\n          if (getter(scope) === refValue) {\n            setter(scope, null);\n          }\n        });\n      };\n    }\n  };\n}];\n\n/* exported ngRepeatDirective */\n\n/**\n * @ngdoc directive\n * @name ngRepeat\n * @multiElement\n * @restrict A\n *\n * @description\n * The `ngRepeat` directive instantiates a template once per item from a collection. Each template\n * instance gets its own scope, where the given loop variable is set to the current collection item,\n * and `$index` is set to the item index or key.\n *\n * Special properties are exposed on the local scope of each template instance, including:\n *\n * | Variable  | Type            | Details                                                                     |\n * |-----------|-----------------|-----------------------------------------------------------------------------|\n * | `$index`  | {@type number}  | iterator offset of the repeated element (0..length-1)                       |\n * | `$first`  | {@type boolean} | true if the repeated element is first in the iterator.                      |\n * | `$middle` | {@type boolean} | true if the repeated element is between the first and last in the iterator. |\n * | `$last`   | {@type boolean} | true if the repeated element is last in the iterator.                       |\n * | `$even`   | {@type boolean} | true if the iterator position `$index` is even (otherwise false).           |\n * | `$odd`    | {@type boolean} | true if the iterator position `$index` is odd (otherwise false).            |\n *\n * <div class=\"alert alert-info\">\n *   Creating aliases for these properties is possible with {@link ng.directive:ngInit `ngInit`}.\n *   This may be useful when, for instance, nesting ngRepeats.\n * </div>\n *\n *\n * ## Iterating over object properties\n *\n * It is possible to get `ngRepeat` to iterate over the properties of an object using the following\n * syntax:\n *\n * ```js\n * <div ng-repeat=\"(key, value) in myObj\"> ... </div>\n * ```\n *\n * However, there are a few limitations compared to array iteration:\n *\n * - The JavaScript specification does not define the order of keys\n *   returned for an object, so AngularJS relies on the order returned by the browser\n *   when running `for key in myObj`. Browsers generally follow the strategy of providing\n *   keys in the order in which they were defined, although there are exceptions when keys are deleted\n *   and reinstated. See the\n *   [MDN page on `delete` for more info](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Operators/delete#Cross-browser_notes).\n *\n * - `ngRepeat` will silently *ignore* object keys starting with `$`, because\n *   it's a prefix used by AngularJS for public (`$`) and private (`$$`) properties.\n *\n * - The built-in filters {@link ng.orderBy orderBy} and {@link ng.filter filter} do not work with\n *   objects, and will throw an error if used with one.\n *\n * If you are hitting any of these limitations, the recommended workaround is to convert your object into an array\n * that is sorted into the order that you prefer before providing it to `ngRepeat`. You could\n * do this with a filter such as [toArrayFilter](http://ngmodules.org/modules/angular-toArrayFilter)\n * or implement a `$watch` on the object yourself.\n *\n *\n * ## Tracking and Duplicates\n *\n * `ngRepeat` uses {@link $rootScope.Scope#$watchCollection $watchCollection} to detect changes in\n * the collection. When a change happens, `ngRepeat` then makes the corresponding changes to the DOM:\n *\n * * When an item is added, a new instance of the template is added to the DOM.\n * * When an item is removed, its template instance is removed from the DOM.\n * * When items are reordered, their respective templates are reordered in the DOM.\n *\n * To minimize creation of DOM elements, `ngRepeat` uses a function\n * to \"keep track\" of all items in the collection and their corresponding DOM elements.\n * For example, if an item is added to the collection, `ngRepeat` will know that all other items\n * already have DOM elements, and will not re-render them.\n *\n * All different types of tracking functions, their syntax, and their support for duplicate\n * items in collections can be found in the\n * {@link ngRepeat#ngRepeat-arguments ngRepeat expression description}.\n *\n * <div class=\"alert alert-success\">\n * **Best Practice:** If you are working with objects that have a unique identifier property, you\n * should track by this identifier instead of the object instance,\n * e.g. `item in items track by item.id`.\n * Should you reload your data later, `ngRepeat` will not have to rebuild the DOM elements for items\n * it has already rendered, even if the JavaScript objects in the collection have been substituted\n * for new ones. For large collections, this significantly improves rendering performance.\n * </div>\n *\n * ### Effects of DOM Element re-use\n *\n * When DOM elements are re-used, ngRepeat updates the scope for the element, which will\n * automatically update any active bindings on the template. However, other\n * functionality will not be updated, because the element is not re-created:\n *\n * - Directives are not re-compiled\n * - {@link guide/expression#one-time-binding one-time expressions} on the repeated template are not\n * updated if they have stabilized.\n *\n * The above affects all kinds of element re-use due to tracking, but may be especially visible\n * when tracking by `$index` due to the way ngRepeat re-uses elements.\n *\n * The following example shows the effects of different actions with tracking:\n\n  <example module=\"ngRepeat\" name=\"ngRepeat-tracking\" deps=\"angular-animate.js\" animations=\"true\">\n    <file name=\"script.js\">\n      angular.module('ngRepeat', ['ngAnimate']).controller('repeatController', function($scope) {\n        var friends = [\n          {name:'John', age:25},\n          {name:'Mary', age:40},\n          {name:'Peter', age:85}\n        ];\n\n        $scope.removeFirst = function() {\n          $scope.friends.shift();\n        };\n\n        $scope.updateAge = function() {\n          $scope.friends.forEach(function(el) {\n            el.age = el.age + 5;\n          });\n        };\n\n        $scope.copy = function() {\n          $scope.friends = angular.copy($scope.friends);\n        };\n\n        $scope.reset = function() {\n          $scope.friends = angular.copy(friends);\n        };\n\n        $scope.reset();\n      });\n    </file>\n    <file name=\"index.html\">\n      <div ng-controller=\"repeatController\">\n        <ol>\n          <li>When you click \"Update Age\", only the first list updates the age, because all others have\n          a one-time binding on the age property. If you then click \"Copy\", the current friend list\n          is copied, and now the second list updates the age, because the identity of the collection items\n          has changed and the list must be re-rendered. The 3rd and 4th list stay the same, because all the\n          items are already known according to their tracking functions.\n          </li>\n          <li>When you click \"Remove First\", the 4th list has the wrong age on both remaining items. This is\n          due to tracking by $index: when the first collection item is removed, ngRepeat reuses the first\n          DOM element for the new first collection item, and so on. Since the age property is one-time\n          bound, the value remains from the collection item which was previously at this index.\n          </li>\n        </ol>\n\n        <button ng-click=\"removeFirst()\">Remove First</button>\n        <button ng-click=\"updateAge()\">Update Age</button>\n        <button ng-click=\"copy()\">Copy</button>\n        <br><button ng-click=\"reset()\">Reset List</button>\n        <br>\n        <code>track by $id(friend)</code> (default):\n        <ul class=\"example-animate-container\">\n          <li class=\"animate-repeat\" ng-repeat=\"friend in friends\">\n            {{friend.name}} is {{friend.age}} years old.\n          </li>\n        </ul>\n        <code>track by $id(friend)</code> (default), with age one-time binding:\n        <ul class=\"example-animate-container\">\n          <li class=\"animate-repeat\" ng-repeat=\"friend in friends\">\n            {{friend.name}} is {{::friend.age}} years old.\n          </li>\n        </ul>\n        <code>track by friend.name</code>, with age one-time binding:\n        <ul class=\"example-animate-container\">\n          <li class=\"animate-repeat\" ng-repeat=\"friend in friends track by friend.name\">\n            {{friend.name}}  is {{::friend.age}} years old.\n          </li>\n        </ul>\n        <code>track by $index</code>, with age one-time binding:\n        <ul class=\"example-animate-container\">\n          <li class=\"animate-repeat\" ng-repeat=\"friend in friends track by $index\">\n            {{friend.name}} is {{::friend.age}} years old.\n          </li>\n        </ul>\n      </div>\n    </file>\n    <file name=\"animations.css\">\n      .example-animate-container {\n        background:white;\n        border:1px solid black;\n        list-style:none;\n        margin:0;\n        padding:0 10px;\n      }\n\n      .animate-repeat {\n        line-height:30px;\n        list-style:none;\n        box-sizing:border-box;\n      }\n\n      .animate-repeat.ng-move,\n      .animate-repeat.ng-enter,\n      .animate-repeat.ng-leave {\n        transition:all linear 0.5s;\n      }\n\n      .animate-repeat.ng-leave.ng-leave-active,\n      .animate-repeat.ng-move,\n      .animate-repeat.ng-enter {\n        opacity:0;\n        max-height:0;\n      }\n\n      .animate-repeat.ng-leave,\n      .animate-repeat.ng-move.ng-move-active,\n      .animate-repeat.ng-enter.ng-enter-active {\n        opacity:1;\n        max-height:30px;\n      }\n    </file>\n  </example>\n\n *\n * ## Special repeat start and end points\n * To repeat a series of elements instead of just one parent element, ngRepeat (as well as other ng directives) supports extending\n * the range of the repeater by defining explicit start and end points by using **ng-repeat-start** and **ng-repeat-end** respectively.\n * The **ng-repeat-start** directive works the same as **ng-repeat**, but will repeat all the HTML code (including the tag it's defined on)\n * up to and including the ending HTML tag where **ng-repeat-end** is placed.\n *\n * The example below makes use of this feature:\n * ```html\n *   <header ng-repeat-start=\"item in items\">\n *     Header {{ item }}\n *   </header>\n *   <div class=\"body\">\n *     Body {{ item }}\n *   </div>\n *   <footer ng-repeat-end>\n *     Footer {{ item }}\n *   </footer>\n * ```\n *\n * And with an input of {@type ['A','B']} for the items variable in the example above, the output will evaluate to:\n * ```html\n *   <header>\n *     Header A\n *   </header>\n *   <div class=\"body\">\n *     Body A\n *   </div>\n *   <footer>\n *     Footer A\n *   </footer>\n *   <header>\n *     Header B\n *   </header>\n *   <div class=\"body\">\n *     Body B\n *   </div>\n *   <footer>\n *     Footer B\n *   </footer>\n * ```\n *\n * The custom start and end points for ngRepeat also support all other HTML directive syntax flavors provided in AngularJS (such\n * as **data-ng-repeat-start**, **x-ng-repeat-start** and **ng:repeat-start**).\n *\n * @animations\n * | Animation                        | Occurs                              |\n * |----------------------------------|-------------------------------------|\n * | {@link ng.$animate#enter enter} | when a new item is added to the list or when an item is revealed after a filter |\n * | {@link ng.$animate#leave leave} | when an item is removed from the list or when an item is filtered out |\n * | {@link ng.$animate#move move } | when an adjacent item is filtered out causing a reorder or when the item contents are reordered |\n *\n * See the example below for defining CSS animations with ngRepeat.\n *\n * @element ANY\n * @scope\n * @priority 1000\n * @param {repeat_expression} ngRepeat The expression indicating how to enumerate a collection. These\n *   formats are currently supported:\n *\n *   * `variable in expression` – where variable is the user defined loop variable and `expression`\n *     is a scope expression giving the collection to enumerate.\n *\n *     For example: `album in artist.albums`.\n *\n *   * `(key, value) in expression` – where `key` and `value` can be any user defined identifiers,\n *     and `expression` is the scope expression giving the collection to enumerate.\n *\n *     For example: `(name, age) in {'adam':10, 'amalie':12}`.\n *\n *   * `variable in expression track by tracking_expression` – You can also provide an optional tracking expression\n *     which can be used to associate the objects in the collection with the DOM elements. If no tracking expression\n *     is specified, ng-repeat associates elements by identity. It is an error to have\n *     more than one tracking expression value resolve to the same key. (This would mean that two distinct objects are\n *     mapped to the same DOM element, which is not possible.)\n *\n *     *Default tracking: $id()*: `item in items` is equivalent to `item in items track by $id(item)`.\n *     This implies that the DOM elements will be associated by item identity in the collection.\n *\n *     The built-in `$id()` function can be used to assign a unique\n *     `$$hashKey` property to each item in the collection. This property is then used as a key to associated DOM elements\n *     with the corresponding item in the collection by identity. Moving the same object would move\n *     the DOM element in the same way in the DOM.\n *     Note that the default id function does not support duplicate primitive values (`number`, `string`),\n *     but supports duplictae non-primitive values (`object`) that are *equal* in shape.\n *\n *     *Custom Expression*: It is possible to use any AngularJS expression to compute the tracking\n *     id, for example with a function, or using a property on the collection items.\n *     `item in items track by item.id` is a typical pattern when the items have a unique identifier,\n *     e.g. database id. In this case the object identity does not matter. Two objects are considered\n *     equivalent as long as their `id` property is same.\n *     Tracking by unique identifier is the most performant way and should be used whenever possible.\n *\n *     *$index*: This special property tracks the collection items by their index, and\n *     re-uses the DOM elements that match that index, e.g. `item in items track by $index`. This can\n *     be used for a performance improvement if no unique identfier is available and the identity of\n *     the collection items cannot be easily computed. It also allows duplicates.\n *\n *     <div class=\"alert alert-warning\">\n *       <strong>Note:</strong> Re-using DOM elements can have unforeseen effects. Read the\n *       {@link ngRepeat#tracking-and-duplicates section on tracking and duplicates} for\n *       more info.\n *     </div>\n *\n *     <div class=\"alert alert-warning\">\n *       <strong>Note:</strong> the `track by` expression must come last - after any filters, and the alias expression:\n *       `item in items | filter:searchText as results  track by item.id`\n *     </div>\n *\n *   * `variable in expression as alias_expression` – You can also provide an optional alias expression which will then store the\n *     intermediate results of the repeater after the filters have been applied. Typically this is used to render a special message\n *     when a filter is active on the repeater, but the filtered result set is empty.\n *\n *     For example: `item in items | filter:x as results` will store the fragment of the repeated items as `results`, but only after\n *     the items have been processed through the filter.\n *\n *     Please note that `as [variable name]` is not an operator but rather a part of ngRepeat\n *     micro-syntax so it can be used only after all filters (and not as operator, inside an expression).\n *\n *     For example: `item in items | filter : x | orderBy : order | limitTo : limit as results track by item.id` .\n *\n * @example\n * This example uses `ngRepeat` to display a list of people. A filter is used to restrict the displayed\n * results by name or by age. New (entering) and removed (leaving) items are animated.\n  <example module=\"ngRepeat\" name=\"ngRepeat\" deps=\"angular-animate.js\" animations=\"true\">\n    <file name=\"index.html\">\n      <div ng-controller=\"repeatController\">\n        I have {{friends.length}} friends. They are:\n        <input type=\"search\" ng-model=\"q\" placeholder=\"filter friends...\" aria-label=\"filter friends\" />\n        <ul class=\"example-animate-container\">\n          <li class=\"animate-repeat\" ng-repeat=\"friend in friends | filter:q as results track by friend.name\">\n            [{{$index + 1}}] {{friend.name}} who is {{friend.age}} years old.\n          </li>\n          <li class=\"animate-repeat\" ng-if=\"results.length === 0\">\n            <strong>No results found...</strong>\n          </li>\n        </ul>\n      </div>\n    </file>\n    <file name=\"script.js\">\n      angular.module('ngRepeat', ['ngAnimate']).controller('repeatController', function($scope) {\n        $scope.friends = [\n          {name:'John', age:25, gender:'boy'},\n          {name:'Jessie', age:30, gender:'girl'},\n          {name:'Johanna', age:28, gender:'girl'},\n          {name:'Joy', age:15, gender:'girl'},\n          {name:'Mary', age:28, gender:'girl'},\n          {name:'Peter', age:95, gender:'boy'},\n          {name:'Sebastian', age:50, gender:'boy'},\n          {name:'Erika', age:27, gender:'girl'},\n          {name:'Patrick', age:40, gender:'boy'},\n          {name:'Samantha', age:60, gender:'girl'}\n        ];\n      });\n    </file>\n    <file name=\"animations.css\">\n      .example-animate-container {\n        background:white;\n        border:1px solid black;\n        list-style:none;\n        margin:0;\n        padding:0 10px;\n      }\n\n      .animate-repeat {\n        line-height:30px;\n        list-style:none;\n        box-sizing:border-box;\n      }\n\n      .animate-repeat.ng-move,\n      .animate-repeat.ng-enter,\n      .animate-repeat.ng-leave {\n        transition:all linear 0.5s;\n      }\n\n      .animate-repeat.ng-leave.ng-leave-active,\n      .animate-repeat.ng-move,\n      .animate-repeat.ng-enter {\n        opacity:0;\n        max-height:0;\n      }\n\n      .animate-repeat.ng-leave,\n      .animate-repeat.ng-move.ng-move-active,\n      .animate-repeat.ng-enter.ng-enter-active {\n        opacity:1;\n        max-height:30px;\n      }\n    </file>\n    <file name=\"protractor.js\" type=\"protractor\">\n      var friends = element.all(by.repeater('friend in friends'));\n\n      it('should render initial data set', function() {\n        expect(friends.count()).toBe(10);\n        expect(friends.get(0).getText()).toEqual('[1] John who is 25 years old.');\n        expect(friends.get(1).getText()).toEqual('[2] Jessie who is 30 years old.');\n        expect(friends.last().getText()).toEqual('[10] Samantha who is 60 years old.');\n        expect(element(by.binding('friends.length')).getText())\n            .toMatch(\"I have 10 friends. They are:\");\n      });\n\n       it('should update repeater when filter predicate changes', function() {\n         expect(friends.count()).toBe(10);\n\n         element(by.model('q')).sendKeys('ma');\n\n         expect(friends.count()).toBe(2);\n         expect(friends.get(0).getText()).toEqual('[1] Mary who is 28 years old.');\n         expect(friends.last().getText()).toEqual('[2] Samantha who is 60 years old.');\n       });\n      </file>\n    </example>\n */\nvar ngRepeatDirective = ['$parse', '$animate', '$compile', function($parse, $animate, $compile) {\n  var NG_REMOVED = '$$NG_REMOVED';\n  var ngRepeatMinErr = minErr('ngRepeat');\n\n  var updateScope = function(scope, index, valueIdentifier, value, keyIdentifier, key, arrayLength) {\n    // TODO(perf): generate setters to shave off ~40ms or 1-1.5%\n    scope[valueIdentifier] = value;\n    if (keyIdentifier) scope[keyIdentifier] = key;\n    scope.$index = index;\n    scope.$first = (index === 0);\n    scope.$last = (index === (arrayLength - 1));\n    scope.$middle = !(scope.$first || scope.$last);\n    // eslint-disable-next-line no-bitwise\n    scope.$odd = !(scope.$even = (index & 1) === 0);\n  };\n\n  var getBlockStart = function(block) {\n    return block.clone[0];\n  };\n\n  var getBlockEnd = function(block) {\n    return block.clone[block.clone.length - 1];\n  };\n\n  var trackByIdArrayFn = function($scope, key, value) {\n    return hashKey(value);\n  };\n\n  var trackByIdObjFn = function($scope, key) {\n    return key;\n  };\n\n  return {\n    restrict: 'A',\n    multiElement: true,\n    transclude: 'element',\n    priority: 1000,\n    terminal: true,\n    $$tlb: true,\n    compile: function ngRepeatCompile($element, $attr) {\n      var expression = $attr.ngRepeat;\n      var ngRepeatEndComment = $compile.$$createComment('end ngRepeat', expression);\n\n      var match = expression.match(/^\\s*([\\s\\S]+?)\\s+in\\s+([\\s\\S]+?)(?:\\s+as\\s+([\\s\\S]+?))?(?:\\s+track\\s+by\\s+([\\s\\S]+?))?\\s*$/);\n\n      if (!match) {\n        throw ngRepeatMinErr('iexp', 'Expected expression in form of \\'_item_ in _collection_[ track by _id_]\\' but got \\'{0}\\'.',\n            expression);\n      }\n\n      var lhs = match[1];\n      var rhs = match[2];\n      var aliasAs = match[3];\n      var trackByExp = match[4];\n\n      match = lhs.match(/^(?:(\\s*[$\\w]+)|\\(\\s*([$\\w]+)\\s*,\\s*([$\\w]+)\\s*\\))$/);\n\n      if (!match) {\n        throw ngRepeatMinErr('iidexp', '\\'_item_\\' in \\'_item_ in _collection_\\' should be an identifier or \\'(_key_, _value_)\\' expression, but got \\'{0}\\'.',\n            lhs);\n      }\n      var valueIdentifier = match[3] || match[1];\n      var keyIdentifier = match[2];\n\n      if (aliasAs && (!/^[$a-zA-Z_][$a-zA-Z0-9_]*$/.test(aliasAs) ||\n          /^(null|undefined|this|\\$index|\\$first|\\$middle|\\$last|\\$even|\\$odd|\\$parent|\\$root|\\$id)$/.test(aliasAs))) {\n        throw ngRepeatMinErr('badident', 'alias \\'{0}\\' is invalid --- must be a valid JS identifier which is not a reserved name.',\n          aliasAs);\n      }\n\n      var trackByIdExpFn;\n\n      if (trackByExp) {\n        var hashFnLocals = {$id: hashKey};\n        var trackByExpGetter = $parse(trackByExp);\n\n        trackByIdExpFn = function($scope, key, value, index) {\n          // assign key, value, and $index to the locals so that they can be used in hash functions\n          if (keyIdentifier) hashFnLocals[keyIdentifier] = key;\n          hashFnLocals[valueIdentifier] = value;\n          hashFnLocals.$index = index;\n          return trackByExpGetter($scope, hashFnLocals);\n        };\n      }\n\n      return function ngRepeatLink($scope, $element, $attr, ctrl, $transclude) {\n\n        // Store a list of elements from previous run. This is a hash where key is the item from the\n        // iterator, and the value is objects with following properties.\n        //   - scope: bound scope\n        //   - clone: previous element.\n        //   - index: position\n        //\n        // We are using no-proto object so that we don't need to guard against inherited props via\n        // hasOwnProperty.\n        var lastBlockMap = createMap();\n\n        //watch props\n        $scope.$watchCollection(rhs, function ngRepeatAction(collection) {\n          var index, length,\n              previousNode = $element[0],     // node that cloned nodes should be inserted after\n                                              // initialized to the comment node anchor\n              nextNode,\n              // Same as lastBlockMap but it has the current state. It will become the\n              // lastBlockMap on the next iteration.\n              nextBlockMap = createMap(),\n              collectionLength,\n              key, value, // key/value of iteration\n              trackById,\n              trackByIdFn,\n              collectionKeys,\n              block,       // last object information {scope, element, id}\n              nextBlockOrder,\n              elementsToRemove;\n\n          if (aliasAs) {\n            $scope[aliasAs] = collection;\n          }\n\n          if (isArrayLike(collection)) {\n            collectionKeys = collection;\n            trackByIdFn = trackByIdExpFn || trackByIdArrayFn;\n          } else {\n            trackByIdFn = trackByIdExpFn || trackByIdObjFn;\n            // if object, extract keys, in enumeration order, unsorted\n            collectionKeys = [];\n            for (var itemKey in collection) {\n              if (hasOwnProperty.call(collection, itemKey) && itemKey.charAt(0) !== '$') {\n                collectionKeys.push(itemKey);\n              }\n            }\n          }\n\n          collectionLength = collectionKeys.length;\n          nextBlockOrder = new Array(collectionLength);\n\n          // locate existing items\n          for (index = 0; index < collectionLength; index++) {\n            key = (collection === collectionKeys) ? index : collectionKeys[index];\n            value = collection[key];\n            trackById = trackByIdFn($scope, key, value, index);\n            if (lastBlockMap[trackById]) {\n              // found previously seen block\n              block = lastBlockMap[trackById];\n              delete lastBlockMap[trackById];\n              nextBlockMap[trackById] = block;\n              nextBlockOrder[index] = block;\n            } else if (nextBlockMap[trackById]) {\n              // if collision detected. restore lastBlockMap and throw an error\n              forEach(nextBlockOrder, function(block) {\n                if (block && block.scope) lastBlockMap[block.id] = block;\n              });\n              throw ngRepeatMinErr('dupes',\n                  'Duplicates in a repeater are not allowed. Use \\'track by\\' expression to specify unique keys. Repeater: {0}, Duplicate key: {1}, Duplicate value: {2}',\n                  expression, trackById, value);\n            } else {\n              // new never before seen block\n              nextBlockOrder[index] = {id: trackById, scope: undefined, clone: undefined};\n              nextBlockMap[trackById] = true;\n            }\n          }\n\n          // Clear the value property from the hashFnLocals object to prevent a reference to the last value\n          // being leaked into the ngRepeatCompile function scope\n          if (hashFnLocals) {\n            hashFnLocals[valueIdentifier] = undefined;\n          }\n\n          // remove leftover items\n          for (var blockKey in lastBlockMap) {\n            block = lastBlockMap[blockKey];\n            elementsToRemove = getBlockNodes(block.clone);\n            $animate.leave(elementsToRemove);\n            if (elementsToRemove[0].parentNode) {\n              // if the element was not removed yet because of pending animation, mark it as deleted\n              // so that we can ignore it later\n              for (index = 0, length = elementsToRemove.length; index < length; index++) {\n                elementsToRemove[index][NG_REMOVED] = true;\n              }\n            }\n            block.scope.$destroy();\n          }\n\n          // we are not using forEach for perf reasons (trying to avoid #call)\n          for (index = 0; index < collectionLength; index++) {\n            key = (collection === collectionKeys) ? index : collectionKeys[index];\n            value = collection[key];\n            block = nextBlockOrder[index];\n\n            if (block.scope) {\n              // if we have already seen this object, then we need to reuse the\n              // associated scope/element\n\n              nextNode = previousNode;\n\n              // skip nodes that are already pending removal via leave animation\n              do {\n                nextNode = nextNode.nextSibling;\n              } while (nextNode && nextNode[NG_REMOVED]);\n\n              if (getBlockStart(block) !== nextNode) {\n                // existing item which got moved\n                $animate.move(getBlockNodes(block.clone), null, previousNode);\n              }\n              previousNode = getBlockEnd(block);\n              updateScope(block.scope, index, valueIdentifier, value, keyIdentifier, key, collectionLength);\n            } else {\n              // new item which we don't know about\n              $transclude(function ngRepeatTransclude(clone, scope) {\n                block.scope = scope;\n                // http://jsperf.com/clone-vs-createcomment\n                var endNode = ngRepeatEndComment.cloneNode(false);\n                clone[clone.length++] = endNode;\n\n                $animate.enter(clone, null, previousNode);\n                previousNode = endNode;\n                // Note: We only need the first/last node of the cloned nodes.\n                // However, we need to keep the reference to the jqlite wrapper as it might be changed later\n                // by a directive with templateUrl when its template arrives.\n                block.clone = clone;\n                nextBlockMap[block.id] = block;\n                updateScope(block.scope, index, valueIdentifier, value, keyIdentifier, key, collectionLength);\n              });\n            }\n          }\n          lastBlockMap = nextBlockMap;\n        });\n      };\n    }\n  };\n}];\n\nvar NG_HIDE_CLASS = 'ng-hide';\nvar NG_HIDE_IN_PROGRESS_CLASS = 'ng-hide-animate';\n/**\n * @ngdoc directive\n * @name ngShow\n * @multiElement\n *\n * @description\n * The `ngShow` directive shows or hides the given HTML element based on the expression provided to\n * the `ngShow` attribute.\n *\n * The element is shown or hidden by removing or adding the `.ng-hide` CSS class onto the element.\n * The `.ng-hide` CSS class is predefined in AngularJS and sets the display style to none (using an\n * `!important` flag). For CSP mode please add `angular-csp.css` to your HTML file (see\n * {@link ng.directive:ngCsp ngCsp}).\n *\n * ```html\n * <!-- when $scope.myValue is truthy (element is visible) -->\n * <div ng-show=\"myValue\"></div>\n *\n * <!-- when $scope.myValue is falsy (element is hidden) -->\n * <div ng-show=\"myValue\" class=\"ng-hide\"></div>\n * ```\n *\n * When the `ngShow` expression evaluates to a falsy value then the `.ng-hide` CSS class is added\n * to the class attribute on the element causing it to become hidden. When truthy, the `.ng-hide`\n * CSS class is removed from the element causing the element not to appear hidden.\n *\n * ## Why is `!important` used?\n *\n * You may be wondering why `!important` is used for the `.ng-hide` CSS class. This is because the\n * `.ng-hide` selector can be easily overridden by heavier selectors. For example, something as\n * simple as changing the display style on a HTML list item would make hidden elements appear\n * visible. This also becomes a bigger issue when dealing with CSS frameworks.\n *\n * By using `!important`, the show and hide behavior will work as expected despite any clash between\n * CSS selector specificity (when `!important` isn't used with any conflicting styles). If a\n * developer chooses to override the styling to change how to hide an element then it is just a\n * matter of using `!important` in their own CSS code.\n *\n * ### Overriding `.ng-hide`\n *\n * By default, the `.ng-hide` class will style the element with `display: none !important`. If you\n * wish to change the hide behavior with `ngShow`/`ngHide`, you can simply overwrite the styles for\n * the `.ng-hide` CSS class. Note that the selector that needs to be used is actually\n * `.ng-hide:not(.ng-hide-animate)` to cope with extra animation classes that can be added.\n *\n * ```css\n * .ng-hide:not(.ng-hide-animate) {\n *   /&#42; These are just alternative ways of hiding an element &#42;/\n *   display: block!important;\n *   position: absolute;\n *   top: -9999px;\n *   left: -9999px;\n * }\n * ```\n *\n * By default you don't need to override anything in CSS and the animations will work around the\n * display style.\n *\n * @animations\n * | Animation                                           | Occurs                                                                                                        |\n * |-----------------------------------------------------|---------------------------------------------------------------------------------------------------------------|\n * | {@link $animate#addClass addClass} `.ng-hide`       | After the `ngShow` expression evaluates to a non truthy value and just before the contents are set to hidden. |\n * | {@link $animate#removeClass removeClass} `.ng-hide` | After the `ngShow` expression evaluates to a truthy value and just before contents are set to visible.        |\n *\n * Animations in `ngShow`/`ngHide` work with the show and hide events that are triggered when the\n * directive expression is true and false. This system works like the animation system present with\n * `ngClass` except that you must also include the `!important` flag to override the display\n * property so that the elements are not actually hidden during the animation.\n *\n * ```css\n * /&#42; A working example can be found at the bottom of this page. &#42;/\n * .my-element.ng-hide-add, .my-element.ng-hide-remove {\n *   transition: all 0.5s linear;\n * }\n *\n * .my-element.ng-hide-add { ... }\n * .my-element.ng-hide-add.ng-hide-add-active { ... }\n * .my-element.ng-hide-remove { ... }\n * .my-element.ng-hide-remove.ng-hide-remove-active { ... }\n * ```\n *\n * Keep in mind that, as of AngularJS version 1.3, there is no need to change the display property\n * to block during animation states - ngAnimate will automatically handle the style toggling for you.\n *\n * @element ANY\n * @param {expression} ngShow If the {@link guide/expression expression} is truthy/falsy then the\n *                            element is shown/hidden respectively.\n *\n * @example\n * A simple example, animating the element's opacity:\n *\n  <example module=\"ngAnimate\" deps=\"angular-animate.js\" animations=\"true\" name=\"ng-show-simple\">\n    <file name=\"index.html\">\n      Show: <input type=\"checkbox\" ng-model=\"checked\" aria-label=\"Toggle ngShow\"><br />\n      <div class=\"check-element animate-show-hide\" ng-show=\"checked\">\n        I show up when your checkbox is checked.\n      </div>\n    </file>\n    <file name=\"animations.css\">\n      .animate-show-hide.ng-hide {\n        opacity: 0;\n      }\n\n      .animate-show-hide.ng-hide-add,\n      .animate-show-hide.ng-hide-remove {\n        transition: all linear 0.5s;\n      }\n\n      .check-element {\n        border: 1px solid black;\n        opacity: 1;\n        padding: 10px;\n      }\n    </file>\n    <file name=\"protractor.js\" type=\"protractor\">\n      it('should check ngShow', function() {\n        var checkbox = element(by.model('checked'));\n        var checkElem = element(by.css('.check-element'));\n\n        expect(checkElem.isDisplayed()).toBe(false);\n        checkbox.click();\n        expect(checkElem.isDisplayed()).toBe(true);\n      });\n    </file>\n  </example>\n *\n * <hr />\n * @example\n * A more complex example, featuring different show/hide animations:\n *\n  <example module=\"ngAnimate\" deps=\"angular-animate.js\" animations=\"true\" name=\"ng-show-complex\">\n    <file name=\"index.html\">\n      Show: <input type=\"checkbox\" ng-model=\"checked\" aria-label=\"Toggle ngShow\"><br />\n      <div class=\"check-element funky-show-hide\" ng-show=\"checked\">\n        I show up when your checkbox is checked.\n      </div>\n    </file>\n    <file name=\"animations.css\">\n      body {\n        overflow: hidden;\n        perspective: 1000px;\n      }\n\n      .funky-show-hide.ng-hide-add {\n        transform: rotateZ(0);\n        transform-origin: right;\n        transition: all 0.5s ease-in-out;\n      }\n\n      .funky-show-hide.ng-hide-add.ng-hide-add-active {\n        transform: rotateZ(-135deg);\n      }\n\n      .funky-show-hide.ng-hide-remove {\n        transform: rotateY(90deg);\n        transform-origin: left;\n        transition: all 0.5s ease;\n      }\n\n      .funky-show-hide.ng-hide-remove.ng-hide-remove-active {\n        transform: rotateY(0);\n      }\n\n      .check-element {\n        border: 1px solid black;\n        opacity: 1;\n        padding: 10px;\n      }\n    </file>\n    <file name=\"protractor.js\" type=\"protractor\">\n      it('should check ngShow', function() {\n        var checkbox = element(by.model('checked'));\n        var checkElem = element(by.css('.check-element'));\n\n        expect(checkElem.isDisplayed()).toBe(false);\n        checkbox.click();\n        expect(checkElem.isDisplayed()).toBe(true);\n      });\n    </file>\n  </example>\n *\n * @knownIssue\n *\n * ### Flickering when using ngShow to toggle between elements\n *\n * When using {@link ngShow} and / or {@link ngHide} to toggle between elements, it can\n * happen that both the element to show and the element to hide are visible for a very short time.\n *\n * This usually happens when the {@link ngAnimate ngAnimate module} is included, but no actual animations\n * are defined for {@link ngShow} / {@link ngHide}. Internet Explorer is affected more often than\n * other browsers.\n *\n * There are several way to mitigate this problem:\n *\n * - {@link guide/animations#how-to-selectively-enable-disable-and-skip-animations Disable animations on the affected elements}.\n * - Use {@link ngIf} or {@link ngSwitch} instead of {@link ngShow} / {@link ngHide}.\n * - Use the special CSS selector `ng-hide.ng-hide-animate` to set `{display: none}` or similar on the affected elements.\n * - Use `ng-class=\"{'ng-hide': expression}` instead of instead of {@link ngShow} / {@link ngHide}.\n * - Define an animation on the affected elements.\n */\nvar ngShowDirective = ['$animate', function($animate) {\n  return {\n    restrict: 'A',\n    multiElement: true,\n    link: function(scope, element, attr) {\n      scope.$watch(attr.ngShow, function ngShowWatchAction(value) {\n        // we're adding a temporary, animation-specific class for ng-hide since this way\n        // we can control when the element is actually displayed on screen without having\n        // to have a global/greedy CSS selector that breaks when other animations are run.\n        // Read: https://github.com/angular/angular.js/issues/9103#issuecomment-58335845\n        $animate[value ? 'removeClass' : 'addClass'](element, NG_HIDE_CLASS, {\n          tempClasses: NG_HIDE_IN_PROGRESS_CLASS\n        });\n      });\n    }\n  };\n}];\n\n\n/**\n * @ngdoc directive\n * @name ngHide\n * @multiElement\n *\n * @description\n * The `ngHide` directive shows or hides the given HTML element based on the expression provided to\n * the `ngHide` attribute.\n *\n * The element is shown or hidden by removing or adding the `.ng-hide` CSS class onto the element.\n * The `.ng-hide` CSS class is predefined in AngularJS and sets the display style to none (using an\n * `!important` flag). For CSP mode please add `angular-csp.css` to your HTML file (see\n * {@link ng.directive:ngCsp ngCsp}).\n *\n * ```html\n * <!-- when $scope.myValue is truthy (element is hidden) -->\n * <div ng-hide=\"myValue\" class=\"ng-hide\"></div>\n *\n * <!-- when $scope.myValue is falsy (element is visible) -->\n * <div ng-hide=\"myValue\"></div>\n * ```\n *\n * When the `ngHide` expression evaluates to a truthy value then the `.ng-hide` CSS class is added\n * to the class attribute on the element causing it to become hidden. When falsy, the `.ng-hide`\n * CSS class is removed from the element causing the element not to appear hidden.\n *\n * ## Why is `!important` used?\n *\n * You may be wondering why `!important` is used for the `.ng-hide` CSS class. This is because the\n * `.ng-hide` selector can be easily overridden by heavier selectors. For example, something as\n * simple as changing the display style on a HTML list item would make hidden elements appear\n * visible. This also becomes a bigger issue when dealing with CSS frameworks.\n *\n * By using `!important`, the show and hide behavior will work as expected despite any clash between\n * CSS selector specificity (when `!important` isn't used with any conflicting styles). If a\n * developer chooses to override the styling to change how to hide an element then it is just a\n * matter of using `!important` in their own CSS code.\n *\n * ### Overriding `.ng-hide`\n *\n * By default, the `.ng-hide` class will style the element with `display: none !important`. If you\n * wish to change the hide behavior with `ngShow`/`ngHide`, you can simply overwrite the styles for\n * the `.ng-hide` CSS class. Note that the selector that needs to be used is actually\n * `.ng-hide:not(.ng-hide-animate)` to cope with extra animation classes that can be added.\n *\n * ```css\n * .ng-hide:not(.ng-hide-animate) {\n *   /&#42; These are just alternative ways of hiding an element &#42;/\n *   display: block!important;\n *   position: absolute;\n *   top: -9999px;\n *   left: -9999px;\n * }\n * ```\n *\n * By default you don't need to override in CSS anything and the animations will work around the\n * display style.\n *\n * @animations\n * | Animation                                           | Occurs                                                                                                     |\n * |-----------------------------------------------------|------------------------------------------------------------------------------------------------------------|\n * | {@link $animate#addClass addClass} `.ng-hide`       | After the `ngHide` expression evaluates to a truthy value and just before the contents are set to hidden.  |\n * | {@link $animate#removeClass removeClass} `.ng-hide` | After the `ngHide` expression evaluates to a non truthy value and just before contents are set to visible. |\n *\n * Animations in `ngShow`/`ngHide` work with the show and hide events that are triggered when the\n * directive expression is true and false. This system works like the animation system present with\n * `ngClass` except that you must also include the `!important` flag to override the display\n * property so that the elements are not actually hidden during the animation.\n *\n * ```css\n * /&#42; A working example can be found at the bottom of this page. &#42;/\n * .my-element.ng-hide-add, .my-element.ng-hide-remove {\n *   transition: all 0.5s linear;\n * }\n *\n * .my-element.ng-hide-add { ... }\n * .my-element.ng-hide-add.ng-hide-add-active { ... }\n * .my-element.ng-hide-remove { ... }\n * .my-element.ng-hide-remove.ng-hide-remove-active { ... }\n * ```\n *\n * Keep in mind that, as of AngularJS version 1.3, there is no need to change the display property\n * to block during animation states - ngAnimate will automatically handle the style toggling for you.\n *\n * @element ANY\n * @param {expression} ngHide If the {@link guide/expression expression} is truthy/falsy then the\n *                            element is hidden/shown respectively.\n *\n * @example\n * A simple example, animating the element's opacity:\n *\n  <example module=\"ngAnimate\" deps=\"angular-animate.js\" animations=\"true\" name=\"ng-hide-simple\">\n    <file name=\"index.html\">\n      Hide: <input type=\"checkbox\" ng-model=\"checked\" aria-label=\"Toggle ngHide\"><br />\n      <div class=\"check-element animate-show-hide\" ng-hide=\"checked\">\n        I hide when your checkbox is checked.\n      </div>\n    </file>\n    <file name=\"animations.css\">\n      .animate-show-hide.ng-hide {\n        opacity: 0;\n      }\n\n      .animate-show-hide.ng-hide-add,\n      .animate-show-hide.ng-hide-remove {\n        transition: all linear 0.5s;\n      }\n\n      .check-element {\n        border: 1px solid black;\n        opacity: 1;\n        padding: 10px;\n      }\n    </file>\n    <file name=\"protractor.js\" type=\"protractor\">\n      it('should check ngHide', function() {\n        var checkbox = element(by.model('checked'));\n        var checkElem = element(by.css('.check-element'));\n\n        expect(checkElem.isDisplayed()).toBe(true);\n        checkbox.click();\n        expect(checkElem.isDisplayed()).toBe(false);\n      });\n    </file>\n  </example>\n *\n * <hr />\n * @example\n * A more complex example, featuring different show/hide animations:\n *\n  <example module=\"ngAnimate\" deps=\"angular-animate.js\" animations=\"true\" name=\"ng-hide-complex\">\n    <file name=\"index.html\">\n      Hide: <input type=\"checkbox\" ng-model=\"checked\" aria-label=\"Toggle ngHide\"><br />\n      <div class=\"check-element funky-show-hide\" ng-hide=\"checked\">\n        I hide when your checkbox is checked.\n      </div>\n    </file>\n    <file name=\"animations.css\">\n      body {\n        overflow: hidden;\n        perspective: 1000px;\n      }\n\n      .funky-show-hide.ng-hide-add {\n        transform: rotateZ(0);\n        transform-origin: right;\n        transition: all 0.5s ease-in-out;\n      }\n\n      .funky-show-hide.ng-hide-add.ng-hide-add-active {\n        transform: rotateZ(-135deg);\n      }\n\n      .funky-show-hide.ng-hide-remove {\n        transform: rotateY(90deg);\n        transform-origin: left;\n        transition: all 0.5s ease;\n      }\n\n      .funky-show-hide.ng-hide-remove.ng-hide-remove-active {\n        transform: rotateY(0);\n      }\n\n      .check-element {\n        border: 1px solid black;\n        opacity: 1;\n        padding: 10px;\n      }\n    </file>\n    <file name=\"protractor.js\" type=\"protractor\">\n      it('should check ngHide', function() {\n        var checkbox = element(by.model('checked'));\n        var checkElem = element(by.css('.check-element'));\n\n        expect(checkElem.isDisplayed()).toBe(true);\n        checkbox.click();\n        expect(checkElem.isDisplayed()).toBe(false);\n      });\n    </file>\n  </example>\n *\n * @knownIssue\n *\n * ### Flickering when using ngHide to toggle between elements\n *\n * When using {@link ngShow} and / or {@link ngHide} to toggle between elements, it can\n * happen that both the element to show and the element to hide are visible for a very short time.\n *\n * This usually happens when the {@link ngAnimate ngAnimate module} is included, but no actual animations\n * are defined for {@link ngShow} / {@link ngHide}. Internet Explorer is affected more often than\n * other browsers.\n *\n * There are several way to mitigate this problem:\n *\n * - {@link guide/animations#how-to-selectively-enable-disable-and-skip-animations Disable animations on the affected elements}.\n * - Use {@link ngIf} or {@link ngSwitch} instead of {@link ngShow} / {@link ngHide}.\n * - Use the special CSS selector `ng-hide.ng-hide-animate` to set `{display: none}` or similar on the affected elements.\n * - Use `ng-class=\"{'ng-hide': expression}` instead of instead of {@link ngShow} / {@link ngHide}.\n * - Define an animation on the affected elements.\n */\nvar ngHideDirective = ['$animate', function($animate) {\n  return {\n    restrict: 'A',\n    multiElement: true,\n    link: function(scope, element, attr) {\n      scope.$watch(attr.ngHide, function ngHideWatchAction(value) {\n        // The comment inside of the ngShowDirective explains why we add and\n        // remove a temporary class for the show/hide animation\n        $animate[value ? 'addClass' : 'removeClass'](element,NG_HIDE_CLASS, {\n          tempClasses: NG_HIDE_IN_PROGRESS_CLASS\n        });\n      });\n    }\n  };\n}];\n\n/**\n * @ngdoc directive\n * @name ngStyle\n * @restrict AC\n *\n * @description\n * The `ngStyle` directive allows you to set CSS style on an HTML element conditionally.\n *\n * @knownIssue\n * You should not use {@link guide/interpolation interpolation} in the value of the `style`\n * attribute, when using the `ngStyle` directive on the same element.\n * See {@link guide/interpolation#known-issues here} for more info.\n *\n * @element ANY\n * @param {expression} ngStyle\n *\n * {@link guide/expression Expression} which evals to an\n * object whose keys are CSS style names and values are corresponding values for those CSS\n * keys.\n *\n * Since some CSS style names are not valid keys for an object, they must be quoted.\n * See the 'background-color' style in the example below.\n *\n * @example\n   <example name=\"ng-style\">\n     <file name=\"index.html\">\n        <input type=\"button\" value=\"set color\" ng-click=\"myStyle={color:'red'}\">\n        <input type=\"button\" value=\"set background\" ng-click=\"myStyle={'background-color':'blue'}\">\n        <input type=\"button\" value=\"clear\" ng-click=\"myStyle={}\">\n        <br/>\n        <span ng-style=\"myStyle\">Sample Text</span>\n        <pre>myStyle={{myStyle}}</pre>\n     </file>\n     <file name=\"style.css\">\n       span {\n         color: black;\n       }\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       var colorSpan = element(by.css('span'));\n\n       it('should check ng-style', function() {\n         expect(colorSpan.getCssValue('color')).toMatch(/rgba\\(0, 0, 0, 1\\)|rgb\\(0, 0, 0\\)/);\n         element(by.css('input[value=\\'set color\\']')).click();\n         expect(colorSpan.getCssValue('color')).toMatch(/rgba\\(255, 0, 0, 1\\)|rgb\\(255, 0, 0\\)/);\n         element(by.css('input[value=clear]')).click();\n         expect(colorSpan.getCssValue('color')).toMatch(/rgba\\(0, 0, 0, 1\\)|rgb\\(0, 0, 0\\)/);\n       });\n     </file>\n   </example>\n */\nvar ngStyleDirective = ngDirective(function(scope, element, attr) {\n  scope.$watchCollection(attr.ngStyle, function ngStyleWatchAction(newStyles, oldStyles) {\n    if (oldStyles && (newStyles !== oldStyles)) {\n      forEach(oldStyles, function(val, style) { element.css(style, ''); });\n    }\n    if (newStyles) element.css(newStyles);\n  });\n});\n\n/**\n * @ngdoc directive\n * @name ngSwitch\n * @restrict EA\n *\n * @description\n * The `ngSwitch` directive is used to conditionally swap DOM structure on your template based on a scope expression.\n * Elements within `ngSwitch` but without `ngSwitchWhen` or `ngSwitchDefault` directives will be preserved at the location\n * as specified in the template.\n *\n * The directive itself works similar to ngInclude, however, instead of downloading template code (or loading it\n * from the template cache), `ngSwitch` simply chooses one of the nested elements and makes it visible based on which element\n * matches the value obtained from the evaluated expression. In other words, you define a container element\n * (where you place the directive), place an expression on the **`on=\"...\"` attribute**\n * (or the **`ng-switch=\"...\"` attribute**), define any inner elements inside of the directive and place\n * a when attribute per element. The when attribute is used to inform ngSwitch which element to display when the on\n * expression is evaluated. If a matching expression is not found via a when attribute then an element with the default\n * attribute is displayed.\n *\n * <div class=\"alert alert-info\">\n * Be aware that the attribute values to match against cannot be expressions. They are interpreted\n * as literal string values to match against.\n * For example, **`ng-switch-when=\"someVal\"`** will match against the string `\"someVal\"` not against the\n * value of the expression `$scope.someVal`.\n * </div>\n\n * @animations\n * | Animation                        | Occurs                              |\n * |----------------------------------|-------------------------------------|\n * | {@link ng.$animate#enter enter}  | after the ngSwitch contents change and the matched child element is placed inside the container |\n * | {@link ng.$animate#leave leave}  | after the ngSwitch contents change and just before the former contents are removed from the DOM |\n *\n * @usage\n *\n * ```\n * <ANY ng-switch=\"expression\">\n *   <ANY ng-switch-when=\"matchValue1\">...</ANY>\n *   <ANY ng-switch-when=\"matchValue2\">...</ANY>\n *   <ANY ng-switch-default>...</ANY>\n * </ANY>\n * ```\n *\n *\n * @scope\n * @priority 1200\n * @param {*} ngSwitch|on expression to match against <code>ng-switch-when</code>.\n * On child elements add:\n *\n * * `ngSwitchWhen`: the case statement to match against. If match then this\n *   case will be displayed. If the same match appears multiple times, all the\n *   elements will be displayed. It is possible to associate multiple values to\n *   the same `ngSwitchWhen` by defining the optional attribute\n *   `ngSwitchWhenSeparator`. The separator will be used to split the value of\n *   the `ngSwitchWhen` attribute into multiple tokens, and the element will show\n *   if any of the `ngSwitch` evaluates to any of these tokens.\n * * `ngSwitchDefault`: the default case when no other case match. If there\n *   are multiple default cases, all of them will be displayed when no other\n *   case match.\n *\n *\n * @example\n  <example module=\"switchExample\" deps=\"angular-animate.js\" animations=\"true\" name=\"ng-switch\">\n    <file name=\"index.html\">\n      <div ng-controller=\"ExampleController\">\n        <select ng-model=\"selection\" ng-options=\"item for item in items\">\n        </select>\n        <code>selection={{selection}}</code>\n        <hr/>\n        <div class=\"animate-switch-container\"\n          ng-switch on=\"selection\">\n            <div class=\"animate-switch\" ng-switch-when=\"settings|options\" ng-switch-when-separator=\"|\">Settings Div</div>\n            <div class=\"animate-switch\" ng-switch-when=\"home\">Home Span</div>\n            <div class=\"animate-switch\" ng-switch-default>default</div>\n        </div>\n      </div>\n    </file>\n    <file name=\"script.js\">\n      angular.module('switchExample', ['ngAnimate'])\n        .controller('ExampleController', ['$scope', function($scope) {\n          $scope.items = ['settings', 'home', 'options', 'other'];\n          $scope.selection = $scope.items[0];\n        }]);\n    </file>\n    <file name=\"animations.css\">\n      .animate-switch-container {\n        position:relative;\n        background:white;\n        border:1px solid black;\n        height:40px;\n        overflow:hidden;\n      }\n\n      .animate-switch {\n        padding:10px;\n      }\n\n      .animate-switch.ng-animate {\n        transition:all cubic-bezier(0.250, 0.460, 0.450, 0.940) 0.5s;\n\n        position:absolute;\n        top:0;\n        left:0;\n        right:0;\n        bottom:0;\n      }\n\n      .animate-switch.ng-leave.ng-leave-active,\n      .animate-switch.ng-enter {\n        top:-50px;\n      }\n      .animate-switch.ng-leave,\n      .animate-switch.ng-enter.ng-enter-active {\n        top:0;\n      }\n    </file>\n    <file name=\"protractor.js\" type=\"protractor\">\n      var switchElem = element(by.css('[ng-switch]'));\n      var select = element(by.model('selection'));\n\n      it('should start in settings', function() {\n        expect(switchElem.getText()).toMatch(/Settings Div/);\n      });\n      it('should change to home', function() {\n        select.all(by.css('option')).get(1).click();\n        expect(switchElem.getText()).toMatch(/Home Span/);\n      });\n      it('should change to settings via \"options\"', function() {\n        select.all(by.css('option')).get(2).click();\n        expect(switchElem.getText()).toMatch(/Settings Div/);\n      });\n      it('should select default', function() {\n        select.all(by.css('option')).get(3).click();\n        expect(switchElem.getText()).toMatch(/default/);\n      });\n    </file>\n  </example>\n */\nvar ngSwitchDirective = ['$animate', '$compile', function($animate, $compile) {\n  return {\n    require: 'ngSwitch',\n\n    // asks for $scope to fool the BC controller module\n    controller: ['$scope', function NgSwitchController() {\n     this.cases = {};\n    }],\n    link: function(scope, element, attr, ngSwitchController) {\n      var watchExpr = attr.ngSwitch || attr.on,\n          selectedTranscludes = [],\n          selectedElements = [],\n          previousLeaveAnimations = [],\n          selectedScopes = [];\n\n      var spliceFactory = function(array, index) {\n          return function(response) {\n            if (response !== false) array.splice(index, 1);\n          };\n      };\n\n      scope.$watch(watchExpr, function ngSwitchWatchAction(value) {\n        var i, ii;\n\n        // Start with the last, in case the array is modified during the loop\n        while (previousLeaveAnimations.length) {\n          $animate.cancel(previousLeaveAnimations.pop());\n        }\n\n        for (i = 0, ii = selectedScopes.length; i < ii; ++i) {\n          var selected = getBlockNodes(selectedElements[i].clone);\n          selectedScopes[i].$destroy();\n          var runner = previousLeaveAnimations[i] = $animate.leave(selected);\n          runner.done(spliceFactory(previousLeaveAnimations, i));\n        }\n\n        selectedElements.length = 0;\n        selectedScopes.length = 0;\n\n        if ((selectedTranscludes = ngSwitchController.cases['!' + value] || ngSwitchController.cases['?'])) {\n          forEach(selectedTranscludes, function(selectedTransclude) {\n            selectedTransclude.transclude(function(caseElement, selectedScope) {\n              selectedScopes.push(selectedScope);\n              var anchor = selectedTransclude.element;\n              caseElement[caseElement.length++] = $compile.$$createComment('end ngSwitchWhen');\n              var block = { clone: caseElement };\n\n              selectedElements.push(block);\n              $animate.enter(caseElement, anchor.parent(), anchor);\n            });\n          });\n        }\n      });\n    }\n  };\n}];\n\nvar ngSwitchWhenDirective = ngDirective({\n  transclude: 'element',\n  priority: 1200,\n  require: '^ngSwitch',\n  multiElement: true,\n  link: function(scope, element, attrs, ctrl, $transclude) {\n\n    var cases = attrs.ngSwitchWhen.split(attrs.ngSwitchWhenSeparator).sort().filter(\n      // Filter duplicate cases\n      function(element, index, array) { return array[index - 1] !== element; }\n    );\n\n    forEach(cases, function(whenCase) {\n      ctrl.cases['!' + whenCase] = (ctrl.cases['!' + whenCase] || []);\n      ctrl.cases['!' + whenCase].push({ transclude: $transclude, element: element });\n    });\n  }\n});\n\nvar ngSwitchDefaultDirective = ngDirective({\n  transclude: 'element',\n  priority: 1200,\n  require: '^ngSwitch',\n  multiElement: true,\n  link: function(scope, element, attr, ctrl, $transclude) {\n    ctrl.cases['?'] = (ctrl.cases['?'] || []);\n    ctrl.cases['?'].push({ transclude: $transclude, element: element });\n   }\n});\n\n/**\n * @ngdoc directive\n * @name ngTransclude\n * @restrict EAC\n *\n * @description\n * Directive that marks the insertion point for the transcluded DOM of the nearest parent directive that uses transclusion.\n *\n * You can specify that you want to insert a named transclusion slot, instead of the default slot, by providing the slot name\n * as the value of the `ng-transclude` or `ng-transclude-slot` attribute.\n *\n * If the transcluded content is not empty (i.e. contains one or more DOM nodes, including whitespace text nodes), any existing\n * content of this element will be removed before the transcluded content is inserted.\n * If the transcluded content is empty (or only whitespace), the existing content is left intact. This lets you provide fallback\n * content in the case that no transcluded content is provided.\n *\n * @element ANY\n *\n * @param {string} ngTransclude|ngTranscludeSlot the name of the slot to insert at this point. If this is not provided, is empty\n *                                               or its value is the same as the name of the attribute then the default slot is used.\n *\n * @example\n * ### Basic transclusion\n * This example demonstrates basic transclusion of content into a component directive.\n * <example name=\"simpleTranscludeExample\" module=\"transcludeExample\">\n *   <file name=\"index.html\">\n *     <script>\n *       angular.module('transcludeExample', [])\n *        .directive('pane', function(){\n *           return {\n *             restrict: 'E',\n *             transclude: true,\n *             scope: { title:'@' },\n *             template: '<div style=\"border: 1px solid black;\">' +\n *                         '<div style=\"background-color: gray\">{{title}}</div>' +\n *                         '<ng-transclude></ng-transclude>' +\n *                       '</div>'\n *           };\n *       })\n *       .controller('ExampleController', ['$scope', function($scope) {\n *         $scope.title = 'Lorem Ipsum';\n *         $scope.text = 'Neque porro quisquam est qui dolorem ipsum quia dolor...';\n *       }]);\n *     </script>\n *     <div ng-controller=\"ExampleController\">\n *       <input ng-model=\"title\" aria-label=\"title\"> <br/>\n *       <textarea ng-model=\"text\" aria-label=\"text\"></textarea> <br/>\n *       <pane title=\"{{title}}\"><span>{{text}}</span></pane>\n *     </div>\n *   </file>\n *   <file name=\"protractor.js\" type=\"protractor\">\n *      it('should have transcluded', function() {\n *        var titleElement = element(by.model('title'));\n *        titleElement.clear();\n *        titleElement.sendKeys('TITLE');\n *        var textElement = element(by.model('text'));\n *        textElement.clear();\n *        textElement.sendKeys('TEXT');\n *        expect(element(by.binding('title')).getText()).toEqual('TITLE');\n *        expect(element(by.binding('text')).getText()).toEqual('TEXT');\n *      });\n *   </file>\n * </example>\n *\n * @example\n * ### Transclude fallback content\n * This example shows how to use `NgTransclude` with fallback content, that\n * is displayed if no transcluded content is provided.\n *\n * <example module=\"transcludeFallbackContentExample\" name=\"ng-transclude\">\n * <file name=\"index.html\">\n * <script>\n * angular.module('transcludeFallbackContentExample', [])\n * .directive('myButton', function(){\n *             return {\n *               restrict: 'E',\n *               transclude: true,\n *               scope: true,\n *               template: '<button style=\"cursor: pointer;\">' +\n *                           '<ng-transclude>' +\n *                             '<b style=\"color: red;\">Button1</b>' +\n *                           '</ng-transclude>' +\n *                         '</button>'\n *             };\n *         });\n * </script>\n * <!-- fallback button content -->\n * <my-button id=\"fallback\"></my-button>\n * <!-- modified button content -->\n * <my-button id=\"modified\">\n *   <i style=\"color: green;\">Button2</i>\n * </my-button>\n * </file>\n * <file name=\"protractor.js\" type=\"protractor\">\n * it('should have different transclude element content', function() {\n *          expect(element(by.id('fallback')).getText()).toBe('Button1');\n *          expect(element(by.id('modified')).getText()).toBe('Button2');\n *        });\n * </file>\n * </example>\n *\n * @example\n * ### Multi-slot transclusion\n * This example demonstrates using multi-slot transclusion in a component directive.\n * <example name=\"multiSlotTranscludeExample\" module=\"multiSlotTranscludeExample\">\n *   <file name=\"index.html\">\n *    <style>\n *      .title, .footer {\n *        background-color: gray\n *      }\n *    </style>\n *    <div ng-controller=\"ExampleController\">\n *      <input ng-model=\"title\" aria-label=\"title\"> <br/>\n *      <textarea ng-model=\"text\" aria-label=\"text\"></textarea> <br/>\n *      <pane>\n *        <pane-title><a ng-href=\"{{link}}\">{{title}}</a></pane-title>\n *        <pane-body><p>{{text}}</p></pane-body>\n *      </pane>\n *    </div>\n *   </file>\n *   <file name=\"app.js\">\n *    angular.module('multiSlotTranscludeExample', [])\n *     .directive('pane', function() {\n *        return {\n *          restrict: 'E',\n *          transclude: {\n *            'title': '?paneTitle',\n *            'body': 'paneBody',\n *            'footer': '?paneFooter'\n *          },\n *          template: '<div style=\"border: 1px solid black;\">' +\n *                      '<div class=\"title\" ng-transclude=\"title\">Fallback Title</div>' +\n *                      '<div ng-transclude=\"body\"></div>' +\n *                      '<div class=\"footer\" ng-transclude=\"footer\">Fallback Footer</div>' +\n *                    '</div>'\n *        };\n *    })\n *    .controller('ExampleController', ['$scope', function($scope) {\n *      $scope.title = 'Lorem Ipsum';\n *      $scope.link = 'https://google.com';\n *      $scope.text = 'Neque porro quisquam est qui dolorem ipsum quia dolor...';\n *    }]);\n *   </file>\n *   <file name=\"protractor.js\" type=\"protractor\">\n *      it('should have transcluded the title and the body', function() {\n *        var titleElement = element(by.model('title'));\n *        titleElement.clear();\n *        titleElement.sendKeys('TITLE');\n *        var textElement = element(by.model('text'));\n *        textElement.clear();\n *        textElement.sendKeys('TEXT');\n *        expect(element(by.css('.title')).getText()).toEqual('TITLE');\n *        expect(element(by.binding('text')).getText()).toEqual('TEXT');\n *        expect(element(by.css('.footer')).getText()).toEqual('Fallback Footer');\n *      });\n *   </file>\n * </example>\n */\nvar ngTranscludeMinErr = minErr('ngTransclude');\nvar ngTranscludeDirective = ['$compile', function($compile) {\n  return {\n    restrict: 'EAC',\n    compile: function ngTranscludeCompile(tElement) {\n\n      // Remove and cache any original content to act as a fallback\n      var fallbackLinkFn = $compile(tElement.contents());\n      tElement.empty();\n\n      return function ngTranscludePostLink($scope, $element, $attrs, controller, $transclude) {\n\n        if (!$transclude) {\n          throw ngTranscludeMinErr('orphan',\n          'Illegal use of ngTransclude directive in the template! ' +\n          'No parent directive that requires a transclusion found. ' +\n          'Element: {0}',\n          startingTag($element));\n        }\n\n\n        // If the attribute is of the form: `ng-transclude=\"ng-transclude\"` then treat it like the default\n        if ($attrs.ngTransclude === $attrs.$attr.ngTransclude) {\n          $attrs.ngTransclude = '';\n        }\n        var slotName = $attrs.ngTransclude || $attrs.ngTranscludeSlot;\n\n        // If the slot is required and no transclusion content is provided then this call will throw an error\n        $transclude(ngTranscludeCloneAttachFn, null, slotName);\n\n        // If the slot is optional and no transclusion content is provided then use the fallback content\n        if (slotName && !$transclude.isSlotFilled(slotName)) {\n          useFallbackContent();\n        }\n\n        function ngTranscludeCloneAttachFn(clone, transcludedScope) {\n          if (clone.length && notWhitespace(clone)) {\n            $element.append(clone);\n          } else {\n            useFallbackContent();\n            // There is nothing linked against the transcluded scope since no content was available,\n            // so it should be safe to clean up the generated scope.\n            transcludedScope.$destroy();\n          }\n        }\n\n        function useFallbackContent() {\n          // Since this is the fallback content rather than the transcluded content,\n          // we link against the scope of this directive rather than the transcluded scope\n          fallbackLinkFn($scope, function(clone) {\n            $element.append(clone);\n          });\n        }\n\n        function notWhitespace(nodes) {\n          for (var i = 0, ii = nodes.length; i < ii; i++) {\n            var node = nodes[i];\n            if (node.nodeType !== NODE_TYPE_TEXT || node.nodeValue.trim()) {\n              return true;\n            }\n          }\n        }\n      };\n    }\n  };\n}];\n\n/**\n * @ngdoc directive\n * @name script\n * @restrict E\n *\n * @description\n * Load the content of a `<script>` element into {@link ng.$templateCache `$templateCache`}, so that the\n * template can be used by {@link ng.directive:ngInclude `ngInclude`},\n * {@link ngRoute.directive:ngView `ngView`}, or {@link guide/directive directives}. The type of the\n * `<script>` element must be specified as `text/ng-template`, and a cache name for the template must be\n * assigned through the element's `id`, which can then be used as a directive's `templateUrl`.\n *\n * @param {string} type Must be set to `'text/ng-template'`.\n * @param {string} id Cache name of the template.\n *\n * @example\n  <example  name=\"script-tag\">\n    <file name=\"index.html\">\n      <script type=\"text/ng-template\" id=\"/tpl.html\">\n        Content of the template.\n      </script>\n\n      <a ng-click=\"currentTpl='/tpl.html'\" id=\"tpl-link\">Load inlined template</a>\n      <div id=\"tpl-content\" ng-include src=\"currentTpl\"></div>\n    </file>\n    <file name=\"protractor.js\" type=\"protractor\">\n      it('should load template defined inside script tag', function() {\n        element(by.css('#tpl-link')).click();\n        expect(element(by.css('#tpl-content')).getText()).toMatch(/Content of the template/);\n      });\n    </file>\n  </example>\n */\nvar scriptDirective = ['$templateCache', function($templateCache) {\n  return {\n    restrict: 'E',\n    terminal: true,\n    compile: function(element, attr) {\n      if (attr.type === 'text/ng-template') {\n        var templateUrl = attr.id,\n            text = element[0].text;\n\n        $templateCache.put(templateUrl, text);\n      }\n    }\n  };\n}];\n\n/* exported selectDirective, optionDirective */\n\nvar noopNgModelController = { $setViewValue: noop, $render: noop };\n\nfunction setOptionSelectedStatus(optionEl, value) {\n  optionEl.prop('selected', value);\n  /**\n   * When unselecting an option, setting the property to null / false should be enough\n   * However, screenreaders might react to the selected attribute instead, see\n   * https://github.com/angular/angular.js/issues/14419\n   * Note: \"selected\" is a boolean attr and will be removed when the \"value\" arg in attr() is false\n   * or null\n   */\n  optionEl.attr('selected', value);\n}\n\n/**\n * @ngdoc type\n * @name  select.SelectController\n *\n * @description\n * The controller for the {@link ng.select select} directive. The controller exposes\n * a few utility methods that can be used to augment the behavior of a regular or an\n * {@link ng.ngOptions ngOptions} select element.\n *\n * @example\n * ### Set a custom error when the unknown option is selected\n *\n * This example sets a custom error \"unknownValue\" on the ngModelController\n * when the select element's unknown option is selected, i.e. when the model is set to a value\n * that is not matched by any option.\n *\n * <example name=\"select-unknown-value-error\" module=\"staticSelect\">\n * <file name=\"index.html\">\n * <div ng-controller=\"ExampleController\">\n *   <form name=\"myForm\">\n *     <label for=\"testSelect\"> Single select: </label><br>\n *     <select name=\"testSelect\" ng-model=\"selected\" unknown-value-error>\n *       <option value=\"option-1\">Option 1</option>\n *       <option value=\"option-2\">Option 2</option>\n *     </select><br>\n *     <span class=\"error\" ng-if=\"myForm.testSelect.$error.unknownValue\">\n *       Error: The current model doesn't match any option</span><br>\n *\n *     <button ng-click=\"forceUnknownOption()\">Force unknown option</button><br>\n *   </form>\n * </div>\n * </file>\n * <file name=\"app.js\">\n *  angular.module('staticSelect', [])\n *    .controller('ExampleController', ['$scope', function($scope) {\n *      $scope.selected = null;\n *\n *      $scope.forceUnknownOption = function() {\n *        $scope.selected = 'nonsense';\n *      };\n *   }])\n *   .directive('unknownValueError', function() {\n *     return {\n *       require: ['ngModel', 'select'],\n *       link: function(scope, element, attrs, ctrls) {\n *         var ngModelCtrl = ctrls[0];\n *         var selectCtrl = ctrls[1];\n *\n *         ngModelCtrl.$validators.unknownValue = function(modelValue, viewValue) {\n *           if (selectCtrl.$isUnknownOptionSelected()) {\n *             return false;\n *           }\n *\n *           return true;\n *         };\n *       }\n *\n *     };\n *   });\n * </file>\n *</example>\n *\n *\n * @example\n * ### Set the \"required\" error when the unknown option is selected.\n *\n * By default, the \"required\" error on the ngModelController is only set on a required select\n * when the empty option is selected. This example adds a custom directive that also sets the\n * error when the unknown option is selected.\n *\n * <example name=\"select-unknown-value-required\" module=\"staticSelect\">\n * <file name=\"index.html\">\n * <div ng-controller=\"ExampleController\">\n *   <form name=\"myForm\">\n *     <label for=\"testSelect\"> Select: </label><br>\n *     <select name=\"testSelect\" ng-model=\"selected\" required unknown-value-required>\n *       <option value=\"option-1\">Option 1</option>\n *       <option value=\"option-2\">Option 2</option>\n *     </select><br>\n *     <span class=\"error\" ng-if=\"myForm.testSelect.$error.required\">Error: Please select a value</span><br>\n *\n *     <button ng-click=\"forceUnknownOption()\">Force unknown option</button><br>\n *   </form>\n * </div>\n * </file>\n * <file name=\"app.js\">\n *  angular.module('staticSelect', [])\n *    .controller('ExampleController', ['$scope', function($scope) {\n *      $scope.selected = null;\n *\n *      $scope.forceUnknownOption = function() {\n *        $scope.selected = 'nonsense';\n *      };\n *   }])\n *   .directive('unknownValueRequired', function() {\n *     return {\n *       priority: 1, // This directive must run after the required directive has added its validator\n *       require: ['ngModel', 'select'],\n *       link: function(scope, element, attrs, ctrls) {\n *         var ngModelCtrl = ctrls[0];\n *         var selectCtrl = ctrls[1];\n *\n *         var originalRequiredValidator = ngModelCtrl.$validators.required;\n *\n *         ngModelCtrl.$validators.required = function() {\n *           if (attrs.required && selectCtrl.$isUnknownOptionSelected()) {\n *             return false;\n *           }\n *\n *           return originalRequiredValidator.apply(this, arguments);\n *         };\n *       }\n *     };\n *   });\n * </file>\n * <file name=\"protractor.js\" type=\"protractor\">\n *  it('should show the error message when the unknown option is selected', function() {\n\n      var error = element(by.className('error'));\n\n      expect(error.getText()).toBe('Error: Please select a value');\n\n      element(by.cssContainingText('option', 'Option 1')).click();\n\n      expect(error.isPresent()).toBe(false);\n\n      element(by.tagName('button')).click();\n\n      expect(error.getText()).toBe('Error: Please select a value');\n    });\n * </file>\n *</example>\n *\n *\n */\nvar SelectController =\n        ['$element', '$scope', /** @this */ function($element, $scope) {\n\n  var self = this,\n      optionsMap = new NgMap();\n\n  self.selectValueMap = {}; // Keys are the hashed values, values the original values\n\n  // If the ngModel doesn't get provided then provide a dummy noop version to prevent errors\n  self.ngModelCtrl = noopNgModelController;\n  self.multiple = false;\n\n  // The \"unknown\" option is one that is prepended to the list if the viewValue\n  // does not match any of the options. When it is rendered the value of the unknown\n  // option is '? XXX ?' where XXX is the hashKey of the value that is not known.\n  //\n  // Support: IE 9 only\n  // We can't just jqLite('<option>') since jqLite is not smart enough\n  // to create it in <select> and IE barfs otherwise.\n  self.unknownOption = jqLite(window.document.createElement('option'));\n\n  // The empty option is an option with the value '' that the application developer can\n  // provide inside the select. It is always selectable and indicates that a \"null\" selection has\n  // been made by the user.\n  // If the select has an empty option, and the model of the select is set to \"undefined\" or \"null\",\n  // the empty option is selected.\n  // If the model is set to a different unmatched value, the unknown option is rendered and\n  // selected, i.e both are present, because a \"null\" selection and an unknown value are different.\n  self.hasEmptyOption = false;\n  self.emptyOption = undefined;\n\n  self.renderUnknownOption = function(val) {\n    var unknownVal = self.generateUnknownOptionValue(val);\n    self.unknownOption.val(unknownVal);\n    $element.prepend(self.unknownOption);\n    setOptionSelectedStatus(self.unknownOption, true);\n    $element.val(unknownVal);\n  };\n\n  self.updateUnknownOption = function(val) {\n    var unknownVal = self.generateUnknownOptionValue(val);\n    self.unknownOption.val(unknownVal);\n    setOptionSelectedStatus(self.unknownOption, true);\n    $element.val(unknownVal);\n  };\n\n  self.generateUnknownOptionValue = function(val) {\n    return '? ' + hashKey(val) + ' ?';\n  };\n\n  self.removeUnknownOption = function() {\n    if (self.unknownOption.parent()) self.unknownOption.remove();\n  };\n\n  self.selectEmptyOption = function() {\n    if (self.emptyOption) {\n      $element.val('');\n      setOptionSelectedStatus(self.emptyOption, true);\n    }\n  };\n\n  self.unselectEmptyOption = function() {\n    if (self.hasEmptyOption) {\n      setOptionSelectedStatus(self.emptyOption, false);\n    }\n  };\n\n  $scope.$on('$destroy', function() {\n    // disable unknown option so that we don't do work when the whole select is being destroyed\n    self.renderUnknownOption = noop;\n  });\n\n  // Read the value of the select control, the implementation of this changes depending\n  // upon whether the select can have multiple values and whether ngOptions is at work.\n  self.readValue = function readSingleValue() {\n    var val = $element.val();\n    // ngValue added option values are stored in the selectValueMap, normal interpolations are not\n    var realVal = val in self.selectValueMap ? self.selectValueMap[val] : val;\n\n    if (self.hasOption(realVal)) {\n      return realVal;\n    }\n\n    return null;\n  };\n\n\n  // Write the value to the select control, the implementation of this changes depending\n  // upon whether the select can have multiple values and whether ngOptions is at work.\n  self.writeValue = function writeSingleValue(value) {\n    // Make sure to remove the selected attribute from the previously selected option\n    // Otherwise, screen readers might get confused\n    var currentlySelectedOption = $element[0].options[$element[0].selectedIndex];\n    if (currentlySelectedOption) setOptionSelectedStatus(jqLite(currentlySelectedOption), false);\n\n    if (self.hasOption(value)) {\n      self.removeUnknownOption();\n\n      var hashedVal = hashKey(value);\n      $element.val(hashedVal in self.selectValueMap ? hashedVal : value);\n\n      // Set selected attribute and property on selected option for screen readers\n      var selectedOption = $element[0].options[$element[0].selectedIndex];\n      setOptionSelectedStatus(jqLite(selectedOption), true);\n    } else {\n      self.selectUnknownOrEmptyOption(value);\n    }\n  };\n\n\n  // Tell the select control that an option, with the given value, has been added\n  self.addOption = function(value, element) {\n    // Skip comment nodes, as they only pollute the `optionsMap`\n    if (element[0].nodeType === NODE_TYPE_COMMENT) return;\n\n    assertNotHasOwnProperty(value, '\"option value\"');\n    if (value === '') {\n      self.hasEmptyOption = true;\n      self.emptyOption = element;\n    }\n    var count = optionsMap.get(value) || 0;\n    optionsMap.set(value, count + 1);\n    // Only render at the end of a digest. This improves render performance when many options\n    // are added during a digest and ensures all relevant options are correctly marked as selected\n    scheduleRender();\n  };\n\n  // Tell the select control that an option, with the given value, has been removed\n  self.removeOption = function(value) {\n    var count = optionsMap.get(value);\n    if (count) {\n      if (count === 1) {\n        optionsMap.delete(value);\n        if (value === '') {\n          self.hasEmptyOption = false;\n          self.emptyOption = undefined;\n        }\n      } else {\n        optionsMap.set(value, count - 1);\n      }\n    }\n  };\n\n  // Check whether the select control has an option matching the given value\n  self.hasOption = function(value) {\n    return !!optionsMap.get(value);\n  };\n\n  /**\n   * @ngdoc method\n   * @name select.SelectController#$hasEmptyOption\n   *\n   * @description\n   *\n   * Returns `true` if the select element currently has an empty option\n   * element, i.e. an option that signifies that the select is empty / the selection is null.\n   *\n   */\n  self.$hasEmptyOption = function() {\n    return self.hasEmptyOption;\n  };\n\n  /**\n   * @ngdoc method\n   * @name select.SelectController#$isUnknownOptionSelected\n   *\n   * @description\n   *\n   * Returns `true` if the select element's unknown option is selected. The unknown option is added\n   * and automatically selected whenever the select model doesn't match any option.\n   *\n   */\n  self.$isUnknownOptionSelected = function() {\n    // Presence of the unknown option means it is selected\n    return $element[0].options[0] === self.unknownOption[0];\n  };\n\n  /**\n   * @ngdoc method\n   * @name select.SelectController#$isEmptyOptionSelected\n   *\n   * @description\n   *\n   * Returns `true` if the select element has an empty option and this empty option is currently\n   * selected. Returns `false` if the select element has no empty option or it is not selected.\n   *\n   */\n  self.$isEmptyOptionSelected = function() {\n    return self.hasEmptyOption && $element[0].options[$element[0].selectedIndex] === self.emptyOption[0];\n  };\n\n  self.selectUnknownOrEmptyOption = function(value) {\n    if (value == null && self.emptyOption) {\n      self.removeUnknownOption();\n      self.selectEmptyOption();\n    } else if (self.unknownOption.parent().length) {\n      self.updateUnknownOption(value);\n    } else {\n      self.renderUnknownOption(value);\n    }\n  };\n\n  var renderScheduled = false;\n  function scheduleRender() {\n    if (renderScheduled) return;\n    renderScheduled = true;\n    $scope.$$postDigest(function() {\n      renderScheduled = false;\n      self.ngModelCtrl.$render();\n    });\n  }\n\n  var updateScheduled = false;\n  function scheduleViewValueUpdate(renderAfter) {\n    if (updateScheduled) return;\n\n    updateScheduled = true;\n\n    $scope.$$postDigest(function() {\n      if ($scope.$$destroyed) return;\n\n      updateScheduled = false;\n      self.ngModelCtrl.$setViewValue(self.readValue());\n      if (renderAfter) self.ngModelCtrl.$render();\n    });\n  }\n\n\n  self.registerOption = function(optionScope, optionElement, optionAttrs, interpolateValueFn, interpolateTextFn) {\n\n    if (optionAttrs.$attr.ngValue) {\n      // The value attribute is set by ngValue\n      var oldVal, hashedVal;\n      optionAttrs.$observe('value', function valueAttributeObserveAction(newVal) {\n\n        var removal;\n        var previouslySelected = optionElement.prop('selected');\n\n        if (isDefined(hashedVal)) {\n          self.removeOption(oldVal);\n          delete self.selectValueMap[hashedVal];\n          removal = true;\n        }\n\n        hashedVal = hashKey(newVal);\n        oldVal = newVal;\n        self.selectValueMap[hashedVal] = newVal;\n        self.addOption(newVal, optionElement);\n        // Set the attribute directly instead of using optionAttrs.$set - this stops the observer\n        // from firing a second time. Other $observers on value will also get the result of the\n        // ngValue expression, not the hashed value\n        optionElement.attr('value', hashedVal);\n\n        if (removal && previouslySelected) {\n          scheduleViewValueUpdate();\n        }\n\n      });\n    } else if (interpolateValueFn) {\n      // The value attribute is interpolated\n      optionAttrs.$observe('value', function valueAttributeObserveAction(newVal) {\n        // This method is overwritten in ngOptions and has side-effects!\n        self.readValue();\n\n        var removal;\n        var previouslySelected = optionElement.prop('selected');\n\n        if (isDefined(oldVal)) {\n          self.removeOption(oldVal);\n          removal = true;\n        }\n        oldVal = newVal;\n        self.addOption(newVal, optionElement);\n\n        if (removal && previouslySelected) {\n          scheduleViewValueUpdate();\n        }\n      });\n    } else if (interpolateTextFn) {\n      // The text content is interpolated\n      optionScope.$watch(interpolateTextFn, function interpolateWatchAction(newVal, oldVal) {\n        optionAttrs.$set('value', newVal);\n        var previouslySelected = optionElement.prop('selected');\n        if (oldVal !== newVal) {\n          self.removeOption(oldVal);\n        }\n        self.addOption(newVal, optionElement);\n\n        if (oldVal && previouslySelected) {\n          scheduleViewValueUpdate();\n        }\n      });\n    } else {\n      // The value attribute is static\n      self.addOption(optionAttrs.value, optionElement);\n    }\n\n\n    optionAttrs.$observe('disabled', function(newVal) {\n\n      // Since model updates will also select disabled options (like ngOptions),\n      // we only have to handle options becoming disabled, not enabled\n\n      if (newVal === 'true' || newVal && optionElement.prop('selected')) {\n        if (self.multiple) {\n          scheduleViewValueUpdate(true);\n        } else {\n          self.ngModelCtrl.$setViewValue(null);\n          self.ngModelCtrl.$render();\n        }\n      }\n    });\n\n    optionElement.on('$destroy', function() {\n      var currentValue = self.readValue();\n      var removeValue = optionAttrs.value;\n\n      self.removeOption(removeValue);\n      scheduleRender();\n\n      if (self.multiple && currentValue && currentValue.indexOf(removeValue) !== -1 ||\n          currentValue === removeValue\n      ) {\n        // When multiple (selected) options are destroyed at the same time, we don't want\n        // to run a model update for each of them. Instead, run a single update in the $$postDigest\n        scheduleViewValueUpdate(true);\n      }\n    });\n  };\n}];\n\n/**\n * @ngdoc directive\n * @name select\n * @restrict E\n *\n * @description\n * HTML `select` element with AngularJS data-binding.\n *\n * The `select` directive is used together with {@link ngModel `ngModel`} to provide data-binding\n * between the scope and the `<select>` control (including setting default values).\n * It also handles dynamic `<option>` elements, which can be added using the {@link ngRepeat `ngRepeat}` or\n * {@link ngOptions `ngOptions`} directives.\n *\n * When an item in the `<select>` menu is selected, the value of the selected option will be bound\n * to the model identified by the `ngModel` directive. With static or repeated options, this is\n * the content of the `value` attribute or the textContent of the `<option>`, if the value attribute is missing.\n * Value and textContent can be interpolated.\n *\n * The {@link select.SelectController select controller} exposes utility functions that can be used\n * to manipulate the select's behavior.\n *\n * ## Matching model and option values\n *\n * In general, the match between the model and an option is evaluated by strictly comparing the model\n * value against the value of the available options.\n *\n * If you are setting the option value with the option's `value` attribute, or textContent, the\n * value will always be a `string` which means that the model value must also be a string.\n * Otherwise the `select` directive cannot match them correctly.\n *\n * To bind the model to a non-string value, you can use one of the following strategies:\n * - the {@link ng.ngOptions `ngOptions`} directive\n *   ({@link ng.select#using-select-with-ngoptions-and-setting-a-default-value})\n * - the {@link ng.ngValue `ngValue`} directive, which allows arbitrary expressions to be\n *   option values ({@link ng.select#using-ngvalue-to-bind-the-model-to-an-array-of-objects Example})\n * - model $parsers / $formatters to convert the string value\n *   ({@link ng.select#binding-select-to-a-non-string-value-via-ngmodel-parsing-formatting Example})\n *\n * If the viewValue of `ngModel` does not match any of the options, then the control\n * will automatically add an \"unknown\" option, which it then removes when the mismatch is resolved.\n *\n * Optionally, a single hard-coded `<option>` element, with the value set to an empty string, can\n * be nested into the `<select>` element. This element will then represent the `null` or \"not selected\"\n * option. See example below for demonstration.\n *\n * ## Choosing between `ngRepeat` and `ngOptions`\n *\n * In many cases, `ngRepeat` can be used on `<option>` elements instead of {@link ng.directive:ngOptions\n * ngOptions} to achieve a similar result. However, `ngOptions` provides some benefits:\n * - more flexibility in how the `<select>`'s model is assigned via the `select` **`as`** part of the\n * comprehension expression\n * - reduced memory consumption by not creating a new scope for each repeated instance\n * - increased render speed by creating the options in a documentFragment instead of individually\n *\n * Specifically, select with repeated options slows down significantly starting at 2000 options in\n * Chrome and Internet Explorer / Edge.\n *\n *\n * @param {string} ngModel Assignable AngularJS expression to data-bind to.\n * @param {string=} name Property name of the form under which the control is published.\n * @param {string=} multiple Allows multiple options to be selected. The selected values will be\n *     bound to the model as an array.\n * @param {string=} required Sets `required` validation error key if the value is not entered.\n * @param {string=} ngRequired Adds required attribute and required validation constraint to\n * the element when the ngRequired expression evaluates to true. Use ngRequired instead of required\n * when you want to data-bind to the required attribute.\n * @param {string=} ngChange AngularJS expression to be executed when selected option(s) changes due to user\n *    interaction with the select element.\n * @param {string=} ngOptions sets the options that the select is populated with and defines what is\n * set on the model on selection. See {@link ngOptions `ngOptions`}.\n * @param {string=} ngAttrSize sets the size of the select element dynamically. Uses the\n * {@link guide/interpolation#-ngattr-for-binding-to-arbitrary-attributes ngAttr} directive.\n *\n *\n * @example\n * ### Simple `select` elements with static options\n *\n * <example name=\"static-select\" module=\"staticSelect\">\n * <file name=\"index.html\">\n * <div ng-controller=\"ExampleController\">\n *   <form name=\"myForm\">\n *     <label for=\"singleSelect\"> Single select: </label><br>\n *     <select name=\"singleSelect\" ng-model=\"data.singleSelect\">\n *       <option value=\"option-1\">Option 1</option>\n *       <option value=\"option-2\">Option 2</option>\n *     </select><br>\n *\n *     <label for=\"singleSelect\"> Single select with \"not selected\" option and dynamic option values: </label><br>\n *     <select name=\"singleSelect\" id=\"singleSelect\" ng-model=\"data.singleSelect\">\n *       <option value=\"\">---Please select---</option> <!-- not selected / blank option -->\n *       <option value=\"{{data.option1}}\">Option 1</option> <!-- interpolation -->\n *       <option value=\"option-2\">Option 2</option>\n *     </select><br>\n *     <button ng-click=\"forceUnknownOption()\">Force unknown option</button><br>\n *     <tt>singleSelect = {{data.singleSelect}}</tt>\n *\n *     <hr>\n *     <label for=\"multipleSelect\"> Multiple select: </label><br>\n *     <select name=\"multipleSelect\" id=\"multipleSelect\" ng-model=\"data.multipleSelect\" multiple>\n *       <option value=\"option-1\">Option 1</option>\n *       <option value=\"option-2\">Option 2</option>\n *       <option value=\"option-3\">Option 3</option>\n *     </select><br>\n *     <tt>multipleSelect = {{data.multipleSelect}}</tt><br/>\n *   </form>\n * </div>\n * </file>\n * <file name=\"app.js\">\n *  angular.module('staticSelect', [])\n *    .controller('ExampleController', ['$scope', function($scope) {\n *      $scope.data = {\n *       singleSelect: null,\n *       multipleSelect: [],\n *       option1: 'option-1'\n *      };\n *\n *      $scope.forceUnknownOption = function() {\n *        $scope.data.singleSelect = 'nonsense';\n *      };\n *   }]);\n * </file>\n *</example>\n *\n * @example\n * ### Using `ngRepeat` to generate `select` options\n * <example name=\"select-ngrepeat\" module=\"ngrepeatSelect\">\n * <file name=\"index.html\">\n * <div ng-controller=\"ExampleController\">\n *   <form name=\"myForm\">\n *     <label for=\"repeatSelect\"> Repeat select: </label>\n *     <select name=\"repeatSelect\" id=\"repeatSelect\" ng-model=\"data.model\">\n *       <option ng-repeat=\"option in data.availableOptions\" value=\"{{option.id}}\">{{option.name}}</option>\n *     </select>\n *   </form>\n *   <hr>\n *   <tt>model = {{data.model}}</tt><br/>\n * </div>\n * </file>\n * <file name=\"app.js\">\n *  angular.module('ngrepeatSelect', [])\n *    .controller('ExampleController', ['$scope', function($scope) {\n *      $scope.data = {\n *       model: null,\n *       availableOptions: [\n *         {id: '1', name: 'Option A'},\n *         {id: '2', name: 'Option B'},\n *         {id: '3', name: 'Option C'}\n *       ]\n *      };\n *   }]);\n * </file>\n *</example>\n *\n * @example\n * ### Using `ngValue` to bind the model to an array of objects\n * <example name=\"select-ngvalue\" module=\"ngvalueSelect\">\n * <file name=\"index.html\">\n * <div ng-controller=\"ExampleController\">\n *   <form name=\"myForm\">\n *     <label for=\"ngvalueselect\"> ngvalue select: </label>\n *     <select size=\"6\" name=\"ngvalueselect\" ng-model=\"data.model\" multiple>\n *       <option ng-repeat=\"option in data.availableOptions\" ng-value=\"option.value\">{{option.name}}</option>\n *     </select>\n *   </form>\n *   <hr>\n *   <pre>model = {{data.model | json}}</pre><br/>\n * </div>\n * </file>\n * <file name=\"app.js\">\n *  angular.module('ngvalueSelect', [])\n *    .controller('ExampleController', ['$scope', function($scope) {\n *      $scope.data = {\n *       model: null,\n *       availableOptions: [\n           {value: 'myString', name: 'string'},\n           {value: 1, name: 'integer'},\n           {value: true, name: 'boolean'},\n           {value: null, name: 'null'},\n           {value: {prop: 'value'}, name: 'object'},\n           {value: ['a'], name: 'array'}\n *       ]\n *      };\n *   }]);\n * </file>\n *</example>\n *\n * @example\n * ### Using `select` with `ngOptions` and setting a default value\n * See the {@link ngOptions ngOptions documentation} for more `ngOptions` usage examples.\n *\n * <example name=\"select-with-default-values\" module=\"defaultValueSelect\">\n * <file name=\"index.html\">\n * <div ng-controller=\"ExampleController\">\n *   <form name=\"myForm\">\n *     <label for=\"mySelect\">Make a choice:</label>\n *     <select name=\"mySelect\" id=\"mySelect\"\n *       ng-options=\"option.name for option in data.availableOptions track by option.id\"\n *       ng-model=\"data.selectedOption\"></select>\n *   </form>\n *   <hr>\n *   <tt>option = {{data.selectedOption}}</tt><br/>\n * </div>\n * </file>\n * <file name=\"app.js\">\n *  angular.module('defaultValueSelect', [])\n *    .controller('ExampleController', ['$scope', function($scope) {\n *      $scope.data = {\n *       availableOptions: [\n *         {id: '1', name: 'Option A'},\n *         {id: '2', name: 'Option B'},\n *         {id: '3', name: 'Option C'}\n *       ],\n *       selectedOption: {id: '3', name: 'Option C'} //This sets the default value of the select in the ui\n *       };\n *   }]);\n * </file>\n *</example>\n *\n * @example\n * ### Binding `select` to a non-string value via `ngModel` parsing / formatting\n *\n * <example name=\"select-with-non-string-options\" module=\"nonStringSelect\">\n *   <file name=\"index.html\">\n *     <select ng-model=\"model.id\" convert-to-number>\n *       <option value=\"0\">Zero</option>\n *       <option value=\"1\">One</option>\n *       <option value=\"2\">Two</option>\n *     </select>\n *     {{ model }}\n *   </file>\n *   <file name=\"app.js\">\n *     angular.module('nonStringSelect', [])\n *       .run(function($rootScope) {\n *         $rootScope.model = { id: 2 };\n *       })\n *       .directive('convertToNumber', function() {\n *         return {\n *           require: 'ngModel',\n *           link: function(scope, element, attrs, ngModel) {\n *             ngModel.$parsers.push(function(val) {\n *               return parseInt(val, 10);\n *             });\n *             ngModel.$formatters.push(function(val) {\n *               return '' + val;\n *             });\n *           }\n *         };\n *       });\n *   </file>\n *   <file name=\"protractor.js\" type=\"protractor\">\n *     it('should initialize to model', function() {\n *       expect(element(by.model('model.id')).$('option:checked').getText()).toEqual('Two');\n *     });\n *   </file>\n * </example>\n *\n */\nvar selectDirective = function() {\n\n  return {\n    restrict: 'E',\n    require: ['select', '?ngModel'],\n    controller: SelectController,\n    priority: 1,\n    link: {\n      pre: selectPreLink,\n      post: selectPostLink\n    }\n  };\n\n  function selectPreLink(scope, element, attr, ctrls) {\n\n      var selectCtrl = ctrls[0];\n      var ngModelCtrl = ctrls[1];\n\n      // if ngModel is not defined, we don't need to do anything but set the registerOption\n      // function to noop, so options don't get added internally\n      if (!ngModelCtrl) {\n        selectCtrl.registerOption = noop;\n        return;\n      }\n\n\n      selectCtrl.ngModelCtrl = ngModelCtrl;\n\n      // When the selected item(s) changes we delegate getting the value of the select control\n      // to the `readValue` method, which can be changed if the select can have multiple\n      // selected values or if the options are being generated by `ngOptions`\n      element.on('change', function() {\n        selectCtrl.removeUnknownOption();\n        scope.$apply(function() {\n          ngModelCtrl.$setViewValue(selectCtrl.readValue());\n        });\n      });\n\n      // If the select allows multiple values then we need to modify how we read and write\n      // values from and to the control; also what it means for the value to be empty and\n      // we have to add an extra watch since ngModel doesn't work well with arrays - it\n      // doesn't trigger rendering if only an item in the array changes.\n      if (attr.multiple) {\n        selectCtrl.multiple = true;\n\n        // Read value now needs to check each option to see if it is selected\n        selectCtrl.readValue = function readMultipleValue() {\n          var array = [];\n          forEach(element.find('option'), function(option) {\n            if (option.selected && !option.disabled) {\n              var val = option.value;\n              array.push(val in selectCtrl.selectValueMap ? selectCtrl.selectValueMap[val] : val);\n            }\n          });\n          return array;\n        };\n\n        // Write value now needs to set the selected property of each matching option\n        selectCtrl.writeValue = function writeMultipleValue(value) {\n          forEach(element.find('option'), function(option) {\n            var shouldBeSelected = !!value && (includes(value, option.value) ||\n                                               includes(value, selectCtrl.selectValueMap[option.value]));\n            var currentlySelected = option.selected;\n\n            // Support: IE 9-11 only, Edge 12-15+\n            // In IE and Edge adding options to the selection via shift+click/UP/DOWN\n            // will de-select already selected options if \"selected\" on those options was set\n            // more than once (i.e. when the options were already selected)\n            // So we only modify the selected property if necessary.\n            // Note: this behavior cannot be replicated via unit tests because it only shows in the\n            // actual user interface.\n            if (shouldBeSelected !== currentlySelected) {\n              setOptionSelectedStatus(jqLite(option), shouldBeSelected);\n            }\n\n          });\n        };\n\n        // we have to do it on each watch since ngModel watches reference, but\n        // we need to work of an array, so we need to see if anything was inserted/removed\n        var lastView, lastViewRef = NaN;\n        scope.$watch(function selectMultipleWatch() {\n          if (lastViewRef === ngModelCtrl.$viewValue && !equals(lastView, ngModelCtrl.$viewValue)) {\n            lastView = shallowCopy(ngModelCtrl.$viewValue);\n            ngModelCtrl.$render();\n          }\n          lastViewRef = ngModelCtrl.$viewValue;\n        });\n\n        // If we are a multiple select then value is now a collection\n        // so the meaning of $isEmpty changes\n        ngModelCtrl.$isEmpty = function(value) {\n          return !value || value.length === 0;\n        };\n\n      }\n    }\n\n    function selectPostLink(scope, element, attrs, ctrls) {\n      // if ngModel is not defined, we don't need to do anything\n      var ngModelCtrl = ctrls[1];\n      if (!ngModelCtrl) return;\n\n      var selectCtrl = ctrls[0];\n\n      // We delegate rendering to the `writeValue` method, which can be changed\n      // if the select can have multiple selected values or if the options are being\n      // generated by `ngOptions`.\n      // This must be done in the postLink fn to prevent $render to be called before\n      // all nodes have been linked correctly.\n      ngModelCtrl.$render = function() {\n        selectCtrl.writeValue(ngModelCtrl.$viewValue);\n      };\n    }\n};\n\n\n// The option directive is purely designed to communicate the existence (or lack of)\n// of dynamically created (and destroyed) option elements to their containing select\n// directive via its controller.\nvar optionDirective = ['$interpolate', function($interpolate) {\n  return {\n    restrict: 'E',\n    priority: 100,\n    compile: function(element, attr) {\n      var interpolateValueFn, interpolateTextFn;\n\n      if (isDefined(attr.ngValue)) {\n        // Will be handled by registerOption\n      } else if (isDefined(attr.value)) {\n        // If the value attribute is defined, check if it contains an interpolation\n        interpolateValueFn = $interpolate(attr.value, true);\n      } else {\n        // If the value attribute is not defined then we fall back to the\n        // text content of the option element, which may be interpolated\n        interpolateTextFn = $interpolate(element.text(), true);\n        if (!interpolateTextFn) {\n          attr.$set('value', element.text());\n        }\n      }\n\n      return function(scope, element, attr) {\n        // This is an optimization over using ^^ since we don't want to have to search\n        // all the way to the root of the DOM for every single option element\n        var selectCtrlName = '$selectController',\n            parent = element.parent(),\n            selectCtrl = parent.data(selectCtrlName) ||\n              parent.parent().data(selectCtrlName); // in case we are in optgroup\n\n        if (selectCtrl) {\n          selectCtrl.registerOption(scope, element, attr, interpolateValueFn, interpolateTextFn);\n        }\n      };\n    }\n  };\n}];\n\n/**\n * @ngdoc directive\n * @name ngRequired\n * @restrict A\n *\n * @param {expression} ngRequired AngularJS expression. If it evaluates to `true`, it sets the\n *                                `required` attribute to the element and adds the `required`\n *                                {@link ngModel.NgModelController#$validators `validator`}.\n *\n * @description\n *\n * ngRequired adds the required {@link ngModel.NgModelController#$validators `validator`} to {@link ngModel `ngModel`}.\n * It is most often used for {@link input `input`} and {@link select `select`} controls, but can also be\n * applied to custom controls.\n *\n * The directive sets the `required` attribute on the element if the AngularJS expression inside\n * `ngRequired` evaluates to true. A special directive for setting `required` is necessary because we\n * cannot use interpolation inside `required`. See the {@link guide/interpolation interpolation guide}\n * for more info.\n *\n * The validator will set the `required` error key to true if the `required` attribute is set and\n * calling {@link ngModel.NgModelController#$isEmpty `NgModelController.$isEmpty`} with the\n * {@link ngModel.NgModelController#$viewValue `ngModel.$viewValue`} returns `true`. For example, the\n * `$isEmpty()` implementation for `input[text]` checks the length of the `$viewValue`. When developing\n * custom controls, `$isEmpty()` can be overwritten to account for a $viewValue that is not string-based.\n *\n * @example\n * <example name=\"ngRequiredDirective\" module=\"ngRequiredExample\">\n *   <file name=\"index.html\">\n *     <script>\n *       angular.module('ngRequiredExample', [])\n *         .controller('ExampleController', ['$scope', function($scope) {\n *           $scope.required = true;\n *         }]);\n *     </script>\n *     <div ng-controller=\"ExampleController\">\n *       <form name=\"form\">\n *         <label for=\"required\">Toggle required: </label>\n *         <input type=\"checkbox\" ng-model=\"required\" id=\"required\" />\n *         <br>\n *         <label for=\"input\">This input must be filled if `required` is true: </label>\n *         <input type=\"text\" ng-model=\"model\" id=\"input\" name=\"input\" ng-required=\"required\" /><br>\n *         <hr>\n *         required error set? = <code>{{form.input.$error.required}}</code><br>\n *         model = <code>{{model}}</code>\n *       </form>\n *     </div>\n *   </file>\n *   <file name=\"protractor.js\" type=\"protractor\">\n       var required = element(by.binding('form.input.$error.required'));\n       var model = element(by.binding('model'));\n       var input = element(by.id('input'));\n\n       it('should set the required error', function() {\n         expect(required.getText()).toContain('true');\n\n         input.sendKeys('123');\n         expect(required.getText()).not.toContain('true');\n         expect(model.getText()).toContain('123');\n       });\n *   </file>\n * </example>\n */\nvar requiredDirective = ['$parse', function($parse) {\n  return {\n    restrict: 'A',\n    require: '?ngModel',\n    link: function(scope, elm, attr, ctrl) {\n      if (!ctrl) return;\n      // For boolean attributes like required, presence means true\n      var value = attr.hasOwnProperty('required') || $parse(attr.ngRequired)(scope);\n\n      if (!attr.ngRequired) {\n        // force truthy in case we are on non input element\n        // (input elements do this automatically for boolean attributes like required)\n        attr.required = true;\n      }\n\n      ctrl.$validators.required = function(modelValue, viewValue) {\n        return !value || !ctrl.$isEmpty(viewValue);\n      };\n\n      attr.$observe('required', function(newVal) {\n\n        if (value !== newVal) {\n          value = newVal;\n          ctrl.$validate();\n        }\n      });\n    }\n  };\n}];\n\n/**\n * @ngdoc directive\n * @name ngPattern\n * @restrict A\n *\n * @param {expression|RegExp} ngPattern AngularJS expression that must evaluate to a `RegExp` or a `String`\n *                                      parsable into a `RegExp`, or a `RegExp` literal. See above for\n *                                      more details.\n *\n * @description\n *\n * ngPattern adds the pattern {@link ngModel.NgModelController#$validators `validator`} to {@link ngModel `ngModel`}.\n * It is most often used for text-based {@link input `input`} controls, but can also be applied to custom text-based controls.\n *\n * The validator sets the `pattern` error key if the {@link ngModel.NgModelController#$viewValue `ngModel.$viewValue`}\n * does not match a RegExp which is obtained from the `ngPattern` attribute value:\n * - the value is an AngularJS expression:\n *   - If the expression evaluates to a RegExp object, then this is used directly.\n *   - If the expression evaluates to a string, then it will be converted to a RegExp after wrapping it\n *     in `^` and `$` characters. For instance, `\"abc\"` will be converted to `new RegExp('^abc$')`.\n * - If the value is a RegExp literal, e.g. `ngPattern=\"/^\\d+$/\"`, it is used directly.\n *\n * <div class=\"alert alert-info\">\n * **Note:** Avoid using the `g` flag on the RegExp, as it will cause each successive search to\n * start at the index of the last search's match, thus not taking the whole input value into\n * account.\n * </div>\n *\n * <div class=\"alert alert-info\">\n * **Note:** This directive is also added when the plain `pattern` attribute is used, with two\n * differences:\n * <ol>\n *   <li>\n *     `ngPattern` does not set the `pattern` attribute and therefore HTML5 constraint validation is\n *     not available.\n *   </li>\n *   <li>\n *     The `ngPattern` attribute must be an expression, while the `pattern` value must be\n *     interpolated.\n *   </li>\n * </ol>\n * </div>\n *\n * @example\n * <example name=\"ngPatternDirective\" module=\"ngPatternExample\">\n *   <file name=\"index.html\">\n *     <script>\n *       angular.module('ngPatternExample', [])\n *         .controller('ExampleController', ['$scope', function($scope) {\n *           $scope.regex = '\\\\d+';\n *         }]);\n *     </script>\n *     <div ng-controller=\"ExampleController\">\n *       <form name=\"form\">\n *         <label for=\"regex\">Set a pattern (regex string): </label>\n *         <input type=\"text\" ng-model=\"regex\" id=\"regex\" />\n *         <br>\n *         <label for=\"input\">This input is restricted by the current pattern: </label>\n *         <input type=\"text\" ng-model=\"model\" id=\"input\" name=\"input\" ng-pattern=\"regex\" /><br>\n *         <hr>\n *         input valid? = <code>{{form.input.$valid}}</code><br>\n *         model = <code>{{model}}</code>\n *       </form>\n *     </div>\n *   </file>\n *   <file name=\"protractor.js\" type=\"protractor\">\n       var model = element(by.binding('model'));\n       var input = element(by.id('input'));\n\n       it('should validate the input with the default pattern', function() {\n         input.sendKeys('aaa');\n         expect(model.getText()).not.toContain('aaa');\n\n         input.clear().then(function() {\n           input.sendKeys('123');\n           expect(model.getText()).toContain('123');\n         });\n       });\n *   </file>\n * </example>\n */\nvar patternDirective = ['$parse', function($parse) {\n  return {\n    restrict: 'A',\n    require: '?ngModel',\n    compile: function(tElm, tAttr) {\n      var patternExp;\n      var parseFn;\n\n      if (tAttr.ngPattern) {\n        patternExp = tAttr.ngPattern;\n\n        // ngPattern might be a scope expression, or an inlined regex, which is not parsable.\n        // We get value of the attribute here, so we can compare the old and the new value\n        // in the observer to avoid unnecessary validations\n        if (tAttr.ngPattern.charAt(0) === '/' && REGEX_STRING_REGEXP.test(tAttr.ngPattern)) {\n          parseFn = function() { return tAttr.ngPattern; };\n        } else {\n          parseFn = $parse(tAttr.ngPattern);\n        }\n      }\n\n      return function(scope, elm, attr, ctrl) {\n        if (!ctrl) return;\n\n        var attrVal = attr.pattern;\n\n        if (attr.ngPattern) {\n          attrVal = parseFn(scope);\n        } else {\n          patternExp = attr.pattern;\n        }\n\n        var regexp = parsePatternAttr(attrVal, patternExp, elm);\n\n        attr.$observe('pattern', function(newVal) {\n          var oldRegexp = regexp;\n\n          regexp = parsePatternAttr(newVal, patternExp, elm);\n\n          if ((oldRegexp && oldRegexp.toString()) !== (regexp && regexp.toString())) {\n            ctrl.$validate();\n          }\n        });\n\n        ctrl.$validators.pattern = function(modelValue, viewValue) {\n          // HTML5 pattern constraint validates the input value, so we validate the viewValue\n          return ctrl.$isEmpty(viewValue) || isUndefined(regexp) || regexp.test(viewValue);\n        };\n      };\n    }\n\n  };\n}];\n\n/**\n * @ngdoc directive\n * @name ngMaxlength\n * @restrict A\n *\n * @param {expression} ngMaxlength AngularJS expression that must evaluate to a `Number` or `String`\n *                                 parsable into a `Number`. Used as value for the `maxlength`\n *                                 {@link ngModel.NgModelController#$validators validator}.\n *\n * @description\n *\n * ngMaxlength adds the maxlength {@link ngModel.NgModelController#$validators `validator`} to {@link ngModel `ngModel`}.\n * It is most often used for text-based {@link input `input`} controls, but can also be applied to custom text-based controls.\n *\n * The validator sets the `maxlength` error key if the {@link ngModel.NgModelController#$viewValue `ngModel.$viewValue`}\n * is longer than the integer obtained by evaluating the AngularJS expression given in the\n * `ngMaxlength` attribute value.\n *\n * <div class=\"alert alert-info\">\n * **Note:** This directive is also added when the plain `maxlength` attribute is used, with two\n * differences:\n * <ol>\n *   <li>\n *     `ngMaxlength` does not set the `maxlength` attribute and therefore HTML5 constraint\n *     validation is not available.\n *   </li>\n *   <li>\n *     The `ngMaxlength` attribute must be an expression, while the `maxlength` value must be\n *     interpolated.\n *   </li>\n * </ol>\n * </div>\n *\n * @example\n * <example name=\"ngMaxlengthDirective\" module=\"ngMaxlengthExample\">\n *   <file name=\"index.html\">\n *     <script>\n *       angular.module('ngMaxlengthExample', [])\n *         .controller('ExampleController', ['$scope', function($scope) {\n *           $scope.maxlength = 5;\n *         }]);\n *     </script>\n *     <div ng-controller=\"ExampleController\">\n *       <form name=\"form\">\n *         <label for=\"maxlength\">Set a maxlength: </label>\n *         <input type=\"number\" ng-model=\"maxlength\" id=\"maxlength\" />\n *         <br>\n *         <label for=\"input\">This input is restricted by the current maxlength: </label>\n *         <input type=\"text\" ng-model=\"model\" id=\"input\" name=\"input\" ng-maxlength=\"maxlength\" /><br>\n *         <hr>\n *         input valid? = <code>{{form.input.$valid}}</code><br>\n *         model = <code>{{model}}</code>\n *       </form>\n *     </div>\n *   </file>\n *   <file name=\"protractor.js\" type=\"protractor\">\n       var model = element(by.binding('model'));\n       var input = element(by.id('input'));\n\n       it('should validate the input with the default maxlength', function() {\n         input.sendKeys('abcdef');\n         expect(model.getText()).not.toContain('abcdef');\n\n         input.clear().then(function() {\n           input.sendKeys('abcde');\n           expect(model.getText()).toContain('abcde');\n         });\n       });\n *   </file>\n * </example>\n */\nvar maxlengthDirective = ['$parse', function($parse) {\n  return {\n    restrict: 'A',\n    require: '?ngModel',\n    link: function(scope, elm, attr, ctrl) {\n      if (!ctrl) return;\n\n      var maxlength = attr.maxlength || $parse(attr.ngMaxlength)(scope);\n      var maxlengthParsed = parseLength(maxlength);\n\n      attr.$observe('maxlength', function(value) {\n        if (maxlength !== value) {\n          maxlengthParsed = parseLength(value);\n          maxlength = value;\n          ctrl.$validate();\n        }\n      });\n      ctrl.$validators.maxlength = function(modelValue, viewValue) {\n        return (maxlengthParsed < 0) || ctrl.$isEmpty(viewValue) || (viewValue.length <= maxlengthParsed);\n      };\n    }\n  };\n}];\n\n/**\n * @ngdoc directive\n * @name ngMinlength\n * @restrict A\n *\n * @param {expression} ngMinlength AngularJS expression that must evaluate to a `Number` or `String`\n *                                 parsable into a `Number`. Used as value for the `minlength`\n *                                 {@link ngModel.NgModelController#$validators validator}.\n *\n * @description\n *\n * ngMinlength adds the minlength {@link ngModel.NgModelController#$validators `validator`} to {@link ngModel `ngModel`}.\n * It is most often used for text-based {@link input `input`} controls, but can also be applied to custom text-based controls.\n *\n * The validator sets the `minlength` error key if the {@link ngModel.NgModelController#$viewValue `ngModel.$viewValue`}\n * is shorter than the integer obtained by evaluating the AngularJS expression given in the\n * `ngMinlength` attribute value.\n *\n * <div class=\"alert alert-info\">\n * **Note:** This directive is also added when the plain `minlength` attribute is used, with two\n * differences:\n * <ol>\n *   <li>\n *     `ngMinlength` does not set the `minlength` attribute and therefore HTML5 constraint\n *     validation is not available.\n *   </li>\n *   <li>\n *     The `ngMinlength` value must be an expression, while the `minlength` value must be\n *     interpolated.\n *   </li>\n * </ol>\n * </div>\n *\n * @example\n * <example name=\"ngMinlengthDirective\" module=\"ngMinlengthExample\">\n *   <file name=\"index.html\">\n *     <script>\n *       angular.module('ngMinlengthExample', [])\n *         .controller('ExampleController', ['$scope', function($scope) {\n *           $scope.minlength = 3;\n *         }]);\n *     </script>\n *     <div ng-controller=\"ExampleController\">\n *       <form name=\"form\">\n *         <label for=\"minlength\">Set a minlength: </label>\n *         <input type=\"number\" ng-model=\"minlength\" id=\"minlength\" />\n *         <br>\n *         <label for=\"input\">This input is restricted by the current minlength: </label>\n *         <input type=\"text\" ng-model=\"model\" id=\"input\" name=\"input\" ng-minlength=\"minlength\" /><br>\n *         <hr>\n *         input valid? = <code>{{form.input.$valid}}</code><br>\n *         model = <code>{{model}}</code>\n *       </form>\n *     </div>\n *   </file>\n *   <file name=\"protractor.js\" type=\"protractor\">\n       var model = element(by.binding('model'));\n       var input = element(by.id('input'));\n\n       it('should validate the input with the default minlength', function() {\n         input.sendKeys('ab');\n         expect(model.getText()).not.toContain('ab');\n\n         input.sendKeys('abc');\n         expect(model.getText()).toContain('abc');\n       });\n *   </file>\n * </example>\n */\nvar minlengthDirective = ['$parse', function($parse) {\n  return {\n    restrict: 'A',\n    require: '?ngModel',\n    link: function(scope, elm, attr, ctrl) {\n      if (!ctrl) return;\n\n      var minlength = attr.minlength || $parse(attr.ngMinlength)(scope);\n      var minlengthParsed = parseLength(minlength) || -1;\n\n      attr.$observe('minlength', function(value) {\n        if (minlength !== value) {\n          minlengthParsed = parseLength(value) || -1;\n          minlength = value;\n          ctrl.$validate();\n        }\n\n      });\n      ctrl.$validators.minlength = function(modelValue, viewValue) {\n        return ctrl.$isEmpty(viewValue) || viewValue.length >= minlengthParsed;\n      };\n    }\n  };\n}];\n\n\nfunction parsePatternAttr(regex, patternExp, elm) {\n  if (!regex) return undefined;\n\n  if (isString(regex)) {\n    regex = new RegExp('^' + regex + '$');\n  }\n\n  if (!regex.test) {\n    throw minErr('ngPattern')('noregexp',\n      'Expected {0} to be a RegExp but was {1}. Element: {2}', patternExp,\n      regex, startingTag(elm));\n  }\n\n  return regex;\n}\n\nfunction parseLength(val) {\n  var intVal = toInt(val);\n  return isNumberNaN(intVal) ? -1 : intVal;\n}\n\nif (window.angular.bootstrap) {\n  // AngularJS is already loaded, so we can return here...\n  if (window.console) {\n    console.log('WARNING: Tried to load AngularJS more than once.');\n  }\n  return;\n}\n\n// try to bind to jquery now so that one can write jqLite(fn)\n// but we will rebind on bootstrap again.\nbindJQuery();\n\npublishExternalAPI(angular);\n\nangular.module(\"ngLocale\", [], [\"$provide\", function($provide) {\nvar PLURAL_CATEGORY = {ZERO: \"zero\", ONE: \"one\", TWO: \"two\", FEW: \"few\", MANY: \"many\", OTHER: \"other\"};\nfunction getDecimals(n) {\n  n = n + '';\n  var i = n.indexOf('.');\n  return (i == -1) ? 0 : n.length - i - 1;\n}\n\nfunction getVF(n, opt_precision) {\n  var v = opt_precision;\n\n  if (undefined === v) {\n    v = Math.min(getDecimals(n), 3);\n  }\n\n  var base = Math.pow(10, v);\n  var f = ((n * base) | 0) % base;\n  return {v: v, f: f};\n}\n\n$provide.value(\"$locale\", {\n  \"DATETIME_FORMATS\": {\n    \"AMPMS\": [\n      \"AM\",\n      \"PM\"\n    ],\n    \"DAY\": [\n      \"Sunday\",\n      \"Monday\",\n      \"Tuesday\",\n      \"Wednesday\",\n      \"Thursday\",\n      \"Friday\",\n      \"Saturday\"\n    ],\n    \"ERANAMES\": [\n      \"Before Christ\",\n      \"Anno Domini\"\n    ],\n    \"ERAS\": [\n      \"BC\",\n      \"AD\"\n    ],\n    \"FIRSTDAYOFWEEK\": 6,\n    \"MONTH\": [\n      \"January\",\n      \"February\",\n      \"March\",\n      \"April\",\n      \"May\",\n      \"June\",\n      \"July\",\n      \"August\",\n      \"September\",\n      \"October\",\n      \"November\",\n      \"December\"\n    ],\n    \"SHORTDAY\": [\n      \"Sun\",\n      \"Mon\",\n      \"Tue\",\n      \"Wed\",\n      \"Thu\",\n      \"Fri\",\n      \"Sat\"\n    ],\n    \"SHORTMONTH\": [\n      \"Jan\",\n      \"Feb\",\n      \"Mar\",\n      \"Apr\",\n      \"May\",\n      \"Jun\",\n      \"Jul\",\n      \"Aug\",\n      \"Sep\",\n      \"Oct\",\n      \"Nov\",\n      \"Dec\"\n    ],\n    \"STANDALONEMONTH\": [\n      \"January\",\n      \"February\",\n      \"March\",\n      \"April\",\n      \"May\",\n      \"June\",\n      \"July\",\n      \"August\",\n      \"September\",\n      \"October\",\n      \"November\",\n      \"December\"\n    ],\n    \"WEEKENDRANGE\": [\n      5,\n      6\n    ],\n    \"fullDate\": \"EEEE, MMMM d, y\",\n    \"longDate\": \"MMMM d, y\",\n    \"medium\": \"MMM d, y h:mm:ss a\",\n    \"mediumDate\": \"MMM d, y\",\n    \"mediumTime\": \"h:mm:ss a\",\n    \"short\": \"M/d/yy h:mm a\",\n    \"shortDate\": \"M/d/yy\",\n    \"shortTime\": \"h:mm a\"\n  },\n  \"NUMBER_FORMATS\": {\n    \"CURRENCY_SYM\": \"$\",\n    \"DECIMAL_SEP\": \".\",\n    \"GROUP_SEP\": \",\",\n    \"PATTERNS\": [\n      {\n        \"gSize\": 3,\n        \"lgSize\": 3,\n        \"maxFrac\": 3,\n        \"minFrac\": 0,\n        \"minInt\": 1,\n        \"negPre\": \"-\",\n        \"negSuf\": \"\",\n        \"posPre\": \"\",\n        \"posSuf\": \"\"\n      },\n      {\n        \"gSize\": 3,\n        \"lgSize\": 3,\n        \"maxFrac\": 2,\n        \"minFrac\": 2,\n        \"minInt\": 1,\n        \"negPre\": \"-\\u00a4\",\n        \"negSuf\": \"\",\n        \"posPre\": \"\\u00a4\",\n        \"posSuf\": \"\"\n      }\n    ]\n  },\n  \"id\": \"en-us\",\n  \"localeID\": \"en_US\",\n  \"pluralCat\": function(n, opt_precision) {  var i = n | 0;  var vf = getVF(n, opt_precision);  if (i == 1 && vf.v == 0) {    return PLURAL_CATEGORY.ONE;  }  return PLURAL_CATEGORY.OTHER;}\n});\n}]);\n\n  jqLite(function() {\n    angularInit(window.document, bootstrap);\n  });\n\n})(window);\n\n!window.angular.$$csp().noInlineStyle && window.angular.element(document.head).prepend(window.angular.element('<style>').text('@charset \"UTF-8\";[ng\\\\:cloak],[ng-cloak],[data-ng-cloak],[x-ng-cloak],.ng-cloak,.x-ng-cloak,.ng-hide:not(.ng-hide-animate){display:none !important;}ng\\\\:form{display:block;}.ng-animate-shim{visibility:hidden;}.ng-anchor{position:absolute;}'));","require('./angular');\nmodule.exports = angular;\n","import angular from \"angular\";\r\n\r\nimport { ApiCrudObject, ApiListItem, CrudApiBase, IUserObjectIndex, ODataQueryOptions, ODataResult, VersionInfo, WorkflowEvent } from \"@salaxy/core\";\r\n\r\nimport { UiHelpers } from \"../../services\";\r\nimport { ODataQueryController } from \"./ODataQueryController\";\r\n\r\n/**\r\n * Base class for version 03 CRUD controllers where OData list functionality has been\r\n * separated from the item editing CRUD functionality.\r\n * This version also shifts away from the old Service-infrastructure.\r\n */\r\nexport abstract class ApiCrudObjectController<TItem extends ApiCrudObject, TListItem extends ApiListItem> implements angular.IController {\r\n\r\n  /**\r\n   * Defines the binding mode of the component.\r\n   *\r\n   * - \"model\" takes the model directly from the model parameter.\r\n   * - \"parentCtrl\" takes the model from the given parent controller. Main actions (like Save, reload) are delegated to that controller.\r\n   * - \"id\" fetches the item from the server using the current-id attribute (currentId property).\r\n   * - \"url\" like \"id\", but the id is fetched from route parameters.\r\n   * - \"new\" Creates a new item as current.\r\n   * - \"null\": Current item is null\r\n   *\r\n   * The mode is set in the model property setter.\r\n   */\r\n  public bindingMode: \"id\" | \"url\" | \"model\" | \"parentCtrl\" | \"new\" | \"null\";\r\n\r\n  /** Action for the controller */\r\n  public action: \"default\" | \"copy-as-new\" | string;\r\n\r\n  /**\r\n   * For list-controls, this is the URL for item select event\r\n   * as well as the URL where a new item is edited. Basically showing the Details view.\r\n   * Id is added directly to the string and this is an angular route.\r\n   * I.e. use \"/calc/details/\" (not \"#/calc/details/\" or \"/calc/details\")\r\n   * For more control, use onListSelect or onCreateNew events.\r\n   * @example <salaxy-payroll-list details-url=\"/myCustomRoute/\"></salaxy-payroll-list>\r\n   */\r\n  public detailsUrl: string;\r\n\r\n  /**\r\n   * URL for the list view. At the moment, if specified, the browser is redirected here after delete.\r\n   * @example\r\n   * <!-- Main worker list is in the front page in this case -->\r\n   * <salaxy-employment-details list-url=\"/home\"></salaxy-employment-details>\r\n   */\r\n  public listUrl: string;\r\n\r\n  /** If the Crud controller is used from within a ODataQueryController, this is the containing controller. */\r\n  public odataController: ODataQueryController;\r\n\r\n  /** If the controller is bound to parent controller, the controller is set here. */\r\n  public parentController: ApiCrudObjectController<TItem, TListItem>;\r\n\r\n  /**\r\n   * Contains the inner value currentId if stored by this controller and not the parent.\r\n   */\r\n  protected _currentId: string;\r\n\r\n  /**\r\n   * The status of the data loading for the current controller.\r\n   */\r\n  private _status: \"noInit\" | \"initialLoading\" | \"loaded\" | \"reloading\" | \"loadError\" = \"noInit\";\r\n  private _current: TItem;\r\n\r\n  private _original: TItem;\r\n\r\n  private _model: any;\r\n\r\n  /** If true, current item is read only */\r\n  private _isReadOnlyForced: boolean;\r\n  private _versions: VersionInfo[];\r\n\r\n  private _versionsId: string;\r\n  private _version: { version: VersionInfo, item?: TItem };\r\n  private _versionId: string;\r\n\r\n  /** The status of the initialization process $onInit  */\r\n  protected initStatus = {\r\n    isInitDone: false,\r\n    isReloadRequested: false,\r\n  };\r\n\r\n  /**\r\n   * Creates a new CrudControllerBase.\r\n   * @param api Api module typically defined in @salaxy/core used for communicating to server.\r\n   * @param uiHelpers - Salaxy ui helpers service.\r\n   * @param $location Angular.js Location service that is used for navigation. Especially the list views.\r\n   * @param $routeParams - Angular.js routing component\r\n   */\r\n  constructor(\r\n    protected api: CrudApiBase<TItem, TListItem>,\r\n    protected uiHelpers: UiHelpers,\r\n    protected $location: angular.ILocationService,\r\n    protected $routeParams: any,\r\n  ) {\r\n    if (!api) {\r\n      throw new Error(\"api is undefined in ApiCrudObjectController\");\r\n    }\r\n    if (!uiHelpers) {\r\n      throw new Error(\"uiHelpers is undefined in ApiCrudObjectController\");\r\n    }\r\n    if (!$location) {\r\n      throw new Error(\"$location is undefined in ApiCrudObjectController\");\r\n    }\r\n    if (!$routeParams) {\r\n      throw new Error(\"$routeParams is undefined in ApiCrudObjectController\");\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Implement IController by providing onInit method.\r\n   * We currently do nothing here, but if you override this function,\r\n   * you should call this method in base class for future compatibility.\r\n   */\r\n  public $onInit() {\r\n    this.bindingMode = this.bindingMode || \"null\";\r\n    if (this.initStatus.isReloadRequested) {\r\n      this.initStatus.isReloadRequested = false;\r\n      this.reload();\r\n    }\r\n    this.initStatus.isInitDone = true;\r\n  }\r\n\r\n  /** URL for the OData list service */\r\n  public get odataServiceUrl(): string {\r\n    return this.parentController ? this.parentController.odataServiceUrl : this.api.getODataUrl();\r\n  }\r\n\r\n  /**\r\n   * Set the Current selected item (the model).\r\n   * The model may be:\r\n   *\r\n   * - TItem: A bound item (default), which can also be null.\r\n   * - ApiCrudObjectController<TItem>: Parent controller of the same type. Model is fetched from its current and all methods are delegated.\r\n   * - \"new\": A new item is created.\r\n   * - \"url\": Fetches the item from the server using the id query string (crudItemId in routeParams).\r\n   * - string: Any other string is interpreted as id which is used to fetch the item from the server.\r\n   */\r\n  public set model(value: \"new\" | \"url\" | string | TItem | ApiCrudObjectController<TItem, TListItem>) {\r\n    this._model = value;\r\n    if (!value) {\r\n      this._currentId = null;\r\n      this.bindingMode = \"null\";\r\n      this.parentController = null;\r\n    } else if (value === \"new\") {\r\n      this._currentId = null;\r\n      this.bindingMode = \"new\";\r\n      this.parentController = null;\r\n    } else if (value === \"url\") {\r\n      this._currentId = this.getRouteData().id;\r\n      this.bindingMode = (this.currentId ? \"url\" : \"null\");\r\n      this.parentController = null;\r\n      this.action = this.action || this.getRouteData().action;\r\n    } else if (angular.isString(value)) {\r\n      this._currentId = value;\r\n      this.bindingMode = (this.currentId ? \"id\" : \"null\");\r\n      this.parentController = null;\r\n    } else {\r\n      if (value && (value as ApiCrudObjectController<TItem, TListItem>).$onInit) {\r\n        // If parent controller, we do not call reload() - it shold be called by the parent itself.\r\n        this.bindingMode = \"parentCtrl\";\r\n        this.parentController = value as ApiCrudObjectController<TItem, TListItem>;\r\n        this.action = this.parentController.action;\r\n        return;\r\n      } else {\r\n        this._currentId = null; // Getter gets it from the object itself.\r\n        this.bindingMode = \"model\";\r\n        this.parentController = null;\r\n      }\r\n    }\r\n    this.action = this.action || \"default\";\r\n    if (this.initStatus.isInitDone) {\r\n      this.reload();\r\n    } else {\r\n      this.initStatus.isReloadRequested = true;\r\n    }\r\n  }\r\n  /** Gets the Current selected item (the model).  */\r\n  public get model() {\r\n    return this._model;\r\n  }\r\n\r\n  /** Gets the Current selected item. */\r\n  public get current(): TItem {\r\n    return this.parentController ? this.parentController.current : this._current;\r\n  }\r\n\r\n  /** The current Id for the controller. */\r\n  public get currentId(): string {\r\n    if (this.parentController) {\r\n      return this.parentController.currentId;\r\n    }\r\n    return this._currentId || (this.current ? this.current.id : null);\r\n  }\r\n\r\n  /** Gets the Original item before changes. */\r\n  public get original(): TItem {\r\n    return this.parentController ? this.parentController.original : this._original;\r\n  }\r\n\r\n  /** Gets the isReadOnlyForced status. */\r\n  public get isReadOnlyForced(): boolean {\r\n    return this.parentController ? this.parentController.isReadOnlyForced : this._isReadOnlyForced;\r\n  }\r\n\r\n  /** Sets the isReadOnlyForced status. */\r\n  public set isReadOnlyForced(value: boolean) {\r\n    /* do not set values by non-bound variables */\r\n    if (value === undefined) {\r\n      return;\r\n    }\r\n    if (this.parentController) {\r\n      this.parentController.isReadOnlyForced = value;\r\n    } else {\r\n      this._isReadOnlyForced = value;\r\n    }\r\n  }\r\n  /**\r\n   * Gets the defaults for service-specific URLs, options etc.\r\n   * This method must be implemented when implementing ApiCrudObjectController.\r\n   */\r\n  public abstract getDefaults(): {\r\n    /**\r\n     * URL for the list view. This is list-url attribute with controller-specific default value (e.g. \"/articles\").\r\n     * At the moment, if specified, the browser is redirected here after delete.\r\n     */\r\n    listUrl: string,\r\n\r\n    /**\r\n     * For lists, this is the URL for item select event as well as the URL where a new item is edited.\r\n     * Basically showing the Details view. For more control, use onListSelect or onCreateNew events.\r\n     * This is details-url attribute with controller-specific default value.\r\n     * Id is added directly to the string and this is an angular route.\r\n     * I.e. use \"/calc/details/\" (not \"#/calc/details/\" or \"/calc/details\")\r\n     */\r\n    detailsUrl: string,\r\n\r\n    /** Template for displaying the items as list.  */\r\n    oDataTemplateUrl: string,\r\n\r\n    /** The OData options for default query. */\r\n    oDataOptions: ODataQueryOptions,\r\n  };\r\n\r\n  /** If true, this is a new unsaved object */\r\n  public isNew(): boolean {\r\n    if (this.parentController) {\r\n      return this.parentController.isNew();\r\n    }\r\n    return !this.currentId || this.currentId === \"new\" || this.action === \"copy-as-new\";\r\n  }\r\n\r\n  /** If true, the component is in the middle of loading data. */\r\n  public get isLoading() {\r\n    switch (this.status) {\r\n      case \"initialLoading\":\r\n      case \"reloading\":\r\n        return true;\r\n      case \"loaded\":\r\n      case \"loadError\":\r\n      case \"noInit\":\r\n      default:\r\n        return false;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * If true, the form controls should be disabled.\r\n   */\r\n  public get isDisabled() {\r\n    switch (this.status) {\r\n      case \"initialLoading\":\r\n      case \"reloading\":\r\n      case \"loadError\":\r\n      case \"noInit\":\r\n        return true;\r\n      case \"loaded\":\r\n      default:\r\n        return false;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * If true, the form controls should be read-only (no input control at all).\r\n   */\r\n  public get isReadOnly(): boolean {\r\n    return this.status === \"noInit\" || this.status === \"initialLoading\" || !this.current || this.current.isReadOnly || this.isReadOnlyForced || false;\r\n  }\r\n\r\n  /** Returns true, if the current object has changes. */\r\n  public get hasChanges(): boolean {\r\n    return this.parentController ? this.parentController.hasChanges : !angular.equals(this._original, this._current);\r\n  }\r\n\r\n  /**\r\n   * Gets the status of the data if it is being loaded from a remote server.\r\n   */\r\n  public get status(): \"noInit\" | \"initialLoading\" | \"loaded\" | \"reloading\" | \"loadError\" {\r\n    return this.parentController ? this.parentController.status : this._status;\r\n  }\r\n\r\n  /** Makes an OData query  */\r\n  public getOData(options: ODataQueryOptions, result: ODataResult<TListItem> = null): Promise<ODataResult<TListItem>> {\r\n    return this.api.getOData(options).then( (data) => {\r\n      if (result) {\r\n        Object.assign(result, data);\r\n      }\r\n      return result ?? data;\r\n    });\r\n  }\r\n\r\n  /** Returns base url of the underlying api. */\r\n  public getBaseUrl(): string {\r\n    return this.api.getBaseUrl();\r\n  }\r\n\r\n  /** Gets the data transmitted in the route / url */\r\n  public getRouteData(): {\r\n    /** id parameter in the route */\r\n    id: string,\r\n    /** Action parameter in the route. */\r\n    action: \"default\" | \"copy-as-new\" | string,\r\n  } {\r\n    const result = {\r\n      id: null,\r\n      action: null,\r\n    };\r\n    if (this.$routeParams && this.$routeParams.crudItemId) {\r\n      let crudItemIdArr = this.$routeParams.crudItemId.split(\"/\");\r\n      crudItemIdArr = crudItemIdArr.map(x => x ? x.replace(/[?&#](.*)/g, \"\") : x); // remove trailing parameters. eg. access_token\r\n      result.id = crudItemIdArr[0] || null;\r\n      if (crudItemIdArr[1]) {\r\n        result.action = crudItemIdArr[1];\r\n      }\r\n    }\r\n    return result;\r\n  }\r\n\r\n  /** Save changes to the current item */\r\n  public save(options: any = undefined): Promise<TItem> {\r\n    if (this.parentController) {\r\n      return this.parentController.save(options);\r\n    }\r\n    const wasNew = this.isNew();\r\n    const loader = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.isSaving\");\r\n    this._status = \"reloading\";\r\n    return this.api.save(this.current, options)\r\n      .then((data) => {\r\n        loader.dismiss();\r\n        this._current = data;\r\n        this._original = angular.copy(data);\r\n        this._status = \"loaded\";\r\n        if (this.bindingMode === \"url\" && wasNew) {\r\n          this.$location.url(this.getDefaults().detailsUrl + data.id);\r\n          this.action = \"default\";\r\n        }\r\n        return data;\r\n      })\r\n      .catch((error) => {\r\n        loader.dismiss();\r\n        this._status = \"loadError\";\r\n        return null;\r\n      });\r\n  }\r\n\r\n  /** Reset the changes in the current element */\r\n  public reset(): TItem {\r\n    if (this.parentController) {\r\n      return this.parentController.reset();\r\n    }\r\n    return angular.copy(this._original, this._current);\r\n  }\r\n\r\n  /**\r\n   * Shows the detail view for the item.\r\n   * Typically, this takes the user to a new page with the ID.\r\n   * @param item Item may be either Container or list item.\r\n   */\r\n  public showDetails(item: TItem | IUserObjectIndex): angular.ILocationService {\r\n    if (this.parentController) {\r\n      return this.parentController.showDetails(item);\r\n    }\r\n    return this.$location.url(this.getDefaults().detailsUrl + this.getId(item));\r\n  }\r\n\r\n  /**\r\n   * Shows the detail view with a new item that is a copy of the given item.\r\n   * Typically, this takes the user to a new page with the ID with action \"copy-as-new\".\r\n   * @param item Item may be either Container or list item.\r\n   */\r\n  public showCopyAsNew(item: TItem | IUserObjectIndex): angular.ILocationService {\r\n    if (this.parentController) {\r\n      return this.parentController.showCopyAsNew(item);\r\n    }\r\n    return this.$location.url(this.getDefaults().detailsUrl + this.getId(item) + \"/copy-as-new\");\r\n  }\r\n\r\n  /**\r\n   * Shows the \"Are you sure?\" dialog and if user clicks OK, deletes the item.\r\n   * Cancels the started payment for the payroll too.\r\n   * @param item Item to be deleted.\r\n   * If not specified, the current item.\r\n   * @param confirmMessage Optional custom message for the confirm dialog.\r\n   * If not specified, a generic message is shown.\r\n   * If set to boolean false, the confirm message is not shown at all.\r\n   * @returns Promise that resolves to true if the item is deleted.\r\n   * False, if user cancels and fails if the deletion fails.\r\n   */\r\n  public delete = (item?: TItem, confirmMessage?: string): Promise<boolean> => {\r\n    if (this.parentController) {\r\n      return this.parentController.delete(item, confirmMessage);\r\n    }\r\n    item = item || this.current;\r\n    return this.uiHelpers.showConfirm(confirmMessage || \"SALAXY.NG1.ApiCrudObjectComponent.deleteDialog\")\r\n      .then((result: boolean) => {\r\n        if (result) {\r\n          return this.deleteNoConfirm(item).then(() => {\r\n            if (this.current === item) {\r\n              this._currentId = null;\r\n              this._current = null;\r\n              this._original = null;\r\n              this._status = \"noInit\";\r\n            }\r\n            if (this.odataController) {\r\n              this.odataController.reload();\r\n            } else {\r\n              this.$location.url(this.getDefaults().listUrl);\r\n            }\r\n            return true;\r\n          });\r\n        } else {\r\n          return Promise.resolve(false);\r\n        }\r\n      });\r\n  };\r\n\r\n  /**\r\n   * Gets the id for the object regardless of whther the object is Container or list item.\r\n   * Error is thrown if the item does not exist.\r\n   * The method is an extension point for future item types that may have other ID's in the future.\r\n   * @param item The item for which to fetch the ID.\r\n   */\r\n  public getId(item: TItem | IUserObjectIndex) {\r\n    if (!item) {\r\n      throw new Error(\"getId called for null item.\");\r\n    }\r\n    if ((item as IUserObjectIndex).containerGuid) {\r\n      return (item as IUserObjectIndex).containerGuid;\r\n    }\r\n    return item.id;\r\n  }\r\n\r\n  /**\r\n   * Deletes an item without showing the confirm dialog.\r\n   * The method shows the \"Please wait...\" loader, but does not refresh the\r\n   * list or move the browser to listUrl. The caller should take care\r\n   * of the UX actions after delete if necessary.\r\n   * @param item Item to be deleted.\r\n   * @returns Promise that resolves to true (never false). Fails if the deletion fails.\r\n   */\r\n  public deleteNoConfirm(item: TItem | IUserObjectIndex): Promise<boolean> {\r\n    if (this.parentController) {\r\n      return this.parentController.deleteNoConfirm(item);\r\n    }\r\n    if (!item) {\r\n      throw new Error(\"item not specified in deleteNoConfirm.\");\r\n    }\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    return this.api.delete(this.getId(item)).then(() => {\r\n      // Wait for the index\r\n      return this.uiHelpers.wait().then(() => {\r\n        loading.dismiss();\r\n        return true;\r\n      });\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Creates a copy of a given item.\r\n   * This is a synchronous method that should basically convert a saved item to a new item.\r\n   * @param copySource Item (container item) to copy as new.\r\n   */\r\n  public copyItem(copySource: TItem): TItem {\r\n    // TODO: Consider moving to logic or probably API.\r\n    const copy = JSON.parse(JSON.stringify(copySource)) as TItem;\r\n    (copy as any).id = null;\r\n    (copy as any).owner = null;\r\n    (copy as any).isReadOnly = false;\r\n    return copy;\r\n  }\r\n\r\n  /**\r\n   * Starts the reload process depending on the bindingMode:\r\n   */\r\n  public reload(): Promise<TItem> {\r\n    // TODO: The promise reloads here may require $scope.apply() so that .then() works on the promise.\r\n    // We should go through whether $scope.apply() should be added here instead of caller needing to worry about it.\r\n    if (this.parentController) {\r\n      this._currentId = this.parentController.currentId;\r\n      return this.parentController.reload().then((item) => {\r\n        this._currentId = this.parentController.currentId;\r\n        return item;\r\n      });\r\n    }\r\n    switch (this.bindingMode) {\r\n      case \"id\":\r\n      case \"url\":\r\n        if (this.bindingMode === \"url\") {\r\n          this._currentId = this.getRouteData().id;\r\n          if (!this.currentId) {\r\n            this.setCurrentRef(null);\r\n            this._status = \"loaded\";\r\n            return Promise.resolve<TItem>(this.current);\r\n          }\r\n        }\r\n        if (this.currentId === \"new\") {\r\n          this.setCurrentRef(this.api.getBlank());\r\n          this._currentId = null;\r\n          this._status = \"loaded\";\r\n          return Promise.resolve<TItem>(this.current);\r\n        }\r\n        // Reloads from server (status is set by the loading).\r\n        return this.setStatus(this.api.getSingle(this.currentId))\r\n          .then((item) => {\r\n            if (!item) {\r\n              this._status = \"loadError\";\r\n              throw new Error(`Item ${this.currentId} not found.`);\r\n            }\r\n            if (this.action === \"copy-as-new\") {\r\n              item = this.copyItem(item);\r\n            }\r\n            this.setCurrentRef(item);\r\n            return item;\r\n          });\r\n      case \"model\":\r\n        // Gets the model again from source.\r\n        this.setCurrentRef(this._model as TItem);\r\n        this._currentId = this.current ? this.current.id : null;\r\n        this._status = this.current ? \"loaded\" : \"noInit\";\r\n        return Promise.resolve<TItem>(this.current);\r\n      case \"parentCtrl\":\r\n        throw new Error(\"Binding mode parentCtrl without parentController.\");\r\n      case \"new\":\r\n        // Recreates a new item\r\n        this.setCurrentRef(this.api.getBlank());\r\n        this._currentId = null;\r\n        this._status = \"loaded\";\r\n        return Promise.resolve<TItem>(this.current);\r\n      case \"null\":\r\n      default:\r\n        // Sets the current as null.\r\n        this.setCurrentRef(null);\r\n        this._currentId = null;\r\n        this._status = \"loaded\";\r\n        return Promise.resolve<TItem>(this.current);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Sets the current item as the given object (reference to a new object).\r\n   * This also resets the original item. This method is typically used when the object is first loaded,\r\n   * when object that is being edited is changed or when object is reloaded from server after saving.\r\n   * @param item The new current item.\r\n   */\r\n  public setCurrentRef(item: TItem) {\r\n    if (this.parentController) {\r\n      return this.parentController.setCurrentRef(item);\r\n    }\r\n    this._current = item;\r\n    this._original = angular.copy(item);\r\n  }\r\n\r\n  /**\r\n   * Sets the current item value:\r\n   * The object reference remains the same, but all its properties are copied using angular.copy().\r\n   * Original object remains as-is by default. This method is typically used at the end of modifyinjg user interfaces.\r\n   * @param item The new current item.\r\n   * @param resetOriginal If true, also resets the orginal value.\r\n   */\r\n  public setCurrentValue(item: TItem, resetOriginal = false) {\r\n    if (this.parentController) {\r\n      return this.parentController.setCurrentValue(item, resetOriginal);\r\n    }\r\n    if (this._current) {\r\n      angular.copy(item, this._current);\r\n    } else {\r\n      // This should not really happen, but just in case the methods are used in a wrong way.\r\n      this._current = item;\r\n    }\r\n    if (resetOriginal) {\r\n      this._original = angular.copy(item);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Sets the current item. This also resets the original item.\r\n   * @param item The new current item.\r\n   * @param keepOriginalAsIs If true, will not update the original.\r\n   */\r\n  public setCurrent(item: TItem, keepOriginalAsIs = false): void {\r\n    if (this.parentController) {\r\n      return this.parentController.setCurrent(item, keepOriginalAsIs);\r\n    }\r\n    if (this._current) {\r\n      angular.copy(item, this._current);\r\n    } else {\r\n      this._current = item;\r\n    }\r\n    if (!keepOriginalAsIs) {\r\n      this._original = angular.copy(item);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Calls a promise updating the status on the controller.\r\n   * @param loadAction The promise that executes the loading from server.\r\n   * If action is null, the status is directly set as \"loaded\".\r\n   */\r\n  public setStatus(loadAction: Promise<TItem>): Promise<TItem> {\r\n    if (this.parentController) {\r\n      return this.parentController.setStatus(loadAction);\r\n    }\r\n    // eslint-disable-next-line @typescript-eslint/no-misused-promises\r\n    if (!loadAction) {\r\n      this._status = \"loaded\";\r\n      return null;\r\n    }\r\n    switch (this._status) {\r\n      case \"noInit\":\r\n        this._status = \"initialLoading\";\r\n        break;\r\n      case \"initialLoading\":\r\n        this._status = \"initialLoading\";\r\n        break;\r\n      case \"loadError\":\r\n        this._status = (this.current ? \"reloading\" : \"initialLoading\");\r\n        break;\r\n      case \"loaded\":\r\n        this._status = \"reloading\";\r\n        break;\r\n      case \"reloading\":\r\n        this._status = \"reloading\";\r\n        break;\r\n      default:\r\n        throw Error(\"Unexpected status: \" + this._status);\r\n    }\r\n    return loadAction.then((data) => {\r\n      this._status = \"loaded\";\r\n      return data;\r\n    })\r\n      .catch((error) => {\r\n        this._status = \"loadError\";\r\n        return null;\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Adds/updates the workflow event for the current using API.\r\n   * @param wfEvent - Workflow event to add/update.\r\n   * @returns - Reloaded item.\r\n   */\r\n  public saveWorkflowEvent(wfEvent: WorkflowEvent): Promise<TItem> {\r\n    return this.api.saveWorkflowEvent(this.current, wfEvent).then(() => {\r\n      return this.reload();\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Deletes the given event or all events with given type using API.\r\n   * @param wfIdOrType Id or type of the workflow event.\r\n   * @returns - Reloaded item.\r\n   */\r\n  public deleteWorkflowEvent(wfIdOrType: string): Promise<TItem> {\r\n    return this.api.deleteWorkflowEvent(this.current, wfIdOrType).then(() => {\r\n      return this.reload();\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Gets a single workflow event for the item.\r\n   * @param wfId Id of the workflow event.\r\n   * @returns - Single workflow event\r\n   */\r\n  public getWorkflowEvent(wfId: string): Promise<WorkflowEvent> {\r\n    return this.api.getWorkflowEvent(this.current, wfId);\r\n  }\r\n\r\n  /** Returns the current api */\r\n  public getApi(): CrudApiBase<TItem, TListItem> {\r\n    return this.api;\r\n  }\r\n\r\n  /**\r\n   * Returns the versions for the current item.\r\n   */\r\n  public get versions(): VersionInfo[] {\r\n    if (!this._versions || this._versionsId !== this.currentId) {\r\n      this._versions = this._versions ?? [];\r\n      this._versions.splice(0,  this._versions.length);\r\n      this._versionsId = this.currentId;\r\n      if (this.currentId) {\r\n        this.api.getVersions(this.currentId).then((data) => {\r\n          this._versions.push(...data);\r\n        });\r\n      }\r\n    }\r\n    return this._versions;\r\n  }\r\n\r\n  /**\r\n   * Gets a version of the current item.\r\n   * @param version VersionInfo of the item.\r\n   */\r\n  public getVersion(version: VersionInfo): { version: VersionInfo, item?: TItem } {\r\n    if (!this._version || this._versionId !== `${this.currentId}-${version?.versionId}`) {\r\n      this._version = (this._version ?? { version: {}, item: null} as any);\r\n      angular.copy(version, this._version.version);\r\n      this._version.item = null;\r\n      this._versionId = `${this.currentId}-${version?.versionId}`;\r\n      if (this.currentId) {\r\n        this.api.getVersion(this.currentId, version?.versionId).then((data) => {\r\n          this._version.item = data;\r\n        });\r\n      }\r\n    }\r\n    return this._version;\r\n  }\r\n}\r\n","/**\r\n * Bindings for the components that use ApiCrudObjectController.\r\n */\r\nexport class ApiCrudObjectControllerBindings {\r\n\r\n  [boundProperty: string]: string;\r\n\r\n  /**\r\n   * URL to which the component navigates when an item is clicked.\r\n   * The \"id\" or \"rowIndex\" property of the selected item is added to the URL.\r\n   * URL is ignored if onListSelect is set. In this case, you may navigate yourself in that method.\r\n   * Id is added directly to the string and this is an angular route.\r\n   * I.e. use \"/calc/details/\" (not \"#/calc/details/\" or \"#/calc/details\")\r\n   * @example <salaxy-payroll-list details-url=\"/myCustomRoute/\"></salaxy-payroll-list>\r\n   */\r\n  public detailsUrl = \"@\";\r\n\r\n  /**\r\n   * URL for the list view. At the moment, if specified, the browser is redirected here after delete.\r\n   * @example\r\n   * <!-- Main worker list is in the front page in this case -->\r\n   * <salaxy-employment-details list-url=\"/home\"></salaxy-employment-details>\r\n   */\r\n  public listUrl = \"@\";\r\n\r\n  /**\r\n   * Set the Current selected item (the model).\r\n   * The model may be:\r\n   *\r\n   * - TItem: A bound item (default), which can also be null.\r\n   * - \"new\": A new item is created.\r\n   * - \"url\": Fetches the item from the server using the id query string (crudItemId in routeParams).\r\n   * - string: Any other string is interpreted as id which is used to fetch the item from the server.\r\n   */\r\n  public model = \"<\";\r\n\r\n   /** If true, current item is read only */\r\n  public isReadOnlyForced = \"<\";\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Base class for list controllers that edit a list of items within a parent object (parent property).\r\n * Abstract class implementation defines the location of list with items of type TListItem.\r\n * Typically, the list items do not have ID's, they and all operations are synchronous.\r\n * Save operation is currently done to the parent, it may be later connected also to this controller.\r\n */\r\nexport abstract class ListControllerBase<TParent, TListItem> implements angular.IController {\r\n\r\n  /**\r\n   * Original parent value for reset. This value is set when the controller is created.\r\n   */\r\n  public original: TParent;\r\n\r\n  /**\r\n   * Event that is fired by the list controller if the user interface indicates that\r\n   * the changes made by the list controller should be committed.\r\n   * Typically this would result to saving of the object.\r\n   * @example <salaxy-calc-rows on-commit=\"$ctrl.save()\"></salaxy-calc-rows>\r\n   */\r\n  public onCommit: (eventData: {\r\n    /** The parent object that contains the list (typically the one that is saved). */\r\n    parent: TParent,\r\n    /** The list that was modified by the control */\r\n    list: TListItem[],\r\n  }) => void;\r\n\r\n  /**\r\n   * Event that is fired by the list controller if the user interface indicates that\r\n   * the changes made by the list controller should be reset (canceled).\r\n   * Typically this would result to just closing the control, but some changes to the parent object may be necessary.\r\n   * @example <salaxy-calc-rows on-reset=\"$ctrl.resetParentThings()\"></salaxy-calc-rows>\r\n   */\r\n  public onReset: (eventData: {\r\n    /** The parent object that contains the list  (typically the one that is reset). */\r\n    parent: TParent,\r\n  }) => void;\r\n\r\n  /**\r\n   * Event that is fired by the list controller if the user switches from read-only mode to edit.\r\n   * Not all components support read-only vs. edit modes.\r\n   * Typically there is no action needed, but e.g. external menu items may be modified.\r\n   * @example <salaxy-calc-rows on-reset=\"$ctrl.showEditMenu()\"></salaxy-calc-rows>\r\n   */\r\n  public onStartEdit: (eventData: {\r\n    /** The parent object that contains the list  (typically the one that is reset). */\r\n    parent: TParent,\r\n  }) => void;\r\n\r\n  /**\r\n   * The edit mode of the component:\r\n   *\r\n   * - edit: Editable, if the calculation is editable.\r\n   * - read-edit: first read-only, but there is an edit button if the calculation is editable.\r\n   * - read-only: Always read-only.\r\n   *\r\n   * Note that not all components support the mode attribute. Also, the default depends on the component logic.\r\n   */\r\n  public mode: \"edit\" | \"read-edit\" | \"read-only\";\r\n\r\n  /** Parent object to which the component is bound.  */\r\n  private _parent: TParent;\r\n\r\n  protected _isInEdit: boolean;\r\n\r\n  /**\r\n   * Creates a new ListControllerBase.\r\n   * @param uiHelpers - Salaxy ui helpers service for dialogs etc.\r\n   */\r\n  constructor(\r\n      protected uiHelpers: UiHelpers,\r\n  ) {\r\n      if (!uiHelpers) {\r\n        throw new Error(\"uiHelpers is undefined in ListControllerBase\");\r\n      }\r\n  }\r\n\r\n  /**\r\n   * Implement IController by providing onInit method.\r\n   * We currently do nothing here, but if you override this function,\r\n   * you should call this method in base class for future compatibility.\r\n   */\r\n  public $onInit() {\r\n    // init here.\r\n  }\r\n\r\n  /**\r\n   * Gets or sets the parent object that contains the list that is being edited.\r\n   * Typically this parent object is an ApiCrudObject.\r\n   */\r\n  public get parent(): TParent {\r\n    return this._parent;\r\n  }\r\n  public set parent(value: TParent) {\r\n    this.original =  angular.copy(this.parent);\r\n    this._parent = value;\r\n  }\r\n\r\n  /**\r\n   * When overriding the abstract class, you should provide the list within the parent that is edited / viewed.\r\n   * If the parent object is not provided or list is not otherwise available, you should provide null.\r\n   */\r\n  public abstract get list(): TListItem[];\r\n\r\n  /** The template URL for the edit dialog. Set to null if you do not want an edit dialog */\r\n  public abstract getEditDialogTemplateUrl(): string;\r\n\r\n  /**\r\n   * Possiblity to define additional logic that is passed to the edit dialog as $ctrl.logic.\r\n   * This may contain additional metadata as well as functions.\r\n   */\r\n  public getEditDialogLogic(): any {\r\n    return {};\r\n  }\r\n\r\n  /** When overriding the abstract class, provide her the factory method that creates a new list item. */\r\n  public abstract getBlank(): TListItem;\r\n\r\n  /** View should call this method if there is a UI component that fires commit (typically save) to the parent. */\r\n  public commit() {\r\n    this.isInEdit = false;\r\n    if (this.onCommit) {\r\n      // Note: When used as component (\"&\"-binding), there is always a value here even if no function is bound. This if is just for controller use without component.\r\n      this.onCommit({\r\n        parent: this.parent,\r\n        list: this.list,\r\n      });\r\n    }\r\n  }\r\n\r\n  /** View should call this method if there is a UI component that fires reset / cancel to the parent. */\r\n  public reset() {\r\n    this.isInEdit = false;\r\n    if (this.onReset) {\r\n      // Note: When used as component (\"&\"-binding), there is always a value here even if no function is bound. This if is just for controller use without component.\r\n      this.onReset({\r\n        parent: this.parent,\r\n        // TODO: Add possibility to signal that reset has been done (from parent back to child).\r\n      });\r\n    }\r\n    if (this.original) {\r\n      angular.copy(this.original, this.parent);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Returns true if the parent can be edited by this component.\r\n   * Takes into account parent being null, isReadOnly and the \"read-only\" mode of the component.\r\n   */\r\n  public get isEditable(): boolean {\r\n    if (!this.parent || (this.parent as any).isReadOnly || this.mode === \"read-only\") {\r\n      return false;\r\n    }\r\n    return true;\r\n  }\r\n\r\n  /**\r\n   * Gets or sets the flag telling whether the component is in edit or read-only mode.\r\n   * This is restricted by the mode and isReadOnly of the parent calculation.\r\n   */\r\n  public get isInEdit(): boolean {\r\n    if (!this.isEditable) {\r\n      return false;\r\n    }\r\n    if (this.mode === \"edit\") {\r\n      return true;\r\n    }\r\n    return !!this._isInEdit;\r\n  }\r\n  public set isInEdit(value: boolean) {\r\n    this._isInEdit = value;\r\n  }\r\n\r\n  /**\r\n   * View should call this method if the component is changed from read-only mode to edit mode.\r\n   * Not all components support read-only vs. edit modes.\r\n   */\r\n  public startEdit() {\r\n    if (this.isEditable) {\r\n      this.isInEdit = true;\r\n      this.onStartEdit({\r\n        parent: this.parent,\r\n      });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Deletes an item from list (no confirm etc.)\r\n   * The method shows the \"Please wait...\" loader, but does not call onDelete\r\n   * or move the browser to listUrl. The caller should take care\r\n   * of the UX actions after delete if necessary.\r\n   * @param item Item to delete.\r\n   * @returns Promise that resolves to true (never false). Fails if the deletion fails.\r\n   */\r\n  public delete(item: TListItem): TListItem[] {\r\n    return this.list.splice(this.list.indexOf(item), 1);\r\n  }\r\n\r\n  /**\r\n   * Shows the edit dialog.\r\n   * @param item Item to edit or string \"new\" for creating a new one.\r\n   * @param isNew Optional way of specifying that the item is a new item (with default values, not yet added to the list).\r\n   * If item is string \"new\", this parameter will have no effect (will always be true).\r\n   */\r\n  public showEditDialog(item: TListItem | \"new\", isNew = false) {\r\n    if (!item) {\r\n      throw new Error(\"showEditDialog called without a parameter.\");\r\n    }\r\n    if (item === \"new\") {\r\n      isNew = true;\r\n      item = this.getBlank();\r\n    }\r\n    this.uiHelpers.openEditDialog(this.getEditDialogTemplateUrl(), item, this.getEditDialogLogic()).then((result) => {\r\n      if (result.action === \"ok\" || result.action === \"ok-no-save\" ) {\r\n        if (isNew) {\r\n          this.list.push(result.item);\r\n        }\r\n        if (( isNew || result.hasChanges) && result.action !== \"ok-no-save\") {\r\n          this.commit();\r\n        }\r\n      } else if (result.action === \"delete\" || result.action === \"delete-no-save\") {\r\n        if (!isNew) {\r\n          this.delete(item as TListItem);\r\n          if (result.action !== \"delete-no-save\" ) {\r\n            this.commit();\r\n          }\r\n        }\r\n      } else {\r\n        // No changes, cancel\r\n      }\r\n      });\r\n  }\r\n}\r\n","/**\r\n * Bindings for the component which uses ListControllerBase.\r\n */\r\nexport class ListControllerBaseBindings {\r\n\r\n  /**\r\n   * Parent object that contains the list that is being edited.\r\n   * Typically this parent object is an ApiCrudObject.\r\n   */\r\n  public parent = \"<\";\r\n\r\n  /**\r\n   * Event that is fired by the list controller if the user interface indicates that\r\n   * the changes made by the list controller should be committed.\r\n   * Typically this would result to saving of the object.\r\n   * @example <salaxy-calc-rows on-commit=\"$ctrl.save()\"></salaxy-calc-rows>\r\n   */\r\n  public onCommit = \"&\";\r\n\r\n  /**\r\n   * Event that is fired by the list controller if the user interface indicates that\r\n   * the changes made by the list controller should be reset (canceled).\r\n   * Typically this would result to just closing the control, but some changes to the parent object may be necessary.\r\n   * @example <salaxy-calc-rows on-reset=\"$ctrl.resetParentThings()\"></salaxy-calc-rows>\r\n   */\r\n  public onReset = \"&\";\r\n\r\n  /**\r\n   * Event that is fired by the list controller if the user switches from read-only mode to edit (within the component).\r\n   * Typically there is no action needed, but e.g. external menu items may be modified.\r\n   * Not all components support read-only vs. edit modes.\r\n   * @example <salaxy-calc-rows on-reset=\"$ctrl.showEditMenu()\"></salaxy-calc-rows>\r\n   */\r\n  public onStartEdit = \"&\";\r\n\r\n  /**\r\n   * Sets the component edit mode (true/false).\r\n   * This is typically subject to isReadOnly (i.e. if isReadOnly is true on parent, true value is ignored).\r\n   * Edit mode depends on the component UI logic and not all components support editable or non-editable modes.\r\n   */\r\n  public isInEdit = \"<\";\r\n\r\n  /**\r\n   * The edit mode of the component:\r\n   *\r\n   * - edit: Editable, if the calculation is editable.\r\n   * - read-edit: first read-only, but there is an edit button if the calculation is editable.\r\n   * - read-only: Always read-only.\r\n   *\r\n   * Note that not all components support the mode attribute.\r\n   * Also, the default depends on the component logic and component may offer additional modes (e.g. calendar).\r\n   */\r\n  public mode = \"@\";\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { AjaxNg1 } from \"../../ajax\";\r\nimport { ODataQueryController } from \"./ODataQueryController\";\r\n\r\n/**\r\n * Controller that provides helper methods in components inside ODataQueryController.\r\n */\r\nexport class ODataHelperController  implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"AjaxNg1\"];\r\n\r\n  /** Signals that the component should render a table column header with orderby (OData sort) */\r\n  public orderby: string;\r\n\r\n  /**\r\n   * Manually defined URL for the nextPageLink.\r\n   * Browser is directed to this URL instead of loading more data from nextPageLink.\r\n   */\r\n  public nextPageUrl: string;\r\n\r\n  /** The parent ODataQueryController that contains the list and all the methods. */\r\n  public $odata: ODataQueryController;\r\n\r\n  constructor(private ajax: AjaxNg1) {\r\n    // Dependency injection\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit = () => {\r\n      // Init\r\n  };\r\n\r\n  /**\r\n   * Gets the \"No items\" message if there is no items to show.\r\n   * Null, if there are rows to show.\r\n   * The message changesdepending on the situation: No items, Not initiated, Authentication required.\r\n   */\r\n  public getNoItemsMessage() {\r\n    if (this.$odata.items && this.$odata.items.length > 0) {\r\n      return null;\r\n    }\r\n    if (!this.$odata.options.anon && this.ajax.getTokenStatus() !== \"ok\") {\r\n      return \"SALAXY.NG1.ODataFooterComponent.getNoItemsMessage.anon\";\r\n    }\r\n    if (this.$odata.status === \"noInit\") {\r\n      // NOTE: This message is for developers => Does not need to be translated.\r\n      return \"OData Service not initialized: Set url property or call setUrl().\";\r\n    }\r\n    if (this.$odata.status === \"loadError\") {\r\n      return \"SALAXY.NG1.ODataFooterComponent.getNoItemsMessage.loadError\";\r\n    }\r\n    if (this.$odata.status === \"reloading\") {\r\n      return null; // Show previous results, just dimmed (opacity 0.7)\r\n    }\r\n    if (this.$odata.status === \"initialLoading\") {\r\n      return \"SALAXY.UI_Terms.loading\";\r\n    }\r\n    if (this.$odata.status === \"loaded\") {\r\n      return \"SALAXY.NG1.ODataFooterComponent.getNoItemsMessage.noItems\";\r\n    }\r\n    return \"SALAXY.NG1.ODataFooterComponent.getNoItemsMessage.noItems\";\r\n  }\r\n\r\n  /** Gets the CSS classes for No items message  */\r\n  public getNoItemsCssClass() {\r\n    if (this.$odata.items && this.$odata.items.length > 0) {\r\n      return \"\";\r\n    }\r\n    if (this.$odata.status === \"noInit\" || this.$odata.status === \"loadError\") {\r\n      // Also invalid token is either noInit or loadError at the moment.\r\n      return \"alert alert-danger\";\r\n    }\r\n    return \"alert alert-default\";\r\n  }\r\n\r\n  /** Gets the paging view to show */\r\n  public getPagingView(): \"clientLimit\" | \"nextPageLink\" | \"url\" | \"allVisible\" {\r\n    if (this.$odata.nextPageLink) {\r\n      return this.nextPageUrl ? \"url\" : \"nextPageLink\";\r\n    }\r\n    if (this.$odata.options.$top) {\r\n      if (this.$odata.count) {\r\n        if (this.$odata.count > this.$odata.items.length) {\r\n          return this.nextPageUrl ? \"url\" : \"clientLimit\";\r\n        } else {\r\n          return \"allVisible\";\r\n        }\r\n      } else {\r\n        if (!this.$odata.items || this.$odata.items.length < ((this.$odata.options.$skip || 0) + this.$odata.options.$top)) {\r\n          return \"allVisible\";\r\n        } else {\r\n          return this.nextPageUrl ? \"url\" : \"clientLimit\";\r\n        }\r\n      }\r\n    }\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { ApiListItem, ApiCrudObject, CrudApiBase, OData, ODataQueryOptions, ODataResult, progressNotification, Ajax } from \"@salaxy/core\";\r\n\r\nimport { AjaxNg1 } from \"../../ajax\";\r\nimport { CacheService, UiHelpers } from \"../../services\";\r\nimport { ApiCrudObjectController } from \"../bases\";\r\n\r\n/**\r\n * User interface logic for making and displaying an OData query and displaying its results as list.\r\n */\r\nexport class ODataQueryController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"CacheService\", \"AjaxNg1\", \"$timeout\", \"$scope\", \"$controller\", \"UiHelpers\"];\r\n\r\n  /**\r\n   * CRUD controller that implements Delete and potentially other methods about the object.\r\n   * If you wish to use this in the view use \"as $controllerName\" syntax\r\n   * @example\r\n   * <salaxy-odata-table crud-controller=\"PayrollCrudController as $crud\" crud-bindings=\"{ myProp: 'foobar' }\">\r\n   */\r\n  public crudController: string;\r\n\r\n  /**\r\n   * Optional bindings for the CRUD controller. All properties are set to crudController before calling init.\r\n   * @example\r\n   * <salaxy-odata-table crud-controller=\"PayrollCrudController as $crud\" crud-bindings=\"{ myProp: 'foobar' }\">\r\n   */\r\n  public crudBindings: { [key: string]: any; };\r\n\r\n  /** OData endpoint URL */\r\n  public url: string;\r\n\r\n  /** The status of the data loading */\r\n  public _status: \"noInit\" | \"initialLoading\" | \"loaded\" | \"reloading\" | \"loadError\" = \"noInit\";\r\n\r\n  /**\r\n   * If true, the items collection has data.\r\n   * This means that items is not null. It may be an empty array though if there is nothing coming from data source.\r\n   */\r\n  public hasData: boolean;\r\n\r\n  /** Query options for the next query */\r\n  public options: ODataQueryOptions;\r\n\r\n  /** Items once loaded from the server. This is an empty array when the loading starts. */\r\n  public items: any[];\r\n\r\n  /** Total count of the items (server-side/storage) if updated in the previous query. */\r\n  public count: number | null = null;\r\n\r\n  /** Link for the next page if available in the previous query */\r\n  public nextPageLink: string = null;\r\n\r\n  /** Data passed from the parent to the component / view */\r\n  public data: any;\r\n\r\n  /** If readOnly is true, edit, copy etc. buttons from the new list view are hidden if readOnly property is supported */\r\n  public readOnly: any;\r\n\r\n  /** Selected search items */\r\n  public selectedItems: any[];\r\n\r\n  /** If set, uses caching to store cache result between controller loads. */\r\n  public cacheKey: string;\r\n\r\n  /** Time in milliseconds when the data was loaded.  */\r\n  public loadedAt: number;\r\n\r\n  /** Optional OData reader. Defaults to AjaxNg1.getJSON -method */\r\n  public reader: {\r\n     /** Gets a JSON-message from server using the API */\r\n     getJSON: (method: string ) => Promise<any>,\r\n  } = null;\r\n\r\n  /**\r\n   * Function that is called when user selects an item in the list.\r\n   * Note that the event is called only in the selections (single and multi). Not when there is a link to details view in a link list.\r\n   * Function has the following locals: value: true/false, item: the last selected/unselected item, allItems: Array of all currently selected items.\r\n   * @example <salaxy-employment-list mode=\"select\" on-list-select=\"$ctrl.updateFromEmployment(item.id)\"></salaxy-employment-list>\r\n   */\r\n  public onListSelect: (params: {\r\n    /** In multi-select mode, the value may be true (selected) or false (unselected). */\r\n    value: true | false,\r\n    /** Item that was last selected / deselected. */\r\n    item: any,\r\n    /** All items that are currently selected. */\r\n    allItems: any[],\r\n  }) => void;\r\n\r\n  /** Function that is called when the data has been loaded and set as values of the items. */\r\n  public onDataLoaded: (params: {\r\n    /** If true, the load was append to previous values. */\r\n    append: boolean,\r\n    /** The resulted data */\r\n    result: ODataResult<any>,\r\n  }) => void;\r\n\r\n  /**\r\n   * When list is used as selection (dialog) specifies whether the selection is single or multiple.\r\n   * NOTE: Currently only affects select all buttons. Later implementations may use to implement single/multiple selections.\r\n   */\r\n  public selectMode: \"multiselect\" | \"select\";\r\n\r\n  /** Used in the searchChanged function if the searchType is \"other\" (potentially some other special searches in the future). */\r\n  public rawSearchStringOther: string;\r\n\r\n  /** Used in the searchChanged function if the searchType is \"owner\" (potentially some other special searches in the future). */\r\n  public rawSearchStringOwner: string;\r\n\r\n  /** HACK: Extract interface */\r\n  private $crudController: ApiCrudObjectController<ApiCrudObject, ApiListItem>;\r\n\r\n  private filterTimeout: any;\r\n\r\n  /**\r\n   * Creates a new controller instance\r\n   * @ignore\r\n   */\r\n  constructor(\r\n\r\n    protected cacheService: CacheService,\r\n    private ajax: AjaxNg1,\r\n    private $timeout: angular.ITimeoutService,\r\n    private $scope: angular.IScope,\r\n    private $controller: angular.IControllerService,\r\n    private uiHelpers: UiHelpers,\r\n  ) { }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit = () => {\r\n\r\n    if (!this.reader) {\r\n      this.reader = this.ajax;\r\n    }\r\n\r\n    if (!this.options) {\r\n      this.options = {\r\n        $count: false,\r\n      };\r\n    }\r\n    if (this.crudController) {\r\n      this.$crudController = this.$controller(this.crudController, { $scope: this.$scope });\r\n      this.$crudController.odataController = this;\r\n      if (this.crudBindings) {\r\n        Object.keys(this.crudBindings).forEach((key) => {\r\n          this.$crudController[key] = this.crudBindings[key];\r\n        });\r\n      }\r\n      this.$crudController.$onInit();\r\n    }\r\n    this.selectedItems = this.selectedItems || [];\r\n    this.items = this.items || [];\r\n\r\n    this.reload();\r\n  };\r\n\r\n  /**\r\n   * Cleaning the timeout.\r\n   */\r\n  public $onDestroy = () => {\r\n    if (angular.isDefined(this.filterTimeout)) {\r\n      this.$timeout.cancel(this.filterTimeout);\r\n    }\r\n  };\r\n\r\n  /**\r\n   * Gets the status of the data if it is being loaded from a remote server.\r\n   */\r\n  public get status(): \"noInit\" | \"initialLoading\" | \"loaded\" | \"reloading\" | \"loadError\" {\r\n    return this._status;\r\n  }\r\n\r\n  /**\r\n   * Set the URL and start reload.\r\n   * @param url OData enndpoint\r\n   * @param queryOptions Optional initial query options.\r\n   */\r\n  public setUrl(url: string, queryOptions?: ODataQueryOptions) {\r\n    this.url = url;\r\n    this.options = queryOptions || this.options;\r\n    this.reload();\r\n  }\r\n\r\n  /**\r\n   * Sets query options. Does not trigger reload.\r\n   * @param queryOptions Query options.\r\n   */\r\n  public setQueryOptions(queryOptions?: ODataQueryOptions) {\r\n    this.options = queryOptions || this.options;\r\n  }\r\n\r\n  /**\r\n   * Method to set the sort by for a column\r\n   * @param column Column to sort by\r\n   * @param direction Optional direction is either \"asc\" for ascending or \"desc\" for descending.\r\n   * If direction is not set, will reverse the sort order or ascending being the default.\r\n   */\r\n  public orderBy(column: string, direction?: \"asc\" | \"desc\") {\r\n    if (!direction) {\r\n      const currentOrder = this.getColumnOrder(column);\r\n      direction = currentOrder === \"asc\" ? \"desc\" : \"asc\";\r\n    }\r\n    this.options.$orderby = column + \" \" + direction;\r\n    this.options.$skip = 0; // Consider not resetting this, when implementing client-side paging.\r\n    this.reload();\r\n    return;\r\n  }\r\n\r\n  /**\r\n   * Sets a column filter and reloads the data set.\r\n   * @param column Name of the column.\r\n   * Set the column name as null, if you want to clear all filters.\r\n   * @param value Value of the filter. Null clears the filter (not filter-by-null).\r\n   * TODO: This could potententially be a comma separated value if requirement comes up.\r\n   * @param operation Possibility to negate the equality.\r\n   * @param andFilters If set, adds these additional filters (with and) to the new primary filter.\r\n   * @param valueType Type for the value. Default is string, other option is date\r\n   */\r\n  public setFilter(column: string | null, value: string, operation: \"eq\" | \"ne\" = \"eq\", andFilters?: string, valueType =\"string\"): void {\r\n    if (column && value) {\r\n      this.options.$filter = `${column} ${operation || \"eq\"} ` + (valueType == \"date\" ? `${value}` : `'${value}'`);\r\n      if (andFilters) {\r\n        this.options.$filter += \" and (\" + andFilters + \")\";\r\n      }\r\n    } else {\r\n      this.options.$filter = andFilters || null;\r\n    }\r\n    this.options.$skip = 0;\r\n    this.reload();\r\n  }\r\n\r\n  /**\r\n   * Gets the text indicating the time that has passed since the data was loaded.\r\n   */\r\n  public getLoadedTime(unit: \"min\" | \"10sec\" | \"sec\" = \"min\"): number {\r\n    if (!this.loadedAt) {\r\n      return null;\r\n    }\r\n    const ms = new Date().getTime() - this.loadedAt;\r\n    switch (unit) {\r\n      case \"min\":{\r\n        const minutes = Math.floor(ms / 60000);\r\n        if (minutes < 1) {\r\n          return null;\r\n        }\r\n        return minutes;\r\n      }\r\n      case \"10sec\":\r\n        return Math.floor(ms / 10000) * 10;\r\n      case \"sec\":\r\n        return Math.floor(ms / 1000);\r\n    }\r\n  }\r\n\r\n  /** Clears the cache and reloads from the server. */\r\n  public refresh() {\r\n    this.cacheService.clear(this.cacheKey);\r\n    this.reload();\r\n  }\r\n\r\n  /** Clears the entire cache - all keys and reloads. */\r\n  public refreshClearAll() {\r\n    this.cacheService.clearAllKeys();\r\n    this.reload();\r\n  }\r\n\r\n  /**\r\n   * Sets an item as selected.\r\n   * @param item Item to set as selected\r\n   * @param value Selected true / false or \"toggle\" to toggle to other value.\r\n   */\r\n  public setSelected(item: any, value: true | false | \"toggle\" = true) {\r\n    // TODO: This now only supports items with id. Add other identifiers if necessary.\r\n    const ix = this.selectedItems.findIndex((x) => x.id === item.id);\r\n    const exists = ix >= 0;\r\n    if (exists) {\r\n      this.selectedItems.splice(ix, 1);\r\n    }\r\n    switch (value) {\r\n      case true:\r\n        this.selectedItems.push(item);\r\n        break;\r\n      case false:\r\n        // Already done\r\n        break;\r\n      case \"toggle\":\r\n        if (!exists) {\r\n          this.selectedItems.push(item);\r\n        }\r\n        break;\r\n    }\r\n    this.onListSelect({\r\n      value: value === \"toggle\" ? !exists : value,\r\n      item,\r\n      allItems: this.selectedItems,\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Returns true if the item is selected.\r\n   * @param item Item to check for selected value.\r\n   */\r\n  public isSelected(item: any) {\r\n    return this.selectedItems.findIndex((x) => x.id === item.id) >= 0;\r\n  }\r\n\r\n  /** Unselect all */\r\n  public unselectAll() {\r\n    if (this.selectedItems) {\r\n      this.selectedItems.splice(0, this.selectedItems.length);\r\n    }\r\n  }\r\n\r\n  /** Select all */\r\n  public selectAll() {\r\n    if (this.selectedItems && this.items) {\r\n      this.selectedItems.splice(0, this.selectedItems.length);\r\n      this.selectedItems.push(...this.items);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Gets a column ordering for the specified column.\r\n   * @param columnName Name of the column\r\n   * @returns Column order \"asc\" or \"desc\" if column is being sorted. Otherwise null.\r\n   */\r\n  public getColumnOrder(columnName: string): \"asc\" | \"desc\" | null {\r\n    if (!columnName) {\r\n      return null;\r\n    }\r\n    if (!(this.options.$orderby || \"\").trim()) {\r\n      return null;\r\n    }\r\n    const columns = this.options.$orderby.split(\",\");\r\n    for (const colSpec of columns) {\r\n      const colArr = colSpec.trim().split(/\\s+/);\r\n      if (colArr[0].trim().toLowerCase() === columnName.trim().toLowerCase()) {\r\n        return colArr.length > 1 && colArr[1].trim().toLowerCase() === \"desc\" ? \"desc\" : \"asc\";\r\n      }\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Loads items on next page\r\n   * @param append If true, appends the data of the next page link to the current set of items\r\n   */\r\n  public loadNextPage(append: boolean) {\r\n    if (this.nextPageLink) {\r\n      const queryString = this.nextPageLink.indexOf(\"?\");\r\n      if (queryString >= 0) {\r\n        const searchParams = new URLSearchParams(this.nextPageLink.substr(queryString));\r\n        if (searchParams.get(\"$skip\")) {\r\n          this.options.$skip = Number(searchParams.get(\"$skip\"));\r\n        }\r\n      }\r\n      this.loadData(this.options, append);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Called by the view when the search text changes\r\n   * @param searchType If \"owner\" or \"other\", the search is performed as owner:search or other:search and the search string is taken from rawSearchString.\r\n   * By default, the search string should be bound to options.$search or options.fullSearch.\r\n   */\r\n  public searchChanged(searchType: \"default\" | \"owner\" | \"other\" | \"both\" = \"default\") {\r\n    if (searchType == \"other\") {\r\n      this.options.fullSearch = `${searchType}:${this.rawSearchStringOther || \"\"}`;\r\n    }\r\n    if (searchType == \"owner\") {\r\n      this.options.fullSearch = `${searchType}:${this.rawSearchStringOwner || \"\"}`;\r\n    }\r\n    if (searchType == \"both\") {\r\n      this.options.fullSearch = `owner:${this.rawSearchStringOwner || \"\"} AND other:${this.rawSearchStringOther || \"\"}`;\r\n    }\r\n    this.options.$skip = 0;\r\n    this.reloadWithDelay(500);\r\n  }\r\n\r\n  /**\r\n   * Starts the reload process.\r\n   * @param delay Loading occurs asyncronously after the specified delay\r\n   */\r\n  public reloadWithDelay(delay: number): void {\r\n    if (!this.getUrl()) {\r\n      return;\r\n    }\r\n    if (angular.isDefined(this.filterTimeout)) {\r\n      this.$timeout.cancel(this.filterTimeout);\r\n    }\r\n    this.filterTimeout = this.$timeout(() => {\r\n      this.loadData(this.options, false);\r\n    }, delay);\r\n  }\r\n\r\n  /**\r\n   * Starts the reload process.\r\n   * @returns A promise of OData result as returned by setValues() method.\r\n   */\r\n  public reload(): Promise<ODataResult<any>> {\r\n    if (!this.getUrl()) {\r\n      return;\r\n    }\r\n    if (angular.isDefined(this.filterTimeout)) {\r\n      this.$timeout.cancel(this.filterTimeout);\r\n    }\r\n    return this.loadData(this.options, false);\r\n  }\r\n\r\n  /** Gets the URL for the server request using the current url and queryOptions */\r\n  public getUrl() {\r\n    const baseUrl = this.url || (this.$crudController ? this.$crudController.odataServiceUrl : null);\r\n    if (!baseUrl) {\r\n      return null;\r\n    }\r\n\r\n    return OData.getUrl(baseUrl, this.options);\r\n  }\r\n\r\n  /** If true, the component is in the middle of loading data. */\r\n  public get isLoading() {\r\n    switch (this.status) {\r\n      case \"initialLoading\":\r\n      case \"reloading\":\r\n        return true;\r\n      case \"loaded\":\r\n      case \"loadError\":\r\n      case \"noInit\":\r\n      default:\r\n        return false;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Gets the CSS classes for OData table container.\r\n   * Main function is to get the `salaxy-loading class`.\r\n   * Also renders `salaxy-component salaxy-odata-table` for convenience\r\n   */\r\n  public getCssClass() {\r\n    return \"salaxy-component salaxy-odata-table\"\r\n      + \" salaxy-odata-table-status-\" + this.status\r\n      + (this.isLoading ? \" salaxy-odata-table-loading\" : \"\");\r\n  }\r\n\r\n  /**\r\n   * Sets the values to items from an OData result.\r\n   * @param data Data as returned from the Ajax component. This is expected being either ODataResult or array of items.\r\n   * @param append If true, appends the result to existing values. Used particularly with nextPageLink if this is used fo \"Load more\", not \"Next page\".\r\n   * @returns The data harmonized as OData result.\r\n   */\r\n  public setValues(data: any, append = false): ODataResult<any> {\r\n    const result = OData.getODataResult<any>(data);\r\n\r\n    this.items = this.items || [];\r\n    if (!append && this.items.length > 0) {\r\n       // remove values\r\n       this.items.splice(0, this.items.length);\r\n    }\r\n    this.items.push(...result.items);\r\n    this.count = result.count;\r\n    this.nextPageLink = result.nextPageLink;\r\n    this.hasData = true;\r\n    this.loadedAt = data.$loaded || new Date().getTime(); // Cache service injects loaded time in $loaded.\r\n    if (this.onDataLoaded) {\r\n      this.onDataLoaded({ append, result });\r\n    }\r\n    return result;\r\n  }\r\n\r\n  /**\r\n   * Calls a promise updating the status on the controller.\r\n   * @param loadAction The promise that executes the loading from server.\r\n   */\r\n  public setStatus(loadAction: Promise<ODataResult<any>>): Promise<ODataResult<any>> {\r\n    switch (this._status) {\r\n      case \"noInit\":\r\n        this._status = \"initialLoading\";\r\n        break;\r\n      case \"initialLoading\":\r\n        // TODO: We should somehow cancel the first call and run only the last one.\r\n        this._status = \"initialLoading\";\r\n        break;\r\n      case \"loadError\":\r\n        this._status = (this.items ? \"reloading\" : \"initialLoading\");\r\n        break;\r\n      case \"loaded\":\r\n        this._status = \"reloading\";\r\n        break;\r\n      case \"reloading\":\r\n        // TODO: We should somehow cancel the first call and run only the last one.\r\n        this._status = \"reloading\";\r\n        break;\r\n      default:\r\n        throw Error(\"Unexpected status: \" + this._status);\r\n    }\r\n    return loadAction.then((data) => {\r\n      this._status = \"loaded\";\r\n      return data;\r\n    })\r\n      .catch((error) => {\r\n        this._status = \"loadError\";\r\n        return null;\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Returns the current crud api.\r\n   */\r\n  public getApi(): CrudApiBase<any, any> {\r\n    if ( this.$crudController ) {\r\n      return this.$crudController.getApi();\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /**\r\n   * Export items. Does not update cache or current items.\r\n   * @param maxCount - maximum number of items to return.\r\n   * maxCount can have the following values:\r\n   * - ```0``` Return all items from the data source.\r\n   * - ```-1``` Return only the currently listed items using the current $filter and $search.\r\n   * - ```n``` Where n is any positive number, returns the given number of items. Should be more than 50 (default page size).\r\n   * @param notify -  function for notifying progress.\r\n   */\r\n  public exportItems(maxCount: number, notify: progressNotification<void> = null): Promise<ApiListItem[]> {\r\n    if (maxCount == -1) {\r\n      return Promise.resolve(this.items || []);\r\n    }\r\n    // TODO: See if all this IF's is really necessary\r\n    if (this.url) {\r\n      return OData.exportItems(this.url, {}, this.reader as Ajax, notify);\r\n    }\r\n    else if (this.$crudController)\r\n    {\r\n      return OData.exportItems(this.$crudController.getApi().getODataUrl(), {}, this.reader as Ajax, notify);\r\n    }\r\n    else\r\n    {\r\n      return Promise.resolve([]);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Makes a http call to server using the curre\r\n   * @param options - Options based on which the OData query is created.\r\n   * @param append - If true, appends the result to the data.\r\n   * @returns A promise of OData result as returned by setValues() method.\r\n   */\r\n  protected loadData(options: ODataQueryOptions, append = false): Promise<ODataResult<any>> {\r\n    // HACK: Go though this logic: When to use the strongly typed API and how to enable hard-coded url.\r\n    const url = this.getUrl();\r\n    if (!append && this.cacheService.hasData(this.cacheKey, url)) {\r\n      // TODO: Consider should we support append in cache as well?\r\n      return this.setStatus(Promise.resolve(this.setValues(this.cacheService.getData(this.cacheKey, url), append)));\r\n    }\r\n    if (this.url) {\r\n      // URL has been overriden\r\n      return this.setStatus(this.reader.getJSON(url).then((data) => {\r\n        this.cacheService.setData(this.cacheKey, url, data, 5 * 60);\r\n        return this.setValues(data, append);\r\n      }));\r\n    }\r\n\r\n    if (this.$crudController) {\r\n      return this.setStatus(this.$crudController.getOData(options).then((data) => {\r\n        this.cacheService.setData(this.cacheKey, url, data, 5 * 60);\r\n        return this.setValues(data, append);\r\n      }));\r\n    }\r\n\r\n    throw Error(\"No url given for OData queries\");\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Certificate, Certificates } from \"@salaxy/core\";\r\n\r\nimport { UiHelpers } from \"../../services\";\r\nimport { ApiCrudObjectController } from \"../bases\";\r\n\r\n/**\r\n * Plain CRUD controller for Certificates.\r\n */\r\nexport class CertificateCrudController extends ApiCrudObjectController<Certificate, never> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"Certificates\",\r\n    \"UiHelpers\",\r\n    \"$location\",\r\n    \"$routeParams\",\r\n  ];\r\n\r\n  constructor(\r\n    private fullApi: Certificates,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n\r\n  ) { // Dependency injection\r\n    super(fullApi, uiHelpers, $location, $routeParams);\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"/certificates\",\r\n      detailsUrl: this.detailsUrl || \"/certificates/details/\",\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/Certificates.html\",\r\n      oDataOptions: { },\r\n    };\r\n  }\r\n}\r\n","\r\n/**\r\n * Known dialog actions: Buttons that result in closing the dialog.\r\n * A dialog action can be a string for special purposes, but if the dialog action is something clerly reuasable, you may add it here.\r\n */\r\nexport enum EditDialogKnownActions {\r\n  /** Primary action of the dialog: Often Save (Insert / Update) */\r\n  Ok = \"ok\",\r\n\r\n  /** Primary action of the dialog: Often Save (Insert / Update). Does not perform any save operation against api. */\r\n  OkNoCommit = \"ok-no-save\",\r\n\r\n  /**\r\n   * Cancel / reset dialog action.\r\n   * Also the close button at the top-right corner, esc keyboard action and clicking outside dialog when available.\r\n   */\r\n  Cancel = \"cancel\",\r\n\r\n  /**\r\n   * Delete item action in editor windows.\r\n   */\r\n  Delete = \"delete\",\r\n\r\n  /**\r\n   * Delete item action in editor windows. Does not perform any delete operation against api.\r\n   */\r\n  DeleteNoCommit = \"delete-no-save\",\r\n}\r\n","/**\r\n * Parameters that are passed to an Edit dialog using uiHelpers.openEditDialog()\r\n * and potentially in the future by other logic.\r\n */\r\nexport class EditDialogParameters<TItem> {\r\n\r\n  /** The edited item - published as $ctrl.current within the view. */\r\n  public current: TItem;\r\n\r\n  /**\r\n   * Additional logic that can be used to pass small functions and non-item parameters / data to view.\r\n   * Large amounts of logic should be passed as custom controllers.\r\n   * Published as $ctrl.logic within the view.\r\n   */\r\n  public logic: any;\r\n}\r\n","import { EditDialogKnownActions } from \"./EditDialogKnownActions\";\r\n\r\n/** Result from a modal dialog */\r\nexport class EditDialogResult<TItem> {\r\n\r\n  /**\r\n   * Result of the modal is typically either OK or Cancel.\r\n   * Edit dialogs often also have \"delete\", but you may add custom actions.\r\n   */\r\n  public action: EditDialogKnownActions | string;\r\n\r\n  /**\r\n   * Result is the object that Dialog sends back in $close() method.\r\n   * If this is string, it is interpreted as action.\r\n   */\r\n  public result: EditDialogKnownActions | string | {\r\n     /** Action of the result. */\r\n     action?: EditDialogKnownActions | string,\r\n     } | any;\r\n\r\n  /**\r\n   * Data that is being edited in the dialog.\r\n   */\r\n  public item: TItem;\r\n\r\n  /**\r\n   * The logic part should typically contain functions for the modal view, but in exceptional\r\n   * scenarios you may pass some data back here as well.\r\n   */\r\n  public logic: any;\r\n\r\n  /** If true, the item has been edited by the user and should typically be saved. */\r\n  public hasChanges: boolean;\r\n}\r\n","import { AjaxNg1 } from \"../../ajax\";\r\n\r\n/**\r\n * Handles error, warning and debug alerts and other such error handling situations.\r\n * Default functionality is to find #salaxy-alert-container and insert a bootstrap alert box into that container.\r\n */\r\nexport class AlertService {\r\n\r\n    /**\r\n     * For NG-dependency injection\r\n     * @ignore\r\n     */\r\n    public static $inject = [\"$rootScope\", \"$timeout\", \"$sce\"];\r\n\r\n    /** Default duration for alerts to be visible */\r\n    public duration = 10;\r\n\r\n    /** Service level counter of alerts. Used for identifier. */\r\n    private alertCounter = 0;\r\n\r\n    private alerts: {\r\n      /** Id for the alert. */\r\n      id: number,\r\n      /** Message of the alert. */\r\n      message: string,\r\n      /** Type of the alert. */\r\n      alertType: string,\r\n    }[] = [];\r\n\r\n    private eventPrefix = \"alert\";\r\n\r\n    /** Dependency injection etc. */\r\n    constructor(private $rootScope: angular.IRootScopeService, private $timeout: angular.ITimeoutService, private $sce: angular.ISCEService) {\r\n        this.init();\r\n    }\r\n\r\n    /**\r\n     * Adds an error message\r\n     * @param message Message to add\r\n     */\r\n    public addError(message: string): void { this.addAlert(message, \"danger\"); }\r\n\r\n    /**\r\n     * Adds a warning message\r\n     * @param message Message to add\r\n     */\r\n    public addWarning(message: string): void { this.addAlert(message, \"warning\"); }\r\n\r\n    /**\r\n     * Adds a success message\r\n     * @param message Message to add\r\n     */\r\n    public addSuccess(message: string): void { this.addAlert(message, \"success\"); }\r\n\r\n    /**\r\n     * Adds an info message\r\n     * @param message Message to add\r\n     */\r\n    public addInfo(message: string): void { this.addAlert(message, \"info\"); }\r\n\r\n    /**\r\n     * Last message - consider this a temporary implementation of the custom alert handling\r\n     * @returns Last message\r\n     */\r\n    public getLastMessage(): string {\r\n        return this.alerts[this.alerts.length - 1].message || null;\r\n    }\r\n\r\n    /**\r\n     * Last alertType is bootstrap type: info (default), success, warning or danger.\r\n     * Consider this a temporary implementation of the custom alert handling\r\n     * @returns Last alert type\r\n     */\r\n    public getLastAlertType(): string {\r\n        return this.alerts[this.alerts.length - 1].alertType || null;\r\n    }\r\n\r\n    /**\r\n     * INTERNAL ONLY: This functionality is under consideration.\r\n     * We may not support it in the future and we may remove it without it being a breaking change.\r\n     *\r\n     * Controllers can subscribe to changes in service data using this method.\r\n     * Read more about the pattern in: http://www.codelord.net/2015/05/04/angularjs-notifying-about-changes-from-services-to-controllers/\r\n     * @ignore\r\n     * @param scope - Controller scope for the subscribing controller (or directive etc.)\r\n     * @param callback - The event listener function. See $on documentation for details\r\n     */\r\n    public onChange(scope: angular.IScope, callback: (event: angular.IAngularEvent, ...args: any[]) => any): void {\r\n        const handler = this.$rootScope.$on(this.eventPrefix + \"-service-event\", callback);\r\n        scope.$on(\"$destroy\", handler);\r\n    }\r\n\r\n    /**\r\n     * Attaches the alert service to AjaxNg1.\r\n     * The init is currently called automatically in constructor, but here you can make an explicit call.\r\n     */\r\n    public init() {\r\n      AjaxNg1.alertService = this;\r\n    }\r\n\r\n    /**\r\n     * Adds an alert message\r\n     * @param message - A message text for the Alert. Preferably a short text so that it fits to the pull-righ box.\r\n     * @param alertType - Bootstrap color code for the alert info (default), success, warning or danger\r\n     */\r\n    private addAlert(message: string, alertType: \"info\" | \"success\" | \"warning\" | \"danger\"): void {\r\n\r\n        const alert = {\r\n            message,\r\n            alertType: alertType || \"info\",\r\n            id: this.alertCounter++,\r\n        };\r\n\r\n        this.alerts.push(alert);\r\n        this.notify();\r\n        this.renderAlerts();\r\n\r\n        this.$timeout(() => {\r\n            this.alerts.splice(0, 1);\r\n            this.notify();\r\n            this.renderAlerts();\r\n        }, 1000 * this.duration);\r\n    }\r\n\r\n    private renderAlerts() {\r\n        const container = document.getElementById(\"salaxy-alert-container\");\r\n        if (!container) {\r\n            return;\r\n        }\r\n\r\n        const hiddenAlerts = [];\r\n        const currentList = container.children;\r\n        for (let i = 0; i < currentList.length; i++) {\r\n            if (currentList[i].classList.contains(\"hide\")) {\r\n                hiddenAlerts.push(currentList[i].id);\r\n            }\r\n        }\r\n\r\n        let html = \"\";\r\n        const length = this.alerts.length;\r\n        for (let i = length; i-- !== 0;) {\r\n            const alert = this.alerts[i];\r\n            const alertElementId = \"salaxy-alert-id-\" + alert.id;\r\n            if (hiddenAlerts.find((x) => x === alertElementId)) {\r\n                continue;\r\n            }\r\n\r\n            html += `<div id=\"${alertElementId}\" class=\"alert alert-${alert.alertType} alert-dismissible\" role=\"alert\">\r\n            ${this.$sce.getTrustedHtml(alert.message)}\r\n            <button type=\"button\" class=\"btn-close\" data-dismiss=\"alert\" aria-label=\"Close\" onclick=\"document.getElementById('${alertElementId}').classList.toggle('hide');\"></button>\r\n          </div>`;\r\n        }\r\n        container.innerHTML = html;\r\n    }\r\n\r\n    private notify(): void {\r\n        this.$rootScope.$emit(this.eventPrefix + \"-service-event\");\r\n    }\r\n}\r\n","/* eslint-disable */\n\n// (C) 1995-2013 Jean-loup Gailly and Mark Adler\n// (C) 2014-2017 Vitaly Puzrin and Andrey Tupitsin\n//\n// This software is provided 'as-is', without any express or implied\n// warranty. In no event will the authors be held liable for any damages\n// arising from the use of this software.\n//\n// Permission is granted to anyone to use this software for any purpose,\n// including commercial applications, and to alter it and redistribute it\n// freely, subject to the following restrictions:\n//\n// 1. The origin of this software must not be misrepresented; you must not\n//   claim that you wrote the original software. If you use this software\n//   in a product, an acknowledgment in the product documentation would be\n//   appreciated but is not required.\n// 2. Altered source versions must be plainly marked as such, and must not be\n//   misrepresented as being the original software.\n// 3. This notice may not be removed or altered from any source distribution.\n\n/* Allowed flush values; see deflate() and inflate() below for details */\nvar Z_NO_FLUSH =          0;\nvar Z_PARTIAL_FLUSH =     1;\nvar Z_SYNC_FLUSH =        2;\nvar Z_FULL_FLUSH =        3;\nvar Z_FINISH =            4;\nvar Z_BLOCK =             5;\nvar Z_TREES =             6;\n\n/* Return codes for the compression/decompression functions. Negative values\n* are errors, positive values are used for special but normal events.\n*/\nvar Z_OK =                0;\nvar Z_STREAM_END =        1;\nvar Z_NEED_DICT =         2;\nvar Z_ERRNO =            -1;\nvar Z_STREAM_ERROR =     -2;\nvar Z_DATA_ERROR =       -3;\n//export var Z_MEM_ERROR =      -4;\nvar Z_BUF_ERROR =        -5;\n//export var Z_VERSION_ERROR =  -6;\n\n/* compression levels */\nvar Z_NO_COMPRESSION =          0;\nvar Z_BEST_SPEED =              1;\nvar Z_BEST_COMPRESSION =        9;\nvar Z_DEFAULT_COMPRESSION =    -1;\n\n\nvar Z_FILTERED =                1;\nvar Z_HUFFMAN_ONLY =            2;\nvar Z_RLE =                     3;\nvar Z_FIXED =                   4;\nvar Z_DEFAULT_STRATEGY =        0;\n\n/* Possible values of the data_type field (though see inflate()) */\nvar Z_BINARY =                  0;\nvar Z_TEXT =                    1;\n//export var Z_ASCII =                 1; // = Z_TEXT (deprecated)\nvar Z_UNKNOWN =                 2;\n\n/* The deflate compression method */\nvar Z_DEFLATED =                8;\n//export var Z_NULL =                  null // Use -1 or null inline; depending on var type\n\n/* eslint-disable */\n\nfunction _has(obj, key) {\n  return Object.prototype.hasOwnProperty.call(obj, key);\n}\n\nfunction assign(obj /*from1, from2, from3, ...*/) {\n  var sources = Array.prototype.slice.call(arguments, 1);\n  while (sources.length) {\n    var source = sources.shift();\n    if (!source) { continue; }\n\n    if (typeof source !== 'object') {\n      throw new TypeError(source + 'must be non-object');\n    }\n\n    for (var p in source) {\n      if (_has(source, p)) {\n        obj[p] = source[p];\n      }\n    }\n  }\n\n  return obj;\n}\n\n\n// reduce buffer size, avoiding mem copy\nfunction shrinkBuf(buf, size) {\n  if (buf.length === size) { return buf; }\n  if (buf.subarray) { return buf.subarray(0, size); }\n  buf.length = size;\n  return buf;\n}\n\nvar fnTyped = {\n  arraySet: function (dest, src, src_offs, len, dest_offs) {\n    if (src.subarray && dest.subarray) {\n      dest.set(src.subarray(src_offs, src_offs + len), dest_offs);\n      return;\n    }\n    // Fallback to ordinary array\n    for (var i = 0; i < len; i++) {\n      dest[dest_offs + i] = src[src_offs + i];\n    }\n  },\n  // Join array of chunks to single array.\n  flattenChunks: function (chunks) {\n    var i, l, len, pos, chunk, result;\n\n    // calculate data length\n    len = 0;\n    for (i = 0, l = chunks.length; i < l; i++) {\n      len += chunks[i].length;\n    }\n\n    // join chunks\n    result = new Uint8Array(len);\n    pos = 0;\n    for (i = 0, l = chunks.length; i < l; i++) {\n      chunk = chunks[i];\n      result.set(chunk, pos);\n      pos += chunk.length;\n    }\n\n    return result;\n  },\n  Buf8: function(size) {\n    return new Uint8Array(size);\n  },\n  Buf16: function(size) {\n    return new Uint16Array(size);\n  },\n  Buf32: function(size) {\n    return new Int32Array(size);\n  }\n};\n\nvar fnUntyped = {\n  arraySet: function (dest, src, src_offs, len, dest_offs) {\n    for (var i = 0; i < len; i++) {\n      dest[dest_offs + i] = src[src_offs + i];\n    }\n  },\n  // Join array of chunks to single array.\n  flattenChunks: function (chunks) {\n    return [].concat.apply([], chunks);\n  },\n  Buf8: function(size) {\n    return new Array(size);\n  },\n  Buf16: function(size) {\n    return new Array(size);\n  },\n  Buf32: function(size) {\n    return new Array(size);\n  }\n};\n\nvar typedOK = function () {\n  var supported =\n    (typeof Uint8Array !== 'undefined') &&\n    (typeof Uint16Array !== 'undefined') &&\n    (typeof Int32Array !== 'undefined');\n\n  typedOK = function () { return supported; };\n  return supported;\n};\n\nvar arraySet = function (dest, src, src_offs, len, dest_offs) {\n  arraySet = typedOK() ?\n    fnTyped.arraySet : fnUntyped.arraySet;\n\n  return arraySet(dest, src, src_offs, len, dest_offs);\n};\n\nvar flattenChunks = function (chunks) {\n  flattenChunks = typedOK() ?\n    fnTyped.flattenChunks : fnUntyped.flattenChunks;\n\n  return flattenChunks(chunks);\n};\n\nvar Buf8 = function (size) {\n  Buf8 = typedOK() ? fnTyped.Buf8 : fnUntyped.Buf8;\n  return Buf8(size);\n};\n\nvar Buf16 = function (size) {\n  Buf16 = typedOK() ? fnTyped.Buf16 : fnUntyped.Buf16;\n  return Buf16(size);\n};\n\nvar Buf32 = function (size) {\n  Buf32 = typedOK() ? fnTyped.Buf32 : fnUntyped.Buf32;\n  return Buf32(size);\n};\n\n/* eslint-disable */\n\n\n// Quick check if we can use fast array to bin string conversion\n//\n// - apply(Array) can fail on Android 2.2\n// - apply(Uint8Array) can fail on iOS 5.1 Safari\nvar strApplyOK = function() {\n    var result = true;\n    try {\n        String.fromCharCode.apply(null, [ 0 ]);\n    } catch (_) {\n        result = false;\n    }\n\n    strApplyOK = function () { return result; };\n    return result;\n};\n\nvar strApplyUintOK = function() {\n    var result = true;\n    try {\n        String.fromCharCode.apply(null, new Uint8Array(1));\n    } catch (_) {\n        result = false;\n    }\n\n    strApplyUintOK = function () { return result; };\n    return result;\n};\n\nvar utf8len = function(c) {\n    // Table with utf8 lengths (calculated by first byte of sequence)\n    // Note, that 5 & 6-byte values and some 4-byte values can not be represented in JS,\n    // because max possible codepoint is 0x10ffff\n    var table = Buf8(256);\n    for (var q = 0; q < 256; q++) {\n      table[q] = (q >= 252 ? 6 : q >= 248 ? 5 : q >= 240 ? 4 : q >= 224 ? 3 : q >= 192 ? 2 : 1);\n    }\n    table[254] = table[254] = 1; // Invalid sequence start\n\n    utf8len = function (arg) { return table[arg]; };\n    return table[c];\n};\n\n// convert string to array (typed, when possible)\nfunction string2buf(str) {\n  var buf, c, c2, m_pos, i, str_len = str.length, buf_len = 0;\n\n  // count binary size\n  for (m_pos = 0; m_pos < str_len; m_pos++) {\n    c = str.charCodeAt(m_pos);\n    if ((c & 0xfc00) === 0xd800 && (m_pos + 1 < str_len)) {\n      c2 = str.charCodeAt(m_pos + 1);\n      if ((c2 & 0xfc00) === 0xdc00) {\n        c = 0x10000 + ((c - 0xd800) << 10) + (c2 - 0xdc00);\n        m_pos++;\n      }\n    }\n    buf_len += c < 0x80 ? 1 : c < 0x800 ? 2 : c < 0x10000 ? 3 : 4;\n  }\n\n  // allocate buffer\n  buf = new Uint8Array(buf_len);\n\n  // convert\n  for (i = 0, m_pos = 0; i < buf_len; m_pos++) {\n    c = str.charCodeAt(m_pos);\n    if ((c & 0xfc00) === 0xd800 && (m_pos + 1 < str_len)) {\n      c2 = str.charCodeAt(m_pos + 1);\n      if ((c2 & 0xfc00) === 0xdc00) {\n        c = 0x10000 + ((c - 0xd800) << 10) + (c2 - 0xdc00);\n        m_pos++;\n      }\n    }\n    if (c < 0x80) {\n      /* one byte */\n      buf[i++] = c;\n    } else if (c < 0x800) {\n      /* two bytes */\n      buf[i++] = 0xC0 | (c >>> 6);\n      buf[i++] = 0x80 | (c & 0x3f);\n    } else if (c < 0x10000) {\n      /* three bytes */\n      buf[i++] = 0xE0 | (c >>> 12);\n      buf[i++] = 0x80 | (c >>> 6 & 0x3f);\n      buf[i++] = 0x80 | (c & 0x3f);\n    } else {\n      /* four bytes */\n      buf[i++] = 0xf0 | (c >>> 18);\n      buf[i++] = 0x80 | (c >>> 12 & 0x3f);\n      buf[i++] = 0x80 | (c >>> 6 & 0x3f);\n      buf[i++] = 0x80 | (c & 0x3f);\n    }\n  }\n\n  return buf;\n}\n\n// Helper (used in 2 places)\nfunction _buf2binstring(buf, len) {\n  // On Chrome, the arguments in a function call that are allowed is `65534`.\n  // If the length of the buffer is smaller than that, we can use this optimization,\n  // otherwise we will take a slower path.\n  if (len < 65534) {\n    if ((buf.subarray && strApplyUintOK()) || (!buf.subarray && strApplyOK())) {\n      return String.fromCharCode.apply(null, shrinkBuf(buf, len));\n    }\n  }\n\n  var result = '';\n  for (var i = 0; i < len; i++) {\n    result += String.fromCharCode(buf[i]);\n  }\n  return result;\n}\n\n\n// Convert byte array to binary string\nfunction buf2binstring(buf) {\n  return _buf2binstring(buf, buf.length);\n}\n\n\n// Convert binary string (typed, when possible)\nfunction binstring2buf(str) {\n  var buf = new Uint8Array(str.length);\n  for (var i = 0, len = buf.length; i < len; i++) {\n    buf[i] = str.charCodeAt(i);\n  }\n  return buf;\n}\n\n\n// convert array to string\nfunction buf2string(buf, max) {\n  var i, out, c, c_len;\n  var len = max || buf.length;\n\n  // Reserve max possible length (2 words per char)\n  // NB: by unknown reasons, Array is significantly faster for\n  //     String.fromCharCode.apply than Uint16Array.\n  var utf16buf = new Array(len * 2);\n\n  for (out = 0, i = 0; i < len;) {\n    c = buf[i++];\n    // quick process ascii\n    if (c < 0x80) { utf16buf[out++] = c; continue; }\n\n    c_len = utf8len(c);\n    // skip 5 & 6 byte codes\n    if (c_len > 4) { utf16buf[out++] = 0xfffd; i += c_len - 1; continue; }\n\n    // apply mask on first byte\n    c &= c_len === 2 ? 0x1f : c_len === 3 ? 0x0f : 0x07;\n    // join the rest\n    while (c_len > 1 && i < len) {\n      c = (c << 6) | (buf[i++] & 0x3f);\n      c_len--;\n    }\n\n    // terminated by end of string?\n    if (c_len > 1) { utf16buf[out++] = 0xfffd; continue; }\n\n    if (c < 0x10000) {\n      utf16buf[out++] = c;\n    } else {\n      c -= 0x10000;\n      utf16buf[out++] = 0xd800 | ((c >> 10) & 0x3ff);\n      utf16buf[out++] = 0xdc00 | (c & 0x3ff);\n    }\n  }\n\n  return _buf2binstring(utf16buf, out);\n}\n\n\n// Calculate max possible position in utf8 buffer,\n// that will not break sequence. If that's not possible\n// - (very small limits) return max size as is.\n//\n// buf[] - utf8 bytes array\n// max   - length limit (mandatory);\nfunction utf8border(buf, max) {\n  var pos;\n\n  max = max || buf.length;\n  if (max > buf.length) { max = buf.length; }\n\n  // go back from last position, until start of sequence found\n  pos = max - 1;\n  while (pos >= 0 && (buf[pos] & 0xC0) === 0x80) { pos--; }\n\n  // Very small and broken sequence,\n  // return max, because we should return something anyway.\n  if (pos < 0) { return max; }\n\n  // If we came to start of buffer - that means buffer is too small,\n  // return max too.\n  if (pos === 0) { return max; }\n\n  return (pos + utf8len(buf[pos]) > max) ? pos : max;\n}\n\n/* eslint-disable */\n\n// Note: adler32 takes 12% for level 0 and 2% for level 6.\n// It isn't worth it to make additional optimizations as in original.\n// Small size is preferable.\n\n// (C) 1995-2013 Jean-loup Gailly and Mark Adler\n// (C) 2014-2017 Vitaly Puzrin and Andrey Tupitsin\n//\n// This software is provided 'as-is', without any express or implied\n// warranty. In no event will the authors be held liable for any damages\n// arising from the use of this software.\n//\n// Permission is granted to anyone to use this software for any purpose,\n// including commercial applications, and to alter it and redistribute it\n// freely, subject to the following restrictions:\n//\n// 1. The origin of this software must not be misrepresented; you must not\n//   claim that you wrote the original software. If you use this software\n//   in a product, an acknowledgment in the product documentation would be\n//   appreciated but is not required.\n// 2. Altered source versions must be plainly marked as such, and must not be\n//   misrepresented as being the original software.\n// 3. This notice may not be removed or altered from any source distribution.\n\nfunction adler32(adler, buf, len, pos) {\n  var s1 = (adler & 0xffff) |0,\n      s2 = ((adler >>> 16) & 0xffff) |0,\n      n = 0;\n\n  while (len !== 0) {\n    // Set limit ~ twice less than 5552, to keep\n    // s2 in 31-bits, because we force signed ints.\n    // in other case %= will fail.\n    n = len > 2000 ? 2000 : len;\n    len -= n;\n\n    do {\n      s1 = (s1 + buf[pos++]) |0;\n      s2 = (s2 + s1) |0;\n    } while (--n);\n\n    s1 %= 65521;\n    s2 %= 65521;\n  }\n\n  return (s1 | (s2 << 16)) |0;\n}\n\n/* eslint-disable */\n\n// Note: we can't get significant speed boost here.\n// So write code to minimize size - no pregenerated tables\n// and array tools dependencies.\n\n// (C) 1995-2013 Jean-loup Gailly and Mark Adler\n// (C) 2014-2017 Vitaly Puzrin and Andrey Tupitsin\n//\n// This software is provided 'as-is', without any express or implied\n// warranty. In no event will the authors be held liable for any damages\n// arising from the use of this software.\n//\n// Permission is granted to anyone to use this software for any purpose,\n// including commercial applications, and to alter it and redistribute it\n// freely, subject to the following restrictions:\n//\n// 1. The origin of this software must not be misrepresented; you must not\n//   claim that you wrote the original software. If you use this software\n//   in a product, an acknowledgment in the product documentation would be\n//   appreciated but is not required.\n// 2. Altered source versions must be plainly marked as such, and must not be\n//   misrepresented as being the original software.\n// 3. This notice may not be removed or altered from any source distribution.\n\n// Use ordinary array, since untyped makes no boost here\nfunction makeTable() {\n  var c, table = [];\n\n  for (var n = 0; n < 256; n++) {\n    c = n;\n    for (var k = 0; k < 8; k++) {\n      c = ((c & 1) ? (0xEDB88320 ^ (c >>> 1)) : (c >>> 1));\n    }\n    table[n] = c;\n  }\n\n  return table;\n}\n\nvar crcTable = function() {\n    var table = makeTable();\n    crcTable = function () { return table; };\n    return table;\n};\n\nfunction crc32(crc, buf, len, pos) {\n  var t = crcTable(),\n      end = pos + len;\n\n  crc ^= -1;\n\n  for (var i = pos; i < end; i++) {\n    crc = (crc >>> 8) ^ t[(crc ^ buf[i]) & 0xFF];\n  }\n\n  return (crc ^ (-1)); // >>> 0;\n}\n\n/* eslint-disable */\n\n// (C) 1995-2013 Jean-loup Gailly and Mark Adler\n// (C) 2014-2017 Vitaly Puzrin and Andrey Tupitsin\n//\n// This software is provided 'as-is', without any express or implied\n// warranty. In no event will the authors be held liable for any damages\n// arising from the use of this software.\n//\n// Permission is granted to anyone to use this software for any purpose,\n// including commercial applications, and to alter it and redistribute it\n// freely, subject to the following restrictions:\n//\n// 1. The origin of this software must not be misrepresented; you must not\n//   claim that you wrote the original software. If you use this software\n//   in a product, an acknowledgment in the product documentation would be\n//   appreciated but is not required.\n// 2. Altered source versions must be plainly marked as such, and must not be\n//   misrepresented as being the original software.\n// 3. This notice may not be removed or altered from any source distribution.\n\n// See state defs from inflate.js\nvar BAD = 30;       /* got a data error -- remain here until reset */\nvar TYPE = 12;      /* i: waiting for type bits, including last-flag bit */\n\n/*\n   Decode literal, length, and distance codes and write out the resulting\n   literal and match bytes until either not enough input or output is\n   available, an end-of-block is encountered, or a data error is encountered.\n   When large enough input and output buffers are supplied to inflate(), for\n   example, a 16K input buffer and a 64K output buffer, more than 95% of the\n   inflate execution time is spent in this routine.\n\n   Entry assumptions:\n\n        state.mode === LEN\n        strm.avail_in >= 6\n        strm.avail_out >= 258\n        start >= strm.avail_out\n        state.bits < 8\n\n   On return, state.mode is one of:\n\n        LEN -- ran out of enough output space or enough available input\n        TYPE -- reached end of block code, inflate() to interpret next block\n        BAD -- error in block data\n\n   Notes:\n\n    - The maximum input bits used by a length/distance pair is 15 bits for the\n      length code, 5 bits for the length extra, 15 bits for the distance code,\n      and 13 bits for the distance extra.  This totals 48 bits, or six bytes.\n      Therefore if strm.avail_in >= 6, then there is enough input to avoid\n      checking for available input while decoding.\n\n    - The maximum bytes that a single length/distance pair can output is 258\n      bytes, which is the maximum length that can be coded.  inflate_fast()\n      requires strm.avail_out >= 258 for each loop to avoid checking for\n      output space.\n */\nfunction inflate_fast(strm, start) {\n  var state;\n  var _in;                    /* local strm.input */\n  var last;                   /* have enough input while in < last */\n  var _out;                   /* local strm.output */\n  var beg;                    /* inflate()'s initial strm.output */\n  var end;                    /* while out < end, enough space available */\n//#ifdef INFLATE_STRICT\n  var dmax;                   /* maximum distance from zlib header */\n//#endif\n  var wsize;                  /* window size or zero if not using window */\n  var whave;                  /* valid bytes in the window */\n  var wnext;                  /* window write index */\n  // Use `s_window` instead `window`, avoid conflict with instrumentation tools\n  var s_window;               /* allocated sliding window, if wsize != 0 */\n  var hold;                   /* local strm.hold */\n  var bits;                   /* local strm.bits */\n  var lcode;                  /* local strm.lencode */\n  var dcode;                  /* local strm.distcode */\n  var lmask;                  /* mask for first level of length codes */\n  var dmask;                  /* mask for first level of distance codes */\n  var here;                   /* retrieved table entry */\n  var op;                     /* code bits, operation, extra bits, or */\n                              /*  window position, window bytes to copy */\n  var len;                    /* match length, unused bytes */\n  var dist;                   /* match distance */\n  var from;                   /* where to copy match from */\n  var from_source;\n\n\n  var input, output; // JS specific, because we have no pointers\n\n  /* copy state to local variables */\n  state = strm.state;\n  //here = state.here;\n  _in = strm.next_in;\n  input = strm.input;\n  last = _in + (strm.avail_in - 5);\n  _out = strm.next_out;\n  output = strm.output;\n  beg = _out - (start - strm.avail_out);\n  end = _out + (strm.avail_out - 257);\n//#ifdef INFLATE_STRICT\n  dmax = state.dmax;\n//#endif\n  wsize = state.wsize;\n  whave = state.whave;\n  wnext = state.wnext;\n  s_window = state.window;\n  hold = state.hold;\n  bits = state.bits;\n  lcode = state.lencode;\n  dcode = state.distcode;\n  lmask = (1 << state.lenbits) - 1;\n  dmask = (1 << state.distbits) - 1;\n\n\n  /* decode literals and length/distances until end-of-block or not enough\n     input data or output space */\n\n  top:\n  do {\n    if (bits < 15) {\n      hold += input[_in++] << bits;\n      bits += 8;\n      hold += input[_in++] << bits;\n      bits += 8;\n    }\n\n    here = lcode[hold & lmask];\n\n    dolen:\n    for (;;) { // Goto emulation\n      op = here >>> 24/*here.bits*/;\n      hold >>>= op;\n      bits -= op;\n      op = (here >>> 16) & 0xff/*here.op*/;\n      if (op === 0) {                          /* literal */\n        //Tracevv((stderr, here.val >= 0x20 && here.val < 0x7f ?\n        //        \"inflate:         literal '%c'\\n\" :\n        //        \"inflate:         literal 0x%02x\\n\", here.val));\n        output[_out++] = here & 0xffff/*here.val*/;\n      }\n      else if (op & 16) {                     /* length base */\n        len = here & 0xffff/*here.val*/;\n        op &= 15;                           /* number of extra bits */\n        if (op) {\n          if (bits < op) {\n            hold += input[_in++] << bits;\n            bits += 8;\n          }\n          len += hold & ((1 << op) - 1);\n          hold >>>= op;\n          bits -= op;\n        }\n        //Tracevv((stderr, \"inflate:         length %u\\n\", len));\n        if (bits < 15) {\n          hold += input[_in++] << bits;\n          bits += 8;\n          hold += input[_in++] << bits;\n          bits += 8;\n        }\n        here = dcode[hold & dmask];\n\n        dodist:\n        for (;;) { // goto emulation\n          op = here >>> 24/*here.bits*/;\n          hold >>>= op;\n          bits -= op;\n          op = (here >>> 16) & 0xff/*here.op*/;\n\n          if (op & 16) {                      /* distance base */\n            dist = here & 0xffff/*here.val*/;\n            op &= 15;                       /* number of extra bits */\n            if (bits < op) {\n              hold += input[_in++] << bits;\n              bits += 8;\n              if (bits < op) {\n                hold += input[_in++] << bits;\n                bits += 8;\n              }\n            }\n            dist += hold & ((1 << op) - 1);\n//#ifdef INFLATE_STRICT\n            if (dist > dmax) {\n              strm.msg = 'invalid distance too far back';\n              state.mode = BAD;\n              break top;\n            }\n//#endif\n            hold >>>= op;\n            bits -= op;\n            //Tracevv((stderr, \"inflate:         distance %u\\n\", dist));\n            op = _out - beg;                /* max distance in output */\n            if (dist > op) {                /* see if copy from window */\n              op = dist - op;               /* distance back in window */\n              if (op > whave) {\n                if (state.sane) {\n                  strm.msg = 'invalid distance too far back';\n                  state.mode = BAD;\n                  break top;\n                }\n\n// (!) This block is disabled in zlib defaults,\n// don't enable it for binary compatibility\n//#ifdef INFLATE_ALLOW_INVALID_DISTANCE_TOOFAR_ARRR\n//                if (len <= op - whave) {\n//                  do {\n//                    output[_out++] = 0;\n//                  } while (--len);\n//                  continue top;\n//                }\n//                len -= op - whave;\n//                do {\n//                  output[_out++] = 0;\n//                } while (--op > whave);\n//                if (op === 0) {\n//                  from = _out - dist;\n//                  do {\n//                    output[_out++] = output[from++];\n//                  } while (--len);\n//                  continue top;\n//                }\n//#endif\n              }\n              from = 0; // window index\n              from_source = s_window;\n              if (wnext === 0) {           /* very common case */\n                from += wsize - op;\n                if (op < len) {         /* some from window */\n                  len -= op;\n                  do {\n                    output[_out++] = s_window[from++];\n                  } while (--op);\n                  from = _out - dist;  /* rest from output */\n                  from_source = output;\n                }\n              }\n              else if (wnext < op) {      /* wrap around window */\n                from += wsize + wnext - op;\n                op -= wnext;\n                if (op < len) {         /* some from end of window */\n                  len -= op;\n                  do {\n                    output[_out++] = s_window[from++];\n                  } while (--op);\n                  from = 0;\n                  if (wnext < len) {  /* some from start of window */\n                    op = wnext;\n                    len -= op;\n                    do {\n                      output[_out++] = s_window[from++];\n                    } while (--op);\n                    from = _out - dist;      /* rest from output */\n                    from_source = output;\n                  }\n                }\n              }\n              else {                      /* contiguous in window */\n                from += wnext - op;\n                if (op < len) {         /* some from window */\n                  len -= op;\n                  do {\n                    output[_out++] = s_window[from++];\n                  } while (--op);\n                  from = _out - dist;  /* rest from output */\n                  from_source = output;\n                }\n              }\n              while (len > 2) {\n                output[_out++] = from_source[from++];\n                output[_out++] = from_source[from++];\n                output[_out++] = from_source[from++];\n                len -= 3;\n              }\n              if (len) {\n                output[_out++] = from_source[from++];\n                if (len > 1) {\n                  output[_out++] = from_source[from++];\n                }\n              }\n            }\n            else {\n              from = _out - dist;          /* copy direct from output */\n              do {                        /* minimum length is three */\n                output[_out++] = output[from++];\n                output[_out++] = output[from++];\n                output[_out++] = output[from++];\n                len -= 3;\n              } while (len > 2);\n              if (len) {\n                output[_out++] = output[from++];\n                if (len > 1) {\n                  output[_out++] = output[from++];\n                }\n              }\n            }\n          }\n          else if ((op & 64) === 0) {          /* 2nd level distance code */\n            here = dcode[(here & 0xffff)/*here.val*/ + (hold & ((1 << op) - 1))];\n            continue dodist;\n          }\n          else {\n            strm.msg = 'invalid distance code';\n            state.mode = BAD;\n            break top;\n          }\n\n          break; // need to emulate goto via \"continue\"\n        }\n      }\n      else if ((op & 64) === 0) {              /* 2nd level length code */\n        here = lcode[(here & 0xffff)/*here.val*/ + (hold & ((1 << op) - 1))];\n        continue dolen;\n      }\n      else if (op & 32) {                     /* end-of-block */\n        //Tracevv((stderr, \"inflate:         end of block\\n\"));\n        state.mode = TYPE;\n        break top;\n      }\n      else {\n        strm.msg = 'invalid literal/length code';\n        state.mode = BAD;\n        break top;\n      }\n\n      break; // need to emulate goto via \"continue\"\n    }\n  } while (_in < last && _out < end);\n\n  /* return unused bytes (on entry, bits < 8, so in won't go too far back) */\n  len = bits >> 3;\n  _in -= len;\n  bits -= len << 3;\n  hold &= (1 << bits) - 1;\n\n  /* update state and return */\n  strm.next_in = _in;\n  strm.next_out = _out;\n  strm.avail_in = (_in < last ? 5 + (last - _in) : 5 - (_in - last));\n  strm.avail_out = (_out < end ? 257 + (end - _out) : 257 - (_out - end));\n  state.hold = hold;\n  state.bits = bits;\n  return;\n}\n\n/* eslint-disable */\n\nvar MAXBITS = 15;\nvar ENOUGH_LENS = 852;\nvar ENOUGH_DISTS = 592;\n//var ENOUGH = (ENOUGH_LENS+ENOUGH_DISTS);\n\nvar CODES = 0;\nvar LENS = 1;\nvar DISTS = 2;\n\nvar lbase = [ /* Length codes 257..285 base */\n  3, 4, 5, 6, 7, 8, 9, 10, 11, 13, 15, 17, 19, 23, 27, 31,\n  35, 43, 51, 59, 67, 83, 99, 115, 131, 163, 195, 227, 258, 0, 0\n];\n\nvar lext = [ /* Length codes 257..285 extra */\n  16, 16, 16, 16, 16, 16, 16, 16, 17, 17, 17, 17, 18, 18, 18, 18,\n  19, 19, 19, 19, 20, 20, 20, 20, 21, 21, 21, 21, 16, 72, 78\n];\n\nvar dbase = [ /* Distance codes 0..29 base */\n  1, 2, 3, 4, 5, 7, 9, 13, 17, 25, 33, 49, 65, 97, 129, 193,\n  257, 385, 513, 769, 1025, 1537, 2049, 3073, 4097, 6145,\n  8193, 12289, 16385, 24577, 0, 0\n];\n\nvar dext = [ /* Distance codes 0..29 extra */\n  16, 16, 16, 16, 17, 17, 18, 18, 19, 19, 20, 20, 21, 21, 22, 22,\n  23, 23, 24, 24, 25, 25, 26, 26, 27, 27,\n  28, 28, 29, 29, 64, 64\n];\n\nfunction inflate_table(type, lens, lens_index, codes, table, table_index, work, opts) {\n  var bits = opts.bits;\n      //here = opts.here; /* table entry for duplication */\n\n  var len = 0;               /* a code's length in bits */\n  var sym = 0;               /* index of code symbols */\n  var min = 0, max = 0;          /* minimum and maximum code lengths */\n  var root = 0;              /* number of index bits for root table */\n  var curr = 0;              /* number of index bits for current table */\n  var drop = 0;              /* code bits to drop for sub-table */\n  var left = 0;                   /* number of prefix codes available */\n  var used = 0;              /* code entries in table used */\n  var huff = 0;              /* Huffman code */\n  var incr;              /* for incrementing code, index */\n  var fill;              /* index for replicating entries */\n  var low;               /* low bits for current root entry */\n  var mask;              /* mask for low root bits */\n  var next;             /* next available space in table */\n  var base = null;     /* base value table to use */\n  var base_index = 0;\n//  var shoextra;    /* extra bits table to use */\n  var end;                    /* use base and extra for symbol > end */\n  var count = Buf16(MAXBITS + 1); //[MAXBITS+1];    /* number of codes of each length */\n  var offs = Buf16(MAXBITS + 1); //[MAXBITS+1];     /* offsets in table for each length */\n  var extra = null;\n  var extra_index = 0;\n\n  var here_bits, here_op, here_val;\n\n  /*\n   Process a set of code lengths to create a canonical Huffman code.  The\n   code lengths are lens[0..codes-1].  Each length corresponds to the\n   symbols 0..codes-1.  The Huffman code is generated by first sorting the\n   symbols by length from short to long, and retaining the symbol order\n   for codes with equal lengths.  Then the code starts with all zero bits\n   for the first code of the shortest length, and the codes are integer\n   increments for the same length, and zeros are appended as the length\n   increases.  For the deflate format, these bits are stored backwards\n   from their more natural integer increment ordering, and so when the\n   decoding tables are built in the large loop below, the integer codes\n   are incremented backwards.\n\n   This routine assumes, but does not check, that all of the entries in\n   lens[] are in the range 0..MAXBITS.  The caller must assure this.\n   1..MAXBITS is interpreted as that code length.  zero means that that\n   symbol does not occur in this code.\n\n   The codes are sorted by computing a count of codes for each length,\n   creating from that a table of starting indices for each length in the\n   sorted table, and then entering the symbols in order in the sorted\n   table.  The sorted table is work[], with that space being provided by\n   the caller.\n\n   The length counts are used for other purposes as well, i.e. finding\n   the minimum and maximum length codes, determining if there are any\n   codes at all, checking for a valid set of lengths, and looking ahead\n   at length counts to determine sub-table sizes when building the\n   decoding tables.\n   */\n\n  /* accumulate lengths for codes (assumes lens[] all in 0..MAXBITS) */\n  for (len = 0; len <= MAXBITS; len++) {\n    count[len] = 0;\n  }\n  for (sym = 0; sym < codes; sym++) {\n    count[lens[lens_index + sym]]++;\n  }\n\n  /* bound code lengths, force root to be within code lengths */\n  root = bits;\n  for (max = MAXBITS; max >= 1; max--) {\n    if (count[max] !== 0) { break; }\n  }\n  if (root > max) {\n    root = max;\n  }\n  if (max === 0) {                     /* no symbols to code at all */\n    //table.op[opts.table_index] = 64;  //here.op = (var char)64;    /* invalid code marker */\n    //table.bits[opts.table_index] = 1;   //here.bits = (var char)1;\n    //table.val[opts.table_index++] = 0;   //here.val = (var short)0;\n    table[table_index++] = (1 << 24) | (64 << 16) | 0;\n\n\n    //table.op[opts.table_index] = 64;\n    //table.bits[opts.table_index] = 1;\n    //table.val[opts.table_index++] = 0;\n    table[table_index++] = (1 << 24) | (64 << 16) | 0;\n\n    opts.bits = 1;\n    return 0;     /* no symbols, but wait for decoding to report error */\n  }\n  for (min = 1; min < max; min++) {\n    if (count[min] !== 0) { break; }\n  }\n  if (root < min) {\n    root = min;\n  }\n\n  /* check for an over-subscribed or incomplete set of lengths */\n  left = 1;\n  for (len = 1; len <= MAXBITS; len++) {\n    left <<= 1;\n    left -= count[len];\n    if (left < 0) {\n      return -1;\n    }        /* over-subscribed */\n  }\n  if (left > 0 && (type === CODES || max !== 1)) {\n    return -1;                      /* incomplete set */\n  }\n\n  /* generate offsets into symbol table for each length for sorting */\n  offs[1] = 0;\n  for (len = 1; len < MAXBITS; len++) {\n    offs[len + 1] = offs[len] + count[len];\n  }\n\n  /* sort symbols by length, by symbol order within each length */\n  for (sym = 0; sym < codes; sym++) {\n    if (lens[lens_index + sym] !== 0) {\n      work[offs[lens[lens_index + sym]]++] = sym;\n    }\n  }\n\n  /*\n   Create and fill in decoding tables.  In this loop, the table being\n   filled is at next and has curr index bits.  The code being used is huff\n   with length len.  That code is converted to an index by dropping drop\n   bits off of the bottom.  For codes where len is less than drop + curr,\n   those top drop + curr - len bits are incremented through all values to\n   fill the table with replicated entries.\n\n   root is the number of index bits for the root table.  When len exceeds\n   root, sub-tables are created pointed to by the root entry with an index\n   of the low root bits of huff.  This is saved in low to check for when a\n   new sub-table should be started.  drop is zero when the root table is\n   being filled, and drop is root when sub-tables are being filled.\n\n   When a new sub-table is needed, it is necessary to look ahead in the\n   code lengths to determine what size sub-table is needed.  The length\n   counts are used for this, and so count[] is decremented as codes are\n   entered in the tables.\n\n   used keeps track of how many table entries have been allocated from the\n   provided *table space.  It is checked for LENS and DIST tables against\n   the constants ENOUGH_LENS and ENOUGH_DISTS to guard against changes in\n   the initial root table size constants.  See the comments in inftrees.h\n   for more information.\n\n   sym increments through all symbols, and the loop terminates when\n   all codes of length max, i.e. all codes, have been processed.  This\n   routine permits incomplete codes, so another loop after this one fills\n   in the rest of the decoding tables with invalid code markers.\n   */\n\n  /* set up for code type */\n  // poor man optimization - use if-else instead of switch,\n  // to avoid deopts in old v8\n  if (type === CODES) {\n    base = extra = work;    /* dummy value--not used */\n    end = 19;\n\n  } else if (type === LENS) {\n    base = lbase;\n    base_index -= 257;\n    extra = lext;\n    extra_index -= 257;\n    end = 256;\n\n  } else {                    /* DISTS */\n    base = dbase;\n    extra = dext;\n    end = -1;\n  }\n\n  /* initialize opts for loop */\n  huff = 0;                   /* starting code */\n  sym = 0;                    /* starting code symbol */\n  len = min;                  /* starting code length */\n  next = table_index;              /* current table to fill in */\n  curr = root;                /* current table index bits */\n  drop = 0;                   /* current bits to drop from code for index */\n  low = -1;                   /* trigger new sub-table when len > root */\n  used = 1 << root;          /* use root table entries */\n  mask = used - 1;            /* mask for comparing low */\n\n  /* check available table space */\n  if ((type === LENS && used > ENOUGH_LENS) ||\n    (type === DISTS && used > ENOUGH_DISTS)) {\n    return 1;\n  }\n\n  /* process all codes and make table entries */\n  for (;;) {\n    /* create table entry */\n    here_bits = len - drop;\n    if (work[sym] < end) {\n      here_op = 0;\n      here_val = work[sym];\n    }\n    else if (work[sym] > end) {\n      here_op = extra[extra_index + work[sym]];\n      here_val = base[base_index + work[sym]];\n    }\n    else {\n      here_op = 32 + 64;         /* end of block */\n      here_val = 0;\n    }\n\n    /* replicate for those indices with low len bits equal to huff */\n    incr = 1 << (len - drop);\n    fill = 1 << curr;\n    min = fill;                 /* save offset to next table */\n    do {\n      fill -= incr;\n      table[next + (huff >> drop) + fill] = (here_bits << 24) | (here_op << 16) | here_val |0;\n    } while (fill !== 0);\n\n    /* backwards increment the len-bit code huff */\n    incr = 1 << (len - 1);\n    while (huff & incr) {\n      incr >>= 1;\n    }\n    if (incr !== 0) {\n      huff &= incr - 1;\n      huff += incr;\n    } else {\n      huff = 0;\n    }\n\n    /* go to next symbol, update count, len */\n    sym++;\n    if (--count[len] === 0) {\n      if (len === max) { break; }\n      len = lens[lens_index + work[sym]];\n    }\n\n    /* create new sub-table if needed */\n    if (len > root && (huff & mask) !== low) {\n      /* if first time, transition to sub-tables */\n      if (drop === 0) {\n        drop = root;\n      }\n\n      /* increment past last table */\n      next += min;            /* here min is 1 << curr */\n\n      /* determine length of next table */\n      curr = len - drop;\n      left = 1 << curr;\n      while (curr + drop < max) {\n        left -= count[curr + drop];\n        if (left <= 0) { break; }\n        curr++;\n        left <<= 1;\n      }\n\n      /* check for enough space */\n      used += 1 << curr;\n      if ((type === LENS && used > ENOUGH_LENS) ||\n        (type === DISTS && used > ENOUGH_DISTS)) {\n        return 1;\n      }\n\n      /* point entry in root table to sub-table */\n      low = huff & mask;\n      /*table.op[low] = curr;\n      table.bits[low] = root;\n      table.val[low] = next - opts.table_index;*/\n      table[low] = (root << 24) | (curr << 16) | (next - table_index) |0;\n    }\n  }\n\n  /* fill in remaining table entry if code is incomplete (guaranteed to have\n   at most one remaining entry, since if the code is incomplete, the\n   maximum code length that was allowed to get this far is one bit) */\n  if (huff !== 0) {\n    //table.op[next + huff] = 64;            /* invalid code marker */\n    //table.bits[next + huff] = len - drop;\n    //table.val[next + huff] = 0;\n    table[next + huff] = ((len - drop) << 24) | (64 << 16) |0;\n  }\n\n  /* set return parameters */\n  //opts.table_index += used;\n  opts.bits = root;\n  return 0;\n}\n\n/* eslint-disable */\n\nvar CODES$1 = 0;\nvar LENS$1 = 1;\nvar DISTS$1 = 2;\n\n/* Public constants ==========================================================*/\n/* ===========================================================================*/\n\n\n/* Allowed flush values; see deflate() and inflate() below for details */\n//var Z_NO_FLUSH      = 0;\n//var Z_PARTIAL_FLUSH = 1;\n//var Z_SYNC_FLUSH    = 2;\n//var Z_FULL_FLUSH    = 3;\nvar Z_FINISH$1        = 4;\nvar Z_BLOCK$1         = 5;\nvar Z_TREES$1         = 6;\n\n\n/* Return codes for the compression/decompression functions. Negative values\n * are errors, positive values are used for special but normal events.\n */\nvar Z_OK$1            = 0;\nvar Z_STREAM_END$1    = 1;\nvar Z_NEED_DICT$1     = 2;\n//var Z_ERRNO         = -1;\nvar Z_STREAM_ERROR$1  = -2;\nvar Z_DATA_ERROR$1    = -3;\nvar Z_MEM_ERROR     = -4;\nvar Z_BUF_ERROR$1     = -5;\n//var Z_VERSION_ERROR = -6;\n\n/* The deflate compression method */\nvar Z_DEFLATED$1  = 8;\n\n\n/* STATES ====================================================================*/\n/* ===========================================================================*/\n\n\nvar    HEAD = 1;       /* i: waiting for magic header */\nvar    FLAGS = 2;      /* i: waiting for method and flags (gzip) */\nvar    TIME = 3;       /* i: waiting for modification time (gzip) */\nvar    OS = 4;         /* i: waiting for extra flags and operating system (gzip) */\nvar    EXLEN = 5;      /* i: waiting for extra length (gzip) */\nvar    EXTRA = 6;      /* i: waiting for extra bytes (gzip) */\nvar    NAME = 7;       /* i: waiting for end of file name (gzip) */\nvar    COMMENT = 8;    /* i: waiting for end of comment (gzip) */\nvar    HCRC = 9;       /* i: waiting for header crc (gzip) */\nvar    DICTID = 10;    /* i: waiting for dictionary check value */\nvar    DICT = 11;      /* waiting for inflateSetDictionary() call */\nvar        TYPE$1 = 12;      /* i: waiting for type bits, including last-flag bit */\nvar        TYPEDO = 13;    /* i: same, but skip check to exit inflate on new block */\nvar        STORED = 14;    /* i: waiting for stored size (length and complement) */\nvar        COPY_ = 15;     /* i/o: same as COPY below, but only first time in */\nvar        COPY = 16;      /* i/o: waiting for input or output to copy stored block */\nvar        TABLE = 17;     /* i: waiting for dynamic block table lengths */\nvar        LENLENS = 18;   /* i: waiting for code length code lengths */\nvar        CODELENS = 19;  /* i: waiting for length/lit and distance code lengths */\nvar            LEN_ = 20;      /* i: same as LEN below, but only first time in */\nvar            LEN = 21;       /* i: waiting for length/lit/eob code */\nvar            LENEXT = 22;    /* i: waiting for length extra bits */\nvar            DIST = 23;      /* i: waiting for distance code */\nvar            DISTEXT = 24;   /* i: waiting for distance extra bits */\nvar            MATCH = 25;     /* o: waiting for output space to copy string */\nvar            LIT = 26;       /* o: waiting for output space to write literal */\nvar    CHECK = 27;     /* i: waiting for 32-bit check value */\nvar    LENGTH = 28;    /* i: waiting for 32-bit length (gzip) */\nvar    DONE = 29;      /* finished check, done -- remain here until reset */\nvar    BAD$1 = 30;       /* got a data error -- remain here until reset */\nvar    MEM = 31;       /* got an inflate() memory error -- remain here until reset */\nvar    SYNC = 32;      /* looking for synchronization bytes to restart inflate() */\n\n/* ===========================================================================*/\n\n\n\nvar ENOUGH_LENS$1 = 852;\nvar ENOUGH_DISTS$1 = 592;\n\n\nfunction zswap32(q) {\n  return  (((q >>> 24) & 0xff) +\n          ((q >>> 8) & 0xff00) +\n          ((q & 0xff00) << 8) +\n          ((q & 0xff) << 24));\n}\n\n\nfunction InflateState() {\n  this.mode = 0;             /* current inflate mode */\n  this.last = false;          /* true if processing last block */\n  this.wrap = 0;              /* bit 0 true for zlib, bit 1 true for gzip */\n  this.havedict = false;      /* true if dictionary provided */\n  this.flags = 0;             /* gzip header method and flags (0 if zlib) */\n  this.dmax = 0;              /* zlib header max distance (INFLATE_STRICT) */\n  this.check = 0;             /* protected copy of check value */\n  this.total = 0;             /* protected copy of output count */\n  // TODO: may be {}\n  this.head = null;           /* where to save gzip header information */\n\n  /* sliding window */\n  this.wbits = 0;             /* log base 2 of requested window size */\n  this.wsize = 0;             /* window size or zero if not using window */\n  this.whave = 0;             /* valid bytes in the window */\n  this.wnext = 0;             /* window write index */\n  this.window = null;         /* allocated sliding window, if needed */\n\n  /* bit accumulator */\n  this.hold = 0;              /* input bit accumulator */\n  this.bits = 0;              /* number of bits in \"in\" */\n\n  /* for string and stored block copying */\n  this.length = 0;            /* literal or length of data to copy */\n  this.offset = 0;            /* distance back to copy string from */\n\n  /* for table and code decoding */\n  this.extra = 0;             /* extra bits needed */\n\n  /* fixed and dynamic code tables */\n  this.lencode = null;          /* starting table for length/literal codes */\n  this.distcode = null;         /* starting table for distance codes */\n  this.lenbits = 0;           /* index bits for lencode */\n  this.distbits = 0;          /* index bits for distcode */\n\n  /* dynamic table building */\n  this.ncode = 0;             /* number of code length code lengths */\n  this.nlen = 0;              /* number of length code lengths */\n  this.ndist = 0;             /* number of distance code lengths */\n  this.have = 0;              /* number of code lengths in lens[] */\n  this.next = null;              /* next available space in codes[] */\n\n  this.lens = Buf16(320); /* temporary storage for code lengths */\n  this.work = Buf16(288); /* work area for code table building */\n\n  /*\n   because we don't have pointers in js, we use lencode and distcode directly\n   as buffers so we don't need codes\n  */\n  //this.codes = Buf32(ENOUGH);       /* space for code tables */\n  this.lendyn = null;              /* dynamic table for length/literal codes (JS specific) */\n  this.distdyn = null;             /* dynamic table for distance codes (JS specific) */\n  this.sane = 0;                   /* if false, allow invalid distance too far */\n  this.back = 0;                   /* bits back of last unprocessed length/lit */\n  this.was = 0;                    /* initial length of match */\n}\n\nfunction inflateResetKeep(strm) {\n  var state;\n\n  if (!strm || !strm.state) { return Z_STREAM_ERROR$1; }\n  state = strm.state;\n  strm.total_in = strm.total_out = state.total = 0;\n  strm.msg = ''; /*Z_NULL*/\n  if (state.wrap) {       /* to support ill-conceived Java test suite */\n    strm.adler = state.wrap & 1;\n  }\n  state.mode = HEAD;\n  state.last = 0;\n  state.havedict = 0;\n  state.dmax = 32768;\n  state.head = null/*Z_NULL*/;\n  state.hold = 0;\n  state.bits = 0;\n  //state.lencode = state.distcode = state.next = state.codes;\n  state.lencode = state.lendyn = Buf32(ENOUGH_LENS$1);\n  state.distcode = state.distdyn = Buf32(ENOUGH_DISTS$1);\n\n  state.sane = 1;\n  state.back = -1;\n  //Tracev((stderr, \"inflate: reset\\n\"));\n  return Z_OK$1;\n}\n\nfunction inflateReset(strm) {\n  var state;\n\n  if (!strm || !strm.state) { return Z_STREAM_ERROR$1; }\n  state = strm.state;\n  state.wsize = 0;\n  state.whave = 0;\n  state.wnext = 0;\n  return inflateResetKeep(strm);\n\n}\n\nfunction inflateReset2(strm, windowBits) {\n  var wrap;\n  var state;\n\n  /* get the state */\n  if (!strm || !strm.state) { return Z_STREAM_ERROR$1; }\n  state = strm.state;\n\n  /* extract wrap request from windowBits parameter */\n  if (windowBits < 0) {\n    wrap = 0;\n    windowBits = -windowBits;\n  }\n  else {\n    wrap = (windowBits >> 4) + 1;\n    if (windowBits < 48) {\n      windowBits &= 15;\n    }\n  }\n\n  /* set number of window bits, free window if different */\n  if (windowBits && (windowBits < 8 || windowBits > 15)) {\n    return Z_STREAM_ERROR$1;\n  }\n  if (state.window !== null && state.wbits !== windowBits) {\n    state.window = null;\n  }\n\n  /* update state and reset the rest of it */\n  state.wrap = wrap;\n  state.wbits = windowBits;\n  return inflateReset(strm);\n}\n\nfunction inflateInit2(strm, windowBits) {\n  var ret;\n  var state;\n\n  if (!strm) { return Z_STREAM_ERROR$1; }\n  //strm.msg = Z_NULL;                 /* in case we return an error */\n\n  state = new InflateState();\n\n  //if (state === Z_NULL) return Z_MEM_ERROR;\n  //Tracev((stderr, \"inflate: allocated\\n\"));\n  strm.state = state;\n  state.window = null/*Z_NULL*/;\n  ret = inflateReset2(strm, windowBits);\n  if (ret !== Z_OK$1) {\n    strm.state = null/*Z_NULL*/;\n  }\n  return ret;\n}\n\n\n/*\n Return state with length and distance decoding tables and index sizes set to\n fixed code decoding.  Normally this returns fixed tables from inffixed.h.\n If BUILDFIXED is defined, then instead this routine builds the tables the\n first time it's called, and returns those tables the first time and\n thereafter.  This reduces the size of the code by about 2K bytes, in\n exchange for a little execution time.  However, BUILDFIXED should not be\n used for threaded applications, since the rewriting of the tables and virgin\n may not be thread-safe.\n */\nvar virgin = true;\n\nvar lenfix, distfix; // We have no pointers in JS, so keep tables separate\n\nfunction fixedtables(state) {\n  /* build fixed huffman tables if first call (may not be thread safe) */\n  if (virgin) {\n    var sym;\n\n    lenfix = Buf32(512);\n    distfix = Buf32(32);\n\n    /* literal/length table */\n    sym = 0;\n    while (sym < 144) { state.lens[sym++] = 8; }\n    while (sym < 256) { state.lens[sym++] = 9; }\n    while (sym < 280) { state.lens[sym++] = 7; }\n    while (sym < 288) { state.lens[sym++] = 8; }\n\n    inflate_table(LENS$1,  state.lens, 0, 288, lenfix,   0, state.work, { bits: 9 });\n\n    /* distance table */\n    sym = 0;\n    while (sym < 32) { state.lens[sym++] = 5; }\n\n    inflate_table(DISTS$1, state.lens, 0, 32,   distfix, 0, state.work, { bits: 5 });\n\n    /* do this just once */\n    virgin = false;\n  }\n\n  state.lencode = lenfix;\n  state.lenbits = 9;\n  state.distcode = distfix;\n  state.distbits = 5;\n}\n\n\n/*\n Update the window with the last wsize (normally 32K) bytes written before\n returning.  If window does not exist yet, create it.  This is only called\n when a window is already in use, or when output has been written during this\n inflate call, but the end of the deflate stream has not been reached yet.\n It is also called to create a window for dictionary data when a dictionary\n is loaded.\n\n Providing output buffers larger than 32K to inflate() should provide a speed\n advantage, since only the last 32K of output is copied to the sliding window\n upon return from inflate(), and since all distances after the first 32K of\n output will fall in the output data, making match copies simpler and faster.\n The advantage may be dependent on the size of the processor's data caches.\n */\nfunction updatewindow(strm, src, end, copy) {\n  var dist;\n  var state = strm.state;\n\n  /* if it hasn't been done already, allocate space for the window */\n  if (state.window === null) {\n    state.wsize = 1 << state.wbits;\n    state.wnext = 0;\n    state.whave = 0;\n\n    state.window = Buf8(state.wsize);\n  }\n\n  /* copy state->wsize or less output bytes into the circular window */\n  if (copy >= state.wsize) {\n    arraySet(state.window, src, end - state.wsize, state.wsize, 0);\n    state.wnext = 0;\n    state.whave = state.wsize;\n  }\n  else {\n    dist = state.wsize - state.wnext;\n    if (dist > copy) {\n      dist = copy;\n    }\n    //zmemcpy(state->window + state->wnext, end - copy, dist);\n    arraySet(state.window, src, end - copy, dist, state.wnext);\n    copy -= dist;\n    if (copy) {\n      //zmemcpy(state->window, end - copy, copy);\n      arraySet(state.window, src, end - copy, copy, 0);\n      state.wnext = copy;\n      state.whave = state.wsize;\n    }\n    else {\n      state.wnext += dist;\n      if (state.wnext === state.wsize) { state.wnext = 0; }\n      if (state.whave < state.wsize) { state.whave += dist; }\n    }\n  }\n  return 0;\n}\n\nfunction inflate(strm, flush) {\n  var state;\n  var input, output;          // input/output buffers\n  var next;                   /* next input INDEX */\n  var put;                    /* next output INDEX */\n  var have, left;             /* available input and output */\n  var hold;                   /* bit buffer */\n  var bits;                   /* bits in bit buffer */\n  var _in, _out;              /* save starting available input and output */\n  var copy;                   /* number of stored or match bytes to copy */\n  var from;                   /* where to copy match bytes from */\n  var from_source;\n  var here = 0;               /* current decoding table entry */\n  var here_bits, here_op, here_val; // paked \"here\" denormalized (JS specific)\n  //var last;                   /* parent table entry */\n  var last_bits, last_op, last_val; // paked \"last\" denormalized (JS specific)\n  var len;                    /* length to copy for repeats, bits to drop */\n  var ret;                    /* return code */\n  var hbuf = Buf8(4);    /* buffer for gzip header crc calculation */\n  var opts;\n\n  var n; // temporary var for NEED_BITS\n\n  var order = /* permutation of code lengths */\n    [ 16, 17, 18, 0, 8, 7, 9, 6, 10, 5, 11, 4, 12, 3, 13, 2, 14, 1, 15 ];\n\n\n  if (!strm || !strm.state || !strm.output ||\n      (!strm.input && strm.avail_in !== 0)) {\n    return Z_STREAM_ERROR$1;\n  }\n\n  state = strm.state;\n  if (state.mode === TYPE$1) { state.mode = TYPEDO; }    /* skip check */\n\n\n  //--- LOAD() ---\n  put = strm.next_out;\n  output = strm.output;\n  left = strm.avail_out;\n  next = strm.next_in;\n  input = strm.input;\n  have = strm.avail_in;\n  hold = state.hold;\n  bits = state.bits;\n  //---\n\n  _in = have;\n  _out = left;\n  ret = Z_OK$1;\n\n  inf_leave: // goto emulation\n  for (;;) {\n    switch (state.mode) {\n      case HEAD:\n        if (state.wrap === 0) {\n          state.mode = TYPEDO;\n          break;\n        }\n        //=== NEEDBITS(16);\n        while (bits < 16) {\n          if (have === 0) { break inf_leave; }\n          have--;\n          hold += input[next++] << bits;\n          bits += 8;\n        }\n        //===//\n        if ((state.wrap & 2) && hold === 0x8b1f) {  /* gzip header */\n          state.check = 0/*crc32(0L, Z_NULL, 0)*/;\n          //=== CRC2(state.check, hold);\n          hbuf[0] = hold & 0xff;\n          hbuf[1] = (hold >>> 8) & 0xff;\n          state.check = crc32(state.check, hbuf, 2, 0);\n          //===//\n\n          //=== INITBITS();\n          hold = 0;\n          bits = 0;\n          //===//\n          state.mode = FLAGS;\n          break;\n        }\n        state.flags = 0;           /* expect zlib header */\n        if (state.head) {\n          state.head.done = false;\n        }\n        if (!(state.wrap & 1) ||   /* check if zlib header allowed */\n          (((hold & 0xff)/*BITS(8)*/ << 8) + (hold >> 8)) % 31) {\n          strm.msg = 'incorrect header check';\n          state.mode = BAD$1;\n          break;\n        }\n        if ((hold & 0x0f)/*BITS(4)*/ !== Z_DEFLATED$1) {\n          strm.msg = 'unknown compression method';\n          state.mode = BAD$1;\n          break;\n        }\n        //--- DROPBITS(4) ---//\n        hold >>>= 4;\n        bits -= 4;\n        //---//\n        len = (hold & 0x0f)/*BITS(4)*/ + 8;\n        if (state.wbits === 0) {\n          state.wbits = len;\n        }\n        else if (len > state.wbits) {\n          strm.msg = 'invalid window size';\n          state.mode = BAD$1;\n          break;\n        }\n        state.dmax = 1 << len;\n        //Tracev((stderr, \"inflate:   zlib header ok\\n\"));\n        strm.adler = state.check = 1/*adler32(0L, Z_NULL, 0)*/;\n        state.mode = hold & 0x200 ? DICTID : TYPE$1;\n        //=== INITBITS();\n        hold = 0;\n        bits = 0;\n        //===//\n        break;\n      case FLAGS:\n        //=== NEEDBITS(16); */\n        while (bits < 16) {\n          if (have === 0) { break inf_leave; }\n          have--;\n          hold += input[next++] << bits;\n          bits += 8;\n        }\n        //===//\n        state.flags = hold;\n        if ((state.flags & 0xff) !== Z_DEFLATED$1) {\n          strm.msg = 'unknown compression method';\n          state.mode = BAD$1;\n          break;\n        }\n        if (state.flags & 0xe000) {\n          strm.msg = 'unknown header flags set';\n          state.mode = BAD$1;\n          break;\n        }\n        if (state.head) {\n          state.head.text = ((hold >> 8) & 1);\n        }\n        if (state.flags & 0x0200) {\n          //=== CRC2(state.check, hold);\n          hbuf[0] = hold & 0xff;\n          hbuf[1] = (hold >>> 8) & 0xff;\n          state.check = crc32(state.check, hbuf, 2, 0);\n          //===//\n        }\n        //=== INITBITS();\n        hold = 0;\n        bits = 0;\n        //===//\n        state.mode = TIME;\n        /* falls through */\n      case TIME:\n        //=== NEEDBITS(32); */\n        while (bits < 32) {\n          if (have === 0) { break inf_leave; }\n          have--;\n          hold += input[next++] << bits;\n          bits += 8;\n        }\n        //===//\n        if (state.head) {\n          state.head.time = hold;\n        }\n        if (state.flags & 0x0200) {\n          //=== CRC4(state.check, hold)\n          hbuf[0] = hold & 0xff;\n          hbuf[1] = (hold >>> 8) & 0xff;\n          hbuf[2] = (hold >>> 16) & 0xff;\n          hbuf[3] = (hold >>> 24) & 0xff;\n          state.check = crc32(state.check, hbuf, 4, 0);\n          //===\n        }\n        //=== INITBITS();\n        hold = 0;\n        bits = 0;\n        //===//\n        state.mode = OS;\n        /* falls through */\n      case OS:\n        //=== NEEDBITS(16); */\n        while (bits < 16) {\n          if (have === 0) { break inf_leave; }\n          have--;\n          hold += input[next++] << bits;\n          bits += 8;\n        }\n        //===//\n        if (state.head) {\n          state.head.xflags = (hold & 0xff);\n          state.head.os = (hold >> 8);\n        }\n        if (state.flags & 0x0200) {\n          //=== CRC2(state.check, hold);\n          hbuf[0] = hold & 0xff;\n          hbuf[1] = (hold >>> 8) & 0xff;\n          state.check = crc32(state.check, hbuf, 2, 0);\n          //===//\n        }\n        //=== INITBITS();\n        hold = 0;\n        bits = 0;\n        //===//\n        state.mode = EXLEN;\n        /* falls through */\n      case EXLEN:\n        if (state.flags & 0x0400) {\n          //=== NEEDBITS(16); */\n          while (bits < 16) {\n            if (have === 0) { break inf_leave; }\n            have--;\n            hold += input[next++] << bits;\n            bits += 8;\n          }\n          //===//\n          state.length = hold;\n          if (state.head) {\n            state.head.extra_len = hold;\n          }\n          if (state.flags & 0x0200) {\n            //=== CRC2(state.check, hold);\n            hbuf[0] = hold & 0xff;\n            hbuf[1] = (hold >>> 8) & 0xff;\n            state.check = crc32(state.check, hbuf, 2, 0);\n            //===//\n          }\n          //=== INITBITS();\n          hold = 0;\n          bits = 0;\n          //===//\n        }\n        else if (state.head) {\n          state.head.extra = null/*Z_NULL*/;\n        }\n        state.mode = EXTRA;\n        /* falls through */\n      case EXTRA:\n        if (state.flags & 0x0400) {\n          copy = state.length;\n          if (copy > have) { copy = have; }\n          if (copy) {\n            if (state.head) {\n              len = state.head.extra_len - state.length;\n              if (!state.head.extra) {\n                // Use untyped array for more convenient processing later\n                state.head.extra = new Array(state.head.extra_len);\n              }\n              arraySet(\n                state.head.extra,\n                input,\n                next,\n                // extra field is limited to 65536 bytes\n                // - no need for additional size check\n                copy,\n                /*len + copy > state.head.extra_max - len ? state.head.extra_max : copy,*/\n                len\n              );\n              //zmemcpy(state.head.extra + len, next,\n              //        len + copy > state.head.extra_max ?\n              //        state.head.extra_max - len : copy);\n            }\n            if (state.flags & 0x0200) {\n              state.check = crc32(state.check, input, copy, next);\n            }\n            have -= copy;\n            next += copy;\n            state.length -= copy;\n          }\n          if (state.length) { break inf_leave; }\n        }\n        state.length = 0;\n        state.mode = NAME;\n        /* falls through */\n      case NAME:\n        if (state.flags & 0x0800) {\n          if (have === 0) { break inf_leave; }\n          copy = 0;\n          do {\n            // TODO: 2 or 1 bytes?\n            len = input[next + copy++];\n            /* use constant limit because in js we should not preallocate memory */\n            if (state.head && len &&\n                (state.length < 65536 /*state.head.name_max*/)) {\n              state.head.name += String.fromCharCode(len);\n            }\n          } while (len && copy < have);\n\n          if (state.flags & 0x0200) {\n            state.check = crc32(state.check, input, copy, next);\n          }\n          have -= copy;\n          next += copy;\n          if (len) { break inf_leave; }\n        }\n        else if (state.head) {\n          state.head.name = null;\n        }\n        state.length = 0;\n        state.mode = COMMENT;\n        /* falls through */\n      case COMMENT:\n        if (state.flags & 0x1000) {\n          if (have === 0) { break inf_leave; }\n          copy = 0;\n          do {\n            len = input[next + copy++];\n            /* use constant limit because in js we should not preallocate memory */\n            if (state.head && len &&\n                (state.length < 65536 /*state.head.comm_max*/)) {\n              state.head.comment += String.fromCharCode(len);\n            }\n          } while (len && copy < have);\n          if (state.flags & 0x0200) {\n            state.check = crc32(state.check, input, copy, next);\n          }\n          have -= copy;\n          next += copy;\n          if (len) { break inf_leave; }\n        }\n        else if (state.head) {\n          state.head.comment = null;\n        }\n        state.mode = HCRC;\n        /* falls through */\n      case HCRC:\n        if (state.flags & 0x0200) {\n          //=== NEEDBITS(16); */\n          while (bits < 16) {\n            if (have === 0) { break inf_leave; }\n            have--;\n            hold += input[next++] << bits;\n            bits += 8;\n          }\n          //===//\n          if (hold !== (state.check & 0xffff)) {\n            strm.msg = 'header crc mismatch';\n            state.mode = BAD$1;\n            break;\n          }\n          //=== INITBITS();\n          hold = 0;\n          bits = 0;\n          //===//\n        }\n        if (state.head) {\n          state.head.hcrc = ((state.flags >> 9) & 1);\n          state.head.done = true;\n        }\n        strm.adler = state.check = 0;\n        state.mode = TYPE$1;\n        break;\n      case DICTID:\n        //=== NEEDBITS(32); */\n        while (bits < 32) {\n          if (have === 0) { break inf_leave; }\n          have--;\n          hold += input[next++] << bits;\n          bits += 8;\n        }\n        //===//\n        strm.adler = state.check = zswap32(hold);\n        //=== INITBITS();\n        hold = 0;\n        bits = 0;\n        //===//\n        state.mode = DICT;\n        /* falls through */\n      case DICT:\n        if (state.havedict === 0) {\n          //--- RESTORE() ---\n          strm.next_out = put;\n          strm.avail_out = left;\n          strm.next_in = next;\n          strm.avail_in = have;\n          state.hold = hold;\n          state.bits = bits;\n          //---\n          return Z_NEED_DICT$1;\n        }\n        strm.adler = state.check = 1/*adler32(0L, Z_NULL, 0)*/;\n        state.mode = TYPE$1;\n        /* falls through */\n      case TYPE$1:\n        if (flush === Z_BLOCK$1 || flush === Z_TREES$1) { break inf_leave; }\n        /* falls through */\n      case TYPEDO:\n        if (state.last) {\n          //--- BYTEBITS() ---//\n          hold >>>= bits & 7;\n          bits -= bits & 7;\n          //---//\n          state.mode = CHECK;\n          break;\n        }\n        //=== NEEDBITS(3); */\n        while (bits < 3) {\n          if (have === 0) { break inf_leave; }\n          have--;\n          hold += input[next++] << bits;\n          bits += 8;\n        }\n        //===//\n        state.last = (hold & 0x01)/*BITS(1)*/;\n        //--- DROPBITS(1) ---//\n        hold >>>= 1;\n        bits -= 1;\n        //---//\n\n        switch ((hold & 0x03)/*BITS(2)*/) {\n          case 0:                             /* stored block */\n            //Tracev((stderr, \"inflate:     stored block%s\\n\",\n            //        state.last ? \" (last)\" : \"\"));\n            state.mode = STORED;\n            break;\n          case 1:                             /* fixed block */\n            fixedtables(state);\n            //Tracev((stderr, \"inflate:     fixed codes block%s\\n\",\n            //        state.last ? \" (last)\" : \"\"));\n            state.mode = LEN_;             /* decode codes */\n            if (flush === Z_TREES$1) {\n              //--- DROPBITS(2) ---//\n              hold >>>= 2;\n              bits -= 2;\n              //---//\n              break inf_leave;\n            }\n            break;\n          case 2:                             /* dynamic block */\n            //Tracev((stderr, \"inflate:     dynamic codes block%s\\n\",\n            //        state.last ? \" (last)\" : \"\"));\n            state.mode = TABLE;\n            break;\n          case 3:\n            strm.msg = 'invalid block type';\n            state.mode = BAD$1;\n        }\n        //--- DROPBITS(2) ---//\n        hold >>>= 2;\n        bits -= 2;\n        //---//\n        break;\n      case STORED:\n        //--- BYTEBITS() ---// /* go to byte boundary */\n        hold >>>= bits & 7;\n        bits -= bits & 7;\n        //---//\n        //=== NEEDBITS(32); */\n        while (bits < 32) {\n          if (have === 0) { break inf_leave; }\n          have--;\n          hold += input[next++] << bits;\n          bits += 8;\n        }\n        //===//\n        if ((hold & 0xffff) !== ((hold >>> 16) ^ 0xffff)) {\n          strm.msg = 'invalid stored block lengths';\n          state.mode = BAD$1;\n          break;\n        }\n        state.length = hold & 0xffff;\n        //Tracev((stderr, \"inflate:       stored length %u\\n\",\n        //        state.length));\n        //=== INITBITS();\n        hold = 0;\n        bits = 0;\n        //===//\n        state.mode = COPY_;\n        if (flush === Z_TREES$1) { break inf_leave; }\n        /* falls through */\n      case COPY_:\n        state.mode = COPY;\n        /* falls through */\n      case COPY:\n        copy = state.length;\n        if (copy) {\n          if (copy > have) { copy = have; }\n          if (copy > left) { copy = left; }\n          if (copy === 0) { break inf_leave; }\n          //--- zmemcpy(put, next, copy); ---\n          arraySet(output, input, next, copy, put);\n          //---//\n          have -= copy;\n          next += copy;\n          left -= copy;\n          put += copy;\n          state.length -= copy;\n          break;\n        }\n        //Tracev((stderr, \"inflate:       stored end\\n\"));\n        state.mode = TYPE$1;\n        break;\n      case TABLE:\n        //=== NEEDBITS(14); */\n        while (bits < 14) {\n          if (have === 0) { break inf_leave; }\n          have--;\n          hold += input[next++] << bits;\n          bits += 8;\n        }\n        //===//\n        state.nlen = (hold & 0x1f)/*BITS(5)*/ + 257;\n        //--- DROPBITS(5) ---//\n        hold >>>= 5;\n        bits -= 5;\n        //---//\n        state.ndist = (hold & 0x1f)/*BITS(5)*/ + 1;\n        //--- DROPBITS(5) ---//\n        hold >>>= 5;\n        bits -= 5;\n        //---//\n        state.ncode = (hold & 0x0f)/*BITS(4)*/ + 4;\n        //--- DROPBITS(4) ---//\n        hold >>>= 4;\n        bits -= 4;\n        //---//\n//#ifndef PKZIP_BUG_WORKAROUND\n        if (state.nlen > 286 || state.ndist > 30) {\n          strm.msg = 'too many length or distance symbols';\n          state.mode = BAD$1;\n          break;\n        }\n//#endif\n        //Tracev((stderr, \"inflate:       table sizes ok\\n\"));\n        state.have = 0;\n        state.mode = LENLENS;\n        /* falls through */\n      case LENLENS:\n        while (state.have < state.ncode) {\n          //=== NEEDBITS(3);\n          while (bits < 3) {\n            if (have === 0) { break inf_leave; }\n            have--;\n            hold += input[next++] << bits;\n            bits += 8;\n          }\n          //===//\n          state.lens[order[state.have++]] = (hold & 0x07);//BITS(3);\n          //--- DROPBITS(3) ---//\n          hold >>>= 3;\n          bits -= 3;\n          //---//\n        }\n        while (state.have < 19) {\n          state.lens[order[state.have++]] = 0;\n        }\n        // We have separate tables & no pointers. 2 commented lines below not needed.\n        //state.next = state.codes;\n        //state.lencode = state.next;\n        // Switch to use dynamic table\n        state.lencode = state.lendyn;\n        state.lenbits = 7;\n\n        opts = { bits: state.lenbits };\n        ret = inflate_table(CODES$1, state.lens, 0, 19, state.lencode, 0, state.work, opts);\n        state.lenbits = opts.bits;\n\n        if (ret) {\n          strm.msg = 'invalid code lengths set';\n          state.mode = BAD$1;\n          break;\n        }\n        //Tracev((stderr, \"inflate:       code lengths ok\\n\"));\n        state.have = 0;\n        state.mode = CODELENS;\n        /* falls through */\n      case CODELENS:\n        while (state.have < state.nlen + state.ndist) {\n          for (;;) {\n            here = state.lencode[hold & ((1 << state.lenbits) - 1)];/*BITS(state.lenbits)*/\n            here_bits = here >>> 24;\n            here_op = (here >>> 16) & 0xff;\n            here_val = here & 0xffff;\n\n            if ((here_bits) <= bits) { break; }\n            //--- PULLBYTE() ---//\n            if (have === 0) { break inf_leave; }\n            have--;\n            hold += input[next++] << bits;\n            bits += 8;\n            //---//\n          }\n          if (here_val < 16) {\n            //--- DROPBITS(here.bits) ---//\n            hold >>>= here_bits;\n            bits -= here_bits;\n            //---//\n            state.lens[state.have++] = here_val;\n          }\n          else {\n            if (here_val === 16) {\n              //=== NEEDBITS(here.bits + 2);\n              n = here_bits + 2;\n              while (bits < n) {\n                if (have === 0) { break inf_leave; }\n                have--;\n                hold += input[next++] << bits;\n                bits += 8;\n              }\n              //===//\n              //--- DROPBITS(here.bits) ---//\n              hold >>>= here_bits;\n              bits -= here_bits;\n              //---//\n              if (state.have === 0) {\n                strm.msg = 'invalid bit length repeat';\n                state.mode = BAD$1;\n                break;\n              }\n              len = state.lens[state.have - 1];\n              copy = 3 + (hold & 0x03);//BITS(2);\n              //--- DROPBITS(2) ---//\n              hold >>>= 2;\n              bits -= 2;\n              //---//\n            }\n            else if (here_val === 17) {\n              //=== NEEDBITS(here.bits + 3);\n              n = here_bits + 3;\n              while (bits < n) {\n                if (have === 0) { break inf_leave; }\n                have--;\n                hold += input[next++] << bits;\n                bits += 8;\n              }\n              //===//\n              //--- DROPBITS(here.bits) ---//\n              hold >>>= here_bits;\n              bits -= here_bits;\n              //---//\n              len = 0;\n              copy = 3 + (hold & 0x07);//BITS(3);\n              //--- DROPBITS(3) ---//\n              hold >>>= 3;\n              bits -= 3;\n              //---//\n            }\n            else {\n              //=== NEEDBITS(here.bits + 7);\n              n = here_bits + 7;\n              while (bits < n) {\n                if (have === 0) { break inf_leave; }\n                have--;\n                hold += input[next++] << bits;\n                bits += 8;\n              }\n              //===//\n              //--- DROPBITS(here.bits) ---//\n              hold >>>= here_bits;\n              bits -= here_bits;\n              //---//\n              len = 0;\n              copy = 11 + (hold & 0x7f);//BITS(7);\n              //--- DROPBITS(7) ---//\n              hold >>>= 7;\n              bits -= 7;\n              //---//\n            }\n            if (state.have + copy > state.nlen + state.ndist) {\n              strm.msg = 'invalid bit length repeat';\n              state.mode = BAD$1;\n              break;\n            }\n            while (copy--) {\n              state.lens[state.have++] = len;\n            }\n          }\n        }\n\n        /* handle error breaks in while */\n        if (state.mode === BAD$1) { break; }\n\n        /* check for end-of-block code (better have one) */\n        if (state.lens[256] === 0) {\n          strm.msg = 'invalid code -- missing end-of-block';\n          state.mode = BAD$1;\n          break;\n        }\n\n        /* build code tables -- note: do not change the lenbits or distbits\n           values here (9 and 6) without reading the comments in inftrees.h\n           concerning the ENOUGH constants, which depend on those values */\n        state.lenbits = 9;\n\n        opts = { bits: state.lenbits };\n        ret = inflate_table(LENS$1, state.lens, 0, state.nlen, state.lencode, 0, state.work, opts);\n        // We have separate tables & no pointers. 2 commented lines below not needed.\n        // state.next_index = opts.table_index;\n        state.lenbits = opts.bits;\n        // state.lencode = state.next;\n\n        if (ret) {\n          strm.msg = 'invalid literal/lengths set';\n          state.mode = BAD$1;\n          break;\n        }\n\n        state.distbits = 6;\n        //state.distcode.copy(state.codes);\n        // Switch to use dynamic table\n        state.distcode = state.distdyn;\n        opts = { bits: state.distbits };\n        ret = inflate_table(DISTS$1, state.lens, state.nlen, state.ndist, state.distcode, 0, state.work, opts);\n        // We have separate tables & no pointers. 2 commented lines below not needed.\n        // state.next_index = opts.table_index;\n        state.distbits = opts.bits;\n        // state.distcode = state.next;\n\n        if (ret) {\n          strm.msg = 'invalid distances set';\n          state.mode = BAD$1;\n          break;\n        }\n        //Tracev((stderr, 'inflate:       codes ok\\n'));\n        state.mode = LEN_;\n        if (flush === Z_TREES$1) { break inf_leave; }\n        /* falls through */\n      case LEN_:\n        state.mode = LEN;\n        /* falls through */\n      case LEN:\n        if (have >= 6 && left >= 258) {\n          //--- RESTORE() ---\n          strm.next_out = put;\n          strm.avail_out = left;\n          strm.next_in = next;\n          strm.avail_in = have;\n          state.hold = hold;\n          state.bits = bits;\n          //---\n          inflate_fast(strm, _out);\n          //--- LOAD() ---\n          put = strm.next_out;\n          output = strm.output;\n          left = strm.avail_out;\n          next = strm.next_in;\n          input = strm.input;\n          have = strm.avail_in;\n          hold = state.hold;\n          bits = state.bits;\n          //---\n\n          if (state.mode === TYPE$1) {\n            state.back = -1;\n          }\n          break;\n        }\n        state.back = 0;\n        for (;;) {\n          here = state.lencode[hold & ((1 << state.lenbits) - 1)];  /*BITS(state.lenbits)*/\n          here_bits = here >>> 24;\n          here_op = (here >>> 16) & 0xff;\n          here_val = here & 0xffff;\n\n          if (here_bits <= bits) { break; }\n          //--- PULLBYTE() ---//\n          if (have === 0) { break inf_leave; }\n          have--;\n          hold += input[next++] << bits;\n          bits += 8;\n          //---//\n        }\n        if (here_op && (here_op & 0xf0) === 0) {\n          last_bits = here_bits;\n          last_op = here_op;\n          last_val = here_val;\n          for (;;) {\n            here = state.lencode[last_val +\n                    ((hold & ((1 << (last_bits + last_op)) - 1))/*BITS(last.bits + last.op)*/ >> last_bits)];\n            here_bits = here >>> 24;\n            here_op = (here >>> 16) & 0xff;\n            here_val = here & 0xffff;\n\n            if ((last_bits + here_bits) <= bits) { break; }\n            //--- PULLBYTE() ---//\n            if (have === 0) { break inf_leave; }\n            have--;\n            hold += input[next++] << bits;\n            bits += 8;\n            //---//\n          }\n          //--- DROPBITS(last.bits) ---//\n          hold >>>= last_bits;\n          bits -= last_bits;\n          //---//\n          state.back += last_bits;\n        }\n        //--- DROPBITS(here.bits) ---//\n        hold >>>= here_bits;\n        bits -= here_bits;\n        //---//\n        state.back += here_bits;\n        state.length = here_val;\n        if (here_op === 0) {\n          //Tracevv((stderr, here.val >= 0x20 && here.val < 0x7f ?\n          //        \"inflate:         literal '%c'\\n\" :\n          //        \"inflate:         literal 0x%02x\\n\", here.val));\n          state.mode = LIT;\n          break;\n        }\n        if (here_op & 32) {\n          //Tracevv((stderr, \"inflate:         end of block\\n\"));\n          state.back = -1;\n          state.mode = TYPE$1;\n          break;\n        }\n        if (here_op & 64) {\n          strm.msg = 'invalid literal/length code';\n          state.mode = BAD$1;\n          break;\n        }\n        state.extra = here_op & 15;\n        state.mode = LENEXT;\n        /* falls through */\n      case LENEXT:\n        if (state.extra) {\n          //=== NEEDBITS(state.extra);\n          n = state.extra;\n          while (bits < n) {\n            if (have === 0) { break inf_leave; }\n            have--;\n            hold += input[next++] << bits;\n            bits += 8;\n          }\n          //===//\n          state.length += hold & ((1 << state.extra) - 1)/*BITS(state.extra)*/;\n          //--- DROPBITS(state.extra) ---//\n          hold >>>= state.extra;\n          bits -= state.extra;\n          //---//\n          state.back += state.extra;\n        }\n        //Tracevv((stderr, \"inflate:         length %u\\n\", state.length));\n        state.was = state.length;\n        state.mode = DIST;\n        /* falls through */\n      case DIST:\n        for (;;) {\n          here = state.distcode[hold & ((1 << state.distbits) - 1)];/*BITS(state.distbits)*/\n          here_bits = here >>> 24;\n          here_op = (here >>> 16) & 0xff;\n          here_val = here & 0xffff;\n\n          if ((here_bits) <= bits) { break; }\n          //--- PULLBYTE() ---//\n          if (have === 0) { break inf_leave; }\n          have--;\n          hold += input[next++] << bits;\n          bits += 8;\n          //---//\n        }\n        if ((here_op & 0xf0) === 0) {\n          last_bits = here_bits;\n          last_op = here_op;\n          last_val = here_val;\n          for (;;) {\n            here = state.distcode[last_val +\n                    ((hold & ((1 << (last_bits + last_op)) - 1))/*BITS(last.bits + last.op)*/ >> last_bits)];\n            here_bits = here >>> 24;\n            here_op = (here >>> 16) & 0xff;\n            here_val = here & 0xffff;\n\n            if ((last_bits + here_bits) <= bits) { break; }\n            //--- PULLBYTE() ---//\n            if (have === 0) { break inf_leave; }\n            have--;\n            hold += input[next++] << bits;\n            bits += 8;\n            //---//\n          }\n          //--- DROPBITS(last.bits) ---//\n          hold >>>= last_bits;\n          bits -= last_bits;\n          //---//\n          state.back += last_bits;\n        }\n        //--- DROPBITS(here.bits) ---//\n        hold >>>= here_bits;\n        bits -= here_bits;\n        //---//\n        state.back += here_bits;\n        if (here_op & 64) {\n          strm.msg = 'invalid distance code';\n          state.mode = BAD$1;\n          break;\n        }\n        state.offset = here_val;\n        state.extra = (here_op) & 15;\n        state.mode = DISTEXT;\n        /* falls through */\n      case DISTEXT:\n        if (state.extra) {\n          //=== NEEDBITS(state.extra);\n          n = state.extra;\n          while (bits < n) {\n            if (have === 0) { break inf_leave; }\n            have--;\n            hold += input[next++] << bits;\n            bits += 8;\n          }\n          //===//\n          state.offset += hold & ((1 << state.extra) - 1)/*BITS(state.extra)*/;\n          //--- DROPBITS(state.extra) ---//\n          hold >>>= state.extra;\n          bits -= state.extra;\n          //---//\n          state.back += state.extra;\n        }\n//#ifdef INFLATE_STRICT\n        if (state.offset > state.dmax) {\n          strm.msg = 'invalid distance too far back';\n          state.mode = BAD$1;\n          break;\n        }\n//#endif\n        //Tracevv((stderr, \"inflate:         distance %u\\n\", state.offset));\n        state.mode = MATCH;\n        /* falls through */\n      case MATCH:\n        if (left === 0) { break inf_leave; }\n        copy = _out - left;\n        if (state.offset > copy) {         /* copy from window */\n          copy = state.offset - copy;\n          if (copy > state.whave) {\n            if (state.sane) {\n              strm.msg = 'invalid distance too far back';\n              state.mode = BAD$1;\n              break;\n            }\n// (!) This block is disabled in zlib defaults,\n// don't enable it for binary compatibility\n//#ifdef INFLATE_ALLOW_INVALID_DISTANCE_TOOFAR_ARRR\n//          Trace((stderr, \"inflate.c too far\\n\"));\n//          copy -= state.whave;\n//          if (copy > state.length) { copy = state.length; }\n//          if (copy > left) { copy = left; }\n//          left -= copy;\n//          state.length -= copy;\n//          do {\n//            output[put++] = 0;\n//          } while (--copy);\n//          if (state.length === 0) { state.mode = LEN; }\n//          break;\n//#endif\n          }\n          if (copy > state.wnext) {\n            copy -= state.wnext;\n            from = state.wsize - copy;\n          }\n          else {\n            from = state.wnext - copy;\n          }\n          if (copy > state.length) { copy = state.length; }\n          from_source = state.window;\n        }\n        else {                              /* copy from output */\n          from_source = output;\n          from = put - state.offset;\n          copy = state.length;\n        }\n        if (copy > left) { copy = left; }\n        left -= copy;\n        state.length -= copy;\n        do {\n          output[put++] = from_source[from++];\n        } while (--copy);\n        if (state.length === 0) { state.mode = LEN; }\n        break;\n      case LIT:\n        if (left === 0) { break inf_leave; }\n        output[put++] = state.length;\n        left--;\n        state.mode = LEN;\n        break;\n      case CHECK:\n        if (state.wrap) {\n          //=== NEEDBITS(32);\n          while (bits < 32) {\n            if (have === 0) { break inf_leave; }\n            have--;\n            // Use '|' instead of '+' to make sure that result is signed\n            hold |= input[next++] << bits;\n            bits += 8;\n          }\n          //===//\n          _out -= left;\n          strm.total_out += _out;\n          state.total += _out;\n          if (_out) {\n            strm.adler = state.check =\n                /*UPDATE(state.check, put - _out, _out);*/\n                (state.flags ? crc32(state.check, output, _out, put - _out) : adler32(state.check, output, _out, put - _out));\n\n          }\n          _out = left;\n          // NB: crc32 stored as signed 32-bit int, zswap32 returns signed too\n          if ((state.flags ? hold : zswap32(hold)) !== state.check) {\n            strm.msg = 'incorrect data check';\n            state.mode = BAD$1;\n            break;\n          }\n          //=== INITBITS();\n          hold = 0;\n          bits = 0;\n          //===//\n          //Tracev((stderr, \"inflate:   check matches trailer\\n\"));\n        }\n        state.mode = LENGTH;\n        /* falls through */\n      case LENGTH:\n        if (state.wrap && state.flags) {\n          //=== NEEDBITS(32);\n          while (bits < 32) {\n            if (have === 0) { break inf_leave; }\n            have--;\n            hold += input[next++] << bits;\n            bits += 8;\n          }\n          //===//\n          if (hold !== (state.total & 0xffffffff)) {\n            strm.msg = 'incorrect length check';\n            state.mode = BAD$1;\n            break;\n          }\n          //=== INITBITS();\n          hold = 0;\n          bits = 0;\n          //===//\n          //Tracev((stderr, \"inflate:   length matches trailer\\n\"));\n        }\n        state.mode = DONE;\n        /* falls through */\n      case DONE:\n        ret = Z_STREAM_END$1;\n        break inf_leave;\n      case BAD$1:\n        ret = Z_DATA_ERROR$1;\n        break inf_leave;\n      case MEM:\n        return Z_MEM_ERROR;\n      case SYNC:\n        /* falls through */\n      default:\n        return Z_STREAM_ERROR$1;\n    }\n  }\n\n  // inf_leave <- here is real place for \"goto inf_leave\", emulated via \"break inf_leave\"\n\n  /*\n     Return from inflate(), updating the total counts and the check value.\n     If there was no progress during the inflate() call, return a buffer\n     error.  Call updatewindow() to create and/or update the window state.\n     Note: a memory error from inflate() is non-recoverable.\n   */\n\n  //--- RESTORE() ---\n  strm.next_out = put;\n  strm.avail_out = left;\n  strm.next_in = next;\n  strm.avail_in = have;\n  state.hold = hold;\n  state.bits = bits;\n  //---\n\n  if (state.wsize || (_out !== strm.avail_out && state.mode < BAD$1 &&\n                      (state.mode < CHECK || flush !== Z_FINISH$1))) {\n    if (updatewindow(strm, strm.output, strm.next_out, _out - strm.avail_out)) ;\n  }\n  _in -= strm.avail_in;\n  _out -= strm.avail_out;\n  strm.total_in += _in;\n  strm.total_out += _out;\n  state.total += _out;\n  if (state.wrap && _out) {\n    strm.adler = state.check = /*UPDATE(state.check, strm.next_out - _out, _out);*/\n      (state.flags ? crc32(state.check, output, _out, strm.next_out - _out) : adler32(state.check, output, _out, strm.next_out - _out));\n  }\n  strm.data_type = state.bits + (state.last ? 64 : 0) +\n                    (state.mode === TYPE$1 ? 128 : 0) +\n                    (state.mode === LEN_ || state.mode === COPY_ ? 256 : 0);\n  if (((_in === 0 && _out === 0) || flush === Z_FINISH$1) && ret === Z_OK$1) {\n    ret = Z_BUF_ERROR$1;\n  }\n  return ret;\n}\n\nfunction inflateEnd(strm) {\n\n  if (!strm || !strm.state /*|| strm->zfree == (free_func)0*/) {\n    return Z_STREAM_ERROR$1;\n  }\n\n  var state = strm.state;\n  if (state.window) {\n    state.window = null;\n  }\n  strm.state = null;\n  return Z_OK$1;\n}\n\nfunction inflateGetHeader(strm, head) {\n  var state;\n\n  /* check state */\n  if (!strm || !strm.state) { return Z_STREAM_ERROR$1; }\n  state = strm.state;\n  if ((state.wrap & 2) === 0) { return Z_STREAM_ERROR$1; }\n\n  /* save header structure */\n  state.head = head;\n  head.done = false;\n  return Z_OK$1;\n}\n\nfunction inflateSetDictionary(strm, dictionary) {\n  var dictLength = dictionary.length;\n\n  var state;\n  var dictid;\n  var ret;\n\n  /* check state */\n  if (!strm /* == Z_NULL */ || !strm.state /* == Z_NULL */) { return Z_STREAM_ERROR$1; }\n  state = strm.state;\n\n  if (state.wrap !== 0 && state.mode !== DICT) {\n    return Z_STREAM_ERROR$1;\n  }\n\n  /* check for correct dictionary identifier */\n  if (state.mode === DICT) {\n    dictid = 1; /* adler32(0, null, 0)*/\n    /* dictid = adler32(dictid, dictionary, dictLength); */\n    dictid = adler32(dictid, dictionary, dictLength, 0);\n    if (dictid !== state.check) {\n      return Z_DATA_ERROR$1;\n    }\n  }\n  /* copy dictionary to window using updatewindow(), which will amend the\n   existing dictionary if appropriate */\n  ret = updatewindow(strm, dictionary, dictLength, dictLength);\n  if (ret) {\n    state.mode = MEM;\n    return Z_MEM_ERROR;\n  }\n  state.havedict = 1;\n  // Tracev((stderr, \"inflate:   dictionary set\\n\"));\n  return Z_OK$1;\n}\n\n/* Not implemented\nexports.inflateCopy = inflateCopy;\nexports.inflateGetDictionary = inflateGetDictionary;\nexports.inflateMark = inflateMark;\nexports.inflatePrime = inflatePrime;\nexports.inflateSync = inflateSync;\nexports.inflateSyncPoint = inflateSyncPoint;\nexports.inflateUndermine = inflateUndermine;\n*/\n\n/* eslint-disable */\n\n// (C) 1995-2013 Jean-loup Gailly and Mark Adler\n// (C) 2014-2017 Vitaly Puzrin and Andrey Tupitsin\n//\n// This software is provided 'as-is', without any express or implied\n// warranty. In no event will the authors be held liable for any damages\n// arising from the use of this software.\n//\n// Permission is granted to anyone to use this software for any purpose,\n// including commercial applications, and to alter it and redistribute it\n// freely, subject to the following restrictions:\n//\n// 1. The origin of this software must not be misrepresented; you must not\n//   claim that you wrote the original software. If you use this software\n//   in a product, an acknowledgment in the product documentation would be\n//   appreciated but is not required.\n// 2. Altered source versions must be plainly marked as such, and must not be\n//   misrepresented as being the original software.\n// 3. This notice may not be removed or altered from any source distribution.\n\nvar msg = {\n  2:      'need dictionary',     /* Z_NEED_DICT       2  */\n  1:      'stream end',          /* Z_STREAM_END      1  */\n  0:      '',                    /* Z_OK              0  */\n  '-1':   'file error',          /* Z_ERRNO         (-1) */\n  '-2':   'stream error',        /* Z_STREAM_ERROR  (-2) */\n  '-3':   'data error',          /* Z_DATA_ERROR    (-3) */\n  '-4':   'insufficient memory', /* Z_MEM_ERROR     (-4) */\n  '-5':   'buffer error',        /* Z_BUF_ERROR     (-5) */\n  '-6':   'incompatible version' /* Z_VERSION_ERROR (-6) */\n};\n\n/* eslint-disable */\n\n// (C) 1995-2013 Jean-loup Gailly and Mark Adler\n// (C) 2014-2017 Vitaly Puzrin and Andrey Tupitsin\n//\n// This software is provided 'as-is', without any express or implied\n// warranty. In no event will the authors be held liable for any damages\n// arising from the use of this software.\n//\n// Permission is granted to anyone to use this software for any purpose,\n// including commercial applications, and to alter it and redistribute it\n// freely, subject to the following restrictions:\n//\n// 1. The origin of this software must not be misrepresented; you must not\n//   claim that you wrote the original software. If you use this software\n//   in a product, an acknowledgment in the product documentation would be\n//   appreciated but is not required.\n// 2. Altered source versions must be plainly marked as such, and must not be\n//   misrepresented as being the original software.\n// 3. This notice may not be removed or altered from any source distribution.\n\nfunction ZStream() {\n  /* next input byte */\n  this.input = null; // JS specific, because we have no pointers\n  this.next_in = 0;\n  /* number of bytes available at input */\n  this.avail_in = 0;\n  /* total number of input bytes read so far */\n  this.total_in = 0;\n  /* next output byte should be put there */\n  this.output = null; // JS specific, because we have no pointers\n  this.next_out = 0;\n  /* remaining free space at output */\n  this.avail_out = 0;\n  /* total number of bytes output so far */\n  this.total_out = 0;\n  /* last error message, NULL if no error */\n  this.msg = ''/*Z_NULL*/;\n  /* not visible by applications */\n  this.state = null;\n  /* best guess about the data type: binary or text */\n  this.data_type = 2/*Z_UNKNOWN*/;\n  /* adler32 value of the uncompressed data */\n  this.adler = 0;\n}\n\n/* eslint-disable */\n\n// (C) 1995-2013 Jean-loup Gailly and Mark Adler\n// (C) 2014-2017 Vitaly Puzrin and Andrey Tupitsin\n//\n// This software is provided 'as-is', without any express or implied\n// warranty. In no event will the authors be held liable for any damages\n// arising from the use of this software.\n//\n// Permission is granted to anyone to use this software for any purpose,\n// including commercial applications, and to alter it and redistribute it\n// freely, subject to the following restrictions:\n//\n// 1. The origin of this software must not be misrepresented; you must not\n//   claim that you wrote the original software. If you use this software\n//   in a product, an acknowledgment in the product documentation would be\n//   appreciated but is not required.\n// 2. Altered source versions must be plainly marked as such, and must not be\n//   misrepresented as being the original software.\n// 3. This notice may not be removed or altered from any source distribution.\n\nfunction GZheader() {\n  /* true if compressed data believed to be text */\n  this.text       = 0;\n  /* modification time */\n  this.time       = 0;\n  /* extra flags (not used when writing a gzip file) */\n  this.xflags     = 0;\n  /* operating system */\n  this.os         = 0;\n  /* pointer to extra field or Z_NULL if none */\n  this.extra      = null;\n  /* extra field length (valid if extra != Z_NULL) */\n  this.extra_len  = 0; // Actually, we don't need it in JS,\n                       // but leave for few code modifications\n\n  //\n  // Setup limits is not necessary because in js we should not preallocate memory\n  // for inflate use constant limit in 65536 bytes\n  //\n\n  /* space at extra (only when reading header) */\n  // this.extra_max  = 0;\n  /* pointer to zero-terminated file name or Z_NULL */\n  this.name       = '';\n  /* space at name (only when reading header) */\n  // this.name_max   = 0;\n  /* pointer to zero-terminated comment or Z_NULL */\n  this.comment    = '';\n  /* space at comment (only when reading header) */\n  // this.comm_max   = 0;\n  /* true if there was or will be a header crc */\n  this.hcrc       = 0;\n  /* true when done reading gzip header (not used when writing a gzip file) */\n  this.done       = false;\n}\n\n/* eslint-disable */\n\nvar toString = Object.prototype.toString;\n\n/**\n * class Inflate\n *\n * Generic JS-style wrapper for zlib calls. If you don't need\n * streaming behaviour - use more simple functions: [[inflate]]\n * and [[inflateRaw]].\n **/\n\n/* internal\n * inflate.chunks -> Array\n *\n * Chunks of output data, if [[Inflate#onData]] not overridden.\n **/\n\n/**\n * Inflate.result -> Uint8Array|Array|String\n *\n * Uncompressed result, generated by default [[Inflate#onData]]\n * and [[Inflate#onEnd]] handlers. Filled after you push last chunk\n * (call [[Inflate#push]] with `Z_FINISH` / `true` param) or if you\n * push a chunk with explicit flush (call [[Inflate#push]] with\n * `Z_SYNC_FLUSH` param).\n **/\n\n/**\n * Inflate.err -> Number\n *\n * Error code after inflate finished. 0 (Z_OK) on success.\n * Should be checked if broken data possible.\n **/\n\n/**\n * Inflate.msg -> String\n *\n * Error message, if [[Inflate.err]] != 0\n **/\n\n\n/**\n * new Inflate(options)\n * - options (Object): zlib inflate options.\n *\n * Creates new inflator instance with specified params. Throws exception\n * on bad params. Supported options:\n *\n * - `windowBits`\n * - `dictionary`\n *\n * [http://zlib.net/manual.html#Advanced](http://zlib.net/manual.html#Advanced)\n * for more information on these.\n *\n * Additional options, for internal needs:\n *\n * - `chunkSize` - size of generated data chunks (16K by default)\n * - `raw` (Boolean) - do raw inflate\n * - `to` (String) - if equal to 'string', then result will be converted\n *   from utf8 to utf16 (javascript) string. When string output requested,\n *   chunk length can differ from `chunkSize`, depending on content.\n *\n * By default, when no options set, autodetect deflate/gzip data format via\n * wrapper header.\n *\n * ##### Example:\n *\n * ```javascript\n * var pako = require('pako')\n *   , chunk1 = Uint8Array([1,2,3,4,5,6,7,8,9])\n *   , chunk2 = Uint8Array([10,11,12,13,14,15,16,17,18,19]);\n *\n * var inflate = new pako.Inflate({ level: 3});\n *\n * inflate.push(chunk1, false);\n * inflate.push(chunk2, true);  // true -> last chunk\n *\n * if (inflate.err) { throw new Error(inflate.err); }\n *\n * console.log(inflate.result);\n * ```\n **/\nvar Inflate = function Inflate(options) {\n  if (!(this instanceof Inflate)) { return new Inflate(options); }\n\n  this.options = assign({\n    chunkSize: 16384,\n    windowBits: 0,\n    to: ''\n  }, options || {});\n\n  var opt = this.options;\n\n  // Force window size for `raw` data, if not set directly,\n  // because we have no header for autodetect.\n  if (opt.raw && (opt.windowBits >= 0) && (opt.windowBits < 16)) {\n    opt.windowBits = -opt.windowBits;\n    if (opt.windowBits === 0) { opt.windowBits = -15; }\n  }\n\n  // If `windowBits` not defined (and mode not raw) - set autodetect flag for gzip/deflate\n  if ((opt.windowBits >= 0) && (opt.windowBits < 16) &&\n      !(options && options.windowBits)) {\n    opt.windowBits += 32;\n  }\n\n  // Gzip header has no info about windows size, we can do autodetect only\n  // for deflate. So, if window size not set, force it to max when gzip possible\n  if ((opt.windowBits > 15) && (opt.windowBits < 48)) {\n    // bit 3 (16) -> gzipped data\n    // bit 4 (32) -> autodetect gzip/deflate\n    if ((opt.windowBits & 15) === 0) {\n      opt.windowBits |= 15;\n    }\n  }\n\n  this.err  = 0;    // error code, if happens (0 = Z_OK)\n  this.msg  = '';   // error message\n  this.ended= false;// used to avoid multiple onEnd() calls\n  this.chunks = [];   // chunks of compressed data\n\n  this.strm = new ZStream();\n  this.strm.avail_out = 0;\n\n  var status= inflateInit2(\n    this.strm,\n    opt.windowBits\n  );\n\n  if (status !== Z_OK) {\n    throw new Error(msg[status]);\n  }\n\n  this.header = new GZheader();\n\n  inflateGetHeader(this.strm, this.header);\n\n  // Setup dictionary\n  if (opt.dictionary) {\n    // Convert data if needed\n    if (typeof opt.dictionary === 'string') {\n      opt.dictionary = string2buf(opt.dictionary);\n    } else if (toString.call(opt.dictionary) === '[object ArrayBuffer]') {\n      opt.dictionary = new Uint8Array(opt.dictionary);\n    }\n    if (opt.raw) { //In raw mode we need to set the dictionary early\n      status = inflateSetDictionary(this.strm, opt.dictionary);\n      if (status !== Z_OK) {\n        throw new Error(msg[status]);\n      }\n    }\n  }\n};\n\n/**\n * Inflate#push(data[, mode]) -> Boolean\n * - data (Uint8Array|Array|ArrayBuffer|String): input data\n * - mode (Number|Boolean): 0..6 for corresponding Z_NO_FLUSH..Z_TREE modes.\n * See constants. Skipped or `false` means Z_NO_FLUSH, `true` means Z_FINISH.\n *\n * Sends input data to inflate pipe, generating [[Inflate#onData]] calls with\n * new output chunks. Returns `true` on success. The last data block must have\n * mode Z_FINISH (or `true`). That will flush internal pending buffers and call\n * [[Inflate#onEnd]]. For interim explicit flushes (without ending the stream) you\n * can use mode Z_SYNC_FLUSH, keeping the decompression context.\n *\n * On fail call [[Inflate#onEnd]] with error code and return false.\n *\n * We strongly recommend to use `Uint8Array` on input for best speed (output\n * format is detected automatically). Also, don't skip last param and always\n * use the same type in your code (boolean or number). That will improve JS speed.\n *\n * For regular `Array`-s make sure all elements are [0..255].\n *\n * ##### Example\n *\n * ```javascript\n * push(chunk, false); // push one of data chunks\n * ...\n * push(chunk, true);// push last chunk\n * ```\n **/\nInflate.prototype.push = function push (data, mode) {\n  var strm = this.strm;\n  var chunkSize = this.options.chunkSize;\n  var dictionary = this.options.dictionary;\n  var status, _mode;\n  var next_out_utf8, tail, utf8str;\n  var dict;\n\n  // Flag to properly process Z_BUF_ERROR on testing inflate call\n  // when we check that all output data was flushed.\n  var allowBufError = false;\n\n  if (this.ended) { return false; }\n  _mode = (mode === ~~mode) ? mode : ((mode === true) ? Z_FINISH : Z_NO_FLUSH);\n\n  // Convert data if needed\n  if (typeof data === 'string') {\n    // Only binary strings can be decompressed on practice\n    strm.input = binstring2buf(data);\n  } else if (toString.call(data) === '[object ArrayBuffer]') {\n    strm.input = new Uint8Array(data);\n  } else {\n    strm.input = data;\n  }\n\n  strm.next_in = 0;\n  strm.avail_in = strm.input.length;\n\n  do {\n    if (strm.avail_out === 0) {\n      strm.output = Buf8(chunkSize);\n      strm.next_out = 0;\n      strm.avail_out = chunkSize;\n    }\n\n    status = inflate(strm, Z_NO_FLUSH);  /* no bad return value */\n\n    if (status === Z_NEED_DICT && dictionary) {\n      // Convert data if needed\n      if (typeof dictionary === 'string') {\n        dict = string2buf(dictionary);\n      } else if (toString.call(dictionary) === '[object ArrayBuffer]') {\n        dict = new Uint8Array(dictionary);\n      } else {\n        dict = dictionary;\n      }\n\n      status = inflateSetDictionary(this.strm, dict);\n\n    }\n\n    if (status === Z_BUF_ERROR && allowBufError === true) {\n      status = Z_OK;\n      allowBufError = false;\n    }\n\n    if (status !== Z_STREAM_END && status !== Z_OK) {\n      this.onEnd(status);\n      this.ended = true;\n      return false;\n    }\n\n    if (strm.next_out) {\n      if (strm.avail_out === 0 || status === Z_STREAM_END || (strm.avail_in === 0 && (_mode === Z_FINISH || _mode === Z_SYNC_FLUSH))) {\n\n        if (this.options.to === 'string') {\n\n          next_out_utf8 = utf8border(strm.output, strm.next_out);\n\n          tail = strm.next_out - next_out_utf8;\n          utf8str = buf2string(strm.output, next_out_utf8);\n\n          // move tail\n          strm.next_out = tail;\n          strm.avail_out = chunkSize - tail;\n          if (tail) { arraySet(strm.output, strm.output, next_out_utf8, tail, 0); }\n\n          this.onData(utf8str);\n\n        } else {\n          this.onData(shrinkBuf(strm.output, strm.next_out));\n        }\n      }\n    }\n\n    // When no more input data, we should check that internal inflate buffers\n    // are flushed. The only way to do it when avail_out = 0 - run one more\n    // inflate pass. But if output data not exists, inflate return Z_BUF_ERROR.\n    // Here we set flag to process this error properly.\n    //\n    // NOTE. Deflate does not return error in this case and does not needs such\n    // logic.\n    if (strm.avail_in === 0 && strm.avail_out === 0) {\n      allowBufError = true;\n    }\n\n  } while ((strm.avail_in > 0 || strm.avail_out === 0) && status !== Z_STREAM_END);\n\n  if (status === Z_STREAM_END) {\n    _mode = Z_FINISH;\n  }\n\n  // Finalize on the last chunk.\n  if (_mode === Z_FINISH) {\n    status = inflateEnd(this.strm);\n    this.onEnd(status);\n    this.ended = true;\n    return status === Z_OK;\n  }\n\n  // callback interim results if Z_SYNC_FLUSH.\n  if (_mode === Z_SYNC_FLUSH) {\n    this.onEnd(Z_OK);\n    strm.avail_out = 0;\n    return true;\n  }\n\n  return true;\n};\n\n\n/**\n * Inflate#onData(chunk) -> Void\n * - chunk (Uint8Array|Array|String): output data. Type of array depends\n * on js engine support. When string output requested, each chunk\n * will be string.\n *\n * By default, stores data blocks in `chunks[]` property and glue\n * those in `onEnd`. Override this handler, if you need another behaviour.\n **/\nInflate.prototype.onData = function onData (chunk) {\n  this.chunks.push(chunk);\n};\n\n\n/**\n * Inflate#onEnd(status) -> Void\n * - status (Number): inflate status. 0 (Z_OK) on success,\n * other if not.\n *\n * Called either after you tell inflate that the input stream is\n * complete (Z_FINISH) or should be flushed (Z_SYNC_FLUSH)\n * or if an error happened. By default - join collected chunks,\n * free memory and fill `results` / `err` properties.\n **/\nInflate.prototype.onEnd = function onEnd (status) {\n  // On success - join\n  if (status === Z_OK) {\n    if (this.options.to === 'string') {\n      // Glue & convert here, until we teach pako to send\n      // utf8 aligned strings to onData\n      this.result = this.chunks.join('');\n    } else {\n      this.result = flattenChunks(this.chunks);\n    }\n  }\n  this.chunks = [];\n  this.err = status;\n  this.msg = this.strm.msg;\n};\n\n/**\n * inflate(data[, options]) -> Uint8Array|Array|String\n * - data (Uint8Array|Array|String): input data to decompress.\n * - options (Object): zlib inflate options.\n *\n * Decompress `data` with inflate/ungzip and `options`. Autodetect\n * format via wrapper header by default. That's why we don't provide\n * separate `ungzip` method.\n *\n * Supported options are:\n *\n * - windowBits\n *\n * [http://zlib.net/manual.html#Advanced](http://zlib.net/manual.html#Advanced)\n * for more information.\n *\n * Sugar (options):\n *\n * - `raw` (Boolean) - say that we work with raw stream, if you don't wish to specify\n *   negative windowBits implicitly.\n * - `to` (String) - if equal to 'string', then result will be converted\n *   from utf8 to utf16 (javascript) string. When string output requested,\n *   chunk length can differ from `chunkSize`, depending on content.\n *\n *\n * ##### Example:\n *\n * ```javascript\n * var pako = require('pako')\n *   , input = pako.deflate([1,2,3,4,5,6,7,8,9])\n *   , output;\n *\n * try {\n *   output = pako.inflate(input);\n * } catch (err)\n *   console.log(err);\n * }\n * ```\n **/\nfunction inflate$1(input, options) {\n  var inflator = new Inflate(options);\n\n  inflator.push(input, true);\n\n  // That will never happens, if you don't cheat with options :)\n  if (inflator.err) { throw inflator.msg || msg[inflator.err]; }\n\n  return inflator.result;\n}\n\n\n/**\n * inflateRaw(data[, options]) -> Uint8Array|Array|String\n * - data (Uint8Array|Array|String): input data to decompress.\n * - options (Object): zlib inflate options.\n *\n * The same as [[inflate]], but creates raw data, without wrapper\n * (header and adler32 crc).\n **/\nfunction inflateRaw(input, options) {\n  options = options || {};\n  options.raw = true;\n  return inflate$1(input, options);\n}\n\n/**\n * ungzip(data[, options]) -> Uint8Array|Array|String\n * - data (Uint8Array|Array|String): input data to decompress.\n * - options (Object): zlib inflate options.\n *\n * Just shortcut to [[inflate]], because it autodetects format\n * by header.content. Done for convenience.\n **/\nvar ungzip = inflate$1;\n\n/* eslint-disable */\n\nfunction zero(buf) { var len = buf.length; while (--len >= 0) { buf[len] = 0; } }\n\n// From zutil.h\n\nvar STORED_BLOCK = 0;\nvar STATIC_TREES = 1;\nvar DYN_TREES    = 2;\n/* The three kinds of block type */\n\nvar MIN_MATCH    = 3;\nvar MAX_MATCH    = 258;\n/* The minimum and maximum match lengths */\n\n// From deflate.h\n/* ===========================================================================\n * Internal compression state.\n */\n\nvar LENGTH_CODES  = 29;\n/* number of length codes, not counting the special END_BLOCK code */\n\nvar LITERALS      = 256;\n/* number of literal bytes 0..255 */\n\nvar L_CODES       = LITERALS + 1 + LENGTH_CODES;\n/* number of Literal or Length codes, including the END_BLOCK code */\n\nvar D_CODES       = 30;\n/* number of distance codes */\n\nvar BL_CODES      = 19;\n/* number of codes used to transfer the bit lengths */\n\nvar HEAP_SIZE     = 2 * L_CODES + 1;\n/* maximum heap size */\n\nvar MAX_BITS      = 15;\n/* All codes must not exceed MAX_BITS bits */\n\nvar Buf_size      = 16;\n/* size of bit buffer in bi_buf */\n\n\n/* ===========================================================================\n * Constants\n */\n\nvar MAX_BL_BITS = 7;\n/* Bit length codes must not exceed MAX_BL_BITS bits */\n\nvar END_BLOCK   = 256;\n/* end of block literal code */\n\nvar REP_3_6     = 16;\n/* repeat previous bit length 3-6 times (2 bits of repeat count) */\n\nvar REPZ_3_10   = 17;\n/* repeat a zero length 3-10 times  (3 bits of repeat count) */\n\nvar REPZ_11_138 = 18;\n/* repeat a zero length 11-138 times  (7 bits of repeat count) */\n\n/* eslint-disable comma-spacing,array-bracket-spacing */\nvar extra_lbits =   /* extra bits for each length code */\n  [0,0,0,0,0,0,0,0,1,1,1,1,2,2,2,2,3,3,3,3,4,4,4,4,5,5,5,5,0];\n\nvar extra_dbits =   /* extra bits for each distance code */\n  [0,0,0,0,1,1,2,2,3,3,4,4,5,5,6,6,7,7,8,8,9,9,10,10,11,11,12,12,13,13];\n\nvar extra_blbits =  /* extra bits for each bit length code */\n  [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,2,3,7];\n\nvar bl_order =\n  [16,17,18,0,8,7,9,6,10,5,11,4,12,3,13,2,14,1,15];\n/* eslint-enable comma-spacing,array-bracket-spacing */\n\n/* The lengths of the bit length codes are sent in order of decreasing\n * probability, to avoid transmitting the lengths for unused bit length codes.\n */\n\n/* ===========================================================================\n * Local data. These are initialized only once.\n */\n\n// We pre-fill arrays with 0 to avoid uninitialized gaps\n\nvar DIST_CODE_LEN = 512; /* see definition of array dist_code below */\n\n// !!!! Use flat array instead of structure, Freq = i*2, Len = i*2+1\nvar static_ltree;\n/* The static literal tree. Since the bit lengths are imposed, there is no\n * need for the L_CODES extra codes used during heap construction. However\n * The codes 286 and 287 are needed to build a canonical tree (see _tr_init\n * below).\n */\n\nvar static_dtree;\n/* The static distance tree. (Actually a trivial tree since all codes use\n * 5 bits.)\n */\n\nvar _dist_code;\n/* Distance codes. The first 256 values correspond to the distances\n * 3 .. 258, the last 256 values correspond to the top 8 bits of\n * the 15 bit distances.\n */\n\nvar _length_code;\n/* length code for each normalized match length (0 == MIN_MATCH) */\n\nvar base_length;\n/* First normalized length for each code (0 = MIN_MATCH) */\n\nvar base_dist;\n/* First normalized distance for each code (0 = distance of 1) */\n\n\nfunction StaticTreeDesc(static_tree, extra_bits, extra_base, elems, max_length) {\n\n  this.static_tree  = static_tree;  /* static tree or NULL */\n  this.extra_bits   = extra_bits;   /* extra bits for each code or NULL */\n  this.extra_base   = extra_base;   /* base index for extra_bits */\n  this.elems        = elems;        /* max number of elements in the tree */\n  this.max_length   = max_length;   /* max bit length for the codes */\n\n  // show if `static_tree` has data or dummy - needed for monomorphic objects\n  this.has_stree    = static_tree && static_tree.length;\n}\n\n\nvar static_l_desc;\nvar static_d_desc;\nvar static_bl_desc;\n\n\nfunction TreeDesc(dyn_tree, stat_desc) {\n  this.dyn_tree = dyn_tree;     /* the dynamic tree */\n  this.max_code = 0;            /* largest code with non zero frequency */\n  this.stat_desc = stat_desc;   /* the corresponding static tree */\n}\n\n\n\nfunction d_code(dist) {\n  return dist < 256 ? _dist_code[dist] : _dist_code[256 + (dist >>> 7)];\n}\n\n\n/* ===========================================================================\n * Output a short LSB first on the stream.\n * IN assertion: there is enough room in pendingBuf.\n */\nfunction put_short(s, w) {\n//    put_byte(s, (uch)((w) & 0xff));\n//    put_byte(s, (uch)((ush)(w) >> 8));\n  s.pending_buf[s.pending++] = (w) & 0xff;\n  s.pending_buf[s.pending++] = (w >>> 8) & 0xff;\n}\n\n\n/* ===========================================================================\n * Send a value on a given number of bits.\n * IN assertion: length <= 16 and value fits in length bits.\n */\nfunction send_bits(s, value, length) {\n  if (s.bi_valid > (Buf_size - length)) {\n    s.bi_buf |= (value << s.bi_valid) & 0xffff;\n    put_short(s, s.bi_buf);\n    s.bi_buf = value >> (Buf_size - s.bi_valid);\n    s.bi_valid += length - Buf_size;\n  } else {\n    s.bi_buf |= (value << s.bi_valid) & 0xffff;\n    s.bi_valid += length;\n  }\n}\n\n\nfunction send_code(s, c, tree) {\n  send_bits(s, tree[c * 2]/*.Code*/, tree[c * 2 + 1]/*.Len*/);\n}\n\n\n/* ===========================================================================\n * Reverse the first len bits of a code, using straightforward code (a faster\n * method would use a table)\n * IN assertion: 1 <= len <= 15\n */\nfunction bi_reverse(code, len) {\n  var res = 0;\n  do {\n    res |= code & 1;\n    code >>>= 1;\n    res <<= 1;\n  } while (--len > 0);\n  return res >>> 1;\n}\n\n\n/* ===========================================================================\n * Flush the bit buffer, keeping at most 7 bits in it.\n */\nfunction bi_flush(s) {\n  if (s.bi_valid === 16) {\n    put_short(s, s.bi_buf);\n    s.bi_buf = 0;\n    s.bi_valid = 0;\n\n  } else if (s.bi_valid >= 8) {\n    s.pending_buf[s.pending++] = s.bi_buf & 0xff;\n    s.bi_buf >>= 8;\n    s.bi_valid -= 8;\n  }\n}\n\n\n/* ===========================================================================\n * Compute the optimal bit lengths for a tree and update the total bit length\n * for the current block.\n * IN assertion: the fields freq and dad are set, heap[heap_max] and\n *    above are the tree nodes sorted by increasing frequency.\n * OUT assertions: the field len is set to the optimal bit length, the\n *     array bl_count contains the frequencies for each bit length.\n *     The length opt_len is updated; static_len is also updated if stree is\n *     not null.\n */\nfunction gen_bitlen(s, desc)\n//    deflate_state *s;\n//    tree_desc *desc;    /* the tree descriptor */\n{\n  var tree            = desc.dyn_tree;\n  var max_code        = desc.max_code;\n  var stree           = desc.stat_desc.static_tree;\n  var has_stree       = desc.stat_desc.has_stree;\n  var extra           = desc.stat_desc.extra_bits;\n  var base            = desc.stat_desc.extra_base;\n  var max_length      = desc.stat_desc.max_length;\n  var h;              /* heap index */\n  var n, m;           /* iterate over the tree elements */\n  var bits;           /* bit length */\n  var xbits;          /* extra bits */\n  var f;              /* frequency */\n  var overflow = 0;   /* number of elements with bit length too large */\n\n  for (bits = 0; bits <= MAX_BITS; bits++) {\n    s.bl_count[bits] = 0;\n  }\n\n  /* In a first pass, compute the optimal bit lengths (which may\n   * overflow in the case of the bit length tree).\n   */\n  tree[s.heap[s.heap_max] * 2 + 1]/*.Len*/ = 0; /* root of the heap */\n\n  for (h = s.heap_max + 1; h < HEAP_SIZE; h++) {\n    n = s.heap[h];\n    bits = tree[tree[n * 2 + 1]/*.Dad*/ * 2 + 1]/*.Len*/ + 1;\n    if (bits > max_length) {\n      bits = max_length;\n      overflow++;\n    }\n    tree[n * 2 + 1]/*.Len*/ = bits;\n    /* We overwrite tree[n].Dad which is no longer needed */\n\n    if (n > max_code) { continue; } /* not a leaf node */\n\n    s.bl_count[bits]++;\n    xbits = 0;\n    if (n >= base) {\n      xbits = extra[n - base];\n    }\n    f = tree[n * 2]/*.Freq*/;\n    s.opt_len += f * (bits + xbits);\n    if (has_stree) {\n      s.static_len += f * (stree[n * 2 + 1]/*.Len*/ + xbits);\n    }\n  }\n  if (overflow === 0) { return; }\n\n  // Trace((stderr,\"\\nbit length overflow\\n\"));\n  /* This happens for example on obj2 and pic of the Calgary corpus */\n\n  /* Find the first bit length which could increase: */\n  do {\n    bits = max_length - 1;\n    while (s.bl_count[bits] === 0) { bits--; }\n    s.bl_count[bits]--;      /* move one leaf down the tree */\n    s.bl_count[bits + 1] += 2; /* move one overflow item as its brother */\n    s.bl_count[max_length]--;\n    /* The brother of the overflow item also moves one step up,\n     * but this does not affect bl_count[max_length]\n     */\n    overflow -= 2;\n  } while (overflow > 0);\n\n  /* Now recompute all bit lengths, scanning in increasing frequency.\n   * h is still equal to HEAP_SIZE. (It is simpler to reconstruct all\n   * lengths instead of fixing only the wrong ones. This idea is taken\n   * from 'ar' written by Haruhiko Okumura.)\n   */\n  for (bits = max_length; bits !== 0; bits--) {\n    n = s.bl_count[bits];\n    while (n !== 0) {\n      m = s.heap[--h];\n      if (m > max_code) { continue; }\n      if (tree[m * 2 + 1]/*.Len*/ !== bits) {\n        // Trace((stderr,\"code %d bits %d->%d\\n\", m, tree[m].Len, bits));\n        s.opt_len += (bits - tree[m * 2 + 1]/*.Len*/) * tree[m * 2]/*.Freq*/;\n        tree[m * 2 + 1]/*.Len*/ = bits;\n      }\n      n--;\n    }\n  }\n}\n\n\n/* ===========================================================================\n * Generate the codes for a given tree and bit counts (which need not be\n * optimal).\n * IN assertion: the array bl_count contains the bit length statistics for\n * the given tree and the field len is set for all tree elements.\n * OUT assertion: the field code is set for all tree elements of non\n *     zero code length.\n */\nfunction gen_codes(tree, max_code, bl_count)\n//    ct_data *tree;             /* the tree to decorate */\n//    int max_code;              /* largest code with non zero frequency */\n//    ushf *bl_count;            /* number of codes at each bit length */\n{\n  var next_code = new Array(MAX_BITS + 1); /* next code value for each bit length */\n  var code = 0;              /* running code value */\n  var bits;                  /* bit index */\n  var n;                     /* code index */\n\n  /* The distribution counts are first used to generate the code values\n   * without bit reversal.\n   */\n  for (bits = 1; bits <= MAX_BITS; bits++) {\n    next_code[bits] = code = (code + bl_count[bits - 1]) << 1;\n  }\n  /* Check that the bit counts in bl_count are consistent. The last code\n   * must be all ones.\n   */\n  //Assert (code + bl_count[MAX_BITS]-1 == (1<<MAX_BITS)-1,\n  //        \"inconsistent bit counts\");\n  //Tracev((stderr,\"\\ngen_codes: max_code %d \", max_code));\n\n  for (n = 0;  n <= max_code; n++) {\n    var len = tree[n * 2 + 1]/*.Len*/;\n    if (len === 0) { continue; }\n    /* Now reverse the bits */\n    tree[n * 2]/*.Code*/ = bi_reverse(next_code[len]++, len);\n\n    //Tracecv(tree != static_ltree, (stderr,\"\\nn %3d %c l %2d c %4x (%x) \",\n    //     n, (isgraph(n) ? n : ' '), len, tree[n].Code, next_code[len]-1));\n  }\n}\n\n\n/* ===========================================================================\n * Initialize the various 'constant' tables.\n */\nfunction tr_static_init() {\n  var n;        /* iterates over tree elements */\n  var bits;     /* bit counter */\n  var length;   /* length value */\n  var code;     /* code value */\n  var dist;     /* distance index */\n  var bl_count = new Array(MAX_BITS + 1);\n  /* number of codes at each bit length for an optimal tree */\n\n  static_ltree  = new Array((L_CODES + 2) * 2);\n  zero(static_ltree);\n\n  static_dtree  = new Array(D_CODES * 2);\n  zero(static_dtree);\n\n  _dist_code    = new Array(DIST_CODE_LEN);\n  zero(_dist_code);\n\n  _length_code  = new Array(MAX_MATCH - MIN_MATCH + 1);\n  zero(_length_code);\n\n  base_length   = new Array(LENGTH_CODES);\n  zero(base_length);\n\n  base_dist     = new Array(D_CODES);\n  zero(base_dist);\n\n  // do check in _tr_init()\n  //if (static_init_done) return;\n\n  /* For some embedded targets, global variables are not initialized: */\n/*#ifdef NO_INIT_GLOBAL_POINTERS\n  static_l_desc.static_tree = static_ltree;\n  static_l_desc.extra_bits = extra_lbits;\n  static_d_desc.static_tree = static_dtree;\n  static_d_desc.extra_bits = extra_dbits;\n  static_bl_desc.extra_bits = extra_blbits;\n#endif*/\n\n  /* Initialize the mapping length (0..255) -> length code (0..28) */\n  length = 0;\n  for (code = 0; code < LENGTH_CODES - 1; code++) {\n    base_length[code] = length;\n    for (n = 0; n < (1 << extra_lbits[code]); n++) {\n      _length_code[length++] = code;\n    }\n  }\n  //Assert (length == 256, \"tr_static_init: length != 256\");\n  /* Note that the length 255 (match length 258) can be represented\n   * in two different ways: code 284 + 5 bits or code 285, so we\n   * overwrite length_code[255] to use the best encoding:\n   */\n  _length_code[length - 1] = code;\n\n  /* Initialize the mapping dist (0..32K) -> dist code (0..29) */\n  dist = 0;\n  for (code = 0; code < 16; code++) {\n    base_dist[code] = dist;\n    for (n = 0; n < (1 << extra_dbits[code]); n++) {\n      _dist_code[dist++] = code;\n    }\n  }\n  //Assert (dist == 256, \"tr_static_init: dist != 256\");\n  dist >>= 7; /* from now on, all distances are divided by 128 */\n  for (; code < D_CODES; code++) {\n    base_dist[code] = dist << 7;\n    for (n = 0; n < (1 << (extra_dbits[code] - 7)); n++) {\n      _dist_code[256 + dist++] = code;\n    }\n  }\n  //Assert (dist == 256, \"tr_static_init: 256+dist != 512\");\n\n  /* Construct the codes of the static literal tree */\n  for (bits = 0; bits <= MAX_BITS; bits++) {\n    bl_count[bits] = 0;\n  }\n\n  n = 0;\n  while (n <= 143) {\n    static_ltree[n * 2 + 1]/*.Len*/ = 8;\n    n++;\n    bl_count[8]++;\n  }\n  while (n <= 255) {\n    static_ltree[n * 2 + 1]/*.Len*/ = 9;\n    n++;\n    bl_count[9]++;\n  }\n  while (n <= 279) {\n    static_ltree[n * 2 + 1]/*.Len*/ = 7;\n    n++;\n    bl_count[7]++;\n  }\n  while (n <= 287) {\n    static_ltree[n * 2 + 1]/*.Len*/ = 8;\n    n++;\n    bl_count[8]++;\n  }\n  /* Codes 286 and 287 do not exist, but we must include them in the\n   * tree construction to get a canonical Huffman tree (longest code\n   * all ones)\n   */\n  gen_codes(static_ltree, L_CODES + 1, bl_count);\n\n  /* The static distance tree is trivial: */\n  for (n = 0; n < D_CODES; n++) {\n    static_dtree[n * 2 + 1]/*.Len*/ = 5;\n    static_dtree[n * 2]/*.Code*/ = bi_reverse(n, 5);\n  }\n\n  // Now data ready and we can init static trees\n  static_l_desc = new StaticTreeDesc(static_ltree, extra_lbits, LITERALS + 1, L_CODES, MAX_BITS);\n  static_d_desc = new StaticTreeDesc(static_dtree, extra_dbits, 0,          D_CODES, MAX_BITS);\n  static_bl_desc = new StaticTreeDesc(new Array(0), extra_blbits, 0,         BL_CODES, MAX_BL_BITS);\n\n  //static_init_done = true;\n}\n\n\n/* ===========================================================================\n * Initialize a new block.\n */\nfunction init_block(s) {\n  var n; /* iterates over tree elements */\n\n  /* Initialize the trees. */\n  for (n = 0; n < L_CODES;  n++) { s.dyn_ltree[n * 2]/*.Freq*/ = 0; }\n  for (n = 0; n < D_CODES;  n++) { s.dyn_dtree[n * 2]/*.Freq*/ = 0; }\n  for (n = 0; n < BL_CODES; n++) { s.bl_tree[n * 2]/*.Freq*/ = 0; }\n\n  s.dyn_ltree[END_BLOCK * 2]/*.Freq*/ = 1;\n  s.opt_len = s.static_len = 0;\n  s.last_lit = s.matches = 0;\n}\n\n\n/* ===========================================================================\n * Flush the bit buffer and align the output on a byte boundary\n */\nfunction bi_windup(s)\n{\n  if (s.bi_valid > 8) {\n    put_short(s, s.bi_buf);\n  } else if (s.bi_valid > 0) {\n    //put_byte(s, (Byte)s->bi_buf);\n    s.pending_buf[s.pending++] = s.bi_buf;\n  }\n  s.bi_buf = 0;\n  s.bi_valid = 0;\n}\n\n/* ===========================================================================\n * Copy a stored block, storing first the length and its\n * one's complement if requested.\n */\nfunction copy_block(s, buf, len, header)\n//DeflateState *s;\n//charf    *buf;    /* the input data */\n//unsigned len;     /* its length */\n//int      header;  /* true if block header must be written */\n{\n  bi_windup(s);        /* align on byte boundary */\n\n  if (header) {\n    put_short(s, len);\n    put_short(s, ~len);\n  }\n//  while (len--) {\n//    put_byte(s, *buf++);\n//  }\n  arraySet(s.pending_buf, s.window, buf, len, s.pending);\n  s.pending += len;\n}\n\n/* ===========================================================================\n * Compares to subtrees, using the tree depth as tie breaker when\n * the subtrees have equal frequency. This minimizes the worst case length.\n */\nfunction smaller(tree, n, m, depth) {\n  var _n2 = n * 2;\n  var _m2 = m * 2;\n  return (tree[_n2]/*.Freq*/ < tree[_m2]/*.Freq*/ ||\n         (tree[_n2]/*.Freq*/ === tree[_m2]/*.Freq*/ && depth[n] <= depth[m]));\n}\n\n/* ===========================================================================\n * Restore the heap property by moving down the tree starting at node k,\n * exchanging a node with the smallest of its two sons if necessary, stopping\n * when the heap property is re-established (each father smaller than its\n * two sons).\n */\nfunction pqdownheap(s, tree, k)\n//    deflate_state *s;\n//    ct_data *tree;  /* the tree to restore */\n//    int k;               /* node to move down */\n{\n  var v = s.heap[k];\n  var j = k << 1;  /* left son of k */\n  while (j <= s.heap_len) {\n    /* Set j to the smallest of the two sons: */\n    if (j < s.heap_len &&\n      smaller(tree, s.heap[j + 1], s.heap[j], s.depth)) {\n      j++;\n    }\n    /* Exit if v is smaller than both sons */\n    if (smaller(tree, v, s.heap[j], s.depth)) { break; }\n\n    /* Exchange v with the smallest son */\n    s.heap[k] = s.heap[j];\n    k = j;\n\n    /* And continue down the tree, setting j to the left son of k */\n    j <<= 1;\n  }\n  s.heap[k] = v;\n}\n\n\n// inlined manually\n// var SMALLEST = 1;\n\n/* ===========================================================================\n * Send the block data compressed using the given Huffman trees\n */\nfunction compress_block(s, ltree, dtree)\n//    deflate_state *s;\n//    const ct_data *ltree; /* literal tree */\n//    const ct_data *dtree; /* distance tree */\n{\n  var dist;           /* distance of matched string */\n  var lc;             /* match length or unmatched char (if dist == 0) */\n  var lx = 0;         /* running index in l_buf */\n  var code;           /* the code to send */\n  var extra;          /* number of extra bits to send */\n\n  if (s.last_lit !== 0) {\n    do {\n      dist = (s.pending_buf[s.d_buf + lx * 2] << 8) | (s.pending_buf[s.d_buf + lx * 2 + 1]);\n      lc = s.pending_buf[s.l_buf + lx];\n      lx++;\n\n      if (dist === 0) {\n        send_code(s, lc, ltree); /* send a literal byte */\n        //Tracecv(isgraph(lc), (stderr,\" '%c' \", lc));\n      } else {\n        /* Here, lc is the match length - MIN_MATCH */\n        code = _length_code[lc];\n        send_code(s, code + LITERALS + 1, ltree); /* send the length code */\n        extra = extra_lbits[code];\n        if (extra !== 0) {\n          lc -= base_length[code];\n          send_bits(s, lc, extra);       /* send the extra length bits */\n        }\n        dist--; /* dist is now the match distance - 1 */\n        code = d_code(dist);\n        //Assert (code < D_CODES, \"bad d_code\");\n\n        send_code(s, code, dtree);       /* send the distance code */\n        extra = extra_dbits[code];\n        if (extra !== 0) {\n          dist -= base_dist[code];\n          send_bits(s, dist, extra);   /* send the extra distance bits */\n        }\n      } /* literal or match pair ? */\n\n      /* Check that the overlay between pending_buf and d_buf+l_buf is ok: */\n      //Assert((uInt)(s->pending) < s->lit_bufsize + 2*lx,\n      //       \"pendingBuf overflow\");\n\n    } while (lx < s.last_lit);\n  }\n\n  send_code(s, END_BLOCK, ltree);\n}\n\n\n/* ===========================================================================\n * Construct one Huffman tree and assigns the code bit strings and lengths.\n * Update the total bit length for the current block.\n * IN assertion: the field freq is set for all tree elements.\n * OUT assertions: the fields len and code are set to the optimal bit length\n *     and corresponding code. The length opt_len is updated; static_len is\n *     also updated if stree is not null. The field max_code is set.\n */\nfunction build_tree(s, desc)\n//    deflate_state *s;\n//    tree_desc *desc; /* the tree descriptor */\n{\n  var tree     = desc.dyn_tree;\n  var stree    = desc.stat_desc.static_tree;\n  var has_stree = desc.stat_desc.has_stree;\n  var elems    = desc.stat_desc.elems;\n  var n, m;          /* iterate over heap elements */\n  var max_code = -1; /* largest code with non zero frequency */\n  var node;          /* new node being created */\n\n  /* Construct the initial heap, with least frequent element in\n   * heap[SMALLEST]. The sons of heap[n] are heap[2*n] and heap[2*n+1].\n   * heap[0] is not used.\n   */\n  s.heap_len = 0;\n  s.heap_max = HEAP_SIZE;\n\n  for (n = 0; n < elems; n++) {\n    if (tree[n * 2]/*.Freq*/ !== 0) {\n      s.heap[++s.heap_len] = max_code = n;\n      s.depth[n] = 0;\n\n    } else {\n      tree[n * 2 + 1]/*.Len*/ = 0;\n    }\n  }\n\n  /* The pkzip format requires that at least one distance code exists,\n   * and that at least one bit should be sent even if there is only one\n   * possible code. So to avoid special checks later on we force at least\n   * two codes of non zero frequency.\n   */\n  while (s.heap_len < 2) {\n    node = s.heap[++s.heap_len] = (max_code < 2 ? ++max_code : 0);\n    tree[node * 2]/*.Freq*/ = 1;\n    s.depth[node] = 0;\n    s.opt_len--;\n\n    if (has_stree) {\n      s.static_len -= stree[node * 2 + 1]/*.Len*/;\n    }\n    /* node is 0 or 1 so it does not have extra bits */\n  }\n  desc.max_code = max_code;\n\n  /* The elements heap[heap_len/2+1 .. heap_len] are leaves of the tree,\n   * establish sub-heaps of increasing lengths:\n   */\n  for (n = (s.heap_len >> 1/*int /2*/); n >= 1; n--) { pqdownheap(s, tree, n); }\n\n  /* Construct the Huffman tree by repeatedly combining the least two\n   * frequent nodes.\n   */\n  node = elems;              /* next internal node of the tree */\n  do {\n    //pqremove(s, tree, n);  /* n = node of least frequency */\n    /*** pqremove ***/\n    n = s.heap[1/*SMALLEST*/];\n    s.heap[1/*SMALLEST*/] = s.heap[s.heap_len--];\n    pqdownheap(s, tree, 1/*SMALLEST*/);\n    /***/\n\n    m = s.heap[1/*SMALLEST*/]; /* m = node of next least frequency */\n\n    s.heap[--s.heap_max] = n; /* keep the nodes sorted by frequency */\n    s.heap[--s.heap_max] = m;\n\n    /* Create a new node father of n and m */\n    tree[node * 2]/*.Freq*/ = tree[n * 2]/*.Freq*/ + tree[m * 2]/*.Freq*/;\n    s.depth[node] = (s.depth[n] >= s.depth[m] ? s.depth[n] : s.depth[m]) + 1;\n    tree[n * 2 + 1]/*.Dad*/ = tree[m * 2 + 1]/*.Dad*/ = node;\n\n    /* and insert the new node in the heap */\n    s.heap[1/*SMALLEST*/] = node++;\n    pqdownheap(s, tree, 1/*SMALLEST*/);\n\n  } while (s.heap_len >= 2);\n\n  s.heap[--s.heap_max] = s.heap[1/*SMALLEST*/];\n\n  /* At this point, the fields freq and dad are set. We can now\n   * generate the bit lengths.\n   */\n  gen_bitlen(s, desc);\n\n  /* The field len is now set, we can generate the bit codes */\n  gen_codes(tree, max_code, s.bl_count);\n}\n\n\n/* ===========================================================================\n * Scan a literal or distance tree to determine the frequencies of the codes\n * in the bit length tree.\n */\nfunction scan_tree(s, tree, max_code)\n//    deflate_state *s;\n//    ct_data *tree;   /* the tree to be scanned */\n//    int max_code;    /* and its largest code of non zero frequency */\n{\n  var n;                     /* iterates over all tree elements */\n  var prevlen = -1;          /* last emitted length */\n  var curlen;                /* length of current code */\n\n  var nextlen = tree[0 * 2 + 1]/*.Len*/; /* length of next code */\n\n  var count = 0;             /* repeat count of the current code */\n  var max_count = 7;         /* max repeat count */\n  var min_count = 4;         /* min repeat count */\n\n  if (nextlen === 0) {\n    max_count = 138;\n    min_count = 3;\n  }\n  tree[(max_code + 1) * 2 + 1]/*.Len*/ = 0xffff; /* guard */\n\n  for (n = 0; n <= max_code; n++) {\n    curlen = nextlen;\n    nextlen = tree[(n + 1) * 2 + 1]/*.Len*/;\n\n    if (++count < max_count && curlen === nextlen) {\n      continue;\n\n    } else if (count < min_count) {\n      s.bl_tree[curlen * 2]/*.Freq*/ += count;\n\n    } else if (curlen !== 0) {\n\n      if (curlen !== prevlen) { s.bl_tree[curlen * 2]/*.Freq*/++; }\n      s.bl_tree[REP_3_6 * 2]/*.Freq*/++;\n\n    } else if (count <= 10) {\n      s.bl_tree[REPZ_3_10 * 2]/*.Freq*/++;\n\n    } else {\n      s.bl_tree[REPZ_11_138 * 2]/*.Freq*/++;\n    }\n\n    count = 0;\n    prevlen = curlen;\n\n    if (nextlen === 0) {\n      max_count = 138;\n      min_count = 3;\n\n    } else if (curlen === nextlen) {\n      max_count = 6;\n      min_count = 3;\n\n    } else {\n      max_count = 7;\n      min_count = 4;\n    }\n  }\n}\n\n\n/* ===========================================================================\n * Send a literal or distance tree in compressed form, using the codes in\n * bl_tree.\n */\nfunction send_tree(s, tree, max_code)\n//    deflate_state *s;\n//    ct_data *tree; /* the tree to be scanned */\n//    int max_code;       /* and its largest code of non zero frequency */\n{\n  var n;                     /* iterates over all tree elements */\n  var prevlen = -1;          /* last emitted length */\n  var curlen;                /* length of current code */\n\n  var nextlen = tree[0 * 2 + 1]/*.Len*/; /* length of next code */\n\n  var count = 0;             /* repeat count of the current code */\n  var max_count = 7;         /* max repeat count */\n  var min_count = 4;         /* min repeat count */\n\n  /* tree[max_code+1].Len = -1; */  /* guard already set */\n  if (nextlen === 0) {\n    max_count = 138;\n    min_count = 3;\n  }\n\n  for (n = 0; n <= max_code; n++) {\n    curlen = nextlen;\n    nextlen = tree[(n + 1) * 2 + 1]/*.Len*/;\n\n    if (++count < max_count && curlen === nextlen) {\n      continue;\n\n    } else if (count < min_count) {\n      do { send_code(s, curlen, s.bl_tree); } while (--count !== 0);\n\n    } else if (curlen !== 0) {\n      if (curlen !== prevlen) {\n        send_code(s, curlen, s.bl_tree);\n        count--;\n      }\n      //Assert(count >= 3 && count <= 6, \" 3_6?\");\n      send_code(s, REP_3_6, s.bl_tree);\n      send_bits(s, count - 3, 2);\n\n    } else if (count <= 10) {\n      send_code(s, REPZ_3_10, s.bl_tree);\n      send_bits(s, count - 3, 3);\n\n    } else {\n      send_code(s, REPZ_11_138, s.bl_tree);\n      send_bits(s, count - 11, 7);\n    }\n\n    count = 0;\n    prevlen = curlen;\n    if (nextlen === 0) {\n      max_count = 138;\n      min_count = 3;\n\n    } else if (curlen === nextlen) {\n      max_count = 6;\n      min_count = 3;\n\n    } else {\n      max_count = 7;\n      min_count = 4;\n    }\n  }\n}\n\n\n/* ===========================================================================\n * Construct the Huffman tree for the bit lengths and return the index in\n * bl_order of the last bit length code to send.\n */\nfunction build_bl_tree(s) {\n  var max_blindex;  /* index of last bit length code of non zero freq */\n\n  /* Determine the bit length frequencies for literal and distance trees */\n  scan_tree(s, s.dyn_ltree, s.l_desc.max_code);\n  scan_tree(s, s.dyn_dtree, s.d_desc.max_code);\n\n  /* Build the bit length tree: */\n  build_tree(s, s.bl_desc);\n  /* opt_len now includes the length of the tree representations, except\n   * the lengths of the bit lengths codes and the 5+5+4 bits for the counts.\n   */\n\n  /* Determine the number of bit length codes to send. The pkzip format\n   * requires that at least 4 bit length codes be sent. (appnote.txt says\n   * 3 but the actual value used is 4.)\n   */\n  for (max_blindex = BL_CODES - 1; max_blindex >= 3; max_blindex--) {\n    if (s.bl_tree[bl_order[max_blindex] * 2 + 1]/*.Len*/ !== 0) {\n      break;\n    }\n  }\n  /* Update opt_len to include the bit length tree and counts */\n  s.opt_len += 3 * (max_blindex + 1) + 5 + 5 + 4;\n  //Tracev((stderr, \"\\ndyn trees: dyn %ld, stat %ld\",\n  //        s->opt_len, s->static_len));\n\n  return max_blindex;\n}\n\n\n/* ===========================================================================\n * Send the header for a block using dynamic Huffman trees: the counts, the\n * lengths of the bit length codes, the literal tree and the distance tree.\n * IN assertion: lcodes >= 257, dcodes >= 1, blcodes >= 4.\n */\nfunction send_all_trees(s, lcodes, dcodes, blcodes)\n//    deflate_state *s;\n//    int lcodes, dcodes, blcodes; /* number of codes for each tree */\n{\n  var rank;                    /* index in bl_order */\n\n  //Assert (lcodes >= 257 && dcodes >= 1 && blcodes >= 4, \"not enough codes\");\n  //Assert (lcodes <= L_CODES && dcodes <= D_CODES && blcodes <= BL_CODES,\n  //        \"too many codes\");\n  //Tracev((stderr, \"\\nbl counts: \"));\n  send_bits(s, lcodes - 257, 5); /* not +255 as stated in appnote.txt */\n  send_bits(s, dcodes - 1,   5);\n  send_bits(s, blcodes - 4,  4); /* not -3 as stated in appnote.txt */\n  for (rank = 0; rank < blcodes; rank++) {\n    //Tracev((stderr, \"\\nbl code %2d \", bl_order[rank]));\n    send_bits(s, s.bl_tree[bl_order[rank] * 2 + 1]/*.Len*/, 3);\n  }\n  //Tracev((stderr, \"\\nbl tree: sent %ld\", s->bits_sent));\n\n  send_tree(s, s.dyn_ltree, lcodes - 1); /* literal tree */\n  //Tracev((stderr, \"\\nlit tree: sent %ld\", s->bits_sent));\n\n  send_tree(s, s.dyn_dtree, dcodes - 1); /* distance tree */\n  //Tracev((stderr, \"\\ndist tree: sent %ld\", s->bits_sent));\n}\n\n\n/* ===========================================================================\n * Check if the data type is TEXT or BINARY, using the following algorithm:\n * - TEXT if the two conditions below are satisfied:\n *    a) There are no non-portable control characters belonging to the\n *       \"black list\" (0..6, 14..25, 28..31).\n *    b) There is at least one printable character belonging to the\n *       \"white list\" (9 {TAB}, 10 {LF}, 13 {CR}, 32..255).\n * - BINARY otherwise.\n * - The following partially-portable control characters form a\n *   \"gray list\" that is ignored in this detection algorithm:\n *   (7 {BEL}, 8 {BS}, 11 {VT}, 12 {FF}, 26 {SUB}, 27 {ESC}).\n * IN assertion: the fields Freq of dyn_ltree are set.\n */\nfunction detect_data_type(s) {\n  /* black_mask is the bit mask of black-listed bytes\n   * set bits 0..6, 14..25, and 28..31\n   * 0xf3ffc07f = binary 11110011111111111100000001111111\n   */\n  var black_mask = 0xf3ffc07f;\n  var n;\n\n  /* Check for non-textual (\"black-listed\") bytes. */\n  for (n = 0; n <= 31; n++, black_mask >>>= 1) {\n    if ((black_mask & 1) && (s.dyn_ltree[n * 2]/*.Freq*/ !== 0)) {\n      return Z_BINARY;\n    }\n  }\n\n  /* Check for textual (\"white-listed\") bytes. */\n  if (s.dyn_ltree[9 * 2]/*.Freq*/ !== 0 || s.dyn_ltree[10 * 2]/*.Freq*/ !== 0 ||\n      s.dyn_ltree[13 * 2]/*.Freq*/ !== 0) {\n    return Z_TEXT;\n  }\n  for (n = 32; n < LITERALS; n++) {\n    if (s.dyn_ltree[n * 2]/*.Freq*/ !== 0) {\n      return Z_TEXT;\n    }\n  }\n\n  /* There are no \"black-listed\" or \"white-listed\" bytes:\n   * this stream either is empty or has tolerated (\"gray-listed\") bytes only.\n   */\n  return Z_BINARY;\n}\n\n\nvar static_init_done = false;\n\n/* ===========================================================================\n * Initialize the tree data structures for a new zlib stream.\n */\nfunction _tr_init(s) {\n\n  if (!static_init_done) {\n    tr_static_init();\n    static_init_done = true;\n  }\n\n  s.l_desc  = new TreeDesc(s.dyn_ltree, static_l_desc);\n  s.d_desc  = new TreeDesc(s.dyn_dtree, static_d_desc);\n  s.bl_desc = new TreeDesc(s.bl_tree, static_bl_desc);\n\n  s.bi_buf = 0;\n  s.bi_valid = 0;\n\n  /* Initialize the first block of the first file: */\n  init_block(s);\n}\n\n\n/* ===========================================================================\n * Send a stored block\n */\nfunction _tr_stored_block(s, buf, stored_len, last) {\n  //DeflateState *s;\n  //charf *buf;       /* input block */\n  //ulg stored_len;   /* length of input block */\n  //int last;         /* one if this is the last block for a file */\n  send_bits(s, (STORED_BLOCK << 1) + (last ? 1 : 0), 3);    /* send block type */\n  copy_block(s, buf, stored_len, true); /* with header */\n}\n\n\n/* ===========================================================================\n * Send one empty static block to give enough lookahead for inflate.\n * This takes 10 bits, of which 7 may remain in the bit buffer.\n */\nfunction _tr_align(s) {\n  send_bits(s, STATIC_TREES << 1, 3);\n  send_code(s, END_BLOCK, static_ltree);\n  bi_flush(s);\n}\n\n\n/* ===========================================================================\n * Determine the best encoding for the current block: dynamic trees, static\n * trees or store, and output the encoded block to the zip file.\n */\nfunction _tr_flush_block(s, buf, stored_len, last) {\n  //DeflateState *s;\n  //charf *buf;       /* input block, or NULL if too old */\n  //ulg stored_len;   /* length of input block */\n  //int last;         /* one if this is the last block for a file */\n  var opt_lenb, static_lenb;  /* opt_len and static_len in bytes */\n  var max_blindex = 0;        /* index of last bit length code of non zero freq */\n\n  /* Build the Huffman trees unless a stored block is forced */\n  if (s.level > 0) {\n\n    /* Check if the file is binary or text */\n    if (s.strm.data_type === Z_UNKNOWN) {\n      s.strm.data_type = detect_data_type(s);\n    }\n\n    /* Construct the literal and distance trees */\n    build_tree(s, s.l_desc);\n    // Tracev((stderr, \"\\nlit data: dyn %ld, stat %ld\", s->opt_len,\n    //        s->static_len));\n\n    build_tree(s, s.d_desc);\n    // Tracev((stderr, \"\\ndist data: dyn %ld, stat %ld\", s->opt_len,\n    //        s->static_len));\n    /* At this point, opt_len and static_len are the total bit lengths of\n     * the compressed block data, excluding the tree representations.\n     */\n\n    /* Build the bit length tree for the above two trees, and get the index\n     * in bl_order of the last bit length code to send.\n     */\n    max_blindex = build_bl_tree(s);\n\n    /* Determine the best encoding. Compute the block lengths in bytes. */\n    opt_lenb = (s.opt_len + 3 + 7) >>> 3;\n    static_lenb = (s.static_len + 3 + 7) >>> 3;\n\n    // Tracev((stderr, \"\\nopt %lu(%lu) stat %lu(%lu) stored %lu lit %u \",\n    //        opt_lenb, s->opt_len, static_lenb, s->static_len, stored_len,\n    //        s->last_lit));\n\n    if (static_lenb <= opt_lenb) { opt_lenb = static_lenb; }\n\n  } else {\n    // Assert(buf != (char*)0, \"lost buf\");\n    opt_lenb = static_lenb = stored_len + 5; /* force a stored block */\n  }\n\n  if ((stored_len + 4 <= opt_lenb) && (buf !== -1)) {\n    /* 4: two words for the lengths */\n\n    /* The test buf != NULL is only necessary if LIT_BUFSIZE > WSIZE.\n     * Otherwise we can't have processed more than WSIZE input bytes since\n     * the last block flush, because compression would have been\n     * successful. If LIT_BUFSIZE <= WSIZE, it is never too late to\n     * transform a block into a stored block.\n     */\n    _tr_stored_block(s, buf, stored_len, last);\n\n  } else if (s.strategy === Z_FIXED || static_lenb === opt_lenb) {\n\n    send_bits(s, (STATIC_TREES << 1) + (last ? 1 : 0), 3);\n    compress_block(s, static_ltree, static_dtree);\n\n  } else {\n    send_bits(s, (DYN_TREES << 1) + (last ? 1 : 0), 3);\n    send_all_trees(s, s.l_desc.max_code + 1, s.d_desc.max_code + 1, max_blindex + 1);\n    compress_block(s, s.dyn_ltree, s.dyn_dtree);\n  }\n  // Assert (s->compressed_len == s->bits_sent, \"bad compressed size\");\n  /* The above check is made mod 2^32, for files larger than 512 MB\n   * and uLong implemented on 32 bits.\n   */\n  init_block(s);\n\n  if (last) {\n    bi_windup(s);\n  }\n  // Tracev((stderr,\"\\ncomprlen %lu(%lu) \", s->compressed_len>>3,\n  //       s->compressed_len-7*last));\n}\n\n/* ===========================================================================\n * Save the match info and tally the frequency counts. Return true if\n * the current block must be flushed.\n */\nfunction _tr_tally(s, dist, lc) {\n  //    deflate_state *s;\n  //    unsigned dist;  /* distance of matched string */\n  //    unsigned lc;    /* match length-MIN_MATCH or unmatched char (if dist==0) */\n  //var out_length, in_length, dcode;\n\n  s.pending_buf[s.d_buf + s.last_lit * 2]     = (dist >>> 8) & 0xff;\n  s.pending_buf[s.d_buf + s.last_lit * 2 + 1] = dist & 0xff;\n\n  s.pending_buf[s.l_buf + s.last_lit] = lc & 0xff;\n  s.last_lit++;\n\n  if (dist === 0) {\n    /* lc is the unmatched char */\n    s.dyn_ltree[lc * 2]/*.Freq*/++;\n  } else {\n    s.matches++;\n    /* Here, lc is the match length - MIN_MATCH */\n    dist--;             /* dist = match distance - 1 */\n    //Assert((ush)dist < (ush)MAX_DIST(s) &&\n    //       (ush)lc <= (ush)(MAX_MATCH-MIN_MATCH) &&\n    //       (ush)d_code(dist) < (ush)D_CODES,  \"_tr_tally: bad match\");\n\n    s.dyn_ltree[(_length_code[lc] + LITERALS + 1) * 2]/*.Freq*/++;\n    s.dyn_dtree[d_code(dist) * 2]/*.Freq*/++;\n  }\n\n// (!) This block is disabled in zlib defaults,\n// don't enable it for binary compatibility\n\n//#ifdef TRUNCATE_BLOCK\n//  /* Try to guess if it is profitable to stop the current block here */\n//  if ((s.last_lit & 0x1fff) === 0 && s.level > 2) {\n//    /* Compute an upper bound for the compressed length */\n//    out_length = s.last_lit*8;\n//    in_length = s.strstart - s.block_start;\n//\n//    for (dcode = 0; dcode < D_CODES; dcode++) {\n//      out_length += s.dyn_dtree[dcode*2]/*.Freq*/ * (5 + extra_dbits[dcode]);\n//    }\n//    out_length >>>= 3;\n//    //Tracev((stderr,\"\\nlast_lit %u, in %ld, out ~%ld(%ld%%) \",\n//    //       s->last_lit, in_length, out_length,\n//    //       100L - out_length*100L/in_length));\n//    if (s.matches < (s.last_lit>>1)/*int /2*/ && out_length < (in_length>>1)/*int /2*/) {\n//      return true;\n//    }\n//  }\n//#endif\n\n  return (s.last_lit === s.lit_bufsize - 1);\n  /* We avoid equality with lit_bufsize because of wraparound at 64K\n   * on 16 bit machines and because stored blocks are restricted to\n   * 64K-1 bytes.\n   */\n}\n\n/* eslint-disable */\n\nvar MAX_MEM_LEVEL = 9;\n\n\nvar LENGTH_CODES$1  = 29;\n/* number of length codes, not counting the special END_BLOCK code */\nvar LITERALS$1      = 256;\n/* number of literal bytes 0..255 */\nvar L_CODES$1       = LITERALS$1 + 1 + LENGTH_CODES$1;\n/* number of Literal or Length codes, including the END_BLOCK code */\nvar D_CODES$1       = 30;\n/* number of distance codes */\nvar BL_CODES$1      = 19;\n/* number of codes used to transfer the bit lengths */\nvar HEAP_SIZE$1     = 2 * L_CODES$1 + 1;\n/* maximum heap size */\nvar MAX_BITS$1  = 15;\n/* All codes must not exceed MAX_BITS bits */\n\nvar MIN_MATCH$1 = 3;\nvar MAX_MATCH$1 = 258;\nvar MIN_LOOKAHEAD = (MAX_MATCH$1 + MIN_MATCH$1 + 1);\n\nvar PRESET_DICT = 0x20;\n\nvar INIT_STATE = 42;\nvar EXTRA_STATE = 69;\nvar NAME_STATE = 73;\nvar COMMENT_STATE = 91;\nvar HCRC_STATE = 103;\nvar BUSY_STATE = 113;\nvar FINISH_STATE = 666;\n\nvar BS_NEED_MORE      = 1; /* block not completed, need more input or more output */\nvar BS_BLOCK_DONE     = 2; /* block flush performed */\nvar BS_FINISH_STARTED = 3; /* finish started, need only more output at next deflate */\nvar BS_FINISH_DONE    = 4; /* finish done, accept no more input or output */\n\nvar OS_CODE = 0x03; // Unix :) . Don't detect, use this default.\n\nfunction err(strm, errorCode) {\n  strm.msg = msg[errorCode];\n  return errorCode;\n}\n\nfunction rank(f) {\n  return ((f) << 1) - ((f) > 4 ? 9 : 0);\n}\n\nfunction zero$1(buf) { var len = buf.length; while (--len >= 0) { buf[len] = 0; } }\n\n\n/* =========================================================================\n * Flush as much pending output as possible. All deflate() output goes\n * through this function so some applications may wish to modify it\n * to avoid allocating a large strm->output buffer and copying into it.\n * (See also read_buf()).\n */\nfunction flush_pending(strm) {\n  var s = strm.state;\n\n  //_tr_flush_bits(s);\n  var len = s.pending;\n  if (len > strm.avail_out) {\n    len = strm.avail_out;\n  }\n  if (len === 0) { return; }\n\n  arraySet(strm.output, s.pending_buf, s.pending_out, len, strm.next_out);\n  strm.next_out += len;\n  s.pending_out += len;\n  strm.total_out += len;\n  strm.avail_out -= len;\n  s.pending -= len;\n  if (s.pending === 0) {\n    s.pending_out = 0;\n  }\n}\n\n\nfunction flush_block_only(s, last) {\n  _tr_flush_block(s, (s.block_start >= 0 ? s.block_start : -1), s.strstart - s.block_start, last);\n  s.block_start = s.strstart;\n  flush_pending(s.strm);\n}\n\n\nfunction put_byte(s, b) {\n  s.pending_buf[s.pending++] = b;\n}\n\n\n/* =========================================================================\n * Put a short in the pending buffer. The 16-bit value is put in MSB order.\n * IN assertion: the stream state is correct and there is enough room in\n * pending_buf.\n */\nfunction putShortMSB(s, b) {\n//  put_byte(s, (Byte)(b >> 8));\n//  put_byte(s, (Byte)(b & 0xff));\n  s.pending_buf[s.pending++] = (b >>> 8) & 0xff;\n  s.pending_buf[s.pending++] = b & 0xff;\n}\n\n\n/* ===========================================================================\n * Read a new buffer from the current input stream, update the adler32\n * and total number of bytes read.  All deflate() input goes through\n * this function so some applications may wish to modify it to avoid\n * allocating a large strm->input buffer and copying from it.\n * (See also flush_pending()).\n */\nfunction read_buf(strm, buf, start, size) {\n  var len = strm.avail_in;\n\n  if (len > size) { len = size; }\n  if (len === 0) { return 0; }\n\n  strm.avail_in -= len;\n\n  // zmemcpy(buf, strm->next_in, len);\n  arraySet(buf, strm.input, strm.next_in, len, start);\n  if (strm.state.wrap === 1) {\n    strm.adler = adler32(strm.adler, buf, len, start);\n  }\n\n  else if (strm.state.wrap === 2) {\n    strm.adler = crc32(strm.adler, buf, len, start);\n  }\n\n  strm.next_in += len;\n  strm.total_in += len;\n\n  return len;\n}\n\n\n/* ===========================================================================\n * Set match_start to the longest match starting at the given string and\n * return its length. Matches shorter or equal to prev_length are discarded,\n * in which case the result is equal to prev_length and match_start is\n * garbage.\n * IN assertions: cur_match is the head of the hash chain for the current\n *   string (strstart) and its distance is <= MAX_DIST, and prev_length >= 1\n * OUT assertion: the match length is not greater than s->lookahead.\n */\nfunction longest_match(s, cur_match) {\n  var chain_length = s.max_chain_length;      /* max hash chain length */\n  var scan = s.strstart; /* current string */\n  var match;                       /* matched string */\n  var len;                           /* length of current match */\n  var best_len = s.prev_length;              /* best match length so far */\n  var nice_match = s.nice_match;             /* stop if match long enough */\n  var limit = (s.strstart > (s.w_size - MIN_LOOKAHEAD)) ?\n      s.strstart - (s.w_size - MIN_LOOKAHEAD) : 0/*NIL*/;\n\n  var _win = s.window; // shortcut\n\n  var wmask = s.w_mask;\n  var prev  = s.prev;\n\n  /* Stop when cur_match becomes <= limit. To simplify the code,\n   * we prevent matches with the string of window index 0.\n   */\n\n  var strend = s.strstart + MAX_MATCH$1;\n  var scan_end1  = _win[scan + best_len - 1];\n  var scan_end   = _win[scan + best_len];\n\n  /* The code is optimized for HASH_BITS >= 8 and MAX_MATCH-2 multiple of 16.\n   * It is easy to get rid of this optimization if necessary.\n   */\n  // Assert(s->hash_bits >= 8 && MAX_MATCH == 258, \"Code too clever\");\n\n  /* Do not waste too much time if we already have a good match: */\n  if (s.prev_length >= s.good_match) {\n    chain_length >>= 2;\n  }\n  /* Do not look for matches beyond the end of the input. This is necessary\n   * to make deflate deterministic.\n   */\n  if (nice_match > s.lookahead) { nice_match = s.lookahead; }\n\n  // Assert((ulg)s->strstart <= s->window_size-MIN_LOOKAHEAD, \"need lookahead\");\n\n  do {\n    // Assert(cur_match < s->strstart, \"no future\");\n    match = cur_match;\n\n    /* Skip to next match if the match length cannot increase\n     * or if the match length is less than 2.  Note that the checks below\n     * for insufficient lookahead only occur occasionally for performance\n     * reasons.  Therefore uninitialized memory will be accessed, and\n     * conditional jumps will be made that depend on those values.\n     * However the length of the match is limited to the lookahead, so\n     * the output of deflate is not affected by the uninitialized values.\n     */\n\n    if (_win[match + best_len]     !== scan_end  ||\n        _win[match + best_len - 1] !== scan_end1 ||\n        _win[match]                !== _win[scan] ||\n        _win[++match]              !== _win[scan + 1]) {\n      continue;\n    }\n\n    /* The check at best_len-1 can be removed because it will be made\n     * again later. (This heuristic is not always a win.)\n     * It is not necessary to compare scan[2] and match[2] since they\n     * are always equal when the other bytes match, given that\n     * the hash keys are equal and that HASH_BITS >= 8.\n     */\n    scan += 2;\n    match++;\n    // Assert(*scan == *match, \"match[2]?\");\n\n    /* We check for insufficient lookahead only every 8th comparison;\n     * the 256th check will be made at strstart+258.\n     */\n    do {\n      /*jshint noempty:false*/\n    } while (_win[++scan] === _win[++match] && _win[++scan] === _win[++match] &&\n             _win[++scan] === _win[++match] && _win[++scan] === _win[++match] &&\n             _win[++scan] === _win[++match] && _win[++scan] === _win[++match] &&\n             _win[++scan] === _win[++match] && _win[++scan] === _win[++match] &&\n             scan < strend);\n\n    // Assert(scan <= s->window+(unsigned)(s->window_size-1), \"wild scan\");\n\n    len = MAX_MATCH$1 - (strend - scan);\n    scan = strend - MAX_MATCH$1;\n\n    if (len > best_len) {\n      s.match_start = cur_match;\n      best_len = len;\n      if (len >= nice_match) {\n        break;\n      }\n      scan_end1  = _win[scan + best_len - 1];\n      scan_end   = _win[scan + best_len];\n    }\n  } while ((cur_match = prev[cur_match & wmask]) > limit && --chain_length !== 0);\n\n  if (best_len <= s.lookahead) {\n    return best_len;\n  }\n  return s.lookahead;\n}\n\n\n/* ===========================================================================\n * Fill the window when the lookahead becomes insufficient.\n * Updates strstart and lookahead.\n *\n * IN assertion: lookahead < MIN_LOOKAHEAD\n * OUT assertions: strstart <= window_size-MIN_LOOKAHEAD\n *    At least one byte has been read, or avail_in == 0; reads are\n *    performed for at least two bytes (required for the zip translate_eol\n *    option -- not supported here).\n */\nfunction fill_window(s) {\n  var _w_size = s.w_size;\n  var p, n, m, more, str;\n\n  //Assert(s->lookahead < MIN_LOOKAHEAD, \"already enough lookahead\");\n\n  do {\n    more = s.window_size - s.lookahead - s.strstart;\n\n    // JS ints have 32 bit, block below not needed\n    /* Deal with !@#$% 64K limit: */\n    //if (sizeof(int) <= 2) {\n    //    if (more == 0 && s->strstart == 0 && s->lookahead == 0) {\n    //        more = wsize;\n    //\n    //  } else if (more == (unsigned)(-1)) {\n    //        /* Very unlikely, but possible on 16 bit machine if\n    //         * strstart == 0 && lookahead == 1 (input done a byte at time)\n    //         */\n    //        more--;\n    //    }\n    //}\n\n\n    /* If the window is almost full and there is insufficient lookahead,\n     * move the upper half to the lower one to make room in the upper half.\n     */\n    if (s.strstart >= _w_size + (_w_size - MIN_LOOKAHEAD)) {\n\n      arraySet(s.window, s.window, _w_size, _w_size, 0);\n      s.match_start -= _w_size;\n      s.strstart -= _w_size;\n      /* we now have strstart >= MAX_DIST */\n      s.block_start -= _w_size;\n\n      /* Slide the hash table (could be avoided with 32 bit values\n       at the expense of memory usage). We slide even when level == 0\n       to keep the hash table consistent if we switch back to level > 0\n       later. (Using level 0 permanently is not an optimal usage of\n       zlib, so we don't care about this pathological case.)\n       */\n\n      n = s.hash_size;\n      p = n;\n      do {\n        m = s.head[--p];\n        s.head[p] = (m >= _w_size ? m - _w_size : 0);\n      } while (--n);\n\n      n = _w_size;\n      p = n;\n      do {\n        m = s.prev[--p];\n        s.prev[p] = (m >= _w_size ? m - _w_size : 0);\n        /* If n is not on any hash chain, prev[n] is garbage but\n         * its value will never be used.\n         */\n      } while (--n);\n\n      more += _w_size;\n    }\n    if (s.strm.avail_in === 0) {\n      break;\n    }\n\n    /* If there was no sliding:\n     *    strstart <= WSIZE+MAX_DIST-1 && lookahead <= MIN_LOOKAHEAD - 1 &&\n     *    more == window_size - lookahead - strstart\n     * => more >= window_size - (MIN_LOOKAHEAD-1 + WSIZE + MAX_DIST-1)\n     * => more >= window_size - 2*WSIZE + 2\n     * In the BIG_MEM or MMAP case (not yet supported),\n     *   window_size == input_size + MIN_LOOKAHEAD  &&\n     *   strstart + s->lookahead <= input_size => more >= MIN_LOOKAHEAD.\n     * Otherwise, window_size == 2*WSIZE so more >= 2.\n     * If there was sliding, more >= WSIZE. So in all cases, more >= 2.\n     */\n    //Assert(more >= 2, \"more < 2\");\n    n = read_buf(s.strm, s.window, s.strstart + s.lookahead, more);\n    s.lookahead += n;\n\n    /* Initialize the hash value now that we have some input: */\n    if (s.lookahead + s.insert >= MIN_MATCH$1) {\n      str = s.strstart - s.insert;\n      s.ins_h = s.window[str];\n\n      /* UPDATE_HASH(s, s->ins_h, s->window[str + 1]); */\n      s.ins_h = ((s.ins_h << s.hash_shift) ^ s.window[str + 1]) & s.hash_mask;\n//#if MIN_MATCH != 3\n//        Call update_hash() MIN_MATCH-3 more times\n//#endif\n      while (s.insert) {\n        /* UPDATE_HASH(s, s->ins_h, s->window[str + MIN_MATCH-1]); */\n        s.ins_h = ((s.ins_h << s.hash_shift) ^ s.window[str + MIN_MATCH$1 - 1]) & s.hash_mask;\n\n        s.prev[str & s.w_mask] = s.head[s.ins_h];\n        s.head[s.ins_h] = str;\n        str++;\n        s.insert--;\n        if (s.lookahead + s.insert < MIN_MATCH$1) {\n          break;\n        }\n      }\n    }\n    /* If the whole input has less than MIN_MATCH bytes, ins_h is garbage,\n     * but this is not important since only literal bytes will be emitted.\n     */\n\n  } while (s.lookahead < MIN_LOOKAHEAD && s.strm.avail_in !== 0);\n\n  /* If the WIN_INIT bytes after the end of the current data have never been\n   * written, then zero those bytes in order to avoid memory check reports of\n   * the use of uninitialized (or uninitialised as Julian writes) bytes by\n   * the longest match routines.  Update the high water mark for the next\n   * time through here.  WIN_INIT is set to MAX_MATCH since the longest match\n   * routines allow scanning to strstart + MAX_MATCH, ignoring lookahead.\n   */\n//  if (s.high_water < s.window_size) {\n//    var curr = s.strstart + s.lookahead;\n//    var init = 0;\n//\n//    if (s.high_water < curr) {\n//      /* Previous high water mark below current data -- zero WIN_INIT\n//       * bytes or up to end of window, whichever is less.\n//       */\n//      init = s.window_size - curr;\n//      if (init > WIN_INIT)\n//        init = WIN_INIT;\n//      zmemzero(s->window + curr, (unsigned)init);\n//      s->high_water = curr + init;\n//    }\n//    else if (s->high_water < (ulg)curr + WIN_INIT) {\n//      /* High water mark at or above current data, but below current data\n//       * plus WIN_INIT -- zero out to current data plus WIN_INIT, or up\n//       * to end of window, whichever is less.\n//       */\n//      init = (ulg)curr + WIN_INIT - s->high_water;\n//      if (init > s->window_size - s->high_water)\n//        init = s->window_size - s->high_water;\n//      zmemzero(s->window + s->high_water, (unsigned)init);\n//      s->high_water += init;\n//    }\n//  }\n//\n//  Assert((ulg)s->strstart <= s->window_size - MIN_LOOKAHEAD,\n//    \"not enough room for search\");\n}\n\n/* ===========================================================================\n * Copy without compression as much as possible from the input stream, return\n * the current block state.\n * This function does not insert new strings in the dictionary since\n * uncompressible data is probably not useful. This function is used\n * only for the level=0 compression option.\n * NOTE: this function should be optimized to avoid extra copying from\n * window to pending_buf.\n */\nfunction deflate_stored(s, flush) {\n  /* Stored blocks are limited to 0xffff bytes, pending_buf is limited\n   * to pending_buf_size, and each stored block has a 5 byte header:\n   */\n  var max_block_size = 0xffff;\n\n  if (max_block_size > s.pending_buf_size - 5) {\n    max_block_size = s.pending_buf_size - 5;\n  }\n\n  /* Copy as much as possible from input to output: */\n  for (;;) {\n    /* Fill the window as much as possible: */\n    if (s.lookahead <= 1) {\n\n      //Assert(s->strstart < s->w_size+MAX_DIST(s) ||\n      //  s->block_start >= (long)s->w_size, \"slide too late\");\n//      if (!(s.strstart < s.w_size + (s.w_size - MIN_LOOKAHEAD) ||\n//        s.block_start >= s.w_size)) {\n//        throw  new Error(\"slide too late\");\n//      }\n\n      fill_window(s);\n      if (s.lookahead === 0 && flush === Z_NO_FLUSH) {\n        return BS_NEED_MORE;\n      }\n\n      if (s.lookahead === 0) {\n        break;\n      }\n      /* flush the current block */\n    }\n    //Assert(s->block_start >= 0L, \"block gone\");\n//    if (s.block_start < 0) throw new Error(\"block gone\");\n\n    s.strstart += s.lookahead;\n    s.lookahead = 0;\n\n    /* Emit a stored block if pending_buf will be full: */\n    var max_start = s.block_start + max_block_size;\n\n    if (s.strstart === 0 || s.strstart >= max_start) {\n      /* strstart == 0 is possible when wraparound on 16-bit machine */\n      s.lookahead = s.strstart - max_start;\n      s.strstart = max_start;\n      /*** FLUSH_BLOCK(s, 0); ***/\n      flush_block_only(s, false);\n      if (s.strm.avail_out === 0) {\n        return BS_NEED_MORE;\n      }\n      /***/\n\n\n    }\n    /* Flush if we may have to slide, otherwise block_start may become\n     * negative and the data will be gone:\n     */\n    if (s.strstart - s.block_start >= (s.w_size - MIN_LOOKAHEAD)) {\n      /*** FLUSH_BLOCK(s, 0); ***/\n      flush_block_only(s, false);\n      if (s.strm.avail_out === 0) {\n        return BS_NEED_MORE;\n      }\n      /***/\n    }\n  }\n\n  s.insert = 0;\n\n  if (flush === Z_FINISH) {\n    /*** FLUSH_BLOCK(s, 1); ***/\n    flush_block_only(s, true);\n    if (s.strm.avail_out === 0) {\n      return BS_FINISH_STARTED;\n    }\n    /***/\n    return BS_FINISH_DONE;\n  }\n\n  if (s.strstart > s.block_start) {\n    /*** FLUSH_BLOCK(s, 0); ***/\n    flush_block_only(s, false);\n    if (s.strm.avail_out === 0) {\n      return BS_NEED_MORE;\n    }\n    /***/\n  }\n\n  return BS_NEED_MORE;\n}\n\n/* ===========================================================================\n * Compress as much as possible from the input stream, return the current\n * block state.\n * This function does not perform lazy evaluation of matches and inserts\n * new strings in the dictionary only for unmatched strings or for short\n * matches. It is used only for the fast compression options.\n */\nfunction deflate_fast(s, flush) {\n  var hash_head;        /* head of the hash chain */\n  var bflush;           /* set if current block must be flushed */\n\n  for (;;) {\n    /* Make sure that we always have enough lookahead, except\n     * at the end of the input file. We need MAX_MATCH bytes\n     * for the next match, plus MIN_MATCH bytes to insert the\n     * string following the next match.\n     */\n    if (s.lookahead < MIN_LOOKAHEAD) {\n      fill_window(s);\n      if (s.lookahead < MIN_LOOKAHEAD && flush === Z_NO_FLUSH) {\n        return BS_NEED_MORE;\n      }\n      if (s.lookahead === 0) {\n        break; /* flush the current block */\n      }\n    }\n\n    /* Insert the string window[strstart .. strstart+2] in the\n     * dictionary, and set hash_head to the head of the hash chain:\n     */\n    hash_head = 0/*NIL*/;\n    if (s.lookahead >= MIN_MATCH$1) {\n      /*** INSERT_STRING(s, s.strstart, hash_head); ***/\n      s.ins_h = ((s.ins_h << s.hash_shift) ^ s.window[s.strstart + MIN_MATCH$1 - 1]) & s.hash_mask;\n      hash_head = s.prev[s.strstart & s.w_mask] = s.head[s.ins_h];\n      s.head[s.ins_h] = s.strstart;\n      /***/\n    }\n\n    /* Find the longest match, discarding those <= prev_length.\n     * At this point we have always match_length < MIN_MATCH\n     */\n    if (hash_head !== 0/*NIL*/ && ((s.strstart - hash_head) <= (s.w_size - MIN_LOOKAHEAD))) {\n      /* To simplify the code, we prevent matches with the string\n       * of window index 0 (in particular we have to avoid a match\n       * of the string with itself at the start of the input file).\n       */\n      s.match_length = longest_match(s, hash_head);\n      /* longest_match() sets match_start */\n    }\n    if (s.match_length >= MIN_MATCH$1) {\n      // check_match(s, s.strstart, s.match_start, s.match_length); // for debug only\n\n      /*** _tr_tally_dist(s, s.strstart - s.match_start,\n                     s.match_length - MIN_MATCH, bflush); ***/\n      bflush = _tr_tally(s, s.strstart - s.match_start, s.match_length - MIN_MATCH$1);\n\n      s.lookahead -= s.match_length;\n\n      /* Insert new strings in the hash table only if the match length\n       * is not too large. This saves time but degrades compression.\n       */\n      if (s.match_length <= s.max_lazy_match/*max_insert_length*/ && s.lookahead >= MIN_MATCH$1) {\n        s.match_length--; /* string at strstart already in table */\n        do {\n          s.strstart++;\n          /*** INSERT_STRING(s, s.strstart, hash_head); ***/\n          s.ins_h = ((s.ins_h << s.hash_shift) ^ s.window[s.strstart + MIN_MATCH$1 - 1]) & s.hash_mask;\n          hash_head = s.prev[s.strstart & s.w_mask] = s.head[s.ins_h];\n          s.head[s.ins_h] = s.strstart;\n          /***/\n          /* strstart never exceeds WSIZE-MAX_MATCH, so there are\n           * always MIN_MATCH bytes ahead.\n           */\n        } while (--s.match_length !== 0);\n        s.strstart++;\n      } else\n      {\n        s.strstart += s.match_length;\n        s.match_length = 0;\n        s.ins_h = s.window[s.strstart];\n        /* UPDATE_HASH(s, s.ins_h, s.window[s.strstart+1]); */\n        s.ins_h = ((s.ins_h << s.hash_shift) ^ s.window[s.strstart + 1]) & s.hash_mask;\n\n//#if MIN_MATCH != 3\n//                Call UPDATE_HASH() MIN_MATCH-3 more times\n//#endif\n        /* If lookahead < MIN_MATCH, ins_h is garbage, but it does not\n         * matter since it will be recomputed at next deflate call.\n         */\n      }\n    } else {\n      /* No match, output a literal byte */\n      //Tracevv((stderr,\"%c\", s.window[s.strstart]));\n      /*** _tr_tally_lit(s, s.window[s.strstart], bflush); ***/\n      bflush = _tr_tally(s, 0, s.window[s.strstart]);\n\n      s.lookahead--;\n      s.strstart++;\n    }\n    if (bflush) {\n      /*** FLUSH_BLOCK(s, 0); ***/\n      flush_block_only(s, false);\n      if (s.strm.avail_out === 0) {\n        return BS_NEED_MORE;\n      }\n      /***/\n    }\n  }\n  s.insert = ((s.strstart < (MIN_MATCH$1 - 1)) ? s.strstart : MIN_MATCH$1 - 1);\n  if (flush === Z_FINISH) {\n    /*** FLUSH_BLOCK(s, 1); ***/\n    flush_block_only(s, true);\n    if (s.strm.avail_out === 0) {\n      return BS_FINISH_STARTED;\n    }\n    /***/\n    return BS_FINISH_DONE;\n  }\n  if (s.last_lit) {\n    /*** FLUSH_BLOCK(s, 0); ***/\n    flush_block_only(s, false);\n    if (s.strm.avail_out === 0) {\n      return BS_NEED_MORE;\n    }\n    /***/\n  }\n  return BS_BLOCK_DONE;\n}\n\n/* ===========================================================================\n * Same as above, but achieves better compression. We use a lazy\n * evaluation for matches: a match is finally adopted only if there is\n * no better match at the next window position.\n */\nfunction deflate_slow(s, flush) {\n  var hash_head;          /* head of hash chain */\n  var bflush;              /* set if current block must be flushed */\n\n  var max_insert;\n\n  /* Process the input block. */\n  for (;;) {\n    /* Make sure that we always have enough lookahead, except\n     * at the end of the input file. We need MAX_MATCH bytes\n     * for the next match, plus MIN_MATCH bytes to insert the\n     * string following the next match.\n     */\n    if (s.lookahead < MIN_LOOKAHEAD) {\n      fill_window(s);\n      if (s.lookahead < MIN_LOOKAHEAD && flush === Z_NO_FLUSH) {\n        return BS_NEED_MORE;\n      }\n      if (s.lookahead === 0) { break; } /* flush the current block */\n    }\n\n    /* Insert the string window[strstart .. strstart+2] in the\n     * dictionary, and set hash_head to the head of the hash chain:\n     */\n    hash_head = 0/*NIL*/;\n    if (s.lookahead >= MIN_MATCH$1) {\n      /*** INSERT_STRING(s, s.strstart, hash_head); ***/\n      s.ins_h = ((s.ins_h << s.hash_shift) ^ s.window[s.strstart + MIN_MATCH$1 - 1]) & s.hash_mask;\n      hash_head = s.prev[s.strstart & s.w_mask] = s.head[s.ins_h];\n      s.head[s.ins_h] = s.strstart;\n      /***/\n    }\n\n    /* Find the longest match, discarding those <= prev_length.\n     */\n    s.prev_length = s.match_length;\n    s.prev_match = s.match_start;\n    s.match_length = MIN_MATCH$1 - 1;\n\n    if (hash_head !== 0/*NIL*/ && s.prev_length < s.max_lazy_match &&\n        s.strstart - hash_head <= (s.w_size - MIN_LOOKAHEAD)/*MAX_DIST(s)*/) {\n      /* To simplify the code, we prevent matches with the string\n       * of window index 0 (in particular we have to avoid a match\n       * of the string with itself at the start of the input file).\n       */\n      s.match_length = longest_match(s, hash_head);\n      /* longest_match() sets match_start */\n\n      if (s.match_length <= 5 &&\n         (s.strategy === Z_FILTERED || (s.match_length === MIN_MATCH$1 && s.strstart - s.match_start > 4096/*TOO_FAR*/))) {\n\n        /* If prev_match is also MIN_MATCH, match_start is garbage\n         * but we will ignore the current match anyway.\n         */\n        s.match_length = MIN_MATCH$1 - 1;\n      }\n    }\n    /* If there was a match at the previous step and the current\n     * match is not better, output the previous match:\n     */\n    if (s.prev_length >= MIN_MATCH$1 && s.match_length <= s.prev_length) {\n      max_insert = s.strstart + s.lookahead - MIN_MATCH$1;\n      /* Do not insert strings in hash table beyond this. */\n\n      //check_match(s, s.strstart-1, s.prev_match, s.prev_length);\n\n      /***_tr_tally_dist(s, s.strstart - 1 - s.prev_match,\n                     s.prev_length - MIN_MATCH, bflush);***/\n      bflush = _tr_tally(s, s.strstart - 1 - s.prev_match, s.prev_length - MIN_MATCH$1);\n      /* Insert in hash table all strings up to the end of the match.\n       * strstart-1 and strstart are already inserted. If there is not\n       * enough lookahead, the last two strings are not inserted in\n       * the hash table.\n       */\n      s.lookahead -= s.prev_length - 1;\n      s.prev_length -= 2;\n      do {\n        if (++s.strstart <= max_insert) {\n          /*** INSERT_STRING(s, s.strstart, hash_head); ***/\n          s.ins_h = ((s.ins_h << s.hash_shift) ^ s.window[s.strstart + MIN_MATCH$1 - 1]) & s.hash_mask;\n          hash_head = s.prev[s.strstart & s.w_mask] = s.head[s.ins_h];\n          s.head[s.ins_h] = s.strstart;\n          /***/\n        }\n      } while (--s.prev_length !== 0);\n      s.match_available = 0;\n      s.match_length = MIN_MATCH$1 - 1;\n      s.strstart++;\n\n      if (bflush) {\n        /*** FLUSH_BLOCK(s, 0); ***/\n        flush_block_only(s, false);\n        if (s.strm.avail_out === 0) {\n          return BS_NEED_MORE;\n        }\n        /***/\n      }\n\n    } else if (s.match_available) {\n      /* If there was no match at the previous position, output a\n       * single literal. If there was a match but the current match\n       * is longer, truncate the previous match to a single literal.\n       */\n      //Tracevv((stderr,\"%c\", s->window[s->strstart-1]));\n      /*** _tr_tally_lit(s, s.window[s.strstart-1], bflush); ***/\n      bflush = _tr_tally(s, 0, s.window[s.strstart - 1]);\n\n      if (bflush) {\n        /*** FLUSH_BLOCK_ONLY(s, 0) ***/\n        flush_block_only(s, false);\n        /***/\n      }\n      s.strstart++;\n      s.lookahead--;\n      if (s.strm.avail_out === 0) {\n        return BS_NEED_MORE;\n      }\n    } else {\n      /* There is no previous match to compare with, wait for\n       * the next step to decide.\n       */\n      s.match_available = 1;\n      s.strstart++;\n      s.lookahead--;\n    }\n  }\n  //Assert (flush != Z_NO_FLUSH, \"no flush?\");\n  if (s.match_available) {\n    //Tracevv((stderr,\"%c\", s->window[s->strstart-1]));\n    /*** _tr_tally_lit(s, s.window[s.strstart-1], bflush); ***/\n    bflush = _tr_tally(s, 0, s.window[s.strstart - 1]);\n\n    s.match_available = 0;\n  }\n  s.insert = s.strstart < MIN_MATCH$1 - 1 ? s.strstart : MIN_MATCH$1 - 1;\n  if (flush === Z_FINISH) {\n    /*** FLUSH_BLOCK(s, 1); ***/\n    flush_block_only(s, true);\n    if (s.strm.avail_out === 0) {\n      return BS_FINISH_STARTED;\n    }\n    /***/\n    return BS_FINISH_DONE;\n  }\n  if (s.last_lit) {\n    /*** FLUSH_BLOCK(s, 0); ***/\n    flush_block_only(s, false);\n    if (s.strm.avail_out === 0) {\n      return BS_NEED_MORE;\n    }\n    /***/\n  }\n\n  return BS_BLOCK_DONE;\n}\n\n\n/* ===========================================================================\n * For Z_RLE, simply look for runs of bytes, generate matches only of distance\n * one.  Do not maintain a hash table.  (It will be regenerated if this run of\n * deflate switches away from Z_RLE.)\n */\nfunction deflate_rle(s, flush) {\n  var bflush;            /* set if current block must be flushed */\n  var prev;              /* byte at distance one to match */\n  var scan, strend;      /* scan goes up to strend for length of run */\n\n  var _win = s.window;\n\n  for (;;) {\n    /* Make sure that we always have enough lookahead, except\n     * at the end of the input file. We need MAX_MATCH bytes\n     * for the longest run, plus one for the unrolled loop.\n     */\n    if (s.lookahead <= MAX_MATCH$1) {\n      fill_window(s);\n      if (s.lookahead <= MAX_MATCH$1 && flush === Z_NO_FLUSH) {\n        return BS_NEED_MORE;\n      }\n      if (s.lookahead === 0) { break; } /* flush the current block */\n    }\n\n    /* See how many times the previous byte repeats */\n    s.match_length = 0;\n    if (s.lookahead >= MIN_MATCH$1 && s.strstart > 0) {\n      scan = s.strstart - 1;\n      prev = _win[scan];\n      if (prev === _win[++scan] && prev === _win[++scan] && prev === _win[++scan]) {\n        strend = s.strstart + MAX_MATCH$1;\n        do {\n          /*jshint noempty:false*/\n        } while (prev === _win[++scan] && prev === _win[++scan] &&\n                 prev === _win[++scan] && prev === _win[++scan] &&\n                 prev === _win[++scan] && prev === _win[++scan] &&\n                 prev === _win[++scan] && prev === _win[++scan] &&\n                 scan < strend);\n        s.match_length = MAX_MATCH$1 - (strend - scan);\n        if (s.match_length > s.lookahead) {\n          s.match_length = s.lookahead;\n        }\n      }\n      //Assert(scan <= s->window+(uInt)(s->window_size-1), \"wild scan\");\n    }\n\n    /* Emit match if have run of MIN_MATCH or longer, else emit literal */\n    if (s.match_length >= MIN_MATCH$1) {\n      //check_match(s, s.strstart, s.strstart - 1, s.match_length);\n\n      /*** _tr_tally_dist(s, 1, s.match_length - MIN_MATCH, bflush); ***/\n      bflush = _tr_tally(s, 1, s.match_length - MIN_MATCH$1);\n\n      s.lookahead -= s.match_length;\n      s.strstart += s.match_length;\n      s.match_length = 0;\n    } else {\n      /* No match, output a literal byte */\n      //Tracevv((stderr,\"%c\", s->window[s->strstart]));\n      /*** _tr_tally_lit(s, s.window[s.strstart], bflush); ***/\n      bflush = _tr_tally(s, 0, s.window[s.strstart]);\n\n      s.lookahead--;\n      s.strstart++;\n    }\n    if (bflush) {\n      /*** FLUSH_BLOCK(s, 0); ***/\n      flush_block_only(s, false);\n      if (s.strm.avail_out === 0) {\n        return BS_NEED_MORE;\n      }\n      /***/\n    }\n  }\n  s.insert = 0;\n  if (flush === Z_FINISH) {\n    /*** FLUSH_BLOCK(s, 1); ***/\n    flush_block_only(s, true);\n    if (s.strm.avail_out === 0) {\n      return BS_FINISH_STARTED;\n    }\n    /***/\n    return BS_FINISH_DONE;\n  }\n  if (s.last_lit) {\n    /*** FLUSH_BLOCK(s, 0); ***/\n    flush_block_only(s, false);\n    if (s.strm.avail_out === 0) {\n      return BS_NEED_MORE;\n    }\n    /***/\n  }\n  return BS_BLOCK_DONE;\n}\n\n/* ===========================================================================\n * For Z_HUFFMAN_ONLY, do not look for matches.  Do not maintain a hash table.\n * (It will be regenerated if this run of deflate switches away from Huffman.)\n */\nfunction deflate_huff(s, flush) {\n  var bflush;             /* set if current block must be flushed */\n\n  for (;;) {\n    /* Make sure that we have a literal to write. */\n    if (s.lookahead === 0) {\n      fill_window(s);\n      if (s.lookahead === 0) {\n        if (flush === Z_NO_FLUSH) {\n          return BS_NEED_MORE;\n        }\n        break;      /* flush the current block */\n      }\n    }\n\n    /* Output a literal byte */\n    s.match_length = 0;\n    //Tracevv((stderr,\"%c\", s->window[s->strstart]));\n    /*** _tr_tally_lit(s, s.window[s.strstart], bflush); ***/\n    bflush = _tr_tally(s, 0, s.window[s.strstart]);\n    s.lookahead--;\n    s.strstart++;\n    if (bflush) {\n      /*** FLUSH_BLOCK(s, 0); ***/\n      flush_block_only(s, false);\n      if (s.strm.avail_out === 0) {\n        return BS_NEED_MORE;\n      }\n      /***/\n    }\n  }\n  s.insert = 0;\n  if (flush === Z_FINISH) {\n    /*** FLUSH_BLOCK(s, 1); ***/\n    flush_block_only(s, true);\n    if (s.strm.avail_out === 0) {\n      return BS_FINISH_STARTED;\n    }\n    /***/\n    return BS_FINISH_DONE;\n  }\n  if (s.last_lit) {\n    /*** FLUSH_BLOCK(s, 0); ***/\n    flush_block_only(s, false);\n    if (s.strm.avail_out === 0) {\n      return BS_NEED_MORE;\n    }\n    /***/\n  }\n  return BS_BLOCK_DONE;\n}\n\n/* Values for max_lazy_match, good_match and max_chain_length, depending on\n * the desired pack level (0..9). The values given below have been tuned to\n * exclude worst case performance for pathological files. Better values may be\n * found for specific files.\n */\nfunction Config(good_length, max_lazy, nice_length, max_chain, func) {\n  this.good_length = good_length;\n  this.max_lazy = max_lazy;\n  this.nice_length = nice_length;\n  this.max_chain = max_chain;\n  this.func = func;\n}\n\nvar configurationTable = function() {\n  var table = [\n    /*      good lazy nice chain */\n    new Config(0, 0, 0, 0, deflate_stored),          /* 0 store only */\n    new Config(4, 4, 8, 4, deflate_fast),            /* 1 max speed, no lazy matches */\n    new Config(4, 5, 16, 8, deflate_fast),           /* 2 */\n    new Config(4, 6, 32, 32, deflate_fast),          /* 3 */\n  \n    new Config(4, 4, 16, 16, deflate_slow),          /* 4 lazy matches */\n    new Config(8, 16, 32, 32, deflate_slow),         /* 5 */\n    new Config(8, 16, 128, 128, deflate_slow),       /* 6 */\n    new Config(8, 32, 128, 256, deflate_slow),       /* 7 */\n    new Config(32, 128, 258, 1024, deflate_slow),    /* 8 */\n    new Config(32, 258, 258, 4096, deflate_slow)     /* 9 max compression */\n  ];\n\n  configurationTable = function () { return table; };\n  return table;\n};\n\n/* ===========================================================================\n * Initialize the \"longest match\" routines for a new zlib stream\n */\nfunction lm_init(s) {\n  s.window_size = 2 * s.w_size;\n\n  /*** CLEAR_HASH(s); ***/\n  zero$1(s.head); // Fill with NIL (= 0);\n\n  var table = configurationTable();\n  /* Set the default configuration parameters:\n   */\n  s.max_lazy_match = table[s.level].max_lazy;\n  s.good_match = table[s.level].good_length;\n  s.nice_match = table[s.level].nice_length;\n  s.max_chain_length = table[s.level].max_chain;\n\n  s.strstart = 0;\n  s.block_start = 0;\n  s.lookahead = 0;\n  s.insert = 0;\n  s.match_length = s.prev_length = MIN_MATCH$1 - 1;\n  s.match_available = 0;\n  s.ins_h = 0;\n}\n\n\nfunction DeflateState() {\n  this.strm = null;            /* pointer back to this zlib stream */\n  this.status = 0;            /* as the name implies */\n  this.pending_buf = null;      /* output still pending */\n  this.pending_buf_size = 0;  /* size of pending_buf */\n  this.pending_out = 0;       /* next pending byte to output to the stream */\n  this.pending = 0;           /* nb of bytes in the pending buffer */\n  this.wrap = 0;              /* bit 0 true for zlib, bit 1 true for gzip */\n  this.gzhead = null;         /* gzip header information to write */\n  this.gzindex = 0;           /* where in extra, name, or comment */\n  this.method = Z_DEFLATED; /* can only be DEFLATED */\n  this.last_flush = -1;   /* value of flush param for previous deflate call */\n\n  this.w_size = 0;  /* LZ77 window size (32K by default) */\n  this.w_bits = 0;  /* log2(w_size)  (8..16) */\n  this.w_mask = 0;  /* w_size - 1 */\n\n  this.window = null;\n  /* Sliding window. Input bytes are read into the second half of the window,\n   * and move to the first half later to keep a dictionary of at least wSize\n   * bytes. With this organization, matches are limited to a distance of\n   * wSize-MAX_MATCH bytes, but this ensures that IO is always\n   * performed with a length multiple of the block size.\n   */\n\n  this.window_size = 0;\n  /* Actual size of window: 2*wSize, except when the user input buffer\n   * is directly used as sliding window.\n   */\n\n  this.prev = null;\n  /* Link to older string with same hash index. To limit the size of this\n   * array to 64K, this link is maintained only for the last 32K strings.\n   * An index in this array is thus a window index modulo 32K.\n   */\n\n  this.head = null;   /* Heads of the hash chains or NIL. */\n\n  this.ins_h = 0;       /* hash index of string to be inserted */\n  this.hash_size = 0;   /* number of elements in hash table */\n  this.hash_bits = 0;   /* log2(hash_size) */\n  this.hash_mask = 0;   /* hash_size-1 */\n\n  this.hash_shift = 0;\n  /* Number of bits by which ins_h must be shifted at each input\n   * step. It must be such that after MIN_MATCH steps, the oldest\n   * byte no longer takes part in the hash key, that is:\n   *   hash_shift * MIN_MATCH >= hash_bits\n   */\n\n  this.block_start = 0;\n  /* Window position at the beginning of the current output block. Gets\n   * negative when the window is moved backwards.\n   */\n\n  this.match_length = 0;      /* length of best match */\n  this.prev_match = 0;        /* previous match */\n  this.match_available = 0;   /* set if previous match exists */\n  this.strstart = 0;          /* start of string to insert */\n  this.match_start = 0;       /* start of matching string */\n  this.lookahead = 0;         /* number of valid bytes ahead in window */\n\n  this.prev_length = 0;\n  /* Length of the best match at previous step. Matches not greater than this\n   * are discarded. This is used in the lazy match evaluation.\n   */\n\n  this.max_chain_length = 0;\n  /* To speed up deflation, hash chains are never searched beyond this\n   * length.  A higher limit improves compression ratio but degrades the\n   * speed.\n   */\n\n  this.max_lazy_match = 0;\n  /* Attempt to find a better match only when the current match is strictly\n   * smaller than this value. This mechanism is used only for compression\n   * levels >= 4.\n   */\n  // That's alias to max_lazy_match, don't use directly\n  //this.max_insert_length = 0;\n  /* Insert new strings in the hash table only if the match length is not\n   * greater than this length. This saves time but degrades compression.\n   * max_insert_length is used only for compression levels <= 3.\n   */\n\n  this.level = 0;     /* compression level (1..9) */\n  this.strategy = 0;  /* favor or force Huffman coding*/\n\n  this.good_match = 0;\n  /* Use a faster search when the previous match is longer than this */\n\n  this.nice_match = 0; /* Stop searching when current match exceeds this */\n\n              /* used by trees.c: */\n\n  /* Didn't use ct_data typedef below to suppress compiler warning */\n\n  // struct ct_data_s dyn_ltree[HEAP_SIZE];   /* literal and length tree */\n  // struct ct_data_s dyn_dtree[2*D_CODES+1]; /* distance tree */\n  // struct ct_data_s bl_tree[2*BL_CODES+1];  /* Huffman tree for bit lengths */\n\n  // Use flat array of DOUBLE size, with interleaved fata,\n  // because JS does not support effective\n  this.dyn_ltree  = Buf16(HEAP_SIZE$1 * 2);\n  this.dyn_dtree  = Buf16((2 * D_CODES$1 + 1) * 2);\n  this.bl_tree    = Buf16((2 * BL_CODES$1 + 1) * 2);\n  zero$1(this.dyn_ltree);\n  zero$1(this.dyn_dtree);\n  zero$1(this.bl_tree);\n\n  this.l_desc   = null;         /* desc. for literal tree */\n  this.d_desc   = null;         /* desc. for distance tree */\n  this.bl_desc  = null;         /* desc. for bit length tree */\n\n  //ush bl_count[MAX_BITS+1];\n  this.bl_count = Buf16(MAX_BITS$1 + 1);\n  /* number of codes at each bit length for an optimal tree */\n\n  //int heap[2*L_CODES+1];      /* heap used to build the Huffman trees */\n  this.heap = Buf16(2 * L_CODES$1 + 1);  /* heap used to build the Huffman trees */\n  zero$1(this.heap);\n\n  this.heap_len = 0;               /* number of elements in the heap */\n  this.heap_max = 0;               /* element of largest frequency */\n  /* The sons of heap[n] are heap[2*n] and heap[2*n+1]. heap[0] is not used.\n   * The same heap array is used to build all trees.\n   */\n\n  this.depth = Buf16(2 * L_CODES$1 + 1); //uch depth[2*L_CODES+1];\n  zero$1(this.depth);\n  /* Depth of each subtree used as tie breaker for trees of equal frequency\n   */\n\n  this.l_buf = 0;          /* buffer index for literals or lengths */\n\n  this.lit_bufsize = 0;\n  /* Size of match buffer for literals/lengths.  There are 4 reasons for\n   * limiting lit_bufsize to 64K:\n   *   - frequencies can be kept in 16 bit counters\n   *   - if compression is not successful for the first block, all input\n   *     data is still in the window so we can still emit a stored block even\n   *     when input comes from standard input.  (This can also be done for\n   *     all blocks if lit_bufsize is not greater than 32K.)\n   *   - if compression is not successful for a file smaller than 64K, we can\n   *     even emit a stored file instead of a stored block (saving 5 bytes).\n   *     This is applicable only for zip (not gzip or zlib).\n   *   - creating new Huffman trees less frequently may not provide fast\n   *     adaptation to changes in the input data statistics. (Take for\n   *     example a binary file with poorly compressible code followed by\n   *     a highly compressible string table.) Smaller buffer sizes give\n   *     fast adaptation but have of course the overhead of transmitting\n   *     trees more frequently.\n   *   - I can't count above 4\n   */\n\n  this.last_lit = 0;      /* running index in l_buf */\n\n  this.d_buf = 0;\n  /* Buffer index for distances. To simplify the code, d_buf and l_buf have\n   * the same number of elements. To use different lengths, an extra flag\n   * array would be necessary.\n   */\n\n  this.opt_len = 0;       /* bit length of current block with optimal trees */\n  this.static_len = 0;    /* bit length of current block with static trees */\n  this.matches = 0;       /* number of string matches in current block */\n  this.insert = 0;        /* bytes at end of window left to insert */\n\n\n  this.bi_buf = 0;\n  /* Output buffer. bits are inserted starting at the bottom (least\n   * significant bits).\n   */\n  this.bi_valid = 0;\n  /* Number of valid bits in bi_buf.  All bits above the last valid bit\n   * are always zero.\n   */\n\n  // Used for window memory init. We safely ignore it for JS. That makes\n  // sense only for pointers and memory check tools.\n  //this.high_water = 0;\n  /* High water mark offset in window for initialized bytes -- bytes above\n   * this are set to zero in order to avoid memory check warnings when\n   * longest match routines access bytes past the input.  This is then\n   * updated to the new high water mark.\n   */\n}\n\n\nfunction deflateResetKeep(strm) {\n  var s;\n\n  if (!strm || !strm.state) {\n    return err(strm, Z_STREAM_ERROR);\n  }\n\n  strm.total_in = strm.total_out = 0;\n  strm.data_type = Z_UNKNOWN;\n\n  s = strm.state;\n  s.pending = 0;\n  s.pending_out = 0;\n\n  if (s.wrap < 0) {\n    s.wrap = -s.wrap;\n    /* was made negative by deflate(..., Z_FINISH); */\n  }\n  s.status = (s.wrap ? INIT_STATE : BUSY_STATE);\n  strm.adler = (s.wrap === 2) ?\n    0  // crc32(0, Z_NULL, 0)\n  :\n    1; // adler32(0, Z_NULL, 0)\n  s.last_flush = Z_NO_FLUSH;\n  _tr_init(s);\n  return Z_OK;\n}\n\n\nfunction deflateReset(strm) {\n  var ret = deflateResetKeep(strm);\n  if (ret === Z_OK) {\n    lm_init(strm.state);\n  }\n  return ret;\n}\n\n\nfunction deflateSetHeader(strm, head) {\n  if (!strm || !strm.state) { return Z_STREAM_ERROR; }\n  if (strm.state.wrap !== 2) { return Z_STREAM_ERROR; }\n  strm.state.gzhead = head;\n  return Z_OK;\n}\n\n\nfunction deflateInit2(strm, level, method, windowBits, memLevel, strategy) {\n  if (!strm) { // === Z_NULL\n    return Z_STREAM_ERROR;\n  }\n  var wrap = 1;\n\n  if (level === Z_DEFAULT_COMPRESSION) {\n    level = 6;\n  }\n\n  if (windowBits < 0) { /* suppress zlib wrapper */\n    wrap = 0;\n    windowBits = -windowBits;\n  }\n\n  else if (windowBits > 15) {\n    wrap = 2;           /* write gzip wrapper instead */\n    windowBits -= 16;\n  }\n\n\n  if (memLevel < 1 || memLevel > MAX_MEM_LEVEL || method !== Z_DEFLATED ||\n    windowBits < 8 || windowBits > 15 || level < 0 || level > 9 ||\n    strategy < 0 || strategy > Z_FIXED) {\n    return err(strm, Z_STREAM_ERROR);\n  }\n\n\n  if (windowBits === 8) {\n    windowBits = 9;\n  }\n  /* until 256-byte window bug fixed */\n\n  var s = new DeflateState();\n\n  strm.state = s;\n  s.strm = strm;\n\n  s.wrap = wrap;\n  s.gzhead = null;\n  s.w_bits = windowBits;\n  s.w_size = 1 << s.w_bits;\n  s.w_mask = s.w_size - 1;\n\n  s.hash_bits = memLevel + 7;\n  s.hash_size = 1 << s.hash_bits;\n  s.hash_mask = s.hash_size - 1;\n  s.hash_shift = ~~((s.hash_bits + MIN_MATCH$1 - 1) / MIN_MATCH$1);\n\n  s.window = Buf8(s.w_size * 2);\n  s.head = Buf16(s.hash_size);\n  s.prev = Buf16(s.w_size);\n\n  // Don't need mem init magic for JS.\n  //s.high_water = 0;  /* nothing written to s->window yet */\n\n  s.lit_bufsize = 1 << (memLevel + 6); /* 16K elements by default */\n\n  s.pending_buf_size = s.lit_bufsize * 4;\n\n  //overlay = (ushf *) ZALLOC(strm, s->lit_bufsize, sizeof(ush)+2);\n  //s->pending_buf = (uchf *) overlay;\n  s.pending_buf = Buf8(s.pending_buf_size);\n\n  // It is offset from `s.pending_buf` (size is `s.lit_bufsize * 2`)\n  //s->d_buf = overlay + s->lit_bufsize/sizeof(ush);\n  s.d_buf = 1 * s.lit_bufsize;\n\n  //s->l_buf = s->pending_buf + (1+sizeof(ush))*s->lit_bufsize;\n  s.l_buf = (1 + 2) * s.lit_bufsize;\n\n  s.level = level;\n  s.strategy = strategy;\n  s.method = method;\n\n  return deflateReset(strm);\n}\n\n\nfunction deflate(strm, flush) {\n  var old_flush, s;\n  var beg, val; // for gzip header write only\n\n  if (!strm || !strm.state ||\n    flush > Z_BLOCK || flush < 0) {\n    return strm ? err(strm, Z_STREAM_ERROR) : Z_STREAM_ERROR;\n  }\n\n  s = strm.state;\n\n  if (!strm.output ||\n      (!strm.input && strm.avail_in !== 0) ||\n      (s.status === FINISH_STATE && flush !== Z_FINISH)) {\n    return err(strm, (strm.avail_out === 0) ? Z_BUF_ERROR : Z_STREAM_ERROR);\n  }\n\n  s.strm = strm; /* just in case */\n  old_flush = s.last_flush;\n  s.last_flush = flush;\n\n  /* Write the header */\n  if (s.status === INIT_STATE) {\n\n    if (s.wrap === 2) { // GZIP header\n      strm.adler = 0;  //crc32(0L, Z_NULL, 0);\n      put_byte(s, 31);\n      put_byte(s, 139);\n      put_byte(s, 8);\n      if (!s.gzhead) { // s->gzhead == Z_NULL\n        put_byte(s, 0);\n        put_byte(s, 0);\n        put_byte(s, 0);\n        put_byte(s, 0);\n        put_byte(s, 0);\n        put_byte(s, s.level === 9 ? 2 :\n                    (s.strategy >= Z_HUFFMAN_ONLY || s.level < 2 ?\n                     4 : 0));\n        put_byte(s, OS_CODE);\n        s.status = BUSY_STATE;\n      }\n      else {\n        put_byte(s, (s.gzhead.text ? 1 : 0) +\n                    (s.gzhead.hcrc ? 2 : 0) +\n                    (!s.gzhead.extra ? 0 : 4) +\n                    (!s.gzhead.name ? 0 : 8) +\n                    (!s.gzhead.comment ? 0 : 16)\n        );\n        put_byte(s, s.gzhead.time & 0xff);\n        put_byte(s, (s.gzhead.time >> 8) & 0xff);\n        put_byte(s, (s.gzhead.time >> 16) & 0xff);\n        put_byte(s, (s.gzhead.time >> 24) & 0xff);\n        put_byte(s, s.level === 9 ? 2 :\n                    (s.strategy >= Z_HUFFMAN_ONLY || s.level < 2 ?\n                     4 : 0));\n        put_byte(s, s.gzhead.os & 0xff);\n        if (s.gzhead.extra && s.gzhead.extra.length) {\n          put_byte(s, s.gzhead.extra.length & 0xff);\n          put_byte(s, (s.gzhead.extra.length >> 8) & 0xff);\n        }\n        if (s.gzhead.hcrc) {\n          strm.adler = crc32(strm.adler, s.pending_buf, s.pending, 0);\n        }\n        s.gzindex = 0;\n        s.status = EXTRA_STATE;\n      }\n    }\n    else // DEFLATE header\n    {\n      var header = (Z_DEFLATED + ((s.w_bits - 8) << 4)) << 8;\n      var level_flags = -1;\n\n      if (s.strategy >= Z_HUFFMAN_ONLY || s.level < 2) {\n        level_flags = 0;\n      } else if (s.level < 6) {\n        level_flags = 1;\n      } else if (s.level === 6) {\n        level_flags = 2;\n      } else {\n        level_flags = 3;\n      }\n      header |= (level_flags << 6);\n      if (s.strstart !== 0) { header |= PRESET_DICT; }\n      header += 31 - (header % 31);\n\n      s.status = BUSY_STATE;\n      putShortMSB(s, header);\n\n      /* Save the adler32 of the preset dictionary: */\n      if (s.strstart !== 0) {\n        putShortMSB(s, strm.adler >>> 16);\n        putShortMSB(s, strm.adler & 0xffff);\n      }\n      strm.adler = 1; // adler32(0L, Z_NULL, 0);\n    }\n  }\n\n//#ifdef GZIP\n  if (s.status === EXTRA_STATE) {\n    if (s.gzhead.extra/* != Z_NULL*/) {\n      beg = s.pending;  /* start of bytes to update crc */\n\n      while (s.gzindex < (s.gzhead.extra.length & 0xffff)) {\n        if (s.pending === s.pending_buf_size) {\n          if (s.gzhead.hcrc && s.pending > beg) {\n            strm.adler = crc32(strm.adler, s.pending_buf, s.pending - beg, beg);\n          }\n          flush_pending(strm);\n          beg = s.pending;\n          if (s.pending === s.pending_buf_size) {\n            break;\n          }\n        }\n        put_byte(s, s.gzhead.extra[s.gzindex] & 0xff);\n        s.gzindex++;\n      }\n      if (s.gzhead.hcrc && s.pending > beg) {\n        strm.adler = crc32(strm.adler, s.pending_buf, s.pending - beg, beg);\n      }\n      if (s.gzindex === s.gzhead.extra.length) {\n        s.gzindex = 0;\n        s.status = NAME_STATE;\n      }\n    }\n    else {\n      s.status = NAME_STATE;\n    }\n  }\n  if (s.status === NAME_STATE) {\n    if (s.gzhead.name/* != Z_NULL*/) {\n      beg = s.pending;  /* start of bytes to update crc */\n      //int val;\n\n      do {\n        if (s.pending === s.pending_buf_size) {\n          if (s.gzhead.hcrc && s.pending > beg) {\n            strm.adler = crc32(strm.adler, s.pending_buf, s.pending - beg, beg);\n          }\n          flush_pending(strm);\n          beg = s.pending;\n          if (s.pending === s.pending_buf_size) {\n            val = 1;\n            break;\n          }\n        }\n        // JS specific: little magic to add zero terminator to end of string\n        if (s.gzindex < s.gzhead.name.length) {\n          val = s.gzhead.name.charCodeAt(s.gzindex++) & 0xff;\n        } else {\n          val = 0;\n        }\n        put_byte(s, val);\n      } while (val !== 0);\n\n      if (s.gzhead.hcrc && s.pending > beg) {\n        strm.adler = crc32(strm.adler, s.pending_buf, s.pending - beg, beg);\n      }\n      if (val === 0) {\n        s.gzindex = 0;\n        s.status = COMMENT_STATE;\n      }\n    }\n    else {\n      s.status = COMMENT_STATE;\n    }\n  }\n  if (s.status === COMMENT_STATE) {\n    if (s.gzhead.comment/* != Z_NULL*/) {\n      beg = s.pending;  /* start of bytes to update crc */\n      //int val;\n\n      do {\n        if (s.pending === s.pending_buf_size) {\n          if (s.gzhead.hcrc && s.pending > beg) {\n            strm.adler = crc32(strm.adler, s.pending_buf, s.pending - beg, beg);\n          }\n          flush_pending(strm);\n          beg = s.pending;\n          if (s.pending === s.pending_buf_size) {\n            val = 1;\n            break;\n          }\n        }\n        // JS specific: little magic to add zero terminator to end of string\n        if (s.gzindex < s.gzhead.comment.length) {\n          val = s.gzhead.comment.charCodeAt(s.gzindex++) & 0xff;\n        } else {\n          val = 0;\n        }\n        put_byte(s, val);\n      } while (val !== 0);\n\n      if (s.gzhead.hcrc && s.pending > beg) {\n        strm.adler = crc32(strm.adler, s.pending_buf, s.pending - beg, beg);\n      }\n      if (val === 0) {\n        s.status = HCRC_STATE;\n      }\n    }\n    else {\n      s.status = HCRC_STATE;\n    }\n  }\n  if (s.status === HCRC_STATE) {\n    if (s.gzhead.hcrc) {\n      if (s.pending + 2 > s.pending_buf_size) {\n        flush_pending(strm);\n      }\n      if (s.pending + 2 <= s.pending_buf_size) {\n        put_byte(s, strm.adler & 0xff);\n        put_byte(s, (strm.adler >> 8) & 0xff);\n        strm.adler = 0; //crc32(0L, Z_NULL, 0);\n        s.status = BUSY_STATE;\n      }\n    }\n    else {\n      s.status = BUSY_STATE;\n    }\n  }\n//#endif\n\n  /* Flush as much pending output as possible */\n  if (s.pending !== 0) {\n    flush_pending(strm);\n    if (strm.avail_out === 0) {\n      /* Since avail_out is 0, deflate will be called again with\n       * more output space, but possibly with both pending and\n       * avail_in equal to zero. There won't be anything to do,\n       * but this is not an error situation so make sure we\n       * return OK instead of BUF_ERROR at next call of deflate:\n       */\n      s.last_flush = -1;\n      return Z_OK;\n    }\n\n    /* Make sure there is something to do and avoid duplicate consecutive\n     * flushes. For repeated and useless calls with Z_FINISH, we keep\n     * returning Z_STREAM_END instead of Z_BUF_ERROR.\n     */\n  } else if (strm.avail_in === 0 && rank(flush) <= rank(old_flush) &&\n    flush !== Z_FINISH) {\n    return err(strm, Z_BUF_ERROR);\n  }\n\n  /* User must not provide more input after the first FINISH: */\n  if (s.status === FINISH_STATE && strm.avail_in !== 0) {\n    return err(strm, Z_BUF_ERROR);\n  }\n\n  /* Start a new block or continue the current one.\n   */\n  if (strm.avail_in !== 0 || s.lookahead !== 0 ||\n    (flush !== Z_NO_FLUSH && s.status !== FINISH_STATE)) {\n    var bstate = (s.strategy === Z_HUFFMAN_ONLY) ? deflate_huff(s, flush) :\n      (s.strategy === Z_RLE ? deflate_rle(s, flush) :\n        configurationTable()[s.level].func(s, flush));\n\n    if (bstate === BS_FINISH_STARTED || bstate === BS_FINISH_DONE) {\n      s.status = FINISH_STATE;\n    }\n    if (bstate === BS_NEED_MORE || bstate === BS_FINISH_STARTED) {\n      if (strm.avail_out === 0) {\n        s.last_flush = -1;\n        /* avoid BUF_ERROR next call, see above */\n      }\n      return Z_OK;\n      /* If flush != Z_NO_FLUSH && avail_out == 0, the next call\n       * of deflate should use the same flush parameter to make sure\n       * that the flush is complete. So we don't have to output an\n       * empty block here, this will be done at next call. This also\n       * ensures that for a very small output buffer, we emit at most\n       * one empty block.\n       */\n    }\n    if (bstate === BS_BLOCK_DONE) {\n      if (flush === Z_PARTIAL_FLUSH) {\n        _tr_align(s);\n      }\n      else if (flush !== Z_BLOCK) { /* FULL_FLUSH or SYNC_FLUSH */\n\n        _tr_stored_block(s, 0, 0, false);\n        /* For a full flush, this empty block will be recognized\n         * as a special marker by inflate_sync().\n         */\n        if (flush === Z_FULL_FLUSH) {\n          /*** CLEAR_HASH(s); ***/             /* forget history */\n          zero$1(s.head); // Fill with NIL (= 0);\n\n          if (s.lookahead === 0) {\n            s.strstart = 0;\n            s.block_start = 0;\n            s.insert = 0;\n          }\n        }\n      }\n      flush_pending(strm);\n      if (strm.avail_out === 0) {\n        s.last_flush = -1; /* avoid BUF_ERROR at next call, see above */\n        return Z_OK;\n      }\n    }\n  }\n  //Assert(strm->avail_out > 0, \"bug2\");\n  //if (strm.avail_out <= 0) { throw new Error(\"bug2\");}\n\n  if (flush !== Z_FINISH) { return Z_OK; }\n  if (s.wrap <= 0) { return Z_STREAM_END; }\n\n  /* Write the trailer */\n  if (s.wrap === 2) {\n    put_byte(s, strm.adler & 0xff);\n    put_byte(s, (strm.adler >> 8) & 0xff);\n    put_byte(s, (strm.adler >> 16) & 0xff);\n    put_byte(s, (strm.adler >> 24) & 0xff);\n    put_byte(s, strm.total_in & 0xff);\n    put_byte(s, (strm.total_in >> 8) & 0xff);\n    put_byte(s, (strm.total_in >> 16) & 0xff);\n    put_byte(s, (strm.total_in >> 24) & 0xff);\n  }\n  else\n  {\n    putShortMSB(s, strm.adler >>> 16);\n    putShortMSB(s, strm.adler & 0xffff);\n  }\n\n  flush_pending(strm);\n  /* If avail_out is zero, the application will call deflate again\n   * to flush the rest.\n   */\n  if (s.wrap > 0) { s.wrap = -s.wrap; }\n  /* write the trailer only once! */\n  return s.pending !== 0 ? Z_OK : Z_STREAM_END;\n}\n\nfunction deflateEnd(strm) {\n  var status;\n\n  if (!strm/*== Z_NULL*/ || !strm.state/*== Z_NULL*/) {\n    return Z_STREAM_ERROR;\n  }\n\n  status = strm.state.status;\n  if (status !== INIT_STATE &&\n    status !== EXTRA_STATE &&\n    status !== NAME_STATE &&\n    status !== COMMENT_STATE &&\n    status !== HCRC_STATE &&\n    status !== BUSY_STATE &&\n    status !== FINISH_STATE\n  ) {\n    return err(strm, Z_STREAM_ERROR);\n  }\n\n  strm.state = null;\n\n  return status === BUSY_STATE ? err(strm, Z_DATA_ERROR) : Z_OK;\n}\n\n\n/* =========================================================================\n * Initializes the compression dictionary from the given byte\n * sequence without producing any compressed output.\n */\nfunction deflateSetDictionary(strm, dictionary) {\n  var dictLength = dictionary.length;\n\n  var s;\n  var str, n;\n  var wrap;\n  var avail;\n  var next;\n  var input;\n  var tmpDict;\n\n  if (!strm/*== Z_NULL*/ || !strm.state/*== Z_NULL*/) {\n    return Z_STREAM_ERROR;\n  }\n\n  s = strm.state;\n  wrap = s.wrap;\n\n  if (wrap === 2 || (wrap === 1 && s.status !== INIT_STATE) || s.lookahead) {\n    return Z_STREAM_ERROR;\n  }\n\n  /* when using zlib wrappers, compute Adler-32 for provided dictionary */\n  if (wrap === 1) {\n    /* adler32(strm->adler, dictionary, dictLength); */\n    strm.adler = adler32(strm.adler, dictionary, dictLength, 0);\n  }\n\n  s.wrap = 0;   /* avoid computing Adler-32 in read_buf */\n\n  /* if dictionary would fill window, just replace the history */\n  if (dictLength >= s.w_size) {\n    if (wrap === 0) {            /* already empty otherwise */\n      /*** CLEAR_HASH(s); ***/\n      zero$1(s.head); // Fill with NIL (= 0);\n      s.strstart = 0;\n      s.block_start = 0;\n      s.insert = 0;\n    }\n    /* use the tail */\n    // dictionary = dictionary.slice(dictLength - s.w_size);\n    tmpDict = Buf8(s.w_size);\n    arraySet(tmpDict, dictionary, dictLength - s.w_size, s.w_size, 0);\n    dictionary = tmpDict;\n    dictLength = s.w_size;\n  }\n  /* insert dictionary into window and hash */\n  avail = strm.avail_in;\n  next = strm.next_in;\n  input = strm.input;\n  strm.avail_in = dictLength;\n  strm.next_in = 0;\n  strm.input = dictionary;\n  fill_window(s);\n  while (s.lookahead >= MIN_MATCH$1) {\n    str = s.strstart;\n    n = s.lookahead - (MIN_MATCH$1 - 1);\n    do {\n      /* UPDATE_HASH(s, s->ins_h, s->window[str + MIN_MATCH-1]); */\n      s.ins_h = ((s.ins_h << s.hash_shift) ^ s.window[str + MIN_MATCH$1 - 1]) & s.hash_mask;\n\n      s.prev[str & s.w_mask] = s.head[s.ins_h];\n\n      s.head[s.ins_h] = str;\n      str++;\n    } while (--n);\n    s.strstart = str;\n    s.lookahead = MIN_MATCH$1 - 1;\n    fill_window(s);\n  }\n  s.strstart += s.lookahead;\n  s.block_start = s.strstart;\n  s.insert = s.lookahead;\n  s.lookahead = 0;\n  s.match_length = s.prev_length = MIN_MATCH$1 - 1;\n  s.match_available = 0;\n  strm.next_in = next;\n  strm.input = input;\n  strm.avail_in = avail;\n  s.wrap = wrap;\n  return Z_OK;\n}\n\n/* Not implemented\nexports.deflateBound = deflateBound;\nexports.deflateCopy = deflateCopy;\nexports.deflateParams = deflateParams;\nexports.deflatePending = deflatePending;\nexports.deflatePrime = deflatePrime;\nexports.deflateTune = deflateTune;\n*/\n\n/* eslint-disable */\n\nvar toString$1 = Object.prototype.toString;\n\n/**\n * class Deflate\n *\n * Generic JS-style wrapper for zlib calls. If you don't need\n * streaming behaviour - use more simple functions: [[deflate]],\n * [[deflateRaw]] and [[gzip]].\n **/\n\n/* internal\n * Deflate.chunks -> Array\n *\n * Chunks of output data, if [[Deflate#onData]] not overridden.\n **/\n\n/**\n * Deflate.result -> Uint8Array|Array\n *\n * Compressed result, generated by default [[Deflate#onData]]\n * and [[Deflate#onEnd]] handlers. Filled after you push last chunk\n * (call [[Deflate#push]] with `Z_FINISH` / `true` param)  or if you\n * push a chunk with explicit flush (call [[Deflate#push]] with\n * `Z_SYNC_FLUSH` param).\n **/\n\n/**\n * Deflate.err -> Number\n *\n * Error code after deflate finished. 0 (Z_OK) on success.\n * You will not need it in real life, because deflate errors\n * are possible only on wrong options or bad `onData` / `onEnd`\n * custom handlers.\n **/\n\n/**\n * Deflate.msg -> String\n *\n * Error message, if [[Deflate.err]] != 0\n **/\n\n/**\n * new Deflate(options)\n * - options (Object): zlib deflate options.\n *\n * Creates new deflator instance with specified params. Throws exception\n * on bad params. Supported options:\n *\n * - `level`\n * - `windowBits`\n * - `memLevel`\n * - `strategy`\n * - `dictionary`\n *\n * [http://zlib.net/manual.html#Advanced](http://zlib.net/manual.html#Advanced)\n * for more information on these.\n *\n * Additional options, for internal needs:\n *\n * - `chunkSize` - size of generated data chunks (16K by default)\n * - `raw` (Boolean) - do raw deflate\n * - `gzip` (Boolean) - create gzip wrapper\n * - `to` (String) - if equal to 'string', then result will be \"binary string\"\n *    (each char code [0..255])\n * - `header` (Object) - custom header for gzip\n *   - `text` (Boolean) - true if compressed data believed to be text\n *   - `time` (Number) - modification time, unix timestamp\n *   - `os` (Number) - operation system code\n *   - `extra` (Array) - array of bytes with extra data (max 65536)\n *   - `name` (String) - file name (binary string)\n *   - `comment` (String) - comment (binary string)\n *   - `hcrc` (Boolean) - true if header crc should be added\n *\n * ##### Example:\n *\n * ```javascript\n * var pako = require('pako')\n *   , chunk1 = Uint8Array([1,2,3,4,5,6,7,8,9])\n *   , chunk2 = Uint8Array([10,11,12,13,14,15,16,17,18,19]);\n *\n * var deflate = new pako.Deflate({ level: 3});\n *\n * deflate.push(chunk1, false);\n * deflate.push(chunk2, true);  // true -> last chunk\n *\n * if (deflate.err) { throw new Error(deflate.err); }\n *\n * console.log(deflate.result);\n * ```\n **/\nvar Deflate = function Deflate(options) {\n  this.options = assign({\n    level: Z_DEFAULT_COMPRESSION,\n    method: Z_DEFLATED,\n    chunkSize: 16384,\n    windowBits: 15,\n    memLevel: 8,\n    strategy: Z_DEFAULT_STRATEGY,\n    to: ''\n  }, options || {});\n\n  var opt = this.options;\n\n  if (opt.raw && (opt.windowBits > 0)) {\n    opt.windowBits = -opt.windowBits;\n  }\n\n  else if (opt.gzip && (opt.windowBits > 0) && (opt.windowBits < 16)) {\n    opt.windowBits += 16;\n  }\n\n  this.err  = 0;    // error code, if happens (0 = Z_OK)\n  this.msg  = '';   // error message\n  this.ended= false;// used to avoid multiple onEnd() calls\n  this.chunks = [];   // chunks of compressed data\n\n  this.strm = new ZStream();\n  this.strm.avail_out = 0;\n\n  var status = deflateInit2(\n    this.strm,\n    opt.level,\n    opt.method,\n    opt.windowBits,\n    opt.memLevel,\n    opt.strategy\n  );\n\n  if (status !== Z_OK) {\n    throw new Error(msg[status]);\n  }\n\n  if (opt.header) {\n    deflateSetHeader(this.strm, opt.header);\n  }\n\n  if (opt.dictionary) {\n    var dict;\n    // Convert data if needed\n    if (typeof opt.dictionary === 'string') {\n      // If we need to compress text, change encoding to utf8.\n      dict = string2buf(opt.dictionary);\n    } else if (toString$1.call(opt.dictionary) === '[object ArrayBuffer]') {\n      dict = new Uint8Array(opt.dictionary);\n    } else {\n      dict = opt.dictionary;\n    }\n\n    status = deflateSetDictionary(this.strm, dict);\n\n    if (status !== Z_OK) {\n      throw new Error(msg[status]);\n    }\n\n    this._dict_set = true;\n  }\n};\n\n/**\n * Deflate#push(data[, mode]) -> Boolean\n * - data (Uint8Array|Array|ArrayBuffer|String): input data. Strings will be\n * converted to utf8 byte sequence.\n * - mode (Number|Boolean): 0..6 for corresponding Z_NO_FLUSH..Z_TREE modes.\n * See constants. Skipped or `false` means Z_NO_FLUSH, `true` means Z_FINISH.\n *\n * Sends input data to deflate pipe, generating [[Deflate#onData]] calls with\n * new compressed chunks. Returns `true` on success. The last data block must have\n * mode Z_FINISH (or `true`). That will flush internal pending buffers and call\n * [[Deflate#onEnd]]. For interim explicit flushes (without ending the stream) you\n * can use mode Z_SYNC_FLUSH, keeping the compression context.\n *\n * On fail call [[Deflate#onEnd]] with error code and return false.\n *\n * We strongly recommend to use `Uint8Array` on input for best speed (output\n * array format is detected automatically). Also, don't skip last param and always\n * use the same type in your code (boolean or number). That will improve JS speed.\n *\n * For regular `Array`-s make sure all elements are [0..255].\n *\n * ##### Example\n *\n * ```javascript\n * push(chunk, false); // push one of data chunks\n * ...\n * push(chunk, true);// push last chunk\n * ```\n **/\nDeflate.prototype.push = function push (data, mode) {\n  var strm = this.strm;\n  var chunkSize = this.options.chunkSize;\n  var status, _mode;\n\n  if (this.ended) { return false; }\n\n  _mode = (mode === ~~mode) ? mode : ((mode === true) ? Z_FINISH : Z_NO_FLUSH);\n\n  // Convert data if needed\n  if (typeof data === 'string') {\n    // If we need to compress text, change encoding to utf8.\n    strm.input = string2buf(data);\n  } else if (toString$1.call(data) === '[object ArrayBuffer]') {\n    strm.input = new Uint8Array(data);\n  } else {\n    strm.input = data;\n  }\n\n  strm.next_in = 0;\n  strm.avail_in = strm.input.length;\n\n  do {\n    if (strm.avail_out === 0) {\n      strm.output = Buf8(chunkSize);\n      strm.next_out = 0;\n      strm.avail_out = chunkSize;\n    }\n    status = deflate(strm, _mode);  /* no bad return value */\n\n    if (status !== Z_STREAM_END && status !== Z_OK) {\n      this.onEnd(status);\n      this.ended = true;\n      return false;\n    }\n    if (strm.avail_out === 0 || (strm.avail_in === 0 && (_mode === Z_FINISH || _mode === Z_SYNC_FLUSH))) {\n      if (this.options.to === 'string') {\n        this.onData(buf2binstring(shrinkBuf(strm.output, strm.next_out)));\n      } else {\n        this.onData(shrinkBuf(strm.output, strm.next_out));\n      }\n    }\n  } while ((strm.avail_in > 0 || strm.avail_out === 0) && status !== Z_STREAM_END);\n\n  // Finalize on the last chunk.\n  if (_mode === Z_FINISH) {\n    status = deflateEnd(this.strm);\n    this.onEnd(status);\n    this.ended = true;\n    return status === Z_OK;\n  }\n\n  // callback interim results if Z_SYNC_FLUSH.\n  if (_mode === Z_SYNC_FLUSH) {\n    this.onEnd(Z_OK);\n    strm.avail_out = 0;\n    return true;\n  }\n\n  return true;\n};\n\n\n/**\n * Deflate#onData(chunk) -> Void\n * - chunk (Uint8Array|Array|String): output data. Type of array depends\n * on js engine support. When string output requested, each chunk\n * will be string.\n *\n * By default, stores data blocks in `chunks[]` property and glue\n * those in `onEnd`. Override this handler, if you need another behaviour.\n **/\nDeflate.prototype.onData = function onData (chunk) {\n  this.chunks.push(chunk);\n};\n\n\n/**\n * Deflate#onEnd(status) -> Void\n * - status (Number): deflate status. 0 (Z_OK) on success,\n * other if not.\n *\n * Called once after you tell deflate that the input stream is\n * complete (Z_FINISH) or should be flushed (Z_SYNC_FLUSH)\n * or if an error happened. By default - join collected chunks,\n * free memory and fill `results` / `err` properties.\n **/\nDeflate.prototype.onEnd = function onEnd (status) {\n  // On success - join\n  if (status === Z_OK) {\n    if (this.options.to === 'string') {\n      this.result = this.chunks.join('');\n    } else {\n      this.result = flattenChunks(this.chunks);\n    }\n  }\n  this.chunks = [];\n  this.err = status;\n  this.msg = this.strm.msg;\n};\n\n\n/**\n * deflate(data[, options]) -> Uint8Array|Array|String\n * - data (Uint8Array|Array|String): input data to compress.\n * - options (Object): zlib deflate options.\n *\n * Compress `data` with deflate algorithm and `options`.\n *\n * Supported options are:\n *\n * - level\n * - windowBits\n * - memLevel\n * - strategy\n * - dictionary\n *\n * [http://zlib.net/manual.html#Advanced](http://zlib.net/manual.html#Advanced)\n * for more information on these.\n *\n * Sugar (options):\n *\n * - `raw` (Boolean) - say that we work with raw stream, if you don't wish to specify\n *   negative windowBits implicitly.\n * - `to` (String) - if equal to 'string', then result will be \"binary string\"\n *    (each char code [0..255])\n *\n * ##### Example:\n *\n * ```javascript\n * var pako = require('pako')\n *   , data = Uint8Array([1,2,3,4,5,6,7,8,9]);\n *\n * console.log(pako.deflate(data));\n * ```\n **/\nfunction deflate$1(input, options) {\n  var deflator = new Deflate(options);\n\n  deflator.push(input, true);\n\n  // That will never happens, if you don't cheat with options :)\n  if (deflator.err) { throw deflator.msg || msg[deflator.err]; }\n\n  return deflator.result;\n}\n\n\n/**\n * deflateRaw(data[, options]) -> Uint8Array|Array|String\n * - data (Uint8Array|Array|String): input data to compress.\n * - options (Object): zlib deflate options.\n *\n * The same as [[deflate]], but creates raw data, without wrapper\n * (header and adler32 crc).\n **/\nfunction deflateRaw(input, options) {\n  options = options || {};\n  options.raw = true;\n  return deflate$1(input, options);\n}\n\n\n/**\n * gzip(data[, options]) -> Uint8Array|Array|String\n * - data (Uint8Array|Array|String): input data to compress.\n * - options (Object): zlib deflate options.\n *\n * The same as [[deflate]], but create gzip wrapper instead of\n * deflate one.\n **/\nfunction gzip(input, options) {\n  options = options || {};\n  options.gzip = true;\n  return deflate$1(input, options);\n}\n\nexport { Deflate, Inflate, Z_BEST_COMPRESSION, Z_BEST_SPEED, Z_BINARY, Z_BLOCK, Z_BUF_ERROR, Z_DATA_ERROR, Z_DEFAULT_COMPRESSION, Z_DEFAULT_STRATEGY, Z_DEFLATED, Z_ERRNO, Z_FILTERED, Z_FINISH, Z_FIXED, Z_FULL_FLUSH, Z_HUFFMAN_ONLY, Z_NEED_DICT, Z_NO_COMPRESSION, Z_NO_FLUSH, Z_OK, Z_PARTIAL_FLUSH, Z_RLE, Z_STREAM_END, Z_STREAM_ERROR, Z_SYNC_FLUSH, Z_TEXT, Z_TREES, Z_UNKNOWN, deflate$1 as deflate, deflateRaw, gzip, inflate$1 as inflate, inflateRaw, ungzip };\n","import { Deflate, Inflate } from '@progress/pako-esm';\n\n/**\n * Let the user use/change some implementations.\n */\nvar external = {\n    Promise: Promise\n};\n\nvar support = {\n    base64: true,\n    array: true,\n    string: true,\n    nodebuffer: false,\n    nodestream: false,\n\n    get arraybuffer() {\n        return typeof ArrayBuffer !== \"undefined\" && typeof Uint8Array !== \"undefined\";\n    },\n\n    // Returns true if JSZip can read/generate Uint8Array, false otherwise.\n    get uint8array() {\n        return typeof Uint8Array !== \"undefined\";\n    },\n\n    get blob() {\n        return blob();\n    }\n};\n\nvar blob = function() {\n    var supported;\n\n    if (typeof ArrayBuffer === \"undefined\") {\n        supported = false;\n    } else {\n        var buffer = new ArrayBuffer(0);\n        try {\n            supported = new Blob([ buffer ], {\n                type: \"application/zip\"\n            }).size === 0;\n        } catch (e) {\n            supported = false;\n        }\n    }\n\n    blob = function () { return supported; };\n    return supported;\n};\n\n/* eslint-disable */\n\n// private property\nvar _keyStr = \"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=\";\n\n// public method for encoding\nvar encode = function(input) {\n    var output = [];\n    var chr1, chr2, chr3, enc1, enc2, enc3, enc4;\n    var i = 0, len = input.length, remainingBytes = len;\n\n    var isArray = typeof input !== \"string\";\n    while (i < input.length) {\n        remainingBytes = len - i;\n\n        if (!isArray) {\n            chr1 = input.charCodeAt(i++);\n            chr2 = i < len ? input.charCodeAt(i++) : 0;\n            chr3 = i < len ? input.charCodeAt(i++) : 0;\n        } else {\n            chr1 = input[i++];\n            chr2 = i < len ? input[i++] : 0;\n            chr3 = i < len ? input[i++] : 0;\n        }\n\n        enc1 = chr1 >> 2;\n        enc2 = ((chr1 & 3) << 4) | (chr2 >> 4);\n        enc3 = remainingBytes > 1 ? (((chr2 & 15) << 2) | (chr3 >> 6)) : 64;\n        enc4 = remainingBytes > 2 ? (chr3 & 63) : 64;\n\n        output.push(_keyStr.charAt(enc1) + _keyStr.charAt(enc2) + _keyStr.charAt(enc3) + _keyStr.charAt(enc4));\n\n    }\n\n    return output.join(\"\");\n};\n\n// public method for decoding\nvar decode = function(input) {\n    var chr1, chr2, chr3;\n    var enc1, enc2, enc3, enc4;\n    var i = 0, resultIndex = 0;\n\n    var dataUrlPrefix = \"data:\";\n\n    if (input.substr(0, dataUrlPrefix.length) === dataUrlPrefix) {\n        // This is a common error: people give a data url\n        // (data:image/png;base64,iVBOR...) with a {base64: true} and\n        // wonders why things don't work.\n        // We can detect that the string input looks like a data url but we\n        // *can't* be sure it is one: removing everything up to the comma would\n        // be too dangerous.\n        throw new Error(\"Invalid base64 input, it looks like a data url.\");\n    }\n\n    input = input.replace(/[^A-Za-z0-9\\+\\/\\=]/g, \"\");\n\n    var totalLength = input.length * 3 / 4;\n    if(input.charAt(input.length - 1) === _keyStr.charAt(64)) {\n        totalLength--;\n    }\n    if(input.charAt(input.length - 2) === _keyStr.charAt(64)) {\n        totalLength--;\n    }\n    if (totalLength % 1 !== 0) {\n        // totalLength is not an integer, the length does not match a valid\n        // base64 content. That can happen if:\n        // - the input is not a base64 content\n        // - the input is *almost* a base64 content, with a extra chars at the\n        //   beginning or at the end\n        // - the input uses a base64 letiant (base64url for example)\n        throw new Error(\"Invalid base64 input, bad content length.\");\n    }\n    var output;\n    if (support.uint8array) {\n        output = new Uint8Array(totalLength|0);\n    } else {\n        output = new Array(totalLength|0);\n    }\n\n    while (i < input.length) {\n\n        enc1 = _keyStr.indexOf(input.charAt(i++));\n        enc2 = _keyStr.indexOf(input.charAt(i++));\n        enc3 = _keyStr.indexOf(input.charAt(i++));\n        enc4 = _keyStr.indexOf(input.charAt(i++));\n\n        chr1 = (enc1 << 2) | (enc2 >> 4);\n        chr2 = ((enc2 & 15) << 4) | (enc3 >> 2);\n        chr3 = ((enc3 & 3) << 6) | enc4;\n\n        output[resultIndex++] = chr1;\n\n        if (enc3 !== 64) {\n            output[resultIndex++] = chr2;\n        }\n        if (enc4 !== 64) {\n            output[resultIndex++] = chr3;\n        }\n\n    }\n\n    return output;\n};\n\n/* eslint-disable */\n\n/**\n * Convert a string that pass as a \"binary string\": it should represent a byte\n * array but may have > 255 char codes. Be sure to take only the first byte\n * and returns the byte array.\n * @param {String} str the string to transform.\n * @return {Array|Uint8Array} the string in a binary format.\n */\nfunction string2binary(str) {\n    var result = null;\n    if (support.uint8array) {\n      result = new Uint8Array(str.length);\n    } else {\n      result = new Array(str.length);\n    }\n    return stringToArrayLike(str, result);\n}\n\n/**\n * Create a new blob with the given content and the given type.\n * @param {String|ArrayBuffer} part the content to put in the blob. DO NOT use\n * an Uint8Array because the stock browser of android 4 won't accept it (it\n * will be silently converted to a string, \"[object Uint8Array]\").\n *\n * Use only ONE part to build the blob to avoid a memory leak in IE11 / Edge:\n * when a large amount of Array is used to create the Blob, the amount of\n * memory consumed is nearly 100 times the original data amount.\n *\n * @param {String} type the mime type of the blob.\n * @return {Blob} the created blob.\n */\nvar newBlob = function(part, type) {\n    checkSupport(\"blob\");\n\n    // Blob constructor\n    return new Blob([part], {\n        type: type\n    });\n};\n\n/**\n * The identity function.\n * @param {Object} input the input.\n * @return {Object} the same input.\n */\nfunction identity(input) {\n    return input;\n}\n\n/**\n * Fill in an array with a string.\n * @param {String} str the string to use.\n * @param {Array|ArrayBuffer|Uint8Array|Buffer} array the array to fill in (will be mutated).\n * @return {Array|ArrayBuffer|Uint8Array|Buffer} the updated array.\n */\nfunction stringToArrayLike(str, array) {\n    for (var i = 0; i < str.length; ++i) {\n        array[i] = str.charCodeAt(i) & 0xFF;\n    }\n    return array;\n}\n\n/**\n * Transform an array of int into a string, chunk by chunk.\n * See the performances notes on arrayLikeToString.\n * @param {Array|ArrayBuffer|Uint8Array|Buffer} array the array to transform.\n * @param {String} type the type of the array.\n * @param {Integer} chunk the chunk size.\n * @return {String} the resulting string.\n * @throws Error if the chunk is too big for the stack.\n */\nfunction stringifyByChunk(array, type, chunk) {\n    var result = [], k = 0, len = array.length;\n    // shortcut\n    if (len <= chunk) {\n        return String.fromCharCode.apply(null, array);\n    }\n    while (k < len) {\n        if (type === \"array\") {\n            result.push(String.fromCharCode.apply(null, array.slice(k, Math.min(k + chunk, len))));\n        }\n        else {\n            result.push(String.fromCharCode.apply(null, array.subarray(k, Math.min(k + chunk, len))));\n        }\n        k += chunk;\n    }\n    return result.join(\"\");\n}\n\n/**\n * Call String.fromCharCode on every item in the array.\n * This is the naive implementation, which generate A LOT of intermediate string.\n * This should be used when everything else fail.\n * @param {Array|ArrayBuffer|Uint8Array|Buffer} array the array to transform.\n * @return {String} the result.\n */\nfunction stringifyByChar(array) {\n    var resultStr = \"\";\n    for(var i = 0; i < array.length; i++) {\n        resultStr += String.fromCharCode(array[i]);\n    }\n    return resultStr;\n}\n\n/**\n * true if the browser accepts to use String.fromCharCode on Uint8Array\n */\nvar fromCharCodeSupportsTypedArrays = function () {\n    var supported;\n    try {\n        supported = support.uint8array && String.fromCharCode.apply(null, new Uint8Array(1)).length === 1;\n    } catch (e) {\n        supported = false;\n    }\n\n    fromCharCodeSupportsTypedArrays = function () { return supported; };\n    return supported;\n};\n\n/**\n * Transform an array-like object to a string.\n * @param {Array|ArrayBuffer|Uint8Array|Buffer} array the array to transform.\n * @return {String} the result.\n */\nfunction arrayLikeToString(array) {\n    // Performances notes :\n    // --------------------\n    // String.fromCharCode.apply(null, array) is the fastest, see\n    // see http://jsperf.com/converting-a-uint8array-to-a-string/2\n    // but the stack is limited (and we can get huge arrays !).\n    //\n    // result += String.fromCharCode(array[i]); generate too many strings !\n    //\n    // This code is inspired by http://jsperf.com/arraybuffer-to-string-apply-performance/2\n    // TODO : we now have workers that split the work. Do we still need that ?\n    var chunk = 65536,\n        type = getTypeOf(array),\n        canUseApply = true;\n    if (type === \"uint8array\") {\n        canUseApply = fromCharCodeSupportsTypedArrays();\n    }\n\n    if (canUseApply) {\n        while (chunk > 1) {\n            try {\n                return stringifyByChunk(array, type, chunk);\n            } catch (e) {\n                chunk = Math.floor(chunk / 2);\n            }\n        }\n    }\n\n    // no apply or chunk error : slow and painful algorithm\n    // default browser on android 4.*\n    return stringifyByChar(array);\n}\n\nvar applyFromCharCode = arrayLikeToString;\n\n\n/**\n * Copy the data from an array-like to an other array-like.\n * @param {Array|ArrayBuffer|Uint8Array|Buffer} arrayFrom the origin array.\n * @param {Array|ArrayBuffer|Uint8Array|Buffer} arrayTo the destination array which will be mutated.\n * @return {Array|ArrayBuffer|Uint8Array|Buffer} the updated destination array.\n */\nfunction arrayLikeToArrayLike(arrayFrom, arrayTo) {\n    for (var i = 0; i < arrayFrom.length; i++) {\n        arrayTo[i] = arrayFrom[i];\n    }\n    return arrayTo;\n}\n\n// a matrix containing functions to transform everything into everything.\nvar transform = {\n    // string to ?\n    \"string\": {\n        \"string\": identity,\n        \"array\": function(input) {\n            return stringToArrayLike(input, new Array(input.length));\n        },\n        \"arraybuffer\": function(input) {\n            return transform[\"string\"][\"uint8array\"](input).buffer;\n        },\n        \"uint8array\": function(input) {\n            return stringToArrayLike(input, new Uint8Array(input.length));\n        }\n    },\n\n    // array to ?\n    \"array\": {\n        \"string\": arrayLikeToString,\n        \"array\": identity,\n        \"arraybuffer\": function(input) {\n            return (new Uint8Array(input)).buffer;\n        },\n        \"uint8array\": function(input) {\n            return new Uint8Array(input);\n        }\n    },\n\n    // arraybuffer to ?\n    \"arraybuffer\": {\n        \"string\": function(input) {\n            return arrayLikeToString(new Uint8Array(input));\n        },\n        \"array\": function(input) {\n            return arrayLikeToArrayLike(new Uint8Array(input), new Array(input.byteLength));\n        },\n        \"arraybuffer\": identity,\n        \"uint8array\": function(input) {\n            return new Uint8Array(input);\n        }\n    },\n\n    // uint8array to ?\n    \"uint8array\": {\n        \"string\": arrayLikeToString,\n        \"array\": function(input) {\n            return arrayLikeToArrayLike(input, new Array(input.length));\n        },\n        \"arraybuffer\": function(input) {\n            return input.buffer;\n        },\n        \"uint8array\": identity\n    }\n};\n\n/**\n * Transform an input into any type.\n * The supported output type are : string, array, uint8array, arraybuffer.\n * If no output type is specified, the unmodified input will be returned.\n * @param {String} outputType the output type.\n * @param {String|Array|ArrayBuffer|Uint8Array|Buffer} input the input to convert.\n * @throws {Error} an Error if the browser doesn't support the requested output type.\n */\nvar transformTo = function(outputType, input) {\n    if (!input) {\n        // undefined, null, etc\n        // an empty string won't harm.\n        input = \"\";\n    }\n    if (!outputType) {\n        return input;\n    }\n    checkSupport(outputType);\n    var inputType = getTypeOf(input);\n    var result = transform[inputType][outputType](input);\n    return result;\n};\n\n/**\n * Return the type of the input.\n * The type will be in a format valid for JSZip.utils.transformTo : string, array, uint8array, arraybuffer.\n * @param {Object} input the input to identify.\n * @return {String} the (lowercase) type of the input.\n */\nvar getTypeOf = function(input) {\n    if (typeof input === \"string\") {\n        return \"string\";\n    }\n    if (Object.prototype.toString.call(input) === \"[object Array]\") {\n        return \"array\";\n    }\n    if (support.uint8array && input instanceof Uint8Array) {\n        return \"uint8array\";\n    }\n    if (support.arraybuffer && input instanceof ArrayBuffer) {\n        return \"arraybuffer\";\n    }\n};\n\n/**\n * Throw an exception if the type is not supported.\n * @param {String} type the type to check.\n * @throws {Error} an Error if the browser doesn't support the requested type.\n */\nvar checkSupport = function(type) {\n    var supported = support[type.toLowerCase()];\n    if (!supported) {\n        throw new Error(type + \" is not supported by this platform\");\n    }\n};\n\nvar MAX_VALUE_16BITS = 65535;\nvar MAX_VALUE_32BITS = -1; // well, \"\\xFF\\xFF\\xFF\\xFF\\xFF\\xFF\\xFF\\xFF\" is parsed as -1\n\n/**\n * Prettify a string read as binary.\n * @param {string} str the string to prettify.\n * @return {string} a pretty string.\n */\nvar pretty = function(str) {\n    var res = '',\n        code, i;\n    for (i = 0; i < (str || \"\").length; i++) {\n        code = str.charCodeAt(i);\n        res += '\\\\x' + (code < 16 ? \"0\" : \"\") + code.toString(16).toUpperCase();\n    }\n    return res;\n};\n\n/**\n * Defer the call of a function.\n * @param {Function} callback the function to call asynchronously.\n * @param {Array} args the arguments to give to the callback.\n */\nvar delay = function(callback, args, self) {\n    setTimeout(function() {\n        callback.apply(self || null, args || []);\n    }, 0);\n};\n\n/**\n * Merge the objects passed as parameters into a new one.\n * @private\n * @param {...Object} var_args All objects to merge.\n * @return {Object} a new object with the data of the others.\n */\nvar extend = function() {\n    var arguments$1 = arguments;\n\n    var result = {}, i, attr;\n    for (i = 0; i < arguments.length; i++) { // arguments is not enumerable in some browsers\n        for (attr in arguments[i]) {\n            if (Object.hasOwnProperty.call(arguments$1[i], attr) && typeof result[attr] === \"undefined\") {\n                result[attr] = arguments$1[i][attr];\n            }\n        }\n    }\n    return result;\n};\n\n/**\n * Transform arbitrary content into a Promise.\n * @param {String} name a name for the content being processed.\n * @param {Object} inputData the content to process.\n * @param {Boolean} isBinary true if the content is not an unicode string\n * @param {Boolean} isOptimizedBinaryString true if the string content only has one byte per character.\n * @param {Boolean} isBase64 true if the string content is encoded with base64.\n * @return {Promise} a promise in a format usable by JSZip.\n */\nvar prepareContent = function(name, inputData, isBinary, isOptimizedBinaryString, isBase64) {\n\n    // if inputData is already a promise, this flatten it.\n    var promise = external.Promise.resolve(inputData).then(function(data) {\n\n\n        var isBlob = support.blob && (data instanceof Blob || ['[object File]', '[object Blob]'].indexOf(Object.prototype.toString.call(data)) !== -1);\n\n        if (isBlob && typeof FileReader !== \"undefined\") {\n            return new external.Promise(function (resolve, reject) {\n                var reader = new FileReader();\n\n                reader.onload = function(e) {\n                    resolve(e.target.result);\n                };\n                reader.onerror = function(e) {\n                    reject(e.target.error);\n                };\n                reader.readAsArrayBuffer(data);\n            });\n        } else {\n            return data;\n        }\n    });\n\n    return promise.then(function(data) {\n        var dataType = getTypeOf(data);\n\n        if (!dataType) {\n            return external.Promise.reject(\n                new Error(\"Can't read the data of '\" + name + \"'. Is it \" +\n                          \"in a supported JavaScript type (String, Blob, ArrayBuffer, etc) ?\")\n            );\n        }\n        // special case : it's way easier to work with Uint8Array than with ArrayBuffer\n        if (dataType === \"arraybuffer\") {\n            data = transformTo(\"uint8array\", data);\n        } else if (dataType === \"string\") {\n            if (isBase64) {\n                data = decode(data);\n            }\n            else if (isBinary) {\n                // optimizedBinaryString === true means that the file has already been filtered with a 0xFF mask\n                if (isOptimizedBinaryString !== true) {\n                    // this is a string, not in a base64 format.\n                    // Be sure that this is a correct \"binary string\"\n                    data = string2binary(data);\n                }\n            }\n        }\n        return data;\n    });\n};\n\n/* eslint-disable */\n\n/**\n * A worker that does nothing but passing chunks to the next one. This is like\n * a nodejs stream but with some differences. On the good side :\n * - it works on IE 6-9 without any issue / polyfill\n * - it weights less than the full dependencies bundled with browserify\n * - it forwards errors (no need to declare an error handler EVERYWHERE)\n *\n * A chunk is an object with 2 attributes : `meta` and `data`. The former is an\n * object containing anything (`percent` for example), see each worker for more\n * details. The latter is the real data (String, Uint8Array, etc).\n *\n * @constructor\n * @param {String} name the name of the stream (mainly used for debugging purposes)\n */\nvar GenericWorker = function GenericWorker(name) {\n    // the name of the worker\n    this.name = name || \"default\";\n    // an object containing metadata about the workers chain\n    this.streamInfo = {};\n    // an error which happened when the worker was paused\n    this.generatedError = null;\n    // an object containing metadata to be merged by this worker into the general metadata\n    this.extraStreamInfo = {};\n    // true if the stream is paused (and should not do anything), false otherwise\n    this.isPaused = true;\n    // true if the stream is finished (and should not do anything), false otherwise\n    this.isFinished = false;\n    // true if the stream is locked to prevent further structure updates (pipe), false otherwise\n    this.isLocked = false;\n    // the event listeners\n    this._listeners = {\n        'data':[],\n        'end':[],\n        'error':[]\n    };\n    // the previous worker, if any\n    this.previous = null;\n};\n\n/**\n * Push a chunk to the next workers.\n * @param {Object} chunk the chunk to push\n */\nGenericWorker.prototype.push = function push (chunk) {\n    this.emit(\"data\", chunk);\n};\n\n/**\n * End the stream.\n * @return {Boolean} true if this call ended the worker, false otherwise.\n */\nGenericWorker.prototype.end = function end () {\n    if (this.isFinished) {\n        return false;\n    }\n\n    this.flush();\n    try {\n        this.emit(\"end\");\n        this.cleanUp();\n        this.isFinished = true;\n    } catch (e) {\n        this.emit(\"error\", e);\n    }\n    return true;\n};\n\n/**\n * End the stream with an error.\n * @param {Error} e the error which caused the premature end.\n * @return {Boolean} true if this call ended the worker with an error, false otherwise.\n */\nGenericWorker.prototype.error = function error (e) {\n    if (this.isFinished) {\n        return false;\n    }\n\n    if(this.isPaused) {\n        this.generatedError = e;\n    } else {\n        this.isFinished = true;\n\n        this.emit(\"error\", e);\n\n        // in the workers chain exploded in the middle of the chain,\n        // the error event will go downward but we also need to notify\n        // workers upward that there has been an error.\n        if(this.previous) {\n            this.previous.error(e);\n        }\n\n        this.cleanUp();\n    }\n    return true;\n};\n\n/**\n * Add a callback on an event.\n * @param {String} name the name of the event (data, end, error)\n * @param {Function} listener the function to call when the event is triggered\n * @return {GenericWorker} the current object for chainability\n */\nGenericWorker.prototype.on = function on (name, listener) {\n    this._listeners[name].push(listener);\n    return this;\n};\n\n/**\n * Clean any references when a worker is ending.\n */\nGenericWorker.prototype.cleanUp = function cleanUp () {\n    this.streamInfo = this.generatedError = this.extraStreamInfo = null;\n    this._listeners = [];\n};\n\n/**\n * Trigger an event. This will call registered callback with the provided arg.\n * @param {String} name the name of the event (data, end, error)\n * @param {Object} arg the argument to call the callback with.\n */\nGenericWorker.prototype.emit = function emit (name, arg) {\n    if (this._listeners[name]) {\n        for(var i = 0; i < this._listeners[name].length; i++) {\n            this._listeners[name][i].call(this, arg);\n        }\n    }\n};\n\n/**\n * Chain a worker with an other.\n * @param {Worker} next the worker receiving events from the current one.\n * @return {worker} the next worker for chainability\n */\nGenericWorker.prototype.pipe = function pipe (next) {\n    return next.registerPrevious(this);\n};\n\n/**\n * Same as `pipe` in the other direction.\n * Using an API with `pipe(next)` is very easy.\n * Implementing the API with the point of view of the next one registering\n * a source is easier, see the ZipFileWorker.\n * @param {Worker} previous the previous worker, sending events to this one\n * @return {Worker} the current worker for chainability\n */\nGenericWorker.prototype.registerPrevious = function registerPrevious (previous) {\n    if (this.isLocked) {\n        throw new Error(\"The stream '\" + this + \"' has already been used.\");\n    }\n\n    // sharing the streamInfo...\n    this.streamInfo = previous.streamInfo;\n    // ... and adding our own bits\n    this.mergeStreamInfo();\n    this.previous =  previous;\n    var self = this;\n    previous.on('data', function (chunk) {\n        self.processChunk(chunk);\n    });\n    previous.on('end', function () {\n        self.end();\n    });\n    previous.on('error', function (e) {\n        self.error(e);\n    });\n    return this;\n};\n\n/**\n * Pause the stream so it doesn't send events anymore.\n * @return {Boolean} true if this call paused the worker, false otherwise.\n */\nGenericWorker.prototype.pause = function pause () {\n    if(this.isPaused || this.isFinished) {\n        return false;\n    }\n    this.isPaused = true;\n\n    if(this.previous) {\n        this.previous.pause();\n    }\n    return true;\n};\n\n/**\n * Resume a paused stream.\n * @return {Boolean} true if this call resumed the worker, false otherwise.\n */\nGenericWorker.prototype.resume = function resume () {\n    if(!this.isPaused || this.isFinished) {\n        return false;\n    }\n    this.isPaused = false;\n\n    // if true, the worker tried to resume but failed\n    var withError = false;\n    if(this.generatedError) {\n        this.error(this.generatedError);\n        withError = true;\n    }\n    if(this.previous) {\n        this.previous.resume();\n    }\n\n    return !withError;\n};\n\n/**\n * Flush any remaining bytes as the stream is ending.\n */\nGenericWorker.prototype.flush = function flush () {};\n\n/**\n * Process a chunk. This is usually the method overridden.\n * @param {Object} chunk the chunk to process.\n */\nGenericWorker.prototype.processChunk = function processChunk (chunk) {\n    this.push(chunk);\n};\n\n/**\n * Add a key/value to be added in the workers chain streamInfo once activated.\n * @param {String} key the key to use\n * @param {Object} value the associated value\n * @return {Worker} the current worker for chainability\n */\nGenericWorker.prototype.withStreamInfo = function withStreamInfo (key, value) {\n    this.extraStreamInfo[key] = value;\n    this.mergeStreamInfo();\n    return this;\n};\n\n/**\n * Merge this worker's streamInfo into the chain's streamInfo.\n */\nGenericWorker.prototype.mergeStreamInfo = function mergeStreamInfo () {\n    for(var key in this.extraStreamInfo) {\n        if (!this.extraStreamInfo.hasOwnProperty(key)) {\n            continue;\n        }\n        this.streamInfo[key] = this.extraStreamInfo[key];\n    }\n};\n\n/**\n * Lock the stream to prevent further updates on the workers chain.\n * After calling this method, all calls to pipe will fail.\n */\nGenericWorker.prototype.lock = function lock () {\n    if (this.isLocked) {\n        throw new Error(\"The stream '\" + this + \"' has already been used.\");\n    }\n    this.isLocked = true;\n    if (this.previous) {\n        this.previous.lock();\n    }\n};\n\n/**\n *\n * Pretty print the workers chain.\n */\nGenericWorker.prototype.toString = function toString () {\n    var me = \"Worker \" + this.name;\n    if (this.previous) {\n        return this.previous + \" -> \" + me;\n    } else {\n        return me;\n    }\n};\n\n/* eslint-disable */\n\n/**\n * The following functions come from pako, from pako/lib/utils/strings\n * released under the MIT license, see pako https://github.com/nodeca/pako/\n */\n\n// Returns the utf8 lengths (calculated by first byte of sequence)\n// Note, that 5 & 6-byte values and some 4-byte values can not be represented in JS,\n// because max possible codepoint is 0x10ffff\nvar utf8len = function(c) {\n    var _utf8len = new Array(256);\n    for (var i = 0; i < 256; i++) {\n        _utf8len[i] = (i >= 252 ? 6 : i >= 248 ? 5 : i >= 240 ? 4 : i >= 224 ? 3 : i >= 192 ? 2 : 1);\n    }\n    _utf8len[254] = _utf8len[254] = 1; // Invalid sequence start\n\n    // Memoize table after first call\n    utf8len = function(c) {\n        return _utf8len[c];\n    };\n\n    return _utf8len[c];\n};\n\n// convert string to array (typed, when possible)\nvar string2buf = function (str) {\n    var buf, c, c2, m_pos, i, str_len = str.length, buf_len = 0;\n\n    // count binary size\n    for (m_pos = 0; m_pos < str_len; m_pos++) {\n        c = str.charCodeAt(m_pos);\n        if ((c & 0xfc00) === 0xd800 && (m_pos+1 < str_len)) {\n            c2 = str.charCodeAt(m_pos+1);\n            if ((c2 & 0xfc00) === 0xdc00) {\n                c = 0x10000 + ((c - 0xd800) << 10) + (c2 - 0xdc00);\n                m_pos++;\n            }\n        }\n        buf_len += c < 0x80 ? 1 : c < 0x800 ? 2 : c < 0x10000 ? 3 : 4;\n    }\n\n    // allocate buffer\n    if (support.uint8array) {\n        buf = new Uint8Array(buf_len);\n    } else {\n        buf = new Array(buf_len);\n    }\n\n    // convert\n    for (i=0, m_pos = 0; i < buf_len; m_pos++) {\n        c = str.charCodeAt(m_pos);\n        if ((c & 0xfc00) === 0xd800 && (m_pos+1 < str_len)) {\n            c2 = str.charCodeAt(m_pos+1);\n            if ((c2 & 0xfc00) === 0xdc00) {\n                c = 0x10000 + ((c - 0xd800) << 10) + (c2 - 0xdc00);\n                m_pos++;\n            }\n        }\n        if (c < 0x80) {\n            /* one byte */\n            buf[i++] = c;\n        } else if (c < 0x800) {\n            /* two bytes */\n            buf[i++] = 0xC0 | (c >>> 6);\n            buf[i++] = 0x80 | (c & 0x3f);\n        } else if (c < 0x10000) {\n            /* three bytes */\n            buf[i++] = 0xE0 | (c >>> 12);\n            buf[i++] = 0x80 | (c >>> 6 & 0x3f);\n            buf[i++] = 0x80 | (c & 0x3f);\n        } else {\n            /* four bytes */\n            buf[i++] = 0xf0 | (c >>> 18);\n            buf[i++] = 0x80 | (c >>> 12 & 0x3f);\n            buf[i++] = 0x80 | (c >>> 6 & 0x3f);\n            buf[i++] = 0x80 | (c & 0x3f);\n        }\n    }\n\n    return buf;\n};\n\n// Calculate max possible position in utf8 buffer,\n// that will not break sequence. If that's not possible\n// - (very small limits) return max size as is.\n//\n// buf[] - utf8 bytes array\n// max   - length limit (mandatory);\nvar utf8border = function(buf, max) {\n    var pos;\n\n    max = max || buf.length;\n    if (max > buf.length) { max = buf.length; }\n\n    // go back from last position, until start of sequence found\n    pos = max-1;\n    while (pos >= 0 && (buf[pos] & 0xC0) === 0x80) { pos--; }\n\n    // Fuckup - very small and broken sequence,\n    // return max, because we should return something anyway.\n    if (pos < 0) { return max; }\n\n    // If we came to start of buffer - that means vuffer is too small,\n    // return max too.\n    if (pos === 0) { return max; }\n\n    return (pos + utf8len(buf[pos]) > max) ? pos : max;\n};\n\n// convert array to string\nvar buf2string = function (buf) {\n    var i, out, c, c_len;\n    var len = buf.length;\n\n    // Reserve max possible length (2 words per char)\n    // NB: by unknown reasons, Array is significantly faster for\n    //     String.fromCharCode.apply than Uint16Array.\n    var utf16buf = new Array(len*2);\n\n    for (out=0, i=0; i<len;) {\n        c = buf[i++];\n        // quick process ascii\n        if (c < 0x80) { utf16buf[out++] = c; continue; }\n\n        c_len = utf8len(c);\n        // skip 5 & 6 byte codes\n        if (c_len > 4) { utf16buf[out++] = 0xfffd; i += c_len-1; continue; }\n\n        // apply mask on first byte\n        c &= c_len === 2 ? 0x1f : c_len === 3 ? 0x0f : 0x07;\n        // join the rest\n        while (c_len > 1 && i < len) {\n            c = (c << 6) | (buf[i++] & 0x3f);\n            c_len--;\n        }\n\n        // terminated by end of string?\n        if (c_len > 1) { utf16buf[out++] = 0xfffd; continue; }\n\n        if (c < 0x10000) {\n            utf16buf[out++] = c;\n        } else {\n            c -= 0x10000;\n            utf16buf[out++] = 0xd800 | ((c >> 10) & 0x3ff);\n            utf16buf[out++] = 0xdc00 | (c & 0x3ff);\n        }\n    }\n\n    // shrinkBuf(utf16buf, out)\n    if (utf16buf.length !== out) {\n        if(utf16buf.subarray) {\n            utf16buf = utf16buf.subarray(0, out);\n        } else {\n            utf16buf.length = out;\n        }\n    }\n\n    // return String.fromCharCode.apply(null, utf16buf);\n    return applyFromCharCode(utf16buf);\n};\n\n\n// That's all for the pako functions.\n\n\n/**\n * Transform a javascript string into an array (typed if possible) of bytes,\n * UTF-8 encoded.\n * @param {String} str the string to encode\n * @return {Array|Uint8Array|Buffer} the UTF-8 encoded string.\n */\nvar utf8encode = function utf8encode(str) {\n    return string2buf(str);\n};\n\n/**\n * Transform a bytes array (or a representation) representing an UTF-8 encoded\n * string into a javascript string.\n * @param {Array|Uint8Array|Buffer} buf the data de decode\n * @return {String} the decoded string.\n */\nvar utf8decode = function utf8decode(buf) {\n    buf = transformTo(support.uint8array ? \"uint8array\" : \"array\", buf);\n\n    return buf2string(buf);\n};\n\n/**\n * A worker to decode utf8 encoded binary chunks into string chunks.\n * @constructor\n */\nvar Utf8DecodeWorker = /*@__PURE__*/(function (GenericWorker) {\n    function Utf8DecodeWorker() {\n        GenericWorker.call(this, \"utf-8 decode\");\n\n        // the last bytes if a chunk didn't end with a complete codepoint.\n        this.leftOver = null;\n    }\n\n    if ( GenericWorker ) Utf8DecodeWorker.__proto__ = GenericWorker;\n    Utf8DecodeWorker.prototype = Object.create( GenericWorker && GenericWorker.prototype );\n    Utf8DecodeWorker.prototype.constructor = Utf8DecodeWorker;\n\n    /**\n     * @see GenericWorker.processChunk\n     */\n    Utf8DecodeWorker.prototype.processChunk = function processChunk (chunk) {\n        var data = transformTo(support.uint8array ? \"uint8array\" : \"array\", chunk.data);\n\n        // 1st step, re-use what's left of the previous chunk\n        if (this.leftOver && this.leftOver.length) {\n            if(support.uint8array) {\n                var previousData = data;\n                data = new Uint8Array(previousData.length + this.leftOver.length);\n                data.set(this.leftOver, 0);\n                data.set(previousData, this.leftOver.length);\n            } else {\n                data = this.leftOver.concat(data);\n            }\n            this.leftOver = null;\n        }\n\n        var nextBoundary = utf8border(data);\n        var usableData = data;\n        if (nextBoundary !== data.length) {\n            if (support.uint8array) {\n                usableData = data.subarray(0, nextBoundary);\n                this.leftOver = data.subarray(nextBoundary, data.length);\n            } else {\n                usableData = data.slice(0, nextBoundary);\n                this.leftOver = data.slice(nextBoundary, data.length);\n            }\n        }\n\n        this.push({\n            data : utf8decode(usableData),\n            meta : chunk.meta\n        });\n    };\n\n    /**\n     * @see GenericWorker.flush\n     */\n    Utf8DecodeWorker.prototype.flush = function flush () {\n        if (this.leftOver && this.leftOver.length) {\n            this.push({\n                data : utf8decode(this.leftOver),\n                meta : {}\n            });\n            this.leftOver = null;\n        }\n    };\n\n    return Utf8DecodeWorker;\n}(GenericWorker));\n\n/**\n * A worker to endcode string chunks into utf8 encoded binary chunks.\n * @constructor\n */\nvar Utf8EncodeWorker = /*@__PURE__*/(function (GenericWorker) {\n    function Utf8EncodeWorker() {\n        GenericWorker.call(this, \"utf-8 encode\");\n    }\n\n    if ( GenericWorker ) Utf8EncodeWorker.__proto__ = GenericWorker;\n    Utf8EncodeWorker.prototype = Object.create( GenericWorker && GenericWorker.prototype );\n    Utf8EncodeWorker.prototype.constructor = Utf8EncodeWorker;\n\n    /**\n     * @see GenericWorker.processChunk\n     */\n    Utf8EncodeWorker.prototype.processChunk = function processChunk (chunk) {\n        this.push({\n            data: utf8encode(chunk.data),\n            meta: chunk.meta\n        });\n    };\n\n    return Utf8EncodeWorker;\n}(GenericWorker));\n\n/**\n * A worker which convert chunks to a specified type.\n * @constructor\n * @param {String} destType the destination type.\n */\nvar ConvertWorker = /*@__PURE__*/(function (GenericWorker) {\n    function ConvertWorker(destType) {\n        GenericWorker.call(this, \"ConvertWorker to \" + destType);\n        this.destType = destType;\n    }\n\n    if ( GenericWorker ) ConvertWorker.__proto__ = GenericWorker;\n    ConvertWorker.prototype = Object.create( GenericWorker && GenericWorker.prototype );\n    ConvertWorker.prototype.constructor = ConvertWorker;\n\n    /**\n     * @see GenericWorker.processChunk\n     */\n    ConvertWorker.prototype.processChunk = function processChunk (chunk) {\n        this.push({\n            data: transformTo(this.destType, chunk.data),\n            meta: chunk.meta\n        });\n    };\n\n    return ConvertWorker;\n}(GenericWorker));\n\n/* eslint-disable */\n\n/**\n * Apply the final transformation of the data. If the user wants a Blob for\n * example, it's easier to work with an U8intArray and finally do the\n * ArrayBuffer/Blob conversion.\n * @param {String} type the name of the final type\n * @param {String|Uint8Array|Buffer} content the content to transform\n * @param {String} mimeType the mime type of the content, if applicable.\n * @return {String|Uint8Array|ArrayBuffer|Buffer|Blob} the content in the right format.\n */\nfunction transformZipOutput(type, content, mimeType) {\n    switch(type) {\n        case \"blob\" :\n            return newBlob(transformTo(\"arraybuffer\", content), mimeType);\n        case \"base64\" :\n            return encode(content);\n        default :\n            return transformTo(type, content);\n    }\n}\n\n/**\n * Concatenate an array of data of the given type.\n * @param {String} type the type of the data in the given array.\n * @param {Array} dataArray the array containing the data chunks to concatenate\n * @return {String|Uint8Array|Buffer} the concatenated data\n * @throws Error if the asked type is unsupported\n */\nfunction concat (type, dataArray) {\n    var i, index = 0, res = null, totalLength = 0;\n    for(i = 0; i < dataArray.length; i++) {\n        totalLength += dataArray[i].length;\n    }\n    switch(type) {\n        case \"string\":\n            return dataArray.join(\"\");\n          case \"array\":\n            return Array.prototype.concat.apply([], dataArray);\n        case \"uint8array\":\n            res = new Uint8Array(totalLength);\n            for(i = 0; i < dataArray.length; i++) {\n                res.set(dataArray[i], index);\n                index += dataArray[i].length;\n            }\n            return res;\n        default:\n            throw new Error(\"concat : unsupported type '\"  + type + \"'\");\n    }\n}\n\n/**\n * Listen a StreamHelper, accumulate its content and concatenate it into a\n * complete block.\n * @param {StreamHelper} helper the helper to use.\n * @param {Function} updateCallback a callback called on each update. Called\n * with one arg :\n * - the metadata linked to the update received.\n * @return Promise the promise for the accumulation.\n */\nfunction accumulate(helper, updateCallback) {\n    return new external.Promise(function (resolve, reject){\n        var dataArray = [];\n        var chunkType = helper._internalType,\n            resultType = helper._outputType,\n            mimeType = helper._mimeType;\n        helper\n        .on('data', function (data, meta) {\n            dataArray.push(data);\n            if(updateCallback) {\n                updateCallback(meta);\n            }\n        })\n        .on('error', function(err) {\n            dataArray = [];\n            reject(err);\n        })\n        .on('end', function (){\n            try {\n                var result = transformZipOutput(resultType, concat(chunkType, dataArray), mimeType);\n                resolve(result);\n            } catch (e) {\n                reject(e);\n            }\n            dataArray = [];\n        })\n        .resume();\n    });\n}\n\n/**\n * An helper to easily use workers outside of JSZip.\n * @constructor\n * @param {Worker} worker the worker to wrap\n * @param {String} outputType the type of data expected by the use\n * @param {String} mimeType the mime type of the content, if applicable.\n */\nvar StreamHelper = function StreamHelper (worker, outputType, mimeType) {\n    var internalType = outputType;\n    switch(outputType) {\n        case \"blob\":\n        case \"arraybuffer\":\n            internalType = \"uint8array\";\n        break;\n        case \"base64\":\n            internalType = \"string\";\n        break;\n    }\n\n    try {\n        // the type used internally\n        this._internalType = internalType;\n        // the type used to output results\n        this._outputType = outputType;\n        // the mime type\n        this._mimeType = mimeType;\n        checkSupport(internalType);\n        this._worker = worker.pipe(new ConvertWorker(internalType));\n        // the last workers can be rewired without issues but we need to\n        // prevent any updates on previous workers.\n        worker.lock();\n    } catch(e) {\n        this._worker = new GenericWorker(\"error\");\n        this._worker.error(e);\n    }\n};\n\n/**\n * Listen a StreamHelper, accumulate its content and concatenate it into a\n * complete block.\n * @param {Function} updateCb the update callback.\n * @return Promise the promise for the accumulation.\n */\nStreamHelper.prototype.accumulate = function accumulate$1 (updateCb) {\n    return accumulate(this, updateCb);\n};\n\n/**\n * Add a listener on an event triggered on a stream.\n * @param {String} evt the name of the event\n * @param {Function} fn the listener\n * @return {StreamHelper} the current helper.\n */\nStreamHelper.prototype.on = function on (evt, fn) {\n    var self = this;\n\n    if(evt === \"data\") {\n        this._worker.on(evt, function (chunk) {\n            fn.call(self, chunk.data, chunk.meta);\n        });\n    } else {\n        this._worker.on(evt, function () {\n            delay(fn, arguments, self);\n        });\n    }\n    return this;\n};\n\n/**\n * Resume the flow of chunks.\n * @return {StreamHelper} the current helper.\n */\nStreamHelper.prototype.resume = function resume () {\n    delay(this._worker.resume, [], this._worker);\n    return this;\n};\n\n/**\n * Pause the flow of chunks.\n * @return {StreamHelper} the current helper.\n */\nStreamHelper.prototype.pause = function pause () {\n    this._worker.pause();\n    return this;\n};\n\nvar base64 = false;\nvar binary = false;\nvar dir = false;\nvar createFolders = true;\nvar date = null;\nvar compression = null;\nvar compressionOptions = null;\nvar comment = null;\nvar unixPermissions = null;\nvar dosPermissions = null;\n\nvar defaults = /*#__PURE__*/Object.freeze({\n    __proto__: null,\n    base64: base64,\n    binary: binary,\n    dir: dir,\n    createFolders: createFolders,\n    date: date,\n    compression: compression,\n    compressionOptions: compressionOptions,\n    comment: comment,\n    unixPermissions: unixPermissions,\n    dosPermissions: dosPermissions\n});\n\n/* eslint-disable */\n\n// the size of the generated chunks\n// TODO expose this as a public variable\nvar DEFAULT_BLOCK_SIZE = 16 * 1024;\n\n/**\n * A worker that reads a content and emits chunks.\n * @constructor\n * @param {Promise} dataP the promise of the data to split\n */\nvar DataWorker = /*@__PURE__*/(function (GenericWorker) {\n    function DataWorker(dataP) {\n        GenericWorker.call(this, \"DataWorker\");\n        var self = this;\n        this.dataIsReady = false;\n        this.index = 0;\n        this.max = 0;\n        this.data = null;\n        this.type = \"\";\n\n        this._tickScheduled = false;\n\n        dataP.then(function (data) {\n            self.dataIsReady = true;\n            self.data = data;\n            self.max = data && data.length || 0;\n            self.type = getTypeOf(data);\n            if(!self.isPaused) {\n                self._tickAndRepeat();\n            }\n        }, function (e) {\n            self.error(e);\n        });\n    }\n\n    if ( GenericWorker ) DataWorker.__proto__ = GenericWorker;\n    DataWorker.prototype = Object.create( GenericWorker && GenericWorker.prototype );\n    DataWorker.prototype.constructor = DataWorker;\n\n    /**\n     * @see GenericWorker.cleanUp\n     */\n    DataWorker.prototype.cleanUp = function cleanUp () {\n        GenericWorker.prototype.cleanUp.call(this);\n        this.data = null;\n    };\n\n    /**\n     * @see GenericWorker.resume\n     */\n    DataWorker.prototype.resume = function resume () {\n        if(!GenericWorker.prototype.resume.call(this)) {\n            return false;\n        }\n\n        if (!this._tickScheduled && this.dataIsReady) {\n            this._tickScheduled = true;\n            delay(this._tickAndRepeat, [], this);\n        }\n        return true;\n    };\n\n    /**\n     * Trigger a tick a schedule an other call to this function.\n     */\n    DataWorker.prototype._tickAndRepeat = function _tickAndRepeat () {\n        this._tickScheduled = false;\n        if(this.isPaused || this.isFinished) {\n            return;\n        }\n        this._tick();\n        if(!this.isFinished) {\n            delay(this._tickAndRepeat, [], this);\n            this._tickScheduled = true;\n        }\n    };\n    /**\n     * Read and push a chunk.\n     */\n    DataWorker.prototype._tick = function _tick () {\n\n        if(this.isPaused || this.isFinished) {\n            return false;\n        }\n\n        var size = DEFAULT_BLOCK_SIZE;\n        var data = null, nextIndex = Math.min(this.max, this.index + size);\n        if (this.index >= this.max) {\n            // EOF\n            return this.end();\n        } else {\n            switch(this.type) {\n                case \"string\":\n                    data = this.data.substring(this.index, nextIndex);\n                break;\n                case \"uint8array\":\n                    data = this.data.subarray(this.index, nextIndex);\n                break;\n                case \"array\":\n                    data = this.data.slice(this.index, nextIndex);\n                break;\n            }\n            this.index = nextIndex;\n            return this.push({\n                data : data,\n                meta : {\n                    percent : this.max ? this.index / this.max * 100 : 0\n                }\n            });\n        }\n    };\n\n    return DataWorker;\n}(GenericWorker));\n\n/**\n * A worker which calculate the total length of the data flowing through.\n * @constructor\n * @param {String} propName the name used to expose the length\n */\nvar DataLengthProbe = /*@__PURE__*/(function (GenericWorker) {\n    function DataLengthProbe(propName) {\n        GenericWorker.call(this, \"DataLengthProbe for \" + propName);\n        this.propName = propName;\n        this.withStreamInfo(propName, 0);\n    }\n\n    if ( GenericWorker ) DataLengthProbe.__proto__ = GenericWorker;\n    DataLengthProbe.prototype = Object.create( GenericWorker && GenericWorker.prototype );\n    DataLengthProbe.prototype.constructor = DataLengthProbe;\n\n    /**\n     * @see GenericWorker.processChunk\n     */\n    DataLengthProbe.prototype.processChunk = function processChunk (chunk) {\n        if (chunk) {\n            var length = this.streamInfo[this.propName] || 0;\n            this.streamInfo[this.propName] = length + chunk.data.length;\n        }\n        GenericWorker.prototype.processChunk.call(this, chunk);\n    };\n\n    return DataLengthProbe;\n}(GenericWorker));\n\n/* eslint-disable */\n\n/**\n * The following functions come from pako, from pako/lib/zlib/crc32.js\n * released under the MIT license, see pako https://github.com/nodeca/pako/\n */\n\nvar makeTable = function() {\n    // Use ordinary array, since untyped makes no boost here\n    var table = [];\n\n    for (var n =0; n < 256; n++){\n        var c = n;\n        for(var k =0; k < 8; k++){\n            c = ((c&1) ? (0xEDB88320 ^ (c >>> 1)) : (c >>> 1));\n        }\n        table[n] = c;\n    }\n\n    // Memoize table on first call.\n    makeTable = function() {\n        return table;\n    };\n\n    return table;\n};\n\nfunction crc32(crc, buf, len, pos) {\n    var t = makeTable();\n    var end = pos + len;\n\n    crc = crc ^ (-1);\n\n    for (var i = pos; i < end; i++ ) {\n        crc = (crc >>> 8) ^ t[(crc ^ buf[i]) & 0xFF];\n    }\n\n    return (crc ^ (-1)); // >>> 0;\n}\n\n// That's all for the pako functions.\n\n/**\n * Compute the crc32 of a string.\n * This is almost the same as the function crc32, but for strings. Using the\n * same function for the two use cases leads to horrible performances.\n * @param {Number} crc the starting value of the crc.\n * @param {String} str the string to use.\n * @param {Number} len the length of the string.\n * @param {Number} pos the starting position for the crc32 computation.\n * @return {Number} the computed crc32.\n */\nfunction crc32str(crc, str, len, pos) {\n    var t = makeTable();\n    var end = pos + len;\n\n    crc = crc ^ (-1);\n\n    for (var i = pos; i < end; i++ ) {\n        crc = (crc >>> 8) ^ t[(crc ^ str.charCodeAt(i)) & 0xFF];\n    }\n\n    return (crc ^ (-1)); // >>> 0;\n}\n\nfunction crc32wrapper(input, crc) {\n    if (typeof input === \"undefined\" || !input.length) {\n        return 0;\n    }\n\n    var isArray = getTypeOf(input) !== \"string\";\n\n    if (isArray) {\n        return crc32(crc | 0, input, input.length, 0);\n    } else {\n        return crc32str(crc | 0, input, input.length, 0);\n    }\n}\n\n/**\n * A worker which calculate the crc32 of the data flowing through.\n * @constructor\n */\nvar Crc32Probe = /*@__PURE__*/(function (GenericWorker) {\n    function Crc32Probe() {\n        GenericWorker.call(this, \"Crc32Probe\");\n        this.withStreamInfo(\"crc32\", 0);\n    }\n\n    if ( GenericWorker ) Crc32Probe.__proto__ = GenericWorker;\n    Crc32Probe.prototype = Object.create( GenericWorker && GenericWorker.prototype );\n    Crc32Probe.prototype.constructor = Crc32Probe;\n\n    /**\n     * @see GenericWorker.processChunk\n     */\n    Crc32Probe.prototype.processChunk = function processChunk (chunk) {\n        this.streamInfo.crc32 = crc32wrapper(chunk.data, this.streamInfo.crc32 || 0);\n        this.push(chunk);\n    };\n\n    return Crc32Probe;\n}(GenericWorker));\n\n/* eslint-disable */\n\n/**\n * Represent a compressed object, with everything needed to decompress it.\n * @constructor\n * @param {number} compressedSize the size of the data compressed.\n * @param {number} uncompressedSize the size of the data after decompression.\n * @param {number} crc32 the crc32 of the decompressed file.\n * @param {object} compression the type of compression, see lib/compressions.js.\n * @param {String|ArrayBuffer|Uint8Array|Buffer} data the compressed data.\n */\nvar CompressedObject = function CompressedObject(compressedSize, uncompressedSize, crc32, compression, data) {\n    this.compressedSize = compressedSize;\n    this.uncompressedSize = uncompressedSize;\n    this.crc32 = crc32;\n    this.compression = compression;\n    this.compressedContent = data;\n};\n\n/**\n * Create a worker to get the uncompressed content.\n * @return {GenericWorker} the worker.\n */\nCompressedObject.prototype.getContentWorker = function getContentWorker () {\n    var worker = new DataWorker(external.Promise.resolve(this.compressedContent))\n    .pipe(this.compression.uncompressWorker())\n    .pipe(new DataLengthProbe(\"data_length\"));\n\n    var that = this;\n    worker.on(\"end\", function () {\n        if(this.streamInfo['data_length'] !== that.uncompressedSize) {\n            throw new Error(\"Bug : uncompressed data size mismatch\");\n        }\n    });\n    return worker;\n};\n\n/**\n * Create a worker to get the compressed content.\n * @return {GenericWorker} the worker.\n */\nCompressedObject.prototype.getCompressedWorker = function getCompressedWorker () {\n    return new DataWorker(external.Promise.resolve(this.compressedContent))\n    .withStreamInfo(\"compressedSize\", this.compressedSize)\n    .withStreamInfo(\"uncompressedSize\", this.uncompressedSize)\n    .withStreamInfo(\"crc32\", this.crc32)\n    .withStreamInfo(\"compression\", this.compression)\n    ;\n};\n\n/**\n * Chain the given worker with other workers to compress the content with the\n * given compression.\n * @param {GenericWorker} uncompressedWorker the worker to pipe.\n * @param {Object} compression the compression object.\n * @param {Object} compressionOptions the options to use when compressing.\n * @return {GenericWorker} the new worker compressing the content.\n */\nCompressedObject.createWorkerFrom = function createWorkerFrom (uncompressedWorker, compression, compressionOptions) {\n    return uncompressedWorker\n    .pipe(new Crc32Probe())\n    .pipe(new DataLengthProbe(\"uncompressedSize\"))\n    .pipe(compression.compressWorker(compressionOptions))\n    .pipe(new DataLengthProbe(\"compressedSize\"))\n    .withStreamInfo(\"compression\", compression);\n};\n\n/* eslint-disable */\n\n/**\n * A simple object representing a file in the zip file.\n * @constructor\n * @param {string} name the name of the file\n * @param {String|ArrayBuffer|Uint8Array|Buffer} data the data\n * @param {Object} options the options of the file\n */\nvar ZipObject = function ZipObject(name, data, options) {\n    this.name = name;\n    this.dir = options.dir;\n    this.date = options.date;\n    this.comment = options.comment;\n    this.unixPermissions = options.unixPermissions;\n    this.dosPermissions = options.dosPermissions;\n\n    this._data = data;\n    this._dataBinary = options.binary;\n    // keep only the compression\n    this.options = {\n        compression : options.compression,\n        compressionOptions : options.compressionOptions\n    };\n};\n\n/**\n * Create an internal stream for the content of this object.\n * @param {String} type the type of each chunk.\n * @return StreamHelper the stream.\n */\nZipObject.prototype.internalStream = function internalStream (type) {\n    var result = null, outputType = \"string\";\n    try {\n        if (!type) {\n            throw new Error(\"No output type specified.\");\n        }\n        outputType = type.toLowerCase();\n        var askUnicodeString = outputType === \"string\" || outputType === \"text\";\n        if (outputType === \"binarystring\" || outputType === \"text\") {\n            outputType = \"string\";\n        }\n        result = this._decompressWorker();\n\n        var isUnicodeString = !this._dataBinary;\n\n        if (isUnicodeString && !askUnicodeString) {\n            result = result.pipe(new Utf8EncodeWorker());\n        }\n        if (!isUnicodeString && askUnicodeString) {\n            result = result.pipe(new Utf8DecodeWorker());\n        }\n    } catch (e) {\n        result = new GenericWorker(\"error\");\n        result.error(e);\n    }\n\n    return new StreamHelper(result, outputType, \"\");\n};\n\n/**\n * Prepare the content in the asked type.\n * @param {String} type the type of the result.\n * @param {Function} onUpdate a function to call on each internal update.\n * @return Promise the promise of the result.\n */\nZipObject.prototype.async = function async (type, onUpdate) {\n    return this.internalStream(type).accumulate(onUpdate);\n};\n\n/**\n * Return a worker for the compressed content.\n * @private\n * @param {Object} compression the compression object to use.\n * @param {Object} compressionOptions the options to use when compressing.\n * @return Worker the worker.\n */\nZipObject.prototype._compressWorker = function _compressWorker (compression, compressionOptions) {\n    if (\n        this._data instanceof CompressedObject &&\n        this._data.compression.magic === compression.magic\n    ) {\n        return this._data.getCompressedWorker();\n    } else {\n        var result = this._decompressWorker();\n        if(!this._dataBinary) {\n            result = result.pipe(new Utf8EncodeWorker());\n        }\n        return CompressedObject.createWorkerFrom(result, compression, compressionOptions);\n    }\n};\n\n/**\n * Return a worker for the decompressed content.\n * @private\n * @return Worker the worker.\n */\nZipObject.prototype._decompressWorker = function _decompressWorker () {\n    if (this._data instanceof CompressedObject) {\n        return this._data.getContentWorker();\n    } else if (this._data instanceof GenericWorker) {\n        return this._data;\n    } else {\n        return new DataWorker(this._data);\n    }\n};\n\nvar arrayType = function() {\n    var useTypedArray = (typeof Uint8Array !== 'undefined') && (typeof Uint16Array !== 'undefined') && (typeof Uint32Array !== 'undefined');\n    var resolved = useTypedArray ? \"uint8array\" : \"array\";\n\n    arrayType = function() {\n        return resolved;\n    };\n};\n\n/**\n * Create a worker that uses pako to inflate/deflate.\n * @constructor\n * @param {String} action the name of the pako function to call : either \"Deflate\" or \"Inflate\".\n * @param {Object} options the options to use when (de)compressing.\n */\nvar FlateWorker = /*@__PURE__*/(function (GenericWorker) {\n    function FlateWorker(action, options) {\n        GenericWorker.call(this, \"FlateWorker/\" + action);\n\n        this._pako = null;\n        this._pakoAction = action;\n        this._pakoOptions = options;\n        // the `meta` object from the last chunk received\n        // this allow this worker to pass around metadata\n        this.meta = {};\n    }\n\n    if ( GenericWorker ) FlateWorker.__proto__ = GenericWorker;\n    FlateWorker.prototype = Object.create( GenericWorker && GenericWorker.prototype );\n    FlateWorker.prototype.constructor = FlateWorker;\n\n    /**\n     * @see GenericWorker.processChunk\n     */\n    FlateWorker.prototype.processChunk = function processChunk (chunk) {\n        this.meta = chunk.meta;\n        if (this._pako === null) {\n            this._createPako();\n        }\n        this._pako.push(transformTo(arrayType(), chunk.data), false);\n    };\n\n    /**\n     * @see GenericWorker.flush\n     */\n    FlateWorker.prototype.flush = function flush () {\n        GenericWorker.prototype.flush.call(this);\n        if (this._pako === null) {\n            this._createPako();\n        }\n        this._pako.push([], true);\n    };\n    /**\n     * @see GenericWorker.cleanUp\n     */\n    FlateWorker.prototype.cleanUp = function cleanUp () {\n        GenericWorker.prototype.cleanUp.call(this);\n        this._pako = null;\n    };\n\n    /**\n     * Create the _pako object.\n     * TODO: lazy-loading this object isn't the best solution but it's the\n     * quickest. The best solution is to lazy-load the worker list. See also the\n     * issue #446.\n     */\n    FlateWorker.prototype._createPako = function _createPako () {\n        var this$1$1 = this;\n\n        var params = {\n            raw: true,\n            level: this._pakoOptions.level || -1 // default compression\n        };\n        this._pako = this._pakoAction === 'Deflate' ? new Deflate(params) : new Inflate(params);\n        this._pako.onData = function (data) {\n            this$1$1.push({\n                data: data,\n                meta: this$1$1.meta\n            });\n        };\n    };\n\n    return FlateWorker;\n}(GenericWorker));\n\nvar DEFLATE = {\n    magic: \"\\x08\\x00\",\n    compressWorker: function(compressionOptions) {\n        return new FlateWorker(\"Deflate\", compressionOptions);\n    },\n\n    uncompressWorker: function() {\n        return new FlateWorker(\"Inflate\", {});\n    }\n};\n\nvar STORE = {\n    magic: \"\\x00\\x00\",\n    compressWorker: function() {\n        return new GenericWorker(\"STORE compression\");\n    },\n    uncompressWorker: function() {\n        return new GenericWorker(\"STORE decompression\");\n    }\n};\n\nvar compressions = {\n    STORE: STORE,\n    DEFLATE: DEFLATE\n};\n\nvar LOCAL_FILE_HEADER = \"PK\\x03\\x04\";\nvar CENTRAL_FILE_HEADER = \"PK\\x01\\x02\";\nvar CENTRAL_DIRECTORY_END = \"PK\\x05\\x06\";\nvar ZIP64_CENTRAL_DIRECTORY_LOCATOR = \"PK\\x06\\x07\";\nvar ZIP64_CENTRAL_DIRECTORY_END = \"PK\\x06\\x06\";\nvar DATA_DESCRIPTOR = \"PK\\x07\\x08\";\n\n/* eslint-disable */\n\n/**\n * Transform an integer into a string in hexadecimal.\n * @private\n * @param {number} dec the number to convert.\n * @param {number} bytes the number of bytes to generate.\n * @returns {string} the result.\n */\nvar decToHex = function(dec, bytes) {\n    var hex = \"\", i;\n    for (i = 0; i < bytes; i++) {\n        hex += String.fromCharCode(dec & 0xff);\n        dec = dec >>> 8;\n    }\n    return hex;\n};\n\n/**\n * Generate the UNIX part of the external file attributes.\n * @param {Object} unixPermissions the unix permissions or null.\n * @param {Boolean} isDir true if the entry is a directory, false otherwise.\n * @return {Number} a 32 bit integer.\n *\n * adapted from http://unix.stackexchange.com/questions/14705/the-zip-formats-external-file-attribute :\n *\n * TTTTsstrwxrwxrwx0000000000ADVSHR\n * ^^^^____________________________ file type, see zipinfo.c (UNX_*)\n *     ^^^_________________________ setuid, setgid, sticky\n *        ^^^^^^^^^________________ permissions\n *                 ^^^^^^^^^^______ not used ?\n *                           ^^^^^^ DOS attribute bits : Archive, Directory, Volume label, System file, Hidden, Read only\n */\nvar generateUnixExternalFileAttr = function (unixPermissions, isDir) {\n\n    var result = unixPermissions;\n    if (!unixPermissions) {\n        // I can't use octal values in strict mode, hence the hexa.\n        //  040775 => 0x41fd\n        // 0100664 => 0x81b4\n        result = isDir ? 0x41fd : 0x81b4;\n    }\n    return (result & 0xFFFF) << 16;\n};\n\n/**\n * Generate the DOS part of the external file attributes.\n * @param {Object} dosPermissions the dos permissions or null.\n * @param {Boolean} isDir true if the entry is a directory, false otherwise.\n * @return {Number} a 32 bit integer.\n *\n * Bit 0     Read-Only\n * Bit 1     Hidden\n * Bit 2     System\n * Bit 3     Volume Label\n * Bit 4     Directory\n * Bit 5     Archive\n */\nvar generateDosExternalFileAttr = function (dosPermissions, isDir) {\n\n    // the dir flag is already set for compatibility\n    return (dosPermissions || 0)  & 0x3F;\n};\n\n/**\n * Generate the various parts used in the construction of the final zip file.\n * @param {Object} streamInfo the hash with information about the compressed file.\n * @param {Boolean} streamedContent is the content streamed ?\n * @param {Boolean} streamingEnded is the stream finished ?\n * @param {number} offset the current offset from the start of the zip file.\n * @param {String} platform let's pretend we are this platform (change platform dependents fields)\n * @param {Function} encodeFileName the function to encode the file name / comment.\n * @return {Object} the zip parts.\n */\nvar generateZipParts = function(streamInfo, streamedContent, streamingEnded, offset, platform, encodeFileName) {\n    var file = streamInfo['file'],\n    compression = streamInfo['compression'],\n    useCustomEncoding = encodeFileName !== utf8encode,\n    encodedFileName = transformTo(\"string\", encodeFileName(file.name)),\n    utfEncodedFileName = transformTo(\"string\", utf8encode(file.name)),\n    comment = file.comment,\n    encodedComment = transformTo(\"string\", encodeFileName(comment)),\n    utfEncodedComment = transformTo(\"string\", utf8encode(comment)),\n    useUTF8ForFileName = utfEncodedFileName.length !== file.name.length,\n    useUTF8ForComment = utfEncodedComment.length !== comment.length,\n    dosTime,\n    dosDate,\n    extraFields = \"\",\n    unicodePathExtraField = \"\",\n    unicodeCommentExtraField = \"\",\n    dir = file.dir,\n    date = file.date;\n\n\n    var dataInfo = {\n        crc32 : 0,\n        compressedSize : 0,\n        uncompressedSize : 0\n    };\n\n    // if the content is streamed, the sizes/crc32 are only available AFTER\n    // the end of the stream.\n    if (!streamedContent || streamingEnded) {\n        dataInfo.crc32 = streamInfo['crc32'];\n        dataInfo.compressedSize = streamInfo['compressedSize'];\n        dataInfo.uncompressedSize = streamInfo['uncompressedSize'];\n    }\n\n    var bitflag = 0;\n    if (streamedContent) {\n        // Bit 3: the sizes/crc32 are set to zero in the local header.\n        // The correct values are put in the data descriptor immediately\n        // following the compressed data.\n        bitflag |= 0x0008;\n    }\n    if (!useCustomEncoding && (useUTF8ForFileName || useUTF8ForComment)) {\n        // Bit 11: Language encoding flag (EFS).\n        bitflag |= 0x0800;\n    }\n\n\n    var extFileAttr = 0;\n    var versionMadeBy = 0;\n    if (dir) {\n        // dos or unix, we set the dos dir flag\n        extFileAttr |= 0x00010;\n    }\n    if(platform === \"UNIX\") {\n        versionMadeBy = 0x031E; // UNIX, version 3.0\n        extFileAttr |= generateUnixExternalFileAttr(file.unixPermissions, dir);\n    } else { // DOS or other, fallback to DOS\n        versionMadeBy = 0x0014; // DOS, version 2.0\n        extFileAttr |= generateDosExternalFileAttr(file.dosPermissions);\n    }\n\n    // date\n    // @see http://www.delorie.com/djgpp/doc/rbinter/it/52/13.html\n    // @see http://www.delorie.com/djgpp/doc/rbinter/it/65/16.html\n    // @see http://www.delorie.com/djgpp/doc/rbinter/it/66/16.html\n\n    dosTime = date.getUTCHours();\n    dosTime = dosTime << 6;\n    dosTime = dosTime | date.getUTCMinutes();\n    dosTime = dosTime << 5;\n    dosTime = dosTime | date.getUTCSeconds() / 2;\n\n    dosDate = date.getUTCFullYear() - 1980;\n    dosDate = dosDate << 4;\n    dosDate = dosDate | (date.getUTCMonth() + 1);\n    dosDate = dosDate << 5;\n    dosDate = dosDate | date.getUTCDate();\n\n    if (useUTF8ForFileName) {\n        // set the unicode path extra field. unzip needs at least one extra\n        // field to correctly handle unicode path, so using the path is as good\n        // as any other information. This could improve the situation with\n        // other archive managers too.\n        // This field is usually used without the utf8 flag, with a non\n        // unicode path in the header (winrar, winzip). This helps (a bit)\n        // with the messy Windows' default compressed folders feature but\n        // breaks on p7zip which doesn't seek the unicode path extra field.\n        // So for now, UTF-8 everywhere !\n        unicodePathExtraField =\n            // Version\n            decToHex(1, 1) +\n            // NameCRC32\n            decToHex(crc32wrapper(encodedFileName), 4) +\n            // UnicodeName\n            utfEncodedFileName;\n\n        extraFields +=\n            // Info-ZIP Unicode Path Extra Field\n            \"\\x75\\x70\" +\n            // size\n            decToHex(unicodePathExtraField.length, 2) +\n            // content\n            unicodePathExtraField;\n    }\n\n    if(useUTF8ForComment) {\n\n        unicodeCommentExtraField =\n            // Version\n            decToHex(1, 1) +\n            // CommentCRC32\n            decToHex(crc32wrapper(encodedComment), 4) +\n            // UnicodeName\n            utfEncodedComment;\n\n        extraFields +=\n            // Info-ZIP Unicode Path Extra Field\n            \"\\x75\\x63\" +\n            // size\n            decToHex(unicodeCommentExtraField.length, 2) +\n            // content\n            unicodeCommentExtraField;\n    }\n\n    var header = \"\";\n\n    // version needed to extract\n    header += \"\\x0A\\x00\";\n    // general purpose bit flag\n    header += decToHex(bitflag, 2);\n    // compression method\n    header += compression.magic;\n    // last mod file time\n    header += decToHex(dosTime, 2);\n    // last mod file date\n    header += decToHex(dosDate, 2);\n    // crc-32\n    header += decToHex(dataInfo.crc32, 4);\n    // compressed size\n    header += decToHex(dataInfo.compressedSize, 4);\n    // uncompressed size\n    header += decToHex(dataInfo.uncompressedSize, 4);\n    // file name length\n    header += decToHex(encodedFileName.length, 2);\n    // extra field length\n    header += decToHex(extraFields.length, 2);\n\n\n    var fileRecord = LOCAL_FILE_HEADER + header + encodedFileName + extraFields;\n\n    var dirRecord = CENTRAL_FILE_HEADER +\n        // version made by (00: DOS)\n        decToHex(versionMadeBy, 2) +\n        // file header (common to file and central directory)\n        header +\n        // file comment length\n        decToHex(encodedComment.length, 2) +\n        // disk number start\n        \"\\x00\\x00\" +\n        // internal file attributes TODO\n        \"\\x00\\x00\" +\n        // external file attributes\n        decToHex(extFileAttr, 4) +\n        // relative offset of local header\n        decToHex(offset, 4) +\n        // file name\n        encodedFileName +\n        // extra field\n        extraFields +\n        // file comment\n        encodedComment;\n\n    return {\n        fileRecord: fileRecord,\n        dirRecord: dirRecord\n    };\n};\n\n/**\n * Generate the EOCD record.\n * @param {Number} entriesCount the number of entries in the zip file.\n * @param {Number} centralDirLength the length (in bytes) of the central dir.\n * @param {Number} localDirLength the length (in bytes) of the local dir.\n * @param {String} comment the zip file comment as a binary string.\n * @param {Function} encodeFileName the function to encode the comment.\n * @return {String} the EOCD record.\n */\nvar generateCentralDirectoryEnd = function (entriesCount, centralDirLength, localDirLength, comment, encodeFileName) {\n    var dirEnd = \"\";\n    var encodedComment = transformTo(\"string\", encodeFileName(comment));\n\n    // end of central dir signature\n    dirEnd = CENTRAL_DIRECTORY_END +\n        // number of this disk\n        \"\\x00\\x00\" +\n        // number of the disk with the start of the central directory\n        \"\\x00\\x00\" +\n        // total number of entries in the central directory on this disk\n        decToHex(entriesCount, 2) +\n        // total number of entries in the central directory\n        decToHex(entriesCount, 2) +\n        // size of the central directory   4 bytes\n        decToHex(centralDirLength, 4) +\n        // offset of start of central directory with respect to the starting disk number\n        decToHex(localDirLength, 4) +\n        // .ZIP file comment length\n        decToHex(encodedComment.length, 2) +\n        // .ZIP file comment\n        encodedComment;\n\n    return dirEnd;\n};\n\n/**\n * Generate data descriptors for a file entry.\n * @param {Object} streamInfo the hash generated by a worker, containing information\n * on the file entry.\n * @return {String} the data descriptors.\n */\nvar generateDataDescriptors = function (streamInfo) {\n    var descriptor = \"\";\n    descriptor = DATA_DESCRIPTOR +\n        // crc-32                          4 bytes\n        decToHex(streamInfo['crc32'], 4) +\n        // compressed size                 4 bytes\n        decToHex(streamInfo['compressedSize'], 4) +\n        // uncompressed size               4 bytes\n        decToHex(streamInfo['uncompressedSize'], 4);\n\n    return descriptor;\n};\n\n\n/**\n * A worker to concatenate other workers to create a zip file.\n * @param {Boolean} streamFiles `true` to stream the content of the files,\n * `false` to accumulate it.\n * @param {String} comment the comment to use.\n * @param {String} platform the platform to use, \"UNIX\" or \"DOS\".\n * @param {Function} encodeFileName the function to encode file names and comments.\n */\nvar ZipFileWorker = /*@__PURE__*/(function (GenericWorker) {\n    function ZipFileWorker(streamFiles, comment, platform, encodeFileName) {\n        GenericWorker.call(this, \"ZipFileWorker\");\n        // The number of bytes written so far. This doesn't count accumulated chunks.\n        this.bytesWritten = 0;\n        // The comment of the zip file\n        this.zipComment = comment;\n        // The platform \"generating\" the zip file.\n        this.zipPlatform = platform;\n        // the function to encode file names and comments.\n        this.encodeFileName = encodeFileName;\n        // Should we stream the content of the files ?\n        this.streamFiles = streamFiles;\n        // If `streamFiles` is false, we will need to accumulate the content of the\n        // files to calculate sizes / crc32 (and write them *before* the content).\n        // This boolean indicates if we are accumulating chunks (it will change a lot\n        // during the lifetime of this worker).\n        this.accumulate = false;\n        // The buffer receiving chunks when accumulating content.\n        this.contentBuffer = [];\n        // The list of generated directory records.\n        this.dirRecords = [];\n        // The offset (in bytes) from the beginning of the zip file for the current source.\n        this.currentSourceOffset = 0;\n        // The total number of entries in this zip file.\n        this.entriesCount = 0;\n        // the name of the file currently being added, null when handling the end of the zip file.\n        // Used for the emitted metadata.\n        this.currentFile = null;\n\n        this._sources = [];\n    }\n\n    if ( GenericWorker ) ZipFileWorker.__proto__ = GenericWorker;\n    ZipFileWorker.prototype = Object.create( GenericWorker && GenericWorker.prototype );\n    ZipFileWorker.prototype.constructor = ZipFileWorker;\n\n    /**\n     * @see GenericWorker.push\n     */\n    ZipFileWorker.prototype.push = function push (chunk) {\n\n        var currentFilePercent = chunk.meta.percent || 0;\n        var entriesCount = this.entriesCount;\n        var remainingFiles = this._sources.length;\n\n        if(this.accumulate) {\n            this.contentBuffer.push(chunk);\n        } else {\n            this.bytesWritten += chunk.data.length;\n\n            GenericWorker.prototype.push.call(this, {\n                data : chunk.data,\n                meta : {\n                    currentFile : this.currentFile,\n                    percent : entriesCount ? (currentFilePercent + 100 * (entriesCount - remainingFiles - 1)) / entriesCount : 100\n                }\n            });\n        }\n    };\n\n    /**\n     * The worker started a new source (an other worker).\n     * @param {Object} streamInfo the streamInfo object from the new source.\n     */\n    ZipFileWorker.prototype.openedSource = function openedSource (streamInfo) {\n        this.currentSourceOffset = this.bytesWritten;\n        this.currentFile = streamInfo['file'].name;\n\n        var streamedContent = this.streamFiles && !streamInfo['file'].dir;\n\n        // don't stream folders (because they don't have any content)\n        if(streamedContent) {\n            var record = generateZipParts(streamInfo, streamedContent, false, this.currentSourceOffset, this.zipPlatform, this.encodeFileName);\n            this.push({\n                data : record.fileRecord,\n                meta : {percent:0}\n            });\n        } else {\n            // we need to wait for the whole file before pushing anything\n            this.accumulate = true;\n        }\n    };\n\n    /**\n     * The worker finished a source (an other worker).\n     * @param {Object} streamInfo the streamInfo object from the finished source.\n     */\n    ZipFileWorker.prototype.closedSource = function closedSource (streamInfo) {\n        this.accumulate = false;\n        var streamedContent = this.streamFiles && !streamInfo['file'].dir;\n        var record = generateZipParts(streamInfo, streamedContent, true, this.currentSourceOffset, this.zipPlatform, this.encodeFileName);\n\n        this.dirRecords.push(record.dirRecord);\n        if(streamedContent) {\n            // after the streamed file, we put data descriptors\n            this.push({\n                data : generateDataDescriptors(streamInfo),\n                meta : {percent:100}\n            });\n        } else {\n            // the content wasn't streamed, we need to push everything now\n            // first the file record, then the content\n            this.push({\n                data : record.fileRecord,\n                meta : {percent:0}\n            });\n            while(this.contentBuffer.length) {\n                this.push(this.contentBuffer.shift());\n            }\n        }\n        this.currentFile = null;\n    };\n\n    /**\n     * @see GenericWorker.flush\n     */\n    ZipFileWorker.prototype.flush = function flush () {\n\n        var localDirLength = this.bytesWritten;\n        for(var i = 0; i < this.dirRecords.length; i++) {\n            this.push({\n                data : this.dirRecords[i],\n                meta : {percent:100}\n            });\n        }\n        var centralDirLength = this.bytesWritten - localDirLength;\n\n        var dirEnd = generateCentralDirectoryEnd(this.dirRecords.length, centralDirLength, localDirLength, this.zipComment, this.encodeFileName);\n\n        this.push({\n            data : dirEnd,\n            meta : {percent:100}\n        });\n    };\n\n    /**\n     * Prepare the next source to be read.\n     */\n    ZipFileWorker.prototype.prepareNextSource = function prepareNextSource () {\n        this.previous = this._sources.shift();\n        this.openedSource(this.previous.streamInfo);\n        if (this.isPaused) {\n            this.previous.pause();\n        } else {\n            this.previous.resume();\n        }\n    };\n\n    /**\n     * @see GenericWorker.registerPrevious\n     */\n    ZipFileWorker.prototype.registerPrevious = function registerPrevious (previous) {\n        this._sources.push(previous);\n        var self = this;\n\n        previous.on('data', function (chunk) {\n            self.processChunk(chunk);\n        });\n        previous.on('end', function () {\n            self.closedSource(self.previous.streamInfo);\n            if(self._sources.length) {\n                self.prepareNextSource();\n            } else {\n                self.end();\n            }\n        });\n        previous.on('error', function (e) {\n            self.error(e);\n        });\n        return this;\n    };\n\n    /**\n     * @see GenericWorker.resume\n     */\n    ZipFileWorker.prototype.resume = function resume () {\n        if(!GenericWorker.prototype.resume.call(this)) {\n            return false;\n        }\n\n        if (!this.previous && this._sources.length) {\n            this.prepareNextSource();\n            return true;\n        }\n        if (!this.previous && !this._sources.length && !this.generatedError) {\n            this.end();\n            return true;\n        }\n    };\n\n    /**\n     * @see GenericWorker.error\n     */\n    ZipFileWorker.prototype.error = function error (e) {\n        var sources = this._sources;\n        if(!GenericWorker.prototype.error.call(this, e)) {\n            return false;\n        }\n        for(var i = 0; i < sources.length; i++) {\n            try {\n                sources[i].error(e);\n            } catch(e$1) {\n                // the `error` exploded, nothing to do\n            }\n        }\n        return true;\n    };\n\n    /**\n     * @see GenericWorker.lock\n     */\n    ZipFileWorker.prototype.lock = function lock () {\n        GenericWorker.prototype.lock.call(this);\n        var sources = this._sources;\n        for(var i = 0; i < sources.length; i++) {\n            sources[i].lock();\n        }\n    };\n\n    return ZipFileWorker;\n}(GenericWorker));\n\n/* eslint-disable */\n\n/**\n * Find the compression to use.\n * @param {String} fileCompression the compression defined at the file level, if any.\n * @param {String} zipCompression the compression defined at the load() level.\n * @return {Object} the compression object to use.\n */\nvar getCompression = function (fileCompression, zipCompression) {\n\n    var compressionName = fileCompression || zipCompression;\n    var compression = compressions[compressionName];\n    if (!compression) {\n        throw new Error(compressionName + \" is not a valid compression method !\");\n    }\n    return compression;\n};\n\n/**\n * Create a worker to generate a zip file.\n * @param {JSZip} zip the JSZip instance at the right root level.\n * @param {Object} options to generate the zip file.\n * @param {String} comment the comment to use.\n */\nvar generateWorker = function (zip, options, comment) {\n\n    var zipFileWorker = new ZipFileWorker(options.streamFiles, comment, options.platform, options.encodeFileName);\n    var entriesCount = 0;\n    try {\n\n        zip.forEach(function (relativePath, file) {\n            entriesCount++;\n            var compression = getCompression(file.options.compression, options.compression);\n            var compressionOptions = file.options.compressionOptions || options.compressionOptions || {};\n            var dir = file.dir, date = file.date;\n\n            file._compressWorker(compression, compressionOptions)\n            .withStreamInfo(\"file\", {\n                name : relativePath,\n                dir : dir,\n                date : date,\n                comment : file.comment || \"\",\n                unixPermissions : file.unixPermissions,\n                dosPermissions : file.dosPermissions\n            })\n            .pipe(zipFileWorker);\n        });\n        zipFileWorker.entriesCount = entriesCount;\n    } catch (e) {\n        zipFileWorker.error(e);\n    }\n\n    return zipFileWorker;\n};\n\n/* eslint-disable */\n\nvar DataReader = function DataReader(data) {\n    this.data = data; // type : see implementation\n    this.length = data.length;\n    this.index = 0;\n    this.zero = 0;\n};\n\n/**\n * Check that the offset will not go too far.\n * @param {string} offset the additional offset to check.\n * @throws {Error} an Error if the offset is out of bounds.\n */\nDataReader.prototype.checkOffset = function checkOffset (offset) {\n    this.checkIndex(this.index + offset);\n};\n\n/**\n * Check that the specified index will not be too far.\n * @param {string} newIndex the index to check.\n * @throws {Error} an Error if the index is out of bounds.\n */\nDataReader.prototype.checkIndex = function checkIndex (newIndex) {\n    if (this.length < this.zero + newIndex || newIndex < 0) {\n        throw new Error(\"End of data reached (data length = \" + this.length + \", asked index = \" + (newIndex) + \"). Corrupted zip ?\");\n    }\n};\n\n/**\n * Change the index.\n * @param {number} newIndex The new index.\n * @throws {Error} if the new index is out of the data.\n */\nDataReader.prototype.setIndex = function setIndex (newIndex) {\n    this.checkIndex(newIndex);\n    this.index = newIndex;\n};\n\n/**\n * Skip the next n bytes.\n * @param {number} n the number of bytes to skip.\n * @throws {Error} if the new index is out of the data.\n */\nDataReader.prototype.skip = function skip (n) {\n    this.setIndex(this.index + n);\n};\n\n/**\n * Get the byte at the specified index.\n * @param {number} i the index to use.\n * @return {number} a byte.\n */\nDataReader.prototype.byteAt = function byteAt (i) {\n    // see implementations\n};\n\n/**\n * Get the next number with a given byte size.\n * @param {number} size the number of bytes to read.\n * @return {number} the corresponding number.\n */\nDataReader.prototype.readInt = function readInt (size) {\n    var result = 0,\n        i;\n    this.checkOffset(size);\n    for (i = this.index + size - 1; i >= this.index; i--) {\n        result = (result << 8) + this.byteAt(i);\n    }\n    this.index += size;\n    return result;\n};\n\n/**\n * Get the next string with a given byte size.\n * @param {number} size the number of bytes to read.\n * @return {string} the corresponding string.\n */\nDataReader.prototype.readString = function readString (size) {\n    return transformTo(\"string\", this.readData(size));\n};\n\n/**\n * Get raw data without conversion, <size> bytes.\n * @param {number} size the number of bytes to read.\n * @return {Object} the raw data, implementation specific.\n */\nDataReader.prototype.readData = function readData (size) {\n    // see implementations\n};\n\n/**\n * Find the last occurrence of a zip signature (4 bytes).\n * @param {string} sig the signature to find.\n * @return {number} the index of the last occurrence, -1 if not found.\n */\nDataReader.prototype.lastIndexOfSignature = function lastIndexOfSignature (sig) {\n    // see implementations\n};\n\n/**\n * Read the signature (4 bytes) at the current position and compare it with sig.\n * @param {string} sig the expected signature\n * @return {boolean} true if the signature matches, false otherwise.\n */\nDataReader.prototype.readAndCheckSignature = function readAndCheckSignature (sig) {\n    // see implementations\n};\n\n/**\n * Get the next date.\n * @return {Date} the date.\n */\nDataReader.prototype.readDate = function readDate () {\n    var dostime = this.readInt(4);\n    return new Date(Date.UTC(\n    ((dostime >> 25) & 0x7f) + 1980, // year\n    ((dostime >> 21) & 0x0f) - 1, // month\n    (dostime >> 16) & 0x1f, // day\n    (dostime >> 11) & 0x1f, // hour\n    (dostime >> 5) & 0x3f, // minute\n    (dostime & 0x1f) << 1)); // second\n};\n\n/* eslint-disable */\n\nvar ArrayReader = /*@__PURE__*/(function (DataReader) {\n    function ArrayReader(data) {\n        DataReader.call(this, data);\n        for(var i = 0; i < this.data.length; i++) {\n            data[i] = data[i] & 0xFF;\n        }\n    }\n\n    if ( DataReader ) ArrayReader.__proto__ = DataReader;\n    ArrayReader.prototype = Object.create( DataReader && DataReader.prototype );\n    ArrayReader.prototype.constructor = ArrayReader;\n\n    /**\n     * @see DataReader.byteAt\n     */\n    ArrayReader.prototype.byteAt = function byteAt (i) {\n        return this.data[this.zero + i];\n    };\n\n    /**\n     * @see DataReader.lastIndexOfSignature\n     */\n    ArrayReader.prototype.lastIndexOfSignature = function lastIndexOfSignature (sig) {\n        var sig0 = sig.charCodeAt(0),\n            sig1 = sig.charCodeAt(1),\n            sig2 = sig.charCodeAt(2),\n            sig3 = sig.charCodeAt(3);\n        for (var i = this.length - 4; i >= 0; --i) {\n            if (this.data[i] === sig0 && this.data[i + 1] === sig1 && this.data[i + 2] === sig2 && this.data[i + 3] === sig3) {\n                return i - this.zero;\n            }\n        }\n\n        return -1;\n    };\n\n    /**\n     * @see DataReader.readAndCheckSignature\n     */\n    ArrayReader.prototype.readAndCheckSignature = function readAndCheckSignature (sig) {\n        var sig0 = sig.charCodeAt(0),\n            sig1 = sig.charCodeAt(1),\n            sig2 = sig.charCodeAt(2),\n            sig3 = sig.charCodeAt(3),\n            data = this.readData(4);\n        return sig0 === data[0] && sig1 === data[1] && sig2 === data[2] && sig3 === data[3];\n    };\n\n    /**\n     * @see DataReader.readData\n     */\n    ArrayReader.prototype.readData = function readData (size) {\n        this.checkOffset(size);\n        if(size === 0) {\n            return [];\n        }\n        var result = this.data.slice(this.zero + this.index, this.zero + this.index + size);\n        this.index += size;\n        return result;\n    };\n\n    return ArrayReader;\n}(DataReader));\n\nvar StringReader = /*@__PURE__*/(function (DataReader) {\n    function StringReader(data) {\n        DataReader.call(this, data);\n    }\n\n    if ( DataReader ) StringReader.__proto__ = DataReader;\n    StringReader.prototype = Object.create( DataReader && DataReader.prototype );\n    StringReader.prototype.constructor = StringReader;\n\n    /**\n     * @see DataReader.byteAt\n     */\n    StringReader.prototype.byteAt = function byteAt (i) {\n        return this.data.charCodeAt(this.zero + i);\n    };\n\n    /**\n     * @see DataReader.lastIndexOfSignature\n     */\n    StringReader.prototype.lastIndexOfSignature = function lastIndexOfSignature (sig) {\n        return this.data.lastIndexOf(sig) - this.zero;\n    };\n\n    /**\n     * @see DataReader.readAndCheckSignature\n     */\n    StringReader.prototype.readAndCheckSignature = function readAndCheckSignature (sig) {\n        var data = this.readData(4);\n        return sig === data;\n    };\n\n    /**\n     * @see DataReader.readData\n     */\n    StringReader.prototype.readData = function readData (size) {\n        this.checkOffset(size);\n        // this will work because the constructor applied the \"& 0xff\" mask.\n        var result = this.data.slice(this.zero + this.index, this.zero + this.index + size);\n        this.index += size;\n        return result;\n    };\n\n    return StringReader;\n}(DataReader));\n\n/* eslint-disable */\n\nvar Uint8ArrayReader = /*@__PURE__*/(function (ArrayReader) {\n    function Uint8ArrayReader(data) {\n        ArrayReader.call(this, data);\n    }\n\n    if ( ArrayReader ) Uint8ArrayReader.__proto__ = ArrayReader;\n    Uint8ArrayReader.prototype = Object.create( ArrayReader && ArrayReader.prototype );\n    Uint8ArrayReader.prototype.constructor = Uint8ArrayReader;\n\n    /**\n     * @see DataReader.readData\n     */\n    Uint8ArrayReader.prototype.readData = function readData (size) {\n        this.checkOffset(size);\n        if(size === 0) {\n            // in IE10, when using subarray(idx, idx), we get the array [0x00] instead of [].\n            return new Uint8Array(0);\n        }\n        var result = this.data.subarray(this.zero + this.index, this.zero + this.index + size);\n        this.index += size;\n        return result;\n    };\n\n    return Uint8ArrayReader;\n}(ArrayReader));\n\n/**\n * Create a reader adapted to the data.\n * @param {String|ArrayBuffer|Uint8Array|Buffer} data the data to read.\n * @return {DataReader} the data reader.\n */\nfunction readerFor(data) {\n    var type = getTypeOf(data);\n    checkSupport(type);\n    if (type === \"string\" && !support.uint8array) {\n        return new StringReader(data);\n    }\n    if (support.uint8array) {\n        return new Uint8ArrayReader(transformTo(\"uint8array\", data));\n    }\n    return new ArrayReader(transformTo(\"array\", data));\n}\n\n/* eslint-disable */\n\nvar MADE_BY_DOS = 0x00;\nvar MADE_BY_UNIX = 0x03;\n\n/**\n * Find a compression registered in JSZip.\n * @param {string} compressionMethod the method magic to find.\n * @return {Object|null} the JSZip compression object, null if none found.\n */\nvar findCompression = function(compressionMethod) {\n    for (var method in compressions) {\n        if (!compressions.hasOwnProperty(method)) {\n            continue;\n        }\n        if (compressions[method].magic === compressionMethod) {\n            return compressions[method];\n        }\n    }\n    return null;\n};\n\n// class ZipEntry {{{\n/**\n * An entry in the zip file.\n * @constructor\n * @param {Object} options Options of the current file.\n * @param {Object} loadOptions Options for loading the stream.\n */\nvar ZipEntry = function ZipEntry(options, loadOptions) {\n    this.options = options;\n    this.loadOptions = loadOptions;\n};\n\n/**\n * say if the file is encrypted.\n * @return {boolean} true if the file is encrypted, false otherwise.\n */\nZipEntry.prototype.isEncrypted = function isEncrypted () {\n    // bit 1 is set\n    return (this.bitFlag & 0x0001) === 0x0001;\n};\n\n/**\n * say if the file has utf-8 filename/comment.\n * @return {boolean} true if the filename/comment is in utf-8, false otherwise.\n */\nZipEntry.prototype.useUTF8 = function useUTF8 () {\n    // bit 11 is set\n    return (this.bitFlag & 0x0800) === 0x0800;\n};\n\n/**\n * Read the local part of a zip file and add the info in this object.\n * @param {DataReader} reader the reader to use.\n */\nZipEntry.prototype.readLocalPart = function readLocalPart (reader) {\n    var compression, localExtraFieldsLength;\n\n    // we already know everything from the central dir !\n    // If the central dir data are false, we are doomed.\n    // On the bright side, the local part is scary  : zip64, data descriptors, both, etc.\n    // The less data we get here, the more reliable this should be.\n    // Let's skip the whole header and dash to the data !\n    reader.skip(22);\n    // in some zip created on windows, the filename stored in the central dir contains \\ instead of /.\n    // Strangely, the filename here is OK.\n    // I would love to treat these zip files as corrupted (see http://www.info-zip.org/FAQ.html#backslashes\n    // or APPNOTE#4.4.17.1, \"All slashes MUST be forward slashes '/'\") but there are a lot of bad zip generators...\n    // Search \"unzip mismatching \"local\" filename continuing with \"central\" filename version\" on\n    // the internet.\n    //\n    // I think I see the logic here : the central directory is used to display\n    // content and the local directory is used to extract the files. Mixing / and \\\n    // may be used to display \\ to windows users and use / when extracting the files.\n    // Unfortunately, this lead also to some issues : http://seclists.org/fulldisclosure/2009/Sep/394\n    this.fileNameLength = reader.readInt(2);\n    localExtraFieldsLength = reader.readInt(2); // can't be sure this will be the same as the central dir\n    // the fileName is stored as binary data, the handleUTF8 method will take care of the encoding.\n    this.fileName = reader.readData(this.fileNameLength);\n    reader.skip(localExtraFieldsLength);\n\n    if (this.compressedSize === -1 || this.uncompressedSize === -1) {\n        throw new Error(\"Bug or corrupted zip : didn't get enough information from the central directory \" + \"(compressedSize === -1 || uncompressedSize === -1)\");\n    }\n\n    compression = findCompression(this.compressionMethod);\n    if (compression === null) { // no compression found\n        throw new Error(\"Corrupted zip : compression \" + pretty(this.compressionMethod) + \" unknown (inner file : \" + transformTo(\"string\", this.fileName) + \")\");\n    }\n    this.decompressed = new CompressedObject(this.compressedSize, this.uncompressedSize, this.crc32, compression, reader.readData(this.compressedSize));\n};\n\n/**\n * Read the central part of a zip file and add the info in this object.\n * @param {DataReader} reader the reader to use.\n */\nZipEntry.prototype.readCentralPart = function readCentralPart (reader) {\n    this.versionMadeBy = reader.readInt(2);\n    reader.skip(2);\n    // this.versionNeeded = reader.readInt(2);\n    this.bitFlag = reader.readInt(2);\n    this.compressionMethod = reader.readString(2);\n    this.date = reader.readDate();\n    this.crc32 = reader.readInt(4);\n    this.compressedSize = reader.readInt(4);\n    this.uncompressedSize = reader.readInt(4);\n    var fileNameLength = reader.readInt(2);\n    this.extraFieldsLength = reader.readInt(2);\n    this.fileCommentLength = reader.readInt(2);\n    this.diskNumberStart = reader.readInt(2);\n    this.internalFileAttributes = reader.readInt(2);\n    this.externalFileAttributes = reader.readInt(4);\n    this.localHeaderOffset = reader.readInt(4);\n\n    if (this.isEncrypted()) {\n        throw new Error(\"Encrypted zip are not supported\");\n    }\n\n    // will be read in the local part, see the comments there\n    reader.skip(fileNameLength);\n    this.readExtraFields(reader);\n    this.parseZIP64ExtraField(reader);\n    this.fileComment = reader.readData(this.fileCommentLength);\n};\n\n/**\n * Parse the external file attributes and get the unix/dos permissions.\n */\nZipEntry.prototype.processAttributes = function processAttributes () {\n    this.unixPermissions = null;\n    this.dosPermissions = null;\n    var madeBy = this.versionMadeBy >> 8;\n\n    // Check if we have the DOS directory flag set.\n    // We look for it in the DOS and UNIX permissions\n    // but some unknown platform could set it as a compatibility flag.\n    this.dir = this.externalFileAttributes & 0x0010 ? true : false;\n\n    if(madeBy === MADE_BY_DOS) {\n        // first 6 bits (0 to 5)\n        this.dosPermissions = this.externalFileAttributes & 0x3F;\n    }\n\n    if(madeBy === MADE_BY_UNIX) {\n        this.unixPermissions = (this.externalFileAttributes >> 16) & 0xFFFF;\n        // the octal permissions are in (this.unixPermissions & 0x01FF).toString(8);\n    }\n\n    // fail safe : if the name ends with a / it probably means a folder\n    if (!this.dir && this.fileNameStr.slice(-1) === '/') {\n        this.dir = true;\n    }\n};\n\n/**\n * Parse the ZIP64 extra field and merge the info in the current ZipEntry.\n * @param {DataReader} reader the reader to use.\n */\nZipEntry.prototype.parseZIP64ExtraField = function parseZIP64ExtraField (reader) {\n\n    if (!this.extraFields[0x0001]) {\n        return;\n    }\n\n    // should be something, preparing the extra reader\n    var extraReader = readerFor(this.extraFields[0x0001].value);\n\n    // I really hope that these 64bits integer can fit in 32 bits integer, because js\n    // won't let us have more.\n    if (this.uncompressedSize === MAX_VALUE_32BITS) {\n        this.uncompressedSize = extraReader.readInt(8);\n    }\n    if (this.compressedSize === MAX_VALUE_32BITS) {\n        this.compressedSize = extraReader.readInt(8);\n    }\n    if (this.localHeaderOffset === MAX_VALUE_32BITS) {\n        this.localHeaderOffset = extraReader.readInt(8);\n    }\n    if (this.diskNumberStart === MAX_VALUE_32BITS) {\n        this.diskNumberStart = extraReader.readInt(4);\n    }\n};\n\n/**\n * Read the central part of a zip file and add the info in this object.\n * @param {DataReader} reader the reader to use.\n */\nZipEntry.prototype.readExtraFields = function readExtraFields (reader) {\n    var end = reader.index + this.extraFieldsLength,\n        extraFieldId,\n        extraFieldLength,\n        extraFieldValue;\n\n    if (!this.extraFields) {\n        this.extraFields = {};\n    }\n\n    while (reader.index < end) {\n        extraFieldId = reader.readInt(2);\n        extraFieldLength = reader.readInt(2);\n        extraFieldValue = reader.readData(extraFieldLength);\n\n        this.extraFields[extraFieldId] = {\n            id: extraFieldId,\n            length: extraFieldLength,\n            value: extraFieldValue\n        };\n    }\n};\n\n/**\n * Apply an UTF8 transformation if needed.\n */\nZipEntry.prototype.handleUTF8 = function handleUTF8 () {\n    var decodeParamType = support.uint8array ? \"uint8array\" : \"array\";\n    if (this.useUTF8()) {\n        this.fileNameStr = utf8decode(this.fileName);\n        this.fileCommentStr = utf8decode(this.fileComment);\n    } else {\n        var upath = this.findExtraFieldUnicodePath();\n        if (upath !== null) {\n            this.fileNameStr = upath;\n        } else {\n            // ASCII text or unsupported code page\n            var fileNameByteArray =  transformTo(decodeParamType, this.fileName);\n            this.fileNameStr = this.loadOptions.decodeFileName(fileNameByteArray);\n        }\n\n        var ucomment = this.findExtraFieldUnicodeComment();\n        if (ucomment !== null) {\n            this.fileCommentStr = ucomment;\n        } else {\n            // ASCII text or unsupported code page\n            var commentByteArray =  transformTo(decodeParamType, this.fileComment);\n            this.fileCommentStr = this.loadOptions.decodeFileName(commentByteArray);\n        }\n    }\n};\n\n/**\n * Find the unicode path declared in the extra field, if any.\n * @return {String} the unicode path, null otherwise.\n */\nZipEntry.prototype.findExtraFieldUnicodePath = function findExtraFieldUnicodePath () {\n    var upathField = this.extraFields[0x7075];\n    if (upathField) {\n        var extraReader = readerFor(upathField.value);\n\n        // wrong version\n        if (extraReader.readInt(1) !== 1) {\n            return null;\n        }\n\n        // the crc of the filename changed, this field is out of date.\n        if (crc32wrapper(this.fileName) !== extraReader.readInt(4)) {\n            return null;\n        }\n\n        return utf8decode(extraReader.readData(upathField.length - 5));\n    }\n    return null;\n};\n\n/**\n * Find the unicode comment declared in the extra field, if any.\n * @return {String} the unicode comment, null otherwise.\n */\nZipEntry.prototype.findExtraFieldUnicodeComment = function findExtraFieldUnicodeComment () {\n    var ucommentField = this.extraFields[0x6375];\n    if (ucommentField) {\n        var extraReader = readerFor(ucommentField.value);\n\n        // wrong version\n        if (extraReader.readInt(1) !== 1) {\n            return null;\n        }\n\n        // the crc of the comment changed, this field is out of date.\n        if (crc32wrapper(this.fileComment) !== extraReader.readInt(4)) {\n            return null;\n        }\n\n        return utf8decode(extraReader.readData(ucommentField.length - 5));\n    }\n    return null;\n};\n\n/* eslint-disable */\n\n//  class ZipEntries {{{\n/**\n * All the entries in the zip file.\n * @constructor\n * @param {Object} loadOptions Options for loading the stream.\n */\nvar ZipEntries = function ZipEntries(loadOptions) {\n    this.files = [];\n    this.loadOptions = loadOptions;\n};\n\n/**\n * Check that the reader is on the specified signature.\n * @param {string} expectedSignature the expected signature.\n * @throws {Error} if it is an other signature.\n */\nZipEntries.prototype.checkSignature = function checkSignature (expectedSignature) {\n    if (!this.reader.readAndCheckSignature(expectedSignature)) {\n        this.reader.index -= 4;\n        var signature = this.reader.readString(4);\n        throw new Error(\"Corrupted zip or bug: unexpected signature \" + \"(\" + pretty(signature) + \", expected \" + pretty(expectedSignature) + \")\");\n    }\n};\n\n/**\n * Check if the given signature is at the given index.\n * @param {number} askedIndex the index to check.\n * @param {string} expectedSignature the signature to expect.\n * @return {boolean} true if the signature is here, false otherwise.\n */\nZipEntries.prototype.isSignature = function isSignature (askedIndex, expectedSignature) {\n    var currentIndex = this.reader.index;\n    this.reader.setIndex(askedIndex);\n    var signature = this.reader.readString(4);\n    var result = signature === expectedSignature;\n    this.reader.setIndex(currentIndex);\n    return result;\n};\n\n/**\n * Read the end of the central directory.\n */\nZipEntries.prototype.readBlockEndOfCentral = function readBlockEndOfCentral () {\n    this.diskNumber = this.reader.readInt(2);\n    this.diskWithCentralDirStart = this.reader.readInt(2);\n    this.centralDirRecordsOnThisDisk = this.reader.readInt(2);\n    this.centralDirRecords = this.reader.readInt(2);\n    this.centralDirSize = this.reader.readInt(4);\n    this.centralDirOffset = this.reader.readInt(4);\n\n    this.zipCommentLength = this.reader.readInt(2);\n    // warning : the encoding depends of the system locale\n    // On a linux machine with LANG=en_US.utf8, this field is utf8 encoded.\n    // On a windows machine, this field is encoded with the localized windows code page.\n    var zipComment = this.reader.readData(this.zipCommentLength);\n    var decodeParamType = support.uint8array ? \"uint8array\" : \"array\";\n    // To get consistent behavior with the generation part, we will assume that\n    // this is utf8 encoded unless specified otherwise.\n    var decodeContent = transformTo(decodeParamType, zipComment);\n    this.zipComment = this.loadOptions.decodeFileName(decodeContent);\n};\n\n/**\n * Read the end of the Zip 64 central directory.\n * Not merged with the method readEndOfCentral :\n * The end of central can coexist with its Zip64 brother,\n * I don't want to read the wrong number of bytes !\n */\nZipEntries.prototype.readBlockZip64EndOfCentral = function readBlockZip64EndOfCentral () {\n    this.zip64EndOfCentralSize = this.reader.readInt(8);\n    this.reader.skip(4);\n    // this.versionMadeBy = this.reader.readString(2);\n    // this.versionNeeded = this.reader.readInt(2);\n    this.diskNumber = this.reader.readInt(4);\n    this.diskWithCentralDirStart = this.reader.readInt(4);\n    this.centralDirRecordsOnThisDisk = this.reader.readInt(8);\n    this.centralDirRecords = this.reader.readInt(8);\n    this.centralDirSize = this.reader.readInt(8);\n    this.centralDirOffset = this.reader.readInt(8);\n\n    this.zip64ExtensibleData = {};\n    var extraDataSize = this.zip64EndOfCentralSize - 44,\n        index = 0,\n        extraFieldId,\n        extraFieldLength,\n        extraFieldValue;\n    while (index < extraDataSize) {\n        extraFieldId = this.reader.readInt(2);\n        extraFieldLength = this.reader.readInt(4);\n        extraFieldValue = this.reader.readData(extraFieldLength);\n        this.zip64ExtensibleData[extraFieldId] = {\n            id: extraFieldId,\n            length: extraFieldLength,\n            value: extraFieldValue\n        };\n    }\n};\n\n/**\n * Read the end of the Zip 64 central directory locator.\n */\nZipEntries.prototype.readBlockZip64EndOfCentralLocator = function readBlockZip64EndOfCentralLocator () {\n    this.diskWithZip64CentralDirStart = this.reader.readInt(4);\n    this.relativeOffsetEndOfZip64CentralDir = this.reader.readInt(8);\n    this.disksCount = this.reader.readInt(4);\n    if (this.disksCount > 1) {\n        throw new Error(\"Multi-volumes zip are not supported\");\n    }\n};\n\n/**\n * Read the local files, based on the offset read in the central part.\n */\nZipEntries.prototype.readLocalFiles = function readLocalFiles () {\n    var i, file;\n    for (i = 0; i < this.files.length; i++) {\n        file = this.files[i];\n        this.reader.setIndex(file.localHeaderOffset);\n        this.checkSignature(LOCAL_FILE_HEADER);\n        file.readLocalPart(this.reader);\n        file.handleUTF8();\n        file.processAttributes();\n    }\n};\n\n/**\n * Read the central directory.\n */\nZipEntries.prototype.readCentralDir = function readCentralDir () {\n    var file;\n\n    this.reader.setIndex(this.centralDirOffset);\n    while (this.reader.readAndCheckSignature(CENTRAL_FILE_HEADER)) {\n        file = new ZipEntry({\n            zip64: this.zip64\n        }, this.loadOptions);\n        file.readCentralPart(this.reader);\n        this.files.push(file);\n    }\n\n    if (this.centralDirRecords !== this.files.length) {\n        if (this.centralDirRecords !== 0 && this.files.length === 0) {\n            // We expected some records but couldn't find ANY.\n            // This is really suspicious, as if something went wrong.\n            throw new Error(\"Corrupted zip or bug: expected \" + this.centralDirRecords + \" records in central dir, got \" + this.files.length);\n        }\n    }\n};\n\n/**\n * Read the end of central directory.\n */\nZipEntries.prototype.readEndOfCentral = function readEndOfCentral () {\n    var offset = this.reader.lastIndexOfSignature(CENTRAL_DIRECTORY_END);\n    if (offset < 0) {\n        // Check if the content is a truncated zip or complete garbage.\n        // A \"LOCAL_FILE_HEADER\" is not required at the beginning (auto\n        // extractible zip for example) but it can give a good hint.\n        // If an ajax request was used without responseType, we will also\n        // get unreadable data.\n        var isGarbage = !this.isSignature(0, LOCAL_FILE_HEADER);\n\n        if (isGarbage) {\n            throw new Error(\"Can't find end of central directory : is this a zip file ? \" +\n                            \"If it is, see https://stuk.github.io/jszip/documentation/howto/read_zip.html\");\n        } else {\n            throw new Error(\"Corrupted zip: can't find end of central directory\");\n        }\n\n    }\n    this.reader.setIndex(offset);\n    var endOfCentralDirOffset = offset;\n    this.checkSignature(CENTRAL_DIRECTORY_END);\n    this.readBlockEndOfCentral();\n\n\n    /* extract from the zip spec :\n        4)  If one of the fields in the end of central directory\n            record is too small to hold required data, the field\n            should be set to -1 (0xFFFF or 0xFFFFFFFF) and the\n            ZIP64 format record should be created.\n        5)  The end of central directory record and the\n            Zip64 end of central directory locator record must\n            reside on the same disk when splitting or spanning\n            an archive.\n     */\n    if (this.diskNumber === MAX_VALUE_16BITS || this.diskWithCentralDirStart === MAX_VALUE_16BITS || this.centralDirRecordsOnThisDisk === MAX_VALUE_16BITS || this.centralDirRecords === MAX_VALUE_16BITS || this.centralDirSize === MAX_VALUE_32BITS || this.centralDirOffset === MAX_VALUE_32BITS) {\n        this.zip64 = true;\n\n        /*\n        Warning : the zip64 extension is supported, but ONLY if the 64bits integer read from\n        the zip file can fit into a 32bits integer. This cannot be solved : JavaScript represents\n        all numbers as 64-bit double precision IEEE 754 floating point numbers.\n        So, we have 53bits for integers and bitwise operations treat everything as 32bits.\n        see https://developer.mozilla.org/en-US/docs/JavaScript/Reference/Operators/Bitwise_Operators\n        and http://www.ecma-international.org/publications/files/ECMA-ST/ECMA-262.pdf section 8.5\n        */\n\n        // should look for a zip64 EOCD locator\n        offset = this.reader.lastIndexOfSignature(ZIP64_CENTRAL_DIRECTORY_LOCATOR);\n        if (offset < 0) {\n            throw new Error(\"Corrupted zip: can't find the ZIP64 end of central directory locator\");\n        }\n        this.reader.setIndex(offset);\n        this.checkSignature(ZIP64_CENTRAL_DIRECTORY_LOCATOR);\n        this.readBlockZip64EndOfCentralLocator();\n\n        // now the zip64 EOCD record\n        if (!this.isSignature(this.relativeOffsetEndOfZip64CentralDir, ZIP64_CENTRAL_DIRECTORY_END)) {\n            // console.warn(\"ZIP64 end of central directory not where expected.\");\n            this.relativeOffsetEndOfZip64CentralDir = this.reader.lastIndexOfSignature(ZIP64_CENTRAL_DIRECTORY_END);\n            if (this.relativeOffsetEndOfZip64CentralDir < 0) {\n                throw new Error(\"Corrupted zip: can't find the ZIP64 end of central directory\");\n            }\n        }\n        this.reader.setIndex(this.relativeOffsetEndOfZip64CentralDir);\n        this.checkSignature(ZIP64_CENTRAL_DIRECTORY_END);\n        this.readBlockZip64EndOfCentral();\n    }\n\n    var expectedEndOfCentralDirOffset = this.centralDirOffset + this.centralDirSize;\n    if (this.zip64) {\n        expectedEndOfCentralDirOffset += 20; // end of central dir 64 locator\n        expectedEndOfCentralDirOffset += 12 /* should not include the leading 12 bytes */ + this.zip64EndOfCentralSize;\n    }\n\n    var extraBytes = endOfCentralDirOffset - expectedEndOfCentralDirOffset;\n\n    if (extraBytes > 0) {\n        // console.warn(extraBytes, \"extra bytes at beginning or within zipfile\");\n        if (this.isSignature(endOfCentralDirOffset, CENTRAL_FILE_HEADER)) ; else {\n            // the offset is wrong, update the \"zero\" of the reader\n            // this happens if data has been prepended (crx files for example)\n            this.reader.zero = extraBytes;\n        }\n    } else if (extraBytes < 0) {\n        throw new Error(\"Corrupted zip: missing \" + Math.abs(extraBytes) + \" bytes.\");\n    }\n};\n\nZipEntries.prototype.prepareReader = function prepareReader (data) {\n    this.reader = readerFor(data);\n};\n\n/**\n * Read a zip file and create ZipEntries.\n * @param {String|ArrayBuffer|Uint8Array|Buffer} data the binary string representing a zip file.\n */\nZipEntries.prototype.load = function load (data) {\n    this.prepareReader(data);\n    this.readEndOfCentral();\n    this.readCentralDir();\n    this.readLocalFiles();\n};\n\n/* eslint-disable */\n\n/**\n * Check the CRC32 of an entry.\n * @param {ZipEntry} zipEntry the zip entry to check.\n * @return {Promise} the result.\n */\nfunction checkEntryCRC32(zipEntry) {\n    return new external.Promise(function (resolve, reject) {\n        var worker = zipEntry.decompressed.getContentWorker().pipe(new Crc32Probe());\n        worker.on(\"error\", function (e) {\n            reject(e);\n        })\n        .on(\"end\", function () {\n            if (worker.streamInfo.crc32 !== zipEntry.decompressed.crc32) {\n                reject(new Error(\"Corrupted zip : CRC32 mismatch\"));\n            } else {\n                resolve();\n            }\n        })\n        .resume();\n    });\n}\n\nfunction load(data, options) {\n    var zip = this;\n    options = extend(options || {}, {\n        base64: false,\n        checkCRC32: false,\n        optimizedBinaryString: false,\n        createFolders: false,\n        decodeFileName: utf8decode\n    });\n\n    return prepareContent(\"the loaded zip file\", data, true, options.optimizedBinaryString, options.base64)\n    .then(function(data) {\n        var zipEntries = new ZipEntries(options);\n        zipEntries.load(data);\n        return zipEntries;\n    }).then(function checkCRC32(zipEntries) {\n        var promises = [external.Promise.resolve(zipEntries)];\n        var files = zipEntries.files;\n        if (options.checkCRC32) {\n            for (var i = 0; i < files.length; i++) {\n                promises.push(checkEntryCRC32(files[i]));\n            }\n        }\n        return external.Promise.all(promises);\n    }).then(function addFiles(results) {\n        var zipEntries = results.shift();\n        var files = zipEntries.files;\n        for (var i = 0; i < files.length; i++) {\n            var input = files[i];\n            zip.file(input.fileNameStr, input.decompressed, {\n                binary: true,\n                optimizedBinaryString: true,\n                date: input.date,\n                dir: input.dir,\n                comment : input.fileCommentStr.length ? input.fileCommentStr : null,\n                unixPermissions : input.unixPermissions,\n                dosPermissions : input.dosPermissions,\n                createFolders: options.createFolders\n            });\n        }\n        if (zipEntries.zipComment.length) {\n            zip.comment = zipEntries.zipComment;\n        }\n\n        return zip;\n    });\n}\n\n/* eslint-disable */\n\n/**\n * Add a file in the current folder.\n * @private\n * @param {string} name the name of the file\n * @param {String|ArrayBuffer|Uint8Array|Buffer} data the data of the file\n * @param {Object} originalOptions the options of the file\n * @return {Object} the new file.\n */\nvar fileAdd = function(name, data, originalOptions) {\n    // be sure sub folders exist\n    var dataType = getTypeOf(data),\n        parent;\n\n\n    /*\n     * Correct options.\n     */\n\n    var o = extend(originalOptions || {}, defaults);\n    o.date = o.date || new Date();\n    if (o.compression !== null) {\n        o.compression = o.compression.toUpperCase();\n    }\n\n    if (typeof o.unixPermissions === \"string\") {\n        o.unixPermissions = parseInt(o.unixPermissions, 8);\n    }\n\n    // UNX_IFDIR  0040000 see zipinfo.c\n    if (o.unixPermissions && (o.unixPermissions & 0x4000)) {\n        o.dir = true;\n    }\n    // Bit 4    Directory\n    if (o.dosPermissions && (o.dosPermissions & 0x0010)) {\n        o.dir = true;\n    }\n\n    if (o.dir) {\n        name = forceTrailingSlash(name);\n    }\n    if (o.createFolders && (parent = parentFolder(name))) {\n        folderAdd.call(this, parent, true);\n    }\n\n    var isUnicodeString = dataType === \"string\" && o.binary === false && o.base64 === false;\n    if (!originalOptions || typeof originalOptions.binary === \"undefined\") {\n        o.binary = !isUnicodeString;\n    }\n\n\n    var isCompressedEmpty = (data instanceof CompressedObject) && data.uncompressedSize === 0;\n\n    if (isCompressedEmpty || o.dir || !data || data.length === 0) {\n        o.base64 = false;\n        o.binary = true;\n        data = \"\";\n        o.compression = \"STORE\";\n        dataType = \"string\";\n    }\n\n    /*\n     * Convert content to fit.\n     */\n\n    var zipObjectContent = null;\n    if (data instanceof CompressedObject || data instanceof GenericWorker) {\n        zipObjectContent = data;\n    } else {\n        zipObjectContent = prepareContent(name, data, o.binary, o.optimizedBinaryString, o.base64);\n    }\n\n    var object = new ZipObject(name, zipObjectContent, o);\n    this.files[name] = object;\n    /*\n    TODO: we can't throw an exception because we have async promises\n    (we can have a promise of a Date() for example) but returning a\n    promise is useless because file(name, data) returns the JSZip\n    object for chaining. Should we break that to allow the user\n    to catch the error ?\n\n    return external.Promise.resolve(zipObjectContent)\n    .then(function () {\n        return object;\n    });\n    */\n};\n\n/**\n * Find the parent folder of the path.\n * @private\n * @param {string} path the path to use\n * @return {string} the parent folder, or \"\"\n */\nvar parentFolder = function (path) {\n    if (path.slice(-1) === '/') {\n        path = path.substring(0, path.length - 1);\n    }\n    var lastSlash = path.lastIndexOf('/');\n    return (lastSlash > 0) ? path.substring(0, lastSlash) : \"\";\n};\n\n/**\n * Returns the path with a slash at the end.\n * @private\n * @param {String} path the path to check.\n * @return {String} the path with a trailing slash.\n */\nvar forceTrailingSlash = function(path) {\n    // Check the name ends with a /\n    if (path.slice(-1) !== \"/\") {\n        path += \"/\"; // IE doesn't like substr(-1)\n    }\n    return path;\n};\n\n/**\n * Add a (sub) folder in the current folder.\n * @private\n * @param {string} name the folder's name\n * @param {boolean=} [createFolders] If true, automatically create sub\n *  folders. Defaults to false.\n * @return {Object} the new folder.\n */\nvar folderAdd = function(name, createFolders$1) {\n    createFolders$1 = (typeof createFolders$1 !== 'undefined') ? createFolders$1 : createFolders;\n\n    name = forceTrailingSlash(name);\n\n    // Does this folder already exist?\n    if (!this.files[name]) {\n        fileAdd.call(this, name, null, {\n            dir: true,\n            createFolders: createFolders$1\n        });\n    }\n    return this.files[name];\n};\n\n/**\n* Cross-window, cross-Node-context regular expression detection\n* @param  {Object}  object Anything\n* @return {Boolean}        true if the object is a regular expression,\n* false otherwise\n*/\nfunction isRegExp(object) {\n    return Object.prototype.toString.call(object) === \"[object RegExp]\";\n}\n\n/**\n * Representation a of zip file in js\n * @constructor\n */\nvar JSZip = function JSZip() {\n    if (arguments.length) {\n        throw new Error(\"The constructor with parameters has been removed in JSZip 3.0, please check the upgrade guide.\");\n    }\n\n    // object containing the files :\n    // {\n    //   \"folder/\" : {...},\n    //   \"folder/data.txt\" : {...}\n    // }\n    // NOTE: we use a null prototype because we do not\n    // want filenames like \"toString\" coming from a zip file\n    // to overwrite methods and attributes in a normal Object.\n    this.files = Object.create(null);\n\n    this.comment = null;\n\n    // Where we are in the hierarchy\n    this.root = \"\";\n    this.clone = function() {\n        var newObj = new JSZip();\n        for (var i in this) {\n            if (typeof this[i] !== \"function\") {\n                newObj[i] = this[i];\n            }\n        }\n        return newObj;\n    };\n};\n\nvar staticAccessors = { support: { configurable: true },defaults: { configurable: true },version: { configurable: true },external: { configurable: true } };\n\n/**\n * @see loadAsync\n */\nJSZip.prototype.load = function load () {\n    throw new Error(\"This method has been removed in JSZip 3.0, please check the upgrade guide.\");\n};\n\n/**\n * Call a callback function for each entry at this folder level.\n * @param {Function} cb the callback function:\n * function (relativePath, file) {...}\n * It takes 2 arguments : the relative path and the file.\n */\nJSZip.prototype.forEach = function forEach (cb) {\n    var filename, relativePath, file;\n    for (filename in this.files) {\n        file = this.files[filename];\n        relativePath = filename.slice(this.root.length, filename.length);\n        if (relativePath && filename.slice(0, this.root.length) === this.root) { // the file is in the current root\n            cb(relativePath, file); // TODO reverse the parameters ? need to be clean AND consistent with the filter search fn...\n        }\n    }\n};\n\n/**\n * Filter nested files/folders with the specified function.\n * @param {Function} search the predicate to use :\n * function (relativePath, file) {...}\n * It takes 2 arguments : the relative path and the file.\n * @return {Array} An array of matching elements.\n */\nJSZip.prototype.filter = function filter (search) {\n    var result = [];\n    this.forEach(function (relativePath, entry) {\n        if (search(relativePath, entry)) { // the file matches the function\n            result.push(entry);\n        }\n\n    });\n    return result;\n};\n\n/**\n * Add a file to the zip file, or search a file.\n * @param   {string|RegExp} name The name of the file to add (if data is defined),\n * the name of the file to find (if no data) or a regex to match files.\n * @param   {String|ArrayBuffer|Uint8Array|Buffer} data  The file data, either raw or base64 encoded\n * @param   {Object} o File options\n * @return  {JSZip|Object|Array} this JSZip object (when adding a file),\n * a file (when searching by string) or an array of files (when searching by regex).\n */\nJSZip.prototype.file = function file (name, data, o) {\n    if (arguments.length === 1) {\n        if (isRegExp(name)) {\n            var regexp = name;\n            return this.filter(function(relativePath, file) {\n                return !file.dir && regexp.test(relativePath);\n            });\n        }\n        else { // text\n            var obj = this.files[this.root + name];\n            if (obj && !obj.dir) {\n                return obj;\n            } else {\n                return null;\n            }\n        }\n    }\n    else { // more than one argument : we have data !\n        name = this.root + name;\n        fileAdd.call(this, name, data, o);\n    }\n    return this;\n};\n\n/**\n * Add a directory to the zip file, or search.\n * @param   {String|RegExp} arg The name of the directory to add, or a regex to search folders.\n * @return  {JSZip} an object with the new directory as the root, or an array containing matching folders.\n */\nJSZip.prototype.folder = function folder (arg) {\n    if (!arg) {\n        return this;\n    }\n\n    if (isRegExp(arg)) {\n        return this.filter(function(relativePath, file) {\n            return file.dir && arg.test(relativePath);\n        });\n    }\n\n    // else, name is a new folder\n    var name = this.root + arg;\n    var newFolder = folderAdd.call(this, name);\n\n    // Allow chaining by returning a new object with this folder as the root\n    var ret = this.clone();\n    ret.root = newFolder.name;\n    return ret;\n};\n\n/**\n * Delete a file, or a directory and all sub-files, from the zip\n * @param {string} name the name of the file to delete\n * @return {JSZip} this JSZip object\n */\nJSZip.prototype.remove = function remove (name) {\n    name = this.root + name;\n    var file = this.files[name];\n    if (!file) {\n        // Look for any folders\n        if (name.slice(-1) !== \"/\") {\n            name += \"/\";\n        }\n        file = this.files[name];\n    }\n\n    if (file && !file.dir) {\n        // file\n        delete this.files[name];\n    } else {\n        // maybe a folder, delete recursively\n        var kids = this.filter(function(relativePath, file) {\n            return file.name.slice(0, name.length) === name;\n        });\n        for (var i = 0; i < kids.length; i++) {\n            delete this.files[kids[i].name];\n        }\n    }\n\n    return this;\n};\n\n/**\n * Generate the complete zip file\n * @param {Object} options the options to generate the zip file :\n * - compression, \"STORE\" by default.\n * - type, \"base64\" by default. Values are : string, base64, uint8array, arraybuffer, blob.\n * @return {String|Uint8Array|ArrayBuffer|Buffer|Blob} the zip file\n */\nJSZip.prototype.generate = function generate (options) {\n    throw new Error(\"This method has been removed in JSZip 3.0, please check the upgrade guide.\");\n};\n\n/**\n * Generate the complete zip file as an internal stream.\n * @param {Object} options the options to generate the zip file :\n * - compression, \"STORE\" by default.\n * - type, \"base64\" by default. Values are : string, base64, uint8array, arraybuffer, blob.\n * @return {StreamHelper} the streamed zip file.\n */\nJSZip.prototype.generateInternalStream = function generateInternalStream (options) {\n  var worker, opts = {};\n  try {\n      opts = extend(options || {}, {\n          streamFiles: false,\n          compression: \"STORE\",\n          compressionOptions : null,\n          type: \"\",\n          platform: \"DOS\",\n          comment: null,\n          mimeType: 'application/zip',\n          encodeFileName: utf8encode\n      });\n\n      opts.type = opts.type.toLowerCase();\n      opts.compression = opts.compression.toUpperCase();\n\n      // \"binarystring\" is preferred but the internals use \"string\".\n      if(opts.type === \"binarystring\") {\n        opts.type = \"string\";\n      }\n\n      if (!opts.type) {\n        throw new Error(\"No output type specified.\");\n      }\n\n      checkSupport(opts.type);\n\n      // accept nodejs `process.platform`\n      if(\n          opts.platform === 'darwin' ||\n          opts.platform === 'freebsd' ||\n          opts.platform === 'linux' ||\n          opts.platform === 'sunos'\n      ) {\n          opts.platform = \"UNIX\";\n      }\n      if (opts.platform === 'win32') {\n          opts.platform = \"DOS\";\n      }\n\n      var comment = opts.comment || this.comment || \"\";\n      worker = generateWorker(this, opts, comment);\n  } catch (e) {\n    worker = new GenericWorker(\"error\");\n    worker.error(e);\n  }\n  return new StreamHelper(worker, opts.type || \"string\", opts.mimeType);\n};\n\n/**\n * Generate the complete zip file asynchronously.\n * @see generateInternalStream\n */\nJSZip.prototype.generateAsync = function generateAsync (options, onUpdate) {\n    return this.generateInternalStream(options).accumulate(onUpdate);\n};\n\nJSZip.prototype.loadAsync = function loadAsync (data, options) {\n    return load.apply(this, [data, options]);\n};\n\nJSZip.loadAsync = function loadAsync (content, options) {\n    return new JSZip().loadAsync(content, options);\n};\n    \nstaticAccessors.support.get = function () {\n    return support;\n};\n\nstaticAccessors.defaults.get = function () {\n    return defaults;\n};\n\nstaticAccessors.version.get = function () {\n    return \"3.2.2-esm\";\n};\n\nstaticAccessors.external.get = function () {\n    return external;\n};\n\nObject.defineProperties( JSZip, staticAccessors );\n\nexport { JSZip as default };\n","(function(a,b){if(\"function\"==typeof define&&define.amd)define([],b);else if(\"undefined\"!=typeof exports)b();else{b(),a.FileSaver={exports:{}}.exports}})(this,function(){\"use strict\";function b(a,b){return\"undefined\"==typeof b?b={autoBom:!1}:\"object\"!=typeof b&&(console.warn(\"Deprecated: Expected third argument to be a object\"),b={autoBom:!b}),b.autoBom&&/^\\s*(?:text\\/\\S*|application\\/xml|\\S*\\/\\S*\\+xml)\\s*;.*charset\\s*=\\s*utf-8/i.test(a.type)?new Blob([\"\\uFEFF\",a],{type:a.type}):a}function c(a,b,c){var d=new XMLHttpRequest;d.open(\"GET\",a),d.responseType=\"blob\",d.onload=function(){g(d.response,b,c)},d.onerror=function(){console.error(\"could not download file\")},d.send()}function d(a){var b=new XMLHttpRequest;b.open(\"HEAD\",a,!1);try{b.send()}catch(a){}return 200<=b.status&&299>=b.status}function e(a){try{a.dispatchEvent(new MouseEvent(\"click\"))}catch(c){var b=document.createEvent(\"MouseEvents\");b.initMouseEvent(\"click\",!0,!0,window,0,0,0,80,20,!1,!1,!1,!1,0,null),a.dispatchEvent(b)}}var f=\"object\"==typeof window&&window.window===window?window:\"object\"==typeof self&&self.self===self?self:\"object\"==typeof global&&global.global===global?global:void 0,a=f.navigator&&/Macintosh/.test(navigator.userAgent)&&/AppleWebKit/.test(navigator.userAgent)&&!/Safari/.test(navigator.userAgent),g=f.saveAs||(\"object\"!=typeof window||window!==f?function(){}:\"download\"in HTMLAnchorElement.prototype&&!a?function(b,g,h){var i=f.URL||f.webkitURL,j=document.createElement(\"a\");g=g||b.name||\"download\",j.download=g,j.rel=\"noopener\",\"string\"==typeof b?(j.href=b,j.origin===location.origin?e(j):d(j.href)?c(b,g,h):e(j,j.target=\"_blank\")):(j.href=i.createObjectURL(b),setTimeout(function(){i.revokeObjectURL(j.href)},4E4),setTimeout(function(){e(j)},0))}:\"msSaveOrOpenBlob\"in navigator?function(f,g,h){if(g=g||f.name||\"download\",\"string\"!=typeof f)navigator.msSaveOrOpenBlob(b(f,h),g);else if(d(f))c(f,g,h);else{var i=document.createElement(\"a\");i.href=f,i.target=\"_blank\",setTimeout(function(){e(i)})}}:function(b,d,e,g){if(g=g||open(\"\",\"_blank\"),g&&(g.document.title=g.document.body.innerText=\"downloading...\"),\"string\"==typeof b)return c(b,d,e);var h=\"application/octet-stream\"===b.type,i=/constructor/i.test(f.HTMLElement)||f.safari,j=/CriOS\\/[\\d]+/.test(navigator.userAgent);if((j||h&&i||a)&&\"undefined\"!=typeof FileReader){var k=new FileReader;k.onloadend=function(){var a=k.result;a=j?a:a.replace(/^data:[^;]*;/,\"data:attachment/file;\"),g?g.location.href=a:location=a,g=null},k.readAsDataURL(b)}else{var l=f.URL||f.webkitURL,m=l.createObjectURL(b);g?g.location=m:location.href=m,g=null,setTimeout(function(){l.revokeObjectURL(m)},4E4)}});f.saveAs=g.saveAs=g,\"undefined\"!=typeof module&&(module.exports=g)});\n\n//# sourceMappingURL=FileSaver.min.js.map","import JSZip from \"@progress/jszip-esm\";\r\n\r\nimport { saveAs } from \"file-saver\";\r\n\r\nimport { Dates, Texts } from \"@salaxy/core\";\r\n\r\n/**\r\n * Copied and modified from https://github.com/egeriis/zipcelx#readme\r\n */\r\nclass Zipcelx {\r\n  private CELL_TYPE_STRING = \"string\";\r\n  private CELL_TYPE_NUMBER = \"number\";\r\n  private CELL_TYPE_DATE = \"date\";\r\n  private CELL_TYPE_BOOLEAN = \"boolean\";\r\n\r\n  private MISSING_KEY_FILENAME = \"Zipclex config missing property filename\";\r\n  private INVALID_TYPE_FILENAME = \"Zipclex filename can only be of type string\";\r\n  private INVALID_TYPE_SHEET = \"Zipcelx sheet data is not of type array\";\r\n  private INVALID_TYPE_SHEET_DATA = \"Zipclex sheet data childs is not of type array\";\r\n\r\n  private stylesXML = `<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"yes\"?>\r\n  <styleSheet xmlns=\"http://schemas.openxmlformats.org/spreadsheetml/2006/main\" >\r\n    <fonts count=\"1\">\r\n      <font>\r\n        <sz val=\"11\" />\r\n        <color theme=\"1\" />\r\n        <name val=\"Calibri\" />\r\n        <family val=\"2\" />\r\n        <scheme val=\"minor\" />\r\n      </font>\r\n    </fonts>\r\n    <fills count=\"2\">\r\n      <fill>\r\n        <patternFill patternType=\"none\" />\r\n      </fill>\r\n      <fill>\r\n        <patternFill patternType=\"gray125\" />\r\n      </fill>\r\n    </fills>\r\n    <borders count=\"1\">\r\n      <border>\r\n        <left />\r\n        <right />\r\n        <top />\r\n        <bottom />\r\n        <diagonal />\r\n      </border>\r\n    </borders>\r\n    <cellStyleXfs count=\"1\">\r\n      <xf numFmtId=\"0\" fontId=\"0\" fillId=\"0\" borderId=\"0\" />\r\n    </cellStyleXfs>\r\n    <cellXfs count=\"2\">\r\n      <xf numFmtId=\"0\" fontId=\"0\" fillId=\"0\" borderId=\"0\" xfId=\"0\" />\r\n      <xf numFmtId=\"14\" fontId=\"0\" fillId=\"0\" borderId=\"0\" xfId=\"0\" applyNumberFormat=\"1\" />\r\n    </cellXfs>\r\n    <cellStyles count=\"1\">\r\n      <cellStyle name=\"Normal\" xfId=\"0\" builtinId=\"0\" />\r\n    </cellStyles>\r\n  </styleSheet>\r\n  `;\r\n  private workbookXML = `<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"yes\"?>\r\n  <workbook xmlns=\"http://schemas.openxmlformats.org/spreadsheetml/2006/main\"\r\n           xmlns:r=\"http://schemas.openxmlformats.org/officeDocument/2006/relationships\">\r\n    <sheets>\r\n      <sheet name=\"Sheet1\" sheetId=\"1\" r:id=\"rId1\" />\r\n    </sheets>\r\n  </workbook>`;\r\n  private workbookXMLRels = `<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"yes\"?>\r\n  <Relationships xmlns=\"http://schemas.openxmlformats.org/package/2006/relationships\">\r\n    <Relationship Id=\"rId3\" Type=\"http://schemas.openxmlformats.org/officeDocument/2006/relationships/styles\" Target=\"styles.xml\" />\r\n    <Relationship Id=\"rId1\" Type=\"http://schemas.openxmlformats.org/officeDocument/2006/relationships/worksheet\" Target=\"worksheets/sheet1.xml\" />\r\n  </Relationships>`;\r\n  private rels = `<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"yes\"?>\r\n  <Relationships xmlns=\"http://schemas.openxmlformats.org/package/2006/relationships\">\r\n    <Relationship Id=\"rId1\" Type=\"http://schemas.openxmlformats.org/officeDocument/2006/relationships/officeDocument\" Target=\"xl/workbook.xml\" />\r\n  </Relationships>`;\r\n  private contentTypes = `<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"yes\"?>\r\n  <Types xmlns=\"http://schemas.openxmlformats.org/package/2006/content-types\">\r\n    <Default Extension=\"rels\" ContentType=\"application/vnd.openxmlformats-package.relationships+xml\" />\r\n    <Default Extension=\"xml\" ContentType=\"application/xml\" />\r\n    <Override PartName=\"/xl/workbook.xml\" ContentType=\"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet.main+xml\" />\r\n    <Override PartName=\"/xl/worksheets/sheet1.xml\" ContentType=\"application/vnd.openxmlformats-officedocument.spreadsheetml.worksheet+xml\" />\r\n    <Override PartName=\"/xl/styles.xml\" ContentType=\"application/vnd.openxmlformats-officedocument.spreadsheetml.styles+xml\" />\r\n  </Types>`;\r\n  private templateSheet = `<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"yes\"?>\r\n  <worksheet xmlns=\"http://schemas.openxmlformats.org/spreadsheetml/2006/main\"\r\n             xmlns:r=\"http://schemas.openxmlformats.org/officeDocument/2006/relationships\">\r\n    <cols>{cols}</cols>\r\n    <sheetData>{rows}</sheetData>\r\n  </worksheet>`;\r\n\r\n  /**\r\n   * Generates excel blob from the configuration\r\n   */\r\n  public generateExcel = (config): Promise<any> => {\r\n    if (!this.validator(config)) {\r\n      throw new Error(\"Validation failed.\");\r\n    }\r\n\r\n    const zip = new JSZip();\r\n    const xl = zip.folder(\"xl\");\r\n    xl.file(\"workbook.xml\", this.workbookXML);\r\n    xl.file(\"styles.xml\", this.stylesXML);\r\n    xl.file(\"_rels/workbook.xml.rels\", this.workbookXMLRels);\r\n    zip.file(\"_rels/.rels\", this.rels);\r\n    zip.file(\"[Content_Types].xml\", this.contentTypes);\r\n\r\n    const worksheet = this.generateXMLWorksheet(config.sheet.data);\r\n    xl.file(\"worksheets/sheet1.xml\", worksheet);\r\n\r\n    return zip.generateAsync({\r\n      type: \"blob\",\r\n      mimeType:\r\n        \"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet\",\r\n    });\r\n  };\r\n\r\n  private childValidator = (array) => {\r\n    return array.every( (item) => Array.isArray(item));\r\n  };\r\n\r\n  private validator = (config) => {\r\n    if (!config.filename) {\r\n      console.error(this.MISSING_KEY_FILENAME);\r\n      return false;\r\n    }\r\n\r\n    if (typeof config.filename !== \"string\") {\r\n      console.error(this.INVALID_TYPE_FILENAME);\r\n      return false;\r\n    }\r\n\r\n    if (!Array.isArray(config.sheet.data)) {\r\n      console.error(this.INVALID_TYPE_SHEET);\r\n      return false;\r\n    }\r\n\r\n    if (!this.childValidator(config.sheet.data)) {\r\n      console.error(this.INVALID_TYPE_SHEET_DATA);\r\n      return false;\r\n    }\r\n\r\n    return true;\r\n  };\r\n\r\n  private generateColumnLetter = (colIndex) => {\r\n    if (typeof colIndex !== \"number\") {\r\n      return \"\";\r\n    }\r\n\r\n    const prefix = Math.floor(colIndex / 26);\r\n    const letter = String.fromCharCode(97 + (colIndex % 26)).toUpperCase();\r\n    if (prefix === 0) {\r\n      return letter;\r\n    }\r\n    return this.generateColumnLetter(prefix - 1) + letter;\r\n  };\r\n\r\n  private generatorCellNumber = (index, rowNumber) => (\r\n    `${this.generateColumnLetter(index)}${rowNumber}`\r\n  );\r\n\r\n  private generatorStringCell = (index, value, rowIndex) => (`<c r=\"${this.generatorCellNumber(index, rowIndex)}\" t=\"inlineStr\"><is><t>${Texts.escapeHtml(value)}</t></is></c>`);\r\n  private generatorNumberCell = (index, value, rowIndex) => (`<c r=\"${this.generatorCellNumber(index, rowIndex)}\" t=\"n\"><v>${value}</v></c>`);\r\n  private generatorDateCell =  (index, value, rowIndex) => (`<c r=\"${this.generatorCellNumber(index, rowIndex)}\" t=\"d\" s=\"1\"><v>${value}</v></c>`);\r\n  private generatorBooleanCell = (index, value, rowIndex) => (`<c r=\"${this.generatorCellNumber(index, rowIndex)}\" t=\"b\"><v>${value}</v></c>`);\r\n  private generatorEmptyCell = (index, value, rowIndex) => (`<c r=\"${this.generatorCellNumber(index, rowIndex)}\"><v></v></c>`);\r\n\r\n  private formatCell = (cell, index, rowIndex) => {\r\n    return (\r\n      cell.type === this.CELL_TYPE_STRING ?\r\n         this.generatorStringCell(index, cell.value, rowIndex) :\r\n      cell.type === this.CELL_TYPE_NUMBER ?\r\n         this.generatorNumberCell(index, cell.value, rowIndex) :\r\n      cell.type === this.CELL_TYPE_DATE ?\r\n         this.generatorDateCell(index, cell.value, rowIndex) :\r\n      cell.type === this.CELL_TYPE_BOOLEAN ?\r\n         this.generatorBooleanCell(index, cell.value, rowIndex) :\r\n         this.generatorEmptyCell(index, cell.value, rowIndex)\r\n    );\r\n  };\r\n\r\n  private formatRow = (row, index) => {\r\n    // To ensure the row number starts as in excel.\r\n    const rowIndex = index + 1;\r\n    const rowCells = row\r\n      .map((cell, cellIndex) => this.formatCell(cell, cellIndex, rowIndex))\r\n      .join(\"\");\r\n\r\n    return `<row r=\"${rowIndex}\">${rowCells}</row>`;\r\n  };\r\n\r\n  private generatorRows = (rows) => (\r\n    rows\r\n      .map((row, index) => this.formatRow(row, index))\r\n      .join(\"\")\r\n  );\r\n\r\n  private formatCol = (col, index) => {\r\n    // To ensure the row number starts as in excel.\r\n    const colIndex = index + 1;\r\n    return `<col min=\"${colIndex}\" max=\"${colIndex}\" width=\"30\" customWidth=\"1\"/>`;\r\n  };\r\n\r\n  private generatorCols = (cols) => (\r\n    cols\r\n      .map((col, index) => this.formatCol(col, index))\r\n      .join(\"\")\r\n  );\r\n\r\n  private generateXMLWorksheet = (rows) => {\r\n    const xmlCols = this.generatorCols(rows.length > 0 ? rows[0] : []);\r\n    const xmlRows = this.generatorRows(rows);\r\n    return this.templateSheet.replace(\"{rows}\", xmlRows).replace(\"{cols}\", xmlCols);\r\n  };\r\n}\r\n\r\n/** Utility service for generating excel files. */\r\nexport class ExcelHelpers {\r\n\r\n  /**\r\n   * Converts a data table to an excel file.\r\n   * @param tableData Array of rows to convert to an excel file. Each row consists of an array of cell values.\r\n   * @param fileName Name for the excel file without the file extension.\r\n   */\r\n  public static export(tableData: any[], fileName: string): Promise<void> {\r\n    const rowMapper = this.getRowMapper();\r\n    const config = {\r\n      filename: fileName,\r\n      sheet: {\r\n        data: tableData.map(rowMapper),\r\n      },\r\n    };\r\n    return this.zipcelx.generateExcel(config).then( (blob) => {\r\n      saveAs(blob, `${config.filename}.xlsx`);\r\n      return;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Converts multiple data tables to a zip file containing excel files.\r\n   * @param tablesData Multiple data tables. Each table contains an array of rows to convert to a excel file. Each row consists of an array of cell values.\r\n   * @param zipName Name for the zip file without the file extension.\r\n   */\r\n  public static exportMany(\r\n    tablesData: {\r\n      /** Array of rows to convert to an excel file. Each row consists of an array of cell values. */\r\n      tableData: any[],\r\n      /** Name for the excel file without the file extension. */\r\n      fileName: string,\r\n    }[],\r\n    zipName: string): Promise<void> {\r\n\r\n    const rowMapper = this.getRowMapper();\r\n    let counter = 0;\r\n    const zip = new JSZip();\r\n    const next = (): Promise<void> => {\r\n      if (counter === tablesData.length) {\r\n        return Promise.resolve();\r\n      }\r\n      const item = tablesData[counter++];\r\n      const config = {\r\n        filename: item.fileName,\r\n        sheet: {\r\n          data: item.tableData.map(rowMapper),\r\n        },\r\n      };\r\n      return this.zipcelx.generateExcel(config).then( (blob) => {\r\n        zip.file(`${config.filename}.xlsx`, blob);\r\n        return next();\r\n      });\r\n    };\r\n\r\n    return next().then ( () => {\r\n      return zip.generateAsync({\r\n        type: \"blob\",\r\n        mimeType:\r\n          \"application/zip\",\r\n      }).then( (blob) => {\r\n        saveAs(blob, `${zipName}.zip`);\r\n        return;\r\n      });\r\n    });\r\n  }\r\n\r\n  private static zipcelx = new Zipcelx();\r\n\r\n  private static getRowMapper() {\r\n    const fieldMapper = this.getFieldMapper();\r\n    return (row) => {\r\n      return row.map(fieldMapper);\r\n    };\r\n  }\r\n\r\n  private static getFieldMapper() {\r\n    return (value) => {\r\n      if (value == null) { // we want to catch anything null-ish, hence just == not ===\r\n        return { value, type: null };\r\n      }\r\n      if (typeof (value) === \"number\") {\r\n        return { value, type: \"number\" };\r\n      }\r\n      if (typeof (value) === \"boolean\") {\r\n        return { value: (value ? \"true\" : \"false\"), type: \"boolean\" };\r\n      }\r\n      if (typeof (value) === \"string\") {\r\n        return { value: value.replace(/\"/g, \"\\\"\\\"\"), type: \"string\" };\r\n      }\r\n      if (typeof (value) === \"object\" && (value instanceof Date)) {\r\n        return { value: Dates.format(value,\"YYYY-MM-DD\"), type: \"date\" };\r\n      }\r\n\r\n      return { value: JSON.stringify(value), type: \"string\" };\r\n    };\r\n  }\r\n}\r\n","import { saveAs } from \"file-saver\";\r\n\r\nimport { Dates, ExportMethod, FileExporter, TableFormat, Tables, Translations } from \"@salaxy/core\";\r\nimport { AlertService } from \"./AlertService\";\r\nimport { ExcelHelpers } from \"./ExcelHelpers\";\r\nimport angular from \"angular\";\r\n\r\n/**\r\n * Provides functionality related to working with files: Download, copy-paste etc.\r\n */\r\nexport class FileService {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"AlertService\", \"$timeout\"];\r\n\r\n  constructor(private alertService: AlertService, private $timeout: angular.ITimeoutService) {\r\n    // Dependency injection\r\n  }\r\n\r\n  /** Copies given data to the clipboard. */\r\n  public copyToClipboard(data: string): Promise<void> {\r\n    return (navigator as any).clipboard.writeText(data).then(() => {\r\n      return this.$timeout(() => {\r\n        return;\r\n      });\r\n    });\r\n  }\r\n\r\n  /** Gets the default exporters available in the current environment / account  */\r\n  public getDefaultExporters(): FileExporter[] {\r\n    return [\r\n      {\r\n        id: ExportMethod.CopyExcel,\r\n        label: Translations.get(\"SALAXY.NG1.ODataActionsComponent.getDefaults.copyExcel\"),\r\n        hasLocales: true,\r\n        export: (rows, locale) => {\r\n          const tabbedData = Tables.export(rows as any, TableFormat.Txt, locale);\r\n          this.copyToClipboard(tabbedData);\r\n          this.alertService.addSuccess(`${rows.length} ${Translations.get(\"SALAXY.NG1.ExportComponent.export.rowsCopiedOnClipboard\")}`);\r\n        }\r\n      },\r\n      {\r\n        id: ExportMethod.FileExcel,\r\n        label: Translations.get(\"SALAXY.NG1.ODataActionsComponent.getDefaults.fileExcel\"),\r\n        hasLocales: false,\r\n        export: (rows) => {\r\n          return ExcelHelpers.export(Tables.exportAsArrays(rows as any), this.getFileName());\r\n        }\r\n      },\r\n      {\r\n        id: ExportMethod.CopyCsv,\r\n        label: Translations.get(\"SALAXY.NG1.ODataActionsComponent.getDefaults.copyCsv\"),\r\n        hasLocales: true,\r\n        export: (rows, locale) => {\r\n          const csvData = Tables.export(rows as any, TableFormat.Csv, locale);\r\n          this.copyToClipboard(csvData);\r\n          this.alertService.addSuccess(`${rows.length} ${Translations.get(\"SALAXY.NG1.ExportComponent.export.rowsCopiedOnClipboard\")}`);\r\n        }\r\n      },\r\n      {\r\n        id: ExportMethod.FileCsv,\r\n        label: Translations.get(\"SALAXY.NG1.ODataActionsComponent.getDefaults.fileCsv\"),\r\n        hasLocales: true,\r\n        export: (rows, locale) => {\r\n          const csvFileData = Tables.export(rows as any, TableFormat.Csv, locale);\r\n          saveAs(new Blob([csvFileData], { type: \"application/octet-stream;charset=utf-8\" }), `${this.getFileName()}.csv`);\r\n        }\r\n      }\r\n    ];\r\n  }\r\n\r\n  /** Gets a filename as ¨export_[YYYYMMDD]¨. */\r\n  private getFileName() {\r\n    return `export_${Dates.format(\"today\", \"YYYYMMDD\")}`;\r\n  }\r\n\r\n}","/* eslint-disable no-bitwise */\r\n\r\n/** Copied and modified from https://css-tricks.com/snippets/javascript/javascript-md5 */\r\nexport class GravatarHelpers {\r\n\r\n  /** Create gravatar url from the given email. */\r\n  public static getGravatarUrl(email: string): string {\r\n    return `https://www.gravatar.com/avatar/${this.md5((email + \"\").trim().toLowerCase())}?d=identicon`;\r\n  }\r\n\r\n  /** Returns true if the url is gravatar url. */\r\n  public static isGravatarUrl(url: string): boolean {\r\n    return (url + \"\").trim().toLowerCase().startsWith(\"https://www.gravatar.com/avatar/\");\r\n  }\r\n\r\n  /**\r\n   * Calculates md5.\r\n   */\r\n  private static md5(str: string): string {\r\n    const rotateLeft = (lValue, iShiftBits) => {\r\n      return (lValue << iShiftBits) | (lValue >>> (32 - iShiftBits));\r\n    };\r\n    const addUnsigned = (lX, lY) => {\r\n      const lX8 = (lX & 0x80000000);\r\n      const lY8 = (lY & 0x80000000);\r\n      const lX4 = (lX & 0x40000000);\r\n      const lY4 = (lY & 0x40000000);\r\n      const lResult = (lX & 0x3FFFFFFF) + (lY & 0x3FFFFFFF);\r\n      if (lX4 & lY4) {\r\n        return (lResult ^ 0x80000000 ^ lX8 ^ lY8);\r\n      }\r\n      if (lX4 | lY4) {\r\n        if (lResult & 0x40000000) {\r\n          return (lResult ^ 0xC0000000 ^ lX8 ^ lY8);\r\n        } else {\r\n          return (lResult ^ 0x40000000 ^ lX8 ^ lY8);\r\n        }\r\n      } else {\r\n        return (lResult ^ lX8 ^ lY8);\r\n      }\r\n    };\r\n    const f = (x, y, z) => (x & y) | ((~x) & z);\r\n    const g = (x, y, z) => (x & z) | (y & (~z));\r\n    const h = (x, y, z) => (x ^ y ^ z);\r\n    const i = (x, y, z) => (y ^ (x | (~z)));\r\n    const ff = (a, b, c, d, x, s, ac) => {\r\n      a = addUnsigned(a, addUnsigned(addUnsigned(f(b, c, d), x), ac));\r\n      return addUnsigned(rotateLeft(a, s), b);\r\n    };\r\n    const gg = (a, b, c, d, x, s, ac) => {\r\n      a = addUnsigned(a, addUnsigned(addUnsigned(g(b, c, d), x), ac));\r\n      return addUnsigned(rotateLeft(a, s), b);\r\n    };\r\n    const hh = (a, b, c, d, x, s, ac) => {\r\n      a = addUnsigned(a, addUnsigned(addUnsigned(h(b, c, d), x), ac));\r\n      return addUnsigned(rotateLeft(a, s), b);\r\n    };\r\n    const ii = (a, b, c, d, x, s, ac) => {\r\n      a = addUnsigned(a, addUnsigned(addUnsigned(i(b, c, d), x), ac));\r\n      return addUnsigned(rotateLeft(a, s), b);\r\n    };\r\n    const convertToWordArray = (str) => {\r\n      let lWordCount;\r\n      const lMessageLength = str.length;\r\n      const lNumberOfWordsTemp1 = lMessageLength + 8;\r\n      const lNumberOfWordsTemp2 = (lNumberOfWordsTemp1 - (lNumberOfWordsTemp1 % 64)) / 64;\r\n      const lNumberOfWords = (lNumberOfWordsTemp2 + 1) * 16;\r\n      const lWordArray = Array(lNumberOfWords - 1);\r\n      let lBytePosition = 0;\r\n      let lByteCount = 0;\r\n      while (lByteCount < lMessageLength) {\r\n        lWordCount = (lByteCount - (lByteCount % 4)) / 4;\r\n        lBytePosition = (lByteCount % 4) * 8;\r\n        lWordArray[lWordCount] = (lWordArray[lWordCount] | (str.charCodeAt(lByteCount) << lBytePosition));\r\n        lByteCount++;\r\n      }\r\n      lWordCount = (lByteCount - (lByteCount % 4)) / 4;\r\n      lBytePosition = (lByteCount % 4) * 8;\r\n      lWordArray[lWordCount] = lWordArray[lWordCount] | (0x80 << lBytePosition);\r\n      lWordArray[lNumberOfWords - 2] = lMessageLength << 3;\r\n      lWordArray[lNumberOfWords - 1] = lMessageLength >>> 29;\r\n      return lWordArray;\r\n    };\r\n    const wordToHex = (lValue) => {\r\n      let wordToHexValue = \"\";\r\n      let wordToHexValueTemp = \"\";\r\n      let lByte;\r\n      let lCount;\r\n      for (lCount = 0; lCount <= 3; lCount++) {\r\n        lByte = (lValue >>> (lCount * 8)) & 255;\r\n        wordToHexValueTemp = \"0\" + lByte.toString(16);\r\n        wordToHexValue = wordToHexValue + wordToHexValueTemp.substr(wordToHexValueTemp.length - 2, 2);\r\n      }\r\n      return wordToHexValue;\r\n    };\r\n    const utf8Encode = (str) => {\r\n      str = str.replace(/\\r\\n/g, \"\\n\");\r\n      let utftext = \"\";\r\n      for (let n = 0; n < str.length; n++) {\r\n        const c = str.charCodeAt(n);\r\n        if (c < 128) {\r\n          utftext += String.fromCharCode(c);\r\n        } else if ((c > 127) && (c < 2048)) {\r\n          utftext += String.fromCharCode((c >> 6) | 192);\r\n          utftext += String.fromCharCode((c & 63) | 128);\r\n        } else {\r\n          utftext += String.fromCharCode((c >> 12) | 224);\r\n          utftext += String.fromCharCode(((c >> 6) & 63) | 128);\r\n          utftext += String.fromCharCode((c & 63) | 128);\r\n        }\r\n      }\r\n      return utftext;\r\n    };\r\n\r\n    let aa;\r\n    let bb;\r\n    let cc;\r\n    let dd;\r\n    let a;\r\n    let b;\r\n    let c;\r\n    let d;\r\n    const s11 = 7;\r\n    const s12 = 12;\r\n    const s13 = 17;\r\n    const s14 = 22;\r\n    const s21 = 5;\r\n    const s22 = 9;\r\n    const s23 = 14;\r\n    const s24 = 20;\r\n    const s31 = 4;\r\n    const s32 = 11;\r\n    const s33 = 16;\r\n    const s34 = 23;\r\n    const s41 = 6;\r\n    const s42 = 10;\r\n    const s43 = 15;\r\n    const s44 = 21;\r\n\r\n    str = utf8Encode(str);\r\n    const x = convertToWordArray(str);\r\n    a = 0x67452301; b = 0xEFCDAB89; c = 0x98BADCFE; d = 0x10325476;\r\n    for (let k = 0; k < x.length; k += 16) {\r\n      aa = a; bb = b; cc = c; dd = d;\r\n      a = ff(a, b, c, d, x[k + 0], s11, 0xD76AA478);\r\n      d = ff(d, a, b, c, x[k + 1], s12, 0xE8C7B756);\r\n      c = ff(c, d, a, b, x[k + 2], s13, 0x242070DB);\r\n      b = ff(b, c, d, a, x[k + 3], s14, 0xC1BDCEEE);\r\n      a = ff(a, b, c, d, x[k + 4], s11, 0xF57C0FAF);\r\n      d = ff(d, a, b, c, x[k + 5], s12, 0x4787C62A);\r\n      c = ff(c, d, a, b, x[k + 6], s13, 0xA8304613);\r\n      b = ff(b, c, d, a, x[k + 7], s14, 0xFD469501);\r\n      a = ff(a, b, c, d, x[k + 8], s11, 0x698098D8);\r\n      d = ff(d, a, b, c, x[k + 9], s12, 0x8B44F7AF);\r\n      c = ff(c, d, a, b, x[k + 10], s13, 0xFFFF5BB1);\r\n      b = ff(b, c, d, a, x[k + 11], s14, 0x895CD7BE);\r\n      a = ff(a, b, c, d, x[k + 12], s11, 0x6B901122);\r\n      d = ff(d, a, b, c, x[k + 13], s12, 0xFD987193);\r\n      c = ff(c, d, a, b, x[k + 14], s13, 0xA679438E);\r\n      b = ff(b, c, d, a, x[k + 15], s14, 0x49B40821);\r\n      a = gg(a, b, c, d, x[k + 1], s21, 0xF61E2562);\r\n      d = gg(d, a, b, c, x[k + 6], s22, 0xC040B340);\r\n      c = gg(c, d, a, b, x[k + 11], s23, 0x265E5A51);\r\n      b = gg(b, c, d, a, x[k + 0], s24, 0xE9B6C7AA);\r\n      a = gg(a, b, c, d, x[k + 5], s21, 0xD62F105D);\r\n      d = gg(d, a, b, c, x[k + 10], s22, 0x2441453);\r\n      c = gg(c, d, a, b, x[k + 15], s23, 0xD8A1E681);\r\n      b = gg(b, c, d, a, x[k + 4], s24, 0xE7D3FBC8);\r\n      a = gg(a, b, c, d, x[k + 9], s21, 0x21E1CDE6);\r\n      d = gg(d, a, b, c, x[k + 14], s22, 0xC33707D6);\r\n      c = gg(c, d, a, b, x[k + 3], s23, 0xF4D50D87);\r\n      b = gg(b, c, d, a, x[k + 8], s24, 0x455A14ED);\r\n      a = gg(a, b, c, d, x[k + 13], s21, 0xA9E3E905);\r\n      d = gg(d, a, b, c, x[k + 2], s22, 0xFCEFA3F8);\r\n      c = gg(c, d, a, b, x[k + 7], s23, 0x676F02D9);\r\n      b = gg(b, c, d, a, x[k + 12], s24, 0x8D2A4C8A);\r\n      a = hh(a, b, c, d, x[k + 5], s31, 0xFFFA3942);\r\n      d = hh(d, a, b, c, x[k + 8], s32, 0x8771F681);\r\n      c = hh(c, d, a, b, x[k + 11], s33, 0x6D9D6122);\r\n      b = hh(b, c, d, a, x[k + 14], s34, 0xFDE5380C);\r\n      a = hh(a, b, c, d, x[k + 1], s31, 0xA4BEEA44);\r\n      d = hh(d, a, b, c, x[k + 4], s32, 0x4BDECFA9);\r\n      c = hh(c, d, a, b, x[k + 7], s33, 0xF6BB4B60);\r\n      b = hh(b, c, d, a, x[k + 10], s34, 0xBEBFBC70);\r\n      a = hh(a, b, c, d, x[k + 13], s31, 0x289B7EC6);\r\n      d = hh(d, a, b, c, x[k + 0], s32, 0xEAA127FA);\r\n      c = hh(c, d, a, b, x[k + 3], s33, 0xD4EF3085);\r\n      b = hh(b, c, d, a, x[k + 6], s34, 0x4881D05);\r\n      a = hh(a, b, c, d, x[k + 9], s31, 0xD9D4D039);\r\n      d = hh(d, a, b, c, x[k + 12], s32, 0xE6DB99E5);\r\n      c = hh(c, d, a, b, x[k + 15], s33, 0x1FA27CF8);\r\n      b = hh(b, c, d, a, x[k + 2], s34, 0xC4AC5665);\r\n      a = ii(a, b, c, d, x[k + 0], s41, 0xF4292244);\r\n      d = ii(d, a, b, c, x[k + 7], s42, 0x432AFF97);\r\n      c = ii(c, d, a, b, x[k + 14], s43, 0xAB9423A7);\r\n      b = ii(b, c, d, a, x[k + 5], s44, 0xFC93A039);\r\n      a = ii(a, b, c, d, x[k + 12], s41, 0x655B59C3);\r\n      d = ii(d, a, b, c, x[k + 3], s42, 0x8F0CCC92);\r\n      c = ii(c, d, a, b, x[k + 10], s43, 0xFFEFF47D);\r\n      b = ii(b, c, d, a, x[k + 1], s44, 0x85845DD1);\r\n      a = ii(a, b, c, d, x[k + 8], s41, 0x6FA87E4F);\r\n      d = ii(d, a, b, c, x[k + 15], s42, 0xFE2CE6E0);\r\n      c = ii(c, d, a, b, x[k + 6], s43, 0xA3014314);\r\n      b = ii(b, c, d, a, x[k + 13], s44, 0x4E0811A1);\r\n      a = ii(a, b, c, d, x[k + 4], s41, 0xF7537E82);\r\n      d = ii(d, a, b, c, x[k + 11], s42, 0xBD3AF235);\r\n      c = ii(c, d, a, b, x[k + 2], s43, 0x2AD7D2BB);\r\n      b = ii(b, c, d, a, x[k + 9], s44, 0xEB86D391);\r\n      a = addUnsigned(a, aa);\r\n      b = addUnsigned(b, bb);\r\n      c = addUnsigned(c, cc);\r\n      d = addUnsigned(d, dd);\r\n    }\r\n\r\n    const temp = wordToHex(a) + wordToHex(b) + wordToHex(c) + wordToHex(d);\r\n\r\n    return temp.toLowerCase();\r\n  }\r\n\r\n}\r\n","import { OpenAPIV3 } from \"@salaxy/core\";\r\n\r\nimport { InputMetadata, JsonInputType, JsonSchemaCache, JsonSchemaCacheItem, JsonSchemaProperty, JsonSchemaUtils } from \"@salaxy/core\";\r\n\r\nimport { AjaxNg1 } from \"../../ajax\";\r\n\r\n/**\r\n * Service for caching JSON schemas and creating user interfaces based on them.\r\n */\r\nexport class JsonSchemaService {\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"AjaxNg1\"];\r\n\r\n  private cache: JsonSchemaCache;\r\n\r\n  constructor(private ajax: AjaxNg1) {\r\n    this.cache = new JsonSchemaCache(ajax);\r\n  }\r\n\r\n  /** Gets the currently loaded schema documents. */\r\n  public getSchemas(): JsonSchemaCacheItem[] {\r\n    return this.cache.schemaCache.filter((x) => !!x.doc);\r\n  }\r\n\r\n  /** Gets the raw schema cache, mainly for injecting to other classes that may need it. */\r\n  public getCache(): JsonSchemaCache {\r\n    return this.cache;\r\n  }\r\n\r\n  /**\r\n   * Assures that a schema document identified by URL is loaded from server to the cache\r\n   * Currently, supports only OpenApi 3, but we may later support OpenApi 2 and/or plain JSON schema.\r\n   * @param openApiUrl URL to the open API document.\r\n   * @returns A promise that resolves when the document has been loaded and you can call other methods on it.\r\n   */\r\n  public assureSchemaDocument (openApiUrl: string): Promise<OpenAPIV3.Document> {\r\n    return this.cache.assureSchemaDocument(openApiUrl);\r\n  }\r\n\r\n  /**\r\n   * Adds a schema document to cache\r\n   * TODO: Reconsider the signature.\r\n   */\r\n  public addSchemaDocument (openApiUrl: string, doc: OpenAPIV3.Document): OpenAPIV3.Document {\r\n    return this.cache.addSchemaDocument(openApiUrl, doc);\r\n  }\r\n\r\n  /**\r\n   * Finds a schema document from the cache.\r\n   * This method is syncronous base method for other schema operations\r\n   * Make sure that the schme document has been loaded before calling as this will not load the document,\r\n   * but will fail instead if the schema document is not there.\r\n   * @param openApiUrl URL to the open API document.\r\n   * @param throwIfNotFound If true, will throw an error if the document is not found in the cache.\r\n   */\r\n  public findSchemaDoc (openApiUrl: string, throwIfNotFound: boolean): JsonSchemaCacheItem {\r\n    return this.cache.findSchemaDoc(openApiUrl, throwIfNotFound);\r\n  }\r\n\r\n  /**\r\n   * Finds a single schema (Data model) within a schema document\r\n   * Make sure that the schme document has been loaded before calling as this will not load the document,\r\n   * but will fail instead if the schema document is not there.\r\n   * @param openApiUrl URL to the open API document.\r\n   * @param name Name of the schema (data model)\r\n   */\r\n  public findSchema (openApiUrl: string, name: string): OpenAPIV3.SchemaObject | null {\r\n    return this.cache.findSchema(openApiUrl, name);\r\n  }\r\n\r\n  /**\r\n   * Gets a property from a schema document. Supports single property names or longer property paths.\r\n   * @param openApiUrl URL to the open API document.\r\n   * @param schemaName The root type from which the property is found.\r\n   * @param path Property path starting with the root schema.\r\n   */\r\n  public getProperty (openApiUrl: string, schemaName: string, path: string): JsonSchemaProperty {\r\n    const schema = this.findSchema(openApiUrl, schemaName);\r\n    return JsonSchemaUtils.getProperty(schema, path);\r\n  }\r\n\r\n  /**\r\n   * Registers a new custom input for type/format combination\r\n   * @param type JSON type\r\n   * @param format Format in the JSON schema\r\n   * @param template Template for the type/foramt combination.\r\n   * Special key \"sxy\" can be used to set default templates based on type/format,\r\n   * e.g. (\"boolean\", \"default\", \"sxy\") => \"salaxy-components/sxy-form/boolean/default.html\".\r\n   */\r\n  public registerInput (type: JsonInputType, format: \"default\" | string, template: \"sxy\" | string) {\r\n    this._registeredInputs[type][format] = (template === \"sxy\" ?\r\n      `salaxy-components/sxy-form/${type}/${format}.html` : template);\r\n  }\r\n\r\n  /** Gets the AngularJS tempalte for the input. */\r\n  public getTemplate (input: InputMetadata): string {\r\n    const type = this._registeredInputs[input.type];\r\n    if (!type) {\r\n      input.content = `Unregistered type: ${input.type}`;\r\n      return \"salaxy-components/sxy-form/error/default.html\";\r\n    }\r\n    if (type[input.format]) {\r\n      return type[input.format].template === \"sxy\" ? `salaxy-components/sxy-form/${input.type}/${input.format}.html` : type[input.format].template;\r\n    }\r\n    return `salaxy-components/sxy-form/${input.type}/${(input.isEnum ? \"enum\" : \"default\")}.html`;\r\n  }\r\n\r\n  /** Gets the registered inputs */\r\n  public getRegisteredInputs(): { [key: string]: { [key: string]: any } } {\r\n    return this._registeredInputs;\r\n  }\r\n\r\n  /**\r\n   * Maps the types and formats to templates.\r\n   */\r\n   private _registeredInputs = {\r\n    \"array\": {\r\n      \"default\": {\r\n        template: \"sxy\"\r\n      },\r\n      \"PercentDimension\": {\r\n        template: \"sxy\"\r\n      },\r\n    },\r\n    \"boolean\": {\r\n      \"default\": {\r\n        template: \"sxy\"\r\n      },\r\n      \"select\": {\r\n        template: \"salaxy-components/sxy-form/boolean/default.html\"\r\n      },\r\n      \"radio\": {\r\n        template: \"sxy\"\r\n      },\r\n      \"checkbox\": {\r\n        template: \"sxy\"\r\n      },\r\n      \"switch\": {\r\n        template: \"sxy\"\r\n      },\r\n    },\r\n    \"integer\": {\r\n      \"default\": {\r\n        template: \"sxy\"\r\n      },\r\n    },\r\n    \"number\": {\r\n      \"default\": {\r\n        template: \"sxy\"\r\n      },\r\n      \"count\": {\r\n        template: \"salaxy-components/sxy-form/number/default.html\"\r\n      },\r\n      \"percent\": {\r\n        template: \"salaxy-components/sxy-form/number/default.html\"\r\n      },\r\n      \"days\": {\r\n        template: \"salaxy-components/sxy-form/number/default.html\"\r\n      },\r\n      \"kilometers\": {\r\n        template: \"salaxy-components/sxy-form/number/default.html\"\r\n      },\r\n      \"hours\": {\r\n        template: \"salaxy-components/sxy-form/number/default.html\"\r\n      },\r\n      \"undefined\": {\r\n        template: \"salaxy-components/sxy-form/number/default.html\"\r\n      },\r\n    },\r\n    \"object\": {\r\n      \"default\": {\r\n        template: \"sxy\"\r\n      },\r\n      \"Avatar\": {\r\n        template: \"sxy\"\r\n      },\r\n      \"DateRange\": {\r\n        template: \"sxy\"\r\n      },\r\n    },\r\n    \"string\": {\r\n      \"default\": {\r\n        template: \"sxy\"\r\n      },\r\n      \"multiline\": {\r\n        template: \"sxy\"\r\n      },\r\n      \"email\": {\r\n        template: \"sxy\"\r\n      },\r\n      \"password\": {\r\n        template: \"sxy\"\r\n      },\r\n      \"telephone\": {\r\n        template: \"sxy\"\r\n      },\r\n      \"date\": {\r\n        template: \"sxy\"\r\n      },\r\n      \"date-time\": {\r\n        template: \"sxy\"\r\n      },\r\n      \"enum\": {\r\n        template: \"sxy\"\r\n      },\r\n      \"radio\": {\r\n        template: \"salaxy-components/sxy-form/string/enum.html\"\r\n      },\r\n      \"typeahead\": {\r\n        template: \"salaxy-components/sxy-form/string/enum.html\"\r\n      },\r\n      \"list\": {\r\n        template: \"salaxy-components/sxy-form/string/enum.html\"\r\n      },\r\n      \"pension-contract-number\": {\r\n        template: \"salaxy-components/sxy-form/string/pension-contract-number.html\",\r\n      }\r\n    },\r\n  };\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Configs } from \"@salaxy/core\";\r\n\r\n/** Exception tracking with AppInsight */\r\nexport class AppInsightExceptionTracking {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  protected static $inject = [\"$provide\"];\r\n\r\n  constructor($provide: angular.auto.IProvideService) {\r\n    $provide.decorator(\"$exceptionHandler\", [\"$delegate\", ($delegate: angular.IExceptionHandlerService) => {\r\n      return (exception: Error, cause?: string) => {\r\n        $delegate(exception, cause);\r\n        const appInsights = Configs.global.appInsights;\r\n        const config = Configs.current;\r\n        if (appInsights && config && config.instrumentationKey) {\r\n          try {\r\n            appInsights.trackException({ exception });\r\n            appInsights.flush();\r\n          } catch (err) {\r\n            console.debug(\"Application insight\", err);\r\n          }\r\n        }\r\n      };\r\n    }]);\r\n  }\r\n}\r\n","import { CalendarSeries } from \"@salaxy/core\";\r\n\r\n/** Helper component for calendar related user interfaces: Dates and Times formatting etc. */\r\nexport class CalendarHelper {\r\n\r\n  /** Periods / date ranges plotted on the chart. */\r\n  public calendarPeriods: CalendarSeries[];\r\n\r\n  constructor(private $sce: angular.ISCEService) {}\r\n\r\n  /**\r\n   * Gets a HTML formatted version of the description.\r\n   * @param description Description text to format\r\n   */\r\n   public formatDescription(description): any\r\n   {\r\n     if (!description) {\r\n       return null;\r\n     }\r\n     const html = description.replace(/<(http[^>]*)>/g, (match: string, p1: string) => {\r\n       if (p1.endsWith(\".jpg\") || p1.endsWith(\".jpeg\") || p1.endsWith(\".png\") || p1.endsWith(\".gif\"))\r\n       {\r\n         return `<a href=\"${p1}\" title=\"${p1}\" target=\"_blank\"><img src=\"${p1}\" alt=\"External image\" style=\"max-width: 400px\"></a>`;\r\n       }\r\n       return `<a href=\"${p1}\" title=\"${p1}\" target=\"_blank\">LINK</a>`;\r\n     });\r\n     return this.$sce.getTrustedHtml(html);\r\n   }\r\n\r\n}","import { SitemapNode } from \"@salaxy/core\";\r\n\r\n/**\r\n * The additional root nodes that should be added in PRO site only\r\n * when the selected account is a Person: Household or Worker (in Raksa/Palkkamylly).\r\n */\r\nexport const sitemap_PersonLeafs: SitemapNode[] = [\r\n  {\r\n    title: \"Laskelmat (henkilö)\",\r\n    url: \"#/person-calc\",\r\n    id: \"personCalc\",\r\n    roles: \"person\",\r\n    children: [\r\n      {\r\n        title: \"Viimeisimmät\",\r\n        url: \"#/calc\",\r\n        id: \"index\",\r\n      },\r\n      {\r\n        title: \"Luonnokset\",\r\n        url: \"#/calc/draft\",\r\n        id: \"draft\",\r\n      },\r\n      {\r\n        title: \"Lähetetyt\",\r\n        url: \"#/calc/shared\",\r\n        id: \"shared\",\r\n      },\r\n      {\r\n        title: \"Palkkalaskelma\",\r\n        url: \"#/calc/details/*\",\r\n        visibility: \"hidden\",\r\n        id: \"details\",\r\n      },\r\n      {\r\n        title: \"Uusi laskelma\",\r\n        url: \"#/calc/details/*/new-for-worker\",\r\n        visibility: \"hidden\",\r\n        id: \"newForWorker\",\r\n      },\r\n      {\r\n        title: \"Laskelman kopio\",\r\n        url: \"#/calc/details/*/copy-as-new\",\r\n        visibility: \"hidden\",\r\n        id: \"copyAsNew\",\r\n      },\r\n      {\r\n        title: \"Työntekijälle maksetut\",\r\n        url: \"#/person-calc/paid-worker\",\r\n        id: \"paidWorker\",\r\n        roles: \"person\"\r\n      },\r\n      {\r\n        title: \"Kotitalouden maksamat\",\r\n        url: \"#/person-calc/paid-household\",\r\n        id: \"paidHousehold\",\r\n        roles: \"person\"\r\n      },\r\n      {\r\n        title: \"Työntekijän lähetetyt\",\r\n        url: \"#/person-calc/sent\",\r\n        roles: \"person\",\r\n        id: \"sent\",\r\n      },\r\n      {\r\n        title: \"Perutut ja virheet\",\r\n        url: \"#/calc/error\",\r\n        roles: \"person\",\r\n        id: \"error\",\r\n      },\r\n    ]\r\n  },\r\n  {\r\n    title: \"Raportit (henkilö)\",\r\n    url: \"#/person-archive/employer-report\",\r\n    id: \"reports\",\r\n    roles: \"person\",\r\n    children: [\r\n      {\r\n        title: \"Työnantajan maksamat palkat\",\r\n        url: \"#/person-archive/employer-report\",\r\n        id: \"personEmployerReport\",\r\n      },\r\n      {\r\n        title: \"Kotitalousvähennys\",\r\n        url: \"#/household-years/active\",\r\n        id: \"householdYears\",\r\n        roles: \"householdService\",\r\n        children: [\r\n          {\r\n            title: \"Kotitalousvähennyksen tiedot\",\r\n            url: \"#/household-years/details/*\",\r\n            visibility: \"hidden\",\r\n            roles: \"householdService\",\r\n            id: \"details\",\r\n          },\r\n        ],\r\n      },\r\n      {\r\n        title: \"Työntekijälle maksetut palkat\",\r\n        url: \"#/person-archive/worker-report\",\r\n        id: \"personWorkerReport\",\r\n      },\r\n      {\r\n        url: \"#/reports/yearly-summary\",\r\n        id: \"yearlySummary\",\r\n      },\r\n      {\r\n        url: \"#/reports/pay-certificate\",\r\n        roles: \"test\",\r\n        id: \"payCertificate\",\r\n      },\r\n      {\r\n        title: \"Laskut\",\r\n        url: \"#/invoices\",\r\n        id: \"invoices\",\r\n        children: [\r\n          {\r\n            title: \"Laskun tiedot\",\r\n            url: \"#/invoices/details/*\",\r\n            visibility: \"hidden\",\r\n            id: \"details\",\r\n          },\r\n        ],\r\n      },\r\n      {\r\n        title: \"Palkkatietoilmoitukset\",\r\n        url: \"#/irepr\",\r\n        children: [{\r\n          title: \"Palkkatietoilmoitus\",\r\n          url: \"#/irepr/details/*\",\r\n        }],\r\n      },\r\n      {\r\n        title: \"Erillisilmoitukset\",\r\n        url: \"#/irpsr\",\r\n        id: \"irpsr\",\r\n        children: [{\r\n          title: \"Erillisilmoitus\",\r\n          url: \"#/irpsr/details/*\",\r\n          id: \"details\",\r\n        }],\r\n      },\r\n    ]\r\n  },\r\n  {\r\n    title: \"Asetukset (henkilö)\",\r\n    url: \"#/person-account\",\r\n    id: \"settings\",\r\n    roles: \"person\",\r\n    children: [\r\n      {\r\n        title: \"Omat tiedot\",\r\n        url: \"#/person-account\",\r\n        id: \"personAccount\",\r\n      },\r\n      {\r\n        url: \"#/settings\",\r\n        id: \"index\",\r\n      },\r\n      {\r\n        title: \"Oma verokortti (työntekijä)\",\r\n        url: \"#/person-taxcards/worker\",\r\n        id: \"workerTaxcard\",\r\n      },\r\n      {\r\n        title: \"Työntekijöiden verokortit\",\r\n        url: \"#/person-taxcards/household\",\r\n        id: \"householdTaxcards\",\r\n      },\r\n      {\r\n        url: \"#/settings/pro-settings\",\r\n        roles: \"test\",\r\n        id: \"proSettings\",\r\n      },\r\n      {\r\n        url: \"#/settings/service-settings\",\r\n        id: \"serviceSettings\",\r\n      },\r\n      {\r\n        url: \"#/settings/authorizations\",\r\n        id: \"authorizations\",\r\n      },\r\n      {\r\n        title: \"Asiakaspalvelu\",\r\n        id: \"accountants\",\r\n        url: \"#/settings/accountants\",\r\n      },\r\n      {\r\n        id: \"accountReset\",\r\n        url: \"#/settings/account-reset\",\r\n        roles: \"test\",\r\n      },\r\n    ]\r\n  },\r\n];","import { SitemapNode } from \"@salaxy/core\";\r\n\r\n/** The default sitemap tree for Company accounts / users. */\r\nexport const sitemap_Company: SitemapNode[] = [\r\n  {\r\n    url: \"#/\",\r\n    id: \"home\",\r\n    roles: \"company\",\r\n    i18n: [\"SALAXY.NG1_Pages.Home\", \"SALAXY.NG1.WorkerListComponent\", \"SALAXY.NG1.WelcomeComponent\", \"SALAXY.NG1.SigningComponent\", \"SALAXY.NG1.ContactInfoComponent\"],\r\n    params: {\r\n      features: {\r\n        title: \"Features\",\r\n        type: \"array\",\r\n        default: [\"welcome\", \"workerList\", \"contact\"],\r\n        items: {\r\n          type: \"string\",\r\n          enum: [\"welcome\", \"workerList\", \"messages\", \"contact\"]\r\n        }\r\n      },\r\n      newCalcDisabled: {\r\n        title: \"Palkanmaksu estetty\",\r\n        type: \"boolean\",\r\n      },\r\n      newMessageThreadDisabled: {\r\n        title: \"Uuden viestiketjun luonti estetty\",\r\n        type: \"boolean\",\r\n      },\r\n    }\r\n  },\r\n  {\r\n    url: \"#/calc\",\r\n    id: \"calculations\",\r\n    i18n: [\"SALAXY.NG1.CalcListComponent.panel\"],\r\n    roles: \"company\",\r\n    children: [\r\n      {\r\n        url: \"#/calc\",\r\n        id: \"index\",\r\n      },\r\n      {\r\n        url: \"#/payroll\",\r\n        id: \"payroll\",\r\n        isFullWidth: true,\r\n        children: [\r\n          {\r\n            url: \"#/payroll/details/*\",\r\n            visibility: \"hidden\",\r\n            id: \"details\",\r\n            params: {\r\n              actions: {\r\n                title: \"Readonly actions\",\r\n                type: \"array\",\r\n                default: [],\r\n                items: {\r\n                  type: \"string\",\r\n                  enum: [\"none\", \"copy\", \"pay\", \"cancel\"],\r\n                }\r\n              }\r\n            }\r\n          },\r\n          {\r\n            url: \"#/payroll/import/*\",\r\n            visibility: \"hidden\",\r\n            id: \"import\",\r\n            isFullWidth: true,\r\n          }\r\n        ],\r\n      },\r\n      {\r\n        url: \"#/calc/details/*/new-for-worker\",\r\n        visibility: \"hidden\",\r\n        id: \"newForWorker\",\r\n      },\r\n      {\r\n        url: \"#/calc/details/*/copy-as-new\",\r\n        visibility: \"hidden\",\r\n        id: \"copyAsNew\",\r\n      },\r\n      {\r\n        url: \"#/calc/details/*\",\r\n        visibility: \"hidden\",\r\n        id: \"details\",\r\n        i18n:[\"SALAXY.NG1.CalcComponent\",\"SALAXY.NG1.CalcNewIntroComponent\", \"SALAXY.NG1.CalcDetailsDialogComponent\",  \"SALAXY.NG1.CalcDetailsWorkerComponent\", \"SALAXY.NG1.CalcWorktimeComponent\", \"SALAXY.NG1.CalcDetailsWorktimeProComponent\",  \"SALAXY.NG1.CalcDetailsSalaryComponent\", \"SALAXY.NG1.CalcDetailsExpensesComponent\",\"SALAXY.NG1.CalcRowsComponent\", \"SALAXY.NG1.CalcResultsComponent\", \"SALAXY.NG1.CalcChartComponent\", \"SALAXY.NG1.CalcReportsComponent\"],\r\n      },\r\n      {\r\n        url: \"#/calc/repair/*\",\r\n        visibility: \"hidden\",\r\n        isFullWidth: true,\r\n        id: \"details\",\r\n        i18n:[\"SALAXY.NG1.CalcComponent\",\"SALAXY.NG1.CalcNewIntroComponent\", \"SALAXY.NG1.CalcDetailsDialogComponent\",  \"SALAXY.NG1.CalcDetailsWorkerComponent\", \"SALAXY.NG1.CalcWorktimeComponent\", \"SALAXY.NG1.CalcDetailsWorktimeProComponent\",  \"SALAXY.NG1.CalcDetailsSalaryComponent\", \"SALAXY.NG1.CalcDetailsExpensesComponent\",\"SALAXY.NG1.CalcRowsComponent\", \"SALAXY.NG1.CalcResultsComponent\", \"SALAXY.NG1.CalcChartComponent\", \"SALAXY.NG1.CalcReportsComponent\"],\r\n      },\r\n      {\r\n        url: \"#/calc/paid\",\r\n        id: \"paid\",\r\n        roles: \"company&&!repairs\",\r\n        i18n:[\"SALAXY.NG1.CalcListComponent\"]\r\n      },\r\n      {\r\n        url: \"#/calc/paid-ir\",\r\n        id: \"paid-ir\",\r\n        roles: \"company&&repairs\",\r\n        i18n:[\"SALAXY.NG1.CalcListComponent\"]\r\n      },\r\n      {\r\n        url: \"#/calc/draft\",\r\n        id: \"draft\",\r\n        i18n:[\"SALAXY.NG1.CalcListComponent\"]\r\n      },\r\n      {\r\n        url: \"#/calc/shared\",\r\n        id: \"shared\",\r\n        i18n:[\"SALAXY.NG1.CalcListComponent\"]\r\n      },\r\n      {\r\n        url: \"#/calc/repairs\",\r\n        id: \"repairs\",\r\n        roles: \"company&&repairs\",\r\n        i18n:[\"SALAXY.NG1.CalcListComponent\"]\r\n      },\r\n      {\r\n        url: \"#/invoices/sepa\",\r\n        isFullWidth: true,\r\n        id: \"sepaInvoices\",\r\n        roles: \"sepaPartner\",\r\n      },\r\n      {\r\n        url: \"#/invoices/company\",\r\n        id: \"companyInvoices\",\r\n        roles: \"test\",\r\n      },\r\n      {\r\n        title:\"Maksetun laskelman muokkaus\",\r\n        url: \"#/calc/editor/*\",\r\n        visibility: \"hidden\",\r\n        isFullWidth: true,\r\n        id: \"editor\",\r\n      },\r\n      {\r\n        url: \"#/calc/import-calcs\",\r\n        id: \"importCalcs\",\r\n        isFullWidth: true,\r\n        roles: \"test\",\r\n      },\r\n      {\r\n        url: \"#/invoices/payment-list\",\r\n        title: \"Maksulista\",\r\n        isFullWidth: true,\r\n        id: \"paymentList\",\r\n        roles: \"test||invoicePaymentList\",\r\n      },\r\n    ],\r\n  },\r\n  {\r\n    url: \"#/payroll\",\r\n    id: \"payroll\",\r\n    roles: \"company\",\r\n    visibility: \"hidden\",\r\n    i18n: [\"SALAXY.NG1.PayrollComponent.payrollList\"],\r\n    children: [\r\n      {\r\n        url: \"#/payroll/details/*\",\r\n        visibility: \"hidden\",\r\n        id: \"payrollDetails\",\r\n        i18n: [\"SALAXY.NG1.PayrollComponent.payrollEdit\", \"SALAXY.NG1.PayrollComponent.payrollCalcs\"],\r\n      },\r\n      {\r\n        url: \"#/payroll/import/*\",\r\n        visibility: \"hidden\",\r\n        id: \"import\",\r\n        isFullWidth: true,\r\n      }\r\n    ],\r\n  },\r\n  {\r\n    id: \"messages\",\r\n    url: \"#/messages\",\r\n    roles: \"partnerMessaging\",\r\n    children: [\r\n      {\r\n      url: \"#/messages\",\r\n      id: \"index\",\r\n      i18n:[\"SALAXY.NG1.ActionButtonComponent.startNewMessage\",\"SALAXY.NG1_Pages.Messages.newMessage.title\", \"SALAXY.NG1_Pages.Messages.newMessage.description.html\"]\r\n    },\r\n    {\r\n      id: \"omapalkka\",\r\n      url: \"#/messages/omapalkka\",\r\n      title: \"Omapalkka\",\r\n      roles: \"test\",\r\n      isFullWidth: true,\r\n    },\r\n    {\r\n      title: \"Hyväksyntä\",\r\n      url: \"#/messages/approval-list\",\r\n      id: \"approval\",\r\n      visibility: \"hidden\",\r\n      children: [{\r\n        title: \"Hyväksy / hylkää\",\r\n        url: \"#/messages/approval/*\",\r\n        visibility: \"hidden\",\r\n        isFullWidth: true,\r\n        id: \"details\",\r\n      }],\r\n    },\r\n    {\r\n      url: \"#/messages/details/new\",\r\n      id: \"new\",\r\n      i18n: [\"SALAXY.NG1_Pages.Messages.newMessageDetails.title\",\"SALAXY.NG1_Pages.Messages.newMessageDetails.description.html\"]\r\n    },\r\n    {\r\n      url: \"#/messages/details/*\",\r\n      visibility: \"hidden\",\r\n      id: \"details\",\r\n    }],\r\n  },\r\n  {\r\n    url: \"#/workers\",\r\n    id: \"workers\",\r\n    roles: \"company\",\r\n    children: [\r\n      {\r\n        url: \"#/workers\",\r\n        id: \"index\",\r\n        params: {\r\n          hidden: {\r\n            title: \"Parts to hide from page\",\r\n            type: \"array\",\r\n            default: [],\r\n            items: {\r\n              type: \"string\",\r\n              enum: [\"workers.employments.records.badge\", \"workers.employments.taxCard\", \"workers.employments.buttons.newCalc\", \"workers.employments.employmentId\"]\r\n            }\r\n          }\r\n        }\r\n      },\r\n      {\r\n        url: \"#/employments\",\r\n        visibility: \"hidden\",\r\n        id: \"employments\",\r\n        children: [\r\n          {\r\n            url: \"#/employments/index\",\r\n            id: \"index\",\r\n            visibility: \"hidden\",\r\n          },\r\n        ]\r\n      },\r\n      {\r\n        url: \"#/employments/details/*\",\r\n        visibility: \"hidden\",\r\n        id: \"details\",\r\n        i18n:[\"SALAXY.NG1.WorkerDetailsComponent\", \"SALAXY.NG1.WorkerHolidaysComponent\", \"SALAXY.NG1.WorkerAbsencesComponent\"],\r\n        params: {\r\n          features: {\r\n            title: \"Features\",\r\n            type: \"array\",\r\n            default: [\"detailsEdit\", \"employment\", \"calcRows\", \"calculations\", \"taxcards\", \"holidays\", \"absences\"],\r\n            items: {\r\n              type: \"string\",\r\n              enum: [\"detailsEdit\", \"employment\", \"calcRows\", \"calculations\", \"taxcards\", \"holidays\", \"absences\"],\r\n            }\r\n          },\r\n          hidden: {\r\n            title: \"Parts to hide from page\",\r\n            type: \"array\",\r\n            default: [],\r\n            items: {\r\n              type: \"string\",\r\n              enum: [\"detailsEdit\", \"employment\", \"calcRows\", \"calculations\", \"taxcards\", \"holidays\", \"absences\", \"employments.defaultCalcRows.features\", \"employments.calcs.copyAsNew\"]\r\n            }\r\n          }\r\n        },\r\n      },\r\n      {\r\n        url: \"#/workers/details/*\",\r\n        visibility: \"hidden\",\r\n        id: \"workerDetails\",\r\n        i18n:[\"SALAXY.NG1.WorkerDetailsComponent\", \"SALAXY.NG1.WorkerHolidaysComponent\", \"SALAXY.NG1.WorkerAbsencesComponent\"],\r\n        params: {\r\n          features: {\r\n            title: \"Features\",\r\n            type: \"array\",\r\n            default: [\"detailsEdit\", \"employment\", \"calcRows\", \"calculations\", \"taxcards\", \"holidays\", \"absences\"],\r\n            items: {\r\n              type: \"string\",\r\n              enum: [\"detailsEdit\", \"employment\", \"calcRows\", \"calculations\", \"taxcards\", \"holidays\", \"absences\"],\r\n            }\r\n          },\r\n        },\r\n      },\r\n      {\r\n        url: \"#/workers/taxcards\",\r\n        id: \"taxcards\",\r\n        i18n:[\"SALAXY.NG1_Pages.Workers.Taxcards.lead\"]\r\n      },\r\n      {\r\n        title: \"Lisää työntekijätili\",\r\n        url: \"#/partners/assure-worker-account\",\r\n        id: \"assureWorkerAccount\",\r\n        isFullWidth: true,\r\n        roles: \"assureWorkerAccount\",\r\n      },\r\n      {\r\n        url: \"#/workers/import-workers\",\r\n        id: \"importWorkers\",\r\n        isFullWidth: true,\r\n        roles: \"test\",\r\n      },\r\n    ],\r\n  },\r\n  {\r\n    url: \"#/reports/holidays\",\r\n    id: \"worktime\",\r\n    isFullWidth: true,\r\n    roles: \"company&&!disableHolidays\",\r\n    children: [\r\n      {\r\n        id: \"holidays\",\r\n        url: \"#/reports/holidays\",\r\n        isFullWidth: true,\r\n      },\r\n      {\r\n        id: \"absences\",\r\n        url: \"#/reports/absences\",\r\n        isFullWidth: true,\r\n      },\r\n    ],\r\n  },\r\n  {\r\n    url: \"#/reports\",\r\n    id: \"reports\",\r\n    roles: \"company\",\r\n    children: [\r\n      {\r\n        url: \"#/reports\",\r\n        id: \"index\",\r\n        i18n: [\"SALAXY.NG1_Pages.Reports.latestReports\", \"SALAXY.NG1.SalaryReportsComponent.calculations\",\"SALAXY.NG1.SalaryReportsComponent.noCalculations\", \"SALAXY.NG1.AccountingReportsComponent.accountingReports\",\"SALAXY.NG1.AccountingReportsComponent.noAccountingReports\", \"SALAXY.NG1.InvoicesComponent.invoices\", \"SALAXY.NG1.InvoicesComponent.noInvoices\"],\r\n        params: {\r\n          features: {\r\n            title: \"Features\",\r\n            type: \"array\",\r\n            default: [\"salaryReportList\", \"accountingReportList\"],\r\n            items: {\r\n              type: \"string\",\r\n              enum: [\"salaryReportList\", \"accountingReportList\", \"invoiceList\"],\r\n            }\r\n          },\r\n        },\r\n      },\r\n      {\r\n        url: \"#/accounting\",\r\n        id: \"accounting\",\r\n        isFullWidth: true,\r\n        children: [{\r\n            url: \"#/accounting/details/*\",\r\n            isFullWidth: true,\r\n            id: \"details\",\r\n            hidden:true,\r\n          }],\r\n      },\r\n      {\r\n        url: \"#/accounting/query\",\r\n        isFullWidth: true,\r\n        id: \"accountingQuery\",\r\n        visibility: \"hidden\",\r\n      },\r\n      {\r\n        url: \"#/accounting/holiday-pay-debt-query\",\r\n        isFullWidth: true,\r\n        id: \"accountingHolidayPayDebtQuery\",\r\n        visibility: \"hidden\",\r\n      },\r\n      {\r\n        url: \"#/reports/salary-reports\",\r\n        id: \"salaryReports\",\r\n      },\r\n      {\r\n        url: \"#/reports/summary-report-query\",\r\n        isFullWidth: true,\r\n        id: \"summaryReportQuery\",\r\n      },\r\n      {\r\n        url: \"#/reports/yearly-summary\",\r\n        id: \"yearlySummary\",\r\n        i18n:[\"SALAXY.NG1_Pages.Reports.yearlySummary\",\"SALAXY.NG1_Pages.Reports.yearlyTitle\"],\r\n      },\r\n      {\r\n        url: \"#/reports/pay-certificate\",\r\n        roles: \"pro\",\r\n        id: \"payCertificate\",\r\n      },\r\n      {\r\n        url: \"#/reports/accounting-legacy\",\r\n        // id: \"accountingLegacy\",\r\n        i18n:[\"SALAXY.NG1_Pages.Reports.accountingIntro\",\"SALAXY.NG1_Pages.Reports.accountingMonthly\", \"SALAXY.NG1_Pages.Reports.accountingYearly\", \"SALAXY.NG1_Sitemap.reports.archive\"],\r\n\r\n        title:\"SALAXY.NG1_Sitemap.personalWeb.archive.main\" // TODO: fix the id and translation\r\n      },\r\n      {\r\n        url: \"#/reports/archive-2018\",\r\n        id: \"archive\",\r\n        visibility: \"hidden\",\r\n      },\r\n      {\r\n        url: \"#/reports/ad-hoc-list\",\r\n        id: \"ad-hoc\",\r\n        roles: \"pro,test\",\r\n        children: [\r\n          {\r\n            url: \"#/reports/ad-hoc/*\",\r\n            isFullWidth: true,\r\n            visibility: \"hidden\",\r\n            id: \"details\",\r\n          },\r\n        ],\r\n      },\r\n      {\r\n        url: \"#/invoices\",\r\n        title:\"Maksut\",\r\n        id: \"invoices\",\r\n        visibility: \"hidden\",\r\n        children: [\r\n          {\r\n            url: \"#/invoices/details/*\",\r\n            visibility: \"hidden\",\r\n            id: \"details\",\r\n            title:\"Maksun tiedot\",\r\n            i18n:[\"SALAXY.NG1_Pages.Invoices\"],\r\n            params: {\r\n              features: {\r\n                title: \"Tabs\",\r\n                type: \"array\",\r\n                default: [\"preview\", \"calc\"],\r\n                items: {\r\n                  type: \"string\",\r\n                  enum: [\"preview\", \"calc\", \"printAndBarCode\", \"actions\"]\r\n                }\r\n              },\r\n            }\r\n          },\r\n        ],\r\n      },\r\n      {\r\n        url: \"#/reports/holiday-report\",\r\n        id: \"holidayReport\",\r\n        visibility: \"visible\",\r\n        isFullWidth: true,\r\n      },\r\n      {\r\n        url: \"#/reports/holiday-pay-report-query/*\",\r\n        isFullWidth: true,\r\n        id: \"holidayPayReportQuery\",\r\n        visibility: \"hidden\",\r\n      },\r\n      {\r\n        url: \"#/reports/pay-stats-report-query/*\",\r\n        isFullWidth: true,\r\n        id: \"payStatsReportQuery\",\r\n        visibility: \"hidden\",\r\n      },\r\n      {\r\n        url: \"#/irepr\",\r\n        id: \"irepr\",\r\n        roles: \"test\",\r\n        children: [{\r\n          url: \"#/irepr/details/*\",\r\n          id: \"details\"\r\n        }],\r\n      },\r\n      {\r\n        url: \"#/irpsr\",\r\n        id: \"irpsr\",\r\n        roles: \"test\",\r\n        children: [{\r\n          url: \"#/irpsr/details/*\",\r\n          id: \"details\",\r\n        }],\r\n      },\r\n    ],\r\n  },\r\n  {\r\n    url: \"#/settings\",\r\n    id: \"settings\",\r\n    roles: \"company\",\r\n    children: [\r\n      {\r\n        url: \"#/settings\",\r\n        id: \"index\",\r\n        params: {\r\n          features: {\r\n            title: \"Features\",\r\n            type: \"array\",\r\n            default: [\"account\", \"insurances\", \"accountant\", \"paymentChannels\"],\r\n            items: {\r\n              type: \"string\",\r\n              enum:  [\"account\", \"insurances\", \"accountant\", \"paymentChannels\"],\r\n            }\r\n          }\r\n        },\r\n      },\r\n      {\r\n        url: \"#/settings/payment-settings\",\r\n        id: \"paymentSettings\",\r\n        i18n: [ \"SALAXY.NG1.PaymentSettingsComponent\"],\r\n\r\n      },\r\n      {\r\n        url: \"#/settings/insurances\",\r\n        id: \"insurances\",\r\n        i18n: [ \"SALAXY.NG1.InsuranceSettingsComponent\"],\r\n      },\r\n      {\r\n        url: \"#/settings/row-types-settings\",\r\n        roles: \"test\",\r\n        id: \"rowTypesSettings\",\r\n      },\r\n      {\r\n        url: \"#/settings/payment-channel-settings\",\r\n        id: \"paymentChannelSettings\",\r\n      },\r\n      {\r\n        url: \"#/settings/accounting-target-settings\",\r\n        id: \"accountingTargetSettings\",\r\n      },\r\n      {\r\n        url: \"#/settings/owner-settings\",\r\n        id: \"ownerSettings\",\r\n      },\r\n      {\r\n        url: \"#/settings/service-settings\",\r\n        id: \"serviceSettings\",\r\n      },\r\n      {\r\n        url: \"#/settings/records\",\r\n        id: \"records\",\r\n        visibility: \"hidden\",\r\n      },\r\n      {\r\n        url: \"#/settings/authorizations\",\r\n        id: \"authorizations\",\r\n      },\r\n      {\r\n        id: \"accountants\",\r\n        url: \"#/settings/accountants\",\r\n        roles: \"company\",\r\n        i18n:[\"SALAXY.NG1.AccountantComponent\",\"SALAXY.NG1.AccountantSelectionComponent\"],\r\n        params: {\r\n          \"accountantRemovalDisabled\": {\r\n            title: \"Tilitoimiston poistaminen estetty\",\r\n            type: \"boolean\",\r\n          }\r\n        }\r\n      },\r\n      {\r\n        id: \"integrations\",\r\n        url: \"#/settings/integrations\",\r\n      },\r\n      {\r\n        id: \"accountReset\",\r\n        url: \"#/settings/account-reset\",\r\n        roles: \"test\",\r\n      },\r\n      {\r\n        id: \"paymentChannel\",\r\n        url: \"#/payment-channel\",\r\n        visibility: \"hidden\",\r\n      },\r\n    ],\r\n  },\r\n  {\r\n    url: \"#/service-models/index\",\r\n    id: \"pro-service\",\r\n    roles: \"test&&company\",\r\n    children: [\r\n      {\r\n        url: \"#/service-models/details/*\",\r\n        id: \"details\",\r\n        visibility: \"hidden\",\r\n        isFullWidth: true,\r\n      },\r\n      {\r\n        url: \"#/settings/pro-settings\",\r\n        id: \"proSettings\",\r\n      },\r\n      {\r\n        id: \"usecases\",\r\n        url: \"#/usecases\",\r\n        children: [\r\n          {\r\n            id: \"details\",\r\n            url: \"#/usecases/details/*\",\r\n            isFullWidth: true,\r\n          }\r\n        ]\r\n      },\r\n      {\r\n        id: \"worktime-imports\",\r\n        url: \"#/worktime-imports\",\r\n        isFullWidth: true,\r\n        children: []\r\n      },\r\n      {\r\n        id: \"datasets\",\r\n        title: \"Datasets\",\r\n        url: \"#/datasets\",\r\n        children: [\r\n          {\r\n            id: \"details\",\r\n            title: \"Dataset\",\r\n            url: \"#/datasets/details/*\",\r\n            isFullWidth: true,\r\n          }\r\n        ]\r\n      },\r\n      {\r\n        id: \"calendar\",\r\n        url: \"#/calendar\",\r\n        children: [\r\n          {\r\n            id: \"details\",\r\n            url: \"#/calendar/details/*\",\r\n          }\r\n        ]\r\n      },\r\n      {\r\n        url: \"#/accounting-targets\",\r\n        id: \"accountingTargets\",\r\n        children: [{\r\n          url: \"#/accounting-targets/details/*\",\r\n          isFullWidth: true,\r\n          id: \"details\",\r\n        }]\r\n      },\r\n      {\r\n        url: \"#/customer-invoices\",\r\n        id: \"customerInvoices\",\r\n        children: [{\r\n          url: \"#/customer-invoices/details/*\",\r\n          isFullWidth: false,\r\n          id: \"details\",\r\n        }]\r\n      },\r\n    ],\r\n  },\r\n  {\r\n    url: \"#/info\", // info\r\n    id: \"info\",\r\n    children: [\r\n      {\r\n        url: \"#/info\",\r\n        id: \"index\",\r\n        hidden:true,\r\n        i18n:[\"SALAXY.NG1_Pages.Info\", \"SALAXY.NG1.ContactInfoComponent\"],\r\n        params: {\r\n          \"hideButtons\": {\r\n            title: \"Piilota palkkaus.fi-napit\",\r\n            type: \"boolean\",\r\n          },\r\n          \"hideContactInfo\": {\r\n            title: \"Piilota Aspan yhteystiedot\",\r\n            type: \"boolean\",\r\n          },\r\n        },\r\n      },\r\n      {\r\n        url: \"#/info/abc\", // temporary fallback\r\n        id: \"abc\",\r\n        visibility: \"hidden\",\r\n      }\r\n    ],\r\n  },\r\n];","import { Arrays, OpenAPIV3, ServiceModelSite, SitemapNode, SitemapVisibility, UserSession } from \"@salaxy/core\";\r\nimport angular from \"angular\";\r\nimport { sitemap_PersonLeafs } from \"./sitemap_PersonLeafs\";\r\nimport { sitemap_Company } from \"./sitemap_Company\";\r\n\r\n/**\r\n * Helper for managing standard web sitemaps in navigation.\r\n */\r\nexport class SitemapHelper {\r\n\r\n  public constructor() {\r\n    console.debug(\"snowpackHack constructor\");\r\n  }\r\n\r\n  /**\r\n   * Gets logical visibility, as used in the views an UI logic, i.e.:\r\n   *\r\n   * - hidden: Node is null or visibility is Hidden, HiddenReadOnly or Disabled.\r\n   * - readOnly: Node is null or visibility is ReadOnly, HiddenReadOnly.\r\n   * - disabled: Visibility is Disabled.\r\n   * - Visible: Visibility is Visible or null, node is not null.\r\n   * - isFullWidth: The node has an isFullWidth boolean flag set to true.\r\n   * Supports exclamation mark (!) in the beginning to denote negation (true <=> false).\r\n   * @param node Node to evaluate\r\n   * @param evaluateFor The visibility value to evaluate for.\r\n   */\r\n  public static getVisibility(node: SitemapNode, evaluateFor: SitemapVisibility | \"isFullWidth\" | string): boolean {\r\n    if (evaluateFor?.[0] == \"!\") {\r\n      return !this.getVisibility(node, evaluateFor.substring(1));\r\n    }\r\n    switch (evaluateFor) {\r\n      case SitemapVisibility.Disabled:\r\n        return node?.visibility == SitemapVisibility.Disabled;\r\n      case SitemapVisibility.Hidden:\r\n        return node == null || node.visibility == SitemapVisibility.Disabled ||\r\n          node.visibility == SitemapVisibility.Hidden || node.visibility == SitemapVisibility.HiddenReadOnly;\r\n      case SitemapVisibility.HiddenReadOnly:\r\n        // Probably does not really make sense, just for copleteness.\r\n        return this.getVisibility(node, SitemapVisibility.Hidden) || this.getVisibility(node, SitemapVisibility.ReadOnly);\r\n      case SitemapVisibility.ReadOnly:\r\n        return node == null || node.visibility == SitemapVisibility.ReadOnly || node.visibility == SitemapVisibility.HiddenReadOnly;\r\n      case SitemapVisibility.Visible:\r\n        return node != null && (!node.visibility || node.visibility == SitemapVisibility.Visible);\r\n      case \"isFullWidth\":\r\n        return !!node?.isFullWidth;\r\n      default:\r\n        throw new Error(\"Unknown visibility value to evaluate:\" + evaluateFor);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Gets the standard company sitemap for Company web sites.\r\n   */\r\n  public static getCompanySiteMap(): SitemapNode[] {\r\n    return this.setSitemapTitles(sitemap_Company);\r\n  }\r\n\r\n  /**\r\n   * Gets the editable version of the sitemap: Full ID's etc.\r\n   * @param site The Site as customized in the Service model.\r\n   * @param nodes Root nodes to start from. If null, a copy of the baseTree is used.\r\n   * @param parentId Identifier of the parent. Used in recursive calls to add fully qualified ID's to all nodes.\r\n   * @returns An editable sitemap.\r\n   */\r\n  public static getEditableSitemap(site: ServiceModelSite, nodes: SitemapNode[] = null, parentId: string = null): SitemapNode[] {\r\n    const i18Prefix = \"SALAXY.NG1_Sitemap\";\r\n    nodes = nodes || angular.copy(sitemap_Company);\r\n    (nodes || []).forEach((node) => {\r\n      let hasChildrenChanges = false;\r\n      const id = parentId ? `${parentId}.${node.id || \"undefined\"}` : node.id;\r\n      if (node.children) {\r\n        hasChildrenChanges = !!this.getEditableSitemap(site, node.children, id).find((x => x.$edit.$hasChanges || x.$edit.$hasTextChanges || x.$edit.$hasChildrenChanges));\r\n      }\r\n      const isOpen = !!node.$edit?.$isOpen;\r\n      node.$edit = site.sitemap?.[id] ? angular.copy(site.sitemap?.[id]) : {};\r\n      if (Object.keys(node.$edit).length) {\r\n        node.$edit.$hasChanges = true;\r\n      }\r\n      node.$edit.$hasChildrenChanges = hasChildrenChanges;\r\n      node.$edit.$isOpen = isOpen;\r\n      node.$edit.$id = id;\r\n      const sectionPostFix = node.children ? \".main\" : \"\";\r\n      node.$edit.$i18nKey = `${i18Prefix}.${id}${sectionPostFix}`;\r\n      if (Object.keys(site.texts ?? {}).find((x) => x.endsWith(node.$edit.$i18nKey))) {\r\n        node.$edit.$hasTextChanges = true;\r\n      }\r\n      switch (node.$edit.visibility || node.visibility) {\r\n        case SitemapVisibility.Disabled:\r\n          node.$edit.$faIcons = [\"fa-ban\"];\r\n          break;\r\n        case SitemapVisibility.Hidden:\r\n          node.$edit.$faIcons = [\"fa-eye-slash\"];\r\n          break;\r\n        case SitemapVisibility.HiddenReadOnly:\r\n          node.$edit.$faIcons = [\"fa-eye-slash\", \"fa-lock\"];\r\n          break;\r\n        case SitemapVisibility.ReadOnly:\r\n          node.$edit.$faIcons = [\"fa-lock\"];\r\n          break;\r\n        case SitemapVisibility.Visible:\r\n        default:\r\n          node.$edit.$faIcons = [];\r\n          break;\r\n      }\r\n      if (node.isFullWidth || node.$edit.isFullWidth) {\r\n        node.$edit.$faIcons.push(\"fa-arrows-h\");\r\n      }\r\n      node.$edit.visibility = node.$edit.visibility || \"default\";\r\n      // TODO: Add proper Array editor and remove this (also in commitSitemapNode()).\r\n      node.$edit.roles = Arrays.assureArray(node.$edit.roles).join(\",\");\r\n      // Direct title is not supported in translations, but it may be used development time.\r\n      node.title = node.title ? node.title : node.$edit.$i18nKey;\r\n    });\r\n    return nodes;\r\n  }\r\n\r\n  /**\r\n   * Applies custom properties from service model to set of sitemap nodes.\r\n   * Also does backward compatibility from old SalaxySitemapNode format to current SitemapNode.\r\n   * @param session User session that potentially contains the service model.\r\n   * If null or no partner.serviceModel.sitemap, the method does nothing.\r\n   * @param nodes Nodes that are being updated.\r\n   * @param parentId Identifier of the parent. Used in recursive calls to add fully qualified ID's to all nodes.\r\n   */\r\n  public static setCustomProperties(session: UserSession, nodes: SitemapNode[], parentId: string = null): void {\r\n    if (!nodes?.length) {\r\n      return;\r\n    }\r\n    const sitemapProps = session?.settings?.partner?.serviceModel?.site?.sitemap;\r\n    nodes.forEach((node) => {\r\n      // \"company-site\" is special root id for the situation when the company site is not the root, e.g. developers.salaxy.com (webs/ng1-dev)\r\n      const id = (parentId && parentId != \"company-site\") ? `${parentId}.${node.id || \"undefined\"}` : node.id;\r\n\r\n      // Backward compatibility\r\n      if (node.hidden && !node.visibility) {\r\n        node.visibility = SitemapVisibility.Hidden;\r\n      }\r\n\r\n      // Set custom properties.\r\n      if (sitemapProps) {\r\n        if (sitemapProps[id]) {\r\n          Object.keys(sitemapProps[id]).forEach((key) => {\r\n            const value = sitemapProps[id][key];\r\n            if (value) {\r\n              node[key] = value;\r\n            }\r\n          });\r\n        }\r\n      }\r\n      this.setCustomProperties(session, node.children, id);\r\n    });\r\n  }\r\n\r\n  /** This just to get snowpack working. */\r\n  public snowpackHack(): string {\r\n    return \"snowpackHack\";\r\n  }\r\n\r\n  /**\r\n   * Gets the combined sitemap that contains the structure for both company\r\n   * and personal (Worker, Household). this is used mainly in development and PRO service:\r\n   * typically, company and personal sites are separate and this tree is not used.\r\n   */\r\n   public static getAllRolesSiteMap(): SitemapNode[] {\r\n     const tree = angular.copy(sitemap_Company);\r\n     tree.splice(tree.length - 1, 0, ...sitemap_PersonLeafs);\r\n     return this.setSitemapTitles(tree);\r\n  }\r\n\r\n  /**\r\n   * Sets the titles for each node in given sitemap based on node id from the given tranlsation.\r\n   * @param sitemap Selected sitemap to add titles to\r\n   * @param currentPath Current node in sitemap object\r\n   * @param i18Prefix Translation key prefix (defaults to SALAXY.NG1_Sitemap)\r\n   */\r\n  public static setSitemapTitles(sitemap: SitemapNode[], currentPath = \"\", i18Prefix = \"SALAXY.NG1_Sitemap\"): SitemapNode[] {\r\n    for (const node of sitemap) {\r\n      const newPath = currentPath ? `${currentPath}.${node.id}` : node.id;\r\n      const sectionPostFix = node.children ? \".main\" : \"\";\r\n      node.title = node.title ? node.title : `${i18Prefix}.${newPath}${sectionPostFix}`;\r\n      if (node.children) {\r\n        this.setSitemapTitles(node.children, newPath, i18Prefix);\r\n      }\r\n    }\r\n    return sitemap;\r\n  }\r\n\r\n\r\n  /**\r\n   * Removes a section based on id.\r\n   * @param sitemap Sitemap from which the section is removed.\r\n   * @param sectionId Identifier for finding the section to remove.\r\n   */\r\n  public static removeSection(sitemap: SitemapNode[], sectionId: string): void {\r\n    const index = sitemap.findIndex((x) => x.id === sectionId);\r\n    if (index >= 0) {\r\n      sitemap.splice(index, 1);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Gets a section based on id.\r\n   * @param sitemap Sitemap from which the section is fetched.\r\n   * @param sectionId Identifier for finding the section to remove.\r\n   */\r\n  public static getSection(sitemap: SitemapNode[], sectionId: string): SitemapNode {\r\n    return sitemap.find((x) => x.id === sectionId);\r\n  }\r\n\r\n  /**\r\n   * Gets a node (subpage) based on id.\r\n   * @param sitemap Sitemap from which the section is fetched.\r\n   * @param sectionId Identifier for finding the section.\r\n   * @param nodeId Identifier for finding the node (subpage to modify or hide).\r\n   */\r\n  public static getNode(sitemap: SitemapNode[], sectionId: string, nodeId: string): SitemapNode {\r\n    const section = this.getSection(sitemap, sectionId);\r\n    if (!section || !section.children) {\r\n      return null;\r\n    }\r\n    return section.children.find((x) => x.id === nodeId);\r\n  }\r\n\r\n  /**\r\n   * Gets a JSON schema of a sitemap node using the params property.\r\n   * NOTE: Advanced properties (i18n, children and params) are not included in this schema. Add if needed.\r\n   */\r\n  public static getSchema(node: SitemapNode): OpenAPIV3.SchemaObject {\r\n    const result: OpenAPIV3.SchemaObject = {\r\n      title: \"Current sitemap node\",\r\n      type: \"object\",\r\n      properties: {\r\n        id: {\r\n          title: \"Identifier for the node: Should be unique within one set of children.\",\r\n          type: \"string\",\r\n        },\r\n        title: {\r\n          title: \"Hard-coded single-language title. This should be used in dev/testing only\",\r\n          type: \"string\",\r\n        },\r\n        url: {\r\n          title: \"Navigation URL for the node.\",\r\n          type: \"string\",\r\n        },\r\n        roles: {\r\n          title: \"Roles for limiting the visibility of the node.\",\r\n          anyOf: [\r\n            {\r\n                \"type\": \"string\",\r\n            },\r\n            {\r\n              type: \"array\",\r\n              items: { type: \"string\" }\r\n            }\r\n          ]\r\n        },\r\n        visibility: {\r\n          title: \"Specifies how the node is shown in the navi / UI. Default / null is 'visible'.\",\r\n          type: \"string\",\r\n        },\r\n        isFullWidth: {\r\n          title: \"If true, sets container class to container-fluid\",\r\n          type: \"string\",\r\n        },\r\n        /*\r\n        i18n: {\r\n          title: \"\",\r\n          type: \"array\",\r\n          items: {\r\n            type: \"string\",\r\n          }\r\n        },\r\n        children: {\r\n          title: \"Array of child nodes.\",\r\n          type: \"object\",\r\n        },\r\n        params: {\r\n          title: \"Defines the json schema for parameters that may be defined for a single node/page.\",\r\n          type: \"object\",\r\n        }\r\n        */\r\n      }\r\n    };\r\n    if (node.params) {\r\n      result.properties = {...result.properties, ...node.params};\r\n    }\r\n    return result;\r\n  }\r\n}\r\n","import { JsonSchemaUtils, Objects, SitemapNode, SitemapVisibility } from \"@salaxy/core\";\r\nimport { SitemapHelper } from \"./SitemapHelper\";\r\n\r\n/** Contains information about the current sitemap node (if resoved) and other data related to route. */\r\nexport class CurrentRoute {\r\n  constructor(currentPath: SitemapNode[]) {\r\n    if (currentPath?.length) {\r\n      this.isResolved = true;\r\n      this.path = currentPath;\r\n      this.node = currentPath[currentPath.length - 1],\r\n      this.section = currentPath[0];\r\n    } else {\r\n      this.isResolved = false;\r\n      this.node = null;\r\n      this.path = [];\r\n      this.section = null;\r\n    }\r\n  }\r\n\r\n  /** The current path if resolved, otherwise an empty array */\r\n  public path: SitemapNode[];\r\n\r\n  /** The current sitemap node */\r\n  public node: SitemapNode;\r\n\r\n  /** The current section if resolved. */\r\n  public section: SitemapNode;\r\n\r\n  /** If true, the route is resolved to current sitemap node. */\r\n  public isResolved: boolean;\r\n\r\n  /**\r\n   * Gets logical visibility, as used in the views an UI logic, i.e.:\r\n   *\r\n   * - hidden: Node is null or visibility is Hidden, HiddenReadOnly or Disabled.\r\n   * - readOnly: Node is null or visibility is ReadOnly, HiddenReadOnly.\r\n   * - disabled: Visibility is Disabled.\r\n   * - Visible: Visibility is Visible or null, node is not null.\r\n   * - isFullWidth: The node has an isFullWidth boolean flag set to true.\r\n   *\r\n   * Supports exclamation mark (!) in the beginning to denote negation (true <=> false).\r\n   * @param visibility The visibility value to evaluate for.\r\n   */\r\n  public getVisibility(visibility: SitemapVisibility | string): boolean {\r\n    return SitemapHelper.getVisibility(this.node, visibility);\r\n  }\r\n\r\n  /** Returns true if the page should be displayed read-only */\r\n  public get readOnly(): boolean {\r\n    return SitemapHelper.getVisibility(this.node, SitemapVisibility.ReadOnly);\r\n  }\r\n\r\n  /**\r\n   * Gets a parameter checking the default value from the schema.\r\n   * The method fails if the parameter is not defined in the schema.\r\n   * @param path Path to the sitemap value / schema definition.\r\n   */\r\n  public getParam(path: string) {\r\n    if (!this.node?.params) {\r\n      throw new Error(`The current node ${this.node?.url} does not have parameters defined (path: '${path}').`);\r\n    }\r\n    const prop = JsonSchemaUtils.getProperty(SitemapHelper.getSchema(this.node), path);\r\n    if (!prop) {\r\n      throw new Error(`The current node ${this.node.url} does not have property ${path} defined in the schema.`);\r\n    }\r\n    const value = Objects.getProperty(this.node, path);\r\n    if (value != null) {\r\n      return value; // Nullish values go to default.\r\n    }\r\n    if (prop.schema.default !== undefined) {\r\n      return prop.schema.default; // Default may be null?\r\n    }\r\n    return null; // Should boolean values default to false?\r\n  }\r\n\r\n  /**\r\n   * Checks if the value contain the given flag value.\r\n   * Typically the value is an array of enum strings and this method checks if it contains an item,\r\n   * but the method also checks for a direct match (without being an array).\r\n   * @param path Path to the sitemap value / schema definition.\r\n   * @param flagValue Text value (typically a string enum) that should be present in the array.\r\n   */\r\n  public getFlag(path: string, flagValue: string): boolean {\r\n    const val = this.getParam(path);\r\n    if (Array.isArray(val)) {\r\n      return !!val.find((x) => x == flagValue);\r\n    }\r\n    return val == flagValue;\r\n  }\r\n\r\n}","import angular from \"angular\";\r\n\r\n/**\r\n * Polyfill which replaces ES6 promises with $q.\r\n * This is required, for example if Promise.resolve -methods are used.\r\n * They are not correctly digested using ES6 promises only.\r\n */\r\nexport class PromisePolyfill {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n\r\n   /** Dependencies */\r\n  public static $inject = [\"$q\", \"$window\"];\r\n  constructor($q: angular.IQService, $window: angular.IWindowService) {\r\n    $window.Promise = function (resolver) {\r\n      return $q(resolver);\r\n    };\r\n\r\n    $window.Promise.all = $q.all.bind($q);\r\n    $window.Promise.reject = $q.reject.bind($q);\r\n    $window.Promise.resolve = $q.resolve.bind($q);\r\n    $window.Promise.race = $q.race.bind($q);\r\n    $window.Promise.allSettled = ((promises) => $window.Promise.all(promises.map(p => p\r\n      .then(value => ({\r\n          status: \"fulfilled\", value\r\n      }))\r\n      .catch(reason => ({\r\n          status: \"rejected\", reason\r\n      }))\r\n    )));\r\n  }\r\n}\r\n","import angular from \"angular\";\r\nimport { Configs} from \"@salaxy/core\";\r\n\r\n/** Helps creating Salaxy standard routing. */\r\nexport class RouteHelperProvider implements angular.IServiceProvider {\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  protected static $inject = [\"$routeProvider\"];\r\n\r\n  /** The root folder that contains the custom views. Default is \"./views\" */\r\n  public customSectionRoot = \"./views\";\r\n\r\n  /**\r\n   * TODO: Consider implementing the IServiceProvider interface\r\n   */\r\n  // eslint-disable-next-line @typescript-eslint/no-unused-vars\r\n  public $get = [\"$rootScope\" , ($rootScope: any) => {\r\n    return \"todo\";\r\n  }];\r\n\r\n  public constructor(private $routeProvider: angular.route.IRouteProvider) {\r\n  }\r\n\r\n  /**\r\n   * Adds a routing section where views are coming by default from custom folder.\r\n   * @param section Navigation section in routing.\r\n   * Also used as default for views folder.\r\n   * @param defaultViews Exceptions to the rule: Individual views / pages that should be mapped\r\n   * to default views stored in ng1 library under \"salaxy-components/pages/\".\r\n   * @param defaultViewsFolder The name of the default views folder if not the same as section.\r\n   * If not specified, the folder is \"salaxy-components/pages/[section]\".\r\n   * If the paths starts with \"salaxy-components\", \"/\" or \".\", the path is assumed being a full path.\r\n   * Otherwise the \"salaxy-components/pages/\" is added before defaultViewsFolder. So typically this can be just a folder / section name (e.g. \"calc\").\r\n   * @param customViewsFolder If specified, this is the path to the custom folder where the views are.\r\n   * If NOT specified, \"[customSectionRoot]/[section]\" is used.\r\n   * If the paths starts with \"/\" or \".\", the path is assumed being a full path.\r\n   * Otherwise the customSectionRoot (default \"./views/\") is added before customViewsFolder. So typically this can be just a folder / section name (e.g. \"calc\").\r\n   * @example\r\n   * RouteHelperProvider.customSection(\"calc\", [\"details\"]).\r\n   * // Adds a route as \"/calc/:viewName?/:crudItemId*?\" where all views are located in \"./views/calc/[:viewName].html\",\r\n   * // except \"/calc/details/:crudItemId*?\", which is mapped to \"salaxy-components/pages/calc/details.html\"\r\n   */\r\n  public customSection(section: string, defaultViews?: string[], defaultViewsFolder?: string, customViewsFolder?: string): RouteHelperProvider {\r\n    defaultViewsFolder = defaultViewsFolder || section;\r\n    if (!defaultViewsFolder.startsWith(\".\") && !defaultViewsFolder.startsWith(\"/\") && !defaultViewsFolder.startsWith(\"salaxy-components/\")) {\r\n      defaultViewsFolder = \"salaxy-components/pages/\" + defaultViewsFolder;\r\n    }\r\n    customViewsFolder = customViewsFolder || section;\r\n    if (!customViewsFolder.startsWith(\".\") && !customViewsFolder.startsWith(\"/\") && !customViewsFolder.startsWith(\"salaxy-components/\")) {\r\n      customViewsFolder = this.customSectionRoot + \"/\" + customViewsFolder;\r\n    }\r\n    if (defaultViews && Array.isArray(defaultViews)) {\r\n      defaultViews.forEach((view) => {\r\n        this.when(`/${section}/${view}/:crudItemId*?`, { templateUrl: `${defaultViewsFolder}/${view}.html` }, section);\r\n      });\r\n    }\r\n    this.when(`/${section}/:viewName?/:crudItemId*?`, {\r\n      templateUrl: (path) => `${customViewsFolder}/${path.viewName || \"index\"}.html`,\r\n    }, section);\r\n    return this;\r\n  }\r\n\r\n  /**\r\n   * Adds a routing section where views are coming by default from the product ng1 library compiled to \"salaxy-components/pages/\".\r\n   * @param section Section for the views, e.g. \"calc\" for \"salaxy-components/pages/calc\"\r\n   * @param customViews Exceptions to the rule:\r\n   * Individual views that should be mapped to custom folder under customSectionRoot.\r\n   * @param customViewsFolder The name of the custom views folder if not the same as section.\r\n   * If the paths starts with \"/\" or \".\", the path is assumed being a full path.\r\n   * Otherwise the customSectionRoot (default \"./views/\") is added before customViewsFolder. So typically this can be just a folder / section name (e.g. \"calc\").\r\n   * @param defaultViewsFolder The name of the default views folder if not the same as section.\r\n   * If not specified, the folder is \"salaxy-components/pages/[section]\".\r\n   * If the paths starts with \"salaxy-components\", \"/\" or \".\", the path is assumed being a full path.\r\n   * Otherwise the \"salaxy-components/pages/\" is added before defaultViewsFolder. So typically this can be just a folder / section name (e.g. \"calc\").\r\n   * @example\r\n   * RouteHelperProvider.defaultSection(\"calc\", [\"details\"], \"ng1/calc\").\r\n   * // Adds a route as \"/calc/:viewName?/:crudItemId*?\" where all views are located in \"salaxy-components/pages/calc/\" folder\r\n   * // except \"/calc/details/:crudItemId*?\", which is mapped to \"./views/ng1/calc/details.html\".\r\n   */\r\n  public defaultSection(section: string, customViews?: string[], customViewsFolder?: string, defaultViewsFolder?: string): RouteHelperProvider {\r\n    customViewsFolder = customViewsFolder || section;\r\n    if (!customViewsFolder.startsWith(\".\") && !customViewsFolder.startsWith(\"/\") && !customViewsFolder.startsWith(\"salaxy-components/\")) {\r\n      customViewsFolder = this.customSectionRoot + \"/\" + customViewsFolder;\r\n    }\r\n    defaultViewsFolder = defaultViewsFolder || section;\r\n    if (!defaultViewsFolder.startsWith(\".\") && !defaultViewsFolder.startsWith(\"/\") && !defaultViewsFolder.startsWith(\"salaxy-components/\")) {\r\n      defaultViewsFolder = \"salaxy-components/pages/\" + defaultViewsFolder;\r\n    }\r\n    if (customViews && Array.isArray(customViews)) {\r\n      customViews.forEach((view) => {\r\n        if (view === \"index\") {\r\n          this.when(`/${section}/index/:crudItemId*?`, { templateUrl: `${customViewsFolder || section}/index.html` }, section);\r\n          this.when(`/${section}`, { templateUrl: `${customViewsFolder || section}/index.html` }, section);\r\n        } else {\r\n          this.when(`/${section}/${view}/:crudItemId*?`, { templateUrl: `${customViewsFolder || section}/${view}.html` }, section);\r\n        }\r\n      });\r\n    }\r\n    this.when(`/${section}/:viewName?/:crudItemId*?`, {\r\n      templateUrl: (path) => `${defaultViewsFolder}/${path.viewName || \"index\"}.html`,\r\n    }, section);\r\n    return this;\r\n  }\r\n\r\n  /**\r\n   * Fluid syntax for setting customSectionRoot.\r\n   * @param customSectionRoot Root folder for the custom views.\r\n   * You can use null to set the customSection to default \"./views\", empty string to none.\r\n   * No trailing dashes i.e. \"./views\", not \"./views/\".\r\n   */\r\n  public setCustomSectionRoot(customSectionRoot: string | null): RouteHelperProvider {\r\n    if (customSectionRoot == null) {\r\n      customSectionRoot = \"./views\";\r\n    }\r\n    this.customSectionRoot = customSectionRoot;\r\n    return this;\r\n  }\r\n\r\n  /**\r\n   * Adds the standard index/home pages: \"/\", \"/index\" and \"/welcome\".\r\n   * May later contain special pages like standard error etc.\r\n   * NOTE: If any of the sections already exists, will not add them.\r\n   * @param customViewsFolder if set, uses the given custom folder. Otherwise, sets the paths from library.\r\n   */\r\n  public homeDefault(customViewsFolder?: string): RouteHelperProvider {\r\n    const homePage = customViewsFolder ? `${this.customSectionRoot}/${customViewsFolder}/index.html` : \"salaxy-components/pages/home/index.html\";\r\n    if (!this.sectionExists(\"\")) {\r\n      this.when(\"/\", { templateUrl: homePage }, \"\");\r\n    }\r\n    if (!this.sectionExists(\"index\")) {\r\n      this.when(\"/index\", { templateUrl: homePage }, \"index\");\r\n    }\r\n    if (!this.sectionExists(\"welcome\")) {\r\n      this.when(\"/welcome\", { templateUrl: homePage }, \"welcome\");\r\n    }\r\n    return this;\r\n  }\r\n\r\n  /**\r\n   * For backward compatibility only: Use commit() instead.\r\n   * @deprecated For backward compatibility only: Use commit() instead.\r\n   */\r\n  public otherwiseDefault(): void {\r\n    this.commit();\r\n  }\r\n\r\n  /**\r\n   * Equivalent for calling $routeProvider.when(): Adds a new route definition to the $route service.\r\n   * Call commit() method for these configurations to have an effect.\r\n   * @param path Route path (matched against $location.path). If $location.path contains redundant trailing slash or is missing one, the route will still match and the $location.path will be updated to add or drop the trailing slash to exactly match the route definition.\r\n   *\r\n   * - path can contain named groups starting with a colon: e.g. :name. All characters up to the next slash are matched and stored in $routeParams under the given name when the route matches.\r\n   * - path can contain named groups starting with a colon and ending with a star: e.g.:name*. All characters are eagerly stored in $routeParams under the given name when the route matches.\r\n   * - path can contain optional named groups with a question mark: e.g.:name?.\r\n   *\r\n   * For example, routes like /color/:color/largecode/:largecode*\\/edit will match /color/brown/largecode/code/with/slashes/edit and extract: color: brown and largecode: code/with/slashes.\r\n   * @param route Mapping information to be assigned to $route.current on route match.\r\n   * @param section identifies the section for later evaluating whether a certain section has been defined or not:\r\n   * This is used in adding the deafults at the commit(): If section is found, it is not filled with defaults\r\n   * E.g. for path \"/calc/details\" this would be \"calc\" and \"/\", it would be \"\".\r\n   * Please note that in the \"calc\" case you would need to make sure all the other \"calc section\" routes are handled,\r\n   * typically by calling defaultSection(\"calc\") or customSection(\"calc\") within the router config.\r\n   */\r\n  public when(path: string, route: angular.route.IRoute, section: string): RouteHelperProvider {\r\n    this.routeModel.when.push({ section, path, route });\r\n    return this;\r\n  }\r\n\r\n  /**\r\n   * Equivalent for calling $routeProvider.otherwise():\r\n   * Sets route definition that will be used on route change when no other route definition is matched.\r\n   * Call commit() method for these configurations to have an effect.\r\n   * @param params information to be assigned to $route.current.\r\n   */\r\n  public otherwise(params: angular.route.IRoute | string): RouteHelperProvider {\r\n    this.routeModel.otherwise = params;\r\n    return this;\r\n  }\r\n\r\n  /**\r\n   * Used in Development and PRO sites to add the Person (Worker/Household) related routes.\r\n   * Typically, sites that target Person accounts are specialized and will not use this method.\r\n   */\r\n  public addPersonRoutes() : RouteHelperProvider {\r\n    this.customSection(\"person-archive\", [], \"salaxy-components/pages-personal/archive\", \"salaxy-components/pages-personal/archive\");\r\n    this.customSection(\"person-account\", [], \"salaxy-components/pages-personal/account\", \"salaxy-components/pages-personal/account\");\r\n    this.customSection(\"person-calc\", [], \"salaxy-components/pages-personal/calc\", \"salaxy-components/pages-personal/calc\");\r\n    this.customSection(\"person-taxcards\", [], \"salaxy-components/pages-personal/taxcards\", \"salaxy-components/pages-personal/taxcards\");\r\n    return this;\r\n  }\r\n\r\n  /**\r\n   * Commits the intermediary routeModel to the AngularJS $routeProvider.\r\n   * If skipDefault is not set to true, will set the defaults by calling\r\n   * homeDefault(), defaultSection for each product section and otherwiseDefault\r\n   * if the corresponding sections have not already been defined.\r\n   * @param skipDefaults By default, the method first adds all the product-defined\r\n   * default routes to the routeModel. If true, will not add the default routes.\r\n   */\r\n  public commit(skipDefaults = false): void {\r\n    if (this.routeModel.isCommitted) {\r\n      throw new Error(\"RouteHelperProvider.commit() called more than once. This is not supported. Are you calling both otherwiseDefault() and commit()? The first is obsolete since the introduction of commit().\");\r\n    }\r\n    if (!skipDefaults) {\r\n      this.homeDefault();\r\n      this.addIfNotExists(\"home\");\r\n      this.addIfNotExists(\"accounting\");\r\n      this.addIfNotExists(\"accountant-wizard\");\r\n      this.addIfNotExists(\"calc\");\r\n      this.addIfNotExists(\"customer-invoices\");\r\n      this.addIfNotExists(\"datasets\");\r\n      this.addIfNotExists(\"messages\");\r\n      this.addIfNotExists(\"service\");\r\n      this.addIfNotExists(\"payroll\");\r\n      this.addIfNotExists(\"reports\");\r\n      this.addIfNotExists(\"irepr\");\r\n      this.addIfNotExists(\"irpsr\");\r\n      this.addIfNotExists(\"settings\");\r\n      this.addIfNotExists(\"accounting-targets\");\r\n      this.addIfNotExists(\"info\");\r\n      this.addIfNotExists(\"welcome\");\r\n      this.addIfNotExists(\"employments\");\r\n      this.addIfNotExists(\"workers\");\r\n      this.addIfNotExists(\"partners\");\r\n      this.addIfNotExists(\"invoices\");\r\n      this.addIfNotExists(\"payment-channel\");\r\n      this.addIfNotExists(\"earnings-payments\");\r\n      this.addIfNotExists(\"salary-reports\");\r\n      this.addIfNotExists(\"test\");\r\n      this.addIfNotExists(\"calendar\");\r\n      this.addIfNotExists(\"usecases\");\r\n      this.addIfNotExists(\"worktime-imports\");\r\n      this.addIfNotExists(\"service-models\");\r\n      this.addIfNotExists(\"household-years\");\r\n      this.addIfNotExists(\"worktime-imports\");\r\n      this.addIfNotExists(\"templates\");\r\n      if (Configs.current?.isTestData) {\r\n        this.addIfNotExists(\"reference-objects\");\r\n      }\r\n\r\n      if (!this.routeModel.otherwise) {\r\n        this.routeModel.otherwise = { templateUrl: \"salaxy-components/pages/home/error404.html\" };\r\n      }\r\n    }\r\n    for (const when of this.routeModel.when) {\r\n      this.$routeProvider.when(when.path, when.route);\r\n    }\r\n    if (this.routeModel.otherwise) {\r\n      this.$routeProvider.otherwise(this.routeModel.otherwise);\r\n    }\r\n    this.routeModel.isCommitted = true;\r\n  }\r\n\r\n  /** Stores the route definition until Commit is being called. */\r\n  public routeModel: routeProviderModel = {\r\n    when: [],\r\n  };\r\n\r\n  /**\r\n   * Returns true if the sction is already defined in the route model.\r\n   * @param section Section for the views, e.g. \"calc\" for \"salaxy-components/pages/calc\"\r\n   */\r\n  public sectionExists(section: string): boolean {\r\n    return !!this.routeModel.when.find((x) => x.section === section);\r\n  }\r\n\r\n  /**\r\n   * Calls the defaultSection(section), but only if the sectrion has not been defined with custom values.\r\n   */\r\n  public addIfNotExists(section: string): boolean {\r\n    if (this.sectionExists(section)) {\r\n      return false;\r\n    }\r\n    this.defaultSection(section);\r\n    return true;\r\n  }\r\n}\r\n\r\n/** Defines a model that sotres the route until Commit is called to really register the route to Angular. */\r\nexport interface routeProviderModel {\r\n\r\n  /** Array of when statements that make up the route */\r\n  when: {\r\n    /** Identifies the section as simple string (e.g. 'calc'). */\r\n    section: string,\r\n    /**\r\n     * Route path (matched against $location.path). If $location.path contains redundant trailing slash or is missing one, the route will still match and the $location.path will be updated to add or drop the trailing slash to exactly match the route definition.\r\n     *\r\n     * - path can contain named groups starting with a colon: e.g. :name. All characters up to the next slash are matched and stored in $routeParams under the given name when the route matches.\r\n     * - path can contain named groups starting with a colon and ending with a star: e.g.:name*. All characters are eagerly stored in $routeParams under the given name when the route matches.\r\n     * - path can contain optional named groups with a question mark: e.g.:name?.\r\n     *\r\n     * For example, routes like /color/:color/largecode/:largecode*\\/edit will match /color/brown/largecode/code/with/slashes/edit and extract: color: brown and largecode: code/with/slashes.\r\n     */\r\n    path: string,\r\n\r\n    /** Mapping information to be assigned to $route.current on route match. */\r\n    route: angular.route.IRoute,\r\n  }[]\r\n\r\n  /** The deafult route (otherwise) */\r\n  otherwise?: angular.route.IRoute | string,\r\n  /** True if the route has been committed to Angular. */\r\n  isCommitted?: boolean;\r\n\r\n}\r\n","export const RRuleFinnish: {\r\n  /** Names of days */\r\n  dayNames: string[]\r\n  /** Names of months */\r\n  monthNames: string[]\r\n  /** Tokens for natural language parsing (NOT IN USE!) */\r\n  tokens: {\r\n    [k: string]: RegExp\r\n  }\r\n  /** The key texts that are used by the gettext method. */\r\n  texts: {\r\n    [k: string]: string\r\n  }\r\n} = {\r\n  dayNames: [\r\n    \"Sunnuntai\", \"Maanantai\", \"Tiisatai\", \"Keskiviikko\",\r\n    \"Torstai\", \"Perjantai\", \"Lauantai\"\r\n  ],\r\n  monthNames: [\r\n    \"Tammikuu\", \"Helmikuu\", \"Maaliskuu\", \"Huhtikuu\", \"Toukokuu\",\r\n    \"Kesäkuu\", \"Heinäkuu\", \"Elokuu\", \"Syyskuu\", \"Lokakuu\",\r\n    \"Marraskuu\", \"Joulukuu\"\r\n  ],\r\n  tokens: {},\r\n  texts: {\r\n    \"(~ approximate)\": \"(~ noin)\",\r\n    \"and\": \"ja\",\r\n    \"at\": \"klo\",\r\n    \"day\": \"päivä\",\r\n    \"days\": \"päivä\",\r\n    \"every\": \"joka\",\r\n    \"for\": \",\",\r\n    \"hour\": \"tunti\",\r\n    \"hours\": \"tunti\",\r\n    \"in\": \", vain kuukausina:\", // TODO: Is this used in other cases\r\n    \"last\": \"viimeisenä päivänä\",\r\n    \"minutes\": \"min\",\r\n    \"month\": \"kuukausi\",\r\n    \"months\": \"kuukausi\",\r\n    \"nd\": \".\",\r\n    \"on the\": \"aina\",\r\n    \"on\": \"on\", // TODO\r\n    \"or\": \"tai\",\r\n    \"rd\": \".\",\r\n    \"st\": \".\",\r\n    \"th\": \".\",\r\n    \"the\": \"\",\r\n    \"time\": \"kerta\",\r\n    \"times\": \"kertaa\",\r\n    \"until\": \"päättyen\",\r\n    \"week\": \"viikko\",\r\n    \"weekday\": \"viikonpäivä\",\r\n    \"weekdays\": \"viikonpäivä\",\r\n    \"weeks\": \"viikko\",\r\n    \"year\": \"vuosi\",\r\n    \"years\": \"vuosi\",\r\n    \"RRule error: Unable to fully convert this rrule to text\": \"Virhe: En ymmärrä tekstiä\"\r\n  }\r\n};\r\n","import angular from \"angular\";\r\n\r\nimport { Arrays, AppStatus, RoleLogic, SitemapNode, UserSession } from \"@salaxy/core\";\r\n\r\nimport { SessionService } from \"./../SessionService\";\r\nimport { CurrentRoute, SitemapHelper } from \"../../helpers\";\r\n\r\n\r\n/**\r\n * Helper service to generate navigation controls:\r\n * Top- and side-menus, paths and controls that show the current title.\r\n * These controls take the navigation logic from an object (sitemap) and are aware of current node / open page on that sitemap.\r\n * NOTE: This is just an optional helper to make creating simple demo sites easier.\r\n * There is no need to use NaviService, NaviController or components in your custom site!\r\n * You can use something completely different.\r\n */\r\nexport class NaviService {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$rootScope\", \"$location\", \"SessionService\", \"$injector\"];\r\n\r\n  /**\r\n   * Contains information about the current sitemap node (if resoved) and other data related to route.\r\n   * This property takes into account that the current node may not be found,\r\n   * i.e. current.node may be null, current.path may be [].\r\n   * However, the \"route\" as an object should never be null.\r\n   * Most other properties in NaviService use first node as default for historical reasons.\r\n   */\r\n  public current: CurrentRoute = new CurrentRoute(null);\r\n\r\n  /**\r\n   * Section where the current node is located.\r\n   * If current node cannot be resolved, this property defaults to first Sitemap node.\r\n   */\r\n  public currentSection: SitemapNode;\r\n\r\n  /**\r\n   * Currently selected sitemap node.\r\n   * If current node cannot be resolved, this property defaults to first Sitemap node.\r\n   */\r\n  public currentNode: SitemapNode;\r\n\r\n  /**\r\n   * Current path from root to the current node.\r\n   * If current node cannot be resolved, this property defaults to first Sitemap node.\r\n   */\r\n  public currentPath: SitemapNode[];\r\n\r\n  /**\r\n   * Title of the section (first level in the sitemap).\r\n   * If current node cannot be resolved, this property defaults to first Sitemap node.\r\n   */\r\n  public sectionTitle: string;\r\n\r\n  /**\r\n   * Title of the current sitemap node.\r\n   * If current node cannot be resolved, this property defaults to first Sitemap node.\r\n   */\r\n  public title: string;\r\n\r\n  /**\r\n   * True if the navigation (e.g. left sidebar) is open.\r\n   * Typically, this property is used only in narrow (mobile) view, otherwise the sidebar is always shown.\r\n   */\r\n  public isNaviOpen = false;\r\n\r\n  /**\r\n   * True if the secondary sidebar (e.g. right sidebar) is open.\r\n   */\r\n  public isSidebarOpen = false;\r\n\r\n  /** Sitemap that describes the structure of this application: For all roles. */\r\n  private sitemapForAllRoles: SitemapNode[];\r\n\r\n  /** Sitemap filtered for the roles of the current user. */\r\n  private sitemapInRole: SitemapNode[];\r\n\r\n  /** Cache for whether the system is using test data. */\r\n  private isTest: boolean;\r\n\r\n  constructor(\r\n    $rootScope: angular.IRootScopeService,\r\n    private $location: angular.ILocationService,\r\n    private sessionService: SessionService,\r\n    $injector: angular.auto.IInjectorService,\r\n  ) {\r\n    if ($injector.has(\"SITEMAP\")) {\r\n      this.setSitemap($injector.get(\"SITEMAP\"));\r\n    } else {\r\n      this.setSitemap([]);\r\n    }\r\n    // eslint-disable-next-line @typescript-eslint/no-unused-vars\r\n    $rootScope.$on(\"$routeChangeSuccess\", (event, current, previous) => {\r\n      this.resolveAndSetCurrentNode();\r\n    });\r\n    sessionService.subscribe($rootScope, () => {\r\n      this.updateSitemapInRole();\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Gets the current sitemap.\r\n   * @returns Sitemap filtered for the roles of the current user.\r\n   */\r\n  public getSitemap(): SitemapNode[] {\r\n    return this.sitemapInRole;\r\n  }\r\n\r\n  /**\r\n   * Sets the sitemap any time during the application lifecycle.\r\n   * Alternative way is to set angular constant \"SITEMAP\", but that must be done before config.\r\n   * @param newSitemap New sitemap to use.\r\n   */\r\n  public setSitemap(newSitemap: SitemapNode[]) {\r\n    this.sitemapForAllRoles = SitemapHelper.setSitemapTitles(newSitemap);\r\n    this.updateSitemapInRole();\r\n  }\r\n\r\n  /**\r\n   * Gets the current section: The first level node in the sitemap\r\n   * @returns Section filtered by the roles.\r\n   */\r\n  public getCurrentSection(): SitemapNode {\r\n    return this.currentSection;\r\n  }\r\n\r\n  /** Determines if a given node is the current node */\r\n  public isCurrent(siteMapNode: SitemapNode): boolean {\r\n    if (!siteMapNode || !this.currentPath) {\r\n      return false;\r\n    }\r\n    return !!this.currentPath.find((x) => x === siteMapNode);\r\n  }\r\n\r\n  /** Determines if a given section is the current section */\r\n  public isCurrentSection(section: SitemapNode): boolean {\r\n    return this.currentSection && section && this.currentSection.url === section.url;\r\n  }\r\n\r\n  /**\r\n   * Get sitemap node using path.\r\n   * @param path - Page URL path for the node.\r\n   * @returns - Node if exists, otherwise null.\r\n   */\r\n  public getNodeByPath(path: string): SitemapNode | null {\r\n    const sitemap = this.sitemapInRole;\r\n\r\n    for (const section of sitemap) {\r\n      const node = this.findNode(section, path);\r\n      if (node) {\r\n        return node;\r\n      }\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /**\r\n   * Get sitemap nodes using path.\r\n   * @param path - Page URL path for the node.\r\n   * @returns - Nodes path if exists, otherwise null.\r\n   */\r\n  public getNodesByPath(path: string): SitemapNode[] | null {\r\n    const targetNode = this.getNodeByPath(path);\r\n    if (!targetNode) {\r\n      return null;\r\n    }\r\n\r\n    const sitemap = this.sitemapInRole;\r\n    const targetNodePath = [targetNode];\r\n\r\n    /*eslint-disable no-constant-condition */\r\n    main:\r\n    while(true) {\r\n      const child = targetNodePath[0];\r\n      for (const section of sitemap) {\r\n        const parent = this.findParentNode(section, child);\r\n        if (parent) {\r\n          targetNodePath.unshift(parent);\r\n          continue main;\r\n        }\r\n      }\r\n      break;\r\n    }\r\n    return targetNodePath;\r\n  }\r\n\r\n  /**\r\n   * Filters the sitemap using the role-restrictions in the sitemap\r\n   * @param session - Optional explicitely given session for filtering the sitemap.\r\n   * @param appStatus - Optional explicitely given appStatus for filtering the sitemap. This must be given with explicitely given session.\r\n   */\r\n  public updateSitemapInRole(session: UserSession = null, appStatus: AppStatus = null): void {\r\n    const newSitemap: SitemapNode[] = angular.copy(this.sitemapForAllRoles);\r\n    this.isTest = session ? RoleLogic.isInRole(session, appStatus, \"test\") : this.sessionService.isInRole(\"test\");\r\n    if (!this.sessionService.isInSomeRole(\"pro,admin\")) {\r\n      // TODO: PRO should have its own service model (service model by role). Until that is implemented, we disable customizations here.\r\n      SitemapHelper.setCustomProperties(session || this.sessionService.session, newSitemap);\r\n    }\r\n    this.sitemapInRole = this.filterSitemapSectionsByRole(newSitemap, session, appStatus);\r\n    this.resolveAndSetCurrentNode();\r\n  }\r\n\r\n  /**\r\n   * Resolve current node from location path\r\n   */\r\n  public resolveAndSetCurrentNode(): void {\r\n    const urlFromPath = \"#\" + this.$location.path().toLowerCase();\r\n    const currentPath = this.resolveCurrent(urlFromPath, this.sitemapInRole);\r\n    this.current = new CurrentRoute(currentPath);\r\n    // Legacy mapping defaults to first sitemap node\r\n    this.currentPath = currentPath || [this.sitemapInRole[0]];\r\n    this.currentSection = this.currentPath[0];\r\n    this.currentNode = this.currentPath[this.currentPath.length - 1];\r\n    this.sectionTitle = this.currentSection?.title;\r\n    this.title = this.currentNode?.title;\r\n  }\r\n\r\n  /**\r\n   * Navigate to given path\r\n   * @param path - Path to navigate.\r\n   * @param checkSession - If true, triggers session refresh\r\n   */\r\n   public navigateTo(path: string, checkSession = false) {\r\n    const check = (): Promise<void> => {\r\n      if (!checkSession) {\r\n        return Promise.resolve();\r\n      } else {\r\n        return this.sessionService.checkSession().then( () => {\r\n          return;\r\n        });\r\n      }\r\n    };\r\n    check().then( () => {\r\n      this.$location.path(path);\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Evaluates wildcard string.\r\n   * @param nodeUrl - URL in the sitemap file (e.g. \"filename.html#/this/is/nodeUrl\"). From this, we take only the hash part (\"#/this/is/nodeUrl\").\r\n   * @param pathUrl - URL to evaluate - this is the hash path (e.g. \"#/this/is/pathUrl\")\r\n   * @returns Boolean whether the path url resides within the given node url.\r\n   */\r\n  private checkUrl(nodeUrl: string, pathUrl: string): boolean {\r\n    if (nodeUrl.indexOf(\"#\") !== -1) {\r\n      nodeUrl = nodeUrl.substr(nodeUrl.indexOf(\"#\"));\r\n    }\r\n    // Check and replace route parameters (:-strings) with wildcard *\r\n    const parts: string[] = nodeUrl.split(\"/\");\r\n    // eslint-disable-next-line @typescript-eslint/no-for-in-array\r\n    for (const i in parts) {\r\n      if (parts[i].indexOf(\":\") === 0) {\r\n        parts[i] = \"*\";\r\n      }\r\n    }\r\n    const newNodeUrl = parts.join(\"/\");\r\n    return this.wildCardMatch(newNodeUrl, pathUrl);\r\n  }\r\n\r\n  /**\r\n   * Evaluates wildcard string\r\n   * @param rule - Wildcard rule\r\n   * @param str - String to evaluate\r\n   * @returns Boolean whether the string matches the given wildcard rule.\r\n   */\r\n  private wildCardMatch(rule: string, str: string): boolean {\r\n    // \".\"  => Find a single character, except newline or line terminator\r\n    // \".*\" => Matches any string that contains zero or more characters\r\n    rule = rule.split(\"*\").join(\".*\");\r\n\r\n    // \"^\"  => Matches any string with the following at the beginning of it\r\n    // \"$\"  => Matches any string with that in front at the end of it\r\n    rule = \"^\" + rule + \"$\";\r\n\r\n    // Create a regular expression object for matching string\r\n    const regex = new RegExp(rule, \"i\");\r\n\r\n    // Returns true if it finds a match, otherwise it returns false\r\n    return regex.test(str);\r\n  }\r\n\r\n  /**\r\n   * Recursive resolver for any depth of sitemap nodes.\r\n   * @param url Url to check for.\r\n   * Note that in AngularJS paths, this should be the NG path starting with \"#\".\r\n   * @param nodes Nodes to check (typically the whole sitemap).\r\n   * @returns The path to current node or null if the current node cannot be resolved.\r\n   */\r\n  private resolveCurrent(url: string, nodes: SitemapNode[] | null): SitemapNode[] | null {\r\n    if (!nodes || nodes.length === 0) {\r\n      return null;\r\n    }\r\n    // home alias for root, this does not have any routeparameters\r\n    for (const node of nodes) {\r\n      const childMatch = this.resolveCurrent(url, node.children);\r\n      if (childMatch) {\r\n        return [node, ...childMatch];\r\n      }\r\n      if (this.checkUrl(node.url, url)) {\r\n        return [node];\r\n      }\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /**\r\n   * Filters a node tree bases on user roles.\r\n   * @param nodes - Array of nodes to filter\r\n   * @param session - Optional explicitely given session for filtering the sitemap.\r\n   * @param appStatus - Optional explicitely given appStatus for filtering the sitemap. This must be given with explicitely given session.\r\n   * @returns Filtered list of nodes.\r\n   */\r\n  private filterSitemapSectionsByRole(nodes: SitemapNode[], session: UserSession = null, appStatus: AppStatus = null): SitemapNode[] {\r\n    if (!nodes) {\r\n      return [];\r\n    }\r\n\r\n    const isInSomeRole = (roles: string | string[]) => {\r\n      return session ?\r\n        RoleLogic.isInSomeRole(session, appStatus,  Arrays.assureArray(roles)):\r\n        this.sessionService.isInSomeRole(roles);\r\n    };\r\n\r\n    const filteredNodes = nodes.filter((node) => {\r\n      const roles = Arrays.assureArray(node.roles);\r\n      if (isInSomeRole(roles)) {\r\n        if (this.isTest && roles.length) {\r\n          // Add marker that this node is visible only because we are in test mode.\r\n          const rolesWithoutTest = roles.filter((x) => x.trim().toLowerCase() !== \"test\");\r\n          if (rolesWithoutTest.length == 0 ||\r\n             (rolesWithoutTest.length !== roles.length && !isInSomeRole(rolesWithoutTest))\r\n            ) {\r\n              node.visibleTestOnly = true;\r\n          }\r\n        }\r\n        return true;\r\n      } else {\r\n        return false;\r\n      }\r\n    });\r\n    filteredNodes.forEach((node) => {\r\n      node.children = this.filterSitemapSectionsByRole(node.children, session, appStatus);\r\n    });\r\n    return filteredNodes;\r\n  }\r\n\r\n  private findNode(parent: SitemapNode, path: string): SitemapNode | null {\r\n    if (parent && path) {\r\n      if (this.checkUrl(parent.url, path)) {\r\n        return parent;\r\n      }\r\n      if (parent.children) {\r\n        for (const child of parent.children) {\r\n          const childNode = this.findNode(child, path);\r\n          if (childNode) {\r\n            return childNode;\r\n          }\r\n        }\r\n      }\r\n    }\r\n    return null;\r\n  }\r\n\r\n  private findParentNode(parent: SitemapNode, node: SitemapNode): SitemapNode | null  {\r\n    if (parent.children) {\r\n      for(const child of parent.children) {\r\n        if (child == node) {\r\n          return parent;\r\n        }\r\n        const childParent = this.findParentNode(child, node);\r\n        if (childParent) {\r\n          return childParent;\r\n        }\r\n      }\r\n    }\r\n    return null;\r\n  }\r\n\r\n}\r\n","import { DatelyObject, Employment, EmploymentRelationTaxcard, Employments, Taxcard, TaxCard2019Logic, TaxcardKind, TaxcardListItem, Taxcards, Translations } from \"@salaxy/core\";\r\n\r\nimport { EditDialogResult } from \"./model\";\r\nimport type { EmploymentDetailsTabs } from \"./model\";\r\nimport { UiHelpers } from \"./UiHelpers\";\r\n\r\n/** Extends UiHelpers methods with business logic (typically save, load etc.) */\r\nexport class UiCrudHelpers {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"UiHelpers\", \"Taxcards\", \"Employments\"];\r\n\r\n  /**\r\n   * Creates a new UiCrudHelpers with dependency injection.\r\n   */\r\n  constructor(\r\n    private uiHelpers: UiHelpers,\r\n    private taxcards: Taxcards,\r\n    private employments: Employments\r\n  ) {\r\n  }\r\n\r\n  /**\r\n   * Shows a dialog for editing an existing employment.\r\n   * If user clicks OK, the changes are saved.\r\n   * @param employmentId - Identifier of the Workers employment.\r\n   * @param buttonTypes \"default\" shows standard save button,\r\n   * \"updateCalc\" shows two buttons \"ok\" for full calc update and \"ok-no-rows\" update without touching default rows.\r\n   * @param initialTab - Tab to open.\r\n   * @returns Dialog result. Note that OK result may be either \"ok\" or \"ok-no-rows\".\r\n   * The latter means that for calculation only worker info should be updated, not the default rows.\r\n   */\r\n  public openEditEmploymentDialog(\r\n    employmentId: string,\r\n    buttonTypes: \"default\" | \"updateCalc\",\r\n    initialTab: EmploymentDetailsTabs = null,\r\n  ): Promise<EditDialogResult<Employment>> {\r\n    const loader = this.uiHelpers.showLoading(\"Ladataan työntekijän tietoja...\");\r\n    return this.employments.getSingle(employmentId).then((employment) => {\r\n      loader.dismiss();\r\n      return this.uiHelpers.openEditEmploymentDialog(employment, initialTab, buttonTypes).then((result) => {\r\n        if (result.action === \"ok\" || result.action === \"ok-no-rows\") {\r\n          const loader = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.isSaving\");\r\n          return this.employments.save(result.item).then((savedEmployment) => {\r\n            loader.dismiss();\r\n            result.item = savedEmployment;\r\n            return result;\r\n          });\r\n        } else {\r\n          return result;\r\n        }\r\n      });\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Opens a wizard dialog for creating a new Employment relation and potentially a manual Taxcard.\r\n   * If user commits at the end, the changes are saved to both items.\r\n   * @returns Result only has the Employment item (not taxcard - add if necessary).\r\n   */\r\n  public async createNewEmployment(): Promise<EditDialogResult<Employment>> {\r\n    const innerResult = await this.uiHelpers.openNewEmploymentWizard();\r\n\r\n    const result: EditDialogResult<Employment> = {\r\n      action: innerResult.action,\r\n      hasChanges: innerResult.hasChanges,\r\n      item: undefined,\r\n      logic: innerResult.logic,\r\n      result: innerResult.result,\r\n    };\r\n    if (innerResult.action === \"ok\") {\r\n      const loader = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.isSaving\");\r\n      result.item = await this.employments.save(innerResult.item.employment);\r\n      const personalId = result.item.identity.personalId;\r\n\r\n      switch (result.item.info.taxcard) {\r\n        case EmploymentRelationTaxcard.NoTaxCard:\r\n          // TODO: Should be handled on server-side.\r\n          await this.taxcards.save(TaxCard2019Logic.getBlank(personalId, TaxcardKind.NoTaxCard));\r\n          break;\r\n        case EmploymentRelationTaxcard.Manual: {\r\n          const kind = innerResult.item.taxcard.card.kind;\r\n          if (kind == TaxcardKind.DefaultYearly || kind == TaxcardKind.NoWithholdingHousehold\r\n            || kind == TaxcardKind.Replacement || kind == TaxcardKind.NoTaxCard) {\r\n            await this.taxcards.save(innerResult.item.taxcard);\r\n          }\r\n          break;\r\n        }\r\n        case EmploymentRelationTaxcard.Auto:\r\n          // TODO: May be moved as a separate button in dialog and then assure handled in payment.\r\n          await this.taxcards.setAuto(personalId);\r\n          break;\r\n        case EmploymentRelationTaxcard.TaxAtSource:\r\n        case EmploymentRelationTaxcard.Undefined:\r\n        default:\r\n          // No taxcard defintion OR info set in employment.\r\n          break;\r\n      }\r\n      loader.dismiss();\r\n    }\r\n    return result;\r\n  }\r\n\r\n  /**\r\n   * Shows the add new taxcard dialog.\r\n   * If user commits at the end, the changes are saved and the ite is the stored taxcard from server.\r\n   * @param personalId Worker personal id is required.\r\n   */\r\n  public createNewTaxcard(personalId: string): Promise<EditDialogResult<Taxcard>> {\r\n    return this.uiHelpers.openNewTaxcardDialog(personalId)\r\n      .then((result) => {\r\n        if (result.action === \"ok\") {\r\n          const loader = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.isSaving\");\r\n          return this.taxcards.save(result.item).then((savedTaxcard) => {\r\n            result.item = savedTaxcard;\r\n            loader.dismiss();\r\n            if (!savedTaxcard) {\r\n              this.uiHelpers.showAlert(Translations.get(\"SALAXY.NG1_Services.UiCrudHelpers.taxcards.noTaxcardTitle\"),\r\n                Translations.get(\"SALAXY.NG1_Services.UiCrudHelpers.taxcards.noTaxcardText\"));\r\n            }\r\n            if (savedTaxcard?.incomeLog.find((x) => x.diff && x.diff !== \"default\")) {\r\n              return this.uiHelpers.openEditDialog(\"salaxy-components/modals/worker/taxcard-income-log.html\", savedTaxcard, {}, \"lg\")\r\n                .then((incomeLogResult) => {\r\n                  if (incomeLogResult.action === \"ok\") {\r\n                    const loader = this.uiHelpers.showLoading(\"Tallennetaan laskelmia...\");\r\n                    return this.taxcards.commitDiff(savedTaxcard).then((commitResult) => {\r\n                      loader.dismiss();\r\n                      result.item = commitResult;\r\n                      return result;\r\n                    });\r\n                  } else {\r\n                    return result;\r\n                  }\r\n                });\r\n            }\r\n            return result;\r\n          });\r\n        } else {\r\n          return result;\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Refreshes the automatic taxcard.\r\n   * @param taxcardId Automatic taxcard id to refresh.\r\n   * @param salaryDate Salary date for the taxcard.\r\n   */\r\n  public refreshAutoTaxcard(taxcardId: string, salaryDate?: DatelyObject): Promise<TaxcardListItem[]> {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\", \"Verokorttia tarkistetaan.\");\r\n    return this.taxcards.refreshAuto(taxcardId, salaryDate, true).then((taxcards) => {\r\n      loading.dismiss();\r\n      return taxcards;\r\n    });\r\n  }\r\n}\r\n","import angular from \"angular\";\r\nimport { saveAs } from \"file-saver\";\r\nimport {\r\n  Calculation, CalculationListItem, CalendarEvent, DatasetListItem, DateRange, Employment, EmploymentListItem, EmploymentLogic, EmploymentRelationTaxcard, ExternalDialogData,\r\n  TaxCard2019Logic,\r\n  Taxcard, Translations\r\n} from \"@salaxy/core\";\r\n\r\nimport { EditDialogKnownActions, EditDialogResult, ExternalDialogConfig } from \"./model\";\r\nimport type { EmploymentDetailsTabs } from \"./model\";\r\n\r\nimport { CrudControllerBase } from \"../../controllers/bases/CrudControllerBase\";\r\nimport { SessionService } from \"../SessionService\";\r\n\r\n/**\r\n * Provides misc. user interface helper methods that are related to AngularJS.\r\n * Please note that these methods do NOT connect to API (load/save) to separate UI logic from business logic:\r\n * The business logic is in separate UiCrudHelpers class.\r\n */\r\nexport class UiHelpers {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$uibModal\", \"$location\", \"$rootScope\", \"$window\", \"$timeout\", \"SessionService\", \"$uibModalStack\"];\r\n\r\n  /**\r\n   * Creates a new UiHelpers with dependency injection.\r\n   */\r\n  constructor(\r\n    private $uibModal: angular.ui.bootstrap.IModalService,\r\n    private $location: angular.ILocationService,\r\n    private $rootScope: angular.IRootScopeService,\r\n    private $window: angular.IWindowService,\r\n\r\n    private $timeout: angular.ITimeoutService,\r\n    private sessionService: SessionService,\r\n    private $uibModalStack: angular.ui.bootstrap.IModalStackService,\r\n  ) {\r\n    this.init();\r\n  }\r\n\r\n  /**\r\n   * Shows an edit dialog - typically for a list item, but potentially for some other editable item.\r\n   * Alternatively, you may use showDialog() if you wish to specify your own controller (with more logic)\r\n   * @param templateUrl - Template url.\r\n   * @param item - The item that is being edited. The logic will support change tracking and reset on this item.\r\n   * @param logic - Additional logic: Helper functions, metadata etc. that view can use to contruct the UI.\r\n   * @param size - Optional size parameter: sm, lg, xl or ''. Default is empty string (normal size).\r\n   * @param controller Optional controller for the modal instance.\r\n   * The item and logic are passed to controller with dependency injection name \"EditDialogParameters\".\r\n   * @param options Rarely used dialog options.\r\n   * @param options.template If set, ignores the templateUrl and uses this inline HTML template instead.\r\n   * @returns A promise that resolves to the result from the dialog.\r\n   * @example\r\n   * this.uiHelpers.showDialog(\"salaxy-components/modals/account/AuthorizedAccountAdd.html\", \"AccountAuthorizationController\")\r\n   */\r\n  public openEditDialog<TItem>(templateUrl: string, item: TItem, logic: any, size: \"sm\" | \"lg\" | \"xl\" | \"\" = \"\",\r\n    controller = \"EditDialogController\", options: {\r\n      template?: string,\r\n    } = {},\r\n  )\r\n    : Promise<EditDialogResult<TItem>> {\r\n    const current = angular.copy(item);\r\n    const modalOptions: angular.ui.bootstrap.IModalSettings = {\r\n      backdrop: \"static\",\r\n      ariaLabelledBy: \"modal-title\",\r\n      ariaDescribedBy: \"modal-body\",\r\n      template: options.template,\r\n      templateUrl: options.template ? null : templateUrl,\r\n      windowTemplateUrl: \"salaxy-components/modals/ui/DialogWindow.html\",\r\n      controller,\r\n      controllerAs: \"$ctrl\",\r\n      size,\r\n      resolve: {\r\n        EditDialogParameters: () => {\r\n          return {\r\n            current,\r\n            logic,\r\n          };\r\n        },\r\n        $element: null,\r\n        $attrs: null,\r\n      },\r\n    };\r\n    const modal = this.$uibModal.open(modalOptions);\r\n    return Promise.resolve(modal.result\r\n      .then((modalResult) => {\r\n        const action = (angular.isString(modalResult) ? modalResult : (modalResult || {}).action) || EditDialogKnownActions.Cancel;\r\n        const hasChanges = !angular.equals(current, item);\r\n        if (action !== EditDialogKnownActions.Cancel && hasChanges) {\r\n          angular.copy(current, item);\r\n        }\r\n        const result: EditDialogResult<TItem> = {\r\n          action,\r\n          result: modalResult,\r\n          item,\r\n          logic,\r\n          hasChanges,\r\n        };\r\n        return result;\r\n      })\r\n      .catch(() => {\r\n        const result: EditDialogResult<TItem> = {\r\n          action: EditDialogKnownActions.Cancel,\r\n          result: null,\r\n          item,\r\n          logic,\r\n          hasChanges: false,\r\n        };\r\n        return result;\r\n      }));\r\n  }\r\n\r\n  private externalWindows: {\r\n    [name: string]: {\r\n      win: any,\r\n      url: string,\r\n      listener: (this: Window, ev: {\r\n        /** The object passed from the other window. */\r\n        data: any,\r\n        /** The origin of the window that sent the message at the time postMessage was called. */\r\n        origin: string,\r\n        /** A reference to the window object that sent the message */\r\n        source: MessageEventSource | null,\r\n      }) => any,\r\n    }\r\n  } = {};\r\n\r\n  /**\r\n   * Shows an external dialog that may be in an untrusted domain.\r\n   * Enables cross-site communication using postMessage events.\r\n   * @param name Name of the unique window\r\n   * @param url Url to show in the Window\r\n   * @param item The item that is being edited. The logic will support change tracking and reset on this item.\r\n   * @param config Configuration of the opened window.\r\n   * @param resolver Optional function for checking if the promise is resolved.\r\n   */\r\n  public showExternalDialog<TData>(name: string, url: string, item: TData, config?: ExternalDialogConfig, resolver?: (ev: {\r\n    /** The object passed from the other window. */\r\n    data: ExternalDialogData<TData>,\r\n    /** The origin of the window that sent the message at the time postMessage was called. */\r\n    origin: string,\r\n    /** A reference to the window object that sent the message */\r\n    source: MessageEventSource | null,\r\n  }) => boolean,\r\n  /** Optional callback function to hide any loading indicator shown while opening the external dialog. */\r\n  hideExternalDialogLoader?: () => void\r\n  )\r\n    : Promise<ExternalDialogData<TData> & { event?: any }> {\r\n    const browserWindow = window;\r\n    config = config || {};\r\n\r\n    if (this.externalWindows[name]?.listener) {\r\n      // Cancel the previous promise and unregister event.\r\n      this.externalWindows[name].listener.call(browserWindow, {\r\n        data: {\r\n          action: \"cancel\",\r\n        },\r\n        origin: null,\r\n        source: null,\r\n      });\r\n      browserWindow.removeEventListener(\"message\", this.externalWindows[name].listener);\r\n    }\r\n\r\n    const width = config.width || 600;\r\n    const height = config.height || 700;\r\n    // access to browserWindow.top is blocked if the site is run in an iframe in a cross domain environment\r\n    // have to use current window only\r\n    const y = browserWindow.outerHeight / 2 + browserWindow.screenY - (height / 2);\r\n    const x = browserWindow.outerWidth / 2 + browserWindow.screenX - (width / 2);\r\n    const windowFeatures = `toolbar=no, menubar=no, width=${width}, height=${height}, top=${y}, left=${x}`;\r\n\r\n    const hostUrl = new URL(url);\r\n    const popupBaseUrl = `${hostUrl.protocol}//${hostUrl.host}`;\r\n    url += (url.indexOf(\"?\") > 0 ? \"&\" : \"?\") + \"data=\" + encodeURIComponent(btoa(JSON.stringify(item)));\r\n    if (url.indexOf(\"http\") !== 0) {\r\n      url += \"&access_token=\" + this.sessionService.getCurrentToken();\r\n    }\r\n\r\n    if (!this.externalWindows[name]?.win || this.externalWindows[name].win.closed || this.externalWindows[name].url !== url) {\r\n      // According to best practice in https://developer.mozilla.org/en-US/docs/Web/API/Window/open\r\n      this.externalWindows[name] = {\r\n        url,\r\n        win: window.open(url, name, windowFeatures),\r\n        listener: null,\r\n      };\r\n    }\r\n    // Focus and check if popup blocked\r\n    try {\r\n      this.externalWindows[name].win.focus();\r\n    }\r\n    catch (e) {\r\n      hideExternalDialogLoader?.();\r\n      return this.showAlert(\"Ponnahdusikkuna estetty selaimen asetuksissa\", \"Toiminto edellyttää, että sallit ponnahdusikkunan avattavan osoitteeseen \" + popupBaseUrl + \".\", \"Sulje\").then(() => {\r\n        return Promise.resolve({\r\n          action: \"cancel\",\r\n          hasChanges: false,\r\n          item,\r\n        });\r\n      });\r\n    }\r\n    hideExternalDialogLoader?.();\r\n    return new Promise<ExternalDialogData<TData> & { event: any }>((resolve) => {\r\n      this.externalWindows[name].listener = (ev: {\r\n        /** The object passed from the other window. */\r\n        data: ExternalDialogData<TData>,\r\n        /** The origin of the window that sent the message at the time postMessage was called. */\r\n        origin: string,\r\n        /** A reference to the window object that sent the message */\r\n        source: MessageEventSource | null,\r\n      }) => {\r\n        console.debug(\"Message received\", ev);\r\n        if (!resolver ||\r\n          resolver(ev)) {\r\n          // HACK: Check origin/source.\r\n          const action = ev.data.action || \"cancel\";\r\n          const hasChanges = !angular.equals(ev.data.item, item);\r\n          if (action !== EditDialogKnownActions.Cancel && hasChanges) {\r\n            angular.copy(ev.data.item, item);\r\n          }\r\n\r\n          browserWindow.removeEventListener(\"message\", this.externalWindows[name].listener);\r\n\r\n          resolve({\r\n            action,\r\n            hasChanges,\r\n            item,\r\n            event: ev\r\n          });\r\n        }\r\n      };\r\n      // add the listener for receiving a message from the popup\r\n      browserWindow.addEventListener(\"message\", this.externalWindows[name].listener, { once: !resolver });\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shows a custom dialog using the given controller and templateUrl.\r\n   * Optionally injects the given data into the controller as 'data'.\r\n   * NOTE: There is an alternative - more simple - modal dialog pattern openEditDialog() if you do not need a custom controller or windowTemplateUrl.\r\n   * @param templateUrl - Template url.\r\n   * @param controller  - Controller for the dialog.\r\n   * @param data - Optional data to inject into the controller.\r\n   * @param windowTemplateUrl - Optional template url for the window. Defaults to 'salaxy-components/modals/ui/DialogWindow.html'. If \"none\", no window is used.\r\n   * @param size - Optional size parameter: sm, lg or ''.\r\n   * @param backdrop - Optional. Controls the presence of a backdrop. Allowed value true, false (no backdrop) 'static' (default) backdrop is present but modal window is not closed when clicking outside of the modal window.\r\n   * @returns A promise that resolves to the result from the dialog.\r\n   * @example\r\n   * this.uiHelpers.showDialog(\"salaxy-components/modals/account/AuthorizedAccountAdd.html\", \"AccountAuthorizationController\")\r\n   */\r\n  public showDialog(\r\n    templateUrl: string,\r\n    controller?: string | any,\r\n    data?: any,\r\n    windowTemplateUrl?: string,\r\n    size?: \"sm\" | \"lg\" | \"landscape\" | \"xl\" | \"\",\r\n    backdrop: string | boolean = \"static\",\r\n  ): Promise<any> {\r\n\r\n    const $attrs: any = {};\r\n    if (controller instanceof CrudControllerBase) {\r\n      $attrs.onCreateNew = controller.onCreateNew;\r\n      $attrs.onListSelect = controller.onListSelect;\r\n      $attrs.onDelete = controller.onDelete;\r\n    }\r\n\r\n    const options: angular.ui.bootstrap.IModalSettings = {\r\n      backdrop,\r\n      ariaLabelledBy: \"modal-title\",\r\n      ariaDescribedBy: \"modal-body\",\r\n      templateUrl,\r\n      windowTemplateUrl: windowTemplateUrl || \"salaxy-components/modals/ui/DialogWindow.html\",\r\n      controller: controller || \"ModalGenericDialogController\",\r\n      controllerAs: \"$ctrl\",\r\n      size,\r\n      resolve: {\r\n        data: () => {\r\n          return data;\r\n        },\r\n        $attrs,\r\n      },\r\n    };\r\n    if (options.windowTemplateUrl === \"none\") {\r\n      delete options.windowTemplateUrl;\r\n    }\r\n    const modal = this.$uibModal.open(options);\r\n\r\n    return Promise.resolve(modal.result)\r\n      .then((value) => {\r\n        return value;\r\n      })\r\n      .catch((reason) => {\r\n        if (reason === \"backdrop click\" || reason === \"dismissAll\") {\r\n          return null;\r\n        }\r\n        throw new Error(\"\" + reason);\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Close all existing modals from modal stack\r\n   */\r\n  public dismissAllModals() {\r\n    if (this.$uibModalStack) {\r\n      this.$uibModalStack.dismissAll(\"dismissAll\");\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Shows a customized loading component (spinner) with an optional message.\r\n   * Returns an object with a dismiss function to call for closing the dialog.\r\n   * Note that there is a separate generic directive 'salaxy-loader' for indicating\r\n   * http-traffic.\r\n   * @param heading Translation key for heading text for the loader.\r\n   * Default text is \"SALAXY.UI_Terms.loading\", but you may set this to null for just the spinner.\r\n   * @param text Optional translation key for additional text paragraph describing what is happening.\r\n   * @returns An object with dismiss function to close the dialog.\r\n   * @example\r\n   * ```ts\r\n   * const loader = this.uiHelper.showLoading(\"SALAXY.UI_Terms.isSaving\", \"SALAXY.UI_Terms.pleaseWait\");\r\n   * setTimeout(() => {\r\n   *   loader.dismiss();\r\n   * }, 2000);\r\n   * ```\r\n   */\r\n  public showLoading(heading = \"SALAXY.UI_Terms.loading\", text?: string, staticBackdrop = false): {\r\n    /** Closes the dialog */\r\n    dismiss: () => void,\r\n    /** Changes the heading text after opening */\r\n    setHeading: (heading: string) => void,\r\n    /** Changes the text after opening */\r\n    setText: (text: string) => void,\r\n  } {\r\n    const data = {\r\n      heading,\r\n      text,\r\n    };\r\n    const options: angular.ui.bootstrap.IModalSettings = {\r\n      ariaLabelledBy: \"modal-title\",\r\n      ariaDescribedBy: \"modal-body\",\r\n      templateUrl: \"salaxy-components/modals/ui/Loading.html\",\r\n      controller: \"ModalGenericDialogController\",\r\n      controllerAs: \"$ctrl\",\r\n      windowClass: \"salaxy-component\",\r\n      size: \"sm\",\r\n      resolve: { data },\r\n      backdrop: staticBackdrop ? \"static\" : true\r\n    };\r\n    const modal = this.$uibModal.open(options);\r\n\r\n    // prevent possibly unhandled rejection errors\r\n    modal.result\r\n      .then(() => {\r\n        // do nothing\r\n      })\r\n      .catch(() => {\r\n        // do nothing\r\n      });\r\n\r\n    return {\r\n      dismiss: () => {\r\n        this.$timeout(() => modal.dismiss());\r\n      },\r\n      setHeading: (heading: string) => {\r\n        this.$timeout(() => { data.heading = heading; });\r\n      },\r\n      setText: (text: string) => {\r\n        this.$timeout(() => { data.text = text; });\r\n      },\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Shows a confirm dialog. Like window.confirm() in JavaScript.\r\n   * Returns true if a user clicks OK -button. Otherwise (cancel or close) returns false.\r\n   * @param heading Heading text of the confirm question as translation key.\r\n   * @param text Optional additional text paragraph describing what is happening.\r\n   * @param okText Possibility to override the OK button text. The given text is run through translation.\r\n   * @param cancelText Possibility to override the Cancel button text. The given text is run through translation.\r\n   * @param html Optional HTML content to show in the dialog. If provided, text parameter is ignored.\r\n   * @returns A promise that resolves to true if user clicks OK, otherwise false.\r\n   * @example\r\n   * ```ts\r\n   * this.uiHelpers\r\n   *     .showConfirm(\"SALAXY.UI_Terms.areYouSure\", \"SALAXY.UI_Terms.sureToDeleteRecord\")\r\n   *     .then((result) => { this.uiHelpers.showAlert(\"result\", result); })\r\n   * ```\r\n   */\r\n  public showConfirm(heading: string, text?: string, okText = \"SALAXY.UI_Terms.ok\", cancelText = \"SALAXY.UI_Terms.cancel\", html: string = null): Promise<boolean> {\r\n    const options: angular.ui.bootstrap.IModalSettings = {\r\n      ariaLabelledBy: \"modal-title\",\r\n      ariaDescribedBy: \"modal-body\",\r\n      templateUrl: \"salaxy-components/modals/ui/Confirm.html\",\r\n      windowTemplateUrl: \"salaxy-components/modals/ui/DialogWindow.html\",\r\n      controller: \"ModalGenericDialogController\",\r\n      controllerAs: \"$ctrl\",\r\n      resolve: {\r\n        data: {\r\n          heading,\r\n          text,\r\n          okText,\r\n          cancelText,\r\n          html\r\n        },\r\n      },\r\n    };\r\n    const modal = this.$uibModal.open(options);\r\n    return Promise.resolve(modal.result)\r\n      .then((result) => {\r\n        return result;\r\n      })\r\n      .catch(() => {\r\n        return false;\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Shows a date range dialog that modifies the date range of the given object.\r\n   * @param target Target object, currently both DateRange and Calculation are supported.\r\n   * Please note that the resulting EditDialogResult is always a DateRange though.\r\n   * @param title Title text for the dialog\r\n   * @param okText Possibility to override the button text. The given text is run through translation.\r\n   * @param cancelText Possibility to override the button text. The given text is run through translation.\r\n   * @returns EditDialogResult with the edited DateRange. Note that this is DateRange even if the object to edit is Calculation.\r\n   */\r\n  public showDateRange(target: DateRange | Calculation, title: string, okText = \"SALAXY.UI_Terms.save\", cancelText = \"SALAXY.UI_Terms.cancel\"): Promise<EditDialogResult<DateRange>> {\r\n    let dateRange: DateRange;\r\n    const calc = (target as Calculation).info ? (target as Calculation) : null;\r\n    if (calc) {\r\n      dateRange = {\r\n        start: calc.info.workStartDate,\r\n        end: calc.info.workEndDate,\r\n        daysCount: calc.framework.numberOfDays,\r\n      };\r\n    } else {\r\n      dateRange = target as DateRange;\r\n    }\r\n    return this.openEditDialog(\"salaxy-components/modals/date-range/DateRange.html\", dateRange, {\r\n      title,\r\n      okText,\r\n      cancelText,\r\n    }, \"sm\").then((dialogResult) => {\r\n      if (dialogResult.action === \"ok\" && calc) {\r\n        // If the editable item was DateRange, those changes are already committed.\r\n        calc.info.workStartDate = dialogResult.item.start;\r\n        calc.info.workEndDate = dialogResult.item.end;\r\n        calc.framework.numberOfDays = dialogResult.item.daysCount;\r\n      }\r\n      return dialogResult;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shows an alert dialog. Like window.alert() in JavaScript.\r\n   * @param heading Heading text as translation key\r\n   * @param text Optional additional text paragraph describing what is happening.\r\n   * @param okText Possibility to override the button text. The given text is run through translation.\r\n   * @returns A promise with boolean: True if OK button was clicked, false if the dialog is closed / dismissed in another way.\r\n   * @example this.uiHelpers.showAlert(\"Please note\", \"There is this thing that we want to tell you.\");\r\n   */\r\n  public showAlert(heading: string, text?: string, okText = \"SALAXY.UI_Terms.ok\"): Promise<boolean> {\r\n    const options: angular.ui.bootstrap.IModalSettings = {\r\n      ariaLabelledBy: \"modal-title\",\r\n      ariaDescribedBy: \"modal-body\",\r\n      templateUrl: \"salaxy-components/modals/ui/Alert.html\",\r\n      controller: \"ModalGenericDialogController\",\r\n      controllerAs: \"$ctrl\",\r\n      windowTemplateUrl: \"salaxy-components/modals/ui/DialogWindow.html\",\r\n      resolve: {\r\n        data: {\r\n          heading,\r\n          text,\r\n          okText,\r\n        },\r\n      },\r\n    };\r\n    const modal = this.$uibModal.open(options);\r\n    return Promise.resolve(modal.result)\r\n      .then((result) => {\r\n        return result;\r\n      })\r\n      .catch(() => {\r\n        return false;\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Shows a dialog for editing an existing employment.\r\n   * NOTE: This method does not Save the Worker: The caller must do it separately.\r\n   * @param employment - Worker Employment edited in dialog.\r\n   * @param initialTab - Tab to open.\r\n   * @param buttonTypes \"default\" shows standard save button,\r\n   * \"updateCalc\" shows two buttons \"ok\" for full calc update and \"ok-no-rows\" update without touching default rows.\r\n   * @returns Dialog result. Note that OK result may be either \"ok\" or \"ok-no-rows\".\r\n   * The latter means that for calculation only worker info should be updated, not the default rows.\r\n   */\r\n  public openEditEmploymentDialog(\r\n    employment: Employment,\r\n    initialTab: EmploymentDetailsTabs = null,\r\n    buttonTypes: \"default\" | \"updateCalc\" = \"default\",\r\n  ): Promise<EditDialogResult<Employment>> {\r\n    return this.openEditDialog(\r\n      \"salaxy-components/worker/EmploymentEditModal.html\", employment, {\r\n      initialTab,\r\n      buttonTypes,\r\n      title: Translations.get(\"SALAXY.NG1.WorkerDetailsComponent.workerEdit.title\"),\r\n    }, \"xl\");\r\n  }\r\n\r\n  /**\r\n   * Opens wizard for creating a new employment relation in a modal dialog.\r\n   * NOTE: This method does not Save the Employment relation: The caller must do it separately.\r\n   * @returns Dialog result with the new employment relation data and potential Taxcard (if manual) that should be created.\r\n   * Only create if action is \"ok\".\r\n   */\r\n  public openNewEmploymentWizard(): Promise<EditDialogResult<{\r\n    /** Employment relation that should be created */\r\n    employment: Employment,\r\n    /** Taxcard that should be created (if it should be created). */\r\n    taxcard?: Taxcard,\r\n  }>> {\r\n    const employment = EmploymentLogic.getBlank();\r\n    return this.openEditDialog(\"salaxy-components/worker/EmploymentWizard/index.html\", employment, null, \"lg\", \"EmploymentWizardController\")\r\n      .then((dialogResult) => {\r\n        const employment: Employment = dialogResult.result.employment;\r\n        let taxcard: Taxcard | undefined = undefined;\r\n        if (dialogResult.action == EditDialogKnownActions.Ok && employment.info.taxcard == EmploymentRelationTaxcard.Manual) {\r\n          taxcard = dialogResult.result.taxcard;\r\n        }\r\n        return {\r\n          action: dialogResult.action,\r\n          item: { employment, taxcard },\r\n          hasChanges: true,\r\n          logic: dialogResult.logic,\r\n          result: dialogResult.action = EditDialogKnownActions.Ok ? EditDialogKnownActions.Ok : EditDialogKnownActions.Cancel,\r\n        };\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Opens a new dialog for adding a new taxcard.\r\n   * @param personalId Worker personal id is required.\r\n   */\r\n  public openNewTaxcardDialog(personalId: string): Promise<EditDialogResult<Taxcard>> {\r\n    if (!personalId) {\r\n      throw new Error(\"Personal ID is required.\");\r\n    }\r\n    const item = TaxCard2019Logic.getBlank(personalId);\r\n    return this.openEditDialog(\"salaxy-components/modals/worker/taxcard-new.html\", item, {});\r\n  }\r\n\r\n  /**\r\n   * Opens a dialog for editing a calendar event.\r\n   * @param calEvent The calendar event that should be created / edited.\r\n   * @param title Title for the dialog.\r\n   * @param template Template to use in create / editing.\r\n   * Simplified is designed for adding scheduling to Calculation / Payroll.\r\n   * @returns Standard dialog result for calendar event.\r\n   */\r\n  public openEditCalendarEvent(calEvent: CalendarEvent, title: string, template: \"default\" | \"simplified\" = \"default\"): Promise<EditDialogResult<CalendarEvent>> {\r\n    const okText = \"SALAXY.UI_Terms.save\";\r\n    const cancelText = \"SALAXY.UI_Terms.cancel\";\r\n    const isSimplified = template === \"simplified\";\r\n    return this.openEditDialog(\"salaxy-components/modals/workflow/CalendarEventEdit.html\", calEvent, { title, okText, cancelText, isSimplified }, \"lg\");\r\n  }\r\n\r\n  /**\r\n   * Opens the list of calculations into a dialog window for selecting a set of them.\r\n   * NOTE: If necessary, add functionality to select only one.\r\n   * @param category Either \"paid\": Read-only or \"draft\": Editable or \"shared\": Shared for approval.\r\n   * @param title Title for the dialog.\r\n   */\r\n  public openSelectCalcs(category: \"paid\" | \"draft\" | \"shared\" = \"draft\", title: string = null): Promise<EditDialogResult<CalculationListItem[]>> {\r\n    const calculations: CalculationListItem[] = [];\r\n    title = title || (category === \"paid\" ? \"Valitse maksetut palkat\" : category == \"shared\" ? \"Valitse lähetetyt\":  \"Valitse luonnokset\" );\r\n    return this.openEditDialog(\"salaxy-components/modals/calc/CalcList.html\", calculations, { title, category });\r\n  }\r\n\r\n  /**\r\n   * Opens the list of employment relations into a dialog window for selecting a set of them.\r\n   * @param title Title for the dialog\r\n   * @returns A set of selected item in dialog result.\r\n   */\r\n  public openSelectEmployments(title: string = null): Promise<EditDialogResult<EmploymentListItem[]>> {\r\n    // HACK: The item now binds to old Worker API (that is really Employment based). Change to the latest Employment API.\r\n    const workerList: EmploymentListItem[] = [];\r\n    title = title || \"Valitse työntekijät\";\r\n    return this.openEditDialog(\"salaxy-components/modals/calc/WorkerList.html\", workerList, { title });\r\n  }\r\n\r\n  /**\r\n   * Opens a search list of specified payload and returns one item.\r\n   * @param title Title for the dialog\r\n   * @returns Selected item or null if none was selected\r\n   */\r\n  public openSelect(title: string = null): Promise<DatasetListItem> {\r\n    const workerList: DatasetListItem[] = [];\r\n    title = title || \"Valitse datasetti\";\r\n    return this.openEditDialog(\"salaxy-components/modals/ui/SelectListItem.html\", workerList, { title }).then((result) => {\r\n      if (result.action === EditDialogKnownActions.Ok && result.item.length) {\r\n        return result.item[0];\r\n      } else {\r\n        return null;\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Caches data to controller: This is needed to avoid $digest loops in AngularJS controllers.\r\n   * NOTE: Default data diff method uses angular.equals(), so it will not recognize difference in properties starting with \"$\" - most notably OData options.\r\n   * @param controller Controller that is used for caching. A property $salaxyCache is added for caching if not there already.\r\n   * @param cacheKey Name for the object that is being cached. Must be unique within the controller scope.\r\n   * @param dataMethod Method that gets the data that is being cached.\r\n   * @param dataDiffMethod Optional method that is used for determining whether the data has changed.\r\n   * If not specified, the dataMethod is used for diff. Should be used if dataMethod returns a lot of data or if it is resource intensive.\r\n   */\r\n  public cache<T>(controller: angular.IController, cacheKey: string, dataMethod: () => T, dataDiffMethod?: () => any): T {\r\n    if (!controller.$salaxyCache) {\r\n      controller.$salaxyCache = {} as any;\r\n    }\r\n    const cache = controller.$salaxyCache;\r\n    if (dataDiffMethod) {\r\n      const keyValue = dataDiffMethod();\r\n      if (!cache[cacheKey] || !angular.equals(cache[cacheKey].key, keyValue)) {\r\n        cache[cacheKey] = {\r\n          key: keyValue,\r\n          data: dataMethod(),\r\n        };\r\n      }\r\n      return cache[cacheKey].data;\r\n    } else {\r\n      const data = dataMethod();\r\n      if (!angular.equals(cache[cacheKey], data)) {\r\n        cache[cacheKey] = data;\r\n      }\r\n      return cache[cacheKey];\r\n    }\r\n  }\r\n  /**\r\n   * Download provide file\r\n   * @param file File blob\r\n   * @param fileName downloaded file name\r\n   */\r\n  public downloadFile(file: Blob, fileName: string) {\r\n    saveAs(file, fileName);\r\n  }\r\n\r\n  /**\r\n   * Opens browser internally generated Blob url\r\n   * @param file File blob\r\n   */\r\n  public openFile(file: Blob) {\r\n    this.$window.open(URL.createObjectURL(file), \"_blank\", \"fullscreen=yes\");\r\n  }\r\n\r\n  /**\r\n   * Shows a dialog for running a batch process.\r\n   * @param header Header text for the dialog\r\n   * @param list List of items for the batch process: The method is run to each of these items.\r\n   * @param method Method that is run for each of the items.\r\n   * @param batchParamsTemplateUrl Template for user input of data about the action: The parameters for the batch process.\r\n   * @param data Usecase specific data that is bound in the controller and can be used in the template and method.\r\n   * @param columns Columns shown from the list may be specified here. Leave null for default columns.\r\n   * @param chunkSize Optional chunk size for the batch process. This is used if the method supports arrays.\r\n   * @param autoStart Optional. If true, the batch process starts immediately after the dialog is opened.\r\n   * @param autoClose Optional. If true, the batch process dialog closes automatically after the process is done.\r\n   * @param silent Optional. If autoStart and autoClose are true, the dialog is not shown if the list size is smaller than the chunk size.\r\n   * This Tabulator configuration.\r\n   */\r\n  public showBatchProcessDialog<T>(\r\n    header: string,\r\n    list: T[],\r\n    method: (\r\n      /** Single item or array (for supporting chunks) in the list that is being processed. */\r\n      itemOrArray: T | T[],\r\n      /** Usecase specific data that is bound in the controller and can be used in the template and method.  */\r\n      data: any\r\n    ) => Promise<{ message: string, result: any}[]>,\r\n    batchParamsTemplateUrl = \"salaxy-components/modals/batch/default.html\",\r\n    data?: any,\r\n    columns?: Array<any>,\r\n    chunkSize?: number,\r\n    autoStart?: boolean,\r\n    autoClose?: boolean,\r\n    silent?: boolean\r\n  ) : Promise<({ done: boolean, results: { message: string, result: any}[] })> {\r\n    data = data || {};\r\n    data.dialogHeader = header;\r\n    data.dialogList = list;\r\n    data.gridColumns = columns;\r\n    data.batchMethod = method;\r\n    data.chunkSize = chunkSize;\r\n    data.batchTemplateUrl = batchParamsTemplateUrl;\r\n    data.autoStart = autoStart ?? false;\r\n    data.autoClose = autoClose ?? false;\r\n    data.silent = silent ?? false;\r\n    data.done = false;\r\n\r\n    if (data.autoStart && data.autoClose && data.silent && data.chunkSize && data.dialogList.length <= data.chunkSize) {\r\n      const loader = this.showLoading(header ?? \"SALAXY.UI_Terms.wait\");\r\n      data.dialogList.forEach((itemToProcess) => {\r\n        itemToProcess.processed = \"Processing...\";\r\n      });\r\n      return method(data.dialogList, data).then((results) => {\r\n        let i = 0;\r\n        for (const itemToProcess of data.dialogList) {\r\n          itemToProcess.processed = \"OK \" + (results[i].message);\r\n          itemToProcess.processedResult = { message: results[i].message, result: results[i].result };\r\n          i++;\r\n        }\r\n        loader.dismiss();\r\n        return { done: true, results: data.dialogList.map((item) => item.processedResult ) };\r\n      });\r\n    }\r\n    else\r\n    {\r\n      return this.showDialog(\"salaxy-components/modals/batch/dialog.html\", \"BatchProcessController\", data, null, \"xl\").then(() => {\r\n        if (data.done) {\r\n          return { done: true, results: data.dialogList.map((item) => item.processedResult ) };\r\n        }\r\n        else\r\n        {\r\n          return { done: false, results: [] };\r\n        }\r\n      });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Converts bytes to blob.\r\n   * @param bytes Bytes encoded in base64.\r\n   * @param mimeType Mime type for the blob.\r\n   */\r\n  public bytes2Blob(bytes: string, mimeType: string): Blob {\r\n    const byteArray = Uint8Array.from(\r\n      atob(bytes)\r\n        .split(\"\") // to char array\r\n        .map((char) => char.charCodeAt(0))\r\n    );\r\n    return new Blob([byteArray], { type: mimeType });\r\n  }\r\n\r\n  /**\r\n   * Waits for a specified delay before resolving the promise.\r\n   * Can be used with index related issues.\r\n   */\r\n  public wait(delay = 3000): Promise<void> {\r\n    return new Promise(resolve => this.$timeout(() => resolve(), delay));\r\n  }\r\n\r\n  /**\r\n   * Shows a dialog based on returnUrl parameter from the current url.\r\n   */\r\n  private showReturnUrlDialog() {\r\n    const returnUrlParameters = this.getReturnUrlParameters();\r\n    if (returnUrlParameters) {\r\n      if (returnUrlParameters.returnUrl &&\r\n        (returnUrlParameters.returnUrl.toLowerCase().startsWith(\"http:\") ||\r\n          returnUrlParameters.returnUrl.toLowerCase().startsWith(\"https:\")\r\n        )) {\r\n        this.showDialog(\r\n          \"salaxy-components/modals/\" + returnUrlParameters.componentTemplate + \".html\",\r\n          null).then(() => {\r\n            this.$window.location.assign(returnUrlParameters.returnUrl);\r\n          });\r\n        this.$rootScope.$evalAsync(() => {\r\n          this.$location.url(\"/\");\r\n        });\r\n      } else {\r\n        this.showDialog(\r\n          \"salaxy-components/modals/\" + returnUrlParameters.componentTemplate + \".html\",\r\n          null);\r\n        // async redirect immediately with dialog\r\n        this.$rootScope.$evalAsync(() => {\r\n          this.$location.url(returnUrlParameters.returnUrl);\r\n        });\r\n      }\r\n    }\r\n  }\r\n\r\n  private getReturnUrlParameters() {\r\n    const url = this.$location.url();\r\n    if (url.indexOf(\"/dialog/\") !== 0) {\r\n      return null;\r\n    }\r\n    const dialog = url.substring(\"/dialog/\".length, url.indexOf(\"?\"));\r\n    const returnUrl = this.$location.search().returnUrl;\r\n    return {\r\n      componentTemplate: dialog,\r\n      returnUrl,\r\n    };\r\n  }\r\n\r\n  private init() {\r\n    this.$rootScope.$on(\"$locationChangeStart\", () => {\r\n      this.showReturnUrlDialog();\r\n    });\r\n  }\r\n}","import angular from \"angular\";\r\n\r\nimport { Numeric } from \"@salaxy/core\";\r\n\r\n/**\r\n * Defines a step in wizard\r\n */\r\nexport interface WizardStep {\r\n  /** A number for the step, typically set by the counter */\r\n  number?: number;\r\n\r\n  /** Short title that is displayed with the Wizard buttons */\r\n  title: string;\r\n\r\n  /** If true, the step is active/selected. Typically, there is only one step active at any given time. */\r\n  active?: boolean;\r\n\r\n  /** If true, the step cannot be clicked/activated */\r\n  disabled?: boolean;\r\n\r\n  /** Path to the view that is shown in the wizard */\r\n  view?: string;\r\n\r\n  /** Path to the buttons view that is shown in the footer of the wizard */\r\n  buttonsView?: string;\r\n\r\n  /** Heading for the step */\r\n  heading?: string;\r\n\r\n  /** Intro text at the top of the wizard */\r\n  intro?: string;\r\n}\r\n\r\n/**\r\n * Manages the state and pages of a Wizard that potentially has multiple\r\n * controllers views etc. in it.\r\n */\r\nexport class WizardService {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$rootScope\"];\r\n\r\n  private steps: WizardStep[] = [];\r\n  private activeStep: number = null;\r\n\r\n  /**\r\n   * Creates a new instance of WizardService\r\n   * @param $rootScope - Angular root scope. Used for event routing\r\n   */\r\n  constructor(private $rootScope: angular.IRootScopeService, newSteps: WizardStep[]) {\r\n    this.setSteps(newSteps, true);\r\n  }\r\n\r\n  /** Gets the Wizard steps as collection */\r\n  public getSteps(): WizardStep[] {\r\n    return this.steps;\r\n  }\r\n\r\n  /**\r\n   * Sets the Wizard steps\r\n   * @param newSteps - the new collection of steps for the wizard.\r\n   * @param skipNotify - If true will not send the the Notify event to Subscribed controllers.\r\n   */\r\n  public setSteps(newSteps: WizardStep[] = [], skipNotify = false): void {\r\n    if (angular.equals(newSteps, this.steps)) {\r\n      return;\r\n    }\r\n    for (let n = 0; n < newSteps.length; n++) {\r\n      if (!Numeric.isNumber(newSteps[n].number)) {\r\n        newSteps[n].number = n + 1;\r\n      }\r\n    }\r\n    this.steps = newSteps;\r\n    this.activeStep = newSteps.length > 0 ? 1 : 0;\r\n    if (!skipNotify) {\r\n      this.notify();\r\n    }\r\n  }\r\n\r\n  /** Gets the number of the currently active step */\r\n  public get activeStepNumber() {\r\n    return this.activeStep;\r\n  }\r\n  /** Sets the number of the currently active step */\r\n  public set activeStepNumber(stepNumber: number) {\r\n    for (const step of this.steps) {\r\n      step.active = false;\r\n    }\r\n    this.steps[stepNumber - 1].active = true;\r\n    this.activeStep = stepNumber;\r\n    this.notify();\r\n  }\r\n\r\n  /**\r\n   * Gets the current step object\r\n   */\r\n  public getCurrentStepObject(): WizardStep {\r\n    return this.activeStep ? this.steps[this.activeStep - 1] : null;\r\n  }\r\n\r\n  /**\r\n   * Controllers can subscribe to changes in service data using this method.\r\n   * Read more about the pattern in: http://www.codelord.net/2015/05/04/angularjs-notifying-about-changes-from-services-to-controllers/\r\n   * @param scope - Controller scope for the subscribing controller (or directive etc.)\r\n   * @param callback - The event listener function. See $on documentation for details\r\n   */\r\n  public subscribe(scope: angular.IScope, callback: (event: angular.IAngularEvent, ...args: any[]) => any): void {\r\n    const handler = this.$rootScope.$on(\"wizard-service-event\", callback);\r\n    scope.$on(\"$destroy\", handler);\r\n  }\r\n\r\n  private notify(): void {\r\n    this.$rootScope.$emit(\"wizard-service-event\");\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { CrudApiBase } from \"@salaxy/core\";\r\n\r\nimport { IService } from \"./IService\";\r\nimport { SessionService } from \"./SessionService\";\r\n\r\n/**\r\n * Legacy service model: Stores the edited items in browser session context.\r\n * Most new implementations should use the new API CRUD model instead.\r\n * However, this service model may still be the right choice in certain circumstances where the editable data should be\r\n * cached or is already in session (like account data).\r\n */\r\nexport abstract class BaseService<T> implements IService<T> {\r\n\r\n    /**\r\n     * List of items loaded to the service.\r\n     * Empty list if items are still been loaded.\r\n     */\r\n    public list: T[] = [];\r\n\r\n    /** Currently selected item. */\r\n    public current: T = null;\r\n\r\n    /** Set to true when the initial data hase been loaded from the server (not the anonymous dummy data). */\r\n    public isInitialDataLoaded: boolean;\r\n\r\n    /** Intial data owner */\r\n    private initialOwner: string;\r\n\r\n    /**\r\n     * String that identifies the service event (onChange/notify).\r\n     * Must be unique for the service class.\r\n     */\r\n    protected abstract eventPrefix;\r\n\r\n    constructor(\r\n        private $rootScope: angular.IRootScopeService,\r\n        protected sessionService: SessionService,\r\n\r\n        private api: CrudApiBase<T, never>,\r\n    ) {\r\n      this.init();\r\n\r\n      sessionService.subscribe($rootScope, () => {\r\n        this.init();\r\n      });\r\n    }\r\n\r\n    /**\r\n     * Gets all items from the service's base URL endpoint.\r\n     * Makes a GET request to the API base URL using the configured Ajax instance.\r\n     * @returns A Promise that resolves to an array of items of type T.\r\n     */\r\n    public getAll(): Promise<T[]> {\r\n      const baseUrl = this.api.getBaseUrl();\r\n      return this.api.getAjax().getJSON(baseUrl);\r\n    }\r\n\r\n    /**\r\n     * Reloads the list from the server - called in init and e.g. after Delete and Add new\r\n     * @returns A Promise with result data\r\n     */\r\n    public reloadList(): Promise<T[]> {\r\n        return this.getAll().then((result) => {\r\n          this.list = result;\r\n          this.isInitialDataLoaded = true;\r\n          this.notify();\r\n          return this.list;\r\n        });\r\n    }\r\n\r\n    /**\r\n     * Client-side (synchronous) method for getting a new blank item as bases for UI binding.\r\n     * @returns A Blank item with default values.\r\n     */\r\n    public getBlank(): T {\r\n        return this.api.getBlank();\r\n    }\r\n\r\n    /**\r\n     * Get the identifier of the current item, null if none is selected.\r\n     * @returns The identifier of current item, or null if not set\r\n     */\r\n    public getCurrentId(): string | null {\r\n        // TODO: Consider typing T either as IIdentifiable or IApiCrudObject\r\n        return this.current ? (this.current as any).id : null;\r\n    }\r\n\r\n    /**\r\n     * Set the current item by id.\r\n     * If id parameter is \"new\", the item is set to a new blank item.\r\n     * If id paramter is null, the current item is set to null.\r\n     * @param id - The Identifier for the item to set as current\r\n     */\r\n    public setCurrentId(id: \"new\" | string): void {\r\n        if (!id) {\r\n            this.setCurrent(null);\r\n            return;\r\n        }\r\n        if (id === \"new\") {\r\n          this.newCurrent();\r\n          return;\r\n        }\r\n        if (id != null && this.list.length > 0) {\r\n            const matches = this.list.filter((x) => (x as any).id === id);\r\n            if (matches.length > 0) {\r\n                this.setCurrent(matches[0]);\r\n            } else {\r\n                throw Error(`Item ${id} could not be set as current.`);\r\n            }\r\n        }\r\n    }\r\n\r\n    /**\r\n     * Set the current item to given item\r\n     * @param item - The item to set as current\r\n     */\r\n    public setCurrent(item: T): void {\r\n        this.current = item;\r\n        this.notify();\r\n    }\r\n\r\n    /**\r\n     * Sets the current item to a new blank item.\r\n     */\r\n    public newCurrent(): void {\r\n        this.setCurrent(this.getBlank());\r\n    }\r\n\r\n    /**\r\n     * Saves the current item to database.\r\n     * @returns A Promise with result data: The current object after round-trip to server.\r\n     */\r\n    public saveCurrent(): Promise<T> {\r\n        if (this.current) {\r\n            return this.save(this.current);\r\n        } else {\r\n            throw new Error(\"SaveCurrent called when current is not set.\");\r\n        }\r\n    }\r\n\r\n    /**\r\n     * Saves the given item to database.\r\n     * @param item - Item to be saved\r\n     * @returns A Promise with the item after the round-trip to server.\r\n     */\r\n    public save(item: T): Promise<T> {\r\n        return this.api.save(item).then((result) => {\r\n            this.setCurrent(result);\r\n            return this.reloadList().then(() => {\r\n                return result;\r\n            });\r\n        });\r\n    }\r\n\r\n    /**\r\n     * Deletes the specified item.\r\n     * @param id - The identifier for the item to be deleted\r\n     * @returns A Promise with result data (\"Object deleted\")\r\n     */\r\n    public delete(id: string): Promise<string> {\r\n        return this.api.delete(id).then((result) => {\r\n            return this.reloadList().then(() => {\r\n                return result;\r\n            });\r\n        });\r\n    }\r\n\r\n    /**\r\n     * Creates a copy of a given item.\r\n     * This method does not yet set the item as current.\r\n     * @param copySource Item to copy as new.\r\n     */\r\n    public copyAsNew(copySource: T): T {\r\n        const copy = JSON.parse(JSON.stringify(copySource)) as T;\r\n        (copy as any).id = null;\r\n        return copy;\r\n    }\r\n\r\n    /**\r\n     * INTERNAL ONLY: This functionality is under consideration.\r\n     * We may not support it in the future and we may remove it without it being a breaking change.\r\n     *\r\n     * Controllers can subscribe to changes in service data using this method.\r\n     * Read more about the pattern in: http://www.codelord.net/2015/05/04/angularjs-notifying-about-changes-from-services-to-controllers/\r\n     * @param scope - Controller scope for the subscribing controller (or directive etc.)\r\n     * @param callback - The event listener function. See $on documentation for details\r\n     * @ignore\r\n     */\r\n    public onChange(scope: angular.IScope, callback: (event: angular.IAngularEvent, ...args: any[]) => any): void {\r\n        const handler = this.$rootScope.$on(this.eventPrefix + \"-service-event\", callback);\r\n        scope.$on(\"$destroy\", handler);\r\n    }\r\n\r\n    /** INTERNAL ONLY: Emits the service event (typically list reload). This functionality may be dropped in future versions without warning. */\r\n    protected notify(): void {\r\n        this.$rootScope.$emit(this.eventPrefix + \"-service-event\");\r\n    }\r\n\r\n    private init() {\r\n      if (this.sessionService.isSessionChecked && this.sessionService.isAuthenticated) {\r\n        const owner = this.sessionService.session.currentAccount.owner;\r\n        if (this.initialOwner != owner){\r\n          this.list = [];\r\n          this.isInitialDataLoaded = false;\r\n          this.initialOwner = owner;\r\n          this.reloadList();\r\n        }\r\n      } else {\r\n        this.current = null;\r\n        this.list = [];\r\n        this.isInitialDataLoaded = false;\r\n        this.initialOwner = null;\r\n      }\r\n    }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { AuthorizedAccounts, AuthorizedAvatar, CompanyAccount, PersonAccount, Translations, Configs } from \"@salaxy/core\";\r\n\r\nimport { BaseService } from \"./BaseService\";\r\nimport { SessionService } from \"./SessionService\";\r\n\r\n/** TODO: Move the data model and data to server-side. */\r\ntype Partner = {\r\n  /** Name of the partner service */\r\n  title?: string,\r\n  /** Unique identifier */\r\n  id: string,\r\n  /** Palkkaus.fi account ID (IBAN) that is authorized. */\r\n  accountId: string,\r\n  /** Square logo image */\r\n  img: string,\r\n  /** Status text: Short description */\r\n  status?: string,\r\n  /** If true, the integration is enabled. */\r\n  enabled?: boolean,\r\n};\r\n\r\n/**\r\n * CRUD functionality for the authorized accounts.\r\n * Additionally listing of authorizing accounts.\r\n */\r\nexport class AuthorizedAccountService extends BaseService<AuthorizedAvatar> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$rootScope\", \"SessionService\", \"AuthorizedAccounts\"];\r\n\r\n  /**\r\n   * String that identifies the service event (onChange/notify).\r\n   * Must be unique for the service class.\r\n   */\r\n  protected eventPrefix = \"authorizedAccount\";\r\n\r\n  private authorizingAccounts: (PersonAccount | CompanyAccount)[] = [];\r\n\r\n  /** Intial data owner */\r\n  private initialAuthorizingAccountsOwner: string;\r\n\r\n  private currentPartnerSite: any;\r\n\r\n  /**\r\n   * List of Software/Integration partner sites\r\n   */\r\n  private partnerIntegrationSiteList: Partner[] = [\r\n    {\r\n      id: \"askelma\",\r\n      accountId: \"FI14POYA0028382282\",\r\n      img: \"https://cdn.salaxy.com/img/salaxy/customer/askelma/logo.png\",\r\n    },\r\n    {\r\n      id: \"easoft\",\r\n      accountId: \"FI11POY10030958375\",\r\n      img: \"https://cdn.salaxy.com/img/salaxy/customer/easoft/logo.png\",\r\n    },\r\n    {\r\n      id: \"domus\",\r\n      accountId: \"FI23POY10006460809\",\r\n      img: \"https://cdn.salaxy.com/img/salaxy/customer/domus/logo.png\",\r\n    },\r\n    {\r\n      id: \"holvi\",\r\n      accountId: \"FI24POYH0021937564\",\r\n      img: \"https://cdn.salaxy.com/img/salaxy/customer/holvi/logo.png\",\r\n    },\r\n    {\r\n      id: \"isolta\",\r\n      accountId: \"FI24POYI0018540478\",\r\n      img: \"https://cdn.salaxy.com/img/salaxy/customer/isolta/logo.svg\",\r\n    },\r\n    {\r\n      id: \"finago\",\r\n      accountId: \"FI15POYA0008369224\",\r\n      img: \"https://cdn.salaxy.com/img/salaxy/customer/finago-solo/logo.png\",\r\n    },\r\n    {\r\n      id: \"accountor\",\r\n      accountId: \"FI03POYA0003689675\",\r\n      img: \"https://cdn.salaxy.com/img/salaxy/customer/accountor-go/logo.png\",\r\n    },\r\n    {\r\n      id: \"briox\",\r\n      accountId: \"FI33POYB0024403824\",\r\n      img: \"https://cdn.salaxy.com/img/salaxy/customer/briox/logo.png\",\r\n    },\r\n    {\r\n      id: \"nocfo\",\r\n      accountId: \"FI45POYN0031497697\",\r\n      img: \"https://cdn.salaxy.com/img/salaxy/customer/nocfo/logo.png\",\r\n    },\r\n    {\r\n      id: \"passeliMerit\",\r\n      accountId: \"FI43POY10010435606\",\r\n      img: \"https://cdn.salaxy.com/img/salaxy/customer/passelimerit/logo.png\",\r\n    },\r\n    {\r\n      id: \"ecom\",\r\n      accountId: Configs.current?.isTestData === true ? \"FI11POYE0009680831\" : \"FI44POY10009680831\",\r\n      img: \"https://cdn.salaxy.com/img/salaxy/customer/ecom/logo.png\",\r\n    }\r\n  ];\r\n\r\n  constructor(\r\n    $rootScope: angular.IRootScopeService,\r\n    sessionService: SessionService,\r\n    private authorizedAccountsApi: AuthorizedAccounts,\r\n  ) {\r\n    super($rootScope, sessionService, authorizedAccountsApi);\r\n\r\n    this.refreshAuthorizingAccounts();\r\n\r\n    sessionService.subscribe($rootScope, () => {\r\n      this.refreshAuthorizingAccounts();\r\n    });\r\n\r\n    this.partnerIntegrationSiteList.forEach((x) => {\r\n      x.title = Translations.get(`SALAXY.NG1_Services.AuthorizedAccountService.partnerIntegrationSiteList.${x.id}.title`);\r\n      x.status = Translations.get(`SALAXY.NG1_Services.AuthorizedAccountService.partnerIntegrationSiteList.${x.id}.description`);\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Refreshes existing authorizing accounts.\r\n   * @returns A Promise with result data (PersonAccount|CompanyAccount)[]\r\n   */\r\n  public reloadAuthorizingAccounts(): Promise<(PersonAccount | CompanyAccount)[]> {\r\n    return this.authorizedAccountsApi.getAuthorizingAccounts().then((data) => this.authorizingAccounts = data);\r\n  }\r\n\r\n  /**\r\n   * Lists all accounts on behalf of which this account has been authorized to act.\r\n   * @returns A Promise with result data (PersonAccount|CompanyAccount)[]\r\n   */\r\n  public getAuthorizingAccounts(): (PersonAccount | CompanyAccount)[] {\r\n    return this.authorizingAccounts;\r\n  }\r\n\r\n  /**\r\n   * Sets the current partner site\r\n   * @param partnerSite A partner site to be set as current\r\n   */\r\n  public setCurrentPartnerSite(partnerSite: any): void {\r\n    this.currentPartnerSite = partnerSite;\r\n  }\r\n\r\n  /**\r\n   * Returns the current partner site\r\n   */\r\n  public getCurrentPartnerSite(): any {\r\n    return this.currentPartnerSite;\r\n  }\r\n\r\n  /**\r\n   * Return a list of all possible Integration partner sites\r\n   *\r\n   * Partner sites are services that have Salaxy or Palkkaus functionality in them. Others are services that have a different sign-in method,\r\n   * and these services need an authorization to access user's Salaxy/Palkkaus account. Others use the Salaxy/Palkkaus sign-in method, so they don't\r\n   * need separate authorization. Due to some services needing an authorization and others not needing it, all partner services need to be stored in a\r\n   * separate property, simply listing authorizations does not suffice.\r\n   *\r\n   * Partner services that need an authorization have a property accountId, that is the IBAN for their Salaxy acccount\r\n   * @returns List of partner site objects.\r\n   */\r\n  public getPartnerIntegrationSiteList(): any {\r\n    this.partnerIntegrationSiteList.forEach((x) => x.enabled = !!this.list.find((y) => y.id === x.accountId));\r\n    return this.partnerIntegrationSiteList;\r\n  }\r\n\r\n  /**\r\n   * Returns the partner site with given id\r\n   * @param id The name of the partner site\r\n   * @returns Partner site object with the given id, or undefined.\r\n   */\r\n  public getPartnerSite(id): any {\r\n    const sites = this.getPartnerIntegrationSiteList().filter((x) => x.id === id);\r\n    return sites.length > 0 ? sites[0] : null;\r\n  }\r\n\r\n  private refreshAuthorizingAccounts() {\r\n    if (this.sessionService.isSessionChecked && this.sessionService.isAuthenticated) {\r\n      const owner = this.sessionService.session.currentAccount.owner;\r\n      if (this.initialAuthorizingAccountsOwner != owner){\r\n        this.authorizingAccounts = [];\r\n        this.initialAuthorizingAccountsOwner = owner;\r\n        this.reloadAuthorizingAccounts();\r\n      }\r\n    } else {\r\n      this.authorizingAccounts = [];\r\n      this.initialAuthorizingAccountsOwner = null;\r\n    }\r\n  }\r\n}\r\n","/** Provides a way to cache lists and items to centralized cache. */\r\nexport class CacheService {\r\n  /** The raw cache array */\r\n  private rawCache: { [key: string]: {\r\n    /**\r\n     * URL that was called to fetch the cache.\r\n     * Technically, this can be any string that just determines whether the URL / query has changed.\r\n     */\r\n    url: string,\r\n\r\n    /** The payload for the cache. */\r\n    data: any,\r\n\r\n    /**\r\n     * Time when the cache expires.\r\n     * This is time in milliseconds, i.e. Date().getTime().\r\n     */\r\n    validMs: number,\r\n  }; } = {};\r\n\r\n  /** Return true if the given item is in the cache. */\r\n  public hasData(key: string, url: string): boolean {\r\n    if (!key) {\r\n      return false;\r\n    }\r\n    const cacheItem = this.rawCache[key];\r\n    if (!cacheItem) {\r\n      return false;\r\n    }\r\n    if (cacheItem.validMs < + new Date().getTime()) {\r\n      this.clear(key);\r\n      return false;\r\n    }\r\n    return cacheItem.url === url;\r\n  }\r\n\r\n  /** Returns the data if exists / is valid. */\r\n  public getData(key: string, url: string): any {\r\n    if (!key) {\r\n      return null;\r\n    }\r\n    if (this.hasData(key, url)) {\r\n      return this.rawCache[key].data;\r\n    }\r\n  }\r\n\r\n  /** Returns the full cache data based on key without any validation. */\r\n  public getFullCache(key: string) {\r\n    if (!key) {\r\n      return null;\r\n    }\r\n    return this.rawCache[key] || {\r\n      data: null,\r\n      key,\r\n      url: null,\r\n      validMs: null,\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Sets the new data to the cache.\r\n   * @param key The cache key. Defining the instance where the cache is being used.\r\n   * If null, does nothing.\r\n   * @param url URL that was called to fetch the cache.\r\n   * Technically, this can be any string that just determines whether the URL / query has changed.\r\n   * @param data Data that is cached\r\n   * @param expiresSeconds Time to live for the data in seconds starting from the current time.\r\n   */\r\n  public setData(key: string, url: string, data: any, expiresSeconds: number): void {\r\n    if (!key) {\r\n      return null;\r\n    }\r\n    data.$loaded = new Date().getTime();\r\n    this.rawCache[key] = {\r\n      data,\r\n      url,\r\n      validMs: new Date().getTime() + (expiresSeconds * 1000),\r\n    };\r\n  }\r\n\r\n  /** Clears the entire cache - all keys. */\r\n  public clearAllKeys() {\r\n    this.rawCache = {};\r\n  }\r\n\r\n  /** Clears a given cache key */\r\n  public clear(key: string) {\r\n    if (!key) {\r\n      return;\r\n    }\r\n    this.rawCache[key] = null;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Certificate, Certificates } from \"@salaxy/core\";\r\n\r\nimport { BaseService } from \"./BaseService\";\r\nimport { SessionService } from \"./SessionService\";\r\n\r\n/**\r\n * CRUD functionality for the Payroll objects and functionality for payroll in general.\r\n */\r\nexport class CertificateService extends BaseService<Certificate> {\r\n\r\n    /**\r\n     * For NG-dependency injection\r\n     * @ignore\r\n     */\r\n    public static $inject = [\"$rootScope\", \"SessionService\", \"Certificates\"];\r\n\r\n    /**\r\n     * String that identifies the service event (onChange/notify).\r\n     * Must be unique for the service class.\r\n     */\r\n    protected eventPrefix = \"certificate\";\r\n\r\n    constructor(\r\n        $rootScope: angular.IRootScopeService,\r\n        sessionService: SessionService,\r\n        private certificateApi: Certificates,\r\n    ) {\r\n        super($rootScope, sessionService, certificateApi);\r\n    }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Credentials, SessionUserCredential } from \"@salaxy/core\";\r\n\r\nimport { BaseService } from \"./BaseService\";\r\nimport { SessionService } from \"./SessionService\";\r\n\r\n/**\r\n * CRUD functionality for the Credentials objects and functionality for Credentials in general.\r\n */\r\nexport class CredentialService extends BaseService<SessionUserCredential> {\r\n\r\n    /**\r\n     * For NG-dependency injection\r\n     * @ignore\r\n     */\r\n    public static $inject = [\"$rootScope\", \"SessionService\", \"Credentials\"];\r\n\r\n    /**\r\n     * String that identifies the service event (onChange/notify).\r\n     * Must be unique for the service class.\r\n     */\r\n    protected eventPrefix = \"certificate\";\r\n\r\n    constructor(\r\n        $rootScope: angular.IRootScopeService,\r\n        sessionService: SessionService,\r\n        private credentialsApi: Credentials,\r\n    ) {\r\n        super($rootScope, sessionService, credentialsApi);\r\n    }\r\n\r\n    /**\r\n     * Returns the url for uploading the avatar image file to the database\r\n     * @returns Id of the credential\r\n     */\r\n    public getAvatarUploadUrl(credentialId): string {\r\n      return this.credentialsApi.getAvatarUploadUrl(credentialId);\r\n  }\r\n}\r\n","import { Arrays, Calculation, CalculatorLogic, Numeric, Payroll03Info, PayrollDetails, Payrolls } from \"@salaxy/core\";\r\n\r\n/**\r\n * Payroll logic that is independent from UI log (AngularJS).\r\n * TODO: Move to @salaxy/core\r\n */\r\nexport class PayrollLogic {\r\n\r\n  /**\r\n   * Gets the Payroll03Info object based on current data (without going to server).\r\n   * @param payroll Payroll object, where info may be outdated.\r\n   * @param calcs Calculations that may be loaded from the server.\r\n   */\r\n  public static getInfo(payroll: PayrollDetails, calcs: Calculation[]): Payroll03Info {\r\n    if (!payroll) {\r\n      return new Payrolls(null).getBlank().info;\r\n    }\r\n    if (!calcs || calcs.length === 0) {\r\n      return payroll.info;\r\n    }\r\n    return {\r\n      calcCount: calcs.length, // Should this be input.calcs.length? Probably does not really matter.\r\n      fees: Arrays.sum(calcs, (x) => x.result.employerCalc.palkkaus),\r\n      totalGrossSalary: Arrays.sum(calcs, (x) => Numeric.round(x.result.totals.totalGrossSalary)),\r\n      totalPayment: Arrays.sum(calcs, (x) => Numeric.round(x.result.employerCalc.totalPayment)),\r\n      // We could potentially do some client-side validation here, but it may not make sense: Real validation is on the server.\r\n      isReadyForPayment: payroll.info.isReadyForPayment,\r\n      // Not updated by this logic:\r\n      date: payroll.info.date,\r\n      salaryDate: payroll.info.salaryDate,\r\n      paymentDate: payroll.info.paymentDate,\r\n      paymentId: payroll.info.paymentId,\r\n      status: payroll.info.status,\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Returns true if there is no net salary payment to worker at all.\r\n   * @param calcs - Calculation objects\r\n   */\r\n  public static isZeroPayment(calcs: Calculation[]): boolean {\r\n    if (!calcs || !calcs.length) {\r\n      return false;\r\n    }\r\n    return calcs.every((x) => CalculatorLogic.isZeroPayment(x));\r\n  }\r\n}\r\n","import {\r\n  Ajax, Avatar, Calculation, CalculationCollection, CalculationResultLogic, Calculations, CalculationStatus, CalculatorLogic,\r\n  Dates, InputEnumOption, ExternalDialogData, Invoice, InvoicePreview, Invoices, InvoiceStatus, InvoicesLogic, InvoiceType, LegalEntityType, Numeric,\r\n  PaymentChannel, PayrollDetails, PayrollStatus, Translations, SalaryDateLogic, InvoiceListItem, SalaryDateKind, Payrolls4, Configs\r\n} from \"@salaxy/core\";\r\nimport angular from \"angular\";\r\n\r\nimport { SessionService } from \"./SessionService\";\r\nimport { SettingsService } from \"./SettingsService\";\r\nimport { OnboardingService } from \"./OnboardingService\";\r\nimport { PayrollLogic } from \"../controllers/calc/PayrollLogic\";\r\nimport { EditDialogKnownActions, UiHelpers } from \"./ui\";\r\n\r\n/** Implements the user interface logic for new Invoices: Salary and side-cost payments. */\r\nexport class InvoicesService {\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Invoices\", \"SessionService\", \"UiHelpers\", \"SettingsService\", \"AjaxNg1\", \"$location\", \"$timeout\", \"Calculations\", \"OnboardingService\"];\r\n\r\n  private _defaultSepaChannel: PaymentChannel = PaymentChannel.PalkkausManual;\r\n\r\n  private _defaultPaymentListChannel: PaymentChannel = PaymentChannel.PalkkausWS;\r\n\r\n  constructor(\r\n    private invoicesApi: Invoices,\r\n    private sessionService: SessionService,\r\n    private uiHelpers: UiHelpers,\r\n    private settingsService: SettingsService,\r\n    private ajax: Ajax,\r\n    private $location: angular.ILocationService,\r\n    private $timeout: angular.ITimeoutService,\r\n    private calculations: Calculations,\r\n    private onboardingService: OnboardingService,\r\n\r\n  ) {\r\n  }\r\n\r\n  /** Gets the default SEPA payment channel. */\r\n  public get defaultSepaChannel(): PaymentChannel {\r\n    return this._defaultSepaChannel;\r\n  }\r\n\r\n  public set defaultSepaChannel(value: PaymentChannel) {\r\n    this._defaultSepaChannel = value;\r\n  }\r\n\r\n  /** Gets the default payment channel. */\r\n  public get defaultPaymentListChannel(): PaymentChannel {\r\n    return this._defaultPaymentListChannel;\r\n  }\r\n\r\n  public set defaultPaymentListChannel(value: PaymentChannel) {\r\n    this._defaultPaymentListChannel = value;\r\n  }\r\n\r\n  /**\r\n   * Application level setting of the default payment channel.\r\n   */\r\n  public get defaultChannel(): PaymentChannel {\r\n    if (this.channels) {\r\n      const defaultChannel = this.sessionService.getSession().settings.defaultPaymentChannel;\r\n      const confirmedChannel = this.channels.filter(x => x.id === defaultChannel).concat(this.channels).find(() => true)?.id as PaymentChannel;\r\n      return confirmedChannel;\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /**\r\n   * Gets the enabled payment channels as avatars for the current session.\r\n   */\r\n  public get channels(): Avatar[] {\r\n    const channelsForRole = () => this.sessionService.getSession().settings?.paymentChannels.filter((x) =>\r\n      x !== PaymentChannel.PalkkausManual ||\r\n      (x === PaymentChannel.PalkkausManual && this.sessionService.isInSomeRole(\"pro,sepaPartner\"))\r\n    );\r\n    return this.uiHelpers.cache(this, \"channels\",\r\n      () => channelsForRole()?.map((x) => InvoicesLogic.getChannelAvatar(x))?.filter(x => !!x),\r\n      () => channelsForRole());\r\n  }\r\n\r\n  /**\r\n   * Gets the enabled payment channels as input enum options for the current session.\r\n   */\r\n  public get channelEnumOptions(): InputEnumOption[] {\r\n    return this.uiHelpers.cache(this, \"channelEnumOptions\",\r\n      () => this.channels?.map((x) => ({ text: x.displayName, value: x.id, title: x.description })),\r\n      () => this.sessionService.getSession()?.settings.paymentChannels);\r\n  }\r\n\r\n  /**\r\n   * Shows the paymment page as dialog.\r\n   * @param paymentObject - The object to pay: Either Calculation or Payroll\r\n   */\r\n  public showPaymentDialog(paymentObject: Calculation | PayrollDetails) {\r\n    if (!this.checkAccountVerificationForPayment()) {\r\n        this.showMissingSignatureAlert();\r\n        return;\r\n    }\r\n\r\n    if (!this.checkChangedSalaryDate(paymentObject)) {\r\n      this.showChangedSalaryDateAlert();\r\n      return;\r\n    }\r\n\r\n    let channel = null;\r\n    if (InvoicesLogic.isPayroll(paymentObject)) {\r\n      channel = paymentObject.input.paymentChannel;\r\n     } else if (InvoicesLogic.isCalculation(paymentObject)) {\r\n      if (this.sessionService.isInRole(\"person\")) {\r\n        paymentObject.info.paymentChannel = PaymentChannel.PalkkausPersonal;\r\n      }\r\n      channel = paymentObject.info.paymentChannel;\r\n    }\r\n\r\n    if(InvoicesLogic.isEcfa(channel)) {\r\n      if(!this.checkKycForPayment()) {\r\n        this.showMissingKycAlert();\r\n        return;\r\n      }\r\n    }\r\n\r\n    const logic = {\r\n      title:\r\n        InvoicesLogic.isPalkkausInvoicesLike(channel) ? Translations.get(\"SALAXY.NG1.InvoicesService.logic.title.palkkausInvoices\") :\r\n        Translations.get(\"SALAXY.NG1.InvoicesService.logic.title.default\"),\r\n      type: InvoicesLogic.isPayroll(paymentObject) ? \"payroll\" : \"calc\",\r\n      okButtonText:\r\n        InvoicesLogic.isPalkkausInvoicesLike(channel) ? Translations.get(\"SALAXY.NG1.InvoicesService.logic.okButtonText.palkkausInvoices\") :\r\n        InvoicesLogic.isCfa(channel) ? Translations.get(\"SALAXY.NG1.InvoicesService.logic.okButtonText.isCfaChannel\") : Translations.get(\"SALAXY.NG1.InvoicesService.logic.okButtonText.default\"),\r\n      channel,\r\n      paymentFunc: null,\r\n      isNullPayment: () => ( InvoicesLogic.isCalculation(paymentObject) && Numeric.round(paymentObject.result.employerCalc.totalPayment) == 0 )\r\n                       ||\r\n                      ( InvoicesLogic.isPayroll(paymentObject) && Numeric.round(paymentObject.info.totalPayment) == 0),\r\n      isReadyForPayment: () => InvoicesLogic.isPayroll(paymentObject) ?\r\n      paymentObject.info &&\r\n      paymentObject.info.isReadyForPayment :\r\n        InvoicesLogic.isCalculation(paymentObject) ?\r\n        paymentObject.worker &&\r\n        paymentObject.worker.tax.isValid &&\r\n          !paymentObject.result.validation.errors.find((e) => (e.type !== \"warning\")) :\r\n          false,\r\n      instructions: null\r\n    };\r\n\r\n    const saveForPreview = (): Promise<Calculation | PayrollDetails> => {\r\n      if (InvoicesLogic.isCalculation(paymentObject) &&\r\n          (\r\n            channel == PaymentChannel.PalkkausPersonal ||\r\n            channel == PaymentChannel.PalkkausEcfaPaytrail\r\n          )) {\r\n        if (!paymentObject.workflow?.status || paymentObject.workflow.status === CalculationStatus.Draft) {\r\n          const loader = this.uiHelpers.showLoading(Translations.get(\"SALAXY.NG1.InvoicesService.saving\") + \"...\");\r\n          return this.calculations.save(paymentObject).then((savedCalculation) => {\r\n            loader.dismiss();\r\n            angular.copy(savedCalculation, paymentObject);\r\n            this.$location.path(\"/calc/details/\" + paymentObject.id + \"&refresh=\" + new Date().getTime());\r\n            return paymentObject;\r\n          });\r\n        }\r\n        else\r\n        {\r\n          return Promise.resolve(paymentObject);\r\n        }\r\n      }\r\n      else\r\n      {\r\n        return Promise.resolve(paymentObject);\r\n      }\r\n    };\r\n\r\n    const paymentObjectForCfa = (): Promise<Calculation | PayrollDetails> => {\r\n      if (InvoicesLogic.isPayroll(paymentObject)) {\r\n        if (paymentObject.calcs.length > 0 ) {\r\n          return Promise.resolve(paymentObject);\r\n        } else {\r\n          const payrolls4Api = new Payrolls4(this.ajax);\r\n          return payrolls4Api.getCalcsOData(paymentObject.id, null).then((listItemResult) => {\r\n            const calcs = listItemResult.items;\r\n            const data: any = {};\r\n            data.listItemType = \"CalculationListItem\";\r\n            const columns = undefined;\r\n            const paramsTemplate = undefined;\r\n            const action = (items /*, data */) => {\r\n              const itemIds = items.map((x) => x.id);\r\n              return this.calculations.getMulti(itemIds).then((result) => {\r\n                const results = items.map(() => ({ message: \"\", result: [] }));\r\n                results[0].result = result;\r\n                return results;\r\n              });\r\n            };\r\n            return this.uiHelpers.showBatchProcessDialog(Translations.get(\"SALAXY.UI_Terms.wait\"), calcs, action, paramsTemplate, data, columns, 20, true, true, true).then((dialogResult) => {\r\n              const payrollCalcs = [];\r\n              if (dialogResult.done) {\r\n                dialogResult.results.forEach((result) => {\r\n                  payrollCalcs.push(...result.result);\r\n                });\r\n              }\r\n              const newPaymentObject:any = angular.copy(paymentObject);\r\n              newPaymentObject.calcs = payrollCalcs;\r\n              newPaymentObject[\"V4\"] = true;\r\n\r\n              return newPaymentObject;\r\n            });\r\n          });\r\n        }\r\n      } else {\r\n        return Promise.resolve(paymentObject);\r\n      }\r\n    };\r\n\r\n    if (InvoicesLogic.isCfa(channel) && channel !== PaymentChannel.PalkkausEcfaPaytrail) {\r\n        paymentObjectForCfa().then((reportingPaymentObject) => {\r\n          paymentObject = reportingPaymentObject;\r\n          this.uiHelpers.openEditDialog(\"salaxy-components/modals/calc/CfaPaymentOverview.html\", paymentObject, logic, \"lg\").then((result) => {\r\n          if (result.action !== EditDialogKnownActions.Ok) {\r\n            return;\r\n          }\r\n          this.createCfaInvoice(channel, paymentObject);\r\n        });\r\n      });\r\n    } else {\r\n      switch (channel) {\r\n        case PaymentChannel.PalkkausEcfaPaytrail:\r\n          {\r\n            paymentObjectForCfa().then((reportingPaymentObject) => {\r\n              paymentObject = reportingPaymentObject;\r\n              logic.paymentFunc = (pObj) => this.createPalkkausCfaPaytrailInvoice(pObj);\r\n              saveForPreview().then(() => this.uiHelpers.openEditDialog(\"salaxy-components/modals/calc/CfaPaymentOverview.html\", paymentObject, logic, \"lg\"));\r\n            });\r\n          }\r\n          break;\r\n        case PaymentChannel.PalkkausWS: {\r\n          this.uiHelpers.openEditDialog(\"salaxy-components/modals/calc/WSPaymentOverview.html\", paymentObject, logic, \"lg\");\r\n          break;\r\n        }\r\n        case PaymentChannel.PalkkausPersonal:\r\n          {\r\n            saveForPreview().then(() => {\r\n              this.uiHelpers.openEditDialog(\"salaxy-components/modals/calc/PalkkausPersonalPaymentOverview.html\", paymentObject, logic, \"lg\", \"PalkkausPersonalPaymentOverviewController\").then((result) => {\r\n                if (result.action) {\r\n                  if (result.action == InvoiceStatus.Canceled) {\r\n                    this.createPalkkausPersonalInvoice(channel, paymentObject, InvoiceStatus.Canceled);\r\n                    this.uiHelpers.showAlert(Translations.get(\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.alerts.headingCancelled\"), `${Translations.get(\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.alerts.cancel.infotext1\")}.\\r\\n${Translations.get(\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.alerts.cancel.infotext2\")}.`\r\n                    , Translations.get(\"SALAXY.UI_Terms.ok\"));\r\n                  } else if (result.action === InvoiceStatus.Paid) {\r\n                    this.createPalkkausPersonalInvoice(channel, paymentObject, InvoiceStatus.Paid);\r\n                    this.uiHelpers.showAlert(Translations.get(\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.alerts.headingPaid\"), `${Translations.get(\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.alerts.paid.text\")}\\r\\n${Translations.get(\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.alerts.paid.infoText1\")}\\r\\n${Translations.get(\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.alerts.paid.infoText2\")}\\r\\n${Translations.get(\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.alerts.paid.infoText3\")}`\r\n                    , Translations.get(\"SALAXY.UI_Terms.ok\"));\r\n                  }\r\n                }\r\n              });\r\n            });\r\n          }\r\n          break;\r\n        default:\r\n          this.uiHelpers.openEditDialog(\"salaxy-components/modals/calc/PaymentOverview.html\", paymentObject, logic, \"lg\");\r\n          break;\r\n      }\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Shows the payment invoice inspection page as dialog.\r\n   * @param paymentObject - Paid calculation\r\n   */\r\n  public showPalkkausPersonalInvoicesDialog(paymentObject: Calculation) {\r\n    const logic = {isInspectingPaidInvoices: true};\r\n    this.uiHelpers.openEditDialog(\"salaxy-components/modals/calc/PalkkausPersonalPaymentOverview.html\", paymentObject, logic, \"xl\", \"PalkkausPersonalPaymentOverviewController\");\r\n  }\r\n\r\n  /**\r\n   * Querys item and opens paymentdialog\r\n   * @param item InvoiceListItem used to query calculation\r\n   */\r\n  public showPaymentDialogForCalculation(item: InvoiceListItem) {\r\n    this.calculations.getSingle(item.businessObjects[0]).then(calculation => {\r\n      this.showPaymentDialog(calculation);\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shows an alert if the signature is missing.\r\n   */\r\n   public showMissingSignatureAlert() {\r\n    this.uiHelpers.showConfirm(Translations.get(\"SALAXY.NG1.InvoicesService.missingSignatureAlert.signatureMissing\"),\r\n    Translations.get(\"SALAXY.NG1.InvoicesService.missingSignatureAlert.creationCompleteBeforePay\") + \"\\n\" +\r\n    Translations.get(\"SALAXY.NG1.InvoicesService.missingSignatureAlert.signSignature\") + \"\\n\\n\" +\r\n    Translations.get(\"SALAXY.NG1.InvoicesService.missingSignatureAlert.continueToSignature\"),\r\n    Translations.get(\"SALAXY.NG1.InvoicesService.missingSignatureAlert.continue\"), Translations.get(\"SALAXY.NG1.InvoicesService.missingSignatureAlert.close\")).then((ok: boolean) => {\r\n        if (ok) {\r\n          if (this.sessionService.getCurrentAccount().entityType === LegalEntityType.Person ) {\r\n            this.onboardingService.launchHouseholdOnboarding();\r\n          } else {\r\n            this.onboardingService.launchCompanyOnboarding();\r\n          }\r\n        }\r\n      });\r\n  }\r\n\r\n\r\n  /**\r\n   * Checks if the company's KYC (Know Your Customer) is completed and not expired for payment.\r\n   * @returns {boolean} Returns true if the KYC is completed and not expired, otherwise false.\r\n   */\r\n  public checkKycForPayment(): boolean {\r\n    const kycExpiresAt = this.sessionService?.kycExpiresAt;\r\n    if (!kycExpiresAt) {\r\n      return false;\r\n    }\r\n    // Expire check valid after 1.9.2025\r\n    //if (Dates.isBefore(Dates.getToday(), \"2025-09-01\")){\r\n      return true;\r\n    //}\r\n\r\n    return Dates.isBefore(Dates.getToday(), kycExpiresAt);\r\n  }\r\n\r\n  /**\r\n   * Shows an alert if the kyc is missing.\r\n   */\r\n  public showMissingKycAlert() {\r\n    this.uiHelpers.showConfirm(\r\n    \"Asiakkaan tuntemistiedot puuttuvat\",\r\n    null,\r\n    \"Päivitä asiakkaan tuntemistiedot nyt\",\r\n    Translations.get(\"SALAXY.NG1.InvoicesService.missingSignatureAlert.close\"),\r\n    \"Asiakasvaratilin kautta maksaminen edellyttää asiakkaan tuntemistietojen päivittämistä. Päivitä KYC-tiedot oheisesta linkistä tai lue ohjeet, kuinka voit välittää päivityslinkin yhtiön nimenkirjoitusoikeudelliselle henkilölle täältä: <a href=\\\"https://help.palkkaus.fi/hc/fi/articles/19590957330589-Asiakkaan-tuntemistietojen-päivitys-KYC\\\" target=\\\"_blank\\\">Asiakkaan tuntemistietojen päivittäminen</a>\"\r\n  ).then((ok: boolean) => {\r\n        if (ok) {\r\n          window.open(Configs.current.isTestData ? \"https://rc-iam.palkkaus.fi/wizard/index.html\" : \"https://iam.palkkaus.fi/wizard/index.html\", \"_blank\");\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Returns true if the current authenticated user has\r\n   * required verification for the payment.\r\n   */\r\n   public checkAccountVerificationForPayment(): boolean {\r\n    return this.sessionService.checkAccountVerification();\r\n  }\r\n\r\n  /** Returns warning message text for the invoice if reported late.*/\r\n  public getEprWarningForPayment(salaryDate: string): string {\r\n    const warning = this.isDelayed(salaryDate) ? Translations.get(\"SALAXY.NG1.InvoicesService.eprWarningForPayment.isDelayed\") : \"\";\r\n    return warning;\r\n  }\r\n\r\n  /** Returns warning message text for the invoice if reported late.*/\r\n  public getEprWarningForCancellation(salaryDate: string, isPaid: boolean): string {\r\n    if (!isPaid) {\r\n      return null;\r\n    }\r\n    const warning = this.isDelayed(salaryDate) ? Translations.get(\"SALAXY.NG1.InvoicesService.eprWarningForCancellation.isDelayed\") + \"\\n\\n\" + Translations.get(\"SALAXY.NG1.InvoicesService.eprWarningForCancellation.infoText\") : \"\";\r\n    return warning;\r\n  }\r\n\r\n /**\r\n  * Checks the salary date validity before payment.\r\n  * @param paymentObject - The object to pay: Either Calculation or Payroll\r\n  */\r\n public checkChangedSalaryDate(paymentObject: Calculation | PayrollDetails) {\r\n  const role =  this.sessionService.isInRole(\"pro\") ? \"pro\" :\r\n                this.sessionService.isInRole(\"admin\") ? \"admin\" : null;\r\n  if (InvoicesLogic.isPayroll(paymentObject)) {\r\n    if (paymentObject.info.status != PayrollStatus.Draft &&\r\n        paymentObject.info.status != PayrollStatus.WaitingApproval)\r\n    {\r\n      return true;\r\n    }\r\n    if (!paymentObject.input.salaryDate) {\r\n      return true;\r\n    }\r\n    if (paymentObject.input.salaryDate != paymentObject.info.salaryDate) {\r\n      return false;\r\n    }\r\n    if (paymentObject.input.salaryDateKind == SalaryDateKind.InPast) {\r\n      return true;\r\n    }\r\n    return SalaryDateLogic.isValidSalaryDate(paymentObject.info.salaryDate, null, null, !!paymentObject.input.salaryDate, paymentObject.input.paymentChannel, PayrollLogic.isZeroPayment(paymentObject.calcs), role);\r\n  } else if (InvoicesLogic.isCalculation(paymentObject)) {\r\n    if (this.sessionService.isInRole(\"person\")) {\r\n      paymentObject.info.paymentChannel = PaymentChannel.PalkkausPersonal;\r\n    }\r\n    if (paymentObject.workflow.status != CalculationStatus.Draft &&\r\n        paymentObject.workflow.status != CalculationStatus.WaitingApproval &&\r\n        paymentObject.workflow.status != CalculationStatus.ProDraft\r\n      ) {\r\n      return true;\r\n    }\r\n    if (!paymentObject.workflow.requestedSalaryDate) {\r\n      return true;\r\n    }\r\n    if (paymentObject.workflow.requestedSalaryDate != paymentObject.workflow.salaryDate) {\r\n      return false;\r\n    }\r\n    if (paymentObject.workflow.salaryDateKind == SalaryDateKind.InPast) {\r\n      return true;\r\n    }\r\n    return SalaryDateLogic.isValidSalaryDate(paymentObject.workflow.salaryDate, paymentObject.worker?.paymentData?.ibanNumber, null, !!paymentObject.workflow.requestedSalaryDate, paymentObject.info.paymentChannel, CalculatorLogic.isZeroPayment(paymentObject), role);\r\n  }\r\n  return true;\r\n }\r\n\r\n  /**\r\n   * Shows an alert for invalid salary date.\r\n   */\r\n   public showChangedSalaryDateAlert() {\r\n    this.uiHelpers.showAlert(Translations.get(\"SALAXY.VALIDATION.Calc.SalaryDateChanged.label\"),Translations.get(\"SALAXY.VALIDATION.Calc.SalaryDateChanged.description\") );\r\n   }\r\n\r\n  /** Checks if the Epr report is delayed. */\r\n  private isDelayed(salaryDate?: string): boolean {\r\n      const officialDate = Dates.add((salaryDate ?? \"today\"),5, \"day\");\r\n      const expiresAt = Dates.addWorkdays(officialDate, 0);\r\n      const today = Dates.asDate(\"today\");\r\n      return today > expiresAt;\r\n}\r\n\r\n  private createCfaInvoice(channel: PaymentChannel, paymentObject: Calculation | PayrollDetails) {\r\n\r\n    const previewInvoices = (): Promise<InvoicePreview[]> => {\r\n      const coll: CalculationCollection = {};\r\n      if (InvoicesLogic.isPayroll(paymentObject)) {\r\n        if ((paymentObject as any).V4) {\r\n          const payrolls4Api = new Payrolls4(this.ajax);\r\n          return payrolls4Api.previewInvoices(paymentObject.id, [], false);\r\n        }\r\n        else\r\n        {\r\n          coll.payrollIds = [paymentObject.id];\r\n          return this.invoicesApi.previewInvoices(channel, coll);\r\n        }\r\n      } else {\r\n        coll.calcs = [paymentObject];\r\n        return this.invoicesApi.previewInvoices(channel, coll);\r\n      }\r\n    };\r\n\r\n    const createNewInvoice = () => {\r\n      if (InvoicesLogic.isPayroll(paymentObject)) {\r\n        if ((paymentObject as any).V4) {\r\n          const payrolls4Api = new Payrolls4(this.ajax);\r\n          return payrolls4Api.createInvoices(paymentObject.id, [], false);\r\n        }\r\n        else\r\n        {\r\n          return this.invoicesApi.createInvoicesForPayroll(channel, paymentObject.id);\r\n        }\r\n      } else {\r\n        return this.invoicesApi.createInvoices(paymentObject, channel);\r\n      }\r\n    };\r\n\r\n    const createInvoice = (): Promise<Invoice> => {\r\n      return previewInvoices().then((previews) => {\r\n        const grossInvoicePreview = previews.find((x) => x.invoice.entityType == InvoiceType.Gross);\r\n        if (!grossInvoicePreview) {\r\n          return null;\r\n        }\r\n        if (grossInvoicePreview.exists) {\r\n          return this.invoicesApi.getSingle(grossInvoicePreview.invoice.id);\r\n        }\r\n        return createNewInvoice().then((invoices) => {\r\n          return invoices.find((x) => x.header.type == InvoiceType.Gross);\r\n        });\r\n      });\r\n    };\r\n\r\n    const navigateToPaymentObject = (businessObjectId) => {\r\n      if (InvoicesLogic.isPayroll(paymentObject)) {\r\n        this.$location.path(\"/payroll/details/\" + businessObjectId + \"&refresh=\" + new Date().getTime());\r\n      } else {\r\n        this.$location.path(\"/calc/details/\" + businessObjectId + \"&refresh=\" + new Date().getTime());\r\n      }\r\n    };\r\n\r\n    const isPaid = (invoice: Invoice) => {\r\n      if (invoice.header.status === InvoiceStatus.Paid) {\r\n        this.uiHelpers.showAlert(Translations.get(\"SALAXY.NG1.InvoicesService.isPaid.payment\"), Translations.get(\"SALAXY.NG1.InvoicesService.isPaid.paid\"));\r\n        return true;\r\n      }\r\n      else if (invoice.header.status !== InvoiceStatus.PaymentStarted && invoice.header.status !== InvoiceStatus.Unread)\r\n      {\r\n        this.uiHelpers.showAlert(Translations.get(\"SALAXY.NG1.InvoicesService.isPaid.cantCreatePayment\"), Translations.get(\"SALAXY.NG1.InvoicesService.isPaid.cantCreatePaymentAlreadyPaid\"));\r\n        return true;\r\n      }\r\n      return false;\r\n    };\r\n\r\n    const loader = this.uiHelpers.showLoading(Translations.get(\"SALAXY.NG1.InvoicesService.creatingPayment\")+ \"...\");\r\n    createInvoice().then((grossInvoice) => {\r\n      if (!grossInvoice) {\r\n        loader.dismiss();\r\n        this.uiHelpers.showAlert(Translations.get(\"SALAXY.NG1.InvoicesService.createInvoice.cantCreateInvoice\"), Translations.get(\"SALAXY.NG1.InvoicesService.createInvoice.cantCreateInvoiceCheck\"));\r\n        return;\r\n      }\r\n      switch (channel) {\r\n        case PaymentChannel.PalkkausEcfaFinvoice:\r\n          {\r\n            if (isPaid(grossInvoice)) {\r\n              loader.dismiss();\r\n              navigateToPaymentObject(grossInvoice.header.businessObjects[0]);\r\n            } else {\r\n              loader.dismiss();\r\n              const settingsReceiver = this.settingsService.current.payments.invoice.eInvoiceReceiver;\r\n              const settingsIntermediator = this.settingsService.current.payments.invoice.eInvoiceIntermediator;\r\n              const item = {\r\n                eInvoiceReceiver: settingsReceiver,\r\n                eInvoiceIntermediator: settingsIntermediator,\r\n              };\r\n              const showAddressSelection = !settingsReceiver || !settingsIntermediator;\r\n\r\n              const sendEInvoice = (address: { eInvoiceReceiver: string, eInvoiceIntermediator: string }): Promise<any> => {\r\n                const sendLoader = this.uiHelpers.showLoading(Translations.get(\"SALAXY.NG1.InvoicesService.sending\")+ \"...\");\r\n                if (address.eInvoiceReceiver !== settingsReceiver || address.eInvoiceIntermediator !== settingsIntermediator) {\r\n                  const settings = this.settingsService.current;\r\n                  settings.payments.invoice.eInvoiceReceiver = address.eInvoiceReceiver;\r\n                  settings.payments.invoice.eInvoiceIntermediator = address.eInvoiceIntermediator;\r\n                  this.settingsService.save();\r\n                }\r\n\r\n                return this.invoicesApi.sendEInvoice(grossInvoice.id, address.eInvoiceReceiver, address.eInvoiceIntermediator).then((result) => {\r\n                  sendLoader.dismiss();\r\n                  let title = Translations.get(\"SALAXY.NG1.InvoicesService.sendEInvoice.ajax.title\");\r\n                  let msg = `${Translations.get(\"SALAXY.NG1.InvoicesService.sendEInvoice.ajax.msg\")} ${address.eInvoiceIntermediator}/${address.eInvoiceReceiver}.`;\r\n                  let freeText = \"\";\r\n                  if (result.Response.Status !== \"OK\") {\r\n                    title = Translations.get(\"SALAXY.NG1.InvoicesService.sendEInvoice.ajax.error.title\");\r\n                    msg = Translations.get(\"SALAXY.NG1.InvoicesService.sendEInvoice.ajax.error.msg\");\r\n                    if (result.Response.FreeText) {\r\n                      for (const ft of result.Response.FreeText) {\r\n                        freeText += ft[\"#text\"] + \"\\n\";\r\n                      }\r\n                    }\r\n                  }\r\n                  freeText = this.textToRows(freeText, 80, \"\\n\");\r\n                  this.uiHelpers.showAlert(title, msg + \"\\n\" + Translations.get(\"SALAXY.NG1.InvoicesService.sendEInvoice.ajax.operatorStatus\") + \":\" + \"\\n\" + result.Response.Status + \" \" + result.Response.StatusCode + \"\\n\" + freeText);\r\n                  return result;\r\n                });\r\n              };\r\n\r\n              if (showAddressSelection) {\r\n                const eInvoiceLogic = {\r\n                  selectEInvoiceAddress: (itemRef) => {\r\n                    this.settingsService.selectEInvoiceAddress(itemRef);\r\n                  },\r\n                };\r\n\r\n                this.uiHelpers.openEditDialog(\"salaxy-components/modals/payment/cfa/EInvoice.html\", item, eInvoiceLogic, null).then((result) => {\r\n                  if (result.action !== EditDialogKnownActions.Ok) {\r\n                    navigateToPaymentObject(grossInvoice.header.businessObjects[0]);\r\n                  } else {\r\n                    sendEInvoice(result.item).then(() => {\r\n                      navigateToPaymentObject(grossInvoice.header.businessObjects[0]);\r\n                    });\r\n                  }\r\n                });\r\n              } else {\r\n                sendEInvoice(item).then(() => {\r\n                  navigateToPaymentObject(grossInvoice.header.businessObjects[0]);\r\n                });\r\n              }\r\n            }\r\n          }\r\n          break;\r\n        case PaymentChannel.PalkkausEcfaReference:\r\n          {\r\n            loader.dismiss();\r\n\r\n            const cfaReferenceCalculations = [];\r\n            if (InvoicesLogic.isPayroll(paymentObject)) {\r\n              cfaReferenceCalculations.push(...paymentObject.calcs);\r\n            } else if (InvoicesLogic.isCalculation(paymentObject)) {\r\n              cfaReferenceCalculations.push(paymentObject);\r\n            }\r\n\r\n            const cfaReferenceTotalResultCalculation = CalculatorLogic.getBlank();\r\n            cfaReferenceTotalResultCalculation.worker.tax = cfaReferenceTotalResultCalculation.worker.tax || {};\r\n            cfaReferenceTotalResultCalculation.result = CalculationResultLogic.add(cfaReferenceCalculations.map((x) => x.result));\r\n\r\n            const referenceLogic = {\r\n              printClass: \"sxyFullPrint\",\r\n              print: (pcls: \"sxyFullPrint\" | \"sxySecurePrint\") => {\r\n                referenceLogic.printClass = pcls;\r\n                setTimeout(() => {\r\n                  window.print();\r\n                }, 0);\r\n              },\r\n              calculations: cfaReferenceCalculations,\r\n              totalResultCalculation: cfaReferenceTotalResultCalculation,\r\n            };\r\n            // show dialog for every invoice status, for paid too\r\n            this.uiHelpers.openEditDialog(\"salaxy-components/modals/payment/cfa/Transfer.html\", grossInvoice, referenceLogic, \"xl\").then(() => {\r\n              navigateToPaymentObject(grossInvoice.header.businessObjects[0]);\r\n            });\r\n          }\r\n          break;\r\n      }\r\n    });\r\n  }\r\n\r\n  private createPalkkausCfaPaytrailInvoice(paymentObject: Calculation | PayrollDetails) {\r\n\r\n    const navigateToPaymentObject = (businessObjectId) => {\r\n      if (InvoicesLogic.isPayroll(paymentObject)) {\r\n        this.$location.path(\"/payroll/details/\" + businessObjectId + \"&refresh=\" + new Date().getTime());\r\n      } else {\r\n        this.$location.path(\"/calc/details/\" + businessObjectId + \"&refresh=\" + new Date().getTime());\r\n      }\r\n    };\r\n\r\n    const getPaytrailUrl = (businessObjectId) => {\r\n      if (InvoicesLogic.isPayroll(paymentObject)) {\r\n        return this.ajax.getServerAddress() + `/SalaryPayment/PayInvoiceForPayroll/${businessObjectId}?access_token=${this.ajax.getCurrentToken()}`;\r\n      } else {\r\n        return this.ajax.getServerAddress() + `/SalaryPayment/PayInvoiceForCalculation/${businessObjectId}?access_token=${this.ajax.getCurrentToken()}`;\r\n      }\r\n    };\r\n\r\n    const paytrailUrl = getPaytrailUrl(paymentObject.id);\r\n    const resolver = (ev: {\r\n      /** The object passed from the other window. */\r\n      data: ExternalDialogData<any>,\r\n      /** The origin of the window that sent the message at the time postMessage was called. */\r\n      origin: string,\r\n      /** A reference to the window object that sent the message */\r\n      source: MessageEventSource | null,\r\n    }) => {\r\n      if (ev?.data.action == \"refresh\") {\r\n        this.$timeout(() => {\r\n          navigateToPaymentObject(paymentObject.id);\r\n        });\r\n        return false;\r\n      }\r\n      return true;\r\n    };\r\n\r\n    this.uiHelpers.showExternalDialog(\"PaytrailPayment\", paytrailUrl, {}, null, resolver).then((result) => {\r\n        if (result.action == \"user-cancel\") {\r\n          this.uiHelpers.showDialog(\"salaxy-components/modals/payment/PaymentCancel.html\").then(() => {\r\n            navigateToPaymentObject(paymentObject.id);\r\n          });\r\n        } else if (result.action == \"invoice-paid\") {\r\n          this.uiHelpers.showAlert(Translations.get(\"SALAXY.NG1.InvoicesService.paytrail.invoicePaid.heading\"), Translations.get(\"SALAXY.NG1.InvoicesService.paytrail.invoicePaid.text\") + \".\").then(() => {\r\n            navigateToPaymentObject(paymentObject.id);\r\n          });\r\n        } else if (result.action == \"invoice-missing\") {\r\n          this.uiHelpers.showAlert(Translations.get(\"SALAXY.NG1.InvoicesService.paytrail.invoiceMissing.heading\"), Translations.get(\"SALAXY.NG1.InvoicesService.paytrail.invoiceMissing.text\") + \".\").then(() => {\r\n          navigateToPaymentObject(paymentObject.id);\r\n          });\r\n        } else if (result.action == EditDialogKnownActions.Ok) {\r\n          this.uiHelpers.showDialog(\"salaxy-components/modals/payment/PaymentConfirm.html\").then(() => {\r\n            navigateToPaymentObject(paymentObject.id);\r\n          });\r\n        }\r\n    });\r\n  }\r\n\r\n  private createPalkkausPersonalInvoice(channel: PaymentChannel, paymentObject: Calculation | PayrollDetails, status: InvoiceStatus) {\r\n    if (InvoicesLogic.isPayroll(paymentObject)) {\r\n      this.uiHelpers.showAlert(Translations.get(\"SALAXY.NG1.InvoicesService.palkkausPersonalInvoice.isPayroll.heading\"), Translations.get(\"SALAXY.NG1.InvoicesService.palkkausPersonalInvoice.isPayroll.text\") + \".\");\r\n      return;\r\n    }\r\n\r\n    const updateInvoiceStatus = (invoice: Invoice, newStatus: InvoiceStatus): Promise<Invoice> => {\r\n      if (invoice.header.status === newStatus) {\r\n        return Promise.resolve(invoice);\r\n      }\r\n      return this.invoicesApi.requestStatusUpdate(invoice.id, newStatus);\r\n    };\r\n\r\n    const previewInvoices = (): Promise<InvoicePreview[]> => {\r\n      return this.invoicesApi.previewInvoices(channel, {\r\n        calcs: [paymentObject],\r\n      });\r\n    };\r\n\r\n    const createNewInvoice = (): Promise<Invoice[]> => {\r\n      return this.invoicesApi.createInvoices(paymentObject, channel);\r\n    };\r\n\r\n    const createInvoice = (): Promise<{netInvoice: Invoice, taxInvoice: Invoice}> => {\r\n      const netAndTaxInvoices: {netInvoice: Invoice, taxInvoice: Invoice} = {netInvoice: null, taxInvoice: null};\r\n      return previewInvoices().then((previews) => {\r\n        const netInvoicePreview = previews.find((x) => x.invoice.entityType == InvoiceType.Net && x.invoice.status !== InvoiceStatus.Canceled && x.invoice.status !== InvoiceStatus.Error);\r\n        if (!netInvoicePreview) {\r\n          return Promise.resolve(netAndTaxInvoices);\r\n        }\r\n        const taxInvoicePreview = previews.find((x) => x.invoice.entityType == InvoiceType.Tax && x.invoice.status !== InvoiceStatus.Canceled && x.invoice.status !== InvoiceStatus.Error);\r\n\r\n        const getNetInvoice = (): Promise<void> => {\r\n          return this.invoicesApi.getSingle(netInvoicePreview.invoice.id).then((netInvoice) => {\r\n            netAndTaxInvoices.netInvoice = netInvoice;\r\n          });\r\n        };\r\n\r\n        const getTaxInvoice = (): Promise<void> => {\r\n          if (!taxInvoicePreview || !taxInvoicePreview.exists) {\r\n            return Promise.resolve(null);\r\n          }\r\n          return this.invoicesApi.getSingle(taxInvoicePreview.invoice.id).then((taxInvoice) => {\r\n            netAndTaxInvoices.taxInvoice = taxInvoice;\r\n          });\r\n        };\r\n\r\n        if (netInvoicePreview.exists) {\r\n          return Promise.all([getNetInvoice(), getTaxInvoice()]).then(() => {\r\n            return netAndTaxInvoices;\r\n          });\r\n        }\r\n\r\n        return createNewInvoice().then((invoices) => {\r\n          netAndTaxInvoices.netInvoice = invoices.find((x) => x.header.type == InvoiceType.Net);\r\n          netAndTaxInvoices.taxInvoice = invoices.find((x) => x.header.type == InvoiceType.Tax);\r\n          return netAndTaxInvoices;\r\n        });\r\n      });\r\n    };\r\n\r\n    const navigateToPaymentObject = (businessObjectId) => {\r\n      this.$location.path(\"/calc/details/\" + businessObjectId + \"&refresh=\" + new Date().getTime());\r\n    };\r\n\r\n    const loader = this.uiHelpers.showLoading(Translations.get(\"SALAXY.NG1.InvoicesService.palkkausPersonalInvoice.updatingPaymentStatus\") + \"...\");\r\n    createInvoice().then((invoices) => {\r\n      if (!invoices.netInvoice) {\r\n        loader.dismiss();\r\n        this.uiHelpers.showAlert(Translations.get(\"SALAXY.NG1.InvoicesService.palkkausPersonalInvoice.createInvoice.heading\"), Translations.get(\"SALAXY.NG1.InvoicesService.palkkausPersonalInvoice.createInvoice.text\") + \"...\");\r\n        return;\r\n      }\r\n\r\n      // If status is Canceled, update only net invoice, backend will handle other invoices cancellation\r\n      if (status === InvoiceStatus.Canceled) {\r\n        updateInvoiceStatus(invoices.netInvoice, status).then(() => {\r\n          loader.dismiss();\r\n          navigateToPaymentObject(invoices.netInvoice.header.businessObjects[0]);\r\n        });\r\n      }\r\n\r\n      // if status is not canceled, update net and tax invoices\r\n      if (status !== InvoiceStatus.Canceled) {\r\n        const promises = [\r\n          updateInvoiceStatus(invoices.netInvoice, status)\r\n        ];\r\n\r\n        if (invoices.taxInvoice) {\r\n          promises.push(updateInvoiceStatus(invoices.taxInvoice, status));\r\n        }\r\n\r\n        Promise.all(promises).then(() => {\r\n          loader.dismiss();\r\n          navigateToPaymentObject(invoices.netInvoice.header.businessObjects[0]);\r\n        });\r\n      }\r\n    });\r\n  }\r\n\r\n  private textToRows(text: string, rowLength: number, separator: string): string {\r\n    if (!text) {\r\n      return text;\r\n    }\r\n    const result = [];\r\n    const rows = text.split(separator);\r\n    for (const row of rows) {\r\n      let remaining = row;\r\n      while (remaining.length > rowLength) {\r\n        result.push(remaining.substr(0, rowLength));\r\n        remaining = remaining.slice(rowLength);\r\n      }\r\n      if (remaining.length > 0) {\r\n        result.push(remaining);\r\n      }\r\n    }\r\n    return result.join(separator);\r\n  }\r\n}","import angular from \"angular\";\r\n\r\nimport { Ajax, Onboarding, Onboardings, WebSiteUserRole } from \"@salaxy/core\";\r\n\r\nimport { SessionService } from \"./SessionService\";\r\nimport { UiHelpers } from \"./ui\";\r\n\r\n/**\r\n * Manages the onboarding process where an account is created.\r\n */\r\nexport class OnboardingService {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$rootScope\", \"$sce\", \"Onboardings\", \"SessionService\", \"UiHelpers\", \"AjaxNg1\", \"$location\"];\r\n\r\n  /** The current onboarding model */\r\n  public model: Onboarding;\r\n\r\n  /** Unique identifier of the onboarding data in storage */\r\n  public id: string;\r\n\r\n  /** Server address for onboarding pages etc. */\r\n  public serverAddress: string;\r\n\r\n  private lastPdfPreviewUrl;\r\n\r\n  constructor(\r\n    private $rootScope: angular.IRootScopeService,\r\n    private $sce: angular.ISCEService,\r\n    private onboardingsApi: Onboardings,\r\n    private sessionService: SessionService,\r\n    private uiHelpers: UiHelpers,\r\n    private ajax: Ajax,\r\n    private $location: angular.ILocationService,\r\n  ) {\r\n    this.init();\r\n  }\r\n\r\n  /** Gets / refreshes the onboarding data from the server  */\r\n  public getOnboardingData(id: string = null): Promise<Onboarding> {\r\n    return this.onboardingsApi.getOnboarding(id || \"latest\").then((result) => {\r\n      this.model = result;\r\n      this.id = result.id;\r\n      this.notify();\r\n      return this.model;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Get the onboarding object for given account.\r\n   * @param accountId - Account id for existing account.\r\n   */\r\n  public getOnboardingDataForAccount(accountId: string): Promise<Onboarding> {\r\n    return this.onboardingsApi.getOnboardingForAccount(accountId).then((data) => {\r\n      if (data) {\r\n        this.id = data.id;\r\n      } else {\r\n        this.id = null;\r\n      }\r\n      this.model = data;\r\n      return this.model;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Saves the current onboarding to database.\r\n   * @returns A Promise with result data (Onboarding)\r\n   */\r\n  public save(): Promise<Onboarding> {\r\n    const method = (this.model.signature as any).method;\r\n    return this.onboardingsApi.saveOnboarding(this.model).then((result) => {\r\n      if (this.id !== result.id) {\r\n        this.id = result.id;\r\n      }\r\n      this.model = result;\r\n      (this.model.signature as any).method = method;\r\n      return this.model;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Commits current onboarding  and creates/changes the account.\r\n   * @returns A Promise with result data (Onboarding)\r\n   */\r\n  public commit(): Promise<Onboarding> {\r\n    return this.onboardingsApi.commitOnboarding(this.model).then((data: Onboarding) => {\r\n      this.model = data;\r\n      return this.model;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Return the new URL for digital signature: Telia and Singicat\r\n   * @param authService Select the signature service (bank / mobile auth).\r\n   * This is only supported for Telia / Persons (not companies Signicat)\r\n   * @param signerPersonalId Possibility to override the signer personal Id.\r\n   * @param testSignerPersonalId Signer personal id for test.\r\n   * @param successUrl Optional success url for the signature.\r\n   * Leaving this empty will return the brower to the current page (path, not query params / hash)\r\n   * @param cancelUrl Optional cancel / error url for the signature. Default is successUrl.\r\n   */\r\n  public getDigitalSignUrl(authService: string = null, signerPersonalId: string = null, testSignerPersonalId: string = null, successUrl = null, cancelUrl = null): string {\r\n    const returnUrl = successUrl ? successUrl :  (parent !== window) ? document.referrer : null;\r\n    return this.getServerAddress() + \"/onboarding/DigitalSignatureBegin?id=\"\r\n      + this.model.owner + \"|\" + this.id\r\n      + \"&signerPersonalId=\" + (signerPersonalId || this.model.signature.personalId || \"\")\r\n      + \"&testSignerPersonalId=\" + (testSignerPersonalId ||\"\")\r\n      + \"&authService=\" + (authService || \"\")\r\n      + \"&timestamp=\" + Date.now()\r\n      + (returnUrl ? \"&successUrl=\" + encodeURIComponent(returnUrl) : \"\")\r\n      + (cancelUrl ? \"&cancelUrl=\" + encodeURIComponent(cancelUrl) : \"\")\r\n      ;\r\n  }\r\n\r\n  /**\r\n   * Gets the PDF preview address taking into account potential changes in the model.\r\n   * @param asUntrusted - Boolean indicating if the return url should be returned as untrusted (not wrapped).\r\n   * By default, the url is returned as trusted url.\r\n   * @returns Url address\r\n   */\r\n  public getPdfPreviewAddress(asUntrusted = false): string {\r\n    let id = \"\";\r\n    if (this.model?.owner && this.id) {\r\n      id = this.model.owner + \"|\" + this.id;\r\n    }\r\n    const url = `${this.getServerAddress()}/onboarding/GetAuthorizationPdfPreview?id=${id}&signer.personalId=${this.model.signature.personalId || \"\"}`;\r\n    if (!this.lastPdfPreviewUrl || this.lastPdfPreviewUrl.url !== url) {\r\n      this.lastPdfPreviewUrl = {\r\n        url,\r\n        sce: this.$sce.trustAsResourceUrl(url),\r\n      };\r\n    }\r\n    if (asUntrusted) {\r\n      return this.lastPdfPreviewUrl.url;\r\n    }\r\n    return this.lastPdfPreviewUrl.sce;\r\n  }\r\n\r\n  /**\r\n   * Controllers can subscribe to changes in service data using this method.\r\n   * Read more about the pattern in: http://www.codelord.net/2015/05/04/angularjs-notifying-about-changes-from-services-to-controllers/\r\n   * @param scope Controller scope for the subscribing controller (or directive etc.)\r\n   * @param callback The event listener function. See $on documentation for details\r\n   */\r\n  public subscribe(scope: angular.IScope, callback: (event: angular.IAngularEvent, ...args: any[]) => any): void {\r\n    const handler = this.$rootScope.$on(\"onboarding-service-event\", callback);\r\n    scope.$on(\"$destroy\", handler);\r\n  }\r\n\r\n  /**\r\n   * Opens customer wizard as modal dialog.\r\n   * @param accountId - Optional accountId for existing company.\r\n   */\r\n  public launchCustomerOnboarding(accountId: string): Promise<any> {\r\n\r\n    const getModel = () => {\r\n      return this.getOnboardingDataForAccount(accountId).then(() => {\r\n        if (!this.model) {\r\n          this.model = {\r\n            accountType: WebSiteUserRole.Company,\r\n            signature: {},\r\n          };\r\n          this.id = null;\r\n          return this.save();\r\n        } else {\r\n          return this.model;\r\n        }\r\n      });\r\n    };\r\n\r\n    return getModel().then(() => {\r\n      // ensure correct role\r\n      this.model.accountType = WebSiteUserRole.Company;\r\n      return this.uiHelpers.showDialog(\r\n        \"salaxy-components/modals/onboarding/customer/index.html\",\r\n        \"CustomerOnboardingController\",\r\n        null,\r\n        null,\r\n        \"lg\");\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shows the current customer invitation as modal dialog.\r\n   * @param accountId - AccountId for existing company.\r\n   */\r\n   public showCustomerInvitation(accountId: string) {\r\n    const getModel = () => {\r\n      return this.getOnboardingDataForAccount(accountId).then(() => {\r\n        if (!this.model.id) {\r\n          return this.save();\r\n        } else {\r\n          return this.model;\r\n        }\r\n      });\r\n    };\r\n\r\n    return getModel().then(() => {\r\n      return this.uiHelpers.showDialog(\r\n        \"salaxy-components/modals/onboarding/customer/invitation.html\",\r\n        \"CustomerOnboardingController\",\r\n        null, null, \"lg\");\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Opens a generic wizard as modal dialog.\r\n   * If account type is known, opens the the wizard for that type.\r\n   * @param id - Optional onboarding id for existing onboarding.\r\n   * @param isModelLoaded  - If true, the method does not load the model from backend any more.\r\n   */\r\n  public launchGenericOnboarding(id: string = null, isModelLoaded = false): void {\r\n    const getModel = () => {\r\n      if (isModelLoaded) {\r\n        return Promise.resolve(this.model);\r\n      }\r\n      return this.getOnboardingData(id);\r\n    };\r\n\r\n    getModel().then(() => {\r\n      if (this.launchOnboardingOfType(this.model.accountType, id, true)) {\r\n        return;\r\n      }\r\n      this.uiHelpers.showDialog(\r\n        \"salaxy-components/modals/onboarding/generic/index.html\",\r\n        null,\r\n        {\r\n          launch: (close) => {\r\n            if (this.launchOnboardingOfType(this.model.accountType, id, true)) {\r\n              close();\r\n            }\r\n          },\r\n          model: this.model,\r\n        },\r\n        null);\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Launches an onboarding of a type if type is specific.\r\n   * @param role Role that is evaluated: Launched if it matches one of the specific roles.\r\n   * Does not start onboarding if role is None / null etc.\r\n   * @param id Identifier of onboarding object.\r\n   * @param isModelLoaded If true, the model is already loaded.\r\n   * @returns True if the dialog is launched.\r\n   */\r\n  public launchOnboardingOfType(role: WebSiteUserRole, id: string = null, isModelLoaded = false) {\r\n    switch (this.model.accountType) {\r\n      case WebSiteUserRole.Company:\r\n        this.launchCompanyOnboarding(id, isModelLoaded);\r\n        return true;\r\n      case WebSiteUserRole.Household:\r\n        this.launchHouseholdOnboarding(id, isModelLoaded);\r\n        return true;\r\n      case WebSiteUserRole.Worker:\r\n        this.launchWorkerOnboarding(id, isModelLoaded);\r\n        return true;\r\n      default:\r\n        return false;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Opens worker wizard as modal dialog.\r\n   * @param id - Optional onboarding id for existing worker.\r\n   * @param isModelLoaded  - If true, the method does not load the model from backend any more.\r\n   */\r\n  public launchWorkerOnboarding(id: string = null, isModelLoaded = false): Promise<any> {\r\n    return this.launchOnboarding(WebSiteUserRole.Worker, \"salaxy-components/modals/onboarding/worker/index.html\", \"WorkerOnboardingController\", id, isModelLoaded);\r\n  }\r\n\r\n  /**\r\n   * Opens company wizard as modal dialog.\r\n   * @param id - Optioanl onboarding id for existing company.\r\n   * @param isModelLoaded  - If true, the method does not load the model from backend any more.\r\n   */\r\n  public launchCompanyOnboarding(id: string = null, isModelLoaded = false): Promise<any> {\r\n    return this.launchOnboarding(WebSiteUserRole.Company, \"salaxy-components/modals/onboarding/company/index.html\", \"CompanyOnboardingController\", id, isModelLoaded);\r\n  }\r\n\r\n  /**\r\n   * Opens household wizard as modal dialog.\r\n   * @param id - Optioanl onboarding id for existing company.\r\n   * @param isModelLoaded  - If true, the method does not load the model from backend any more.\r\n   */\r\n  public launchHouseholdOnboarding(id: string = null, isModelLoaded = false): Promise<any> {\r\n    return this.launchOnboarding(WebSiteUserRole.Household, \"salaxy-components/modals/onboarding/household/index.html\", \"HouseholdOnboardingController\", id, isModelLoaded);\r\n  }\r\n\r\n  /**\r\n   * Opens a simple signature page for federation (currently for Raksa / Palkkamylly only)\r\n   * @param id - Optioanl onboarding id for existing person.\r\n   * @param isModelLoaded  - If true, the method does not load the model from backend any more.\r\n   */\r\n   public launchFederateSign(id: string = null, isModelLoaded = false): Promise<any> {\r\n    return this.launchOnboarding(WebSiteUserRole.Worker, \"salaxy-components/modals/onboarding/palkkamylly/federate-sign.html\", \"WorkerOnboardingController\", id, isModelLoaded);\r\n  }\r\n\r\n  private launchOnboarding(role: WebSiteUserRole, index: string, ctrl: string, id: string = null, isModelLoaded = false, data: any = null): Promise<any> {\r\n    const getModel = () => {\r\n      if (isModelLoaded) {\r\n        return Promise.resolve(this.model);\r\n      }\r\n\r\n      return this.getOnboardingData(id);\r\n    };\r\n\r\n    return getModel().then(() => {\r\n      // ensure correct role\r\n      this.model.accountType = role;\r\n      return this.uiHelpers.showDialog(\r\n        index,\r\n        ctrl,\r\n        data,\r\n        null,\r\n        \"lg\");\r\n    });\r\n  }\r\n\r\n  private notify(): void {\r\n    this.$rootScope.$emit(\"onboarding-service-event\");\r\n  }\r\n\r\n  private getServerAddress(): string {\r\n    if (this.serverAddress) {\r\n      return this.serverAddress.replace(/\\/+$/, \"\");\r\n    }\r\n    return this.sessionService.getServerAddress();\r\n  }\r\n\r\n  /**\r\n   * Continues based on returnUrl parameter from the current url.\r\n   */\r\n  private launchReturnUrlOnboarding() {\r\n    const returnUrlParameters = this.getReturnUrlOnboardingParameters();\r\n\r\n    if (returnUrlParameters) {\r\n\r\n      const authenticate = (): Promise<any> => {\r\n        const token = this.readTokenFromUrl(\"ob_token=\");\r\n        if (token) {\r\n          this.ajax.setCurrentToken(token);\r\n          return this.sessionService.checkSession();\r\n        } else {\r\n          return Promise.resolve();\r\n        }\r\n      };\r\n\r\n      authenticate().then(() => {\r\n        switch (returnUrlParameters.onboardingType) {\r\n          case \"company\":\r\n            this.launchCompanyOnboarding(returnUrlParameters.id);\r\n            break;\r\n          case \"household\":\r\n            this.launchHouseholdOnboarding(returnUrlParameters.id);\r\n            break;\r\n          case \"worker\":\r\n            this.launchWorkerOnboarding(returnUrlParameters.id);\r\n            break;\r\n          case \"customer\":\r\n            this.launchOnboarding(WebSiteUserRole.Company, \"salaxy-components/modals/onboarding/customer/index.html\", \"CustomerOnboardingController\", returnUrlParameters.id);\r\n            break;\r\n          default:\r\n            break; // do nothing\r\n        }\r\n        this.$rootScope.$evalAsync(() => {\r\n          this.$location.path(\"/\");\r\n        });\r\n\r\n      });\r\n    }\r\n  }\r\n\r\n  private getReturnUrlOnboardingParameters() {\r\n    let url = this.$location.url();\r\n    if (url.indexOf(\"/onboarding/\") !== 0) {\r\n      url = this.readTokenFromUrl(\"url=\");\r\n      if (!url || url.indexOf(\"/onboarding/\") !== 0) {\r\n        return null;\r\n      }\r\n    }\r\n    // onboarding/company/xyz\r\n    // use regex...\r\n    const params = url.substr(\"/onboarding/\".length).split(\"/\");\r\n    if (params.length < 2) {\r\n      return;\r\n    }\r\n    const onboardingType = params[0];\r\n    const id = params[1].split(\"&\")[0];\r\n    return {\r\n      onboardingType,\r\n      id,\r\n    };\r\n  }\r\n\r\n  private readTokenFromUrl(key: string): string {\r\n    // shoud use regex...\r\n    const url = this.$location.url();\r\n    const start = url.toLowerCase().indexOf(key);\r\n    if (start >= 0) {\r\n      const end = url.indexOf(\"&\", start);\r\n      return end >= 0\r\n        ? url.substring(start + key.length, end)\r\n        : url.substring(start + key.length);\r\n    }\r\n    return null;\r\n  }\r\n\r\n  private init() {\r\n    this.$rootScope.$on(\"$locationChangeStart\", () => {\r\n      this.launchReturnUrlOnboarding();\r\n    });\r\n  }\r\n}\r\n","import { BrandListItem } from \"@salaxy/core\";\r\n\r\nimport { SessionService } from \"./SessionService\";\r\nimport { EditDialogKnownActions, EditDialogResult } from \"./ui\";\r\nimport { UiHelpers } from \"./ui/UiHelpers\";\r\n\r\n/**\r\n * Provides methods for managing the Primary partner,\r\n * which is primary source of service in payroll matters.\r\n * Typically, this would be customer's primary Accounting company.\r\n */\r\nexport class PartnerService {\r\n\r\n  /**\r\n   * For NG-dependency injection.\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"SessionService\", \"UiHelpers\"];\r\n\r\n  /** Skin that is currently in use as a temporary override (for preview purposes) or null if default skin is used. */\r\n  public overrideSkin: string;\r\n\r\n  /** Partner id that is currently in use as a temporary override (for preview purposes) or null if real id used. */\r\n  public overridePartnerId: string;\r\n\r\n  /**\r\n   * Creates a new instance of the PartnerService with dependency injection.\r\n   */\r\n  constructor(private sessionService: SessionService, private uiHelpers: UiHelpers) {\r\n  }\r\n\r\n  /**\r\n   * Shows a dialog for brand selection.\r\n   * The result may be \"ok\" for selected brand or \"set-default\" for reset to original brand.\r\n   */\r\n  public showBrandSelection() : Promise<EditDialogResult<BrandListItem>> {\r\n    const item: {\r\n      brand: BrandListItem\r\n    } = {\r\n      brand: null\r\n    };\r\n    return this.uiHelpers.openEditDialog(\"salaxy-components/modals/settings/BrandSelection.html\", item, null).then((dialog) => {\r\n      const result: EditDialogResult<BrandListItem> = {\r\n        action: dialog.action,\r\n        hasChanges: dialog.hasChanges,\r\n        logic: dialog.logic,\r\n        result: dialog.result,\r\n        item: dialog.result == EditDialogKnownActions.Ok ? dialog.item.brand : null,\r\n      };\r\n      return result;\r\n    });\r\n  }\r\n\r\n\r\n  /**\r\n   * Shows a dialog for switching the CSS.\r\n   */\r\n   public showSwitchCss(): void {\r\n     this.showBrandSelection().then((dialog) => {\r\n      if (dialog.result == EditDialogKnownActions.Ok) {\r\n        this.overrideSkin = dialog.item.data.skin;\r\n        this.overridePartnerId = dialog.item.id;\r\n        this.sessionService.switchCss(dialog.item.data.skin);\r\n      } else if (dialog.result == \"set-default\") {\r\n        this.overrideSkin = null;\r\n        this.overridePartnerId = null;\r\n        this.sessionService.switchCss(null);\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Temporary method only used in development\r\n   * Shows a dialog for switching the CSS.\r\n   */\r\n  public showSwitchCssDev(): void {\r\n    this.showBrandSelection().then((dialog) => {\r\n     if (dialog.result == EditDialogKnownActions.Ok) {\r\n       this.overrideSkin = dialog.item.data.skin;\r\n       this.overridePartnerId = dialog.item.id;\r\n       this.sessionService.switchCss(dialog.item.data.skin, true);\r\n     } else if (dialog.result == \"set-default\") {\r\n       this.overrideSkin = null;\r\n       this.overridePartnerId = null;\r\n       this.sessionService.switchCss(null, true);\r\n     }\r\n   });\r\n }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { AccountingReportTable, AccountingReportTableType, calcReportType, Calculation, PeriodType, Report, reportPartial, Reports, ReportsLogic, ReportType } from \"@salaxy/core\";\r\n\r\nimport { SessionService } from \"./SessionService\";\r\nimport { UiHelpers } from \"./ui\";\r\n\r\n/**\r\n * Methods for viewing and later also generating different reports.\r\n */\r\nexport class ReportsService {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$rootScope\", \"SessionService\", \"UiHelpers\", \"Reports\", \"$sce\"];\r\n\r\n  /**\r\n   * Convenience property for navigation controls to set a current report type.\r\n   * Checked, when getReports is called with null or \"current\"\r\n   */\r\n  public currentReportType: ReportType = null;\r\n\r\n  /** Cache for reports-by-type as generated on the server */\r\n  private reportMetadataCache: { owner?: string, [key:string]: any} = {};\r\n\r\n  /**\r\n   * Creates a new instance of ReportsService\r\n   * @param $rootScope - Angular rootscope.\r\n   * @param sessionService - Session service notifies when the user is known to be authenticated.\r\n   * @param uiHelpers - Salaxy ui helpers service.\r\n   * @param reportsApi - The Reports API that is used to communicating with the server.\r\n   * @param $sce - $sce is a service that provides Strict Contextual Escaping services to AngularJS\r\n   */\r\n  constructor(\r\n    $rootScope: angular.IRootScopeService,\r\n    private sessionService: SessionService,\r\n    private uiHelpers: UiHelpers,\r\n    private reportsApi: Reports,\r\n\r\n    private $sce: angular.ISCEService,\r\n  ) {\r\n    this.refresh();\r\n\r\n    sessionService.subscribe($rootScope, () => {\r\n      this.refresh();\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Clear metadata cache.\r\n   */\r\n  public refresh() {\r\n    if (this.sessionService.isSessionChecked && this.sessionService.isAuthenticated) {\r\n      const owner = this.sessionService.session.currentAccount.owner;\r\n      if (this.reportMetadataCache.owner != owner){\r\n        this.reportMetadataCache = { owner };\r\n      }\r\n    } else {\r\n      this.reportMetadataCache = {};\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Gets a list of reports (metadata only) filtered by a report type.\r\n   * @param type - Type of report. See type (string enumeration) for possible values.\r\n   * Also supports value \"current\" for showing reports defined by currentReportType.\r\n   * @returns A Promise with result data (<Report[]) if dataset not fetched, else the fetched dataset\r\n   */\r\n  public getReports(type: ReportType | \"current\"): Promise<Report[]> | Report[] {\r\n    if (!type || type === \"current\") {\r\n      type = this.currentReportType;\r\n    }\r\n    if (!type || type as any === \"undefined\") {\r\n      return [];\r\n    }\r\n    let list = this.reportMetadataCache[type];\r\n    if (!list) {\r\n      list = [];\r\n      this.reportMetadataCache[type] = [];\r\n      return this.reportsApi.getReportsByType(type).then((result) => {\r\n        this.reportMetadataCache[type] = result;\r\n        return result;\r\n      });\r\n    }\r\n    return list;\r\n  }\r\n\r\n  /**\r\n   * Gets a link URL for a yearly report. This is a full link with token and absolute URL.\r\n   * @param type - Type of the report must be one of the yearly reports\r\n   * @param year - Year for the report\r\n   * @param id - Worker ID for those reports that are specific to one Worker.\r\n   * @param id2 - Second Worker ID for those reports that have two Workers in one report\r\n   * @returns Yearly report URL string\r\n   */\r\n  public getYearlyReportUrl(type: ReportType, year: number, id?: string, id2?: string): string {\r\n    return this.sessionService.getServerAddress()\r\n      + ReportsLogic.getYearlyReportUrl(type, year, this.sessionService.getCurrentToken(), id, id2);\r\n  }\r\n\r\n\r\n  /**\r\n   * Gets a. URL for a calculation pdf.\r\n   * If report has not been saved (ID is null), returns null.\r\n   * @param reportType - Type of report\r\n   * @param calcId - Identifier of the calculation. This method requires that the calculation has been saved.\r\n   * @param inline - If true, the Content-Disposition header is returned with inline parameter.\r\n   * @returns Url for specified report\r\n   */\r\n  public getPdfUrlForCalc(reportType: calcReportType, calcId: string, inline = false): string {\r\n    if (!calcId) {\r\n      return null;\r\n    }\r\n    return this.sessionService.getServerAddress()\r\n      + ReportsLogic.getCalcPdfUrl(reportType, calcId, inline, this.sessionService.getCurrentToken());\r\n  }\r\n\r\n  /**\r\n   * Gets an URL for pdf report for one or more calculations.\r\n   * @param type - Type of report\r\n   * @param ids - Identifiers of the calculations. This method requires that the calculations have been saved.\r\n   * @param inline - If true, the Content-Disposition header is returned with inline parameter.\r\n   * @returns Url for specified report\r\n   */\r\n   public getPdfUrlForCalcs(type: \"salarySlip\" | \"employerReport\" | \"paymentReport\", ids: string[], inline = false): string {\r\n    if (!ids || ids.length === 0) {\r\n      return null;\r\n    }\r\n\r\n    return this.sessionService.getServerAddress() +\r\n    `/v03/api/reports/assure-pdf/${type}?ids=${ids.join(\"&ids=\")}&disposition=${inline ? \"inline\" : \"attachment\"}&access_token=${encodeURIComponent(this.sessionService.getCurrentToken())}`;\r\n  }\r\n\r\n  /**\r\n   * Show a report modal (a preview modal dialog) for a given calculation.\r\n   * The calculation may not be stored to backend. I.e. this reporting method is available also to\r\n   * non-authenticated users unlike the more resource intensive methods that generate PDF-files and require CRUD rights.\r\n   * @param reportType - Type of the report to show.\r\n   * @param calculation - Calculation to show in the report.\r\n   * @param view - The default view shown in the UI: \"page1\" (default), \"partial\" or \"full\".\r\n   * @param preview - If true, adds the preview watermark to the report.\r\n   */\r\n  public showReportModalForCalc(reportType: calcReportType, calculation: any, view: \"partial\" | \"page1\" | \"full\" = \"page1\", preview = false): void {\r\n\r\n    const calcs: Calculation[] = [calculation];\r\n\r\n    const data = {\r\n      reportType,\r\n      calcs,\r\n      view,\r\n      preview,\r\n    };\r\n\r\n    this.uiHelpers.showDialog(\r\n      \"salaxy-components/modals/calc/CalcReports.html\",\r\n      null,\r\n      data,\r\n      null,\r\n      \"xl\",\r\n      true);\r\n  }\r\n\r\n  /**\r\n   * Gets the monthly / quarterly/ yearly accounting data for the current account.\r\n   * @param refDate - Reference date for the period. Please note that even if the date is not the first day of the given period, the entire period is returned.\r\n   * @param tableType  - Accounting table type.\r\n   * @param periodType - Month, quarter, year or a custom period. The custom period requires endDate. Default value is the month.\r\n   * @param endDate - End date for the period. Required only for the custom period.\r\n   * @returns A Promise with result data (Raw data for accounting purposes).\r\n   */\r\n  public getAccountingReportTableForPeriod(refDate: string, tableType: AccountingReportTableType = AccountingReportTableType.Classic, periodType: PeriodType = PeriodType.Month, endDate: string = null): Promise<AccountingReportTable> {\r\n    return this.reportsApi.getAccountingReportTableForPeriod(refDate, tableType, periodType, endDate);\r\n  }\r\n\r\n  /**\r\n   * Experimental: Gets the accounting report based on given set of calculations.\r\n   * @param calculationIds - Calculations that are the bases for the report.\r\n   * @param tableType  - Accounting table type.\r\n   * @returns Account report based on the calculations.\r\n   * @ignore\r\n   */\r\n  public getAccountingReportTableForCalculationIds(calculationIds: string[], tableType: AccountingReportTableType = AccountingReportTableType.Classic): Promise<AccountingReportTable> {\r\n    return this.reportsApi.getAccountingReportTableForCalculationIds(calculationIds, tableType);\r\n  }\r\n\r\n  /**\r\n   * Experimental: Gets the accounting report based on given set of calculations.\r\n   * @param calculations - Calculations that are the bases for the report.\r\n   * @param tableType  - Accounting table type.\r\n   * @returns Account report based on the calculations.\r\n   * @ignore\r\n   */\r\n  public getAccountingReportTableForCalculations(calculations: Calculation[], tableType: AccountingReportTableType = AccountingReportTableType.Classic): Promise<AccountingReportTable> {\r\n    return this.reportsApi.getAccountingReportTableForCalculations(calculations, tableType);\r\n  }\r\n\r\n  /**\r\n   * Gets an HTML report based on Calculation ID and runs it through $sce.\r\n   * @param reportType - Type of the report to fetch. See the HtmlReportType enumeration for possible values.\r\n   * @param calculationId - GUID for the calculation\r\n   * @returns A Promise with result HTML - already run through $sce.\r\n   */\r\n  public getReportHtmlById(reportType: reportPartial, calculationId: string): Promise<any> {\r\n    return this.reportsApi.getReportHtmlById(reportType, calculationId).then((html) => {\r\n      return this.$sce.getTrustedHtml(html);\r\n    });\r\n  }\r\n}\r\n","import { SettingsService } from \"./SettingsService\";\r\nimport { CalcRowConfig, CalcRowsLogic, CalculationRowCategories, CalculationRowSource, CalculationRowType, RowTypeDefinition, UserDefinedRow, Years } from \"@salaxy/core\";\r\nimport { SessionService } from \"./SessionService\";\r\n\r\n/**\r\n * Provides access to the row types including the company specific custom row types.\r\n */\r\nexport class RowTypeService {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"SettingsService\", \"SessionService\"];\r\n\r\n  /** A key that signals when the settings were last updated => Used by downstream caches to refresh.  */\r\n  public timestamp: string;\r\n\r\n\r\n  /** Cached version of the CalcRowsLogic */\r\n  private _logic?: CalcRowsLogic;\r\n\r\n  /**\r\n   * Creates a new instance of RowTypeService\r\n   */\r\n  constructor(private settingsService: SettingsService, private session: SessionService) {\r\n  }\r\n\r\n  /**\r\n   * Gets a cached version of CalcRowsLogic with current settings (if available).\r\n   */\r\n  public get logic(): CalcRowsLogic {\r\n    if (this.session.isInRole(\"household\")) {\r\n      if (!this._logic) {\r\n        this.refresh();\r\n        this._logic = new CalcRowsLogic(\"household\");\r\n      }\r\n      return this._logic;\r\n    }\r\n    if (!this.isReady) {\r\n      // Just provide dynamic, should not neede to be cached.\r\n      return new CalcRowsLogic(\"company\");\r\n    }\r\n    if (!this._logic) {\r\n      this.refresh();\r\n      this._logic = new CalcRowsLogic(this.settingsService.current);\r\n    }\r\n    return this._logic;\r\n  }\r\n\r\n  /** Clears the cache and reloads the row types (from settings service singleton, not all the way from the server). */\r\n  public refresh(): void {\r\n    this._logic = null;\r\n    this.timestamp = new Date().toLocaleTimeString();\r\n  }\r\n\r\n  /**\r\n   * If true, the custom row types (currently in settings) have been loaded from the server.\r\n   */\r\n  public get isReady(): boolean {\r\n    return !!this.settingsService.current;\r\n  }\r\n\r\n  /**\r\n   * Gets a filtered list of row types configs\r\n   * @param group If specified, filters the configs by group (builtIn, custom).\r\n   */\r\n  public getConfigs(group?: \"builtIn\" | \"custom\", categories?: CalculationRowCategories[]): CalcRowConfig[] {\r\n    let result = this.configs;\r\n    if (group) {\r\n      result = result.filter((x) => x.group === group);\r\n    }\r\n    if (categories && categories.length > 0) {\r\n      result = result.filter((x) => categories.indexOf(x.category) >= 0);\r\n    }\r\n\r\n    const obsolete: string[] = [\r\n      CalculationRowType.PaidSickLeaveSalary,\r\n      CalculationRowType.PaidSickLeaveHourlySalary,\r\n      CalculationRowType.PaidSickLeaveMonthlySalary,\r\n      CalculationRowType.TrainingSalary,\r\n      CalculationRowType.TrainingHourlySalary,\r\n      CalculationRowType.TrainingMonthlySalary,\r\n      CalculationRowType.ServiceCharge\r\n    ];\r\n    result = result.filter((x) => !(obsolete.indexOf(x.name) >= 0));\r\n\r\n    // For pro and admin only\r\n    if (!this.session.isInSomeRole(\"pro,admin\")) {\r\n      result = result.filter((x) => x.name != CalculationRowType.Service);\r\n    }\r\n\r\n    // For bizconfigs only\r\n    if (!this.session.isInRole(\"bizConfigs\")) {\r\n      result = result.filter((x) => x.name != CalculationRowType.Script && x.name != CalculationRowType.PayStats);\r\n    }\r\n\r\n    return result;\r\n  }\r\n\r\n  private listCache: {\r\n    /** Cache key */\r\n    key: string,\r\n    /** Cache value */\r\n    value: CalcRowConfig[],\r\n  } = null;\r\n\r\n  /** Gets a cached list of all configs (even the ones that should typically be hidden from the list by role or because they are obsolete). */\r\n  public get configs(): CalcRowConfig[] {\r\n    if (!this.listCache || this.listCache.key !== this.timestamp) {\r\n      const value = this.logic.getRowConfigs();\r\n      this.listCache = { key: this.timestamp, value };\r\n    }\r\n    return this.listCache.value;\r\n  }\r\n\r\n  /** Gets the editble rows collection. */\r\n  public get allCustomRows(): RowTypeDefinition[] {\r\n    return this.settingsService.current?.calc.salaryDefaults as RowTypeDefinition[] ?? [];\r\n  }\r\n\r\n  /**\r\n   * Gets the configuration for a row: May be built-in or custom row type..\r\n   * @param row Row for which to get the configuration.\r\n   * @returns A configuration if found, otherwise undefined.\r\n   */\r\n  public getConfig(row: UserDefinedRow): CalcRowConfig | undefined {\r\n    if (!row) {\r\n      return undefined;\r\n    }\r\n    if (row.source == CalculationRowSource.CustomRowtype) {\r\n      return (row as RowTypeDefinition).config as CalcRowConfig;\r\n    }\r\n    let result: CalcRowConfig;\r\n    if (row.type?.startsWith(\"/\")) {\r\n      result = this.logic.getRowConfigs().find((x) => x.type == row.type);\r\n      if (result) {\r\n        return result;\r\n      }\r\n      console.warn(`Unable to find the row based on the new type '${row.type}' => Fall back to rowType based resolve.`);\r\n    }\r\n\r\n    result = this.logic.getRowConfig(row.rowType);\r\n    if (!result) {\r\n      console.error(`Row type '${row.rowType}' not found in the row type definitions.`);\r\n    }\r\n    return result;\r\n  }\r\n\r\n  /**\r\n   * Deletes an item in the allCustomRows collection.\r\n   * This does not yet save the changes or even refresh the cache.\r\n   */\r\n  public deleteRow(row: RowTypeDefinition): void {\r\n    const index = this.allCustomRows.indexOf(row);\r\n    if (index >= 0) {\r\n      this.allCustomRows.splice(index, 1);\r\n    }\r\n  }\r\n\r\n  /** Saves the current, potentitally modified set of custom rows. */\r\n  public async save(): Promise<void> {\r\n    this.settingsService.saveWithoutSessionCheck();\r\n    this.refresh();\r\n  }\r\n\r\n  /**\r\n   * Call this method when a new row is created to apply the default values.\r\n   */\r\n  public applyDefaultsToNewRow(row: UserDefinedRow, salaryDate: string): void {\r\n    if (!row || !row.rowType) {\r\n      return;\r\n    }\r\n    const config = this.getConfig(row);\r\n    if (config.amount.default) {\r\n      row.count = config.amount.default;\r\n    }\r\n    if (config.price.default) {\r\n      row.price = config.price.default;\r\n    }\r\n\r\n    const specialKnownRowTypes = this.specialKnownRowTypesAtSalaryDate(salaryDate);\r\n    if (specialKnownRowTypes[config.name]) {\r\n      row.price = specialKnownRowTypes[config.name];\r\n    }\r\n\r\n    if (config.group == \"custom\") {\r\n      const customRow = this.allCustomRows.find((x) => x.source == CalculationRowSource.CustomRowtype && x.type == config.type);\r\n      if (customRow) {\r\n        //Set message explicitly because the report rendering does not have access to company specific custom rows (yet).\r\n        if(config.label) {\r\n          row.message = config.label;\r\n        }\r\n        if(customRow.message) {\r\n          row.message = customRow.message;\r\n        }\r\n        if (customRow.count) {\r\n          row.count = customRow.count;\r\n        }\r\n        if (customRow.price) {\r\n          row.price = customRow.price;\r\n        }\r\n        if(customRow.unit) {\r\n          row.unit = customRow.unit;\r\n        }\r\n        if(customRow.accounting) {\r\n          row.accounting = customRow.accounting;\r\n        }\r\n        if(customRow.data) {\r\n          row.data = customRow.data;\r\n        }\r\n      }\r\n    }\r\n  }\r\n\r\n  private specialKnownRowTypesAtSalaryDate(salaryDate): { [key: string]: number } {\r\n    const yearlyNumbers = Years.getYearlyChangingNumbers(salaryDate ?? \"today\");\r\n    return {\r\n      dailyAllowance: yearlyNumbers.sideCosts.taxFreeDailyAllowance,\r\n      dailyAllowanceHalf: yearlyNumbers.sideCosts.taxFreeDailyHalfAllowance,\r\n      mealCompensation: yearlyNumbers.sideCosts.taxFreeMealAllowance,\r\n    };\r\n  }\r\n\r\n}","import angular from \"angular\";\r\n\r\nimport {\r\n  AccountBase,\r\n  Accounts,\r\n  Ajax,\r\n  AppStatus,\r\n  Arrays,\r\n  Avatar,\r\n  CompanyAccount,\r\n  Configs,\r\n  Language,\r\n  OAuthSalaxyAuthorizeMode,\r\n  PaymentChannel,\r\n  PersonAccount,\r\n  Role,\r\n  RoleLogic,\r\n  Session,\r\n  SystemRole,\r\n  Token,\r\n  Translations,\r\n  UserSession,\r\n  Workers,\r\n  InvoicesLogic,\r\n  Dates\r\n} from \"@salaxy/core\";\r\nimport { AlertService } from \"./ui\";\r\n\r\n/**\r\n * Helps in managing the login process and provides information of the current session\r\n */\r\nexport class SessionService {\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"$rootScope\",\r\n    \"Session\",\r\n    \"Accounts\",\r\n    \"$window\",\r\n    \"$location\",\r\n    \"AjaxNg1\",\r\n    \"$timeout\",\r\n    \"AlertService\",\r\n    \"Workers\",\r\n    \"$locale\"\r\n  ];\r\n\r\n  /** If true, the user is authenticated */\r\n  public isAuthenticated: boolean;\r\n\r\n  /** If true, the session has been checked from the server */\r\n  public isSessionChecked: boolean;\r\n\r\n  /** If true, the session call is progressing  */\r\n  public isSessionChecking: boolean;\r\n\r\n  /** Avatar to show in the login screen */\r\n  public avatar: Avatar;\r\n\r\n  /** The full session objcet */\r\n  public session: UserSession;\r\n\r\n  /** The person account object if the currently selected account is a person */\r\n  public personAccount: PersonAccount = null;\r\n\r\n  /** The company account object if the currently selected account is a company */\r\n  public companyAccount: CompanyAccount = null;\r\n\r\n  /** Sign in error */\r\n  public signInError: string;\r\n\r\n  /** Sign in error description */\r\n  public signInErrorDescription: string;\r\n\r\n  /** Sign in error page url */\r\n  public signInErrorUrl: string;\r\n\r\n  /** Partner site */\r\n  public partnerSite: string;\r\n\r\n  /**\r\n   * Application specific roles that are set on the client (browser code)\r\n   * as opposed to normal server-side defined roles.\r\n   */\r\n  public clientRoles: string[] = [];\r\n\r\n  private _isLoading: boolean;\r\n  public workerLangs: { [key: string]: Language } = {};\r\n  private static SKIN_SESSION_STORAGE = \"salaxy.skin\";\r\n\r\n  constructor(\r\n    private $rootScope: angular.IRootScopeService,\r\n    private sessionApi: Session,\r\n    private accountApi: Accounts,\r\n    private $window: angular.IWindowService,\r\n    private $location: angular.ILocationService,\r\n    private ajax: Ajax,\r\n\r\n    private $timeout: angular.ITimeoutService,\r\n    private alertService: AlertService,\r\n    private workers: Workers,\r\n\r\n    private $locale: any,\r\n  ) {\r\n    this.subscribeToLocationChange();\r\n  }\r\n\r\n  /**\r\n   * Initializes the session service.\r\n   * Note that the session loading will currently begin already in constructor.\r\n   */\r\n  public init(): void {\r\n    this.alertService.init(); // This should be done automatically in constructor, but we make sure here so that there is an explicit reference.\r\n  }\r\n\r\n  /**\r\n   * Controllers can subscribe to changes in service data using this method.\r\n   * Read more about the pattern in: http://www.codelord.net/2015/05/04/angularjs-notifying-about-changes-from-services-to-controllers/\r\n   * @param scope - Controller scope for the subscribing controller (or directive etc.)\r\n   * @param callback - The event listener function. See $on documentation for details\r\n   */\r\n  public subscribe(scope: angular.IScope, callback: (event: angular.IAngularEvent, ...args: any[]) => any): void {\r\n    const handler = this.$rootScope.$on(\"session-service-event\", callback);\r\n    scope.$on(\"$destroy\", handler);\r\n  }\r\n\r\n  /**\r\n   * Services can subscribe to this event to be notified when it is known that there is an authenticated session\r\n   * (as opposed to anonymous session). Uses the same pattern as subscribe.\r\n   * @param scope - Controller scope for the subscribing controller (or directive etc.)\r\n   * @param callback - The event listener function. See $on documentation for details\r\n   */\r\n  public onAuthenticatedSession(scope: angular.IScope, callback: (event: angular.IAngularEvent, ...args: any[]) => any): void {\r\n    const handler = this.$rootScope.$on(\"session-auth-session-event\", callback);\r\n    scope.$on(\"$destroy\", handler);\r\n  }\r\n\r\n  /**\r\n   * If true, the session is loading: Session, i18n files, service model or something else\r\n   * that may break the entire user interface is (re)loading: User interface should show a loader.\r\n   * Note that isSessionChecking overrides the set value in getter.\r\n   */\r\n  public get isLoading(): boolean {\r\n    return this._isLoading || this.isSessionChecking;\r\n  }\r\n  public set isLoading(value: boolean) {\r\n    this._isLoading = value;\r\n  }\r\n\r\n  /** If true, the user is authenticated */\r\n  public getIsAuthenticated(): boolean {\r\n    return this.isAuthenticated;\r\n  }\r\n\r\n  /** If true, the session has been checked from the server */\r\n  public getIsSessionChecked(): boolean {\r\n    return this.isSessionChecked;\r\n  }\r\n\r\n  /** If true, the session call is progressing */\r\n  public getIsSessionChecking(): boolean {\r\n    return this.isSessionChecking;\r\n  }\r\n\r\n  /** Avatar to show in the login screen */\r\n  public getAvatar(): Avatar {\r\n    return this.avatar;\r\n  }\r\n\r\n  /** The full session objcet */\r\n  public getSession(): UserSession {\r\n    return this.session;\r\n  }\r\n\r\n  /** Gets either the Company account or PErson account depending of the type of the current account. */\r\n  public getCurrentAccount(): AccountBase {\r\n    return this.getCompanyAccount() || this.getPersonAccount();\r\n  }\r\n\r\n  /** Get the person account object if the currently selected account is a person */\r\n  public getPersonAccount(): PersonAccount {\r\n    return this.personAccount;\r\n  }\r\n\r\n  /** The company account object if the currently selected account is a company */\r\n  public getCompanyAccount(): CompanyAccount {\r\n    return this.companyAccount;\r\n  }\r\n\r\n  /** Gets the address for the API server where the session is connected */\r\n  public getServerAddress(): string {\r\n    return this.sessionApi.getServerAddress();\r\n  }\r\n\r\n  /**\r\n   * Returns current access token\r\n   */\r\n  public getCurrentToken(): string {\r\n    return this.ajax.getCurrentToken();\r\n  }\r\n\r\n  /**\r\n   * Checks whether the user is in a given role\r\n   * @param role - One of the known roles or role from server.\r\n   * You can also use exclamation mark for negative (e.g. \"!test\")\r\n   * @returns True if user is in the given role,\r\n   * or if given roles is null/empty.\r\n   */\r\n  public isInRole(role: SystemRole | Role | string): boolean {\r\n    return RoleLogic.isInRole(this.getSession(), this.getAppStatus(), role);\r\n  }\r\n\r\n  /**\r\n   * Checks if the user is in ANY of the roles.\r\n   * @param commaSeparatedRolesList - Array of roles or comma separated string containing role names.\r\n   * @returns True if user is in one of the given roles,\r\n   * or if given roles is null or an empty array.\r\n   */\r\n  public isInSomeRole(commaSeparatedRolesList: (SystemRole | Role | string)[] | string): any {\r\n    return RoleLogic.isInSomeRole(this.session, this.getAppStatus(), Arrays.assureArray(commaSeparatedRolesList));\r\n  }\r\n\r\n  /**\r\n   * Tests if the current account has ALL the given roles.\r\n   * @param accountRoles - Array of roles.\r\n   * @returns Returns true if the account has all the given roles,\r\n   * or if given roles is null or an empty array.\r\n   */\r\n  public isInAllRoles(accountRoles: (SystemRole | Role | string)[]): boolean {\r\n    return RoleLogic.isInAllRoles(this.session, this.getAppStatus(), accountRoles);\r\n  }\r\n\r\n  /** Posts a message to the parent window. The message is sent as salaxySessionEvent  */\r\n  public postMessageToParent(message: string) {\r\n    if (window.parent !== window && window.parent.postMessage) {\r\n      window.parent.postMessage({ salaxySessionEvent: message }, \"*\");\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Checks the current session from the server if user has token (either in-memory or in cookie)\r\n   * @returns A Promise with result data (UserSession)\r\n   */\r\n  public checkSession(): Promise<UserSession> {\r\n    this.isSessionChecking = true;\r\n    let token = this.ajax.getCurrentToken();\r\n    if (Token.validate(token) !== \"ok\") {\r\n      token = null;\r\n      this.ajax.setCurrentToken(token);\r\n    }\r\n\r\n    if (!token) {\r\n      this.isSessionChecked = true;\r\n      this.isAuthenticated = false;\r\n      this.avatar = null;\r\n      this.session = null;\r\n      this.setLanguageForSession();\r\n      this.companyAccount = null;\r\n      this.notify();\r\n      this.isSessionChecking = false;\r\n      return new Promise((resolve) => {\r\n        this.$timeout(() => {\r\n          resolve(null);\r\n        });\r\n      });\r\n    }\r\n\r\n    // Use always real partner css first in production\r\n    const cssUrl = this.resolveCss();\r\n    const isDev = (cssUrl?.startsWith(\"/dev-skins\"));\r\n    this.switchCss(cssUrl, isDev);\r\n\r\n    return this.sessionApi.getSession().then((result: UserSession) => {\r\n      return this.setSession(result);\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Sets the session to a session object that has already been fetched from the server.\r\n   * Note that the caller should also set the token to Ajax.\r\n   * @param session - Session object to set as current session.\r\n   */\r\n  public setSession(session: UserSession | undefined): UserSession {\r\n    this.isSessionChecking = false;\r\n    this.isSessionChecked = true;\r\n    if (session) {\r\n      this.isAuthenticated = session.isAuthorized;\r\n      this.avatar = session.avatar;\r\n      this.session = session;\r\n      this.setLanguageForSession();\r\n      if (this.session.isAuthorized) {\r\n        const entityType = (session.currentAccount as AccountBase).entityType;\r\n        if (entityType === \"company\") {\r\n          this.companyAccount = this.session.currentAccount;\r\n        } else if (entityType === \"person\") {\r\n          this.personAccount = this.session.currentAccount;\r\n        }\r\n        this.notify();\r\n        this.notifyAuthenticatedSession();\r\n        this.postMessageToParent(\"success\");\r\n        return this.session;\r\n      } else {\r\n        this.notify();\r\n        this.postMessageToParent(\"failure\");\r\n        return this.session;\r\n      }\r\n    } else {\r\n      this.isAuthenticated = false;\r\n      this.avatar = null;\r\n      this.session = null;\r\n      this.companyAccount = null;\r\n      this.notify();\r\n      this.postMessageToParent(\"failure\");\r\n      return session;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Switches the current web site usage role and refreshes the session.\r\n   * @param role - household or worker.\r\n   * @returns A Promise with result data (new role as string)\r\n   */\r\n  public switchRole(role: \"household\" | \"worker\"): Promise<\"household\" | \"worker\"> {\r\n    return this.accountApi.switchRole(role).then((result) => {\r\n      return this.checkSession().then(() => {\r\n        return result;\r\n      });\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Sends the browser to standard Sign-in page on Salaxy API server.\r\n   * @param redirectUrl - The URL where the user is taken after a successfull login\r\n   * @param role - Optional role (household, worker or company) for the situations where it is known - mainly for new users\r\n   * @param partnerSite Identifier of the partner or service model from which the login UI is fetched.\r\n   * @param urlPostfix Additional string that is added to the OAuth2 URL.\r\n   * Used in adding other parameters to the URL, e.g. \"&salaxy_language=en\"\r\n   */\r\n  public signIn(redirectUrl: string = null, role: string = null, partnerSite: string = null, urlPostfix: string = null): void {\r\n    this.authorize(redirectUrl, role, partnerSite, OAuthSalaxyAuthorizeMode.Sign_in, urlPostfix);\r\n  }\r\n\r\n  /**\r\n   * Sends the browser to standard signUp / register page on Salaxy API server.\r\n   * @param redirectUrl - The URL where the user is taken after a successfull login\r\n   * @param role - Optional role (household, worker or company) for the situations where it is known - mainly for new users\r\n   * @param partnerSite Identifier of the certified partner which should be granted access rights in account creation.\r\n   * Also sets SignIn dialog and onboarding wizard UI skin.\r\n   * @param urlPostfix Additional string that is added to the OAuth2 URL.\r\n   * Used in adding other parameters to the URL, e.g. \"&salaxy_language=en\"\r\n   */\r\n  public register(redirectUrl: string = null, role: string = null, partnerSite: string = null, urlPostfix: string = null): void {\r\n    this.authorize(redirectUrl, role, partnerSite, OAuthSalaxyAuthorizeMode.Sign_up, urlPostfix);\r\n  }\r\n\r\n  /**\r\n   * Sends the user to the Sign-out page\r\n   * @param redirectUrl - URL where user is redirected after log out.\r\n   * Must be absolute URL. Default is the root of the current server.\r\n   */\r\n  public signOut(redirectUrl?: string): void {\r\n    this.ajax.setCurrentToken(null);\r\n\r\n    const getOrigin = () =>\r\n      window.location.protocol +\r\n      \"//\" +\r\n      window.location.hostname +\r\n      (window.location.port ? \":\" + window.location.port : \"\");\r\n\r\n    const regEx = new RegExp(/www2\\./, \"ig\");\r\n    redirectUrl = (redirectUrl || getOrigin()).replace(regEx, \"www.\");\r\n    this.checkSession().then(() => {\r\n      this.$window.location.href = redirectUrl;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Returns true if the current authenticated user has signed the contract.\r\n   */\r\n  public isSigningOk(): boolean {\r\n    if (this.session\r\n      && this.session.currentAccount\r\n      && this.session.currentAccount.identity.contract\r\n      && this.session.currentAccount.identity.contract.isSigned) {\r\n      return true;\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /**\r\n   * Returns true if the current authenticated user has signed the contract\r\n   * OR if the user does not have session OR if user is anonymous.\r\n   */\r\n  public checkAccountVerification(): boolean {\r\n    // Anon user cannot have contract, return always true\r\n    if (!this.session || !this.session.currentAccount) {\r\n      return true;\r\n    }\r\n    // Return true if session and signing\r\n    if (this.session.currentAccount.identity.contract\r\n      && this.session.currentAccount.identity.contract.isSigned) {\r\n      return true;\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /**\r\n   * Gets the application status that supports the UserSession object by providing additional\r\n   * information about the status of fetching the session, data, expiration etc.\r\n   */\r\n  public getAppStatus(): AppStatus {\r\n    // TODO: We should probably add isTestData to Ajax, but that needs changes in all environments.\r\n    // Fetching from config should work fine in NG as is compatible with future changes.\r\n    let isTestData: boolean = null;\r\n    const config = Configs.current;\r\n    if (config && config.isTestData != null) {\r\n      isTestData = config.isTestData;\r\n    }\r\n\r\n    const clientRoles = angular.copy(this.clientRoles ?? []);\r\n    /*\r\n      if (clientRoles.indexOf(\"pro\") < 0 && this.parseRoleFromAccessToken(\"pro\")) {\r\n        clientRoles.push(\"pro\");\r\n      }\r\n      if (clientRoles.indexOf(\"admin\") < 0 && this.parseRoleFromAccessToken(\"admin\")) {\r\n        clientRoles.push(\"admin\");\r\n      }\r\n    */\r\n    return {\r\n      sessionCheckInProgress: this.getIsSessionChecking() || !this.getIsSessionChecked(),\r\n      clientRoles,\r\n      isTestData,\r\n    };\r\n  }\r\n\r\n  /**\r\n   * TODO: Encapsulate this functionality to Ui-customization service. MJ\r\n   *\r\n   * Switches the CSS link to partner-specific CSS.\r\n   * @param cssUrl URL for the CSS file. Typically, \"css/skins/${skin}.css\"\r\n   * @param useDevelopmentFolder If true, uses the local css file (development environment only).\r\n   * By default, uses the CDN.\r\n   */\r\n  public switchCss(cssUrl: string, useDevelopmentFolder = false) {\r\n    const linkId = \"salaxyMainCss\";\r\n    const link = document.getElementById(linkId) as HTMLLinkElement;\r\n    // If link id exists, we can customize the css\r\n    if (link) {\r\n      cssUrl = cssUrl || \"css/skins/palkkaus.css\";\r\n      if (useDevelopmentFolder) {\r\n        cssUrl = cssUrl.replace(\"css/skins\", \"/dev-skins\");\r\n      } else {\r\n        cssUrl = this.convertSkinPath(cssUrl || \"css/skins/palkkaus.css\");\r\n      }\r\n      if (link.href !== cssUrl) {\r\n        // Save the selected skin in session storage to survive over page reloads\r\n        if (this.isInRole(\"test\") && !this.isInRole(\"pro\")) {\r\n          window.sessionStorage.setItem(SessionService.SKIN_SESSION_STORAGE, cssUrl);\r\n        }\r\n        link.href = cssUrl;\r\n      }\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Resolves current css cdn url with following priority:\r\n   * 1. Url (https://test-yritys.palkkaus.fi/embedded.html?skin=emu#/)\r\n   * 2. Token (Token.parsePayload(token))\r\n   * @returns cdn url to css\r\n   */\r\n  public resolveCss(): string {\r\n    if (this.isInRole(\"test\")) {\r\n      const urlParams = new URLSearchParams(window.location.search);\r\n      if (urlParams.has(\"skin\")) {\r\n        return `https://cdn.salaxy.com/skins/bs5/${urlParams.get(\"skin\")}.css`;\r\n      }\r\n      if (urlParams.has(\"skin-dev\")) {\r\n        // skins with dynamic compile\r\n        return `/dev-skins/${urlParams.get(\"skin-dev\")}.css`;\r\n      }\r\n    }\r\n    const token = this.ajax.getCurrentToken();\r\n    return (this.isInRole(\"test\") && !this.isInRole(\"pro\")) ?\r\n      (window.sessionStorage.getItem(SessionService.SKIN_SESSION_STORAGE) ||\r\n        Token.parsePayload(token).account_partner_css)\r\n      :\r\n      Token.parsePayload(token).account_partner_css;\r\n  }\r\n\r\n  /**\r\n   * Parses name of current skin from cdn url\r\n   * @returns name of current skin\r\n   */\r\n  public getCurrentCss(): string {\r\n    const cssUrl = (document.getElementById(\"salaxyMainCss\") as HTMLLinkElement)?.href ||\r\n    (document.getElementById(\"salaxyForcedCss\") as HTMLLinkElement)?.href;\r\n    return cssUrl?.substring(cssUrl?.lastIndexOf(\"/\") + 1)?.replace(/\\.[^/.]+$/, \"\");\r\n  }\r\n\r\n  /**\r\n   * Get report lang\r\n   * @param workerId optional workerId to get worker\r\n   * @returns report lang\r\n   */\r\n  public getReportLang(workerId = null): Promise<Language> {\r\n    let lang = (this.session?.currentAccount as any)?.language ?? Language.Fi;\r\n    lang = lang === Language.Default ? Language.Fi : lang;\r\n    const params = new URLSearchParams(window.location.search);\r\n    if (params.has(\"lang\")) {\r\n      const langParam = params.get(\"lang\")?.toLowerCase() as Language;\r\n      if (langParam) {\r\n        lang = langParam;\r\n      }\r\n    }\r\n    if (!workerId) {\r\n      return Promise.resolve(lang);\r\n    }\r\n\r\n    // Check if workerId already exists in workerLangs\r\n    if (this.workerLangs[workerId]) {\r\n      return Promise.resolve(this.workerLangs[workerId]);\r\n    }\r\n    // Get worker with id (io)\r\n    return this.workers.getSingle(workerId).then((worker) => {\r\n      const workerLang = worker?.language ?? lang;\r\n      this.workerLangs[workerId] = workerLang === Language.Default ? lang : workerLang;\r\n      return this.workerLangs[workerId];\r\n    });\r\n  }\r\n\r\n  // TODO: This method should return an array of channels\r\n  /** Returns the owned payment channel for the current account. */\r\n  public getOwnedPaymentChannel(): PaymentChannel {\r\n\r\n    const channelAccounts = {\r\n      FI03POYA0003689675: PaymentChannel.AccountorGo, // Accountor\r\n      FI15POYA0008369224: PaymentChannel.FinagoSolo, // FinagoSolo\r\n      FI06POYT0009439335: PaymentChannel.Kevytyrittaja, // Kevytyrittaja\r\n      FI14POYA0028382282: PaymentChannel.Askelma, // Askelma\r\n      FI33POYB0024403824: PaymentChannel.Briox, // Briox\r\n      FI42POYT0025991058: PaymentChannel.Lemonaid, // LemonTree\r\n      FI71POYL0029361387: PaymentChannel.Laskupiste, // Laskupiste\r\n      FI43POY10010435606: PaymentChannel.PasseliMerit, // PasseliMerit\r\n      FI79POYA0034612101: PaymentChannel.Odoo, // Odoo\r\n      FI86POYF0022398945: PaymentChannel.Hausvise, // Festum\r\n      ... (Configs.current?.isTestData === true ? { FI11POYE0009680831: PaymentChannel.Ecom } : { FI44POY10009680831: PaymentChannel.Ecom }), // Ecom\r\n      ... (Configs.current?.isTestData === true ? { FI88POYP0010378082: PaymentChannel.Kompassi } : { FI15POYY0010378082: PaymentChannel.Kompassi }), // Kompassi\r\n      FI23POY10006460809: PaymentChannel.Domus, // Tietoaika\r\n      FI24POYH0021937564: PaymentChannel.Holvi, // Holvi\r\n      FI88POYT0025514542: PaymentChannel.TalenomOnline, // Talenom\r\n      FI53POYS0025543933: PaymentChannel.PalkkausWS, // SPL\r\n      FI51POYT0031925356: PaymentChannel.TalenomManual, // TalenomManual\r\n    };\r\n    if (this.session && this.session.currentAccount) {\r\n      return channelAccounts[this.session.currentAccount.id] || null;\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /**\r\n   * Does a \"soft refresh\" of the AngularJS user interface by setting isLoading flag to\r\n   * true and then false after digest loop has run. Layouts should implement this in a way\r\n   * that all views are destroyed and then recreated.\r\n   */\r\n  public refreshUi() {\r\n    this.isLoading = true;\r\n    this.$timeout(() => {\r\n      this.isLoading = false;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Sets the language of the session for the given language.\r\n   * Also loads the dictionary for the language if not already loaded.\r\n   * @param lang Language to set.\r\n   */\r\n  public setLanguage(lang: Language) {\r\n    if (!lang || lang === Language.Default) {\r\n      lang = Language.Fi;\r\n    }\r\n    this.isLoading = true;\r\n    Translations.loadLanguage(lang)\r\n      .then(() => {\r\n        Translations.setLanguage(lang as \"fi\" | \"en\" | \"sv\");\r\n        // TODO: This is unnecessary if the language is already loaded (Translations.loadedLanguages)\r\n        Translations.instance.setTerms(this.session?.settings?.partner?.serviceModel?.site?.texts);\r\n        // Override texts use by the components (not the entire culture) in the AngularJS locales\r\n        this.$locale.DATETIME_FORMATS.MONTH = Arrays.getRange(1, 12).map((x) => Translations.get(`SALAXY.ENUM.CalendarMonth.month${x}.label`));\r\n        this.$locale.DATETIME_FORMATS.SHORTDAY = [Translations.get(`SALAXY.ENUM.Weekday.day7.short`), ...Arrays.getRange(1, 6).map((x) => Translations.get(`SALAXY.ENUM.Weekday.day${x}.short`))];\r\n        this.refreshUi();\r\n      });\r\n  }\r\n  /** Parses origin url from $location*/\r\n  public getOrigin(): string {\r\n    let url = this.$location.absUrl();\r\n    // If not in root remove $location.path from $location.absUrl\r\n    if(this.$location.path() != \"/\") {\r\n      url = url.replace(this.$location.path(), \"\");\r\n    }\r\n    // If last character of url is /, remove\r\n    if(url.charAt(url.length - 1) == \"/\") {\r\n      url = url.slice(0, -1);\r\n    }\r\n    // If last character of url is #, remove\r\n    if (url.charAt(url.length - 1) == \"#\") {\r\n      url = url.slice(0, -1);\r\n    }\r\n    // Split url by / and if splits contains .html or .aspx remove it\r\n    const splits = url.split(\"/\");\r\n    if(splits[splits.length - 1].toLowerCase().includes(\".html\") || splits[splits.length - 1].toLowerCase().includes(\".aspx\")) {\r\n      url = url.replace(splits[splits.length - 1], \"\");\r\n    }\r\n    // if last char is not /, add it\r\n    if (url.charAt(url.length - 1) != \"/\") {\r\n      url = url + \"/\";\r\n    }\r\n\r\n    return url;\r\n  }\r\n\r\n  /**\r\n   * Determines whether the customer is a cfa customer.\r\n   * @returns A boolean value indicating whether the customer is a cfa customer.\r\n   */\r\n  public get isCfaCustomer(): boolean {\r\n    return !!this.session?.settings?.paymentChannels?.some((x) => InvoicesLogic.isCfa(x));\r\n  }\r\n\r\n\r\n  /** get kyc state */\r\n  public get kycState(): \"ignored\" | \"valid\" | \"expired\" | \"missing\" {\r\n    if (!this.isCfaCustomer) {\r\n      return \"ignored\";\r\n    }\r\n\r\n    // No kyc information\r\n    if (!this.session?.currentAccount?.identity?.kycUpdatedAt) {\r\n      return \"missing\";\r\n    }\r\n\r\n    // kyc expired/expires\r\n    if (Dates.isBefore(this.session.currentAccount.identity.kycUpdatedAt, Dates.add(Dates.getToday(), -10, \"month\"))) {\r\n      return \"expired\";\r\n    }\r\n\r\n    return \"valid\";\r\n  }\r\n\r\n  /** returns last updated at for kyc. */\r\n  public get kycUpdatedAt(): string {\r\n    return this.session?.currentAccount?.identity?.kycUpdatedAt;\r\n  }\r\n\r\n  /** returns expiration date for kyc. */\r\n  public get kycExpiresAt(): string {\r\n    const kycUpdatedAt = this.session?.currentAccount?.identity?.kycUpdatedAt;\r\n    if (!kycUpdatedAt) {\r\n      return \"\";\r\n    }\r\n    return Dates.add(Dates.asDate(kycUpdatedAt), 12, \"month\");\r\n  }\r\n\r\n  /**\r\n   * Parsers given roles from the access token.\r\n   * Returns the first found role from the list in order.\r\n   * @param roles Comma separated list of roles or array of roles.\r\n   */\r\n  private parseRoleFromAccessToken(roles: string | string[]): string {\r\n    if (!roles) {\r\n      return null;\r\n    }\r\n    const roleList = Arrays.assureArray(roles);\r\n    if (!roles.length) {\r\n      return null;\r\n    }\r\n\r\n    const token = this.ajax.getCurrentToken();\r\n    if (!token) {\r\n      return null;\r\n    }\r\n    const parsedToken = Token.parsePayload(token);\r\n    const scopes = (parsedToken.scope ?? \"\").split(\" \");\r\n    for (const role of roleList) {\r\n      switch (role) {\r\n        case \"pro\":\r\n          if (scopes.indexOf(\"pro:on_behalf_of\") > -1) {\r\n            return role;\r\n          }\r\n          break;\r\n        case \"admin\":\r\n          if (scopes.indexOf(\"admin:on_behalf_of\") > -1) {\r\n            return role;\r\n          }\r\n          break;\r\n      }\r\n    }\r\n    return null;\r\n  }\r\n\r\n  private notify(): void {\r\n    this.$rootScope.$emit(\"session-service-event\");\r\n  }\r\n\r\n  private notifyAuthenticatedSession() {\r\n    this.$rootScope.$emit(\"session-auth-session-event\");\r\n  }\r\n\r\n  /**\r\n   * Sends the browser to standard Sign-in page on Salaxy API server.\r\n   * @param redirectUrl The URL where the user is taken after a successfull login.\r\n   * @param role Optional role (household, worker or company) for the situations where it is known - mainly for new users.\r\n   * @param partnerSite The partner site is passed as client_id to the sign-in process.\r\n   * @param mode Salaxy login mode: \"sign_in\" or \"sign_up\".\r\n   * @param urlPostfix Additional string that is added to tha URL.\r\n   * Used in adding other parameters to the URL, e.g. \"&salaxy_language=en\"\r\n   */\r\n  private authorize(\r\n    redirectUrl: string = null,\r\n    role: string = null,\r\n    partnerSite: string = null,\r\n    mode: OAuthSalaxyAuthorizeMode = null,\r\n    urlPostfix: string = null,\r\n  ): void {\r\n    const config = Configs.current;\r\n    const partner = partnerSite || this.partnerSite || config?.partnerSite || \"unknown\";\r\n\r\n    if ((urlPostfix || \"\").indexOf(\"salaxy_skin\") === -1) {\r\n      const skin = this.getCurrentCss();\r\n      if (skin) {\r\n        urlPostfix = `${urlPostfix || \"\"}&salaxy_skin=${skin}`;\r\n      }\r\n    }\r\n    const url = this.sessionApi.getSignInAddress(redirectUrl, role, partner, mode, urlPostfix);\r\n    this.$window.location.href = url;\r\n  }\r\n\r\n  private readTokenFromUrl(key: string, path: string): string {\r\n    // use regex...\r\n    const start = path.toLowerCase().indexOf(key);\r\n    if (start >= 0) {\r\n      const end = path.indexOf(\"&\", start);\r\n      return end >= 0\r\n        ? path.substring(start + key.length, end)\r\n        : path.substring(start + key.length);\r\n    }\r\n    return null;\r\n  }\r\n\r\n  private checkSessionFromUrl() {\r\n    const url = this.$location.url();\r\n    const token = this.readTokenFromUrl(\"access_token=\", url);\r\n    if (token) {\r\n      this.ajax.setCurrentToken(token);\r\n      const removeTokensFromPath = ((tt: string[], p: string) => {\r\n        for (const t of tt) {\r\n          const rg = new RegExp(`\\\\b${t}\\\\=[^&]+&?`);\r\n          p = p.replace(rg, \"\");\r\n        }\r\n        return p;\r\n      });\r\n      const cleanPath = (path: string) => {\r\n        // remove trailing & and ?\r\n        path = path.replace(/[?&]$/, \"\").trim();\r\n        // remove trailing slash if not following hash, cannot use backward looking regex, not supported in Safari\r\n        if (path.endsWith(\"/\") && !path.endsWith(\"#/\")) {\r\n          path = path.replace(/\\/$/, \"\").trim();\r\n        }\r\n        return path;\r\n      };\r\n\r\n      this.$rootScope.$evalAsync(() => {\r\n        this.$location\r\n          .path(cleanPath(removeTokensFromPath([\"access_token\", \"token_type\", \"state\", \"expires_in\", \"scope\"], this.$location.path())))\r\n          .search(\"access_token\", null)\r\n          .search(\"token_type\", null)\r\n          .search(\"state\", null)\r\n          .search(\"expires_in\", null)\r\n          .search(\"scope\", null);\r\n      });\r\n      return this.checkSession();\r\n    } else {\r\n      const error = this.readTokenFromUrl(\"error=\", url);\r\n      if (error) {\r\n        const errorDescription =\r\n          this.readTokenFromUrl(\"error_description=\", url) || \"\";\r\n        const errorUri = this.readTokenFromUrl(\"error_uri=\", url) || \"\";\r\n        const state = this.readTokenFromUrl(\"state=\", url) || \"\";\r\n        this.signInError = decodeURIComponent(error);\r\n        this.signInErrorDescription = decodeURIComponent(errorDescription.replace(/\\+/g, \"%20\"));\r\n\r\n        this.$rootScope.$evalAsync(() => {\r\n          this.$location\r\n            .path(this.signInErrorUrl || \"/\")\r\n            .search(\"error\", decodeURIComponent(error.replace(/\\+/g, \"%20\")))\r\n            .search(\"error_description\", decodeURIComponent(errorDescription.replace(/\\+/g, \"%20\")))\r\n            .search(\"error_uri\", decodeURIComponent(errorUri.replace(/\\+/g, \"%20\")))\r\n            .search(\"state\", decodeURIComponent(state.replace(/\\+/g, \"%20\")));\r\n        });\r\n        return this.checkSession();\r\n      }\r\n    }\r\n    return Promise.resolve(null);\r\n  }\r\n\r\n  private subscribeToLocationChange() {\r\n    this.$rootScope.$on(\"$locationChangeStart\", () => {\r\n      this.checkSessionFromUrl().then(() => {\r\n        if (!this.isSessionChecked && !this.isSessionChecking) {\r\n          this.checkSession();\r\n        }\r\n      });\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Temporary fix to replace old skin paths \"ng1/css/something.css\" with the new monorepo\r\n   * style \"/skins/css/something.css\" until the skin paths are fixed at the source.\r\n   */\r\n  private convertSkinPath(path: string): string {\r\n    // Check if the path is null or already converted\r\n    if (!path || path.indexOf(\"skins/css/\") >= 0) {\r\n      return path;\r\n    }\r\n    // Convert to new format\r\n    return path ? \"https://cdn.salaxy.com/skins/bs5/\" + path.substr(path.lastIndexOf(\"/\") + 1) : path;\r\n  }\r\n\r\n  private setLanguageForSession(): void {\r\n    // Possibility to override the language in query string\r\n    const params = new URLSearchParams(window.location.search);\r\n    if (params.has(\"lang\")) {\r\n      const lang = params.get(\"lang\")?.toLowerCase() as Language;\r\n      if (lang) {\r\n        this.setLanguage(lang);\r\n        return;\r\n      }\r\n    }\r\n    if (this.session?.currentAccount && this.session.currentAccount.language) {\r\n      this.setLanguage(this.session.currentAccount.language);\r\n    }\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { AccountSettings, Ajax, CompanyAccountSettings, LegalEntityType } from \"@salaxy/core\";\r\nimport { ReportOptions } from \"@salaxy/reports\";\r\nimport { SessionService } from \"./SessionService\";\r\nimport { EditDialogResult, UiHelpers } from \"./ui\";\r\n\r\n/**\r\n * Provides singleton for the full editable settings object:\r\n * Mainly for editing, but may also be used by other parts that require access to settings.\r\n * This implementation is for Company employers. There may be a specialized Household employers and/or Worker, Pro version later.\r\n */\r\nexport class SettingsService {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$rootScope\", \"SessionService\", \"AccountSettings\", \"UiHelpers\", \"AjaxNg1\", \"$timeout\"];\r\n\r\n  /**\r\n   * The current settings object or null if the object is still being loaded.\r\n   * The loading starts as soon as the settings service is loaded in the first controller.\r\n   */\r\n  public current: CompanyAccountSettings;\r\n\r\n  private reportOptions: ReportOptions;\r\n\r\n  private _reportOptionsLoading = false;\r\n\r\n  constructor($rootScope: angular.IRootScopeService, private sessionService: SessionService, private accountSettings: AccountSettings, private uiHelpers: UiHelpers, private ajax: Ajax, private $timeout: angular.ITimeoutService) {\r\n    this.refresh();\r\n\r\n    sessionService.subscribe($rootScope, () => {\r\n      this.refresh();\r\n    });\r\n  }\r\n\r\n  /** Saves the session and does the refresh, but not a complete sessionService.checkSession() as in default save().  */\r\n  public saveWithoutSessionCheck(): Promise<CompanyAccountSettings> {\r\n    return this.accountSettings.save(this.current).then((result) => {\r\n      this.current = result;\r\n      return result;\r\n    });\r\n  }\r\n\r\n  /** Refreshes the current settings from the server. */\r\n  public refresh() {\r\n    if (this.sessionService.isSessionChecked && this.sessionService.isAuthenticated) {\r\n      const owner = this.sessionService.session.currentAccount.owner;\r\n      if (this.current?.owner != owner){\r\n        this.reportOptions = null;\r\n        this.current = null;\r\n        this._reportOptionsLoading = false;\r\n      }\r\n      return this.accountSettings.get().then((result) => {\r\n        this.current = result;\r\n        return this.current;\r\n      });\r\n    } else {\r\n      this.reportOptions = null;\r\n      this.current = null;\r\n      this._reportOptionsLoading = false;\r\n    }\r\n  }\r\n\r\n  /** Saves the current settings back to storage. */\r\n  public save(): Promise<CompanyAccountSettings> {\r\n    return this.accountSettings.save(this.current).then((result) => {\r\n      this.current = result;\r\n      return this.sessionService.checkSession().then(() => {\r\n        return result;\r\n      });\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Creates a new IR certificate.\r\n   * @param transferId Transfer ID for the IR certificate.\r\n   * @param transferPassword One time transfer password for the IR certificate.\r\n   * @returns Information about the created IR certificate.\r\n   */\r\n  public createIrCertificate(transferId: string, transferPassword: string): Promise<any> {\r\n    return this.accountSettings.createIrCertificate(transferId, transferPassword);\r\n  }\r\n\r\n  /**\r\n   * Renews an existing IR certificate.\r\n   * @returns Information about the created IR certificate.\r\n   */\r\n  public renewIrCertificate(): Promise<any> {\r\n    return this.accountSettings.renewIrCertificate();\r\n  }\r\n\r\n  /**\r\n   * Gets the detials of the existing IR certificate or null if no certificate exists.\r\n   * @returns Information about the current IR certificate.\r\n   */\r\n  public getIrCertificate(): Promise<any> {\r\n    return this.accountSettings.getIrCertificate();\r\n  }\r\n\r\n  /** Sets the eInvoice address using a dialog */\r\n  public selectEInvoiceAddress(address: { eInvoiceReceiver?: string, eInvoiceIntermediator?: string }): Promise<EditDialogResult<any>> {\r\n    const item = {\r\n      receiver: address.eInvoiceReceiver,\r\n      intermediator: address.eInvoiceIntermediator,\r\n    };\r\n    const logic = {\r\n      title: \"Hae osoite Y-tunnuksella\",\r\n      officialId: this.sessionService.session.currentAccount.identity.officialId,\r\n      isLoading: false,\r\n      addresses: [],\r\n      isSelected: (current, item) => {\r\n        return current.receiver === item.receiver;\r\n      },\r\n      isAnySelected: (current) => {\r\n        return logic.addresses.some((x) => logic.isSelected(current, x));\r\n      },\r\n      setCurrent: (current, item) => {\r\n        current.receiver = item.receiver;\r\n        current.intermediator = item.intermediator;\r\n      },\r\n      search: () => {\r\n        logic.isLoading = true;\r\n        const path = `/payments/einvoice/receiver?officialId=${encodeURIComponent(logic.officialId)}`;\r\n        this.ajax.getJSON(path).then((items) => {\r\n          logic.addresses = items;\r\n          logic.isLoading = false;\r\n        });\r\n      },\r\n    };\r\n    logic.search();\r\n    return this.uiHelpers.openEditDialog(\"salaxy-components/modals/account/EInvoiceAddressList.html\", item, logic).then((result) => {\r\n\r\n      if (result.action === \"ok\") {\r\n        address.eInvoiceReceiver = result.item.receiver;\r\n        address.eInvoiceIntermediator = result.item.intermediator;\r\n      } else if (result.action === \"reset\") {\r\n        address.eInvoiceReceiver = null;\r\n        address.eInvoiceIntermediator = null;\r\n      }\r\n      return result;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Gets ReportOptions\r\n   * @returns returns tempalte ReportOptions\r\n   */\r\n  public getReportOptions(): Promise<ReportOptions> {\r\n    if (this.reportOptions) {\r\n      return Promise.resolve(this.reportOptions);\r\n    }\r\n\r\n    if (!this.sessionService?.session?.currentAccount ||\r\n      this.sessionService.session.currentAccount.avatar.entityType !== LegalEntityType.Company) {\r\n      return Promise.resolve({});\r\n    }\r\n    if (!this._reportOptionsLoading) {\r\n      this._reportOptionsLoading = true;\r\n      let reportOptions: any = {};\r\n      const settings = this.current;\r\n      const reporting = settings?.reporting;\r\n      if (reporting?.layoutTemplateId) {\r\n        this.ajax.getJSON(`${this.ajax.serverAddress}/v03/api/settings/layout/${reporting.layoutTemplateId}`).then((template) => {\r\n          if (template) {\r\n            reportOptions = template;\r\n            if (reporting.logo && reporting.layoutTemplateId.toLowerCase() === \"logo-report-options@FI53POYS0025543933\".toLowerCase()) {\r\n              if (!reporting.logo.trim().startsWith(\"<\")) {\r\n                this.ajax.getJSON(`${this.ajax.serverAddress}/v03/api/settings/logo/${reporting.logo}`).then((logoMarkup) => {\r\n                  if (logoMarkup != null) {\r\n                    reportOptions.logo = logoMarkup;\r\n                  } else {\r\n                    reportOptions.logo = reporting.logo;\r\n                  }\r\n                  this.reportOptions = reportOptions;\r\n                });\r\n              } else {\r\n                reportOptions.logo = reporting.logo;\r\n                this.reportOptions = reportOptions;\r\n              }\r\n            } else {\r\n              this.reportOptions = reportOptions;\r\n            }\r\n          } else {\r\n            this.reportOptions = reportOptions;\r\n          }\r\n        });\r\n      } else {\r\n        this.reportOptions = reportOptions;\r\n      }\r\n    }\r\n\r\n    const getOptions = (): Promise<ReportOptions> => {\r\n      return new Promise((resolve) => {\r\n        const check = () => {\r\n          if (this.reportOptions) {\r\n            return resolve(this.reportOptions);\r\n          }\r\n          this.$timeout(() => check(), 50);\r\n        };\r\n\r\n        check();\r\n      });\r\n    };\r\n    return getOptions();\r\n  }\r\n}\r\n\r\n","import angular from \"angular\";\r\n\r\nimport { OnboardingLogic } from \"@salaxy/core\";\r\n\r\n/**\r\n * Defines a supported signature method.\r\n */\r\nexport class SignatureMethod {\r\n    /** Title for the signing method. */\r\n    public title?: string;\r\n    /** Name for the signing method. */\r\n    public name: string;\r\n    /** Id for the signing method. */\r\n    public value: string;\r\n    /** Image url for the signing method. */\r\n    public img: string;\r\n    /** Boolean to indicate that the method is popular and should be shown among first methods. */\r\n    public isPopular?: boolean;\r\n}\r\n\r\n/**\r\n * Handles Digital Signature scenarios to Onnistuu.fi-service.\r\n */\r\nexport class SignatureService {\r\n\r\n    /**\r\n     * For NG-dependency injection\r\n     * @ignore\r\n     */\r\n    public static $inject = [\"$rootScope\"];\r\n\r\n    private tupasMethods: SignatureMethod[] = null;\r\n\r\n    private teliaMethods: SignatureMethod[] = null;\r\n\r\n    /**\r\n     * Creates a new instance of SignatureService\r\n     * @param $rootScope - Angular root scope. Used for event routing\r\n     */\r\n    constructor(\r\n        private $rootScope: angular.IRootScopeService,\r\n    ) {\r\n    }\r\n\r\n    /**\r\n     * Gets a list of available signature methods. Use img-property to show.\r\n     * @param methodGroup - Method group \"telia\" for Telia Tunnistus and \"tupas\" for Visma Sign. Default is \"tupas\".\r\n     */\r\n    public getMethods(methodGroup: \"tupas\" | \"telia\" = \"tupas\"): SignatureMethod[] {\r\n        methodGroup ??= \"tupas\";\r\n        switch (methodGroup) {\r\n          case \"tupas\":\r\n            this.tupasMethods ??= OnboardingLogic.getTupasMethods().map((x) => (\r\n              {\r\n                  id: x.id,\r\n                  title: x.title,\r\n                  name: x.id.substr(6), // for backward compatibility\r\n                  value: x.id,\r\n                  img: x.img,\r\n                  isPopular: x.isPopular,\r\n              }));\r\n            return this.tupasMethods;\r\n          case \"telia\":\r\n            this.teliaMethods ??= OnboardingLogic.getTeliaMethods().map((x) => (\r\n              {\r\n                  id: x.id,\r\n                  title: x.title,\r\n                  name: x.title,\r\n                  value: x.id,\r\n                  img: x.img,\r\n                  isPopular: x.isPopular,\r\n              }));\r\n            return this.teliaMethods;\r\n          default:\r\n            return [];\r\n        }\r\n    }\r\n}\r\n","import { UiTranslatorDictionaryItem } from \"./ui/model/UiTranslatorDictionaryItem\";\r\n\r\n/**\r\n * Stores the state of editable i18n dictionary and related translation methods.\r\n */\r\nexport class UiTranslatorService {\r\n  private dictionary: Array<UiTranslatorDictionaryItem> = [];\r\n  /**\r\n   * Get dictionary\r\n   * @returns UiTranslatorDictionaryItem array\r\n   */\r\n  public getDictionary() {\r\n    return this.dictionary;\r\n  }\r\n\r\n  /**\r\n   * Adds item to dictionary\r\n   * @param item item to be added to dictionary\r\n   */\r\n  public addToDictionary(item: UiTranslatorDictionaryItem) {\r\n    this.dictionary.push(item);\r\n  }\r\n}","import { Numeric, Translations, Files } from \"@salaxy/core\";\r\n\r\nimport { AjaxNg1 } from \"../ajax\";\r\n\r\n/** Abstracts the Upload process to a helper class instead of using upload directly. */\r\nexport class UploadService {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Upload\", \"AjaxNg1\", \"$q\", \"Files\"];\r\n\r\n  constructor(\r\n    private angularUpload: angular.angularFileUpload.IUploadService,\r\n    private ajax: AjaxNg1,\r\n    private $q: angular.IQService,\r\n\r\n    private files: Files\r\n  ) {\r\n  }\r\n\r\n  /**\r\n   * Standard upload method that uploads data as form POST (multipart/form-data)\r\n   * @param url Service URL that receives the upload.\r\n   * @param data The form data (including the files) that is sent to the server.\r\n   * @param notify Optional function that is called for upload notifications: Progress and error.\r\n   * @returns Message from server as defined by IReturnType.\r\n   */\r\n  public upload<IReturnType>(url: string, data: any, notify?: (\r\n    /** Upload progress is a number between 0-100 */\r\n    progress: number,\r\n    /** In the case of error, the english error message is returned here and progress is null. */\r\n    error?: string,\r\n  ) => any): angular.IPromise<IReturnType> {\r\n    return this.$q((resolve, reject) => {\r\n      this.angularUpload.upload<IReturnType>({\r\n        method: \"POST\",\r\n        url,\r\n        data,\r\n        headers: { Authorization: \"Bearer \" + this.ajax.getCurrentToken() },\r\n      }).then((response) => {\r\n        resolve(response.data);\r\n      }, (response) => {\r\n        response = response || {};\r\n        const error = (response.status || \"ERROR\") + \": \" + (response.data || \"No data\");\r\n        if (notify){\r\n          notify(null, error);\r\n        }\r\n        reject(error);\r\n      }, (evt) => {\r\n        const progress = Math.min(100, Numeric.round(100.0 * evt.loaded / evt.total, 0));\r\n        if (notify) {\r\n          notify(progress);\r\n        }\r\n      });\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Gets a the URL (with token) for a stream of given uploaded file.\r\n   * @param fileId Identifier of the file.\r\n   */\r\n  public getFileUrl(fileId: string) {\r\n    return `${this.files.getContentUrl(fileId)}?access_token=${this.ajax.getCurrentToken()}`;\r\n  }\r\n\r\n  /**\r\n   * Gets a preview URL (with token) for a given uploaded file.\r\n   * @param fileId Identifier of the file.\r\n   */\r\n  public getPreviewUrl(fileId: string) {\r\n    return `${this.files.getPreviewUrl(fileId)}?access_token=${this.ajax.getCurrentToken()}`;\r\n  }\r\n\r\n  /**\r\n   * Gets a language versined error description ng-file-upload invalidFile errors (client-side before actual upload).\r\n   * @param invalidFile Invalid file of ng-file-upload component.\r\n   * @param invalidFile.$error Error key, e.g. 'pattern', minSize' or  'maxSize'\r\n   * @param invalidFile.$errorParam Additional error param, e.g. '50KB' or '10MB' for file sizes.\r\n   */\r\n  public getInvalidFileDescription(invalidFile: {\r\n    $error: string,\r\n    $errorParam: string,\r\n  }): string {\r\n    if (!invalidFile || !invalidFile.$error) {\r\n      return null;\r\n    }\r\n    // TODO: Error messages should be moved to the right path in dictionary.\r\n    switch (invalidFile.$error) {\r\n      case \"pattern\":\r\n        return Translations.get(\"SALAXY.NG1.CurrentTaxCardComponent.uploadErrorFormat\");\r\n      case \"minSize\":\r\n        // $errorParam contains the size, e.g '50KB' if that is needed.\r\n        return Translations.get(\"SALAXY.NG1.CurrentTaxCardComponent.uploadErrorSmall\");\r\n      case \"maxSize\":\r\n        // $errorParam contains the size, e.g '10MB' if that is needed.\r\n        return Translations.get(\"SALAXY.NG1.CurrentTaxCardComponent.uploadErrorLarge\");\r\n      default:\r\n        return Translations.get(\"SALAXY.NG1.CurrentTaxCardComponent.uploadError\");\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Gets a font-awesome icon for supported file types.\r\n   * @param fileName The extension of the file name is used for determining the icon.\r\n   */\r\n  public getFileIcon(fileName: string): string {\r\n    if (!fileName || fileName.indexOf(\".\") < 0) {\r\n      return \"fa-exclamation-triangle\";\r\n    }\r\n    const extension = fileName.substring(fileName.lastIndexOf(\".\") + 1);\r\n    switch (extension) {\r\n      case \"txt\":\r\n      case \"text\":\r\n      case \"csv\":\r\n      case \"cs\":  // If these are really used at some point, you probalby want to reconsider theses\r\n      case \"css\":\r\n      case \"htm\":\r\n      case \"html\":\r\n      case \"js\":\r\n      case \"json\":\r\n      case \"xml\":\r\n        return \"bi-file-earmark-text\";\r\n      case \"bmp\":\r\n      case \"gif\":\r\n      case \"jpg\":\r\n      case \"jpeg\":\r\n      case \"png\":\r\n      case \"svg\":\r\n      case \"tif\":\r\n      case \"tiff\":\r\n        return \"bi-image\";\r\n      case \"pdf\":\r\n        return \"bi-file-earmark-pdf\";\r\n      case \"xls\":\r\n      case \"xlsx\":\r\n        return \"bi-file-earmark-excel\";\r\n      case \"doc\":\r\n      case \"docx\":\r\n        return \"bi-file-earmark-word\";\r\n      case \"zip\":\r\n        return \"bi-file-earmark-zip\";\r\n      case \"ppt\":\r\n      case \"pptx\":\r\n        return \"bi-filetype-ppt\";\r\n      default:\r\n        return \"bi-file-earmark\";\r\n    }\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { ApiItemType, StorageLogic, Usecase, UsecaseInSettings, UsecaseStatus, Usecases, UsecaseListItem } from \"@salaxy/core\";\r\n\r\nimport { SessionUsecase } from \"./model\";\r\nimport { SessionService } from \"./SessionService\";\r\nimport { UsecaseApiCrudObject } from \"./ui/model\";\r\n\r\n/** Provides caching for usecases and resolves them to business objects. */\r\nexport class UsecasesService {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Usecases\", \"SessionService\", \"$sce\"];\r\n\r\n  constructor(private usecases: Usecases, private sessionService: SessionService, private $sce: angular.ISCEService) {\r\n  }\r\n\r\n  /**\r\n   * Gets active usecases that are shown in listings (selection of usecase)\r\n   * including type-specific default usecases (applied if no other usecase is defined).\r\n   */\r\n  public getActiveUsecases(type: ApiItemType = null, defaultOnly = false): UsecaseInSettings[] {\r\n    const listInSettings: UsecaseInSettings[] = this.sessionService.session?.settings?.usecases || [];\r\n    let filteredList = listInSettings.filter((x) => !type || type == x.itemType);\r\n    if (defaultOnly) {\r\n      filteredList = filteredList.filter((x) => x.status === UsecaseStatus.Default);\r\n    }\r\n    return filteredList;\r\n  }\r\n\r\n  /**\r\n   * Gets the active items as list items. The list of all usecases is cached.\r\n   * @param type Type of items to fetch.\r\n   * TODO: The method currently supports max 50 active usecases (of all types).\r\n   */\r\n  public getActiveUsecaseListItems(type: ApiItemType = null): Promise<UsecaseListItem[]> {\r\n    const filter = (x: UsecaseListItem) => (!type || type == x.entityType) && (x.status == UsecaseStatus.Active || x.status == UsecaseStatus.Default);\r\n    if (this.cachedActiveListItems) {\r\n      return Promise.resolve(this.cachedActiveListItems.filter(filter));\r\n    }\r\n    return this.usecases.getOData({ $filter: `status eq 'active' or status eq 'default'` }).then((result) => {\r\n      this.cachedActiveListItems = result.items;\r\n      return this.cachedActiveListItems.filter(filter);\r\n    });\r\n  }\r\n\r\n  private cachedActiveListItems: UsecaseListItem[];\r\n\r\n  /**\r\n   * Gets the activity type of usecase from the settings.\r\n   * @param uri Usecase URI\r\n   * @returns Information on whether the usecase is active or not - or default usecase (also active).\r\n   */\r\n  public getActive(uri: string): UsecaseStatus {\r\n    if (!uri) {\r\n      return UsecaseStatus.Inactive;\r\n    }\r\n    if (uri.startsWith(\"http\")) {\r\n      uri = new URL(uri).pathname;\r\n    }\r\n    const item = this.sessionService.session?.settings?.usecases?.find((x) => x.uri == uri);\r\n    if (!item || item.status === UsecaseStatus.Undefined ) {\r\n      return UsecaseStatus.Inactive;\r\n    }\r\n    return item.status;\r\n  }\r\n\r\n  /**\r\n   * Gets the order  of usecase from the settings.\r\n   * @param uri Usecase URI\r\n   * @returns Order number for the usecase, 0 if not set.\r\n   */\r\n   public getOrder(uri: string): number {\r\n    if (!uri) {\r\n      return 0;\r\n    }\r\n    if (uri.startsWith(\"http\")) {\r\n      uri = new URL(uri).pathname;\r\n    }\r\n    const item = this.sessionService.session?.settings?.usecases?.find((x) => x.uri == uri);\r\n    return item?.order ?? 0;\r\n  }\r\n\r\n  /**\r\n   * Assures that the usecase model is fetched and data model is initialized according to usecase.\r\n   * @param type Type of business object\r\n   * @param item Business object to initialize.\r\n   * @param defaultUri Usecase uri if passed by the calling component (e.g. in URL or component attribute).\r\n   * @returns The usecase with session / role related data or null if none is set.\r\n   */\r\n  public assureUsecase(type: ApiItemType, item: UsecaseApiCrudObject, defaultUri: string): Promise<SessionUsecase> {\r\n    if (!item) {\r\n      return Promise.resolve(null);\r\n    }\r\n    return this.getUsecaseForObject(type, item, defaultUri).then((usecase) => {\r\n      // Prepare the usecase data model for data binding: Should either be in Core or in data binding logic (sxy-forms).\r\n      item.usecase = item.usecase || {};\r\n      item.usecase.data = item.usecase.data || {};\r\n      if (!usecase) {\r\n        return null;\r\n      }\r\n      if (usecase) {\r\n        item.usecase.uri = usecase.uri;\r\n        item.usecase.label = usecase.label;\r\n        item.usecase.description = usecase.description;\r\n      }\r\n      return usecase;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Gets a usecase definition based on business object (that has usecase data item).\r\n   * @param type Business object type\r\n   * @param item The business objec to evaluate.\r\n   * @param defaultUri Usecase uri if passed by the calling component (e.g. in URL or component attribute).\r\n   * @returns The usecase with session / role related data or null if none is set.\r\n   */\r\n  public getUsecaseForObject(type: ApiItemType, item: UsecaseApiCrudObject, defaultUri: string): Promise<SessionUsecase> {\r\n    if (!item) {\r\n      return Promise.resolve(null);\r\n    }\r\n    if (type == ApiItemType.Calculation) {\r\n      // HACK: Handle these exceptions on product level.\r\n      const considerEmpty = [\r\n        \"palkkaus.fi/usecases/payroll-service/pro-calc\",\r\n        \"palkkaus.fi/usecases/payroll-service/calc\",\r\n      ];\r\n      if (item?.usecase?.uri && !considerEmpty.find((x) => item.usecase.uri == x)) {\r\n        return this.getUsecase(item.usecase.uri);\r\n      }\r\n    }\r\n    else if (item?.usecase?.uri) {\r\n      return this.getUsecase(item.usecase.uri);\r\n    }\r\n    defaultUri = defaultUri || this.getActiveUsecases(type, true)[0]?.uri;\r\n    return defaultUri ? this.getUsecase(defaultUri) : Promise.resolve(null);\r\n  }\r\n\r\n  /** Clears the usecase cache: Will be fetched from the server in next getUsecase(). */\r\n  public clearCache(): void {\r\n    this.cachedUsecases = {};\r\n  }\r\n\r\n  /**\r\n   * Adds abilitity to set the contents of a usecase in cache.\r\n   * This is used in dynamic preview in edit usecase scenarios.\r\n   * @param newVersion A version of the usecase that is set into usecases cache.\r\n   */\r\n  public setToCache(newVersion: Usecase): void {\r\n    const sessionUsecase = newVersion as SessionUsecase;\r\n    sessionUsecase.isLoaded = true;\r\n    sessionUsecase.exists = true;\r\n    if (sessionUsecase.views?.length && newVersion.uri) {\r\n      // Later, we may have some profiling logic here: Different UI for different roles etc.\r\n      sessionUsecase.defaultView = this.$sce.trustAsResourceUrl(this.usecases.getResourceUrl(newVersion.uri, \"html\"));\r\n    }\r\n    this.cachedUsecases[newVersion.uri] = newVersion;\r\n  }\r\n\r\n  /**\r\n   * Gets a usecase based on URI using the session cache.\r\n   * @param uri Uri of the usecase\r\n   * @returns The usecase, typically cached in session.\r\n   */\r\n  public getUsecase(uri: string): Promise<SessionUsecase> {\r\n    // Note that current implementation is not completely optimal: If several queries to one usecase uri\r\n    // are made before first query returns, several http calls are made.\r\n\r\n    uri = StorageLogic.getLocalUri(uri);\r\n    const usecasesInProduct = [\"/UsecaseDefinition/FI53POYS0025543933/costcenter-percentages\"];\r\n    if (usecasesInProduct.indexOf(uri) >= 0) {\r\n      return Promise.resolve({\r\n        isLoaded: true,\r\n        exists: true,\r\n        uri: uri,\r\n      });\r\n    }\r\n    const usecase = this.cachedUsecases[uri];\r\n    if (usecase) {\r\n      if (usecase.exists) {\r\n        return Promise.resolve(usecase);\r\n      }\r\n      // Just a marker that the item has already been checked from server.\r\n      return Promise.resolve(null);\r\n    }\r\n    return this.usecases.getSingle(StorageLogic.getIdAtOwner(uri)).then((usecase: SessionUsecase) => {\r\n      if (usecase) {\r\n        this.setToCache(usecase);\r\n        return usecase;\r\n      } else {\r\n        this.cachedUsecases[uri] = {\r\n          isLoaded: true,\r\n          exists: false,\r\n          uri: uri,\r\n        };\r\n        return null;\r\n      }\r\n    });\r\n  }\r\n\r\n  private cachedUsecases: { [key: string]: SessionUsecase } = {};\r\n}","/**\r\n * Manages user-specific settings which are currently stored in the local storage (browser).\r\n * User settigns are mostly UI, such as default selections, filters, column orders, etc.\r\n * Later implementations may store the settings in the server do that they transfer from one browser to another\r\n * within the same user.\r\n */\r\nexport class UserSettingsService {\r\n\r\n  private settings: { [key: string]: any };\r\n\r\n  /**\r\n   * Returns an object with one property \"val\" that is bound to the given key.\r\n   * Used for easier data binding in AngularJS models.\r\n   * @param key Key for the property.\r\n   * @returns An object with one property \"val\" that is bound to the given key (getter and setter).\r\n   * @example\r\n   * <salaxy-input-boolean name=\"myInput\" ng-model=\"$ctrl.userSettings.ng1Binder('payroll.newVersion').val\" label=\"Uusi versio\"></salaxy-input>\r\n   */\r\n  public ng1Binder(key: string) {\r\n    // eslint-disable-next-line @typescript-eslint/no-this-alias\r\n    const that = this; // Cannot use lambda in getter/setter. Other warkarounds to preserve \"this\" would probably be more complex.\r\n    return {\r\n      /** Property the is bound to the given key. */\r\n      get val() {\r\n        return that.get(key);\r\n      },\r\n      set val(value: any) {\r\n        that.set(key, value);\r\n      }\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Gets a setting value from local storage\r\n   * @param key String key for the value\r\n   * @returns The value\r\n   */\r\n  public get<T>(key: string): T {\r\n    key = key.toLowerCase().trim();\r\n    return this.getAll()[key];\r\n  }\r\n\r\n  /**\r\n   * Sets a setting value to local sotrage\r\n   * @param key String key for the value\r\n   * @param value The value.\r\n   */\r\n  public set<T>(key: string, value: T): void {\r\n    key = key.toLowerCase().trim();\r\n    if (!key) {\r\n      throw new Error(\"Key cannot be empty\");\r\n    }\r\n    const all = this.getAll();\r\n    all[key] = value;\r\n    this.setAll(all);\r\n  }\r\n\r\n  private getAll(): { [key: string]: any } {\r\n    if (!this.settings) {\r\n      if (!localStorage[\"salaxy-user-settings\"]) {\r\n        localStorage[\"salaxy-user-settings\"] = JSON.stringify({});\r\n      }\r\n      this.settings = JSON.parse(localStorage[\"salaxy-user-settings\"]);\r\n    }\r\n    return this.settings;\r\n  }\r\n\r\n  private setAll(settings: { [key: string]: any }): void {\r\n    localStorage[\"salaxy-user-settings\"] = JSON.stringify(settings);\r\n    this.settings = settings;\r\n  }\r\n\r\n}","import { PartnerServices, VarmaPensionOrder } from \"@salaxy/core\";\r\n\r\nimport { SessionService } from \"./SessionService\";\r\n\r\n/**\r\n * Varma pension service. Contains methods for getting order template, validating the order\r\n * and sending the order.\r\n */\r\nexport class VarmaPensionService {\r\n\r\n    /**\r\n     * For NG-dependency injection\r\n     * @ignore\r\n     */\r\n    public static $inject = [\"SessionService\", \"PartnerServices\"];\r\n\r\n    /** Current order  */\r\n    private current: VarmaPensionOrder & { owner?: string | null };\r\n\r\n    constructor(\r\n        private sessionService: SessionService,\r\n        private partnerServicesApi: PartnerServices,\r\n    ) {\r\n    }\r\n\r\n    /** Lazy loading of current pension order template */\r\n    public getCurrent(): VarmaPensionOrder {\r\n        const getEmptyOrder = () => ({\r\n            owner: null,\r\n            orderer: {\r\n                contact: {},\r\n            },\r\n            tyel: {},\r\n            yel: {},\r\n            validation: {},\r\n            });\r\n        if (this.sessionService.isSessionChecked && this.sessionService.isAuthenticated) {\r\n              const owner = this.sessionService.session.currentAccount.owner;\r\n              if (this.current?.owner != owner) {\r\n                  this.current = getEmptyOrder();\r\n                  this.current.owner = owner;\r\n                  // trigger loading\r\n                  this.partnerServicesApi.getNewVarmaPensionOrder().then((order) => {\r\n                    this.current = { ...order, owner };\r\n                  });\r\n              }\r\n        } else {\r\n            this.current = null;\r\n        }\r\n        return this.current ??= getEmptyOrder();\r\n    }\r\n\r\n    /**\r\n     * Sends order for processing.\r\n     */\r\n    public send(): Promise<VarmaPensionOrder> {\r\n        const owner = this.sessionService.session.currentAccount.owner;\r\n        return this.partnerServicesApi.sendVarmaPensionOrder(this.current).then((order) => {\r\n            this.current = order;\r\n            this.current.owner = owner;\r\n            // refresh products\r\n            return this.sessionService.checkSession().then ( () => {\r\n                return  this.current;\r\n            });\r\n        });\r\n    }\r\n\r\n    /**\r\n     * Validates the order.\r\n     */\r\n    public validate(): Promise<VarmaPensionOrder> {\r\n      const owner = this.sessionService.session.currentAccount.owner;\r\n      return this.partnerServicesApi.validateVarmaPensionOrder(this.current).then((order) => {\r\n          this.current = order;\r\n          this.current.owner = owner;\r\n          return this.current;\r\n      });\r\n    }\r\n\r\n    /**\r\n     * Resets the current order.\r\n     */\r\n    public reset() {\r\n        this.current = null;\r\n    }\r\n}\r\n","import { ApiCrudObject, SessionUserCredential, WorkflowEvent } from \"@salaxy/core\";\r\n\r\nimport {CredentialService} from \"./CredentialService\";\r\nimport {SessionService} from \"./SessionService\";\r\n\r\nimport {ApiCrudObjectController} from \"../controllers/bases/ApiCrudObjectController\";\r\n\r\n/**\r\n * Service for workflow logic.\r\n * For implementation specific workflows you shoud extend this class\r\n * and inject the extended class as a WorkflowService.\r\n */\r\nexport class WorkflowService {\r\n\r\n    /**\r\n     * For NG-dependency injection\r\n     * @ignore\r\n     */\r\n    public static $inject = [\"SessionService\", \"CredentialService\"];\r\n\r\n   /**\r\n    * Creates a new instance of WorkflowService.\r\n    */\r\n    constructor(protected sessionService: SessionService, protected credentialService: CredentialService) { }\r\n\r\n  /**\r\n   * Returns credentials for the current account.\r\n   * Override this in the pro environment.\r\n   */\r\n  public get credentials(): SessionUserCredential[] {\r\n    return this.credentialService.list;\r\n  }\r\n\r\n  /**\r\n   * Returns the credential for current session.\r\n   * Override this in the pro environment.\r\n   */\r\n  public get self(): SessionUserCredential {\r\n    return this.sessionService.session.currentCredential;\r\n  }\r\n\r\n  /**\r\n   * Adds/updates the workflow event for the current item.\r\n   * @param apiCtrl API CRUD object controller for the item.\r\n   * @param wfEvent Workflow event to add/update.\r\n   * @returns Reloaded item.\r\n   */\r\n  public saveWorkflowEvent<TItem extends ApiCrudObject>(apiCtrl: ApiCrudObjectController<TItem, any>, wfEvent: WorkflowEvent): Promise<TItem> {\r\n    return apiCtrl.saveWorkflowEvent(wfEvent);\r\n  }\r\n\r\n  /**\r\n   * Deletes the given event or all events with given type.\r\n   * @param apiCtrl API CRUD object controller for the item.\r\n   * @param wfIdOrType Id or type of the workflow event.\r\n   * @returns - Reloaded item.\r\n   */\r\n  public deleteWorkflowEvent<TItem extends ApiCrudObject>(apiCtrl: ApiCrudObjectController<TItem, any>, wfIdOrType: string): Promise<TItem> {\r\n    return apiCtrl.deleteWorkflowEvent(wfIdOrType);\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Avatar, AvatarPictureType, SessionUserCredential, Translations } from \"@salaxy/core\";\r\n\r\nimport { CredentialService, GravatarHelpers, SessionService, UiHelpers, UploadService } from \"../../services\";\r\nimport { CrudControllerBase } from \"../bases/CrudControllerBase\";\r\n\r\n/** Credential controller for listing credentials and removing existing credentials. */\r\nexport class CredentialController extends CrudControllerBase<SessionUserCredential> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"UploadService\", \"CredentialService\", \"SessionService\", \"$location\", \"$attrs\", \"UiHelpers\"];\r\n\r\n  /**\r\n   * Translated color options for input enum\r\n   */\r\n  public colorOptions: any = {\r\n    \"#7F2C2A\": Translations.get(\"SALAXY.NG1.CredentialsComponent.color.brown\"),\r\n    \"#91D214\": Translations.get(\"SALAXY.NG1.CredentialsComponent.color.lime\"),\r\n    \"#61703B\": Translations.get(\"SALAXY.NG1.CredentialsComponent.color.darkGreen\"),\r\n    \"#D10074\": Translations.get(\"SALAXY.NG1.CredentialsComponent.color.pink\"),\r\n  };\r\n\r\n  private originalAvatar: Avatar = null;\r\n\r\n  /** Constructor for dependency injection */\r\n  constructor(\r\n    private uploadService: UploadService,\r\n    private credentialService: CredentialService,\r\n    private sessionService: SessionService,\r\n    $location: angular.ILocationService,\r\n    $attrs: angular.IAttributes,\r\n    uiHelpers: UiHelpers,\r\n  ) {\r\n    super(credentialService, $location, $attrs, uiHelpers);\r\n  }\r\n\r\n  /**\r\n   * Uploads avatar image file to the server.\r\n   * @param file - selected file\r\n   */\r\n  public uploadAvatarImage(file: any) {\r\n    if (!file) {\r\n      return;\r\n    }\r\n    this.uploadService.upload<SessionUserCredential>(this.credentialService.getAvatarUploadUrl(this.current.id), { file })\r\n      .then((resp) => {\r\n        this.current.avatar.url = resp.avatar.url;\r\n        this.current.avatar.pictureType = resp.avatar.pictureType;\r\n      });\r\n  }\r\n\r\n  /** Called when avatar changes */\r\n  public emailForAvatarChanged() {\r\n    if (!this.current || !this.current.avatar) {\r\n      return;\r\n    }\r\n    if (this.current.avatar.pictureType === AvatarPictureType.Gravatar) {\r\n      this.current.avatar.url = GravatarHelpers.getGravatarUrl(this.current.email);\r\n    }\r\n  }\r\n  /** Called when avatar changes */\r\n  public typeForAvatarChanged() {\r\n    if (!this.current || !this.current.avatar) {\r\n      return;\r\n    }\r\n\r\n    if (this.current.avatar.pictureType === AvatarPictureType.Gravatar) {\r\n      this.current.avatar.url = GravatarHelpers.getGravatarUrl(this.current.email);\r\n    } else {\r\n      if (GravatarHelpers.isGravatarUrl(this.current.avatar.url)) {\r\n        this.current.avatar.url = null;\r\n      }\r\n      if (this.current.avatar.pictureType === AvatarPictureType.Uploaded) {\r\n        if (!this.current.avatar.url && this.originalAvatar && this.originalAvatar.url) {\r\n          if (this.originalAvatar.pictureType === AvatarPictureType.Uploaded &&\r\n            !GravatarHelpers.isGravatarUrl(this.originalAvatar.url)) {\r\n            this.current.avatar.url = this.originalAvatar.url;\r\n          }\r\n        }\r\n      }\r\n    }\r\n  }\r\n\r\n  /** Set current credential for edit. */\r\n  public setCurrent(item: SessionUserCredential) {\r\n    if (item) {\r\n      this.originalAvatar = angular.copy(item.avatar);\r\n    }\r\n    super.setCurrent(item);\r\n  }\r\n\r\n  /** Saves a new credential */\r\n  public saveCurrent(): Promise<SessionUserCredential> {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    return super.saveCurrent().then((credential: SessionUserCredential) => {\r\n      this.originalAvatar = angular.copy(credential.avatar);\r\n      return this.sessionService.checkSession().then(() => {\r\n        loading.dismiss();\r\n        return credential;\r\n      });\r\n    });\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { SessionService, UserSettingsService } from \"../../services\";\r\nimport { AjaxNg1 } from \"../../ajax\";\r\nimport { UserSession } from \"@salaxy/core\";\r\n\r\n/**\r\n * The controller is used in creating embedded UI:s: When this NG1 based SPA is run in an iframe\r\n * and the parent sends token, session and settings as window messages.\r\n */\r\nexport class EmbeddedUiController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"SessionService\", \"$timeout\", \"AjaxNg1\", \"$location\", \"UserSettingsService\"];\r\n\r\n  private _isLoading = true;\r\n\r\n  /**\r\n   * Creates a new EmbeddedUiController\r\n   * @ignore\r\n   */\r\n  constructor(private sessionService: SessionService, private $timeout: angular.ITimeoutService, private ajax: AjaxNg1, private $location: angular.ILocationService, private userSettingsService: UserSettingsService) { }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit = () => {\r\n    this.startListening();\r\n  };\r\n\r\n  /**\r\n   * If true, the layout should show a full-page loader instead of normal pages.\r\n   * Controllers in normal pages should be destoyed (e.g. using ng-if) so that this can also\r\n   * be used in reloading the AngularJS user interface without full Browser reload.\r\n   */\r\n  public get showFullPageLoader(): boolean {\r\n    return this._isLoading || this.sessionService.isLoading;\r\n  }\r\n\r\n  /**\r\n   * Gets the user-specific setting (service), stored in the local storage.\r\n   */\r\n  public get userSettings() {\r\n    return this.userSettingsService;\r\n  }\r\n\r\n  private firstMessageTimeout: number |undefined;\r\n  private parentOrigin: string | undefined;\r\n\r\n  /**\r\n   * Starts listening for the session change events from the parent frame.\r\n   */\r\n  public startListening(): void {\r\n      if (window.parent === window) {\r\n        throw new Error(\"This is the parent window.\");\r\n      }\r\n      window.addEventListener(\"message\", this.onMessageReceived);\r\n      this.firstMessageTimeout = window.setTimeout(() => {\r\n        throw new Error(\"Timeout while waiting for session.\");\r\n      }, 4000);\r\n      // This does not work in refresh => Can we determine the parent referrer in some other way?\r\n      // this.parentOrigin = document.referrer.replace(/\\/[^/]*$/, \"\");\r\n      this.parentOrigin = \"*\";\r\n      window.parent.postMessage({ action: \"sxy-iframe-ready\" }, this.parentOrigin);\r\n  }\r\n\r\n  private onMessageReceived = (ev: MessageEvent<SessionChangeEventData>) => {\r\n    if (ev.data.action === \"sxy-iframe-change-session\") {\r\n      if (this.firstMessageTimeout) {\r\n        clearTimeout(this.firstMessageTimeout);\r\n        this.firstMessageTimeout = undefined;\r\n      }\r\n      if (ev.origin !== this.parentOrigin && this.parentOrigin !== \"*\") {\r\n        console.error(`Invalid origin ${ev.origin} vs ${this.parentOrigin}.`);\r\n        return;\r\n      }\r\n      const data: SessionChangeEventData = ev.data;\r\n      if (!data.session || !data.token) {\r\n        throw new Error(\"Session or token not defined in sxy-session-response event.\");\r\n      }\r\n      if ( this.sessionService.session?.currentAccount?.id !== data.session.currentAccount.id || this.sessionService.getCurrentToken() !== data.token ) {\r\n        this.ajax.useCookie = false;\r\n        this.ajax.setCurrentToken(data.token);\r\n        // Set the isLoading flag to true to show the loader even if _isLoading will be false for the short time period before sessionService loads the en/sv language file.\r\n        this.sessionService.isLoading = true;\r\n        this.sessionService.setSession(data.session);\r\n      }\r\n      if (data.route) {\r\n        this.$location.url(data.route);\r\n      }\r\n      this._isLoading = false;\r\n      this.$timeout();\r\n    } else {\r\n      // throw new Error(`Invalid action ${ev.data.action}.`);\r\n    }\r\n  };\r\n\r\n}\r\n\r\n/**\r\n * Structure of Session event as passed from Vue-based new UI to AngularJS-based old embedded UI (NG1).\r\n */\r\ntype SessionChangeEventData = {\r\n\r\n  /** Identifies the event. */\r\n  action: \"sxy-iframe-change-session\";\r\n\r\n  /** User session data. */\r\n  session: UserSession;\r\n\r\n  /** Token for the new session. */\r\n  token: string;\r\n\r\n  /** Route to which the application should go to. */\r\n  route: string;\r\n\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Configs } from \"@salaxy/core\";\r\nimport { PartnerService, SessionService } from \"../../services\";\r\n\r\n/**\r\n * User interface logic for brand selection,\r\n */\r\nexport class PartnerController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"PartnerService\", \"SessionService\"];\r\n\r\n  /** If true, the all partners all shown */\r\n  private showAll = false;\r\n\r\n  /**\r\n   * Creates a new PartnerController using dependency injection.\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    private partnerService: PartnerService,\r\n    private sessionService: SessionService,\r\n    ) {}\r\n\r\n  /** Controller initialization. */\r\n  public $onInit = () => {\r\n    // empty\r\n  };\r\n\r\n  /** Shows the skin that is currently in use: \"default\" for the real skin or overriden preview skin for preview purposes. */\r\n  public get skin() {\r\n    return this.partnerService.overrideSkin || \"default\";\r\n  }\r\n\r\n  /**\r\n   * Shows the Brand ID that should be used for preview purposes: Either real service model or temporary override ID.\r\n   * Note that the service model may also be null, if there is no partner\r\n   */\r\n  public get brandId() {\r\n    return this.partnerService.overridePartnerId || this.sessionService.getSession()?.settings.partner?.serviceModelId;\r\n  }\r\n\r\n  /**\r\n   * Shows a dialog for brand selection.\r\n   */\r\n  public showSwitchCss() {\r\n    this.partnerService.showSwitchCss();\r\n  }\r\n\r\n  /**\r\n   * Temporary method only used in development\r\n   * Shows a dialog for brand selection.\r\n   */\r\n  public showSwitchCssDev() {\r\n    this.partnerService.showSwitchCssDev();\r\n  }\r\n\r\n  /**\r\n   * Gets the URL for the login screen. Mainly for testing / preview purposes.\r\n   */\r\n  public getLoginUrl() {\r\n    const server = Configs.current.wwwServer || \"https://test-www.palkkaus.fi\";\r\n    return server +  \"/Security/Authorize?client_id=\" + (this.brandId || \"\");\r\n  }\r\n\r\n  /**\r\n   * Gets the URL for the onboarding screen. Mainly for testing / preview purposes.\r\n   */\r\n   public getOnboardingUrl() {\r\n    const server = Configs.current.apiServer || \"https://test-secure.palkkaus.fi\";\r\n    let url = `${server}/Onboarding/Wizard?id=test&role=company`;\r\n    if (this.brandId) {\r\n      url = url + \"&partner=\" + this.brandId;\r\n    }\r\n    return url;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Ajax, Configs, Language, PaymentChannel, SystemRole, Translations } from \"@salaxy/core\";\r\n\r\nimport { SessionService, UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * User interaction with the current session: UserCredentials, Current Account(s) and Login/Logout.\r\n */\r\nexport class SessionController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"SessionService\",\r\n    \"$location\",\r\n    \"AjaxNg1\",\r\n    \"UiHelpers\",\r\n  ];\r\n\r\n  /** Default redirect URL for signIn and register if not specified by the method */\r\n  public redirectUrl: string;\r\n\r\n  constructor(\r\n    private sessionService: SessionService,\r\n    private $location: angular.ILocationService,\r\n    private ajax: Ajax,\r\n\r\n    private uiHelpers: UiHelpers,\r\n  ) {\r\n\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit = () => {\r\n    //\r\n  };\r\n\r\n  /** If true, the session has been checked from theserver - i.e. isAuthenticated = false means that the user really cannot be authenticated. */\r\n  public get isSessionChecked() {\r\n    return this.sessionService.getIsSessionChecked();\r\n  }\r\n\r\n  /** If true, the session check call is progressing. */\r\n  public get isSessionChecking() {\r\n    return this.sessionService.getIsSessionChecking();\r\n  }\r\n\r\n  /** If true, the user is authenticated */\r\n  public get isAuthenticated() {\r\n    return this.sessionService.getIsAuthenticated();\r\n  }\r\n\r\n  /** Avatar to show in the login screen */\r\n  public get avatar(): any {\r\n    return this.sessionService.getAvatar();\r\n  }\r\n\r\n  /** The full session objcet */\r\n  public get session(): any {\r\n    return this.sessionService.getSession();\r\n  }\r\n\r\n  /** The company account if the current account is company - and if the full account info is fetched */\r\n  public get company(): any {\r\n    return this.sessionService.getCompanyAccount();\r\n  }\r\n\r\n  /** The person account if the current account is person - and if the full account info is fetched */\r\n  public get person(): any {\r\n    return this.sessionService.getPersonAccount();\r\n  }\r\n\r\n  /**\r\n   * Opens the login form for the current user\r\n   * @param redirectUrl - The URL where the user is taken after a successfull login.\r\n   * @param role - Optional role (household, worker or company) for the situations where it is known - mainly for new users\r\n   * @param partnerSite Identifier of the partner or service model from which the login UI is fetched.\r\n   * @param urlPostfix Additional string that is added to the OAuth2 URL.\r\n   * Used in adding other parameters to the URL, e.g. \"&salaxy_language=en\"\r\n   */\r\n  public signIn(redirectUrl: string = null, role: string = null, partnerSite: string = null, urlPostfix: string = null) {\r\n    this.sessionService.signIn(redirectUrl || this.redirectUrl, role, partnerSite, urlPostfix);\r\n  }\r\n\r\n  /**\r\n   * Opens the login dialog with signUp / register functionality\r\n   * @param  redirectUrl - The URL where the user is taken after a successfull login\r\n   * @param  role - Optional role (household, worker or company) for the situations where it is known - mainly for new users\r\n   * @param partnerSite Identifier of the certified partner which should be granted access rights in account creation.\r\n   * Also sets register dialog and onboarding wizard UI skin.\r\n   * @param urlPostfix Additional string that is added to the OAuth2 URL.\r\n   * Used in adding other parameters to the URL, e.g. \"&salaxy_language=en\"\r\n   */\r\n\r\n  public register(redirectUrl: string = null, role: string = null, partnerSite: string = null, urlPostfix: string = null) {\r\n    this.sessionService.register(redirectUrl || this.redirectUrl, role, partnerSite, urlPostfix);\r\n  }\r\n\r\n  /** If false, the current authenticated user has not signed the contract. */\r\n  public get isAccountVerified(): boolean {\r\n    return this.sessionService.checkAccountVerification();\r\n  }\r\n\r\n  /**\r\n   * Sends the user to the Sign-out page\r\n   * @param redirectUrl - URL where user is redirected after log out.\r\n   * Must be absolute URL. Default is the root of the current server.\r\n   */\r\n  public signOut(redirectUrl?: string) {\r\n    this.sessionService.signOut(redirectUrl);\r\n  }\r\n\r\n  /**\r\n   * Switches the current web site usage role between household and worker.\r\n   * @param role - household or worker.\r\n   * @returns A Promise with result data (new role as string)\r\n   */\r\n  public switchRole(role: \"worker\" | \"household\"): Promise<\"household\" | \"worker\"> {\r\n    return this.sessionService.switchRole(role).then((resultRole) => {\r\n      if (role === \"worker\") {\r\n        window.location.href = \"/Worker#/\";\r\n      } else {\r\n        window.location.href = \"/Household#/\";\r\n      }\r\n      return resultRole;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * When called, will show the login screen if the user is not logged in\r\n   */\r\n  public checkAuthenticated() {\r\n    if (this.isSessionChecked && !this.isAuthenticated) {\r\n      this.signIn(window.location.href);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Checks whether the user is in a given role\r\n   * @param  role - One of the known roles\r\n   */\r\n  public isInRole(role: SystemRole): boolean {\r\n    return this.sessionService.isInRole(role);\r\n  }\r\n\r\n  /**\r\n   * Set the language for UI in the current session.\r\n   * @param lang - Language to select: fi, en, sv.\r\n   */\r\n  public setLanguage(lang: Language) {\r\n    this.sessionService.setLanguage(lang);\r\n  }\r\n\r\n  /**\r\n   * Get the current language for UI in the current session.\r\n   */\r\n  public getLanguage() {\r\n    return Translations.getLanguage();\r\n  }\r\n\r\n  /**\r\n   * Switches the CSS link to partner-specific CSS.\r\n   * @param cssUrl URL for the CSS file.\r\n   */\r\n  public switchCss(cssUrl: string) {\r\n    this.sessionService.switchCss(cssUrl);\r\n  }\r\n\r\n  /** Sign in error */\r\n  public get signInError(): string {\r\n    return this.sessionService.signInError;\r\n  }\r\n  /** Sign in error description */\r\n  public get signInErrorDescription(): string {\r\n    return this.sessionService.signInErrorDescription;\r\n  }\r\n  /** Sign in error page url */\r\n  public get signInErrorPageUrl(): string {\r\n    return this.sessionService.signInErrorUrl;\r\n  }\r\n\r\n  /** Returns current token if exists. */\r\n  public get currentToken(): string {\r\n    return this.ajax.getCurrentToken();\r\n  }\r\n\r\n  /** Returns the url to the authorization pdf. */\r\n  public get authorizationPdfUrl() {\r\n    return `${Configs.current.apiServer}/Onboarding/GetAuthorizationPdf?access_token=${encodeURIComponent(this.ajax.getCurrentToken())}`;\r\n  }\r\n\r\n  /** Returns owned payment channel for current account */\r\n  public get ownedPaymentChannel(): PaymentChannel {\r\n    return this.sessionService.getOwnedPaymentChannel();\r\n  }\r\n\r\n/** get kyc state */\r\n  public get kycState(): \"ignored\" | \"valid\" | \"expired\" | \"missing\" {\r\n   return this.sessionService.kycState;\r\n  }\r\n\r\n  /** returns latest update date for kyc. */\r\n  public get kycUpdatedAt(): string {\r\n    return this.sessionService.kycUpdatedAt;\r\n  }\r\n\r\n  /** returns expiration date for kyc. */\r\n  public get kycExpiresAt(): string {\r\n    return this.sessionService.kycExpiresAt;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Accounts, Ajax, Avatar, AvatarPictureType, CompanyAccount, WorkflowEvent } from \"@salaxy/core\";\r\n\r\nimport { GravatarHelpers, SessionService, UiHelpers, UploadService } from \"../../services\";\r\n\r\n/** Company account controller for editing basic information. */\r\nexport class CompanyAccountController implements angular.IComponentController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Accounts\", \"SessionService\", \"AjaxNg1\", \"UiHelpers\", \"UploadService\"];\r\n\r\n  /** Current company account */\r\n  public current: CompanyAccount = null;\r\n\r\n  /** Constructor for dependency injection */\r\n  constructor(\r\n    private accounts: Accounts,\r\n    private sessionService: SessionService,\r\n    private ajax: Ajax,\r\n    private uiHelpers: UiHelpers,\r\n    private uploadService: UploadService,\r\n  ) {\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    if (!this.current) {\r\n      this.accounts.getCompany().then((company) => {\r\n        this.current = company;\r\n      });\r\n    }\r\n  }\r\n\r\n  /** Gets the language of the current company */\r\n  public getAccountLanguage() {\r\n    return this.current?.language;\r\n  }\r\n  /** Updates the company */\r\n  public saveCurrent(): Promise<CompanyAccount> {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    return this.ajax.postJSON(\"/accounts/company\", this.current).then((company: CompanyAccount) => {\r\n      this.current = company;\r\n      return this.sessionService.checkSession().then(() => {\r\n        loading.dismiss();\r\n        return company;\r\n      });\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Uploads avatar image file to the server.\r\n   * @param avatar - selected file\r\n   */\r\n  public uploadAvatarImage(avatar: any, current: CompanyAccount = null) {\r\n    if (!avatar) {\r\n      return;\r\n    }\r\n    current = current ?? this.current;\r\n    this.uploadService.upload<Avatar>(this.accounts.getAvatarUploadUrl(), { avatar })\r\n      .then((resp) => {\r\n        current.avatar.url = resp.url;\r\n        current.avatar.pictureType = resp.pictureType;\r\n      });\r\n  }\r\n\r\n  /** Called when avatar changes */\r\n  public emailForAvatarChanged(current: CompanyAccount = null) {\r\n    current = current  ?? this.current;\r\n    if (!current || !current.avatar) {\r\n      return;\r\n    }\r\n    if (current.avatar.pictureType === AvatarPictureType.Gravatar) {\r\n      current.avatar.url = GravatarHelpers.getGravatarUrl(current.contact.email);\r\n    }\r\n  }\r\n  /** Called when avatar changes */\r\n  public typeForAvatarChanged(current: CompanyAccount = null) {\r\n    current = current  ?? this.current;\r\n    if (!current || !current.avatar) {\r\n      return;\r\n    }\r\n    if (current.avatar.pictureType === AvatarPictureType.Gravatar) {\r\n      current.avatar.url = GravatarHelpers.getGravatarUrl(current.contact.email);\r\n    } else {\r\n      if (GravatarHelpers.isGravatarUrl(current.avatar.url)) {\r\n        current.avatar.url = null;\r\n      }\r\n      if (current.avatar.pictureType === AvatarPictureType.Uploaded) {\r\n        const originalAvatar = (this.sessionService.getPersonAccount() || {}).avatar;\r\n        if (!current.avatar.url && originalAvatar && originalAvatar.url) {\r\n          if (originalAvatar.pictureType === AvatarPictureType.Uploaded &&\r\n            !GravatarHelpers.isGravatarUrl(originalAvatar.url)) {\r\n            current.avatar.url = originalAvatar.url;\r\n          }\r\n        }\r\n      }\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Adds/updates the workflow event for the current using API.\r\n   * @param wfEvent - Workflow event to add/update.\r\n   * @returns - Reloaded item.\r\n   */\r\n  public saveWorkflowEvent(wfEvent: WorkflowEvent): Promise<void | CompanyAccount> {\r\n    return this.accounts.saveWorkflowEvent(this.current, wfEvent).then(() => {\r\n      return this.accounts.getCompany().then((company) => {\r\n        this.current = company;\r\n      });\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Deletes the given event or all events with given type using API.\r\n   * @param wfIdOrType Id or type of the workflow event.\r\n   * @returns - Reloaded item.\r\n   */\r\n  public deleteWorkflowEvent(wfIdOrType: string): Promise<void | CompanyAccount> {\r\n    return this.accounts.deleteWorkflowEvent(this.current, wfIdOrType).then(() => {\r\n      return this.accounts.getCompany().then((company) => {\r\n        this.current = company;\r\n      });\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Gets a single workflow event for the item.\r\n   * @param wfId Id the workflow event.\r\n   * @returns - Workflow event.\r\n   */\r\n  public getWorkflowEvent(wfId: string): Promise<WorkflowEvent> {\r\n    return this.accounts.getWorkflowEvent(this.current, wfId);\r\n  }\r\n\r\n  /**\r\n   * Opens modal for avatar edit\r\n   */\r\n  public openEditDialog(editType: \"avatar\" | \"contactInfo\"): void {\r\n    const logic = {\r\n      typeForAvatarChanged: (current) => this.typeForAvatarChanged(current),\r\n      uploadAvatarImage: (file, current) => this.uploadAvatarImage(file, current),\r\n      emailForAvatarChanged: (current) => this.emailForAvatarChanged(current)\r\n    };\r\n    this.uiHelpers.openEditDialog(\r\n      editType === \"avatar\" ? \"salaxy-components/modals/account/AccountAvatarEdit.html\" : \"salaxy-components/modals/account/AccountContactEdit.html\",\r\n      this.current,\r\n      logic\r\n      ).then((result) => {\r\n        if (result.action === \"ok\") {\r\n          this.current = result.item;\r\n          this.saveCurrent();\r\n        }\r\n      });\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Calculation } from \"@salaxy/core\";\r\nimport { UiCrudHelpers, UiHelpers } from \"../../../services\";\r\nimport { CalculationCrudController } from \"../CalculationCrudController\";\r\n\r\n/**\r\n * Allows editing the employmen\r\n */\r\nexport class CalcEmploymentController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"UiHelpers\", \"UiCrudHelpers\"];\r\n\r\n  /**\r\n   * Setter for the calculations controller that edits the current item.\r\n   * Possibility to support other data types.\r\n   */\r\n  public model: CalculationCrudController;\r\n\r\n  /**\r\n   * If true, will also update the calculation rows from employment relation when the employment\r\n   * relation is selected. By default, does not update the rows.\r\n   */\r\n  public updateRows: boolean;\r\n\r\n  constructor(\r\n    private uiHelpers: UiHelpers,\r\n    private uiCrudHelpers: UiCrudHelpers,\r\n  ) {\r\n    // Dependency injection\r\n  }\r\n\r\n  /** Gets the current calculation. By convention, set in model. */\r\n  public get current(): Calculation {\r\n    return this.model.current;\r\n  }\r\n\r\n  /**\r\n   * Opens a dialog that shows the wizard to create a new Employment relation.\r\n   */\r\n  public launchEmploymentWizard(): void {\r\n    this.uiCrudHelpers.createNewEmployment().then((result) => {\r\n      if (result.action === \"ok\") {\r\n        const loader = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.isSaving\");\r\n        this.model.updateFromEmployment(result.item.id, this.updateRows || false).then(() => {\r\n          loader.dismiss();\r\n        });\r\n      }\r\n    });\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Calculation, Calculations, CalculationStatus, CalculatorLogic, PaymentChannel, Translations, CalculationListItem, SystemRole } from \"@salaxy/core\";\r\n\r\nimport { InvoicesService, ReportsService, SessionService, UiHelpers } from \"../../services\";\r\nimport { ApiCrudObjectController } from \"../bases\";\r\n\r\n/**\r\n * The new ApiCrudObject type of CRUD controller for the calculations.\r\n */\r\nexport class CalculationCrudController extends ApiCrudObjectController<Calculation, CalculationListItem> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Calculations\", \"ReportsService\", \"UiHelpers\", \"$location\", \"$routeParams\", \"SessionService\", \"InvoicesService\"];\r\n\r\n  /**\r\n   * If true, will also update the calculation rows from employment relation when the employment\r\n   * relation is selected. Note that this value is true by default for historical reasons.\r\n   */\r\n  public updateRows: boolean;\r\n\r\n  constructor(\r\n    private calculationsApi: Calculations,\r\n    protected reportsService: ReportsService,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    protected sessionService: SessionService,\r\n    protected invoicesService: InvoicesService,\r\n  ) {\r\n    // Dependency injection\r\n    super(calculationsApi, uiHelpers, $location, $routeParams);\r\n  }\r\n  /**\r\n   * Initialization code.\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n    if (this.updateRows == null) {\r\n      this.updateRows = true;\r\n    }\r\n  }\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"/calc\",\r\n      detailsUrl: this.detailsUrl || \"/calc/details/\",\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/CalculationsAll.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n\r\n  /** Recalculates the current calculation */\r\n  public recalculate() {\r\n    this.setStatus(this.calculationsApi.recalculate(this.current))\r\n      .then((calc) => {\r\n        this.setCurrentValue(calc);\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Gets the URL for a calculation pdf.\r\n   * If report has not been saved (ID is null), returns null.s\r\n   * @param calc - Calculation. This method requires that the calculation has been saved.\r\n   * @returns Url for specified report\r\n   */\r\n  public getPdfUrl(calc: Calculation) {\r\n    if (!calc) {\r\n      return null;\r\n    }\r\n    return this.reportsService.getPdfUrlForCalc(\"salarySlip\", calc.id, true);\r\n  }\r\n\r\n  /**\r\n   * If true, this is a new unsaved object.\r\n   * Adds \"new-for-employment\" actions as new item.\r\n   */\r\n  public isNew(): boolean {\r\n    if (this.parentController) {\r\n      return this.parentController.isNew();\r\n    }\r\n    return this.action === \"new-for-worker\" || this.action === \"new-for-employment\" || super.isNew();\r\n  }\r\n\r\n  /**\r\n   * Starts the reload process depending on the bindingMode:\r\n   * Overrides a different load process for \"new-for-employment\".\r\n   */\r\n  public reload(): Promise<Calculation> {\r\n    if (this.action === \"new-for-worker\" || this.action === \"new-for-employment\") {\r\n      if (this.parentController) {\r\n        return this.parentController.reload().then((item) => {\r\n          this._currentId = null;\r\n          return item;\r\n        });\r\n      } else {\r\n        const calc = this.api.getBlank();\r\n        if (this.currentId === \"new\") {\r\n          this._currentId = null;\r\n        }\r\n        if (this.action === \"new-for-worker\") {\r\n          calc.worker.accountId = this.currentId;\r\n        } else {\r\n          calc.worker.employmentId = this.currentId;\r\n        }\r\n        this._currentId = null;\r\n        this.setDefaultPaymentChannel(calc);\r\n        return this.setStatus(this.calculationsApi.updateFromEmployment(calc, false, this.updateRows))\r\n          .then((item) => {\r\n            this.setCurrentRef(item);\r\n            return item;\r\n          });\r\n      }\r\n    } else {\r\n      if (this.isNew() && this.sessionService.isInRole(\"worker\")) {\r\n        if (this.parentController) {\r\n          return this.parentController.reload().then((item) => {\r\n            this._currentId = null;\r\n            return item;\r\n          });\r\n        } else {\r\n          const getNewCalc = (): Promise<Calculation> => {\r\n            if (this.action === \"copy-as-new\") {\r\n              return this.setStatus(this.api.getSingle(this.currentId)).then((item) => {\r\n                return this.copyItem(item || this.api.getBlank());\r\n              });\r\n            } else {\r\n              return Promise.resolve(this.api.getBlank());\r\n            }\r\n          };\r\n          return getNewCalc().then((newCalc) => {\r\n            newCalc.worker.isSelf = true;\r\n            newCalc.employer.isSelf = false;\r\n            this._currentId = null;\r\n            this.setDefaultPaymentChannel(newCalc);\r\n            return this.setStatus(this.calculationsApi.recalculate(newCalc)).then((calc) => {\r\n              this.setCurrentRef(calc);\r\n              return calc;\r\n            });\r\n          });\r\n        }\r\n      }\r\n\r\n      return super.reload().then((reloaded) => {\r\n        if (super.isNew()) {\r\n          this.setDefaultPaymentChannel(reloaded);\r\n        }\r\n        return reloaded;\r\n      });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Creates a copy of a given item.\r\n   * This is a synchronous method that should basically convert a saved item to a new item.\r\n   * @param copySource Item (container item) to copy as new.\r\n   */\r\n  public copyItem(copySource: Calculation): Calculation {\r\n    const copy = super.copyItem(copySource);\r\n    copy.id = null;\r\n    copy.info.workStartDate = null;\r\n    copy.info.workEndDate = null;\r\n    copy.info.workerMessage = null;\r\n    copy.info.paymentId = null;\r\n    copy.info.payrollId = null;\r\n    copy.info.backofficeNotes = null;\r\n    copy.info.pensionPaymentDate = null;\r\n    copy.info.pensionPaymentRef = null;\r\n    copy.info.pensionPaymentSpecifier = null;\r\n    copy.info.paymentChannel = PaymentChannel.Undefined;\r\n    copy.info.messageThreadId = null;\r\n    copy.worktime = {};\r\n    copy.workflow.status = CalculationStatus.Draft;\r\n    copy.workflow.paidAt = null;\r\n    copy.workflow.salaryDate = null;\r\n    copy.workflow.requestedSalaryDate = null;\r\n    copy.workflow.salaryPaidAt = null;\r\n    copy.createdAt = null;\r\n    copy.updatedAt = null;\r\n    if (copy.framework) {\r\n      copy.framework.numberOfDays = 0;\r\n    }\r\n    // HACK: remove payroll-service flag. This will be replaced with invoicing flags eventually.\r\n    if (copy.usecase &&\r\n      (copy.usecase.uri === \"palkkaus.fi/usecases/payroll-service/pro-calc\" ||\r\n        copy.usecase.uri === \"palkkaus.fi/usecases/payroll-service/calc\")) {\r\n      copy.usecase = {};\r\n    }\r\n    copy.isReadOnly = false;\r\n    this.setDefaultPaymentChannel(copy);\r\n    return copy;\r\n  }\r\n\r\n  /** Shows the paymentd dialog / the invoices UI. */\r\n  public showPaymentDialog() {\r\n    this.invoicesService.showPaymentDialog(this.current);\r\n  }\r\n\r\n  /** Shows inspection dialog for invoices of paid calculation*/\r\n  public showInvoicesDialog() {\r\n    this.invoicesService.showPalkkausPersonalInvoicesDialog(this.current);\r\n  }\r\n\r\n  /**\r\n   * Updates the calculation from Employment ID by deleting all the rows and re-setting the employment.\r\n   * @param employmentId Employement Id to set.\r\n   * If null, the employment Id already in calculation is used:\r\n   * This method cannot be used to remove the Worker (extend if necessary).\r\n   * @param updateRows If true, updates also the calc rows from the default rows in\r\n   * employment relation. If false, the rows are kept as is.\r\n   * @returns The Calculation after recalc (no saving).\r\n   */\r\n  public updateFromEmployment(employmentId: string = null, updateRows: boolean): Promise<Calculation> {\r\n    if (employmentId) {\r\n      this.current.worker.employmentId = employmentId;\r\n    }\r\n    return this.calculationsApi.updateFromEmployment(this.current, false, updateRows).then((calc) => {\r\n      super.setCurrentValue(calc);\r\n      return calc;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Cancels the payment or invoice processing for the current calculation.\r\n   */\r\n  public cancel(): Promise<Calculation> {\r\n    const eprWarningMessage = this.invoicesService.getEprWarningForCancellation(this.current.workflow?.salaryDate, this.current.workflow?.status == CalculationStatus.PaymentSucceeded);\r\n    const eprText = eprWarningMessage ? \"\\n\" + eprWarningMessage : \"\";\r\n    return this.uiHelpers.showConfirm(Translations.get(\"SALAXY.NG1.CalcResultsComponent.cancelDialogTitle\") + \"?\", Translations.get(\"SALAXY.NG1.CalcResultsComponent.cancelDialogDescr\") + `${eprText}`, \"SALAXY.NG1.CalcResultsComponent.cancelDialogYes\", \"SALAXY.NG1.CalcResultsComponent.cancelDialogNo\").then((result) => {\r\n      if (result) {\r\n        const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n        return this.calculationsApi.cancel(this.currentId).then((item: Calculation) => {\r\n          this.setCurrentValue(item);\r\n          loading.dismiss();\r\n          return this.current;\r\n        });\r\n      } else {\r\n        return this.current;\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Opens the list for selecting a new paid calculation for repair.\r\n   * @param onAfterAction Function to call after the action.\r\n   * @param calcId Optional ID of the calculation to repair.\r\n   */\r\n  public launchCreateRepair(onAfterAction: () => Promise<void>, calcId: string = null) {\r\n    if (calcId) {\r\n      const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n      return this.calculationsApi.startRepair(calcId).then(() => {\r\n        // Wait for the index\r\n        return this.uiHelpers.wait().then(() => {\r\n          loading.dismiss();\r\n          if (onAfterAction) {\r\n            return onAfterAction();\r\n          }\r\n        });\r\n      });\r\n    }\r\n    else {\r\n      return this.uiHelpers.openEditDialog(\r\n        \"salaxy-components/modals/calc/CalcList.html\",\r\n        [],\r\n        {\r\n          title: \"SALAXY.UI_Terms.select\",\r\n          category: \"paid\",\r\n          options: { $filter: this.sessionService.isInRole(\"admin\") ? \"status eq 'paymentSucceeded'\" : \"status eq 'paymentSucceeded' and not( data/paymentChannel eq 'palkkausCfaTest' or data/paymentChannel eq 'palkkausCfaPaytrail' or data/paymentChannel eq 'palkkausEcfaPaytrail' or data/paymentChannel eq 'palkkausCfaReference' or data/paymentChannel eq 'palkkausEcfaReference' or data/paymentChannel eq 'palkkausCfaFinvoice' or data/paymentChannel eq 'palkkausEcfaFinvoice' )\" },\r\n          okButtonText: \"SALAXY.UI_Terms.ok\",\r\n          cancelButtonText: \"SALAXY.UI_Terms.cancel\",\r\n        }).then((result) => {\r\n          if (result.action === \"ok\" && result.item.length > 0) {\r\n            const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n            return Promise.all(result.item.map(x => this.calculationsApi.startRepair(x.id))).then(() => {\r\n              // Wait for the index\r\n              return this.uiHelpers.wait().then(() => {\r\n                loading.dismiss();\r\n                if (onAfterAction) {\r\n                  return onAfterAction();\r\n                }\r\n              });\r\n            });\r\n          } else {\r\n            return;\r\n          }\r\n        });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * If true, the form controls should be read-only (no control at all).\r\n   */\r\n  public get isReadOnly() {\r\n    return super.isReadOnly || this.current.workflow?.status === CalculationStatus.PaymentStarted;\r\n  }\r\n\r\n  /**\r\n   * Returns true if there is no net salary payment to worker at all.\r\n   */\r\n  public get isCurrentZeroPayment(): boolean {\r\n    return CalculatorLogic.isZeroPayment(this.current);\r\n  }\r\n\r\n  private setDefaultPaymentChannel(calc: Calculation) {\r\n    if (calc && calc.info && this.sessionService.getSession() && (!calc.info.paymentChannel || calc.info.paymentChannel === PaymentChannel.Undefined)) {\r\n      calc.info.paymentChannel = this.invoicesService.defaultChannel;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * HACK: This will be removed after moved to useCase based calculators.\r\n   * Temporary redirecting to correct details view.\r\n   * TODO: Should be replaced with full usecase logic based implementation.\r\n   */\r\n  public showDetails(item: Calculation | CalculationListItem) {\r\n    // HACK: This implementation is a bit hacky, but it should work.\r\n    // This is to be replaced with logic that checks the usecase and makes the redirect accordingly.\r\n    if (!this.sessionService.isInRole(SystemRole.Test)) {\r\n      if ((item as Calculation)?.workflow?.status == CalculationStatus.History) {\r\n        this.detailsUrl = \"/calc/history/\";\r\n      }\r\n      if ((item as CalculationListItem)?.status == CalculationStatus.History) {\r\n        this.detailsUrl = \"/calc/history/\";\r\n      }\r\n    }\r\n    if ((item as CalculationListItem)?.status == CalculationStatus.Repair) {\r\n      this.detailsUrl = \"/calc/repair/\";\r\n    }\r\n    return super.showDetails(item);\r\n  }\r\n\r\n  /** Shows the earnings payment report for the epr. */\r\n  public showEpr(item: Calculation | CalculationListItem) {\r\n    return this.calculationsApi.getEpr(item.id).then((epr) => {\r\n      if (!epr) {\r\n        this.uiHelpers.showAlert(\"Palkkatietoilmoitusta ei ole\", \"Palkkatietoilmoitusta ei ole vielä luotu tälle laskelmalle.\");\r\n        return null;\r\n      }\r\n      return this.$location.path(\"/irepr/details/\" + epr.id);\r\n    });\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { ApiItemType, Arrays, calcReportType, Calculation, CalculationRowType, Calculations, Usecase, UsecaseListItem, CalculationStatus, SalaryDateKind, PaymentChannel, InvoicesLogic } from \"@salaxy/core\";\r\n\r\nimport { CalculationCrudController } from \"../CalculationCrudController\";\r\nimport { EditDialogKnownActions, InvoicesService, ReportsService, SessionService, UiCrudHelpers, UiHelpers, UsecasesService } from \"../../../services\";\r\nimport { ApiCrudObjectControllerBindings } from \"../../bases\";\r\n\r\n/** Enumerations for calculator actions */\r\nenum CalculatorActions {\r\n  AllowForcePay = \"allowForcePay\",\r\n  Approve = \"approve\",\r\n  Cancel = \"cancel\",\r\n  CopyAsNew = \"copyAsNew\",\r\n  Delete = \"delete\",\r\n  Pay = \"pay\",\r\n  Recalculate = \"recalculate\",\r\n  Reject = \"reject\",\r\n  Save = \"save\",\r\n  SendToPro = \"sendToPro\",\r\n  ShowPaymentDialog = \"showPaymentDialog\",\r\n  SetSalaryDateKind = \"setSalaryDateKind\",\r\n}\r\n/**\r\n * Year 2022 version of the Calculator controller designed for customized calculator UI's (usecases).\r\n * Removes old methods that are no longer necessary (household, old calculator UI)\r\n * and adds more support for customization.\r\n */\r\nexport class Calculator2022Controller extends CalculationCrudController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Calculations\", \"ReportsService\", \"UiHelpers\", \"$location\", \"$routeParams\", \"SessionService\", \"InvoicesService\", \"UiCrudHelpers\", \"UsecasesService\"];\r\n\r\n  /** Component bindings */\r\n  public static crudBindings = (new class extends ApiCrudObjectControllerBindings {\r\n  }());\r\n\r\n  /**\r\n   * The usecase definition if specified and loaded.\r\n   * Check the usecaseState if the.\r\n   */\r\n  public usecase: null | Usecase = null;\r\n\r\n  /** Available usecases if the user needs to make a selection of which usecase to take. */\r\n  public usecases: UsecaseListItem[];\r\n\r\n\r\n  /** If true, additional worker info is displayed in the UI */\r\n  public isWorkerInfoOpen: boolean;\r\n\r\n\r\n  constructor(\r\n    calcApi: Calculations,\r\n    reportsService: ReportsService,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    sessionService: SessionService,\r\n    protected invoicesService: InvoicesService,\r\n    protected uiCrudHelpers: UiCrudHelpers,\r\n    private usecasesService: UsecasesService,\r\n  ) {\r\n    // Dependency injection\r\n    super(calcApi, reportsService, uiHelpers, $location, $routeParams, sessionService, invoicesService);\r\n  }\r\n\r\n  /**\r\n   * Initialization code.\r\n   */\r\n  public $onInit() {\r\n    this.isWorkerInfoOpen = false;\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Overrides the reload to assure that usecase is also loaded. */\r\n  public reload(): Promise<Calculation> {\r\n    return super.reload().then((calc) => {\r\n      const usecaseUri = this.$location?.search().usecase;\r\n      if (!usecaseUri && this.isNew()) {\r\n        return this.showUsecasesSelection();\r\n      }\r\n      return this.usecasesService.assureUsecase(ApiItemType.Calculation, calc, usecaseUri).then((usecase) => {\r\n        this.usecase = usecase;\r\n        //this.callEvent(\"onLoad\");\r\n        return calc;\r\n      });\r\n    });\r\n  }\r\n\r\n  /**\r\n   * If true, the given action (button) is displayed.\r\n   * @param action One of the action values.\r\n   * For now, validation and role based action logic is in UI.\r\n   * Todo: some edge cases, i.e. isForcePayAllAllowed (for pay-button) are still in UI.\r\n   */\r\n  public showAction(action: CalculatorActions): boolean {\r\n\r\n    if (!this.current) {\r\n      return false;\r\n    }\r\n    // In read only mode\r\n    if (this.isReadOnlyForced && action != CalculatorActions.ShowPaymentDialog) {\r\n      return false;\r\n    }\r\n    if (this.isReadOnlyForced && action == CalculatorActions.ShowPaymentDialog) {\r\n      return true;\r\n    }\r\n    if (this.current.workflow.status == CalculationStatus.PayrollDraft) {\r\n      // Not possible to make changes to editable payroll calculation\r\n      return false;\r\n    }\r\n    if (this.current.isReadOnly) {\r\n      switch (action) {\r\n        case CalculatorActions.Cancel:\r\n          return this.current.workflow.status == CalculationStatus.PaymentStarted &&\r\n            (\r\n              [\r\n                PaymentChannel.PalkkausManual,\r\n              PaymentChannel.TalenomManual,\r\n                PaymentChannel.PalkkausPersonal,\r\n                PaymentChannel.PalkkausInvoices\r\n              ].indexOf(this.current.info.paymentChannel) > -1 ||\r\n              (\r\n                InvoicesLogic.isCfa(this.current.info.paymentChannel) &&\r\n                !this.current.info.payrollId\r\n              )\r\n            );\r\n        case CalculatorActions.CopyAsNew:\r\n          return !this.isReadOnlyForced; // Not needed?\r\n        case CalculatorActions.ShowPaymentDialog:\r\n          return true;\r\n        case CalculatorActions.AllowForcePay: // \"Allow forcepay\" action is payment action when calculation is not valid. Logic handled in UI for now.\r\n        case CalculatorActions.Pay:\r\n        case CalculatorActions.Recalculate:\r\n        default:\r\n          return false;\r\n      }\r\n    } else {\r\n      switch (action) {\r\n        case CalculatorActions.AllowForcePay:\r\n          //TODO: refactor this to contain only allowed status, not disallowed\r\n          return this.isForcePayAllAllowed &&\r\n            (this.current.workflow.status != CalculationStatus.WaitingApproval &&\r\n              this.current.workflow.status != CalculationStatus.SharedRejected &&\r\n              this.current.workflow.status != CalculationStatus.SharedWaiting &&\r\n              this.current.workflow.status != CalculationStatus.Repair\r\n            );\r\n        case CalculatorActions.Pay:\r\n          // add here isValid?\r\n          return this.current.workflow.status == CalculationStatus.Draft ||\r\n            this.current.workflow.status == CalculationStatus.ProDraft ||\r\n            this.current.workflow.status == CalculationStatus.SharedApproved;\r\n        case CalculatorActions.Save:\r\n          return this.current.workflow.status == CalculationStatus.Draft ||\r\n            this.current.workflow.status == CalculationStatus.ProDraft ||\r\n            this.current.workflow.status == CalculationStatus.SharedApproved ||\r\n            this.current.workflow.status == CalculationStatus.History ||\r\n            this.current.workflow.status == CalculationStatus.Repair;\r\n        case CalculatorActions.Delete:\r\n          return this.current.workflow.status == CalculationStatus.Draft ||\r\n            this.current.workflow.status == CalculationStatus.ProDraft ||\r\n            this.current.workflow.status == CalculationStatus.SharedRejected ||\r\n            this.current.workflow.status == CalculationStatus.History ||\r\n            this.current.workflow.status == CalculationStatus.Repair;\r\n        case CalculatorActions.SendToPro:\r\n          return this.current.workflow.status == CalculationStatus.WaitingApproval;\r\n        case CalculatorActions.Recalculate:\r\n          return true;\r\n        case CalculatorActions.Reject:\r\n          return this.current.workflow.status == CalculationStatus.SharedApproved ||\r\n            this.current.workflow.status == CalculationStatus.SharedWaiting;\r\n        case CalculatorActions.Approve:\r\n          return this.current.workflow.status == CalculationStatus.SharedRejected ||\r\n            this.current.workflow.status == CalculationStatus.SharedWaiting;\r\n        case CalculatorActions.SetSalaryDateKind:\r\n          return (this.current.workflow.status == CalculationStatus.Draft ||\r\n            this.current.workflow.status == CalculationStatus.ProDraft ||\r\n            this.current.workflow.status == CalculationStatus.SharedApproved) &&\r\n            (\r\n              InvoicesLogic.isPalkkausManualLike(this.current.info.paymentChannel) ||\r\n              InvoicesLogic.isPalkkausInvoicesLike(this.current.info.paymentChannel) ||\r\n              this.current.info.paymentChannel == PaymentChannel.PalkkausCfaTest ||\r\n              this.current.info.paymentChannel == PaymentChannel.Briox ||\r\n              this.current.info.paymentChannel == PaymentChannel.Askelma ||\r\n              this.current.info.paymentChannel == PaymentChannel.PasseliMerit ||\r\n              this.current.info.paymentChannel == PaymentChannel.Ecom ||\r\n              this.current.info.paymentChannel == PaymentChannel.Hausvise\r\n            );\r\n        default:\r\n          return false;\r\n      }\r\n    }\r\n\r\n  }\r\n\r\n  /**\r\n   * Returns true, if action (button) is disabled\r\n   * TODO: Add rules based on roles and validation? Pay button logic is in UI.\r\n   */\r\n  public isActionDisabled(action: CalculatorActions): boolean {\r\n    if (!this.current) {\r\n      return true;\r\n    }\r\n    // In read only mode\r\n    if (this.isReadOnlyForced) {\r\n      return true;\r\n    }\r\n\r\n    if (this.current.isReadOnly) {\r\n      switch (action) {\r\n        case CalculatorActions.Delete:\r\n          return this.current.workflow.status == CalculationStatus.PaymentStarted;\r\n        case CalculatorActions.Save:\r\n          // add here isValid?\r\n          return this.current.workflow.status == CalculationStatus.PaymentStarted;\r\n        default:\r\n          return true;\r\n      }\r\n    }\r\n  }\r\n\r\n  /** Loads the available usecases => The UI shows them as selection. */\r\n  public showUsecasesSelection(): Promise<Calculation> {\r\n    this.usecases = [];\r\n    return this.setStatus(this.usecasesService.getActiveUsecaseListItems(ApiItemType.Calculation).then((list) => {\r\n      if (list.length) {\r\n        this.usecases = list.sort((a, b) => (a.data.order || 100) - (b.data.order || 100));\r\n      } else {\r\n        // No usecases => use default\r\n        this.usecases = null;\r\n      }\r\n      return this.current;\r\n    }));\r\n  }\r\n\r\n  /**\r\n   * Sets the given usecase to the current calculation.\r\n   * @param uri Uri for the new usecase.\r\n   */\r\n  public setUsecase(uri: string): void {\r\n    this.setStatus(this.usecasesService.assureUsecase(ApiItemType.Calculation, this.current, uri).then((uc) => {\r\n      this.usecase = uc;\r\n      //this.callEvent(\"onLoad\");\r\n      this.usecases = null;\r\n      return this.current;\r\n    }));\r\n  }\r\n\r\n\r\n  /**\r\n   * Gets a total of row type(s)\r\n   * @param types A single row type or array of types to filter for calculation.\r\n   */\r\n  public getRowTotal(types: CalculationRowType | CalculationRowType[]) {\r\n    if (!types) {\r\n      return 0;\r\n    }\r\n    if (!Array.isArray(types)) {\r\n      types = [types];\r\n    }\r\n    return Arrays.sum(this.current?.result?.rows || [], (x) => types.indexOf(x.rowType) >= 0 ? x.total : 0);\r\n  }\r\n\r\n  /**\r\n   * Shows a report for the current calculation using a modal dialog.\r\n   * @param reportType - Type of report to show\r\n   */\r\n  public showReportDialog(reportType: calcReportType) {\r\n    this.reportsService.showReportModalForCalc(reportType, this.current);\r\n  }\r\n\r\n  /**\r\n   * Shows a dialog for modifying an existing Worker:\r\n   * Saves changes and updates the calculation.\r\n   */\r\n  public showWorkerEditDialog() {\r\n    this.uiCrudHelpers.openEditEmploymentDialog(this.current.worker.employmentId, \"updateCalc\")\r\n      .then((result) => {\r\n        if (result.action === \"ok\" || result.action === \"ok-no-rows\") {\r\n          const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.CalcComponent.dialog.showWorkerEditDialogLoading\");\r\n          this.updateFromEmployment(result.item.id, result.action === \"ok\").then(() => {\r\n            loader.dismiss();\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n  /** Shows infor dialog about the current usecase in the calculation. */\r\n  public showUsecaseInfo(): void {\r\n    this.uiHelpers.openEditDialog(\"salaxy-components/modals/workflow/UsecaseInfo.html\", this.usecase, {\r\n      objUsecase: this.current.usecase,\r\n      canDelete: this.isNew(),\r\n    }, \"lg\").then((result) => {\r\n      if (result.action == EditDialogKnownActions.Delete && this.isNew()) {\r\n        this.usecase = null;\r\n        this.current.usecase = {};\r\n        return this.showUsecasesSelection();\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shows a dialog during the check of auto taxcard.\r\n   */\r\n  public showRefreshAutoTaxcardDialog() {\r\n    const loader = this.uiHelpers.showLoading();\r\n    this.uiCrudHelpers.refreshAutoTaxcard(this.current.worker.tax?.taxcardId, this.current.workflow?.salaryDate).then(() => {\r\n      loader.dismiss();\r\n      this.recalculate();\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shows a dialog for adding a new Employment relation.\r\n   * If user goes through the wizard the employment relation is saved and set to the calculation.\r\n   */\r\n  public showNewWorkerDialog() {\r\n    this.uiCrudHelpers.createNewEmployment().then((result) => {\r\n      if (result.action === \"ok\") {\r\n        this.updateFromEmployment(result.item.id, true);\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Returns validation for current calculation or empty validation object if the calculation has not been recalculated (validated).\r\n   */\r\n  public get validation() {\r\n    return this.current?.result?.validation || { errors: [], hasAllRequiredFields: true, isValid: true };\r\n  }\r\n\r\n  /** Returns true if the payment is possible when the employer pays all.  */\r\n  public get isForcePayAllAllowed(): boolean {\r\n    const obj = this.validation.errors.find((x) =>\r\n      (x.type !== \"warning\"));\r\n    return !obj;\r\n  }\r\n  /** HACK: This will be removed after moved to useCase based calculators. Placeholder for usecase specific logic in history calculation. */\r\n  public historyUsecase = {\r\n    save: () => {\r\n      this.detailsUrl = \"/calc/history/\";\r\n      this.current.workflow.status = CalculationStatus.History,\r\n        this.current.workflow.salaryDateKind = SalaryDateKind.InPast;\r\n      this.save();\r\n    },\r\n    recalculate: () => {\r\n      this.current.workflow.status = CalculationStatus.History,\r\n        this.current.workflow.salaryDateKind = SalaryDateKind.InPast;\r\n      this.recalculate();\r\n    }\r\n  };\r\n}","import angular from \"angular\";\r\n\r\nimport { ApiValidation, CalculationRowType, DataMapper, Dataset, DatasetListItem, Datasets, Employment, Employments, FileParser, HrSuuntiImportLogic, Importable, RowTypeMatch, SalaryBasesRow, ValidationHelper } from \"@salaxy/core\";\r\nimport { SalaryBases } from \"./SalaryBases\";\r\nimport { EditDialogKnownActions, JsonSchemaService, UiCrudHelpers, UiHelpers } from \"../../../services\";\r\nimport { PayrollCrudController } from \"../PayrollCrudController\";\r\nimport { AjaxNg1 } from \"../../../ajax\";\r\nimport { ImportController } from \"../../helpers/ImportController\";\r\n\r\n/**\r\n * Controller for employer and worker charts using angular-chart\r\n */\r\nexport class SalaryBasesController implements angular.IController {\r\n\r\n  /*\r\n  TODO-lista:\r\n  - Uuden rivin luominen: Eri tyypit (ignore, warning etc.)\r\n  - Warning ja Error toimimaan\r\n  - TODO ja HACK\r\n  - Saako rivin muokkauksen dialogiin (Usecase)\r\n  - Rivin muokkaus Rivit-näkymään (rowType-dialogi)\r\n  */\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Employments\", \"UiCrudHelpers\", \"UiHelpers\", \"AjaxNg1\", \"JsonSchemaService\", \"Datasets\"];\r\n\r\n  /** Source data that is mapped to salary bases suitable to creating calculations etc. */\r\n  public current: SalaryBases;\r\n\r\n  /** Full set of employments for binding to data. */\r\n  public employments: Employment[];\r\n\r\n  /** Datasets that define the import pattern / settings. */\r\n  public datasets: DatasetListItem[];\r\n\r\n  /** Current dataset that contains the definition data for the import. */\r\n  public dataset: Dataset;\r\n\r\n  /** Payroll controller that contains the payroll that is being edited. */\r\n  public payrollController: PayrollCrudController;\r\n\r\n  public importController: ImportController;\r\n\r\n  /** Active tab: set by the import operations. */\r\n  public currentTab: string;\r\n\r\n  /** TODO: Move to enum, also add descriptions */\r\n  public matchTypes = {\r\n    row: \"Oletusrivi\",\r\n    hourlyRow: \"Tuntipalkkaan perustuva rivi\",\r\n    monthlySalary: \"Kuukausipalkka\",\r\n    ignore: \"Ohitetaan\",\r\n    warning: \"Varoitus\",\r\n    error: \"Virhe\",\r\n  };\r\n\r\n  /**\r\n   * Creates a new SalaryBasesController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    private employmentsApi: Employments,\r\n    private uiCrudHelpers: UiCrudHelpers,\r\n    private uiHelpers: UiHelpers,\r\n    private ajax: AjaxNg1,\r\n    private jsonSchemaService: JsonSchemaService,\r\n    private datasetsApi: Datasets\r\n    ) {\r\n    // Dependency injection\r\n  }\r\n\r\n  /** Initializes the controller. */\r\n  public $onInit() {\r\n    this.current = {};\r\n    this.datasetsApi.getOData({\r\n      // TODO: Perhaps add `status eq \"draft/instance/template\"`\r\n      $filter: `entityType eq 'import'`,\r\n    }).then((result) => {\r\n      this.datasets = result.items;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Loads the given dataset.\r\n   * @param datasetToLoad List item for which the whole dataset should be loaded.\r\n   */\r\n  public loadDataset(datasetToLoad: DatasetListItem): void {\r\n    const loader = this.uiHelpers.showLoading();\r\n    this.datasetsApi.getSingle(datasetToLoad.id).then((result) => {\r\n      this.dataset = result;\r\n      loader.dismiss();\r\n    });\r\n  }\r\n\r\n  /** The row types mapper from the dataset */\r\n  public getRowTypeMapper(): RowTypeMatch[] {\r\n    if (!this.dataset.data[0]?.content?.length) {\r\n      this.dataset.data[0].content = HrSuuntiImportLogic.getRowTypeMapperEditable();\r\n    }\r\n    return this.dataset.data[0].content;\r\n  }\r\n\r\n  /** Fetches the employment relations for operations on this UI. */\r\n  public getEmployments() {\r\n    const loader = this.uiHelpers.showLoading(\"Ladataan työsuhteita...\");\r\n    this.employmentsApi.getActiveFullObject(null).then((result) => {\r\n      if (this.payrollController?.current) {\r\n        const payrollEmployments = this.payrollController.current.calcs.map((x) => x.worker.employmentId);\r\n        result.forEach((x) => {\r\n          if (payrollEmployments.find((id) => x.id == id)) {\r\n            x.usecase.data = x.usecase.data || {};\r\n            x.usecase.data.isPayroll = true;\r\n          }\r\n        });\r\n      }\r\n      this.employments = result;\r\n      this.currentTab = \"employments\";\r\n      loader.dismiss();\r\n    });\r\n  }\r\n\r\n  /** Gets the importable interface for importing the SalaryBasesRows */\r\n  public getImportable(): Importable<SalaryBasesRow> {\r\n    const result: Importable<SalaryBasesRow> = {\r\n      getImportMappers() {\r\n        return [{\r\n          value: \"NG1/SalaryBasesController/HRSuunti\",\r\n          text: \"HR Suunti / Tikon tuonti\",\r\n        }];\r\n      },\r\n      getImportMapper: async () => {\r\n        const mapper = new DataMapper<any, SalaryBasesRow>(\"NG1/SalaryBasesController/HRSuunti\", \"HR Suunti / Tikon tuonti\");\r\n        const map = {\r\n          PVM: \"date\",\r\n          TYNRO: \"srcEmploymentId\",\r\n          PLNRO: \"srcRowTypeId\",\r\n          TVR: null,\r\n          \"KPL/MISTÄ\": \"count\",\r\n          \"AIKA/MIHIN\": null,\r\n          \"MK/EUR\": null,\r\n          \"OSASTO\": \"costCenter\",\r\n        };\r\n        await mapper.setSchemaFromCache(this.jsonSchemaService.getCache(), \"salaxy-secure/schemas/v02.json\", \"SalaryBasesRow\", \"target\");\r\n        mapper.setPaths(map);\r\n        mapper.generateSchema(\"HRSuuntiTikon\", \"source\");\r\n        return mapper;\r\n      },\r\n      parsers: FileParser.getDefaultParsers(),\r\n      finalize: (items) => {\r\n        this.current.rows = items;\r\n        this.currentTab = \"rows\";\r\n        return Promise.resolve();\r\n      },\r\n      validate: (item: SalaryBasesRow, ix): Promise<{item: SalaryBasesRow, validation: ApiValidation }> => {\r\n        const validation: ApiValidation = {};\r\n        const helper = new ValidationHelper(validation);\r\n        if (this.employments?.length) {\r\n          HrSuuntiImportLogic.resolveEmployment(item, this.employments);\r\n          helper.checkNotEmpty(item, \"employmentId\", `Työntekijää ei löydy: ${item.srcEmploymentId}.`);\r\n        } else {\r\n          if (ix == 0) {\r\n            helper.error(\"Ei työsuhteita - tietoja ei voi tuoda! Hae ensin työsuhteet ja tuo rivit vasta sen jälkeen.\", \"Ei työsuhteita\");\r\n          }\r\n        }\r\n\r\n        helper.checkNotEmpty(item, \"srcRowTypeId\", \"TYNRO (srcRowTypeId) puuttuu\");\r\n        helper.checkNotEmpty(item, \"date\", \"PVM (date) puuttuu\");\r\n        helper.checkNotEmpty(item, \"srcRowTypeId\", \"PLNRO (srcRowTypeId) puuttuu\");\r\n        helper.checkNotEmpty(item, \"count\", \"KPL/MISTÄ (count) puuttuu\");\r\n        helper.checkNotEmpty(item, \"costCenter\", \"OSASTO (costCenter) puuttuu\");\r\n        helper.recalc();\r\n        return Promise.resolve({ item, validation });\r\n      },\r\n    };\r\n    return result;\r\n  }\r\n\r\n  /** Saves the dataset. */\r\n  public save(): void {\r\n    const loader = this.uiHelpers.showLoading(\"Tallennetaan\");\r\n    this.dataset.data[0].content.forEach((row) => {\r\n      Object.keys(row).filter((key) => key[0] == \"$\") .forEach((key) => {\r\n        delete row[key];\r\n      });\r\n    });\r\n    this.datasetsApi.save(this.dataset).then((result) => {\r\n      this.dataset = result;\r\n      loader.dismiss();\r\n    });\r\n  }\r\n\r\n  /** Processes the import  */\r\n  public processImport() {\r\n    if (!this.current.rows?.length) {\r\n      alert(\"Hae ensin työsuhteet (1.) ja lataa data (2.)!\");\r\n      return;\r\n    }\r\n\r\n    // TODO: Copying is done so that String => RegEx is not saved. Handle this in core.\r\n    const mapper = angular.copy(this.getRowTypeMapper());\r\n    HrSuuntiImportLogic.resolveTypesAndPrices(this.current.rows, mapper);\r\n    this.currentTab = \"rows\";\r\n  }\r\n\r\n  /** Saves the rows to the given payroll */\r\n  public saveToPayroll() {\r\n    if ((this.payrollController?.currentId || \"new\") == \"new\") {\r\n      alert(\"Palkkalista ei ole vielä ladattu! Ei voi tallentaa!\");\r\n      return;\r\n    }\r\n    if (!this.current?.rows?.length) {\r\n      alert(\"Ei rivejä!\");\r\n      return;\r\n    }\r\n    const rows = this.current.rows.filter((x) => x.rowType && x.rowType != CalculationRowType.Unknown);\r\n    const loader = this.uiHelpers.showLoading(\"Tallennetaan palkkalistaa\");\r\n    HrSuuntiImportLogic.addToPayroll(this.payrollController.currentId, rows, this.employments, this.ajax).then((x) => {\r\n      loader.dismiss();\r\n      alert(\"Rivit on tallennettu palkkalistaan: \" + x.id);\r\n      this.currentTab = \"payroll\";\r\n      this.payrollController.reload();\r\n    });\r\n  }\r\n\r\n\r\n  /** Shows a dialog box for editing the employment. */\r\n  public editEmployment(row: Employment) {\r\n    this.uiCrudHelpers.openEditEmploymentDialog(row.id, \"updateCalc\").then((result) => {\r\n      if (result.action == EditDialogKnownActions.Ok) {\r\n        angular.merge(row, result.item);\r\n      }\r\n    });\r\n  }\r\n}\r\n","/*!\n * @kurkle/color v0.3.2\n * https://github.com/kurkle/color#readme\n * (c) 2023 Jukka Kurkela\n * Released under the MIT License\n */\nfunction round(v) {\n  return v + 0.5 | 0;\n}\nconst lim = (v, l, h) => Math.max(Math.min(v, h), l);\nfunction p2b(v) {\n  return lim(round(v * 2.55), 0, 255);\n}\nfunction b2p(v) {\n  return lim(round(v / 2.55), 0, 100);\n}\nfunction n2b(v) {\n  return lim(round(v * 255), 0, 255);\n}\nfunction b2n(v) {\n  return lim(round(v / 2.55) / 100, 0, 1);\n}\nfunction n2p(v) {\n  return lim(round(v * 100), 0, 100);\n}\n\nconst map$1 = {0: 0, 1: 1, 2: 2, 3: 3, 4: 4, 5: 5, 6: 6, 7: 7, 8: 8, 9: 9, A: 10, B: 11, C: 12, D: 13, E: 14, F: 15, a: 10, b: 11, c: 12, d: 13, e: 14, f: 15};\nconst hex = [...'0123456789ABCDEF'];\nconst h1 = b => hex[b & 0xF];\nconst h2 = b => hex[(b & 0xF0) >> 4] + hex[b & 0xF];\nconst eq = b => ((b & 0xF0) >> 4) === (b & 0xF);\nconst isShort = v => eq(v.r) && eq(v.g) && eq(v.b) && eq(v.a);\nfunction hexParse(str) {\n  var len = str.length;\n  var ret;\n  if (str[0] === '#') {\n    if (len === 4 || len === 5) {\n      ret = {\n        r: 255 & map$1[str[1]] * 17,\n        g: 255 & map$1[str[2]] * 17,\n        b: 255 & map$1[str[3]] * 17,\n        a: len === 5 ? map$1[str[4]] * 17 : 255\n      };\n    } else if (len === 7 || len === 9) {\n      ret = {\n        r: map$1[str[1]] << 4 | map$1[str[2]],\n        g: map$1[str[3]] << 4 | map$1[str[4]],\n        b: map$1[str[5]] << 4 | map$1[str[6]],\n        a: len === 9 ? (map$1[str[7]] << 4 | map$1[str[8]]) : 255\n      };\n    }\n  }\n  return ret;\n}\nconst alpha = (a, f) => a < 255 ? f(a) : '';\nfunction hexString(v) {\n  var f = isShort(v) ? h1 : h2;\n  return v\n    ? '#' + f(v.r) + f(v.g) + f(v.b) + alpha(v.a, f)\n    : undefined;\n}\n\nconst HUE_RE = /^(hsla?|hwb|hsv)\\(\\s*([-+.e\\d]+)(?:deg)?[\\s,]+([-+.e\\d]+)%[\\s,]+([-+.e\\d]+)%(?:[\\s,]+([-+.e\\d]+)(%)?)?\\s*\\)$/;\nfunction hsl2rgbn(h, s, l) {\n  const a = s * Math.min(l, 1 - l);\n  const f = (n, k = (n + h / 30) % 12) => l - a * Math.max(Math.min(k - 3, 9 - k, 1), -1);\n  return [f(0), f(8), f(4)];\n}\nfunction hsv2rgbn(h, s, v) {\n  const f = (n, k = (n + h / 60) % 6) => v - v * s * Math.max(Math.min(k, 4 - k, 1), 0);\n  return [f(5), f(3), f(1)];\n}\nfunction hwb2rgbn(h, w, b) {\n  const rgb = hsl2rgbn(h, 1, 0.5);\n  let i;\n  if (w + b > 1) {\n    i = 1 / (w + b);\n    w *= i;\n    b *= i;\n  }\n  for (i = 0; i < 3; i++) {\n    rgb[i] *= 1 - w - b;\n    rgb[i] += w;\n  }\n  return rgb;\n}\nfunction hueValue(r, g, b, d, max) {\n  if (r === max) {\n    return ((g - b) / d) + (g < b ? 6 : 0);\n  }\n  if (g === max) {\n    return (b - r) / d + 2;\n  }\n  return (r - g) / d + 4;\n}\nfunction rgb2hsl(v) {\n  const range = 255;\n  const r = v.r / range;\n  const g = v.g / range;\n  const b = v.b / range;\n  const max = Math.max(r, g, b);\n  const min = Math.min(r, g, b);\n  const l = (max + min) / 2;\n  let h, s, d;\n  if (max !== min) {\n    d = max - min;\n    s = l > 0.5 ? d / (2 - max - min) : d / (max + min);\n    h = hueValue(r, g, b, d, max);\n    h = h * 60 + 0.5;\n  }\n  return [h | 0, s || 0, l];\n}\nfunction calln(f, a, b, c) {\n  return (\n    Array.isArray(a)\n      ? f(a[0], a[1], a[2])\n      : f(a, b, c)\n  ).map(n2b);\n}\nfunction hsl2rgb(h, s, l) {\n  return calln(hsl2rgbn, h, s, l);\n}\nfunction hwb2rgb(h, w, b) {\n  return calln(hwb2rgbn, h, w, b);\n}\nfunction hsv2rgb(h, s, v) {\n  return calln(hsv2rgbn, h, s, v);\n}\nfunction hue(h) {\n  return (h % 360 + 360) % 360;\n}\nfunction hueParse(str) {\n  const m = HUE_RE.exec(str);\n  let a = 255;\n  let v;\n  if (!m) {\n    return;\n  }\n  if (m[5] !== v) {\n    a = m[6] ? p2b(+m[5]) : n2b(+m[5]);\n  }\n  const h = hue(+m[2]);\n  const p1 = +m[3] / 100;\n  const p2 = +m[4] / 100;\n  if (m[1] === 'hwb') {\n    v = hwb2rgb(h, p1, p2);\n  } else if (m[1] === 'hsv') {\n    v = hsv2rgb(h, p1, p2);\n  } else {\n    v = hsl2rgb(h, p1, p2);\n  }\n  return {\n    r: v[0],\n    g: v[1],\n    b: v[2],\n    a: a\n  };\n}\nfunction rotate(v, deg) {\n  var h = rgb2hsl(v);\n  h[0] = hue(h[0] + deg);\n  h = hsl2rgb(h);\n  v.r = h[0];\n  v.g = h[1];\n  v.b = h[2];\n}\nfunction hslString(v) {\n  if (!v) {\n    return;\n  }\n  const a = rgb2hsl(v);\n  const h = a[0];\n  const s = n2p(a[1]);\n  const l = n2p(a[2]);\n  return v.a < 255\n    ? `hsla(${h}, ${s}%, ${l}%, ${b2n(v.a)})`\n    : `hsl(${h}, ${s}%, ${l}%)`;\n}\n\nconst map = {\n  x: 'dark',\n  Z: 'light',\n  Y: 're',\n  X: 'blu',\n  W: 'gr',\n  V: 'medium',\n  U: 'slate',\n  A: 'ee',\n  T: 'ol',\n  S: 'or',\n  B: 'ra',\n  C: 'lateg',\n  D: 'ights',\n  R: 'in',\n  Q: 'turquois',\n  E: 'hi',\n  P: 'ro',\n  O: 'al',\n  N: 'le',\n  M: 'de',\n  L: 'yello',\n  F: 'en',\n  K: 'ch',\n  G: 'arks',\n  H: 'ea',\n  I: 'ightg',\n  J: 'wh'\n};\nconst names$1 = {\n  OiceXe: 'f0f8ff',\n  antiquewEte: 'faebd7',\n  aqua: 'ffff',\n  aquamarRe: '7fffd4',\n  azuY: 'f0ffff',\n  beige: 'f5f5dc',\n  bisque: 'ffe4c4',\n  black: '0',\n  blanKedOmond: 'ffebcd',\n  Xe: 'ff',\n  XeviTet: '8a2be2',\n  bPwn: 'a52a2a',\n  burlywood: 'deb887',\n  caMtXe: '5f9ea0',\n  KartYuse: '7fff00',\n  KocTate: 'd2691e',\n  cSO: 'ff7f50',\n  cSnflowerXe: '6495ed',\n  cSnsilk: 'fff8dc',\n  crimson: 'dc143c',\n  cyan: 'ffff',\n  xXe: '8b',\n  xcyan: '8b8b',\n  xgTMnPd: 'b8860b',\n  xWay: 'a9a9a9',\n  xgYF: '6400',\n  xgYy: 'a9a9a9',\n  xkhaki: 'bdb76b',\n  xmagFta: '8b008b',\n  xTivegYF: '556b2f',\n  xSange: 'ff8c00',\n  xScEd: '9932cc',\n  xYd: '8b0000',\n  xsOmon: 'e9967a',\n  xsHgYF: '8fbc8f',\n  xUXe: '483d8b',\n  xUWay: '2f4f4f',\n  xUgYy: '2f4f4f',\n  xQe: 'ced1',\n  xviTet: '9400d3',\n  dAppRk: 'ff1493',\n  dApskyXe: 'bfff',\n  dimWay: '696969',\n  dimgYy: '696969',\n  dodgerXe: '1e90ff',\n  fiYbrick: 'b22222',\n  flSOwEte: 'fffaf0',\n  foYstWAn: '228b22',\n  fuKsia: 'ff00ff',\n  gaRsbSo: 'dcdcdc',\n  ghostwEte: 'f8f8ff',\n  gTd: 'ffd700',\n  gTMnPd: 'daa520',\n  Way: '808080',\n  gYF: '8000',\n  gYFLw: 'adff2f',\n  gYy: '808080',\n  honeyMw: 'f0fff0',\n  hotpRk: 'ff69b4',\n  RdianYd: 'cd5c5c',\n  Rdigo: '4b0082',\n  ivSy: 'fffff0',\n  khaki: 'f0e68c',\n  lavFMr: 'e6e6fa',\n  lavFMrXsh: 'fff0f5',\n  lawngYF: '7cfc00',\n  NmoncEffon: 'fffacd',\n  ZXe: 'add8e6',\n  ZcSO: 'f08080',\n  Zcyan: 'e0ffff',\n  ZgTMnPdLw: 'fafad2',\n  ZWay: 'd3d3d3',\n  ZgYF: '90ee90',\n  ZgYy: 'd3d3d3',\n  ZpRk: 'ffb6c1',\n  ZsOmon: 'ffa07a',\n  ZsHgYF: '20b2aa',\n  ZskyXe: '87cefa',\n  ZUWay: '778899',\n  ZUgYy: '778899',\n  ZstAlXe: 'b0c4de',\n  ZLw: 'ffffe0',\n  lime: 'ff00',\n  limegYF: '32cd32',\n  lRF: 'faf0e6',\n  magFta: 'ff00ff',\n  maPon: '800000',\n  VaquamarRe: '66cdaa',\n  VXe: 'cd',\n  VScEd: 'ba55d3',\n  VpurpN: '9370db',\n  VsHgYF: '3cb371',\n  VUXe: '7b68ee',\n  VsprRggYF: 'fa9a',\n  VQe: '48d1cc',\n  VviTetYd: 'c71585',\n  midnightXe: '191970',\n  mRtcYam: 'f5fffa',\n  mistyPse: 'ffe4e1',\n  moccasR: 'ffe4b5',\n  navajowEte: 'ffdead',\n  navy: '80',\n  Tdlace: 'fdf5e6',\n  Tive: '808000',\n  TivedBb: '6b8e23',\n  Sange: 'ffa500',\n  SangeYd: 'ff4500',\n  ScEd: 'da70d6',\n  pOegTMnPd: 'eee8aa',\n  pOegYF: '98fb98',\n  pOeQe: 'afeeee',\n  pOeviTetYd: 'db7093',\n  papayawEp: 'ffefd5',\n  pHKpuff: 'ffdab9',\n  peru: 'cd853f',\n  pRk: 'ffc0cb',\n  plum: 'dda0dd',\n  powMrXe: 'b0e0e6',\n  purpN: '800080',\n  YbeccapurpN: '663399',\n  Yd: 'ff0000',\n  Psybrown: 'bc8f8f',\n  PyOXe: '4169e1',\n  saddNbPwn: '8b4513',\n  sOmon: 'fa8072',\n  sandybPwn: 'f4a460',\n  sHgYF: '2e8b57',\n  sHshell: 'fff5ee',\n  siFna: 'a0522d',\n  silver: 'c0c0c0',\n  skyXe: '87ceeb',\n  UXe: '6a5acd',\n  UWay: '708090',\n  UgYy: '708090',\n  snow: 'fffafa',\n  sprRggYF: 'ff7f',\n  stAlXe: '4682b4',\n  tan: 'd2b48c',\n  teO: '8080',\n  tEstN: 'd8bfd8',\n  tomato: 'ff6347',\n  Qe: '40e0d0',\n  viTet: 'ee82ee',\n  JHt: 'f5deb3',\n  wEte: 'ffffff',\n  wEtesmoke: 'f5f5f5',\n  Lw: 'ffff00',\n  LwgYF: '9acd32'\n};\nfunction unpack() {\n  const unpacked = {};\n  const keys = Object.keys(names$1);\n  const tkeys = Object.keys(map);\n  let i, j, k, ok, nk;\n  for (i = 0; i < keys.length; i++) {\n    ok = nk = keys[i];\n    for (j = 0; j < tkeys.length; j++) {\n      k = tkeys[j];\n      nk = nk.replace(k, map[k]);\n    }\n    k = parseInt(names$1[ok], 16);\n    unpacked[nk] = [k >> 16 & 0xFF, k >> 8 & 0xFF, k & 0xFF];\n  }\n  return unpacked;\n}\n\nlet names;\nfunction nameParse(str) {\n  if (!names) {\n    names = unpack();\n    names.transparent = [0, 0, 0, 0];\n  }\n  const a = names[str.toLowerCase()];\n  return a && {\n    r: a[0],\n    g: a[1],\n    b: a[2],\n    a: a.length === 4 ? a[3] : 255\n  };\n}\n\nconst RGB_RE = /^rgba?\\(\\s*([-+.\\d]+)(%)?[\\s,]+([-+.e\\d]+)(%)?[\\s,]+([-+.e\\d]+)(%)?(?:[\\s,/]+([-+.e\\d]+)(%)?)?\\s*\\)$/;\nfunction rgbParse(str) {\n  const m = RGB_RE.exec(str);\n  let a = 255;\n  let r, g, b;\n  if (!m) {\n    return;\n  }\n  if (m[7] !== r) {\n    const v = +m[7];\n    a = m[8] ? p2b(v) : lim(v * 255, 0, 255);\n  }\n  r = +m[1];\n  g = +m[3];\n  b = +m[5];\n  r = 255 & (m[2] ? p2b(r) : lim(r, 0, 255));\n  g = 255 & (m[4] ? p2b(g) : lim(g, 0, 255));\n  b = 255 & (m[6] ? p2b(b) : lim(b, 0, 255));\n  return {\n    r: r,\n    g: g,\n    b: b,\n    a: a\n  };\n}\nfunction rgbString(v) {\n  return v && (\n    v.a < 255\n      ? `rgba(${v.r}, ${v.g}, ${v.b}, ${b2n(v.a)})`\n      : `rgb(${v.r}, ${v.g}, ${v.b})`\n  );\n}\n\nconst to = v => v <= 0.0031308 ? v * 12.92 : Math.pow(v, 1.0 / 2.4) * 1.055 - 0.055;\nconst from = v => v <= 0.04045 ? v / 12.92 : Math.pow((v + 0.055) / 1.055, 2.4);\nfunction interpolate(rgb1, rgb2, t) {\n  const r = from(b2n(rgb1.r));\n  const g = from(b2n(rgb1.g));\n  const b = from(b2n(rgb1.b));\n  return {\n    r: n2b(to(r + t * (from(b2n(rgb2.r)) - r))),\n    g: n2b(to(g + t * (from(b2n(rgb2.g)) - g))),\n    b: n2b(to(b + t * (from(b2n(rgb2.b)) - b))),\n    a: rgb1.a + t * (rgb2.a - rgb1.a)\n  };\n}\n\nfunction modHSL(v, i, ratio) {\n  if (v) {\n    let tmp = rgb2hsl(v);\n    tmp[i] = Math.max(0, Math.min(tmp[i] + tmp[i] * ratio, i === 0 ? 360 : 1));\n    tmp = hsl2rgb(tmp);\n    v.r = tmp[0];\n    v.g = tmp[1];\n    v.b = tmp[2];\n  }\n}\nfunction clone(v, proto) {\n  return v ? Object.assign(proto || {}, v) : v;\n}\nfunction fromObject(input) {\n  var v = {r: 0, g: 0, b: 0, a: 255};\n  if (Array.isArray(input)) {\n    if (input.length >= 3) {\n      v = {r: input[0], g: input[1], b: input[2], a: 255};\n      if (input.length > 3) {\n        v.a = n2b(input[3]);\n      }\n    }\n  } else {\n    v = clone(input, {r: 0, g: 0, b: 0, a: 1});\n    v.a = n2b(v.a);\n  }\n  return v;\n}\nfunction functionParse(str) {\n  if (str.charAt(0) === 'r') {\n    return rgbParse(str);\n  }\n  return hueParse(str);\n}\nclass Color {\n  constructor(input) {\n    if (input instanceof Color) {\n      return input;\n    }\n    const type = typeof input;\n    let v;\n    if (type === 'object') {\n      v = fromObject(input);\n    } else if (type === 'string') {\n      v = hexParse(input) || nameParse(input) || functionParse(input);\n    }\n    this._rgb = v;\n    this._valid = !!v;\n  }\n  get valid() {\n    return this._valid;\n  }\n  get rgb() {\n    var v = clone(this._rgb);\n    if (v) {\n      v.a = b2n(v.a);\n    }\n    return v;\n  }\n  set rgb(obj) {\n    this._rgb = fromObject(obj);\n  }\n  rgbString() {\n    return this._valid ? rgbString(this._rgb) : undefined;\n  }\n  hexString() {\n    return this._valid ? hexString(this._rgb) : undefined;\n  }\n  hslString() {\n    return this._valid ? hslString(this._rgb) : undefined;\n  }\n  mix(color, weight) {\n    if (color) {\n      const c1 = this.rgb;\n      const c2 = color.rgb;\n      let w2;\n      const p = weight === w2 ? 0.5 : weight;\n      const w = 2 * p - 1;\n      const a = c1.a - c2.a;\n      const w1 = ((w * a === -1 ? w : (w + a) / (1 + w * a)) + 1) / 2.0;\n      w2 = 1 - w1;\n      c1.r = 0xFF & w1 * c1.r + w2 * c2.r + 0.5;\n      c1.g = 0xFF & w1 * c1.g + w2 * c2.g + 0.5;\n      c1.b = 0xFF & w1 * c1.b + w2 * c2.b + 0.5;\n      c1.a = p * c1.a + (1 - p) * c2.a;\n      this.rgb = c1;\n    }\n    return this;\n  }\n  interpolate(color, t) {\n    if (color) {\n      this._rgb = interpolate(this._rgb, color._rgb, t);\n    }\n    return this;\n  }\n  clone() {\n    return new Color(this.rgb);\n  }\n  alpha(a) {\n    this._rgb.a = n2b(a);\n    return this;\n  }\n  clearer(ratio) {\n    const rgb = this._rgb;\n    rgb.a *= 1 - ratio;\n    return this;\n  }\n  greyscale() {\n    const rgb = this._rgb;\n    const val = round(rgb.r * 0.3 + rgb.g * 0.59 + rgb.b * 0.11);\n    rgb.r = rgb.g = rgb.b = val;\n    return this;\n  }\n  opaquer(ratio) {\n    const rgb = this._rgb;\n    rgb.a *= 1 + ratio;\n    return this;\n  }\n  negate() {\n    const v = this._rgb;\n    v.r = 255 - v.r;\n    v.g = 255 - v.g;\n    v.b = 255 - v.b;\n    return this;\n  }\n  lighten(ratio) {\n    modHSL(this._rgb, 2, ratio);\n    return this;\n  }\n  darken(ratio) {\n    modHSL(this._rgb, 2, -ratio);\n    return this;\n  }\n  saturate(ratio) {\n    modHSL(this._rgb, 1, ratio);\n    return this;\n  }\n  desaturate(ratio) {\n    modHSL(this._rgb, 1, -ratio);\n    return this;\n  }\n  rotate(deg) {\n    rotate(this._rgb, deg);\n    return this;\n  }\n}\n\nfunction index_esm(input) {\n  return new Color(input);\n}\n\nexport { Color, b2n, b2p, index_esm as default, hexParse, hexString, hsl2rgb, hslString, hsv2rgb, hueParse, hwb2rgb, lim, n2b, n2p, nameParse, p2b, rgb2hsl, rgbParse, rgbString, rotate, round };\n","/*!\n * Chart.js v4.4.2\n * https://www.chartjs.org\n * (c) 2024 Chart.js Contributors\n * Released under the MIT License\n */\nimport { Color } from '@kurkle/color';\n\n/**\n * @namespace Chart.helpers\n */ /**\n * An empty function that can be used, for example, for optional callback.\n */ function noop() {\n/* noop */ }\n/**\n * Returns a unique id, sequentially generated from a global variable.\n */ const uid = (()=>{\n    let id = 0;\n    return ()=>id++;\n})();\n/**\n * Returns true if `value` is neither null nor undefined, else returns false.\n * @param value - The value to test.\n * @since 2.7.0\n */ function isNullOrUndef(value) {\n    return value === null || typeof value === 'undefined';\n}\n/**\n * Returns true if `value` is an array (including typed arrays), else returns false.\n * @param value - The value to test.\n * @function\n */ function isArray(value) {\n    if (Array.isArray && Array.isArray(value)) {\n        return true;\n    }\n    const type = Object.prototype.toString.call(value);\n    if (type.slice(0, 7) === '[object' && type.slice(-6) === 'Array]') {\n        return true;\n    }\n    return false;\n}\n/**\n * Returns true if `value` is an object (excluding null), else returns false.\n * @param value - The value to test.\n * @since 2.7.0\n */ function isObject(value) {\n    return value !== null && Object.prototype.toString.call(value) === '[object Object]';\n}\n/**\n * Returns true if `value` is a finite number, else returns false\n * @param value  - The value to test.\n */ function isNumberFinite(value) {\n    return (typeof value === 'number' || value instanceof Number) && isFinite(+value);\n}\n/**\n * Returns `value` if finite, else returns `defaultValue`.\n * @param value - The value to return if defined.\n * @param defaultValue - The value to return if `value` is not finite.\n */ function finiteOrDefault(value, defaultValue) {\n    return isNumberFinite(value) ? value : defaultValue;\n}\n/**\n * Returns `value` if defined, else returns `defaultValue`.\n * @param value - The value to return if defined.\n * @param defaultValue - The value to return if `value` is undefined.\n */ function valueOrDefault(value, defaultValue) {\n    return typeof value === 'undefined' ? defaultValue : value;\n}\nconst toPercentage = (value, dimension)=>typeof value === 'string' && value.endsWith('%') ? parseFloat(value) / 100 : +value / dimension;\nconst toDimension = (value, dimension)=>typeof value === 'string' && value.endsWith('%') ? parseFloat(value) / 100 * dimension : +value;\n/**\n * Calls `fn` with the given `args` in the scope defined by `thisArg` and returns the\n * value returned by `fn`. If `fn` is not a function, this method returns undefined.\n * @param fn - The function to call.\n * @param args - The arguments with which `fn` should be called.\n * @param [thisArg] - The value of `this` provided for the call to `fn`.\n */ function callback(fn, args, thisArg) {\n    if (fn && typeof fn.call === 'function') {\n        return fn.apply(thisArg, args);\n    }\n}\nfunction each(loopable, fn, thisArg, reverse) {\n    let i, len, keys;\n    if (isArray(loopable)) {\n        len = loopable.length;\n        if (reverse) {\n            for(i = len - 1; i >= 0; i--){\n                fn.call(thisArg, loopable[i], i);\n            }\n        } else {\n            for(i = 0; i < len; i++){\n                fn.call(thisArg, loopable[i], i);\n            }\n        }\n    } else if (isObject(loopable)) {\n        keys = Object.keys(loopable);\n        len = keys.length;\n        for(i = 0; i < len; i++){\n            fn.call(thisArg, loopable[keys[i]], keys[i]);\n        }\n    }\n}\n/**\n * Returns true if the `a0` and `a1` arrays have the same content, else returns false.\n * @param a0 - The array to compare\n * @param a1 - The array to compare\n * @private\n */ function _elementsEqual(a0, a1) {\n    let i, ilen, v0, v1;\n    if (!a0 || !a1 || a0.length !== a1.length) {\n        return false;\n    }\n    for(i = 0, ilen = a0.length; i < ilen; ++i){\n        v0 = a0[i];\n        v1 = a1[i];\n        if (v0.datasetIndex !== v1.datasetIndex || v0.index !== v1.index) {\n            return false;\n        }\n    }\n    return true;\n}\n/**\n * Returns a deep copy of `source` without keeping references on objects and arrays.\n * @param source - The value to clone.\n */ function clone(source) {\n    if (isArray(source)) {\n        return source.map(clone);\n    }\n    if (isObject(source)) {\n        const target = Object.create(null);\n        const keys = Object.keys(source);\n        const klen = keys.length;\n        let k = 0;\n        for(; k < klen; ++k){\n            target[keys[k]] = clone(source[keys[k]]);\n        }\n        return target;\n    }\n    return source;\n}\nfunction isValidKey(key) {\n    return [\n        '__proto__',\n        'prototype',\n        'constructor'\n    ].indexOf(key) === -1;\n}\n/**\n * The default merger when Chart.helpers.merge is called without merger option.\n * Note(SB): also used by mergeConfig and mergeScaleConfig as fallback.\n * @private\n */ function _merger(key, target, source, options) {\n    if (!isValidKey(key)) {\n        return;\n    }\n    const tval = target[key];\n    const sval = source[key];\n    if (isObject(tval) && isObject(sval)) {\n        // eslint-disable-next-line @typescript-eslint/no-use-before-define\n        merge(tval, sval, options);\n    } else {\n        target[key] = clone(sval);\n    }\n}\nfunction merge(target, source, options) {\n    const sources = isArray(source) ? source : [\n        source\n    ];\n    const ilen = sources.length;\n    if (!isObject(target)) {\n        return target;\n    }\n    options = options || {};\n    const merger = options.merger || _merger;\n    let current;\n    for(let i = 0; i < ilen; ++i){\n        current = sources[i];\n        if (!isObject(current)) {\n            continue;\n        }\n        const keys = Object.keys(current);\n        for(let k = 0, klen = keys.length; k < klen; ++k){\n            merger(keys[k], target, current, options);\n        }\n    }\n    return target;\n}\nfunction mergeIf(target, source) {\n    // eslint-disable-next-line @typescript-eslint/no-use-before-define\n    return merge(target, source, {\n        merger: _mergerIf\n    });\n}\n/**\n * Merges source[key] in target[key] only if target[key] is undefined.\n * @private\n */ function _mergerIf(key, target, source) {\n    if (!isValidKey(key)) {\n        return;\n    }\n    const tval = target[key];\n    const sval = source[key];\n    if (isObject(tval) && isObject(sval)) {\n        mergeIf(tval, sval);\n    } else if (!Object.prototype.hasOwnProperty.call(target, key)) {\n        target[key] = clone(sval);\n    }\n}\n/**\n * @private\n */ function _deprecated(scope, value, previous, current) {\n    if (value !== undefined) {\n        console.warn(scope + ': \"' + previous + '\" is deprecated. Please use \"' + current + '\" instead');\n    }\n}\n// resolveObjectKey resolver cache\nconst keyResolvers = {\n    // Chart.helpers.core resolveObjectKey should resolve empty key to root object\n    '': (v)=>v,\n    // default resolvers\n    x: (o)=>o.x,\n    y: (o)=>o.y\n};\n/**\n * @private\n */ function _splitKey(key) {\n    const parts = key.split('.');\n    const keys = [];\n    let tmp = '';\n    for (const part of parts){\n        tmp += part;\n        if (tmp.endsWith('\\\\')) {\n            tmp = tmp.slice(0, -1) + '.';\n        } else {\n            keys.push(tmp);\n            tmp = '';\n        }\n    }\n    return keys;\n}\nfunction _getKeyResolver(key) {\n    const keys = _splitKey(key);\n    return (obj)=>{\n        for (const k of keys){\n            if (k === '') {\n                break;\n            }\n            obj = obj && obj[k];\n        }\n        return obj;\n    };\n}\nfunction resolveObjectKey(obj, key) {\n    const resolver = keyResolvers[key] || (keyResolvers[key] = _getKeyResolver(key));\n    return resolver(obj);\n}\n/**\n * @private\n */ function _capitalize(str) {\n    return str.charAt(0).toUpperCase() + str.slice(1);\n}\nconst defined = (value)=>typeof value !== 'undefined';\nconst isFunction = (value)=>typeof value === 'function';\n// Adapted from https://stackoverflow.com/questions/31128855/comparing-ecma6-sets-for-equality#31129384\nconst setsEqual = (a, b)=>{\n    if (a.size !== b.size) {\n        return false;\n    }\n    for (const item of a){\n        if (!b.has(item)) {\n            return false;\n        }\n    }\n    return true;\n};\n/**\n * @param e - The event\n * @private\n */ function _isClickEvent(e) {\n    return e.type === 'mouseup' || e.type === 'click' || e.type === 'contextmenu';\n}\n\n/**\n * @alias Chart.helpers.math\n * @namespace\n */ const PI = Math.PI;\nconst TAU = 2 * PI;\nconst PITAU = TAU + PI;\nconst INFINITY = Number.POSITIVE_INFINITY;\nconst RAD_PER_DEG = PI / 180;\nconst HALF_PI = PI / 2;\nconst QUARTER_PI = PI / 4;\nconst TWO_THIRDS_PI = PI * 2 / 3;\nconst log10 = Math.log10;\nconst sign = Math.sign;\nfunction almostEquals(x, y, epsilon) {\n    return Math.abs(x - y) < epsilon;\n}\n/**\n * Implementation of the nice number algorithm used in determining where axis labels will go\n */ function niceNum(range) {\n    const roundedRange = Math.round(range);\n    range = almostEquals(range, roundedRange, range / 1000) ? roundedRange : range;\n    const niceRange = Math.pow(10, Math.floor(log10(range)));\n    const fraction = range / niceRange;\n    const niceFraction = fraction <= 1 ? 1 : fraction <= 2 ? 2 : fraction <= 5 ? 5 : 10;\n    return niceFraction * niceRange;\n}\n/**\n * Returns an array of factors sorted from 1 to sqrt(value)\n * @private\n */ function _factorize(value) {\n    const result = [];\n    const sqrt = Math.sqrt(value);\n    let i;\n    for(i = 1; i < sqrt; i++){\n        if (value % i === 0) {\n            result.push(i);\n            result.push(value / i);\n        }\n    }\n    if (sqrt === (sqrt | 0)) {\n        result.push(sqrt);\n    }\n    result.sort((a, b)=>a - b).pop();\n    return result;\n}\nfunction isNumber(n) {\n    return !isNaN(parseFloat(n)) && isFinite(n);\n}\nfunction almostWhole(x, epsilon) {\n    const rounded = Math.round(x);\n    return rounded - epsilon <= x && rounded + epsilon >= x;\n}\n/**\n * @private\n */ function _setMinAndMaxByKey(array, target, property) {\n    let i, ilen, value;\n    for(i = 0, ilen = array.length; i < ilen; i++){\n        value = array[i][property];\n        if (!isNaN(value)) {\n            target.min = Math.min(target.min, value);\n            target.max = Math.max(target.max, value);\n        }\n    }\n}\nfunction toRadians(degrees) {\n    return degrees * (PI / 180);\n}\nfunction toDegrees(radians) {\n    return radians * (180 / PI);\n}\n/**\n * Returns the number of decimal places\n * i.e. the number of digits after the decimal point, of the value of this Number.\n * @param x - A number.\n * @returns The number of decimal places.\n * @private\n */ function _decimalPlaces(x) {\n    if (!isNumberFinite(x)) {\n        return;\n    }\n    let e = 1;\n    let p = 0;\n    while(Math.round(x * e) / e !== x){\n        e *= 10;\n        p++;\n    }\n    return p;\n}\n// Gets the angle from vertical upright to the point about a centre.\nfunction getAngleFromPoint(centrePoint, anglePoint) {\n    const distanceFromXCenter = anglePoint.x - centrePoint.x;\n    const distanceFromYCenter = anglePoint.y - centrePoint.y;\n    const radialDistanceFromCenter = Math.sqrt(distanceFromXCenter * distanceFromXCenter + distanceFromYCenter * distanceFromYCenter);\n    let angle = Math.atan2(distanceFromYCenter, distanceFromXCenter);\n    if (angle < -0.5 * PI) {\n        angle += TAU; // make sure the returned angle is in the range of (-PI/2, 3PI/2]\n    }\n    return {\n        angle,\n        distance: radialDistanceFromCenter\n    };\n}\nfunction distanceBetweenPoints(pt1, pt2) {\n    return Math.sqrt(Math.pow(pt2.x - pt1.x, 2) + Math.pow(pt2.y - pt1.y, 2));\n}\n/**\n * Shortest distance between angles, in either direction.\n * @private\n */ function _angleDiff(a, b) {\n    return (a - b + PITAU) % TAU - PI;\n}\n/**\n * Normalize angle to be between 0 and 2*PI\n * @private\n */ function _normalizeAngle(a) {\n    return (a % TAU + TAU) % TAU;\n}\n/**\n * @private\n */ function _angleBetween(angle, start, end, sameAngleIsFullCircle) {\n    const a = _normalizeAngle(angle);\n    const s = _normalizeAngle(start);\n    const e = _normalizeAngle(end);\n    const angleToStart = _normalizeAngle(s - a);\n    const angleToEnd = _normalizeAngle(e - a);\n    const startToAngle = _normalizeAngle(a - s);\n    const endToAngle = _normalizeAngle(a - e);\n    return a === s || a === e || sameAngleIsFullCircle && s === e || angleToStart > angleToEnd && startToAngle < endToAngle;\n}\n/**\n * Limit `value` between `min` and `max`\n * @param value\n * @param min\n * @param max\n * @private\n */ function _limitValue(value, min, max) {\n    return Math.max(min, Math.min(max, value));\n}\n/**\n * @param {number} value\n * @private\n */ function _int16Range(value) {\n    return _limitValue(value, -32768, 32767);\n}\n/**\n * @param value\n * @param start\n * @param end\n * @param [epsilon]\n * @private\n */ function _isBetween(value, start, end, epsilon = 1e-6) {\n    return value >= Math.min(start, end) - epsilon && value <= Math.max(start, end) + epsilon;\n}\n\nfunction _lookup(table, value, cmp) {\n    cmp = cmp || ((index)=>table[index] < value);\n    let hi = table.length - 1;\n    let lo = 0;\n    let mid;\n    while(hi - lo > 1){\n        mid = lo + hi >> 1;\n        if (cmp(mid)) {\n            lo = mid;\n        } else {\n            hi = mid;\n        }\n    }\n    return {\n        lo,\n        hi\n    };\n}\n/**\n * Binary search\n * @param table - the table search. must be sorted!\n * @param key - property name for the value in each entry\n * @param value - value to find\n * @param last - lookup last index\n * @private\n */ const _lookupByKey = (table, key, value, last)=>_lookup(table, value, last ? (index)=>{\n        const ti = table[index][key];\n        return ti < value || ti === value && table[index + 1][key] === value;\n    } : (index)=>table[index][key] < value);\n/**\n * Reverse binary search\n * @param table - the table search. must be sorted!\n * @param key - property name for the value in each entry\n * @param value - value to find\n * @private\n */ const _rlookupByKey = (table, key, value)=>_lookup(table, value, (index)=>table[index][key] >= value);\n/**\n * Return subset of `values` between `min` and `max` inclusive.\n * Values are assumed to be in sorted order.\n * @param values - sorted array of values\n * @param min - min value\n * @param max - max value\n */ function _filterBetween(values, min, max) {\n    let start = 0;\n    let end = values.length;\n    while(start < end && values[start] < min){\n        start++;\n    }\n    while(end > start && values[end - 1] > max){\n        end--;\n    }\n    return start > 0 || end < values.length ? values.slice(start, end) : values;\n}\nconst arrayEvents = [\n    'push',\n    'pop',\n    'shift',\n    'splice',\n    'unshift'\n];\nfunction listenArrayEvents(array, listener) {\n    if (array._chartjs) {\n        array._chartjs.listeners.push(listener);\n        return;\n    }\n    Object.defineProperty(array, '_chartjs', {\n        configurable: true,\n        enumerable: false,\n        value: {\n            listeners: [\n                listener\n            ]\n        }\n    });\n    arrayEvents.forEach((key)=>{\n        const method = '_onData' + _capitalize(key);\n        const base = array[key];\n        Object.defineProperty(array, key, {\n            configurable: true,\n            enumerable: false,\n            value (...args) {\n                const res = base.apply(this, args);\n                array._chartjs.listeners.forEach((object)=>{\n                    if (typeof object[method] === 'function') {\n                        object[method](...args);\n                    }\n                });\n                return res;\n            }\n        });\n    });\n}\nfunction unlistenArrayEvents(array, listener) {\n    const stub = array._chartjs;\n    if (!stub) {\n        return;\n    }\n    const listeners = stub.listeners;\n    const index = listeners.indexOf(listener);\n    if (index !== -1) {\n        listeners.splice(index, 1);\n    }\n    if (listeners.length > 0) {\n        return;\n    }\n    arrayEvents.forEach((key)=>{\n        delete array[key];\n    });\n    delete array._chartjs;\n}\n/**\n * @param items\n */ function _arrayUnique(items) {\n    const set = new Set(items);\n    if (set.size === items.length) {\n        return items;\n    }\n    return Array.from(set);\n}\n\nfunction fontString(pixelSize, fontStyle, fontFamily) {\n    return fontStyle + ' ' + pixelSize + 'px ' + fontFamily;\n}\n/**\n* Request animation polyfill\n*/ const requestAnimFrame = function() {\n    if (typeof window === 'undefined') {\n        return function(callback) {\n            return callback();\n        };\n    }\n    return window.requestAnimationFrame;\n}();\n/**\n * Throttles calling `fn` once per animation frame\n * Latest arguments are used on the actual call\n */ function throttled(fn, thisArg) {\n    let argsToUse = [];\n    let ticking = false;\n    return function(...args) {\n        // Save the args for use later\n        argsToUse = args;\n        if (!ticking) {\n            ticking = true;\n            requestAnimFrame.call(window, ()=>{\n                ticking = false;\n                fn.apply(thisArg, argsToUse);\n            });\n        }\n    };\n}\n/**\n * Debounces calling `fn` for `delay` ms\n */ function debounce(fn, delay) {\n    let timeout;\n    return function(...args) {\n        if (delay) {\n            clearTimeout(timeout);\n            timeout = setTimeout(fn, delay, args);\n        } else {\n            fn.apply(this, args);\n        }\n        return delay;\n    };\n}\n/**\n * Converts 'start' to 'left', 'end' to 'right' and others to 'center'\n * @private\n */ const _toLeftRightCenter = (align)=>align === 'start' ? 'left' : align === 'end' ? 'right' : 'center';\n/**\n * Returns `start`, `end` or `(start + end) / 2` depending on `align`. Defaults to `center`\n * @private\n */ const _alignStartEnd = (align, start, end)=>align === 'start' ? start : align === 'end' ? end : (start + end) / 2;\n/**\n * Returns `left`, `right` or `(left + right) / 2` depending on `align`. Defaults to `left`\n * @private\n */ const _textX = (align, left, right, rtl)=>{\n    const check = rtl ? 'left' : 'right';\n    return align === check ? right : align === 'center' ? (left + right) / 2 : left;\n};\n/**\n * Return start and count of visible points.\n * @private\n */ function _getStartAndCountOfVisiblePoints(meta, points, animationsDisabled) {\n    const pointCount = points.length;\n    let start = 0;\n    let count = pointCount;\n    if (meta._sorted) {\n        const { iScale , _parsed  } = meta;\n        const axis = iScale.axis;\n        const { min , max , minDefined , maxDefined  } = iScale.getUserBounds();\n        if (minDefined) {\n            start = _limitValue(Math.min(// @ts-expect-error Need to type _parsed\n            _lookupByKey(_parsed, axis, min).lo, // @ts-expect-error Need to fix types on _lookupByKey\n            animationsDisabled ? pointCount : _lookupByKey(points, axis, iScale.getPixelForValue(min)).lo), 0, pointCount - 1);\n        }\n        if (maxDefined) {\n            count = _limitValue(Math.max(// @ts-expect-error Need to type _parsed\n            _lookupByKey(_parsed, iScale.axis, max, true).hi + 1, // @ts-expect-error Need to fix types on _lookupByKey\n            animationsDisabled ? 0 : _lookupByKey(points, axis, iScale.getPixelForValue(max), true).hi + 1), start, pointCount) - start;\n        } else {\n            count = pointCount - start;\n        }\n    }\n    return {\n        start,\n        count\n    };\n}\n/**\n * Checks if the scale ranges have changed.\n * @param {object} meta - dataset meta.\n * @returns {boolean}\n * @private\n */ function _scaleRangesChanged(meta) {\n    const { xScale , yScale , _scaleRanges  } = meta;\n    const newRanges = {\n        xmin: xScale.min,\n        xmax: xScale.max,\n        ymin: yScale.min,\n        ymax: yScale.max\n    };\n    if (!_scaleRanges) {\n        meta._scaleRanges = newRanges;\n        return true;\n    }\n    const changed = _scaleRanges.xmin !== xScale.min || _scaleRanges.xmax !== xScale.max || _scaleRanges.ymin !== yScale.min || _scaleRanges.ymax !== yScale.max;\n    Object.assign(_scaleRanges, newRanges);\n    return changed;\n}\n\nconst atEdge = (t)=>t === 0 || t === 1;\nconst elasticIn = (t, s, p)=>-(Math.pow(2, 10 * (t -= 1)) * Math.sin((t - s) * TAU / p));\nconst elasticOut = (t, s, p)=>Math.pow(2, -10 * t) * Math.sin((t - s) * TAU / p) + 1;\n/**\n * Easing functions adapted from Robert Penner's easing equations.\n * @namespace Chart.helpers.easing.effects\n * @see http://www.robertpenner.com/easing/\n */ const effects = {\n    linear: (t)=>t,\n    easeInQuad: (t)=>t * t,\n    easeOutQuad: (t)=>-t * (t - 2),\n    easeInOutQuad: (t)=>(t /= 0.5) < 1 ? 0.5 * t * t : -0.5 * (--t * (t - 2) - 1),\n    easeInCubic: (t)=>t * t * t,\n    easeOutCubic: (t)=>(t -= 1) * t * t + 1,\n    easeInOutCubic: (t)=>(t /= 0.5) < 1 ? 0.5 * t * t * t : 0.5 * ((t -= 2) * t * t + 2),\n    easeInQuart: (t)=>t * t * t * t,\n    easeOutQuart: (t)=>-((t -= 1) * t * t * t - 1),\n    easeInOutQuart: (t)=>(t /= 0.5) < 1 ? 0.5 * t * t * t * t : -0.5 * ((t -= 2) * t * t * t - 2),\n    easeInQuint: (t)=>t * t * t * t * t,\n    easeOutQuint: (t)=>(t -= 1) * t * t * t * t + 1,\n    easeInOutQuint: (t)=>(t /= 0.5) < 1 ? 0.5 * t * t * t * t * t : 0.5 * ((t -= 2) * t * t * t * t + 2),\n    easeInSine: (t)=>-Math.cos(t * HALF_PI) + 1,\n    easeOutSine: (t)=>Math.sin(t * HALF_PI),\n    easeInOutSine: (t)=>-0.5 * (Math.cos(PI * t) - 1),\n    easeInExpo: (t)=>t === 0 ? 0 : Math.pow(2, 10 * (t - 1)),\n    easeOutExpo: (t)=>t === 1 ? 1 : -Math.pow(2, -10 * t) + 1,\n    easeInOutExpo: (t)=>atEdge(t) ? t : t < 0.5 ? 0.5 * Math.pow(2, 10 * (t * 2 - 1)) : 0.5 * (-Math.pow(2, -10 * (t * 2 - 1)) + 2),\n    easeInCirc: (t)=>t >= 1 ? t : -(Math.sqrt(1 - t * t) - 1),\n    easeOutCirc: (t)=>Math.sqrt(1 - (t -= 1) * t),\n    easeInOutCirc: (t)=>(t /= 0.5) < 1 ? -0.5 * (Math.sqrt(1 - t * t) - 1) : 0.5 * (Math.sqrt(1 - (t -= 2) * t) + 1),\n    easeInElastic: (t)=>atEdge(t) ? t : elasticIn(t, 0.075, 0.3),\n    easeOutElastic: (t)=>atEdge(t) ? t : elasticOut(t, 0.075, 0.3),\n    easeInOutElastic (t) {\n        const s = 0.1125;\n        const p = 0.45;\n        return atEdge(t) ? t : t < 0.5 ? 0.5 * elasticIn(t * 2, s, p) : 0.5 + 0.5 * elasticOut(t * 2 - 1, s, p);\n    },\n    easeInBack (t) {\n        const s = 1.70158;\n        return t * t * ((s + 1) * t - s);\n    },\n    easeOutBack (t) {\n        const s = 1.70158;\n        return (t -= 1) * t * ((s + 1) * t + s) + 1;\n    },\n    easeInOutBack (t) {\n        let s = 1.70158;\n        if ((t /= 0.5) < 1) {\n            return 0.5 * (t * t * (((s *= 1.525) + 1) * t - s));\n        }\n        return 0.5 * ((t -= 2) * t * (((s *= 1.525) + 1) * t + s) + 2);\n    },\n    easeInBounce: (t)=>1 - effects.easeOutBounce(1 - t),\n    easeOutBounce (t) {\n        const m = 7.5625;\n        const d = 2.75;\n        if (t < 1 / d) {\n            return m * t * t;\n        }\n        if (t < 2 / d) {\n            return m * (t -= 1.5 / d) * t + 0.75;\n        }\n        if (t < 2.5 / d) {\n            return m * (t -= 2.25 / d) * t + 0.9375;\n        }\n        return m * (t -= 2.625 / d) * t + 0.984375;\n    },\n    easeInOutBounce: (t)=>t < 0.5 ? effects.easeInBounce(t * 2) * 0.5 : effects.easeOutBounce(t * 2 - 1) * 0.5 + 0.5\n};\n\nfunction isPatternOrGradient(value) {\n    if (value && typeof value === 'object') {\n        const type = value.toString();\n        return type === '[object CanvasPattern]' || type === '[object CanvasGradient]';\n    }\n    return false;\n}\nfunction color(value) {\n    return isPatternOrGradient(value) ? value : new Color(value);\n}\nfunction getHoverColor(value) {\n    return isPatternOrGradient(value) ? value : new Color(value).saturate(0.5).darken(0.1).hexString();\n}\n\nconst numbers = [\n    'x',\n    'y',\n    'borderWidth',\n    'radius',\n    'tension'\n];\nconst colors = [\n    'color',\n    'borderColor',\n    'backgroundColor'\n];\nfunction applyAnimationsDefaults(defaults) {\n    defaults.set('animation', {\n        delay: undefined,\n        duration: 1000,\n        easing: 'easeOutQuart',\n        fn: undefined,\n        from: undefined,\n        loop: undefined,\n        to: undefined,\n        type: undefined\n    });\n    defaults.describe('animation', {\n        _fallback: false,\n        _indexable: false,\n        _scriptable: (name)=>name !== 'onProgress' && name !== 'onComplete' && name !== 'fn'\n    });\n    defaults.set('animations', {\n        colors: {\n            type: 'color',\n            properties: colors\n        },\n        numbers: {\n            type: 'number',\n            properties: numbers\n        }\n    });\n    defaults.describe('animations', {\n        _fallback: 'animation'\n    });\n    defaults.set('transitions', {\n        active: {\n            animation: {\n                duration: 400\n            }\n        },\n        resize: {\n            animation: {\n                duration: 0\n            }\n        },\n        show: {\n            animations: {\n                colors: {\n                    from: 'transparent'\n                },\n                visible: {\n                    type: 'boolean',\n                    duration: 0\n                }\n            }\n        },\n        hide: {\n            animations: {\n                colors: {\n                    to: 'transparent'\n                },\n                visible: {\n                    type: 'boolean',\n                    easing: 'linear',\n                    fn: (v)=>v | 0\n                }\n            }\n        }\n    });\n}\n\nfunction applyLayoutsDefaults(defaults) {\n    defaults.set('layout', {\n        autoPadding: true,\n        padding: {\n            top: 0,\n            right: 0,\n            bottom: 0,\n            left: 0\n        }\n    });\n}\n\nconst intlCache = new Map();\nfunction getNumberFormat(locale, options) {\n    options = options || {};\n    const cacheKey = locale + JSON.stringify(options);\n    let formatter = intlCache.get(cacheKey);\n    if (!formatter) {\n        formatter = new Intl.NumberFormat(locale, options);\n        intlCache.set(cacheKey, formatter);\n    }\n    return formatter;\n}\nfunction formatNumber(num, locale, options) {\n    return getNumberFormat(locale, options).format(num);\n}\n\nconst formatters = {\n values (value) {\n        return isArray(value) ?  value : '' + value;\n    },\n numeric (tickValue, index, ticks) {\n        if (tickValue === 0) {\n            return '0';\n        }\n        const locale = this.chart.options.locale;\n        let notation;\n        let delta = tickValue;\n        if (ticks.length > 1) {\n            const maxTick = Math.max(Math.abs(ticks[0].value), Math.abs(ticks[ticks.length - 1].value));\n            if (maxTick < 1e-4 || maxTick > 1e+15) {\n                notation = 'scientific';\n            }\n            delta = calculateDelta(tickValue, ticks);\n        }\n        const logDelta = log10(Math.abs(delta));\n        const numDecimal = isNaN(logDelta) ? 1 : Math.max(Math.min(-1 * Math.floor(logDelta), 20), 0);\n        const options = {\n            notation,\n            minimumFractionDigits: numDecimal,\n            maximumFractionDigits: numDecimal\n        };\n        Object.assign(options, this.options.ticks.format);\n        return formatNumber(tickValue, locale, options);\n    },\n logarithmic (tickValue, index, ticks) {\n        if (tickValue === 0) {\n            return '0';\n        }\n        const remain = ticks[index].significand || tickValue / Math.pow(10, Math.floor(log10(tickValue)));\n        if ([\n            1,\n            2,\n            3,\n            5,\n            10,\n            15\n        ].includes(remain) || index > 0.8 * ticks.length) {\n            return formatters.numeric.call(this, tickValue, index, ticks);\n        }\n        return '';\n    }\n};\nfunction calculateDelta(tickValue, ticks) {\n    let delta = ticks.length > 3 ? ticks[2].value - ticks[1].value : ticks[1].value - ticks[0].value;\n    if (Math.abs(delta) >= 1 && tickValue !== Math.floor(tickValue)) {\n        delta = tickValue - Math.floor(tickValue);\n    }\n    return delta;\n}\n var Ticks = {\n    formatters\n};\n\nfunction applyScaleDefaults(defaults) {\n    defaults.set('scale', {\n        display: true,\n        offset: false,\n        reverse: false,\n        beginAtZero: false,\n bounds: 'ticks',\n        clip: true,\n grace: 0,\n        grid: {\n            display: true,\n            lineWidth: 1,\n            drawOnChartArea: true,\n            drawTicks: true,\n            tickLength: 8,\n            tickWidth: (_ctx, options)=>options.lineWidth,\n            tickColor: (_ctx, options)=>options.color,\n            offset: false\n        },\n        border: {\n            display: true,\n            dash: [],\n            dashOffset: 0.0,\n            width: 1\n        },\n        title: {\n            display: false,\n            text: '',\n            padding: {\n                top: 4,\n                bottom: 4\n            }\n        },\n        ticks: {\n            minRotation: 0,\n            maxRotation: 50,\n            mirror: false,\n            textStrokeWidth: 0,\n            textStrokeColor: '',\n            padding: 3,\n            display: true,\n            autoSkip: true,\n            autoSkipPadding: 3,\n            labelOffset: 0,\n            callback: Ticks.formatters.values,\n            minor: {},\n            major: {},\n            align: 'center',\n            crossAlign: 'near',\n            showLabelBackdrop: false,\n            backdropColor: 'rgba(255, 255, 255, 0.75)',\n            backdropPadding: 2\n        }\n    });\n    defaults.route('scale.ticks', 'color', '', 'color');\n    defaults.route('scale.grid', 'color', '', 'borderColor');\n    defaults.route('scale.border', 'color', '', 'borderColor');\n    defaults.route('scale.title', 'color', '', 'color');\n    defaults.describe('scale', {\n        _fallback: false,\n        _scriptable: (name)=>!name.startsWith('before') && !name.startsWith('after') && name !== 'callback' && name !== 'parser',\n        _indexable: (name)=>name !== 'borderDash' && name !== 'tickBorderDash' && name !== 'dash'\n    });\n    defaults.describe('scales', {\n        _fallback: 'scale'\n    });\n    defaults.describe('scale.ticks', {\n        _scriptable: (name)=>name !== 'backdropPadding' && name !== 'callback',\n        _indexable: (name)=>name !== 'backdropPadding'\n    });\n}\n\nconst overrides = Object.create(null);\nconst descriptors = Object.create(null);\n function getScope$1(node, key) {\n    if (!key) {\n        return node;\n    }\n    const keys = key.split('.');\n    for(let i = 0, n = keys.length; i < n; ++i){\n        const k = keys[i];\n        node = node[k] || (node[k] = Object.create(null));\n    }\n    return node;\n}\nfunction set(root, scope, values) {\n    if (typeof scope === 'string') {\n        return merge(getScope$1(root, scope), values);\n    }\n    return merge(getScope$1(root, ''), scope);\n}\n class Defaults {\n    constructor(_descriptors, _appliers){\n        this.animation = undefined;\n        this.backgroundColor = 'rgba(0,0,0,0.1)';\n        this.borderColor = 'rgba(0,0,0,0.1)';\n        this.color = '#666';\n        this.datasets = {};\n        this.devicePixelRatio = (context)=>context.chart.platform.getDevicePixelRatio();\n        this.elements = {};\n        this.events = [\n            'mousemove',\n            'mouseout',\n            'click',\n            'touchstart',\n            'touchmove'\n        ];\n        this.font = {\n            family: \"'Helvetica Neue', 'Helvetica', 'Arial', sans-serif\",\n            size: 12,\n            style: 'normal',\n            lineHeight: 1.2,\n            weight: null\n        };\n        this.hover = {};\n        this.hoverBackgroundColor = (ctx, options)=>getHoverColor(options.backgroundColor);\n        this.hoverBorderColor = (ctx, options)=>getHoverColor(options.borderColor);\n        this.hoverColor = (ctx, options)=>getHoverColor(options.color);\n        this.indexAxis = 'x';\n        this.interaction = {\n            mode: 'nearest',\n            intersect: true,\n            includeInvisible: false\n        };\n        this.maintainAspectRatio = true;\n        this.onHover = null;\n        this.onClick = null;\n        this.parsing = true;\n        this.plugins = {};\n        this.responsive = true;\n        this.scale = undefined;\n        this.scales = {};\n        this.showLine = true;\n        this.drawActiveElementsOnTop = true;\n        this.describe(_descriptors);\n        this.apply(_appliers);\n    }\n set(scope, values) {\n        return set(this, scope, values);\n    }\n get(scope) {\n        return getScope$1(this, scope);\n    }\n describe(scope, values) {\n        return set(descriptors, scope, values);\n    }\n    override(scope, values) {\n        return set(overrides, scope, values);\n    }\n route(scope, name, targetScope, targetName) {\n        const scopeObject = getScope$1(this, scope);\n        const targetScopeObject = getScope$1(this, targetScope);\n        const privateName = '_' + name;\n        Object.defineProperties(scopeObject, {\n            [privateName]: {\n                value: scopeObject[name],\n                writable: true\n            },\n            [name]: {\n                enumerable: true,\n                get () {\n                    const local = this[privateName];\n                    const target = targetScopeObject[targetName];\n                    if (isObject(local)) {\n                        return Object.assign({}, target, local);\n                    }\n                    return valueOrDefault(local, target);\n                },\n                set (value) {\n                    this[privateName] = value;\n                }\n            }\n        });\n    }\n    apply(appliers) {\n        appliers.forEach((apply)=>apply(this));\n    }\n}\nvar defaults = /* #__PURE__ */ new Defaults({\n    _scriptable: (name)=>!name.startsWith('on'),\n    _indexable: (name)=>name !== 'events',\n    hover: {\n        _fallback: 'interaction'\n    },\n    interaction: {\n        _scriptable: false,\n        _indexable: false\n    }\n}, [\n    applyAnimationsDefaults,\n    applyLayoutsDefaults,\n    applyScaleDefaults\n]);\n\n/**\n * Converts the given font object into a CSS font string.\n * @param font - A font object.\n * @return The CSS font string. See https://developer.mozilla.org/en-US/docs/Web/CSS/font\n * @private\n */ function toFontString(font) {\n    if (!font || isNullOrUndef(font.size) || isNullOrUndef(font.family)) {\n        return null;\n    }\n    return (font.style ? font.style + ' ' : '') + (font.weight ? font.weight + ' ' : '') + font.size + 'px ' + font.family;\n}\n/**\n * @private\n */ function _measureText(ctx, data, gc, longest, string) {\n    let textWidth = data[string];\n    if (!textWidth) {\n        textWidth = data[string] = ctx.measureText(string).width;\n        gc.push(string);\n    }\n    if (textWidth > longest) {\n        longest = textWidth;\n    }\n    return longest;\n}\n/**\n * @private\n */ // eslint-disable-next-line complexity\nfunction _longestText(ctx, font, arrayOfThings, cache) {\n    cache = cache || {};\n    let data = cache.data = cache.data || {};\n    let gc = cache.garbageCollect = cache.garbageCollect || [];\n    if (cache.font !== font) {\n        data = cache.data = {};\n        gc = cache.garbageCollect = [];\n        cache.font = font;\n    }\n    ctx.save();\n    ctx.font = font;\n    let longest = 0;\n    const ilen = arrayOfThings.length;\n    let i, j, jlen, thing, nestedThing;\n    for(i = 0; i < ilen; i++){\n        thing = arrayOfThings[i];\n        // Undefined strings and arrays should not be measured\n        if (thing !== undefined && thing !== null && !isArray(thing)) {\n            longest = _measureText(ctx, data, gc, longest, thing);\n        } else if (isArray(thing)) {\n            // if it is an array lets measure each element\n            // to do maybe simplify this function a bit so we can do this more recursively?\n            for(j = 0, jlen = thing.length; j < jlen; j++){\n                nestedThing = thing[j];\n                // Undefined strings and arrays should not be measured\n                if (nestedThing !== undefined && nestedThing !== null && !isArray(nestedThing)) {\n                    longest = _measureText(ctx, data, gc, longest, nestedThing);\n                }\n            }\n        }\n    }\n    ctx.restore();\n    const gcLen = gc.length / 2;\n    if (gcLen > arrayOfThings.length) {\n        for(i = 0; i < gcLen; i++){\n            delete data[gc[i]];\n        }\n        gc.splice(0, gcLen);\n    }\n    return longest;\n}\n/**\n * Returns the aligned pixel value to avoid anti-aliasing blur\n * @param chart - The chart instance.\n * @param pixel - A pixel value.\n * @param width - The width of the element.\n * @returns The aligned pixel value.\n * @private\n */ function _alignPixel(chart, pixel, width) {\n    const devicePixelRatio = chart.currentDevicePixelRatio;\n    const halfWidth = width !== 0 ? Math.max(width / 2, 0.5) : 0;\n    return Math.round((pixel - halfWidth) * devicePixelRatio) / devicePixelRatio + halfWidth;\n}\n/**\n * Clears the entire canvas.\n */ function clearCanvas(canvas, ctx) {\n    ctx = ctx || canvas.getContext('2d');\n    ctx.save();\n    // canvas.width and canvas.height do not consider the canvas transform,\n    // while clearRect does\n    ctx.resetTransform();\n    ctx.clearRect(0, 0, canvas.width, canvas.height);\n    ctx.restore();\n}\nfunction drawPoint(ctx, options, x, y) {\n    // eslint-disable-next-line @typescript-eslint/no-use-before-define\n    drawPointLegend(ctx, options, x, y, null);\n}\n// eslint-disable-next-line complexity\nfunction drawPointLegend(ctx, options, x, y, w) {\n    let type, xOffset, yOffset, size, cornerRadius, width, xOffsetW, yOffsetW;\n    const style = options.pointStyle;\n    const rotation = options.rotation;\n    const radius = options.radius;\n    let rad = (rotation || 0) * RAD_PER_DEG;\n    if (style && typeof style === 'object') {\n        type = style.toString();\n        if (type === '[object HTMLImageElement]' || type === '[object HTMLCanvasElement]') {\n            ctx.save();\n            ctx.translate(x, y);\n            ctx.rotate(rad);\n            ctx.drawImage(style, -style.width / 2, -style.height / 2, style.width, style.height);\n            ctx.restore();\n            return;\n        }\n    }\n    if (isNaN(radius) || radius <= 0) {\n        return;\n    }\n    ctx.beginPath();\n    switch(style){\n        // Default includes circle\n        default:\n            if (w) {\n                ctx.ellipse(x, y, w / 2, radius, 0, 0, TAU);\n            } else {\n                ctx.arc(x, y, radius, 0, TAU);\n            }\n            ctx.closePath();\n            break;\n        case 'triangle':\n            width = w ? w / 2 : radius;\n            ctx.moveTo(x + Math.sin(rad) * width, y - Math.cos(rad) * radius);\n            rad += TWO_THIRDS_PI;\n            ctx.lineTo(x + Math.sin(rad) * width, y - Math.cos(rad) * radius);\n            rad += TWO_THIRDS_PI;\n            ctx.lineTo(x + Math.sin(rad) * width, y - Math.cos(rad) * radius);\n            ctx.closePath();\n            break;\n        case 'rectRounded':\n            // NOTE: the rounded rect implementation changed to use `arc` instead of\n            // `quadraticCurveTo` since it generates better results when rect is\n            // almost a circle. 0.516 (instead of 0.5) produces results with visually\n            // closer proportion to the previous impl and it is inscribed in the\n            // circle with `radius`. For more details, see the following PRs:\n            // https://github.com/chartjs/Chart.js/issues/5597\n            // https://github.com/chartjs/Chart.js/issues/5858\n            cornerRadius = radius * 0.516;\n            size = radius - cornerRadius;\n            xOffset = Math.cos(rad + QUARTER_PI) * size;\n            xOffsetW = Math.cos(rad + QUARTER_PI) * (w ? w / 2 - cornerRadius : size);\n            yOffset = Math.sin(rad + QUARTER_PI) * size;\n            yOffsetW = Math.sin(rad + QUARTER_PI) * (w ? w / 2 - cornerRadius : size);\n            ctx.arc(x - xOffsetW, y - yOffset, cornerRadius, rad - PI, rad - HALF_PI);\n            ctx.arc(x + yOffsetW, y - xOffset, cornerRadius, rad - HALF_PI, rad);\n            ctx.arc(x + xOffsetW, y + yOffset, cornerRadius, rad, rad + HALF_PI);\n            ctx.arc(x - yOffsetW, y + xOffset, cornerRadius, rad + HALF_PI, rad + PI);\n            ctx.closePath();\n            break;\n        case 'rect':\n            if (!rotation) {\n                size = Math.SQRT1_2 * radius;\n                width = w ? w / 2 : size;\n                ctx.rect(x - width, y - size, 2 * width, 2 * size);\n                break;\n            }\n            rad += QUARTER_PI;\n        /* falls through */ case 'rectRot':\n            xOffsetW = Math.cos(rad) * (w ? w / 2 : radius);\n            xOffset = Math.cos(rad) * radius;\n            yOffset = Math.sin(rad) * radius;\n            yOffsetW = Math.sin(rad) * (w ? w / 2 : radius);\n            ctx.moveTo(x - xOffsetW, y - yOffset);\n            ctx.lineTo(x + yOffsetW, y - xOffset);\n            ctx.lineTo(x + xOffsetW, y + yOffset);\n            ctx.lineTo(x - yOffsetW, y + xOffset);\n            ctx.closePath();\n            break;\n        case 'crossRot':\n            rad += QUARTER_PI;\n        /* falls through */ case 'cross':\n            xOffsetW = Math.cos(rad) * (w ? w / 2 : radius);\n            xOffset = Math.cos(rad) * radius;\n            yOffset = Math.sin(rad) * radius;\n            yOffsetW = Math.sin(rad) * (w ? w / 2 : radius);\n            ctx.moveTo(x - xOffsetW, y - yOffset);\n            ctx.lineTo(x + xOffsetW, y + yOffset);\n            ctx.moveTo(x + yOffsetW, y - xOffset);\n            ctx.lineTo(x - yOffsetW, y + xOffset);\n            break;\n        case 'star':\n            xOffsetW = Math.cos(rad) * (w ? w / 2 : radius);\n            xOffset = Math.cos(rad) * radius;\n            yOffset = Math.sin(rad) * radius;\n            yOffsetW = Math.sin(rad) * (w ? w / 2 : radius);\n            ctx.moveTo(x - xOffsetW, y - yOffset);\n            ctx.lineTo(x + xOffsetW, y + yOffset);\n            ctx.moveTo(x + yOffsetW, y - xOffset);\n            ctx.lineTo(x - yOffsetW, y + xOffset);\n            rad += QUARTER_PI;\n            xOffsetW = Math.cos(rad) * (w ? w / 2 : radius);\n            xOffset = Math.cos(rad) * radius;\n            yOffset = Math.sin(rad) * radius;\n            yOffsetW = Math.sin(rad) * (w ? w / 2 : radius);\n            ctx.moveTo(x - xOffsetW, y - yOffset);\n            ctx.lineTo(x + xOffsetW, y + yOffset);\n            ctx.moveTo(x + yOffsetW, y - xOffset);\n            ctx.lineTo(x - yOffsetW, y + xOffset);\n            break;\n        case 'line':\n            xOffset = w ? w / 2 : Math.cos(rad) * radius;\n            yOffset = Math.sin(rad) * radius;\n            ctx.moveTo(x - xOffset, y - yOffset);\n            ctx.lineTo(x + xOffset, y + yOffset);\n            break;\n        case 'dash':\n            ctx.moveTo(x, y);\n            ctx.lineTo(x + Math.cos(rad) * (w ? w / 2 : radius), y + Math.sin(rad) * radius);\n            break;\n        case false:\n            ctx.closePath();\n            break;\n    }\n    ctx.fill();\n    if (options.borderWidth > 0) {\n        ctx.stroke();\n    }\n}\n/**\n * Returns true if the point is inside the rectangle\n * @param point - The point to test\n * @param area - The rectangle\n * @param margin - allowed margin\n * @private\n */ function _isPointInArea(point, area, margin) {\n    margin = margin || 0.5; // margin - default is to match rounded decimals\n    return !area || point && point.x > area.left - margin && point.x < area.right + margin && point.y > area.top - margin && point.y < area.bottom + margin;\n}\nfunction clipArea(ctx, area) {\n    ctx.save();\n    ctx.beginPath();\n    ctx.rect(area.left, area.top, area.right - area.left, area.bottom - area.top);\n    ctx.clip();\n}\nfunction unclipArea(ctx) {\n    ctx.restore();\n}\n/**\n * @private\n */ function _steppedLineTo(ctx, previous, target, flip, mode) {\n    if (!previous) {\n        return ctx.lineTo(target.x, target.y);\n    }\n    if (mode === 'middle') {\n        const midpoint = (previous.x + target.x) / 2.0;\n        ctx.lineTo(midpoint, previous.y);\n        ctx.lineTo(midpoint, target.y);\n    } else if (mode === 'after' !== !!flip) {\n        ctx.lineTo(previous.x, target.y);\n    } else {\n        ctx.lineTo(target.x, previous.y);\n    }\n    ctx.lineTo(target.x, target.y);\n}\n/**\n * @private\n */ function _bezierCurveTo(ctx, previous, target, flip) {\n    if (!previous) {\n        return ctx.lineTo(target.x, target.y);\n    }\n    ctx.bezierCurveTo(flip ? previous.cp1x : previous.cp2x, flip ? previous.cp1y : previous.cp2y, flip ? target.cp2x : target.cp1x, flip ? target.cp2y : target.cp1y, target.x, target.y);\n}\nfunction setRenderOpts(ctx, opts) {\n    if (opts.translation) {\n        ctx.translate(opts.translation[0], opts.translation[1]);\n    }\n    if (!isNullOrUndef(opts.rotation)) {\n        ctx.rotate(opts.rotation);\n    }\n    if (opts.color) {\n        ctx.fillStyle = opts.color;\n    }\n    if (opts.textAlign) {\n        ctx.textAlign = opts.textAlign;\n    }\n    if (opts.textBaseline) {\n        ctx.textBaseline = opts.textBaseline;\n    }\n}\nfunction decorateText(ctx, x, y, line, opts) {\n    if (opts.strikethrough || opts.underline) {\n        /**\n     * Now that IE11 support has been dropped, we can use more\n     * of the TextMetrics object. The actual bounding boxes\n     * are unflagged in Chrome, Firefox, Edge, and Safari so they\n     * can be safely used.\n     * See https://developer.mozilla.org/en-US/docs/Web/API/TextMetrics#Browser_compatibility\n     */ const metrics = ctx.measureText(line);\n        const left = x - metrics.actualBoundingBoxLeft;\n        const right = x + metrics.actualBoundingBoxRight;\n        const top = y - metrics.actualBoundingBoxAscent;\n        const bottom = y + metrics.actualBoundingBoxDescent;\n        const yDecoration = opts.strikethrough ? (top + bottom) / 2 : bottom;\n        ctx.strokeStyle = ctx.fillStyle;\n        ctx.beginPath();\n        ctx.lineWidth = opts.decorationWidth || 2;\n        ctx.moveTo(left, yDecoration);\n        ctx.lineTo(right, yDecoration);\n        ctx.stroke();\n    }\n}\nfunction drawBackdrop(ctx, opts) {\n    const oldColor = ctx.fillStyle;\n    ctx.fillStyle = opts.color;\n    ctx.fillRect(opts.left, opts.top, opts.width, opts.height);\n    ctx.fillStyle = oldColor;\n}\n/**\n * Render text onto the canvas\n */ function renderText(ctx, text, x, y, font, opts = {}) {\n    const lines = isArray(text) ? text : [\n        text\n    ];\n    const stroke = opts.strokeWidth > 0 && opts.strokeColor !== '';\n    let i, line;\n    ctx.save();\n    ctx.font = font.string;\n    setRenderOpts(ctx, opts);\n    for(i = 0; i < lines.length; ++i){\n        line = lines[i];\n        if (opts.backdrop) {\n            drawBackdrop(ctx, opts.backdrop);\n        }\n        if (stroke) {\n            if (opts.strokeColor) {\n                ctx.strokeStyle = opts.strokeColor;\n            }\n            if (!isNullOrUndef(opts.strokeWidth)) {\n                ctx.lineWidth = opts.strokeWidth;\n            }\n            ctx.strokeText(line, x, y, opts.maxWidth);\n        }\n        ctx.fillText(line, x, y, opts.maxWidth);\n        decorateText(ctx, x, y, line, opts);\n        y += Number(font.lineHeight);\n    }\n    ctx.restore();\n}\n/**\n * Add a path of a rectangle with rounded corners to the current sub-path\n * @param ctx - Context\n * @param rect - Bounding rect\n */ function addRoundedRectPath(ctx, rect) {\n    const { x , y , w , h , radius  } = rect;\n    // top left arc\n    ctx.arc(x + radius.topLeft, y + radius.topLeft, radius.topLeft, 1.5 * PI, PI, true);\n    // line from top left to bottom left\n    ctx.lineTo(x, y + h - radius.bottomLeft);\n    // bottom left arc\n    ctx.arc(x + radius.bottomLeft, y + h - radius.bottomLeft, radius.bottomLeft, PI, HALF_PI, true);\n    // line from bottom left to bottom right\n    ctx.lineTo(x + w - radius.bottomRight, y + h);\n    // bottom right arc\n    ctx.arc(x + w - radius.bottomRight, y + h - radius.bottomRight, radius.bottomRight, HALF_PI, 0, true);\n    // line from bottom right to top right\n    ctx.lineTo(x + w, y + radius.topRight);\n    // top right arc\n    ctx.arc(x + w - radius.topRight, y + radius.topRight, radius.topRight, 0, -HALF_PI, true);\n    // line from top right to top left\n    ctx.lineTo(x + radius.topLeft, y);\n}\n\nconst LINE_HEIGHT = /^(normal|(\\d+(?:\\.\\d+)?)(px|em|%)?)$/;\nconst FONT_STYLE = /^(normal|italic|initial|inherit|unset|(oblique( -?[0-9]?[0-9]deg)?))$/;\n/**\n * @alias Chart.helpers.options\n * @namespace\n */ /**\n * Converts the given line height `value` in pixels for a specific font `size`.\n * @param value - The lineHeight to parse (eg. 1.6, '14px', '75%', '1.6em').\n * @param size - The font size (in pixels) used to resolve relative `value`.\n * @returns The effective line height in pixels (size * 1.2 if value is invalid).\n * @see https://developer.mozilla.org/en-US/docs/Web/CSS/line-height\n * @since 2.7.0\n */ function toLineHeight(value, size) {\n    const matches = ('' + value).match(LINE_HEIGHT);\n    if (!matches || matches[1] === 'normal') {\n        return size * 1.2;\n    }\n    value = +matches[2];\n    switch(matches[3]){\n        case 'px':\n            return value;\n        case '%':\n            value /= 100;\n            break;\n    }\n    return size * value;\n}\nconst numberOrZero = (v)=>+v || 0;\nfunction _readValueToProps(value, props) {\n    const ret = {};\n    const objProps = isObject(props);\n    const keys = objProps ? Object.keys(props) : props;\n    const read = isObject(value) ? objProps ? (prop)=>valueOrDefault(value[prop], value[props[prop]]) : (prop)=>value[prop] : ()=>value;\n    for (const prop of keys){\n        ret[prop] = numberOrZero(read(prop));\n    }\n    return ret;\n}\n/**\n * Converts the given value into a TRBL object.\n * @param value - If a number, set the value to all TRBL component,\n *  else, if an object, use defined properties and sets undefined ones to 0.\n *  x / y are shorthands for same value for left/right and top/bottom.\n * @returns The padding values (top, right, bottom, left)\n * @since 3.0.0\n */ function toTRBL(value) {\n    return _readValueToProps(value, {\n        top: 'y',\n        right: 'x',\n        bottom: 'y',\n        left: 'x'\n    });\n}\n/**\n * Converts the given value into a TRBL corners object (similar with css border-radius).\n * @param value - If a number, set the value to all TRBL corner components,\n *  else, if an object, use defined properties and sets undefined ones to 0.\n * @returns The TRBL corner values (topLeft, topRight, bottomLeft, bottomRight)\n * @since 3.0.0\n */ function toTRBLCorners(value) {\n    return _readValueToProps(value, [\n        'topLeft',\n        'topRight',\n        'bottomLeft',\n        'bottomRight'\n    ]);\n}\n/**\n * Converts the given value into a padding object with pre-computed width/height.\n * @param value - If a number, set the value to all TRBL component,\n *  else, if an object, use defined properties and sets undefined ones to 0.\n *  x / y are shorthands for same value for left/right and top/bottom.\n * @returns The padding values (top, right, bottom, left, width, height)\n * @since 2.7.0\n */ function toPadding(value) {\n    const obj = toTRBL(value);\n    obj.width = obj.left + obj.right;\n    obj.height = obj.top + obj.bottom;\n    return obj;\n}\n/**\n * Parses font options and returns the font object.\n * @param options - A object that contains font options to be parsed.\n * @param fallback - A object that contains fallback font options.\n * @return The font object.\n * @private\n */ function toFont(options, fallback) {\n    options = options || {};\n    fallback = fallback || defaults.font;\n    let size = valueOrDefault(options.size, fallback.size);\n    if (typeof size === 'string') {\n        size = parseInt(size, 10);\n    }\n    let style = valueOrDefault(options.style, fallback.style);\n    if (style && !('' + style).match(FONT_STYLE)) {\n        console.warn('Invalid font style specified: \"' + style + '\"');\n        style = undefined;\n    }\n    const font = {\n        family: valueOrDefault(options.family, fallback.family),\n        lineHeight: toLineHeight(valueOrDefault(options.lineHeight, fallback.lineHeight), size),\n        size,\n        style,\n        weight: valueOrDefault(options.weight, fallback.weight),\n        string: ''\n    };\n    font.string = toFontString(font);\n    return font;\n}\n/**\n * Evaluates the given `inputs` sequentially and returns the first defined value.\n * @param inputs - An array of values, falling back to the last value.\n * @param context - If defined and the current value is a function, the value\n * is called with `context` as first argument and the result becomes the new input.\n * @param index - If defined and the current value is an array, the value\n * at `index` become the new input.\n * @param info - object to return information about resolution in\n * @param info.cacheable - Will be set to `false` if option is not cacheable.\n * @since 2.7.0\n */ function resolve(inputs, context, index, info) {\n    let cacheable = true;\n    let i, ilen, value;\n    for(i = 0, ilen = inputs.length; i < ilen; ++i){\n        value = inputs[i];\n        if (value === undefined) {\n            continue;\n        }\n        if (context !== undefined && typeof value === 'function') {\n            value = value(context);\n            cacheable = false;\n        }\n        if (index !== undefined && isArray(value)) {\n            value = value[index % value.length];\n            cacheable = false;\n        }\n        if (value !== undefined) {\n            if (info && !cacheable) {\n                info.cacheable = false;\n            }\n            return value;\n        }\n    }\n}\n/**\n * @param minmax\n * @param grace\n * @param beginAtZero\n * @private\n */ function _addGrace(minmax, grace, beginAtZero) {\n    const { min , max  } = minmax;\n    const change = toDimension(grace, (max - min) / 2);\n    const keepZero = (value, add)=>beginAtZero && value === 0 ? 0 : value + add;\n    return {\n        min: keepZero(min, -Math.abs(change)),\n        max: keepZero(max, change)\n    };\n}\nfunction createContext(parentContext, context) {\n    return Object.assign(Object.create(parentContext), context);\n}\n\n/**\n * Creates a Proxy for resolving raw values for options.\n * @param scopes - The option scopes to look for values, in resolution order\n * @param prefixes - The prefixes for values, in resolution order.\n * @param rootScopes - The root option scopes\n * @param fallback - Parent scopes fallback\n * @param getTarget - callback for getting the target for changed values\n * @returns Proxy\n * @private\n */ function _createResolver(scopes, prefixes = [\n    ''\n], rootScopes, fallback, getTarget = ()=>scopes[0]) {\n    const finalRootScopes = rootScopes || scopes;\n    if (typeof fallback === 'undefined') {\n        fallback = _resolve('_fallback', scopes);\n    }\n    const cache = {\n        [Symbol.toStringTag]: 'Object',\n        _cacheable: true,\n        _scopes: scopes,\n        _rootScopes: finalRootScopes,\n        _fallback: fallback,\n        _getTarget: getTarget,\n        override: (scope)=>_createResolver([\n                scope,\n                ...scopes\n            ], prefixes, finalRootScopes, fallback)\n    };\n    return new Proxy(cache, {\n        /**\n     * A trap for the delete operator.\n     */ deleteProperty (target, prop) {\n            delete target[prop]; // remove from cache\n            delete target._keys; // remove cached keys\n            delete scopes[0][prop]; // remove from top level scope\n            return true;\n        },\n        /**\n     * A trap for getting property values.\n     */ get (target, prop) {\n            return _cached(target, prop, ()=>_resolveWithPrefixes(prop, prefixes, scopes, target));\n        },\n        /**\n     * A trap for Object.getOwnPropertyDescriptor.\n     * Also used by Object.hasOwnProperty.\n     */ getOwnPropertyDescriptor (target, prop) {\n            return Reflect.getOwnPropertyDescriptor(target._scopes[0], prop);\n        },\n        /**\n     * A trap for Object.getPrototypeOf.\n     */ getPrototypeOf () {\n            return Reflect.getPrototypeOf(scopes[0]);\n        },\n        /**\n     * A trap for the in operator.\n     */ has (target, prop) {\n            return getKeysFromAllScopes(target).includes(prop);\n        },\n        /**\n     * A trap for Object.getOwnPropertyNames and Object.getOwnPropertySymbols.\n     */ ownKeys (target) {\n            return getKeysFromAllScopes(target);\n        },\n        /**\n     * A trap for setting property values.\n     */ set (target, prop, value) {\n            const storage = target._storage || (target._storage = getTarget());\n            target[prop] = storage[prop] = value; // set to top level scope + cache\n            delete target._keys; // remove cached keys\n            return true;\n        }\n    });\n}\n/**\n * Returns an Proxy for resolving option values with context.\n * @param proxy - The Proxy returned by `_createResolver`\n * @param context - Context object for scriptable/indexable options\n * @param subProxy - The proxy provided for scriptable options\n * @param descriptorDefaults - Defaults for descriptors\n * @private\n */ function _attachContext(proxy, context, subProxy, descriptorDefaults) {\n    const cache = {\n        _cacheable: false,\n        _proxy: proxy,\n        _context: context,\n        _subProxy: subProxy,\n        _stack: new Set(),\n        _descriptors: _descriptors(proxy, descriptorDefaults),\n        setContext: (ctx)=>_attachContext(proxy, ctx, subProxy, descriptorDefaults),\n        override: (scope)=>_attachContext(proxy.override(scope), context, subProxy, descriptorDefaults)\n    };\n    return new Proxy(cache, {\n        /**\n     * A trap for the delete operator.\n     */ deleteProperty (target, prop) {\n            delete target[prop]; // remove from cache\n            delete proxy[prop]; // remove from proxy\n            return true;\n        },\n        /**\n     * A trap for getting property values.\n     */ get (target, prop, receiver) {\n            return _cached(target, prop, ()=>_resolveWithContext(target, prop, receiver));\n        },\n        /**\n     * A trap for Object.getOwnPropertyDescriptor.\n     * Also used by Object.hasOwnProperty.\n     */ getOwnPropertyDescriptor (target, prop) {\n            return target._descriptors.allKeys ? Reflect.has(proxy, prop) ? {\n                enumerable: true,\n                configurable: true\n            } : undefined : Reflect.getOwnPropertyDescriptor(proxy, prop);\n        },\n        /**\n     * A trap for Object.getPrototypeOf.\n     */ getPrototypeOf () {\n            return Reflect.getPrototypeOf(proxy);\n        },\n        /**\n     * A trap for the in operator.\n     */ has (target, prop) {\n            return Reflect.has(proxy, prop);\n        },\n        /**\n     * A trap for Object.getOwnPropertyNames and Object.getOwnPropertySymbols.\n     */ ownKeys () {\n            return Reflect.ownKeys(proxy);\n        },\n        /**\n     * A trap for setting property values.\n     */ set (target, prop, value) {\n            proxy[prop] = value; // set to proxy\n            delete target[prop]; // remove from cache\n            return true;\n        }\n    });\n}\n/**\n * @private\n */ function _descriptors(proxy, defaults = {\n    scriptable: true,\n    indexable: true\n}) {\n    const { _scriptable =defaults.scriptable , _indexable =defaults.indexable , _allKeys =defaults.allKeys  } = proxy;\n    return {\n        allKeys: _allKeys,\n        scriptable: _scriptable,\n        indexable: _indexable,\n        isScriptable: isFunction(_scriptable) ? _scriptable : ()=>_scriptable,\n        isIndexable: isFunction(_indexable) ? _indexable : ()=>_indexable\n    };\n}\nconst readKey = (prefix, name)=>prefix ? prefix + _capitalize(name) : name;\nconst needsSubResolver = (prop, value)=>isObject(value) && prop !== 'adapters' && (Object.getPrototypeOf(value) === null || value.constructor === Object);\nfunction _cached(target, prop, resolve) {\n    if (Object.prototype.hasOwnProperty.call(target, prop)) {\n        return target[prop];\n    }\n    const value = resolve();\n    // cache the resolved value\n    target[prop] = value;\n    return value;\n}\nfunction _resolveWithContext(target, prop, receiver) {\n    const { _proxy , _context , _subProxy , _descriptors: descriptors  } = target;\n    let value = _proxy[prop]; // resolve from proxy\n    // resolve with context\n    if (isFunction(value) && descriptors.isScriptable(prop)) {\n        value = _resolveScriptable(prop, value, target, receiver);\n    }\n    if (isArray(value) && value.length) {\n        value = _resolveArray(prop, value, target, descriptors.isIndexable);\n    }\n    if (needsSubResolver(prop, value)) {\n        // if the resolved value is an object, create a sub resolver for it\n        value = _attachContext(value, _context, _subProxy && _subProxy[prop], descriptors);\n    }\n    return value;\n}\nfunction _resolveScriptable(prop, getValue, target, receiver) {\n    const { _proxy , _context , _subProxy , _stack  } = target;\n    if (_stack.has(prop)) {\n        throw new Error('Recursion detected: ' + Array.from(_stack).join('->') + '->' + prop);\n    }\n    _stack.add(prop);\n    let value = getValue(_context, _subProxy || receiver);\n    _stack.delete(prop);\n    if (needsSubResolver(prop, value)) {\n        // When scriptable option returns an object, create a resolver on that.\n        value = createSubResolver(_proxy._scopes, _proxy, prop, value);\n    }\n    return value;\n}\nfunction _resolveArray(prop, value, target, isIndexable) {\n    const { _proxy , _context , _subProxy , _descriptors: descriptors  } = target;\n    if (typeof _context.index !== 'undefined' && isIndexable(prop)) {\n        return value[_context.index % value.length];\n    } else if (isObject(value[0])) {\n        // Array of objects, return array or resolvers\n        const arr = value;\n        const scopes = _proxy._scopes.filter((s)=>s !== arr);\n        value = [];\n        for (const item of arr){\n            const resolver = createSubResolver(scopes, _proxy, prop, item);\n            value.push(_attachContext(resolver, _context, _subProxy && _subProxy[prop], descriptors));\n        }\n    }\n    return value;\n}\nfunction resolveFallback(fallback, prop, value) {\n    return isFunction(fallback) ? fallback(prop, value) : fallback;\n}\nconst getScope = (key, parent)=>key === true ? parent : typeof key === 'string' ? resolveObjectKey(parent, key) : undefined;\nfunction addScopes(set, parentScopes, key, parentFallback, value) {\n    for (const parent of parentScopes){\n        const scope = getScope(key, parent);\n        if (scope) {\n            set.add(scope);\n            const fallback = resolveFallback(scope._fallback, key, value);\n            if (typeof fallback !== 'undefined' && fallback !== key && fallback !== parentFallback) {\n                // When we reach the descriptor that defines a new _fallback, return that.\n                // The fallback will resume to that new scope.\n                return fallback;\n            }\n        } else if (scope === false && typeof parentFallback !== 'undefined' && key !== parentFallback) {\n            // Fallback to `false` results to `false`, when falling back to different key.\n            // For example `interaction` from `hover` or `plugins.tooltip` and `animation` from `animations`\n            return null;\n        }\n    }\n    return false;\n}\nfunction createSubResolver(parentScopes, resolver, prop, value) {\n    const rootScopes = resolver._rootScopes;\n    const fallback = resolveFallback(resolver._fallback, prop, value);\n    const allScopes = [\n        ...parentScopes,\n        ...rootScopes\n    ];\n    const set = new Set();\n    set.add(value);\n    let key = addScopesFromKey(set, allScopes, prop, fallback || prop, value);\n    if (key === null) {\n        return false;\n    }\n    if (typeof fallback !== 'undefined' && fallback !== prop) {\n        key = addScopesFromKey(set, allScopes, fallback, key, value);\n        if (key === null) {\n            return false;\n        }\n    }\n    return _createResolver(Array.from(set), [\n        ''\n    ], rootScopes, fallback, ()=>subGetTarget(resolver, prop, value));\n}\nfunction addScopesFromKey(set, allScopes, key, fallback, item) {\n    while(key){\n        key = addScopes(set, allScopes, key, fallback, item);\n    }\n    return key;\n}\nfunction subGetTarget(resolver, prop, value) {\n    const parent = resolver._getTarget();\n    if (!(prop in parent)) {\n        parent[prop] = {};\n    }\n    const target = parent[prop];\n    if (isArray(target) && isObject(value)) {\n        // For array of objects, the object is used to store updated values\n        return value;\n    }\n    return target || {};\n}\nfunction _resolveWithPrefixes(prop, prefixes, scopes, proxy) {\n    let value;\n    for (const prefix of prefixes){\n        value = _resolve(readKey(prefix, prop), scopes);\n        if (typeof value !== 'undefined') {\n            return needsSubResolver(prop, value) ? createSubResolver(scopes, proxy, prop, value) : value;\n        }\n    }\n}\nfunction _resolve(key, scopes) {\n    for (const scope of scopes){\n        if (!scope) {\n            continue;\n        }\n        const value = scope[key];\n        if (typeof value !== 'undefined') {\n            return value;\n        }\n    }\n}\nfunction getKeysFromAllScopes(target) {\n    let keys = target._keys;\n    if (!keys) {\n        keys = target._keys = resolveKeysFromAllScopes(target._scopes);\n    }\n    return keys;\n}\nfunction resolveKeysFromAllScopes(scopes) {\n    const set = new Set();\n    for (const scope of scopes){\n        for (const key of Object.keys(scope).filter((k)=>!k.startsWith('_'))){\n            set.add(key);\n        }\n    }\n    return Array.from(set);\n}\nfunction _parseObjectDataRadialScale(meta, data, start, count) {\n    const { iScale  } = meta;\n    const { key ='r'  } = this._parsing;\n    const parsed = new Array(count);\n    let i, ilen, index, item;\n    for(i = 0, ilen = count; i < ilen; ++i){\n        index = i + start;\n        item = data[index];\n        parsed[i] = {\n            r: iScale.parse(resolveObjectKey(item, key), index)\n        };\n    }\n    return parsed;\n}\n\nconst EPSILON = Number.EPSILON || 1e-14;\nconst getPoint = (points, i)=>i < points.length && !points[i].skip && points[i];\nconst getValueAxis = (indexAxis)=>indexAxis === 'x' ? 'y' : 'x';\nfunction splineCurve(firstPoint, middlePoint, afterPoint, t) {\n    // Props to Rob Spencer at scaled innovation for his post on splining between points\n    // http://scaledinnovation.com/analytics/splines/aboutSplines.html\n    // This function must also respect \"skipped\" points\n    const previous = firstPoint.skip ? middlePoint : firstPoint;\n    const current = middlePoint;\n    const next = afterPoint.skip ? middlePoint : afterPoint;\n    const d01 = distanceBetweenPoints(current, previous);\n    const d12 = distanceBetweenPoints(next, current);\n    let s01 = d01 / (d01 + d12);\n    let s12 = d12 / (d01 + d12);\n    // If all points are the same, s01 & s02 will be inf\n    s01 = isNaN(s01) ? 0 : s01;\n    s12 = isNaN(s12) ? 0 : s12;\n    const fa = t * s01; // scaling factor for triangle Ta\n    const fb = t * s12;\n    return {\n        previous: {\n            x: current.x - fa * (next.x - previous.x),\n            y: current.y - fa * (next.y - previous.y)\n        },\n        next: {\n            x: current.x + fb * (next.x - previous.x),\n            y: current.y + fb * (next.y - previous.y)\n        }\n    };\n}\n/**\n * Adjust tangents to ensure monotonic properties\n */ function monotoneAdjust(points, deltaK, mK) {\n    const pointsLen = points.length;\n    let alphaK, betaK, tauK, squaredMagnitude, pointCurrent;\n    let pointAfter = getPoint(points, 0);\n    for(let i = 0; i < pointsLen - 1; ++i){\n        pointCurrent = pointAfter;\n        pointAfter = getPoint(points, i + 1);\n        if (!pointCurrent || !pointAfter) {\n            continue;\n        }\n        if (almostEquals(deltaK[i], 0, EPSILON)) {\n            mK[i] = mK[i + 1] = 0;\n            continue;\n        }\n        alphaK = mK[i] / deltaK[i];\n        betaK = mK[i + 1] / deltaK[i];\n        squaredMagnitude = Math.pow(alphaK, 2) + Math.pow(betaK, 2);\n        if (squaredMagnitude <= 9) {\n            continue;\n        }\n        tauK = 3 / Math.sqrt(squaredMagnitude);\n        mK[i] = alphaK * tauK * deltaK[i];\n        mK[i + 1] = betaK * tauK * deltaK[i];\n    }\n}\nfunction monotoneCompute(points, mK, indexAxis = 'x') {\n    const valueAxis = getValueAxis(indexAxis);\n    const pointsLen = points.length;\n    let delta, pointBefore, pointCurrent;\n    let pointAfter = getPoint(points, 0);\n    for(let i = 0; i < pointsLen; ++i){\n        pointBefore = pointCurrent;\n        pointCurrent = pointAfter;\n        pointAfter = getPoint(points, i + 1);\n        if (!pointCurrent) {\n            continue;\n        }\n        const iPixel = pointCurrent[indexAxis];\n        const vPixel = pointCurrent[valueAxis];\n        if (pointBefore) {\n            delta = (iPixel - pointBefore[indexAxis]) / 3;\n            pointCurrent[`cp1${indexAxis}`] = iPixel - delta;\n            pointCurrent[`cp1${valueAxis}`] = vPixel - delta * mK[i];\n        }\n        if (pointAfter) {\n            delta = (pointAfter[indexAxis] - iPixel) / 3;\n            pointCurrent[`cp2${indexAxis}`] = iPixel + delta;\n            pointCurrent[`cp2${valueAxis}`] = vPixel + delta * mK[i];\n        }\n    }\n}\n/**\n * This function calculates Bézier control points in a similar way than |splineCurve|,\n * but preserves monotonicity of the provided data and ensures no local extremums are added\n * between the dataset discrete points due to the interpolation.\n * See : https://en.wikipedia.org/wiki/Monotone_cubic_interpolation\n */ function splineCurveMonotone(points, indexAxis = 'x') {\n    const valueAxis = getValueAxis(indexAxis);\n    const pointsLen = points.length;\n    const deltaK = Array(pointsLen).fill(0);\n    const mK = Array(pointsLen);\n    // Calculate slopes (deltaK) and initialize tangents (mK)\n    let i, pointBefore, pointCurrent;\n    let pointAfter = getPoint(points, 0);\n    for(i = 0; i < pointsLen; ++i){\n        pointBefore = pointCurrent;\n        pointCurrent = pointAfter;\n        pointAfter = getPoint(points, i + 1);\n        if (!pointCurrent) {\n            continue;\n        }\n        if (pointAfter) {\n            const slopeDelta = pointAfter[indexAxis] - pointCurrent[indexAxis];\n            // In the case of two points that appear at the same x pixel, slopeDeltaX is 0\n            deltaK[i] = slopeDelta !== 0 ? (pointAfter[valueAxis] - pointCurrent[valueAxis]) / slopeDelta : 0;\n        }\n        mK[i] = !pointBefore ? deltaK[i] : !pointAfter ? deltaK[i - 1] : sign(deltaK[i - 1]) !== sign(deltaK[i]) ? 0 : (deltaK[i - 1] + deltaK[i]) / 2;\n    }\n    monotoneAdjust(points, deltaK, mK);\n    monotoneCompute(points, mK, indexAxis);\n}\nfunction capControlPoint(pt, min, max) {\n    return Math.max(Math.min(pt, max), min);\n}\nfunction capBezierPoints(points, area) {\n    let i, ilen, point, inArea, inAreaPrev;\n    let inAreaNext = _isPointInArea(points[0], area);\n    for(i = 0, ilen = points.length; i < ilen; ++i){\n        inAreaPrev = inArea;\n        inArea = inAreaNext;\n        inAreaNext = i < ilen - 1 && _isPointInArea(points[i + 1], area);\n        if (!inArea) {\n            continue;\n        }\n        point = points[i];\n        if (inAreaPrev) {\n            point.cp1x = capControlPoint(point.cp1x, area.left, area.right);\n            point.cp1y = capControlPoint(point.cp1y, area.top, area.bottom);\n        }\n        if (inAreaNext) {\n            point.cp2x = capControlPoint(point.cp2x, area.left, area.right);\n            point.cp2y = capControlPoint(point.cp2y, area.top, area.bottom);\n        }\n    }\n}\n/**\n * @private\n */ function _updateBezierControlPoints(points, options, area, loop, indexAxis) {\n    let i, ilen, point, controlPoints;\n    // Only consider points that are drawn in case the spanGaps option is used\n    if (options.spanGaps) {\n        points = points.filter((pt)=>!pt.skip);\n    }\n    if (options.cubicInterpolationMode === 'monotone') {\n        splineCurveMonotone(points, indexAxis);\n    } else {\n        let prev = loop ? points[points.length - 1] : points[0];\n        for(i = 0, ilen = points.length; i < ilen; ++i){\n            point = points[i];\n            controlPoints = splineCurve(prev, point, points[Math.min(i + 1, ilen - (loop ? 0 : 1)) % ilen], options.tension);\n            point.cp1x = controlPoints.previous.x;\n            point.cp1y = controlPoints.previous.y;\n            point.cp2x = controlPoints.next.x;\n            point.cp2y = controlPoints.next.y;\n            prev = point;\n        }\n    }\n    if (options.capBezierPoints) {\n        capBezierPoints(points, area);\n    }\n}\n\n/**\n * Note: typedefs are auto-exported, so use a made-up `dom` namespace where\n * necessary to avoid duplicates with `export * from './helpers`; see\n * https://github.com/microsoft/TypeScript/issues/46011\n * @typedef { import('../core/core.controller.js').default } dom.Chart\n * @typedef { import('../../types').ChartEvent } ChartEvent\n */ /**\n * @private\n */ function _isDomSupported() {\n    return typeof window !== 'undefined' && typeof document !== 'undefined';\n}\n/**\n * @private\n */ function _getParentNode(domNode) {\n    let parent = domNode.parentNode;\n    if (parent && parent.toString() === '[object ShadowRoot]') {\n        parent = parent.host;\n    }\n    return parent;\n}\n/**\n * convert max-width/max-height values that may be percentages into a number\n * @private\n */ function parseMaxStyle(styleValue, node, parentProperty) {\n    let valueInPixels;\n    if (typeof styleValue === 'string') {\n        valueInPixels = parseInt(styleValue, 10);\n        if (styleValue.indexOf('%') !== -1) {\n            // percentage * size in dimension\n            valueInPixels = valueInPixels / 100 * node.parentNode[parentProperty];\n        }\n    } else {\n        valueInPixels = styleValue;\n    }\n    return valueInPixels;\n}\nconst getComputedStyle = (element)=>element.ownerDocument.defaultView.getComputedStyle(element, null);\nfunction getStyle(el, property) {\n    return getComputedStyle(el).getPropertyValue(property);\n}\nconst positions = [\n    'top',\n    'right',\n    'bottom',\n    'left'\n];\nfunction getPositionedStyle(styles, style, suffix) {\n    const result = {};\n    suffix = suffix ? '-' + suffix : '';\n    for(let i = 0; i < 4; i++){\n        const pos = positions[i];\n        result[pos] = parseFloat(styles[style + '-' + pos + suffix]) || 0;\n    }\n    result.width = result.left + result.right;\n    result.height = result.top + result.bottom;\n    return result;\n}\nconst useOffsetPos = (x, y, target)=>(x > 0 || y > 0) && (!target || !target.shadowRoot);\n/**\n * @param e\n * @param canvas\n * @returns Canvas position\n */ function getCanvasPosition(e, canvas) {\n    const touches = e.touches;\n    const source = touches && touches.length ? touches[0] : e;\n    const { offsetX , offsetY  } = source;\n    let box = false;\n    let x, y;\n    if (useOffsetPos(offsetX, offsetY, e.target)) {\n        x = offsetX;\n        y = offsetY;\n    } else {\n        const rect = canvas.getBoundingClientRect();\n        x = source.clientX - rect.left;\n        y = source.clientY - rect.top;\n        box = true;\n    }\n    return {\n        x,\n        y,\n        box\n    };\n}\n/**\n * Gets an event's x, y coordinates, relative to the chart area\n * @param event\n * @param chart\n * @returns x and y coordinates of the event\n */ function getRelativePosition(event, chart) {\n    if ('native' in event) {\n        return event;\n    }\n    const { canvas , currentDevicePixelRatio  } = chart;\n    const style = getComputedStyle(canvas);\n    const borderBox = style.boxSizing === 'border-box';\n    const paddings = getPositionedStyle(style, 'padding');\n    const borders = getPositionedStyle(style, 'border', 'width');\n    const { x , y , box  } = getCanvasPosition(event, canvas);\n    const xOffset = paddings.left + (box && borders.left);\n    const yOffset = paddings.top + (box && borders.top);\n    let { width , height  } = chart;\n    if (borderBox) {\n        width -= paddings.width + borders.width;\n        height -= paddings.height + borders.height;\n    }\n    return {\n        x: Math.round((x - xOffset) / width * canvas.width / currentDevicePixelRatio),\n        y: Math.round((y - yOffset) / height * canvas.height / currentDevicePixelRatio)\n    };\n}\nfunction getContainerSize(canvas, width, height) {\n    let maxWidth, maxHeight;\n    if (width === undefined || height === undefined) {\n        const container = _getParentNode(canvas);\n        if (!container) {\n            width = canvas.clientWidth;\n            height = canvas.clientHeight;\n        } else {\n            const rect = container.getBoundingClientRect(); // this is the border box of the container\n            const containerStyle = getComputedStyle(container);\n            const containerBorder = getPositionedStyle(containerStyle, 'border', 'width');\n            const containerPadding = getPositionedStyle(containerStyle, 'padding');\n            width = rect.width - containerPadding.width - containerBorder.width;\n            height = rect.height - containerPadding.height - containerBorder.height;\n            maxWidth = parseMaxStyle(containerStyle.maxWidth, container, 'clientWidth');\n            maxHeight = parseMaxStyle(containerStyle.maxHeight, container, 'clientHeight');\n        }\n    }\n    return {\n        width,\n        height,\n        maxWidth: maxWidth || INFINITY,\n        maxHeight: maxHeight || INFINITY\n    };\n}\nconst round1 = (v)=>Math.round(v * 10) / 10;\n// eslint-disable-next-line complexity\nfunction getMaximumSize(canvas, bbWidth, bbHeight, aspectRatio) {\n    const style = getComputedStyle(canvas);\n    const margins = getPositionedStyle(style, 'margin');\n    const maxWidth = parseMaxStyle(style.maxWidth, canvas, 'clientWidth') || INFINITY;\n    const maxHeight = parseMaxStyle(style.maxHeight, canvas, 'clientHeight') || INFINITY;\n    const containerSize = getContainerSize(canvas, bbWidth, bbHeight);\n    let { width , height  } = containerSize;\n    if (style.boxSizing === 'content-box') {\n        const borders = getPositionedStyle(style, 'border', 'width');\n        const paddings = getPositionedStyle(style, 'padding');\n        width -= paddings.width + borders.width;\n        height -= paddings.height + borders.height;\n    }\n    width = Math.max(0, width - margins.width);\n    height = Math.max(0, aspectRatio ? width / aspectRatio : height - margins.height);\n    width = round1(Math.min(width, maxWidth, containerSize.maxWidth));\n    height = round1(Math.min(height, maxHeight, containerSize.maxHeight));\n    if (width && !height) {\n        // https://github.com/chartjs/Chart.js/issues/4659\n        // If the canvas has width, but no height, default to aspectRatio of 2 (canvas default)\n        height = round1(width / 2);\n    }\n    const maintainHeight = bbWidth !== undefined || bbHeight !== undefined;\n    if (maintainHeight && aspectRatio && containerSize.height && height > containerSize.height) {\n        height = containerSize.height;\n        width = round1(Math.floor(height * aspectRatio));\n    }\n    return {\n        width,\n        height\n    };\n}\n/**\n * @param chart\n * @param forceRatio\n * @param forceStyle\n * @returns True if the canvas context size or transformation has changed.\n */ function retinaScale(chart, forceRatio, forceStyle) {\n    const pixelRatio = forceRatio || 1;\n    const deviceHeight = Math.floor(chart.height * pixelRatio);\n    const deviceWidth = Math.floor(chart.width * pixelRatio);\n    chart.height = Math.floor(chart.height);\n    chart.width = Math.floor(chart.width);\n    const canvas = chart.canvas;\n    // If no style has been set on the canvas, the render size is used as display size,\n    // making the chart visually bigger, so let's enforce it to the \"correct\" values.\n    // See https://github.com/chartjs/Chart.js/issues/3575\n    if (canvas.style && (forceStyle || !canvas.style.height && !canvas.style.width)) {\n        canvas.style.height = `${chart.height}px`;\n        canvas.style.width = `${chart.width}px`;\n    }\n    if (chart.currentDevicePixelRatio !== pixelRatio || canvas.height !== deviceHeight || canvas.width !== deviceWidth) {\n        chart.currentDevicePixelRatio = pixelRatio;\n        canvas.height = deviceHeight;\n        canvas.width = deviceWidth;\n        chart.ctx.setTransform(pixelRatio, 0, 0, pixelRatio, 0, 0);\n        return true;\n    }\n    return false;\n}\n/**\n * Detects support for options object argument in addEventListener.\n * https://developer.mozilla.org/en-US/docs/Web/API/EventTarget/addEventListener#Safely_detecting_option_support\n * @private\n */ const supportsEventListenerOptions = function() {\n    let passiveSupported = false;\n    try {\n        const options = {\n            get passive () {\n                passiveSupported = true;\n                return false;\n            }\n        };\n        if (_isDomSupported()) {\n            window.addEventListener('test', null, options);\n            window.removeEventListener('test', null, options);\n        }\n    } catch (e) {\n    // continue regardless of error\n    }\n    return passiveSupported;\n}();\n/**\n * The \"used\" size is the final value of a dimension property after all calculations have\n * been performed. This method uses the computed style of `element` but returns undefined\n * if the computed style is not expressed in pixels. That can happen in some cases where\n * `element` has a size relative to its parent and this last one is not yet displayed,\n * for example because of `display: none` on a parent node.\n * @see https://developer.mozilla.org/en-US/docs/Web/CSS/used_value\n * @returns Size in pixels or undefined if unknown.\n */ function readUsedSize(element, property) {\n    const value = getStyle(element, property);\n    const matches = value && value.match(/^(\\d+)(\\.\\d+)?px$/);\n    return matches ? +matches[1] : undefined;\n}\n\n/**\n * @private\n */ function _pointInLine(p1, p2, t, mode) {\n    return {\n        x: p1.x + t * (p2.x - p1.x),\n        y: p1.y + t * (p2.y - p1.y)\n    };\n}\n/**\n * @private\n */ function _steppedInterpolation(p1, p2, t, mode) {\n    return {\n        x: p1.x + t * (p2.x - p1.x),\n        y: mode === 'middle' ? t < 0.5 ? p1.y : p2.y : mode === 'after' ? t < 1 ? p1.y : p2.y : t > 0 ? p2.y : p1.y\n    };\n}\n/**\n * @private\n */ function _bezierInterpolation(p1, p2, t, mode) {\n    const cp1 = {\n        x: p1.cp2x,\n        y: p1.cp2y\n    };\n    const cp2 = {\n        x: p2.cp1x,\n        y: p2.cp1y\n    };\n    const a = _pointInLine(p1, cp1, t);\n    const b = _pointInLine(cp1, cp2, t);\n    const c = _pointInLine(cp2, p2, t);\n    const d = _pointInLine(a, b, t);\n    const e = _pointInLine(b, c, t);\n    return _pointInLine(d, e, t);\n}\n\nconst getRightToLeftAdapter = function(rectX, width) {\n    return {\n        x (x) {\n            return rectX + rectX + width - x;\n        },\n        setWidth (w) {\n            width = w;\n        },\n        textAlign (align) {\n            if (align === 'center') {\n                return align;\n            }\n            return align === 'right' ? 'left' : 'right';\n        },\n        xPlus (x, value) {\n            return x - value;\n        },\n        leftForLtr (x, itemWidth) {\n            return x - itemWidth;\n        }\n    };\n};\nconst getLeftToRightAdapter = function() {\n    return {\n        x (x) {\n            return x;\n        },\n        setWidth (w) {},\n        textAlign (align) {\n            return align;\n        },\n        xPlus (x, value) {\n            return x + value;\n        },\n        leftForLtr (x, _itemWidth) {\n            return x;\n        }\n    };\n};\nfunction getRtlAdapter(rtl, rectX, width) {\n    return rtl ? getRightToLeftAdapter(rectX, width) : getLeftToRightAdapter();\n}\nfunction overrideTextDirection(ctx, direction) {\n    let style, original;\n    if (direction === 'ltr' || direction === 'rtl') {\n        style = ctx.canvas.style;\n        original = [\n            style.getPropertyValue('direction'),\n            style.getPropertyPriority('direction')\n        ];\n        style.setProperty('direction', direction, 'important');\n        ctx.prevTextDirection = original;\n    }\n}\nfunction restoreTextDirection(ctx, original) {\n    if (original !== undefined) {\n        delete ctx.prevTextDirection;\n        ctx.canvas.style.setProperty('direction', original[0], original[1]);\n    }\n}\n\nfunction propertyFn(property) {\n    if (property === 'angle') {\n        return {\n            between: _angleBetween,\n            compare: _angleDiff,\n            normalize: _normalizeAngle\n        };\n    }\n    return {\n        between: _isBetween,\n        compare: (a, b)=>a - b,\n        normalize: (x)=>x\n    };\n}\nfunction normalizeSegment({ start , end , count , loop , style  }) {\n    return {\n        start: start % count,\n        end: end % count,\n        loop: loop && (end - start + 1) % count === 0,\n        style\n    };\n}\nfunction getSegment(segment, points, bounds) {\n    const { property , start: startBound , end: endBound  } = bounds;\n    const { between , normalize  } = propertyFn(property);\n    const count = points.length;\n    let { start , end , loop  } = segment;\n    let i, ilen;\n    if (loop) {\n        start += count;\n        end += count;\n        for(i = 0, ilen = count; i < ilen; ++i){\n            if (!between(normalize(points[start % count][property]), startBound, endBound)) {\n                break;\n            }\n            start--;\n            end--;\n        }\n        start %= count;\n        end %= count;\n    }\n    if (end < start) {\n        end += count;\n    }\n    return {\n        start,\n        end,\n        loop,\n        style: segment.style\n    };\n}\n function _boundSegment(segment, points, bounds) {\n    if (!bounds) {\n        return [\n            segment\n        ];\n    }\n    const { property , start: startBound , end: endBound  } = bounds;\n    const count = points.length;\n    const { compare , between , normalize  } = propertyFn(property);\n    const { start , end , loop , style  } = getSegment(segment, points, bounds);\n    const result = [];\n    let inside = false;\n    let subStart = null;\n    let value, point, prevValue;\n    const startIsBefore = ()=>between(startBound, prevValue, value) && compare(startBound, prevValue) !== 0;\n    const endIsBefore = ()=>compare(endBound, value) === 0 || between(endBound, prevValue, value);\n    const shouldStart = ()=>inside || startIsBefore();\n    const shouldStop = ()=>!inside || endIsBefore();\n    for(let i = start, prev = start; i <= end; ++i){\n        point = points[i % count];\n        if (point.skip) {\n            continue;\n        }\n        value = normalize(point[property]);\n        if (value === prevValue) {\n            continue;\n        }\n        inside = between(value, startBound, endBound);\n        if (subStart === null && shouldStart()) {\n            subStart = compare(value, startBound) === 0 ? i : prev;\n        }\n        if (subStart !== null && shouldStop()) {\n            result.push(normalizeSegment({\n                start: subStart,\n                end: i,\n                loop,\n                count,\n                style\n            }));\n            subStart = null;\n        }\n        prev = i;\n        prevValue = value;\n    }\n    if (subStart !== null) {\n        result.push(normalizeSegment({\n            start: subStart,\n            end,\n            loop,\n            count,\n            style\n        }));\n    }\n    return result;\n}\n function _boundSegments(line, bounds) {\n    const result = [];\n    const segments = line.segments;\n    for(let i = 0; i < segments.length; i++){\n        const sub = _boundSegment(segments[i], line.points, bounds);\n        if (sub.length) {\n            result.push(...sub);\n        }\n    }\n    return result;\n}\n function findStartAndEnd(points, count, loop, spanGaps) {\n    let start = 0;\n    let end = count - 1;\n    if (loop && !spanGaps) {\n        while(start < count && !points[start].skip){\n            start++;\n        }\n    }\n    while(start < count && points[start].skip){\n        start++;\n    }\n    start %= count;\n    if (loop) {\n        end += start;\n    }\n    while(end > start && points[end % count].skip){\n        end--;\n    }\n    end %= count;\n    return {\n        start,\n        end\n    };\n}\n function solidSegments(points, start, max, loop) {\n    const count = points.length;\n    const result = [];\n    let last = start;\n    let prev = points[start];\n    let end;\n    for(end = start + 1; end <= max; ++end){\n        const cur = points[end % count];\n        if (cur.skip || cur.stop) {\n            if (!prev.skip) {\n                loop = false;\n                result.push({\n                    start: start % count,\n                    end: (end - 1) % count,\n                    loop\n                });\n                start = last = cur.stop ? end : null;\n            }\n        } else {\n            last = end;\n            if (prev.skip) {\n                start = end;\n            }\n        }\n        prev = cur;\n    }\n    if (last !== null) {\n        result.push({\n            start: start % count,\n            end: last % count,\n            loop\n        });\n    }\n    return result;\n}\n function _computeSegments(line, segmentOptions) {\n    const points = line.points;\n    const spanGaps = line.options.spanGaps;\n    const count = points.length;\n    if (!count) {\n        return [];\n    }\n    const loop = !!line._loop;\n    const { start , end  } = findStartAndEnd(points, count, loop, spanGaps);\n    if (spanGaps === true) {\n        return splitByStyles(line, [\n            {\n                start,\n                end,\n                loop\n            }\n        ], points, segmentOptions);\n    }\n    const max = end < start ? end + count : end;\n    const completeLoop = !!line._fullLoop && start === 0 && end === count - 1;\n    return splitByStyles(line, solidSegments(points, start, max, completeLoop), points, segmentOptions);\n}\n function splitByStyles(line, segments, points, segmentOptions) {\n    if (!segmentOptions || !segmentOptions.setContext || !points) {\n        return segments;\n    }\n    return doSplitByStyles(line, segments, points, segmentOptions);\n}\n function doSplitByStyles(line, segments, points, segmentOptions) {\n    const chartContext = line._chart.getContext();\n    const baseStyle = readStyle(line.options);\n    const { _datasetIndex: datasetIndex , options: { spanGaps  }  } = line;\n    const count = points.length;\n    const result = [];\n    let prevStyle = baseStyle;\n    let start = segments[0].start;\n    let i = start;\n    function addStyle(s, e, l, st) {\n        const dir = spanGaps ? -1 : 1;\n        if (s === e) {\n            return;\n        }\n        s += count;\n        while(points[s % count].skip){\n            s -= dir;\n        }\n        while(points[e % count].skip){\n            e += dir;\n        }\n        if (s % count !== e % count) {\n            result.push({\n                start: s % count,\n                end: e % count,\n                loop: l,\n                style: st\n            });\n            prevStyle = st;\n            start = e % count;\n        }\n    }\n    for (const segment of segments){\n        start = spanGaps ? start : segment.start;\n        let prev = points[start % count];\n        let style;\n        for(i = start + 1; i <= segment.end; i++){\n            const pt = points[i % count];\n            style = readStyle(segmentOptions.setContext(createContext(chartContext, {\n                type: 'segment',\n                p0: prev,\n                p1: pt,\n                p0DataIndex: (i - 1) % count,\n                p1DataIndex: i % count,\n                datasetIndex\n            })));\n            if (styleChanged(style, prevStyle)) {\n                addStyle(start, i - 1, segment.loop, prevStyle);\n            }\n            prev = pt;\n            prevStyle = style;\n        }\n        if (start < i - 1) {\n            addStyle(start, i - 1, segment.loop, prevStyle);\n        }\n    }\n    return result;\n}\nfunction readStyle(options) {\n    return {\n        backgroundColor: options.backgroundColor,\n        borderCapStyle: options.borderCapStyle,\n        borderDash: options.borderDash,\n        borderDashOffset: options.borderDashOffset,\n        borderJoinStyle: options.borderJoinStyle,\n        borderWidth: options.borderWidth,\n        borderColor: options.borderColor\n    };\n}\nfunction styleChanged(style, prevStyle) {\n    if (!prevStyle) {\n        return false;\n    }\n    const cache = [];\n    const replacer = function(key, value) {\n        if (!isPatternOrGradient(value)) {\n            return value;\n        }\n        if (!cache.includes(value)) {\n            cache.push(value);\n        }\n        return cache.indexOf(value);\n    };\n    return JSON.stringify(style, replacer) !== JSON.stringify(prevStyle, replacer);\n}\n\nexport { unclipArea as $, _rlookupByKey as A, _lookupByKey as B, _isPointInArea as C, getAngleFromPoint as D, toPadding as E, each as F, getMaximumSize as G, HALF_PI as H, _getParentNode as I, readUsedSize as J, supportsEventListenerOptions as K, throttled as L, _isDomSupported as M, _factorize as N, finiteOrDefault as O, PI as P, callback as Q, _addGrace as R, _limitValue as S, TAU as T, toDegrees as U, _measureText as V, _int16Range as W, _alignPixel as X, clipArea as Y, renderText as Z, _arrayUnique as _, resolve as a, fontString as a$, toFont as a0, _toLeftRightCenter as a1, _alignStartEnd as a2, overrides as a3, merge as a4, _capitalize as a5, descriptors as a6, isFunction as a7, _attachContext as a8, _createResolver as a9, overrideTextDirection as aA, _textX as aB, restoreTextDirection as aC, drawPointLegend as aD, distanceBetweenPoints as aE, noop as aF, _setMinAndMaxByKey as aG, niceNum as aH, almostWhole as aI, almostEquals as aJ, _decimalPlaces as aK, Ticks as aL, log10 as aM, _longestText as aN, _filterBetween as aO, _lookup as aP, isPatternOrGradient as aQ, getHoverColor as aR, clone as aS, _merger as aT, _mergerIf as aU, _deprecated as aV, _splitKey as aW, toFontString as aX, splineCurve as aY, splineCurveMonotone as aZ, getStyle as a_, _descriptors as aa, mergeIf as ab, uid as ac, debounce as ad, retinaScale as ae, clearCanvas as af, setsEqual as ag, _elementsEqual as ah, _isClickEvent as ai, _isBetween as aj, _readValueToProps as ak, _updateBezierControlPoints as al, _computeSegments as am, _boundSegments as an, _steppedInterpolation as ao, _bezierInterpolation as ap, _pointInLine as aq, _steppedLineTo as ar, _bezierCurveTo as as, drawPoint as at, addRoundedRectPath as au, toTRBL as av, toTRBLCorners as aw, _boundSegment as ax, _normalizeAngle as ay, getRtlAdapter as az, isArray as b, toLineHeight as b0, PITAU as b1, INFINITY as b2, RAD_PER_DEG as b3, QUARTER_PI as b4, TWO_THIRDS_PI as b5, _angleDiff as b6, color as c, defaults as d, effects as e, resolveObjectKey as f, isNumberFinite as g, defined as h, isObject as i, createContext as j, isNullOrUndef as k, listenArrayEvents as l, toPercentage as m, toDimension as n, formatNumber as o, _angleBetween as p, _getStartAndCountOfVisiblePoints as q, requestAnimFrame as r, sign as s, toRadians as t, unlistenArrayEvents as u, valueOrDefault as v, _scaleRangesChanged as w, isNumber as x, _parseObjectDataRadialScale as y, getRelativePosition as z };\n//# sourceMappingURL=helpers.segment.js.map\n","/*!\n * Chart.js v4.4.2\n * https://www.chartjs.org\n * (c) 2024 Chart.js Contributors\n * Released under the MIT License\n */\nimport { r as requestAnimFrame, a as resolve, e as effects, c as color, i as isObject, d as defaults, b as isArray, v as valueOrDefault, u as unlistenArrayEvents, l as listenArrayEvents, f as resolveObjectKey, g as isNumberFinite, h as defined, s as sign, j as createContext, k as isNullOrUndef, _ as _arrayUnique, t as toRadians, m as toPercentage, n as toDimension, T as TAU, o as formatNumber, p as _angleBetween, H as HALF_PI, P as PI, q as _getStartAndCountOfVisiblePoints, w as _scaleRangesChanged, x as isNumber, y as _parseObjectDataRadialScale, z as getRelativePosition, A as _rlookupByKey, B as _lookupByKey, C as _isPointInArea, D as getAngleFromPoint, E as toPadding, F as each, G as getMaximumSize, I as _getParentNode, J as readUsedSize, K as supportsEventListenerOptions, L as throttled, M as _isDomSupported, N as _factorize, O as finiteOrDefault, Q as callback, R as _addGrace, S as _limitValue, U as toDegrees, V as _measureText, W as _int16Range, X as _alignPixel, Y as clipArea, Z as renderText, $ as unclipArea, a0 as toFont, a1 as _toLeftRightCenter, a2 as _alignStartEnd, a3 as overrides, a4 as merge, a5 as _capitalize, a6 as descriptors, a7 as isFunction, a8 as _attachContext, a9 as _createResolver, aa as _descriptors, ab as mergeIf, ac as uid, ad as debounce, ae as retinaScale, af as clearCanvas, ag as setsEqual, ah as _elementsEqual, ai as _isClickEvent, aj as _isBetween, ak as _readValueToProps, al as _updateBezierControlPoints, am as _computeSegments, an as _boundSegments, ao as _steppedInterpolation, ap as _bezierInterpolation, aq as _pointInLine, ar as _steppedLineTo, as as _bezierCurveTo, at as drawPoint, au as addRoundedRectPath, av as toTRBL, aw as toTRBLCorners, ax as _boundSegment, ay as _normalizeAngle, az as getRtlAdapter, aA as overrideTextDirection, aB as _textX, aC as restoreTextDirection, aD as drawPointLegend, aE as distanceBetweenPoints, aF as noop, aG as _setMinAndMaxByKey, aH as niceNum, aI as almostWhole, aJ as almostEquals, aK as _decimalPlaces, aL as Ticks, aM as log10, aN as _longestText, aO as _filterBetween, aP as _lookup } from './chunks/helpers.segment.js';\nimport '@kurkle/color';\n\nclass Animator {\n    constructor(){\n        this._request = null;\n        this._charts = new Map();\n        this._running = false;\n        this._lastDate = undefined;\n    }\n _notify(chart, anims, date, type) {\n        const callbacks = anims.listeners[type];\n        const numSteps = anims.duration;\n        callbacks.forEach((fn)=>fn({\n                chart,\n                initial: anims.initial,\n                numSteps,\n                currentStep: Math.min(date - anims.start, numSteps)\n            }));\n    }\n _refresh() {\n        if (this._request) {\n            return;\n        }\n        this._running = true;\n        this._request = requestAnimFrame.call(window, ()=>{\n            this._update();\n            this._request = null;\n            if (this._running) {\n                this._refresh();\n            }\n        });\n    }\n _update(date = Date.now()) {\n        let remaining = 0;\n        this._charts.forEach((anims, chart)=>{\n            if (!anims.running || !anims.items.length) {\n                return;\n            }\n            const items = anims.items;\n            let i = items.length - 1;\n            let draw = false;\n            let item;\n            for(; i >= 0; --i){\n                item = items[i];\n                if (item._active) {\n                    if (item._total > anims.duration) {\n                        anims.duration = item._total;\n                    }\n                    item.tick(date);\n                    draw = true;\n                } else {\n                    items[i] = items[items.length - 1];\n                    items.pop();\n                }\n            }\n            if (draw) {\n                chart.draw();\n                this._notify(chart, anims, date, 'progress');\n            }\n            if (!items.length) {\n                anims.running = false;\n                this._notify(chart, anims, date, 'complete');\n                anims.initial = false;\n            }\n            remaining += items.length;\n        });\n        this._lastDate = date;\n        if (remaining === 0) {\n            this._running = false;\n        }\n    }\n _getAnims(chart) {\n        const charts = this._charts;\n        let anims = charts.get(chart);\n        if (!anims) {\n            anims = {\n                running: false,\n                initial: true,\n                items: [],\n                listeners: {\n                    complete: [],\n                    progress: []\n                }\n            };\n            charts.set(chart, anims);\n        }\n        return anims;\n    }\n listen(chart, event, cb) {\n        this._getAnims(chart).listeners[event].push(cb);\n    }\n add(chart, items) {\n        if (!items || !items.length) {\n            return;\n        }\n        this._getAnims(chart).items.push(...items);\n    }\n has(chart) {\n        return this._getAnims(chart).items.length > 0;\n    }\n start(chart) {\n        const anims = this._charts.get(chart);\n        if (!anims) {\n            return;\n        }\n        anims.running = true;\n        anims.start = Date.now();\n        anims.duration = anims.items.reduce((acc, cur)=>Math.max(acc, cur._duration), 0);\n        this._refresh();\n    }\n    running(chart) {\n        if (!this._running) {\n            return false;\n        }\n        const anims = this._charts.get(chart);\n        if (!anims || !anims.running || !anims.items.length) {\n            return false;\n        }\n        return true;\n    }\n stop(chart) {\n        const anims = this._charts.get(chart);\n        if (!anims || !anims.items.length) {\n            return;\n        }\n        const items = anims.items;\n        let i = items.length - 1;\n        for(; i >= 0; --i){\n            items[i].cancel();\n        }\n        anims.items = [];\n        this._notify(chart, anims, Date.now(), 'complete');\n    }\n remove(chart) {\n        return this._charts.delete(chart);\n    }\n}\nvar animator = /* #__PURE__ */ new Animator();\n\nconst transparent = 'transparent';\nconst interpolators = {\n    boolean (from, to, factor) {\n        return factor > 0.5 ? to : from;\n    },\n color (from, to, factor) {\n        const c0 = color(from || transparent);\n        const c1 = c0.valid && color(to || transparent);\n        return c1 && c1.valid ? c1.mix(c0, factor).hexString() : to;\n    },\n    number (from, to, factor) {\n        return from + (to - from) * factor;\n    }\n};\nclass Animation {\n    constructor(cfg, target, prop, to){\n        const currentValue = target[prop];\n        to = resolve([\n            cfg.to,\n            to,\n            currentValue,\n            cfg.from\n        ]);\n        const from = resolve([\n            cfg.from,\n            currentValue,\n            to\n        ]);\n        this._active = true;\n        this._fn = cfg.fn || interpolators[cfg.type || typeof from];\n        this._easing = effects[cfg.easing] || effects.linear;\n        this._start = Math.floor(Date.now() + (cfg.delay || 0));\n        this._duration = this._total = Math.floor(cfg.duration);\n        this._loop = !!cfg.loop;\n        this._target = target;\n        this._prop = prop;\n        this._from = from;\n        this._to = to;\n        this._promises = undefined;\n    }\n    active() {\n        return this._active;\n    }\n    update(cfg, to, date) {\n        if (this._active) {\n            this._notify(false);\n            const currentValue = this._target[this._prop];\n            const elapsed = date - this._start;\n            const remain = this._duration - elapsed;\n            this._start = date;\n            this._duration = Math.floor(Math.max(remain, cfg.duration));\n            this._total += elapsed;\n            this._loop = !!cfg.loop;\n            this._to = resolve([\n                cfg.to,\n                to,\n                currentValue,\n                cfg.from\n            ]);\n            this._from = resolve([\n                cfg.from,\n                currentValue,\n                to\n            ]);\n        }\n    }\n    cancel() {\n        if (this._active) {\n            this.tick(Date.now());\n            this._active = false;\n            this._notify(false);\n        }\n    }\n    tick(date) {\n        const elapsed = date - this._start;\n        const duration = this._duration;\n        const prop = this._prop;\n        const from = this._from;\n        const loop = this._loop;\n        const to = this._to;\n        let factor;\n        this._active = from !== to && (loop || elapsed < duration);\n        if (!this._active) {\n            this._target[prop] = to;\n            this._notify(true);\n            return;\n        }\n        if (elapsed < 0) {\n            this._target[prop] = from;\n            return;\n        }\n        factor = elapsed / duration % 2;\n        factor = loop && factor > 1 ? 2 - factor : factor;\n        factor = this._easing(Math.min(1, Math.max(0, factor)));\n        this._target[prop] = this._fn(from, to, factor);\n    }\n    wait() {\n        const promises = this._promises || (this._promises = []);\n        return new Promise((res, rej)=>{\n            promises.push({\n                res,\n                rej\n            });\n        });\n    }\n    _notify(resolved) {\n        const method = resolved ? 'res' : 'rej';\n        const promises = this._promises || [];\n        for(let i = 0; i < promises.length; i++){\n            promises[i][method]();\n        }\n    }\n}\n\nclass Animations {\n    constructor(chart, config){\n        this._chart = chart;\n        this._properties = new Map();\n        this.configure(config);\n    }\n    configure(config) {\n        if (!isObject(config)) {\n            return;\n        }\n        const animationOptions = Object.keys(defaults.animation);\n        const animatedProps = this._properties;\n        Object.getOwnPropertyNames(config).forEach((key)=>{\n            const cfg = config[key];\n            if (!isObject(cfg)) {\n                return;\n            }\n            const resolved = {};\n            for (const option of animationOptions){\n                resolved[option] = cfg[option];\n            }\n            (isArray(cfg.properties) && cfg.properties || [\n                key\n            ]).forEach((prop)=>{\n                if (prop === key || !animatedProps.has(prop)) {\n                    animatedProps.set(prop, resolved);\n                }\n            });\n        });\n    }\n _animateOptions(target, values) {\n        const newOptions = values.options;\n        const options = resolveTargetOptions(target, newOptions);\n        if (!options) {\n            return [];\n        }\n        const animations = this._createAnimations(options, newOptions);\n        if (newOptions.$shared) {\n            awaitAll(target.options.$animations, newOptions).then(()=>{\n                target.options = newOptions;\n            }, ()=>{\n            });\n        }\n        return animations;\n    }\n _createAnimations(target, values) {\n        const animatedProps = this._properties;\n        const animations = [];\n        const running = target.$animations || (target.$animations = {});\n        const props = Object.keys(values);\n        const date = Date.now();\n        let i;\n        for(i = props.length - 1; i >= 0; --i){\n            const prop = props[i];\n            if (prop.charAt(0) === '$') {\n                continue;\n            }\n            if (prop === 'options') {\n                animations.push(...this._animateOptions(target, values));\n                continue;\n            }\n            const value = values[prop];\n            let animation = running[prop];\n            const cfg = animatedProps.get(prop);\n            if (animation) {\n                if (cfg && animation.active()) {\n                    animation.update(cfg, value, date);\n                    continue;\n                } else {\n                    animation.cancel();\n                }\n            }\n            if (!cfg || !cfg.duration) {\n                target[prop] = value;\n                continue;\n            }\n            running[prop] = animation = new Animation(cfg, target, prop, value);\n            animations.push(animation);\n        }\n        return animations;\n    }\n update(target, values) {\n        if (this._properties.size === 0) {\n            Object.assign(target, values);\n            return;\n        }\n        const animations = this._createAnimations(target, values);\n        if (animations.length) {\n            animator.add(this._chart, animations);\n            return true;\n        }\n    }\n}\nfunction awaitAll(animations, properties) {\n    const running = [];\n    const keys = Object.keys(properties);\n    for(let i = 0; i < keys.length; i++){\n        const anim = animations[keys[i]];\n        if (anim && anim.active()) {\n            running.push(anim.wait());\n        }\n    }\n    return Promise.all(running);\n}\nfunction resolveTargetOptions(target, newOptions) {\n    if (!newOptions) {\n        return;\n    }\n    let options = target.options;\n    if (!options) {\n        target.options = newOptions;\n        return;\n    }\n    if (options.$shared) {\n        target.options = options = Object.assign({}, options, {\n            $shared: false,\n            $animations: {}\n        });\n    }\n    return options;\n}\n\nfunction scaleClip(scale, allowedOverflow) {\n    const opts = scale && scale.options || {};\n    const reverse = opts.reverse;\n    const min = opts.min === undefined ? allowedOverflow : 0;\n    const max = opts.max === undefined ? allowedOverflow : 0;\n    return {\n        start: reverse ? max : min,\n        end: reverse ? min : max\n    };\n}\nfunction defaultClip(xScale, yScale, allowedOverflow) {\n    if (allowedOverflow === false) {\n        return false;\n    }\n    const x = scaleClip(xScale, allowedOverflow);\n    const y = scaleClip(yScale, allowedOverflow);\n    return {\n        top: y.end,\n        right: x.end,\n        bottom: y.start,\n        left: x.start\n    };\n}\nfunction toClip(value) {\n    let t, r, b, l;\n    if (isObject(value)) {\n        t = value.top;\n        r = value.right;\n        b = value.bottom;\n        l = value.left;\n    } else {\n        t = r = b = l = value;\n    }\n    return {\n        top: t,\n        right: r,\n        bottom: b,\n        left: l,\n        disabled: value === false\n    };\n}\nfunction getSortedDatasetIndices(chart, filterVisible) {\n    const keys = [];\n    const metasets = chart._getSortedDatasetMetas(filterVisible);\n    let i, ilen;\n    for(i = 0, ilen = metasets.length; i < ilen; ++i){\n        keys.push(metasets[i].index);\n    }\n    return keys;\n}\nfunction applyStack(stack, value, dsIndex, options = {}) {\n    const keys = stack.keys;\n    const singleMode = options.mode === 'single';\n    let i, ilen, datasetIndex, otherValue;\n    if (value === null) {\n        return;\n    }\n    for(i = 0, ilen = keys.length; i < ilen; ++i){\n        datasetIndex = +keys[i];\n        if (datasetIndex === dsIndex) {\n            if (options.all) {\n                continue;\n            }\n            break;\n        }\n        otherValue = stack.values[datasetIndex];\n        if (isNumberFinite(otherValue) && (singleMode || value === 0 || sign(value) === sign(otherValue))) {\n            value += otherValue;\n        }\n    }\n    return value;\n}\nfunction convertObjectDataToArray(data) {\n    const keys = Object.keys(data);\n    const adata = new Array(keys.length);\n    let i, ilen, key;\n    for(i = 0, ilen = keys.length; i < ilen; ++i){\n        key = keys[i];\n        adata[i] = {\n            x: key,\n            y: data[key]\n        };\n    }\n    return adata;\n}\nfunction isStacked(scale, meta) {\n    const stacked = scale && scale.options.stacked;\n    return stacked || stacked === undefined && meta.stack !== undefined;\n}\nfunction getStackKey(indexScale, valueScale, meta) {\n    return `${indexScale.id}.${valueScale.id}.${meta.stack || meta.type}`;\n}\nfunction getUserBounds(scale) {\n    const { min , max , minDefined , maxDefined  } = scale.getUserBounds();\n    return {\n        min: minDefined ? min : Number.NEGATIVE_INFINITY,\n        max: maxDefined ? max : Number.POSITIVE_INFINITY\n    };\n}\nfunction getOrCreateStack(stacks, stackKey, indexValue) {\n    const subStack = stacks[stackKey] || (stacks[stackKey] = {});\n    return subStack[indexValue] || (subStack[indexValue] = {});\n}\nfunction getLastIndexInStack(stack, vScale, positive, type) {\n    for (const meta of vScale.getMatchingVisibleMetas(type).reverse()){\n        const value = stack[meta.index];\n        if (positive && value > 0 || !positive && value < 0) {\n            return meta.index;\n        }\n    }\n    return null;\n}\nfunction updateStacks(controller, parsed) {\n    const { chart , _cachedMeta: meta  } = controller;\n    const stacks = chart._stacks || (chart._stacks = {});\n    const { iScale , vScale , index: datasetIndex  } = meta;\n    const iAxis = iScale.axis;\n    const vAxis = vScale.axis;\n    const key = getStackKey(iScale, vScale, meta);\n    const ilen = parsed.length;\n    let stack;\n    for(let i = 0; i < ilen; ++i){\n        const item = parsed[i];\n        const { [iAxis]: index , [vAxis]: value  } = item;\n        const itemStacks = item._stacks || (item._stacks = {});\n        stack = itemStacks[vAxis] = getOrCreateStack(stacks, key, index);\n        stack[datasetIndex] = value;\n        stack._top = getLastIndexInStack(stack, vScale, true, meta.type);\n        stack._bottom = getLastIndexInStack(stack, vScale, false, meta.type);\n        const visualValues = stack._visualValues || (stack._visualValues = {});\n        visualValues[datasetIndex] = value;\n    }\n}\nfunction getFirstScaleId(chart, axis) {\n    const scales = chart.scales;\n    return Object.keys(scales).filter((key)=>scales[key].axis === axis).shift();\n}\nfunction createDatasetContext(parent, index) {\n    return createContext(parent, {\n        active: false,\n        dataset: undefined,\n        datasetIndex: index,\n        index,\n        mode: 'default',\n        type: 'dataset'\n    });\n}\nfunction createDataContext(parent, index, element) {\n    return createContext(parent, {\n        active: false,\n        dataIndex: index,\n        parsed: undefined,\n        raw: undefined,\n        element,\n        index,\n        mode: 'default',\n        type: 'data'\n    });\n}\nfunction clearStacks(meta, items) {\n    const datasetIndex = meta.controller.index;\n    const axis = meta.vScale && meta.vScale.axis;\n    if (!axis) {\n        return;\n    }\n    items = items || meta._parsed;\n    for (const parsed of items){\n        const stacks = parsed._stacks;\n        if (!stacks || stacks[axis] === undefined || stacks[axis][datasetIndex] === undefined) {\n            return;\n        }\n        delete stacks[axis][datasetIndex];\n        if (stacks[axis]._visualValues !== undefined && stacks[axis]._visualValues[datasetIndex] !== undefined) {\n            delete stacks[axis]._visualValues[datasetIndex];\n        }\n    }\n}\nconst isDirectUpdateMode = (mode)=>mode === 'reset' || mode === 'none';\nconst cloneIfNotShared = (cached, shared)=>shared ? cached : Object.assign({}, cached);\nconst createStack = (canStack, meta, chart)=>canStack && !meta.hidden && meta._stacked && {\n        keys: getSortedDatasetIndices(chart, true),\n        values: null\n    };\nclass DatasetController {\n static defaults = {};\n static datasetElementType = null;\n static dataElementType = null;\n constructor(chart, datasetIndex){\n        this.chart = chart;\n        this._ctx = chart.ctx;\n        this.index = datasetIndex;\n        this._cachedDataOpts = {};\n        this._cachedMeta = this.getMeta();\n        this._type = this._cachedMeta.type;\n        this.options = undefined;\n         this._parsing = false;\n        this._data = undefined;\n        this._objectData = undefined;\n        this._sharedOptions = undefined;\n        this._drawStart = undefined;\n        this._drawCount = undefined;\n        this.enableOptionSharing = false;\n        this.supportsDecimation = false;\n        this.$context = undefined;\n        this._syncList = [];\n        this.datasetElementType = new.target.datasetElementType;\n        this.dataElementType = new.target.dataElementType;\n        this.initialize();\n    }\n    initialize() {\n        const meta = this._cachedMeta;\n        this.configure();\n        this.linkScales();\n        meta._stacked = isStacked(meta.vScale, meta);\n        this.addElements();\n        if (this.options.fill && !this.chart.isPluginEnabled('filler')) {\n            console.warn(\"Tried to use the 'fill' option without the 'Filler' plugin enabled. Please import and register the 'Filler' plugin and make sure it is not disabled in the options\");\n        }\n    }\n    updateIndex(datasetIndex) {\n        if (this.index !== datasetIndex) {\n            clearStacks(this._cachedMeta);\n        }\n        this.index = datasetIndex;\n    }\n    linkScales() {\n        const chart = this.chart;\n        const meta = this._cachedMeta;\n        const dataset = this.getDataset();\n        const chooseId = (axis, x, y, r)=>axis === 'x' ? x : axis === 'r' ? r : y;\n        const xid = meta.xAxisID = valueOrDefault(dataset.xAxisID, getFirstScaleId(chart, 'x'));\n        const yid = meta.yAxisID = valueOrDefault(dataset.yAxisID, getFirstScaleId(chart, 'y'));\n        const rid = meta.rAxisID = valueOrDefault(dataset.rAxisID, getFirstScaleId(chart, 'r'));\n        const indexAxis = meta.indexAxis;\n        const iid = meta.iAxisID = chooseId(indexAxis, xid, yid, rid);\n        const vid = meta.vAxisID = chooseId(indexAxis, yid, xid, rid);\n        meta.xScale = this.getScaleForId(xid);\n        meta.yScale = this.getScaleForId(yid);\n        meta.rScale = this.getScaleForId(rid);\n        meta.iScale = this.getScaleForId(iid);\n        meta.vScale = this.getScaleForId(vid);\n    }\n    getDataset() {\n        return this.chart.data.datasets[this.index];\n    }\n    getMeta() {\n        return this.chart.getDatasetMeta(this.index);\n    }\n getScaleForId(scaleID) {\n        return this.chart.scales[scaleID];\n    }\n _getOtherScale(scale) {\n        const meta = this._cachedMeta;\n        return scale === meta.iScale ? meta.vScale : meta.iScale;\n    }\n    reset() {\n        this._update('reset');\n    }\n _destroy() {\n        const meta = this._cachedMeta;\n        if (this._data) {\n            unlistenArrayEvents(this._data, this);\n        }\n        if (meta._stacked) {\n            clearStacks(meta);\n        }\n    }\n _dataCheck() {\n        const dataset = this.getDataset();\n        const data = dataset.data || (dataset.data = []);\n        const _data = this._data;\n        if (isObject(data)) {\n            this._data = convertObjectDataToArray(data);\n        } else if (_data !== data) {\n            if (_data) {\n                unlistenArrayEvents(_data, this);\n                const meta = this._cachedMeta;\n                clearStacks(meta);\n                meta._parsed = [];\n            }\n            if (data && Object.isExtensible(data)) {\n                listenArrayEvents(data, this);\n            }\n            this._syncList = [];\n            this._data = data;\n        }\n    }\n    addElements() {\n        const meta = this._cachedMeta;\n        this._dataCheck();\n        if (this.datasetElementType) {\n            meta.dataset = new this.datasetElementType();\n        }\n    }\n    buildOrUpdateElements(resetNewElements) {\n        const meta = this._cachedMeta;\n        const dataset = this.getDataset();\n        let stackChanged = false;\n        this._dataCheck();\n        const oldStacked = meta._stacked;\n        meta._stacked = isStacked(meta.vScale, meta);\n        if (meta.stack !== dataset.stack) {\n            stackChanged = true;\n            clearStacks(meta);\n            meta.stack = dataset.stack;\n        }\n        this._resyncElements(resetNewElements);\n        if (stackChanged || oldStacked !== meta._stacked) {\n            updateStacks(this, meta._parsed);\n        }\n    }\n configure() {\n        const config = this.chart.config;\n        const scopeKeys = config.datasetScopeKeys(this._type);\n        const scopes = config.getOptionScopes(this.getDataset(), scopeKeys, true);\n        this.options = config.createResolver(scopes, this.getContext());\n        this._parsing = this.options.parsing;\n        this._cachedDataOpts = {};\n    }\n parse(start, count) {\n        const { _cachedMeta: meta , _data: data  } = this;\n        const { iScale , _stacked  } = meta;\n        const iAxis = iScale.axis;\n        let sorted = start === 0 && count === data.length ? true : meta._sorted;\n        let prev = start > 0 && meta._parsed[start - 1];\n        let i, cur, parsed;\n        if (this._parsing === false) {\n            meta._parsed = data;\n            meta._sorted = true;\n            parsed = data;\n        } else {\n            if (isArray(data[start])) {\n                parsed = this.parseArrayData(meta, data, start, count);\n            } else if (isObject(data[start])) {\n                parsed = this.parseObjectData(meta, data, start, count);\n            } else {\n                parsed = this.parsePrimitiveData(meta, data, start, count);\n            }\n            const isNotInOrderComparedToPrev = ()=>cur[iAxis] === null || prev && cur[iAxis] < prev[iAxis];\n            for(i = 0; i < count; ++i){\n                meta._parsed[i + start] = cur = parsed[i];\n                if (sorted) {\n                    if (isNotInOrderComparedToPrev()) {\n                        sorted = false;\n                    }\n                    prev = cur;\n                }\n            }\n            meta._sorted = sorted;\n        }\n        if (_stacked) {\n            updateStacks(this, parsed);\n        }\n    }\n parsePrimitiveData(meta, data, start, count) {\n        const { iScale , vScale  } = meta;\n        const iAxis = iScale.axis;\n        const vAxis = vScale.axis;\n        const labels = iScale.getLabels();\n        const singleScale = iScale === vScale;\n        const parsed = new Array(count);\n        let i, ilen, index;\n        for(i = 0, ilen = count; i < ilen; ++i){\n            index = i + start;\n            parsed[i] = {\n                [iAxis]: singleScale || iScale.parse(labels[index], index),\n                [vAxis]: vScale.parse(data[index], index)\n            };\n        }\n        return parsed;\n    }\n parseArrayData(meta, data, start, count) {\n        const { xScale , yScale  } = meta;\n        const parsed = new Array(count);\n        let i, ilen, index, item;\n        for(i = 0, ilen = count; i < ilen; ++i){\n            index = i + start;\n            item = data[index];\n            parsed[i] = {\n                x: xScale.parse(item[0], index),\n                y: yScale.parse(item[1], index)\n            };\n        }\n        return parsed;\n    }\n parseObjectData(meta, data, start, count) {\n        const { xScale , yScale  } = meta;\n        const { xAxisKey ='x' , yAxisKey ='y'  } = this._parsing;\n        const parsed = new Array(count);\n        let i, ilen, index, item;\n        for(i = 0, ilen = count; i < ilen; ++i){\n            index = i + start;\n            item = data[index];\n            parsed[i] = {\n                x: xScale.parse(resolveObjectKey(item, xAxisKey), index),\n                y: yScale.parse(resolveObjectKey(item, yAxisKey), index)\n            };\n        }\n        return parsed;\n    }\n getParsed(index) {\n        return this._cachedMeta._parsed[index];\n    }\n getDataElement(index) {\n        return this._cachedMeta.data[index];\n    }\n applyStack(scale, parsed, mode) {\n        const chart = this.chart;\n        const meta = this._cachedMeta;\n        const value = parsed[scale.axis];\n        const stack = {\n            keys: getSortedDatasetIndices(chart, true),\n            values: parsed._stacks[scale.axis]._visualValues\n        };\n        return applyStack(stack, value, meta.index, {\n            mode\n        });\n    }\n updateRangeFromParsed(range, scale, parsed, stack) {\n        const parsedValue = parsed[scale.axis];\n        let value = parsedValue === null ? NaN : parsedValue;\n        const values = stack && parsed._stacks[scale.axis];\n        if (stack && values) {\n            stack.values = values;\n            value = applyStack(stack, parsedValue, this._cachedMeta.index);\n        }\n        range.min = Math.min(range.min, value);\n        range.max = Math.max(range.max, value);\n    }\n getMinMax(scale, canStack) {\n        const meta = this._cachedMeta;\n        const _parsed = meta._parsed;\n        const sorted = meta._sorted && scale === meta.iScale;\n        const ilen = _parsed.length;\n        const otherScale = this._getOtherScale(scale);\n        const stack = createStack(canStack, meta, this.chart);\n        const range = {\n            min: Number.POSITIVE_INFINITY,\n            max: Number.NEGATIVE_INFINITY\n        };\n        const { min: otherMin , max: otherMax  } = getUserBounds(otherScale);\n        let i, parsed;\n        function _skip() {\n            parsed = _parsed[i];\n            const otherValue = parsed[otherScale.axis];\n            return !isNumberFinite(parsed[scale.axis]) || otherMin > otherValue || otherMax < otherValue;\n        }\n        for(i = 0; i < ilen; ++i){\n            if (_skip()) {\n                continue;\n            }\n            this.updateRangeFromParsed(range, scale, parsed, stack);\n            if (sorted) {\n                break;\n            }\n        }\n        if (sorted) {\n            for(i = ilen - 1; i >= 0; --i){\n                if (_skip()) {\n                    continue;\n                }\n                this.updateRangeFromParsed(range, scale, parsed, stack);\n                break;\n            }\n        }\n        return range;\n    }\n    getAllParsedValues(scale) {\n        const parsed = this._cachedMeta._parsed;\n        const values = [];\n        let i, ilen, value;\n        for(i = 0, ilen = parsed.length; i < ilen; ++i){\n            value = parsed[i][scale.axis];\n            if (isNumberFinite(value)) {\n                values.push(value);\n            }\n        }\n        return values;\n    }\n getMaxOverflow() {\n        return false;\n    }\n getLabelAndValue(index) {\n        const meta = this._cachedMeta;\n        const iScale = meta.iScale;\n        const vScale = meta.vScale;\n        const parsed = this.getParsed(index);\n        return {\n            label: iScale ? '' + iScale.getLabelForValue(parsed[iScale.axis]) : '',\n            value: vScale ? '' + vScale.getLabelForValue(parsed[vScale.axis]) : ''\n        };\n    }\n _update(mode) {\n        const meta = this._cachedMeta;\n        this.update(mode || 'default');\n        meta._clip = toClip(valueOrDefault(this.options.clip, defaultClip(meta.xScale, meta.yScale, this.getMaxOverflow())));\n    }\n update(mode) {}\n    draw() {\n        const ctx = this._ctx;\n        const chart = this.chart;\n        const meta = this._cachedMeta;\n        const elements = meta.data || [];\n        const area = chart.chartArea;\n        const active = [];\n        const start = this._drawStart || 0;\n        const count = this._drawCount || elements.length - start;\n        const drawActiveElementsOnTop = this.options.drawActiveElementsOnTop;\n        let i;\n        if (meta.dataset) {\n            meta.dataset.draw(ctx, area, start, count);\n        }\n        for(i = start; i < start + count; ++i){\n            const element = elements[i];\n            if (element.hidden) {\n                continue;\n            }\n            if (element.active && drawActiveElementsOnTop) {\n                active.push(element);\n            } else {\n                element.draw(ctx, area);\n            }\n        }\n        for(i = 0; i < active.length; ++i){\n            active[i].draw(ctx, area);\n        }\n    }\n getStyle(index, active) {\n        const mode = active ? 'active' : 'default';\n        return index === undefined && this._cachedMeta.dataset ? this.resolveDatasetElementOptions(mode) : this.resolveDataElementOptions(index || 0, mode);\n    }\n getContext(index, active, mode) {\n        const dataset = this.getDataset();\n        let context;\n        if (index >= 0 && index < this._cachedMeta.data.length) {\n            const element = this._cachedMeta.data[index];\n            context = element.$context || (element.$context = createDataContext(this.getContext(), index, element));\n            context.parsed = this.getParsed(index);\n            context.raw = dataset.data[index];\n            context.index = context.dataIndex = index;\n        } else {\n            context = this.$context || (this.$context = createDatasetContext(this.chart.getContext(), this.index));\n            context.dataset = dataset;\n            context.index = context.datasetIndex = this.index;\n        }\n        context.active = !!active;\n        context.mode = mode;\n        return context;\n    }\n resolveDatasetElementOptions(mode) {\n        return this._resolveElementOptions(this.datasetElementType.id, mode);\n    }\n resolveDataElementOptions(index, mode) {\n        return this._resolveElementOptions(this.dataElementType.id, mode, index);\n    }\n _resolveElementOptions(elementType, mode = 'default', index) {\n        const active = mode === 'active';\n        const cache = this._cachedDataOpts;\n        const cacheKey = elementType + '-' + mode;\n        const cached = cache[cacheKey];\n        const sharing = this.enableOptionSharing && defined(index);\n        if (cached) {\n            return cloneIfNotShared(cached, sharing);\n        }\n        const config = this.chart.config;\n        const scopeKeys = config.datasetElementScopeKeys(this._type, elementType);\n        const prefixes = active ? [\n            `${elementType}Hover`,\n            'hover',\n            elementType,\n            ''\n        ] : [\n            elementType,\n            ''\n        ];\n        const scopes = config.getOptionScopes(this.getDataset(), scopeKeys);\n        const names = Object.keys(defaults.elements[elementType]);\n        const context = ()=>this.getContext(index, active, mode);\n        const values = config.resolveNamedOptions(scopes, names, context, prefixes);\n        if (values.$shared) {\n            values.$shared = sharing;\n            cache[cacheKey] = Object.freeze(cloneIfNotShared(values, sharing));\n        }\n        return values;\n    }\n _resolveAnimations(index, transition, active) {\n        const chart = this.chart;\n        const cache = this._cachedDataOpts;\n        const cacheKey = `animation-${transition}`;\n        const cached = cache[cacheKey];\n        if (cached) {\n            return cached;\n        }\n        let options;\n        if (chart.options.animation !== false) {\n            const config = this.chart.config;\n            const scopeKeys = config.datasetAnimationScopeKeys(this._type, transition);\n            const scopes = config.getOptionScopes(this.getDataset(), scopeKeys);\n            options = config.createResolver(scopes, this.getContext(index, active, transition));\n        }\n        const animations = new Animations(chart, options && options.animations);\n        if (options && options._cacheable) {\n            cache[cacheKey] = Object.freeze(animations);\n        }\n        return animations;\n    }\n getSharedOptions(options) {\n        if (!options.$shared) {\n            return;\n        }\n        return this._sharedOptions || (this._sharedOptions = Object.assign({}, options));\n    }\n includeOptions(mode, sharedOptions) {\n        return !sharedOptions || isDirectUpdateMode(mode) || this.chart._animationsDisabled;\n    }\n _getSharedOptions(start, mode) {\n        const firstOpts = this.resolveDataElementOptions(start, mode);\n        const previouslySharedOptions = this._sharedOptions;\n        const sharedOptions = this.getSharedOptions(firstOpts);\n        const includeOptions = this.includeOptions(mode, sharedOptions) || sharedOptions !== previouslySharedOptions;\n        this.updateSharedOptions(sharedOptions, mode, firstOpts);\n        return {\n            sharedOptions,\n            includeOptions\n        };\n    }\n updateElement(element, index, properties, mode) {\n        if (isDirectUpdateMode(mode)) {\n            Object.assign(element, properties);\n        } else {\n            this._resolveAnimations(index, mode).update(element, properties);\n        }\n    }\n updateSharedOptions(sharedOptions, mode, newOptions) {\n        if (sharedOptions && !isDirectUpdateMode(mode)) {\n            this._resolveAnimations(undefined, mode).update(sharedOptions, newOptions);\n        }\n    }\n _setStyle(element, index, mode, active) {\n        element.active = active;\n        const options = this.getStyle(index, active);\n        this._resolveAnimations(index, mode, active).update(element, {\n            options: !active && this.getSharedOptions(options) || options\n        });\n    }\n    removeHoverStyle(element, datasetIndex, index) {\n        this._setStyle(element, index, 'active', false);\n    }\n    setHoverStyle(element, datasetIndex, index) {\n        this._setStyle(element, index, 'active', true);\n    }\n _removeDatasetHoverStyle() {\n        const element = this._cachedMeta.dataset;\n        if (element) {\n            this._setStyle(element, undefined, 'active', false);\n        }\n    }\n _setDatasetHoverStyle() {\n        const element = this._cachedMeta.dataset;\n        if (element) {\n            this._setStyle(element, undefined, 'active', true);\n        }\n    }\n _resyncElements(resetNewElements) {\n        const data = this._data;\n        const elements = this._cachedMeta.data;\n        for (const [method, arg1, arg2] of this._syncList){\n            this[method](arg1, arg2);\n        }\n        this._syncList = [];\n        const numMeta = elements.length;\n        const numData = data.length;\n        const count = Math.min(numData, numMeta);\n        if (count) {\n            this.parse(0, count);\n        }\n        if (numData > numMeta) {\n            this._insertElements(numMeta, numData - numMeta, resetNewElements);\n        } else if (numData < numMeta) {\n            this._removeElements(numData, numMeta - numData);\n        }\n    }\n _insertElements(start, count, resetNewElements = true) {\n        const meta = this._cachedMeta;\n        const data = meta.data;\n        const end = start + count;\n        let i;\n        const move = (arr)=>{\n            arr.length += count;\n            for(i = arr.length - 1; i >= end; i--){\n                arr[i] = arr[i - count];\n            }\n        };\n        move(data);\n        for(i = start; i < end; ++i){\n            data[i] = new this.dataElementType();\n        }\n        if (this._parsing) {\n            move(meta._parsed);\n        }\n        this.parse(start, count);\n        if (resetNewElements) {\n            this.updateElements(data, start, count, 'reset');\n        }\n    }\n    updateElements(element, start, count, mode) {}\n _removeElements(start, count) {\n        const meta = this._cachedMeta;\n        if (this._parsing) {\n            const removed = meta._parsed.splice(start, count);\n            if (meta._stacked) {\n                clearStacks(meta, removed);\n            }\n        }\n        meta.data.splice(start, count);\n    }\n _sync(args) {\n        if (this._parsing) {\n            this._syncList.push(args);\n        } else {\n            const [method, arg1, arg2] = args;\n            this[method](arg1, arg2);\n        }\n        this.chart._dataChanges.push([\n            this.index,\n            ...args\n        ]);\n    }\n    _onDataPush() {\n        const count = arguments.length;\n        this._sync([\n            '_insertElements',\n            this.getDataset().data.length - count,\n            count\n        ]);\n    }\n    _onDataPop() {\n        this._sync([\n            '_removeElements',\n            this._cachedMeta.data.length - 1,\n            1\n        ]);\n    }\n    _onDataShift() {\n        this._sync([\n            '_removeElements',\n            0,\n            1\n        ]);\n    }\n    _onDataSplice(start, count) {\n        if (count) {\n            this._sync([\n                '_removeElements',\n                start,\n                count\n            ]);\n        }\n        const newCount = arguments.length - 2;\n        if (newCount) {\n            this._sync([\n                '_insertElements',\n                start,\n                newCount\n            ]);\n        }\n    }\n    _onDataUnshift() {\n        this._sync([\n            '_insertElements',\n            0,\n            arguments.length\n        ]);\n    }\n}\n\nfunction getAllScaleValues(scale, type) {\n    if (!scale._cache.$bar) {\n        const visibleMetas = scale.getMatchingVisibleMetas(type);\n        let values = [];\n        for(let i = 0, ilen = visibleMetas.length; i < ilen; i++){\n            values = values.concat(visibleMetas[i].controller.getAllParsedValues(scale));\n        }\n        scale._cache.$bar = _arrayUnique(values.sort((a, b)=>a - b));\n    }\n    return scale._cache.$bar;\n}\n function computeMinSampleSize(meta) {\n    const scale = meta.iScale;\n    const values = getAllScaleValues(scale, meta.type);\n    let min = scale._length;\n    let i, ilen, curr, prev;\n    const updateMinAndPrev = ()=>{\n        if (curr === 32767 || curr === -32768) {\n            return;\n        }\n        if (defined(prev)) {\n            min = Math.min(min, Math.abs(curr - prev) || min);\n        }\n        prev = curr;\n    };\n    for(i = 0, ilen = values.length; i < ilen; ++i){\n        curr = scale.getPixelForValue(values[i]);\n        updateMinAndPrev();\n    }\n    prev = undefined;\n    for(i = 0, ilen = scale.ticks.length; i < ilen; ++i){\n        curr = scale.getPixelForTick(i);\n        updateMinAndPrev();\n    }\n    return min;\n}\n function computeFitCategoryTraits(index, ruler, options, stackCount) {\n    const thickness = options.barThickness;\n    let size, ratio;\n    if (isNullOrUndef(thickness)) {\n        size = ruler.min * options.categoryPercentage;\n        ratio = options.barPercentage;\n    } else {\n        size = thickness * stackCount;\n        ratio = 1;\n    }\n    return {\n        chunk: size / stackCount,\n        ratio,\n        start: ruler.pixels[index] - size / 2\n    };\n}\n function computeFlexCategoryTraits(index, ruler, options, stackCount) {\n    const pixels = ruler.pixels;\n    const curr = pixels[index];\n    let prev = index > 0 ? pixels[index - 1] : null;\n    let next = index < pixels.length - 1 ? pixels[index + 1] : null;\n    const percent = options.categoryPercentage;\n    if (prev === null) {\n        prev = curr - (next === null ? ruler.end - ruler.start : next - curr);\n    }\n    if (next === null) {\n        next = curr + curr - prev;\n    }\n    const start = curr - (curr - Math.min(prev, next)) / 2 * percent;\n    const size = Math.abs(next - prev) / 2 * percent;\n    return {\n        chunk: size / stackCount,\n        ratio: options.barPercentage,\n        start\n    };\n}\nfunction parseFloatBar(entry, item, vScale, i) {\n    const startValue = vScale.parse(entry[0], i);\n    const endValue = vScale.parse(entry[1], i);\n    const min = Math.min(startValue, endValue);\n    const max = Math.max(startValue, endValue);\n    let barStart = min;\n    let barEnd = max;\n    if (Math.abs(min) > Math.abs(max)) {\n        barStart = max;\n        barEnd = min;\n    }\n    item[vScale.axis] = barEnd;\n    item._custom = {\n        barStart,\n        barEnd,\n        start: startValue,\n        end: endValue,\n        min,\n        max\n    };\n}\nfunction parseValue(entry, item, vScale, i) {\n    if (isArray(entry)) {\n        parseFloatBar(entry, item, vScale, i);\n    } else {\n        item[vScale.axis] = vScale.parse(entry, i);\n    }\n    return item;\n}\nfunction parseArrayOrPrimitive(meta, data, start, count) {\n    const iScale = meta.iScale;\n    const vScale = meta.vScale;\n    const labels = iScale.getLabels();\n    const singleScale = iScale === vScale;\n    const parsed = [];\n    let i, ilen, item, entry;\n    for(i = start, ilen = start + count; i < ilen; ++i){\n        entry = data[i];\n        item = {};\n        item[iScale.axis] = singleScale || iScale.parse(labels[i], i);\n        parsed.push(parseValue(entry, item, vScale, i));\n    }\n    return parsed;\n}\nfunction isFloatBar(custom) {\n    return custom && custom.barStart !== undefined && custom.barEnd !== undefined;\n}\nfunction barSign(size, vScale, actualBase) {\n    if (size !== 0) {\n        return sign(size);\n    }\n    return (vScale.isHorizontal() ? 1 : -1) * (vScale.min >= actualBase ? 1 : -1);\n}\nfunction borderProps(properties) {\n    let reverse, start, end, top, bottom;\n    if (properties.horizontal) {\n        reverse = properties.base > properties.x;\n        start = 'left';\n        end = 'right';\n    } else {\n        reverse = properties.base < properties.y;\n        start = 'bottom';\n        end = 'top';\n    }\n    if (reverse) {\n        top = 'end';\n        bottom = 'start';\n    } else {\n        top = 'start';\n        bottom = 'end';\n    }\n    return {\n        start,\n        end,\n        reverse,\n        top,\n        bottom\n    };\n}\nfunction setBorderSkipped(properties, options, stack, index) {\n    let edge = options.borderSkipped;\n    const res = {};\n    if (!edge) {\n        properties.borderSkipped = res;\n        return;\n    }\n    if (edge === true) {\n        properties.borderSkipped = {\n            top: true,\n            right: true,\n            bottom: true,\n            left: true\n        };\n        return;\n    }\n    const { start , end , reverse , top , bottom  } = borderProps(properties);\n    if (edge === 'middle' && stack) {\n        properties.enableBorderRadius = true;\n        if ((stack._top || 0) === index) {\n            edge = top;\n        } else if ((stack._bottom || 0) === index) {\n            edge = bottom;\n        } else {\n            res[parseEdge(bottom, start, end, reverse)] = true;\n            edge = top;\n        }\n    }\n    res[parseEdge(edge, start, end, reverse)] = true;\n    properties.borderSkipped = res;\n}\nfunction parseEdge(edge, a, b, reverse) {\n    if (reverse) {\n        edge = swap(edge, a, b);\n        edge = startEnd(edge, b, a);\n    } else {\n        edge = startEnd(edge, a, b);\n    }\n    return edge;\n}\nfunction swap(orig, v1, v2) {\n    return orig === v1 ? v2 : orig === v2 ? v1 : orig;\n}\nfunction startEnd(v, start, end) {\n    return v === 'start' ? start : v === 'end' ? end : v;\n}\nfunction setInflateAmount(properties, { inflateAmount  }, ratio) {\n    properties.inflateAmount = inflateAmount === 'auto' ? ratio === 1 ? 0.33 : 0 : inflateAmount;\n}\nclass BarController extends DatasetController {\n    static id = 'bar';\n static defaults = {\n        datasetElementType: false,\n        dataElementType: 'bar',\n        categoryPercentage: 0.8,\n        barPercentage: 0.9,\n        grouped: true,\n        animations: {\n            numbers: {\n                type: 'number',\n                properties: [\n                    'x',\n                    'y',\n                    'base',\n                    'width',\n                    'height'\n                ]\n            }\n        }\n    };\n static overrides = {\n        scales: {\n            _index_: {\n                type: 'category',\n                offset: true,\n                grid: {\n                    offset: true\n                }\n            },\n            _value_: {\n                type: 'linear',\n                beginAtZero: true\n            }\n        }\n    };\n parsePrimitiveData(meta, data, start, count) {\n        return parseArrayOrPrimitive(meta, data, start, count);\n    }\n parseArrayData(meta, data, start, count) {\n        return parseArrayOrPrimitive(meta, data, start, count);\n    }\n parseObjectData(meta, data, start, count) {\n        const { iScale , vScale  } = meta;\n        const { xAxisKey ='x' , yAxisKey ='y'  } = this._parsing;\n        const iAxisKey = iScale.axis === 'x' ? xAxisKey : yAxisKey;\n        const vAxisKey = vScale.axis === 'x' ? xAxisKey : yAxisKey;\n        const parsed = [];\n        let i, ilen, item, obj;\n        for(i = start, ilen = start + count; i < ilen; ++i){\n            obj = data[i];\n            item = {};\n            item[iScale.axis] = iScale.parse(resolveObjectKey(obj, iAxisKey), i);\n            parsed.push(parseValue(resolveObjectKey(obj, vAxisKey), item, vScale, i));\n        }\n        return parsed;\n    }\n updateRangeFromParsed(range, scale, parsed, stack) {\n        super.updateRangeFromParsed(range, scale, parsed, stack);\n        const custom = parsed._custom;\n        if (custom && scale === this._cachedMeta.vScale) {\n            range.min = Math.min(range.min, custom.min);\n            range.max = Math.max(range.max, custom.max);\n        }\n    }\n getMaxOverflow() {\n        return 0;\n    }\n getLabelAndValue(index) {\n        const meta = this._cachedMeta;\n        const { iScale , vScale  } = meta;\n        const parsed = this.getParsed(index);\n        const custom = parsed._custom;\n        const value = isFloatBar(custom) ? '[' + custom.start + ', ' + custom.end + ']' : '' + vScale.getLabelForValue(parsed[vScale.axis]);\n        return {\n            label: '' + iScale.getLabelForValue(parsed[iScale.axis]),\n            value\n        };\n    }\n    initialize() {\n        this.enableOptionSharing = true;\n        super.initialize();\n        const meta = this._cachedMeta;\n        meta.stack = this.getDataset().stack;\n    }\n    update(mode) {\n        const meta = this._cachedMeta;\n        this.updateElements(meta.data, 0, meta.data.length, mode);\n    }\n    updateElements(bars, start, count, mode) {\n        const reset = mode === 'reset';\n        const { index , _cachedMeta: { vScale  }  } = this;\n        const base = vScale.getBasePixel();\n        const horizontal = vScale.isHorizontal();\n        const ruler = this._getRuler();\n        const { sharedOptions , includeOptions  } = this._getSharedOptions(start, mode);\n        for(let i = start; i < start + count; i++){\n            const parsed = this.getParsed(i);\n            const vpixels = reset || isNullOrUndef(parsed[vScale.axis]) ? {\n                base,\n                head: base\n            } : this._calculateBarValuePixels(i);\n            const ipixels = this._calculateBarIndexPixels(i, ruler);\n            const stack = (parsed._stacks || {})[vScale.axis];\n            const properties = {\n                horizontal,\n                base: vpixels.base,\n                enableBorderRadius: !stack || isFloatBar(parsed._custom) || index === stack._top || index === stack._bottom,\n                x: horizontal ? vpixels.head : ipixels.center,\n                y: horizontal ? ipixels.center : vpixels.head,\n                height: horizontal ? ipixels.size : Math.abs(vpixels.size),\n                width: horizontal ? Math.abs(vpixels.size) : ipixels.size\n            };\n            if (includeOptions) {\n                properties.options = sharedOptions || this.resolveDataElementOptions(i, bars[i].active ? 'active' : mode);\n            }\n            const options = properties.options || bars[i].options;\n            setBorderSkipped(properties, options, stack, index);\n            setInflateAmount(properties, options, ruler.ratio);\n            this.updateElement(bars[i], i, properties, mode);\n        }\n    }\n _getStacks(last, dataIndex) {\n        const { iScale  } = this._cachedMeta;\n        const metasets = iScale.getMatchingVisibleMetas(this._type).filter((meta)=>meta.controller.options.grouped);\n        const stacked = iScale.options.stacked;\n        const stacks = [];\n        const skipNull = (meta)=>{\n            const parsed = meta.controller.getParsed(dataIndex);\n            const val = parsed && parsed[meta.vScale.axis];\n            if (isNullOrUndef(val) || isNaN(val)) {\n                return true;\n            }\n        };\n        for (const meta of metasets){\n            if (dataIndex !== undefined && skipNull(meta)) {\n                continue;\n            }\n            if (stacked === false || stacks.indexOf(meta.stack) === -1 || stacked === undefined && meta.stack === undefined) {\n                stacks.push(meta.stack);\n            }\n            if (meta.index === last) {\n                break;\n            }\n        }\n        if (!stacks.length) {\n            stacks.push(undefined);\n        }\n        return stacks;\n    }\n _getStackCount(index) {\n        return this._getStacks(undefined, index).length;\n    }\n _getStackIndex(datasetIndex, name, dataIndex) {\n        const stacks = this._getStacks(datasetIndex, dataIndex);\n        const index = name !== undefined ? stacks.indexOf(name) : -1;\n        return index === -1 ? stacks.length - 1 : index;\n    }\n _getRuler() {\n        const opts = this.options;\n        const meta = this._cachedMeta;\n        const iScale = meta.iScale;\n        const pixels = [];\n        let i, ilen;\n        for(i = 0, ilen = meta.data.length; i < ilen; ++i){\n            pixels.push(iScale.getPixelForValue(this.getParsed(i)[iScale.axis], i));\n        }\n        const barThickness = opts.barThickness;\n        const min = barThickness || computeMinSampleSize(meta);\n        return {\n            min,\n            pixels,\n            start: iScale._startPixel,\n            end: iScale._endPixel,\n            stackCount: this._getStackCount(),\n            scale: iScale,\n            grouped: opts.grouped,\n            ratio: barThickness ? 1 : opts.categoryPercentage * opts.barPercentage\n        };\n    }\n _calculateBarValuePixels(index) {\n        const { _cachedMeta: { vScale , _stacked , index: datasetIndex  } , options: { base: baseValue , minBarLength  }  } = this;\n        const actualBase = baseValue || 0;\n        const parsed = this.getParsed(index);\n        const custom = parsed._custom;\n        const floating = isFloatBar(custom);\n        let value = parsed[vScale.axis];\n        let start = 0;\n        let length = _stacked ? this.applyStack(vScale, parsed, _stacked) : value;\n        let head, size;\n        if (length !== value) {\n            start = length - value;\n            length = value;\n        }\n        if (floating) {\n            value = custom.barStart;\n            length = custom.barEnd - custom.barStart;\n            if (value !== 0 && sign(value) !== sign(custom.barEnd)) {\n                start = 0;\n            }\n            start += value;\n        }\n        const startValue = !isNullOrUndef(baseValue) && !floating ? baseValue : start;\n        let base = vScale.getPixelForValue(startValue);\n        if (this.chart.getDataVisibility(index)) {\n            head = vScale.getPixelForValue(start + length);\n        } else {\n            head = base;\n        }\n        size = head - base;\n        if (Math.abs(size) < minBarLength) {\n            size = barSign(size, vScale, actualBase) * minBarLength;\n            if (value === actualBase) {\n                base -= size / 2;\n            }\n            const startPixel = vScale.getPixelForDecimal(0);\n            const endPixel = vScale.getPixelForDecimal(1);\n            const min = Math.min(startPixel, endPixel);\n            const max = Math.max(startPixel, endPixel);\n            base = Math.max(Math.min(base, max), min);\n            head = base + size;\n            if (_stacked && !floating) {\n                parsed._stacks[vScale.axis]._visualValues[datasetIndex] = vScale.getValueForPixel(head) - vScale.getValueForPixel(base);\n            }\n        }\n        if (base === vScale.getPixelForValue(actualBase)) {\n            const halfGrid = sign(size) * vScale.getLineWidthForValue(actualBase) / 2;\n            base += halfGrid;\n            size -= halfGrid;\n        }\n        return {\n            size,\n            base,\n            head,\n            center: head + size / 2\n        };\n    }\n _calculateBarIndexPixels(index, ruler) {\n        const scale = ruler.scale;\n        const options = this.options;\n        const skipNull = options.skipNull;\n        const maxBarThickness = valueOrDefault(options.maxBarThickness, Infinity);\n        let center, size;\n        if (ruler.grouped) {\n            const stackCount = skipNull ? this._getStackCount(index) : ruler.stackCount;\n            const range = options.barThickness === 'flex' ? computeFlexCategoryTraits(index, ruler, options, stackCount) : computeFitCategoryTraits(index, ruler, options, stackCount);\n            const stackIndex = this._getStackIndex(this.index, this._cachedMeta.stack, skipNull ? index : undefined);\n            center = range.start + range.chunk * stackIndex + range.chunk / 2;\n            size = Math.min(maxBarThickness, range.chunk * range.ratio);\n        } else {\n            center = scale.getPixelForValue(this.getParsed(index)[scale.axis], index);\n            size = Math.min(maxBarThickness, ruler.min * ruler.ratio);\n        }\n        return {\n            base: center - size / 2,\n            head: center + size / 2,\n            center,\n            size\n        };\n    }\n    draw() {\n        const meta = this._cachedMeta;\n        const vScale = meta.vScale;\n        const rects = meta.data;\n        const ilen = rects.length;\n        let i = 0;\n        for(; i < ilen; ++i){\n            if (this.getParsed(i)[vScale.axis] !== null) {\n                rects[i].draw(this._ctx);\n            }\n        }\n    }\n}\n\nclass BubbleController extends DatasetController {\n    static id = 'bubble';\n static defaults = {\n        datasetElementType: false,\n        dataElementType: 'point',\n        animations: {\n            numbers: {\n                type: 'number',\n                properties: [\n                    'x',\n                    'y',\n                    'borderWidth',\n                    'radius'\n                ]\n            }\n        }\n    };\n static overrides = {\n        scales: {\n            x: {\n                type: 'linear'\n            },\n            y: {\n                type: 'linear'\n            }\n        }\n    };\n    initialize() {\n        this.enableOptionSharing = true;\n        super.initialize();\n    }\n parsePrimitiveData(meta, data, start, count) {\n        const parsed = super.parsePrimitiveData(meta, data, start, count);\n        for(let i = 0; i < parsed.length; i++){\n            parsed[i]._custom = this.resolveDataElementOptions(i + start).radius;\n        }\n        return parsed;\n    }\n parseArrayData(meta, data, start, count) {\n        const parsed = super.parseArrayData(meta, data, start, count);\n        for(let i = 0; i < parsed.length; i++){\n            const item = data[start + i];\n            parsed[i]._custom = valueOrDefault(item[2], this.resolveDataElementOptions(i + start).radius);\n        }\n        return parsed;\n    }\n parseObjectData(meta, data, start, count) {\n        const parsed = super.parseObjectData(meta, data, start, count);\n        for(let i = 0; i < parsed.length; i++){\n            const item = data[start + i];\n            parsed[i]._custom = valueOrDefault(item && item.r && +item.r, this.resolveDataElementOptions(i + start).radius);\n        }\n        return parsed;\n    }\n getMaxOverflow() {\n        const data = this._cachedMeta.data;\n        let max = 0;\n        for(let i = data.length - 1; i >= 0; --i){\n            max = Math.max(max, data[i].size(this.resolveDataElementOptions(i)) / 2);\n        }\n        return max > 0 && max;\n    }\n getLabelAndValue(index) {\n        const meta = this._cachedMeta;\n        const labels = this.chart.data.labels || [];\n        const { xScale , yScale  } = meta;\n        const parsed = this.getParsed(index);\n        const x = xScale.getLabelForValue(parsed.x);\n        const y = yScale.getLabelForValue(parsed.y);\n        const r = parsed._custom;\n        return {\n            label: labels[index] || '',\n            value: '(' + x + ', ' + y + (r ? ', ' + r : '') + ')'\n        };\n    }\n    update(mode) {\n        const points = this._cachedMeta.data;\n        this.updateElements(points, 0, points.length, mode);\n    }\n    updateElements(points, start, count, mode) {\n        const reset = mode === 'reset';\n        const { iScale , vScale  } = this._cachedMeta;\n        const { sharedOptions , includeOptions  } = this._getSharedOptions(start, mode);\n        const iAxis = iScale.axis;\n        const vAxis = vScale.axis;\n        for(let i = start; i < start + count; i++){\n            const point = points[i];\n            const parsed = !reset && this.getParsed(i);\n            const properties = {};\n            const iPixel = properties[iAxis] = reset ? iScale.getPixelForDecimal(0.5) : iScale.getPixelForValue(parsed[iAxis]);\n            const vPixel = properties[vAxis] = reset ? vScale.getBasePixel() : vScale.getPixelForValue(parsed[vAxis]);\n            properties.skip = isNaN(iPixel) || isNaN(vPixel);\n            if (includeOptions) {\n                properties.options = sharedOptions || this.resolveDataElementOptions(i, point.active ? 'active' : mode);\n                if (reset) {\n                    properties.options.radius = 0;\n                }\n            }\n            this.updateElement(point, i, properties, mode);\n        }\n    }\n resolveDataElementOptions(index, mode) {\n        const parsed = this.getParsed(index);\n        let values = super.resolveDataElementOptions(index, mode);\n        if (values.$shared) {\n            values = Object.assign({}, values, {\n                $shared: false\n            });\n        }\n        const radius = values.radius;\n        if (mode !== 'active') {\n            values.radius = 0;\n        }\n        values.radius += valueOrDefault(parsed && parsed._custom, radius);\n        return values;\n    }\n}\n\nfunction getRatioAndOffset(rotation, circumference, cutout) {\n    let ratioX = 1;\n    let ratioY = 1;\n    let offsetX = 0;\n    let offsetY = 0;\n    if (circumference < TAU) {\n        const startAngle = rotation;\n        const endAngle = startAngle + circumference;\n        const startX = Math.cos(startAngle);\n        const startY = Math.sin(startAngle);\n        const endX = Math.cos(endAngle);\n        const endY = Math.sin(endAngle);\n        const calcMax = (angle, a, b)=>_angleBetween(angle, startAngle, endAngle, true) ? 1 : Math.max(a, a * cutout, b, b * cutout);\n        const calcMin = (angle, a, b)=>_angleBetween(angle, startAngle, endAngle, true) ? -1 : Math.min(a, a * cutout, b, b * cutout);\n        const maxX = calcMax(0, startX, endX);\n        const maxY = calcMax(HALF_PI, startY, endY);\n        const minX = calcMin(PI, startX, endX);\n        const minY = calcMin(PI + HALF_PI, startY, endY);\n        ratioX = (maxX - minX) / 2;\n        ratioY = (maxY - minY) / 2;\n        offsetX = -(maxX + minX) / 2;\n        offsetY = -(maxY + minY) / 2;\n    }\n    return {\n        ratioX,\n        ratioY,\n        offsetX,\n        offsetY\n    };\n}\nclass DoughnutController extends DatasetController {\n    static id = 'doughnut';\n static defaults = {\n        datasetElementType: false,\n        dataElementType: 'arc',\n        animation: {\n            animateRotate: true,\n            animateScale: false\n        },\n        animations: {\n            numbers: {\n                type: 'number',\n                properties: [\n                    'circumference',\n                    'endAngle',\n                    'innerRadius',\n                    'outerRadius',\n                    'startAngle',\n                    'x',\n                    'y',\n                    'offset',\n                    'borderWidth',\n                    'spacing'\n                ]\n            }\n        },\n        cutout: '50%',\n        rotation: 0,\n        circumference: 360,\n        radius: '100%',\n        spacing: 0,\n        indexAxis: 'r'\n    };\n    static descriptors = {\n        _scriptable: (name)=>name !== 'spacing',\n        _indexable: (name)=>name !== 'spacing' && !name.startsWith('borderDash') && !name.startsWith('hoverBorderDash')\n    };\n static overrides = {\n        aspectRatio: 1,\n        plugins: {\n            legend: {\n                labels: {\n                    generateLabels (chart) {\n                        const data = chart.data;\n                        if (data.labels.length && data.datasets.length) {\n                            const { labels: { pointStyle , color  }  } = chart.legend.options;\n                            return data.labels.map((label, i)=>{\n                                const meta = chart.getDatasetMeta(0);\n                                const style = meta.controller.getStyle(i);\n                                return {\n                                    text: label,\n                                    fillStyle: style.backgroundColor,\n                                    strokeStyle: style.borderColor,\n                                    fontColor: color,\n                                    lineWidth: style.borderWidth,\n                                    pointStyle: pointStyle,\n                                    hidden: !chart.getDataVisibility(i),\n                                    index: i\n                                };\n                            });\n                        }\n                        return [];\n                    }\n                },\n                onClick (e, legendItem, legend) {\n                    legend.chart.toggleDataVisibility(legendItem.index);\n                    legend.chart.update();\n                }\n            }\n        }\n    };\n    constructor(chart, datasetIndex){\n        super(chart, datasetIndex);\n        this.enableOptionSharing = true;\n        this.innerRadius = undefined;\n        this.outerRadius = undefined;\n        this.offsetX = undefined;\n        this.offsetY = undefined;\n    }\n    linkScales() {}\n parse(start, count) {\n        const data = this.getDataset().data;\n        const meta = this._cachedMeta;\n        if (this._parsing === false) {\n            meta._parsed = data;\n        } else {\n            let getter = (i)=>+data[i];\n            if (isObject(data[start])) {\n                const { key ='value'  } = this._parsing;\n                getter = (i)=>+resolveObjectKey(data[i], key);\n            }\n            let i, ilen;\n            for(i = start, ilen = start + count; i < ilen; ++i){\n                meta._parsed[i] = getter(i);\n            }\n        }\n    }\n _getRotation() {\n        return toRadians(this.options.rotation - 90);\n    }\n _getCircumference() {\n        return toRadians(this.options.circumference);\n    }\n _getRotationExtents() {\n        let min = TAU;\n        let max = -TAU;\n        for(let i = 0; i < this.chart.data.datasets.length; ++i){\n            if (this.chart.isDatasetVisible(i) && this.chart.getDatasetMeta(i).type === this._type) {\n                const controller = this.chart.getDatasetMeta(i).controller;\n                const rotation = controller._getRotation();\n                const circumference = controller._getCircumference();\n                min = Math.min(min, rotation);\n                max = Math.max(max, rotation + circumference);\n            }\n        }\n        return {\n            rotation: min,\n            circumference: max - min\n        };\n    }\n update(mode) {\n        const chart = this.chart;\n        const { chartArea  } = chart;\n        const meta = this._cachedMeta;\n        const arcs = meta.data;\n        const spacing = this.getMaxBorderWidth() + this.getMaxOffset(arcs) + this.options.spacing;\n        const maxSize = Math.max((Math.min(chartArea.width, chartArea.height) - spacing) / 2, 0);\n        const cutout = Math.min(toPercentage(this.options.cutout, maxSize), 1);\n        const chartWeight = this._getRingWeight(this.index);\n        const { circumference , rotation  } = this._getRotationExtents();\n        const { ratioX , ratioY , offsetX , offsetY  } = getRatioAndOffset(rotation, circumference, cutout);\n        const maxWidth = (chartArea.width - spacing) / ratioX;\n        const maxHeight = (chartArea.height - spacing) / ratioY;\n        const maxRadius = Math.max(Math.min(maxWidth, maxHeight) / 2, 0);\n        const outerRadius = toDimension(this.options.radius, maxRadius);\n        const innerRadius = Math.max(outerRadius * cutout, 0);\n        const radiusLength = (outerRadius - innerRadius) / this._getVisibleDatasetWeightTotal();\n        this.offsetX = offsetX * outerRadius;\n        this.offsetY = offsetY * outerRadius;\n        meta.total = this.calculateTotal();\n        this.outerRadius = outerRadius - radiusLength * this._getRingWeightOffset(this.index);\n        this.innerRadius = Math.max(this.outerRadius - radiusLength * chartWeight, 0);\n        this.updateElements(arcs, 0, arcs.length, mode);\n    }\n _circumference(i, reset) {\n        const opts = this.options;\n        const meta = this._cachedMeta;\n        const circumference = this._getCircumference();\n        if (reset && opts.animation.animateRotate || !this.chart.getDataVisibility(i) || meta._parsed[i] === null || meta.data[i].hidden) {\n            return 0;\n        }\n        return this.calculateCircumference(meta._parsed[i] * circumference / TAU);\n    }\n    updateElements(arcs, start, count, mode) {\n        const reset = mode === 'reset';\n        const chart = this.chart;\n        const chartArea = chart.chartArea;\n        const opts = chart.options;\n        const animationOpts = opts.animation;\n        const centerX = (chartArea.left + chartArea.right) / 2;\n        const centerY = (chartArea.top + chartArea.bottom) / 2;\n        const animateScale = reset && animationOpts.animateScale;\n        const innerRadius = animateScale ? 0 : this.innerRadius;\n        const outerRadius = animateScale ? 0 : this.outerRadius;\n        const { sharedOptions , includeOptions  } = this._getSharedOptions(start, mode);\n        let startAngle = this._getRotation();\n        let i;\n        for(i = 0; i < start; ++i){\n            startAngle += this._circumference(i, reset);\n        }\n        for(i = start; i < start + count; ++i){\n            const circumference = this._circumference(i, reset);\n            const arc = arcs[i];\n            const properties = {\n                x: centerX + this.offsetX,\n                y: centerY + this.offsetY,\n                startAngle,\n                endAngle: startAngle + circumference,\n                circumference,\n                outerRadius,\n                innerRadius\n            };\n            if (includeOptions) {\n                properties.options = sharedOptions || this.resolveDataElementOptions(i, arc.active ? 'active' : mode);\n            }\n            startAngle += circumference;\n            this.updateElement(arc, i, properties, mode);\n        }\n    }\n    calculateTotal() {\n        const meta = this._cachedMeta;\n        const metaData = meta.data;\n        let total = 0;\n        let i;\n        for(i = 0; i < metaData.length; i++){\n            const value = meta._parsed[i];\n            if (value !== null && !isNaN(value) && this.chart.getDataVisibility(i) && !metaData[i].hidden) {\n                total += Math.abs(value);\n            }\n        }\n        return total;\n    }\n    calculateCircumference(value) {\n        const total = this._cachedMeta.total;\n        if (total > 0 && !isNaN(value)) {\n            return TAU * (Math.abs(value) / total);\n        }\n        return 0;\n    }\n    getLabelAndValue(index) {\n        const meta = this._cachedMeta;\n        const chart = this.chart;\n        const labels = chart.data.labels || [];\n        const value = formatNumber(meta._parsed[index], chart.options.locale);\n        return {\n            label: labels[index] || '',\n            value\n        };\n    }\n    getMaxBorderWidth(arcs) {\n        let max = 0;\n        const chart = this.chart;\n        let i, ilen, meta, controller, options;\n        if (!arcs) {\n            for(i = 0, ilen = chart.data.datasets.length; i < ilen; ++i){\n                if (chart.isDatasetVisible(i)) {\n                    meta = chart.getDatasetMeta(i);\n                    arcs = meta.data;\n                    controller = meta.controller;\n                    break;\n                }\n            }\n        }\n        if (!arcs) {\n            return 0;\n        }\n        for(i = 0, ilen = arcs.length; i < ilen; ++i){\n            options = controller.resolveDataElementOptions(i);\n            if (options.borderAlign !== 'inner') {\n                max = Math.max(max, options.borderWidth || 0, options.hoverBorderWidth || 0);\n            }\n        }\n        return max;\n    }\n    getMaxOffset(arcs) {\n        let max = 0;\n        for(let i = 0, ilen = arcs.length; i < ilen; ++i){\n            const options = this.resolveDataElementOptions(i);\n            max = Math.max(max, options.offset || 0, options.hoverOffset || 0);\n        }\n        return max;\n    }\n _getRingWeightOffset(datasetIndex) {\n        let ringWeightOffset = 0;\n        for(let i = 0; i < datasetIndex; ++i){\n            if (this.chart.isDatasetVisible(i)) {\n                ringWeightOffset += this._getRingWeight(i);\n            }\n        }\n        return ringWeightOffset;\n    }\n _getRingWeight(datasetIndex) {\n        return Math.max(valueOrDefault(this.chart.data.datasets[datasetIndex].weight, 1), 0);\n    }\n _getVisibleDatasetWeightTotal() {\n        return this._getRingWeightOffset(this.chart.data.datasets.length) || 1;\n    }\n}\n\nclass LineController extends DatasetController {\n    static id = 'line';\n static defaults = {\n        datasetElementType: 'line',\n        dataElementType: 'point',\n        showLine: true,\n        spanGaps: false\n    };\n static overrides = {\n        scales: {\n            _index_: {\n                type: 'category'\n            },\n            _value_: {\n                type: 'linear'\n            }\n        }\n    };\n    initialize() {\n        this.enableOptionSharing = true;\n        this.supportsDecimation = true;\n        super.initialize();\n    }\n    update(mode) {\n        const meta = this._cachedMeta;\n        const { dataset: line , data: points = [] , _dataset  } = meta;\n        const animationsDisabled = this.chart._animationsDisabled;\n        let { start , count  } = _getStartAndCountOfVisiblePoints(meta, points, animationsDisabled);\n        this._drawStart = start;\n        this._drawCount = count;\n        if (_scaleRangesChanged(meta)) {\n            start = 0;\n            count = points.length;\n        }\n        line._chart = this.chart;\n        line._datasetIndex = this.index;\n        line._decimated = !!_dataset._decimated;\n        line.points = points;\n        const options = this.resolveDatasetElementOptions(mode);\n        if (!this.options.showLine) {\n            options.borderWidth = 0;\n        }\n        options.segment = this.options.segment;\n        this.updateElement(line, undefined, {\n            animated: !animationsDisabled,\n            options\n        }, mode);\n        this.updateElements(points, start, count, mode);\n    }\n    updateElements(points, start, count, mode) {\n        const reset = mode === 'reset';\n        const { iScale , vScale , _stacked , _dataset  } = this._cachedMeta;\n        const { sharedOptions , includeOptions  } = this._getSharedOptions(start, mode);\n        const iAxis = iScale.axis;\n        const vAxis = vScale.axis;\n        const { spanGaps , segment  } = this.options;\n        const maxGapLength = isNumber(spanGaps) ? spanGaps : Number.POSITIVE_INFINITY;\n        const directUpdate = this.chart._animationsDisabled || reset || mode === 'none';\n        const end = start + count;\n        const pointsCount = points.length;\n        let prevParsed = start > 0 && this.getParsed(start - 1);\n        for(let i = 0; i < pointsCount; ++i){\n            const point = points[i];\n            const properties = directUpdate ? point : {};\n            if (i < start || i >= end) {\n                properties.skip = true;\n                continue;\n            }\n            const parsed = this.getParsed(i);\n            const nullData = isNullOrUndef(parsed[vAxis]);\n            const iPixel = properties[iAxis] = iScale.getPixelForValue(parsed[iAxis], i);\n            const vPixel = properties[vAxis] = reset || nullData ? vScale.getBasePixel() : vScale.getPixelForValue(_stacked ? this.applyStack(vScale, parsed, _stacked) : parsed[vAxis], i);\n            properties.skip = isNaN(iPixel) || isNaN(vPixel) || nullData;\n            properties.stop = i > 0 && Math.abs(parsed[iAxis] - prevParsed[iAxis]) > maxGapLength;\n            if (segment) {\n                properties.parsed = parsed;\n                properties.raw = _dataset.data[i];\n            }\n            if (includeOptions) {\n                properties.options = sharedOptions || this.resolveDataElementOptions(i, point.active ? 'active' : mode);\n            }\n            if (!directUpdate) {\n                this.updateElement(point, i, properties, mode);\n            }\n            prevParsed = parsed;\n        }\n    }\n getMaxOverflow() {\n        const meta = this._cachedMeta;\n        const dataset = meta.dataset;\n        const border = dataset.options && dataset.options.borderWidth || 0;\n        const data = meta.data || [];\n        if (!data.length) {\n            return border;\n        }\n        const firstPoint = data[0].size(this.resolveDataElementOptions(0));\n        const lastPoint = data[data.length - 1].size(this.resolveDataElementOptions(data.length - 1));\n        return Math.max(border, firstPoint, lastPoint) / 2;\n    }\n    draw() {\n        const meta = this._cachedMeta;\n        meta.dataset.updateControlPoints(this.chart.chartArea, meta.iScale.axis);\n        super.draw();\n    }\n}\n\nclass PolarAreaController extends DatasetController {\n    static id = 'polarArea';\n static defaults = {\n        dataElementType: 'arc',\n        animation: {\n            animateRotate: true,\n            animateScale: true\n        },\n        animations: {\n            numbers: {\n                type: 'number',\n                properties: [\n                    'x',\n                    'y',\n                    'startAngle',\n                    'endAngle',\n                    'innerRadius',\n                    'outerRadius'\n                ]\n            }\n        },\n        indexAxis: 'r',\n        startAngle: 0\n    };\n static overrides = {\n        aspectRatio: 1,\n        plugins: {\n            legend: {\n                labels: {\n                    generateLabels (chart) {\n                        const data = chart.data;\n                        if (data.labels.length && data.datasets.length) {\n                            const { labels: { pointStyle , color  }  } = chart.legend.options;\n                            return data.labels.map((label, i)=>{\n                                const meta = chart.getDatasetMeta(0);\n                                const style = meta.controller.getStyle(i);\n                                return {\n                                    text: label,\n                                    fillStyle: style.backgroundColor,\n                                    strokeStyle: style.borderColor,\n                                    fontColor: color,\n                                    lineWidth: style.borderWidth,\n                                    pointStyle: pointStyle,\n                                    hidden: !chart.getDataVisibility(i),\n                                    index: i\n                                };\n                            });\n                        }\n                        return [];\n                    }\n                },\n                onClick (e, legendItem, legend) {\n                    legend.chart.toggleDataVisibility(legendItem.index);\n                    legend.chart.update();\n                }\n            }\n        },\n        scales: {\n            r: {\n                type: 'radialLinear',\n                angleLines: {\n                    display: false\n                },\n                beginAtZero: true,\n                grid: {\n                    circular: true\n                },\n                pointLabels: {\n                    display: false\n                },\n                startAngle: 0\n            }\n        }\n    };\n    constructor(chart, datasetIndex){\n        super(chart, datasetIndex);\n        this.innerRadius = undefined;\n        this.outerRadius = undefined;\n    }\n    getLabelAndValue(index) {\n        const meta = this._cachedMeta;\n        const chart = this.chart;\n        const labels = chart.data.labels || [];\n        const value = formatNumber(meta._parsed[index].r, chart.options.locale);\n        return {\n            label: labels[index] || '',\n            value\n        };\n    }\n    parseObjectData(meta, data, start, count) {\n        return _parseObjectDataRadialScale.bind(this)(meta, data, start, count);\n    }\n    update(mode) {\n        const arcs = this._cachedMeta.data;\n        this._updateRadius();\n        this.updateElements(arcs, 0, arcs.length, mode);\n    }\n getMinMax() {\n        const meta = this._cachedMeta;\n        const range = {\n            min: Number.POSITIVE_INFINITY,\n            max: Number.NEGATIVE_INFINITY\n        };\n        meta.data.forEach((element, index)=>{\n            const parsed = this.getParsed(index).r;\n            if (!isNaN(parsed) && this.chart.getDataVisibility(index)) {\n                if (parsed < range.min) {\n                    range.min = parsed;\n                }\n                if (parsed > range.max) {\n                    range.max = parsed;\n                }\n            }\n        });\n        return range;\n    }\n _updateRadius() {\n        const chart = this.chart;\n        const chartArea = chart.chartArea;\n        const opts = chart.options;\n        const minSize = Math.min(chartArea.right - chartArea.left, chartArea.bottom - chartArea.top);\n        const outerRadius = Math.max(minSize / 2, 0);\n        const innerRadius = Math.max(opts.cutoutPercentage ? outerRadius / 100 * opts.cutoutPercentage : 1, 0);\n        const radiusLength = (outerRadius - innerRadius) / chart.getVisibleDatasetCount();\n        this.outerRadius = outerRadius - radiusLength * this.index;\n        this.innerRadius = this.outerRadius - radiusLength;\n    }\n    updateElements(arcs, start, count, mode) {\n        const reset = mode === 'reset';\n        const chart = this.chart;\n        const opts = chart.options;\n        const animationOpts = opts.animation;\n        const scale = this._cachedMeta.rScale;\n        const centerX = scale.xCenter;\n        const centerY = scale.yCenter;\n        const datasetStartAngle = scale.getIndexAngle(0) - 0.5 * PI;\n        let angle = datasetStartAngle;\n        let i;\n        const defaultAngle = 360 / this.countVisibleElements();\n        for(i = 0; i < start; ++i){\n            angle += this._computeAngle(i, mode, defaultAngle);\n        }\n        for(i = start; i < start + count; i++){\n            const arc = arcs[i];\n            let startAngle = angle;\n            let endAngle = angle + this._computeAngle(i, mode, defaultAngle);\n            let outerRadius = chart.getDataVisibility(i) ? scale.getDistanceFromCenterForValue(this.getParsed(i).r) : 0;\n            angle = endAngle;\n            if (reset) {\n                if (animationOpts.animateScale) {\n                    outerRadius = 0;\n                }\n                if (animationOpts.animateRotate) {\n                    startAngle = endAngle = datasetStartAngle;\n                }\n            }\n            const properties = {\n                x: centerX,\n                y: centerY,\n                innerRadius: 0,\n                outerRadius,\n                startAngle,\n                endAngle,\n                options: this.resolveDataElementOptions(i, arc.active ? 'active' : mode)\n            };\n            this.updateElement(arc, i, properties, mode);\n        }\n    }\n    countVisibleElements() {\n        const meta = this._cachedMeta;\n        let count = 0;\n        meta.data.forEach((element, index)=>{\n            if (!isNaN(this.getParsed(index).r) && this.chart.getDataVisibility(index)) {\n                count++;\n            }\n        });\n        return count;\n    }\n _computeAngle(index, mode, defaultAngle) {\n        return this.chart.getDataVisibility(index) ? toRadians(this.resolveDataElementOptions(index, mode).angle || defaultAngle) : 0;\n    }\n}\n\nclass PieController extends DoughnutController {\n    static id = 'pie';\n static defaults = {\n        cutout: 0,\n        rotation: 0,\n        circumference: 360,\n        radius: '100%'\n    };\n}\n\nclass RadarController extends DatasetController {\n    static id = 'radar';\n static defaults = {\n        datasetElementType: 'line',\n        dataElementType: 'point',\n        indexAxis: 'r',\n        showLine: true,\n        elements: {\n            line: {\n                fill: 'start'\n            }\n        }\n    };\n static overrides = {\n        aspectRatio: 1,\n        scales: {\n            r: {\n                type: 'radialLinear'\n            }\n        }\n    };\n getLabelAndValue(index) {\n        const vScale = this._cachedMeta.vScale;\n        const parsed = this.getParsed(index);\n        return {\n            label: vScale.getLabels()[index],\n            value: '' + vScale.getLabelForValue(parsed[vScale.axis])\n        };\n    }\n    parseObjectData(meta, data, start, count) {\n        return _parseObjectDataRadialScale.bind(this)(meta, data, start, count);\n    }\n    update(mode) {\n        const meta = this._cachedMeta;\n        const line = meta.dataset;\n        const points = meta.data || [];\n        const labels = meta.iScale.getLabels();\n        line.points = points;\n        if (mode !== 'resize') {\n            const options = this.resolveDatasetElementOptions(mode);\n            if (!this.options.showLine) {\n                options.borderWidth = 0;\n            }\n            const properties = {\n                _loop: true,\n                _fullLoop: labels.length === points.length,\n                options\n            };\n            this.updateElement(line, undefined, properties, mode);\n        }\n        this.updateElements(points, 0, points.length, mode);\n    }\n    updateElements(points, start, count, mode) {\n        const scale = this._cachedMeta.rScale;\n        const reset = mode === 'reset';\n        for(let i = start; i < start + count; i++){\n            const point = points[i];\n            const options = this.resolveDataElementOptions(i, point.active ? 'active' : mode);\n            const pointPosition = scale.getPointPositionForValue(i, this.getParsed(i).r);\n            const x = reset ? scale.xCenter : pointPosition.x;\n            const y = reset ? scale.yCenter : pointPosition.y;\n            const properties = {\n                x,\n                y,\n                angle: pointPosition.angle,\n                skip: isNaN(x) || isNaN(y),\n                options\n            };\n            this.updateElement(point, i, properties, mode);\n        }\n    }\n}\n\nclass ScatterController extends DatasetController {\n    static id = 'scatter';\n static defaults = {\n        datasetElementType: false,\n        dataElementType: 'point',\n        showLine: false,\n        fill: false\n    };\n static overrides = {\n        interaction: {\n            mode: 'point'\n        },\n        scales: {\n            x: {\n                type: 'linear'\n            },\n            y: {\n                type: 'linear'\n            }\n        }\n    };\n getLabelAndValue(index) {\n        const meta = this._cachedMeta;\n        const labels = this.chart.data.labels || [];\n        const { xScale , yScale  } = meta;\n        const parsed = this.getParsed(index);\n        const x = xScale.getLabelForValue(parsed.x);\n        const y = yScale.getLabelForValue(parsed.y);\n        return {\n            label: labels[index] || '',\n            value: '(' + x + ', ' + y + ')'\n        };\n    }\n    update(mode) {\n        const meta = this._cachedMeta;\n        const { data: points = []  } = meta;\n        const animationsDisabled = this.chart._animationsDisabled;\n        let { start , count  } = _getStartAndCountOfVisiblePoints(meta, points, animationsDisabled);\n        this._drawStart = start;\n        this._drawCount = count;\n        if (_scaleRangesChanged(meta)) {\n            start = 0;\n            count = points.length;\n        }\n        if (this.options.showLine) {\n            if (!this.datasetElementType) {\n                this.addElements();\n            }\n            const { dataset: line , _dataset  } = meta;\n            line._chart = this.chart;\n            line._datasetIndex = this.index;\n            line._decimated = !!_dataset._decimated;\n            line.points = points;\n            const options = this.resolveDatasetElementOptions(mode);\n            options.segment = this.options.segment;\n            this.updateElement(line, undefined, {\n                animated: !animationsDisabled,\n                options\n            }, mode);\n        } else if (this.datasetElementType) {\n            delete meta.dataset;\n            this.datasetElementType = false;\n        }\n        this.updateElements(points, start, count, mode);\n    }\n    addElements() {\n        const { showLine  } = this.options;\n        if (!this.datasetElementType && showLine) {\n            this.datasetElementType = this.chart.registry.getElement('line');\n        }\n        super.addElements();\n    }\n    updateElements(points, start, count, mode) {\n        const reset = mode === 'reset';\n        const { iScale , vScale , _stacked , _dataset  } = this._cachedMeta;\n        const firstOpts = this.resolveDataElementOptions(start, mode);\n        const sharedOptions = this.getSharedOptions(firstOpts);\n        const includeOptions = this.includeOptions(mode, sharedOptions);\n        const iAxis = iScale.axis;\n        const vAxis = vScale.axis;\n        const { spanGaps , segment  } = this.options;\n        const maxGapLength = isNumber(spanGaps) ? spanGaps : Number.POSITIVE_INFINITY;\n        const directUpdate = this.chart._animationsDisabled || reset || mode === 'none';\n        let prevParsed = start > 0 && this.getParsed(start - 1);\n        for(let i = start; i < start + count; ++i){\n            const point = points[i];\n            const parsed = this.getParsed(i);\n            const properties = directUpdate ? point : {};\n            const nullData = isNullOrUndef(parsed[vAxis]);\n            const iPixel = properties[iAxis] = iScale.getPixelForValue(parsed[iAxis], i);\n            const vPixel = properties[vAxis] = reset || nullData ? vScale.getBasePixel() : vScale.getPixelForValue(_stacked ? this.applyStack(vScale, parsed, _stacked) : parsed[vAxis], i);\n            properties.skip = isNaN(iPixel) || isNaN(vPixel) || nullData;\n            properties.stop = i > 0 && Math.abs(parsed[iAxis] - prevParsed[iAxis]) > maxGapLength;\n            if (segment) {\n                properties.parsed = parsed;\n                properties.raw = _dataset.data[i];\n            }\n            if (includeOptions) {\n                properties.options = sharedOptions || this.resolveDataElementOptions(i, point.active ? 'active' : mode);\n            }\n            if (!directUpdate) {\n                this.updateElement(point, i, properties, mode);\n            }\n            prevParsed = parsed;\n        }\n        this.updateSharedOptions(sharedOptions, mode, firstOpts);\n    }\n getMaxOverflow() {\n        const meta = this._cachedMeta;\n        const data = meta.data || [];\n        if (!this.options.showLine) {\n            let max = 0;\n            for(let i = data.length - 1; i >= 0; --i){\n                max = Math.max(max, data[i].size(this.resolveDataElementOptions(i)) / 2);\n            }\n            return max > 0 && max;\n        }\n        const dataset = meta.dataset;\n        const border = dataset.options && dataset.options.borderWidth || 0;\n        if (!data.length) {\n            return border;\n        }\n        const firstPoint = data[0].size(this.resolveDataElementOptions(0));\n        const lastPoint = data[data.length - 1].size(this.resolveDataElementOptions(data.length - 1));\n        return Math.max(border, firstPoint, lastPoint) / 2;\n    }\n}\n\nvar controllers = /*#__PURE__*/Object.freeze({\n__proto__: null,\nBarController: BarController,\nBubbleController: BubbleController,\nDoughnutController: DoughnutController,\nLineController: LineController,\nPieController: PieController,\nPolarAreaController: PolarAreaController,\nRadarController: RadarController,\nScatterController: ScatterController\n});\n\n/**\n * @namespace Chart._adapters\n * @since 2.8.0\n * @private\n */ function abstract() {\n    throw new Error('This method is not implemented: Check that a complete date adapter is provided.');\n}\n/**\n * Date adapter (current used by the time scale)\n * @namespace Chart._adapters._date\n * @memberof Chart._adapters\n * @private\n */ class DateAdapterBase {\n    /**\n   * Override default date adapter methods.\n   * Accepts type parameter to define options type.\n   * @example\n   * Chart._adapters._date.override<{myAdapterOption: string}>({\n   *   init() {\n   *     console.log(this.options.myAdapterOption);\n   *   }\n   * })\n   */ static override(members) {\n        Object.assign(DateAdapterBase.prototype, members);\n    }\n    options;\n    constructor(options){\n        this.options = options || {};\n    }\n    // eslint-disable-next-line @typescript-eslint/no-empty-function\n    init() {}\n    formats() {\n        return abstract();\n    }\n    parse() {\n        return abstract();\n    }\n    format() {\n        return abstract();\n    }\n    add() {\n        return abstract();\n    }\n    diff() {\n        return abstract();\n    }\n    startOf() {\n        return abstract();\n    }\n    endOf() {\n        return abstract();\n    }\n}\nvar adapters = {\n    _date: DateAdapterBase\n};\n\nfunction binarySearch(metaset, axis, value, intersect) {\n    const { controller , data , _sorted  } = metaset;\n    const iScale = controller._cachedMeta.iScale;\n    if (iScale && axis === iScale.axis && axis !== 'r' && _sorted && data.length) {\n        const lookupMethod = iScale._reversePixels ? _rlookupByKey : _lookupByKey;\n        if (!intersect) {\n            return lookupMethod(data, axis, value);\n        } else if (controller._sharedOptions) {\n            const el = data[0];\n            const range = typeof el.getRange === 'function' && el.getRange(axis);\n            if (range) {\n                const start = lookupMethod(data, axis, value - range);\n                const end = lookupMethod(data, axis, value + range);\n                return {\n                    lo: start.lo,\n                    hi: end.hi\n                };\n            }\n        }\n    }\n    return {\n        lo: 0,\n        hi: data.length - 1\n    };\n}\n function evaluateInteractionItems(chart, axis, position, handler, intersect) {\n    const metasets = chart.getSortedVisibleDatasetMetas();\n    const value = position[axis];\n    for(let i = 0, ilen = metasets.length; i < ilen; ++i){\n        const { index , data  } = metasets[i];\n        const { lo , hi  } = binarySearch(metasets[i], axis, value, intersect);\n        for(let j = lo; j <= hi; ++j){\n            const element = data[j];\n            if (!element.skip) {\n                handler(element, index, j);\n            }\n        }\n    }\n}\n function getDistanceMetricForAxis(axis) {\n    const useX = axis.indexOf('x') !== -1;\n    const useY = axis.indexOf('y') !== -1;\n    return function(pt1, pt2) {\n        const deltaX = useX ? Math.abs(pt1.x - pt2.x) : 0;\n        const deltaY = useY ? Math.abs(pt1.y - pt2.y) : 0;\n        return Math.sqrt(Math.pow(deltaX, 2) + Math.pow(deltaY, 2));\n    };\n}\n function getIntersectItems(chart, position, axis, useFinalPosition, includeInvisible) {\n    const items = [];\n    if (!includeInvisible && !chart.isPointInArea(position)) {\n        return items;\n    }\n    const evaluationFunc = function(element, datasetIndex, index) {\n        if (!includeInvisible && !_isPointInArea(element, chart.chartArea, 0)) {\n            return;\n        }\n        if (element.inRange(position.x, position.y, useFinalPosition)) {\n            items.push({\n                element,\n                datasetIndex,\n                index\n            });\n        }\n    };\n    evaluateInteractionItems(chart, axis, position, evaluationFunc, true);\n    return items;\n}\n function getNearestRadialItems(chart, position, axis, useFinalPosition) {\n    let items = [];\n    function evaluationFunc(element, datasetIndex, index) {\n        const { startAngle , endAngle  } = element.getProps([\n            'startAngle',\n            'endAngle'\n        ], useFinalPosition);\n        const { angle  } = getAngleFromPoint(element, {\n            x: position.x,\n            y: position.y\n        });\n        if (_angleBetween(angle, startAngle, endAngle)) {\n            items.push({\n                element,\n                datasetIndex,\n                index\n            });\n        }\n    }\n    evaluateInteractionItems(chart, axis, position, evaluationFunc);\n    return items;\n}\n function getNearestCartesianItems(chart, position, axis, intersect, useFinalPosition, includeInvisible) {\n    let items = [];\n    const distanceMetric = getDistanceMetricForAxis(axis);\n    let minDistance = Number.POSITIVE_INFINITY;\n    function evaluationFunc(element, datasetIndex, index) {\n        const inRange = element.inRange(position.x, position.y, useFinalPosition);\n        if (intersect && !inRange) {\n            return;\n        }\n        const center = element.getCenterPoint(useFinalPosition);\n        const pointInArea = !!includeInvisible || chart.isPointInArea(center);\n        if (!pointInArea && !inRange) {\n            return;\n        }\n        const distance = distanceMetric(position, center);\n        if (distance < minDistance) {\n            items = [\n                {\n                    element,\n                    datasetIndex,\n                    index\n                }\n            ];\n            minDistance = distance;\n        } else if (distance === minDistance) {\n            items.push({\n                element,\n                datasetIndex,\n                index\n            });\n        }\n    }\n    evaluateInteractionItems(chart, axis, position, evaluationFunc);\n    return items;\n}\n function getNearestItems(chart, position, axis, intersect, useFinalPosition, includeInvisible) {\n    if (!includeInvisible && !chart.isPointInArea(position)) {\n        return [];\n    }\n    return axis === 'r' && !intersect ? getNearestRadialItems(chart, position, axis, useFinalPosition) : getNearestCartesianItems(chart, position, axis, intersect, useFinalPosition, includeInvisible);\n}\n function getAxisItems(chart, position, axis, intersect, useFinalPosition) {\n    const items = [];\n    const rangeMethod = axis === 'x' ? 'inXRange' : 'inYRange';\n    let intersectsItem = false;\n    evaluateInteractionItems(chart, axis, position, (element, datasetIndex, index)=>{\n        if (element[rangeMethod](position[axis], useFinalPosition)) {\n            items.push({\n                element,\n                datasetIndex,\n                index\n            });\n            intersectsItem = intersectsItem || element.inRange(position.x, position.y, useFinalPosition);\n        }\n    });\n    if (intersect && !intersectsItem) {\n        return [];\n    }\n    return items;\n}\n var Interaction = {\n    evaluateInteractionItems,\n    modes: {\n index (chart, e, options, useFinalPosition) {\n            const position = getRelativePosition(e, chart);\n            const axis = options.axis || 'x';\n            const includeInvisible = options.includeInvisible || false;\n            const items = options.intersect ? getIntersectItems(chart, position, axis, useFinalPosition, includeInvisible) : getNearestItems(chart, position, axis, false, useFinalPosition, includeInvisible);\n            const elements = [];\n            if (!items.length) {\n                return [];\n            }\n            chart.getSortedVisibleDatasetMetas().forEach((meta)=>{\n                const index = items[0].index;\n                const element = meta.data[index];\n                if (element && !element.skip) {\n                    elements.push({\n                        element,\n                        datasetIndex: meta.index,\n                        index\n                    });\n                }\n            });\n            return elements;\n        },\n dataset (chart, e, options, useFinalPosition) {\n            const position = getRelativePosition(e, chart);\n            const axis = options.axis || 'xy';\n            const includeInvisible = options.includeInvisible || false;\n            let items = options.intersect ? getIntersectItems(chart, position, axis, useFinalPosition, includeInvisible) : getNearestItems(chart, position, axis, false, useFinalPosition, includeInvisible);\n            if (items.length > 0) {\n                const datasetIndex = items[0].datasetIndex;\n                const data = chart.getDatasetMeta(datasetIndex).data;\n                items = [];\n                for(let i = 0; i < data.length; ++i){\n                    items.push({\n                        element: data[i],\n                        datasetIndex,\n                        index: i\n                    });\n                }\n            }\n            return items;\n        },\n point (chart, e, options, useFinalPosition) {\n            const position = getRelativePosition(e, chart);\n            const axis = options.axis || 'xy';\n            const includeInvisible = options.includeInvisible || false;\n            return getIntersectItems(chart, position, axis, useFinalPosition, includeInvisible);\n        },\n nearest (chart, e, options, useFinalPosition) {\n            const position = getRelativePosition(e, chart);\n            const axis = options.axis || 'xy';\n            const includeInvisible = options.includeInvisible || false;\n            return getNearestItems(chart, position, axis, options.intersect, useFinalPosition, includeInvisible);\n        },\n x (chart, e, options, useFinalPosition) {\n            const position = getRelativePosition(e, chart);\n            return getAxisItems(chart, position, 'x', options.intersect, useFinalPosition);\n        },\n y (chart, e, options, useFinalPosition) {\n            const position = getRelativePosition(e, chart);\n            return getAxisItems(chart, position, 'y', options.intersect, useFinalPosition);\n        }\n    }\n};\n\nconst STATIC_POSITIONS = [\n    'left',\n    'top',\n    'right',\n    'bottom'\n];\nfunction filterByPosition(array, position) {\n    return array.filter((v)=>v.pos === position);\n}\nfunction filterDynamicPositionByAxis(array, axis) {\n    return array.filter((v)=>STATIC_POSITIONS.indexOf(v.pos) === -1 && v.box.axis === axis);\n}\nfunction sortByWeight(array, reverse) {\n    return array.sort((a, b)=>{\n        const v0 = reverse ? b : a;\n        const v1 = reverse ? a : b;\n        return v0.weight === v1.weight ? v0.index - v1.index : v0.weight - v1.weight;\n    });\n}\nfunction wrapBoxes(boxes) {\n    const layoutBoxes = [];\n    let i, ilen, box, pos, stack, stackWeight;\n    for(i = 0, ilen = (boxes || []).length; i < ilen; ++i){\n        box = boxes[i];\n        ({ position: pos , options: { stack , stackWeight =1  }  } = box);\n        layoutBoxes.push({\n            index: i,\n            box,\n            pos,\n            horizontal: box.isHorizontal(),\n            weight: box.weight,\n            stack: stack && pos + stack,\n            stackWeight\n        });\n    }\n    return layoutBoxes;\n}\nfunction buildStacks(layouts) {\n    const stacks = {};\n    for (const wrap of layouts){\n        const { stack , pos , stackWeight  } = wrap;\n        if (!stack || !STATIC_POSITIONS.includes(pos)) {\n            continue;\n        }\n        const _stack = stacks[stack] || (stacks[stack] = {\n            count: 0,\n            placed: 0,\n            weight: 0,\n            size: 0\n        });\n        _stack.count++;\n        _stack.weight += stackWeight;\n    }\n    return stacks;\n}\n function setLayoutDims(layouts, params) {\n    const stacks = buildStacks(layouts);\n    const { vBoxMaxWidth , hBoxMaxHeight  } = params;\n    let i, ilen, layout;\n    for(i = 0, ilen = layouts.length; i < ilen; ++i){\n        layout = layouts[i];\n        const { fullSize  } = layout.box;\n        const stack = stacks[layout.stack];\n        const factor = stack && layout.stackWeight / stack.weight;\n        if (layout.horizontal) {\n            layout.width = factor ? factor * vBoxMaxWidth : fullSize && params.availableWidth;\n            layout.height = hBoxMaxHeight;\n        } else {\n            layout.width = vBoxMaxWidth;\n            layout.height = factor ? factor * hBoxMaxHeight : fullSize && params.availableHeight;\n        }\n    }\n    return stacks;\n}\nfunction buildLayoutBoxes(boxes) {\n    const layoutBoxes = wrapBoxes(boxes);\n    const fullSize = sortByWeight(layoutBoxes.filter((wrap)=>wrap.box.fullSize), true);\n    const left = sortByWeight(filterByPosition(layoutBoxes, 'left'), true);\n    const right = sortByWeight(filterByPosition(layoutBoxes, 'right'));\n    const top = sortByWeight(filterByPosition(layoutBoxes, 'top'), true);\n    const bottom = sortByWeight(filterByPosition(layoutBoxes, 'bottom'));\n    const centerHorizontal = filterDynamicPositionByAxis(layoutBoxes, 'x');\n    const centerVertical = filterDynamicPositionByAxis(layoutBoxes, 'y');\n    return {\n        fullSize,\n        leftAndTop: left.concat(top),\n        rightAndBottom: right.concat(centerVertical).concat(bottom).concat(centerHorizontal),\n        chartArea: filterByPosition(layoutBoxes, 'chartArea'),\n        vertical: left.concat(right).concat(centerVertical),\n        horizontal: top.concat(bottom).concat(centerHorizontal)\n    };\n}\nfunction getCombinedMax(maxPadding, chartArea, a, b) {\n    return Math.max(maxPadding[a], chartArea[a]) + Math.max(maxPadding[b], chartArea[b]);\n}\nfunction updateMaxPadding(maxPadding, boxPadding) {\n    maxPadding.top = Math.max(maxPadding.top, boxPadding.top);\n    maxPadding.left = Math.max(maxPadding.left, boxPadding.left);\n    maxPadding.bottom = Math.max(maxPadding.bottom, boxPadding.bottom);\n    maxPadding.right = Math.max(maxPadding.right, boxPadding.right);\n}\nfunction updateDims(chartArea, params, layout, stacks) {\n    const { pos , box  } = layout;\n    const maxPadding = chartArea.maxPadding;\n    if (!isObject(pos)) {\n        if (layout.size) {\n            chartArea[pos] -= layout.size;\n        }\n        const stack = stacks[layout.stack] || {\n            size: 0,\n            count: 1\n        };\n        stack.size = Math.max(stack.size, layout.horizontal ? box.height : box.width);\n        layout.size = stack.size / stack.count;\n        chartArea[pos] += layout.size;\n    }\n    if (box.getPadding) {\n        updateMaxPadding(maxPadding, box.getPadding());\n    }\n    const newWidth = Math.max(0, params.outerWidth - getCombinedMax(maxPadding, chartArea, 'left', 'right'));\n    const newHeight = Math.max(0, params.outerHeight - getCombinedMax(maxPadding, chartArea, 'top', 'bottom'));\n    const widthChanged = newWidth !== chartArea.w;\n    const heightChanged = newHeight !== chartArea.h;\n    chartArea.w = newWidth;\n    chartArea.h = newHeight;\n    return layout.horizontal ? {\n        same: widthChanged,\n        other: heightChanged\n    } : {\n        same: heightChanged,\n        other: widthChanged\n    };\n}\nfunction handleMaxPadding(chartArea) {\n    const maxPadding = chartArea.maxPadding;\n    function updatePos(pos) {\n        const change = Math.max(maxPadding[pos] - chartArea[pos], 0);\n        chartArea[pos] += change;\n        return change;\n    }\n    chartArea.y += updatePos('top');\n    chartArea.x += updatePos('left');\n    updatePos('right');\n    updatePos('bottom');\n}\nfunction getMargins(horizontal, chartArea) {\n    const maxPadding = chartArea.maxPadding;\n    function marginForPositions(positions) {\n        const margin = {\n            left: 0,\n            top: 0,\n            right: 0,\n            bottom: 0\n        };\n        positions.forEach((pos)=>{\n            margin[pos] = Math.max(chartArea[pos], maxPadding[pos]);\n        });\n        return margin;\n    }\n    return horizontal ? marginForPositions([\n        'left',\n        'right'\n    ]) : marginForPositions([\n        'top',\n        'bottom'\n    ]);\n}\nfunction fitBoxes(boxes, chartArea, params, stacks) {\n    const refitBoxes = [];\n    let i, ilen, layout, box, refit, changed;\n    for(i = 0, ilen = boxes.length, refit = 0; i < ilen; ++i){\n        layout = boxes[i];\n        box = layout.box;\n        box.update(layout.width || chartArea.w, layout.height || chartArea.h, getMargins(layout.horizontal, chartArea));\n        const { same , other  } = updateDims(chartArea, params, layout, stacks);\n        refit |= same && refitBoxes.length;\n        changed = changed || other;\n        if (!box.fullSize) {\n            refitBoxes.push(layout);\n        }\n    }\n    return refit && fitBoxes(refitBoxes, chartArea, params, stacks) || changed;\n}\nfunction setBoxDims(box, left, top, width, height) {\n    box.top = top;\n    box.left = left;\n    box.right = left + width;\n    box.bottom = top + height;\n    box.width = width;\n    box.height = height;\n}\nfunction placeBoxes(boxes, chartArea, params, stacks) {\n    const userPadding = params.padding;\n    let { x , y  } = chartArea;\n    for (const layout of boxes){\n        const box = layout.box;\n        const stack = stacks[layout.stack] || {\n            count: 1,\n            placed: 0,\n            weight: 1\n        };\n        const weight = layout.stackWeight / stack.weight || 1;\n        if (layout.horizontal) {\n            const width = chartArea.w * weight;\n            const height = stack.size || box.height;\n            if (defined(stack.start)) {\n                y = stack.start;\n            }\n            if (box.fullSize) {\n                setBoxDims(box, userPadding.left, y, params.outerWidth - userPadding.right - userPadding.left, height);\n            } else {\n                setBoxDims(box, chartArea.left + stack.placed, y, width, height);\n            }\n            stack.start = y;\n            stack.placed += width;\n            y = box.bottom;\n        } else {\n            const height = chartArea.h * weight;\n            const width = stack.size || box.width;\n            if (defined(stack.start)) {\n                x = stack.start;\n            }\n            if (box.fullSize) {\n                setBoxDims(box, x, userPadding.top, width, params.outerHeight - userPadding.bottom - userPadding.top);\n            } else {\n                setBoxDims(box, x, chartArea.top + stack.placed, width, height);\n            }\n            stack.start = x;\n            stack.placed += height;\n            x = box.right;\n        }\n    }\n    chartArea.x = x;\n    chartArea.y = y;\n}\nvar layouts = {\n addBox (chart, item) {\n        if (!chart.boxes) {\n            chart.boxes = [];\n        }\n        item.fullSize = item.fullSize || false;\n        item.position = item.position || 'top';\n        item.weight = item.weight || 0;\n        item._layers = item._layers || function() {\n            return [\n                {\n                    z: 0,\n                    draw (chartArea) {\n                        item.draw(chartArea);\n                    }\n                }\n            ];\n        };\n        chart.boxes.push(item);\n    },\n removeBox (chart, layoutItem) {\n        const index = chart.boxes ? chart.boxes.indexOf(layoutItem) : -1;\n        if (index !== -1) {\n            chart.boxes.splice(index, 1);\n        }\n    },\n configure (chart, item, options) {\n        item.fullSize = options.fullSize;\n        item.position = options.position;\n        item.weight = options.weight;\n    },\n update (chart, width, height, minPadding) {\n        if (!chart) {\n            return;\n        }\n        const padding = toPadding(chart.options.layout.padding);\n        const availableWidth = Math.max(width - padding.width, 0);\n        const availableHeight = Math.max(height - padding.height, 0);\n        const boxes = buildLayoutBoxes(chart.boxes);\n        const verticalBoxes = boxes.vertical;\n        const horizontalBoxes = boxes.horizontal;\n        each(chart.boxes, (box)=>{\n            if (typeof box.beforeLayout === 'function') {\n                box.beforeLayout();\n            }\n        });\n        const visibleVerticalBoxCount = verticalBoxes.reduce((total, wrap)=>wrap.box.options && wrap.box.options.display === false ? total : total + 1, 0) || 1;\n        const params = Object.freeze({\n            outerWidth: width,\n            outerHeight: height,\n            padding,\n            availableWidth,\n            availableHeight,\n            vBoxMaxWidth: availableWidth / 2 / visibleVerticalBoxCount,\n            hBoxMaxHeight: availableHeight / 2\n        });\n        const maxPadding = Object.assign({}, padding);\n        updateMaxPadding(maxPadding, toPadding(minPadding));\n        const chartArea = Object.assign({\n            maxPadding,\n            w: availableWidth,\n            h: availableHeight,\n            x: padding.left,\n            y: padding.top\n        }, padding);\n        const stacks = setLayoutDims(verticalBoxes.concat(horizontalBoxes), params);\n        fitBoxes(boxes.fullSize, chartArea, params, stacks);\n        fitBoxes(verticalBoxes, chartArea, params, stacks);\n        if (fitBoxes(horizontalBoxes, chartArea, params, stacks)) {\n            fitBoxes(verticalBoxes, chartArea, params, stacks);\n        }\n        handleMaxPadding(chartArea);\n        placeBoxes(boxes.leftAndTop, chartArea, params, stacks);\n        chartArea.x += chartArea.w;\n        chartArea.y += chartArea.h;\n        placeBoxes(boxes.rightAndBottom, chartArea, params, stacks);\n        chart.chartArea = {\n            left: chartArea.left,\n            top: chartArea.top,\n            right: chartArea.left + chartArea.w,\n            bottom: chartArea.top + chartArea.h,\n            height: chartArea.h,\n            width: chartArea.w\n        };\n        each(boxes.chartArea, (layout)=>{\n            const box = layout.box;\n            Object.assign(box, chart.chartArea);\n            box.update(chartArea.w, chartArea.h, {\n                left: 0,\n                top: 0,\n                right: 0,\n                bottom: 0\n            });\n        });\n    }\n};\n\nclass BasePlatform {\n acquireContext(canvas, aspectRatio) {}\n releaseContext(context) {\n        return false;\n    }\n addEventListener(chart, type, listener) {}\n removeEventListener(chart, type, listener) {}\n getDevicePixelRatio() {\n        return 1;\n    }\n getMaximumSize(element, width, height, aspectRatio) {\n        width = Math.max(0, width || element.width);\n        height = height || element.height;\n        return {\n            width,\n            height: Math.max(0, aspectRatio ? Math.floor(width / aspectRatio) : height)\n        };\n    }\n isAttached(canvas) {\n        return true;\n    }\n updateConfig(config) {\n    }\n}\n\nclass BasicPlatform extends BasePlatform {\n    acquireContext(item) {\n        return item && item.getContext && item.getContext('2d') || null;\n    }\n    updateConfig(config) {\n        config.options.animation = false;\n    }\n}\n\nconst EXPANDO_KEY = '$chartjs';\n const EVENT_TYPES = {\n    touchstart: 'mousedown',\n    touchmove: 'mousemove',\n    touchend: 'mouseup',\n    pointerenter: 'mouseenter',\n    pointerdown: 'mousedown',\n    pointermove: 'mousemove',\n    pointerup: 'mouseup',\n    pointerleave: 'mouseout',\n    pointerout: 'mouseout'\n};\nconst isNullOrEmpty = (value)=>value === null || value === '';\n function initCanvas(canvas, aspectRatio) {\n    const style = canvas.style;\n    const renderHeight = canvas.getAttribute('height');\n    const renderWidth = canvas.getAttribute('width');\n    canvas[EXPANDO_KEY] = {\n        initial: {\n            height: renderHeight,\n            width: renderWidth,\n            style: {\n                display: style.display,\n                height: style.height,\n                width: style.width\n            }\n        }\n    };\n    style.display = style.display || 'block';\n    style.boxSizing = style.boxSizing || 'border-box';\n    if (isNullOrEmpty(renderWidth)) {\n        const displayWidth = readUsedSize(canvas, 'width');\n        if (displayWidth !== undefined) {\n            canvas.width = displayWidth;\n        }\n    }\n    if (isNullOrEmpty(renderHeight)) {\n        if (canvas.style.height === '') {\n            canvas.height = canvas.width / (aspectRatio || 2);\n        } else {\n            const displayHeight = readUsedSize(canvas, 'height');\n            if (displayHeight !== undefined) {\n                canvas.height = displayHeight;\n            }\n        }\n    }\n    return canvas;\n}\nconst eventListenerOptions = supportsEventListenerOptions ? {\n    passive: true\n} : false;\nfunction addListener(node, type, listener) {\n    if (node) {\n        node.addEventListener(type, listener, eventListenerOptions);\n    }\n}\nfunction removeListener(chart, type, listener) {\n    if (chart && chart.canvas) {\n        chart.canvas.removeEventListener(type, listener, eventListenerOptions);\n    }\n}\nfunction fromNativeEvent(event, chart) {\n    const type = EVENT_TYPES[event.type] || event.type;\n    const { x , y  } = getRelativePosition(event, chart);\n    return {\n        type,\n        chart,\n        native: event,\n        x: x !== undefined ? x : null,\n        y: y !== undefined ? y : null\n    };\n}\nfunction nodeListContains(nodeList, canvas) {\n    for (const node of nodeList){\n        if (node === canvas || node.contains(canvas)) {\n            return true;\n        }\n    }\n}\nfunction createAttachObserver(chart, type, listener) {\n    const canvas = chart.canvas;\n    const observer = new MutationObserver((entries)=>{\n        let trigger = false;\n        for (const entry of entries){\n            trigger = trigger || nodeListContains(entry.addedNodes, canvas);\n            trigger = trigger && !nodeListContains(entry.removedNodes, canvas);\n        }\n        if (trigger) {\n            listener();\n        }\n    });\n    observer.observe(document, {\n        childList: true,\n        subtree: true\n    });\n    return observer;\n}\nfunction createDetachObserver(chart, type, listener) {\n    const canvas = chart.canvas;\n    const observer = new MutationObserver((entries)=>{\n        let trigger = false;\n        for (const entry of entries){\n            trigger = trigger || nodeListContains(entry.removedNodes, canvas);\n            trigger = trigger && !nodeListContains(entry.addedNodes, canvas);\n        }\n        if (trigger) {\n            listener();\n        }\n    });\n    observer.observe(document, {\n        childList: true,\n        subtree: true\n    });\n    return observer;\n}\nconst drpListeningCharts = new Map();\nlet oldDevicePixelRatio = 0;\nfunction onWindowResize() {\n    const dpr = window.devicePixelRatio;\n    if (dpr === oldDevicePixelRatio) {\n        return;\n    }\n    oldDevicePixelRatio = dpr;\n    drpListeningCharts.forEach((resize, chart)=>{\n        if (chart.currentDevicePixelRatio !== dpr) {\n            resize();\n        }\n    });\n}\nfunction listenDevicePixelRatioChanges(chart, resize) {\n    if (!drpListeningCharts.size) {\n        window.addEventListener('resize', onWindowResize);\n    }\n    drpListeningCharts.set(chart, resize);\n}\nfunction unlistenDevicePixelRatioChanges(chart) {\n    drpListeningCharts.delete(chart);\n    if (!drpListeningCharts.size) {\n        window.removeEventListener('resize', onWindowResize);\n    }\n}\nfunction createResizeObserver(chart, type, listener) {\n    const canvas = chart.canvas;\n    const container = canvas && _getParentNode(canvas);\n    if (!container) {\n        return;\n    }\n    const resize = throttled((width, height)=>{\n        const w = container.clientWidth;\n        listener(width, height);\n        if (w < container.clientWidth) {\n            listener();\n        }\n    }, window);\n    const observer = new ResizeObserver((entries)=>{\n        const entry = entries[0];\n        const width = entry.contentRect.width;\n        const height = entry.contentRect.height;\n        if (width === 0 && height === 0) {\n            return;\n        }\n        resize(width, height);\n    });\n    observer.observe(container);\n    listenDevicePixelRatioChanges(chart, resize);\n    return observer;\n}\nfunction releaseObserver(chart, type, observer) {\n    if (observer) {\n        observer.disconnect();\n    }\n    if (type === 'resize') {\n        unlistenDevicePixelRatioChanges(chart);\n    }\n}\nfunction createProxyAndListen(chart, type, listener) {\n    const canvas = chart.canvas;\n    const proxy = throttled((event)=>{\n        if (chart.ctx !== null) {\n            listener(fromNativeEvent(event, chart));\n        }\n    }, chart);\n    addListener(canvas, type, proxy);\n    return proxy;\n}\n class DomPlatform extends BasePlatform {\n acquireContext(canvas, aspectRatio) {\n        const context = canvas && canvas.getContext && canvas.getContext('2d');\n        if (context && context.canvas === canvas) {\n            initCanvas(canvas, aspectRatio);\n            return context;\n        }\n        return null;\n    }\n releaseContext(context) {\n        const canvas = context.canvas;\n        if (!canvas[EXPANDO_KEY]) {\n            return false;\n        }\n        const initial = canvas[EXPANDO_KEY].initial;\n        [\n            'height',\n            'width'\n        ].forEach((prop)=>{\n            const value = initial[prop];\n            if (isNullOrUndef(value)) {\n                canvas.removeAttribute(prop);\n            } else {\n                canvas.setAttribute(prop, value);\n            }\n        });\n        const style = initial.style || {};\n        Object.keys(style).forEach((key)=>{\n            canvas.style[key] = style[key];\n        });\n        canvas.width = canvas.width;\n        delete canvas[EXPANDO_KEY];\n        return true;\n    }\n addEventListener(chart, type, listener) {\n        this.removeEventListener(chart, type);\n        const proxies = chart.$proxies || (chart.$proxies = {});\n        const handlers = {\n            attach: createAttachObserver,\n            detach: createDetachObserver,\n            resize: createResizeObserver\n        };\n        const handler = handlers[type] || createProxyAndListen;\n        proxies[type] = handler(chart, type, listener);\n    }\n removeEventListener(chart, type) {\n        const proxies = chart.$proxies || (chart.$proxies = {});\n        const proxy = proxies[type];\n        if (!proxy) {\n            return;\n        }\n        const handlers = {\n            attach: releaseObserver,\n            detach: releaseObserver,\n            resize: releaseObserver\n        };\n        const handler = handlers[type] || removeListener;\n        handler(chart, type, proxy);\n        proxies[type] = undefined;\n    }\n    getDevicePixelRatio() {\n        return window.devicePixelRatio;\n    }\n getMaximumSize(canvas, width, height, aspectRatio) {\n        return getMaximumSize(canvas, width, height, aspectRatio);\n    }\n isAttached(canvas) {\n        const container = _getParentNode(canvas);\n        return !!(container && container.isConnected);\n    }\n}\n\nfunction _detectPlatform(canvas) {\n    if (!_isDomSupported() || typeof OffscreenCanvas !== 'undefined' && canvas instanceof OffscreenCanvas) {\n        return BasicPlatform;\n    }\n    return DomPlatform;\n}\n\nclass Element {\n    static defaults = {};\n    static defaultRoutes = undefined;\n    x;\n    y;\n    active = false;\n    options;\n    $animations;\n    tooltipPosition(useFinalPosition) {\n        const { x , y  } = this.getProps([\n            'x',\n            'y'\n        ], useFinalPosition);\n        return {\n            x,\n            y\n        };\n    }\n    hasValue() {\n        return isNumber(this.x) && isNumber(this.y);\n    }\n    getProps(props, final) {\n        const anims = this.$animations;\n        if (!final || !anims) {\n            // let's not create an object, if not needed\n            return this;\n        }\n        const ret = {};\n        props.forEach((prop)=>{\n            ret[prop] = anims[prop] && anims[prop].active() ? anims[prop]._to : this[prop];\n        });\n        return ret;\n    }\n}\n\nfunction autoSkip(scale, ticks) {\n    const tickOpts = scale.options.ticks;\n    const determinedMaxTicks = determineMaxTicks(scale);\n    const ticksLimit = Math.min(tickOpts.maxTicksLimit || determinedMaxTicks, determinedMaxTicks);\n    const majorIndices = tickOpts.major.enabled ? getMajorIndices(ticks) : [];\n    const numMajorIndices = majorIndices.length;\n    const first = majorIndices[0];\n    const last = majorIndices[numMajorIndices - 1];\n    const newTicks = [];\n    if (numMajorIndices > ticksLimit) {\n        skipMajors(ticks, newTicks, majorIndices, numMajorIndices / ticksLimit);\n        return newTicks;\n    }\n    const spacing = calculateSpacing(majorIndices, ticks, ticksLimit);\n    if (numMajorIndices > 0) {\n        let i, ilen;\n        const avgMajorSpacing = numMajorIndices > 1 ? Math.round((last - first) / (numMajorIndices - 1)) : null;\n        skip(ticks, newTicks, spacing, isNullOrUndef(avgMajorSpacing) ? 0 : first - avgMajorSpacing, first);\n        for(i = 0, ilen = numMajorIndices - 1; i < ilen; i++){\n            skip(ticks, newTicks, spacing, majorIndices[i], majorIndices[i + 1]);\n        }\n        skip(ticks, newTicks, spacing, last, isNullOrUndef(avgMajorSpacing) ? ticks.length : last + avgMajorSpacing);\n        return newTicks;\n    }\n    skip(ticks, newTicks, spacing);\n    return newTicks;\n}\nfunction determineMaxTicks(scale) {\n    const offset = scale.options.offset;\n    const tickLength = scale._tickSize();\n    const maxScale = scale._length / tickLength + (offset ? 0 : 1);\n    const maxChart = scale._maxLength / tickLength;\n    return Math.floor(Math.min(maxScale, maxChart));\n}\n function calculateSpacing(majorIndices, ticks, ticksLimit) {\n    const evenMajorSpacing = getEvenSpacing(majorIndices);\n    const spacing = ticks.length / ticksLimit;\n    if (!evenMajorSpacing) {\n        return Math.max(spacing, 1);\n    }\n    const factors = _factorize(evenMajorSpacing);\n    for(let i = 0, ilen = factors.length - 1; i < ilen; i++){\n        const factor = factors[i];\n        if (factor > spacing) {\n            return factor;\n        }\n    }\n    return Math.max(spacing, 1);\n}\n function getMajorIndices(ticks) {\n    const result = [];\n    let i, ilen;\n    for(i = 0, ilen = ticks.length; i < ilen; i++){\n        if (ticks[i].major) {\n            result.push(i);\n        }\n    }\n    return result;\n}\n function skipMajors(ticks, newTicks, majorIndices, spacing) {\n    let count = 0;\n    let next = majorIndices[0];\n    let i;\n    spacing = Math.ceil(spacing);\n    for(i = 0; i < ticks.length; i++){\n        if (i === next) {\n            newTicks.push(ticks[i]);\n            count++;\n            next = majorIndices[count * spacing];\n        }\n    }\n}\n function skip(ticks, newTicks, spacing, majorStart, majorEnd) {\n    const start = valueOrDefault(majorStart, 0);\n    const end = Math.min(valueOrDefault(majorEnd, ticks.length), ticks.length);\n    let count = 0;\n    let length, i, next;\n    spacing = Math.ceil(spacing);\n    if (majorEnd) {\n        length = majorEnd - majorStart;\n        spacing = length / Math.floor(length / spacing);\n    }\n    next = start;\n    while(next < 0){\n        count++;\n        next = Math.round(start + count * spacing);\n    }\n    for(i = Math.max(start, 0); i < end; i++){\n        if (i === next) {\n            newTicks.push(ticks[i]);\n            count++;\n            next = Math.round(start + count * spacing);\n        }\n    }\n}\n function getEvenSpacing(arr) {\n    const len = arr.length;\n    let i, diff;\n    if (len < 2) {\n        return false;\n    }\n    for(diff = arr[0], i = 1; i < len; ++i){\n        if (arr[i] - arr[i - 1] !== diff) {\n            return false;\n        }\n    }\n    return diff;\n}\n\nconst reverseAlign = (align)=>align === 'left' ? 'right' : align === 'right' ? 'left' : align;\nconst offsetFromEdge = (scale, edge, offset)=>edge === 'top' || edge === 'left' ? scale[edge] + offset : scale[edge] - offset;\nconst getTicksLimit = (ticksLength, maxTicksLimit)=>Math.min(maxTicksLimit || ticksLength, ticksLength);\n function sample(arr, numItems) {\n    const result = [];\n    const increment = arr.length / numItems;\n    const len = arr.length;\n    let i = 0;\n    for(; i < len; i += increment){\n        result.push(arr[Math.floor(i)]);\n    }\n    return result;\n}\n function getPixelForGridLine(scale, index, offsetGridLines) {\n    const length = scale.ticks.length;\n    const validIndex = Math.min(index, length - 1);\n    const start = scale._startPixel;\n    const end = scale._endPixel;\n    const epsilon = 1e-6;\n    let lineValue = scale.getPixelForTick(validIndex);\n    let offset;\n    if (offsetGridLines) {\n        if (length === 1) {\n            offset = Math.max(lineValue - start, end - lineValue);\n        } else if (index === 0) {\n            offset = (scale.getPixelForTick(1) - lineValue) / 2;\n        } else {\n            offset = (lineValue - scale.getPixelForTick(validIndex - 1)) / 2;\n        }\n        lineValue += validIndex < index ? offset : -offset;\n        if (lineValue < start - epsilon || lineValue > end + epsilon) {\n            return;\n        }\n    }\n    return lineValue;\n}\n function garbageCollect(caches, length) {\n    each(caches, (cache)=>{\n        const gc = cache.gc;\n        const gcLen = gc.length / 2;\n        let i;\n        if (gcLen > length) {\n            for(i = 0; i < gcLen; ++i){\n                delete cache.data[gc[i]];\n            }\n            gc.splice(0, gcLen);\n        }\n    });\n}\n function getTickMarkLength(options) {\n    return options.drawTicks ? options.tickLength : 0;\n}\n function getTitleHeight(options, fallback) {\n    if (!options.display) {\n        return 0;\n    }\n    const font = toFont(options.font, fallback);\n    const padding = toPadding(options.padding);\n    const lines = isArray(options.text) ? options.text.length : 1;\n    return lines * font.lineHeight + padding.height;\n}\nfunction createScaleContext(parent, scale) {\n    return createContext(parent, {\n        scale,\n        type: 'scale'\n    });\n}\nfunction createTickContext(parent, index, tick) {\n    return createContext(parent, {\n        tick,\n        index,\n        type: 'tick'\n    });\n}\nfunction titleAlign(align, position, reverse) {\n     let ret = _toLeftRightCenter(align);\n    if (reverse && position !== 'right' || !reverse && position === 'right') {\n        ret = reverseAlign(ret);\n    }\n    return ret;\n}\nfunction titleArgs(scale, offset, position, align) {\n    const { top , left , bottom , right , chart  } = scale;\n    const { chartArea , scales  } = chart;\n    let rotation = 0;\n    let maxWidth, titleX, titleY;\n    const height = bottom - top;\n    const width = right - left;\n    if (scale.isHorizontal()) {\n        titleX = _alignStartEnd(align, left, right);\n        if (isObject(position)) {\n            const positionAxisID = Object.keys(position)[0];\n            const value = position[positionAxisID];\n            titleY = scales[positionAxisID].getPixelForValue(value) + height - offset;\n        } else if (position === 'center') {\n            titleY = (chartArea.bottom + chartArea.top) / 2 + height - offset;\n        } else {\n            titleY = offsetFromEdge(scale, position, offset);\n        }\n        maxWidth = right - left;\n    } else {\n        if (isObject(position)) {\n            const positionAxisID = Object.keys(position)[0];\n            const value = position[positionAxisID];\n            titleX = scales[positionAxisID].getPixelForValue(value) - width + offset;\n        } else if (position === 'center') {\n            titleX = (chartArea.left + chartArea.right) / 2 - width + offset;\n        } else {\n            titleX = offsetFromEdge(scale, position, offset);\n        }\n        titleY = _alignStartEnd(align, bottom, top);\n        rotation = position === 'left' ? -HALF_PI : HALF_PI;\n    }\n    return {\n        titleX,\n        titleY,\n        maxWidth,\n        rotation\n    };\n}\nclass Scale extends Element {\n    constructor(cfg){\n        super();\n         this.id = cfg.id;\n         this.type = cfg.type;\n         this.options = undefined;\n         this.ctx = cfg.ctx;\n         this.chart = cfg.chart;\n         this.top = undefined;\n         this.bottom = undefined;\n         this.left = undefined;\n         this.right = undefined;\n         this.width = undefined;\n         this.height = undefined;\n        this._margins = {\n            left: 0,\n            right: 0,\n            top: 0,\n            bottom: 0\n        };\n         this.maxWidth = undefined;\n         this.maxHeight = undefined;\n         this.paddingTop = undefined;\n         this.paddingBottom = undefined;\n         this.paddingLeft = undefined;\n         this.paddingRight = undefined;\n         this.axis = undefined;\n         this.labelRotation = undefined;\n        this.min = undefined;\n        this.max = undefined;\n        this._range = undefined;\n         this.ticks = [];\n         this._gridLineItems = null;\n         this._labelItems = null;\n         this._labelSizes = null;\n        this._length = 0;\n        this._maxLength = 0;\n        this._longestTextCache = {};\n         this._startPixel = undefined;\n         this._endPixel = undefined;\n        this._reversePixels = false;\n        this._userMax = undefined;\n        this._userMin = undefined;\n        this._suggestedMax = undefined;\n        this._suggestedMin = undefined;\n        this._ticksLength = 0;\n        this._borderValue = 0;\n        this._cache = {};\n        this._dataLimitsCached = false;\n        this.$context = undefined;\n    }\n init(options) {\n        this.options = options.setContext(this.getContext());\n        this.axis = options.axis;\n        this._userMin = this.parse(options.min);\n        this._userMax = this.parse(options.max);\n        this._suggestedMin = this.parse(options.suggestedMin);\n        this._suggestedMax = this.parse(options.suggestedMax);\n    }\n parse(raw, index) {\n        return raw;\n    }\n getUserBounds() {\n        let { _userMin , _userMax , _suggestedMin , _suggestedMax  } = this;\n        _userMin = finiteOrDefault(_userMin, Number.POSITIVE_INFINITY);\n        _userMax = finiteOrDefault(_userMax, Number.NEGATIVE_INFINITY);\n        _suggestedMin = finiteOrDefault(_suggestedMin, Number.POSITIVE_INFINITY);\n        _suggestedMax = finiteOrDefault(_suggestedMax, Number.NEGATIVE_INFINITY);\n        return {\n            min: finiteOrDefault(_userMin, _suggestedMin),\n            max: finiteOrDefault(_userMax, _suggestedMax),\n            minDefined: isNumberFinite(_userMin),\n            maxDefined: isNumberFinite(_userMax)\n        };\n    }\n getMinMax(canStack) {\n        let { min , max , minDefined , maxDefined  } = this.getUserBounds();\n        let range;\n        if (minDefined && maxDefined) {\n            return {\n                min,\n                max\n            };\n        }\n        const metas = this.getMatchingVisibleMetas();\n        for(let i = 0, ilen = metas.length; i < ilen; ++i){\n            range = metas[i].controller.getMinMax(this, canStack);\n            if (!minDefined) {\n                min = Math.min(min, range.min);\n            }\n            if (!maxDefined) {\n                max = Math.max(max, range.max);\n            }\n        }\n        min = maxDefined && min > max ? max : min;\n        max = minDefined && min > max ? min : max;\n        return {\n            min: finiteOrDefault(min, finiteOrDefault(max, min)),\n            max: finiteOrDefault(max, finiteOrDefault(min, max))\n        };\n    }\n getPadding() {\n        return {\n            left: this.paddingLeft || 0,\n            top: this.paddingTop || 0,\n            right: this.paddingRight || 0,\n            bottom: this.paddingBottom || 0\n        };\n    }\n getTicks() {\n        return this.ticks;\n    }\n getLabels() {\n        const data = this.chart.data;\n        return this.options.labels || (this.isHorizontal() ? data.xLabels : data.yLabels) || data.labels || [];\n    }\n getLabelItems(chartArea = this.chart.chartArea) {\n        const items = this._labelItems || (this._labelItems = this._computeLabelItems(chartArea));\n        return items;\n    }\n    beforeLayout() {\n        this._cache = {};\n        this._dataLimitsCached = false;\n    }\n    beforeUpdate() {\n        callback(this.options.beforeUpdate, [\n            this\n        ]);\n    }\n update(maxWidth, maxHeight, margins) {\n        const { beginAtZero , grace , ticks: tickOpts  } = this.options;\n        const sampleSize = tickOpts.sampleSize;\n        this.beforeUpdate();\n        this.maxWidth = maxWidth;\n        this.maxHeight = maxHeight;\n        this._margins = margins = Object.assign({\n            left: 0,\n            right: 0,\n            top: 0,\n            bottom: 0\n        }, margins);\n        this.ticks = null;\n        this._labelSizes = null;\n        this._gridLineItems = null;\n        this._labelItems = null;\n        this.beforeSetDimensions();\n        this.setDimensions();\n        this.afterSetDimensions();\n        this._maxLength = this.isHorizontal() ? this.width + margins.left + margins.right : this.height + margins.top + margins.bottom;\n        if (!this._dataLimitsCached) {\n            this.beforeDataLimits();\n            this.determineDataLimits();\n            this.afterDataLimits();\n            this._range = _addGrace(this, grace, beginAtZero);\n            this._dataLimitsCached = true;\n        }\n        this.beforeBuildTicks();\n        this.ticks = this.buildTicks() || [];\n        this.afterBuildTicks();\n        const samplingEnabled = sampleSize < this.ticks.length;\n        this._convertTicksToLabels(samplingEnabled ? sample(this.ticks, sampleSize) : this.ticks);\n        this.configure();\n        this.beforeCalculateLabelRotation();\n        this.calculateLabelRotation();\n        this.afterCalculateLabelRotation();\n        if (tickOpts.display && (tickOpts.autoSkip || tickOpts.source === 'auto')) {\n            this.ticks = autoSkip(this, this.ticks);\n            this._labelSizes = null;\n            this.afterAutoSkip();\n        }\n        if (samplingEnabled) {\n            this._convertTicksToLabels(this.ticks);\n        }\n        this.beforeFit();\n        this.fit();\n        this.afterFit();\n        this.afterUpdate();\n    }\n configure() {\n        let reversePixels = this.options.reverse;\n        let startPixel, endPixel;\n        if (this.isHorizontal()) {\n            startPixel = this.left;\n            endPixel = this.right;\n        } else {\n            startPixel = this.top;\n            endPixel = this.bottom;\n            reversePixels = !reversePixels;\n        }\n        this._startPixel = startPixel;\n        this._endPixel = endPixel;\n        this._reversePixels = reversePixels;\n        this._length = endPixel - startPixel;\n        this._alignToPixels = this.options.alignToPixels;\n    }\n    afterUpdate() {\n        callback(this.options.afterUpdate, [\n            this\n        ]);\n    }\n    beforeSetDimensions() {\n        callback(this.options.beforeSetDimensions, [\n            this\n        ]);\n    }\n    setDimensions() {\n        if (this.isHorizontal()) {\n            this.width = this.maxWidth;\n            this.left = 0;\n            this.right = this.width;\n        } else {\n            this.height = this.maxHeight;\n            this.top = 0;\n            this.bottom = this.height;\n        }\n        this.paddingLeft = 0;\n        this.paddingTop = 0;\n        this.paddingRight = 0;\n        this.paddingBottom = 0;\n    }\n    afterSetDimensions() {\n        callback(this.options.afterSetDimensions, [\n            this\n        ]);\n    }\n    _callHooks(name) {\n        this.chart.notifyPlugins(name, this.getContext());\n        callback(this.options[name], [\n            this\n        ]);\n    }\n    beforeDataLimits() {\n        this._callHooks('beforeDataLimits');\n    }\n    determineDataLimits() {}\n    afterDataLimits() {\n        this._callHooks('afterDataLimits');\n    }\n    beforeBuildTicks() {\n        this._callHooks('beforeBuildTicks');\n    }\n buildTicks() {\n        return [];\n    }\n    afterBuildTicks() {\n        this._callHooks('afterBuildTicks');\n    }\n    beforeTickToLabelConversion() {\n        callback(this.options.beforeTickToLabelConversion, [\n            this\n        ]);\n    }\n generateTickLabels(ticks) {\n        const tickOpts = this.options.ticks;\n        let i, ilen, tick;\n        for(i = 0, ilen = ticks.length; i < ilen; i++){\n            tick = ticks[i];\n            tick.label = callback(tickOpts.callback, [\n                tick.value,\n                i,\n                ticks\n            ], this);\n        }\n    }\n    afterTickToLabelConversion() {\n        callback(this.options.afterTickToLabelConversion, [\n            this\n        ]);\n    }\n    beforeCalculateLabelRotation() {\n        callback(this.options.beforeCalculateLabelRotation, [\n            this\n        ]);\n    }\n    calculateLabelRotation() {\n        const options = this.options;\n        const tickOpts = options.ticks;\n        const numTicks = getTicksLimit(this.ticks.length, options.ticks.maxTicksLimit);\n        const minRotation = tickOpts.minRotation || 0;\n        const maxRotation = tickOpts.maxRotation;\n        let labelRotation = minRotation;\n        let tickWidth, maxHeight, maxLabelDiagonal;\n        if (!this._isVisible() || !tickOpts.display || minRotation >= maxRotation || numTicks <= 1 || !this.isHorizontal()) {\n            this.labelRotation = minRotation;\n            return;\n        }\n        const labelSizes = this._getLabelSizes();\n        const maxLabelWidth = labelSizes.widest.width;\n        const maxLabelHeight = labelSizes.highest.height;\n        const maxWidth = _limitValue(this.chart.width - maxLabelWidth, 0, this.maxWidth);\n        tickWidth = options.offset ? this.maxWidth / numTicks : maxWidth / (numTicks - 1);\n        if (maxLabelWidth + 6 > tickWidth) {\n            tickWidth = maxWidth / (numTicks - (options.offset ? 0.5 : 1));\n            maxHeight = this.maxHeight - getTickMarkLength(options.grid) - tickOpts.padding - getTitleHeight(options.title, this.chart.options.font);\n            maxLabelDiagonal = Math.sqrt(maxLabelWidth * maxLabelWidth + maxLabelHeight * maxLabelHeight);\n            labelRotation = toDegrees(Math.min(Math.asin(_limitValue((labelSizes.highest.height + 6) / tickWidth, -1, 1)), Math.asin(_limitValue(maxHeight / maxLabelDiagonal, -1, 1)) - Math.asin(_limitValue(maxLabelHeight / maxLabelDiagonal, -1, 1))));\n            labelRotation = Math.max(minRotation, Math.min(maxRotation, labelRotation));\n        }\n        this.labelRotation = labelRotation;\n    }\n    afterCalculateLabelRotation() {\n        callback(this.options.afterCalculateLabelRotation, [\n            this\n        ]);\n    }\n    afterAutoSkip() {}\n    beforeFit() {\n        callback(this.options.beforeFit, [\n            this\n        ]);\n    }\n    fit() {\n        const minSize = {\n            width: 0,\n            height: 0\n        };\n        const { chart , options: { ticks: tickOpts , title: titleOpts , grid: gridOpts  }  } = this;\n        const display = this._isVisible();\n        const isHorizontal = this.isHorizontal();\n        if (display) {\n            const titleHeight = getTitleHeight(titleOpts, chart.options.font);\n            if (isHorizontal) {\n                minSize.width = this.maxWidth;\n                minSize.height = getTickMarkLength(gridOpts) + titleHeight;\n            } else {\n                minSize.height = this.maxHeight;\n                minSize.width = getTickMarkLength(gridOpts) + titleHeight;\n            }\n            if (tickOpts.display && this.ticks.length) {\n                const { first , last , widest , highest  } = this._getLabelSizes();\n                const tickPadding = tickOpts.padding * 2;\n                const angleRadians = toRadians(this.labelRotation);\n                const cos = Math.cos(angleRadians);\n                const sin = Math.sin(angleRadians);\n                if (isHorizontal) {\n                    const labelHeight = tickOpts.mirror ? 0 : sin * widest.width + cos * highest.height;\n                    minSize.height = Math.min(this.maxHeight, minSize.height + labelHeight + tickPadding);\n                } else {\n                    const labelWidth = tickOpts.mirror ? 0 : cos * widest.width + sin * highest.height;\n                    minSize.width = Math.min(this.maxWidth, minSize.width + labelWidth + tickPadding);\n                }\n                this._calculatePadding(first, last, sin, cos);\n            }\n        }\n        this._handleMargins();\n        if (isHorizontal) {\n            this.width = this._length = chart.width - this._margins.left - this._margins.right;\n            this.height = minSize.height;\n        } else {\n            this.width = minSize.width;\n            this.height = this._length = chart.height - this._margins.top - this._margins.bottom;\n        }\n    }\n    _calculatePadding(first, last, sin, cos) {\n        const { ticks: { align , padding  } , position  } = this.options;\n        const isRotated = this.labelRotation !== 0;\n        const labelsBelowTicks = position !== 'top' && this.axis === 'x';\n        if (this.isHorizontal()) {\n            const offsetLeft = this.getPixelForTick(0) - this.left;\n            const offsetRight = this.right - this.getPixelForTick(this.ticks.length - 1);\n            let paddingLeft = 0;\n            let paddingRight = 0;\n            if (isRotated) {\n                if (labelsBelowTicks) {\n                    paddingLeft = cos * first.width;\n                    paddingRight = sin * last.height;\n                } else {\n                    paddingLeft = sin * first.height;\n                    paddingRight = cos * last.width;\n                }\n            } else if (align === 'start') {\n                paddingRight = last.width;\n            } else if (align === 'end') {\n                paddingLeft = first.width;\n            } else if (align !== 'inner') {\n                paddingLeft = first.width / 2;\n                paddingRight = last.width / 2;\n            }\n            this.paddingLeft = Math.max((paddingLeft - offsetLeft + padding) * this.width / (this.width - offsetLeft), 0);\n            this.paddingRight = Math.max((paddingRight - offsetRight + padding) * this.width / (this.width - offsetRight), 0);\n        } else {\n            let paddingTop = last.height / 2;\n            let paddingBottom = first.height / 2;\n            if (align === 'start') {\n                paddingTop = 0;\n                paddingBottom = first.height;\n            } else if (align === 'end') {\n                paddingTop = last.height;\n                paddingBottom = 0;\n            }\n            this.paddingTop = paddingTop + padding;\n            this.paddingBottom = paddingBottom + padding;\n        }\n    }\n _handleMargins() {\n        if (this._margins) {\n            this._margins.left = Math.max(this.paddingLeft, this._margins.left);\n            this._margins.top = Math.max(this.paddingTop, this._margins.top);\n            this._margins.right = Math.max(this.paddingRight, this._margins.right);\n            this._margins.bottom = Math.max(this.paddingBottom, this._margins.bottom);\n        }\n    }\n    afterFit() {\n        callback(this.options.afterFit, [\n            this\n        ]);\n    }\n isHorizontal() {\n        const { axis , position  } = this.options;\n        return position === 'top' || position === 'bottom' || axis === 'x';\n    }\n isFullSize() {\n        return this.options.fullSize;\n    }\n _convertTicksToLabels(ticks) {\n        this.beforeTickToLabelConversion();\n        this.generateTickLabels(ticks);\n        let i, ilen;\n        for(i = 0, ilen = ticks.length; i < ilen; i++){\n            if (isNullOrUndef(ticks[i].label)) {\n                ticks.splice(i, 1);\n                ilen--;\n                i--;\n            }\n        }\n        this.afterTickToLabelConversion();\n    }\n _getLabelSizes() {\n        let labelSizes = this._labelSizes;\n        if (!labelSizes) {\n            const sampleSize = this.options.ticks.sampleSize;\n            let ticks = this.ticks;\n            if (sampleSize < ticks.length) {\n                ticks = sample(ticks, sampleSize);\n            }\n            this._labelSizes = labelSizes = this._computeLabelSizes(ticks, ticks.length, this.options.ticks.maxTicksLimit);\n        }\n        return labelSizes;\n    }\n _computeLabelSizes(ticks, length, maxTicksLimit) {\n        const { ctx , _longestTextCache: caches  } = this;\n        const widths = [];\n        const heights = [];\n        const increment = Math.floor(length / getTicksLimit(length, maxTicksLimit));\n        let widestLabelSize = 0;\n        let highestLabelSize = 0;\n        let i, j, jlen, label, tickFont, fontString, cache, lineHeight, width, height, nestedLabel;\n        for(i = 0; i < length; i += increment){\n            label = ticks[i].label;\n            tickFont = this._resolveTickFontOptions(i);\n            ctx.font = fontString = tickFont.string;\n            cache = caches[fontString] = caches[fontString] || {\n                data: {},\n                gc: []\n            };\n            lineHeight = tickFont.lineHeight;\n            width = height = 0;\n            if (!isNullOrUndef(label) && !isArray(label)) {\n                width = _measureText(ctx, cache.data, cache.gc, width, label);\n                height = lineHeight;\n            } else if (isArray(label)) {\n                for(j = 0, jlen = label.length; j < jlen; ++j){\n                    nestedLabel =  label[j];\n                    if (!isNullOrUndef(nestedLabel) && !isArray(nestedLabel)) {\n                        width = _measureText(ctx, cache.data, cache.gc, width, nestedLabel);\n                        height += lineHeight;\n                    }\n                }\n            }\n            widths.push(width);\n            heights.push(height);\n            widestLabelSize = Math.max(width, widestLabelSize);\n            highestLabelSize = Math.max(height, highestLabelSize);\n        }\n        garbageCollect(caches, length);\n        const widest = widths.indexOf(widestLabelSize);\n        const highest = heights.indexOf(highestLabelSize);\n        const valueAt = (idx)=>({\n                width: widths[idx] || 0,\n                height: heights[idx] || 0\n            });\n        return {\n            first: valueAt(0),\n            last: valueAt(length - 1),\n            widest: valueAt(widest),\n            highest: valueAt(highest),\n            widths,\n            heights\n        };\n    }\n getLabelForValue(value) {\n        return value;\n    }\n getPixelForValue(value, index) {\n        return NaN;\n    }\n getValueForPixel(pixel) {}\n getPixelForTick(index) {\n        const ticks = this.ticks;\n        if (index < 0 || index > ticks.length - 1) {\n            return null;\n        }\n        return this.getPixelForValue(ticks[index].value);\n    }\n getPixelForDecimal(decimal) {\n        if (this._reversePixels) {\n            decimal = 1 - decimal;\n        }\n        const pixel = this._startPixel + decimal * this._length;\n        return _int16Range(this._alignToPixels ? _alignPixel(this.chart, pixel, 0) : pixel);\n    }\n getDecimalForPixel(pixel) {\n        const decimal = (pixel - this._startPixel) / this._length;\n        return this._reversePixels ? 1 - decimal : decimal;\n    }\n getBasePixel() {\n        return this.getPixelForValue(this.getBaseValue());\n    }\n getBaseValue() {\n        const { min , max  } = this;\n        return min < 0 && max < 0 ? max : min > 0 && max > 0 ? min : 0;\n    }\n getContext(index) {\n        const ticks = this.ticks || [];\n        if (index >= 0 && index < ticks.length) {\n            const tick = ticks[index];\n            return tick.$context || (tick.$context = createTickContext(this.getContext(), index, tick));\n        }\n        return this.$context || (this.$context = createScaleContext(this.chart.getContext(), this));\n    }\n _tickSize() {\n        const optionTicks = this.options.ticks;\n        const rot = toRadians(this.labelRotation);\n        const cos = Math.abs(Math.cos(rot));\n        const sin = Math.abs(Math.sin(rot));\n        const labelSizes = this._getLabelSizes();\n        const padding = optionTicks.autoSkipPadding || 0;\n        const w = labelSizes ? labelSizes.widest.width + padding : 0;\n        const h = labelSizes ? labelSizes.highest.height + padding : 0;\n        return this.isHorizontal() ? h * cos > w * sin ? w / cos : h / sin : h * sin < w * cos ? h / cos : w / sin;\n    }\n _isVisible() {\n        const display = this.options.display;\n        if (display !== 'auto') {\n            return !!display;\n        }\n        return this.getMatchingVisibleMetas().length > 0;\n    }\n _computeGridLineItems(chartArea) {\n        const axis = this.axis;\n        const chart = this.chart;\n        const options = this.options;\n        const { grid , position , border  } = options;\n        const offset = grid.offset;\n        const isHorizontal = this.isHorizontal();\n        const ticks = this.ticks;\n        const ticksLength = ticks.length + (offset ? 1 : 0);\n        const tl = getTickMarkLength(grid);\n        const items = [];\n        const borderOpts = border.setContext(this.getContext());\n        const axisWidth = borderOpts.display ? borderOpts.width : 0;\n        const axisHalfWidth = axisWidth / 2;\n        const alignBorderValue = function(pixel) {\n            return _alignPixel(chart, pixel, axisWidth);\n        };\n        let borderValue, i, lineValue, alignedLineValue;\n        let tx1, ty1, tx2, ty2, x1, y1, x2, y2;\n        if (position === 'top') {\n            borderValue = alignBorderValue(this.bottom);\n            ty1 = this.bottom - tl;\n            ty2 = borderValue - axisHalfWidth;\n            y1 = alignBorderValue(chartArea.top) + axisHalfWidth;\n            y2 = chartArea.bottom;\n        } else if (position === 'bottom') {\n            borderValue = alignBorderValue(this.top);\n            y1 = chartArea.top;\n            y2 = alignBorderValue(chartArea.bottom) - axisHalfWidth;\n            ty1 = borderValue + axisHalfWidth;\n            ty2 = this.top + tl;\n        } else if (position === 'left') {\n            borderValue = alignBorderValue(this.right);\n            tx1 = this.right - tl;\n            tx2 = borderValue - axisHalfWidth;\n            x1 = alignBorderValue(chartArea.left) + axisHalfWidth;\n            x2 = chartArea.right;\n        } else if (position === 'right') {\n            borderValue = alignBorderValue(this.left);\n            x1 = chartArea.left;\n            x2 = alignBorderValue(chartArea.right) - axisHalfWidth;\n            tx1 = borderValue + axisHalfWidth;\n            tx2 = this.left + tl;\n        } else if (axis === 'x') {\n            if (position === 'center') {\n                borderValue = alignBorderValue((chartArea.top + chartArea.bottom) / 2 + 0.5);\n            } else if (isObject(position)) {\n                const positionAxisID = Object.keys(position)[0];\n                const value = position[positionAxisID];\n                borderValue = alignBorderValue(this.chart.scales[positionAxisID].getPixelForValue(value));\n            }\n            y1 = chartArea.top;\n            y2 = chartArea.bottom;\n            ty1 = borderValue + axisHalfWidth;\n            ty2 = ty1 + tl;\n        } else if (axis === 'y') {\n            if (position === 'center') {\n                borderValue = alignBorderValue((chartArea.left + chartArea.right) / 2);\n            } else if (isObject(position)) {\n                const positionAxisID = Object.keys(position)[0];\n                const value = position[positionAxisID];\n                borderValue = alignBorderValue(this.chart.scales[positionAxisID].getPixelForValue(value));\n            }\n            tx1 = borderValue - axisHalfWidth;\n            tx2 = tx1 - tl;\n            x1 = chartArea.left;\n            x2 = chartArea.right;\n        }\n        const limit = valueOrDefault(options.ticks.maxTicksLimit, ticksLength);\n        const step = Math.max(1, Math.ceil(ticksLength / limit));\n        for(i = 0; i < ticksLength; i += step){\n            const context = this.getContext(i);\n            const optsAtIndex = grid.setContext(context);\n            const optsAtIndexBorder = border.setContext(context);\n            const lineWidth = optsAtIndex.lineWidth;\n            const lineColor = optsAtIndex.color;\n            const borderDash = optsAtIndexBorder.dash || [];\n            const borderDashOffset = optsAtIndexBorder.dashOffset;\n            const tickWidth = optsAtIndex.tickWidth;\n            const tickColor = optsAtIndex.tickColor;\n            const tickBorderDash = optsAtIndex.tickBorderDash || [];\n            const tickBorderDashOffset = optsAtIndex.tickBorderDashOffset;\n            lineValue = getPixelForGridLine(this, i, offset);\n            if (lineValue === undefined) {\n                continue;\n            }\n            alignedLineValue = _alignPixel(chart, lineValue, lineWidth);\n            if (isHorizontal) {\n                tx1 = tx2 = x1 = x2 = alignedLineValue;\n            } else {\n                ty1 = ty2 = y1 = y2 = alignedLineValue;\n            }\n            items.push({\n                tx1,\n                ty1,\n                tx2,\n                ty2,\n                x1,\n                y1,\n                x2,\n                y2,\n                width: lineWidth,\n                color: lineColor,\n                borderDash,\n                borderDashOffset,\n                tickWidth,\n                tickColor,\n                tickBorderDash,\n                tickBorderDashOffset\n            });\n        }\n        this._ticksLength = ticksLength;\n        this._borderValue = borderValue;\n        return items;\n    }\n _computeLabelItems(chartArea) {\n        const axis = this.axis;\n        const options = this.options;\n        const { position , ticks: optionTicks  } = options;\n        const isHorizontal = this.isHorizontal();\n        const ticks = this.ticks;\n        const { align , crossAlign , padding , mirror  } = optionTicks;\n        const tl = getTickMarkLength(options.grid);\n        const tickAndPadding = tl + padding;\n        const hTickAndPadding = mirror ? -padding : tickAndPadding;\n        const rotation = -toRadians(this.labelRotation);\n        const items = [];\n        let i, ilen, tick, label, x, y, textAlign, pixel, font, lineHeight, lineCount, textOffset;\n        let textBaseline = 'middle';\n        if (position === 'top') {\n            y = this.bottom - hTickAndPadding;\n            textAlign = this._getXAxisLabelAlignment();\n        } else if (position === 'bottom') {\n            y = this.top + hTickAndPadding;\n            textAlign = this._getXAxisLabelAlignment();\n        } else if (position === 'left') {\n            const ret = this._getYAxisLabelAlignment(tl);\n            textAlign = ret.textAlign;\n            x = ret.x;\n        } else if (position === 'right') {\n            const ret = this._getYAxisLabelAlignment(tl);\n            textAlign = ret.textAlign;\n            x = ret.x;\n        } else if (axis === 'x') {\n            if (position === 'center') {\n                y = (chartArea.top + chartArea.bottom) / 2 + tickAndPadding;\n            } else if (isObject(position)) {\n                const positionAxisID = Object.keys(position)[0];\n                const value = position[positionAxisID];\n                y = this.chart.scales[positionAxisID].getPixelForValue(value) + tickAndPadding;\n            }\n            textAlign = this._getXAxisLabelAlignment();\n        } else if (axis === 'y') {\n            if (position === 'center') {\n                x = (chartArea.left + chartArea.right) / 2 - tickAndPadding;\n            } else if (isObject(position)) {\n                const positionAxisID = Object.keys(position)[0];\n                const value = position[positionAxisID];\n                x = this.chart.scales[positionAxisID].getPixelForValue(value);\n            }\n            textAlign = this._getYAxisLabelAlignment(tl).textAlign;\n        }\n        if (axis === 'y') {\n            if (align === 'start') {\n                textBaseline = 'top';\n            } else if (align === 'end') {\n                textBaseline = 'bottom';\n            }\n        }\n        const labelSizes = this._getLabelSizes();\n        for(i = 0, ilen = ticks.length; i < ilen; ++i){\n            tick = ticks[i];\n            label = tick.label;\n            const optsAtIndex = optionTicks.setContext(this.getContext(i));\n            pixel = this.getPixelForTick(i) + optionTicks.labelOffset;\n            font = this._resolveTickFontOptions(i);\n            lineHeight = font.lineHeight;\n            lineCount = isArray(label) ? label.length : 1;\n            const halfCount = lineCount / 2;\n            const color = optsAtIndex.color;\n            const strokeColor = optsAtIndex.textStrokeColor;\n            const strokeWidth = optsAtIndex.textStrokeWidth;\n            let tickTextAlign = textAlign;\n            if (isHorizontal) {\n                x = pixel;\n                if (textAlign === 'inner') {\n                    if (i === ilen - 1) {\n                        tickTextAlign = !this.options.reverse ? 'right' : 'left';\n                    } else if (i === 0) {\n                        tickTextAlign = !this.options.reverse ? 'left' : 'right';\n                    } else {\n                        tickTextAlign = 'center';\n                    }\n                }\n                if (position === 'top') {\n                    if (crossAlign === 'near' || rotation !== 0) {\n                        textOffset = -lineCount * lineHeight + lineHeight / 2;\n                    } else if (crossAlign === 'center') {\n                        textOffset = -labelSizes.highest.height / 2 - halfCount * lineHeight + lineHeight;\n                    } else {\n                        textOffset = -labelSizes.highest.height + lineHeight / 2;\n                    }\n                } else {\n                    if (crossAlign === 'near' || rotation !== 0) {\n                        textOffset = lineHeight / 2;\n                    } else if (crossAlign === 'center') {\n                        textOffset = labelSizes.highest.height / 2 - halfCount * lineHeight;\n                    } else {\n                        textOffset = labelSizes.highest.height - lineCount * lineHeight;\n                    }\n                }\n                if (mirror) {\n                    textOffset *= -1;\n                }\n                if (rotation !== 0 && !optsAtIndex.showLabelBackdrop) {\n                    x += lineHeight / 2 * Math.sin(rotation);\n                }\n            } else {\n                y = pixel;\n                textOffset = (1 - lineCount) * lineHeight / 2;\n            }\n            let backdrop;\n            if (optsAtIndex.showLabelBackdrop) {\n                const labelPadding = toPadding(optsAtIndex.backdropPadding);\n                const height = labelSizes.heights[i];\n                const width = labelSizes.widths[i];\n                let top = textOffset - labelPadding.top;\n                let left = 0 - labelPadding.left;\n                switch(textBaseline){\n                    case 'middle':\n                        top -= height / 2;\n                        break;\n                    case 'bottom':\n                        top -= height;\n                        break;\n                }\n                switch(textAlign){\n                    case 'center':\n                        left -= width / 2;\n                        break;\n                    case 'right':\n                        left -= width;\n                        break;\n                    case 'inner':\n                        if (i === ilen - 1) {\n                            left -= width;\n                        } else if (i > 0) {\n                            left -= width / 2;\n                        }\n                        break;\n                }\n                backdrop = {\n                    left,\n                    top,\n                    width: width + labelPadding.width,\n                    height: height + labelPadding.height,\n                    color: optsAtIndex.backdropColor\n                };\n            }\n            items.push({\n                label,\n                font,\n                textOffset,\n                options: {\n                    rotation,\n                    color,\n                    strokeColor,\n                    strokeWidth,\n                    textAlign: tickTextAlign,\n                    textBaseline,\n                    translation: [\n                        x,\n                        y\n                    ],\n                    backdrop\n                }\n            });\n        }\n        return items;\n    }\n    _getXAxisLabelAlignment() {\n        const { position , ticks  } = this.options;\n        const rotation = -toRadians(this.labelRotation);\n        if (rotation) {\n            return position === 'top' ? 'left' : 'right';\n        }\n        let align = 'center';\n        if (ticks.align === 'start') {\n            align = 'left';\n        } else if (ticks.align === 'end') {\n            align = 'right';\n        } else if (ticks.align === 'inner') {\n            align = 'inner';\n        }\n        return align;\n    }\n    _getYAxisLabelAlignment(tl) {\n        const { position , ticks: { crossAlign , mirror , padding  }  } = this.options;\n        const labelSizes = this._getLabelSizes();\n        const tickAndPadding = tl + padding;\n        const widest = labelSizes.widest.width;\n        let textAlign;\n        let x;\n        if (position === 'left') {\n            if (mirror) {\n                x = this.right + padding;\n                if (crossAlign === 'near') {\n                    textAlign = 'left';\n                } else if (crossAlign === 'center') {\n                    textAlign = 'center';\n                    x += widest / 2;\n                } else {\n                    textAlign = 'right';\n                    x += widest;\n                }\n            } else {\n                x = this.right - tickAndPadding;\n                if (crossAlign === 'near') {\n                    textAlign = 'right';\n                } else if (crossAlign === 'center') {\n                    textAlign = 'center';\n                    x -= widest / 2;\n                } else {\n                    textAlign = 'left';\n                    x = this.left;\n                }\n            }\n        } else if (position === 'right') {\n            if (mirror) {\n                x = this.left + padding;\n                if (crossAlign === 'near') {\n                    textAlign = 'right';\n                } else if (crossAlign === 'center') {\n                    textAlign = 'center';\n                    x -= widest / 2;\n                } else {\n                    textAlign = 'left';\n                    x -= widest;\n                }\n            } else {\n                x = this.left + tickAndPadding;\n                if (crossAlign === 'near') {\n                    textAlign = 'left';\n                } else if (crossAlign === 'center') {\n                    textAlign = 'center';\n                    x += widest / 2;\n                } else {\n                    textAlign = 'right';\n                    x = this.right;\n                }\n            }\n        } else {\n            textAlign = 'right';\n        }\n        return {\n            textAlign,\n            x\n        };\n    }\n _computeLabelArea() {\n        if (this.options.ticks.mirror) {\n            return;\n        }\n        const chart = this.chart;\n        const position = this.options.position;\n        if (position === 'left' || position === 'right') {\n            return {\n                top: 0,\n                left: this.left,\n                bottom: chart.height,\n                right: this.right\n            };\n        }\n        if (position === 'top' || position === 'bottom') {\n            return {\n                top: this.top,\n                left: 0,\n                bottom: this.bottom,\n                right: chart.width\n            };\n        }\n    }\n drawBackground() {\n        const { ctx , options: { backgroundColor  } , left , top , width , height  } = this;\n        if (backgroundColor) {\n            ctx.save();\n            ctx.fillStyle = backgroundColor;\n            ctx.fillRect(left, top, width, height);\n            ctx.restore();\n        }\n    }\n    getLineWidthForValue(value) {\n        const grid = this.options.grid;\n        if (!this._isVisible() || !grid.display) {\n            return 0;\n        }\n        const ticks = this.ticks;\n        const index = ticks.findIndex((t)=>t.value === value);\n        if (index >= 0) {\n            const opts = grid.setContext(this.getContext(index));\n            return opts.lineWidth;\n        }\n        return 0;\n    }\n drawGrid(chartArea) {\n        const grid = this.options.grid;\n        const ctx = this.ctx;\n        const items = this._gridLineItems || (this._gridLineItems = this._computeGridLineItems(chartArea));\n        let i, ilen;\n        const drawLine = (p1, p2, style)=>{\n            if (!style.width || !style.color) {\n                return;\n            }\n            ctx.save();\n            ctx.lineWidth = style.width;\n            ctx.strokeStyle = style.color;\n            ctx.setLineDash(style.borderDash || []);\n            ctx.lineDashOffset = style.borderDashOffset;\n            ctx.beginPath();\n            ctx.moveTo(p1.x, p1.y);\n            ctx.lineTo(p2.x, p2.y);\n            ctx.stroke();\n            ctx.restore();\n        };\n        if (grid.display) {\n            for(i = 0, ilen = items.length; i < ilen; ++i){\n                const item = items[i];\n                if (grid.drawOnChartArea) {\n                    drawLine({\n                        x: item.x1,\n                        y: item.y1\n                    }, {\n                        x: item.x2,\n                        y: item.y2\n                    }, item);\n                }\n                if (grid.drawTicks) {\n                    drawLine({\n                        x: item.tx1,\n                        y: item.ty1\n                    }, {\n                        x: item.tx2,\n                        y: item.ty2\n                    }, {\n                        color: item.tickColor,\n                        width: item.tickWidth,\n                        borderDash: item.tickBorderDash,\n                        borderDashOffset: item.tickBorderDashOffset\n                    });\n                }\n            }\n        }\n    }\n drawBorder() {\n        const { chart , ctx , options: { border , grid  }  } = this;\n        const borderOpts = border.setContext(this.getContext());\n        const axisWidth = border.display ? borderOpts.width : 0;\n        if (!axisWidth) {\n            return;\n        }\n        const lastLineWidth = grid.setContext(this.getContext(0)).lineWidth;\n        const borderValue = this._borderValue;\n        let x1, x2, y1, y2;\n        if (this.isHorizontal()) {\n            x1 = _alignPixel(chart, this.left, axisWidth) - axisWidth / 2;\n            x2 = _alignPixel(chart, this.right, lastLineWidth) + lastLineWidth / 2;\n            y1 = y2 = borderValue;\n        } else {\n            y1 = _alignPixel(chart, this.top, axisWidth) - axisWidth / 2;\n            y2 = _alignPixel(chart, this.bottom, lastLineWidth) + lastLineWidth / 2;\n            x1 = x2 = borderValue;\n        }\n        ctx.save();\n        ctx.lineWidth = borderOpts.width;\n        ctx.strokeStyle = borderOpts.color;\n        ctx.beginPath();\n        ctx.moveTo(x1, y1);\n        ctx.lineTo(x2, y2);\n        ctx.stroke();\n        ctx.restore();\n    }\n drawLabels(chartArea) {\n        const optionTicks = this.options.ticks;\n        if (!optionTicks.display) {\n            return;\n        }\n        const ctx = this.ctx;\n        const area = this._computeLabelArea();\n        if (area) {\n            clipArea(ctx, area);\n        }\n        const items = this.getLabelItems(chartArea);\n        for (const item of items){\n            const renderTextOptions = item.options;\n            const tickFont = item.font;\n            const label = item.label;\n            const y = item.textOffset;\n            renderText(ctx, label, 0, y, tickFont, renderTextOptions);\n        }\n        if (area) {\n            unclipArea(ctx);\n        }\n    }\n drawTitle() {\n        const { ctx , options: { position , title , reverse  }  } = this;\n        if (!title.display) {\n            return;\n        }\n        const font = toFont(title.font);\n        const padding = toPadding(title.padding);\n        const align = title.align;\n        let offset = font.lineHeight / 2;\n        if (position === 'bottom' || position === 'center' || isObject(position)) {\n            offset += padding.bottom;\n            if (isArray(title.text)) {\n                offset += font.lineHeight * (title.text.length - 1);\n            }\n        } else {\n            offset += padding.top;\n        }\n        const { titleX , titleY , maxWidth , rotation  } = titleArgs(this, offset, position, align);\n        renderText(ctx, title.text, 0, 0, font, {\n            color: title.color,\n            maxWidth,\n            rotation,\n            textAlign: titleAlign(align, position, reverse),\n            textBaseline: 'middle',\n            translation: [\n                titleX,\n                titleY\n            ]\n        });\n    }\n    draw(chartArea) {\n        if (!this._isVisible()) {\n            return;\n        }\n        this.drawBackground();\n        this.drawGrid(chartArea);\n        this.drawBorder();\n        this.drawTitle();\n        this.drawLabels(chartArea);\n    }\n _layers() {\n        const opts = this.options;\n        const tz = opts.ticks && opts.ticks.z || 0;\n        const gz = valueOrDefault(opts.grid && opts.grid.z, -1);\n        const bz = valueOrDefault(opts.border && opts.border.z, 0);\n        if (!this._isVisible() || this.draw !== Scale.prototype.draw) {\n            return [\n                {\n                    z: tz,\n                    draw: (chartArea)=>{\n                        this.draw(chartArea);\n                    }\n                }\n            ];\n        }\n        return [\n            {\n                z: gz,\n                draw: (chartArea)=>{\n                    this.drawBackground();\n                    this.drawGrid(chartArea);\n                    this.drawTitle();\n                }\n            },\n            {\n                z: bz,\n                draw: ()=>{\n                    this.drawBorder();\n                }\n            },\n            {\n                z: tz,\n                draw: (chartArea)=>{\n                    this.drawLabels(chartArea);\n                }\n            }\n        ];\n    }\n getMatchingVisibleMetas(type) {\n        const metas = this.chart.getSortedVisibleDatasetMetas();\n        const axisID = this.axis + 'AxisID';\n        const result = [];\n        let i, ilen;\n        for(i = 0, ilen = metas.length; i < ilen; ++i){\n            const meta = metas[i];\n            if (meta[axisID] === this.id && (!type || meta.type === type)) {\n                result.push(meta);\n            }\n        }\n        return result;\n    }\n _resolveTickFontOptions(index) {\n        const opts = this.options.ticks.setContext(this.getContext(index));\n        return toFont(opts.font);\n    }\n _maxDigits() {\n        const fontSize = this._resolveTickFontOptions(0).lineHeight;\n        return (this.isHorizontal() ? this.width : this.height) / fontSize;\n    }\n}\n\nclass TypedRegistry {\n    constructor(type, scope, override){\n        this.type = type;\n        this.scope = scope;\n        this.override = override;\n        this.items = Object.create(null);\n    }\n    isForType(type) {\n        return Object.prototype.isPrototypeOf.call(this.type.prototype, type.prototype);\n    }\n register(item) {\n        const proto = Object.getPrototypeOf(item);\n        let parentScope;\n        if (isIChartComponent(proto)) {\n            parentScope = this.register(proto);\n        }\n        const items = this.items;\n        const id = item.id;\n        const scope = this.scope + '.' + id;\n        if (!id) {\n            throw new Error('class does not have id: ' + item);\n        }\n        if (id in items) {\n            return scope;\n        }\n        items[id] = item;\n        registerDefaults(item, scope, parentScope);\n        if (this.override) {\n            defaults.override(item.id, item.overrides);\n        }\n        return scope;\n    }\n get(id) {\n        return this.items[id];\n    }\n unregister(item) {\n        const items = this.items;\n        const id = item.id;\n        const scope = this.scope;\n        if (id in items) {\n            delete items[id];\n        }\n        if (scope && id in defaults[scope]) {\n            delete defaults[scope][id];\n            if (this.override) {\n                delete overrides[id];\n            }\n        }\n    }\n}\nfunction registerDefaults(item, scope, parentScope) {\n    const itemDefaults = merge(Object.create(null), [\n        parentScope ? defaults.get(parentScope) : {},\n        defaults.get(scope),\n        item.defaults\n    ]);\n    defaults.set(scope, itemDefaults);\n    if (item.defaultRoutes) {\n        routeDefaults(scope, item.defaultRoutes);\n    }\n    if (item.descriptors) {\n        defaults.describe(scope, item.descriptors);\n    }\n}\nfunction routeDefaults(scope, routes) {\n    Object.keys(routes).forEach((property)=>{\n        const propertyParts = property.split('.');\n        const sourceName = propertyParts.pop();\n        const sourceScope = [\n            scope\n        ].concat(propertyParts).join('.');\n        const parts = routes[property].split('.');\n        const targetName = parts.pop();\n        const targetScope = parts.join('.');\n        defaults.route(sourceScope, sourceName, targetScope, targetName);\n    });\n}\nfunction isIChartComponent(proto) {\n    return 'id' in proto && 'defaults' in proto;\n}\n\nclass Registry {\n    constructor(){\n        this.controllers = new TypedRegistry(DatasetController, 'datasets', true);\n        this.elements = new TypedRegistry(Element, 'elements');\n        this.plugins = new TypedRegistry(Object, 'plugins');\n        this.scales = new TypedRegistry(Scale, 'scales');\n        this._typedRegistries = [\n            this.controllers,\n            this.scales,\n            this.elements\n        ];\n    }\n add(...args) {\n        this._each('register', args);\n    }\n    remove(...args) {\n        this._each('unregister', args);\n    }\n addControllers(...args) {\n        this._each('register', args, this.controllers);\n    }\n addElements(...args) {\n        this._each('register', args, this.elements);\n    }\n addPlugins(...args) {\n        this._each('register', args, this.plugins);\n    }\n addScales(...args) {\n        this._each('register', args, this.scales);\n    }\n getController(id) {\n        return this._get(id, this.controllers, 'controller');\n    }\n getElement(id) {\n        return this._get(id, this.elements, 'element');\n    }\n getPlugin(id) {\n        return this._get(id, this.plugins, 'plugin');\n    }\n getScale(id) {\n        return this._get(id, this.scales, 'scale');\n    }\n removeControllers(...args) {\n        this._each('unregister', args, this.controllers);\n    }\n removeElements(...args) {\n        this._each('unregister', args, this.elements);\n    }\n removePlugins(...args) {\n        this._each('unregister', args, this.plugins);\n    }\n removeScales(...args) {\n        this._each('unregister', args, this.scales);\n    }\n _each(method, args, typedRegistry) {\n        [\n            ...args\n        ].forEach((arg)=>{\n            const reg = typedRegistry || this._getRegistryForType(arg);\n            if (typedRegistry || reg.isForType(arg) || reg === this.plugins && arg.id) {\n                this._exec(method, reg, arg);\n            } else {\n                each(arg, (item)=>{\n                    const itemReg = typedRegistry || this._getRegistryForType(item);\n                    this._exec(method, itemReg, item);\n                });\n            }\n        });\n    }\n _exec(method, registry, component) {\n        const camelMethod = _capitalize(method);\n        callback(component['before' + camelMethod], [], component);\n        registry[method](component);\n        callback(component['after' + camelMethod], [], component);\n    }\n _getRegistryForType(type) {\n        for(let i = 0; i < this._typedRegistries.length; i++){\n            const reg = this._typedRegistries[i];\n            if (reg.isForType(type)) {\n                return reg;\n            }\n        }\n        return this.plugins;\n    }\n _get(id, typedRegistry, type) {\n        const item = typedRegistry.get(id);\n        if (item === undefined) {\n            throw new Error('\"' + id + '\" is not a registered ' + type + '.');\n        }\n        return item;\n    }\n}\nvar registry = /* #__PURE__ */ new Registry();\n\nclass PluginService {\n    constructor(){\n        this._init = [];\n    }\n notify(chart, hook, args, filter) {\n        if (hook === 'beforeInit') {\n            this._init = this._createDescriptors(chart, true);\n            this._notify(this._init, chart, 'install');\n        }\n        const descriptors = filter ? this._descriptors(chart).filter(filter) : this._descriptors(chart);\n        const result = this._notify(descriptors, chart, hook, args);\n        if (hook === 'afterDestroy') {\n            this._notify(descriptors, chart, 'stop');\n            this._notify(this._init, chart, 'uninstall');\n        }\n        return result;\n    }\n _notify(descriptors, chart, hook, args) {\n        args = args || {};\n        for (const descriptor of descriptors){\n            const plugin = descriptor.plugin;\n            const method = plugin[hook];\n            const params = [\n                chart,\n                args,\n                descriptor.options\n            ];\n            if (callback(method, params, plugin) === false && args.cancelable) {\n                return false;\n            }\n        }\n        return true;\n    }\n    invalidate() {\n        if (!isNullOrUndef(this._cache)) {\n            this._oldCache = this._cache;\n            this._cache = undefined;\n        }\n    }\n _descriptors(chart) {\n        if (this._cache) {\n            return this._cache;\n        }\n        const descriptors = this._cache = this._createDescriptors(chart);\n        this._notifyStateChanges(chart);\n        return descriptors;\n    }\n    _createDescriptors(chart, all) {\n        const config = chart && chart.config;\n        const options = valueOrDefault(config.options && config.options.plugins, {});\n        const plugins = allPlugins(config);\n        return options === false && !all ? [] : createDescriptors(chart, plugins, options, all);\n    }\n _notifyStateChanges(chart) {\n        const previousDescriptors = this._oldCache || [];\n        const descriptors = this._cache;\n        const diff = (a, b)=>a.filter((x)=>!b.some((y)=>x.plugin.id === y.plugin.id));\n        this._notify(diff(previousDescriptors, descriptors), chart, 'stop');\n        this._notify(diff(descriptors, previousDescriptors), chart, 'start');\n    }\n}\n function allPlugins(config) {\n    const localIds = {};\n    const plugins = [];\n    const keys = Object.keys(registry.plugins.items);\n    for(let i = 0; i < keys.length; i++){\n        plugins.push(registry.getPlugin(keys[i]));\n    }\n    const local = config.plugins || [];\n    for(let i = 0; i < local.length; i++){\n        const plugin = local[i];\n        if (plugins.indexOf(plugin) === -1) {\n            plugins.push(plugin);\n            localIds[plugin.id] = true;\n        }\n    }\n    return {\n        plugins,\n        localIds\n    };\n}\nfunction getOpts(options, all) {\n    if (!all && options === false) {\n        return null;\n    }\n    if (options === true) {\n        return {};\n    }\n    return options;\n}\nfunction createDescriptors(chart, { plugins , localIds  }, options, all) {\n    const result = [];\n    const context = chart.getContext();\n    for (const plugin of plugins){\n        const id = plugin.id;\n        const opts = getOpts(options[id], all);\n        if (opts === null) {\n            continue;\n        }\n        result.push({\n            plugin,\n            options: pluginOpts(chart.config, {\n                plugin,\n                local: localIds[id]\n            }, opts, context)\n        });\n    }\n    return result;\n}\nfunction pluginOpts(config, { plugin , local  }, opts, context) {\n    const keys = config.pluginScopeKeys(plugin);\n    const scopes = config.getOptionScopes(opts, keys);\n    if (local && plugin.defaults) {\n        scopes.push(plugin.defaults);\n    }\n    return config.createResolver(scopes, context, [\n        ''\n    ], {\n        scriptable: false,\n        indexable: false,\n        allKeys: true\n    });\n}\n\nfunction getIndexAxis(type, options) {\n    const datasetDefaults = defaults.datasets[type] || {};\n    const datasetOptions = (options.datasets || {})[type] || {};\n    return datasetOptions.indexAxis || options.indexAxis || datasetDefaults.indexAxis || 'x';\n}\nfunction getAxisFromDefaultScaleID(id, indexAxis) {\n    let axis = id;\n    if (id === '_index_') {\n        axis = indexAxis;\n    } else if (id === '_value_') {\n        axis = indexAxis === 'x' ? 'y' : 'x';\n    }\n    return axis;\n}\nfunction getDefaultScaleIDFromAxis(axis, indexAxis) {\n    return axis === indexAxis ? '_index_' : '_value_';\n}\nfunction idMatchesAxis(id) {\n    if (id === 'x' || id === 'y' || id === 'r') {\n        return id;\n    }\n}\nfunction axisFromPosition(position) {\n    if (position === 'top' || position === 'bottom') {\n        return 'x';\n    }\n    if (position === 'left' || position === 'right') {\n        return 'y';\n    }\n}\nfunction determineAxis(id, ...scaleOptions) {\n    if (idMatchesAxis(id)) {\n        return id;\n    }\n    for (const opts of scaleOptions){\n        const axis = opts.axis || axisFromPosition(opts.position) || id.length > 1 && idMatchesAxis(id[0].toLowerCase());\n        if (axis) {\n            return axis;\n        }\n    }\n    throw new Error(`Cannot determine type of '${id}' axis. Please provide 'axis' or 'position' option.`);\n}\nfunction getAxisFromDataset(id, axis, dataset) {\n    if (dataset[axis + 'AxisID'] === id) {\n        return {\n            axis\n        };\n    }\n}\nfunction retrieveAxisFromDatasets(id, config) {\n    if (config.data && config.data.datasets) {\n        const boundDs = config.data.datasets.filter((d)=>d.xAxisID === id || d.yAxisID === id);\n        if (boundDs.length) {\n            return getAxisFromDataset(id, 'x', boundDs[0]) || getAxisFromDataset(id, 'y', boundDs[0]);\n        }\n    }\n    return {};\n}\nfunction mergeScaleConfig(config, options) {\n    const chartDefaults = overrides[config.type] || {\n        scales: {}\n    };\n    const configScales = options.scales || {};\n    const chartIndexAxis = getIndexAxis(config.type, options);\n    const scales = Object.create(null);\n    Object.keys(configScales).forEach((id)=>{\n        const scaleConf = configScales[id];\n        if (!isObject(scaleConf)) {\n            return console.error(`Invalid scale configuration for scale: ${id}`);\n        }\n        if (scaleConf._proxy) {\n            return console.warn(`Ignoring resolver passed as options for scale: ${id}`);\n        }\n        const axis = determineAxis(id, scaleConf, retrieveAxisFromDatasets(id, config), defaults.scales[scaleConf.type]);\n        const defaultId = getDefaultScaleIDFromAxis(axis, chartIndexAxis);\n        const defaultScaleOptions = chartDefaults.scales || {};\n        scales[id] = mergeIf(Object.create(null), [\n            {\n                axis\n            },\n            scaleConf,\n            defaultScaleOptions[axis],\n            defaultScaleOptions[defaultId]\n        ]);\n    });\n    config.data.datasets.forEach((dataset)=>{\n        const type = dataset.type || config.type;\n        const indexAxis = dataset.indexAxis || getIndexAxis(type, options);\n        const datasetDefaults = overrides[type] || {};\n        const defaultScaleOptions = datasetDefaults.scales || {};\n        Object.keys(defaultScaleOptions).forEach((defaultID)=>{\n            const axis = getAxisFromDefaultScaleID(defaultID, indexAxis);\n            const id = dataset[axis + 'AxisID'] || axis;\n            scales[id] = scales[id] || Object.create(null);\n            mergeIf(scales[id], [\n                {\n                    axis\n                },\n                configScales[id],\n                defaultScaleOptions[defaultID]\n            ]);\n        });\n    });\n    Object.keys(scales).forEach((key)=>{\n        const scale = scales[key];\n        mergeIf(scale, [\n            defaults.scales[scale.type],\n            defaults.scale\n        ]);\n    });\n    return scales;\n}\nfunction initOptions(config) {\n    const options = config.options || (config.options = {});\n    options.plugins = valueOrDefault(options.plugins, {});\n    options.scales = mergeScaleConfig(config, options);\n}\nfunction initData(data) {\n    data = data || {};\n    data.datasets = data.datasets || [];\n    data.labels = data.labels || [];\n    return data;\n}\nfunction initConfig(config) {\n    config = config || {};\n    config.data = initData(config.data);\n    initOptions(config);\n    return config;\n}\nconst keyCache = new Map();\nconst keysCached = new Set();\nfunction cachedKeys(cacheKey, generate) {\n    let keys = keyCache.get(cacheKey);\n    if (!keys) {\n        keys = generate();\n        keyCache.set(cacheKey, keys);\n        keysCached.add(keys);\n    }\n    return keys;\n}\nconst addIfFound = (set, obj, key)=>{\n    const opts = resolveObjectKey(obj, key);\n    if (opts !== undefined) {\n        set.add(opts);\n    }\n};\nclass Config {\n    constructor(config){\n        this._config = initConfig(config);\n        this._scopeCache = new Map();\n        this._resolverCache = new Map();\n    }\n    get platform() {\n        return this._config.platform;\n    }\n    get type() {\n        return this._config.type;\n    }\n    set type(type) {\n        this._config.type = type;\n    }\n    get data() {\n        return this._config.data;\n    }\n    set data(data) {\n        this._config.data = initData(data);\n    }\n    get options() {\n        return this._config.options;\n    }\n    set options(options) {\n        this._config.options = options;\n    }\n    get plugins() {\n        return this._config.plugins;\n    }\n    update() {\n        const config = this._config;\n        this.clearCache();\n        initOptions(config);\n    }\n    clearCache() {\n        this._scopeCache.clear();\n        this._resolverCache.clear();\n    }\n datasetScopeKeys(datasetType) {\n        return cachedKeys(datasetType, ()=>[\n                [\n                    `datasets.${datasetType}`,\n                    ''\n                ]\n            ]);\n    }\n datasetAnimationScopeKeys(datasetType, transition) {\n        return cachedKeys(`${datasetType}.transition.${transition}`, ()=>[\n                [\n                    `datasets.${datasetType}.transitions.${transition}`,\n                    `transitions.${transition}`\n                ],\n                [\n                    `datasets.${datasetType}`,\n                    ''\n                ]\n            ]);\n    }\n datasetElementScopeKeys(datasetType, elementType) {\n        return cachedKeys(`${datasetType}-${elementType}`, ()=>[\n                [\n                    `datasets.${datasetType}.elements.${elementType}`,\n                    `datasets.${datasetType}`,\n                    `elements.${elementType}`,\n                    ''\n                ]\n            ]);\n    }\n pluginScopeKeys(plugin) {\n        const id = plugin.id;\n        const type = this.type;\n        return cachedKeys(`${type}-plugin-${id}`, ()=>[\n                [\n                    `plugins.${id}`,\n                    ...plugin.additionalOptionScopes || []\n                ]\n            ]);\n    }\n _cachedScopes(mainScope, resetCache) {\n        const _scopeCache = this._scopeCache;\n        let cache = _scopeCache.get(mainScope);\n        if (!cache || resetCache) {\n            cache = new Map();\n            _scopeCache.set(mainScope, cache);\n        }\n        return cache;\n    }\n getOptionScopes(mainScope, keyLists, resetCache) {\n        const { options , type  } = this;\n        const cache = this._cachedScopes(mainScope, resetCache);\n        const cached = cache.get(keyLists);\n        if (cached) {\n            return cached;\n        }\n        const scopes = new Set();\n        keyLists.forEach((keys)=>{\n            if (mainScope) {\n                scopes.add(mainScope);\n                keys.forEach((key)=>addIfFound(scopes, mainScope, key));\n            }\n            keys.forEach((key)=>addIfFound(scopes, options, key));\n            keys.forEach((key)=>addIfFound(scopes, overrides[type] || {}, key));\n            keys.forEach((key)=>addIfFound(scopes, defaults, key));\n            keys.forEach((key)=>addIfFound(scopes, descriptors, key));\n        });\n        const array = Array.from(scopes);\n        if (array.length === 0) {\n            array.push(Object.create(null));\n        }\n        if (keysCached.has(keyLists)) {\n            cache.set(keyLists, array);\n        }\n        return array;\n    }\n chartOptionScopes() {\n        const { options , type  } = this;\n        return [\n            options,\n            overrides[type] || {},\n            defaults.datasets[type] || {},\n            {\n                type\n            },\n            defaults,\n            descriptors\n        ];\n    }\n resolveNamedOptions(scopes, names, context, prefixes = [\n        ''\n    ]) {\n        const result = {\n            $shared: true\n        };\n        const { resolver , subPrefixes  } = getResolver(this._resolverCache, scopes, prefixes);\n        let options = resolver;\n        if (needContext(resolver, names)) {\n            result.$shared = false;\n            context = isFunction(context) ? context() : context;\n            const subResolver = this.createResolver(scopes, context, subPrefixes);\n            options = _attachContext(resolver, context, subResolver);\n        }\n        for (const prop of names){\n            result[prop] = options[prop];\n        }\n        return result;\n    }\n createResolver(scopes, context, prefixes = [\n        ''\n    ], descriptorDefaults) {\n        const { resolver  } = getResolver(this._resolverCache, scopes, prefixes);\n        return isObject(context) ? _attachContext(resolver, context, undefined, descriptorDefaults) : resolver;\n    }\n}\nfunction getResolver(resolverCache, scopes, prefixes) {\n    let cache = resolverCache.get(scopes);\n    if (!cache) {\n        cache = new Map();\n        resolverCache.set(scopes, cache);\n    }\n    const cacheKey = prefixes.join();\n    let cached = cache.get(cacheKey);\n    if (!cached) {\n        const resolver = _createResolver(scopes, prefixes);\n        cached = {\n            resolver,\n            subPrefixes: prefixes.filter((p)=>!p.toLowerCase().includes('hover'))\n        };\n        cache.set(cacheKey, cached);\n    }\n    return cached;\n}\nconst hasFunction = (value)=>isObject(value) && Object.getOwnPropertyNames(value).some((key)=>isFunction(value[key]));\nfunction needContext(proxy, names) {\n    const { isScriptable , isIndexable  } = _descriptors(proxy);\n    for (const prop of names){\n        const scriptable = isScriptable(prop);\n        const indexable = isIndexable(prop);\n        const value = (indexable || scriptable) && proxy[prop];\n        if (scriptable && (isFunction(value) || hasFunction(value)) || indexable && isArray(value)) {\n            return true;\n        }\n    }\n    return false;\n}\n\nvar version = \"4.4.2\";\n\nconst KNOWN_POSITIONS = [\n    'top',\n    'bottom',\n    'left',\n    'right',\n    'chartArea'\n];\nfunction positionIsHorizontal(position, axis) {\n    return position === 'top' || position === 'bottom' || KNOWN_POSITIONS.indexOf(position) === -1 && axis === 'x';\n}\nfunction compare2Level(l1, l2) {\n    return function(a, b) {\n        return a[l1] === b[l1] ? a[l2] - b[l2] : a[l1] - b[l1];\n    };\n}\nfunction onAnimationsComplete(context) {\n    const chart = context.chart;\n    const animationOptions = chart.options.animation;\n    chart.notifyPlugins('afterRender');\n    callback(animationOptions && animationOptions.onComplete, [\n        context\n    ], chart);\n}\nfunction onAnimationProgress(context) {\n    const chart = context.chart;\n    const animationOptions = chart.options.animation;\n    callback(animationOptions && animationOptions.onProgress, [\n        context\n    ], chart);\n}\n function getCanvas(item) {\n    if (_isDomSupported() && typeof item === 'string') {\n        item = document.getElementById(item);\n    } else if (item && item.length) {\n        item = item[0];\n    }\n    if (item && item.canvas) {\n        item = item.canvas;\n    }\n    return item;\n}\nconst instances = {};\nconst getChart = (key)=>{\n    const canvas = getCanvas(key);\n    return Object.values(instances).filter((c)=>c.canvas === canvas).pop();\n};\nfunction moveNumericKeys(obj, start, move) {\n    const keys = Object.keys(obj);\n    for (const key of keys){\n        const intKey = +key;\n        if (intKey >= start) {\n            const value = obj[key];\n            delete obj[key];\n            if (move > 0 || intKey > start) {\n                obj[intKey + move] = value;\n            }\n        }\n    }\n}\n function determineLastEvent(e, lastEvent, inChartArea, isClick) {\n    if (!inChartArea || e.type === 'mouseout') {\n        return null;\n    }\n    if (isClick) {\n        return lastEvent;\n    }\n    return e;\n}\nfunction getSizeForArea(scale, chartArea, field) {\n    return scale.options.clip ? scale[field] : chartArea[field];\n}\nfunction getDatasetArea(meta, chartArea) {\n    const { xScale , yScale  } = meta;\n    if (xScale && yScale) {\n        return {\n            left: getSizeForArea(xScale, chartArea, 'left'),\n            right: getSizeForArea(xScale, chartArea, 'right'),\n            top: getSizeForArea(yScale, chartArea, 'top'),\n            bottom: getSizeForArea(yScale, chartArea, 'bottom')\n        };\n    }\n    return chartArea;\n}\nclass Chart {\n    static defaults = defaults;\n    static instances = instances;\n    static overrides = overrides;\n    static registry = registry;\n    static version = version;\n    static getChart = getChart;\n    static register(...items) {\n        registry.add(...items);\n        invalidatePlugins();\n    }\n    static unregister(...items) {\n        registry.remove(...items);\n        invalidatePlugins();\n    }\n    constructor(item, userConfig){\n        const config = this.config = new Config(userConfig);\n        const initialCanvas = getCanvas(item);\n        const existingChart = getChart(initialCanvas);\n        if (existingChart) {\n            throw new Error('Canvas is already in use. Chart with ID \\'' + existingChart.id + '\\'' + ' must be destroyed before the canvas with ID \\'' + existingChart.canvas.id + '\\' can be reused.');\n        }\n        const options = config.createResolver(config.chartOptionScopes(), this.getContext());\n        this.platform = new (config.platform || _detectPlatform(initialCanvas))();\n        this.platform.updateConfig(config);\n        const context = this.platform.acquireContext(initialCanvas, options.aspectRatio);\n        const canvas = context && context.canvas;\n        const height = canvas && canvas.height;\n        const width = canvas && canvas.width;\n        this.id = uid();\n        this.ctx = context;\n        this.canvas = canvas;\n        this.width = width;\n        this.height = height;\n        this._options = options;\n        this._aspectRatio = this.aspectRatio;\n        this._layers = [];\n        this._metasets = [];\n        this._stacks = undefined;\n        this.boxes = [];\n        this.currentDevicePixelRatio = undefined;\n        this.chartArea = undefined;\n        this._active = [];\n        this._lastEvent = undefined;\n        this._listeners = {};\n         this._responsiveListeners = undefined;\n        this._sortedMetasets = [];\n        this.scales = {};\n        this._plugins = new PluginService();\n        this.$proxies = {};\n        this._hiddenIndices = {};\n        this.attached = false;\n        this._animationsDisabled = undefined;\n        this.$context = undefined;\n        this._doResize = debounce((mode)=>this.update(mode), options.resizeDelay || 0);\n        this._dataChanges = [];\n        instances[this.id] = this;\n        if (!context || !canvas) {\n            console.error(\"Failed to create chart: can't acquire context from the given item\");\n            return;\n        }\n        animator.listen(this, 'complete', onAnimationsComplete);\n        animator.listen(this, 'progress', onAnimationProgress);\n        this._initialize();\n        if (this.attached) {\n            this.update();\n        }\n    }\n    get aspectRatio() {\n        const { options: { aspectRatio , maintainAspectRatio  } , width , height , _aspectRatio  } = this;\n        if (!isNullOrUndef(aspectRatio)) {\n            return aspectRatio;\n        }\n        if (maintainAspectRatio && _aspectRatio) {\n            return _aspectRatio;\n        }\n        return height ? width / height : null;\n    }\n    get data() {\n        return this.config.data;\n    }\n    set data(data) {\n        this.config.data = data;\n    }\n    get options() {\n        return this._options;\n    }\n    set options(options) {\n        this.config.options = options;\n    }\n    get registry() {\n        return registry;\n    }\n _initialize() {\n        this.notifyPlugins('beforeInit');\n        if (this.options.responsive) {\n            this.resize();\n        } else {\n            retinaScale(this, this.options.devicePixelRatio);\n        }\n        this.bindEvents();\n        this.notifyPlugins('afterInit');\n        return this;\n    }\n    clear() {\n        clearCanvas(this.canvas, this.ctx);\n        return this;\n    }\n    stop() {\n        animator.stop(this);\n        return this;\n    }\n resize(width, height) {\n        if (!animator.running(this)) {\n            this._resize(width, height);\n        } else {\n            this._resizeBeforeDraw = {\n                width,\n                height\n            };\n        }\n    }\n    _resize(width, height) {\n        const options = this.options;\n        const canvas = this.canvas;\n        const aspectRatio = options.maintainAspectRatio && this.aspectRatio;\n        const newSize = this.platform.getMaximumSize(canvas, width, height, aspectRatio);\n        const newRatio = options.devicePixelRatio || this.platform.getDevicePixelRatio();\n        const mode = this.width ? 'resize' : 'attach';\n        this.width = newSize.width;\n        this.height = newSize.height;\n        this._aspectRatio = this.aspectRatio;\n        if (!retinaScale(this, newRatio, true)) {\n            return;\n        }\n        this.notifyPlugins('resize', {\n            size: newSize\n        });\n        callback(options.onResize, [\n            this,\n            newSize\n        ], this);\n        if (this.attached) {\n            if (this._doResize(mode)) {\n                this.render();\n            }\n        }\n    }\n    ensureScalesHaveIDs() {\n        const options = this.options;\n        const scalesOptions = options.scales || {};\n        each(scalesOptions, (axisOptions, axisID)=>{\n            axisOptions.id = axisID;\n        });\n    }\n buildOrUpdateScales() {\n        const options = this.options;\n        const scaleOpts = options.scales;\n        const scales = this.scales;\n        const updated = Object.keys(scales).reduce((obj, id)=>{\n            obj[id] = false;\n            return obj;\n        }, {});\n        let items = [];\n        if (scaleOpts) {\n            items = items.concat(Object.keys(scaleOpts).map((id)=>{\n                const scaleOptions = scaleOpts[id];\n                const axis = determineAxis(id, scaleOptions);\n                const isRadial = axis === 'r';\n                const isHorizontal = axis === 'x';\n                return {\n                    options: scaleOptions,\n                    dposition: isRadial ? 'chartArea' : isHorizontal ? 'bottom' : 'left',\n                    dtype: isRadial ? 'radialLinear' : isHorizontal ? 'category' : 'linear'\n                };\n            }));\n        }\n        each(items, (item)=>{\n            const scaleOptions = item.options;\n            const id = scaleOptions.id;\n            const axis = determineAxis(id, scaleOptions);\n            const scaleType = valueOrDefault(scaleOptions.type, item.dtype);\n            if (scaleOptions.position === undefined || positionIsHorizontal(scaleOptions.position, axis) !== positionIsHorizontal(item.dposition)) {\n                scaleOptions.position = item.dposition;\n            }\n            updated[id] = true;\n            let scale = null;\n            if (id in scales && scales[id].type === scaleType) {\n                scale = scales[id];\n            } else {\n                const scaleClass = registry.getScale(scaleType);\n                scale = new scaleClass({\n                    id,\n                    type: scaleType,\n                    ctx: this.ctx,\n                    chart: this\n                });\n                scales[scale.id] = scale;\n            }\n            scale.init(scaleOptions, options);\n        });\n        each(updated, (hasUpdated, id)=>{\n            if (!hasUpdated) {\n                delete scales[id];\n            }\n        });\n        each(scales, (scale)=>{\n            layouts.configure(this, scale, scale.options);\n            layouts.addBox(this, scale);\n        });\n    }\n _updateMetasets() {\n        const metasets = this._metasets;\n        const numData = this.data.datasets.length;\n        const numMeta = metasets.length;\n        metasets.sort((a, b)=>a.index - b.index);\n        if (numMeta > numData) {\n            for(let i = numData; i < numMeta; ++i){\n                this._destroyDatasetMeta(i);\n            }\n            metasets.splice(numData, numMeta - numData);\n        }\n        this._sortedMetasets = metasets.slice(0).sort(compare2Level('order', 'index'));\n    }\n _removeUnreferencedMetasets() {\n        const { _metasets: metasets , data: { datasets  }  } = this;\n        if (metasets.length > datasets.length) {\n            delete this._stacks;\n        }\n        metasets.forEach((meta, index)=>{\n            if (datasets.filter((x)=>x === meta._dataset).length === 0) {\n                this._destroyDatasetMeta(index);\n            }\n        });\n    }\n    buildOrUpdateControllers() {\n        const newControllers = [];\n        const datasets = this.data.datasets;\n        let i, ilen;\n        this._removeUnreferencedMetasets();\n        for(i = 0, ilen = datasets.length; i < ilen; i++){\n            const dataset = datasets[i];\n            let meta = this.getDatasetMeta(i);\n            const type = dataset.type || this.config.type;\n            if (meta.type && meta.type !== type) {\n                this._destroyDatasetMeta(i);\n                meta = this.getDatasetMeta(i);\n            }\n            meta.type = type;\n            meta.indexAxis = dataset.indexAxis || getIndexAxis(type, this.options);\n            meta.order = dataset.order || 0;\n            meta.index = i;\n            meta.label = '' + dataset.label;\n            meta.visible = this.isDatasetVisible(i);\n            if (meta.controller) {\n                meta.controller.updateIndex(i);\n                meta.controller.linkScales();\n            } else {\n                const ControllerClass = registry.getController(type);\n                const { datasetElementType , dataElementType  } = defaults.datasets[type];\n                Object.assign(ControllerClass, {\n                    dataElementType: registry.getElement(dataElementType),\n                    datasetElementType: datasetElementType && registry.getElement(datasetElementType)\n                });\n                meta.controller = new ControllerClass(this, i);\n                newControllers.push(meta.controller);\n            }\n        }\n        this._updateMetasets();\n        return newControllers;\n    }\n _resetElements() {\n        each(this.data.datasets, (dataset, datasetIndex)=>{\n            this.getDatasetMeta(datasetIndex).controller.reset();\n        }, this);\n    }\n reset() {\n        this._resetElements();\n        this.notifyPlugins('reset');\n    }\n    update(mode) {\n        const config = this.config;\n        config.update();\n        const options = this._options = config.createResolver(config.chartOptionScopes(), this.getContext());\n        const animsDisabled = this._animationsDisabled = !options.animation;\n        this._updateScales();\n        this._checkEventBindings();\n        this._updateHiddenIndices();\n        this._plugins.invalidate();\n        if (this.notifyPlugins('beforeUpdate', {\n            mode,\n            cancelable: true\n        }) === false) {\n            return;\n        }\n        const newControllers = this.buildOrUpdateControllers();\n        this.notifyPlugins('beforeElementsUpdate');\n        let minPadding = 0;\n        for(let i = 0, ilen = this.data.datasets.length; i < ilen; i++){\n            const { controller  } = this.getDatasetMeta(i);\n            const reset = !animsDisabled && newControllers.indexOf(controller) === -1;\n            controller.buildOrUpdateElements(reset);\n            minPadding = Math.max(+controller.getMaxOverflow(), minPadding);\n        }\n        minPadding = this._minPadding = options.layout.autoPadding ? minPadding : 0;\n        this._updateLayout(minPadding);\n        if (!animsDisabled) {\n            each(newControllers, (controller)=>{\n                controller.reset();\n            });\n        }\n        this._updateDatasets(mode);\n        this.notifyPlugins('afterUpdate', {\n            mode\n        });\n        this._layers.sort(compare2Level('z', '_idx'));\n        const { _active , _lastEvent  } = this;\n        if (_lastEvent) {\n            this._eventHandler(_lastEvent, true);\n        } else if (_active.length) {\n            this._updateHoverStyles(_active, _active, true);\n        }\n        this.render();\n    }\n _updateScales() {\n        each(this.scales, (scale)=>{\n            layouts.removeBox(this, scale);\n        });\n        this.ensureScalesHaveIDs();\n        this.buildOrUpdateScales();\n    }\n _checkEventBindings() {\n        const options = this.options;\n        const existingEvents = new Set(Object.keys(this._listeners));\n        const newEvents = new Set(options.events);\n        if (!setsEqual(existingEvents, newEvents) || !!this._responsiveListeners !== options.responsive) {\n            this.unbindEvents();\n            this.bindEvents();\n        }\n    }\n _updateHiddenIndices() {\n        const { _hiddenIndices  } = this;\n        const changes = this._getUniformDataChanges() || [];\n        for (const { method , start , count  } of changes){\n            const move = method === '_removeElements' ? -count : count;\n            moveNumericKeys(_hiddenIndices, start, move);\n        }\n    }\n _getUniformDataChanges() {\n        const _dataChanges = this._dataChanges;\n        if (!_dataChanges || !_dataChanges.length) {\n            return;\n        }\n        this._dataChanges = [];\n        const datasetCount = this.data.datasets.length;\n        const makeSet = (idx)=>new Set(_dataChanges.filter((c)=>c[0] === idx).map((c, i)=>i + ',' + c.splice(1).join(',')));\n        const changeSet = makeSet(0);\n        for(let i = 1; i < datasetCount; i++){\n            if (!setsEqual(changeSet, makeSet(i))) {\n                return;\n            }\n        }\n        return Array.from(changeSet).map((c)=>c.split(',')).map((a)=>({\n                method: a[1],\n                start: +a[2],\n                count: +a[3]\n            }));\n    }\n _updateLayout(minPadding) {\n        if (this.notifyPlugins('beforeLayout', {\n            cancelable: true\n        }) === false) {\n            return;\n        }\n        layouts.update(this, this.width, this.height, minPadding);\n        const area = this.chartArea;\n        const noArea = area.width <= 0 || area.height <= 0;\n        this._layers = [];\n        each(this.boxes, (box)=>{\n            if (noArea && box.position === 'chartArea') {\n                return;\n            }\n            if (box.configure) {\n                box.configure();\n            }\n            this._layers.push(...box._layers());\n        }, this);\n        this._layers.forEach((item, index)=>{\n            item._idx = index;\n        });\n        this.notifyPlugins('afterLayout');\n    }\n _updateDatasets(mode) {\n        if (this.notifyPlugins('beforeDatasetsUpdate', {\n            mode,\n            cancelable: true\n        }) === false) {\n            return;\n        }\n        for(let i = 0, ilen = this.data.datasets.length; i < ilen; ++i){\n            this.getDatasetMeta(i).controller.configure();\n        }\n        for(let i = 0, ilen = this.data.datasets.length; i < ilen; ++i){\n            this._updateDataset(i, isFunction(mode) ? mode({\n                datasetIndex: i\n            }) : mode);\n        }\n        this.notifyPlugins('afterDatasetsUpdate', {\n            mode\n        });\n    }\n _updateDataset(index, mode) {\n        const meta = this.getDatasetMeta(index);\n        const args = {\n            meta,\n            index,\n            mode,\n            cancelable: true\n        };\n        if (this.notifyPlugins('beforeDatasetUpdate', args) === false) {\n            return;\n        }\n        meta.controller._update(mode);\n        args.cancelable = false;\n        this.notifyPlugins('afterDatasetUpdate', args);\n    }\n    render() {\n        if (this.notifyPlugins('beforeRender', {\n            cancelable: true\n        }) === false) {\n            return;\n        }\n        if (animator.has(this)) {\n            if (this.attached && !animator.running(this)) {\n                animator.start(this);\n            }\n        } else {\n            this.draw();\n            onAnimationsComplete({\n                chart: this\n            });\n        }\n    }\n    draw() {\n        let i;\n        if (this._resizeBeforeDraw) {\n            const { width , height  } = this._resizeBeforeDraw;\n            this._resize(width, height);\n            this._resizeBeforeDraw = null;\n        }\n        this.clear();\n        if (this.width <= 0 || this.height <= 0) {\n            return;\n        }\n        if (this.notifyPlugins('beforeDraw', {\n            cancelable: true\n        }) === false) {\n            return;\n        }\n        const layers = this._layers;\n        for(i = 0; i < layers.length && layers[i].z <= 0; ++i){\n            layers[i].draw(this.chartArea);\n        }\n        this._drawDatasets();\n        for(; i < layers.length; ++i){\n            layers[i].draw(this.chartArea);\n        }\n        this.notifyPlugins('afterDraw');\n    }\n _getSortedDatasetMetas(filterVisible) {\n        const metasets = this._sortedMetasets;\n        const result = [];\n        let i, ilen;\n        for(i = 0, ilen = metasets.length; i < ilen; ++i){\n            const meta = metasets[i];\n            if (!filterVisible || meta.visible) {\n                result.push(meta);\n            }\n        }\n        return result;\n    }\n getSortedVisibleDatasetMetas() {\n        return this._getSortedDatasetMetas(true);\n    }\n _drawDatasets() {\n        if (this.notifyPlugins('beforeDatasetsDraw', {\n            cancelable: true\n        }) === false) {\n            return;\n        }\n        const metasets = this.getSortedVisibleDatasetMetas();\n        for(let i = metasets.length - 1; i >= 0; --i){\n            this._drawDataset(metasets[i]);\n        }\n        this.notifyPlugins('afterDatasetsDraw');\n    }\n _drawDataset(meta) {\n        const ctx = this.ctx;\n        const clip = meta._clip;\n        const useClip = !clip.disabled;\n        const area = getDatasetArea(meta, this.chartArea);\n        const args = {\n            meta,\n            index: meta.index,\n            cancelable: true\n        };\n        if (this.notifyPlugins('beforeDatasetDraw', args) === false) {\n            return;\n        }\n        if (useClip) {\n            clipArea(ctx, {\n                left: clip.left === false ? 0 : area.left - clip.left,\n                right: clip.right === false ? this.width : area.right + clip.right,\n                top: clip.top === false ? 0 : area.top - clip.top,\n                bottom: clip.bottom === false ? this.height : area.bottom + clip.bottom\n            });\n        }\n        meta.controller.draw();\n        if (useClip) {\n            unclipArea(ctx);\n        }\n        args.cancelable = false;\n        this.notifyPlugins('afterDatasetDraw', args);\n    }\n isPointInArea(point) {\n        return _isPointInArea(point, this.chartArea, this._minPadding);\n    }\n    getElementsAtEventForMode(e, mode, options, useFinalPosition) {\n        const method = Interaction.modes[mode];\n        if (typeof method === 'function') {\n            return method(this, e, options, useFinalPosition);\n        }\n        return [];\n    }\n    getDatasetMeta(datasetIndex) {\n        const dataset = this.data.datasets[datasetIndex];\n        const metasets = this._metasets;\n        let meta = metasets.filter((x)=>x && x._dataset === dataset).pop();\n        if (!meta) {\n            meta = {\n                type: null,\n                data: [],\n                dataset: null,\n                controller: null,\n                hidden: null,\n                xAxisID: null,\n                yAxisID: null,\n                order: dataset && dataset.order || 0,\n                index: datasetIndex,\n                _dataset: dataset,\n                _parsed: [],\n                _sorted: false\n            };\n            metasets.push(meta);\n        }\n        return meta;\n    }\n    getContext() {\n        return this.$context || (this.$context = createContext(null, {\n            chart: this,\n            type: 'chart'\n        }));\n    }\n    getVisibleDatasetCount() {\n        return this.getSortedVisibleDatasetMetas().length;\n    }\n    isDatasetVisible(datasetIndex) {\n        const dataset = this.data.datasets[datasetIndex];\n        if (!dataset) {\n            return false;\n        }\n        const meta = this.getDatasetMeta(datasetIndex);\n        return typeof meta.hidden === 'boolean' ? !meta.hidden : !dataset.hidden;\n    }\n    setDatasetVisibility(datasetIndex, visible) {\n        const meta = this.getDatasetMeta(datasetIndex);\n        meta.hidden = !visible;\n    }\n    toggleDataVisibility(index) {\n        this._hiddenIndices[index] = !this._hiddenIndices[index];\n    }\n    getDataVisibility(index) {\n        return !this._hiddenIndices[index];\n    }\n _updateVisibility(datasetIndex, dataIndex, visible) {\n        const mode = visible ? 'show' : 'hide';\n        const meta = this.getDatasetMeta(datasetIndex);\n        const anims = meta.controller._resolveAnimations(undefined, mode);\n        if (defined(dataIndex)) {\n            meta.data[dataIndex].hidden = !visible;\n            this.update();\n        } else {\n            this.setDatasetVisibility(datasetIndex, visible);\n            anims.update(meta, {\n                visible\n            });\n            this.update((ctx)=>ctx.datasetIndex === datasetIndex ? mode : undefined);\n        }\n    }\n    hide(datasetIndex, dataIndex) {\n        this._updateVisibility(datasetIndex, dataIndex, false);\n    }\n    show(datasetIndex, dataIndex) {\n        this._updateVisibility(datasetIndex, dataIndex, true);\n    }\n _destroyDatasetMeta(datasetIndex) {\n        const meta = this._metasets[datasetIndex];\n        if (meta && meta.controller) {\n            meta.controller._destroy();\n        }\n        delete this._metasets[datasetIndex];\n    }\n    _stop() {\n        let i, ilen;\n        this.stop();\n        animator.remove(this);\n        for(i = 0, ilen = this.data.datasets.length; i < ilen; ++i){\n            this._destroyDatasetMeta(i);\n        }\n    }\n    destroy() {\n        this.notifyPlugins('beforeDestroy');\n        const { canvas , ctx  } = this;\n        this._stop();\n        this.config.clearCache();\n        if (canvas) {\n            this.unbindEvents();\n            clearCanvas(canvas, ctx);\n            this.platform.releaseContext(ctx);\n            this.canvas = null;\n            this.ctx = null;\n        }\n        delete instances[this.id];\n        this.notifyPlugins('afterDestroy');\n    }\n    toBase64Image(...args) {\n        return this.canvas.toDataURL(...args);\n    }\n bindEvents() {\n        this.bindUserEvents();\n        if (this.options.responsive) {\n            this.bindResponsiveEvents();\n        } else {\n            this.attached = true;\n        }\n    }\n bindUserEvents() {\n        const listeners = this._listeners;\n        const platform = this.platform;\n        const _add = (type, listener)=>{\n            platform.addEventListener(this, type, listener);\n            listeners[type] = listener;\n        };\n        const listener = (e, x, y)=>{\n            e.offsetX = x;\n            e.offsetY = y;\n            this._eventHandler(e);\n        };\n        each(this.options.events, (type)=>_add(type, listener));\n    }\n bindResponsiveEvents() {\n        if (!this._responsiveListeners) {\n            this._responsiveListeners = {};\n        }\n        const listeners = this._responsiveListeners;\n        const platform = this.platform;\n        const _add = (type, listener)=>{\n            platform.addEventListener(this, type, listener);\n            listeners[type] = listener;\n        };\n        const _remove = (type, listener)=>{\n            if (listeners[type]) {\n                platform.removeEventListener(this, type, listener);\n                delete listeners[type];\n            }\n        };\n        const listener = (width, height)=>{\n            if (this.canvas) {\n                this.resize(width, height);\n            }\n        };\n        let detached;\n        const attached = ()=>{\n            _remove('attach', attached);\n            this.attached = true;\n            this.resize();\n            _add('resize', listener);\n            _add('detach', detached);\n        };\n        detached = ()=>{\n            this.attached = false;\n            _remove('resize', listener);\n            this._stop();\n            this._resize(0, 0);\n            _add('attach', attached);\n        };\n        if (platform.isAttached(this.canvas)) {\n            attached();\n        } else {\n            detached();\n        }\n    }\n unbindEvents() {\n        each(this._listeners, (listener, type)=>{\n            this.platform.removeEventListener(this, type, listener);\n        });\n        this._listeners = {};\n        each(this._responsiveListeners, (listener, type)=>{\n            this.platform.removeEventListener(this, type, listener);\n        });\n        this._responsiveListeners = undefined;\n    }\n    updateHoverStyle(items, mode, enabled) {\n        const prefix = enabled ? 'set' : 'remove';\n        let meta, item, i, ilen;\n        if (mode === 'dataset') {\n            meta = this.getDatasetMeta(items[0].datasetIndex);\n            meta.controller['_' + prefix + 'DatasetHoverStyle']();\n        }\n        for(i = 0, ilen = items.length; i < ilen; ++i){\n            item = items[i];\n            const controller = item && this.getDatasetMeta(item.datasetIndex).controller;\n            if (controller) {\n                controller[prefix + 'HoverStyle'](item.element, item.datasetIndex, item.index);\n            }\n        }\n    }\n getActiveElements() {\n        return this._active || [];\n    }\n setActiveElements(activeElements) {\n        const lastActive = this._active || [];\n        const active = activeElements.map(({ datasetIndex , index  })=>{\n            const meta = this.getDatasetMeta(datasetIndex);\n            if (!meta) {\n                throw new Error('No dataset found at index ' + datasetIndex);\n            }\n            return {\n                datasetIndex,\n                element: meta.data[index],\n                index\n            };\n        });\n        const changed = !_elementsEqual(active, lastActive);\n        if (changed) {\n            this._active = active;\n            this._lastEvent = null;\n            this._updateHoverStyles(active, lastActive);\n        }\n    }\n notifyPlugins(hook, args, filter) {\n        return this._plugins.notify(this, hook, args, filter);\n    }\n isPluginEnabled(pluginId) {\n        return this._plugins._cache.filter((p)=>p.plugin.id === pluginId).length === 1;\n    }\n _updateHoverStyles(active, lastActive, replay) {\n        const hoverOptions = this.options.hover;\n        const diff = (a, b)=>a.filter((x)=>!b.some((y)=>x.datasetIndex === y.datasetIndex && x.index === y.index));\n        const deactivated = diff(lastActive, active);\n        const activated = replay ? active : diff(active, lastActive);\n        if (deactivated.length) {\n            this.updateHoverStyle(deactivated, hoverOptions.mode, false);\n        }\n        if (activated.length && hoverOptions.mode) {\n            this.updateHoverStyle(activated, hoverOptions.mode, true);\n        }\n    }\n _eventHandler(e, replay) {\n        const args = {\n            event: e,\n            replay,\n            cancelable: true,\n            inChartArea: this.isPointInArea(e)\n        };\n        const eventFilter = (plugin)=>(plugin.options.events || this.options.events).includes(e.native.type);\n        if (this.notifyPlugins('beforeEvent', args, eventFilter) === false) {\n            return;\n        }\n        const changed = this._handleEvent(e, replay, args.inChartArea);\n        args.cancelable = false;\n        this.notifyPlugins('afterEvent', args, eventFilter);\n        if (changed || args.changed) {\n            this.render();\n        }\n        return this;\n    }\n _handleEvent(e, replay, inChartArea) {\n        const { _active: lastActive = [] , options  } = this;\n        const useFinalPosition = replay;\n        const active = this._getActiveElements(e, lastActive, inChartArea, useFinalPosition);\n        const isClick = _isClickEvent(e);\n        const lastEvent = determineLastEvent(e, this._lastEvent, inChartArea, isClick);\n        if (inChartArea) {\n            this._lastEvent = null;\n            callback(options.onHover, [\n                e,\n                active,\n                this\n            ], this);\n            if (isClick) {\n                callback(options.onClick, [\n                    e,\n                    active,\n                    this\n                ], this);\n            }\n        }\n        const changed = !_elementsEqual(active, lastActive);\n        if (changed || replay) {\n            this._active = active;\n            this._updateHoverStyles(active, lastActive, replay);\n        }\n        this._lastEvent = lastEvent;\n        return changed;\n    }\n _getActiveElements(e, lastActive, inChartArea, useFinalPosition) {\n        if (e.type === 'mouseout') {\n            return [];\n        }\n        if (!inChartArea) {\n            return lastActive;\n        }\n        const hoverOptions = this.options.hover;\n        return this.getElementsAtEventForMode(e, hoverOptions.mode, hoverOptions, useFinalPosition);\n    }\n}\nfunction invalidatePlugins() {\n    return each(Chart.instances, (chart)=>chart._plugins.invalidate());\n}\n\nfunction clipArc(ctx, element, endAngle) {\n    const { startAngle , pixelMargin , x , y , outerRadius , innerRadius  } = element;\n    let angleMargin = pixelMargin / outerRadius;\n    // Draw an inner border by clipping the arc and drawing a double-width border\n    // Enlarge the clipping arc by 0.33 pixels to eliminate glitches between borders\n    ctx.beginPath();\n    ctx.arc(x, y, outerRadius, startAngle - angleMargin, endAngle + angleMargin);\n    if (innerRadius > pixelMargin) {\n        angleMargin = pixelMargin / innerRadius;\n        ctx.arc(x, y, innerRadius, endAngle + angleMargin, startAngle - angleMargin, true);\n    } else {\n        ctx.arc(x, y, pixelMargin, endAngle + HALF_PI, startAngle - HALF_PI);\n    }\n    ctx.closePath();\n    ctx.clip();\n}\nfunction toRadiusCorners(value) {\n    return _readValueToProps(value, [\n        'outerStart',\n        'outerEnd',\n        'innerStart',\n        'innerEnd'\n    ]);\n}\n/**\n * Parse border radius from the provided options\n */ function parseBorderRadius$1(arc, innerRadius, outerRadius, angleDelta) {\n    const o = toRadiusCorners(arc.options.borderRadius);\n    const halfThickness = (outerRadius - innerRadius) / 2;\n    const innerLimit = Math.min(halfThickness, angleDelta * innerRadius / 2);\n    // Outer limits are complicated. We want to compute the available angular distance at\n    // a radius of outerRadius - borderRadius because for small angular distances, this term limits.\n    // We compute at r = outerRadius - borderRadius because this circle defines the center of the border corners.\n    //\n    // If the borderRadius is large, that value can become negative.\n    // This causes the outer borders to lose their radius entirely, which is rather unexpected. To solve that, if borderRadius > outerRadius\n    // we know that the thickness term will dominate and compute the limits at that point\n    const computeOuterLimit = (val)=>{\n        const outerArcLimit = (outerRadius - Math.min(halfThickness, val)) * angleDelta / 2;\n        return _limitValue(val, 0, Math.min(halfThickness, outerArcLimit));\n    };\n    return {\n        outerStart: computeOuterLimit(o.outerStart),\n        outerEnd: computeOuterLimit(o.outerEnd),\n        innerStart: _limitValue(o.innerStart, 0, innerLimit),\n        innerEnd: _limitValue(o.innerEnd, 0, innerLimit)\n    };\n}\n/**\n * Convert (r, 𝜃) to (x, y)\n */ function rThetaToXY(r, theta, x, y) {\n    return {\n        x: x + r * Math.cos(theta),\n        y: y + r * Math.sin(theta)\n    };\n}\n/**\n * Path the arc, respecting border radius by separating into left and right halves.\n *\n *   Start      End\n *\n *    1--->a--->2    Outer\n *   /           \\\n *   8           3\n *   |           |\n *   |           |\n *   7           4\n *   \\           /\n *    6<---b<---5    Inner\n */ function pathArc(ctx, element, offset, spacing, end, circular) {\n    const { x , y , startAngle: start , pixelMargin , innerRadius: innerR  } = element;\n    const outerRadius = Math.max(element.outerRadius + spacing + offset - pixelMargin, 0);\n    const innerRadius = innerR > 0 ? innerR + spacing + offset + pixelMargin : 0;\n    let spacingOffset = 0;\n    const alpha = end - start;\n    if (spacing) {\n        // When spacing is present, it is the same for all items\n        // So we adjust the start and end angle of the arc such that\n        // the distance is the same as it would be without the spacing\n        const noSpacingInnerRadius = innerR > 0 ? innerR - spacing : 0;\n        const noSpacingOuterRadius = outerRadius > 0 ? outerRadius - spacing : 0;\n        const avNogSpacingRadius = (noSpacingInnerRadius + noSpacingOuterRadius) / 2;\n        const adjustedAngle = avNogSpacingRadius !== 0 ? alpha * avNogSpacingRadius / (avNogSpacingRadius + spacing) : alpha;\n        spacingOffset = (alpha - adjustedAngle) / 2;\n    }\n    const beta = Math.max(0.001, alpha * outerRadius - offset / PI) / outerRadius;\n    const angleOffset = (alpha - beta) / 2;\n    const startAngle = start + angleOffset + spacingOffset;\n    const endAngle = end - angleOffset - spacingOffset;\n    const { outerStart , outerEnd , innerStart , innerEnd  } = parseBorderRadius$1(element, innerRadius, outerRadius, endAngle - startAngle);\n    const outerStartAdjustedRadius = outerRadius - outerStart;\n    const outerEndAdjustedRadius = outerRadius - outerEnd;\n    const outerStartAdjustedAngle = startAngle + outerStart / outerStartAdjustedRadius;\n    const outerEndAdjustedAngle = endAngle - outerEnd / outerEndAdjustedRadius;\n    const innerStartAdjustedRadius = innerRadius + innerStart;\n    const innerEndAdjustedRadius = innerRadius + innerEnd;\n    const innerStartAdjustedAngle = startAngle + innerStart / innerStartAdjustedRadius;\n    const innerEndAdjustedAngle = endAngle - innerEnd / innerEndAdjustedRadius;\n    ctx.beginPath();\n    if (circular) {\n        // The first arc segments from point 1 to point a to point 2\n        const outerMidAdjustedAngle = (outerStartAdjustedAngle + outerEndAdjustedAngle) / 2;\n        ctx.arc(x, y, outerRadius, outerStartAdjustedAngle, outerMidAdjustedAngle);\n        ctx.arc(x, y, outerRadius, outerMidAdjustedAngle, outerEndAdjustedAngle);\n        // The corner segment from point 2 to point 3\n        if (outerEnd > 0) {\n            const pCenter = rThetaToXY(outerEndAdjustedRadius, outerEndAdjustedAngle, x, y);\n            ctx.arc(pCenter.x, pCenter.y, outerEnd, outerEndAdjustedAngle, endAngle + HALF_PI);\n        }\n        // The line from point 3 to point 4\n        const p4 = rThetaToXY(innerEndAdjustedRadius, endAngle, x, y);\n        ctx.lineTo(p4.x, p4.y);\n        // The corner segment from point 4 to point 5\n        if (innerEnd > 0) {\n            const pCenter = rThetaToXY(innerEndAdjustedRadius, innerEndAdjustedAngle, x, y);\n            ctx.arc(pCenter.x, pCenter.y, innerEnd, endAngle + HALF_PI, innerEndAdjustedAngle + Math.PI);\n        }\n        // The inner arc from point 5 to point b to point 6\n        const innerMidAdjustedAngle = (endAngle - innerEnd / innerRadius + (startAngle + innerStart / innerRadius)) / 2;\n        ctx.arc(x, y, innerRadius, endAngle - innerEnd / innerRadius, innerMidAdjustedAngle, true);\n        ctx.arc(x, y, innerRadius, innerMidAdjustedAngle, startAngle + innerStart / innerRadius, true);\n        // The corner segment from point 6 to point 7\n        if (innerStart > 0) {\n            const pCenter = rThetaToXY(innerStartAdjustedRadius, innerStartAdjustedAngle, x, y);\n            ctx.arc(pCenter.x, pCenter.y, innerStart, innerStartAdjustedAngle + Math.PI, startAngle - HALF_PI);\n        }\n        // The line from point 7 to point 8\n        const p8 = rThetaToXY(outerStartAdjustedRadius, startAngle, x, y);\n        ctx.lineTo(p8.x, p8.y);\n        // The corner segment from point 8 to point 1\n        if (outerStart > 0) {\n            const pCenter = rThetaToXY(outerStartAdjustedRadius, outerStartAdjustedAngle, x, y);\n            ctx.arc(pCenter.x, pCenter.y, outerStart, startAngle - HALF_PI, outerStartAdjustedAngle);\n        }\n    } else {\n        ctx.moveTo(x, y);\n        const outerStartX = Math.cos(outerStartAdjustedAngle) * outerRadius + x;\n        const outerStartY = Math.sin(outerStartAdjustedAngle) * outerRadius + y;\n        ctx.lineTo(outerStartX, outerStartY);\n        const outerEndX = Math.cos(outerEndAdjustedAngle) * outerRadius + x;\n        const outerEndY = Math.sin(outerEndAdjustedAngle) * outerRadius + y;\n        ctx.lineTo(outerEndX, outerEndY);\n    }\n    ctx.closePath();\n}\nfunction drawArc(ctx, element, offset, spacing, circular) {\n    const { fullCircles , startAngle , circumference  } = element;\n    let endAngle = element.endAngle;\n    if (fullCircles) {\n        pathArc(ctx, element, offset, spacing, endAngle, circular);\n        for(let i = 0; i < fullCircles; ++i){\n            ctx.fill();\n        }\n        if (!isNaN(circumference)) {\n            endAngle = startAngle + (circumference % TAU || TAU);\n        }\n    }\n    pathArc(ctx, element, offset, spacing, endAngle, circular);\n    ctx.fill();\n    return endAngle;\n}\nfunction drawBorder(ctx, element, offset, spacing, circular) {\n    const { fullCircles , startAngle , circumference , options  } = element;\n    const { borderWidth , borderJoinStyle , borderDash , borderDashOffset  } = options;\n    const inner = options.borderAlign === 'inner';\n    if (!borderWidth) {\n        return;\n    }\n    ctx.setLineDash(borderDash || []);\n    ctx.lineDashOffset = borderDashOffset;\n    if (inner) {\n        ctx.lineWidth = borderWidth * 2;\n        ctx.lineJoin = borderJoinStyle || 'round';\n    } else {\n        ctx.lineWidth = borderWidth;\n        ctx.lineJoin = borderJoinStyle || 'bevel';\n    }\n    let endAngle = element.endAngle;\n    if (fullCircles) {\n        pathArc(ctx, element, offset, spacing, endAngle, circular);\n        for(let i = 0; i < fullCircles; ++i){\n            ctx.stroke();\n        }\n        if (!isNaN(circumference)) {\n            endAngle = startAngle + (circumference % TAU || TAU);\n        }\n    }\n    if (inner) {\n        clipArc(ctx, element, endAngle);\n    }\n    if (!fullCircles) {\n        pathArc(ctx, element, offset, spacing, endAngle, circular);\n        ctx.stroke();\n    }\n}\nclass ArcElement extends Element {\n    static id = 'arc';\n    static defaults = {\n        borderAlign: 'center',\n        borderColor: '#fff',\n        borderDash: [],\n        borderDashOffset: 0,\n        borderJoinStyle: undefined,\n        borderRadius: 0,\n        borderWidth: 2,\n        offset: 0,\n        spacing: 0,\n        angle: undefined,\n        circular: true\n    };\n    static defaultRoutes = {\n        backgroundColor: 'backgroundColor'\n    };\n    static descriptors = {\n        _scriptable: true,\n        _indexable: (name)=>name !== 'borderDash'\n    };\n    circumference;\n    endAngle;\n    fullCircles;\n    innerRadius;\n    outerRadius;\n    pixelMargin;\n    startAngle;\n    constructor(cfg){\n        super();\n        this.options = undefined;\n        this.circumference = undefined;\n        this.startAngle = undefined;\n        this.endAngle = undefined;\n        this.innerRadius = undefined;\n        this.outerRadius = undefined;\n        this.pixelMargin = 0;\n        this.fullCircles = 0;\n        if (cfg) {\n            Object.assign(this, cfg);\n        }\n    }\n    inRange(chartX, chartY, useFinalPosition) {\n        const point = this.getProps([\n            'x',\n            'y'\n        ], useFinalPosition);\n        const { angle , distance  } = getAngleFromPoint(point, {\n            x: chartX,\n            y: chartY\n        });\n        const { startAngle , endAngle , innerRadius , outerRadius , circumference  } = this.getProps([\n            'startAngle',\n            'endAngle',\n            'innerRadius',\n            'outerRadius',\n            'circumference'\n        ], useFinalPosition);\n        const rAdjust = (this.options.spacing + this.options.borderWidth) / 2;\n        const _circumference = valueOrDefault(circumference, endAngle - startAngle);\n        const betweenAngles = _circumference >= TAU || _angleBetween(angle, startAngle, endAngle);\n        const withinRadius = _isBetween(distance, innerRadius + rAdjust, outerRadius + rAdjust);\n        return betweenAngles && withinRadius;\n    }\n    getCenterPoint(useFinalPosition) {\n        const { x , y , startAngle , endAngle , innerRadius , outerRadius  } = this.getProps([\n            'x',\n            'y',\n            'startAngle',\n            'endAngle',\n            'innerRadius',\n            'outerRadius'\n        ], useFinalPosition);\n        const { offset , spacing  } = this.options;\n        const halfAngle = (startAngle + endAngle) / 2;\n        const halfRadius = (innerRadius + outerRadius + spacing + offset) / 2;\n        return {\n            x: x + Math.cos(halfAngle) * halfRadius,\n            y: y + Math.sin(halfAngle) * halfRadius\n        };\n    }\n    tooltipPosition(useFinalPosition) {\n        return this.getCenterPoint(useFinalPosition);\n    }\n    draw(ctx) {\n        const { options , circumference  } = this;\n        const offset = (options.offset || 0) / 4;\n        const spacing = (options.spacing || 0) / 2;\n        const circular = options.circular;\n        this.pixelMargin = options.borderAlign === 'inner' ? 0.33 : 0;\n        this.fullCircles = circumference > TAU ? Math.floor(circumference / TAU) : 0;\n        if (circumference === 0 || this.innerRadius < 0 || this.outerRadius < 0) {\n            return;\n        }\n        ctx.save();\n        const halfAngle = (this.startAngle + this.endAngle) / 2;\n        ctx.translate(Math.cos(halfAngle) * offset, Math.sin(halfAngle) * offset);\n        const fix = 1 - Math.sin(Math.min(PI, circumference || 0));\n        const radiusOffset = offset * fix;\n        ctx.fillStyle = options.backgroundColor;\n        ctx.strokeStyle = options.borderColor;\n        drawArc(ctx, this, radiusOffset, spacing, circular);\n        drawBorder(ctx, this, radiusOffset, spacing, circular);\n        ctx.restore();\n    }\n}\n\nfunction setStyle(ctx, options, style = options) {\n    ctx.lineCap = valueOrDefault(style.borderCapStyle, options.borderCapStyle);\n    ctx.setLineDash(valueOrDefault(style.borderDash, options.borderDash));\n    ctx.lineDashOffset = valueOrDefault(style.borderDashOffset, options.borderDashOffset);\n    ctx.lineJoin = valueOrDefault(style.borderJoinStyle, options.borderJoinStyle);\n    ctx.lineWidth = valueOrDefault(style.borderWidth, options.borderWidth);\n    ctx.strokeStyle = valueOrDefault(style.borderColor, options.borderColor);\n}\nfunction lineTo(ctx, previous, target) {\n    ctx.lineTo(target.x, target.y);\n}\n function getLineMethod(options) {\n    if (options.stepped) {\n        return _steppedLineTo;\n    }\n    if (options.tension || options.cubicInterpolationMode === 'monotone') {\n        return _bezierCurveTo;\n    }\n    return lineTo;\n}\nfunction pathVars(points, segment, params = {}) {\n    const count = points.length;\n    const { start: paramsStart = 0 , end: paramsEnd = count - 1  } = params;\n    const { start: segmentStart , end: segmentEnd  } = segment;\n    const start = Math.max(paramsStart, segmentStart);\n    const end = Math.min(paramsEnd, segmentEnd);\n    const outside = paramsStart < segmentStart && paramsEnd < segmentStart || paramsStart > segmentEnd && paramsEnd > segmentEnd;\n    return {\n        count,\n        start,\n        loop: segment.loop,\n        ilen: end < start && !outside ? count + end - start : end - start\n    };\n}\n function pathSegment(ctx, line, segment, params) {\n    const { points , options  } = line;\n    const { count , start , loop , ilen  } = pathVars(points, segment, params);\n    const lineMethod = getLineMethod(options);\n    let { move =true , reverse  } = params || {};\n    let i, point, prev;\n    for(i = 0; i <= ilen; ++i){\n        point = points[(start + (reverse ? ilen - i : i)) % count];\n        if (point.skip) {\n            continue;\n        } else if (move) {\n            ctx.moveTo(point.x, point.y);\n            move = false;\n        } else {\n            lineMethod(ctx, prev, point, reverse, options.stepped);\n        }\n        prev = point;\n    }\n    if (loop) {\n        point = points[(start + (reverse ? ilen : 0)) % count];\n        lineMethod(ctx, prev, point, reverse, options.stepped);\n    }\n    return !!loop;\n}\n function fastPathSegment(ctx, line, segment, params) {\n    const points = line.points;\n    const { count , start , ilen  } = pathVars(points, segment, params);\n    const { move =true , reverse  } = params || {};\n    let avgX = 0;\n    let countX = 0;\n    let i, point, prevX, minY, maxY, lastY;\n    const pointIndex = (index)=>(start + (reverse ? ilen - index : index)) % count;\n    const drawX = ()=>{\n        if (minY !== maxY) {\n            ctx.lineTo(avgX, maxY);\n            ctx.lineTo(avgX, minY);\n            ctx.lineTo(avgX, lastY);\n        }\n    };\n    if (move) {\n        point = points[pointIndex(0)];\n        ctx.moveTo(point.x, point.y);\n    }\n    for(i = 0; i <= ilen; ++i){\n        point = points[pointIndex(i)];\n        if (point.skip) {\n            continue;\n        }\n        const x = point.x;\n        const y = point.y;\n        const truncX = x | 0;\n        if (truncX === prevX) {\n            if (y < minY) {\n                minY = y;\n            } else if (y > maxY) {\n                maxY = y;\n            }\n            avgX = (countX * avgX + x) / ++countX;\n        } else {\n            drawX();\n            ctx.lineTo(x, y);\n            prevX = truncX;\n            countX = 0;\n            minY = maxY = y;\n        }\n        lastY = y;\n    }\n    drawX();\n}\n function _getSegmentMethod(line) {\n    const opts = line.options;\n    const borderDash = opts.borderDash && opts.borderDash.length;\n    const useFastPath = !line._decimated && !line._loop && !opts.tension && opts.cubicInterpolationMode !== 'monotone' && !opts.stepped && !borderDash;\n    return useFastPath ? fastPathSegment : pathSegment;\n}\n function _getInterpolationMethod(options) {\n    if (options.stepped) {\n        return _steppedInterpolation;\n    }\n    if (options.tension || options.cubicInterpolationMode === 'monotone') {\n        return _bezierInterpolation;\n    }\n    return _pointInLine;\n}\nfunction strokePathWithCache(ctx, line, start, count) {\n    let path = line._path;\n    if (!path) {\n        path = line._path = new Path2D();\n        if (line.path(path, start, count)) {\n            path.closePath();\n        }\n    }\n    setStyle(ctx, line.options);\n    ctx.stroke(path);\n}\nfunction strokePathDirect(ctx, line, start, count) {\n    const { segments , options  } = line;\n    const segmentMethod = _getSegmentMethod(line);\n    for (const segment of segments){\n        setStyle(ctx, options, segment.style);\n        ctx.beginPath();\n        if (segmentMethod(ctx, line, segment, {\n            start,\n            end: start + count - 1\n        })) {\n            ctx.closePath();\n        }\n        ctx.stroke();\n    }\n}\nconst usePath2D = typeof Path2D === 'function';\nfunction draw(ctx, line, start, count) {\n    if (usePath2D && !line.options.segment) {\n        strokePathWithCache(ctx, line, start, count);\n    } else {\n        strokePathDirect(ctx, line, start, count);\n    }\n}\nclass LineElement extends Element {\n    static id = 'line';\n static defaults = {\n        borderCapStyle: 'butt',\n        borderDash: [],\n        borderDashOffset: 0,\n        borderJoinStyle: 'miter',\n        borderWidth: 3,\n        capBezierPoints: true,\n        cubicInterpolationMode: 'default',\n        fill: false,\n        spanGaps: false,\n        stepped: false,\n        tension: 0\n    };\n static defaultRoutes = {\n        backgroundColor: 'backgroundColor',\n        borderColor: 'borderColor'\n    };\n    static descriptors = {\n        _scriptable: true,\n        _indexable: (name)=>name !== 'borderDash' && name !== 'fill'\n    };\n    constructor(cfg){\n        super();\n        this.animated = true;\n        this.options = undefined;\n        this._chart = undefined;\n        this._loop = undefined;\n        this._fullLoop = undefined;\n        this._path = undefined;\n        this._points = undefined;\n        this._segments = undefined;\n        this._decimated = false;\n        this._pointsUpdated = false;\n        this._datasetIndex = undefined;\n        if (cfg) {\n            Object.assign(this, cfg);\n        }\n    }\n    updateControlPoints(chartArea, indexAxis) {\n        const options = this.options;\n        if ((options.tension || options.cubicInterpolationMode === 'monotone') && !options.stepped && !this._pointsUpdated) {\n            const loop = options.spanGaps ? this._loop : this._fullLoop;\n            _updateBezierControlPoints(this._points, options, chartArea, loop, indexAxis);\n            this._pointsUpdated = true;\n        }\n    }\n    set points(points) {\n        this._points = points;\n        delete this._segments;\n        delete this._path;\n        this._pointsUpdated = false;\n    }\n    get points() {\n        return this._points;\n    }\n    get segments() {\n        return this._segments || (this._segments = _computeSegments(this, this.options.segment));\n    }\n first() {\n        const segments = this.segments;\n        const points = this.points;\n        return segments.length && points[segments[0].start];\n    }\n last() {\n        const segments = this.segments;\n        const points = this.points;\n        const count = segments.length;\n        return count && points[segments[count - 1].end];\n    }\n interpolate(point, property) {\n        const options = this.options;\n        const value = point[property];\n        const points = this.points;\n        const segments = _boundSegments(this, {\n            property,\n            start: value,\n            end: value\n        });\n        if (!segments.length) {\n            return;\n        }\n        const result = [];\n        const _interpolate = _getInterpolationMethod(options);\n        let i, ilen;\n        for(i = 0, ilen = segments.length; i < ilen; ++i){\n            const { start , end  } = segments[i];\n            const p1 = points[start];\n            const p2 = points[end];\n            if (p1 === p2) {\n                result.push(p1);\n                continue;\n            }\n            const t = Math.abs((value - p1[property]) / (p2[property] - p1[property]));\n            const interpolated = _interpolate(p1, p2, t, options.stepped);\n            interpolated[property] = point[property];\n            result.push(interpolated);\n        }\n        return result.length === 1 ? result[0] : result;\n    }\n pathSegment(ctx, segment, params) {\n        const segmentMethod = _getSegmentMethod(this);\n        return segmentMethod(ctx, this, segment, params);\n    }\n path(ctx, start, count) {\n        const segments = this.segments;\n        const segmentMethod = _getSegmentMethod(this);\n        let loop = this._loop;\n        start = start || 0;\n        count = count || this.points.length - start;\n        for (const segment of segments){\n            loop &= segmentMethod(ctx, this, segment, {\n                start,\n                end: start + count - 1\n            });\n        }\n        return !!loop;\n    }\n draw(ctx, chartArea, start, count) {\n        const options = this.options || {};\n        const points = this.points || [];\n        if (points.length && options.borderWidth) {\n            ctx.save();\n            draw(ctx, this, start, count);\n            ctx.restore();\n        }\n        if (this.animated) {\n            this._pointsUpdated = false;\n            this._path = undefined;\n        }\n    }\n}\n\nfunction inRange$1(el, pos, axis, useFinalPosition) {\n    const options = el.options;\n    const { [axis]: value  } = el.getProps([\n        axis\n    ], useFinalPosition);\n    return Math.abs(pos - value) < options.radius + options.hitRadius;\n}\nclass PointElement extends Element {\n    static id = 'point';\n    parsed;\n    skip;\n    stop;\n    /**\n   * @type {any}\n   */ static defaults = {\n        borderWidth: 1,\n        hitRadius: 1,\n        hoverBorderWidth: 1,\n        hoverRadius: 4,\n        pointStyle: 'circle',\n        radius: 3,\n        rotation: 0\n    };\n    /**\n   * @type {any}\n   */ static defaultRoutes = {\n        backgroundColor: 'backgroundColor',\n        borderColor: 'borderColor'\n    };\n    constructor(cfg){\n        super();\n        this.options = undefined;\n        this.parsed = undefined;\n        this.skip = undefined;\n        this.stop = undefined;\n        if (cfg) {\n            Object.assign(this, cfg);\n        }\n    }\n    inRange(mouseX, mouseY, useFinalPosition) {\n        const options = this.options;\n        const { x , y  } = this.getProps([\n            'x',\n            'y'\n        ], useFinalPosition);\n        return Math.pow(mouseX - x, 2) + Math.pow(mouseY - y, 2) < Math.pow(options.hitRadius + options.radius, 2);\n    }\n    inXRange(mouseX, useFinalPosition) {\n        return inRange$1(this, mouseX, 'x', useFinalPosition);\n    }\n    inYRange(mouseY, useFinalPosition) {\n        return inRange$1(this, mouseY, 'y', useFinalPosition);\n    }\n    getCenterPoint(useFinalPosition) {\n        const { x , y  } = this.getProps([\n            'x',\n            'y'\n        ], useFinalPosition);\n        return {\n            x,\n            y\n        };\n    }\n    size(options) {\n        options = options || this.options || {};\n        let radius = options.radius || 0;\n        radius = Math.max(radius, radius && options.hoverRadius || 0);\n        const borderWidth = radius && options.borderWidth || 0;\n        return (radius + borderWidth) * 2;\n    }\n    draw(ctx, area) {\n        const options = this.options;\n        if (this.skip || options.radius < 0.1 || !_isPointInArea(this, area, this.size(options) / 2)) {\n            return;\n        }\n        ctx.strokeStyle = options.borderColor;\n        ctx.lineWidth = options.borderWidth;\n        ctx.fillStyle = options.backgroundColor;\n        drawPoint(ctx, options, this.x, this.y);\n    }\n    getRange() {\n        const options = this.options || {};\n        // @ts-expect-error Fallbacks should never be hit in practice\n        return options.radius + options.hitRadius;\n    }\n}\n\nfunction getBarBounds(bar, useFinalPosition) {\n    const { x , y , base , width , height  } =  bar.getProps([\n        'x',\n        'y',\n        'base',\n        'width',\n        'height'\n    ], useFinalPosition);\n    let left, right, top, bottom, half;\n    if (bar.horizontal) {\n        half = height / 2;\n        left = Math.min(x, base);\n        right = Math.max(x, base);\n        top = y - half;\n        bottom = y + half;\n    } else {\n        half = width / 2;\n        left = x - half;\n        right = x + half;\n        top = Math.min(y, base);\n        bottom = Math.max(y, base);\n    }\n    return {\n        left,\n        top,\n        right,\n        bottom\n    };\n}\nfunction skipOrLimit(skip, value, min, max) {\n    return skip ? 0 : _limitValue(value, min, max);\n}\nfunction parseBorderWidth(bar, maxW, maxH) {\n    const value = bar.options.borderWidth;\n    const skip = bar.borderSkipped;\n    const o = toTRBL(value);\n    return {\n        t: skipOrLimit(skip.top, o.top, 0, maxH),\n        r: skipOrLimit(skip.right, o.right, 0, maxW),\n        b: skipOrLimit(skip.bottom, o.bottom, 0, maxH),\n        l: skipOrLimit(skip.left, o.left, 0, maxW)\n    };\n}\nfunction parseBorderRadius(bar, maxW, maxH) {\n    const { enableBorderRadius  } = bar.getProps([\n        'enableBorderRadius'\n    ]);\n    const value = bar.options.borderRadius;\n    const o = toTRBLCorners(value);\n    const maxR = Math.min(maxW, maxH);\n    const skip = bar.borderSkipped;\n    const enableBorder = enableBorderRadius || isObject(value);\n    return {\n        topLeft: skipOrLimit(!enableBorder || skip.top || skip.left, o.topLeft, 0, maxR),\n        topRight: skipOrLimit(!enableBorder || skip.top || skip.right, o.topRight, 0, maxR),\n        bottomLeft: skipOrLimit(!enableBorder || skip.bottom || skip.left, o.bottomLeft, 0, maxR),\n        bottomRight: skipOrLimit(!enableBorder || skip.bottom || skip.right, o.bottomRight, 0, maxR)\n    };\n}\nfunction boundingRects(bar) {\n    const bounds = getBarBounds(bar);\n    const width = bounds.right - bounds.left;\n    const height = bounds.bottom - bounds.top;\n    const border = parseBorderWidth(bar, width / 2, height / 2);\n    const radius = parseBorderRadius(bar, width / 2, height / 2);\n    return {\n        outer: {\n            x: bounds.left,\n            y: bounds.top,\n            w: width,\n            h: height,\n            radius\n        },\n        inner: {\n            x: bounds.left + border.l,\n            y: bounds.top + border.t,\n            w: width - border.l - border.r,\n            h: height - border.t - border.b,\n            radius: {\n                topLeft: Math.max(0, radius.topLeft - Math.max(border.t, border.l)),\n                topRight: Math.max(0, radius.topRight - Math.max(border.t, border.r)),\n                bottomLeft: Math.max(0, radius.bottomLeft - Math.max(border.b, border.l)),\n                bottomRight: Math.max(0, radius.bottomRight - Math.max(border.b, border.r))\n            }\n        }\n    };\n}\nfunction inRange(bar, x, y, useFinalPosition) {\n    const skipX = x === null;\n    const skipY = y === null;\n    const skipBoth = skipX && skipY;\n    const bounds = bar && !skipBoth && getBarBounds(bar, useFinalPosition);\n    return bounds && (skipX || _isBetween(x, bounds.left, bounds.right)) && (skipY || _isBetween(y, bounds.top, bounds.bottom));\n}\nfunction hasRadius(radius) {\n    return radius.topLeft || radius.topRight || radius.bottomLeft || radius.bottomRight;\n}\n function addNormalRectPath(ctx, rect) {\n    ctx.rect(rect.x, rect.y, rect.w, rect.h);\n}\nfunction inflateRect(rect, amount, refRect = {}) {\n    const x = rect.x !== refRect.x ? -amount : 0;\n    const y = rect.y !== refRect.y ? -amount : 0;\n    const w = (rect.x + rect.w !== refRect.x + refRect.w ? amount : 0) - x;\n    const h = (rect.y + rect.h !== refRect.y + refRect.h ? amount : 0) - y;\n    return {\n        x: rect.x + x,\n        y: rect.y + y,\n        w: rect.w + w,\n        h: rect.h + h,\n        radius: rect.radius\n    };\n}\nclass BarElement extends Element {\n    static id = 'bar';\n static defaults = {\n        borderSkipped: 'start',\n        borderWidth: 0,\n        borderRadius: 0,\n        inflateAmount: 'auto',\n        pointStyle: undefined\n    };\n static defaultRoutes = {\n        backgroundColor: 'backgroundColor',\n        borderColor: 'borderColor'\n    };\n    constructor(cfg){\n        super();\n        this.options = undefined;\n        this.horizontal = undefined;\n        this.base = undefined;\n        this.width = undefined;\n        this.height = undefined;\n        this.inflateAmount = undefined;\n        if (cfg) {\n            Object.assign(this, cfg);\n        }\n    }\n    draw(ctx) {\n        const { inflateAmount , options: { borderColor , backgroundColor  }  } = this;\n        const { inner , outer  } = boundingRects(this);\n        const addRectPath = hasRadius(outer.radius) ? addRoundedRectPath : addNormalRectPath;\n        ctx.save();\n        if (outer.w !== inner.w || outer.h !== inner.h) {\n            ctx.beginPath();\n            addRectPath(ctx, inflateRect(outer, inflateAmount, inner));\n            ctx.clip();\n            addRectPath(ctx, inflateRect(inner, -inflateAmount, outer));\n            ctx.fillStyle = borderColor;\n            ctx.fill('evenodd');\n        }\n        ctx.beginPath();\n        addRectPath(ctx, inflateRect(inner, inflateAmount));\n        ctx.fillStyle = backgroundColor;\n        ctx.fill();\n        ctx.restore();\n    }\n    inRange(mouseX, mouseY, useFinalPosition) {\n        return inRange(this, mouseX, mouseY, useFinalPosition);\n    }\n    inXRange(mouseX, useFinalPosition) {\n        return inRange(this, mouseX, null, useFinalPosition);\n    }\n    inYRange(mouseY, useFinalPosition) {\n        return inRange(this, null, mouseY, useFinalPosition);\n    }\n    getCenterPoint(useFinalPosition) {\n        const { x , y , base , horizontal  } =  this.getProps([\n            'x',\n            'y',\n            'base',\n            'horizontal'\n        ], useFinalPosition);\n        return {\n            x: horizontal ? (x + base) / 2 : x,\n            y: horizontal ? y : (y + base) / 2\n        };\n    }\n    getRange(axis) {\n        return axis === 'x' ? this.width / 2 : this.height / 2;\n    }\n}\n\nvar elements = /*#__PURE__*/Object.freeze({\n__proto__: null,\nArcElement: ArcElement,\nBarElement: BarElement,\nLineElement: LineElement,\nPointElement: PointElement\n});\n\nconst BORDER_COLORS = [\n    'rgb(54, 162, 235)',\n    'rgb(255, 99, 132)',\n    'rgb(255, 159, 64)',\n    'rgb(255, 205, 86)',\n    'rgb(75, 192, 192)',\n    'rgb(153, 102, 255)',\n    'rgb(201, 203, 207)' // grey\n];\n// Border colors with 50% transparency\nconst BACKGROUND_COLORS = /* #__PURE__ */ BORDER_COLORS.map((color)=>color.replace('rgb(', 'rgba(').replace(')', ', 0.5)'));\nfunction getBorderColor(i) {\n    return BORDER_COLORS[i % BORDER_COLORS.length];\n}\nfunction getBackgroundColor(i) {\n    return BACKGROUND_COLORS[i % BACKGROUND_COLORS.length];\n}\nfunction colorizeDefaultDataset(dataset, i) {\n    dataset.borderColor = getBorderColor(i);\n    dataset.backgroundColor = getBackgroundColor(i);\n    return ++i;\n}\nfunction colorizeDoughnutDataset(dataset, i) {\n    dataset.backgroundColor = dataset.data.map(()=>getBorderColor(i++));\n    return i;\n}\nfunction colorizePolarAreaDataset(dataset, i) {\n    dataset.backgroundColor = dataset.data.map(()=>getBackgroundColor(i++));\n    return i;\n}\nfunction getColorizer(chart) {\n    let i = 0;\n    return (dataset, datasetIndex)=>{\n        const controller = chart.getDatasetMeta(datasetIndex).controller;\n        if (controller instanceof DoughnutController) {\n            i = colorizeDoughnutDataset(dataset, i);\n        } else if (controller instanceof PolarAreaController) {\n            i = colorizePolarAreaDataset(dataset, i);\n        } else if (controller) {\n            i = colorizeDefaultDataset(dataset, i);\n        }\n    };\n}\nfunction containsColorsDefinitions(descriptors) {\n    let k;\n    for(k in descriptors){\n        if (descriptors[k].borderColor || descriptors[k].backgroundColor) {\n            return true;\n        }\n    }\n    return false;\n}\nfunction containsColorsDefinition(descriptor) {\n    return descriptor && (descriptor.borderColor || descriptor.backgroundColor);\n}\nvar plugin_colors = {\n    id: 'colors',\n    defaults: {\n        enabled: true,\n        forceOverride: false\n    },\n    beforeLayout (chart, _args, options) {\n        if (!options.enabled) {\n            return;\n        }\n        const { data: { datasets  } , options: chartOptions  } = chart.config;\n        const { elements  } = chartOptions;\n        if (!options.forceOverride && (containsColorsDefinitions(datasets) || containsColorsDefinition(chartOptions) || elements && containsColorsDefinitions(elements))) {\n            return;\n        }\n        const colorizer = getColorizer(chart);\n        datasets.forEach(colorizer);\n    }\n};\n\nfunction lttbDecimation(data, start, count, availableWidth, options) {\n const samples = options.samples || availableWidth;\n    if (samples >= count) {\n        return data.slice(start, start + count);\n    }\n    const decimated = [];\n    const bucketWidth = (count - 2) / (samples - 2);\n    let sampledIndex = 0;\n    const endIndex = start + count - 1;\n    let a = start;\n    let i, maxAreaPoint, maxArea, area, nextA;\n    decimated[sampledIndex++] = data[a];\n    for(i = 0; i < samples - 2; i++){\n        let avgX = 0;\n        let avgY = 0;\n        let j;\n        const avgRangeStart = Math.floor((i + 1) * bucketWidth) + 1 + start;\n        const avgRangeEnd = Math.min(Math.floor((i + 2) * bucketWidth) + 1, count) + start;\n        const avgRangeLength = avgRangeEnd - avgRangeStart;\n        for(j = avgRangeStart; j < avgRangeEnd; j++){\n            avgX += data[j].x;\n            avgY += data[j].y;\n        }\n        avgX /= avgRangeLength;\n        avgY /= avgRangeLength;\n        const rangeOffs = Math.floor(i * bucketWidth) + 1 + start;\n        const rangeTo = Math.min(Math.floor((i + 1) * bucketWidth) + 1, count) + start;\n        const { x: pointAx , y: pointAy  } = data[a];\n        maxArea = area = -1;\n        for(j = rangeOffs; j < rangeTo; j++){\n            area = 0.5 * Math.abs((pointAx - avgX) * (data[j].y - pointAy) - (pointAx - data[j].x) * (avgY - pointAy));\n            if (area > maxArea) {\n                maxArea = area;\n                maxAreaPoint = data[j];\n                nextA = j;\n            }\n        }\n        decimated[sampledIndex++] = maxAreaPoint;\n        a = nextA;\n    }\n    decimated[sampledIndex++] = data[endIndex];\n    return decimated;\n}\nfunction minMaxDecimation(data, start, count, availableWidth) {\n    let avgX = 0;\n    let countX = 0;\n    let i, point, x, y, prevX, minIndex, maxIndex, startIndex, minY, maxY;\n    const decimated = [];\n    const endIndex = start + count - 1;\n    const xMin = data[start].x;\n    const xMax = data[endIndex].x;\n    const dx = xMax - xMin;\n    for(i = start; i < start + count; ++i){\n        point = data[i];\n        x = (point.x - xMin) / dx * availableWidth;\n        y = point.y;\n        const truncX = x | 0;\n        if (truncX === prevX) {\n            if (y < minY) {\n                minY = y;\n                minIndex = i;\n            } else if (y > maxY) {\n                maxY = y;\n                maxIndex = i;\n            }\n            avgX = (countX * avgX + point.x) / ++countX;\n        } else {\n            const lastIndex = i - 1;\n            if (!isNullOrUndef(minIndex) && !isNullOrUndef(maxIndex)) {\n                const intermediateIndex1 = Math.min(minIndex, maxIndex);\n                const intermediateIndex2 = Math.max(minIndex, maxIndex);\n                if (intermediateIndex1 !== startIndex && intermediateIndex1 !== lastIndex) {\n                    decimated.push({\n                        ...data[intermediateIndex1],\n                        x: avgX\n                    });\n                }\n                if (intermediateIndex2 !== startIndex && intermediateIndex2 !== lastIndex) {\n                    decimated.push({\n                        ...data[intermediateIndex2],\n                        x: avgX\n                    });\n                }\n            }\n            if (i > 0 && lastIndex !== startIndex) {\n                decimated.push(data[lastIndex]);\n            }\n            decimated.push(point);\n            prevX = truncX;\n            countX = 0;\n            minY = maxY = y;\n            minIndex = maxIndex = startIndex = i;\n        }\n    }\n    return decimated;\n}\nfunction cleanDecimatedDataset(dataset) {\n    if (dataset._decimated) {\n        const data = dataset._data;\n        delete dataset._decimated;\n        delete dataset._data;\n        Object.defineProperty(dataset, 'data', {\n            configurable: true,\n            enumerable: true,\n            writable: true,\n            value: data\n        });\n    }\n}\nfunction cleanDecimatedData(chart) {\n    chart.data.datasets.forEach((dataset)=>{\n        cleanDecimatedDataset(dataset);\n    });\n}\nfunction getStartAndCountOfVisiblePointsSimplified(meta, points) {\n    const pointCount = points.length;\n    let start = 0;\n    let count;\n    const { iScale  } = meta;\n    const { min , max , minDefined , maxDefined  } = iScale.getUserBounds();\n    if (minDefined) {\n        start = _limitValue(_lookupByKey(points, iScale.axis, min).lo, 0, pointCount - 1);\n    }\n    if (maxDefined) {\n        count = _limitValue(_lookupByKey(points, iScale.axis, max).hi + 1, start, pointCount) - start;\n    } else {\n        count = pointCount - start;\n    }\n    return {\n        start,\n        count\n    };\n}\nvar plugin_decimation = {\n    id: 'decimation',\n    defaults: {\n        algorithm: 'min-max',\n        enabled: false\n    },\n    beforeElementsUpdate: (chart, args, options)=>{\n        if (!options.enabled) {\n            cleanDecimatedData(chart);\n            return;\n        }\n        const availableWidth = chart.width;\n        chart.data.datasets.forEach((dataset, datasetIndex)=>{\n            const { _data , indexAxis  } = dataset;\n            const meta = chart.getDatasetMeta(datasetIndex);\n            const data = _data || dataset.data;\n            if (resolve([\n                indexAxis,\n                chart.options.indexAxis\n            ]) === 'y') {\n                return;\n            }\n            if (!meta.controller.supportsDecimation) {\n                return;\n            }\n            const xAxis = chart.scales[meta.xAxisID];\n            if (xAxis.type !== 'linear' && xAxis.type !== 'time') {\n                return;\n            }\n            if (chart.options.parsing) {\n                return;\n            }\n            let { start , count  } = getStartAndCountOfVisiblePointsSimplified(meta, data);\n            const threshold = options.threshold || 4 * availableWidth;\n            if (count <= threshold) {\n                cleanDecimatedDataset(dataset);\n                return;\n            }\n            if (isNullOrUndef(_data)) {\n                dataset._data = data;\n                delete dataset.data;\n                Object.defineProperty(dataset, 'data', {\n                    configurable: true,\n                    enumerable: true,\n                    get: function() {\n                        return this._decimated;\n                    },\n                    set: function(d) {\n                        this._data = d;\n                    }\n                });\n            }\n            let decimated;\n            switch(options.algorithm){\n                case 'lttb':\n                    decimated = lttbDecimation(data, start, count, availableWidth, options);\n                    break;\n                case 'min-max':\n                    decimated = minMaxDecimation(data, start, count, availableWidth);\n                    break;\n                default:\n                    throw new Error(`Unsupported decimation algorithm '${options.algorithm}'`);\n            }\n            dataset._decimated = decimated;\n        });\n    },\n    destroy (chart) {\n        cleanDecimatedData(chart);\n    }\n};\n\nfunction _segments(line, target, property) {\n    const segments = line.segments;\n    const points = line.points;\n    const tpoints = target.points;\n    const parts = [];\n    for (const segment of segments){\n        let { start , end  } = segment;\n        end = _findSegmentEnd(start, end, points);\n        const bounds = _getBounds(property, points[start], points[end], segment.loop);\n        if (!target.segments) {\n            parts.push({\n                source: segment,\n                target: bounds,\n                start: points[start],\n                end: points[end]\n            });\n            continue;\n        }\n        const targetSegments = _boundSegments(target, bounds);\n        for (const tgt of targetSegments){\n            const subBounds = _getBounds(property, tpoints[tgt.start], tpoints[tgt.end], tgt.loop);\n            const fillSources = _boundSegment(segment, points, subBounds);\n            for (const fillSource of fillSources){\n                parts.push({\n                    source: fillSource,\n                    target: tgt,\n                    start: {\n                        [property]: _getEdge(bounds, subBounds, 'start', Math.max)\n                    },\n                    end: {\n                        [property]: _getEdge(bounds, subBounds, 'end', Math.min)\n                    }\n                });\n            }\n        }\n    }\n    return parts;\n}\nfunction _getBounds(property, first, last, loop) {\n    if (loop) {\n        return;\n    }\n    let start = first[property];\n    let end = last[property];\n    if (property === 'angle') {\n        start = _normalizeAngle(start);\n        end = _normalizeAngle(end);\n    }\n    return {\n        property,\n        start,\n        end\n    };\n}\nfunction _pointsFromSegments(boundary, line) {\n    const { x =null , y =null  } = boundary || {};\n    const linePoints = line.points;\n    const points = [];\n    line.segments.forEach(({ start , end  })=>{\n        end = _findSegmentEnd(start, end, linePoints);\n        const first = linePoints[start];\n        const last = linePoints[end];\n        if (y !== null) {\n            points.push({\n                x: first.x,\n                y\n            });\n            points.push({\n                x: last.x,\n                y\n            });\n        } else if (x !== null) {\n            points.push({\n                x,\n                y: first.y\n            });\n            points.push({\n                x,\n                y: last.y\n            });\n        }\n    });\n    return points;\n}\nfunction _findSegmentEnd(start, end, points) {\n    for(; end > start; end--){\n        const point = points[end];\n        if (!isNaN(point.x) && !isNaN(point.y)) {\n            break;\n        }\n    }\n    return end;\n}\nfunction _getEdge(a, b, prop, fn) {\n    if (a && b) {\n        return fn(a[prop], b[prop]);\n    }\n    return a ? a[prop] : b ? b[prop] : 0;\n}\n\nfunction _createBoundaryLine(boundary, line) {\n    let points = [];\n    let _loop = false;\n    if (isArray(boundary)) {\n        _loop = true;\n        points = boundary;\n    } else {\n        points = _pointsFromSegments(boundary, line);\n    }\n    return points.length ? new LineElement({\n        points,\n        options: {\n            tension: 0\n        },\n        _loop,\n        _fullLoop: _loop\n    }) : null;\n}\nfunction _shouldApplyFill(source) {\n    return source && source.fill !== false;\n}\n\nfunction _resolveTarget(sources, index, propagate) {\n    const source = sources[index];\n    let fill = source.fill;\n    const visited = [\n        index\n    ];\n    let target;\n    if (!propagate) {\n        return fill;\n    }\n    while(fill !== false && visited.indexOf(fill) === -1){\n        if (!isNumberFinite(fill)) {\n            return fill;\n        }\n        target = sources[fill];\n        if (!target) {\n            return false;\n        }\n        if (target.visible) {\n            return fill;\n        }\n        visited.push(fill);\n        fill = target.fill;\n    }\n    return false;\n}\n function _decodeFill(line, index, count) {\n     const fill = parseFillOption(line);\n    if (isObject(fill)) {\n        return isNaN(fill.value) ? false : fill;\n    }\n    let target = parseFloat(fill);\n    if (isNumberFinite(target) && Math.floor(target) === target) {\n        return decodeTargetIndex(fill[0], index, target, count);\n    }\n    return [\n        'origin',\n        'start',\n        'end',\n        'stack',\n        'shape'\n    ].indexOf(fill) >= 0 && fill;\n}\nfunction decodeTargetIndex(firstCh, index, target, count) {\n    if (firstCh === '-' || firstCh === '+') {\n        target = index + target;\n    }\n    if (target === index || target < 0 || target >= count) {\n        return false;\n    }\n    return target;\n}\n function _getTargetPixel(fill, scale) {\n    let pixel = null;\n    if (fill === 'start') {\n        pixel = scale.bottom;\n    } else if (fill === 'end') {\n        pixel = scale.top;\n    } else if (isObject(fill)) {\n        pixel = scale.getPixelForValue(fill.value);\n    } else if (scale.getBasePixel) {\n        pixel = scale.getBasePixel();\n    }\n    return pixel;\n}\n function _getTargetValue(fill, scale, startValue) {\n    let value;\n    if (fill === 'start') {\n        value = startValue;\n    } else if (fill === 'end') {\n        value = scale.options.reverse ? scale.min : scale.max;\n    } else if (isObject(fill)) {\n        value = fill.value;\n    } else {\n        value = scale.getBaseValue();\n    }\n    return value;\n}\n function parseFillOption(line) {\n    const options = line.options;\n    const fillOption = options.fill;\n    let fill = valueOrDefault(fillOption && fillOption.target, fillOption);\n    if (fill === undefined) {\n        fill = !!options.backgroundColor;\n    }\n    if (fill === false || fill === null) {\n        return false;\n    }\n    if (fill === true) {\n        return 'origin';\n    }\n    return fill;\n}\n\nfunction _buildStackLine(source) {\n    const { scale , index , line  } = source;\n    const points = [];\n    const segments = line.segments;\n    const sourcePoints = line.points;\n    const linesBelow = getLinesBelow(scale, index);\n    linesBelow.push(_createBoundaryLine({\n        x: null,\n        y: scale.bottom\n    }, line));\n    for(let i = 0; i < segments.length; i++){\n        const segment = segments[i];\n        for(let j = segment.start; j <= segment.end; j++){\n            addPointsBelow(points, sourcePoints[j], linesBelow);\n        }\n    }\n    return new LineElement({\n        points,\n        options: {}\n    });\n}\n function getLinesBelow(scale, index) {\n    const below = [];\n    const metas = scale.getMatchingVisibleMetas('line');\n    for(let i = 0; i < metas.length; i++){\n        const meta = metas[i];\n        if (meta.index === index) {\n            break;\n        }\n        if (!meta.hidden) {\n            below.unshift(meta.dataset);\n        }\n    }\n    return below;\n}\n function addPointsBelow(points, sourcePoint, linesBelow) {\n    const postponed = [];\n    for(let j = 0; j < linesBelow.length; j++){\n        const line = linesBelow[j];\n        const { first , last , point  } = findPoint(line, sourcePoint, 'x');\n        if (!point || first && last) {\n            continue;\n        }\n        if (first) {\n            postponed.unshift(point);\n        } else {\n            points.push(point);\n            if (!last) {\n                break;\n            }\n        }\n    }\n    points.push(...postponed);\n}\n function findPoint(line, sourcePoint, property) {\n    const point = line.interpolate(sourcePoint, property);\n    if (!point) {\n        return {};\n    }\n    const pointValue = point[property];\n    const segments = line.segments;\n    const linePoints = line.points;\n    let first = false;\n    let last = false;\n    for(let i = 0; i < segments.length; i++){\n        const segment = segments[i];\n        const firstValue = linePoints[segment.start][property];\n        const lastValue = linePoints[segment.end][property];\n        if (_isBetween(pointValue, firstValue, lastValue)) {\n            first = pointValue === firstValue;\n            last = pointValue === lastValue;\n            break;\n        }\n    }\n    return {\n        first,\n        last,\n        point\n    };\n}\n\nclass simpleArc {\n    constructor(opts){\n        this.x = opts.x;\n        this.y = opts.y;\n        this.radius = opts.radius;\n    }\n    pathSegment(ctx, bounds, opts) {\n        const { x , y , radius  } = this;\n        bounds = bounds || {\n            start: 0,\n            end: TAU\n        };\n        ctx.arc(x, y, radius, bounds.end, bounds.start, true);\n        return !opts.bounds;\n    }\n    interpolate(point) {\n        const { x , y , radius  } = this;\n        const angle = point.angle;\n        return {\n            x: x + Math.cos(angle) * radius,\n            y: y + Math.sin(angle) * radius,\n            angle\n        };\n    }\n}\n\nfunction _getTarget(source) {\n    const { chart , fill , line  } = source;\n    if (isNumberFinite(fill)) {\n        return getLineByIndex(chart, fill);\n    }\n    if (fill === 'stack') {\n        return _buildStackLine(source);\n    }\n    if (fill === 'shape') {\n        return true;\n    }\n    const boundary = computeBoundary(source);\n    if (boundary instanceof simpleArc) {\n        return boundary;\n    }\n    return _createBoundaryLine(boundary, line);\n}\n function getLineByIndex(chart, index) {\n    const meta = chart.getDatasetMeta(index);\n    const visible = meta && chart.isDatasetVisible(index);\n    return visible ? meta.dataset : null;\n}\nfunction computeBoundary(source) {\n    const scale = source.scale || {};\n    if (scale.getPointPositionForValue) {\n        return computeCircularBoundary(source);\n    }\n    return computeLinearBoundary(source);\n}\nfunction computeLinearBoundary(source) {\n    const { scale ={} , fill  } = source;\n    const pixel = _getTargetPixel(fill, scale);\n    if (isNumberFinite(pixel)) {\n        const horizontal = scale.isHorizontal();\n        return {\n            x: horizontal ? pixel : null,\n            y: horizontal ? null : pixel\n        };\n    }\n    return null;\n}\nfunction computeCircularBoundary(source) {\n    const { scale , fill  } = source;\n    const options = scale.options;\n    const length = scale.getLabels().length;\n    const start = options.reverse ? scale.max : scale.min;\n    const value = _getTargetValue(fill, scale, start);\n    const target = [];\n    if (options.grid.circular) {\n        const center = scale.getPointPositionForValue(0, start);\n        return new simpleArc({\n            x: center.x,\n            y: center.y,\n            radius: scale.getDistanceFromCenterForValue(value)\n        });\n    }\n    for(let i = 0; i < length; ++i){\n        target.push(scale.getPointPositionForValue(i, value));\n    }\n    return target;\n}\n\nfunction _drawfill(ctx, source, area) {\n    const target = _getTarget(source);\n    const { line , scale , axis  } = source;\n    const lineOpts = line.options;\n    const fillOption = lineOpts.fill;\n    const color = lineOpts.backgroundColor;\n    const { above =color , below =color  } = fillOption || {};\n    if (target && line.points.length) {\n        clipArea(ctx, area);\n        doFill(ctx, {\n            line,\n            target,\n            above,\n            below,\n            area,\n            scale,\n            axis\n        });\n        unclipArea(ctx);\n    }\n}\nfunction doFill(ctx, cfg) {\n    const { line , target , above , below , area , scale  } = cfg;\n    const property = line._loop ? 'angle' : cfg.axis;\n    ctx.save();\n    if (property === 'x' && below !== above) {\n        clipVertical(ctx, target, area.top);\n        fill(ctx, {\n            line,\n            target,\n            color: above,\n            scale,\n            property\n        });\n        ctx.restore();\n        ctx.save();\n        clipVertical(ctx, target, area.bottom);\n    }\n    fill(ctx, {\n        line,\n        target,\n        color: below,\n        scale,\n        property\n    });\n    ctx.restore();\n}\nfunction clipVertical(ctx, target, clipY) {\n    const { segments , points  } = target;\n    let first = true;\n    let lineLoop = false;\n    ctx.beginPath();\n    for (const segment of segments){\n        const { start , end  } = segment;\n        const firstPoint = points[start];\n        const lastPoint = points[_findSegmentEnd(start, end, points)];\n        if (first) {\n            ctx.moveTo(firstPoint.x, firstPoint.y);\n            first = false;\n        } else {\n            ctx.lineTo(firstPoint.x, clipY);\n            ctx.lineTo(firstPoint.x, firstPoint.y);\n        }\n        lineLoop = !!target.pathSegment(ctx, segment, {\n            move: lineLoop\n        });\n        if (lineLoop) {\n            ctx.closePath();\n        } else {\n            ctx.lineTo(lastPoint.x, clipY);\n        }\n    }\n    ctx.lineTo(target.first().x, clipY);\n    ctx.closePath();\n    ctx.clip();\n}\nfunction fill(ctx, cfg) {\n    const { line , target , property , color , scale  } = cfg;\n    const segments = _segments(line, target, property);\n    for (const { source: src , target: tgt , start , end  } of segments){\n        const { style: { backgroundColor =color  } = {}  } = src;\n        const notShape = target !== true;\n        ctx.save();\n        ctx.fillStyle = backgroundColor;\n        clipBounds(ctx, scale, notShape && _getBounds(property, start, end));\n        ctx.beginPath();\n        const lineLoop = !!line.pathSegment(ctx, src);\n        let loop;\n        if (notShape) {\n            if (lineLoop) {\n                ctx.closePath();\n            } else {\n                interpolatedLineTo(ctx, target, end, property);\n            }\n            const targetLoop = !!target.pathSegment(ctx, tgt, {\n                move: lineLoop,\n                reverse: true\n            });\n            loop = lineLoop && targetLoop;\n            if (!loop) {\n                interpolatedLineTo(ctx, target, start, property);\n            }\n        }\n        ctx.closePath();\n        ctx.fill(loop ? 'evenodd' : 'nonzero');\n        ctx.restore();\n    }\n}\nfunction clipBounds(ctx, scale, bounds) {\n    const { top , bottom  } = scale.chart.chartArea;\n    const { property , start , end  } = bounds || {};\n    if (property === 'x') {\n        ctx.beginPath();\n        ctx.rect(start, top, end - start, bottom - top);\n        ctx.clip();\n    }\n}\nfunction interpolatedLineTo(ctx, target, point, property) {\n    const interpolatedPoint = target.interpolate(point, property);\n    if (interpolatedPoint) {\n        ctx.lineTo(interpolatedPoint.x, interpolatedPoint.y);\n    }\n}\n\nvar index = {\n    id: 'filler',\n    afterDatasetsUpdate (chart, _args, options) {\n        const count = (chart.data.datasets || []).length;\n        const sources = [];\n        let meta, i, line, source;\n        for(i = 0; i < count; ++i){\n            meta = chart.getDatasetMeta(i);\n            line = meta.dataset;\n            source = null;\n            if (line && line.options && line instanceof LineElement) {\n                source = {\n                    visible: chart.isDatasetVisible(i),\n                    index: i,\n                    fill: _decodeFill(line, i, count),\n                    chart,\n                    axis: meta.controller.options.indexAxis,\n                    scale: meta.vScale,\n                    line\n                };\n            }\n            meta.$filler = source;\n            sources.push(source);\n        }\n        for(i = 0; i < count; ++i){\n            source = sources[i];\n            if (!source || source.fill === false) {\n                continue;\n            }\n            source.fill = _resolveTarget(sources, i, options.propagate);\n        }\n    },\n    beforeDraw (chart, _args, options) {\n        const draw = options.drawTime === 'beforeDraw';\n        const metasets = chart.getSortedVisibleDatasetMetas();\n        const area = chart.chartArea;\n        for(let i = metasets.length - 1; i >= 0; --i){\n            const source = metasets[i].$filler;\n            if (!source) {\n                continue;\n            }\n            source.line.updateControlPoints(area, source.axis);\n            if (draw && source.fill) {\n                _drawfill(chart.ctx, source, area);\n            }\n        }\n    },\n    beforeDatasetsDraw (chart, _args, options) {\n        if (options.drawTime !== 'beforeDatasetsDraw') {\n            return;\n        }\n        const metasets = chart.getSortedVisibleDatasetMetas();\n        for(let i = metasets.length - 1; i >= 0; --i){\n            const source = metasets[i].$filler;\n            if (_shouldApplyFill(source)) {\n                _drawfill(chart.ctx, source, chart.chartArea);\n            }\n        }\n    },\n    beforeDatasetDraw (chart, args, options) {\n        const source = args.meta.$filler;\n        if (!_shouldApplyFill(source) || options.drawTime !== 'beforeDatasetDraw') {\n            return;\n        }\n        _drawfill(chart.ctx, source, chart.chartArea);\n    },\n    defaults: {\n        propagate: true,\n        drawTime: 'beforeDatasetDraw'\n    }\n};\n\nconst getBoxSize = (labelOpts, fontSize)=>{\n    let { boxHeight =fontSize , boxWidth =fontSize  } = labelOpts;\n    if (labelOpts.usePointStyle) {\n        boxHeight = Math.min(boxHeight, fontSize);\n        boxWidth = labelOpts.pointStyleWidth || Math.min(boxWidth, fontSize);\n    }\n    return {\n        boxWidth,\n        boxHeight,\n        itemHeight: Math.max(fontSize, boxHeight)\n    };\n};\nconst itemsEqual = (a, b)=>a !== null && b !== null && a.datasetIndex === b.datasetIndex && a.index === b.index;\nclass Legend extends Element {\n constructor(config){\n        super();\n        this._added = false;\n        this.legendHitBoxes = [];\n this._hoveredItem = null;\n        this.doughnutMode = false;\n        this.chart = config.chart;\n        this.options = config.options;\n        this.ctx = config.ctx;\n        this.legendItems = undefined;\n        this.columnSizes = undefined;\n        this.lineWidths = undefined;\n        this.maxHeight = undefined;\n        this.maxWidth = undefined;\n        this.top = undefined;\n        this.bottom = undefined;\n        this.left = undefined;\n        this.right = undefined;\n        this.height = undefined;\n        this.width = undefined;\n        this._margins = undefined;\n        this.position = undefined;\n        this.weight = undefined;\n        this.fullSize = undefined;\n    }\n    update(maxWidth, maxHeight, margins) {\n        this.maxWidth = maxWidth;\n        this.maxHeight = maxHeight;\n        this._margins = margins;\n        this.setDimensions();\n        this.buildLabels();\n        this.fit();\n    }\n    setDimensions() {\n        if (this.isHorizontal()) {\n            this.width = this.maxWidth;\n            this.left = this._margins.left;\n            this.right = this.width;\n        } else {\n            this.height = this.maxHeight;\n            this.top = this._margins.top;\n            this.bottom = this.height;\n        }\n    }\n    buildLabels() {\n        const labelOpts = this.options.labels || {};\n        let legendItems = callback(labelOpts.generateLabels, [\n            this.chart\n        ], this) || [];\n        if (labelOpts.filter) {\n            legendItems = legendItems.filter((item)=>labelOpts.filter(item, this.chart.data));\n        }\n        if (labelOpts.sort) {\n            legendItems = legendItems.sort((a, b)=>labelOpts.sort(a, b, this.chart.data));\n        }\n        if (this.options.reverse) {\n            legendItems.reverse();\n        }\n        this.legendItems = legendItems;\n    }\n    fit() {\n        const { options , ctx  } = this;\n        if (!options.display) {\n            this.width = this.height = 0;\n            return;\n        }\n        const labelOpts = options.labels;\n        const labelFont = toFont(labelOpts.font);\n        const fontSize = labelFont.size;\n        const titleHeight = this._computeTitleHeight();\n        const { boxWidth , itemHeight  } = getBoxSize(labelOpts, fontSize);\n        let width, height;\n        ctx.font = labelFont.string;\n        if (this.isHorizontal()) {\n            width = this.maxWidth;\n            height = this._fitRows(titleHeight, fontSize, boxWidth, itemHeight) + 10;\n        } else {\n            height = this.maxHeight;\n            width = this._fitCols(titleHeight, labelFont, boxWidth, itemHeight) + 10;\n        }\n        this.width = Math.min(width, options.maxWidth || this.maxWidth);\n        this.height = Math.min(height, options.maxHeight || this.maxHeight);\n    }\n _fitRows(titleHeight, fontSize, boxWidth, itemHeight) {\n        const { ctx , maxWidth , options: { labels: { padding  }  }  } = this;\n        const hitboxes = this.legendHitBoxes = [];\n        const lineWidths = this.lineWidths = [\n            0\n        ];\n        const lineHeight = itemHeight + padding;\n        let totalHeight = titleHeight;\n        ctx.textAlign = 'left';\n        ctx.textBaseline = 'middle';\n        let row = -1;\n        let top = -lineHeight;\n        this.legendItems.forEach((legendItem, i)=>{\n            const itemWidth = boxWidth + fontSize / 2 + ctx.measureText(legendItem.text).width;\n            if (i === 0 || lineWidths[lineWidths.length - 1] + itemWidth + 2 * padding > maxWidth) {\n                totalHeight += lineHeight;\n                lineWidths[lineWidths.length - (i > 0 ? 0 : 1)] = 0;\n                top += lineHeight;\n                row++;\n            }\n            hitboxes[i] = {\n                left: 0,\n                top,\n                row,\n                width: itemWidth,\n                height: itemHeight\n            };\n            lineWidths[lineWidths.length - 1] += itemWidth + padding;\n        });\n        return totalHeight;\n    }\n    _fitCols(titleHeight, labelFont, boxWidth, _itemHeight) {\n        const { ctx , maxHeight , options: { labels: { padding  }  }  } = this;\n        const hitboxes = this.legendHitBoxes = [];\n        const columnSizes = this.columnSizes = [];\n        const heightLimit = maxHeight - titleHeight;\n        let totalWidth = padding;\n        let currentColWidth = 0;\n        let currentColHeight = 0;\n        let left = 0;\n        let col = 0;\n        this.legendItems.forEach((legendItem, i)=>{\n            const { itemWidth , itemHeight  } = calculateItemSize(boxWidth, labelFont, ctx, legendItem, _itemHeight);\n            if (i > 0 && currentColHeight + itemHeight + 2 * padding > heightLimit) {\n                totalWidth += currentColWidth + padding;\n                columnSizes.push({\n                    width: currentColWidth,\n                    height: currentColHeight\n                });\n                left += currentColWidth + padding;\n                col++;\n                currentColWidth = currentColHeight = 0;\n            }\n            hitboxes[i] = {\n                left,\n                top: currentColHeight,\n                col,\n                width: itemWidth,\n                height: itemHeight\n            };\n            currentColWidth = Math.max(currentColWidth, itemWidth);\n            currentColHeight += itemHeight + padding;\n        });\n        totalWidth += currentColWidth;\n        columnSizes.push({\n            width: currentColWidth,\n            height: currentColHeight\n        });\n        return totalWidth;\n    }\n    adjustHitBoxes() {\n        if (!this.options.display) {\n            return;\n        }\n        const titleHeight = this._computeTitleHeight();\n        const { legendHitBoxes: hitboxes , options: { align , labels: { padding  } , rtl  }  } = this;\n        const rtlHelper = getRtlAdapter(rtl, this.left, this.width);\n        if (this.isHorizontal()) {\n            let row = 0;\n            let left = _alignStartEnd(align, this.left + padding, this.right - this.lineWidths[row]);\n            for (const hitbox of hitboxes){\n                if (row !== hitbox.row) {\n                    row = hitbox.row;\n                    left = _alignStartEnd(align, this.left + padding, this.right - this.lineWidths[row]);\n                }\n                hitbox.top += this.top + titleHeight + padding;\n                hitbox.left = rtlHelper.leftForLtr(rtlHelper.x(left), hitbox.width);\n                left += hitbox.width + padding;\n            }\n        } else {\n            let col = 0;\n            let top = _alignStartEnd(align, this.top + titleHeight + padding, this.bottom - this.columnSizes[col].height);\n            for (const hitbox of hitboxes){\n                if (hitbox.col !== col) {\n                    col = hitbox.col;\n                    top = _alignStartEnd(align, this.top + titleHeight + padding, this.bottom - this.columnSizes[col].height);\n                }\n                hitbox.top = top;\n                hitbox.left += this.left + padding;\n                hitbox.left = rtlHelper.leftForLtr(rtlHelper.x(hitbox.left), hitbox.width);\n                top += hitbox.height + padding;\n            }\n        }\n    }\n    isHorizontal() {\n        return this.options.position === 'top' || this.options.position === 'bottom';\n    }\n    draw() {\n        if (this.options.display) {\n            const ctx = this.ctx;\n            clipArea(ctx, this);\n            this._draw();\n            unclipArea(ctx);\n        }\n    }\n _draw() {\n        const { options: opts , columnSizes , lineWidths , ctx  } = this;\n        const { align , labels: labelOpts  } = opts;\n        const defaultColor = defaults.color;\n        const rtlHelper = getRtlAdapter(opts.rtl, this.left, this.width);\n        const labelFont = toFont(labelOpts.font);\n        const { padding  } = labelOpts;\n        const fontSize = labelFont.size;\n        const halfFontSize = fontSize / 2;\n        let cursor;\n        this.drawTitle();\n        ctx.textAlign = rtlHelper.textAlign('left');\n        ctx.textBaseline = 'middle';\n        ctx.lineWidth = 0.5;\n        ctx.font = labelFont.string;\n        const { boxWidth , boxHeight , itemHeight  } = getBoxSize(labelOpts, fontSize);\n        const drawLegendBox = function(x, y, legendItem) {\n            if (isNaN(boxWidth) || boxWidth <= 0 || isNaN(boxHeight) || boxHeight < 0) {\n                return;\n            }\n            ctx.save();\n            const lineWidth = valueOrDefault(legendItem.lineWidth, 1);\n            ctx.fillStyle = valueOrDefault(legendItem.fillStyle, defaultColor);\n            ctx.lineCap = valueOrDefault(legendItem.lineCap, 'butt');\n            ctx.lineDashOffset = valueOrDefault(legendItem.lineDashOffset, 0);\n            ctx.lineJoin = valueOrDefault(legendItem.lineJoin, 'miter');\n            ctx.lineWidth = lineWidth;\n            ctx.strokeStyle = valueOrDefault(legendItem.strokeStyle, defaultColor);\n            ctx.setLineDash(valueOrDefault(legendItem.lineDash, []));\n            if (labelOpts.usePointStyle) {\n                const drawOptions = {\n                    radius: boxHeight * Math.SQRT2 / 2,\n                    pointStyle: legendItem.pointStyle,\n                    rotation: legendItem.rotation,\n                    borderWidth: lineWidth\n                };\n                const centerX = rtlHelper.xPlus(x, boxWidth / 2);\n                const centerY = y + halfFontSize;\n                drawPointLegend(ctx, drawOptions, centerX, centerY, labelOpts.pointStyleWidth && boxWidth);\n            } else {\n                const yBoxTop = y + Math.max((fontSize - boxHeight) / 2, 0);\n                const xBoxLeft = rtlHelper.leftForLtr(x, boxWidth);\n                const borderRadius = toTRBLCorners(legendItem.borderRadius);\n                ctx.beginPath();\n                if (Object.values(borderRadius).some((v)=>v !== 0)) {\n                    addRoundedRectPath(ctx, {\n                        x: xBoxLeft,\n                        y: yBoxTop,\n                        w: boxWidth,\n                        h: boxHeight,\n                        radius: borderRadius\n                    });\n                } else {\n                    ctx.rect(xBoxLeft, yBoxTop, boxWidth, boxHeight);\n                }\n                ctx.fill();\n                if (lineWidth !== 0) {\n                    ctx.stroke();\n                }\n            }\n            ctx.restore();\n        };\n        const fillText = function(x, y, legendItem) {\n            renderText(ctx, legendItem.text, x, y + itemHeight / 2, labelFont, {\n                strikethrough: legendItem.hidden,\n                textAlign: rtlHelper.textAlign(legendItem.textAlign)\n            });\n        };\n        const isHorizontal = this.isHorizontal();\n        const titleHeight = this._computeTitleHeight();\n        if (isHorizontal) {\n            cursor = {\n                x: _alignStartEnd(align, this.left + padding, this.right - lineWidths[0]),\n                y: this.top + padding + titleHeight,\n                line: 0\n            };\n        } else {\n            cursor = {\n                x: this.left + padding,\n                y: _alignStartEnd(align, this.top + titleHeight + padding, this.bottom - columnSizes[0].height),\n                line: 0\n            };\n        }\n        overrideTextDirection(this.ctx, opts.textDirection);\n        const lineHeight = itemHeight + padding;\n        this.legendItems.forEach((legendItem, i)=>{\n            ctx.strokeStyle = legendItem.fontColor;\n            ctx.fillStyle = legendItem.fontColor;\n            const textWidth = ctx.measureText(legendItem.text).width;\n            const textAlign = rtlHelper.textAlign(legendItem.textAlign || (legendItem.textAlign = labelOpts.textAlign));\n            const width = boxWidth + halfFontSize + textWidth;\n            let x = cursor.x;\n            let y = cursor.y;\n            rtlHelper.setWidth(this.width);\n            if (isHorizontal) {\n                if (i > 0 && x + width + padding > this.right) {\n                    y = cursor.y += lineHeight;\n                    cursor.line++;\n                    x = cursor.x = _alignStartEnd(align, this.left + padding, this.right - lineWidths[cursor.line]);\n                }\n            } else if (i > 0 && y + lineHeight > this.bottom) {\n                x = cursor.x = x + columnSizes[cursor.line].width + padding;\n                cursor.line++;\n                y = cursor.y = _alignStartEnd(align, this.top + titleHeight + padding, this.bottom - columnSizes[cursor.line].height);\n            }\n            const realX = rtlHelper.x(x);\n            drawLegendBox(realX, y, legendItem);\n            x = _textX(textAlign, x + boxWidth + halfFontSize, isHorizontal ? x + width : this.right, opts.rtl);\n            fillText(rtlHelper.x(x), y, legendItem);\n            if (isHorizontal) {\n                cursor.x += width + padding;\n            } else if (typeof legendItem.text !== 'string') {\n                const fontLineHeight = labelFont.lineHeight;\n                cursor.y += calculateLegendItemHeight(legendItem, fontLineHeight) + padding;\n            } else {\n                cursor.y += lineHeight;\n            }\n        });\n        restoreTextDirection(this.ctx, opts.textDirection);\n    }\n drawTitle() {\n        const opts = this.options;\n        const titleOpts = opts.title;\n        const titleFont = toFont(titleOpts.font);\n        const titlePadding = toPadding(titleOpts.padding);\n        if (!titleOpts.display) {\n            return;\n        }\n        const rtlHelper = getRtlAdapter(opts.rtl, this.left, this.width);\n        const ctx = this.ctx;\n        const position = titleOpts.position;\n        const halfFontSize = titleFont.size / 2;\n        const topPaddingPlusHalfFontSize = titlePadding.top + halfFontSize;\n        let y;\n        let left = this.left;\n        let maxWidth = this.width;\n        if (this.isHorizontal()) {\n            maxWidth = Math.max(...this.lineWidths);\n            y = this.top + topPaddingPlusHalfFontSize;\n            left = _alignStartEnd(opts.align, left, this.right - maxWidth);\n        } else {\n            const maxHeight = this.columnSizes.reduce((acc, size)=>Math.max(acc, size.height), 0);\n            y = topPaddingPlusHalfFontSize + _alignStartEnd(opts.align, this.top, this.bottom - maxHeight - opts.labels.padding - this._computeTitleHeight());\n        }\n        const x = _alignStartEnd(position, left, left + maxWidth);\n        ctx.textAlign = rtlHelper.textAlign(_toLeftRightCenter(position));\n        ctx.textBaseline = 'middle';\n        ctx.strokeStyle = titleOpts.color;\n        ctx.fillStyle = titleOpts.color;\n        ctx.font = titleFont.string;\n        renderText(ctx, titleOpts.text, x, y, titleFont);\n    }\n _computeTitleHeight() {\n        const titleOpts = this.options.title;\n        const titleFont = toFont(titleOpts.font);\n        const titlePadding = toPadding(titleOpts.padding);\n        return titleOpts.display ? titleFont.lineHeight + titlePadding.height : 0;\n    }\n _getLegendItemAt(x, y) {\n        let i, hitBox, lh;\n        if (_isBetween(x, this.left, this.right) && _isBetween(y, this.top, this.bottom)) {\n            lh = this.legendHitBoxes;\n            for(i = 0; i < lh.length; ++i){\n                hitBox = lh[i];\n                if (_isBetween(x, hitBox.left, hitBox.left + hitBox.width) && _isBetween(y, hitBox.top, hitBox.top + hitBox.height)) {\n                    return this.legendItems[i];\n                }\n            }\n        }\n        return null;\n    }\n handleEvent(e) {\n        const opts = this.options;\n        if (!isListened(e.type, opts)) {\n            return;\n        }\n        const hoveredItem = this._getLegendItemAt(e.x, e.y);\n        if (e.type === 'mousemove' || e.type === 'mouseout') {\n            const previous = this._hoveredItem;\n            const sameItem = itemsEqual(previous, hoveredItem);\n            if (previous && !sameItem) {\n                callback(opts.onLeave, [\n                    e,\n                    previous,\n                    this\n                ], this);\n            }\n            this._hoveredItem = hoveredItem;\n            if (hoveredItem && !sameItem) {\n                callback(opts.onHover, [\n                    e,\n                    hoveredItem,\n                    this\n                ], this);\n            }\n        } else if (hoveredItem) {\n            callback(opts.onClick, [\n                e,\n                hoveredItem,\n                this\n            ], this);\n        }\n    }\n}\nfunction calculateItemSize(boxWidth, labelFont, ctx, legendItem, _itemHeight) {\n    const itemWidth = calculateItemWidth(legendItem, boxWidth, labelFont, ctx);\n    const itemHeight = calculateItemHeight(_itemHeight, legendItem, labelFont.lineHeight);\n    return {\n        itemWidth,\n        itemHeight\n    };\n}\nfunction calculateItemWidth(legendItem, boxWidth, labelFont, ctx) {\n    let legendItemText = legendItem.text;\n    if (legendItemText && typeof legendItemText !== 'string') {\n        legendItemText = legendItemText.reduce((a, b)=>a.length > b.length ? a : b);\n    }\n    return boxWidth + labelFont.size / 2 + ctx.measureText(legendItemText).width;\n}\nfunction calculateItemHeight(_itemHeight, legendItem, fontLineHeight) {\n    let itemHeight = _itemHeight;\n    if (typeof legendItem.text !== 'string') {\n        itemHeight = calculateLegendItemHeight(legendItem, fontLineHeight);\n    }\n    return itemHeight;\n}\nfunction calculateLegendItemHeight(legendItem, fontLineHeight) {\n    const labelHeight = legendItem.text ? legendItem.text.length : 0;\n    return fontLineHeight * labelHeight;\n}\nfunction isListened(type, opts) {\n    if ((type === 'mousemove' || type === 'mouseout') && (opts.onHover || opts.onLeave)) {\n        return true;\n    }\n    if (opts.onClick && (type === 'click' || type === 'mouseup')) {\n        return true;\n    }\n    return false;\n}\nvar plugin_legend = {\n    id: 'legend',\n _element: Legend,\n    start (chart, _args, options) {\n        const legend = chart.legend = new Legend({\n            ctx: chart.ctx,\n            options,\n            chart\n        });\n        layouts.configure(chart, legend, options);\n        layouts.addBox(chart, legend);\n    },\n    stop (chart) {\n        layouts.removeBox(chart, chart.legend);\n        delete chart.legend;\n    },\n    beforeUpdate (chart, _args, options) {\n        const legend = chart.legend;\n        layouts.configure(chart, legend, options);\n        legend.options = options;\n    },\n    afterUpdate (chart) {\n        const legend = chart.legend;\n        legend.buildLabels();\n        legend.adjustHitBoxes();\n    },\n    afterEvent (chart, args) {\n        if (!args.replay) {\n            chart.legend.handleEvent(args.event);\n        }\n    },\n    defaults: {\n        display: true,\n        position: 'top',\n        align: 'center',\n        fullSize: true,\n        reverse: false,\n        weight: 1000,\n        onClick (e, legendItem, legend) {\n            const index = legendItem.datasetIndex;\n            const ci = legend.chart;\n            if (ci.isDatasetVisible(index)) {\n                ci.hide(index);\n                legendItem.hidden = true;\n            } else {\n                ci.show(index);\n                legendItem.hidden = false;\n            }\n        },\n        onHover: null,\n        onLeave: null,\n        labels: {\n            color: (ctx)=>ctx.chart.options.color,\n            boxWidth: 40,\n            padding: 10,\n            generateLabels (chart) {\n                const datasets = chart.data.datasets;\n                const { labels: { usePointStyle , pointStyle , textAlign , color , useBorderRadius , borderRadius  }  } = chart.legend.options;\n                return chart._getSortedDatasetMetas().map((meta)=>{\n                    const style = meta.controller.getStyle(usePointStyle ? 0 : undefined);\n                    const borderWidth = toPadding(style.borderWidth);\n                    return {\n                        text: datasets[meta.index].label,\n                        fillStyle: style.backgroundColor,\n                        fontColor: color,\n                        hidden: !meta.visible,\n                        lineCap: style.borderCapStyle,\n                        lineDash: style.borderDash,\n                        lineDashOffset: style.borderDashOffset,\n                        lineJoin: style.borderJoinStyle,\n                        lineWidth: (borderWidth.width + borderWidth.height) / 4,\n                        strokeStyle: style.borderColor,\n                        pointStyle: pointStyle || style.pointStyle,\n                        rotation: style.rotation,\n                        textAlign: textAlign || style.textAlign,\n                        borderRadius: useBorderRadius && (borderRadius || style.borderRadius),\n                        datasetIndex: meta.index\n                    };\n                }, this);\n            }\n        },\n        title: {\n            color: (ctx)=>ctx.chart.options.color,\n            display: false,\n            position: 'center',\n            text: ''\n        }\n    },\n    descriptors: {\n        _scriptable: (name)=>!name.startsWith('on'),\n        labels: {\n            _scriptable: (name)=>![\n                    'generateLabels',\n                    'filter',\n                    'sort'\n                ].includes(name)\n        }\n    }\n};\n\nclass Title extends Element {\n constructor(config){\n        super();\n        this.chart = config.chart;\n        this.options = config.options;\n        this.ctx = config.ctx;\n        this._padding = undefined;\n        this.top = undefined;\n        this.bottom = undefined;\n        this.left = undefined;\n        this.right = undefined;\n        this.width = undefined;\n        this.height = undefined;\n        this.position = undefined;\n        this.weight = undefined;\n        this.fullSize = undefined;\n    }\n    update(maxWidth, maxHeight) {\n        const opts = this.options;\n        this.left = 0;\n        this.top = 0;\n        if (!opts.display) {\n            this.width = this.height = this.right = this.bottom = 0;\n            return;\n        }\n        this.width = this.right = maxWidth;\n        this.height = this.bottom = maxHeight;\n        const lineCount = isArray(opts.text) ? opts.text.length : 1;\n        this._padding = toPadding(opts.padding);\n        const textSize = lineCount * toFont(opts.font).lineHeight + this._padding.height;\n        if (this.isHorizontal()) {\n            this.height = textSize;\n        } else {\n            this.width = textSize;\n        }\n    }\n    isHorizontal() {\n        const pos = this.options.position;\n        return pos === 'top' || pos === 'bottom';\n    }\n    _drawArgs(offset) {\n        const { top , left , bottom , right , options  } = this;\n        const align = options.align;\n        let rotation = 0;\n        let maxWidth, titleX, titleY;\n        if (this.isHorizontal()) {\n            titleX = _alignStartEnd(align, left, right);\n            titleY = top + offset;\n            maxWidth = right - left;\n        } else {\n            if (options.position === 'left') {\n                titleX = left + offset;\n                titleY = _alignStartEnd(align, bottom, top);\n                rotation = PI * -0.5;\n            } else {\n                titleX = right - offset;\n                titleY = _alignStartEnd(align, top, bottom);\n                rotation = PI * 0.5;\n            }\n            maxWidth = bottom - top;\n        }\n        return {\n            titleX,\n            titleY,\n            maxWidth,\n            rotation\n        };\n    }\n    draw() {\n        const ctx = this.ctx;\n        const opts = this.options;\n        if (!opts.display) {\n            return;\n        }\n        const fontOpts = toFont(opts.font);\n        const lineHeight = fontOpts.lineHeight;\n        const offset = lineHeight / 2 + this._padding.top;\n        const { titleX , titleY , maxWidth , rotation  } = this._drawArgs(offset);\n        renderText(ctx, opts.text, 0, 0, fontOpts, {\n            color: opts.color,\n            maxWidth,\n            rotation,\n            textAlign: _toLeftRightCenter(opts.align),\n            textBaseline: 'middle',\n            translation: [\n                titleX,\n                titleY\n            ]\n        });\n    }\n}\nfunction createTitle(chart, titleOpts) {\n    const title = new Title({\n        ctx: chart.ctx,\n        options: titleOpts,\n        chart\n    });\n    layouts.configure(chart, title, titleOpts);\n    layouts.addBox(chart, title);\n    chart.titleBlock = title;\n}\nvar plugin_title = {\n    id: 'title',\n _element: Title,\n    start (chart, _args, options) {\n        createTitle(chart, options);\n    },\n    stop (chart) {\n        const titleBlock = chart.titleBlock;\n        layouts.removeBox(chart, titleBlock);\n        delete chart.titleBlock;\n    },\n    beforeUpdate (chart, _args, options) {\n        const title = chart.titleBlock;\n        layouts.configure(chart, title, options);\n        title.options = options;\n    },\n    defaults: {\n        align: 'center',\n        display: false,\n        font: {\n            weight: 'bold'\n        },\n        fullSize: true,\n        padding: 10,\n        position: 'top',\n        text: '',\n        weight: 2000\n    },\n    defaultRoutes: {\n        color: 'color'\n    },\n    descriptors: {\n        _scriptable: true,\n        _indexable: false\n    }\n};\n\nconst map = new WeakMap();\nvar plugin_subtitle = {\n    id: 'subtitle',\n    start (chart, _args, options) {\n        const title = new Title({\n            ctx: chart.ctx,\n            options,\n            chart\n        });\n        layouts.configure(chart, title, options);\n        layouts.addBox(chart, title);\n        map.set(chart, title);\n    },\n    stop (chart) {\n        layouts.removeBox(chart, map.get(chart));\n        map.delete(chart);\n    },\n    beforeUpdate (chart, _args, options) {\n        const title = map.get(chart);\n        layouts.configure(chart, title, options);\n        title.options = options;\n    },\n    defaults: {\n        align: 'center',\n        display: false,\n        font: {\n            weight: 'normal'\n        },\n        fullSize: true,\n        padding: 0,\n        position: 'top',\n        text: '',\n        weight: 1500\n    },\n    defaultRoutes: {\n        color: 'color'\n    },\n    descriptors: {\n        _scriptable: true,\n        _indexable: false\n    }\n};\n\nconst positioners = {\n average (items) {\n        if (!items.length) {\n            return false;\n        }\n        let i, len;\n        let xSet = new Set();\n        let y = 0;\n        let count = 0;\n        for(i = 0, len = items.length; i < len; ++i){\n            const el = items[i].element;\n            if (el && el.hasValue()) {\n                const pos = el.tooltipPosition();\n                xSet.add(pos.x);\n                y += pos.y;\n                ++count;\n            }\n        }\n        const xAverage = [\n            ...xSet\n        ].reduce((a, b)=>a + b) / xSet.size;\n        return {\n            x: xAverage,\n            y: y / count\n        };\n    },\n nearest (items, eventPosition) {\n        if (!items.length) {\n            return false;\n        }\n        let x = eventPosition.x;\n        let y = eventPosition.y;\n        let minDistance = Number.POSITIVE_INFINITY;\n        let i, len, nearestElement;\n        for(i = 0, len = items.length; i < len; ++i){\n            const el = items[i].element;\n            if (el && el.hasValue()) {\n                const center = el.getCenterPoint();\n                const d = distanceBetweenPoints(eventPosition, center);\n                if (d < minDistance) {\n                    minDistance = d;\n                    nearestElement = el;\n                }\n            }\n        }\n        if (nearestElement) {\n            const tp = nearestElement.tooltipPosition();\n            x = tp.x;\n            y = tp.y;\n        }\n        return {\n            x,\n            y\n        };\n    }\n};\nfunction pushOrConcat(base, toPush) {\n    if (toPush) {\n        if (isArray(toPush)) {\n            Array.prototype.push.apply(base, toPush);\n        } else {\n            base.push(toPush);\n        }\n    }\n    return base;\n}\n function splitNewlines(str) {\n    if ((typeof str === 'string' || str instanceof String) && str.indexOf('\\n') > -1) {\n        return str.split('\\n');\n    }\n    return str;\n}\n function createTooltipItem(chart, item) {\n    const { element , datasetIndex , index  } = item;\n    const controller = chart.getDatasetMeta(datasetIndex).controller;\n    const { label , value  } = controller.getLabelAndValue(index);\n    return {\n        chart,\n        label,\n        parsed: controller.getParsed(index),\n        raw: chart.data.datasets[datasetIndex].data[index],\n        formattedValue: value,\n        dataset: controller.getDataset(),\n        dataIndex: index,\n        datasetIndex,\n        element\n    };\n}\n function getTooltipSize(tooltip, options) {\n    const ctx = tooltip.chart.ctx;\n    const { body , footer , title  } = tooltip;\n    const { boxWidth , boxHeight  } = options;\n    const bodyFont = toFont(options.bodyFont);\n    const titleFont = toFont(options.titleFont);\n    const footerFont = toFont(options.footerFont);\n    const titleLineCount = title.length;\n    const footerLineCount = footer.length;\n    const bodyLineItemCount = body.length;\n    const padding = toPadding(options.padding);\n    let height = padding.height;\n    let width = 0;\n    let combinedBodyLength = body.reduce((count, bodyItem)=>count + bodyItem.before.length + bodyItem.lines.length + bodyItem.after.length, 0);\n    combinedBodyLength += tooltip.beforeBody.length + tooltip.afterBody.length;\n    if (titleLineCount) {\n        height += titleLineCount * titleFont.lineHeight + (titleLineCount - 1) * options.titleSpacing + options.titleMarginBottom;\n    }\n    if (combinedBodyLength) {\n        const bodyLineHeight = options.displayColors ? Math.max(boxHeight, bodyFont.lineHeight) : bodyFont.lineHeight;\n        height += bodyLineItemCount * bodyLineHeight + (combinedBodyLength - bodyLineItemCount) * bodyFont.lineHeight + (combinedBodyLength - 1) * options.bodySpacing;\n    }\n    if (footerLineCount) {\n        height += options.footerMarginTop + footerLineCount * footerFont.lineHeight + (footerLineCount - 1) * options.footerSpacing;\n    }\n    let widthPadding = 0;\n    const maxLineWidth = function(line) {\n        width = Math.max(width, ctx.measureText(line).width + widthPadding);\n    };\n    ctx.save();\n    ctx.font = titleFont.string;\n    each(tooltip.title, maxLineWidth);\n    ctx.font = bodyFont.string;\n    each(tooltip.beforeBody.concat(tooltip.afterBody), maxLineWidth);\n    widthPadding = options.displayColors ? boxWidth + 2 + options.boxPadding : 0;\n    each(body, (bodyItem)=>{\n        each(bodyItem.before, maxLineWidth);\n        each(bodyItem.lines, maxLineWidth);\n        each(bodyItem.after, maxLineWidth);\n    });\n    widthPadding = 0;\n    ctx.font = footerFont.string;\n    each(tooltip.footer, maxLineWidth);\n    ctx.restore();\n    width += padding.width;\n    return {\n        width,\n        height\n    };\n}\nfunction determineYAlign(chart, size) {\n    const { y , height  } = size;\n    if (y < height / 2) {\n        return 'top';\n    } else if (y > chart.height - height / 2) {\n        return 'bottom';\n    }\n    return 'center';\n}\nfunction doesNotFitWithAlign(xAlign, chart, options, size) {\n    const { x , width  } = size;\n    const caret = options.caretSize + options.caretPadding;\n    if (xAlign === 'left' && x + width + caret > chart.width) {\n        return true;\n    }\n    if (xAlign === 'right' && x - width - caret < 0) {\n        return true;\n    }\n}\nfunction determineXAlign(chart, options, size, yAlign) {\n    const { x , width  } = size;\n    const { width: chartWidth , chartArea: { left , right  }  } = chart;\n    let xAlign = 'center';\n    if (yAlign === 'center') {\n        xAlign = x <= (left + right) / 2 ? 'left' : 'right';\n    } else if (x <= width / 2) {\n        xAlign = 'left';\n    } else if (x >= chartWidth - width / 2) {\n        xAlign = 'right';\n    }\n    if (doesNotFitWithAlign(xAlign, chart, options, size)) {\n        xAlign = 'center';\n    }\n    return xAlign;\n}\n function determineAlignment(chart, options, size) {\n    const yAlign = size.yAlign || options.yAlign || determineYAlign(chart, size);\n    return {\n        xAlign: size.xAlign || options.xAlign || determineXAlign(chart, options, size, yAlign),\n        yAlign\n    };\n}\nfunction alignX(size, xAlign) {\n    let { x , width  } = size;\n    if (xAlign === 'right') {\n        x -= width;\n    } else if (xAlign === 'center') {\n        x -= width / 2;\n    }\n    return x;\n}\nfunction alignY(size, yAlign, paddingAndSize) {\n    let { y , height  } = size;\n    if (yAlign === 'top') {\n        y += paddingAndSize;\n    } else if (yAlign === 'bottom') {\n        y -= height + paddingAndSize;\n    } else {\n        y -= height / 2;\n    }\n    return y;\n}\n function getBackgroundPoint(options, size, alignment, chart) {\n    const { caretSize , caretPadding , cornerRadius  } = options;\n    const { xAlign , yAlign  } = alignment;\n    const paddingAndSize = caretSize + caretPadding;\n    const { topLeft , topRight , bottomLeft , bottomRight  } = toTRBLCorners(cornerRadius);\n    let x = alignX(size, xAlign);\n    const y = alignY(size, yAlign, paddingAndSize);\n    if (yAlign === 'center') {\n        if (xAlign === 'left') {\n            x += paddingAndSize;\n        } else if (xAlign === 'right') {\n            x -= paddingAndSize;\n        }\n    } else if (xAlign === 'left') {\n        x -= Math.max(topLeft, bottomLeft) + caretSize;\n    } else if (xAlign === 'right') {\n        x += Math.max(topRight, bottomRight) + caretSize;\n    }\n    return {\n        x: _limitValue(x, 0, chart.width - size.width),\n        y: _limitValue(y, 0, chart.height - size.height)\n    };\n}\nfunction getAlignedX(tooltip, align, options) {\n    const padding = toPadding(options.padding);\n    return align === 'center' ? tooltip.x + tooltip.width / 2 : align === 'right' ? tooltip.x + tooltip.width - padding.right : tooltip.x + padding.left;\n}\n function getBeforeAfterBodyLines(callback) {\n    return pushOrConcat([], splitNewlines(callback));\n}\nfunction createTooltipContext(parent, tooltip, tooltipItems) {\n    return createContext(parent, {\n        tooltip,\n        tooltipItems,\n        type: 'tooltip'\n    });\n}\nfunction overrideCallbacks(callbacks, context) {\n    const override = context && context.dataset && context.dataset.tooltip && context.dataset.tooltip.callbacks;\n    return override ? callbacks.override(override) : callbacks;\n}\nconst defaultCallbacks = {\n    beforeTitle: noop,\n    title (tooltipItems) {\n        if (tooltipItems.length > 0) {\n            const item = tooltipItems[0];\n            const labels = item.chart.data.labels;\n            const labelCount = labels ? labels.length : 0;\n            if (this && this.options && this.options.mode === 'dataset') {\n                return item.dataset.label || '';\n            } else if (item.label) {\n                return item.label;\n            } else if (labelCount > 0 && item.dataIndex < labelCount) {\n                return labels[item.dataIndex];\n            }\n        }\n        return '';\n    },\n    afterTitle: noop,\n    beforeBody: noop,\n    beforeLabel: noop,\n    label (tooltipItem) {\n        if (this && this.options && this.options.mode === 'dataset') {\n            return tooltipItem.label + ': ' + tooltipItem.formattedValue || tooltipItem.formattedValue;\n        }\n        let label = tooltipItem.dataset.label || '';\n        if (label) {\n            label += ': ';\n        }\n        const value = tooltipItem.formattedValue;\n        if (!isNullOrUndef(value)) {\n            label += value;\n        }\n        return label;\n    },\n    labelColor (tooltipItem) {\n        const meta = tooltipItem.chart.getDatasetMeta(tooltipItem.datasetIndex);\n        const options = meta.controller.getStyle(tooltipItem.dataIndex);\n        return {\n            borderColor: options.borderColor,\n            backgroundColor: options.backgroundColor,\n            borderWidth: options.borderWidth,\n            borderDash: options.borderDash,\n            borderDashOffset: options.borderDashOffset,\n            borderRadius: 0\n        };\n    },\n    labelTextColor () {\n        return this.options.bodyColor;\n    },\n    labelPointStyle (tooltipItem) {\n        const meta = tooltipItem.chart.getDatasetMeta(tooltipItem.datasetIndex);\n        const options = meta.controller.getStyle(tooltipItem.dataIndex);\n        return {\n            pointStyle: options.pointStyle,\n            rotation: options.rotation\n        };\n    },\n    afterLabel: noop,\n    afterBody: noop,\n    beforeFooter: noop,\n    footer: noop,\n    afterFooter: noop\n};\n function invokeCallbackWithFallback(callbacks, name, ctx, arg) {\n    const result = callbacks[name].call(ctx, arg);\n    if (typeof result === 'undefined') {\n        return defaultCallbacks[name].call(ctx, arg);\n    }\n    return result;\n}\nclass Tooltip extends Element {\n static positioners = positioners;\n    constructor(config){\n        super();\n        this.opacity = 0;\n        this._active = [];\n        this._eventPosition = undefined;\n        this._size = undefined;\n        this._cachedAnimations = undefined;\n        this._tooltipItems = [];\n        this.$animations = undefined;\n        this.$context = undefined;\n        this.chart = config.chart;\n        this.options = config.options;\n        this.dataPoints = undefined;\n        this.title = undefined;\n        this.beforeBody = undefined;\n        this.body = undefined;\n        this.afterBody = undefined;\n        this.footer = undefined;\n        this.xAlign = undefined;\n        this.yAlign = undefined;\n        this.x = undefined;\n        this.y = undefined;\n        this.height = undefined;\n        this.width = undefined;\n        this.caretX = undefined;\n        this.caretY = undefined;\n        this.labelColors = undefined;\n        this.labelPointStyles = undefined;\n        this.labelTextColors = undefined;\n    }\n    initialize(options) {\n        this.options = options;\n        this._cachedAnimations = undefined;\n        this.$context = undefined;\n    }\n _resolveAnimations() {\n        const cached = this._cachedAnimations;\n        if (cached) {\n            return cached;\n        }\n        const chart = this.chart;\n        const options = this.options.setContext(this.getContext());\n        const opts = options.enabled && chart.options.animation && options.animations;\n        const animations = new Animations(this.chart, opts);\n        if (opts._cacheable) {\n            this._cachedAnimations = Object.freeze(animations);\n        }\n        return animations;\n    }\n getContext() {\n        return this.$context || (this.$context = createTooltipContext(this.chart.getContext(), this, this._tooltipItems));\n    }\n    getTitle(context, options) {\n        const { callbacks  } = options;\n        const beforeTitle = invokeCallbackWithFallback(callbacks, 'beforeTitle', this, context);\n        const title = invokeCallbackWithFallback(callbacks, 'title', this, context);\n        const afterTitle = invokeCallbackWithFallback(callbacks, 'afterTitle', this, context);\n        let lines = [];\n        lines = pushOrConcat(lines, splitNewlines(beforeTitle));\n        lines = pushOrConcat(lines, splitNewlines(title));\n        lines = pushOrConcat(lines, splitNewlines(afterTitle));\n        return lines;\n    }\n    getBeforeBody(tooltipItems, options) {\n        return getBeforeAfterBodyLines(invokeCallbackWithFallback(options.callbacks, 'beforeBody', this, tooltipItems));\n    }\n    getBody(tooltipItems, options) {\n        const { callbacks  } = options;\n        const bodyItems = [];\n        each(tooltipItems, (context)=>{\n            const bodyItem = {\n                before: [],\n                lines: [],\n                after: []\n            };\n            const scoped = overrideCallbacks(callbacks, context);\n            pushOrConcat(bodyItem.before, splitNewlines(invokeCallbackWithFallback(scoped, 'beforeLabel', this, context)));\n            pushOrConcat(bodyItem.lines, invokeCallbackWithFallback(scoped, 'label', this, context));\n            pushOrConcat(bodyItem.after, splitNewlines(invokeCallbackWithFallback(scoped, 'afterLabel', this, context)));\n            bodyItems.push(bodyItem);\n        });\n        return bodyItems;\n    }\n    getAfterBody(tooltipItems, options) {\n        return getBeforeAfterBodyLines(invokeCallbackWithFallback(options.callbacks, 'afterBody', this, tooltipItems));\n    }\n    getFooter(tooltipItems, options) {\n        const { callbacks  } = options;\n        const beforeFooter = invokeCallbackWithFallback(callbacks, 'beforeFooter', this, tooltipItems);\n        const footer = invokeCallbackWithFallback(callbacks, 'footer', this, tooltipItems);\n        const afterFooter = invokeCallbackWithFallback(callbacks, 'afterFooter', this, tooltipItems);\n        let lines = [];\n        lines = pushOrConcat(lines, splitNewlines(beforeFooter));\n        lines = pushOrConcat(lines, splitNewlines(footer));\n        lines = pushOrConcat(lines, splitNewlines(afterFooter));\n        return lines;\n    }\n _createItems(options) {\n        const active = this._active;\n        const data = this.chart.data;\n        const labelColors = [];\n        const labelPointStyles = [];\n        const labelTextColors = [];\n        let tooltipItems = [];\n        let i, len;\n        for(i = 0, len = active.length; i < len; ++i){\n            tooltipItems.push(createTooltipItem(this.chart, active[i]));\n        }\n        if (options.filter) {\n            tooltipItems = tooltipItems.filter((element, index, array)=>options.filter(element, index, array, data));\n        }\n        if (options.itemSort) {\n            tooltipItems = tooltipItems.sort((a, b)=>options.itemSort(a, b, data));\n        }\n        each(tooltipItems, (context)=>{\n            const scoped = overrideCallbacks(options.callbacks, context);\n            labelColors.push(invokeCallbackWithFallback(scoped, 'labelColor', this, context));\n            labelPointStyles.push(invokeCallbackWithFallback(scoped, 'labelPointStyle', this, context));\n            labelTextColors.push(invokeCallbackWithFallback(scoped, 'labelTextColor', this, context));\n        });\n        this.labelColors = labelColors;\n        this.labelPointStyles = labelPointStyles;\n        this.labelTextColors = labelTextColors;\n        this.dataPoints = tooltipItems;\n        return tooltipItems;\n    }\n    update(changed, replay) {\n        const options = this.options.setContext(this.getContext());\n        const active = this._active;\n        let properties;\n        let tooltipItems = [];\n        if (!active.length) {\n            if (this.opacity !== 0) {\n                properties = {\n                    opacity: 0\n                };\n            }\n        } else {\n            const position = positioners[options.position].call(this, active, this._eventPosition);\n            tooltipItems = this._createItems(options);\n            this.title = this.getTitle(tooltipItems, options);\n            this.beforeBody = this.getBeforeBody(tooltipItems, options);\n            this.body = this.getBody(tooltipItems, options);\n            this.afterBody = this.getAfterBody(tooltipItems, options);\n            this.footer = this.getFooter(tooltipItems, options);\n            const size = this._size = getTooltipSize(this, options);\n            const positionAndSize = Object.assign({}, position, size);\n            const alignment = determineAlignment(this.chart, options, positionAndSize);\n            const backgroundPoint = getBackgroundPoint(options, positionAndSize, alignment, this.chart);\n            this.xAlign = alignment.xAlign;\n            this.yAlign = alignment.yAlign;\n            properties = {\n                opacity: 1,\n                x: backgroundPoint.x,\n                y: backgroundPoint.y,\n                width: size.width,\n                height: size.height,\n                caretX: position.x,\n                caretY: position.y\n            };\n        }\n        this._tooltipItems = tooltipItems;\n        this.$context = undefined;\n        if (properties) {\n            this._resolveAnimations().update(this, properties);\n        }\n        if (changed && options.external) {\n            options.external.call(this, {\n                chart: this.chart,\n                tooltip: this,\n                replay\n            });\n        }\n    }\n    drawCaret(tooltipPoint, ctx, size, options) {\n        const caretPosition = this.getCaretPosition(tooltipPoint, size, options);\n        ctx.lineTo(caretPosition.x1, caretPosition.y1);\n        ctx.lineTo(caretPosition.x2, caretPosition.y2);\n        ctx.lineTo(caretPosition.x3, caretPosition.y3);\n    }\n    getCaretPosition(tooltipPoint, size, options) {\n        const { xAlign , yAlign  } = this;\n        const { caretSize , cornerRadius  } = options;\n        const { topLeft , topRight , bottomLeft , bottomRight  } = toTRBLCorners(cornerRadius);\n        const { x: ptX , y: ptY  } = tooltipPoint;\n        const { width , height  } = size;\n        let x1, x2, x3, y1, y2, y3;\n        if (yAlign === 'center') {\n            y2 = ptY + height / 2;\n            if (xAlign === 'left') {\n                x1 = ptX;\n                x2 = x1 - caretSize;\n                y1 = y2 + caretSize;\n                y3 = y2 - caretSize;\n            } else {\n                x1 = ptX + width;\n                x2 = x1 + caretSize;\n                y1 = y2 - caretSize;\n                y3 = y2 + caretSize;\n            }\n            x3 = x1;\n        } else {\n            if (xAlign === 'left') {\n                x2 = ptX + Math.max(topLeft, bottomLeft) + caretSize;\n            } else if (xAlign === 'right') {\n                x2 = ptX + width - Math.max(topRight, bottomRight) - caretSize;\n            } else {\n                x2 = this.caretX;\n            }\n            if (yAlign === 'top') {\n                y1 = ptY;\n                y2 = y1 - caretSize;\n                x1 = x2 - caretSize;\n                x3 = x2 + caretSize;\n            } else {\n                y1 = ptY + height;\n                y2 = y1 + caretSize;\n                x1 = x2 + caretSize;\n                x3 = x2 - caretSize;\n            }\n            y3 = y1;\n        }\n        return {\n            x1,\n            x2,\n            x3,\n            y1,\n            y2,\n            y3\n        };\n    }\n    drawTitle(pt, ctx, options) {\n        const title = this.title;\n        const length = title.length;\n        let titleFont, titleSpacing, i;\n        if (length) {\n            const rtlHelper = getRtlAdapter(options.rtl, this.x, this.width);\n            pt.x = getAlignedX(this, options.titleAlign, options);\n            ctx.textAlign = rtlHelper.textAlign(options.titleAlign);\n            ctx.textBaseline = 'middle';\n            titleFont = toFont(options.titleFont);\n            titleSpacing = options.titleSpacing;\n            ctx.fillStyle = options.titleColor;\n            ctx.font = titleFont.string;\n            for(i = 0; i < length; ++i){\n                ctx.fillText(title[i], rtlHelper.x(pt.x), pt.y + titleFont.lineHeight / 2);\n                pt.y += titleFont.lineHeight + titleSpacing;\n                if (i + 1 === length) {\n                    pt.y += options.titleMarginBottom - titleSpacing;\n                }\n            }\n        }\n    }\n _drawColorBox(ctx, pt, i, rtlHelper, options) {\n        const labelColor = this.labelColors[i];\n        const labelPointStyle = this.labelPointStyles[i];\n        const { boxHeight , boxWidth  } = options;\n        const bodyFont = toFont(options.bodyFont);\n        const colorX = getAlignedX(this, 'left', options);\n        const rtlColorX = rtlHelper.x(colorX);\n        const yOffSet = boxHeight < bodyFont.lineHeight ? (bodyFont.lineHeight - boxHeight) / 2 : 0;\n        const colorY = pt.y + yOffSet;\n        if (options.usePointStyle) {\n            const drawOptions = {\n                radius: Math.min(boxWidth, boxHeight) / 2,\n                pointStyle: labelPointStyle.pointStyle,\n                rotation: labelPointStyle.rotation,\n                borderWidth: 1\n            };\n            const centerX = rtlHelper.leftForLtr(rtlColorX, boxWidth) + boxWidth / 2;\n            const centerY = colorY + boxHeight / 2;\n            ctx.strokeStyle = options.multiKeyBackground;\n            ctx.fillStyle = options.multiKeyBackground;\n            drawPoint(ctx, drawOptions, centerX, centerY);\n            ctx.strokeStyle = labelColor.borderColor;\n            ctx.fillStyle = labelColor.backgroundColor;\n            drawPoint(ctx, drawOptions, centerX, centerY);\n        } else {\n            ctx.lineWidth = isObject(labelColor.borderWidth) ? Math.max(...Object.values(labelColor.borderWidth)) : labelColor.borderWidth || 1;\n            ctx.strokeStyle = labelColor.borderColor;\n            ctx.setLineDash(labelColor.borderDash || []);\n            ctx.lineDashOffset = labelColor.borderDashOffset || 0;\n            const outerX = rtlHelper.leftForLtr(rtlColorX, boxWidth);\n            const innerX = rtlHelper.leftForLtr(rtlHelper.xPlus(rtlColorX, 1), boxWidth - 2);\n            const borderRadius = toTRBLCorners(labelColor.borderRadius);\n            if (Object.values(borderRadius).some((v)=>v !== 0)) {\n                ctx.beginPath();\n                ctx.fillStyle = options.multiKeyBackground;\n                addRoundedRectPath(ctx, {\n                    x: outerX,\n                    y: colorY,\n                    w: boxWidth,\n                    h: boxHeight,\n                    radius: borderRadius\n                });\n                ctx.fill();\n                ctx.stroke();\n                ctx.fillStyle = labelColor.backgroundColor;\n                ctx.beginPath();\n                addRoundedRectPath(ctx, {\n                    x: innerX,\n                    y: colorY + 1,\n                    w: boxWidth - 2,\n                    h: boxHeight - 2,\n                    radius: borderRadius\n                });\n                ctx.fill();\n            } else {\n                ctx.fillStyle = options.multiKeyBackground;\n                ctx.fillRect(outerX, colorY, boxWidth, boxHeight);\n                ctx.strokeRect(outerX, colorY, boxWidth, boxHeight);\n                ctx.fillStyle = labelColor.backgroundColor;\n                ctx.fillRect(innerX, colorY + 1, boxWidth - 2, boxHeight - 2);\n            }\n        }\n        ctx.fillStyle = this.labelTextColors[i];\n    }\n    drawBody(pt, ctx, options) {\n        const { body  } = this;\n        const { bodySpacing , bodyAlign , displayColors , boxHeight , boxWidth , boxPadding  } = options;\n        const bodyFont = toFont(options.bodyFont);\n        let bodyLineHeight = bodyFont.lineHeight;\n        let xLinePadding = 0;\n        const rtlHelper = getRtlAdapter(options.rtl, this.x, this.width);\n        const fillLineOfText = function(line) {\n            ctx.fillText(line, rtlHelper.x(pt.x + xLinePadding), pt.y + bodyLineHeight / 2);\n            pt.y += bodyLineHeight + bodySpacing;\n        };\n        const bodyAlignForCalculation = rtlHelper.textAlign(bodyAlign);\n        let bodyItem, textColor, lines, i, j, ilen, jlen;\n        ctx.textAlign = bodyAlign;\n        ctx.textBaseline = 'middle';\n        ctx.font = bodyFont.string;\n        pt.x = getAlignedX(this, bodyAlignForCalculation, options);\n        ctx.fillStyle = options.bodyColor;\n        each(this.beforeBody, fillLineOfText);\n        xLinePadding = displayColors && bodyAlignForCalculation !== 'right' ? bodyAlign === 'center' ? boxWidth / 2 + boxPadding : boxWidth + 2 + boxPadding : 0;\n        for(i = 0, ilen = body.length; i < ilen; ++i){\n            bodyItem = body[i];\n            textColor = this.labelTextColors[i];\n            ctx.fillStyle = textColor;\n            each(bodyItem.before, fillLineOfText);\n            lines = bodyItem.lines;\n            if (displayColors && lines.length) {\n                this._drawColorBox(ctx, pt, i, rtlHelper, options);\n                bodyLineHeight = Math.max(bodyFont.lineHeight, boxHeight);\n            }\n            for(j = 0, jlen = lines.length; j < jlen; ++j){\n                fillLineOfText(lines[j]);\n                bodyLineHeight = bodyFont.lineHeight;\n            }\n            each(bodyItem.after, fillLineOfText);\n        }\n        xLinePadding = 0;\n        bodyLineHeight = bodyFont.lineHeight;\n        each(this.afterBody, fillLineOfText);\n        pt.y -= bodySpacing;\n    }\n    drawFooter(pt, ctx, options) {\n        const footer = this.footer;\n        const length = footer.length;\n        let footerFont, i;\n        if (length) {\n            const rtlHelper = getRtlAdapter(options.rtl, this.x, this.width);\n            pt.x = getAlignedX(this, options.footerAlign, options);\n            pt.y += options.footerMarginTop;\n            ctx.textAlign = rtlHelper.textAlign(options.footerAlign);\n            ctx.textBaseline = 'middle';\n            footerFont = toFont(options.footerFont);\n            ctx.fillStyle = options.footerColor;\n            ctx.font = footerFont.string;\n            for(i = 0; i < length; ++i){\n                ctx.fillText(footer[i], rtlHelper.x(pt.x), pt.y + footerFont.lineHeight / 2);\n                pt.y += footerFont.lineHeight + options.footerSpacing;\n            }\n        }\n    }\n    drawBackground(pt, ctx, tooltipSize, options) {\n        const { xAlign , yAlign  } = this;\n        const { x , y  } = pt;\n        const { width , height  } = tooltipSize;\n        const { topLeft , topRight , bottomLeft , bottomRight  } = toTRBLCorners(options.cornerRadius);\n        ctx.fillStyle = options.backgroundColor;\n        ctx.strokeStyle = options.borderColor;\n        ctx.lineWidth = options.borderWidth;\n        ctx.beginPath();\n        ctx.moveTo(x + topLeft, y);\n        if (yAlign === 'top') {\n            this.drawCaret(pt, ctx, tooltipSize, options);\n        }\n        ctx.lineTo(x + width - topRight, y);\n        ctx.quadraticCurveTo(x + width, y, x + width, y + topRight);\n        if (yAlign === 'center' && xAlign === 'right') {\n            this.drawCaret(pt, ctx, tooltipSize, options);\n        }\n        ctx.lineTo(x + width, y + height - bottomRight);\n        ctx.quadraticCurveTo(x + width, y + height, x + width - bottomRight, y + height);\n        if (yAlign === 'bottom') {\n            this.drawCaret(pt, ctx, tooltipSize, options);\n        }\n        ctx.lineTo(x + bottomLeft, y + height);\n        ctx.quadraticCurveTo(x, y + height, x, y + height - bottomLeft);\n        if (yAlign === 'center' && xAlign === 'left') {\n            this.drawCaret(pt, ctx, tooltipSize, options);\n        }\n        ctx.lineTo(x, y + topLeft);\n        ctx.quadraticCurveTo(x, y, x + topLeft, y);\n        ctx.closePath();\n        ctx.fill();\n        if (options.borderWidth > 0) {\n            ctx.stroke();\n        }\n    }\n _updateAnimationTarget(options) {\n        const chart = this.chart;\n        const anims = this.$animations;\n        const animX = anims && anims.x;\n        const animY = anims && anims.y;\n        if (animX || animY) {\n            const position = positioners[options.position].call(this, this._active, this._eventPosition);\n            if (!position) {\n                return;\n            }\n            const size = this._size = getTooltipSize(this, options);\n            const positionAndSize = Object.assign({}, position, this._size);\n            const alignment = determineAlignment(chart, options, positionAndSize);\n            const point = getBackgroundPoint(options, positionAndSize, alignment, chart);\n            if (animX._to !== point.x || animY._to !== point.y) {\n                this.xAlign = alignment.xAlign;\n                this.yAlign = alignment.yAlign;\n                this.width = size.width;\n                this.height = size.height;\n                this.caretX = position.x;\n                this.caretY = position.y;\n                this._resolveAnimations().update(this, point);\n            }\n        }\n    }\n _willRender() {\n        return !!this.opacity;\n    }\n    draw(ctx) {\n        const options = this.options.setContext(this.getContext());\n        let opacity = this.opacity;\n        if (!opacity) {\n            return;\n        }\n        this._updateAnimationTarget(options);\n        const tooltipSize = {\n            width: this.width,\n            height: this.height\n        };\n        const pt = {\n            x: this.x,\n            y: this.y\n        };\n        opacity = Math.abs(opacity) < 1e-3 ? 0 : opacity;\n        const padding = toPadding(options.padding);\n        const hasTooltipContent = this.title.length || this.beforeBody.length || this.body.length || this.afterBody.length || this.footer.length;\n        if (options.enabled && hasTooltipContent) {\n            ctx.save();\n            ctx.globalAlpha = opacity;\n            this.drawBackground(pt, ctx, tooltipSize, options);\n            overrideTextDirection(ctx, options.textDirection);\n            pt.y += padding.top;\n            this.drawTitle(pt, ctx, options);\n            this.drawBody(pt, ctx, options);\n            this.drawFooter(pt, ctx, options);\n            restoreTextDirection(ctx, options.textDirection);\n            ctx.restore();\n        }\n    }\n getActiveElements() {\n        return this._active || [];\n    }\n setActiveElements(activeElements, eventPosition) {\n        const lastActive = this._active;\n        const active = activeElements.map(({ datasetIndex , index  })=>{\n            const meta = this.chart.getDatasetMeta(datasetIndex);\n            if (!meta) {\n                throw new Error('Cannot find a dataset at index ' + datasetIndex);\n            }\n            return {\n                datasetIndex,\n                element: meta.data[index],\n                index\n            };\n        });\n        const changed = !_elementsEqual(lastActive, active);\n        const positionChanged = this._positionChanged(active, eventPosition);\n        if (changed || positionChanged) {\n            this._active = active;\n            this._eventPosition = eventPosition;\n            this._ignoreReplayEvents = true;\n            this.update(true);\n        }\n    }\n handleEvent(e, replay, inChartArea = true) {\n        if (replay && this._ignoreReplayEvents) {\n            return false;\n        }\n        this._ignoreReplayEvents = false;\n        const options = this.options;\n        const lastActive = this._active || [];\n        const active = this._getActiveElements(e, lastActive, replay, inChartArea);\n        const positionChanged = this._positionChanged(active, e);\n        const changed = replay || !_elementsEqual(active, lastActive) || positionChanged;\n        if (changed) {\n            this._active = active;\n            if (options.enabled || options.external) {\n                this._eventPosition = {\n                    x: e.x,\n                    y: e.y\n                };\n                this.update(true, replay);\n            }\n        }\n        return changed;\n    }\n _getActiveElements(e, lastActive, replay, inChartArea) {\n        const options = this.options;\n        if (e.type === 'mouseout') {\n            return [];\n        }\n        if (!inChartArea) {\n            return lastActive.filter((i)=>this.chart.data.datasets[i.datasetIndex] && this.chart.getDatasetMeta(i.datasetIndex).controller.getParsed(i.index) !== undefined);\n        }\n        const active = this.chart.getElementsAtEventForMode(e, options.mode, options, replay);\n        if (options.reverse) {\n            active.reverse();\n        }\n        return active;\n    }\n _positionChanged(active, e) {\n        const { caretX , caretY , options  } = this;\n        const position = positioners[options.position].call(this, active, e);\n        return position !== false && (caretX !== position.x || caretY !== position.y);\n    }\n}\nvar plugin_tooltip = {\n    id: 'tooltip',\n    _element: Tooltip,\n    positioners,\n    afterInit (chart, _args, options) {\n        if (options) {\n            chart.tooltip = new Tooltip({\n                chart,\n                options\n            });\n        }\n    },\n    beforeUpdate (chart, _args, options) {\n        if (chart.tooltip) {\n            chart.tooltip.initialize(options);\n        }\n    },\n    reset (chart, _args, options) {\n        if (chart.tooltip) {\n            chart.tooltip.initialize(options);\n        }\n    },\n    afterDraw (chart) {\n        const tooltip = chart.tooltip;\n        if (tooltip && tooltip._willRender()) {\n            const args = {\n                tooltip\n            };\n            if (chart.notifyPlugins('beforeTooltipDraw', {\n                ...args,\n                cancelable: true\n            }) === false) {\n                return;\n            }\n            tooltip.draw(chart.ctx);\n            chart.notifyPlugins('afterTooltipDraw', args);\n        }\n    },\n    afterEvent (chart, args) {\n        if (chart.tooltip) {\n            const useFinalPosition = args.replay;\n            if (chart.tooltip.handleEvent(args.event, useFinalPosition, args.inChartArea)) {\n                args.changed = true;\n            }\n        }\n    },\n    defaults: {\n        enabled: true,\n        external: null,\n        position: 'average',\n        backgroundColor: 'rgba(0,0,0,0.8)',\n        titleColor: '#fff',\n        titleFont: {\n            weight: 'bold'\n        },\n        titleSpacing: 2,\n        titleMarginBottom: 6,\n        titleAlign: 'left',\n        bodyColor: '#fff',\n        bodySpacing: 2,\n        bodyFont: {},\n        bodyAlign: 'left',\n        footerColor: '#fff',\n        footerSpacing: 2,\n        footerMarginTop: 6,\n        footerFont: {\n            weight: 'bold'\n        },\n        footerAlign: 'left',\n        padding: 6,\n        caretPadding: 2,\n        caretSize: 5,\n        cornerRadius: 6,\n        boxHeight: (ctx, opts)=>opts.bodyFont.size,\n        boxWidth: (ctx, opts)=>opts.bodyFont.size,\n        multiKeyBackground: '#fff',\n        displayColors: true,\n        boxPadding: 0,\n        borderColor: 'rgba(0,0,0,0)',\n        borderWidth: 0,\n        animation: {\n            duration: 400,\n            easing: 'easeOutQuart'\n        },\n        animations: {\n            numbers: {\n                type: 'number',\n                properties: [\n                    'x',\n                    'y',\n                    'width',\n                    'height',\n                    'caretX',\n                    'caretY'\n                ]\n            },\n            opacity: {\n                easing: 'linear',\n                duration: 200\n            }\n        },\n        callbacks: defaultCallbacks\n    },\n    defaultRoutes: {\n        bodyFont: 'font',\n        footerFont: 'font',\n        titleFont: 'font'\n    },\n    descriptors: {\n        _scriptable: (name)=>name !== 'filter' && name !== 'itemSort' && name !== 'external',\n        _indexable: false,\n        callbacks: {\n            _scriptable: false,\n            _indexable: false\n        },\n        animation: {\n            _fallback: false\n        },\n        animations: {\n            _fallback: 'animation'\n        }\n    },\n    additionalOptionScopes: [\n        'interaction'\n    ]\n};\n\nvar plugins = /*#__PURE__*/Object.freeze({\n__proto__: null,\nColors: plugin_colors,\nDecimation: plugin_decimation,\nFiller: index,\nLegend: plugin_legend,\nSubTitle: plugin_subtitle,\nTitle: plugin_title,\nTooltip: plugin_tooltip\n});\n\nconst addIfString = (labels, raw, index, addedLabels)=>{\n    if (typeof raw === 'string') {\n        index = labels.push(raw) - 1;\n        addedLabels.unshift({\n            index,\n            label: raw\n        });\n    } else if (isNaN(raw)) {\n        index = null;\n    }\n    return index;\n};\nfunction findOrAddLabel(labels, raw, index, addedLabels) {\n    const first = labels.indexOf(raw);\n    if (first === -1) {\n        return addIfString(labels, raw, index, addedLabels);\n    }\n    const last = labels.lastIndexOf(raw);\n    return first !== last ? index : first;\n}\nconst validIndex = (index, max)=>index === null ? null : _limitValue(Math.round(index), 0, max);\nfunction _getLabelForValue(value) {\n    const labels = this.getLabels();\n    if (value >= 0 && value < labels.length) {\n        return labels[value];\n    }\n    return value;\n}\nclass CategoryScale extends Scale {\n    static id = 'category';\n static defaults = {\n        ticks: {\n            callback: _getLabelForValue\n        }\n    };\n    constructor(cfg){\n        super(cfg);\n         this._startValue = undefined;\n        this._valueRange = 0;\n        this._addedLabels = [];\n    }\n    init(scaleOptions) {\n        const added = this._addedLabels;\n        if (added.length) {\n            const labels = this.getLabels();\n            for (const { index , label  } of added){\n                if (labels[index] === label) {\n                    labels.splice(index, 1);\n                }\n            }\n            this._addedLabels = [];\n        }\n        super.init(scaleOptions);\n    }\n    parse(raw, index) {\n        if (isNullOrUndef(raw)) {\n            return null;\n        }\n        const labels = this.getLabels();\n        index = isFinite(index) && labels[index] === raw ? index : findOrAddLabel(labels, raw, valueOrDefault(index, raw), this._addedLabels);\n        return validIndex(index, labels.length - 1);\n    }\n    determineDataLimits() {\n        const { minDefined , maxDefined  } = this.getUserBounds();\n        let { min , max  } = this.getMinMax(true);\n        if (this.options.bounds === 'ticks') {\n            if (!minDefined) {\n                min = 0;\n            }\n            if (!maxDefined) {\n                max = this.getLabels().length - 1;\n            }\n        }\n        this.min = min;\n        this.max = max;\n    }\n    buildTicks() {\n        const min = this.min;\n        const max = this.max;\n        const offset = this.options.offset;\n        const ticks = [];\n        let labels = this.getLabels();\n        labels = min === 0 && max === labels.length - 1 ? labels : labels.slice(min, max + 1);\n        this._valueRange = Math.max(labels.length - (offset ? 0 : 1), 1);\n        this._startValue = this.min - (offset ? 0.5 : 0);\n        for(let value = min; value <= max; value++){\n            ticks.push({\n                value\n            });\n        }\n        return ticks;\n    }\n    getLabelForValue(value) {\n        return _getLabelForValue.call(this, value);\n    }\n configure() {\n        super.configure();\n        if (!this.isHorizontal()) {\n            this._reversePixels = !this._reversePixels;\n        }\n    }\n    getPixelForValue(value) {\n        if (typeof value !== 'number') {\n            value = this.parse(value);\n        }\n        return value === null ? NaN : this.getPixelForDecimal((value - this._startValue) / this._valueRange);\n    }\n    getPixelForTick(index) {\n        const ticks = this.ticks;\n        if (index < 0 || index > ticks.length - 1) {\n            return null;\n        }\n        return this.getPixelForValue(ticks[index].value);\n    }\n    getValueForPixel(pixel) {\n        return Math.round(this._startValue + this.getDecimalForPixel(pixel) * this._valueRange);\n    }\n    getBasePixel() {\n        return this.bottom;\n    }\n}\n\nfunction generateTicks$1(generationOptions, dataRange) {\n    const ticks = [];\n    const MIN_SPACING = 1e-14;\n    const { bounds , step , min , max , precision , count , maxTicks , maxDigits , includeBounds  } = generationOptions;\n    const unit = step || 1;\n    const maxSpaces = maxTicks - 1;\n    const { min: rmin , max: rmax  } = dataRange;\n    const minDefined = !isNullOrUndef(min);\n    const maxDefined = !isNullOrUndef(max);\n    const countDefined = !isNullOrUndef(count);\n    const minSpacing = (rmax - rmin) / (maxDigits + 1);\n    let spacing = niceNum((rmax - rmin) / maxSpaces / unit) * unit;\n    let factor, niceMin, niceMax, numSpaces;\n    if (spacing < MIN_SPACING && !minDefined && !maxDefined) {\n        return [\n            {\n                value: rmin\n            },\n            {\n                value: rmax\n            }\n        ];\n    }\n    numSpaces = Math.ceil(rmax / spacing) - Math.floor(rmin / spacing);\n    if (numSpaces > maxSpaces) {\n        spacing = niceNum(numSpaces * spacing / maxSpaces / unit) * unit;\n    }\n    if (!isNullOrUndef(precision)) {\n        factor = Math.pow(10, precision);\n        spacing = Math.ceil(spacing * factor) / factor;\n    }\n    if (bounds === 'ticks') {\n        niceMin = Math.floor(rmin / spacing) * spacing;\n        niceMax = Math.ceil(rmax / spacing) * spacing;\n    } else {\n        niceMin = rmin;\n        niceMax = rmax;\n    }\n    if (minDefined && maxDefined && step && almostWhole((max - min) / step, spacing / 1000)) {\n        numSpaces = Math.round(Math.min((max - min) / spacing, maxTicks));\n        spacing = (max - min) / numSpaces;\n        niceMin = min;\n        niceMax = max;\n    } else if (countDefined) {\n        niceMin = minDefined ? min : niceMin;\n        niceMax = maxDefined ? max : niceMax;\n        numSpaces = count - 1;\n        spacing = (niceMax - niceMin) / numSpaces;\n    } else {\n        numSpaces = (niceMax - niceMin) / spacing;\n        if (almostEquals(numSpaces, Math.round(numSpaces), spacing / 1000)) {\n            numSpaces = Math.round(numSpaces);\n        } else {\n            numSpaces = Math.ceil(numSpaces);\n        }\n    }\n    const decimalPlaces = Math.max(_decimalPlaces(spacing), _decimalPlaces(niceMin));\n    factor = Math.pow(10, isNullOrUndef(precision) ? decimalPlaces : precision);\n    niceMin = Math.round(niceMin * factor) / factor;\n    niceMax = Math.round(niceMax * factor) / factor;\n    let j = 0;\n    if (minDefined) {\n        if (includeBounds && niceMin !== min) {\n            ticks.push({\n                value: min\n            });\n            if (niceMin < min) {\n                j++;\n            }\n            if (almostEquals(Math.round((niceMin + j * spacing) * factor) / factor, min, relativeLabelSize(min, minSpacing, generationOptions))) {\n                j++;\n            }\n        } else if (niceMin < min) {\n            j++;\n        }\n    }\n    for(; j < numSpaces; ++j){\n        const tickValue = Math.round((niceMin + j * spacing) * factor) / factor;\n        if (maxDefined && tickValue > max) {\n            break;\n        }\n        ticks.push({\n            value: tickValue\n        });\n    }\n    if (maxDefined && includeBounds && niceMax !== max) {\n        if (ticks.length && almostEquals(ticks[ticks.length - 1].value, max, relativeLabelSize(max, minSpacing, generationOptions))) {\n            ticks[ticks.length - 1].value = max;\n        } else {\n            ticks.push({\n                value: max\n            });\n        }\n    } else if (!maxDefined || niceMax === max) {\n        ticks.push({\n            value: niceMax\n        });\n    }\n    return ticks;\n}\nfunction relativeLabelSize(value, minSpacing, { horizontal , minRotation  }) {\n    const rad = toRadians(minRotation);\n    const ratio = (horizontal ? Math.sin(rad) : Math.cos(rad)) || 0.001;\n    const length = 0.75 * minSpacing * ('' + value).length;\n    return Math.min(minSpacing / ratio, length);\n}\nclass LinearScaleBase extends Scale {\n    constructor(cfg){\n        super(cfg);\n         this.start = undefined;\n         this.end = undefined;\n         this._startValue = undefined;\n         this._endValue = undefined;\n        this._valueRange = 0;\n    }\n    parse(raw, index) {\n        if (isNullOrUndef(raw)) {\n            return null;\n        }\n        if ((typeof raw === 'number' || raw instanceof Number) && !isFinite(+raw)) {\n            return null;\n        }\n        return +raw;\n    }\n    handleTickRangeOptions() {\n        const { beginAtZero  } = this.options;\n        const { minDefined , maxDefined  } = this.getUserBounds();\n        let { min , max  } = this;\n        const setMin = (v)=>min = minDefined ? min : v;\n        const setMax = (v)=>max = maxDefined ? max : v;\n        if (beginAtZero) {\n            const minSign = sign(min);\n            const maxSign = sign(max);\n            if (minSign < 0 && maxSign < 0) {\n                setMax(0);\n            } else if (minSign > 0 && maxSign > 0) {\n                setMin(0);\n            }\n        }\n        if (min === max) {\n            let offset = max === 0 ? 1 : Math.abs(max * 0.05);\n            setMax(max + offset);\n            if (!beginAtZero) {\n                setMin(min - offset);\n            }\n        }\n        this.min = min;\n        this.max = max;\n    }\n    getTickLimit() {\n        const tickOpts = this.options.ticks;\n        let { maxTicksLimit , stepSize  } = tickOpts;\n        let maxTicks;\n        if (stepSize) {\n            maxTicks = Math.ceil(this.max / stepSize) - Math.floor(this.min / stepSize) + 1;\n            if (maxTicks > 1000) {\n                console.warn(`scales.${this.id}.ticks.stepSize: ${stepSize} would result generating up to ${maxTicks} ticks. Limiting to 1000.`);\n                maxTicks = 1000;\n            }\n        } else {\n            maxTicks = this.computeTickLimit();\n            maxTicksLimit = maxTicksLimit || 11;\n        }\n        if (maxTicksLimit) {\n            maxTicks = Math.min(maxTicksLimit, maxTicks);\n        }\n        return maxTicks;\n    }\n computeTickLimit() {\n        return Number.POSITIVE_INFINITY;\n    }\n    buildTicks() {\n        const opts = this.options;\n        const tickOpts = opts.ticks;\n        let maxTicks = this.getTickLimit();\n        maxTicks = Math.max(2, maxTicks);\n        const numericGeneratorOptions = {\n            maxTicks,\n            bounds: opts.bounds,\n            min: opts.min,\n            max: opts.max,\n            precision: tickOpts.precision,\n            step: tickOpts.stepSize,\n            count: tickOpts.count,\n            maxDigits: this._maxDigits(),\n            horizontal: this.isHorizontal(),\n            minRotation: tickOpts.minRotation || 0,\n            includeBounds: tickOpts.includeBounds !== false\n        };\n        const dataRange = this._range || this;\n        const ticks = generateTicks$1(numericGeneratorOptions, dataRange);\n        if (opts.bounds === 'ticks') {\n            _setMinAndMaxByKey(ticks, this, 'value');\n        }\n        if (opts.reverse) {\n            ticks.reverse();\n            this.start = this.max;\n            this.end = this.min;\n        } else {\n            this.start = this.min;\n            this.end = this.max;\n        }\n        return ticks;\n    }\n configure() {\n        const ticks = this.ticks;\n        let start = this.min;\n        let end = this.max;\n        super.configure();\n        if (this.options.offset && ticks.length) {\n            const offset = (end - start) / Math.max(ticks.length - 1, 1) / 2;\n            start -= offset;\n            end += offset;\n        }\n        this._startValue = start;\n        this._endValue = end;\n        this._valueRange = end - start;\n    }\n    getLabelForValue(value) {\n        return formatNumber(value, this.chart.options.locale, this.options.ticks.format);\n    }\n}\n\nclass LinearScale extends LinearScaleBase {\n    static id = 'linear';\n static defaults = {\n        ticks: {\n            callback: Ticks.formatters.numeric\n        }\n    };\n    determineDataLimits() {\n        const { min , max  } = this.getMinMax(true);\n        this.min = isNumberFinite(min) ? min : 0;\n        this.max = isNumberFinite(max) ? max : 1;\n        this.handleTickRangeOptions();\n    }\n computeTickLimit() {\n        const horizontal = this.isHorizontal();\n        const length = horizontal ? this.width : this.height;\n        const minRotation = toRadians(this.options.ticks.minRotation);\n        const ratio = (horizontal ? Math.sin(minRotation) : Math.cos(minRotation)) || 0.001;\n        const tickFont = this._resolveTickFontOptions(0);\n        return Math.ceil(length / Math.min(40, tickFont.lineHeight / ratio));\n    }\n    getPixelForValue(value) {\n        return value === null ? NaN : this.getPixelForDecimal((value - this._startValue) / this._valueRange);\n    }\n    getValueForPixel(pixel) {\n        return this._startValue + this.getDecimalForPixel(pixel) * this._valueRange;\n    }\n}\n\nconst log10Floor = (v)=>Math.floor(log10(v));\nconst changeExponent = (v, m)=>Math.pow(10, log10Floor(v) + m);\nfunction isMajor(tickVal) {\n    const remain = tickVal / Math.pow(10, log10Floor(tickVal));\n    return remain === 1;\n}\nfunction steps(min, max, rangeExp) {\n    const rangeStep = Math.pow(10, rangeExp);\n    const start = Math.floor(min / rangeStep);\n    const end = Math.ceil(max / rangeStep);\n    return end - start;\n}\nfunction startExp(min, max) {\n    const range = max - min;\n    let rangeExp = log10Floor(range);\n    while(steps(min, max, rangeExp) > 10){\n        rangeExp++;\n    }\n    while(steps(min, max, rangeExp) < 10){\n        rangeExp--;\n    }\n    return Math.min(rangeExp, log10Floor(min));\n}\n function generateTicks(generationOptions, { min , max  }) {\n    min = finiteOrDefault(generationOptions.min, min);\n    const ticks = [];\n    const minExp = log10Floor(min);\n    let exp = startExp(min, max);\n    let precision = exp < 0 ? Math.pow(10, Math.abs(exp)) : 1;\n    const stepSize = Math.pow(10, exp);\n    const base = minExp > exp ? Math.pow(10, minExp) : 0;\n    const start = Math.round((min - base) * precision) / precision;\n    const offset = Math.floor((min - base) / stepSize / 10) * stepSize * 10;\n    let significand = Math.floor((start - offset) / Math.pow(10, exp));\n    let value = finiteOrDefault(generationOptions.min, Math.round((base + offset + significand * Math.pow(10, exp)) * precision) / precision);\n    while(value < max){\n        ticks.push({\n            value,\n            major: isMajor(value),\n            significand\n        });\n        if (significand >= 10) {\n            significand = significand < 15 ? 15 : 20;\n        } else {\n            significand++;\n        }\n        if (significand >= 20) {\n            exp++;\n            significand = 2;\n            precision = exp >= 0 ? 1 : precision;\n        }\n        value = Math.round((base + offset + significand * Math.pow(10, exp)) * precision) / precision;\n    }\n    const lastTick = finiteOrDefault(generationOptions.max, value);\n    ticks.push({\n        value: lastTick,\n        major: isMajor(lastTick),\n        significand\n    });\n    return ticks;\n}\nclass LogarithmicScale extends Scale {\n    static id = 'logarithmic';\n static defaults = {\n        ticks: {\n            callback: Ticks.formatters.logarithmic,\n            major: {\n                enabled: true\n            }\n        }\n    };\n    constructor(cfg){\n        super(cfg);\n         this.start = undefined;\n         this.end = undefined;\n         this._startValue = undefined;\n        this._valueRange = 0;\n    }\n    parse(raw, index) {\n        const value = LinearScaleBase.prototype.parse.apply(this, [\n            raw,\n            index\n        ]);\n        if (value === 0) {\n            this._zero = true;\n            return undefined;\n        }\n        return isNumberFinite(value) && value > 0 ? value : null;\n    }\n    determineDataLimits() {\n        const { min , max  } = this.getMinMax(true);\n        this.min = isNumberFinite(min) ? Math.max(0, min) : null;\n        this.max = isNumberFinite(max) ? Math.max(0, max) : null;\n        if (this.options.beginAtZero) {\n            this._zero = true;\n        }\n        if (this._zero && this.min !== this._suggestedMin && !isNumberFinite(this._userMin)) {\n            this.min = min === changeExponent(this.min, 0) ? changeExponent(this.min, -1) : changeExponent(this.min, 0);\n        }\n        this.handleTickRangeOptions();\n    }\n    handleTickRangeOptions() {\n        const { minDefined , maxDefined  } = this.getUserBounds();\n        let min = this.min;\n        let max = this.max;\n        const setMin = (v)=>min = minDefined ? min : v;\n        const setMax = (v)=>max = maxDefined ? max : v;\n        if (min === max) {\n            if (min <= 0) {\n                setMin(1);\n                setMax(10);\n            } else {\n                setMin(changeExponent(min, -1));\n                setMax(changeExponent(max, +1));\n            }\n        }\n        if (min <= 0) {\n            setMin(changeExponent(max, -1));\n        }\n        if (max <= 0) {\n            setMax(changeExponent(min, +1));\n        }\n        this.min = min;\n        this.max = max;\n    }\n    buildTicks() {\n        const opts = this.options;\n        const generationOptions = {\n            min: this._userMin,\n            max: this._userMax\n        };\n        const ticks = generateTicks(generationOptions, this);\n        if (opts.bounds === 'ticks') {\n            _setMinAndMaxByKey(ticks, this, 'value');\n        }\n        if (opts.reverse) {\n            ticks.reverse();\n            this.start = this.max;\n            this.end = this.min;\n        } else {\n            this.start = this.min;\n            this.end = this.max;\n        }\n        return ticks;\n    }\n getLabelForValue(value) {\n        return value === undefined ? '0' : formatNumber(value, this.chart.options.locale, this.options.ticks.format);\n    }\n configure() {\n        const start = this.min;\n        super.configure();\n        this._startValue = log10(start);\n        this._valueRange = log10(this.max) - log10(start);\n    }\n    getPixelForValue(value) {\n        if (value === undefined || value === 0) {\n            value = this.min;\n        }\n        if (value === null || isNaN(value)) {\n            return NaN;\n        }\n        return this.getPixelForDecimal(value === this.min ? 0 : (log10(value) - this._startValue) / this._valueRange);\n    }\n    getValueForPixel(pixel) {\n        const decimal = this.getDecimalForPixel(pixel);\n        return Math.pow(10, this._startValue + decimal * this._valueRange);\n    }\n}\n\nfunction getTickBackdropHeight(opts) {\n    const tickOpts = opts.ticks;\n    if (tickOpts.display && opts.display) {\n        const padding = toPadding(tickOpts.backdropPadding);\n        return valueOrDefault(tickOpts.font && tickOpts.font.size, defaults.font.size) + padding.height;\n    }\n    return 0;\n}\nfunction measureLabelSize(ctx, font, label) {\n    label = isArray(label) ? label : [\n        label\n    ];\n    return {\n        w: _longestText(ctx, font.string, label),\n        h: label.length * font.lineHeight\n    };\n}\nfunction determineLimits(angle, pos, size, min, max) {\n    if (angle === min || angle === max) {\n        return {\n            start: pos - size / 2,\n            end: pos + size / 2\n        };\n    } else if (angle < min || angle > max) {\n        return {\n            start: pos - size,\n            end: pos\n        };\n    }\n    return {\n        start: pos,\n        end: pos + size\n    };\n}\n function fitWithPointLabels(scale) {\n    const orig = {\n        l: scale.left + scale._padding.left,\n        r: scale.right - scale._padding.right,\n        t: scale.top + scale._padding.top,\n        b: scale.bottom - scale._padding.bottom\n    };\n    const limits = Object.assign({}, orig);\n    const labelSizes = [];\n    const padding = [];\n    const valueCount = scale._pointLabels.length;\n    const pointLabelOpts = scale.options.pointLabels;\n    const additionalAngle = pointLabelOpts.centerPointLabels ? PI / valueCount : 0;\n    for(let i = 0; i < valueCount; i++){\n        const opts = pointLabelOpts.setContext(scale.getPointLabelContext(i));\n        padding[i] = opts.padding;\n        const pointPosition = scale.getPointPosition(i, scale.drawingArea + padding[i], additionalAngle);\n        const plFont = toFont(opts.font);\n        const textSize = measureLabelSize(scale.ctx, plFont, scale._pointLabels[i]);\n        labelSizes[i] = textSize;\n        const angleRadians = _normalizeAngle(scale.getIndexAngle(i) + additionalAngle);\n        const angle = Math.round(toDegrees(angleRadians));\n        const hLimits = determineLimits(angle, pointPosition.x, textSize.w, 0, 180);\n        const vLimits = determineLimits(angle, pointPosition.y, textSize.h, 90, 270);\n        updateLimits(limits, orig, angleRadians, hLimits, vLimits);\n    }\n    scale.setCenterPoint(orig.l - limits.l, limits.r - orig.r, orig.t - limits.t, limits.b - orig.b);\n    scale._pointLabelItems = buildPointLabelItems(scale, labelSizes, padding);\n}\nfunction updateLimits(limits, orig, angle, hLimits, vLimits) {\n    const sin = Math.abs(Math.sin(angle));\n    const cos = Math.abs(Math.cos(angle));\n    let x = 0;\n    let y = 0;\n    if (hLimits.start < orig.l) {\n        x = (orig.l - hLimits.start) / sin;\n        limits.l = Math.min(limits.l, orig.l - x);\n    } else if (hLimits.end > orig.r) {\n        x = (hLimits.end - orig.r) / sin;\n        limits.r = Math.max(limits.r, orig.r + x);\n    }\n    if (vLimits.start < orig.t) {\n        y = (orig.t - vLimits.start) / cos;\n        limits.t = Math.min(limits.t, orig.t - y);\n    } else if (vLimits.end > orig.b) {\n        y = (vLimits.end - orig.b) / cos;\n        limits.b = Math.max(limits.b, orig.b + y);\n    }\n}\nfunction createPointLabelItem(scale, index, itemOpts) {\n    const outerDistance = scale.drawingArea;\n    const { extra , additionalAngle , padding , size  } = itemOpts;\n    const pointLabelPosition = scale.getPointPosition(index, outerDistance + extra + padding, additionalAngle);\n    const angle = Math.round(toDegrees(_normalizeAngle(pointLabelPosition.angle + HALF_PI)));\n    const y = yForAngle(pointLabelPosition.y, size.h, angle);\n    const textAlign = getTextAlignForAngle(angle);\n    const left = leftForTextAlign(pointLabelPosition.x, size.w, textAlign);\n    return {\n        visible: true,\n        x: pointLabelPosition.x,\n        y,\n        textAlign,\n        left,\n        top: y,\n        right: left + size.w,\n        bottom: y + size.h\n    };\n}\nfunction isNotOverlapped(item, area) {\n    if (!area) {\n        return true;\n    }\n    const { left , top , right , bottom  } = item;\n    const apexesInArea = _isPointInArea({\n        x: left,\n        y: top\n    }, area) || _isPointInArea({\n        x: left,\n        y: bottom\n    }, area) || _isPointInArea({\n        x: right,\n        y: top\n    }, area) || _isPointInArea({\n        x: right,\n        y: bottom\n    }, area);\n    return !apexesInArea;\n}\nfunction buildPointLabelItems(scale, labelSizes, padding) {\n    const items = [];\n    const valueCount = scale._pointLabels.length;\n    const opts = scale.options;\n    const { centerPointLabels , display  } = opts.pointLabels;\n    const itemOpts = {\n        extra: getTickBackdropHeight(opts) / 2,\n        additionalAngle: centerPointLabels ? PI / valueCount : 0\n    };\n    let area;\n    for(let i = 0; i < valueCount; i++){\n        itemOpts.padding = padding[i];\n        itemOpts.size = labelSizes[i];\n        const item = createPointLabelItem(scale, i, itemOpts);\n        items.push(item);\n        if (display === 'auto') {\n            item.visible = isNotOverlapped(item, area);\n            if (item.visible) {\n                area = item;\n            }\n        }\n    }\n    return items;\n}\nfunction getTextAlignForAngle(angle) {\n    if (angle === 0 || angle === 180) {\n        return 'center';\n    } else if (angle < 180) {\n        return 'left';\n    }\n    return 'right';\n}\nfunction leftForTextAlign(x, w, align) {\n    if (align === 'right') {\n        x -= w;\n    } else if (align === 'center') {\n        x -= w / 2;\n    }\n    return x;\n}\nfunction yForAngle(y, h, angle) {\n    if (angle === 90 || angle === 270) {\n        y -= h / 2;\n    } else if (angle > 270 || angle < 90) {\n        y -= h;\n    }\n    return y;\n}\nfunction drawPointLabelBox(ctx, opts, item) {\n    const { left , top , right , bottom  } = item;\n    const { backdropColor  } = opts;\n    if (!isNullOrUndef(backdropColor)) {\n        const borderRadius = toTRBLCorners(opts.borderRadius);\n        const padding = toPadding(opts.backdropPadding);\n        ctx.fillStyle = backdropColor;\n        const backdropLeft = left - padding.left;\n        const backdropTop = top - padding.top;\n        const backdropWidth = right - left + padding.width;\n        const backdropHeight = bottom - top + padding.height;\n        if (Object.values(borderRadius).some((v)=>v !== 0)) {\n            ctx.beginPath();\n            addRoundedRectPath(ctx, {\n                x: backdropLeft,\n                y: backdropTop,\n                w: backdropWidth,\n                h: backdropHeight,\n                radius: borderRadius\n            });\n            ctx.fill();\n        } else {\n            ctx.fillRect(backdropLeft, backdropTop, backdropWidth, backdropHeight);\n        }\n    }\n}\nfunction drawPointLabels(scale, labelCount) {\n    const { ctx , options: { pointLabels  }  } = scale;\n    for(let i = labelCount - 1; i >= 0; i--){\n        const item = scale._pointLabelItems[i];\n        if (!item.visible) {\n            continue;\n        }\n        const optsAtIndex = pointLabels.setContext(scale.getPointLabelContext(i));\n        drawPointLabelBox(ctx, optsAtIndex, item);\n        const plFont = toFont(optsAtIndex.font);\n        const { x , y , textAlign  } = item;\n        renderText(ctx, scale._pointLabels[i], x, y + plFont.lineHeight / 2, plFont, {\n            color: optsAtIndex.color,\n            textAlign: textAlign,\n            textBaseline: 'middle'\n        });\n    }\n}\nfunction pathRadiusLine(scale, radius, circular, labelCount) {\n    const { ctx  } = scale;\n    if (circular) {\n        ctx.arc(scale.xCenter, scale.yCenter, radius, 0, TAU);\n    } else {\n        let pointPosition = scale.getPointPosition(0, radius);\n        ctx.moveTo(pointPosition.x, pointPosition.y);\n        for(let i = 1; i < labelCount; i++){\n            pointPosition = scale.getPointPosition(i, radius);\n            ctx.lineTo(pointPosition.x, pointPosition.y);\n        }\n    }\n}\nfunction drawRadiusLine(scale, gridLineOpts, radius, labelCount, borderOpts) {\n    const ctx = scale.ctx;\n    const circular = gridLineOpts.circular;\n    const { color , lineWidth  } = gridLineOpts;\n    if (!circular && !labelCount || !color || !lineWidth || radius < 0) {\n        return;\n    }\n    ctx.save();\n    ctx.strokeStyle = color;\n    ctx.lineWidth = lineWidth;\n    ctx.setLineDash(borderOpts.dash);\n    ctx.lineDashOffset = borderOpts.dashOffset;\n    ctx.beginPath();\n    pathRadiusLine(scale, radius, circular, labelCount);\n    ctx.closePath();\n    ctx.stroke();\n    ctx.restore();\n}\nfunction createPointLabelContext(parent, index, label) {\n    return createContext(parent, {\n        label,\n        index,\n        type: 'pointLabel'\n    });\n}\nclass RadialLinearScale extends LinearScaleBase {\n    static id = 'radialLinear';\n static defaults = {\n        display: true,\n        animate: true,\n        position: 'chartArea',\n        angleLines: {\n            display: true,\n            lineWidth: 1,\n            borderDash: [],\n            borderDashOffset: 0.0\n        },\n        grid: {\n            circular: false\n        },\n        startAngle: 0,\n        ticks: {\n            showLabelBackdrop: true,\n            callback: Ticks.formatters.numeric\n        },\n        pointLabels: {\n            backdropColor: undefined,\n            backdropPadding: 2,\n            display: true,\n            font: {\n                size: 10\n            },\n            callback (label) {\n                return label;\n            },\n            padding: 5,\n            centerPointLabels: false\n        }\n    };\n    static defaultRoutes = {\n        'angleLines.color': 'borderColor',\n        'pointLabels.color': 'color',\n        'ticks.color': 'color'\n    };\n    static descriptors = {\n        angleLines: {\n            _fallback: 'grid'\n        }\n    };\n    constructor(cfg){\n        super(cfg);\n         this.xCenter = undefined;\n         this.yCenter = undefined;\n         this.drawingArea = undefined;\n         this._pointLabels = [];\n        this._pointLabelItems = [];\n    }\n    setDimensions() {\n        const padding = this._padding = toPadding(getTickBackdropHeight(this.options) / 2);\n        const w = this.width = this.maxWidth - padding.width;\n        const h = this.height = this.maxHeight - padding.height;\n        this.xCenter = Math.floor(this.left + w / 2 + padding.left);\n        this.yCenter = Math.floor(this.top + h / 2 + padding.top);\n        this.drawingArea = Math.floor(Math.min(w, h) / 2);\n    }\n    determineDataLimits() {\n        const { min , max  } = this.getMinMax(false);\n        this.min = isNumberFinite(min) && !isNaN(min) ? min : 0;\n        this.max = isNumberFinite(max) && !isNaN(max) ? max : 0;\n        this.handleTickRangeOptions();\n    }\n computeTickLimit() {\n        return Math.ceil(this.drawingArea / getTickBackdropHeight(this.options));\n    }\n    generateTickLabels(ticks) {\n        LinearScaleBase.prototype.generateTickLabels.call(this, ticks);\n        this._pointLabels = this.getLabels().map((value, index)=>{\n            const label = callback(this.options.pointLabels.callback, [\n                value,\n                index\n            ], this);\n            return label || label === 0 ? label : '';\n        }).filter((v, i)=>this.chart.getDataVisibility(i));\n    }\n    fit() {\n        const opts = this.options;\n        if (opts.display && opts.pointLabels.display) {\n            fitWithPointLabels(this);\n        } else {\n            this.setCenterPoint(0, 0, 0, 0);\n        }\n    }\n    setCenterPoint(leftMovement, rightMovement, topMovement, bottomMovement) {\n        this.xCenter += Math.floor((leftMovement - rightMovement) / 2);\n        this.yCenter += Math.floor((topMovement - bottomMovement) / 2);\n        this.drawingArea -= Math.min(this.drawingArea / 2, Math.max(leftMovement, rightMovement, topMovement, bottomMovement));\n    }\n    getIndexAngle(index) {\n        const angleMultiplier = TAU / (this._pointLabels.length || 1);\n        const startAngle = this.options.startAngle || 0;\n        return _normalizeAngle(index * angleMultiplier + toRadians(startAngle));\n    }\n    getDistanceFromCenterForValue(value) {\n        if (isNullOrUndef(value)) {\n            return NaN;\n        }\n        const scalingFactor = this.drawingArea / (this.max - this.min);\n        if (this.options.reverse) {\n            return (this.max - value) * scalingFactor;\n        }\n        return (value - this.min) * scalingFactor;\n    }\n    getValueForDistanceFromCenter(distance) {\n        if (isNullOrUndef(distance)) {\n            return NaN;\n        }\n        const scaledDistance = distance / (this.drawingArea / (this.max - this.min));\n        return this.options.reverse ? this.max - scaledDistance : this.min + scaledDistance;\n    }\n    getPointLabelContext(index) {\n        const pointLabels = this._pointLabels || [];\n        if (index >= 0 && index < pointLabels.length) {\n            const pointLabel = pointLabels[index];\n            return createPointLabelContext(this.getContext(), index, pointLabel);\n        }\n    }\n    getPointPosition(index, distanceFromCenter, additionalAngle = 0) {\n        const angle = this.getIndexAngle(index) - HALF_PI + additionalAngle;\n        return {\n            x: Math.cos(angle) * distanceFromCenter + this.xCenter,\n            y: Math.sin(angle) * distanceFromCenter + this.yCenter,\n            angle\n        };\n    }\n    getPointPositionForValue(index, value) {\n        return this.getPointPosition(index, this.getDistanceFromCenterForValue(value));\n    }\n    getBasePosition(index) {\n        return this.getPointPositionForValue(index || 0, this.getBaseValue());\n    }\n    getPointLabelPosition(index) {\n        const { left , top , right , bottom  } = this._pointLabelItems[index];\n        return {\n            left,\n            top,\n            right,\n            bottom\n        };\n    }\n drawBackground() {\n        const { backgroundColor , grid: { circular  }  } = this.options;\n        if (backgroundColor) {\n            const ctx = this.ctx;\n            ctx.save();\n            ctx.beginPath();\n            pathRadiusLine(this, this.getDistanceFromCenterForValue(this._endValue), circular, this._pointLabels.length);\n            ctx.closePath();\n            ctx.fillStyle = backgroundColor;\n            ctx.fill();\n            ctx.restore();\n        }\n    }\n drawGrid() {\n        const ctx = this.ctx;\n        const opts = this.options;\n        const { angleLines , grid , border  } = opts;\n        const labelCount = this._pointLabels.length;\n        let i, offset, position;\n        if (opts.pointLabels.display) {\n            drawPointLabels(this, labelCount);\n        }\n        if (grid.display) {\n            this.ticks.forEach((tick, index)=>{\n                if (index !== 0 || index === 0 && this.min < 0) {\n                    offset = this.getDistanceFromCenterForValue(tick.value);\n                    const context = this.getContext(index);\n                    const optsAtIndex = grid.setContext(context);\n                    const optsAtIndexBorder = border.setContext(context);\n                    drawRadiusLine(this, optsAtIndex, offset, labelCount, optsAtIndexBorder);\n                }\n            });\n        }\n        if (angleLines.display) {\n            ctx.save();\n            for(i = labelCount - 1; i >= 0; i--){\n                const optsAtIndex = angleLines.setContext(this.getPointLabelContext(i));\n                const { color , lineWidth  } = optsAtIndex;\n                if (!lineWidth || !color) {\n                    continue;\n                }\n                ctx.lineWidth = lineWidth;\n                ctx.strokeStyle = color;\n                ctx.setLineDash(optsAtIndex.borderDash);\n                ctx.lineDashOffset = optsAtIndex.borderDashOffset;\n                offset = this.getDistanceFromCenterForValue(opts.ticks.reverse ? this.min : this.max);\n                position = this.getPointPosition(i, offset);\n                ctx.beginPath();\n                ctx.moveTo(this.xCenter, this.yCenter);\n                ctx.lineTo(position.x, position.y);\n                ctx.stroke();\n            }\n            ctx.restore();\n        }\n    }\n drawBorder() {}\n drawLabels() {\n        const ctx = this.ctx;\n        const opts = this.options;\n        const tickOpts = opts.ticks;\n        if (!tickOpts.display) {\n            return;\n        }\n        const startAngle = this.getIndexAngle(0);\n        let offset, width;\n        ctx.save();\n        ctx.translate(this.xCenter, this.yCenter);\n        ctx.rotate(startAngle);\n        ctx.textAlign = 'center';\n        ctx.textBaseline = 'middle';\n        this.ticks.forEach((tick, index)=>{\n            if (index === 0 && this.min >= 0 && !opts.reverse) {\n                return;\n            }\n            const optsAtIndex = tickOpts.setContext(this.getContext(index));\n            const tickFont = toFont(optsAtIndex.font);\n            offset = this.getDistanceFromCenterForValue(this.ticks[index].value);\n            if (optsAtIndex.showLabelBackdrop) {\n                ctx.font = tickFont.string;\n                width = ctx.measureText(tick.label).width;\n                ctx.fillStyle = optsAtIndex.backdropColor;\n                const padding = toPadding(optsAtIndex.backdropPadding);\n                ctx.fillRect(-width / 2 - padding.left, -offset - tickFont.size / 2 - padding.top, width + padding.width, tickFont.size + padding.height);\n            }\n            renderText(ctx, tick.label, 0, -offset, tickFont, {\n                color: optsAtIndex.color,\n                strokeColor: optsAtIndex.textStrokeColor,\n                strokeWidth: optsAtIndex.textStrokeWidth\n            });\n        });\n        ctx.restore();\n    }\n drawTitle() {}\n}\n\nconst INTERVALS = {\n    millisecond: {\n        common: true,\n        size: 1,\n        steps: 1000\n    },\n    second: {\n        common: true,\n        size: 1000,\n        steps: 60\n    },\n    minute: {\n        common: true,\n        size: 60000,\n        steps: 60\n    },\n    hour: {\n        common: true,\n        size: 3600000,\n        steps: 24\n    },\n    day: {\n        common: true,\n        size: 86400000,\n        steps: 30\n    },\n    week: {\n        common: false,\n        size: 604800000,\n        steps: 4\n    },\n    month: {\n        common: true,\n        size: 2.628e9,\n        steps: 12\n    },\n    quarter: {\n        common: false,\n        size: 7.884e9,\n        steps: 4\n    },\n    year: {\n        common: true,\n        size: 3.154e10\n    }\n};\n const UNITS =  /* #__PURE__ */ Object.keys(INTERVALS);\n function sorter(a, b) {\n    return a - b;\n}\n function parse(scale, input) {\n    if (isNullOrUndef(input)) {\n        return null;\n    }\n    const adapter = scale._adapter;\n    const { parser , round , isoWeekday  } = scale._parseOpts;\n    let value = input;\n    if (typeof parser === 'function') {\n        value = parser(value);\n    }\n    if (!isNumberFinite(value)) {\n        value = typeof parser === 'string' ? adapter.parse(value,  parser) : adapter.parse(value);\n    }\n    if (value === null) {\n        return null;\n    }\n    if (round) {\n        value = round === 'week' && (isNumber(isoWeekday) || isoWeekday === true) ? adapter.startOf(value, 'isoWeek', isoWeekday) : adapter.startOf(value, round);\n    }\n    return +value;\n}\n function determineUnitForAutoTicks(minUnit, min, max, capacity) {\n    const ilen = UNITS.length;\n    for(let i = UNITS.indexOf(minUnit); i < ilen - 1; ++i){\n        const interval = INTERVALS[UNITS[i]];\n        const factor = interval.steps ? interval.steps : Number.MAX_SAFE_INTEGER;\n        if (interval.common && Math.ceil((max - min) / (factor * interval.size)) <= capacity) {\n            return UNITS[i];\n        }\n    }\n    return UNITS[ilen - 1];\n}\n function determineUnitForFormatting(scale, numTicks, minUnit, min, max) {\n    for(let i = UNITS.length - 1; i >= UNITS.indexOf(minUnit); i--){\n        const unit = UNITS[i];\n        if (INTERVALS[unit].common && scale._adapter.diff(max, min, unit) >= numTicks - 1) {\n            return unit;\n        }\n    }\n    return UNITS[minUnit ? UNITS.indexOf(minUnit) : 0];\n}\n function determineMajorUnit(unit) {\n    for(let i = UNITS.indexOf(unit) + 1, ilen = UNITS.length; i < ilen; ++i){\n        if (INTERVALS[UNITS[i]].common) {\n            return UNITS[i];\n        }\n    }\n}\n function addTick(ticks, time, timestamps) {\n    if (!timestamps) {\n        ticks[time] = true;\n    } else if (timestamps.length) {\n        const { lo , hi  } = _lookup(timestamps, time);\n        const timestamp = timestamps[lo] >= time ? timestamps[lo] : timestamps[hi];\n        ticks[timestamp] = true;\n    }\n}\n function setMajorTicks(scale, ticks, map, majorUnit) {\n    const adapter = scale._adapter;\n    const first = +adapter.startOf(ticks[0].value, majorUnit);\n    const last = ticks[ticks.length - 1].value;\n    let major, index;\n    for(major = first; major <= last; major = +adapter.add(major, 1, majorUnit)){\n        index = map[major];\n        if (index >= 0) {\n            ticks[index].major = true;\n        }\n    }\n    return ticks;\n}\n function ticksFromTimestamps(scale, values, majorUnit) {\n    const ticks = [];\n     const map = {};\n    const ilen = values.length;\n    let i, value;\n    for(i = 0; i < ilen; ++i){\n        value = values[i];\n        map[value] = i;\n        ticks.push({\n            value,\n            major: false\n        });\n    }\n    return ilen === 0 || !majorUnit ? ticks : setMajorTicks(scale, ticks, map, majorUnit);\n}\nclass TimeScale extends Scale {\n    static id = 'time';\n static defaults = {\n bounds: 'data',\n        adapters: {},\n        time: {\n            parser: false,\n            unit: false,\n            round: false,\n            isoWeekday: false,\n            minUnit: 'millisecond',\n            displayFormats: {}\n        },\n        ticks: {\n source: 'auto',\n            callback: false,\n            major: {\n                enabled: false\n            }\n        }\n    };\n constructor(props){\n        super(props);\n         this._cache = {\n            data: [],\n            labels: [],\n            all: []\n        };\n         this._unit = 'day';\n         this._majorUnit = undefined;\n        this._offsets = {};\n        this._normalized = false;\n        this._parseOpts = undefined;\n    }\n    init(scaleOpts, opts = {}) {\n        const time = scaleOpts.time || (scaleOpts.time = {});\n         const adapter = this._adapter = new adapters._date(scaleOpts.adapters.date);\n        adapter.init(opts);\n        mergeIf(time.displayFormats, adapter.formats());\n        this._parseOpts = {\n            parser: time.parser,\n            round: time.round,\n            isoWeekday: time.isoWeekday\n        };\n        super.init(scaleOpts);\n        this._normalized = opts.normalized;\n    }\n parse(raw, index) {\n        if (raw === undefined) {\n            return null;\n        }\n        return parse(this, raw);\n    }\n    beforeLayout() {\n        super.beforeLayout();\n        this._cache = {\n            data: [],\n            labels: [],\n            all: []\n        };\n    }\n    determineDataLimits() {\n        const options = this.options;\n        const adapter = this._adapter;\n        const unit = options.time.unit || 'day';\n        let { min , max , minDefined , maxDefined  } = this.getUserBounds();\n function _applyBounds(bounds) {\n            if (!minDefined && !isNaN(bounds.min)) {\n                min = Math.min(min, bounds.min);\n            }\n            if (!maxDefined && !isNaN(bounds.max)) {\n                max = Math.max(max, bounds.max);\n            }\n        }\n        if (!minDefined || !maxDefined) {\n            _applyBounds(this._getLabelBounds());\n            if (options.bounds !== 'ticks' || options.ticks.source !== 'labels') {\n                _applyBounds(this.getMinMax(false));\n            }\n        }\n        min = isNumberFinite(min) && !isNaN(min) ? min : +adapter.startOf(Date.now(), unit);\n        max = isNumberFinite(max) && !isNaN(max) ? max : +adapter.endOf(Date.now(), unit) + 1;\n        this.min = Math.min(min, max - 1);\n        this.max = Math.max(min + 1, max);\n    }\n _getLabelBounds() {\n        const arr = this.getLabelTimestamps();\n        let min = Number.POSITIVE_INFINITY;\n        let max = Number.NEGATIVE_INFINITY;\n        if (arr.length) {\n            min = arr[0];\n            max = arr[arr.length - 1];\n        }\n        return {\n            min,\n            max\n        };\n    }\n buildTicks() {\n        const options = this.options;\n        const timeOpts = options.time;\n        const tickOpts = options.ticks;\n        const timestamps = tickOpts.source === 'labels' ? this.getLabelTimestamps() : this._generate();\n        if (options.bounds === 'ticks' && timestamps.length) {\n            this.min = this._userMin || timestamps[0];\n            this.max = this._userMax || timestamps[timestamps.length - 1];\n        }\n        const min = this.min;\n        const max = this.max;\n        const ticks = _filterBetween(timestamps, min, max);\n        this._unit = timeOpts.unit || (tickOpts.autoSkip ? determineUnitForAutoTicks(timeOpts.minUnit, this.min, this.max, this._getLabelCapacity(min)) : determineUnitForFormatting(this, ticks.length, timeOpts.minUnit, this.min, this.max));\n        this._majorUnit = !tickOpts.major.enabled || this._unit === 'year' ? undefined : determineMajorUnit(this._unit);\n        this.initOffsets(timestamps);\n        if (options.reverse) {\n            ticks.reverse();\n        }\n        return ticksFromTimestamps(this, ticks, this._majorUnit);\n    }\n    afterAutoSkip() {\n        if (this.options.offsetAfterAutoskip) {\n            this.initOffsets(this.ticks.map((tick)=>+tick.value));\n        }\n    }\n initOffsets(timestamps = []) {\n        let start = 0;\n        let end = 0;\n        let first, last;\n        if (this.options.offset && timestamps.length) {\n            first = this.getDecimalForValue(timestamps[0]);\n            if (timestamps.length === 1) {\n                start = 1 - first;\n            } else {\n                start = (this.getDecimalForValue(timestamps[1]) - first) / 2;\n            }\n            last = this.getDecimalForValue(timestamps[timestamps.length - 1]);\n            if (timestamps.length === 1) {\n                end = last;\n            } else {\n                end = (last - this.getDecimalForValue(timestamps[timestamps.length - 2])) / 2;\n            }\n        }\n        const limit = timestamps.length < 3 ? 0.5 : 0.25;\n        start = _limitValue(start, 0, limit);\n        end = _limitValue(end, 0, limit);\n        this._offsets = {\n            start,\n            end,\n            factor: 1 / (start + 1 + end)\n        };\n    }\n _generate() {\n        const adapter = this._adapter;\n        const min = this.min;\n        const max = this.max;\n        const options = this.options;\n        const timeOpts = options.time;\n        const minor = timeOpts.unit || determineUnitForAutoTicks(timeOpts.minUnit, min, max, this._getLabelCapacity(min));\n        const stepSize = valueOrDefault(options.ticks.stepSize, 1);\n        const weekday = minor === 'week' ? timeOpts.isoWeekday : false;\n        const hasWeekday = isNumber(weekday) || weekday === true;\n        const ticks = {};\n        let first = min;\n        let time, count;\n        if (hasWeekday) {\n            first = +adapter.startOf(first, 'isoWeek', weekday);\n        }\n        first = +adapter.startOf(first, hasWeekday ? 'day' : minor);\n        if (adapter.diff(max, min, minor) > 100000 * stepSize) {\n            throw new Error(min + ' and ' + max + ' are too far apart with stepSize of ' + stepSize + ' ' + minor);\n        }\n        const timestamps = options.ticks.source === 'data' && this.getDataTimestamps();\n        for(time = first, count = 0; time < max; time = +adapter.add(time, stepSize, minor), count++){\n            addTick(ticks, time, timestamps);\n        }\n        if (time === max || options.bounds === 'ticks' || count === 1) {\n            addTick(ticks, time, timestamps);\n        }\n        return Object.keys(ticks).sort(sorter).map((x)=>+x);\n    }\n getLabelForValue(value) {\n        const adapter = this._adapter;\n        const timeOpts = this.options.time;\n        if (timeOpts.tooltipFormat) {\n            return adapter.format(value, timeOpts.tooltipFormat);\n        }\n        return adapter.format(value, timeOpts.displayFormats.datetime);\n    }\n format(value, format) {\n        const options = this.options;\n        const formats = options.time.displayFormats;\n        const unit = this._unit;\n        const fmt = format || formats[unit];\n        return this._adapter.format(value, fmt);\n    }\n _tickFormatFunction(time, index, ticks, format) {\n        const options = this.options;\n        const formatter = options.ticks.callback;\n        if (formatter) {\n            return callback(formatter, [\n                time,\n                index,\n                ticks\n            ], this);\n        }\n        const formats = options.time.displayFormats;\n        const unit = this._unit;\n        const majorUnit = this._majorUnit;\n        const minorFormat = unit && formats[unit];\n        const majorFormat = majorUnit && formats[majorUnit];\n        const tick = ticks[index];\n        const major = majorUnit && majorFormat && tick && tick.major;\n        return this._adapter.format(time, format || (major ? majorFormat : minorFormat));\n    }\n generateTickLabels(ticks) {\n        let i, ilen, tick;\n        for(i = 0, ilen = ticks.length; i < ilen; ++i){\n            tick = ticks[i];\n            tick.label = this._tickFormatFunction(tick.value, i, ticks);\n        }\n    }\n getDecimalForValue(value) {\n        return value === null ? NaN : (value - this.min) / (this.max - this.min);\n    }\n getPixelForValue(value) {\n        const offsets = this._offsets;\n        const pos = this.getDecimalForValue(value);\n        return this.getPixelForDecimal((offsets.start + pos) * offsets.factor);\n    }\n getValueForPixel(pixel) {\n        const offsets = this._offsets;\n        const pos = this.getDecimalForPixel(pixel) / offsets.factor - offsets.end;\n        return this.min + pos * (this.max - this.min);\n    }\n _getLabelSize(label) {\n        const ticksOpts = this.options.ticks;\n        const tickLabelWidth = this.ctx.measureText(label).width;\n        const angle = toRadians(this.isHorizontal() ? ticksOpts.maxRotation : ticksOpts.minRotation);\n        const cosRotation = Math.cos(angle);\n        const sinRotation = Math.sin(angle);\n        const tickFontSize = this._resolveTickFontOptions(0).size;\n        return {\n            w: tickLabelWidth * cosRotation + tickFontSize * sinRotation,\n            h: tickLabelWidth * sinRotation + tickFontSize * cosRotation\n        };\n    }\n _getLabelCapacity(exampleTime) {\n        const timeOpts = this.options.time;\n        const displayFormats = timeOpts.displayFormats;\n        const format = displayFormats[timeOpts.unit] || displayFormats.millisecond;\n        const exampleLabel = this._tickFormatFunction(exampleTime, 0, ticksFromTimestamps(this, [\n            exampleTime\n        ], this._majorUnit), format);\n        const size = this._getLabelSize(exampleLabel);\n        const capacity = Math.floor(this.isHorizontal() ? this.width / size.w : this.height / size.h) - 1;\n        return capacity > 0 ? capacity : 1;\n    }\n getDataTimestamps() {\n        let timestamps = this._cache.data || [];\n        let i, ilen;\n        if (timestamps.length) {\n            return timestamps;\n        }\n        const metas = this.getMatchingVisibleMetas();\n        if (this._normalized && metas.length) {\n            return this._cache.data = metas[0].controller.getAllParsedValues(this);\n        }\n        for(i = 0, ilen = metas.length; i < ilen; ++i){\n            timestamps = timestamps.concat(metas[i].controller.getAllParsedValues(this));\n        }\n        return this._cache.data = this.normalize(timestamps);\n    }\n getLabelTimestamps() {\n        const timestamps = this._cache.labels || [];\n        let i, ilen;\n        if (timestamps.length) {\n            return timestamps;\n        }\n        const labels = this.getLabels();\n        for(i = 0, ilen = labels.length; i < ilen; ++i){\n            timestamps.push(parse(this, labels[i]));\n        }\n        return this._cache.labels = this._normalized ? timestamps : this.normalize(timestamps);\n    }\n normalize(values) {\n        return _arrayUnique(values.sort(sorter));\n    }\n}\n\nfunction interpolate(table, val, reverse) {\n    let lo = 0;\n    let hi = table.length - 1;\n    let prevSource, nextSource, prevTarget, nextTarget;\n    if (reverse) {\n        if (val >= table[lo].pos && val <= table[hi].pos) {\n            ({ lo , hi  } = _lookupByKey(table, 'pos', val));\n        }\n        ({ pos: prevSource , time: prevTarget  } = table[lo]);\n        ({ pos: nextSource , time: nextTarget  } = table[hi]);\n    } else {\n        if (val >= table[lo].time && val <= table[hi].time) {\n            ({ lo , hi  } = _lookupByKey(table, 'time', val));\n        }\n        ({ time: prevSource , pos: prevTarget  } = table[lo]);\n        ({ time: nextSource , pos: nextTarget  } = table[hi]);\n    }\n    const span = nextSource - prevSource;\n    return span ? prevTarget + (nextTarget - prevTarget) * (val - prevSource) / span : prevTarget;\n}\nclass TimeSeriesScale extends TimeScale {\n    static id = 'timeseries';\n static defaults = TimeScale.defaults;\n constructor(props){\n        super(props);\n         this._table = [];\n         this._minPos = undefined;\n         this._tableRange = undefined;\n    }\n initOffsets() {\n        const timestamps = this._getTimestampsForTable();\n        const table = this._table = this.buildLookupTable(timestamps);\n        this._minPos = interpolate(table, this.min);\n        this._tableRange = interpolate(table, this.max) - this._minPos;\n        super.initOffsets(timestamps);\n    }\n buildLookupTable(timestamps) {\n        const { min , max  } = this;\n        const items = [];\n        const table = [];\n        let i, ilen, prev, curr, next;\n        for(i = 0, ilen = timestamps.length; i < ilen; ++i){\n            curr = timestamps[i];\n            if (curr >= min && curr <= max) {\n                items.push(curr);\n            }\n        }\n        if (items.length < 2) {\n            return [\n                {\n                    time: min,\n                    pos: 0\n                },\n                {\n                    time: max,\n                    pos: 1\n                }\n            ];\n        }\n        for(i = 0, ilen = items.length; i < ilen; ++i){\n            next = items[i + 1];\n            prev = items[i - 1];\n            curr = items[i];\n            if (Math.round((next + prev) / 2) !== curr) {\n                table.push({\n                    time: curr,\n                    pos: i / (ilen - 1)\n                });\n            }\n        }\n        return table;\n    }\n _generate() {\n        const min = this.min;\n        const max = this.max;\n        let timestamps = super.getDataTimestamps();\n        if (!timestamps.includes(min) || !timestamps.length) {\n            timestamps.splice(0, 0, min);\n        }\n        if (!timestamps.includes(max) || timestamps.length === 1) {\n            timestamps.push(max);\n        }\n        return timestamps.sort((a, b)=>a - b);\n    }\n _getTimestampsForTable() {\n        let timestamps = this._cache.all || [];\n        if (timestamps.length) {\n            return timestamps;\n        }\n        const data = this.getDataTimestamps();\n        const label = this.getLabelTimestamps();\n        if (data.length && label.length) {\n            timestamps = this.normalize(data.concat(label));\n        } else {\n            timestamps = data.length ? data : label;\n        }\n        timestamps = this._cache.all = timestamps;\n        return timestamps;\n    }\n getDecimalForValue(value) {\n        return (interpolate(this._table, value) - this._minPos) / this._tableRange;\n    }\n getValueForPixel(pixel) {\n        const offsets = this._offsets;\n        const decimal = this.getDecimalForPixel(pixel) / offsets.factor - offsets.end;\n        return interpolate(this._table, decimal * this._tableRange + this._minPos, true);\n    }\n}\n\nvar scales = /*#__PURE__*/Object.freeze({\n__proto__: null,\nCategoryScale: CategoryScale,\nLinearScale: LinearScale,\nLogarithmicScale: LogarithmicScale,\nRadialLinearScale: RadialLinearScale,\nTimeScale: TimeScale,\nTimeSeriesScale: TimeSeriesScale\n});\n\nconst registerables = [\n    controllers,\n    elements,\n    plugins,\n    scales\n];\n\nexport { Animation, Animations, ArcElement, BarController, BarElement, BasePlatform, BasicPlatform, BubbleController, CategoryScale, Chart, plugin_colors as Colors, DatasetController, plugin_decimation as Decimation, DomPlatform, DoughnutController, Element, index as Filler, Interaction, plugin_legend as Legend, LineController, LineElement, LinearScale, LogarithmicScale, PieController, PointElement, PolarAreaController, RadarController, RadialLinearScale, Scale, ScatterController, plugin_subtitle as SubTitle, Ticks, TimeScale, TimeSeriesScale, plugin_title as Title, plugin_tooltip as Tooltip, adapters as _adapters, _detectPlatform, animator, controllers, defaults, elements, layouts, plugins, registerables, registry, scales };\n//# sourceMappingURL=chart.js.map\n","import angular from \"angular\";\r\nimport { Brand, Calculation, Translations } from \"@salaxy/core\";\r\nimport { Chart, registerables } from \"chart.js\";\r\nimport type { ChartType } from \"chart.js\";\r\n/** Register chart registerables (ex. tooltip) */\r\nChart.register(...registerables);\r\n\r\n/**\r\n * Controller for employer and worker charts using chart.js\r\n */\r\nexport class CalcChartController implements angular.IController {\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$element\", \"$timeout\", \"$scope\"];\r\n\r\n  /** Role for which the chart is rendered: employer (default) or worker */\r\n  public role: \"employer\" | \"worker\";\r\n\r\n  /** Calculation that is rendered. */\r\n  public calc: Calculation;\r\n\r\n  /** Y axis scale */\r\n  public scaleYAxis: boolean;\r\n\r\n  /** Chart type: \"pie\" and \"bar\" (default) are currently supported. */\r\n  public chartType: \"pie\" | \"bar\";\r\n\r\n  private chart: Chart;\r\n\r\n  /** Created datasets from Calculation input */\r\n  private datasetData: any = {};\r\n\r\n  private barChartOptions: any = {};\r\n\r\n  private pieChartOptions: any = {};\r\n\r\n  private chartColors: any = {};\r\n\r\n  constructor(\r\n    private $element: JQLite,\r\n    private $timeout: angular.ITimeoutService,\r\n    private $scope: angular.IScope,\r\n  ) {}\r\n\r\n  /** Initializes the controller. */\r\n  public init() {\r\n    this.role = this.role || \"employer\";\r\n    this.chartType = this.chartType || \"bar\";\r\n    this.setChartOptions();\r\n    this.setChartColors();\r\n    this.$timeout(() => {\r\n      this.createChart();\r\n    });\r\n    this.$scope.$watch(() => ( { chartType: this.chartType, result: this.calc?.result } ), (newValue) => {\r\n      if (newValue) {\r\n\r\n        // update chart does not work, but renders columns instead of pie.\r\n        // this.updateChart();\r\n        if (this.chart) {\r\n          this.chart.destroy();\r\n          this.chart = null;\r\n        }\r\n        this.createChart();\r\n      }\r\n    }, true);\r\n  }\r\n\r\n  /** Creates chart based on data and options to canvas or updates chart if it already exists */\r\n  public createChart(): void {\r\n    this.datasetData = this.getDatasetData;\r\n    if (this.scaleYAxis) {\r\n      if (\r\n        this.datasetData.workerChartScale > this.datasetData.employerChartScale\r\n      ) {\r\n        this.setChartYAxisLimit(this.datasetData.workerChartScale);\r\n      } else {\r\n        this.setChartYAxisLimit(this.datasetData.employerChartScale);\r\n      }\r\n    } else {\r\n      if (this.role === \"worker\") {\r\n        this.setChartYAxisLimit(this.datasetData.workerChartScale);\r\n      } else {\r\n        this.setChartYAxisLimit(this.datasetData.employerChartScale);\r\n      }\r\n    }\r\n    const data = this.getChartData();\r\n    const options = this.chartType === \"bar\" ? this.barChartOptions : this.pieChartOptions;\r\n    if (!this.chart) {\r\n      const ctx = (this.$element.find(\"canvas\")[0] as HTMLCanvasElement)?.getContext(\"2d\");\r\n      if (ctx) {\r\n        this.chart = new Chart(ctx, {\r\n          type: this.chartType as ChartType,\r\n          data,\r\n          options,\r\n        });\r\n      }\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Updates provided current chart\r\n   * \"none\" parameters means no animation for update\r\n   */\r\n  public updateChart(): void {\r\n    if(this.chart) {\r\n      this.datasetData = this.getDatasetData;\r\n      if (this.scaleYAxis) {\r\n        if (\r\n          this.datasetData.workerChartScale > this.datasetData.employerChartScale\r\n        ) {\r\n          this.setChartYAxisLimit(this.datasetData.workerChartScale);\r\n        } else {\r\n          this.setChartYAxisLimit(this.datasetData.employerChartScale);\r\n        }\r\n      } else {\r\n        if (this.role === \"worker\") {\r\n          this.setChartYAxisLimit(this.datasetData.workerChartScale);\r\n        } else {\r\n          this.setChartYAxisLimit(this.datasetData.employerChartScale);\r\n        }\r\n      }\r\n      const data = this.getChartData();\r\n      const options = this.chartType === \"bar\" ? this.barChartOptions : this.pieChartOptions;\r\n      this.chart.data = data;\r\n      this.chart.options = options;\r\n      this.chart.update(\"none\");\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Calculates and sets a proper Y axis max value for a given value\r\n   * @param value The number of the highest bar in chart\r\n   */\r\n  private setChartYAxisLimit(value: number) {\r\n    const log = Math.round(Math.log10(value));\r\n    const times = Math.ceil(value / Math.pow(10, log - 1));\r\n    const newValue = Math.pow(10, log - 1) * times;\r\n    this.barChartOptions.scales.y = {\r\n      stacked: true,\r\n      min: 0,\r\n      max: newValue,\r\n      ticks: {\r\n        callback: function(val) {\r\n          return Number.isInteger(val) ? val : null;\r\n        }\r\n      }\r\n    };\r\n  }\r\n\r\n  private getChartData(): { labels: string[]; datasets: any[] } {\r\n    switch (this.role) {\r\n      case \"worker\":\r\n        return {\r\n          labels: [\r\n            `${Translations.get(\r\n              \"SALAXY.NG1.CalcChartComponent.createChartWorker.seriesLabel.salaryPayment\"\r\n            )} ${this.formatCurrency(this.datasetData.salaryPayment)}`,\r\n            `${Translations.get(\r\n              \"SALAXY.NG1.CalcChartComponent.createChartWorker.seriesLabel.tax\"\r\n            )} ${this.formatCurrency(this.datasetData.tax)}`,\r\n            `${Translations.get(\r\n              \"SALAXY.NG1.CalcChartComponent.createChartWorker.seriesLabel.workerSideCosts\"\r\n            )} ${this.formatCurrency(this.datasetData.workerSideCosts)}`,\r\n            `${Translations.get(\r\n              \"SALAXY.NG1.CalcChartComponent.createChartWorker.seriesLabel.totalExpenses\"\r\n            )} ${this.formatCurrency(\r\n              this.datasetData.benefits + this.datasetData.totalExpenses\r\n            )}`,\r\n          ],\r\n          datasets: this.getDatasets(),\r\n        };\r\n      case \"employer\":\r\n        return {\r\n          labels: [\r\n            `${Translations.get(\r\n              \"SALAXY.NG1.CalcChartComponent.createChartEmployer.seriesLabel.totalGrossSalary\"\r\n            )} ${this.formatCurrency(this.datasetData.totalGrossSalary)}`,\r\n            `${Translations.get(\r\n              \"SALAXY.NG1.CalcChartComponent.createChartEmployer.seriesLabel.salaryAdditions\"\r\n            )} ${this.formatCurrency(this.datasetData.salaryAdditions)}`,\r\n            `${Translations.get(\r\n              \"SALAXY.NG1.CalcChartComponent.createChartEmployer.seriesLabel.allSideCosts\"\r\n            )} ${this.formatCurrency(this.datasetData.allSideCosts)}`,\r\n            `${Translations.get(\r\n              \"SALAXY.NG1.CalcChartComponent.createChartEmployer.seriesLabel.totalExpenses\"\r\n            )} ${this.formatCurrency(this.datasetData.totalExpenses)}`,\r\n          ],\r\n          datasets: this.getDatasets(),\r\n        };\r\n      default:\r\n        return {\r\n          labels: [],\r\n          datasets: [],\r\n        };\r\n    }\r\n  }\r\n\r\n  private formatCurrency(value: number) {\r\n    const formatter = new Intl.NumberFormat(\"fi-FI\", {\r\n      style: \"currency\",\r\n      currency: \"EUR\",\r\n      minimumFractionDigits: 2,\r\n    });\r\n    return formatter.format(value);\r\n  }\r\n  private setChartOptions(): any {\r\n    this.barChartOptions = {\r\n      label: \"\",\r\n      responsive: true,\r\n      maintainAspectRatio: false,\r\n      scales: {\r\n        x: {\r\n          stacked: true,\r\n          min: 0,\r\n          max: 0,\r\n          display: false,\r\n        },\r\n        y: {\r\n          stacked: true,\r\n          min: 0,\r\n          max: 5000,\r\n          ticks: {\r\n            callback: function(val) {\r\n              return Number.isInteger(val) ? val : null;\r\n            }\r\n          }\r\n        },\r\n      },\r\n      plugins: {\r\n        datalabels: {\r\n          display: false,\r\n        },\r\n        legend: {\r\n          display: false,\r\n        },\r\n        tooltip: {\r\n          mode: \"index\",\r\n          callbacks: {\r\n            title() {\r\n              return \"\";\r\n            },\r\n            label(context: any) {\r\n              return context.dataset.label ?? \"\";\r\n            },\r\n          },\r\n          itemSort(a: { datasetIndex: number }, b: { datasetIndex: number }) {\r\n            return b.datasetIndex - a.datasetIndex;\r\n          },\r\n        },\r\n      },\r\n      events: [\"mousemove\", \"click\"],\r\n    };\r\n\r\n    this.pieChartOptions = {\r\n      plugins: {\r\n        legend: {\r\n          display: false,\r\n        },\r\n        tooltip: {\r\n          mode: \"dataset\",\r\n          callbacks: {\r\n            title() {\r\n              return \"\";\r\n            },\r\n            label(context: any) {\r\n              return context.label ?? \"\";\r\n            },\r\n          },\r\n          itemSort(a: { datasetIndex: number }, b: { datasetIndex: number }) {\r\n            return b.datasetIndex - a.datasetIndex;\r\n          },\r\n        },\r\n      },\r\n      events: [\"mousemove\", \"click\"],\r\n    };\r\n  }\r\n\r\n  private getDatasets(): any[] {\r\n    if (this.chartType === \"pie\") {\r\n      switch (this.role) {\r\n        case \"worker\":\r\n          return [\r\n            {\r\n              label: \"\",\r\n              data: [\r\n                this.datasetData.salaryPayment,\r\n                this.datasetData.tax,\r\n                this.datasetData.workerSideCosts,\r\n                this.datasetData.benefits + this.datasetData.totalExpenses,\r\n              ],\r\n              backgroundColor: [\r\n                this.chartColors.info,\r\n                this.chartColors.success,\r\n                this.chartColors.warning,\r\n                this.chartColors.danger,\r\n              ],\r\n            },\r\n          ];\r\n        case \"employer\":\r\n          return [\r\n            {\r\n              label: \"\",\r\n              data: [\r\n                this.datasetData.totalGrossSalary,\r\n                this.datasetData.salaryAdditions,\r\n                this.datasetData.allSideCosts,\r\n                this.datasetData.totalExpenses,\r\n              ],\r\n              backgroundColor: [\r\n                this.chartColors.info,\r\n                this.chartColors.success,\r\n                this.chartColors.warning,\r\n                this.chartColors.danger,\r\n              ],\r\n            },\r\n          ];\r\n        default:\r\n          return [];\r\n      }\r\n    } else {\r\n      switch (this.role) {\r\n        case \"worker\":\r\n          return [\r\n            {\r\n              label:\r\n                Translations.get(\r\n                  \"SALAXY.NG1.CalcChartComponent.createChartWorker.seriesLabel.salaryPayment\"\r\n                ) + this.formatCurrency(this.datasetData.salaryPayment),\r\n              data: [this.datasetData.salaryPayment],\r\n              backgroundColor: this.chartColors.info,\r\n            },\r\n            {\r\n              label:\r\n                Translations.get(\r\n                  \"SALAXY.NG1.CalcChartComponent.createChartWorker.seriesLabel.tax\"\r\n                ) + this.formatCurrency(this.datasetData.tax),\r\n              data: [this.datasetData.tax],\r\n              backgroundColor: this.chartColors.success,\r\n            },\r\n            {\r\n              label:\r\n                Translations.get(\r\n                  \"SALAXY.NG1.CalcChartComponent.createChartWorker.seriesLabel.workerSideCosts\"\r\n                ) + this.formatCurrency(this.datasetData.workerSideCosts),\r\n              data: [this.datasetData.workerSideCosts],\r\n              backgroundColor: this.chartColors.warning,\r\n            },\r\n            {\r\n              label:\r\n                Translations.get(\r\n                  \"SALAXY.NG1.CalcChartComponent.createChartWorker.seriesLabel.totalExpenses\"\r\n                ) +\r\n                this.formatCurrency(\r\n                  this.datasetData.benefits + this.datasetData.totalExpenses\r\n                ),\r\n              data: [\r\n                this.datasetData.benefits + this.datasetData.totalExpenses,\r\n              ],\r\n              backgroundColor: this.chartColors.danger,\r\n            },\r\n          ];\r\n        case \"employer\":\r\n          return [\r\n            {\r\n              label:\r\n                Translations.get(\r\n                  \"SALAXY.NG1.CalcChartComponent.createChartEmployer.seriesLabel.totalGrossSalary\"\r\n                ) + this.formatCurrency(this.datasetData.totalGrossSalary),\r\n              data: [this.datasetData.totalGrossSalary],\r\n              backgroundColor: this.chartColors.info,\r\n            },\r\n            {\r\n              label:\r\n                Translations.get(\r\n                  \"SALAXY.NG1.CalcChartComponent.createChartEmployer.seriesLabel.salaryAdditions\"\r\n                ) + this.formatCurrency(this.datasetData.salaryAdditions),\r\n              data: [this.datasetData.salaryAdditions],\r\n              backgroundColor: this.chartColors.success,\r\n            },\r\n            {\r\n              label:\r\n                Translations.get(\r\n                  \"SALAXY.NG1.CalcChartComponent.createChartEmployer.seriesLabel.allSideCosts\"\r\n                ) + this.formatCurrency(this.datasetData.allSideCosts),\r\n              data: [this.datasetData.allSideCosts],\r\n              backgroundColor: this.chartColors.warning,\r\n            },\r\n            {\r\n              label:\r\n                Translations.get(\r\n                  \"SALAXY.NG1.CalcChartComponent.createChartEmployer.seriesLabel.totalExpenses\"\r\n                ) + this.formatCurrency(this.datasetData.totalExpenses),\r\n              data: [this.datasetData.totalExpenses],\r\n              backgroundColor: this.chartColors.danger,\r\n            },\r\n          ];\r\n\r\n        default:\r\n          return [];\r\n      }\r\n    }\r\n  }\r\n\r\n  private setChartColors() {\r\n    const getColorSet = (code: string) =>\r\n      Brand.getBrandColor(code as any, \"rgba\");\r\n    this.chartColors = {\r\n      info: getColorSet(\"info\"),\r\n      success: getColorSet(\"success\"),\r\n      warning: getColorSet(\"warning\"),\r\n      danger: getColorSet(\"danger\"),\r\n    };\r\n  }\r\n\r\n  private get getDatasetData(): any {\r\n    const calc: Calculation = this.calc;\r\n    if (!calc || !calc.result) {\r\n      return {};\r\n    }\r\n\r\n    const { result } = calc;\r\n    const data = {\r\n      // Employer numbers\r\n      totalGrossSalary: result.totals.totalBaseSalary,\r\n      salaryAdditions:\r\n        result.totals.totalGrossSalary - result.totals?.totalBaseSalary,\r\n      allSideCosts: result.employerCalc.allSideCosts,\r\n      finalCost: result.employerCalc.finalCost,\r\n\r\n      // Worker numbers\r\n      salaryPayment: result.workerCalc.salaryPayment,\r\n      tax: result.workerCalc.tax,\r\n      workerSideCosts: result.workerCalc.workerSideCosts,\r\n      benefits: result.workerCalc.benefits,\r\n      totalExpenses: result.totals.totalExpenses,\r\n      totalWorkerPayment: result.workerCalc.totalWorkerPayment,\r\n\r\n      // Chart scales\r\n      employerChartScale: 0,\r\n      workerChartScale: 0,\r\n    };\r\n\r\n    // Calculating max y axis limits\r\n    data.employerChartScale =\r\n      data.totalGrossSalary +\r\n      data.salaryAdditions +\r\n      data.allSideCosts +\r\n      data.totalExpenses;\r\n    data.workerChartScale =\r\n      data.salaryPayment +\r\n      data.tax +\r\n      data.workerSideCosts +\r\n      data.benefits +\r\n      data.totalExpenses;\r\n    return data;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {\r\n  Calculation, CalculationRowType, CalculationRowUnit, Calculations, CalculatorLogic, DateRange,\r\n  HouseholdUsecase, HouseholdUsecasesLogic, UserDefinedRow, WorkerAccount, Workers, CalcWorktime, Dates, Translations,\r\n} from \"@salaxy/core\";\r\n\r\nimport { UiHelpers\r\n} from \"../../services\";\r\n\r\n/**\r\n * Handles the user interaction of Worktime within the Calculator.\r\n * The Worktime contains the logic for fetching holidays and absences\r\n * for that particular period and adding calculation rows for them if necessary.\r\n */\r\nexport class CalcHouseholdUsecaseController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"UiHelpers\",\r\n    \"Calculations\",\r\n    \"Workers\",\r\n  ];\r\n\r\n    /** User interface shortcuts for period selection */\r\n    public periodShortcuts: {\r\n      /** Text for current month. */\r\n      monthCurrent: string,\r\n      /** Text for last month. */\r\n      monthLast: string,\r\n      /** Text for other month. */\r\n      monthOther: string,\r\n      // monthMulti: \"Monta kuukautta\",\r\n      /** Text for two weeks. */\r\n      weeks2: string,\r\n      /** Text for half a month */\r\n      monthHalf: string,\r\n      /** Text for other period. */\r\n      other: string,\r\n    };\r\n  /** The calculation that the controller edits. */\r\n  public calc: Calculation;\r\n\r\n  /** Alternative data binding: creates a calculation based on Worker defaults. */\r\n  public worker: WorkerAccount;\r\n\r\n  /**\r\n   * Shows the Save and Reset buttons.\r\n   * Currently, this is only enabled for WorkerAccount data binding, but mayu later be enabled for calc.\r\n   */\r\n  public showSave: boolean;\r\n\r\n  /**\r\n   * If true, indicates that we are editing salary template information for employment relation:\r\n   * Not a concrete calculation.\r\n   */\r\n  public isEmployment: boolean;\r\n\r\n  /** If true, the UI is in read-only mode. */\r\n  public isReadOnly: boolean;\r\n\r\n\r\n  /** If there is a validation error in period start, it is added here. */\r\n  public periodStartDateError = null;\r\n\r\n  /**\r\n   * Worktime data for the period fetched from the server\r\n   */\r\n  public worktime: CalcWorktime;\r\n\r\n\r\n  /** The tree for selecting the calculation usecase (household) */\r\n  private tree = HouseholdUsecasesLogic.getUsecaseTree();\r\n\r\n  private _periodStartDate;\r\n\r\n  private _dateRange: DateRange;\r\n\r\n\r\n  /**\r\n   * Creates a new CalcHouseholdUsecaseController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    private uiHelpers: UiHelpers,\r\n    private calcApi: Calculations,\r\n    private workersApi: Workers,\r\n\r\n  ) {\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    if (!this.calc && this.worker) {\r\n      this.resetEmployment();\r\n    }\r\n    this.initDateRanges();\r\n\r\n  }\r\n\r\n\r\n  /**\r\n   * The use case that we are editing\r\n   */\r\n  public get usecaseData(): HouseholdUsecase {\r\n    return this.calc.usecase.data as HouseholdUsecase;\r\n  }\r\n\r\n  /** Gets the view template that is used for showing the usecase details part. */\r\n  public getTemplate() {\r\n    let group = \"other\";\r\n    switch (this.usecaseData.uri) {\r\n      case HouseholdUsecasesLogic.knownUseCases.childCare:\r\n      case HouseholdUsecasesLogic.knownUseCases.mll:\r\n        group = \"childCare\";\r\n        break;\r\n      case HouseholdUsecasesLogic.knownUseCases.cleaning:\r\n        group = \"cleaning\";\r\n        break;\r\n      case HouseholdUsecasesLogic.knownUseCases.construction:\r\n        group = \"construction\";\r\n        break;\r\n      case HouseholdUsecasesLogic.knownUseCases.santaClaus:\r\n      case HouseholdUsecasesLogic.knownUseCases.other:\r\n      default:\r\n        group = \"other\";\r\n        break;\r\n    }\r\n    return `salaxy-components/calc/usecases/household-${group}.html`;\r\n  }\r\n\r\n  /**\r\n   * Gets or sets the isHouseholdDeductible within the usecase.\r\n   * Currently, this is part of the usecase specification and will be set to Salary (household properties in V03) from there.\r\n   */\r\n  public get isHouseholdDeductible(): boolean {\r\n    return this.usecaseData.isHouseholdDeductible;\r\n  }\r\n  public set isHouseholdDeductible(value: boolean) {\r\n    this.usecaseData.isHouseholdDeductible = value;\r\n  }\r\n\r\n   /** Gets the current calculation object */\r\n   public get currentCalc(): Calculation {\r\n    return this.calc;\r\n  }\r\n\r\n  /**\r\n   * Returns true if there is no net salary payment to worker at all.\r\n   */\r\n  public get isCurrentZeroPayment(): boolean {\r\n    return CalculatorLogic.isZeroPayment(this.calc);\r\n  }\r\n\r\n  /**\r\n   * Submit the usecase data and recalculate\r\n   */\r\n  public submitHouseholdUsecase() {\r\n    const loader = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.isCalculating\");\r\n    HouseholdUsecasesLogic.applyUseCase(this.calc);\r\n    this.calcApi.recalculate(this.calc).then((data) => {\r\n      angular.copy(data, this.calc);\r\n      loader.dismiss();\r\n    });\r\n  }\r\n\r\n  /** Saves the usecase to employment */\r\n  public saveEmployment() {\r\n    const loader = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.isSaving\");\r\n    this.isReadOnly = true;\r\n    this.updateWorkerAccount().then(() => {\r\n      this.workersApi.save(this.worker).then(() => {\r\n        loader.dismiss();\r\n      });\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Does recalculation on the usecase and and applies it to worker account.\r\n   * @returns The updated worker account. The changes are also applied to the worker property.\r\n   */\r\n  public updateWorkerAccount(): Promise<WorkerAccount> {\r\n    HouseholdUsecasesLogic.applyUseCase(this.calc);\r\n    return this.calcApi.recalculate(this.calc).then((calcResult) => {\r\n      this.worker.employment.usecase = calcResult.usecase;\r\n      this.worker.employment.usecase.data.copyToCalc = true;\r\n      this.worker.employment.work.salaryDefaults = calcResult.rows;\r\n      this.worker.employment.work.occupationCode = calcResult.info.occupationCode;\r\n      return this.worker;\r\n    });\r\n  }\r\n\r\n  /** Resets the usecase from employment */\r\n  public resetEmployment() {\r\n    this.isEmployment = true;\r\n    this.calc = CalculatorLogic.getBlank();\r\n    this.calc.usecase = {};\r\n    angular.copy(this.worker.employment.work.salaryDefaults, this.calc.rows);\r\n    angular.copy(this.worker.employment.usecase, this.calc.usecase);\r\n    if (this.calc.usecase?.uri) {\r\n      this.isReadOnly = true;\r\n      HouseholdUsecasesLogic.applyUseCase(this.calc);\r\n    } else {\r\n      this.isReadOnly = false;\r\n    }\r\n  }\r\n\r\n  /** Starts the edit mode if the component is in read-only mode.  */\r\n  public startEdit() {\r\n    this.isReadOnly = false;\r\n  }\r\n\r\n  /**\r\n   * The salary row is the first row is the first row in the rows list\r\n   */\r\n  public get salaryRow(): UserDefinedRow {\r\n    return CalculatorLogic.getSalaryRow(this.calc);\r\n  }\r\n\r\n  /** Returns true if the usecase has been selected. */\r\n  public get isUsecaseSelected(): boolean {\r\n    return !!this.calc?.usecase?.uri;\r\n  }\r\n\r\n  /** Gets the label for price input */\r\n  public get priceLabel() {\r\n    switch (this.salaryRow.rowType) {\r\n      case CalculationRowType.Compensation:\r\n        return \"Työkorvaus\";\r\n      case CalculationRowType.Salary:\r\n        return \"Kertakorvaus\";\r\n      case CalculationRowType.HourlySalary:\r\n        return \"Tuntipalkka\";\r\n      case CalculationRowType.MonthlySalary:\r\n        return \"Kuukausipalkka\";\r\n      case CalculationRowType.TotalEmployerPayment:\r\n        return \"Kokonaiskustannus\";\r\n      case CalculationRowType.TotalWorkerPayment:\r\n        return \"Nettopalkka\";\r\n      default:\r\n        return \"Hinta\";\r\n    }\r\n  }\r\n  /**\r\n   * Select and set usecase in UI\r\n   */\r\n  public selectUsecase(usecase) {\r\n    this.calc.rows = [];\r\n    HouseholdUsecasesLogic.setUsecase(this.calc, usecase);\r\n  }\r\n\r\n  /** Resets the price and amount when row type is changed. */\r\n  public changeRowType() {\r\n    this.salaryRow.price = null;\r\n    if (this.salaryRow.rowType === CalculationRowType.HourlySalary) {\r\n      this.salaryRow.count = null;\r\n      this.salaryRow.unit = CalculationRowUnit.Hours;\r\n    } else {\r\n      this.salaryRow.count = 1;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Resets the usecase to empty: Shows the usecase selection again.\r\n   */\r\n  public resetUsecase() {\r\n    this.calc.usecase = {};\r\n  }\r\n\r\n  /** Getter and setter for Calculation daterange in compatible format for new DateRange component. */\r\n  public get dateRange(): DateRange {\r\n    const info = (this.calc || {}).info;\r\n    const framework = (this.calc || {}).framework;\r\n    if (!this._dateRange) {\r\n      this._dateRange = {\r\n        start: info.workStartDate,\r\n        end: info.workEndDate,\r\n        daysCount: framework.numberOfDays,\r\n      };\r\n    }\r\n    return this._dateRange;\r\n  }\r\n  public set dateRange(value: DateRange) {\r\n    this._dateRange = value;\r\n  }\r\n\r\n  /**\r\n   * Called when the date range changes.\r\n   * @param noPeriodStartDateUpdate If true, the _periodStartDate is not updated.\r\n   * Should be true if the change is triggered by that input to avoid UI flickering.\r\n   */\r\n  public dateRangeChange(noPeriodStartDateUpdate = false) {\r\n    const info = (this.currentCalc || {}).info;\r\n    const framework = (this.currentCalc || {}).framework;\r\n    info.workStartDate = this.dateRange.start;\r\n    if (!noPeriodStartDateUpdate) {\r\n      this._periodStartDate = Dates.format(this.dateRange.start, \"D.M.\", null);\r\n    }\r\n    info.workEndDate = this.dateRange.end;\r\n    framework.numberOfDays = this.dateRange.daysCount;\r\n  }\r\n\r\n  /**\r\n   * Gets or sets the period start date, which is bound to editable input in case the period type\r\n   * is not \"other\" (date the range / calendar component)\r\n   */\r\n  public get periodStartDate(): string {\r\n    return this._periodStartDate;\r\n  }\r\n  public set periodStartDate(value: string) {\r\n    this._periodStartDate = value;\r\n    const parts = (value || \"\").split(\".\");\r\n    if (parts.length < 2 || parts.length > 3) {\r\n      this.periodStartDateError = \"Syötä muodossa 'pv.kk.'\";\r\n      return;\r\n    }\r\n    let year = (parts.length === 3) ? Number((parts[2] || \"\").trim()) : null;\r\n    if (!year || year < 2019 || year > 2100) {\r\n      year = Number(this.dateRange.start.substr(0, 4));\r\n    }\r\n    const date = Dates.getDate(year, Number(parts[1]), Number(parts[0]));\r\n    if (date) {\r\n      this.periodStartDateError = null;\r\n      switch (this.periodShortcut) {\r\n        case \"monthCurrent\":\r\n        case \"monthLast\":\r\n        case \"monthOther\":\r\n          this.dateRange = Dates.getDateRange(date, Dates.add(Dates.add(date,1,\"month\"),-1,\"day\"));\r\n          break;\r\n        case \"weeks2\":\r\n          this.dateRange = Dates.getDateRange(date, Dates.add(Dates.add(date,2,\"week\"),-1,\"day\"));\r\n          break;\r\n        case \"monthHalf\":\r\n          if (Dates.getDay(date) === 15 || Dates.getDay(date) === 16) {\r\n            this.dateRange = Dates.getDateRange(date, Dates.startEnd(date,\"end-month\"));\r\n          } else {\r\n            this.dateRange = Dates.getDateRange(date, Dates.add(date,14, \"day\"));\r\n          }\r\n          break;\r\n        case \"other\":\r\n          this.dateRange = Dates.getDateRange(date, date);\r\n          break;\r\n      }\r\n      this.dateRangeChange(true);\r\n    } else {\r\n      this.periodStartDateError = `${value} ei ole päivämäärä.`;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Gets the user interface shortcut for the period type:\r\n   * Different user interfaces are shown depending on the period shortcut.\r\n   */\r\n  public get periodShortcut(): \"monthCurrent\" | \"monthLast\" | \"monthOther\" | \"weeks2\" | \"monthHalf\" | \"other\" {\r\n    if (!this.dateRange.start || !this.dateRange.end) {\r\n      return null;\r\n    }\r\n    if (this.dateRange.start === Dates.getDate(\"today\", \"today\", 1)\r\n      && this.dateRange.end === Dates.startEnd(\"today\",\"end-month\")) {\r\n\r\n      return \"monthCurrent\";\r\n    }\r\n    if (this.dateRange.start === Dates.add(Dates.startEnd(\"today\",\"start-month\"),-1,\"month\")\r\n      && this.dateRange.end === Dates.startEnd(Dates.add(Dates.startEnd(\"today\", \"start-month\"),-1,\"month\"),\"end-month\")) {\r\n      return \"monthLast\";\r\n    }\r\n    if (this.dateRange.end === Dates.add(Dates.add(this.dateRange.start, 1, \"month\"), -1, \"day\")) {\r\n      return \"monthOther\";\r\n    }\r\n    if (this.dateRange.end === Dates.add(Dates.add(this.dateRange.start,2, \"week\"),-1, \"day\")) {\r\n      return \"weeks2\";\r\n    }\r\n\r\n    // if the range is 15 (14) days or\r\n    // starts 15th or 16th and ends month end\r\n    if ((Dates.getDuration(this.dateRange.start, this.dateRange.end).days() === 14)\r\n      || (Dates.getDay(this.dateRange.start) === 15 && this.dateRange.end === Dates.startEnd(this.dateRange.start,\"end-month\"))\r\n      || (Dates.getDay(this.dateRange.start) === 16 && this.dateRange.end === Dates.startEnd(this.dateRange.start,\"end-month\"))) {\r\n      return \"monthHalf\";\r\n    }\r\n    return \"other\";\r\n  }\r\n  public set periodShortcut(value: \"monthCurrent\" | \"monthLast\" | \"monthOther\" | \"weeks2\" | \"monthHalf\" | \"other\") {\r\n    this.periodStartDateError = null;\r\n    switch (value) {\r\n      case \"monthCurrent\":\r\n        this.dateRange.start = Dates.getDate(\"today\", \"today\", 1);\r\n        this.dateRange.end = Dates.startEnd(\"today\",\"end-month\");\r\n        break;\r\n      case \"monthOther\":\r\n        if (Dates.getDay(\"today\") === 1) {\r\n          // Move to tomorrow so that the selection is monthOther and not monthCurrent.\r\n          this.dateRange.start = Dates.add(\"today\",1,\"day\");\r\n        } else {\r\n          this.dateRange.start = Dates.asDate(\"today\");\r\n        }\r\n        this.dateRange.end = Dates.add(Dates.add(this.dateRange.start,1,\"month\"),-1,\"day\");\r\n        break;\r\n      case \"monthLast\":\r\n        this.dateRange.start = Dates.add(Dates.startEnd(\"today\",\"start-month\"),-1,\"month\");\r\n        this.dateRange.end = Dates.startEnd(this.dateRange.start,\"end-month\");\r\n        break;\r\n        case \"weeks2\": //TODO Review this\r\n        this.dateRange.start = Dates.add(Dates.startEnd(\"today\",\"start-week\"),-2,\"week\"); //shift to start of current week, and then 2 weeks before\r\n        this.dateRange.end = Dates.add(Dates.startEnd(\"today\",\"start-week\"),-1,\"day\"); //shift to last day of previous week.\r\n        break;\r\n      case \"monthHalf\":\r\n        // TODO Check this\r\n        if (Dates.getDay(\"today\") < 16) {\r\n          // 16 - (28,29,30,31)\r\n          this.dateRange.start = Dates.add(Dates.add(Dates.startEnd(\"today\", \"start-month\"),-1,\"month\"),15,\"day\");\r\n          this.dateRange.end = Dates.startEnd(this.dateRange.start,\"end-month\");\r\n        } else {\r\n          // 1 - 15\r\n          this.dateRange.start = Dates.startEnd(\"today\",\"start-month\");\r\n          this.dateRange.end = Dates.add(this.dateRange.start,14,\"day\");\r\n        }\r\n        break;\r\n      case \"other\":\r\n        this.dateRange.start = Dates.add(\"today\",-1,\"day\");\r\n        this.dateRange.end = Dates.asDate(\"today\");\r\n        break;\r\n    }\r\n    this.dateRange = Dates.getDateRange(this.dateRange.start, this.dateRange.end);\r\n    this.dateRangeChange();\r\n  }\r\n  private initDateRanges() {\r\n    const currentMonth = Dates.getMonth(Dates.getToday());\r\n    this.periodShortcuts = {\r\n      monthCurrent: Translations.get(`SALAXY.ENUM.CalendarMonth.month${currentMonth}.label`),\r\n      monthLast: Translations.get(`SALAXY.ENUM.CalendarMonth.month${currentMonth === 1 ? 12 : (currentMonth - 1)}.label`),\r\n      monthOther: \"Muu kuukausi\",\r\n      // monthMulti: \"Monta kuukautta\",\r\n      weeks2: Translations.get(\"SALAXY.UI_Terms.week2\"),\r\n      monthHalf: Translations.get(\"SALAXY.UI_Terms.monthHalf\"),\r\n      other: Translations.get(\"SALAXY.UI_Terms.otherPeriod\"),\r\n    };\r\n    this._periodStartDate = Dates.format(this.dateRange.start, \"D.M.\", null);\r\n  }\r\n}\r\n","/** Logical section / area of the calculator ui. */\r\nexport class CalculatorSection {\r\n\r\n  /**\r\n   * Creates a new CalculatorSection\r\n   * @param isActive - If true, the section is currently active / selected in te user interface.\r\n   * @param isSelectionDone - If true, user has selected some values for the section\r\n   * @param title - Short text title for the section\r\n   */\r\n  constructor(public isActive: boolean, public isSelectionDone: boolean, public title: string) {\r\n  }\r\n\r\n  /**\r\n   * Shortcut for isSelectionDone or isActive.\r\n   * This is when the overview window should be shown colored\r\n   */\r\n  get isOverviewActive() {\r\n      return this.isSelectionDone || this.isActive;\r\n  }\r\n}\r\n","import { Calculation, CalculationStatus, CalculatorLogic, Numeric, Translations, UnionPaymentType } from \"@salaxy/core\";\r\nimport { CalculatorSection } from \"./CalculatorSection\";\r\n\r\n/** Sections defines areas of the calculator: worker, household-usecase, worktime, salary, expenses and results. */\r\nexport class CalculatorSections {\r\n\r\n  /**\r\n   * Creates a new CalculatorSections helper for a calculation\r\n   * @param calc The Calculation object for which the helper operates\r\n   */\r\n  constructor(public calc: Calculation) {\r\n    if (!calc || Object.keys(calc).length === 0) {\r\n      this.calc = CalculatorLogic.getBlank();\r\n    }\r\n  }\r\n\r\n  /** Stores the UI properties to the calculation until a roundtrip to server. Then the property is set to null */\r\n  public get ui(): any {\r\n    return CalculatorLogic.getUiCache(this.calc);\r\n  }\r\n\r\n  /**\r\n   * Activates a section in the calculator (opens the detail view).\r\n   * @param section - Name of the section\r\n   */\r\n  public setActive(section: string) {\r\n    this.ui.activeSection = section;\r\n  }\r\n\r\n  /**\r\n   * Toggles the section\r\n   */\r\n  public toggleActive(section: string) {\r\n    this.ui.activeSection = this.ui.activeSection === section ? null : section;\r\n  }\r\n\r\n  /**\r\n   * Toggles the section active / non-active.\r\n   */\r\n  public toggle(section: string) {\r\n    if (this.ui.activeSection === section) {\r\n      this.ui.activeSection = null;\r\n    } else {\r\n      this.ui.activeSection = section;\r\n    }\r\n  }\r\n\r\n  /** Gets a section */\r\n  public get(section: string) {\r\n    const isActive = this.ui.activeSection === section;\r\n    switch (section) {\r\n      case \"worker\":\r\n        return new CalculatorSection(\r\n          isActive,\r\n          this.calc.worker && this.calc.worker.avatar.id != null,\r\n          (this.calc.worker && this.calc.worker.avatar.displayName)\r\n            ? this.calc.worker.avatar.displayName\r\n            : Translations.get(\"SALAXY.NG1.CalcComponent.workerSectionDefaultInfo\"),\r\n        );\r\n      case \"household-usecase\":\r\n        return new CalculatorSection(\r\n          isActive,\r\n          this.calc.usecase == null || this.calc.usecase.label != null,\r\n          null, // No longer in use\r\n        );\r\n      case \"worktime\":\r\n        return new CalculatorSection(\r\n          isActive,\r\n          !!(this.calc.info.workStartDate && this.calc.info.workEndDate),\r\n          null, // No longer in use in Calculator2018\r\n        );\r\n      case \"expenses\": {\r\n        const expenses = CalculatorLogic.getTotalForCategory(this.calc, \"expenses\");\r\n        const benefits = CalculatorLogic.getTotalForCategory(this.calc, \"benefits\");\r\n        const deductions = CalculatorLogic.getTotalForCategory(this.calc, \"deductions\");\r\n        const isHouseholdDeductible = this.calc.salary.isHouseholdDeductible;\r\n        const unionPaymentType = (this.calc.framework as any).unionPayment;\r\n        return new CalculatorSection(\r\n          isActive,\r\n          ((expenses + benefits > 0) || (deductions > 0) || isHouseholdDeductible || (unionPaymentType && unionPaymentType !== UnionPaymentType.NotSelected)),\r\n          Numeric.toFixed(expenses + benefits, 2) + \" € - \" + Numeric.toFixed(deductions, 2) + \" €\",\r\n        );\r\n      }\r\n      case \"salary\": {\r\n        const allSalary = CalculatorLogic.getTotalForCategory(this.calc, \"salary\");\r\n        const salaryAdditions = CalculatorLogic.getTotalForCategory(this.calc, \"salaryAdditions\");\r\n        return new CalculatorSection(\r\n          isActive,\r\n          allSalary > 0,\r\n          (\r\n            allSalary === 0\r\n              ? \"0 €\"\r\n              : salaryAdditions > 0\r\n                ? Numeric.toFixed(this.calc.result.totals.totalBaseSalary, 2) + \" + \" + Numeric.toFixed(salaryAdditions, 2) + \" €\"\r\n                : Numeric.toFixed(this.calc.result.totals.totalBaseSalary, 2) + \" €\"\r\n          ),\r\n        );\r\n      }\r\n      case \"result\": {\r\n        const isResultsActive = (this.calc.result && this.calc.result.totals &&\r\n          (this.calc.rows.length > 0 || this.calc.result.totals.total !== 0 || this.calc.workflow.status !== CalculationStatus.Draft)) || false;\r\n        return new CalculatorSection(\r\n          isResultsActive,\r\n          isResultsActive,\r\n          Translations.get(\"SALAXY.NG1.CalcComponent.resultSectionCalculation\"),\r\n        );\r\n      }\r\n    }\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {\r\n  Arrays, AvatarPictureType, BootstrapStyle, calcReportType, Calculation, CalculationRowType,\r\n  Calculations, CalculationStatus, CalculatorLogic, Dates, LegalEntityType, PaymentChannel, TaxCard2019Logic, TaxcardUiInfo, TaxDeductionWorkCategories,\r\n  Translations, UserDefinedRow, Ajax,\r\n  AbsenceCauseCode, InvoicesLogic\r\n} from \"@salaxy/core\";\r\n\r\nimport { InvoicesService, ReportsService, SessionService, UiCrudHelpers, UiHelpers } from \"../../services\";\r\nimport { ApiCrudObjectControllerBindings } from \"../bases\";\r\nimport { CalculationCrudController } from \"./CalculationCrudController\";\r\nimport { CalculatorSections } from \"./CalculatorSections\";\r\n\r\n\r\n/** Enumerations for calculator actions */\r\nenum CalculatorActions {\r\n  AllowForcePay = \"allowForcePay\",\r\n  Approve = \"approve\",\r\n  Cancel = \"cancel\",\r\n  CopyAsNew = \"copyAsNew\",\r\n  Delete = \"delete\",\r\n  Pay = \"pay\",\r\n  Recalculate = \"recalculate\",\r\n  Reject = \"reject\",\r\n  Save = \"save\",\r\n  SendToPro = \"sendToPro\",\r\n  ShowPaymentDialog = \"showPaymentDialog\",\r\n  SetSalaryDateKind = \"setSalaryDateKind\",\r\n  ContinuePsdPayment = \"continuePsdPayment\",\r\n}\r\n\r\nclass Calculator2019ControllerCrudBindings extends ApiCrudObjectControllerBindings {\r\n  /** Options for the behavior of the calculator when in anonymous (demo) mode. */\r\n  public anonOptions = \"<\";\r\n}\r\n\r\n\r\n/**\r\n * Year 2019 Calculator controller that is not dependent on sigleton Calculations service.\r\n * This controller extends ApiCrudObjectController (via CalculationCrudController).\r\n */\r\nexport class Calculator2019Controller extends CalculationCrudController {\r\n\r\n  /** Component bindings */\r\n  public static crudBindings = new Calculator2019ControllerCrudBindings();\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Calculations\", \"UiHelpers\", \"UiCrudHelpers\", \"$location\", \"$routeParams\", \"SessionService\", \"ReportsService\", \"InvoicesService\", \"AjaxNg1\"];\r\n\r\n  /** Type of the chart to show by default. */\r\n  public chartType = \"bar\";\r\n\r\n  /** Options for the behavior of the calculator when in anonymous (demo) mode. */\r\n  public anonOptions = {\r\n    role: \"company\" as \"company\" | \"household\",\r\n  };\r\n\r\n\r\n  /** Flags to indicate if the request is in progress */\r\n  public loaders: any = {};\r\n\r\n\r\n  constructor(\r\n    private calcApi: Calculations,\r\n    uiHelpers: UiHelpers,\r\n    protected uiCrudHelpers: UiCrudHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    sessionService: SessionService,\r\n    reportsService: ReportsService,\r\n    protected invoicesService: InvoicesService,\r\n    private ajax: Ajax\r\n  ) {\r\n    // Dependency injection\r\n    super(calcApi, reportsService, uiHelpers, $location, $routeParams, sessionService, invoicesService);\r\n  }\r\n  /**\r\n   * Initialization code.\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Returns the current. Called currentCalc for backward compatibility with the old views. */\r\n  public get currentCalc(): Calculation {\r\n    return this.current;\r\n  }\r\n\r\n  /**\r\n   * Gets the Sections object for the current calculation.\r\n   * It keeps track of which section is currently shown and what text etc. is shown in that section.\r\n   */\r\n  public get calcSections(): CalculatorSections {\r\n    return new CalculatorSections(this.current);\r\n  }\r\n\r\n  /**\r\n   * Gets or sets the isHouseholdDeductible.\r\n   * This will be moved to a different location in V03, hence the abstraction.\r\n   */\r\n  public get isHouseholdDeductible(): boolean {\r\n    if (!this.current) {\r\n      return false;\r\n    }\r\n    return this.current.salary.isHouseholdDeductible;\r\n  }\r\n  public set isHouseholdDeductible(value: boolean) {\r\n    this.current.salary.isHouseholdDeductible = value;\r\n  }\r\n\r\n  /**\r\n   * Gets or sets the taxDeductionCategory (used to be salary.taxDeductionCategories).\r\n   * This will be moved to a different location in V03, hence the abstraction.\r\n   */\r\n  public get taxDeductionCategory(): TaxDeductionWorkCategories {\r\n    return this.current.salary.taxDeductionCategories;\r\n  }\r\n  public set taxDeductionCategory(value: TaxDeductionWorkCategories) {\r\n    this.current.salary.taxDeductionCategories = value;\r\n  }\r\n\r\n  /**\r\n   * Returns true if the calculator is in \"household\" mode (as opposed to default \"company\" mode).\r\n   */\r\n  public get isHousehold() {\r\n    if (this.sessionService.isInRole(\"pro\") && this.sessionService.isInRole(\"person\")) {\r\n      return true; // All person created calaulations are considered pro for now.\r\n    }\r\n    if (this.sessionService.isInRole(\"worker\")) {\r\n      return false; // Uses calculator for companies in old Worker site (to be replaced by Omapalkka)\r\n    }\r\n    if (this.sessionService.isInRole(\"anon\")) {\r\n      if (this.anonOptions && this.anonOptions.role === \"household\") {\r\n        return true;\r\n      }\r\n      return false;\r\n    }\r\n    return this.sessionService.isInRole(\"household\");\r\n  }\r\n\r\n\r\n  /**\r\n   * If true, the given action (button) is displayed.\r\n   * @param action One of the action values.\r\n   * For now, validation and role based action logic is in UI.\r\n   * Todo: some edge cases, i.e. isForcePayAllAllowed (for pay-button) are still in UI.\r\n   */\r\n  public showAction(action: CalculatorActions): boolean {\r\n    if (!this.current) {\r\n      return false;\r\n    }\r\n    // In read only mode\r\n    if (this.isReadOnlyForced && action != CalculatorActions.ShowPaymentDialog) {\r\n      return false;\r\n    }\r\n    if (this.isReadOnlyForced && action == CalculatorActions.ShowPaymentDialog) {\r\n      return true;\r\n    }\r\n    if (this.current.workflow.status == CalculationStatus.PayrollDraft) {\r\n      // Not possible to make changes to editable payroll calculation\r\n      return false;\r\n    }\r\n    if (this.current.isReadOnly) {\r\n      switch (action) {\r\n        case CalculatorActions.Cancel:\r\n          return this.current.workflow.status == CalculationStatus.PaymentStarted &&\r\n            (\r\n              [\r\n                PaymentChannel.PalkkausManual,\r\n              PaymentChannel.TalenomManual,\r\n                PaymentChannel.PalkkausPersonal,\r\n                PaymentChannel.PalkkausInvoices\r\n              ].indexOf(this.current.info.paymentChannel) > -1 ||\r\n              (\r\n                InvoicesLogic.isCfa(this.current.info.paymentChannel) &&\r\n                !this.current.info.payrollId\r\n              )\r\n            );\r\n        case CalculatorActions.CopyAsNew:\r\n          return !this.isReadOnlyForced; // Not needed?\r\n        case CalculatorActions.ShowPaymentDialog:\r\n          return true;\r\n        case CalculatorActions.ContinuePsdPayment:\r\n          return this.current.info.paymentChannel == PaymentChannel.PalkkausPSD && this.current.workflow.status == CalculationStatus.PaymentStarted;\r\n        case CalculatorActions.AllowForcePay: // \"Allow forcepay\" action is payment action when calculation is not valid. Logic handled in UI for now.\r\n        case CalculatorActions.Pay:\r\n        case CalculatorActions.Recalculate:\r\n        default:\r\n          return false;\r\n      }\r\n    } else {\r\n      switch (action) {\r\n        case CalculatorActions.AllowForcePay:\r\n          //TODO: refactor this to contain only allowed status, not disallowed\r\n          return this.isForcePayAllAllowed &&\r\n            (this.current.workflow.status != CalculationStatus.WaitingApproval &&\r\n              this.current.workflow.status != CalculationStatus.SharedRejected &&\r\n              this.current.workflow.status != CalculationStatus.SharedWaiting &&\r\n              this.current.workflow.status != CalculationStatus.Repair\r\n            );\r\n        case CalculatorActions.Pay:\r\n          // add here isValid?\r\n          return this.current.workflow.status == CalculationStatus.Draft ||\r\n            this.current.workflow.status == CalculationStatus.ProDraft ||\r\n            this.current.workflow.status == CalculationStatus.SharedApproved;\r\n        case CalculatorActions.Save:\r\n          return this.current.workflow.status == CalculationStatus.Draft ||\r\n            this.current.workflow.status == CalculationStatus.ProDraft ||\r\n            this.current.workflow.status == CalculationStatus.SharedApproved ||\r\n            this.current.workflow.status == CalculationStatus.History ||\r\n            this.current.workflow.status == CalculationStatus.Repair;\r\n        case CalculatorActions.Delete:\r\n          return this.current.workflow.status == CalculationStatus.Draft ||\r\n            this.current.workflow.status == CalculationStatus.ProDraft ||\r\n            this.current.workflow.status == CalculationStatus.SharedRejected ||\r\n            this.current.workflow.status == CalculationStatus.History ||\r\n            this.current.workflow.status == CalculationStatus.Repair;\r\n        case CalculatorActions.SendToPro:\r\n          return this.current.workflow.status == CalculationStatus.WaitingApproval;\r\n        case CalculatorActions.Recalculate:\r\n          return true;\r\n        case CalculatorActions.Reject:\r\n          return this.current.workflow.status == CalculationStatus.SharedApproved ||\r\n            this.current.workflow.status == CalculationStatus.SharedWaiting;\r\n        case CalculatorActions.Approve:\r\n          return this.current.workflow.status == CalculationStatus.SharedRejected ||\r\n            this.current.workflow.status == CalculationStatus.SharedWaiting;\r\n        case CalculatorActions.SetSalaryDateKind:\r\n          return (this.current.workflow.status == CalculationStatus.Draft ||\r\n            this.current.workflow.status == CalculationStatus.ProDraft ||\r\n            this.current.workflow.status == CalculationStatus.SharedApproved) &&\r\n            (\r\n              InvoicesLogic.isPalkkausManualLike(this.current.info.paymentChannel) ||\r\n              InvoicesLogic.isPalkkausInvoicesLike(this.current.info.paymentChannel) ||\r\n              this.current.info.paymentChannel == PaymentChannel.PalkkausCfaTest ||\r\n              this.current.info.paymentChannel == PaymentChannel.Briox ||\r\n              this.current.info.paymentChannel == PaymentChannel.Askelma ||\r\n              this.current.info.paymentChannel == PaymentChannel.PasseliMerit ||\r\n              this.current.info.paymentChannel == PaymentChannel.Ecom ||\r\n              this.current.info.paymentChannel == PaymentChannel.Hausvise\r\n            );\r\n        default:\r\n          return false;\r\n      }\r\n    }\r\n\r\n  }\r\n\r\n  /**\r\n   * Returns true, if action (button) is disabled\r\n   * TODO: Add rules based on roles and validation? Pay button logic is in UI.\r\n   */\r\n  public isActionDisabled(action: CalculatorActions): boolean {\r\n    if (!this.current) {\r\n      return true;\r\n    }\r\n    // In read only mode\r\n    if (this.isReadOnlyForced) {\r\n      return true;\r\n    }\r\n\r\n    if (this.current.isReadOnly) {\r\n      switch (action) {\r\n        case CalculatorActions.Delete:\r\n          return this.current.workflow.status == CalculationStatus.PaymentStarted;\r\n        case CalculatorActions.Save:\r\n          // add here isValid?\r\n          return this.current.workflow.status == CalculationStatus.PaymentStarted;\r\n        default:\r\n          return true;\r\n      }\r\n    }\r\n  }\r\n  /**\r\n   * Gets the first row of the calculation assuring that it exists\r\n   * If there is no current calculation, the calculation is not added.\r\n   */\r\n  public getFirstRow(): UserDefinedRow {\r\n    return CalculatorLogic.getFirstRow(this.current);\r\n  }\r\n\r\n  /**\r\n   * Takes the current calculation, creates a copy of it in draft state\r\n   * and sets that calculation as current.\r\n   * This is done typically, when a calculation was in Paid state.\r\n   */\r\n  public copyAsNew() {\r\n    const copy = this.copyItem(this.current);\r\n    this.calcApi.recalculate(copy).then((calc) => {\r\n      this.setCurrentRef(calc);\r\n      if ((this as any)?.worktimeCtrl) {\r\n        (this as any).worktimeCtrl.reset();\r\n      }\r\n      else if ((this.parentController as any)?.worktimeCtrl) {\r\n        (this.parentController as any).worktimeCtrl.reset();\r\n      }\r\n      this.calcSections.setActive(\"worktime\");\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Reset worker in the calculations.\r\n   */\r\n  public resetWorker() {\r\n    this.currentCalc.worker = CalculatorLogic.getBlank().worker;\r\n  }\r\n\r\n  /**\r\n   * Gets misc. logic calculations and operations (client side, based on rows etc.)\r\n   * that affect how the user interface is rendered.\r\n   */\r\n  public get calcLogic() {\r\n    if (!this.current) {\r\n      return {};\r\n    }\r\n    const workerCalc = ((this.current.result || {}).workerCalc || {});\r\n    return {\r\n      /** If true, calcualtion contains compensation. This is useful for customizing texts and other UI elements */\r\n      hasCompensation: !!this.current.rows.find((x) => x.rowType === CalculationRowType.Compensation),\r\n      /** Expenses box total. TODO: We should see can we move this to result / server side! */\r\n      expensesTotal: workerCalc.prepaidExpenses + workerCalc.deductions - workerCalc.unemploymentInsurance - workerCalc.pension - workerCalc.tax,\r\n\r\n      /** Sum for child care subsidy. This is shown separately in the UI. */\r\n      childCareSubsidy: (this.current.result && this.current.result.rows) ? Arrays.sum(this.current.result.rows.filter((x) => x.rowType === CalculationRowType.ChildCareSubsidy), (x) => x.total) : null,\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Opens the login form for the current user\r\n   * @param redirectUrl - The URL where the user is taken after a successfull login.\r\n   * @param role - Optional role (household, worker or company) for the situations where it is known - mainly for new users\r\n   */\r\n  public signIn(redirectUrl: string = null, role: string = null) {\r\n    this.sessionService.signIn(redirectUrl, role);\r\n  }\r\n\r\n  /**\r\n   * Opens the login dialog with signUp / register functionality\r\n   * @param redirectUrl - The URL where the user is taken after a successfull login\r\n   * @param role - Optional role (household, worker or company) for the situations where it is known - mainly for new users\r\n   */\r\n  public register(redirectUrl: string = null, role: string = null) {\r\n    this.sessionService.register(redirectUrl, role);\r\n  }\r\n\r\n  /**\r\n   * Shows a report for the current calculation using a modal dialog.\r\n   * @param reportType - Type of report to show\r\n   */\r\n  public showReportDialog(reportType: calcReportType) {\r\n    this.reportsService.showReportModalForCalc(reportType, this.current);\r\n  }\r\n\r\n  /**\r\n   * Deletes the currently selected calculation\r\n   */\r\n  public deleteCalc(path: string) {\r\n    this.uiHelpers.showConfirm(\"SALAXY.NG1.CalcComponent.dialog.deleteCalc\")\r\n      .then((result: boolean) => {\r\n        if (result) {\r\n          if(this.isNew()){\r\n            this.$location.path(path || \"/\");\r\n          } else {\r\n            const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n            this.deleteNoConfirm(this.current).then(() => {\r\n            this.setCurrentRef(this.api.getBlank());\r\n            loading.dismiss();\r\n            this.$location.path(path || \"/\");\r\n          });\r\n          }\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Recalculates the current calculation using the API.\r\n   * @returns A Promise with result data (Calculation)\r\n   */\r\n  public recalculate(): Promise<Calculation> {\r\n    // Sets the accounts before recalculate and not after in setCurrent.\r\n    if (this.sessionService.isInRole(\"worker\")) {\r\n      this.current.worker.isSelf = true;\r\n    } else {\r\n      this.current.employer.isSelf = true;\r\n    }\r\n    return this.calcApi.recalculate(this.current).then((calc) => {\r\n      // TODO: Check that the spinner works here. Also remove unnecessary spinners in other places.\r\n      super.setCurrentValue(calc);\r\n      return calc;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Sets the current item as the given object (reference to a new object).\r\n   * This also resets the original item and sets the state as loaded.\r\n   * Override also sets either employer or worker based on the current role.\r\n   * @param item The new current item.\r\n   */\r\n  public setCurrentRef(item: Calculation) {\r\n    if (item) {\r\n      if (this.sessionService.isInRole(\"worker\")) {\r\n        item.worker.isSelf = true;\r\n      } else {\r\n        item.employer.isSelf = true;\r\n      }\r\n    }\r\n    super.setCurrentRef(item);\r\n  }\r\n\r\n  /** Overrides the save method to allow anonymous saving to local storage */\r\n  public save() {\r\n    /** Not sure whether the local storage saving is enabled anywhere? */\r\n    if (!this.sessionService.isAuthenticated) {\r\n      this.current.id = \"anon\";\r\n      return this.recalculate().then(() => {\r\n        this.current.worker.accountId = \"anon\";\r\n        this.current.worker.avatar.id = this.current.worker.accountId;\r\n        this.current.worker.avatar.color = \"lime\";\r\n        this.current.worker.avatar.displayName = \"SALAXY.NG1.CalcComponent.saveNotAuthenticatedDisplayName\";\r\n        this.current.worker.avatar.entityType = LegalEntityType.Person;\r\n        this.current.worker.avatar.pictureType = AvatarPictureType.Icon;\r\n        this.setToLocalStorage(this.current);\r\n        return this.current;\r\n      });\r\n    } else {\r\n      if (this.current.worker.accountId === \"anon\") {\r\n        this.current.worker.accountId = null;\r\n      }\r\n      if (!this.current.worker.accountId) {\r\n        this.deleteFromLocalStorage();\r\n      }\r\n      if (this.current.id === \"anon\") {\r\n        this.current.id = null;\r\n      }\r\n      return super.save();\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Returns validation for current calculation or empty validation object if the calculation has not been recalculated (validated).\r\n   */\r\n  public get validation() {\r\n    return this.currentCalc?.result?.validation || { errors: [], hasAllRequiredFields: true, isValid: true };\r\n  }\r\n\r\n  /** Returns date range text. */\r\n  public getDatesRangeText() {\r\n    if (!this.currentCalc.info.workStartDate || !this.currentCalc.info.workEndDate) {\r\n      return \"SALAXY.NG1.CalcComponent.getDatesRangeText\";\r\n    }\r\n    return Dates.getFormattedRange(this.currentCalc.info.workStartDate, this.currentCalc.info.workEndDate)\r\n      + ` (${this.currentCalc.framework.numberOfDays}\\xa0${Translations.get(\"SALAXY.NG1.CalcComponent.getUsecaseTextNumberOfDays\")})`; // \"\\xa0\" is non-breaking space.\r\n  }\r\n\r\n  /** Returns household usecase text */\r\n  public getUsecaseText() {\r\n    if (!this.currentCalc.usecase && !this.currentCalc.framework.numberOfDays) {\r\n      return \"SALAXY.NG1.CalcComponent.getUsecaseText\";\r\n    }\r\n    if (this.currentCalc.usecase && !this.currentCalc.framework.numberOfDays) {\r\n      return ` ${this.currentCalc.usecase.label}.` + Translations.get(\"SALAXY.NG1.CalcComponent.getUsecaseText2\");\r\n    }\r\n    return Dates.getFormattedRange(this.currentCalc.info.workStartDate, this.currentCalc.info.workEndDate)\r\n      + ` (${this.currentCalc.framework.numberOfDays} ${Translations.get(\"SALAXY.NG1.CalcComponent.getUsecaseTextNumberOfDays\")}, ${this.currentCalc.usecase.label})`;\r\n  }\r\n\r\n  /** Returns true if the payment is possible when the employer pays all.  */\r\n  public get isForcePayAllAllowed(): boolean {\r\n    const obj = this.validation.errors.find((x) =>\r\n      (x.type !== \"warning\"));\r\n    return !obj;\r\n  }\r\n\r\n  /**\r\n   * Shows a dialog for adding a new Employment relation.\r\n   * If user goes through the wizard the employment relation is saved and set to the calculation.\r\n   */\r\n  public showNewWorkerDialog() {\r\n    this.uiCrudHelpers.createNewEmployment().then((result) => {\r\n      if (result.action === \"ok\") {\r\n        this.updateFromEmployment(result.item.id, true);\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shows a dialog during the check of auto taxcard.\r\n   */\r\n  public showRefreshAutoTaxcardDialog() {\r\n    this.loaders[\"showRefreshAutoTaxcardDialog\"] = true;\r\n    this.uiCrudHelpers.refreshAutoTaxcard(this.current.worker.tax?.taxcardId, this.current.workflow?.salaryDate).then(() => {\r\n      this.recalculate();\r\n      this.loaders[\"showRefreshAutoTaxcardDialog\"] = false;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shows a dialog for modifying an existing Worker:\r\n   * Saves changes and updates the calculation.\r\n   */\r\n  public showWorkerEditDialog() {\r\n    this.uiCrudHelpers.openEditEmploymentDialog(this.current.worker.employmentId, \"updateCalc\")\r\n      .then((result) => {\r\n        if (result.action === \"ok\" || result.action === \"ok-no-rows\") {\r\n          const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.CalcComponent.dialog.showWorkerEditDialogLoading\");\r\n          this.updateFromEmployment(result.item.id, result.action === \"ok\").then(() => {\r\n            loader.dismiss();\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n  /** UI related data and texts about the taxcard. */\r\n  public get taxUi(): TaxcardUiInfo {\r\n    return TaxCard2019Logic.getCalcTaxcardInfo(this.current);\r\n  }\r\n\r\n  /**\r\n   * Gets the text for pension.\r\n   * @param isOverview If true, returns the shorter text for overview.\r\n   */\r\n  public getPensionText(isOverview = false) {\r\n    if (this.current?.result?.responsibilities?.pensionCalculation) {\r\n      return Translations.get(`SALAXY.ENUM.PensionCalculation.${this.current.result.responsibilities.pensionCalculation}.${isOverview ? \"labelForIncome\" : \"labelWithEnumLabel\"}`);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Sends the payroll from company to PRO.\r\n   * @param message Message to the accountant\r\n   */\r\n  public sendToPro(message: string) {\r\n    const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.CalcComponent.dialog.sendToProSending\", \"SALAXY.NG1.CalcComponent.dialog.sendToProSendingDescr\");\r\n    this.current.workflow.status = CalculationStatus.ProDraft;\r\n    this.save().then(() => {\r\n\r\n      this.api.saveWorkflowEvent(this.current, {\r\n        type: \"PartnerMessageClosed\",\r\n        ui: BootstrapStyle.Success,\r\n        message: message ? Translations.get(\"SALAXY.NG1.CalcComponent.dialog.sendToProMessage\") + message : Translations.get(\"SALAXY.NG1.CalcComponent.dialog.sendToProMessageChecked\"),\r\n      }).then(() => {\r\n        loader.dismiss();\r\n        this.$location.path(\"/service\");\r\n      });\r\n    });\r\n    return;\r\n  }\r\n\r\n  /**\r\n   * Calculates the total amount of days for the given period type.\r\n   * @param periodType Period type to calculate days for.\r\n   * @returns Sum of days for the given period type.\r\n   */\r\n  public calculatePeriodDays(periodType: \"absencesDays\"  | \"leavesDays\" | \"paidAbsencesDays\") {\r\n    switch (periodType) {\r\n      case \"leavesDays\":\r\n        return Arrays.sum(this.currentCalc.worktime?.absencesPeriods?.filter(x => x.causeCode == AbsenceCauseCode.AnnualLeave) ?? [], (x) => x.period.daysCount);\r\n      case \"absencesDays\":\r\n        return Arrays.sum(this.currentCalc.worktime?.absencesPeriods?.filter(x => x.causeCode != AbsenceCauseCode.AnnualLeave && !x.isPaid) ?? [], (x) => x.period.daysCount);\r\n      case \"paidAbsencesDays\":\r\n        return Arrays.sum(this.currentCalc.worktime?.absencesPeriods?.filter(x => x.causeCode != AbsenceCauseCode.AnnualLeave && x.isPaid) ?? [], (x) => x.period.daysCount);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Saves a calculation to local storage\r\n   * @param calc - Calculation to store\r\n   */\r\n  private setToLocalStorage(calc: any): void {\r\n    if (window.localStorage) {\r\n      window.localStorage.setItem(\"salaxy-calculation\", JSON.stringify(calc));\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Deletes a calculation in local storage\r\n   */\r\n  private deleteFromLocalStorage(): void {\r\n    if (window.localStorage) {\r\n      window.localStorage.removeItem(\"salaxy-calculation\");\r\n    }\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {\r\n  Calculations, IncomeTypeMetadata, IncomeTypesLogic, IrRow, IrRowSourceType, Unit, Translations, Ajax\r\n} from \"@salaxy/core\";\r\n\r\nimport {\r\n  InvoicesService,\r\n  ReportsService,\r\n  SessionService,\r\n  UiCrudHelpers,\r\n  UiHelpers,\r\n} from \"../../services\";\r\n\r\nimport { Calculator2019Controller } from \"./Calculator2019Controller\";\r\n\r\n/**\r\n * IR-rows based editor for calculation\r\n */\r\nexport class CalcIrRowsController extends Calculator2019Controller {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Calculations\", \"UiHelpers\", \"UiCrudHelpers\", \"$location\", \"$routeParams\", \"SessionService\", \"ReportsService\", \"InvoicesService\", \"AjaxNg1\"];\r\n\r\n  /**\r\n   * Translated enums\r\n   */\r\n  public groupingOptions: any = {\r\n    baseSalary: Translations.get(\"SALAXY.NG1.CalcRowsComponent.irRows.baseSalary\"),\r\n    benefits: Translations.get(\"SALAXY.NG1.CalcRowsComponent.irRows.benefits\"),\r\n    deductions: Translations.get(\"SALAXY.NG1.CalcRowsComponent.irRows.deductions\"),\r\n    disabled: Translations.get(\"SALAXY.NG1.CalcRowsComponent.irRows.disabled\"),\r\n    expenses: Translations.get(\"SALAXY.NG1.CalcRowsComponent.irRows.expenses\"),\r\n    otherNoPayment: Translations.get(\"SALAXY.NG1.CalcRowsComponent.irRows.otherNoPayment\"),\r\n    salaryAdditions: Translations.get(\"SALAXY.NG1.CalcRowsComponent.irRows.salaryAdditions\"),\r\n    totals: Translations.get(\"SALAXY.NG1.CalcRowsComponent.irRows.totals\"),\r\n  };\r\n\r\n  /**\r\n   * Active tab of editor\r\n   */\r\n  protected activeTab = 1;\r\n\r\n  private _currentRow: IrRow;\r\n\r\n  /**\r\n   * Creates a new instance of the controller with dependency injection.\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    calcApi: Calculations,\r\n    uiHelpers: UiHelpers,\r\n    uiCrudHelpers: UiCrudHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    sessionService: SessionService,\r\n    reportsService: ReportsService,\r\n    protected invoicesService: InvoicesService,\r\n    ajax: Ajax,\r\n  ) {\r\n    super(calcApi, uiHelpers, uiCrudHelpers, $location, $routeParams, sessionService, reportsService, invoicesService, ajax);\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /** The current row that is being viewed / edited. */\r\n  public get currentRow(): IrRow {\r\n    if (!this._currentRow || !this.currentCalc.result || !this.currentCalc.result.irRows) {\r\n      return null;\r\n    }\r\n    if (!this.currentCalc.result.irRows.find((x) => x === this._currentRow)) {\r\n      // Recalculation outside this controller has destroyed the current row.\r\n      this._currentRow = null;\r\n    }\r\n    return this._currentRow;\r\n  }\r\n\r\n  /** The metadata that describes currentRow */\r\n  public get currentRowType(): IncomeTypeMetadata {\r\n    return this.getIncomeType(this.currentRow);\r\n  }\r\n\r\n  /** IR-rows that are viewed / edited by the controller */\r\n  public get irRows(): IrRow[] {\r\n    if (!this.currentCalc || !this.currentCalc.result) {\r\n      return [];\r\n    }\r\n    return this.currentCalc.result.irRows;\r\n  }\r\n\r\n  /** Sets the current edited / viewd row */\r\n  public setCurrentIrRow(row: IrRow) {\r\n    this._currentRow = row;\r\n  }\r\n\r\n  /** Deletes a row */\r\n  public deleteIrRow(row: any) {\r\n    this.irRows.splice(this.irRows.indexOf(row), 1);\r\n  }\r\n\r\n  /** Returns true if the row is read-only: Cannot be directly edited. */\r\n  public get isIrRowReadOnly() {\r\n    return this.currentRow == null || this.currentRow.type !== \"manual\";\r\n  }\r\n\r\n  /** Updates the current row type. */\r\n  public updateCurrentRowType() {\r\n    if (this.currentRowType) {\r\n      if (!this.currentRow.message || IncomeTypesLogic.getAll().find((x) => x.label === this.currentRow.message)) {\r\n        this.currentRow.message = this.currentRowType.label;\r\n      }\r\n    }\r\n  }\r\n\r\n  /** Gets the income type (the metadata) object for the currently selected row. */\r\n  public getIncomeType(row: any): IncomeTypeMetadata {\r\n    return IncomeTypesLogic.getAll().find((x) => x.code === row.irData.code);\r\n  }\r\n\r\n  /** Adds a new IR row to the collection. */\r\n  public addIrRow() {\r\n    const row: IrRow = {\r\n      type: IrRowSourceType.Manual,\r\n      irData: {\r\n        code: null,\r\n      },\r\n      count: 1,\r\n      unit: Unit.Undefined,\r\n      price: 0,\r\n    };\r\n    this.irRows.push(row);\r\n    this.setCurrentIrRow(row as any);\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {\r\n  Ajax,\r\n  Calculation,\r\n  Language,\r\n  Numeric,\r\n  calcReportType,\r\n  ReportType,\r\n  Translations,\r\n  Reports,\r\n  Objects\r\n} from \"@salaxy/core\";\r\nimport { SessionService, SettingsService, UiHelpers } from \"../../services\";\r\nimport {\r\n  CalculationMapper,\r\n  CalculationReport,\r\n  ESalaryMapper,\r\n  ReportData,\r\n  ReportOptions,\r\n  Templates,\r\n  TotalsReportConfigGenerator\r\n} from \"@salaxy/reports\";\r\nimport { ColumnDefinition } from \"tabulator-tables\";\r\nimport { SxyTableOptions, SxyTableController } from \"../sxy-table/SxyTableController\";\r\n\r\n/**\r\n * Renders a calculation report or a calculation summary report for the given calculation(s).\r\n * Uses Handlebars templates (@salaxy/reports).\r\n */\r\nexport class CalcReportController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"Templates\",\r\n    \"AjaxNg1\",\r\n    \"$sce\",\r\n    \"SettingsService\",\r\n    \"$timeout\",\r\n    \"SessionService\",\r\n    \"Reports\",\r\n    \"UiHelpers\",\r\n  ];\r\n\r\n  /** The calculation(s) for the report. Todo add Calcs*/\r\n  public calc: Calculation | Calculation[];\r\n\r\n  /** Template for the report */\r\n  public templateName: string;\r\n\r\n  /** Boolean indicating if the refresh is in progress. */\r\n  public refreshInprogress: boolean;\r\n\r\n  /**Selected report language */\r\n  public lang: Language;\r\n\r\n  /** If true, adds the preview watermark to the preview. */\r\n  public preview?: boolean;\r\n\r\n  /**\r\n   * Function that is called when the report type has been changed\r\n   * Function has the following locals:  reportType: the selected report type.\r\n   */\r\n  public onReportTypeChange: (params: {\r\n    /** Selected reportType */\r\n    reportType: ReportType | calcReportType,\r\n  }) => void;\r\n\r\n  /** Ref to used SxyTable */\r\n  public $sxyTable: SxyTableController;\r\n\r\n  /** The type for the calculation report. */\r\n  private _reportType: ReportType | calcReportType;\r\n\r\n  private renderedCalc: Calculation | Calculation[];\r\n\r\n  private renderedOptions: string;\r\n\r\n  private renderedLang: string;\r\n\r\n  private htmlData: any;\r\n\r\n  private reportOptions: ReportOptions;\r\n\r\n  private reportData: ReportData<CalculationReport> = {\r\n    headerFooter: {},\r\n    layout: {},\r\n    report: {},\r\n  };\r\n  private isXslLoading: boolean;\r\n  private xslText: string;\r\n\r\n  private sxyTableConfig: { currentCalc: Calculation | Calculation[], reportLang: Language, config: { options: SxyTableOptions, include: ColumnDefinition[], data: any[] } } = {\r\n    currentCalc: null,\r\n    reportLang: Language.Default,\r\n    config: null\r\n  };\r\n\r\n  /**\r\n   * Creates a new CalcReportController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    private templates: Templates,\r\n    private ajax: Ajax,\r\n    private $sce: angular.ISCEService,\r\n    private settingsService: SettingsService,\r\n    private $timeout: angular.ITimeoutService,\r\n\r\n    private sessionService: SessionService,\r\n    private reportsApi: Reports,\r\n\r\n    private uiHelpers: UiHelpers\r\n  ) {\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    // no initializations\r\n  }\r\n\r\n  /** The type for the calculation report. */\r\n  public get reportType(): ReportType | calcReportType {\r\n    return this._reportType;\r\n  }\r\n\r\n  /** The type for the calculation report. */\r\n  public set reportType(value: ReportType | calcReportType) {\r\n    if (value != this._reportType) {\r\n      this._reportType = value;\r\n      if (this.onReportTypeChange) {\r\n        this.onReportTypeChange({ reportType: value });\r\n      }\r\n    }\r\n  }\r\n\r\n  /** Bindable and trusted html. */\r\n  public get html(): any {\r\n    if (!this.calc) {\r\n      this.renderedCalc = null;\r\n      this.renderedOptions = null;\r\n      this.renderedLang = null;\r\n    } else {\r\n      const calc = angular.copy(this.calc);\r\n\r\n      if (!this.renderedCalc ||\r\n        !angular.equals(calc, this.renderedCalc) ||\r\n        this.renderedOptions !== this.reportType + \";\" + this.templateName ||\r\n        this.renderedLang !== this.lang) {\r\n        this.renderedCalc = angular.copy(calc);\r\n        this.renderedOptions = this.reportType + \";\" + this.templateName;\r\n        this.renderedLang = this.lang;\r\n        this.getDefaultLanguage(this.lang).then((lang) => {\r\n          this.lang = lang;\r\n          this.renderedLang = this.lang;\r\n          // Refresh html reports\r\n          if (this.reportType !== ReportType.ESalarySpecification) {\r\n            this.refresh();\r\n          }\r\n          // Refresh eSalary xml\r\n          if (this.reportType === ReportType.ESalarySpecification && !this.isXslLoading) {\r\n            this.isXslLoading = true;\r\n            if (!this.xslText) {\r\n              fetch(`https://cdn.salaxy.com/reports/PayslipCommon20.xsl`)\r\n                .then(response => response.text())\r\n                .then(text => {\r\n                  this.xslText = text;\r\n                  this.refreshESalaryXml();\r\n                });\r\n            } else {\r\n              this.refreshESalaryXml();\r\n            }\r\n          }\r\n          return;\r\n        });\r\n      }\r\n    }\r\n    return this.htmlData;\r\n  }\r\n\r\n  /**\r\n   * Config for SxyTable\r\n   */\r\n  public get tableConfig(): { options: SxyTableOptions, include: ColumnDefinition[], data: any[] } {\r\n    if (!this.calc) {\r\n      this.sxyTableConfig = {\r\n        currentCalc: null,\r\n        reportLang: null,\r\n        config: null\r\n      };\r\n    } else {\r\n      const calcs = angular.copy(this.calc);\r\n      if (!Objects.equal(this.sxyTableConfig.currentCalc, calcs) || this.lang !== this.sxyTableConfig.reportLang) {\r\n        this.sxyTableConfig.currentCalc = calcs;\r\n        this.sxyTableConfig.reportLang = this.lang;\r\n        this.getDefaultLanguage(this.lang).then((lang) => {\r\n          this.lang = lang;\r\n          this.renderedLang = this.lang;\r\n          this.refreshTableConfig();\r\n        });\r\n      }\r\n    }\r\n    return this.sxyTableConfig.config;\r\n  }\r\n\r\n  /**\r\n   * Method used to refresh table config\r\n   */\r\n  public async refreshTableConfig() {\r\n    const renderingLang = this.lang ?? Language.Fi;\r\n    await Translations.loadLanguage(renderingLang);\r\n    this.sxyTableConfig.config = TotalsReportConfigGenerator.getConfig(this.calc, renderingLang);\r\n    await this.$timeout();\r\n    this.$sxyTable.refresh();\r\n  }\r\n\r\n  private async refreshESalaryXml() {\r\n    const calc = await this.resolveCumulativeCalculation(Array.isArray(this.calc) ? this.calc[0] : this.calc);\r\n    const xml = this.templates.getHtml(\"eSalary\", ESalaryMapper.getESalary(calc), this.lang ?? Language.Fi);\r\n    const xsltProcessor = new XSLTProcessor();\r\n    const xslDoc = new window.DOMParser().parseFromString(this.xslText, \"text/xml\");\r\n    const xmlDoc = new window.DOMParser().parseFromString(xml, \"text/xml\");\r\n    xsltProcessor.importStylesheet(xslDoc);\r\n    const resultDocument = xsltProcessor.transformToDocument(xmlDoc);\r\n    this.htmlData = this.$sce.trustAsHtml(resultDocument.documentElement.innerHTML);\r\n    this.isXslLoading = false;\r\n    this.$timeout();\r\n  }\r\n\r\n  private async resolveCumulativeCalculation(calc: Calculation): Promise<Calculation> {\r\n    if (calc.id) {\r\n      calc = angular.copy(calc);\r\n      const cumulativeCalc = await this.reportsApi.getCumulativeCalculation(calc.id);\r\n      (calc as any).cumulative = cumulativeCalc.cumulative;\r\n      return Promise.resolve(calc);\r\n    }\r\n    return Promise.resolve(calc);\r\n  }\r\n\r\n  /**\r\n   * Refresh calculation report data.\r\n   */\r\n  private async refresh() {\r\n    if (this.refreshInprogress) {\r\n      return;\r\n    }\r\n    this.refreshInprogress = true;\r\n    this.settingsService.getReportOptions().then(async (options) => {\r\n      this.reportOptions = options;\r\n      const renderingLang = this.lang ?? Language.Fi;\r\n      await Translations.loadLanguage(renderingLang);\r\n      if (Array.isArray(this.calc)) {\r\n        this.reportData.report = CalculationMapper.getCalculationSummaryReport(this.calc, renderingLang);\r\n        this.reportData.headerFooter = CalculationMapper.getCalculationSummaryReportHeaderFooter(this.calc, this.reportOptions, renderingLang);\r\n      } else {\r\n        this.reportData.report = CalculationMapper.getCalculationReport(this.calc, this.reportType as ReportType, renderingLang);\r\n        this.reportData.headerFooter = CalculationMapper.getHeaderFooter(this.reportType as ReportType, this.calc, this.reportOptions, renderingLang);\r\n      }\r\n      const reportOptions = this.getDefaultReportOptions(angular.copy(this.reportOptions));\r\n      this.reportData.layout = CalculationMapper.getReportLayout(false, false, this.preview ? \"default\" : undefined);\r\n      // Special case (simple report), no mapper needed\r\n      if (this.reportType === ReportType.TotalsReport) {\r\n        this.reportData.report = Array.isArray(this.calc) ? this.calc as CalculationReport : [this.calc] as CalculationReport;\r\n        this.reportData.headerFooter = CalculationMapper.getTotalReportHeaderFooter(Array.isArray(this.calc) ? this.calc[0] : this.calc, this.reportOptions, renderingLang);\r\n        this.reportData.layout = CalculationMapper.getReportLayout(true, false, this.preview ? \"default\" : undefined);\r\n      }\r\n      const css = \"\";\r\n      this.reportData.layout.hasCustomCss = false;\r\n      this.reportData.layout.customCss = (css || \"\");\r\n      if (this.preview) {\r\n        this.reportData.layout.isPreview = true;\r\n      }\r\n      this.reportData.layout.margin = {\r\n        top: reportOptions.margin.top,\r\n        right: reportOptions.margin.right,\r\n        bottom: reportOptions.margin.bottom,\r\n        left: reportOptions.margin.left\r\n      };\r\n      const templates = new Templates();\r\n      this.reportData.headerHtml = this.reportOptions?.headerTemplate ? templates.getHtmlDynamic(this.reportOptions.headerTemplate, this.reportData.headerFooter, renderingLang) : \"\";\r\n      this.reportData.footerHtml = this.reportOptions?.headerTemplate ? templates.getHtmlDynamic(this.reportOptions.footerTemplate, this.reportData.headerFooter, renderingLang) : \"\";\r\n      this.htmlData = this.$sce.trustAsHtml(this.templates.getHtml(this.templateName, this.reportData, renderingLang));\r\n      this.refreshInprogress = false;\r\n      this.$timeout();\r\n    });\r\n\r\n  }\r\n\r\n  private getDefaultReportOptions(optionsInput?: ReportOptions): ReportOptions {\r\n    optionsInput = optionsInput || {};\r\n    optionsInput.margin = optionsInput.margin || {};\r\n    optionsInput.margin.top = Numeric.parseNumber(optionsInput.margin.top) || 30;\r\n    optionsInput.margin.right = Numeric.parseNumber(optionsInput.margin.right) || 10;\r\n    optionsInput.margin.bottom = Numeric.parseNumber(optionsInput.margin.bottom) || 40;\r\n    optionsInput.margin.left = Numeric.parseNumber(optionsInput.margin.left) || 10;\r\n    return optionsInput;\r\n  }\r\n\r\n  private async getDefaultLanguage(lang: Language): Promise<Language> {\r\n    if (!lang) {\r\n      return this.sessionService.getReportLang();\r\n    }\r\n    return Promise.resolve(lang);\r\n  }\r\n\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {\r\n  Ajax,\r\n  calcReportType,\r\n  Calculation,\r\n  Calculations,\r\n  Language,\r\n  Reports,\r\n  ReportType,\r\n  Objects,\r\n  Translations,\r\n  Texts,\r\n  Dates,\r\n  irepr,\r\n} from \"@salaxy/core\";\r\nimport { CostCenterReportConfigGenerator, IrRowsReportConfigGenerator, RowsReportConfigGenerator, TotalsReportConfigGenerator } from \"@salaxy/reports\";\r\nimport { ColumnDefinition } from \"tabulator-tables\";\r\nimport { SxyTableController, SxyTableOptions } from \"../sxy-table/SxyTableController\";\r\nimport {\r\n  SessionService,\r\n  UiHelpers,\r\n  ExcelHelpers\r\n} from \"../../services\";\r\nimport { CalcReportController } from \"./CalcReportController\";\r\nimport { CalcsIrRowsController } from \"./CalcsIrRowsController\";\r\n\r\n/**\r\n * Displays the reports for the given calculations.\r\n */\r\nexport class CalcReportsController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"AjaxNg1\",\r\n    \"UiHelpers\",\r\n    \"SessionService\",\r\n    \"$timeout\",\r\n    \"$http\",\r\n    \"Reports\",\r\n    \"Calculations\"\r\n  ];\r\n\r\n  /** Calculations for the reports. */\r\n  public calcs: Calculation[] = [];\r\n  /** Current selected language from UI. */\r\n  public reportLang = Language.Default;\r\n\r\n  /** Ref to used CalcReports */\r\n  public $calcReports: CalcReportController;\r\n\r\n  /** Ref to used SxyTable */\r\n  public $sxyTable: SxyTableController;\r\n\r\n  /** Ref to used CalcsIrRows */\r\n  public $calcsIrRows: CalcsIrRowsController;\r\n\r\n  /**\r\n   * The current view of the report. Partial is the default.\r\n   * Please note that not all reports support \"page1\" or \"full\".\r\n   */\r\n  public view: \"partial\" | \"page1\" | \"full\";\r\n\r\n  /** If true, adds the preview watermark to the preview. */\r\n  public preview?: boolean;\r\n\r\n  /**\r\n   * Function that is called when the report type has been changed\r\n   * Function has the following locals:  reportType: the selected report type.\r\n   */\r\n  public onReportTypeChange: (params: {\r\n    /** Selected reportType */\r\n    reportType: ReportType | calcReportType,\r\n  }) => void;\r\n\r\n  /** Report type */\r\n  private _reportType: ReportType | calcReportType;\r\n\r\n  private employerLang: Language;\r\n\r\n  private workerLangs: { [key: string]: Language } = {};\r\n\r\n  /** Report templates and the currently selected template */\r\n  private reports = {\r\n    salarySlip: {\r\n      full: \"salarySlipV2\",\r\n      page1: \"salarySlipV2Page1\",\r\n      partial: \"workerCalculationTablesV2\",\r\n    },\r\n    employerReport: {\r\n      full: \"employerReportV2\",\r\n      page1: \"employerReportV2Page1\",\r\n      partial: \"employerCalculationTablesV2\",\r\n    },\r\n    paymentReport: {\r\n      full: \"paymentReportV2\",\r\n      page1: \"paymentReportV2\",\r\n      partial: \"paymentTablesV2\",\r\n    },\r\n    paymentSummaryReport: {\r\n      full: \"paymentSummaryReportV2\",\r\n      page1: \"paymentSummaryReportV2\",\r\n      partial: \"paymentTablesV2\",\r\n    },\r\n    totalsReport: {\r\n      full: \"totalsReport\",\r\n      page1: \"totalsReport\",\r\n      partial: \"totalsTables\",\r\n    },\r\n  };\r\n\r\n  private sxyTableConfig: { currentCalc: Calculation | Calculation[], reportLang: Language, config: { options: SxyTableOptions, include: ColumnDefinition[], data: any[] } } = {\r\n    currentCalc: null,\r\n    reportLang: Language.Default,\r\n    config: null\r\n  };\r\n\r\n  private _epr = {\r\n    loading: {},\r\n    pending: {},\r\n    latestCalc: {},\r\n    current: {}\r\n  };\r\n\r\n  /**\r\n   * Creates a new CalcReportsController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    private ajax: Ajax,\r\n    private uiHelpers: UiHelpers,\r\n    private sessionService: SessionService,\r\n    private $timeout: angular.ITimeoutService,\r\n    private $http: angular.IHttpService,\r\n    private reportsApi: Reports,\r\n    private calculationsApi: Calculations\r\n  ) {\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    this.view = this.view || \"partial\";\r\n    this.sessionService.getReportLang().then((lang) => {\r\n      this.reportLang = lang;\r\n    });\r\n  }\r\n\r\n  /** Sets reportLang and refreshes table if $sxyTable exists */\r\n  public async setReportLang(lang: Language) {\r\n    this.reportLang = lang;\r\n    switch (this.reportType) {\r\n      case ReportType.TotalsReport: {\r\n        if (this.$calcReports) {\r\n          await this.$calcReports.refreshTableConfig();\r\n        }\r\n      }\r\n        break;\r\n      case \"rowsReport\": {\r\n        if (this.$sxyTable) {\r\n          await this.refreshTableConfig();\r\n        }\r\n      }\r\n        break;\r\n      case \"irRows\": {\r\n        if (this.$calcsIrRows) {\r\n          await this.$calcsIrRows.refreshTableConfig();\r\n        }\r\n      }\r\n        break;\r\n      case \"costCenterReport\" as any: {\r\n        if (this.$sxyTable) {\r\n          await this.refreshTableConfig();\r\n        }\r\n        break;\r\n      }\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Get lang for employer reports\r\n   * @returns language for calculation\r\n   */\r\n  public getEmployerLang(): Language {\r\n    if (this.reportLang !== Language.Default) {\r\n      return this.reportLang;\r\n    }\r\n    else {\r\n      if (!this.employerLang) {\r\n        this.employerLang = Language.Default;\r\n        this.sessionService.getReportLang().then(lang => {\r\n          this.employerLang = lang;\r\n          // Trigger AngularJs to redraw\r\n          this.$timeout();\r\n        });\r\n      }\r\n    }\r\n    return this.employerLang;\r\n  }\r\n\r\n  /**\r\n   * Get lang for worker reports\r\n   * @param calc selected calculation\r\n   * @returns language for calculation\r\n   */\r\n  public getWorkerLang(calc: Calculation): Language {\r\n    if (this.reportLang !== Language.Default) {\r\n      return this.reportLang;\r\n    }\r\n    if (!this.workerLangs[calc.worker.accountId]) {\r\n      this.workerLangs[calc.worker.accountId] = Language.Default;\r\n      this.sessionService.getReportLang(calc.worker.accountId).then(lang => {\r\n        this.workerLangs[calc.worker.accountId] = lang;\r\n        // Trigger AngularJs to redraw\r\n        this.$timeout();\r\n      });\r\n    }\r\n\r\n    return this.workerLangs[calc.worker.accountId];\r\n  }\r\n\r\n  /** The type for the calculation report. */\r\n  public get reportType(): ReportType | calcReportType {\r\n    return this._reportType;\r\n  }\r\n\r\n  /** The type for the calculation report. */\r\n  public set reportType(value: ReportType | calcReportType) {\r\n    if (value != this._reportType) {\r\n      this._reportType = value;\r\n      if (this.onReportTypeChange) {\r\n        this.onReportTypeChange({ reportType: value });\r\n      }\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Return languge text to ui\r\n   */\r\n  public get languageText() {\r\n    switch (this.reportLang) {\r\n      case Language.Fi:\r\n        return \"SALAXY.ENUM.Language.fi.label\";\r\n      case Language.En:\r\n        return \"SALAXY.ENUM.Language.en.label\";\r\n      case Language.Sv:\r\n        return \"SALAXY.ENUM.Language.sv.label\";\r\n      case Language.Default:\r\n        return (this.reportType === \"salarySlip\" || this.reportType === \"employerReport\" || this.reportType === \"paymentReport\") ? \"SALAXY.NG1.CalcReportsComponent.reportLanguageWorker\" : \"SALAXY.NG1.CalcReportsComponent.reportLanguageCompany\";\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Exports tabulator based reports data as excel file\r\n   */\r\n  public async downloadExcel() {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    const getExportData = async (data: Calculation[]) => {\r\n      const renderingLang = this.getEmployerLang() ?? Language.Fi;\r\n      await Translations.loadLanguage(renderingLang);\r\n      switch (this.reportType) {\r\n        case \"totalsReport\": {\r\n          return TotalsReportConfigGenerator.getTableData(data, renderingLang);\r\n        }\r\n        case \"rowsReport\": {\r\n          return RowsReportConfigGenerator.getTableData(data, renderingLang);\r\n        }\r\n        case \"irRows\": {\r\n          return IrRowsReportConfigGenerator.getTableData(data, renderingLang);\r\n        }\r\n      }\r\n    };\r\n    const fileNames = {\r\n      \"totalsReport\": \"SALAXY.ENUM.ReportType.totalsReport.label\",\r\n      \"rowsReport\": \"SALAXY.NG1.CalcReportsComponent.rowsReport\",\r\n      \"irRows\": \"SALAXY.NG1.CalcReportsComponent.irRows\"\r\n    };\r\n    const getFileName = (): string => {\r\n      return Texts.escapeFileName(`${Translations.get(fileNames[this.reportType])}_${Dates.format(\"today\", \"YYYY_MM\")}`);\r\n    };\r\n\r\n    ExcelHelpers.export(await getExportData(this.calcs), getFileName());\r\n    loading.dismiss();\r\n  }\r\n\r\n  /**\r\n   * Shows a download dialog for the given calculations.\r\n   * @param inline - If true, the download link opens the pdf into a new web page.\r\n   */\r\n  public showDownloadDialog(inline = false) {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.loading\");\r\n    this.reportsApi.getCalculationReport(this.calcs, this.reportType as calcReportType, this.getEmployerLang(), this.reportLang).then(response => {\r\n      if (inline) {\r\n        this.uiHelpers.openFile(response.data as any);\r\n      } else {\r\n        this.uiHelpers.downloadFile(response.data as any, decodeURIComponent(response.headers[\"content-disposition\"]).match(/filename\\s*=\\s*\"?(?<file>.*?)(?:\\s*;|\"|\\s*$)/)?.groups?.file);\r\n      }\r\n      loading.dismiss();\r\n    });\r\n  }\r\n\r\n  /** Reloads the current report */\r\n  public reload() {\r\n    const reportType = this.reportType;\r\n    this.reportType = null;\r\n    this.$timeout(0).then(() => {\r\n      this.reportType = reportType;\r\n    });\r\n  }\r\n\r\n  /** Loads epr for the calculation */\r\n  public loadEpr(calc: Calculation): irepr.EarningsPayment {\r\n    this.checkForEprChange(calc);\r\n    if (this._epr.pending[calc.id]) {\r\n      if (!this._epr.loading[calc.id]) {\r\n        this._epr.loading[calc.id] = true;\r\n        const load = () => {\r\n          this._epr.pending[calc.id] = false;\r\n          return this.calculationsApi.convertToEpr(calc).then((epr) => {\r\n            this._epr.current[calc.id] = this._epr.current[calc.id] ?? {};\r\n            angular.copy(epr, this._epr.current[calc.id]);\r\n            return this._epr.current[calc.id];\r\n          });\r\n        };\r\n\r\n        load().then(() => {\r\n          if (this._epr.pending[calc.id]) {\r\n            load();\r\n          }\r\n          else {\r\n            this._epr.loading[calc.id] = false;\r\n          }\r\n        });\r\n      }\r\n    }\r\n    return this._epr.current[calc.id];\r\n  }\r\n\r\n  /**\r\n   * Config for SxyTable\r\n   */\r\n  public get reportTableConfig(): { options: SxyTableOptions, include: ColumnDefinition[], data: any[] } {\r\n    if (!this.calcs) {\r\n      this.sxyTableConfig = {\r\n        currentCalc: null,\r\n        reportLang: null,\r\n        config: null\r\n      };\r\n    } else {\r\n      const calcs = angular.copy(this.calcs);\r\n      if (!Objects.equal(this.sxyTableConfig.currentCalc, calcs) || this.reportLang !== this.sxyTableConfig.reportLang) {\r\n        this.sxyTableConfig.currentCalc = calcs;\r\n        this.sxyTableConfig.reportLang = this.reportLang;\r\n        this.getDefaultLanguage(this.reportLang).then((lang) => {\r\n          this.reportLang = lang;\r\n          this.refreshTableConfig();\r\n        });\r\n      }\r\n    }\r\n    return this.sxyTableConfig.config;\r\n  }\r\n\r\n  private async refreshTableConfig() {\r\n    if (this.reportLang == Language.Default) {\r\n      this.reportLang = await this.sessionService.getReportLang();\r\n    }\r\n    const renderingLang = this.reportLang ?? Language.Fi;\r\n    await Translations.loadLanguage(renderingLang);\r\n    switch (this.reportType) {\r\n      case \"rowsReport\":\r\n        this.sxyTableConfig.config = RowsReportConfigGenerator.getConfig(this.calcs, renderingLang);\r\n        break;\r\n      case \"costCenterReport\" as any:\r\n        this.sxyTableConfig.config = CostCenterReportConfigGenerator.getConfig(this.calcs, this.sessionService.session?.settings?.costAccounting?.dimensions);\r\n        break;\r\n    }\r\n    await this.$timeout();\r\n    this.$sxyTable?.refresh();\r\n  }\r\n\r\n  private async getDefaultLanguage(lang: Language): Promise<Language> {\r\n    if (!lang) {\r\n      return this.sessionService.getReportLang();\r\n    }\r\n    return Promise.resolve(lang);\r\n  }\r\n  private checkForEprChange(calc: Calculation) {\r\n    if (!calc?.id) {\r\n      return false;\r\n    }\r\n    if (!angular.equals(calc, this._epr.latestCalc[calc.id])) {\r\n      this._epr.latestCalc[calc.id] = angular.copy(calc);\r\n      this._epr.pending[calc.id] = true;\r\n    }\r\n  }\r\n}\r\n","import angular from \"angular\";\r\nimport { calcReportType, Calculation, Calculations } from \"@salaxy/core\";\r\nimport { UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Handles user interaction for displaying calculation\r\n */\r\nexport class CalcReportsDisplayController implements angular.IController {\r\n  public static $inject = [\r\n    \"UiHelpers\",\r\n    \"Calculations\"\r\n  ];\r\n  /**\r\n   * Creates a new instance of CalcReportsDisplayController\r\n   * @param uiHelpers - Salaxy ui helpers service.\r\n   */\r\n constructor(\r\n  private uiHelpers: UiHelpers,\r\n  private calculations: Calculations\r\n) {}\r\n\r\n/**\r\n * Display CalcReports\r\n * @param reportType Report type\r\n * @param calculation BusinessObject\r\n */\r\npublic display(reportType: calcReportType, calculation: Calculation): void {\r\n    const calcs: Calculation[] = [calculation];\r\n    const data = {\r\n      reportType,\r\n      calcs,\r\n    };\r\n\r\n    this.uiHelpers.showDialog(\r\n      \"salaxy-components/modals/calc/CalcReports.html\",\r\n      null,\r\n      data,\r\n      null,\r\n      \"lg\",\r\n      true);\r\n  }\r\n\r\n/**\r\n * Display CalcReports\r\n * @param reportType Report type\r\n * @param calculationId BusinessObject id\r\n */\r\npublic async displayForId(reportType: calcReportType, calculationId: string): Promise<void> {\r\n    const calculation = await this.calculations.getSingle(calculationId);\r\n    const calcs: Calculation[] = [calculation];\r\n    const data = {\r\n      reportType,\r\n      calcs,\r\n    };\r\n\r\n    this.uiHelpers.showDialog(\r\n      \"salaxy-components/modals/calc/CalcReports.html\",\r\n      null,\r\n      data,\r\n      null,\r\n      \"lg\",\r\n      true);\r\n  }\r\n}","import angular from \"angular\";\r\n\r\nimport { CalcRowConfig, CalculationRowCategory, CalculationRowType, CalculatorLogic, InputEnumOption, Objects, Translations, UserDefinedRow } from \"@salaxy/core\";\r\n\r\nimport { RowTypeService, SessionService, UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * UI logic for changing the row type and potentially the kind for UserDefined row in calculation.\r\n * Note that changing the type may change the message of the row as well:\r\n * In the future, usecase defaults may also be changed.\r\n */\r\nexport class CalcRowTypeController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"SessionService\", \"UiHelpers\", \"RowTypeService\"];\r\n\r\n  /** Type of the input element. Default is typeahead. */\r\n  public type: \"typehead\" | \"list\" | \"read-only\";\r\n\r\n  /** If set, filters the rows based on categories (plus rowTypes if set) */\r\n  public categories: CalculationRowCategory[];\r\n\r\n  /** If set, shows only these types (plus categories if set) */\r\n  public rowTypes: CalculationRowType[];\r\n\r\n  /** Name and identifier of the typehead input */\r\n  public name: string;\r\n\r\n  /**\r\n   * Placeholder text in the typeahead input.\r\n   * Default is 'SALAXY.UI_Terms.select'.\r\n   */\r\n  public placeholder: string;\r\n\r\n  /**\r\n   * If true, the list will show all the children under each parent that is shown as a direct hit.\r\n   */\r\n  public showChildren: boolean;\r\n\r\n  /**\r\n   * Function that is called after the row type and potentially kind and message have been changed.\r\n   * @example <salaxy-calc-row-type on-row-changed=\"$ctrl.commitNewRow()\"></salaxy-calc-row-type>\r\n   */\r\n  public onRowChanged: (eventData: {\r\n    /** New item which was created. */\r\n    row: UserDefinedRow,\r\n  }) => void;\r\n\r\n  /** The calculation row that this component modifies. */\r\n  public model: UserDefinedRow;\r\n\r\n  /**\r\n   * The default number of items that is returned from the typeahead search list.\r\n   * Default is 50.\r\n   */\r\n  public top: number;\r\n\r\n  private _internalValue: InputEnumOption;\r\n\r\n  private modelRowType;\r\n\r\n  private modelType;\r\n\r\n  private modelDataKind;\r\n\r\n  private listCache: {\r\n    /** Cache key */\r\n    key: string,\r\n    /** Cache value */\r\n    value: CalcRowConfig[],\r\n  } = null;\r\n\r\n  constructor(private session: SessionService, private uiHelpers: UiHelpers, private rowTypeService: RowTypeService) {\r\n  }\r\n\r\n  /** Sets the default values in init. */\r\n  public $onInit() {\r\n    this.top = this.top || 50;\r\n    if (!this.type) {\r\n      this.type = \"typehead\";\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Detects the changes in the model properties \"rowType\" and \"data.kind\"\r\n   * and reflects them to internalValue.\r\n   */\r\n  public $doCheck() {\r\n    let hasChanges = false;\r\n    if (this.model?.rowType !== this.modelRowType) {\r\n      this.modelRowType = this.model?.rowType;\r\n      hasChanges = true;\r\n    }\r\n    if (this.model?.data?.kind !== this.modelDataKind) {\r\n      this.modelDataKind = this.model?.data?.kind;\r\n      hasChanges = true;\r\n    }\r\n    if (this.model?.type !== this.modelType) {\r\n      this.modelType = this.model?.type;\r\n      hasChanges = true;\r\n    }\r\n\r\n    if (hasChanges) {\r\n      const listRowType = this.modelType ? this.modelType.split(\"/\")[2] : this.modelRowType;\r\n      // NOTE: There is potential incoherent behavior here: depending on in which order attributes \"categories\"\r\n      //       \"rowTypes\" and \"model\" are set, the filters may behave differently in edge case where model value\r\n      //       is outside these filters. This was not considered significant at the time of writing.\r\n      if (this.modelDataKind) {\r\n        this._internalValue = this.getList().find((x) => x.value === `${listRowType}.${this.modelDataKind}`);\r\n      } else {\r\n        this._internalValue = this.getList().find((x) => x.value === (listRowType));\r\n      }\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Internal value from view to the controller. This is one of the numerations returned by getList()\r\n   * if model has been set and it matches to oneof those values.\r\n   */\r\n  protected get internalValue(): InputEnumOption {\r\n    return this._internalValue;\r\n  }\r\n  protected set internalValue(val: InputEnumOption) {\r\n    this._internalValue = val;\r\n    if (!this.model) {\r\n      return;\r\n    }\r\n    this.model.data = this.model.data || {};\r\n    if (!val) {\r\n      this.model.rowType = null;\r\n      this.model.data.kind = null;\r\n      this.model.type = null;\r\n    } else if (val.value.indexOf(\".\")) {\r\n      const valueArr = val.value.split(\".\");\r\n      this.model.rowType = valueArr[0] as CalculationRowType;\r\n      this.model.data.kind = valueArr[1] || undefined;\r\n      // TODO: Requires refactoring => type should be directly in value\r\n      if (val.ui) {\r\n        this.model.type = val.ui.type;\r\n        this.model.rowType = val.ui.rowType;\r\n        (this.model as any).config = {\r\n          group: val.ui.group,\r\n        };\r\n      }\r\n    } else {\r\n      this.model.rowType = val.value as CalculationRowType;\r\n      this.model.data.kind = undefined;\r\n      // TODO: Requires refactoring => type should be directly in value\r\n      if (val.ui) {\r\n        this.model.type = val.ui.type;\r\n        this.model.rowType = val.ui.rowType;\r\n        (this.model as any).config = {\r\n          group: val.ui.group,\r\n        };\r\n      }\r\n    }\r\n    this.onRowChanged({ row: this.model });\r\n  }\r\n\r\n  /**\r\n   * Gets the list of row types according to options:\r\n   * This list changes and is cached based on role (household/company), language,\r\n   * rowTypes and categories. Currently the same as search(null), but cached.\r\n   */\r\n  public getList(): InputEnumOption[] {\r\n    return this.uiHelpers.cache(this, \"list\",\r\n      () => { return this.search(null, true, true); },\r\n      () => Translations.getLanguage() + this.rowTypes?.join(\"\") + this.categories?.join(\"\"));\r\n  }\r\n\r\n  /**\r\n   * Gets the search as cached item: Can be bound to ng-repeat.\r\n   * @param searchText The search text. If null or empty, returns the full list.\r\n   */\r\n  public getCachedSearch(searchText: string): InputEnumOption[] {\r\n    return this.uiHelpers.cache(this, \"search\",\r\n      () => { return this.search(searchText, true, null); },\r\n      () => searchText + this.categories?.toString());\r\n  }\r\n\r\n  /**\r\n   * Searches the row types.\r\n   * @param searchText The search text. If null or empty, returns the full list.\r\n   * @param ignoreTop If true, ignores the this.top setting to return only top n items of the search\r\n   * @param showChildren Forces the showChildren value to true for this run.\r\n   * By default, children are only shown if they match the search.\r\n   */\r\n  public search = (searchText: string, ignoreTop = false, showChildren: boolean = null): InputEnumOption[] => {\r\n    if (showChildren == null) {\r\n      showChildren = this.showChildren;\r\n    }\r\n    const toOption = (config: CalcRowConfig) => {\r\n      return {\r\n        text: config.label,\r\n        value: config.name,\r\n        title: config.descr,\r\n        ui: {\r\n          color: config.color,\r\n          iconText: config.iconText,\r\n          addedByChild: null,\r\n          initials: config.iconText,\r\n          entityType: \"company\",\r\n          // TODO: Requires refactoring\r\n          group: config.group,\r\n          type: config.type,\r\n          rowType: config.rowType,\r\n          isChild: false\r\n        },\r\n      };\r\n    };\r\n    const result: InputEnumOption[] = [];\r\n    searchText = (searchText || \"\").trim().toLowerCase();\r\n    this.getRowTypes().forEach((rowConfig) => {\r\n      let isParentAdded = false;\r\n      let isParentAddedAsSelf = false;\r\n      if (\r\n        !searchText\r\n        || (rowConfig.label + rowConfig.descr + rowConfig.name).toLowerCase().indexOf(searchText) >= 0\r\n      ) {\r\n        result.push(toOption(rowConfig));\r\n        if (!ignoreTop && result.length >= this.top) {\r\n          return result;\r\n        }\r\n        isParentAdded = true;\r\n        isParentAddedAsSelf = true;\r\n      }\r\n      if (rowConfig.kind?.values) {\r\n        rowConfig.kind.values.forEach((kind) => {\r\n          if (\r\n            !(kind.name == \"undefined\" || kind.name == \"unknown\") &&\r\n            (\r\n              (isParentAddedAsSelf && showChildren)\r\n              || (searchText && (kind.label + kind.descr + kind.name).toLowerCase().indexOf(searchText) >= 0)\r\n            )\r\n          ) {\r\n            if (!isParentAdded) {\r\n              const option = toOption(rowConfig);\r\n              option.ui.addedByChild = true;\r\n              result.push(option);\r\n              isParentAdded = true;\r\n            }\r\n            result.push({\r\n              text: kind.label,\r\n              value: rowConfig.name + \".\" + kind.name,\r\n              title: kind.descr,\r\n              // TODO: Requires refactoring\r\n              ui: {\r\n                group: rowConfig.group,\r\n                type: rowConfig.type,\r\n                rowType: rowConfig.rowType,\r\n                isChild: true\r\n              }\r\n            });\r\n            if (!ignoreTop && result.length >= this.top) {\r\n              return result;\r\n            }\r\n          }\r\n        });\r\n      }\r\n    });\r\n\r\n    if (result.length === 2 && result[0].ui.addedByChild) {\r\n      // If only one parent with one child (child is exact match) => Merge to one row.\r\n      return [{\r\n        text: result[0].text + \": \" + result[1].text,\r\n        value: result[1].value,\r\n        title: result[1].title,\r\n        ui: result[0].ui,\r\n      }];\r\n    }\r\n\r\n    return result;\r\n  };\r\n\r\n  /** Gets a label for the given internal value. */\r\n  public getRowLabel(rowTypeKey: string) {\r\n    if (!rowTypeKey) {\r\n      return null;\r\n    }\r\n    let rowTypeName = null;\r\n    let kindName = null;\r\n    if (rowTypeKey.indexOf(\".\")) {\r\n      const valueArr = rowTypeKey.split(\".\");\r\n      rowTypeName = valueArr[0] as CalculationRowType;\r\n      kindName = valueArr[1];\r\n      if (kindName === \"undefined\") {\r\n        kindName = null; // For undefined, take the main category.\r\n      }\r\n    } else {\r\n      rowTypeName = rowTypeKey as CalculationRowType;\r\n    }\r\n    const rowType = this.getRowTypes().find((type) => type.name === rowTypeName);\r\n    if (!rowType) {\r\n      return null;\r\n    }\r\n    const kind = rowType.kind?.values?.find((x) => x.name === kindName);\r\n    return kind ? kind.label : rowType.label;\r\n  }\r\n\r\n  /**\r\n   * Shows a dilaog that contains information about the row type.\r\n   * @param rowType The row type to show information about.\r\n   */\r\n  public showInfoScreen(rowType: InputEnumOption){\r\n    this.model = this.model || {\r\n      rowIndex: 0,\r\n      data: {\r\n        dimensions: {},\r\n        accounting: {},\r\n      },\r\n    };\r\n    this.internalValue = rowType; // Updates the model.\r\n    this.uiHelpers.openEditDialog(\"salaxy-components/calc/rows/RowTypeEditDialog.html\", this.model, {\r\n      calc: CalculatorLogic.getBlank(),\r\n    }, \"lg\", \"CalcRows2019Controller\", ).then((_result) => {\r\n      // Do something?\r\n    });\r\n\r\n  }\r\n\r\n  /**\r\n   * Gets the list of row types. Method filters based on rowTypes and categories,\r\n   * the texts are language versioned and there is a role filter for \"household\"/\"company\".\r\n   */\r\n  private getRowTypes(): CalcRowConfig[] {\r\n    const key = \"\" + this.categories + this.rowTypes + this.rowTypeService.isReady;\r\n    if (!this.listCache || this.listCache.key !== key) {\r\n      const rowsLogic = this.rowTypeService.logic;\r\n      let value;\r\n      if ((this.categories || []).length + (this.rowTypes || []).length > 0) {\r\n        const rowConfigsByCategory =  Objects.copy(rowsLogic.getRowConfigsByCategory(this.categories));\r\n        // Remove kind from IrIncomeType: prevent listing of income types in category based lists\r\n        const irIncomeType = rowConfigsByCategory.find( (x) => x.name === CalculationRowType.IrIncomeType);\r\n        if (irIncomeType != null) {\r\n          irIncomeType.kind = null;\r\n        }\r\n        value = rowsLogic.getRowConfigsByType(this.rowTypes).concat(rowConfigsByCategory);\r\n      } else {\r\n        value = rowsLogic.getRowConfigs();\r\n      }\r\n\r\n      // Obsolete\r\n      const obsolete = [\r\n        CalculationRowType.PaidSickLeaveSalary,\r\n        CalculationRowType.PaidSickLeaveHourlySalary,\r\n        CalculationRowType.PaidSickLeaveMonthlySalary,\r\n        CalculationRowType.TrainingSalary,\r\n        CalculationRowType.TrainingHourlySalary,\r\n        CalculationRowType.TrainingMonthlySalary,\r\n        CalculationRowType.ServiceCharge\r\n      ];\r\n      value = value.filter((x) => !(obsolete.indexOf(x.name) >= 0));\r\n\r\n      // For pro and admin only\r\n      if (!this.session.isInSomeRole(\"pro,admin\")) {\r\n        value = value.filter((x) => x.name != CalculationRowType.Service);\r\n      }\r\n\r\n      // For bizconfigs only\r\n      if (!this.session.isInRole(\"bizConfigs\")) {\r\n        value = value.filter((x) => x.name != CalculationRowType.Script && x.name != CalculationRowType.PayStats);\r\n      }\r\n\r\n      this.listCache = { key, value };\r\n    }\r\n    return this.listCache.value;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\nimport { SettingsService, UiHelpers } from \"../../services\";\r\nimport { CalcRowScriptConfig, InputEnumOption, RowTypeDefinition, HelpersRoot, Employment, Employments, Calculations, Calculation } from \"@salaxy/core\";\r\n/**\r\n * Controller for the CalcRowFormula component that provides formula editing capabilities for calculation rows.\r\n * Used by the CalcRowFormula component to manage formula editing functionality.\r\n * @implements {angular.IController}\r\n */\r\nexport class CalcRowFormulaController implements angular.IController {\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"SettingsService\", \"UiHelpers\", \"Employments\", \"Calculations\"];\r\n  /** Currently edited row */\r\n  public row: RowTypeDefinition;\r\n\r\n  /** Available properties for scripting */\r\n  public scriptNames: InputEnumOption[] = [\r\n    {\r\n      value: \"price\",\r\n      text: \"Hinta\",\r\n    },\r\n    {\r\n      value: \"count\",\r\n      text: \"Määrä\",\r\n    },\r\n    {\r\n      value: \"message\",\r\n      text: \"Rivin teksti\",\r\n    },\r\n    {\r\n      value: \"unit\",\r\n      text: \"Yksikkö\",\r\n    },\r\n    {\r\n      value: \"sourceId\",\r\n      text: \"ID lähdejärjestelmässä\",\r\n    },\r\n    {\r\n      value: \"accounting.dimensions\",\r\n      text: \"Kustannuspaikat\",\r\n    },\r\n    {\r\n      value: \"accounting.vatPercent\",\r\n      text: \"ALV %\",\r\n    },\r\n    {\r\n      value: \"accounting.vatEntries\",\r\n      text: \"ALV rivit\",\r\n    },\r\n    {\r\n      value: \"period\",\r\n      text: \"Palkkakausi\",\r\n    },\r\n    {\r\n      value: \"period.start\",\r\n      text: \"Palkkaukauden alku\",\r\n    },\r\n    {\r\n      value: \"period.end\",\r\n      text: \"Palkkaukauden loppu\",\r\n    },\r\n    {\r\n      value: \"period.daysCount\",\r\n      text: \"Palkkaukauden työpäivien määrä\",\r\n    },\r\n    {\r\n      value: \"period.days\",\r\n      text: \"Palkkaukauden työpäivät\",\r\n    },\r\n    {\r\n      value: \"data\",\r\n      text: \"Rivin data\"\r\n    },\r\n    {\r\n      value: \"data.kind\",\r\n      text: \"Rivin alalaji\"\r\n    },\r\n    {\r\n      value: \"calculation\",\r\n      text: \"Koko laskelman muokkaus\"\r\n    }\r\n  ];\r\n\r\n  public selectedEmployment: Employment;\r\n  public selectedCalc: Calculation;\r\n\r\n  /** Selected script name for addScript */\r\n  public selectedScriptName: string;\r\n\r\n  public evalResult: string;\r\n\r\n  /**\r\n   * Creates a new EmbeddedUiController\r\n   * @ignore\r\n   */\r\n  constructor(private settingsService: SettingsService, private uiHelpers: UiHelpers, private employments: Employments, private calculations: Calculations) { }\r\n\r\n  /** Gets the description for a script name */\r\n  public getDescription(scriptName: string) {\r\n    return this.scriptNames.find(n => n.value === scriptName)?.text;\r\n  }\r\n\r\n  /** Returns true if the selected script name has already been added. */\r\n  public get selectedScriptAdded(): boolean {\r\n    // TODO: add kind support later: name + kind as unique key\r\n    return !!this.row.config?.scripts?.some(script => script.name === this.selectedScriptName);\r\n  }\r\n\r\n  /**\r\n   * Adds a new script expression to the row.\r\n   * @param {string} scriptName - The name of the script to add. selectedScriptName is used if not provided.\r\n   */\r\n  public addScript(scriptName?: string) {\r\n    scriptName = scriptName || this.selectedScriptName;\r\n    this.row.config.scripts ??= [];\r\n    if (this.row.config.scripts.some(script => script.name === scriptName)) {\r\n      return;\r\n    }\r\n    this.row.config.scripts.push({ name: scriptName, script: \"\" });\r\n  }\r\n\r\n  /** Name of the script that is currently edited in full-dialog editor. */\r\n  public editingScript?: CalcRowScriptConfig;\r\n\r\n  /**\r\n   * Selects a script for editing in full-dialog editor.\r\n   * @param {string} script - The script object to edit.\r\n   * Undefined for closing the editor.\r\n   */\r\n  public editScript(script?: CalcRowScriptConfig) {\r\n    this.editingScript = script;\r\n    this.evaluateEditingScript();\r\n  }\r\n\r\n  /**\r\n   * Removes a script from the row.\r\n   * @param {string} script - The script to remove.\r\n   */\r\n  public removeScript(script: CalcRowScriptConfig) {\r\n    const index = this.row.config.scripts?.indexOf(script);\r\n    if (index >= 0) {\r\n      this.row.config.scripts.splice(index, 1);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Determines if the currently edited script can be evaluated.\r\n   * A script is evaluatable when all required dependencies are available:\r\n   * - A selected employment is set\r\n   * - A selected calculation is set\r\n   * - A script is currently being edited\r\n   * @returns {boolean} True if the script can be evaluated, false otherwise\r\n   */\r\n  public isScriptEvaluatable(): boolean {\r\n    return !!(this.selectedEmployment && this.selectedCalc && this.editingScript);\r\n  }\r\n\r\n  /**\r\n   * Evaluates the currently edited script using a wrapped eval pattern.\r\n   * The script can refer to $data (which includes sxy and settings).\r\n   * @returns {*} The result of the evaluated script.\r\n   */\r\n  public evaluateEditingScript(): any {\r\n    this.evalResult = \"\";\r\n    if (!this.isScriptEvaluatable()) {\r\n      return;\r\n    }\r\n    /* const settings = this.settingsService.current;\r\n    globalThis.settings = settings;\r\n    const fn = Function(`return (${this.editingScript.script})`);\r\n    const result = fn.bind({sxy: new HelpersRoot()})(); */\r\n    //TODO: Instantiate row from this.row\r\n    //Check rowsService or something\r\n    //globalThis.row = {rowType: this.row.config.type};\r\n    globalThis.sxy = new HelpersRoot();\r\n    globalThis.settings = angular.copy(this.settingsService.current as any);\r\n    globalThis.employment = angular.copy(this.selectedEmployment);\r\n    globalThis.calculation = angular.copy(this.selectedCalc);\r\n    globalThis.row = {};\r\n    if (this.editingScript.name === \"calculation\") {\r\n      const fn = new Function(`return (${this.editingScript.script})`);\r\n      const returnedCalculation = fn();\r\n      this.evalResult = JSON.stringify(fn(), null, 2);\r\n      if (returnedCalculation) {\r\n        angular.copy(returnedCalculation, this.selectedCalc);\r\n      }\r\n    }\r\n    else\r\n    {\r\n      const fn = new Function(`return (${this.editingScript.script})`);\r\n      this.evalResult = JSON.stringify(fn(), null, 2);\r\n    }\r\n  }\r\n  /**\r\n   * Opens a dialog to select an existing calculation.\r\n   * @returns {Promise<void>} A promise that resolves when the dialog is closed.\r\n   */\r\n  public addExistingCalc() {\r\n    return this.uiHelpers.openEditDialog(\r\n      \"salaxy-components/modals/calc/CalcList.html\",\r\n      [],\r\n      {\r\n        title: \"SALAXY.UI_Terms.select\",\r\n        category: \"draft\",\r\n        options:  {$filter: \"status eq 'draft'\"},\r\n        okButtonText: \"SALAXY.UI_Terms.ok\",\r\n        cancelButtonText: \"SALAXY.UI_Terms.cancel\",\r\n      }).then((result) => {\r\n      if (result.action === \"ok\" && result.item.length == 1) {\r\n       return this.calculations.getSingle(result.item[0].id).then((calc) => {\r\n        this.selectedCalc = calc;\r\n        console.log(this.selectedCalc);\r\n        return this.employments.getSingle(calc.worker.employmentId).then((employment) => {\r\n          this.selectedEmployment = employment;\r\n          console.log(this.selectedEmployment);\r\n        });\r\n       });\r\n      } else if (result.action === \"ok\" && result.item.length > 1) {\r\n        this.uiHelpers.showAlert(\"Valitse vain yksi laskelma\");\r\n      }\r\n    });\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {\r\n  AbsenceCauseCode,\r\n  Calculation, Calculations, Calculator, CalculatorLogic, CalcWorktime, DateRange, Dates, HolidayCode, HolidayYear, MonthlyHolidayAccrual, SalaryDateKind, SalaryDateLogic, Translations, WageBasis, WorkerAbsences, Employments, Employment,\r\n  HolidaysLogic, AnnualLeave,Arrays, InputEnumOption, HolidayPayCalculation, CalculationStatus\r\n} from \"@salaxy/core\";\r\n\r\nimport { SessionService, UiHelpers } from \"../../services\";\r\nimport { HolidayYearCrudController, WorkerAbsencesCrudController } from \"../worker\";\r\nimport { CalculatorSections } from \"./CalculatorSections\";\r\n\r\n/**\r\n * Handles the user interaction of Worktime within the Calculator.\r\n * The Worktime contains the logic for fetching holidays and absences\r\n * for that particular period and adding calculation rows for them if necessary.\r\n */\r\nexport class CalcWorktimeController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"UiHelpers\",\r\n    \"Calculations\",\r\n    \"Calculator\",\r\n    \"SessionService\",\r\n    \"Employments\",\r\n    \"$timeout\"\r\n  ];\r\n\r\n  /** User interface shortcuts for period selection */\r\n  public periodShortcuts: {\r\n    /** Text for current month. */\r\n    monthCurrent: string,\r\n    /** Text for last month. */\r\n    monthLast: string,\r\n    /** Text for other month. */\r\n    monthOther: string,\r\n    // monthMulti: \"Monta kuukautta\",\r\n    /** Text for two weeks. */\r\n    weeks2: string,\r\n    /** Text for half a month */\r\n    monthHalf: string,\r\n    /** Text for other period. */\r\n    other: string,\r\n  };\r\n\r\n  /** The calculation that the controller edits (shows in read-only mode). */\r\n  public calc: Calculation;\r\n\r\n  /**\r\n   * The employment data for the worker.\r\n   */\r\n  public workerEmployment: Employment;\r\n\r\n  /**\r\n   * Worktime data for the period fetched from the server\r\n   */\r\n  public worktime: CalcWorktime;\r\n\r\n  /** If there is a validation error in period start, it is added here. */\r\n  public periodStartDateError = null;\r\n\r\n  /** Demodata for the anonymous demo calculator. */\r\n  public demoData: {\r\n    /** Start date for which the data was generated. */\r\n    startDate: string,\r\n    /** End date for which the data was generated. */\r\n    endDate: string,\r\n    /** The holiday data */\r\n    holidays?: HolidayYear,\r\n    /** Absences data. */\r\n    absences?: WorkerAbsences,\r\n  } = { startDate: null, endDate: null };\r\n\r\n  private _periodStartDate;\r\n  private _dateRange: DateRange;\r\n\r\n  /**\r\n   * Creates a new CalcWorktimeController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    private uiHelpers: UiHelpers,\r\n    private calcApi: Calculations,\r\n    private anonCalcApi: Calculator,\r\n    private sessionService: SessionService,\r\n    private employmentsApi: Employments,\r\n    private $timeout: angular.ITimeoutService,\r\n  ) {\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    this.initDateRanges();\r\n    if (this.currentCalc && this.currentCalc.info.workStartDate && this.currentCalc.info.workEndDate) {\r\n      this.reloadHolidays();\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Reset the controller to initial state.\r\n   */\r\n  public reset() {\r\n    this._dateRange = {};\r\n    this._periodStartDate = null;\r\n    this.worktime ??= {};\r\n    angular.copy(this.calc?.worktime ?? {}, this.worktime);\r\n  }\r\n\r\n  /**\r\n   * Loads the employment data for the current worker.\r\n   */\r\n  public async loadEmployment(): Promise<void> {\r\n    if(this.currentCalc.worker.employmentId) {\r\n      const result = await this.employmentsApi.getSingle(this.currentCalc.worker.employmentId);\r\n      this.workerEmployment = result;\r\n      this.$timeout();\r\n\r\n    } else {\r\n      this.workerEmployment = null;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Getter for checking if WorkerHolidays is active.\r\n   */\r\n  public get isWorkerHolidaysActive(): boolean {\r\n    if(this.workerEmployment && this.workerEmployment.holidays) {\r\n      return HolidaysLogic.isWorkerHolidaysActive(this.workerEmployment.holidays);\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /** Gets the requested salary date */\r\n  public get requestedSalaryDate(): string {\r\n    return this.calc.workflow.requestedSalaryDate;\r\n  }\r\n  public set requestedSalaryDate(value: string) {\r\n    this.calc.workflow.requestedSalaryDate = value;\r\n    this.calc.workflow.salaryDate = value; // Set the salary date to the requestedSalaryDate until the next recalculation.\r\n  }\r\n\r\n  /**\r\n   * Reloads the holidays from server.\r\n   */\r\n  public reloadHolidays(): void {\r\n    this.worktime ??= {};\r\n    if(this.sessionService.isInRole(\"disableHolidays\")) {\r\n      return;\r\n    }\r\n    angular.copy(this.calc.worktime ?? {}, this.worktime);\r\n    if (this.sessionService.isAuthenticated) {\r\n      if (this.calc?.isReadOnly || this.calc?.workflow?.status === CalculationStatus.PaymentStarted) {\r\n        return;\r\n      }\r\n      this.calcApi.getWorktimeData(this.calc).then((result) => angular.copy(result, this.worktime));\r\n    } else {\r\n      this.checkDemoData();\r\n      this.anonCalcApi.getWorktimeData(this.calc, this.demoData.holidays, this.demoData.absences).then((result) => angular.copy(result, this.worktime));\r\n    }\r\n  }\r\n\r\n  /** Holiday year has been changed and must be saved and reloaded. */\r\n  public holidaysChanged(holidaysCtrl: HolidayYearCrudController) {\r\n    holidaysCtrl.save().then(() => {\r\n      this.reloadHolidays();\r\n    });\r\n  }\r\n\r\n  /** Absences has been changed and must be saved and reloaded. */\r\n  public absencesChanged(absencesCtrl: WorkerAbsencesCrudController) {\r\n    absencesCtrl.save().then(() => {\r\n      this.reloadHolidays();\r\n    });\r\n  }\r\n\r\n  /** Gets the current calculation object */\r\n  public get currentCalc(): Calculation {\r\n    return this.calc;\r\n  }\r\n\r\n  /**\r\n   * Returns true if there is no net salary payment to worker at all.\r\n   */\r\n  public get isCurrentZeroPayment(): boolean {\r\n      return CalculatorLogic.isZeroPayment(this.calc);\r\n  }\r\n\r\n  /** Disable function for the salary date picker. */\r\n  public isDisabledSalaryDate = (date): boolean => {\r\n    const role =  this.sessionService.isInRole(\"pro\") ? \"pro\" :\r\n                this.sessionService.isInRole(\"admin\") ? \"admin\" : null;\r\n    switch(this.calc.workflow.salaryDateKind) {\r\n      case SalaryDateKind.InPast:\r\n        return false;\r\n      case SalaryDateKind.Default:\r\n      default:\r\n        return !SalaryDateLogic.isValidSalaryDate(date, null, null, true, this.calc.info.paymentChannel, CalculatorLogic.isZeroPayment(this.calc), role, true);\r\n    }\r\n  };\r\n\r\n  /** Getter and setter for Calculation daterange in compatible format for new DateRange component. */\r\n  public get dateRange(): DateRange {\r\n    const info = (this.currentCalc || {}).info;\r\n    const framework = (this.currentCalc || {}).framework;\r\n    if (!this._dateRange) {\r\n      this._dateRange = {\r\n        start: info.workStartDate,\r\n        end: info.workEndDate,\r\n        daysCount: framework.numberOfDays,\r\n      };\r\n    }\r\n    return this._dateRange;\r\n  }\r\n  public set dateRange(value: DateRange) {\r\n    this._dateRange = value;\r\n  }\r\n\r\n  /** Returns true if the holidays uses accrual. */\r\n  public get isHolidayAccrual(): boolean {\r\n    if (!this.worktime?.holidaySpec) {\r\n      return false;\r\n    }\r\n    return  this.worktime.holidaySpec.code == HolidayCode.Permanent14Days ||\r\n    this.worktime.holidaySpec.code == HolidayCode.Permanent35Hours ||\r\n    this.worktime.holidaySpec.code == HolidayCode.TemporaryTimeOff ||\r\n    this.worktime.holidaySpec.code == HolidayCode.Other ||\r\n    this.worktime.holidaySpec.code == HolidayCode.Script;\r\n  }\r\n\r\n\r\n  /** Returns true if holidays are accrued for this calc. */\r\n  public get accruesHolidays(): boolean {\r\n    if (!this.worktime?.accrualSpec) {\r\n      return false;\r\n    }\r\n    return  this.worktime.accrualSpec.code == HolidayCode.Permanent14Days ||\r\n    this.worktime.accrualSpec.code == HolidayCode.Permanent35Hours ||\r\n    this.worktime.accrualSpec.code == HolidayCode.TemporaryTimeOff ||\r\n    this.worktime.accrualSpec.code == HolidayCode.Other ||\r\n    this.worktime.accrualSpec.code == HolidayCode.Script;\r\n  }\r\n\r\n\r\n  /**\r\n   * Called when the date range changes.\r\n   * @param noPeriodStartDateUpdate If true, the _periodStartDate is not updated.\r\n   * Should be true if the change is triggered by that input to avoid UI flickering.\r\n   */\r\n  public dateRangeChange(noPeriodStartDateUpdate = false) {\r\n    const info = (this.currentCalc || {}).info;\r\n    const framework = (this.currentCalc || {}).framework;\r\n    info.workStartDate = this.dateRange.start;\r\n    if (!noPeriodStartDateUpdate) {\r\n      this._periodStartDate = Dates.format(this.dateRange.start, \"D.M.\", null);\r\n    }\r\n    info.workEndDate = this.dateRange.end;\r\n    framework.numberOfDays = this.dateRange.daysCount;\r\n    this.reloadHolidays();\r\n  }\r\n\r\n  /**\r\n   * Gets or sets the period start date, which is bound to editable input in case the period type\r\n   * is not \"other\" (date the range / calendar component)\r\n   */\r\n  public get periodStartDate(): string {\r\n    return this._periodStartDate;\r\n  }\r\n  public set periodStartDate(value: string) {\r\n    this._periodStartDate = value;\r\n    const parts = (value || \"\").split(\".\");\r\n    if (parts.length < 2 || parts.length > 3) {\r\n      this.periodStartDateError = \"SALAXY.NG1.CalcWorktimeComponent.periodStartDateErrorFormat\";\r\n      return;\r\n    }\r\n    let year = (parts.length === 3) ? Number((parts[2] || \"\").trim()) : null;\r\n    if (!year || year < 2019 || year > 2100) {\r\n      year = Number(this.dateRange.start.substr(0, 4));\r\n    }\r\n    const date = Dates.getDate(year, Number(parts[1]), Number(parts[0]));\r\n    if (date) {\r\n      this.periodStartDateError = null;\r\n      switch (this.periodShortcut) {\r\n        case \"monthCurrent\":\r\n        case \"monthLast\":\r\n        case \"monthOther\":\r\n          this.dateRange = Dates.getDateRange(date, Dates.add(Dates.add(date,1,\"month\"),-1,\"day\"));\r\n          break;\r\n        case \"weeks2\":\r\n          this.dateRange = Dates.getDateRange(date, Dates.add(Dates.add(date,2,\"week\"),-1,\"day\"));\r\n          break;\r\n        case \"monthHalf\":\r\n          if (Dates.getDay(date) === 15 || Dates.getDay(date) === 16) {\r\n            this.dateRange = Dates.getDateRange(date, Dates.startEnd(date, \"end-month\"));\r\n          } else {\r\n            this.dateRange = Dates.getDateRange(date, Dates.add(date,14,\"day\"));\r\n          }\r\n          break;\r\n        case \"other\":\r\n          this.dateRange = Dates.getDateRange(date, date);\r\n          break;\r\n      }\r\n      this.dateRangeChange(true);\r\n    } else {\r\n      this.periodStartDateError = value + \" \" + Translations.get(\"SALAXY.NG1.CalcWorktimeComponent.periodStartDateErrorNotDate\");\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Gets the user interface shortcut for the period type:\r\n   * Different user interfaces are shown depending on the period shortcut.\r\n   */\r\n  public get periodShortcut(): \"monthCurrent\" | \"monthLast\" | \"monthOther\" | \"weeks2\" | \"monthHalf\" | \"other\" {\r\n    if (!this.dateRange.start || !this.dateRange.end) {\r\n      return null;\r\n    }\r\n    if (this.dateRange.start === Dates.getDate(\"today\", \"today\", 1)\r\n      && this.dateRange.end === Dates.startEnd(\"today\", \"end-month\")) {\r\n\r\n      return \"monthCurrent\";\r\n    }\r\n    if (this.dateRange.start === Dates.add(Dates.startEnd(\"today\",\"start-month\"),-1,\"month\")\r\n      && this.dateRange.end === Dates.startEnd(Dates.add(Dates.startEnd(\"today\", \"start-month\"),-1,\"month\"),\"end-month\")) {\r\n      return \"monthLast\";\r\n    }\r\n    if (this.dateRange.end === Dates.add(Dates.add(this.dateRange.start, 1, \"month\"), -1, \"day\")) {\r\n      return \"monthOther\";\r\n    }\r\n    if (this.dateRange.end === Dates.add(Dates.add(this.dateRange.start,2, \"week\"),-1, \"day\")) {\r\n      return \"weeks2\";\r\n    }\r\n\r\n    // if the range is 15 (14) days or\r\n    // starts 15th or 16th and ends month end\r\n    if ((Dates.getDuration(this.dateRange.start, this.dateRange.end).days() === 14)\r\n      || (Dates.getDay(this.dateRange.start) === 15 && this.dateRange.end === Dates.startEnd(this.dateRange.start,\"end-month\"))\r\n      || (Dates.getDay(this.dateRange.start) === 16 && this.dateRange.end === Dates.startEnd(this.dateRange.start,\"end-month\"))) {\r\n      return \"monthHalf\";\r\n    }\r\n    return \"other\";\r\n  }\r\n\r\n  public set periodShortcut(value: \"monthCurrent\" | \"monthLast\" | \"monthOther\" | \"weeks2\" | \"monthHalf\" | \"other\") {\r\n    this.periodStartDateError = null;\r\n    switch (value) {\r\n      case \"monthCurrent\":\r\n        this.dateRange.start = Dates.startEnd(\"today\",\"start-month\");\r\n        this.dateRange.end = Dates.startEnd(\"today\",\"end-month\");\r\n        break;\r\n      case \"monthOther\":\r\n        if (Dates.getDay(\"today\") === 1) {\r\n          // Move to tomorrow so that the selection is monthOther and not monthCurrent.\r\n          this.dateRange.start = Dates.add(\"today\",1,\"day\");\r\n        } else {\r\n          this.dateRange.start = Dates.asDate(\"today\");\r\n        }\r\n        this.dateRange.end = Dates.add(Dates.add(this.dateRange.start,1,\"month\"),-1,\"day\");\r\n        break;\r\n      case \"monthLast\":\r\n        this.dateRange.start = Dates.add(Dates.startEnd(\"today\",\"start-month\"),-1,\"month\");\r\n        this.dateRange.end = Dates.startEnd(this.dateRange.start,\"end-month\");\r\n        break;\r\n      case \"weeks2\": //TODO Review this\r\n        this.dateRange.start = Dates.add(Dates.startEnd(\"today\",\"start-week\"),-2,\"week\"); //shift to start of current week, and then 2 weeks before\r\n        this.dateRange.end = Dates.add(Dates.startEnd(\"today\",\"start-week\"),-1,\"day\"); //shift to last day of previous week.\r\n        break;\r\n      case \"monthHalf\":\r\n        if (Dates.getDay(\"today\") < 16) {\r\n          // 16 - (28,29,30,31)\r\n          this.dateRange.start = Dates.add(Dates.add(Dates.startEnd(\"today\", \"start-month\"),-1,\"month\"),15,\"day\");\r\n          this.dateRange.end = Dates.startEnd(this.dateRange.start,\"end-month\");\r\n        } else {\r\n          // 1 - 15\r\n          this.dateRange.start = Dates.startEnd(\"today\",\"start-month\");\r\n          this.dateRange.end = Dates.add(this.dateRange.start,14,\"day\");\r\n        }\r\n        break;\r\n      case \"other\":\r\n        this.dateRange.start = Dates.add(\"today\",-1,\"day\");\r\n        this.dateRange.end = Dates.asDate(\"today\");\r\n        break;\r\n    }\r\n    this.dateRange = Dates.getDateRange(this.dateRange.start, this.dateRange.end);\r\n    this.dateRangeChange();\r\n  }\r\n\r\n  /**\r\n   * Submit the data in the Worktime (period) dialog.\r\n   */\r\n  public submitWorktime() {\r\n    const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.CalcWorktimeComponent.submitWorktimeTitle\");\r\n      angular.copy(this.worktime, this.calc.worktime);\r\n      this.calcApi.recalculateWorktime(this.calc).then((result) => {\r\n        angular.copy(result, this.calc);\r\n        angular.copy(this.calc.worktime, this.worktime);\r\n        loader.dismiss();\r\n        new CalculatorSections(this.currentCalc).setActive(\"salary\");\r\n    });\r\n  }\r\n\r\n  /** Returns true if the current worktime data seems to have holidays or absences to add as rows in the salary calculation.  */\r\n  public hasHolidaysOrAbsences() {\r\n\r\n    return this.worktime?.holidaySpec?.code === HolidayCode.HolidayCompensation\r\n      || this.worktime?.holidaySpec?.code === HolidayCode.HolidayCompensationIncluded\r\n      || (this.worktime?.absencesPeriods ?? []).length > 0\r\n      ;\r\n  }\r\n\r\n  /**\r\n   * Returns the logic for the worktime data related lists\r\n   * @returns Logic object for the lists.\r\n   */\r\n  public getLogicForLists(): any {\r\n    const logic = {\r\n      getAbcencesForPeriod: () => {\r\n        return this.worktime.absencesPeriods.filter(x => x.causeCode != AbsenceCauseCode.AnnualLeave);\r\n      },\r\n      getAbcensePeriodsTotalDays: (type: \"all\" | \"absencesPaid\" | \"absencesUnpaid\" | \"absencesHolidayAccrual\" | \"absencesNoHolidayAccrual\" = \"all\") => {\r\n        const list = logic.getAbcencesForPeriod();\r\n        switch (type) {\r\n          case \"all\":\r\n            return Arrays.sum(list, (x) => x.period.daysCount);\r\n          case \"absencesPaid\":\r\n            return Arrays.sum(list.filter((x) => x.isPaid), (x) => x.period.daysCount);\r\n          case \"absencesUnpaid\":\r\n            return Arrays.sum(list.filter((x) => !x.isPaid), (x) => x.period.daysCount);\r\n          case \"absencesHolidayAccrual\":\r\n            return Arrays.sum(list.filter((x) => x.isHolidayAccrual), (x) => x.period.daysCount);\r\n          case \"absencesNoHolidayAccrual\":\r\n            return Arrays.sum(list.filter((x) => !x.isHolidayAccrual), (x) => x.period.daysCount);\r\n        }\r\n      },\r\n      getAnnualLeavesForPeriod: () => {\r\n        return this.worktime.absencesPeriods.filter(x => x.causeCode == AbsenceCauseCode.AnnualLeave);\r\n      },\r\n      getAnnualLeaveDescription: (row: AnnualLeave) => {\r\n        if (row.notes) {\r\n          return row.notes;\r\n        }\r\n        return row.period.start < `${Dates.getYear(this.worktime.workDays.start)}-10-1` ? Translations.get(\"SALAXY.NG1.CalcWorktimeComponent.lists.annualLeaves.summerHoliday\") : Translations.get(\"SALAXY.NG1.CalcWorktimeComponent.lists.annualLeaves.winterHoliday\");\r\n      },\r\n      getAnnualLeavesTotalDays: () => {\r\n        const list = logic.getAnnualLeavesForPeriod();\r\n        return Arrays.sum(list, (x) => x.period.daysCount);\r\n      },\r\n      getAnnualLeavesBonusDays: () => {\r\n        const list = logic.getAnnualLeavesForPeriod();\r\n        return Arrays.sum(list, (x) => x.bonusDaysCount ?? 0);\r\n      },\r\n      getholidayPayCalculationOptions:(): InputEnumOption[] => {\r\n        return this.uiHelpers.cache(this, \"holidayPayCalculationOptions\", () => {\r\n          switch (this.worktime.holidaySpec?.code) {\r\n            case HolidayCode.Permanent14Days:\r\n              if(this.worktime.holidaySpec?.wageBasis === WageBasis.Monthly) {\r\n                return [\r\n                  {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.normalMonthlyPay.label\"), value: HolidayPayCalculation.NormalMonthlyPay},\r\n                  {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.otherPay.label\"), value: HolidayPayCalculation.OtherPay},\r\n                  ...(this.sessionService.isInRole(\"bizConfigs\") ? [{text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.scriptPay.label\"), value: HolidayPayCalculation.ScriptPay}] : []),\r\n                ];\r\n              } else {\r\n                return [\r\n                  {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.averageDailyPay.label\"), value: HolidayPayCalculation.AverageDailyPay},\r\n                  {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.averageHourlyPay.label\"), value: HolidayPayCalculation.AverageHourlyPay},\r\n                  {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.otherPay.label\"), value: HolidayPayCalculation.OtherPay},\r\n                  ...(this.sessionService.isInRole(\"bizConfigs\") ? [{text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.scriptPay.label\"), value: HolidayPayCalculation.ScriptPay}] : []),\r\n                ];\r\n              }\r\n            case HolidayCode.Permanent35Hours:\r\n              if(this.worktime.holidaySpec?.wageBasis === WageBasis.Monthly) {\r\n                return [\r\n                  {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.normalMonthlyPay.label\"), value: HolidayPayCalculation.NormalMonthlyPay},\r\n                  {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.percentageBasedPay.label\"), value: HolidayPayCalculation.PercentageBasedPay},\r\n                  {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.otherPay.label\"), value: HolidayPayCalculation.OtherPay},\r\n                  ...(this.sessionService.isInRole(\"bizConfigs\") ? [{text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.scriptPay.label\"), value: HolidayPayCalculation.ScriptPay}] : []),\r\n                ];\r\n              } else {\r\n                return [\r\n                  {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.percentageBasedPay.label\"), value: HolidayPayCalculation.PercentageBasedPay},\r\n                  {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.otherPay.label\"), value: HolidayPayCalculation.OtherPay},\r\n                  ...(this.sessionService.isInRole(\"bizConfigs\") ? [{text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.scriptPay.label\"), value: HolidayPayCalculation.ScriptPay}] : []),\r\n                ];\r\n              }\r\n            case HolidayCode.TemporaryTimeOff:\r\n              if(this.worktime.holidaySpec?.wageBasis === WageBasis.Monthly || this.worktime.holidaySpec?.wageBasis === WageBasis.PerformanceBased || this.worktime.holidaySpec?.wageBasis === WageBasis.Hourly) {\r\n                return [\r\n                  {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.holidayCompensation.label\"), value: HolidayPayCalculation.HolidayCompensation},\r\n                  {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.otherPay.label\"), value: HolidayPayCalculation.OtherPay},\r\n                  ...(this.sessionService.isInRole(\"bizConfigs\") ? [{text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.scriptPay.label\"), value: HolidayPayCalculation.ScriptPay}] : []),\r\n                ];\r\n              }\r\n              break;\r\n              case HolidayCode.Other:\r\n              case HolidayCode.Script:\r\n                if(this.worktime.holidaySpec?.wageBasis === WageBasis.Monthly) {\r\n                  return [\r\n                    {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.normalMonthlyPay.label\"), value: HolidayPayCalculation.NormalMonthlyPay},\r\n                    {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.percentageBasedPay.label\"), value: HolidayPayCalculation.PercentageBasedPay},\r\n                    {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.holidayCompensation.label\"), value: HolidayPayCalculation.HolidayCompensation},\r\n                    {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.otherPay.label\"), value: HolidayPayCalculation.OtherPay},\r\n                    ...(this.sessionService.isInRole(\"bizConfigs\") ? [{text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.scriptPay.label\"), value: HolidayPayCalculation.ScriptPay}] : []),\r\n                  ];\r\n                } else {\r\n                  return [\r\n                    {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.averageDailyPay.label\"), value: HolidayPayCalculation.AverageDailyPay},\r\n                    {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.averageHourlyPay.label\"), value: HolidayPayCalculation.AverageHourlyPay},\r\n                    {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.percentageBasedPay.label\"), value: HolidayPayCalculation.PercentageBasedPay},\r\n                    {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.holidayCompensation.label\"), value: HolidayPayCalculation.HolidayCompensation},\r\n                    {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.otherPay.label\"), value: HolidayPayCalculation.OtherPay},\r\n                    ...(this.sessionService.isInRole(\"bizConfigs\") ? [{text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.scriptPay.label\"), value: HolidayPayCalculation.ScriptPay}] : []),\r\n                  ];\r\n                }\r\n                break;\r\n            default:\r\n              return [];\r\n          }\r\n        });\r\n      }\r\n    };\r\n    return logic;\r\n  }\r\n\r\n  /** Shows the pro-dialog */\r\n  public showPeriodDetails() {\r\n    const detailsModel = {\r\n      worktime: this.worktime,\r\n      logic: this.getLogicForLists()\r\n    };\r\n    this.uiHelpers.showDialog(\"salaxy-components/calc/details/worktime-pro.html\", null, detailsModel, null, \"lg\");\r\n  }\r\n\r\n  /**\r\n   * Gets the status for the current holidays and absences fetching.\r\n   * These are fetched from the server when the period and / or worker changes.\r\n   */\r\n  public getHolidaysStatus(): \"noWorker\" | \"noPeriod\" | \"loading\" | \"ok\" {\r\n    if (!this.currentCalc.worker?.employmentId && this.sessionService.isAuthenticated) {\r\n      return \"noWorker\";\r\n    }\r\n    if (!this.currentCalc.info.workStartDate || !(this.currentCalc.framework.numberOfDays > 0)) {\r\n      return \"noPeriod\";\r\n    }\r\n    return this.worktime?.holidaySpec == null ? \"loading\" : \"ok\";\r\n  }\r\n\r\n  /**\r\n   * Gets the monthly text for calendar month for accruals.\r\n   * @param type Type of the text is either header or description.\r\n   */\r\n  public getAccrualMonthText(type: \"header\" | \"description\", month: MonthlyHolidayAccrual) {\r\n    if (type === \"header\") {\r\n      (month as any) = Dates.getMonth(month.month);\r\n    }\r\n    switch (type) {\r\n      case \"header\":\r\n        return month ? Translations.get(`SALAXY.ENUM.CalendarMonth.month${month}.label`) : \"#err month\";\r\n      case \"description\": {\r\n        switch (this.worktime.accrualSpec.code) {\r\n          case HolidayCode.Permanent14Days:\r\n            return \"SALAXY.NG1.CalcWorktimeComponent.getAccrualMonthText.permanent14Days\";\r\n          case HolidayCode.Permanent35Hours:\r\n            return \"SALAXY.NG1.CalcWorktimeComponent.getAccrualMonthText.permanent35Hours\";\r\n          case HolidayCode.TemporaryTimeOff:\r\n            return \"SALAXY.NG1.CalcWorktimeComponent.getAccrualMonthText.temporaryTimeOff\";\r\n          case HolidayCode.Other:\r\n            return \"SALAXY.NG1.CalcWorktimeComponent.getAccrualMonthText.other\";\r\n          case HolidayCode.Script:\r\n            return \"SALAXY.NG1.CalcWorktimeComponent.getAccrualMonthText.script\";\r\n          default:\r\n            return \"SALAXY.NG1.CalcWorktimeComponent.getAccrualMonthText.default\";\r\n        }\r\n      }\r\n    }\r\n    return \"#err \" + type;\r\n  }\r\n\r\n  /**\r\n   * Gets the accrual explanation text. This is currently not in use.\r\n   * TODO: translate\r\n   */\r\n  public getAccrualText(monthlyAccrual: MonthlyHolidayAccrual): string {\r\n    if (this.worktime.accrualSpec.code === HolidayCode.Permanent14Days) {\r\n      if (monthlyAccrual.workDays < 14) {\r\n        return `${monthlyAccrual.workDays} pv < 14 pv => Ei lomakertymää.`;\r\n      } else {\r\n        return `${monthlyAccrual.workDays} pv > 14 pv => Lomakertymä ${monthlyAccrual.daysAccrued} pv.`;\r\n      }\r\n    } else if (this.worktime.accrualSpec.code === HolidayCode.Permanent35Hours) {\r\n      if (monthlyAccrual.workHours == null) {\r\n        return `Ei tietoa tunneista, oletus yli 35h => Lomakertymä ${monthlyAccrual.daysAccrued} pv.`;\r\n      } else if (monthlyAccrual.workHours < 35) {\r\n        return `${monthlyAccrual.workHours} h < 35 h => Ei lomakertymää.`;\r\n      } else {\r\n        return `${monthlyAccrual.workHours} h > 35 h => Lomakertymä ${monthlyAccrual.daysAccrued} pv.`;\r\n      }\r\n    } else if (this.worktime.accrualSpec.code === HolidayCode.TemporaryTimeOff) {\r\n      return `Vapaan ansaintasäännössä lomapäivien kertymä on aina ${monthlyAccrual.daysAccrued} pv / kalenterikuukausi.`;\r\n    } else if (this.worktime.accrualSpec.code === HolidayCode.Other) {\r\n      return Translations.get(\"SALAXY.ENUM.HolidayCode.other.description\");\r\n    } else if (this.worktime.accrualSpec.code === HolidayCode.Script) {\r\n      return Translations.get(\"SALAXY.ENUM.HolidayCode.script.description\");\r\n    } else {\r\n      return \"Ei lomapäivien kertymää.\";\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Opens the dialog for editing calculation payments\r\n   */\r\n  public openCalcLeavesDialog(): void {\r\n    const logic = {calc: this.currentCalc, worktime: this.worktime};\r\n    this.uiHelpers.openEditDialog(\"salaxy-components/modals/calc/CalcLeaves.html\", logic, null, \"lg\").then(dialogResult => {\r\n      if (dialogResult.result) {\r\n        this.worktime.absencesPeriods = dialogResult.result.absencesPeriods;\r\n      }\r\n    });\r\n  }\r\n\r\n  /** Checks if the period has changed and if so resets the demo data. */\r\n  public checkDemoData(): void {\r\n    if (\r\n      this.currentCalc.info.workStartDate == this.demoData.startDate && this.currentCalc.info.workEndDate == this.demoData.endDate) {\r\n      return;\r\n    }\r\n    let holiday = null;\r\n    let absenceDay = null;\r\n    if (this.currentCalc.info.workStartDate && this.currentCalc.info.workEndDate) {\r\n        const workdays = Dates.getWorkdays(this.currentCalc.info.workStartDate, this.currentCalc.info.workEndDate);\r\n        if (workdays.length > 5) {\r\n          holiday = workdays[Math.round(workdays.length / 2)];\r\n          absenceDay = workdays[Math.round(workdays.length / 2) + 1];\r\n        }\r\n    }\r\n    this.demoData = this.demoData || {} as any;\r\n    this.demoData.startDate = this.currentCalc.info.workStartDate;\r\n    this.demoData.endDate = this.currentCalc.info.workEndDate;\r\n\r\n    if (!holiday) {\r\n      this.demoData.holidays = null;\r\n      this.demoData.absences = null;\r\n      return;\r\n    }\r\n    this.demoData.holidays = {\r\n      year: Dates.getYear(holiday),\r\n      employmentId: null,\r\n      spec: {\r\n        wageBasis: WageBasis.Monthly,\r\n      }\r\n    };\r\n    this.demoData.absences = {\r\n      employmentId: null,\r\n      periods: [\r\n        {\r\n          causeCode: AbsenceCauseCode.Illness,\r\n          notes: \"Poissaolo demodatassa\",\r\n          period: {\r\n            start: absenceDay,\r\n            end: absenceDay,\r\n            daysCount: 1,\r\n            days: absenceDay,\r\n          },\r\n        }\r\n      ]\r\n    };\r\n  }\r\n\r\n  private initDateRanges() {\r\n    const currentMonth = Dates.getMonth(Dates.getToday());\r\n    this.periodShortcuts = {\r\n      monthCurrent: Translations.get(`SALAXY.ENUM.CalendarMonth.month${currentMonth}.label`),\r\n      monthLast: Translations.get(`SALAXY.ENUM.CalendarMonth.month${currentMonth === 1 ? 12 : (currentMonth - 1)}.label`),\r\n      monthOther: Translations.get(\"SALAXY.NG1.DateRange.otherMonth\"),\r\n      // monthMulti: \"Monta kuukautta\",\r\n      weeks2: Translations.get(\"SALAXY.UI_Terms.week2\"),\r\n      monthHalf: Translations.get(\"SALAXY.UI_Terms.monthHalf\"),\r\n      other: Translations.get(\"SALAXY.UI_Terms.otherPeriod\"),\r\n    };\r\n    this._periodStartDate = Dates.format(this.dateRange.start, \"D.M.\", null);\r\n  }\r\n\r\n  /** Programmatic tab change via a UI link text. */\r\n  public changeTab(tabId: string) {\r\n    const tabButton = document.querySelector(`#tabs-buttons-calcWorktime #${tabId}-tab-button`) as HTMLElement;\r\n    tabButton ? tabButton.click() : \"\";\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { CostAccountingDimensionDefinition, CostAccountingDimension, CostAccountingDimensionScope, UserDefinedRow } from \"@salaxy/core\";\r\nimport { UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Controller for handling row dimension input in the CalcRowsEditor.\r\n */\r\nexport class CalcRowDimensionInputController implements angular.IController {\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"UiHelpers\"];\r\n\r\n  /** Currently edited row */\r\n  public row: UserDefinedRow;\r\n  /** Current dimension defition */\r\n  public definition: CostAccountingDimensionDefinition;\r\n  /** Possible upper level (e.g. calculation) dimensions that are inherited */\r\n  private _inherited: CostAccountingDimension[];\r\n  /** Bindable read-only */\r\n  public readOnly?: boolean;\r\n  /**\r\n   * Style of inputs.\r\n   * If null or empty, displays normal input.\r\n   * - \"openeClose\" shows readOnly-like input with toggle button to open the field for editing.\r\n   */\r\n  public inputMode: \"\" | \"openClose\";\r\n\r\n  private _options: Array<{\r\n    /** Option value. */\r\n    value: any,\r\n    /** Option text.  */\r\n    text: string,\r\n    /** Option description. */\r\n    title?: string,\r\n  }>= [];\r\n\r\n  private _newDimensions: CostAccountingDimension[] = [];\r\n\r\n  constructor(\r\n    private uiHelpers: UiHelpers\r\n  ) {\r\n    // Dependency injection\r\n  }\r\n\r\n  /** Copy of inherited dimensions */\r\n  public get inherited(): CostAccountingDimension[] {\r\n    return this._inherited;\r\n  }\r\n\r\n  /** Copy of inherited dimensions */\r\n  public set inherited(value: CostAccountingDimension[])  {\r\n    this._inherited = angular.copy(value);\r\n  }\r\n\r\n  /**\r\n   * Returns true if the dimension values are inherited.\r\n   */\r\n  public isInherited(): boolean {\r\n    if(!this.row.accounting.dimensions.some((x) => x.id === this.definition.id && !!x.value)) {\r\n      return !!this.cleanDimensions(this.inherited)?.some((x) => x.id === this.definition.id);\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /**\r\n   * Determines if cost sharing is enabled based on the current definition.\r\n   * @returns {boolean} True if cost sharing is allowed, otherwise false.\r\n   */\r\n  public isCostSharingEnabled(): boolean {\r\n    const dimensionIds = this.row.accounting.dimensions.map(d => d.id);\r\n    if(dimensionIds.length !== new Set(dimensionIds).size) {\r\n      return true;\r\n    }\r\n    return this.definition.allowCostSharing;\r\n  }\r\n\r\n  /**\r\n   * Retrieves the cost sharing values for the current row dimension.\r\n   * This method uses a caching mechanism to store the computed values for performance optimization. It truncates the text values to a maximum of 10 characters, appending \"...\" if the text exceeds this length\r\n   * If the dimension is inherited, it filters and maps the inherited dimensions to the required format. Otherwise, it uses the current row's accounting dimensions.\r\n   */\r\n  public getCostSharingValues(): {text: string, value: number}[] {\r\n    return this.uiHelpers.cache(this, \"costSharingValues\", () => {\r\n      const truncate = (text: string | undefined): string => {\r\n        if (!text) {\r\n          return \"\";\r\n        }\r\n        if (text?.length <= 10) {\r\n          return text;\r\n        }\r\n        return text?.substring(0, 10) + \"...\";\r\n      };\r\n      if(this.isInherited()) {\r\n        return this.cleanDimensions(this.inherited).filter((x) => x.id === this.definition.id).map((x) => ({ text: truncate(this.definition.options.find(option => option.value === x.value).value), value: x.percent ?? 0 }));\r\n      } else {\r\n        return this.row.accounting.dimensions.filter((x) => x.id === this.definition.id).map((x) => ({ text: truncate(this.definition.options.find(option => option.value === x.value).value), value: x.percent ?? 0 }));\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Returns inherited single value.\r\n   */\r\n  public getInheritedSingleValue(): CostAccountingDimension | undefined {\r\n    return (this.cleanDimensions(this.inherited) ?? []).find((x) => x.id === this.definition.id);\r\n  }\r\n\r\n  /**\r\n   * Sets single value.\r\n   */\r\n  public setSingleValue(value: any) {\r\n    const singleValue = this.row.accounting.dimensions?.find((x) => x.id === this.definition.id);\r\n    if (singleValue) {\r\n      singleValue.value = value;\r\n    } else {\r\n      this.row.accounting.dimensions.push({ id: this.definition.id, value });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Returns single value.\r\n   */\r\n  public getSingleValue() {\r\n    let singleValue = this.row.accounting.dimensions?.find((x) => x.id === this.definition.id) ?? this._newDimensions.find((x) => x.id === this.definition.id);\r\n    if (!singleValue && !this.readOnly) {\r\n      singleValue = { id: this.definition.id };\r\n      this._newDimensions.push(singleValue);\r\n    }\r\n\r\n    return singleValue;\r\n  }\r\n\r\n  /**\r\n   * Returns true if options exists for the dimension.\r\n   * @returns True, if an option exists for the value.\r\n   */\r\n  public hasOptions(): boolean {\r\n    const opts = this.getOptions();\r\n    return opts.filter(x => x.value).length > 0;\r\n  }\r\n\r\n  /**\r\n   * Returns available options for dimension.\r\n   */\r\n  public getOptions() {\r\n    if (!this._options) {\r\n      this._options = [];\r\n    }\r\n\r\n    let newOptions = [];\r\n\r\n    if (this.definition) {\r\n      newOptions = this.definition.options.filter((x) =>\r\n        x.scope !== CostAccountingDimensionScope.Hidden &&\r\n        (\r\n          // show if scope definition for dimension not given\r\n          ( !x.scope || x.scope === CostAccountingDimensionScope.None) ||\r\n          // or this scope\r\n          (CostAccountingDimensionScope.Row === x.scope)\r\n        )\r\n      )\r\n      .map( (x) => ({ value: x.value, text: x.text }));\r\n    }\r\n\r\n    this.modifyOptions(newOptions, this._options);\r\n    return this._options;\r\n  }\r\n\r\n  private cleanDimensions(dimensions: CostAccountingDimension[]) {\r\n    if (!dimensions) {\r\n      return dimensions;\r\n    }\r\n    const cleaned = dimensions.filter(x => x?.value && x?.id);\r\n    return cleaned;\r\n  }\r\n\r\n  private modifyOptions(\r\n    source: any[],\r\n    target: any[]) {\r\n    if (angular.equals(source, target)) {\r\n      return;\r\n    }\r\n    target.splice(0, target.length);\r\n    target.push(...source);\r\n  }\r\n}","import angular from \"angular\";\r\nimport { UserDefinedRow, Configs, RowsUsecaseLogic } from \"@salaxy/core\";\r\n\r\nimport {\r\n  UiHelpers,\r\n} from \"../../services\";\r\n\r\n/**\r\n * Interface representing the structure of row type documentation\r\n * @interface RowTypeDocumentation\r\n */\r\ninterface RowTypeDocumentation {\r\n  /** The type identifier for the row */\r\n  type: string;\r\n  /** Optional description of the row type */\r\n  description?: string;\r\n  /** Optional array of sample configurations */\r\n  samples?: Array<{\r\n    /** Description of the sample */\r\n    description: string;\r\n    /** The specific kind/variant of the sample */\r\n    kind: string;\r\n    /** Code sample */\r\n    code: string;\r\n  }>;\r\n}\r\n\r\n/**\r\n * Controller responsible for handling the documentation of calculation rows.\r\n * Implements the Angular IController interface.\r\n */\r\nexport class CalcRowDocumentationController implements angular.IController {\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"UiHelpers\",\r\n    \"$timeout\",\r\n  ];\r\n\r\n  /** Currently edited row */\r\n  public row: UserDefinedRow;\r\n\r\n  /**\r\n   * An object that holds example data for the CalcRowDocumentationController.\r\n   */\r\n  public allExamples: RowTypeDocumentation[] = [];\r\n\r\n  public selectedKind: string;\r\n\r\n  private _isLoading: boolean;\r\n\r\n  public tabOptions: { value: string; text: number }[] = [];\r\n\r\n  /**\r\n   * Constructor to initialize the controller with dependencies.\r\n   * @param uiHelpers - Helper utilities for UI operations.\r\n   * @param $timeout - Angular's timeout service.\r\n   */\r\n  constructor(private uiHelpers: UiHelpers, private $timeout: angular.ITimeoutService) {}\r\n\r\n  /**\r\n   * Lifecycle hook that is called after the controller's data-bound properties have been initialized.\r\n   * Fetches example data from the CDN and updates the loading state.\r\n   */\r\n  public $onInit() {\r\n    this._isLoading = true;\r\n    this.fetchExamplesFromCdn().then(result => {\r\n      this.allExamples = result;\r\n      this.generateExampleLocally();\r\n      this._isLoading = false;\r\n      this.$timeout();\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Determines if the loader should be displayed.\r\n   * @returns {boolean} True if the loader should be shown, false otherwise.\r\n   */\r\n  public showLoader(): boolean {\r\n    return this._isLoading;\r\n  }\r\n\r\n  /**\r\n   * Fetches a file from the CDN.\r\n   */\r\n  public async fetchExamplesFromCdn(): Promise<RowTypeDocumentation[]> {\r\n    const examplesCdnUrl = Configs.current.isTestData ? \"https://cdn.salaxy.com/docs/row-types/samples/test/examples.json\" : \"https://cdn.salaxy.com/docs/row-types/samples/prod/examples.json\";\r\n    try {\r\n      const response = await fetch(examplesCdnUrl);\r\n      if (!response.ok) {\r\n        console.error(`HTTP error! status: ${response.status}`);\r\n      }\r\n      const data = await response.json();\r\n      return data.examples;\r\n    } catch (error) {\r\n      console.error(\"Error fetching file from CDN:\", error);\r\n      return [];\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Gets the description text for the current example type.\r\n   */\r\n  public get example() {\r\n    return this.allExamples?.find(x => x.type === (this.row as any)?.config.type);\r\n  }\r\n\r\n  /**\r\n   * Generates a local example for the current row type and selected kind.\r\n   * This method:\r\n   * 1. Checks if there is a valid row to generate an example for\r\n   * 2. Determines if the row has a kind configuration\r\n   * 3. If conditions are met:\r\n   * - Finds or creates an example for the current row type\r\n   * - Removes any existing generated examples\r\n   * - Creates a new sample with generated code\r\n   * - Adds the sample to the examples collection\r\n   * 4. Triggers Angular digest cycle via $timeout\r\n   */\r\n  public generateExampleLocally() {\r\n    if (!this.row) {\r\n      return;\r\n    }\r\n    const rowConfig = (this.row as any).config;\r\n    const rowType = rowConfig.type;\r\n    const hasKind = rowConfig?.kind?.name;\r\n\r\n    if (!hasKind && !this.selectedKind || hasKind && this.selectedKind) {\r\n      const example = this.allExamples.find(x => x.type === rowType);\r\n      if (example) {\r\n        example.samples = example.samples.filter(x => x.description !== \"Generated example\");\r\n      }\r\n      const newSample = {\r\n        code: this.generateCodeExample(),\r\n        description: \"Generated example\",\r\n        kind: hasKind ? this.selectedKind : null\r\n      };\r\n\r\n      if (example) {\r\n        example.samples.push(newSample);\r\n      } else {\r\n        const description = `Examples for ${this.row.rowType}`;\r\n\r\n        this.allExamples.push({\r\n          type: rowType,\r\n          description,\r\n          samples: [newSample]\r\n        });\r\n      }\r\n    }\r\n    this.$timeout();\r\n  }\r\n\r\n  /**\r\n   * Gets the code samples for the current row type and kind.\r\n   * Results are cached based on the type and kind combination.\r\n   */\r\n  public get exampleSamples() {\r\n    return this.uiHelpers.cache(this, \"exampleSamples\", () => {\r\n      this.tabOptions = [];\r\n      const example = this.allExamples.find(x => x.type === (this.row as any)?.config.type);\r\n      const hasKind = (this.row as any).config?.kind?.name;\r\n      if (hasKind && !this.selectedKind) {\r\n        return [];\r\n      }\r\n\r\n      const filteredSamples = example?.samples?.filter(x => !hasKind || x.kind === this.selectedKind) ?? [];\r\n      for (let i = 1; i < filteredSamples.length+1; i++) {\r\n        this.tabOptions.push({ value: \"tab\" + i, text: i });\r\n      }\r\n\r\n      return filteredSamples;\r\n    }, () => `${(this.row as any)?.config.type}-${this.selectedKind}`);\r\n  }\r\n\r\n  private generateCodeExample(): string {\r\n    const rowConfig = (this.row as any).config;\r\n    const hasKind = rowConfig?.kind?.name;\r\n    if (!hasKind) {\r\n      return `import {CalculatorLogic, CalculationRowType, RowsUsecaseLogic} from \"@salaxy/core\"; \\n//Make an entry for row\\nconst row = RowsUsecaseLogic.getBlankUsecaseRow(CalculationRowType.${this.row.rowType.substr(0, 1).toUpperCase() + this.row.rowType.substr(1)});\\n// Add created row to new calculation\\nconst calculation = CalculatorLogic.getBlank();\\ncalculation.rows.push(row);`;\r\n    } else {\r\n      const data = RowsUsecaseLogic.getUsecaseExampleData(this.row.rowType as any, this.selectedKind);\r\n      const dataWithoutKind = Object.assign({}, data);\r\n      delete dataWithoutKind.kind;\r\n      const dataString = JSON.stringify(dataWithoutKind, null, 2).replace(/^{/, \"{\\n  \\\"kind\\\": \" + rowConfig.kind.name + \".\" + this.selectedKind.substr(0, 1).toUpperCase() + this.selectedKind.substr(1) + \",\");\r\n      return `import {CalculatorLogic, CalculationRowType, RowsUsecaseLogic, ${rowConfig.kind.name}} from \"@salaxy/core\"; \\n//Make an entry for row\\nconst row = RowsUsecaseLogic.getBlankUsecaseRow(CalculationRowType.${this.row.rowType.substr(0, 1).toUpperCase() + this.row.rowType.substr(1)});\\nrow.data = ${dataString} \\n// Add created row to new calculation\\nconst calculation = CalculatorLogic.getBlank();\\ncalculation.rows.push(row);`;\r\n    }\r\n  }\r\n}","import angular from \"angular\";\r\n\r\nimport {\r\n  AccountingTargets,\r\n  CalcRowConfig,\r\n  CalcRowsLogic,\r\n  Calculation,\r\n  Calculations,\r\n  CalculationRowType,\r\n  CalculatorLogic,\r\n  Dates,\r\n  EnumerationsLogic,\r\n  IncomeTypesLogic,\r\n  Numeric,\r\n  RowsUsecaseLogic,\r\n  UserDefinedRow,\r\n  YearlyChangingNumbers,\r\n  Years,\r\n  IncomeTypeMetadata,\r\n  BaseUsecaseLogic,\r\n  InputEnumOption,\r\n  MilageOwnCarUsecaseLogic,\r\n  Translations,\r\n  UserDefinedRowLogic,\r\n  CalculationRowUnit,\r\n  WorktimeImportRow,\r\n  Arrays,\r\n  CostAccountingDimensionDefinition,\r\n  CostAccountingDimensionScope,\r\n  CalculationRowSource\r\n} from \"@salaxy/core\";\r\n\r\nimport {\r\n  EditDialogParameters,\r\n  RowTypeService,\r\n  SessionService,\r\n  UiHelpers,\r\n} from \"../../services\";\r\n\r\nimport { ListControllerBase, ListControllerBaseBindings } from \"../bases\";\r\n\r\nclass CalcRows2019ControllerBindings extends ListControllerBaseBindings {\r\n  /** Sets the title in the table header. */\r\n  public title = \"@\";\r\n\r\n  /** Shows edit buttons. Used in Payroll. */\r\n  public showEditButtons = \"<\";\r\n\r\n  /** Shows gross totals and total payment in table footer */\r\n  public showGrossTotals = \"<\";\r\n\r\n  /**\r\n   * Alternative binding for parent: Give just a stand-alone rows list.\r\n   * Setting the row to an array will set these rows to the parent component\r\n   * or create a new parent component if no parent component is specified.\r\n   */\r\n  public rows = \"<\";\r\n\r\n  /** If set, filters the rows based on categories (plus rowTypes if set) */\r\n  public categories = \"<\";\r\n\r\n  /** If set, filters the rows based on statuses (Worktime rows only) */\r\n  public statuses = \"<\";\r\n\r\n  /**\r\n   * Defines the helper texts and branding color for row type selection list dialog.\r\n   * Null for default \"primary\" (no texts)\r\n   */\r\n  public rowTypeSelectHelp = \"@\";\r\n\r\n  /** If set, shows only these types (plus categories if set) */\r\n  public rowTypes = \"<\";\r\n\r\n  /**\r\n   * If set, shows only these sources in the source drop-down.\r\n   * This is a comma separated list of enum values.\r\n   */\r\n  public rowSources = \"@\";\r\n\r\n  /**\r\n   * Optional CostAccountingDimensionDefinitions\r\n   * If not set, cost accounting dimensions and their options are read from the settings.\r\n   */\r\n  public dimensions = \"<\";\r\n\r\n  /**\r\n   * User interface type of the editor: \"default\" is the one used in calculators.\r\n   * \"worktime-import\" is used in editing worktime import (contains employment relation).\r\n   * \"worktime-import-employment\" is used in editing worktime import (no employment, contains period).\r\n   * \"salary-defaults\" is used behind empoloyment to specify defaults (also in the settings).\r\n   */\r\n  public type = \"@\";\r\n\r\n  /** Hides final cost row. */\r\n  public hideFinalCostRow = \"<\";\r\n\r\n  /**\r\n   * Propertieds and logic for the situation where the dialog is dispalyed as part of row type definition editor.\r\n   */\r\n  public definitionEditor = \"<\";\r\n\r\n  /** Default dimension id to show in rows editor */\r\n  public defaultDimension = \"@\";\r\n\r\n  /** Count of dimension to show in editor */\r\n  public dimensionCount = \"<\";\r\n\r\n  /** In supported modes, shows the rows selection checkboxes */\r\n  public showRowSelection = \"<\";\r\n}\r\n\r\n/**\r\n * Editor for Calculation rows / usecases.\r\n * Can be bound to a Calculation or to Employment relation.\r\n */\r\nexport class CalcRows2019Controller extends ListControllerBase<\r\n  Calculation,\r\n  WorktimeImportRow\r\n> {\r\n  /** Bindings for components that use this controller */\r\n  public static bindings = new CalcRows2019ControllerBindings();\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"UiHelpers\",\r\n    \"$timeout\",\r\n    \"SessionService\",\r\n    \"EditDialogParameters\",\r\n    \"$element\",\r\n    \"RowTypeService\",\r\n    \"AccountingTargets\",\r\n    \"Calculations\"\r\n  ];\r\n\r\n  /** New empty row for databinding when creating a new row. */\r\n  public newRow: UserDefinedRow;\r\n\r\n  /** Currently selected row in 2022 UI. */\r\n  public current: UserDefinedRow;\r\n\r\n  /** Title in the Table header */\r\n  public title: string;\r\n\r\n  /** Shows edit buttons. Used in Payroll. */\r\n  public showEditButtons: boolean;\r\n\r\n  /** Shows gross totals and total payment in table footer */\r\n  public showGrossTotals: boolean;\r\n\r\n  /**\r\n   * Alternative binding for parent: Give just a stand-alone rows list.\r\n   * Setting the row to an array will set these rows to the parent component\r\n   * or create a new parent component if no parent component is specified.\r\n   * The resolving occures in list get, so the order of setting is not an issue.\r\n   */\r\n  public rows: UserDefinedRow[];\r\n\r\n  /**\r\n   * Propertieds and logic for the situation where the dialog is displayed as part of row type definition editor.\r\n   * If undefined, this is a rows editor (typically for a calculation) and not a row type definition editor.\r\n   */\r\n  public definitionEditor?: {\r\n    /** Mode of the definition editor. */\r\n    mode: \"builtIn\" | \"custom\" | \"prices\";\r\n  };\r\n\r\n  /**\r\n   * If set, filters the rows based on categories (plus rowTypes if set).\r\n   * Note that category error (validation errors) is added later and may not be supported by all parts of the UI.\r\n   */\r\n  public categories: (\r\n    | \"salary\"\r\n    | \"salaryCalc\"\r\n    | \"holidays\"\r\n    | \"salaryAdditions\"\r\n    | \"benefits\"\r\n    | \"expenses\"\r\n    | \"deductions\"\r\n    | \"other\"\r\n  )[];\r\n\r\n  /**\r\n   * Defines the helper texts and branding color for row type selection list dialog\r\n   * (showRowTypeSelectionDialog method)\r\n   */\r\n  public rowTypeSelectHelp: \"salaries\" | \"benefits\" | \"expenses\" | \"deductions\";\r\n\r\n  /** If set, shows only these types (plus categories if set) */\r\n  public rowTypes: CalculationRowType[];\r\n\r\n  /** If set, shows only the rows with these statuses. */\r\n  public statuses: string[] | string;\r\n\r\n  /**\r\n   * If set, shows only these sources in the source drop-down.\r\n   * This is a comma separated list of enum values.\r\n   */\r\n  public rowSources: string;\r\n\r\n  /** User interface type of the editor: Default is the one used in calculators. */\r\n  public type: \"worktime-import\" | \"worktime-import-employment\" | \"salary-defaults\" | \"default\";\r\n\r\n  /** If true, the current UI is a modal dialog. */\r\n  public isDialog: boolean;\r\n\r\n  /** Information on the usecase specific data / UI for this row. */\r\n  public usecase: {\r\n    isLoading?: boolean;\r\n    schema?: any;\r\n    isDefined?: boolean;\r\n  } = {};\r\n\r\n  /** Hides final cost row. */\r\n  public hideFinalCostRow = false;\r\n\r\n  /** Default dimension to show in rows editor */\r\n  public defaultDimension: string;\r\n\r\n  /** Count of dimension to show in editor */\r\n  public dimensionCount = 0;\r\n\r\n  public _dimensions: CostAccountingDimensionDefinition[] = undefined;\r\n\r\n  private _vehicleTypeSelection: InputEnumOption[];\r\n  private _vehicleAdditions: InputEnumOption[];\r\n\r\n  private _dailyAllowanceRegions: InputEnumOption[];\r\n\r\n  /**\r\n   * Creates a new CalcRows2019Controller\r\n   * @param uiHelpers - Salaxy UI helpers service.\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    uiHelpers: UiHelpers,\r\n    private $timeout: angular.ITimeoutService,\r\n\r\n    private session: SessionService,\r\n    editDialogParams: EditDialogParameters<any>,\r\n    private $element: JQLite,\r\n    private rowTypeService: RowTypeService,\r\n    private accountingTargets: AccountingTargets,\r\n    private calculations: Calculations\r\n  ) {\r\n    super(uiHelpers);\r\n    if (editDialogParams.logic?.calc) {\r\n      // EditDialogParameters inject controller data in dialog situation.\r\n      // At the moment this is always a single item, but may later be extended to lists.\r\n      this.parent = editDialogParams.logic.calc;\r\n      if (editDialogParams.logic.definitionEditor) {\r\n        this.definitionEditor = editDialogParams.logic.definitionEditor;\r\n        this.isDialog = false;\r\n      } else {\r\n        this.isDialog = true;\r\n      }\r\n      this.current = editDialogParams.current;\r\n    }\r\n  }\r\n\r\n  /** Sets the default values in init. */\r\n  public $onInit() {\r\n    this.newRow = this.getBlank();\r\n  }\r\n\r\n  /** Yearlysidecosts for translations, used in template */\r\n  public get yearlySideCosts(): {\r\n    current: YearlyChangingNumbers;\r\n    previous: YearlyChangingNumbers;\r\n  } {\r\n    const currentYear = Dates.getToday();\r\n    const previousYear = Dates.add(currentYear, -1, \"year\");\r\n    return {\r\n      current: this.formatYearlyNumbers(\r\n        Years.getYearlyChangingNumbers(currentYear)\r\n      ),\r\n      previous: this.formatYearlyNumbers(\r\n        Years.getYearlyChangingNumbers(previousYear)\r\n      ),\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Marks that the editor is stand-alone, meaning that it does not edit a calculation,\r\n   * but it just edits a set of rows, typically in employment or settings.\r\n   * In this case the editor has creaed a fake calculation (because calculation is currently required for the row editor to work).\r\n   * TODO: Consider separating Calculation rows editor from stand-alone row editor.\r\n   */\r\n  public get isStandAlone(): boolean {\r\n    return !!this.parent?.usecase?.data?.standAloneRows;\r\n  }\r\n\r\n  /** Copies the given text to clipboard. */\r\n  public copyToClipboard(text: string) {\r\n    navigator.clipboard.writeText(text);\r\n  }\r\n\r\n  /** List of rows  */\r\n  public get list(): WorktimeImportRow[] | null {\r\n    if (!this.parent) {\r\n      if (this.rows) {\r\n        this.parent = CalculatorLogic.getBlank();\r\n        this.parent.usecase.data.standAloneRows = true;\r\n        this.parent.isReadOnly = this.mode == \"read-only\";\r\n      } else {\r\n        return null;\r\n      }\r\n    }\r\n    // HACK: This does not belong here: Move to server-side (in v03 release candidate).\r\n    CalculatorLogic.moveSalaryToRows(this.parent);\r\n    if (this.rows && this.parent.rows !== this.rows) {\r\n      // Rows has been set outside.\r\n      this.parent.rows = this.rows;\r\n    }\r\n    return this.parent.rows;\r\n  }\r\n\r\n  /** List filtered by categories and rowTypes. */\r\n  public get filteredList(): WorktimeImportRow[] | null {\r\n    const typesToShow = this.rowTypesToShow.map((x) => x as string);\r\n    const statuses = Arrays.assureArray(this.statuses);\r\n    const rowSources = Arrays.assureArray(this.rowSources);\r\n    if (typesToShow.length === 0 && statuses.length === 0 && rowSources.length === 0) {\r\n      return this.list;\r\n    }\r\n    return this.list.filter((x) =>\r\n      (!typesToShow.length || typesToShow.indexOf(x.rowType) >= 0) &&\r\n      (!statuses.length || statuses.indexOf((x as any).status) >= 0) &&\r\n      // HACK: rowSources property should be completely removed when moving default row display to RowTypeSettings editor\r\n      (!rowSources.length || x.source != CalculationRowSource.PriceEmployment)\r\n    );\r\n  }\r\n\r\n  /** Combines together categories and rowTypes properties as one list of row types. */\r\n  public get rowTypesToShow() {\r\n    const rowsLogic = new CalcRowsLogic(\r\n      this.session.isInRole(\"household\") ? \"household\" : \"company\"\r\n    );\r\n    const types = [...(this.rowTypes || [])];\r\n    if (this.categories) {\r\n      for (const cat of this.categories) {\r\n        types.push(...rowsLogic.getRowTypesByCategory(cat as any));\r\n      }\r\n    }\r\n    return types;\r\n  }\r\n\r\n  /** Creating of a new item. */\r\n  public getBlank(): UserDefinedRow {\r\n    const newRow = UserDefinedRowLogic.getBlank(this.list?.filter((x) => x.rowIndex >= 0).length || 0);\r\n    return newRow;\r\n  }\r\n\r\n  /**\r\n   * Returns a validation message for a row or null if none is required.\r\n   * @param row The row that is validated.\r\n   */\r\n  public getValidation(row: UserDefinedRow): {\r\n    /** Validation message */\r\n    msg: string;\r\n    /** Type of validation message */\r\n    type: \"default\" | \"error\";\r\n  } | undefined {\r\n    return RowsUsecaseLogic.getValidation(row) as { msg: string; type: \"default\" | \"error\"; } | undefined;\r\n  }\r\n\r\n  /** Template for edit UI that is shown in a modal dialog. */\r\n  public getEditDialogTemplateUrl() {\r\n    return \"salaxy-components/calc/rows/CalcRows2019EditDialog.html\";\r\n  }\r\n\r\n  /**\r\n   * Shows whether accounting editing is enabled\r\n   * @returns true if accounting editing is enabled\r\n   */\r\n  public showAccountingEditing(): boolean {\r\n    return ![\r\n      CalculationRowType.AbsencePeriod,\r\n      CalculationRowType.BicycleBenefit,\r\n      CalculationRowType.CarBenefit,\r\n      CalculationRowType.MealBenefit,\r\n      CalculationRowType.SubsidisedCommute,\r\n      CalculationRowType.HourlySalaryWithWorkingTimeCompensation,\r\n      CalculationRowType.TotalWorkerPayment,\r\n      CalculationRowType.TaxAtSource,\r\n      CalculationRowType.TaxWithholding].includes(this.current.rowType);\r\n  }\r\n\r\n  /**\r\n   * Opens the accounting ruleset selection dialog\r\n   * @param isDebit - Whether to set debit account (true) or credit account (false)\r\n   * @returns Promise that resolves when the dialog is closed\r\n   */\r\n  public async openAccountingRulesetSelection(isDebit: boolean): Promise<void> {\r\n    try {\r\n      const targetOdata = (await this.accountingTargets.getOData({$filter: `id eq '${this.session.session?.settings?.accountingTarget.id}'`})).items[0];\r\n      if(!targetOdata) {\r\n        this.uiHelpers.showConfirm(\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.entry.rulesetSelection.error\", \"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.entry.rulesetSelection.targetCoANotFound\");\r\n        return;\r\n      }\r\n\r\n      const target = await this.accountingTargets.getSingle(`${this.session.session?.settings?.accountingTarget.id}@${targetOdata.owner}`);\r\n      if(!target) {\r\n        this.uiHelpers.showConfirm(\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.entry.rulesetSelection.error\", \"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.entry.rulesetSelection.targetCoANotFound\");\r\n        return;\r\n      }\r\n\r\n      const logic = { title: \"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.entry.rulesetSelection.selectTargetCoA\", items: target.ruleSet.accounts };\r\n      const res = await this.uiHelpers.openEditDialog(\"salaxy-components/modals/calc/SelectRuleset.html\", null, logic);\r\n\r\n      if(res.result?.account) {\r\n        this.current.accounting ??= {};\r\n        (this.current.accounting as any).entry ??= {};\r\n        (this.current.accounting as any).entry[isDebit ? \"debitAccountNumber\" : \"creditAccountNumber\"] = res.result.account;\r\n      }\r\n    } catch(error) {\r\n      console.error(error);\r\n      this.uiHelpers.showConfirm(\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.entry.rulesetSelection.error\", \"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.entry.rulesetSelection.targetCoANotFound\");\r\n    }\r\n  }\r\n  /**\r\n   * Shows a preview of the accounting report for the currently selected row.\r\n   * Creates a calculation with only the current row, recalculates it, and opens\r\n   * a dialog to display the accounting report query.\r\n   * @returns Promise that resolves when the dialog is closed\r\n   * @throws {Error} If no current row is selected or if recalculation fails\r\n   * @example\r\n   * // Show accounting preview for the current row\r\n   * await this.showRowAccountingPreview();\r\n   */\r\n  public async showRowAccountingPreview(): Promise<void> {\r\n    try {\r\n      let calc = angular.copy(this.parent);\r\n      const currentRow = calc.rows.find((x) => x.rowIndex === this.current.rowIndex);\r\n      if(currentRow) {\r\n        currentRow.accounting ??= {};\r\n        (currentRow.accounting as any).entry = (this.current.accounting as any).entry;\r\n      }\r\n      calc = await this.calculations.recalculate(calc);\r\n\r\n      // Prepare the logic object for the dialog\r\n      const logic = {\r\n        title: \"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.entry.rowAccountingPreview.targetCoA\",\r\n        lang: Translations.getLanguage(),\r\n        calcs: [calc],\r\n        view: \"partial\"\r\n      };\r\n\r\n      // Open the accounting report query dialog\r\n      await this.uiHelpers.openEditDialog(\r\n        \"salaxy-components/modals/calc/CalcAccountingReportQuery.html\",\r\n        null,\r\n        logic,\r\n        \"xl\"\r\n      );\r\n    } catch (error) {\r\n      console.error(\"Error showing row accounting preview:\", error);\r\n      this.uiHelpers.showConfirm(\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.entry.rowAccountingPreview.error\", \"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.entry.rowAccountingPreview.accountingPreviewFailed\");\r\n      throw error;\r\n    }\r\n  }\r\n\r\n  /** checks if the image fileUrl given in the cost line is not a blob (omapalkka image upload adds blob) */\r\n  public showImagePreview(): boolean {\r\n    return (\r\n      this.current?.data?.fileUrl &&\r\n      !this.current?.data?.fileUrl.startsWith(\"blob:\")\r\n    );\r\n  }\r\n\r\n  /**\r\n   * Gets the UX configuration for a row.\r\n   * @param row Row for which the config is fetched.\r\n   * If not set, gets the config for current.\r\n   */\r\n  public getConfig(row: UserDefinedRow = null): CalcRowConfig | undefined {\r\n    return this.rowTypeService.getConfig(row || this.current);\r\n  }\r\n\r\n  /**\r\n   * Gets the placeholder text for an input.\r\n   */\r\n  public getPlaceholderText(row: UserDefinedRow, field: \"amount\" | \"price\") {\r\n    if (!row.rowType) {\r\n      return \"\";\r\n    }\r\n    const config = this.getConfig(row);\r\n    if (field === \"amount\") {\r\n      return config.amount.label;\r\n    } else {\r\n      return config.price.label;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Return the total for the row\r\n   */\r\n  public getRowTotal(row: UserDefinedRow) {\r\n    if (row == null) {\r\n      return null;\r\n    }\r\n    if (row.count == null) {\r\n      return row.price;\r\n    } else {\r\n      return row.count * row.price;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Returns true, if the row is disabled. The row is interpreted as disabled if it has no rowType\r\n   * or it has been set as hidden in the configuration.\r\n   * @param row Row to check\r\n   * @param field Type of the input / field.\r\n   */\r\n  public isDisabled(row: UserDefinedRow, field: \"amount\" | \"price\") {\r\n    if (!row?.rowType) {\r\n      return true;\r\n    }\r\n    const config = this.getConfig(row);\r\n    if (!config?.amount || !config?.price) {\r\n      console.debug(\"Row config not found for row\", row);\r\n      return false;\r\n    }\r\n    switch (field) {\r\n      case \"amount\":\r\n        return config.amount.input === \"hidden\";\r\n      case \"price\":\r\n        return config.price.input === \"hidden\";\r\n      default:\r\n        return false;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Updates the compensation row with the calculated price based on the unit type.\r\n   * @param row - The row containing both the main row price and compensation row data.\r\n   */\r\n  public updateCompensationRow(row: UserDefinedRow): void {\r\n    const compRow = row.data.compensationRows[0];\r\n    let price = 0;\r\n    switch (compRow.unit) {\r\n      case \"percent\":\r\n        price = row.price * compRow.count;\r\n        break;\r\n      case \"hours\":\r\n        price = compRow.price;\r\n        break;\r\n    }\r\n    compRow.price = price;\r\n  }\r\n\r\n  /** Row type changes on a row */\r\n  public rowTypeChanged(row: UserDefinedRow) {\r\n    this.rowTypeService.applyDefaultsToNewRow(row, this.parent?.workflow?.salaryDate ?? \"today\");\r\n  }\r\n\r\n  /**\r\n   * Commits the new row in newRow property and adds it to the rows list.\r\n   * Updates usecase and sets the newRow as new blank row.\r\n   */\r\n  public commitNewRow(showEdit = false): UserDefinedRow {\r\n    if (!this.newRow?.rowType) {\r\n      console.error(\"No row type set for the new row.\");\r\n      return null;\r\n    }\r\n    const row = this.newRow;\r\n    this.rowTypeChanged(row);\r\n    this.updateUsecase(row);\r\n    this.list.push(row);\r\n    this.$timeout(() => {\r\n      // Reset new row type after timeout to avoid debounce\r\n      this.newRow = this.getBlank();\r\n    }, 300);\r\n    if (showEdit) {\r\n      this.showEdit(row, \"auto\");\r\n    } else {\r\n      this.$timeout(() => {\r\n        let elem: HTMLElement = null;\r\n        if (this.isDisabled(row, \"amount\")) {\r\n          elem = (this.$element[0] as HTMLElement).querySelector(\r\n            \"#iptPrice\" + row.rowIndex\r\n          );\r\n        } else {\r\n          elem = (this.$element[0] as HTMLElement).querySelector(\r\n            \"#iptCount\" + row.rowIndex\r\n          );\r\n        }\r\n        if (elem) {\r\n          elem.focus();\r\n        }\r\n      }, 500);\r\n    }\r\n    return row;\r\n  }\r\n\r\n  /** Shows the selection dialog for the row type. */\r\n  public showRowTypeSelectionDialog() {\r\n    this.uiHelpers\r\n      .openEditDialog(\r\n        \"salaxy-components/modals/calc/row-type-select.html\",\r\n        this.newRow,\r\n        {\r\n          categories: this.categories,\r\n          rowTypes: this.rowTypes,\r\n          rowTypeSelectHelp: this.rowTypeSelectHelp,\r\n        }\r\n      )\r\n      .then((result) => {\r\n        if (result.action === \"ok\" && result.hasChanges) {\r\n          this.showEdit(this.commitNewRow(), \"auto\");\r\n        }\r\n      });\r\n  }\r\n\r\n  /** Updates the usecase property values without going to server. */\r\n  public updateUsecase(row: UserDefinedRow) {\r\n    this.getUsecaseLogic(row);\r\n  }\r\n\r\n  /**\r\n   * Returns the usecase logic instance for current row, also running the first update cycle on the row.\r\n   */\r\n  public getUsecaseLogic(row: UserDefinedRow): BaseUsecaseLogic {\r\n    return RowsUsecaseLogic.getUsecaseLogicForCalc(row, this.parent, true);\r\n  }\r\n\r\n  /**\r\n   * Gets vehicle type selections from usecase\r\n   * @returns InputEnumOption[] of vehicle selections\r\n   */\r\n  public getVehicleTypeSelection(): InputEnumOption[] {\r\n    if (!this._vehicleTypeSelection) {\r\n      this._vehicleTypeSelection = [];\r\n      const vehicleTypes: InputEnumOption[] = (\r\n        RowsUsecaseLogic.getUsecaseLogicForCalc(\r\n          this.current,\r\n          this.parent,\r\n          true\r\n        ) as MilageOwnCarUsecaseLogic\r\n      ).getVehicleTypeSelection();\r\n      this._vehicleTypeSelection.push(...vehicleTypes);\r\n    }\r\n    return this._vehicleTypeSelection;\r\n  }\r\n\r\n  /**\r\n   * Gets vehicle additions from usecase\r\n   * @returns InputEnumOption[] of vehicle additions\r\n   */\r\n  public getVehicleAdditions(): InputEnumOption[] {\r\n    if (!this._vehicleAdditions) {\r\n      this._vehicleAdditions = [];\r\n      const vehicleAdditions: InputEnumOption[] = (\r\n        RowsUsecaseLogic.getUsecaseLogicForCalc(\r\n          this.current,\r\n          this.parent,\r\n          true\r\n        ) as MilageOwnCarUsecaseLogic\r\n      ).getAdditionsSelection();\r\n      this._vehicleAdditions.push(...vehicleAdditions);\r\n    }\r\n    return this._vehicleAdditions;\r\n  }\r\n\r\n  /**\r\n   * Gets the regions for InternationalDailyAllowance as of today\r\n   */\r\n  public get dailyAllowanceRegions(): InputEnumOption[] {\r\n    if (!this._dailyAllowanceRegions) {\r\n      this._dailyAllowanceRegions = [];\r\n      const result = [];\r\n      Object.entries(Years.getYearlyTaxFreeNumbers(\"today\").countries).forEach(\r\n        (x) => {\r\n          result.push({\r\n            text: `${Translations.get(\r\n              `SALAXY.CORE.yearlyTaxfreeYears.countries.${x[0]}`\r\n            )} (${x[1]}€)`,\r\n            value: (x[0] as any) ?? \"\",\r\n          });\r\n        }\r\n      );\r\n      this._dailyAllowanceRegions.push(...result);\r\n    }\r\n    this._dailyAllowanceRegions = this._dailyAllowanceRegions.sort((a, b) =>\r\n      a.text.localeCompare(b.text)\r\n    );\r\n    return this._dailyAllowanceRegions;\r\n  }\r\n\r\n  /**\r\n   * Gets the Incomes Register metadata for a calculation row.\r\n   * @param row Row to check, null for current row.\r\n   * @returns The income type metadata. Empty object for empty row or empty irData.\r\n   */\r\n  public getIrCodeData(row: UserDefinedRow = null) {\r\n    row = row || this.current;\r\n    if (row?.data?.irData) {\r\n      return IncomeTypesLogic.getAll().find(\r\n        (x) => x.code === row.data.irData.code\r\n      );\r\n    }\r\n    return {};\r\n  }\r\n\r\n  /** Return the metadata based on irCode */\r\n  public getIrCodeDataWithCode(irCode: number): IncomeTypeMetadata {\r\n    return IncomeTypesLogic.getAll().find((x) => x.code === irCode);\r\n  }\r\n\r\n  /** Returns true if the filtered list has any rows. */\r\n  public get hasRows(): boolean {\r\n    return (this.filteredList || []).length > 0;\r\n  }\r\n\r\n  /** Gets the total for the current rows. */\r\n  public getTotal() {\r\n    return (this.filteredList || []).reduce(\r\n      (prev, curr) => prev + curr.count * curr.price,\r\n      0\r\n    );\r\n  }\r\n  /**\r\n   * Gets the gross total for the calculation.\r\n   * Current implementation does not support filtering.\r\n   */\r\n  public getGrossTotal() {\r\n    if (!this.parent || !this.parent.result || !this.parent.result.totals) {\r\n      return null;\r\n    }\r\n    return this.parent.result.totals.totalGrossSalary;\r\n  }\r\n\r\n  /**\r\n   * Gets the total payment for the calculation.\r\n   * Current implementation does not support filtering.\r\n   */\r\n  public getFinalCost() {\r\n    if (\r\n      !this.parent ||\r\n      !this.parent.result ||\r\n      !this.parent.result.employerCalc\r\n    ) {\r\n      return null;\r\n    }\r\n    return this.parent.result.employerCalc.finalCost;\r\n  }\r\n  /**\r\n   * Gets the net salary for the calculation.\r\n   * Current implementation does not support filtering.\r\n   */\r\n  public getNetSalary() {\r\n    return this.parent.result.workerCalc.salaryPayment;\r\n  }\r\n\r\n  /**\r\n   * Gets the total payment that is paid to palkkaus.fi.\r\n   * Current implementation does not support filtering.\r\n   */\r\n  public getTotalPayment() {\r\n    return this.parent.result.employerCalc.totalPayment;\r\n  }\r\n\r\n  /**\r\n   * Closes the edit dialog (either modal dialog or inline).\r\n   * @param method The closing method.\r\n   * @param $close In the case of modal dialog, this is the modal dialog close method.\r\n   */\r\n  public closeEditDialog(\r\n    method: \"cancel\" | \"ok-no-save\" | \"delete-no-save\",\r\n    $close: any = null\r\n  ): void {\r\n    if ($close) {\r\n      $close(method);\r\n      return;\r\n    }\r\n    switch (method) {\r\n      case \"delete-no-save\":\r\n        this.delete(this.current);\r\n        this.current = null;\r\n        return;\r\n      case \"ok-no-save\": // Perhaps later have commit functionality.\r\n      case \"cancel\":\r\n      default:\r\n        this.current = null;\r\n        return;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Shows the editor UI that may either be a dialog or an inline edit UI.\r\n   * @param item Item to edit. If rowIndex is null/undefined, the item is considered a new row and the properties\r\n   * extend new item (fetched from getBlank()).\r\n   * @param type Type of the edit UI.\r\n   */\r\n  public showEdit(\r\n    item: UserDefinedRow,\r\n    type: \"dialog\" | \"inline\" | \"auto\" = \"auto\"\r\n  ) {\r\n    if (!item) {\r\n      throw new Error(\"showEditDialog called without a parameter.\");\r\n    }\r\n    const isNew = this.isInEdit && item.rowIndex == null;\r\n    if (isNew) {\r\n      item = angular.merge({}, this.getBlank(), item);\r\n      this.rowTypeChanged(item);\r\n      this.updateUsecase(item);\r\n    } else {\r\n      item.data = item.data ?? {};\r\n      item.accounting = item.accounting ?? {};\r\n    }\r\n\r\n    if (type != \"dialog\" && type != \"inline\") {\r\n      const elem = this.$element[0]?.querySelector(\r\n        \".salaxy-calc-rows-editor-details-container\"\r\n      ) as HTMLElement;\r\n      if (\r\n        elem &&\r\n        (elem.offsetWidth || elem.offsetHeight || elem.getClientRects().length)\r\n      ) {\r\n        // jQuery isVisible: https://stackoverflow.com/questions/19669786/check-if-element-is-visible-in-dom\r\n        type = \"inline\";\r\n      } else {\r\n        type = \"dialog\";\r\n      }\r\n    }\r\n    if (type == \"dialog\") {\r\n      this.showEditDialog(item, isNew);\r\n      return;\r\n    }\r\n\r\n    // Inline edit UI.\r\n    if (this.current == item) {\r\n      this.current = null;\r\n    } else {\r\n      if (isNew) {\r\n        this.list.push(item);\r\n      }\r\n      this.current = item;\r\n      this.$timeout(() => {\r\n        const elem: HTMLElement = (\r\n          this.$element[0] as HTMLElement\r\n        ).querySelector(\".salaxy-calc-details-dialog .form-control\");\r\n        if (elem) {\r\n          elem.focus();\r\n        }\r\n      }, 300);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Shows the edit dialog: Extends the base functionality with custom controller (non-supported results removed).\r\n   * @param item Item to edit or string \"new\" for creating a new one.\r\n   * @param isNew Optional way of specifying that the item is a new item (with default values, not yet added to the list).\r\n   * If item is string \"new\", this parameter will have no effect (will always be true).\r\n   */\r\n  public showEditDialog(item: UserDefinedRow | \"new\", isNew = false) {\r\n    if (!item) {\r\n      throw new Error(\"showEditDialog called without a parameter.\");\r\n    }\r\n    if (item === \"new\") {\r\n      isNew = true;\r\n      item = this.getBlank();\r\n    }\r\n\r\n    item.data = item.data ?? {};\r\n    item.accounting = item.accounting ?? {};\r\n    this.uiHelpers\r\n      .openEditDialog(\r\n        this.getEditDialogTemplateUrl(),\r\n        item,\r\n        {\r\n          calc: this.parent,\r\n          readOnly: !this.isInEdit,\r\n        },\r\n        \"\",\r\n        \"CalcRows2019Controller\"\r\n      )\r\n      .then((result) => {\r\n        if (result.action === \"ok-no-save\") {\r\n          if (isNew) {\r\n            this.list.push(result.item);\r\n          }\r\n        } else if (result.action === \"delete-no-save\") {\r\n          if (!isNew) {\r\n            this.delete(item as UserDefinedRow);\r\n          }\r\n        } else {\r\n          // No changes, cancel\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Gets or sets the flag telling whether the component is in edit or read-only mode.\r\n   */\r\n  public get isInEdit(): boolean {\r\n    if (!this.isEditable) {\r\n      return !!this._isInEdit;\r\n    }\r\n    return super.isInEdit;\r\n  }\r\n  public set isInEdit(value: boolean) {\r\n    super.isInEdit = value;\r\n  }\r\n\r\n  /**\r\n   * Changes the view from read-only mode to edit mode.\r\n   */\r\n  public startEdit() {\r\n    if (!this.isEditable) {\r\n      this.isInEdit = true;\r\n      this.onStartEdit({\r\n        parent: this.parent,\r\n      });\r\n    } else {\r\n      super.startEdit();\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Returns placeholder text for row\r\n   * @param row used row\r\n   * @returns row message as string\r\n   */\r\n  public getMessagePlaceholderText(row: UserDefinedRow): string {\r\n    if (row.message) {\r\n      return row.message;\r\n    }\r\n    let label = \"\";\r\n    if (row.rowType === CalculationRowType.IrIncomeType) {\r\n      label = IncomeTypesLogic.getAll().find(\r\n        (x) =>\r\n          (row.data?.kind && x.transactionCode === row.data.kind) ||\r\n          (row.data?.irData?.code > 0 && x.code === row.data.irData.code)\r\n      )?.label;\r\n    } else if (row.rowType == CalculationRowType.AbsencePeriod) {\r\n      label = EnumerationsLogic.getEnumLabel(\r\n        \"AbsenceCauseCode\",\r\n        row.data?.kind\r\n      );\r\n    } else if (\r\n      [\r\n        CalculationRowType.DailyAllowance,\r\n        CalculationRowType.EmploymentTermination,\r\n        CalculationRowType.WorkingTimeCompensation,\r\n        CalculationRowType.Remuneration,\r\n        CalculationRowType.OtherCompensation,\r\n        CalculationRowType.NonProfitOrg,\r\n        CalculationRowType.MealBenefit,\r\n        CalculationRowType.Training,\r\n        CalculationRowType.PaidSickLeave,\r\n        CalculationRowType.TotalWorkerPayment,\r\n        CalculationRowType.TimeRatePay,\r\n      ].includes(row.rowType) &&\r\n      row.data?.kind\r\n    ) {\r\n      label = EnumerationsLogic.getEnumLabel(\r\n        `${row.rowType}Kind`,\r\n        row.data.kind\r\n      );\r\n    }\r\n\r\n    return (\r\n      label || EnumerationsLogic.getEnumLabel(\"CalculationRowType\", row.rowType)\r\n    );\r\n  }\r\n\r\n  /** Initializes and returns the unit for the row. */\r\n  public ensureUnit(row: UserDefinedRow): CalculationRowUnit {\r\n    if (!row.unit) {\r\n      const config = this.getConfig(row);\r\n      row.unit = config.amount.unit;\r\n    }\r\n    return row.unit;\r\n  }\r\n\r\n  /**\r\n   * Select a row in the list or unselect if already selected.\r\n   * @param row Row to select or \"all\" to select all currently vivisble rows.\r\n   * @param value Optional value to force selection true or false regardless of the current state.\r\n   */\r\n  public toggleSelectedRow(row: WorktimeImportRow | \"all\", value?: boolean) {\r\n    if (row == \"all\") {\r\n      this.filteredList.forEach((x) => {\r\n        this.toggleSelectedRow(x, value);\r\n      });\r\n      return;\r\n    }\r\n    if (row.data.isSelected && !value) {\r\n      // Toggle / Force unselect (undefined/false), Force select (true) keeps as is.\r\n      row.data.isSelected = false;\r\n    } else if (value !== false) {\r\n      // Toggle or Force select (undefined/true). Force unselect (false) keeps as is.\r\n      row.data.isSelected = true;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Gets the selected rows in the list (only the filtered / visible rows).\r\n   * @returns The selected rows.\r\n   */\r\n  public getSelectedRows(): WorktimeImportRow[] {\r\n    return this.filteredList.filter((x) => x.data.isSelected);\r\n  }\r\n\r\n  /**\r\n   * Determines the visibility of dimensions based on certain conditions.\r\n   * @returns {boolean} - Returns `true` if dimensions should be visible, otherwise `false`.\r\n   */\r\n  public showDimension(): boolean {\r\n    return this.dimensionsCountToShow() > 0;\r\n  }\r\n\r\n  /**\r\n   * Returns the number of dimensions to show.\r\n   * @returns {number} The number of dimensions to show. If `dimensionCount` is not defined, returns 0.\r\n   */\r\n  public dimensionsCountToShow(): number {\r\n    return this.getDimensionsToShow().length;\r\n  }\r\n\r\n  /**\r\n   * Retrieves the dimensions to show based on the session settings and predefined rules.\r\n   * This method filters the available dimensions to exclude hidden ones and includes\r\n   * those that match specific scope criteria. It prioritizes adding the default dimension\r\n   * and cost center first, followed by the remaining dimensions until the limit defined\r\n   * by `dimensionsCountToShow` is reached.\r\n   * @returns {CostAccountingDimensionDefinition[]} An array of dimensions to be displayed.\r\n   */\r\n  public getDimensionsToShow(): CostAccountingDimensionDefinition[] {\r\n    if (!this._dimensions) {\r\n      const dimensions = (this.session.session?.settings?.costAccounting?.dimensions ?? [])\r\n      .filter( (x) =>\r\n        // no hidden scope\r\n        x.scope !== CostAccountingDimensionScope.Hidden &&\r\n        (\r\n          // show if scope definition for dimension not given\r\n          ( !x.scope || x.scope === CostAccountingDimensionScope.None) ||\r\n          // or this scope\r\n          (CostAccountingDimensionScope.Row === x.scope)\r\n        )\r\n      );\r\n      const defaultDimension = this.defaultDimension || \"costCenter\";\r\n      // take a copy\r\n      const ordered = dimensions.slice(0);\r\n      // sort and mutate\r\n      ordered.sort( (x, y) => x.id == defaultDimension ? -1 : x.id == \"costCenter\" && y.id != defaultDimension ? -1: 0  );\r\n      // set length\r\n      ordered.length = (ordered.length > (this.dimensionCount ?? 0)) ? this.dimensionCount ?? 0: ordered.length;\r\n      return this._dimensions = ordered;\r\n    }\r\n    return this._dimensions;\r\n  }\r\n\r\n  private formatYearlyNumbers(\r\n    yearlyNumbers: YearlyChangingNumbers\r\n  ): YearlyChangingNumbers {\r\n    const keys = Object.keys(yearlyNumbers.sideCosts);\r\n    for (const key of keys) {\r\n      if (yearlyNumbers.sideCosts[key] >= 1) {\r\n        yearlyNumbers.sideCosts[key + \"Formatted\"] = Numeric.formatPrice(\r\n          yearlyNumbers.sideCosts[key]\r\n        );\r\n      }\r\n    }\r\n    return yearlyNumbers;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Calculation, Calculations, CalculationStatus } from \"@salaxy/core\";\r\n\r\nimport { InvoicesService, ReportsService, SessionService, UiHelpers } from \"../../services\";\r\nimport { CalculationCrudController } from \"./CalculationCrudController\";\r\n\r\n/**\r\n * Controller for sharing actions: accept, decline\r\n */\r\nexport class CalcSharingReceiptActionController extends CalculationCrudController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Calculations\", \"ReportsService\", \"UiHelpers\", \"$location\", \"$routeParams\", \"SessionService\", \"InvoicesService\"];\r\n\r\n  /**\r\n   * Creates a new CalcSharingController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    calculationsApi: Calculations,\r\n    reportsService: ReportsService,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    sessionService: SessionService,\r\n    protected invoicesService: InvoicesService,\r\n  ) {\r\n    super(calculationsApi, reportsService, uiHelpers, $location, $routeParams, sessionService, invoicesService);\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Approve the the calculation requested by the worker. */\r\n  public approve(): Promise<Calculation> {\r\n    switch (this.current.workflow.status) {\r\n      case CalculationStatus.SharedWaiting:\r\n      case CalculationStatus.SharedRejected:\r\n        this.current.workflow.status = CalculationStatus.SharedApproved;\r\n        return this.save();\r\n      case CalculationStatus.SharedApproved:\r\n      default:\r\n        return Promise.resolve(this.current);\r\n    }\r\n  }\r\n\r\n  /** Reject the the calculation requested by the worker. */\r\n  public reject(): Promise<Calculation> {\r\n    switch (this.current.workflow.status) {\r\n      case CalculationStatus.SharedWaiting:\r\n      case CalculationStatus.SharedApproved:\r\n        this.current.workflow.status = CalculationStatus.SharedRejected;\r\n        return this.save();\r\n      case CalculationStatus.SharedRejected:\r\n      default:\r\n        return Promise.resolve(this.current);\r\n    }\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {\r\n  Calculation,\r\n  Language,\r\n  Translations,\r\n  Objects\r\n} from \"@salaxy/core\";\r\nimport {IrRowsReportConfigGenerator} from \"@salaxy/reports\";\r\nimport { SessionService } from \"../../services\";\r\nimport { ColumnDefinition } from \"tabulator-tables\";\r\nimport {SxyTableOptions} from \"../sxy-table/SxyTableController\";\r\nimport { SxyTableController } from \"../sxy-table/SxyTableController\";\r\n/**\r\n * Renders ir rows report for given calculations\r\n * Uses Tabulator tables.\r\n */\r\nexport class CalcsIrRowsController implements angular.IController {\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"$timeout\",\r\n    \"SessionService\"\r\n  ];\r\n\r\n  /** The calculations for the report. Todo add Calcs*/\r\n  public calcs: Calculation[];\r\n\r\n  /**Selected report language */\r\n  public lang: Language;\r\n\r\n  /** Ref to used SxyTable */\r\n  public $sxyTable: SxyTableController;\r\n\r\n  private sxyTableConfig: {currentCalc: Calculation | Calculation[], reportLang: Language, config: {options: SxyTableOptions, include: ColumnDefinition[], data: any[]}} = {\r\n    currentCalc: null,\r\n    reportLang: Language.Default,\r\n    config: null\r\n  };\r\n\r\n  private renderedLang: string;\r\n\r\n  /**\r\n   * Creates a new CalcReportController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    private $timeout: angular.ITimeoutService,\r\n\r\n    private sessionService: SessionService\r\n  ) {\r\n  }\r\n\r\n  /**\r\n   * Config for SxyTable\r\n   */\r\n  public get tableConfig(): {options: SxyTableOptions, include: ColumnDefinition[], data: any[]}{\r\n    if(!this.calcs) {\r\n      this.sxyTableConfig = {\r\n        currentCalc: null,\r\n        reportLang: null,\r\n        config: null\r\n      };\r\n    } else {\r\n      const calcs = angular.copy(this.calcs);\r\n      if(!Objects.equal(this.sxyTableConfig.currentCalc, calcs) || this.lang !== this.sxyTableConfig.reportLang) {\r\n        this.sxyTableConfig.currentCalc = calcs;\r\n        this.sxyTableConfig.reportLang = this.lang;\r\n        this.getDefaultLanguage(this.lang).then((lang) => {\r\n          this.lang = lang;\r\n          this.renderedLang = this.lang;\r\n          this.refreshTableConfig();\r\n        });\r\n      }\r\n    }\r\n    return this.sxyTableConfig.config;\r\n  }\r\n\r\n  /** Refreshes table config */\r\n  public async refreshTableConfig() {\r\n    const renderingLang = this.lang ?? Language.Fi;\r\n    await Translations.loadLanguage(renderingLang);\r\n    this.sxyTableConfig.config = IrRowsReportConfigGenerator.getConfig(this.calcs, renderingLang);\r\n    await this.$timeout();\r\n    this.$sxyTable.refresh();\r\n  }\r\n\r\n  private async getDefaultLanguage(lang: Language): Promise<Language> {\r\n    if (!lang) {\r\n      return this.sessionService.getReportLang();\r\n    }\r\n    return Promise.resolve(lang);\r\n  }\r\n}","import { Calculation, CalculatorLogic } from \"@salaxy/core\";\r\n\r\n/**\r\n * Defines the panels logic in the Calculator\r\n */\r\nexport class CalculatorPanels {\r\n\r\n    /**\r\n     * Creates a new CalculatorPanels helper for a calculation\r\n     * @param calc - The Calculation object for which the helper operates\r\n     */\r\n    constructor(public calc: Calculation) {\r\n        if (!calc || Object.keys(calc).length === 0) {\r\n            calc = CalculatorLogic.getBlank();\r\n        }\r\n    }\r\n\r\n    /** Stores the UI properties to the calculation until a roundtrip to server. Then the property is set to null */\r\n    public get ui(): any {\r\n      if (!this.calc) {\r\n        return null;\r\n      }\r\n      const calcAsAny = this.calc as any;\r\n      calcAsAny.$ui = calcAsAny.$ui || {};\r\n      calcAsAny.$ui.activePanels = calcAsAny.$ui.activePanels || [];\r\n      return calcAsAny.$ui;\r\n    }\r\n\r\n    /**\r\n     * Toggles the user interface panels active (open/close) in a hierarchical way.\r\n     * The functionality mimics a hierarchical panel/menu structure in HTML / components that are not hierarchical.\r\n     * See the example to better understand the logic.\r\n     * Hierarchy logic is supported to 2 levels only - it is not tested on deeper hierarchy though it may function.\r\n     * @param panels - Identifiers of panel or two panels (panel and its child) that should be toggled.\r\n     * @example\r\n     * Assume we have these two panels open: \"panel1\", \"panel2\"\r\n     *\r\n     * - togglePanel(\"panel1\", \"panel2\") => [\"panel1\"]      // Normal 2nd level toggle opens and closes the last level.\r\n     * - togglePanel(\"panel2\") => [\"panel1\"]                // Alternative explicit last level close\r\n     * - togglePanel(\"panel1\") => []                        // Normal 1st level toggle opens and closes the first level\r\n     * - togglePanel(\"panel3\") => [\"panel3\"]                // Opening another \"path\" of the hierarchy\r\n     * - togglePanel(\"panel3\", \"panel4\") => [\"panel3\", \"panel4\"]\r\n     * - togglePanel(\"panel1\", \"panel4\") => [\"panel1\", \"panel4\"]    // Being a separate \"path\" is determined by last element only\r\n     * - togglePanel(\"last\") => [\"panel1\"]                  // Special keyword for closing the last panel\r\n     * - togglePanel() => []                                // Closes all panels\r\n     */\r\n    public toggleActivePanel(...panels: any[]) {\r\n        if (panels.length === 0 || !panels[0]) {\r\n            // Closing all\r\n            this.ui.activePanels = [];\r\n            return;\r\n        }\r\n        if (panels[0] === \"last\") {\r\n            // Closing last\r\n            if (this.ui.activePanels.length > 0) {\r\n                this.ui.activePanels.splice(this.ui.activePanels.length - 1);\r\n            }\r\n            return;\r\n        }\r\n        const positionOfLastPanel = this.ui.activePanels.indexOf(panels[panels.length - 1]);\r\n        if (positionOfLastPanel === -1) {\r\n            // New hierarchy path\r\n            this.ui.activePanels = panels;\r\n        } else {\r\n            // Remove starting from the match\r\n            this.ui.activePanels.splice(positionOfLastPanel, this.ui.activePanels.length);\r\n        }\r\n    }\r\n\r\n    /**\r\n     * Returns true if the panel is active (open).\r\n     * @param panel - identifier of the panel.\r\n     */\r\n    public isPanelActive(panel: string) {\r\n        return (this.ui.activePanels as string[]).indexOf(panel) >= 0;\r\n    }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Dates, Invoice, InvoicePreview, Numeric, BicHelper, Iban, InvoicesLogic } from \"@salaxy/core\";\r\nimport { Barcodes, QrCodes } from \"@salaxy/reports\";\r\n/**\r\n * Shows an invoice as credit transfer: Either as printable display, copy-pasteable barcode or both.\r\n */\r\nexport class CreditTransferController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$scope\", \"$sce\", \"$timeout\"];\r\n\r\n  /** Invoice that is shown as credit transfer: The main data object. */\r\n  public invoice: Invoice;\r\n\r\n  private invoiceQrCode = \"\";\r\n\r\n  /**\r\n   * Display mode is either\r\n   *\r\n   * - \"official\": The official printable credit transfer (Finanssialan keskusliitto)\r\n   * - \"barcode-copy\": The copy-paste input + button (in a div) for copy pasting the the barcode into a web bank\r\n   * - \"default\": Both of the above separted by an explaining text.\r\n   */\r\n  public mode: \"default\" | \"official\" | \"barcode-copy\";\r\n\r\n  private _invoicePreview: InvoicePreview;\r\n\r\n  /**\r\n   * Creates a new CreditTransferController.\r\n   * @ignore\r\n   */\r\n  constructor(private $scope: angular.IScope, private $sce: angular.ISCEService, private $timeout: angular.ITimeoutService) {\r\n    // Dependency injection if necessary.\r\n  }\r\n\r\n  /** Copies the barcode from input to clipboard. */\r\n  public copyBarcode(): void {\r\n    const id = \"barcode\" + this.getId();\r\n    (document.getElementById(id) as HTMLInputElement).select();\r\n    document.execCommand(\"copy\");\r\n  }\r\n\r\n  /** Gets a unique id for the barcode input (from which the copying to clipboard is done). */\r\n  public getId(): number {\r\n    return this.$scope.$id;\r\n  }\r\n\r\n  /**\r\n   * Retrieves the QR code for the specified invoice item.\r\n   * If the QR code is not already cached, it generates the QR code and caches it for future use.\r\n   * @returns The QR code string.\r\n   */\r\n  public getQrCode(): string {\r\n    if(!this.invoiceQrCode) {\r\n      this.invoiceQrCode = \"loading\";\r\n      this.generateQrCodeSvgForInvoice().then((qrCode) => {\r\n        if(!qrCode) {\r\n          this.invoiceQrCode = \"error\";\r\n          this.$timeout();\r\n          return this.invoiceQrCode;\r\n        } else {\r\n          this.invoiceQrCode = qrCode;\r\n          this.$timeout();\r\n          return this.$sce.trustAsHtml(this.invoiceQrCode);\r\n        }\r\n      });\r\n    }\r\n    if(this.invoiceQrCode === \"error\") {\r\n      return this.invoiceQrCode;\r\n    }\r\n    return this.$sce.trustAsHtml(this.invoiceQrCode);\r\n  }\r\n\r\n  /**\r\n   * Sets the Invoice based on an invoice preview (list item based preview) if the invoice is not empty.\r\n   * I.e. if you wish to set to null, you need to set the invoice null separately.\r\n   * Gets the original preview object if set.\r\n   */\r\n  public get invoicePreview(): InvoicePreview {\r\n    return this._invoicePreview;\r\n  }\r\n  public set invoicePreview(value: InvoicePreview) {\r\n    this._invoicePreview = value;\r\n    if (value?.invoice) {\r\n      this.invoice = this.getInvoice(value);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Retrieves the barcode for the invoice recipient's IBAN.\r\n   * If the IBAN does not start with \"fi\" or is not provided, an empty string is returned.\r\n   * The barcode is generated using the Barcodes.createBarcode function.\r\n   * @returns The barcode as a string, wrapped in an HTML trust object.\r\n   */\r\n  public getBarcode(): string {\r\n    if (!this.invoice?.recipient.iban || !this.invoice?.recipient.iban.toLowerCase().trim().startsWith(\"fi\")) {\r\n      return \"\";\r\n    }\r\n    const getDocumentAndSvgNode = () => {\r\n      return {document, svgNode: document.createElementNS(\"http://www.w3.org/2000/svg\", \"svg\")};\r\n    };\r\n\r\n    const result = Barcodes.createBarcode(\r\n      getDocumentAndSvgNode,\r\n      this.invoice.recipient.iban || \"\",\r\n      this.invoice.header.referenceNumber || \"\",\r\n      Dates.asDate(this.invoice.header.dueDate),\r\n      Numeric.round(this.invoice.header.total * 100, 0),\r\n      {\r\n        width: 1.42,\r\n        height: 35,\r\n        displayValue: true,\r\n        fontSize: 15\r\n      }\r\n    );\r\n    if(!result) {\r\n      return \"\";\r\n    }\r\n    return this.$sce.trustAsHtml(new XMLSerializer().serializeToString(result as any));\r\n  }\r\n\r\n  /** Barcode value */\r\n  public get bcValue(): string {\r\n    if (!this.invoice?.recipient.iban) {\r\n      return \"\";\r\n    }\r\n    return Barcodes.getValue(\r\n      this.invoice.recipient.iban || \"\",\r\n      this.invoice.header.referenceNumber || \"\",\r\n      Dates.asDate(this.invoice.header.dueDate),\r\n      Numeric.round(this.invoice.header.total * 100, 0));\r\n  }\r\n\r\n  /**\r\n   * Generates the QR code for the invoice.\r\n   */\r\n  public async generateQrCodeSvgForInvoice(): Promise<string> {\r\n    if (!this.invoice) {\r\n      return;\r\n    }\r\n    const svg = await QrCodes.getValue(\r\n      this.getBicForIban(this.invoice?.recipient?.iban),\r\n      this.invoice.recipient.fullName,\r\n      this.invoice.recipient.iban,\r\n      this.invoice.header.referenceNumber,\r\n      null,\r\n      this.invoice.header.total,\r\n      this.invoice.header.dueDate\r\n    );\r\n    return svg;\r\n  }\r\n\r\n  /**\r\n   * Returns bic for iban\r\n   * @param iban Iban to get bic for\r\n   */\r\n  public getBicForIban(iban: string): string {\r\n    return BicHelper.getBicForIban(iban);\r\n  }\r\n\r\n  /**\r\n   * Determines whether to show the QR code for the invoice.\r\n   * @returns A boolean indicating whether to show the QR code.\r\n   */\r\n  public showQrCode(): boolean {\r\n    return InvoicesLogic.isEcfa(this.invoice.header.channel);\r\n  }\r\n\r\n  /**\r\n   * Checks if the IBAN of the recipient is an international IBAN.\r\n   * @returns {boolean} True if the IBAN is international, false otherwise.\r\n   */\r\n  public isInternationalIban(): boolean {\r\n    return Iban.isInternationalIban(this.invoice.recipient.iban ?? \"\");\r\n  }\r\n\r\n  /** Maps an invoice preview object to invoice. */\r\n  private getInvoice(preview: InvoicePreview): Invoice {\r\n    if (!preview?.invoice) {\r\n      return null;\r\n    }\r\n    return {\r\n      header: {\r\n        dueDate: preview.invoice.data.dueDate,\r\n        total: preview.invoice.payment,\r\n        referenceNumber: preview.invoice.reference,\r\n      },\r\n      rows: [],\r\n      payer: {\r\n        avatar: preview.invoice.ownerInfo.avatar,\r\n        officialId: preview.invoice.ownerInfo.officialId,\r\n        contact: {\r\n          email: preview.invoice.ownerInfo.email,\r\n          telephone: preview.invoice.ownerInfo.telephone,\r\n        },\r\n      },\r\n      recipient: {\r\n        fullName: preview.invoice.otherPartyInfo.avatar.displayName,\r\n        iban: preview.invoice.otherPartyInfo.ibanNumber,\r\n        officialId: preview.invoice.otherPartyInfo.officialId,\r\n        contact: {\r\n          email: preview.invoice.otherPartyInfo.email,\r\n          telephone: preview.invoice.otherPartyInfo.telephone,\r\n        },\r\n      },\r\n    };\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {\r\n  ApiListItemValidation, BootstrapStyle, calcReportType, Calculation, CalculationResult, CalculationResultLogic, Calculations,\r\n  CalendarEvents, Dates, Employments, InputEnumOption, MessageFrom, MessageThreadStatus, Objects, ODataResult, PaymentChannel, Payroll03Info, PayrollDetails,\r\n  Payrolls, PayrollStatus, SalaryDateKind, SalaryDateLogic, ThreadedMessageType, Translations, TaxcardUiInfo, TaxCard2019Logic, IApiListItem, PayrollListItem,\r\n  Taxcards,\r\n  EmploymentRelationTaxcard, HolidayCode, Arrays,\r\n  AbsenceCauseCode\r\n} from \"@salaxy/core\";\r\n\r\nimport { InvoicesService, ReportsService, SessionService, UiCrudHelpers, UiHelpers } from \"../../services\";\r\nimport { ApiCrudObjectController } from \"../bases\";\r\nimport { PayrollLogic } from \"./PayrollLogic\";\r\nimport { MessageThreadCrudController } from \"../communications\";\r\n\r\n/**\r\n * Payroll (Palkkalista) is a list of employees who receive salary or wages from a particular organization.\r\n * Typical usecase is that a a company has e.g. a monthly salary list that is paid\r\n * at the end of month. For next month, a copy is then made from the latest list and\r\n * the copy is potentially modified with the changes of that particular month.\r\n */\r\nexport class PayrollCrudController extends ApiCrudObjectController<PayrollDetails, PayrollListItem> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Payrolls\", \"UiHelpers\", \"UiCrudHelpers\", \"$location\", \"$routeParams\", \"Calculations\", \"ReportsService\", \"SessionService\", \"InvoicesService\", \"CalendarEvents\", \"Employments\", \"$timeout\", \"Taxcards\"];\r\n\r\n  /** Index of the active tab in the combined edit view. */\r\n  public activeTab = \"properties\";\r\n\r\n  /** Flags to indicate if the request is in progress */\r\n  public loaders: any = {};\r\n\r\n  /**\r\n   * Action buttons that are visible in the user interface.\r\n   * Default is \"copy\", \"cancel\". If read only is forced neither is included.\r\n   * TODO: Current implementation is for read-only view only.\r\n   */\r\n  public actions: (\"none\" | \"copy\" | \"pay\" | \"cancel\")[];\r\n\r\n  /** All employment list items related to all calcs in payroll. */\r\n  private _employments: { [key: string]: IApiListItem } = {};\r\n\r\n  /** TODO: Items to refactor before going to production. */\r\n  /** Cache for changedCalcCount so that it is called only once within on $digest loop. */\r\n  protected changedCalcCountCache;\r\n\r\n  /** User interface related properties. */\r\n  private calcUiProperties: {\r\n    /** Calculation ID */\r\n    id: string,\r\n    /** If true, the calc is in edit mode. */\r\n    isInEdit: boolean,\r\n    /** If true, the calculation is in collapsed mode (not showing the details) */\r\n    isCollapsed: boolean,\r\n  }[] = [];\r\n\r\n  /**\r\n   * Reference to the latest calculation result\r\n   */\r\n  private _calcsResult: CalculationResult;\r\n\r\n  /**\r\n   * Reference to empty calculation array.\r\n   * Prevents infinite $digest iterations, when the reference to empty array does not change.\r\n   */\r\n  private emptyCalcList: Calculation[] = [];\r\n\r\n  /** Available channels */\r\n  private _availableChannels: Array<{ value: string, text: string }> = [];\r\n\r\n  constructor(\r\n    private payrollsApi: Payrolls,\r\n    uiHelpers: UiHelpers,\r\n    private uiCrudHelpers: UiCrudHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    private calcsApi: Calculations,\r\n    private reportsService: ReportsService,\r\n    private sessionService: SessionService,\r\n    private invoicesService: InvoicesService,\r\n    private calendarEvents: CalendarEvents,\r\n    private employmentsApi: Employments,\r\n    private $timeout: angular.ITimeoutService,\r\n    private taxcardsApi: Taxcards,\r\n  ) {\r\n    // Dependency injection\r\n    super(payrollsApi, uiHelpers, $location, $routeParams);\r\n  }\r\n\r\n  /**\r\n   * Initialization code.\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n    if (this.isReadOnlyForced) {\r\n      this.activeTab = \"reports\";\r\n    }\r\n  }\r\n\r\n  /** Catched the return of reload to update values. */\r\n  public reload(): Promise<PayrollDetails> {\r\n    return super.reload().then((payroll) => {\r\n      if (super.isNew()) {\r\n        this.setPaymentChannel(payroll);\r\n      }\r\n      return payroll;\r\n    });\r\n  }\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"/payroll\",\r\n      detailsUrl: this.detailsUrl || \"/payroll/details/\",\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/Payrolls.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n\r\n\r\n  /**\r\n   * Returns true, if the given action button should be shown\r\n   * @param action One of the action values: See actions field type for supported values.\r\n   */\r\n  public showAction(action: string): boolean {\r\n    const actions = this.actions?.length ? this.actions :\r\n      this.isReadOnlyForced ? [] : [\"copy\", \"cancel\"];\r\n\r\n    if (action === \"pay\") {\r\n      // Check action and status\r\n      return !!actions.find(x => x == action) &&\r\n      ( !!this.current &&\r\n        ( this.current.info.status === PayrollStatus.Draft ||\r\n          this.current.info.status === PayrollStatus.WaitingApproval\r\n        )\r\n      );\r\n    }\r\n\r\n    return !!actions.find(x => x == action);\r\n  }\r\n\r\n  /** Returns true if any calculations have been added to the Payroll */\r\n  public get hasCalculations() {\r\n    return this.current && this.current.calcs.length > 0;\r\n  }\r\n\r\n  /** Save changes to the payroll as well as to changed calculations */\r\n  public save(): Promise<PayrollDetails> {\r\n    if (this.changedCalcCount > 0) {\r\n      // Just to not show \"Saving calculations...\"\r\n      return this.commitAllCalcs().then(() => {\r\n        return super.save();\r\n      });\r\n    }\r\n    return super.save();\r\n  }\r\n\r\n  /** Recalculate and save worktimes of all calculations. */\r\n  public recalculateWorktimes(): Promise<Calculation[]> {\r\n    const loader = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    const recalcs: Promise<Calculation>[] = this.calcs.map((apiCalc) => {\r\n    return this.calcsApi.getWorktimeData(apiCalc).then((worktime) => {\r\n      apiCalc.worktime = worktime;\r\n      return this.calcsApi.recalculateWorktime(apiCalc).then((resultCalc) => {\r\n          return angular.copy(resultCalc, apiCalc);\r\n        });\r\n      });\r\n    });\r\n    return Promise.all(recalcs).then((result) => {\r\n      loader.dismiss();\r\n      return result;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Calculates the total amount of days for the given period type.\r\n   * @param calc Calculation to calculate days for.\r\n   * @param periodType Period type to calculate days for.\r\n   * @returns Sum of days for the given period type.\r\n   */\r\n  public calculatePeriodDays(calc: Calculation, periodType: \"absencesDays\"  | \"leavesDays\" | \"paidAbsencesDays\" | \"accruedDays\") {\r\n    switch (periodType) {\r\n      case \"leavesDays\":\r\n        return Arrays.sum(calc.worktime?.absencesPeriods?.filter(x => x.causeCode == AbsenceCauseCode.AnnualLeave) ?? [], (x) => x.period.daysCount);\r\n      case \"absencesDays\":\r\n        return Arrays.sum(calc.worktime?.absencesPeriods?.filter(x => x.causeCode != AbsenceCauseCode.AnnualLeave && !x.isPaid) ?? [], (x) => x.period.daysCount);\r\n      case \"paidAbsencesDays\":\r\n        return Arrays.sum(calc.worktime?.absencesPeriods?.filter(x => x.causeCode != AbsenceCauseCode.AnnualLeave && x.isPaid) ?? [], (x) => x.period.daysCount);\r\n      case \"accruedDays\":\r\n        if (this.showAccruals(calc)) {\r\n          return Arrays.sum(calc.worktime?.accruals, (x) => x.daysAccrued);\r\n        }\r\n        return 0;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Returns true if the accruals are accumulated.\r\n   * @param calc Calculation.\r\n   * @returns Returns true if the accruals are accumulated.\r\n   */\r\n  public showAccruals(calc: Calculation) {\r\n    return calc.worktime?.accrualSpec?.code ==  HolidayCode.Permanent14Days || calc.worktime?.accrualSpec?.code ==  HolidayCode.Permanent35Hours || calc.worktime?.accrualSpec?.code ==  HolidayCode.TemporaryTimeOff || calc.worktime?.accrualSpec?.code == HolidayCode.Other || calc.worktime?.accrualSpec?.code == HolidayCode.Script;\r\n  }\r\n\r\n  /**\r\n   * Creates a copy of a payroll\r\n   * This is a synchronous method that should basically convert a saved item to a new item.\r\n   * @param copySource Item (container item) to copy as new.\r\n   */\r\n  public copyItem(copySource: PayrollDetails): PayrollDetails {\r\n    const oldId = copySource.id;\r\n    const copy = super.copyItem(copySource);\r\n    copy.info.messageThreadId = null;\r\n    if (copy.info.status === PayrollStatus.Template) {\r\n      copy.input.template = oldId;\r\n      copy.info.status = PayrollStatus.Draft;\r\n    }\r\n    // HACK: remove payroll-service flag. This will be replaced with invoicing flags eventually.\r\n    if (copy.usecase &&\r\n      (copy.usecase.uri === \"palkkaus.fi/usecases/payroll-service/pro-calc\" ||\r\n        copy.usecase.uri === \"palkkaus.fi/usecases/payroll-service/calc\")) {\r\n      copy.usecase = {};\r\n    }\r\n    return copy;\r\n  }\r\n\r\n  /**\r\n   * Reloads the validations and info for the current item.\r\n   * These are constructed based on calculations data and if changed, will update the Payroll in storage.\r\n   */\r\n  public reloadValidation() {\r\n    // TODO: Add indication that validation is being updated.\r\n    // TODO: This would become obsolete when we separate calculations modification to a separate controller.\r\n    if (this.currentId) {\r\n      this.api.getSingle(this.currentId).then((payroll) => {\r\n        this.current.validations = payroll.validations;\r\n        this.current.info = payroll.info;\r\n        this.original.validations = payroll.validations;\r\n        this.original.info = payroll.info;\r\n      });\r\n    }\r\n  }\r\n\r\n  /** Gets a validation object for a calculation */\r\n  public getValidation(calc: Calculation): ApiListItemValidation {\r\n    return this.current.validations.find((x) => x.id === calc.id) || {\r\n      id: calc.id, // Paid Payrolls will not have validations.\r\n      isValid: true,\r\n    };\r\n  }\r\n\r\n  /** UI related data and texts about the taxcard. */\r\n  public getTaxUi(calc: Calculation): TaxcardUiInfo {\r\n    return TaxCard2019Logic.getCalcTaxcardInfo(calc);\r\n  }\r\n\r\n  /** Show add new taxcard dialog */\r\n  public async showAddNewTaxcard(calc: Calculation) {\r\n    const empl = await this.employmentsApi.getSingle(calc.worker.employmentId);\r\n    if (!empl) {\r\n      return;\r\n    }\r\n\r\n    // try to set to auto as first\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    if(empl.info.taxcard==EmploymentRelationTaxcard.Undefined || empl.info.taxcard==EmploymentRelationTaxcard.Auto){\r\n      const taxcard = await this.taxcardsApi.setAuto(calc.worker.paymentData.socialSecurityNumberValid);\r\n      if (taxcard) {\r\n        await this.commitCalc(calc, false, true);\r\n        loading.dismiss();\r\n        return;\r\n      }\r\n    }\r\n\r\n    const result = await this.uiCrudHelpers.createNewTaxcard(calc.worker.paymentData.socialSecurityNumberValid);\r\n    if (result.action === \"ok\") {\r\n      await this.commitCalc(calc, false, true);\r\n      loading.dismiss();\r\n      return;\r\n    }\r\n\r\n    loading.dismiss();\r\n  }\r\n\r\n  /**\r\n   * Returns true if the date is overdue (smaller than today).\r\n   * @param date Date to compare to today.\r\n   */\r\n  public isOverdue(date: string): boolean {\r\n    date = Dates.asDate(date);\r\n    return date < Dates.getToday();\r\n  }\r\n\r\n  /** Gets the list of calculations in this payroll object */\r\n  public get calcs(): Calculation[] {\r\n    return this.current ? this.current.calcs : this.emptyCalcList;\r\n  }\r\n\r\n  /** Returns the constantly updating info component from the open calculations (without round-trip to server) */\r\n  public get info(): Payroll03Info {\r\n    return PayrollLogic.getInfo(this.current, this.calcs);\r\n  }\r\n\r\n  /** Summarized CalculationResult for all calculations in the payroll. */\r\n  public get calcsResult(): CalculationResult {\r\n    const result = CalculationResultLogic.add(this.calcs.map((x) => x.result));\r\n    if (!angular.equals(result, this._calcsResult)) {\r\n      this._calcsResult = result;\r\n    }\r\n    return this._calcsResult;\r\n  }\r\n\r\n  /** Returns true if there is no net salary payment to worker at all. */\r\n  public get isCurrentZeroPayment(): boolean {\r\n    return PayrollLogic.isZeroPayment(this.calcs ?? []);\r\n  }\r\n\r\n  /** Disable function for the salary date picker. */\r\n  public isDisabledSalaryDate = (date): boolean => {\r\n    const role = this.sessionService.isInRole(\"pro\") ? \"pro\" :\r\n      this.sessionService.isInRole(\"admin\") ? \"admin\" : null;\r\n    switch (this.current.input.salaryDateKind) {\r\n      case SalaryDateKind.InPast:\r\n        return false;\r\n      case SalaryDateKind.Default:\r\n      default:\r\n        return !SalaryDateLogic.isValidSalaryDate(date, null, null, true, this.current.input.paymentChannel, PayrollLogic.isZeroPayment(this.calcs ?? []), role);\r\n    }\r\n  };\r\n\r\n  /**\r\n   * Checks if user is in one of the given roles.\r\n   * @param roles A comma separated list of roles, potentially with exlamation mark\r\n   */\r\n  public isInSomeRole(roles: string): boolean {\r\n    return this.sessionService.isInSomeRole(roles);\r\n  }\r\n\r\n  /** Gets the UI properties for a calculation */\r\n  public getUi(calc: Calculation): {\r\n    /** Calculation ID */\r\n    id: string,\r\n    /** If true, the calc is in edit mode. */\r\n    isInEdit: boolean,\r\n    /** If true, the calculation is in collabsed mode (not showing the details) */\r\n    isCollapsed: boolean,\r\n  } {\r\n    if (!calc || !calc.id) {\r\n      return {} as any;\r\n    }\r\n    let ui = this.calcUiProperties.find((x) => x.id === calc.id);\r\n    if (ui == null) {\r\n      ui = {\r\n        id: calc.id,\r\n        isCollapsed: true,\r\n        isInEdit: false,\r\n      };\r\n      this.calcUiProperties.push(ui);\r\n    }\r\n    return ui;\r\n  }\r\n\r\n  /**\r\n   * Set calculation rows editable\r\n   */\r\n  public setRowsEditable(calc: Calculation | \"all\") {\r\n    if (calc === \"all\") {\r\n      this.setUiForAll(\"isInEdit\", true);\r\n      this.setUiForAll(\"isCollapsed\", false);\r\n    } else {\r\n      this.getUi(calc).isCollapsed = false;\r\n      this.getUi(calc).isInEdit = false; // First to false to assure firing of the setter.\r\n      this.getUi(calc).isInEdit = true;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Sets a UI property for all calculations.\r\n   * @param prop Name of the property to set.\r\n   * @param value New value for the property.\r\n   */\r\n  public setUiForAll(prop: \"isCollapsed\" | \"isInEdit\", value: boolean) {\r\n    this.calcs.forEach((calc) => {\r\n      this.getUi(calc)[prop] = value;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Recalculates and saves calculation to the server.\r\n   * @param calc Calculation to save.\r\n   * @param noReloadValidation If true, the parent should call reloadValidation().\r\n   * @param forceSave If true, changes are saved even when there are no changes.\r\n   */\r\n  public commitCalc(calc: Calculation, noReloadValidation = false, forceSave = false): Promise<{\r\n    /** Calculation (after save, if saved) */\r\n    calc: Calculation,\r\n    /** True, if the calculation was saved. Unchanged calculations are not saved. */\r\n    isSaved: boolean,\r\n  }> {\r\n    this.getUi(calc).isInEdit = false;\r\n    if (forceSave || this.hasCalcChanges(calc)) {\r\n      return this.payrollsApi.calculationSave(calc, this.current.id).then((result) => {\r\n        if (!noReloadValidation) {\r\n          this.reloadValidation();\r\n        }\r\n        return this.setCalc(result);\r\n      });\r\n    }\r\n    return Promise.resolve({ calc, isSaved: false });\r\n  }\r\n\r\n  /** Sets the calculation after round-trip from the server. */\r\n  public setCalc = (newCalc: Calculation) => {\r\n    const oldCalc = this.current.calcs.find((x) => x.id === newCalc.id);\r\n    const originalCalc = this.original.calcs.find((x) => x.id === newCalc.id);\r\n    angular.copy(newCalc, oldCalc);\r\n    angular.copy(newCalc, originalCalc);\r\n    return { calc: newCalc, isSaved: true };\r\n  };\r\n\r\n  /**\r\n   * Reset any modifications to a calculation.\r\n   * @param calc Calculation that was edited.\r\n   */\r\n  public resetCalc(calc: Calculation) {\r\n    this.getUi(calc).isInEdit = false;\r\n    if (this.hasCalcChanges(calc)) {\r\n      const originalCalc = this.original.calcs.find((x) => x.id === calc.id);\r\n      angular.copy(originalCalc, calc);\r\n    }\r\n  }\r\n\r\n  /** Gets the count of changed calculations. */\r\n  public get changedCalcCount() {\r\n    // Cache within one $digest loop.\r\n    this.changedCalcCountCache = this.calcs.filter((x) => this.hasCalcChanges(x)).length;\r\n    return this.changedCalcCountCache;\r\n  }\r\n\r\n  /** Returns true if a calculation has changes to its original. */\r\n  public hasCalcChanges(calc: Calculation): boolean {\r\n    // TODO: Move this check to be run in every $digest loop\r\n    const originalCalc = this.original.calcs.find((x) => x.id === calc.id);\r\n    if (!originalCalc) {\r\n      throw new Error(\"Unexpected: No original calc in hasCalcChanges.\");\r\n    }\r\n    return !angular.equals(originalCalc, calc);\r\n  }\r\n\r\n  /**\r\n   * Commits changes to all calculations that are in edit mode.\r\n   * @returns A promise with the number of saved (changed) calculations.\r\n   */\r\n  public commitAllCalcs(): Promise<number> {\r\n    const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.PayrollComponent.commitAllCalcs.heading\");\r\n    this.setUiForAll(\"isCollapsed\", true);\r\n    this.setUiForAll(\"isInEdit\", false);\r\n    const promises = this.calcs.map((x) => this.commitCalc(x, true));\r\n    return Promise.all(promises).then((result) => {\r\n      loader.dismiss();\r\n      this.reloadValidation();\r\n      return result.filter((x) => x.isSaved).length;\r\n    });\r\n  }\r\n\r\n  /** Resets all calculations to their unsaved state. */\r\n  public resetAllCalcs() {\r\n    this.calcs.forEach((x) => this.resetCalc(x));\r\n  }\r\n\r\n  /**\r\n   * Opens DateRange component in modal dialog.\r\n   * If daterange is changed asks whether all calculations should be changed to a new period.\r\n   * Saves changes to server.\r\n   */\r\n  public showDateRange() {\r\n    this.uiHelpers.showDateRange(this.current.input.period, \"SALAXY.NG1.PayrollComponent.showDateRangeTitle\", \"SALAXY.UI_Terms.save\").then((result) => {\r\n      if (result.result === \"ok\" && result.hasChanges && this.calcs.length > 0) {\r\n        this.uiHelpers.showConfirm(\"SALAXY.NG1.PayrollComponent.showDateRangeDialogTitle\",\r\n          \"SALAXY.NG1.PayrollComponent.showDateRangeDialogDescr\",\r\n          \"SALAXY.UI_Terms.yes\", \"SALAXY.UI_Terms.no\").then((value) => {\r\n            if (value) {\r\n              this.calcs.forEach((calc) => {\r\n                calc.info.workStartDate = this.current.input.period.start;\r\n                calc.info.workEndDate = this.current.input.period.end;\r\n                calc.framework.numberOfDays = this.current.input.period.daysCount;\r\n              });\r\n              this.save();\r\n            } else {\r\n              super.save();\r\n            }\r\n          });\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shows a DateRange edit component for a single calculation.\r\n   * @param calc Calculation to modify.\r\n   */\r\n  public showDateRangeForCalculation(calc: Calculation) {\r\n    this.uiHelpers.showDateRange(calc, \"SALAXY.NG1.PayrollComponent.showDateRangeTitle\", \"SALAXY.UI_Terms.ok\");\r\n  }\r\n\r\n  /**\r\n   * Shows the calculation in a new dialog.\r\n   * @param calc Calculation to modify / view in dialog.\r\n   */\r\n  public showEditCalcDialog(calc: Calculation, dialog: \"default\" | \"ir\" = \"default\"): Promise<Calculation> {\r\n    const template = dialog === \"ir\" ? \"salaxy-components/modals/calc/CalcIr.html\" : \"salaxy-components/modals/calc/Calc.html\";\r\n    const title = dialog === \"ir\" ? Translations.get(\"SALAXY.NG1.CalcReportsComponent.irRows\") : Translations.get(\"SALAXY.NG1.PayrollComponent.showEditCalcDialog\");\r\n    return this.uiHelpers.openEditDialog(\r\n      template,\r\n      calc,\r\n      {\r\n        title,\r\n      },\r\n      \"xl\",\r\n    ).then((result) => {\r\n      if (result.action === \"ok\") {\r\n        if (result.hasChanges) {\r\n          return this.commitCalc(result.item).then((result) => {\r\n            return result.calc;\r\n          });\r\n        } else {\r\n          return calc;\r\n        }\r\n      } else if (result.action === \"delete\") {\r\n        this.deleteCalc(calc);\r\n        return null;\r\n      } else {\r\n        this.resetCalc(calc);\r\n        return calc;\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shows a dialog for editing an existing worker.\r\n   * @param calc - Calculation that should be edited\r\n   */\r\n  public showEditWorkerDialog(calc: Calculation): void {\r\n    if (!calc.worker?.accountId) {\r\n      this.showAddWorkerDialog(calc);\r\n    }\r\n    else {\r\n      this.uiCrudHelpers.openEditEmploymentDialog(calc.worker.employmentId, \"updateCalc\").then((result) => {\r\n        if (result.action === \"ok\" || result.action === \"ok-no-rows\") {\r\n          const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.PayrollComponent.showEditWorkerDialogUpdating\");\r\n          this.calcsApi.updateFromEmployment(calc, true, result.action === \"ok\").then((result2) => {\r\n            this.reloadValidation();\r\n            this.setCalc(result2);\r\n            loader.dismiss();\r\n          });\r\n        }\r\n      });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Opens a list of workers in to a dialog window.\r\n   * Edits the  calculation for the selected worker and current payroll.\r\n   */\r\n  public showAddWorkerDialog(calc: Calculation): void {\r\n    const workerList = [];\r\n    this.uiHelpers.openEditDialog(\r\n      \"salaxy-components/modals/calc/WorkerSelect.html\",\r\n      workerList,\r\n      {\r\n        title: \"SALAXY.NG1.PayrollComponent.validate.addWorker\",\r\n      }).then((result) => {\r\n        if (result.action === \"ok\" && result.item.length == 1) {\r\n          const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.PayrollComponent.showEditWorkerDialogUpdating\");\r\n          calc.worker.employmentId = result.item[0].id;\r\n          this.calcsApi.updateFromEmployment(calc, true, false).then((result2) => {\r\n            this.reloadValidation();\r\n            this.setCalc(result2);\r\n            loader.dismiss();\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Shows a dialog during the check of auto taxcard.\r\n   */\r\n  public showRefreshAutoTaxcardDialog(calc: Calculation) {\r\n    this.loaders[\"showRefreshAutoTaxcardDialog\"] = true;\r\n    this.uiCrudHelpers.refreshAutoTaxcard(calc.worker.tax?.taxcardId, calc.workflow?.salaryDate).then(() => {\r\n      this.commitCalc(calc, false, true);\r\n      this.loaders[\"showRefreshAutoTaxcardDialog\"] = false;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shows a confirm dialog if payroll has any calculations.\r\n   * Returns true if a user clicks OK -button. Otherwise (cancel or close) returns false.\r\n   * @returns True if the user confirmed the operation.\r\n   */\r\n  public importEmploymentDataAll(): Promise<boolean> {\r\n    const payroll = this.current as any;\r\n    if (!payroll.info.calcCount || payroll.info.calcCount === 0) {\r\n      return this.uiHelpers.showAlert(\"SALAXY.NG1.PayrollComponent.importEmploymentDataAllAlertTitle\", \"SALAXY.NG1.PayrollComponent.importEmploymentDataAllAlertDescr\").then(() => false);\r\n    } else {\r\n      return this.uiHelpers.showConfirm(\r\n        \"SALAXY.NG1.PayrollComponent.importEmploymentDataAllConfirmTitle\",\r\n        \"SALAXY.NG1.PayrollComponent.importEmploymentDataAllConfirmDescr\",\r\n        \"SALAXY.UI_Terms.continue\",\r\n        \"SALAXY.UI_Terms.cancel\",\r\n      ).then((result: boolean) => {\r\n        if (result) {\r\n          const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.PayrollComponent.importEmploymentDataAllLoading\");\r\n          const promises = this.calcs.map((x) => this.calcsApi.updateFromEmployment(x, true, true).then((result) => this.setCalc(result)));\r\n          return Promise.all(promises).then(() => {\r\n            loader.dismiss();\r\n            this.reloadValidation();\r\n            return true;\r\n          });\r\n        } else {\r\n          return false;\r\n        }\r\n      });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Adds default rows (SalaryDefault) from employment information to calculation.\r\n   * Also saves the calculation\r\n   * @param calc The calculation to update.\r\n   */\r\n  public importEmploymentData(calc: Calculation): Promise<{\r\n    /** Calculation (after save, if saved) */\r\n    calc: Calculation,\r\n    /** True, if the calculation was saved. Unchanged calculations are not saved. */\r\n    isSaved: boolean,\r\n  }> {\r\n    return this.uiHelpers.showConfirm(\r\n      \"SALAXY.NG1.PayrollComponent.importEmploymentDataTitle\",\r\n      \"SALAXY.NG1.PayrollComponent.importEmploymentDataDescr\",\r\n      \"SALAXY.UI_Terms.continue\",\r\n      \"SALAXY.UI_Terms.cancel\",\r\n    ).then((result: boolean) => {\r\n      if (result) {\r\n        const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.PayrollComponent.importEmploymentDataLoading\");\r\n        return this.calcsApi.updateFromEmployment(calc, true, true).then((result) => {\r\n          loader.dismiss();\r\n          this.reloadValidation();\r\n          return this.setCalc(result);\r\n        });\r\n      } else {\r\n        return Promise.resolve({ calc, isSaved: false });\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Show confirm dialog and export employment data from calculation to Employment relation.\r\n   * If the calculation has unmodified changes, the calculation is saved.\r\n   * @param calc Calculation that should be exported to Employment.\r\n   * @returns True if the user confirmed the operation.\r\n   */\r\n  public exportEmploymentData(calc: Calculation): Promise<boolean> {\r\n    return this.uiHelpers.showConfirm(\r\n      \"SALAXY.NG1.PayrollComponent.exportEmploymentDataTitle\",\r\n      \"SALAXY.NG1.PayrollComponent.exportEmploymentDataDescr\",\r\n      \"SALAXY.UI_Terms.continue\",\r\n      \"SALAXY.UI_Terms.cancel\",\r\n    ).then((result: boolean) => {\r\n      if (result) {\r\n        const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.PayrollComponent.exportEmploymentDataLoading\");\r\n        this.exportEmploymentDataNoConfirm(calc).then((resultInner) => {\r\n          if (resultInner.isSaved) {\r\n            this.reloadValidation();\r\n          }\r\n          loader.dismiss();\r\n          return true;\r\n        });\r\n      } else {\r\n        return false;\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Deletes the calculation\r\n   * @param calc Calculation to delete\r\n   * @param unlink If true, will not delete the actual calculation, but instead unlinks it as a separate calculation outside this payroll.\r\n   */\r\n  public deleteCalc(calc: Calculation, unlink = false) {\r\n\r\n    if (unlink) {\r\n      this.uiHelpers.showConfirm(\"SALAXY.NG1.PayrollComponent.payrollCalcs.unlinkCalcDialog.heading\",\r\n        \"SALAXY.NG1.PayrollComponent.payrollCalcs.unlinkCalcDialog.intro\",\r\n        \"SALAXY.NG1.PayrollComponent.payrollCalcs.unlinkCalcDialog.confirmButton\",\r\n        \"SALAXY.NG1.PayrollComponent.payrollCalcs.unlinkCalcDialog.cancelButton\")\r\n        .then((result: boolean) => {\r\n          if (result) {\r\n            const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.PayrollComponent.payrollCalcs.unlinkCalcDialog.loading\");\r\n            this.payrollsApi.unlinkCalculations(this.current, [calc.id])\r\n              .then((savedPayroll) => {\r\n                this.setCurrentValue(savedPayroll, true);\r\n                loader.dismiss();\r\n              });\r\n          }\r\n        });\r\n    } else {\r\n      this.uiHelpers.showConfirm(\r\n        \"SALAXY.NG1.PayrollComponent.payrollCalcs.deleteCalcDialog.heading\",\r\n        this.changedCalcCount > 0 ? \"SALAXY.NG1.PayrollComponent.payrollCalcs.deleteCalcDialog.introChanges\" : \"SALAXY.NG1.PayrollComponent.payrollCalcs.deleteCalcDialog.introNoChanges\",\r\n        \"SALAXY.NG1.PayrollComponent.payrollCalcs.deleteCalcDialog.confirmButton\",\r\n        \"SALAXY.NG1.PayrollComponent.payrollCalcs.deleteCalcDialog.cancelButton\")\r\n        .then((result: boolean) => {\r\n          if (result) {\r\n            const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.PayrollComponent.payrollCalcs.deleteCalcDialog.loading\");\r\n            this.payrollsApi.deleteCalculations(this.current, [calc.id])\r\n              .then((savedPayroll) => {\r\n                this.setCurrentValue(savedPayroll, true);\r\n                loader.dismiss();\r\n              });\r\n          }\r\n        });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Gets the URL for a payroll pdf.\r\n   * If report has not been saved (ID is null), returns null.\r\n   * @returns Url for specified report\r\n   */\r\n  public getPdfUrl() {\r\n    if (!this.current) {\r\n      return null;\r\n    }\r\n    return this.reportsService.getPdfUrlForCalcs(\"salarySlip\", this.current.calcs.filter((x) => x.id).map((x) => x.id), true);\r\n  }\r\n\r\n  /**\r\n   * Shows a report for the payroll calculation using a modal dialog.\r\n   * @param reportType - Type of report to show\r\n   * @param calculation - Calculation for the report\r\n   */\r\n  public showReport(reportType: calcReportType, calculation: Calculation) {\r\n    this.reportsService.showReportModalForCalc(reportType, calculation);\r\n  }\r\n\r\n  /**\r\n   * Opens a list of workers in to a dialog window.\r\n   * Creates a new calculation for the selected worker and current payroll.\r\n   */\r\n  public createNewCalc() {\r\n    const workerList = [];\r\n    this.uiHelpers.openEditDialog(\r\n      \"salaxy-components/modals/calc/WorkerList.html\",\r\n      workerList,\r\n      {\r\n        title: \"SALAXY.NG1.PayrollComponent.createNewCalcDialog\",\r\n      }).then((result) => {\r\n        if (result.action === \"ok\" && workerList.length > 0) {\r\n          const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.PayrollComponent.createNewCalcLoading\");\r\n          this.payrollsApi.addEmployments(this.current, workerList.map((x) => x.id))\r\n            .then((savedPayroll) => {\r\n              this.setCurrentValue(savedPayroll, true);\r\n              loader.dismiss();\r\n            });\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Opens the list of calculations into a dialog window for selection and then adds them to payroll\r\n   * @param category Either \"paid\": Read-only, a copy is added ... or \"draft\": Editable, moved with status changed.\r\n   */\r\n  public addExistingCalc(category: \"paid\" | \"draft\" = \"draft\") {\r\n    const title = (category === \"paid\" ? \"SALAXY.NG1.PayrollComponent.addExistingCalcCopy\" : \"SALAXY.NG1.PayrollComponent.addExistingCalcMove\");\r\n    this.uiHelpers.openSelectCalcs(category, title).then((result) => {\r\n      if (result.action === \"ok\" && result.item.length > 0) {\r\n        const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.PayrollComponent.addExistingCalcLoading\");\r\n        this.payrollsApi.addCalculations(this.current, result.item.map((x) => x.id))\r\n          .then((savedPayroll) => {\r\n            this.setCurrentValue(savedPayroll, true);\r\n            loader.dismiss();\r\n          });\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Opens a list of payrolls for merging the payroll calculations to the current payroll.\r\n   * @param removeImportedRows If true, the operation removes all the imported rows,\r\n   * meaning all the rows in the target Payroll calcs that have a sourceId.\r\n   */\r\n  public async mergePayroll(removeImportedRows = false): Promise<void> {\r\n    const payrolls = [];\r\n    const result = await this.uiHelpers.openEditDialog(\"salaxy-components/modals/payroll/PayrollList.html\", payrolls, {\r\n      title: \"Valitse tuotava palkkalista\",\r\n      category: \"draft\",\r\n    }, \"lg\");\r\n    if (result.action != \"ok\" || payrolls.length < 1) {\r\n      return;\r\n    }\r\n    const loader = this.uiHelpers.showLoading(\"Yhdistetään palkkalistoja\");\r\n    const source = await this.payrollsApi.getSingle(payrolls[0].id);\r\n    let target = this.current;\r\n    const targetEmployments = target.calcs.map(x => x.worker.employmentId);\r\n    const newEmployments = new Set(source.calcs.map(x => x.worker.employmentId).filter(x => targetEmployments.indexOf(x) < 0));\r\n    if (newEmployments.size) {\r\n      loader.setText(`Lisätään ${newEmployments.size} työntekijää.`);\r\n      target = await this.payrollsApi.addEmployments(target, [...newEmployments]);\r\n      this.setCurrentValue(target, true);\r\n    }\r\n\r\n    const calcsToSave: Calculation[] = [];\r\n    if (removeImportedRows) {\r\n      target.calcs.forEach((calc) => {\r\n        if (calc.rows.find(x => !!x.sourceId)) {\r\n          calc.rows = calc.rows.filter(x => !x.sourceId);\r\n          calcsToSave.push(calc);\r\n        }\r\n      });\r\n    }\r\n\r\n    source.calcs.forEach((srcCalc) => {\r\n      const targetCalc = target.calcs.find((x) => x.worker.employmentId == srcCalc.worker.employmentId);\r\n      if (!targetCalc) {\r\n        throw new Error(\"No calculation: This is unexpected.\");\r\n      }\r\n      targetCalc.rows = targetCalc.rows.filter((x) => x.sourceId != srcCalc.id);\r\n      const newRows = Objects.copy(srcCalc.rows);\r\n      newRows.forEach(row => {\r\n        row.sourceId = srcCalc.id;\r\n      });\r\n      targetCalc.rows.push(...newRows);\r\n      if (calcsToSave.indexOf(targetCalc) < 0) {\r\n        calcsToSave.push(targetCalc);\r\n      }\r\n    });\r\n    const promises = calcsToSave.map((calc) => this.payrollsApi.calculationSave(calc, target.id));\r\n    loader.setText(`Tallennetaan ${promises.length} muokattua laskelmaa.`);\r\n    const calcs = await Promise.all(promises);\r\n    calcs.forEach((calc) => {\r\n      this.setCalc(calc);\r\n    });\r\n    this.reloadValidation();\r\n    loader.dismiss();\r\n  }\r\n\r\n  /** Returns true if the period of a calculation is different than the period of the Payroll. */\r\n  public isDateDifferent(calc: Calculation) {\r\n    return calc.info.workStartDate !== this.current.input.period.start\r\n      || calc.info.workEndDate !== this.current.input.period.end\r\n      || calc.framework.numberOfDays !== this.current.input.period.daysCount;\r\n  }\r\n\r\n  /**\r\n   * If true, the form controls should be read-only (no control at all).\r\n   */\r\n  public get isReadOnly() {\r\n    return super.isReadOnly\r\n      || (\r\n        this.current.info.status === PayrollStatus.PaymentStarted &&\r\n        this.current.input.paymentChannel !== PaymentChannel.Undefined\r\n      )\r\n      || (!this.sessionService.isInRole(\"pro\") && this.current.info.status === PayrollStatus.PaymentStarted);\r\n  }\r\n\r\n  /**\r\n   * Exports employment data from calculation to Employment relation.\r\n   * If the calculation has unmodified changes, the calculation is saved.\r\n   * @param calc Calculation that should be exported to Employment.\r\n   */\r\n  private exportEmploymentDataNoConfirm(calc: Calculation): Promise<{\r\n    /** Calculation (after save, if saved) */\r\n    calc: Calculation,\r\n    /** True, if the calculation was saved. Unchanged calculations are not saved. */\r\n    isSaved: boolean,\r\n  }> {\r\n    if (this.hasCalcChanges(calc)) {\r\n      return this.calcsApi.updateToEmployment(calc).then(() => this.commitCalc(calc, true));\r\n    } else {\r\n      return this.calcsApi.updateToEmployment(calc).then(() => {\r\n        return Promise.resolve({ calc, isSaved: false });\r\n      });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Sends a payroll with messaging system and sets\r\n   * @param $msg The MessageThreadCrudController that is used for creating the message thread.\r\n   */\r\n  public sendPayroll($msg: MessageThreadCrudController): Promise<void> {\r\n    if (!$msg.current) {\r\n      $msg.model = \"new\";\r\n    }\r\n    const model = $msg.current;\r\n    model.otherParty = this.sessionService.session.settings.partner.accountId;\r\n    model.status = MessageThreadStatus.Active;\r\n    model.title = model.title || \"Palkkalista \" + this.current.input.title;\r\n    model.ownerWorkflow = {\r\n      salaryDate: this.current.info.salaryDate,\r\n    };\r\n    model.messages.push({\r\n      contentId: this.currentId,\r\n      fromParty: this.sessionService.isInRole(\"pro\") ? MessageFrom.OtherParty : MessageFrom.Owner,\r\n      type: ThreadedMessageType.Payroll\r\n    });\r\n    return $msg.save().then((msg) => {\r\n      if (this.current.info.status != PayrollStatus.WaitingApproval) {\r\n        this.current.info.messageThreadId = msg.id;\r\n        this.current.info.status = PayrollStatus.WaitingApproval;\r\n        return this.save().then(() => {\r\n          return;\r\n        });\r\n      } else {\r\n        this.current.info.messageThreadId = msg.id; // This is done by messageThread logic on server => ne need to save.\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Gets the message title for the action.\r\n   * TODO: This could be replaced by enums.\r\n   */\r\n  public getTitle(action: string) {\r\n    return this.messageActions.find((x) => x.value == action).title + \": \" + this.current.input.title;\r\n  }\r\n\r\n  /**\r\n   * Available actions for the message.\r\n   * TODO: This could be replaced by enums or it may come from Service model.\r\n   */\r\n  public messageActions: InputEnumOption[] = [\r\n    {\r\n      text: \"Maksa\",\r\n      value: \"pay\",\r\n      title: \"Maksa palkkalista\",\r\n    },/* {\r\n      text: \"Tarkista (hyväksy/hylkää)\",\r\n      value: \"approve\",\r\n      title: \"Tarkista palkkalista\",\r\n    },*/\r\n    {\r\n      text: \"Tiedoksi\",\r\n      value: \"info\",\r\n      title: \"Tiedoksi palkkalista\",\r\n    }, {\r\n      text: \"Vastaa kysymykseen\",\r\n      value: \"question\",\r\n      title: \"Kysymyksiä palkkalistasta\",\r\n    }\r\n  ];\r\n\r\n  /**\r\n   * Deletes a linked message: Both the message thread and msg id in this payroll.\r\n   * @param $msg The MessageThreadCrudController that contains the current message.\r\n   */\r\n  public deleteMessage($msg: MessageThreadCrudController) {\r\n    this.uiHelpers.showConfirm(\"Haluatko poistaa viestiketjun?\", \"Haluatko varmasti poistaa viestiketjun?\")\r\n      .then((result) => {\r\n        if (result) {\r\n          if ($msg.current) {\r\n            $msg.deleteNoConfirm($msg.current).then(() => {\r\n              this.current.info.messageThreadId = null;\r\n              this.save();\r\n            });\r\n          } else {\r\n            this.current.info.messageThreadId = null;\r\n            this.save();\r\n          }\r\n        }\r\n      });\r\n  }\r\n\r\n  /** Shows the paymentd dialog / the invoices UI. */\r\n  public showPaymentDialog() {\r\n    this.invoicesService.showPaymentDialog(this.current);\r\n  }\r\n\r\n  private setPaymentChannel(payroll: PayrollDetails) {\r\n    if (payroll && payroll.input) {\r\n      payroll.input.paymentChannel = this.invoicesService.defaultChannel;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Sends the payroll from company to PRO.\r\n   * @param message Message to the accountant\r\n   */\r\n  public sendToPro(message: string): void {\r\n    const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.PayrollComponent.sendToProSending\", \"SALAXY.NG1.PayrollComponent.sendToProSendingDescr\");\r\n    this.current.info.status = PayrollStatus.Draft;\r\n    this.save().then(() => {\r\n\r\n      this.api.saveWorkflowEvent(this.current, {\r\n        type: \"PartnerMessageClosed\",\r\n        ui: BootstrapStyle.Success,\r\n        message: message ? Translations.get(\"SALAXY.NG1.PayrollComponent.sendToProMessage\") + message : Translations.get(\"SALAXY.NG1.PayrollComponent.sendToProMessageChecked\"),\r\n      }).then(() => {\r\n        loader.dismiss();\r\n        this.$location.path(\"/\");\r\n      });\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Cancels the payment or invoice processing for the current payroll.\r\n   */\r\n  public cancel(): Promise<PayrollDetails> {\r\n    const eprWarningMessage = this.invoicesService.getEprWarningForCancellation(this.current.info.salaryDate, this.current.info.status == PayrollStatus.PaymentSucceeded);\r\n    const eprText = eprWarningMessage ? \"\\n\" + eprWarningMessage : \"\";\r\n    return this.uiHelpers.showConfirm(Translations.get(\"SALAXY.NG1.CalcResultsComponent.cancelDialogTitle\") + \"?\", Translations.get(\"SALAXY.NG1.CalcResultsComponent.cancelDialogDescr\") + `${eprText}`, \"SALAXY.NG1.CalcResultsComponent.cancelDialogYes\", \"SALAXY.NG1.CalcResultsComponent.cancelDialogNo\").then((result) => {\r\n      if (result) {\r\n        const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n        return this.payrollsApi.cancel(this.currentId).then((item: PayrollDetails) => {\r\n          this.setCurrentValue(item);\r\n          loading.dismiss();\r\n          return this.current;\r\n        });\r\n      } else {\r\n        return this.current;\r\n      }\r\n    });\r\n  }\r\n\r\n  /** Fetches and returns all employment list items related to all calcs in payroll. */\r\n  public get employments(): { [key: string]: IApiListItem } {\r\n    if (this.calcs) {\r\n      const calcsEmploymentIds = this.calcs.map((x) => x.worker.employmentId).filter((x) => !!x);\r\n      if (calcsEmploymentIds.length > 0) {\r\n        const fetchedEmploymenIds = Object.keys(this._employments);\r\n        const missingIds = calcsEmploymentIds.filter((x) => fetchedEmploymenIds.indexOf(x) < 0);\r\n        if (missingIds.length > 0) {\r\n          Object.assign(this._employments, Object.fromEntries(missingIds.map((id) => [id, undefined])));\r\n          const chunkSize = 15; // maximum possible without maxNodeCount error\r\n          const calls: Promise<ODataResult<any>>[] = [];\r\n          for (let i = 0; i < missingIds.length; i += chunkSize) {\r\n            const callIds = missingIds.slice(i, i + chunkSize);\r\n            calls.push(this.employmentsApi.getOData({ $filter: callIds.map((id) => `id eq '${id}'`).join(\" or \") }));\r\n          }\r\n          Promise.all(calls).then((results) => {\r\n            results.forEach((result) => {\r\n              result.items.forEach((item) => {\r\n                this._employments[item.id] = item;\r\n              });\r\n            });\r\n            this.$timeout();\r\n          });\r\n        }\r\n      }\r\n    }\r\n\r\n    return this._employments;\r\n  }\r\n}","import angular from \"angular\";\r\n\r\nimport {\r\n  ContactType, EmploymentLogic, Dates, Taxcards, EmploymentRelationTaxcard, MessageThreadStatus, MessageFrom,\r\n  ThreadedMessageType, Arrays, Numeric, PayrollDetails, Payrolls4, PayrollListItem, CalculationListItem, Calculation,\r\n  Calculations, PayrollStatus, SalaryDateKind, SalaryDateLogic, Translations, Employment, Employments, InvoicesLogic,\r\n  ApiListItemValidation, CalculationStatus, InputEnumOption, HolidayCode, AbsenceCauseCode, Objects, WorktimeImport,\r\n  EmploymentRelationType, WorktimeImportRow, IApiListItem, ODataResult\r\n} from \"@salaxy/core\";\r\n\r\nimport { UiHelpers, UiCrudHelpers, InvoicesService, UserSettingsService, SessionService } from \"../../services\";\r\nimport { ApiCrudObjectController } from \"../bases\";\r\nimport { MessageThreadCrudController } from \"../communications/MessageThreadCrudController\";\r\nimport { TabButtonsController } from \"../../controllers/helpers/TabButtonsController\";\r\n/**\r\n * Payroll header change info.\r\n */\r\nclass HeaderChangeInfo {\r\n\r\n  /** The payment channel has been changed. */\r\n  public isPaymentChannelChanged: boolean;\r\n  /** The period has been changed. */\r\n  public isPeriodChanged: boolean;\r\n  /** Salary date or salary date kind has been changed */\r\n  public isSalaryDateChanged: boolean;\r\n}\r\n\r\n/**\r\n * v4 version of the Payrolls CRUD Controller.\r\n */\r\nexport class Payroll4CrudController extends ApiCrudObjectController<PayrollDetails, PayrollListItem> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Payrolls4\", \"UiHelpers\", \"$location\", \"$routeParams\", \"Calculations\", \"Employments\", \"InvoicesService\", \"$timeout\", \"UserSettingsService\", \"SessionService\", \"Taxcards\", \"UiCrudHelpers\", \"$rootScope\", \"$scope\"];\r\n\r\n  /** Current calculation ID if one is selected. */\r\n  public calcId: string | undefined;\r\n\r\n  /** Current calculation if on is selected and loaded. */\r\n  public calc: Calculation | undefined;\r\n\r\n  /** Original calculation */\r\n  public originalCalc: Calculation | undefined;\r\n\r\n  /** Current calc list item*/\r\n  public calcListItem: CalculationListItem | undefined;\r\n\r\n  /** Active tab for single calculation. */\r\n  public calcTab = \"rows\";\r\n\r\n  /** Flags to indicate if the request is in progress */\r\n  public loaders: any = {};\r\n\r\n  /** Flag for showing the header dialog */\r\n  public showHeader = false;\r\n\r\n  /** Calculations for the reports. */\r\n  public reportCalcs: CalculationListItem[] = [];\r\n\r\n  /** Tab buttons component controller, to programmatically change tabs. */\r\n  private tabButtonsCtrl: TabButtonsController;\r\n\r\n  /**\r\n   * Action buttons that are visible in the user interface.\r\n   * Default is \"copy\", \"cancel\". If read only is forced neither is included.\r\n   * TODO: Current implementation is for read-only view only.\r\n   */\r\n  public actions: (\"none\" | \"copy\" | \"pay\" | \"cancel\")[];\r\n\r\n  /** order field */\r\n  public orderField: string = undefined;\r\n  /** order direction */\r\n  public orderReverse: boolean = false;\r\n\r\n  /** Page size */\r\n  public pageSize = 20;\r\n\r\n  /** List of employments data for the calcs. */\r\n  public employments: { [key: string]: IApiListItem };\r\n\r\n  /** Page size options */\r\n  public pageSizeOptions = { \"10\": \"10\", \"20\": \"20\", \"30\": \"30\", \"40\": \"40\", \"50\": \"50\" };\r\n\r\n  /** AI assistant  */\r\n  private _openAiKey: string = null;\r\n\r\n  /** Column filter choices that affect the backend query. */\r\n  private columnFilters = {\r\n    \"PartnerMessageClosed\": \"\",\r\n    \"PartnerMessageIssue\": \"\"\r\n  };\r\n\r\n  constructor(\r\n    private payrollsApi: Payrolls4,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    private calcsApi: Calculations,\r\n    private employmentsApi: Employments,\r\n    private invoicesService: InvoicesService,\r\n    private $timeout: angular.ITimeoutService,\r\n    private userSettingsService: UserSettingsService,\r\n    private sessionService: SessionService,\r\n    private taxcardsApi: Taxcards,\r\n    private uiCrudHelpers: UiCrudHelpers,\r\n    private $rootScope: angular.IRootScopeService,\r\n    private $scope: angular.IScope,\r\n  ) {\r\n    // Dependency injection\r\n    super(payrollsApi, uiHelpers, $location, $routeParams);\r\n    const handler = this.$rootScope.$on(\"payroll-tab-event\", (_event: any, tabToSelect: string) => {\r\n      this.selectTab(tabToSelect);\r\n    });\r\n    this.$scope.$on(\"$destroy\", handler);\r\n  }\r\n\r\n  /**\r\n   * Initialization code.\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n\r\n    this.$scope.$on(\"tabButtonsControllerReady\", (event, data: { ctrl: TabButtonsController, tabsId: string }) => {\r\n      if (data.tabsId === \"payrollDetails\") {\r\n        this.tabButtonsCtrl = data.ctrl;\r\n        if (this.isAiDemoEditable) {\r\n          this.selectTab(\"rows\");\r\n        }\r\n        else if (this.isReadOnlyForced) {\r\n          this.selectTab(\"reports\");\r\n        }\r\n      }\r\n    });\r\n  }\r\n\r\n  /** Catched the return of reload to update values. */\r\n  public reload(): Promise<PayrollDetails> {\r\n    return super.reload().then((payroll) => {\r\n      if (super.isNew()) {\r\n        if (payroll?.input) {\r\n          payroll.input.paymentChannel = this.invoicesService.defaultChannel;\r\n        }\r\n      }\r\n      return payroll;\r\n    });\r\n  }\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"/payroll\",\r\n      detailsUrl: this.detailsUrl || \"/payroll/details/\",\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/Payrolls.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n\r\n  /** Page size */\r\n  public get pageSizeOption() {\r\n    return `${this.pageSize}`;\r\n  }\r\n\r\n  /** Page size */\r\n  public set pageSizeOption(value: string) {\r\n    this.pageSize = Number.parseInt(value);\r\n  }\r\n\r\n  /** Check assistant key */\r\n  public get hasAssistantKey(): boolean {\r\n    this._openAiKey = this._openAiKey || window.localStorage.getItem(\"openAiKey\") || \"\";\r\n    return !!this._openAiKey;\r\n  }\r\n\r\n  /** Returns true for AI Demo approval case */\r\n  public get isAiDemoWaitingApproval(): boolean {\r\n    return this.sessionService.isInRole(\"aidemo\") && !this.sessionService.isInRole(\"pro\") && this.current?.info?.status === PayrollStatus.WaitingApproval;\r\n  }\r\n\r\n    /** Returns true for AI Demo approval case */\r\n  public get isAiDemoEditable(): boolean {\r\n    return this.sessionService.isInRole(\"aidemo\") && !this.sessionService.isInRole(\"pro\") && !this.current?.isReadOnly;\r\n  }\r\n\r\n  /** Shows dummy dialog for AI demo approval */\r\n  public showAiDemoApproval() {\r\n    this.uiHelpers.showConfirm(\"Palkkalistan hyväksyntä\", \"Haluatko hyväksyä tämän palkkalistan ja siirtää palkkalistan maksettavaksi?\", \"Hyväksy\", \"Peruuta\");\r\n  }\r\n\r\n  /**\r\n   * Selects and shows a tab in the payroll details view\r\n   */\r\n  public selectTab(tab: string): void {\r\n    this.tabButtonsCtrl.showTab(tab);\r\n  }\r\n\r\n  /**\r\n   * Returns true, if the given action button should be shown\r\n   * @param action One of the action values: See actions field type for supported values.\r\n   */\r\n  public showAction(action: string): boolean {\r\n    const actions = this.actions?.length ? this.actions :\r\n      this.isReadOnlyForced ? [] : [\"copy\", \"cancel\"];\r\n\r\n    if (action === \"pay\") {\r\n      // Check action and status\r\n      return !!actions.find(x => x == action) &&\r\n        (!!this.current &&\r\n          (this.current.info.status === PayrollStatus.Draft ||\r\n            this.current.info.status === PayrollStatus.WaitingApproval\r\n          )\r\n        );\r\n    }\r\n\r\n    return !!actions.find(x => x == action);\r\n  }\r\n\r\n  /**\r\n   * If true, the form controls should be read-only (no control at all).\r\n   */\r\n  public get isReadOnly() {\r\n    return super.isReadOnly || this.current?.info?.status === PayrollStatus.PaymentStarted;\r\n  }\r\n\r\n  /** Returns true if the period of a calculation is different than the period of the Payroll. */\r\n  public isDateDifferent(calc: CalculationListItem): boolean {\r\n    if (!calc?.data) {\r\n      return false;\r\n    }\r\n    return Dates.asDate(calc.data.workStartDate) !== Dates.asDate(this.current.input.period.start)\r\n      || Dates.asDate(calc.data.workEndDate) !== Dates.asDate(this.current.input.period.end);\r\n  }\r\n\r\n  /** Save changes to the payroll as well as to changed calculations */\r\n  public save(options: { applyEmploymentDefaultRows: boolean } = null): Promise<PayrollDetails> {\r\n    this.loaders[this.current?.id || \"new\"] = true;\r\n    if (this.isNew() && this.current?.input?.calculations?.length > 0) {\r\n      // Create new payroll\r\n      const calcIds = this.current.input.calculations.slice();\r\n      this.current.input.calculations = [];\r\n      return this.calcsApi.getSingle(calcIds[0]).then((calc) => {\r\n        return this.payrollsApi.getCalcsOData(calc.info.payrollId, null).then((odataResult) => {\r\n          return super.save(options).then(() => {\r\n            const calcs = this.orderCalcs(calcIds, odataResult.items);\r\n            const data: any = {};\r\n            data.listItemType = \"CalculationListItem\";\r\n            const columns = undefined;\r\n            const paramsTemplate = undefined;\r\n            const action = (items /*, data */) => {\r\n              const itemIds = items.map((x) => x.id);\r\n              const removeAllRows = options?.applyEmploymentDefaultRows;\r\n              return this.payrollsApi.saveCalculations(this.current.id, itemIds, false, options?.applyEmploymentDefaultRows, removeAllRows).then((result) => {\r\n                const results = items.map(() => ({ message: \"\", result: [] }));\r\n                if (results.length > 0) {\r\n                  results[0].result = result;\r\n                }\r\n                return results;\r\n              });\r\n            };\r\n            return this.uiHelpers.showBatchProcessDialog(Translations.get(\"SALAXY.UI_Terms.wait\"), calcs, action, paramsTemplate, data, columns, 20, true, true, true).then(() => {\r\n              return this.$timeout(() => this.reload().then(() => {\r\n                this.$location.path(\"/payroll/details/\" + this.current.id + \"&refresh=\" + new Date().getTime());\r\n                return this.current;\r\n              }), 5000); // HACK: wait for index\r\n            });\r\n          });\r\n        });\r\n      });\r\n    }\r\n    else {\r\n      const wasNew = this.isNew();\r\n      const headerChangeInfo = this.getHeaderChangeInfo();\r\n      return super.save(options).then((result) => {\r\n        if (wasNew) {\r\n          delete this.loaders[\"new\"];\r\n          delete this.loaders[this.current.id];\r\n          return result;\r\n        }\r\n        else {\r\n          if (headerChangeInfo.isPaymentChannelChanged || headerChangeInfo.isSalaryDateChanged || headerChangeInfo.isPeriodChanged) {\r\n            const shouldChangePeriod = () => {\r\n              if (headerChangeInfo.isPeriodChanged) {\r\n                return this.uiHelpers.showConfirm(\"SALAXY.NG1.PayrollComponent.showDateRangeDialogTitle\",\r\n                  \"SALAXY.NG1.PayrollComponent.showDateRangeDialogDescr\",\r\n                  \"SALAXY.UI_Terms.yes\", \"SALAXY.UI_Terms.no\");\r\n              }\r\n              else {\r\n                return Promise.resolve(false);\r\n              }\r\n            };\r\n            return shouldChangePeriod().then((doChangePeriod) => {\r\n              if (!doChangePeriod && !headerChangeInfo.isPaymentChannelChanged && !headerChangeInfo.isSalaryDateChanged) {\r\n                delete this.loaders[\"new\"];\r\n                delete this.loaders[this.current.id];\r\n                return result;\r\n              }\r\n              else {\r\n                const calcs = this.calcs.slice(0);\r\n                const data: any = {};\r\n                data.listItemType = \"CalculationListItem\";\r\n                const columns = undefined;\r\n                const paramsTemplate = undefined;\r\n                const action = (items /*, data */) => {\r\n                  const itemIds = items.map((x) => x.id);\r\n                  return this.calcsApi.getMulti(itemIds).then((apiCalcs) => {\r\n                    for (const apiCalc of apiCalcs) {\r\n                      if (doChangePeriod) {\r\n                        apiCalc.info.workStartDate = this.current.input.period.start;\r\n                        apiCalc.info.workEndDate = this.current.input.period.end;\r\n                        apiCalc.framework.numberOfDays = this.current.input.period.daysCount;\r\n                      }\r\n                    }\r\n                    return this.payrollsApi.saveCalculations(this.current.id, apiCalcs).then((calcsResult) => {\r\n                      const results = items.map(() => ({ message: \"\", result: [] }));\r\n                      if (results.length > 0) {\r\n                        results[0].result = calcsResult;\r\n                      }\r\n                      return results;\r\n                    });\r\n                  });\r\n                };\r\n                return this.uiHelpers.showBatchProcessDialog(Translations.get(\"SALAXY.NG1.PayrollComponent.commitAllCalcs.heading\"), calcs, action, paramsTemplate, data, columns, 20, true, true, true).then((dialogResult) => {\r\n                  if (dialogResult.done) {\r\n                    dialogResult.results.forEach((result) => {\r\n                      for (const item of result.result) {\r\n                        const listItem = this.calcs.find((c) => c.id === item.id);\r\n                        if (listItem) {\r\n                          angular.copy(item, listItem);\r\n                        }\r\n                        else {\r\n                          this.calcs.push(item);\r\n                        }\r\n                      }\r\n                    });\r\n                    this.setPageItems();\r\n                  }\r\n                  delete this.loaders[\"new\"];\r\n                  delete this.loaders[this.current.id];\r\n                  return this.reload();\r\n                });\r\n              }\r\n            });\r\n          }\r\n          else {\r\n            delete this.loaders[\"new\"];\r\n            delete this.loaders[this.current.id];\r\n            return result;\r\n          }\r\n        }\r\n      });\r\n    }\r\n  }\r\n\r\n  /** Recalculate and save worktimes of all calculations. */\r\n  public saveWorktimes(): Promise<void> {\r\n    this.loaders[\"worktime\" + this.current?.id] = true;\r\n    const calcs = this.calcs.slice(0);\r\n    const data: any = {};\r\n    data.listItemType = \"CalculationListItem\";\r\n    const columns = undefined;\r\n    const paramsTemplate = undefined;\r\n    const action = (items) => {\r\n      const itemIds = items.map((x) => x.id);\r\n      return this.payrollsApi.saveCalculations(this.current.id, itemIds, true).then((result) => {\r\n        const results = items.map(() => ({ message: \"\", result: [] }));\r\n        if (results.length > 0) {\r\n          results[0].result = result;\r\n        }\r\n        return results;\r\n      });\r\n    };\r\n    return this.uiHelpers.showBatchProcessDialog(Translations.get(\"SALAXY.NG1.PayrollComponent.commitAllCalcs.heading\"), calcs, action, paramsTemplate, data, columns, 20, true, true, true).then((dialogResult) => {\r\n      if (dialogResult.done) {\r\n        dialogResult.results.forEach((result) => {\r\n          for (const item of result.result) {\r\n            const listItem = this.calcs.find((c) => c.id === item.id);\r\n            if (listItem) {\r\n              angular.copy(item, listItem);\r\n            }\r\n          }\r\n        });\r\n        const currentPage = this.page;\r\n        // start reload calculations\r\n        currentPage.calcs = [];\r\n        currentPage.originalCalcs = [];\r\n        // and payroll\r\n        return this.reload();\r\n      }\r\n    }).then(() => {\r\n      delete this.loaders[\"worktime\" + this.current?.id];\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Calculates the total amount of days for the given period type.\r\n   * @param calc Calculation to calculate days for.\r\n   * @param periodType Period type to calculate days for.\r\n   * @returns Sum of days for the given period type.\r\n   */\r\n  public calculatePeriodDays(calc: Calculation, periodType: \"absencesDays\" | \"leavesDays\" | \"paidAbsencesDays\" | \"accruedDays\") {\r\n    switch (periodType) {\r\n      case \"leavesDays\":\r\n        return Arrays.sum(calc.worktime?.absencesPeriods?.filter(x => x.causeCode == AbsenceCauseCode.AnnualLeave) ?? [], (x) => x.period.daysCount);\r\n      case \"absencesDays\":\r\n        return Arrays.sum(calc.worktime?.absencesPeriods?.filter(x => x.causeCode != AbsenceCauseCode.AnnualLeave && !x.isPaid) ?? [], (x) => x.period.daysCount);\r\n      case \"paidAbsencesDays\":\r\n        return Arrays.sum(calc.worktime?.absencesPeriods?.filter(x => x.causeCode != AbsenceCauseCode.AnnualLeave && x.isPaid) ?? [], (x) => x.period.daysCount);\r\n      case \"accruedDays\":\r\n        if (this.showAccruals(calc)) {\r\n          return Arrays.sum(calc.worktime?.accruals, (x) => x.daysAccrued);\r\n        }\r\n        return 0;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Returns true if the accruals are accumulated.\r\n   * @param calc Calculation.\r\n   * @returns Returns true if the accruals are accumulated.\r\n   */\r\n  public showAccruals(calc: Calculation) {\r\n    return calc.worktime?.accrualSpec?.code == HolidayCode.Permanent14Days || calc.worktime?.accrualSpec?.code == HolidayCode.Permanent35Hours || calc.worktime?.accrualSpec?.code == HolidayCode.TemporaryTimeOff || calc.worktime?.accrualSpec?.code == HolidayCode.Other || calc.worktime?.accrualSpec?.code == HolidayCode.Script;\r\n  }\r\n\r\n  /**\r\n   * Creates a copy of a payroll\r\n   * This is a synchronous method that should basically convert a saved item to a new item.\r\n   * @param copySource Item (container item) to copy as new.\r\n   */\r\n  public copyItem(copySource: PayrollDetails): PayrollDetails {\r\n    const oldId = copySource.id;\r\n    const copy = super.copyItem(copySource);\r\n    copy.input.salaryDate = null;\r\n    copy.info.salaryDate = null;\r\n    copy.info.messageThreadId = null;\r\n    copy.info.originalPaymentId = undefined;\r\n    copy.info.paymentId = undefined;\r\n    if (copy.info.status === PayrollStatus.Template) {\r\n      copy.input.template = oldId;\r\n    }\r\n    copy.info.status = PayrollStatus.Draft;\r\n    // HACK: remove payroll-service flag. This will be replaced with invoicing flags eventually.\r\n    if (copy.usecase &&\r\n      (copy.usecase.uri === \"palkkaus.fi/usecases/payroll-service/pro-calc\" ||\r\n        copy.usecase.uri === \"palkkaus.fi/usecases/payroll-service/calc\")) {\r\n      copy.usecase = {};\r\n    }\r\n    return copy;\r\n  }\r\n\r\n  /** Close the header dialog */\r\n  public closeHeader() {\r\n    delete this.showHeader;\r\n    if (this.isNew()) {\r\n      this.$location.path(this.getDefaults().listUrl);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Sets the current calculation ID\r\n   * @param calcId The ID of the calculation to set.\r\n   * Set as undefined to hide the current calculation.\r\n   */\r\n  public setCalc(calcId: string | undefined) {\r\n    this.calcId = calcId;\r\n    this.calcListItem = this.calcs.find((c) => c.id === calcId);\r\n    this.calc = undefined;\r\n    this.originalCalc = undefined;\r\n    if (calcId) {\r\n      const loadedCalc = this.page.calcs.find((c) => c.id === calcId);\r\n      if (loadedCalc && !!loadedCalc.rows) {\r\n        // this is needed for refresh the calc page\r\n        this.uiHelpers.wait(0).then(() => {\r\n          this.calc = loadedCalc;\r\n          this.originalCalc = this.page.originalCalcs.find((c) => c.id === calcId);\r\n        });\r\n      }\r\n      else {\r\n        this.calcsApi.getSingle(calcId).then((result) => {\r\n          // find from current page\r\n          const preCalc = this.page.calcs.find((c) => c.id === calcId);\r\n          if (preCalc) {\r\n            const calc = result;\r\n            angular.copy(calc, preCalc);\r\n            const originalCalc = this.page.originalCalcs.find((c) => c.id === calcId);\r\n            angular.copy(calc, originalCalc);\r\n            this.calc = preCalc;\r\n            this.originalCalc = originalCalc;\r\n          }\r\n          else {\r\n            // find from all pages\r\n            const page = this._pages.pages.find((p) => p.items.find((c) => c.id === calcId));\r\n            if (page) {\r\n              const calc = result;\r\n              page.calcs.push(calc);\r\n              const originalCalc = angular.copy(calc);\r\n              page.originalCalcs.push(originalCalc);\r\n              this.calc = calc;\r\n              this.originalCalc = originalCalc;\r\n              this._pages.currentIdx = page.current - 1;\r\n            }\r\n          }\r\n        });\r\n      }\r\n    }\r\n  }\r\n\r\n  private _canvasInfo = {\r\n    calc: false,\r\n    header: false\r\n  };\r\n  /**\r\n   * Returns true if the canvas should be shown.\r\n   */\r\n  public shouldShowCanvas(canvas: \"calc\" | \"header\", truly: any): boolean {\r\n    const showCanvas = !!truly;\r\n    const launcher = document.querySelector(\"iframe#launcher\") as HTMLElement;\r\n    if (launcher) {\r\n      this._canvasInfo[canvas] = showCanvas;\r\n      const hideHelp = this._canvasInfo[\"calc\"] || this._canvasInfo[\"header\"];\r\n      if (hideHelp) {\r\n        launcher.style.display = \"none\";\r\n      }\r\n      else {\r\n        launcher.style.display = \"\";\r\n      }\r\n    }\r\n    return showCanvas;\r\n  }\r\n\r\n  /**\r\n   * Advances to next calc.\r\n   */\r\n  public goToCalc(previous = false) {\r\n    let idx = this.calcs.indexOf(this.calcListItem);\r\n    if (idx == -1) {\r\n      return;\r\n    }\r\n\r\n\r\n    const saveIfChanged = () => {\r\n      if (this.hasEmploymentChange) {\r\n        return this.saveEmployment((this as any).$employment.current, false);\r\n      }\r\n      else if (this.hasCalcChange) {\r\n        return this.saveCalc(this.calc);\r\n      }\r\n      else {\r\n        return Promise.resolve(this.current);\r\n      }\r\n    };\r\n\r\n    return saveIfChanged().then(() => {\r\n      if (previous) {\r\n        idx -= 1;\r\n        return idx > -1 ? this.setCalc(this.calcs[idx].id) : this.setCalc(this.calcs[this.calcs.length - 1].id);\r\n      }\r\n      else {\r\n        idx += 1;\r\n        return idx < this.calcs.length ? this.setCalc(this.calcs[idx].id) : this.setCalc(this.calcs[0].id);\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Checks if the current calcs has changes.\r\n   */\r\n  public get hasCalcChange(): boolean {\r\n    if (this.calc?.isReadOnly) {\r\n      return false;\r\n    }\r\n    return !angular.equals(this.calc, this.originalCalc);\r\n  }\r\n\r\n  /**\r\n   * Checks if the current employment has changes.\r\n   */\r\n  public get hasEmploymentChange(): boolean {\r\n    if (this.calc?.isReadOnly) {\r\n      return false;\r\n    }\r\n    const employment = (this as any).$employment;\r\n\r\n    if (employment?.current && employment?.original) {\r\n      // HACK fixes\r\n      // remove $$hashKey added by angular\r\n      const current = angular.fromJson(angular.toJson(employment.current));\r\n      // add defaults to original as in current\r\n      const original = angular.copy(employment.original);\r\n      EmploymentLogic.getContact(original, ContactType.EmployerOverride);\r\n      return !angular.equals(current, original);\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /**\r\n   * Toggles the current calculation ID\r\n   * @param calcId The ID of the calculation to set.\r\n   */\r\n  public toggleCalc(calcId: string | undefined) {\r\n    if (this.calcId === calcId) {\r\n      this.setCalc(undefined);\r\n    } else {\r\n      this.setCalc(calcId);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Saves the calculation and reloads the payroll.\r\n   */\r\n  public saveCalc(calcToSave: Calculation, applyWorktime = false, applyEmploymentDefaultRows = false): Promise<PayrollDetails> {\r\n    const calcId = calcToSave.id;\r\n\r\n    this.loaders[calcId] = true;\r\n    return this.payrollsApi.saveCalculations(this.current.id, [calcToSave], applyWorktime, applyEmploymentDefaultRows).then((items) => {\r\n      for (const item of items) {\r\n        const listItem = this.calcs.find((c) => c.id === item.id);\r\n        if (listItem) {\r\n          angular.copy(item, listItem);\r\n        }\r\n      }\r\n      delete this.loaders[calcId];\r\n      return this.calcsApi.getSingle(calcId).then((calc) => {\r\n        if (this.calcId == calcId) {\r\n          if (this.calc) {\r\n            angular.copy(calc, this.calc);\r\n            angular.copy(calc, this.originalCalc);\r\n          }\r\n          else {\r\n            this.calc = calc;\r\n            this.originalCalc = angular.copy(calc);\r\n          }\r\n        }\r\n        else {\r\n          // start reload calculations\r\n          const currentPage = this.page;\r\n          currentPage.calcs = currentPage.calcs.filter((x) => x.id != calcId);\r\n          currentPage.originalCalcs = currentPage.originalCalcs.filter((x) => x.id != calcId);\r\n        }\r\n        return this.reload();\r\n      });\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Refreshes the calculation by removing the specified calculation from the current page's\r\n   * calculations and original calculations, then reloads the data.\r\n   */\r\n  public refreshCalc(calc: Calculation): angular.IPromise<PayrollDetails> {\r\n    const currentPage = this.page;\r\n    currentPage.calcs = currentPage.calcs.filter((x) => x.id != calc.id);\r\n    currentPage.originalCalcs = currentPage.originalCalcs.filter((x) => x.id != calc.id);\r\n    return this.$timeout(() => {\r\n      return this.calcsApi.getOData({$filter: `id eq '${calc.id}'`}).then(result => {\r\n        const item = result.items[0];\r\n        const listItem = this.calcs.find((c) => c.id === item.id);\r\n        if (listItem) {\r\n          angular.copy(item, listItem);\r\n        }\r\n        return this.current;\r\n      });\r\n    }, 5000);\r\n  }\r\n\r\n  /**\r\n   * Refreshes the calculation after a workflow event by:\r\n   * 1. Fetching the latest version of the calculation from the API\r\n   * 2. Updating the local calc and originalCalc copies\r\n   * 3. Triggering a refresh of the calculation in the list\r\n   * @returns Promise that resolves with the updated PayrollDetails\r\n   */\r\n  public refreshAfterWorkflow(): Promise<PayrollDetails> {\r\n    return this.calcsApi.getSingle(this.calc.id).then((calc) => {\r\n      if (this.calc) {\r\n        angular.copy(calc, this.calc);\r\n        angular.copy(calc, this.originalCalc);\r\n      } else {\r\n        this.calc = calc;\r\n        this.originalCalc = angular.copy(calc);\r\n      }\r\n      return this.refreshCalc(this.calc);\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Adds salary defaults to the current calculation by saving it with the addSalaryDefaults flag.\r\n   * @returns Promise that resolves with the updated PayrollDetails after saving\r\n   */\r\n  public async addSalaryDefaultsToCalc(): Promise<PayrollDetails> {\r\n    this.loaders[this.calc.id + \"-add-salary-defaults\"] = true;\r\n    return this.saveCalc(this.calc, false, true).then(() => {\r\n      delete this.loaders[this.calc.id + \"-add-salary-defaults\"];\r\n      return this.current;\r\n    });\r\n  }\r\n\r\n  /** Saves the employment and updates the calcs rows optionally */\r\n  public saveEmployment(employment: Employment, updateRows = false): Promise<PayrollDetails> {\r\n    this.loaders[this.calc.id + \"-employment-\" + updateRows] = true;\r\n    return this.employmentsApi.save(employment).then(() => {\r\n      if (this[\"$employment\"]) {\r\n        this[\"$employment\"].reload();\r\n      }\r\n      return this.calcsApi.updateFromEmployment(this.calc, false, updateRows).then((calc) => {\r\n        if (this.calc) {\r\n          angular.copy(calc, this.calc);\r\n          angular.copy(calc, this.originalCalc);\r\n        }\r\n        else {\r\n          this.calc = calc;\r\n          this.originalCalc = angular.copy(calc);\r\n        }\r\n        return this.saveCalc(this.calc).then(() => {\r\n          delete this.loaders[this.calc.id + \"-employment-\" + updateRows];\r\n          return this.current;\r\n        });\r\n      });\r\n    });\r\n  }\r\n\r\n  private _calcs: CalculationListItem[] | undefined;\r\n\r\n  /**\r\n   * Gets the list items of the calculations of the current payroll.\r\n   * HACK: This is temporary dev version => Need to consider different apprroaches for the final version.\r\n   */\r\n  public get calcs(): CalculationListItem[] | undefined {\r\n    if (!this.current?.id) {\r\n      return undefined;\r\n    }\r\n    if (!this._calcs) {\r\n      this._calcs = [];\r\n      this._pages = { currentIdx: 0, pages: [] };\r\n      this.payrollsApi.getCalcsOData(this.current.id, {}).then((result) => {\r\n        this._calcs = this.orderCalcs(this.current.input.calculations, result.items);\r\n        this.setPageItems();\r\n        this.getEmployments();\r\n      });\r\n    }\r\n    return this._calcs;\r\n  }\r\n\r\n  /**\r\n   * Filters the rows based on column header selection.\r\n   * @param column The name of the column in question.\r\n   * @param value Filtering value string.\r\n   */\r\n  public setColumnFilter(column: string, value?: string): void {\r\n    let filter = \"\";\r\n\r\n    if (column == \"PartnerMessageClosed\" || column == \"PartnerMessageIssue\") {\r\n      const filters = [];\r\n      this.columnFilters[column] = value;\r\n\r\n      for (const [key, value] of Object.entries(this.columnFilters)) {\r\n        if (value == \"true\") {\r\n          filters.push(`flags/any(f: f eq '${key}')`);\r\n        } else if (value == \"false\") {\r\n          filters.push(`not flags/any(f: f eq '${key}')`);\r\n        }\r\n      }\r\n\r\n      filter = filters.join(\" and \");\r\n    }\r\n\r\n    this.payrollsApi.getCalcsOData(this.current.id, {\r\n      $filter: filter\r\n    }).then((result) => {\r\n      this._calcs = this.orderCalcs(this.current.input.calculations, result.items);\r\n      this.setPageItems();\r\n      this.getEmployments();\r\n    });\r\n  }\r\n\r\n  /** Fetches and returns all employment list items related to all calcs in payroll. */\r\n  public getEmployments(): void {\r\n    if (this.calcs) {\r\n      const calcsEmploymentIds = this.calcs.map((x) => x.data.employmentId).filter((x) => !!x);\r\n\r\n      if (calcsEmploymentIds.length > 0) {\r\n          this.employments = Object.fromEntries(calcsEmploymentIds.map((id) => [id, undefined]));\r\n          const chunkSize = 15; // maximum possible without maxNodeCount error\r\n          const calls: Promise<ODataResult<any>>[] = [];\r\n          for (let i = 0; i < calcsEmploymentIds.length; i += chunkSize) {\r\n            const callIds = calcsEmploymentIds.slice(i, i + chunkSize);\r\n            calls.push(this.employmentsApi.getOData({ $filter: callIds.map((id) => `id eq '${id}'`).join(\" or \") }));\r\n          }\r\n\r\n          Promise.all(calls).then((results) => {\r\n            results.forEach((result) => {\r\n              result.items.forEach((item) => {\r\n                this.employments[item.id] = item;\r\n              });\r\n            });\r\n            this.$timeout();\r\n          });\r\n      }\r\n    }\r\n  }\r\n\r\n  private _pages: { currentIdx: number, pages: Array<{ current: number, total: number, items: CalculationListItem[], calcs: Calculation[], originalCalcs: Calculation[], calcRange: string, totalCalcCount }> };\r\n /** Returns current calc page. */\r\n  public get page(): { current: number, total: number, items: CalculationListItem[], calcs: Calculation[], originalCalcs: Calculation[], calcRange: string, totalCalcCount: number } | undefined {\r\n    if (this._pages) {\r\n      for (let i = 0; i < this._pages.pages.length; i++) {\r\n        if (i !== this._pages.currentIdx && this._pages.pages[i].calcs.length > 0) {\r\n          this._pages.pages[i].calcs = [];\r\n          this._pages.pages[i].originalCalcs = [];\r\n        }\r\n      }\r\n    }\r\n    return this._pages?.pages[this._pages.currentIdx];\r\n  }\r\n\r\n  /** Set page items. */\r\n  public setPageItems() {\r\n    if (this._pages) {\r\n      this._pages.currentIdx = 0;\r\n      this._pages.pages.splice(0, this._pages.pages.length);\r\n      const totalCalcCount = this._calcs.length;\r\n      const pageTotal = Math.ceil(this._calcs.length / this.pageSize);\r\n      for (let i = 0; i < this._calcs.length; i += this.pageSize) {\r\n        const items = this._calcs.slice(i, i + this.pageSize);\r\n        const calcRange = (i + 1) + \" - \" + (i + items.length);\r\n        this._pages.pages.push({ current: Math.ceil((i + 1) / this.pageSize), total: pageTotal, items, calcs: [], originalCalcs: [], calcRange, totalCalcCount });\r\n      }\r\n    }\r\n  }\r\n\r\n  /** Returns current calc page. */\r\n  public getPageCalc(item: CalculationListItem): Calculation | undefined {\r\n    if (this._pages) {\r\n      const currentPage = this.page;\r\n      currentPage.calcs ??= [];\r\n      currentPage.originalCalcs ??= [];\r\n      const calc = currentPage.calcs.find((x) => x.id == item.id);\r\n      if (calc) {\r\n        if (calc.rows) {\r\n          // ready\r\n          return calc;\r\n        }\r\n        else {\r\n          // precalc\r\n          return undefined;\r\n        }\r\n      }\r\n      else {\r\n        const preCalc = { id: item.id };\r\n        const preOriginalCalc = angular.copy(preCalc);\r\n        currentPage.calcs.push(preCalc);\r\n        currentPage.originalCalcs.push(preOriginalCalc);\r\n        this.calcsApi.getSingle(item.id).then((calc) => {\r\n          angular.copy(calc, preCalc);\r\n          angular.copy(calc, preOriginalCalc);\r\n        });\r\n      }\r\n    }\r\n    else {\r\n      return undefined;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Saves the calculation and reloads the payroll.\r\n   */\r\n  public savePageCalcs(): Promise<PayrollDetails> {\r\n    const currentPage = this.page;\r\n    this.loaders[\"pageCalcs\" + currentPage.current] = true;\r\n    // no precalcs, no readonly\r\n    const calcs = this.page.calcs.filter((x) => !!x.rows && x.isReadOnly !== true);\r\n    const changedCalcs = calcs.filter((x) => !angular.equals(x, currentPage.originalCalcs.find((c) => c.id === x.id)));\r\n    return this.payrollsApi.saveCalculations(this.current.id, changedCalcs).then((items) => {\r\n      for (const item of items) {\r\n        const listItem = this.calcs.find((c) => c.id === item.id);\r\n        if (listItem) {\r\n          angular.copy(item, listItem);\r\n        }\r\n      }\r\n      delete this.loaders[\"pageCalcs\" + currentPage.current];\r\n      // start reload calculations\r\n      currentPage.calcs = currentPage.calcs.filter((x) => !changedCalcs.find((c) => c.id === x.id));\r\n      currentPage.originalCalcs = currentPage.originalCalcs.filter((x) => !changedCalcs.find((c) => c.id === x.id));\r\n      // and payroll\r\n      return this.reload();\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Checks if the current page calcs have changes.\r\n   * Returns the number of changed calcs.\r\n   */\r\n  public get numOfChangedPageCalcs(): number {\r\n    const currentPage = this.page;\r\n    if (!currentPage) {\r\n      return 0;\r\n    }\r\n    // no precalcs, no readonly\r\n    const calcs = this.page.calcs.filter((x) => !!x.rows && x.isReadOnly !== true);\r\n\r\n    return calcs.filter((x) => !angular.equals(x, currentPage.originalCalcs.find((c) => c.id === x.id))).length;\r\n  }\r\n\r\n  /** Gets calculation validity from the calc table entry */\r\n  public getCalcValidity(row: CalculationListItem): ApiListItemValidation {\r\n    return this.current?.validations?.find((x) => x.id === row.id);\r\n  }\r\n\r\n  /**\r\n   * Advances to next page.\r\n   */\r\n  public goToPage(previous = false) {\r\n    if (!this._pages) {\r\n      return;\r\n    }\r\n\r\n    const saveIfChanged = () => {\r\n      if (this.numOfChangedPageCalcs > 0) {\r\n        return this.savePageCalcs();\r\n      }\r\n      else {\r\n        return Promise.resolve(this.current);\r\n      }\r\n    };\r\n\r\n    return saveIfChanged().then(() => {\r\n      let idx = this._pages.currentIdx;\r\n      if (previous) {\r\n        idx -= 1;\r\n        this._pages.currentIdx = idx > -1 ? idx : this._pages.pages.length - 1;\r\n      }\r\n      else {\r\n        idx += 1;\r\n        this._pages.currentIdx = idx < this._pages.pages.length ? idx : 0;\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Opens a list of workers in to a dialog window.\r\n   * Creates a new calculation for the selected worker and current payroll.\r\n   */\r\n  public addEmployments() {\r\n    const workerList = [];\r\n    this.uiHelpers.openEditDialog(\r\n      \"salaxy-components/modals/calc/WorkerList.html\",\r\n      workerList,\r\n      {\r\n        title: \"SALAXY.NG1.PayrollComponent.createNewCalcDialog\",\r\n      }).then((result) => {\r\n        if (result.action === \"ok\" && workerList.length > 0) {\r\n          const data: any = {};\r\n          data.listItemType = \"EmploymentListItem\";\r\n          const columns = undefined;\r\n          const paramsTemplate = undefined;\r\n          const action = (items, /*data*/) => {\r\n            const itemIds = items.map((x) => x.id);\r\n            return this.payrollsApi.addEmployments(this.current.id, itemIds).then((result) => {\r\n              const results = items.map(() => ({ message: \"\", result: [] }));\r\n              if (results.length > 0) {\r\n                results[0].result = result;\r\n              }\r\n              return results;\r\n            });\r\n          };\r\n          return this.uiHelpers.showBatchProcessDialog(Translations.get(\"SALAXY.NG1.PayrollComponent.createNewCalcLoading\"), workerList, action, paramsTemplate, data, columns, 20, true, true, true).then((dialogResult) => {\r\n            if (dialogResult.done) {\r\n              dialogResult.results.forEach((result) => {\r\n                for (const item of result.result) {\r\n                  const listItem = this.calcs.find((c) => c.id === item.id);\r\n                  if (listItem) {\r\n                    angular.copy(item, listItem);\r\n                  }\r\n                  else {\r\n                    this.calcs.push(item);\r\n                  }\r\n                }\r\n              });\r\n              this.setPageItems();\r\n            }\r\n            return this.reload();\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Opens the list of calculations into a dialog window for selection and then adds them to payroll\r\n   * @param category Either \"paid\": Read-only, a copy is added ... or \"draft\": Editable, moved with status changed.\r\n   * @param isMerge If true, the operation merges the calculations to the current payroll.\r\n   * @param removeAllRows If true, the merge operation removes all the rows from the calculation.\r\n   * @param applyEmploymentDefaultRows If true, the merge operation adds the employment default rows to the calculations.\r\n   */\r\n  public addCalcs(category: \"paid\" | \"shared\" | \"draft\" = \"draft\", isMerge = false, removeAllRows = false, applyEmploymentDefaultRows = false) {\r\n    const title = (category === \"paid\" ? \"SALAXY.NG1.PayrollComponent.addExistingCalcCopy\" : category == \"shared\" ? \"SALAXY.NG1.PayrollComponent.addExistingCalcMoveShared\" : \"SALAXY.NG1.PayrollComponent.addExistingCalcMove\");\r\n    this.uiHelpers.openSelectCalcs(category, title).then((result) => {\r\n      if (result.action === \"ok\" && result.item.length > 0) {\r\n\r\n        const calcs = result.item;\r\n        const data: any = {};\r\n        data.listItemType = \"CalculationListItem\";\r\n        const columns = undefined;\r\n        const paramsTemplate = undefined;\r\n        const action = (items, /*data*/) => {\r\n          const itemIds = items.map((x) => x.id);\r\n          return (!isMerge ? this.payrollsApi.addCalculations(this.current.id, itemIds) :\r\n            this.payrollsApi.mergeCalculations(this.current.id, itemIds, removeAllRows, applyEmploymentDefaultRows)).then((result) => {\r\n              const results = items.map(() => ({ message: \"\", result: [] }));\r\n              if (results.length > 0) {\r\n                results[0].result = result;\r\n              }\r\n              return results;\r\n            });\r\n        };\r\n        return this.uiHelpers.showBatchProcessDialog(Translations.get(\"SALAXY.NG1.PayrollComponent.addExistingCalcLoading\"), calcs, action, paramsTemplate, data, columns, 20, true, true, true).then((dialogResult) => {\r\n          if (dialogResult.done) {\r\n            dialogResult.results.forEach((result) => {\r\n              for (const item of result.result) {\r\n                const listItem = this.calcs.find((c) => c.id === item.id);\r\n                if (listItem) {\r\n                  angular.copy(item, listItem);\r\n                }\r\n                else {\r\n                  this.calcs.push(item);\r\n                }\r\n              }\r\n            });\r\n            this.setPageItems();\r\n          }\r\n          return this.reload();\r\n        });\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Deletes the calculation\r\n   * @param unlink If true, will not delete the actual calculation, but instead unlinks it as a separate calculation outside this payroll.\r\n   */\r\n  public deleteCalc(unlink = false) {\r\n    const calcId = this.calcId;\r\n    if (unlink) {\r\n      this.uiHelpers.showConfirm(\"SALAXY.NG1.PayrollComponent.payrollCalcs.unlinkCalcDialog.heading\",\r\n        \"SALAXY.NG1.PayrollComponent.payrollCalcs.unlinkCalcDialog.intro\",\r\n        \"SALAXY.NG1.PayrollComponent.payrollCalcs.unlinkCalcDialog.confirmButton\",\r\n        \"SALAXY.NG1.PayrollComponent.payrollCalcs.unlinkCalcDialog.cancelButton\")\r\n        .then((result: boolean) => {\r\n          if (result) {\r\n            const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.PayrollComponent.payrollCalcs.unlinkCalcDialog.loading\");\r\n            this.payrollsApi.unlinkCalculation(this.current.id, calcId).then((savedPayroll) => {\r\n              this.setCurrentValue(savedPayroll, true);\r\n              if (this.current.input.calculations.indexOf(calcId) == -1) {\r\n                // remove list item\r\n                const listItem = this.calcs.find((c) => c.id === calcId);\r\n                if (listItem) {\r\n                  this.calcs.splice(this.calcs.indexOf(listItem), 1);\r\n                  this.setPageItems();\r\n                }\r\n                this.setCalc(undefined);\r\n              }\r\n              loader.dismiss();\r\n            });\r\n          }\r\n          else {\r\n            // cancel\r\n            return;\r\n          }\r\n        });\r\n    } else {\r\n      this.uiHelpers.showConfirm(\r\n        \"SALAXY.NG1.PayrollComponent.payrollCalcs.deleteCalcDialog.heading\",\r\n        \"SALAXY.NG1.PayrollComponent.payrollCalcs.deleteCalcDialog.introNoChanges\",\r\n        \"SALAXY.NG1.PayrollComponent.payrollCalcs.deleteCalcDialog.confirmButton\",\r\n        \"SALAXY.NG1.PayrollComponent.payrollCalcs.deleteCalcDialog.cancelButton\")\r\n        .then((result: boolean) => {\r\n          if (result) {\r\n            const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.PayrollComponent.payrollCalcs.deleteCalcDialog.loading\");\r\n            this.payrollsApi.deleteCalculation(this.current.id, calcId)\r\n              .then((savedPayroll) => {\r\n                this.setCurrentValue(savedPayroll, true);\r\n                if (this.current.input.calculations.indexOf(calcId) == -1) {\r\n                  // remove list item\r\n                  const listItem = this.calcs.find((c) => c.id === calcId);\r\n                  if (listItem) {\r\n                    this.calcs.splice(this.calcs.indexOf(listItem), 1);\r\n                    this.setPageItems();\r\n                  }\r\n                  this.setCalc(undefined);\r\n                }\r\n                loader.dismiss();\r\n              });\r\n          }\r\n          else {\r\n            return;\r\n          }\r\n        });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Opens a list of payrolls for merging the payroll calculations to the current payroll.\r\n   * @param removeAllRows If true, the operation removes all the rows from the calculation.\r\n   * @param applyEmploymentDefaultRows If true, the operation applies the employment default rows to the new calculations.\r\n   */\r\n  public mergePayroll(removeAllRows = false, applyEmploymentDefaultRows = false): Promise<PayrollDetails> {\r\n    const payrollItems = [];\r\n    return this.uiHelpers.openEditDialog(\"salaxy-components/modals/payroll/PayrollDetailsList.html\", payrollItems, {\r\n      title: Translations.get(\"SALAXY.NG1.PayrollComponent.mergePayroll.title\"),\r\n      category: \"draft\",\r\n    }, \"lg\").then((result) => {\r\n\r\n      if (result.action != \"ok\" || payrollItems.length < 1) {\r\n        return this.current;\r\n      }\r\n\r\n      // get all calcs\r\n      const calcs = [];\r\n      let calcPromises = undefined;\r\n      for (const payrollItem of payrollItems) {\r\n        if (payrollItem.id == this.current.id) {\r\n          continue;\r\n        }\r\n        const calcPromise = this.payrollsApi.getSingle(payrollItem.id)\r\n          .then((payroll) => this.payrollsApi.getCalcsOData(payrollItem.id, null)\r\n            .then((result) => calcs.push(...this.orderCalcs(payroll.input.calculations, result.items))));\r\n        calcPromises = !calcPromises ? calcPromise : calcPromises.then(calcPromise);\r\n      }\r\n\r\n      return calcPromises.then(() => {\r\n        const data: any = {};\r\n        data.listItemType = \"CalculationListItem\";\r\n        const columns = undefined;\r\n        const paramsTemplate = undefined;\r\n        const action = (items) => {\r\n          const itemIds = items.map((x) => x.id);\r\n          return this.payrollsApi.mergeCalculations(this.current.id, itemIds, removeAllRows, applyEmploymentDefaultRows).then((result) => {\r\n            const results = items.map(() => ({ message: \"\", result: [] }));\r\n            if (results.length > 0) {\r\n              results[0].result = result;\r\n            }\r\n            return results;\r\n          });\r\n        };\r\n        return this.uiHelpers.showBatchProcessDialog(Translations.get(\"SALAXY.NG1.PayrollComponent.mergePayroll.batchProcessTitle\"), calcs, action, paramsTemplate, data, columns, 20, true, true, true).then((dialogResult) => {\r\n          if (dialogResult.done) {\r\n            dialogResult.results.forEach((result) => {\r\n              for (const item of result.result) {\r\n                const listItem = this.calcs.find((c) => c.id === item.id);\r\n                if (listItem) {\r\n                  angular.copy(item, listItem);\r\n                }\r\n                else {\r\n                  this.calcs.push(item);\r\n                }\r\n              }\r\n            });\r\n            this.setPageItems();\r\n          }\r\n          return this.reload();\r\n        });\r\n      });\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shows a confirm dialog if payroll has any calculations.\r\n   * Returns true if a user clicks OK -button. Otherwise (cancel or close) returns false.\r\n   * @returns True if the user confirmed the operation.\r\n   */\r\n  public importEmploymentDataAll(): Promise<boolean> {\r\n    const payroll = this.current;\r\n    if (!payroll.info.calcCount || payroll.info.calcCount === 0) {\r\n      return this.uiHelpers.showAlert(\"SALAXY.NG1.PayrollComponent.importEmploymentDataAllAlertTitle\", \"SALAXY.NG1.PayrollComponent.importEmploymentDataAllAlertDescr\").then(() => false);\r\n    } else {\r\n      return this.uiHelpers.showConfirm(\r\n        \"SALAXY.NG1.PayrollComponent.importEmploymentDataAllConfirmTitle\",\r\n        \"SALAXY.NG1.PayrollComponent.importEmploymentDataAllConfirmDescr\",\r\n        \"SALAXY.UI_Terms.continue\",\r\n        \"SALAXY.UI_Terms.cancel\",\r\n      ).then((result: boolean) => {\r\n        if (result) {\r\n          const calcs = this.calcs.slice(0);\r\n          const data: any = {};\r\n          data.listItemType = \"CalculationListItem\";\r\n          const columns = undefined;\r\n          const paramsTemplate = undefined;\r\n          const action = (item /*, data */) => {\r\n            return this.calcsApi.getSingle(item.id).then((calc) => {\r\n              return this.calcsApi.updateFromEmployment(calc, true, true).then(() => {\r\n                return [{ message: \"\", result: [] }];\r\n              });\r\n            });\r\n          };\r\n          return this.uiHelpers.showBatchProcessDialog(Translations.get(\"SALAXY.NG1.PayrollComponent.importEmploymentDataAllLoading\"), calcs, action, paramsTemplate, data, columns, null, true, true).then(() => {\r\n            return this.reload().then(() => {\r\n              this._calcs = null;\r\n              return true;\r\n            });\r\n          });\r\n        } else {\r\n          return false;\r\n        }\r\n      });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Adds salary defaults to all calculations in the current payroll.\r\n   * Shows a confirmation dialog before proceeding.\r\n   * If there are no calculations in the payroll, shows an alert and returns false.\r\n   * Otherwise shows a confirmation dialog:\r\n   * If user confirms, processes all calculations in batches of 20:\r\n   * 1. Saves the calculations with salary defaults via payrollsApi\r\n   * 2. Updates the local calcs list with the returned results\r\n   * 3. Reloads the payroll data\r\n   * 4. Returns true on success\r\n   * If user cancels, returns false\r\n   * @returns Promise<boolean> - True if salary defaults were successfully added, false if cancelled or no calculations\r\n   */\r\n  public async addSalaryDefaultsToAllCalcs(): Promise<boolean> {\r\n    const payroll = this.current;\r\n    if (!payroll.info.calcCount || payroll.info.calcCount === 0) {\r\n      return this.uiHelpers.showAlert(\"SALAXY.NG1.PayrollComponent.importEmploymentDataAllAlertTitle\", \"SALAXY.NG1.PayrollComponent.addSalaryDefaultsToAllCalcsAlertTitle\").then(() => false);\r\n    } else {\r\n      return this.uiHelpers.showConfirm(\r\n        \"SALAXY.NG1.PayrollComponent.addSalaryDefaultsToAllCalcsTitle\",\r\n        \"SALAXY.NG1.PayrollComponent.addSalaryDefaultsToAllCalcsDescr\",\r\n        \"SALAXY.UI_Terms.continue\",\r\n        \"SALAXY.UI_Terms.cancel\",\r\n      ).then((result: boolean) => {\r\n        if (result) {\r\n          const calcs = this.calcs.slice(0);\r\n          const data: any = {};\r\n          data.listItemType = \"CalculationListItem\";\r\n          const columns = undefined;\r\n          const paramsTemplate = undefined;\r\n          const action = (items) => {\r\n            const itemIds = items.map((x) => x.id);\r\n            return this.payrollsApi.saveCalculations(this.current.id, itemIds, false, true).then((result) => {\r\n              const results = items.map(() => ({ message: \"\", result: [] }));\r\n              if (results.length > 0) {\r\n                results[0].result = result;\r\n              }\r\n              return results;\r\n            });\r\n          };\r\n          return this.uiHelpers.showBatchProcessDialog(Translations.get(\"SALAXY.NG1.PayrollComponent.importEmploymentDataAllLoading\"), calcs, action, paramsTemplate, data, columns, 20, true, true, true).then((dialogResult) => {\r\n            if (dialogResult.done) {\r\n              dialogResult.results.forEach((result) => {\r\n                for (const item of result.result) {\r\n                  const listItem = this.calcs.find((c) => c.id === item.id);\r\n                  if (listItem) {\r\n                    angular.copy(item, listItem);\r\n                  }\r\n                  else {\r\n                    this.calcs.push(item);\r\n                  }\r\n                }\r\n              });\r\n              this.setPageItems();\r\n            }\r\n            return this.reload().then(() => {\r\n              this._calcs = null;\r\n              return true;\r\n            });\r\n          });\r\n        } else {\r\n          return false;\r\n        }\r\n      });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Show confirm dialog and export employment data from calculation to Employment relation.\r\n   * If the calculation has unmodified changes, the calculation is saved.\r\n   * @returns True if the user confirmed the operation.\r\n   */\r\n  public exportEmploymentData(): Promise<boolean> {\r\n    return this.uiHelpers.showConfirm(\r\n      \"SALAXY.NG1.PayrollComponent.exportEmploymentDataTitle\",\r\n      \"SALAXY.NG1.PayrollComponent.exportEmploymentDataDescr\",\r\n      \"SALAXY.UI_Terms.continue\",\r\n      \"SALAXY.UI_Terms.cancel\",\r\n    ).then((ok) => {\r\n      if (ok) {\r\n        const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.PayrollComponent.exportEmploymentDataLoading\");\r\n        return this.saveCalc(this.calc).then(() => {\r\n          return this.calcsApi.updateToEmployment(this.calc).then(() => {\r\n            loader.dismiss();\r\n            return true;\r\n          });\r\n        });\r\n      }\r\n      else {\r\n        return false;\r\n      }\r\n    });\r\n  }\r\n\r\n  /** Free reports */\r\n  public clearReports() {\r\n    this.reportCalcs = null;\r\n    this.reportCalcs = [];\r\n  }\r\n\r\n  /** Refreshses the reports for the payroll. */\r\n  public refreshReports(): Promise<Calculation[]> {\r\n    const payroll = this.current;\r\n    if (payroll.info.calcCount && payroll.info.calcCount > 0) {\r\n      const calcs = this.calcs.slice(0);\r\n      const data: any = {};\r\n      data.listItemType = \"CalculationListItem\";\r\n      const columns = undefined;\r\n      const paramsTemplate = undefined;\r\n      const action = (items /*, data */) => {\r\n        const itemIds = items.map((x) => x.id);\r\n        return this.calcsApi.getMulti(itemIds).then((result) => {\r\n          const results = items.map(() => ({ message: \"\", result: [] }));\r\n          if (results.length > 0) {\r\n            results[0].result = result;\r\n          }\r\n          return results;\r\n        });\r\n      };\r\n      return this.uiHelpers.showBatchProcessDialog(Translations.get(\"SALAXY.UI_Terms.wait\"), calcs, action, paramsTemplate, data, columns, 20, true, true, true).then((dialogResult) => {\r\n        if (dialogResult.done) {\r\n          this.reportCalcs.splice(0, this.reportCalcs.length);\r\n          dialogResult.results.forEach((result) => {\r\n            this.reportCalcs.push(...result.result);\r\n          });\r\n        }\r\n        return this.reportCalcs;\r\n      });\r\n    }\r\n    else {\r\n      this.reportCalcs.splice(0, this.reportCalcs.length);\r\n      return Promise.resolve(this.reportCalcs);\r\n    }\r\n  }\r\n\r\n  /** Disable function for the salary date picker. */\r\n  public isDisabledSalaryDate = (date): boolean => {\r\n    switch (this.current.input.salaryDateKind) {\r\n      case SalaryDateKind.InPast:\r\n        return false;\r\n      case SalaryDateKind.Default:\r\n      default:\r\n        return !SalaryDateLogic.isValidSalaryDate(date, null, null, true, this.current.input.paymentChannel, false, undefined, true);\r\n    }\r\n  };\r\n\r\n  /** Shows the paymentd dialog / the invoices UI. */\r\n  public showPaymentDialog() {\r\n    this.invoicesService.showPaymentDialog(this.current);\r\n  }\r\n\r\n  /**\r\n   * Cancels the payment or invoice processing for the current payroll.\r\n   */\r\n  public cancelInvoices(): Promise<PayrollDetails> {\r\n    const eprWarningMessage = this.invoicesService.getEprWarningForCancellation(this.current.info.salaryDate, this.current.info.status == PayrollStatus.PaymentSucceeded);\r\n    const eprText = eprWarningMessage ? \"\\n\" + eprWarningMessage : \"\";\r\n    return this.uiHelpers.showConfirm(Translations.get(\"SALAXY.NG1.CalcResultsComponent.cancelDialogTitle\") + \"?\", Translations.get(\"SALAXY.NG1.CalcResultsComponent.cancelDialogDescr\") + `${eprText}`, \"SALAXY.NG1.CalcResultsComponent.cancelDialogYes\", \"SALAXY.NG1.CalcResultsComponent.cancelDialogNo\").then((ok) => {\r\n      if (ok) {\r\n        if (InvoicesLogic.isCfa(this.current.input.paymentChannel)) {\r\n          const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n          return this.payrollsApi.cancelInvoices(this.current.id, [], false).then(() => {\r\n            return this.reload().then(() => {\r\n              loading.dismiss();\r\n              this._calcs = null;\r\n              return this.current;\r\n            });\r\n          });\r\n        }\r\n        else {\r\n          const calcs = angular.copy(this.calcs);\r\n          const data: any = {};\r\n          data.listItemType = \"CalculationListItem\";\r\n          const columns = undefined;\r\n          const paramsTemplate = undefined;\r\n          const action = (items, data) => {\r\n            const itemIds = items.map((x) => x.id);\r\n            const remainingAfterThis = data.dialogList.filter((x) => !x.processed).length;\r\n            const excludePeriodic = remainingAfterThis == 0 ? false : true;\r\n            return this.payrollsApi.cancelInvoices(this.current.id, itemIds, excludePeriodic).then(() => {\r\n              const results = items.map(() => ({ message: \"\", result: [] }));\r\n              return results;\r\n            });\r\n          };\r\n          return this.uiHelpers.showBatchProcessDialog(Translations.get(\"SALAXY.UI_Terms.wait\"), calcs, action, paramsTemplate, data, columns, 20, true, true, true).then(() => {\r\n            return this.reload().then(() => {\r\n              this._calcs = null;\r\n              return this.current;\r\n            });\r\n          });\r\n        }\r\n      }\r\n      else {\r\n        return this.current;\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Gets the user-specific setting (service), stored in the local storage.\r\n   */\r\n  public get userSettings() {\r\n    return this.userSettingsService;\r\n  }\r\n\r\n\r\n  private _info = {\r\n    calcCount: {\r\n      actual: 0,\r\n      original: 0,\r\n      exception: false,\r\n    },\r\n    totalGrossSalary: {\r\n      actual: 0,\r\n      original: 0,\r\n      exception: false,\r\n    },\r\n    totalPayment: {\r\n      actual: 0,\r\n      original: 0,\r\n      exception: false,\r\n    },\r\n  };\r\n\r\n  /** Get calculated header info. */\r\n  public get info() {\r\n    const allCalcs = this.calcs ?? [];\r\n    const infoCalcs = allCalcs.filter((x) => {\r\n      switch (this.current?.info.status) {\r\n        case PayrollStatus.PaymentSucceeded:\r\n          return x.status === CalculationStatus.PaymentSucceeded;\r\n        case PayrollStatus.PaymentStarted:\r\n          return x.status === CalculationStatus.PaymentStarted || x.status === CalculationStatus.PaymentSucceeded;\r\n        default:\r\n          return true;\r\n      }\r\n    });\r\n\r\n    this._info.calcCount.original = this.current?.info.calcCount ?? 0;\r\n    this._info.calcCount.actual = infoCalcs.length;\r\n    this._info.calcCount.exception = this._info.calcCount.actual !== this._info.calcCount.original;\r\n\r\n    this._info.totalGrossSalary.original = Numeric.round(this.current?.info.totalGrossSalary ?? 0);\r\n    this._info.totalGrossSalary.actual = Numeric.round(Arrays.sum(infoCalcs, (x) => x.grossSalary ?? 0));\r\n    this._info.totalGrossSalary.exception = this._info.totalGrossSalary.actual !== this._info.totalGrossSalary.original;\r\n\r\n    this._info.totalPayment.original = Numeric.round(this.current?.info.totalPayment ?? 0);\r\n    this._info.totalPayment.actual = Numeric.round(Arrays.sum(infoCalcs, (x) => x.payment ?? 0));\r\n    this._info.totalPayment.exception = this._info.totalPayment.actual !== this._info.totalPayment.original;\r\n\r\n    return this._info;\r\n  }\r\n\r\n  /** Returns exception style. */\r\n  public getExceptionStyle(hasException: boolean) {\r\n    if (hasException) {\r\n      return { \"text-decoration\": \"line-through\" };\r\n    }\r\n    return {};\r\n  }\r\n\r\n  /** Returns true, if a warning should be indicated in a row. */\r\n  public rowStatusWarning(row: CalculationListItem): boolean {\r\n    switch (this.current?.info.status) {\r\n      case PayrollStatus.PaymentSucceeded:\r\n        return !(row.status === CalculationStatus.PaymentSucceeded);\r\n      case PayrollStatus.PaymentStarted:\r\n        return !(row.status === CalculationStatus.PaymentStarted || row.status === CalculationStatus.PaymentSucceeded);\r\n      default:\r\n        return false;\r\n    }\r\n  }\r\n\r\n  /** Copy current calc */\r\n  public copyCalc() {\r\n    const copy = angular.copy(this.calc);\r\n    copy.id = null;\r\n    copy.info.payrollId = null;\r\n    copy.workflow.status = CalculationStatus.Draft;\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    return this.calcsApi.save(copy).then(() => {\r\n      loading.dismiss();\r\n    });\r\n  }\r\n\r\n  /** Returns true if the curren payroll has cfa payment channel. */\r\n  public get isCfa(): boolean {\r\n    return InvoicesLogic.isCfa(this.current?.input?.paymentChannel);\r\n  }\r\n\r\n  /** Pay current calc */\r\n  public payCalc() {\r\n    if (!this.isCfa) {\r\n      this.invoicesService.showPaymentDialog(this.calc);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Sends a payroll with messaging system and sets\r\n   * @param $msg The MessageThreadCrudController that is used for creating the message thread.\r\n   */\r\n  public sendPayrollMessage($msg: MessageThreadCrudController): Promise<void> {\r\n    if (!$msg.current) {\r\n      $msg.model = \"new\";\r\n    }\r\n    const model = $msg.current;\r\n    model.otherParty = this.sessionService.session.settings.partner.accountId;\r\n    model.status = MessageThreadStatus.Active;\r\n    model.title = model.title || \"Palkkalista \" + this.current.input.title;\r\n    model.ownerWorkflow = {\r\n      salaryDate: this.current.info.salaryDate,\r\n    };\r\n    model.messages.push({\r\n      contentId: this.currentId,\r\n      fromParty: this.sessionService.isInRole(\"pro\") ? MessageFrom.OtherParty : MessageFrom.Owner,\r\n      type: ThreadedMessageType.Payroll\r\n    });\r\n    return $msg.save().then((msg) => {\r\n      if (this.current.info.status != PayrollStatus.WaitingApproval) {\r\n        this.current.info.messageThreadId = msg.id;\r\n        this.current.info.status = PayrollStatus.WaitingApproval;\r\n        return this.save().then(() => {\r\n          return;\r\n        });\r\n      } else {\r\n        this.current.info.messageThreadId = msg.id; // This is done by messageThread logic on server => ne need to save.\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Opens the workflow for the payroll.\r\n   * @param $msg The MessageThreadCrudController that is used for creating the message thread.\r\n   */\r\n  public openWorkflowForpayroll($msg: MessageThreadCrudController): Promise<void> {\r\n    if (!$msg.current) {\r\n      $msg.model = \"new\";\r\n    }\r\n    const model = $msg.current;\r\n    model.otherParty = this.sessionService.session.settings.partner.accountId;\r\n    model.status = MessageThreadStatus.Active;\r\n    model.title = model.title || \"Palkkalista \" + this.current.input.title;\r\n    model.ownerWorkflow = {\r\n      salaryDate: this.current.info.salaryDate,\r\n    };\r\n    model.messages.push({\r\n      contentId: this.currentId,\r\n      fromParty: this.sessionService.isInRole(\"pro\") ? MessageFrom.OtherParty : MessageFrom.Owner,\r\n      type: ThreadedMessageType.Payroll\r\n    });\r\n    return $msg.save().then((msg) => {\r\n      this.current.info.messageThreadId = msg.id;\r\n        return this.save().then(() => {\r\n          return;\r\n        });\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Gets the message title for the action.\r\n   */\r\n  public getMessageTitle(action: string) {\r\n    return this.messageActions.find((x) => x.value == action).title + \": \" + this.current.input.title;\r\n  }\r\n\r\n  /**\r\n   * Available actions for the message.\r\n   * TODO: This could be replaced by enums or it may come from Service model.\r\n   */\r\n  public messageActions: InputEnumOption[] = [\r\n    {\r\n      text: \"Tarkista\",\r\n      value: \"check\",\r\n      title: \"Tarkista ennen maksuun lähetystä palkkalista\",\r\n    },\r\n    {\r\n      text: \"Maksa\",\r\n      value: \"pay\",\r\n      title: \"Maksa palkkalista\",\r\n    },/* {\r\n      text: \"Tarkista (hyväksy/hylkää)\",\r\n      value: \"approve\",\r\n      title: \"Tarkista palkkalista\",\r\n    },*/\r\n    {\r\n      text: \"Tiedoksi\",\r\n      value: \"info\",\r\n      title: \"Tiedoksi palkkalista\",\r\n    }, {\r\n      text: \"Vastaa kysymykseen\",\r\n      value: \"question\",\r\n      title: \"Kysymyksiä palkkalistasta\",\r\n    }\r\n  ];\r\n\r\n  /**\r\n   * Deletes a linked message: Both the message thread and msg id in this payroll.\r\n   * @param $msg The MessageThreadCrudController that contains the current message.\r\n   */\r\n  public deleteMessage($msg: MessageThreadCrudController) {\r\n    this.uiHelpers.showConfirm(\"Haluatko poistaa viestiketjun?\", \"Haluatko varmasti poistaa viestiketjun?\")\r\n      .then((result) => {\r\n        if (result) {\r\n          if ($msg.current) {\r\n            $msg.deleteNoConfirm($msg.current).then(() => {\r\n              this.current.info.messageThreadId = null;\r\n              this.save();\r\n            });\r\n          } else {\r\n            this.current.info.messageThreadId = null;\r\n            this.save();\r\n          }\r\n        }\r\n      });\r\n  }\r\n\r\n  /** Show add new taxcard dialog */\r\n  public async showAddNewTaxcard($event: angular.IAngularEvent, item: CalculationListItem) {\r\n    $event.stopPropagation();\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n\r\n    const calc = this.getPageCalc(item) ?? await this.calcsApi.getSingle(item.id);\r\n\r\n    if (!calc || calc.isReadOnly) {\r\n      loading.dismiss();\r\n      return;\r\n    }\r\n    const empl = await this.employmentsApi.getSingle(calc.worker.employmentId);\r\n    if (!empl) {\r\n      loading.dismiss();\r\n      return;\r\n    }\r\n\r\n    if (empl.info.taxcard == EmploymentRelationTaxcard.Undefined || empl.info.taxcard == EmploymentRelationTaxcard.Auto) {\r\n      const taxcard = await this.taxcardsApi.setAuto(calc.worker.paymentData.socialSecurityNumberValid);\r\n      if (taxcard) {\r\n        await this.saveCalc(calc);\r\n        loading.dismiss();\r\n        return;\r\n      }\r\n    }\r\n\r\n    const result = await this.uiCrudHelpers.createNewTaxcard(calc.worker.paymentData.socialSecurityNumberValid);\r\n    if (result.action === \"ok\") {\r\n      await this.saveCalc(calc);\r\n      loading.dismiss();\r\n      return;\r\n    }\r\n\r\n    loading.dismiss();\r\n  }\r\n\r\n\r\n  /** Sets the ordering for the rows. */\r\n  public orderBy(field: string) {\r\n    if (this.orderField == field) {\r\n      if (this.orderReverse) {\r\n        // reset to original\r\n        this.orderField = null;\r\n        this.orderReverse = false;\r\n      }\r\n      else {\r\n        // flip\r\n        this.orderReverse = true;\r\n      }\r\n    }\r\n    else {\r\n      this.orderField = field;\r\n      this.orderReverse = false;\r\n    }\r\n\r\n    if (!this.orderField) {\r\n      this.orderCalcs(this.current.input.calculations, this.calcs);\r\n    }\r\n    else {\r\n      this.calcs.sort(this.getOrderBy());\r\n    }\r\n\r\n    this.setPageItems();\r\n  }\r\n\r\n  public rowsImportParams = {\r\n    title: \"\",\r\n    personalId: \"\",\r\n    employmentType: \"\",\r\n    payrollId: \"\",\r\n    period: {\r\n      start: \"\",\r\n      end: \"\",\r\n      daysCount: 0,\r\n    },\r\n  };\r\n\r\n  /** Initializes the UI parameters for the rows import data. */\r\n  public initRowsImportParams() {\r\n    this.rowsImportParams.title = `Demo data from calculation ${this.calc.worker.avatar.sortableName} ${this.calc.workflow.salaryDate || \"No date\"}`;\r\n    this.rowsImportParams.personalId = this.calc.worker.paymentData.socialSecurityNumberValid;\r\n    this.rowsImportParams.employmentType = this.calc.result.responsibilities.employmentType;\r\n    this.rowsImportParams.payrollId = this.current.id;\r\n    this.rowsImportParams.period.start = this.calc.info.workStartDate;\r\n    this.rowsImportParams.period.end = this.calc.info.workEndDate;\r\n    this.rowsImportParams.period.daysCount = this.calc.framework.numberOfDays;\r\n  }\r\n\r\n  /** Copies the rows import data to the clipboard. */\r\n  public copyRowsImportData() {\r\n    if (!this.calc?.rows?.length) {\r\n      alert(\"Ei rivejä valitussa laskelmassa.\");\r\n      return;\r\n    }\r\n\r\n    const period = {\r\n      start: this.rowsImportParams.period.start,\r\n      end: this.rowsImportParams.period.end,\r\n    };\r\n    let counter = 0;\r\n    const data: WorktimeImport = {\r\n      header: {\r\n        title: this.rowsImportParams.title,\r\n        period,\r\n      },\r\n      rows: this.calc.rows.map((x) => {\r\n        const row: WorktimeImportRow = {\r\n          employmentType: this.rowsImportParams.employmentType as EmploymentRelationType,\r\n          personalId: this.rowsImportParams.personalId,\r\n          rowType: x.rowType,\r\n          type: x.type,\r\n          count: x.count,\r\n          message: x.message,\r\n          period: x.period || {},\r\n          accounting: x.accounting,\r\n          sourceId: \"DemoImport\" + counter++,\r\n          // Not typically used in import data.\r\n          // price: x.price,\r\n          // unit: x.unit,\r\n          data: {\r\n          }\r\n        };\r\n        row.period.start = row.period?.start || period.start;\r\n        row.period.end = row.period?.end || period.end;\r\n        const data = structuredClone(x.data);\r\n        delete data.payrollPeriodId;\r\n        delete data.importExplicitPrice;\r\n        delete data.committedAt;\r\n        delete data.status;\r\n        data.isApproved = true;\r\n        data.payrollId = this.rowsImportParams.payrollId;\r\n        row.data = data;\r\n        return row;\r\n      }),\r\n    };\r\n    const json = JSON.stringify(data, null, 2);\r\n    window.navigator.clipboard.writeText(json);\r\n\r\n    alert(\"Rivit on kopioitu leikepöydälle\");\r\n  }\r\n\r\n  /** Ordering filter */\r\n  private getOrderBy(): (a: CalculationListItem, b: CalculationListItem) => number | null {\r\n    switch (this.orderField) {\r\n      case \"status\":\r\n        return (r1, r2) => {\r\n          const status1 = `${Translations.get(\"SALAXY.ENUM.CalculationStatus.\" + (Objects.getProperty(r1, this.orderField) ?? \"\") + \".label\")}`;\r\n          const status2 = `${Translations.get(\"SALAXY.ENUM.CalculationStatus.\" + (Objects.getProperty(r2, this.orderField) ?? \"\") + \".label\")}`;\r\n          return (this.orderReverse ? -1 : 1) * status1.localeCompare(status2, \"fi\");\r\n        };\r\n        break;\r\n      // numbers\r\n      case \"grossSalary\":\r\n      case \"data.workerPayment\":\r\n        return (r1, r2) => {\r\n          return (this.orderReverse ? -1 : 1) * ((Objects.getProperty(r1, this.orderField) ?? 0) - (Objects.getProperty(r2, this.orderField) ?? 0));\r\n        };\r\n      // strings\r\n      default:\r\n        return (r1, r2) => {\r\n          return (this.orderReverse ? -1 : 1) * (Objects.getProperty(r1, this.orderField) ?? \"\").localeCompare(Objects.getProperty(r2, this.orderField) ?? \"\", \"fi\");\r\n        };\r\n    }\r\n  }\r\n\r\n  private getHeaderChangeInfo(): HeaderChangeInfo {\r\n    return {\r\n      isPaymentChannelChanged: this.current.input.paymentChannel !== this.original.input.paymentChannel,\r\n      isPeriodChanged: (this.current.input.period.daysCount !== this.original.input.period.daysCount ||\r\n        this.current.input.period.start !== this.original.input.period.start ||\r\n        this.current.input.period.end !== this.original.input.period.end),\r\n      isSalaryDateChanged: this.current.input.salaryDate !== this.original.input.salaryDate || this.current.input.salaryDateKind !== this.original.input.salaryDateKind,\r\n    };\r\n  }\r\n\r\n  private orderCalcs(ids: string[], items: CalculationListItem[]): CalculationListItem[] {\r\n    if (!items) {\r\n      return items;\r\n    }\r\n    items.sort((a, b) => ids.indexOf(a.id) - ids.indexOf(b.id));\r\n    return items;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {\r\n  Avatar,\r\n  Calculation,\r\n  InvoicesLogic,\r\n  PaymentChannel,\r\n  PayrollDetails,\r\n  Translations,\r\n} from \"@salaxy/core\";\r\n\r\nimport { InvoicesService } from \"../../services\";\r\n\r\n/**\r\n * Contains functionality for executing payments for payrolls or calculations.\r\n */\r\nexport class PaymentController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"InvoicesService\"];\r\n\r\n  /**\r\n   * The current business item that is being paid: Either Calculation or PayrollDetails.\r\n   * Currently only supports direct reference. May later support 'url' etc. like CRUD controllers.\r\n   */\r\n  public model: Calculation | PayrollDetails;\r\n\r\n  /** Button text set from the element */\r\n  public label: string;\r\n\r\n  /** Mode is either \"pay-button\" (default), \"channel-select\" \"button-and-channel\" or \"button-and-channel-horizontal\" */\r\n  public mode: \"pay-button\" | \"channel-select\" | \"button-and-channel\" | \"button-and-channel-horizontal\";\r\n\r\n /**\r\n  * Function that is called when the payment channel has been chagned\r\n  * Function has the following locals:\r\n  * paymentChannel: the selected payment channel.\r\n  * businessObject: the current business object which has been changed.\r\n  */\r\n  public onPaymentChannelChange: (params: {\r\n    /** Selected payment channel */\r\n    paymentChannel: PaymentChannel,\r\n    /** The current business object which has been changed.  */\r\n    businessObject: Calculation | PayrollDetails,\r\n  }) => void;\r\n\r\n  constructor(private invoicesService: InvoicesService) {\r\n  }\r\n\r\n  /**\r\n   * Initializes the controller\r\n   */\r\n  public $onInit() {\r\n    // Init here\r\n  }\r\n\r\n  /**\r\n   * Text for the payment button\r\n   * This is typically customized in custom payment scenarios.\r\n   */\r\n  public getPaymentButtonText(): string {\r\n    return this.label ? Translations.get(this.label) : Translations.get(\"SALAXY.UI_Terms.pay\");\r\n  }\r\n\r\n  /**\r\n   * Shows the payment process first page in a dialog (the invoice create process).\r\n   */\r\n  public goToInvoices() {\r\n    this.invoicesService.showPaymentDialog(this.businessObject);\r\n  }\r\n\r\n  /** Returns current business object */\r\n  public get businessObject(): Calculation | PayrollDetails {\r\n    return this.model;\r\n  }\r\n\r\n  /**\r\n   * Returns true if there is a selected channel for the business object.\r\n   */\r\n  public get isChannelDefined() {\r\n    return this.getCurrentChannel() != PaymentChannel.Undefined;\r\n  }\r\n\r\n  /** Gets the current channel avatar. */\r\n  public get currentChannel(): Avatar {\r\n    return InvoicesLogic.getChannelAvatar(this.getCurrentChannel());\r\n  }\r\n\r\n  /** Sets the payment channel and starts recalculation. */\r\n  public setPaymentChannel(newChannel: PaymentChannel) {\r\n    if (InvoicesLogic.isCalculation(this.businessObject)) {\r\n      this.businessObject.info.paymentChannel = newChannel;\r\n      if (this.businessObject.workflow) {\r\n        this.businessObject.workflow.salaryDateKind = null;\r\n      }\r\n    } else if (InvoicesLogic.isPayroll(this.businessObject)) {\r\n      this.businessObject.input.paymentChannel = newChannel;\r\n      this.businessObject.input.salaryDateKind = null;\r\n    } else {\r\n      throw new Error(\"Unknwon business object type.\");\r\n    }\r\n    this.onPaymentChannelChange({ paymentChannel: newChannel, businessObject: this.businessObject });\r\n  }\r\n\r\n  /** Gets the enabled channels. */\r\n  public get allChannels(): Avatar[] {\r\n    return this.invoicesService.channels;\r\n  }\r\n\r\n  private getCurrentChannel(): PaymentChannel {\r\n    let channel = null;\r\n    if (InvoicesLogic.isCalculation(this.businessObject)) {\r\n      channel = this.businessObject.info.paymentChannel;\r\n    } else if (InvoicesLogic.isPayroll(this.businessObject)) {\r\n      channel = this.businessObject.input.paymentChannel;\r\n    }\r\n    return channel ?? PaymentChannel.Undefined;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Ajax, AccountingData, Calculations, DateRange, Calculation, CalculationCorrection, CalculationResultLogic, Reports, VersionInfo, ApiListItem, ApiValidationErrorType, Translations, InputEnumOption, Language, kevaEmploymentRegCodes} from \"@salaxy/core\";\r\n\r\nimport { EditDialogKnownActions, InvoicesService, ReportsService, SessionService, UiCrudHelpers, UiHelpers } from \"../../services\";\r\nimport { CalculationCrudController } from \"./CalculationCrudController\";\r\n\r\n/**\r\n * CalculationEditorController used to handle EPR actions\r\n * This controller extends ApiCrudObjectController (via CalculationCrudController).\r\n */\r\nexport class CalculationEditorController extends CalculationCrudController {\r\n\r\n  /** Bindings for components that use this controller */\r\n  public static bindings = {\r\n\r\n  };\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Calculations\", \"UiHelpers\", \"UiCrudHelpers\", \"$location\", \"$routeParams\", \"SessionService\", \"ReportsService\", \"InvoicesService\", \"Reports\", \"AjaxNg1\"];\r\n\r\n\r\n   /** Flags to indicate if the request is in progress */\r\n   public loaders:any = {};\r\n\r\n   /** Indicates if the details sidebar is open */\r\n   public isRightSidebarOpen: boolean;\r\n\r\n  /** Data reader for the accounting diffa data. */\r\n  public accountingDiffDataReader = {\r\n    /** Function to read data into given array */\r\n    read: (target: string, ruleSet: string, arr: AccountingData[]): Promise<void> => {\r\n      if (this.accountingDiffData) {\r\n        arr.push(this.accountingDiffData);\r\n        return Promise.resolve();\r\n      } else {\r\n        return Promise.resolve();\r\n      }\r\n    },\r\n    /** Optional label for data export */\r\n    exportLabel: null,\r\n    /** Indicates if the export is not possible */\r\n    disabled: () => !this.accountingDiffData,\r\n    /* Indicates if row is expandable */\r\n    showExpand: true,\r\n    /* Indicates if rows exists*/\r\n    hasRows: () => !this.accountingDiffData?.ledgerAccounts\r\n  };\r\n\r\n  /** Status for diff data . */\r\n  private accountingDiffDataStatus: \"initial\" | \"loading\" | string = \"initial\";\r\n\r\n  private _accountingDiffData: AccountingData;\r\n\r\n  private _diffCalc: Calculation = {};\r\n\r\n  private latestCurrent: Calculation;\r\n\r\n  private latestBase: Calculation;\r\n\r\n  private pendingAccountingDiffData = false;\r\n\r\n  private _documentFlow: { item: ApiListItem, children: any[]};\r\n\r\n  private _state: string;\r\n\r\n  private baseCalc: Calculation;\r\n  private versionId: string;\r\n\r\n  constructor(\r\n    calcApi: Calculations,\r\n    uiHelpers: UiHelpers,\r\n    protected uiCrudHelpers: UiCrudHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    sessionService: SessionService,\r\n    reportsService: ReportsService,\r\n    protected invoicesService: InvoicesService,\r\n    private reportsApi: Reports,\r\n    private ajax: Ajax,\r\n  ) {\r\n    // Dependency injection\r\n    super(calcApi, reportsService, uiHelpers, $location, $routeParams, sessionService, invoicesService);\r\n    calcApi.getSingle = (id: string) =>  {\r\n      return this.ajax.getJSON(`/v03-rc/api/calculations/correction/${id}`).then((data: CalculationCorrection) => {\r\n        return data.calculation;\r\n      });\r\n    };\r\n  }\r\n  /**\r\n   * Initializes the controller\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Calculation total result diff between original and current calculation. */\r\n  public get diffCalc() {\r\n    this.onCalculationChange();\r\n    return this._diffCalc;\r\n  }\r\n\r\n  /** Accounting data diff between original and current calculation. */\r\n  public get accountingDiffData() {\r\n    this.onCalculationChange();\r\n    return this._accountingDiffData;\r\n  }\r\n\r\n   /** Document flow for the current calculation */\r\n   public get documentFlow() {\r\n    if (!this._documentFlow && this.current?.id) {\r\n      this._documentFlow = { item: null, children: null};\r\n      this.ajax.getJSON(`/v03-rc/api/calculations/correction/${this.current.id}/document-flow`).then((data) => {\r\n        angular.copy(data, this._documentFlow);\r\n      });\r\n    }\r\n    return this._documentFlow;\r\n  }\r\n\r\n  /**\r\n   * Returns validation for calculation\r\n   */\r\n  public get validation() {\r\n    // Currently apiValidation isValid is false even if all the items are warnings\r\n    if (!this.current) {\r\n      return null;\r\n    }\r\n    if (!this.current.result.validation.isValid) {\r\n      (this.current.result.validation as any).isValid = this.current.result.validation.errors.every(x => x.type === ApiValidationErrorType.Warning);\r\n    }\r\n\r\n    return this.current.result.validation;\r\n  }\r\n\r\n  /**\r\n   * Starts the reload process depending on the bindingMode:\r\n   */\r\n   public reload(): Promise<Calculation> {\r\n    return super.reload().then((calculation) => {\r\n      calculation.isReadOnly = false;\r\n      return calculation;\r\n    });\r\n  }\r\n  /** Load accounting data and calculate diff. */\r\n  public loadAccountingDiffData(targetId: string = null) {\r\n    if (targetId == null) {\r\n      if (this.accountingDiffDataStatus === \"initial\") {\r\n        targetId = \"default\";\r\n      }\r\n      else if (this.accountingDiffDataStatus === \"loading\") {\r\n        return;\r\n      }\r\n      else {\r\n        targetId = this.accountingDiffDataStatus;\r\n      }\r\n    }\r\n    if (this.accountingDiffDataStatus !== \"loading\") {\r\n      this.pendingAccountingDiffData = false;\r\n      // Start downloading for the new id\r\n      this.accountingDiffDataStatus = \"loading\";\r\n\r\n      const promises = [this.base,this.current].map((x) =>  this.reportsApi.getAccountingDataForCalculations([x], targetId, null));\r\n      Promise.all(promises).then( (accountingReports) => {\r\n        if (accountingReports && accountingReports.length == 2) {\r\n          this._accountingDiffData = this.diffAccountingData(accountingReports[0], accountingReports[1]);\r\n        }\r\n        this.accountingDiffDataStatus = targetId;\r\n\r\n        if(this.pendingAccountingDiffData){\r\n          this.loadAccountingDiffData();\r\n        }\r\n      });\r\n    }\r\n  }\r\n\r\n\r\n  /**\r\n   * Change base calculations\r\n   */\r\n   public changeBase() {\r\n    this.uiHelpers.showDialog(\r\n      \"salaxy-components/modals/calc/SelectVersion.html\",\r\n      null,\r\n      {\r\n        versions: this.versions,\r\n        versionId: this.versionId,\r\n      }).then((result) => {\r\n        if (result && result != \"cancel\") {\r\n          const version = result as VersionInfo;\r\n          this.api.getVersion(this.currentId, version?.versionId).then((data) => {\r\n            data.isReadOnly = false;\r\n            this.baseCalc = data;\r\n            this.versionId = version?.versionId;\r\n            this.onCalculationChange();\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n\r\n  // TODO: refresh -method should be called after every field update in the ui. Including rows.\r\n\r\n  /**\r\n   * Refreshes the calculation using the server side logic.\r\n   * @param refresh Option for refresh.\r\n   */\r\n   public refresh(refresh = \"default\"){\r\n\r\n    let confirmationDescription = \"\";\r\n\r\n    if(refresh == \"default\"){\r\n      this.loaders[refresh] = true;\r\n        const payload = {\r\n          id : this.current.id,\r\n          calculation: this.current,\r\n          state: this._state,\r\n        };\r\n        this.ajax.postJSON(`/v03-rc/api/calculations/correction/refresh/${refresh}`, payload).then((data) => {\r\n          this._state = data.state;\r\n          data.calculation.isReadOnly = false;\r\n          angular.copy(data.calculation, this.current);\r\n          this.loaders[refresh] = false;\r\n        });\r\n    } else {\r\n      switch (refresh) {\r\n        case \"worker\":\r\n          confirmationDescription = \"Haluatko päivittää työntekijän tiedot laskelmalle?\";\r\n          break;\r\n        case \"employer\":\r\n          confirmationDescription = \"Haluatko päivittää työnantajan tiedot laskelmalle?\";\r\n          break;\r\n        case \"employment\":\r\n          confirmationDescription = \"Haluatko päivittää työsuhteen tiedot laskelmalle?\";\r\n          break;\r\n        case \"taxcard\":\r\n          confirmationDescription = \"Haluatko päivittää verokortin tiedot laskelmalle?\";\r\n          break;\r\n        case \"insurances\":\r\n          confirmationDescription = \"Haluatko päivittää vero-, eläke- ja vakuutustiedot laskelmalle?\";\r\n          break;\r\n        case \"cfa\":\r\n          confirmationDescription = \"Haluatko päivittää asiakasvaraerät laskelmalle?\";\r\n          break;\r\n        default:\r\n          confirmationDescription = \"\";\r\n      }\r\n      this.uiHelpers.showConfirm(\"Haluatko jatkaa?\", confirmationDescription, \"Päivitä\", \"Peruuta\").then((result) =>\r\n    {\r\n      if (result) {\r\n        this.loaders[refresh] = true;\r\n        const payload = {\r\n          id : this.current.id,\r\n          calculation: this.current,\r\n          state: this._state,\r\n        };\r\n        this.ajax.postJSON(`/v03-rc/api/calculations/correction/refresh/${refresh}`, payload).then((data) => {\r\n          this._state = data.state;\r\n          data.calculation.isReadOnly = false;\r\n          angular.copy(data.calculation, this.current);\r\n          this.loaders[refresh] = false;\r\n        });\r\n        }\r\n        else\r\n        {\r\n          return;\r\n        }\r\n      });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Saves the edited readonly calculation.\r\n   */\r\n   public saveEdited(){\r\n    const payload = {\r\n      id : this.current.id,\r\n      calculation: this.current,\r\n      state: this._state,\r\n      snapshot: {\r\n        categories: []\r\n      }\r\n    };\r\n    this.ajax.getJSON(\"/v03-rc/api/calculations/correction/snapshot/categories\").then((categories) =>\r\n    {\r\n      this.uiHelpers.openEditDialog(\"salaxy-components/modals/calc/EditorConfirm.html\", { categories : [\"\"]}, { categories}).then((result) =>\r\n      {\r\n        if (result.action == EditDialogKnownActions.Ok) {\r\n          const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.isSaving\");\r\n            payload.snapshot = result.item;\r\n            this.ajax.postJSON(`/v03-rc/api/calculations/correction`, payload).then((data) =>\r\n            {\r\n              loading.dismiss();\r\n              this._state = data.state;\r\n              data.calculation.isReadOnly = false;\r\n              angular.copy(data.calculation, this.current);\r\n            });\r\n          }\r\n          else\r\n          {\r\n            return;\r\n          }\r\n        });\r\n    });\r\n  }\r\n\r\n  private _dateRange: DateRange;\r\n\r\n  /** Getter and setter for Calculation daterange in compatible format for new DateRange component. */\r\n  public get dateRange(): DateRange {\r\n    if (!this.current) {\r\n      return null;\r\n    }\r\n    if (!this._dateRange) {\r\n      this._dateRange = {\r\n        start: this.current.info.workStartDate,\r\n        end: this.current.info.workEndDate,\r\n        daysCount: this.current.framework.numberOfDays,\r\n      };\r\n    }\r\n    return this._dateRange;\r\n  }\r\n  public set dateRange(value: DateRange) {\r\n    this._dateRange = value;\r\n  }\r\n\r\n  /**\r\n   * Called when the date range changes.\r\n   */\r\n  public dateRangeChange() {\r\n    if (!this.dateRange || !this.current) {\r\n      return;\r\n    }\r\n    this.current.info.workStartDate = this.dateRange.start;\r\n    this.current.info.workEndDate = this.dateRange.end;\r\n    this.current.framework.numberOfDays = this.dateRange.daysCount;\r\n  }\r\n\r\n  private get base() {\r\n    if (!this.baseCalc && this.versions.length > 0) {\r\n      this.versionId = this.versions[this.versions.length - 1].versionId;\r\n      this.baseCalc = angular.copy(this.original);\r\n    }\r\n    return this.baseCalc ?? this.original;\r\n  }\r\n\r\n  /**\r\n   * Returns valid employment reg codes for the selected pensions company.\r\n   * @returns Options for the employment reg codes.\r\n   */\r\n  public getEmploymentRegCodeOptions(): Array<InputEnumOption> {\r\n    return this.uiHelpers.cache(this, \"employmentRegCodes\",\r\n    () => kevaEmploymentRegCodes.filter((x) => x.pensionCompany === this.current.result.responsibilities.pensionCompany).map((regCode) =>\r\n      ({ value: regCode.code, text: Translations.getLanguage() === Language.Sv ? regCode.labelSv : regCode.labelFi })),\r\n    () => this.current.result.responsibilities.pensionCompany);\r\n  }\r\n\r\n  private diffAccountingData(originalAccountingData: AccountingData, modifiedAccountingData: AccountingData): AccountingData {\r\n    // Leave only top level.\r\n    originalAccountingData.ledgerAccounts.forEach((x) => x.entries = []);\r\n    originalAccountingData.summary = {};\r\n    modifiedAccountingData.ledgerAccounts.forEach((x) => x.entries = []);\r\n    modifiedAccountingData.summary = {};\r\n    const result = modifiedAccountingData;\r\n\r\n    originalAccountingData.ledgerAccounts.forEach( (orig) => {\r\n      const modified =  result.ledgerAccounts.find((x) => x.accountNumber === orig.accountNumber && x.accountGrouping == orig.accountGrouping );\r\n      if (modified) {\r\n        (modified as any).saldo = modified.saldo - orig.saldo;\r\n      } else {\r\n        const removedAccount = angular.copy(orig);\r\n        (removedAccount as any).saldo = 0.0 - orig.saldo;\r\n        result.ledgerAccounts.push(removedAccount);\r\n      }\r\n    });\r\n    result.ledgerAccounts.forEach((x) => x.entries =\r\n    [\r\n      {\r\n        id: null,\r\n        entryDate: null,\r\n        description: \"Ero\",\r\n        isDebit: x.saldo >= 0,\r\n        amount: x.saldo >= 0 ? x.saldo : -1.0 * x.saldo,\r\n        vatPercent: null,\r\n        accountNumber: x.accountNumber,\r\n        accountName: x.accountName,\r\n        accountGrouping: x.accountGrouping,\r\n        dimension: {},\r\n      }\r\n    ]);\r\n    return result;\r\n  }\r\n\r\n  private onCalculationChange(){\r\n    if (this.base && this.current && ( !angular.equals(this.current, this.latestCurrent) || !angular.equals(this.base, this.latestBase))) {\r\n      this.latestCurrent = angular.copy(this.current);\r\n      this.latestBase = angular.copy(this.base);\r\n      const diff = angular.copy(this.base);\r\n      diff.result = CalculationResultLogic.diff(this.base.result, this.current.result);\r\n      angular.copy(diff, this._diffCalc);\r\n      this.pendingAccountingDiffData = true;\r\n      this.loadAccountingDiffData();\r\n    }\r\n  }\r\n\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Arrays, CostAccountingDimensionDefinition, CostAccountingDimension, CostAccountingDimensionScope } from \"@salaxy/core\";\r\n\r\nimport { SessionService} from \"../../services\";\r\n\r\n/**\r\n * Handles the user interaction for entering cost accounting data.\r\n */\r\nexport class CostAccountingController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"SessionService\"];\r\n\r\n  /** Scope for the cost accounting: calculation or row. */\r\n  public scope: CostAccountingDimensionScope;\r\n\r\n  /** Dimension values to edit.*/\r\n  public current: CostAccountingDimension[];\r\n\r\n  /** Possible upper level (e.g. calculation) dimensions that are inherited */\r\n  private _inherited: CostAccountingDimension[];\r\n\r\n  /** Bindable read-only */\r\n  public readOnly?: boolean;\r\n\r\n  /** CostAccountingDimensionDefinition including label, type and options */\r\n  public dimensions: CostAccountingDimensionDefinition[];\r\n\r\n  /**\r\n   * Style of inputs.\r\n   * If null or empty, displays normal input.\r\n   * - \"openeClose\" shows readOnly-like input with toggle button to open the field for editing.\r\n   */\r\n  public inputMode: \"\" | \"openClose\";\r\n\r\n  private _definitions:  CostAccountingDimensionDefinition[] = [];\r\n  private _options: { [key: string] : Array<{\r\n    /** Option value. */\r\n    value: any,\r\n    /** Option text.  */\r\n    text: string,\r\n    /** Option description. */\r\n    title?: string,\r\n  }> } = {};\r\n\r\n  private _values:  { [key: string] : Array<CostAccountingDimension> } = {};\r\n\r\n  private _inheritedValues:  { [key: string] : Array<CostAccountingDimension> } = {};\r\n  private _obsoleteValues: Array<CostAccountingDimension> = [];\r\n  private _newDimensions: CostAccountingDimension[] = [];\r\n\r\n  /**\r\n   * Creates a new CalcCostAccountingController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    protected  sessionService: SessionService\r\n  ) {\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n   // empty\r\n  }\r\n\r\n  /** Copy of inherited dimensions */\r\n  public get inherited(): CostAccountingDimension[] {\r\n    return this._inherited;\r\n  }\r\n\r\n  /** Copy of inherited dimensions */\r\n  public set inherited(value: CostAccountingDimension[])  {\r\n    this._inherited = angular.copy(value);\r\n  }\r\n\r\n  /** Returns applicable dimensions*/\r\n  public get definitions(): CostAccountingDimensionDefinition[] {\r\n    const d = (this.dimensions ?? this.sessionService.session?.settings?.costAccounting?.dimensions ?? [])\r\n    .filter( (x) =>\r\n      // no hidden scope\r\n      x.scope !== CostAccountingDimensionScope.Hidden &&\r\n      (\r\n        // show if scope definition for dimension not given\r\n        ( !x.scope || x.scope === CostAccountingDimensionScope.None) ||\r\n        // or if scope definition for use given\r\n        (!this.scope || this.scope === CostAccountingDimensionScope.None) ||\r\n        // or this scope\r\n        (this.scope === x.scope)\r\n      )\r\n    );\r\n    this.modifyOptions(d, this._definitions);\r\n    return this._definitions;\r\n  }\r\n\r\n  /**\r\n   * Returns true, if the dimension exists.\r\n   * @param id Id of the dimension.\r\n   * @returns True, if the dimension with given id exists.\r\n   */\r\n  public getDefinition(id: string) {\r\n    return this.definitions.find( (x) => x.id == id);\r\n  }\r\n\r\n   /**\r\n    * Returns total percentage for the dimension\r\n    * @param id Name of the dimension.\r\n    */\r\n  public getSum(id: string ): number {\r\n      return Arrays.sum((this.current ?? []).filter((x) => x.id == id), (x: any) => x.percent ?? 0);\r\n  }\r\n\r\n   /**\r\n    * Returns available options.\r\n    * @param id Id of the dimension.\r\n    */\r\n  public getOptions(id: string) {\r\n    if (!this._options[id]) {\r\n      this._options[id] = [];\r\n    }\r\n\r\n    let newOptions = [];\r\n    const dimensionForOptions = this.definitions.find((x) => x.id === id);\r\n    if (dimensionForOptions) {\r\n      newOptions = dimensionForOptions.options.filter((x) =>\r\n        x.scope !== CostAccountingDimensionScope.Hidden &&\r\n        (\r\n          // show if scope definition for dimension not given\r\n          ( !x.scope || x.scope === CostAccountingDimensionScope.None) ||\r\n          // or if scope definition for use given\r\n          (!this.scope || this.scope === CostAccountingDimensionScope.None) ||\r\n          // or this scope\r\n          (this.scope === x.scope)\r\n        )\r\n      )\r\n      .map( (x) => ({ value: x.value, text: x.text }));\r\n    }\r\n\r\n    this.modifyOptions(newOptions, this._options[id]);\r\n    return this._options[id];\r\n  }\r\n\r\n  /**\r\n   * Returns true if options exists for the dimension.\r\n   * @param id Id of the dimension.\r\n   * @param value Value of the dimension.\r\n   * @returns True, if an option exists for the value.\r\n   */\r\n  public hasOptions(id: string, value: string): boolean {\r\n    const opts = this.getOptions(id);\r\n    if (!value) {\r\n      return opts.filter(x => x.value).length > 0;\r\n    }\r\n    return !!opts.find((x) => x.value == value);\r\n  }\r\n\r\n   /**\r\n    * Returns single value.\r\n    * @param id Id of the dimension.\r\n    */\r\n   public getSingleValue(id: string) {\r\n    let singleValue = this.current?.find((x) => x.id === id) ?? this._newDimensions.find((x) => x.id === id);\r\n    if (!singleValue && !this.readOnly) {\r\n      singleValue = { id };\r\n      this._newDimensions.push(singleValue);\r\n    }\r\n    return singleValue;\r\n  }\r\n\r\n  /**\r\n   * Sets single value.\r\n   * @param id Id of the dimension.\r\n   * @param value Value of the dimension.\r\n   */\r\n    public setSingleValue(id: string, value: string) {\r\n      const singleValue = this.current?.find((x) => x.id === id);\r\n      if (singleValue) {\r\n        singleValue.value = value;\r\n      }\r\n      else {\r\n        this.current.push({ id, value });\r\n      }\r\n    }\r\n\r\n  /**\r\n   * Returns current values.\r\n   * @param id Id of the dimension.\r\n   */\r\n  public getValues(id: string) {\r\n    if (!this._values[id]) {\r\n      this._values[id] = [];\r\n    }\r\n\r\n    const values = (this.current ?? []).filter((x) => x.id === id);\r\n    this.modifyOptions(values, this._values[id]);\r\n\r\n    return this._values[id];\r\n  }\r\n\r\n  /**\r\n   * Sets values.\r\n   * @param values Values of the dimension.\r\n   */\r\n  public setValues(values: CostAccountingDimension[]) {\r\n    this.current.push( ... angular.copy(values));\r\n  }\r\n\r\n  /**\r\n   * Deletes value from the dimensions\r\n   * @param value Value to delete\r\n   */\r\n  public deleteValue(value: CostAccountingDimension) {\r\n    const index = this.current.indexOf(value);\r\n    if (index >= 0) {\r\n      this.current.splice(index,1);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Returns true if the dimension values are inherited.\r\n   * @param id Id of the dimension.\r\n   */\r\n  public isInherited(id: string) {\r\n    if ( !this.current?.some((x) => x.id === id && !!x.value)) {\r\n      return !!this.cleanDimensions(this.inherited)?.some((x) => x.id === id);\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /**\r\n   * Returns inherited single value.\r\n   * @param id Id of the dimension.\r\n   */\r\n  public getInheritedSingleValue(id: string) {\r\n    const singleValue = (this.cleanDimensions(this.inherited) ?? []).find((x) => x.id === id);\r\n    return singleValue;\r\n  }\r\n\r\n  /**\r\n   * Returns inherited values.\r\n   * @param id Id of the dimension.\r\n   */\r\n   public getInheritedValues(id: string) {\r\n\r\n    if (!this._inheritedValues[id]) {\r\n      this._inheritedValues[id] = [];\r\n    }\r\n\r\n    const values = (this.cleanDimensions(this.inherited) ?? []).filter((x) => x.id === id);\r\n    this.modifyOptions(values, this._inheritedValues[id]);\r\n\r\n    return this._inheritedValues[id];\r\n  }\r\n\r\n  /**\r\n   * Returns total percentage for the dimension for inherited values\r\n   * @param id Name of the dimension.\r\n   */\r\n   public getInheritedSum(id: string ): number {\r\n      return Arrays.sum((this.cleanDimensions(this.inherited)  ?? []).filter((x) => x.id == id), (x: any) => x.percent ?? 0);\r\n  }\r\n\r\n  /**\r\n   * Returns current obsolete values.\r\n   */\r\n    public get obsoleteValues() {\r\n      if (this.current){\r\n        const obsolete = this.current.filter((x) => !this._definitions.find((d) => d.id === x.id)).sort((a,b) => (a.id ?? \"\").localeCompare(b.id ?? \"\") );\r\n        this.modifyOptions(obsolete, this._obsoleteValues);\r\n      }\r\n      return this._obsoleteValues;\r\n    }\r\n\r\n  /**\r\n   * Returns true if the values contains obsolete dimensions.\r\n   * @returns True if the values contains obsolete dimensions.\r\n   */\r\n  public get hasObsoleteValues(): boolean {\r\n    return this.obsoleteValues.length > 0;\r\n  }\r\n\r\n  private modifyOptions(\r\n    source: any[],\r\n    target: any[]) {\r\n    if (angular.equals(source, target)) {\r\n      return;\r\n    }\r\n    target.splice(0, target.length);\r\n    target.push(...source);\r\n  }\r\n\r\n  private cleanDimensions(dimensions: CostAccountingDimension[]) {\r\n    if (!dimensions) {\r\n      return dimensions;\r\n    }\r\n    const cleaned = dimensions.filter(x => x.value && x.id);\r\n    return cleaned;\r\n  }\r\n}\r\n","import { Arrays, Calculation, CostAccountingDimensionScope } from \"@salaxy/core\";\r\n\r\nimport { SessionService} from \"../../services\";\r\n\r\nimport { CostAccountingController } from \"./CostAccountingController\";\r\n\r\n/**\r\n * Handles the user interaction for entering cost accounting data for the calculation.\r\n */\r\nexport class CalcCostAccountingController extends CostAccountingController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"SessionService\"];\r\n\r\n  /** The calculation*/\r\n  public calc: Calculation;\r\n\r\n  /**\r\n   * Creates a new CalcCostAccountingController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    sessionService: SessionService\r\n  ) {\r\n    super(sessionService);\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n   this.scope = CostAccountingDimensionScope.Calculation;\r\n   super.$onInit();\r\n  }\r\n\r\n  /**\r\n   * Returns true if the current calculation is read only.\r\n   */\r\n   public get isReadOnly(): boolean {\r\n    if (this.readOnly === true || this.readOnly === false) {\r\n      return this.readOnly;\r\n    }\r\n    return this.calc.isReadOnly;\r\n  }\r\n\r\n  // TO BE REMOVED\r\n\r\n  /** Returns the cost accounting model type */\r\n  public get isLegacy(): boolean {\r\n    //backward compat.\r\n    if (this.calc.usecase?.uri === \"/UsecaseDefinition/FI53POYS0025543933/costcenter-percentages\") {\r\n      return true;\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /** Returns total cost center percentage */\r\n  public getLegacySum(): number {\r\n    if (this.isLegacy) {\r\n      return Arrays.sum(this.calc.usecase?.data?.dimensions?.costCenter ?? [], (x: any) => x.percent ?? 0);\r\n    }\r\n    return 0;\r\n  }\r\n\r\n  /** Returns current costCenter. */\r\n  public get costCenter() {\r\n    if (this.isLegacy) {\r\n      if (!this.calc.usecase) {\r\n        this.calc.usecase = {};\r\n      }\r\n      if (!this.calc.usecase.data) {\r\n        this.calc.usecase.data = {};\r\n      }\r\n      if (!this.calc.usecase.data.dimensions) {\r\n        this.calc.usecase.data.dimensions = {};\r\n      }\r\n      if (!this.calc.usecase.data.dimensions.costCenter) {\r\n        this.calc.usecase.data.dimensions.costCenter = [];\r\n      }\r\n    }\r\n    return this.calc.usecase?.data?.dimensions?.costCenter;\r\n  }\r\n}\r\n","import { Arrays, Calculation, CostAccountingDimensionScope, UserDefinedRow } from \"@salaxy/core\";\r\n\r\nimport { SessionService } from \"../../services\";\r\nimport { CostAccountingController } from \"./CostAccountingController\";\r\n\r\n/**\r\n * Handles the user interaction for entering cost accounting data for the calculation row.\r\n */\r\nexport class CalcRowCostAccountingController extends CostAccountingController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"SessionService\"];\r\n\r\n  /** The calculation for row */\r\n  public calc: Calculation;\r\n\r\n  /** Current row */\r\n  public row: UserDefinedRow;\r\n\r\n  /**\r\n   * Creates a new CalcCostAccountingController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    sessionService: SessionService,\r\n\r\n  ) {\r\n    super(sessionService);\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    this.scope = CostAccountingDimensionScope.Row;\r\n    super.$onInit();\r\n  }\r\n\r\n  /**\r\n   * Returns true if the current calculation is read only.\r\n   */\r\n   public get isReadOnly(): boolean {\r\n    if (this.readOnly === true || this.readOnly === false) {\r\n      return this.readOnly;\r\n    }\r\n    return this.calc.isReadOnly;\r\n  }\r\n\r\n  /** Returns the cost accounting model type */\r\n  public get isLegacy(): boolean {\r\n    //backward compat.\r\n    if (this.calc.usecase?.uri === \"/UsecaseDefinition/FI53POYS0025543933/costcenter-percentages\") {\r\n      return true;\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /** Returns total cost center percentage */\r\n  public getLegacySum(): number {\r\n    if (this.isLegacy) {\r\n      return Arrays.sum(this.row?.data?.dimensions?.costCenter ?? [], (x: any) => x.percent ?? 0);\r\n    }\r\n    return 0;\r\n  }\r\n\r\n  /** Returns current costCenter. */\r\n  public get costCenter() {\r\n    if (this.isLegacy) {\r\n      if (!this.row.data) {\r\n        this.row.data = {};\r\n      }\r\n      if (!this.row.data.dimensions) {\r\n        this.row.data.dimensions = {};\r\n      }\r\n      if (!this.row.data.dimensions.costCenter) {\r\n        this.row.data.dimensions.costCenter = [];\r\n      }\r\n    }\r\n\r\n    return this.row.data?.dimensions?.costCenter;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\nimport { Calculation, CalculationStatus } from \"@salaxy/core\";\r\nimport { WizardController } from \"../bases/WizardController\";\r\nimport { WizardStep, WizardService, InvoicesService, EditDialogParameters } from \"../../services\";\r\n\r\n/**\r\n * Wizard for creating personal payment.\r\n */\r\nexport class PalkkausPersonalPaymentOverviewController extends WizardController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n   public static $inject = [\"$scope\", \"InvoicesService\", \"EditDialogParameters\", \"WizardService\"];\r\n\r\n   /** Used calculation */\r\n  public model: Calculation;\r\n\r\n  /**\r\n   * Creates a new WizardController with dependency injection.\r\n   * @ignore\r\n   */\r\n   constructor(\r\n    $scope: angular.IScope,\r\n    private invoices: InvoicesService,\r\n    private editDialogParameters: EditDialogParameters<Calculation>,\r\n    wizardService: WizardService\r\n  ) {\r\n    super($scope, wizardService);\r\n  }\r\n\r\n  /**\r\n   * Initialization of the controller\r\n   */\r\n   public $onInit() {\r\n    super.$onInit();\r\n\r\n    this.wizardService.setSteps(this.getWizardSteps());\r\n    this.wizardService.activeStepNumber = 1;\r\n    if (!this.editDialogParameters) {\r\n      throw new Error(\"No editDialogParameters coming in.\");\r\n    }\r\n    this.model = this.editDialogParameters.current as Calculation;\r\n    if (this.model?.workflow?.status === CalculationStatus.PaymentSucceeded && !this.editDialogParameters?.logic?.isInspectingPaidInvoices) {\r\n      this.step = 4;\r\n    }\r\n  }\r\n\r\n  /** Worker wizard configuration */\r\n  public getWizardSteps(): WizardStep[] {\r\n    if (this.editDialogParameters?.logic?.isInspectingPaidInvoices) {\r\n      return [\r\n        {\r\n          title: \"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.steps.step1.heading\",\r\n          view: \"salaxy-components/modals/calc/personal-payment/TotalWorkerPayment.html\",\r\n        },\r\n        {\r\n          title: \"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.steps.step2.heading\",\r\n          view: \"salaxy-components/modals/calc/personal-payment/Tax.html\",\r\n        },\r\n        {\r\n          title: \"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.steps.step3.heading\",\r\n          view: \"salaxy-components/modals/calc/personal-payment/SideCosts.html\",\r\n        },\r\n      ];\r\n    }\r\n    return [\r\n      {\r\n        title: \"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.steps.step1.heading\",\r\n        view: \"salaxy-components/modals/calc/personal-payment/TotalWorkerPayment.html\",\r\n      },\r\n      {\r\n        title: \"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.steps.step2.heading\",\r\n        view: \"salaxy-components/modals/calc/personal-payment/Tax.html\",\r\n      },\r\n      {\r\n        title: \"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.steps.step3.heading\",\r\n        view: \"salaxy-components/modals/calc/personal-payment/SideCosts.html\",\r\n      },\r\n      {\r\n        title: \"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.steps.step4.heading\",\r\n        view: \"salaxy-components/modals/calc/personal-payment/Approval.html\",\r\n      },\r\n    ];\r\n  }\r\n\r\n  /** Returns true if user can go forward in  the wizard  */\r\n  public get canGoNext(): boolean {\r\n    if (this.steps.length > this.step) {\r\n      if (this.steps[this.step] && !this.steps[this.step].disabled) {\r\n          return true;\r\n      }\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /**\r\n   * Navigates to the next step if possible.\r\n   * Override adds the taxcard if personalId is there and resets it if personalId has changed.\r\n   */\r\n   public goNext() {\r\n    super.goNext();\r\n  }\r\n\r\n  /**\r\n   * Checks if user can navigate to previuous step\r\n   */\r\n  public get canGoPrevious(): boolean {\r\n    if (this.model?.workflow?.status === CalculationStatus.PaymentSucceeded && !this.editDialogParameters?.logic?.isInspectingPaidInvoices) {\r\n      return false;\r\n    }\r\n\r\n    if (this.step > 1 && !this.steps[this.step - 2].disabled) {\r\n        return true;\r\n    }\r\n    return false;\r\n}\r\n\r\n  /**\r\n   * Return EPR payment warning to template\r\n   */\r\n  public get eprPaymentWarning() {\r\n    return this.invoices.getEprWarningForPayment(this.model?.workflow?.salaryDate);\r\n  }\r\n\r\n  /**\r\n   * Return EPR cancel warning to template\r\n   */\r\n   public get eprCancelWarning() {\r\n    return this.invoices.getEprWarningForCancellation(this.model?.workflow?.salaryDate, this.model?.workflow?.status === CalculationStatus.PaymentSucceeded ? true : false);\r\n  }\r\n}","import angular from \"angular\";\r\n\r\nimport {\r\n  Calculation,\r\n  InvoicesLogic,\r\n  PayrollDetails,\r\n  SalaryDateKind,\r\n  Brand\r\n} from \"@salaxy/core\";\r\n\r\nimport { EditDialogKnownActions, UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Contains functionality for switching between salary date kinds for payrolls or calculations.\r\n */\r\nexport class SalaryDateKindController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"UiHelpers\"];\r\n\r\n  /**\r\n   * The current business item that is being paid: Either Calculation or PayrollDetails.\r\n   */\r\n  public model: Calculation | PayrollDetails;\r\n\r\n /**\r\n  * Function that is called when the salary date kind has been chagned\r\n  * Function has the following locals:\r\n  * paymentChannel: the selected payment channel.\r\n  * businessObject: the current business object which has been changed.\r\n  */\r\n  public onSalaryDateKindChange: (params: {\r\n    /** Selected payment channel */\r\n    salaryDateKind: SalaryDateKind,\r\n    /** The current business object which has been changed.  */\r\n    businessObject: Calculation | PayrollDetails,\r\n  }) => void;\r\n\r\n  public salaryDateKinds = SalaryDateKindController.getSalaryDateKinds();\r\n\r\n  constructor(private uiHelpers: UiHelpers) {\r\n  }\r\n\r\n  /**\r\n   * Initializes the controller\r\n   */\r\n  public $onInit() {\r\n    // Init here\r\n  }\r\n\r\n  /** Gets the current salary date kind object. */\r\n  public get currentSalaryDateKind() {\r\n    let currentValue: SalaryDateKind = undefined;\r\n    if (InvoicesLogic.isCalculation(this.model)) {\r\n      currentValue = this.model.workflow.salaryDateKind;\r\n    } else if (InvoicesLogic.isPayroll(this.model)) {\r\n      currentValue = this.model.input.salaryDateKind;\r\n    }\r\n    return this.salaryDateKinds.find((x) => x.value == currentValue) ?? this.salaryDateKinds[0];\r\n  }\r\n\r\n\r\n  /** Sets the salary date kind and starts recalculation. */\r\n  public setSalaryDateKind(newSalaryDateKind: SalaryDateKind) {\r\n    if (InvoicesLogic.isCalculation(this.model)) {\r\n      this.showCalculationSalaryDateKindSelection(newSalaryDateKind, this.model);\r\n    } else if (InvoicesLogic.isPayroll(this.model)) {\r\n      this.showPayrollSalaryDateKindSelection(newSalaryDateKind, this.model);\r\n    } else {\r\n      throw new Error(\"Unknwon business object type.\");\r\n    }\r\n  }\r\n\r\n\r\n\r\n  /** Shows the salary date kind dialog */\r\n  private showCalculationSalaryDateKindSelection(newSalaryDateKind: SalaryDateKind, calculation: Calculation) {\r\n    const original = calculation.workflow.salaryDateKind;\r\n    const isCfa = InvoicesLogic.isCfa(calculation.info.paymentChannel);\r\n    const logic = {\r\n        value: newSalaryDateKind,\r\n        text: `SALAXY.ENUM.SalaryDateKind.${newSalaryDateKind}.label`,\r\n        title: `SALAXY.ENUM.SalaryDateKind.${newSalaryDateKind}.description${isCfa ? \"Cfa\" : \"NonCfa\"}`\r\n    };\r\n\r\n    this.uiHelpers.openEditDialog(\"salaxy-components/modals/calc/SalaryDateKind.html\", calculation.workflow.salaryDateKind, logic).then( (result) => {\r\n      if (result.action ==  EditDialogKnownActions.Ok) {\r\n        if (original != newSalaryDateKind) {\r\n          calculation.workflow.salaryDateKind = newSalaryDateKind;\r\n          this.onSalaryDateKindChange({ salaryDateKind: newSalaryDateKind, businessObject: calculation });\r\n        }\r\n      }\r\n    });\r\n  }\r\n\r\n  /** Shows the salary date kind dialog */\r\n  private showPayrollSalaryDateKindSelection(newSalaryDateKind: SalaryDateKind, payroll: PayrollDetails) {\r\n\r\n    const original = payroll.input.salaryDateKind;\r\n    const isCfa = InvoicesLogic.isCfa(payroll.input.paymentChannel);\r\n    const logic = {\r\n        value: newSalaryDateKind,\r\n        text: `SALAXY.ENUM.SalaryDateKind.${newSalaryDateKind}.label`,\r\n        title: `SALAXY.ENUM.SalaryDateKind.${newSalaryDateKind}.description${isCfa ? \"Cfa\" : \"NonCfa\"}`\r\n    };\r\n\r\n    this.uiHelpers.openEditDialog(\"salaxy-components/modals/calc/SalaryDateKind.html\", payroll.input.salaryDateKind, logic).then( (result) => {\r\n      if (result.action ==  EditDialogKnownActions.Ok) {\r\n        if (original != newSalaryDateKind) {\r\n          payroll.input.salaryDateKind = newSalaryDateKind;\r\n          this.onSalaryDateKindChange({ salaryDateKind: newSalaryDateKind, businessObject: payroll });\r\n        }\r\n      }\r\n    });\r\n  }\r\n\r\n  private static getSalaryDateKinds() {\r\n    return [\r\n      {\r\n        value : SalaryDateKind.Default,\r\n        text: \"SALAXY.ENUM.SalaryDateKind.default.label\",\r\n        avatar: {\r\n          color: Brand.getBrandColor(\"primary\", \"rgba\"),\r\n          icon: \"bi-clock\",\r\n        }\r\n      },\r\n      {\r\n        value : SalaryDateKind.InPast,\r\n        text: \"SALAXY.ENUM.SalaryDateKind.inPast.label\",\r\n        avatar: {\r\n          color: Brand.getBrandColor(\"danger\", \"rgba\"),\r\n          icon: \"bi-clock-history\",\r\n        }\r\n      },\r\n    ];\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {Calculation,CalcWorktime, HolidayYears, HolidayYear, Dates, AbsencePeriod, Arrays, HolidayBonusPaymentMethod, AbsenceCauseCode} from \"@salaxy/core\";\r\nimport {UiHelpers} from \"../../services\";\r\n\r\n/**\r\n * Displays leaves for current calculation period.\r\n */\r\nexport class CalcLeavesController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"HolidayYears\", \"UiHelpers\"];\r\n\r\n  public annualLeavestoBePaid: AbsencePeriod[] = [];\r\n  public annualLeavesWaitingForPayment: AbsencePeriod[] = [];\r\n  public absencesToUse: AbsencePeriod[] = [];\r\n  public absencesToReject: AbsencePeriod[] = [];\r\n\r\n  /** Current calculation. */\r\n  public calc: Calculation;\r\n\r\n   /** Current worktime. */\r\n   public worktime: CalcWorktime;\r\n\r\n   /** All holiday years for employment */\r\n   public employmentHolidayYears: HolidayYear[] = [];\r\n\r\n   /** Current holiday year for employment */\r\n   public currentEmploymentHolidayYear: HolidayYear;\r\n\r\n  /**\r\n   * Creates a new CalcReportsController\r\n   * @ignore\r\n   */\r\n  constructor(private fullApi: HolidayYears, private uiHelpers: UiHelpers) {\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    this.absencesToUse.push(...this.worktime.absencesPeriods?.filter((x) => x.causeCode !== AbsenceCauseCode.AnnualLeave) || []);\r\n    // generate ids for absences\r\n    this.absencesToUse.forEach((x) => x.id = x.id || \"$\"+this.newGuid());\r\n    this.absencesToReject.push(...angular.copy(this.absencesToUse));\r\n    // there is no need to load absences, because absences can only be used or not used. No picking from other periods should be possible.\r\n    // probably there is no need to edit absences either\r\n\r\n    this.getHolidayYearsForEmployment(this.calc.worker.employmentId).then(() => {\r\n      this.annualLeavestoBePaid = this.worktime.absencesPeriods?.filter((x) => x.causeCode == AbsenceCauseCode.AnnualLeave) || [];\r\n      this.annualLeavesWaitingForPayment = this.currentEmploymentHolidayYear.leaves.planned.map( x => ({\r\n        causeCode: AbsenceCauseCode.AnnualLeave,\r\n        id: x.id,\r\n        period: angular.copy(x.period),\r\n        notes: x.notes\r\n      }));\r\n    });\r\n  }\r\n\r\n  /** Returns final absences periods */\r\n  public getAbsencesPeriods() {\r\n    const result = angular.copy(([] as AbsencePeriod[]).concat(...this.annualLeavestoBePaid).concat(...this.absencesToUse));\r\n    // remove absence ids\r\n    result.forEach((x) => {\r\n      if (x.id?.startsWith(\"$\")) {\r\n        delete x.id;\r\n      }\r\n    });\r\n    return result;\r\n  }\r\n\r\n  /** Loads holiday years for employment and sets current holiday year */\r\n  public getHolidayYearsForEmployment(employmentId: string): Promise<HolidayYear[]> {\r\n    return this.fullApi.getForEmployment(employmentId).then((result) => {\r\n      this.employmentHolidayYears = result;\r\n      const periodStart = Dates.asDate(this.calc.info.workStartDate || Dates.getToday());\r\n      const year = periodStart > Dates.getDate(Dates.getYear(periodStart), 3, 31) ? Dates.getYear(periodStart) : Dates.getYear(periodStart) - 1;\r\n\r\n      this.currentEmploymentHolidayYear = this.employmentHolidayYears.find((holidayYear) => holidayYear.year === year);\r\n      return result;\r\n    });\r\n  }\r\n\r\n /**\r\n  * Moves an item between different payment lists.\r\n  * @param item - The item to be moved.\r\n  * @param target - The target payment list.\r\n  */\r\n  public moveItem(item: any, target:\"annualLeavestoBePaid\" | \"annualLeavesWaitingForPayment\") {\r\n    if(target ===\"annualLeavesWaitingForPayment\") {\r\n      const index = this.annualLeavestoBePaid.indexOf(item);\r\n      if (index > -1) {\r\n        this.annualLeavestoBePaid.splice(index, 1);\r\n      }\r\n    }\r\n    if(target ===\"annualLeavestoBePaid\") {\r\n      this.annualLeavestoBePaid.push(item);\r\n    }\r\n  }\r\n\r\n /**\r\n  * Moves an item between different payment lists.\r\n  * @param item - The item to be moved.\r\n  * @param target - The target payment list.\r\n  */\r\n   public moveAbsenceItem(item: any, target:\"absencesToUse\" | \"absencesToReject\") {\r\n    if(target ===\"absencesToReject\") {\r\n      const index = this.absencesToUse.indexOf(item);\r\n      if (index > -1) {\r\n        this.absencesToUse.splice(index, 1);\r\n      }\r\n    }\r\n    if(target ===\"absencesToUse\") {\r\n      this.absencesToUse.push(item);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Determines if a given leave should be disabled based on its type and whether it's in the list of leaves to be paid.\r\n   * @param {AnnualLeave} leave - The leave object to check.\r\n   */\r\n  public isSelectedToBePaid(leave: AbsencePeriod) {\r\n    return this.annualLeavestoBePaid?.some((item) => item.id === leave.id);\r\n  }\r\n\r\n  /**\r\n   * Determines if a given absence should be disabled based on it's in the list of absences to use.\r\n   * @param {AbsencePeriod} absence - The leave object to check.\r\n   */\r\n    public isAbsenceSelectedToUse(absence: AbsencePeriod) {\r\n      return this.absencesToUse?.some((item) => item.id === absence.id);\r\n    }\r\n\r\n  /**\r\n   * Determines the style for a given leave based on whether it should be disabled or not.\r\n   * @param {AnnualLeave} leave - The leave object to check.\r\n   */\r\n  public getDisabledStyle(leave: AbsencePeriod) {\r\n    if (this.isSelectedToBePaid(leave)) {\r\n      return {\r\n        \"background-color\": \"lightgrey\",\r\n        \"opacity\": \"0.5\"\r\n      };\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Determines the style for a given absence based on whether it should be disabled or not.\r\n   * @param {AnnualLeave} absence - The absences object to check.\r\n   */\r\n    public getAbsenceDisabledStyle(absence: AbsencePeriod) {\r\n      if (this.isAbsenceSelectedToUse(absence)) {\r\n        return {\r\n          \"background-color\": \"lightgrey\",\r\n          \"opacity\": \"0.5\"\r\n        };\r\n      }\r\n    }\r\n\r\n  /** Returns daysCount sum of annualLeavestoBePaid/bonusPeriodstoBePaid depending on type parameter*/\r\n  public getAccrualRemaningsToBePaid(type: \"holidayPay\" | \"holidayBonus\") {\r\n    return type === \"holidayPay\" ? Arrays.sum(this.annualLeavestoBePaid, (x) => x.period.daysCount) || 0 : Arrays.sum(this.annualLeavestoBePaid, (x) => x.bonusDaysCount) || 0;\r\n  }\r\n\r\n  /**\r\n   * Shows the edit dialog.\r\n   * @param item AnnualLeave to edit.\r\n   */\r\n  public showEditDialog(item: AbsencePeriod) {\r\n    if (!item) {\r\n      throw new Error(\"showEditDialog called without a parameter.\");\r\n    }\r\n\r\n    const logic =  {\r\n      /** Updates the workdays count */\r\n      updatePeriodDays: (current: AbsencePeriod) => {\r\n        if (current.period.start > current.period.end) {\r\n          current.period.end = current.period.start;\r\n        }\r\n        if (current.period.start && current.period.end) {\r\n          if (current.period.days) {\r\n            current.period.days = Dates.getVacationDays(current.period.start, current.period.end);\r\n            current.period.daysCount = current.period.days.length;\r\n            if (this.worktime.holidaySpec.bonusMethod !== HolidayBonusPaymentMethod.None) {\r\n              current.bonusDaysCount = current.period.days.length;\r\n            }\r\n          } else {\r\n            current.period.daysCount = Dates.getVacationDays(current.period.start, current.period.end).length;\r\n            if (this.worktime.holidaySpec.bonusMethod !== HolidayBonusPaymentMethod.None) {\r\n              current.bonusDaysCount = current.period.daysCount;\r\n            }\r\n          }\r\n        }\r\n      },\r\n\r\n      /** Sets the days array in period to enable days selection UI. */\r\n      setDaysSelection: (period: AbsencePeriod) => {\r\n        period.period.days = Dates.getVacationDays(period.period.start, period.period.end);\r\n        period.period.daysCount = period.period.days.length;\r\n        if (this.worktime.holidaySpec.bonusMethod !== HolidayBonusPaymentMethod.None) {\r\n          period.bonusDaysCount = period.period.days.length;\r\n        }\r\n      },\r\n\r\n    };\r\n    this.uiHelpers.openEditDialog(\"salaxy-components/worker/holidays/HolidayYearHolidaysEditDialog.html\", item, logic).then((result) => {\r\n       if (result.action === \"delete\" || result.action === \"delete-no-save\") {\r\n        this.annualLeavestoBePaid.splice(this.annualLeavestoBePaid.indexOf(item), 1);\r\n      } else {\r\n        // No changes, cancel\r\n      }\r\n      });\r\n  }\r\n\r\n  private newGuid(): string {\r\n    let dt = new Date().getTime();\r\n    const uuid = \"xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx\".replace(/[xy]/g, (c) => {\r\n      /* eslint-disable-next-line no-bitwise */\r\n      const r = (dt + Math.random() * 16) % 16 | 0;\r\n      dt = Math.floor(dt / 16);\r\n      /* eslint-disable-next-line no-bitwise */\r\n      return (c === \"x\" ? r : (r & 0x3 | 0x8)).toString(16);\r\n    });\r\n    return uuid;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Calculations, Ajax, Calculation, DocumentFlowItem, AccountingData, Reports, CalculationResultLogic, DateRange, InputEnumOption, Translations, Language, kevaEmploymentRegCodes } from \"@salaxy/core\";\r\nimport { InvoicesService, ReportsService, SessionService, UiCrudHelpers, UiHelpers } from \"../../services\";\r\nimport { Calculator2019Controller } from \"./Calculator2019Controller\";\r\n\r\n/**\r\n * Controller for repairing paid calculations.\r\n */\r\nexport class CalcRepairController extends Calculator2019Controller {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   */\r\n  public static $inject = [\r\n    \"Calculations\",\r\n    \"UiHelpers\",\r\n    \"UiCrudHelpers\",\r\n    \"$location\",\r\n    \"$routeParams\",\r\n    \"SessionService\",\r\n    \"ReportsService\",\r\n    \"InvoicesService\",\r\n    \"AjaxNg1\",\r\n    \"Reports\"\r\n  ];\r\n\r\n  /** Data reader for the accounting diffa data. */\r\n  public accountingDiffDataReader = {\r\n    /** Function to read data into given array */\r\n    read: (target: string, ruleSet: string, arr: AccountingData[]): Promise<void> => {\r\n      if (this.accountingDiffData) {\r\n        arr.push(this.accountingDiffData);\r\n        return Promise.resolve();\r\n      } else {\r\n        return Promise.resolve();\r\n      }\r\n    },\r\n    /** Optional label for data export */\r\n    exportLabel: null,\r\n    /** Indicates if the export is not possible */\r\n    disabled: () => !this.accountingDiffData,\r\n    /* Indicates if row is expandable */\r\n    showExpand: true,\r\n    /* Indicates if rows exists*/\r\n    hasRows: () => !this.accountingDiffData?.ledgerAccounts\r\n  };\r\n\r\n  public excludeDiffPaths = [\"workflow\", \"id\", \"createdAt\", \"updatedAt\", \"isReadOnly\", \"result.totals\", \"result.irRows\", \"result.employerCalc\", \"result.workerCalc\", \"result.rows\", \"result.validation\"];\r\n\r\n  /** Calc reports type */\r\n  public shared = {\r\n    reportType: \"salarySlip\"\r\n  };\r\n\r\n  private _loading = {\r\n    accountingDiffData: false,\r\n  };\r\n\r\n  private _pendingChanges = {\r\n    accountingDiffData: false,\r\n    accountingDiffTargetId: \"default\"\r\n  };\r\n\r\n  private _accountingDiffData: AccountingData;\r\n\r\n  private _diffCalc: Calculation = {};\r\n\r\n  private _latestCurrent: Calculation;\r\n\r\n  private _latestBase: Calculation;\r\n\r\n  private _base: Calculation;\r\n  private _documentFlow: DocumentFlowItem;\r\n  private _dateRange: DateRange;\r\n\r\n  private _baseCfa: any = { net: 0, tax:0, pension:0, service:0, fee:0, total:0 };\r\n\r\n  private _currentCfa: any = { net: 0, tax:0, pension:0, service:0, fee:0, total:0 };\r\n\r\n  /**\r\n   * Creates a new CalculationsProController\r\n   */\r\n  constructor(\r\n    private repairApi: Calculations,\r\n    private uiHelpersApi: UiHelpers,\r\n    uiCrudHelpers: UiCrudHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    sessionService: SessionService,\r\n    reportsService: ReportsService,\r\n    invoicesService: InvoicesService,\r\n    ajax: Ajax,\r\n    private reportsApi: Reports,\r\n  ) {\r\n    super(repairApi, uiHelpersApi, uiCrudHelpers, $location, $routeParams, sessionService, reportsService, invoicesService, ajax);\r\n  }\r\n\r\n  /** Initialize */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /**\r\n   * Finalize the repair and replace the original version with the new one.\r\n   */\r\n  public commitRepair() {\r\n    return this.uiHelpers.showConfirm( \"Korvaa alkuperäinen laskelma?\",\r\n      \"Tämä korjattu versio laskelmasta korvaa alkuperäisen laskelman. \" +\r\n      \"Samalla päivitetään tiedot tulorekisteri-ilmoituksiin ja laskuihin. \" +\r\n      \"Korjausta ei voi perua, mutta voit aina korjata viimeisimmän version laskelmasta.\",\r\n       \"Korvaa alkuperäinen\", \"Peruuta\").then((result) => {\r\n        if (result) {\r\n          const loading = this.uiHelpersApi.showLoading(\"SALAXY.UI_Terms.wait\");\r\n          return this.repairApi.commitRepair(this.current).then(() => {\r\n            loading.dismiss();\r\n            this.uiHelpers.showAlert(\"Laskelma korvattu onnistuneesti.\");\r\n            this.$location.path(\"/calc/repairs\");\r\n          });\r\n        }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Update repair\r\n   */\r\n  public saveRepair(): Promise<Calculation> {\r\n    return this.repairApi.saveRepair(this.current).then( (saved) => {\r\n      this.setCurrent(saved);\r\n      return this.current;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Recalculate repair\r\n   */\r\n    public recalculateRepair(): Promise<Calculation> {\r\n      return this.repairApi.recalculateRepair(this.current).then( (saved) => {\r\n        this.setCurrent(saved);\r\n        return this.current;\r\n      });\r\n    }\r\n\r\n  /**\r\n   * Select taxcard for the repaired calc.\r\n   */\r\n  public selectTaxcard() {\r\n    return this.uiHelpers.openEditDialog(\r\n      \"salaxy-components/modals/calc/TaxcardSelect.html\",\r\n      [],\r\n      {\r\n        title: \"SALAXY.UI_Terms.select\",\r\n        options:  {$filter: \"data/employmentId eq '\" + this.current.worker.employmentId + \"' and (startAt le \" + this.current.workflow.salaryDate + \"Z and endAt ge \" + this.current.workflow.salaryDate + \"Z)\"},\r\n        okButtonText: \"SALAXY.UI_Terms.ok\",\r\n        cancelButtonText: \"SALAXY.UI_Terms.cancel\",\r\n      }).then((result) => {\r\n        if (result.action === \"ok\" && result.item.length > 0) {\r\n          const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n          this.current.worker.tax.taxcardId = result.item[0].id;\r\n          return this.recalculate().then(() => {\r\n              loading.dismiss();\r\n          });\r\n        }\r\n        else\r\n        {\r\n          return;\r\n        }\r\n      });\r\n  }\r\n\r\n  /** Original calculation */\r\n  public get base() {\r\n    if (!this._base) {\r\n      if ((this.current?.workflow as any)?.originalId) {\r\n        this._base = {};\r\n        this.repairApi.getSingle((this.current?.workflow as any)?.originalId).then((calc) => {\r\n          angular.copy(calc, this._base);\r\n        });\r\n      }\r\n    }\r\n    return this._base?.info ? this._base : null;\r\n  }\r\n\r\n  /** Document flow for the current calculation */\r\n  public get documentFlow() {\r\n    if (!this._documentFlow) {\r\n      if (this.base?.id) {\r\n        this._documentFlow = { item: null, children: null };\r\n        this.repairApi.getDocumentFlow(this.base.id).then((data) => {\r\n          angular.copy(data, this._documentFlow);\r\n        });\r\n      }\r\n    }\r\n    return this._documentFlow;\r\n  }\r\n\r\n  /** Calculation total result diff between original and current calculation. */\r\n  public get diffCalc() {\r\n    this.checkCalculationChange();\r\n    return this._diffCalc;\r\n  }\r\n\r\n  /** Accounting data diff between original and current calculation. */\r\n  public get accountingDiffData() {\r\n    this.checkCalculationChange();\r\n    this.loadAccountingDiffData();\r\n    return this._accountingDiffData;\r\n  }\r\n\r\n  /** Change accounting data target */\r\n  public onTargetChange(targetId: string = \"default\") {\r\n    this._pendingChanges.accountingDiffData = true;\r\n    this._pendingChanges.accountingDiffTargetId = targetId;\r\n    this.loadAccountingDiffData();\r\n  }\r\n\r\n  /** Returns cfa data for base. */\r\n  public get baseCfa() {\r\n    if (this.base) {\r\n      this.calculateCfa(this.base, this._baseCfa);\r\n    }\r\n    return this._baseCfa;\r\n  }\r\n\r\n    /** Returns cfa data for current. */\r\n  public get currentCfa() {\r\n    if (this.current) {\r\n      this.calculateCfa(this.current, this._currentCfa);\r\n    }\r\n    return this._currentCfa;\r\n  }\r\n\r\n  /** Getter and setter for Calculation daterange in compatible format for new DateRange component. */\r\n  public get dateRange(): DateRange {\r\n    if (!this.current) {\r\n      return null;\r\n    }\r\n    if (!this._dateRange) {\r\n      this._dateRange = {\r\n        start: this.current.info.workStartDate,\r\n        end: this.current.info.workEndDate,\r\n        daysCount: this.current.framework.numberOfDays,\r\n      };\r\n    }\r\n    return this._dateRange;\r\n  }\r\n  public set dateRange(value: DateRange) {\r\n    this._dateRange = value;\r\n  }\r\n\r\n  /**\r\n   * Called when the date range changes.\r\n   */\r\n  public dateRangeChange() {\r\n    if (!this.dateRange || !this.current) {\r\n      return;\r\n    }\r\n    this.current.info.workStartDate = this.dateRange.start;\r\n    this.current.info.workEndDate = this.dateRange.end;\r\n    this.current.framework.numberOfDays = this.dateRange.daysCount;\r\n  }\r\n\r\n  /**\r\n   * Returns valid employment reg codes for the selected pensions company.\r\n   * @returns Options for the employment reg codes.\r\n   */\r\n  public getEmploymentRegCodeOptions(): Array<InputEnumOption> {\r\n    return this.uiHelpers.cache(this, \"employmentRegCodes\",\r\n    () => kevaEmploymentRegCodes.filter((x) => x.pensionCompany === this.current.result.responsibilities.pensionCompany).map((regCode) =>\r\n      ({ value: regCode.code, text: Translations.getLanguage() === Language.Sv ? regCode.labelSv : regCode.labelFi })),\r\n    () => this.current.result.responsibilities.pensionCompany);\r\n  }\r\n\r\n  /** Load accounting data and calculate diff. */\r\n  private loadAccountingDiffData() {\r\n    if (this._pendingChanges.accountingDiffData) {\r\n      if (!this._loading.accountingDiffData) {\r\n        this._loading.accountingDiffData = true;\r\n        const load = () => {\r\n          this._pendingChanges.accountingDiffData = false;\r\n          const promises = [this.base, this.current].map((x) => this.reportsApi.getAccountingDataForCalculations([x], this._pendingChanges.accountingDiffTargetId, null));\r\n          return Promise.all(promises).then((accountingReports) => {\r\n            if (accountingReports && accountingReports.length == 2) {\r\n              this._accountingDiffData = this._accountingDiffData ?? {};\r\n              angular.copy(this.diffAccountingData(accountingReports[0], accountingReports[1]), this._accountingDiffData);\r\n            }\r\n            return this._accountingDiffData;\r\n          });\r\n        };\r\n\r\n        load().then(() => {\r\n          if (this._pendingChanges.accountingDiffData) {\r\n            load();\r\n          }\r\n          else {\r\n            this._loading.accountingDiffData = false;\r\n          }\r\n        });\r\n      }\r\n    }\r\n  }\r\n\r\n  private diffAccountingData(originalAccountingData: AccountingData, modifiedAccountingData: AccountingData): AccountingData {\r\n    // Leave only top level.\r\n    originalAccountingData.ledgerAccounts.forEach((x) => x.entries = []);\r\n    originalAccountingData.summary = {};\r\n    modifiedAccountingData.ledgerAccounts.forEach((x) => x.entries = []);\r\n    modifiedAccountingData.summary = {};\r\n    const result = modifiedAccountingData;\r\n\r\n    originalAccountingData.ledgerAccounts.forEach((orig) => {\r\n      const modified = result.ledgerAccounts.find((x) => x.accountNumber === orig.accountNumber && x.accountGrouping == orig.accountGrouping);\r\n      if (modified) {\r\n        (modified as any).saldo = modified.saldo - orig.saldo;\r\n      } else {\r\n        const removedAccount = angular.copy(orig);\r\n        (removedAccount as any).saldo = 0.0 - orig.saldo;\r\n        result.ledgerAccounts.push(removedAccount);\r\n      }\r\n    });\r\n    result.ledgerAccounts.forEach((x) => x.entries =\r\n      [\r\n        {\r\n          id: null,\r\n          entryDate: null,\r\n          description: \"Ero\",\r\n          isDebit: x.saldo >= 0,\r\n          amount: x.saldo >= 0 ? x.saldo : -1.0 * x.saldo,\r\n          vatPercent: null,\r\n          accountNumber: x.accountNumber,\r\n          accountName: x.accountName,\r\n          accountGrouping: x.accountGrouping,\r\n          dimension: {},\r\n        }\r\n      ]);\r\n    return result;\r\n  }\r\n\r\n\r\n  private checkCalculationChange() {\r\n    if (this.base && this.current && (!angular.equals(this.current, this._latestCurrent) || !angular.equals(this.base, this._latestBase))) {\r\n      this._latestCurrent = angular.copy(this.current);\r\n      this._latestBase = angular.copy(this.base);\r\n\r\n      const diff = angular.copy(this.base);\r\n      diff.result = CalculationResultLogic.diff(this.base.result, this.current.result);\r\n      angular.copy(diff, this._diffCalc);\r\n      this._pendingChanges.accountingDiffData = true;\r\n    }\r\n  }\r\n\r\n  private calculateCfa(calc: Calculation, target: any) {\r\n    target.net = calc.result.workerCalc.totalWorkerPayment - calc.result.employerCalc.deductionWorkerSelfPayment;\r\n    target.pension = calc.result.totals.pension - calc.result.employerCalc.deductionPensionSelfPayment;\r\n    target.tax = calc.result.workerCalc.tax + calc.result.employerCalc.socialSecurity + calc.result.workerCalc.taxAtSource +  calc.result.workerCalc.socialSecurity - calc.result.employerCalc.deductionTaxAndSocialSecuritySelfPayment;\r\n    target.service = calc.result.employerCalc.service;\r\n    target.fee = calc.result.employerCalc.palkkaus;\r\n    target.total = target.net + target.pension + target.tax + target.service + target.fee;\r\n  }\r\n\r\n}\r\n","/*! xlsx.js (C) 2013-present SheetJS -- http://sheetjs.com */\n/* vim: set ts=2: */\n/*exported XLSX */\n/*global process:false, Buffer:false, ArrayBuffer:false, DataView:false, Deno:false */\nvar XLSX = {};\nXLSX.version = '0.18.5';\nvar current_codepage = 1200, current_ansi = 1252;\n\nvar VALID_ANSI = [ 874, 932, 936, 949, 950, 1250, 1251, 1252, 1253, 1254, 1255, 1256, 1257, 1258, 10000 ];\n/* ECMA-376 Part I 18.4.1 charset to codepage mapping */\nvar CS2CP = ({\n\t/*::[*/0/*::]*/:    1252, /* ANSI */\n\t/*::[*/1/*::]*/:   65001, /* DEFAULT */\n\t/*::[*/2/*::]*/:   65001, /* SYMBOL */\n\t/*::[*/77/*::]*/:  10000, /* MAC */\n\t/*::[*/128/*::]*/:   932, /* SHIFTJIS */\n\t/*::[*/129/*::]*/:   949, /* HANGUL */\n\t/*::[*/130/*::]*/:  1361, /* JOHAB */\n\t/*::[*/134/*::]*/:   936, /* GB2312 */\n\t/*::[*/136/*::]*/:   950, /* CHINESEBIG5 */\n\t/*::[*/161/*::]*/:  1253, /* GREEK */\n\t/*::[*/162/*::]*/:  1254, /* TURKISH */\n\t/*::[*/163/*::]*/:  1258, /* VIETNAMESE */\n\t/*::[*/177/*::]*/:  1255, /* HEBREW */\n\t/*::[*/178/*::]*/:  1256, /* ARABIC */\n\t/*::[*/186/*::]*/:  1257, /* BALTIC */\n\t/*::[*/204/*::]*/:  1251, /* RUSSIAN */\n\t/*::[*/222/*::]*/:   874, /* THAI */\n\t/*::[*/238/*::]*/:  1250, /* EASTEUROPE */\n\t/*::[*/255/*::]*/:  1252, /* OEM */\n\t/*::[*/69/*::]*/:   6969  /* MISC */\n}/*:any*/);\n\nvar set_ansi = function(cp/*:number*/) { if(VALID_ANSI.indexOf(cp) == -1) return; current_ansi = CS2CP[0] = cp; };\nfunction reset_ansi() { set_ansi(1252); }\n\nvar set_cp = function(cp/*:number*/) { current_codepage = cp; set_ansi(cp); };\nfunction reset_cp() { set_cp(1200); reset_ansi(); }\n\nfunction char_codes(data/*:string*/)/*:Array<number>*/ { var o/*:Array<number>*/ = []; for(var i = 0, len = data.length; i < len; ++i) o[i] = data.charCodeAt(i); return o; }\n\nfunction utf16leread(data/*:string*/)/*:string*/ {\n\tvar o/*:Array<string>*/ = [];\n\tfor(var i = 0; i < (data.length>>1); ++i) o[i] = String.fromCharCode(data.charCodeAt(2*i) + (data.charCodeAt(2*i+1)<<8));\n\treturn o.join(\"\");\n}\nfunction utf16beread(data/*:string*/)/*:string*/ {\n\tvar o/*:Array<string>*/ = [];\n\tfor(var i = 0; i < (data.length>>1); ++i) o[i] = String.fromCharCode(data.charCodeAt(2*i+1) + (data.charCodeAt(2*i)<<8));\n\treturn o.join(\"\");\n}\n\nvar debom = function(data/*:string*/)/*:string*/ {\n\tvar c1 = data.charCodeAt(0), c2 = data.charCodeAt(1);\n\tif(c1 == 0xFF && c2 == 0xFE) return utf16leread(data.slice(2));\n\tif(c1 == 0xFE && c2 == 0xFF) return utf16beread(data.slice(2));\n\tif(c1 == 0xFEFF) return data.slice(1);\n\treturn data;\n};\n\nvar _getchar = function _gc1(x/*:number*/)/*:string*/ { return String.fromCharCode(x); };\nvar _getansi = function _ga1(x/*:number*/)/*:string*/ { return String.fromCharCode(x); };\n\nvar $cptable;\nfunction set_cptable(cptable) {\n\t$cptable = cptable;\n\tset_cp = function(cp/*:number*/) { current_codepage = cp; set_ansi(cp); };\n\tdebom = function(data/*:string*/) {\n\t\tif(data.charCodeAt(0) === 0xFF && data.charCodeAt(1) === 0xFE) { return $cptable.utils.decode(1200, char_codes(data.slice(2))); }\n\t\treturn data;\n\t};\n\t_getchar = function _gc2(x/*:number*/)/*:string*/ {\n\t\tif(current_codepage === 1200) return String.fromCharCode(x);\n\t\treturn $cptable.utils.decode(current_codepage, [x&255,x>>8])[0];\n\t};\n\t_getansi = function _ga2(x/*:number*/)/*:string*/ {\n\t\treturn $cptable.utils.decode(current_ansi, [x])[0];\n\t};\n\tcpdoit();\n}\nexport { set_cptable };\nvar DENSE = null;\nvar DIF_XL = true;\nvar Base64_map = \"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=\";\nfunction Base64_encode(input) {\n  var o = \"\";\n  var c1 = 0, c2 = 0, c3 = 0, e1 = 0, e2 = 0, e3 = 0, e4 = 0;\n  for (var i = 0; i < input.length; ) {\n    c1 = input.charCodeAt(i++);\n    e1 = c1 >> 2;\n    c2 = input.charCodeAt(i++);\n    e2 = (c1 & 3) << 4 | c2 >> 4;\n    c3 = input.charCodeAt(i++);\n    e3 = (c2 & 15) << 2 | c3 >> 6;\n    e4 = c3 & 63;\n    if (isNaN(c2)) {\n      e3 = e4 = 64;\n    } else if (isNaN(c3)) {\n      e4 = 64;\n    }\n    o += Base64_map.charAt(e1) + Base64_map.charAt(e2) + Base64_map.charAt(e3) + Base64_map.charAt(e4);\n  }\n  return o;\n}\nfunction Base64_decode(input) {\n  var o = \"\";\n  var c1 = 0, c2 = 0, c3 = 0, e1 = 0, e2 = 0, e3 = 0, e4 = 0;\n  input = input.replace(/[^\\w\\+\\/\\=]/g, \"\");\n  for (var i = 0; i < input.length; ) {\n    e1 = Base64_map.indexOf(input.charAt(i++));\n    e2 = Base64_map.indexOf(input.charAt(i++));\n    c1 = e1 << 2 | e2 >> 4;\n    o += String.fromCharCode(c1);\n    e3 = Base64_map.indexOf(input.charAt(i++));\n    c2 = (e2 & 15) << 4 | e3 >> 2;\n    if (e3 !== 64) {\n      o += String.fromCharCode(c2);\n    }\n    e4 = Base64_map.indexOf(input.charAt(i++));\n    c3 = (e3 & 3) << 6 | e4;\n    if (e4 !== 64) {\n      o += String.fromCharCode(c3);\n    }\n  }\n  return o;\n}\nvar has_buf = /*#__PURE__*/(function() { return typeof Buffer !== 'undefined' && typeof process !== 'undefined' && typeof process.versions !== 'undefined' && !!process.versions.node; })();\n\nvar Buffer_from = /*#__PURE__*/(function() {\n\tif(typeof Buffer !== 'undefined') {\n\t\tvar nbfs = !Buffer.from;\n\t\tif(!nbfs) try { Buffer.from(\"foo\", \"utf8\"); } catch(e) { nbfs = true; }\n\t\treturn nbfs ? function(buf, enc) { return (enc) ? new Buffer(buf, enc) : new Buffer(buf); } : Buffer.from.bind(Buffer);\n\t}\n\treturn function() {};\n})();\n\n\nfunction new_raw_buf(len/*:number*/) {\n\t/* jshint -W056 */\n\tif(has_buf) return Buffer.alloc ? Buffer.alloc(len) : new Buffer(len);\n\treturn typeof Uint8Array != \"undefined\" ? new Uint8Array(len) : new Array(len);\n\t/* jshint +W056 */\n}\n\nfunction new_unsafe_buf(len/*:number*/) {\n\t/* jshint -W056 */\n\tif(has_buf) return Buffer.allocUnsafe ? Buffer.allocUnsafe(len) : new Buffer(len);\n\treturn typeof Uint8Array != \"undefined\" ? new Uint8Array(len) : new Array(len);\n\t/* jshint +W056 */\n}\n\nvar s2a = function s2a(s/*:string*/)/*:any*/ {\n\tif(has_buf) return Buffer_from(s, \"binary\");\n\treturn s.split(\"\").map(function(x/*:string*/)/*:number*/{ return x.charCodeAt(0) & 0xff; });\n};\n\nfunction s2ab(s/*:string*/)/*:any*/ {\n\tif(typeof ArrayBuffer === 'undefined') return s2a(s);\n\tvar buf = new ArrayBuffer(s.length), view = new Uint8Array(buf);\n\tfor (var i=0; i!=s.length; ++i) view[i] = s.charCodeAt(i) & 0xFF;\n\treturn buf;\n}\n\nfunction a2s(data/*:any*/)/*:string*/ {\n\tif(Array.isArray(data)) return data.map(function(c) { return String.fromCharCode(c); }).join(\"\");\n\tvar o/*:Array<string>*/ = []; for(var i = 0; i < data.length; ++i) o[i] = String.fromCharCode(data[i]); return o.join(\"\");\n}\n\nfunction a2u(data/*:Array<number>*/)/*:Uint8Array*/ {\n\tif(typeof Uint8Array === 'undefined') throw new Error(\"Unsupported\");\n\treturn new Uint8Array(data);\n}\n\nfunction ab2a(data/*:ArrayBuffer|Uint8Array*/)/*:Array<number>*/ {\n\tif(typeof ArrayBuffer == 'undefined') throw new Error(\"Unsupported\");\n\tif(data instanceof ArrayBuffer) return ab2a(new Uint8Array(data));\n\t/*:: if(data instanceof ArrayBuffer) throw new Error(\"unreachable\"); */\n\tvar o = new Array(data.length);\n\tfor(var i = 0; i < data.length; ++i) o[i] = data[i];\n\treturn o;\n}\n\nvar bconcat = has_buf ? function(bufs) { return Buffer.concat(bufs.map(function(buf) { return Buffer.isBuffer(buf) ? buf : Buffer_from(buf); })); } : function(bufs) {\n\tif(typeof Uint8Array !== \"undefined\") {\n\t\tvar i = 0, maxlen = 0;\n\t\tfor(i = 0; i < bufs.length; ++i) maxlen += bufs[i].length;\n\t\tvar o = new Uint8Array(maxlen);\n\t\tvar len = 0;\n\t\tfor(i = 0, maxlen = 0; i < bufs.length; maxlen += len, ++i) {\n\t\t\tlen = bufs[i].length;\n\t\t\tif(bufs[i] instanceof Uint8Array) o.set(bufs[i], maxlen);\n\t\t\telse if(typeof bufs[i] == \"string\") { throw \"wtf\"; }\n\t\t\telse o.set(new Uint8Array(bufs[i]), maxlen);\n\t\t}\n\t\treturn o;\n\t}\n\treturn [].concat.apply([], bufs.map(function(buf) { return Array.isArray(buf) ? buf : [].slice.call(buf); }));\n};\n\nfunction utf8decode(content/*:string*/) {\n\tvar out = [], widx = 0, L = content.length + 250;\n\tvar o = new_raw_buf(content.length + 255);\n\tfor(var ridx = 0; ridx < content.length; ++ridx) {\n\t\tvar c = content.charCodeAt(ridx);\n\t\tif(c < 0x80) o[widx++] = c;\n\t\telse if(c < 0x800) {\n\t\t\to[widx++] = (192|((c>>6)&31));\n\t\t\to[widx++] = (128|(c&63));\n\t\t} else if(c >= 0xD800 && c < 0xE000) {\n\t\t\tc = (c&1023)+64;\n\t\t\tvar d = content.charCodeAt(++ridx)&1023;\n\t\t\to[widx++] = (240|((c>>8)&7));\n\t\t\to[widx++] = (128|((c>>2)&63));\n\t\t\to[widx++] = (128|((d>>6)&15)|((c&3)<<4));\n\t\t\to[widx++] = (128|(d&63));\n\t\t} else {\n\t\t\to[widx++] = (224|((c>>12)&15));\n\t\t\to[widx++] = (128|((c>>6)&63));\n\t\t\to[widx++] = (128|(c&63));\n\t\t}\n\t\tif(widx > L) {\n\t\t\tout.push(o.slice(0, widx));\n\t\t\twidx = 0;\n\t\t\to = new_raw_buf(65535);\n\t\t\tL = 65530;\n\t\t}\n\t}\n\tout.push(o.slice(0, widx));\n\treturn bconcat(out);\n}\n\nvar chr0 = /\\u0000/g, chr1 = /[\\u0001-\\u0006]/g;\n/*::\ndeclare type Block = any;\ndeclare type BufArray = {\n\tnewblk(sz:number):Block;\n\tnext(sz:number):Block;\n\tend():any;\n\tpush(buf:Block):void;\n};\n\ntype RecordHopperCB = {(d:any, Rn:string, RT:number):?boolean;};\n\ntype EvertType = {[string]:string};\ntype EvertNumType = {[string]:number};\ntype EvertArrType = {[string]:Array<string>};\n\ntype StringConv = {(string):string};\n\n*/\n/* ssf.js (C) 2013-present SheetJS -- http://sheetjs.com */\n/*jshint -W041 */\nfunction _strrev(x/*:string*/)/*:string*/ { var o = \"\", i = x.length-1; while(i>=0) o += x.charAt(i--); return o; }\nfunction pad0(v/*:any*/,d/*:number*/)/*:string*/{var t=\"\"+v; return t.length>=d?t:fill('0',d-t.length)+t;}\nfunction pad_(v/*:any*/,d/*:number*/)/*:string*/{var t=\"\"+v;return t.length>=d?t:fill(' ',d-t.length)+t;}\nfunction rpad_(v/*:any*/,d/*:number*/)/*:string*/{var t=\"\"+v; return t.length>=d?t:t+fill(' ',d-t.length);}\nfunction pad0r1(v/*:any*/,d/*:number*/)/*:string*/{var t=\"\"+Math.round(v); return t.length>=d?t:fill('0',d-t.length)+t;}\nfunction pad0r2(v/*:any*/,d/*:number*/)/*:string*/{var t=\"\"+v; return t.length>=d?t:fill('0',d-t.length)+t;}\nvar p2_32 = /*#__PURE__*/Math.pow(2,32);\nfunction pad0r(v/*:any*/,d/*:number*/)/*:string*/{if(v>p2_32||v<-p2_32) return pad0r1(v,d); var i = Math.round(v); return pad0r2(i,d); }\n/* yes, in 2022 this is still faster than string compare */\nfunction SSF_isgeneral(s/*:string*/, i/*:?number*/)/*:boolean*/ { i = i || 0; return s.length >= 7 + i && (s.charCodeAt(i)|32) === 103 && (s.charCodeAt(i+1)|32) === 101 && (s.charCodeAt(i+2)|32) === 110 && (s.charCodeAt(i+3)|32) === 101 && (s.charCodeAt(i+4)|32) === 114 && (s.charCodeAt(i+5)|32) === 97 && (s.charCodeAt(i+6)|32) === 108; }\nvar days/*:Array<Array<string> >*/ = [\n\t['Sun', 'Sunday'],\n\t['Mon', 'Monday'],\n\t['Tue', 'Tuesday'],\n\t['Wed', 'Wednesday'],\n\t['Thu', 'Thursday'],\n\t['Fri', 'Friday'],\n\t['Sat', 'Saturday']\n];\nvar months/*:Array<Array<string> >*/ = [\n\t['J', 'Jan', 'January'],\n\t['F', 'Feb', 'February'],\n\t['M', 'Mar', 'March'],\n\t['A', 'Apr', 'April'],\n\t['M', 'May', 'May'],\n\t['J', 'Jun', 'June'],\n\t['J', 'Jul', 'July'],\n\t['A', 'Aug', 'August'],\n\t['S', 'Sep', 'September'],\n\t['O', 'Oct', 'October'],\n\t['N', 'Nov', 'November'],\n\t['D', 'Dec', 'December']\n];\nfunction SSF_init_table(t/*:any*/) {\n\tif(!t) t = {};\n\tt[0]=  'General';\n\tt[1]=  '0';\n\tt[2]=  '0.00';\n\tt[3]=  '#,##0';\n\tt[4]=  '#,##0.00';\n\tt[9]=  '0%';\n\tt[10]= '0.00%';\n\tt[11]= '0.00E+00';\n\tt[12]= '# ?/?';\n\tt[13]= '# ??/??';\n\tt[14]= 'm/d/yy';\n\tt[15]= 'd-mmm-yy';\n\tt[16]= 'd-mmm';\n\tt[17]= 'mmm-yy';\n\tt[18]= 'h:mm AM/PM';\n\tt[19]= 'h:mm:ss AM/PM';\n\tt[20]= 'h:mm';\n\tt[21]= 'h:mm:ss';\n\tt[22]= 'm/d/yy h:mm';\n\tt[37]= '#,##0 ;(#,##0)';\n\tt[38]= '#,##0 ;[Red](#,##0)';\n\tt[39]= '#,##0.00;(#,##0.00)';\n\tt[40]= '#,##0.00;[Red](#,##0.00)';\n\tt[45]= 'mm:ss';\n\tt[46]= '[h]:mm:ss';\n\tt[47]= 'mmss.0';\n\tt[48]= '##0.0E+0';\n\tt[49]= '@';\n\tt[56]= '\"上午/下午 \"hh\"時\"mm\"分\"ss\"秒 \"';\n\treturn t;\n}\n/* repeated to satiate webpack */\nvar table_fmt = {\n\t0:  'General',\n\t1:  '0',\n\t2:  '0.00',\n\t3:  '#,##0',\n\t4:  '#,##0.00',\n\t9:  '0%',\n\t10: '0.00%',\n\t11: '0.00E+00',\n\t12: '# ?/?',\n\t13: '# ??/??',\n\t14: 'm/d/yy',\n\t15: 'd-mmm-yy',\n\t16: 'd-mmm',\n\t17: 'mmm-yy',\n\t18: 'h:mm AM/PM',\n\t19: 'h:mm:ss AM/PM',\n\t20: 'h:mm',\n\t21: 'h:mm:ss',\n\t22: 'm/d/yy h:mm',\n\t37: '#,##0 ;(#,##0)',\n\t38: '#,##0 ;[Red](#,##0)',\n\t39: '#,##0.00;(#,##0.00)',\n\t40: '#,##0.00;[Red](#,##0.00)',\n\t45: 'mm:ss',\n\t46: '[h]:mm:ss',\n\t47: 'mmss.0',\n\t48: '##0.0E+0',\n\t49: '@',\n\t56: '\"上午/下午 \"hh\"時\"mm\"分\"ss\"秒 \"'\n};\n\n/* Defaults determined by systematically testing in Excel 2019 */\n\n/* These formats appear to default to other formats in the table */\nvar SSF_default_map = {\n\t5:  37, 6:  38, 7:  39, 8:  40,         //  5 -> 37 ...  8 -> 40\n\n\t23:  0, 24:  0, 25:  0, 26:  0,         // 23 ->  0 ... 26 ->  0\n\n\t27: 14, 28: 14, 29: 14, 30: 14, 31: 14, // 27 -> 14 ... 31 -> 14\n\n\t50: 14, 51: 14, 52: 14, 53: 14, 54: 14, // 50 -> 14 ... 58 -> 14\n\t55: 14, 56: 14, 57: 14, 58: 14,\n\t59:  1, 60:  2, 61:  3, 62:  4,         // 59 ->  1 ... 62 ->  4\n\n\t67:  9, 68: 10,                         // 67 ->  9 ... 68 -> 10\n\t69: 12, 70: 13, 71: 14,                 // 69 -> 12 ... 71 -> 14\n\t72: 14, 73: 15, 74: 16, 75: 17,         // 72 -> 14 ... 75 -> 17\n\t76: 20, 77: 21, 78: 22,                 // 76 -> 20 ... 78 -> 22\n\t79: 45, 80: 46, 81: 47,                 // 79 -> 45 ... 81 -> 47\n\t82: 0                                   // 82 ->  0 ... 65536 -> 0 (omitted)\n};\n\n\n/* These formats technically refer to Accounting formats with no equivalent */\nvar SSF_default_str = {\n\t//  5 -- Currency,   0 decimal, black negative\n\t5:  '\"$\"#,##0_);\\\\(\"$\"#,##0\\\\)',\n\t63: '\"$\"#,##0_);\\\\(\"$\"#,##0\\\\)',\n\n\t//  6 -- Currency,   0 decimal, red   negative\n\t6:  '\"$\"#,##0_);[Red]\\\\(\"$\"#,##0\\\\)',\n\t64: '\"$\"#,##0_);[Red]\\\\(\"$\"#,##0\\\\)',\n\n\t//  7 -- Currency,   2 decimal, black negative\n\t7:  '\"$\"#,##0.00_);\\\\(\"$\"#,##0.00\\\\)',\n\t65: '\"$\"#,##0.00_);\\\\(\"$\"#,##0.00\\\\)',\n\n\t//  8 -- Currency,   2 decimal, red   negative\n\t8:  '\"$\"#,##0.00_);[Red]\\\\(\"$\"#,##0.00\\\\)',\n\t66: '\"$\"#,##0.00_);[Red]\\\\(\"$\"#,##0.00\\\\)',\n\n\t// 41 -- Accounting, 0 decimal, No Symbol\n\t41: '_(* #,##0_);_(* \\\\(#,##0\\\\);_(* \"-\"_);_(@_)',\n\n\t// 42 -- Accounting, 0 decimal, $  Symbol\n\t42: '_(\"$\"* #,##0_);_(\"$\"* \\\\(#,##0\\\\);_(\"$\"* \"-\"_);_(@_)',\n\n\t// 43 -- Accounting, 2 decimal, No Symbol\n\t43: '_(* #,##0.00_);_(* \\\\(#,##0.00\\\\);_(* \"-\"??_);_(@_)',\n\n\t// 44 -- Accounting, 2 decimal, $  Symbol\n\t44: '_(\"$\"* #,##0.00_);_(\"$\"* \\\\(#,##0.00\\\\);_(\"$\"* \"-\"??_);_(@_)'\n};\n\nfunction SSF_frac(x/*:number*/, D/*:number*/, mixed/*:?boolean*/)/*:Array<number>*/ {\n\tvar sgn = x < 0 ? -1 : 1;\n\tvar B = x * sgn;\n\tvar P_2 = 0, P_1 = 1, P = 0;\n\tvar Q_2 = 1, Q_1 = 0, Q = 0;\n\tvar A = Math.floor(B);\n\twhile(Q_1 < D) {\n\t\tA = Math.floor(B);\n\t\tP = A * P_1 + P_2;\n\t\tQ = A * Q_1 + Q_2;\n\t\tif((B - A) < 0.00000005) break;\n\t\tB = 1 / (B - A);\n\t\tP_2 = P_1; P_1 = P;\n\t\tQ_2 = Q_1; Q_1 = Q;\n\t}\n\tif(Q > D) { if(Q_1 > D) { Q = Q_2; P = P_2; } else { Q = Q_1; P = P_1; } }\n\tif(!mixed) return [0, sgn * P, Q];\n\tvar q = Math.floor(sgn * P/Q);\n\treturn [q, sgn*P - q*Q, Q];\n}\nfunction SSF_parse_date_code(v/*:number*/,opts/*:?any*/,b2/*:?boolean*/) {\n\tif(v > 2958465 || v < 0) return null;\n\tvar date = (v|0), time = Math.floor(86400 * (v - date)), dow=0;\n\tvar dout=[];\n\tvar out={D:date, T:time, u:86400*(v-date)-time,y:0,m:0,d:0,H:0,M:0,S:0,q:0};\n\tif(Math.abs(out.u) < 1e-6) out.u = 0;\n\tif(opts && opts.date1904) date += 1462;\n\tif(out.u > 0.9999) {\n\t\tout.u = 0;\n\t\tif(++time == 86400) { out.T = time = 0; ++date; ++out.D; }\n\t}\n\tif(date === 60) {dout = b2 ? [1317,10,29] : [1900,2,29]; dow=3;}\n\telse if(date === 0) {dout = b2 ? [1317,8,29] : [1900,1,0]; dow=6;}\n\telse {\n\t\tif(date > 60) --date;\n\t\t/* 1 = Jan 1 1900 in Gregorian */\n\t\tvar d = new Date(1900, 0, 1);\n\t\td.setDate(d.getDate() + date - 1);\n\t\tdout = [d.getFullYear(), d.getMonth()+1,d.getDate()];\n\t\tdow = d.getDay();\n\t\tif(date < 60) dow = (dow + 6) % 7;\n\t\tif(b2) dow = SSF_fix_hijri(d, dout);\n\t}\n\tout.y = dout[0]; out.m = dout[1]; out.d = dout[2];\n\tout.S = time % 60; time = Math.floor(time / 60);\n\tout.M = time % 60; time = Math.floor(time / 60);\n\tout.H = time;\n\tout.q = dow;\n\treturn out;\n}\nvar SSFbasedate = /*#__PURE__*/new Date(1899, 11, 31, 0, 0, 0);\nvar SSFdnthresh = /*#__PURE__*/SSFbasedate.getTime();\nvar SSFbase1904 = /*#__PURE__*/new Date(1900, 2, 1, 0, 0, 0);\nfunction datenum_local(v/*:Date*/, date1904/*:?boolean*/)/*:number*/ {\n\tvar epoch = /*#__PURE__*/v.getTime();\n\tif(date1904) epoch -= 1461*24*60*60*1000;\n\telse if(v >= SSFbase1904) epoch += 24*60*60*1000;\n\treturn (epoch - (SSFdnthresh + (/*#__PURE__*/v.getTimezoneOffset() - /*#__PURE__*/SSFbasedate.getTimezoneOffset()) * 60000)) / (24 * 60 * 60 * 1000);\n}\n/* ECMA-376 18.8.30 numFmt*/\n/* Note: `toPrecision` uses standard form when prec > E and E >= -6 */\n/* exponent >= -9 and <= 9 */\nfunction SSF_strip_decimal(o/*:string*/)/*:string*/ {\n\treturn (o.indexOf(\".\") == -1) ? o : o.replace(/(?:\\.0*|(\\.\\d*[1-9])0+)$/, \"$1\");\n}\n\n/* General Exponential always shows 2 digits exp and trims the mantissa */\nfunction SSF_normalize_exp(o/*:string*/)/*:string*/ {\n\tif(o.indexOf(\"E\") == -1) return o;\n\treturn o.replace(/(?:\\.0*|(\\.\\d*[1-9])0+)[Ee]/,\"$1E\").replace(/(E[+-])(\\d)$/,\"$10$2\");\n}\n\n/* exponent >= -9 and <= 9 */\nfunction SSF_small_exp(v/*:number*/)/*:string*/ {\n\tvar w = (v<0?12:11);\n\tvar o = SSF_strip_decimal(v.toFixed(12)); if(o.length <= w) return o;\n\to = v.toPrecision(10); if(o.length <= w) return o;\n\treturn v.toExponential(5);\n}\n\n/* exponent >= 11 or <= -10 likely exponential */\nfunction SSF_large_exp(v/*:number*/)/*:string*/ {\n\tvar o = SSF_strip_decimal(v.toFixed(11));\n\treturn (o.length > (v<0?12:11) || o === \"0\" || o === \"-0\") ? v.toPrecision(6) : o;\n}\n\nfunction SSF_general_num(v/*:number*/)/*:string*/ {\n\tvar V = Math.floor(Math.log(Math.abs(v))*Math.LOG10E), o;\n\n\tif(V >= -4 && V <= -1) o = v.toPrecision(10+V);\n\telse if(Math.abs(V) <= 9) o = SSF_small_exp(v);\n\telse if(V === 10) o = v.toFixed(10).substr(0,12);\n\telse o = SSF_large_exp(v);\n\n\treturn SSF_strip_decimal(SSF_normalize_exp(o.toUpperCase()));\n}\n\n\n/*\n\t\"General\" rules:\n\t- text is passed through (\"@\")\n\t- booleans are rendered as TRUE/FALSE\n\t- \"up to 11 characters\" displayed for numbers\n\t- Default date format (code 14) used for Dates\n\n\tThe longest 32-bit integer text is \"-2147483648\", exactly 11 chars\n\tTODO: technically the display depends on the width of the cell\n*/\nfunction SSF_general(v/*:any*/, opts/*:any*/) {\n\tswitch(typeof v) {\n\t\tcase 'string': return v;\n\t\tcase 'boolean': return v ? \"TRUE\" : \"FALSE\";\n\t\tcase 'number': return (v|0) === v ? v.toString(10) : SSF_general_num(v);\n\t\tcase 'undefined': return \"\";\n\t\tcase 'object':\n\t\t\tif(v == null) return \"\";\n\t\t\tif(v instanceof Date) return SSF_format(14, datenum_local(v, opts && opts.date1904), opts);\n\t}\n\tthrow new Error(\"unsupported value in General format: \" + v);\n}\n\nfunction SSF_fix_hijri(date/*:Date*/, o/*:[number, number, number]*/) {\n  /* TODO: properly adjust y/m/d and  */\n  o[0] -= 581;\n  var dow = date.getDay();\n  if(date < 60) dow = (dow + 6) % 7;\n  return dow;\n}\n//var THAI_DIGITS = \"\\u0E50\\u0E51\\u0E52\\u0E53\\u0E54\\u0E55\\u0E56\\u0E57\\u0E58\\u0E59\".split(\"\");\nfunction SSF_write_date(type/*:number*/, fmt/*:string*/, val, ss0/*:?number*/)/*:string*/ {\n\tvar o=\"\", ss=0, tt=0, y = val.y, out, outl = 0;\n\tswitch(type) {\n\t\tcase 98: /* 'b' buddhist year */\n\t\t\ty = val.y + 543;\n\t\t\t/* falls through */\n\t\tcase 121: /* 'y' year */\n\t\tswitch(fmt.length) {\n\t\t\tcase 1: case 2: out = y % 100; outl = 2; break;\n\t\t\tdefault: out = y % 10000; outl = 4; break;\n\t\t} break;\n\t\tcase 109: /* 'm' month */\n\t\tswitch(fmt.length) {\n\t\t\tcase 1: case 2: out = val.m; outl = fmt.length; break;\n\t\t\tcase 3: return months[val.m-1][1];\n\t\t\tcase 5: return months[val.m-1][0];\n\t\t\tdefault: return months[val.m-1][2];\n\t\t} break;\n\t\tcase 100: /* 'd' day */\n\t\tswitch(fmt.length) {\n\t\t\tcase 1: case 2: out = val.d; outl = fmt.length; break;\n\t\t\tcase 3: return days[val.q][0];\n\t\t\tdefault: return days[val.q][1];\n\t\t} break;\n\t\tcase 104: /* 'h' 12-hour */\n\t\tswitch(fmt.length) {\n\t\t\tcase 1: case 2: out = 1+(val.H+11)%12; outl = fmt.length; break;\n\t\t\tdefault: throw 'bad hour format: ' + fmt;\n\t\t} break;\n\t\tcase 72: /* 'H' 24-hour */\n\t\tswitch(fmt.length) {\n\t\t\tcase 1: case 2: out = val.H; outl = fmt.length; break;\n\t\t\tdefault: throw 'bad hour format: ' + fmt;\n\t\t} break;\n\t\tcase 77: /* 'M' minutes */\n\t\tswitch(fmt.length) {\n\t\t\tcase 1: case 2: out = val.M; outl = fmt.length; break;\n\t\t\tdefault: throw 'bad minute format: ' + fmt;\n\t\t} break;\n\t\tcase 115: /* 's' seconds */\n\t\t\tif(fmt != 's' && fmt != 'ss' && fmt != '.0' && fmt != '.00' && fmt != '.000') throw 'bad second format: ' + fmt;\n\t\t\tif(val.u === 0 && (fmt == \"s\" || fmt == \"ss\")) return pad0(val.S, fmt.length);\n\t\t\t/*::if(!ss0) ss0 = 0; */\n\t\t\tif(ss0 >= 2) tt = ss0 === 3 ? 1000 : 100;\n\t\t\telse tt = ss0 === 1 ? 10 : 1;\n\t\t\tss = Math.round((tt)*(val.S + val.u));\n\t\t\tif(ss >= 60*tt) ss = 0;\n\t\t\tif(fmt === 's') return ss === 0 ? \"0\" : \"\"+ss/tt;\n\t\t\to = pad0(ss,2 + ss0);\n\t\t\tif(fmt === 'ss') return o.substr(0,2);\n\t\t\treturn \".\" + o.substr(2,fmt.length-1);\n\t\tcase 90: /* 'Z' absolute time */\n\t\tswitch(fmt) {\n\t\t\tcase '[h]': case '[hh]': out = val.D*24+val.H; break;\n\t\t\tcase '[m]': case '[mm]': out = (val.D*24+val.H)*60+val.M; break;\n\t\t\tcase '[s]': case '[ss]': out = ((val.D*24+val.H)*60+val.M)*60+Math.round(val.S+val.u); break;\n\t\t\tdefault: throw 'bad abstime format: ' + fmt;\n\t\t} outl = fmt.length === 3 ? 1 : 2; break;\n\t\tcase 101: /* 'e' era */\n\t\t\tout = y; outl = 1; break;\n\t}\n\tvar outstr = outl > 0 ? pad0(out, outl) : \"\";\n\treturn outstr;\n}\n\n\n/*jshint -W086 */\n/*jshint +W086 */\nfunction commaify(s/*:string*/)/*:string*/ {\n\tvar w = 3;\n\tif(s.length <= w) return s;\n\tvar j = (s.length % w), o = s.substr(0,j);\n\tfor(; j!=s.length; j+=w) o+=(o.length > 0 ? \",\" : \"\") + s.substr(j,w);\n\treturn o;\n}\nvar pct1 = /%/g;\nfunction write_num_pct(type/*:string*/, fmt/*:string*/, val/*:number*/)/*:string*/{\n\tvar sfmt = fmt.replace(pct1,\"\"), mul = fmt.length - sfmt.length;\n\treturn write_num(type, sfmt, val * Math.pow(10,2*mul)) + fill(\"%\",mul);\n}\n\nfunction write_num_cm(type/*:string*/, fmt/*:string*/, val/*:number*/)/*:string*/{\n\tvar idx = fmt.length - 1;\n\twhile(fmt.charCodeAt(idx-1) === 44) --idx;\n\treturn write_num(type, fmt.substr(0,idx), val / Math.pow(10,3*(fmt.length-idx)));\n}\n\nfunction write_num_exp(fmt/*:string*/, val/*:number*/)/*:string*/{\n\tvar o/*:string*/;\n\tvar idx = fmt.indexOf(\"E\") - fmt.indexOf(\".\") - 1;\n\tif(fmt.match(/^#+0.0E\\+0$/)) {\n\t\tif(val == 0) return \"0.0E+0\";\n\t\telse if(val < 0) return \"-\" + write_num_exp(fmt, -val);\n\t\tvar period = fmt.indexOf(\".\"); if(period === -1) period=fmt.indexOf('E');\n\t\tvar ee = Math.floor(Math.log(val)*Math.LOG10E)%period;\n\t\tif(ee < 0) ee += period;\n\t\to = (val/Math.pow(10,ee)).toPrecision(idx+1+(period+ee)%period);\n\t\tif(o.indexOf(\"e\") === -1) {\n\t\t\tvar fakee = Math.floor(Math.log(val)*Math.LOG10E);\n\t\t\tif(o.indexOf(\".\") === -1) o = o.charAt(0) + \".\" + o.substr(1) + \"E+\" + (fakee - o.length+ee);\n\t\t\telse o += \"E+\" + (fakee - ee);\n\t\t\twhile(o.substr(0,2) === \"0.\") {\n\t\t\t\to = o.charAt(0) + o.substr(2,period) + \".\" + o.substr(2+period);\n\t\t\t\to = o.replace(/^0+([1-9])/,\"$1\").replace(/^0+\\./,\"0.\");\n\t\t\t}\n\t\t\to = o.replace(/\\+-/,\"-\");\n\t\t}\n\t\to = o.replace(/^([+-]?)(\\d*)\\.(\\d*)[Ee]/,function($$,$1,$2,$3) { return $1 + $2 + $3.substr(0,(period+ee)%period) + \".\" + $3.substr(ee) + \"E\"; });\n\t} else o = val.toExponential(idx);\n\tif(fmt.match(/E\\+00$/) && o.match(/e[+-]\\d$/)) o = o.substr(0,o.length-1) + \"0\" + o.charAt(o.length-1);\n\tif(fmt.match(/E\\-/) && o.match(/e\\+/)) o = o.replace(/e\\+/,\"e\");\n\treturn o.replace(\"e\",\"E\");\n}\nvar frac1 = /# (\\?+)( ?)\\/( ?)(\\d+)/;\nfunction write_num_f1(r/*:Array<string>*/, aval/*:number*/, sign/*:string*/)/*:string*/ {\n\tvar den = parseInt(r[4],10), rr = Math.round(aval * den), base = Math.floor(rr/den);\n\tvar myn = (rr - base*den), myd = den;\n\treturn sign + (base === 0 ? \"\" : \"\"+base) + \" \" + (myn === 0 ? fill(\" \", r[1].length + 1 + r[4].length) : pad_(myn,r[1].length) + r[2] + \"/\" + r[3] + pad0(myd,r[4].length));\n}\nfunction write_num_f2(r/*:Array<string>*/, aval/*:number*/, sign/*:string*/)/*:string*/ {\n\treturn sign + (aval === 0 ? \"\" : \"\"+aval) + fill(\" \", r[1].length + 2 + r[4].length);\n}\nvar dec1 = /^#*0*\\.([0#]+)/;\nvar closeparen = /\\).*[0#]/;\nvar phone = /\\(###\\) ###\\\\?-####/;\nfunction hashq(str/*:string*/)/*:string*/ {\n\tvar o = \"\", cc;\n\tfor(var i = 0; i != str.length; ++i) switch((cc=str.charCodeAt(i))) {\n\t\tcase 35: break;\n\t\tcase 63: o+= \" \"; break;\n\t\tcase 48: o+= \"0\"; break;\n\t\tdefault: o+= String.fromCharCode(cc);\n\t}\n\treturn o;\n}\nfunction rnd(val/*:number*/, d/*:number*/)/*:string*/ { var dd = Math.pow(10,d); return \"\"+(Math.round(val * dd)/dd); }\nfunction dec(val/*:number*/, d/*:number*/)/*:number*/ {\n\tvar _frac = val - Math.floor(val), dd = Math.pow(10,d);\n\tif (d < ('' + Math.round(_frac * dd)).length) return 0;\n\treturn Math.round(_frac * dd);\n}\nfunction carry(val/*:number*/, d/*:number*/)/*:number*/ {\n\tif (d < ('' + Math.round((val-Math.floor(val))*Math.pow(10,d))).length) {\n\t\treturn 1;\n\t}\n\treturn 0;\n}\nfunction flr(val/*:number*/)/*:string*/ {\n\tif(val < 2147483647 && val > -2147483648) return \"\"+(val >= 0 ? (val|0) : (val-1|0));\n\treturn \"\"+Math.floor(val);\n}\nfunction write_num_flt(type/*:string*/, fmt/*:string*/, val/*:number*/)/*:string*/ {\n\tif(type.charCodeAt(0) === 40 && !fmt.match(closeparen)) {\n\t\tvar ffmt = fmt.replace(/\\( */,\"\").replace(/ \\)/,\"\").replace(/\\)/,\"\");\n\t\tif(val >= 0) return write_num_flt('n', ffmt, val);\n\t\treturn '(' + write_num_flt('n', ffmt, -val) + ')';\n\t}\n\tif(fmt.charCodeAt(fmt.length - 1) === 44) return write_num_cm(type, fmt, val);\n\tif(fmt.indexOf('%') !== -1) return write_num_pct(type, fmt, val);\n\tif(fmt.indexOf('E') !== -1) return write_num_exp(fmt, val);\n\tif(fmt.charCodeAt(0) === 36) return \"$\"+write_num_flt(type,fmt.substr(fmt.charAt(1)==' '?2:1),val);\n\tvar o;\n\tvar r/*:?Array<string>*/, ri, ff, aval = Math.abs(val), sign = val < 0 ? \"-\" : \"\";\n\tif(fmt.match(/^00+$/)) return sign + pad0r(aval,fmt.length);\n\tif(fmt.match(/^[#?]+$/)) {\n\t\to = pad0r(val,0); if(o === \"0\") o = \"\";\n\t\treturn o.length > fmt.length ? o : hashq(fmt.substr(0,fmt.length-o.length)) + o;\n\t}\n\tif((r = fmt.match(frac1))) return write_num_f1(r, aval, sign);\n\tif(fmt.match(/^#+0+$/)) return sign + pad0r(aval,fmt.length - fmt.indexOf(\"0\"));\n\tif((r = fmt.match(dec1))) {\n\t\to = rnd(val, r[1].length).replace(/^([^\\.]+)$/,\"$1.\"+hashq(r[1])).replace(/\\.$/,\".\"+hashq(r[1])).replace(/\\.(\\d*)$/,function($$, $1) { return \".\" + $1 + fill(\"0\", hashq(/*::(*/r/*::||[\"\"])*/[1]).length-$1.length); });\n\t\treturn fmt.indexOf(\"0.\") !== -1 ? o : o.replace(/^0\\./,\".\");\n\t}\n\tfmt = fmt.replace(/^#+([0.])/, \"$1\");\n\tif((r = fmt.match(/^(0*)\\.(#*)$/))) {\n\t\treturn sign + rnd(aval, r[2].length).replace(/\\.(\\d*[1-9])0*$/,\".$1\").replace(/^(-?\\d*)$/,\"$1.\").replace(/^0\\./,r[1].length?\"0.\":\".\");\n\t}\n\tif((r = fmt.match(/^#{1,3},##0(\\.?)$/))) return sign + commaify(pad0r(aval,0));\n\tif((r = fmt.match(/^#,##0\\.([#0]*0)$/))) {\n\t\treturn val < 0 ? \"-\" + write_num_flt(type, fmt, -val) : commaify(\"\"+(Math.floor(val) + carry(val, r[1].length))) + \".\" + pad0(dec(val, r[1].length),r[1].length);\n\t}\n\tif((r = fmt.match(/^#,#*,#0/))) return write_num_flt(type,fmt.replace(/^#,#*,/,\"\"),val);\n\tif((r = fmt.match(/^([0#]+)(\\\\?-([0#]+))+$/))) {\n\t\to = _strrev(write_num_flt(type, fmt.replace(/[\\\\-]/g,\"\"), val));\n\t\tri = 0;\n\t\treturn _strrev(_strrev(fmt.replace(/\\\\/g,\"\")).replace(/[0#]/g,function(x){return ri<o.length?o.charAt(ri++):x==='0'?'0':\"\";}));\n\t}\n\tif(fmt.match(phone)) {\n\t\to = write_num_flt(type, \"##########\", val);\n\t\treturn \"(\" + o.substr(0,3) + \") \" + o.substr(3, 3) + \"-\" + o.substr(6);\n\t}\n\tvar oa = \"\";\n\tif((r = fmt.match(/^([#0?]+)( ?)\\/( ?)([#0?]+)/))) {\n\t\tri = Math.min(/*::String(*/r[4]/*::)*/.length,7);\n\t\tff = SSF_frac(aval, Math.pow(10,ri)-1, false);\n\t\to = \"\" + sign;\n\t\toa = write_num(\"n\", /*::String(*/r[1]/*::)*/, ff[1]);\n\t\tif(oa.charAt(oa.length-1) == \" \") oa = oa.substr(0,oa.length-1) + \"0\";\n\t\to += oa + /*::String(*/r[2]/*::)*/ + \"/\" + /*::String(*/r[3]/*::)*/;\n\t\toa = rpad_(ff[2],ri);\n\t\tif(oa.length < r[4].length) oa = hashq(r[4].substr(r[4].length-oa.length)) + oa;\n\t\to += oa;\n\t\treturn o;\n\t}\n\tif((r = fmt.match(/^# ([#0?]+)( ?)\\/( ?)([#0?]+)/))) {\n\t\tri = Math.min(Math.max(r[1].length, r[4].length),7);\n\t\tff = SSF_frac(aval, Math.pow(10,ri)-1, true);\n\t\treturn sign + (ff[0]||(ff[1] ? \"\" : \"0\")) + \" \" + (ff[1] ? pad_(ff[1],ri) + r[2] + \"/\" + r[3] + rpad_(ff[2],ri): fill(\" \", 2*ri+1 + r[2].length + r[3].length));\n\t}\n\tif((r = fmt.match(/^[#0?]+$/))) {\n\t\to = pad0r(val, 0);\n\t\tif(fmt.length <= o.length) return o;\n\t\treturn hashq(fmt.substr(0,fmt.length-o.length)) + o;\n\t}\n\tif((r = fmt.match(/^([#0?]+)\\.([#0]+)$/))) {\n\t\to = \"\" + val.toFixed(Math.min(r[2].length,10)).replace(/([^0])0+$/,\"$1\");\n\t\tri = o.indexOf(\".\");\n\t\tvar lres = fmt.indexOf(\".\") - ri, rres = fmt.length - o.length - lres;\n\t\treturn hashq(fmt.substr(0,lres) + o + fmt.substr(fmt.length-rres));\n\t}\n\tif((r = fmt.match(/^00,000\\.([#0]*0)$/))) {\n\t\tri = dec(val, r[1].length);\n\t\treturn val < 0 ? \"-\" + write_num_flt(type, fmt, -val) : commaify(flr(val)).replace(/^\\d,\\d{3}$/,\"0$&\").replace(/^\\d*$/,function($$) { return \"00,\" + ($$.length < 3 ? pad0(0,3-$$.length) : \"\") + $$; }) + \".\" + pad0(ri,r[1].length);\n\t}\n\tswitch(fmt) {\n\t\tcase \"###,##0.00\": return write_num_flt(type, \"#,##0.00\", val);\n\t\tcase \"###,###\":\n\t\tcase \"##,###\":\n\t\tcase \"#,###\": var x = commaify(pad0r(aval,0)); return x !== \"0\" ? sign + x : \"\";\n\t\tcase \"###,###.00\": return write_num_flt(type, \"###,##0.00\",val).replace(/^0\\./,\".\");\n\t\tcase \"#,###.00\": return write_num_flt(type, \"#,##0.00\",val).replace(/^0\\./,\".\");\n\t\tdefault:\n\t}\n\tthrow new Error(\"unsupported format |\" + fmt + \"|\");\n}\nfunction write_num_cm2(type/*:string*/, fmt/*:string*/, val/*:number*/)/*:string*/{\n\tvar idx = fmt.length - 1;\n\twhile(fmt.charCodeAt(idx-1) === 44) --idx;\n\treturn write_num(type, fmt.substr(0,idx), val / Math.pow(10,3*(fmt.length-idx)));\n}\nfunction write_num_pct2(type/*:string*/, fmt/*:string*/, val/*:number*/)/*:string*/{\n\tvar sfmt = fmt.replace(pct1,\"\"), mul = fmt.length - sfmt.length;\n\treturn write_num(type, sfmt, val * Math.pow(10,2*mul)) + fill(\"%\",mul);\n}\nfunction write_num_exp2(fmt/*:string*/, val/*:number*/)/*:string*/{\n\tvar o/*:string*/;\n\tvar idx = fmt.indexOf(\"E\") - fmt.indexOf(\".\") - 1;\n\tif(fmt.match(/^#+0.0E\\+0$/)) {\n\t\tif(val == 0) return \"0.0E+0\";\n\t\telse if(val < 0) return \"-\" + write_num_exp2(fmt, -val);\n\t\tvar period = fmt.indexOf(\".\"); if(period === -1) period=fmt.indexOf('E');\n\t\tvar ee = Math.floor(Math.log(val)*Math.LOG10E)%period;\n\t\tif(ee < 0) ee += period;\n\t\to = (val/Math.pow(10,ee)).toPrecision(idx+1+(period+ee)%period);\n\t\tif(!o.match(/[Ee]/)) {\n\t\t\tvar fakee = Math.floor(Math.log(val)*Math.LOG10E);\n\t\t\tif(o.indexOf(\".\") === -1) o = o.charAt(0) + \".\" + o.substr(1) + \"E+\" + (fakee - o.length+ee);\n\t\t\telse o += \"E+\" + (fakee - ee);\n\t\t\to = o.replace(/\\+-/,\"-\");\n\t\t}\n\t\to = o.replace(/^([+-]?)(\\d*)\\.(\\d*)[Ee]/,function($$,$1,$2,$3) { return $1 + $2 + $3.substr(0,(period+ee)%period) + \".\" + $3.substr(ee) + \"E\"; });\n\t} else o = val.toExponential(idx);\n\tif(fmt.match(/E\\+00$/) && o.match(/e[+-]\\d$/)) o = o.substr(0,o.length-1) + \"0\" + o.charAt(o.length-1);\n\tif(fmt.match(/E\\-/) && o.match(/e\\+/)) o = o.replace(/e\\+/,\"e\");\n\treturn o.replace(\"e\",\"E\");\n}\nfunction write_num_int(type/*:string*/, fmt/*:string*/, val/*:number*/)/*:string*/ {\n\tif(type.charCodeAt(0) === 40 && !fmt.match(closeparen)) {\n\t\tvar ffmt = fmt.replace(/\\( */,\"\").replace(/ \\)/,\"\").replace(/\\)/,\"\");\n\t\tif(val >= 0) return write_num_int('n', ffmt, val);\n\t\treturn '(' + write_num_int('n', ffmt, -val) + ')';\n\t}\n\tif(fmt.charCodeAt(fmt.length - 1) === 44) return write_num_cm2(type, fmt, val);\n\tif(fmt.indexOf('%') !== -1) return write_num_pct2(type, fmt, val);\n\tif(fmt.indexOf('E') !== -1) return write_num_exp2(fmt, val);\n\tif(fmt.charCodeAt(0) === 36) return \"$\"+write_num_int(type,fmt.substr(fmt.charAt(1)==' '?2:1),val);\n\tvar o;\n\tvar r/*:?Array<string>*/, ri, ff, aval = Math.abs(val), sign = val < 0 ? \"-\" : \"\";\n\tif(fmt.match(/^00+$/)) return sign + pad0(aval,fmt.length);\n\tif(fmt.match(/^[#?]+$/)) {\n\t\to = (\"\"+val); if(val === 0) o = \"\";\n\t\treturn o.length > fmt.length ? o : hashq(fmt.substr(0,fmt.length-o.length)) + o;\n\t}\n\tif((r = fmt.match(frac1))) return write_num_f2(r, aval, sign);\n\tif(fmt.match(/^#+0+$/)) return sign + pad0(aval,fmt.length - fmt.indexOf(\"0\"));\n\tif((r = fmt.match(dec1))) {\n\t\t/*:: if(!Array.isArray(r)) throw new Error(\"unreachable\"); */\n\t\to = (\"\"+val).replace(/^([^\\.]+)$/,\"$1.\"+hashq(r[1])).replace(/\\.$/,\".\"+hashq(r[1]));\n\t\to = o.replace(/\\.(\\d*)$/,function($$, $1) {\n\t\t/*:: if(!Array.isArray(r)) throw new Error(\"unreachable\"); */\n\t\t\treturn \".\" + $1 + fill(\"0\", hashq(r[1]).length-$1.length); });\n\t\treturn fmt.indexOf(\"0.\") !== -1 ? o : o.replace(/^0\\./,\".\");\n\t}\n\tfmt = fmt.replace(/^#+([0.])/, \"$1\");\n\tif((r = fmt.match(/^(0*)\\.(#*)$/))) {\n\t\treturn sign + (\"\"+aval).replace(/\\.(\\d*[1-9])0*$/,\".$1\").replace(/^(-?\\d*)$/,\"$1.\").replace(/^0\\./,r[1].length?\"0.\":\".\");\n\t}\n\tif((r = fmt.match(/^#{1,3},##0(\\.?)$/))) return sign + commaify((\"\"+aval));\n\tif((r = fmt.match(/^#,##0\\.([#0]*0)$/))) {\n\t\treturn val < 0 ? \"-\" + write_num_int(type, fmt, -val) : commaify((\"\"+val)) + \".\" + fill('0',r[1].length);\n\t}\n\tif((r = fmt.match(/^#,#*,#0/))) return write_num_int(type,fmt.replace(/^#,#*,/,\"\"),val);\n\tif((r = fmt.match(/^([0#]+)(\\\\?-([0#]+))+$/))) {\n\t\to = _strrev(write_num_int(type, fmt.replace(/[\\\\-]/g,\"\"), val));\n\t\tri = 0;\n\t\treturn _strrev(_strrev(fmt.replace(/\\\\/g,\"\")).replace(/[0#]/g,function(x){return ri<o.length?o.charAt(ri++):x==='0'?'0':\"\";}));\n\t}\n\tif(fmt.match(phone)) {\n\t\to = write_num_int(type, \"##########\", val);\n\t\treturn \"(\" + o.substr(0,3) + \") \" + o.substr(3, 3) + \"-\" + o.substr(6);\n\t}\n\tvar oa = \"\";\n\tif((r = fmt.match(/^([#0?]+)( ?)\\/( ?)([#0?]+)/))) {\n\t\tri = Math.min(/*::String(*/r[4]/*::)*/.length,7);\n\t\tff = SSF_frac(aval, Math.pow(10,ri)-1, false);\n\t\to = \"\" + sign;\n\t\toa = write_num(\"n\", /*::String(*/r[1]/*::)*/, ff[1]);\n\t\tif(oa.charAt(oa.length-1) == \" \") oa = oa.substr(0,oa.length-1) + \"0\";\n\t\to += oa + /*::String(*/r[2]/*::)*/ + \"/\" + /*::String(*/r[3]/*::)*/;\n\t\toa = rpad_(ff[2],ri);\n\t\tif(oa.length < r[4].length) oa = hashq(r[4].substr(r[4].length-oa.length)) + oa;\n\t\to += oa;\n\t\treturn o;\n\t}\n\tif((r = fmt.match(/^# ([#0?]+)( ?)\\/( ?)([#0?]+)/))) {\n\t\tri = Math.min(Math.max(r[1].length, r[4].length),7);\n\t\tff = SSF_frac(aval, Math.pow(10,ri)-1, true);\n\t\treturn sign + (ff[0]||(ff[1] ? \"\" : \"0\")) + \" \" + (ff[1] ? pad_(ff[1],ri) + r[2] + \"/\" + r[3] + rpad_(ff[2],ri): fill(\" \", 2*ri+1 + r[2].length + r[3].length));\n\t}\n\tif((r = fmt.match(/^[#0?]+$/))) {\n\t\to = \"\" + val;\n\t\tif(fmt.length <= o.length) return o;\n\t\treturn hashq(fmt.substr(0,fmt.length-o.length)) + o;\n\t}\n\tif((r = fmt.match(/^([#0]+)\\.([#0]+)$/))) {\n\t\to = \"\" + val.toFixed(Math.min(r[2].length,10)).replace(/([^0])0+$/,\"$1\");\n\t\tri = o.indexOf(\".\");\n\t\tvar lres = fmt.indexOf(\".\") - ri, rres = fmt.length - o.length - lres;\n\t\treturn hashq(fmt.substr(0,lres) + o + fmt.substr(fmt.length-rres));\n\t}\n\tif((r = fmt.match(/^00,000\\.([#0]*0)$/))) {\n\t\treturn val < 0 ? \"-\" + write_num_int(type, fmt, -val) : commaify(\"\"+val).replace(/^\\d,\\d{3}$/,\"0$&\").replace(/^\\d*$/,function($$) { return \"00,\" + ($$.length < 3 ? pad0(0,3-$$.length) : \"\") + $$; }) + \".\" + pad0(0,r[1].length);\n\t}\n\tswitch(fmt) {\n\t\tcase \"###,###\":\n\t\tcase \"##,###\":\n\t\tcase \"#,###\": var x = commaify(\"\"+aval); return x !== \"0\" ? sign + x : \"\";\n\t\tdefault:\n\t\t\tif(fmt.match(/\\.[0#?]*$/)) return write_num_int(type, fmt.slice(0,fmt.lastIndexOf(\".\")), val) + hashq(fmt.slice(fmt.lastIndexOf(\".\")));\n\t}\n\tthrow new Error(\"unsupported format |\" + fmt + \"|\");\n}\nfunction write_num(type/*:string*/, fmt/*:string*/, val/*:number*/)/*:string*/ {\n\treturn (val|0) === val ? write_num_int(type, fmt, val) : write_num_flt(type, fmt, val);\n}\nfunction SSF_split_fmt(fmt/*:string*/)/*:Array<string>*/ {\n\tvar out/*:Array<string>*/ = [];\n\tvar in_str = false/*, cc*/;\n\tfor(var i = 0, j = 0; i < fmt.length; ++i) switch((/*cc=*/fmt.charCodeAt(i))) {\n\t\tcase 34: /* '\"' */\n\t\t\tin_str = !in_str; break;\n\t\tcase 95: case 42: case 92: /* '_' '*' '\\\\' */\n\t\t\t++i; break;\n\t\tcase 59: /* ';' */\n\t\t\tout[out.length] = fmt.substr(j,i-j);\n\t\t\tj = i+1;\n\t}\n\tout[out.length] = fmt.substr(j);\n\tif(in_str === true) throw new Error(\"Format |\" + fmt + \"| unterminated string \");\n\treturn out;\n}\n\nvar SSF_abstime = /\\[[HhMmSs\\u0E0A\\u0E19\\u0E17]*\\]/;\nfunction fmt_is_date(fmt/*:string*/)/*:boolean*/ {\n\tvar i = 0, /*cc = 0,*/ c = \"\", o = \"\";\n\twhile(i < fmt.length) {\n\t\tswitch((c = fmt.charAt(i))) {\n\t\t\tcase 'G': if(SSF_isgeneral(fmt, i)) i+= 6; i++; break;\n\t\t\tcase '\"': for(;(/*cc=*/fmt.charCodeAt(++i)) !== 34 && i < fmt.length;){/*empty*/} ++i; break;\n\t\t\tcase '\\\\': i+=2; break;\n\t\t\tcase '_': i+=2; break;\n\t\t\tcase '@': ++i; break;\n\t\t\tcase 'B': case 'b':\n\t\t\t\tif(fmt.charAt(i+1) === \"1\" || fmt.charAt(i+1) === \"2\") return true;\n\t\t\t\t/* falls through */\n\t\t\tcase 'M': case 'D': case 'Y': case 'H': case 'S': case 'E':\n\t\t\t\t/* falls through */\n\t\t\tcase 'm': case 'd': case 'y': case 'h': case 's': case 'e': case 'g': return true;\n\t\t\tcase 'A': case 'a': case '上':\n\t\t\t\tif(fmt.substr(i, 3).toUpperCase() === \"A/P\") return true;\n\t\t\t\tif(fmt.substr(i, 5).toUpperCase() === \"AM/PM\") return true;\n\t\t\t\tif(fmt.substr(i, 5).toUpperCase() === \"上午/下午\") return true;\n\t\t\t\t++i; break;\n\t\t\tcase '[':\n\t\t\t\to = c;\n\t\t\t\twhile(fmt.charAt(i++) !== ']' && i < fmt.length) o += fmt.charAt(i);\n\t\t\t\tif(o.match(SSF_abstime)) return true;\n\t\t\t\tbreak;\n\t\t\tcase '.':\n\t\t\t\t/* falls through */\n\t\t\tcase '0': case '#':\n\t\t\t\twhile(i < fmt.length && (\"0#?.,E+-%\".indexOf(c=fmt.charAt(++i)) > -1 || (c=='\\\\' && fmt.charAt(i+1) == \"-\" && \"0#\".indexOf(fmt.charAt(i+2))>-1))){/* empty */}\n\t\t\t\tbreak;\n\t\t\tcase '?': while(fmt.charAt(++i) === c){/* empty */} break;\n\t\t\tcase '*': ++i; if(fmt.charAt(i) == ' ' || fmt.charAt(i) == '*') ++i; break;\n\t\t\tcase '(': case ')': ++i; break;\n\t\t\tcase '1': case '2': case '3': case '4': case '5': case '6': case '7': case '8': case '9':\n\t\t\t\twhile(i < fmt.length && \"0123456789\".indexOf(fmt.charAt(++i)) > -1){/* empty */} break;\n\t\t\tcase ' ': ++i; break;\n\t\t\tdefault: ++i; break;\n\t\t}\n\t}\n\treturn false;\n}\n\nfunction eval_fmt(fmt/*:string*/, v/*:any*/, opts/*:any*/, flen/*:number*/) {\n\tvar out = [], o = \"\", i = 0, c = \"\", lst='t', dt, j, cc;\n\tvar hr='H';\n\t/* Tokenize */\n\twhile(i < fmt.length) {\n\t\tswitch((c = fmt.charAt(i))) {\n\t\t\tcase 'G': /* General */\n\t\t\t\tif(!SSF_isgeneral(fmt, i)) throw new Error('unrecognized character ' + c + ' in ' +fmt);\n\t\t\t\tout[out.length] = {t:'G', v:'General'}; i+=7; break;\n\t\t\tcase '\"': /* Literal text */\n\t\t\t\tfor(o=\"\";(cc=fmt.charCodeAt(++i)) !== 34 && i < fmt.length;) o += String.fromCharCode(cc);\n\t\t\t\tout[out.length] = {t:'t', v:o}; ++i; break;\n\t\t\tcase '\\\\': var w = fmt.charAt(++i), t = (w === \"(\" || w === \")\") ? w : 't';\n\t\t\t\tout[out.length] = {t:t, v:w}; ++i; break;\n\t\t\tcase '_': out[out.length] = {t:'t', v:\" \"}; i+=2; break;\n\t\t\tcase '@': /* Text Placeholder */\n\t\t\t\tout[out.length] = {t:'T', v:v}; ++i; break;\n\t\t\tcase 'B': case 'b':\n\t\t\t\tif(fmt.charAt(i+1) === \"1\" || fmt.charAt(i+1) === \"2\") {\n\t\t\t\t\tif(dt==null) { dt=SSF_parse_date_code(v, opts, fmt.charAt(i+1) === \"2\"); if(dt==null) return \"\"; }\n\t\t\t\t\tout[out.length] = {t:'X', v:fmt.substr(i,2)}; lst = c; i+=2; break;\n\t\t\t\t}\n\t\t\t\t/* falls through */\n\t\t\tcase 'M': case 'D': case 'Y': case 'H': case 'S': case 'E':\n\t\t\t\tc = c.toLowerCase();\n\t\t\t\t/* falls through */\n\t\t\tcase 'm': case 'd': case 'y': case 'h': case 's': case 'e': case 'g':\n\t\t\t\tif(v < 0) return \"\";\n\t\t\t\tif(dt==null) { dt=SSF_parse_date_code(v, opts); if(dt==null) return \"\"; }\n\t\t\t\to = c; while(++i < fmt.length && fmt.charAt(i).toLowerCase() === c) o+=c;\n\t\t\t\tif(c === 'm' && lst.toLowerCase() === 'h') c = 'M';\n\t\t\t\tif(c === 'h') c = hr;\n\t\t\t\tout[out.length] = {t:c, v:o}; lst = c; break;\n\t\t\tcase 'A': case 'a': case '上':\n\t\t\t\tvar q={t:c, v:c};\n\t\t\t\tif(dt==null) dt=SSF_parse_date_code(v, opts);\n\t\t\t\tif(fmt.substr(i, 3).toUpperCase() === \"A/P\") { if(dt!=null) q.v = dt.H >= 12 ? \"P\" : \"A\"; q.t = 'T'; hr='h';i+=3;}\n\t\t\t\telse if(fmt.substr(i,5).toUpperCase() === \"AM/PM\") { if(dt!=null) q.v = dt.H >= 12 ? \"PM\" : \"AM\"; q.t = 'T'; i+=5; hr='h'; }\n\t\t\t\telse if(fmt.substr(i,5).toUpperCase() === \"上午/下午\") { if(dt!=null) q.v = dt.H >= 12 ? \"下午\" : \"上午\"; q.t = 'T'; i+=5; hr='h'; }\n\t\t\t\telse { q.t = \"t\"; ++i; }\n\t\t\t\tif(dt==null && q.t === 'T') return \"\";\n\t\t\t\tout[out.length] = q; lst = c; break;\n\t\t\tcase '[':\n\t\t\t\to = c;\n\t\t\t\twhile(fmt.charAt(i++) !== ']' && i < fmt.length) o += fmt.charAt(i);\n\t\t\t\tif(o.slice(-1) !== ']') throw 'unterminated \"[\" block: |' + o + '|';\n\t\t\t\tif(o.match(SSF_abstime)) {\n\t\t\t\t\tif(dt==null) { dt=SSF_parse_date_code(v, opts); if(dt==null) return \"\"; }\n\t\t\t\t\tout[out.length] = {t:'Z', v:o.toLowerCase()};\n\t\t\t\t\tlst = o.charAt(1);\n\t\t\t\t} else if(o.indexOf(\"$\") > -1) {\n\t\t\t\t\to = (o.match(/\\$([^-\\[\\]]*)/)||[])[1]||\"$\";\n\t\t\t\t\tif(!fmt_is_date(fmt)) out[out.length] = {t:'t',v:o};\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\t/* Numbers */\n\t\t\tcase '.':\n\t\t\t\tif(dt != null) {\n\t\t\t\t\to = c; while(++i < fmt.length && (c=fmt.charAt(i)) === \"0\") o += c;\n\t\t\t\t\tout[out.length] = {t:'s', v:o}; break;\n\t\t\t\t}\n\t\t\t\t/* falls through */\n\t\t\tcase '0': case '#':\n\t\t\t\to = c; while(++i < fmt.length && \"0#?.,E+-%\".indexOf(c=fmt.charAt(i)) > -1) o += c;\n\t\t\t\tout[out.length] = {t:'n', v:o}; break;\n\t\t\tcase '?':\n\t\t\t\to = c; while(fmt.charAt(++i) === c) o+=c;\n\t\t\t\tout[out.length] = {t:c, v:o}; lst = c; break;\n\t\t\tcase '*': ++i; if(fmt.charAt(i) == ' ' || fmt.charAt(i) == '*') ++i; break; // **\n\t\t\tcase '(': case ')': out[out.length] = {t:(flen===1?'t':c), v:c}; ++i; break;\n\t\t\tcase '1': case '2': case '3': case '4': case '5': case '6': case '7': case '8': case '9':\n\t\t\t\to = c; while(i < fmt.length && \"0123456789\".indexOf(fmt.charAt(++i)) > -1) o+=fmt.charAt(i);\n\t\t\t\tout[out.length] = {t:'D', v:o}; break;\n\t\t\tcase ' ': out[out.length] = {t:c, v:c}; ++i; break;\n\t\t\tcase '$': out[out.length] = {t:'t', v:'$'}; ++i; break;\n\t\t\tdefault:\n\t\t\t\tif(\",$-+/():!^&'~{}<>=€acfijklopqrtuvwxzP\".indexOf(c) === -1) throw new Error('unrecognized character ' + c + ' in ' + fmt);\n\t\t\t\tout[out.length] = {t:'t', v:c}; ++i; break;\n\t\t}\n\t}\n\n\t/* Scan for date/time parts */\n\tvar bt = 0, ss0 = 0, ssm;\n\tfor(i=out.length-1, lst='t'; i >= 0; --i) {\n\t\tswitch(out[i].t) {\n\t\t\tcase 'h': case 'H': out[i].t = hr; lst='h'; if(bt < 1) bt = 1; break;\n\t\t\tcase 's':\n\t\t\t\tif((ssm=out[i].v.match(/\\.0+$/))) ss0=Math.max(ss0,ssm[0].length-1);\n\t\t\t\tif(bt < 3) bt = 3;\n\t\t\t/* falls through */\n\t\t\tcase 'd': case 'y': case 'M': case 'e': lst=out[i].t; break;\n\t\t\tcase 'm': if(lst === 's') { out[i].t = 'M'; if(bt < 2) bt = 2; } break;\n\t\t\tcase 'X': /*if(out[i].v === \"B2\");*/\n\t\t\t\tbreak;\n\t\t\tcase 'Z':\n\t\t\t\tif(bt < 1 && out[i].v.match(/[Hh]/)) bt = 1;\n\t\t\t\tif(bt < 2 && out[i].v.match(/[Mm]/)) bt = 2;\n\t\t\t\tif(bt < 3 && out[i].v.match(/[Ss]/)) bt = 3;\n\t\t}\n\t}\n\t/* time rounding depends on presence of minute / second / usec fields */\n\tswitch(bt) {\n\t\tcase 0: break;\n\t\tcase 1:\n\t\t\t/*::if(!dt) break;*/\n\t\t\tif(dt.u >= 0.5) { dt.u = 0; ++dt.S; }\n\t\t\tif(dt.S >=  60) { dt.S = 0; ++dt.M; }\n\t\t\tif(dt.M >=  60) { dt.M = 0; ++dt.H; }\n\t\t\tbreak;\n\t\tcase 2:\n\t\t\t/*::if(!dt) break;*/\n\t\t\tif(dt.u >= 0.5) { dt.u = 0; ++dt.S; }\n\t\t\tif(dt.S >=  60) { dt.S = 0; ++dt.M; }\n\t\t\tbreak;\n\t}\n\n\t/* replace fields */\n\tvar nstr = \"\", jj;\n\tfor(i=0; i < out.length; ++i) {\n\t\tswitch(out[i].t) {\n\t\t\tcase 't': case 'T': case ' ': case 'D': break;\n\t\t\tcase 'X': out[i].v = \"\"; out[i].t = \";\"; break;\n\t\t\tcase 'd': case 'm': case 'y': case 'h': case 'H': case 'M': case 's': case 'e': case 'b': case 'Z':\n\t\t\t\t/*::if(!dt) throw \"unreachable\"; */\n\t\t\t\tout[i].v = SSF_write_date(out[i].t.charCodeAt(0), out[i].v, dt, ss0);\n\t\t\t\tout[i].t = 't'; break;\n\t\t\tcase 'n': case '?':\n\t\t\t\tjj = i+1;\n\t\t\t\twhile(out[jj] != null && (\n\t\t\t\t\t(c=out[jj].t) === \"?\" || c === \"D\" ||\n\t\t\t\t\t((c === \" \" || c === \"t\") && out[jj+1] != null && (out[jj+1].t === '?' || out[jj+1].t === \"t\" && out[jj+1].v === '/')) ||\n\t\t\t\t\t(out[i].t === '(' && (c === ' ' || c === 'n' || c === ')')) ||\n\t\t\t\t\t(c === 't' && (out[jj].v === '/' || out[jj].v === ' ' && out[jj+1] != null && out[jj+1].t == '?'))\n\t\t\t\t)) {\n\t\t\t\t\tout[i].v += out[jj].v;\n\t\t\t\t\tout[jj] = {v:\"\", t:\";\"}; ++jj;\n\t\t\t\t}\n\t\t\t\tnstr += out[i].v;\n\t\t\t\ti = jj-1; break;\n\t\t\tcase 'G': out[i].t = 't'; out[i].v = SSF_general(v,opts); break;\n\t\t}\n\t}\n\tvar vv = \"\", myv, ostr;\n\tif(nstr.length > 0) {\n\t\tif(nstr.charCodeAt(0) == 40) /* '(' */ {\n\t\t\tmyv = (v<0&&nstr.charCodeAt(0) === 45 ? -v : v);\n\t\t\tostr = write_num('n', nstr, myv);\n\t\t} else {\n\t\t\tmyv = (v<0 && flen > 1 ? -v : v);\n\t\t\tostr = write_num('n', nstr, myv);\n\t\t\tif(myv < 0 && out[0] && out[0].t == 't') {\n\t\t\t\tostr = ostr.substr(1);\n\t\t\t\tout[0].v = \"-\" + out[0].v;\n\t\t\t}\n\t\t}\n\t\tjj=ostr.length-1;\n\t\tvar decpt = out.length;\n\t\tfor(i=0; i < out.length; ++i) if(out[i] != null && out[i].t != 't' && out[i].v.indexOf(\".\") > -1) { decpt = i; break; }\n\t\tvar lasti=out.length;\n\t\tif(decpt === out.length && ostr.indexOf(\"E\") === -1) {\n\t\t\tfor(i=out.length-1; i>= 0;--i) {\n\t\t\t\tif(out[i] == null || 'n?'.indexOf(out[i].t) === -1) continue;\n\t\t\t\tif(jj>=out[i].v.length-1) { jj -= out[i].v.length; out[i].v = ostr.substr(jj+1, out[i].v.length); }\n\t\t\t\telse if(jj < 0) out[i].v = \"\";\n\t\t\t\telse { out[i].v = ostr.substr(0, jj+1); jj = -1; }\n\t\t\t\tout[i].t = 't';\n\t\t\t\tlasti = i;\n\t\t\t}\n\t\t\tif(jj>=0 && lasti<out.length) out[lasti].v = ostr.substr(0,jj+1) + out[lasti].v;\n\t\t}\n\t\telse if(decpt !== out.length && ostr.indexOf(\"E\") === -1) {\n\t\t\tjj = ostr.indexOf(\".\")-1;\n\t\t\tfor(i=decpt; i>= 0; --i) {\n\t\t\t\tif(out[i] == null || 'n?'.indexOf(out[i].t) === -1) continue;\n\t\t\t\tj=out[i].v.indexOf(\".\")>-1&&i===decpt?out[i].v.indexOf(\".\")-1:out[i].v.length-1;\n\t\t\t\tvv = out[i].v.substr(j+1);\n\t\t\t\tfor(; j>=0; --j) {\n\t\t\t\t\tif(jj>=0 && (out[i].v.charAt(j) === \"0\" || out[i].v.charAt(j) === \"#\")) vv = ostr.charAt(jj--) + vv;\n\t\t\t\t}\n\t\t\t\tout[i].v = vv;\n\t\t\t\tout[i].t = 't';\n\t\t\t\tlasti = i;\n\t\t\t}\n\t\t\tif(jj>=0 && lasti<out.length) out[lasti].v = ostr.substr(0,jj+1) + out[lasti].v;\n\t\t\tjj = ostr.indexOf(\".\")+1;\n\t\t\tfor(i=decpt; i<out.length; ++i) {\n\t\t\t\tif(out[i] == null || ('n?('.indexOf(out[i].t) === -1 && i !== decpt)) continue;\n\t\t\t\tj=out[i].v.indexOf(\".\")>-1&&i===decpt?out[i].v.indexOf(\".\")+1:0;\n\t\t\t\tvv = out[i].v.substr(0,j);\n\t\t\t\tfor(; j<out[i].v.length; ++j) {\n\t\t\t\t\tif(jj<ostr.length) vv += ostr.charAt(jj++);\n\t\t\t\t}\n\t\t\t\tout[i].v = vv;\n\t\t\t\tout[i].t = 't';\n\t\t\t\tlasti = i;\n\t\t\t}\n\t\t}\n\t}\n\tfor(i=0; i<out.length; ++i) if(out[i] != null && 'n?'.indexOf(out[i].t)>-1) {\n\t\tmyv = (flen >1 && v < 0 && i>0 && out[i-1].v === \"-\" ? -v:v);\n\t\tout[i].v = write_num(out[i].t, out[i].v, myv);\n\t\tout[i].t = 't';\n\t}\n\tvar retval = \"\";\n\tfor(i=0; i !== out.length; ++i) if(out[i] != null) retval += out[i].v;\n\treturn retval;\n}\n\nvar cfregex2 = /\\[(=|>[=]?|<[>=]?)(-?\\d+(?:\\.\\d*)?)\\]/;\nfunction chkcond(v, rr) {\n\tif(rr == null) return false;\n\tvar thresh = parseFloat(rr[2]);\n\tswitch(rr[1]) {\n\t\tcase \"=\":  if(v == thresh) return true; break;\n\t\tcase \">\":  if(v >  thresh) return true; break;\n\t\tcase \"<\":  if(v <  thresh) return true; break;\n\t\tcase \"<>\": if(v != thresh) return true; break;\n\t\tcase \">=\": if(v >= thresh) return true; break;\n\t\tcase \"<=\": if(v <= thresh) return true; break;\n\t}\n\treturn false;\n}\nfunction choose_fmt(f/*:string*/, v/*:any*/) {\n\tvar fmt = SSF_split_fmt(f);\n\tvar l = fmt.length, lat = fmt[l-1].indexOf(\"@\");\n\tif(l<4 && lat>-1) --l;\n\tif(fmt.length > 4) throw new Error(\"cannot find right format for |\" + fmt.join(\"|\") + \"|\");\n\tif(typeof v !== \"number\") return [4, fmt.length === 4 || lat>-1?fmt[fmt.length-1]:\"@\"];\n\tswitch(fmt.length) {\n\t\tcase 1: fmt = lat>-1 ? [\"General\", \"General\", \"General\", fmt[0]] : [fmt[0], fmt[0], fmt[0], \"@\"]; break;\n\t\tcase 2: fmt = lat>-1 ? [fmt[0], fmt[0], fmt[0], fmt[1]] : [fmt[0], fmt[1], fmt[0], \"@\"]; break;\n\t\tcase 3: fmt = lat>-1 ? [fmt[0], fmt[1], fmt[0], fmt[2]] : [fmt[0], fmt[1], fmt[2], \"@\"]; break;\n\t\tcase 4: break;\n\t}\n\tvar ff = v > 0 ? fmt[0] : v < 0 ? fmt[1] : fmt[2];\n\tif(fmt[0].indexOf(\"[\") === -1 && fmt[1].indexOf(\"[\") === -1) return [l, ff];\n\tif(fmt[0].match(/\\[[=<>]/) != null || fmt[1].match(/\\[[=<>]/) != null) {\n\t\tvar m1 = fmt[0].match(cfregex2);\n\t\tvar m2 = fmt[1].match(cfregex2);\n\t\treturn chkcond(v, m1) ? [l, fmt[0]] : chkcond(v, m2) ? [l, fmt[1]] : [l, fmt[m1 != null && m2 != null ? 2 : 1]];\n\t}\n\treturn [l, ff];\n}\nfunction SSF_format(fmt/*:string|number*/,v/*:any*/,o/*:?any*/) {\n\tif(o == null) o = {};\n\tvar sfmt = \"\";\n\tswitch(typeof fmt) {\n\t\tcase \"string\":\n\t\t\tif(fmt == \"m/d/yy\" && o.dateNF) sfmt = o.dateNF;\n\t\t\telse sfmt = fmt;\n\t\t\tbreak;\n\t\tcase \"number\":\n\t\t\tif(fmt == 14 && o.dateNF) sfmt = o.dateNF;\n\t\t\telse sfmt = (o.table != null ? (o.table/*:any*/) : table_fmt)[fmt];\n\t\t\tif(sfmt == null) sfmt = (o.table && o.table[SSF_default_map[fmt]]) || table_fmt[SSF_default_map[fmt]];\n\t\t\tif(sfmt == null) sfmt = SSF_default_str[fmt] || \"General\";\n\t\t\tbreak;\n\t}\n\tif(SSF_isgeneral(sfmt,0)) return SSF_general(v, o);\n\tif(v instanceof Date) v = datenum_local(v, o.date1904);\n\tvar f = choose_fmt(sfmt, v);\n\tif(SSF_isgeneral(f[1])) return SSF_general(v, o);\n\tif(v === true) v = \"TRUE\"; else if(v === false) v = \"FALSE\";\n\telse if(v === \"\" || v == null) return \"\";\n\treturn eval_fmt(f[1], v, o, f[0]);\n}\nfunction SSF_load(fmt/*:string*/, idx/*:?number*/)/*:number*/ {\n\tif(typeof idx != 'number') {\n\t\tidx = +idx || -1;\n/*::if(typeof idx != 'number') return 0x188; */\n\t\tfor(var i = 0; i < 0x0188; ++i) {\n/*::if(typeof idx != 'number') return 0x188; */\n\t\t\tif(table_fmt[i] == undefined) { if(idx < 0) idx = i; continue; }\n\t\t\tif(table_fmt[i] == fmt) { idx = i; break; }\n\t\t}\n/*::if(typeof idx != 'number') return 0x188; */\n\t\tif(idx < 0) idx = 0x187;\n\t}\n/*::if(typeof idx != 'number') return 0x188; */\n\ttable_fmt[idx] = fmt;\n\treturn idx;\n}\nfunction SSF_load_table(tbl/*:SSFTable*/)/*:void*/ {\n\tfor(var i=0; i!=0x0188; ++i)\n\t\tif(tbl[i] !== undefined) SSF_load(tbl[i], i);\n}\n\nfunction make_ssf() {\n\ttable_fmt = SSF_init_table();\n}\n\nvar SSF = {\n\tformat: SSF_format,\n\tload: SSF_load,\n\t_table: table_fmt,\n\tload_table: SSF_load_table,\n\tparse_date_code: SSF_parse_date_code,\n\tis_date: fmt_is_date,\n\tget_table: function get_table() { return SSF._table = table_fmt; }\n};\n\nvar SSFImplicit/*{[number]:string}*/ = ({\n\t\"5\": '\"$\"#,##0_);\\\\(\"$\"#,##0\\\\)',\n\t\"6\": '\"$\"#,##0_);[Red]\\\\(\"$\"#,##0\\\\)',\n\t\"7\": '\"$\"#,##0.00_);\\\\(\"$\"#,##0.00\\\\)',\n\t\"8\": '\"$\"#,##0.00_);[Red]\\\\(\"$\"#,##0.00\\\\)',\n\t\"23\": 'General', \"24\": 'General', \"25\": 'General', \"26\": 'General',\n\t\"27\": 'm/d/yy', \"28\": 'm/d/yy', \"29\": 'm/d/yy', \"30\": 'm/d/yy', \"31\": 'm/d/yy',\n\t\"32\": 'h:mm:ss', \"33\": 'h:mm:ss', \"34\": 'h:mm:ss', \"35\": 'h:mm:ss',\n\t\"36\": 'm/d/yy',\n\t\"41\": '_(* #,##0_);_(* \\(#,##0\\);_(* \"-\"_);_(@_)',\n\t\"42\": '_(\"$\"* #,##0_);_(\"$\"* \\(#,##0\\);_(\"$\"* \"-\"_);_(@_)',\n\t\"43\": '_(* #,##0.00_);_(* \\(#,##0.00\\);_(* \"-\"??_);_(@_)',\n\t\"44\": '_(\"$\"* #,##0.00_);_(\"$\"* \\(#,##0.00\\);_(\"$\"* \"-\"??_);_(@_)',\n\t\"50\": 'm/d/yy', \"51\": 'm/d/yy', \"52\": 'm/d/yy', \"53\": 'm/d/yy', \"54\": 'm/d/yy',\n\t\"55\": 'm/d/yy', \"56\": 'm/d/yy', \"57\": 'm/d/yy', \"58\": 'm/d/yy',\n\t\"59\": '0',\n\t\"60\": '0.00',\n\t\"61\": '#,##0',\n\t\"62\": '#,##0.00',\n\t\"63\": '\"$\"#,##0_);\\\\(\"$\"#,##0\\\\)',\n\t\"64\": '\"$\"#,##0_);[Red]\\\\(\"$\"#,##0\\\\)',\n\t\"65\": '\"$\"#,##0.00_);\\\\(\"$\"#,##0.00\\\\)',\n\t\"66\": '\"$\"#,##0.00_);[Red]\\\\(\"$\"#,##0.00\\\\)',\n\t\"67\": '0%',\n\t\"68\": '0.00%',\n\t\"69\": '# ?/?',\n\t\"70\": '# ??/??',\n\t\"71\": 'm/d/yy',\n\t\"72\": 'm/d/yy',\n\t\"73\": 'd-mmm-yy',\n\t\"74\": 'd-mmm',\n\t\"75\": 'mmm-yy',\n\t\"76\": 'h:mm',\n\t\"77\": 'h:mm:ss',\n\t\"78\": 'm/d/yy h:mm',\n\t\"79\": 'mm:ss',\n\t\"80\": '[h]:mm:ss',\n\t\"81\": 'mmss.0'\n}/*:any*/);\n\n/* dateNF parse TODO: move to SSF */\nvar dateNFregex = /[dD]+|[mM]+|[yYeE]+|[Hh]+|[Ss]+/g;\nfunction dateNF_regex(dateNF/*:string|number*/)/*:RegExp*/ {\n\tvar fmt = typeof dateNF == \"number\" ? table_fmt[dateNF] : dateNF;\n\tfmt = fmt.replace(dateNFregex, \"(\\\\d+)\");\n\treturn new RegExp(\"^\" + fmt + \"$\");\n}\nfunction dateNF_fix(str/*:string*/, dateNF/*:string*/, match/*:Array<string>*/)/*:string*/ {\n\tvar Y = -1, m = -1, d = -1, H = -1, M = -1, S = -1;\n\t(dateNF.match(dateNFregex)||[]).forEach(function(n, i) {\n\t\tvar v = parseInt(match[i+1], 10);\n\t\tswitch(n.toLowerCase().charAt(0)) {\n\t\t\tcase 'y': Y = v; break; case 'd': d = v; break;\n\t\t\tcase 'h': H = v; break; case 's': S = v; break;\n\t\t\tcase 'm': if(H >= 0) M = v; else m = v; break;\n\t\t}\n\t});\n\tif(S >= 0 && M == -1 && m >= 0) { M = m; m = -1; }\n\tvar datestr = ((\"\" + (Y>=0?Y: new Date().getFullYear())).slice(-4) + \"-\" + (\"00\" + (m>=1?m:1)).slice(-2) + \"-\" + (\"00\" + (d>=1?d:1)).slice(-2));\n\tif(datestr.length == 7) datestr = \"0\" + datestr;\n\tif(datestr.length == 8) datestr = \"20\" + datestr;\n\tvar timestr = ((\"00\" + (H>=0?H:0)).slice(-2) + \":\" + (\"00\" + (M>=0?M:0)).slice(-2) + \":\" + (\"00\" + (S>=0?S:0)).slice(-2));\n\tif(H == -1 && M == -1 && S == -1) return datestr;\n\tif(Y == -1 && m == -1 && d == -1) return timestr;\n\treturn datestr + \"T\" + timestr;\n}\n\n/*::\ndeclare var ReadShift:any;\ndeclare var CheckField:any;\ndeclare var prep_blob:any;\ndeclare var __readUInt32LE:any;\ndeclare var __readInt32LE:any;\ndeclare var __toBuffer:any;\ndeclare var __utf16le:any;\ndeclare var bconcat:any;\ndeclare var s2a:any;\ndeclare var chr0:any;\ndeclare var chr1:any;\ndeclare var has_buf:boolean;\ndeclare var new_buf:any;\ndeclare var new_raw_buf:any;\ndeclare var new_unsafe_buf:any;\ndeclare var Buffer_from:any;\n*/\n/* cfb.js (C) 2013-present SheetJS -- http://sheetjs.com */\n/* vim: set ts=2: */\n/*jshint eqnull:true */\n/*exported CFB */\n/*global Uint8Array:false, Uint16Array:false */\n\n/*::\ntype SectorEntry = {\n\tname?:string;\n\tnodes?:Array<number>;\n\tdata:RawBytes;\n};\ntype SectorList = {\n\t[k:string|number]:SectorEntry;\n\tname:?string;\n\tfat_addrs:Array<number>;\n\tssz:number;\n}\ntype CFBFiles = {[n:string]:CFBEntry};\n*/\n/* crc32.js (C) 2014-present SheetJS -- http://sheetjs.com */\n/* vim: set ts=2: */\n/*exported CRC32 */\nvar CRC32 = /*#__PURE__*/(function() {\nvar CRC32 = {};\nCRC32.version = '1.2.0';\n/* see perf/crc32table.js */\n/*global Int32Array */\nfunction signed_crc_table()/*:any*/ {\n\tvar c = 0, table/*:Array<number>*/ = new Array(256);\n\n\tfor(var n =0; n != 256; ++n){\n\t\tc = n;\n\t\tc = ((c&1) ? (-306674912 ^ (c >>> 1)) : (c >>> 1));\n\t\tc = ((c&1) ? (-306674912 ^ (c >>> 1)) : (c >>> 1));\n\t\tc = ((c&1) ? (-306674912 ^ (c >>> 1)) : (c >>> 1));\n\t\tc = ((c&1) ? (-306674912 ^ (c >>> 1)) : (c >>> 1));\n\t\tc = ((c&1) ? (-306674912 ^ (c >>> 1)) : (c >>> 1));\n\t\tc = ((c&1) ? (-306674912 ^ (c >>> 1)) : (c >>> 1));\n\t\tc = ((c&1) ? (-306674912 ^ (c >>> 1)) : (c >>> 1));\n\t\tc = ((c&1) ? (-306674912 ^ (c >>> 1)) : (c >>> 1));\n\t\ttable[n] = c;\n\t}\n\n\treturn typeof Int32Array !== 'undefined' ? new Int32Array(table) : table;\n}\n\nvar T0 = signed_crc_table();\nfunction slice_by_16_tables(T) {\n\tvar c = 0, v = 0, n = 0, table/*:Array<number>*/ = typeof Int32Array !== 'undefined' ? new Int32Array(4096) : new Array(4096) ;\n\n\tfor(n = 0; n != 256; ++n) table[n] = T[n];\n\tfor(n = 0; n != 256; ++n) {\n\t\tv = T[n];\n\t\tfor(c = 256 + n; c < 4096; c += 256) v = table[c] = (v >>> 8) ^ T[v & 0xFF];\n\t}\n\tvar out = [];\n\tfor(n = 1; n != 16; ++n) out[n - 1] = typeof Int32Array !== 'undefined' ? table.subarray(n * 256, n * 256 + 256) : table.slice(n * 256, n * 256 + 256);\n\treturn out;\n}\nvar TT = slice_by_16_tables(T0);\nvar T1 = TT[0],  T2 = TT[1],  T3 = TT[2],  T4 = TT[3],  T5 = TT[4];\nvar T6 = TT[5],  T7 = TT[6],  T8 = TT[7],  T9 = TT[8],  Ta = TT[9];\nvar Tb = TT[10], Tc = TT[11], Td = TT[12], Te = TT[13], Tf = TT[14];\nfunction crc32_bstr(bstr/*:string*/, seed/*:number*/)/*:number*/ {\n\tvar C = seed/*:: ? 0 : 0 */ ^ -1;\n\tfor(var i = 0, L = bstr.length; i < L;) C = (C>>>8) ^ T0[(C^bstr.charCodeAt(i++))&0xFF];\n\treturn ~C;\n}\n\nfunction crc32_buf(B/*:Uint8Array|Array<number>*/, seed/*:number*/)/*:number*/ {\n\tvar C = seed/*:: ? 0 : 0 */ ^ -1, L = B.length - 15, i = 0;\n\tfor(; i < L;) C =\n\t\tTf[B[i++] ^ (C & 255)] ^\n\t\tTe[B[i++] ^ ((C >> 8) & 255)] ^\n\t\tTd[B[i++] ^ ((C >> 16) & 255)] ^\n\t\tTc[B[i++] ^ (C >>> 24)] ^\n\t\tTb[B[i++]] ^ Ta[B[i++]] ^ T9[B[i++]] ^ T8[B[i++]] ^\n\t\tT7[B[i++]] ^ T6[B[i++]] ^ T5[B[i++]] ^ T4[B[i++]] ^\n\t\tT3[B[i++]] ^ T2[B[i++]] ^ T1[B[i++]] ^ T0[B[i++]];\n\tL += 15;\n\twhile(i < L) C = (C>>>8) ^ T0[(C^B[i++])&0xFF];\n\treturn ~C;\n}\n\nfunction crc32_str(str/*:string*/, seed/*:number*/)/*:number*/ {\n\tvar C = seed ^ -1;\n\tfor(var i = 0, L = str.length, c = 0, d = 0; i < L;) {\n\t\tc = str.charCodeAt(i++);\n\t\tif(c < 0x80) {\n\t\t\tC = (C>>>8) ^ T0[(C^c)&0xFF];\n\t\t} else if(c < 0x800) {\n\t\t\tC = (C>>>8) ^ T0[(C ^ (192|((c>>6)&31)))&0xFF];\n\t\t\tC = (C>>>8) ^ T0[(C ^ (128|(c&63)))&0xFF];\n\t\t} else if(c >= 0xD800 && c < 0xE000) {\n\t\t\tc = (c&1023)+64; d = str.charCodeAt(i++)&1023;\n\t\t\tC = (C>>>8) ^ T0[(C ^ (240|((c>>8)&7)))&0xFF];\n\t\t\tC = (C>>>8) ^ T0[(C ^ (128|((c>>2)&63)))&0xFF];\n\t\t\tC = (C>>>8) ^ T0[(C ^ (128|((d>>6)&15)|((c&3)<<4)))&0xFF];\n\t\t\tC = (C>>>8) ^ T0[(C ^ (128|(d&63)))&0xFF];\n\t\t} else {\n\t\t\tC = (C>>>8) ^ T0[(C ^ (224|((c>>12)&15)))&0xFF];\n\t\t\tC = (C>>>8) ^ T0[(C ^ (128|((c>>6)&63)))&0xFF];\n\t\t\tC = (C>>>8) ^ T0[(C ^ (128|(c&63)))&0xFF];\n\t\t}\n\t}\n\treturn ~C;\n}\nCRC32.table = T0;\nCRC32.bstr = crc32_bstr;\nCRC32.buf = crc32_buf;\nCRC32.str = crc32_str;\nreturn CRC32;\n})();\n/* [MS-CFB] v20171201 */\nvar CFB = /*#__PURE__*/(function _CFB(){\nvar exports = {};\nexports.version = '1.2.1';\n/* [MS-CFB] 2.6.4 */\nfunction namecmp(l/*:string*/, r/*:string*/)/*:number*/ {\n\tvar L = l.split(\"/\"), R = r.split(\"/\");\n\tfor(var i = 0, c = 0, Z = Math.min(L.length, R.length); i < Z; ++i) {\n\t\tif((c = L[i].length - R[i].length)) return c;\n\t\tif(L[i] != R[i]) return L[i] < R[i] ? -1 : 1;\n\t}\n\treturn L.length - R.length;\n}\nfunction dirname(p/*:string*/)/*:string*/ {\n\tif(p.charAt(p.length - 1) == \"/\") return (p.slice(0,-1).indexOf(\"/\") === -1) ? p : dirname(p.slice(0, -1));\n\tvar c = p.lastIndexOf(\"/\");\n\treturn (c === -1) ? p : p.slice(0, c+1);\n}\n\nfunction filename(p/*:string*/)/*:string*/ {\n\tif(p.charAt(p.length - 1) == \"/\") return filename(p.slice(0, -1));\n\tvar c = p.lastIndexOf(\"/\");\n\treturn (c === -1) ? p : p.slice(c+1);\n}\n/* -------------------------------------------------------------------------- */\n/* DOS Date format:\n   high|YYYYYYYm.mmmddddd.HHHHHMMM.MMMSSSSS|low\n   add 1980 to stored year\n   stored second should be doubled\n*/\n\n/* write JS date to buf as a DOS date */\nfunction write_dos_date(buf/*:CFBlob*/, date/*:Date|string*/) {\n\tif(typeof date === \"string\") date = new Date(date);\n\tvar hms/*:number*/ = date.getHours();\n\thms = hms << 6 | date.getMinutes();\n\thms = hms << 5 | (date.getSeconds()>>>1);\n\tbuf.write_shift(2, hms);\n\tvar ymd/*:number*/ = (date.getFullYear() - 1980);\n\tymd = ymd << 4 | (date.getMonth()+1);\n\tymd = ymd << 5 | date.getDate();\n\tbuf.write_shift(2, ymd);\n}\n\n/* read four bytes from buf and interpret as a DOS date */\nfunction parse_dos_date(buf/*:CFBlob*/)/*:Date*/ {\n\tvar hms = buf.read_shift(2) & 0xFFFF;\n\tvar ymd = buf.read_shift(2) & 0xFFFF;\n\tvar val = new Date();\n\tvar d = ymd & 0x1F; ymd >>>= 5;\n\tvar m = ymd & 0x0F; ymd >>>= 4;\n\tval.setMilliseconds(0);\n\tval.setFullYear(ymd + 1980);\n\tval.setMonth(m-1);\n\tval.setDate(d);\n\tvar S = hms & 0x1F; hms >>>= 5;\n\tvar M = hms & 0x3F; hms >>>= 6;\n\tval.setHours(hms);\n\tval.setMinutes(M);\n\tval.setSeconds(S<<1);\n\treturn val;\n}\nfunction parse_extra_field(blob/*:CFBlob*/)/*:any*/ {\n\tprep_blob(blob, 0);\n\tvar o = /*::(*/{}/*:: :any)*/;\n\tvar flags = 0;\n\twhile(blob.l <= blob.length - 4) {\n\t\tvar type = blob.read_shift(2);\n\t\tvar sz = blob.read_shift(2), tgt = blob.l + sz;\n\t\tvar p = {};\n\t\tswitch(type) {\n\t\t\t/* UNIX-style Timestamps */\n\t\t\tcase 0x5455: {\n\t\t\t\tflags = blob.read_shift(1);\n\t\t\t\tif(flags & 1) p.mtime = blob.read_shift(4);\n\t\t\t\t/* for some reason, CD flag corresponds to LFH */\n\t\t\t\tif(sz > 5) {\n\t\t\t\t\tif(flags & 2) p.atime = blob.read_shift(4);\n\t\t\t\t\tif(flags & 4) p.ctime = blob.read_shift(4);\n\t\t\t\t}\n\t\t\t\tif(p.mtime) p.mt = new Date(p.mtime*1000);\n\t\t\t}\n\t\t\tbreak;\n\t\t}\n\t\tblob.l = tgt;\n\t\to[type] = p;\n\t}\n\treturn o;\n}\nvar fs/*:: = require('fs'); */;\nfunction get_fs() { return fs || (fs = {}); }\nfunction parse(file/*:RawBytes*/, options/*:CFBReadOpts*/)/*:CFBContainer*/ {\nif(file[0] == 0x50 && file[1] == 0x4b) return parse_zip(file, options);\nif((file[0] | 0x20) == 0x6d && (file[1]|0x20) == 0x69) return parse_mad(file, options);\nif(file.length < 512) throw new Error(\"CFB file size \" + file.length + \" < 512\");\nvar mver = 3;\nvar ssz = 512;\nvar nmfs = 0; // number of mini FAT sectors\nvar difat_sec_cnt = 0;\nvar dir_start = 0;\nvar minifat_start = 0;\nvar difat_start = 0;\n\nvar fat_addrs/*:Array<number>*/ = []; // locations of FAT sectors\n\n/* [MS-CFB] 2.2 Compound File Header */\nvar blob/*:CFBlob*/ = /*::(*/file.slice(0,512)/*:: :any)*/;\nprep_blob(blob, 0);\n\n/* major version */\nvar mv = check_get_mver(blob);\nmver = mv[0];\nswitch(mver) {\n\tcase 3: ssz = 512; break; case 4: ssz = 4096; break;\n\tcase 0: if(mv[1] == 0) return parse_zip(file, options);\n\t/* falls through */\n\tdefault: throw new Error(\"Major Version: Expected 3 or 4 saw \" + mver);\n}\n\n/* reprocess header */\nif(ssz !== 512) { blob = /*::(*/file.slice(0,ssz)/*:: :any)*/; prep_blob(blob, 28 /* blob.l */); }\n/* Save header for final object */\nvar header/*:RawBytes*/ = file.slice(0,ssz);\n\ncheck_shifts(blob, mver);\n\n// Number of Directory Sectors\nvar dir_cnt/*:number*/ = blob.read_shift(4, 'i');\nif(mver === 3 && dir_cnt !== 0) throw new Error('# Directory Sectors: Expected 0 saw ' + dir_cnt);\n\n// Number of FAT Sectors\nblob.l += 4;\n\n// First Directory Sector Location\ndir_start = blob.read_shift(4, 'i');\n\n// Transaction Signature\nblob.l += 4;\n\n// Mini Stream Cutoff Size\nblob.chk('00100000', 'Mini Stream Cutoff Size: ');\n\n// First Mini FAT Sector Location\nminifat_start = blob.read_shift(4, 'i');\n\n// Number of Mini FAT Sectors\nnmfs = blob.read_shift(4, 'i');\n\n// First DIFAT sector location\ndifat_start = blob.read_shift(4, 'i');\n\n// Number of DIFAT Sectors\ndifat_sec_cnt = blob.read_shift(4, 'i');\n\n// Grab FAT Sector Locations\nfor(var q = -1, j = 0; j < 109; ++j) { /* 109 = (512 - blob.l)>>>2; */\n\tq = blob.read_shift(4, 'i');\n\tif(q<0) break;\n\tfat_addrs[j] = q;\n}\n\n/** Break the file up into sectors */\nvar sectors/*:Array<RawBytes>*/ = sectorify(file, ssz);\n\nsleuth_fat(difat_start, difat_sec_cnt, sectors, ssz, fat_addrs);\n\n/** Chains */\nvar sector_list/*:SectorList*/ = make_sector_list(sectors, dir_start, fat_addrs, ssz);\n\nsector_list[dir_start].name = \"!Directory\";\nif(nmfs > 0 && minifat_start !== ENDOFCHAIN) sector_list[minifat_start].name = \"!MiniFAT\";\nsector_list[fat_addrs[0]].name = \"!FAT\";\nsector_list.fat_addrs = fat_addrs;\nsector_list.ssz = ssz;\n\n/* [MS-CFB] 2.6.1 Compound File Directory Entry */\nvar files/*:CFBFiles*/ = {}, Paths/*:Array<string>*/ = [], FileIndex/*:CFBFileIndex*/ = [], FullPaths/*:Array<string>*/ = [];\nread_directory(dir_start, sector_list, sectors, Paths, nmfs, files, FileIndex, minifat_start);\n\nbuild_full_paths(FileIndex, FullPaths, Paths);\nPaths.shift();\n\nvar o = {\n\tFileIndex: FileIndex,\n\tFullPaths: FullPaths\n};\n\n// $FlowIgnore\nif(options && options.raw) o.raw = {header: header, sectors: sectors};\nreturn o;\n} // parse\n\n/* [MS-CFB] 2.2 Compound File Header -- read up to major version */\nfunction check_get_mver(blob/*:CFBlob*/)/*:[number, number]*/ {\n\tif(blob[blob.l] == 0x50 && blob[blob.l + 1] == 0x4b) return [0, 0];\n\t// header signature 8\n\tblob.chk(HEADER_SIGNATURE, 'Header Signature: ');\n\n\t// clsid 16\n\t//blob.chk(HEADER_CLSID, 'CLSID: ');\n\tblob.l += 16;\n\n\t// minor version 2\n\tvar mver/*:number*/ = blob.read_shift(2, 'u');\n\n\treturn [blob.read_shift(2,'u'), mver];\n}\nfunction check_shifts(blob/*:CFBlob*/, mver/*:number*/)/*:void*/ {\n\tvar shift = 0x09;\n\n\t// Byte Order\n\t//blob.chk('feff', 'Byte Order: '); // note: some writers put 0xffff\n\tblob.l += 2;\n\n\t// Sector Shift\n\tswitch((shift = blob.read_shift(2))) {\n\t\tcase 0x09: if(mver != 3) throw new Error('Sector Shift: Expected 9 saw ' + shift); break;\n\t\tcase 0x0c: if(mver != 4) throw new Error('Sector Shift: Expected 12 saw ' + shift); break;\n\t\tdefault: throw new Error('Sector Shift: Expected 9 or 12 saw ' + shift);\n\t}\n\n\t// Mini Sector Shift\n\tblob.chk('0600', 'Mini Sector Shift: ');\n\n\t// Reserved\n\tblob.chk('000000000000', 'Reserved: ');\n}\n\n/** Break the file up into sectors */\nfunction sectorify(file/*:RawBytes*/, ssz/*:number*/)/*:Array<RawBytes>*/ {\n\tvar nsectors = Math.ceil(file.length/ssz)-1;\n\tvar sectors/*:Array<RawBytes>*/ = [];\n\tfor(var i=1; i < nsectors; ++i) sectors[i-1] = file.slice(i*ssz,(i+1)*ssz);\n\tsectors[nsectors-1] = file.slice(nsectors*ssz);\n\treturn sectors;\n}\n\n/* [MS-CFB] 2.6.4 Red-Black Tree */\nfunction build_full_paths(FI/*:CFBFileIndex*/, FP/*:Array<string>*/, Paths/*:Array<string>*/)/*:void*/ {\n\tvar i = 0, L = 0, R = 0, C = 0, j = 0, pl = Paths.length;\n\tvar dad/*:Array<number>*/ = [], q/*:Array<number>*/ = [];\n\n\tfor(; i < pl; ++i) { dad[i]=q[i]=i; FP[i]=Paths[i]; }\n\n\tfor(; j < q.length; ++j) {\n\t\ti = q[j];\n\t\tL = FI[i].L; R = FI[i].R; C = FI[i].C;\n\t\tif(dad[i] === i) {\n\t\t\tif(L !== -1 /*NOSTREAM*/ && dad[L] !== L) dad[i] = dad[L];\n\t\t\tif(R !== -1 && dad[R] !== R) dad[i] = dad[R];\n\t\t}\n\t\tif(C !== -1 /*NOSTREAM*/) dad[C] = i;\n\t\tif(L !== -1 && i != dad[i]) { dad[L] = dad[i]; if(q.lastIndexOf(L) < j) q.push(L); }\n\t\tif(R !== -1 && i != dad[i]) { dad[R] = dad[i]; if(q.lastIndexOf(R) < j) q.push(R); }\n\t}\n\tfor(i=1; i < pl; ++i) if(dad[i] === i) {\n\t\tif(R !== -1 /*NOSTREAM*/ && dad[R] !== R) dad[i] = dad[R];\n\t\telse if(L !== -1 && dad[L] !== L) dad[i] = dad[L];\n\t}\n\n\tfor(i=1; i < pl; ++i) {\n\t\tif(FI[i].type === 0 /* unknown */) continue;\n\t\tj = i;\n\t\tif(j != dad[j]) do {\n\t\t\tj = dad[j];\n\t\t\tFP[i] = FP[j] + \"/\" + FP[i];\n\t\t} while (j !== 0 && -1 !== dad[j] && j != dad[j]);\n\t\tdad[i] = -1;\n\t}\n\n\tFP[0] += \"/\";\n\tfor(i=1; i < pl; ++i) {\n\t\tif(FI[i].type !== 2 /* stream */) FP[i] += \"/\";\n\t}\n}\n\nfunction get_mfat_entry(entry/*:CFBEntry*/, payload/*:RawBytes*/, mini/*:?RawBytes*/)/*:CFBlob*/ {\n\tvar start = entry.start, size = entry.size;\n\t//return (payload.slice(start*MSSZ, start*MSSZ + size)/*:any*/);\n\tvar o = [];\n\tvar idx = start;\n\twhile(mini && size > 0 && idx >= 0) {\n\t\to.push(payload.slice(idx * MSSZ, idx * MSSZ + MSSZ));\n\t\tsize -= MSSZ;\n\t\tidx = __readInt32LE(mini, idx * 4);\n\t}\n\tif(o.length === 0) return (new_buf(0)/*:any*/);\n\treturn (bconcat(o).slice(0, entry.size)/*:any*/);\n}\n\n/** Chase down the rest of the DIFAT chain to build a comprehensive list\n    DIFAT chains by storing the next sector number as the last 32 bits */\nfunction sleuth_fat(idx/*:number*/, cnt/*:number*/, sectors/*:Array<RawBytes>*/, ssz/*:number*/, fat_addrs)/*:void*/ {\n\tvar q/*:number*/ = ENDOFCHAIN;\n\tif(idx === ENDOFCHAIN) {\n\t\tif(cnt !== 0) throw new Error(\"DIFAT chain shorter than expected\");\n\t} else if(idx !== -1 /*FREESECT*/) {\n\t\tvar sector = sectors[idx], m = (ssz>>>2)-1;\n\t\tif(!sector) return;\n\t\tfor(var i = 0; i < m; ++i) {\n\t\t\tif((q = __readInt32LE(sector,i*4)) === ENDOFCHAIN) break;\n\t\t\tfat_addrs.push(q);\n\t\t}\n\t\tsleuth_fat(__readInt32LE(sector,ssz-4),cnt - 1, sectors, ssz, fat_addrs);\n\t}\n}\n\n/** Follow the linked list of sectors for a given starting point */\nfunction get_sector_list(sectors/*:Array<RawBytes>*/, start/*:number*/, fat_addrs/*:Array<number>*/, ssz/*:number*/, chkd/*:?Array<boolean>*/)/*:SectorEntry*/ {\n\tvar buf/*:Array<number>*/ = [], buf_chain/*:Array<any>*/ = [];\n\tif(!chkd) chkd = [];\n\tvar modulus = ssz - 1, j = 0, jj = 0;\n\tfor(j=start; j>=0;) {\n\t\tchkd[j] = true;\n\t\tbuf[buf.length] = j;\n\t\tbuf_chain.push(sectors[j]);\n\t\tvar addr = fat_addrs[Math.floor(j*4/ssz)];\n\t\tjj = ((j*4) & modulus);\n\t\tif(ssz < 4 + jj) throw new Error(\"FAT boundary crossed: \" + j + \" 4 \"+ssz);\n\t\tif(!sectors[addr]) break;\n\t\tj = __readInt32LE(sectors[addr], jj);\n\t}\n\treturn {nodes: buf, data:__toBuffer([buf_chain])};\n}\n\n/** Chase down the sector linked lists */\nfunction make_sector_list(sectors/*:Array<RawBytes>*/, dir_start/*:number*/, fat_addrs/*:Array<number>*/, ssz/*:number*/)/*:SectorList*/ {\n\tvar sl = sectors.length, sector_list/*:SectorList*/ = ([]/*:any*/);\n\tvar chkd/*:Array<boolean>*/ = [], buf/*:Array<number>*/ = [], buf_chain/*:Array<RawBytes>*/ = [];\n\tvar modulus = ssz - 1, i=0, j=0, k=0, jj=0;\n\tfor(i=0; i < sl; ++i) {\n\t\tbuf = ([]/*:Array<number>*/);\n\t\tk = (i + dir_start); if(k >= sl) k-=sl;\n\t\tif(chkd[k]) continue;\n\t\tbuf_chain = [];\n\t\tvar seen = [];\n\t\tfor(j=k; j>=0;) {\n\t\t\tseen[j] = true;\n\t\t\tchkd[j] = true;\n\t\t\tbuf[buf.length] = j;\n\t\t\tbuf_chain.push(sectors[j]);\n\t\t\tvar addr/*:number*/ = fat_addrs[Math.floor(j*4/ssz)];\n\t\t\tjj = ((j*4) & modulus);\n\t\t\tif(ssz < 4 + jj) throw new Error(\"FAT boundary crossed: \" + j + \" 4 \"+ssz);\n\t\t\tif(!sectors[addr]) break;\n\t\t\tj = __readInt32LE(sectors[addr], jj);\n\t\t\tif(seen[j]) break;\n\t\t}\n\t\tsector_list[k] = ({nodes: buf, data:__toBuffer([buf_chain])}/*:SectorEntry*/);\n\t}\n\treturn sector_list;\n}\n\n/* [MS-CFB] 2.6.1 Compound File Directory Entry */\nfunction read_directory(dir_start/*:number*/, sector_list/*:SectorList*/, sectors/*:Array<RawBytes>*/, Paths/*:Array<string>*/, nmfs, files, FileIndex, mini) {\n\tvar minifat_store = 0, pl = (Paths.length?2:0);\n\tvar sector = sector_list[dir_start].data;\n\tvar i = 0, namelen = 0, name;\n\tfor(; i < sector.length; i+= 128) {\n\t\tvar blob/*:CFBlob*/ = /*::(*/sector.slice(i, i+128)/*:: :any)*/;\n\t\tprep_blob(blob, 64);\n\t\tnamelen = blob.read_shift(2);\n\t\tname = __utf16le(blob,0,namelen-pl);\n\t\tPaths.push(name);\n\t\tvar o/*:CFBEntry*/ = ({\n\t\t\tname:  name,\n\t\t\ttype:  blob.read_shift(1),\n\t\t\tcolor: blob.read_shift(1),\n\t\t\tL:     blob.read_shift(4, 'i'),\n\t\t\tR:     blob.read_shift(4, 'i'),\n\t\t\tC:     blob.read_shift(4, 'i'),\n\t\t\tclsid: blob.read_shift(16),\n\t\t\tstate: blob.read_shift(4, 'i'),\n\t\t\tstart: 0,\n\t\t\tsize: 0\n\t\t});\n\t\tvar ctime/*:number*/ = blob.read_shift(2) + blob.read_shift(2) + blob.read_shift(2) + blob.read_shift(2);\n\t\tif(ctime !== 0) o.ct = read_date(blob, blob.l-8);\n\t\tvar mtime/*:number*/ = blob.read_shift(2) + blob.read_shift(2) + blob.read_shift(2) + blob.read_shift(2);\n\t\tif(mtime !== 0) o.mt = read_date(blob, blob.l-8);\n\t\to.start = blob.read_shift(4, 'i');\n\t\to.size = blob.read_shift(4, 'i');\n\t\tif(o.size < 0 && o.start < 0) { o.size = o.type = 0; o.start = ENDOFCHAIN; o.name = \"\"; }\n\t\tif(o.type === 5) { /* root */\n\t\t\tminifat_store = o.start;\n\t\t\tif(nmfs > 0 && minifat_store !== ENDOFCHAIN) sector_list[minifat_store].name = \"!StreamData\";\n\t\t\t/*minifat_size = o.size;*/\n\t\t} else if(o.size >= 4096 /* MSCSZ */) {\n\t\t\to.storage = 'fat';\n\t\t\tif(sector_list[o.start] === undefined) sector_list[o.start] = get_sector_list(sectors, o.start, sector_list.fat_addrs, sector_list.ssz);\n\t\t\tsector_list[o.start].name = o.name;\n\t\t\to.content = (sector_list[o.start].data.slice(0,o.size)/*:any*/);\n\t\t} else {\n\t\t\to.storage = 'minifat';\n\t\t\tif(o.size < 0) o.size = 0;\n\t\t\telse if(minifat_store !== ENDOFCHAIN && o.start !== ENDOFCHAIN && sector_list[minifat_store]) {\n\t\t\t\to.content = get_mfat_entry(o, sector_list[minifat_store].data, (sector_list[mini]||{}).data);\n\t\t\t}\n\t\t}\n\t\tif(o.content) prep_blob(o.content, 0);\n\t\tfiles[name] = o;\n\t\tFileIndex.push(o);\n\t}\n}\n\nfunction read_date(blob/*:RawBytes|CFBlob*/, offset/*:number*/)/*:Date*/ {\n\treturn new Date(( ( (__readUInt32LE(blob,offset+4)/1e7)*Math.pow(2,32)+__readUInt32LE(blob,offset)/1e7 ) - 11644473600)*1000);\n}\n\nfunction read_file(filename/*:string*/, options/*:CFBReadOpts*/) {\n\tget_fs();\n\treturn parse(fs.readFileSync(filename), options);\n}\n\nfunction read(blob/*:RawBytes|string*/, options/*:CFBReadOpts*/) {\n\tvar type = options && options.type;\n\tif(!type) {\n\t\tif(has_buf && Buffer.isBuffer(blob)) type = \"buffer\";\n\t}\n\tswitch(type || \"base64\") {\n\t\tcase \"file\": /*:: if(typeof blob !== 'string') throw \"Must pass a filename when type='file'\"; */return read_file(blob, options);\n\t\tcase \"base64\": /*:: if(typeof blob !== 'string') throw \"Must pass a base64-encoded binary string when type='file'\"; */return parse(s2a(Base64_decode(blob)), options);\n\t\tcase \"binary\": /*:: if(typeof blob !== 'string') throw \"Must pass a binary string when type='file'\"; */return parse(s2a(blob), options);\n\t}\n\treturn parse(/*::typeof blob == 'string' ? new Buffer(blob, 'utf-8') : */blob, options);\n}\n\nfunction init_cfb(cfb/*:CFBContainer*/, opts/*:?any*/)/*:void*/ {\n\tvar o = opts || {}, root = o.root || \"Root Entry\";\n\tif(!cfb.FullPaths) cfb.FullPaths = [];\n\tif(!cfb.FileIndex) cfb.FileIndex = [];\n\tif(cfb.FullPaths.length !== cfb.FileIndex.length) throw new Error(\"inconsistent CFB structure\");\n\tif(cfb.FullPaths.length === 0) {\n\t\tcfb.FullPaths[0] = root + \"/\";\n\t\tcfb.FileIndex[0] = ({ name: root, type: 5 }/*:any*/);\n\t}\n\tif(o.CLSID) cfb.FileIndex[0].clsid = o.CLSID;\n\tseed_cfb(cfb);\n}\nfunction seed_cfb(cfb/*:CFBContainer*/)/*:void*/ {\n\tvar nm = \"\\u0001Sh33tJ5\";\n\tif(CFB.find(cfb, \"/\" + nm)) return;\n\tvar p = new_buf(4); p[0] = 55; p[1] = p[3] = 50; p[2] = 54;\n\tcfb.FileIndex.push(({ name: nm, type: 2, content:p, size:4, L:69, R:69, C:69 }/*:any*/));\n\tcfb.FullPaths.push(cfb.FullPaths[0] + nm);\n\trebuild_cfb(cfb);\n}\nfunction rebuild_cfb(cfb/*:CFBContainer*/, f/*:?boolean*/)/*:void*/ {\n\tinit_cfb(cfb);\n\tvar gc = false, s = false;\n\tfor(var i = cfb.FullPaths.length - 1; i >= 0; --i) {\n\t\tvar _file = cfb.FileIndex[i];\n\t\tswitch(_file.type) {\n\t\t\tcase 0:\n\t\t\t\tif(s) gc = true;\n\t\t\t\telse { cfb.FileIndex.pop(); cfb.FullPaths.pop(); }\n\t\t\t\tbreak;\n\t\t\tcase 1: case 2: case 5:\n\t\t\t\ts = true;\n\t\t\t\tif(isNaN(_file.R * _file.L * _file.C)) gc = true;\n\t\t\t\tif(_file.R > -1 && _file.L > -1 && _file.R == _file.L) gc = true;\n\t\t\t\tbreak;\n\t\t\tdefault: gc = true; break;\n\t\t}\n\t}\n\tif(!gc && !f) return;\n\n\tvar now = new Date(1987, 1, 19), j = 0;\n\t// Track which names exist\n\tvar fullPaths = Object.create ? Object.create(null) : {};\n\tvar data/*:Array<[string, CFBEntry]>*/ = [];\n\tfor(i = 0; i < cfb.FullPaths.length; ++i) {\n\t\tfullPaths[cfb.FullPaths[i]] = true;\n\t\tif(cfb.FileIndex[i].type === 0) continue;\n\t\tdata.push([cfb.FullPaths[i], cfb.FileIndex[i]]);\n\t}\n\tfor(i = 0; i < data.length; ++i) {\n\t\tvar dad = dirname(data[i][0]);\n\t\ts = fullPaths[dad];\n\t\tif(!s) {\n\t\t\tdata.push([dad, ({\n\t\t\t\tname: filename(dad).replace(\"/\",\"\"),\n\t\t\t\ttype: 1,\n\t\t\t\tclsid: HEADER_CLSID,\n\t\t\t\tct: now, mt: now,\n\t\t\t\tcontent: null\n\t\t\t}/*:any*/)]);\n\t\t\t// Add name to set\n\t\t\tfullPaths[dad] = true;\n\t\t}\n\t}\n\n\tdata.sort(function(x,y) { return namecmp(x[0], y[0]); });\n\tcfb.FullPaths = []; cfb.FileIndex = [];\n\tfor(i = 0; i < data.length; ++i) { cfb.FullPaths[i] = data[i][0]; cfb.FileIndex[i] = data[i][1]; }\n\tfor(i = 0; i < data.length; ++i) {\n\t\tvar elt = cfb.FileIndex[i];\n\t\tvar nm = cfb.FullPaths[i];\n\n\t\telt.name =  filename(nm).replace(\"/\",\"\");\n\t\telt.L = elt.R = elt.C = -(elt.color = 1);\n\t\telt.size = elt.content ? elt.content.length : 0;\n\t\telt.start = 0;\n\t\telt.clsid = (elt.clsid || HEADER_CLSID);\n\t\tif(i === 0) {\n\t\t\telt.C = data.length > 1 ? 1 : -1;\n\t\t\telt.size = 0;\n\t\t\telt.type = 5;\n\t\t} else if(nm.slice(-1) == \"/\") {\n\t\t\tfor(j=i+1;j < data.length; ++j) if(dirname(cfb.FullPaths[j])==nm) break;\n\t\t\telt.C = j >= data.length ? -1 : j;\n\t\t\tfor(j=i+1;j < data.length; ++j) if(dirname(cfb.FullPaths[j])==dirname(nm)) break;\n\t\t\telt.R = j >= data.length ? -1 : j;\n\t\t\telt.type = 1;\n\t\t} else {\n\t\t\tif(dirname(cfb.FullPaths[i+1]||\"\") == dirname(nm)) elt.R = i + 1;\n\t\t\telt.type = 2;\n\t\t}\n\t}\n\n}\n\nfunction _write(cfb/*:CFBContainer*/, options/*:CFBWriteOpts*/)/*:RawBytes|string*/ {\n\tvar _opts = options || {};\n\t/* MAD is order-sensitive, skip rebuild and sort */\n\tif(_opts.fileType == 'mad') return write_mad(cfb, _opts);\n\trebuild_cfb(cfb);\n\tswitch(_opts.fileType) {\n\t\tcase 'zip': return write_zip(cfb, _opts);\n\t\t//case 'mad': return write_mad(cfb, _opts);\n\t}\n\tvar L = (function(cfb/*:CFBContainer*/)/*:Array<number>*/{\n\t\tvar mini_size = 0, fat_size = 0;\n\t\tfor(var i = 0; i < cfb.FileIndex.length; ++i) {\n\t\t\tvar file = cfb.FileIndex[i];\n\t\t\tif(!file.content) continue;\n\t\t\t/*:: if(file.content == null) throw new Error(\"unreachable\"); */\n\t\t\tvar flen = file.content.length;\n\t\t\tif(flen > 0){\n\t\t\t\tif(flen < 0x1000) mini_size += (flen + 0x3F) >> 6;\n\t\t\t\telse fat_size += (flen + 0x01FF) >> 9;\n\t\t\t}\n\t\t}\n\t\tvar dir_cnt = (cfb.FullPaths.length +3) >> 2;\n\t\tvar mini_cnt = (mini_size + 7) >> 3;\n\t\tvar mfat_cnt = (mini_size + 0x7F) >> 7;\n\t\tvar fat_base = mini_cnt + fat_size + dir_cnt + mfat_cnt;\n\t\tvar fat_cnt = (fat_base + 0x7F) >> 7;\n\t\tvar difat_cnt = fat_cnt <= 109 ? 0 : Math.ceil((fat_cnt-109)/0x7F);\n\t\twhile(((fat_base + fat_cnt + difat_cnt + 0x7F) >> 7) > fat_cnt) difat_cnt = ++fat_cnt <= 109 ? 0 : Math.ceil((fat_cnt-109)/0x7F);\n\t\tvar L =  [1, difat_cnt, fat_cnt, mfat_cnt, dir_cnt, fat_size, mini_size, 0];\n\t\tcfb.FileIndex[0].size = mini_size << 6;\n\t\tL[7] = (cfb.FileIndex[0].start=L[0]+L[1]+L[2]+L[3]+L[4]+L[5])+((L[6]+7) >> 3);\n\t\treturn L;\n\t})(cfb);\n\tvar o = new_buf(L[7] << 9);\n\tvar i = 0, T = 0;\n\t{\n\t\tfor(i = 0; i < 8; ++i) o.write_shift(1, HEADER_SIG[i]);\n\t\tfor(i = 0; i < 8; ++i) o.write_shift(2, 0);\n\t\to.write_shift(2, 0x003E);\n\t\to.write_shift(2, 0x0003);\n\t\to.write_shift(2, 0xFFFE);\n\t\to.write_shift(2, 0x0009);\n\t\to.write_shift(2, 0x0006);\n\t\tfor(i = 0; i < 3; ++i) o.write_shift(2, 0);\n\t\to.write_shift(4, 0);\n\t\to.write_shift(4, L[2]);\n\t\to.write_shift(4, L[0] + L[1] + L[2] + L[3] - 1);\n\t\to.write_shift(4, 0);\n\t\to.write_shift(4, 1<<12);\n\t\to.write_shift(4, L[3] ? L[0] + L[1] + L[2] - 1: ENDOFCHAIN);\n\t\to.write_shift(4, L[3]);\n\t\to.write_shift(-4, L[1] ? L[0] - 1: ENDOFCHAIN);\n\t\to.write_shift(4, L[1]);\n\t\tfor(i = 0; i < 109; ++i) o.write_shift(-4, i < L[2] ? L[1] + i : -1);\n\t}\n\tif(L[1]) {\n\t\tfor(T = 0; T < L[1]; ++T) {\n\t\t\tfor(; i < 236 + T * 127; ++i) o.write_shift(-4, i < L[2] ? L[1] + i : -1);\n\t\t\to.write_shift(-4, T === L[1] - 1 ? ENDOFCHAIN : T + 1);\n\t\t}\n\t}\n\tvar chainit = function(w/*:number*/)/*:void*/ {\n\t\tfor(T += w; i<T-1; ++i) o.write_shift(-4, i+1);\n\t\tif(w) { ++i; o.write_shift(-4, ENDOFCHAIN); }\n\t};\n\tT = i = 0;\n\tfor(T+=L[1]; i<T; ++i) o.write_shift(-4, consts.DIFSECT);\n\tfor(T+=L[2]; i<T; ++i) o.write_shift(-4, consts.FATSECT);\n\tchainit(L[3]);\n\tchainit(L[4]);\n\tvar j/*:number*/ = 0, flen/*:number*/ = 0;\n\tvar file/*:CFBEntry*/ = cfb.FileIndex[0];\n\tfor(; j < cfb.FileIndex.length; ++j) {\n\t\tfile = cfb.FileIndex[j];\n\t\tif(!file.content) continue;\n\t\t/*:: if(file.content == null) throw new Error(\"unreachable\"); */\n\t\tflen = file.content.length;\n\t\tif(flen < 0x1000) continue;\n\t\tfile.start = T;\n\t\tchainit((flen + 0x01FF) >> 9);\n\t}\n\tchainit((L[6] + 7) >> 3);\n\twhile(o.l & 0x1FF) o.write_shift(-4, consts.ENDOFCHAIN);\n\tT = i = 0;\n\tfor(j = 0; j < cfb.FileIndex.length; ++j) {\n\t\tfile = cfb.FileIndex[j];\n\t\tif(!file.content) continue;\n\t\t/*:: if(file.content == null) throw new Error(\"unreachable\"); */\n\t\tflen = file.content.length;\n\t\tif(!flen || flen >= 0x1000) continue;\n\t\tfile.start = T;\n\t\tchainit((flen + 0x3F) >> 6);\n\t}\n\twhile(o.l & 0x1FF) o.write_shift(-4, consts.ENDOFCHAIN);\n\tfor(i = 0; i < L[4]<<2; ++i) {\n\t\tvar nm = cfb.FullPaths[i];\n\t\tif(!nm || nm.length === 0) {\n\t\t\tfor(j = 0; j < 17; ++j) o.write_shift(4, 0);\n\t\t\tfor(j = 0; j < 3; ++j) o.write_shift(4, -1);\n\t\t\tfor(j = 0; j < 12; ++j) o.write_shift(4, 0);\n\t\t\tcontinue;\n\t\t}\n\t\tfile = cfb.FileIndex[i];\n\t\tif(i === 0) file.start = file.size ? file.start - 1 : ENDOFCHAIN;\n\t\tvar _nm/*:string*/ = (i === 0 && _opts.root) || file.name;\n\t\tflen = 2*(_nm.length+1);\n\t\to.write_shift(64, _nm, \"utf16le\");\n\t\to.write_shift(2, flen);\n\t\to.write_shift(1, file.type);\n\t\to.write_shift(1, file.color);\n\t\to.write_shift(-4, file.L);\n\t\to.write_shift(-4, file.R);\n\t\to.write_shift(-4, file.C);\n\t\tif(!file.clsid) for(j = 0; j < 4; ++j) o.write_shift(4, 0);\n\t\telse o.write_shift(16, file.clsid, \"hex\");\n\t\to.write_shift(4, file.state || 0);\n\t\to.write_shift(4, 0); o.write_shift(4, 0);\n\t\to.write_shift(4, 0); o.write_shift(4, 0);\n\t\to.write_shift(4, file.start);\n\t\to.write_shift(4, file.size); o.write_shift(4, 0);\n\t}\n\tfor(i = 1; i < cfb.FileIndex.length; ++i) {\n\t\tfile = cfb.FileIndex[i];\n\t\t/*:: if(!file.content) throw new Error(\"unreachable\"); */\n\t\tif(file.size >= 0x1000) {\n\t\t\to.l = (file.start+1) << 9;\n\t\t\tif (has_buf && Buffer.isBuffer(file.content)) {\n\t\t\t\tfile.content.copy(o, o.l, 0, file.size);\n\t\t\t\t// o is a 0-filled Buffer so just set next offset\n\t\t\t\to.l += (file.size + 511) & -512;\n\t\t\t} else {\n\t\t\t\tfor(j = 0; j < file.size; ++j) o.write_shift(1, file.content[j]);\n\t\t\t\tfor(; j & 0x1FF; ++j) o.write_shift(1, 0);\n\t\t\t}\n\t\t}\n\t}\n\tfor(i = 1; i < cfb.FileIndex.length; ++i) {\n\t\tfile = cfb.FileIndex[i];\n\t\t/*:: if(!file.content) throw new Error(\"unreachable\"); */\n\t\tif(file.size > 0 && file.size < 0x1000) {\n\t\t\tif (has_buf && Buffer.isBuffer(file.content)) {\n\t\t\t\tfile.content.copy(o, o.l, 0, file.size);\n\t\t\t\t// o is a 0-filled Buffer so just set next offset\n\t\t\t\to.l += (file.size + 63) & -64;\n\t\t\t} else {\n\t\t\t\tfor(j = 0; j < file.size; ++j) o.write_shift(1, file.content[j]);\n\t\t\t\tfor(; j & 0x3F; ++j) o.write_shift(1, 0);\n\t\t\t}\n\t\t}\n\t}\n\tif (has_buf) {\n\t\to.l = o.length;\n\t} else {\n\t\t// When using Buffer, already 0-filled\n\t\twhile(o.l < o.length) o.write_shift(1, 0);\n\t}\n\treturn o;\n}\n/* [MS-CFB] 2.6.4 (Unicode 3.0.1 case conversion) */\nfunction find(cfb/*:CFBContainer*/, path/*:string*/)/*:?CFBEntry*/ {\n\tvar UCFullPaths/*:Array<string>*/ = cfb.FullPaths.map(function(x) { return x.toUpperCase(); });\n\tvar UCPaths/*:Array<string>*/ = UCFullPaths.map(function(x) { var y = x.split(\"/\"); return y[y.length - (x.slice(-1) == \"/\" ? 2 : 1)]; });\n\tvar k/*:boolean*/ = false;\n\tif(path.charCodeAt(0) === 47 /* \"/\" */) { k = true; path = UCFullPaths[0].slice(0, -1) + path; }\n\telse k = path.indexOf(\"/\") !== -1;\n\tvar UCPath/*:string*/ = path.toUpperCase();\n\tvar w/*:number*/ = k === true ? UCFullPaths.indexOf(UCPath) : UCPaths.indexOf(UCPath);\n\tif(w !== -1) return cfb.FileIndex[w];\n\n\tvar m = !UCPath.match(chr1);\n\tUCPath = UCPath.replace(chr0,'');\n\tif(m) UCPath = UCPath.replace(chr1,'!');\n\tfor(w = 0; w < UCFullPaths.length; ++w) {\n\t\tif((m ? UCFullPaths[w].replace(chr1,'!') : UCFullPaths[w]).replace(chr0,'') == UCPath) return cfb.FileIndex[w];\n\t\tif((m ? UCPaths[w].replace(chr1,'!') : UCPaths[w]).replace(chr0,'') == UCPath) return cfb.FileIndex[w];\n\t}\n\treturn null;\n}\n/** CFB Constants */\nvar MSSZ = 64; /* Mini Sector Size = 1<<6 */\n//var MSCSZ = 4096; /* Mini Stream Cutoff Size */\n/* 2.1 Compound File Sector Numbers and Types */\nvar ENDOFCHAIN = -2;\n/* 2.2 Compound File Header */\nvar HEADER_SIGNATURE = 'd0cf11e0a1b11ae1';\nvar HEADER_SIG = [0xD0, 0xCF, 0x11, 0xE0, 0xA1, 0xB1, 0x1A, 0xE1];\nvar HEADER_CLSID = '00000000000000000000000000000000';\nvar consts = {\n\t/* 2.1 Compund File Sector Numbers and Types */\n\tMAXREGSECT: -6,\n\tDIFSECT: -4,\n\tFATSECT: -3,\n\tENDOFCHAIN: ENDOFCHAIN,\n\tFREESECT: -1,\n\t/* 2.2 Compound File Header */\n\tHEADER_SIGNATURE: HEADER_SIGNATURE,\n\tHEADER_MINOR_VERSION: '3e00',\n\tMAXREGSID: -6,\n\tNOSTREAM: -1,\n\tHEADER_CLSID: HEADER_CLSID,\n\t/* 2.6.1 Compound File Directory Entry */\n\tEntryTypes: ['unknown','storage','stream','lockbytes','property','root']\n};\n\nfunction write_file(cfb/*:CFBContainer*/, filename/*:string*/, options/*:CFBWriteOpts*/)/*:void*/ {\n\tget_fs();\n\tvar o = _write(cfb, options);\n\t/*:: if(typeof Buffer == 'undefined' || !Buffer.isBuffer(o) || !(o instanceof Buffer)) throw new Error(\"unreachable\"); */\n\tfs.writeFileSync(filename, o);\n}\n\nfunction a2s(o/*:RawBytes*/)/*:string*/ {\n\tvar out = new Array(o.length);\n\tfor(var i = 0; i < o.length; ++i) out[i] = String.fromCharCode(o[i]);\n\treturn out.join(\"\");\n}\n\nfunction write(cfb/*:CFBContainer*/, options/*:CFBWriteOpts*/)/*:RawBytes|string*/ {\n\tvar o = _write(cfb, options);\n\tswitch(options && options.type || \"buffer\") {\n\t\tcase \"file\": get_fs(); fs.writeFileSync(options.filename, (o/*:any*/)); return o;\n\t\tcase \"binary\": return typeof o == \"string\" ? o : a2s(o);\n\t\tcase \"base64\": return Base64_encode(typeof o == \"string\" ? o : a2s(o));\n\t\tcase \"buffer\": if(has_buf) return Buffer.isBuffer(o) ? o : Buffer_from(o);\n\t\t\t/* falls through */\n\t\tcase \"array\": return typeof o == \"string\" ? s2a(o) : o;\n\t}\n\treturn o;\n}\n/* node < 8.1 zlib does not expose bytesRead, so default to pure JS */\nvar _zlib;\nfunction use_zlib(zlib) { try {\n\tvar InflateRaw = zlib.InflateRaw;\n\tvar InflRaw = new InflateRaw();\n\tInflRaw._processChunk(new Uint8Array([3, 0]), InflRaw._finishFlushFlag);\n\tif(InflRaw.bytesRead) _zlib = zlib;\n\telse throw new Error(\"zlib does not expose bytesRead\");\n} catch(e) {console.error(\"cannot use native zlib: \" + (e.message || e)); } }\n\nfunction _inflateRawSync(payload, usz) {\n\tif(!_zlib) return _inflate(payload, usz);\n\tvar InflateRaw = _zlib.InflateRaw;\n\tvar InflRaw = new InflateRaw();\n\tvar out = InflRaw._processChunk(payload.slice(payload.l), InflRaw._finishFlushFlag);\n\tpayload.l += InflRaw.bytesRead;\n\treturn out;\n}\n\nfunction _deflateRawSync(payload) {\n\treturn _zlib ? _zlib.deflateRawSync(payload) : _deflate(payload);\n}\nvar CLEN_ORDER = [ 16, 17, 18, 0, 8, 7, 9, 6, 10, 5, 11, 4, 12, 3, 13, 2, 14, 1, 15 ];\n\n/*  LEN_ID = [ 257, 258, 259, 260, 261, 262, 263, 264, 265, 266, 267, 268, 269, 270, 271, 272, 273, 274, 275, 276, 277, 278, 279, 280, 281, 282, 283, 284, 285 ]; */\nvar LEN_LN = [   3,   4,   5,   6,   7,   8,   9,  10,  11,  13 , 15,  17,  19,  23,  27,  31,  35,  43,  51,  59,  67,  83,  99, 115, 131, 163, 195, 227, 258 ];\n\n/*  DST_ID = [  0,  1,  2,  3,  4,  5,  6,  7,  8,  9, 10, 11, 12, 13,  14,  15,  16,  17,  18,  19,   20,   21,   22,   23,   24,   25,   26,    27,    28,    29 ]; */\nvar DST_LN = [  1,  2,  3,  4,  5,  7,  9, 13, 17, 25, 33, 49, 65, 97, 129, 193, 257, 385, 513, 769, 1025, 1537, 2049, 3073, 4097, 6145, 8193, 12289, 16385, 24577 ];\n\nfunction bit_swap_8(n) { var t = (((((n<<1)|(n<<11)) & 0x22110) | (((n<<5)|(n<<15)) & 0x88440))); return ((t>>16) | (t>>8) |t)&0xFF; }\n\nvar use_typed_arrays = typeof Uint8Array !== 'undefined';\n\nvar bitswap8 = use_typed_arrays ? new Uint8Array(1<<8) : [];\nfor(var q = 0; q < (1<<8); ++q) bitswap8[q] = bit_swap_8(q);\n\nfunction bit_swap_n(n, b) {\n\tvar rev = bitswap8[n & 0xFF];\n\tif(b <= 8) return rev >>> (8-b);\n\trev = (rev << 8) | bitswap8[(n>>8)&0xFF];\n\tif(b <= 16) return rev >>> (16-b);\n\trev = (rev << 8) | bitswap8[(n>>16)&0xFF];\n\treturn rev >>> (24-b);\n}\n\n/* helpers for unaligned bit reads */\nfunction read_bits_2(buf, bl) { var w = (bl&7), h = (bl>>>3); return ((buf[h]|(w <= 6 ? 0 : buf[h+1]<<8))>>>w)& 0x03; }\nfunction read_bits_3(buf, bl) { var w = (bl&7), h = (bl>>>3); return ((buf[h]|(w <= 5 ? 0 : buf[h+1]<<8))>>>w)& 0x07; }\nfunction read_bits_4(buf, bl) { var w = (bl&7), h = (bl>>>3); return ((buf[h]|(w <= 4 ? 0 : buf[h+1]<<8))>>>w)& 0x0F; }\nfunction read_bits_5(buf, bl) { var w = (bl&7), h = (bl>>>3); return ((buf[h]|(w <= 3 ? 0 : buf[h+1]<<8))>>>w)& 0x1F; }\nfunction read_bits_7(buf, bl) { var w = (bl&7), h = (bl>>>3); return ((buf[h]|(w <= 1 ? 0 : buf[h+1]<<8))>>>w)& 0x7F; }\n\n/* works up to n = 3 * 8 + 1 = 25 */\nfunction read_bits_n(buf, bl, n) {\n\tvar w = (bl&7), h = (bl>>>3), f = ((1<<n)-1);\n\tvar v = buf[h] >>> w;\n\tif(n < 8 - w) return v & f;\n\tv |= buf[h+1]<<(8-w);\n\tif(n < 16 - w) return v & f;\n\tv |= buf[h+2]<<(16-w);\n\tif(n < 24 - w) return v & f;\n\tv |= buf[h+3]<<(24-w);\n\treturn v & f;\n}\n\n/* helpers for unaligned bit writes */\nfunction write_bits_3(buf, bl, v) { var w = bl & 7, h = bl >>> 3;\n\tif(w <= 5) buf[h] |= (v & 7) << w;\n\telse {\n\t\tbuf[h] |= (v << w) & 0xFF;\n\t\tbuf[h+1] = (v&7) >> (8-w);\n\t}\n\treturn bl + 3;\n}\n\nfunction write_bits_1(buf, bl, v) {\n\tvar w = bl & 7, h = bl >>> 3;\n\tv = (v&1) << w;\n\tbuf[h] |= v;\n\treturn bl + 1;\n}\nfunction write_bits_8(buf, bl, v) {\n\tvar w = bl & 7, h = bl >>> 3;\n\tv <<= w;\n\tbuf[h] |=  v & 0xFF; v >>>= 8;\n\tbuf[h+1] = v;\n\treturn bl + 8;\n}\nfunction write_bits_16(buf, bl, v) {\n\tvar w = bl & 7, h = bl >>> 3;\n\tv <<= w;\n\tbuf[h] |=  v & 0xFF; v >>>= 8;\n\tbuf[h+1] = v & 0xFF;\n\tbuf[h+2] = v >>> 8;\n\treturn bl + 16;\n}\n\n/* until ArrayBuffer#realloc is a thing, fake a realloc */\nfunction realloc(b, sz/*:number*/) {\n\tvar L = b.length, M = 2*L > sz ? 2*L : sz + 5, i = 0;\n\tif(L >= sz) return b;\n\tif(has_buf) {\n\t\tvar o = new_unsafe_buf(M);\n\t\t// $FlowIgnore\n\t\tif(b.copy) b.copy(o);\n\t\telse for(; i < b.length; ++i) o[i] = b[i];\n\t\treturn o;\n\t} else if(use_typed_arrays) {\n\t\tvar a = new Uint8Array(M);\n\t\tif(a.set) a.set(b);\n\t\telse for(; i < L; ++i) a[i] = b[i];\n\t\treturn a;\n\t}\n\tb.length = M;\n\treturn b;\n}\n\n/* zero-filled arrays for older browsers */\nfunction zero_fill_array(n) {\n\tvar o = new Array(n);\n\tfor(var i = 0; i < n; ++i) o[i] = 0;\n\treturn o;\n}\n\n/* build tree (used for literals and lengths) */\nfunction build_tree(clens, cmap, MAX/*:number*/)/*:number*/ {\n\tvar maxlen = 1, w = 0, i = 0, j = 0, ccode = 0, L = clens.length;\n\n\tvar bl_count  = use_typed_arrays ? new Uint16Array(32) : zero_fill_array(32);\n\tfor(i = 0; i < 32; ++i) bl_count[i] = 0;\n\n\tfor(i = L; i < MAX; ++i) clens[i] = 0;\n\tL = clens.length;\n\n\tvar ctree = use_typed_arrays ? new Uint16Array(L) : zero_fill_array(L); // []\n\n\t/* build code tree */\n\tfor(i = 0; i < L; ++i) {\n\t\tbl_count[(w = clens[i])]++;\n\t\tif(maxlen < w) maxlen = w;\n\t\tctree[i] = 0;\n\t}\n\tbl_count[0] = 0;\n\tfor(i = 1; i <= maxlen; ++i) bl_count[i+16] = (ccode = (ccode + bl_count[i-1])<<1);\n\tfor(i = 0; i < L; ++i) {\n\t\tccode = clens[i];\n\t\tif(ccode != 0) ctree[i] = bl_count[ccode+16]++;\n\t}\n\n\t/* cmap[maxlen + 4 bits] = (off&15) + (lit<<4) reverse mapping */\n\tvar cleni = 0;\n\tfor(i = 0; i < L; ++i) {\n\t\tcleni = clens[i];\n\t\tif(cleni != 0) {\n\t\t\tccode = bit_swap_n(ctree[i], maxlen)>>(maxlen-cleni);\n\t\t\tfor(j = (1<<(maxlen + 4 - cleni)) - 1; j>=0; --j)\n\t\t\t\tcmap[ccode|(j<<cleni)] = (cleni&15) | (i<<4);\n\t\t}\n\t}\n\treturn maxlen;\n}\n\n/* Fixed Huffman */\nvar fix_lmap = use_typed_arrays ? new Uint16Array(512) : zero_fill_array(512);\nvar fix_dmap = use_typed_arrays ? new Uint16Array(32)  : zero_fill_array(32);\nif(!use_typed_arrays) {\n\tfor(var i = 0; i < 512; ++i) fix_lmap[i] = 0;\n\tfor(i = 0; i < 32; ++i) fix_dmap[i] = 0;\n}\n(function() {\n\tvar dlens/*:Array<number>*/ = [];\n\tvar i = 0;\n\tfor(;i<32; i++) dlens.push(5);\n\tbuild_tree(dlens, fix_dmap, 32);\n\n\tvar clens/*:Array<number>*/ = [];\n\ti = 0;\n\tfor(; i<=143; i++) clens.push(8);\n\tfor(; i<=255; i++) clens.push(9);\n\tfor(; i<=279; i++) clens.push(7);\n\tfor(; i<=287; i++) clens.push(8);\n\tbuild_tree(clens, fix_lmap, 288);\n})();var _deflateRaw = /*#__PURE__*/(function _deflateRawIIFE() {\n\tvar DST_LN_RE = use_typed_arrays ? new Uint8Array(0x8000) : [];\n\tvar j = 0, k = 0;\n\tfor(; j < DST_LN.length - 1; ++j) {\n\t\tfor(; k < DST_LN[j+1]; ++k) DST_LN_RE[k] = j;\n\t}\n\tfor(;k < 32768; ++k) DST_LN_RE[k] = 29;\n\n\tvar LEN_LN_RE = use_typed_arrays ? new Uint8Array(0x103) : [];\n\tfor(j = 0, k = 0; j < LEN_LN.length - 1; ++j) {\n\t\tfor(; k < LEN_LN[j+1]; ++k) LEN_LN_RE[k] = j;\n\t}\n\n\tfunction write_stored(data, out) {\n\t\tvar boff = 0;\n\t\twhile(boff < data.length) {\n\t\t\tvar L = Math.min(0xFFFF, data.length - boff);\n\t\t\tvar h = boff + L == data.length;\n\t\t\tout.write_shift(1, +h);\n\t\t\tout.write_shift(2, L);\n\t\t\tout.write_shift(2, (~L) & 0xFFFF);\n\t\t\twhile(L-- > 0) out[out.l++] = data[boff++];\n\t\t}\n\t\treturn out.l;\n\t}\n\n\t/* Fixed Huffman */\n\tfunction write_huff_fixed(data, out) {\n\t\tvar bl = 0;\n\t\tvar boff = 0;\n\t\tvar addrs = use_typed_arrays ? new Uint16Array(0x8000) : [];\n\t\twhile(boff < data.length) {\n\t\t\tvar L = /* data.length - boff; */ Math.min(0xFFFF, data.length - boff);\n\n\t\t\t/* write a stored block for short data */\n\t\t\tif(L < 10) {\n\t\t\t\tbl = write_bits_3(out, bl, +!!(boff + L == data.length)); // jshint ignore:line\n\t\t\t\tif(bl & 7) bl += 8 - (bl & 7);\n\t\t\t\tout.l = (bl / 8) | 0;\n\t\t\t\tout.write_shift(2, L);\n\t\t\t\tout.write_shift(2, (~L) & 0xFFFF);\n\t\t\t\twhile(L-- > 0) out[out.l++] = data[boff++];\n\t\t\t\tbl = out.l * 8;\n\t\t\t\tcontinue;\n\t\t\t}\n\n\t\t\tbl = write_bits_3(out, bl, +!!(boff + L == data.length) + 2); // jshint ignore:line\n\t\t\tvar hash = 0;\n\t\t\twhile(L-- > 0) {\n\t\t\t\tvar d = data[boff];\n\t\t\t\thash = ((hash << 5) ^ d) & 0x7FFF;\n\n\t\t\t\tvar match = -1, mlen = 0;\n\n\t\t\t\tif((match = addrs[hash])) {\n\t\t\t\t\tmatch |= boff & ~0x7FFF;\n\t\t\t\t\tif(match > boff) match -= 0x8000;\n\t\t\t\t\tif(match < boff) while(data[match + mlen] == data[boff + mlen] && mlen < 250) ++mlen;\n\t\t\t\t}\n\n\t\t\t\tif(mlen > 2) {\n\t\t\t\t\t/* Copy Token  */\n\t\t\t\t\td = LEN_LN_RE[mlen];\n\t\t\t\t\tif(d <= 22) bl = write_bits_8(out, bl, bitswap8[d+1]>>1) - 1;\n\t\t\t\t\telse {\n\t\t\t\t\t\twrite_bits_8(out, bl, 3);\n\t\t\t\t\t\tbl += 5;\n\t\t\t\t\t\twrite_bits_8(out, bl, bitswap8[d-23]>>5);\n\t\t\t\t\t\tbl += 3;\n\t\t\t\t\t}\n\t\t\t\t\tvar len_eb = (d < 8) ? 0 : ((d - 4)>>2);\n\t\t\t\t\tif(len_eb > 0) {\n\t\t\t\t\t\twrite_bits_16(out, bl, mlen - LEN_LN[d]);\n\t\t\t\t\t\tbl += len_eb;\n\t\t\t\t\t}\n\n\t\t\t\t\td = DST_LN_RE[boff - match];\n\t\t\t\t\tbl = write_bits_8(out, bl, bitswap8[d]>>3);\n\t\t\t\t\tbl -= 3;\n\n\t\t\t\t\tvar dst_eb = d < 4 ? 0 : (d-2)>>1;\n\t\t\t\t\tif(dst_eb > 0) {\n\t\t\t\t\t\twrite_bits_16(out, bl, boff - match - DST_LN[d]);\n\t\t\t\t\t\tbl += dst_eb;\n\t\t\t\t\t}\n\t\t\t\t\tfor(var q = 0; q < mlen; ++q) {\n\t\t\t\t\t\taddrs[hash] = boff & 0x7FFF;\n\t\t\t\t\t\thash = ((hash << 5) ^ data[boff]) & 0x7FFF;\n\t\t\t\t\t\t++boff;\n\t\t\t\t\t}\n\t\t\t\t\tL-= mlen - 1;\n\t\t\t\t} else {\n\t\t\t\t\t/* Literal Token */\n\t\t\t\t\tif(d <= 143) d = d + 48;\n\t\t\t\t\telse bl = write_bits_1(out, bl, 1);\n\t\t\t\t\tbl = write_bits_8(out, bl, bitswap8[d]);\n\t\t\t\t\taddrs[hash] = boff & 0x7FFF;\n\t\t\t\t\t++boff;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tbl = write_bits_8(out, bl, 0) - 1;\n\t\t}\n\t\tout.l = ((bl + 7)/8)|0;\n\t\treturn out.l;\n\t}\n\treturn function _deflateRaw(data, out) {\n\t\tif(data.length < 8) return write_stored(data, out);\n\t\treturn write_huff_fixed(data, out);\n\t};\n})();\n\nfunction _deflate(data) {\n\tvar buf = new_buf(50+Math.floor(data.length*1.1));\n\tvar off = _deflateRaw(data, buf);\n\treturn buf.slice(0, off);\n}\n/* modified inflate function also moves original read head */\n\nvar dyn_lmap = use_typed_arrays ? new Uint16Array(32768) : zero_fill_array(32768);\nvar dyn_dmap = use_typed_arrays ? new Uint16Array(32768) : zero_fill_array(32768);\nvar dyn_cmap = use_typed_arrays ? new Uint16Array(128)   : zero_fill_array(128);\nvar dyn_len_1 = 1, dyn_len_2 = 1;\n\n/* 5.5.3 Expanding Huffman Codes */\nfunction dyn(data, boff/*:number*/) {\n\t/* nomenclature from RFC1951 refers to bit values; these are offset by the implicit constant */\n\tvar _HLIT = read_bits_5(data, boff) + 257; boff += 5;\n\tvar _HDIST = read_bits_5(data, boff) + 1; boff += 5;\n\tvar _HCLEN = read_bits_4(data, boff) + 4; boff += 4;\n\tvar w = 0;\n\n\t/* grab and store code lengths */\n\tvar clens = use_typed_arrays ? new Uint8Array(19) : zero_fill_array(19);\n\tvar ctree = [ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 ];\n\tvar maxlen = 1;\n\tvar bl_count =  use_typed_arrays ? new Uint8Array(8) : zero_fill_array(8);\n\tvar next_code = use_typed_arrays ? new Uint8Array(8) : zero_fill_array(8);\n\tvar L = clens.length; /* 19 */\n\tfor(var i = 0; i < _HCLEN; ++i) {\n\t\tclens[CLEN_ORDER[i]] = w = read_bits_3(data, boff);\n\t\tif(maxlen < w) maxlen = w;\n\t\tbl_count[w]++;\n\t\tboff += 3;\n\t}\n\n\t/* build code tree */\n\tvar ccode = 0;\n\tbl_count[0] = 0;\n\tfor(i = 1; i <= maxlen; ++i) next_code[i] = ccode = (ccode + bl_count[i-1])<<1;\n\tfor(i = 0; i < L; ++i) if((ccode = clens[i]) != 0) ctree[i] = next_code[ccode]++;\n\t/* cmap[7 bits from stream] = (off&7) + (lit<<3) */\n\tvar cleni = 0;\n\tfor(i = 0; i < L; ++i) {\n\t\tcleni = clens[i];\n\t\tif(cleni != 0) {\n\t\t\tccode = bitswap8[ctree[i]]>>(8-cleni);\n\t\t\tfor(var j = (1<<(7-cleni))-1; j>=0; --j) dyn_cmap[ccode|(j<<cleni)] = (cleni&7) | (i<<3);\n\t\t}\n\t}\n\n\t/* read literal and dist codes at once */\n\tvar hcodes/*:Array<number>*/ = [];\n\tmaxlen = 1;\n\tfor(; hcodes.length < _HLIT + _HDIST;) {\n\t\tccode = dyn_cmap[read_bits_7(data, boff)];\n\t\tboff += ccode & 7;\n\t\tswitch((ccode >>>= 3)) {\n\t\t\tcase 16:\n\t\t\t\tw = 3 + read_bits_2(data, boff); boff += 2;\n\t\t\t\tccode = hcodes[hcodes.length - 1];\n\t\t\t\twhile(w-- > 0) hcodes.push(ccode);\n\t\t\t\tbreak;\n\t\t\tcase 17:\n\t\t\t\tw = 3 + read_bits_3(data, boff); boff += 3;\n\t\t\t\twhile(w-- > 0) hcodes.push(0);\n\t\t\t\tbreak;\n\t\t\tcase 18:\n\t\t\t\tw = 11 + read_bits_7(data, boff); boff += 7;\n\t\t\t\twhile(w -- > 0) hcodes.push(0);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\thcodes.push(ccode);\n\t\t\t\tif(maxlen < ccode) maxlen = ccode;\n\t\t\t\tbreak;\n\t\t}\n\t}\n\n\t/* build literal / length trees */\n\tvar h1 = hcodes.slice(0, _HLIT), h2 = hcodes.slice(_HLIT);\n\tfor(i = _HLIT; i < 286; ++i) h1[i] = 0;\n\tfor(i = _HDIST; i < 30; ++i) h2[i] = 0;\n\tdyn_len_1 = build_tree(h1, dyn_lmap, 286);\n\tdyn_len_2 = build_tree(h2, dyn_dmap, 30);\n\treturn boff;\n}\n\n/* return [ data, bytesRead ] */\nfunction inflate(data, usz/*:number*/) {\n\t/* shortcircuit for empty buffer [0x03, 0x00] */\n\tif(data[0] == 3 && !(data[1] & 0x3)) { return [new_raw_buf(usz), 2]; }\n\n\t/* bit offset */\n\tvar boff = 0;\n\n\t/* header includes final bit and type bits */\n\tvar header = 0;\n\n\tvar outbuf = new_unsafe_buf(usz ? usz : (1<<18));\n\tvar woff = 0;\n\tvar OL = outbuf.length>>>0;\n\tvar max_len_1 = 0, max_len_2 = 0;\n\n\twhile((header&1) == 0) {\n\t\theader = read_bits_3(data, boff); boff += 3;\n\t\tif((header >>> 1) == 0) {\n\t\t\t/* Stored block */\n\t\t\tif(boff & 7) boff += 8 - (boff&7);\n\t\t\t/* 2 bytes sz, 2 bytes bit inverse */\n\t\t\tvar sz = data[boff>>>3] | data[(boff>>>3)+1]<<8;\n\t\t\tboff += 32;\n\t\t\t/* push sz bytes */\n\t\t\tif(sz > 0) {\n\t\t\t\tif(!usz && OL < woff + sz) { outbuf = realloc(outbuf, woff + sz); OL = outbuf.length; }\n\t\t\t\twhile(sz-- > 0) { outbuf[woff++] = data[boff>>>3]; boff += 8; }\n\t\t\t}\n\t\t\tcontinue;\n\t\t} else if((header >> 1) == 1) {\n\t\t\t/* Fixed Huffman */\n\t\t\tmax_len_1 = 9; max_len_2 = 5;\n\t\t} else {\n\t\t\t/* Dynamic Huffman */\n\t\t\tboff = dyn(data, boff);\n\t\t\tmax_len_1 = dyn_len_1; max_len_2 = dyn_len_2;\n\t\t}\n\t\tfor(;;) { // while(true) is apparently out of vogue in modern JS circles\n\t\t\tif(!usz && (OL < woff + 32767)) { outbuf = realloc(outbuf, woff + 32767); OL = outbuf.length; }\n\t\t\t/* ingest code and move read head */\n\t\t\tvar bits = read_bits_n(data, boff, max_len_1);\n\t\t\tvar code = (header>>>1) == 1 ? fix_lmap[bits] : dyn_lmap[bits];\n\t\t\tboff += code & 15; code >>>= 4;\n\t\t\t/* 0-255 are literals, 256 is end of block token, 257+ are copy tokens */\n\t\t\tif(((code>>>8)&0xFF) === 0) outbuf[woff++] = code;\n\t\t\telse if(code == 256) break;\n\t\t\telse {\n\t\t\t\tcode -= 257;\n\t\t\t\tvar len_eb = (code < 8) ? 0 : ((code-4)>>2); if(len_eb > 5) len_eb = 0;\n\t\t\t\tvar tgt = woff + LEN_LN[code];\n\t\t\t\t/* length extra bits */\n\t\t\t\tif(len_eb > 0) {\n\t\t\t\t\ttgt += read_bits_n(data, boff, len_eb);\n\t\t\t\t\tboff += len_eb;\n\t\t\t\t}\n\n\t\t\t\t/* dist code */\n\t\t\t\tbits = read_bits_n(data, boff, max_len_2);\n\t\t\t\tcode = (header>>>1) == 1 ? fix_dmap[bits] : dyn_dmap[bits];\n\t\t\t\tboff += code & 15; code >>>= 4;\n\t\t\t\tvar dst_eb = (code < 4 ? 0 : (code-2)>>1);\n\t\t\t\tvar dst = DST_LN[code];\n\t\t\t\t/* dist extra bits */\n\t\t\t\tif(dst_eb > 0) {\n\t\t\t\t\tdst += read_bits_n(data, boff, dst_eb);\n\t\t\t\t\tboff += dst_eb;\n\t\t\t\t}\n\n\t\t\t\t/* in the common case, manual byte copy is faster than TA set / Buffer copy */\n\t\t\t\tif(!usz && OL < tgt) { outbuf = realloc(outbuf, tgt + 100); OL = outbuf.length; }\n\t\t\t\twhile(woff < tgt) { outbuf[woff] = outbuf[woff - dst]; ++woff; }\n\t\t\t}\n\t\t}\n\t}\n\tif(usz) return [outbuf, (boff+7)>>>3];\n\treturn [outbuf.slice(0, woff), (boff+7)>>>3];\n}\n\nfunction _inflate(payload, usz) {\n\tvar data = payload.slice(payload.l||0);\n\tvar out = inflate(data, usz);\n\tpayload.l += out[1];\n\treturn out[0];\n}\n\nfunction warn_or_throw(wrn, msg) {\n\tif(wrn) { if(typeof console !== 'undefined') console.error(msg); }\n\telse throw new Error(msg);\n}\n\nfunction parse_zip(file/*:RawBytes*/, options/*:CFBReadOpts*/)/*:CFBContainer*/ {\n\tvar blob/*:CFBlob*/ = /*::(*/file/*:: :any)*/;\n\tprep_blob(blob, 0);\n\n\tvar FileIndex/*:CFBFileIndex*/ = [], FullPaths/*:Array<string>*/ = [];\n\tvar o = {\n\t\tFileIndex: FileIndex,\n\t\tFullPaths: FullPaths\n\t};\n\tinit_cfb(o, { root: options.root });\n\n\t/* find end of central directory, start just after signature */\n\tvar i = blob.length - 4;\n\twhile((blob[i] != 0x50 || blob[i+1] != 0x4b || blob[i+2] != 0x05 || blob[i+3] != 0x06) && i >= 0) --i;\n\tblob.l = i + 4;\n\n\t/* parse end of central directory */\n\tblob.l += 4;\n\tvar fcnt = blob.read_shift(2);\n\tblob.l += 6;\n\tvar start_cd = blob.read_shift(4);\n\n\t/* parse central directory */\n\tblob.l = start_cd;\n\n\tfor(i = 0; i < fcnt; ++i) {\n\t\t/* trust local file header instead of CD entry */\n\t\tblob.l += 20;\n\t\tvar csz = blob.read_shift(4);\n\t\tvar usz = blob.read_shift(4);\n\t\tvar namelen = blob.read_shift(2);\n\t\tvar efsz = blob.read_shift(2);\n\t\tvar fcsz = blob.read_shift(2);\n\t\tblob.l += 8;\n\t\tvar offset = blob.read_shift(4);\n\t\tvar EF = parse_extra_field(/*::(*/blob.slice(blob.l+namelen, blob.l+namelen+efsz)/*:: :any)*/);\n\t\tblob.l += namelen + efsz + fcsz;\n\n\t\tvar L = blob.l;\n\t\tblob.l = offset + 4;\n\t\tparse_local_file(blob, csz, usz, o, EF);\n\t\tblob.l = L;\n\t}\n\treturn o;\n}\n\n\n/* head starts just after local file header signature */\nfunction parse_local_file(blob/*:CFBlob*/, csz/*:number*/, usz/*:number*/, o/*:CFBContainer*/, EF) {\n\t/* [local file header] */\n\tblob.l += 2;\n\tvar flags = blob.read_shift(2);\n\tvar meth = blob.read_shift(2);\n\tvar date = parse_dos_date(blob);\n\n\tif(flags & 0x2041) throw new Error(\"Unsupported ZIP encryption\");\n\tvar crc32 = blob.read_shift(4);\n\tvar _csz = blob.read_shift(4);\n\tvar _usz = blob.read_shift(4);\n\n\tvar namelen = blob.read_shift(2);\n\tvar efsz = blob.read_shift(2);\n\n\t// TODO: flags & (1<<11) // UTF8\n\tvar name = \"\"; for(var i = 0; i < namelen; ++i) name += String.fromCharCode(blob[blob.l++]);\n\tif(efsz) {\n\t\tvar ef = parse_extra_field(/*::(*/blob.slice(blob.l, blob.l + efsz)/*:: :any)*/);\n\t\tif((ef[0x5455]||{}).mt) date = ef[0x5455].mt;\n\t\tif(((EF||{})[0x5455]||{}).mt) date = EF[0x5455].mt;\n\t}\n\tblob.l += efsz;\n\n\t/* [encryption header] */\n\n\t/* [file data] */\n\tvar data = blob.slice(blob.l, blob.l + _csz);\n\tswitch(meth) {\n\t\tcase 8: data = _inflateRawSync(blob, _usz); break;\n\t\tcase 0: break; // TODO: scan for magic number\n\t\tdefault: throw new Error(\"Unsupported ZIP Compression method \" + meth);\n\t}\n\n\t/* [data descriptor] */\n\tvar wrn = false;\n\tif(flags & 8) {\n\t\tcrc32 = blob.read_shift(4);\n\t\tif(crc32 == 0x08074b50) { crc32 = blob.read_shift(4); wrn = true; }\n\t\t_csz = blob.read_shift(4);\n\t\t_usz = blob.read_shift(4);\n\t}\n\n\tif(_csz != csz) warn_or_throw(wrn, \"Bad compressed size: \" + csz + \" != \" + _csz);\n\tif(_usz != usz) warn_or_throw(wrn, \"Bad uncompressed size: \" + usz + \" != \" + _usz);\n\t//var _crc32 = CRC32.buf(data, 0);\n\t//if((crc32>>0) != (_crc32>>0)) warn_or_throw(wrn, \"Bad CRC32 checksum: \" + crc32 + \" != \" + _crc32);\n\tcfb_add(o, name, data, {unsafe: true, mt: date});\n}\nfunction write_zip(cfb/*:CFBContainer*/, options/*:CFBWriteOpts*/)/*:RawBytes*/ {\n\tvar _opts = options || {};\n\tvar out = [], cdirs = [];\n\tvar o/*:CFBlob*/ = new_buf(1);\n\tvar method = (_opts.compression ? 8 : 0), flags = 0;\n\tvar desc = false;\n\tif(desc) flags |= 8;\n\tvar i = 0, j = 0;\n\n\tvar start_cd = 0, fcnt = 0;\n\tvar root = cfb.FullPaths[0], fp = root, fi = cfb.FileIndex[0];\n\tvar crcs = [];\n\tvar sz_cd = 0;\n\n\tfor(i = 1; i < cfb.FullPaths.length; ++i) {\n\t\tfp = cfb.FullPaths[i].slice(root.length); fi = cfb.FileIndex[i];\n\t\tif(!fi.size || !fi.content || fp == \"\\u0001Sh33tJ5\") continue;\n\t\tvar start = start_cd;\n\n\t\t/* TODO: CP437 filename */\n\t\tvar namebuf = new_buf(fp.length);\n\t\tfor(j = 0; j < fp.length; ++j) namebuf.write_shift(1, fp.charCodeAt(j) & 0x7F);\n\t\tnamebuf = namebuf.slice(0, namebuf.l);\n\t\tcrcs[fcnt] = CRC32.buf(/*::((*/fi.content/*::||[]):any)*/, 0);\n\n\t\tvar outbuf = fi.content/*::||[]*/;\n\t\tif(method == 8) outbuf = _deflateRawSync(outbuf);\n\n\t\t/* local file header */\n\t\to = new_buf(30);\n\t\to.write_shift(4, 0x04034b50);\n\t\to.write_shift(2, 20);\n\t\to.write_shift(2, flags);\n\t\to.write_shift(2, method);\n\t\t/* TODO: last mod file time/date */\n\t\tif(fi.mt) write_dos_date(o, fi.mt);\n\t\telse o.write_shift(4, 0);\n\t\to.write_shift(-4, (flags & 8) ? 0 : crcs[fcnt]);\n\t\to.write_shift(4,  (flags & 8) ? 0 : outbuf.length);\n\t\to.write_shift(4,  (flags & 8) ? 0 : /*::(*/fi.content/*::||[])*/.length);\n\t\to.write_shift(2, namebuf.length);\n\t\to.write_shift(2, 0);\n\n\t\tstart_cd += o.length;\n\t\tout.push(o);\n\t\tstart_cd += namebuf.length;\n\t\tout.push(namebuf);\n\n\t\t/* TODO: extra fields? */\n\n\t\t/* TODO: encryption header ? */\n\n\t\tstart_cd += outbuf.length;\n\t\tout.push(outbuf);\n\n\t\t/* data descriptor */\n\t\tif(flags & 8) {\n\t\t\to = new_buf(12);\n\t\t\to.write_shift(-4, crcs[fcnt]);\n\t\t\to.write_shift(4, outbuf.length);\n\t\t\to.write_shift(4, /*::(*/fi.content/*::||[])*/.length);\n\t\t\tstart_cd += o.l;\n\t\t\tout.push(o);\n\t\t}\n\n\t\t/* central directory */\n\t\to = new_buf(46);\n\t\to.write_shift(4, 0x02014b50);\n\t\to.write_shift(2, 0);\n\t\to.write_shift(2, 20);\n\t\to.write_shift(2, flags);\n\t\to.write_shift(2, method);\n\t\to.write_shift(4, 0); /* TODO: last mod file time/date */\n\t\to.write_shift(-4, crcs[fcnt]);\n\n\t\to.write_shift(4, outbuf.length);\n\t\to.write_shift(4, /*::(*/fi.content/*::||[])*/.length);\n\t\to.write_shift(2, namebuf.length);\n\t\to.write_shift(2, 0);\n\t\to.write_shift(2, 0);\n\t\to.write_shift(2, 0);\n\t\to.write_shift(2, 0);\n\t\to.write_shift(4, 0);\n\t\to.write_shift(4, start);\n\n\t\tsz_cd += o.l;\n\t\tcdirs.push(o);\n\t\tsz_cd += namebuf.length;\n\t\tcdirs.push(namebuf);\n\t\t++fcnt;\n\t}\n\n\t/* end of central directory */\n\to = new_buf(22);\n\to.write_shift(4, 0x06054b50);\n\to.write_shift(2, 0);\n\to.write_shift(2, 0);\n\to.write_shift(2, fcnt);\n\to.write_shift(2, fcnt);\n\to.write_shift(4, sz_cd);\n\to.write_shift(4, start_cd);\n\to.write_shift(2, 0);\n\n\treturn bconcat(([bconcat((out/*:any*/)), bconcat(cdirs), o]/*:any*/));\n}\nvar ContentTypeMap = ({\n\t\"htm\": \"text/html\",\n\t\"xml\": \"text/xml\",\n\n\t\"gif\": \"image/gif\",\n\t\"jpg\": \"image/jpeg\",\n\t\"png\": \"image/png\",\n\n\t\"mso\": \"application/x-mso\",\n\t\"thmx\": \"application/vnd.ms-officetheme\",\n\t\"sh33tj5\": \"application/octet-stream\"\n}/*:any*/);\n\nfunction get_content_type(fi/*:CFBEntry*/, fp/*:string*/)/*:string*/ {\n\tif(fi.ctype) return fi.ctype;\n\n\tvar ext = fi.name || \"\", m = ext.match(/\\.([^\\.]+)$/);\n\tif(m && ContentTypeMap[m[1]]) return ContentTypeMap[m[1]];\n\n\tif(fp) {\n\t\tm = (ext = fp).match(/[\\.\\\\]([^\\.\\\\])+$/);\n\t\tif(m && ContentTypeMap[m[1]]) return ContentTypeMap[m[1]];\n\t}\n\n\treturn \"application/octet-stream\";\n}\n\n/* 76 character chunks TODO: intertwine encoding */\nfunction write_base64_76(bstr/*:string*/)/*:string*/ {\n\tvar data = Base64_encode(bstr);\n\tvar o = [];\n\tfor(var i = 0; i < data.length; i+= 76) o.push(data.slice(i, i+76));\n\treturn o.join(\"\\r\\n\") + \"\\r\\n\";\n}\n\n/*\nRules for QP:\n\t- escape =## applies for all non-display characters and literal \"=\"\n\t- space or tab at end of line must be encoded\n\t- \\r\\n newlines can be preserved, but bare \\r and \\n must be escaped\n\t- lines must not exceed 76 characters, use soft breaks =\\r\\n\n\nTODO: Some files from word appear to write line extensions with bare equals:\n\n```\n<table class=3DMsoTableGrid border=3D1 cellspacing=3D0 cellpadding=3D0 width=\n=\"70%\"\n```\n*/\nfunction write_quoted_printable(text/*:string*/)/*:string*/ {\n\tvar encoded = text.replace(/[\\x00-\\x08\\x0B\\x0C\\x0E-\\x1F\\x7E-\\xFF=]/g, function(c) {\n\t\tvar w = c.charCodeAt(0).toString(16).toUpperCase();\n\t\treturn \"=\" + (w.length == 1 ? \"0\" + w : w);\n\t});\n\n\tencoded = encoded.replace(/ $/mg, \"=20\").replace(/\\t$/mg, \"=09\");\n\n\tif(encoded.charAt(0) == \"\\n\") encoded = \"=0D\" + encoded.slice(1);\n\tencoded = encoded.replace(/\\r(?!\\n)/mg, \"=0D\").replace(/\\n\\n/mg, \"\\n=0A\").replace(/([^\\r\\n])\\n/mg, \"$1=0A\");\n\n\tvar o/*:Array<string>*/ = [], split = encoded.split(\"\\r\\n\");\n\tfor(var si = 0; si < split.length; ++si) {\n\t\tvar str = split[si];\n\t\tif(str.length == 0) { o.push(\"\"); continue; }\n\t\tfor(var i = 0; i < str.length;) {\n\t\t\tvar end = 76;\n\t\t\tvar tmp = str.slice(i, i + end);\n\t\t\tif(tmp.charAt(end - 1) == \"=\") end --;\n\t\t\telse if(tmp.charAt(end - 2) == \"=\") end -= 2;\n\t\t\telse if(tmp.charAt(end - 3) == \"=\") end -= 3;\n\t\t\ttmp = str.slice(i, i + end);\n\t\t\ti += end;\n\t\t\tif(i < str.length) tmp += \"=\";\n\t\t\to.push(tmp);\n\t\t}\n\t}\n\n\treturn o.join(\"\\r\\n\");\n}\nfunction parse_quoted_printable(data/*:Array<string>*/)/*:RawBytes*/ {\n\tvar o = [];\n\n\t/* unify long lines */\n\tfor(var di = 0; di < data.length; ++di) {\n\t\tvar line = data[di];\n\t\twhile(di <= data.length && line.charAt(line.length - 1) == \"=\") line = line.slice(0, line.length - 1) + data[++di];\n\t\to.push(line);\n\t}\n\n\t/* decode */\n\tfor(var oi = 0; oi < o.length; ++oi) o[oi] = o[oi].replace(/[=][0-9A-Fa-f]{2}/g, function($$) { return String.fromCharCode(parseInt($$.slice(1), 16)); });\n\treturn s2a(o.join(\"\\r\\n\"));\n}\n\n\nfunction parse_mime(cfb/*:CFBContainer*/, data/*:Array<string>*/, root/*:string*/)/*:void*/ {\n\tvar fname = \"\", cte = \"\", ctype = \"\", fdata;\n\tvar di = 0;\n\tfor(;di < 10; ++di) {\n\t\tvar line = data[di];\n\t\tif(!line || line.match(/^\\s*$/)) break;\n\t\tvar m = line.match(/^(.*?):\\s*([^\\s].*)$/);\n\t\tif(m) switch(m[1].toLowerCase()) {\n\t\t\tcase \"content-location\": fname = m[2].trim(); break;\n\t\t\tcase \"content-type\": ctype = m[2].trim(); break;\n\t\t\tcase \"content-transfer-encoding\": cte = m[2].trim(); break;\n\t\t}\n\t}\n\t++di;\n\tswitch(cte.toLowerCase()) {\n\t\tcase 'base64': fdata = s2a(Base64_decode(data.slice(di).join(\"\"))); break;\n\t\tcase 'quoted-printable': fdata = parse_quoted_printable(data.slice(di)); break;\n\t\tdefault: throw new Error(\"Unsupported Content-Transfer-Encoding \" + cte);\n\t}\n\tvar file = cfb_add(cfb, fname.slice(root.length), fdata, {unsafe: true});\n\tif(ctype) file.ctype = ctype;\n}\n\nfunction parse_mad(file/*:RawBytes*/, options/*:CFBReadOpts*/)/*:CFBContainer*/ {\n\tif(a2s(file.slice(0,13)).toLowerCase() != \"mime-version:\") throw new Error(\"Unsupported MAD header\");\n\tvar root = (options && options.root || \"\");\n\t// $FlowIgnore\n\tvar data = (has_buf && Buffer.isBuffer(file) ? file.toString(\"binary\") : a2s(file)).split(\"\\r\\n\");\n\tvar di = 0, row = \"\";\n\n\t/* if root is not specified, scan for the common prefix */\n\tfor(di = 0; di < data.length; ++di) {\n\t\trow = data[di];\n\t\tif(!/^Content-Location:/i.test(row)) continue;\n\t\trow = row.slice(row.indexOf(\"file\"));\n\t\tif(!root) root = row.slice(0, row.lastIndexOf(\"/\") + 1);\n\t\tif(row.slice(0, root.length) == root) continue;\n\t\twhile(root.length > 0) {\n\t\t\troot = root.slice(0, root.length - 1);\n\t\t\troot = root.slice(0, root.lastIndexOf(\"/\") + 1);\n\t\t\tif(row.slice(0,root.length) == root) break;\n\t\t}\n\t}\n\n\tvar mboundary = (data[1] || \"\").match(/boundary=\"(.*?)\"/);\n\tif(!mboundary) throw new Error(\"MAD cannot find boundary\");\n\tvar boundary = \"--\" + (mboundary[1] || \"\");\n\n\tvar FileIndex/*:CFBFileIndex*/ = [], FullPaths/*:Array<string>*/ = [];\n\tvar o = {\n\t\tFileIndex: FileIndex,\n\t\tFullPaths: FullPaths\n\t};\n\tinit_cfb(o);\n\tvar start_di, fcnt = 0;\n\tfor(di = 0; di < data.length; ++di) {\n\t\tvar line = data[di];\n\t\tif(line !== boundary && line !== boundary + \"--\") continue;\n\t\tif(fcnt++) parse_mime(o, data.slice(start_di, di), root);\n\t\tstart_di = di;\n\t}\n\treturn o;\n}\n\nfunction write_mad(cfb/*:CFBContainer*/, options/*:CFBWriteOpts*/)/*:string*/ {\n\tvar opts = options || {};\n\tvar boundary = opts.boundary || \"SheetJS\";\n\tboundary = '------=' + boundary;\n\n\tvar out = [\n\t\t'MIME-Version: 1.0',\n\t\t'Content-Type: multipart/related; boundary=\"' + boundary.slice(2) + '\"',\n\t\t'',\n\t\t'',\n\t\t''\n\t];\n\n\tvar root = cfb.FullPaths[0], fp = root, fi = cfb.FileIndex[0];\n\tfor(var i = 1; i < cfb.FullPaths.length; ++i) {\n\t\tfp = cfb.FullPaths[i].slice(root.length);\n\t\tfi = cfb.FileIndex[i];\n\t\tif(!fi.size || !fi.content || fp == \"\\u0001Sh33tJ5\") continue;\n\n\t\t/* Normalize filename */\n\t\tfp = fp.replace(/[\\x00-\\x08\\x0B\\x0C\\x0E-\\x1F\\x7E-\\xFF]/g, function(c) {\n\t\t\treturn \"_x\" + c.charCodeAt(0).toString(16) + \"_\";\n\t\t}).replace(/[\\u0080-\\uFFFF]/g, function(u) {\n\t\t\treturn \"_u\" + u.charCodeAt(0).toString(16) + \"_\";\n\t\t});\n\n\t\t/* Extract content as binary string */\n\t\tvar ca = fi.content;\n\t\t// $FlowIgnore\n\t\tvar cstr = has_buf && Buffer.isBuffer(ca) ? ca.toString(\"binary\") : a2s(ca);\n\n\t\t/* 4/5 of first 1024 chars ascii -> quoted printable, else base64 */\n\t\tvar dispcnt = 0, L = Math.min(1024, cstr.length), cc = 0;\n\t\tfor(var csl = 0; csl <= L; ++csl) if((cc=cstr.charCodeAt(csl)) >= 0x20 && cc < 0x80) ++dispcnt;\n\t\tvar qp = dispcnt >= L * 4 / 5;\n\n\t\tout.push(boundary);\n\t\tout.push('Content-Location: ' + (opts.root || 'file:///C:/SheetJS/') + fp);\n\t\tout.push('Content-Transfer-Encoding: ' + (qp ? 'quoted-printable' : 'base64'));\n\t\tout.push('Content-Type: ' + get_content_type(fi, fp));\n\t\tout.push('');\n\n\t\tout.push(qp ? write_quoted_printable(cstr) : write_base64_76(cstr));\n\t}\n\tout.push(boundary + '--\\r\\n');\n\treturn out.join(\"\\r\\n\");\n}\nfunction cfb_new(opts/*:?any*/)/*:CFBContainer*/ {\n\tvar o/*:CFBContainer*/ = ({}/*:any*/);\n\tinit_cfb(o, opts);\n\treturn o;\n}\n\nfunction cfb_add(cfb/*:CFBContainer*/, name/*:string*/, content/*:?RawBytes*/, opts/*:?any*/)/*:CFBEntry*/ {\n\tvar unsafe = opts && opts.unsafe;\n\tif(!unsafe) init_cfb(cfb);\n\tvar file = !unsafe && CFB.find(cfb, name);\n\tif(!file) {\n\t\tvar fpath/*:string*/ = cfb.FullPaths[0];\n\t\tif(name.slice(0, fpath.length) == fpath) fpath = name;\n\t\telse {\n\t\t\tif(fpath.slice(-1) != \"/\") fpath += \"/\";\n\t\t\tfpath = (fpath + name).replace(\"//\",\"/\");\n\t\t}\n\t\tfile = ({name: filename(name), type: 2}/*:any*/);\n\t\tcfb.FileIndex.push(file);\n\t\tcfb.FullPaths.push(fpath);\n\t\tif(!unsafe) CFB.utils.cfb_gc(cfb);\n\t}\n\t/*:: if(!file) throw new Error(\"unreachable\"); */\n\tfile.content = (content/*:any*/);\n\tfile.size = content ? content.length : 0;\n\tif(opts) {\n\t\tif(opts.CLSID) file.clsid = opts.CLSID;\n\t\tif(opts.mt) file.mt = opts.mt;\n\t\tif(opts.ct) file.ct = opts.ct;\n\t}\n\treturn file;\n}\n\nfunction cfb_del(cfb/*:CFBContainer*/, name/*:string*/)/*:boolean*/ {\n\tinit_cfb(cfb);\n\tvar file = CFB.find(cfb, name);\n\tif(file) for(var j = 0; j < cfb.FileIndex.length; ++j) if(cfb.FileIndex[j] == file) {\n\t\tcfb.FileIndex.splice(j, 1);\n\t\tcfb.FullPaths.splice(j, 1);\n\t\treturn true;\n\t}\n\treturn false;\n}\n\nfunction cfb_mov(cfb/*:CFBContainer*/, old_name/*:string*/, new_name/*:string*/)/*:boolean*/ {\n\tinit_cfb(cfb);\n\tvar file = CFB.find(cfb, old_name);\n\tif(file) for(var j = 0; j < cfb.FileIndex.length; ++j) if(cfb.FileIndex[j] == file) {\n\t\tcfb.FileIndex[j].name = filename(new_name);\n\t\tcfb.FullPaths[j] = new_name;\n\t\treturn true;\n\t}\n\treturn false;\n}\n\nfunction cfb_gc(cfb/*:CFBContainer*/)/*:void*/ { rebuild_cfb(cfb, true); }\n\nexports.find = find;\nexports.read = read;\nexports.parse = parse;\nexports.write = write;\nexports.writeFile = write_file;\nexports.utils = {\n\tcfb_new: cfb_new,\n\tcfb_add: cfb_add,\n\tcfb_del: cfb_del,\n\tcfb_mov: cfb_mov,\n\tcfb_gc: cfb_gc,\n\tReadShift: ReadShift,\n\tCheckField: CheckField,\n\tprep_blob: prep_blob,\n\tbconcat: bconcat,\n\tuse_zlib: use_zlib,\n\t_deflateRaw: _deflate,\n\t_inflateRaw: _inflate,\n\tconsts: consts\n};\n\nreturn exports;\n})();\n\nlet _fs = void 0;\nfunction set_fs(fs) { _fs = fs; }\nexport { set_fs };\n\n/* normalize data for blob ctor */\nfunction blobify(data) {\n\tif(typeof data === \"string\") return s2ab(data);\n\tif(Array.isArray(data)) return a2u(data);\n\treturn data;\n}\n/* write or download file */\nfunction write_dl(fname/*:string*/, payload/*:any*/, enc/*:?string*/) {\n\t/*global IE_SaveFile, Blob, navigator, saveAs, document, File, chrome */\n\tif(typeof _fs !== 'undefined' && _fs.writeFileSync) return enc ? _fs.writeFileSync(fname, payload, enc) : _fs.writeFileSync(fname, payload);\n\tif(typeof Deno !== 'undefined') {\n\t\t/* in this spot, it's safe to assume typed arrays and TextEncoder/TextDecoder exist */\n\t\tif(enc && typeof payload == \"string\") switch(enc) {\n\t\t\tcase \"utf8\": payload = new TextEncoder(enc).encode(payload); break;\n\t\t\tcase \"binary\": payload = s2ab(payload); break;\n\t\t\t/* TODO: binary equivalent */\n\t\t\tdefault: throw new Error(\"Unsupported encoding \" + enc);\n\t\t}\n\t\treturn Deno.writeFileSync(fname, payload);\n\t}\n\tvar data = (enc == \"utf8\") ? utf8write(payload) : payload;\n\t/*:: declare var IE_SaveFile: any; */\n\tif(typeof IE_SaveFile !== 'undefined') return IE_SaveFile(data, fname);\n\tif(typeof Blob !== 'undefined') {\n\t\tvar blob = new Blob([blobify(data)], {type:\"application/octet-stream\"});\n\t\t/*:: declare var navigator: any; */\n\t\tif(typeof navigator !== 'undefined' && navigator.msSaveBlob) return navigator.msSaveBlob(blob, fname);\n\t\t/*:: declare var saveAs: any; */\n\t\tif(typeof saveAs !== 'undefined') return saveAs(blob, fname);\n\t\tif(typeof URL !== 'undefined' && typeof document !== 'undefined' && document.createElement && URL.createObjectURL) {\n\t\t\tvar url = URL.createObjectURL(blob);\n\t\t\t/*:: declare var chrome: any; */\n\t\t\tif(typeof chrome === 'object' && typeof (chrome.downloads||{}).download == \"function\") {\n\t\t\t\tif(URL.revokeObjectURL && typeof setTimeout !== 'undefined') setTimeout(function() { URL.revokeObjectURL(url); }, 60000);\n\t\t\t\treturn chrome.downloads.download({ url: url, filename: fname, saveAs: true});\n\t\t\t}\n\t\t\tvar a = document.createElement(\"a\");\n\t\t\tif(a.download != null) {\n\t\t\t\t/*:: if(document.body == null) throw new Error(\"unreachable\"); */\n\t\t\t\ta.download = fname; a.href = url; document.body.appendChild(a); a.click();\n\t\t\t\t/*:: if(document.body == null) throw new Error(\"unreachable\"); */ document.body.removeChild(a);\n\t\t\t\tif(URL.revokeObjectURL && typeof setTimeout !== 'undefined') setTimeout(function() { URL.revokeObjectURL(url); }, 60000);\n\t\t\t\treturn url;\n\t\t\t}\n\t\t}\n\t}\n\t// $FlowIgnore\n\tif(typeof $ !== 'undefined' && typeof File !== 'undefined' && typeof Folder !== 'undefined') try { // extendscript\n\t\t// $FlowIgnore\n\t\tvar out = File(fname); out.open(\"w\"); out.encoding = \"binary\";\n\t\tif(Array.isArray(payload)) payload = a2s(payload);\n\t\tout.write(payload); out.close(); return payload;\n\t} catch(e) { if(!e.message || !e.message.match(/onstruct/)) throw e; }\n\tthrow new Error(\"cannot save file \" + fname);\n}\n\n/* read binary data from file */\nfunction read_binary(path/*:string*/) {\n\tif(typeof _fs !== 'undefined') return _fs.readFileSync(path);\n\tif(typeof Deno !== 'undefined') return Deno.readFileSync(path);\n\t// $FlowIgnore\n\tif(typeof $ !== 'undefined' && typeof File !== 'undefined' && typeof Folder !== 'undefined') try { // extendscript\n\t\t// $FlowIgnore\n\t\tvar infile = File(path); infile.open(\"r\"); infile.encoding = \"binary\";\n\t\tvar data = infile.read(); infile.close();\n\t\treturn data;\n\t} catch(e) { if(!e.message || !e.message.match(/onstruct/)) throw e; }\n\tthrow new Error(\"Cannot access file \" + path);\n}\nfunction keys(o/*:any*/)/*:Array<any>*/ {\n\tvar ks = Object.keys(o), o2 = [];\n\tfor(var i = 0; i < ks.length; ++i) if(Object.prototype.hasOwnProperty.call(o, ks[i])) o2.push(ks[i]);\n\treturn o2;\n}\n\nfunction evert_key(obj/*:any*/, key/*:string*/)/*:EvertType*/ {\n\tvar o = ([]/*:any*/), K = keys(obj);\n\tfor(var i = 0; i !== K.length; ++i) if(o[obj[K[i]][key]] == null) o[obj[K[i]][key]] = K[i];\n\treturn o;\n}\n\nfunction evert(obj/*:any*/)/*:EvertType*/ {\n\tvar o = ([]/*:any*/), K = keys(obj);\n\tfor(var i = 0; i !== K.length; ++i) o[obj[K[i]]] = K[i];\n\treturn o;\n}\n\nfunction evert_num(obj/*:any*/)/*:EvertNumType*/ {\n\tvar o = ([]/*:any*/), K = keys(obj);\n\tfor(var i = 0; i !== K.length; ++i) o[obj[K[i]]] = parseInt(K[i],10);\n\treturn o;\n}\n\nfunction evert_arr(obj/*:any*/)/*:EvertArrType*/ {\n\tvar o/*:EvertArrType*/ = ([]/*:any*/), K = keys(obj);\n\tfor(var i = 0; i !== K.length; ++i) {\n\t\tif(o[obj[K[i]]] == null) o[obj[K[i]]] = [];\n\t\to[obj[K[i]]].push(K[i]);\n\t}\n\treturn o;\n}\n\nvar basedate = /*#__PURE__*/new Date(1899, 11, 30, 0, 0, 0); // 2209161600000\nfunction datenum(v/*:Date*/, date1904/*:?boolean*/)/*:number*/ {\n\tvar epoch = /*#__PURE__*/v.getTime();\n\tif(date1904) epoch -= 1462*24*60*60*1000;\n\tvar dnthresh = /*#__PURE__*/basedate.getTime() + (/*#__PURE__*/v.getTimezoneOffset() - /*#__PURE__*/basedate.getTimezoneOffset()) * 60000;\n\treturn (epoch - dnthresh) / (24 * 60 * 60 * 1000);\n}\nvar refdate = /*#__PURE__*/new Date();\nvar dnthresh = /*#__PURE__*/basedate.getTime() + (/*#__PURE__*/refdate.getTimezoneOffset() - /*#__PURE__*/basedate.getTimezoneOffset()) * 60000;\nvar refoffset = /*#__PURE__*/refdate.getTimezoneOffset();\nfunction numdate(v/*:number*/)/*:Date*/ {\n\tvar out = new Date();\n\tout.setTime(v * 24 * 60 * 60 * 1000 + dnthresh);\n\tif (out.getTimezoneOffset() !== refoffset) {\n\t\tout.setTime(out.getTime() + (out.getTimezoneOffset() - refoffset) * 60000);\n\t}\n\treturn out;\n}\n\n/* ISO 8601 Duration */\nfunction parse_isodur(s) {\n\tvar sec = 0, mt = 0, time = false;\n\tvar m = s.match(/P([0-9\\.]+Y)?([0-9\\.]+M)?([0-9\\.]+D)?T([0-9\\.]+H)?([0-9\\.]+M)?([0-9\\.]+S)?/);\n\tif(!m) throw new Error(\"|\" + s + \"| is not an ISO8601 Duration\");\n\tfor(var i = 1; i != m.length; ++i) {\n\t\tif(!m[i]) continue;\n\t\tmt = 1;\n\t\tif(i > 3) time = true;\n\t\tswitch(m[i].slice(m[i].length-1)) {\n\t\t\tcase 'Y':\n\t\t\t\tthrow new Error(\"Unsupported ISO Duration Field: \" + m[i].slice(m[i].length-1));\n\t\t\tcase 'D': mt *= 24;\n\t\t\t\t/* falls through */\n\t\t\tcase 'H': mt *= 60;\n\t\t\t\t/* falls through */\n\t\t\tcase 'M':\n\t\t\t\tif(!time) throw new Error(\"Unsupported ISO Duration Field: M\");\n\t\t\t\telse mt *= 60;\n\t\t\t\t/* falls through */\n\t\t\tcase 'S': break;\n\t\t}\n\t\tsec += mt * parseInt(m[i], 10);\n\t}\n\treturn sec;\n}\n\nvar good_pd_date_1 = /*#__PURE__*/new Date('2017-02-19T19:06:09.000Z');\nvar good_pd_date = /*#__PURE__*/isNaN(/*#__PURE__*/good_pd_date_1.getFullYear()) ? /*#__PURE__*/new Date('2/19/17') : good_pd_date_1;\nvar good_pd = /*#__PURE__*/good_pd_date.getFullYear() == 2017;\n/* parses a date as a local date */\nfunction parseDate(str/*:string|Date*/, fixdate/*:?number*/)/*:Date*/ {\n\tvar d = new Date(str);\n\tif(good_pd) {\n\t\t/*:: if(fixdate == null) fixdate = 0; */\n\t\tif(fixdate > 0) d.setTime(d.getTime() + d.getTimezoneOffset() * 60 * 1000);\n\t\telse if(fixdate < 0) d.setTime(d.getTime() - d.getTimezoneOffset() * 60 * 1000);\n\t\treturn d;\n\t}\n\tif(str instanceof Date) return str;\n\tif(good_pd_date.getFullYear() == 1917 && !isNaN(d.getFullYear())) {\n\t\tvar s = d.getFullYear();\n\t\tif(str.indexOf(\"\" + s) > -1) return d;\n\t\td.setFullYear(d.getFullYear() + 100); return d;\n\t}\n\tvar n = str.match(/\\d+/g)||[\"2017\",\"2\",\"19\",\"0\",\"0\",\"0\"];\n\tvar out = new Date(+n[0], +n[1] - 1, +n[2], (+n[3]||0), (+n[4]||0), (+n[5]||0));\n\tif(str.indexOf(\"Z\") > -1) out = new Date(out.getTime() - out.getTimezoneOffset() * 60 * 1000);\n\treturn out;\n}\n\nfunction cc2str(arr/*:Array<number>*/, debomit)/*:string*/ {\n\tif(has_buf && Buffer.isBuffer(arr)) {\n\t\tif(debomit) {\n\t\t\tif(arr[0] == 0xFF && arr[1] == 0xFE) return utf8write(arr.slice(2).toString(\"utf16le\"));\n\t\t\tif(arr[1] == 0xFE && arr[2] == 0xFF) return utf8write(utf16beread(arr.slice(2).toString(\"binary\")));\n\t\t}\n\t\treturn arr.toString(\"binary\");\n\t}\n\n\tif(typeof TextDecoder !== \"undefined\") try {\n\t\tif(debomit) {\n\t\t\tif(arr[0] == 0xFF && arr[1] == 0xFE) return utf8write(new TextDecoder(\"utf-16le\").decode(arr.slice(2)));\n\t\t\tif(arr[0] == 0xFE && arr[1] == 0xFF) return utf8write(new TextDecoder(\"utf-16be\").decode(arr.slice(2)));\n\t\t}\n\t\tvar rev = {\n\t\t\t\"\\u20ac\": \"\\x80\", \"\\u201a\": \"\\x82\", \"\\u0192\": \"\\x83\", \"\\u201e\": \"\\x84\",\n\t\t\t\"\\u2026\": \"\\x85\", \"\\u2020\": \"\\x86\", \"\\u2021\": \"\\x87\", \"\\u02c6\": \"\\x88\",\n\t\t\t\"\\u2030\": \"\\x89\", \"\\u0160\": \"\\x8a\", \"\\u2039\": \"\\x8b\", \"\\u0152\": \"\\x8c\",\n\t\t\t\"\\u017d\": \"\\x8e\", \"\\u2018\": \"\\x91\", \"\\u2019\": \"\\x92\", \"\\u201c\": \"\\x93\",\n\t\t\t\"\\u201d\": \"\\x94\", \"\\u2022\": \"\\x95\", \"\\u2013\": \"\\x96\", \"\\u2014\": \"\\x97\",\n\t\t\t\"\\u02dc\": \"\\x98\", \"\\u2122\": \"\\x99\", \"\\u0161\": \"\\x9a\", \"\\u203a\": \"\\x9b\",\n\t\t\t\"\\u0153\": \"\\x9c\", \"\\u017e\": \"\\x9e\", \"\\u0178\": \"\\x9f\"\n\t\t};\n\t\tif(Array.isArray(arr)) arr = new Uint8Array(arr);\n\t\treturn new TextDecoder(\"latin1\").decode(arr).replace(/[€‚ƒ„…†‡ˆ‰Š‹ŒŽ‘’“”•–—˜™š›œžŸ]/g, function(c) { return rev[c] || c; });\n\t} catch(e) {}\n\n\tvar o = [];\n\tfor(var i = 0; i != arr.length; ++i) o.push(String.fromCharCode(arr[i]));\n\treturn o.join(\"\");\n}\n\nfunction dup(o/*:any*/)/*:any*/ {\n\tif(typeof JSON != 'undefined' && !Array.isArray(o)) return JSON.parse(JSON.stringify(o));\n\tif(typeof o != 'object' || o == null) return o;\n\tif(o instanceof Date) return new Date(o.getTime());\n\tvar out = {};\n\tfor(var k in o) if(Object.prototype.hasOwnProperty.call(o, k)) out[k] = dup(o[k]);\n\treturn out;\n}\n\nfunction fill(c/*:string*/,l/*:number*/)/*:string*/ { var o = \"\"; while(o.length < l) o+=c; return o; }\n\n/* TODO: stress test */\nfunction fuzzynum(s/*:string*/)/*:number*/ {\n\tvar v/*:number*/ = Number(s);\n\tif(!isNaN(v)) return isFinite(v) ? v : NaN;\n\tif(!/\\d/.test(s)) return v;\n\tvar wt = 1;\n\tvar ss = s.replace(/([\\d]),([\\d])/g,\"$1$2\").replace(/[$]/g,\"\").replace(/[%]/g, function() { wt *= 100; return \"\";});\n\tif(!isNaN(v = Number(ss))) return v / wt;\n\tss = ss.replace(/[(](.*)[)]/,function($$, $1) { wt = -wt; return $1;});\n\tif(!isNaN(v = Number(ss))) return v / wt;\n\treturn v;\n}\nvar lower_months = ['january', 'february', 'march', 'april', 'may', 'june', 'july', 'august', 'september', 'october', 'november', 'december'];\nfunction fuzzydate(s/*:string*/)/*:Date*/ {\n\tvar o = new Date(s), n = new Date(NaN);\n\tvar y = o.getYear(), m = o.getMonth(), d = o.getDate();\n\tif(isNaN(d)) return n;\n\tvar lower = s.toLowerCase();\n\tif(lower.match(/jan|feb|mar|apr|may|jun|jul|aug|sep|oct|nov|dec/)) {\n\t\tlower = lower.replace(/[^a-z]/g,\"\").replace(/([^a-z]|^)[ap]m?([^a-z]|$)/,\"\");\n\t\tif(lower.length > 3 && lower_months.indexOf(lower) == -1) return n;\n\t} else if(lower.match(/[a-z]/)) return n;\n\tif(y < 0 || y > 8099) return n;\n\tif((m > 0 || d > 1) && y != 101) return o;\n\tif(s.match(/[^-0-9:,\\/\\\\]/)) return n;\n\treturn o;\n}\n\nvar split_regex = /*#__PURE__*/(function() {\n\tvar safe_split_regex = \"abacaba\".split(/(:?b)/i).length == 5;\n\treturn function split_regex(str/*:string*/, re, def/*:string*/)/*:Array<string>*/ {\n\t\tif(safe_split_regex || typeof re == \"string\") return str.split(re);\n\t\tvar p = str.split(re), o = [p[0]];\n\t\tfor(var i = 1; i < p.length; ++i) { o.push(def); o.push(p[i]); }\n\t\treturn o;\n\t};\n})();\nfunction getdatastr(data)/*:?string*/ {\n\tif(!data) return null;\n\tif(data.content && data.type) return cc2str(data.content, true);\n\tif(data.data) return debom(data.data);\n\tif(data.asNodeBuffer && has_buf) return debom(data.asNodeBuffer().toString('binary'));\n\tif(data.asBinary) return debom(data.asBinary());\n\tif(data._data && data._data.getContent) return debom(cc2str(Array.prototype.slice.call(data._data.getContent(),0)));\n\treturn null;\n}\n\nfunction getdatabin(data) {\n\tif(!data) return null;\n\tif(data.data) return char_codes(data.data);\n\tif(data.asNodeBuffer && has_buf) return data.asNodeBuffer();\n\tif(data._data && data._data.getContent) {\n\t\tvar o = data._data.getContent();\n\t\tif(typeof o == \"string\") return char_codes(o);\n\t\treturn Array.prototype.slice.call(o);\n\t}\n\tif(data.content && data.type) return data.content;\n\treturn null;\n}\n\nfunction getdata(data) { return (data && data.name.slice(-4) === \".bin\") ? getdatabin(data) : getdatastr(data); }\n\n/* Part 2 Section 10.1.2 \"Mapping Content Types\" Names are case-insensitive */\n/* OASIS does not comment on filename case sensitivity */\nfunction safegetzipfile(zip, file/*:string*/) {\n\tvar k = zip.FullPaths || keys(zip.files);\n\tvar f = file.toLowerCase().replace(/[\\/]/g, '\\\\'), g = f.replace(/\\\\/g,'\\/');\n\tfor(var i=0; i<k.length; ++i) {\n\t\tvar n = k[i].replace(/^Root Entry[\\/]/,\"\").toLowerCase();\n\t\tif(f == n || g == n) return zip.files ? zip.files[k[i]] : zip.FileIndex[i];\n\t}\n\treturn null;\n}\n\nfunction getzipfile(zip, file/*:string*/) {\n\tvar o = safegetzipfile(zip, file);\n\tif(o == null) throw new Error(\"Cannot find file \" + file + \" in zip\");\n\treturn o;\n}\n\nfunction getzipdata(zip, file/*:string*/, safe/*:?boolean*/)/*:any*/ {\n\tif(!safe) return getdata(getzipfile(zip, file));\n\tif(!file) return null;\n\ttry { return getzipdata(zip, file); } catch(e) { return null; }\n}\n\nfunction getzipstr(zip, file/*:string*/, safe/*:?boolean*/)/*:?string*/ {\n\tif(!safe) return getdatastr(getzipfile(zip, file));\n\tif(!file) return null;\n\ttry { return getzipstr(zip, file); } catch(e) { return null; }\n}\n\nfunction getzipbin(zip, file/*:string*/, safe/*:?boolean*/)/*:any*/ {\n\tif(!safe) return getdatabin(getzipfile(zip, file));\n\tif(!file) return null;\n\ttry { return getzipbin(zip, file); } catch(e) { return null; }\n}\n\nfunction zipentries(zip) {\n\tvar k = zip.FullPaths || keys(zip.files), o = [];\n\tfor(var i = 0; i < k.length; ++i) if(k[i].slice(-1) != '/') o.push(k[i].replace(/^Root Entry[\\/]/, \"\"));\n\treturn o.sort();\n}\n\nfunction zip_add_file(zip, path, content) {\n\tif(zip.FullPaths) {\n\t\tif(typeof content == \"string\") {\n\t\t\tvar res;\n\t\t\tif(has_buf) res = Buffer_from(content);\n\t\t\t/* TODO: investigate performance in Edge 13 */\n\t\t\t//else if(typeof TextEncoder !== \"undefined\") res = new TextEncoder().encode(content);\n\t\t\telse res = utf8decode(content);\n\t\t\treturn CFB.utils.cfb_add(zip, path, res);\n\t\t}\n\t\tCFB.utils.cfb_add(zip, path, content);\n\t}\n\telse zip.file(path, content);\n}\n\nfunction zip_new() { return CFB.utils.cfb_new(); }\n\nfunction zip_read(d, o) {\n\tswitch(o.type) {\n\t\tcase \"base64\": return CFB.read(d, { type: \"base64\" });\n\t\tcase \"binary\": return CFB.read(d, { type: \"binary\" });\n\t\tcase \"buffer\": case \"array\": return CFB.read(d, { type: \"buffer\" });\n\t}\n\tthrow new Error(\"Unrecognized type \" + o.type);\n}\n\nfunction resolve_path(path/*:string*/, base/*:string*/)/*:string*/ {\n\tif(path.charAt(0) == \"/\") return path.slice(1);\n\tvar result = base.split('/');\n\tif(base.slice(-1) != \"/\") result.pop(); // folder path\n\tvar target = path.split('/');\n\twhile (target.length !== 0) {\n\t\tvar step = target.shift();\n\t\tif (step === '..') result.pop();\n\t\telse if (step !== '.') result.push(step);\n\t}\n\treturn result.join('/');\n}\nvar XML_HEADER = '<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"yes\"?>\\r\\n';\nvar attregexg=/([^\"\\s?>\\/]+)\\s*=\\s*((?:\")([^\"]*)(?:\")|(?:')([^']*)(?:')|([^'\">\\s]+))/g;\nvar tagregex1=/<[\\/\\?]?[a-zA-Z0-9:_-]+(?:\\s+[^\"\\s?>\\/]+\\s*=\\s*(?:\"[^\"]*\"|'[^']*'|[^'\">\\s=]+))*\\s*[\\/\\?]?>/mg, tagregex2 = /<[^>]*>/g;\nvar tagregex = /*#__PURE__*/XML_HEADER.match(tagregex1) ? tagregex1 : tagregex2;\nvar nsregex=/<\\w*:/, nsregex2 = /<(\\/?)\\w+:/;\nfunction parsexmltag(tag/*:string*/, skip_root/*:?boolean*/, skip_LC/*:?boolean*/)/*:any*/ {\n\tvar z = ({}/*:any*/);\n\tvar eq = 0, c = 0;\n\tfor(; eq !== tag.length; ++eq) if((c = tag.charCodeAt(eq)) === 32 || c === 10 || c === 13) break;\n\tif(!skip_root) z[0] = tag.slice(0, eq);\n\tif(eq === tag.length) return z;\n\tvar m = tag.match(attregexg), j=0, v=\"\", i=0, q=\"\", cc=\"\", quot = 1;\n\tif(m) for(i = 0; i != m.length; ++i) {\n\t\tcc = m[i];\n\t\tfor(c=0; c != cc.length; ++c) if(cc.charCodeAt(c) === 61) break;\n\t\tq = cc.slice(0,c).trim();\n\t\twhile(cc.charCodeAt(c+1) == 32) ++c;\n\t\tquot = ((eq=cc.charCodeAt(c+1)) == 34 || eq == 39) ? 1 : 0;\n\t\tv = cc.slice(c+1+quot, cc.length-quot);\n\t\tfor(j=0;j!=q.length;++j) if(q.charCodeAt(j) === 58) break;\n\t\tif(j===q.length) {\n\t\t\tif(q.indexOf(\"_\") > 0) q = q.slice(0, q.indexOf(\"_\")); // from ods\n\t\t\tz[q] = v;\n\t\t\tif(!skip_LC) z[q.toLowerCase()] = v;\n\t\t}\n\t\telse {\n\t\t\tvar k = (j===5 && q.slice(0,5)===\"xmlns\"?\"xmlns\":\"\")+q.slice(j+1);\n\t\t\tif(z[k] && q.slice(j-3,j) == \"ext\") continue; // from ods\n\t\t\tz[k] = v;\n\t\t\tif(!skip_LC) z[k.toLowerCase()] = v;\n\t\t}\n\t}\n\treturn z;\n}\nfunction strip_ns(x/*:string*/)/*:string*/ { return x.replace(nsregex2, \"<$1\"); }\n\nvar encodings = {\n\t'&quot;': '\"',\n\t'&apos;': \"'\",\n\t'&gt;': '>',\n\t'&lt;': '<',\n\t'&amp;': '&'\n};\nvar rencoding = /*#__PURE__*/evert(encodings);\n//var rencstr = \"&<>'\\\"\".split(\"\");\n\n// TODO: CP remap (need to read file version to determine OS)\nvar unescapexml/*:StringConv*/ = /*#__PURE__*/(function() {\n\t/* 22.4.2.4 bstr (Basic String) */\n\tvar encregex = /&(?:quot|apos|gt|lt|amp|#x?([\\da-fA-F]+));/ig, coderegex = /_x([\\da-fA-F]{4})_/ig;\n\treturn function unescapexml(text/*:string*/)/*:string*/ {\n\t\tvar s = text + '', i = s.indexOf(\"<![CDATA[\");\n\t\tif(i == -1) return s.replace(encregex, function($$, $1) { return encodings[$$]||String.fromCharCode(parseInt($1,$$.indexOf(\"x\")>-1?16:10))||$$; }).replace(coderegex,function(m,c) {return String.fromCharCode(parseInt(c,16));});\n\t\tvar j = s.indexOf(\"]]>\");\n\t\treturn unescapexml(s.slice(0, i)) + s.slice(i+9,j) + unescapexml(s.slice(j+3));\n\t};\n})();\n\nvar decregex=/[&<>'\"]/g, charegex = /[\\u0000-\\u0008\\u000b-\\u001f]/g;\nfunction escapexml(text/*:string*/)/*:string*/{\n\tvar s = text + '';\n\treturn s.replace(decregex, function(y) { return rencoding[y]; }).replace(charegex,function(s) { return \"_x\" + (\"000\"+s.charCodeAt(0).toString(16)).slice(-4) + \"_\";});\n}\nfunction escapexmltag(text/*:string*/)/*:string*/{ return escapexml(text).replace(/ /g,\"_x0020_\"); }\n\nvar htmlcharegex = /[\\u0000-\\u001f]/g;\nfunction escapehtml(text/*:string*/)/*:string*/{\n\tvar s = text + '';\n\treturn s.replace(decregex, function(y) { return rencoding[y]; }).replace(/\\n/g, \"<br/>\").replace(htmlcharegex,function(s) { return \"&#x\" + (\"000\"+s.charCodeAt(0).toString(16)).slice(-4) + \";\"; });\n}\n\nfunction escapexlml(text/*:string*/)/*:string*/{\n\tvar s = text + '';\n\treturn s.replace(decregex, function(y) { return rencoding[y]; }).replace(htmlcharegex,function(s) { return \"&#x\" + (s.charCodeAt(0).toString(16)).toUpperCase() + \";\"; });\n}\n\n/* TODO: handle codepages */\nvar xlml_fixstr/*:StringConv*/ = /*#__PURE__*/(function() {\n\tvar entregex = /&#(\\d+);/g;\n\tfunction entrepl($$/*:string*/,$1/*:string*/)/*:string*/ { return String.fromCharCode(parseInt($1,10)); }\n\treturn function xlml_fixstr(str/*:string*/)/*:string*/ { return str.replace(entregex,entrepl); };\n})();\nfunction xlml_unfixstr(str/*:string*/)/*:string*/ { return str.replace(/(\\r\\n|[\\r\\n])/g,\"\\&#10;\"); }\n\nfunction parsexmlbool(value/*:any*/)/*:boolean*/ {\n\tswitch(value) {\n\t\tcase 1: case true: case '1': case 'true': case 'TRUE': return true;\n\t\t/* case '0': case 'false': case 'FALSE':*/\n\t\tdefault: return false;\n\t}\n}\n\nfunction utf8reada(orig/*:string*/)/*:string*/ {\n\tvar out = \"\", i = 0, c = 0, d = 0, e = 0, f = 0, w = 0;\n\twhile (i < orig.length) {\n\t\tc = orig.charCodeAt(i++);\n\t\tif (c < 128) { out += String.fromCharCode(c); continue; }\n\t\td = orig.charCodeAt(i++);\n\t\tif (c>191 && c<224) { f = ((c & 31) << 6); f |= (d & 63); out += String.fromCharCode(f); continue; }\n\t\te = orig.charCodeAt(i++);\n\t\tif (c < 240) { out += String.fromCharCode(((c & 15) << 12) | ((d & 63) << 6) | (e & 63)); continue; }\n\t\tf = orig.charCodeAt(i++);\n\t\tw = (((c & 7) << 18) | ((d & 63) << 12) | ((e & 63) << 6) | (f & 63))-65536;\n\t\tout += String.fromCharCode(0xD800 + ((w>>>10)&1023));\n\t\tout += String.fromCharCode(0xDC00 + (w&1023));\n\t}\n\treturn out;\n}\n\nfunction utf8readb(data) {\n\tvar out = new_raw_buf(2*data.length), w, i, j = 1, k = 0, ww=0, c;\n\tfor(i = 0; i < data.length; i+=j) {\n\t\tj = 1;\n\t\tif((c=data.charCodeAt(i)) < 128) w = c;\n\t\telse if(c < 224) { w = (c&31)*64+(data.charCodeAt(i+1)&63); j=2; }\n\t\telse if(c < 240) { w=(c&15)*4096+(data.charCodeAt(i+1)&63)*64+(data.charCodeAt(i+2)&63); j=3; }\n\t\telse { j = 4;\n\t\t\tw = (c & 7)*262144+(data.charCodeAt(i+1)&63)*4096+(data.charCodeAt(i+2)&63)*64+(data.charCodeAt(i+3)&63);\n\t\t\tw -= 65536; ww = 0xD800 + ((w>>>10)&1023); w = 0xDC00 + (w&1023);\n\t\t}\n\t\tif(ww !== 0) { out[k++] = ww&255; out[k++] = ww>>>8; ww = 0; }\n\t\tout[k++] = w%256; out[k++] = w>>>8;\n\t}\n\treturn out.slice(0,k).toString('ucs2');\n}\n\nfunction utf8readc(data) { return Buffer_from(data, 'binary').toString('utf8'); }\n\nvar utf8corpus = \"foo bar baz\\u00e2\\u0098\\u0083\\u00f0\\u009f\\u008d\\u00a3\";\nvar utf8read = has_buf && (/*#__PURE__*/utf8readc(utf8corpus) == /*#__PURE__*/utf8reada(utf8corpus) && utf8readc || /*#__PURE__*/utf8readb(utf8corpus) == /*#__PURE__*/utf8reada(utf8corpus) && utf8readb) || utf8reada;\n\nvar utf8write/*:StringConv*/ = has_buf ? function(data) { return Buffer_from(data, 'utf8').toString(\"binary\"); } : function(orig/*:string*/)/*:string*/ {\n\tvar out/*:Array<string>*/ = [], i = 0, c = 0, d = 0;\n\twhile(i < orig.length) {\n\t\tc = orig.charCodeAt(i++);\n\t\tswitch(true) {\n\t\t\tcase c < 128: out.push(String.fromCharCode(c)); break;\n\t\t\tcase c < 2048:\n\t\t\t\tout.push(String.fromCharCode(192 + (c >> 6)));\n\t\t\t\tout.push(String.fromCharCode(128 + (c & 63)));\n\t\t\t\tbreak;\n\t\t\tcase c >= 55296 && c < 57344:\n\t\t\t\tc -= 55296; d = orig.charCodeAt(i++) - 56320 + (c<<10);\n\t\t\t\tout.push(String.fromCharCode(240 + ((d >>18) & 7)));\n\t\t\t\tout.push(String.fromCharCode(144 + ((d >>12) & 63)));\n\t\t\t\tout.push(String.fromCharCode(128 + ((d >> 6) & 63)));\n\t\t\t\tout.push(String.fromCharCode(128 + (d & 63)));\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tout.push(String.fromCharCode(224 + (c >> 12)));\n\t\t\t\tout.push(String.fromCharCode(128 + ((c >> 6) & 63)));\n\t\t\t\tout.push(String.fromCharCode(128 + (c & 63)));\n\t\t}\n\t}\n\treturn out.join(\"\");\n};\n\n// matches <foo>...</foo> extracts content\nvar matchtag = /*#__PURE__*/(function() {\n\tvar mtcache/*:{[k:string]:RegExp}*/ = ({}/*:any*/);\n\treturn function matchtag(f/*:string*/,g/*:?string*/)/*:RegExp*/ {\n\t\tvar t = f+\"|\"+(g||\"\");\n\t\tif(mtcache[t]) return mtcache[t];\n\t\treturn (mtcache[t] = new RegExp('<(?:\\\\w+:)?'+f+'(?: xml:space=\"preserve\")?(?:[^>]*)>([\\\\s\\\\S]*?)</(?:\\\\w+:)?'+f+'>',((g||\"\")/*:any*/)));\n\t};\n})();\n\nvar htmldecode/*:{(s:string):string}*/ = /*#__PURE__*/(function() {\n\tvar entities/*:Array<[RegExp, string]>*/ = [\n\t\t['nbsp', ' '], ['middot', '·'],\n\t\t['quot', '\"'], ['apos', \"'\"], ['gt',   '>'], ['lt',   '<'], ['amp',  '&']\n\t].map(function(x/*:[string, string]*/) { return [new RegExp('&' + x[0] + ';', \"ig\"), x[1]]; });\n\treturn function htmldecode(str/*:string*/)/*:string*/ {\n\t\tvar o = str\n\t\t\t\t// Remove new lines and spaces from start of content\n\t\t\t\t.replace(/^[\\t\\n\\r ]+/, \"\")\n\t\t\t\t// Remove new lines and spaces from end of content\n\t\t\t\t.replace(/[\\t\\n\\r ]+$/,\"\")\n\t\t\t\t// Added line which removes any white space characters after and before html tags\n\t\t\t\t.replace(/>\\s+/g,\">\").replace(/\\s+</g,\"<\")\n\t\t\t\t// Replace remaining new lines and spaces with space\n\t\t\t\t.replace(/[\\t\\n\\r ]+/g, \" \")\n\t\t\t\t// Replace <br> tags with new lines\n\t\t\t\t.replace(/<\\s*[bB][rR]\\s*\\/?>/g,\"\\n\")\n\t\t\t\t// Strip HTML elements\n\t\t\t\t.replace(/<[^>]*>/g,\"\");\n\t\tfor(var i = 0; i < entities.length; ++i) o = o.replace(entities[i][0], entities[i][1]);\n\t\treturn o;\n\t};\n})();\n\nvar vtregex = /*#__PURE__*/(function(){ var vt_cache = {};\n\treturn function vt_regex(bt) {\n\t\tif(vt_cache[bt] !== undefined) return vt_cache[bt];\n\t\treturn (vt_cache[bt] = new RegExp(\"<(?:vt:)?\" + bt + \">([\\\\s\\\\S]*?)</(?:vt:)?\" + bt + \">\", 'g') );\n};})();\nvar vtvregex = /<\\/?(?:vt:)?variant>/g, vtmregex = /<(?:vt:)([^>]*)>([\\s\\S]*)</;\nfunction parseVector(data/*:string*/, opts)/*:Array<{v:string,t:string}>*/ {\n\tvar h = parsexmltag(data);\n\n\tvar matches/*:Array<string>*/ = data.match(vtregex(h.baseType))||[];\n\tvar res/*:Array<any>*/ = [];\n\tif(matches.length != h.size) {\n\t\tif(opts.WTF) throw new Error(\"unexpected vector length \" + matches.length + \" != \" + h.size);\n\t\treturn res;\n\t}\n\tmatches.forEach(function(x/*:string*/) {\n\t\tvar v = x.replace(vtvregex,\"\").match(vtmregex);\n\t\tif(v) res.push({v:utf8read(v[2]), t:v[1]});\n\t});\n\treturn res;\n}\n\nvar wtregex = /(^\\s|\\s$|\\n)/;\nfunction writetag(f/*:string*/,g/*:string*/)/*:string*/ { return '<' + f + (g.match(wtregex)?' xml:space=\"preserve\"' : \"\") + '>' + g + '</' + f + '>'; }\n\nfunction wxt_helper(h)/*:string*/ { return keys(h).map(function(k) { return \" \" + k + '=\"' + h[k] + '\"';}).join(\"\"); }\nfunction writextag(f/*:string*/,g/*:?string*/,h) { return '<' + f + ((h != null) ? wxt_helper(h) : \"\") + ((g != null) ? (g.match(wtregex)?' xml:space=\"preserve\"' : \"\") + '>' + g + '</' + f : \"/\") + '>';}\n\nfunction write_w3cdtf(d/*:Date*/, t/*:?boolean*/)/*:string*/ { try { return d.toISOString().replace(/\\.\\d*/,\"\"); } catch(e) { if(t) throw e; } return \"\"; }\n\nfunction write_vt(s, xlsx/*:?boolean*/)/*:string*/ {\n\tswitch(typeof s) {\n\t\tcase 'string':\n\t\t\tvar o = writextag('vt:lpwstr', escapexml(s));\n\t\t\tif(xlsx) o = o.replace(/&quot;/g, \"_x0022_\");\n\t\t\treturn o;\n\t\tcase 'number': return writextag((s|0)==s?'vt:i4':'vt:r8', escapexml(String(s)));\n\t\tcase 'boolean': return writextag('vt:bool',s?'true':'false');\n\t}\n\tif(s instanceof Date) return writextag('vt:filetime', write_w3cdtf(s));\n\tthrow new Error(\"Unable to serialize \" + s);\n}\n\nfunction xlml_normalize(d)/*:string*/ {\n\tif(has_buf &&/*::typeof Buffer !== \"undefined\" && d != null && d instanceof Buffer &&*/ Buffer.isBuffer(d)) return d.toString('utf8');\n\tif(typeof d === 'string') return d;\n\t/* duktape */\n\tif(typeof Uint8Array !== 'undefined' && d instanceof Uint8Array) return utf8read(a2s(ab2a(d)));\n\tthrow new Error(\"Bad input format: expected Buffer or string\");\n}\n/* UOS uses CJK in tags */\nvar xlmlregex = /<(\\/?)([^\\s?><!\\/:]*:|)([^\\s?<>:\\/]+)(?:[\\s?:\\/][^>]*)?>/mg;\n//var xlmlregex = /<(\\/?)([a-z0-9]*:|)(\\w+)[^>]*>/mg;\n\nvar XMLNS = ({\n\tCORE_PROPS: 'http://schemas.openxmlformats.org/package/2006/metadata/core-properties',\n\tCUST_PROPS: \"http://schemas.openxmlformats.org/officeDocument/2006/custom-properties\",\n\tEXT_PROPS: \"http://schemas.openxmlformats.org/officeDocument/2006/extended-properties\",\n\tCT: 'http://schemas.openxmlformats.org/package/2006/content-types',\n\tRELS: 'http://schemas.openxmlformats.org/package/2006/relationships',\n\tTCMNT: 'http://schemas.microsoft.com/office/spreadsheetml/2018/threadedcomments',\n\t'dc': 'http://purl.org/dc/elements/1.1/',\n\t'dcterms': 'http://purl.org/dc/terms/',\n\t'dcmitype': 'http://purl.org/dc/dcmitype/',\n\t'mx': 'http://schemas.microsoft.com/office/mac/excel/2008/main',\n\t'r': 'http://schemas.openxmlformats.org/officeDocument/2006/relationships',\n\t'sjs': 'http://schemas.openxmlformats.org/package/2006/sheetjs/core-properties',\n\t'vt': 'http://schemas.openxmlformats.org/officeDocument/2006/docPropsVTypes',\n\t'xsi': 'http://www.w3.org/2001/XMLSchema-instance',\n\t'xsd': 'http://www.w3.org/2001/XMLSchema'\n}/*:any*/);\n\nvar XMLNS_main = [\n\t'http://schemas.openxmlformats.org/spreadsheetml/2006/main',\n\t'http://purl.oclc.org/ooxml/spreadsheetml/main',\n\t'http://schemas.microsoft.com/office/excel/2006/main',\n\t'http://schemas.microsoft.com/office/excel/2006/2'\n];\n\nvar XLMLNS = ({\n\t'o':    'urn:schemas-microsoft-com:office:office',\n\t'x':    'urn:schemas-microsoft-com:office:excel',\n\t'ss':   'urn:schemas-microsoft-com:office:spreadsheet',\n\t'dt':   'uuid:C2F41010-65B3-11d1-A29F-00AA00C14882',\n\t'mv':   'http://macVmlSchemaUri',\n\t'v':    'urn:schemas-microsoft-com:vml',\n\t'html': 'http://www.w3.org/TR/REC-html40'\n}/*:any*/);\nfunction read_double_le(b/*:RawBytes|CFBlob*/, idx/*:number*/)/*:number*/ {\n\tvar s = 1 - 2 * (b[idx + 7] >>> 7);\n\tvar e = ((b[idx + 7] & 0x7f) << 4) + ((b[idx + 6] >>> 4) & 0x0f);\n\tvar m = (b[idx+6]&0x0f);\n\tfor(var i = 5; i >= 0; --i) m = m * 256 + b[idx + i];\n\tif(e == 0x7ff) return m == 0 ? (s * Infinity) : NaN;\n\tif(e == 0) e = -1022;\n\telse { e -= 1023; m += Math.pow(2,52); }\n\treturn s * Math.pow(2, e - 52) * m;\n}\n\nfunction write_double_le(b/*:RawBytes|CFBlob*/, v/*:number*/, idx/*:number*/) {\n\tvar bs = ((((v < 0) || (1/v == -Infinity)) ? 1 : 0) << 7), e = 0, m = 0;\n\tvar av = bs ? (-v) : v;\n\tif(!isFinite(av)) { e = 0x7ff; m = isNaN(v) ? 0x6969 : 0; }\n\telse if(av == 0) e = m = 0;\n\telse {\n\t\te = Math.floor(Math.log(av) / Math.LN2);\n\t\tm = av * Math.pow(2, 52 - e);\n\t\tif((e <= -1023) && (!isFinite(m) || (m < Math.pow(2,52)))) { e = -1022; }\n\t\telse { m -= Math.pow(2,52); e+=1023; }\n\t}\n\tfor(var i = 0; i <= 5; ++i, m/=256) b[idx + i] = m & 0xff;\n\tb[idx + 6] = ((e & 0x0f) << 4) | (m & 0xf);\n\tb[idx + 7] = (e >> 4) | bs;\n}\n\nvar ___toBuffer = function(bufs/*:Array<Array<RawBytes> >*/)/*:RawBytes*/ { var x=[],w=10240; for(var i=0;i<bufs[0].length;++i) if(bufs[0][i]) for(var j=0,L=bufs[0][i].length;j<L;j+=w) x.push.apply(x, bufs[0][i].slice(j,j+w)); return x; };\nvar __toBuffer = has_buf ? function(bufs) { return (bufs[0].length > 0 && Buffer.isBuffer(bufs[0][0])) ? Buffer.concat(bufs[0].map(function(x) { return Buffer.isBuffer(x) ? x : Buffer_from(x); })) : ___toBuffer(bufs);} : ___toBuffer;\n\nvar ___utf16le = function(b/*:RawBytes|CFBlob*/,s/*:number*/,e/*:number*/)/*:string*/ { var ss/*:Array<string>*/=[]; for(var i=s; i<e; i+=2) ss.push(String.fromCharCode(__readUInt16LE(b,i))); return ss.join(\"\").replace(chr0,''); };\nvar __utf16le = has_buf ? function(b/*:RawBytes|CFBlob*/,s/*:number*/,e/*:number*/)/*:string*/ { if(!Buffer.isBuffer(b)/*:: || !(b instanceof Buffer)*/) return ___utf16le(b,s,e); return b.toString('utf16le',s,e).replace(chr0,'')/*.replace(chr1,'!')*/; } : ___utf16le;\n\nvar ___hexlify = function(b/*:RawBytes|CFBlob*/,s/*:number*/,l/*:number*/)/*:string*/ { var ss/*:Array<string>*/=[]; for(var i=s; i<s+l; ++i) ss.push((\"0\" + b[i].toString(16)).slice(-2)); return ss.join(\"\"); };\nvar __hexlify = has_buf ? function(b/*:RawBytes|CFBlob*/,s/*:number*/,l/*:number*/)/*:string*/ { return Buffer.isBuffer(b)/*:: && b instanceof Buffer*/ ? b.toString('hex',s,s+l) : ___hexlify(b,s,l); } : ___hexlify;\n\nvar ___utf8 = function(b/*:RawBytes|CFBlob*/,s/*:number*/,e/*:number*/) { var ss=[]; for(var i=s; i<e; i++) ss.push(String.fromCharCode(__readUInt8(b,i))); return ss.join(\"\"); };\nvar __utf8 = has_buf ? function utf8_b(b/*:RawBytes|CFBlob*/, s/*:number*/, e/*:number*/) { return (Buffer.isBuffer(b)/*:: && (b instanceof Buffer)*/) ? b.toString('utf8',s,e) : ___utf8(b,s,e); } : ___utf8;\n\nvar ___lpstr = function(b/*:RawBytes|CFBlob*/,i/*:number*/) { var len = __readUInt32LE(b,i); return len > 0 ? __utf8(b, i+4,i+4+len-1) : \"\";};\nvar __lpstr = ___lpstr;\n\nvar ___cpstr = function(b/*:RawBytes|CFBlob*/,i/*:number*/) { var len = __readUInt32LE(b,i); return len > 0 ? __utf8(b, i+4,i+4+len-1) : \"\";};\nvar __cpstr = ___cpstr;\n\nvar ___lpwstr = function(b/*:RawBytes|CFBlob*/,i/*:number*/) { var len = 2*__readUInt32LE(b,i); return len > 0 ? __utf8(b, i+4,i+4+len-1) : \"\";};\nvar __lpwstr = ___lpwstr;\n\nvar ___lpp4 = function lpp4_(b/*:RawBytes|CFBlob*/,i/*:number*/) { var len = __readUInt32LE(b,i); return len > 0 ? __utf16le(b, i+4,i+4+len) : \"\";};\nvar __lpp4 = ___lpp4;\n\nvar ___8lpp4 = function(b/*:RawBytes|CFBlob*/,i/*:number*/) { var len = __readUInt32LE(b,i); return len > 0 ? __utf8(b, i+4,i+4+len) : \"\";};\nvar __8lpp4 = ___8lpp4;\n\nvar ___double = function(b/*:RawBytes|CFBlob*/, idx/*:number*/) { return read_double_le(b, idx);};\nvar __double = ___double;\n\nvar is_buf = function is_buf_a(a) { return Array.isArray(a) || (typeof Uint8Array !== \"undefined\" && a instanceof Uint8Array); };\n\nif(has_buf/*:: && typeof Buffer !== 'undefined'*/) {\n\t__lpstr = function lpstr_b(b/*:RawBytes|CFBlob*/, i/*:number*/) { if(!Buffer.isBuffer(b)/*:: || !(b instanceof Buffer)*/) return ___lpstr(b, i); var len = b.readUInt32LE(i); return len > 0 ? b.toString('utf8',i+4,i+4+len-1) : \"\";};\n\t__cpstr = function cpstr_b(b/*:RawBytes|CFBlob*/, i/*:number*/) { if(!Buffer.isBuffer(b)/*:: || !(b instanceof Buffer)*/) return ___cpstr(b, i); var len = b.readUInt32LE(i); return len > 0 ? b.toString('utf8',i+4,i+4+len-1) : \"\";};\n\t__lpwstr = function lpwstr_b(b/*:RawBytes|CFBlob*/, i/*:number*/) { if(!Buffer.isBuffer(b)/*:: || !(b instanceof Buffer)*/) return ___lpwstr(b, i); var len = 2*b.readUInt32LE(i); return b.toString('utf16le',i+4,i+4+len-1);};\n\t__lpp4 = function lpp4_b(b/*:RawBytes|CFBlob*/, i/*:number*/) { if(!Buffer.isBuffer(b)/*:: || !(b instanceof Buffer)*/) return ___lpp4(b, i); var len = b.readUInt32LE(i); return b.toString('utf16le',i+4,i+4+len);};\n\t__8lpp4 = function lpp4_8b(b/*:RawBytes|CFBlob*/, i/*:number*/) { if(!Buffer.isBuffer(b)/*:: || !(b instanceof Buffer)*/) return ___8lpp4(b, i); var len = b.readUInt32LE(i); return b.toString('utf8',i+4,i+4+len);};\n\t__double = function double_(b/*:RawBytes|CFBlob*/, i/*:number*/) { if(Buffer.isBuffer(b)/*::&& b instanceof Buffer*/) return b.readDoubleLE(i); return ___double(b,i); };\n\tis_buf = function is_buf_b(a) { return Buffer.isBuffer(a) || Array.isArray(a) || (typeof Uint8Array !== \"undefined\" && a instanceof Uint8Array); };\n}\n\n/* from js-xls */\nfunction cpdoit() {\n\t__utf16le = function(b/*:RawBytes|CFBlob*/,s/*:number*/,e/*:number*/) { return $cptable.utils.decode(1200, b.slice(s,e)).replace(chr0, ''); };\n\t__utf8 = function(b/*:RawBytes|CFBlob*/,s/*:number*/,e/*:number*/) { return $cptable.utils.decode(65001, b.slice(s,e)); };\n\t__lpstr = function(b/*:RawBytes|CFBlob*/,i/*:number*/) { var len = __readUInt32LE(b,i); return len > 0 ? $cptable.utils.decode(current_ansi, b.slice(i+4, i+4+len-1)) : \"\";};\n\t__cpstr = function(b/*:RawBytes|CFBlob*/,i/*:number*/) { var len = __readUInt32LE(b,i); return len > 0 ? $cptable.utils.decode(current_codepage, b.slice(i+4, i+4+len-1)) : \"\";};\n\t__lpwstr = function(b/*:RawBytes|CFBlob*/,i/*:number*/) { var len = 2*__readUInt32LE(b,i); return len > 0 ? $cptable.utils.decode(1200, b.slice(i+4,i+4+len-1)) : \"\";};\n\t__lpp4 = function(b/*:RawBytes|CFBlob*/,i/*:number*/) { var len = __readUInt32LE(b,i); return len > 0 ? $cptable.utils.decode(1200, b.slice(i+4,i+4+len)) : \"\";};\n\t__8lpp4 = function(b/*:RawBytes|CFBlob*/,i/*:number*/) { var len = __readUInt32LE(b,i); return len > 0 ? $cptable.utils.decode(65001, b.slice(i+4,i+4+len)) : \"\";};\n}\nif(typeof $cptable !== 'undefined') cpdoit();\n\nvar __readUInt8 = function(b/*:RawBytes|CFBlob*/, idx/*:number*/)/*:number*/ { return b[idx]; };\nvar __readUInt16LE = function(b/*:RawBytes|CFBlob*/, idx/*:number*/)/*:number*/ { return (b[idx+1]*(1<<8))+b[idx]; };\nvar __readInt16LE = function(b/*:RawBytes|CFBlob*/, idx/*:number*/)/*:number*/ { var u = (b[idx+1]*(1<<8))+b[idx]; return (u < 0x8000) ? u : ((0xffff - u + 1) * -1); };\nvar __readUInt32LE = function(b/*:RawBytes|CFBlob*/, idx/*:number*/)/*:number*/ { return b[idx+3]*(1<<24)+(b[idx+2]<<16)+(b[idx+1]<<8)+b[idx]; };\nvar __readInt32LE = function(b/*:RawBytes|CFBlob*/, idx/*:number*/)/*:number*/ { return (b[idx+3]<<24)|(b[idx+2]<<16)|(b[idx+1]<<8)|b[idx]; };\nvar __readInt32BE = function(b/*:RawBytes|CFBlob*/, idx/*:number*/)/*:number*/ { return (b[idx]<<24)|(b[idx+1]<<16)|(b[idx+2]<<8)|b[idx+3]; };\n\nfunction ReadShift(size/*:number*/, t/*:?string*/)/*:number|string*/ {\n\tvar o=\"\", oI/*:: :number = 0*/, oR, oo=[], w, vv, i, loc;\n\tswitch(t) {\n\t\tcase 'dbcs':\n\t\t\tloc = this.l;\n\t\t\tif(has_buf && Buffer.isBuffer(this)) o = this.slice(this.l, this.l+2*size).toString(\"utf16le\");\n\t\t\telse for(i = 0; i < size; ++i) { o+=String.fromCharCode(__readUInt16LE(this, loc)); loc+=2; }\n\t\t\tsize *= 2;\n\t\t\tbreak;\n\n\t\tcase 'utf8': o = __utf8(this, this.l, this.l + size); break;\n\t\tcase 'utf16le': size *= 2; o = __utf16le(this, this.l, this.l + size); break;\n\n\t\tcase 'wstr':\n\t\t\tif(typeof $cptable !== 'undefined') o = $cptable.utils.decode(current_codepage, this.slice(this.l, this.l+2*size));\n\t\t\telse return ReadShift.call(this, size, 'dbcs');\n\t\t\tsize = 2 * size; break;\n\n\t\t/* [MS-OLEDS] 2.1.4 LengthPrefixedAnsiString */\n\t\tcase 'lpstr-ansi': o = __lpstr(this, this.l); size = 4 + __readUInt32LE(this, this.l); break;\n\t\tcase 'lpstr-cp': o = __cpstr(this, this.l); size = 4 + __readUInt32LE(this, this.l); break;\n\t\t/* [MS-OLEDS] 2.1.5 LengthPrefixedUnicodeString */\n\t\tcase 'lpwstr': o = __lpwstr(this, this.l); size = 4 + 2 * __readUInt32LE(this, this.l); break;\n\t\t/* [MS-OFFCRYPTO] 2.1.2 Length-Prefixed Padded Unicode String (UNICODE-LP-P4) */\n\t\tcase 'lpp4': size = 4 +  __readUInt32LE(this, this.l); o = __lpp4(this, this.l); if(size & 0x02) size += 2; break;\n\t\t/* [MS-OFFCRYPTO] 2.1.3 Length-Prefixed UTF-8 String (UTF-8-LP-P4) */\n\t\tcase '8lpp4': size = 4 +  __readUInt32LE(this, this.l); o = __8lpp4(this, this.l); if(size & 0x03) size += 4 - (size & 0x03); break;\n\n\t\tcase 'cstr': size = 0; o = \"\";\n\t\t\twhile((w=__readUInt8(this, this.l + size++))!==0) oo.push(_getchar(w));\n\t\t\to = oo.join(\"\"); break;\n\t\tcase '_wstr': size = 0; o = \"\";\n\t\t\twhile((w=__readUInt16LE(this,this.l +size))!==0){oo.push(_getchar(w));size+=2;}\n\t\t\tsize+=2; o = oo.join(\"\"); break;\n\n\t\t/* sbcs and dbcs support continue records in the SST way TODO codepages */\n\t\tcase 'dbcs-cont': o = \"\"; loc = this.l;\n\t\t\tfor(i = 0; i < size; ++i) {\n\t\t\t\tif(this.lens && this.lens.indexOf(loc) !== -1) {\n\t\t\t\t\tw = __readUInt8(this, loc);\n\t\t\t\t\tthis.l = loc + 1;\n\t\t\t\t\tvv = ReadShift.call(this, size-i, w ? 'dbcs-cont' : 'sbcs-cont');\n\t\t\t\t\treturn oo.join(\"\") + vv;\n\t\t\t\t}\n\t\t\t\too.push(_getchar(__readUInt16LE(this, loc)));\n\t\t\t\tloc+=2;\n\t\t\t} o = oo.join(\"\"); size *= 2; break;\n\n\t\tcase 'cpstr':\n\t\t\tif(typeof $cptable !== 'undefined') {\n\t\t\t\to = $cptable.utils.decode(current_codepage, this.slice(this.l, this.l + size));\n\t\t\t\tbreak;\n\t\t\t}\n\t\t/* falls through */\n\t\tcase 'sbcs-cont': o = \"\"; loc = this.l;\n\t\t\tfor(i = 0; i != size; ++i) {\n\t\t\t\tif(this.lens && this.lens.indexOf(loc) !== -1) {\n\t\t\t\t\tw = __readUInt8(this, loc);\n\t\t\t\t\tthis.l = loc + 1;\n\t\t\t\t\tvv = ReadShift.call(this, size-i, w ? 'dbcs-cont' : 'sbcs-cont');\n\t\t\t\t\treturn oo.join(\"\") + vv;\n\t\t\t\t}\n\t\t\t\too.push(_getchar(__readUInt8(this, loc)));\n\t\t\t\tloc+=1;\n\t\t\t} o = oo.join(\"\"); break;\n\n\t\tdefault:\n\tswitch(size) {\n\t\tcase 1: oI = __readUInt8(this, this.l); this.l++; return oI;\n\t\tcase 2: oI = (t === 'i' ? __readInt16LE : __readUInt16LE)(this, this.l); this.l += 2; return oI;\n\t\tcase 4: case -4:\n\t\t\tif(t === 'i' || ((this[this.l+3] & 0x80)===0)) { oI = ((size > 0) ? __readInt32LE : __readInt32BE)(this, this.l); this.l += 4; return oI; }\n\t\t\telse { oR = __readUInt32LE(this, this.l); this.l += 4; } return oR;\n\t\tcase 8: case -8:\n\t\t\tif(t === 'f') {\n\t\t\t\tif(size == 8) oR = __double(this, this.l);\n\t\t\t\telse oR = __double([this[this.l+7],this[this.l+6],this[this.l+5],this[this.l+4],this[this.l+3],this[this.l+2],this[this.l+1],this[this.l+0]], 0);\n\t\t\t\tthis.l += 8; return oR;\n\t\t\t} else size = 8;\n\t\t/* falls through */\n\t\tcase 16: o = __hexlify(this, this.l, size); break;\n\t}}\n\tthis.l+=size; return o;\n}\n\nvar __writeUInt32LE = function(b/*:RawBytes|CFBlob*/, val/*:number*/, idx/*:number*/)/*:void*/ { b[idx] = (val & 0xFF); b[idx+1] = ((val >>> 8) & 0xFF); b[idx+2] = ((val >>> 16) & 0xFF); b[idx+3] = ((val >>> 24) & 0xFF); };\nvar __writeInt32LE  = function(b/*:RawBytes|CFBlob*/, val/*:number*/, idx/*:number*/)/*:void*/ { b[idx] = (val & 0xFF); b[idx+1] = ((val >> 8) & 0xFF); b[idx+2] = ((val >> 16) & 0xFF); b[idx+3] = ((val >> 24) & 0xFF); };\nvar __writeUInt16LE = function(b/*:RawBytes|CFBlob*/, val/*:number*/, idx/*:number*/)/*:void*/ { b[idx] = (val & 0xFF); b[idx+1] = ((val >>> 8) & 0xFF); };\n\nfunction WriteShift(t/*:number*/, val/*:string|number*/, f/*:?string*/)/*:any*/ {\n\tvar size = 0, i = 0;\n\tif(f === 'dbcs') {\n\t\t/*:: if(typeof val !== 'string') throw new Error(\"unreachable\"); */\n\t\tfor(i = 0; i != val.length; ++i) __writeUInt16LE(this, val.charCodeAt(i), this.l + 2 * i);\n\t\tsize = 2 * val.length;\n\t} else if(f === 'sbcs') {\n\t\tif(typeof $cptable !== 'undefined' && current_ansi == 874) {\n\t\t\t/* TODO: use tables directly, don't encode */\n\t\t\t/*:: if(typeof val !== \"string\") throw new Error(\"unreachable\"); */\n\t\t\tfor(i = 0; i != val.length; ++i) {\n\t\t\t\tvar cppayload = $cptable.utils.encode(current_ansi, val.charAt(i));\n\t\t\t\tthis[this.l + i] = cppayload[0];\n\t\t\t}\n\t\t} else {\n\t\t\t/*:: if(typeof val !== 'string') throw new Error(\"unreachable\"); */\n\t\t\tval = val.replace(/[^\\x00-\\x7F]/g, \"_\");\n\t\t\t/*:: if(typeof val !== 'string') throw new Error(\"unreachable\"); */\n\t\t\tfor(i = 0; i != val.length; ++i) this[this.l + i] = (val.charCodeAt(i) & 0xFF);\n\t\t}\n\t\tsize = val.length;\n\t} else if(f === 'hex') {\n\t\tfor(; i < t; ++i) {\n\t\t\t/*:: if(typeof val !== \"string\") throw new Error(\"unreachable\"); */\n\t\t\tthis[this.l++] = (parseInt(val.slice(2*i, 2*i+2), 16)||0);\n\t\t} return this;\n\t} else if(f === 'utf16le') {\n\t\t\t/*:: if(typeof val !== \"string\") throw new Error(\"unreachable\"); */\n\t\t\tvar end/*:number*/ = Math.min(this.l + t, this.length);\n\t\t\tfor(i = 0; i < Math.min(val.length, t); ++i) {\n\t\t\t\tvar cc = val.charCodeAt(i);\n\t\t\t\tthis[this.l++] = (cc & 0xff);\n\t\t\t\tthis[this.l++] = (cc >> 8);\n\t\t\t}\n\t\t\twhile(this.l < end) this[this.l++] = 0;\n\t\t\treturn this;\n\t} else /*:: if(typeof val === 'number') */ switch(t) {\n\t\tcase  1: size = 1; this[this.l] = val&0xFF; break;\n\t\tcase  2: size = 2; this[this.l] = val&0xFF; val >>>= 8; this[this.l+1] = val&0xFF; break;\n\t\tcase  3: size = 3; this[this.l] = val&0xFF; val >>>= 8; this[this.l+1] = val&0xFF; val >>>= 8; this[this.l+2] = val&0xFF; break;\n\t\tcase  4: size = 4; __writeUInt32LE(this, val, this.l); break;\n\t\tcase  8: size = 8; if(f === 'f') { write_double_le(this, val, this.l); break; }\n\t\t/* falls through */\n\t\tcase 16: break;\n\t\tcase -4: size = 4; __writeInt32LE(this, val, this.l); break;\n\t}\n\tthis.l += size; return this;\n}\n\nfunction CheckField(hexstr/*:string*/, fld/*:string*/)/*:void*/ {\n\tvar m = __hexlify(this,this.l,hexstr.length>>1);\n\tif(m !== hexstr) throw new Error(fld + 'Expected ' + hexstr + ' saw ' + m);\n\tthis.l += hexstr.length>>1;\n}\n\nfunction prep_blob(blob, pos/*:number*/)/*:void*/ {\n\tblob.l = pos;\n\tblob.read_shift = /*::(*/ReadShift/*:: :any)*/;\n\tblob.chk = CheckField;\n\tblob.write_shift = WriteShift;\n}\n\nfunction parsenoop(blob, length/*:: :number, opts?:any */) { blob.l += length; }\n\nfunction new_buf(sz/*:number*/)/*:Block*/ {\n\tvar o = new_raw_buf(sz);\n\tprep_blob(o, 0);\n\treturn o;\n}\n\n/* [MS-XLSB] 2.1.4 Record */\nfunction recordhopper(data, cb/*:RecordHopperCB*/, opts/*:?any*/) {\n\tif(!data) return;\n\tvar tmpbyte, cntbyte, length;\n\tprep_blob(data, data.l || 0);\n\tvar L = data.length, RT = 0, tgt = 0;\n\twhile(data.l < L) {\n\t\tRT = data.read_shift(1);\n\t\tif(RT & 0x80) RT = (RT & 0x7F) + ((data.read_shift(1) & 0x7F)<<7);\n\t\tvar R = XLSBRecordEnum[RT] || XLSBRecordEnum[0xFFFF];\n\t\ttmpbyte = data.read_shift(1);\n\t\tlength = tmpbyte & 0x7F;\n\t\tfor(cntbyte = 1; cntbyte <4 && (tmpbyte & 0x80); ++cntbyte) length += ((tmpbyte = data.read_shift(1)) & 0x7F)<<(7*cntbyte);\n\t\ttgt = data.l + length;\n\t\tvar d = R.f && R.f(data, length, opts);\n\t\tdata.l = tgt;\n\t\tif(cb(d, R, RT)) return;\n\t}\n}\n\n/* control buffer usage for fixed-length buffers */\nfunction buf_array()/*:BufArray*/ {\n\tvar bufs/*:Array<Block>*/ = [], blksz = has_buf ? 256 : 2048;\n\tvar newblk = function ba_newblk(sz/*:number*/)/*:Block*/ {\n\t\tvar o/*:Block*/ = (new_buf(sz)/*:any*/);\n\t\tprep_blob(o, 0);\n\t\treturn o;\n\t};\n\n\tvar curbuf/*:Block*/ = newblk(blksz);\n\n\tvar endbuf = function ba_endbuf() {\n\t\tif(!curbuf) return;\n\t\tif(curbuf.length > curbuf.l) { curbuf = curbuf.slice(0, curbuf.l); curbuf.l = curbuf.length; }\n\t\tif(curbuf.length > 0) bufs.push(curbuf);\n\t\tcurbuf = null;\n\t};\n\n\tvar next = function ba_next(sz/*:number*/)/*:Block*/ {\n\t\tif(curbuf && (sz < (curbuf.length - curbuf.l))) return curbuf;\n\t\tendbuf();\n\t\treturn (curbuf = newblk(Math.max(sz+1, blksz)));\n\t};\n\n\tvar end = function ba_end() {\n\t\tendbuf();\n\t\treturn bconcat(bufs);\n\t};\n\n\tvar push = function ba_push(buf) { endbuf(); curbuf = buf; if(curbuf.l == null) curbuf.l = curbuf.length; next(blksz); };\n\n\treturn ({ next:next, push:push, end:end, _bufs:bufs }/*:any*/);\n}\n\nfunction write_record(ba/*:BufArray*/, type/*:number*/, payload, length/*:?number*/) {\n\tvar t/*:number*/ = +type, l;\n\tif(isNaN(t)) return; // TODO: throw something here?\n\tif(!length) length = XLSBRecordEnum[t].p || (payload||[]).length || 0;\n\tl = 1 + (t >= 0x80 ? 1 : 0) + 1/* + length*/;\n\tif(length >= 0x80) ++l; if(length >= 0x4000) ++l; if(length >= 0x200000) ++l;\n\tvar o = ba.next(l);\n\tif(t <= 0x7F) o.write_shift(1, t);\n\telse {\n\t\to.write_shift(1, (t & 0x7F) + 0x80);\n\t\to.write_shift(1, (t >> 7));\n\t}\n\tfor(var i = 0; i != 4; ++i) {\n\t\tif(length >= 0x80) { o.write_shift(1, (length & 0x7F)+0x80); length >>= 7; }\n\t\telse { o.write_shift(1, length); break; }\n\t}\n\tif(/*:: length != null &&*/length > 0 && is_buf(payload)) ba.push(payload);\n}\n/* XLS ranges enforced */\nfunction shift_cell_xls(cell/*:CellAddress*/, tgt/*:any*/, opts/*:?any*/)/*:CellAddress*/ {\n\tvar out = dup(cell);\n\tif(tgt.s) {\n\t\tif(out.cRel) out.c += tgt.s.c;\n\t\tif(out.rRel) out.r += tgt.s.r;\n\t} else {\n\t\tif(out.cRel) out.c += tgt.c;\n\t\tif(out.rRel) out.r += tgt.r;\n\t}\n\tif(!opts || opts.biff < 12) {\n\t\twhile(out.c >= 0x100) out.c -= 0x100;\n\t\twhile(out.r >= 0x10000) out.r -= 0x10000;\n\t}\n\treturn out;\n}\n\nfunction shift_range_xls(cell, range, opts) {\n\tvar out = dup(cell);\n\tout.s = shift_cell_xls(out.s, range.s, opts);\n\tout.e = shift_cell_xls(out.e, range.s, opts);\n\treturn out;\n}\n\nfunction encode_cell_xls(c/*:CellAddress*/, biff/*:number*/)/*:string*/ {\n\tif(c.cRel && c.c < 0) { c = dup(c); while(c.c < 0) c.c += (biff > 8) ? 0x4000 : 0x100; }\n\tif(c.rRel && c.r < 0) { c = dup(c); while(c.r < 0) c.r += (biff > 8) ? 0x100000 : ((biff > 5) ? 0x10000 : 0x4000); }\n\tvar s = encode_cell(c);\n\tif(!c.cRel && c.cRel != null) s = fix_col(s);\n\tif(!c.rRel && c.rRel != null) s = fix_row(s);\n\treturn s;\n}\n\nfunction encode_range_xls(r, opts)/*:string*/ {\n\tif(r.s.r == 0 && !r.s.rRel) {\n\t\tif(r.e.r == (opts.biff >= 12 ? 0xFFFFF : (opts.biff >= 8 ? 0x10000 : 0x4000)) && !r.e.rRel) {\n\t\t\treturn (r.s.cRel ? \"\" : \"$\") + encode_col(r.s.c) + \":\" + (r.e.cRel ? \"\" : \"$\") + encode_col(r.e.c);\n\t\t}\n\t}\n\tif(r.s.c == 0 && !r.s.cRel) {\n\t\tif(r.e.c == (opts.biff >= 12 ? 0x3FFF : 0xFF) && !r.e.cRel) {\n\t\t\treturn (r.s.rRel ? \"\" : \"$\") + encode_row(r.s.r) + \":\" + (r.e.rRel ? \"\" : \"$\") + encode_row(r.e.r);\n\t\t}\n\t}\n\treturn encode_cell_xls(r.s, opts.biff) + \":\" + encode_cell_xls(r.e, opts.biff);\n}\nfunction decode_row(rowstr/*:string*/)/*:number*/ { return parseInt(unfix_row(rowstr),10) - 1; }\nfunction encode_row(row/*:number*/)/*:string*/ { return \"\" + (row + 1); }\nfunction fix_row(cstr/*:string*/)/*:string*/ { return cstr.replace(/([A-Z]|^)(\\d+)$/,\"$1$$$2\"); }\nfunction unfix_row(cstr/*:string*/)/*:string*/ { return cstr.replace(/\\$(\\d+)$/,\"$1\"); }\n\nfunction decode_col(colstr/*:string*/)/*:number*/ { var c = unfix_col(colstr), d = 0, i = 0; for(; i !== c.length; ++i) d = 26*d + c.charCodeAt(i) - 64; return d - 1; }\nfunction encode_col(col/*:number*/)/*:string*/ { if(col < 0) throw new Error(\"invalid column \" + col); var s=\"\"; for(++col; col; col=Math.floor((col-1)/26)) s = String.fromCharCode(((col-1)%26) + 65) + s; return s; }\nfunction fix_col(cstr/*:string*/)/*:string*/ { return cstr.replace(/^([A-Z])/,\"$$$1\"); }\nfunction unfix_col(cstr/*:string*/)/*:string*/ { return cstr.replace(/^\\$([A-Z])/,\"$1\"); }\n\nfunction split_cell(cstr/*:string*/)/*:Array<string>*/ { return cstr.replace(/(\\$?[A-Z]*)(\\$?\\d*)/,\"$1,$2\").split(\",\"); }\n//function decode_cell(cstr/*:string*/)/*:CellAddress*/ { var splt = split_cell(cstr); return { c:decode_col(splt[0]), r:decode_row(splt[1]) }; }\nfunction decode_cell(cstr/*:string*/)/*:CellAddress*/ {\n\tvar R = 0, C = 0;\n\tfor(var i = 0; i < cstr.length; ++i) {\n\t\tvar cc = cstr.charCodeAt(i);\n\t\tif(cc >= 48 && cc <= 57) R = 10 * R + (cc - 48);\n\t\telse if(cc >= 65 && cc <= 90) C = 26 * C + (cc - 64);\n\t}\n\treturn { c: C - 1, r:R - 1 };\n}\n//function encode_cell(cell/*:CellAddress*/)/*:string*/ { return encode_col(cell.c) + encode_row(cell.r); }\nfunction encode_cell(cell/*:CellAddress*/)/*:string*/ {\n\tvar col = cell.c + 1;\n\tvar s=\"\";\n\tfor(; col; col=((col-1)/26)|0) s = String.fromCharCode(((col-1)%26) + 65) + s;\n\treturn s + (cell.r + 1);\n}\nfunction decode_range(range/*:string*/)/*:Range*/ {\n\tvar idx = range.indexOf(\":\");\n\tif(idx == -1) return { s: decode_cell(range), e: decode_cell(range) };\n\treturn { s: decode_cell(range.slice(0, idx)), e: decode_cell(range.slice(idx + 1)) };\n}\n/*# if only one arg, it is assumed to be a Range.  If 2 args, both are cell addresses */\nfunction encode_range(cs/*:CellAddrSpec|Range*/,ce/*:?CellAddrSpec*/)/*:string*/ {\n\tif(typeof ce === 'undefined' || typeof ce === 'number') {\n/*:: if(!(cs instanceof Range)) throw \"unreachable\"; */\n\t\treturn encode_range(cs.s, cs.e);\n\t}\n/*:: if((cs instanceof Range)) throw \"unreachable\"; */\n\tif(typeof cs !== 'string') cs = encode_cell((cs/*:any*/));\n\tif(typeof ce !== 'string') ce = encode_cell((ce/*:any*/));\n/*:: if(typeof cs !== 'string') throw \"unreachable\"; */\n/*:: if(typeof ce !== 'string') throw \"unreachable\"; */\n\treturn cs == ce ? cs : cs + \":\" + ce;\n}\n\nfunction safe_decode_range(range/*:string*/)/*:Range*/ {\n\tvar o = {s:{c:0,r:0},e:{c:0,r:0}};\n\tvar idx = 0, i = 0, cc = 0;\n\tvar len = range.length;\n\tfor(idx = 0; i < len; ++i) {\n\t\tif((cc=range.charCodeAt(i)-64) < 1 || cc > 26) break;\n\t\tidx = 26*idx + cc;\n\t}\n\to.s.c = --idx;\n\n\tfor(idx = 0; i < len; ++i) {\n\t\tif((cc=range.charCodeAt(i)-48) < 0 || cc > 9) break;\n\t\tidx = 10*idx + cc;\n\t}\n\to.s.r = --idx;\n\n\tif(i === len || cc != 10) { o.e.c=o.s.c; o.e.r=o.s.r; return o; }\n\t++i;\n\n\tfor(idx = 0; i != len; ++i) {\n\t\tif((cc=range.charCodeAt(i)-64) < 1 || cc > 26) break;\n\t\tidx = 26*idx + cc;\n\t}\n\to.e.c = --idx;\n\n\tfor(idx = 0; i != len; ++i) {\n\t\tif((cc=range.charCodeAt(i)-48) < 0 || cc > 9) break;\n\t\tidx = 10*idx + cc;\n\t}\n\to.e.r = --idx;\n\treturn o;\n}\n\nfunction safe_format_cell(cell/*:Cell*/, v/*:any*/) {\n\tvar q = (cell.t == 'd' && v instanceof Date);\n\tif(cell.z != null) try { return (cell.w = SSF_format(cell.z, q ? datenum(v) : v)); } catch(e) { }\n\ttry { return (cell.w = SSF_format((cell.XF||{}).numFmtId||(q ? 14 : 0),  q ? datenum(v) : v)); } catch(e) { return ''+v; }\n}\n\nfunction format_cell(cell/*:Cell*/, v/*:any*/, o/*:any*/) {\n\tif(cell == null || cell.t == null || cell.t == 'z') return \"\";\n\tif(cell.w !== undefined) return cell.w;\n\tif(cell.t == 'd' && !cell.z && o && o.dateNF) cell.z = o.dateNF;\n\tif(cell.t == \"e\") return BErr[cell.v] || cell.v;\n\tif(v == undefined) return safe_format_cell(cell, cell.v);\n\treturn safe_format_cell(cell, v);\n}\n\nfunction sheet_to_workbook(sheet/*:Worksheet*/, opts)/*:Workbook*/ {\n\tvar n = opts && opts.sheet ? opts.sheet : \"Sheet1\";\n\tvar sheets = {}; sheets[n] = sheet;\n\treturn { SheetNames: [n], Sheets: sheets };\n}\n\nfunction sheet_add_aoa(_ws/*:?Worksheet*/, data/*:AOA*/, opts/*:?any*/)/*:Worksheet*/ {\n\tvar o = opts || {};\n\tvar dense = _ws ? Array.isArray(_ws) : o.dense;\n\tif(DENSE != null && dense == null) dense = DENSE;\n\tvar ws/*:Worksheet*/ = _ws || (dense ? ([]/*:any*/) : ({}/*:any*/));\n\tvar _R = 0, _C = 0;\n\tif(ws && o.origin != null) {\n\t\tif(typeof o.origin == 'number') _R = o.origin;\n\t\telse {\n\t\t\tvar _origin/*:CellAddress*/ = typeof o.origin == \"string\" ? decode_cell(o.origin) : o.origin;\n\t\t\t_R = _origin.r; _C = _origin.c;\n\t\t}\n\t\tif(!ws[\"!ref\"]) ws[\"!ref\"] = \"A1:A1\";\n\t}\n\tvar range/*:Range*/ = ({s: {c:10000000, r:10000000}, e: {c:0, r:0}}/*:any*/);\n\tif(ws['!ref']) {\n\t\tvar _range = safe_decode_range(ws['!ref']);\n\t\trange.s.c = _range.s.c;\n\t\trange.s.r = _range.s.r;\n\t\trange.e.c = Math.max(range.e.c, _range.e.c);\n\t\trange.e.r = Math.max(range.e.r, _range.e.r);\n\t\tif(_R == -1) range.e.r = _R = _range.e.r + 1;\n\t}\n\tfor(var R = 0; R != data.length; ++R) {\n\t\tif(!data[R]) continue;\n\t\tif(!Array.isArray(data[R])) throw new Error(\"aoa_to_sheet expects an array of arrays\");\n\t\tfor(var C = 0; C != data[R].length; ++C) {\n\t\t\tif(typeof data[R][C] === 'undefined') continue;\n\t\t\tvar cell/*:Cell*/ = ({v: data[R][C] }/*:any*/);\n\t\t\tvar __R = _R + R, __C = _C + C;\n\t\t\tif(range.s.r > __R) range.s.r = __R;\n\t\t\tif(range.s.c > __C) range.s.c = __C;\n\t\t\tif(range.e.r < __R) range.e.r = __R;\n\t\t\tif(range.e.c < __C) range.e.c = __C;\n\t\t\tif(data[R][C] && typeof data[R][C] === 'object' && !Array.isArray(data[R][C]) && !(data[R][C] instanceof Date)) cell = data[R][C];\n\t\t\telse {\n\t\t\t\tif(Array.isArray(cell.v)) { cell.f = data[R][C][1]; cell.v = cell.v[0]; }\n\t\t\t\tif(cell.v === null) {\n\t\t\t\t\tif(cell.f) cell.t = 'n';\n\t\t\t\t\telse if(o.nullError) { cell.t = 'e'; cell.v = 0; }\n\t\t\t\t\telse if(!o.sheetStubs) continue;\n\t\t\t\t\telse cell.t = 'z';\n\t\t\t\t}\n\t\t\t\telse if(typeof cell.v === 'number') cell.t = 'n';\n\t\t\t\telse if(typeof cell.v === 'boolean') cell.t = 'b';\n\t\t\t\telse if(cell.v instanceof Date) {\n\t\t\t\t\tcell.z = o.dateNF || table_fmt[14];\n\t\t\t\t\tif(o.cellDates) { cell.t = 'd'; cell.w = SSF_format(cell.z, datenum(cell.v)); }\n\t\t\t\t\telse { cell.t = 'n'; cell.v = datenum(cell.v); cell.w = SSF_format(cell.z, cell.v); }\n\t\t\t\t}\n\t\t\t\telse cell.t = 's';\n\t\t\t}\n\t\t\tif(dense) {\n\t\t\t\tif(!ws[__R]) ws[__R] = [];\n\t\t\t\tif(ws[__R][__C] && ws[__R][__C].z) cell.z = ws[__R][__C].z;\n\t\t\t\tws[__R][__C] = cell;\n\t\t\t} else {\n\t\t\t\tvar cell_ref = encode_cell(({c:__C,r:__R}/*:any*/));\n\t\t\t\tif(ws[cell_ref] && ws[cell_ref].z) cell.z = ws[cell_ref].z;\n\t\t\t\tws[cell_ref] = cell;\n\t\t\t}\n\t\t}\n\t}\n\tif(range.s.c < 10000000) ws['!ref'] = encode_range(range);\n\treturn ws;\n}\nfunction aoa_to_sheet(data/*:AOA*/, opts/*:?any*/)/*:Worksheet*/ { return sheet_add_aoa(null, data, opts); }\n\nfunction parse_Int32LE(data) {\n\treturn data.read_shift(4, 'i');\n}\nfunction write_UInt32LE(x/*:number*/, o) {\n\tif (!o) o = new_buf(4);\n\to.write_shift(4, x);\n\treturn o;\n}\n\n/* [MS-XLSB] 2.5.168 */\nfunction parse_XLWideString(data/*::, length*/)/*:string*/ {\n\tvar cchCharacters = data.read_shift(4);\n\treturn cchCharacters === 0 ? \"\" : data.read_shift(cchCharacters, 'dbcs');\n}\nfunction write_XLWideString(data/*:string*/, o) {\n\tvar _null = false; if (o == null) { _null = true; o = new_buf(4 + 2 * data.length); }\n\to.write_shift(4, data.length);\n\tif (data.length > 0) o.write_shift(0, data, 'dbcs');\n\treturn _null ? o.slice(0, o.l) : o;\n}\n\n/* [MS-XLSB] 2.5.91 */\n//function parse_LPWideString(data/*::, length*/)/*:string*/ {\n//\tvar cchCharacters = data.read_shift(2);\n//\treturn cchCharacters === 0 ? \"\" : data.read_shift(cchCharacters, \"utf16le\");\n//}\n\n/* [MS-XLSB] 2.5.143 */\nfunction parse_StrRun(data) {\n\treturn { ich: data.read_shift(2), ifnt: data.read_shift(2) };\n}\nfunction write_StrRun(run, o) {\n\tif (!o) o = new_buf(4);\n\to.write_shift(2, run.ich || 0);\n\to.write_shift(2, run.ifnt || 0);\n\treturn o;\n}\n\n/* [MS-XLSB] 2.5.121 */\nfunction parse_RichStr(data, length/*:number*/)/*:XLString*/ {\n\tvar start = data.l;\n\tvar flags = data.read_shift(1);\n\tvar str = parse_XLWideString(data);\n\tvar rgsStrRun = [];\n\tvar z = ({ t: str, h: str }/*:any*/);\n\tif ((flags & 1) !== 0) { /* fRichStr */\n\t\t/* TODO: formatted string */\n\t\tvar dwSizeStrRun = data.read_shift(4);\n\t\tfor (var i = 0; i != dwSizeStrRun; ++i) rgsStrRun.push(parse_StrRun(data));\n\t\tz.r = rgsStrRun;\n\t}\n\telse z.r = [{ ich: 0, ifnt: 0 }];\n\t//if((flags & 2) !== 0) { /* fExtStr */\n\t//\t/* TODO: phonetic string */\n\t//}\n\tdata.l = start + length;\n\treturn z;\n}\nfunction write_RichStr(str/*:XLString*/, o/*:?Block*/)/*:Block*/ {\n\t/* TODO: formatted string */\n\tvar _null = false; if (o == null) { _null = true; o = new_buf(15 + 4 * str.t.length); }\n\to.write_shift(1, 0);\n\twrite_XLWideString(str.t, o);\n\treturn _null ? o.slice(0, o.l) : o;\n}\n/* [MS-XLSB] 2.4.328 BrtCommentText (RichStr w/1 run) */\nvar parse_BrtCommentText = parse_RichStr;\nfunction write_BrtCommentText(str/*:XLString*/, o/*:?Block*/)/*:Block*/ {\n\t/* TODO: formatted string */\n\tvar _null = false; if (o == null) { _null = true; o = new_buf(23 + 4 * str.t.length); }\n\to.write_shift(1, 1);\n\twrite_XLWideString(str.t, o);\n\to.write_shift(4, 1);\n\twrite_StrRun({ ich: 0, ifnt: 0 }, o);\n\treturn _null ? o.slice(0, o.l) : o;\n}\n\n/* [MS-XLSB] 2.5.9 */\nfunction parse_XLSBCell(data)/*:any*/ {\n\tvar col = data.read_shift(4);\n\tvar iStyleRef = data.read_shift(2);\n\tiStyleRef += data.read_shift(1) << 16;\n\tdata.l++; //var fPhShow = data.read_shift(1);\n\treturn { c: col, iStyleRef: iStyleRef };\n}\nfunction write_XLSBCell(cell/*:any*/, o/*:?Block*/) {\n\tif (o == null) o = new_buf(8);\n\to.write_shift(-4, cell.c);\n\to.write_shift(3, cell.iStyleRef || cell.s);\n\to.write_shift(1, 0); /* fPhShow */\n\treturn o;\n}\n\n/* Short XLSB Cell does not include column */\nfunction parse_XLSBShortCell(data)/*:any*/ {\n\tvar iStyleRef = data.read_shift(2);\n\tiStyleRef += data.read_shift(1) <<16;\n\tdata.l++; //var fPhShow = data.read_shift(1);\n\treturn { c:-1, iStyleRef: iStyleRef };\n}\nfunction write_XLSBShortCell(cell/*:any*/, o/*:?Block*/) {\n\tif(o == null) o = new_buf(4);\n\to.write_shift(3, cell.iStyleRef || cell.s);\n\to.write_shift(1, 0); /* fPhShow */\n\treturn o;\n}\n\n/* [MS-XLSB] 2.5.21 */\nvar parse_XLSBCodeName = parse_XLWideString;\nvar write_XLSBCodeName = write_XLWideString;\n\n/* [MS-XLSB] 2.5.166 */\nfunction parse_XLNullableWideString(data/*::, length*/)/*:string*/ {\n\tvar cchCharacters = data.read_shift(4);\n\treturn cchCharacters === 0 || cchCharacters === 0xFFFFFFFF ? \"\" : data.read_shift(cchCharacters, 'dbcs');\n}\nfunction write_XLNullableWideString(data/*:string*/, o) {\n\tvar _null = false; if (o == null) { _null = true; o = new_buf(127); }\n\to.write_shift(4, data.length > 0 ? data.length : 0xFFFFFFFF);\n\tif (data.length > 0) o.write_shift(0, data, 'dbcs');\n\treturn _null ? o.slice(0, o.l) : o;\n}\n\n/* [MS-XLSB] 2.5.165 */\nvar parse_XLNameWideString = parse_XLWideString;\n//var write_XLNameWideString = write_XLWideString;\n\n/* [MS-XLSB] 2.5.114 */\nvar parse_RelID = parse_XLNullableWideString;\nvar write_RelID = write_XLNullableWideString;\n\n\n/* [MS-XLS] 2.5.217 ; [MS-XLSB] 2.5.122 */\nfunction parse_RkNumber(data)/*:number*/ {\n\tvar b = data.slice(data.l, data.l + 4);\n\tvar fX100 = (b[0] & 1), fInt = (b[0] & 2);\n\tdata.l += 4;\n\tvar RK = fInt === 0 ? __double([0, 0, 0, 0, (b[0] & 0xFC), b[1], b[2], b[3]], 0) : __readInt32LE(b, 0) >> 2;\n\treturn fX100 ? (RK / 100) : RK;\n}\nfunction write_RkNumber(data/*:number*/, o) {\n\tif (o == null) o = new_buf(4);\n\tvar fX100 = 0, fInt = 0, d100 = data * 100;\n\tif ((data == (data | 0)) && (data >= -(1 << 29)) && (data < (1 << 29))) { fInt = 1; }\n\telse if ((d100 == (d100 | 0)) && (d100 >= -(1 << 29)) && (d100 < (1 << 29))) { fInt = 1; fX100 = 1; }\n\tif (fInt) o.write_shift(-4, ((fX100 ? d100 : data) << 2) + (fX100 + 2));\n\telse throw new Error(\"unsupported RkNumber \" + data); // TODO\n}\n\n\n/* [MS-XLSB] 2.5.117 RfX */\nfunction parse_RfX(data /*::, length*/)/*:Range*/ {\n\tvar cell/*:Range*/ = ({ s: {}, e: {} }/*:any*/);\n\tcell.s.r = data.read_shift(4);\n\tcell.e.r = data.read_shift(4);\n\tcell.s.c = data.read_shift(4);\n\tcell.e.c = data.read_shift(4);\n\treturn cell;\n}\nfunction write_RfX(r/*:Range*/, o) {\n\tif (!o) o = new_buf(16);\n\to.write_shift(4, r.s.r);\n\to.write_shift(4, r.e.r);\n\to.write_shift(4, r.s.c);\n\to.write_shift(4, r.e.c);\n\treturn o;\n}\n\n/* [MS-XLSB] 2.5.153 UncheckedRfX */\nvar parse_UncheckedRfX = parse_RfX;\nvar write_UncheckedRfX = write_RfX;\n\n/* [MS-XLSB] 2.5.155 UncheckedSqRfX */\n//function parse_UncheckedSqRfX(data) {\n//\tvar cnt = data.read_shift(4);\n//\tvar out = [];\n//\tfor(var i = 0; i < cnt; ++i) {\n//\t\tvar rng = parse_UncheckedRfX(data);\n//\t\tout.push(encode_range(rng));\n//\t}\n//\treturn out.join(\",\");\n//}\n//function write_UncheckedSqRfX(sqrfx/*:string*/) {\n//\tvar parts = sqrfx.split(/\\s*,\\s*/);\n//\tvar o = new_buf(4); o.write_shift(4, parts.length);\n//\tvar out = [o];\n//\tparts.forEach(function(rng) {\n//\t\tout.push(write_UncheckedRfX(safe_decode_range(rng)));\n//\t});\n//\treturn bconcat(out);\n//}\n\n/* [MS-XLS] 2.5.342 ; [MS-XLSB] 2.5.171 */\n/* TODO: error checking, NaN and Infinity values are not valid Xnum */\nfunction parse_Xnum(data/*::, length*/) {\n\tif(data.length - data.l < 8) throw \"XLS Xnum Buffer underflow\";\n\treturn data.read_shift(8, 'f');\n}\nfunction write_Xnum(data, o) { return (o || new_buf(8)).write_shift(8, data, 'f'); }\n\n/* [MS-XLSB] 2.4.324 BrtColor */\nfunction parse_BrtColor(data/*::, length*/) {\n\tvar out = {};\n\tvar d = data.read_shift(1);\n\n\t//var fValidRGB = d & 1;\n\tvar xColorType = d >>> 1;\n\n\tvar index = data.read_shift(1);\n\tvar nTS = data.read_shift(2, 'i');\n\tvar bR = data.read_shift(1);\n\tvar bG = data.read_shift(1);\n\tvar bB = data.read_shift(1);\n\tdata.l++; //var bAlpha = data.read_shift(1);\n\n\tswitch (xColorType) {\n\t\tcase 0: out.auto = 1; break;\n\t\tcase 1:\n\t\t\tout.index = index;\n\t\t\tvar icv = XLSIcv[index];\n\t\t\t/* automatic pseudo index 81 */\n\t\t\tif (icv) out.rgb = rgb2Hex(icv);\n\t\t\tbreak;\n\t\tcase 2:\n\t\t\t/* if(!fValidRGB) throw new Error(\"invalid\"); */\n\t\t\tout.rgb = rgb2Hex([bR, bG, bB]);\n\t\t\tbreak;\n\t\tcase 3: out.theme = index; break;\n\t}\n\tif (nTS != 0) out.tint = nTS > 0 ? nTS / 32767 : nTS / 32768;\n\n\treturn out;\n}\nfunction write_BrtColor(color, o) {\n\tif (!o) o = new_buf(8);\n\tif (!color || color.auto) { o.write_shift(4, 0); o.write_shift(4, 0); return o; }\n\tif (color.index != null) {\n\t\to.write_shift(1, 0x02);\n\t\to.write_shift(1, color.index);\n\t} else if (color.theme != null) {\n\t\to.write_shift(1, 0x06);\n\t\to.write_shift(1, color.theme);\n\t} else {\n\t\to.write_shift(1, 0x05);\n\t\to.write_shift(1, 0);\n\t}\n\tvar nTS = color.tint || 0;\n\tif (nTS > 0) nTS *= 32767;\n\telse if (nTS < 0) nTS *= 32768;\n\to.write_shift(2, nTS);\n\tif (!color.rgb || color.theme != null) {\n\t\to.write_shift(2, 0);\n\t\to.write_shift(1, 0);\n\t\to.write_shift(1, 0);\n\t} else {\n\t\tvar rgb = (color.rgb || 'FFFFFF');\n\t\tif (typeof rgb == 'number') rgb = (\"000000\" + rgb.toString(16)).slice(-6);\n\t\to.write_shift(1, parseInt(rgb.slice(0, 2), 16));\n\t\to.write_shift(1, parseInt(rgb.slice(2, 4), 16));\n\t\to.write_shift(1, parseInt(rgb.slice(4, 6), 16));\n\t\to.write_shift(1, 0xFF);\n\t}\n\treturn o;\n}\n\n/* [MS-XLSB] 2.5.52 */\nfunction parse_FontFlags(data/*::, length, opts*/) {\n\tvar d = data.read_shift(1);\n\tdata.l++;\n\tvar out = {\n\t\tfBold: d & 0x01,\n\t\tfItalic: d & 0x02,\n\t\tfUnderline: d & 0x04,\n\t\tfStrikeout: d & 0x08,\n\t\tfOutline: d & 0x10,\n\t\tfShadow: d & 0x20,\n\t\tfCondense: d & 0x40,\n\t\tfExtend: d & 0x80\n\t};\n\treturn out;\n}\nfunction write_FontFlags(font, o) {\n\tif (!o) o = new_buf(2);\n\tvar grbit =\n\t\t(font.italic ? 0x02 : 0) |\n\t\t(font.strike ? 0x08 : 0) |\n\t\t(font.outline ? 0x10 : 0) |\n\t\t(font.shadow ? 0x20 : 0) |\n\t\t(font.condense ? 0x40 : 0) |\n\t\t(font.extend ? 0x80 : 0);\n\to.write_shift(1, grbit);\n\to.write_shift(1, 0);\n\treturn o;\n}\n\n/* [MS-OLEDS] 2.3.1 and 2.3.2 */\nfunction parse_ClipboardFormatOrString(o, w/*:number*/)/*:string*/ {\n\t// $FlowIgnore\n\tvar ClipFmt = { 2: \"BITMAP\", 3: \"METAFILEPICT\", 8: \"DIB\", 14: \"ENHMETAFILE\" };\n\tvar m/*:number*/ = o.read_shift(4);\n\tswitch (m) {\n\t\tcase 0x00000000: return \"\";\n\t\tcase 0xffffffff: case 0xfffffffe: return ClipFmt[o.read_shift(4)] || \"\";\n\t}\n\tif (m > 0x190) throw new Error(\"Unsupported Clipboard: \" + m.toString(16));\n\to.l -= 4;\n\treturn o.read_shift(0, w == 1 ? \"lpstr\" : \"lpwstr\");\n}\nfunction parse_ClipboardFormatOrAnsiString(o) { return parse_ClipboardFormatOrString(o, 1); }\nfunction parse_ClipboardFormatOrUnicodeString(o) { return parse_ClipboardFormatOrString(o, 2); }\n\n/* [MS-OLEPS] 2.2 PropertyType */\n// Note: some tree shakers cannot handle VT_VECTOR | $CONST, hence extra vars\n//var VT_EMPTY    = 0x0000;\n//var VT_NULL     = 0x0001;\nvar VT_I2       = 0x0002;\nvar VT_I4       = 0x0003;\n//var VT_R4       = 0x0004;\n//var VT_R8       = 0x0005;\n//var VT_CY       = 0x0006;\n//var VT_DATE     = 0x0007;\n//var VT_BSTR     = 0x0008;\n//var VT_ERROR    = 0x000A;\nvar VT_BOOL     = 0x000B;\nvar VT_VARIANT  = 0x000C;\n//var VT_DECIMAL  = 0x000E;\n//var VT_I1       = 0x0010;\n//var VT_UI1      = 0x0011;\n//var VT_UI2      = 0x0012;\nvar VT_UI4      = 0x0013;\n//var VT_I8       = 0x0014;\n//var VT_UI8      = 0x0015;\n//var VT_INT      = 0x0016;\n//var VT_UINT     = 0x0017;\nvar VT_LPSTR    = 0x001E;\n//var VT_LPWSTR   = 0x001F;\nvar VT_FILETIME = 0x0040;\nvar VT_BLOB     = 0x0041;\n//var VT_STREAM   = 0x0042;\n//var VT_STORAGE  = 0x0043;\n//var VT_STREAMED_Object  = 0x0044;\n//var VT_STORED_Object    = 0x0045;\n//var VT_BLOB_Object      = 0x0046;\nvar VT_CF       = 0x0047;\n//var VT_CLSID    = 0x0048;\n//var VT_VERSIONED_STREAM = 0x0049;\nvar VT_VECTOR   = 0x1000;\nvar VT_VECTOR_VARIANT = 0x100C;\nvar VT_VECTOR_LPSTR   = 0x101E;\n//var VT_ARRAY    = 0x2000;\n\nvar VT_STRING   = 0x0050; // 2.3.3.1.11 VtString\nvar VT_USTR     = 0x0051; // 2.3.3.1.12 VtUnalignedString\nvar VT_CUSTOM   = [VT_STRING, VT_USTR];\n\n/* [MS-OSHARED] 2.3.3.2.2.1 Document Summary Information PIDDSI */\nvar DocSummaryPIDDSI = {\n\t/*::[*/0x01/*::]*/: { n: 'CodePage', t: VT_I2 },\n\t/*::[*/0x02/*::]*/: { n: 'Category', t: VT_STRING },\n\t/*::[*/0x03/*::]*/: { n: 'PresentationFormat', t: VT_STRING },\n\t/*::[*/0x04/*::]*/: { n: 'ByteCount', t: VT_I4 },\n\t/*::[*/0x05/*::]*/: { n: 'LineCount', t: VT_I4 },\n\t/*::[*/0x06/*::]*/: { n: 'ParagraphCount', t: VT_I4 },\n\t/*::[*/0x07/*::]*/: { n: 'SlideCount', t: VT_I4 },\n\t/*::[*/0x08/*::]*/: { n: 'NoteCount', t: VT_I4 },\n\t/*::[*/0x09/*::]*/: { n: 'HiddenCount', t: VT_I4 },\n\t/*::[*/0x0a/*::]*/: { n: 'MultimediaClipCount', t: VT_I4 },\n\t/*::[*/0x0b/*::]*/: { n: 'ScaleCrop', t: VT_BOOL },\n\t/*::[*/0x0c/*::]*/: { n: 'HeadingPairs', t: VT_VECTOR_VARIANT /* VT_VECTOR | VT_VARIANT */ },\n\t/*::[*/0x0d/*::]*/: { n: 'TitlesOfParts', t: VT_VECTOR_LPSTR /* VT_VECTOR | VT_LPSTR */ },\n\t/*::[*/0x0e/*::]*/: { n: 'Manager', t: VT_STRING },\n\t/*::[*/0x0f/*::]*/: { n: 'Company', t: VT_STRING },\n\t/*::[*/0x10/*::]*/: { n: 'LinksUpToDate', t: VT_BOOL },\n\t/*::[*/0x11/*::]*/: { n: 'CharacterCount', t: VT_I4 },\n\t/*::[*/0x13/*::]*/: { n: 'SharedDoc', t: VT_BOOL },\n\t/*::[*/0x16/*::]*/: { n: 'HyperlinksChanged', t: VT_BOOL },\n\t/*::[*/0x17/*::]*/: { n: 'AppVersion', t: VT_I4, p: 'version' },\n\t/*::[*/0x18/*::]*/: { n: 'DigSig', t: VT_BLOB },\n\t/*::[*/0x1A/*::]*/: { n: 'ContentType', t: VT_STRING },\n\t/*::[*/0x1B/*::]*/: { n: 'ContentStatus', t: VT_STRING },\n\t/*::[*/0x1C/*::]*/: { n: 'Language', t: VT_STRING },\n\t/*::[*/0x1D/*::]*/: { n: 'Version', t: VT_STRING },\n\t/*::[*/0xFF/*::]*/: {},\n\t/* [MS-OLEPS] 2.18 */\n\t/*::[*/0x80000000/*::]*/: { n: 'Locale', t: VT_UI4 },\n\t/*::[*/0x80000003/*::]*/: { n: 'Behavior', t: VT_UI4 },\n\t/*::[*/0x72627262/*::]*/: {}\n};\n\n/* [MS-OSHARED] 2.3.3.2.1.1 Summary Information Property Set PIDSI */\nvar SummaryPIDSI = {\n\t/*::[*/0x01/*::]*/: { n: 'CodePage', t: VT_I2 },\n\t/*::[*/0x02/*::]*/: { n: 'Title', t: VT_STRING },\n\t/*::[*/0x03/*::]*/: { n: 'Subject', t: VT_STRING },\n\t/*::[*/0x04/*::]*/: { n: 'Author', t: VT_STRING },\n\t/*::[*/0x05/*::]*/: { n: 'Keywords', t: VT_STRING },\n\t/*::[*/0x06/*::]*/: { n: 'Comments', t: VT_STRING },\n\t/*::[*/0x07/*::]*/: { n: 'Template', t: VT_STRING },\n\t/*::[*/0x08/*::]*/: { n: 'LastAuthor', t: VT_STRING },\n\t/*::[*/0x09/*::]*/: { n: 'RevNumber', t: VT_STRING },\n\t/*::[*/0x0A/*::]*/: { n: 'EditTime', t: VT_FILETIME },\n\t/*::[*/0x0B/*::]*/: { n: 'LastPrinted', t: VT_FILETIME },\n\t/*::[*/0x0C/*::]*/: { n: 'CreatedDate', t: VT_FILETIME },\n\t/*::[*/0x0D/*::]*/: { n: 'ModifiedDate', t: VT_FILETIME },\n\t/*::[*/0x0E/*::]*/: { n: 'PageCount', t: VT_I4 },\n\t/*::[*/0x0F/*::]*/: { n: 'WordCount', t: VT_I4 },\n\t/*::[*/0x10/*::]*/: { n: 'CharCount', t: VT_I4 },\n\t/*::[*/0x11/*::]*/: { n: 'Thumbnail', t: VT_CF },\n\t/*::[*/0x12/*::]*/: { n: 'Application', t: VT_STRING },\n\t/*::[*/0x13/*::]*/: { n: 'DocSecurity', t: VT_I4 },\n\t/*::[*/0xFF/*::]*/: {},\n\t/* [MS-OLEPS] 2.18 */\n\t/*::[*/0x80000000/*::]*/: { n: 'Locale', t: VT_UI4 },\n\t/*::[*/0x80000003/*::]*/: { n: 'Behavior', t: VT_UI4 },\n\t/*::[*/0x72627262/*::]*/: {}\n};\n\n/* [MS-XLS] 2.4.63 Country/Region codes */\nvar CountryEnum = {\n\t/*::[*/0x0001/*::]*/: \"US\", // United States\n\t/*::[*/0x0002/*::]*/: \"CA\", // Canada\n\t/*::[*/0x0003/*::]*/: \"\", // Latin America (except Brazil)\n\t/*::[*/0x0007/*::]*/: \"RU\", // Russia\n\t/*::[*/0x0014/*::]*/: \"EG\", // Egypt\n\t/*::[*/0x001E/*::]*/: \"GR\", // Greece\n\t/*::[*/0x001F/*::]*/: \"NL\", // Netherlands\n\t/*::[*/0x0020/*::]*/: \"BE\", // Belgium\n\t/*::[*/0x0021/*::]*/: \"FR\", // France\n\t/*::[*/0x0022/*::]*/: \"ES\", // Spain\n\t/*::[*/0x0024/*::]*/: \"HU\", // Hungary\n\t/*::[*/0x0027/*::]*/: \"IT\", // Italy\n\t/*::[*/0x0029/*::]*/: \"CH\", // Switzerland\n\t/*::[*/0x002B/*::]*/: \"AT\", // Austria\n\t/*::[*/0x002C/*::]*/: \"GB\", // United Kingdom\n\t/*::[*/0x002D/*::]*/: \"DK\", // Denmark\n\t/*::[*/0x002E/*::]*/: \"SE\", // Sweden\n\t/*::[*/0x002F/*::]*/: \"NO\", // Norway\n\t/*::[*/0x0030/*::]*/: \"PL\", // Poland\n\t/*::[*/0x0031/*::]*/: \"DE\", // Germany\n\t/*::[*/0x0034/*::]*/: \"MX\", // Mexico\n\t/*::[*/0x0037/*::]*/: \"BR\", // Brazil\n\t/*::[*/0x003d/*::]*/: \"AU\", // Australia\n\t/*::[*/0x0040/*::]*/: \"NZ\", // New Zealand\n\t/*::[*/0x0042/*::]*/: \"TH\", // Thailand\n\t/*::[*/0x0051/*::]*/: \"JP\", // Japan\n\t/*::[*/0x0052/*::]*/: \"KR\", // Korea\n\t/*::[*/0x0054/*::]*/: \"VN\", // Viet Nam\n\t/*::[*/0x0056/*::]*/: \"CN\", // China\n\t/*::[*/0x005A/*::]*/: \"TR\", // Turkey\n\t/*::[*/0x0069/*::]*/: \"JS\", // Ramastan\n\t/*::[*/0x00D5/*::]*/: \"DZ\", // Algeria\n\t/*::[*/0x00D8/*::]*/: \"MA\", // Morocco\n\t/*::[*/0x00DA/*::]*/: \"LY\", // Libya\n\t/*::[*/0x015F/*::]*/: \"PT\", // Portugal\n\t/*::[*/0x0162/*::]*/: \"IS\", // Iceland\n\t/*::[*/0x0166/*::]*/: \"FI\", // Finland\n\t/*::[*/0x01A4/*::]*/: \"CZ\", // Czech Republic\n\t/*::[*/0x0376/*::]*/: \"TW\", // Taiwan\n\t/*::[*/0x03C1/*::]*/: \"LB\", // Lebanon\n\t/*::[*/0x03C2/*::]*/: \"JO\", // Jordan\n\t/*::[*/0x03C3/*::]*/: \"SY\", // Syria\n\t/*::[*/0x03C4/*::]*/: \"IQ\", // Iraq\n\t/*::[*/0x03C5/*::]*/: \"KW\", // Kuwait\n\t/*::[*/0x03C6/*::]*/: \"SA\", // Saudi Arabia\n\t/*::[*/0x03CB/*::]*/: \"AE\", // United Arab Emirates\n\t/*::[*/0x03CC/*::]*/: \"IL\", // Israel\n\t/*::[*/0x03CE/*::]*/: \"QA\", // Qatar\n\t/*::[*/0x03D5/*::]*/: \"IR\", // Iran\n\t/*::[*/0xFFFF/*::]*/: \"US\"  // United States\n};\n\n/* [MS-XLS] 2.5.127 */\nvar XLSFillPattern = [\n\tnull,\n\t'solid',\n\t'mediumGray',\n\t'darkGray',\n\t'lightGray',\n\t'darkHorizontal',\n\t'darkVertical',\n\t'darkDown',\n\t'darkUp',\n\t'darkGrid',\n\t'darkTrellis',\n\t'lightHorizontal',\n\t'lightVertical',\n\t'lightDown',\n\t'lightUp',\n\t'lightGrid',\n\t'lightTrellis',\n\t'gray125',\n\t'gray0625'\n];\n\nfunction rgbify(arr/*:Array<number>*/)/*:Array<[number, number, number]>*/ { return arr.map(function(x) { return [(x>>16)&255,(x>>8)&255,x&255]; }); }\n\n/* [MS-XLS] 2.5.161 */\n/* [MS-XLSB] 2.5.75 Icv */\nvar _XLSIcv = /*#__PURE__*/ rgbify([\n\t/* Color Constants */\n\t0x000000,\n\t0xFFFFFF,\n\t0xFF0000,\n\t0x00FF00,\n\t0x0000FF,\n\t0xFFFF00,\n\t0xFF00FF,\n\t0x00FFFF,\n\n\t/* Overridable Defaults */\n\t0x000000,\n\t0xFFFFFF,\n\t0xFF0000,\n\t0x00FF00,\n\t0x0000FF,\n\t0xFFFF00,\n\t0xFF00FF,\n\t0x00FFFF,\n\n\t0x800000,\n\t0x008000,\n\t0x000080,\n\t0x808000,\n\t0x800080,\n\t0x008080,\n\t0xC0C0C0,\n\t0x808080,\n\t0x9999FF,\n\t0x993366,\n\t0xFFFFCC,\n\t0xCCFFFF,\n\t0x660066,\n\t0xFF8080,\n\t0x0066CC,\n\t0xCCCCFF,\n\n\t0x000080,\n\t0xFF00FF,\n\t0xFFFF00,\n\t0x00FFFF,\n\t0x800080,\n\t0x800000,\n\t0x008080,\n\t0x0000FF,\n\t0x00CCFF,\n\t0xCCFFFF,\n\t0xCCFFCC,\n\t0xFFFF99,\n\t0x99CCFF,\n\t0xFF99CC,\n\t0xCC99FF,\n\t0xFFCC99,\n\n\t0x3366FF,\n\t0x33CCCC,\n\t0x99CC00,\n\t0xFFCC00,\n\t0xFF9900,\n\t0xFF6600,\n\t0x666699,\n\t0x969696,\n\t0x003366,\n\t0x339966,\n\t0x003300,\n\t0x333300,\n\t0x993300,\n\t0x993366,\n\t0x333399,\n\t0x333333,\n\n\t/* Other entries to appease BIFF8/12 */\n\t0xFFFFFF, /* 0x40 icvForeground ?? */\n\t0x000000, /* 0x41 icvBackground ?? */\n\t0x000000, /* 0x42 icvFrame ?? */\n\t0x000000, /* 0x43 icv3D ?? */\n\t0x000000, /* 0x44 icv3DText ?? */\n\t0x000000, /* 0x45 icv3DHilite ?? */\n\t0x000000, /* 0x46 icv3DShadow ?? */\n\t0x000000, /* 0x47 icvHilite ?? */\n\t0x000000, /* 0x48 icvCtlText ?? */\n\t0x000000, /* 0x49 icvCtlScrl ?? */\n\t0x000000, /* 0x4A icvCtlInv ?? */\n\t0x000000, /* 0x4B icvCtlBody ?? */\n\t0x000000, /* 0x4C icvCtlFrame ?? */\n\t0x000000, /* 0x4D icvCtlFore ?? */\n\t0x000000, /* 0x4E icvCtlBack ?? */\n\t0x000000, /* 0x4F icvCtlNeutral */\n\t0x000000, /* 0x50 icvInfoBk ?? */\n\t0x000000 /* 0x51 icvInfoText ?? */\n]);\nvar XLSIcv = /*#__PURE__*/dup(_XLSIcv);\n\n/* [MS-XLSB] 2.5.97.2 */\nvar BErr = {\n\t/*::[*/0x00/*::]*/: \"#NULL!\",\n\t/*::[*/0x07/*::]*/: \"#DIV/0!\",\n\t/*::[*/0x0F/*::]*/: \"#VALUE!\",\n\t/*::[*/0x17/*::]*/: \"#REF!\",\n\t/*::[*/0x1D/*::]*/: \"#NAME?\",\n\t/*::[*/0x24/*::]*/: \"#NUM!\",\n\t/*::[*/0x2A/*::]*/: \"#N/A\",\n\t/*::[*/0x2B/*::]*/: \"#GETTING_DATA\",\n\t/*::[*/0xFF/*::]*/: \"#WTF?\"\n};\n//var RBErr = evert_num(BErr);\nvar RBErr = {\n\t\"#NULL!\":        0x00,\n\t\"#DIV/0!\":       0x07,\n\t\"#VALUE!\":       0x0F,\n\t\"#REF!\":         0x17,\n\t\"#NAME?\":        0x1D,\n\t\"#NUM!\":         0x24,\n\t\"#N/A\":          0x2A,\n\t\"#GETTING_DATA\": 0x2B,\n\t\"#WTF?\":         0xFF\n};\n\n/* Parts enumerated in OPC spec, MS-XLSB and MS-XLSX */\n/* 12.3 Part Summary <SpreadsheetML> */\n/* 14.2 Part Summary <DrawingML> */\n/* [MS-XLSX] 2.1 Part Enumerations ; [MS-XLSB] 2.1.7 Part Enumeration */\nvar ct2type/*{[string]:string}*/ = ({\n\t/* Workbook */\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet.main+xml\": \"workbooks\",\n\t\"application/vnd.ms-excel.sheet.macroEnabled.main+xml\": \"workbooks\",\n\t\"application/vnd.ms-excel.sheet.binary.macroEnabled.main\": \"workbooks\",\n\t\"application/vnd.ms-excel.addin.macroEnabled.main+xml\": \"workbooks\",\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.template.main+xml\": \"workbooks\",\n\n\t/* Worksheet */\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.worksheet+xml\": \"sheets\",\n\t\"application/vnd.ms-excel.worksheet\": \"sheets\",\n\t\"application/vnd.ms-excel.binIndexWs\": \"TODO\", /* Binary Index */\n\n\t/* Chartsheet */\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.chartsheet+xml\": \"charts\",\n\t\"application/vnd.ms-excel.chartsheet\": \"charts\",\n\n\t/* Macrosheet */\n\t\"application/vnd.ms-excel.macrosheet+xml\": \"macros\",\n\t\"application/vnd.ms-excel.macrosheet\": \"macros\",\n\t\"application/vnd.ms-excel.intlmacrosheet\": \"TODO\",\n\t\"application/vnd.ms-excel.binIndexMs\": \"TODO\", /* Binary Index */\n\n\t/* Dialogsheet */\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.dialogsheet+xml\": \"dialogs\",\n\t\"application/vnd.ms-excel.dialogsheet\": \"dialogs\",\n\n\t/* Shared Strings */\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.sharedStrings+xml\": \"strs\",\n\t\"application/vnd.ms-excel.sharedStrings\": \"strs\",\n\n\t/* Styles */\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.styles+xml\": \"styles\",\n\t\"application/vnd.ms-excel.styles\": \"styles\",\n\n\t/* File Properties */\n\t\"application/vnd.openxmlformats-package.core-properties+xml\": \"coreprops\",\n\t\"application/vnd.openxmlformats-officedocument.custom-properties+xml\": \"custprops\",\n\t\"application/vnd.openxmlformats-officedocument.extended-properties+xml\": \"extprops\",\n\n\t/* Custom Data Properties */\n\t\"application/vnd.openxmlformats-officedocument.customXmlProperties+xml\": \"TODO\",\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.customProperty\": \"TODO\",\n\n\t/* Comments */\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.comments+xml\": \"comments\",\n\t\"application/vnd.ms-excel.comments\": \"comments\",\n\t\"application/vnd.ms-excel.threadedcomments+xml\": \"threadedcomments\",\n\t\"application/vnd.ms-excel.person+xml\": \"people\",\n\n\t/* Metadata (Stock/Geography and Dynamic Array) */\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.sheetMetadata+xml\": \"metadata\",\n\t\"application/vnd.ms-excel.sheetMetadata\": \"metadata\",\n\n\t/* PivotTable */\n\t\"application/vnd.ms-excel.pivotTable\": \"TODO\",\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.pivotTable+xml\": \"TODO\",\n\n\t/* Chart Objects */\n\t\"application/vnd.openxmlformats-officedocument.drawingml.chart+xml\": \"TODO\",\n\n\t/* Chart Colors */\n\t\"application/vnd.ms-office.chartcolorstyle+xml\": \"TODO\",\n\n\t/* Chart Style */\n\t\"application/vnd.ms-office.chartstyle+xml\": \"TODO\",\n\n\t/* Chart Advanced */\n\t\"application/vnd.ms-office.chartex+xml\": \"TODO\",\n\n\t/* Calculation Chain */\n\t\"application/vnd.ms-excel.calcChain\": \"calcchains\",\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.calcChain+xml\": \"calcchains\",\n\n\t/* Printer Settings */\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.printerSettings\": \"TODO\",\n\n\t/* ActiveX */\n\t\"application/vnd.ms-office.activeX\": \"TODO\",\n\t\"application/vnd.ms-office.activeX+xml\": \"TODO\",\n\n\t/* Custom Toolbars */\n\t\"application/vnd.ms-excel.attachedToolbars\": \"TODO\",\n\n\t/* External Data Connections */\n\t\"application/vnd.ms-excel.connections\": \"TODO\",\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.connections+xml\": \"TODO\",\n\n\t/* External Links */\n\t\"application/vnd.ms-excel.externalLink\": \"links\",\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.externalLink+xml\": \"links\",\n\n\t/* PivotCache */\n\t\"application/vnd.ms-excel.pivotCacheDefinition\": \"TODO\",\n\t\"application/vnd.ms-excel.pivotCacheRecords\": \"TODO\",\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.pivotCacheDefinition+xml\": \"TODO\",\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.pivotCacheRecords+xml\": \"TODO\",\n\n\t/* Query Table */\n\t\"application/vnd.ms-excel.queryTable\": \"TODO\",\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.queryTable+xml\": \"TODO\",\n\n\t/* Shared Workbook */\n\t\"application/vnd.ms-excel.userNames\": \"TODO\",\n\t\"application/vnd.ms-excel.revisionHeaders\": \"TODO\",\n\t\"application/vnd.ms-excel.revisionLog\": \"TODO\",\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.revisionHeaders+xml\": \"TODO\",\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.revisionLog+xml\": \"TODO\",\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.userNames+xml\": \"TODO\",\n\n\t/* Single Cell Table */\n\t\"application/vnd.ms-excel.tableSingleCells\": \"TODO\",\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.tableSingleCells+xml\": \"TODO\",\n\n\t/* Slicer */\n\t\"application/vnd.ms-excel.slicer\": \"TODO\",\n\t\"application/vnd.ms-excel.slicerCache\": \"TODO\",\n\t\"application/vnd.ms-excel.slicer+xml\": \"TODO\",\n\t\"application/vnd.ms-excel.slicerCache+xml\": \"TODO\",\n\n\t/* Sort Map */\n\t\"application/vnd.ms-excel.wsSortMap\": \"TODO\",\n\n\t/* Table */\n\t\"application/vnd.ms-excel.table\": \"TODO\",\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.table+xml\": \"TODO\",\n\n\t/* Themes */\n\t\"application/vnd.openxmlformats-officedocument.theme+xml\": \"themes\",\n\n\t/* Theme Override */\n\t\"application/vnd.openxmlformats-officedocument.themeOverride+xml\": \"TODO\",\n\n\t/* Timeline */\n\t\"application/vnd.ms-excel.Timeline+xml\": \"TODO\", /* verify */\n\t\"application/vnd.ms-excel.TimelineCache+xml\": \"TODO\", /* verify */\n\n\t/* VBA */\n\t\"application/vnd.ms-office.vbaProject\": \"vba\",\n\t\"application/vnd.ms-office.vbaProjectSignature\": \"TODO\",\n\n\t/* Volatile Dependencies */\n\t\"application/vnd.ms-office.volatileDependencies\": \"TODO\",\n\t\"application/vnd.openxmlformats-officedocument.spreadsheetml.volatileDependencies+xml\": \"TODO\",\n\n\t/* Control Properties */\n\t\"application/vnd.ms-excel.controlproperties+xml\": \"TODO\",\n\n\t/* Data Model */\n\t\"application/vnd.openxmlformats-officedocument.model+data\": \"TODO\",\n\n\t/* Survey */\n\t\"application/vnd.ms-excel.Survey+xml\": \"TODO\",\n\n\t/* Drawing */\n\t\"application/vnd.openxmlformats-officedocument.drawing+xml\": \"drawings\",\n\t\"application/vnd.openxmlformats-officedocument.drawingml.chartshapes+xml\": \"TODO\",\n\t\"application/vnd.openxmlformats-officedocument.drawingml.diagramColors+xml\": \"TODO\",\n\t\"application/vnd.openxmlformats-officedocument.drawingml.diagramData+xml\": \"TODO\",\n\t\"application/vnd.openxmlformats-officedocument.drawingml.diagramLayout+xml\": \"TODO\",\n\t\"application/vnd.openxmlformats-officedocument.drawingml.diagramStyle+xml\": \"TODO\",\n\n\t/* VML */\n\t\"application/vnd.openxmlformats-officedocument.vmlDrawing\": \"TODO\",\n\n\t\"application/vnd.openxmlformats-package.relationships+xml\": \"rels\",\n\t\"application/vnd.openxmlformats-officedocument.oleObject\": \"TODO\",\n\n\t/* Image */\n\t\"image/png\": \"TODO\",\n\n\t\"sheet\": \"js\"\n}/*:any*/);\n\nvar CT_LIST = {\n\t\tworkbooks: {\n\t\t\txlsx: \"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet.main+xml\",\n\t\t\txlsm: \"application/vnd.ms-excel.sheet.macroEnabled.main+xml\",\n\t\t\txlsb: \"application/vnd.ms-excel.sheet.binary.macroEnabled.main\",\n\t\t\txlam: \"application/vnd.ms-excel.addin.macroEnabled.main+xml\",\n\t\t\txltx: \"application/vnd.openxmlformats-officedocument.spreadsheetml.template.main+xml\"\n\t\t},\n\t\tstrs: { /* Shared Strings */\n\t\t\txlsx: \"application/vnd.openxmlformats-officedocument.spreadsheetml.sharedStrings+xml\",\n\t\t\txlsb: \"application/vnd.ms-excel.sharedStrings\"\n\t\t},\n\t\tcomments: { /* Comments */\n\t\t\txlsx: \"application/vnd.openxmlformats-officedocument.spreadsheetml.comments+xml\",\n\t\t\txlsb: \"application/vnd.ms-excel.comments\"\n\t\t},\n\t\tsheets: { /* Worksheet */\n\t\t\txlsx: \"application/vnd.openxmlformats-officedocument.spreadsheetml.worksheet+xml\",\n\t\t\txlsb: \"application/vnd.ms-excel.worksheet\"\n\t\t},\n\t\tcharts: { /* Chartsheet */\n\t\t\txlsx: \"application/vnd.openxmlformats-officedocument.spreadsheetml.chartsheet+xml\",\n\t\t\txlsb: \"application/vnd.ms-excel.chartsheet\"\n\t\t},\n\t\tdialogs: { /* Dialogsheet */\n\t\t\txlsx: \"application/vnd.openxmlformats-officedocument.spreadsheetml.dialogsheet+xml\",\n\t\t\txlsb: \"application/vnd.ms-excel.dialogsheet\"\n\t\t},\n\t\tmacros: { /* Macrosheet (Excel 4.0 Macros) */\n\t\t\txlsx: \"application/vnd.ms-excel.macrosheet+xml\",\n\t\t\txlsb: \"application/vnd.ms-excel.macrosheet\"\n\t\t},\n\t\tmetadata: { /* Metadata (Stock/Geography and Dynamic Array) */\n\t\t\txlsx: \"application/vnd.openxmlformats-officedocument.spreadsheetml.sheetMetadata+xml\",\n\t\t\txlsb: \"application/vnd.ms-excel.sheetMetadata\"\n\t\t},\n\t\tstyles: { /* Styles */\n\t\t\txlsx: \"application/vnd.openxmlformats-officedocument.spreadsheetml.styles+xml\",\n\t\t\txlsb: \"application/vnd.ms-excel.styles\"\n\t\t}\n};\n\nfunction new_ct()/*:any*/ {\n\treturn ({\n\t\tworkbooks:[], sheets:[], charts:[], dialogs:[], macros:[],\n\t\trels:[], strs:[], comments:[], threadedcomments:[], links:[],\n\t\tcoreprops:[], extprops:[], custprops:[], themes:[], styles:[],\n\t\tcalcchains:[], vba: [], drawings: [], metadata: [], people:[],\n\t\tTODO:[], xmlns: \"\" }/*:any*/);\n}\n\nfunction parse_ct(data/*:?string*/) {\n\tvar ct = new_ct();\n\tif(!data || !data.match) return ct;\n\tvar ctext = {};\n\t(data.match(tagregex)||[]).forEach(function(x) {\n\t\tvar y = parsexmltag(x);\n\t\tswitch(y[0].replace(nsregex,\"<\")) {\n\t\t\tcase '<?xml': break;\n\t\t\tcase '<Types': ct.xmlns = y['xmlns' + (y[0].match(/<(\\w+):/)||[\"\",\"\"])[1] ]; break;\n\t\t\tcase '<Default': ctext[y.Extension] = y.ContentType; break;\n\t\t\tcase '<Override':\n\t\t\t\tif(ct[ct2type[y.ContentType]] !== undefined) ct[ct2type[y.ContentType]].push(y.PartName);\n\t\t\t\tbreak;\n\t\t}\n\t});\n\tif(ct.xmlns !== XMLNS.CT) throw new Error(\"Unknown Namespace: \" + ct.xmlns);\n\tct.calcchain = ct.calcchains.length > 0 ? ct.calcchains[0] : \"\";\n\tct.sst = ct.strs.length > 0 ? ct.strs[0] : \"\";\n\tct.style = ct.styles.length > 0 ? ct.styles[0] : \"\";\n\tct.defaults = ctext;\n\tdelete ct.calcchains;\n\treturn ct;\n}\n\nfunction write_ct(ct, opts)/*:string*/ {\n\tvar type2ct/*{[string]:Array<string>}*/ = evert_arr(ct2type);\n\n\tvar o/*:Array<string>*/ = [], v;\n\to[o.length] = (XML_HEADER);\n\to[o.length] = writextag('Types', null, {\n\t\t'xmlns': XMLNS.CT,\n\t\t'xmlns:xsd': XMLNS.xsd,\n\t\t'xmlns:xsi': XMLNS.xsi\n\t});\n\n\to = o.concat([\n\t\t['xml', 'application/xml'],\n\t\t['bin', 'application/vnd.ms-excel.sheet.binary.macroEnabled.main'],\n\t\t['vml', 'application/vnd.openxmlformats-officedocument.vmlDrawing'],\n\t\t['data', 'application/vnd.openxmlformats-officedocument.model+data'],\n\t\t/* from test files */\n\t\t['bmp', 'image/bmp'],\n\t\t['png', 'image/png'],\n\t\t['gif', 'image/gif'],\n\t\t['emf', 'image/x-emf'],\n\t\t['wmf', 'image/x-wmf'],\n\t\t['jpg', 'image/jpeg'], ['jpeg', 'image/jpeg'],\n\t\t['tif', 'image/tiff'], ['tiff', 'image/tiff'],\n\t\t['pdf', 'application/pdf'],\n\t\t['rels', 'application/vnd.openxmlformats-package.relationships+xml']\n\t].map(function(x) {\n\t\treturn writextag('Default', null, {'Extension':x[0], 'ContentType': x[1]});\n\t}));\n\n\t/* only write first instance */\n\tvar f1 = function(w) {\n\t\tif(ct[w] && ct[w].length > 0) {\n\t\t\tv = ct[w][0];\n\t\t\to[o.length] = (writextag('Override', null, {\n\t\t\t\t'PartName': (v[0] == '/' ? \"\":\"/\") + v,\n\t\t\t\t'ContentType': CT_LIST[w][opts.bookType] || CT_LIST[w]['xlsx']\n\t\t\t}));\n\t\t}\n\t};\n\n\t/* book type-specific */\n\tvar f2 = function(w) {\n\t\t(ct[w]||[]).forEach(function(v) {\n\t\t\to[o.length] = (writextag('Override', null, {\n\t\t\t\t'PartName': (v[0] == '/' ? \"\":\"/\") + v,\n\t\t\t\t'ContentType': CT_LIST[w][opts.bookType] || CT_LIST[w]['xlsx']\n\t\t\t}));\n\t\t});\n\t};\n\n\t/* standard type */\n\tvar f3 = function(t) {\n\t\t(ct[t]||[]).forEach(function(v) {\n\t\t\to[o.length] = (writextag('Override', null, {\n\t\t\t\t'PartName': (v[0] == '/' ? \"\":\"/\") + v,\n\t\t\t\t'ContentType': type2ct[t][0]\n\t\t\t}));\n\t\t});\n\t};\n\n\tf1('workbooks');\n\tf2('sheets');\n\tf2('charts');\n\tf3('themes');\n\t['strs', 'styles'].forEach(f1);\n\t['coreprops', 'extprops', 'custprops'].forEach(f3);\n\tf3('vba');\n\tf3('comments');\n\tf3('threadedcomments');\n\tf3('drawings');\n\tf2('metadata');\n\tf3('people');\n\tif(o.length>2){ o[o.length] = ('</Types>'); o[1]=o[1].replace(\"/>\",\">\"); }\n\treturn o.join(\"\");\n}\n/* 9.3 Relationships */\nvar RELS = ({\n\tWB: \"http://schemas.openxmlformats.org/officeDocument/2006/relationships/officeDocument\",\n\tSHEET: \"http://sheetjs.openxmlformats.org/officeDocument/2006/relationships/officeDocument\",\n\tHLINK: \"http://schemas.openxmlformats.org/officeDocument/2006/relationships/hyperlink\",\n\tVML: \"http://schemas.openxmlformats.org/officeDocument/2006/relationships/vmlDrawing\",\n\tXPATH: \"http://schemas.openxmlformats.org/officeDocument/2006/relationships/externalLinkPath\",\n\tXMISS: \"http://schemas.microsoft.com/office/2006/relationships/xlExternalLinkPath/xlPathMissing\",\n\tXLINK: \"http://schemas.openxmlformats.org/officeDocument/2006/relationships/externalLink\",\n\tCXML: \"http://schemas.openxmlformats.org/officeDocument/2006/relationships/customXml\",\n\tCXMLP: \"http://schemas.openxmlformats.org/officeDocument/2006/relationships/customXmlProps\",\n\tCMNT: \"http://schemas.openxmlformats.org/officeDocument/2006/relationships/comments\",\n\tCORE_PROPS: \"http://schemas.openxmlformats.org/package/2006/relationships/metadata/core-properties\",\n\tEXT_PROPS: 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/extended-properties',\n\tCUST_PROPS: 'http://schemas.openxmlformats.org/officeDocument/2006/relationships/custom-properties',\n\tSST: \"http://schemas.openxmlformats.org/officeDocument/2006/relationships/sharedStrings\",\n\tSTY: \"http://schemas.openxmlformats.org/officeDocument/2006/relationships/styles\",\n\tTHEME: \"http://schemas.openxmlformats.org/officeDocument/2006/relationships/theme\",\n\tCHART: \"http://schemas.openxmlformats.org/officeDocument/2006/relationships/chart\",\n\tCHARTEX: \"http://schemas.microsoft.com/office/2014/relationships/chartEx\",\n\tCS: \"http://schemas.openxmlformats.org/officeDocument/2006/relationships/chartsheet\",\n\tWS: [\n\t\t\"http://schemas.openxmlformats.org/officeDocument/2006/relationships/worksheet\",\n\t\t\"http://purl.oclc.org/ooxml/officeDocument/relationships/worksheet\"\n\t],\n\tDS: \"http://schemas.openxmlformats.org/officeDocument/2006/relationships/dialogsheet\",\n\tMS: \"http://schemas.microsoft.com/office/2006/relationships/xlMacrosheet\",\n\tIMG: \"http://schemas.openxmlformats.org/officeDocument/2006/relationships/image\",\n\tDRAW: \"http://schemas.openxmlformats.org/officeDocument/2006/relationships/drawing\",\n\tXLMETA: \"http://schemas.openxmlformats.org/officeDocument/2006/relationships/sheetMetadata\",\n\tTCMNT: \"http://schemas.microsoft.com/office/2017/10/relationships/threadedComment\",\n\tPEOPLE: \"http://schemas.microsoft.com/office/2017/10/relationships/person\",\n\tVBA: \"http://schemas.microsoft.com/office/2006/relationships/vbaProject\"\n}/*:any*/);\n\n\n/* 9.3.3 Representing Relationships */\nfunction get_rels_path(file/*:string*/)/*:string*/ {\n\tvar n = file.lastIndexOf(\"/\");\n\treturn file.slice(0,n+1) + '_rels/' + file.slice(n+1) + \".rels\";\n}\n\nfunction parse_rels(data/*:?string*/, currentFilePath/*:string*/) {\n\tvar rels = {\"!id\":{}};\n\tif (!data) return rels;\n\tif (currentFilePath.charAt(0) !== '/') {\n\t\tcurrentFilePath = '/'+currentFilePath;\n\t}\n\tvar hash = {};\n\n\t(data.match(tagregex)||[]).forEach(function(x) {\n\t\tvar y = parsexmltag(x);\n\t\t/* 9.3.2.2 OPC_Relationships */\n\t\tif (y[0] === '<Relationship') {\n\t\t\tvar rel = {}; rel.Type = y.Type; rel.Target = y.Target; rel.Id = y.Id; if(y.TargetMode) rel.TargetMode = y.TargetMode;\n\t\t\tvar canonictarget = y.TargetMode === 'External' ? y.Target : resolve_path(y.Target, currentFilePath);\n\t\t\trels[canonictarget] = rel;\n\t\t\thash[y.Id] = rel;\n\t\t}\n\t});\n\trels[\"!id\"] = hash;\n\treturn rels;\n}\n\n\n/* TODO */\nfunction write_rels(rels)/*:string*/ {\n\tvar o = [XML_HEADER, writextag('Relationships', null, {\n\t\t//'xmlns:ns0': XMLNS.RELS,\n\t\t'xmlns': XMLNS.RELS\n\t})];\n\tkeys(rels['!id']).forEach(function(rid) {\n\t\to[o.length] = (writextag('Relationship', null, rels['!id'][rid]));\n\t});\n\tif(o.length>2){ o[o.length] = ('</Relationships>'); o[1]=o[1].replace(\"/>\",\">\"); }\n\treturn o.join(\"\");\n}\n\nfunction add_rels(rels, rId/*:number*/, f, type, relobj, targetmode/*:?string*/)/*:number*/ {\n\tif(!relobj) relobj = {};\n\tif(!rels['!id']) rels['!id'] = {};\n\tif(!rels['!idx']) rels['!idx'] = 1;\n\tif(rId < 0) for(rId = rels['!idx']; rels['!id']['rId' + rId]; ++rId){/* empty */}\n\trels['!idx'] = rId + 1;\n\trelobj.Id = 'rId' + rId;\n\trelobj.Type = type;\n\trelobj.Target = f;\n\tif(targetmode) relobj.TargetMode = targetmode;\n\telse if([RELS.HLINK, RELS.XPATH, RELS.XMISS].indexOf(relobj.Type) > -1) relobj.TargetMode = \"External\";\n\tif(rels['!id'][relobj.Id]) throw new Error(\"Cannot rewrite rId \" + rId);\n\trels['!id'][relobj.Id] = relobj;\n\trels[('/' + relobj.Target).replace(\"//\",\"/\")] = relobj;\n\treturn rId;\n}\n/* Open Document Format for Office Applications (OpenDocument) Version 1.2 */\n/* Part 3 Section 4 Manifest File */\nvar CT_ODS = \"application/vnd.oasis.opendocument.spreadsheet\";\nfunction parse_manifest(d, opts) {\n\tvar str = xlml_normalize(d);\n\tvar Rn;\n\tvar FEtag;\n\twhile((Rn = xlmlregex.exec(str))) switch(Rn[3]) {\n\t\tcase 'manifest': break; // 4.2 <manifest:manifest>\n\t\tcase 'file-entry': // 4.3 <manifest:file-entry>\n\t\t\tFEtag = parsexmltag(Rn[0], false);\n\t\t\tif(FEtag.path == '/' && FEtag.type !== CT_ODS) throw new Error(\"This OpenDocument is not a spreadsheet\");\n\t\t\tbreak;\n\t\tcase 'encryption-data': // 4.4 <manifest:encryption-data>\n\t\tcase 'algorithm': // 4.5 <manifest:algorithm>\n\t\tcase 'start-key-generation': // 4.6 <manifest:start-key-generation>\n\t\tcase 'key-derivation': // 4.7 <manifest:key-derivation>\n\t\t\tthrow new Error(\"Unsupported ODS Encryption\");\n\t\tdefault: if(opts && opts.WTF) throw Rn;\n\t}\n}\n\nfunction write_manifest(manifest/*:Array<Array<string> >*/)/*:string*/ {\n\tvar o = [XML_HEADER];\n\to.push('<manifest:manifest xmlns:manifest=\"urn:oasis:names:tc:opendocument:xmlns:manifest:1.0\" manifest:version=\"1.2\">\\n');\n\to.push('  <manifest:file-entry manifest:full-path=\"/\" manifest:version=\"1.2\" manifest:media-type=\"application/vnd.oasis.opendocument.spreadsheet\"/>\\n');\n\tfor(var i = 0; i < manifest.length; ++i) o.push('  <manifest:file-entry manifest:full-path=\"' + manifest[i][0] + '\" manifest:media-type=\"' + manifest[i][1] + '\"/>\\n');\n\to.push('</manifest:manifest>');\n\treturn o.join(\"\");\n}\n\n/* Part 3 Section 6 Metadata Manifest File */\nfunction write_rdf_type(file/*:string*/, res/*:string*/, tag/*:?string*/) {\n\treturn [\n\t\t'  <rdf:Description rdf:about=\"' + file + '\">\\n',\n\t\t'    <rdf:type rdf:resource=\"http://docs.oasis-open.org/ns/office/1.2/meta/' + (tag || \"odf\") + '#' + res + '\"/>\\n',\n\t\t'  </rdf:Description>\\n'\n\t].join(\"\");\n}\nfunction write_rdf_has(base/*:string*/, file/*:string*/) {\n\treturn [\n\t\t'  <rdf:Description rdf:about=\"' + base + '\">\\n',\n\t\t'    <ns0:hasPart xmlns:ns0=\"http://docs.oasis-open.org/ns/office/1.2/meta/pkg#\" rdf:resource=\"' + file + '\"/>\\n',\n\t\t'  </rdf:Description>\\n'\n\t].join(\"\");\n}\nfunction write_rdf(rdf) {\n\tvar o = [XML_HEADER];\n\to.push('<rdf:RDF xmlns:rdf=\"http://www.w3.org/1999/02/22-rdf-syntax-ns#\">\\n');\n\tfor(var i = 0; i != rdf.length; ++i) {\n\t\to.push(write_rdf_type(rdf[i][0], rdf[i][1]));\n\t\to.push(write_rdf_has(\"\",rdf[i][0]));\n\t}\n\to.push(write_rdf_type(\"\",\"Document\", \"pkg\"));\n\to.push('</rdf:RDF>');\n\treturn o.join(\"\");\n}\n/* TODO: pull properties */\nfunction write_meta_ods(/*:: wb: Workbook, opts: any*/)/*:string*/ {\n\treturn '<office:document-meta xmlns:office=\"urn:oasis:names:tc:opendocument:xmlns:office:1.0\" xmlns:meta=\"urn:oasis:names:tc:opendocument:xmlns:meta:1.0\" xmlns:dc=\"http://purl.org/dc/elements/1.1/\" xmlns:xlink=\"http://www.w3.org/1999/xlink\" office:version=\"1.2\"><office:meta><meta:generator>Sheet' + 'JS ' + XLSX.version + '</meta:generator></office:meta></office:document-meta>';\n}\n\n/* ECMA-376 Part II 11.1 Core Properties Part */\n/* [MS-OSHARED] 2.3.3.2.[1-2].1 (PIDSI/PIDDSI) */\nvar CORE_PROPS/*:Array<Array<string> >*/ = [\n\t[\"cp:category\", \"Category\"],\n\t[\"cp:contentStatus\", \"ContentStatus\"],\n\t[\"cp:keywords\", \"Keywords\"],\n\t[\"cp:lastModifiedBy\", \"LastAuthor\"],\n\t[\"cp:lastPrinted\", \"LastPrinted\"],\n\t[\"cp:revision\", \"RevNumber\"],\n\t[\"cp:version\", \"Version\"],\n\t[\"dc:creator\", \"Author\"],\n\t[\"dc:description\", \"Comments\"],\n\t[\"dc:identifier\", \"Identifier\"],\n\t[\"dc:language\", \"Language\"],\n\t[\"dc:subject\", \"Subject\"],\n\t[\"dc:title\", \"Title\"],\n\t[\"dcterms:created\", \"CreatedDate\", 'date'],\n\t[\"dcterms:modified\", \"ModifiedDate\", 'date']\n];\n\nvar CORE_PROPS_REGEX/*:Array<RegExp>*/ = /*#__PURE__*/(function() {\n\tvar r = new Array(CORE_PROPS.length);\n\tfor(var i = 0; i < CORE_PROPS.length; ++i) {\n\t\tvar f = CORE_PROPS[i];\n\t\tvar g = \"(?:\"+ f[0].slice(0,f[0].indexOf(\":\")) +\":)\"+ f[0].slice(f[0].indexOf(\":\")+1);\n\t\tr[i] = new RegExp(\"<\" + g + \"[^>]*>([\\\\s\\\\S]*?)<\\/\" + g + \">\");\n\t}\n\treturn r;\n})();\n\nfunction parse_core_props(data) {\n\tvar p = {};\n\tdata = utf8read(data);\n\n\tfor(var i = 0; i < CORE_PROPS.length; ++i) {\n\t\tvar f = CORE_PROPS[i], cur = data.match(CORE_PROPS_REGEX[i]);\n\t\tif(cur != null && cur.length > 0) p[f[1]] = unescapexml(cur[1]);\n\t\tif(f[2] === 'date' && p[f[1]]) p[f[1]] = parseDate(p[f[1]]);\n\t}\n\n\treturn p;\n}\n\nfunction cp_doit(f, g, h, o, p) {\n\tif(p[f] != null || g == null || g === \"\") return;\n\tp[f] = g;\n\tg = escapexml(g);\n\to[o.length] = (h ? writextag(f,g,h) : writetag(f,g));\n}\n\nfunction write_core_props(cp, _opts) {\n\tvar opts = _opts || {};\n\tvar o = [XML_HEADER, writextag('cp:coreProperties', null, {\n\t\t//'xmlns': XMLNS.CORE_PROPS,\n\t\t'xmlns:cp': XMLNS.CORE_PROPS,\n\t\t'xmlns:dc': XMLNS.dc,\n\t\t'xmlns:dcterms': XMLNS.dcterms,\n\t\t'xmlns:dcmitype': XMLNS.dcmitype,\n\t\t'xmlns:xsi': XMLNS.xsi\n\t})], p = {};\n\tif(!cp && !opts.Props) return o.join(\"\");\n\n\tif(cp) {\n\t\tif(cp.CreatedDate != null) cp_doit(\"dcterms:created\", typeof cp.CreatedDate === \"string\" ? cp.CreatedDate : write_w3cdtf(cp.CreatedDate, opts.WTF), {\"xsi:type\":\"dcterms:W3CDTF\"}, o, p);\n\t\tif(cp.ModifiedDate != null) cp_doit(\"dcterms:modified\", typeof cp.ModifiedDate === \"string\" ? cp.ModifiedDate : write_w3cdtf(cp.ModifiedDate, opts.WTF), {\"xsi:type\":\"dcterms:W3CDTF\"}, o, p);\n\t}\n\n\tfor(var i = 0; i != CORE_PROPS.length; ++i) {\n\t\tvar f = CORE_PROPS[i];\n\t\tvar v = opts.Props && opts.Props[f[1]] != null ? opts.Props[f[1]] : cp ? cp[f[1]] : null;\n\t\tif(v === true) v = \"1\";\n\t\telse if(v === false) v = \"0\";\n\t\telse if(typeof v == \"number\") v = String(v);\n\t\tif(v != null) cp_doit(f[0], v, null, o, p);\n\t}\n\tif(o.length>2){ o[o.length] = ('</cp:coreProperties>'); o[1]=o[1].replace(\"/>\",\">\"); }\n\treturn o.join(\"\");\n}\n/* 15.2.12.3 Extended File Properties Part */\n/* [MS-OSHARED] 2.3.3.2.[1-2].1 (PIDSI/PIDDSI) */\nvar EXT_PROPS/*:Array<Array<string> >*/ = [\n\t[\"Application\", \"Application\", \"string\"],\n\t[\"AppVersion\", \"AppVersion\", \"string\"],\n\t[\"Company\", \"Company\", \"string\"],\n\t[\"DocSecurity\", \"DocSecurity\", \"string\"],\n\t[\"Manager\", \"Manager\", \"string\"],\n\t[\"HyperlinksChanged\", \"HyperlinksChanged\", \"bool\"],\n\t[\"SharedDoc\", \"SharedDoc\", \"bool\"],\n\t[\"LinksUpToDate\", \"LinksUpToDate\", \"bool\"],\n\t[\"ScaleCrop\", \"ScaleCrop\", \"bool\"],\n\t[\"HeadingPairs\", \"HeadingPairs\", \"raw\"],\n\t[\"TitlesOfParts\", \"TitlesOfParts\", \"raw\"]\n];\n\nvar PseudoPropsPairs = [\n\t\"Worksheets\",  \"SheetNames\",\n\t\"NamedRanges\", \"DefinedNames\",\n\t\"Chartsheets\", \"ChartNames\"\n];\nfunction load_props_pairs(HP/*:string|Array<Array<any>>*/, TOP, props, opts) {\n\tvar v = [];\n\tif(typeof HP == \"string\") v = parseVector(HP, opts);\n\telse for(var j = 0; j < HP.length; ++j) v = v.concat(HP[j].map(function(hp) { return {v:hp}; }));\n\tvar parts = (typeof TOP == \"string\") ? parseVector(TOP, opts).map(function (x) { return x.v; }) : TOP;\n\tvar idx = 0, len = 0;\n\tif(parts.length > 0) for(var i = 0; i !== v.length; i += 2) {\n\t\tlen = +(v[i+1].v);\n\t\tswitch(v[i].v) {\n\t\t\tcase \"Worksheets\":\n\t\t\tcase \"工作表\":\n\t\t\tcase \"Листы\":\n\t\t\tcase \"أوراق العمل\":\n\t\t\tcase \"ワークシート\":\n\t\t\tcase \"גליונות עבודה\":\n\t\t\tcase \"Arbeitsblätter\":\n\t\t\tcase \"Çalışma Sayfaları\":\n\t\t\tcase \"Feuilles de calcul\":\n\t\t\tcase \"Fogli di lavoro\":\n\t\t\tcase \"Folhas de cálculo\":\n\t\t\tcase \"Planilhas\":\n\t\t\tcase \"Regneark\":\n\t\t\tcase \"Hojas de cálculo\":\n\t\t\tcase \"Werkbladen\":\n\t\t\t\tprops.Worksheets = len;\n\t\t\t\tprops.SheetNames = parts.slice(idx, idx + len);\n\t\t\t\tbreak;\n\n\t\t\tcase \"Named Ranges\":\n\t\t\tcase \"Rangos con nombre\":\n\t\t\tcase \"名前付き一覧\":\n\t\t\tcase \"Benannte Bereiche\":\n\t\t\tcase \"Navngivne områder\":\n\t\t\t\tprops.NamedRanges = len;\n\t\t\t\tprops.DefinedNames = parts.slice(idx, idx + len);\n\t\t\t\tbreak;\n\n\t\t\tcase \"Charts\":\n\t\t\tcase \"Diagramme\":\n\t\t\t\tprops.Chartsheets = len;\n\t\t\t\tprops.ChartNames = parts.slice(idx, idx + len);\n\t\t\t\tbreak;\n\t\t}\n\t\tidx += len;\n\t}\n}\n\nfunction parse_ext_props(data, p, opts) {\n\tvar q = {}; if(!p) p = {};\n\tdata = utf8read(data);\n\n\tEXT_PROPS.forEach(function(f) {\n\t\tvar xml = (data.match(matchtag(f[0]))||[])[1];\n\t\tswitch(f[2]) {\n\t\t\tcase \"string\": if(xml) p[f[1]] = unescapexml(xml); break;\n\t\t\tcase \"bool\": p[f[1]] = xml === \"true\"; break;\n\t\t\tcase \"raw\":\n\t\t\t\tvar cur = data.match(new RegExp(\"<\" + f[0] + \"[^>]*>([\\\\s\\\\S]*?)<\\/\" + f[0] + \">\"));\n\t\t\t\tif(cur && cur.length > 0) q[f[1]] = cur[1];\n\t\t\t\tbreak;\n\t\t}\n\t});\n\n\tif(q.HeadingPairs && q.TitlesOfParts) load_props_pairs(q.HeadingPairs, q.TitlesOfParts, p, opts);\n\n\treturn p;\n}\n\nfunction write_ext_props(cp/*::, opts*/)/*:string*/ {\n\tvar o/*:Array<string>*/ = [], W = writextag;\n\tif(!cp) cp = {};\n\tcp.Application = \"SheetJS\";\n\to[o.length] = (XML_HEADER);\n\to[o.length] = (writextag('Properties', null, {\n\t\t'xmlns': XMLNS.EXT_PROPS,\n\t\t'xmlns:vt': XMLNS.vt\n\t}));\n\n\tEXT_PROPS.forEach(function(f) {\n\t\tif(cp[f[1]] === undefined) return;\n\t\tvar v;\n\t\tswitch(f[2]) {\n\t\t\tcase 'string': v = escapexml(String(cp[f[1]])); break;\n\t\t\tcase 'bool': v = cp[f[1]] ? 'true' : 'false'; break;\n\t\t}\n\t\tif(v !== undefined) o[o.length] = (W(f[0], v));\n\t});\n\n\t/* TODO: HeadingPairs, TitlesOfParts */\n\to[o.length] = (W('HeadingPairs', W('vt:vector', W('vt:variant', '<vt:lpstr>Worksheets</vt:lpstr>')+W('vt:variant', W('vt:i4', String(cp.Worksheets))), {size:2, baseType:\"variant\"})));\n\to[o.length] = (W('TitlesOfParts', W('vt:vector', cp.SheetNames.map(function(s) { return \"<vt:lpstr>\" + escapexml(s) + \"</vt:lpstr>\"; }).join(\"\"), {size: cp.Worksheets, baseType:\"lpstr\"})));\n\tif(o.length>2){ o[o.length] = ('</Properties>'); o[1]=o[1].replace(\"/>\",\">\"); }\n\treturn o.join(\"\");\n}\n/* 15.2.12.2 Custom File Properties Part */\nvar custregex = /<[^>]+>[^<]*/g;\nfunction parse_cust_props(data/*:string*/, opts) {\n\tvar p = {}, name = \"\";\n\tvar m = data.match(custregex);\n\tif(m) for(var i = 0; i != m.length; ++i) {\n\t\tvar x = m[i], y = parsexmltag(x);\n\t\tswitch(y[0]) {\n\t\t\tcase '<?xml': break;\n\t\t\tcase '<Properties': break;\n\t\t\tcase '<property': name = unescapexml(y.name); break;\n\t\t\tcase '</property>': name = null; break;\n\t\t\tdefault: if (x.indexOf('<vt:') === 0) {\n\t\t\t\tvar toks = x.split('>');\n\t\t\t\tvar type = toks[0].slice(4), text = toks[1];\n\t\t\t\t/* 22.4.2.32 (CT_Variant). Omit the binary types from 22.4 (Variant Types) */\n\t\t\t\tswitch(type) {\n\t\t\t\t\tcase 'lpstr': case 'bstr': case 'lpwstr':\n\t\t\t\t\t\tp[name] = unescapexml(text);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase 'bool':\n\t\t\t\t\t\tp[name] = parsexmlbool(text);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase 'i1': case 'i2': case 'i4': case 'i8': case 'int': case 'uint':\n\t\t\t\t\t\tp[name] = parseInt(text, 10);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase 'r4': case 'r8': case 'decimal':\n\t\t\t\t\t\tp[name] = parseFloat(text);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase 'filetime': case 'date':\n\t\t\t\t\t\tp[name] = parseDate(text);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase 'cy': case 'error':\n\t\t\t\t\t\tp[name] = unescapexml(text);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tdefault:\n\t\t\t\t\t\tif(type.slice(-1) == '/') break;\n\t\t\t\t\t\tif(opts.WTF && typeof console !== 'undefined') console.warn('Unexpected', x, type, toks);\n\t\t\t\t}\n\t\t\t} else if(x.slice(0,2) === \"</\") {/* empty */\n\t\t\t} else if(opts.WTF) throw new Error(x);\n\t\t}\n\t}\n\treturn p;\n}\n\nfunction write_cust_props(cp/*::, opts*/)/*:string*/ {\n\tvar o = [XML_HEADER, writextag('Properties', null, {\n\t\t'xmlns': XMLNS.CUST_PROPS,\n\t\t'xmlns:vt': XMLNS.vt\n\t})];\n\tif(!cp) return o.join(\"\");\n\tvar pid = 1;\n\tkeys(cp).forEach(function custprop(k) { ++pid;\n\t\to[o.length] = (writextag('property', write_vt(cp[k], true), {\n\t\t\t'fmtid': '{D5CDD505-2E9C-101B-9397-08002B2CF9AE}',\n\t\t\t'pid': pid,\n\t\t\t'name': escapexml(k)\n\t\t}));\n\t});\n\tif(o.length>2){ o[o.length] = '</Properties>'; o[1]=o[1].replace(\"/>\",\">\"); }\n\treturn o.join(\"\");\n}\n/* Common Name -> XLML Name */\nvar XLMLDocPropsMap = {\n\tTitle: 'Title',\n\tSubject: 'Subject',\n\tAuthor: 'Author',\n\tKeywords: 'Keywords',\n\tComments: 'Description',\n\tLastAuthor: 'LastAuthor',\n\tRevNumber: 'Revision',\n\tApplication: 'AppName',\n\t/* TotalTime: 'TotalTime', */\n\tLastPrinted: 'LastPrinted',\n\tCreatedDate: 'Created',\n\tModifiedDate: 'LastSaved',\n\t/* Pages */\n\t/* Words */\n\t/* Characters */\n\tCategory: 'Category',\n\t/* PresentationFormat */\n\tManager: 'Manager',\n\tCompany: 'Company',\n\t/* Guid */\n\t/* HyperlinkBase */\n\t/* Bytes */\n\t/* Lines */\n\t/* Paragraphs */\n\t/* CharactersWithSpaces */\n\tAppVersion: 'Version',\n\n\tContentStatus: 'ContentStatus', /* NOTE: missing from schema */\n\tIdentifier: 'Identifier', /* NOTE: missing from schema */\n\tLanguage: 'Language' /* NOTE: missing from schema */\n};\nvar evert_XLMLDPM;\n\nfunction xlml_set_prop(Props, tag/*:string*/, val) {\n\tif(!evert_XLMLDPM) evert_XLMLDPM = evert(XLMLDocPropsMap);\n\ttag = evert_XLMLDPM[tag] || tag;\n\tProps[tag] = val;\n}\n\nfunction xlml_write_docprops(Props, opts) {\n\tvar o/*:Array<string>*/ = [];\n\tkeys(XLMLDocPropsMap).map(function(m) {\n\t\tfor(var i = 0; i < CORE_PROPS.length; ++i) if(CORE_PROPS[i][1] == m) return CORE_PROPS[i];\n\t\tfor(i = 0; i < EXT_PROPS.length; ++i) if(EXT_PROPS[i][1] == m) return EXT_PROPS[i];\n\t\tthrow m;\n\t}).forEach(function(p) {\n\t\tif(Props[p[1]] == null) return;\n\t\tvar m = opts && opts.Props && opts.Props[p[1]] != null ? opts.Props[p[1]] : Props[p[1]];\n\t\tswitch(p[2]) {\n\t\t\tcase 'date': m = new Date(m).toISOString().replace(/\\.\\d*Z/,\"Z\"); break;\n\t\t}\n\t\tif(typeof m == 'number') m = String(m);\n\t\telse if(m === true || m === false) { m = m ? \"1\" : \"0\"; }\n\t\telse if(m instanceof Date) m = new Date(m).toISOString().replace(/\\.\\d*Z/,\"\");\n\t\to.push(writetag(XLMLDocPropsMap[p[1]] || p[1], m));\n\t});\n\treturn writextag('DocumentProperties', o.join(\"\"), {xmlns:XLMLNS.o });\n}\nfunction xlml_write_custprops(Props, Custprops/*::, opts*/) {\n\tvar BLACKLIST = [\"Worksheets\",\"SheetNames\"];\n\tvar T = 'CustomDocumentProperties';\n\tvar o/*:Array<string>*/ = [];\n\tif(Props) keys(Props).forEach(function(k) {\n\t\t/*:: if(!Props) return; */\n\t\tif(!Object.prototype.hasOwnProperty.call(Props, k)) return;\n\t\tfor(var i = 0; i < CORE_PROPS.length; ++i) if(k == CORE_PROPS[i][1]) return;\n\t\tfor(i = 0; i < EXT_PROPS.length; ++i) if(k == EXT_PROPS[i][1]) return;\n\t\tfor(i = 0; i < BLACKLIST.length; ++i) if(k == BLACKLIST[i]) return;\n\n\t\tvar m = Props[k];\n\t\tvar t = \"string\";\n\t\tif(typeof m == 'number') { t = \"float\"; m = String(m); }\n\t\telse if(m === true || m === false) { t = \"boolean\"; m = m ? \"1\" : \"0\"; }\n\t\telse m = String(m);\n\t\to.push(writextag(escapexmltag(k), m, {\"dt:dt\":t}));\n\t});\n\tif(Custprops) keys(Custprops).forEach(function(k) {\n\t\t/*:: if(!Custprops) return; */\n\t\tif(!Object.prototype.hasOwnProperty.call(Custprops, k)) return;\n\t\tif(Props && Object.prototype.hasOwnProperty.call(Props, k)) return;\n\t\tvar m = Custprops[k];\n\t\tvar t = \"string\";\n\t\tif(typeof m == 'number') { t = \"float\"; m = String(m); }\n\t\telse if(m === true || m === false) { t = \"boolean\"; m = m ? \"1\" : \"0\"; }\n\t\telse if(m instanceof Date) { t = \"dateTime.tz\"; m = m.toISOString(); }\n\t\telse m = String(m);\n\t\to.push(writextag(escapexmltag(k), m, {\"dt:dt\":t}));\n\t});\n\treturn '<' + T + ' xmlns=\"' + XLMLNS.o + '\">' + o.join(\"\") + '</' + T + '>';\n}\n/* [MS-DTYP] 2.3.3 FILETIME */\n/* [MS-OLEDS] 2.1.3 FILETIME (Packet Version) */\n/* [MS-OLEPS] 2.8 FILETIME (Packet Version) */\nfunction parse_FILETIME(blob) {\n\tvar dwLowDateTime = blob.read_shift(4), dwHighDateTime = blob.read_shift(4);\n\treturn new Date(((dwHighDateTime/1e7*Math.pow(2,32) + dwLowDateTime/1e7) - 11644473600)*1000).toISOString().replace(/\\.000/,\"\");\n}\nfunction write_FILETIME(time/*:string|Date*/) {\n\tvar date = (typeof time == \"string\") ? new Date(Date.parse(time)) : time;\n\tvar t = date.getTime() / 1000 + 11644473600;\n\tvar l = t % Math.pow(2,32), h = (t - l) / Math.pow(2,32);\n\tl *= 1e7; h *= 1e7;\n\tvar w = (l / Math.pow(2,32)) | 0;\n\tif(w > 0) { l = l % Math.pow(2,32); h += w; }\n\tvar o = new_buf(8); o.write_shift(4, l); o.write_shift(4, h); return o;\n}\n\n/* [MS-OSHARED] 2.3.3.1.4 Lpstr */\nfunction parse_lpstr(blob, type, pad/*:?number*/) {\n\tvar start = blob.l;\n\tvar str = blob.read_shift(0, 'lpstr-cp');\n\tif(pad) while((blob.l - start) & 3) ++blob.l;\n\treturn str;\n}\n\n/* [MS-OSHARED] 2.3.3.1.6 Lpwstr */\nfunction parse_lpwstr(blob, type, pad) {\n\tvar str = blob.read_shift(0, 'lpwstr');\n\tif(pad) blob.l += (4 - ((str.length+1) & 3)) & 3;\n\treturn str;\n}\n\n\n/* [MS-OSHARED] 2.3.3.1.11 VtString */\n/* [MS-OSHARED] 2.3.3.1.12 VtUnalignedString */\nfunction parse_VtStringBase(blob, stringType, pad) {\n\tif(stringType === 0x1F /*VT_LPWSTR*/) return parse_lpwstr(blob);\n\treturn parse_lpstr(blob, stringType, pad);\n}\n\nfunction parse_VtString(blob, t/*:number*/, pad/*:?boolean*/) { return parse_VtStringBase(blob, t, pad === false ? 0: 4); }\nfunction parse_VtUnalignedString(blob, t/*:number*/) { if(!t) throw new Error(\"VtUnalignedString must have positive length\"); return parse_VtStringBase(blob, t, 0); }\n\n/* [MS-OSHARED] 2.3.3.1.7 VtVecLpwstrValue */\nfunction parse_VtVecLpwstrValue(blob)/*:Array<string>*/ {\n\tvar length = blob.read_shift(4);\n\tvar ret/*:Array<string>*/ = [];\n\tfor(var i = 0; i != length; ++i) {\n\t\tvar start = blob.l;\n\t\tret[i] = blob.read_shift(0, 'lpwstr').replace(chr0,'');\n\t\tif((blob.l - start) & 0x02) blob.l += 2;\n\t}\n\treturn ret;\n}\n\n/* [MS-OSHARED] 2.3.3.1.9 VtVecUnalignedLpstrValue */\nfunction parse_VtVecUnalignedLpstrValue(blob)/*:Array<string>*/ {\n\tvar length = blob.read_shift(4);\n\tvar ret/*:Array<string>*/ = [];\n\tfor(var i = 0; i != length; ++i) ret[i] = blob.read_shift(0, 'lpstr-cp').replace(chr0,'');\n\treturn ret;\n}\n\n\n/* [MS-OSHARED] 2.3.3.1.13 VtHeadingPair */\nfunction parse_VtHeadingPair(blob) {\n\tvar start = blob.l;\n\tvar headingString = parse_TypedPropertyValue(blob, VT_USTR);\n\tif(blob[blob.l] == 0x00 && blob[blob.l+1] == 0x00 && ((blob.l - start) & 0x02)) blob.l += 2;\n\tvar headerParts = parse_TypedPropertyValue(blob, VT_I4);\n\treturn [headingString, headerParts];\n}\n\n/* [MS-OSHARED] 2.3.3.1.14 VtVecHeadingPairValue */\nfunction parse_VtVecHeadingPairValue(blob) {\n\tvar cElements = blob.read_shift(4);\n\tvar out = [];\n\tfor(var i = 0; i < cElements / 2; ++i) out.push(parse_VtHeadingPair(blob));\n\treturn out;\n}\n\n/* [MS-OLEPS] 2.18.1 Dictionary (uses 2.17, 2.16) */\nfunction parse_dictionary(blob,CodePage) {\n\tvar cnt = blob.read_shift(4);\n\tvar dict/*:{[number]:string}*/ = ({}/*:any*/);\n\tfor(var j = 0; j != cnt; ++j) {\n\t\tvar pid = blob.read_shift(4);\n\t\tvar len = blob.read_shift(4);\n\t\tdict[pid] = blob.read_shift(len, (CodePage === 0x4B0 ?'utf16le':'utf8')).replace(chr0,'').replace(chr1,'!');\n\t\tif(CodePage === 0x4B0 && (len % 2)) blob.l += 2;\n\t}\n\tif(blob.l & 3) blob.l = (blob.l>>2+1)<<2;\n\treturn dict;\n}\n\n/* [MS-OLEPS] 2.9 BLOB */\nfunction parse_BLOB(blob) {\n\tvar size = blob.read_shift(4);\n\tvar bytes = blob.slice(blob.l,blob.l+size);\n\tblob.l += size;\n\tif((size & 3) > 0) blob.l += (4 - (size & 3)) & 3;\n\treturn bytes;\n}\n\n/* [MS-OLEPS] 2.11 ClipboardData */\nfunction parse_ClipboardData(blob) {\n\t// TODO\n\tvar o = {};\n\to.Size = blob.read_shift(4);\n\t//o.Format = blob.read_shift(4);\n\tblob.l += o.Size + 3 - (o.Size - 1) % 4;\n\treturn o;\n}\n\n/* [MS-OLEPS] 2.15 TypedPropertyValue */\nfunction parse_TypedPropertyValue(blob, type/*:number*/, _opts)/*:any*/ {\n\tvar t = blob.read_shift(2), ret, opts = _opts||{};\n\tblob.l += 2;\n\tif(type !== VT_VARIANT)\n\tif(t !== type && VT_CUSTOM.indexOf(type)===-1 && !((type & 0xFFFE) == 0x101E && (t & 0xFFFE) == 0x101E)) throw new Error('Expected type ' + type + ' saw ' + t);\n\tswitch(type === VT_VARIANT ? t : type) {\n\t\tcase 0x02 /*VT_I2*/: ret = blob.read_shift(2, 'i'); if(!opts.raw) blob.l += 2; return ret;\n\t\tcase 0x03 /*VT_I4*/: ret = blob.read_shift(4, 'i'); return ret;\n\t\tcase 0x0B /*VT_BOOL*/: return blob.read_shift(4) !== 0x0;\n\t\tcase 0x13 /*VT_UI4*/: ret = blob.read_shift(4); return ret;\n\t\tcase 0x1E /*VT_LPSTR*/: return parse_lpstr(blob, t, 4).replace(chr0,'');\n\t\tcase 0x1F /*VT_LPWSTR*/: return parse_lpwstr(blob);\n\t\tcase 0x40 /*VT_FILETIME*/: return parse_FILETIME(blob);\n\t\tcase 0x41 /*VT_BLOB*/: return parse_BLOB(blob);\n\t\tcase 0x47 /*VT_CF*/: return parse_ClipboardData(blob);\n\t\tcase 0x50 /*VT_STRING*/: return parse_VtString(blob, t, !opts.raw).replace(chr0,'');\n\t\tcase 0x51 /*VT_USTR*/: return parse_VtUnalignedString(blob, t/*, 4*/).replace(chr0,'');\n\t\tcase 0x100C /*VT_VECTOR|VT_VARIANT*/: return parse_VtVecHeadingPairValue(blob);\n\t\tcase 0x101E /*VT_VECTOR|VT_LPSTR*/:\n\t\tcase 0x101F /*VT_VECTOR|VT_LPWSTR*/:\n\t\t\treturn t == 0x101F ? parse_VtVecLpwstrValue(blob) : parse_VtVecUnalignedLpstrValue(blob);\n\t\tdefault: throw new Error(\"TypedPropertyValue unrecognized type \" + type + \" \" + t);\n\t}\n}\nfunction write_TypedPropertyValue(type/*:number*/, value) {\n\tvar o = new_buf(4), p = new_buf(4);\n\to.write_shift(4, type == 0x50 ? 0x1F : type);\n\tswitch(type) {\n\t\tcase 0x03 /*VT_I4*/: p.write_shift(-4, value); break;\n\t\tcase 0x05 /*VT_I4*/: p = new_buf(8); p.write_shift(8, value, 'f'); break;\n\t\tcase 0x0B /*VT_BOOL*/: p.write_shift(4, value ? 0x01 : 0x00); break;\n\t\tcase 0x40 /*VT_FILETIME*/: /*:: if(typeof value !== \"string\" && !(value instanceof Date)) throw \"unreachable\"; */ p = write_FILETIME(value); break;\n\t\tcase 0x1F /*VT_LPWSTR*/:\n\t\tcase 0x50 /*VT_STRING*/:\n\t\t\t/*:: if(typeof value !== \"string\") throw \"unreachable\"; */\n\t\t\tp = new_buf(4 + 2 * (value.length + 1) + (value.length % 2 ? 0 : 2));\n\t\t\tp.write_shift(4, value.length + 1);\n\t\t\tp.write_shift(0, value, \"dbcs\");\n\t\t\twhile(p.l != p.length) p.write_shift(1, 0);\n\t\t\tbreak;\n\t\tdefault: throw new Error(\"TypedPropertyValue unrecognized type \" + type + \" \" + value);\n\t}\n\treturn bconcat([o, p]);\n}\n\n/* [MS-OLEPS] 2.20 PropertySet */\nfunction parse_PropertySet(blob, PIDSI) {\n\tvar start_addr = blob.l;\n\tvar size = blob.read_shift(4);\n\tvar NumProps = blob.read_shift(4);\n\tvar Props = [], i = 0;\n\tvar CodePage = 0;\n\tvar Dictionary = -1, DictObj/*:{[number]:string}*/ = ({}/*:any*/);\n\tfor(i = 0; i != NumProps; ++i) {\n\t\tvar PropID = blob.read_shift(4);\n\t\tvar Offset = blob.read_shift(4);\n\t\tProps[i] = [PropID, Offset + start_addr];\n\t}\n\tProps.sort(function(x,y) { return x[1] - y[1]; });\n\tvar PropH = {};\n\tfor(i = 0; i != NumProps; ++i) {\n\t\tif(blob.l !== Props[i][1]) {\n\t\t\tvar fail = true;\n\t\t\tif(i>0 && PIDSI) switch(PIDSI[Props[i-1][0]].t) {\n\t\t\t\tcase 0x02 /*VT_I2*/: if(blob.l+2 === Props[i][1]) { blob.l+=2; fail = false; } break;\n\t\t\t\tcase 0x50 /*VT_STRING*/: if(blob.l <= Props[i][1]) { blob.l=Props[i][1]; fail = false; } break;\n\t\t\t\tcase 0x100C /*VT_VECTOR|VT_VARIANT*/: if(blob.l <= Props[i][1]) { blob.l=Props[i][1]; fail = false; } break;\n\t\t\t}\n\t\t\tif((!PIDSI||i==0) && blob.l <= Props[i][1]) { fail=false; blob.l = Props[i][1]; }\n\t\t\tif(fail) throw new Error(\"Read Error: Expected address \" + Props[i][1] + ' at ' + blob.l + ' :' + i);\n\t\t}\n\t\tif(PIDSI) {\n\t\t\tvar piddsi = PIDSI[Props[i][0]];\n\t\t\tPropH[piddsi.n] = parse_TypedPropertyValue(blob, piddsi.t, {raw:true});\n\t\t\tif(piddsi.p === 'version') PropH[piddsi.n] = String(PropH[piddsi.n] >> 16) + \".\" + (\"0000\" + String(PropH[piddsi.n] & 0xFFFF)).slice(-4);\n\t\t\tif(piddsi.n == \"CodePage\") switch(PropH[piddsi.n]) {\n\t\t\t\tcase 0: PropH[piddsi.n] = 1252;\n\t\t\t\t\t/* falls through */\n\t\t\t\tcase 874:\n\t\t\t\tcase 932:\n\t\t\t\tcase 936:\n\t\t\t\tcase 949:\n\t\t\t\tcase 950:\n\t\t\t\tcase 1250:\n\t\t\t\tcase 1251:\n\t\t\t\tcase 1253:\n\t\t\t\tcase 1254:\n\t\t\t\tcase 1255:\n\t\t\t\tcase 1256:\n\t\t\t\tcase 1257:\n\t\t\t\tcase 1258:\n\t\t\t\tcase 10000:\n\t\t\t\tcase 1200:\n\t\t\t\tcase 1201:\n\t\t\t\tcase 1252:\n\t\t\t\tcase 65000: case -536:\n\t\t\t\tcase 65001: case -535:\n\t\t\t\t\tset_cp(CodePage = (PropH[piddsi.n]>>>0) & 0xFFFF); break;\n\t\t\t\tdefault: throw new Error(\"Unsupported CodePage: \" + PropH[piddsi.n]);\n\t\t\t}\n\t\t} else {\n\t\t\tif(Props[i][0] === 0x1) {\n\t\t\t\tCodePage = PropH.CodePage = (parse_TypedPropertyValue(blob, VT_I2)/*:number*/);\n\t\t\t\tset_cp(CodePage);\n\t\t\t\tif(Dictionary !== -1) {\n\t\t\t\t\tvar oldpos = blob.l;\n\t\t\t\t\tblob.l = Props[Dictionary][1];\n\t\t\t\t\tDictObj = parse_dictionary(blob,CodePage);\n\t\t\t\t\tblob.l = oldpos;\n\t\t\t\t}\n\t\t\t} else if(Props[i][0] === 0) {\n\t\t\t\tif(CodePage === 0) { Dictionary = i; blob.l = Props[i+1][1]; continue; }\n\t\t\t\tDictObj = parse_dictionary(blob,CodePage);\n\t\t\t} else {\n\t\t\t\tvar name = DictObj[Props[i][0]];\n\t\t\t\tvar val;\n\t\t\t\t/* [MS-OSHARED] 2.3.3.2.3.1.2 + PROPVARIANT */\n\t\t\t\tswitch(blob[blob.l]) {\n\t\t\t\t\tcase 0x41 /*VT_BLOB*/: blob.l += 4; val = parse_BLOB(blob); break;\n\t\t\t\t\tcase 0x1E /*VT_LPSTR*/: blob.l += 4; val = parse_VtString(blob, blob[blob.l-4]).replace(/\\u0000+$/,\"\"); break;\n\t\t\t\t\tcase 0x1F /*VT_LPWSTR*/: blob.l += 4; val = parse_VtString(blob, blob[blob.l-4]).replace(/\\u0000+$/,\"\"); break;\n\t\t\t\t\tcase 0x03 /*VT_I4*/: blob.l += 4; val = blob.read_shift(4, 'i'); break;\n\t\t\t\t\tcase 0x13 /*VT_UI4*/: blob.l += 4; val = blob.read_shift(4); break;\n\t\t\t\t\tcase 0x05 /*VT_R8*/: blob.l += 4; val = blob.read_shift(8, 'f'); break;\n\t\t\t\t\tcase 0x0B /*VT_BOOL*/: blob.l += 4; val = parsebool(blob, 4); break;\n\t\t\t\t\tcase 0x40 /*VT_FILETIME*/: blob.l += 4; val = parseDate(parse_FILETIME(blob)); break;\n\t\t\t\t\tdefault: throw new Error(\"unparsed value: \" + blob[blob.l]);\n\t\t\t\t}\n\t\t\t\tPropH[name] = val;\n\t\t\t}\n\t\t}\n\t}\n\tblob.l = start_addr + size; /* step ahead to skip padding */\n\treturn PropH;\n}\nvar XLSPSSkip = [ \"CodePage\", \"Thumbnail\", \"_PID_LINKBASE\", \"_PID_HLINKS\", \"SystemIdentifier\", \"FMTID\" ]; //.concat(PseudoPropsPairs);\nfunction guess_property_type(val/*:any*/)/*:number*/ {\n\tswitch(typeof val) {\n\t\tcase \"boolean\": return 0x0B;\n\t\tcase \"number\": return ((val|0)==val) ? 0x03 : 0x05;\n\t\tcase \"string\": return 0x1F;\n\t\tcase \"object\": if(val instanceof Date) return 0x40; break;\n\t}\n\treturn -1;\n}\nfunction write_PropertySet(entries, RE, PIDSI) {\n\tvar hdr = new_buf(8), piao = [], prop = [];\n\tvar sz = 8, i = 0;\n\n\tvar pr = new_buf(8), pio = new_buf(8);\n\tpr.write_shift(4, 0x0002);\n\tpr.write_shift(4, 0x04B0);\n\tpio.write_shift(4, 0x0001);\n\tprop.push(pr); piao.push(pio);\n\tsz += 8 + pr.length;\n\n\tif(!RE) {\n\t\tpio = new_buf(8);\n\t\tpio.write_shift(4, 0);\n\t\tpiao.unshift(pio);\n\n\t\tvar bufs = [new_buf(4)];\n\t\tbufs[0].write_shift(4, entries.length);\n\t\tfor(i = 0; i < entries.length; ++i) {\n\t\t\tvar value = entries[i][0];\n\t\t\tpr = new_buf(4 + 4 + 2 * (value.length + 1) + (value.length % 2 ? 0 : 2));\n\t\t\tpr.write_shift(4, i+2);\n\t\t\tpr.write_shift(4, value.length + 1);\n\t\t\tpr.write_shift(0, value, \"dbcs\");\n\t\t\twhile(pr.l != pr.length) pr.write_shift(1, 0);\n\t\t\tbufs.push(pr);\n\t\t}\n\t\tpr = bconcat(bufs);\n\t\tprop.unshift(pr);\n\t\tsz += 8 + pr.length;\n\t}\n\n\tfor(i = 0; i < entries.length; ++i) {\n\t\tif(RE && !RE[entries[i][0]]) continue;\n\t\tif(XLSPSSkip.indexOf(entries[i][0]) > -1 || PseudoPropsPairs.indexOf(entries[i][0]) > -1) continue;\n\t\tif(entries[i][1] == null) continue;\n\n\t\tvar val = entries[i][1], idx = 0;\n\t\tif(RE) {\n\t\t\tidx = +RE[entries[i][0]];\n\t\t\tvar pinfo = (PIDSI/*:: || {}*/)[idx]/*:: || {} */;\n\t\t\tif(pinfo.p == \"version\" && typeof val == \"string\") {\n\t\t\t\t/*:: if(typeof val !== \"string\") throw \"unreachable\"; */\n\t\t\t\tvar arr = val.split(\".\");\n\t\t\t\tval = ((+arr[0])<<16) + ((+arr[1])||0);\n\t\t\t}\n\t\t\tpr = write_TypedPropertyValue(pinfo.t, val);\n\t\t} else {\n\t\t\tvar T = guess_property_type(val);\n\t\t\tif(T == -1) { T = 0x1F; val = String(val); }\n\t\t\tpr = write_TypedPropertyValue(T, val);\n\t\t}\n\t\tprop.push(pr);\n\n\t\tpio = new_buf(8);\n\t\tpio.write_shift(4, !RE ? 2+i : idx);\n\t\tpiao.push(pio);\n\n\t\tsz += 8 + pr.length;\n\t}\n\n\tvar w = 8 * (prop.length + 1);\n\tfor(i = 0; i < prop.length; ++i) { piao[i].write_shift(4, w); w += prop[i].length; }\n\thdr.write_shift(4, sz);\n\thdr.write_shift(4, prop.length);\n\treturn bconcat([hdr].concat(piao).concat(prop));\n}\n\n/* [MS-OLEPS] 2.21 PropertySetStream */\nfunction parse_PropertySetStream(file, PIDSI, clsid) {\n\tvar blob = file.content;\n\tif(!blob) return ({}/*:any*/);\n\tprep_blob(blob, 0);\n\n\tvar NumSets, FMTID0, FMTID1, Offset0, Offset1 = 0;\n\tblob.chk('feff', 'Byte Order: ');\n\n\t/*var vers = */blob.read_shift(2); // TODO: check version\n\tvar SystemIdentifier = blob.read_shift(4);\n\tvar CLSID = blob.read_shift(16);\n\tif(CLSID !== CFB.utils.consts.HEADER_CLSID && CLSID !== clsid) throw new Error(\"Bad PropertySet CLSID \" + CLSID);\n\tNumSets = blob.read_shift(4);\n\tif(NumSets !== 1 && NumSets !== 2) throw new Error(\"Unrecognized #Sets: \" + NumSets);\n\tFMTID0 = blob.read_shift(16); Offset0 = blob.read_shift(4);\n\n\tif(NumSets === 1 && Offset0 !== blob.l) throw new Error(\"Length mismatch: \" + Offset0 + \" !== \" + blob.l);\n\telse if(NumSets === 2) { FMTID1 = blob.read_shift(16); Offset1 = blob.read_shift(4); }\n\tvar PSet0 = parse_PropertySet(blob, PIDSI);\n\n\tvar rval = ({ SystemIdentifier: SystemIdentifier }/*:any*/);\n\tfor(var y in PSet0) rval[y] = PSet0[y];\n\t//rval.blob = blob;\n\trval.FMTID = FMTID0;\n\t//rval.PSet0 = PSet0;\n\tif(NumSets === 1) return rval;\n\tif(Offset1 - blob.l == 2) blob.l += 2;\n\tif(blob.l !== Offset1) throw new Error(\"Length mismatch 2: \" + blob.l + \" !== \" + Offset1);\n\tvar PSet1;\n\ttry { PSet1 = parse_PropertySet(blob, null); } catch(e) {/* empty */}\n\tfor(y in PSet1) rval[y] = PSet1[y];\n\trval.FMTID = [FMTID0, FMTID1]; // TODO: verify FMTID0/1\n\treturn rval;\n}\nfunction write_PropertySetStream(entries, clsid, RE, PIDSI/*:{[key:string|number]:any}*/, entries2/*:?any*/, clsid2/*:?any*/) {\n\tvar hdr = new_buf(entries2 ? 68 : 48);\n\tvar bufs = [hdr];\n\thdr.write_shift(2, 0xFFFE);\n\thdr.write_shift(2, 0x0000); /* TODO: type 1 props */\n\thdr.write_shift(4, 0x32363237);\n\thdr.write_shift(16, CFB.utils.consts.HEADER_CLSID, \"hex\");\n\thdr.write_shift(4, (entries2 ? 2 : 1));\n\thdr.write_shift(16, clsid, \"hex\");\n\thdr.write_shift(4, (entries2 ? 68 : 48));\n\tvar ps0 = write_PropertySet(entries, RE, PIDSI);\n\tbufs.push(ps0);\n\n\tif(entries2) {\n\t\tvar ps1 = write_PropertySet(entries2, null, null);\n\t\thdr.write_shift(16, clsid2, \"hex\");\n\t\thdr.write_shift(4, 68 + ps0.length);\n\t\tbufs.push(ps1);\n\t}\n\treturn bconcat(bufs);\n}\n\nfunction parsenoop2(blob, length) { blob.read_shift(length); return null; }\nfunction writezeroes(n, o) { if(!o) o=new_buf(n); for(var j=0; j<n; ++j) o.write_shift(1, 0); return o; }\n\nfunction parslurp(blob, length, cb) {\n\tvar arr = [], target = blob.l + length;\n\twhile(blob.l < target) arr.push(cb(blob, target - blob.l));\n\tif(target !== blob.l) throw new Error(\"Slurp error\");\n\treturn arr;\n}\n\nfunction parsebool(blob, length/*:number*/) { return blob.read_shift(length) === 0x1; }\nfunction writebool(v/*:any*/, o) { if(!o) o=new_buf(2); o.write_shift(2, +!!v); return o; }\n\nfunction parseuint16(blob/*::, length:?number, opts:?any*/) { return blob.read_shift(2, 'u'); }\nfunction writeuint16(v/*:number*/, o) { if(!o) o=new_buf(2); o.write_shift(2, v); return o; }\nfunction parseuint16a(blob, length/*:: :?number, opts:?any*/) { return parslurp(blob,length,parseuint16);}\n\n/* --- 2.5 Structures --- */\n\n/* [MS-XLS] 2.5.10 Bes (boolean or error) */\nfunction parse_Bes(blob/*::, length*/) {\n\tvar v = blob.read_shift(1), t = blob.read_shift(1);\n\treturn t === 0x01 ? v : v === 0x01;\n}\nfunction write_Bes(v, t/*:string*/, o) {\n\tif(!o) o = new_buf(2);\n\to.write_shift(1, ((t == 'e') ? +v : +!!v));\n\to.write_shift(1, ((t == 'e') ? 1 : 0));\n\treturn o;\n}\n\n/* [MS-XLS] 2.5.240 ShortXLUnicodeString */\nfunction parse_ShortXLUnicodeString(blob, length, opts) {\n\tvar cch = blob.read_shift(opts && opts.biff >= 12 ? 2 : 1);\n\tvar encoding = 'sbcs-cont';\n\tvar cp = current_codepage;\n\tif(opts && opts.biff >= 8) current_codepage = 1200;\n\tif(!opts || opts.biff == 8 ) {\n\t\tvar fHighByte = blob.read_shift(1);\n\t\tif(fHighByte) { encoding = 'dbcs-cont'; }\n\t} else if(opts.biff == 12) {\n\t\tencoding = 'wstr';\n\t}\n\tif(opts.biff >= 2 && opts.biff <= 5) encoding = 'cpstr';\n\tvar o = cch ? blob.read_shift(cch, encoding) : \"\";\n\tcurrent_codepage = cp;\n\treturn o;\n}\n\n/* 2.5.293 XLUnicodeRichExtendedString */\nfunction parse_XLUnicodeRichExtendedString(blob) {\n\tvar cp = current_codepage;\n\tcurrent_codepage = 1200;\n\tvar cch = blob.read_shift(2), flags = blob.read_shift(1);\n\tvar /*fHighByte = flags & 0x1,*/ fExtSt = flags & 0x4, fRichSt = flags & 0x8;\n\tvar width = 1 + (flags & 0x1); // 0x0 -> utf8, 0x1 -> dbcs\n\tvar cRun = 0, cbExtRst;\n\tvar z = {};\n\tif(fRichSt) cRun = blob.read_shift(2);\n\tif(fExtSt) cbExtRst = blob.read_shift(4);\n\tvar encoding = width == 2 ? 'dbcs-cont' : 'sbcs-cont';\n\tvar msg = cch === 0 ? \"\" : blob.read_shift(cch, encoding);\n\tif(fRichSt) blob.l += 4 * cRun; //TODO: parse this\n\tif(fExtSt) blob.l += cbExtRst; //TODO: parse this\n\tz.t = msg;\n\tif(!fRichSt) { z.raw = \"<t>\" + z.t + \"</t>\"; z.r = z.t; }\n\tcurrent_codepage = cp;\n\treturn z;\n}\nfunction write_XLUnicodeRichExtendedString(xlstr/*:: :XLString, opts*/) {\n\tvar str = (xlstr.t||\"\"), nfmts = 1;\n\n\tvar hdr = new_buf(3 + (nfmts > 1 ? 2 : 0));\n\thdr.write_shift(2, str.length);\n\thdr.write_shift(1, (nfmts > 1 ? 0x08 : 0x00) | 0x01);\n\tif(nfmts > 1) hdr.write_shift(2, nfmts);\n\n\tvar otext = new_buf(2 * str.length);\n\totext.write_shift(2 * str.length, str, 'utf16le');\n\n\tvar out = [hdr, otext];\n\n\treturn bconcat(out);\n}\n\n/* 2.5.296 XLUnicodeStringNoCch */\nfunction parse_XLUnicodeStringNoCch(blob, cch, opts) {\n\tvar retval;\n\tif(opts) {\n\t\tif(opts.biff >= 2 && opts.biff <= 5) return blob.read_shift(cch, 'cpstr');\n\t\tif(opts.biff >= 12) return blob.read_shift(cch, 'dbcs-cont');\n\t}\n\tvar fHighByte = blob.read_shift(1);\n\tif(fHighByte===0) { retval = blob.read_shift(cch, 'sbcs-cont'); }\n\telse { retval = blob.read_shift(cch, 'dbcs-cont'); }\n\treturn retval;\n}\n\n/* 2.5.294 XLUnicodeString */\nfunction parse_XLUnicodeString(blob, length, opts) {\n\tvar cch = blob.read_shift(opts && opts.biff == 2 ? 1 : 2);\n\tif(cch === 0) { blob.l++; return \"\"; }\n\treturn parse_XLUnicodeStringNoCch(blob, cch, opts);\n}\n/* BIFF5 override */\nfunction parse_XLUnicodeString2(blob, length, opts) {\n\tif(opts.biff > 5) return parse_XLUnicodeString(blob, length, opts);\n\tvar cch = blob.read_shift(1);\n\tif(cch === 0) { blob.l++; return \"\"; }\n\treturn blob.read_shift(cch, (opts.biff <= 4 || !blob.lens ) ? 'cpstr' : 'sbcs-cont');\n}\n/* TODO: BIFF5 and lower, codepage awareness */\nfunction write_XLUnicodeString(str, opts, o) {\n\tif(!o) o = new_buf(3 + 2 * str.length);\n\to.write_shift(2, str.length);\n\to.write_shift(1, 1);\n\to.write_shift(31, str, 'utf16le');\n\treturn o;\n}\n\n/* [MS-XLS] 2.5.61 ControlInfo */\nfunction parse_ControlInfo(blob/*::, length, opts*/) {\n\tvar flags = blob.read_shift(1);\n\tblob.l++;\n\tvar accel = blob.read_shift(2);\n\tblob.l += 2;\n\treturn [flags, accel];\n}\n\n/* [MS-OSHARED] 2.3.7.6 URLMoniker TODO: flags */\nfunction parse_URLMoniker(blob/*::, length, opts*/) {\n\tvar len = blob.read_shift(4), start = blob.l;\n\tvar extra = false;\n\tif(len > 24) {\n\t\t/* look ahead */\n\t\tblob.l += len - 24;\n\t\tif(blob.read_shift(16) === \"795881f43b1d7f48af2c825dc4852763\") extra = true;\n\t\tblob.l = start;\n\t}\n\tvar url = blob.read_shift((extra?len-24:len)>>1, 'utf16le').replace(chr0,\"\");\n\tif(extra) blob.l += 24;\n\treturn url;\n}\n\n/* [MS-OSHARED] 2.3.7.8 FileMoniker TODO: all fields */\nfunction parse_FileMoniker(blob/*::, length*/) {\n\tvar cAnti = blob.read_shift(2);\n\tvar preamble = \"\"; while(cAnti-- > 0) preamble += \"../\";\n\tvar ansiPath = blob.read_shift(0, 'lpstr-ansi');\n\tblob.l += 2; //var endServer = blob.read_shift(2);\n\tif(blob.read_shift(2) != 0xDEAD) throw new Error(\"Bad FileMoniker\");\n\tvar sz = blob.read_shift(4);\n\tif(sz === 0) return preamble + ansiPath.replace(/\\\\/g,\"/\");\n\tvar bytes = blob.read_shift(4);\n\tif(blob.read_shift(2) != 3) throw new Error(\"Bad FileMoniker\");\n\tvar unicodePath = blob.read_shift(bytes>>1, 'utf16le').replace(chr0,\"\");\n\treturn preamble + unicodePath;\n}\n\n/* [MS-OSHARED] 2.3.7.2 HyperlinkMoniker TODO: all the monikers */\nfunction parse_HyperlinkMoniker(blob, length) {\n\tvar clsid = blob.read_shift(16); length -= 16;\n\tswitch(clsid) {\n\t\tcase \"e0c9ea79f9bace118c8200aa004ba90b\": return parse_URLMoniker(blob, length);\n\t\tcase \"0303000000000000c000000000000046\": return parse_FileMoniker(blob, length);\n\t\tdefault: throw new Error(\"Unsupported Moniker \" + clsid);\n\t}\n}\n\n/* [MS-OSHARED] 2.3.7.9 HyperlinkString */\nfunction parse_HyperlinkString(blob/*::, length*/) {\n\tvar len = blob.read_shift(4);\n\tvar o = len > 0 ? blob.read_shift(len, 'utf16le').replace(chr0, \"\") : \"\";\n\treturn o;\n}\nfunction write_HyperlinkString(str/*:string*/, o) {\n\tif(!o) o = new_buf(6 + str.length * 2);\n\to.write_shift(4, 1 + str.length);\n\tfor(var i = 0; i < str.length; ++i) o.write_shift(2, str.charCodeAt(i));\n\to.write_shift(2, 0);\n\treturn o;\n}\n\n/* [MS-OSHARED] 2.3.7.1 Hyperlink Object */\nfunction parse_Hyperlink(blob, length)/*:Hyperlink*/ {\n\tvar end = blob.l + length;\n\tvar sVer = blob.read_shift(4);\n\tif(sVer !== 2) throw new Error(\"Unrecognized streamVersion: \" + sVer);\n\tvar flags = blob.read_shift(2);\n\tblob.l += 2;\n\tvar displayName, targetFrameName, moniker, oleMoniker, Loc=\"\", guid, fileTime;\n\tif(flags & 0x0010) displayName = parse_HyperlinkString(blob, end - blob.l);\n\tif(flags & 0x0080) targetFrameName = parse_HyperlinkString(blob, end - blob.l);\n\tif((flags & 0x0101) === 0x0101) moniker = parse_HyperlinkString(blob, end - blob.l);\n\tif((flags & 0x0101) === 0x0001) oleMoniker = parse_HyperlinkMoniker(blob, end - blob.l);\n\tif(flags & 0x0008) Loc = parse_HyperlinkString(blob, end - blob.l);\n\tif(flags & 0x0020) guid = blob.read_shift(16);\n\tif(flags & 0x0040) fileTime = parse_FILETIME(blob/*, 8*/);\n\tblob.l = end;\n\tvar target = targetFrameName||moniker||oleMoniker||\"\";\n\tif(target && Loc) target+=\"#\"+Loc;\n\tif(!target) target = \"#\" + Loc;\n\tif((flags & 0x0002) && target.charAt(0) == \"/\" && target.charAt(1) != \"/\") target = \"file://\" + target;\n\tvar out = ({Target:target}/*:any*/);\n\tif(guid) out.guid = guid;\n\tif(fileTime) out.time = fileTime;\n\tif(displayName) out.Tooltip = displayName;\n\treturn out;\n}\nfunction write_Hyperlink(hl) {\n\tvar out = new_buf(512), i = 0;\n\tvar Target = hl.Target;\n\tif(Target.slice(0,7) == \"file://\") Target = Target.slice(7);\n\tvar hashidx = Target.indexOf(\"#\");\n\tvar F = hashidx > -1 ? 0x1f : 0x17;\n\tswitch(Target.charAt(0)) { case \"#\": F=0x1c; break; case \".\": F&=~2; break; }\n\tout.write_shift(4,2); out.write_shift(4, F);\n\tvar data = [8,6815827,6619237,4849780,83]; for(i = 0; i < data.length; ++i) out.write_shift(4, data[i]);\n\tif(F == 0x1C) {\n\t\tTarget = Target.slice(1);\n\t\twrite_HyperlinkString(Target, out);\n\t} else if(F & 0x02) {\n\t\tdata = \"e0 c9 ea 79 f9 ba ce 11 8c 82 00 aa 00 4b a9 0b\".split(\" \");\n\t\tfor(i = 0; i < data.length; ++i) out.write_shift(1, parseInt(data[i], 16));\n\t\tvar Pretarget = hashidx > -1 ? Target.slice(0, hashidx) : Target;\n\t\tout.write_shift(4, 2*(Pretarget.length + 1));\n\t\tfor(i = 0; i < Pretarget.length; ++i) out.write_shift(2, Pretarget.charCodeAt(i));\n\t\tout.write_shift(2, 0);\n\t\tif(F & 0x08) write_HyperlinkString(hashidx > -1 ? Target.slice(hashidx+1): \"\", out);\n\t} else {\n\t\tdata = \"03 03 00 00 00 00 00 00 c0 00 00 00 00 00 00 46\".split(\" \");\n\t\tfor(i = 0; i < data.length; ++i) out.write_shift(1, parseInt(data[i], 16));\n\t\tvar P = 0;\n\t\twhile(Target.slice(P*3,P*3+3)==\"../\"||Target.slice(P*3,P*3+3)==\"..\\\\\") ++P;\n\t\tout.write_shift(2, P);\n\t\tout.write_shift(4, Target.length - 3 * P + 1);\n\t\tfor(i = 0; i < Target.length - 3 * P; ++i) out.write_shift(1, Target.charCodeAt(i + 3 * P) & 0xFF);\n\t\tout.write_shift(1, 0);\n\t\tout.write_shift(2, 0xFFFF);\n\t\tout.write_shift(2, 0xDEAD);\n\t\tfor(i = 0; i < 6; ++i) out.write_shift(4, 0);\n\t}\n\treturn out.slice(0, out.l);\n}\n\n/* 2.5.178 LongRGBA */\nfunction parse_LongRGBA(blob/*::, length*/) { var r = blob.read_shift(1), g = blob.read_shift(1), b = blob.read_shift(1), a = blob.read_shift(1); return [r,g,b,a]; }\n\n/* 2.5.177 LongRGB */\nfunction parse_LongRGB(blob, length) { var x = parse_LongRGBA(blob, length); x[3] = 0; return x; }\n\n\n/* [MS-XLS] 2.5.19 */\nfunction parse_XLSCell(blob/*::, length*/)/*:Cell*/ {\n\tvar rw = blob.read_shift(2); // 0-indexed\n\tvar col = blob.read_shift(2);\n\tvar ixfe = blob.read_shift(2);\n\treturn ({r:rw, c:col, ixfe:ixfe}/*:any*/);\n}\nfunction write_XLSCell(R/*:number*/, C/*:number*/, ixfe/*:?number*/, o) {\n\tif(!o) o = new_buf(6);\n\to.write_shift(2, R);\n\to.write_shift(2, C);\n\to.write_shift(2, ixfe||0);\n\treturn o;\n}\n\n/* [MS-XLS] 2.5.134 */\nfunction parse_frtHeader(blob) {\n\tvar rt = blob.read_shift(2);\n\tvar flags = blob.read_shift(2); // TODO: parse these flags\n\tblob.l += 8;\n\treturn {type: rt, flags: flags};\n}\n\n\n\nfunction parse_OptXLUnicodeString(blob, length, opts) { return length === 0 ? \"\" : parse_XLUnicodeString2(blob, length, opts); }\n\n/* [MS-XLS] 2.5.344 */\nfunction parse_XTI(blob, length, opts) {\n\tvar w = opts.biff > 8 ? 4 : 2;\n\tvar iSupBook = blob.read_shift(w), itabFirst = blob.read_shift(w,'i'), itabLast = blob.read_shift(w,'i');\n\treturn [iSupBook, itabFirst, itabLast];\n}\n\n/* [MS-XLS] 2.5.218 */\nfunction parse_RkRec(blob) {\n\tvar ixfe = blob.read_shift(2);\n\tvar RK = parse_RkNumber(blob);\n\treturn [ixfe, RK];\n}\n\n/* [MS-XLS] 2.5.1 */\nfunction parse_AddinUdf(blob, length, opts) {\n\tblob.l += 4; length -= 4;\n\tvar l = blob.l + length;\n\tvar udfName = parse_ShortXLUnicodeString(blob, length, opts);\n\tvar cb = blob.read_shift(2);\n\tl -= blob.l;\n\tif(cb !== l) throw new Error(\"Malformed AddinUdf: padding = \" + l + \" != \" + cb);\n\tblob.l += cb;\n\treturn udfName;\n}\n\n/* [MS-XLS] 2.5.209 TODO: Check sizes */\nfunction parse_Ref8U(blob/*::, length*/) {\n\tvar rwFirst = blob.read_shift(2);\n\tvar rwLast = blob.read_shift(2);\n\tvar colFirst = blob.read_shift(2);\n\tvar colLast = blob.read_shift(2);\n\treturn {s:{c:colFirst, r:rwFirst}, e:{c:colLast,r:rwLast}};\n}\nfunction write_Ref8U(r/*:Range*/, o) {\n\tif(!o) o = new_buf(8);\n\to.write_shift(2, r.s.r);\n\to.write_shift(2, r.e.r);\n\to.write_shift(2, r.s.c);\n\to.write_shift(2, r.e.c);\n\treturn o;\n}\n\n/* [MS-XLS] 2.5.211 */\nfunction parse_RefU(blob/*::, length*/) {\n\tvar rwFirst = blob.read_shift(2);\n\tvar rwLast = blob.read_shift(2);\n\tvar colFirst = blob.read_shift(1);\n\tvar colLast = blob.read_shift(1);\n\treturn {s:{c:colFirst, r:rwFirst}, e:{c:colLast,r:rwLast}};\n}\n\n/* [MS-XLS] 2.5.207 */\nvar parse_Ref = parse_RefU;\n\n/* [MS-XLS] 2.5.143 */\nfunction parse_FtCmo(blob/*::, length*/) {\n\tblob.l += 4;\n\tvar ot = blob.read_shift(2);\n\tvar id = blob.read_shift(2);\n\tvar flags = blob.read_shift(2);\n\tblob.l+=12;\n\treturn [id, ot, flags];\n}\n\n/* [MS-XLS] 2.5.149 */\nfunction parse_FtNts(blob) {\n\tvar out = {};\n\tblob.l += 4;\n\tblob.l += 16; // GUID TODO\n\tout.fSharedNote = blob.read_shift(2);\n\tblob.l += 4;\n\treturn out;\n}\n\n/* [MS-XLS] 2.5.142 */\nfunction parse_FtCf(blob) {\n\tvar out = {};\n\tblob.l += 4;\n\tblob.cf = blob.read_shift(2);\n\treturn out;\n}\n\n/* [MS-XLS] 2.5.140 - 2.5.154 and friends */\nfunction parse_FtSkip(blob) { blob.l += 2; blob.l += blob.read_shift(2); }\nvar FtTab = {\n\t/*::[*/0x00/*::]*/: parse_FtSkip,      /* FtEnd */\n\t/*::[*/0x04/*::]*/: parse_FtSkip,      /* FtMacro */\n\t/*::[*/0x05/*::]*/: parse_FtSkip,      /* FtButton */\n\t/*::[*/0x06/*::]*/: parse_FtSkip,      /* FtGmo */\n\t/*::[*/0x07/*::]*/: parse_FtCf,        /* FtCf */\n\t/*::[*/0x08/*::]*/: parse_FtSkip,      /* FtPioGrbit */\n\t/*::[*/0x09/*::]*/: parse_FtSkip,      /* FtPictFmla */\n\t/*::[*/0x0A/*::]*/: parse_FtSkip,      /* FtCbls */\n\t/*::[*/0x0B/*::]*/: parse_FtSkip,      /* FtRbo */\n\t/*::[*/0x0C/*::]*/: parse_FtSkip,      /* FtSbs */\n\t/*::[*/0x0D/*::]*/: parse_FtNts,       /* FtNts */\n\t/*::[*/0x0E/*::]*/: parse_FtSkip,      /* FtSbsFmla */\n\t/*::[*/0x0F/*::]*/: parse_FtSkip,      /* FtGboData */\n\t/*::[*/0x10/*::]*/: parse_FtSkip,      /* FtEdoData */\n\t/*::[*/0x11/*::]*/: parse_FtSkip,      /* FtRboData */\n\t/*::[*/0x12/*::]*/: parse_FtSkip,      /* FtCblsData */\n\t/*::[*/0x13/*::]*/: parse_FtSkip,      /* FtLbsData */\n\t/*::[*/0x14/*::]*/: parse_FtSkip,      /* FtCblsFmla */\n\t/*::[*/0x15/*::]*/: parse_FtCmo\n};\nfunction parse_FtArray(blob, length/*::, ot*/) {\n\tvar tgt = blob.l + length;\n\tvar fts = [];\n\twhile(blob.l < tgt) {\n\t\tvar ft = blob.read_shift(2);\n\t\tblob.l-=2;\n\t\ttry {\n\t\t\tfts.push(FtTab[ft](blob, tgt - blob.l));\n\t\t} catch(e) { blob.l = tgt; return fts; }\n\t}\n\tif(blob.l != tgt) blob.l = tgt; //throw new Error(\"bad Object Ft-sequence\");\n\treturn fts;\n}\n\n/* --- 2.4 Records --- */\n\n/* [MS-XLS] 2.4.21 */\nfunction parse_BOF(blob, length) {\n\tvar o = {BIFFVer:0, dt:0};\n\to.BIFFVer = blob.read_shift(2); length -= 2;\n\tif(length >= 2) { o.dt = blob.read_shift(2); blob.l -= 2; }\n\tswitch(o.BIFFVer) {\n\t\tcase 0x0600: /* BIFF8 */\n\t\tcase 0x0500: /* BIFF5 */\n\t\tcase 0x0400: /* BIFF4 */\n\t\tcase 0x0300: /* BIFF3 */\n\t\tcase 0x0200: /* BIFF2 */\n\t\tcase 0x0002: case 0x0007: /* BIFF2 */\n\t\t\tbreak;\n\t\tdefault: if(length > 6) throw new Error(\"Unexpected BIFF Ver \" + o.BIFFVer);\n\t}\n\n\tblob.read_shift(length);\n\treturn o;\n}\nfunction write_BOF(wb/*:Workbook*/, t/*:number*/, o) {\n\tvar h = 0x0600, w = 16;\n\tswitch(o.bookType) {\n\t\tcase 'biff8': break;\n\t\tcase 'biff5': h = 0x0500; w = 8; break;\n\t\tcase 'biff4': h = 0x0004; w = 6; break;\n\t\tcase 'biff3': h = 0x0003; w = 6; break;\n\t\tcase 'biff2': h = 0x0002; w = 4; break;\n\t\tcase 'xla': break;\n\t\tdefault: throw new Error(\"unsupported BIFF version\");\n\t}\n\tvar out = new_buf(w);\n\tout.write_shift(2, h);\n\tout.write_shift(2, t);\n\tif(w > 4) out.write_shift(2, 0x7262);\n\tif(w > 6) out.write_shift(2, 0x07CD);\n\tif(w > 8) {\n\t\tout.write_shift(2, 0xC009);\n\t\tout.write_shift(2, 0x0001);\n\t\tout.write_shift(2, 0x0706);\n\t\tout.write_shift(2, 0x0000);\n\t}\n\treturn out;\n}\n\n\n/* [MS-XLS] 2.4.146 */\nfunction parse_InterfaceHdr(blob, length) {\n\tif(length === 0) return 0x04b0;\n\tif((blob.read_shift(2))!==0x04b0){/* empty */}\n\treturn 0x04b0;\n}\n\n\n/* [MS-XLS] 2.4.349 */\nfunction parse_WriteAccess(blob, length, opts) {\n\tif(opts.enc) { blob.l += length; return \"\"; }\n\tvar l = blob.l;\n\t// TODO: make sure XLUnicodeString doesnt overrun\n\tvar UserName = parse_XLUnicodeString2(blob, 0, opts);\n\tblob.read_shift(length + l - blob.l);\n\treturn UserName;\n}\nfunction write_WriteAccess(s/*:string*/, opts) {\n\tvar b8 = !opts || opts.biff == 8;\n\tvar o = new_buf(b8 ? 112 : 54);\n\to.write_shift(opts.biff == 8 ? 2 : 1, 7);\n\tif(b8) o.write_shift(1, 0);\n\to.write_shift(4, 0x33336853);\n\to.write_shift(4, (0x00534A74 | (b8 ? 0 : 0x20000000)));\n\twhile(o.l < o.length) o.write_shift(1, (b8 ? 0 : 32));\n\treturn o;\n}\n\n/* [MS-XLS] 2.4.351 */\nfunction parse_WsBool(blob, length, opts) {\n\tvar flags = opts && opts.biff == 8 || length == 2 ? blob.read_shift(2) : (blob.l += length, 0);\n\treturn { fDialog: flags & 0x10, fBelow: flags & 0x40, fRight: flags & 0x80 };\n}\n\n/* [MS-XLS] 2.4.28 */\nfunction parse_BoundSheet8(blob, length, opts) {\n\tvar pos = blob.read_shift(4);\n\tvar hidden = blob.read_shift(1) & 0x03;\n\tvar dt = blob.read_shift(1);\n\tswitch(dt) {\n\t\tcase 0: dt = 'Worksheet'; break;\n\t\tcase 1: dt = 'Macrosheet'; break;\n\t\tcase 2: dt = 'Chartsheet'; break;\n\t\tcase 6: dt = 'VBAModule'; break;\n\t}\n\tvar name = parse_ShortXLUnicodeString(blob, 0, opts);\n\tif(name.length === 0) name = \"Sheet1\";\n\treturn { pos:pos, hs:hidden, dt:dt, name:name };\n}\nfunction write_BoundSheet8(data, opts) {\n\tvar w = (!opts || opts.biff >= 8 ? 2 : 1);\n\tvar o = new_buf(8 + w * data.name.length);\n\to.write_shift(4, data.pos);\n\to.write_shift(1, data.hs || 0);\n\to.write_shift(1, data.dt);\n\to.write_shift(1, data.name.length);\n\tif(opts.biff >= 8) o.write_shift(1, 1);\n\to.write_shift(w * data.name.length, data.name, opts.biff < 8 ? 'sbcs' : 'utf16le');\n\tvar out = o.slice(0, o.l);\n\tout.l = o.l; return out;\n}\n\n/* [MS-XLS] 2.4.265 TODO */\nfunction parse_SST(blob, length)/*:SST*/ {\n\tvar end = blob.l + length;\n\tvar cnt = blob.read_shift(4);\n\tvar ucnt = blob.read_shift(4);\n\tvar strs/*:SST*/ = ([]/*:any*/);\n\tfor(var i = 0; i != ucnt && blob.l < end; ++i) {\n\t\tstrs.push(parse_XLUnicodeRichExtendedString(blob));\n\t}\n\tstrs.Count = cnt; strs.Unique = ucnt;\n\treturn strs;\n}\nfunction write_SST(sst, opts) {\n\tvar header = new_buf(8);\n\theader.write_shift(4, sst.Count);\n\theader.write_shift(4, sst.Unique);\n\tvar strs = [];\n\tfor(var j = 0; j < sst.length; ++j) strs[j] = write_XLUnicodeRichExtendedString(sst[j], opts);\n\tvar o = bconcat([header].concat(strs));\n\t/*::(*/o/*:: :any)*/.parts = [header.length].concat(strs.map(function(str) { return str.length; }));\n\treturn o;\n}\n\n/* [MS-XLS] 2.4.107 */\nfunction parse_ExtSST(blob, length) {\n\tvar extsst = {};\n\textsst.dsst = blob.read_shift(2);\n\tblob.l += length-2;\n\treturn extsst;\n}\n\n\n/* [MS-XLS] 2.4.221 TODO: check BIFF2-4 */\nfunction parse_Row(blob) {\n\tvar z = ({}/*:any*/);\n\tz.r = blob.read_shift(2);\n\tz.c = blob.read_shift(2);\n\tz.cnt = blob.read_shift(2) - z.c;\n\tvar miyRw = blob.read_shift(2);\n\tblob.l += 4; // reserved(2), unused(2)\n\tvar flags = blob.read_shift(1); // various flags\n\tblob.l += 3; // reserved(8), ixfe(12), flags(4)\n\tif(flags & 0x07) z.level = flags & 0x07;\n\t// collapsed: flags & 0x10\n\tif(flags & 0x20) z.hidden = true;\n\tif(flags & 0x40) z.hpt = miyRw / 20;\n\treturn z;\n}\n\n\n/* [MS-XLS] 2.4.125 */\nfunction parse_ForceFullCalculation(blob) {\n\tvar header = parse_frtHeader(blob);\n\tif(header.type != 0x08A3) throw new Error(\"Invalid Future Record \" + header.type);\n\tvar fullcalc = blob.read_shift(4);\n\treturn fullcalc !== 0x0;\n}\n\n\n\n\n\n/* [MS-XLS] 2.4.215 rt */\nfunction parse_RecalcId(blob) {\n\tblob.read_shift(2);\n\treturn blob.read_shift(4);\n}\n\n/* [MS-XLS] 2.4.87 */\nfunction parse_DefaultRowHeight(blob, length, opts) {\n\tvar f = 0;\n\tif(!(opts && opts.biff == 2)) {\n\t\tf = blob.read_shift(2);\n\t}\n\tvar miyRw = blob.read_shift(2);\n\tif((opts && opts.biff == 2)) {\n\t\tf = 1 - (miyRw >> 15); miyRw &= 0x7fff;\n\t}\n\tvar fl = {Unsynced:f&1,DyZero:(f&2)>>1,ExAsc:(f&4)>>2,ExDsc:(f&8)>>3};\n\treturn [fl, miyRw];\n}\n\n/* [MS-XLS] 2.4.345 TODO */\nfunction parse_Window1(blob) {\n\tvar xWn = blob.read_shift(2), yWn = blob.read_shift(2), dxWn = blob.read_shift(2), dyWn = blob.read_shift(2);\n\tvar flags = blob.read_shift(2), iTabCur = blob.read_shift(2), iTabFirst = blob.read_shift(2);\n\tvar ctabSel = blob.read_shift(2), wTabRatio = blob.read_shift(2);\n\treturn { Pos: [xWn, yWn], Dim: [dxWn, dyWn], Flags: flags, CurTab: iTabCur,\n\t\tFirstTab: iTabFirst, Selected: ctabSel, TabRatio: wTabRatio };\n}\nfunction write_Window1(/*::opts*/) {\n\tvar o = new_buf(18);\n\to.write_shift(2, 0);\n\to.write_shift(2, 0);\n\to.write_shift(2, 0x7260);\n\to.write_shift(2, 0x44c0);\n\to.write_shift(2, 0x38);\n\to.write_shift(2, 0);\n\to.write_shift(2, 0);\n\to.write_shift(2, 1);\n\to.write_shift(2, 0x01f4);\n\treturn o;\n}\n/* [MS-XLS] 2.4.346 TODO */\nfunction parse_Window2(blob, length, opts) {\n\tif(opts && opts.biff >= 2 && opts.biff < 5) return {};\n\tvar f = blob.read_shift(2);\n\treturn { RTL: f & 0x40 };\n}\nfunction write_Window2(view) {\n\tvar o = new_buf(18), f = 0x6b6;\n\tif(view && view.RTL) f |= 0x40;\n\to.write_shift(2, f);\n\to.write_shift(4, 0);\n\to.write_shift(4, 64);\n\to.write_shift(4, 0);\n\to.write_shift(4, 0);\n\treturn o;\n}\n\n/* [MS-XLS] 2.4.189 TODO */\nfunction parse_Pane(/*blob, length, opts*/) {\n}\n\n/* [MS-XLS] 2.4.122 TODO */\nfunction parse_Font(blob, length, opts) {\n\tvar o/*:any*/ = {\n\t\tdyHeight: blob.read_shift(2),\n\t\tfl: blob.read_shift(2)\n\t};\n\tswitch((opts && opts.biff) || 8) {\n\t\tcase 2: break;\n\t\tcase 3: case 4: blob.l += 2; break;\n\t\tdefault: blob.l += 10; break;\n\t}\n\to.name = parse_ShortXLUnicodeString(blob, 0, opts);\n\treturn o;\n}\nfunction write_Font(data, opts) {\n\tvar name = data.name || \"Arial\";\n\tvar b5 = (opts && (opts.biff == 5)), w = (b5 ? (15 + name.length) : (16 + 2 * name.length));\n\tvar o = new_buf(w);\n\to.write_shift(2, (data.sz || 12) * 20);\n\to.write_shift(4, 0);\n\to.write_shift(2, 400);\n\to.write_shift(4, 0);\n\to.write_shift(2, 0);\n\to.write_shift(1, name.length);\n\tif(!b5) o.write_shift(1, 1);\n\to.write_shift((b5 ? 1 : 2) * name.length, name, (b5 ? \"sbcs\" : \"utf16le\"));\n\treturn o;\n}\n\n/* [MS-XLS] 2.4.149 */\nfunction parse_LabelSst(blob) {\n\tvar cell = parse_XLSCell(blob);\n\tcell.isst = blob.read_shift(4);\n\treturn cell;\n}\nfunction write_LabelSst(R/*:number*/, C/*:number*/, v/*:number*/, os/*:number*/ /*::, opts*/) {\n\tvar o = new_buf(10);\n\twrite_XLSCell(R, C, os, o);\n\to.write_shift(4, v);\n\treturn o;\n}\n\n/* [MS-XLS] 2.4.148 */\nfunction parse_Label(blob, length, opts) {\n\tif(opts.biffguess && opts.biff == 2) opts.biff = 5;\n\tvar target = blob.l + length;\n\tvar cell = parse_XLSCell(blob, 6);\n\tif(opts.biff == 2) blob.l++;\n\tvar str = parse_XLUnicodeString(blob, target - blob.l, opts);\n\tcell.val = str;\n\treturn cell;\n}\nfunction write_Label(R/*:number*/, C/*:number*/, v/*:string*/, os/*:number*/, opts) {\n\tvar b8 = !opts || opts.biff == 8;\n\tvar o = new_buf(6 + 2 + (+b8) + (1 + b8) * v.length);\n\twrite_XLSCell(R, C, os, o);\n\to.write_shift(2, v.length);\n\tif(b8) o.write_shift(1, 1);\n\to.write_shift((1 + b8) * v.length, v, b8 ? 'utf16le' : 'sbcs');\n\treturn o;\n}\n\n\n/* [MS-XLS] 2.4.126 Number Formats */\nfunction parse_Format(blob, length, opts) {\n\tvar numFmtId = blob.read_shift(2);\n\tvar fmtstr = parse_XLUnicodeString2(blob, 0, opts);\n\treturn [numFmtId, fmtstr];\n}\nfunction write_Format(i/*:number*/, f/*:string*/, opts, o) {\n\tvar b5 = (opts && (opts.biff == 5));\n\tif(!o) o = new_buf(b5 ? (3 + f.length) : (5 + 2 * f.length));\n\to.write_shift(2, i);\n\to.write_shift((b5 ? 1 : 2), f.length);\n\tif(!b5) o.write_shift(1, 1);\n\to.write_shift((b5 ? 1 : 2) * f.length, f, (b5 ? 'sbcs' : 'utf16le'));\n\tvar out = (o.length > o.l) ? o.slice(0, o.l) : o;\n\tif(out.l == null) out.l = out.length;\n\treturn out;\n}\nvar parse_BIFF2Format = parse_XLUnicodeString2;\n\n/* [MS-XLS] 2.4.90 */\nfunction parse_Dimensions(blob, length, opts) {\n\tvar end = blob.l + length;\n\tvar w = opts.biff == 8 || !opts.biff ? 4 : 2;\n\tvar r = blob.read_shift(w), R = blob.read_shift(w);\n\tvar c = blob.read_shift(2), C = blob.read_shift(2);\n\tblob.l = end;\n\treturn {s: {r:r, c:c}, e: {r:R, c:C}};\n}\nfunction write_Dimensions(range, opts) {\n\tvar w = opts.biff == 8 || !opts.biff ? 4 : 2;\n\tvar o = new_buf(2*w + 6);\n\to.write_shift(w, range.s.r);\n\to.write_shift(w, range.e.r + 1);\n\to.write_shift(2, range.s.c);\n\to.write_shift(2, range.e.c + 1);\n\to.write_shift(2, 0);\n\treturn o;\n}\n\n/* [MS-XLS] 2.4.220 */\nfunction parse_RK(blob) {\n\tvar rw = blob.read_shift(2), col = blob.read_shift(2);\n\tvar rkrec = parse_RkRec(blob);\n\treturn {r:rw, c:col, ixfe:rkrec[0], rknum:rkrec[1]};\n}\n\n/* [MS-XLS] 2.4.175 */\nfunction parse_MulRk(blob, length) {\n\tvar target = blob.l + length - 2;\n\tvar rw = blob.read_shift(2), col = blob.read_shift(2);\n\tvar rkrecs = [];\n\twhile(blob.l < target) rkrecs.push(parse_RkRec(blob));\n\tif(blob.l !== target) throw new Error(\"MulRK read error\");\n\tvar lastcol = blob.read_shift(2);\n\tif(rkrecs.length != lastcol - col + 1) throw new Error(\"MulRK length mismatch\");\n\treturn {r:rw, c:col, C:lastcol, rkrec:rkrecs};\n}\n/* [MS-XLS] 2.4.174 */\nfunction parse_MulBlank(blob, length) {\n\tvar target = blob.l + length - 2;\n\tvar rw = blob.read_shift(2), col = blob.read_shift(2);\n\tvar ixfes = [];\n\twhile(blob.l < target) ixfes.push(blob.read_shift(2));\n\tif(blob.l !== target) throw new Error(\"MulBlank read error\");\n\tvar lastcol = blob.read_shift(2);\n\tif(ixfes.length != lastcol - col + 1) throw new Error(\"MulBlank length mismatch\");\n\treturn {r:rw, c:col, C:lastcol, ixfe:ixfes};\n}\n\n/* [MS-XLS] 2.5.20 2.5.249 TODO: interpret values here */\nfunction parse_CellStyleXF(blob, length, style, opts) {\n\tvar o = {};\n\tvar a = blob.read_shift(4), b = blob.read_shift(4);\n\tvar c = blob.read_shift(4), d = blob.read_shift(2);\n\to.patternType = XLSFillPattern[c >> 26];\n\n\tif(!opts.cellStyles) return o;\n\to.alc = a & 0x07;\n\to.fWrap = (a >> 3) & 0x01;\n\to.alcV = (a >> 4) & 0x07;\n\to.fJustLast = (a >> 7) & 0x01;\n\to.trot = (a >> 8) & 0xFF;\n\to.cIndent = (a >> 16) & 0x0F;\n\to.fShrinkToFit = (a >> 20) & 0x01;\n\to.iReadOrder = (a >> 22) & 0x02;\n\to.fAtrNum = (a >> 26) & 0x01;\n\to.fAtrFnt = (a >> 27) & 0x01;\n\to.fAtrAlc = (a >> 28) & 0x01;\n\to.fAtrBdr = (a >> 29) & 0x01;\n\to.fAtrPat = (a >> 30) & 0x01;\n\to.fAtrProt = (a >> 31) & 0x01;\n\n\to.dgLeft = b & 0x0F;\n\to.dgRight = (b >> 4) & 0x0F;\n\to.dgTop = (b >> 8) & 0x0F;\n\to.dgBottom = (b >> 12) & 0x0F;\n\to.icvLeft = (b >> 16) & 0x7F;\n\to.icvRight = (b >> 23) & 0x7F;\n\to.grbitDiag = (b >> 30) & 0x03;\n\n\to.icvTop = c & 0x7F;\n\to.icvBottom = (c >> 7) & 0x7F;\n\to.icvDiag = (c >> 14) & 0x7F;\n\to.dgDiag = (c >> 21) & 0x0F;\n\n\to.icvFore = d & 0x7F;\n\to.icvBack = (d >> 7) & 0x7F;\n\to.fsxButton = (d >> 14) & 0x01;\n\treturn o;\n}\n//function parse_CellXF(blob, length, opts) {return parse_CellStyleXF(blob,length,0, opts);}\n//function parse_StyleXF(blob, length, opts) {return parse_CellStyleXF(blob,length,1, opts);}\n\n/* [MS-XLS] 2.4.353 TODO: actually do this right */\nfunction parse_XF(blob, length, opts) {\n\tvar o = {};\n\to.ifnt = blob.read_shift(2); o.numFmtId = blob.read_shift(2); o.flags = blob.read_shift(2);\n\to.fStyle = (o.flags >> 2) & 0x01;\n\tlength -= 6;\n\to.data = parse_CellStyleXF(blob, length, o.fStyle, opts);\n\treturn o;\n}\nfunction write_XF(data, ixfeP, opts, o) {\n\tvar b5 = (opts && (opts.biff == 5));\n\tif(!o) o = new_buf(b5 ? 16 : 20);\n\to.write_shift(2, 0);\n\tif(data.style) {\n\t\to.write_shift(2, (data.numFmtId||0));\n\t\to.write_shift(2, 0xFFF4);\n\t} else {\n\t\to.write_shift(2, (data.numFmtId||0));\n\t\to.write_shift(2, (ixfeP<<4));\n\t}\n\tvar f = 0;\n\tif(data.numFmtId > 0 && b5) f |= 0x0400;\n\to.write_shift(4, f);\n\to.write_shift(4, 0);\n\tif(!b5) o.write_shift(4, 0);\n\to.write_shift(2, 0);\n\treturn o;\n}\n\n/* [MS-XLS] 2.4.134 */\nfunction parse_Guts(blob) {\n\tblob.l += 4;\n\tvar out = [blob.read_shift(2), blob.read_shift(2)];\n\tif(out[0] !== 0) out[0]--;\n\tif(out[1] !== 0) out[1]--;\n\tif(out[0] > 7 || out[1] > 7) throw new Error(\"Bad Gutters: \" + out.join(\"|\"));\n\treturn out;\n}\nfunction write_Guts(guts/*:Array<number>*/) {\n\tvar o = new_buf(8);\n\to.write_shift(4, 0);\n\to.write_shift(2, guts[0] ? guts[0] + 1 : 0);\n\to.write_shift(2, guts[1] ? guts[1] + 1 : 0);\n\treturn o;\n}\n\n/* [MS-XLS] 2.4.24 */\nfunction parse_BoolErr(blob, length, opts) {\n\tvar cell = parse_XLSCell(blob, 6);\n\tif(opts.biff == 2 || length == 9) ++blob.l;\n\tvar val = parse_Bes(blob, 2);\n\tcell.val = val;\n\tcell.t = (val === true || val === false) ? 'b' : 'e';\n\treturn cell;\n}\nfunction write_BoolErr(R/*:number*/, C/*:number*/, v, os/*:number*/, opts, t/*:string*/) {\n\tvar o = new_buf(8);\n\twrite_XLSCell(R, C, os, o);\n\twrite_Bes(v, t, o);\n\treturn o;\n}\n\n/* [MS-XLS] 2.4.180 Number */\nfunction parse_Number(blob, length, opts) {\n\tif(opts.biffguess && opts.biff == 2) opts.biff = 5;\n\tvar cell = parse_XLSCell(blob, 6);\n\tvar xnum = parse_Xnum(blob, 8);\n\tcell.val = xnum;\n\treturn cell;\n}\nfunction write_Number(R/*:number*/, C/*:number*/, v, os/*:: :number, opts*/) {\n\tvar o = new_buf(14);\n\twrite_XLSCell(R, C, os, o);\n\twrite_Xnum(v, o);\n\treturn o;\n}\n\nvar parse_XLHeaderFooter = parse_OptXLUnicodeString; // TODO: parse 2.4.136\n\n/* [MS-XLS] 2.4.271 */\nfunction parse_SupBook(blob, length, opts) {\n\tvar end = blob.l + length;\n\tvar ctab = blob.read_shift(2);\n\tvar cch = blob.read_shift(2);\n\topts.sbcch = cch;\n\tif(cch == 0x0401 || cch == 0x3A01) return [cch, ctab];\n\tif(cch < 0x01 || cch >0xff) throw new Error(\"Unexpected SupBook type: \"+cch);\n\tvar virtPath = parse_XLUnicodeStringNoCch(blob, cch);\n\t/* TODO: 2.5.277 Virtual Path */\n\tvar rgst = [];\n\twhile(end > blob.l) rgst.push(parse_XLUnicodeString(blob));\n\treturn [cch, ctab, virtPath, rgst];\n}\n\n/* [MS-XLS] 2.4.105 TODO */\nfunction parse_ExternName(blob, length, opts) {\n\tvar flags = blob.read_shift(2);\n\tvar body;\n\tvar o = ({\n\t\tfBuiltIn: flags & 0x01,\n\t\tfWantAdvise: (flags >>> 1) & 0x01,\n\t\tfWantPict: (flags >>> 2) & 0x01,\n\t\tfOle: (flags >>> 3) & 0x01,\n\t\tfOleLink: (flags >>> 4) & 0x01,\n\t\tcf: (flags >>> 5) & 0x3FF,\n\t\tfIcon: flags >>> 15 & 0x01\n\t}/*:any*/);\n\tif(opts.sbcch === 0x3A01) body = parse_AddinUdf(blob, length-2, opts);\n\t//else throw new Error(\"unsupported SupBook cch: \" + opts.sbcch);\n\to.body = body || blob.read_shift(length-2);\n\tif(typeof body === \"string\") o.Name = body;\n\treturn o;\n}\n\n/* [MS-XLS] 2.4.150 TODO */\nvar XLSLblBuiltIn = [\n\t\"_xlnm.Consolidate_Area\",\n\t\"_xlnm.Auto_Open\",\n\t\"_xlnm.Auto_Close\",\n\t\"_xlnm.Extract\",\n\t\"_xlnm.Database\",\n\t\"_xlnm.Criteria\",\n\t\"_xlnm.Print_Area\",\n\t\"_xlnm.Print_Titles\",\n\t\"_xlnm.Recorder\",\n\t\"_xlnm.Data_Form\",\n\t\"_xlnm.Auto_Activate\",\n\t\"_xlnm.Auto_Deactivate\",\n\t\"_xlnm.Sheet_Title\",\n\t\"_xlnm._FilterDatabase\"\n];\nfunction parse_Lbl(blob, length, opts) {\n\tvar target = blob.l + length;\n\tvar flags = blob.read_shift(2);\n\tvar chKey = blob.read_shift(1);\n\tvar cch = blob.read_shift(1);\n\tvar cce = blob.read_shift(opts && opts.biff == 2 ? 1 : 2);\n\tvar itab = 0;\n\tif(!opts || opts.biff >= 5) {\n\t\tif(opts.biff != 5) blob.l += 2;\n\t\titab = blob.read_shift(2);\n\t\tif(opts.biff == 5) blob.l += 2;\n\t\tblob.l += 4;\n\t}\n\tvar name = parse_XLUnicodeStringNoCch(blob, cch, opts);\n\tif(flags & 0x20) name = XLSLblBuiltIn[name.charCodeAt(0)];\n\tvar npflen = target - blob.l; if(opts && opts.biff == 2) --npflen;\n\t/*jshint -W018 */\n\tvar rgce = (target == blob.l || cce === 0 || !(npflen > 0)) ? [] : parse_NameParsedFormula(blob, npflen, opts, cce);\n\t/*jshint +W018 */\n\treturn {\n\t\tchKey: chKey,\n\t\tName: name,\n\t\titab: itab,\n\t\trgce: rgce\n\t};\n}\n\n/* [MS-XLS] 2.4.106 TODO: verify filename encoding */\nfunction parse_ExternSheet(blob, length, opts) {\n\tif(opts.biff < 8) return parse_BIFF5ExternSheet(blob, length, opts);\n\tvar o = [], target = blob.l + length, len = blob.read_shift(opts.biff > 8 ? 4 : 2);\n\twhile(len-- !== 0) o.push(parse_XTI(blob, opts.biff > 8 ? 12 : 6, opts));\n\t\t// [iSupBook, itabFirst, itabLast];\n\tif(blob.l != target) throw new Error(\"Bad ExternSheet: \" + blob.l + \" != \" + target);\n\treturn o;\n}\nfunction parse_BIFF5ExternSheet(blob, length, opts) {\n\tif(blob[blob.l + 1] == 0x03) blob[blob.l]++;\n\tvar o = parse_ShortXLUnicodeString(blob, length, opts);\n\treturn o.charCodeAt(0) == 0x03 ? o.slice(1) : o;\n}\n\n/* [MS-XLS] 2.4.176 TODO: check older biff */\nfunction parse_NameCmt(blob, length, opts) {\n\tif(opts.biff < 8) { blob.l += length; return; }\n\tvar cchName = blob.read_shift(2);\n\tvar cchComment = blob.read_shift(2);\n\tvar name = parse_XLUnicodeStringNoCch(blob, cchName, opts);\n\tvar comment = parse_XLUnicodeStringNoCch(blob, cchComment, opts);\n\treturn [name, comment];\n}\n\n/* [MS-XLS] 2.4.260 */\nfunction parse_ShrFmla(blob, length, opts) {\n\tvar ref = parse_RefU(blob, 6);\n\tblob.l++;\n\tvar cUse = blob.read_shift(1);\n\tlength -= 8;\n\treturn [parse_SharedParsedFormula(blob, length, opts), cUse, ref];\n}\n\n/* [MS-XLS] 2.4.4 TODO */\nfunction parse_Array(blob, length, opts) {\n\tvar ref = parse_Ref(blob, 6);\n\t/* TODO: fAlwaysCalc */\n\tswitch(opts.biff) {\n\t\tcase 2: blob.l ++; length -= 7; break;\n\t\tcase 3: case 4: blob.l += 2; length -= 8; break;\n\t\tdefault: blob.l += 6; length -= 12;\n\t}\n\treturn [ref, parse_ArrayParsedFormula(blob, length, opts, ref)];\n}\n\n/* [MS-XLS] 2.4.173 */\nfunction parse_MTRSettings(blob) {\n\tvar fMTREnabled = blob.read_shift(4) !== 0x00;\n\tvar fUserSetThreadCount = blob.read_shift(4) !== 0x00;\n\tvar cUserThreadCount = blob.read_shift(4);\n\treturn [fMTREnabled, fUserSetThreadCount, cUserThreadCount];\n}\n\n/* [MS-XLS] 2.5.186 TODO: BIFF5 */\nfunction parse_NoteSh(blob, length, opts) {\n\tif(opts.biff < 8) return;\n\tvar row = blob.read_shift(2), col = blob.read_shift(2);\n\tvar flags = blob.read_shift(2), idObj = blob.read_shift(2);\n\tvar stAuthor = parse_XLUnicodeString2(blob, 0, opts);\n\tif(opts.biff < 8) blob.read_shift(1);\n\treturn [{r:row,c:col}, stAuthor, idObj, flags];\n}\n\n/* [MS-XLS] 2.4.179 */\nfunction parse_Note(blob, length, opts) {\n\t/* TODO: Support revisions */\n\treturn parse_NoteSh(blob, length, opts);\n}\n\n/* [MS-XLS] 2.4.168 */\nfunction parse_MergeCells(blob, length)/*:Array<Range>*/ {\n\tvar merges/*:Array<Range>*/ = [];\n\tvar cmcs = blob.read_shift(2);\n\twhile (cmcs--) merges.push(parse_Ref8U(blob,length));\n\treturn merges;\n}\nfunction write_MergeCells(merges/*:Array<Range>*/) {\n\tvar o = new_buf(2 + merges.length * 8);\n\to.write_shift(2, merges.length);\n\tfor(var i = 0; i < merges.length; ++i) write_Ref8U(merges[i], o);\n\treturn o;\n}\n\n/* [MS-XLS] 2.4.181 TODO: parse all the things! */\nfunction parse_Obj(blob, length, opts) {\n\tif(opts && opts.biff < 8) return parse_BIFF5Obj(blob, length, opts);\n\tvar cmo = parse_FtCmo(blob, 22); // id, ot, flags\n\tvar fts = parse_FtArray(blob, length-22, cmo[1]);\n\treturn { cmo: cmo, ft:fts };\n}\n/* from older spec */\nvar parse_BIFF5OT = {\n0x08: function(blob, length) {\n\tvar tgt = blob.l + length;\n\tblob.l += 10; // todo\n\tvar cf = blob.read_shift(2);\n\tblob.l += 4;\n\tblob.l += 2; //var cbPictFmla = blob.read_shift(2);\n\tblob.l += 2;\n\tblob.l += 2; //var grbit = blob.read_shift(2);\n\tblob.l += 4;\n\tvar cchName = blob.read_shift(1);\n\tblob.l += cchName; // TODO: stName\n\tblob.l = tgt; // TODO: fmla\n\treturn { fmt:cf };\n}\n};\n\nfunction parse_BIFF5Obj(blob, length, opts) {\n\tblob.l += 4; //var cnt = blob.read_shift(4);\n\tvar ot = blob.read_shift(2);\n\tvar id = blob.read_shift(2);\n\tvar grbit = blob.read_shift(2);\n\tblob.l += 2; //var colL = blob.read_shift(2);\n\tblob.l += 2; //var dxL = blob.read_shift(2);\n\tblob.l += 2; //var rwT = blob.read_shift(2);\n\tblob.l += 2; //var dyT = blob.read_shift(2);\n\tblob.l += 2; //var colR = blob.read_shift(2);\n\tblob.l += 2; //var dxR = blob.read_shift(2);\n\tblob.l += 2; //var rwB = blob.read_shift(2);\n\tblob.l += 2; //var dyB = blob.read_shift(2);\n\tblob.l += 2; //var cbMacro = blob.read_shift(2);\n\tblob.l += 6;\n\tlength -= 36;\n\tvar fts = [];\n\tfts.push((parse_BIFF5OT[ot]||parsenoop)(blob, length, opts));\n\treturn { cmo: [id, ot, grbit], ft:fts };\n}\n\n/* [MS-XLS] 2.4.329 TODO: parse properly */\nfunction parse_TxO(blob, length, opts) {\n\tvar s = blob.l;\n\tvar texts = \"\";\ntry {\n\tblob.l += 4;\n\tvar ot = (opts.lastobj||{cmo:[0,0]}).cmo[1];\n\tvar controlInfo; // eslint-disable-line no-unused-vars\n\tif([0,5,7,11,12,14].indexOf(ot) == -1) blob.l += 6;\n\telse controlInfo = parse_ControlInfo(blob, 6, opts); // eslint-disable-line no-unused-vars\n\tvar cchText = blob.read_shift(2);\n\t/*var cbRuns = */blob.read_shift(2);\n\t/*var ifntEmpty = */parseuint16(blob, 2);\n\tvar len = blob.read_shift(2);\n\tblob.l += len;\n\t//var fmla = parse_ObjFmla(blob, s + length - blob.l);\n\n\tfor(var i = 1; i < blob.lens.length-1; ++i) {\n\t\tif(blob.l-s != blob.lens[i]) throw new Error(\"TxO: bad continue record\");\n\t\tvar hdr = blob[blob.l];\n\t\tvar t = parse_XLUnicodeStringNoCch(blob, blob.lens[i+1]-blob.lens[i]-1);\n\t\ttexts += t;\n\t\tif(texts.length >= (hdr ? cchText : 2*cchText)) break;\n\t}\n\tif(texts.length !== cchText && texts.length !== cchText*2) {\n\t\tthrow new Error(\"cchText: \" + cchText + \" != \" + texts.length);\n\t}\n\n\tblob.l = s + length;\n\t/* [MS-XLS] 2.5.272 TxORuns */\n//\tvar rgTxoRuns = [];\n//\tfor(var j = 0; j != cbRuns/8-1; ++j) blob.l += 8;\n//\tvar cchText2 = blob.read_shift(2);\n//\tif(cchText2 !== cchText) throw new Error(\"TxOLastRun mismatch: \" + cchText2 + \" \" + cchText);\n//\tblob.l += 6;\n//\tif(s + length != blob.l) throw new Error(\"TxO \" + (s + length) + \", at \" + blob.l);\n\treturn { t: texts };\n} catch(e) { blob.l = s + length; return { t: texts }; }\n}\n\n/* [MS-XLS] 2.4.140 */\nfunction parse_HLink(blob, length) {\n\tvar ref = parse_Ref8U(blob, 8);\n\tblob.l += 16; /* CLSID */\n\tvar hlink = parse_Hyperlink(blob, length-24);\n\treturn [ref, hlink];\n}\nfunction write_HLink(hl) {\n\tvar O = new_buf(24);\n\tvar ref = decode_cell(hl[0]);\n\tO.write_shift(2, ref.r); O.write_shift(2, ref.r);\n\tO.write_shift(2, ref.c); O.write_shift(2, ref.c);\n\tvar clsid = \"d0 c9 ea 79 f9 ba ce 11 8c 82 00 aa 00 4b a9 0b\".split(\" \");\n\tfor(var i = 0; i < 16; ++i) O.write_shift(1, parseInt(clsid[i], 16));\n\treturn bconcat([O, write_Hyperlink(hl[1])]);\n}\n\n\n/* [MS-XLS] 2.4.141 */\nfunction parse_HLinkTooltip(blob, length) {\n\tblob.read_shift(2);\n\tvar ref = parse_Ref8U(blob, 8);\n\tvar wzTooltip = blob.read_shift((length-10)/2, 'dbcs-cont');\n\twzTooltip = wzTooltip.replace(chr0,\"\");\n\treturn [ref, wzTooltip];\n}\nfunction write_HLinkTooltip(hl) {\n\tvar TT = hl[1].Tooltip;\n\tvar O = new_buf(10 + 2 * (TT.length + 1));\n\tO.write_shift(2, 0x0800);\n\tvar ref = decode_cell(hl[0]);\n\tO.write_shift(2, ref.r); O.write_shift(2, ref.r);\n\tO.write_shift(2, ref.c); O.write_shift(2, ref.c);\n\tfor(var i = 0; i < TT.length; ++i) O.write_shift(2, TT.charCodeAt(i));\n\tO.write_shift(2, 0);\n\treturn O;\n}\n\n/* [MS-XLS] 2.4.63 */\nfunction parse_Country(blob)/*:[string|number, string|number]*/ {\n\tvar o = [0,0], d;\n\td = blob.read_shift(2); o[0] = CountryEnum[d] || d;\n\td = blob.read_shift(2); o[1] = CountryEnum[d] || d;\n\treturn o;\n}\nfunction write_Country(o) {\n\tif(!o) o = new_buf(4);\n\to.write_shift(2, 0x01);\n\to.write_shift(2, 0x01);\n\treturn o;\n}\n\n/* [MS-XLS] 2.4.50 ClrtClient */\nfunction parse_ClrtClient(blob) {\n\tvar ccv = blob.read_shift(2);\n\tvar o = [];\n\twhile(ccv-->0) o.push(parse_LongRGB(blob, 8));\n\treturn o;\n}\n\n/* [MS-XLS] 2.4.188 */\nfunction parse_Palette(blob) {\n\tvar ccv = blob.read_shift(2);\n\tvar o = [];\n\twhile(ccv-->0) o.push(parse_LongRGB(blob, 8));\n\treturn o;\n}\n\n/* [MS-XLS] 2.4.354 */\nfunction parse_XFCRC(blob) {\n\tblob.l += 2;\n\tvar o = {cxfs:0, crc:0};\n\to.cxfs = blob.read_shift(2);\n\to.crc = blob.read_shift(4);\n\treturn o;\n}\n\n/* [MS-XLS] 2.4.53 TODO: parse flags */\n/* [MS-XLSB] 2.4.323 TODO: parse flags */\nfunction parse_ColInfo(blob, length, opts) {\n\tif(!opts.cellStyles) return parsenoop(blob, length);\n\tvar w = opts && opts.biff >= 12 ? 4 : 2;\n\tvar colFirst = blob.read_shift(w);\n\tvar colLast = blob.read_shift(w);\n\tvar coldx = blob.read_shift(w);\n\tvar ixfe = blob.read_shift(w);\n\tvar flags = blob.read_shift(2);\n\tif(w == 2) blob.l += 2;\n\tvar o = ({s:colFirst, e:colLast, w:coldx, ixfe:ixfe, flags:flags}/*:any*/);\n\tif(opts.biff >= 5 || !opts.biff) o.level = (flags >> 8) & 0x7;\n\treturn o;\n}\nfunction write_ColInfo(col, idx) {\n\tvar o = new_buf(12);\n\to.write_shift(2, idx);\n\to.write_shift(2, idx);\n\to.write_shift(2, col.width * 256);\n\to.write_shift(2, 0);\n\tvar f = 0;\n\tif(col.hidden) f |= 1;\n\to.write_shift(1, f);\n\tf = col.level || 0;\n\to.write_shift(1, f);\n\to.write_shift(2, 0);\n\treturn o;\n}\n\n/* [MS-XLS] 2.4.257 */\nfunction parse_Setup(blob, length) {\n\tvar o = {};\n\tif(length < 32) return o;\n\tblob.l += 16;\n\to.header = parse_Xnum(blob, 8);\n\to.footer = parse_Xnum(blob, 8);\n\tblob.l += 2;\n\treturn o;\n}\n\n/* [MS-XLS] 2.4.261 */\nfunction parse_ShtProps(blob, length, opts) {\n\tvar def = {area:false};\n\tif(opts.biff != 5) { blob.l += length; return def; }\n\tvar d = blob.read_shift(1); blob.l += 3;\n\tif((d & 0x10)) def.area = true;\n\treturn def;\n}\n\n/* [MS-XLS] 2.4.241 */\nfunction write_RRTabId(n/*:number*/) {\n\tvar out = new_buf(2 * n);\n\tfor(var i = 0; i < n; ++i) out.write_shift(2, i+1);\n\treturn out;\n}\n\nvar parse_Blank = parse_XLSCell; /* [MS-XLS] 2.4.20 Just the cell */\nvar parse_Scl = parseuint16a; /* [MS-XLS] 2.4.247 num, den */\nvar parse_String = parse_XLUnicodeString; /* [MS-XLS] 2.4.268 */\n\n/* --- Specific to versions before BIFF8 --- */\nfunction parse_ImData(blob) {\n\tvar cf = blob.read_shift(2);\n\tvar env = blob.read_shift(2);\n\tvar lcb = blob.read_shift(4);\n\tvar o = {fmt:cf, env:env, len:lcb, data:blob.slice(blob.l,blob.l+lcb)};\n\tblob.l += lcb;\n\treturn o;\n}\n\n/* BIFF2_??? where ??? is the name from [XLS] */\nfunction parse_BIFF2STR(blob, length, opts) {\n\tif(opts.biffguess && opts.biff == 5) opts.biff = 2;\n\tvar cell = parse_XLSCell(blob, 6);\n\t++blob.l;\n\tvar str = parse_XLUnicodeString2(blob, length-7, opts);\n\tcell.t = 'str';\n\tcell.val = str;\n\treturn cell;\n}\n\nfunction parse_BIFF2NUM(blob/*::, length*/) {\n\tvar cell = parse_XLSCell(blob, 6);\n\t++blob.l;\n\tvar num = parse_Xnum(blob, 8);\n\tcell.t = 'n';\n\tcell.val = num;\n\treturn cell;\n}\nfunction write_BIFF2NUM(r/*:number*/, c/*:number*/, val/*:number*/) {\n\tvar out = new_buf(15);\n\twrite_BIFF2Cell(out, r, c);\n\tout.write_shift(8, val, 'f');\n\treturn out;\n}\n\nfunction parse_BIFF2INT(blob) {\n\tvar cell = parse_XLSCell(blob, 6);\n\t++blob.l;\n\tvar num = blob.read_shift(2);\n\tcell.t = 'n';\n\tcell.val = num;\n\treturn cell;\n}\nfunction write_BIFF2INT(r/*:number*/, c/*:number*/, val/*:number*/) {\n\tvar out = new_buf(9);\n\twrite_BIFF2Cell(out, r, c);\n\tout.write_shift(2, val);\n\treturn out;\n}\n\nfunction parse_BIFF2STRING(blob) {\n\tvar cch = blob.read_shift(1);\n\tif(cch === 0) { blob.l++; return \"\"; }\n\treturn blob.read_shift(cch, 'sbcs-cont');\n}\n\n/* TODO: convert to BIFF8 font struct */\nfunction parse_BIFF2FONTXTRA(blob, length) {\n\tblob.l += 6; // unknown\n\tblob.l += 2; // font weight \"bls\"\n\tblob.l += 1; // charset\n\tblob.l += 3; // unknown\n\tblob.l += 1; // font family\n\tblob.l += length - 13;\n}\n\n/* TODO: parse rich text runs */\nfunction parse_RString(blob, length, opts) {\n\tvar end = blob.l + length;\n\tvar cell = parse_XLSCell(blob, 6);\n\tvar cch = blob.read_shift(2);\n\tvar str = parse_XLUnicodeStringNoCch(blob, cch, opts);\n\tblob.l = end;\n\tcell.t = 'str';\n\tcell.val = str;\n\treturn cell;\n}\n/* from js-harb (C) 2014-present  SheetJS */\nvar DBF_SUPPORTED_VERSIONS = [0x02, 0x03, 0x30, 0x31, 0x83, 0x8B, 0x8C, 0xF5];\nvar DBF = /*#__PURE__*/(function() {\nvar dbf_codepage_map = {\n\t/* Code Pages Supported by Visual FoxPro */\n\t/*::[*/0x01/*::]*/:   437,           /*::[*/0x02/*::]*/:   850,\n\t/*::[*/0x03/*::]*/:  1252,           /*::[*/0x04/*::]*/: 10000,\n\t/*::[*/0x64/*::]*/:   852,           /*::[*/0x65/*::]*/:   866,\n\t/*::[*/0x66/*::]*/:   865,           /*::[*/0x67/*::]*/:   861,\n\t/*::[*/0x68/*::]*/:   895,           /*::[*/0x69/*::]*/:   620,\n\t/*::[*/0x6A/*::]*/:   737,           /*::[*/0x6B/*::]*/:   857,\n\t/*::[*/0x78/*::]*/:   950,           /*::[*/0x79/*::]*/:   949,\n\t/*::[*/0x7A/*::]*/:   936,           /*::[*/0x7B/*::]*/:   932,\n\t/*::[*/0x7C/*::]*/:   874,           /*::[*/0x7D/*::]*/:  1255,\n\t/*::[*/0x7E/*::]*/:  1256,           /*::[*/0x96/*::]*/: 10007,\n\t/*::[*/0x97/*::]*/: 10029,           /*::[*/0x98/*::]*/: 10006,\n\t/*::[*/0xC8/*::]*/:  1250,           /*::[*/0xC9/*::]*/:  1251,\n\t/*::[*/0xCA/*::]*/:  1254,           /*::[*/0xCB/*::]*/:  1253,\n\n\t/* shapefile DBF extension */\n\t/*::[*/0x00/*::]*/: 20127,           /*::[*/0x08/*::]*/:   865,\n\t/*::[*/0x09/*::]*/:   437,           /*::[*/0x0A/*::]*/:   850,\n\t/*::[*/0x0B/*::]*/:   437,           /*::[*/0x0D/*::]*/:   437,\n\t/*::[*/0x0E/*::]*/:   850,           /*::[*/0x0F/*::]*/:   437,\n\t/*::[*/0x10/*::]*/:   850,           /*::[*/0x11/*::]*/:   437,\n\t/*::[*/0x12/*::]*/:   850,           /*::[*/0x13/*::]*/:   932,\n\t/*::[*/0x14/*::]*/:   850,           /*::[*/0x15/*::]*/:   437,\n\t/*::[*/0x16/*::]*/:   850,           /*::[*/0x17/*::]*/:   865,\n\t/*::[*/0x18/*::]*/:   437,           /*::[*/0x19/*::]*/:   437,\n\t/*::[*/0x1A/*::]*/:   850,           /*::[*/0x1B/*::]*/:   437,\n\t/*::[*/0x1C/*::]*/:   863,           /*::[*/0x1D/*::]*/:   850,\n\t/*::[*/0x1F/*::]*/:   852,           /*::[*/0x22/*::]*/:   852,\n\t/*::[*/0x23/*::]*/:   852,           /*::[*/0x24/*::]*/:   860,\n\t/*::[*/0x25/*::]*/:   850,           /*::[*/0x26/*::]*/:   866,\n\t/*::[*/0x37/*::]*/:   850,           /*::[*/0x40/*::]*/:   852,\n\t/*::[*/0x4D/*::]*/:   936,           /*::[*/0x4E/*::]*/:   949,\n\t/*::[*/0x4F/*::]*/:   950,           /*::[*/0x50/*::]*/:   874,\n\t/*::[*/0x57/*::]*/:  1252,           /*::[*/0x58/*::]*/:  1252,\n\t/*::[*/0x59/*::]*/:  1252,           /*::[*/0x6C/*::]*/:   863,\n\t/*::[*/0x86/*::]*/:   737,           /*::[*/0x87/*::]*/:   852,\n\t/*::[*/0x88/*::]*/:   857,           /*::[*/0xCC/*::]*/:  1257,\n\n\t/*::[*/0xFF/*::]*/: 16969\n};\nvar dbf_reverse_map = evert({\n\t/*::[*/0x01/*::]*/:   437,           /*::[*/0x02/*::]*/:   850,\n\t/*::[*/0x03/*::]*/:  1252,           /*::[*/0x04/*::]*/: 10000,\n\t/*::[*/0x64/*::]*/:   852,           /*::[*/0x65/*::]*/:   866,\n\t/*::[*/0x66/*::]*/:   865,           /*::[*/0x67/*::]*/:   861,\n\t/*::[*/0x68/*::]*/:   895,           /*::[*/0x69/*::]*/:   620,\n\t/*::[*/0x6A/*::]*/:   737,           /*::[*/0x6B/*::]*/:   857,\n\t/*::[*/0x78/*::]*/:   950,           /*::[*/0x79/*::]*/:   949,\n\t/*::[*/0x7A/*::]*/:   936,           /*::[*/0x7B/*::]*/:   932,\n\t/*::[*/0x7C/*::]*/:   874,           /*::[*/0x7D/*::]*/:  1255,\n\t/*::[*/0x7E/*::]*/:  1256,           /*::[*/0x96/*::]*/: 10007,\n\t/*::[*/0x97/*::]*/: 10029,           /*::[*/0x98/*::]*/: 10006,\n\t/*::[*/0xC8/*::]*/:  1250,           /*::[*/0xC9/*::]*/:  1251,\n\t/*::[*/0xCA/*::]*/:  1254,           /*::[*/0xCB/*::]*/:  1253,\n\t/*::[*/0x00/*::]*/: 20127\n});\n/* TODO: find an actual specification */\nfunction dbf_to_aoa(buf, opts)/*:AOA*/ {\n\tvar out/*:AOA*/ = [];\n\tvar d/*:Block*/ = (new_raw_buf(1)/*:any*/);\n\tswitch(opts.type) {\n\t\tcase 'base64': d = s2a(Base64_decode(buf)); break;\n\t\tcase 'binary': d = s2a(buf); break;\n\t\tcase 'buffer':\n\t\tcase 'array': d = buf; break;\n\t}\n\tprep_blob(d, 0);\n\n\t/* header */\n\tvar ft = d.read_shift(1);\n\tvar memo = !!(ft & 0x88);\n\tvar vfp = false, l7 = false;\n\tswitch(ft) {\n\t\tcase 0x02: break; // dBASE II\n\t\tcase 0x03: break; // dBASE III\n\t\tcase 0x30: vfp = true; memo = true; break; // VFP\n\t\tcase 0x31: vfp = true; memo = true; break; // VFP with autoincrement\n\t\t// 0x43 dBASE IV SQL table files\n\t\t// 0x63 dBASE IV SQL system files\n\t\tcase 0x83: break; // dBASE III with memo\n\t\tcase 0x8B: break; // dBASE IV with memo\n\t\tcase 0x8C: l7 = true; break; // dBASE Level 7 with memo\n\t\t// case 0xCB dBASE IV SQL table files with memo\n\t\tcase 0xF5: break; // FoxPro 2.x with memo\n\t\t// case 0xFB FoxBASE\n\t\tdefault: throw new Error(\"DBF Unsupported Version: \" + ft.toString(16));\n\t}\n\n\tvar nrow = 0, fpos = 0x0209;\n\tif(ft == 0x02) nrow = d.read_shift(2);\n\td.l += 3; // dBASE II stores DDMMYY date, others use YYMMDD\n\tif(ft != 0x02) nrow = d.read_shift(4);\n\tif(nrow > 1048576) nrow = 1e6;\n\n\tif(ft != 0x02) fpos = d.read_shift(2); // header length\n\tvar rlen = d.read_shift(2); // record length\n\n\tvar /*flags = 0,*/ current_cp = opts.codepage || 1252;\n\tif(ft != 0x02) { // 20 reserved bytes\n\t\td.l+=16;\n\t\t/*flags = */d.read_shift(1);\n\t\t//if(memo && ((flags & 0x02) === 0)) throw new Error(\"DBF Flags \" + flags.toString(16) + \" ft \" + ft.toString(16));\n\n\t\t/* codepage present in FoxPro and dBASE Level 7 */\n\t\tif(d[d.l] !== 0) current_cp = dbf_codepage_map[d[d.l]];\n\t\td.l+=1;\n\n\t\td.l+=2;\n\t}\n\tif(l7) d.l += 36; // Level 7: 32 byte \"Language driver name\", 4 byte reserved\n\n/*:: type DBFField = { name:string; len:number; type:string; } */\n\tvar fields/*:Array<DBFField>*/ = [], field/*:DBFField*/ = ({}/*:any*/);\n\tvar hend = Math.min(d.length, (ft == 0x02 ? 0x209 : (fpos - 10 - (vfp ? 264 : 0))));\n\tvar ww = l7 ? 32 : 11;\n\twhile(d.l < hend && d[d.l] != 0x0d) {\n\t\tfield = ({}/*:any*/);\n\t\tfield.name = $cptable.utils.decode(current_cp, d.slice(d.l, d.l+ww)).replace(/[\\u0000\\r\\n].*$/g,\"\");\n\t\td.l += ww;\n\t\tfield.type = String.fromCharCode(d.read_shift(1));\n\t\tif(ft != 0x02 && !l7) field.offset = d.read_shift(4);\n\t\tfield.len = d.read_shift(1);\n\t\tif(ft == 0x02) field.offset = d.read_shift(2);\n\t\tfield.dec = d.read_shift(1);\n\t\tif(field.name.length) fields.push(field);\n\t\tif(ft != 0x02) d.l += l7 ? 13 : 14;\n\t\tswitch(field.type) {\n\t\t\tcase 'B': // Double (VFP) / Binary (dBASE L7)\n\t\t\t\tif((!vfp || field.len != 8) && opts.WTF) console.log('Skipping ' + field.name + ':' + field.type);\n\t\t\t\tbreak;\n\t\t\tcase 'G': // General (FoxPro and dBASE L7)\n\t\t\tcase 'P': // Picture (FoxPro and dBASE L7)\n\t\t\t\tif(opts.WTF) console.log('Skipping ' + field.name + ':' + field.type);\n\t\t\t\tbreak;\n\t\t\tcase '+': // Autoincrement (dBASE L7 only)\n\t\t\tcase '0': // _NullFlags (VFP only)\n\t\t\tcase '@': // Timestamp (dBASE L7 only)\n\t\t\tcase 'C': // Character (dBASE II)\n\t\t\tcase 'D': // Date (dBASE III)\n\t\t\tcase 'F': // Float (dBASE IV)\n\t\t\tcase 'I': // Long (VFP and dBASE L7)\n\t\t\tcase 'L': // Logical (dBASE II)\n\t\t\tcase 'M': // Memo (dBASE III)\n\t\t\tcase 'N': // Number (dBASE II)\n\t\t\tcase 'O': // Double (dBASE L7 only)\n\t\t\tcase 'T': // Datetime (VFP only)\n\t\t\tcase 'Y': // Currency (VFP only)\n\t\t\t\tbreak;\n\t\t\tdefault: throw new Error('Unknown Field Type: ' + field.type);\n\t\t}\n\t}\n\n\tif(d[d.l] !== 0x0D) d.l = fpos-1;\n\tif(d.read_shift(1) !== 0x0D) throw new Error(\"DBF Terminator not found \" + d.l + \" \" + d[d.l]);\n\td.l = fpos;\n\n\t/* data */\n\tvar R = 0, C = 0;\n\tout[0] = [];\n\tfor(C = 0; C != fields.length; ++C) out[0][C] = fields[C].name;\n\twhile(nrow-- > 0) {\n\t\tif(d[d.l] === 0x2A) {\n\t\t\t// TODO: record marked as deleted -- create a hidden row?\n\t\t\td.l+=rlen;\n\t\t\tcontinue;\n\t\t}\n\t\t++d.l;\n\t\tout[++R] = []; C = 0;\n\t\tfor(C = 0; C != fields.length; ++C) {\n\t\t\tvar dd = d.slice(d.l, d.l+fields[C].len); d.l+=fields[C].len;\n\t\t\tprep_blob(dd, 0);\n\t\t\tvar s = $cptable.utils.decode(current_cp, dd);\n\t\t\tswitch(fields[C].type) {\n\t\t\t\tcase 'C':\n\t\t\t\t\t// NOTE: it is conventional to write '  /  /  ' for empty dates\n\t\t\t\t\tif(s.trim().length) out[R][C] = s.replace(/\\s+$/,\"\");\n\t\t\t\t\tbreak;\n\t\t\t\tcase 'D':\n\t\t\t\t\tif(s.length === 8) out[R][C] = new Date(+s.slice(0,4), +s.slice(4,6)-1, +s.slice(6,8));\n\t\t\t\t\telse out[R][C] = s;\n\t\t\t\t\tbreak;\n\t\t\t\tcase 'F': out[R][C] = parseFloat(s.trim()); break;\n\t\t\t\tcase '+': case 'I': out[R][C] = l7 ? dd.read_shift(-4, 'i') ^ 0x80000000 : dd.read_shift(4, 'i'); break;\n\t\t\t\tcase 'L': switch(s.trim().toUpperCase()) {\n\t\t\t\t\tcase 'Y': case 'T': out[R][C] = true; break;\n\t\t\t\t\tcase 'N': case 'F': out[R][C] = false; break;\n\t\t\t\t\tcase '': case '?': break;\n\t\t\t\t\tdefault: throw new Error(\"DBF Unrecognized L:|\" + s + \"|\");\n\t\t\t\t\t} break;\n\t\t\t\tcase 'M': /* TODO: handle memo files */\n\t\t\t\t\tif(!memo) throw new Error(\"DBF Unexpected MEMO for type \" + ft.toString(16));\n\t\t\t\t\tout[R][C] = \"##MEMO##\" + (l7 ? parseInt(s.trim(), 10): dd.read_shift(4));\n\t\t\t\t\tbreak;\n\t\t\t\tcase 'N':\n\t\t\t\t\ts = s.replace(/\\u0000/g,\"\").trim();\n\t\t\t\t\t// NOTE: dBASE II interprets \"  .  \" as 0\n\t\t\t\t\tif(s && s != \".\") out[R][C] = +s || 0; break;\n\t\t\t\tcase '@':\n\t\t\t\t\t// NOTE: dBASE specs appear to be incorrect\n\t\t\t\t\tout[R][C] = new Date(dd.read_shift(-8, 'f') - 0x388317533400);\n\t\t\t\t\tbreak;\n\t\t\t\tcase 'T': out[R][C] = new Date((dd.read_shift(4) - 0x253D8C) * 0x5265C00 + dd.read_shift(4)); break;\n\t\t\t\tcase 'Y': out[R][C] = dd.read_shift(4,'i')/1e4 + (dd.read_shift(4, 'i')/1e4)*Math.pow(2,32); break;\n\t\t\t\tcase 'O': out[R][C] = -dd.read_shift(-8, 'f'); break;\n\t\t\t\tcase 'B': if(vfp && fields[C].len == 8) { out[R][C] = dd.read_shift(8,'f'); break; }\n\t\t\t\t\t/* falls through */\n\t\t\t\tcase 'G': case 'P': dd.l += fields[C].len; break;\n\t\t\t\tcase '0':\n\t\t\t\t\tif(fields[C].name === '_NullFlags') break;\n\t\t\t\t\t/* falls through */\n\t\t\t\tdefault: throw new Error(\"DBF Unsupported data type \" + fields[C].type);\n\t\t\t}\n\t\t}\n\t}\n\tif(ft != 0x02) if(d.l < d.length && d[d.l++] != 0x1A) throw new Error(\"DBF EOF Marker missing \" + (d.l-1) + \" of \" + d.length + \" \" + d[d.l-1].toString(16));\n\tif(opts && opts.sheetRows) out = out.slice(0, opts.sheetRows);\n\topts.DBF = fields;\n\treturn out;\n}\n\nfunction dbf_to_sheet(buf, opts)/*:Worksheet*/ {\n\tvar o = opts || {};\n\tif(!o.dateNF) o.dateNF = \"yyyymmdd\";\n\tvar ws = aoa_to_sheet(dbf_to_aoa(buf, o), o);\n\tws[\"!cols\"] = o.DBF.map(function(field) { return {\n\t\twch: field.len,\n\t\tDBF: field\n\t};});\n\tdelete o.DBF;\n\treturn ws;\n}\n\nfunction dbf_to_workbook(buf, opts)/*:Workbook*/ {\n\ttry { return sheet_to_workbook(dbf_to_sheet(buf, opts), opts); }\n\tcatch(e) { if(opts && opts.WTF) throw e; }\n\treturn ({SheetNames:[],Sheets:{}});\n}\n\nvar _RLEN = { 'B': 8, 'C': 250, 'L': 1, 'D': 8, '?': 0, '': 0 };\nfunction sheet_to_dbf(ws/*:Worksheet*/, opts/*:WriteOpts*/) {\n\tvar o = opts || {};\n\tif(+o.codepage >= 0) set_cp(+o.codepage);\n\tif(o.type == \"string\") throw new Error(\"Cannot write DBF to JS string\");\n\tvar ba = buf_array();\n\tvar aoa/*:AOA*/ = sheet_to_json(ws, {header:1, raw:true, cellDates:true});\n\tvar headers = aoa[0], data = aoa.slice(1), cols = ws[\"!cols\"] || [];\n\tvar i = 0, j = 0, hcnt = 0, rlen = 1;\n\tfor(i = 0; i < headers.length; ++i) {\n\t\tif(((cols[i]||{}).DBF||{}).name) { headers[i] = cols[i].DBF.name; ++hcnt; continue; }\n\t\tif(headers[i] == null) continue;\n\t\t++hcnt;\n\t\tif(typeof headers[i] === 'number') headers[i] = headers[i].toString(10);\n\t\tif(typeof headers[i] !== 'string') throw new Error(\"DBF Invalid column name \" + headers[i] + \" |\" + (typeof headers[i]) + \"|\");\n\t\tif(headers.indexOf(headers[i]) !== i) for(j=0; j<1024;++j)\n\t\t\tif(headers.indexOf(headers[i] + \"_\" + j) == -1) { headers[i] += \"_\" + j; break; }\n\t}\n\tvar range = safe_decode_range(ws['!ref']);\n\tvar coltypes/*:Array<string>*/ = [];\n\tvar colwidths/*:Array<number>*/ = [];\n\tvar coldecimals/*:Array<number>*/ = [];\n\tfor(i = 0; i <= range.e.c - range.s.c; ++i) {\n\t\tvar guess = '', _guess = '', maxlen = 0;\n\t\tvar col/*:Array<any>*/ = [];\n\t\tfor(j=0; j < data.length; ++j) {\n\t\t\tif(data[j][i] != null) col.push(data[j][i]);\n\t\t}\n\t\tif(col.length == 0 || headers[i] == null) { coltypes[i] = '?'; continue; }\n\t\tfor(j = 0; j < col.length; ++j) {\n\t\t\tswitch(typeof col[j]) {\n\t\t\t\t/* TODO: check if L2 compat is desired */\n\t\t\t\tcase 'number': _guess = 'B'; break;\n\t\t\t\tcase 'string': _guess = 'C'; break;\n\t\t\t\tcase 'boolean': _guess = 'L'; break;\n\t\t\t\tcase 'object': _guess = col[j] instanceof Date ? 'D' : 'C'; break;\n\t\t\t\tdefault: _guess = 'C';\n\t\t\t}\n\t\t\tmaxlen = Math.max(maxlen, String(col[j]).length);\n\t\t\tguess = guess && guess != _guess ? 'C' : _guess;\n\t\t\t//if(guess == 'C') break;\n\t\t}\n\t\tif(maxlen > 250) maxlen = 250;\n\t\t_guess = ((cols[i]||{}).DBF||{}).type;\n\t\t/* TODO: more fine grained control over DBF type resolution */\n\t\tif(_guess == 'C') {\n\t\t\tif(cols[i].DBF.len > maxlen) maxlen = cols[i].DBF.len;\n\t\t}\n\t\tif(guess == 'B' && _guess == 'N') {\n\t\t\tguess = 'N';\n\t\t\tcoldecimals[i] = cols[i].DBF.dec;\n\t\t\tmaxlen = cols[i].DBF.len;\n\t\t}\n\t\tcolwidths[i] = guess == 'C' || _guess == 'N' ? maxlen : (_RLEN[guess] || 0);\n\t\trlen += colwidths[i];\n\t\tcoltypes[i] = guess;\n\t}\n\n\tvar h = ba.next(32);\n\th.write_shift(4, 0x13021130);\n\th.write_shift(4, data.length);\n\th.write_shift(2, 296 + 32 * hcnt);\n\th.write_shift(2, rlen);\n\tfor(i=0; i < 4; ++i) h.write_shift(4, 0);\n\th.write_shift(4, 0x00000000 | ((+dbf_reverse_map[/*::String(*/current_ansi/*::)*/] || 0x03)<<8));\n\n\tfor(i = 0, j = 0; i < headers.length; ++i) {\n\t\tif(headers[i] == null) continue;\n\t\tvar hf = ba.next(32);\n\t\tvar _f = (headers[i].slice(-10) + \"\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00\\x00\").slice(0, 11);\n\t\thf.write_shift(1, _f, \"sbcs\");\n\t\thf.write_shift(1, coltypes[i] == '?' ? 'C' : coltypes[i], \"sbcs\");\n\t\thf.write_shift(4, j);\n\t\thf.write_shift(1, colwidths[i] || _RLEN[coltypes[i]] || 0);\n\t\thf.write_shift(1, coldecimals[i] || 0);\n\t\thf.write_shift(1, 0x02);\n\t\thf.write_shift(4, 0);\n\t\thf.write_shift(1, 0);\n\t\thf.write_shift(4, 0);\n\t\thf.write_shift(4, 0);\n\t\tj += (colwidths[i] || _RLEN[coltypes[i]] || 0);\n\t}\n\n\tvar hb = ba.next(264);\n\thb.write_shift(4, 0x0000000D);\n\tfor(i=0; i < 65;++i) hb.write_shift(4, 0x00000000);\n\tfor(i=0; i < data.length; ++i) {\n\t\tvar rout = ba.next(rlen);\n\t\trout.write_shift(1, 0);\n\t\tfor(j=0; j<headers.length; ++j) {\n\t\t\tif(headers[j] == null) continue;\n\t\t\tswitch(coltypes[j]) {\n\t\t\t\tcase 'L': rout.write_shift(1, data[i][j] == null ? 0x3F : data[i][j] ? 0x54 : 0x46); break;\n\t\t\t\tcase 'B': rout.write_shift(8, data[i][j]||0, 'f'); break;\n\t\t\t\tcase 'N':\n\t\t\t\t\tvar _n = \"0\";\n\t\t\t\t\tif(typeof data[i][j] == \"number\") _n = data[i][j].toFixed(coldecimals[j]||0);\n\t\t\t\t\tfor(hcnt=0; hcnt < colwidths[j]-_n.length; ++hcnt) rout.write_shift(1, 0x20);\n\t\t\t\t\trout.write_shift(1, _n, \"sbcs\");\n\t\t\t\t\tbreak;\n\t\t\t\tcase 'D':\n\t\t\t\t\tif(!data[i][j]) rout.write_shift(8, \"00000000\", \"sbcs\");\n\t\t\t\t\telse {\n\t\t\t\t\t\trout.write_shift(4, (\"0000\"+data[i][j].getFullYear()).slice(-4), \"sbcs\");\n\t\t\t\t\t\trout.write_shift(2, (\"00\"+(data[i][j].getMonth()+1)).slice(-2), \"sbcs\");\n\t\t\t\t\t\trout.write_shift(2, (\"00\"+data[i][j].getDate()).slice(-2), \"sbcs\");\n\t\t\t\t\t} break;\n\t\t\t\tcase 'C':\n\t\t\t\t\tvar _s = String(data[i][j] != null ? data[i][j] : \"\").slice(0, colwidths[j]);\n\t\t\t\t\trout.write_shift(1, _s, \"sbcs\");\n\t\t\t\t\tfor(hcnt=0; hcnt < colwidths[j]-_s.length; ++hcnt) rout.write_shift(1, 0x20); break;\n\t\t\t}\n\t\t}\n\t\t// data\n\t}\n\tba.next(1).write_shift(1, 0x1A);\n\treturn ba.end();\n}\n\treturn {\n\t\tto_workbook: dbf_to_workbook,\n\t\tto_sheet: dbf_to_sheet,\n\t\tfrom_sheet: sheet_to_dbf\n\t};\n})();\n\nvar SYLK = /*#__PURE__*/(function() {\n\t/* TODO: stress test sequences */\n\tvar sylk_escapes = ({\n\t\tAA:'À', BA:'Á', CA:'Â', DA:195, HA:'Ä', JA:197,\n\t\tAE:'È', BE:'É', CE:'Ê',         HE:'Ë',\n\t\tAI:'Ì', BI:'Í', CI:'Î',         HI:'Ï',\n\t\tAO:'Ò', BO:'Ó', CO:'Ô', DO:213, HO:'Ö',\n\t\tAU:'Ù', BU:'Ú', CU:'Û',         HU:'Ü',\n\t\tAa:'à', Ba:'á', Ca:'â', Da:227, Ha:'ä', Ja:229,\n\t\tAe:'è', Be:'é', Ce:'ê',         He:'ë',\n\t\tAi:'ì', Bi:'í', Ci:'î',         Hi:'ï',\n\t\tAo:'ò', Bo:'ó', Co:'ô', Do:245, Ho:'ö',\n\t\tAu:'ù', Bu:'ú', Cu:'û',         Hu:'ü',\n\t\tKC:'Ç', Kc:'ç', q:'æ',  z:'œ',  a:'Æ',  j:'Œ',\n\t\tDN:209, Dn:241, Hy:255,\n\t\tS:169,  c:170,  R:174,  \"B \":180,\n\t\t/*::[*/0/*::]*/:176,    /*::[*/1/*::]*/:177,  /*::[*/2/*::]*/:178,\n\t\t/*::[*/3/*::]*/:179,    /*::[*/5/*::]*/:181,  /*::[*/6/*::]*/:182,\n\t\t/*::[*/7/*::]*/:183,    Q:185,  k:186,  b:208,  i:216,  l:222,  s:240,  y:248,\n\t\t\"!\":161, '\"':162, \"#\":163, \"(\":164, \"%\":165, \"'\":167, \"H \":168,\n\t\t\"+\":171, \";\":187, \"<\":188, \"=\":189, \">\":190, \"?\":191, \"{\":223\n\t}/*:any*/);\n\tvar sylk_char_regex = new RegExp(\"\\u001BN(\" + keys(sylk_escapes).join(\"|\").replace(/\\|\\|\\|/, \"|\\\\||\").replace(/([?()+])/g,\"\\\\$1\") + \"|\\\\|)\", \"gm\");\n\tvar sylk_char_fn = function(_, $1){ var o = sylk_escapes[$1]; return typeof o == \"number\" ? _getansi(o) : o; };\n\tvar decode_sylk_char = function($$, $1, $2) { var newcc = (($1.charCodeAt(0) - 0x20)<<4) | ($2.charCodeAt(0) - 0x30); return newcc == 59 ? $$ : _getansi(newcc); };\n\tsylk_escapes[\"|\"] = 254;\n\t/* TODO: find an actual specification */\n\tfunction sylk_to_aoa(d/*:RawData*/, opts)/*:[AOA, Worksheet]*/ {\n\t\tswitch(opts.type) {\n\t\t\tcase 'base64': return sylk_to_aoa_str(Base64_decode(d), opts);\n\t\t\tcase 'binary': return sylk_to_aoa_str(d, opts);\n\t\t\tcase 'buffer': return sylk_to_aoa_str(has_buf && Buffer.isBuffer(d) ? d.toString('binary') : a2s(d), opts);\n\t\t\tcase 'array': return sylk_to_aoa_str(cc2str(d), opts);\n\t\t}\n\t\tthrow new Error(\"Unrecognized type \" + opts.type);\n\t}\n\tfunction sylk_to_aoa_str(str/*:string*/, opts)/*:[AOA, Worksheet]*/ {\n\t\tvar records = str.split(/[\\n\\r]+/), R = -1, C = -1, ri = 0, rj = 0, arr/*:AOA*/ = [];\n\t\tvar formats/*:Array<string>*/ = [];\n\t\tvar next_cell_format/*:string|null*/ = null;\n\t\tvar sht = {}, rowinfo/*:Array<RowInfo>*/ = [], colinfo/*:Array<ColInfo>*/ = [], cw/*:Array<string>*/ = [];\n\t\tvar Mval = 0, j;\n\t\tif(+opts.codepage >= 0) set_cp(+opts.codepage);\n\t\tfor (; ri !== records.length; ++ri) {\n\t\t\tMval = 0;\n\t\t\tvar rstr=records[ri].trim().replace(/\\x1B([\\x20-\\x2F])([\\x30-\\x3F])/g, decode_sylk_char).replace(sylk_char_regex, sylk_char_fn);\n\t\t\tvar record=rstr.replace(/;;/g, \"\\u0000\").split(\";\").map(function(x) { return x.replace(/\\u0000/g, \";\"); });\n\t\t\tvar RT=record[0], val;\n\t\t\tif(rstr.length > 0) switch(RT) {\n\t\t\tcase 'ID': break; /* header */\n\t\t\tcase 'E': break; /* EOF */\n\t\t\tcase 'B': break; /* dimensions */\n\t\t\tcase 'O': break; /* options? */\n\t\t\tcase 'W': break; /* window? */\n\t\t\tcase 'P':\n\t\t\t\tif(record[1].charAt(0) == 'P')\n\t\t\t\t\tformats.push(rstr.slice(3).replace(/;;/g, \";\"));\n\t\t\t\tbreak;\n\t\t\tcase 'C':\n\t\t\tvar C_seen_K = false, C_seen_X = false, C_seen_S = false, C_seen_E = false, _R = -1, _C = -1;\n\t\t\tfor(rj=1; rj<record.length; ++rj) switch(record[rj].charAt(0)) {\n\t\t\t\tcase 'A': break; // TODO: comment\n\t\t\t\tcase 'X': C = parseInt(record[rj].slice(1))-1; C_seen_X = true; break;\n\t\t\t\tcase 'Y':\n\t\t\t\t\tR = parseInt(record[rj].slice(1))-1; if(!C_seen_X) C = 0;\n\t\t\t\t\tfor(j = arr.length; j <= R; ++j) arr[j] = [];\n\t\t\t\t\tbreak;\n\t\t\t\tcase 'K':\n\t\t\t\t\tval = record[rj].slice(1);\n\t\t\t\t\tif(val.charAt(0) === '\"') val = val.slice(1,val.length - 1);\n\t\t\t\t\telse if(val === 'TRUE') val = true;\n\t\t\t\t\telse if(val === 'FALSE') val = false;\n\t\t\t\t\telse if(!isNaN(fuzzynum(val))) {\n\t\t\t\t\t\tval = fuzzynum(val);\n\t\t\t\t\t\tif(next_cell_format !== null && fmt_is_date(next_cell_format)) val = numdate(val);\n\t\t\t\t\t} else if(!isNaN(fuzzydate(val).getDate())) {\n\t\t\t\t\t\tval = parseDate(val);\n\t\t\t\t\t}\n\t\t\t\t\tif(typeof $cptable !== 'undefined' && typeof val == \"string\" && ((opts||{}).type != \"string\") && (opts||{}).codepage) val = $cptable.utils.decode(opts.codepage, val);\n\t\t\t\t\tC_seen_K = true;\n\t\t\t\t\tbreak;\n\t\t\t\tcase 'E':\n\t\t\t\t\tC_seen_E = true;\n\t\t\t\t\tvar formula = rc_to_a1(record[rj].slice(1), {r:R,c:C});\n\t\t\t\t\tarr[R][C] = [arr[R][C], formula];\n\t\t\t\t\tbreak;\n\t\t\t\tcase 'S':\n\t\t\t\t\tC_seen_S = true;\n\t\t\t\t\tarr[R][C] = [arr[R][C], \"S5S\"];\n\t\t\t\t\tbreak;\n\t\t\t\tcase 'G': break; // unknown\n\t\t\t\tcase 'R': _R = parseInt(record[rj].slice(1))-1; break;\n\t\t\t\tcase 'C': _C = parseInt(record[rj].slice(1))-1; break;\n\t\t\t\tdefault: if(opts && opts.WTF) throw new Error(\"SYLK bad record \" + rstr);\n\t\t\t}\n\t\t\tif(C_seen_K) {\n\t\t\t\tif(arr[R][C] && arr[R][C].length == 2) arr[R][C][0] = val;\n\t\t\t\telse arr[R][C] = val;\n\t\t\t\tnext_cell_format = null;\n\t\t\t}\n\t\t\tif(C_seen_S) {\n\t\t\t\tif(C_seen_E) throw new Error(\"SYLK shared formula cannot have own formula\");\n\t\t\t\tvar shrbase = _R > -1 && arr[_R][_C];\n\t\t\t\tif(!shrbase || !shrbase[1]) throw new Error(\"SYLK shared formula cannot find base\");\n\t\t\t\tarr[R][C][1] = shift_formula_str(shrbase[1], {r: R - _R, c: C - _C});\n\t\t\t}\n\t\t\tbreak;\n\t\t\tcase 'F':\n\t\t\tvar F_seen = 0;\n\t\t\tfor(rj=1; rj<record.length; ++rj) switch(record[rj].charAt(0)) {\n\t\t\t\tcase 'X': C = parseInt(record[rj].slice(1))-1; ++F_seen; break;\n\t\t\t\tcase 'Y':\n\t\t\t\t\tR = parseInt(record[rj].slice(1))-1; /*C = 0;*/\n\t\t\t\t\tfor(j = arr.length; j <= R; ++j) arr[j] = [];\n\t\t\t\t\tbreak;\n\t\t\t\tcase 'M': Mval = parseInt(record[rj].slice(1)) / 20; break;\n\t\t\t\tcase 'F': break; /* ??? */\n\t\t\t\tcase 'G': break; /* hide grid */\n\t\t\t\tcase 'P':\n\t\t\t\t\tnext_cell_format = formats[parseInt(record[rj].slice(1))];\n\t\t\t\t\tbreak;\n\t\t\t\tcase 'S': break; /* cell style */\n\t\t\t\tcase 'D': break; /* column */\n\t\t\t\tcase 'N': break; /* font */\n\t\t\t\tcase 'W':\n\t\t\t\t\tcw = record[rj].slice(1).split(\" \");\n\t\t\t\t\tfor(j = parseInt(cw[0], 10); j <= parseInt(cw[1], 10); ++j) {\n\t\t\t\t\t\tMval = parseInt(cw[2], 10);\n\t\t\t\t\t\tcolinfo[j-1] = Mval === 0 ? {hidden:true}: {wch:Mval}; process_col(colinfo[j-1]);\n\t\t\t\t\t} break;\n\t\t\t\tcase 'C': /* default column format */\n\t\t\t\t\tC = parseInt(record[rj].slice(1))-1;\n\t\t\t\t\tif(!colinfo[C]) colinfo[C] = {};\n\t\t\t\t\tbreak;\n\t\t\t\tcase 'R': /* row properties */\n\t\t\t\t\tR = parseInt(record[rj].slice(1))-1;\n\t\t\t\t\tif(!rowinfo[R]) rowinfo[R] = {};\n\t\t\t\t\tif(Mval > 0) { rowinfo[R].hpt = Mval; rowinfo[R].hpx = pt2px(Mval); }\n\t\t\t\t\telse if(Mval === 0) rowinfo[R].hidden = true;\n\t\t\t\t\tbreak;\n\t\t\t\tdefault: if(opts && opts.WTF) throw new Error(\"SYLK bad record \" + rstr);\n\t\t\t}\n\t\t\tif(F_seen < 1) next_cell_format = null; break;\n\t\t\tdefault: if(opts && opts.WTF) throw new Error(\"SYLK bad record \" + rstr);\n\t\t\t}\n\t\t}\n\t\tif(rowinfo.length > 0) sht['!rows'] = rowinfo;\n\t\tif(colinfo.length > 0) sht['!cols'] = colinfo;\n\t\tif(opts && opts.sheetRows) arr = arr.slice(0, opts.sheetRows);\n\t\treturn [arr, sht];\n\t}\n\n\tfunction sylk_to_sheet(d/*:RawData*/, opts)/*:Worksheet*/ {\n\t\tvar aoasht = sylk_to_aoa(d, opts);\n\t\tvar aoa = aoasht[0], ws = aoasht[1];\n\t\tvar o = aoa_to_sheet(aoa, opts);\n\t\tkeys(ws).forEach(function(k) { o[k] = ws[k]; });\n\t\treturn o;\n\t}\n\n\tfunction sylk_to_workbook(d/*:RawData*/, opts)/*:Workbook*/ { return sheet_to_workbook(sylk_to_sheet(d, opts), opts); }\n\n\tfunction write_ws_cell_sylk(cell/*:Cell*/, ws/*:Worksheet*/, R/*:number*/, C/*:number*//*::, opts*/)/*:string*/ {\n\t\tvar o = \"C;Y\" + (R+1) + \";X\" + (C+1) + \";K\";\n\t\tswitch(cell.t) {\n\t\t\tcase 'n':\n\t\t\t\to += (cell.v||0);\n\t\t\t\tif(cell.f && !cell.F) o += \";E\" + a1_to_rc(cell.f, {r:R, c:C}); break;\n\t\t\tcase 'b': o += cell.v ? \"TRUE\" : \"FALSE\"; break;\n\t\t\tcase 'e': o += cell.w || cell.v; break;\n\t\t\tcase 'd': o += '\"' + (cell.w || cell.v) + '\"'; break;\n\t\t\tcase 's': o += '\"' + cell.v.replace(/\"/g,\"\").replace(/;/g, \";;\") + '\"'; break;\n\t\t}\n\t\treturn o;\n\t}\n\n\tfunction write_ws_cols_sylk(out, cols) {\n\t\tcols.forEach(function(col, i) {\n\t\t\tvar rec = \"F;W\" + (i+1) + \" \" + (i+1) + \" \";\n\t\t\tif(col.hidden) rec += \"0\";\n\t\t\telse {\n\t\t\t\tif(typeof col.width == 'number' && !col.wpx) col.wpx = width2px(col.width);\n\t\t\t\tif(typeof col.wpx == 'number' && !col.wch) col.wch = px2char(col.wpx);\n\t\t\t\tif(typeof col.wch == 'number') rec += Math.round(col.wch);\n\t\t\t}\n\t\t\tif(rec.charAt(rec.length - 1) != \" \") out.push(rec);\n\t\t});\n\t}\n\n\tfunction write_ws_rows_sylk(out/*:Array<string>*/, rows/*:Array<RowInfo>*/) {\n\t\trows.forEach(function(row, i) {\n\t\t\tvar rec = \"F;\";\n\t\t\tif(row.hidden) rec += \"M0;\";\n\t\t\telse if(row.hpt) rec += \"M\" + 20 * row.hpt + \";\";\n\t\t\telse if(row.hpx) rec += \"M\" + 20 * px2pt(row.hpx) + \";\";\n\t\t\tif(rec.length > 2) out.push(rec + \"R\" + (i+1));\n\t\t});\n\t}\n\n\tfunction sheet_to_sylk(ws/*:Worksheet*/, opts/*:?any*/)/*:string*/ {\n\t\tvar preamble/*:Array<string>*/ = [\"ID;PWXL;N;E\"], o/*:Array<string>*/ = [];\n\t\tvar r = safe_decode_range(ws['!ref']), cell/*:Cell*/;\n\t\tvar dense = Array.isArray(ws);\n\t\tvar RS = \"\\r\\n\";\n\n\t\tpreamble.push(\"P;PGeneral\");\n\t\tpreamble.push(\"F;P0;DG0G8;M255\");\n\t\tif(ws['!cols']) write_ws_cols_sylk(preamble, ws['!cols']);\n\t\tif(ws['!rows']) write_ws_rows_sylk(preamble, ws['!rows']);\n\n\t\tpreamble.push(\"B;Y\" + (r.e.r - r.s.r + 1) + \";X\" + (r.e.c - r.s.c + 1) + \";D\" + [r.s.c,r.s.r,r.e.c,r.e.r].join(\" \"));\n\t\tfor(var R = r.s.r; R <= r.e.r; ++R) {\n\t\t\tfor(var C = r.s.c; C <= r.e.c; ++C) {\n\t\t\t\tvar coord = encode_cell({r:R,c:C});\n\t\t\t\tcell = dense ? (ws[R]||[])[C]: ws[coord];\n\t\t\t\tif(!cell || (cell.v == null && (!cell.f || cell.F))) continue;\n\t\t\t\to.push(write_ws_cell_sylk(cell, ws, R, C, opts));\n\t\t\t}\n\t\t}\n\t\treturn preamble.join(RS) + RS + o.join(RS) + RS + \"E\" + RS;\n\t}\n\n\treturn {\n\t\tto_workbook: sylk_to_workbook,\n\t\tto_sheet: sylk_to_sheet,\n\t\tfrom_sheet: sheet_to_sylk\n\t};\n})();\n\nvar DIF = /*#__PURE__*/(function() {\n\tfunction dif_to_aoa(d/*:RawData*/, opts)/*:AOA*/ {\n\t\tswitch(opts.type) {\n\t\t\tcase 'base64': return dif_to_aoa_str(Base64_decode(d), opts);\n\t\t\tcase 'binary': return dif_to_aoa_str(d, opts);\n\t\t\tcase 'buffer': return dif_to_aoa_str(has_buf && Buffer.isBuffer(d) ? d.toString('binary') : a2s(d), opts);\n\t\t\tcase 'array': return dif_to_aoa_str(cc2str(d), opts);\n\t\t}\n\t\tthrow new Error(\"Unrecognized type \" + opts.type);\n\t}\n\tfunction dif_to_aoa_str(str/*:string*/, opts)/*:AOA*/ {\n\t\tvar records = str.split('\\n'), R = -1, C = -1, ri = 0, arr/*:AOA*/ = [];\n\t\tfor (; ri !== records.length; ++ri) {\n\t\t\tif (records[ri].trim() === 'BOT') { arr[++R] = []; C = 0; continue; }\n\t\t\tif (R < 0) continue;\n\t\t\tvar metadata = records[ri].trim().split(\",\");\n\t\t\tvar type = metadata[0], value = metadata[1];\n\t\t\t++ri;\n\t\t\tvar data = records[ri] || \"\";\n\t\t\twhile(((data.match(/[\"]/g)||[]).length & 1) && ri < records.length - 1) data += \"\\n\" + records[++ri];\n\t\t\tdata = data.trim();\n\t\t\tswitch (+type) {\n\t\t\t\tcase -1:\n\t\t\t\t\tif (data === 'BOT') { arr[++R] = []; C = 0; continue; }\n\t\t\t\t\telse if (data !== 'EOD') throw new Error(\"Unrecognized DIF special command \" + data);\n\t\t\t\t\tbreak;\n\t\t\t\tcase 0:\n\t\t\t\t\tif(data === 'TRUE') arr[R][C] = true;\n\t\t\t\t\telse if(data === 'FALSE') arr[R][C] = false;\n\t\t\t\t\telse if(!isNaN(fuzzynum(value))) arr[R][C] = fuzzynum(value);\n\t\t\t\t\telse if(!isNaN(fuzzydate(value).getDate())) arr[R][C] = parseDate(value);\n\t\t\t\t\telse arr[R][C] = value;\n\t\t\t\t\t++C; break;\n\t\t\t\tcase 1:\n\t\t\t\t\tdata = data.slice(1,data.length-1);\n\t\t\t\t\tdata = data.replace(/\"\"/g, '\"');\n\t\t\t\t\tif(DIF_XL && data && data.match(/^=\".*\"$/)) data = data.slice(2, -1);\n\t\t\t\t\tarr[R][C++] = data !== '' ? data : null;\n\t\t\t\t\tbreak;\n\t\t\t}\n\t\t\tif (data === 'EOD') break;\n\t\t}\n\t\tif(opts && opts.sheetRows) arr = arr.slice(0, opts.sheetRows);\n\t\treturn arr;\n\t}\n\n\tfunction dif_to_sheet(str/*:string*/, opts)/*:Worksheet*/ { return aoa_to_sheet(dif_to_aoa(str, opts), opts); }\n\tfunction dif_to_workbook(str/*:string*/, opts)/*:Workbook*/ { return sheet_to_workbook(dif_to_sheet(str, opts), opts); }\n\n\tvar sheet_to_dif = /*#__PURE__*/(function() {\n\t\tvar push_field = function pf(o/*:Array<string>*/, topic/*:string*/, v/*:number*/, n/*:number*/, s/*:string*/) {\n\t\t\to.push(topic);\n\t\t\to.push(v + \",\" + n);\n\t\t\to.push('\"' + s.replace(/\"/g,'\"\"') + '\"');\n\t\t};\n\t\tvar push_value = function po(o/*:Array<string>*/, type/*:number*/, v/*:any*/, s/*:string*/) {\n\t\t\to.push(type + \",\" + v);\n\t\t\to.push(type == 1 ? '\"' + s.replace(/\"/g,'\"\"') + '\"' : s);\n\t\t};\n\t\treturn function sheet_to_dif(ws/*:Worksheet*//*::, opts:?any*/)/*:string*/ {\n\t\t\tvar o/*:Array<string>*/ = [];\n\t\t\tvar r = safe_decode_range(ws['!ref']), cell/*:Cell*/;\n\t\t\tvar dense = Array.isArray(ws);\n\t\t\tpush_field(o, \"TABLE\", 0, 1, \"sheetjs\");\n\t\t\tpush_field(o, \"VECTORS\", 0, r.e.r - r.s.r + 1,\"\");\n\t\t\tpush_field(o, \"TUPLES\", 0, r.e.c - r.s.c + 1,\"\");\n\t\t\tpush_field(o, \"DATA\", 0, 0,\"\");\n\t\t\tfor(var R = r.s.r; R <= r.e.r; ++R) {\n\t\t\t\tpush_value(o, -1, 0, \"BOT\");\n\t\t\t\tfor(var C = r.s.c; C <= r.e.c; ++C) {\n\t\t\t\t\tvar coord = encode_cell({r:R,c:C});\n\t\t\t\t\tcell = dense ? (ws[R]||[])[C] : ws[coord];\n\t\t\t\t\tif(!cell) { push_value(o, 1, 0, \"\"); continue;}\n\t\t\t\t\tswitch(cell.t) {\n\t\t\t\t\t\tcase 'n':\n\t\t\t\t\t\t\tvar val = DIF_XL ? cell.w : cell.v;\n\t\t\t\t\t\t\tif(!val && cell.v != null) val = cell.v;\n\t\t\t\t\t\t\tif(val == null) {\n\t\t\t\t\t\t\t\tif(DIF_XL && cell.f && !cell.F) push_value(o, 1, 0, \"=\" + cell.f);\n\t\t\t\t\t\t\t\telse push_value(o, 1, 0, \"\");\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\telse push_value(o, 0, val, \"V\");\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase 'b':\n\t\t\t\t\t\t\tpush_value(o, 0, cell.v ? 1 : 0, cell.v ? \"TRUE\" : \"FALSE\");\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase 's':\n\t\t\t\t\t\t\tpush_value(o, 1, 0, (!DIF_XL || isNaN(cell.v)) ? cell.v : '=\"' + cell.v + '\"');\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase 'd':\n\t\t\t\t\t\t\tif(!cell.w) cell.w = SSF_format(cell.z || table_fmt[14], datenum(parseDate(cell.v)));\n\t\t\t\t\t\t\tif(DIF_XL) push_value(o, 0, cell.w, \"V\");\n\t\t\t\t\t\t\telse push_value(o, 1, 0, cell.w);\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tdefault: push_value(o, 1, 0, \"\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tpush_value(o, -1, 0, \"EOD\");\n\t\t\tvar RS = \"\\r\\n\";\n\t\t\tvar oo = o.join(RS);\n\t\t\t//while((oo.length & 0x7F) != 0) oo += \"\\0\";\n\t\t\treturn oo;\n\t\t};\n\t})();\n\treturn {\n\t\tto_workbook: dif_to_workbook,\n\t\tto_sheet: dif_to_sheet,\n\t\tfrom_sheet: sheet_to_dif\n\t};\n})();\n\nvar ETH = /*#__PURE__*/(function() {\n\tfunction decode(s/*:string*/)/*:string*/ { return s.replace(/\\\\b/g,\"\\\\\").replace(/\\\\c/g,\":\").replace(/\\\\n/g,\"\\n\"); }\n\tfunction encode(s/*:string*/)/*:string*/ { return s.replace(/\\\\/g, \"\\\\b\").replace(/:/g, \"\\\\c\").replace(/\\n/g,\"\\\\n\"); }\n\n\tfunction eth_to_aoa(str/*:string*/, opts)/*:AOA*/ {\n\t\tvar records = str.split('\\n'), R = -1, C = -1, ri = 0, arr/*:AOA*/ = [];\n\t\tfor (; ri !== records.length; ++ri) {\n\t\t\tvar record = records[ri].trim().split(\":\");\n\t\t\tif(record[0] !== 'cell') continue;\n\t\t\tvar addr = decode_cell(record[1]);\n\t\t\tif(arr.length <= addr.r) for(R = arr.length; R <= addr.r; ++R) if(!arr[R]) arr[R] = [];\n\t\t\tR = addr.r; C = addr.c;\n\t\t\tswitch(record[2]) {\n\t\t\t\tcase 't': arr[R][C] = decode(record[3]); break;\n\t\t\t\tcase 'v': arr[R][C] = +record[3]; break;\n\t\t\t\tcase 'vtf': var _f = record[record.length - 1];\n\t\t\t\t\t/* falls through */\n\t\t\t\tcase 'vtc':\n\t\t\t\t\tswitch(record[3]) {\n\t\t\t\t\t\tcase 'nl': arr[R][C] = +record[4] ? true : false; break;\n\t\t\t\t\t\tdefault: arr[R][C] = +record[4]; break;\n\t\t\t\t\t}\n\t\t\t\t\tif(record[2] == 'vtf') arr[R][C] = [arr[R][C], _f];\n\t\t\t}\n\t\t}\n\t\tif(opts && opts.sheetRows) arr = arr.slice(0, opts.sheetRows);\n\t\treturn arr;\n\t}\n\n\tfunction eth_to_sheet(d/*:string*/, opts)/*:Worksheet*/ { return aoa_to_sheet(eth_to_aoa(d, opts), opts); }\n\tfunction eth_to_workbook(d/*:string*/, opts)/*:Workbook*/ { return sheet_to_workbook(eth_to_sheet(d, opts), opts); }\n\n\tvar header = [\n\t\t\"socialcalc:version:1.5\",\n\t\t\"MIME-Version: 1.0\",\n\t\t\"Content-Type: multipart/mixed; boundary=SocialCalcSpreadsheetControlSave\"\n\t].join(\"\\n\");\n\n\tvar sep = [\n\t\t\"--SocialCalcSpreadsheetControlSave\",\n\t\t\"Content-type: text/plain; charset=UTF-8\"\n\t].join(\"\\n\") + \"\\n\";\n\n\t/* TODO: the other parts */\n\tvar meta = [\n\t\t\"# SocialCalc Spreadsheet Control Save\",\n\t\t\"part:sheet\"\n\t].join(\"\\n\");\n\n\tvar end = \"--SocialCalcSpreadsheetControlSave--\";\n\n\tfunction sheet_to_eth_data(ws/*:Worksheet*/)/*:string*/ {\n\t\tif(!ws || !ws['!ref']) return \"\";\n\t\tvar o/*:Array<string>*/ = [], oo/*:Array<string>*/ = [], cell, coord = \"\";\n\t\tvar r = decode_range(ws['!ref']);\n\t\tvar dense = Array.isArray(ws);\n\t\tfor(var R = r.s.r; R <= r.e.r; ++R) {\n\t\t\tfor(var C = r.s.c; C <= r.e.c; ++C) {\n\t\t\t\tcoord = encode_cell({r:R,c:C});\n\t\t\t\tcell = dense ? (ws[R]||[])[C] : ws[coord];\n\t\t\t\tif(!cell || cell.v == null || cell.t === 'z') continue;\n\t\t\t\too = [\"cell\", coord, 't'];\n\t\t\t\tswitch(cell.t) {\n\t\t\t\t\tcase 's': case 'str': oo.push(encode(cell.v)); break;\n\t\t\t\t\tcase 'n':\n\t\t\t\t\t\tif(!cell.f) { oo[2]='v'; oo[3]=cell.v; }\n\t\t\t\t\t\telse { oo[2]='vtf'; oo[3]='n'; oo[4]=cell.v; oo[5]=encode(cell.f); }\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase 'b':\n\t\t\t\t\t\too[2] = 'vt'+(cell.f?'f':'c'); oo[3]='nl'; oo[4]=cell.v?\"1\":\"0\";\n\t\t\t\t\t\too[5] = encode(cell.f||(cell.v?'TRUE':'FALSE'));\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase 'd':\n\t\t\t\t\t\tvar t = datenum(parseDate(cell.v));\n\t\t\t\t\t\too[2] = 'vtc'; oo[3] = 'nd'; oo[4] = \"\"+t;\n\t\t\t\t\t\too[5] = cell.w || SSF_format(cell.z || table_fmt[14], t);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase 'e': continue;\n\t\t\t\t}\n\t\t\t\to.push(oo.join(\":\"));\n\t\t\t}\n\t\t}\n\t\to.push(\"sheet:c:\" + (r.e.c-r.s.c+1) + \":r:\" + (r.e.r-r.s.r+1) + \":tvf:1\");\n\t\to.push(\"valueformat:1:text-wiki\");\n\t\t//o.push(\"copiedfrom:\" + ws['!ref']); // clipboard only\n\t\treturn o.join(\"\\n\");\n\t}\n\n\tfunction sheet_to_eth(ws/*:Worksheet*//*::, opts:?any*/)/*:string*/ {\n\t\treturn [header, sep, meta, sep, sheet_to_eth_data(ws), end].join(\"\\n\");\n\t\t// return [\"version:1.5\", sheet_to_eth_data(ws)].join(\"\\n\"); // clipboard form\n\t}\n\n\treturn {\n\t\tto_workbook: eth_to_workbook,\n\t\tto_sheet: eth_to_sheet,\n\t\tfrom_sheet: sheet_to_eth\n\t};\n})();\n\nvar PRN = /*#__PURE__*/(function() {\n\tfunction set_text_arr(data/*:string*/, arr/*:AOA*/, R/*:number*/, C/*:number*/, o/*:any*/) {\n\t\tif(o.raw) arr[R][C] = data;\n\t\telse if(data === \"\"){/* empty */}\n\t\telse if(data === 'TRUE') arr[R][C] = true;\n\t\telse if(data === 'FALSE') arr[R][C] = false;\n\t\telse if(!isNaN(fuzzynum(data))) arr[R][C] = fuzzynum(data);\n\t\telse if(!isNaN(fuzzydate(data).getDate())) arr[R][C] = parseDate(data);\n\t\telse arr[R][C] = data;\n\t}\n\n\tfunction prn_to_aoa_str(f/*:string*/, opts)/*:AOA*/ {\n\t\tvar o = opts || {};\n\t\tvar arr/*:AOA*/ = ([]/*:any*/);\n\t\tif(!f || f.length === 0) return arr;\n\t\tvar lines = f.split(/[\\r\\n]/);\n\t\tvar L = lines.length - 1;\n\t\twhile(L >= 0 && lines[L].length === 0) --L;\n\t\tvar start = 10, idx = 0;\n\t\tvar R = 0;\n\t\tfor(; R <= L; ++R) {\n\t\t\tidx = lines[R].indexOf(\" \");\n\t\t\tif(idx == -1) idx = lines[R].length; else idx++;\n\t\t\tstart = Math.max(start, idx);\n\t\t}\n\t\tfor(R = 0; R <= L; ++R) {\n\t\t\tarr[R] = [];\n\t\t\t/* TODO: confirm that widths are always 10 */\n\t\t\tvar C = 0;\n\t\t\tset_text_arr(lines[R].slice(0, start).trim(), arr, R, C, o);\n\t\t\tfor(C = 1; C <= (lines[R].length - start)/10 + 1; ++C)\n\t\t\t\tset_text_arr(lines[R].slice(start+(C-1)*10,start+C*10).trim(),arr,R,C,o);\n\t\t}\n\t\tif(o.sheetRows) arr = arr.slice(0, o.sheetRows);\n\t\treturn arr;\n\t}\n\n\t// List of accepted CSV separators\n\tvar guess_seps = {\n\t\t/*::[*/0x2C/*::]*/: ',',\n\t\t/*::[*/0x09/*::]*/: \"\\t\",\n\t\t/*::[*/0x3B/*::]*/: ';',\n\t\t/*::[*/0x7C/*::]*/: '|'\n\t};\n\n\t// CSV separator weights to be used in case of equal numbers\n\tvar guess_sep_weights = {\n\t\t/*::[*/0x2C/*::]*/: 3,\n\t\t/*::[*/0x09/*::]*/: 2,\n\t\t/*::[*/0x3B/*::]*/: 1,\n\t\t/*::[*/0x7C/*::]*/: 0\n\t};\n\n\tfunction guess_sep(str) {\n\t\tvar cnt = {}, instr = false, end = 0, cc = 0;\n\t\tfor(;end < str.length;++end) {\n\t\t\tif((cc=str.charCodeAt(end)) == 0x22) instr = !instr;\n\t\t\telse if(!instr && cc in guess_seps) cnt[cc] = (cnt[cc]||0)+1;\n\t\t}\n\n\t\tcc = [];\n\t\tfor(end in cnt) if ( Object.prototype.hasOwnProperty.call(cnt, end) ) {\n\t\t\tcc.push([ cnt[end], end ]);\n\t\t}\n\n\t\tif ( !cc.length ) {\n\t\t\tcnt = guess_sep_weights;\n\t\t\tfor(end in cnt) if ( Object.prototype.hasOwnProperty.call(cnt, end) ) {\n\t\t\t\tcc.push([ cnt[end], end ]);\n\t\t\t}\n\t\t}\n\n\t\tcc.sort(function(a, b) { return a[0] - b[0] || guess_sep_weights[a[1]] - guess_sep_weights[b[1]]; });\n\n\t\treturn guess_seps[cc.pop()[1]] || 0x2C;\n\t}\n\n\tfunction dsv_to_sheet_str(str/*:string*/, opts)/*:Worksheet*/ {\n\t\tvar o = opts || {};\n\t\tvar sep = \"\";\n\t\tif(DENSE != null && o.dense == null) o.dense = DENSE;\n\t\tvar ws/*:Worksheet*/ = o.dense ? ([]/*:any*/) : ({}/*:any*/);\n\t\tvar range/*:Range*/ = ({s: {c:0, r:0}, e: {c:0, r:0}}/*:any*/);\n\n\t\tif(str.slice(0,4) == \"sep=\") {\n\t\t\t// If the line ends in \\r\\n\n\t\t\tif(str.charCodeAt(5) == 13 && str.charCodeAt(6) == 10 ) {\n\t\t\t\tsep = str.charAt(4); str = str.slice(7);\n\t\t\t}\n\t\t\t// If line ends in \\r OR \\n\n\t\t\telse if(str.charCodeAt(5) == 13 || str.charCodeAt(5) == 10 ) {\n\t\t\t\tsep = str.charAt(4); str = str.slice(6);\n\t\t\t}\n\t\t\telse sep = guess_sep(str.slice(0,1024));\n\t\t}\n\t\telse if(o && o.FS) sep = o.FS;\n\t\telse sep = guess_sep(str.slice(0,1024));\n\t\tvar R = 0, C = 0, v = 0;\n\t\tvar start = 0, end = 0, sepcc = sep.charCodeAt(0), instr = false, cc=0, startcc=str.charCodeAt(0);\n\t\tstr = str.replace(/\\r\\n/mg, \"\\n\");\n\t\tvar _re/*:?RegExp*/ = o.dateNF != null ? dateNF_regex(o.dateNF) : null;\n\t\tfunction finish_cell() {\n\t\t\tvar s = str.slice(start, end);\n\t\t\tvar cell = ({}/*:any*/);\n\t\t\tif(s.charAt(0) == '\"' && s.charAt(s.length - 1) == '\"') s = s.slice(1,-1).replace(/\"\"/g,'\"');\n\t\t\tif(s.length === 0) cell.t = 'z';\n\t\t\telse if(o.raw) { cell.t = 's'; cell.v = s; }\n\t\t\telse if(s.trim().length === 0) { cell.t = 's'; cell.v = s; }\n\t\t\telse if(s.charCodeAt(0) == 0x3D) {\n\t\t\t\tif(s.charCodeAt(1) == 0x22 && s.charCodeAt(s.length - 1) == 0x22) { cell.t = 's'; cell.v = s.slice(2,-1).replace(/\"\"/g,'\"'); }\n\t\t\t\telse if(fuzzyfmla(s)) { cell.t = 'n'; cell.f = s.slice(1); }\n\t\t\t\telse { cell.t = 's'; cell.v = s; } }\n\t\t\telse if(s == \"TRUE\") { cell.t = 'b'; cell.v = true; }\n\t\t\telse if(s == \"FALSE\") { cell.t = 'b'; cell.v = false; }\n\t\t\telse if(!isNaN(v = fuzzynum(s))) { cell.t = 'n'; if(o.cellText !== false) cell.w = s; cell.v = v; }\n\t\t\telse if(!isNaN(fuzzydate(s).getDate()) || _re && s.match(_re)) {\n\t\t\t\tcell.z = o.dateNF || table_fmt[14];\n\t\t\t\tvar k = 0;\n\t\t\t\tif(_re && s.match(_re)){ s=dateNF_fix(s, o.dateNF, (s.match(_re)||[])); k=1; }\n\t\t\t\tif(o.cellDates) { cell.t = 'd'; cell.v = parseDate(s, k); }\n\t\t\t\telse { cell.t = 'n'; cell.v = datenum(parseDate(s, k)); }\n\t\t\t\tif(o.cellText !== false) cell.w = SSF_format(cell.z, cell.v instanceof Date ? datenum(cell.v):cell.v);\n\t\t\t\tif(!o.cellNF) delete cell.z;\n\t\t\t} else {\n\t\t\t\tcell.t = 's';\n\t\t\t\tcell.v = s;\n\t\t\t}\n\t\t\tif(cell.t == 'z'){}\n\t\t\telse if(o.dense) { if(!ws[R]) ws[R] = []; ws[R][C] = cell; }\n\t\t\telse ws[encode_cell({c:C,r:R})] = cell;\n\t\t\tstart = end+1; startcc = str.charCodeAt(start);\n\t\t\tif(range.e.c < C) range.e.c = C;\n\t\t\tif(range.e.r < R) range.e.r = R;\n\t\t\tif(cc == sepcc) ++C; else { C = 0; ++R; if(o.sheetRows && o.sheetRows <= R) return true; }\n\t\t}\n\t\touter: for(;end < str.length;++end) switch((cc=str.charCodeAt(end))) {\n\t\t\tcase 0x22: if(startcc === 0x22) instr = !instr; break;\n\t\t\tcase sepcc: case 0x0a: case 0x0d: if(!instr && finish_cell()) break outer; break;\n\t\t\tdefault: break;\n\t\t}\n\t\tif(end - start > 0) finish_cell();\n\n\t\tws['!ref'] = encode_range(range);\n\t\treturn ws;\n\t}\n\n\tfunction prn_to_sheet_str(str/*:string*/, opts)/*:Worksheet*/ {\n\t\tif(!(opts && opts.PRN)) return dsv_to_sheet_str(str, opts);\n\t\tif(opts.FS) return dsv_to_sheet_str(str, opts);\n\t\tif(str.slice(0,4) == \"sep=\") return dsv_to_sheet_str(str, opts);\n\t\tif(str.indexOf(\"\\t\") >= 0 || str.indexOf(\",\") >= 0 || str.indexOf(\";\") >= 0) return dsv_to_sheet_str(str, opts);\n\t\treturn aoa_to_sheet(prn_to_aoa_str(str, opts), opts);\n\t}\n\n\tfunction prn_to_sheet(d/*:RawData*/, opts)/*:Worksheet*/ {\n\t\tvar str = \"\", bytes = opts.type == 'string' ? [0,0,0,0] : firstbyte(d, opts);\n\t\tswitch(opts.type) {\n\t\t\tcase 'base64': str = Base64_decode(d); break;\n\t\t\tcase 'binary': str = d; break;\n\t\t\tcase 'buffer':\n\t\t\t\tif(opts.codepage == 65001) str = d.toString('utf8'); // TODO: test if buf\n\t\t\t\telse if(opts.codepage && typeof $cptable !== 'undefined') str = $cptable.utils.decode(opts.codepage, d);\n\t\t\t\telse str = has_buf && Buffer.isBuffer(d) ? d.toString('binary') : a2s(d);\n\t\t\t\tbreak;\n\t\t\tcase 'array': str = cc2str(d); break;\n\t\t\tcase 'string': str = d; break;\n\t\t\tdefault: throw new Error(\"Unrecognized type \" + opts.type);\n\t\t}\n\t\tif(bytes[0] == 0xEF && bytes[1] == 0xBB && bytes[2] == 0xBF) str = utf8read(str.slice(3));\n\t\telse if(opts.type != 'string' && opts.type != 'buffer' && opts.codepage == 65001) str = utf8read(str);\n\t\telse if((opts.type == 'binary') && typeof $cptable !== 'undefined' && opts.codepage)  str = $cptable.utils.decode(opts.codepage, $cptable.utils.encode(28591,str));\n\t\tif(str.slice(0,19) == \"socialcalc:version:\") return ETH.to_sheet(opts.type == 'string' ? str : utf8read(str), opts);\n\t\treturn prn_to_sheet_str(str, opts);\n\t}\n\n\tfunction prn_to_workbook(d/*:RawData*/, opts)/*:Workbook*/ { return sheet_to_workbook(prn_to_sheet(d, opts), opts); }\n\n\tfunction sheet_to_prn(ws/*:Worksheet*//*::, opts:?any*/)/*:string*/ {\n\t\tvar o/*:Array<string>*/ = [];\n\t\tvar r = safe_decode_range(ws['!ref']), cell/*:Cell*/;\n\t\tvar dense = Array.isArray(ws);\n\t\tfor(var R = r.s.r; R <= r.e.r; ++R) {\n\t\t\tvar oo/*:Array<string>*/ = [];\n\t\t\tfor(var C = r.s.c; C <= r.e.c; ++C) {\n\t\t\t\tvar coord = encode_cell({r:R,c:C});\n\t\t\t\tcell = dense ? (ws[R]||[])[C] : ws[coord];\n\t\t\t\tif(!cell || cell.v == null) { oo.push(\"          \"); continue; }\n\t\t\t\tvar w = (cell.w || (format_cell(cell), cell.w) || \"\").slice(0,10);\n\t\t\t\twhile(w.length < 10) w += \" \";\n\t\t\t\too.push(w + (C === 0 ? \" \" : \"\"));\n\t\t\t}\n\t\t\to.push(oo.join(\"\"));\n\t\t}\n\t\treturn o.join(\"\\n\");\n\t}\n\n\treturn {\n\t\tto_workbook: prn_to_workbook,\n\t\tto_sheet: prn_to_sheet,\n\t\tfrom_sheet: sheet_to_prn\n\t};\n})();\n\n/* Excel defaults to SYLK but warns if data is not valid */\nfunction read_wb_ID(d, opts) {\n\tvar o = opts || {}, OLD_WTF = !!o.WTF; o.WTF = true;\n\ttry {\n\t\tvar out = SYLK.to_workbook(d, o);\n\t\to.WTF = OLD_WTF;\n\t\treturn out;\n\t} catch(e) {\n\t\to.WTF = OLD_WTF;\n\t\tif(!e.message.match(/SYLK bad record ID/) && OLD_WTF) throw e;\n\t\treturn PRN.to_workbook(d, opts);\n\t}\n}\n\nvar WK_ = /*#__PURE__*/(function() {\n\tfunction lotushopper(data, cb/*:RecordHopperCB*/, opts/*:any*/) {\n\t\tif(!data) return;\n\t\tprep_blob(data, data.l || 0);\n\t\tvar Enum = opts.Enum || WK1Enum;\n\t\twhile(data.l < data.length) {\n\t\t\tvar RT = data.read_shift(2);\n\t\t\tvar R = Enum[RT] || Enum[0xFFFF];\n\t\t\tvar length = data.read_shift(2);\n\t\t\tvar tgt = data.l + length;\n\t\t\tvar d = R.f && R.f(data, length, opts);\n\t\t\tdata.l = tgt;\n\t\t\tif(cb(d, R, RT)) return;\n\t\t}\n\t}\n\n\tfunction lotus_to_workbook(d/*:RawData*/, opts) {\n\t\tswitch(opts.type) {\n\t\t\tcase 'base64': return lotus_to_workbook_buf(s2a(Base64_decode(d)), opts);\n\t\t\tcase 'binary': return lotus_to_workbook_buf(s2a(d), opts);\n\t\t\tcase 'buffer':\n\t\t\tcase 'array': return lotus_to_workbook_buf(d, opts);\n\t\t}\n\t\tthrow \"Unsupported type \" + opts.type;\n\t}\n\n\tfunction lotus_to_workbook_buf(d, opts)/*:Workbook*/ {\n\t\tif(!d) return d;\n\t\tvar o = opts || {};\n\t\tif(DENSE != null && o.dense == null) o.dense = DENSE;\n\t\tvar s/*:Worksheet*/ = ((o.dense ? [] : {})/*:any*/), n = \"Sheet1\", next_n = \"\", sidx = 0;\n\t\tvar sheets = {}, snames = [], realnames = [];\n\n\t\tvar refguess = {s: {r:0, c:0}, e: {r:0, c:0} };\n\t\tvar sheetRows = o.sheetRows || 0;\n\n\t\tif(d[2] == 0x00) {\n\t\t\tif(d[3] == 0x08 || d[3] == 0x09) {\n\t\t\t\tif(d.length >= 16 && d[14] == 0x05 && d[15] === 0x6c) throw new Error(\"Unsupported Works 3 for Mac file\");\n\t\t\t}\n\t\t}\n\n\t\tif(d[2] == 0x02) {\n\t\t\to.Enum = WK1Enum;\n\t\t\tlotushopper(d, function(val, R, RT) { switch(RT) {\n\t\t\t\tcase 0x00: /* BOF */\n\t\t\t\t\to.vers = val;\n\t\t\t\t\tif(val >= 0x1000) o.qpro = true;\n\t\t\t\t\tbreak;\n\t\t\t\tcase 0x06: refguess = val; break; /* RANGE */\n\t\t\t\tcase 0xCC: if(val) next_n = val; break; /* SHEETNAMECS */\n\t\t\t\tcase 0xDE: next_n = val; break; /* SHEETNAMELP */\n\t\t\t\tcase 0x0F: /* LABEL */\n\t\t\t\tcase 0x33: /* STRING */\n\t\t\t\t\tif(!o.qpro) val[1].v = val[1].v.slice(1);\n\t\t\t\t\t/* falls through */\n\t\t\t\tcase 0x0D: /* INTEGER */\n\t\t\t\tcase 0x0E: /* NUMBER */\n\t\t\t\tcase 0x10: /* FORMULA */\n\t\t\t\t\t/* TODO: actual translation of the format code */\n\t\t\t\t\tif(RT == 0x0E && (val[2] & 0x70) == 0x70 && (val[2] & 0x0F) > 1 && (val[2] & 0x0F) < 15) {\n\t\t\t\t\t\tval[1].z = o.dateNF || table_fmt[14];\n\t\t\t\t\t\tif(o.cellDates) { val[1].t = 'd'; val[1].v = numdate(val[1].v); }\n\t\t\t\t\t}\n\n\t\t\t\t\tif(o.qpro) {\n\t\t\t\t\t\tif(val[3] > sidx) {\n\t\t\t\t\t\t\ts[\"!ref\"] = encode_range(refguess);\n\t\t\t\t\t\t\tsheets[n] = s;\n\t\t\t\t\t\t\tsnames.push(n);\n\t\t\t\t\t\t\ts = (o.dense ? [] : {});\n\t\t\t\t\t\t\trefguess = {s: {r:0, c:0}, e: {r:0, c:0} };\n\t\t\t\t\t\t\tsidx = val[3]; n = next_n || \"Sheet\" + (sidx + 1); next_n = \"\";\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\tvar tmpcell = o.dense ? (s[val[0].r]||[])[val[0].c] : s[encode_cell(val[0])];\n\t\t\t\t\tif(tmpcell) {\n\t\t\t\t\t\ttmpcell.t = val[1].t; tmpcell.v = val[1].v;\n\t\t\t\t\t\tif(val[1].z != null) tmpcell.z = val[1].z;\n\t\t\t\t\t\tif(val[1].f != null) tmpcell.f = val[1].f;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t\tif(o.dense) {\n\t\t\t\t\t\tif(!s[val[0].r]) s[val[0].r] = [];\n\t\t\t\t\t\ts[val[0].r][val[0].c] = val[1];\n\t\t\t\t\t} else s[encode_cell(val[0])] = val[1];\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t}}, o);\n\t\t} else if(d[2] == 0x1A || d[2] == 0x0E) {\n\t\t\to.Enum = WK3Enum;\n\t\t\tif(d[2] == 0x0E) { o.qpro = true; d.l = 0; }\n\t\t\tlotushopper(d, function(val, R, RT) { switch(RT) {\n\t\t\t\tcase 0xCC: n = val; break; /* SHEETNAMECS */\n\t\t\t\tcase 0x16: /* LABEL16 */\n\t\t\t\t\tval[1].v = val[1].v.slice(1);\n\t\t\t\t\t/* falls through */\n\t\t\t\tcase 0x17: /* NUMBER17 */\n\t\t\t\tcase 0x18: /* NUMBER18 */\n\t\t\t\tcase 0x19: /* FORMULA19 */\n\t\t\t\tcase 0x25: /* NUMBER25 */\n\t\t\t\tcase 0x27: /* NUMBER27 */\n\t\t\t\tcase 0x28: /* FORMULA28 */\n\t\t\t\t\tif(val[3] > sidx) {\n\t\t\t\t\t\ts[\"!ref\"] = encode_range(refguess);\n\t\t\t\t\t\tsheets[n] = s;\n\t\t\t\t\t\tsnames.push(n);\n\t\t\t\t\t\ts = (o.dense ? [] : {});\n\t\t\t\t\t\trefguess = {s: {r:0, c:0}, e: {r:0, c:0} };\n\t\t\t\t\t\tsidx = val[3]; n = \"Sheet\" + (sidx + 1);\n\t\t\t\t\t}\n\t\t\t\t\tif(sheetRows > 0 && val[0].r >= sheetRows) break;\n\t\t\t\t\tif(o.dense) {\n\t\t\t\t\t\tif(!s[val[0].r]) s[val[0].r] = [];\n\t\t\t\t\t\ts[val[0].r][val[0].c] = val[1];\n\t\t\t\t\t} else s[encode_cell(val[0])] = val[1];\n\t\t\t\t\tif(refguess.e.c < val[0].c) refguess.e.c = val[0].c;\n\t\t\t\t\tif(refguess.e.r < val[0].r) refguess.e.r = val[0].r;\n\t\t\t\t\tbreak;\n\t\t\t\tcase 0x1B: /* XFORMAT */\n\t\t\t\t\tif(val[0x36b0]) realnames[val[0x36b0][0]] = val[0x36b0][1];\n\t\t\t\t\tbreak;\n\t\t\t\tcase 0x0601: /* SHEETINFOQP */\n\t\t\t\t\trealnames[val[0]] = val[1]; if(val[0] == sidx) n = val[1]; break;\n\t\t\t\tdefault: break;\n\t\t\t}}, o);\n\t\t} else throw new Error(\"Unrecognized LOTUS BOF \" + d[2]);\n\t\ts[\"!ref\"] = encode_range(refguess);\n\t\tsheets[next_n || n] = s;\n\t\tsnames.push(next_n || n);\n\t\tif(!realnames.length) return { SheetNames: snames, Sheets: sheets };\n\t\tvar osheets = {}, rnames = [];\n\t\t/* TODO: verify no collisions */\n\t\tfor(var i = 0; i < realnames.length; ++i) if(sheets[snames[i]]) {\n\t\t\trnames.push(realnames[i] || snames[i]);\n\t\t\tosheets[realnames[i]] = sheets[realnames[i]] || sheets[snames[i]];\n\t\t} else {\n\t\t\trnames.push(realnames[i]);\n\t\t\tosheets[realnames[i]] = ({ \"!ref\": \"A1\" });\n\t\t}\n\t\treturn { SheetNames: rnames, Sheets: osheets };\n\t}\n\n\tfunction sheet_to_wk1(ws/*:Worksheet*/, opts/*:WriteOpts*/) {\n\t\tvar o = opts || {};\n\t\tif(+o.codepage >= 0) set_cp(+o.codepage);\n\t\tif(o.type == \"string\") throw new Error(\"Cannot write WK1 to JS string\");\n\t\tvar ba = buf_array();\n\t\tvar range = safe_decode_range(ws[\"!ref\"]);\n\t\tvar dense = Array.isArray(ws);\n\t\tvar cols = [];\n\n\t\twrite_biff_rec(ba, 0x00, write_BOF_WK1(0x0406));\n\t\twrite_biff_rec(ba, 0x06, write_RANGE(range));\n\t\tvar max_R = Math.min(range.e.r, 8191);\n\t\tfor(var R = range.s.r; R <= max_R; ++R) {\n\t\t\tvar rr = encode_row(R);\n\t\t\tfor(var C = range.s.c; C <= range.e.c; ++C) {\n\t\t\t\tif(R === range.s.r) cols[C] = encode_col(C);\n\t\t\t\tvar ref = cols[C] + rr;\n\t\t\t\tvar cell = dense ? (ws[R]||[])[C] : ws[ref];\n\t\t\t\tif(!cell || cell.t == \"z\") continue;\n\t\t\t\t/* TODO: formula records */\n\t\t\t\tif(cell.t == \"n\") {\n\t\t\t\t\tif((cell.v|0)==cell.v && cell.v >= -32768 && cell.v <= 32767) write_biff_rec(ba, 0x0d, write_INTEGER(R, C, cell.v));\n\t\t\t\t\telse write_biff_rec(ba, 0x0e, write_NUMBER(R, C, cell.v));\n\t\t\t\t} else {\n\t\t\t\t\tvar str = format_cell(cell);\n\t\t\t\t\twrite_biff_rec(ba, 0x0F, write_LABEL(R, C, str.slice(0, 239)));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\twrite_biff_rec(ba, 0x01);\n\t\treturn ba.end();\n\t}\n\n\tfunction book_to_wk3(wb/*:Workbook*/, opts/*:WriteOpts*/) {\n\t\tvar o = opts || {};\n\t\tif(+o.codepage >= 0) set_cp(+o.codepage);\n\t\tif(o.type == \"string\") throw new Error(\"Cannot write WK3 to JS string\");\n\t\tvar ba = buf_array();\n\n\t\twrite_biff_rec(ba, 0x00, write_BOF_WK3(wb));\n\n\t\tfor(var i = 0, cnt = 0; i < wb.SheetNames.length; ++i) if((wb.Sheets[wb.SheetNames[i]] || {})[\"!ref\"]) write_biff_rec(ba, 0x1b, write_XFORMAT_SHEETNAME(wb.SheetNames[i], cnt++));\n\n\t\tvar wsidx = 0;\n\t\tfor(i = 0; i < wb.SheetNames.length; ++i) {\n\t\t\tvar ws = wb.Sheets[wb.SheetNames[i]];\n\t\t\tif(!ws || !ws[\"!ref\"]) continue;\n\t\t\tvar range = safe_decode_range(ws[\"!ref\"]);\n\t\t\tvar dense = Array.isArray(ws);\n\t\t\tvar cols = [];\n\t\t\tvar max_R = Math.min(range.e.r, 8191);\n\t\t\tfor(var R = range.s.r; R <= max_R; ++R) {\n\t\t\t\tvar rr = encode_row(R);\n\t\t\t\tfor(var C = range.s.c; C <= range.e.c; ++C) {\n\t\t\t\t\tif(R === range.s.r) cols[C] = encode_col(C);\n\t\t\t\t\tvar ref = cols[C] + rr;\n\t\t\t\t\tvar cell = dense ? (ws[R]||[])[C] : ws[ref];\n\t\t\t\t\tif(!cell || cell.t == \"z\") continue;\n\t\t\t\t\t/* TODO: FORMULA19 NUMBER18 records */\n\t\t\t\t\tif(cell.t == \"n\") {\n\t\t\t\t\t\twrite_biff_rec(ba, 0x17, write_NUMBER_17(R, C, wsidx, cell.v));\n\t\t\t\t\t} else {\n\t\t\t\t\t\tvar str = format_cell(cell);\n\t\t\t\t\t\t/* TODO: max len? */\n\t\t\t\t\t\twrite_biff_rec(ba, 0x16, write_LABEL_16(R, C, wsidx, str.slice(0, 239)));\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t++wsidx;\n\t\t}\n\n\t\twrite_biff_rec(ba, 0x01);\n\t\treturn ba.end();\n\t}\n\n\n\tfunction write_BOF_WK1(v/*:number*/) {\n\t\tvar out = new_buf(2);\n\t\tout.write_shift(2, v);\n\t\treturn out;\n\t}\n\n\tfunction write_BOF_WK3(wb/*:Workbook*/) {\n\t\tvar out = new_buf(26);\n\t\tout.write_shift(2, 0x1000);\n\t\tout.write_shift(2, 0x0004);\n\t\tout.write_shift(4, 0x0000);\n\t\tvar rows = 0, cols = 0, wscnt = 0;\n\t\tfor(var i = 0; i < wb.SheetNames.length; ++i) {\n\t\t\tvar name = wb.SheetNames[i];\n\t\t\tvar ws = wb.Sheets[name];\n\t\t\tif(!ws || !ws[\"!ref\"]) continue;\n\t\t\t++wscnt;\n\t\t\tvar range = decode_range(ws[\"!ref\"]);\n\t\t\tif(rows < range.e.r) rows = range.e.r;\n\t\t\tif(cols < range.e.c) cols = range.e.c;\n\t\t}\n\t\tif(rows > 8191) rows = 8191;\n\t\tout.write_shift(2, rows);\n\t\tout.write_shift(1, wscnt);\n\t\tout.write_shift(1, cols);\n\t\tout.write_shift(2, 0x00);\n\t\tout.write_shift(2, 0x00);\n\t\tout.write_shift(1, 0x01);\n\t\tout.write_shift(1, 0x02);\n\t\tout.write_shift(4, 0);\n\t\tout.write_shift(4, 0);\n\t\treturn out;\n\t}\n\n\tfunction parse_RANGE(blob, length, opts) {\n\t\tvar o = {s:{c:0,r:0},e:{c:0,r:0}};\n\t\tif(length == 8 && opts.qpro) {\n\t\t\to.s.c = blob.read_shift(1);\n\t\t\tblob.l++;\n\t\t\to.s.r = blob.read_shift(2);\n\t\t\to.e.c = blob.read_shift(1);\n\t\t\tblob.l++;\n\t\t\to.e.r = blob.read_shift(2);\n\t\t\treturn o;\n\t\t}\n\t\to.s.c = blob.read_shift(2);\n\t\to.s.r = blob.read_shift(2);\n\t\tif(length == 12 && opts.qpro) blob.l += 2;\n\t\to.e.c = blob.read_shift(2);\n\t\to.e.r = blob.read_shift(2);\n\t\tif(length == 12 && opts.qpro) blob.l += 2;\n\t\tif(o.s.c == 0xFFFF) o.s.c = o.e.c = o.s.r = o.e.r = 0;\n\t\treturn o;\n\t}\n\tfunction write_RANGE(range) {\n\t\tvar out = new_buf(8);\n\t\tout.write_shift(2, range.s.c);\n\t\tout.write_shift(2, range.s.r);\n\t\tout.write_shift(2, range.e.c);\n\t\tout.write_shift(2, range.e.r);\n\t\treturn out;\n\t}\n\n\tfunction parse_cell(blob, length, opts) {\n\t\tvar o = [{c:0,r:0}, {t:'n',v:0}, 0, 0];\n\t\tif(opts.qpro && opts.vers != 0x5120) {\n\t\t\to[0].c = blob.read_shift(1);\n\t\t\to[3] = blob.read_shift(1);\n\t\t\to[0].r = blob.read_shift(2);\n\t\t\tblob.l+=2;\n\t\t} else {\n\t\t\to[2] = blob.read_shift(1);\n\t\t\to[0].c = blob.read_shift(2); o[0].r = blob.read_shift(2);\n\t\t}\n\t\treturn o;\n\t}\n\n\tfunction parse_LABEL(blob, length, opts) {\n\t\tvar tgt = blob.l + length;\n\t\tvar o = parse_cell(blob, length, opts);\n\t\to[1].t = 's';\n\t\tif(opts.vers == 0x5120) {\n\t\t\tblob.l++;\n\t\t\tvar len = blob.read_shift(1);\n\t\t\to[1].v = blob.read_shift(len, 'utf8');\n\t\t\treturn o;\n\t\t}\n\t\tif(opts.qpro) blob.l++;\n\t\to[1].v = blob.read_shift(tgt - blob.l, 'cstr');\n\t\treturn o;\n\t}\n\tfunction write_LABEL(R, C, s) {\n\t\t/* TODO: encoding */\n\t\tvar o = new_buf(7 + s.length);\n\t\to.write_shift(1, 0xFF);\n\t\to.write_shift(2, C);\n\t\to.write_shift(2, R);\n\t\to.write_shift(1, 0x27); // ??\n\t\tfor(var i = 0; i < o.length; ++i) {\n\t\t\tvar cc = s.charCodeAt(i);\n\t\t\to.write_shift(1, cc >= 0x80 ? 0x5F : cc);\n\t\t}\n\t\to.write_shift(1, 0);\n\t\treturn o;\n\t}\n\n\tfunction parse_INTEGER(blob, length, opts) {\n\t\tvar o = parse_cell(blob, length, opts);\n\t\to[1].v = blob.read_shift(2, 'i');\n\t\treturn o;\n\t}\n\tfunction write_INTEGER(R, C, v) {\n\t\tvar o = new_buf(7);\n\t\to.write_shift(1, 0xFF);\n\t\to.write_shift(2, C);\n\t\to.write_shift(2, R);\n\t\to.write_shift(2, v, 'i');\n\t\treturn o;\n\t}\n\n\tfunction parse_NUMBER(blob, length, opts) {\n\t\tvar o = parse_cell(blob, length, opts);\n\t\to[1].v = blob.read_shift(8, 'f');\n\t\treturn o;\n\t}\n\tfunction write_NUMBER(R, C, v) {\n\t\tvar o = new_buf(13);\n\t\to.write_shift(1, 0xFF);\n\t\to.write_shift(2, C);\n\t\to.write_shift(2, R);\n\t\to.write_shift(8, v, 'f');\n\t\treturn o;\n\t}\n\n\tfunction parse_FORMULA(blob, length, opts) {\n\t\tvar tgt = blob.l + length;\n\t\tvar o = parse_cell(blob, length, opts);\n\t\t/* TODO: formula */\n\t\to[1].v = blob.read_shift(8, 'f');\n\t\tif(opts.qpro) blob.l = tgt;\n\t\telse {\n\t\t\tvar flen = blob.read_shift(2);\n\t\t\twk1_fmla_to_csf(blob.slice(blob.l, blob.l + flen), o);\n\t\t\tblob.l += flen;\n\t\t}\n\t\treturn o;\n\t}\n\n\tfunction wk1_parse_rc(B, V, col) {\n\t\tvar rel = V & 0x8000;\n\t\tV &= ~0x8000;\n\t\tV = (rel ? B : 0) + ((V >= 0x2000) ? V - 0x4000 : V);\n\t\treturn (rel ? \"\" : \"$\") + (col ? encode_col(V) : encode_row(V));\n\t}\n\t/* var oprec = [\n\t\t8, 8, 8, 8, 8, 8, 8, 8, 6, 4, 4, 5, 5, 7, 3, 3,\n\t\t3, 3, 3, 3, 1, 1, 2, 6, 8, 8, 8, 8, 8, 8, 8, 8\n\t]; */\n\t/* TODO: flesh out */\n\tvar FuncTab = {\n\t\t0x33: [\"FALSE\", 0],\n\t\t0x34: [\"TRUE\", 0],\n\t\t0x46: [\"LEN\", 1],\n\t\t0x50: [\"SUM\", 69],\n\t\t0x51: [\"AVERAGEA\", 69],\n\t\t0x52: [\"COUNTA\", 69],\n\t\t0x53: [\"MINA\", 69],\n\t\t0x54: [\"MAXA\", 69],\n\t\t0x6F: [\"T\", 1]\n\t};\n\tvar BinOpTab = [\n\t\t  \"\",   \"\",   \"\",   \"\",   \"\",   \"\",   \"\",   \"\", // eslint-disable-line no-mixed-spaces-and-tabs\n\t\t  \"\",  \"+\",  \"-\",  \"*\",  \"/\",  \"^\",  \"=\", \"<>\", // eslint-disable-line no-mixed-spaces-and-tabs\n\t\t\"<=\", \">=\",  \"<\",  \">\",   \"\",   \"\",   \"\",   \"\", // eslint-disable-line no-mixed-spaces-and-tabs\n\t\t \"&\",   \"\",   \"\",   \"\",   \"\",   \"\",   \"\",   \"\"  // eslint-disable-line no-mixed-spaces-and-tabs\n\t];\n\n\tfunction wk1_fmla_to_csf(blob, o) {\n\t\tprep_blob(blob, 0);\n\t\tvar out = [], argc = 0, R = \"\", C = \"\", argL = \"\", argR = \"\";\n\t\twhile(blob.l < blob.length) {\n\t\t\tvar cc = blob[blob.l++];\n\t\t\tswitch(cc) {\n\t\t\t\tcase 0x00: out.push(blob.read_shift(8, 'f')); break;\n\t\t\t\tcase 0x01: {\n\t\t\t\t\tC = wk1_parse_rc(o[0].c, blob.read_shift(2), true);\n\t\t\t\t\tR = wk1_parse_rc(o[0].r, blob.read_shift(2), false);\n\t\t\t\t\tout.push(C + R);\n\t\t\t\t} break;\n\t\t\t\tcase 0x02: {\n\t\t\t\t\tvar c = wk1_parse_rc(o[0].c, blob.read_shift(2), true);\n\t\t\t\t\tvar r = wk1_parse_rc(o[0].r, blob.read_shift(2), false);\n\t\t\t\t\tC = wk1_parse_rc(o[0].c, blob.read_shift(2), true);\n\t\t\t\t\tR = wk1_parse_rc(o[0].r, blob.read_shift(2), false);\n\t\t\t\t\tout.push(c + r + \":\" + C + R);\n\t\t\t\t} break;\n\t\t\t\tcase 0x03:\n\t\t\t\t\tif(blob.l < blob.length) { console.error(\"WK1 premature formula end\"); return; }\n\t\t\t\t\tbreak;\n\t\t\t\tcase 0x04: out.push(\"(\" + out.pop() + \")\"); break;\n\t\t\t\tcase 0x05: out.push(blob.read_shift(2)); break;\n\t\t\t\tcase 0x06: {\n\t\t\t\t\t/* TODO: text encoding */\n\t\t\t\t\tvar Z = \"\"; while((cc = blob[blob.l++])) Z += String.fromCharCode(cc);\n\t\t\t\t\tout.push('\"' + Z.replace(/\"/g, '\"\"') + '\"');\n\t\t\t\t} break;\n\n\t\t\t\tcase 0x08: out.push(\"-\" + out.pop()); break;\n\t\t\t\tcase 0x17: out.push(\"+\" + out.pop()); break;\n\t\t\t\tcase 0x16: out.push(\"NOT(\" + out.pop() + \")\"); break;\n\n\t\t\t\tcase 0x14: case 0x15: {\n\t\t\t\t\targR = out.pop(); argL = out.pop();\n\t\t\t\t\tout.push([\"AND\", \"OR\"][cc - 0x14] + \"(\" + argL + \",\" + argR + \")\");\n\t\t\t\t} break;\n\n\t\t\t\tdefault:\n\t\t\t\t\tif(cc < 0x20 && BinOpTab[cc]) {\n\t\t\t\t\t\targR = out.pop(); argL = out.pop();\n\t\t\t\t\t\tout.push(argL + BinOpTab[cc] + argR);\n\t\t\t\t\t} else if(FuncTab[cc]) {\n\t\t\t\t\t\targc = FuncTab[cc][1];\n\t\t\t\t\t\tif(argc == 69) argc = blob[blob.l++];\n\t\t\t\t\t\tif(argc > out.length) { console.error(\"WK1 bad formula parse 0x\" + cc.toString(16) + \":|\" + out.join(\"|\") + \"|\"); return; }\n\t\t\t\t\t\tvar args = out.slice(-argc);\n\t\t\t\t\t\tout.length -= argc;\n\t\t\t\t\t\tout.push(FuncTab[cc][0] + \"(\" + args.join(\",\") + \")\");\n\t\t\t\t\t}\n\t\t\t\t\telse if(cc <= 0x07) return console.error(\"WK1 invalid opcode \" + cc.toString(16));\n\t\t\t\t\telse if(cc <= 0x18) return console.error(\"WK1 unsupported op \" + cc.toString(16));\n\t\t\t\t\telse if(cc <= 0x1E) return console.error(\"WK1 invalid opcode \" + cc.toString(16));\n\t\t\t\t\telse if(cc <= 0x73) return console.error(\"WK1 unsupported function opcode \" + cc.toString(16));\n\t\t\t\t\t// possible future functions ??\n\t\t\t\t\telse return console.error(\"WK1 unrecognized opcode \" + cc.toString(16));\n\t\t\t}\n\t\t}\n\t\tif(out.length == 1) o[1].f = \"\" + out[0];\n\t\telse console.error(\"WK1 bad formula parse |\" + out.join(\"|\") + \"|\");\n\t}\n\n\n\tfunction parse_cell_3(blob/*::, length*/) {\n\t\tvar o = [{c:0,r:0}, {t:'n',v:0}, 0];\n\t\to[0].r = blob.read_shift(2); o[3] = blob[blob.l++]; o[0].c = blob[blob.l++];\n\t\treturn o;\n\t}\n\n\tfunction parse_LABEL_16(blob, length) {\n\t\tvar o = parse_cell_3(blob, length);\n\t\to[1].t = 's';\n\t\to[1].v = blob.read_shift(length - 4, 'cstr');\n\t\treturn o;\n\t}\n\tfunction write_LABEL_16(R, C, wsidx, s) {\n\t\t/* TODO: encoding */\n\t\tvar o = new_buf(6 + s.length);\n\t\to.write_shift(2, R);\n\t\to.write_shift(1, wsidx);\n\t\to.write_shift(1, C);\n\t\to.write_shift(1, 0x27);\n\t\tfor(var i = 0; i < s.length; ++i) {\n\t\t\tvar cc = s.charCodeAt(i);\n\t\t\to.write_shift(1, cc >= 0x80 ? 0x5F : cc);\n\t\t}\n\t\to.write_shift(1, 0);\n\t\treturn o;\n\t}\n\n\tfunction parse_NUMBER_18(blob, length) {\n\t\tvar o = parse_cell_3(blob, length);\n\t\to[1].v = blob.read_shift(2);\n\t\tvar v = o[1].v >> 1;\n\t\tif(o[1].v & 0x1) {\n\t\t\tswitch(v & 0x07) {\n\t\t\t\tcase 0: v = (v >> 3) * 5000; break;\n\t\t\t\tcase 1: v = (v >> 3) * 500; break;\n\t\t\t\tcase 2: v = (v >> 3) / 20; break;\n\t\t\t\tcase 3: v = (v >> 3) / 200; break;\n\t\t\t\tcase 4: v = (v >> 3) / 2000; break;\n\t\t\t\tcase 5: v = (v >> 3) / 20000; break;\n\t\t\t\tcase 6: v = (v >> 3) / 16; break;\n\t\t\t\tcase 7: v = (v >> 3) / 64; break;\n\t\t\t}\n\t\t}\n\t\to[1].v = v;\n\t\treturn o;\n\t}\n\n\tfunction parse_NUMBER_17(blob, length) {\n\t\tvar o = parse_cell_3(blob, length);\n\t\tvar v1 = blob.read_shift(4);\n\t\tvar v2 = blob.read_shift(4);\n\t\tvar e = blob.read_shift(2);\n\t\tif(e == 0xFFFF) {\n\t\t\tif(v1 === 0 && v2 === 0xC0000000) { o[1].t = \"e\"; o[1].v = 0x0F; } // ERR -> #VALUE!\n\t\t\telse if(v1 === 0 && v2 === 0xD0000000) { o[1].t = \"e\"; o[1].v = 0x2A; } // NA -> #N/A\n\t\t\telse o[1].v = 0;\n\t\t\treturn o;\n\t\t}\n\t\tvar s = e & 0x8000; e = (e&0x7FFF) - 16446;\n\t\to[1].v = (1 - s*2) * (v2 * Math.pow(2, e+32) + v1 * Math.pow(2, e));\n\t\treturn o;\n\t}\n\tfunction write_NUMBER_17(R, C, wsidx, v) {\n\t\tvar o = new_buf(14);\n\t\to.write_shift(2, R);\n\t\to.write_shift(1, wsidx);\n\t\to.write_shift(1, C);\n\t\tif(v == 0) {\n\t\t\to.write_shift(4, 0);\n\t\t\to.write_shift(4, 0);\n\t\t\to.write_shift(2, 0xFFFF);\n\t\t\treturn o;\n\t\t}\n\t\tvar s = 0, e = 0, v1 = 0, v2 = 0;\n\t\tif(v < 0) { s = 1; v = -v; }\n\t\te = Math.log2(v) | 0;\n\t\tv /= Math.pow(2, e-31);\n\t\tv2 = (v)>>>0;\n\t\tif((v2&0x80000000) == 0) { v/=2; ++e; v2 = v >>> 0; }\n\t\tv -= v2;\n\t\tv2 |= 0x80000000;\n\t\tv2 >>>= 0;\n\t\tv *= Math.pow(2, 32);\n\t\tv1 = v>>>0;\n\t\to.write_shift(4, v1);\n\t\to.write_shift(4, v2);\n\t\te += 0x3FFF + (s ? 0x8000 : 0);\n\t\to.write_shift(2, e);\n\t\treturn o;\n\t}\n\n\tfunction parse_FORMULA_19(blob, length) {\n\t\tvar o = parse_NUMBER_17(blob, 14);\n\t\tblob.l += length - 14; /* TODO: WK3 formula */\n\t\treturn o;\n\t}\n\n\tfunction parse_NUMBER_25(blob, length) {\n\t\tvar o = parse_cell_3(blob, length);\n\t\tvar v1 = blob.read_shift(4);\n\t\to[1].v = v1 >> 6;\n\t\treturn o;\n\t}\n\n\tfunction parse_NUMBER_27(blob, length) {\n\t\tvar o = parse_cell_3(blob, length);\n\t\tvar v1 = blob.read_shift(8,'f');\n\t\to[1].v = v1;\n\t\treturn o;\n\t}\n\n\tfunction parse_FORMULA_28(blob, length) {\n\t\tvar o = parse_NUMBER_27(blob, 14);\n\t\tblob.l += length - 10; /* TODO: formula */\n\t\treturn o;\n\t}\n\n\tfunction parse_SHEETNAMECS(blob, length) {\n\t\treturn blob[blob.l + length - 1] == 0 ? blob.read_shift(length, 'cstr') : \"\";\n\t}\n\n\tfunction parse_SHEETNAMELP(blob, length) {\n\t\tvar len = blob[blob.l++];\n\t\tif(len > length - 1) len = length - 1;\n\t\tvar o = \"\"; while(o.length < len) o += String.fromCharCode(blob[blob.l++]);\n\t\treturn o;\n\t}\n\n\tfunction parse_SHEETINFOQP(blob, length, opts) {\n\t\tif(!opts.qpro || length < 21) return;\n\t\tvar id = blob.read_shift(1);\n\t\tblob.l += 17;\n\t\tblob.l += 1; //var len = blob.read_shift(1);\n\t\tblob.l += 2;\n\t\tvar nm = blob.read_shift(length - 21, 'cstr');\n\t\treturn [id, nm];\n\t}\n\n\tfunction parse_XFORMAT(blob, length) {\n\t\tvar o = {}, tgt = blob.l + length;\n\t\twhile(blob.l < tgt) {\n\t\t\tvar dt = blob.read_shift(2);\n\t\t\tif(dt == 0x36b0) {\n\t\t\t\to[dt] = [0, \"\"];\n\t\t\t\to[dt][0] = blob.read_shift(2);\n\t\t\t\twhile(blob[blob.l]) { o[dt][1] += String.fromCharCode(blob[blob.l]); blob.l++; } blob.l++;\n\t\t\t}\n\t\t\t// TODO: 0x3a99 ??\n\t\t}\n\t\treturn o;\n\t}\n\tfunction write_XFORMAT_SHEETNAME(name, wsidx) {\n\t\tvar out = new_buf(5 + name.length);\n\t\tout.write_shift(2, 0x36b0);\n\t\tout.write_shift(2, wsidx);\n\t\tfor(var i = 0; i < name.length; ++i) {\n\t\t\tvar cc = name.charCodeAt(i);\n\t\t\tout[out.l++] = cc > 0x7F ? 0x5F : cc;\n\t\t}\n\t\tout[out.l++] = 0;\n\t\treturn out;\n\t}\n\n\tvar WK1Enum = {\n\t\t/*::[*/0x0000/*::]*/: { n:\"BOF\", f:parseuint16 },\n\t\t/*::[*/0x0001/*::]*/: { n:\"EOF\" },\n\t\t/*::[*/0x0002/*::]*/: { n:\"CALCMODE\" },\n\t\t/*::[*/0x0003/*::]*/: { n:\"CALCORDER\" },\n\t\t/*::[*/0x0004/*::]*/: { n:\"SPLIT\" },\n\t\t/*::[*/0x0005/*::]*/: { n:\"SYNC\" },\n\t\t/*::[*/0x0006/*::]*/: { n:\"RANGE\", f:parse_RANGE },\n\t\t/*::[*/0x0007/*::]*/: { n:\"WINDOW1\" },\n\t\t/*::[*/0x0008/*::]*/: { n:\"COLW1\" },\n\t\t/*::[*/0x0009/*::]*/: { n:\"WINTWO\" },\n\t\t/*::[*/0x000A/*::]*/: { n:\"COLW2\" },\n\t\t/*::[*/0x000B/*::]*/: { n:\"NAME\" },\n\t\t/*::[*/0x000C/*::]*/: { n:\"BLANK\" },\n\t\t/*::[*/0x000D/*::]*/: { n:\"INTEGER\", f:parse_INTEGER },\n\t\t/*::[*/0x000E/*::]*/: { n:\"NUMBER\", f:parse_NUMBER },\n\t\t/*::[*/0x000F/*::]*/: { n:\"LABEL\", f:parse_LABEL },\n\t\t/*::[*/0x0010/*::]*/: { n:\"FORMULA\", f:parse_FORMULA },\n\t\t/*::[*/0x0018/*::]*/: { n:\"TABLE\" },\n\t\t/*::[*/0x0019/*::]*/: { n:\"ORANGE\" },\n\t\t/*::[*/0x001A/*::]*/: { n:\"PRANGE\" },\n\t\t/*::[*/0x001B/*::]*/: { n:\"SRANGE\" },\n\t\t/*::[*/0x001C/*::]*/: { n:\"FRANGE\" },\n\t\t/*::[*/0x001D/*::]*/: { n:\"KRANGE1\" },\n\t\t/*::[*/0x0020/*::]*/: { n:\"HRANGE\" },\n\t\t/*::[*/0x0023/*::]*/: { n:\"KRANGE2\" },\n\t\t/*::[*/0x0024/*::]*/: { n:\"PROTEC\" },\n\t\t/*::[*/0x0025/*::]*/: { n:\"FOOTER\" },\n\t\t/*::[*/0x0026/*::]*/: { n:\"HEADER\" },\n\t\t/*::[*/0x0027/*::]*/: { n:\"SETUP\" },\n\t\t/*::[*/0x0028/*::]*/: { n:\"MARGINS\" },\n\t\t/*::[*/0x0029/*::]*/: { n:\"LABELFMT\" },\n\t\t/*::[*/0x002A/*::]*/: { n:\"TITLES\" },\n\t\t/*::[*/0x002B/*::]*/: { n:\"SHEETJS\" },\n\t\t/*::[*/0x002D/*::]*/: { n:\"GRAPH\" },\n\t\t/*::[*/0x002E/*::]*/: { n:\"NGRAPH\" },\n\t\t/*::[*/0x002F/*::]*/: { n:\"CALCCOUNT\" },\n\t\t/*::[*/0x0030/*::]*/: { n:\"UNFORMATTED\" },\n\t\t/*::[*/0x0031/*::]*/: { n:\"CURSORW12\" },\n\t\t/*::[*/0x0032/*::]*/: { n:\"WINDOW\" },\n\t\t/*::[*/0x0033/*::]*/: { n:\"STRING\", f:parse_LABEL },\n\t\t/*::[*/0x0037/*::]*/: { n:\"PASSWORD\" },\n\t\t/*::[*/0x0038/*::]*/: { n:\"LOCKED\" },\n\t\t/*::[*/0x003C/*::]*/: { n:\"QUERY\" },\n\t\t/*::[*/0x003D/*::]*/: { n:\"QUERYNAME\" },\n\t\t/*::[*/0x003E/*::]*/: { n:\"PRINT\" },\n\t\t/*::[*/0x003F/*::]*/: { n:\"PRINTNAME\" },\n\t\t/*::[*/0x0040/*::]*/: { n:\"GRAPH2\" },\n\t\t/*::[*/0x0041/*::]*/: { n:\"GRAPHNAME\" },\n\t\t/*::[*/0x0042/*::]*/: { n:\"ZOOM\" },\n\t\t/*::[*/0x0043/*::]*/: { n:\"SYMSPLIT\" },\n\t\t/*::[*/0x0044/*::]*/: { n:\"NSROWS\" },\n\t\t/*::[*/0x0045/*::]*/: { n:\"NSCOLS\" },\n\t\t/*::[*/0x0046/*::]*/: { n:\"RULER\" },\n\t\t/*::[*/0x0047/*::]*/: { n:\"NNAME\" },\n\t\t/*::[*/0x0048/*::]*/: { n:\"ACOMM\" },\n\t\t/*::[*/0x0049/*::]*/: { n:\"AMACRO\" },\n\t\t/*::[*/0x004A/*::]*/: { n:\"PARSE\" },\n\t\t/*::[*/0x0066/*::]*/: { n:\"PRANGES??\" },\n\t\t/*::[*/0x0067/*::]*/: { n:\"RRANGES??\" },\n\t\t/*::[*/0x0068/*::]*/: { n:\"FNAME??\" },\n\t\t/*::[*/0x0069/*::]*/: { n:\"MRANGES??\" },\n\t\t/*::[*/0x00CC/*::]*/: { n:\"SHEETNAMECS\", f:parse_SHEETNAMECS },\n\t\t/*::[*/0x00DE/*::]*/: { n:\"SHEETNAMELP\", f:parse_SHEETNAMELP },\n\t\t/*::[*/0xFFFF/*::]*/: { n:\"\" }\n\t};\n\n\tvar WK3Enum = {\n\t\t/*::[*/0x0000/*::]*/: { n:\"BOF\" },\n\t\t/*::[*/0x0001/*::]*/: { n:\"EOF\" },\n\t\t/*::[*/0x0002/*::]*/: { n:\"PASSWORD\" },\n\t\t/*::[*/0x0003/*::]*/: { n:\"CALCSET\" },\n\t\t/*::[*/0x0004/*::]*/: { n:\"WINDOWSET\" },\n\t\t/*::[*/0x0005/*::]*/: { n:\"SHEETCELLPTR\" },\n\t\t/*::[*/0x0006/*::]*/: { n:\"SHEETLAYOUT\" },\n\t\t/*::[*/0x0007/*::]*/: { n:\"COLUMNWIDTH\" },\n\t\t/*::[*/0x0008/*::]*/: { n:\"HIDDENCOLUMN\" },\n\t\t/*::[*/0x0009/*::]*/: { n:\"USERRANGE\" },\n\t\t/*::[*/0x000A/*::]*/: { n:\"SYSTEMRANGE\" },\n\t\t/*::[*/0x000B/*::]*/: { n:\"ZEROFORCE\" },\n\t\t/*::[*/0x000C/*::]*/: { n:\"SORTKEYDIR\" },\n\t\t/*::[*/0x000D/*::]*/: { n:\"FILESEAL\" },\n\t\t/*::[*/0x000E/*::]*/: { n:\"DATAFILLNUMS\" },\n\t\t/*::[*/0x000F/*::]*/: { n:\"PRINTMAIN\" },\n\t\t/*::[*/0x0010/*::]*/: { n:\"PRINTSTRING\" },\n\t\t/*::[*/0x0011/*::]*/: { n:\"GRAPHMAIN\" },\n\t\t/*::[*/0x0012/*::]*/: { n:\"GRAPHSTRING\" },\n\t\t/*::[*/0x0013/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0014/*::]*/: { n:\"ERRCELL\" },\n\t\t/*::[*/0x0015/*::]*/: { n:\"NACELL\" },\n\t\t/*::[*/0x0016/*::]*/: { n:\"LABEL16\", f:parse_LABEL_16},\n\t\t/*::[*/0x0017/*::]*/: { n:\"NUMBER17\", f:parse_NUMBER_17 },\n\t\t/*::[*/0x0018/*::]*/: { n:\"NUMBER18\", f:parse_NUMBER_18 },\n\t\t/*::[*/0x0019/*::]*/: { n:\"FORMULA19\", f:parse_FORMULA_19},\n\t\t/*::[*/0x001A/*::]*/: { n:\"FORMULA1A\" },\n\t\t/*::[*/0x001B/*::]*/: { n:\"XFORMAT\", f:parse_XFORMAT },\n\t\t/*::[*/0x001C/*::]*/: { n:\"DTLABELMISC\" },\n\t\t/*::[*/0x001D/*::]*/: { n:\"DTLABELCELL\" },\n\t\t/*::[*/0x001E/*::]*/: { n:\"GRAPHWINDOW\" },\n\t\t/*::[*/0x001F/*::]*/: { n:\"CPA\" },\n\t\t/*::[*/0x0020/*::]*/: { n:\"LPLAUTO\" },\n\t\t/*::[*/0x0021/*::]*/: { n:\"QUERY\" },\n\t\t/*::[*/0x0022/*::]*/: { n:\"HIDDENSHEET\" },\n\t\t/*::[*/0x0023/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0025/*::]*/: { n:\"NUMBER25\", f:parse_NUMBER_25 },\n\t\t/*::[*/0x0026/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0027/*::]*/: { n:\"NUMBER27\", f:parse_NUMBER_27 },\n\t\t/*::[*/0x0028/*::]*/: { n:\"FORMULA28\", f:parse_FORMULA_28 },\n\t\t/*::[*/0x008E/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0093/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0096/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0097/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0098/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0099/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x009A/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x009B/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x009C/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x00A3/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x00AE/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x00AF/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x00B0/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x00B1/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x00B8/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x00B9/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x00BA/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x00BB/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x00BC/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x00C3/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x00C9/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x00CC/*::]*/: { n:\"SHEETNAMECS\", f:parse_SHEETNAMECS },\n\t\t/*::[*/0x00CD/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x00CE/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x00CF/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x00D0/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0100/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0103/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0104/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0105/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0106/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0107/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0109/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x010A/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x010B/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x010C/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x010E/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x010F/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0180/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0185/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0186/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0189/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x018C/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0200/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0202/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0201/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0204/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0205/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0280/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0281/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0282/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0283/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0284/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0285/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0286/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0287/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0288/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0292/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0293/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0294/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0295/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0296/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0299/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x029A/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0300/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0304/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0601/*::]*/: { n:\"SHEETINFOQP\", f:parse_SHEETINFOQP },\n\t\t/*::[*/0x0640/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0642/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0701/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0702/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0703/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0704/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0780/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0800/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0801/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0804/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x0A80/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x2AF6/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x3231/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x6E49/*::]*/: { n:\"??\" },\n\t\t/*::[*/0x6F44/*::]*/: { n:\"??\" },\n\t\t/*::[*/0xFFFF/*::]*/: { n:\"\" }\n\t};\n\treturn {\n\t\tsheet_to_wk1: sheet_to_wk1,\n\t\tbook_to_wk3: book_to_wk3,\n\t\tto_workbook: lotus_to_workbook\n\t};\n})();\n/* 18.4.7 rPr CT_RPrElt */\nfunction parse_rpr(rpr) {\n\tvar font = {}, m = rpr.match(tagregex), i = 0;\n\tvar pass = false;\n\tif(m) for(;i!=m.length; ++i) {\n\t\tvar y = parsexmltag(m[i]);\n\t\tswitch(y[0].replace(/\\w*:/g,\"\")) {\n\t\t\t/* 18.8.12 condense CT_BooleanProperty */\n\t\t\t/* ** not required . */\n\t\t\tcase '<condense': break;\n\t\t\t/* 18.8.17 extend CT_BooleanProperty */\n\t\t\t/* ** not required . */\n\t\t\tcase '<extend': break;\n\t\t\t/* 18.8.36 shadow CT_BooleanProperty */\n\t\t\t/* ** not required . */\n\t\t\tcase '<shadow':\n\t\t\t\tif(!y.val) break;\n\t\t\t\t/* falls through */\n\t\t\tcase '<shadow>':\n\t\t\tcase '<shadow/>': font.shadow = 1; break;\n\t\t\tcase '</shadow>': break;\n\n\t\t\t/* 18.4.1 charset CT_IntProperty TODO */\n\t\t\tcase '<charset':\n\t\t\t\tif(y.val == '1') break;\n\t\t\t\tfont.cp = CS2CP[parseInt(y.val, 10)];\n\t\t\t\tbreak;\n\n\t\t\t/* 18.4.2 outline CT_BooleanProperty TODO */\n\t\t\tcase '<outline':\n\t\t\t\tif(!y.val) break;\n\t\t\t\t/* falls through */\n\t\t\tcase '<outline>':\n\t\t\tcase '<outline/>': font.outline = 1; break;\n\t\t\tcase '</outline>': break;\n\n\t\t\t/* 18.4.5 rFont CT_FontName */\n\t\t\tcase '<rFont': font.name = y.val; break;\n\n\t\t\t/* 18.4.11 sz CT_FontSize */\n\t\t\tcase '<sz': font.sz = y.val; break;\n\n\t\t\t/* 18.4.10 strike CT_BooleanProperty */\n\t\t\tcase '<strike':\n\t\t\t\tif(!y.val) break;\n\t\t\t\t/* falls through */\n\t\t\tcase '<strike>':\n\t\t\tcase '<strike/>': font.strike = 1; break;\n\t\t\tcase '</strike>': break;\n\n\t\t\t/* 18.4.13 u CT_UnderlineProperty */\n\t\t\tcase '<u':\n\t\t\t\tif(!y.val) break;\n\t\t\t\tswitch(y.val) {\n\t\t\t\t\tcase 'double': font.uval = \"double\"; break;\n\t\t\t\t\tcase 'singleAccounting': font.uval = \"single-accounting\"; break;\n\t\t\t\t\tcase 'doubleAccounting': font.uval = \"double-accounting\"; break;\n\t\t\t\t}\n\t\t\t\t/* falls through */\n\t\t\tcase '<u>':\n\t\t\tcase '<u/>': font.u = 1; break;\n\t\t\tcase '</u>': break;\n\n\t\t\t/* 18.8.2 b */\n\t\t\tcase '<b':\n\t\t\t\tif(y.val == '0') break;\n\t\t\t\t/* falls through */\n\t\t\tcase '<b>':\n\t\t\tcase '<b/>': font.b = 1; break;\n\t\t\tcase '</b>': break;\n\n\t\t\t/* 18.8.26 i */\n\t\t\tcase '<i':\n\t\t\t\tif(y.val == '0') break;\n\t\t\t\t/* falls through */\n\t\t\tcase '<i>':\n\t\t\tcase '<i/>': font.i = 1; break;\n\t\t\tcase '</i>': break;\n\n\t\t\t/* 18.3.1.15 color CT_Color TODO: tint, theme, auto, indexed */\n\t\t\tcase '<color':\n\t\t\t\tif(y.rgb) font.color = y.rgb.slice(2,8);\n\t\t\t\tbreak;\n\t\t\tcase '<color>': case '<color/>': case '</color>': break;\n\n\t\t\t/* 18.8.18 family ST_FontFamily */\n\t\t\tcase '<family': font.family = y.val; break;\n\t\t\tcase '<family>': case '<family/>': case '</family>': break;\n\n\t\t\t/* 18.4.14 vertAlign CT_VerticalAlignFontProperty TODO */\n\t\t\tcase '<vertAlign': font.valign = y.val; break;\n\t\t\tcase '<vertAlign>': case '<vertAlign/>': case '</vertAlign>': break;\n\n\t\t\t/* 18.8.35 scheme CT_FontScheme TODO */\n\t\t\tcase '<scheme': break;\n\t\t\tcase '<scheme>': case '<scheme/>': case '</scheme>': break;\n\n\t\t\t/* 18.2.10 extLst CT_ExtensionList ? */\n\t\t\tcase '<extLst': case '<extLst>': case '</extLst>': break;\n\t\t\tcase '<ext': pass = true; break;\n\t\t\tcase '</ext>': pass = false; break;\n\t\t\tdefault:\n\t\t\t\tif(y[0].charCodeAt(1) !== 47 && !pass) throw new Error('Unrecognized rich format ' + y[0]);\n\t\t}\n\t}\n\treturn font;\n}\n\nvar parse_rs = /*#__PURE__*/(function() {\n\tvar tregex = matchtag(\"t\"), rpregex = matchtag(\"rPr\");\n\t/* 18.4.4 r CT_RElt */\n\tfunction parse_r(r) {\n\t\t/* 18.4.12 t ST_Xstring */\n\t\tvar t = r.match(tregex)/*, cp = 65001*/;\n\t\tif(!t) return {t:\"s\", v:\"\"};\n\n\t\tvar o/*:Cell*/ = ({t:'s', v:unescapexml(t[1])}/*:any*/);\n\t\tvar rpr = r.match(rpregex);\n\t\tif(rpr) o.s = parse_rpr(rpr[1]);\n\t\treturn o;\n\t}\n\tvar rregex = /<(?:\\w+:)?r>/g, rend = /<\\/(?:\\w+:)?r>/;\n\treturn function parse_rs(rs) {\n\t\treturn rs.replace(rregex,\"\").split(rend).map(parse_r).filter(function(r) { return r.v; });\n\t};\n})();\n\n\n/* Parse a list of <r> tags */\nvar rs_to_html = /*#__PURE__*/(function parse_rs_factory() {\n\tvar nlregex = /(\\r\\n|\\n)/g;\n\tfunction parse_rpr2(font, intro, outro) {\n\t\tvar style/*:Array<string>*/ = [];\n\n\t\tif(font.u) style.push(\"text-decoration: underline;\");\n\t\tif(font.uval) style.push(\"text-underline-style:\" + font.uval + \";\");\n\t\tif(font.sz) style.push(\"font-size:\" + font.sz + \"pt;\");\n\t\tif(font.outline) style.push(\"text-effect: outline;\");\n\t\tif(font.shadow) style.push(\"text-shadow: auto;\");\n\t\tintro.push('<span style=\"' + style.join(\"\") + '\">');\n\n\t\tif(font.b) { intro.push(\"<b>\"); outro.push(\"</b>\"); }\n\t\tif(font.i) { intro.push(\"<i>\"); outro.push(\"</i>\"); }\n\t\tif(font.strike) { intro.push(\"<s>\"); outro.push(\"</s>\"); }\n\n\t\tvar align = font.valign || \"\";\n\t\tif(align == \"superscript\" || align == \"super\") align = \"sup\";\n\t\telse if(align == \"subscript\") align = \"sub\";\n\t\tif(align != \"\") { intro.push(\"<\" + align + \">\"); outro.push(\"</\" + align + \">\"); }\n\n\t\toutro.push(\"</span>\");\n\t\treturn font;\n\t}\n\n\t/* 18.4.4 r CT_RElt */\n\tfunction r_to_html(r) {\n\t\tvar terms/*:[Array<string>, string, Array<string>]*/ = [[],r.v,[]];\n\t\tif(!r.v) return \"\";\n\n\t\tif(r.s) parse_rpr2(r.s, terms[0], terms[2]);\n\n\t\treturn terms[0].join(\"\") + terms[1].replace(nlregex,'<br/>') + terms[2].join(\"\");\n\t}\n\n\treturn function parse_rs(rs) {\n\t\treturn rs.map(r_to_html).join(\"\");\n\t};\n})();\n\n/* 18.4.8 si CT_Rst */\nvar sitregex = /<(?:\\w+:)?t[^>]*>([^<]*)<\\/(?:\\w+:)?t>/g, sirregex = /<(?:\\w+:)?r>/;\nvar sirphregex = /<(?:\\w+:)?rPh.*?>([\\s\\S]*?)<\\/(?:\\w+:)?rPh>/g;\nfunction parse_si(x, opts) {\n\tvar html = opts ? opts.cellHTML : true;\n\tvar z = {};\n\tif(!x) return { t: \"\" };\n\t//var y;\n\t/* 18.4.12 t ST_Xstring (Plaintext String) */\n\t// TODO: is whitespace actually valid here?\n\tif(x.match(/^\\s*<(?:\\w+:)?t[^>]*>/)) {\n\t\tz.t = unescapexml(utf8read(x.slice(x.indexOf(\">\")+1).split(/<\\/(?:\\w+:)?t>/)[0]||\"\"));\n\t\tz.r = utf8read(x);\n\t\tif(html) z.h = escapehtml(z.t);\n\t}\n\t/* 18.4.4 r CT_RElt (Rich Text Run) */\n\telse if((/*y = */x.match(sirregex))) {\n\t\tz.r = utf8read(x);\n\t\tz.t = unescapexml(utf8read((x.replace(sirphregex, '').match(sitregex)||[]).join(\"\").replace(tagregex,\"\")));\n\t\tif(html) z.h = rs_to_html(parse_rs(z.r));\n\t}\n\t/* 18.4.3 phoneticPr CT_PhoneticPr (TODO: needed for Asian support) */\n\t/* 18.4.6 rPh CT_PhoneticRun (TODO: needed for Asian support) */\n\treturn z;\n}\n\n/* 18.4 Shared String Table */\nvar sstr0 = /<(?:\\w+:)?sst([^>]*)>([\\s\\S]*)<\\/(?:\\w+:)?sst>/;\nvar sstr1 = /<(?:\\w+:)?(?:si|sstItem)>/g;\nvar sstr2 = /<\\/(?:\\w+:)?(?:si|sstItem)>/;\nfunction parse_sst_xml(data/*:string*/, opts)/*:SST*/ {\n\tvar s/*:SST*/ = ([]/*:any*/), ss = \"\";\n\tif(!data) return s;\n\t/* 18.4.9 sst CT_Sst */\n\tvar sst = data.match(sstr0);\n\tif(sst) {\n\t\tss = sst[2].replace(sstr1,\"\").split(sstr2);\n\t\tfor(var i = 0; i != ss.length; ++i) {\n\t\t\tvar o = parse_si(ss[i].trim(), opts);\n\t\t\tif(o != null) s[s.length] = o;\n\t\t}\n\t\tsst = parsexmltag(sst[1]); s.Count = sst.count; s.Unique = sst.uniqueCount;\n\t}\n\treturn s;\n}\n\nvar straywsregex = /^\\s|\\s$|[\\t\\n\\r]/;\nfunction write_sst_xml(sst/*:SST*/, opts)/*:string*/ {\n\tif(!opts.bookSST) return \"\";\n\tvar o = [XML_HEADER];\n\to[o.length] = (writextag('sst', null, {\n\t\txmlns: XMLNS_main[0],\n\t\tcount: sst.Count,\n\t\tuniqueCount: sst.Unique\n\t}));\n\tfor(var i = 0; i != sst.length; ++i) { if(sst[i] == null) continue;\n\t\tvar s/*:XLString*/ = sst[i];\n\t\tvar sitag = \"<si>\";\n\t\tif(s.r) sitag += s.r;\n\t\telse {\n\t\t\tsitag += \"<t\";\n\t\t\tif(!s.t) s.t = \"\";\n\t\t\tif(s.t.match(straywsregex)) sitag += ' xml:space=\"preserve\"';\n\t\t\tsitag += \">\" + escapexml(s.t) + \"</t>\";\n\t\t}\n\t\tsitag += \"</si>\";\n\t\to[o.length] = (sitag);\n\t}\n\tif(o.length>2){ o[o.length] = ('</sst>'); o[1]=o[1].replace(\"/>\",\">\"); }\n\treturn o.join(\"\");\n}\n/* [MS-XLSB] 2.4.221 BrtBeginSst */\nfunction parse_BrtBeginSst(data) {\n\treturn [data.read_shift(4), data.read_shift(4)];\n}\n\n/* [MS-XLSB] 2.1.7.45 Shared Strings */\nfunction parse_sst_bin(data, opts)/*:SST*/ {\n\tvar s/*:SST*/ = ([]/*:any*/);\n\tvar pass = false;\n\trecordhopper(data, function hopper_sst(val, R, RT) {\n\t\tswitch(RT) {\n\t\t\tcase 0x009F: /* BrtBeginSst */\n\t\t\t\ts.Count = val[0]; s.Unique = val[1]; break;\n\t\t\tcase 0x0013: /* BrtSSTItem */\n\t\t\t\ts.push(val); break;\n\t\t\tcase 0x00A0: /* BrtEndSst */\n\t\t\t\treturn true;\n\n\t\t\tcase 0x0023: /* BrtFRTBegin */\n\t\t\t\tpass = true; break;\n\t\t\tcase 0x0024: /* BrtFRTEnd */\n\t\t\t\tpass = false; break;\n\n\t\t\tdefault:\n\t\t\t\tif(R.T){}\n\t\t\t\tif(!pass || opts.WTF) throw new Error(\"Unexpected record 0x\" + RT.toString(16));\n\t\t}\n\t});\n\treturn s;\n}\n\nfunction write_BrtBeginSst(sst, o) {\n\tif(!o) o = new_buf(8);\n\to.write_shift(4, sst.Count);\n\to.write_shift(4, sst.Unique);\n\treturn o;\n}\n\nvar write_BrtSSTItem = write_RichStr;\n\nfunction write_sst_bin(sst/*::, opts*/) {\n\tvar ba = buf_array();\n\twrite_record(ba, 0x009F /* BrtBeginSst */, write_BrtBeginSst(sst));\n\tfor(var i = 0; i < sst.length; ++i) write_record(ba, 0x0013 /* BrtSSTItem */, write_BrtSSTItem(sst[i]));\n\t/* FRTSST */\n\twrite_record(ba, 0x00A0 /* BrtEndSst */);\n\treturn ba.end();\n}\nfunction _JS2ANSI(str/*:string*/)/*:Array<number>*/ {\n\tif(typeof $cptable !== 'undefined') return $cptable.utils.encode(current_ansi, str);\n\tvar o/*:Array<number>*/ = [], oo = str.split(\"\");\n\tfor(var i = 0; i < oo.length; ++i) o[i] = oo[i].charCodeAt(0);\n\treturn o;\n}\n\n/* [MS-OFFCRYPTO] 2.1.4 Version */\nfunction parse_CRYPTOVersion(blob, length/*:?number*/) {\n\tvar o/*:any*/ = {};\n\to.Major = blob.read_shift(2);\n\to.Minor = blob.read_shift(2);\n\t/*:: if(length == null) return o; */\n\tif(length >= 4) blob.l += length - 4;\n\treturn o;\n}\n\n/* [MS-OFFCRYPTO] 2.1.5 DataSpaceVersionInfo */\nfunction parse_DataSpaceVersionInfo(blob) {\n\tvar o = {};\n\to.id = blob.read_shift(0, 'lpp4');\n\to.R = parse_CRYPTOVersion(blob, 4);\n\to.U = parse_CRYPTOVersion(blob, 4);\n\to.W = parse_CRYPTOVersion(blob, 4);\n\treturn o;\n}\n\n/* [MS-OFFCRYPTO] 2.1.6.1 DataSpaceMapEntry Structure */\nfunction parse_DataSpaceMapEntry(blob) {\n\tvar len = blob.read_shift(4);\n\tvar end = blob.l + len - 4;\n\tvar o = {};\n\tvar cnt = blob.read_shift(4);\n\tvar comps/*:Array<{t:number, v:string}>*/ = [];\n\t/* [MS-OFFCRYPTO] 2.1.6.2 DataSpaceReferenceComponent Structure */\n\twhile(cnt-- > 0) comps.push({ t: blob.read_shift(4), v: blob.read_shift(0, 'lpp4') });\n\to.name = blob.read_shift(0, 'lpp4');\n\to.comps = comps;\n\tif(blob.l != end) throw new Error(\"Bad DataSpaceMapEntry: \" + blob.l + \" != \" + end);\n\treturn o;\n}\n\n/* [MS-OFFCRYPTO] 2.1.6 DataSpaceMap */\nfunction parse_DataSpaceMap(blob) {\n\tvar o = [];\n\tblob.l += 4; // must be 0x8\n\tvar cnt = blob.read_shift(4);\n\twhile(cnt-- > 0) o.push(parse_DataSpaceMapEntry(blob));\n\treturn o;\n}\n\n/* [MS-OFFCRYPTO] 2.1.7 DataSpaceDefinition */\nfunction parse_DataSpaceDefinition(blob)/*:Array<string>*/ {\n\tvar o/*:Array<string>*/ = [];\n\tblob.l += 4; // must be 0x8\n\tvar cnt = blob.read_shift(4);\n\twhile(cnt-- > 0) o.push(blob.read_shift(0, 'lpp4'));\n\treturn o;\n}\n\n/* [MS-OFFCRYPTO] 2.1.8 DataSpaceDefinition */\nfunction parse_TransformInfoHeader(blob) {\n\tvar o = {};\n\t/*var len = */blob.read_shift(4);\n\tblob.l += 4; // must be 0x1\n\to.id = blob.read_shift(0, 'lpp4');\n\to.name = blob.read_shift(0, 'lpp4');\n\to.R = parse_CRYPTOVersion(blob, 4);\n\to.U = parse_CRYPTOVersion(blob, 4);\n\to.W = parse_CRYPTOVersion(blob, 4);\n\treturn o;\n}\n\nfunction parse_Primary(blob) {\n\t/* [MS-OFFCRYPTO] 2.2.6 IRMDSTransformInfo */\n\tvar hdr = parse_TransformInfoHeader(blob);\n\t/* [MS-OFFCRYPTO] 2.1.9 EncryptionTransformInfo */\n\thdr.ename = blob.read_shift(0, '8lpp4');\n\thdr.blksz = blob.read_shift(4);\n\thdr.cmode = blob.read_shift(4);\n\tif(blob.read_shift(4) != 0x04) throw new Error(\"Bad !Primary record\");\n\treturn hdr;\n}\n\n/* [MS-OFFCRYPTO] 2.3.2 Encryption Header */\nfunction parse_EncryptionHeader(blob, length/*:number*/) {\n\tvar tgt = blob.l + length;\n\tvar o = {};\n\to.Flags = (blob.read_shift(4) & 0x3F);\n\tblob.l += 4;\n\to.AlgID = blob.read_shift(4);\n\tvar valid = false;\n\tswitch(o.AlgID) {\n\t\tcase 0x660E: case 0x660F: case 0x6610: valid = (o.Flags == 0x24); break;\n\t\tcase 0x6801: valid = (o.Flags == 0x04); break;\n\t\tcase 0: valid = (o.Flags == 0x10 || o.Flags == 0x04 || o.Flags == 0x24); break;\n\t\tdefault: throw 'Unrecognized encryption algorithm: ' + o.AlgID;\n\t}\n\tif(!valid) throw new Error(\"Encryption Flags/AlgID mismatch\");\n\to.AlgIDHash = blob.read_shift(4);\n\to.KeySize = blob.read_shift(4);\n\to.ProviderType = blob.read_shift(4);\n\tblob.l += 8;\n\to.CSPName = blob.read_shift((tgt-blob.l)>>1, 'utf16le');\n\tblob.l = tgt;\n\treturn o;\n}\n\n/* [MS-OFFCRYPTO] 2.3.3 Encryption Verifier */\nfunction parse_EncryptionVerifier(blob, length/*:number*/) {\n\tvar o = {}, tgt = blob.l + length;\n\tblob.l += 4; // SaltSize must be 0x10\n\to.Salt = blob.slice(blob.l, blob.l+16); blob.l += 16;\n\to.Verifier = blob.slice(blob.l, blob.l+16); blob.l += 16;\n\t/*var sz = */blob.read_shift(4);\n\to.VerifierHash = blob.slice(blob.l, tgt); blob.l = tgt;\n\treturn o;\n}\n\n/* [MS-OFFCRYPTO] 2.3.4.* EncryptionInfo Stream */\nfunction parse_EncryptionInfo(blob) {\n\tvar vers = parse_CRYPTOVersion(blob);\n\tswitch(vers.Minor) {\n\t\tcase 0x02: return [vers.Minor, parse_EncInfoStd(blob, vers)];\n\t\tcase 0x03: return [vers.Minor, parse_EncInfoExt(blob, vers)];\n\t\tcase 0x04: return [vers.Minor, parse_EncInfoAgl(blob, vers)];\n\t}\n\tthrow new Error(\"ECMA-376 Encrypted file unrecognized Version: \" + vers.Minor);\n}\n\n/* [MS-OFFCRYPTO] 2.3.4.5  EncryptionInfo Stream (Standard Encryption) */\nfunction parse_EncInfoStd(blob/*::, vers*/) {\n\tvar flags = blob.read_shift(4);\n\tif((flags & 0x3F) != 0x24) throw new Error(\"EncryptionInfo mismatch\");\n\tvar sz = blob.read_shift(4);\n\t//var tgt = blob.l + sz;\n\tvar hdr = parse_EncryptionHeader(blob, sz);\n\tvar verifier = parse_EncryptionVerifier(blob, blob.length - blob.l);\n\treturn { t:\"Std\", h:hdr, v:verifier };\n}\n/* [MS-OFFCRYPTO] 2.3.4.6  EncryptionInfo Stream (Extensible Encryption) */\nfunction parse_EncInfoExt(/*::blob, vers*/) { throw new Error(\"File is password-protected: ECMA-376 Extensible\"); }\n/* [MS-OFFCRYPTO] 2.3.4.10 EncryptionInfo Stream (Agile Encryption) */\nfunction parse_EncInfoAgl(blob/*::, vers*/) {\n\tvar KeyData = [\"saltSize\",\"blockSize\",\"keyBits\",\"hashSize\",\"cipherAlgorithm\",\"cipherChaining\",\"hashAlgorithm\",\"saltValue\"];\n\tblob.l+=4;\n\tvar xml = blob.read_shift(blob.length - blob.l, 'utf8');\n\tvar o = {};\n\txml.replace(tagregex, function xml_agile(x) {\n\t\tvar y/*:any*/ = parsexmltag(x);\n\t\tswitch(strip_ns(y[0])) {\n\t\t\tcase '<?xml': break;\n\t\t\tcase '<encryption': case '</encryption>': break;\n\t\t\tcase '<keyData': KeyData.forEach(function(k) { o[k] = y[k]; }); break;\n\t\t\tcase '<dataIntegrity': o.encryptedHmacKey = y.encryptedHmacKey; o.encryptedHmacValue = y.encryptedHmacValue; break;\n\t\t\tcase '<keyEncryptors>': case '<keyEncryptors': o.encs = []; break;\n\t\t\tcase '</keyEncryptors>': break;\n\n\t\t\tcase '<keyEncryptor': o.uri = y.uri; break;\n\t\t\tcase '</keyEncryptor>': break;\n\t\t\tcase '<encryptedKey': o.encs.push(y); break;\n\t\t\tdefault: throw y[0];\n\t\t}\n\t});\n\treturn o;\n}\n\n/* [MS-OFFCRYPTO] 2.3.5.1 RC4 CryptoAPI Encryption Header */\nfunction parse_RC4CryptoHeader(blob, length/*:number*/) {\n\tvar o = {};\n\tvar vers = o.EncryptionVersionInfo = parse_CRYPTOVersion(blob, 4); length -= 4;\n\tif(vers.Minor != 2) throw new Error('unrecognized minor version code: ' + vers.Minor);\n\tif(vers.Major > 4 || vers.Major < 2) throw new Error('unrecognized major version code: ' + vers.Major);\n\to.Flags = blob.read_shift(4); length -= 4;\n\tvar sz = blob.read_shift(4); length -= 4;\n\to.EncryptionHeader = parse_EncryptionHeader(blob, sz); length -= sz;\n\to.EncryptionVerifier = parse_EncryptionVerifier(blob, length);\n\treturn o;\n}\n/* [MS-OFFCRYPTO] 2.3.6.1 RC4 Encryption Header */\nfunction parse_RC4Header(blob/*::, length*/) {\n\tvar o = {};\n\tvar vers = o.EncryptionVersionInfo = parse_CRYPTOVersion(blob, 4);\n\tif(vers.Major != 1 || vers.Minor != 1) throw 'unrecognized version code ' + vers.Major + ' : ' + vers.Minor;\n\to.Salt = blob.read_shift(16);\n\to.EncryptedVerifier = blob.read_shift(16);\n\to.EncryptedVerifierHash = blob.read_shift(16);\n\treturn o;\n}\n\n/* [MS-OFFCRYPTO] 2.3.7.1 Binary Document Password Verifier Derivation */\nfunction crypto_CreatePasswordVerifier_Method1(Password/*:string*/) {\n\tvar Verifier = 0x0000, PasswordArray;\n\tvar PasswordDecoded = _JS2ANSI(Password);\n\tvar len = PasswordDecoded.length + 1, i, PasswordByte;\n\tvar Intermediate1, Intermediate2, Intermediate3;\n\tPasswordArray = new_raw_buf(len);\n\tPasswordArray[0] = PasswordDecoded.length;\n\tfor(i = 1; i != len; ++i) PasswordArray[i] = PasswordDecoded[i-1];\n\tfor(i = len-1; i >= 0; --i) {\n\t\tPasswordByte = PasswordArray[i];\n\t\tIntermediate1 = ((Verifier & 0x4000) === 0x0000) ? 0 : 1;\n\t\tIntermediate2 = (Verifier << 1) & 0x7FFF;\n\t\tIntermediate3 = Intermediate1 | Intermediate2;\n\t\tVerifier = Intermediate3 ^ PasswordByte;\n\t}\n\treturn Verifier ^ 0xCE4B;\n}\n\n/* [MS-OFFCRYPTO] 2.3.7.2 Binary Document XOR Array Initialization */\nvar crypto_CreateXorArray_Method1 = /*#__PURE__*/(function() {\n\tvar PadArray = [0xBB, 0xFF, 0xFF, 0xBA, 0xFF, 0xFF, 0xB9, 0x80, 0x00, 0xBE, 0x0F, 0x00, 0xBF, 0x0F, 0x00];\n\tvar InitialCode = [0xE1F0, 0x1D0F, 0xCC9C, 0x84C0, 0x110C, 0x0E10, 0xF1CE, 0x313E, 0x1872, 0xE139, 0xD40F, 0x84F9, 0x280C, 0xA96A, 0x4EC3];\n\tvar XorMatrix = [0xAEFC, 0x4DD9, 0x9BB2, 0x2745, 0x4E8A, 0x9D14, 0x2A09, 0x7B61, 0xF6C2, 0xFDA5, 0xEB6B, 0xC6F7, 0x9DCF, 0x2BBF, 0x4563, 0x8AC6, 0x05AD, 0x0B5A, 0x16B4, 0x2D68, 0x5AD0, 0x0375, 0x06EA, 0x0DD4, 0x1BA8, 0x3750, 0x6EA0, 0xDD40, 0xD849, 0xA0B3, 0x5147, 0xA28E, 0x553D, 0xAA7A, 0x44D5, 0x6F45, 0xDE8A, 0xAD35, 0x4A4B, 0x9496, 0x390D, 0x721A, 0xEB23, 0xC667, 0x9CEF, 0x29FF, 0x53FE, 0xA7FC, 0x5FD9, 0x47D3, 0x8FA6, 0x0F6D, 0x1EDA, 0x3DB4, 0x7B68, 0xF6D0, 0xB861, 0x60E3, 0xC1C6, 0x93AD, 0x377B, 0x6EF6, 0xDDEC, 0x45A0, 0x8B40, 0x06A1, 0x0D42, 0x1A84, 0x3508, 0x6A10, 0xAA51, 0x4483, 0x8906, 0x022D, 0x045A, 0x08B4, 0x1168, 0x76B4, 0xED68, 0xCAF1, 0x85C3, 0x1BA7, 0x374E, 0x6E9C, 0x3730, 0x6E60, 0xDCC0, 0xA9A1, 0x4363, 0x86C6, 0x1DAD, 0x3331, 0x6662, 0xCCC4, 0x89A9, 0x0373, 0x06E6, 0x0DCC, 0x1021, 0x2042, 0x4084, 0x8108, 0x1231, 0x2462, 0x48C4];\n\tvar Ror = function(Byte) { return ((Byte/2) | (Byte*128)) & 0xFF; };\n\tvar XorRor = function(byte1, byte2) { return Ror(byte1 ^ byte2); };\n\tvar CreateXorKey_Method1 = function(Password) {\n\t\tvar XorKey = InitialCode[Password.length - 1];\n\t\tvar CurrentElement = 0x68;\n\t\tfor(var i = Password.length-1; i >= 0; --i) {\n\t\t\tvar Char = Password[i];\n\t\t\tfor(var j = 0; j != 7; ++j) {\n\t\t\t\tif(Char & 0x40) XorKey ^= XorMatrix[CurrentElement];\n\t\t\t\tChar *= 2; --CurrentElement;\n\t\t\t}\n\t\t}\n\t\treturn XorKey;\n\t};\n\treturn function(password/*:string*/) {\n\t\tvar Password = _JS2ANSI(password);\n\t\tvar XorKey = CreateXorKey_Method1(Password);\n\t\tvar Index = Password.length;\n\t\tvar ObfuscationArray = new_raw_buf(16);\n\t\tfor(var i = 0; i != 16; ++i) ObfuscationArray[i] = 0x00;\n\t\tvar Temp, PasswordLastChar, PadIndex;\n\t\tif((Index & 1) === 1) {\n\t\t\tTemp = XorKey >> 8;\n\t\t\tObfuscationArray[Index] = XorRor(PadArray[0], Temp);\n\t\t\t--Index;\n\t\t\tTemp = XorKey & 0xFF;\n\t\t\tPasswordLastChar = Password[Password.length - 1];\n\t\t\tObfuscationArray[Index] = XorRor(PasswordLastChar, Temp);\n\t\t}\n\t\twhile(Index > 0) {\n\t\t\t--Index;\n\t\t\tTemp = XorKey >> 8;\n\t\t\tObfuscationArray[Index] = XorRor(Password[Index], Temp);\n\t\t\t--Index;\n\t\t\tTemp = XorKey & 0xFF;\n\t\t\tObfuscationArray[Index] = XorRor(Password[Index], Temp);\n\t\t}\n\t\tIndex = 15;\n\t\tPadIndex = 15 - Password.length;\n\t\twhile(PadIndex > 0) {\n\t\t\tTemp = XorKey >> 8;\n\t\t\tObfuscationArray[Index] = XorRor(PadArray[PadIndex], Temp);\n\t\t\t--Index;\n\t\t\t--PadIndex;\n\t\t\tTemp = XorKey & 0xFF;\n\t\t\tObfuscationArray[Index] = XorRor(Password[Index], Temp);\n\t\t\t--Index;\n\t\t\t--PadIndex;\n\t\t}\n\t\treturn ObfuscationArray;\n\t};\n})();\n\n/* [MS-OFFCRYPTO] 2.3.7.3 Binary Document XOR Data Transformation Method 1 */\nvar crypto_DecryptData_Method1 = function(password/*:string*/, Data, XorArrayIndex, XorArray, O) {\n\t/* If XorArray is set, use it; if O is not set, make changes in-place */\n\tif(!O) O = Data;\n\tif(!XorArray) XorArray = crypto_CreateXorArray_Method1(password);\n\tvar Index, Value;\n\tfor(Index = 0; Index != Data.length; ++Index) {\n\t\tValue = Data[Index];\n\t\tValue ^= XorArray[XorArrayIndex];\n\t\tValue = ((Value>>5) | (Value<<3)) & 0xFF;\n\t\tO[Index] = Value;\n\t\t++XorArrayIndex;\n\t}\n\treturn [O, XorArrayIndex, XorArray];\n};\n\nvar crypto_MakeXorDecryptor = function(password/*:string*/) {\n\tvar XorArrayIndex = 0, XorArray = crypto_CreateXorArray_Method1(password);\n\treturn function(Data) {\n\t\tvar O = crypto_DecryptData_Method1(\"\", Data, XorArrayIndex, XorArray);\n\t\tXorArrayIndex = O[1];\n\t\treturn O[0];\n\t};\n};\n\n/* 2.5.343 */\nfunction parse_XORObfuscation(blob, length, opts, out) {\n\tvar o = ({ key: parseuint16(blob), verificationBytes: parseuint16(blob) }/*:any*/);\n\tif(opts.password) o.verifier = crypto_CreatePasswordVerifier_Method1(opts.password);\n\tout.valid = o.verificationBytes === o.verifier;\n\tif(out.valid) out.insitu = crypto_MakeXorDecryptor(opts.password);\n\treturn o;\n}\n\n/* 2.4.117 */\nfunction parse_FilePassHeader(blob, length/*:number*/, oo) {\n\tvar o = oo || {}; o.Info = blob.read_shift(2); blob.l -= 2;\n\tif(o.Info === 1) o.Data = parse_RC4Header(blob, length);\n\telse o.Data = parse_RC4CryptoHeader(blob, length);\n\treturn o;\n}\nfunction parse_FilePass(blob, length/*:number*/, opts) {\n\tvar o = ({ Type: opts.biff >= 8 ? blob.read_shift(2) : 0 }/*:any*/); /* wEncryptionType */\n\tif(o.Type) parse_FilePassHeader(blob, length-2, o);\n\telse parse_XORObfuscation(blob, opts.biff >= 8 ? length : length - 2, opts, o);\n\treturn o;\n}\n\n\nvar RTF = /*#__PURE__*/(function() {\n\tfunction rtf_to_sheet(d/*:RawData*/, opts)/*:Worksheet*/ {\n\t\tswitch(opts.type) {\n\t\t\tcase 'base64': return rtf_to_sheet_str(Base64_decode(d), opts);\n\t\t\tcase 'binary': return rtf_to_sheet_str(d, opts);\n\t\t\tcase 'buffer': return rtf_to_sheet_str(has_buf && Buffer.isBuffer(d) ? d.toString('binary') : a2s(d), opts);\n\t\t\tcase 'array':  return rtf_to_sheet_str(cc2str(d), opts);\n\t\t}\n\t\tthrow new Error(\"Unrecognized type \" + opts.type);\n\t}\n\n\t/* TODO: this is a stub */\n\tfunction rtf_to_sheet_str(str/*:string*/, opts)/*:Worksheet*/ {\n\t\tvar o = opts || {};\n\t\tvar ws/*:Worksheet*/ = o.dense ? ([]/*:any*/) : ({}/*:any*/);\n\n\t\tvar rows = str.match(/\\\\trowd.*?\\\\row\\b/g);\n\t\tif(!rows.length) throw new Error(\"RTF missing table\");\n\t\tvar range/*:Range*/ = ({s: {c:0, r:0}, e: {c:0, r:rows.length - 1}}/*:any*/);\n\t\trows.forEach(function(rowtf, R) {\n\t\t\tif(Array.isArray(ws)) ws[R] = [];\n\t\t\tvar rtfre = /\\\\\\w+\\b/g;\n\t\t\tvar last_index = 0;\n\t\t\tvar res;\n\t\t\tvar C = -1;\n\t\t\twhile((res = rtfre.exec(rowtf))) {\n\t\t\t\tswitch(res[0]) {\n\t\t\t\t\tcase \"\\\\cell\":\n\t\t\t\t\t\tvar data = rowtf.slice(last_index, rtfre.lastIndex - res[0].length);\n\t\t\t\t\t\tif(data[0] == \" \") data = data.slice(1);\n\t\t\t\t\t\t++C;\n\t\t\t\t\t\tif(data.length) {\n\t\t\t\t\t\t\t// TODO: value parsing, including codepage adjustments\n\t\t\t\t\t\t\tvar cell = {v: data, t:\"s\"};\n\t\t\t\t\t\t\tif(Array.isArray(ws)) ws[R][C] = cell;\n\t\t\t\t\t\t\telse ws[encode_cell({r:R, c:C})] = cell;\n\t\t\t\t\t\t}\n\t\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\tlast_index = rtfre.lastIndex;\n\t\t\t}\n\t\t\tif(C > range.e.c) range.e.c = C;\n\t\t});\n\t\tws['!ref'] = encode_range(range);\n\t\treturn ws;\n\t}\n\n\tfunction rtf_to_workbook(d/*:RawData*/, opts)/*:Workbook*/ { return sheet_to_workbook(rtf_to_sheet(d, opts), opts); }\n\n\t/* TODO: this is a stub */\n\tfunction sheet_to_rtf(ws/*:Worksheet*//*::, opts*/)/*:string*/ {\n\t\tvar o = [\"{\\\\rtf1\\\\ansi\"];\n\t\tvar r = safe_decode_range(ws['!ref']), cell/*:Cell*/;\n\t\tvar dense = Array.isArray(ws);\n\t\tfor(var R = r.s.r; R <= r.e.r; ++R) {\n\t\t\to.push(\"\\\\trowd\\\\trautofit1\");\n\t\t\tfor(var C = r.s.c; C <= r.e.c; ++C) o.push(\"\\\\cellx\" + (C+1));\n\t\t\to.push(\"\\\\pard\\\\intbl\");\n\t\t\tfor(C = r.s.c; C <= r.e.c; ++C) {\n\t\t\t\tvar coord = encode_cell({r:R,c:C});\n\t\t\t\tcell = dense ? (ws[R]||[])[C]: ws[coord];\n\t\t\t\tif(!cell || cell.v == null && (!cell.f || cell.F)) continue;\n\t\t\t\to.push(\" \" + (cell.w || (format_cell(cell), cell.w)));\n\t\t\t\to.push(\"\\\\cell\");\n\t\t\t}\n\t\t\to.push(\"\\\\pard\\\\intbl\\\\row\");\n\t\t}\n\t\treturn o.join(\"\") + \"}\";\n\t}\n\n\treturn {\n\t\tto_workbook: rtf_to_workbook,\n\t\tto_sheet: rtf_to_sheet,\n\t\tfrom_sheet: sheet_to_rtf\n\t};\n})();\nfunction hex2RGB(h) {\n\tvar o = h.slice(h[0]===\"#\"?1:0).slice(0,6);\n\treturn [parseInt(o.slice(0,2),16),parseInt(o.slice(2,4),16),parseInt(o.slice(4,6),16)];\n}\nfunction rgb2Hex(rgb) {\n\tfor(var i=0,o=1; i!=3; ++i) o = o*256 + (rgb[i]>255?255:rgb[i]<0?0:rgb[i]);\n\treturn o.toString(16).toUpperCase().slice(1);\n}\n\nfunction rgb2HSL(rgb) {\n\tvar R = rgb[0]/255, G = rgb[1]/255, B=rgb[2]/255;\n\tvar M = Math.max(R, G, B), m = Math.min(R, G, B), C = M - m;\n\tif(C === 0) return [0, 0, R];\n\n\tvar H6 = 0, S = 0, L2 = (M + m);\n\tS = C / (L2 > 1 ? 2 - L2 : L2);\n\tswitch(M){\n\t\tcase R: H6 = ((G - B) / C + 6)%6; break;\n\t\tcase G: H6 = ((B - R) / C + 2); break;\n\t\tcase B: H6 = ((R - G) / C + 4); break;\n\t}\n\treturn [H6 / 6, S, L2 / 2];\n}\n\nfunction hsl2RGB(hsl){\n\tvar H = hsl[0], S = hsl[1], L = hsl[2];\n\tvar C = S * 2 * (L < 0.5 ? L : 1 - L), m = L - C/2;\n\tvar rgb = [m,m,m], h6 = 6*H;\n\n\tvar X;\n\tif(S !== 0) switch(h6|0) {\n\t\tcase 0: case 6: X = C * h6; rgb[0] += C; rgb[1] += X; break;\n\t\tcase 1: X = C * (2 - h6);   rgb[0] += X; rgb[1] += C; break;\n\t\tcase 2: X = C * (h6 - 2);   rgb[1] += C; rgb[2] += X; break;\n\t\tcase 3: X = C * (4 - h6);   rgb[1] += X; rgb[2] += C; break;\n\t\tcase 4: X = C * (h6 - 4);   rgb[2] += C; rgb[0] += X; break;\n\t\tcase 5: X = C * (6 - h6);   rgb[2] += X; rgb[0] += C; break;\n\t}\n\tfor(var i = 0; i != 3; ++i) rgb[i] = Math.round(rgb[i]*255);\n\treturn rgb;\n}\n\n/* 18.8.3 bgColor tint algorithm */\nfunction rgb_tint(hex, tint) {\n\tif(tint === 0) return hex;\n\tvar hsl = rgb2HSL(hex2RGB(hex));\n\tif (tint < 0) hsl[2] = hsl[2] * (1 + tint);\n\telse hsl[2] = 1 - (1 - hsl[2]) * (1 - tint);\n\treturn rgb2Hex(hsl2RGB(hsl));\n}\n\n/* 18.3.1.13 width calculations */\n/* [MS-OI29500] 2.1.595 Column Width & Formatting */\nvar DEF_MDW = 6, MAX_MDW = 15, MIN_MDW = 1, MDW = DEF_MDW;\nfunction width2px(width) { return Math.floor(( width + (Math.round(128/MDW))/256 )* MDW ); }\nfunction px2char(px) { return (Math.floor((px - 5)/MDW * 100 + 0.5))/100; }\nfunction char2width(chr) { return (Math.round((chr * MDW + 5)/MDW*256))/256; }\n//function px2char_(px) { return (((px - 5)/MDW * 100 + 0.5))/100; }\n//function char2width_(chr) { return (((chr * MDW + 5)/MDW*256))/256; }\nfunction cycle_width(collw) { return char2width(px2char(width2px(collw))); }\n/* XLSX/XLSB/XLS specify width in units of MDW */\nfunction find_mdw_colw(collw) {\n\tvar delta = Math.abs(collw - cycle_width(collw)), _MDW = MDW;\n\tif(delta > 0.005) for(MDW=MIN_MDW; MDW<MAX_MDW; ++MDW) if(Math.abs(collw - cycle_width(collw)) <= delta) { delta = Math.abs(collw - cycle_width(collw)); _MDW = MDW; }\n\tMDW = _MDW;\n}\n/* XLML specifies width in terms of pixels */\n/*function find_mdw_wpx(wpx) {\n\tvar delta = Infinity, guess = 0, _MDW = MIN_MDW;\n\tfor(MDW=MIN_MDW; MDW<MAX_MDW; ++MDW) {\n\t\tguess = char2width_(px2char_(wpx))*256;\n\t\tguess = (guess) % 1;\n\t\tif(guess > 0.5) guess--;\n\t\tif(Math.abs(guess) < delta) { delta = Math.abs(guess); _MDW = MDW; }\n\t}\n\tMDW = _MDW;\n}*/\n\nfunction process_col(coll/*:ColInfo*/) {\n\tif(coll.width) {\n\t\tcoll.wpx = width2px(coll.width);\n\t\tcoll.wch = px2char(coll.wpx);\n\t\tcoll.MDW = MDW;\n\t} else if(coll.wpx) {\n\t\tcoll.wch = px2char(coll.wpx);\n\t\tcoll.width = char2width(coll.wch);\n\t\tcoll.MDW = MDW;\n\t} else if(typeof coll.wch == 'number') {\n\t\tcoll.width = char2width(coll.wch);\n\t\tcoll.wpx = width2px(coll.width);\n\t\tcoll.MDW = MDW;\n\t}\n\tif(coll.customWidth) delete coll.customWidth;\n}\n\nvar DEF_PPI = 96, PPI = DEF_PPI;\nfunction px2pt(px) { return px * 96 / PPI; }\nfunction pt2px(pt) { return pt * PPI / 96; }\n\n/* [MS-EXSPXML3] 2.4.54 ST_enmPattern */\nvar XLMLPatternTypeMap = {\n\t\"None\": \"none\",\n\t\"Solid\": \"solid\",\n\t\"Gray50\": \"mediumGray\",\n\t\"Gray75\": \"darkGray\",\n\t\"Gray25\": \"lightGray\",\n\t\"HorzStripe\": \"darkHorizontal\",\n\t\"VertStripe\": \"darkVertical\",\n\t\"ReverseDiagStripe\": \"darkDown\",\n\t\"DiagStripe\": \"darkUp\",\n\t\"DiagCross\": \"darkGrid\",\n\t\"ThickDiagCross\": \"darkTrellis\",\n\t\"ThinHorzStripe\": \"lightHorizontal\",\n\t\"ThinVertStripe\": \"lightVertical\",\n\t\"ThinReverseDiagStripe\": \"lightDown\",\n\t\"ThinHorzCross\": \"lightGrid\"\n};\n\n/* 18.8.5 borders CT_Borders */\nfunction parse_borders(t, styles, themes, opts) {\n\tstyles.Borders = [];\n\tvar border = {};\n\tvar pass = false;\n\t(t[0].match(tagregex)||[]).forEach(function(x) {\n\t\tvar y = parsexmltag(x);\n\t\tswitch(strip_ns(y[0])) {\n\t\t\tcase '<borders': case '<borders>': case '</borders>': break;\n\n\t\t\t/* 18.8.4 border CT_Border */\n\t\t\tcase '<border': case '<border>': case '<border/>':\n\t\t\t\tborder = /*::(*/{}/*:: :any)*/;\n\t\t\t\tif(y.diagonalUp) border.diagonalUp = parsexmlbool(y.diagonalUp);\n\t\t\t\tif(y.diagonalDown) border.diagonalDown = parsexmlbool(y.diagonalDown);\n\t\t\t\tstyles.Borders.push(border);\n\t\t\t\tbreak;\n\t\t\tcase '</border>': break;\n\n\t\t\t/* note: not in spec, appears to be CT_BorderPr */\n\t\t\tcase '<left/>': break;\n\t\t\tcase '<left': case '<left>': break;\n\t\t\tcase '</left>': break;\n\n\t\t\t/* note: not in spec, appears to be CT_BorderPr */\n\t\t\tcase '<right/>': break;\n\t\t\tcase '<right': case '<right>': break;\n\t\t\tcase '</right>': break;\n\n\t\t\t/* 18.8.43 top CT_BorderPr */\n\t\t\tcase '<top/>': break;\n\t\t\tcase '<top': case '<top>': break;\n\t\t\tcase '</top>': break;\n\n\t\t\t/* 18.8.6 bottom CT_BorderPr */\n\t\t\tcase '<bottom/>': break;\n\t\t\tcase '<bottom': case '<bottom>': break;\n\t\t\tcase '</bottom>': break;\n\n\t\t\t/* 18.8.13 diagonal CT_BorderPr */\n\t\t\tcase '<diagonal': case '<diagonal>': case '<diagonal/>': break;\n\t\t\tcase '</diagonal>': break;\n\n\t\t\t/* 18.8.25 horizontal CT_BorderPr */\n\t\t\tcase '<horizontal': case '<horizontal>': case '<horizontal/>': break;\n\t\t\tcase '</horizontal>': break;\n\n\t\t\t/* 18.8.44 vertical CT_BorderPr */\n\t\t\tcase '<vertical': case '<vertical>': case '<vertical/>': break;\n\t\t\tcase '</vertical>': break;\n\n\t\t\t/* 18.8.37 start CT_BorderPr */\n\t\t\tcase '<start': case '<start>': case '<start/>': break;\n\t\t\tcase '</start>': break;\n\n\t\t\t/* 18.8.16 end CT_BorderPr */\n\t\t\tcase '<end': case '<end>': case '<end/>': break;\n\t\t\tcase '</end>': break;\n\n\t\t\t/* 18.8.? color CT_Color */\n\t\t\tcase '<color': case '<color>':\n\t\t\t\tbreak;\n\t\t\tcase '<color/>': case '</color>': break;\n\n\t\t\t/* 18.2.10 extLst CT_ExtensionList ? */\n\t\t\tcase '<extLst': case '<extLst>': case '</extLst>': break;\n\t\t\tcase '<ext': pass = true; break;\n\t\t\tcase '</ext>': pass = false; break;\n\t\t\tdefault: if(opts && opts.WTF) {\n\t\t\t\tif(!pass) throw new Error('unrecognized ' + y[0] + ' in borders');\n\t\t\t}\n\t\t}\n\t});\n}\n\n/* 18.8.21 fills CT_Fills */\nfunction parse_fills(t, styles, themes, opts) {\n\tstyles.Fills = [];\n\tvar fill = {};\n\tvar pass = false;\n\t(t[0].match(tagregex)||[]).forEach(function(x) {\n\t\tvar y = parsexmltag(x);\n\t\tswitch(strip_ns(y[0])) {\n\t\t\tcase '<fills': case '<fills>': case '</fills>': break;\n\n\t\t\t/* 18.8.20 fill CT_Fill */\n\t\t\tcase '<fill>': case '<fill': case '<fill/>':\n\t\t\t\tfill = {}; styles.Fills.push(fill); break;\n\t\t\tcase '</fill>': break;\n\n\t\t\t/* 18.8.24 gradientFill CT_GradientFill */\n\t\t\tcase '<gradientFill>': break;\n\t\t\tcase '<gradientFill':\n\t\t\tcase '</gradientFill>': styles.Fills.push(fill); fill = {}; break;\n\n\t\t\t/* 18.8.32 patternFill CT_PatternFill */\n\t\t\tcase '<patternFill': case '<patternFill>':\n\t\t\t\tif(y.patternType) fill.patternType = y.patternType;\n\t\t\t\tbreak;\n\t\t\tcase '<patternFill/>': case '</patternFill>': break;\n\n\t\t\t/* 18.8.3 bgColor CT_Color */\n\t\t\tcase '<bgColor':\n\t\t\t\tif(!fill.bgColor) fill.bgColor = {};\n\t\t\t\tif(y.indexed) fill.bgColor.indexed = parseInt(y.indexed, 10);\n\t\t\t\tif(y.theme) fill.bgColor.theme = parseInt(y.theme, 10);\n\t\t\t\tif(y.tint) fill.bgColor.tint = parseFloat(y.tint);\n\t\t\t\t/* Excel uses ARGB strings */\n\t\t\t\tif(y.rgb) fill.bgColor.rgb = y.rgb.slice(-6);\n\t\t\t\tbreak;\n\t\t\tcase '<bgColor/>': case '</bgColor>': break;\n\n\t\t\t/* 18.8.19 fgColor CT_Color */\n\t\t\tcase '<fgColor':\n\t\t\t\tif(!fill.fgColor) fill.fgColor = {};\n\t\t\t\tif(y.theme) fill.fgColor.theme = parseInt(y.theme, 10);\n\t\t\t\tif(y.tint) fill.fgColor.tint = parseFloat(y.tint);\n\t\t\t\t/* Excel uses ARGB strings */\n\t\t\t\tif(y.rgb != null) fill.fgColor.rgb = y.rgb.slice(-6);\n\t\t\t\tbreak;\n\t\t\tcase '<fgColor/>': case '</fgColor>': break;\n\n\t\t\t/* 18.8.38 stop CT_GradientStop */\n\t\t\tcase '<stop': case '<stop/>': break;\n\t\t\tcase '</stop>': break;\n\n\t\t\t/* 18.8.? color CT_Color */\n\t\t\tcase '<color': case '<color/>': break;\n\t\t\tcase '</color>': break;\n\n\t\t\t/* 18.2.10 extLst CT_ExtensionList ? */\n\t\t\tcase '<extLst': case '<extLst>': case '</extLst>': break;\n\t\t\tcase '<ext': pass = true; break;\n\t\t\tcase '</ext>': pass = false; break;\n\t\t\tdefault: if(opts && opts.WTF) {\n\t\t\t\tif(!pass) throw new Error('unrecognized ' + y[0] + ' in fills');\n\t\t\t}\n\t\t}\n\t});\n}\n\n/* 18.8.23 fonts CT_Fonts */\nfunction parse_fonts(t, styles, themes, opts) {\n\tstyles.Fonts = [];\n\tvar font = {};\n\tvar pass = false;\n\t(t[0].match(tagregex)||[]).forEach(function(x) {\n\t\tvar y = parsexmltag(x);\n\t\tswitch(strip_ns(y[0])) {\n\t\t\tcase '<fonts': case '<fonts>': case '</fonts>': break;\n\n\t\t\t/* 18.8.22 font CT_Font */\n\t\t\tcase '<font': case '<font>': break;\n\t\t\tcase '</font>': case '<font/>':\n\t\t\t\tstyles.Fonts.push(font);\n\t\t\t\tfont = {};\n\t\t\t\tbreak;\n\n\t\t\t/* 18.8.29 name CT_FontName */\n\t\t\tcase '<name': if(y.val) font.name = utf8read(y.val); break;\n\t\t\tcase '<name/>': case '</name>': break;\n\n\t\t\t/* 18.8.2  b CT_BooleanProperty */\n\t\t\tcase '<b': font.bold = y.val ? parsexmlbool(y.val) : 1; break;\n\t\t\tcase '<b/>': font.bold = 1; break;\n\n\t\t\t/* 18.8.26 i CT_BooleanProperty */\n\t\t\tcase '<i': font.italic = y.val ? parsexmlbool(y.val) : 1; break;\n\t\t\tcase '<i/>': font.italic = 1; break;\n\n\t\t\t/* 18.4.13 u CT_UnderlineProperty */\n\t\t\tcase '<u':\n\t\t\t\tswitch(y.val) {\n\t\t\t\t\tcase \"none\": font.underline = 0x00; break;\n\t\t\t\t\tcase \"single\": font.underline = 0x01; break;\n\t\t\t\t\tcase \"double\": font.underline = 0x02; break;\n\t\t\t\t\tcase \"singleAccounting\": font.underline = 0x21; break;\n\t\t\t\t\tcase \"doubleAccounting\": font.underline = 0x22; break;\n\t\t\t\t} break;\n\t\t\tcase '<u/>': font.underline = 1; break;\n\n\t\t\t/* 18.4.10 strike CT_BooleanProperty */\n\t\t\tcase '<strike': font.strike = y.val ? parsexmlbool(y.val) : 1; break;\n\t\t\tcase '<strike/>': font.strike = 1; break;\n\n\t\t\t/* 18.4.2  outline CT_BooleanProperty */\n\t\t\tcase '<outline': font.outline = y.val ? parsexmlbool(y.val) : 1; break;\n\t\t\tcase '<outline/>': font.outline = 1; break;\n\n\t\t\t/* 18.8.36 shadow CT_BooleanProperty */\n\t\t\tcase '<shadow': font.shadow = y.val ? parsexmlbool(y.val) : 1; break;\n\t\t\tcase '<shadow/>': font.shadow = 1; break;\n\n\t\t\t/* 18.8.12 condense CT_BooleanProperty */\n\t\t\tcase '<condense': font.condense = y.val ? parsexmlbool(y.val) : 1; break;\n\t\t\tcase '<condense/>': font.condense = 1; break;\n\n\t\t\t/* 18.8.17 extend CT_BooleanProperty */\n\t\t\tcase '<extend': font.extend = y.val ? parsexmlbool(y.val) : 1; break;\n\t\t\tcase '<extend/>': font.extend = 1; break;\n\n\t\t\t/* 18.4.11 sz CT_FontSize */\n\t\t\tcase '<sz': if(y.val) font.sz = +y.val; break;\n\t\t\tcase '<sz/>': case '</sz>': break;\n\n\t\t\t/* 18.4.14 vertAlign CT_VerticalAlignFontProperty */\n\t\t\tcase '<vertAlign': if(y.val) font.vertAlign = y.val; break;\n\t\t\tcase '<vertAlign/>': case '</vertAlign>': break;\n\n\t\t\t/* 18.8.18 family CT_FontFamily */\n\t\t\tcase '<family': if(y.val) font.family = parseInt(y.val,10); break;\n\t\t\tcase '<family/>': case '</family>': break;\n\n\t\t\t/* 18.8.35 scheme CT_FontScheme */\n\t\t\tcase '<scheme': if(y.val) font.scheme = y.val; break;\n\t\t\tcase '<scheme/>': case '</scheme>': break;\n\n\t\t\t/* 18.4.1 charset CT_IntProperty */\n\t\t\tcase '<charset':\n\t\t\t\tif(y.val == '1') break;\n\t\t\t\ty.codepage = CS2CP[parseInt(y.val, 10)];\n\t\t\t\tbreak;\n\n\t\t\t/* 18.?.? color CT_Color */\n\t\t\tcase '<color':\n\t\t\t\tif(!font.color) font.color = {};\n\t\t\t\tif(y.auto) font.color.auto = parsexmlbool(y.auto);\n\n\t\t\t\tif(y.rgb) font.color.rgb = y.rgb.slice(-6);\n\t\t\t\telse if(y.indexed) {\n\t\t\t\t\tfont.color.index = parseInt(y.indexed, 10);\n\t\t\t\t\tvar icv = XLSIcv[font.color.index];\n\t\t\t\t\tif(font.color.index == 81) icv = XLSIcv[1];\n\t\t\t\t\tif(!icv) icv = XLSIcv[1]; //throw new Error(x); // note: 206 is valid\n\t\t\t\t\tfont.color.rgb = icv[0].toString(16) + icv[1].toString(16) + icv[2].toString(16);\n\t\t\t\t} else if(y.theme) {\n\t\t\t\t\tfont.color.theme = parseInt(y.theme, 10);\n\t\t\t\t\tif(y.tint) font.color.tint = parseFloat(y.tint);\n\t\t\t\t\tif(y.theme && themes.themeElements && themes.themeElements.clrScheme) {\n\t\t\t\t\t\tfont.color.rgb = rgb_tint(themes.themeElements.clrScheme[font.color.theme].rgb, font.color.tint || 0);\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\tbreak;\n\t\t\tcase '<color/>': case '</color>': break;\n\n\t\t\t/* note: sometimes mc:AlternateContent appears bare */\n\t\t\tcase '<AlternateContent': pass = true; break;\n\t\t\tcase '</AlternateContent>': pass = false; break;\n\n\t\t\t/* 18.2.10 extLst CT_ExtensionList ? */\n\t\t\tcase '<extLst': case '<extLst>': case '</extLst>': break;\n\t\t\tcase '<ext': pass = true; break;\n\t\t\tcase '</ext>': pass = false; break;\n\t\t\tdefault: if(opts && opts.WTF) {\n\t\t\t\tif(!pass) throw new Error('unrecognized ' + y[0] + ' in fonts');\n\t\t\t}\n\t\t}\n\t});\n}\n\n/* 18.8.31 numFmts CT_NumFmts */\nfunction parse_numFmts(t, styles, opts) {\n\tstyles.NumberFmt = [];\n\tvar k/*Array<number>*/ = (keys(table_fmt)/*:any*/);\n\tfor(var i=0; i < k.length; ++i) styles.NumberFmt[k[i]] = table_fmt[k[i]];\n\tvar m = t[0].match(tagregex);\n\tif(!m) return;\n\tfor(i=0; i < m.length; ++i) {\n\t\tvar y = parsexmltag(m[i]);\n\t\tswitch(strip_ns(y[0])) {\n\t\t\tcase '<numFmts': case '</numFmts>': case '<numFmts/>': case '<numFmts>': break;\n\t\t\tcase '<numFmt': {\n\t\t\t\tvar f=unescapexml(utf8read(y.formatCode)), j=parseInt(y.numFmtId,10);\n\t\t\t\tstyles.NumberFmt[j] = f;\n\t\t\t\tif(j>0) {\n\t\t\t\t\tif(j > 0x188) {\n\t\t\t\t\t\tfor(j = 0x188; j > 0x3c; --j) if(styles.NumberFmt[j] == null) break;\n\t\t\t\t\t\tstyles.NumberFmt[j] = f;\n\t\t\t\t\t}\n\t\t\t\t\tSSF_load(f,j);\n\t\t\t\t}\n\t\t\t} break;\n\t\t\tcase '</numFmt>': break;\n\t\t\tdefault: if(opts.WTF) throw new Error('unrecognized ' + y[0] + ' in numFmts');\n\t\t}\n\t}\n}\n\nfunction write_numFmts(NF/*:{[n:number|string]:string}*//*::, opts*/) {\n\tvar o = [\"<numFmts>\"];\n\t[[5,8],[23,26],[41,44],[/*63*/50,/*66],[164,*/392]].forEach(function(r) {\n\t\tfor(var i = r[0]; i <= r[1]; ++i) if(NF[i] != null) o[o.length] = (writextag('numFmt',null,{numFmtId:i,formatCode:escapexml(NF[i])}));\n\t});\n\tif(o.length === 1) return \"\";\n\to[o.length] = (\"</numFmts>\");\n\to[0] = writextag('numFmts', null, { count:o.length-2 }).replace(\"/>\", \">\");\n\treturn o.join(\"\");\n}\n\n/* 18.8.10 cellXfs CT_CellXfs */\nvar cellXF_uint = [ \"numFmtId\", \"fillId\", \"fontId\", \"borderId\", \"xfId\" ];\nvar cellXF_bool = [ \"applyAlignment\", \"applyBorder\", \"applyFill\", \"applyFont\", \"applyNumberFormat\", \"applyProtection\", \"pivotButton\", \"quotePrefix\" ];\nfunction parse_cellXfs(t, styles, opts) {\n\tstyles.CellXf = [];\n\tvar xf;\n\tvar pass = false;\n\t(t[0].match(tagregex)||[]).forEach(function(x) {\n\t\tvar y = parsexmltag(x), i = 0;\n\t\tswitch(strip_ns(y[0])) {\n\t\t\tcase '<cellXfs': case '<cellXfs>': case '<cellXfs/>': case '</cellXfs>': break;\n\n\t\t\t/* 18.8.45 xf CT_Xf */\n\t\t\tcase '<xf': case '<xf/>':\n\t\t\t\txf = y;\n\t\t\t\tdelete xf[0];\n\t\t\t\tfor(i = 0; i < cellXF_uint.length; ++i) if(xf[cellXF_uint[i]])\n\t\t\t\t\txf[cellXF_uint[i]] = parseInt(xf[cellXF_uint[i]], 10);\n\t\t\t\tfor(i = 0; i < cellXF_bool.length; ++i) if(xf[cellXF_bool[i]])\n\t\t\t\t\txf[cellXF_bool[i]] = parsexmlbool(xf[cellXF_bool[i]]);\n\t\t\t\tif(styles.NumberFmt && xf.numFmtId > 0x188) {\n\t\t\t\t\tfor(i = 0x188; i > 0x3c; --i) if(styles.NumberFmt[xf.numFmtId] == styles.NumberFmt[i]) { xf.numFmtId = i; break; }\n\t\t\t\t}\n\t\t\t\tstyles.CellXf.push(xf); break;\n\t\t\tcase '</xf>': break;\n\n\t\t\t/* 18.8.1 alignment CT_CellAlignment */\n\t\t\tcase '<alignment': case '<alignment/>':\n\t\t\t\tvar alignment = {};\n\t\t\t\tif(y.vertical) alignment.vertical = y.vertical;\n\t\t\t\tif(y.horizontal) alignment.horizontal = y.horizontal;\n\t\t\t\tif(y.textRotation != null) alignment.textRotation = y.textRotation;\n\t\t\t\tif(y.indent) alignment.indent = y.indent;\n\t\t\t\tif(y.wrapText) alignment.wrapText = parsexmlbool(y.wrapText);\n\t\t\t\txf.alignment = alignment;\n\t\t\t\tbreak;\n\t\t\tcase '</alignment>': break;\n\n\t\t\t/* 18.8.33 protection CT_CellProtection */\n\t\t\tcase '<protection':\n\t\t\t\tbreak;\n\t\t\tcase '</protection>': case '<protection/>': break;\n\n\t\t\t/* note: sometimes mc:AlternateContent appears bare */\n\t\t\tcase '<AlternateContent': pass = true; break;\n\t\t\tcase '</AlternateContent>': pass = false; break;\n\n\t\t\t/* 18.2.10 extLst CT_ExtensionList ? */\n\t\t\tcase '<extLst': case '<extLst>': case '</extLst>': break;\n\t\t\tcase '<ext': pass = true; break;\n\t\t\tcase '</ext>': pass = false; break;\n\t\t\tdefault: if(opts && opts.WTF) {\n\t\t\t\tif(!pass) throw new Error('unrecognized ' + y[0] + ' in cellXfs');\n\t\t\t}\n\t\t}\n\t});\n}\n\nfunction write_cellXfs(cellXfs)/*:string*/ {\n\tvar o/*:Array<string>*/ = [];\n\to[o.length] = (writextag('cellXfs',null));\n\tcellXfs.forEach(function(c) {\n\t\to[o.length] = (writextag('xf', null, c));\n\t});\n\to[o.length] = (\"</cellXfs>\");\n\tif(o.length === 2) return \"\";\n\to[0] = writextag('cellXfs',null, {count:o.length-2}).replace(\"/>\",\">\");\n\treturn o.join(\"\");\n}\n\n/* 18.8 Styles CT_Stylesheet*/\nvar parse_sty_xml= /*#__PURE__*/(function make_pstyx() {\nvar numFmtRegex = /<(?:\\w+:)?numFmts([^>]*)>[\\S\\s]*?<\\/(?:\\w+:)?numFmts>/;\nvar cellXfRegex = /<(?:\\w+:)?cellXfs([^>]*)>[\\S\\s]*?<\\/(?:\\w+:)?cellXfs>/;\nvar fillsRegex = /<(?:\\w+:)?fills([^>]*)>[\\S\\s]*?<\\/(?:\\w+:)?fills>/;\nvar fontsRegex = /<(?:\\w+:)?fonts([^>]*)>[\\S\\s]*?<\\/(?:\\w+:)?fonts>/;\nvar bordersRegex = /<(?:\\w+:)?borders([^>]*)>[\\S\\s]*?<\\/(?:\\w+:)?borders>/;\n\nreturn function parse_sty_xml(data, themes, opts) {\n\tvar styles = {};\n\tif(!data) return styles;\n\tdata = data.replace(/<!--([\\s\\S]*?)-->/mg,\"\").replace(/<!DOCTYPE[^\\[]*\\[[^\\]]*\\]>/gm,\"\");\n\t/* 18.8.39 styleSheet CT_Stylesheet */\n\tvar t;\n\n\t/* 18.8.31 numFmts CT_NumFmts ? */\n\tif((t=data.match(numFmtRegex))) parse_numFmts(t, styles, opts);\n\n\t/* 18.8.23 fonts CT_Fonts ? */\n\tif((t=data.match(fontsRegex))) parse_fonts(t, styles, themes, opts);\n\n\t/* 18.8.21 fills CT_Fills ? */\n\tif((t=data.match(fillsRegex))) parse_fills(t, styles, themes, opts);\n\n\t/* 18.8.5  borders CT_Borders ? */\n\tif((t=data.match(bordersRegex))) parse_borders(t, styles, themes, opts);\n\n\t/* 18.8.9  cellStyleXfs CT_CellStyleXfs ? */\n\t/* 18.8.8  cellStyles CT_CellStyles ? */\n\n\t/* 18.8.10 cellXfs CT_CellXfs ? */\n\tif((t=data.match(cellXfRegex))) parse_cellXfs(t, styles, opts);\n\n\t/* 18.8.15 dxfs CT_Dxfs ? */\n\t/* 18.8.42 tableStyles CT_TableStyles ? */\n\t/* 18.8.11 colors CT_Colors ? */\n\t/* 18.2.10 extLst CT_ExtensionList ? */\n\n\treturn styles;\n};\n})();\n\nfunction write_sty_xml(wb/*:Workbook*/, opts)/*:string*/ {\n\tvar o = [XML_HEADER, writextag('styleSheet', null, {\n\t\t'xmlns': XMLNS_main[0],\n\t\t'xmlns:vt': XMLNS.vt\n\t})], w;\n\tif(wb.SSF && (w = write_numFmts(wb.SSF)) != null) o[o.length] = w;\n\to[o.length] = ('<fonts count=\"1\"><font><sz val=\"12\"/><color theme=\"1\"/><name val=\"Calibri\"/><family val=\"2\"/><scheme val=\"minor\"/></font></fonts>');\n\to[o.length] = ('<fills count=\"2\"><fill><patternFill patternType=\"none\"/></fill><fill><patternFill patternType=\"gray125\"/></fill></fills>');\n\to[o.length] = ('<borders count=\"1\"><border><left/><right/><top/><bottom/><diagonal/></border></borders>');\n\to[o.length] = ('<cellStyleXfs count=\"1\"><xf numFmtId=\"0\" fontId=\"0\" fillId=\"0\" borderId=\"0\"/></cellStyleXfs>');\n\tif((w = write_cellXfs(opts.cellXfs))) o[o.length] = (w);\n\to[o.length] = ('<cellStyles count=\"1\"><cellStyle name=\"Normal\" xfId=\"0\" builtinId=\"0\"/></cellStyles>');\n\to[o.length] = ('<dxfs count=\"0\"/>');\n\to[o.length] = ('<tableStyles count=\"0\" defaultTableStyle=\"TableStyleMedium9\" defaultPivotStyle=\"PivotStyleMedium4\"/>');\n\n\tif(o.length>2){ o[o.length] = ('</styleSheet>'); o[1]=o[1].replace(\"/>\",\">\"); }\n\treturn o.join(\"\");\n}\n/* [MS-XLSB] 2.4.657 BrtFmt */\nfunction parse_BrtFmt(data, length/*:number*/) {\n\tvar numFmtId = data.read_shift(2);\n\tvar stFmtCode = parse_XLWideString(data,length-2);\n\treturn [numFmtId, stFmtCode];\n}\nfunction write_BrtFmt(i/*:number*/, f/*:string*/, o) {\n\tif(!o) o = new_buf(6 + 4 * f.length);\n\to.write_shift(2, i);\n\twrite_XLWideString(f, o);\n\tvar out = (o.length > o.l) ? o.slice(0, o.l) : o;\n\tif(o.l == null) o.l = o.length;\n\treturn out;\n}\n\n/* [MS-XLSB] 2.4.659 BrtFont TODO */\nfunction parse_BrtFont(data, length/*:number*/, opts) {\n\tvar out = ({}/*:any*/);\n\n\tout.sz = data.read_shift(2) / 20;\n\n\tvar grbit = parse_FontFlags(data, 2, opts);\n\tif(grbit.fItalic) out.italic = 1;\n\tif(grbit.fCondense) out.condense = 1;\n\tif(grbit.fExtend) out.extend = 1;\n\tif(grbit.fShadow) out.shadow = 1;\n\tif(grbit.fOutline) out.outline = 1;\n\tif(grbit.fStrikeout) out.strike = 1;\n\n\tvar bls = data.read_shift(2);\n\tif(bls === 0x02BC) out.bold = 1;\n\n\tswitch(data.read_shift(2)) {\n\t\t/* case 0: out.vertAlign = \"baseline\"; break; */\n\t\tcase 1: out.vertAlign = \"superscript\"; break;\n\t\tcase 2: out.vertAlign = \"subscript\"; break;\n\t}\n\n\tvar underline = data.read_shift(1);\n\tif(underline != 0) out.underline = underline;\n\n\tvar family = data.read_shift(1);\n\tif(family > 0) out.family = family;\n\n\tvar bCharSet = data.read_shift(1);\n\tif(bCharSet > 0) out.charset = bCharSet;\n\n\tdata.l++;\n\tout.color = parse_BrtColor(data, 8);\n\n\tswitch(data.read_shift(1)) {\n\t\t/* case 0: out.scheme = \"none\": break; */\n\t\tcase 1: out.scheme = \"major\"; break;\n\t\tcase 2: out.scheme = \"minor\"; break;\n\t}\n\n\tout.name = parse_XLWideString(data, length - 21);\n\n\treturn out;\n}\nfunction write_BrtFont(font/*:any*/, o) {\n\tif(!o) o = new_buf(25+4*32);\n\to.write_shift(2, font.sz * 20);\n\twrite_FontFlags(font, o);\n\to.write_shift(2, font.bold ? 0x02BC : 0x0190);\n\tvar sss = 0;\n\tif(font.vertAlign == \"superscript\") sss = 1;\n\telse if(font.vertAlign == \"subscript\") sss = 2;\n\to.write_shift(2, sss);\n\to.write_shift(1, font.underline || 0);\n\to.write_shift(1, font.family || 0);\n\to.write_shift(1, font.charset || 0);\n\to.write_shift(1, 0);\n\twrite_BrtColor(font.color, o);\n\tvar scheme = 0;\n\tif(font.scheme == \"major\") scheme = 1;\n\tif(font.scheme == \"minor\") scheme = 2;\n\to.write_shift(1, scheme);\n\twrite_XLWideString(font.name, o);\n\treturn o.length > o.l ? o.slice(0, o.l) : o;\n}\n\n/* [MS-XLSB] 2.4.650 BrtFill */\nvar XLSBFillPTNames = [\n\t\"none\",\n\t\"solid\",\n\t\"mediumGray\",\n\t\"darkGray\",\n\t\"lightGray\",\n\t\"darkHorizontal\",\n\t\"darkVertical\",\n\t\"darkDown\",\n\t\"darkUp\",\n\t\"darkGrid\",\n\t\"darkTrellis\",\n\t\"lightHorizontal\",\n\t\"lightVertical\",\n\t\"lightDown\",\n\t\"lightUp\",\n\t\"lightGrid\",\n\t\"lightTrellis\",\n\t\"gray125\",\n\t\"gray0625\"\n];\nvar rev_XLSBFillPTNames/*:EvertNumType*/;\n/* TODO: gradient fill representation */\nvar parse_BrtFill = parsenoop;\nfunction write_BrtFill(fill, o) {\n\tif(!o) o = new_buf(4*3 + 8*7 + 16*1);\n\tif(!rev_XLSBFillPTNames) rev_XLSBFillPTNames = (evert(XLSBFillPTNames)/*:any*/);\n\tvar fls/*:number*/ = rev_XLSBFillPTNames[fill.patternType];\n\tif(fls == null) fls = 0x28;\n\to.write_shift(4, fls);\n\tvar j = 0;\n\tif(fls != 0x28) {\n\t\t/* TODO: custom FG Color */\n\t\twrite_BrtColor({auto:1}, o);\n\t\t/* TODO: custom BG Color */\n\t\twrite_BrtColor({auto:1}, o);\n\n\t\tfor(; j < 12; ++j) o.write_shift(4, 0);\n\t} else {\n\t\tfor(; j < 4; ++j) o.write_shift(4, 0);\n\n\t\tfor(; j < 12; ++j) o.write_shift(4, 0); /* TODO */\n\t\t/* iGradientType */\n\t\t/* xnumDegree */\n\t\t/* xnumFillToLeft */\n\t\t/* xnumFillToRight */\n\t\t/* xnumFillToTop */\n\t\t/* xnumFillToBottom */\n\t\t/* cNumStop */\n\t\t/* xfillGradientStop */\n\t}\n\treturn o.length > o.l ? o.slice(0, o.l) : o;\n}\n\n/* [MS-XLSB] 2.4.824 BrtXF */\nfunction parse_BrtXF(data, length/*:number*/) {\n\tvar tgt = data.l + length;\n\tvar ixfeParent = data.read_shift(2);\n\tvar ifmt = data.read_shift(2);\n\tdata.l = tgt;\n\treturn {ixfe:ixfeParent, numFmtId:ifmt };\n}\nfunction write_BrtXF(data, ixfeP, o) {\n\tif(!o) o = new_buf(16);\n\to.write_shift(2, ixfeP||0);\n\to.write_shift(2, data.numFmtId||0);\n\to.write_shift(2, 0); /* iFont */\n\to.write_shift(2, 0); /* iFill */\n\to.write_shift(2, 0); /* ixBorder */\n\to.write_shift(1, 0); /* trot */\n\to.write_shift(1, 0); /* indent */\n\tvar flow = 0;\n\to.write_shift(1, flow); /* flags */\n\to.write_shift(1, 0); /* flags */\n\to.write_shift(1, 0); /* xfGrbitAtr */\n\to.write_shift(1, 0);\n\treturn o;\n}\n\n/* [MS-XLSB] 2.5.4 Blxf TODO */\nfunction write_Blxf(data, o) {\n\tif(!o) o = new_buf(10);\n\to.write_shift(1, 0); /* dg */\n\to.write_shift(1, 0);\n\to.write_shift(4, 0); /* color */\n\to.write_shift(4, 0); /* color */\n\treturn o;\n}\n/* [MS-XLSB] 2.4.302 BrtBorder TODO */\nvar parse_BrtBorder = parsenoop;\nfunction write_BrtBorder(border, o) {\n\tif(!o) o = new_buf(51);\n\to.write_shift(1, 0); /* diagonal */\n\twrite_Blxf(null, o); /* top */\n\twrite_Blxf(null, o); /* bottom */\n\twrite_Blxf(null, o); /* left */\n\twrite_Blxf(null, o); /* right */\n\twrite_Blxf(null, o); /* diag */\n\treturn o.length > o.l ? o.slice(0, o.l) : o;\n}\n\n/* [MS-XLSB] 2.4.763 BrtStyle TODO */\nfunction write_BrtStyle(style, o) {\n\tif(!o) o = new_buf(12+4*10);\n\to.write_shift(4, style.xfId);\n\to.write_shift(2, 1);\n\to.write_shift(1, +style.builtinId);\n\to.write_shift(1, 0); /* iLevel */\n\twrite_XLNullableWideString(style.name || \"\", o);\n\treturn o.length > o.l ? o.slice(0, o.l) : o;\n}\n\n/* [MS-XLSB] 2.4.272 BrtBeginTableStyles */\nfunction write_BrtBeginTableStyles(cnt, defTableStyle, defPivotStyle) {\n\tvar o = new_buf(4+256*2*4);\n\to.write_shift(4, cnt);\n\twrite_XLNullableWideString(defTableStyle, o);\n\twrite_XLNullableWideString(defPivotStyle, o);\n\treturn o.length > o.l ? o.slice(0, o.l) : o;\n}\n\n/* [MS-XLSB] 2.1.7.50 Styles */\nfunction parse_sty_bin(data, themes, opts) {\n\tvar styles = {};\n\tstyles.NumberFmt = ([]/*:any*/);\n\tfor(var y in table_fmt) styles.NumberFmt[y] = table_fmt[y];\n\n\tstyles.CellXf = [];\n\tstyles.Fonts = [];\n\tvar state/*:Array<string>*/ = [];\n\tvar pass = false;\n\trecordhopper(data, function hopper_sty(val, R, RT) {\n\t\tswitch(RT) {\n\t\t\tcase 0x002C: /* BrtFmt */\n\t\t\t\tstyles.NumberFmt[val[0]] = val[1]; SSF_load(val[1], val[0]);\n\t\t\t\tbreak;\n\t\t\tcase 0x002B: /* BrtFont */\n\t\t\t\tstyles.Fonts.push(val);\n\t\t\t\tif(val.color.theme != null && themes && themes.themeElements && themes.themeElements.clrScheme) {\n\t\t\t\t\tval.color.rgb = rgb_tint(themes.themeElements.clrScheme[val.color.theme].rgb, val.color.tint || 0);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase 0x0401: /* BrtKnownFonts */ break;\n\t\t\tcase 0x002D: /* BrtFill */\n\t\t\t\tbreak;\n\t\t\tcase 0x002E: /* BrtBorder */\n\t\t\t\tbreak;\n\t\t\tcase 0x002F: /* BrtXF */\n\t\t\t\tif(state[state.length - 1] == 0x0269 /* BrtBeginCellXFs */) {\n\t\t\t\t\tstyles.CellXf.push(val);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase 0x0030: /* BrtStyle */\n\t\t\tcase 0x01FB: /* BrtDXF */\n\t\t\tcase 0x023C: /* BrtMRUColor */\n\t\t\tcase 0x01DB: /* BrtIndexedColor */\n\t\t\t\tbreak;\n\n\t\t\tcase 0x0493: /* BrtDXF14 */\n\t\t\tcase 0x0836: /* BrtDXF15 */\n\t\t\tcase 0x046A: /* BrtSlicerStyleElement */\n\t\t\tcase 0x0200: /* BrtTableStyleElement */\n\t\t\tcase 0x082F: /* BrtTimelineStyleElement */\n\t\t\tcase 0x0C00: /* BrtUid */\n\t\t\t\tbreak;\n\n\t\t\tcase 0x0023: /* BrtFRTBegin */\n\t\t\t\tpass = true; break;\n\t\t\tcase 0x0024: /* BrtFRTEnd */\n\t\t\t\tpass = false; break;\n\t\t\tcase 0x0025: /* BrtACBegin */\n\t\t\t\tstate.push(RT); pass = true; break;\n\t\t\tcase 0x0026: /* BrtACEnd */\n\t\t\t\tstate.pop(); pass = false; break;\n\n\t\t\tdefault:\n\t\t\t\tif(R.T > 0) state.push(RT);\n\t\t\t\telse if(R.T < 0) state.pop();\n\t\t\t\telse if(!pass || (opts.WTF && state[state.length-1] != 0x0025 /* BrtACBegin */)) throw new Error(\"Unexpected record 0x\" + RT.toString(16));\n\t\t}\n\t});\n\treturn styles;\n}\n\nfunction write_FMTS_bin(ba, NF/*:?SSFTable*/) {\n\tif(!NF) return;\n\tvar cnt = 0;\n\t[[5,8],[23,26],[41,44],[/*63*/50,/*66],[164,*/392]].forEach(function(r) {\n\t\t/*:: if(!NF) return; */\n\t\tfor(var i = r[0]; i <= r[1]; ++i) if(NF[i] != null) ++cnt;\n\t});\n\n\tif(cnt == 0) return;\n\twrite_record(ba, 0x0267 /* BrtBeginFmts */, write_UInt32LE(cnt));\n\t[[5,8],[23,26],[41,44],[/*63*/50,/*66],[164,*/392]].forEach(function(r) {\n\t\t/*:: if(!NF) return; */\n\t\tfor(var i = r[0]; i <= r[1]; ++i) if(NF[i] != null) write_record(ba, 0x002C /* BrtFmt */, write_BrtFmt(i, NF[i]));\n\t});\n\twrite_record(ba, 0x0268 /* BrtEndFmts */);\n}\n\nfunction write_FONTS_bin(ba/*::, data*/) {\n\tvar cnt = 1;\n\n\tif(cnt == 0) return;\n\twrite_record(ba, 0x0263 /* BrtBeginFonts */, write_UInt32LE(cnt));\n\twrite_record(ba, 0x002B /* BrtFont */, write_BrtFont({\n\t\tsz:12,\n\t\tcolor: {theme:1},\n\t\tname: \"Calibri\",\n\t\tfamily: 2,\n\t\tscheme: \"minor\"\n\t}));\n\t/* 1*65491BrtFont [ACFONTS] */\n\twrite_record(ba, 0x0264 /* BrtEndFonts */);\n}\n\nfunction write_FILLS_bin(ba/*::, data*/) {\n\tvar cnt = 2;\n\n\tif(cnt == 0) return;\n\twrite_record(ba, 0x025B /* BrtBeginFills */, write_UInt32LE(cnt));\n\twrite_record(ba, 0x002D /* BrtFill */, write_BrtFill({patternType:\"none\"}));\n\twrite_record(ba, 0x002D /* BrtFill */, write_BrtFill({patternType:\"gray125\"}));\n\t/* 1*65431BrtFill */\n\twrite_record(ba, 0x025C /* BrtEndFills */);\n}\n\nfunction write_BORDERS_bin(ba/*::, data*/) {\n\tvar cnt = 1;\n\n\tif(cnt == 0) return;\n\twrite_record(ba, 0x0265 /* BrtBeginBorders */, write_UInt32LE(cnt));\n\twrite_record(ba, 0x002E /* BrtBorder */, write_BrtBorder({}));\n\t/* 1*65430BrtBorder */\n\twrite_record(ba, 0x0266 /* BrtEndBorders */);\n}\n\nfunction write_CELLSTYLEXFS_bin(ba/*::, data*/) {\n\tvar cnt = 1;\n\twrite_record(ba, 0x0272 /* BrtBeginCellStyleXFs */, write_UInt32LE(cnt));\n\twrite_record(ba, 0x002F /* BrtXF */, write_BrtXF({\n\t\tnumFmtId: 0,\n\t\tfontId:   0,\n\t\tfillId:   0,\n\t\tborderId: 0\n\t}, 0xFFFF));\n\t/* 1*65430(BrtXF *FRT) */\n\twrite_record(ba, 0x0273 /* BrtEndCellStyleXFs */);\n}\n\nfunction write_CELLXFS_bin(ba, data) {\n\twrite_record(ba, 0x0269 /* BrtBeginCellXFs */, write_UInt32LE(data.length));\n\tdata.forEach(function(c) { write_record(ba, 0x002F /* BrtXF */, write_BrtXF(c,0)); });\n\t/* 1*65430(BrtXF *FRT) */\n\twrite_record(ba, 0x026A /* BrtEndCellXFs */);\n}\n\nfunction write_STYLES_bin(ba/*::, data*/) {\n\tvar cnt = 1;\n\n\twrite_record(ba, 0x026B /* BrtBeginStyles */, write_UInt32LE(cnt));\n\twrite_record(ba, 0x0030 /* BrtStyle */, write_BrtStyle({\n\t\txfId:0,\n\t\tbuiltinId:0,\n\t\tname:\"Normal\"\n\t}));\n\t/* 1*65430(BrtStyle *FRT) */\n\twrite_record(ba, 0x026C /* BrtEndStyles */);\n}\n\nfunction write_DXFS_bin(ba/*::, data*/) {\n\tvar cnt = 0;\n\n\twrite_record(ba, 0x01F9 /* BrtBeginDXFs */, write_UInt32LE(cnt));\n\t/* *2147483647(BrtDXF *FRT) */\n\twrite_record(ba, 0x01FA /* BrtEndDXFs */);\n}\n\nfunction write_TABLESTYLES_bin(ba/*::, data*/) {\n\tvar cnt = 0;\n\n\twrite_record(ba, 0x01FC /* BrtBeginTableStyles */, write_BrtBeginTableStyles(cnt, \"TableStyleMedium9\", \"PivotStyleMedium4\"));\n\t/* *TABLESTYLE */\n\twrite_record(ba, 0x01FD /* BrtEndTableStyles */);\n}\n\nfunction write_COLORPALETTE_bin(/*::ba, data*/) {\n\treturn;\n\t/* BrtBeginColorPalette [INDEXEDCOLORS] [MRUCOLORS] BrtEndColorPalette */\n}\n\n/* [MS-XLSB] 2.1.7.50 Styles */\nfunction write_sty_bin(wb, opts) {\n\tvar ba = buf_array();\n\twrite_record(ba, 0x0116 /* BrtBeginStyleSheet */);\n\twrite_FMTS_bin(ba, wb.SSF);\n\twrite_FONTS_bin(ba, wb);\n\twrite_FILLS_bin(ba, wb);\n\twrite_BORDERS_bin(ba, wb);\n\twrite_CELLSTYLEXFS_bin(ba, wb);\n\twrite_CELLXFS_bin(ba, opts.cellXfs);\n\twrite_STYLES_bin(ba, wb);\n\twrite_DXFS_bin(ba, wb);\n\twrite_TABLESTYLES_bin(ba, wb);\n\twrite_COLORPALETTE_bin(ba, wb);\n\t/* FRTSTYLESHEET*/\n\twrite_record(ba, 0x0117 /* BrtEndStyleSheet */);\n\treturn ba.end();\n}\n/* Even though theme layout is dk1 lt1 dk2 lt2, true order is lt1 dk1 lt2 dk2 */\nvar XLSXThemeClrScheme = [\n\t'</a:lt1>', '</a:dk1>', '</a:lt2>', '</a:dk2>',\n\t'</a:accent1>', '</a:accent2>', '</a:accent3>',\n\t'</a:accent4>', '</a:accent5>', '</a:accent6>',\n\t'</a:hlink>', '</a:folHlink>'\n];\n/* 20.1.6.2 clrScheme CT_ColorScheme */\nfunction parse_clrScheme(t, themes, opts) {\n\tthemes.themeElements.clrScheme = [];\n\tvar color = {};\n\t(t[0].match(tagregex)||[]).forEach(function(x) {\n\t\tvar y = parsexmltag(x);\n\t\tswitch(y[0]) {\n\t\t\t/* 20.1.6.2 clrScheme (Color Scheme) CT_ColorScheme */\n\t\t\tcase '<a:clrScheme': case '</a:clrScheme>': break;\n\n\t\t\t/* 20.1.2.3.32 srgbClr CT_SRgbColor */\n\t\t\tcase '<a:srgbClr':\n\t\t\t\tcolor.rgb = y.val; break;\n\n\t\t\t/* 20.1.2.3.33 sysClr CT_SystemColor */\n\t\t\tcase '<a:sysClr':\n\t\t\t\tcolor.rgb = y.lastClr; break;\n\n\t\t\t/* 20.1.4.1.1 accent1 (Accent 1) */\n\t\t\t/* 20.1.4.1.2 accent2 (Accent 2) */\n\t\t\t/* 20.1.4.1.3 accent3 (Accent 3) */\n\t\t\t/* 20.1.4.1.4 accent4 (Accent 4) */\n\t\t\t/* 20.1.4.1.5 accent5 (Accent 5) */\n\t\t\t/* 20.1.4.1.6 accent6 (Accent 6) */\n\t\t\t/* 20.1.4.1.9 dk1 (Dark 1) */\n\t\t\t/* 20.1.4.1.10 dk2 (Dark 2) */\n\t\t\t/* 20.1.4.1.15 folHlink (Followed Hyperlink) */\n\t\t\t/* 20.1.4.1.19 hlink (Hyperlink) */\n\t\t\t/* 20.1.4.1.22 lt1 (Light 1) */\n\t\t\t/* 20.1.4.1.23 lt2 (Light 2) */\n\t\t\tcase '<a:dk1>': case '</a:dk1>':\n\t\t\tcase '<a:lt1>': case '</a:lt1>':\n\t\t\tcase '<a:dk2>': case '</a:dk2>':\n\t\t\tcase '<a:lt2>': case '</a:lt2>':\n\t\t\tcase '<a:accent1>': case '</a:accent1>':\n\t\t\tcase '<a:accent2>': case '</a:accent2>':\n\t\t\tcase '<a:accent3>': case '</a:accent3>':\n\t\t\tcase '<a:accent4>': case '</a:accent4>':\n\t\t\tcase '<a:accent5>': case '</a:accent5>':\n\t\t\tcase '<a:accent6>': case '</a:accent6>':\n\t\t\tcase '<a:hlink>': case '</a:hlink>':\n\t\t\tcase '<a:folHlink>': case '</a:folHlink>':\n\t\t\t\tif (y[0].charAt(1) === '/') {\n\t\t\t\t\tthemes.themeElements.clrScheme[XLSXThemeClrScheme.indexOf(y[0])] = color;\n\t\t\t\t\tcolor = {};\n\t\t\t\t} else {\n\t\t\t\t\tcolor.name = y[0].slice(3, y[0].length - 1);\n\t\t\t\t}\n\t\t\t\tbreak;\n\n\t\t\tdefault: if(opts && opts.WTF) throw new Error('Unrecognized ' + y[0] + ' in clrScheme');\n\t\t}\n\t});\n}\n\n/* 20.1.4.1.18 fontScheme CT_FontScheme */\nfunction parse_fontScheme(/*::t, themes, opts*/) { }\n\n/* 20.1.4.1.15 fmtScheme CT_StyleMatrix */\nfunction parse_fmtScheme(/*::t, themes, opts*/) { }\n\nvar clrsregex = /<a:clrScheme([^>]*)>[\\s\\S]*<\\/a:clrScheme>/;\nvar fntsregex = /<a:fontScheme([^>]*)>[\\s\\S]*<\\/a:fontScheme>/;\nvar fmtsregex = /<a:fmtScheme([^>]*)>[\\s\\S]*<\\/a:fmtScheme>/;\n\n/* 20.1.6.10 themeElements CT_BaseStyles */\nfunction parse_themeElements(data, themes, opts) {\n\tthemes.themeElements = {};\n\n\tvar t;\n\n\t[\n\t\t/* clrScheme CT_ColorScheme */\n\t\t['clrScheme', clrsregex, parse_clrScheme],\n\t\t/* fontScheme CT_FontScheme */\n\t\t['fontScheme', fntsregex, parse_fontScheme],\n\t\t/* fmtScheme CT_StyleMatrix */\n\t\t['fmtScheme', fmtsregex, parse_fmtScheme]\n\t].forEach(function(m) {\n\t\tif(!(t=data.match(m[1]))) throw new Error(m[0] + ' not found in themeElements');\n\t\tm[2](t, themes, opts);\n\t});\n}\n\nvar themeltregex = /<a:themeElements([^>]*)>[\\s\\S]*<\\/a:themeElements>/;\n\n/* 14.2.7 Theme Part */\nfunction parse_theme_xml(data/*:string*/, opts) {\n\t/* 20.1.6.9 theme CT_OfficeStyleSheet */\n\tif(!data || data.length === 0) data = write_theme();\n\n\tvar t;\n\tvar themes = {};\n\n\t/* themeElements CT_BaseStyles */\n\tif(!(t=data.match(themeltregex))) throw new Error('themeElements not found in theme');\n\tparse_themeElements(t[0], themes, opts);\n\tthemes.raw = data;\n\treturn themes;\n}\n\nfunction write_theme(Themes, opts)/*:string*/ {\n\tif(opts && opts.themeXLSX) return opts.themeXLSX;\n\tif(Themes && typeof Themes.raw == \"string\") return Themes.raw;\n\tvar o = [XML_HEADER];\n\to[o.length] = '<a:theme xmlns:a=\"http://schemas.openxmlformats.org/drawingml/2006/main\" name=\"Office Theme\">';\n\to[o.length] =  '<a:themeElements>';\n\n\to[o.length] =   '<a:clrScheme name=\"Office\">';\n\to[o.length] =    '<a:dk1><a:sysClr val=\"windowText\" lastClr=\"000000\"/></a:dk1>';\n\to[o.length] =    '<a:lt1><a:sysClr val=\"window\" lastClr=\"FFFFFF\"/></a:lt1>';\n\to[o.length] =    '<a:dk2><a:srgbClr val=\"1F497D\"/></a:dk2>';\n\to[o.length] =    '<a:lt2><a:srgbClr val=\"EEECE1\"/></a:lt2>';\n\to[o.length] =    '<a:accent1><a:srgbClr val=\"4F81BD\"/></a:accent1>';\n\to[o.length] =    '<a:accent2><a:srgbClr val=\"C0504D\"/></a:accent2>';\n\to[o.length] =    '<a:accent3><a:srgbClr val=\"9BBB59\"/></a:accent3>';\n\to[o.length] =    '<a:accent4><a:srgbClr val=\"8064A2\"/></a:accent4>';\n\to[o.length] =    '<a:accent5><a:srgbClr val=\"4BACC6\"/></a:accent5>';\n\to[o.length] =    '<a:accent6><a:srgbClr val=\"F79646\"/></a:accent6>';\n\to[o.length] =    '<a:hlink><a:srgbClr val=\"0000FF\"/></a:hlink>';\n\to[o.length] =    '<a:folHlink><a:srgbClr val=\"800080\"/></a:folHlink>';\n\to[o.length] =   '</a:clrScheme>';\n\n\to[o.length] =   '<a:fontScheme name=\"Office\">';\n\to[o.length] =    '<a:majorFont>';\n\to[o.length] =     '<a:latin typeface=\"Cambria\"/>';\n\to[o.length] =     '<a:ea typeface=\"\"/>';\n\to[o.length] =     '<a:cs typeface=\"\"/>';\n\to[o.length] =     '<a:font script=\"Jpan\" typeface=\"ＭＳ Ｐゴシック\"/>';\n\to[o.length] =     '<a:font script=\"Hang\" typeface=\"맑은 고딕\"/>';\n\to[o.length] =     '<a:font script=\"Hans\" typeface=\"宋体\"/>';\n\to[o.length] =     '<a:font script=\"Hant\" typeface=\"新細明體\"/>';\n\to[o.length] =     '<a:font script=\"Arab\" typeface=\"Times New Roman\"/>';\n\to[o.length] =     '<a:font script=\"Hebr\" typeface=\"Times New Roman\"/>';\n\to[o.length] =     '<a:font script=\"Thai\" typeface=\"Tahoma\"/>';\n\to[o.length] =     '<a:font script=\"Ethi\" typeface=\"Nyala\"/>';\n\to[o.length] =     '<a:font script=\"Beng\" typeface=\"Vrinda\"/>';\n\to[o.length] =     '<a:font script=\"Gujr\" typeface=\"Shruti\"/>';\n\to[o.length] =     '<a:font script=\"Khmr\" typeface=\"MoolBoran\"/>';\n\to[o.length] =     '<a:font script=\"Knda\" typeface=\"Tunga\"/>';\n\to[o.length] =     '<a:font script=\"Guru\" typeface=\"Raavi\"/>';\n\to[o.length] =     '<a:font script=\"Cans\" typeface=\"Euphemia\"/>';\n\to[o.length] =     '<a:font script=\"Cher\" typeface=\"Plantagenet Cherokee\"/>';\n\to[o.length] =     '<a:font script=\"Yiii\" typeface=\"Microsoft Yi Baiti\"/>';\n\to[o.length] =     '<a:font script=\"Tibt\" typeface=\"Microsoft Himalaya\"/>';\n\to[o.length] =     '<a:font script=\"Thaa\" typeface=\"MV Boli\"/>';\n\to[o.length] =     '<a:font script=\"Deva\" typeface=\"Mangal\"/>';\n\to[o.length] =     '<a:font script=\"Telu\" typeface=\"Gautami\"/>';\n\to[o.length] =     '<a:font script=\"Taml\" typeface=\"Latha\"/>';\n\to[o.length] =     '<a:font script=\"Syrc\" typeface=\"Estrangelo Edessa\"/>';\n\to[o.length] =     '<a:font script=\"Orya\" typeface=\"Kalinga\"/>';\n\to[o.length] =     '<a:font script=\"Mlym\" typeface=\"Kartika\"/>';\n\to[o.length] =     '<a:font script=\"Laoo\" typeface=\"DokChampa\"/>';\n\to[o.length] =     '<a:font script=\"Sinh\" typeface=\"Iskoola Pota\"/>';\n\to[o.length] =     '<a:font script=\"Mong\" typeface=\"Mongolian Baiti\"/>';\n\to[o.length] =     '<a:font script=\"Viet\" typeface=\"Times New Roman\"/>';\n\to[o.length] =     '<a:font script=\"Uigh\" typeface=\"Microsoft Uighur\"/>';\n\to[o.length] =     '<a:font script=\"Geor\" typeface=\"Sylfaen\"/>';\n\to[o.length] =    '</a:majorFont>';\n\to[o.length] =    '<a:minorFont>';\n\to[o.length] =     '<a:latin typeface=\"Calibri\"/>';\n\to[o.length] =     '<a:ea typeface=\"\"/>';\n\to[o.length] =     '<a:cs typeface=\"\"/>';\n\to[o.length] =     '<a:font script=\"Jpan\" typeface=\"ＭＳ Ｐゴシック\"/>';\n\to[o.length] =     '<a:font script=\"Hang\" typeface=\"맑은 고딕\"/>';\n\to[o.length] =     '<a:font script=\"Hans\" typeface=\"宋体\"/>';\n\to[o.length] =     '<a:font script=\"Hant\" typeface=\"新細明體\"/>';\n\to[o.length] =     '<a:font script=\"Arab\" typeface=\"Arial\"/>';\n\to[o.length] =     '<a:font script=\"Hebr\" typeface=\"Arial\"/>';\n\to[o.length] =     '<a:font script=\"Thai\" typeface=\"Tahoma\"/>';\n\to[o.length] =     '<a:font script=\"Ethi\" typeface=\"Nyala\"/>';\n\to[o.length] =     '<a:font script=\"Beng\" typeface=\"Vrinda\"/>';\n\to[o.length] =     '<a:font script=\"Gujr\" typeface=\"Shruti\"/>';\n\to[o.length] =     '<a:font script=\"Khmr\" typeface=\"DaunPenh\"/>';\n\to[o.length] =     '<a:font script=\"Knda\" typeface=\"Tunga\"/>';\n\to[o.length] =     '<a:font script=\"Guru\" typeface=\"Raavi\"/>';\n\to[o.length] =     '<a:font script=\"Cans\" typeface=\"Euphemia\"/>';\n\to[o.length] =     '<a:font script=\"Cher\" typeface=\"Plantagenet Cherokee\"/>';\n\to[o.length] =     '<a:font script=\"Yiii\" typeface=\"Microsoft Yi Baiti\"/>';\n\to[o.length] =     '<a:font script=\"Tibt\" typeface=\"Microsoft Himalaya\"/>';\n\to[o.length] =     '<a:font script=\"Thaa\" typeface=\"MV Boli\"/>';\n\to[o.length] =     '<a:font script=\"Deva\" typeface=\"Mangal\"/>';\n\to[o.length] =     '<a:font script=\"Telu\" typeface=\"Gautami\"/>';\n\to[o.length] =     '<a:font script=\"Taml\" typeface=\"Latha\"/>';\n\to[o.length] =     '<a:font script=\"Syrc\" typeface=\"Estrangelo Edessa\"/>';\n\to[o.length] =     '<a:font script=\"Orya\" typeface=\"Kalinga\"/>';\n\to[o.length] =     '<a:font script=\"Mlym\" typeface=\"Kartika\"/>';\n\to[o.length] =     '<a:font script=\"Laoo\" typeface=\"DokChampa\"/>';\n\to[o.length] =     '<a:font script=\"Sinh\" typeface=\"Iskoola Pota\"/>';\n\to[o.length] =     '<a:font script=\"Mong\" typeface=\"Mongolian Baiti\"/>';\n\to[o.length] =     '<a:font script=\"Viet\" typeface=\"Arial\"/>';\n\to[o.length] =     '<a:font script=\"Uigh\" typeface=\"Microsoft Uighur\"/>';\n\to[o.length] =     '<a:font script=\"Geor\" typeface=\"Sylfaen\"/>';\n\to[o.length] =    '</a:minorFont>';\n\to[o.length] =   '</a:fontScheme>';\n\n\to[o.length] =   '<a:fmtScheme name=\"Office\">';\n\to[o.length] =    '<a:fillStyleLst>';\n\to[o.length] =     '<a:solidFill><a:schemeClr val=\"phClr\"/></a:solidFill>';\n\to[o.length] =     '<a:gradFill rotWithShape=\"1\">';\n\to[o.length] =      '<a:gsLst>';\n\to[o.length] =       '<a:gs pos=\"0\"><a:schemeClr val=\"phClr\"><a:tint val=\"50000\"/><a:satMod val=\"300000\"/></a:schemeClr></a:gs>';\n\to[o.length] =       '<a:gs pos=\"35000\"><a:schemeClr val=\"phClr\"><a:tint val=\"37000\"/><a:satMod val=\"300000\"/></a:schemeClr></a:gs>';\n\to[o.length] =       '<a:gs pos=\"100000\"><a:schemeClr val=\"phClr\"><a:tint val=\"15000\"/><a:satMod val=\"350000\"/></a:schemeClr></a:gs>';\n\to[o.length] =      '</a:gsLst>';\n\to[o.length] =      '<a:lin ang=\"16200000\" scaled=\"1\"/>';\n\to[o.length] =     '</a:gradFill>';\n\to[o.length] =     '<a:gradFill rotWithShape=\"1\">';\n\to[o.length] =      '<a:gsLst>';\n\to[o.length] =       '<a:gs pos=\"0\"><a:schemeClr val=\"phClr\"><a:tint val=\"100000\"/><a:shade val=\"100000\"/><a:satMod val=\"130000\"/></a:schemeClr></a:gs>';\n\to[o.length] =       '<a:gs pos=\"100000\"><a:schemeClr val=\"phClr\"><a:tint val=\"50000\"/><a:shade val=\"100000\"/><a:satMod val=\"350000\"/></a:schemeClr></a:gs>';\n\to[o.length] =      '</a:gsLst>';\n\to[o.length] =      '<a:lin ang=\"16200000\" scaled=\"0\"/>';\n\to[o.length] =     '</a:gradFill>';\n\to[o.length] =    '</a:fillStyleLst>';\n\to[o.length] =    '<a:lnStyleLst>';\n\to[o.length] =     '<a:ln w=\"9525\" cap=\"flat\" cmpd=\"sng\" algn=\"ctr\"><a:solidFill><a:schemeClr val=\"phClr\"><a:shade val=\"95000\"/><a:satMod val=\"105000\"/></a:schemeClr></a:solidFill><a:prstDash val=\"solid\"/></a:ln>';\n\to[o.length] =     '<a:ln w=\"25400\" cap=\"flat\" cmpd=\"sng\" algn=\"ctr\"><a:solidFill><a:schemeClr val=\"phClr\"/></a:solidFill><a:prstDash val=\"solid\"/></a:ln>';\n\to[o.length] =     '<a:ln w=\"38100\" cap=\"flat\" cmpd=\"sng\" algn=\"ctr\"><a:solidFill><a:schemeClr val=\"phClr\"/></a:solidFill><a:prstDash val=\"solid\"/></a:ln>';\n\to[o.length] =    '</a:lnStyleLst>';\n\to[o.length] =    '<a:effectStyleLst>';\n\to[o.length] =     '<a:effectStyle>';\n\to[o.length] =      '<a:effectLst>';\n\to[o.length] =       '<a:outerShdw blurRad=\"40000\" dist=\"20000\" dir=\"5400000\" rotWithShape=\"0\"><a:srgbClr val=\"000000\"><a:alpha val=\"38000\"/></a:srgbClr></a:outerShdw>';\n\to[o.length] =      '</a:effectLst>';\n\to[o.length] =     '</a:effectStyle>';\n\to[o.length] =     '<a:effectStyle>';\n\to[o.length] =      '<a:effectLst>';\n\to[o.length] =       '<a:outerShdw blurRad=\"40000\" dist=\"23000\" dir=\"5400000\" rotWithShape=\"0\"><a:srgbClr val=\"000000\"><a:alpha val=\"35000\"/></a:srgbClr></a:outerShdw>';\n\to[o.length] =      '</a:effectLst>';\n\to[o.length] =     '</a:effectStyle>';\n\to[o.length] =     '<a:effectStyle>';\n\to[o.length] =      '<a:effectLst>';\n\to[o.length] =       '<a:outerShdw blurRad=\"40000\" dist=\"23000\" dir=\"5400000\" rotWithShape=\"0\"><a:srgbClr val=\"000000\"><a:alpha val=\"35000\"/></a:srgbClr></a:outerShdw>';\n\to[o.length] =      '</a:effectLst>';\n\to[o.length] =      '<a:scene3d><a:camera prst=\"orthographicFront\"><a:rot lat=\"0\" lon=\"0\" rev=\"0\"/></a:camera><a:lightRig rig=\"threePt\" dir=\"t\"><a:rot lat=\"0\" lon=\"0\" rev=\"1200000\"/></a:lightRig></a:scene3d>';\n\to[o.length] =      '<a:sp3d><a:bevelT w=\"63500\" h=\"25400\"/></a:sp3d>';\n\to[o.length] =     '</a:effectStyle>';\n\to[o.length] =    '</a:effectStyleLst>';\n\to[o.length] =    '<a:bgFillStyleLst>';\n\to[o.length] =     '<a:solidFill><a:schemeClr val=\"phClr\"/></a:solidFill>';\n\to[o.length] =     '<a:gradFill rotWithShape=\"1\">';\n\to[o.length] =      '<a:gsLst>';\n\to[o.length] =       '<a:gs pos=\"0\"><a:schemeClr val=\"phClr\"><a:tint val=\"40000\"/><a:satMod val=\"350000\"/></a:schemeClr></a:gs>';\n\to[o.length] =       '<a:gs pos=\"40000\"><a:schemeClr val=\"phClr\"><a:tint val=\"45000\"/><a:shade val=\"99000\"/><a:satMod val=\"350000\"/></a:schemeClr></a:gs>';\n\to[o.length] =       '<a:gs pos=\"100000\"><a:schemeClr val=\"phClr\"><a:shade val=\"20000\"/><a:satMod val=\"255000\"/></a:schemeClr></a:gs>';\n\to[o.length] =      '</a:gsLst>';\n\to[o.length] =      '<a:path path=\"circle\"><a:fillToRect l=\"50000\" t=\"-80000\" r=\"50000\" b=\"180000\"/></a:path>';\n\to[o.length] =     '</a:gradFill>';\n\to[o.length] =     '<a:gradFill rotWithShape=\"1\">';\n\to[o.length] =      '<a:gsLst>';\n\to[o.length] =       '<a:gs pos=\"0\"><a:schemeClr val=\"phClr\"><a:tint val=\"80000\"/><a:satMod val=\"300000\"/></a:schemeClr></a:gs>';\n\to[o.length] =       '<a:gs pos=\"100000\"><a:schemeClr val=\"phClr\"><a:shade val=\"30000\"/><a:satMod val=\"200000\"/></a:schemeClr></a:gs>';\n\to[o.length] =      '</a:gsLst>';\n\to[o.length] =      '<a:path path=\"circle\"><a:fillToRect l=\"50000\" t=\"50000\" r=\"50000\" b=\"50000\"/></a:path>';\n\to[o.length] =     '</a:gradFill>';\n\to[o.length] =    '</a:bgFillStyleLst>';\n\to[o.length] =   '</a:fmtScheme>';\n\to[o.length] =  '</a:themeElements>';\n\n\to[o.length] =  '<a:objectDefaults>';\n\to[o.length] =   '<a:spDef>';\n\to[o.length] =    '<a:spPr/><a:bodyPr/><a:lstStyle/><a:style><a:lnRef idx=\"1\"><a:schemeClr val=\"accent1\"/></a:lnRef><a:fillRef idx=\"3\"><a:schemeClr val=\"accent1\"/></a:fillRef><a:effectRef idx=\"2\"><a:schemeClr val=\"accent1\"/></a:effectRef><a:fontRef idx=\"minor\"><a:schemeClr val=\"lt1\"/></a:fontRef></a:style>';\n\to[o.length] =   '</a:spDef>';\n\to[o.length] =   '<a:lnDef>';\n\to[o.length] =    '<a:spPr/><a:bodyPr/><a:lstStyle/><a:style><a:lnRef idx=\"2\"><a:schemeClr val=\"accent1\"/></a:lnRef><a:fillRef idx=\"0\"><a:schemeClr val=\"accent1\"/></a:fillRef><a:effectRef idx=\"1\"><a:schemeClr val=\"accent1\"/></a:effectRef><a:fontRef idx=\"minor\"><a:schemeClr val=\"tx1\"/></a:fontRef></a:style>';\n\to[o.length] =   '</a:lnDef>';\n\to[o.length] =  '</a:objectDefaults>';\n\to[o.length] =  '<a:extraClrSchemeLst/>';\n\to[o.length] = '</a:theme>';\n\treturn o.join(\"\");\n}\n/* [MS-XLS] 2.4.326 TODO: payload is a zip file */\nfunction parse_Theme(blob, length, opts) {\n\tvar end = blob.l + length;\n\tvar dwThemeVersion = blob.read_shift(4);\n\tif(dwThemeVersion === 124226) return;\n\tif(!opts.cellStyles) { blob.l = end; return; }\n\tvar data = blob.slice(blob.l);\n\tblob.l = end;\n\tvar zip; try { zip = zip_read(data, {type: \"array\"}); } catch(e) { return; }\n\tvar themeXML = getzipstr(zip, \"theme/theme/theme1.xml\", true);\n\tif(!themeXML) return;\n\treturn parse_theme_xml(themeXML, opts);\n}\n\n/* 2.5.49 */\nfunction parse_ColorTheme(blob/*::, length*/) { return blob.read_shift(4); }\n\n/* 2.5.155 */\nfunction parse_FullColorExt(blob/*::, length*/) {\n\tvar o = {};\n\to.xclrType = blob.read_shift(2);\n\to.nTintShade = blob.read_shift(2);\n\tswitch(o.xclrType) {\n\t\tcase 0: blob.l += 4; break;\n\t\tcase 1: o.xclrValue = parse_IcvXF(blob, 4); break;\n\t\tcase 2: o.xclrValue = parse_LongRGBA(blob, 4); break;\n\t\tcase 3: o.xclrValue = parse_ColorTheme(blob, 4); break;\n\t\tcase 4: blob.l += 4; break;\n\t}\n\tblob.l += 8;\n\treturn o;\n}\n\n/* 2.5.164 TODO: read 7 bits*/\nfunction parse_IcvXF(blob, length) {\n\treturn parsenoop(blob, length);\n}\n\n/* 2.5.280 */\nfunction parse_XFExtGradient(blob, length) {\n\treturn parsenoop(blob, length);\n}\n\n/* [MS-XLS] 2.5.108 */\nfunction parse_ExtProp(blob/*::, length*/)/*:Array<any>*/ {\n\tvar extType = blob.read_shift(2);\n\tvar cb = blob.read_shift(2) - 4;\n\tvar o = [extType];\n\tswitch(extType) {\n\t\tcase 0x04: case 0x05: case 0x07: case 0x08:\n\t\tcase 0x09: case 0x0A: case 0x0B: case 0x0D:\n\t\t\to[1] = parse_FullColorExt(blob, cb); break;\n\t\tcase 0x06: o[1] = parse_XFExtGradient(blob, cb); break;\n\t\tcase 0x0E: case 0x0F: o[1] = blob.read_shift(cb === 1 ? 1 : 2); break;\n\t\tdefault: throw new Error(\"Unrecognized ExtProp type: \" + extType + \" \" + cb);\n\t}\n\treturn o;\n}\n\n/* 2.4.355 */\nfunction parse_XFExt(blob, length) {\n\tvar end = blob.l + length;\n\tblob.l += 2;\n\tvar ixfe = blob.read_shift(2);\n\tblob.l += 2;\n\tvar cexts = blob.read_shift(2);\n\tvar ext/*:AOA*/ = [];\n\twhile(cexts-- > 0) ext.push(parse_ExtProp(blob, end-blob.l));\n\treturn {ixfe:ixfe, ext:ext};\n}\n\n/* xf is an XF, see parse_XFExt for xfext */\nfunction update_xfext(xf, xfext) {\n\txfext.forEach(function(xfe) {\n\t\tswitch(xfe[0]) { /* 2.5.108 extPropData */\n\t\t\tcase 0x04: break; /* foreground color */\n\t\t\tcase 0x05: break; /* background color */\n\t\t\tcase 0x06: break; /* gradient fill */\n\t\t\tcase 0x07: break; /* top cell border color */\n\t\t\tcase 0x08: break; /* bottom cell border color */\n\t\t\tcase 0x09: break; /* left cell border color */\n\t\t\tcase 0x0a: break; /* right cell border color */\n\t\t\tcase 0x0b: break; /* diagonal cell border color */\n\t\t\tcase 0x0d: /* text color */\n\t\t\t\tbreak;\n\t\t\tcase 0x0e: break; /* font scheme */\n\t\t\tcase 0x0f: break; /* indentation level */\n\t\t}\n\t});\n}\n\nfunction parse_BrtMdtinfo(data, length) {\n  return {\n    flags: data.read_shift(4),\n    version: data.read_shift(4),\n    name: parse_XLWideString(data, length - 8)\n  };\n}\nfunction write_BrtMdtinfo(data) {\n  var o = new_buf(12 + 2 * data.name.length);\n  o.write_shift(4, data.flags);\n  o.write_shift(4, data.version);\n  write_XLWideString(data.name, o);\n  return o.slice(0, o.l);\n}\nfunction parse_BrtMdb(data) {\n  var out = [];\n  var cnt = data.read_shift(4);\n  while (cnt-- > 0)\n    out.push([data.read_shift(4), data.read_shift(4)]);\n  return out;\n}\nfunction write_BrtMdb(mdb) {\n  var o = new_buf(4 + 8 * mdb.length);\n  o.write_shift(4, mdb.length);\n  for (var i = 0; i < mdb.length; ++i) {\n    o.write_shift(4, mdb[i][0]);\n    o.write_shift(4, mdb[i][1]);\n  }\n  return o;\n}\nfunction write_BrtBeginEsfmd(cnt, name) {\n  var o = new_buf(8 + 2 * name.length);\n  o.write_shift(4, cnt);\n  write_XLWideString(name, o);\n  return o.slice(0, o.l);\n}\nfunction parse_BrtBeginEsmdb(data) {\n  data.l += 4;\n  return data.read_shift(4) != 0;\n}\nfunction write_BrtBeginEsmdb(cnt, cm) {\n  var o = new_buf(8);\n  o.write_shift(4, cnt);\n  o.write_shift(4, cm ? 1 : 0);\n  return o;\n}\nfunction parse_xlmeta_bin(data, name, _opts) {\n  var out = { Types: [], Cell: [], Value: [] };\n  var opts = _opts || {};\n  var state = [];\n  var pass = false;\n  var metatype = 2;\n  recordhopper(data, function(val, R, RT) {\n    switch (RT) {\n      case 335:\n        out.Types.push({ name: val.name });\n        break;\n      case 51:\n        val.forEach(function(r) {\n          if (metatype == 1)\n            out.Cell.push({ type: out.Types[r[0] - 1].name, index: r[1] });\n          else if (metatype == 0)\n            out.Value.push({ type: out.Types[r[0] - 1].name, index: r[1] });\n        });\n        break;\n      case 337:\n        metatype = val ? 1 : 0;\n        break;\n      case 338:\n        metatype = 2;\n        break;\n      case 35:\n        state.push(RT);\n        pass = true;\n        break;\n      case 36:\n        state.pop();\n        pass = false;\n        break;\n      default:\n        if (R.T) {\n        } else if (!pass || opts.WTF && state[state.length - 1] != 35)\n          throw new Error(\"Unexpected record 0x\" + RT.toString(16));\n    }\n  });\n  return out;\n}\nfunction write_xlmeta_bin() {\n  var ba = buf_array();\n  write_record(ba, 332);\n  write_record(ba, 334, write_UInt32LE(1));\n  write_record(ba, 335, write_BrtMdtinfo({\n    name: \"XLDAPR\",\n    version: 12e4,\n    flags: 3496657072\n  }));\n  write_record(ba, 336);\n  write_record(ba, 339, write_BrtBeginEsfmd(1, \"XLDAPR\"));\n  write_record(ba, 52);\n  write_record(ba, 35, write_UInt32LE(514));\n  write_record(ba, 4096, write_UInt32LE(0));\n  write_record(ba, 4097, writeuint16(1));\n  write_record(ba, 36);\n  write_record(ba, 53);\n  write_record(ba, 340);\n  write_record(ba, 337, write_BrtBeginEsmdb(1, true));\n  write_record(ba, 51, write_BrtMdb([[1, 0]]));\n  write_record(ba, 338);\n  write_record(ba, 333);\n  return ba.end();\n}\nfunction parse_xlmeta_xml(data, name, opts) {\n  var out = { Types: [], Cell: [], Value: [] };\n  if (!data)\n    return out;\n  var pass = false;\n  var metatype = 2;\n  var lastmeta;\n  data.replace(tagregex, function(x) {\n    var y = parsexmltag(x);\n    switch (strip_ns(y[0])) {\n      case \"<?xml\":\n        break;\n      case \"<metadata\":\n      case \"</metadata>\":\n        break;\n      case \"<metadataTypes\":\n      case \"</metadataTypes>\":\n        break;\n      case \"<metadataType\":\n        out.Types.push({ name: y.name });\n        break;\n      case \"</metadataType>\":\n        break;\n      case \"<futureMetadata\":\n        for (var j = 0; j < out.Types.length; ++j)\n          if (out.Types[j].name == y.name)\n            lastmeta = out.Types[j];\n        break;\n      case \"</futureMetadata>\":\n        break;\n      case \"<bk>\":\n        break;\n      case \"</bk>\":\n        break;\n      case \"<rc\":\n        if (metatype == 1)\n          out.Cell.push({ type: out.Types[y.t - 1].name, index: +y.v });\n        else if (metatype == 0)\n          out.Value.push({ type: out.Types[y.t - 1].name, index: +y.v });\n        break;\n      case \"</rc>\":\n        break;\n      case \"<cellMetadata\":\n        metatype = 1;\n        break;\n      case \"</cellMetadata>\":\n        metatype = 2;\n        break;\n      case \"<valueMetadata\":\n        metatype = 0;\n        break;\n      case \"</valueMetadata>\":\n        metatype = 2;\n        break;\n      case \"<extLst\":\n      case \"<extLst>\":\n      case \"</extLst>\":\n      case \"<extLst/>\":\n        break;\n      case \"<ext\":\n        pass = true;\n        break;\n      case \"</ext>\":\n        pass = false;\n        break;\n      case \"<rvb\":\n        if (!lastmeta)\n          break;\n        if (!lastmeta.offsets)\n          lastmeta.offsets = [];\n        lastmeta.offsets.push(+y.i);\n        break;\n      default:\n        if (!pass && opts.WTF)\n          throw new Error(\"unrecognized \" + y[0] + \" in metadata\");\n    }\n    return x;\n  });\n  return out;\n}\nfunction write_xlmeta_xml() {\n  var o = [XML_HEADER];\n  o.push('<metadata xmlns=\"http://schemas.openxmlformats.org/spreadsheetml/2006/main\" xmlns:xlrd=\"http://schemas.microsoft.com/office/spreadsheetml/2017/richdata\" xmlns:xda=\"http://schemas.microsoft.com/office/spreadsheetml/2017/dynamicarray\">\\n  <metadataTypes count=\"1\">\\n    <metadataType name=\"XLDAPR\" minSupportedVersion=\"120000\" copy=\"1\" pasteAll=\"1\" pasteValues=\"1\" merge=\"1\" splitFirst=\"1\" rowColShift=\"1\" clearFormats=\"1\" clearComments=\"1\" assign=\"1\" coerce=\"1\" cellMeta=\"1\"/>\\n  </metadataTypes>\\n  <futureMetadata name=\"XLDAPR\" count=\"1\">\\n    <bk>\\n      <extLst>\\n        <ext uri=\"{bdbb8cdc-fa1e-496e-a857-3c3f30c029c3}\">\\n          <xda:dynamicArrayProperties fDynamic=\"1\" fCollapsed=\"0\"/>\\n        </ext>\\n      </extLst>\\n    </bk>\\n  </futureMetadata>\\n  <cellMetadata count=\"1\">\\n    <bk>\\n      <rc t=\"1\" v=\"0\"/>\\n    </bk>\\n  </cellMetadata>\\n</metadata>');\n  return o.join(\"\");\n}\n/* 18.6 Calculation Chain */\nfunction parse_cc_xml(data/*::, name, opts*/)/*:Array<any>*/ {\n\tvar d = [];\n\tif(!data) return d;\n\tvar i = 1;\n\t(data.match(tagregex)||[]).forEach(function(x) {\n\t\tvar y = parsexmltag(x);\n\t\tswitch(y[0]) {\n\t\t\tcase '<?xml': break;\n\t\t\t/* 18.6.2  calcChain CT_CalcChain 1 */\n\t\t\tcase '<calcChain': case '<calcChain>': case '</calcChain>': break;\n\t\t\t/* 18.6.1  c CT_CalcCell 1 */\n\t\t\tcase '<c': delete y[0]; if(y.i) i = y.i; else y.i = i; d.push(y); break;\n\t\t}\n\t});\n\treturn d;\n}\n\n//function write_cc_xml(data, opts) { }\n\n/* [MS-XLSB] 2.6.4.1 */\nfunction parse_BrtCalcChainItem$(data) {\n\tvar out = {};\n\tout.i = data.read_shift(4);\n\tvar cell = {};\n\tcell.r = data.read_shift(4);\n\tcell.c = data.read_shift(4);\n\tout.r = encode_cell(cell);\n\tvar flags = data.read_shift(1);\n\tif(flags & 0x2) out.l = '1';\n\tif(flags & 0x8) out.a = '1';\n\treturn out;\n}\n\n/* 18.6 Calculation Chain */\nfunction parse_cc_bin(data, name, opts) {\n\tvar out = [];\n\tvar pass = false;\n\trecordhopper(data, function hopper_cc(val, R, RT) {\n\t\tswitch(RT) {\n\t\t\tcase 0x003F: /* 'BrtCalcChainItem$' */\n\t\t\t\tout.push(val); break;\n\n\t\t\tdefault:\n\t\t\t\tif(R.T){/* empty */}\n\t\t\t\telse if(!pass || opts.WTF) throw new Error(\"Unexpected record 0x\" + RT.toString(16));\n\t\t}\n\t});\n\treturn out;\n}\n\n//function write_cc_bin(data, opts) { }\n/* 18.14 Supplementary Workbook Data */\nfunction parse_xlink_xml(/*::data, rel, name:string, _opts*/) {\n\t//var opts = _opts || {};\n\t//if(opts.WTF) throw \"XLSX External Link\";\n}\n\n/* [MS-XLSB] 2.1.7.25 External Link */\nfunction parse_xlink_bin(data, rel, name/*:string*/, _opts) {\n\tif(!data) return data;\n\tvar opts = _opts || {};\n\n\tvar pass = false, end = false;\n\n\trecordhopper(data, function xlink_parse(val, R, RT) {\n\t\tif(end) return;\n\t\tswitch(RT) {\n\t\t\tcase 0x0167: /* 'BrtSupTabs' */\n\t\t\tcase 0x016B: /* 'BrtExternTableStart' */\n\t\t\tcase 0x016C: /* 'BrtExternTableEnd' */\n\t\t\tcase 0x016E: /* 'BrtExternRowHdr' */\n\t\t\tcase 0x016F: /* 'BrtExternCellBlank' */\n\t\t\tcase 0x0170: /* 'BrtExternCellReal' */\n\t\t\tcase 0x0171: /* 'BrtExternCellBool' */\n\t\t\tcase 0x0172: /* 'BrtExternCellError' */\n\t\t\tcase 0x0173: /* 'BrtExternCellString' */\n\t\t\tcase 0x01D8: /* 'BrtExternValueMeta' */\n\t\t\tcase 0x0241: /* 'BrtSupNameStart' */\n\t\t\tcase 0x0242: /* 'BrtSupNameValueStart' */\n\t\t\tcase 0x0243: /* 'BrtSupNameValueEnd' */\n\t\t\tcase 0x0244: /* 'BrtSupNameNum' */\n\t\t\tcase 0x0245: /* 'BrtSupNameErr' */\n\t\t\tcase 0x0246: /* 'BrtSupNameSt' */\n\t\t\tcase 0x0247: /* 'BrtSupNameNil' */\n\t\t\tcase 0x0248: /* 'BrtSupNameBool' */\n\t\t\tcase 0x0249: /* 'BrtSupNameFmla' */\n\t\t\tcase 0x024A: /* 'BrtSupNameBits' */\n\t\t\tcase 0x024B: /* 'BrtSupNameEnd' */\n\t\t\t\tbreak;\n\n\t\t\tcase 0x0023: /* 'BrtFRTBegin' */\n\t\t\t\tpass = true; break;\n\t\t\tcase 0x0024: /* 'BrtFRTEnd' */\n\t\t\t\tpass = false; break;\n\n\t\t\tdefault:\n\t\t\t\tif(R.T){/* empty */}\n\t\t\t\telse if(!pass || opts.WTF) throw new Error(\"Unexpected record 0x\" + RT.toString(16));\n\t\t}\n\t}, opts);\n}\n/* 20.5 DrawingML - SpreadsheetML Drawing */\n/* 20.5.2.35 wsDr CT_Drawing */\nfunction parse_drawing(data, rels/*:any*/) {\n\tif(!data) return \"??\";\n\t/*\n\t  Chartsheet Drawing:\n\t   - 20.5.2.35 wsDr CT_Drawing\n\t    - 20.5.2.1  absoluteAnchor CT_AbsoluteAnchor\n\t     - 20.5.2.16 graphicFrame CT_GraphicalObjectFrame\n\t      - 20.1.2.2.16 graphic CT_GraphicalObject\n\t       - 20.1.2.2.17 graphicData CT_GraphicalObjectData\n          - chart reference\n\t   the actual type is based on the URI of the graphicData\n\t\tTODO: handle embedded charts and other types of graphics\n\t*/\n\tvar id = (data.match(/<c:chart [^>]*r:id=\"([^\"]*)\"/)||[\"\",\"\"])[1];\n\n\treturn rels['!id'][id].Target;\n}\n\n/* L.5.5.2 SpreadsheetML Comments + VML Schema */\nvar _shapeid = 1024;\nfunction write_comments_vml(rId/*:number*/, comments) {\n\tvar csize = [21600, 21600];\n\t/* L.5.2.1.2 Path Attribute */\n\tvar bbox = [\"m0,0l0\",csize[1],csize[0],csize[1],csize[0],\"0xe\"].join(\",\");\n\tvar o = [\n\t\twritextag(\"xml\", null, { 'xmlns:v': XLMLNS.v, 'xmlns:o': XLMLNS.o, 'xmlns:x': XLMLNS.x, 'xmlns:mv': XLMLNS.mv }).replace(/\\/>/,\">\"),\n\t\twritextag(\"o:shapelayout\", writextag(\"o:idmap\", null, {'v:ext':\"edit\", 'data':rId}), {'v:ext':\"edit\"}),\n\t\twritextag(\"v:shapetype\", [\n\t\t\twritextag(\"v:stroke\", null, {joinstyle:\"miter\"}),\n\t\t\twritextag(\"v:path\", null, {gradientshapeok:\"t\", 'o:connecttype':\"rect\"})\n\t\t].join(\"\"), {id:\"_x0000_t202\", 'o:spt':202, coordsize:csize.join(\",\"),path:bbox})\n\t];\n\twhile(_shapeid < rId * 1000) _shapeid += 1000;\n\n\tcomments.forEach(function(x) {\n\tvar c = decode_cell(x[0]);\n\tvar fillopts = /*::(*/{'color2':\"#BEFF82\", 'type':\"gradient\"}/*:: :any)*/;\n\tif(fillopts.type == \"gradient\") fillopts.angle = \"-180\";\n\tvar fillparm = fillopts.type == \"gradient\" ? writextag(\"o:fill\", null, {type:\"gradientUnscaled\", 'v:ext':\"view\"}) : null;\n\tvar fillxml = writextag('v:fill', fillparm, fillopts);\n\n\tvar shadata = ({on:\"t\", 'obscured':\"t\"}/*:any*/);\n\t++_shapeid;\n\n\to = o.concat([\n\t'<v:shape' + wxt_helper({\n\t\tid:'_x0000_s' + _shapeid,\n\t\ttype:\"#_x0000_t202\",\n\t\tstyle:\"position:absolute; margin-left:80pt;margin-top:5pt;width:104pt;height:64pt;z-index:10\" + (x[1].hidden ? \";visibility:hidden\" : \"\") ,\n\t\tfillcolor:\"#ECFAD4\",\n\t\tstrokecolor:\"#edeaa1\"\n\t}) + '>',\n\t\tfillxml,\n\t\twritextag(\"v:shadow\", null, shadata),\n\t\twritextag(\"v:path\", null, {'o:connecttype':\"none\"}),\n\t\t'<v:textbox><div style=\"text-align:left\"></div></v:textbox>',\n\t\t'<x:ClientData ObjectType=\"Note\">',\n\t\t\t'<x:MoveWithCells/>',\n\t\t\t'<x:SizeWithCells/>',\n\t\t\t/* Part 4 19.4.2.3 Anchor (Anchor) */\n\t\t\twritetag('x:Anchor', [c.c+1, 0, c.r+1, 0, c.c+3, 20, c.r+5, 20].join(\",\")),\n\t\t\twritetag('x:AutoFill', \"False\"),\n\t\t\twritetag('x:Row', String(c.r)),\n\t\t\twritetag('x:Column', String(c.c)),\n\t\t\tx[1].hidden ? '' : '<x:Visible/>',\n\t\t'</x:ClientData>',\n\t'</v:shape>'\n\t]); });\n\to.push('</xml>');\n\treturn o.join(\"\");\n}\nfunction sheet_insert_comments(sheet, comments/*:Array<RawComment>*/, threaded/*:boolean*/, people/*:?Array<any>*/) {\n\tvar dense = Array.isArray(sheet);\n\tvar cell/*:Cell*/;\n\tcomments.forEach(function(comment) {\n\t\tvar r = decode_cell(comment.ref);\n\t\tif(dense) {\n\t\t\tif(!sheet[r.r]) sheet[r.r] = [];\n\t\t\tcell = sheet[r.r][r.c];\n\t\t} else cell = sheet[comment.ref];\n\t\tif (!cell) {\n\t\t\tcell = ({t:\"z\"}/*:any*/);\n\t\t\tif(dense) sheet[r.r][r.c] = cell;\n\t\t\telse sheet[comment.ref] = cell;\n\t\t\tvar range = safe_decode_range(sheet[\"!ref\"]||\"BDWGO1000001:A1\");\n\t\t\tif(range.s.r > r.r) range.s.r = r.r;\n\t\t\tif(range.e.r < r.r) range.e.r = r.r;\n\t\t\tif(range.s.c > r.c) range.s.c = r.c;\n\t\t\tif(range.e.c < r.c) range.e.c = r.c;\n\t\t\tvar encoded = encode_range(range);\n\t\t\tif (encoded !== sheet[\"!ref\"]) sheet[\"!ref\"] = encoded;\n\t\t}\n\n\t\tif (!cell.c) cell.c = [];\n\t\tvar o/*:Comment*/ = ({a: comment.author, t: comment.t, r: comment.r, T: threaded});\n\t\tif(comment.h) o.h = comment.h;\n\n\t\t/* threaded comments always override */\n\t\tfor(var i = cell.c.length - 1; i >= 0; --i) {\n\t\t\tif(!threaded && cell.c[i].T) return;\n\t\t\tif(threaded && !cell.c[i].T) cell.c.splice(i, 1);\n\t\t}\n\t\tif(threaded && people) for(i = 0; i < people.length; ++i) {\n\t\t\tif(o.a == people[i].id) { o.a = people[i].name || o.a; break; }\n\t\t}\n\t\tcell.c.push(o);\n\t});\n}\n\n/* 18.7 Comments */\nfunction parse_comments_xml(data/*:string*/, opts)/*:Array<RawComment>*/ {\n\t/* 18.7.6 CT_Comments */\n\tif(data.match(/<(?:\\w+:)?comments *\\/>/)) return [];\n\tvar authors/*:Array<string>*/ = [];\n\tvar commentList/*:Array<RawComment>*/ = [];\n\tvar authtag = data.match(/<(?:\\w+:)?authors>([\\s\\S]*)<\\/(?:\\w+:)?authors>/);\n\tif(authtag && authtag[1]) authtag[1].split(/<\\/\\w*:?author>/).forEach(function(x) {\n\t\tif(x === \"\" || x.trim() === \"\") return;\n\t\tvar a = x.match(/<(?:\\w+:)?author[^>]*>(.*)/);\n\t\tif(a) authors.push(a[1]);\n\t});\n\tvar cmnttag = data.match(/<(?:\\w+:)?commentList>([\\s\\S]*)<\\/(?:\\w+:)?commentList>/);\n\tif(cmnttag && cmnttag[1]) cmnttag[1].split(/<\\/\\w*:?comment>/).forEach(function(x) {\n\t\tif(x === \"\" || x.trim() === \"\") return;\n\t\tvar cm = x.match(/<(?:\\w+:)?comment[^>]*>/);\n\t\tif(!cm) return;\n\t\tvar y = parsexmltag(cm[0]);\n\t\tvar comment/*:RawComment*/ = ({ author: y.authorId && authors[y.authorId] || \"sheetjsghost\", ref: y.ref, guid: y.guid }/*:any*/);\n\t\tvar cell = decode_cell(y.ref);\n\t\tif(opts.sheetRows && opts.sheetRows <= cell.r) return;\n\t\tvar textMatch = x.match(/<(?:\\w+:)?text>([\\s\\S]*)<\\/(?:\\w+:)?text>/);\n\t\tvar rt = !!textMatch && !!textMatch[1] && parse_si(textMatch[1]) || {r:\"\",t:\"\",h:\"\"};\n\t\tcomment.r = rt.r;\n\t\tif(rt.r == \"<t></t>\") rt.t = rt.h = \"\";\n\t\tcomment.t = (rt.t||\"\").replace(/\\r\\n/g,\"\\n\").replace(/\\r/g,\"\\n\");\n\t\tif(opts.cellHTML) comment.h = rt.h;\n\t\tcommentList.push(comment);\n\t});\n\treturn commentList;\n}\n\nfunction write_comments_xml(data/*::, opts*/) {\n\tvar o = [XML_HEADER, writextag('comments', null, { 'xmlns': XMLNS_main[0] })];\n\n\tvar iauthor/*:Array<string>*/ = [];\n\to.push(\"<authors>\");\n\tdata.forEach(function(x) { x[1].forEach(function(w) { var a = escapexml(w.a);\n\t\tif(iauthor.indexOf(a) == -1) {\n\t\t\tiauthor.push(a);\n\t\t\to.push(\"<author>\" + a + \"</author>\");\n\t\t}\n\t\tif(w.T && w.ID && iauthor.indexOf(\"tc=\" + w.ID) == -1) {\n\t\t\tiauthor.push(\"tc=\" + w.ID);\n\t\t\to.push(\"<author>\" + \"tc=\" + w.ID + \"</author>\");\n\t\t}\n\t}); });\n\tif(iauthor.length == 0) { iauthor.push(\"SheetJ5\"); o.push(\"<author>SheetJ5</author>\"); }\n\to.push(\"</authors>\");\n\to.push(\"<commentList>\");\n\tdata.forEach(function(d) {\n\t\t/* 18.7.3 CT_Comment */\n\t\tvar lastauthor = 0, ts = [];\n\t\tif(d[1][0] && d[1][0].T && d[1][0].ID) lastauthor = iauthor.indexOf(\"tc=\" + d[1][0].ID);\n\t\telse d[1].forEach(function(c) {\n\t\t\tif(c.a) lastauthor = iauthor.indexOf(escapexml(c.a));\n\t\t\tts.push(c.t||\"\");\n\t\t});\n\t\to.push('<comment ref=\"' + d[0] + '\" authorId=\"' + lastauthor + '\"><text>');\n\t\tif(ts.length <= 1) o.push(writetag(\"t\", escapexml(ts[0]||\"\")));\n\t\telse {\n\t\t\t/* based on Threaded Comments -> Comments projection */\n\t\t\tvar t = \"Comment:\\n    \" + (ts[0]) + \"\\n\";\n\t\t\tfor(var i = 1; i < ts.length; ++i) t += \"Reply:\\n    \" + ts[i] + \"\\n\";\n\t\t\to.push(writetag(\"t\", escapexml(t)));\n\t\t}\n\t\to.push('</text></comment>');\n\t});\n\to.push(\"</commentList>\");\n\tif(o.length>2) { o[o.length] = ('</comments>'); o[1]=o[1].replace(\"/>\",\">\"); }\n\treturn o.join(\"\");\n}\n\n/* [MS-XLSX] 2.1.17 */\nfunction parse_tcmnt_xml(data/*:string*/, opts)/*:Array<RawComment>*/ {\n\tvar out = [];\n\tvar pass = false, comment = {}, tidx = 0;\n\tdata.replace(tagregex, function xml_tcmnt(x, idx) {\n\t\tvar y/*:any*/ = parsexmltag(x);\n\t\tswitch(strip_ns(y[0])) {\n\t\t\tcase '<?xml': break;\n\n\t\t\t/* 2.6.207 ThreadedComments CT_ThreadedComments */\n\t\t\tcase '<ThreadedComments': break;\n\t\t\tcase '</ThreadedComments>': break;\n\n\t\t\t/* 2.6.205 threadedComment CT_ThreadedComment */\n\t\t\tcase '<threadedComment': comment = {author: y.personId, guid: y.id, ref: y.ref, T: 1}; break;\n\t\t\tcase '</threadedComment>': if(comment.t != null) out.push(comment); break;\n\n\t\t\tcase '<text>': case '<text': tidx = idx + x.length; break;\n\t\t\tcase '</text>': comment.t = data.slice(tidx, idx).replace(/\\r\\n/g, \"\\n\").replace(/\\r/g, \"\\n\"); break;\n\n\t\t\t/* 2.6.206 mentions CT_ThreadedCommentMentions TODO */\n\t\t\tcase '<mentions': case '<mentions>': pass = true; break;\n\t\t\tcase '</mentions>': pass = false; break;\n\n\t\t\t/* 2.6.202 mention CT_Mention TODO */\n\n\t\t\t/* 18.2.10 extLst CT_ExtensionList ? */\n\t\t\tcase '<extLst': case '<extLst>': case '</extLst>': case '<extLst/>': break;\n\t\t\t/* 18.2.7  ext CT_Extension + */\n\t\t\tcase '<ext': pass=true; break;\n\t\t\tcase '</ext>': pass=false; break;\n\n\t\t\tdefault: if(!pass && opts.WTF) throw new Error('unrecognized ' + y[0] + ' in threaded comments');\n\t\t}\n\t\treturn x;\n\t});\n\treturn out;\n}\n\nfunction write_tcmnt_xml(comments, people, opts) {\n\tvar o = [XML_HEADER, writextag('ThreadedComments', null, { 'xmlns': XMLNS.TCMNT }).replace(/[\\/]>/, \">\")];\n\tcomments.forEach(function(carr) {\n\t\tvar rootid = \"\";\n\t\t(carr[1] || []).forEach(function(c, idx) {\n\t\t\tif(!c.T) { delete c.ID; return; }\n\t\t\tif(c.a && people.indexOf(c.a) == -1) people.push(c.a);\n\t\t\tvar tcopts = {\n\t\t\t\tref: carr[0],\n\t\t\t\tid: \"{54EE7951-7262-4200-6969-\" + (\"000000000000\" + opts.tcid++).slice(-12) + \"}\"\n\t\t\t};\n\t\t\tif(idx == 0) rootid = tcopts.id;\n\t\t\telse tcopts.parentId = rootid;\n\t\t\tc.ID = tcopts.id;\n\t\t\tif(c.a) tcopts.personId = \"{54EE7950-7262-4200-6969-\" + (\"000000000000\" + people.indexOf(c.a)).slice(-12) + \"}\";\n\t\t\to.push(writextag('threadedComment', writetag('text', c.t||\"\"), tcopts));\n\t\t});\n\t});\n\to.push('</ThreadedComments>');\n\treturn o.join(\"\");\n}\n\n/* [MS-XLSX] 2.1.18 */\nfunction parse_people_xml(data/*:string*/, opts) {\n\tvar out = [];\n\tvar pass = false;\n\tdata.replace(tagregex, function xml_tcmnt(x) {\n\t\tvar y/*:any*/ = parsexmltag(x);\n\t\tswitch(strip_ns(y[0])) {\n\t\t\tcase '<?xml': break;\n\n\t\t\t/* 2.4.85 personList CT_PersonList */\n\t\t\tcase '<personList': break;\n\t\t\tcase '</personList>': break;\n\n\t\t\t/* 2.6.203 person CT_Person TODO: providers */\n\t\t\tcase '<person': out.push({name: y.displayname, id: y.id }); break;\n\t\t\tcase '</person>': break;\n\n\t\t\t/* 18.2.10 extLst CT_ExtensionList ? */\n\t\t\tcase '<extLst': case '<extLst>': case '</extLst>': case '<extLst/>': break;\n\t\t\t/* 18.2.7  ext CT_Extension + */\n\t\t\tcase '<ext': pass=true; break;\n\t\t\tcase '</ext>': pass=false; break;\n\n\t\t\tdefault: if(!pass && opts.WTF) throw new Error('unrecognized ' + y[0] + ' in threaded comments');\n\t\t}\n\t\treturn x;\n\t});\n\treturn out;\n}\nfunction write_people_xml(people/*, opts*/) {\n\tvar o = [XML_HEADER, writextag('personList', null, {\n\t\t'xmlns': XMLNS.TCMNT,\n\t\t'xmlns:x': XMLNS_main[0]\n\t}).replace(/[\\/]>/, \">\")];\n\tpeople.forEach(function(person, idx) {\n\t\to.push(writextag('person', null, {\n\t\t\tdisplayName: person,\n\t\t\tid: \"{54EE7950-7262-4200-6969-\" + (\"000000000000\" + idx).slice(-12) + \"}\",\n\t\t\tuserId: person,\n\t\t\tproviderId: \"None\"\n\t\t}));\n\t});\n\to.push(\"</personList>\");\n\treturn o.join(\"\");\n}\n/* [MS-XLSB] 2.4.28 BrtBeginComment */\nfunction parse_BrtBeginComment(data) {\n\tvar out = {};\n\tout.iauthor = data.read_shift(4);\n\tvar rfx = parse_UncheckedRfX(data, 16);\n\tout.rfx = rfx.s;\n\tout.ref = encode_cell(rfx.s);\n\tdata.l += 16; /*var guid = parse_GUID(data); */\n\treturn out;\n}\nfunction write_BrtBeginComment(data, o) {\n\tif(o == null) o = new_buf(36);\n\to.write_shift(4, data[1].iauthor);\n\twrite_UncheckedRfX((data[0]/*:any*/), o);\n\to.write_shift(4, 0);\n\to.write_shift(4, 0);\n\to.write_shift(4, 0);\n\to.write_shift(4, 0);\n\treturn o;\n}\n\n/* [MS-XLSB] 2.4.327 BrtCommentAuthor */\nvar parse_BrtCommentAuthor = parse_XLWideString;\nfunction write_BrtCommentAuthor(data) { return write_XLWideString(data.slice(0, 54)); }\n\n/* [MS-XLSB] 2.1.7.8 Comments */\nfunction parse_comments_bin(data, opts)/*:Array<RawComment>*/ {\n\tvar out/*:Array<RawComment>*/ = [];\n\tvar authors/*:Array<string>*/ = [];\n\tvar c = {};\n\tvar pass = false;\n\trecordhopper(data, function hopper_cmnt(val, R, RT) {\n\t\tswitch(RT) {\n\t\t\tcase 0x0278: /* 'BrtCommentAuthor' */\n\t\t\t\tauthors.push(val); break;\n\t\t\tcase 0x027B: /* 'BrtBeginComment' */\n\t\t\t\tc = val; break;\n\t\t\tcase 0x027D: /* 'BrtCommentText' */\n\t\t\t\tc.t = val.t; c.h = val.h; c.r = val.r; break;\n\t\t\tcase 0x027C: /* 'BrtEndComment' */\n\t\t\t\tc.author = authors[c.iauthor];\n\t\t\t\tdelete (c/*:any*/).iauthor;\n\t\t\t\tif(opts.sheetRows && c.rfx && opts.sheetRows <= c.rfx.r) break;\n\t\t\t\tif(!c.t) c.t = \"\";\n\t\t\t\tdelete c.rfx; out.push(c); break;\n\n\t\t\tcase 0x0C00: /* 'BrtUid' */\n\t\t\t\tbreak;\n\n\t\t\tcase 0x0023: /* 'BrtFRTBegin' */\n\t\t\t\tpass = true; break;\n\t\t\tcase 0x0024: /* 'BrtFRTEnd' */\n\t\t\t\tpass = false; break;\n\t\t\tcase 0x0025: /* 'BrtACBegin' */ break;\n\t\t\tcase 0x0026: /* 'BrtACEnd' */ break;\n\n\n\t\t\tdefault:\n\t\t\t\tif(R.T){/* empty */}\n\t\t\t\telse if(!pass || opts.WTF) throw new Error(\"Unexpected record 0x\" + RT.toString(16));\n\t\t}\n\t});\n\treturn out;\n}\n\nfunction write_comments_bin(data/*::, opts*/) {\n\tvar ba = buf_array();\n\tvar iauthor/*:Array<string>*/ = [];\n\twrite_record(ba, 0x0274 /* BrtBeginComments */);\n\n\twrite_record(ba, 0x0276 /* BrtBeginCommentAuthors */);\n\tdata.forEach(function(comment) {\n\t\tcomment[1].forEach(function(c) {\n\t\t\tif(iauthor.indexOf(c.a) > -1) return;\n\t\t\tiauthor.push(c.a.slice(0,54));\n\t\t\twrite_record(ba, 0x0278 /* BrtCommentAuthor */, write_BrtCommentAuthor(c.a));\n\t\t});\n\t});\n\twrite_record(ba, 0x0277 /* BrtEndCommentAuthors */);\n\n\twrite_record(ba, 0x0279 /* BrtBeginCommentList */);\n\tdata.forEach(function(comment) {\n\t\tcomment[1].forEach(function(c) {\n\t\t\tc.iauthor = iauthor.indexOf(c.a);\n\t\t\tvar range = {s:decode_cell(comment[0]),e:decode_cell(comment[0])};\n\t\t\twrite_record(ba, 0x027B /* BrtBeginComment */, write_BrtBeginComment([range, c]));\n\t\t\tif(c.t && c.t.length > 0) write_record(ba, 0x027D /* BrtCommentText */, write_BrtCommentText(c));\n\t\t\twrite_record(ba, 0x027C /* BrtEndComment */);\n\t\t\tdelete c.iauthor;\n\t\t});\n\t});\n\twrite_record(ba, 0x027A /* BrtEndCommentList */);\n\n\twrite_record(ba, 0x0275 /* BrtEndComments */);\n\treturn ba.end();\n}\nvar CT_VBA = \"application/vnd.ms-office.vbaProject\";\nfunction make_vba_xls(cfb) {\n  var newcfb = CFB.utils.cfb_new({ root: \"R\" });\n  cfb.FullPaths.forEach(function(p, i) {\n    if (p.slice(-1) === \"/\" || !p.match(/_VBA_PROJECT_CUR/))\n      return;\n    var newpath = p.replace(/^[^\\/]*/, \"R\").replace(/\\/_VBA_PROJECT_CUR\\u0000*/, \"\");\n    CFB.utils.cfb_add(newcfb, newpath, cfb.FileIndex[i].content);\n  });\n  return CFB.write(newcfb);\n}\nfunction fill_vba_xls(cfb, vba) {\n  vba.FullPaths.forEach(function(p, i) {\n    if (i == 0)\n      return;\n    var newpath = p.replace(/[^\\/]*[\\/]/, \"/_VBA_PROJECT_CUR/\");\n    if (newpath.slice(-1) !== \"/\")\n      CFB.utils.cfb_add(cfb, newpath, vba.FileIndex[i].content);\n  });\n}\nvar VBAFMTS = [\"xlsb\", \"xlsm\", \"xlam\", \"biff8\", \"xla\"];\n/* macro and dialog sheet stubs */\nfunction parse_ds_bin(/*::data:any, opts, idx:number, rels, wb, themes, styles*/)/*:Worksheet*/ { return {'!type':'dialog'}; }\nfunction parse_ds_xml(/*::data:any, opts, idx:number, rels, wb, themes, styles*/)/*:Worksheet*/ { return {'!type':'dialog'}; }\nfunction parse_ms_bin(/*::data:any, opts, idx:number, rels, wb, themes, styles*/)/*:Worksheet*/ { return {'!type':'macro'}; }\nfunction parse_ms_xml(/*::data:any, opts, idx:number, rels, wb, themes, styles*/)/*:Worksheet*/ { return {'!type':'macro'}; }\n/* TODO: it will be useful to parse the function str */\nvar rc_to_a1 = /*#__PURE__*/(function(){\n\tvar rcregex = /(^|[^A-Za-z_])R(\\[?-?\\d+\\]|[1-9]\\d*|)C(\\[?-?\\d+\\]|[1-9]\\d*|)(?![A-Za-z0-9_])/g;\n\tvar rcbase/*:Cell*/ = ({r:0,c:0}/*:any*/);\n\tfunction rcfunc($$,$1,$2,$3) {\n\t\tvar cRel = false, rRel = false;\n\n\t\tif($2.length == 0) rRel = true;\n\t\telse if($2.charAt(0) == \"[\") { rRel = true; $2 = $2.slice(1, -1); }\n\n\t\tif($3.length == 0) cRel = true;\n\t\telse if($3.charAt(0) == \"[\") { cRel = true; $3 = $3.slice(1, -1); }\n\n\t\tvar R = $2.length>0?parseInt($2,10)|0:0, C = $3.length>0?parseInt($3,10)|0:0;\n\n\t\tif(cRel) C += rcbase.c; else --C;\n\t\tif(rRel) R += rcbase.r; else --R;\n\t\treturn $1 + (cRel ? \"\" : \"$\") + encode_col(C) + (rRel ? \"\" : \"$\") + encode_row(R);\n\t}\n\treturn function rc_to_a1(fstr/*:string*/, base/*:Cell*/)/*:string*/ {\n\t\trcbase = base;\n\t\treturn fstr.replace(rcregex, rcfunc);\n\t};\n})();\n\nvar crefregex = /(^|[^._A-Z0-9])([$]?)([A-Z]{1,2}|[A-W][A-Z]{2}|X[A-E][A-Z]|XF[A-D])([$]?)(10[0-3]\\d{4}|104[0-7]\\d{3}|1048[0-4]\\d{2}|10485[0-6]\\d|104857[0-6]|[1-9]\\d{0,5})(?![_.\\(A-Za-z0-9])/g;\nvar a1_to_rc = /*#__PURE__*/(function(){\n\treturn function a1_to_rc(fstr/*:string*/, base/*:CellAddress*/) {\n\t\treturn fstr.replace(crefregex, function($0, $1, $2, $3, $4, $5) {\n\t\t\tvar c = decode_col($3) - ($2 ? 0 : base.c);\n\t\t\tvar r = decode_row($5) - ($4 ? 0 : base.r);\n\t\t\tvar R = (r == 0 ? \"\" : !$4 ? \"[\" + r + \"]\" : (r+1));\n\t\t\tvar C = (c == 0 ? \"\" : !$2 ? \"[\" + c + \"]\" : (c+1));\n\t\t\treturn $1 + \"R\" + R + \"C\" + C;\n\t\t});\n\t};\n})();\n\n/* no defined name can collide with a valid cell address A1:XFD1048576 ... except LOG10! */\nfunction shift_formula_str(f/*:string*/, delta/*:Cell*/)/*:string*/ {\n\treturn f.replace(crefregex, function($0, $1, $2, $3, $4, $5) {\n\t\treturn $1+($2==\"$\" ? $2+$3 : encode_col(decode_col($3)+delta.c))+($4==\"$\" ? $4+$5 : encode_row(decode_row($5) + delta.r));\n\t});\n}\n\nfunction shift_formula_xlsx(f/*:string*/, range/*:string*/, cell/*:string*/)/*:string*/ {\n\tvar r = decode_range(range), s = r.s, c = decode_cell(cell);\n\tvar delta = {r:c.r - s.r, c:c.c - s.c};\n\treturn shift_formula_str(f, delta);\n}\n\n/* TODO: parse formula */\nfunction fuzzyfmla(f/*:string*/)/*:boolean*/ {\n\tif(f.length == 1) return false;\n\treturn true;\n}\n\nfunction _xlfn(f/*:string*/)/*:string*/ {\n\treturn f.replace(/_xlfn\\./g,\"\");\n}\nfunction parseread1(blob) { blob.l+=1; return; }\n\n/* [MS-XLS] 2.5.51 */\nfunction parse_ColRelU(blob, length) {\n\tvar c = blob.read_shift(length == 1 ? 1 : 2);\n\treturn [c & 0x3FFF, (c >> 14) & 1, (c >> 15) & 1];\n}\n\n/* [MS-XLS] 2.5.198.105 ; [MS-XLSB] 2.5.97.89 */\nfunction parse_RgceArea(blob, length, opts) {\n\tvar w = 2;\n\tif(opts) {\n\t\tif(opts.biff >= 2 && opts.biff <= 5) return parse_RgceArea_BIFF2(blob, length, opts);\n\t\telse if(opts.biff == 12) w = 4;\n\t}\n\tvar r=blob.read_shift(w), R=blob.read_shift(w);\n\tvar c=parse_ColRelU(blob, 2);\n\tvar C=parse_ColRelU(blob, 2);\n\treturn { s:{r:r, c:c[0], cRel:c[1], rRel:c[2]}, e:{r:R, c:C[0], cRel:C[1], rRel:C[2]} };\n}\n/* BIFF 2-5 encodes flags in the row field */\nfunction parse_RgceArea_BIFF2(blob/*::, length, opts*/) {\n\tvar r=parse_ColRelU(blob, 2), R=parse_ColRelU(blob, 2);\n\tvar c=blob.read_shift(1);\n\tvar C=blob.read_shift(1);\n\treturn { s:{r:r[0], c:c, cRel:r[1], rRel:r[2]}, e:{r:R[0], c:C, cRel:R[1], rRel:R[2]} };\n}\n\n/* [MS-XLS] 2.5.198.105 ; [MS-XLSB] 2.5.97.90 */\nfunction parse_RgceAreaRel(blob, length, opts) {\n\tif(opts.biff < 8) return parse_RgceArea_BIFF2(blob, length, opts);\n\tvar r=blob.read_shift(opts.biff == 12 ? 4 : 2), R=blob.read_shift(opts.biff == 12 ? 4 : 2);\n\tvar c=parse_ColRelU(blob, 2);\n\tvar C=parse_ColRelU(blob, 2);\n\treturn { s:{r:r, c:c[0], cRel:c[1], rRel:c[2]}, e:{r:R, c:C[0], cRel:C[1], rRel:C[2]} };\n}\n\n/* [MS-XLS] 2.5.198.109 ; [MS-XLSB] 2.5.97.91 */\nfunction parse_RgceLoc(blob, length, opts) {\n\tif(opts && opts.biff >= 2 && opts.biff <= 5) return parse_RgceLoc_BIFF2(blob, length, opts);\n\tvar r = blob.read_shift(opts && opts.biff == 12 ? 4 : 2);\n\tvar c = parse_ColRelU(blob, 2);\n\treturn {r:r, c:c[0], cRel:c[1], rRel:c[2]};\n}\nfunction parse_RgceLoc_BIFF2(blob/*::, length, opts*/) {\n\tvar r = parse_ColRelU(blob, 2);\n\tvar c = blob.read_shift(1);\n\treturn {r:r[0], c:c, cRel:r[1], rRel:r[2]};\n}\n\n/* [MS-XLS] 2.5.198.107, 2.5.47 */\nfunction parse_RgceElfLoc(blob/*::, length, opts*/) {\n\tvar r = blob.read_shift(2);\n\tvar c = blob.read_shift(2);\n\treturn {r:r, c:c & 0xFF, fQuoted:!!(c & 0x4000), cRel:c>>15, rRel:c>>15 };\n}\n\n/* [MS-XLS] 2.5.198.111 ; [MS-XLSB] 2.5.97.92 TODO */\nfunction parse_RgceLocRel(blob, length, opts) {\n\tvar biff = opts && opts.biff ? opts.biff : 8;\n\tif(biff >= 2 && biff <= 5) return parse_RgceLocRel_BIFF2(blob, length, opts);\n\tvar r = blob.read_shift(biff >= 12 ? 4 : 2);\n\tvar cl = blob.read_shift(2);\n\tvar cRel = (cl & 0x4000) >> 14, rRel = (cl & 0x8000) >> 15;\n\tcl &= 0x3FFF;\n\tif(rRel == 1) while(r > 0x7FFFF) r -= 0x100000;\n\tif(cRel == 1) while(cl > 0x1FFF) cl = cl - 0x4000;\n\treturn {r:r,c:cl,cRel:cRel,rRel:rRel};\n}\nfunction parse_RgceLocRel_BIFF2(blob/*::, length:number, opts*/) {\n\tvar rl = blob.read_shift(2);\n\tvar c = blob.read_shift(1);\n\tvar rRel = (rl & 0x8000) >> 15, cRel = (rl & 0x4000) >> 14;\n\trl &= 0x3FFF;\n\tif(rRel == 1 && rl >= 0x2000) rl = rl - 0x4000;\n\tif(cRel == 1 && c >= 0x80) c = c - 0x100;\n\treturn {r:rl,c:c,cRel:cRel,rRel:rRel};\n}\n\n/* [MS-XLS] 2.5.198.27 ; [MS-XLSB] 2.5.97.18 */\nfunction parse_PtgArea(blob, length, opts) {\n\tvar type = (blob[blob.l++] & 0x60) >> 5;\n\tvar area = parse_RgceArea(blob, opts.biff >= 2 && opts.biff <= 5 ? 6 : 8, opts);\n\treturn [type, area];\n}\n\n/* [MS-XLS] 2.5.198.28 ; [MS-XLSB] 2.5.97.19 */\nfunction parse_PtgArea3d(blob, length, opts) {\n\tvar type = (blob[blob.l++] & 0x60) >> 5;\n\tvar ixti = blob.read_shift(2, 'i');\n\tvar w = 8;\n\tif(opts) switch(opts.biff) {\n\t\tcase 5: blob.l += 12; w = 6; break;\n\t\tcase 12: w = 12; break;\n\t}\n\tvar area = parse_RgceArea(blob, w, opts);\n\treturn [type, ixti, area];\n}\n\n/* [MS-XLS] 2.5.198.29 ; [MS-XLSB] 2.5.97.20 */\nfunction parse_PtgAreaErr(blob, length, opts) {\n\tvar type = (blob[blob.l++] & 0x60) >> 5;\n\tblob.l += opts && (opts.biff > 8) ? 12 : (opts.biff < 8 ? 6 : 8);\n\treturn [type];\n}\n/* [MS-XLS] 2.5.198.30 ; [MS-XLSB] 2.5.97.21 */\nfunction parse_PtgAreaErr3d(blob, length, opts) {\n\tvar type = (blob[blob.l++] & 0x60) >> 5;\n\tvar ixti = blob.read_shift(2);\n\tvar w = 8;\n\tif(opts) switch(opts.biff) {\n\t\tcase 5: blob.l += 12; w = 6; break;\n\t\tcase 12: w = 12; break;\n\t}\n\tblob.l += w;\n\treturn [type, ixti];\n}\n\n/* [MS-XLS] 2.5.198.31 ; [MS-XLSB] 2.5.97.22 */\nfunction parse_PtgAreaN(blob, length, opts) {\n\tvar type = (blob[blob.l++] & 0x60) >> 5;\n\tvar area = parse_RgceAreaRel(blob, length - 1, opts);\n\treturn [type, area];\n}\n\n/* [MS-XLS] 2.5.198.32 ; [MS-XLSB] 2.5.97.23 */\nfunction parse_PtgArray(blob, length, opts) {\n\tvar type = (blob[blob.l++] & 0x60) >> 5;\n\tblob.l += opts.biff == 2 ? 6 : opts.biff == 12 ? 14 : 7;\n\treturn [type];\n}\n\n/* [MS-XLS] 2.5.198.33 ; [MS-XLSB] 2.5.97.24 */\nfunction parse_PtgAttrBaxcel(blob) {\n\tvar bitSemi = blob[blob.l+1] & 0x01; /* 1 = volatile */\n\tvar bitBaxcel = 1;\n\tblob.l += 4;\n\treturn [bitSemi, bitBaxcel];\n}\n\n/* [MS-XLS] 2.5.198.34 ; [MS-XLSB] 2.5.97.25 */\nfunction parse_PtgAttrChoose(blob, length, opts)/*:Array<number>*/ {\n\tblob.l +=2;\n\tvar offset = blob.read_shift(opts && opts.biff == 2 ? 1 : 2);\n\tvar o/*:Array<number>*/ = [];\n\t/* offset is 1 less than the number of elements */\n\tfor(var i = 0; i <= offset; ++i) o.push(blob.read_shift(opts && opts.biff == 2 ? 1 : 2));\n\treturn o;\n}\n\n/* [MS-XLS] 2.5.198.35 ; [MS-XLSB] 2.5.97.26 */\nfunction parse_PtgAttrGoto(blob, length, opts) {\n\tvar bitGoto = (blob[blob.l+1] & 0xFF) ? 1 : 0;\n\tblob.l += 2;\n\treturn [bitGoto, blob.read_shift(opts && opts.biff == 2 ? 1 : 2)];\n}\n\n/* [MS-XLS] 2.5.198.36 ; [MS-XLSB] 2.5.97.27 */\nfunction parse_PtgAttrIf(blob, length, opts) {\n\tvar bitIf = (blob[blob.l+1] & 0xFF) ? 1 : 0;\n\tblob.l += 2;\n\treturn [bitIf, blob.read_shift(opts && opts.biff == 2 ? 1 : 2)];\n}\n\n/* [MS-XLSB] 2.5.97.28 */\nfunction parse_PtgAttrIfError(blob) {\n\tvar bitIf = (blob[blob.l+1] & 0xFF) ? 1 : 0;\n\tblob.l += 2;\n\treturn [bitIf, blob.read_shift(2)];\n}\n\n/* [MS-XLS] 2.5.198.37 ; [MS-XLSB] 2.5.97.29 */\nfunction parse_PtgAttrSemi(blob, length, opts) {\n\tvar bitSemi = (blob[blob.l+1] & 0xFF) ? 1 : 0;\n\tblob.l += opts && opts.biff == 2 ? 3 : 4;\n\treturn [bitSemi];\n}\n\n/* [MS-XLS] 2.5.198.40 ; [MS-XLSB] 2.5.97.32 */\nfunction parse_PtgAttrSpaceType(blob/*::, length*/) {\n\tvar type = blob.read_shift(1), cch = blob.read_shift(1);\n\treturn [type, cch];\n}\n\n/* [MS-XLS] 2.5.198.38 ; [MS-XLSB] 2.5.97.30 */\nfunction parse_PtgAttrSpace(blob) {\n\tblob.read_shift(2);\n\treturn parse_PtgAttrSpaceType(blob, 2);\n}\n\n/* [MS-XLS] 2.5.198.39 ; [MS-XLSB] 2.5.97.31 */\nfunction parse_PtgAttrSpaceSemi(blob) {\n\tblob.read_shift(2);\n\treturn parse_PtgAttrSpaceType(blob, 2);\n}\n\n/* [MS-XLS] 2.5.198.84 ; [MS-XLSB] 2.5.97.68 TODO */\nfunction parse_PtgRef(blob, length, opts) {\n\t//var ptg = blob[blob.l] & 0x1F;\n\tvar type = (blob[blob.l] & 0x60)>>5;\n\tblob.l += 1;\n\tvar loc = parse_RgceLoc(blob, 0, opts);\n\treturn [type, loc];\n}\n\n/* [MS-XLS] 2.5.198.88 ; [MS-XLSB] 2.5.97.72 TODO */\nfunction parse_PtgRefN(blob, length, opts) {\n\tvar type = (blob[blob.l] & 0x60)>>5;\n\tblob.l += 1;\n\tvar loc = parse_RgceLocRel(blob, 0, opts);\n\treturn [type, loc];\n}\n\n/* [MS-XLS] 2.5.198.85 ; [MS-XLSB] 2.5.97.69 TODO */\nfunction parse_PtgRef3d(blob, length, opts) {\n\tvar type = (blob[blob.l] & 0x60)>>5;\n\tblob.l += 1;\n\tvar ixti = blob.read_shift(2); // XtiIndex\n\tif(opts && opts.biff == 5) blob.l += 12;\n\tvar loc = parse_RgceLoc(blob, 0, opts); // TODO: or RgceLocRel\n\treturn [type, ixti, loc];\n}\n\n\n/* [MS-XLS] 2.5.198.62 ; [MS-XLSB] 2.5.97.45 TODO */\nfunction parse_PtgFunc(blob, length, opts) {\n\t//var ptg = blob[blob.l] & 0x1F;\n\tvar type = (blob[blob.l] & 0x60)>>5;\n\tblob.l += 1;\n\tvar iftab = blob.read_shift(opts && opts.biff <= 3 ? 1 : 2);\n\treturn [FtabArgc[iftab], Ftab[iftab], type];\n}\n/* [MS-XLS] 2.5.198.63 ; [MS-XLSB] 2.5.97.46 TODO */\nfunction parse_PtgFuncVar(blob, length, opts) {\n\tvar type = blob[blob.l++];\n\tvar cparams = blob.read_shift(1), tab = opts && opts.biff <= 3 ? [(type == 0x58 ? -1 : 0), blob.read_shift(1)]: parsetab(blob);\n\treturn [cparams, (tab[0] === 0 ? Ftab : Cetab)[tab[1]]];\n}\n\nfunction parsetab(blob) {\n\treturn [blob[blob.l+1]>>7, blob.read_shift(2) & 0x7FFF];\n}\n\n/* [MS-XLS] 2.5.198.41 ; [MS-XLSB] 2.5.97.33 */\nfunction parse_PtgAttrSum(blob, length, opts) {\n\tblob.l += opts && opts.biff == 2 ? 3 : 4; return;\n}\n\n/* [MS-XLS] 2.5.198.58 ; [MS-XLSB] 2.5.97.40 */\nfunction parse_PtgExp(blob, length, opts) {\n\tblob.l++;\n\tif(opts && opts.biff == 12) return [blob.read_shift(4, 'i'), 0];\n\tvar row = blob.read_shift(2);\n\tvar col = blob.read_shift(opts && opts.biff == 2 ? 1 : 2);\n\treturn [row, col];\n}\n\n/* [MS-XLS] 2.5.198.57 ; [MS-XLSB] 2.5.97.39 */\nfunction parse_PtgErr(blob) { blob.l++; return BErr[blob.read_shift(1)]; }\n\n/* [MS-XLS] 2.5.198.66 ; [MS-XLSB] 2.5.97.49 */\nfunction parse_PtgInt(blob) { blob.l++; return blob.read_shift(2); }\n\n/* [MS-XLS] 2.5.198.42 ; [MS-XLSB] 2.5.97.34 */\nfunction parse_PtgBool(blob) { blob.l++; return blob.read_shift(1)!==0;}\n\n/* [MS-XLS] 2.5.198.79 ; [MS-XLSB] 2.5.97.63 */\nfunction parse_PtgNum(blob) { blob.l++; return parse_Xnum(blob, 8); }\n\n/* [MS-XLS] 2.5.198.89 ; [MS-XLSB] 2.5.97.74 */\nfunction parse_PtgStr(blob, length, opts) { blob.l++; return parse_ShortXLUnicodeString(blob, length-1, opts); }\n\n/* [MS-XLS] 2.5.192.112 + 2.5.192.11{3,4,5,6,7} */\n/* [MS-XLSB] 2.5.97.93 + 2.5.97.9{4,5,6,7} */\nfunction parse_SerAr(blob, biff/*:number*/) {\n\tvar val = [blob.read_shift(1)];\n\tif(biff == 12) switch(val[0]) {\n\t\tcase 0x02: val[0] = 0x04; break; /* SerBool */\n\t\tcase 0x04: val[0] = 0x10; break; /* SerErr */\n\t\tcase 0x00: val[0] = 0x01; break; /* SerNum */\n\t\tcase 0x01: val[0] = 0x02; break; /* SerStr */\n\t}\n\tswitch(val[0]) {\n\t\tcase 0x04: /* SerBool -- boolean */\n\t\t\tval[1] = parsebool(blob, 1) ? 'TRUE' : 'FALSE';\n\t\t\tif(biff != 12) blob.l += 7; break;\n\t\tcase 0x25: /* appears to be an alias */\n\t\tcase 0x10: /* SerErr -- error */\n\t\t\tval[1] = BErr[blob[blob.l]];\n\t\t\tblob.l += ((biff == 12) ? 4 : 8); break;\n\t\tcase 0x00: /* SerNil -- honestly, I'm not sure how to reproduce this */\n\t\t\tblob.l += 8; break;\n\t\tcase 0x01: /* SerNum -- Xnum */\n\t\t\tval[1] = parse_Xnum(blob, 8); break;\n\t\tcase 0x02: /* SerStr -- XLUnicodeString (<256 chars) */\n\t\t\tval[1] = parse_XLUnicodeString2(blob, 0, {biff:biff > 0 && biff < 8 ? 2 : biff}); break;\n\t\tdefault: throw new Error(\"Bad SerAr: \" + val[0]); /* Unreachable */\n\t}\n\treturn val;\n}\n\n/* [MS-XLS] 2.5.198.61 ; [MS-XLSB] 2.5.97.44 */\nfunction parse_PtgExtraMem(blob, cce, opts) {\n\tvar count = blob.read_shift((opts.biff == 12) ? 4 : 2);\n\tvar out/*:Array<Range>*/ = [];\n\tfor(var i = 0; i != count; ++i) out.push(((opts.biff == 12) ? parse_UncheckedRfX : parse_Ref8U)(blob, 8));\n\treturn out;\n}\n\n/* [MS-XLS] 2.5.198.59 ; [MS-XLSB] 2.5.97.41 */\nfunction parse_PtgExtraArray(blob, length, opts) {\n\tvar rows = 0, cols = 0;\n\tif(opts.biff == 12) {\n\t\trows = blob.read_shift(4); // DRw\n\t\tcols = blob.read_shift(4); // DCol\n\t} else {\n\t\tcols = 1 + blob.read_shift(1); //DColByteU\n\t\trows = 1 + blob.read_shift(2); //DRw\n\t}\n\tif(opts.biff >= 2 && opts.biff < 8) { --rows; if(--cols == 0) cols = 0x100; }\n\t// $FlowIgnore\n\tfor(var i = 0, o/*:Array<Array<any>>*/ = []; i != rows && (o[i] = []); ++i)\n\t\tfor(var j = 0; j != cols; ++j) o[i][j] = parse_SerAr(blob, opts.biff);\n\treturn o;\n}\n\n/* [MS-XLS] 2.5.198.76 ; [MS-XLSB] 2.5.97.60 */\nfunction parse_PtgName(blob, length, opts) {\n\tvar type = (blob.read_shift(1) >>> 5) & 0x03;\n\tvar w = (!opts || (opts.biff >= 8)) ? 4 : 2;\n\tvar nameindex = blob.read_shift(w);\n\tswitch(opts.biff) {\n\t\tcase 2: blob.l += 5; break;\n\t\tcase 3: case 4: blob.l += 8; break;\n\t\tcase 5: blob.l += 12; break;\n\t}\n\treturn [type, 0, nameindex];\n}\n\n/* [MS-XLS] 2.5.198.77 ; [MS-XLSB] 2.5.97.61 */\nfunction parse_PtgNameX(blob, length, opts) {\n\tif(opts.biff == 5) return parse_PtgNameX_BIFF5(blob, length, opts);\n\tvar type = (blob.read_shift(1) >>> 5) & 0x03;\n\tvar ixti = blob.read_shift(2); // XtiIndex\n\tvar nameindex = blob.read_shift(4);\n\treturn [type, ixti, nameindex];\n}\nfunction parse_PtgNameX_BIFF5(blob/*::, length, opts*/) {\n\tvar type = (blob.read_shift(1) >>> 5) & 0x03;\n\tvar ixti = blob.read_shift(2, 'i'); // XtiIndex\n\tblob.l += 8;\n\tvar nameindex = blob.read_shift(2);\n\tblob.l += 12;\n\treturn [type, ixti, nameindex];\n}\n\n/* [MS-XLS] 2.5.198.70 ; [MS-XLSB] 2.5.97.54 */\nfunction parse_PtgMemArea(blob, length, opts) {\n\tvar type = (blob.read_shift(1) >>> 5) & 0x03;\n\tblob.l += (opts && opts.biff == 2 ? 3 : 4);\n\tvar cce = blob.read_shift(opts && opts.biff == 2 ? 1 : 2);\n\treturn [type, cce];\n}\n\n/* [MS-XLS] 2.5.198.72 ; [MS-XLSB] 2.5.97.56 */\nfunction parse_PtgMemFunc(blob, length, opts) {\n\tvar type = (blob.read_shift(1) >>> 5) & 0x03;\n\tvar cce = blob.read_shift(opts && opts.biff == 2 ? 1 : 2);\n\treturn [type, cce];\n}\n\n\n/* [MS-XLS] 2.5.198.86 ; [MS-XLSB] 2.5.97.69 */\nfunction parse_PtgRefErr(blob, length, opts) {\n\tvar type = (blob.read_shift(1) >>> 5) & 0x03;\n\tblob.l += 4;\n\tif(opts.biff < 8) blob.l--;\n\tif(opts.biff == 12) blob.l += 2;\n\treturn [type];\n}\n\n/* [MS-XLS] 2.5.198.87 ; [MS-XLSB] 2.5.97.71 */\nfunction parse_PtgRefErr3d(blob, length, opts) {\n\tvar type = (blob[blob.l++] & 0x60) >> 5;\n\tvar ixti = blob.read_shift(2);\n\tvar w = 4;\n\tif(opts) switch(opts.biff) {\n\t\tcase 5: w = 15; break;\n\t\tcase 12: w = 6; break;\n\t}\n\tblob.l += w;\n\treturn [type, ixti];\n}\n\n/* [MS-XLS] 2.5.198.71 ; [MS-XLSB] 2.5.97.55 */\nvar parse_PtgMemErr = parsenoop;\n/* [MS-XLS] 2.5.198.73  ; [MS-XLSB] 2.5.97.57 */\nvar parse_PtgMemNoMem = parsenoop;\n/* [MS-XLS] 2.5.198.92 */\nvar parse_PtgTbl = parsenoop;\n\nfunction parse_PtgElfLoc(blob, length, opts) {\n\tblob.l += 2;\n\treturn [parse_RgceElfLoc(blob, 4, opts)];\n}\nfunction parse_PtgElfNoop(blob/*::, length, opts*/) {\n\tblob.l += 6;\n\treturn [];\n}\n/* [MS-XLS] 2.5.198.46 */\nvar parse_PtgElfCol = parse_PtgElfLoc;\n/* [MS-XLS] 2.5.198.47 */\nvar parse_PtgElfColS = parse_PtgElfNoop;\n/* [MS-XLS] 2.5.198.48 */\nvar parse_PtgElfColSV = parse_PtgElfNoop;\n/* [MS-XLS] 2.5.198.49 */\nvar parse_PtgElfColV = parse_PtgElfLoc;\n/* [MS-XLS] 2.5.198.50 */\nfunction parse_PtgElfLel(blob/*::, length, opts*/) {\n\tblob.l += 2;\n\treturn [parseuint16(blob), blob.read_shift(2) & 0x01];\n}\n/* [MS-XLS] 2.5.198.51 */\nvar parse_PtgElfRadical = parse_PtgElfLoc;\n/* [MS-XLS] 2.5.198.52 */\nvar parse_PtgElfRadicalLel = parse_PtgElfLel;\n/* [MS-XLS] 2.5.198.53 */\nvar parse_PtgElfRadicalS = parse_PtgElfNoop;\n/* [MS-XLS] 2.5.198.54 */\nvar parse_PtgElfRw = parse_PtgElfLoc;\n/* [MS-XLS] 2.5.198.55 */\nvar parse_PtgElfRwV = parse_PtgElfLoc;\n\n/* [MS-XLSB] 2.5.97.52 TODO */\nvar PtgListRT = [\n\t\"Data\",\n\t\"All\",\n\t\"Headers\",\n\t\"??\",\n\t\"?Data2\",\n\t\"??\",\n\t\"?DataHeaders\",\n\t\"??\",\n\t\"Totals\",\n\t\"??\",\n\t\"??\",\n\t\"??\",\n\t\"?DataTotals\",\n\t\"??\",\n\t\"??\",\n\t\"??\",\n\t\"?Current\"\n];\nfunction parse_PtgList(blob/*::, length, opts*/) {\n\tblob.l += 2;\n\tvar ixti = blob.read_shift(2);\n\tvar flags = blob.read_shift(2);\n\tvar idx = blob.read_shift(4);\n\tvar c = blob.read_shift(2);\n\tvar C = blob.read_shift(2);\n\tvar rt = PtgListRT[(flags >> 2) & 0x1F];\n\treturn {ixti: ixti, coltype:(flags&0x3), rt:rt, idx:idx, c:c, C:C};\n}\n/* [MS-XLS] 2.5.198.91 ; [MS-XLSB] 2.5.97.76 */\nfunction parse_PtgSxName(blob/*::, length, opts*/) {\n\tblob.l += 2;\n\treturn [blob.read_shift(4)];\n}\n\n/* [XLS] old spec */\nfunction parse_PtgSheet(blob, length, opts) {\n\tblob.l += 5;\n\tblob.l += 2;\n\tblob.l += (opts.biff == 2 ? 1 : 4);\n\treturn [\"PTGSHEET\"];\n}\nfunction parse_PtgEndSheet(blob, length, opts) {\n\tblob.l += (opts.biff == 2 ? 4 : 5);\n\treturn [\"PTGENDSHEET\"];\n}\nfunction parse_PtgMemAreaN(blob/*::, length, opts*/) {\n\tvar type = (blob.read_shift(1) >>> 5) & 0x03;\n\tvar cce = blob.read_shift(2);\n\treturn [type, cce];\n}\nfunction parse_PtgMemNoMemN(blob/*::, length, opts*/) {\n\tvar type = (blob.read_shift(1) >>> 5) & 0x03;\n\tvar cce = blob.read_shift(2);\n\treturn [type, cce];\n}\nfunction parse_PtgAttrNoop(blob/*::, length, opts*/) {\n\tblob.l += 4;\n\treturn [0, 0];\n}\n\n/* [MS-XLS] 2.5.198.25 ; [MS-XLSB] 2.5.97.16 */\nvar PtgTypes = {\n\t/*::[*/0x01/*::]*/: { n:'PtgExp', f:parse_PtgExp },\n\t/*::[*/0x02/*::]*/: { n:'PtgTbl', f:parse_PtgTbl },\n\t/*::[*/0x03/*::]*/: { n:'PtgAdd', f:parseread1 },\n\t/*::[*/0x04/*::]*/: { n:'PtgSub', f:parseread1 },\n\t/*::[*/0x05/*::]*/: { n:'PtgMul', f:parseread1 },\n\t/*::[*/0x06/*::]*/: { n:'PtgDiv', f:parseread1 },\n\t/*::[*/0x07/*::]*/: { n:'PtgPower', f:parseread1 },\n\t/*::[*/0x08/*::]*/: { n:'PtgConcat', f:parseread1 },\n\t/*::[*/0x09/*::]*/: { n:'PtgLt', f:parseread1 },\n\t/*::[*/0x0A/*::]*/: { n:'PtgLe', f:parseread1 },\n\t/*::[*/0x0B/*::]*/: { n:'PtgEq', f:parseread1 },\n\t/*::[*/0x0C/*::]*/: { n:'PtgGe', f:parseread1 },\n\t/*::[*/0x0D/*::]*/: { n:'PtgGt', f:parseread1 },\n\t/*::[*/0x0E/*::]*/: { n:'PtgNe', f:parseread1 },\n\t/*::[*/0x0F/*::]*/: { n:'PtgIsect', f:parseread1 },\n\t/*::[*/0x10/*::]*/: { n:'PtgUnion', f:parseread1 },\n\t/*::[*/0x11/*::]*/: { n:'PtgRange', f:parseread1 },\n\t/*::[*/0x12/*::]*/: { n:'PtgUplus', f:parseread1 },\n\t/*::[*/0x13/*::]*/: { n:'PtgUminus', f:parseread1 },\n\t/*::[*/0x14/*::]*/: { n:'PtgPercent', f:parseread1 },\n\t/*::[*/0x15/*::]*/: { n:'PtgParen', f:parseread1 },\n\t/*::[*/0x16/*::]*/: { n:'PtgMissArg', f:parseread1 },\n\t/*::[*/0x17/*::]*/: { n:'PtgStr', f:parse_PtgStr },\n\t/*::[*/0x1A/*::]*/: { n:'PtgSheet', f:parse_PtgSheet },\n\t/*::[*/0x1B/*::]*/: { n:'PtgEndSheet', f:parse_PtgEndSheet },\n\t/*::[*/0x1C/*::]*/: { n:'PtgErr', f:parse_PtgErr },\n\t/*::[*/0x1D/*::]*/: { n:'PtgBool', f:parse_PtgBool },\n\t/*::[*/0x1E/*::]*/: { n:'PtgInt', f:parse_PtgInt },\n\t/*::[*/0x1F/*::]*/: { n:'PtgNum', f:parse_PtgNum },\n\t/*::[*/0x20/*::]*/: { n:'PtgArray', f:parse_PtgArray },\n\t/*::[*/0x21/*::]*/: { n:'PtgFunc', f:parse_PtgFunc },\n\t/*::[*/0x22/*::]*/: { n:'PtgFuncVar', f:parse_PtgFuncVar },\n\t/*::[*/0x23/*::]*/: { n:'PtgName', f:parse_PtgName },\n\t/*::[*/0x24/*::]*/: { n:'PtgRef', f:parse_PtgRef },\n\t/*::[*/0x25/*::]*/: { n:'PtgArea', f:parse_PtgArea },\n\t/*::[*/0x26/*::]*/: { n:'PtgMemArea', f:parse_PtgMemArea },\n\t/*::[*/0x27/*::]*/: { n:'PtgMemErr', f:parse_PtgMemErr },\n\t/*::[*/0x28/*::]*/: { n:'PtgMemNoMem', f:parse_PtgMemNoMem },\n\t/*::[*/0x29/*::]*/: { n:'PtgMemFunc', f:parse_PtgMemFunc },\n\t/*::[*/0x2A/*::]*/: { n:'PtgRefErr', f:parse_PtgRefErr },\n\t/*::[*/0x2B/*::]*/: { n:'PtgAreaErr', f:parse_PtgAreaErr },\n\t/*::[*/0x2C/*::]*/: { n:'PtgRefN', f:parse_PtgRefN },\n\t/*::[*/0x2D/*::]*/: { n:'PtgAreaN', f:parse_PtgAreaN },\n\t/*::[*/0x2E/*::]*/: { n:'PtgMemAreaN', f:parse_PtgMemAreaN },\n\t/*::[*/0x2F/*::]*/: { n:'PtgMemNoMemN', f:parse_PtgMemNoMemN },\n\t/*::[*/0x39/*::]*/: { n:'PtgNameX', f:parse_PtgNameX },\n\t/*::[*/0x3A/*::]*/: { n:'PtgRef3d', f:parse_PtgRef3d },\n\t/*::[*/0x3B/*::]*/: { n:'PtgArea3d', f:parse_PtgArea3d },\n\t/*::[*/0x3C/*::]*/: { n:'PtgRefErr3d', f:parse_PtgRefErr3d },\n\t/*::[*/0x3D/*::]*/: { n:'PtgAreaErr3d', f:parse_PtgAreaErr3d },\n\t/*::[*/0xFF/*::]*/: {}\n};\n/* These are duplicated in the PtgTypes table */\nvar PtgDupes = {\n\t/*::[*/0x40/*::]*/: 0x20, /*::[*/0x60/*::]*/: 0x20,\n\t/*::[*/0x41/*::]*/: 0x21, /*::[*/0x61/*::]*/: 0x21,\n\t/*::[*/0x42/*::]*/: 0x22, /*::[*/0x62/*::]*/: 0x22,\n\t/*::[*/0x43/*::]*/: 0x23, /*::[*/0x63/*::]*/: 0x23,\n\t/*::[*/0x44/*::]*/: 0x24, /*::[*/0x64/*::]*/: 0x24,\n\t/*::[*/0x45/*::]*/: 0x25, /*::[*/0x65/*::]*/: 0x25,\n\t/*::[*/0x46/*::]*/: 0x26, /*::[*/0x66/*::]*/: 0x26,\n\t/*::[*/0x47/*::]*/: 0x27, /*::[*/0x67/*::]*/: 0x27,\n\t/*::[*/0x48/*::]*/: 0x28, /*::[*/0x68/*::]*/: 0x28,\n\t/*::[*/0x49/*::]*/: 0x29, /*::[*/0x69/*::]*/: 0x29,\n\t/*::[*/0x4A/*::]*/: 0x2A, /*::[*/0x6A/*::]*/: 0x2A,\n\t/*::[*/0x4B/*::]*/: 0x2B, /*::[*/0x6B/*::]*/: 0x2B,\n\t/*::[*/0x4C/*::]*/: 0x2C, /*::[*/0x6C/*::]*/: 0x2C,\n\t/*::[*/0x4D/*::]*/: 0x2D, /*::[*/0x6D/*::]*/: 0x2D,\n\t/*::[*/0x4E/*::]*/: 0x2E, /*::[*/0x6E/*::]*/: 0x2E,\n\t/*::[*/0x4F/*::]*/: 0x2F, /*::[*/0x6F/*::]*/: 0x2F,\n\t/*::[*/0x58/*::]*/: 0x22, /*::[*/0x78/*::]*/: 0x22,\n\t/*::[*/0x59/*::]*/: 0x39, /*::[*/0x79/*::]*/: 0x39,\n\t/*::[*/0x5A/*::]*/: 0x3A, /*::[*/0x7A/*::]*/: 0x3A,\n\t/*::[*/0x5B/*::]*/: 0x3B, /*::[*/0x7B/*::]*/: 0x3B,\n\t/*::[*/0x5C/*::]*/: 0x3C, /*::[*/0x7C/*::]*/: 0x3C,\n\t/*::[*/0x5D/*::]*/: 0x3D, /*::[*/0x7D/*::]*/: 0x3D\n};\n\nvar Ptg18 = {\n\t/*::[*/0x01/*::]*/: { n:'PtgElfLel', f:parse_PtgElfLel },\n\t/*::[*/0x02/*::]*/: { n:'PtgElfRw', f:parse_PtgElfRw },\n\t/*::[*/0x03/*::]*/: { n:'PtgElfCol', f:parse_PtgElfCol },\n\t/*::[*/0x06/*::]*/: { n:'PtgElfRwV', f:parse_PtgElfRwV },\n\t/*::[*/0x07/*::]*/: { n:'PtgElfColV', f:parse_PtgElfColV },\n\t/*::[*/0x0A/*::]*/: { n:'PtgElfRadical', f:parse_PtgElfRadical },\n\t/*::[*/0x0B/*::]*/: { n:'PtgElfRadicalS', f:parse_PtgElfRadicalS },\n\t/*::[*/0x0D/*::]*/: { n:'PtgElfColS', f:parse_PtgElfColS },\n\t/*::[*/0x0F/*::]*/: { n:'PtgElfColSV', f:parse_PtgElfColSV },\n\t/*::[*/0x10/*::]*/: { n:'PtgElfRadicalLel', f:parse_PtgElfRadicalLel },\n\t/*::[*/0x19/*::]*/: { n:'PtgList', f:parse_PtgList },\n\t/*::[*/0x1D/*::]*/: { n:'PtgSxName', f:parse_PtgSxName },\n\t/*::[*/0xFF/*::]*/: {}\n};\nvar Ptg19 = {\n\t/*::[*/0x00/*::]*/: { n:'PtgAttrNoop', f:parse_PtgAttrNoop },\n\t/*::[*/0x01/*::]*/: { n:'PtgAttrSemi', f:parse_PtgAttrSemi },\n\t/*::[*/0x02/*::]*/: { n:'PtgAttrIf', f:parse_PtgAttrIf },\n\t/*::[*/0x04/*::]*/: { n:'PtgAttrChoose', f:parse_PtgAttrChoose },\n\t/*::[*/0x08/*::]*/: { n:'PtgAttrGoto', f:parse_PtgAttrGoto },\n\t/*::[*/0x10/*::]*/: { n:'PtgAttrSum', f:parse_PtgAttrSum },\n\t/*::[*/0x20/*::]*/: { n:'PtgAttrBaxcel', f:parse_PtgAttrBaxcel },\n\t/*::[*/0x21/*::]*/: { n:'PtgAttrBaxcel', f:parse_PtgAttrBaxcel },\n\t/*::[*/0x40/*::]*/: { n:'PtgAttrSpace', f:parse_PtgAttrSpace },\n\t/*::[*/0x41/*::]*/: { n:'PtgAttrSpaceSemi', f:parse_PtgAttrSpaceSemi },\n\t/*::[*/0x80/*::]*/: { n:'PtgAttrIfError', f:parse_PtgAttrIfError },\n\t/*::[*/0xFF/*::]*/: {}\n};\n\n/* [MS-XLS] 2.5.198.103 ; [MS-XLSB] 2.5.97.87 */\nfunction parse_RgbExtra(blob, length, rgce, opts) {\n\tif(opts.biff < 8) return parsenoop(blob, length);\n\tvar target = blob.l + length;\n\tvar o = [];\n\tfor(var i = 0; i !== rgce.length; ++i) {\n\t\tswitch(rgce[i][0]) {\n\t\t\tcase 'PtgArray': /* PtgArray -> PtgExtraArray */\n\t\t\t\trgce[i][1] = parse_PtgExtraArray(blob, 0, opts);\n\t\t\t\to.push(rgce[i][1]);\n\t\t\t\tbreak;\n\t\t\tcase 'PtgMemArea': /* PtgMemArea -> PtgExtraMem */\n\t\t\t\trgce[i][2] = parse_PtgExtraMem(blob, rgce[i][1], opts);\n\t\t\t\to.push(rgce[i][2]);\n\t\t\t\tbreak;\n\t\t\tcase 'PtgExp': /* PtgExp -> PtgExtraCol */\n\t\t\t\tif(opts && opts.biff == 12) {\n\t\t\t\t\trgce[i][1][1] = blob.read_shift(4);\n\t\t\t\t\to.push(rgce[i][1]);\n\t\t\t\t} break;\n\t\t\tcase 'PtgList': /* TODO: PtgList -> PtgExtraList */\n\t\t\tcase 'PtgElfRadicalS': /* TODO: PtgElfRadicalS -> PtgExtraElf */\n\t\t\tcase 'PtgElfColS': /* TODO: PtgElfColS -> PtgExtraElf */\n\t\t\tcase 'PtgElfColSV': /* TODO: PtgElfColSV -> PtgExtraElf */\n\t\t\t\tthrow \"Unsupported \" + rgce[i][0];\n\t\t\tdefault: break;\n\t\t}\n\t}\n\tlength = target - blob.l;\n\t/* note: this is technically an error but Excel disregards */\n\t//if(target !== blob.l && blob.l !== target - length) throw new Error(target + \" != \" + blob.l);\n\tif(length !== 0) o.push(parsenoop(blob, length));\n\treturn o;\n}\n\n/* [MS-XLS] 2.5.198.104 ; [MS-XLSB] 2.5.97.88 */\nfunction parse_Rgce(blob, length, opts) {\n\tvar target = blob.l + length;\n\tvar R, id, ptgs = [];\n\twhile(target != blob.l) {\n\t\tlength = target - blob.l;\n\t\tid = blob[blob.l];\n\t\tR = PtgTypes[id] || PtgTypes[PtgDupes[id]];\n\t\tif(id === 0x18 || id === 0x19) R = (id === 0x18 ? Ptg18 : Ptg19)[blob[blob.l + 1]];\n\t\tif(!R || !R.f) { /*ptgs.push*/(parsenoop(blob, length)); }\n\t\telse { ptgs.push([R.n, R.f(blob, length, opts)]); }\n\t}\n\treturn ptgs;\n}\n\nfunction stringify_array(f/*:Array<Array<string>>*/)/*:string*/ {\n\tvar o/*:Array<string>*/ = [];\n\tfor(var i = 0; i < f.length; ++i) {\n\t\tvar x = f[i], r/*:Array<string>*/ = [];\n\t\tfor(var j = 0; j < x.length; ++j) {\n\t\t\tvar y = x[j];\n\t\t\tif(y) switch(y[0]) {\n\t\t\t\t// TODO: handle embedded quotes\n\t\t\t\tcase 0x02:\n\t\t\t\t\t/*:: if(typeof y[1] != 'string') throw \"unreachable\"; */\n\t\t\t\t\tr.push('\"' + y[1].replace(/\"/g,'\"\"') + '\"'); break;\n\t\t\t\tdefault: r.push(y[1]);\n\t\t\t} else r.push(\"\");\n\t\t}\n\t\to.push(r.join(\",\"));\n\t}\n\treturn o.join(\";\");\n}\n\n/* [MS-XLS] 2.2.2 ; [MS-XLSB] 2.2.2 TODO */\nvar PtgBinOp = {\n\tPtgAdd: \"+\",\n\tPtgConcat: \"&\",\n\tPtgDiv: \"/\",\n\tPtgEq: \"=\",\n\tPtgGe: \">=\",\n\tPtgGt: \">\",\n\tPtgLe: \"<=\",\n\tPtgLt: \"<\",\n\tPtgMul: \"*\",\n\tPtgNe: \"<>\",\n\tPtgPower: \"^\",\n\tPtgSub: \"-\"\n};\n\n// List of invalid characters needs to be tested further\nfunction formula_quote_sheet_name(sname/*:string*/, opts)/*:string*/ {\n\tif(!sname && !(opts && opts.biff <= 5 && opts.biff >= 2)) throw new Error(\"empty sheet name\");\n\tif (/[^\\w\\u4E00-\\u9FFF\\u3040-\\u30FF]/.test(sname)) return \"'\" + sname + \"'\";\n\treturn sname;\n}\nfunction get_ixti_raw(supbooks, ixti/*:number*/, opts)/*:string*/ {\n\tif(!supbooks) return \"SH33TJSERR0\";\n\tif(opts.biff > 8 && (!supbooks.XTI || !supbooks.XTI[ixti])) return supbooks.SheetNames[ixti];\n\tif(!supbooks.XTI) return \"SH33TJSERR6\";\n\tvar XTI = supbooks.XTI[ixti];\n\tif(opts.biff < 8) {\n\t\tif(ixti > 10000) ixti-= 65536;\n\t\tif(ixti < 0) ixti = -ixti;\n\t\treturn ixti == 0 ? \"\" : supbooks.XTI[ixti - 1];\n\t}\n\tif(!XTI) return \"SH33TJSERR1\";\n\tvar o = \"\";\n\tif(opts.biff > 8) switch(supbooks[XTI[0]][0]) {\n\t\tcase 0x0165: /* 'BrtSupSelf' */\n\t\t\to = XTI[1] == -1 ? \"#REF\" : supbooks.SheetNames[XTI[1]];\n\t\t\treturn XTI[1] == XTI[2] ? o : o + \":\" + supbooks.SheetNames[XTI[2]];\n\t\tcase 0x0166: /* 'BrtSupSame' */\n\t\t\tif(opts.SID != null) return supbooks.SheetNames[opts.SID];\n\t\t\treturn \"SH33TJSSAME\" + supbooks[XTI[0]][0];\n\t\tcase 0x0163: /* 'BrtSupBookSrc' */\n\t\t\t/* falls through */\n\t\tdefault: return \"SH33TJSSRC\" + supbooks[XTI[0]][0];\n\t}\n\tswitch(supbooks[XTI[0]][0][0]) {\n\t\tcase 0x0401:\n\t\t\to = XTI[1] == -1 ? \"#REF\" : (supbooks.SheetNames[XTI[1]] || \"SH33TJSERR3\");\n\t\t\treturn XTI[1] == XTI[2] ? o : o + \":\" + supbooks.SheetNames[XTI[2]];\n\t\tcase 0x3A01: return supbooks[XTI[0]].slice(1).map(function(name) { return name.Name; }).join(\";;\"); //return \"SH33TJSERR8\";\n\t\tdefault:\n\t\t\tif(!supbooks[XTI[0]][0][3]) return \"SH33TJSERR2\";\n\t\t\to = XTI[1] == -1 ? \"#REF\" : (supbooks[XTI[0]][0][3][XTI[1]] || \"SH33TJSERR4\");\n\t\t\treturn XTI[1] == XTI[2] ? o : o + \":\" + supbooks[XTI[0]][0][3][XTI[2]];\n\t}\n}\nfunction get_ixti(supbooks, ixti/*:number*/, opts)/*:string*/ {\n\tvar ixtiraw = get_ixti_raw(supbooks, ixti, opts);\n\treturn ixtiraw == \"#REF\" ? ixtiraw : formula_quote_sheet_name(ixtiraw, opts);\n}\nfunction stringify_formula(formula/*Array<any>*/, range, cell/*:any*/, supbooks, opts)/*:string*/ {\n\tvar biff = (opts && opts.biff) || 8;\n\tvar _range = /*range != null ? range :*/ {s:{c:0, r:0},e:{c:0, r:0}};\n\tvar stack/*:Array<string>*/ = [], e1, e2, /*::type,*/ c/*:CellAddress*/, ixti=0, nameidx=0, r, sname=\"\";\n\tif(!formula[0] || !formula[0][0]) return \"\";\n\tvar last_sp = -1, sp = \"\";\n\tfor(var ff = 0, fflen = formula[0].length; ff < fflen; ++ff) {\n\t\tvar f = formula[0][ff];\n\t\tswitch(f[0]) {\n\t\t\tcase 'PtgUminus': /* [MS-XLS] 2.5.198.93 */\n\t\t\t\tstack.push(\"-\" + stack.pop()); break;\n\t\t\tcase 'PtgUplus': /* [MS-XLS] 2.5.198.95 */\n\t\t\t\tstack.push(\"+\" + stack.pop()); break;\n\t\t\tcase 'PtgPercent': /* [MS-XLS] 2.5.198.81 */\n\t\t\t\tstack.push(stack.pop() + \"%\"); break;\n\n\t\t\tcase 'PtgAdd':    /* [MS-XLS] 2.5.198.26 */\n\t\t\tcase 'PtgConcat': /* [MS-XLS] 2.5.198.43 */\n\t\t\tcase 'PtgDiv':    /* [MS-XLS] 2.5.198.45 */\n\t\t\tcase 'PtgEq':     /* [MS-XLS] 2.5.198.56 */\n\t\t\tcase 'PtgGe':     /* [MS-XLS] 2.5.198.64 */\n\t\t\tcase 'PtgGt':     /* [MS-XLS] 2.5.198.65 */\n\t\t\tcase 'PtgLe':     /* [MS-XLS] 2.5.198.68 */\n\t\t\tcase 'PtgLt':     /* [MS-XLS] 2.5.198.69 */\n\t\t\tcase 'PtgMul':    /* [MS-XLS] 2.5.198.75 */\n\t\t\tcase 'PtgNe':     /* [MS-XLS] 2.5.198.78 */\n\t\t\tcase 'PtgPower':  /* [MS-XLS] 2.5.198.82 */\n\t\t\tcase 'PtgSub':    /* [MS-XLS] 2.5.198.90 */\n\t\t\t\te1 = stack.pop(); e2 = stack.pop();\n\t\t\t\tif(last_sp >= 0) {\n\t\t\t\t\tswitch(formula[0][last_sp][1][0]) {\n\t\t\t\t\t\tcase 0:\n\t\t\t\t\t\t\t// $FlowIgnore\n\t\t\t\t\t\t\tsp = fill(\" \", formula[0][last_sp][1][1]); break;\n\t\t\t\t\t\tcase 1:\n\t\t\t\t\t\t\t// $FlowIgnore\n\t\t\t\t\t\t\tsp = fill(\"\\r\", formula[0][last_sp][1][1]); break;\n\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\tsp = \"\";\n\t\t\t\t\t\t\t// $FlowIgnore\n\t\t\t\t\t\t\tif(opts.WTF) throw new Error(\"Unexpected PtgAttrSpaceType \" + formula[0][last_sp][1][0]);\n\t\t\t\t\t}\n\t\t\t\t\te2 = e2 + sp;\n\t\t\t\t\tlast_sp = -1;\n\t\t\t\t}\n\t\t\t\tstack.push(e2+PtgBinOp[f[0]]+e1);\n\t\t\t\tbreak;\n\n\t\t\tcase 'PtgIsect': /* [MS-XLS] 2.5.198.67 */\n\t\t\t\te1 = stack.pop(); e2 = stack.pop();\n\t\t\t\tstack.push(e2+\" \"+e1);\n\t\t\t\tbreak;\n\t\t\tcase 'PtgUnion': /* [MS-XLS] 2.5.198.94 */\n\t\t\t\te1 = stack.pop(); e2 = stack.pop();\n\t\t\t\tstack.push(e2+\",\"+e1);\n\t\t\t\tbreak;\n\t\t\tcase 'PtgRange': /* [MS-XLS] 2.5.198.83 */\n\t\t\t\te1 = stack.pop(); e2 = stack.pop();\n\t\t\t\tstack.push(e2+\":\"+e1);\n\t\t\t\tbreak;\n\n\t\t\tcase 'PtgAttrChoose': /* [MS-XLS] 2.5.198.34 */\n\t\t\t\tbreak;\n\t\t\tcase 'PtgAttrGoto': /* [MS-XLS] 2.5.198.35 */\n\t\t\t\tbreak;\n\t\t\tcase 'PtgAttrIf': /* [MS-XLS] 2.5.198.36 */\n\t\t\t\tbreak;\n\t\t\tcase 'PtgAttrIfError': /* [MS-XLSB] 2.5.97.28 */\n\t\t\t\tbreak;\n\n\n\t\t\tcase 'PtgRef': /* [MS-XLS] 2.5.198.84 */\n\t\t\t\t/*::type = f[1][0]; */c = shift_cell_xls((f[1][1]/*:any*/), _range, opts);\n\t\t\t\tstack.push(encode_cell_xls(c, biff));\n\t\t\t\tbreak;\n\t\t\tcase 'PtgRefN': /* [MS-XLS] 2.5.198.88 */\n\t\t\t\t/*::type = f[1][0]; */c = cell ? shift_cell_xls((f[1][1]/*:any*/), cell, opts) : (f[1][1]/*:any*/);\n\t\t\t\tstack.push(encode_cell_xls(c, biff));\n\t\t\t\tbreak;\n\t\t\tcase 'PtgRef3d': /* [MS-XLS] 2.5.198.85 */\n\t\t\t\t/*::type = f[1][0]; */ixti = /*::Number(*/f[1][1]/*::)*/; c = shift_cell_xls((f[1][2]/*:any*/), _range, opts);\n\t\t\t\tsname = get_ixti(supbooks, ixti, opts);\n\t\t\t\tvar w = sname; /* IE9 fails on defined names */ // eslint-disable-line no-unused-vars\n\t\t\t\tstack.push(sname + \"!\" + encode_cell_xls(c, biff));\n\t\t\t\tbreak;\n\n\t\t\tcase 'PtgFunc': /* [MS-XLS] 2.5.198.62 */\n\t\t\tcase 'PtgFuncVar': /* [MS-XLS] 2.5.198.63 */\n\t\t\t\t/* f[1] = [argc, func, type] */\n\t\t\t\tvar argc/*:number*/ = (f[1][0]/*:any*/), func/*:string*/ = (f[1][1]/*:any*/);\n\t\t\t\tif(!argc) argc = 0;\n\t\t\t\targc &= 0x7F;\n\t\t\t\tvar args = argc == 0 ? [] : stack.slice(-argc);\n\t\t\t\tstack.length -= argc;\n\t\t\t\tif(func === 'User') func = args.shift();\n\t\t\t\tstack.push(func + \"(\" + args.join(\",\") + \")\");\n\t\t\t\tbreak;\n\n\t\t\tcase 'PtgBool': /* [MS-XLS] 2.5.198.42 */\n\t\t\t\tstack.push(f[1] ? \"TRUE\" : \"FALSE\"); break;\n\t\t\tcase 'PtgInt': /* [MS-XLS] 2.5.198.66 */\n\t\t\t\tstack.push(/*::String(*/f[1]/*::)*/); break;\n\t\t\tcase 'PtgNum': /* [MS-XLS] 2.5.198.79 TODO: precision? */\n\t\t\t\tstack.push(String(f[1])); break;\n\t\t\tcase 'PtgStr': /* [MS-XLS] 2.5.198.89 */\n\t\t\t\t// $FlowIgnore\n\t\t\t\tstack.push('\"' + f[1].replace(/\"/g, '\"\"') + '\"'); break;\n\t\t\tcase 'PtgErr': /* [MS-XLS] 2.5.198.57 */\n\t\t\t\tstack.push(/*::String(*/f[1]/*::)*/); break;\n\t\t\tcase 'PtgAreaN': /* [MS-XLS] 2.5.198.31 TODO */\n\t\t\t\t/*::type = f[1][0]; */r = shift_range_xls(f[1][1], cell ? {s:cell} : _range, opts);\n\t\t\t\tstack.push(encode_range_xls((r/*:any*/), opts));\n\t\t\t\tbreak;\n\t\t\tcase 'PtgArea': /* [MS-XLS] 2.5.198.27 TODO: fixed points */\n\t\t\t\t/*::type = f[1][0]; */r = shift_range_xls(f[1][1], _range, opts);\n\t\t\t\tstack.push(encode_range_xls((r/*:any*/), opts));\n\t\t\t\tbreak;\n\t\t\tcase 'PtgArea3d': /* [MS-XLS] 2.5.198.28 TODO */\n\t\t\t\t/*::type = f[1][0]; */ixti = /*::Number(*/f[1][1]/*::)*/; r = f[1][2];\n\t\t\t\tsname = get_ixti(supbooks, ixti, opts);\n\t\t\t\tstack.push(sname + \"!\" + encode_range_xls((r/*:any*/), opts));\n\t\t\t\tbreak;\n\t\t\tcase 'PtgAttrSum': /* [MS-XLS] 2.5.198.41 */\n\t\t\t\tstack.push(\"SUM(\" + stack.pop() + \")\");\n\t\t\t\tbreak;\n\n\t\t\tcase 'PtgAttrBaxcel': /* [MS-XLS] 2.5.198.33 */\n\t\t\tcase 'PtgAttrSemi': /* [MS-XLS] 2.5.198.37 */\n\t\t\t\tbreak;\n\n\t\t\tcase 'PtgName': /* [MS-XLS] 2.5.198.76 ; [MS-XLSB] 2.5.97.60 TODO: revisions */\n\t\t\t\t/* f[1] = type, 0, nameindex */\n\t\t\t\tnameidx = (f[1][2]/*:any*/);\n\t\t\t\tvar lbl = (supbooks.names||[])[nameidx-1] || (supbooks[0]||[])[nameidx];\n\t\t\t\tvar name = lbl ? lbl.Name : \"SH33TJSNAME\" + String(nameidx);\n\t\t\t\t/* [MS-XLSB] 2.5.97.10 Ftab -- last verified 20220204 */\n\t\t\t\tif(name && name.slice(0,6) == \"_xlfn.\" && !opts.xlfn) name = name.slice(6);\n\t\t\t\tstack.push(name);\n\t\t\t\tbreak;\n\n\t\t\tcase 'PtgNameX': /* [MS-XLS] 2.5.198.77 ; [MS-XLSB] 2.5.97.61 TODO: revisions */\n\t\t\t\t/* f[1] = type, ixti, nameindex */\n\t\t\t\tvar bookidx/*:number*/ = (f[1][1]/*:any*/); nameidx = (f[1][2]/*:any*/); var externbook;\n\t\t\t\t/* TODO: Properly handle missing values -- this should be using get_ixti_raw primarily */\n\t\t\t\tif(opts.biff <= 5) {\n\t\t\t\t\tif(bookidx < 0) bookidx = -bookidx;\n\t\t\t\t\tif(supbooks[bookidx]) externbook = supbooks[bookidx][nameidx];\n\t\t\t\t} else {\n\t\t\t\t\tvar o = \"\";\n\t\t\t\t\tif(((supbooks[bookidx]||[])[0]||[])[0] == 0x3A01){/* empty */}\n\t\t\t\t\telse if(((supbooks[bookidx]||[])[0]||[])[0] == 0x0401){\n\t\t\t\t\t\tif(supbooks[bookidx][nameidx] && supbooks[bookidx][nameidx].itab > 0) {\n\t\t\t\t\t\t\to = supbooks.SheetNames[supbooks[bookidx][nameidx].itab-1] + \"!\";\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\telse o = supbooks.SheetNames[nameidx-1]+ \"!\";\n\t\t\t\t\tif(supbooks[bookidx] && supbooks[bookidx][nameidx]) o += supbooks[bookidx][nameidx].Name;\n\t\t\t\t\telse if(supbooks[0] && supbooks[0][nameidx]) o += supbooks[0][nameidx].Name;\n\t\t\t\t\telse {\n\t\t\t\t\t\tvar ixtidata = (get_ixti_raw(supbooks, bookidx, opts)||\"\").split(\";;\");\n\t\t\t\t\t\tif(ixtidata[nameidx - 1]) o = ixtidata[nameidx - 1]; // TODO: confirm this is correct\n\t\t\t\t\t\telse o += \"SH33TJSERRX\";\n\t\t\t\t\t}\n\t\t\t\t\tstack.push(o);\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\tif(!externbook) externbook = {Name: \"SH33TJSERRY\"};\n\t\t\t\tstack.push(externbook.Name);\n\t\t\t\tbreak;\n\n\t\t\tcase 'PtgParen': /* [MS-XLS] 2.5.198.80 */\n\t\t\t\tvar lp = '(', rp = ')';\n\t\t\t\tif(last_sp >= 0) {\n\t\t\t\t\tsp = \"\";\n\t\t\t\t\tswitch(formula[0][last_sp][1][0]) {\n\t\t\t\t\t\t// $FlowIgnore\n\t\t\t\t\t\tcase 2: lp = fill(\" \", formula[0][last_sp][1][1]) + lp; break;\n\t\t\t\t\t\t// $FlowIgnore\n\t\t\t\t\t\tcase 3: lp = fill(\"\\r\", formula[0][last_sp][1][1]) + lp; break;\n\t\t\t\t\t\t// $FlowIgnore\n\t\t\t\t\t\tcase 4: rp = fill(\" \", formula[0][last_sp][1][1]) + rp; break;\n\t\t\t\t\t\t// $FlowIgnore\n\t\t\t\t\t\tcase 5: rp = fill(\"\\r\", formula[0][last_sp][1][1]) + rp; break;\n\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\t// $FlowIgnore\n\t\t\t\t\t\t\tif(opts.WTF) throw new Error(\"Unexpected PtgAttrSpaceType \" + formula[0][last_sp][1][0]);\n\t\t\t\t\t}\n\t\t\t\t\tlast_sp = -1;\n\t\t\t\t}\n\t\t\t\tstack.push(lp + stack.pop() + rp); break;\n\n\t\t\tcase 'PtgRefErr': /* [MS-XLS] 2.5.198.86 */\n\t\t\t\tstack.push('#REF!'); break;\n\n\t\t\tcase 'PtgRefErr3d': /* [MS-XLS] 2.5.198.87 */\n\t\t\t\tstack.push('#REF!'); break;\n\n\t\t\tcase 'PtgExp': /* [MS-XLS] 2.5.198.58 TODO */\n\t\t\t\tc = {c:(f[1][1]/*:any*/),r:(f[1][0]/*:any*/)};\n\t\t\t\tvar q = ({c: cell.c, r:cell.r}/*:any*/);\n\t\t\t\tif(supbooks.sharedf[encode_cell(c)]) {\n\t\t\t\t\tvar parsedf = (supbooks.sharedf[encode_cell(c)]);\n\t\t\t\t\tstack.push(stringify_formula(parsedf, _range, q, supbooks, opts));\n\t\t\t\t} else {\n\t\t\t\t\tvar fnd = false;\n\t\t\t\t\tfor(e1=0;e1!=supbooks.arrayf.length; ++e1) {\n\t\t\t\t\t\t/* TODO: should be something like range_has */\n\t\t\t\t\t\te2 = supbooks.arrayf[e1];\n\t\t\t\t\t\tif(c.c < e2[0].s.c || c.c > e2[0].e.c) continue;\n\t\t\t\t\t\tif(c.r < e2[0].s.r || c.r > e2[0].e.r) continue;\n\t\t\t\t\t\tstack.push(stringify_formula(e2[1], _range, q, supbooks, opts));\n\t\t\t\t\t\tfnd = true;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t\tif(!fnd) stack.push(/*::String(*/f[1]/*::)*/);\n\t\t\t\t}\n\t\t\t\tbreak;\n\n\t\t\tcase 'PtgArray': /* [MS-XLS] 2.5.198.32 TODO */\n\t\t\t\tstack.push(\"{\" + stringify_array(/*::(*/f[1]/*:: :any)*/) + \"}\");\n\t\t\t\tbreak;\n\n\t\t\tcase 'PtgMemArea': /* [MS-XLS] 2.5.198.70 TODO: confirm this is a non-display */\n\t\t\t\t//stack.push(\"(\" + f[2].map(encode_range).join(\",\") + \")\");\n\t\t\t\tbreak;\n\n\t\t\tcase 'PtgAttrSpace': /* [MS-XLS] 2.5.198.38 */\n\t\t\tcase 'PtgAttrSpaceSemi': /* [MS-XLS] 2.5.198.39 */\n\t\t\t\tlast_sp = ff;\n\t\t\t\tbreak;\n\n\t\t\tcase 'PtgTbl': /* [MS-XLS] 2.5.198.92 TODO */\n\t\t\t\tbreak;\n\n\t\t\tcase 'PtgMemErr': /* [MS-XLS] 2.5.198.71 */\n\t\t\t\tbreak;\n\n\t\t\tcase 'PtgMissArg': /* [MS-XLS] 2.5.198.74 */\n\t\t\t\tstack.push(\"\");\n\t\t\t\tbreak;\n\n\t\t\tcase 'PtgAreaErr': /* [MS-XLS] 2.5.198.29 */\n\t\t\t\tstack.push(\"#REF!\"); break;\n\n\t\t\tcase 'PtgAreaErr3d': /* [MS-XLS] 2.5.198.30 */\n\t\t\t\tstack.push(\"#REF!\"); break;\n\n\t\t\tcase 'PtgList': /* [MS-XLSB] 2.5.97.52 */\n\t\t\t\t// $FlowIgnore\n\t\t\t\tstack.push(\"Table\" + f[1].idx + \"[#\" + f[1].rt + \"]\");\n\t\t\t\tbreak;\n\n\t\t\tcase 'PtgMemAreaN':\n\t\t\tcase 'PtgMemNoMemN':\n\t\t\tcase 'PtgAttrNoop':\n\t\t\tcase 'PtgSheet':\n\t\t\tcase 'PtgEndSheet':\n\t\t\t\tbreak;\n\n\t\t\tcase 'PtgMemFunc': /* [MS-XLS] 2.5.198.72 TODO */\n\t\t\t\tbreak;\n\t\t\tcase 'PtgMemNoMem': /* [MS-XLS] 2.5.198.73 TODO */\n\t\t\t\tbreak;\n\n\t\t\tcase 'PtgElfCol': /* [MS-XLS] 2.5.198.46 */\n\t\t\tcase 'PtgElfColS': /* [MS-XLS] 2.5.198.47 */\n\t\t\tcase 'PtgElfColSV': /* [MS-XLS] 2.5.198.48 */\n\t\t\tcase 'PtgElfColV': /* [MS-XLS] 2.5.198.49 */\n\t\t\tcase 'PtgElfLel': /* [MS-XLS] 2.5.198.50 */\n\t\t\tcase 'PtgElfRadical': /* [MS-XLS] 2.5.198.51 */\n\t\t\tcase 'PtgElfRadicalLel': /* [MS-XLS] 2.5.198.52 */\n\t\t\tcase 'PtgElfRadicalS': /* [MS-XLS] 2.5.198.53 */\n\t\t\tcase 'PtgElfRw': /* [MS-XLS] 2.5.198.54 */\n\t\t\tcase 'PtgElfRwV': /* [MS-XLS] 2.5.198.55 */\n\t\t\t\tthrow new Error(\"Unsupported ELFs\");\n\n\t\t\tcase 'PtgSxName': /* [MS-XLS] 2.5.198.91 TODO -- find a test case */\n\t\t\t\tthrow new Error('Unrecognized Formula Token: ' + String(f));\n\t\t\tdefault: throw new Error('Unrecognized Formula Token: ' + String(f));\n\t\t}\n\t\tvar PtgNonDisp = ['PtgAttrSpace', 'PtgAttrSpaceSemi', 'PtgAttrGoto'];\n\t\tif(opts.biff != 3) if(last_sp >= 0 && PtgNonDisp.indexOf(formula[0][ff][0]) == -1) {\n\t\t\tf = formula[0][last_sp];\n\t\t\tvar _left = true;\n\t\t\tswitch(f[1][0]) {\n\t\t\t\t/* note: some bad XLSB files omit the PtgParen */\n\t\t\t\tcase 4: _left = false;\n\t\t\t\t/* falls through */\n\t\t\t\tcase 0:\n\t\t\t\t\t// $FlowIgnore\n\t\t\t\t\tsp = fill(\" \", f[1][1]); break;\n\t\t\t\tcase 5: _left = false;\n\t\t\t\t/* falls through */\n\t\t\t\tcase 1:\n\t\t\t\t\t// $FlowIgnore\n\t\t\t\t\tsp = fill(\"\\r\", f[1][1]); break;\n\t\t\t\tdefault:\n\t\t\t\t\tsp = \"\";\n\t\t\t\t\t// $FlowIgnore\n\t\t\t\t\tif(opts.WTF) throw new Error(\"Unexpected PtgAttrSpaceType \" + f[1][0]);\n\t\t\t}\n\t\t\tstack.push((_left ? sp : \"\") + stack.pop() + (_left ? \"\" : sp));\n\t\t\tlast_sp = -1;\n\t\t}\n\t}\n\tif(stack.length > 1 && opts.WTF) throw new Error(\"bad formula stack\");\n\treturn stack[0];\n}\n\n/* [MS-XLS] 2.5.198.1 TODO */\nfunction parse_ArrayParsedFormula(blob, length, opts/*::, ref*/) {\n\tvar target = blob.l + length, len = opts.biff == 2 ? 1 : 2;\n\tvar rgcb, cce = blob.read_shift(len); // length of rgce\n\tif(cce == 0xFFFF) return [[],parsenoop(blob, length-2)];\n\tvar rgce = parse_Rgce(blob, cce, opts);\n\tif(length !== cce + len) rgcb = parse_RgbExtra(blob, length - cce - len, rgce, opts);\n\tblob.l = target;\n\treturn [rgce, rgcb];\n}\n\n/* [MS-XLS] 2.5.198.3 TODO */\nfunction parse_XLSCellParsedFormula(blob, length, opts) {\n\tvar target = blob.l + length, len = opts.biff == 2 ? 1 : 2;\n\tvar rgcb, cce = blob.read_shift(len); // length of rgce\n\tif(cce == 0xFFFF) return [[],parsenoop(blob, length-2)];\n\tvar rgce = parse_Rgce(blob, cce, opts);\n\tif(length !== cce + len) rgcb = parse_RgbExtra(blob, length - cce - len, rgce, opts);\n\tblob.l = target;\n\treturn [rgce, rgcb];\n}\n\n/* [MS-XLS] 2.5.198.21 */\nfunction parse_NameParsedFormula(blob, length, opts, cce) {\n\tvar target = blob.l + length;\n\tvar rgce = parse_Rgce(blob, cce, opts);\n\tvar rgcb;\n\tif(target !== blob.l) rgcb = parse_RgbExtra(blob, target - blob.l, rgce, opts);\n\treturn [rgce, rgcb];\n}\n\n/* [MS-XLS] 2.5.198.118 TODO */\nfunction parse_SharedParsedFormula(blob, length, opts) {\n\tvar target = blob.l + length;\n\tvar rgcb, cce = blob.read_shift(2); // length of rgce\n\tvar rgce = parse_Rgce(blob, cce, opts);\n\tif(cce == 0xFFFF) return [[],parsenoop(blob, length-2)];\n\tif(length !== cce + 2) rgcb = parse_RgbExtra(blob, target - cce - 2, rgce, opts);\n\treturn [rgce, rgcb];\n}\n\n/* [MS-XLS] 2.5.133 TODO: how to emit empty strings? */\nfunction parse_FormulaValue(blob/*::, length*/) {\n\tvar b;\n\tif(__readUInt16LE(blob,blob.l + 6) !== 0xFFFF) return [parse_Xnum(blob),'n'];\n\tswitch(blob[blob.l]) {\n\t\tcase 0x00: blob.l += 8; return [\"String\", 's'];\n\t\tcase 0x01: b = blob[blob.l+2] === 0x1; blob.l += 8; return [b,'b'];\n\t\tcase 0x02: b = blob[blob.l+2]; blob.l += 8; return [b,'e'];\n\t\tcase 0x03: blob.l += 8; return [\"\",'s'];\n\t}\n\treturn [];\n}\nfunction write_FormulaValue(value) {\n\tif(value == null) {\n\t\t// Blank String Value\n\t\tvar o = new_buf(8);\n\t\to.write_shift(1, 0x03);\n\t\to.write_shift(1, 0);\n\t\to.write_shift(2, 0);\n\t\to.write_shift(2, 0);\n\t\to.write_shift(2, 0xFFFF);\n\t\treturn o;\n\t} else if(typeof value == \"number\") return write_Xnum(value);\n\treturn write_Xnum(0);\n}\n\n/* [MS-XLS] 2.4.127 TODO */\nfunction parse_Formula(blob, length, opts) {\n\tvar end = blob.l + length;\n\tvar cell = parse_XLSCell(blob, 6);\n\tif(opts.biff == 2) ++blob.l;\n\tvar val = parse_FormulaValue(blob,8);\n\tvar flags = blob.read_shift(1);\n\tif(opts.biff != 2) {\n\t\tblob.read_shift(1);\n\t\tif(opts.biff >= 5) {\n\t\t\t/*var chn = */blob.read_shift(4);\n\t\t}\n\t}\n\tvar cbf = parse_XLSCellParsedFormula(blob, end - blob.l, opts);\n\treturn {cell:cell, val:val[0], formula:cbf, shared: (flags >> 3) & 1, tt:val[1]};\n}\nfunction write_Formula(cell/*:Cell*/, R/*:number*/, C/*:number*/, opts, os/*:number*/) {\n\t// Cell\n\tvar o1 = write_XLSCell(R, C, os);\n\n\t// FormulaValue\n\tvar o2 = write_FormulaValue(cell.v);\n\n\t// flags + cache\n\tvar o3 = new_buf(6);\n\tvar flags = 0x01 | 0x20;\n\to3.write_shift(2, flags);\n\to3.write_shift(4, 0);\n\n\t// CellParsedFormula\n\tvar bf = new_buf(cell.bf.length);\n\tfor(var i = 0; i < cell.bf.length; ++i) bf[i] = cell.bf[i];\n\n\tvar out = bconcat([o1, o2, o3, bf]);\n\treturn out;\n}\n\n\n/* XLSB Parsed Formula records have the same shape */\nfunction parse_XLSBParsedFormula(data, length, opts) {\n\tvar cce = data.read_shift(4);\n\tvar rgce = parse_Rgce(data, cce, opts);\n\tvar cb = data.read_shift(4);\n\tvar rgcb = cb > 0 ? parse_RgbExtra(data, cb, rgce, opts) : null;\n\treturn [rgce, rgcb];\n}\n\n/* [MS-XLSB] 2.5.97.1 ArrayParsedFormula */\nvar parse_XLSBArrayParsedFormula = parse_XLSBParsedFormula;\n/* [MS-XLSB] 2.5.97.4 CellParsedFormula */\nvar parse_XLSBCellParsedFormula = parse_XLSBParsedFormula;\n/* [MS-XLSB] 2.5.97.8 DVParsedFormula */\n//var parse_XLSBDVParsedFormula = parse_XLSBParsedFormula;\n/* [MS-XLSB] 2.5.97.9 FRTParsedFormula */\n//var parse_XLSBFRTParsedFormula = parse_XLSBParsedFormula2;\n/* [MS-XLSB] 2.5.97.12 NameParsedFormula */\nvar parse_XLSBNameParsedFormula = parse_XLSBParsedFormula;\n/* [MS-XLSB] 2.5.97.98 SharedParsedFormula */\nvar parse_XLSBSharedParsedFormula = parse_XLSBParsedFormula;\nvar Cetab = {\n  0: \"BEEP\",\n  1: \"OPEN\",\n  2: \"OPEN.LINKS\",\n  3: \"CLOSE.ALL\",\n  4: \"SAVE\",\n  5: \"SAVE.AS\",\n  6: \"FILE.DELETE\",\n  7: \"PAGE.SETUP\",\n  8: \"PRINT\",\n  9: \"PRINTER.SETUP\",\n  10: \"QUIT\",\n  11: \"NEW.WINDOW\",\n  12: \"ARRANGE.ALL\",\n  13: \"WINDOW.SIZE\",\n  14: \"WINDOW.MOVE\",\n  15: \"FULL\",\n  16: \"CLOSE\",\n  17: \"RUN\",\n  22: \"SET.PRINT.AREA\",\n  23: \"SET.PRINT.TITLES\",\n  24: \"SET.PAGE.BREAK\",\n  25: \"REMOVE.PAGE.BREAK\",\n  26: \"FONT\",\n  27: \"DISPLAY\",\n  28: \"PROTECT.DOCUMENT\",\n  29: \"PRECISION\",\n  30: \"A1.R1C1\",\n  31: \"CALCULATE.NOW\",\n  32: \"CALCULATION\",\n  34: \"DATA.FIND\",\n  35: \"EXTRACT\",\n  36: \"DATA.DELETE\",\n  37: \"SET.DATABASE\",\n  38: \"SET.CRITERIA\",\n  39: \"SORT\",\n  40: \"DATA.SERIES\",\n  41: \"TABLE\",\n  42: \"FORMAT.NUMBER\",\n  43: \"ALIGNMENT\",\n  44: \"STYLE\",\n  45: \"BORDER\",\n  46: \"CELL.PROTECTION\",\n  47: \"COLUMN.WIDTH\",\n  48: \"UNDO\",\n  49: \"CUT\",\n  50: \"COPY\",\n  51: \"PASTE\",\n  52: \"CLEAR\",\n  53: \"PASTE.SPECIAL\",\n  54: \"EDIT.DELETE\",\n  55: \"INSERT\",\n  56: \"FILL.RIGHT\",\n  57: \"FILL.DOWN\",\n  61: \"DEFINE.NAME\",\n  62: \"CREATE.NAMES\",\n  63: \"FORMULA.GOTO\",\n  64: \"FORMULA.FIND\",\n  65: \"SELECT.LAST.CELL\",\n  66: \"SHOW.ACTIVE.CELL\",\n  67: \"GALLERY.AREA\",\n  68: \"GALLERY.BAR\",\n  69: \"GALLERY.COLUMN\",\n  70: \"GALLERY.LINE\",\n  71: \"GALLERY.PIE\",\n  72: \"GALLERY.SCATTER\",\n  73: \"COMBINATION\",\n  74: \"PREFERRED\",\n  75: \"ADD.OVERLAY\",\n  76: \"GRIDLINES\",\n  77: \"SET.PREFERRED\",\n  78: \"AXES\",\n  79: \"LEGEND\",\n  80: \"ATTACH.TEXT\",\n  81: \"ADD.ARROW\",\n  82: \"SELECT.CHART\",\n  83: \"SELECT.PLOT.AREA\",\n  84: \"PATTERNS\",\n  85: \"MAIN.CHART\",\n  86: \"OVERLAY\",\n  87: \"SCALE\",\n  88: \"FORMAT.LEGEND\",\n  89: \"FORMAT.TEXT\",\n  90: \"EDIT.REPEAT\",\n  91: \"PARSE\",\n  92: \"JUSTIFY\",\n  93: \"HIDE\",\n  94: \"UNHIDE\",\n  95: \"WORKSPACE\",\n  96: \"FORMULA\",\n  97: \"FORMULA.FILL\",\n  98: \"FORMULA.ARRAY\",\n  99: \"DATA.FIND.NEXT\",\n  100: \"DATA.FIND.PREV\",\n  101: \"FORMULA.FIND.NEXT\",\n  102: \"FORMULA.FIND.PREV\",\n  103: \"ACTIVATE\",\n  104: \"ACTIVATE.NEXT\",\n  105: \"ACTIVATE.PREV\",\n  106: \"UNLOCKED.NEXT\",\n  107: \"UNLOCKED.PREV\",\n  108: \"COPY.PICTURE\",\n  109: \"SELECT\",\n  110: \"DELETE.NAME\",\n  111: \"DELETE.FORMAT\",\n  112: \"VLINE\",\n  113: \"HLINE\",\n  114: \"VPAGE\",\n  115: \"HPAGE\",\n  116: \"VSCROLL\",\n  117: \"HSCROLL\",\n  118: \"ALERT\",\n  119: \"NEW\",\n  120: \"CANCEL.COPY\",\n  121: \"SHOW.CLIPBOARD\",\n  122: \"MESSAGE\",\n  124: \"PASTE.LINK\",\n  125: \"APP.ACTIVATE\",\n  126: \"DELETE.ARROW\",\n  127: \"ROW.HEIGHT\",\n  128: \"FORMAT.MOVE\",\n  129: \"FORMAT.SIZE\",\n  130: \"FORMULA.REPLACE\",\n  131: \"SEND.KEYS\",\n  132: \"SELECT.SPECIAL\",\n  133: \"APPLY.NAMES\",\n  134: \"REPLACE.FONT\",\n  135: \"FREEZE.PANES\",\n  136: \"SHOW.INFO\",\n  137: \"SPLIT\",\n  138: \"ON.WINDOW\",\n  139: \"ON.DATA\",\n  140: \"DISABLE.INPUT\",\n  142: \"OUTLINE\",\n  143: \"LIST.NAMES\",\n  144: \"FILE.CLOSE\",\n  145: \"SAVE.WORKBOOK\",\n  146: \"DATA.FORM\",\n  147: \"COPY.CHART\",\n  148: \"ON.TIME\",\n  149: \"WAIT\",\n  150: \"FORMAT.FONT\",\n  151: \"FILL.UP\",\n  152: \"FILL.LEFT\",\n  153: \"DELETE.OVERLAY\",\n  155: \"SHORT.MENUS\",\n  159: \"SET.UPDATE.STATUS\",\n  161: \"COLOR.PALETTE\",\n  162: \"DELETE.STYLE\",\n  163: \"WINDOW.RESTORE\",\n  164: \"WINDOW.MAXIMIZE\",\n  166: \"CHANGE.LINK\",\n  167: \"CALCULATE.DOCUMENT\",\n  168: \"ON.KEY\",\n  169: \"APP.RESTORE\",\n  170: \"APP.MOVE\",\n  171: \"APP.SIZE\",\n  172: \"APP.MINIMIZE\",\n  173: \"APP.MAXIMIZE\",\n  174: \"BRING.TO.FRONT\",\n  175: \"SEND.TO.BACK\",\n  185: \"MAIN.CHART.TYPE\",\n  186: \"OVERLAY.CHART.TYPE\",\n  187: \"SELECT.END\",\n  188: \"OPEN.MAIL\",\n  189: \"SEND.MAIL\",\n  190: \"STANDARD.FONT\",\n  191: \"CONSOLIDATE\",\n  192: \"SORT.SPECIAL\",\n  193: \"GALLERY.3D.AREA\",\n  194: \"GALLERY.3D.COLUMN\",\n  195: \"GALLERY.3D.LINE\",\n  196: \"GALLERY.3D.PIE\",\n  197: \"VIEW.3D\",\n  198: \"GOAL.SEEK\",\n  199: \"WORKGROUP\",\n  200: \"FILL.GROUP\",\n  201: \"UPDATE.LINK\",\n  202: \"PROMOTE\",\n  203: \"DEMOTE\",\n  204: \"SHOW.DETAIL\",\n  206: \"UNGROUP\",\n  207: \"OBJECT.PROPERTIES\",\n  208: \"SAVE.NEW.OBJECT\",\n  209: \"SHARE\",\n  210: \"SHARE.NAME\",\n  211: \"DUPLICATE\",\n  212: \"APPLY.STYLE\",\n  213: \"ASSIGN.TO.OBJECT\",\n  214: \"OBJECT.PROTECTION\",\n  215: \"HIDE.OBJECT\",\n  216: \"SET.EXTRACT\",\n  217: \"CREATE.PUBLISHER\",\n  218: \"SUBSCRIBE.TO\",\n  219: \"ATTRIBUTES\",\n  220: \"SHOW.TOOLBAR\",\n  222: \"PRINT.PREVIEW\",\n  223: \"EDIT.COLOR\",\n  224: \"SHOW.LEVELS\",\n  225: \"FORMAT.MAIN\",\n  226: \"FORMAT.OVERLAY\",\n  227: \"ON.RECALC\",\n  228: \"EDIT.SERIES\",\n  229: \"DEFINE.STYLE\",\n  240: \"LINE.PRINT\",\n  243: \"ENTER.DATA\",\n  249: \"GALLERY.RADAR\",\n  250: \"MERGE.STYLES\",\n  251: \"EDITION.OPTIONS\",\n  252: \"PASTE.PICTURE\",\n  253: \"PASTE.PICTURE.LINK\",\n  254: \"SPELLING\",\n  256: \"ZOOM\",\n  259: \"INSERT.OBJECT\",\n  260: \"WINDOW.MINIMIZE\",\n  265: \"SOUND.NOTE\",\n  266: \"SOUND.PLAY\",\n  267: \"FORMAT.SHAPE\",\n  268: \"EXTEND.POLYGON\",\n  269: \"FORMAT.AUTO\",\n  272: \"GALLERY.3D.BAR\",\n  273: \"GALLERY.3D.SURFACE\",\n  274: \"FILL.AUTO\",\n  276: \"CUSTOMIZE.TOOLBAR\",\n  277: \"ADD.TOOL\",\n  278: \"EDIT.OBJECT\",\n  279: \"ON.DOUBLECLICK\",\n  280: \"ON.ENTRY\",\n  281: \"WORKBOOK.ADD\",\n  282: \"WORKBOOK.MOVE\",\n  283: \"WORKBOOK.COPY\",\n  284: \"WORKBOOK.OPTIONS\",\n  285: \"SAVE.WORKSPACE\",\n  288: \"CHART.WIZARD\",\n  289: \"DELETE.TOOL\",\n  290: \"MOVE.TOOL\",\n  291: \"WORKBOOK.SELECT\",\n  292: \"WORKBOOK.ACTIVATE\",\n  293: \"ASSIGN.TO.TOOL\",\n  295: \"COPY.TOOL\",\n  296: \"RESET.TOOL\",\n  297: \"CONSTRAIN.NUMERIC\",\n  298: \"PASTE.TOOL\",\n  302: \"WORKBOOK.NEW\",\n  305: \"SCENARIO.CELLS\",\n  306: \"SCENARIO.DELETE\",\n  307: \"SCENARIO.ADD\",\n  308: \"SCENARIO.EDIT\",\n  309: \"SCENARIO.SHOW\",\n  310: \"SCENARIO.SHOW.NEXT\",\n  311: \"SCENARIO.SUMMARY\",\n  312: \"PIVOT.TABLE.WIZARD\",\n  313: \"PIVOT.FIELD.PROPERTIES\",\n  314: \"PIVOT.FIELD\",\n  315: \"PIVOT.ITEM\",\n  316: \"PIVOT.ADD.FIELDS\",\n  318: \"OPTIONS.CALCULATION\",\n  319: \"OPTIONS.EDIT\",\n  320: \"OPTIONS.VIEW\",\n  321: \"ADDIN.MANAGER\",\n  322: \"MENU.EDITOR\",\n  323: \"ATTACH.TOOLBARS\",\n  324: \"VBAActivate\",\n  325: \"OPTIONS.CHART\",\n  328: \"VBA.INSERT.FILE\",\n  330: \"VBA.PROCEDURE.DEFINITION\",\n  336: \"ROUTING.SLIP\",\n  338: \"ROUTE.DOCUMENT\",\n  339: \"MAIL.LOGON\",\n  342: \"INSERT.PICTURE\",\n  343: \"EDIT.TOOL\",\n  344: \"GALLERY.DOUGHNUT\",\n  350: \"CHART.TREND\",\n  352: \"PIVOT.ITEM.PROPERTIES\",\n  354: \"WORKBOOK.INSERT\",\n  355: \"OPTIONS.TRANSITION\",\n  356: \"OPTIONS.GENERAL\",\n  370: \"FILTER.ADVANCED\",\n  373: \"MAIL.ADD.MAILER\",\n  374: \"MAIL.DELETE.MAILER\",\n  375: \"MAIL.REPLY\",\n  376: \"MAIL.REPLY.ALL\",\n  377: \"MAIL.FORWARD\",\n  378: \"MAIL.NEXT.LETTER\",\n  379: \"DATA.LABEL\",\n  380: \"INSERT.TITLE\",\n  381: \"FONT.PROPERTIES\",\n  382: \"MACRO.OPTIONS\",\n  383: \"WORKBOOK.HIDE\",\n  384: \"WORKBOOK.UNHIDE\",\n  385: \"WORKBOOK.DELETE\",\n  386: \"WORKBOOK.NAME\",\n  388: \"GALLERY.CUSTOM\",\n  390: \"ADD.CHART.AUTOFORMAT\",\n  391: \"DELETE.CHART.AUTOFORMAT\",\n  392: \"CHART.ADD.DATA\",\n  393: \"AUTO.OUTLINE\",\n  394: \"TAB.ORDER\",\n  395: \"SHOW.DIALOG\",\n  396: \"SELECT.ALL\",\n  397: \"UNGROUP.SHEETS\",\n  398: \"SUBTOTAL.CREATE\",\n  399: \"SUBTOTAL.REMOVE\",\n  400: \"RENAME.OBJECT\",\n  412: \"WORKBOOK.SCROLL\",\n  413: \"WORKBOOK.NEXT\",\n  414: \"WORKBOOK.PREV\",\n  415: \"WORKBOOK.TAB.SPLIT\",\n  416: \"FULL.SCREEN\",\n  417: \"WORKBOOK.PROTECT\",\n  420: \"SCROLLBAR.PROPERTIES\",\n  421: \"PIVOT.SHOW.PAGES\",\n  422: \"TEXT.TO.COLUMNS\",\n  423: \"FORMAT.CHARTTYPE\",\n  424: \"LINK.FORMAT\",\n  425: \"TRACER.DISPLAY\",\n  430: \"TRACER.NAVIGATE\",\n  431: \"TRACER.CLEAR\",\n  432: \"TRACER.ERROR\",\n  433: \"PIVOT.FIELD.GROUP\",\n  434: \"PIVOT.FIELD.UNGROUP\",\n  435: \"CHECKBOX.PROPERTIES\",\n  436: \"LABEL.PROPERTIES\",\n  437: \"LISTBOX.PROPERTIES\",\n  438: \"EDITBOX.PROPERTIES\",\n  439: \"PIVOT.REFRESH\",\n  440: \"LINK.COMBO\",\n  441: \"OPEN.TEXT\",\n  442: \"HIDE.DIALOG\",\n  443: \"SET.DIALOG.FOCUS\",\n  444: \"ENABLE.OBJECT\",\n  445: \"PUSHBUTTON.PROPERTIES\",\n  446: \"SET.DIALOG.DEFAULT\",\n  447: \"FILTER\",\n  448: \"FILTER.SHOW.ALL\",\n  449: \"CLEAR.OUTLINE\",\n  450: \"FUNCTION.WIZARD\",\n  451: \"ADD.LIST.ITEM\",\n  452: \"SET.LIST.ITEM\",\n  453: \"REMOVE.LIST.ITEM\",\n  454: \"SELECT.LIST.ITEM\",\n  455: \"SET.CONTROL.VALUE\",\n  456: \"SAVE.COPY.AS\",\n  458: \"OPTIONS.LISTS.ADD\",\n  459: \"OPTIONS.LISTS.DELETE\",\n  460: \"SERIES.AXES\",\n  461: \"SERIES.X\",\n  462: \"SERIES.Y\",\n  463: \"ERRORBAR.X\",\n  464: \"ERRORBAR.Y\",\n  465: \"FORMAT.CHART\",\n  466: \"SERIES.ORDER\",\n  467: \"MAIL.LOGOFF\",\n  468: \"CLEAR.ROUTING.SLIP\",\n  469: \"APP.ACTIVATE.MICROSOFT\",\n  470: \"MAIL.EDIT.MAILER\",\n  471: \"ON.SHEET\",\n  472: \"STANDARD.WIDTH\",\n  473: \"SCENARIO.MERGE\",\n  474: \"SUMMARY.INFO\",\n  475: \"FIND.FILE\",\n  476: \"ACTIVE.CELL.FONT\",\n  477: \"ENABLE.TIPWIZARD\",\n  478: \"VBA.MAKE.ADDIN\",\n  480: \"INSERTDATATABLE\",\n  481: \"WORKGROUP.OPTIONS\",\n  482: \"MAIL.SEND.MAILER\",\n  485: \"AUTOCORRECT\",\n  489: \"POST.DOCUMENT\",\n  491: \"PICKLIST\",\n  493: \"VIEW.SHOW\",\n  494: \"VIEW.DEFINE\",\n  495: \"VIEW.DELETE\",\n  509: \"SHEET.BACKGROUND\",\n  510: \"INSERT.MAP.OBJECT\",\n  511: \"OPTIONS.MENONO\",\n  517: \"MSOCHECKS\",\n  518: \"NORMAL\",\n  519: \"LAYOUT\",\n  520: \"RM.PRINT.AREA\",\n  521: \"CLEAR.PRINT.AREA\",\n  522: \"ADD.PRINT.AREA\",\n  523: \"MOVE.BRK\",\n  545: \"HIDECURR.NOTE\",\n  546: \"HIDEALL.NOTES\",\n  547: \"DELETE.NOTE\",\n  548: \"TRAVERSE.NOTES\",\n  549: \"ACTIVATE.NOTES\",\n  620: \"PROTECT.REVISIONS\",\n  621: \"UNPROTECT.REVISIONS\",\n  647: \"OPTIONS.ME\",\n  653: \"WEB.PUBLISH\",\n  667: \"NEWWEBQUERY\",\n  673: \"PIVOT.TABLE.CHART\",\n  753: \"OPTIONS.SAVE\",\n  755: \"OPTIONS.SPELL\",\n  808: \"HIDEALL.INKANNOTS\"\n};\nvar Ftab = {\n  0: \"COUNT\",\n  1: \"IF\",\n  2: \"ISNA\",\n  3: \"ISERROR\",\n  4: \"SUM\",\n  5: \"AVERAGE\",\n  6: \"MIN\",\n  7: \"MAX\",\n  8: \"ROW\",\n  9: \"COLUMN\",\n  10: \"NA\",\n  11: \"NPV\",\n  12: \"STDEV\",\n  13: \"DOLLAR\",\n  14: \"FIXED\",\n  15: \"SIN\",\n  16: \"COS\",\n  17: \"TAN\",\n  18: \"ATAN\",\n  19: \"PI\",\n  20: \"SQRT\",\n  21: \"EXP\",\n  22: \"LN\",\n  23: \"LOG10\",\n  24: \"ABS\",\n  25: \"INT\",\n  26: \"SIGN\",\n  27: \"ROUND\",\n  28: \"LOOKUP\",\n  29: \"INDEX\",\n  30: \"REPT\",\n  31: \"MID\",\n  32: \"LEN\",\n  33: \"VALUE\",\n  34: \"TRUE\",\n  35: \"FALSE\",\n  36: \"AND\",\n  37: \"OR\",\n  38: \"NOT\",\n  39: \"MOD\",\n  40: \"DCOUNT\",\n  41: \"DSUM\",\n  42: \"DAVERAGE\",\n  43: \"DMIN\",\n  44: \"DMAX\",\n  45: \"DSTDEV\",\n  46: \"VAR\",\n  47: \"DVAR\",\n  48: \"TEXT\",\n  49: \"LINEST\",\n  50: \"TREND\",\n  51: \"LOGEST\",\n  52: \"GROWTH\",\n  53: \"GOTO\",\n  54: \"HALT\",\n  55: \"RETURN\",\n  56: \"PV\",\n  57: \"FV\",\n  58: \"NPER\",\n  59: \"PMT\",\n  60: \"RATE\",\n  61: \"MIRR\",\n  62: \"IRR\",\n  63: \"RAND\",\n  64: \"MATCH\",\n  65: \"DATE\",\n  66: \"TIME\",\n  67: \"DAY\",\n  68: \"MONTH\",\n  69: \"YEAR\",\n  70: \"WEEKDAY\",\n  71: \"HOUR\",\n  72: \"MINUTE\",\n  73: \"SECOND\",\n  74: \"NOW\",\n  75: \"AREAS\",\n  76: \"ROWS\",\n  77: \"COLUMNS\",\n  78: \"OFFSET\",\n  79: \"ABSREF\",\n  80: \"RELREF\",\n  81: \"ARGUMENT\",\n  82: \"SEARCH\",\n  83: \"TRANSPOSE\",\n  84: \"ERROR\",\n  85: \"STEP\",\n  86: \"TYPE\",\n  87: \"ECHO\",\n  88: \"SET.NAME\",\n  89: \"CALLER\",\n  90: \"DEREF\",\n  91: \"WINDOWS\",\n  92: \"SERIES\",\n  93: \"DOCUMENTS\",\n  94: \"ACTIVE.CELL\",\n  95: \"SELECTION\",\n  96: \"RESULT\",\n  97: \"ATAN2\",\n  98: \"ASIN\",\n  99: \"ACOS\",\n  100: \"CHOOSE\",\n  101: \"HLOOKUP\",\n  102: \"VLOOKUP\",\n  103: \"LINKS\",\n  104: \"INPUT\",\n  105: \"ISREF\",\n  106: \"GET.FORMULA\",\n  107: \"GET.NAME\",\n  108: \"SET.VALUE\",\n  109: \"LOG\",\n  110: \"EXEC\",\n  111: \"CHAR\",\n  112: \"LOWER\",\n  113: \"UPPER\",\n  114: \"PROPER\",\n  115: \"LEFT\",\n  116: \"RIGHT\",\n  117: \"EXACT\",\n  118: \"TRIM\",\n  119: \"REPLACE\",\n  120: \"SUBSTITUTE\",\n  121: \"CODE\",\n  122: \"NAMES\",\n  123: \"DIRECTORY\",\n  124: \"FIND\",\n  125: \"CELL\",\n  126: \"ISERR\",\n  127: \"ISTEXT\",\n  128: \"ISNUMBER\",\n  129: \"ISBLANK\",\n  130: \"T\",\n  131: \"N\",\n  132: \"FOPEN\",\n  133: \"FCLOSE\",\n  134: \"FSIZE\",\n  135: \"FREADLN\",\n  136: \"FREAD\",\n  137: \"FWRITELN\",\n  138: \"FWRITE\",\n  139: \"FPOS\",\n  140: \"DATEVALUE\",\n  141: \"TIMEVALUE\",\n  142: \"SLN\",\n  143: \"SYD\",\n  144: \"DDB\",\n  145: \"GET.DEF\",\n  146: \"REFTEXT\",\n  147: \"TEXTREF\",\n  148: \"INDIRECT\",\n  149: \"REGISTER\",\n  150: \"CALL\",\n  151: \"ADD.BAR\",\n  152: \"ADD.MENU\",\n  153: \"ADD.COMMAND\",\n  154: \"ENABLE.COMMAND\",\n  155: \"CHECK.COMMAND\",\n  156: \"RENAME.COMMAND\",\n  157: \"SHOW.BAR\",\n  158: \"DELETE.MENU\",\n  159: \"DELETE.COMMAND\",\n  160: \"GET.CHART.ITEM\",\n  161: \"DIALOG.BOX\",\n  162: \"CLEAN\",\n  163: \"MDETERM\",\n  164: \"MINVERSE\",\n  165: \"MMULT\",\n  166: \"FILES\",\n  167: \"IPMT\",\n  168: \"PPMT\",\n  169: \"COUNTA\",\n  170: \"CANCEL.KEY\",\n  171: \"FOR\",\n  172: \"WHILE\",\n  173: \"BREAK\",\n  174: \"NEXT\",\n  175: \"INITIATE\",\n  176: \"REQUEST\",\n  177: \"POKE\",\n  178: \"EXECUTE\",\n  179: \"TERMINATE\",\n  180: \"RESTART\",\n  181: \"HELP\",\n  182: \"GET.BAR\",\n  183: \"PRODUCT\",\n  184: \"FACT\",\n  185: \"GET.CELL\",\n  186: \"GET.WORKSPACE\",\n  187: \"GET.WINDOW\",\n  188: \"GET.DOCUMENT\",\n  189: \"DPRODUCT\",\n  190: \"ISNONTEXT\",\n  191: \"GET.NOTE\",\n  192: \"NOTE\",\n  193: \"STDEVP\",\n  194: \"VARP\",\n  195: \"DSTDEVP\",\n  196: \"DVARP\",\n  197: \"TRUNC\",\n  198: \"ISLOGICAL\",\n  199: \"DCOUNTA\",\n  200: \"DELETE.BAR\",\n  201: \"UNREGISTER\",\n  204: \"USDOLLAR\",\n  205: \"FINDB\",\n  206: \"SEARCHB\",\n  207: \"REPLACEB\",\n  208: \"LEFTB\",\n  209: \"RIGHTB\",\n  210: \"MIDB\",\n  211: \"LENB\",\n  212: \"ROUNDUP\",\n  213: \"ROUNDDOWN\",\n  214: \"ASC\",\n  215: \"DBCS\",\n  216: \"RANK\",\n  219: \"ADDRESS\",\n  220: \"DAYS360\",\n  221: \"TODAY\",\n  222: \"VDB\",\n  223: \"ELSE\",\n  224: \"ELSE.IF\",\n  225: \"END.IF\",\n  226: \"FOR.CELL\",\n  227: \"MEDIAN\",\n  228: \"SUMPRODUCT\",\n  229: \"SINH\",\n  230: \"COSH\",\n  231: \"TANH\",\n  232: \"ASINH\",\n  233: \"ACOSH\",\n  234: \"ATANH\",\n  235: \"DGET\",\n  236: \"CREATE.OBJECT\",\n  237: \"VOLATILE\",\n  238: \"LAST.ERROR\",\n  239: \"CUSTOM.UNDO\",\n  240: \"CUSTOM.REPEAT\",\n  241: \"FORMULA.CONVERT\",\n  242: \"GET.LINK.INFO\",\n  243: \"TEXT.BOX\",\n  244: \"INFO\",\n  245: \"GROUP\",\n  246: \"GET.OBJECT\",\n  247: \"DB\",\n  248: \"PAUSE\",\n  251: \"RESUME\",\n  252: \"FREQUENCY\",\n  253: \"ADD.TOOLBAR\",\n  254: \"DELETE.TOOLBAR\",\n  255: \"User\",\n  256: \"RESET.TOOLBAR\",\n  257: \"EVALUATE\",\n  258: \"GET.TOOLBAR\",\n  259: \"GET.TOOL\",\n  260: \"SPELLING.CHECK\",\n  261: \"ERROR.TYPE\",\n  262: \"APP.TITLE\",\n  263: \"WINDOW.TITLE\",\n  264: \"SAVE.TOOLBAR\",\n  265: \"ENABLE.TOOL\",\n  266: \"PRESS.TOOL\",\n  267: \"REGISTER.ID\",\n  268: \"GET.WORKBOOK\",\n  269: \"AVEDEV\",\n  270: \"BETADIST\",\n  271: \"GAMMALN\",\n  272: \"BETAINV\",\n  273: \"BINOMDIST\",\n  274: \"CHIDIST\",\n  275: \"CHIINV\",\n  276: \"COMBIN\",\n  277: \"CONFIDENCE\",\n  278: \"CRITBINOM\",\n  279: \"EVEN\",\n  280: \"EXPONDIST\",\n  281: \"FDIST\",\n  282: \"FINV\",\n  283: \"FISHER\",\n  284: \"FISHERINV\",\n  285: \"FLOOR\",\n  286: \"GAMMADIST\",\n  287: \"GAMMAINV\",\n  288: \"CEILING\",\n  289: \"HYPGEOMDIST\",\n  290: \"LOGNORMDIST\",\n  291: \"LOGINV\",\n  292: \"NEGBINOMDIST\",\n  293: \"NORMDIST\",\n  294: \"NORMSDIST\",\n  295: \"NORMINV\",\n  296: \"NORMSINV\",\n  297: \"STANDARDIZE\",\n  298: \"ODD\",\n  299: \"PERMUT\",\n  300: \"POISSON\",\n  301: \"TDIST\",\n  302: \"WEIBULL\",\n  303: \"SUMXMY2\",\n  304: \"SUMX2MY2\",\n  305: \"SUMX2PY2\",\n  306: \"CHITEST\",\n  307: \"CORREL\",\n  308: \"COVAR\",\n  309: \"FORECAST\",\n  310: \"FTEST\",\n  311: \"INTERCEPT\",\n  312: \"PEARSON\",\n  313: \"RSQ\",\n  314: \"STEYX\",\n  315: \"SLOPE\",\n  316: \"TTEST\",\n  317: \"PROB\",\n  318: \"DEVSQ\",\n  319: \"GEOMEAN\",\n  320: \"HARMEAN\",\n  321: \"SUMSQ\",\n  322: \"KURT\",\n  323: \"SKEW\",\n  324: \"ZTEST\",\n  325: \"LARGE\",\n  326: \"SMALL\",\n  327: \"QUARTILE\",\n  328: \"PERCENTILE\",\n  329: \"PERCENTRANK\",\n  330: \"MODE\",\n  331: \"TRIMMEAN\",\n  332: \"TINV\",\n  334: \"MOVIE.COMMAND\",\n  335: \"GET.MOVIE\",\n  336: \"CONCATENATE\",\n  337: \"POWER\",\n  338: \"PIVOT.ADD.DATA\",\n  339: \"GET.PIVOT.TABLE\",\n  340: \"GET.PIVOT.FIELD\",\n  341: \"GET.PIVOT.ITEM\",\n  342: \"RADIANS\",\n  343: \"DEGREES\",\n  344: \"SUBTOTAL\",\n  345: \"SUMIF\",\n  346: \"COUNTIF\",\n  347: \"COUNTBLANK\",\n  348: \"SCENARIO.GET\",\n  349: \"OPTIONS.LISTS.GET\",\n  350: \"ISPMT\",\n  351: \"DATEDIF\",\n  352: \"DATESTRING\",\n  353: \"NUMBERSTRING\",\n  354: \"ROMAN\",\n  355: \"OPEN.DIALOG\",\n  356: \"SAVE.DIALOG\",\n  357: \"VIEW.GET\",\n  358: \"GETPIVOTDATA\",\n  359: \"HYPERLINK\",\n  360: \"PHONETIC\",\n  361: \"AVERAGEA\",\n  362: \"MAXA\",\n  363: \"MINA\",\n  364: \"STDEVPA\",\n  365: \"VARPA\",\n  366: \"STDEVA\",\n  367: \"VARA\",\n  368: \"BAHTTEXT\",\n  369: \"THAIDAYOFWEEK\",\n  370: \"THAIDIGIT\",\n  371: \"THAIMONTHOFYEAR\",\n  372: \"THAINUMSOUND\",\n  373: \"THAINUMSTRING\",\n  374: \"THAISTRINGLENGTH\",\n  375: \"ISTHAIDIGIT\",\n  376: \"ROUNDBAHTDOWN\",\n  377: \"ROUNDBAHTUP\",\n  378: \"THAIYEAR\",\n  379: \"RTD\",\n  380: \"CUBEVALUE\",\n  381: \"CUBEMEMBER\",\n  382: \"CUBEMEMBERPROPERTY\",\n  383: \"CUBERANKEDMEMBER\",\n  384: \"HEX2BIN\",\n  385: \"HEX2DEC\",\n  386: \"HEX2OCT\",\n  387: \"DEC2BIN\",\n  388: \"DEC2HEX\",\n  389: \"DEC2OCT\",\n  390: \"OCT2BIN\",\n  391: \"OCT2HEX\",\n  392: \"OCT2DEC\",\n  393: \"BIN2DEC\",\n  394: \"BIN2OCT\",\n  395: \"BIN2HEX\",\n  396: \"IMSUB\",\n  397: \"IMDIV\",\n  398: \"IMPOWER\",\n  399: \"IMABS\",\n  400: \"IMSQRT\",\n  401: \"IMLN\",\n  402: \"IMLOG2\",\n  403: \"IMLOG10\",\n  404: \"IMSIN\",\n  405: \"IMCOS\",\n  406: \"IMEXP\",\n  407: \"IMARGUMENT\",\n  408: \"IMCONJUGATE\",\n  409: \"IMAGINARY\",\n  410: \"IMREAL\",\n  411: \"COMPLEX\",\n  412: \"IMSUM\",\n  413: \"IMPRODUCT\",\n  414: \"SERIESSUM\",\n  415: \"FACTDOUBLE\",\n  416: \"SQRTPI\",\n  417: \"QUOTIENT\",\n  418: \"DELTA\",\n  419: \"GESTEP\",\n  420: \"ISEVEN\",\n  421: \"ISODD\",\n  422: \"MROUND\",\n  423: \"ERF\",\n  424: \"ERFC\",\n  425: \"BESSELJ\",\n  426: \"BESSELK\",\n  427: \"BESSELY\",\n  428: \"BESSELI\",\n  429: \"XIRR\",\n  430: \"XNPV\",\n  431: \"PRICEMAT\",\n  432: \"YIELDMAT\",\n  433: \"INTRATE\",\n  434: \"RECEIVED\",\n  435: \"DISC\",\n  436: \"PRICEDISC\",\n  437: \"YIELDDISC\",\n  438: \"TBILLEQ\",\n  439: \"TBILLPRICE\",\n  440: \"TBILLYIELD\",\n  441: \"PRICE\",\n  442: \"YIELD\",\n  443: \"DOLLARDE\",\n  444: \"DOLLARFR\",\n  445: \"NOMINAL\",\n  446: \"EFFECT\",\n  447: \"CUMPRINC\",\n  448: \"CUMIPMT\",\n  449: \"EDATE\",\n  450: \"EOMONTH\",\n  451: \"YEARFRAC\",\n  452: \"COUPDAYBS\",\n  453: \"COUPDAYS\",\n  454: \"COUPDAYSNC\",\n  455: \"COUPNCD\",\n  456: \"COUPNUM\",\n  457: \"COUPPCD\",\n  458: \"DURATION\",\n  459: \"MDURATION\",\n  460: \"ODDLPRICE\",\n  461: \"ODDLYIELD\",\n  462: \"ODDFPRICE\",\n  463: \"ODDFYIELD\",\n  464: \"RANDBETWEEN\",\n  465: \"WEEKNUM\",\n  466: \"AMORDEGRC\",\n  467: \"AMORLINC\",\n  468: \"CONVERT\",\n  724: \"SHEETJS\",\n  469: \"ACCRINT\",\n  470: \"ACCRINTM\",\n  471: \"WORKDAY\",\n  472: \"NETWORKDAYS\",\n  473: \"GCD\",\n  474: \"MULTINOMIAL\",\n  475: \"LCM\",\n  476: \"FVSCHEDULE\",\n  477: \"CUBEKPIMEMBER\",\n  478: \"CUBESET\",\n  479: \"CUBESETCOUNT\",\n  480: \"IFERROR\",\n  481: \"COUNTIFS\",\n  482: \"SUMIFS\",\n  483: \"AVERAGEIF\",\n  484: \"AVERAGEIFS\"\n};\nvar FtabArgc = {\n  2: 1,\n  3: 1,\n  10: 0,\n  15: 1,\n  16: 1,\n  17: 1,\n  18: 1,\n  19: 0,\n  20: 1,\n  21: 1,\n  22: 1,\n  23: 1,\n  24: 1,\n  25: 1,\n  26: 1,\n  27: 2,\n  30: 2,\n  31: 3,\n  32: 1,\n  33: 1,\n  34: 0,\n  35: 0,\n  38: 1,\n  39: 2,\n  40: 3,\n  41: 3,\n  42: 3,\n  43: 3,\n  44: 3,\n  45: 3,\n  47: 3,\n  48: 2,\n  53: 1,\n  61: 3,\n  63: 0,\n  65: 3,\n  66: 3,\n  67: 1,\n  68: 1,\n  69: 1,\n  70: 1,\n  71: 1,\n  72: 1,\n  73: 1,\n  74: 0,\n  75: 1,\n  76: 1,\n  77: 1,\n  79: 2,\n  80: 2,\n  83: 1,\n  85: 0,\n  86: 1,\n  89: 0,\n  90: 1,\n  94: 0,\n  95: 0,\n  97: 2,\n  98: 1,\n  99: 1,\n  101: 3,\n  102: 3,\n  105: 1,\n  106: 1,\n  108: 2,\n  111: 1,\n  112: 1,\n  113: 1,\n  114: 1,\n  117: 2,\n  118: 1,\n  119: 4,\n  121: 1,\n  126: 1,\n  127: 1,\n  128: 1,\n  129: 1,\n  130: 1,\n  131: 1,\n  133: 1,\n  134: 1,\n  135: 1,\n  136: 2,\n  137: 2,\n  138: 2,\n  140: 1,\n  141: 1,\n  142: 3,\n  143: 4,\n  144: 4,\n  161: 1,\n  162: 1,\n  163: 1,\n  164: 1,\n  165: 2,\n  172: 1,\n  175: 2,\n  176: 2,\n  177: 3,\n  178: 2,\n  179: 1,\n  184: 1,\n  186: 1,\n  189: 3,\n  190: 1,\n  195: 3,\n  196: 3,\n  197: 1,\n  198: 1,\n  199: 3,\n  201: 1,\n  207: 4,\n  210: 3,\n  211: 1,\n  212: 2,\n  213: 2,\n  214: 1,\n  215: 1,\n  225: 0,\n  229: 1,\n  230: 1,\n  231: 1,\n  232: 1,\n  233: 1,\n  234: 1,\n  235: 3,\n  244: 1,\n  247: 4,\n  252: 2,\n  257: 1,\n  261: 1,\n  271: 1,\n  273: 4,\n  274: 2,\n  275: 2,\n  276: 2,\n  277: 3,\n  278: 3,\n  279: 1,\n  280: 3,\n  281: 3,\n  282: 3,\n  283: 1,\n  284: 1,\n  285: 2,\n  286: 4,\n  287: 3,\n  288: 2,\n  289: 4,\n  290: 3,\n  291: 3,\n  292: 3,\n  293: 4,\n  294: 1,\n  295: 3,\n  296: 1,\n  297: 3,\n  298: 1,\n  299: 2,\n  300: 3,\n  301: 3,\n  302: 4,\n  303: 2,\n  304: 2,\n  305: 2,\n  306: 2,\n  307: 2,\n  308: 2,\n  309: 3,\n  310: 2,\n  311: 2,\n  312: 2,\n  313: 2,\n  314: 2,\n  315: 2,\n  316: 4,\n  325: 2,\n  326: 2,\n  327: 2,\n  328: 2,\n  331: 2,\n  332: 2,\n  337: 2,\n  342: 1,\n  343: 1,\n  346: 2,\n  347: 1,\n  350: 4,\n  351: 3,\n  352: 1,\n  353: 2,\n  360: 1,\n  368: 1,\n  369: 1,\n  370: 1,\n  371: 1,\n  372: 1,\n  373: 1,\n  374: 1,\n  375: 1,\n  376: 1,\n  377: 1,\n  378: 1,\n  382: 3,\n  385: 1,\n  392: 1,\n  393: 1,\n  396: 2,\n  397: 2,\n  398: 2,\n  399: 1,\n  400: 1,\n  401: 1,\n  402: 1,\n  403: 1,\n  404: 1,\n  405: 1,\n  406: 1,\n  407: 1,\n  408: 1,\n  409: 1,\n  410: 1,\n  414: 4,\n  415: 1,\n  416: 1,\n  417: 2,\n  420: 1,\n  421: 1,\n  422: 2,\n  424: 1,\n  425: 2,\n  426: 2,\n  427: 2,\n  428: 2,\n  430: 3,\n  438: 3,\n  439: 3,\n  440: 3,\n  443: 2,\n  444: 2,\n  445: 2,\n  446: 2,\n  447: 6,\n  448: 6,\n  449: 2,\n  450: 2,\n  464: 2,\n  468: 3,\n  476: 2,\n  479: 1,\n  480: 2,\n  65535: 0\n};\n/* Part 3 TODO: actually parse formulae */\nfunction ods_to_csf_formula(f/*:string*/)/*:string*/ {\n\tif(f.slice(0,3) == \"of:\") f = f.slice(3);\n\t/* 5.2 Basic Expressions */\n\tif(f.charCodeAt(0) == 61) {\n\t\tf = f.slice(1);\n\t\tif(f.charCodeAt(0) == 61) f = f.slice(1);\n\t}\n\tf = f.replace(/COM\\.MICROSOFT\\./g, \"\");\n\t/* Part 3 Section 5.8 References */\n\tf = f.replace(/\\[((?:\\.[A-Z]+[0-9]+)(?::\\.[A-Z]+[0-9]+)?)\\]/g, function($$, $1) { return $1.replace(/\\./g,\"\"); });\n\t/* TODO: something other than this */\n\tf = f.replace(/\\[.(#[A-Z]*[?!])\\]/g, \"$1\");\n\treturn f.replace(/[;~]/g,\",\").replace(/\\|/g,\";\");\n}\n\nfunction csf_to_ods_formula(f/*:string*/)/*:string*/ {\n\tvar o = \"of:=\" + f.replace(crefregex, \"$1[.$2$3$4$5]\").replace(/\\]:\\[/g,\":\");\n\t/* TODO: something other than this */\n\treturn o.replace(/;/g, \"|\").replace(/,/g,\";\");\n}\n\nfunction ods_to_csf_3D(r/*:string*/)/*:[string, string]*/ {\n\tvar a = r.split(\":\");\n\tvar s = a[0].split(\".\")[0];\n\treturn [s, a[0].split(\".\")[1] + (a.length > 1 ? (\":\" + (a[1].split(\".\")[1] || a[1].split(\".\")[0])) : \"\")];\n}\n\nfunction csf_to_ods_3D(r/*:string*/)/*:string*/ {\n\treturn r.replace(/\\./,\"!\");\n}\n\nvar strs = {}; // shared strings\nvar _ssfopts = {}; // spreadsheet formatting options\n\n\n/*global Map */\nvar browser_has_Map = typeof Map !== 'undefined';\n\nfunction get_sst_id(sst/*:SST*/, str/*:string*/, rev)/*:number*/ {\n\tvar i = 0, len = sst.length;\n\tif(rev) {\n\t\tif(browser_has_Map ? rev.has(str) : Object.prototype.hasOwnProperty.call(rev, str)) {\n\t\t\tvar revarr = browser_has_Map ? rev.get(str) : rev[str];\n\t\t\tfor(; i < revarr.length; ++i) {\n\t\t\t\tif(sst[revarr[i]].t === str) { sst.Count ++; return revarr[i]; }\n\t\t\t}\n\t\t}\n\t} else for(; i < len; ++i) {\n\t\tif(sst[i].t === str) { sst.Count ++; return i; }\n\t}\n\tsst[len] = ({t:str}/*:any*/); sst.Count ++; sst.Unique ++;\n\tif(rev) {\n\t\tif(browser_has_Map) {\n\t\t\tif(!rev.has(str)) rev.set(str, []);\n\t\t\trev.get(str).push(len);\n\t\t} else {\n\t\t\tif(!Object.prototype.hasOwnProperty.call(rev, str)) rev[str] = [];\n\t\t\trev[str].push(len);\n\t\t}\n\t}\n\treturn len;\n}\n\nfunction col_obj_w(C/*:number*/, col) {\n\tvar p = ({min:C+1,max:C+1}/*:any*/);\n\t/* wch (chars), wpx (pixels) */\n\tvar wch = -1;\n\tif(col.MDW) MDW = col.MDW;\n\tif(col.width != null) p.customWidth = 1;\n\telse if(col.wpx != null) wch = px2char(col.wpx);\n\telse if(col.wch != null) wch = col.wch;\n\tif(wch > -1) { p.width = char2width(wch); p.customWidth = 1; }\n\telse if(col.width != null) p.width = col.width;\n\tif(col.hidden) p.hidden = true;\n\tif(col.level != null) { p.outlineLevel = p.level = col.level; }\n\treturn p;\n}\n\nfunction default_margins(margins/*:Margins*/, mode/*:?string*/) {\n\tif(!margins) return;\n\tvar defs = [0.7, 0.7, 0.75, 0.75, 0.3, 0.3];\n\tif(mode == 'xlml') defs = [1, 1, 1, 1, 0.5, 0.5];\n\tif(margins.left   == null) margins.left   = defs[0];\n\tif(margins.right  == null) margins.right  = defs[1];\n\tif(margins.top    == null) margins.top    = defs[2];\n\tif(margins.bottom == null) margins.bottom = defs[3];\n\tif(margins.header == null) margins.header = defs[4];\n\tif(margins.footer == null) margins.footer = defs[5];\n}\n\nfunction get_cell_style(styles/*:Array<any>*/, cell/*:Cell*/, opts) {\n\tvar z = opts.revssf[cell.z != null ? cell.z : \"General\"];\n\tvar i = 0x3c, len = styles.length;\n\tif(z == null && opts.ssf) {\n\t\tfor(; i < 0x188; ++i) if(opts.ssf[i] == null) {\n\t\t\tSSF_load(cell.z, i);\n\t\t\t// $FlowIgnore\n\t\t\topts.ssf[i] = cell.z;\n\t\t\topts.revssf[cell.z] = z = i;\n\t\t\tbreak;\n\t\t}\n\t}\n\tfor(i = 0; i != len; ++i) if(styles[i].numFmtId === z) return i;\n\tstyles[len] = {\n\t\tnumFmtId:z,\n\t\tfontId:0,\n\t\tfillId:0,\n\t\tborderId:0,\n\t\txfId:0,\n\t\tapplyNumberFormat:1\n\t};\n\treturn len;\n}\n\nfunction safe_format(p/*:Cell*/, fmtid/*:number*/, fillid/*:?number*/, opts, themes, styles) {\n\ttry {\n\t\tif(opts.cellNF) p.z = table_fmt[fmtid];\n\t} catch(e) { if(opts.WTF) throw e; }\n\tif(p.t === 'z' && !opts.cellStyles) return;\n\tif(p.t === 'd' && typeof p.v === 'string') p.v = parseDate(p.v);\n\tif((!opts || opts.cellText !== false) && p.t !== 'z') try {\n\t\tif(table_fmt[fmtid] == null) SSF_load(SSFImplicit[fmtid] || \"General\", fmtid);\n\t\tif(p.t === 'e') p.w = p.w || BErr[p.v];\n\t\telse if(fmtid === 0) {\n\t\t\tif(p.t === 'n') {\n\t\t\t\tif((p.v|0) === p.v) p.w = p.v.toString(10);\n\t\t\t\telse p.w = SSF_general_num(p.v);\n\t\t\t}\n\t\t\telse if(p.t === 'd') {\n\t\t\t\tvar dd = datenum(p.v);\n\t\t\t\tif((dd|0) === dd) p.w = dd.toString(10);\n\t\t\t\telse p.w = SSF_general_num(dd);\n\t\t\t}\n\t\t\telse if(p.v === undefined) return \"\";\n\t\t\telse p.w = SSF_general(p.v,_ssfopts);\n\t\t}\n\t\telse if(p.t === 'd') p.w = SSF_format(fmtid,datenum(p.v),_ssfopts);\n\t\telse p.w = SSF_format(fmtid,p.v,_ssfopts);\n\t} catch(e) { if(opts.WTF) throw e; }\n\tif(!opts.cellStyles) return;\n\tif(fillid != null) try {\n\t\tp.s = styles.Fills[fillid];\n\t\tif (p.s.fgColor && p.s.fgColor.theme && !p.s.fgColor.rgb) {\n\t\t\tp.s.fgColor.rgb = rgb_tint(themes.themeElements.clrScheme[p.s.fgColor.theme].rgb, p.s.fgColor.tint || 0);\n\t\t\tif(opts.WTF) p.s.fgColor.raw_rgb = themes.themeElements.clrScheme[p.s.fgColor.theme].rgb;\n\t\t}\n\t\tif (p.s.bgColor && p.s.bgColor.theme) {\n\t\t\tp.s.bgColor.rgb = rgb_tint(themes.themeElements.clrScheme[p.s.bgColor.theme].rgb, p.s.bgColor.tint || 0);\n\t\t\tif(opts.WTF) p.s.bgColor.raw_rgb = themes.themeElements.clrScheme[p.s.bgColor.theme].rgb;\n\t\t}\n\t} catch(e) { if(opts.WTF && styles.Fills) throw e; }\n}\n\nfunction check_ws(ws/*:Worksheet*/, sname/*:string*/, i/*:number*/) {\n\tif(ws && ws['!ref']) {\n\t\tvar range = safe_decode_range(ws['!ref']);\n\t\tif(range.e.c < range.s.c || range.e.r < range.s.r) throw new Error(\"Bad range (\" + i + \"): \" + ws['!ref']);\n\t}\n}\nfunction parse_ws_xml_dim(ws/*:Worksheet*/, s/*:string*/) {\n\tvar d = safe_decode_range(s);\n\tif(d.s.r<=d.e.r && d.s.c<=d.e.c && d.s.r>=0 && d.s.c>=0) ws[\"!ref\"] = encode_range(d);\n}\nvar mergecregex = /<(?:\\w:)?mergeCell ref=\"[A-Z0-9:]+\"\\s*[\\/]?>/g;\nvar sheetdataregex = /<(?:\\w+:)?sheetData[^>]*>([\\s\\S]*)<\\/(?:\\w+:)?sheetData>/;\nvar hlinkregex = /<(?:\\w:)?hyperlink [^>]*>/mg;\nvar dimregex = /\"(\\w*:\\w*)\"/;\nvar colregex = /<(?:\\w:)?col\\b[^>]*[\\/]?>/g;\nvar afregex = /<(?:\\w:)?autoFilter[^>]*([\\/]|>([\\s\\S]*)<\\/(?:\\w:)?autoFilter)>/g;\nvar marginregex= /<(?:\\w:)?pageMargins[^>]*\\/>/g;\nvar sheetprregex = /<(?:\\w:)?sheetPr\\b(?:[^>a-z][^>]*)?\\/>/;\nvar sheetprregex2= /<(?:\\w:)?sheetPr[^>]*(?:[\\/]|>([\\s\\S]*)<\\/(?:\\w:)?sheetPr)>/;\nvar svsregex = /<(?:\\w:)?sheetViews[^>]*(?:[\\/]|>([\\s\\S]*)<\\/(?:\\w:)?sheetViews)>/;\n\n/* 18.3 Worksheets */\nfunction parse_ws_xml(data/*:?string*/, opts, idx/*:number*/, rels, wb/*:WBWBProps*/, themes, styles)/*:Worksheet*/ {\n\tif(!data) return data;\n\tif(!rels) rels = {'!id':{}};\n\tif(DENSE != null && opts.dense == null) opts.dense = DENSE;\n\n\t/* 18.3.1.99 worksheet CT_Worksheet */\n\tvar s = opts.dense ? ([]/*:any*/) : ({}/*:any*/);\n\tvar refguess/*:Range*/ = ({s: {r:2000000, c:2000000}, e: {r:0, c:0} }/*:any*/);\n\n\tvar data1 = \"\", data2 = \"\";\n\tvar mtch/*:?any*/ = data.match(sheetdataregex);\n\tif(mtch) {\n\t\tdata1 = data.slice(0, mtch.index);\n\t\tdata2 = data.slice(mtch.index + mtch[0].length);\n\t} else data1 = data2 = data;\n\n\t/* 18.3.1.82 sheetPr CT_SheetPr */\n\tvar sheetPr = data1.match(sheetprregex);\n\tif(sheetPr) parse_ws_xml_sheetpr(sheetPr[0], s, wb, idx);\n\telse if((sheetPr = data1.match(sheetprregex2))) parse_ws_xml_sheetpr2(sheetPr[0], sheetPr[1]||\"\", s, wb, idx, styles, themes);\n\n\t/* 18.3.1.35 dimension CT_SheetDimension */\n\tvar ridx = (data1.match(/<(?:\\w*:)?dimension/)||{index:-1}).index;\n\tif(ridx > 0) {\n\t\tvar ref = data1.slice(ridx,ridx+50).match(dimregex);\n\t\tif(ref) parse_ws_xml_dim(s, ref[1]);\n\t}\n\n\t/* 18.3.1.88 sheetViews CT_SheetViews */\n\tvar svs = data1.match(svsregex);\n\tif(svs && svs[1]) parse_ws_xml_sheetviews(svs[1], wb);\n\n\t/* 18.3.1.17 cols CT_Cols */\n\tvar columns/*:Array<ColInfo>*/ = [];\n\tif(opts.cellStyles) {\n\t\t/* 18.3.1.13 col CT_Col */\n\t\tvar cols = data1.match(colregex);\n\t\tif(cols) parse_ws_xml_cols(columns, cols);\n\t}\n\n\t/* 18.3.1.80 sheetData CT_SheetData ? */\n\tif(mtch) parse_ws_xml_data(mtch[1], s, opts, refguess, themes, styles);\n\n\t/* 18.3.1.2  autoFilter CT_AutoFilter */\n\tvar afilter = data2.match(afregex);\n\tif(afilter) s['!autofilter'] = parse_ws_xml_autofilter(afilter[0]);\n\n\t/* 18.3.1.55 mergeCells CT_MergeCells */\n\tvar merges/*:Array<Range>*/ = [];\n\tvar _merge = data2.match(mergecregex);\n\tif(_merge) for(ridx = 0; ridx != _merge.length; ++ridx)\n\t\tmerges[ridx] = safe_decode_range(_merge[ridx].slice(_merge[ridx].indexOf(\"\\\"\")+1));\n\n\t/* 18.3.1.48 hyperlinks CT_Hyperlinks */\n\tvar hlink = data2.match(hlinkregex);\n\tif(hlink) parse_ws_xml_hlinks(s, hlink, rels);\n\n\t/* 18.3.1.62 pageMargins CT_PageMargins */\n\tvar margins = data2.match(marginregex);\n\tif(margins) s['!margins'] = parse_ws_xml_margins(parsexmltag(margins[0]));\n\n\tif(!s[\"!ref\"] && refguess.e.c >= refguess.s.c && refguess.e.r >= refguess.s.r) s[\"!ref\"] = encode_range(refguess);\n\tif(opts.sheetRows > 0 && s[\"!ref\"]) {\n\t\tvar tmpref = safe_decode_range(s[\"!ref\"]);\n\t\tif(opts.sheetRows <= +tmpref.e.r) {\n\t\t\ttmpref.e.r = opts.sheetRows - 1;\n\t\t\tif(tmpref.e.r > refguess.e.r) tmpref.e.r = refguess.e.r;\n\t\t\tif(tmpref.e.r < tmpref.s.r) tmpref.s.r = tmpref.e.r;\n\t\t\tif(tmpref.e.c > refguess.e.c) tmpref.e.c = refguess.e.c;\n\t\t\tif(tmpref.e.c < tmpref.s.c) tmpref.s.c = tmpref.e.c;\n\t\t\ts[\"!fullref\"] = s[\"!ref\"];\n\t\t\ts[\"!ref\"] = encode_range(tmpref);\n\t\t}\n\t}\n\tif(columns.length > 0) s[\"!cols\"] = columns;\n\tif(merges.length > 0) s[\"!merges\"] = merges;\n\treturn s;\n}\n\nfunction write_ws_xml_merges(merges/*:Array<Range>*/)/*:string*/ {\n\tif(merges.length === 0) return \"\";\n\tvar o = '<mergeCells count=\"' + merges.length + '\">';\n\tfor(var i = 0; i != merges.length; ++i) o += '<mergeCell ref=\"' + encode_range(merges[i]) + '\"/>';\n\treturn o + '</mergeCells>';\n}\n\n/* 18.3.1.82-3 sheetPr CT_ChartsheetPr / CT_SheetPr */\nfunction parse_ws_xml_sheetpr(sheetPr/*:string*/, s, wb/*:WBWBProps*/, idx/*:number*/) {\n\tvar data = parsexmltag(sheetPr);\n\tif(!wb.Sheets[idx]) wb.Sheets[idx] = {};\n\tif(data.codeName) wb.Sheets[idx].CodeName = unescapexml(utf8read(data.codeName));\n}\nfunction parse_ws_xml_sheetpr2(sheetPr/*:string*/, body/*:string*/, s, wb/*:WBWBProps*/, idx/*:number*/) {\n\tparse_ws_xml_sheetpr(sheetPr.slice(0, sheetPr.indexOf(\">\")), s, wb, idx);\n}\nfunction write_ws_xml_sheetpr(ws, wb, idx, opts, o) {\n\tvar needed = false;\n\tvar props = {}, payload = null;\n\tif(opts.bookType !== 'xlsx' && wb.vbaraw) {\n\t\tvar cname = wb.SheetNames[idx];\n\t\ttry { if(wb.Workbook) cname = wb.Workbook.Sheets[idx].CodeName || cname; } catch(e) {}\n\t\tneeded = true;\n\t\tprops.codeName = utf8write(escapexml(cname));\n\t}\n\n\tif(ws && ws[\"!outline\"]) {\n\t\tvar outlineprops = {summaryBelow:1, summaryRight:1};\n\t\tif(ws[\"!outline\"].above) outlineprops.summaryBelow = 0;\n\t\tif(ws[\"!outline\"].left) outlineprops.summaryRight = 0;\n\t\tpayload = (payload||\"\") + writextag('outlinePr', null, outlineprops);\n\t}\n\n\tif(!needed && !payload) return;\n\to[o.length] = (writextag('sheetPr', payload, props));\n}\n\n/* 18.3.1.85 sheetProtection CT_SheetProtection */\nvar sheetprot_deffalse = [\"objects\", \"scenarios\", \"selectLockedCells\", \"selectUnlockedCells\"];\nvar sheetprot_deftrue = [\n\t\"formatColumns\", \"formatRows\", \"formatCells\",\n\t\"insertColumns\", \"insertRows\", \"insertHyperlinks\",\n\t\"deleteColumns\", \"deleteRows\",\n\t\"sort\", \"autoFilter\", \"pivotTables\"\n];\nfunction write_ws_xml_protection(sp)/*:string*/ {\n\t// algorithmName, hashValue, saltValue, spinCount\n\tvar o = ({sheet:1}/*:any*/);\n\tsheetprot_deffalse.forEach(function(n) { if(sp[n] != null && sp[n]) o[n] = \"1\"; });\n\tsheetprot_deftrue.forEach(function(n) { if(sp[n] != null && !sp[n]) o[n] = \"0\"; });\n\t/* TODO: algorithm */\n\tif(sp.password) o.password = crypto_CreatePasswordVerifier_Method1(sp.password).toString(16).toUpperCase();\n\treturn writextag('sheetProtection', null, o);\n}\n\nfunction parse_ws_xml_hlinks(s, data/*:Array<string>*/, rels) {\n\tvar dense = Array.isArray(s);\n\tfor(var i = 0; i != data.length; ++i) {\n\t\tvar val = parsexmltag(utf8read(data[i]), true);\n\t\tif(!val.ref) return;\n\t\tvar rel = ((rels || {})['!id']||[])[val.id];\n\t\tif(rel) {\n\t\t\tval.Target = rel.Target;\n\t\t\tif(val.location) val.Target += \"#\"+unescapexml(val.location);\n\t\t} else {\n\t\t\tval.Target = \"#\" + unescapexml(val.location);\n\t\t\trel = {Target: val.Target, TargetMode: 'Internal'};\n\t\t}\n\t\tval.Rel = rel;\n\t\tif(val.tooltip) { val.Tooltip = val.tooltip; delete val.tooltip; }\n\t\tvar rng = safe_decode_range(val.ref);\n\t\tfor(var R=rng.s.r;R<=rng.e.r;++R) for(var C=rng.s.c;C<=rng.e.c;++C) {\n\t\t\tvar addr = encode_cell({c:C,r:R});\n\t\t\tif(dense) {\n\t\t\t\tif(!s[R]) s[R] = [];\n\t\t\t\tif(!s[R][C]) s[R][C] = {t:\"z\",v:undefined};\n\t\t\t\ts[R][C].l = val;\n\t\t\t} else {\n\t\t\t\tif(!s[addr]) s[addr] = {t:\"z\",v:undefined};\n\t\t\t\ts[addr].l = val;\n\t\t\t}\n\t\t}\n\t}\n}\n\nfunction parse_ws_xml_margins(margin) {\n\tvar o = {};\n\t[\"left\", \"right\", \"top\", \"bottom\", \"header\", \"footer\"].forEach(function(k) {\n\t\tif(margin[k]) o[k] = parseFloat(margin[k]);\n\t});\n\treturn o;\n}\nfunction write_ws_xml_margins(margin)/*:string*/ {\n\tdefault_margins(margin);\n\treturn writextag('pageMargins', null, margin);\n}\n\nfunction parse_ws_xml_cols(columns, cols) {\n\tvar seencol = false;\n\tfor(var coli = 0; coli != cols.length; ++coli) {\n\t\tvar coll = parsexmltag(cols[coli], true);\n\t\tif(coll.hidden) coll.hidden = parsexmlbool(coll.hidden);\n\t\tvar colm=parseInt(coll.min, 10)-1, colM=parseInt(coll.max,10)-1;\n\t\tif(coll.outlineLevel) coll.level = (+coll.outlineLevel || 0);\n\t\tdelete coll.min; delete coll.max; coll.width = +coll.width;\n\t\tif(!seencol && coll.width) { seencol = true; find_mdw_colw(coll.width); }\n\t\tprocess_col(coll);\n\t\twhile(colm <= colM) columns[colm++] = dup(coll);\n\t}\n}\nfunction write_ws_xml_cols(ws, cols)/*:string*/ {\n\tvar o = [\"<cols>\"], col;\n\tfor(var i = 0; i != cols.length; ++i) {\n\t\tif(!(col = cols[i])) continue;\n\t\to[o.length] = (writextag('col', null, col_obj_w(i, col)));\n\t}\n\to[o.length] = \"</cols>\";\n\treturn o.join(\"\");\n}\n\nfunction parse_ws_xml_autofilter(data/*:string*/) {\n\tvar o = { ref: (data.match(/ref=\"([^\"]*)\"/)||[])[1]};\n\treturn o;\n}\nfunction write_ws_xml_autofilter(data, ws, wb, idx)/*:string*/ {\n\tvar ref = typeof data.ref == \"string\" ? data.ref : encode_range(data.ref);\n\tif(!wb.Workbook) wb.Workbook = ({Sheets:[]}/*:any*/);\n\tif(!wb.Workbook.Names) wb.Workbook.Names = [];\n\tvar names/*: Array<any> */ = wb.Workbook.Names;\n\tvar range = decode_range(ref);\n\tif(range.s.r == range.e.r) { range.e.r = decode_range(ws[\"!ref\"]).e.r; ref = encode_range(range); }\n\tfor(var i = 0; i < names.length; ++i) {\n\t\tvar name = names[i];\n\t\tif(name.Name != '_xlnm._FilterDatabase') continue;\n\t\tif(name.Sheet != idx) continue;\n\t\tname.Ref = \"'\" + wb.SheetNames[idx] + \"'!\" + ref; break;\n\t}\n\tif(i == names.length) names.push({ Name: '_xlnm._FilterDatabase', Sheet: idx, Ref: \"'\" + wb.SheetNames[idx] + \"'!\" + ref  });\n\treturn writextag(\"autoFilter\", null, {ref:ref});\n}\n\n/* 18.3.1.88 sheetViews CT_SheetViews */\n/* 18.3.1.87 sheetView CT_SheetView */\nvar sviewregex = /<(?:\\w:)?sheetView(?:[^>a-z][^>]*)?\\/?>/;\nfunction parse_ws_xml_sheetviews(data, wb/*:WBWBProps*/) {\n\tif(!wb.Views) wb.Views = [{}];\n\t(data.match(sviewregex)||[]).forEach(function(r/*:string*/, i/*:number*/) {\n\t\tvar tag = parsexmltag(r);\n\t\t// $FlowIgnore\n\t\tif(!wb.Views[i]) wb.Views[i] = {};\n\t\t// $FlowIgnore\n\t\tif(+tag.zoomScale) wb.Views[i].zoom = +tag.zoomScale;\n\t\t// $FlowIgnore\n\t\tif(parsexmlbool(tag.rightToLeft)) wb.Views[i].RTL = true;\n\t});\n}\nfunction write_ws_xml_sheetviews(ws, opts, idx, wb)/*:string*/ {\n\tvar sview = ({workbookViewId:\"0\"}/*:any*/);\n\t// $FlowIgnore\n\tif((((wb||{}).Workbook||{}).Views||[])[0]) sview.rightToLeft = wb.Workbook.Views[0].RTL ? \"1\" : \"0\";\n\treturn writextag(\"sheetViews\", writextag(\"sheetView\", null, sview), {});\n}\n\nfunction write_ws_xml_cell(cell/*:Cell*/, ref, ws, opts/*::, idx, wb*/)/*:string*/ {\n\tif(cell.c) ws['!comments'].push([ref, cell.c]);\n\tif(cell.v === undefined && typeof cell.f !== \"string\" || cell.t === 'z' && !cell.f) return \"\";\n\tvar vv = \"\";\n\tvar oldt = cell.t, oldv = cell.v;\n\tif(cell.t !== \"z\") switch(cell.t) {\n\t\tcase 'b': vv = cell.v ? \"1\" : \"0\"; break;\n\t\tcase 'n': vv = ''+cell.v; break;\n\t\tcase 'e': vv = BErr[cell.v]; break;\n\t\tcase 'd':\n\t\t\tif(opts && opts.cellDates) vv = parseDate(cell.v, -1).toISOString();\n\t\t\telse {\n\t\t\t\tcell = dup(cell);\n\t\t\t\tcell.t = 'n';\n\t\t\t\tvv = ''+(cell.v = datenum(parseDate(cell.v)));\n\t\t\t}\n\t\t\tif(typeof cell.z === 'undefined') cell.z = table_fmt[14];\n\t\t\tbreak;\n\t\tdefault: vv = cell.v; break;\n\t}\n\tvar v = writetag('v', escapexml(vv)), o = ({r:ref}/*:any*/);\n\t/* TODO: cell style */\n\tvar os = get_cell_style(opts.cellXfs, cell, opts);\n\tif(os !== 0) o.s = os;\n\tswitch(cell.t) {\n\t\tcase 'n': break;\n\t\tcase 'd': o.t = \"d\"; break;\n\t\tcase 'b': o.t = \"b\"; break;\n\t\tcase 'e': o.t = \"e\"; break;\n\t\tcase 'z': break;\n\t\tdefault: if(cell.v == null) { delete cell.t; break; }\n\t\t\tif(cell.v.length > 32767) throw new Error(\"Text length must not exceed 32767 characters\");\n\t\t\tif(opts && opts.bookSST) {\n\t\t\t\tv = writetag('v', ''+get_sst_id(opts.Strings, cell.v, opts.revStrings));\n\t\t\t\to.t = \"s\"; break;\n\t\t\t}\n\t\t\to.t = \"str\"; break;\n\t}\n\tif(cell.t != oldt) { cell.t = oldt; cell.v = oldv; }\n\tif(typeof cell.f == \"string\" && cell.f) {\n\t\tvar ff = cell.F && cell.F.slice(0, ref.length) == ref ? {t:\"array\", ref:cell.F} : null;\n\t\tv = writextag('f', escapexml(cell.f), ff) + (cell.v != null ? v : \"\");\n\t}\n\tif(cell.l) ws['!links'].push([ref, cell.l]);\n\tif(cell.D) o.cm = 1;\n\treturn writextag('c', v, o);\n}\n\nvar parse_ws_xml_data = /*#__PURE__*/(function() {\n\tvar cellregex = /<(?:\\w+:)?c[ \\/>]/, rowregex = /<\\/(?:\\w+:)?row>/;\n\tvar rregex = /r=[\"']([^\"']*)[\"']/, isregex = /<(?:\\w+:)?is>([\\S\\s]*?)<\\/(?:\\w+:)?is>/;\n\tvar refregex = /ref=[\"']([^\"']*)[\"']/;\n\tvar match_v = matchtag(\"v\"), match_f = matchtag(\"f\");\n\nreturn function parse_ws_xml_data(sdata/*:string*/, s, opts, guess/*:Range*/, themes, styles) {\n\tvar ri = 0, x = \"\", cells/*:Array<string>*/ = [], cref/*:?Array<string>*/ = [], idx=0, i=0, cc=0, d=\"\", p/*:any*/;\n\tvar tag, tagr = 0, tagc = 0;\n\tvar sstr, ftag;\n\tvar fmtid = 0, fillid = 0;\n\tvar do_format = Array.isArray(styles.CellXf), cf;\n\tvar arrayf/*:Array<[Range, string]>*/ = [];\n\tvar sharedf = [];\n\tvar dense = Array.isArray(s);\n\tvar rows/*:Array<RowInfo>*/ = [], rowobj = {}, rowrite = false;\n\tvar sheetStubs = !!opts.sheetStubs;\n\tfor(var marr = sdata.split(rowregex), mt = 0, marrlen = marr.length; mt != marrlen; ++mt) {\n\t\tx = marr[mt].trim();\n\t\tvar xlen = x.length;\n\t\tif(xlen === 0) continue;\n\n\t\t/* 18.3.1.73 row CT_Row */\n\t\tvar rstarti = 0;\n\t\touta: for(ri = 0; ri < xlen; ++ri) switch(/*x.charCodeAt(ri)*/x[ri]) {\n\t\t\tcase \">\" /*62*/:\n\t\t\t\tif(/*x.charCodeAt(ri-1) != 47*/x[ri-1] != \"/\") { ++ri; break outa; }\n\t\t\t\tif(opts && opts.cellStyles) {\n\t\t\t\t\t// TODO: avoid duplication\n\t\t\t\t\ttag = parsexmltag(x.slice(rstarti,ri), true);\n\t\t\t\t\ttagr = tag.r != null ? parseInt(tag.r, 10) : tagr+1; tagc = -1;\n\t\t\t\t\tif(opts.sheetRows && opts.sheetRows < tagr) continue;\n\t\t\t\t\trowobj = {}; rowrite = false;\n\t\t\t\t\tif(tag.ht) { rowrite = true; rowobj.hpt = parseFloat(tag.ht); rowobj.hpx = pt2px(rowobj.hpt); }\n\t\t\t\t\tif(tag.hidden == \"1\") { rowrite = true; rowobj.hidden = true; }\n\t\t\t\t\tif(tag.outlineLevel != null) { rowrite = true; rowobj.level = +tag.outlineLevel; }\n\t\t\t\t\tif(rowrite) rows[tagr-1] = rowobj;\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase \"<\" /*60*/: rstarti = ri; break;\n\t\t}\n\t\tif(rstarti >= ri) break;\n\t\ttag = parsexmltag(x.slice(rstarti,ri), true);\n\t\ttagr = tag.r != null ? parseInt(tag.r, 10) : tagr+1; tagc = -1;\n\t\tif(opts.sheetRows && opts.sheetRows < tagr) continue;\n\t\tif(guess.s.r > tagr - 1) guess.s.r = tagr - 1;\n\t\tif(guess.e.r < tagr - 1) guess.e.r = tagr - 1;\n\n\t\tif(opts && opts.cellStyles) {\n\t\t\trowobj = {}; rowrite = false;\n\t\t\tif(tag.ht) { rowrite = true; rowobj.hpt = parseFloat(tag.ht); rowobj.hpx = pt2px(rowobj.hpt); }\n\t\t\tif(tag.hidden == \"1\") { rowrite = true; rowobj.hidden = true; }\n\t\t\tif(tag.outlineLevel != null) { rowrite = true; rowobj.level = +tag.outlineLevel; }\n\t\t\tif(rowrite) rows[tagr-1] = rowobj;\n\t\t}\n\n\t\t/* 18.3.1.4 c CT_Cell */\n\t\tcells = x.slice(ri).split(cellregex);\n\t\tfor(var rslice = 0; rslice != cells.length; ++rslice) if(cells[rslice].trim().charAt(0) != \"<\") break;\n\t\tcells = cells.slice(rslice);\n\t\tfor(ri = 0; ri != cells.length; ++ri) {\n\t\t\tx = cells[ri].trim();\n\t\t\tif(x.length === 0) continue;\n\t\t\tcref = x.match(rregex); idx = ri; i=0; cc=0;\n\t\t\tx = \"<c \" + (x.slice(0,1)==\"<\"?\">\":\"\") + x;\n\t\t\tif(cref != null && cref.length === 2) {\n\t\t\t\tidx = 0; d=cref[1];\n\t\t\t\tfor(i=0; i != d.length; ++i) {\n\t\t\t\t\tif((cc=d.charCodeAt(i)-64) < 1 || cc > 26) break;\n\t\t\t\t\tidx = 26*idx + cc;\n\t\t\t\t}\n\t\t\t\t--idx;\n\t\t\t\ttagc = idx;\n\t\t\t} else ++tagc;\n\t\t\tfor(i = 0; i != x.length; ++i) if(x.charCodeAt(i) === 62) break; ++i;\n\t\t\ttag = parsexmltag(x.slice(0,i), true);\n\t\t\tif(!tag.r) tag.r = encode_cell({r:tagr-1, c:tagc});\n\t\t\td = x.slice(i);\n\t\t\tp = ({t:\"\"}/*:any*/);\n\n\t\t\tif((cref=d.match(match_v))!= null && /*::cref != null && */cref[1] !== '') p.v=unescapexml(cref[1]);\n\t\t\tif(opts.cellFormula) {\n\t\t\t\tif((cref=d.match(match_f))!= null && /*::cref != null && */cref[1] !== '') {\n\t\t\t\t\t/* TODO: match against XLSXFutureFunctions */\n\t\t\t\t\tp.f=unescapexml(utf8read(cref[1])).replace(/\\r\\n/g, \"\\n\");\n\t\t\t\t\tif(!opts.xlfn) p.f = _xlfn(p.f);\n\t\t\t\t\tif(/*::cref != null && cref[0] != null && */cref[0].indexOf('t=\"array\"') > -1) {\n\t\t\t\t\t\tp.F = (d.match(refregex)||[])[1];\n\t\t\t\t\t\tif(p.F.indexOf(\":\") > -1) arrayf.push([safe_decode_range(p.F), p.F]);\n\t\t\t\t\t} else if(/*::cref != null && cref[0] != null && */cref[0].indexOf('t=\"shared\"') > -1) {\n\t\t\t\t\t\t// TODO: parse formula\n\t\t\t\t\t\tftag = parsexmltag(cref[0]);\n\t\t\t\t\t\tvar ___f = unescapexml(utf8read(cref[1]));\n\t\t\t\t\t\tif(!opts.xlfn) ___f = _xlfn(___f);\n\t\t\t\t\t\tsharedf[parseInt(ftag.si, 10)] = [ftag, ___f, tag.r];\n\t\t\t\t\t}\n\t\t\t\t} else if((cref=d.match(/<f[^>]*\\/>/))) {\n\t\t\t\t\tftag = parsexmltag(cref[0]);\n\t\t\t\t\tif(sharedf[ftag.si]) p.f = shift_formula_xlsx(sharedf[ftag.si][1], sharedf[ftag.si][2]/*[0].ref*/, tag.r);\n\t\t\t\t}\n\t\t\t\t/* TODO: factor out contains logic */\n\t\t\t\tvar _tag = decode_cell(tag.r);\n\t\t\t\tfor(i = 0; i < arrayf.length; ++i)\n\t\t\t\t\tif(_tag.r >= arrayf[i][0].s.r && _tag.r <= arrayf[i][0].e.r)\n\t\t\t\t\t\tif(_tag.c >= arrayf[i][0].s.c && _tag.c <= arrayf[i][0].e.c)\n\t\t\t\t\t\t\tp.F = arrayf[i][1];\n\t\t\t}\n\n\t\t\tif(tag.t == null && p.v === undefined) {\n\t\t\t\tif(p.f || p.F) {\n\t\t\t\t\tp.v = 0; p.t = \"n\";\n\t\t\t\t} else if(!sheetStubs) continue;\n\t\t\t\telse p.t = \"z\";\n\t\t\t}\n\t\t\telse p.t = tag.t || \"n\";\n\t\t\tif(guess.s.c > tagc) guess.s.c = tagc;\n\t\t\tif(guess.e.c < tagc) guess.e.c = tagc;\n\t\t\t/* 18.18.11 t ST_CellType */\n\t\t\tswitch(p.t) {\n\t\t\t\tcase 'n':\n\t\t\t\t\tif(p.v == \"\" || p.v == null) {\n\t\t\t\t\t\tif(!sheetStubs) continue;\n\t\t\t\t\t\tp.t = 'z';\n\t\t\t\t\t} else p.v = parseFloat(p.v);\n\t\t\t\t\tbreak;\n\t\t\t\tcase 's':\n\t\t\t\t\tif(typeof p.v == 'undefined') {\n\t\t\t\t\t\tif(!sheetStubs) continue;\n\t\t\t\t\t\tp.t = 'z';\n\t\t\t\t\t} else {\n\t\t\t\t\t\tsstr = strs[parseInt(p.v, 10)];\n\t\t\t\t\t\tp.v = sstr.t;\n\t\t\t\t\t\tp.r = sstr.r;\n\t\t\t\t\t\tif(opts.cellHTML) p.h = sstr.h;\n\t\t\t\t\t}\n\t\t\t\t\tbreak;\n\t\t\t\tcase 'str':\n\t\t\t\t\tp.t = \"s\";\n\t\t\t\t\tp.v = (p.v!=null) ? utf8read(p.v) : '';\n\t\t\t\t\tif(opts.cellHTML) p.h = escapehtml(p.v);\n\t\t\t\t\tbreak;\n\t\t\t\tcase 'inlineStr':\n\t\t\t\t\tcref = d.match(isregex);\n\t\t\t\t\tp.t = 's';\n\t\t\t\t\tif(cref != null && (sstr = parse_si(cref[1]))) {\n\t\t\t\t\t\tp.v = sstr.t;\n\t\t\t\t\t\tif(opts.cellHTML) p.h = sstr.h;\n\t\t\t\t\t} else p.v = \"\";\n\t\t\t\t\tbreak;\n\t\t\t\tcase 'b': p.v = parsexmlbool(p.v); break;\n\t\t\t\tcase 'd':\n\t\t\t\t\tif(opts.cellDates) p.v = parseDate(p.v, 1);\n\t\t\t\t\telse { p.v = datenum(parseDate(p.v, 1)); p.t = 'n'; }\n\t\t\t\t\tbreak;\n\t\t\t\t/* error string in .w, number in .v */\n\t\t\t\tcase 'e':\n\t\t\t\t\tif(!opts || opts.cellText !== false) p.w = p.v;\n\t\t\t\t\tp.v = RBErr[p.v]; break;\n\t\t\t}\n\t\t\t/* formatting */\n\t\t\tfmtid = fillid = 0;\n\t\t\tcf = null;\n\t\t\tif(do_format && tag.s !== undefined) {\n\t\t\t\tcf = styles.CellXf[tag.s];\n\t\t\t\tif(cf != null) {\n\t\t\t\t\tif(cf.numFmtId != null) fmtid = cf.numFmtId;\n\t\t\t\t\tif(opts.cellStyles) {\n\t\t\t\t\t\tif(cf.fillId != null) fillid = cf.fillId;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tsafe_format(p, fmtid, fillid, opts, themes, styles);\n\t\t\tif(opts.cellDates && do_format && p.t == 'n' && fmt_is_date(table_fmt[fmtid])) { p.t = 'd'; p.v = numdate(p.v); }\n\t\t\tif(tag.cm && opts.xlmeta) {\n\t\t\t\tvar cm = (opts.xlmeta.Cell||[])[+tag.cm-1];\n\t\t\t\tif(cm && cm.type == 'XLDAPR') p.D = true;\n\t\t\t}\n\t\t\tif(dense) {\n\t\t\t\tvar _r = decode_cell(tag.r);\n\t\t\t\tif(!s[_r.r]) s[_r.r] = [];\n\t\t\t\ts[_r.r][_r.c] = p;\n\t\t\t} else s[tag.r] = p;\n\t\t}\n\t}\n\tif(rows.length > 0) s['!rows'] = rows;\n}; })();\n\nfunction write_ws_xml_data(ws/*:Worksheet*/, opts, idx/*:number*/, wb/*:Workbook*//*::, rels*/)/*:string*/ {\n\tvar o/*:Array<string>*/ = [], r/*:Array<string>*/ = [], range = safe_decode_range(ws['!ref']), cell=\"\", ref, rr = \"\", cols/*:Array<string>*/ = [], R=0, C=0, rows = ws['!rows'];\n\tvar dense = Array.isArray(ws);\n\tvar params = ({r:rr}/*:any*/), row/*:RowInfo*/, height = -1;\n\tfor(C = range.s.c; C <= range.e.c; ++C) cols[C] = encode_col(C);\n\tfor(R = range.s.r; R <= range.e.r; ++R) {\n\t\tr = [];\n\t\trr = encode_row(R);\n\t\tfor(C = range.s.c; C <= range.e.c; ++C) {\n\t\t\tref = cols[C] + rr;\n\t\t\tvar _cell = dense ? (ws[R]||[])[C]: ws[ref];\n\t\t\tif(_cell === undefined) continue;\n\t\t\tif((cell = write_ws_xml_cell(_cell, ref, ws, opts, idx, wb)) != null) r.push(cell);\n\t\t}\n\t\tif(r.length > 0 || (rows && rows[R])) {\n\t\t\tparams = ({r:rr}/*:any*/);\n\t\t\tif(rows && rows[R]) {\n\t\t\t\trow = rows[R];\n\t\t\t\tif(row.hidden) params.hidden = 1;\n\t\t\t\theight = -1;\n\t\t\t\tif(row.hpx) height = px2pt(row.hpx);\n\t\t\t\telse if(row.hpt) height = row.hpt;\n\t\t\t\tif(height > -1) { params.ht = height; params.customHeight = 1; }\n\t\t\t\tif(row.level) { params.outlineLevel = row.level; }\n\t\t\t}\n\t\t\to[o.length] = (writextag('row', r.join(\"\"), params));\n\t\t}\n\t}\n\tif(rows) for(; R < rows.length; ++R) {\n\t\tif(rows && rows[R]) {\n\t\t\tparams = ({r:R+1}/*:any*/);\n\t\t\trow = rows[R];\n\t\t\tif(row.hidden) params.hidden = 1;\n\t\t\theight = -1;\n\t\t\tif (row.hpx) height = px2pt(row.hpx);\n\t\t\telse if (row.hpt) height = row.hpt;\n\t\t\tif (height > -1) { params.ht = height; params.customHeight = 1; }\n\t\t\tif (row.level) { params.outlineLevel = row.level; }\n\t\t\to[o.length] = (writextag('row', \"\", params));\n\t\t}\n\t}\n\treturn o.join(\"\");\n}\n\nfunction write_ws_xml(idx/*:number*/, opts, wb/*:Workbook*/, rels)/*:string*/ {\n\tvar o = [XML_HEADER, writextag('worksheet', null, {\n\t\t'xmlns': XMLNS_main[0],\n\t\t'xmlns:r': XMLNS.r\n\t})];\n\tvar s = wb.SheetNames[idx], sidx = 0, rdata = \"\";\n\tvar ws = wb.Sheets[s];\n\tif(ws == null) ws = {};\n\tvar ref = ws['!ref'] || 'A1';\n\tvar range = safe_decode_range(ref);\n\tif(range.e.c > 0x3FFF || range.e.r > 0xFFFFF) {\n\t\tif(opts.WTF) throw new Error(\"Range \" + ref + \" exceeds format limit A1:XFD1048576\");\n\t\trange.e.c = Math.min(range.e.c, 0x3FFF);\n\t\trange.e.r = Math.min(range.e.c, 0xFFFFF);\n\t\tref = encode_range(range);\n\t}\n\tif(!rels) rels = {};\n\tws['!comments'] = [];\n\tvar _drawing = [];\n\n\twrite_ws_xml_sheetpr(ws, wb, idx, opts, o);\n\n\to[o.length] = (writextag('dimension', null, {'ref': ref}));\n\n\to[o.length] = write_ws_xml_sheetviews(ws, opts, idx, wb);\n\n\t/* TODO: store in WB, process styles */\n\tif(opts.sheetFormat) o[o.length] = (writextag('sheetFormatPr', null, {\n\t\tdefaultRowHeight:opts.sheetFormat.defaultRowHeight||'16',\n\t\tbaseColWidth:opts.sheetFormat.baseColWidth||'10',\n\t\toutlineLevelRow:opts.sheetFormat.outlineLevelRow||'7'\n\t}));\n\n\tif(ws['!cols'] != null && ws['!cols'].length > 0) o[o.length] = (write_ws_xml_cols(ws, ws['!cols']));\n\n\to[sidx = o.length] = '<sheetData/>';\n\tws['!links'] = [];\n\tif(ws['!ref'] != null) {\n\t\trdata = write_ws_xml_data(ws, opts, idx, wb, rels);\n\t\tif(rdata.length > 0) o[o.length] = (rdata);\n\t}\n\tif(o.length>sidx+1) { o[o.length] = ('</sheetData>'); o[sidx]=o[sidx].replace(\"/>\",\">\"); }\n\n\t/* sheetCalcPr */\n\n\tif(ws['!protect']) o[o.length] = write_ws_xml_protection(ws['!protect']);\n\n\t/* protectedRanges */\n\t/* scenarios */\n\n\tif(ws['!autofilter'] != null) o[o.length] = write_ws_xml_autofilter(ws['!autofilter'], ws, wb, idx);\n\n\t/* sortState */\n\t/* dataConsolidate */\n\t/* customSheetViews */\n\n\tif(ws['!merges'] != null && ws['!merges'].length > 0) o[o.length] = (write_ws_xml_merges(ws['!merges']));\n\n\t/* phoneticPr */\n\t/* conditionalFormatting */\n\t/* dataValidations */\n\n\tvar relc = -1, rel, rId = -1;\n\tif(/*::(*/ws['!links']/*::||[])*/.length > 0) {\n\t\to[o.length] = \"<hyperlinks>\";\n\t\t/*::(*/ws['!links']/*::||[])*/.forEach(function(l) {\n\t\t\tif(!l[1].Target) return;\n\t\t\trel = ({\"ref\":l[0]}/*:any*/);\n\t\t\tif(l[1].Target.charAt(0) != \"#\") {\n\t\t\t\trId = add_rels(rels, -1, escapexml(l[1].Target).replace(/#.*$/, \"\"), RELS.HLINK);\n\t\t\t\trel[\"r:id\"] = \"rId\"+rId;\n\t\t\t}\n\t\t\tif((relc = l[1].Target.indexOf(\"#\")) > -1) rel.location = escapexml(l[1].Target.slice(relc+1));\n\t\t\tif(l[1].Tooltip) rel.tooltip = escapexml(l[1].Tooltip);\n\t\t\to[o.length] = writextag(\"hyperlink\",null,rel);\n\t\t});\n\t\to[o.length] = \"</hyperlinks>\";\n\t}\n\tdelete ws['!links'];\n\n\t/* printOptions */\n\n\tif(ws['!margins'] != null) o[o.length] =  write_ws_xml_margins(ws['!margins']);\n\n\t/* pageSetup */\n\t/* headerFooter */\n\t/* rowBreaks */\n\t/* colBreaks */\n\t/* customProperties */\n\t/* cellWatches */\n\n\tif(!opts || opts.ignoreEC || (opts.ignoreEC == (void 0))) o[o.length] = writetag(\"ignoredErrors\", writextag(\"ignoredError\", null, {numberStoredAsText:1, sqref:ref}));\n\n\t/* smartTags */\n\n\tif(_drawing.length > 0) {\n\t\trId = add_rels(rels, -1, \"../drawings/drawing\" + (idx+1) + \".xml\", RELS.DRAW);\n\t\to[o.length] = writextag(\"drawing\", null, {\"r:id\":\"rId\" + rId});\n\t\tws['!drawing'] = _drawing;\n\t}\n\n\tif(ws['!comments'].length > 0) {\n\t\trId = add_rels(rels, -1, \"../drawings/vmlDrawing\" + (idx+1) + \".vml\", RELS.VML);\n\t\to[o.length] = writextag(\"legacyDrawing\", null, {\"r:id\":\"rId\" + rId});\n\t\tws['!legacy'] = rId;\n\t}\n\n\t/* legacyDrawingHF */\n\t/* picture */\n\t/* oleObjects */\n\t/* controls */\n\t/* webPublishItems */\n\t/* tableParts */\n\t/* extLst */\n\n\tif(o.length>1) { o[o.length] = ('</worksheet>'); o[1]=o[1].replace(\"/>\",\">\"); }\n\treturn o.join(\"\");\n}\n\n/* [MS-XLSB] 2.4.726 BrtRowHdr */\nfunction parse_BrtRowHdr(data, length) {\n\tvar z = ({}/*:any*/);\n\tvar tgt = data.l + length;\n\tz.r = data.read_shift(4);\n\tdata.l += 4; // TODO: ixfe\n\tvar miyRw = data.read_shift(2);\n\tdata.l += 1; // TODO: top/bot padding\n\tvar flags = data.read_shift(1);\n\tdata.l = tgt;\n\tif(flags & 0x07) z.level = flags & 0x07;\n\tif(flags & 0x10) z.hidden = true;\n\tif(flags & 0x20) z.hpt = miyRw / 20;\n\treturn z;\n}\nfunction write_BrtRowHdr(R/*:number*/, range, ws) {\n\tvar o = new_buf(17+8*16);\n\tvar row = (ws['!rows']||[])[R]||{};\n\to.write_shift(4, R);\n\n\to.write_shift(4, 0); /* TODO: ixfe */\n\n\tvar miyRw = 0x0140;\n\tif(row.hpx) miyRw = px2pt(row.hpx) * 20;\n\telse if(row.hpt) miyRw = row.hpt * 20;\n\to.write_shift(2, miyRw);\n\n\to.write_shift(1, 0); /* top/bot padding */\n\n\tvar flags = 0x0;\n\tif(row.level) flags |= row.level;\n\tif(row.hidden) flags |= 0x10;\n\tif(row.hpx || row.hpt) flags |= 0x20;\n\to.write_shift(1, flags);\n\n\to.write_shift(1, 0); /* phonetic guide */\n\n\t/* [MS-XLSB] 2.5.8 BrtColSpan explains the mechanism */\n\tvar ncolspan = 0, lcs = o.l;\n\to.l += 4;\n\n\tvar caddr = {r:R, c:0};\n\tfor(var i = 0; i < 16; ++i) {\n\t\tif((range.s.c > ((i+1) << 10)) || (range.e.c < (i << 10))) continue;\n\t\tvar first = -1, last = -1;\n\t\tfor(var j = (i<<10); j < ((i+1)<<10); ++j) {\n\t\t\tcaddr.c = j;\n\t\t\tvar cell = Array.isArray(ws) ? (ws[caddr.r]||[])[caddr.c] : ws[encode_cell(caddr)];\n\t\t\tif(cell) { if(first < 0) first = j; last = j; }\n\t\t}\n\t\tif(first < 0) continue;\n\t\t++ncolspan;\n\t\to.write_shift(4, first);\n\t\to.write_shift(4, last);\n\t}\n\n\tvar l = o.l;\n\to.l = lcs;\n\to.write_shift(4, ncolspan);\n\to.l = l;\n\n\treturn o.length > o.l ? o.slice(0, o.l) : o;\n}\nfunction write_row_header(ba, ws, range, R) {\n\tvar o = write_BrtRowHdr(R, range, ws);\n\tif((o.length > 17) || (ws['!rows']||[])[R]) write_record(ba, 0x0000 /* BrtRowHdr */, o);\n}\n\n/* [MS-XLSB] 2.4.820 BrtWsDim */\nvar parse_BrtWsDim = parse_UncheckedRfX;\nvar write_BrtWsDim = write_UncheckedRfX;\n\n/* [MS-XLSB] 2.4.821 BrtWsFmtInfo */\nfunction parse_BrtWsFmtInfo(/*::data, length*/) {\n}\n//function write_BrtWsFmtInfo(ws, o) { }\n\n/* [MS-XLSB] 2.4.823 BrtWsProp */\nfunction parse_BrtWsProp(data, length) {\n\tvar z = {};\n\tvar f = data[data.l]; ++data.l;\n\tz.above = !(f & 0x40);\n\tz.left  = !(f & 0x80);\n\t/* TODO: pull flags */\n\tdata.l += 18;\n\tz.name = parse_XLSBCodeName(data, length - 19);\n\treturn z;\n}\nfunction write_BrtWsProp(str, outl, o) {\n\tif(o == null) o = new_buf(84+4*str.length);\n\tvar f = 0xC0;\n\tif(outl) {\n\t\tif(outl.above) f &= ~0x40;\n\t\tif(outl.left)  f &= ~0x80;\n\t}\n\to.write_shift(1, f);\n\tfor(var i = 1; i < 3; ++i) o.write_shift(1,0);\n\twrite_BrtColor({auto:1}, o);\n\to.write_shift(-4,-1);\n\to.write_shift(-4,-1);\n\twrite_XLSBCodeName(str, o);\n\treturn o.slice(0, o.l);\n}\n\n/* [MS-XLSB] 2.4.306 BrtCellBlank */\nfunction parse_BrtCellBlank(data) {\n\tvar cell = parse_XLSBCell(data);\n\treturn [cell];\n}\nfunction write_BrtCellBlank(cell, ncell, o) {\n\tif(o == null) o = new_buf(8);\n\treturn write_XLSBCell(ncell, o);\n}\nfunction parse_BrtShortBlank(data) {\n\tvar cell = parse_XLSBShortCell(data);\n\treturn [cell];\n}\nfunction write_BrtShortBlank(cell, ncell, o) {\n\tif(o == null) o = new_buf(4);\n\treturn write_XLSBShortCell(ncell, o);\n}\n\n/* [MS-XLSB] 2.4.307 BrtCellBool */\nfunction parse_BrtCellBool(data) {\n\tvar cell = parse_XLSBCell(data);\n\tvar fBool = data.read_shift(1);\n\treturn [cell, fBool, 'b'];\n}\nfunction write_BrtCellBool(cell, ncell, o) {\n\tif(o == null) o = new_buf(9);\n\twrite_XLSBCell(ncell, o);\n\to.write_shift(1, cell.v ? 1 : 0);\n\treturn o;\n}\nfunction parse_BrtShortBool(data) {\n\tvar cell = parse_XLSBShortCell(data);\n\tvar fBool = data.read_shift(1);\n\treturn [cell, fBool, 'b'];\n}\nfunction write_BrtShortBool(cell, ncell, o) {\n\tif(o == null) o = new_buf(5);\n\twrite_XLSBShortCell(ncell, o);\n\to.write_shift(1, cell.v ? 1 : 0);\n\treturn o;\n}\n\n/* [MS-XLSB] 2.4.308 BrtCellError */\nfunction parse_BrtCellError(data) {\n\tvar cell = parse_XLSBCell(data);\n\tvar bError = data.read_shift(1);\n\treturn [cell, bError, 'e'];\n}\nfunction write_BrtCellError(cell, ncell, o) {\n\tif(o == null) o = new_buf(9);\n\twrite_XLSBCell(ncell, o);\n\to.write_shift(1, cell.v);\n\treturn o;\n}\nfunction parse_BrtShortError(data) {\n\tvar cell = parse_XLSBShortCell(data);\n\tvar bError = data.read_shift(1);\n\treturn [cell, bError, 'e'];\n}\nfunction write_BrtShortError(cell, ncell, o) {\n\tif(o == null) o = new_buf(8);\n\twrite_XLSBShortCell(ncell, o);\n\to.write_shift(1, cell.v);\n\to.write_shift(2, 0);\n\to.write_shift(1, 0);\n\treturn o;\n}\n\n\n/* [MS-XLSB] 2.4.311 BrtCellIsst */\nfunction parse_BrtCellIsst(data) {\n\tvar cell = parse_XLSBCell(data);\n\tvar isst = data.read_shift(4);\n\treturn [cell, isst, 's'];\n}\nfunction write_BrtCellIsst(cell, ncell, o) {\n\tif(o == null) o = new_buf(12);\n\twrite_XLSBCell(ncell, o);\n\to.write_shift(4, ncell.v);\n\treturn o;\n}\nfunction parse_BrtShortIsst(data) {\n\tvar cell = parse_XLSBShortCell(data);\n\tvar isst = data.read_shift(4);\n\treturn [cell, isst, 's'];\n}\nfunction write_BrtShortIsst(cell, ncell, o) {\n\tif(o == null) o = new_buf(8);\n\twrite_XLSBShortCell(ncell, o);\n\to.write_shift(4, ncell.v);\n\treturn o;\n}\n\n/* [MS-XLSB] 2.4.313 BrtCellReal */\nfunction parse_BrtCellReal(data) {\n\tvar cell = parse_XLSBCell(data);\n\tvar value = parse_Xnum(data);\n\treturn [cell, value, 'n'];\n}\nfunction write_BrtCellReal(cell, ncell, o) {\n\tif(o == null) o = new_buf(16);\n\twrite_XLSBCell(ncell, o);\n\twrite_Xnum(cell.v, o);\n\treturn o;\n}\nfunction parse_BrtShortReal(data) {\n\tvar cell = parse_XLSBShortCell(data);\n\tvar value = parse_Xnum(data);\n\treturn [cell, value, 'n'];\n}\nfunction write_BrtShortReal(cell, ncell, o) {\n\tif(o == null) o = new_buf(12);\n\twrite_XLSBShortCell(ncell, o);\n\twrite_Xnum(cell.v, o);\n\treturn o;\n}\n\n/* [MS-XLSB] 2.4.314 BrtCellRk */\nfunction parse_BrtCellRk(data) {\n\tvar cell = parse_XLSBCell(data);\n\tvar value = parse_RkNumber(data);\n\treturn [cell, value, 'n'];\n}\nfunction write_BrtCellRk(cell, ncell, o) {\n\tif(o == null) o = new_buf(12);\n\twrite_XLSBCell(ncell, o);\n\twrite_RkNumber(cell.v, o);\n\treturn o;\n}\nfunction parse_BrtShortRk(data) {\n\tvar cell = parse_XLSBShortCell(data);\n\tvar value = parse_RkNumber(data);\n\treturn [cell, value, 'n'];\n}\nfunction write_BrtShortRk(cell, ncell, o) {\n\tif(o == null) o = new_buf(8);\n\twrite_XLSBShortCell(ncell, o);\n\twrite_RkNumber(cell.v, o);\n\treturn o;\n}\n\n/* [MS-XLSB] 2.4.323 BrtCellRString */\nfunction parse_BrtCellRString(data) {\n\tvar cell = parse_XLSBCell(data);\n\tvar value = parse_RichStr(data);\n\treturn [cell, value, 'is'];\n}\n\n/* [MS-XLSB] 2.4.317 BrtCellSt */\nfunction parse_BrtCellSt(data) {\n\tvar cell = parse_XLSBCell(data);\n\tvar value = parse_XLWideString(data);\n\treturn [cell, value, 'str'];\n}\nfunction write_BrtCellSt(cell, ncell, o) {\n\tif(o == null) o = new_buf(12 + 4 * cell.v.length);\n\twrite_XLSBCell(ncell, o);\n\twrite_XLWideString(cell.v, o);\n\treturn o.length > o.l ? o.slice(0, o.l) : o;\n}\nfunction parse_BrtShortSt(data) {\n\tvar cell = parse_XLSBShortCell(data);\n\tvar value = parse_XLWideString(data);\n\treturn [cell, value, 'str'];\n}\nfunction write_BrtShortSt(cell, ncell, o) {\n\tif(o == null) o = new_buf(8 + 4 * cell.v.length);\n\twrite_XLSBShortCell(ncell, o);\n\twrite_XLWideString(cell.v, o);\n\treturn o.length > o.l ? o.slice(0, o.l) : o;\n}\n\n/* [MS-XLSB] 2.4.653 BrtFmlaBool */\nfunction parse_BrtFmlaBool(data, length, opts) {\n\tvar end = data.l + length;\n\tvar cell = parse_XLSBCell(data);\n\tcell.r = opts['!row'];\n\tvar value = data.read_shift(1);\n\tvar o = [cell, value, 'b'];\n\tif(opts.cellFormula) {\n\t\tdata.l += 2;\n\t\tvar formula = parse_XLSBCellParsedFormula(data, end - data.l, opts);\n\t\to[3] = stringify_formula(formula, null/*range*/, cell, opts.supbooks, opts);/* TODO */\n\t}\n\telse data.l = end;\n\treturn o;\n}\n\n/* [MS-XLSB] 2.4.654 BrtFmlaError */\nfunction parse_BrtFmlaError(data, length, opts) {\n\tvar end = data.l + length;\n\tvar cell = parse_XLSBCell(data);\n\tcell.r = opts['!row'];\n\tvar value = data.read_shift(1);\n\tvar o = [cell, value, 'e'];\n\tif(opts.cellFormula) {\n\t\tdata.l += 2;\n\t\tvar formula = parse_XLSBCellParsedFormula(data, end - data.l, opts);\n\t\to[3] = stringify_formula(formula, null/*range*/, cell, opts.supbooks, opts);/* TODO */\n\t}\n\telse data.l = end;\n\treturn o;\n}\n\n/* [MS-XLSB] 2.4.655 BrtFmlaNum */\nfunction parse_BrtFmlaNum(data, length, opts) {\n\tvar end = data.l + length;\n\tvar cell = parse_XLSBCell(data);\n\tcell.r = opts['!row'];\n\tvar value = parse_Xnum(data);\n\tvar o = [cell, value, 'n'];\n\tif(opts.cellFormula) {\n\t\tdata.l += 2;\n\t\tvar formula = parse_XLSBCellParsedFormula(data, end - data.l, opts);\n\t\to[3] = stringify_formula(formula, null/*range*/, cell, opts.supbooks, opts);/* TODO */\n\t}\n\telse data.l = end;\n\treturn o;\n}\n\n/* [MS-XLSB] 2.4.656 BrtFmlaString */\nfunction parse_BrtFmlaString(data, length, opts) {\n\tvar end = data.l + length;\n\tvar cell = parse_XLSBCell(data);\n\tcell.r = opts['!row'];\n\tvar value = parse_XLWideString(data);\n\tvar o = [cell, value, 'str'];\n\tif(opts.cellFormula) {\n\t\tdata.l += 2;\n\t\tvar formula = parse_XLSBCellParsedFormula(data, end - data.l, opts);\n\t\to[3] = stringify_formula(formula, null/*range*/, cell, opts.supbooks, opts);/* TODO */\n\t}\n\telse data.l = end;\n\treturn o;\n}\n\n/* [MS-XLSB] 2.4.682 BrtMergeCell */\nvar parse_BrtMergeCell = parse_UncheckedRfX;\nvar write_BrtMergeCell = write_UncheckedRfX;\n/* [MS-XLSB] 2.4.107 BrtBeginMergeCells */\nfunction write_BrtBeginMergeCells(cnt, o) {\n\tif(o == null) o = new_buf(4);\n\to.write_shift(4, cnt);\n\treturn o;\n}\n\n/* [MS-XLSB] 2.4.662 BrtHLink */\nfunction parse_BrtHLink(data, length/*::, opts*/) {\n\tvar end = data.l + length;\n\tvar rfx = parse_UncheckedRfX(data, 16);\n\tvar relId = parse_XLNullableWideString(data);\n\tvar loc = parse_XLWideString(data);\n\tvar tooltip = parse_XLWideString(data);\n\tvar display = parse_XLWideString(data);\n\tdata.l = end;\n\tvar o = ({rfx:rfx, relId:relId, loc:loc, display:display}/*:any*/);\n\tif(tooltip) o.Tooltip = tooltip;\n\treturn o;\n}\nfunction write_BrtHLink(l, rId) {\n\tvar o = new_buf(50+4*(l[1].Target.length + (l[1].Tooltip || \"\").length));\n\twrite_UncheckedRfX({s:decode_cell(l[0]), e:decode_cell(l[0])}, o);\n\twrite_RelID(\"rId\" + rId, o);\n\tvar locidx = l[1].Target.indexOf(\"#\");\n\tvar loc = locidx == -1 ? \"\" : l[1].Target.slice(locidx+1);\n\twrite_XLWideString(loc || \"\", o);\n\twrite_XLWideString(l[1].Tooltip || \"\", o);\n\twrite_XLWideString(\"\", o);\n\treturn o.slice(0, o.l);\n}\n\n/* [MS-XLSB] 2.4.692 BrtPane */\nfunction parse_BrtPane(/*data, length, opts*/) {\n}\n\n/* [MS-XLSB] 2.4.6 BrtArrFmla */\nfunction parse_BrtArrFmla(data, length, opts) {\n\tvar end = data.l + length;\n\tvar rfx = parse_RfX(data, 16);\n\tvar fAlwaysCalc = data.read_shift(1);\n\tvar o = [rfx]; o[2] = fAlwaysCalc;\n\tif(opts.cellFormula) {\n\t\tvar formula = parse_XLSBArrayParsedFormula(data, end - data.l, opts);\n\t\to[1] = formula;\n\t} else data.l = end;\n\treturn o;\n}\n\n/* [MS-XLSB] 2.4.750 BrtShrFmla */\nfunction parse_BrtShrFmla(data, length, opts) {\n\tvar end = data.l + length;\n\tvar rfx = parse_UncheckedRfX(data, 16);\n\tvar o = [rfx];\n\tif(opts.cellFormula) {\n\t\tvar formula = parse_XLSBSharedParsedFormula(data, end - data.l, opts);\n\t\to[1] = formula;\n\t\tdata.l = end;\n\t} else data.l = end;\n\treturn o;\n}\n\n/* [MS-XLSB] 2.4.323 BrtColInfo */\n/* TODO: once XLS ColInfo is set, combine the functions */\nfunction write_BrtColInfo(C/*:number*/, col, o) {\n\tif(o == null) o = new_buf(18);\n\tvar p = col_obj_w(C, col);\n\to.write_shift(-4, C);\n\to.write_shift(-4, C);\n\to.write_shift(4, (p.width || 10) * 256);\n\to.write_shift(4, 0/*ixfe*/); // style\n\tvar flags = 0;\n\tif(col.hidden) flags |= 0x01;\n\tif(typeof p.width == 'number') flags |= 0x02;\n\tif(col.level) flags |= (col.level << 8);\n\to.write_shift(2, flags); // bit flag\n\treturn o;\n}\n\n/* [MS-XLSB] 2.4.678 BrtMargins */\nvar BrtMarginKeys = [\"left\",\"right\",\"top\",\"bottom\",\"header\",\"footer\"];\nfunction parse_BrtMargins(data/*::, length, opts*/)/*:Margins*/ {\n\tvar margins = ({}/*:any*/);\n\tBrtMarginKeys.forEach(function(k) { margins[k] = parse_Xnum(data, 8); });\n\treturn margins;\n}\nfunction write_BrtMargins(margins/*:Margins*/, o) {\n\tif(o == null) o = new_buf(6*8);\n\tdefault_margins(margins);\n\tBrtMarginKeys.forEach(function(k) { write_Xnum((margins/*:any*/)[k], o); });\n\treturn o;\n}\n\n/* [MS-XLSB] 2.4.299 BrtBeginWsView */\nfunction parse_BrtBeginWsView(data/*::, length, opts*/) {\n\tvar f = data.read_shift(2);\n\tdata.l += 28;\n\treturn { RTL: f & 0x20 };\n}\nfunction write_BrtBeginWsView(ws, Workbook, o) {\n\tif(o == null) o = new_buf(30);\n\tvar f = 0x39c;\n\tif((((Workbook||{}).Views||[])[0]||{}).RTL) f |= 0x20;\n\to.write_shift(2, f); // bit flag\n\to.write_shift(4, 0);\n\to.write_shift(4, 0); // view first row\n\to.write_shift(4, 0); // view first col\n\to.write_shift(1, 0); // gridline color ICV\n\to.write_shift(1, 0);\n\to.write_shift(2, 0);\n\to.write_shift(2, 100); // zoom scale\n\to.write_shift(2, 0);\n\to.write_shift(2, 0);\n\to.write_shift(2, 0);\n\to.write_shift(4, 0); // workbook view id\n\treturn o;\n}\n\n/* [MS-XLSB] 2.4.309 BrtCellIgnoreEC */\nfunction write_BrtCellIgnoreEC(ref) {\n\tvar o = new_buf(24);\n\to.write_shift(4, 4);\n\to.write_shift(4, 1);\n\twrite_UncheckedRfX(ref, o);\n\treturn o;\n}\n\n/* [MS-XLSB] 2.4.748 BrtSheetProtection */\nfunction write_BrtSheetProtection(sp, o) {\n\tif(o == null) o = new_buf(16*4+2);\n\to.write_shift(2, sp.password ? crypto_CreatePasswordVerifier_Method1(sp.password) : 0);\n\to.write_shift(4, 1); // this record should not be written if no protection\n\t[\n\t\t[\"objects\",             false], // fObjects\n\t\t[\"scenarios\",           false], // fScenarios\n\t\t[\"formatCells\",          true], // fFormatCells\n\t\t[\"formatColumns\",        true], // fFormatColumns\n\t\t[\"formatRows\",           true], // fFormatRows\n\t\t[\"insertColumns\",        true], // fInsertColumns\n\t\t[\"insertRows\",           true], // fInsertRows\n\t\t[\"insertHyperlinks\",     true], // fInsertHyperlinks\n\t\t[\"deleteColumns\",        true], // fDeleteColumns\n\t\t[\"deleteRows\",           true], // fDeleteRows\n\t\t[\"selectLockedCells\",   false], // fSelLockedCells\n\t\t[\"sort\",                 true], // fSort\n\t\t[\"autoFilter\",           true], // fAutoFilter\n\t\t[\"pivotTables\",          true], // fPivotTables\n\t\t[\"selectUnlockedCells\", false]  // fSelUnlockedCells\n\t].forEach(function(n) {\n\t\t/*:: if(o == null) throw \"unreachable\"; */\n\t\tif(n[1]) o.write_shift(4, sp[n[0]] != null && !sp[n[0]] ? 1 : 0);\n\t\telse      o.write_shift(4, sp[n[0]] != null && sp[n[0]] ? 0 : 1);\n\t});\n\treturn o;\n}\n\nfunction parse_BrtDVal(/*data, length, opts*/) {\n}\nfunction parse_BrtDVal14(/*data, length, opts*/) {\n}\n/* [MS-XLSB] 2.1.7.61 Worksheet */\nfunction parse_ws_bin(data, _opts, idx, rels, wb/*:WBWBProps*/, themes, styles)/*:Worksheet*/ {\n\tif(!data) return data;\n\tvar opts = _opts || {};\n\tif(!rels) rels = {'!id':{}};\n\tif(DENSE != null && opts.dense == null) opts.dense = DENSE;\n\tvar s/*:Worksheet*/ = (opts.dense ? [] : {});\n\n\tvar ref;\n\tvar refguess = {s: {r:2000000, c:2000000}, e: {r:0, c:0} };\n\n\tvar state/*:Array<string>*/ = [];\n\tvar pass = false, end = false;\n\tvar row, p, cf, R, C, addr, sstr, rr, cell/*:Cell*/;\n\tvar merges/*:Array<Range>*/ = [];\n\topts.biff = 12;\n\topts['!row'] = 0;\n\n\tvar ai = 0, af = false;\n\n\tvar arrayf/*:Array<[Range, string]>*/ = [];\n\tvar sharedf = {};\n\tvar supbooks = opts.supbooks || /*::(*/wb/*:: :any)*/.supbooks || ([[]]/*:any*/);\n\tsupbooks.sharedf = sharedf;\n\tsupbooks.arrayf = arrayf;\n\tsupbooks.SheetNames = wb.SheetNames || wb.Sheets.map(function(x) { return x.name; });\n\tif(!opts.supbooks) {\n\t\topts.supbooks = supbooks;\n\t\tif(wb.Names) for(var i = 0; i < wb.Names.length; ++i) supbooks[0][i+1] = wb.Names[i];\n\t}\n\n\tvar colinfo/*:Array<ColInfo>*/ = [], rowinfo/*:Array<RowInfo>*/ = [];\n\tvar seencol = false;\n\n\tXLSBRecordEnum[0x0010] = { n:\"BrtShortReal\", f:parse_BrtShortReal };\n\n\tvar cm, vm;\n\n\trecordhopper(data, function ws_parse(val, RR, RT) {\n\t\tif(end) return;\n\t\tswitch(RT) {\n\t\t\tcase 0x0094: /* 'BrtWsDim' */\n\t\t\t\tref = val; break;\n\t\t\tcase 0x0000: /* 'BrtRowHdr' */\n\t\t\t\trow = val;\n\t\t\t\tif(opts.sheetRows && opts.sheetRows <= row.r) end=true;\n\t\t\t\trr = encode_row(R = row.r);\n\t\t\t\topts['!row'] = row.r;\n\t\t\t\tif(val.hidden || val.hpt || val.level != null) {\n\t\t\t\t\tif(val.hpt) val.hpx = pt2px(val.hpt);\n\t\t\t\t\trowinfo[val.r] = val;\n\t\t\t\t}\n\t\t\t\tbreak;\n\n\t\t\tcase 0x0002: /* 'BrtCellRk' */\n\t\t\tcase 0x0003: /* 'BrtCellError' */\n\t\t\tcase 0x0004: /* 'BrtCellBool' */\n\t\t\tcase 0x0005: /* 'BrtCellReal' */\n\t\t\tcase 0x0006: /* 'BrtCellSt' */\n\t\t\tcase 0x0007: /* 'BrtCellIsst' */\n\t\t\tcase 0x0008: /* 'BrtFmlaString' */\n\t\t\tcase 0x0009: /* 'BrtFmlaNum' */\n\t\t\tcase 0x000A: /* 'BrtFmlaBool' */\n\t\t\tcase 0x000B: /* 'BrtFmlaError' */\n\t\t\tcase 0x000D: /* 'BrtShortRk' */\n\t\t\tcase 0x000E: /* 'BrtShortError' */\n\t\t\tcase 0x000F: /* 'BrtShortBool' */\n\t\t\tcase 0x0010: /* 'BrtShortReal' */\n\t\t\tcase 0x0011: /* 'BrtShortSt' */\n\t\t\tcase 0x0012: /* 'BrtShortIsst' */\n\t\t\tcase 0x003E: /* 'BrtCellRString' */\n\t\t\t\tp = ({t:val[2]}/*:any*/);\n\t\t\t\tswitch(val[2]) {\n\t\t\t\t\tcase 'n': p.v = val[1]; break;\n\t\t\t\t\tcase 's': sstr = strs[val[1]]; p.v = sstr.t; p.r = sstr.r; break;\n\t\t\t\t\tcase 'b': p.v = val[1] ? true : false; break;\n\t\t\t\t\tcase 'e': p.v = val[1]; if(opts.cellText !== false) p.w = BErr[p.v]; break;\n\t\t\t\t\tcase 'str': p.t = 's'; p.v = val[1]; break;\n\t\t\t\t\tcase 'is': p.t = 's'; p.v = val[1].t; break;\n\t\t\t\t}\n\t\t\t\tif((cf = styles.CellXf[val[0].iStyleRef])) safe_format(p,cf.numFmtId,null,opts, themes, styles);\n\t\t\t\tC = val[0].c == -1 ? C + 1 : val[0].c;\n\t\t\t\tif(opts.dense) { if(!s[R]) s[R] = []; s[R][C] = p; }\n\t\t\t\telse s[encode_col(C) + rr] = p;\n\t\t\t\tif(opts.cellFormula) {\n\t\t\t\t\taf = false;\n\t\t\t\t\tfor(ai = 0; ai < arrayf.length; ++ai) {\n\t\t\t\t\t\tvar aii = arrayf[ai];\n\t\t\t\t\t\tif(row.r >= aii[0].s.r && row.r <= aii[0].e.r)\n\t\t\t\t\t\t\tif(C >= aii[0].s.c && C <= aii[0].e.c) {\n\t\t\t\t\t\t\t\tp.F = encode_range(aii[0]); af = true;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tif(!af && val.length > 3) p.f = val[3];\n\t\t\t\t}\n\n\t\t\t\tif(refguess.s.r > row.r) refguess.s.r = row.r;\n\t\t\t\tif(refguess.s.c > C) refguess.s.c = C;\n\t\t\t\tif(refguess.e.r < row.r) refguess.e.r = row.r;\n\t\t\t\tif(refguess.e.c < C) refguess.e.c = C;\n\t\t\t\tif(opts.cellDates && cf && p.t == 'n' && fmt_is_date(table_fmt[cf.numFmtId])) {\n\t\t\t\t\tvar _d = SSF_parse_date_code(p.v); if(_d) { p.t = 'd'; p.v = new Date(_d.y, _d.m-1,_d.d,_d.H,_d.M,_d.S,_d.u); }\n\t\t\t\t}\n\t\t\t\tif(cm) {\n\t\t\t\t\tif(cm.type == 'XLDAPR') p.D = true;\n\t\t\t\t\tcm = void 0;\n\t\t\t\t}\n\t\t\t\tif(vm) vm = void 0;\n\t\t\t\tbreak;\n\n\t\t\tcase 0x0001: /* 'BrtCellBlank' */\n\t\t\tcase 0x000C: /* 'BrtShortBlank' */\n\t\t\t\tif(!opts.sheetStubs || pass) break;\n\t\t\t\tp = ({t:'z',v:void 0}/*:any*/);\n\t\t\t\tC = val[0].c == -1 ? C + 1 : val[0].c;\n\t\t\t\tif(opts.dense) { if(!s[R]) s[R] = []; s[R][C] = p; }\n\t\t\t\telse s[encode_col(C) + rr] = p;\n\t\t\t\tif(refguess.s.r > row.r) refguess.s.r = row.r;\n\t\t\t\tif(refguess.s.c > C) refguess.s.c = C;\n\t\t\t\tif(refguess.e.r < row.r) refguess.e.r = row.r;\n\t\t\t\tif(refguess.e.c < C) refguess.e.c = C;\n\t\t\t\tif(cm) {\n\t\t\t\t\tif(cm.type == 'XLDAPR') p.D = true;\n\t\t\t\t\tcm = void 0;\n\t\t\t\t}\n\t\t\t\tif(vm) vm = void 0;\n\t\t\t\tbreak;\n\n\t\t\tcase 0x00B0: /* 'BrtMergeCell' */\n\t\t\t\tmerges.push(val); break;\n\n\t\t\tcase 0x0031: { /* 'BrtCellMeta' */\n\t\t\t\tcm = ((opts.xlmeta||{}).Cell||[])[val-1];\n\t\t\t} break;\n\n\t\t\tcase 0x01EE: /* 'BrtHLink' */\n\t\t\t\tvar rel = rels['!id'][val.relId];\n\t\t\t\tif(rel) {\n\t\t\t\t\tval.Target = rel.Target;\n\t\t\t\t\tif(val.loc) val.Target += \"#\"+val.loc;\n\t\t\t\t\tval.Rel = rel;\n\t\t\t\t} else if(val.relId == '') {\n\t\t\t\t\tval.Target = \"#\" + val.loc;\n\t\t\t\t}\n\t\t\t\tfor(R=val.rfx.s.r;R<=val.rfx.e.r;++R) for(C=val.rfx.s.c;C<=val.rfx.e.c;++C) {\n\t\t\t\t\tif(opts.dense) {\n\t\t\t\t\t\tif(!s[R]) s[R] = [];\n\t\t\t\t\t\tif(!s[R][C]) s[R][C] = {t:'z',v:undefined};\n\t\t\t\t\t\ts[R][C].l = val;\n\t\t\t\t\t} else {\n\t\t\t\t\t\taddr = encode_cell({c:C,r:R});\n\t\t\t\t\t\tif(!s[addr]) s[addr] = {t:'z',v:undefined};\n\t\t\t\t\t\ts[addr].l = val;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tbreak;\n\n\t\t\tcase 0x01AA: /* 'BrtArrFmla' */\n\t\t\t\tif(!opts.cellFormula) break;\n\t\t\t\tarrayf.push(val);\n\t\t\t\tcell = ((opts.dense ? s[R][C] : s[encode_col(C) + rr])/*:any*/);\n\t\t\t\tcell.f = stringify_formula(val[1], refguess, {r:row.r, c:C}, supbooks, opts);\n\t\t\t\tcell.F = encode_range(val[0]);\n\t\t\t\tbreak;\n\t\t\tcase 0x01AB: /* 'BrtShrFmla' */\n\t\t\t\tif(!opts.cellFormula) break;\n\t\t\t\tsharedf[encode_cell(val[0].s)] = val[1];\n\t\t\t\tcell = (opts.dense ? s[R][C] : s[encode_col(C) + rr]);\n\t\t\t\tcell.f = stringify_formula(val[1], refguess, {r:row.r, c:C}, supbooks, opts);\n\t\t\t\tbreak;\n\n\t\t\t/* identical to 'ColInfo' in XLS */\n\t\t\tcase 0x003C: /* 'BrtColInfo' */\n\t\t\t\tif(!opts.cellStyles) break;\n\t\t\t\twhile(val.e >= val.s) {\n\t\t\t\t\tcolinfo[val.e--] = { width: val.w/256, hidden: !!(val.flags & 0x01), level: val.level };\n\t\t\t\t\tif(!seencol) { seencol = true; find_mdw_colw(val.w/256); }\n\t\t\t\t\tprocess_col(colinfo[val.e+1]);\n\t\t\t\t}\n\t\t\t\tbreak;\n\n\t\t\tcase 0x00A1: /* 'BrtBeginAFilter' */\n\t\t\t\ts['!autofilter'] = { ref:encode_range(val) };\n\t\t\t\tbreak;\n\n\t\t\tcase 0x01DC: /* 'BrtMargins' */\n\t\t\t\ts['!margins'] = val;\n\t\t\t\tbreak;\n\n\t\t\tcase 0x0093: /* 'BrtWsProp' */\n\t\t\t\tif(!wb.Sheets[idx]) wb.Sheets[idx] = {};\n\t\t\t\tif(val.name) wb.Sheets[idx].CodeName = val.name;\n\t\t\t\tif(val.above || val.left) s['!outline'] = { above: val.above, left: val.left };\n\t\t\t\tbreak;\n\n\t\t\tcase 0x0089: /* 'BrtBeginWsView' */\n\t\t\t\tif(!wb.Views) wb.Views = [{}];\n\t\t\t\tif(!wb.Views[0]) wb.Views[0] = {};\n\t\t\t\tif(val.RTL) wb.Views[0].RTL = true;\n\t\t\t\tbreak;\n\n\t\t\tcase 0x01E5: /* 'BrtWsFmtInfo' */\n\t\t\t\tbreak;\n\n\t\t\tcase 0x0040: /* 'BrtDVal' */\n\t\t\tcase 0x041D: /* 'BrtDVal14' */\n\t\t\t\tbreak;\n\n\t\t\tcase 0x0097: /* 'BrtPane' */\n\t\t\t\tbreak;\n\t\t\tcase 0x0098: /* 'BrtSel' */\n\t\t\tcase 0x00AF: /* 'BrtAFilterDateGroupItem' */\n\t\t\tcase 0x0284: /* 'BrtActiveX' */\n\t\t\tcase 0x0271: /* 'BrtBigName' */\n\t\t\tcase 0x0232: /* 'BrtBkHim' */\n\t\t\tcase 0x018C: /* 'BrtBrk' */\n\t\t\tcase 0x0458: /* 'BrtCFIcon' */\n\t\t\tcase 0x047A: /* 'BrtCFRuleExt' */\n\t\t\tcase 0x01D7: /* 'BrtCFVO' */\n\t\t\tcase 0x041A: /* 'BrtCFVO14' */\n\t\t\tcase 0x0289: /* 'BrtCellIgnoreEC' */\n\t\t\tcase 0x0451: /* 'BrtCellIgnoreEC14' */\n\t\t\tcase 0x024D: /* 'BrtCellSmartTagProperty' */\n\t\t\tcase 0x025F: /* 'BrtCellWatch' */\n\t\t\tcase 0x0234: /* 'BrtColor' */\n\t\t\tcase 0x041F: /* 'BrtColor14' */\n\t\t\tcase 0x00A8: /* 'BrtColorFilter' */\n\t\t\tcase 0x00AE: /* 'BrtCustomFilter' */\n\t\t\tcase 0x049C: /* 'BrtCustomFilter14' */\n\t\t\tcase 0x01F3: /* 'BrtDRef' */\n\t\t\tcase 0x01FB: /* 'BrtDXF' */\n\t\t\tcase 0x0226: /* 'BrtDrawing' */\n\t\t\tcase 0x00AB: /* 'BrtDynamicFilter' */\n\t\t\tcase 0x00A7: /* 'BrtFilter' */\n\t\t\tcase 0x0499: /* 'BrtFilter14' */\n\t\t\tcase 0x00A9: /* 'BrtIconFilter' */\n\t\t\tcase 0x049D: /* 'BrtIconFilter14' */\n\t\t\tcase 0x0227: /* 'BrtLegacyDrawing' */\n\t\t\tcase 0x0228: /* 'BrtLegacyDrawingHF' */\n\t\t\tcase 0x0295: /* 'BrtListPart' */\n\t\t\tcase 0x027F: /* 'BrtOleObject' */\n\t\t\tcase 0x01DE: /* 'BrtPageSetup' */\n\t\t\tcase 0x0219: /* 'BrtPhoneticInfo' */\n\t\t\tcase 0x01DD: /* 'BrtPrintOptions' */\n\t\t\tcase 0x0218: /* 'BrtRangeProtection' */\n\t\t\tcase 0x044F: /* 'BrtRangeProtection14' */\n\t\t\tcase 0x02A8: /* 'BrtRangeProtectionIso' */\n\t\t\tcase 0x0450: /* 'BrtRangeProtectionIso14' */\n\t\t\tcase 0x0400: /* 'BrtRwDescent' */\n\t\t\tcase 0x0297: /* 'BrtSheetCalcProp' */\n\t\t\tcase 0x0217: /* 'BrtSheetProtection' */\n\t\t\tcase 0x02A6: /* 'BrtSheetProtectionIso' */\n\t\t\tcase 0x01F8: /* 'BrtSlc' */\n\t\t\tcase 0x0413: /* 'BrtSparkline' */\n\t\t\tcase 0x01AC: /* 'BrtTable' */\n\t\t\tcase 0x00AA: /* 'BrtTop10Filter' */\n\t\t\tcase 0x0C00: /* 'BrtUid' */\n\t\t\tcase 0x0032: /* 'BrtValueMeta' */\n\t\t\tcase 0x0816: /* 'BrtWebExtension' */\n\t\t\tcase 0x0415: /* 'BrtWsFmtInfoEx14' */\n\t\t\t\tbreak;\n\n\t\t\tcase 0x0023: /* 'BrtFRTBegin' */\n\t\t\t\tpass = true; break;\n\t\t\tcase 0x0024: /* 'BrtFRTEnd' */\n\t\t\t\tpass = false; break;\n\t\t\tcase 0x0025: /* 'BrtACBegin' */\n\t\t\t\tstate.push(RT); pass = true; break;\n\t\t\tcase 0x0026: /* 'BrtACEnd' */\n\t\t\t\tstate.pop(); pass = false; break;\n\n\t\t\tdefault:\n\t\t\t\tif(RR.T){/* empty */}\n\t\t\t\telse if(!pass || opts.WTF) throw new Error(\"Unexpected record 0x\" + RT.toString(16));\n\t\t}\n\t}, opts);\n\n\tdelete opts.supbooks;\n\tdelete opts['!row'];\n\n\tif(!s[\"!ref\"] && (refguess.s.r < 2000000 || ref && (ref.e.r > 0 || ref.e.c > 0 || ref.s.r > 0 || ref.s.c > 0))) s[\"!ref\"] = encode_range(ref || refguess);\n\tif(opts.sheetRows && s[\"!ref\"]) {\n\t\tvar tmpref = safe_decode_range(s[\"!ref\"]);\n\t\tif(opts.sheetRows <= +tmpref.e.r) {\n\t\t\ttmpref.e.r = opts.sheetRows - 1;\n\t\t\tif(tmpref.e.r > refguess.e.r) tmpref.e.r = refguess.e.r;\n\t\t\tif(tmpref.e.r < tmpref.s.r) tmpref.s.r = tmpref.e.r;\n\t\t\tif(tmpref.e.c > refguess.e.c) tmpref.e.c = refguess.e.c;\n\t\t\tif(tmpref.e.c < tmpref.s.c) tmpref.s.c = tmpref.e.c;\n\t\t\ts[\"!fullref\"] = s[\"!ref\"];\n\t\t\ts[\"!ref\"] = encode_range(tmpref);\n\t\t}\n\t}\n\tif(merges.length > 0) s[\"!merges\"] = merges;\n\tif(colinfo.length > 0) s[\"!cols\"] = colinfo;\n\tif(rowinfo.length > 0) s[\"!rows\"] = rowinfo;\n\treturn s;\n}\n\n/* TODO: something useful -- this is a stub */\nfunction write_ws_bin_cell(ba/*:BufArray*/, cell/*:Cell*/, R/*:number*/, C/*:number*/, opts, ws/*:Worksheet*/, last_seen/*:boolean*/)/*:boolean*/ {\n\tif(cell.v === undefined) return false;\n\tvar vv = \"\";\n\tswitch(cell.t) {\n\t\tcase 'b': vv = cell.v ? \"1\" : \"0\"; break;\n\t\tcase 'd': // no BrtCellDate :(\n\t\t\tcell = dup(cell);\n\t\t\tcell.z = cell.z || table_fmt[14];\n\t\t\tcell.v = datenum(parseDate(cell.v)); cell.t = 'n';\n\t\t\tbreak;\n\t\t/* falls through */\n\t\tcase 'n': case 'e': vv = ''+cell.v; break;\n\t\tdefault: vv = cell.v; break;\n\t}\n\tvar o/*:any*/ = ({r:R, c:C}/*:any*/);\n\t/* TODO: cell style */\n\to.s = get_cell_style(opts.cellXfs, cell, opts);\n\tif(cell.l) ws['!links'].push([encode_cell(o), cell.l]);\n\tif(cell.c) ws['!comments'].push([encode_cell(o), cell.c]);\n\tswitch(cell.t) {\n\t\tcase 's': case 'str':\n\t\t\tif(opts.bookSST) {\n\t\t\t\tvv = get_sst_id(opts.Strings, (cell.v/*:any*/), opts.revStrings);\n\t\t\t\to.t = \"s\"; o.v = vv;\n\t\t\t\tif(last_seen) write_record(ba, 0x0012 /* BrtShortIsst */, write_BrtShortIsst(cell, o));\n\t\t\t\telse write_record(ba, 0x0007 /* BrtCellIsst */, write_BrtCellIsst(cell, o));\n\t\t\t} else {\n\t\t\t\to.t = \"str\";\n\t\t\t\tif(last_seen) write_record(ba, 0x0011 /* BrtShortSt */, write_BrtShortSt(cell, o));\n\t\t\t\telse write_record(ba, 0x0006 /* BrtCellSt */, write_BrtCellSt(cell, o));\n\t\t\t}\n\t\t\treturn true;\n\t\tcase 'n':\n\t\t\t/* TODO: determine threshold for Real vs RK */\n\t\t\tif(cell.v == (cell.v | 0) && cell.v > -1000 && cell.v < 1000) {\n\t\t\t\tif(last_seen) write_record(ba, 0x000D /* BrtShortRk */, write_BrtShortRk(cell, o));\n\t\t\t\telse write_record(ba, 0x0002 /* BrtCellRk */, write_BrtCellRk(cell, o));\n\t\t\t} else {\n\t\t\t\tif(last_seen) write_record(ba, 0x0010 /* BrtShortReal */, write_BrtShortReal(cell, o));\n\t\t\t\telse write_record(ba, 0x0005 /* BrtCellReal */, write_BrtCellReal(cell, o));\n\t\t\t} return true;\n\t\tcase 'b':\n\t\t\to.t = \"b\";\n\t\t\tif(last_seen) write_record(ba, 0x000F /* BrtShortBool */, write_BrtShortBool(cell, o));\n\t\t\telse write_record(ba, 0x0004 /* BrtCellBool */, write_BrtCellBool(cell, o));\n\t\t\treturn true;\n\t\tcase 'e':\n\t\t\to.t = \"e\";\n\t\t\tif(last_seen) write_record(ba, 0x000E /* BrtShortError */, write_BrtShortError(cell, o));\n\t\t\telse write_record(ba, 0x0003 /* BrtCellError */, write_BrtCellError(cell, o));\n\t\t\treturn true;\n\t}\n\tif(last_seen) write_record(ba, 0x000C /* BrtShortBlank */, write_BrtShortBlank(cell, o));\n\telse write_record(ba, 0x0001 /* BrtCellBlank */, write_BrtCellBlank(cell, o));\n\treturn true;\n}\n\nfunction write_CELLTABLE(ba, ws/*:Worksheet*/, idx/*:number*/, opts/*::, wb:Workbook*/) {\n\tvar range = safe_decode_range(ws['!ref'] || \"A1\"), ref, rr = \"\", cols/*:Array<string>*/ = [];\n\twrite_record(ba, 0x0091 /* BrtBeginSheetData */);\n\tvar dense = Array.isArray(ws);\n\tvar cap = range.e.r;\n\tif(ws['!rows']) cap = Math.max(range.e.r, ws['!rows'].length - 1);\n\tfor(var R = range.s.r; R <= cap; ++R) {\n\t\trr = encode_row(R);\n\t\t/* [ACCELLTABLE] */\n\t\t/* BrtRowHdr */\n\t\twrite_row_header(ba, ws, range, R);\n\t\tvar last_seen = false;\n\t\tif(R <= range.e.r) for(var C = range.s.c; C <= range.e.c; ++C) {\n\t\t\t/* *16384CELL */\n\t\t\tif(R === range.s.r) cols[C] = encode_col(C);\n\t\t\tref = cols[C] + rr;\n\t\t\tvar cell = dense ? (ws[R]||[])[C] : ws[ref];\n\t\t\tif(!cell) { last_seen = false; continue; }\n\t\t\t/* write cell */\n\t\t\tlast_seen = write_ws_bin_cell(ba, cell, R, C, opts, ws, last_seen);\n\t\t}\n\t}\n\twrite_record(ba, 0x0092 /* BrtEndSheetData */);\n}\n\nfunction write_MERGECELLS(ba, ws/*:Worksheet*/) {\n\tif(!ws || !ws['!merges']) return;\n\twrite_record(ba, 0x00B1 /* BrtBeginMergeCells */, write_BrtBeginMergeCells(ws['!merges'].length));\n\tws['!merges'].forEach(function(m) { write_record(ba, 0x00B0 /* BrtMergeCell */, write_BrtMergeCell(m)); });\n\twrite_record(ba, 0x00B2 /* BrtEndMergeCells */);\n}\n\nfunction write_COLINFOS(ba, ws/*:Worksheet*//*::, idx:number, opts, wb:Workbook*/) {\n\tif(!ws || !ws['!cols']) return;\n\twrite_record(ba, 0x0186 /* BrtBeginColInfos */);\n\tws['!cols'].forEach(function(m, i) { if(m) write_record(ba, 0x003C /* 'BrtColInfo' */, write_BrtColInfo(i, m)); });\n\twrite_record(ba, 0x0187 /* BrtEndColInfos */);\n}\n\nfunction write_IGNOREECS(ba, ws/*:Worksheet*/) {\n\tif(!ws || !ws['!ref']) return;\n\twrite_record(ba, 0x0288 /* BrtBeginCellIgnoreECs */);\n\twrite_record(ba, 0x0289 /* BrtCellIgnoreEC */, write_BrtCellIgnoreEC(safe_decode_range(ws['!ref'])));\n\twrite_record(ba, 0x028A /* BrtEndCellIgnoreECs */);\n}\n\nfunction write_HLINKS(ba, ws/*:Worksheet*/, rels) {\n\t/* *BrtHLink */\n\tws['!links'].forEach(function(l) {\n\t\tif(!l[1].Target) return;\n\t\tvar rId = add_rels(rels, -1, l[1].Target.replace(/#.*$/, \"\"), RELS.HLINK);\n\t\twrite_record(ba, 0x01EE /* BrtHLink */, write_BrtHLink(l, rId));\n\t});\n\tdelete ws['!links'];\n}\nfunction write_LEGACYDRAWING(ba, ws/*:Worksheet*/, idx/*:number*/, rels) {\n\t/* [BrtLegacyDrawing] */\n\tif(ws['!comments'].length > 0) {\n\t\tvar rId = add_rels(rels, -1, \"../drawings/vmlDrawing\" + (idx+1) + \".vml\", RELS.VML);\n\t\twrite_record(ba, 0x0227 /* BrtLegacyDrawing */, write_RelID(\"rId\" + rId));\n\t\tws['!legacy'] = rId;\n\t}\n}\n\nfunction write_AUTOFILTER(ba, ws, wb, idx) {\n\tif(!ws['!autofilter']) return;\n\tvar data = ws['!autofilter'];\n\tvar ref = typeof data.ref === \"string\" ? data.ref : encode_range(data.ref);\n\n\t/* Update FilterDatabase defined name for the worksheet */\n\tif(!wb.Workbook) wb.Workbook = ({Sheets:[]}/*:any*/);\n\tif(!wb.Workbook.Names) wb.Workbook.Names = [];\n\tvar names/*: Array<any> */ = wb.Workbook.Names;\n\tvar range = decode_range(ref);\n\tif(range.s.r == range.e.r) { range.e.r = decode_range(ws[\"!ref\"]).e.r; ref = encode_range(range); }\n\tfor(var i = 0; i < names.length; ++i) {\n\t\tvar name = names[i];\n\t\tif(name.Name != '_xlnm._FilterDatabase') continue;\n\t\tif(name.Sheet != idx) continue;\n\t\tname.Ref = \"'\" + wb.SheetNames[idx] + \"'!\" + ref; break;\n\t}\n\tif(i == names.length) names.push({ Name: '_xlnm._FilterDatabase', Sheet: idx, Ref: \"'\" + wb.SheetNames[idx] + \"'!\" + ref  });\n\n\twrite_record(ba, 0x00A1 /* BrtBeginAFilter */, write_UncheckedRfX(safe_decode_range(ref)));\n\t/* *FILTERCOLUMN */\n\t/* [SORTSTATE] */\n\t/* BrtEndAFilter */\n\twrite_record(ba, 0x00A2 /* BrtEndAFilter */);\n}\n\nfunction write_WSVIEWS2(ba, ws, Workbook) {\n\twrite_record(ba, 0x0085 /* BrtBeginWsViews */);\n\t{ /* 1*WSVIEW2 */\n\t\t/* [ACUID] */\n\t\twrite_record(ba, 0x0089 /* BrtBeginWsView */, write_BrtBeginWsView(ws, Workbook));\n\t\t/* [BrtPane] */\n\t\t/* *4BrtSel */\n\t\t/* *4SXSELECT */\n\t\t/* *FRT */\n\t\twrite_record(ba, 0x008A /* BrtEndWsView */);\n\t}\n\t/* *FRT */\n\twrite_record(ba, 0x0086 /* BrtEndWsViews */);\n}\n\nfunction write_WSFMTINFO(/*::ba, ws*/) {\n\t/* [ACWSFMTINFO] */\n\t// write_record(ba, 0x01E5 /* BrtWsFmtInfo */, write_BrtWsFmtInfo(ws));\n}\n\nfunction write_SHEETPROTECT(ba, ws) {\n\tif(!ws['!protect']) return;\n\t/* [BrtSheetProtectionIso] */\n\twrite_record(ba, 0x0217 /* BrtSheetProtection */, write_BrtSheetProtection(ws['!protect']));\n}\n\nfunction write_ws_bin(idx/*:number*/, opts, wb/*:Workbook*/, rels) {\n\tvar ba = buf_array();\n\tvar s = wb.SheetNames[idx], ws = wb.Sheets[s] || {};\n\tvar c/*:string*/ = s; try { if(wb && wb.Workbook) c = wb.Workbook.Sheets[idx].CodeName || c; } catch(e) {}\n\tvar r = safe_decode_range(ws['!ref'] || \"A1\");\n\tif(r.e.c > 0x3FFF || r.e.r > 0xFFFFF) {\n\t\tif(opts.WTF) throw new Error(\"Range \" + (ws['!ref'] || \"A1\") + \" exceeds format limit A1:XFD1048576\");\n\t\tr.e.c = Math.min(r.e.c, 0x3FFF);\n\t\tr.e.r = Math.min(r.e.c, 0xFFFFF);\n\t}\n\tws['!links'] = [];\n\t/* passed back to write_zip and removed there */\n\tws['!comments'] = [];\n\twrite_record(ba, 0x0081 /* BrtBeginSheet */);\n\tif(wb.vbaraw || ws['!outline']) write_record(ba, 0x0093 /* BrtWsProp */, write_BrtWsProp(c, ws['!outline']));\n\twrite_record(ba, 0x0094 /* BrtWsDim */, write_BrtWsDim(r));\n\twrite_WSVIEWS2(ba, ws, wb.Workbook);\n\twrite_WSFMTINFO(ba, ws);\n\twrite_COLINFOS(ba, ws, idx, opts, wb);\n\twrite_CELLTABLE(ba, ws, idx, opts, wb);\n\t/* [BrtSheetCalcProp] */\n\twrite_SHEETPROTECT(ba, ws);\n\t/* *([BrtRangeProtectionIso] BrtRangeProtection) */\n\t/* [SCENMAN] */\n\twrite_AUTOFILTER(ba, ws, wb, idx);\n\t/* [SORTSTATE] */\n\t/* [DCON] */\n\t/* [USERSHVIEWS] */\n\twrite_MERGECELLS(ba, ws);\n\t/* [BrtPhoneticInfo] */\n\t/* *CONDITIONALFORMATTING */\n\t/* [DVALS] */\n\twrite_HLINKS(ba, ws, rels);\n\t/* [BrtPrintOptions] */\n\tif(ws['!margins']) write_record(ba, 0x01DC /* BrtMargins */, write_BrtMargins(ws['!margins']));\n\t/* [BrtPageSetup] */\n\t/* [HEADERFOOTER] */\n\t/* [RWBRK] */\n\t/* [COLBRK] */\n\t/* *BrtBigName */\n\t/* [CELLWATCHES] */\n\tif(!opts || opts.ignoreEC || (opts.ignoreEC == (void 0))) write_IGNOREECS(ba, ws);\n\t/* [SMARTTAGS] */\n\t/* [BrtDrawing] */\n\twrite_LEGACYDRAWING(ba, ws, idx, rels);\n\t/* [BrtLegacyDrawingHF] */\n\t/* [BrtBkHim] */\n\t/* [OLEOBJECTS] */\n\t/* [ACTIVEXCONTROLS] */\n\t/* [WEBPUBITEMS] */\n\t/* [LISTPARTS] */\n\t/* FRTWORKSHEET */\n\twrite_record(ba, 0x0082 /* BrtEndSheet */);\n\treturn ba.end();\n}\nfunction parse_Cache(data/*:string*/)/*:[Array<number|string>, string, ?string]*/ {\n\tvar col/*:Array<number|string>*/ = [];\n\tvar num = data.match(/^<c:numCache>/);\n\tvar f;\n\n\t/* 21.2.2.150 pt CT_NumVal */\n\t(data.match(/<c:pt idx=\"(\\d*)\">(.*?)<\\/c:pt>/mg)||[]).forEach(function(pt) {\n\t\tvar q = pt.match(/<c:pt idx=\"(\\d*?)\"><c:v>(.*)<\\/c:v><\\/c:pt>/);\n\t\tif(!q) return;\n\t\tcol[+q[1]] = num ? +q[2] : q[2];\n\t});\n\n\t/* 21.2.2.71 formatCode CT_Xstring */\n\tvar nf = unescapexml((data.match(/<c:formatCode>([\\s\\S]*?)<\\/c:formatCode>/) || [\"\",\"General\"])[1]);\n\n\t(data.match(/<c:f>(.*?)<\\/c:f>/mg)||[]).forEach(function(F) { f = F.replace(/<.*?>/g,\"\"); });\n\n\treturn [col, nf, f];\n}\n\n/* 21.2 DrawingML - Charts */\nfunction parse_chart(data/*:?string*/, name/*:string*/, opts, rels, wb, csheet) {\n\tvar cs/*:Worksheet*/ = ((csheet || {\"!type\":\"chart\"})/*:any*/);\n\tif(!data) return csheet;\n\t/* 21.2.2.27 chart CT_Chart */\n\n\tvar C = 0, R = 0, col = \"A\";\n\tvar refguess = {s: {r:2000000, c:2000000}, e: {r:0, c:0} };\n\n\t/* 21.2.2.120 numCache CT_NumData */\n\t(data.match(/<c:numCache>[\\s\\S]*?<\\/c:numCache>/gm)||[]).forEach(function(nc) {\n\t\tvar cache = parse_Cache(nc);\n\t\trefguess.s.r = refguess.s.c = 0;\n\t\trefguess.e.c = C;\n\t\tcol = encode_col(C);\n\t\tcache[0].forEach(function(n,i) {\n\t\t\tcs[col + encode_row(i)] = {t:'n', v:n, z:cache[1] };\n\t\t\tR = i;\n\t\t});\n\t\tif(refguess.e.r < R) refguess.e.r = R;\n\t\t++C;\n\t});\n\tif(C > 0) cs[\"!ref\"] = encode_range(refguess);\n\treturn cs;\n}\n/* 18.3 Worksheets also covers Chartsheets */\nfunction parse_cs_xml(data/*:?string*/, opts, idx/*:number*/, rels, wb/*::, themes, styles*/)/*:Worksheet*/ {\n\tif(!data) return data;\n\t/* 18.3.1.12 chartsheet CT_ChartSheet */\n\tif(!rels) rels = {'!id':{}};\n\tvar s = ({'!type':\"chart\", '!drawel':null, '!rel':\"\"}/*:any*/);\n\tvar m;\n\n\t/* 18.3.1.83 sheetPr CT_ChartsheetPr */\n\tvar sheetPr = data.match(sheetprregex);\n\tif(sheetPr) parse_ws_xml_sheetpr(sheetPr[0], s, wb, idx);\n\n\t/* 18.3.1.36 drawing CT_Drawing */\n\tif((m = data.match(/drawing r:id=\"(.*?)\"/))) s['!rel'] = m[1];\n\n\tif(rels['!id'][s['!rel']]) s['!drawel'] = rels['!id'][s['!rel']];\n\treturn s;\n}\nfunction write_cs_xml(idx/*:number*/, opts, wb/*:Workbook*/, rels)/*:string*/ {\n\tvar o = [XML_HEADER, writextag('chartsheet', null, {\n\t\t'xmlns': XMLNS_main[0],\n\t\t'xmlns:r': XMLNS.r\n\t})];\n\to[o.length] = writextag(\"drawing\", null, {\"r:id\": \"rId1\"});\n\tadd_rels(rels, -1, \"../drawings/drawing\" + (idx+1) + \".xml\", RELS.DRAW);\n\tif(o.length>2) { o[o.length] = ('</chartsheet>'); o[1]=o[1].replace(\"/>\",\">\"); }\n\treturn o.join(\"\");\n}\n\n/* [MS-XLSB] 2.4.331 BrtCsProp */\nfunction parse_BrtCsProp(data, length/*:number*/) {\n\tdata.l += 10;\n\tvar name = parse_XLWideString(data, length - 10);\n\treturn { name: name };\n}\n\n/* [MS-XLSB] 2.1.7.7 Chart Sheet */\nfunction parse_cs_bin(data, opts, idx/*:number*/, rels, wb/*::, themes, styles*/)/*:Worksheet*/ {\n\tif(!data) return data;\n\tif(!rels) rels = {'!id':{}};\n\tvar s = {'!type':\"chart\", '!drawel':null, '!rel':\"\"};\n\tvar state/*:Array<string>*/ = [];\n\tvar pass = false;\n\trecordhopper(data, function cs_parse(val, R, RT) {\n\t\tswitch(RT) {\n\n\t\t\tcase 0x0226: /* 'BrtDrawing' */\n\t\t\t\ts['!rel'] = val; break;\n\n\t\t\tcase 0x028B: /* 'BrtCsProp' */\n\t\t\t\tif(!wb.Sheets[idx]) wb.Sheets[idx] = {};\n\t\t\t\tif(val.name) wb.Sheets[idx].CodeName = val.name;\n\t\t\t\tbreak;\n\n\t\t\tcase 0x0232: /* 'BrtBkHim' */\n\t\t\tcase 0x028C: /* 'BrtCsPageSetup' */\n\t\t\tcase 0x029D: /* 'BrtCsProtection' */\n\t\t\tcase 0x02A7: /* 'BrtCsProtectionIso' */\n\t\t\tcase 0x0227: /* 'BrtLegacyDrawing' */\n\t\t\tcase 0x0228: /* 'BrtLegacyDrawingHF' */\n\t\t\tcase 0x01DC: /* 'BrtMargins' */\n\t\t\tcase 0x0C00: /* 'BrtUid' */\n\t\t\t\tbreak;\n\n\t\t\tcase 0x0023: /* 'BrtFRTBegin' */\n\t\t\t\tpass = true; break;\n\t\t\tcase 0x0024: /* 'BrtFRTEnd' */\n\t\t\t\tpass = false; break;\n\t\t\tcase 0x0025: /* 'BrtACBegin' */\n\t\t\t\tstate.push(RT); break;\n\t\t\tcase 0x0026: /* 'BrtACEnd' */\n\t\t\t\tstate.pop(); break;\n\n\t\t\tdefault:\n\t\t\t\tif(R.T > 0) state.push(RT);\n\t\t\t\telse if(R.T < 0) state.pop();\n\t\t\t\telse if(!pass || opts.WTF) throw new Error(\"Unexpected record 0x\" + RT.toString(16));\n\t\t}\n\t}, opts);\n\n\tif(rels['!id'][s['!rel']]) s['!drawel'] = rels['!id'][s['!rel']];\n\treturn s;\n}\nfunction write_cs_bin(/*::idx:number, opts, wb:Workbook, rels*/) {\n\tvar ba = buf_array();\n\twrite_record(ba, 0x0081 /* BrtBeginSheet */);\n\t/* [BrtCsProp] */\n\t/* CSVIEWS */\n\t/* [[BrtCsProtectionIso] BrtCsProtection] */\n\t/* [USERCSVIEWS] */\n\t/* [BrtMargins] */\n\t/* [BrtCsPageSetup] */\n\t/* [HEADERFOOTER] */\n\t/* BrtDrawing */\n\t/* [BrtLegacyDrawing] */\n\t/* [BrtLegacyDrawingHF] */\n\t/* [BrtBkHim] */\n\t/* [WEBPUBITEMS] */\n\t/* FRTCHARTSHEET */\n\twrite_record(ba, 0x0082 /* BrtEndSheet */);\n\treturn ba.end();\n}\n/* 18.2.28 (CT_WorkbookProtection) Defaults */\nvar WBPropsDef = [\n\t['allowRefreshQuery',           false, \"bool\"],\n\t['autoCompressPictures',        true,  \"bool\"],\n\t['backupFile',                  false, \"bool\"],\n\t['checkCompatibility',          false, \"bool\"],\n\t['CodeName',                    ''],\n\t['date1904',                    false, \"bool\"],\n\t['defaultThemeVersion',         0,      \"int\"],\n\t['filterPrivacy',               false, \"bool\"],\n\t['hidePivotFieldList',          false, \"bool\"],\n\t['promptedSolutions',           false, \"bool\"],\n\t['publishItems',                false, \"bool\"],\n\t['refreshAllConnections',       false, \"bool\"],\n\t['saveExternalLinkValues',      true,  \"bool\"],\n\t['showBorderUnselectedTables',  true,  \"bool\"],\n\t['showInkAnnotation',           true,  \"bool\"],\n\t['showObjects',                 'all'],\n\t['showPivotChartFilter',        false, \"bool\"],\n\t['updateLinks', 'userSet']\n];\n\n/* 18.2.30 (CT_BookView) Defaults */\nvar WBViewDef = [\n\t['activeTab',                   0,      \"int\"],\n\t['autoFilterDateGrouping',      true,  \"bool\"],\n\t['firstSheet',                  0,      \"int\"],\n\t['minimized',                   false, \"bool\"],\n\t['showHorizontalScroll',        true,  \"bool\"],\n\t['showSheetTabs',               true,  \"bool\"],\n\t['showVerticalScroll',          true,  \"bool\"],\n\t['tabRatio',                    600,    \"int\"],\n\t['visibility',                  'visible']\n\t//window{Height,Width}, {x,y}Window\n];\n\n/* 18.2.19 (CT_Sheet) Defaults */\nvar SheetDef = [\n\t//['state', 'visible']\n];\n\n/* 18.2.2  (CT_CalcPr) Defaults */\nvar CalcPrDef = [\n\t['calcCompleted', 'true'],\n\t['calcMode', 'auto'],\n\t['calcOnSave', 'true'],\n\t['concurrentCalc', 'true'],\n\t['fullCalcOnLoad', 'false'],\n\t['fullPrecision', 'true'],\n\t['iterate', 'false'],\n\t['iterateCount', '100'],\n\t['iterateDelta', '0.001'],\n\t['refMode', 'A1']\n];\n\n/* 18.2.3 (CT_CustomWorkbookView) Defaults */\n/*var CustomWBViewDef = [\n\t['autoUpdate', 'false'],\n\t['changesSavedWin', 'false'],\n\t['includeHiddenRowCol', 'true'],\n\t['includePrintSettings', 'true'],\n\t['maximized', 'false'],\n\t['minimized', 'false'],\n\t['onlySync', 'false'],\n\t['personalView', 'false'],\n\t['showComments', 'commIndicator'],\n\t['showFormulaBar', 'true'],\n\t['showHorizontalScroll', 'true'],\n\t['showObjects', 'all'],\n\t['showSheetTabs', 'true'],\n\t['showStatusbar', 'true'],\n\t['showVerticalScroll', 'true'],\n\t['tabRatio', '600'],\n\t['xWindow', '0'],\n\t['yWindow', '0']\n];*/\n\nfunction push_defaults_array(target, defaults) {\n\tfor(var j = 0; j != target.length; ++j) { var w = target[j];\n\t\tfor(var i=0; i != defaults.length; ++i) { var z = defaults[i];\n\t\t\tif(w[z[0]] == null) w[z[0]] = z[1];\n\t\t\telse switch(z[2]) {\n\t\t\tcase \"bool\": if(typeof w[z[0]] == \"string\") w[z[0]] = parsexmlbool(w[z[0]]); break;\n\t\t\tcase \"int\": if(typeof w[z[0]] == \"string\") w[z[0]] = parseInt(w[z[0]], 10); break;\n\t\t\t}\n\t\t}\n\t}\n}\nfunction push_defaults(target, defaults) {\n\tfor(var i = 0; i != defaults.length; ++i) { var z = defaults[i];\n\t\tif(target[z[0]] == null) target[z[0]] = z[1];\n\t\telse switch(z[2]) {\n\t\t\tcase \"bool\": if(typeof target[z[0]] == \"string\") target[z[0]] = parsexmlbool(target[z[0]]); break;\n\t\t\tcase \"int\": if(typeof target[z[0]] == \"string\") target[z[0]] = parseInt(target[z[0]], 10); break;\n\t\t}\n\t}\n}\n\nfunction parse_wb_defaults(wb) {\n\tpush_defaults(wb.WBProps, WBPropsDef);\n\tpush_defaults(wb.CalcPr, CalcPrDef);\n\n\tpush_defaults_array(wb.WBView, WBViewDef);\n\tpush_defaults_array(wb.Sheets, SheetDef);\n\n\t_ssfopts.date1904 = parsexmlbool(wb.WBProps.date1904);\n}\n\nfunction safe1904(wb/*:Workbook*/)/*:string*/ {\n\t/* TODO: store date1904 somewhere else */\n\tif(!wb.Workbook) return \"false\";\n\tif(!wb.Workbook.WBProps) return \"false\";\n\treturn parsexmlbool(wb.Workbook.WBProps.date1904) ? \"true\" : \"false\";\n}\n\nvar badchars = /*#__PURE__*/\"][*?\\/\\\\\".split(\"\");\nfunction check_ws_name(n/*:string*/, safe/*:?boolean*/)/*:boolean*/ {\n\tif(n.length > 31) { if(safe) return false; throw new Error(\"Sheet names cannot exceed 31 chars\"); }\n\tvar _good = true;\n\tbadchars.forEach(function(c) {\n\t\tif(n.indexOf(c) == -1) return;\n\t\tif(!safe) throw new Error(\"Sheet name cannot contain : \\\\ / ? * [ ]\");\n\t\t_good = false;\n\t});\n\treturn _good;\n}\nfunction check_wb_names(N, S, codes) {\n\tN.forEach(function(n,i) {\n\t\tcheck_ws_name(n);\n\t\tfor(var j = 0; j < i; ++j) if(n == N[j]) throw new Error(\"Duplicate Sheet Name: \" + n);\n\t\tif(codes) {\n\t\t\tvar cn = (S && S[i] && S[i].CodeName) || n;\n\t\t\tif(cn.charCodeAt(0) == 95 && cn.length > 22) throw new Error(\"Bad Code Name: Worksheet\" + cn);\n\t\t}\n\t});\n}\nfunction check_wb(wb) {\n\tif(!wb || !wb.SheetNames || !wb.Sheets) throw new Error(\"Invalid Workbook\");\n\tif(!wb.SheetNames.length) throw new Error(\"Workbook is empty\");\n\tvar Sheets = (wb.Workbook && wb.Workbook.Sheets) || [];\n\tcheck_wb_names(wb.SheetNames, Sheets, !!wb.vbaraw);\n\tfor(var i = 0; i < wb.SheetNames.length; ++i) check_ws(wb.Sheets[wb.SheetNames[i]], wb.SheetNames[i], i);\n\t/* TODO: validate workbook */\n}\n/* 18.2 Workbook */\nvar wbnsregex = /<\\w+:workbook/;\nfunction parse_wb_xml(data, opts)/*:WorkbookFile*/ {\n\tif(!data) throw new Error(\"Could not find file\");\n\tvar wb = /*::(*/{ AppVersion:{}, WBProps:{}, WBView:[], Sheets:[], CalcPr:{}, Names:[], xmlns: \"\" }/*::)*/;\n\tvar pass = false, xmlns = \"xmlns\";\n\tvar dname = {}, dnstart = 0;\n\tdata.replace(tagregex, function xml_wb(x, idx) {\n\t\tvar y/*:any*/ = parsexmltag(x);\n\t\tswitch(strip_ns(y[0])) {\n\t\t\tcase '<?xml': break;\n\n\t\t\t/* 18.2.27 workbook CT_Workbook 1 */\n\t\t\tcase '<workbook':\n\t\t\t\tif(x.match(wbnsregex)) xmlns = \"xmlns\" + x.match(/<(\\w+):/)[1];\n\t\t\t\twb.xmlns = y[xmlns];\n\t\t\t\tbreak;\n\t\t\tcase '</workbook>': break;\n\n\t\t\t/* 18.2.13 fileVersion CT_FileVersion ? */\n\t\t\tcase '<fileVersion': delete y[0]; wb.AppVersion = y; break;\n\t\t\tcase '<fileVersion/>': case '</fileVersion>': break;\n\n\t\t\t/* 18.2.12 fileSharing CT_FileSharing ? */\n\t\t\tcase '<fileSharing':\n\t\t\t\tbreak;\n\t\t\tcase '<fileSharing/>': break;\n\n\t\t\t/* 18.2.28 workbookPr CT_WorkbookPr ? */\n\t\t\tcase '<workbookPr':\n\t\t\tcase '<workbookPr/>':\n\t\t\t\tWBPropsDef.forEach(function(w) {\n\t\t\t\t\tif(y[w[0]] == null) return;\n\t\t\t\t\tswitch(w[2]) {\n\t\t\t\t\t\tcase \"bool\": wb.WBProps[w[0]] = parsexmlbool(y[w[0]]); break;\n\t\t\t\t\t\tcase \"int\": wb.WBProps[w[0]] = parseInt(y[w[0]], 10); break;\n\t\t\t\t\t\tdefault: wb.WBProps[w[0]] = y[w[0]];\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t\tif(y.codeName) wb.WBProps.CodeName = utf8read(y.codeName);\n\t\t\t\tbreak;\n\t\t\tcase '</workbookPr>': break;\n\n\t\t\t/* 18.2.29 workbookProtection CT_WorkbookProtection ? */\n\t\t\tcase '<workbookProtection':\n\t\t\t\tbreak;\n\t\t\tcase '<workbookProtection/>': break;\n\n\t\t\t/* 18.2.1  bookViews CT_BookViews ? */\n\t\t\tcase '<bookViews': case '<bookViews>': case '</bookViews>': break;\n\t\t\t/* 18.2.30   workbookView CT_BookView + */\n\t\t\tcase '<workbookView': case '<workbookView/>': delete y[0]; wb.WBView.push(y); break;\n\t\t\tcase '</workbookView>': break;\n\n\t\t\t/* 18.2.20 sheets CT_Sheets 1 */\n\t\t\tcase '<sheets': case '<sheets>': case '</sheets>': break; // aggregate sheet\n\t\t\t/* 18.2.19   sheet CT_Sheet + */\n\t\t\tcase '<sheet':\n\t\t\t\tswitch(y.state) {\n\t\t\t\t\tcase \"hidden\": y.Hidden = 1; break;\n\t\t\t\t\tcase \"veryHidden\": y.Hidden = 2; break;\n\t\t\t\t\tdefault: y.Hidden = 0;\n\t\t\t\t}\n\t\t\t\tdelete y.state;\n\t\t\t\ty.name = unescapexml(utf8read(y.name));\n\t\t\t\tdelete y[0]; wb.Sheets.push(y); break;\n\t\t\tcase '</sheet>': break;\n\n\t\t\t/* 18.2.15 functionGroups CT_FunctionGroups ? */\n\t\t\tcase '<functionGroups': case '<functionGroups/>': break;\n\t\t\t/* 18.2.14   functionGroup CT_FunctionGroup + */\n\t\t\tcase '<functionGroup': break;\n\n\t\t\t/* 18.2.9  externalReferences CT_ExternalReferences ? */\n\t\t\tcase '<externalReferences': case '</externalReferences>': case '<externalReferences>': break;\n\t\t\t/* 18.2.8    externalReference CT_ExternalReference + */\n\t\t\tcase '<externalReference': break;\n\n\t\t\t/* 18.2.6  definedNames CT_DefinedNames ? */\n\t\t\tcase '<definedNames/>': break;\n\t\t\tcase '<definedNames>': case '<definedNames': pass=true; break;\n\t\t\tcase '</definedNames>': pass=false; break;\n\t\t\t/* 18.2.5    definedName CT_DefinedName + */\n\t\t\tcase '<definedName': {\n\t\t\t\tdname = {};\n\t\t\t\tdname.Name = utf8read(y.name);\n\t\t\t\tif(y.comment) dname.Comment = y.comment;\n\t\t\t\tif(y.localSheetId) dname.Sheet = +y.localSheetId;\n\t\t\t\tif(parsexmlbool(y.hidden||\"0\")) dname.Hidden = true;\n\t\t\t\tdnstart = idx + x.length;\n\t\t\t}\tbreak;\n\t\t\tcase '</definedName>': {\n\t\t\t\tdname.Ref = unescapexml(utf8read(data.slice(dnstart, idx)));\n\t\t\t\twb.Names.push(dname);\n\t\t\t} break;\n\t\t\tcase '<definedName/>': break;\n\n\t\t\t/* 18.2.2  calcPr CT_CalcPr ? */\n\t\t\tcase '<calcPr': delete y[0]; wb.CalcPr = y; break;\n\t\t\tcase '<calcPr/>': delete y[0]; wb.CalcPr = y; break;\n\t\t\tcase '</calcPr>': break;\n\n\t\t\t/* 18.2.16 oleSize CT_OleSize ? (ref required) */\n\t\t\tcase '<oleSize': break;\n\n\t\t\t/* 18.2.4  customWorkbookViews CT_CustomWorkbookViews ? */\n\t\t\tcase '<customWorkbookViews>': case '</customWorkbookViews>': case '<customWorkbookViews': break;\n\t\t\t/* 18.2.3  customWorkbookView CT_CustomWorkbookView + */\n\t\t\tcase '<customWorkbookView': case '</customWorkbookView>': break;\n\n\t\t\t/* 18.2.18 pivotCaches CT_PivotCaches ? */\n\t\t\tcase '<pivotCaches>': case '</pivotCaches>': case '<pivotCaches': break;\n\t\t\t/* 18.2.17 pivotCache CT_PivotCache ? */\n\t\t\tcase '<pivotCache': break;\n\n\t\t\t/* 18.2.21 smartTagPr CT_SmartTagPr ? */\n\t\t\tcase '<smartTagPr': case '<smartTagPr/>': break;\n\n\t\t\t/* 18.2.23 smartTagTypes CT_SmartTagTypes ? */\n\t\t\tcase '<smartTagTypes': case '<smartTagTypes>': case '</smartTagTypes>': break;\n\t\t\t/* 18.2.22 smartTagType CT_SmartTagType ? */\n\t\t\tcase '<smartTagType': break;\n\n\t\t\t/* 18.2.24 webPublishing CT_WebPublishing ? */\n\t\t\tcase '<webPublishing': case '<webPublishing/>': break;\n\n\t\t\t/* 18.2.11 fileRecoveryPr CT_FileRecoveryPr ? */\n\t\t\tcase '<fileRecoveryPr': case '<fileRecoveryPr/>': break;\n\n\t\t\t/* 18.2.26 webPublishObjects CT_WebPublishObjects ? */\n\t\t\tcase '<webPublishObjects>': case '<webPublishObjects': case '</webPublishObjects>': break;\n\t\t\t/* 18.2.25 webPublishObject CT_WebPublishObject ? */\n\t\t\tcase '<webPublishObject': break;\n\n\t\t\t/* 18.2.10 extLst CT_ExtensionList ? */\n\t\t\tcase '<extLst': case '<extLst>': case '</extLst>': case '<extLst/>': break;\n\t\t\t/* 18.2.7  ext CT_Extension + */\n\t\t\tcase '<ext': pass=true; break; //TODO: check with versions of excel\n\t\t\tcase '</ext>': pass=false; break;\n\n\t\t\t/* Others */\n\t\t\tcase '<ArchID': break;\n\t\t\tcase '<AlternateContent':\n\t\t\tcase '<AlternateContent>': pass=true; break;\n\t\t\tcase '</AlternateContent>': pass=false; break;\n\n\t\t\t/* TODO */\n\t\t\tcase '<revisionPtr': break;\n\n\t\t\tdefault: if(!pass && opts.WTF) throw new Error('unrecognized ' + y[0] + ' in workbook');\n\t\t}\n\t\treturn x;\n\t});\n\tif(XMLNS_main.indexOf(wb.xmlns) === -1) throw new Error(\"Unknown Namespace: \" + wb.xmlns);\n\n\tparse_wb_defaults(wb);\n\n\treturn wb;\n}\n\nfunction write_wb_xml(wb/*:Workbook*//*::, opts:?WriteOpts*/)/*:string*/ {\n\tvar o = [XML_HEADER];\n\to[o.length] = writextag('workbook', null, {\n\t\t'xmlns': XMLNS_main[0],\n\t\t//'xmlns:mx': XMLNS.mx,\n\t\t//'xmlns:s': XMLNS_main[0],\n\t\t'xmlns:r': XMLNS.r\n\t});\n\n\tvar write_names = (wb.Workbook && (wb.Workbook.Names||[]).length > 0);\n\n\t/* fileVersion */\n\t/* fileSharing */\n\n\tvar workbookPr/*:any*/ = ({codeName:\"ThisWorkbook\"}/*:any*/);\n\tif(wb.Workbook && wb.Workbook.WBProps) {\n\t\tWBPropsDef.forEach(function(x) {\n\t\t\t/*:: if(!wb.Workbook || !wb.Workbook.WBProps) throw \"unreachable\"; */\n\t\t\tif((wb.Workbook.WBProps[x[0]]/*:any*/) == null) return;\n\t\t\tif((wb.Workbook.WBProps[x[0]]/*:any*/) == x[1]) return;\n\t\t\tworkbookPr[x[0]] = (wb.Workbook.WBProps[x[0]]/*:any*/);\n\t\t});\n\t\t/*:: if(!wb.Workbook || !wb.Workbook.WBProps) throw \"unreachable\"; */\n\t\tif(wb.Workbook.WBProps.CodeName) { workbookPr.codeName = wb.Workbook.WBProps.CodeName; delete workbookPr.CodeName; }\n\t}\n\to[o.length] = (writextag('workbookPr', null, workbookPr));\n\n\t/* workbookProtection */\n\n\tvar sheets = wb.Workbook && wb.Workbook.Sheets || [];\n\tvar i = 0;\n\n\t/* bookViews only written if first worksheet is hidden */\n\tif(sheets && sheets[0] && !!sheets[0].Hidden) {\n\t\to[o.length] = \"<bookViews>\";\n\t\tfor(i = 0; i != wb.SheetNames.length; ++i) {\n\t\t\tif(!sheets[i]) break;\n\t\t\tif(!sheets[i].Hidden) break;\n\t\t}\n\t\tif(i == wb.SheetNames.length) i = 0;\n\t\to[o.length] = '<workbookView firstSheet=\"' + i + '\" activeTab=\"' + i + '\"/>';\n\t\to[o.length] = \"</bookViews>\";\n\t}\n\n\to[o.length] = \"<sheets>\";\n\tfor(i = 0; i != wb.SheetNames.length; ++i) {\n\t\tvar sht = ({name:escapexml(wb.SheetNames[i].slice(0,31))}/*:any*/);\n\t\tsht.sheetId = \"\"+(i+1);\n\t\tsht[\"r:id\"] = \"rId\"+(i+1);\n\t\tif(sheets[i]) switch(sheets[i].Hidden) {\n\t\t\tcase 1: sht.state = \"hidden\"; break;\n\t\t\tcase 2: sht.state = \"veryHidden\"; break;\n\t\t}\n\t\to[o.length] = (writextag('sheet',null,sht));\n\t}\n\to[o.length] = \"</sheets>\";\n\n\t/* functionGroups */\n\t/* externalReferences */\n\n\tif(write_names) {\n\t\to[o.length] = \"<definedNames>\";\n\t\tif(wb.Workbook && wb.Workbook.Names) wb.Workbook.Names.forEach(function(n) {\n\t\t\tvar d/*:any*/ = {name:n.Name};\n\t\t\tif(n.Comment) d.comment = n.Comment;\n\t\t\tif(n.Sheet != null) d.localSheetId = \"\"+n.Sheet;\n\t\t\tif(n.Hidden) d.hidden = \"1\";\n\t\t\tif(!n.Ref) return;\n\t\t\to[o.length] = writextag('definedName', escapexml(n.Ref), d);\n\t\t});\n\t\to[o.length] = \"</definedNames>\";\n\t}\n\n\t/* calcPr */\n\t/* oleSize */\n\t/* customWorkbookViews */\n\t/* pivotCaches */\n\t/* smartTagPr */\n\t/* smartTagTypes */\n\t/* webPublishing */\n\t/* fileRecoveryPr */\n\t/* webPublishObjects */\n\t/* extLst */\n\n\tif(o.length>2){ o[o.length] = '</workbook>'; o[1]=o[1].replace(\"/>\",\">\"); }\n\treturn o.join(\"\");\n}\n/* [MS-XLSB] 2.4.304 BrtBundleSh */\nfunction parse_BrtBundleSh(data, length/*:number*/) {\n\tvar z = {};\n\tz.Hidden = data.read_shift(4); //hsState ST_SheetState\n\tz.iTabID = data.read_shift(4);\n\tz.strRelID = parse_RelID(data,length-8);\n\tz.name = parse_XLWideString(data);\n\treturn z;\n}\nfunction write_BrtBundleSh(data, o) {\n\tif(!o) o = new_buf(127);\n\to.write_shift(4, data.Hidden);\n\to.write_shift(4, data.iTabID);\n\twrite_RelID(data.strRelID, o);\n\twrite_XLWideString(data.name.slice(0,31), o);\n\treturn o.length > o.l ? o.slice(0, o.l) : o;\n}\n\n/* [MS-XLSB] 2.4.815 BrtWbProp */\nfunction parse_BrtWbProp(data, length)/*:WBProps*/ {\n\tvar o/*:WBProps*/ = ({}/*:any*/);\n\tvar flags = data.read_shift(4);\n\to.defaultThemeVersion = data.read_shift(4);\n\tvar strName = (length > 8) ? parse_XLWideString(data) : \"\";\n\tif(strName.length > 0) o.CodeName = strName;\n\to.autoCompressPictures = !!(flags & 0x10000);\n\to.backupFile = !!(flags & 0x40);\n\to.checkCompatibility = !!(flags & 0x1000);\n\to.date1904 = !!(flags & 0x01);\n\to.filterPrivacy = !!(flags & 0x08);\n\to.hidePivotFieldList = !!(flags & 0x400);\n\to.promptedSolutions = !!(flags & 0x10);\n\to.publishItems = !!(flags & 0x800);\n\to.refreshAllConnections = !!(flags & 0x40000);\n\to.saveExternalLinkValues = !!(flags & 0x80);\n\to.showBorderUnselectedTables = !!(flags & 0x04);\n\to.showInkAnnotation = !!(flags & 0x20);\n\to.showObjects = [\"all\", \"placeholders\", \"none\"][(flags >> 13) & 0x03];\n\to.showPivotChartFilter = !!(flags & 0x8000);\n\to.updateLinks = [\"userSet\", \"never\", \"always\"][(flags >> 8) & 0x03];\n\treturn o;\n}\nfunction write_BrtWbProp(data/*:?WBProps*/, o) {\n\tif(!o) o = new_buf(72);\n\tvar flags = 0;\n\tif(data) {\n\t\t/* TODO: mirror parse_BrtWbProp fields */\n\t\tif(data.filterPrivacy) flags |= 0x08;\n\t}\n\to.write_shift(4, flags);\n\to.write_shift(4, 0);\n\twrite_XLSBCodeName(data && data.CodeName || \"ThisWorkbook\", o);\n\treturn o.slice(0, o.l);\n}\n\nfunction parse_BrtFRTArchID$(data, length) {\n\tvar o = {};\n\tdata.read_shift(4);\n\to.ArchID = data.read_shift(4);\n\tdata.l += length - 8;\n\treturn o;\n}\n\n/* [MS-XLSB] 2.4.687 BrtName */\nfunction parse_BrtName(data, length, opts) {\n\tvar end = data.l + length;\n\tdata.l += 4; //var flags = data.read_shift(4);\n\tdata.l += 1; //var chKey = data.read_shift(1);\n\tvar itab = data.read_shift(4);\n\tvar name = parse_XLNameWideString(data);\n\tvar formula = parse_XLSBNameParsedFormula(data, 0, opts);\n\tvar comment = parse_XLNullableWideString(data);\n\t//if(0 /* fProc */) {\n\t\t// unusedstring1: XLNullableWideString\n\t\t// description: XLNullableWideString\n\t\t// helpTopic: XLNullableWideString\n\t\t// unusedstring2: XLNullableWideString\n\t//}\n\tdata.l = end;\n\tvar out = ({Name:name, Ptg:formula}/*:any*/);\n\tif(itab < 0xFFFFFFF) out.Sheet = itab;\n\tif(comment) out.Comment = comment;\n\treturn out;\n}\n\n/* [MS-XLSB] 2.1.7.61 Workbook */\nfunction parse_wb_bin(data, opts)/*:WorkbookFile*/ {\n\tvar wb = { AppVersion:{}, WBProps:{}, WBView:[], Sheets:[], CalcPr:{}, xmlns: \"\" };\n\tvar state/*:Array<string>*/ = [];\n\tvar pass = false;\n\n\tif(!opts) opts = {};\n\topts.biff = 12;\n\n\tvar Names = [];\n\tvar supbooks = ([[]]/*:any*/);\n\tsupbooks.SheetNames = [];\n\tsupbooks.XTI = [];\n\n\tXLSBRecordEnum[0x0010] = { n:\"BrtFRTArchID$\", f:parse_BrtFRTArchID$ };\n\n\trecordhopper(data, function hopper_wb(val, R, RT) {\n\t\tswitch(RT) {\n\t\t\tcase 0x009C: /* 'BrtBundleSh' */\n\t\t\t\tsupbooks.SheetNames.push(val.name);\n\t\t\t\twb.Sheets.push(val); break;\n\n\t\t\tcase 0x0099: /* 'BrtWbProp' */\n\t\t\t\twb.WBProps = val; break;\n\n\t\t\tcase 0x0027: /* 'BrtName' */\n\t\t\t\tif(val.Sheet != null) opts.SID = val.Sheet;\n\t\t\t\tval.Ref = stringify_formula(val.Ptg, null, null, supbooks, opts);\n\t\t\t\tdelete opts.SID;\n\t\t\t\tdelete val.Ptg;\n\t\t\t\tNames.push(val);\n\t\t\t\tbreak;\n\t\t\tcase 0x040C: /* 'BrtNameExt' */ break;\n\n\t\t\tcase 0x0165: /* 'BrtSupSelf' */\n\t\t\tcase 0x0166: /* 'BrtSupSame' */\n\t\t\tcase 0x0163: /* 'BrtSupBookSrc' */\n\t\t\tcase 0x029B: /* 'BrtSupAddin' */\n\t\t\t\tif(!supbooks[0].length) supbooks[0] = [RT, val];\n\t\t\t\telse supbooks.push([RT, val]);\n\t\t\t\tsupbooks[supbooks.length - 1].XTI = [];\n\t\t\t\tbreak;\n\t\t\tcase 0x016A: /* 'BrtExternSheet' */\n\t\t\t\tif(supbooks.length === 0) { supbooks[0] = []; supbooks[0].XTI = []; }\n\t\t\t\tsupbooks[supbooks.length - 1].XTI = supbooks[supbooks.length - 1].XTI.concat(val);\n\t\t\t\tsupbooks.XTI = supbooks.XTI.concat(val);\n\t\t\t\tbreak;\n\t\t\tcase 0x0169: /* 'BrtPlaceholderName' */\n\t\t\t\tbreak;\n\n\t\t\tcase 0x0817: /* 'BrtAbsPath15' */\n\t\t\tcase 0x009E: /* 'BrtBookView' */\n\t\t\tcase 0x008F: /* 'BrtBeginBundleShs' */\n\t\t\tcase 0x0298: /* 'BrtBeginFnGroup' */\n\t\t\tcase 0x0161: /* 'BrtBeginExternals' */\n\t\t\t\tbreak;\n\n\t\t\t/* case 'BrtModelTimeGroupingCalcCol' */\n\t\t\tcase 0x0C00: /* 'BrtUid' */\n\t\t\tcase 0x0C01: /* 'BrtRevisionPtr' */\n\t\t\tcase 0x0216: /* 'BrtBookProtection' */\n\t\t\tcase 0x02A5: /* 'BrtBookProtectionIso' */\n\t\t\tcase 0x009D: /* 'BrtCalcProp' */\n\t\t\tcase 0x0262: /* 'BrtCrashRecErr' */\n\t\t\tcase 0x0802: /* 'BrtDecoupledPivotCacheID' */\n\t\t\tcase 0x009B: /* 'BrtFileRecover' */\n\t\t\tcase 0x0224: /* 'BrtFileSharing' */\n\t\t\tcase 0x02A4: /* 'BrtFileSharingIso' */\n\t\t\tcase 0x0080: /* 'BrtFileVersion' */\n\t\t\tcase 0x0299: /* 'BrtFnGroup' */\n\t\t\tcase 0x0850: /* 'BrtModelRelationship' */\n\t\t\tcase 0x084D: /* 'BrtModelTable' */\n\t\t\tcase 0x0225: /* 'BrtOleSize' */\n\t\t\tcase 0x0805: /* 'BrtPivotTableRef' */\n\t\t\tcase 0x0254: /* 'BrtSmartTagType' */\n\t\t\tcase 0x081C: /* 'BrtTableSlicerCacheID' */\n\t\t\tcase 0x081B: /* 'BrtTableSlicerCacheIDs' */\n\t\t\tcase 0x0822: /* 'BrtTimelineCachePivotCacheID' */\n\t\t\tcase 0x018D: /* 'BrtUserBookView' */\n\t\t\tcase 0x009A: /* 'BrtWbFactoid' */\n\t\t\tcase 0x045D: /* 'BrtWbProp14' */\n\t\t\tcase 0x0229: /* 'BrtWebOpt' */\n\t\t\tcase 0x082B: /* 'BrtWorkBookPr15' */\n\t\t\t\tbreak;\n\n\t\t\tcase 0x0023: /* 'BrtFRTBegin' */\n\t\t\t\tstate.push(RT); pass = true; break;\n\t\t\tcase 0x0024: /* 'BrtFRTEnd' */\n\t\t\t\tstate.pop(); pass = false; break;\n\t\t\tcase 0x0025: /* 'BrtACBegin' */\n\t\t\t\tstate.push(RT); pass = true; break;\n\t\t\tcase 0x0026: /* 'BrtACEnd' */\n\t\t\t\tstate.pop(); pass = false; break;\n\n\t\t\tcase 0x0010: /* 'BrtFRTArchID$' */ break;\n\n\t\t\tdefault:\n\t\t\t\tif(R.T){/* empty */}\n\t\t\t\telse if(!pass || (opts.WTF && state[state.length-1] != 0x0025 /* BrtACBegin */ && state[state.length-1] != 0x0023 /* BrtFRTBegin */)) throw new Error(\"Unexpected record 0x\" + RT.toString(16));\n\t\t}\n\t}, opts);\n\n\tparse_wb_defaults(wb);\n\n\t// $FlowIgnore\n\twb.Names = Names;\n\n\t(wb/*:any*/).supbooks = supbooks;\n\treturn wb;\n}\n\nfunction write_BUNDLESHS(ba, wb/*::, opts*/) {\n\twrite_record(ba, 0x008F /* BrtBeginBundleShs */);\n\tfor(var idx = 0; idx != wb.SheetNames.length; ++idx) {\n\t\tvar viz = wb.Workbook && wb.Workbook.Sheets && wb.Workbook.Sheets[idx] && wb.Workbook.Sheets[idx].Hidden || 0;\n\t\tvar d = { Hidden: viz, iTabID: idx+1, strRelID: 'rId' + (idx+1), name: wb.SheetNames[idx] };\n\t\twrite_record(ba, 0x009C /* BrtBundleSh */, write_BrtBundleSh(d));\n\t}\n\twrite_record(ba, 0x0090 /* BrtEndBundleShs */);\n}\n\n/* [MS-XLSB] 2.4.649 BrtFileVersion */\nfunction write_BrtFileVersion(data, o) {\n\tif(!o) o = new_buf(127);\n\tfor(var i = 0; i != 4; ++i) o.write_shift(4, 0);\n\twrite_XLWideString(\"SheetJS\", o);\n\twrite_XLWideString(XLSX.version, o);\n\twrite_XLWideString(XLSX.version, o);\n\twrite_XLWideString(\"7262\", o);\n\treturn o.length > o.l ? o.slice(0, o.l) : o;\n}\n\n/* [MS-XLSB] 2.4.301 BrtBookView */\nfunction write_BrtBookView(idx, o) {\n\tif(!o) o = new_buf(29);\n\to.write_shift(-4, 0);\n\to.write_shift(-4, 460);\n\to.write_shift(4,  28800);\n\to.write_shift(4,  17600);\n\to.write_shift(4,  500);\n\to.write_shift(4,  idx);\n\to.write_shift(4,  idx);\n\tvar flags = 0x78;\n\to.write_shift(1,  flags);\n\treturn o.length > o.l ? o.slice(0, o.l) : o;\n}\n\nfunction write_BOOKVIEWS(ba, wb/*::, opts*/) {\n\t/* required if hidden tab appears before visible tab */\n\tif(!wb.Workbook || !wb.Workbook.Sheets) return;\n\tvar sheets = wb.Workbook.Sheets;\n\tvar i = 0, vistab = -1, hidden = -1;\n\tfor(; i < sheets.length; ++i) {\n\t\tif(!sheets[i] || !sheets[i].Hidden && vistab == -1) vistab = i;\n\t\telse if(sheets[i].Hidden == 1 && hidden == -1) hidden = i;\n\t}\n\tif(hidden > vistab) return;\n\twrite_record(ba, 0x0087 /* BrtBeginBookViews */);\n\twrite_record(ba, 0x009E /* BrtBookView */, write_BrtBookView(vistab));\n\t/* 1*(BrtBookView *FRT) */\n\twrite_record(ba, 0x0088 /* BrtEndBookViews */);\n}\n\n/* [MS-XLSB] 2.4.305 BrtCalcProp */\n/*function write_BrtCalcProp(data, o) {\n\tif(!o) o = new_buf(26);\n\to.write_shift(4,0); // force recalc\n\to.write_shift(4,1);\n\to.write_shift(4,0);\n\twrite_Xnum(0, o);\n\to.write_shift(-4, 1023);\n\to.write_shift(1, 0x33);\n\to.write_shift(1, 0x00);\n\treturn o;\n}*/\n\n/* [MS-XLSB] 2.4.646 BrtFileRecover */\n/*function write_BrtFileRecover(data, o) {\n\tif(!o) o = new_buf(1);\n\to.write_shift(1,0);\n\treturn o;\n}*/\n\n/* [MS-XLSB] 2.1.7.61 Workbook */\nfunction write_wb_bin(wb, opts) {\n\tvar ba = buf_array();\n\twrite_record(ba, 0x0083 /* BrtBeginBook */);\n\twrite_record(ba, 0x0080 /* BrtFileVersion */, write_BrtFileVersion());\n\t/* [[BrtFileSharingIso] BrtFileSharing] */\n\twrite_record(ba, 0x0099 /* BrtWbProp */, write_BrtWbProp(wb.Workbook && wb.Workbook.WBProps || null));\n\t/* [ACABSPATH] */\n\t/* [[BrtBookProtectionIso] BrtBookProtection] */\n\twrite_BOOKVIEWS(ba, wb, opts);\n\twrite_BUNDLESHS(ba, wb, opts);\n\t/* [FNGROUP] */\n\t/* [EXTERNALS] */\n\t/* *BrtName */\n\t/* write_record(ba, 0x009D BrtCalcProp, write_BrtCalcProp()); */\n\t/* [BrtOleSize] */\n\t/* *(BrtUserBookView *FRT) */\n\t/* [PIVOTCACHEIDS] */\n\t/* [BrtWbFactoid] */\n\t/* [SMARTTAGTYPES] */\n\t/* [BrtWebOpt] */\n\t/* write_record(ba, 0x009B BrtFileRecover, write_BrtFileRecover()); */\n\t/* [WEBPUBITEMS] */\n\t/* [CRERRS] */\n\t/* FRTWORKBOOK */\n\twrite_record(ba, 0x0084 /* BrtEndBook */);\n\n\treturn ba.end();\n}\nfunction parse_wb(data, name/*:string*/, opts)/*:WorkbookFile*/ {\n\tif(name.slice(-4)===\".bin\") return parse_wb_bin((data/*:any*/), opts);\n\treturn parse_wb_xml((data/*:any*/), opts);\n}\n\nfunction parse_ws(data, name/*:string*/, idx/*:number*/, opts, rels, wb, themes, styles)/*:Worksheet*/ {\n\tif(name.slice(-4)===\".bin\") return parse_ws_bin((data/*:any*/), opts, idx, rels, wb, themes, styles);\n\treturn parse_ws_xml((data/*:any*/), opts, idx, rels, wb, themes, styles);\n}\n\nfunction parse_cs(data, name/*:string*/, idx/*:number*/, opts, rels, wb, themes, styles)/*:Worksheet*/ {\n\tif(name.slice(-4)===\".bin\") return parse_cs_bin((data/*:any*/), opts, idx, rels, wb, themes, styles);\n\treturn parse_cs_xml((data/*:any*/), opts, idx, rels, wb, themes, styles);\n}\n\nfunction parse_ms(data, name/*:string*/, idx/*:number*/, opts, rels, wb, themes, styles)/*:Worksheet*/ {\n\tif(name.slice(-4)===\".bin\") return parse_ms_bin((data/*:any*/), opts, idx, rels, wb, themes, styles);\n\treturn parse_ms_xml((data/*:any*/), opts, idx, rels, wb, themes, styles);\n}\n\nfunction parse_ds(data, name/*:string*/, idx/*:number*/, opts, rels, wb, themes, styles)/*:Worksheet*/ {\n\tif(name.slice(-4)===\".bin\") return parse_ds_bin((data/*:any*/), opts, idx, rels, wb, themes, styles);\n\treturn parse_ds_xml((data/*:any*/), opts, idx, rels, wb, themes, styles);\n}\n\nfunction parse_sty(data, name/*:string*/, themes, opts) {\n\tif(name.slice(-4)===\".bin\") return parse_sty_bin((data/*:any*/), themes, opts);\n\treturn parse_sty_xml((data/*:any*/), themes, opts);\n}\n\nfunction parse_theme(data/*:string*/, name/*:string*/, opts) {\n\treturn parse_theme_xml(data, opts);\n}\n\nfunction parse_sst(data, name/*:string*/, opts)/*:SST*/ {\n\tif(name.slice(-4)===\".bin\") return parse_sst_bin((data/*:any*/), opts);\n\treturn parse_sst_xml((data/*:any*/), opts);\n}\n\nfunction parse_cmnt(data, name/*:string*/, opts)/*:Array<RawComment>*/ {\n\tif(name.slice(-4)===\".bin\") return parse_comments_bin((data/*:any*/), opts);\n\treturn parse_comments_xml((data/*:any*/), opts);\n}\n\nfunction parse_cc(data, name/*:string*/, opts) {\n\tif(name.slice(-4)===\".bin\") return parse_cc_bin((data/*:any*/), name, opts);\n\treturn parse_cc_xml((data/*:any*/), name, opts);\n}\n\nfunction parse_xlink(data, rel, name/*:string*/, opts) {\n\tif(name.slice(-4)===\".bin\") return parse_xlink_bin((data/*:any*/), rel, name, opts);\n\treturn parse_xlink_xml((data/*:any*/), rel, name, opts);\n}\n\nfunction parse_xlmeta(data, name/*:string*/, opts) {\n\tif(name.slice(-4)===\".bin\") return parse_xlmeta_bin((data/*:any*/), name, opts);\n\treturn parse_xlmeta_xml((data/*:any*/), name, opts);\n}\n\nfunction write_wb(wb, name/*:string*/, opts) {\n\treturn (name.slice(-4)===\".bin\" ? write_wb_bin : write_wb_xml)(wb, opts);\n}\n\nfunction write_ws(data/*:number*/, name/*:string*/, opts, wb/*:Workbook*/, rels) {\n\treturn (name.slice(-4)===\".bin\" ? write_ws_bin : write_ws_xml)(data, opts, wb, rels);\n}\n\n// eslint-disable-next-line no-unused-vars\nfunction write_cs(data/*:number*/, name/*:string*/, opts, wb/*:Workbook*/, rels) {\n\treturn (name.slice(-4)===\".bin\" ? write_cs_bin : write_cs_xml)(data, opts, wb, rels);\n}\n\nfunction write_sty(data, name/*:string*/, opts) {\n\treturn (name.slice(-4)===\".bin\" ? write_sty_bin : write_sty_xml)(data, opts);\n}\n\nfunction write_sst(data/*:SST*/, name/*:string*/, opts) {\n\treturn (name.slice(-4)===\".bin\" ? write_sst_bin : write_sst_xml)(data, opts);\n}\n\nfunction write_cmnt(data/*:Array<any>*/, name/*:string*/, opts) {\n\treturn (name.slice(-4)===\".bin\" ? write_comments_bin : write_comments_xml)(data, opts);\n}\n/*\nfunction write_cc(data, name:string, opts) {\n\treturn (name.slice(-4)===\".bin\" ? write_cc_bin : write_cc_xml)(data, opts);\n}\n*/\n\nfunction write_xlmeta(name/*:string*/) {\n\treturn (name.slice(-4)===\".bin\" ? write_xlmeta_bin : write_xlmeta_xml)();\n}\nvar attregexg2=/([\\w:]+)=((?:\")([^\"]*)(?:\")|(?:')([^']*)(?:'))/g;\nvar attregex2=/([\\w:]+)=((?:\")(?:[^\"]*)(?:\")|(?:')(?:[^']*)(?:'))/;\nfunction xlml_parsexmltag(tag/*:string*/, skip_root/*:?boolean*/) {\n\tvar words = tag.split(/\\s+/);\n\tvar z/*:any*/ = ([]/*:any*/); if(!skip_root) z[0] = words[0];\n\tif(words.length === 1) return z;\n\tvar m = tag.match(attregexg2), y, j, w, i;\n\tif(m) for(i = 0; i != m.length; ++i) {\n\t\ty = m[i].match(attregex2);\n/*:: if(!y || !y[2]) continue; */\n\t\tif((j=y[1].indexOf(\":\")) === -1) z[y[1]] = y[2].slice(1,y[2].length-1);\n\t\telse {\n\t\t\tif(y[1].slice(0,6) === \"xmlns:\") w = \"xmlns\"+y[1].slice(6);\n\t\t\telse w = y[1].slice(j+1);\n\t\t\tz[w] = y[2].slice(1,y[2].length-1);\n\t\t}\n\t}\n\treturn z;\n}\nfunction xlml_parsexmltagobj(tag/*:string*/) {\n\tvar words = tag.split(/\\s+/);\n\tvar z = {};\n\tif(words.length === 1) return z;\n\tvar m = tag.match(attregexg2), y, j, w, i;\n\tif(m) for(i = 0; i != m.length; ++i) {\n\t\ty = m[i].match(attregex2);\n/*:: if(!y || !y[2]) continue; */\n\t\tif((j=y[1].indexOf(\":\")) === -1) z[y[1]] = y[2].slice(1,y[2].length-1);\n\t\telse {\n\t\t\tif(y[1].slice(0,6) === \"xmlns:\") w = \"xmlns\"+y[1].slice(6);\n\t\t\telse w = y[1].slice(j+1);\n\t\t\tz[w] = y[2].slice(1,y[2].length-1);\n\t\t}\n\t}\n\treturn z;\n}\n\n// ----\n\n/* map from xlml named formats to SSF TODO: localize */\nvar XLMLFormatMap/*: {[string]:string}*/;\n\nfunction xlml_format(format, value)/*:string*/ {\n\tvar fmt = XLMLFormatMap[format] || unescapexml(format);\n\tif(fmt === \"General\") return SSF_general(value);\n\treturn SSF_format(fmt, value);\n}\n\nfunction xlml_set_custprop(Custprops, key, cp, val/*:string*/) {\n\tvar oval/*:any*/ = val;\n\tswitch((cp[0].match(/dt:dt=\"([\\w.]+)\"/)||[\"\",\"\"])[1]) {\n\t\tcase \"boolean\": oval = parsexmlbool(val); break;\n\t\tcase \"i2\": case \"int\": oval = parseInt(val, 10); break;\n\t\tcase \"r4\": case \"float\": oval = parseFloat(val); break;\n\t\tcase \"date\": case \"dateTime.tz\": oval = parseDate(val); break;\n\t\tcase \"i8\": case \"string\": case \"fixed\": case \"uuid\": case \"bin.base64\": break;\n\t\tdefault: throw new Error(\"bad custprop:\" + cp[0]);\n\t}\n\tCustprops[unescapexml(key)] = oval;\n}\n\nfunction safe_format_xlml(cell/*:Cell*/, nf, o) {\n\tif(cell.t === 'z') return;\n\tif(!o || o.cellText !== false) try {\n\t\tif(cell.t === 'e') { cell.w = cell.w || BErr[cell.v]; }\n\t\telse if(nf === \"General\") {\n\t\t\tif(cell.t === 'n') {\n\t\t\t\tif((cell.v|0) === cell.v) cell.w = cell.v.toString(10);\n\t\t\t\telse cell.w = SSF_general_num(cell.v);\n\t\t\t}\n\t\t\telse cell.w = SSF_general(cell.v);\n\t\t}\n\t\telse cell.w = xlml_format(nf||\"General\", cell.v);\n\t} catch(e) { if(o.WTF) throw e; }\n\ttry {\n\t\tvar z = XLMLFormatMap[nf]||nf||\"General\";\n\t\tif(o.cellNF) cell.z = z;\n\t\tif(o.cellDates && cell.t == 'n' && fmt_is_date(z)) {\n\t\t\tvar _d = SSF_parse_date_code(cell.v); if(_d) { cell.t = 'd'; cell.v = new Date(_d.y, _d.m-1,_d.d,_d.H,_d.M,_d.S,_d.u); }\n\t\t}\n\t} catch(e) { if(o.WTF) throw e; }\n}\n\nfunction process_style_xlml(styles, stag, opts) {\n\tif(opts.cellStyles) {\n\t\tif(stag.Interior) {\n\t\t\tvar I = stag.Interior;\n\t\t\tif(I.Pattern) I.patternType = XLMLPatternTypeMap[I.Pattern] || I.Pattern;\n\t\t}\n\t}\n\tstyles[stag.ID] = stag;\n}\n\n/* TODO: there must exist some form of OSP-blessed spec */\nfunction parse_xlml_data(xml, ss, data, cell/*:any*/, base, styles, csty, row, arrayf, o) {\n\tvar nf = \"General\", sid = cell.StyleID, S = {}; o = o || {};\n\tvar interiors = [];\n\tvar i = 0;\n\tif(sid === undefined && row) sid = row.StyleID;\n\tif(sid === undefined && csty) sid = csty.StyleID;\n\twhile(styles[sid] !== undefined) {\n\t\tif(styles[sid].nf) nf = styles[sid].nf;\n\t\tif(styles[sid].Interior) interiors.push(styles[sid].Interior);\n\t\tif(!styles[sid].Parent) break;\n\t\tsid = styles[sid].Parent;\n\t}\n\tswitch(data.Type) {\n\t\tcase 'Boolean':\n\t\t\tcell.t = 'b';\n\t\t\tcell.v = parsexmlbool(xml);\n\t\t\tbreak;\n\t\tcase 'String':\n\t\t\tcell.t = 's'; cell.r = xlml_fixstr(unescapexml(xml));\n\t\t\tcell.v = (xml.indexOf(\"<\") > -1 ? unescapexml(ss||xml).replace(/<.*?>/g, \"\") : cell.r); // todo: BR etc\n\t\t\tbreak;\n\t\tcase 'DateTime':\n\t\t\tif(xml.slice(-1) != \"Z\") xml += \"Z\";\n\t\t\tcell.v = (parseDate(xml) - new Date(Date.UTC(1899, 11, 30))) / (24 * 60 * 60 * 1000);\n\t\t\tif(cell.v !== cell.v) cell.v = unescapexml(xml);\n\t\t\telse if(cell.v<60) cell.v = cell.v -1;\n\t\t\tif(!nf || nf == \"General\") nf = \"yyyy-mm-dd\";\n\t\t\t/* falls through */\n\t\tcase 'Number':\n\t\t\tif(cell.v === undefined) cell.v=+xml;\n\t\t\tif(!cell.t) cell.t = 'n';\n\t\t\tbreak;\n\t\tcase 'Error': cell.t = 'e'; cell.v = RBErr[xml]; if(o.cellText !== false) cell.w = xml; break;\n\t\tdefault:\n\t\t\tif(xml == \"\" && ss == \"\") { cell.t = 'z'; }\n\t\t\telse { cell.t = 's'; cell.v = xlml_fixstr(ss||xml); }\n\t\t\tbreak;\n\t}\n\tsafe_format_xlml(cell, nf, o);\n\tif(o.cellFormula !== false) {\n\t\tif(cell.Formula) {\n\t\t\tvar fstr = unescapexml(cell.Formula);\n\t\t\t/* strictly speaking, the leading = is required but some writers omit */\n\t\t\tif(fstr.charCodeAt(0) == 61 /* = */) fstr = fstr.slice(1);\n\t\t\tcell.f = rc_to_a1(fstr, base);\n\t\t\tdelete cell.Formula;\n\t\t\tif(cell.ArrayRange == \"RC\") cell.F = rc_to_a1(\"RC:RC\", base);\n\t\t\telse if(cell.ArrayRange) {\n\t\t\t\tcell.F = rc_to_a1(cell.ArrayRange, base);\n\t\t\t\tarrayf.push([safe_decode_range(cell.F), cell.F]);\n\t\t\t}\n\t\t} else {\n\t\t\tfor(i = 0; i < arrayf.length; ++i)\n\t\t\t\tif(base.r >= arrayf[i][0].s.r && base.r <= arrayf[i][0].e.r)\n\t\t\t\t\tif(base.c >= arrayf[i][0].s.c && base.c <= arrayf[i][0].e.c)\n\t\t\t\t\t\tcell.F = arrayf[i][1];\n\t\t}\n\t}\n\tif(o.cellStyles) {\n\t\tinteriors.forEach(function(x) {\n\t\t\tif(!S.patternType && x.patternType) S.patternType = x.patternType;\n\t\t});\n\t\tcell.s = S;\n\t}\n\tif(cell.StyleID !== undefined) cell.ixfe = cell.StyleID;\n}\n\nfunction xlml_clean_comment(comment/*:any*/) {\n\tcomment.t = comment.v || \"\";\n\tcomment.t = comment.t.replace(/\\r\\n/g,\"\\n\").replace(/\\r/g,\"\\n\");\n\tcomment.v = comment.w = comment.ixfe = undefined;\n}\n\n/* TODO: Everything */\nfunction parse_xlml_xml(d, _opts)/*:Workbook*/ {\n\tvar opts = _opts || {};\n\tmake_ssf();\n\tvar str = debom(xlml_normalize(d));\n\tif(opts.type == 'binary' || opts.type == 'array' || opts.type == 'base64') {\n\t\tif(typeof $cptable !== 'undefined') str = $cptable.utils.decode(65001, char_codes(str));\n\t\telse str = utf8read(str);\n\t}\n\tvar opening = str.slice(0, 1024).toLowerCase(), ishtml = false;\n\topening = opening.replace(/\".*?\"/g, \"\");\n\tif((opening.indexOf(\">\") & 1023) > Math.min((opening.indexOf(\",\") & 1023), (opening.indexOf(\";\")&1023))) { var _o = dup(opts); _o.type = \"string\"; return PRN.to_workbook(str, _o); }\n\tif(opening.indexOf(\"<?xml\") == -1) [\"html\", \"table\", \"head\", \"meta\", \"script\", \"style\", \"div\"].forEach(function(tag) { if(opening.indexOf(\"<\" + tag) >= 0) ishtml = true; });\n\tif(ishtml) return html_to_workbook(str, opts);\n\n\tXLMLFormatMap = ({\n\t\t\"General Number\": \"General\",\n\t\t\"General Date\": table_fmt[22],\n\t\t\"Long Date\": \"dddd, mmmm dd, yyyy\",\n\t\t\"Medium Date\": table_fmt[15],\n\t\t\"Short Date\": table_fmt[14],\n\t\t\"Long Time\": table_fmt[19],\n\t\t\"Medium Time\": table_fmt[18],\n\t\t\"Short Time\": table_fmt[20],\n\t\t\"Currency\": '\"$\"#,##0.00_);[Red]\\\\(\"$\"#,##0.00\\\\)',\n\t\t\"Fixed\": table_fmt[2],\n\t\t\"Standard\": table_fmt[4],\n\t\t\"Percent\": table_fmt[10],\n\t\t\"Scientific\": table_fmt[11],\n\t\t\"Yes/No\": '\"Yes\";\"Yes\";\"No\";@',\n\t\t\"True/False\": '\"True\";\"True\";\"False\";@',\n\t\t\"On/Off\": '\"Yes\";\"Yes\";\"No\";@'\n\t}/*:any*/);\n\n\n\tvar Rn;\n\tvar state = [], tmp;\n\tif(DENSE != null && opts.dense == null) opts.dense = DENSE;\n\tvar sheets = {}, sheetnames/*:Array<string>*/ = [], cursheet/*:Worksheet*/ = (opts.dense ? [] : {}), sheetname = \"\";\n\tvar cell = ({}/*:any*/), row = {};// eslint-disable-line no-unused-vars\n\tvar dtag = xlml_parsexmltag('<Data ss:Type=\"String\">'), didx = 0;\n\tvar c = 0, r = 0;\n\tvar refguess/*:Range*/ = {s: {r:2000000, c:2000000}, e: {r:0, c:0} };\n\tvar styles = {}, stag = {};\n\tvar ss = \"\", fidx = 0;\n\tvar merges/*:Array<Range>*/ = [];\n\tvar Props = {}, Custprops = {}, pidx = 0, cp = [];\n\tvar comments/*:Array<Comment>*/ = [], comment/*:Comment*/ = ({}/*:any*/);\n\tvar cstys = [], csty, seencol = false;\n\tvar arrayf/*:Array<[Range, string]>*/ = [];\n\tvar rowinfo/*:Array<RowInfo>*/ = [], rowobj = {}, cc = 0, rr = 0;\n\tvar Workbook/*:WBWBProps*/ = ({ Sheets:[], WBProps:{date1904:false} }/*:any*/), wsprops = {};\n\txlmlregex.lastIndex = 0;\n\tstr = str.replace(/<!--([\\s\\S]*?)-->/mg,\"\");\n\tvar raw_Rn3 = \"\";\n\twhile((Rn = xlmlregex.exec(str))) switch((Rn[3] = (raw_Rn3 = Rn[3]).toLowerCase())) {\n\t\tcase 'data' /*case 'Data'*/:\n\t\t\tif(raw_Rn3 == \"data\") {\n\t\t\t\tif(Rn[1]==='/'){if((tmp=state.pop())[0]!==Rn[3]) throw new Error(\"Bad state: \"+tmp.join(\"|\"));}\n\t\t\t\telse if(Rn[0].charAt(Rn[0].length-2) !== '/') state.push([Rn[3], true]);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tif(state[state.length-1][1]) break;\n\t\t\tif(Rn[1]==='/') parse_xlml_data(str.slice(didx, Rn.index), ss, dtag, state[state.length-1][0]==/*\"Comment\"*/\"comment\"?comment:cell, {c:c,r:r}, styles, cstys[c], row, arrayf, opts);\n\t\t\telse { ss = \"\"; dtag = xlml_parsexmltag(Rn[0]); didx = Rn.index + Rn[0].length; }\n\t\t\tbreak;\n\t\tcase 'cell' /*case 'Cell'*/:\n\t\t\tif(Rn[1]==='/'){\n\t\t\t\tif(comments.length > 0) cell.c = comments;\n\t\t\t\tif((!opts.sheetRows || opts.sheetRows > r) && cell.v !== undefined) {\n\t\t\t\t\tif(opts.dense) {\n\t\t\t\t\t\tif(!cursheet[r]) cursheet[r] = [];\n\t\t\t\t\t\tcursheet[r][c] = cell;\n\t\t\t\t\t} else cursheet[encode_col(c) + encode_row(r)] = cell;\n\t\t\t\t}\n\t\t\t\tif(cell.HRef) {\n\t\t\t\t\tcell.l = ({Target:unescapexml(cell.HRef)}/*:any*/);\n\t\t\t\t\tif(cell.HRefScreenTip) cell.l.Tooltip = cell.HRefScreenTip;\n\t\t\t\t\tdelete cell.HRef; delete cell.HRefScreenTip;\n\t\t\t\t}\n\t\t\t\tif(cell.MergeAcross || cell.MergeDown) {\n\t\t\t\t\tcc = c + (parseInt(cell.MergeAcross,10)|0);\n\t\t\t\t\trr = r + (parseInt(cell.MergeDown,10)|0);\n\t\t\t\t\tmerges.push({s:{c:c,r:r},e:{c:cc,r:rr}});\n\t\t\t\t}\n\t\t\t\tif(!opts.sheetStubs) { if(cell.MergeAcross) c = cc + 1; else ++c; }\n\t\t\t\telse if(cell.MergeAcross || cell.MergeDown) {\n\t\t\t\t\t/*:: if(!cc) cc = 0; if(!rr) rr = 0; */\n\t\t\t\t\tfor(var cma = c; cma <= cc; ++cma) {\n\t\t\t\t\t\tfor(var cmd = r; cmd <= rr; ++cmd) {\n\t\t\t\t\t\t\tif(cma > c || cmd > r) {\n\t\t\t\t\t\t\t\tif(opts.dense) {\n\t\t\t\t\t\t\t\t\tif(!cursheet[cmd]) cursheet[cmd] = [];\n\t\t\t\t\t\t\t\t\tcursheet[cmd][cma] = {t:'z'};\n\t\t\t\t\t\t\t\t} else cursheet[encode_col(cma) + encode_row(cmd)] = {t:'z'};\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tc = cc + 1;\n\t\t\t\t}\n\t\t\t\telse ++c;\n\t\t\t} else {\n\t\t\t\tcell = xlml_parsexmltagobj(Rn[0]);\n\t\t\t\tif(cell.Index) c = +cell.Index - 1;\n\t\t\t\tif(c < refguess.s.c) refguess.s.c = c;\n\t\t\t\tif(c > refguess.e.c) refguess.e.c = c;\n\t\t\t\tif(Rn[0].slice(-2) === \"/>\") ++c;\n\t\t\t\tcomments = [];\n\t\t\t}\n\t\t\tbreak;\n\t\tcase 'row' /*case 'Row'*/:\n\t\t\tif(Rn[1]==='/' || Rn[0].slice(-2) === \"/>\") {\n\t\t\t\tif(r < refguess.s.r) refguess.s.r = r;\n\t\t\t\tif(r > refguess.e.r) refguess.e.r = r;\n\t\t\t\tif(Rn[0].slice(-2) === \"/>\") {\n\t\t\t\t\trow = xlml_parsexmltag(Rn[0]);\n\t\t\t\t\tif(row.Index) r = +row.Index - 1;\n\t\t\t\t}\n\t\t\t\tc = 0; ++r;\n\t\t\t} else {\n\t\t\t\trow = xlml_parsexmltag(Rn[0]);\n\t\t\t\tif(row.Index) r = +row.Index - 1;\n\t\t\t\trowobj = {};\n\t\t\t\tif(row.AutoFitHeight == \"0\" || row.Height) {\n\t\t\t\t\trowobj.hpx = parseInt(row.Height, 10); rowobj.hpt = px2pt(rowobj.hpx);\n\t\t\t\t\trowinfo[r] = rowobj;\n\t\t\t\t}\n\t\t\t\tif(row.Hidden == \"1\") { rowobj.hidden = true; rowinfo[r] = rowobj; }\n\t\t\t}\n\t\t\tbreak;\n\t\tcase 'worksheet' /*case 'Worksheet'*/: /* TODO: read range from FullRows/FullColumns */\n\t\t\tif(Rn[1]==='/'){\n\t\t\t\tif((tmp=state.pop())[0]!==Rn[3]) throw new Error(\"Bad state: \"+tmp.join(\"|\"));\n\t\t\t\tsheetnames.push(sheetname);\n\t\t\t\tif(refguess.s.r <= refguess.e.r && refguess.s.c <= refguess.e.c) {\n\t\t\t\t\tcursheet[\"!ref\"] = encode_range(refguess);\n\t\t\t\t\tif(opts.sheetRows && opts.sheetRows <= refguess.e.r) {\n\t\t\t\t\t\tcursheet[\"!fullref\"] = cursheet[\"!ref\"];\n\t\t\t\t\t\trefguess.e.r = opts.sheetRows - 1;\n\t\t\t\t\t\tcursheet[\"!ref\"] = encode_range(refguess);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif(merges.length) cursheet[\"!merges\"] = merges;\n\t\t\t\tif(cstys.length > 0) cursheet[\"!cols\"] = cstys;\n\t\t\t\tif(rowinfo.length > 0) cursheet[\"!rows\"] = rowinfo;\n\t\t\t\tsheets[sheetname] = cursheet;\n\t\t\t} else {\n\t\t\t\trefguess = {s: {r:2000000, c:2000000}, e: {r:0, c:0} };\n\t\t\t\tr = c = 0;\n\t\t\t\tstate.push([Rn[3], false]);\n\t\t\t\ttmp = xlml_parsexmltag(Rn[0]);\n\t\t\t\tsheetname = unescapexml(tmp.Name);\n\t\t\t\tcursheet = (opts.dense ? [] : {});\n\t\t\t\tmerges = [];\n\t\t\t\tarrayf = [];\n\t\t\t\trowinfo = [];\n\t\t\t\twsprops = {name:sheetname, Hidden:0};\n\t\t\t\tWorkbook.Sheets.push(wsprops);\n\t\t\t}\n\t\t\tbreak;\n\t\tcase 'table' /*case 'Table'*/:\n\t\t\tif(Rn[1]==='/'){if((tmp=state.pop())[0]!==Rn[3]) throw new Error(\"Bad state: \"+tmp.join(\"|\"));}\n\t\t\telse if(Rn[0].slice(-2) == \"/>\") break;\n\t\t\telse {\n\t\t\t\tstate.push([Rn[3], false]);\n\t\t\t\tcstys = []; seencol = false;\n\t\t\t}\n\t\t\tbreak;\n\n\t\tcase 'style' /*case 'Style'*/:\n\t\t\tif(Rn[1]==='/') process_style_xlml(styles, stag, opts);\n\t\t\telse stag = xlml_parsexmltag(Rn[0]);\n\t\t\tbreak;\n\n\t\tcase 'numberformat' /*case 'NumberFormat'*/:\n\t\t\tstag.nf = unescapexml(xlml_parsexmltag(Rn[0]).Format || \"General\");\n\t\t\tif(XLMLFormatMap[stag.nf]) stag.nf = XLMLFormatMap[stag.nf];\n\t\t\tfor(var ssfidx = 0; ssfidx != 0x188; ++ssfidx) if(table_fmt[ssfidx] == stag.nf) break;\n\t\t\tif(ssfidx == 0x188) for(ssfidx = 0x39; ssfidx != 0x188; ++ssfidx) if(table_fmt[ssfidx] == null) { SSF_load(stag.nf, ssfidx); break; }\n\t\t\tbreak;\n\n\t\tcase 'column' /*case 'Column'*/:\n\t\t\tif(state[state.length-1][0] !== /*'Table'*/'table') break;\n\t\t\tcsty = xlml_parsexmltag(Rn[0]);\n\t\t\tif(csty.Hidden) { csty.hidden = true; delete csty.Hidden; }\n\t\t\tif(csty.Width) csty.wpx = parseInt(csty.Width, 10);\n\t\t\tif(!seencol && csty.wpx > 10) {\n\t\t\t\tseencol = true; MDW = DEF_MDW; //find_mdw_wpx(csty.wpx);\n\t\t\t\tfor(var _col = 0; _col < cstys.length; ++_col) if(cstys[_col]) process_col(cstys[_col]);\n\t\t\t}\n\t\t\tif(seencol) process_col(csty);\n\t\t\tcstys[(csty.Index-1||cstys.length)] = csty;\n\t\t\tfor(var i = 0; i < +csty.Span; ++i) cstys[cstys.length] = dup(csty);\n\t\t\tbreak;\n\n\t\tcase 'namedrange' /*case 'NamedRange'*/:\n\t\t\tif(Rn[1]==='/') break;\n\t\t\tif(!Workbook.Names) Workbook.Names = [];\n\t\t\tvar _NamedRange = parsexmltag(Rn[0]);\n\t\t\tvar _DefinedName/*:DefinedName*/ = ({\n\t\t\t\tName: _NamedRange.Name,\n\t\t\t\tRef: rc_to_a1(_NamedRange.RefersTo.slice(1), {r:0, c:0})\n\t\t\t}/*:any*/);\n\t\t\tif(Workbook.Sheets.length>0) _DefinedName.Sheet=Workbook.Sheets.length-1;\n\t\t\t/*:: if(Workbook.Names) */Workbook.Names.push(_DefinedName);\n\t\t\tbreak;\n\n\t\tcase 'namedcell' /*case 'NamedCell'*/: break;\n\t\tcase 'b' /*case 'B'*/: break;\n\t\tcase 'i' /*case 'I'*/: break;\n\t\tcase 'u' /*case 'U'*/: break;\n\t\tcase 's' /*case 'S'*/: break;\n\t\tcase 'em' /*case 'EM'*/: break;\n\t\tcase 'h2' /*case 'H2'*/: break;\n\t\tcase 'h3' /*case 'H3'*/: break;\n\t\tcase 'sub' /*case 'Sub'*/: break;\n\t\tcase 'sup' /*case 'Sup'*/: break;\n\t\tcase 'span' /*case 'Span'*/: break;\n\t\tcase 'alignment' /*case 'Alignment'*/:\n\t\t\tbreak;\n\t\tcase 'borders' /*case 'Borders'*/: break;\n\t\tcase 'border' /*case 'Border'*/: break;\n\t\tcase 'font' /*case 'Font'*/:\n\t\t\tif(Rn[0].slice(-2) === \"/>\") break;\n\t\t\telse if(Rn[1]===\"/\") ss += str.slice(fidx, Rn.index);\n\t\t\telse fidx = Rn.index + Rn[0].length;\n\t\t\tbreak;\n\t\tcase 'interior' /*case 'Interior'*/:\n\t\t\tif(!opts.cellStyles) break;\n\t\t\tstag.Interior = xlml_parsexmltag(Rn[0]);\n\t\t\tbreak;\n\t\tcase 'protection' /*case 'Protection'*/: break;\n\n\t\tcase 'author' /*case 'Author'*/:\n\t\tcase 'title' /*case 'Title'*/:\n\t\tcase 'description' /*case 'Description'*/:\n\t\tcase 'created' /*case 'Created'*/:\n\t\tcase 'keywords' /*case 'Keywords'*/:\n\t\tcase 'subject' /*case 'Subject'*/:\n\t\tcase 'category' /*case 'Category'*/:\n\t\tcase 'company' /*case 'Company'*/:\n\t\tcase 'lastauthor' /*case 'LastAuthor'*/:\n\t\tcase 'lastsaved' /*case 'LastSaved'*/:\n\t\tcase 'lastprinted' /*case 'LastPrinted'*/:\n\t\tcase 'version' /*case 'Version'*/:\n\t\tcase 'revision' /*case 'Revision'*/:\n\t\tcase 'totaltime' /*case 'TotalTime'*/:\n\t\tcase 'hyperlinkbase' /*case 'HyperlinkBase'*/:\n\t\tcase 'manager' /*case 'Manager'*/:\n\t\tcase 'contentstatus' /*case 'ContentStatus'*/:\n\t\tcase 'identifier' /*case 'Identifier'*/:\n\t\tcase 'language' /*case 'Language'*/:\n\t\tcase 'appname' /*case 'AppName'*/:\n\t\t\tif(Rn[0].slice(-2) === \"/>\") break;\n\t\t\telse if(Rn[1]===\"/\") xlml_set_prop(Props, raw_Rn3, str.slice(pidx, Rn.index));\n\t\t\telse pidx = Rn.index + Rn[0].length;\n\t\t\tbreak;\n\t\tcase 'paragraphs' /*case 'Paragraphs'*/: break;\n\n\t\tcase 'styles' /*case 'Styles'*/:\n\t\tcase 'workbook' /*case 'Workbook'*/:\n\t\t\tif(Rn[1]==='/'){if((tmp=state.pop())[0]!==Rn[3]) throw new Error(\"Bad state: \"+tmp.join(\"|\"));}\n\t\t\telse state.push([Rn[3], false]);\n\t\t\tbreak;\n\n\t\tcase 'comment' /*case 'Comment'*/:\n\t\t\tif(Rn[1]==='/'){\n\t\t\t\tif((tmp=state.pop())[0]!==Rn[3]) throw new Error(\"Bad state: \"+tmp.join(\"|\"));\n\t\t\t\txlml_clean_comment(comment);\n\t\t\t\tcomments.push(comment);\n\t\t\t} else {\n\t\t\t\tstate.push([Rn[3], false]);\n\t\t\t\ttmp = xlml_parsexmltag(Rn[0]);\n\t\t\t\tcomment = ({a:tmp.Author}/*:any*/);\n\t\t\t}\n\t\t\tbreak;\n\n\t\tcase 'autofilter' /*case 'AutoFilter'*/:\n\t\t\tif(Rn[1]==='/'){if((tmp=state.pop())[0]!==Rn[3]) throw new Error(\"Bad state: \"+tmp.join(\"|\"));}\n\t\t\telse if(Rn[0].charAt(Rn[0].length-2) !== '/') {\n\t\t\t\tvar AutoFilter = xlml_parsexmltag(Rn[0]);\n\t\t\t\tcursheet['!autofilter'] = { ref:rc_to_a1(AutoFilter.Range).replace(/\\$/g,\"\") };\n\t\t\t\tstate.push([Rn[3], true]);\n\t\t\t}\n\t\t\tbreak;\n\n\t\tcase 'name' /*case 'Name'*/: break;\n\n\t\tcase 'datavalidation' /*case 'DataValidation'*/:\n\t\t\tif(Rn[1]==='/'){\n\t\t\t\tif((tmp=state.pop())[0]!==Rn[3]) throw new Error(\"Bad state: \"+tmp.join(\"|\"));\n\t\t\t} else {\n\t\t\t\tif(Rn[0].charAt(Rn[0].length-2) !== '/') state.push([Rn[3], true]);\n\t\t\t}\n\t\t\tbreak;\n\n\t\tcase 'pixelsperinch' /*case 'PixelsPerInch'*/:\n\t\t\tbreak;\n\t\tcase 'componentoptions' /*case 'ComponentOptions'*/:\n\t\tcase 'documentproperties' /*case 'DocumentProperties'*/:\n\t\tcase 'customdocumentproperties' /*case 'CustomDocumentProperties'*/:\n\t\tcase 'officedocumentsettings' /*case 'OfficeDocumentSettings'*/:\n\t\tcase 'pivottable' /*case 'PivotTable'*/:\n\t\tcase 'pivotcache' /*case 'PivotCache'*/:\n\t\tcase 'names' /*case 'Names'*/:\n\t\tcase 'mapinfo' /*case 'MapInfo'*/:\n\t\tcase 'pagebreaks' /*case 'PageBreaks'*/:\n\t\tcase 'querytable' /*case 'QueryTable'*/:\n\t\tcase 'sorting' /*case 'Sorting'*/:\n\t\tcase 'schema' /*case 'Schema'*/: //case 'data' /*case 'data'*/:\n\t\tcase 'conditionalformatting' /*case 'ConditionalFormatting'*/:\n\t\tcase 'smarttagtype' /*case 'SmartTagType'*/:\n\t\tcase 'smarttags' /*case 'SmartTags'*/:\n\t\tcase 'excelworkbook' /*case 'ExcelWorkbook'*/:\n\t\tcase 'workbookoptions' /*case 'WorkbookOptions'*/:\n\t\tcase 'worksheetoptions' /*case 'WorksheetOptions'*/:\n\t\t\tif(Rn[1]==='/'){if((tmp=state.pop())[0]!==Rn[3]) throw new Error(\"Bad state: \"+tmp.join(\"|\"));}\n\t\t\telse if(Rn[0].charAt(Rn[0].length-2) !== '/') state.push([Rn[3], true]);\n\t\t\tbreak;\n\n\t\tcase 'null' /*case 'Null'*/: break;\n\n\t\tdefault:\n\t\t\t/* FODS file root is <office:document> */\n\t\t\tif(state.length == 0 && Rn[3] == \"document\") return parse_fods(str, opts);\n\t\t\t/* UOS file root is <uof:UOF> */\n\t\t\tif(state.length == 0 && Rn[3] == \"uof\"/*\"UOF\"*/) return parse_fods(str, opts);\n\n\t\t\tvar seen = true;\n\t\t\tswitch(state[state.length-1][0]) {\n\t\t\t\t/* OfficeDocumentSettings */\n\t\t\t\tcase 'officedocumentsettings' /*case 'OfficeDocumentSettings'*/: switch(Rn[3]) {\n\t\t\t\t\tcase 'allowpng' /*case 'AllowPNG'*/: break;\n\t\t\t\t\tcase 'removepersonalinformation' /*case 'RemovePersonalInformation'*/: break;\n\t\t\t\t\tcase 'downloadcomponents' /*case 'DownloadComponents'*/: break;\n\t\t\t\t\tcase 'locationofcomponents' /*case 'LocationOfComponents'*/: break;\n\t\t\t\t\tcase 'colors' /*case 'Colors'*/: break;\n\t\t\t\t\tcase 'color' /*case 'Color'*/: break;\n\t\t\t\t\tcase 'index' /*case 'Index'*/: break;\n\t\t\t\t\tcase 'rgb' /*case 'RGB'*/: break;\n\t\t\t\t\tcase 'targetscreensize' /*case 'TargetScreenSize'*/: break;\n\t\t\t\t\tcase 'readonlyrecommended' /*case 'ReadOnlyRecommended'*/: break;\n\t\t\t\t\tdefault: seen = false;\n\t\t\t\t} break;\n\n\t\t\t\t/* ComponentOptions */\n\t\t\t\tcase 'componentoptions' /*case 'ComponentOptions'*/: switch(Rn[3]) {\n\t\t\t\t\tcase 'toolbar' /*case 'Toolbar'*/: break;\n\t\t\t\t\tcase 'hideofficelogo' /*case 'HideOfficeLogo'*/: break;\n\t\t\t\t\tcase 'spreadsheetautofit' /*case 'SpreadsheetAutoFit'*/: break;\n\t\t\t\t\tcase 'label' /*case 'Label'*/: break;\n\t\t\t\t\tcase 'caption' /*case 'Caption'*/: break;\n\t\t\t\t\tcase 'maxheight' /*case 'MaxHeight'*/: break;\n\t\t\t\t\tcase 'maxwidth' /*case 'MaxWidth'*/: break;\n\t\t\t\t\tcase 'nextsheetnumber' /*case 'NextSheetNumber'*/: break;\n\t\t\t\t\tdefault: seen = false;\n\t\t\t\t} break;\n\n\t\t\t\t/* ExcelWorkbook */\n\t\t\t\tcase 'excelworkbook' /*case 'ExcelWorkbook'*/: switch(Rn[3]) {\n\t\t\t\t\tcase 'date1904' /*case 'Date1904'*/:\n\t\t\t\t\t\t/*:: if(!Workbook.WBProps) Workbook.WBProps = {}; */\n\t\t\t\t\t\tWorkbook.WBProps.date1904 = true;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase 'windowheight' /*case 'WindowHeight'*/: break;\n\t\t\t\t\tcase 'windowwidth' /*case 'WindowWidth'*/: break;\n\t\t\t\t\tcase 'windowtopx' /*case 'WindowTopX'*/: break;\n\t\t\t\t\tcase 'windowtopy' /*case 'WindowTopY'*/: break;\n\t\t\t\t\tcase 'tabratio' /*case 'TabRatio'*/: break;\n\t\t\t\t\tcase 'protectstructure' /*case 'ProtectStructure'*/: break;\n\t\t\t\t\tcase 'protectwindow' /*case 'ProtectWindow'*/: break;\n\t\t\t\t\tcase 'protectwindows' /*case 'ProtectWindows'*/: break;\n\t\t\t\t\tcase 'activesheet' /*case 'ActiveSheet'*/: break;\n\t\t\t\t\tcase 'displayinknotes' /*case 'DisplayInkNotes'*/: break;\n\t\t\t\t\tcase 'firstvisiblesheet' /*case 'FirstVisibleSheet'*/: break;\n\t\t\t\t\tcase 'supbook' /*case 'SupBook'*/: break;\n\t\t\t\t\tcase 'sheetname' /*case 'SheetName'*/: break;\n\t\t\t\t\tcase 'sheetindex' /*case 'SheetIndex'*/: break;\n\t\t\t\t\tcase 'sheetindexfirst' /*case 'SheetIndexFirst'*/: break;\n\t\t\t\t\tcase 'sheetindexlast' /*case 'SheetIndexLast'*/: break;\n\t\t\t\t\tcase 'dll' /*case 'Dll'*/: break;\n\t\t\t\t\tcase 'acceptlabelsinformulas' /*case 'AcceptLabelsInFormulas'*/: break;\n\t\t\t\t\tcase 'donotsavelinkvalues' /*case 'DoNotSaveLinkValues'*/: break;\n\t\t\t\t\tcase 'iteration' /*case 'Iteration'*/: break;\n\t\t\t\t\tcase 'maxiterations' /*case 'MaxIterations'*/: break;\n\t\t\t\t\tcase 'maxchange' /*case 'MaxChange'*/: break;\n\t\t\t\t\tcase 'path' /*case 'Path'*/: break;\n\t\t\t\t\tcase 'xct' /*case 'Xct'*/: break;\n\t\t\t\t\tcase 'count' /*case 'Count'*/: break;\n\t\t\t\t\tcase 'selectedsheets' /*case 'SelectedSheets'*/: break;\n\t\t\t\t\tcase 'calculation' /*case 'Calculation'*/: break;\n\t\t\t\t\tcase 'uncalced' /*case 'Uncalced'*/: break;\n\t\t\t\t\tcase 'startupprompt' /*case 'StartupPrompt'*/: break;\n\t\t\t\t\tcase 'crn' /*case 'Crn'*/: break;\n\t\t\t\t\tcase 'externname' /*case 'ExternName'*/: break;\n\t\t\t\t\tcase 'formula' /*case 'Formula'*/: break;\n\t\t\t\t\tcase 'colfirst' /*case 'ColFirst'*/: break;\n\t\t\t\t\tcase 'collast' /*case 'ColLast'*/: break;\n\t\t\t\t\tcase 'wantadvise' /*case 'WantAdvise'*/: break;\n\t\t\t\t\tcase 'boolean' /*case 'Boolean'*/: break;\n\t\t\t\t\tcase 'error' /*case 'Error'*/: break;\n\t\t\t\t\tcase 'text' /*case 'Text'*/: break;\n\t\t\t\t\tcase 'ole' /*case 'OLE'*/: break;\n\t\t\t\t\tcase 'noautorecover' /*case 'NoAutoRecover'*/: break;\n\t\t\t\t\tcase 'publishobjects' /*case 'PublishObjects'*/: break;\n\t\t\t\t\tcase 'donotcalculatebeforesave' /*case 'DoNotCalculateBeforeSave'*/: break;\n\t\t\t\t\tcase 'number' /*case 'Number'*/: break;\n\t\t\t\t\tcase 'refmoder1c1' /*case 'RefModeR1C1'*/: break;\n\t\t\t\t\tcase 'embedsavesmarttags' /*case 'EmbedSaveSmartTags'*/: break;\n\t\t\t\t\tdefault: seen = false;\n\t\t\t\t} break;\n\n\t\t\t\t/* WorkbookOptions */\n\t\t\t\tcase 'workbookoptions' /*case 'WorkbookOptions'*/: switch(Rn[3]) {\n\t\t\t\t\tcase 'owcversion' /*case 'OWCVersion'*/: break;\n\t\t\t\t\tcase 'height' /*case 'Height'*/: break;\n\t\t\t\t\tcase 'width' /*case 'Width'*/: break;\n\t\t\t\t\tdefault: seen = false;\n\t\t\t\t} break;\n\n\t\t\t\t/* WorksheetOptions */\n\t\t\t\tcase 'worksheetoptions' /*case 'WorksheetOptions'*/: switch(Rn[3]) {\n\t\t\t\t\tcase 'visible' /*case 'Visible'*/:\n\t\t\t\t\t\tif(Rn[0].slice(-2) === \"/>\"){/* empty */}\n\t\t\t\t\t\telse if(Rn[1]===\"/\") switch(str.slice(pidx, Rn.index)) {\n\t\t\t\t\t\t\tcase \"SheetHidden\": wsprops.Hidden = 1; break;\n\t\t\t\t\t\t\tcase \"SheetVeryHidden\": wsprops.Hidden = 2; break;\n\t\t\t\t\t\t}\n\t\t\t\t\t\telse pidx = Rn.index + Rn[0].length;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase 'header' /*case 'Header'*/:\n\t\t\t\t\t\tif(!cursheet['!margins']) default_margins(cursheet['!margins']={}, 'xlml');\n\t\t\t\t\t\tif(!isNaN(+parsexmltag(Rn[0]).Margin)) cursheet['!margins'].header = +parsexmltag(Rn[0]).Margin;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase 'footer' /*case 'Footer'*/:\n\t\t\t\t\t\tif(!cursheet['!margins']) default_margins(cursheet['!margins']={}, 'xlml');\n\t\t\t\t\t\tif(!isNaN(+parsexmltag(Rn[0]).Margin)) cursheet['!margins'].footer = +parsexmltag(Rn[0]).Margin;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase 'pagemargins' /*case 'PageMargins'*/:\n\t\t\t\t\t\tvar pagemargins = parsexmltag(Rn[0]);\n\t\t\t\t\t\tif(!cursheet['!margins']) default_margins(cursheet['!margins']={},'xlml');\n\t\t\t\t\t\tif(!isNaN(+pagemargins.Top)) cursheet['!margins'].top = +pagemargins.Top;\n\t\t\t\t\t\tif(!isNaN(+pagemargins.Left)) cursheet['!margins'].left = +pagemargins.Left;\n\t\t\t\t\t\tif(!isNaN(+pagemargins.Right)) cursheet['!margins'].right = +pagemargins.Right;\n\t\t\t\t\t\tif(!isNaN(+pagemargins.Bottom)) cursheet['!margins'].bottom = +pagemargins.Bottom;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase 'displayrighttoleft' /*case 'DisplayRightToLeft'*/:\n\t\t\t\t\t\tif(!Workbook.Views) Workbook.Views = [];\n\t\t\t\t\t\tif(!Workbook.Views[0]) Workbook.Views[0] = {};\n\t\t\t\t\t\tWorkbook.Views[0].RTL = true;\n\t\t\t\t\t\tbreak;\n\n\t\t\t\t\tcase 'freezepanes' /*case 'FreezePanes'*/: break;\n\t\t\t\t\tcase 'frozennosplit' /*case 'FrozenNoSplit'*/: break;\n\n\t\t\t\t\tcase 'splithorizontal' /*case 'SplitHorizontal'*/:\n\t\t\t\t\tcase 'splitvertical' /*case 'SplitVertical'*/:\n\t\t\t\t\t\tbreak;\n\n\t\t\t\t\tcase 'donotdisplaygridlines' /*case 'DoNotDisplayGridlines'*/:\n\t\t\t\t\t\tbreak;\n\n\t\t\t\t\tcase 'activerow' /*case 'ActiveRow'*/: break;\n\t\t\t\t\tcase 'activecol' /*case 'ActiveCol'*/: break;\n\t\t\t\t\tcase 'toprowbottompane' /*case 'TopRowBottomPane'*/: break;\n\t\t\t\t\tcase 'leftcolumnrightpane' /*case 'LeftColumnRightPane'*/: break;\n\n\t\t\t\t\tcase 'unsynced' /*case 'Unsynced'*/: break;\n\t\t\t\t\tcase 'print' /*case 'Print'*/: break;\n\t\t\t\t\tcase 'printerrors' /*case 'PrintErrors'*/: break;\n\t\t\t\t\tcase 'panes' /*case 'Panes'*/: break;\n\t\t\t\t\tcase 'scale' /*case 'Scale'*/: break;\n\t\t\t\t\tcase 'pane' /*case 'Pane'*/: break;\n\t\t\t\t\tcase 'number' /*case 'Number'*/: break;\n\t\t\t\t\tcase 'layout' /*case 'Layout'*/: break;\n\t\t\t\t\tcase 'pagesetup' /*case 'PageSetup'*/: break;\n\t\t\t\t\tcase 'selected' /*case 'Selected'*/: break;\n\t\t\t\t\tcase 'protectobjects' /*case 'ProtectObjects'*/: break;\n\t\t\t\t\tcase 'enableselection' /*case 'EnableSelection'*/: break;\n\t\t\t\t\tcase 'protectscenarios' /*case 'ProtectScenarios'*/: break;\n\t\t\t\t\tcase 'validprinterinfo' /*case 'ValidPrinterInfo'*/: break;\n\t\t\t\t\tcase 'horizontalresolution' /*case 'HorizontalResolution'*/: break;\n\t\t\t\t\tcase 'verticalresolution' /*case 'VerticalResolution'*/: break;\n\t\t\t\t\tcase 'numberofcopies' /*case 'NumberofCopies'*/: break;\n\t\t\t\t\tcase 'activepane' /*case 'ActivePane'*/: break;\n\t\t\t\t\tcase 'toprowvisible' /*case 'TopRowVisible'*/: break;\n\t\t\t\t\tcase 'leftcolumnvisible' /*case 'LeftColumnVisible'*/: break;\n\t\t\t\t\tcase 'fittopage' /*case 'FitToPage'*/: break;\n\t\t\t\t\tcase 'rangeselection' /*case 'RangeSelection'*/: break;\n\t\t\t\t\tcase 'papersizeindex' /*case 'PaperSizeIndex'*/: break;\n\t\t\t\t\tcase 'pagelayoutzoom' /*case 'PageLayoutZoom'*/: break;\n\t\t\t\t\tcase 'pagebreakzoom' /*case 'PageBreakZoom'*/: break;\n\t\t\t\t\tcase 'filteron' /*case 'FilterOn'*/: break;\n\t\t\t\t\tcase 'fitwidth' /*case 'FitWidth'*/: break;\n\t\t\t\t\tcase 'fitheight' /*case 'FitHeight'*/: break;\n\t\t\t\t\tcase 'commentslayout' /*case 'CommentsLayout'*/: break;\n\t\t\t\t\tcase 'zoom' /*case 'Zoom'*/: break;\n\t\t\t\t\tcase 'lefttoright' /*case 'LeftToRight'*/: break;\n\t\t\t\t\tcase 'gridlines' /*case 'Gridlines'*/: break;\n\t\t\t\t\tcase 'allowsort' /*case 'AllowSort'*/: break;\n\t\t\t\t\tcase 'allowfilter' /*case 'AllowFilter'*/: break;\n\t\t\t\t\tcase 'allowinsertrows' /*case 'AllowInsertRows'*/: break;\n\t\t\t\t\tcase 'allowdeleterows' /*case 'AllowDeleteRows'*/: break;\n\t\t\t\t\tcase 'allowinsertcols' /*case 'AllowInsertCols'*/: break;\n\t\t\t\t\tcase 'allowdeletecols' /*case 'AllowDeleteCols'*/: break;\n\t\t\t\t\tcase 'allowinserthyperlinks' /*case 'AllowInsertHyperlinks'*/: break;\n\t\t\t\t\tcase 'allowformatcells' /*case 'AllowFormatCells'*/: break;\n\t\t\t\t\tcase 'allowsizecols' /*case 'AllowSizeCols'*/: break;\n\t\t\t\t\tcase 'allowsizerows' /*case 'AllowSizeRows'*/: break;\n\t\t\t\t\tcase 'nosummaryrowsbelowdetail' /*case 'NoSummaryRowsBelowDetail'*/:\n\t\t\t\t\t\tif(!cursheet[\"!outline\"]) cursheet[\"!outline\"] = {};\n\t\t\t\t\t\tcursheet[\"!outline\"].above = true;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase 'tabcolorindex' /*case 'TabColorIndex'*/: break;\n\t\t\t\t\tcase 'donotdisplayheadings' /*case 'DoNotDisplayHeadings'*/: break;\n\t\t\t\t\tcase 'showpagelayoutzoom' /*case 'ShowPageLayoutZoom'*/: break;\n\t\t\t\t\tcase 'nosummarycolumnsrightdetail' /*case 'NoSummaryColumnsRightDetail'*/:\n\t\t\t\t\t\tif(!cursheet[\"!outline\"]) cursheet[\"!outline\"] = {};\n\t\t\t\t\t\tcursheet[\"!outline\"].left = true;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase 'blackandwhite' /*case 'BlackAndWhite'*/: break;\n\t\t\t\t\tcase 'donotdisplayzeros' /*case 'DoNotDisplayZeros'*/: break;\n\t\t\t\t\tcase 'displaypagebreak' /*case 'DisplayPageBreak'*/: break;\n\t\t\t\t\tcase 'rowcolheadings' /*case 'RowColHeadings'*/: break;\n\t\t\t\t\tcase 'donotdisplayoutline' /*case 'DoNotDisplayOutline'*/: break;\n\t\t\t\t\tcase 'noorientation' /*case 'NoOrientation'*/: break;\n\t\t\t\t\tcase 'allowusepivottables' /*case 'AllowUsePivotTables'*/: break;\n\t\t\t\t\tcase 'zeroheight' /*case 'ZeroHeight'*/: break;\n\t\t\t\t\tcase 'viewablerange' /*case 'ViewableRange'*/: break;\n\t\t\t\t\tcase 'selection' /*case 'Selection'*/: break;\n\t\t\t\t\tcase 'protectcontents' /*case 'ProtectContents'*/: break;\n\t\t\t\t\tdefault: seen = false;\n\t\t\t\t} break;\n\n\t\t\t\t/* PivotTable */\n\t\t\t\tcase 'pivottable' /*case 'PivotTable'*/: case 'pivotcache' /*case 'PivotCache'*/: switch(Rn[3]) {\n\t\t\t\t\tcase 'immediateitemsondrop' /*case 'ImmediateItemsOnDrop'*/: break;\n\t\t\t\t\tcase 'showpagemultipleitemlabel' /*case 'ShowPageMultipleItemLabel'*/: break;\n\t\t\t\t\tcase 'compactrowindent' /*case 'CompactRowIndent'*/: break;\n\t\t\t\t\tcase 'location' /*case 'Location'*/: break;\n\t\t\t\t\tcase 'pivotfield' /*case 'PivotField'*/: break;\n\t\t\t\t\tcase 'orientation' /*case 'Orientation'*/: break;\n\t\t\t\t\tcase 'layoutform' /*case 'LayoutForm'*/: break;\n\t\t\t\t\tcase 'layoutsubtotallocation' /*case 'LayoutSubtotalLocation'*/: break;\n\t\t\t\t\tcase 'layoutcompactrow' /*case 'LayoutCompactRow'*/: break;\n\t\t\t\t\tcase 'position' /*case 'Position'*/: break;\n\t\t\t\t\tcase 'pivotitem' /*case 'PivotItem'*/: break;\n\t\t\t\t\tcase 'datatype' /*case 'DataType'*/: break;\n\t\t\t\t\tcase 'datafield' /*case 'DataField'*/: break;\n\t\t\t\t\tcase 'sourcename' /*case 'SourceName'*/: break;\n\t\t\t\t\tcase 'parentfield' /*case 'ParentField'*/: break;\n\t\t\t\t\tcase 'ptlineitems' /*case 'PTLineItems'*/: break;\n\t\t\t\t\tcase 'ptlineitem' /*case 'PTLineItem'*/: break;\n\t\t\t\t\tcase 'countofsameitems' /*case 'CountOfSameItems'*/: break;\n\t\t\t\t\tcase 'item' /*case 'Item'*/: break;\n\t\t\t\t\tcase 'itemtype' /*case 'ItemType'*/: break;\n\t\t\t\t\tcase 'ptsource' /*case 'PTSource'*/: break;\n\t\t\t\t\tcase 'cacheindex' /*case 'CacheIndex'*/: break;\n\t\t\t\t\tcase 'consolidationreference' /*case 'ConsolidationReference'*/: break;\n\t\t\t\t\tcase 'filename' /*case 'FileName'*/: break;\n\t\t\t\t\tcase 'reference' /*case 'Reference'*/: break;\n\t\t\t\t\tcase 'nocolumngrand' /*case 'NoColumnGrand'*/: break;\n\t\t\t\t\tcase 'norowgrand' /*case 'NoRowGrand'*/: break;\n\t\t\t\t\tcase 'blanklineafteritems' /*case 'BlankLineAfterItems'*/: break;\n\t\t\t\t\tcase 'hidden' /*case 'Hidden'*/: break;\n\t\t\t\t\tcase 'subtotal' /*case 'Subtotal'*/: break;\n\t\t\t\t\tcase 'basefield' /*case 'BaseField'*/: break;\n\t\t\t\t\tcase 'mapchilditems' /*case 'MapChildItems'*/: break;\n\t\t\t\t\tcase 'function' /*case 'Function'*/: break;\n\t\t\t\t\tcase 'refreshonfileopen' /*case 'RefreshOnFileOpen'*/: break;\n\t\t\t\t\tcase 'printsettitles' /*case 'PrintSetTitles'*/: break;\n\t\t\t\t\tcase 'mergelabels' /*case 'MergeLabels'*/: break;\n\t\t\t\t\tcase 'defaultversion' /*case 'DefaultVersion'*/: break;\n\t\t\t\t\tcase 'refreshname' /*case 'RefreshName'*/: break;\n\t\t\t\t\tcase 'refreshdate' /*case 'RefreshDate'*/: break;\n\t\t\t\t\tcase 'refreshdatecopy' /*case 'RefreshDateCopy'*/: break;\n\t\t\t\t\tcase 'versionlastrefresh' /*case 'VersionLastRefresh'*/: break;\n\t\t\t\t\tcase 'versionlastupdate' /*case 'VersionLastUpdate'*/: break;\n\t\t\t\t\tcase 'versionupdateablemin' /*case 'VersionUpdateableMin'*/: break;\n\t\t\t\t\tcase 'versionrefreshablemin' /*case 'VersionRefreshableMin'*/: break;\n\t\t\t\t\tcase 'calculation' /*case 'Calculation'*/: break;\n\t\t\t\t\tdefault: seen = false;\n\t\t\t\t} break;\n\n\t\t\t\t/* PageBreaks */\n\t\t\t\tcase 'pagebreaks' /*case 'PageBreaks'*/: switch(Rn[3]) {\n\t\t\t\t\tcase 'colbreaks' /*case 'ColBreaks'*/: break;\n\t\t\t\t\tcase 'colbreak' /*case 'ColBreak'*/: break;\n\t\t\t\t\tcase 'rowbreaks' /*case 'RowBreaks'*/: break;\n\t\t\t\t\tcase 'rowbreak' /*case 'RowBreak'*/: break;\n\t\t\t\t\tcase 'colstart' /*case 'ColStart'*/: break;\n\t\t\t\t\tcase 'colend' /*case 'ColEnd'*/: break;\n\t\t\t\t\tcase 'rowend' /*case 'RowEnd'*/: break;\n\t\t\t\t\tdefault: seen = false;\n\t\t\t\t} break;\n\n\t\t\t\t/* AutoFilter */\n\t\t\t\tcase 'autofilter' /*case 'AutoFilter'*/: switch(Rn[3]) {\n\t\t\t\t\tcase 'autofiltercolumn' /*case 'AutoFilterColumn'*/: break;\n\t\t\t\t\tcase 'autofiltercondition' /*case 'AutoFilterCondition'*/: break;\n\t\t\t\t\tcase 'autofilterand' /*case 'AutoFilterAnd'*/: break;\n\t\t\t\t\tcase 'autofilteror' /*case 'AutoFilterOr'*/: break;\n\t\t\t\t\tdefault: seen = false;\n\t\t\t\t} break;\n\n\t\t\t\t/* QueryTable */\n\t\t\t\tcase 'querytable' /*case 'QueryTable'*/: switch(Rn[3]) {\n\t\t\t\t\tcase 'id' /*case 'Id'*/: break;\n\t\t\t\t\tcase 'autoformatfont' /*case 'AutoFormatFont'*/: break;\n\t\t\t\t\tcase 'autoformatpattern' /*case 'AutoFormatPattern'*/: break;\n\t\t\t\t\tcase 'querysource' /*case 'QuerySource'*/: break;\n\t\t\t\t\tcase 'querytype' /*case 'QueryType'*/: break;\n\t\t\t\t\tcase 'enableredirections' /*case 'EnableRedirections'*/: break;\n\t\t\t\t\tcase 'refreshedinxl9' /*case 'RefreshedInXl9'*/: break;\n\t\t\t\t\tcase 'urlstring' /*case 'URLString'*/: break;\n\t\t\t\t\tcase 'htmltables' /*case 'HTMLTables'*/: break;\n\t\t\t\t\tcase 'connection' /*case 'Connection'*/: break;\n\t\t\t\t\tcase 'commandtext' /*case 'CommandText'*/: break;\n\t\t\t\t\tcase 'refreshinfo' /*case 'RefreshInfo'*/: break;\n\t\t\t\t\tcase 'notitles' /*case 'NoTitles'*/: break;\n\t\t\t\t\tcase 'nextid' /*case 'NextId'*/: break;\n\t\t\t\t\tcase 'columninfo' /*case 'ColumnInfo'*/: break;\n\t\t\t\t\tcase 'overwritecells' /*case 'OverwriteCells'*/: break;\n\t\t\t\t\tcase 'donotpromptforfile' /*case 'DoNotPromptForFile'*/: break;\n\t\t\t\t\tcase 'textwizardsettings' /*case 'TextWizardSettings'*/: break;\n\t\t\t\t\tcase 'source' /*case 'Source'*/: break;\n\t\t\t\t\tcase 'number' /*case 'Number'*/: break;\n\t\t\t\t\tcase 'decimal' /*case 'Decimal'*/: break;\n\t\t\t\t\tcase 'thousandseparator' /*case 'ThousandSeparator'*/: break;\n\t\t\t\t\tcase 'trailingminusnumbers' /*case 'TrailingMinusNumbers'*/: break;\n\t\t\t\t\tcase 'formatsettings' /*case 'FormatSettings'*/: break;\n\t\t\t\t\tcase 'fieldtype' /*case 'FieldType'*/: break;\n\t\t\t\t\tcase 'delimiters' /*case 'Delimiters'*/: break;\n\t\t\t\t\tcase 'tab' /*case 'Tab'*/: break;\n\t\t\t\t\tcase 'comma' /*case 'Comma'*/: break;\n\t\t\t\t\tcase 'autoformatname' /*case 'AutoFormatName'*/: break;\n\t\t\t\t\tcase 'versionlastedit' /*case 'VersionLastEdit'*/: break;\n\t\t\t\t\tcase 'versionlastrefresh' /*case 'VersionLastRefresh'*/: break;\n\t\t\t\t\tdefault: seen = false;\n\t\t\t\t} break;\n\n\t\t\t\tcase 'datavalidation' /*case 'DataValidation'*/:\n\t\t\t\tswitch(Rn[3]) {\n\t\t\t\t\tcase 'range' /*case 'Range'*/: break;\n\n\t\t\t\t\tcase 'type' /*case 'Type'*/: break;\n\t\t\t\t\tcase 'min' /*case 'Min'*/: break;\n\t\t\t\t\tcase 'max' /*case 'Max'*/: break;\n\t\t\t\t\tcase 'sort' /*case 'Sort'*/: break;\n\t\t\t\t\tcase 'descending' /*case 'Descending'*/: break;\n\t\t\t\t\tcase 'order' /*case 'Order'*/: break;\n\t\t\t\t\tcase 'casesensitive' /*case 'CaseSensitive'*/: break;\n\t\t\t\t\tcase 'value' /*case 'Value'*/: break;\n\t\t\t\t\tcase 'errorstyle' /*case 'ErrorStyle'*/: break;\n\t\t\t\t\tcase 'errormessage' /*case 'ErrorMessage'*/: break;\n\t\t\t\t\tcase 'errortitle' /*case 'ErrorTitle'*/: break;\n\t\t\t\t\tcase 'inputmessage' /*case 'InputMessage'*/: break;\n\t\t\t\t\tcase 'inputtitle' /*case 'InputTitle'*/: break;\n\t\t\t\t\tcase 'combohide' /*case 'ComboHide'*/: break;\n\t\t\t\t\tcase 'inputhide' /*case 'InputHide'*/: break;\n\t\t\t\t\tcase 'condition' /*case 'Condition'*/: break;\n\t\t\t\t\tcase 'qualifier' /*case 'Qualifier'*/: break;\n\t\t\t\t\tcase 'useblank' /*case 'UseBlank'*/: break;\n\t\t\t\t\tcase 'value1' /*case 'Value1'*/: break;\n\t\t\t\t\tcase 'value2' /*case 'Value2'*/: break;\n\t\t\t\t\tcase 'format' /*case 'Format'*/: break;\n\n\t\t\t\t\tcase 'cellrangelist' /*case 'CellRangeList'*/: break;\n\t\t\t\t\tdefault: seen = false;\n\t\t\t\t} break;\n\n\t\t\t\tcase 'sorting' /*case 'Sorting'*/:\n\t\t\t\tcase 'conditionalformatting' /*case 'ConditionalFormatting'*/:\n\t\t\t\tswitch(Rn[3]) {\n\t\t\t\t\tcase 'range' /*case 'Range'*/: break;\n\t\t\t\t\tcase 'type' /*case 'Type'*/: break;\n\t\t\t\t\tcase 'min' /*case 'Min'*/: break;\n\t\t\t\t\tcase 'max' /*case 'Max'*/: break;\n\t\t\t\t\tcase 'sort' /*case 'Sort'*/: break;\n\t\t\t\t\tcase 'descending' /*case 'Descending'*/: break;\n\t\t\t\t\tcase 'order' /*case 'Order'*/: break;\n\t\t\t\t\tcase 'casesensitive' /*case 'CaseSensitive'*/: break;\n\t\t\t\t\tcase 'value' /*case 'Value'*/: break;\n\t\t\t\t\tcase 'errorstyle' /*case 'ErrorStyle'*/: break;\n\t\t\t\t\tcase 'errormessage' /*case 'ErrorMessage'*/: break;\n\t\t\t\t\tcase 'errortitle' /*case 'ErrorTitle'*/: break;\n\t\t\t\t\tcase 'cellrangelist' /*case 'CellRangeList'*/: break;\n\t\t\t\t\tcase 'inputmessage' /*case 'InputMessage'*/: break;\n\t\t\t\t\tcase 'inputtitle' /*case 'InputTitle'*/: break;\n\t\t\t\t\tcase 'combohide' /*case 'ComboHide'*/: break;\n\t\t\t\t\tcase 'inputhide' /*case 'InputHide'*/: break;\n\t\t\t\t\tcase 'condition' /*case 'Condition'*/: break;\n\t\t\t\t\tcase 'qualifier' /*case 'Qualifier'*/: break;\n\t\t\t\t\tcase 'useblank' /*case 'UseBlank'*/: break;\n\t\t\t\t\tcase 'value1' /*case 'Value1'*/: break;\n\t\t\t\t\tcase 'value2' /*case 'Value2'*/: break;\n\t\t\t\t\tcase 'format' /*case 'Format'*/: break;\n\t\t\t\t\tdefault: seen = false;\n\t\t\t\t} break;\n\n\t\t\t\t/* MapInfo (schema) */\n\t\t\t\tcase 'mapinfo' /*case 'MapInfo'*/: case 'schema' /*case 'Schema'*/: case 'data' /*case 'data'*/: switch(Rn[3]) {\n\t\t\t\t\tcase 'map' /*case 'Map'*/: break;\n\t\t\t\t\tcase 'entry' /*case 'Entry'*/: break;\n\t\t\t\t\tcase 'range' /*case 'Range'*/: break;\n\t\t\t\t\tcase 'xpath' /*case 'XPath'*/: break;\n\t\t\t\t\tcase 'field' /*case 'Field'*/: break;\n\t\t\t\t\tcase 'xsdtype' /*case 'XSDType'*/: break;\n\t\t\t\t\tcase 'filteron' /*case 'FilterOn'*/: break;\n\t\t\t\t\tcase 'aggregate' /*case 'Aggregate'*/: break;\n\t\t\t\t\tcase 'elementtype' /*case 'ElementType'*/: break;\n\t\t\t\t\tcase 'attributetype' /*case 'AttributeType'*/: break;\n\t\t\t\t/* These are from xsd (XML Schema Definition) */\n\t\t\t\t\tcase 'schema' /*case 'schema'*/:\n\t\t\t\t\tcase 'element' /*case 'element'*/:\n\t\t\t\t\tcase 'complextype' /*case 'complexType'*/:\n\t\t\t\t\tcase 'datatype' /*case 'datatype'*/:\n\t\t\t\t\tcase 'all' /*case 'all'*/:\n\t\t\t\t\tcase 'attribute' /*case 'attribute'*/:\n\t\t\t\t\tcase 'extends' /*case 'extends'*/: break;\n\n\t\t\t\t\tcase 'row' /*case 'row'*/: break;\n\t\t\t\t\tdefault: seen = false;\n\t\t\t\t} break;\n\n\t\t\t\t/* SmartTags (can be anything) */\n\t\t\t\tcase 'smarttags' /*case 'SmartTags'*/: break;\n\n\t\t\t\tdefault: seen = false; break;\n\t\t\t}\n\t\t\tif(seen) break;\n\t\t\t/* CustomDocumentProperties */\n\t\t\tif(Rn[3].match(/!\\[CDATA/)) break;\n\t\t\tif(!state[state.length-1][1]) throw 'Unrecognized tag: ' + Rn[3] + \"|\" + state.join(\"|\");\n\t\t\tif(state[state.length-1][0]===/*'CustomDocumentProperties'*/'customdocumentproperties') {\n\t\t\t\tif(Rn[0].slice(-2) === \"/>\") break;\n\t\t\t\telse if(Rn[1]===\"/\") xlml_set_custprop(Custprops, raw_Rn3, cp, str.slice(pidx, Rn.index));\n\t\t\t\telse { cp = Rn; pidx = Rn.index + Rn[0].length; }\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tif(opts.WTF) throw 'Unrecognized tag: ' + Rn[3] + \"|\" + state.join(\"|\");\n\t}\n\tvar out = ({}/*:any*/);\n\tif(!opts.bookSheets && !opts.bookProps) out.Sheets = sheets;\n\tout.SheetNames = sheetnames;\n\tout.Workbook = Workbook;\n\tout.SSF = dup(table_fmt);\n\tout.Props = Props;\n\tout.Custprops = Custprops;\n\treturn out;\n}\n\nfunction parse_xlml(data/*:RawBytes|string*/, opts)/*:Workbook*/ {\n\tfix_read_opts(opts=opts||{});\n\tswitch(opts.type||\"base64\") {\n\t\tcase \"base64\": return parse_xlml_xml(Base64_decode(data), opts);\n\t\tcase \"binary\": case \"buffer\": case \"file\": return parse_xlml_xml(data, opts);\n\t\tcase \"array\": return parse_xlml_xml(a2s(data), opts);\n\t}\n\t/*:: throw new Error(\"unsupported type \" + opts.type); */\n}\n\n/* TODO */\nfunction write_props_xlml(wb/*:Workbook*/, opts)/*:string*/ {\n\tvar o/*:Array<string>*/ = [];\n\t/* DocumentProperties */\n\tif(wb.Props) o.push(xlml_write_docprops(wb.Props, opts));\n\t/* CustomDocumentProperties */\n\tif(wb.Custprops) o.push(xlml_write_custprops(wb.Props, wb.Custprops, opts));\n\treturn o.join(\"\");\n}\n/* TODO */\nfunction write_wb_xlml(/*::wb, opts*/)/*:string*/ {\n\t/* OfficeDocumentSettings */\n\t/* ExcelWorkbook */\n\treturn \"\";\n}\n/* TODO */\nfunction write_sty_xlml(wb, opts)/*:string*/ {\n\t/* Styles */\n\tvar styles/*:Array<string>*/ = ['<Style ss:ID=\"Default\" ss:Name=\"Normal\"><NumberFormat/></Style>'];\n\topts.cellXfs.forEach(function(xf, id) {\n\t\tvar payload/*:Array<string>*/ = [];\n\t\tpayload.push(writextag('NumberFormat', null, {\"ss:Format\": escapexml(table_fmt[xf.numFmtId])}));\n\n\t\tvar o = /*::(*/{\"ss:ID\": \"s\" + (21+id)}/*:: :any)*/;\n\t\tstyles.push(writextag('Style', payload.join(\"\"), o));\n\t});\n\treturn writextag(\"Styles\", styles.join(\"\"));\n}\nfunction write_name_xlml(n) { return writextag(\"NamedRange\", null, {\"ss:Name\": n.Name, \"ss:RefersTo\":\"=\" + a1_to_rc(n.Ref, {r:0,c:0})}); }\nfunction write_names_xlml(wb/*::, opts*/)/*:string*/ {\n\tif(!((wb||{}).Workbook||{}).Names) return \"\";\n\t/*:: if(!wb || !wb.Workbook || !wb.Workbook.Names) throw new Error(\"unreachable\"); */\n\tvar names/*:Array<any>*/ = wb.Workbook.Names;\n\tvar out/*:Array<string>*/ = [];\n\tfor(var i = 0; i < names.length; ++i) {\n\t\tvar n = names[i];\n\t\tif(n.Sheet != null) continue;\n\t\tif(n.Name.match(/^_xlfn\\./)) continue;\n\t\tout.push(write_name_xlml(n));\n\t}\n\treturn writextag(\"Names\", out.join(\"\"));\n}\nfunction write_ws_xlml_names(ws/*:Worksheet*/, opts, idx/*:number*/, wb/*:Workbook*/)/*:string*/ {\n\tif(!ws) return \"\";\n\tif(!((wb||{}).Workbook||{}).Names) return \"\";\n\t/*:: if(!wb || !wb.Workbook || !wb.Workbook.Names) throw new Error(\"unreachable\"); */\n\tvar names/*:Array<any>*/ = wb.Workbook.Names;\n\tvar out/*:Array<string>*/ = [];\n\tfor(var i = 0; i < names.length; ++i) {\n\t\tvar n = names[i];\n\t\tif(n.Sheet != idx) continue;\n\t\t/*switch(n.Name) {\n\t\t\tcase \"_\": continue;\n\t\t}*/\n\t\tif(n.Name.match(/^_xlfn\\./)) continue;\n\t\tout.push(write_name_xlml(n));\n\t}\n\treturn out.join(\"\");\n}\n/* WorksheetOptions */\nfunction write_ws_xlml_wsopts(ws/*:Worksheet*/, opts, idx/*:number*/, wb/*:Workbook*/)/*:string*/ {\n\tif(!ws) return \"\";\n\tvar o/*:Array<string>*/ = [];\n\t/* NOTE: spec technically allows any order, but stick with implied order */\n\n\t/* FitToPage */\n\t/* DoNotDisplayColHeaders */\n\t/* DoNotDisplayRowHeaders */\n\t/* ViewableRange */\n\t/* Selection */\n\t/* GridlineColor */\n\t/* Name */\n\t/* ExcelWorksheetType */\n\t/* IntlMacro */\n\t/* Unsynced */\n\t/* Selected */\n\t/* CodeName */\n\n\tif(ws['!margins']) {\n\t\to.push(\"<PageSetup>\");\n\t\tif(ws['!margins'].header) o.push(writextag(\"Header\", null, {'x:Margin':ws['!margins'].header}));\n\t\tif(ws['!margins'].footer) o.push(writextag(\"Footer\", null, {'x:Margin':ws['!margins'].footer}));\n\t\to.push(writextag(\"PageMargins\", null, {\n\t\t\t'x:Bottom': ws['!margins'].bottom || \"0.75\",\n\t\t\t'x:Left': ws['!margins'].left || \"0.7\",\n\t\t\t'x:Right': ws['!margins'].right || \"0.7\",\n\t\t\t'x:Top': ws['!margins'].top || \"0.75\"\n\t\t}));\n\t\to.push(\"</PageSetup>\");\n\t}\n\n\t/* PageSetup */\n\t/* DisplayPageBreak */\n\t/* TransitionExpressionEvaluation */\n\t/* TransitionFormulaEntry */\n\t/* Print */\n\t/* Zoom */\n\t/* PageLayoutZoom */\n\t/* PageBreakZoom */\n\t/* ShowPageBreakZoom */\n\t/* DefaultRowHeight */\n\t/* DefaultColumnWidth */\n\t/* StandardWidth */\n\n\tif(wb && wb.Workbook && wb.Workbook.Sheets && wb.Workbook.Sheets[idx]) {\n\t\t/* Visible */\n\t\tif(wb.Workbook.Sheets[idx].Hidden) o.push(writextag(\"Visible\", (wb.Workbook.Sheets[idx].Hidden == 1 ? \"SheetHidden\" : \"SheetVeryHidden\"), {}));\n\t\telse {\n\t\t\t/* Selected */\n\t\t\tfor(var i = 0; i < idx; ++i) if(wb.Workbook.Sheets[i] && !wb.Workbook.Sheets[i].Hidden) break;\n\t\t\tif(i == idx) o.push(\"<Selected/>\");\n\t\t}\n\t}\n\n\t/* LeftColumnVisible */\n\n\tif(((((wb||{}).Workbook||{}).Views||[])[0]||{}).RTL) o.push(\"<DisplayRightToLeft/>\");\n\n\t/* GridlineColorIndex */\n\t/* DisplayFormulas */\n\t/* DoNotDisplayGridlines */\n\t/* DoNotDisplayHeadings */\n\t/* DoNotDisplayOutline */\n\t/* ApplyAutomaticOutlineStyles */\n\t/* NoSummaryRowsBelowDetail */\n\t/* NoSummaryColumnsRightDetail */\n\t/* DoNotDisplayZeros */\n\t/* ActiveRow */\n\t/* ActiveColumn */\n\t/* FilterOn */\n\t/* RangeSelection */\n\t/* TopRowVisible */\n\t/* TopRowBottomPane */\n\t/* LeftColumnRightPane */\n\t/* ActivePane */\n\t/* SplitHorizontal */\n\t/* SplitVertical */\n\t/* FreezePanes */\n\t/* FrozenNoSplit */\n\t/* TabColorIndex */\n\t/* Panes */\n\n\t/* NOTE: Password not supported in XLML Format */\n\tif(ws['!protect']) {\n\t\to.push(writetag(\"ProtectContents\", \"True\"));\n\t\tif(ws['!protect'].objects) o.push(writetag(\"ProtectObjects\", \"True\"));\n\t\tif(ws['!protect'].scenarios) o.push(writetag(\"ProtectScenarios\", \"True\"));\n\t\tif(ws['!protect'].selectLockedCells != null && !ws['!protect'].selectLockedCells) o.push(writetag(\"EnableSelection\", \"NoSelection\"));\n\t\telse if(ws['!protect'].selectUnlockedCells != null && !ws['!protect'].selectUnlockedCells) o.push(writetag(\"EnableSelection\", \"UnlockedCells\"));\n\t[\n\t\t[ \"formatCells\", \"AllowFormatCells\" ],\n\t\t[ \"formatColumns\", \"AllowSizeCols\" ],\n\t\t[ \"formatRows\", \"AllowSizeRows\" ],\n\t\t[ \"insertColumns\", \"AllowInsertCols\" ],\n\t\t[ \"insertRows\", \"AllowInsertRows\" ],\n\t\t[ \"insertHyperlinks\", \"AllowInsertHyperlinks\" ],\n\t\t[ \"deleteColumns\", \"AllowDeleteCols\" ],\n\t\t[ \"deleteRows\", \"AllowDeleteRows\" ],\n\t\t[ \"sort\", \"AllowSort\" ],\n\t\t[ \"autoFilter\", \"AllowFilter\" ],\n\t\t[ \"pivotTables\", \"AllowUsePivotTables\" ]\n\t].forEach(function(x) { if(ws['!protect'][x[0]]) o.push(\"<\"+x[1]+\"/>\"); });\n\t}\n\n\tif(o.length == 0) return \"\";\n\treturn writextag(\"WorksheetOptions\", o.join(\"\"), {xmlns:XLMLNS.x});\n}\nfunction write_ws_xlml_comment(comments/*:Array<any>*/)/*:string*/ {\n\treturn comments.map(function(c) {\n\t\t// TODO: formatted text\n\t\tvar t = xlml_unfixstr(c.t||\"\");\n\t\tvar d =writextag(\"ss:Data\", t, {\"xmlns\":\"http://www.w3.org/TR/REC-html40\"});\n\t\treturn writextag(\"Comment\", d, {\"ss:Author\":c.a});\n\t}).join(\"\");\n}\nfunction write_ws_xlml_cell(cell, ref/*:string*/, ws, opts, idx/*:number*/, wb, addr)/*:string*/{\n\tif(!cell || (cell.v == undefined && cell.f == undefined)) return \"\";\n\n\tvar attr = {};\n\tif(cell.f) attr[\"ss:Formula\"] = \"=\" + escapexml(a1_to_rc(cell.f, addr));\n\tif(cell.F && cell.F.slice(0, ref.length) == ref) {\n\t\tvar end = decode_cell(cell.F.slice(ref.length + 1));\n\t\tattr[\"ss:ArrayRange\"] = \"RC:R\" + (end.r == addr.r ? \"\" : \"[\" + (end.r - addr.r) + \"]\") + \"C\" + (end.c == addr.c ? \"\" : \"[\" + (end.c - addr.c) + \"]\");\n\t}\n\n\tif(cell.l && cell.l.Target) {\n\t\tattr[\"ss:HRef\"] = escapexml(cell.l.Target);\n\t\tif(cell.l.Tooltip) attr[\"x:HRefScreenTip\"] = escapexml(cell.l.Tooltip);\n\t}\n\n\tif(ws['!merges']) {\n\t\tvar marr = ws['!merges'];\n\t\tfor(var mi = 0; mi != marr.length; ++mi) {\n\t\t\tif(marr[mi].s.c != addr.c || marr[mi].s.r != addr.r) continue;\n\t\t\tif(marr[mi].e.c > marr[mi].s.c) attr['ss:MergeAcross'] = marr[mi].e.c - marr[mi].s.c;\n\t\t\tif(marr[mi].e.r > marr[mi].s.r) attr['ss:MergeDown'] = marr[mi].e.r - marr[mi].s.r;\n\t\t}\n\t}\n\n\tvar t = \"\", p = \"\";\n\tswitch(cell.t) {\n\t\tcase 'z': if(!opts.sheetStubs) return \"\"; break;\n\t\tcase 'n': t = 'Number'; p = String(cell.v); break;\n\t\tcase 'b': t = 'Boolean'; p = (cell.v ? \"1\" : \"0\"); break;\n\t\tcase 'e': t = 'Error'; p = BErr[cell.v]; break;\n\t\tcase 'd': t = 'DateTime'; p = new Date(cell.v).toISOString(); if(cell.z == null) cell.z = cell.z || table_fmt[14]; break;\n\t\tcase 's': t = 'String'; p = escapexlml(cell.v||\"\"); break;\n\t}\n\t/* TODO: cell style */\n\tvar os = get_cell_style(opts.cellXfs, cell, opts);\n\tattr[\"ss:StyleID\"] = \"s\" + (21+os);\n\tattr[\"ss:Index\"] = addr.c + 1;\n\tvar _v = (cell.v != null ? p : \"\");\n\tvar m = cell.t == 'z' ? \"\" : ('<Data ss:Type=\"' + t + '\">' + _v + '</Data>');\n\n\tif((cell.c||[]).length > 0) m += write_ws_xlml_comment(cell.c);\n\n\treturn writextag(\"Cell\", m, attr);\n}\nfunction write_ws_xlml_row(R/*:number*/, row)/*:string*/ {\n\tvar o = '<Row ss:Index=\"' + (R+1) + '\"';\n\tif(row) {\n\t\tif(row.hpt && !row.hpx) row.hpx = pt2px(row.hpt);\n\t\tif(row.hpx) o += ' ss:AutoFitHeight=\"0\" ss:Height=\"' + row.hpx + '\"';\n\t\tif(row.hidden) o += ' ss:Hidden=\"1\"';\n\t}\n\treturn o + '>';\n}\n/* TODO */\nfunction write_ws_xlml_table(ws/*:Worksheet*/, opts, idx/*:number*/, wb/*:Workbook*/)/*:string*/ {\n\tif(!ws['!ref']) return \"\";\n\tvar range/*:Range*/ = safe_decode_range(ws['!ref']);\n\tvar marr/*:Array<Range>*/ = ws['!merges'] || [], mi = 0;\n\tvar o/*:Array<string>*/ = [];\n\tif(ws['!cols']) ws['!cols'].forEach(function(n, i) {\n\t\tprocess_col(n);\n\t\tvar w = !!n.width;\n\t\tvar p = col_obj_w(i, n);\n\t\tvar k/*:any*/ = {\"ss:Index\":i+1};\n\t\tif(w) k['ss:Width'] = width2px(p.width);\n\t\tif(n.hidden) k['ss:Hidden']=\"1\";\n\t\to.push(writextag(\"Column\",null,k));\n\t});\n\tvar dense = Array.isArray(ws);\n\tfor(var R = range.s.r; R <= range.e.r; ++R) {\n\t\tvar row = [write_ws_xlml_row(R, (ws['!rows']||[])[R])];\n\t\tfor(var C = range.s.c; C <= range.e.c; ++C) {\n\t\t\tvar skip = false;\n\t\t\tfor(mi = 0; mi != marr.length; ++mi) {\n\t\t\t\tif(marr[mi].s.c > C) continue;\n\t\t\t\tif(marr[mi].s.r > R) continue;\n\t\t\t\tif(marr[mi].e.c < C) continue;\n\t\t\t\tif(marr[mi].e.r < R) continue;\n\t\t\t\tif(marr[mi].s.c != C || marr[mi].s.r != R) skip = true;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tif(skip) continue;\n\t\t\tvar addr = {r:R,c:C};\n\t\t\tvar ref = encode_cell(addr), cell = dense ? (ws[R]||[])[C] : ws[ref];\n\t\t\trow.push(write_ws_xlml_cell(cell, ref, ws, opts, idx, wb, addr));\n\t\t}\n\t\trow.push(\"</Row>\");\n\t\tif(row.length > 2) o.push(row.join(\"\"));\n\t}\n\treturn o.join(\"\");\n}\nfunction write_ws_xlml(idx/*:number*/, opts, wb/*:Workbook*/)/*:string*/ {\n\tvar o/*:Array<string>*/ = [];\n\tvar s = wb.SheetNames[idx];\n\tvar ws = wb.Sheets[s];\n\n\tvar t/*:string*/ = ws ? write_ws_xlml_names(ws, opts, idx, wb) : \"\";\n\tif(t.length > 0) o.push(\"<Names>\" + t + \"</Names>\");\n\n\t/* Table */\n\tt = ws ? write_ws_xlml_table(ws, opts, idx, wb) : \"\";\n\tif(t.length > 0) o.push(\"<Table>\" + t + \"</Table>\");\n\n\t/* WorksheetOptions */\n\to.push(write_ws_xlml_wsopts(ws, opts, idx, wb));\n\n\treturn o.join(\"\");\n}\nfunction write_xlml(wb, opts)/*:string*/ {\n\tif(!opts) opts = {};\n\tif(!wb.SSF) wb.SSF = dup(table_fmt);\n\tif(wb.SSF) {\n\t\tmake_ssf(); SSF_load_table(wb.SSF);\n\t\t// $FlowIgnore\n\t\topts.revssf = evert_num(wb.SSF); opts.revssf[wb.SSF[65535]] = 0;\n\t\topts.ssf = wb.SSF;\n\t\topts.cellXfs = [];\n\t\tget_cell_style(opts.cellXfs, {}, {revssf:{\"General\":0}});\n\t}\n\tvar d/*:Array<string>*/ = [];\n\td.push(write_props_xlml(wb, opts));\n\td.push(write_wb_xlml(wb, opts));\n\td.push(\"\");\n\td.push(\"\");\n\tfor(var i = 0; i < wb.SheetNames.length; ++i)\n\t\td.push(writextag(\"Worksheet\", write_ws_xlml(i, opts, wb), {\"ss:Name\":escapexml(wb.SheetNames[i])}));\n\td[2] = write_sty_xlml(wb, opts);\n\td[3] = write_names_xlml(wb, opts);\n\treturn XML_HEADER + writextag(\"Workbook\", d.join(\"\"), {\n\t\t'xmlns':      XLMLNS.ss,\n\t\t'xmlns:o':    XLMLNS.o,\n\t\t'xmlns:x':    XLMLNS.x,\n\t\t'xmlns:ss':   XLMLNS.ss,\n\t\t'xmlns:dt':   XLMLNS.dt,\n\t\t'xmlns:html': XLMLNS.html\n\t});\n}\n/* [MS-OLEDS] 2.3.8 CompObjStream */\nfunction parse_compobj(obj/*:CFBEntry*/) {\n\tvar v = {};\n\tvar o = obj.content;\n\t/*:: if(o == null) return; */\n\n\t/* [MS-OLEDS] 2.3.7 CompObjHeader -- All fields MUST be ignored */\n\to.l = 28;\n\n\tv.AnsiUserType = o.read_shift(0, \"lpstr-ansi\");\n\tv.AnsiClipboardFormat = parse_ClipboardFormatOrAnsiString(o);\n\n\tif(o.length - o.l <= 4) return v;\n\n\tvar m/*:number*/ = o.read_shift(4);\n\tif(m == 0 || m > 40) return v;\n\to.l-=4; v.Reserved1 = o.read_shift(0, \"lpstr-ansi\");\n\n\tif(o.length - o.l <= 4) return v;\n\tm = o.read_shift(4);\n\tif(m !== 0x71b239f4) return v;\n\tv.UnicodeClipboardFormat = parse_ClipboardFormatOrUnicodeString(o);\n\n\tm = o.read_shift(4);\n\tif(m == 0 || m > 40) return v;\n\to.l-=4; v.Reserved2 = o.read_shift(0, \"lpwstr\");\n}\n\n/*\n\tContinue logic for:\n\t- 2.4.58 Continue          0x003c\n\t- 2.4.59 ContinueBigName   0x043c\n\t- 2.4.60 ContinueFrt       0x0812\n\t- 2.4.61 ContinueFrt11     0x0875\n\t- 2.4.62 ContinueFrt12     0x087f\n*/\nvar CONTINUE_RT = [ 0x003c, 0x043c, 0x0812, 0x0875, 0x087f ];\nfunction slurp(RecordType, R, blob, length/*:number*/, opts)/*:any*/ {\n\tvar l = length;\n\tvar bufs = [];\n\tvar d = blob.slice(blob.l,blob.l+l);\n\tif(opts && opts.enc && opts.enc.insitu && d.length > 0) switch(RecordType) {\n\tcase 0x0009: case 0x0209: case 0x0409: case 0x0809/* BOF */: case 0x002f /* FilePass */: case 0x0195 /* FileLock */: case 0x00e1 /* InterfaceHdr */: case 0x0196 /* RRDInfo */: case 0x0138 /* RRDHead */: case 0x0194 /* UsrExcl */: case 0x000a /* EOF */:\n\t\tbreak;\n\tcase 0x0085 /* BoundSheet8 */:\n\t\tbreak;\n\tdefault:\n\t\topts.enc.insitu(d);\n\t}\n\tbufs.push(d);\n\tblob.l += l;\n\tvar nextrt = __readUInt16LE(blob,blob.l), next = XLSRecordEnum[nextrt];\n\tvar start = 0;\n\twhile(next != null && CONTINUE_RT.indexOf(nextrt) > -1) {\n\t\tl = __readUInt16LE(blob,blob.l+2);\n\t\tstart = blob.l + 4;\n\t\tif(nextrt == 0x0812 /* ContinueFrt */) start += 4;\n\t\telse if(nextrt == 0x0875 || nextrt == 0x087f) {\n\t\t\tstart += 12;\n\t\t}\n\t\td = blob.slice(start,blob.l+4+l);\n\t\tbufs.push(d);\n\t\tblob.l += 4+l;\n\t\tnext = (XLSRecordEnum[nextrt = __readUInt16LE(blob, blob.l)]);\n\t}\n\tvar b = (bconcat(bufs)/*:any*/);\n\tprep_blob(b, 0);\n\tvar ll = 0; b.lens = [];\n\tfor(var j = 0; j < bufs.length; ++j) { b.lens.push(ll); ll += bufs[j].length; }\n\tif(b.length < length) throw \"XLS Record 0x\" + RecordType.toString(16) + \" Truncated: \" + b.length + \" < \" + length;\n\treturn R.f(b, b.length, opts);\n}\n\nfunction safe_format_xf(p/*:any*/, opts/*:ParseOpts*/, date1904/*:?boolean*/) {\n\tif(p.t === 'z') return;\n\tif(!p.XF) return;\n\tvar fmtid = 0;\n\ttry {\n\t\tfmtid = p.z || p.XF.numFmtId || 0;\n\t\tif(opts.cellNF) p.z = table_fmt[fmtid];\n\t} catch(e) { if(opts.WTF) throw e; }\n\tif(!opts || opts.cellText !== false) try {\n\t\tif(p.t === 'e') { p.w = p.w || BErr[p.v]; }\n\t\telse if(fmtid === 0 || fmtid == \"General\") {\n\t\t\tif(p.t === 'n') {\n\t\t\t\tif((p.v|0) === p.v) p.w = p.v.toString(10);\n\t\t\t\telse p.w = SSF_general_num(p.v);\n\t\t\t}\n\t\t\telse p.w = SSF_general(p.v);\n\t\t}\n\t\telse p.w = SSF_format(fmtid,p.v, {date1904:!!date1904, dateNF: opts && opts.dateNF});\n\t} catch(e) { if(opts.WTF) throw e; }\n\tif(opts.cellDates && fmtid && p.t == 'n' && fmt_is_date(table_fmt[fmtid] || String(fmtid))) {\n\t\tvar _d = SSF_parse_date_code(p.v); if(_d) { p.t = 'd'; p.v = new Date(_d.y, _d.m-1,_d.d,_d.H,_d.M,_d.S,_d.u); }\n\t}\n}\n\nfunction make_cell(val, ixfe, t)/*:Cell*/ {\n\treturn ({v:val, ixfe:ixfe, t:t}/*:any*/);\n}\n\n// 2.3.2\nfunction parse_workbook(blob, options/*:ParseOpts*/)/*:Workbook*/ {\n\tvar wb = ({opts:{}}/*:any*/);\n\tvar Sheets = {};\n\tif(DENSE != null && options.dense == null) options.dense = DENSE;\n\tvar out/*:Worksheet*/ = ((options.dense ? [] : {})/*:any*/);\n\tvar Directory = {};\n\tvar range/*:Range*/ = ({}/*:any*/);\n\tvar last_formula = null;\n\tvar sst/*:SST*/ = ([]/*:any*/);\n\tvar cur_sheet = \"\";\n\tvar Preamble = {};\n\tvar lastcell, last_cell = \"\", cc/*:Cell*/, cmnt, rngC, rngR;\n\tvar sharedf = {};\n\tvar arrayf/*:Array<[Range, string]>*/ = [];\n\tvar temp_val/*:Cell*/;\n\tvar country;\n\tvar XFs = []; /* XF records */\n\tvar palette/*:Array<[number, number, number]>*/ = [];\n\tvar Workbook/*:WBWBProps*/ = ({ Sheets:[], WBProps:{date1904:false}, Views:[{}] }/*:any*/), wsprops = {};\n\tvar get_rgb = function getrgb(icv/*:number*/)/*:[number, number, number]*/ {\n\t\tif(icv < 8) return XLSIcv[icv];\n\t\tif(icv < 64) return palette[icv-8] || XLSIcv[icv];\n\t\treturn XLSIcv[icv];\n\t};\n\tvar process_cell_style = function pcs(cell, line/*:any*/, options) {\n\t\tvar xfd = line.XF.data;\n\t\tif(!xfd || !xfd.patternType || !options || !options.cellStyles) return;\n\t\tline.s = ({}/*:any*/);\n\t\tline.s.patternType = xfd.patternType;\n\t\tvar t;\n\t\tif((t = rgb2Hex(get_rgb(xfd.icvFore)))) { line.s.fgColor = {rgb:t}; }\n\t\tif((t = rgb2Hex(get_rgb(xfd.icvBack)))) { line.s.bgColor = {rgb:t}; }\n\t};\n\tvar addcell = function addcell(cell/*:any*/, line/*:any*/, options/*:any*/) {\n\t\tif(file_depth > 1) return;\n\t\tif(options.sheetRows && cell.r >= options.sheetRows) return;\n\t\tif(options.cellStyles && line.XF && line.XF.data) process_cell_style(cell, line, options);\n\t\tdelete line.ixfe; delete line.XF;\n\t\tlastcell = cell;\n\t\tlast_cell = encode_cell(cell);\n\t\tif(!range || !range.s || !range.e) range = {s:{r:0,c:0},e:{r:0,c:0}};\n\t\tif(cell.r < range.s.r) range.s.r = cell.r;\n\t\tif(cell.c < range.s.c) range.s.c = cell.c;\n\t\tif(cell.r + 1 > range.e.r) range.e.r = cell.r + 1;\n\t\tif(cell.c + 1 > range.e.c) range.e.c = cell.c + 1;\n\t\tif(options.cellFormula && line.f) {\n\t\t\tfor(var afi = 0; afi < arrayf.length; ++afi) {\n\t\t\t\tif(arrayf[afi][0].s.c > cell.c || arrayf[afi][0].s.r > cell.r) continue;\n\t\t\t\tif(arrayf[afi][0].e.c < cell.c || arrayf[afi][0].e.r < cell.r) continue;\n\t\t\t\tline.F = encode_range(arrayf[afi][0]);\n\t\t\t\tif(arrayf[afi][0].s.c != cell.c || arrayf[afi][0].s.r != cell.r) delete line.f;\n\t\t\t\tif(line.f) line.f = \"\" + stringify_formula(arrayf[afi][1], range, cell, supbooks, opts);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\t{\n\t\t\tif(options.dense) {\n\t\t\t\tif(!out[cell.r]) out[cell.r] = [];\n\t\t\t\tout[cell.r][cell.c] = line;\n\t\t\t} else out[last_cell] = line;\n\t\t}\n\t};\n\tvar opts = ({\n\t\tenc: false, // encrypted\n\t\tsbcch: 0, // cch in the preceding SupBook\n\t\tsnames: [], // sheetnames\n\t\tsharedf: sharedf, // shared formulae by address\n\t\tarrayf: arrayf, // array formulae array\n\t\trrtabid: [], // RRTabId\n\t\tlastuser: \"\", // Last User from WriteAccess\n\t\tbiff: 8, // BIFF version\n\t\tcodepage: 0, // CP from CodePage record\n\t\twinlocked: 0, // fLockWn from WinProtect\n\t\tcellStyles: !!options && !!options.cellStyles,\n\t\tWTF: !!options && !!options.wtf\n\t}/*:any*/);\n\tif(options.password) opts.password = options.password;\n\tvar themes;\n\tvar merges/*:Array<Range>*/ = [];\n\tvar objects = [];\n\tvar colinfo/*:Array<ColInfo>*/ = [], rowinfo/*:Array<RowInfo>*/ = [];\n\tvar seencol = false;\n\tvar supbooks = ([]/*:any*/); // 1-indexed, will hold extern names\n\tsupbooks.SheetNames = opts.snames;\n\tsupbooks.sharedf = opts.sharedf;\n\tsupbooks.arrayf = opts.arrayf;\n\tsupbooks.names = [];\n\tsupbooks.XTI = [];\n\tvar last_RT = 0;\n\tvar file_depth = 0; /* TODO: make a real stack */\n\tvar BIFF2Fmt = 0, BIFF2FmtTable/*:Array<string>*/ = [];\n\tvar FilterDatabases = []; /* TODO: sort out supbooks and process elsewhere */\n\tvar last_lbl/*:?DefinedName*/;\n\n\t/* explicit override for some broken writers */\n\topts.codepage = 1200;\n\tset_cp(1200);\n\tvar seen_codepage = false;\n\twhile(blob.l < blob.length - 1) {\n\t\tvar s = blob.l;\n\t\tvar RecordType = blob.read_shift(2);\n\t\tif(RecordType === 0 && last_RT === 0x000a /* EOF */) break;\n\t\tvar length = (blob.l === blob.length ? 0 : blob.read_shift(2));\n\t\tvar R = XLSRecordEnum[RecordType];\n\t\t//console.log(RecordType.toString(16), RecordType, R, blob.l, length, blob.length);\n\t\t//if(!R) console.log(blob.slice(blob.l, blob.l + length));\n\t\tif(R && R.f) {\n\t\t\tif(options.bookSheets) {\n\t\t\t\tif(last_RT === 0x0085 /* BoundSheet8 */ && RecordType !== 0x0085 /* R.n !== 'BoundSheet8' */) break;\n\t\t\t}\n\t\t\tlast_RT = RecordType;\n\t\t\tif(R.r === 2 || R.r == 12) {\n\t\t\t\tvar rt = blob.read_shift(2); length -= 2;\n\t\t\t\tif(!opts.enc && rt !== RecordType && (((rt&0xFF)<<8)|(rt>>8)) !== RecordType) throw new Error(\"rt mismatch: \" + rt + \"!=\" + RecordType);\n\t\t\t\tif(R.r == 12){\n\t\t\t\t\tblob.l += 10; length -= 10;\n\t\t\t\t} // skip FRT\n\t\t\t}\n\t\t\t//console.error(R,blob.l,length,blob.length);\n\t\t\tvar val/*:any*/ = ({}/*:any*/);\n\t\t\tif(RecordType === 0x000a /* EOF */) val = /*::(*/R.f(blob, length, opts)/*:: :any)*/;\n\t\t\telse val = /*::(*/slurp(RecordType, R, blob, length, opts)/*:: :any)*/;\n\t\t\t/*:: val = (val:any); */\n\t\t\tif(file_depth == 0 && [0x0009, 0x0209, 0x0409, 0x0809].indexOf(last_RT) === -1 /* 'BOF' */) continue;\n\t\t\tswitch(RecordType) {\n\t\t\t\tcase 0x0022 /* Date1904 */:\n\t\t\t\t\t/*:: if(!Workbook.WBProps) Workbook.WBProps = {}; */\n\t\t\t\t\twb.opts.Date1904 = Workbook.WBProps.date1904 = val; break;\n\t\t\t\tcase 0x0086 /* WriteProtect */: wb.opts.WriteProtect = true; break;\n\t\t\t\tcase 0x002f /* FilePass */:\n\t\t\t\t\tif(!opts.enc) blob.l = 0;\n\t\t\t\t\topts.enc = val;\n\t\t\t\t\tif(!options.password) throw new Error(\"File is password-protected\");\n\t\t\t\t\tif(val.valid == null) throw new Error(\"Encryption scheme unsupported\");\n\t\t\t\t\tif(!val.valid) throw new Error(\"Password is incorrect\");\n\t\t\t\t\tbreak;\n\t\t\t\tcase 0x005c /* WriteAccess */: opts.lastuser = val; break;\n\t\t\t\tcase 0x0042 /* CodePage */:\n\t\t\t\t\tvar cpval = Number(val);\n\t\t\t\t\t/* overrides based on test cases */\n\t\t\t\t\tswitch(cpval) {\n\t\t\t\t\t\tcase 0x5212: cpval =  1200; break;\n\t\t\t\t\t\tcase 0x8000: cpval = 10000; break;\n\t\t\t\t\t\tcase 0x8001: cpval =  1252; break;\n\t\t\t\t\t}\n\t\t\t\t\tset_cp(opts.codepage = cpval);\n\t\t\t\t\tseen_codepage = true;\n\t\t\t\t\tbreak;\n\t\t\t\tcase 0x013d /* RRTabId */: opts.rrtabid = val; break;\n\t\t\t\tcase 0x0019 /* WinProtect */: opts.winlocked = val; break;\n\t\t\t\tcase 0x01b7 /* RefreshAll */: wb.opts[\"RefreshAll\"] = val; break;\n\t\t\t\tcase 0x000c /* CalcCount */: wb.opts[\"CalcCount\"] = val; break;\n\t\t\t\tcase 0x0010 /* CalcDelta */: wb.opts[\"CalcDelta\"] = val; break;\n\t\t\t\tcase 0x0011 /* CalcIter */: wb.opts[\"CalcIter\"] = val; break;\n\t\t\t\tcase 0x000d /* CalcMode */: wb.opts[\"CalcMode\"] = val; break;\n\t\t\t\tcase 0x000e /* CalcPrecision */: wb.opts[\"CalcPrecision\"] = val; break;\n\t\t\t\tcase 0x005f /* CalcSaveRecalc */: wb.opts[\"CalcSaveRecalc\"] = val; break;\n\t\t\t\tcase 0x000f /* CalcRefMode */: opts.CalcRefMode = val; break; // TODO: implement R1C1\n\t\t\t\tcase 0x08a3 /* ForceFullCalculation */: wb.opts.FullCalc = val; break;\n\t\t\t\tcase 0x0081 /* WsBool */:\n\t\t\t\t\tif(val.fDialog) out[\"!type\"] = \"dialog\";\n\t\t\t\t\tif(!val.fBelow) (out[\"!outline\"] || (out[\"!outline\"] = {})).above = true;\n\t\t\t\t\tif(!val.fRight) (out[\"!outline\"] || (out[\"!outline\"] = {})).left = true;\n\t\t\t\t\tbreak; // TODO\n\t\t\t\tcase 0x00e0 /* XF */:\n\t\t\t\t\tXFs.push(val); break;\n\t\t\t\tcase 0x01ae /* SupBook */:\n\t\t\t\t\tsupbooks.push([val]);\n\t\t\t\t\tsupbooks[supbooks.length-1].XTI = [];\n\t\t\t\t\tbreak;\n\t\t\t\tcase 0x0023: case 0x0223 /* ExternName */:\n\t\t\t\t\tsupbooks[supbooks.length-1].push(val);\n\t\t\t\t\tbreak;\n\t\t\t\tcase 0x0018: case 0x0218 /* Lbl */:\n\t\t\t\t\tlast_lbl = ({\n\t\t\t\t\t\tName: val.Name,\n\t\t\t\t\t\tRef: stringify_formula(val.rgce,range,null,supbooks,opts)\n\t\t\t\t\t}/*:DefinedName*/);\n\t\t\t\t\tif(val.itab > 0) last_lbl.Sheet = val.itab - 1;\n\t\t\t\t\tsupbooks.names.push(last_lbl);\n\t\t\t\t\tif(!supbooks[0]) { supbooks[0] = []; supbooks[0].XTI = []; }\n\t\t\t\t\tsupbooks[supbooks.length-1].push(val);\n\t\t\t\t\tif(val.Name == \"_xlnm._FilterDatabase\" && val.itab > 0)\n\t\t\t\t\t\tif(val.rgce && val.rgce[0] && val.rgce[0][0] && val.rgce[0][0][0] == 'PtgArea3d')\n\t\t\t\t\t\t\tFilterDatabases[val.itab - 1] = { ref: encode_range(val.rgce[0][0][1][2]) };\n\t\t\t\t\tbreak;\n\t\t\t\tcase 0x0016 /* ExternCount */: opts.ExternCount = val; break;\n\t\t\t\tcase 0x0017 /* ExternSheet */:\n\t\t\t\t\tif(supbooks.length == 0) { supbooks[0] = []; supbooks[0].XTI = []; }\n\t\t\t\t\tsupbooks[supbooks.length - 1].XTI = supbooks[supbooks.length - 1].XTI.concat(val); supbooks.XTI = supbooks.XTI.concat(val); break;\n\t\t\t\tcase 0x0894 /* NameCmt */:\n\t\t\t\t\t/* TODO: search for correct name */\n\t\t\t\t\tif(opts.biff < 8) break;\n\t\t\t\t\tif(last_lbl != null) last_lbl.Comment = val[1];\n\t\t\t\t\tbreak;\n\t\t\t\tcase 0x0012 /* Protect */: out[\"!protect\"] = val; break; /* for sheet or book */\n\t\t\t\tcase 0x0013 /* Password */: if(val !== 0 && opts.WTF) console.error(\"Password verifier: \" + val); break;\n\t\t\t\tcase 0x0085 /* BoundSheet8 */: {\n\t\t\t\t\tDirectory[val.pos] = val;\n\t\t\t\t\topts.snames.push(val.name);\n\t\t\t\t} break;\n\t\t\t\tcase 0x000a /* EOF */: {\n\t\t\t\t\tif(--file_depth) break;\n\t\t\t\t\tif(range.e) {\n\t\t\t\t\t\tif(range.e.r > 0 && range.e.c > 0) {\n\t\t\t\t\t\t\trange.e.r--; range.e.c--;\n\t\t\t\t\t\t\tout[\"!ref\"] = encode_range(range);\n\t\t\t\t\t\t\tif(options.sheetRows && options.sheetRows <= range.e.r) {\n\t\t\t\t\t\t\t\tvar tmpri = range.e.r;\n\t\t\t\t\t\t\t\trange.e.r = options.sheetRows - 1;\n\t\t\t\t\t\t\t\tout[\"!fullref\"] = out[\"!ref\"];\n\t\t\t\t\t\t\t\tout[\"!ref\"] = encode_range(range);\n\t\t\t\t\t\t\t\trange.e.r = tmpri;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\trange.e.r++; range.e.c++;\n\t\t\t\t\t\t}\n\t\t\t\t\t\tif(merges.length > 0) out[\"!merges\"] = merges;\n\t\t\t\t\t\tif(objects.length > 0) out[\"!objects\"] = objects;\n\t\t\t\t\t\tif(colinfo.length > 0) out[\"!cols\"] = colinfo;\n\t\t\t\t\t\tif(rowinfo.length > 0) out[\"!rows\"] = rowinfo;\n\t\t\t\t\t\tWorkbook.Sheets.push(wsprops);\n\t\t\t\t\t}\n\t\t\t\t\tif(cur_sheet === \"\") Preamble = out; else Sheets[cur_sheet] = out;\n\t\t\t\t\tout = ((options.dense ? [] : {})/*:any*/);\n\t\t\t\t} break;\n\t\t\t\tcase 0x0009: case 0x0209: case 0x0409: case 0x0809 /* BOF */: {\n\t\t\t\t\tif(opts.biff === 8) opts.biff = {\n\t\t\t\t\t\t/*::[*/0x0009/*::]*/:2,\n\t\t\t\t\t\t/*::[*/0x0209/*::]*/:3,\n\t\t\t\t\t\t/*::[*/0x0409/*::]*/:4\n\t\t\t\t\t}[RecordType] || {\n\t\t\t\t\t\t/*::[*/0x0200/*::]*/:2,\n\t\t\t\t\t\t/*::[*/0x0300/*::]*/:3,\n\t\t\t\t\t\t/*::[*/0x0400/*::]*/:4,\n\t\t\t\t\t\t/*::[*/0x0500/*::]*/:5,\n\t\t\t\t\t\t/*::[*/0x0600/*::]*/:8,\n\t\t\t\t\t\t/*::[*/0x0002/*::]*/:2,\n\t\t\t\t\t\t/*::[*/0x0007/*::]*/:2\n\t\t\t\t\t}[val.BIFFVer] || 8;\n\t\t\t\t\topts.biffguess = val.BIFFVer == 0;\n\t\t\t\t\tif(val.BIFFVer == 0 && val.dt == 0x1000) { opts.biff = 5; seen_codepage = true; set_cp(opts.codepage = 28591); }\n\t\t\t\t\tif(opts.biff == 8 && val.BIFFVer == 0 && val.dt == 16) opts.biff = 2;\n\t\t\t\t\tif(file_depth++) break;\n\t\t\t\t\tout = ((options.dense ? [] : {})/*:any*/);\n\n\t\t\t\t\tif(opts.biff < 8 && !seen_codepage) { seen_codepage = true; set_cp(opts.codepage = options.codepage || 1252); }\n\n\t\t\t\t\tif(opts.biff < 5 || val.BIFFVer == 0 && val.dt == 0x1000) {\n\t\t\t\t\t\tif(cur_sheet === \"\") cur_sheet = \"Sheet1\";\n\t\t\t\t\t\trange = {s:{r:0,c:0},e:{r:0,c:0}};\n\t\t\t\t\t\t/* fake BoundSheet8 */\n\t\t\t\t\t\tvar fakebs8 = {pos: blob.l - length, name:cur_sheet};\n\t\t\t\t\t\tDirectory[fakebs8.pos] = fakebs8;\n\t\t\t\t\t\topts.snames.push(cur_sheet);\n\t\t\t\t\t}\n\t\t\t\t\telse cur_sheet = (Directory[s] || {name:\"\"}).name;\n\t\t\t\t\tif(val.dt == 0x20) out[\"!type\"] = \"chart\";\n\t\t\t\t\tif(val.dt == 0x40) out[\"!type\"] = \"macro\";\n\t\t\t\t\tmerges = [];\n\t\t\t\t\tobjects = [];\n\t\t\t\t\topts.arrayf = arrayf = [];\n\t\t\t\t\tcolinfo = []; rowinfo = [];\n\t\t\t\t\tseencol = false;\n\t\t\t\t\twsprops = {Hidden:(Directory[s]||{hs:0}).hs, name:cur_sheet };\n\t\t\t\t} break;\n\t\t\t\tcase 0x0203 /* Number */: case 0x0003 /* BIFF2NUM */: case 0x0002 /* BIFF2INT */: {\n\t\t\t\t\tif(out[\"!type\"] == \"chart\") if(options.dense ? (out[val.r]||[])[val.c]: out[encode_cell({c:val.c, r:val.r})]) ++val.c;\n\t\t\t\t\ttemp_val = ({ixfe: val.ixfe, XF: XFs[val.ixfe]||{}, v:val.val, t:'n'}/*:any*/);\n\t\t\t\t\tif(BIFF2Fmt > 0) temp_val.z = BIFF2FmtTable[(temp_val.ixfe>>8) & 0x3F];\n\t\t\t\t\tsafe_format_xf(temp_val, options, wb.opts.Date1904);\n\t\t\t\t\taddcell({c:val.c, r:val.r}, temp_val, options);\n\t\t\t\t} break;\n\t\t\t\tcase 0x0005: case 0x0205 /* BoolErr */: {\n\t\t\t\t\ttemp_val = ({ixfe: val.ixfe, XF: XFs[val.ixfe], v:val.val, t:val.t}/*:any*/);\n\t\t\t\t\tif(BIFF2Fmt > 0) temp_val.z = BIFF2FmtTable[(temp_val.ixfe>>8) & 0x3F];\n\t\t\t\t\tsafe_format_xf(temp_val, options, wb.opts.Date1904);\n\t\t\t\t\taddcell({c:val.c, r:val.r}, temp_val, options);\n\t\t\t\t} break;\n\t\t\t\tcase 0x027e /* RK */: {\n\t\t\t\t\ttemp_val = ({ixfe: val.ixfe, XF: XFs[val.ixfe], v:val.rknum, t:'n'}/*:any*/);\n\t\t\t\t\tif(BIFF2Fmt > 0) temp_val.z = BIFF2FmtTable[(temp_val.ixfe>>8) & 0x3F];\n\t\t\t\t\tsafe_format_xf(temp_val, options, wb.opts.Date1904);\n\t\t\t\t\taddcell({c:val.c, r:val.r}, temp_val, options);\n\t\t\t\t} break;\n\t\t\t\tcase 0x00bd /* MulRk */: {\n\t\t\t\t\tfor(var j = val.c; j <= val.C; ++j) {\n\t\t\t\t\t\tvar ixfe = val.rkrec[j-val.c][0];\n\t\t\t\t\t\ttemp_val= ({ixfe:ixfe, XF:XFs[ixfe], v:val.rkrec[j-val.c][1], t:'n'}/*:any*/);\n\t\t\t\t\t\tif(BIFF2Fmt > 0) temp_val.z = BIFF2FmtTable[(temp_val.ixfe>>8) & 0x3F];\n\t\t\t\t\t\tsafe_format_xf(temp_val, options, wb.opts.Date1904);\n\t\t\t\t\t\taddcell({c:j, r:val.r}, temp_val, options);\n\t\t\t\t\t}\n\t\t\t\t} break;\n\t\t\t\tcase 0x0006: case 0x0206: case 0x0406 /* Formula */: {\n\t\t\t\t\tif(val.val == 'String') { last_formula = val; break; }\n\t\t\t\t\ttemp_val = make_cell(val.val, val.cell.ixfe, val.tt);\n\t\t\t\t\ttemp_val.XF = XFs[temp_val.ixfe];\n\t\t\t\t\tif(options.cellFormula) {\n\t\t\t\t\t\tvar _f = val.formula;\n\t\t\t\t\t\tif(_f && _f[0] && _f[0][0] && _f[0][0][0] == 'PtgExp') {\n\t\t\t\t\t\t\tvar _fr = _f[0][0][1][0], _fc = _f[0][0][1][1];\n\t\t\t\t\t\t\tvar _fe = encode_cell({r:_fr, c:_fc});\n\t\t\t\t\t\t\tif(sharedf[_fe]) temp_val.f = \"\"+stringify_formula(val.formula,range,val.cell,supbooks, opts);\n\t\t\t\t\t\t\telse temp_val.F = ((options.dense ? (out[_fr]||[])[_fc]: out[_fe]) || {}).F;\n\t\t\t\t\t\t} else temp_val.f = \"\"+stringify_formula(val.formula,range,val.cell,supbooks, opts);\n\t\t\t\t\t}\n\t\t\t\t\tif(BIFF2Fmt > 0) temp_val.z = BIFF2FmtTable[(temp_val.ixfe>>8) & 0x3F];\n\t\t\t\t\tsafe_format_xf(temp_val, options, wb.opts.Date1904);\n\t\t\t\t\taddcell(val.cell, temp_val, options);\n\t\t\t\t\tlast_formula = val;\n\t\t\t\t} break;\n\t\t\t\tcase 0x0007: case 0x0207 /* String */: {\n\t\t\t\t\tif(last_formula) { /* technically always true */\n\t\t\t\t\t\tlast_formula.val = val;\n\t\t\t\t\t\ttemp_val = make_cell(val, last_formula.cell.ixfe, 's');\n\t\t\t\t\t\ttemp_val.XF = XFs[temp_val.ixfe];\n\t\t\t\t\t\tif(options.cellFormula) {\n\t\t\t\t\t\t\ttemp_val.f = \"\"+stringify_formula(last_formula.formula, range, last_formula.cell, supbooks, opts);\n\t\t\t\t\t\t}\n\t\t\t\t\t\tif(BIFF2Fmt > 0) temp_val.z = BIFF2FmtTable[(temp_val.ixfe>>8) & 0x3F];\n\t\t\t\t\t\tsafe_format_xf(temp_val, options, wb.opts.Date1904);\n\t\t\t\t\t\taddcell(last_formula.cell, temp_val, options);\n\t\t\t\t\t\tlast_formula = null;\n\t\t\t\t\t} else throw new Error(\"String record expects Formula\");\n\t\t\t\t} break;\n\t\t\t\tcase 0x0021: case 0x0221 /* Array */: {\n\t\t\t\t\tarrayf.push(val);\n\t\t\t\t\tvar _arraystart = encode_cell(val[0].s);\n\t\t\t\t\tcc = options.dense ? (out[val[0].s.r]||[])[val[0].s.c] : out[_arraystart];\n\t\t\t\t\tif(options.cellFormula && cc) {\n\t\t\t\t\t\tif(!last_formula) break; /* technically unreachable */\n\t\t\t\t\t\tif(!_arraystart || !cc) break;\n\t\t\t\t\t\tcc.f = \"\"+stringify_formula(val[1], range, val[0], supbooks, opts);\n\t\t\t\t\t\tcc.F = encode_range(val[0]);\n\t\t\t\t\t}\n\t\t\t\t} break;\n\t\t\t\tcase 0x04bc /* ShrFmla */: {\n\t\t\t\t\tif(!options.cellFormula) break;\n\t\t\t\t\tif(last_cell) {\n\t\t\t\t\t\t/* TODO: capture range */\n\t\t\t\t\t\tif(!last_formula) break; /* technically unreachable */\n\t\t\t\t\t\tsharedf[encode_cell(last_formula.cell)]= val[0];\n\t\t\t\t\t\tcc = options.dense ? (out[last_formula.cell.r]||[])[last_formula.cell.c] : out[encode_cell(last_formula.cell)];\n\t\t\t\t\t\t(cc||{}).f = \"\"+stringify_formula(val[0], range, lastcell, supbooks, opts);\n\t\t\t\t\t}\n\t\t\t\t} break;\n\t\t\t\tcase 0x00fd /* LabelSst */:\n\t\t\t\t\ttemp_val=make_cell(sst[val.isst].t, val.ixfe, 's');\n\t\t\t\t\tif(sst[val.isst].h) temp_val.h = sst[val.isst].h;\n\t\t\t\t\ttemp_val.XF = XFs[temp_val.ixfe];\n\t\t\t\t\tif(BIFF2Fmt > 0) temp_val.z = BIFF2FmtTable[(temp_val.ixfe>>8) & 0x3F];\n\t\t\t\t\tsafe_format_xf(temp_val, options, wb.opts.Date1904);\n\t\t\t\t\taddcell({c:val.c, r:val.r}, temp_val, options);\n\t\t\t\t\tbreak;\n\t\t\t\tcase 0x0201 /* Blank */: if(options.sheetStubs) {\n\t\t\t\t\ttemp_val = ({ixfe: val.ixfe, XF: XFs[val.ixfe], t:'z'}/*:any*/);\n\t\t\t\t\tif(BIFF2Fmt > 0) temp_val.z = BIFF2FmtTable[(temp_val.ixfe>>8) & 0x3F];\n\t\t\t\t\tsafe_format_xf(temp_val, options, wb.opts.Date1904);\n\t\t\t\t\taddcell({c:val.c, r:val.r}, temp_val, options);\n\t\t\t\t} break;\n\t\t\t\tcase 0x00be /* MulBlank */: if(options.sheetStubs) {\n\t\t\t\t\tfor(var _j = val.c; _j <= val.C; ++_j) {\n\t\t\t\t\t\tvar _ixfe = val.ixfe[_j-val.c];\n\t\t\t\t\t\ttemp_val= ({ixfe:_ixfe, XF:XFs[_ixfe], t:'z'}/*:any*/);\n\t\t\t\t\t\tif(BIFF2Fmt > 0) temp_val.z = BIFF2FmtTable[(temp_val.ixfe>>8) & 0x3F];\n\t\t\t\t\t\tsafe_format_xf(temp_val, options, wb.opts.Date1904);\n\t\t\t\t\t\taddcell({c:_j, r:val.r}, temp_val, options);\n\t\t\t\t\t}\n\t\t\t\t} break;\n\t\t\t\tcase 0x00d6 /* RString */:\n\t\t\t\tcase 0x0204 /* Label */: case 0x0004 /* BIFF2STR */:\n\t\t\t\t\ttemp_val=make_cell(val.val, val.ixfe, 's');\n\t\t\t\t\ttemp_val.XF = XFs[temp_val.ixfe];\n\t\t\t\t\tif(BIFF2Fmt > 0) temp_val.z = BIFF2FmtTable[(temp_val.ixfe>>8) & 0x3F];\n\t\t\t\t\tsafe_format_xf(temp_val, options, wb.opts.Date1904);\n\t\t\t\t\taddcell({c:val.c, r:val.r}, temp_val, options);\n\t\t\t\t\tbreak;\n\n\t\t\t\tcase 0x0000: case 0x0200 /* Dimensions */: {\n\t\t\t\t\tif(file_depth === 1) range = val; /* TODO: stack */\n\t\t\t\t} break;\n\t\t\t\tcase 0x00fc /* SST */: {\n\t\t\t\t\tsst = val;\n\t\t\t\t} break;\n\t\t\t\tcase 0x041e /* Format */: { /* val = [id, fmt] */\n\t\t\t\t\tif(opts.biff == 4) {\n\t\t\t\t\t\tBIFF2FmtTable[BIFF2Fmt++] = val[1];\n\t\t\t\t\t\tfor(var b4idx = 0; b4idx < BIFF2Fmt + 163; ++b4idx) if(table_fmt[b4idx] == val[1]) break;\n\t\t\t\t\t\tif(b4idx >= 163) SSF_load(val[1], BIFF2Fmt + 163);\n\t\t\t\t\t}\n\t\t\t\t\telse SSF_load(val[1], val[0]);\n\t\t\t\t} break;\n\t\t\t\tcase 0x001e /* BIFF2FORMAT */: {\n\t\t\t\t\tBIFF2FmtTable[BIFF2Fmt++] = val;\n\t\t\t\t\tfor(var b2idx = 0; b2idx < BIFF2Fmt + 163; ++b2idx) if(table_fmt[b2idx] == val) break;\n\t\t\t\t\tif(b2idx >= 163) SSF_load(val, BIFF2Fmt + 163);\n\t\t\t\t} break;\n\n\t\t\t\tcase 0x00e5 /* MergeCells */: merges = merges.concat(val); break;\n\n\t\t\t\tcase 0x005d /* Obj */: objects[val.cmo[0]] = opts.lastobj = val; break;\n\t\t\t\tcase 0x01b6 /* TxO */: opts.lastobj.TxO = val; break;\n\t\t\t\tcase 0x007f /* ImData */: opts.lastobj.ImData = val; break;\n\n\t\t\t\tcase 0x01b8 /* HLink */: {\n\t\t\t\t\tfor(rngR = val[0].s.r; rngR <= val[0].e.r; ++rngR)\n\t\t\t\t\t\tfor(rngC = val[0].s.c; rngC <= val[0].e.c; ++rngC) {\n\t\t\t\t\t\t\tcc = options.dense ? (out[rngR]||[])[rngC] : out[encode_cell({c:rngC,r:rngR})];\n\t\t\t\t\t\t\tif(cc) cc.l = val[1];\n\t\t\t\t\t\t}\n\t\t\t\t} break;\n\t\t\t\tcase 0x0800 /* HLinkTooltip */: {\n\t\t\t\t\tfor(rngR = val[0].s.r; rngR <= val[0].e.r; ++rngR)\n\t\t\t\t\t\tfor(rngC = val[0].s.c; rngC <= val[0].e.c; ++rngC) {\n\t\t\t\t\t\t\tcc = options.dense ? (out[rngR]||[])[rngC] : out[encode_cell({c:rngC,r:rngR})];\n\t\t\t\t\t\t\tif(cc && cc.l) cc.l.Tooltip = val[1];\n\t\t\t\t\t\t\t}\n\t\t\t\t} break;\n\t\t\t\tcase 0x001c /* Note */: {\n\t\t\t\t\tif(opts.biff <= 5 && opts.biff >= 2) break; /* TODO: BIFF5 */\n\t\t\t\t\tcc = options.dense ? (out[val[0].r]||[])[val[0].c] : out[encode_cell(val[0])];\n\t\t\t\t\tvar noteobj = objects[val[2]];\n\t\t\t\t\tif(!cc) {\n\t\t\t\t\t\tif(options.dense) {\n\t\t\t\t\t\t\tif(!out[val[0].r]) out[val[0].r] = [];\n\t\t\t\t\t\t\tcc = out[val[0].r][val[0].c] = ({t:\"z\"}/*:any*/);\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tcc = out[encode_cell(val[0])] = ({t:\"z\"}/*:any*/);\n\t\t\t\t\t\t}\n\t\t\t\t\t\trange.e.r = Math.max(range.e.r, val[0].r);\n\t\t\t\t\t\trange.s.r = Math.min(range.s.r, val[0].r);\n\t\t\t\t\t\trange.e.c = Math.max(range.e.c, val[0].c);\n\t\t\t\t\t\trange.s.c = Math.min(range.s.c, val[0].c);\n\t\t\t\t\t}\n\t\t\t\t\tif(!cc.c) cc.c = [];\n\t\t\t\t\tcmnt = {a:val[1],t:noteobj.TxO.t};\n\t\t\t\t\tcc.c.push(cmnt);\n\t\t\t\t} break;\n\t\t\t\tcase 0x087d /* XFExt */: update_xfext(XFs[val.ixfe], val.ext); break;\n\t\t\t\tcase 0x007d /* ColInfo */: {\n\t\t\t\t\tif(!opts.cellStyles) break;\n\t\t\t\t\twhile(val.e >= val.s) {\n\t\t\t\t\t\tcolinfo[val.e--] = { width: val.w/256, level: (val.level || 0), hidden: !!(val.flags & 1) };\n\t\t\t\t\t\tif(!seencol) { seencol = true; find_mdw_colw(val.w/256); }\n\t\t\t\t\t\tprocess_col(colinfo[val.e+1]);\n\t\t\t\t\t}\n\t\t\t\t} break;\n\t\t\t\tcase 0x0208 /* Row */: {\n\t\t\t\t\tvar rowobj = {};\n\t\t\t\t\tif(val.level != null) { rowinfo[val.r] = rowobj; rowobj.level = val.level; }\n\t\t\t\t\tif(val.hidden) { rowinfo[val.r] = rowobj; rowobj.hidden = true; }\n\t\t\t\t\tif(val.hpt) {\n\t\t\t\t\t\trowinfo[val.r] = rowobj;\n\t\t\t\t\t\trowobj.hpt = val.hpt; rowobj.hpx = pt2px(val.hpt);\n\t\t\t\t\t}\n\t\t\t\t} break;\n\t\t\t\tcase 0x0026 /* LeftMargin */:\n\t\t\t\tcase 0x0027 /* RightMargin */:\n\t\t\t\tcase 0x0028 /* TopMargin */:\n\t\t\t\tcase 0x0029 /* BottomMargin */:\n\t\t\t\t\tif(!out['!margins']) default_margins(out['!margins'] = {});\n\t\t\t\t\tout['!margins'][({0x26: \"left\", 0x27:\"right\", 0x28:\"top\", 0x29:\"bottom\"})[RecordType]] = val;\n\t\t\t\t\tbreak;\n\t\t\t\tcase 0x00a1 /* Setup */: // TODO\n\t\t\t\t\tif(!out['!margins']) default_margins(out['!margins'] = {});\n\t\t\t\t\tout['!margins'].header = val.header;\n\t\t\t\t\tout['!margins'].footer = val.footer;\n\t\t\t\t\tbreak;\n\t\t\t\tcase 0x023e /* Window2 */: // TODO\n\t\t\t\t\t// $FlowIgnore\n\t\t\t\t\tif(val.RTL) Workbook.Views[0].RTL = true;\n\t\t\t\t\tbreak;\n\t\t\t\tcase 0x0092 /* Palette */: palette = val; break;\n\t\t\t\tcase 0x0896 /* Theme */: themes = val; break;\n\t\t\t\tcase 0x008c /* Country */: country = val; break;\n\t\t\t\tcase 0x01ba /* CodeName */: {\n\t\t\t\t\t/*:: if(!Workbook.WBProps) Workbook.WBProps = {}; */\n\t\t\t\t\tif(!cur_sheet) Workbook.WBProps.CodeName = val || \"ThisWorkbook\";\n\t\t\t\t\telse wsprops.CodeName = val || wsprops.name;\n\t\t\t\t} break;\n\t\t\t}\n\t\t} else {\n\t\t\tif(!R) console.error(\"Missing Info for XLS Record 0x\" + RecordType.toString(16));\n\t\t\tblob.l += length;\n\t\t}\n\t}\n\twb.SheetNames=keys(Directory).sort(function(a,b) { return Number(a) - Number(b); }).map(function(x){return Directory[x].name;});\n\tif(!options.bookSheets) wb.Sheets=Sheets;\n\tif(!wb.SheetNames.length && Preamble[\"!ref\"]) {\n\t\twb.SheetNames.push(\"Sheet1\");\n\t\t/*jshint -W069 */\n\t\tif(wb.Sheets) wb.Sheets[\"Sheet1\"] = Preamble;\n\t\t/*jshint +W069 */\n\t} else wb.Preamble=Preamble;\n\tif(wb.Sheets) FilterDatabases.forEach(function(r,i) { wb.Sheets[wb.SheetNames[i]]['!autofilter'] = r; });\n\twb.Strings = sst;\n\twb.SSF = dup(table_fmt);\n\tif(opts.enc) wb.Encryption = opts.enc;\n\tif(themes) wb.Themes = themes;\n\twb.Metadata = {};\n\tif(country !== undefined) wb.Metadata.Country = country;\n\tif(supbooks.names.length > 0) Workbook.Names = supbooks.names;\n\twb.Workbook = Workbook;\n\treturn wb;\n}\n\n/* TODO: split props*/\nvar PSCLSID = {\n\tSI: \"e0859ff2f94f6810ab9108002b27b3d9\",\n\tDSI: \"02d5cdd59c2e1b10939708002b2cf9ae\",\n\tUDI: \"05d5cdd59c2e1b10939708002b2cf9ae\"\n};\nfunction parse_xls_props(cfb/*:CFBContainer*/, props, o) {\n\t/* [MS-OSHARED] 2.3.3.2.2 Document Summary Information Property Set */\n\tvar DSI = CFB.find(cfb, '/!DocumentSummaryInformation');\n\tif(DSI && DSI.size > 0) try {\n\t\tvar DocSummary = parse_PropertySetStream(DSI, DocSummaryPIDDSI, PSCLSID.DSI);\n\t\tfor(var d in DocSummary) props[d] = DocSummary[d];\n\t} catch(e) {if(o.WTF) throw e;/* empty */}\n\n\t/* [MS-OSHARED] 2.3.3.2.1 Summary Information Property Set*/\n\tvar SI = CFB.find(cfb, '/!SummaryInformation');\n\tif(SI && SI.size > 0) try {\n\t\tvar Summary = parse_PropertySetStream(SI, SummaryPIDSI, PSCLSID.SI);\n\t\tfor(var s in Summary) if(props[s] == null) props[s] = Summary[s];\n\t} catch(e) {if(o.WTF) throw e;/* empty */}\n\n\tif(props.HeadingPairs && props.TitlesOfParts) {\n\t\tload_props_pairs(props.HeadingPairs, props.TitlesOfParts, props, o);\n\t\tdelete props.HeadingPairs; delete props.TitlesOfParts;\n\t}\n}\nfunction write_xls_props(wb/*:Workbook*/, cfb/*:CFBContainer*/) {\n\tvar DSEntries = [], SEntries = [], CEntries = [];\n\tvar i = 0, Keys;\n\tvar DocSummaryRE/*:{[key:string]:string}*/ = evert_key(DocSummaryPIDDSI, \"n\");\n\tvar SummaryRE/*:{[key:string]:string}*/ = evert_key(SummaryPIDSI, \"n\");\n\tif(wb.Props) {\n\t\tKeys = keys(wb.Props);\n\t\t// $FlowIgnore\n\t\tfor(i = 0; i < Keys.length; ++i) (Object.prototype.hasOwnProperty.call(DocSummaryRE, Keys[i]) ? DSEntries : Object.prototype.hasOwnProperty.call(SummaryRE, Keys[i]) ? SEntries : CEntries).push([Keys[i], wb.Props[Keys[i]]]);\n\t}\n\tif(wb.Custprops) {\n\t\tKeys = keys(wb.Custprops);\n\t\t// $FlowIgnore\n\t\tfor(i = 0; i < Keys.length; ++i) if(!Object.prototype.hasOwnProperty.call((wb.Props||{}), Keys[i])) (Object.prototype.hasOwnProperty.call(DocSummaryRE, Keys[i]) ? DSEntries : Object.prototype.hasOwnProperty.call(SummaryRE, Keys[i]) ? SEntries : CEntries).push([Keys[i], wb.Custprops[Keys[i]]]);\n\t}\n\tvar CEntries2 = [];\n\tfor(i = 0; i < CEntries.length; ++i) {\n\t\tif(XLSPSSkip.indexOf(CEntries[i][0]) > -1 || PseudoPropsPairs.indexOf(CEntries[i][0]) > -1) continue;\n\t\tif(CEntries[i][1] == null) continue;\n\t\tCEntries2.push(CEntries[i]);\n\t}\n\tif(SEntries.length) CFB.utils.cfb_add(cfb, \"/\\u0005SummaryInformation\", write_PropertySetStream(SEntries, PSCLSID.SI, SummaryRE, SummaryPIDSI));\n\tif(DSEntries.length || CEntries2.length) CFB.utils.cfb_add(cfb, \"/\\u0005DocumentSummaryInformation\", write_PropertySetStream(DSEntries, PSCLSID.DSI, DocSummaryRE, DocSummaryPIDDSI, CEntries2.length ? CEntries2 : null, PSCLSID.UDI));\n}\n\nfunction parse_xlscfb(cfb/*:any*/, options/*:?ParseOpts*/)/*:Workbook*/ {\nif(!options) options = {};\nfix_read_opts(options);\nreset_cp();\nif(options.codepage) set_ansi(options.codepage);\nvar CompObj/*:?CFBEntry*/, WB/*:?any*/;\nif(cfb.FullPaths) {\n\tif(CFB.find(cfb, '/encryption')) throw new Error(\"File is password-protected\");\n\tCompObj = CFB.find(cfb, '!CompObj');\n\tWB = CFB.find(cfb, '/Workbook') || CFB.find(cfb, '/Book');\n} else {\n\tswitch(options.type) {\n\t\tcase 'base64': cfb = s2a(Base64_decode(cfb)); break;\n\t\tcase 'binary': cfb = s2a(cfb); break;\n\t\tcase 'buffer': break;\n\t\tcase 'array': if(!Array.isArray(cfb)) cfb = Array.prototype.slice.call(cfb); break;\n\t}\n\tprep_blob(cfb, 0);\n\tWB = ({content: cfb}/*:any*/);\n}\nvar /*::CompObjP, */WorkbookP/*:: :Workbook = XLSX.utils.book_new(); */;\n\nvar _data/*:?any*/;\nif(CompObj) /*::CompObjP = */parse_compobj(CompObj);\nif(options.bookProps && !options.bookSheets) WorkbookP = ({}/*:any*/);\nelse/*:: if(cfb instanceof CFBContainer) */ {\n\tvar T = has_buf ? 'buffer' : 'array';\n\tif(WB && WB.content) WorkbookP = parse_workbook(WB.content, options);\n\t/* Quattro Pro 7-8 */\n\telse if((_data=CFB.find(cfb, 'PerfectOffice_MAIN')) && _data.content) WorkbookP = WK_.to_workbook(_data.content, (options.type = T, options));\n\t/* Quattro Pro 9 */\n\telse if((_data=CFB.find(cfb, 'NativeContent_MAIN')) && _data.content) WorkbookP = WK_.to_workbook(_data.content, (options.type = T, options));\n\t/* Works 4 for Mac */\n\telse if((_data=CFB.find(cfb, 'MN0')) && _data.content) throw new Error(\"Unsupported Works 4 for Mac file\");\n\telse throw new Error(\"Cannot find Workbook stream\");\n\tif(options.bookVBA && cfb.FullPaths && CFB.find(cfb, '/_VBA_PROJECT_CUR/VBA/dir')) WorkbookP.vbaraw = make_vba_xls(cfb);\n}\n\nvar props = {};\nif(cfb.FullPaths) parse_xls_props(/*::((*/cfb/*:: :any):CFBContainer)*/, props, options);\n\nWorkbookP.Props = WorkbookP.Custprops = props; /* TODO: split up properties */\nif(options.bookFiles) WorkbookP.cfb = cfb;\n/*WorkbookP.CompObjP = CompObjP; // TODO: storage? */\nreturn WorkbookP;\n}\n\n\nfunction write_xlscfb(wb/*:Workbook*/, opts/*:WriteOpts*/)/*:CFBContainer*/ {\n\tvar o = opts || {};\n\tvar cfb = CFB.utils.cfb_new({root:\"R\"});\n\tvar wbpath = \"/Workbook\";\n\tswitch(o.bookType || \"xls\") {\n\t\tcase \"xls\": o.bookType = \"biff8\";\n\t\t/* falls through */\n\t\tcase \"xla\": if(!o.bookType) o.bookType = \"xla\";\n\t\t/* falls through */\n\t\tcase \"biff8\": wbpath = \"/Workbook\"; o.biff = 8; break;\n\t\tcase \"biff5\": wbpath = \"/Book\"; o.biff = 5; break;\n\t\tdefault: throw new Error(\"invalid type \" + o.bookType + \" for XLS CFB\");\n\t}\n\tCFB.utils.cfb_add(cfb, wbpath, write_biff_buf(wb, o));\n\tif(o.biff == 8 && (wb.Props || wb.Custprops)) write_xls_props(wb, cfb);\n\t// TODO: SI, DSI, CO\n\tif(o.biff == 8 && wb.vbaraw) fill_vba_xls(cfb, CFB.read(wb.vbaraw, {type: typeof wb.vbaraw == \"string\" ? \"binary\" : \"buffer\"}));\n\treturn cfb;\n}\n/* [MS-XLSB] 2.3 Record Enumeration */\nvar XLSBRecordEnum = {\n\t/*::[*/0x0000/*::]*/: { /* n:\"BrtRowHdr\", */ f:parse_BrtRowHdr },\n\t/*::[*/0x0001/*::]*/: { /* n:\"BrtCellBlank\", */ f:parse_BrtCellBlank },\n\t/*::[*/0x0002/*::]*/: { /* n:\"BrtCellRk\", */ f:parse_BrtCellRk },\n\t/*::[*/0x0003/*::]*/: { /* n:\"BrtCellError\", */ f:parse_BrtCellError },\n\t/*::[*/0x0004/*::]*/: { /* n:\"BrtCellBool\", */ f:parse_BrtCellBool },\n\t/*::[*/0x0005/*::]*/: { /* n:\"BrtCellReal\", */ f:parse_BrtCellReal },\n\t/*::[*/0x0006/*::]*/: { /* n:\"BrtCellSt\", */ f:parse_BrtCellSt },\n\t/*::[*/0x0007/*::]*/: { /* n:\"BrtCellIsst\", */ f:parse_BrtCellIsst },\n\t/*::[*/0x0008/*::]*/: { /* n:\"BrtFmlaString\", */ f:parse_BrtFmlaString },\n\t/*::[*/0x0009/*::]*/: { /* n:\"BrtFmlaNum\", */ f:parse_BrtFmlaNum },\n\t/*::[*/0x000A/*::]*/: { /* n:\"BrtFmlaBool\", */ f:parse_BrtFmlaBool },\n\t/*::[*/0x000B/*::]*/: { /* n:\"BrtFmlaError\", */ f:parse_BrtFmlaError },\n\t/*::[*/0x000C/*::]*/: { /* n:\"BrtShortBlank\", */ f:parse_BrtShortBlank },\n\t/*::[*/0x000D/*::]*/: { /* n:\"BrtShortRk\", */ f:parse_BrtShortRk },\n\t/*::[*/0x000E/*::]*/: { /* n:\"BrtShortError\", */ f:parse_BrtShortError },\n\t/*::[*/0x000F/*::]*/: { /* n:\"BrtShortBool\", */ f:parse_BrtShortBool },\n\t/*::[*/0x0010/*::]*/: { /* n:\"BrtShortReal\", */ f:parse_BrtShortReal },\n\t/*::[*/0x0011/*::]*/: { /* n:\"BrtShortSt\", */ f:parse_BrtShortSt },\n\t/*::[*/0x0012/*::]*/: { /* n:\"BrtShortIsst\", */ f:parse_BrtShortIsst },\n\t/*::[*/0x0013/*::]*/: { /* n:\"BrtSSTItem\", */ f:parse_RichStr },\n\t/*::[*/0x0014/*::]*/: { /* n:\"BrtPCDIMissing\" */ },\n\t/*::[*/0x0015/*::]*/: { /* n:\"BrtPCDINumber\" */ },\n\t/*::[*/0x0016/*::]*/: { /* n:\"BrtPCDIBoolean\" */ },\n\t/*::[*/0x0017/*::]*/: { /* n:\"BrtPCDIError\" */ },\n\t/*::[*/0x0018/*::]*/: { /* n:\"BrtPCDIString\" */ },\n\t/*::[*/0x0019/*::]*/: { /* n:\"BrtPCDIDatetime\" */ },\n\t/*::[*/0x001A/*::]*/: { /* n:\"BrtPCDIIndex\" */ },\n\t/*::[*/0x001B/*::]*/: { /* n:\"BrtPCDIAMissing\" */ },\n\t/*::[*/0x001C/*::]*/: { /* n:\"BrtPCDIANumber\" */ },\n\t/*::[*/0x001D/*::]*/: { /* n:\"BrtPCDIABoolean\" */ },\n\t/*::[*/0x001E/*::]*/: { /* n:\"BrtPCDIAError\" */ },\n\t/*::[*/0x001F/*::]*/: { /* n:\"BrtPCDIAString\" */ },\n\t/*::[*/0x0020/*::]*/: { /* n:\"BrtPCDIADatetime\" */ },\n\t/*::[*/0x0021/*::]*/: { /* n:\"BrtPCRRecord\" */ },\n\t/*::[*/0x0022/*::]*/: { /* n:\"BrtPCRRecordDt\" */ },\n\t/*::[*/0x0023/*::]*/: { /* n:\"BrtFRTBegin\", */ T:1 },\n\t/*::[*/0x0024/*::]*/: { /* n:\"BrtFRTEnd\", */ T:-1 },\n\t/*::[*/0x0025/*::]*/: { /* n:\"BrtACBegin\", */ T:1 },\n\t/*::[*/0x0026/*::]*/: { /* n:\"BrtACEnd\", */ T:-1 },\n\t/*::[*/0x0027/*::]*/: { /* n:\"BrtName\", */ f:parse_BrtName },\n\t/*::[*/0x0028/*::]*/: { /* n:\"BrtIndexRowBlock\" */ },\n\t/*::[*/0x002A/*::]*/: { /* n:\"BrtIndexBlock\" */ },\n\t/*::[*/0x002B/*::]*/: { /* n:\"BrtFont\", */ f:parse_BrtFont },\n\t/*::[*/0x002C/*::]*/: { /* n:\"BrtFmt\", */ f:parse_BrtFmt },\n\t/*::[*/0x002D/*::]*/: { /* n:\"BrtFill\", */ f:parse_BrtFill },\n\t/*::[*/0x002E/*::]*/: { /* n:\"BrtBorder\", */ f:parse_BrtBorder },\n\t/*::[*/0x002F/*::]*/: { /* n:\"BrtXF\", */ f:parse_BrtXF },\n\t/*::[*/0x0030/*::]*/: { /* n:\"BrtStyle\" */ },\n\t/*::[*/0x0031/*::]*/: { /* n:\"BrtCellMeta\", */ f:parse_Int32LE },\n\t/*::[*/0x0032/*::]*/: { /* n:\"BrtValueMeta\" */ },\n\t/*::[*/0x0033/*::]*/: { /* n:\"BrtMdb\" */ f:parse_BrtMdb },\n\t/*::[*/0x0034/*::]*/: { /* n:\"BrtBeginFmd\", */ T:1 },\n\t/*::[*/0x0035/*::]*/: { /* n:\"BrtEndFmd\", */ T:-1 },\n\t/*::[*/0x0036/*::]*/: { /* n:\"BrtBeginMdx\", */ T:1 },\n\t/*::[*/0x0037/*::]*/: { /* n:\"BrtEndMdx\", */ T:-1 },\n\t/*::[*/0x0038/*::]*/: { /* n:\"BrtBeginMdxTuple\", */ T:1 },\n\t/*::[*/0x0039/*::]*/: { /* n:\"BrtEndMdxTuple\", */ T:-1 },\n\t/*::[*/0x003A/*::]*/: { /* n:\"BrtMdxMbrIstr\" */ },\n\t/*::[*/0x003B/*::]*/: { /* n:\"BrtStr\" */ },\n\t/*::[*/0x003C/*::]*/: { /* n:\"BrtColInfo\", */ f:parse_ColInfo },\n\t/*::[*/0x003E/*::]*/: { /* n:\"BrtCellRString\", */ f:parse_BrtCellRString },\n\t/*::[*/0x003F/*::]*/: { /* n:\"BrtCalcChainItem$\", */ f:parse_BrtCalcChainItem$ },\n\t/*::[*/0x0040/*::]*/: { /* n:\"BrtDVal\", */ f:parse_BrtDVal },\n\t/*::[*/0x0041/*::]*/: { /* n:\"BrtSxvcellNum\" */ },\n\t/*::[*/0x0042/*::]*/: { /* n:\"BrtSxvcellStr\" */ },\n\t/*::[*/0x0043/*::]*/: { /* n:\"BrtSxvcellBool\" */ },\n\t/*::[*/0x0044/*::]*/: { /* n:\"BrtSxvcellErr\" */ },\n\t/*::[*/0x0045/*::]*/: { /* n:\"BrtSxvcellDate\" */ },\n\t/*::[*/0x0046/*::]*/: { /* n:\"BrtSxvcellNil\" */ },\n\t/*::[*/0x0080/*::]*/: { /* n:\"BrtFileVersion\" */ },\n\t/*::[*/0x0081/*::]*/: { /* n:\"BrtBeginSheet\", */ T:1 },\n\t/*::[*/0x0082/*::]*/: { /* n:\"BrtEndSheet\", */ T:-1 },\n\t/*::[*/0x0083/*::]*/: { /* n:\"BrtBeginBook\", */ T:1, f:parsenoop, p:0 },\n\t/*::[*/0x0084/*::]*/: { /* n:\"BrtEndBook\", */ T:-1 },\n\t/*::[*/0x0085/*::]*/: { /* n:\"BrtBeginWsViews\", */ T:1 },\n\t/*::[*/0x0086/*::]*/: { /* n:\"BrtEndWsViews\", */ T:-1 },\n\t/*::[*/0x0087/*::]*/: { /* n:\"BrtBeginBookViews\", */ T:1 },\n\t/*::[*/0x0088/*::]*/: { /* n:\"BrtEndBookViews\", */ T:-1 },\n\t/*::[*/0x0089/*::]*/: { /* n:\"BrtBeginWsView\", */ T:1, f:parse_BrtBeginWsView },\n\t/*::[*/0x008A/*::]*/: { /* n:\"BrtEndWsView\", */ T:-1 },\n\t/*::[*/0x008B/*::]*/: { /* n:\"BrtBeginCsViews\", */ T:1 },\n\t/*::[*/0x008C/*::]*/: { /* n:\"BrtEndCsViews\", */ T:-1 },\n\t/*::[*/0x008D/*::]*/: { /* n:\"BrtBeginCsView\", */ T:1 },\n\t/*::[*/0x008E/*::]*/: { /* n:\"BrtEndCsView\", */ T:-1 },\n\t/*::[*/0x008F/*::]*/: { /* n:\"BrtBeginBundleShs\", */ T:1 },\n\t/*::[*/0x0090/*::]*/: { /* n:\"BrtEndBundleShs\", */ T:-1 },\n\t/*::[*/0x0091/*::]*/: { /* n:\"BrtBeginSheetData\", */ T:1 },\n\t/*::[*/0x0092/*::]*/: { /* n:\"BrtEndSheetData\", */ T:-1 },\n\t/*::[*/0x0093/*::]*/: { /* n:\"BrtWsProp\", */ f:parse_BrtWsProp },\n\t/*::[*/0x0094/*::]*/: { /* n:\"BrtWsDim\", */ f:parse_BrtWsDim, p:16 },\n\t/*::[*/0x0097/*::]*/: { /* n:\"BrtPane\", */ f:parse_BrtPane },\n\t/*::[*/0x0098/*::]*/: { /* n:\"BrtSel\" */ },\n\t/*::[*/0x0099/*::]*/: { /* n:\"BrtWbProp\", */ f:parse_BrtWbProp },\n\t/*::[*/0x009A/*::]*/: { /* n:\"BrtWbFactoid\" */ },\n\t/*::[*/0x009B/*::]*/: { /* n:\"BrtFileRecover\" */ },\n\t/*::[*/0x009C/*::]*/: { /* n:\"BrtBundleSh\", */ f:parse_BrtBundleSh },\n\t/*::[*/0x009D/*::]*/: { /* n:\"BrtCalcProp\" */ },\n\t/*::[*/0x009E/*::]*/: { /* n:\"BrtBookView\" */ },\n\t/*::[*/0x009F/*::]*/: { /* n:\"BrtBeginSst\", */ T:1, f:parse_BrtBeginSst },\n\t/*::[*/0x00A0/*::]*/: { /* n:\"BrtEndSst\", */ T:-1 },\n\t/*::[*/0x00A1/*::]*/: { /* n:\"BrtBeginAFilter\", */ T:1, f:parse_UncheckedRfX },\n\t/*::[*/0x00A2/*::]*/: { /* n:\"BrtEndAFilter\", */ T:-1 },\n\t/*::[*/0x00A3/*::]*/: { /* n:\"BrtBeginFilterColumn\", */ T:1 },\n\t/*::[*/0x00A4/*::]*/: { /* n:\"BrtEndFilterColumn\", */ T:-1 },\n\t/*::[*/0x00A5/*::]*/: { /* n:\"BrtBeginFilters\", */ T:1 },\n\t/*::[*/0x00A6/*::]*/: { /* n:\"BrtEndFilters\", */ T:-1 },\n\t/*::[*/0x00A7/*::]*/: { /* n:\"BrtFilter\" */ },\n\t/*::[*/0x00A8/*::]*/: { /* n:\"BrtColorFilter\" */ },\n\t/*::[*/0x00A9/*::]*/: { /* n:\"BrtIconFilter\" */ },\n\t/*::[*/0x00AA/*::]*/: { /* n:\"BrtTop10Filter\" */ },\n\t/*::[*/0x00AB/*::]*/: { /* n:\"BrtDynamicFilter\" */ },\n\t/*::[*/0x00AC/*::]*/: { /* n:\"BrtBeginCustomFilters\", */ T:1 },\n\t/*::[*/0x00AD/*::]*/: { /* n:\"BrtEndCustomFilters\", */ T:-1 },\n\t/*::[*/0x00AE/*::]*/: { /* n:\"BrtCustomFilter\" */ },\n\t/*::[*/0x00AF/*::]*/: { /* n:\"BrtAFilterDateGroupItem\" */ },\n\t/*::[*/0x00B0/*::]*/: { /* n:\"BrtMergeCell\", */ f:parse_BrtMergeCell },\n\t/*::[*/0x00B1/*::]*/: { /* n:\"BrtBeginMergeCells\", */ T:1 },\n\t/*::[*/0x00B2/*::]*/: { /* n:\"BrtEndMergeCells\", */ T:-1 },\n\t/*::[*/0x00B3/*::]*/: { /* n:\"BrtBeginPivotCacheDef\", */ T:1 },\n\t/*::[*/0x00B4/*::]*/: { /* n:\"BrtEndPivotCacheDef\", */ T:-1 },\n\t/*::[*/0x00B5/*::]*/: { /* n:\"BrtBeginPCDFields\", */ T:1 },\n\t/*::[*/0x00B6/*::]*/: { /* n:\"BrtEndPCDFields\", */ T:-1 },\n\t/*::[*/0x00B7/*::]*/: { /* n:\"BrtBeginPCDField\", */ T:1 },\n\t/*::[*/0x00B8/*::]*/: { /* n:\"BrtEndPCDField\", */ T:-1 },\n\t/*::[*/0x00B9/*::]*/: { /* n:\"BrtBeginPCDSource\", */ T:1 },\n\t/*::[*/0x00BA/*::]*/: { /* n:\"BrtEndPCDSource\", */ T:-1 },\n\t/*::[*/0x00BB/*::]*/: { /* n:\"BrtBeginPCDSRange\", */ T:1 },\n\t/*::[*/0x00BC/*::]*/: { /* n:\"BrtEndPCDSRange\", */ T:-1 },\n\t/*::[*/0x00BD/*::]*/: { /* n:\"BrtBeginPCDFAtbl\", */ T:1 },\n\t/*::[*/0x00BE/*::]*/: { /* n:\"BrtEndPCDFAtbl\", */ T:-1 },\n\t/*::[*/0x00BF/*::]*/: { /* n:\"BrtBeginPCDIRun\", */ T:1 },\n\t/*::[*/0x00C0/*::]*/: { /* n:\"BrtEndPCDIRun\", */ T:-1 },\n\t/*::[*/0x00C1/*::]*/: { /* n:\"BrtBeginPivotCacheRecords\", */ T:1 },\n\t/*::[*/0x00C2/*::]*/: { /* n:\"BrtEndPivotCacheRecords\", */ T:-1 },\n\t/*::[*/0x00C3/*::]*/: { /* n:\"BrtBeginPCDHierarchies\", */ T:1 },\n\t/*::[*/0x00C4/*::]*/: { /* n:\"BrtEndPCDHierarchies\", */ T:-1 },\n\t/*::[*/0x00C5/*::]*/: { /* n:\"BrtBeginPCDHierarchy\", */ T:1 },\n\t/*::[*/0x00C6/*::]*/: { /* n:\"BrtEndPCDHierarchy\", */ T:-1 },\n\t/*::[*/0x00C7/*::]*/: { /* n:\"BrtBeginPCDHFieldsUsage\", */ T:1 },\n\t/*::[*/0x00C8/*::]*/: { /* n:\"BrtEndPCDHFieldsUsage\", */ T:-1 },\n\t/*::[*/0x00C9/*::]*/: { /* n:\"BrtBeginExtConnection\", */ T:1 },\n\t/*::[*/0x00CA/*::]*/: { /* n:\"BrtEndExtConnection\", */ T:-1 },\n\t/*::[*/0x00CB/*::]*/: { /* n:\"BrtBeginECDbProps\", */ T:1 },\n\t/*::[*/0x00CC/*::]*/: { /* n:\"BrtEndECDbProps\", */ T:-1 },\n\t/*::[*/0x00CD/*::]*/: { /* n:\"BrtBeginECOlapProps\", */ T:1 },\n\t/*::[*/0x00CE/*::]*/: { /* n:\"BrtEndECOlapProps\", */ T:-1 },\n\t/*::[*/0x00CF/*::]*/: { /* n:\"BrtBeginPCDSConsol\", */ T:1 },\n\t/*::[*/0x00D0/*::]*/: { /* n:\"BrtEndPCDSConsol\", */ T:-1 },\n\t/*::[*/0x00D1/*::]*/: { /* n:\"BrtBeginPCDSCPages\", */ T:1 },\n\t/*::[*/0x00D2/*::]*/: { /* n:\"BrtEndPCDSCPages\", */ T:-1 },\n\t/*::[*/0x00D3/*::]*/: { /* n:\"BrtBeginPCDSCPage\", */ T:1 },\n\t/*::[*/0x00D4/*::]*/: { /* n:\"BrtEndPCDSCPage\", */ T:-1 },\n\t/*::[*/0x00D5/*::]*/: { /* n:\"BrtBeginPCDSCPItem\", */ T:1 },\n\t/*::[*/0x00D6/*::]*/: { /* n:\"BrtEndPCDSCPItem\", */ T:-1 },\n\t/*::[*/0x00D7/*::]*/: { /* n:\"BrtBeginPCDSCSets\", */ T:1 },\n\t/*::[*/0x00D8/*::]*/: { /* n:\"BrtEndPCDSCSets\", */ T:-1 },\n\t/*::[*/0x00D9/*::]*/: { /* n:\"BrtBeginPCDSCSet\", */ T:1 },\n\t/*::[*/0x00DA/*::]*/: { /* n:\"BrtEndPCDSCSet\", */ T:-1 },\n\t/*::[*/0x00DB/*::]*/: { /* n:\"BrtBeginPCDFGroup\", */ T:1 },\n\t/*::[*/0x00DC/*::]*/: { /* n:\"BrtEndPCDFGroup\", */ T:-1 },\n\t/*::[*/0x00DD/*::]*/: { /* n:\"BrtBeginPCDFGItems\", */ T:1 },\n\t/*::[*/0x00DE/*::]*/: { /* n:\"BrtEndPCDFGItems\", */ T:-1 },\n\t/*::[*/0x00DF/*::]*/: { /* n:\"BrtBeginPCDFGRange\", */ T:1 },\n\t/*::[*/0x00E0/*::]*/: { /* n:\"BrtEndPCDFGRange\", */ T:-1 },\n\t/*::[*/0x00E1/*::]*/: { /* n:\"BrtBeginPCDFGDiscrete\", */ T:1 },\n\t/*::[*/0x00E2/*::]*/: { /* n:\"BrtEndPCDFGDiscrete\", */ T:-1 },\n\t/*::[*/0x00E3/*::]*/: { /* n:\"BrtBeginPCDSDTupleCache\", */ T:1 },\n\t/*::[*/0x00E4/*::]*/: { /* n:\"BrtEndPCDSDTupleCache\", */ T:-1 },\n\t/*::[*/0x00E5/*::]*/: { /* n:\"BrtBeginPCDSDTCEntries\", */ T:1 },\n\t/*::[*/0x00E6/*::]*/: { /* n:\"BrtEndPCDSDTCEntries\", */ T:-1 },\n\t/*::[*/0x00E7/*::]*/: { /* n:\"BrtBeginPCDSDTCEMembers\", */ T:1 },\n\t/*::[*/0x00E8/*::]*/: { /* n:\"BrtEndPCDSDTCEMembers\", */ T:-1 },\n\t/*::[*/0x00E9/*::]*/: { /* n:\"BrtBeginPCDSDTCEMember\", */ T:1 },\n\t/*::[*/0x00EA/*::]*/: { /* n:\"BrtEndPCDSDTCEMember\", */ T:-1 },\n\t/*::[*/0x00EB/*::]*/: { /* n:\"BrtBeginPCDSDTCQueries\", */ T:1 },\n\t/*::[*/0x00EC/*::]*/: { /* n:\"BrtEndPCDSDTCQueries\", */ T:-1 },\n\t/*::[*/0x00ED/*::]*/: { /* n:\"BrtBeginPCDSDTCQuery\", */ T:1 },\n\t/*::[*/0x00EE/*::]*/: { /* n:\"BrtEndPCDSDTCQuery\", */ T:-1 },\n\t/*::[*/0x00EF/*::]*/: { /* n:\"BrtBeginPCDSDTCSets\", */ T:1 },\n\t/*::[*/0x00F0/*::]*/: { /* n:\"BrtEndPCDSDTCSets\", */ T:-1 },\n\t/*::[*/0x00F1/*::]*/: { /* n:\"BrtBeginPCDSDTCSet\", */ T:1 },\n\t/*::[*/0x00F2/*::]*/: { /* n:\"BrtEndPCDSDTCSet\", */ T:-1 },\n\t/*::[*/0x00F3/*::]*/: { /* n:\"BrtBeginPCDCalcItems\", */ T:1 },\n\t/*::[*/0x00F4/*::]*/: { /* n:\"BrtEndPCDCalcItems\", */ T:-1 },\n\t/*::[*/0x00F5/*::]*/: { /* n:\"BrtBeginPCDCalcItem\", */ T:1 },\n\t/*::[*/0x00F6/*::]*/: { /* n:\"BrtEndPCDCalcItem\", */ T:-1 },\n\t/*::[*/0x00F7/*::]*/: { /* n:\"BrtBeginPRule\", */ T:1 },\n\t/*::[*/0x00F8/*::]*/: { /* n:\"BrtEndPRule\", */ T:-1 },\n\t/*::[*/0x00F9/*::]*/: { /* n:\"BrtBeginPRFilters\", */ T:1 },\n\t/*::[*/0x00FA/*::]*/: { /* n:\"BrtEndPRFilters\", */ T:-1 },\n\t/*::[*/0x00FB/*::]*/: { /* n:\"BrtBeginPRFilter\", */ T:1 },\n\t/*::[*/0x00FC/*::]*/: { /* n:\"BrtEndPRFilter\", */ T:-1 },\n\t/*::[*/0x00FD/*::]*/: { /* n:\"BrtBeginPNames\", */ T:1 },\n\t/*::[*/0x00FE/*::]*/: { /* n:\"BrtEndPNames\", */ T:-1 },\n\t/*::[*/0x00FF/*::]*/: { /* n:\"BrtBeginPName\", */ T:1 },\n\t/*::[*/0x0100/*::]*/: { /* n:\"BrtEndPName\", */ T:-1 },\n\t/*::[*/0x0101/*::]*/: { /* n:\"BrtBeginPNPairs\", */ T:1 },\n\t/*::[*/0x0102/*::]*/: { /* n:\"BrtEndPNPairs\", */ T:-1 },\n\t/*::[*/0x0103/*::]*/: { /* n:\"BrtBeginPNPair\", */ T:1 },\n\t/*::[*/0x0104/*::]*/: { /* n:\"BrtEndPNPair\", */ T:-1 },\n\t/*::[*/0x0105/*::]*/: { /* n:\"BrtBeginECWebProps\", */ T:1 },\n\t/*::[*/0x0106/*::]*/: { /* n:\"BrtEndECWebProps\", */ T:-1 },\n\t/*::[*/0x0107/*::]*/: { /* n:\"BrtBeginEcWpTables\", */ T:1 },\n\t/*::[*/0x0108/*::]*/: { /* n:\"BrtEndECWPTables\", */ T:-1 },\n\t/*::[*/0x0109/*::]*/: { /* n:\"BrtBeginECParams\", */ T:1 },\n\t/*::[*/0x010A/*::]*/: { /* n:\"BrtEndECParams\", */ T:-1 },\n\t/*::[*/0x010B/*::]*/: { /* n:\"BrtBeginECParam\", */ T:1 },\n\t/*::[*/0x010C/*::]*/: { /* n:\"BrtEndECParam\", */ T:-1 },\n\t/*::[*/0x010D/*::]*/: { /* n:\"BrtBeginPCDKPIs\", */ T:1 },\n\t/*::[*/0x010E/*::]*/: { /* n:\"BrtEndPCDKPIs\", */ T:-1 },\n\t/*::[*/0x010F/*::]*/: { /* n:\"BrtBeginPCDKPI\", */ T:1 },\n\t/*::[*/0x0110/*::]*/: { /* n:\"BrtEndPCDKPI\", */ T:-1 },\n\t/*::[*/0x0111/*::]*/: { /* n:\"BrtBeginDims\", */ T:1 },\n\t/*::[*/0x0112/*::]*/: { /* n:\"BrtEndDims\", */ T:-1 },\n\t/*::[*/0x0113/*::]*/: { /* n:\"BrtBeginDim\", */ T:1 },\n\t/*::[*/0x0114/*::]*/: { /* n:\"BrtEndDim\", */ T:-1 },\n\t/*::[*/0x0115/*::]*/: { /* n:\"BrtIndexPartEnd\" */ },\n\t/*::[*/0x0116/*::]*/: { /* n:\"BrtBeginStyleSheet\", */ T:1 },\n\t/*::[*/0x0117/*::]*/: { /* n:\"BrtEndStyleSheet\", */ T:-1 },\n\t/*::[*/0x0118/*::]*/: { /* n:\"BrtBeginSXView\", */ T:1 },\n\t/*::[*/0x0119/*::]*/: { /* n:\"BrtEndSXVI\", */ T:-1 },\n\t/*::[*/0x011A/*::]*/: { /* n:\"BrtBeginSXVI\", */ T:1 },\n\t/*::[*/0x011B/*::]*/: { /* n:\"BrtBeginSXVIs\", */ T:1 },\n\t/*::[*/0x011C/*::]*/: { /* n:\"BrtEndSXVIs\", */ T:-1 },\n\t/*::[*/0x011D/*::]*/: { /* n:\"BrtBeginSXVD\", */ T:1 },\n\t/*::[*/0x011E/*::]*/: { /* n:\"BrtEndSXVD\", */ T:-1 },\n\t/*::[*/0x011F/*::]*/: { /* n:\"BrtBeginSXVDs\", */ T:1 },\n\t/*::[*/0x0120/*::]*/: { /* n:\"BrtEndSXVDs\", */ T:-1 },\n\t/*::[*/0x0121/*::]*/: { /* n:\"BrtBeginSXPI\", */ T:1 },\n\t/*::[*/0x0122/*::]*/: { /* n:\"BrtEndSXPI\", */ T:-1 },\n\t/*::[*/0x0123/*::]*/: { /* n:\"BrtBeginSXPIs\", */ T:1 },\n\t/*::[*/0x0124/*::]*/: { /* n:\"BrtEndSXPIs\", */ T:-1 },\n\t/*::[*/0x0125/*::]*/: { /* n:\"BrtBeginSXDI\", */ T:1 },\n\t/*::[*/0x0126/*::]*/: { /* n:\"BrtEndSXDI\", */ T:-1 },\n\t/*::[*/0x0127/*::]*/: { /* n:\"BrtBeginSXDIs\", */ T:1 },\n\t/*::[*/0x0128/*::]*/: { /* n:\"BrtEndSXDIs\", */ T:-1 },\n\t/*::[*/0x0129/*::]*/: { /* n:\"BrtBeginSXLI\", */ T:1 },\n\t/*::[*/0x012A/*::]*/: { /* n:\"BrtEndSXLI\", */ T:-1 },\n\t/*::[*/0x012B/*::]*/: { /* n:\"BrtBeginSXLIRws\", */ T:1 },\n\t/*::[*/0x012C/*::]*/: { /* n:\"BrtEndSXLIRws\", */ T:-1 },\n\t/*::[*/0x012D/*::]*/: { /* n:\"BrtBeginSXLICols\", */ T:1 },\n\t/*::[*/0x012E/*::]*/: { /* n:\"BrtEndSXLICols\", */ T:-1 },\n\t/*::[*/0x012F/*::]*/: { /* n:\"BrtBeginSXFormat\", */ T:1 },\n\t/*::[*/0x0130/*::]*/: { /* n:\"BrtEndSXFormat\", */ T:-1 },\n\t/*::[*/0x0131/*::]*/: { /* n:\"BrtBeginSXFormats\", */ T:1 },\n\t/*::[*/0x0132/*::]*/: { /* n:\"BrtEndSxFormats\", */ T:-1 },\n\t/*::[*/0x0133/*::]*/: { /* n:\"BrtBeginSxSelect\", */ T:1 },\n\t/*::[*/0x0134/*::]*/: { /* n:\"BrtEndSxSelect\", */ T:-1 },\n\t/*::[*/0x0135/*::]*/: { /* n:\"BrtBeginISXVDRws\", */ T:1 },\n\t/*::[*/0x0136/*::]*/: { /* n:\"BrtEndISXVDRws\", */ T:-1 },\n\t/*::[*/0x0137/*::]*/: { /* n:\"BrtBeginISXVDCols\", */ T:1 },\n\t/*::[*/0x0138/*::]*/: { /* n:\"BrtEndISXVDCols\", */ T:-1 },\n\t/*::[*/0x0139/*::]*/: { /* n:\"BrtEndSXLocation\", */ T:-1 },\n\t/*::[*/0x013A/*::]*/: { /* n:\"BrtBeginSXLocation\", */ T:1 },\n\t/*::[*/0x013B/*::]*/: { /* n:\"BrtEndSXView\", */ T:-1 },\n\t/*::[*/0x013C/*::]*/: { /* n:\"BrtBeginSXTHs\", */ T:1 },\n\t/*::[*/0x013D/*::]*/: { /* n:\"BrtEndSXTHs\", */ T:-1 },\n\t/*::[*/0x013E/*::]*/: { /* n:\"BrtBeginSXTH\", */ T:1 },\n\t/*::[*/0x013F/*::]*/: { /* n:\"BrtEndSXTH\", */ T:-1 },\n\t/*::[*/0x0140/*::]*/: { /* n:\"BrtBeginISXTHRws\", */ T:1 },\n\t/*::[*/0x0141/*::]*/: { /* n:\"BrtEndISXTHRws\", */ T:-1 },\n\t/*::[*/0x0142/*::]*/: { /* n:\"BrtBeginISXTHCols\", */ T:1 },\n\t/*::[*/0x0143/*::]*/: { /* n:\"BrtEndISXTHCols\", */ T:-1 },\n\t/*::[*/0x0144/*::]*/: { /* n:\"BrtBeginSXTDMPS\", */ T:1 },\n\t/*::[*/0x0145/*::]*/: { /* n:\"BrtEndSXTDMPs\", */ T:-1 },\n\t/*::[*/0x0146/*::]*/: { /* n:\"BrtBeginSXTDMP\", */ T:1 },\n\t/*::[*/0x0147/*::]*/: { /* n:\"BrtEndSXTDMP\", */ T:-1 },\n\t/*::[*/0x0148/*::]*/: { /* n:\"BrtBeginSXTHItems\", */ T:1 },\n\t/*::[*/0x0149/*::]*/: { /* n:\"BrtEndSXTHItems\", */ T:-1 },\n\t/*::[*/0x014A/*::]*/: { /* n:\"BrtBeginSXTHItem\", */ T:1 },\n\t/*::[*/0x014B/*::]*/: { /* n:\"BrtEndSXTHItem\", */ T:-1 },\n\t/*::[*/0x014C/*::]*/: { /* n:\"BrtBeginMetadata\", */ T:1 },\n\t/*::[*/0x014D/*::]*/: { /* n:\"BrtEndMetadata\", */ T:-1 },\n\t/*::[*/0x014E/*::]*/: { /* n:\"BrtBeginEsmdtinfo\", */ T:1 },\n\t/*::[*/0x014F/*::]*/: { /* n:\"BrtMdtinfo\", */ f:parse_BrtMdtinfo },\n\t/*::[*/0x0150/*::]*/: { /* n:\"BrtEndEsmdtinfo\", */ T:-1 },\n\t/*::[*/0x0151/*::]*/: { /* n:\"BrtBeginEsmdb\", */ f:parse_BrtBeginEsmdb, T:1 },\n\t/*::[*/0x0152/*::]*/: { /* n:\"BrtEndEsmdb\", */ T:-1 },\n\t/*::[*/0x0153/*::]*/: { /* n:\"BrtBeginEsfmd\", */ T:1 },\n\t/*::[*/0x0154/*::]*/: { /* n:\"BrtEndEsfmd\", */ T:-1 },\n\t/*::[*/0x0155/*::]*/: { /* n:\"BrtBeginSingleCells\", */ T:1 },\n\t/*::[*/0x0156/*::]*/: { /* n:\"BrtEndSingleCells\", */ T:-1 },\n\t/*::[*/0x0157/*::]*/: { /* n:\"BrtBeginList\", */ T:1 },\n\t/*::[*/0x0158/*::]*/: { /* n:\"BrtEndList\", */ T:-1 },\n\t/*::[*/0x0159/*::]*/: { /* n:\"BrtBeginListCols\", */ T:1 },\n\t/*::[*/0x015A/*::]*/: { /* n:\"BrtEndListCols\", */ T:-1 },\n\t/*::[*/0x015B/*::]*/: { /* n:\"BrtBeginListCol\", */ T:1 },\n\t/*::[*/0x015C/*::]*/: { /* n:\"BrtEndListCol\", */ T:-1 },\n\t/*::[*/0x015D/*::]*/: { /* n:\"BrtBeginListXmlCPr\", */ T:1 },\n\t/*::[*/0x015E/*::]*/: { /* n:\"BrtEndListXmlCPr\", */ T:-1 },\n\t/*::[*/0x015F/*::]*/: { /* n:\"BrtListCCFmla\" */ },\n\t/*::[*/0x0160/*::]*/: { /* n:\"BrtListTrFmla\" */ },\n\t/*::[*/0x0161/*::]*/: { /* n:\"BrtBeginExternals\", */ T:1 },\n\t/*::[*/0x0162/*::]*/: { /* n:\"BrtEndExternals\", */ T:-1 },\n\t/*::[*/0x0163/*::]*/: { /* n:\"BrtSupBookSrc\", */ f:parse_RelID},\n\t/*::[*/0x0165/*::]*/: { /* n:\"BrtSupSelf\" */ },\n\t/*::[*/0x0166/*::]*/: { /* n:\"BrtSupSame\" */ },\n\t/*::[*/0x0167/*::]*/: { /* n:\"BrtSupTabs\" */ },\n\t/*::[*/0x0168/*::]*/: { /* n:\"BrtBeginSupBook\", */ T:1 },\n\t/*::[*/0x0169/*::]*/: { /* n:\"BrtPlaceholderName\" */ },\n\t/*::[*/0x016A/*::]*/: { /* n:\"BrtExternSheet\", */ f:parse_ExternSheet },\n\t/*::[*/0x016B/*::]*/: { /* n:\"BrtExternTableStart\" */ },\n\t/*::[*/0x016C/*::]*/: { /* n:\"BrtExternTableEnd\" */ },\n\t/*::[*/0x016E/*::]*/: { /* n:\"BrtExternRowHdr\" */ },\n\t/*::[*/0x016F/*::]*/: { /* n:\"BrtExternCellBlank\" */ },\n\t/*::[*/0x0170/*::]*/: { /* n:\"BrtExternCellReal\" */ },\n\t/*::[*/0x0171/*::]*/: { /* n:\"BrtExternCellBool\" */ },\n\t/*::[*/0x0172/*::]*/: { /* n:\"BrtExternCellError\" */ },\n\t/*::[*/0x0173/*::]*/: { /* n:\"BrtExternCellString\" */ },\n\t/*::[*/0x0174/*::]*/: { /* n:\"BrtBeginEsmdx\", */ T:1 },\n\t/*::[*/0x0175/*::]*/: { /* n:\"BrtEndEsmdx\", */ T:-1 },\n\t/*::[*/0x0176/*::]*/: { /* n:\"BrtBeginMdxSet\", */ T:1 },\n\t/*::[*/0x0177/*::]*/: { /* n:\"BrtEndMdxSet\", */ T:-1 },\n\t/*::[*/0x0178/*::]*/: { /* n:\"BrtBeginMdxMbrProp\", */ T:1 },\n\t/*::[*/0x0179/*::]*/: { /* n:\"BrtEndMdxMbrProp\", */ T:-1 },\n\t/*::[*/0x017A/*::]*/: { /* n:\"BrtBeginMdxKPI\", */ T:1 },\n\t/*::[*/0x017B/*::]*/: { /* n:\"BrtEndMdxKPI\", */ T:-1 },\n\t/*::[*/0x017C/*::]*/: { /* n:\"BrtBeginEsstr\", */ T:1 },\n\t/*::[*/0x017D/*::]*/: { /* n:\"BrtEndEsstr\", */ T:-1 },\n\t/*::[*/0x017E/*::]*/: { /* n:\"BrtBeginPRFItem\", */ T:1 },\n\t/*::[*/0x017F/*::]*/: { /* n:\"BrtEndPRFItem\", */ T:-1 },\n\t/*::[*/0x0180/*::]*/: { /* n:\"BrtBeginPivotCacheIDs\", */ T:1 },\n\t/*::[*/0x0181/*::]*/: { /* n:\"BrtEndPivotCacheIDs\", */ T:-1 },\n\t/*::[*/0x0182/*::]*/: { /* n:\"BrtBeginPivotCacheID\", */ T:1 },\n\t/*::[*/0x0183/*::]*/: { /* n:\"BrtEndPivotCacheID\", */ T:-1 },\n\t/*::[*/0x0184/*::]*/: { /* n:\"BrtBeginISXVIs\", */ T:1 },\n\t/*::[*/0x0185/*::]*/: { /* n:\"BrtEndISXVIs\", */ T:-1 },\n\t/*::[*/0x0186/*::]*/: { /* n:\"BrtBeginColInfos\", */ T:1 },\n\t/*::[*/0x0187/*::]*/: { /* n:\"BrtEndColInfos\", */ T:-1 },\n\t/*::[*/0x0188/*::]*/: { /* n:\"BrtBeginRwBrk\", */ T:1 },\n\t/*::[*/0x0189/*::]*/: { /* n:\"BrtEndRwBrk\", */ T:-1 },\n\t/*::[*/0x018A/*::]*/: { /* n:\"BrtBeginColBrk\", */ T:1 },\n\t/*::[*/0x018B/*::]*/: { /* n:\"BrtEndColBrk\", */ T:-1 },\n\t/*::[*/0x018C/*::]*/: { /* n:\"BrtBrk\" */ },\n\t/*::[*/0x018D/*::]*/: { /* n:\"BrtUserBookView\" */ },\n\t/*::[*/0x018E/*::]*/: { /* n:\"BrtInfo\" */ },\n\t/*::[*/0x018F/*::]*/: { /* n:\"BrtCUsr\" */ },\n\t/*::[*/0x0190/*::]*/: { /* n:\"BrtUsr\" */ },\n\t/*::[*/0x0191/*::]*/: { /* n:\"BrtBeginUsers\", */ T:1 },\n\t/*::[*/0x0193/*::]*/: { /* n:\"BrtEOF\" */ },\n\t/*::[*/0x0194/*::]*/: { /* n:\"BrtUCR\" */ },\n\t/*::[*/0x0195/*::]*/: { /* n:\"BrtRRInsDel\" */ },\n\t/*::[*/0x0196/*::]*/: { /* n:\"BrtRREndInsDel\" */ },\n\t/*::[*/0x0197/*::]*/: { /* n:\"BrtRRMove\" */ },\n\t/*::[*/0x0198/*::]*/: { /* n:\"BrtRREndMove\" */ },\n\t/*::[*/0x0199/*::]*/: { /* n:\"BrtRRChgCell\" */ },\n\t/*::[*/0x019A/*::]*/: { /* n:\"BrtRREndChgCell\" */ },\n\t/*::[*/0x019B/*::]*/: { /* n:\"BrtRRHeader\" */ },\n\t/*::[*/0x019C/*::]*/: { /* n:\"BrtRRUserView\" */ },\n\t/*::[*/0x019D/*::]*/: { /* n:\"BrtRRRenSheet\" */ },\n\t/*::[*/0x019E/*::]*/: { /* n:\"BrtRRInsertSh\" */ },\n\t/*::[*/0x019F/*::]*/: { /* n:\"BrtRRDefName\" */ },\n\t/*::[*/0x01A0/*::]*/: { /* n:\"BrtRRNote\" */ },\n\t/*::[*/0x01A1/*::]*/: { /* n:\"BrtRRConflict\" */ },\n\t/*::[*/0x01A2/*::]*/: { /* n:\"BrtRRTQSIF\" */ },\n\t/*::[*/0x01A3/*::]*/: { /* n:\"BrtRRFormat\" */ },\n\t/*::[*/0x01A4/*::]*/: { /* n:\"BrtRREndFormat\" */ },\n\t/*::[*/0x01A5/*::]*/: { /* n:\"BrtRRAutoFmt\" */ },\n\t/*::[*/0x01A6/*::]*/: { /* n:\"BrtBeginUserShViews\", */ T:1 },\n\t/*::[*/0x01A7/*::]*/: { /* n:\"BrtBeginUserShView\", */ T:1 },\n\t/*::[*/0x01A8/*::]*/: { /* n:\"BrtEndUserShView\", */ T:-1 },\n\t/*::[*/0x01A9/*::]*/: { /* n:\"BrtEndUserShViews\", */ T:-1 },\n\t/*::[*/0x01AA/*::]*/: { /* n:\"BrtArrFmla\", */ f:parse_BrtArrFmla },\n\t/*::[*/0x01AB/*::]*/: { /* n:\"BrtShrFmla\", */ f:parse_BrtShrFmla },\n\t/*::[*/0x01AC/*::]*/: { /* n:\"BrtTable\" */ },\n\t/*::[*/0x01AD/*::]*/: { /* n:\"BrtBeginExtConnections\", */ T:1 },\n\t/*::[*/0x01AE/*::]*/: { /* n:\"BrtEndExtConnections\", */ T:-1 },\n\t/*::[*/0x01AF/*::]*/: { /* n:\"BrtBeginPCDCalcMems\", */ T:1 },\n\t/*::[*/0x01B0/*::]*/: { /* n:\"BrtEndPCDCalcMems\", */ T:-1 },\n\t/*::[*/0x01B1/*::]*/: { /* n:\"BrtBeginPCDCalcMem\", */ T:1 },\n\t/*::[*/0x01B2/*::]*/: { /* n:\"BrtEndPCDCalcMem\", */ T:-1 },\n\t/*::[*/0x01B3/*::]*/: { /* n:\"BrtBeginPCDHGLevels\", */ T:1 },\n\t/*::[*/0x01B4/*::]*/: { /* n:\"BrtEndPCDHGLevels\", */ T:-1 },\n\t/*::[*/0x01B5/*::]*/: { /* n:\"BrtBeginPCDHGLevel\", */ T:1 },\n\t/*::[*/0x01B6/*::]*/: { /* n:\"BrtEndPCDHGLevel\", */ T:-1 },\n\t/*::[*/0x01B7/*::]*/: { /* n:\"BrtBeginPCDHGLGroups\", */ T:1 },\n\t/*::[*/0x01B8/*::]*/: { /* n:\"BrtEndPCDHGLGroups\", */ T:-1 },\n\t/*::[*/0x01B9/*::]*/: { /* n:\"BrtBeginPCDHGLGroup\", */ T:1 },\n\t/*::[*/0x01BA/*::]*/: { /* n:\"BrtEndPCDHGLGroup\", */ T:-1 },\n\t/*::[*/0x01BB/*::]*/: { /* n:\"BrtBeginPCDHGLGMembers\", */ T:1 },\n\t/*::[*/0x01BC/*::]*/: { /* n:\"BrtEndPCDHGLGMembers\", */ T:-1 },\n\t/*::[*/0x01BD/*::]*/: { /* n:\"BrtBeginPCDHGLGMember\", */ T:1 },\n\t/*::[*/0x01BE/*::]*/: { /* n:\"BrtEndPCDHGLGMember\", */ T:-1 },\n\t/*::[*/0x01BF/*::]*/: { /* n:\"BrtBeginQSI\", */ T:1 },\n\t/*::[*/0x01C0/*::]*/: { /* n:\"BrtEndQSI\", */ T:-1 },\n\t/*::[*/0x01C1/*::]*/: { /* n:\"BrtBeginQSIR\", */ T:1 },\n\t/*::[*/0x01C2/*::]*/: { /* n:\"BrtEndQSIR\", */ T:-1 },\n\t/*::[*/0x01C3/*::]*/: { /* n:\"BrtBeginDeletedNames\", */ T:1 },\n\t/*::[*/0x01C4/*::]*/: { /* n:\"BrtEndDeletedNames\", */ T:-1 },\n\t/*::[*/0x01C5/*::]*/: { /* n:\"BrtBeginDeletedName\", */ T:1 },\n\t/*::[*/0x01C6/*::]*/: { /* n:\"BrtEndDeletedName\", */ T:-1 },\n\t/*::[*/0x01C7/*::]*/: { /* n:\"BrtBeginQSIFs\", */ T:1 },\n\t/*::[*/0x01C8/*::]*/: { /* n:\"BrtEndQSIFs\", */ T:-1 },\n\t/*::[*/0x01C9/*::]*/: { /* n:\"BrtBeginQSIF\", */ T:1 },\n\t/*::[*/0x01CA/*::]*/: { /* n:\"BrtEndQSIF\", */ T:-1 },\n\t/*::[*/0x01CB/*::]*/: { /* n:\"BrtBeginAutoSortScope\", */ T:1 },\n\t/*::[*/0x01CC/*::]*/: { /* n:\"BrtEndAutoSortScope\", */ T:-1 },\n\t/*::[*/0x01CD/*::]*/: { /* n:\"BrtBeginConditionalFormatting\", */ T:1 },\n\t/*::[*/0x01CE/*::]*/: { /* n:\"BrtEndConditionalFormatting\", */ T:-1 },\n\t/*::[*/0x01CF/*::]*/: { /* n:\"BrtBeginCFRule\", */ T:1 },\n\t/*::[*/0x01D0/*::]*/: { /* n:\"BrtEndCFRule\", */ T:-1 },\n\t/*::[*/0x01D1/*::]*/: { /* n:\"BrtBeginIconSet\", */ T:1 },\n\t/*::[*/0x01D2/*::]*/: { /* n:\"BrtEndIconSet\", */ T:-1 },\n\t/*::[*/0x01D3/*::]*/: { /* n:\"BrtBeginDatabar\", */ T:1 },\n\t/*::[*/0x01D4/*::]*/: { /* n:\"BrtEndDatabar\", */ T:-1 },\n\t/*::[*/0x01D5/*::]*/: { /* n:\"BrtBeginColorScale\", */ T:1 },\n\t/*::[*/0x01D6/*::]*/: { /* n:\"BrtEndColorScale\", */ T:-1 },\n\t/*::[*/0x01D7/*::]*/: { /* n:\"BrtCFVO\" */ },\n\t/*::[*/0x01D8/*::]*/: { /* n:\"BrtExternValueMeta\" */ },\n\t/*::[*/0x01D9/*::]*/: { /* n:\"BrtBeginColorPalette\", */ T:1 },\n\t/*::[*/0x01DA/*::]*/: { /* n:\"BrtEndColorPalette\", */ T:-1 },\n\t/*::[*/0x01DB/*::]*/: { /* n:\"BrtIndexedColor\" */ },\n\t/*::[*/0x01DC/*::]*/: { /* n:\"BrtMargins\", */ f:parse_BrtMargins },\n\t/*::[*/0x01DD/*::]*/: { /* n:\"BrtPrintOptions\" */ },\n\t/*::[*/0x01DE/*::]*/: { /* n:\"BrtPageSetup\" */ },\n\t/*::[*/0x01DF/*::]*/: { /* n:\"BrtBeginHeaderFooter\", */ T:1 },\n\t/*::[*/0x01E0/*::]*/: { /* n:\"BrtEndHeaderFooter\", */ T:-1 },\n\t/*::[*/0x01E1/*::]*/: { /* n:\"BrtBeginSXCrtFormat\", */ T:1 },\n\t/*::[*/0x01E2/*::]*/: { /* n:\"BrtEndSXCrtFormat\", */ T:-1 },\n\t/*::[*/0x01E3/*::]*/: { /* n:\"BrtBeginSXCrtFormats\", */ T:1 },\n\t/*::[*/0x01E4/*::]*/: { /* n:\"BrtEndSXCrtFormats\", */ T:-1 },\n\t/*::[*/0x01E5/*::]*/: { /* n:\"BrtWsFmtInfo\", */ f:parse_BrtWsFmtInfo },\n\t/*::[*/0x01E6/*::]*/: { /* n:\"BrtBeginMgs\", */ T:1 },\n\t/*::[*/0x01E7/*::]*/: { /* n:\"BrtEndMGs\", */ T:-1 },\n\t/*::[*/0x01E8/*::]*/: { /* n:\"BrtBeginMGMaps\", */ T:1 },\n\t/*::[*/0x01E9/*::]*/: { /* n:\"BrtEndMGMaps\", */ T:-1 },\n\t/*::[*/0x01EA/*::]*/: { /* n:\"BrtBeginMG\", */ T:1 },\n\t/*::[*/0x01EB/*::]*/: { /* n:\"BrtEndMG\", */ T:-1 },\n\t/*::[*/0x01EC/*::]*/: { /* n:\"BrtBeginMap\", */ T:1 },\n\t/*::[*/0x01ED/*::]*/: { /* n:\"BrtEndMap\", */ T:-1 },\n\t/*::[*/0x01EE/*::]*/: { /* n:\"BrtHLink\", */ f:parse_BrtHLink },\n\t/*::[*/0x01EF/*::]*/: { /* n:\"BrtBeginDCon\", */ T:1 },\n\t/*::[*/0x01F0/*::]*/: { /* n:\"BrtEndDCon\", */ T:-1 },\n\t/*::[*/0x01F1/*::]*/: { /* n:\"BrtBeginDRefs\", */ T:1 },\n\t/*::[*/0x01F2/*::]*/: { /* n:\"BrtEndDRefs\", */ T:-1 },\n\t/*::[*/0x01F3/*::]*/: { /* n:\"BrtDRef\" */ },\n\t/*::[*/0x01F4/*::]*/: { /* n:\"BrtBeginScenMan\", */ T:1 },\n\t/*::[*/0x01F5/*::]*/: { /* n:\"BrtEndScenMan\", */ T:-1 },\n\t/*::[*/0x01F6/*::]*/: { /* n:\"BrtBeginSct\", */ T:1 },\n\t/*::[*/0x01F7/*::]*/: { /* n:\"BrtEndSct\", */ T:-1 },\n\t/*::[*/0x01F8/*::]*/: { /* n:\"BrtSlc\" */ },\n\t/*::[*/0x01F9/*::]*/: { /* n:\"BrtBeginDXFs\", */ T:1 },\n\t/*::[*/0x01FA/*::]*/: { /* n:\"BrtEndDXFs\", */ T:-1 },\n\t/*::[*/0x01FB/*::]*/: { /* n:\"BrtDXF\" */ },\n\t/*::[*/0x01FC/*::]*/: { /* n:\"BrtBeginTableStyles\", */ T:1 },\n\t/*::[*/0x01FD/*::]*/: { /* n:\"BrtEndTableStyles\", */ T:-1 },\n\t/*::[*/0x01FE/*::]*/: { /* n:\"BrtBeginTableStyle\", */ T:1 },\n\t/*::[*/0x01FF/*::]*/: { /* n:\"BrtEndTableStyle\", */ T:-1 },\n\t/*::[*/0x0200/*::]*/: { /* n:\"BrtTableStyleElement\" */ },\n\t/*::[*/0x0201/*::]*/: { /* n:\"BrtTableStyleClient\" */ },\n\t/*::[*/0x0202/*::]*/: { /* n:\"BrtBeginVolDeps\", */ T:1 },\n\t/*::[*/0x0203/*::]*/: { /* n:\"BrtEndVolDeps\", */ T:-1 },\n\t/*::[*/0x0204/*::]*/: { /* n:\"BrtBeginVolType\", */ T:1 },\n\t/*::[*/0x0205/*::]*/: { /* n:\"BrtEndVolType\", */ T:-1 },\n\t/*::[*/0x0206/*::]*/: { /* n:\"BrtBeginVolMain\", */ T:1 },\n\t/*::[*/0x0207/*::]*/: { /* n:\"BrtEndVolMain\", */ T:-1 },\n\t/*::[*/0x0208/*::]*/: { /* n:\"BrtBeginVolTopic\", */ T:1 },\n\t/*::[*/0x0209/*::]*/: { /* n:\"BrtEndVolTopic\", */ T:-1 },\n\t/*::[*/0x020A/*::]*/: { /* n:\"BrtVolSubtopic\" */ },\n\t/*::[*/0x020B/*::]*/: { /* n:\"BrtVolRef\" */ },\n\t/*::[*/0x020C/*::]*/: { /* n:\"BrtVolNum\" */ },\n\t/*::[*/0x020D/*::]*/: { /* n:\"BrtVolErr\" */ },\n\t/*::[*/0x020E/*::]*/: { /* n:\"BrtVolStr\" */ },\n\t/*::[*/0x020F/*::]*/: { /* n:\"BrtVolBool\" */ },\n\t/*::[*/0x0210/*::]*/: { /* n:\"BrtBeginCalcChain$\", */ T:1 },\n\t/*::[*/0x0211/*::]*/: { /* n:\"BrtEndCalcChain$\", */ T:-1 },\n\t/*::[*/0x0212/*::]*/: { /* n:\"BrtBeginSortState\", */ T:1 },\n\t/*::[*/0x0213/*::]*/: { /* n:\"BrtEndSortState\", */ T:-1 },\n\t/*::[*/0x0214/*::]*/: { /* n:\"BrtBeginSortCond\", */ T:1 },\n\t/*::[*/0x0215/*::]*/: { /* n:\"BrtEndSortCond\", */ T:-1 },\n\t/*::[*/0x0216/*::]*/: { /* n:\"BrtBookProtection\" */ },\n\t/*::[*/0x0217/*::]*/: { /* n:\"BrtSheetProtection\" */ },\n\t/*::[*/0x0218/*::]*/: { /* n:\"BrtRangeProtection\" */ },\n\t/*::[*/0x0219/*::]*/: { /* n:\"BrtPhoneticInfo\" */ },\n\t/*::[*/0x021A/*::]*/: { /* n:\"BrtBeginECTxtWiz\", */ T:1 },\n\t/*::[*/0x021B/*::]*/: { /* n:\"BrtEndECTxtWiz\", */ T:-1 },\n\t/*::[*/0x021C/*::]*/: { /* n:\"BrtBeginECTWFldInfoLst\", */ T:1 },\n\t/*::[*/0x021D/*::]*/: { /* n:\"BrtEndECTWFldInfoLst\", */ T:-1 },\n\t/*::[*/0x021E/*::]*/: { /* n:\"BrtBeginECTwFldInfo\", */ T:1 },\n\t/*::[*/0x0224/*::]*/: { /* n:\"BrtFileSharing\" */ },\n\t/*::[*/0x0225/*::]*/: { /* n:\"BrtOleSize\" */ },\n\t/*::[*/0x0226/*::]*/: { /* n:\"BrtDrawing\", */ f:parse_RelID },\n\t/*::[*/0x0227/*::]*/: { /* n:\"BrtLegacyDrawing\" */ },\n\t/*::[*/0x0228/*::]*/: { /* n:\"BrtLegacyDrawingHF\" */ },\n\t/*::[*/0x0229/*::]*/: { /* n:\"BrtWebOpt\" */ },\n\t/*::[*/0x022A/*::]*/: { /* n:\"BrtBeginWebPubItems\", */ T:1 },\n\t/*::[*/0x022B/*::]*/: { /* n:\"BrtEndWebPubItems\", */ T:-1 },\n\t/*::[*/0x022C/*::]*/: { /* n:\"BrtBeginWebPubItem\", */ T:1 },\n\t/*::[*/0x022D/*::]*/: { /* n:\"BrtEndWebPubItem\", */ T:-1 },\n\t/*::[*/0x022E/*::]*/: { /* n:\"BrtBeginSXCondFmt\", */ T:1 },\n\t/*::[*/0x022F/*::]*/: { /* n:\"BrtEndSXCondFmt\", */ T:-1 },\n\t/*::[*/0x0230/*::]*/: { /* n:\"BrtBeginSXCondFmts\", */ T:1 },\n\t/*::[*/0x0231/*::]*/: { /* n:\"BrtEndSXCondFmts\", */ T:-1 },\n\t/*::[*/0x0232/*::]*/: { /* n:\"BrtBkHim\" */ },\n\t/*::[*/0x0234/*::]*/: { /* n:\"BrtColor\" */ },\n\t/*::[*/0x0235/*::]*/: { /* n:\"BrtBeginIndexedColors\", */ T:1 },\n\t/*::[*/0x0236/*::]*/: { /* n:\"BrtEndIndexedColors\", */ T:-1 },\n\t/*::[*/0x0239/*::]*/: { /* n:\"BrtBeginMRUColors\", */ T:1 },\n\t/*::[*/0x023A/*::]*/: { /* n:\"BrtEndMRUColors\", */ T:-1 },\n\t/*::[*/0x023C/*::]*/: { /* n:\"BrtMRUColor\" */ },\n\t/*::[*/0x023D/*::]*/: { /* n:\"BrtBeginDVals\", */ T:1 },\n\t/*::[*/0x023E/*::]*/: { /* n:\"BrtEndDVals\", */ T:-1 },\n\t/*::[*/0x0241/*::]*/: { /* n:\"BrtSupNameStart\" */ },\n\t/*::[*/0x0242/*::]*/: { /* n:\"BrtSupNameValueStart\" */ },\n\t/*::[*/0x0243/*::]*/: { /* n:\"BrtSupNameValueEnd\" */ },\n\t/*::[*/0x0244/*::]*/: { /* n:\"BrtSupNameNum\" */ },\n\t/*::[*/0x0245/*::]*/: { /* n:\"BrtSupNameErr\" */ },\n\t/*::[*/0x0246/*::]*/: { /* n:\"BrtSupNameSt\" */ },\n\t/*::[*/0x0247/*::]*/: { /* n:\"BrtSupNameNil\" */ },\n\t/*::[*/0x0248/*::]*/: { /* n:\"BrtSupNameBool\" */ },\n\t/*::[*/0x0249/*::]*/: { /* n:\"BrtSupNameFmla\" */ },\n\t/*::[*/0x024A/*::]*/: { /* n:\"BrtSupNameBits\" */ },\n\t/*::[*/0x024B/*::]*/: { /* n:\"BrtSupNameEnd\" */ },\n\t/*::[*/0x024C/*::]*/: { /* n:\"BrtEndSupBook\", */ T:-1 },\n\t/*::[*/0x024D/*::]*/: { /* n:\"BrtCellSmartTagProperty\" */ },\n\t/*::[*/0x024E/*::]*/: { /* n:\"BrtBeginCellSmartTag\", */ T:1 },\n\t/*::[*/0x024F/*::]*/: { /* n:\"BrtEndCellSmartTag\", */ T:-1 },\n\t/*::[*/0x0250/*::]*/: { /* n:\"BrtBeginCellSmartTags\", */ T:1 },\n\t/*::[*/0x0251/*::]*/: { /* n:\"BrtEndCellSmartTags\", */ T:-1 },\n\t/*::[*/0x0252/*::]*/: { /* n:\"BrtBeginSmartTags\", */ T:1 },\n\t/*::[*/0x0253/*::]*/: { /* n:\"BrtEndSmartTags\", */ T:-1 },\n\t/*::[*/0x0254/*::]*/: { /* n:\"BrtSmartTagType\" */ },\n\t/*::[*/0x0255/*::]*/: { /* n:\"BrtBeginSmartTagTypes\", */ T:1 },\n\t/*::[*/0x0256/*::]*/: { /* n:\"BrtEndSmartTagTypes\", */ T:-1 },\n\t/*::[*/0x0257/*::]*/: { /* n:\"BrtBeginSXFilters\", */ T:1 },\n\t/*::[*/0x0258/*::]*/: { /* n:\"BrtEndSXFilters\", */ T:-1 },\n\t/*::[*/0x0259/*::]*/: { /* n:\"BrtBeginSXFILTER\", */ T:1 },\n\t/*::[*/0x025A/*::]*/: { /* n:\"BrtEndSXFilter\", */ T:-1 },\n\t/*::[*/0x025B/*::]*/: { /* n:\"BrtBeginFills\", */ T:1 },\n\t/*::[*/0x025C/*::]*/: { /* n:\"BrtEndFills\", */ T:-1 },\n\t/*::[*/0x025D/*::]*/: { /* n:\"BrtBeginCellWatches\", */ T:1 },\n\t/*::[*/0x025E/*::]*/: { /* n:\"BrtEndCellWatches\", */ T:-1 },\n\t/*::[*/0x025F/*::]*/: { /* n:\"BrtCellWatch\" */ },\n\t/*::[*/0x0260/*::]*/: { /* n:\"BrtBeginCRErrs\", */ T:1 },\n\t/*::[*/0x0261/*::]*/: { /* n:\"BrtEndCRErrs\", */ T:-1 },\n\t/*::[*/0x0262/*::]*/: { /* n:\"BrtCrashRecErr\" */ },\n\t/*::[*/0x0263/*::]*/: { /* n:\"BrtBeginFonts\", */ T:1 },\n\t/*::[*/0x0264/*::]*/: { /* n:\"BrtEndFonts\", */ T:-1 },\n\t/*::[*/0x0265/*::]*/: { /* n:\"BrtBeginBorders\", */ T:1 },\n\t/*::[*/0x0266/*::]*/: { /* n:\"BrtEndBorders\", */ T:-1 },\n\t/*::[*/0x0267/*::]*/: { /* n:\"BrtBeginFmts\", */ T:1 },\n\t/*::[*/0x0268/*::]*/: { /* n:\"BrtEndFmts\", */ T:-1 },\n\t/*::[*/0x0269/*::]*/: { /* n:\"BrtBeginCellXFs\", */ T:1 },\n\t/*::[*/0x026A/*::]*/: { /* n:\"BrtEndCellXFs\", */ T:-1 },\n\t/*::[*/0x026B/*::]*/: { /* n:\"BrtBeginStyles\", */ T:1 },\n\t/*::[*/0x026C/*::]*/: { /* n:\"BrtEndStyles\", */ T:-1 },\n\t/*::[*/0x0271/*::]*/: { /* n:\"BrtBigName\" */ },\n\t/*::[*/0x0272/*::]*/: { /* n:\"BrtBeginCellStyleXFs\", */ T:1 },\n\t/*::[*/0x0273/*::]*/: { /* n:\"BrtEndCellStyleXFs\", */ T:-1 },\n\t/*::[*/0x0274/*::]*/: { /* n:\"BrtBeginComments\", */ T:1 },\n\t/*::[*/0x0275/*::]*/: { /* n:\"BrtEndComments\", */ T:-1 },\n\t/*::[*/0x0276/*::]*/: { /* n:\"BrtBeginCommentAuthors\", */ T:1 },\n\t/*::[*/0x0277/*::]*/: { /* n:\"BrtEndCommentAuthors\", */ T:-1 },\n\t/*::[*/0x0278/*::]*/: { /* n:\"BrtCommentAuthor\", */ f:parse_BrtCommentAuthor },\n\t/*::[*/0x0279/*::]*/: { /* n:\"BrtBeginCommentList\", */ T:1 },\n\t/*::[*/0x027A/*::]*/: { /* n:\"BrtEndCommentList\", */ T:-1 },\n\t/*::[*/0x027B/*::]*/: { /* n:\"BrtBeginComment\", */ T:1, f:parse_BrtBeginComment},\n\t/*::[*/0x027C/*::]*/: { /* n:\"BrtEndComment\", */ T:-1 },\n\t/*::[*/0x027D/*::]*/: { /* n:\"BrtCommentText\", */ f:parse_BrtCommentText },\n\t/*::[*/0x027E/*::]*/: { /* n:\"BrtBeginOleObjects\", */ T:1 },\n\t/*::[*/0x027F/*::]*/: { /* n:\"BrtOleObject\" */ },\n\t/*::[*/0x0280/*::]*/: { /* n:\"BrtEndOleObjects\", */ T:-1 },\n\t/*::[*/0x0281/*::]*/: { /* n:\"BrtBeginSxrules\", */ T:1 },\n\t/*::[*/0x0282/*::]*/: { /* n:\"BrtEndSxRules\", */ T:-1 },\n\t/*::[*/0x0283/*::]*/: { /* n:\"BrtBeginActiveXControls\", */ T:1 },\n\t/*::[*/0x0284/*::]*/: { /* n:\"BrtActiveX\" */ },\n\t/*::[*/0x0285/*::]*/: { /* n:\"BrtEndActiveXControls\", */ T:-1 },\n\t/*::[*/0x0286/*::]*/: { /* n:\"BrtBeginPCDSDTCEMembersSortBy\", */ T:1 },\n\t/*::[*/0x0288/*::]*/: { /* n:\"BrtBeginCellIgnoreECs\", */ T:1 },\n\t/*::[*/0x0289/*::]*/: { /* n:\"BrtCellIgnoreEC\" */ },\n\t/*::[*/0x028A/*::]*/: { /* n:\"BrtEndCellIgnoreECs\", */ T:-1 },\n\t/*::[*/0x028B/*::]*/: { /* n:\"BrtCsProp\", */ f:parse_BrtCsProp },\n\t/*::[*/0x028C/*::]*/: { /* n:\"BrtCsPageSetup\" */ },\n\t/*::[*/0x028D/*::]*/: { /* n:\"BrtBeginUserCsViews\", */ T:1 },\n\t/*::[*/0x028E/*::]*/: { /* n:\"BrtEndUserCsViews\", */ T:-1 },\n\t/*::[*/0x028F/*::]*/: { /* n:\"BrtBeginUserCsView\", */ T:1 },\n\t/*::[*/0x0290/*::]*/: { /* n:\"BrtEndUserCsView\", */ T:-1 },\n\t/*::[*/0x0291/*::]*/: { /* n:\"BrtBeginPcdSFCIEntries\", */ T:1 },\n\t/*::[*/0x0292/*::]*/: { /* n:\"BrtEndPCDSFCIEntries\", */ T:-1 },\n\t/*::[*/0x0293/*::]*/: { /* n:\"BrtPCDSFCIEntry\" */ },\n\t/*::[*/0x0294/*::]*/: { /* n:\"BrtBeginListParts\", */ T:1 },\n\t/*::[*/0x0295/*::]*/: { /* n:\"BrtListPart\" */ },\n\t/*::[*/0x0296/*::]*/: { /* n:\"BrtEndListParts\", */ T:-1 },\n\t/*::[*/0x0297/*::]*/: { /* n:\"BrtSheetCalcProp\" */ },\n\t/*::[*/0x0298/*::]*/: { /* n:\"BrtBeginFnGroup\", */ T:1 },\n\t/*::[*/0x0299/*::]*/: { /* n:\"BrtFnGroup\" */ },\n\t/*::[*/0x029A/*::]*/: { /* n:\"BrtEndFnGroup\", */ T:-1 },\n\t/*::[*/0x029B/*::]*/: { /* n:\"BrtSupAddin\" */ },\n\t/*::[*/0x029C/*::]*/: { /* n:\"BrtSXTDMPOrder\" */ },\n\t/*::[*/0x029D/*::]*/: { /* n:\"BrtCsProtection\" */ },\n\t/*::[*/0x029F/*::]*/: { /* n:\"BrtBeginWsSortMap\", */ T:1 },\n\t/*::[*/0x02A0/*::]*/: { /* n:\"BrtEndWsSortMap\", */ T:-1 },\n\t/*::[*/0x02A1/*::]*/: { /* n:\"BrtBeginRRSort\", */ T:1 },\n\t/*::[*/0x02A2/*::]*/: { /* n:\"BrtEndRRSort\", */ T:-1 },\n\t/*::[*/0x02A3/*::]*/: { /* n:\"BrtRRSortItem\" */ },\n\t/*::[*/0x02A4/*::]*/: { /* n:\"BrtFileSharingIso\" */ },\n\t/*::[*/0x02A5/*::]*/: { /* n:\"BrtBookProtectionIso\" */ },\n\t/*::[*/0x02A6/*::]*/: { /* n:\"BrtSheetProtectionIso\" */ },\n\t/*::[*/0x02A7/*::]*/: { /* n:\"BrtCsProtectionIso\" */ },\n\t/*::[*/0x02A8/*::]*/: { /* n:\"BrtRangeProtectionIso\" */ },\n\t/*::[*/0x02A9/*::]*/: { /* n:\"BrtDValList\" */ },\n\t/*::[*/0x0400/*::]*/: { /* n:\"BrtRwDescent\" */ },\n\t/*::[*/0x0401/*::]*/: { /* n:\"BrtKnownFonts\" */ },\n\t/*::[*/0x0402/*::]*/: { /* n:\"BrtBeginSXTupleSet\", */ T:1 },\n\t/*::[*/0x0403/*::]*/: { /* n:\"BrtEndSXTupleSet\", */ T:-1 },\n\t/*::[*/0x0404/*::]*/: { /* n:\"BrtBeginSXTupleSetHeader\", */ T:1 },\n\t/*::[*/0x0405/*::]*/: { /* n:\"BrtEndSXTupleSetHeader\", */ T:-1 },\n\t/*::[*/0x0406/*::]*/: { /* n:\"BrtSXTupleSetHeaderItem\" */ },\n\t/*::[*/0x0407/*::]*/: { /* n:\"BrtBeginSXTupleSetData\", */ T:1 },\n\t/*::[*/0x0408/*::]*/: { /* n:\"BrtEndSXTupleSetData\", */ T:-1 },\n\t/*::[*/0x0409/*::]*/: { /* n:\"BrtBeginSXTupleSetRow\", */ T:1 },\n\t/*::[*/0x040A/*::]*/: { /* n:\"BrtEndSXTupleSetRow\", */ T:-1 },\n\t/*::[*/0x040B/*::]*/: { /* n:\"BrtSXTupleSetRowItem\" */ },\n\t/*::[*/0x040C/*::]*/: { /* n:\"BrtNameExt\" */ },\n\t/*::[*/0x040D/*::]*/: { /* n:\"BrtPCDH14\" */ },\n\t/*::[*/0x040E/*::]*/: { /* n:\"BrtBeginPCDCalcMem14\", */ T:1 },\n\t/*::[*/0x040F/*::]*/: { /* n:\"BrtEndPCDCalcMem14\", */ T:-1 },\n\t/*::[*/0x0410/*::]*/: { /* n:\"BrtSXTH14\" */ },\n\t/*::[*/0x0411/*::]*/: { /* n:\"BrtBeginSparklineGroup\", */ T:1 },\n\t/*::[*/0x0412/*::]*/: { /* n:\"BrtEndSparklineGroup\", */ T:-1 },\n\t/*::[*/0x0413/*::]*/: { /* n:\"BrtSparkline\" */ },\n\t/*::[*/0x0414/*::]*/: { /* n:\"BrtSXDI14\" */ },\n\t/*::[*/0x0415/*::]*/: { /* n:\"BrtWsFmtInfoEx14\" */ },\n\t/*::[*/0x0416/*::]*/: { /* n:\"BrtBeginConditionalFormatting14\", */ T:1 },\n\t/*::[*/0x0417/*::]*/: { /* n:\"BrtEndConditionalFormatting14\", */ T:-1 },\n\t/*::[*/0x0418/*::]*/: { /* n:\"BrtBeginCFRule14\", */ T:1 },\n\t/*::[*/0x0419/*::]*/: { /* n:\"BrtEndCFRule14\", */ T:-1 },\n\t/*::[*/0x041A/*::]*/: { /* n:\"BrtCFVO14\" */ },\n\t/*::[*/0x041B/*::]*/: { /* n:\"BrtBeginDatabar14\", */ T:1 },\n\t/*::[*/0x041C/*::]*/: { /* n:\"BrtBeginIconSet14\", */ T:1 },\n\t/*::[*/0x041D/*::]*/: { /* n:\"BrtDVal14\", */ f: parse_BrtDVal14 },\n\t/*::[*/0x041E/*::]*/: { /* n:\"BrtBeginDVals14\", */ T:1 },\n\t/*::[*/0x041F/*::]*/: { /* n:\"BrtColor14\" */ },\n\t/*::[*/0x0420/*::]*/: { /* n:\"BrtBeginSparklines\", */ T:1 },\n\t/*::[*/0x0421/*::]*/: { /* n:\"BrtEndSparklines\", */ T:-1 },\n\t/*::[*/0x0422/*::]*/: { /* n:\"BrtBeginSparklineGroups\", */ T:1 },\n\t/*::[*/0x0423/*::]*/: { /* n:\"BrtEndSparklineGroups\", */ T:-1 },\n\t/*::[*/0x0425/*::]*/: { /* n:\"BrtSXVD14\" */ },\n\t/*::[*/0x0426/*::]*/: { /* n:\"BrtBeginSXView14\", */ T:1 },\n\t/*::[*/0x0427/*::]*/: { /* n:\"BrtEndSXView14\", */ T:-1 },\n\t/*::[*/0x0428/*::]*/: { /* n:\"BrtBeginSXView16\", */ T:1 },\n\t/*::[*/0x0429/*::]*/: { /* n:\"BrtEndSXView16\", */ T:-1 },\n\t/*::[*/0x042A/*::]*/: { /* n:\"BrtBeginPCD14\", */ T:1 },\n\t/*::[*/0x042B/*::]*/: { /* n:\"BrtEndPCD14\", */ T:-1 },\n\t/*::[*/0x042C/*::]*/: { /* n:\"BrtBeginExtConn14\", */ T:1 },\n\t/*::[*/0x042D/*::]*/: { /* n:\"BrtEndExtConn14\", */ T:-1 },\n\t/*::[*/0x042E/*::]*/: { /* n:\"BrtBeginSlicerCacheIDs\", */ T:1 },\n\t/*::[*/0x042F/*::]*/: { /* n:\"BrtEndSlicerCacheIDs\", */ T:-1 },\n\t/*::[*/0x0430/*::]*/: { /* n:\"BrtBeginSlicerCacheID\", */ T:1 },\n\t/*::[*/0x0431/*::]*/: { /* n:\"BrtEndSlicerCacheID\", */ T:-1 },\n\t/*::[*/0x0433/*::]*/: { /* n:\"BrtBeginSlicerCache\", */ T:1 },\n\t/*::[*/0x0434/*::]*/: { /* n:\"BrtEndSlicerCache\", */ T:-1 },\n\t/*::[*/0x0435/*::]*/: { /* n:\"BrtBeginSlicerCacheDef\", */ T:1 },\n\t/*::[*/0x0436/*::]*/: { /* n:\"BrtEndSlicerCacheDef\", */ T:-1 },\n\t/*::[*/0x0437/*::]*/: { /* n:\"BrtBeginSlicersEx\", */ T:1 },\n\t/*::[*/0x0438/*::]*/: { /* n:\"BrtEndSlicersEx\", */ T:-1 },\n\t/*::[*/0x0439/*::]*/: { /* n:\"BrtBeginSlicerEx\", */ T:1 },\n\t/*::[*/0x043A/*::]*/: { /* n:\"BrtEndSlicerEx\", */ T:-1 },\n\t/*::[*/0x043B/*::]*/: { /* n:\"BrtBeginSlicer\", */ T:1 },\n\t/*::[*/0x043C/*::]*/: { /* n:\"BrtEndSlicer\", */ T:-1 },\n\t/*::[*/0x043D/*::]*/: { /* n:\"BrtSlicerCachePivotTables\" */ },\n\t/*::[*/0x043E/*::]*/: { /* n:\"BrtBeginSlicerCacheOlapImpl\", */ T:1 },\n\t/*::[*/0x043F/*::]*/: { /* n:\"BrtEndSlicerCacheOlapImpl\", */ T:-1 },\n\t/*::[*/0x0440/*::]*/: { /* n:\"BrtBeginSlicerCacheLevelsData\", */ T:1 },\n\t/*::[*/0x0441/*::]*/: { /* n:\"BrtEndSlicerCacheLevelsData\", */ T:-1 },\n\t/*::[*/0x0442/*::]*/: { /* n:\"BrtBeginSlicerCacheLevelData\", */ T:1 },\n\t/*::[*/0x0443/*::]*/: { /* n:\"BrtEndSlicerCacheLevelData\", */ T:-1 },\n\t/*::[*/0x0444/*::]*/: { /* n:\"BrtBeginSlicerCacheSiRanges\", */ T:1 },\n\t/*::[*/0x0445/*::]*/: { /* n:\"BrtEndSlicerCacheSiRanges\", */ T:-1 },\n\t/*::[*/0x0446/*::]*/: { /* n:\"BrtBeginSlicerCacheSiRange\", */ T:1 },\n\t/*::[*/0x0447/*::]*/: { /* n:\"BrtEndSlicerCacheSiRange\", */ T:-1 },\n\t/*::[*/0x0448/*::]*/: { /* n:\"BrtSlicerCacheOlapItem\" */ },\n\t/*::[*/0x0449/*::]*/: { /* n:\"BrtBeginSlicerCacheSelections\", */ T:1 },\n\t/*::[*/0x044A/*::]*/: { /* n:\"BrtSlicerCacheSelection\" */ },\n\t/*::[*/0x044B/*::]*/: { /* n:\"BrtEndSlicerCacheSelections\", */ T:-1 },\n\t/*::[*/0x044C/*::]*/: { /* n:\"BrtBeginSlicerCacheNative\", */ T:1 },\n\t/*::[*/0x044D/*::]*/: { /* n:\"BrtEndSlicerCacheNative\", */ T:-1 },\n\t/*::[*/0x044E/*::]*/: { /* n:\"BrtSlicerCacheNativeItem\" */ },\n\t/*::[*/0x044F/*::]*/: { /* n:\"BrtRangeProtection14\" */ },\n\t/*::[*/0x0450/*::]*/: { /* n:\"BrtRangeProtectionIso14\" */ },\n\t/*::[*/0x0451/*::]*/: { /* n:\"BrtCellIgnoreEC14\" */ },\n\t/*::[*/0x0457/*::]*/: { /* n:\"BrtList14\" */ },\n\t/*::[*/0x0458/*::]*/: { /* n:\"BrtCFIcon\" */ },\n\t/*::[*/0x0459/*::]*/: { /* n:\"BrtBeginSlicerCachesPivotCacheIDs\", */ T:1 },\n\t/*::[*/0x045A/*::]*/: { /* n:\"BrtEndSlicerCachesPivotCacheIDs\", */ T:-1 },\n\t/*::[*/0x045B/*::]*/: { /* n:\"BrtBeginSlicers\", */ T:1 },\n\t/*::[*/0x045C/*::]*/: { /* n:\"BrtEndSlicers\", */ T:-1 },\n\t/*::[*/0x045D/*::]*/: { /* n:\"BrtWbProp14\" */ },\n\t/*::[*/0x045E/*::]*/: { /* n:\"BrtBeginSXEdit\", */ T:1 },\n\t/*::[*/0x045F/*::]*/: { /* n:\"BrtEndSXEdit\", */ T:-1 },\n\t/*::[*/0x0460/*::]*/: { /* n:\"BrtBeginSXEdits\", */ T:1 },\n\t/*::[*/0x0461/*::]*/: { /* n:\"BrtEndSXEdits\", */ T:-1 },\n\t/*::[*/0x0462/*::]*/: { /* n:\"BrtBeginSXChange\", */ T:1 },\n\t/*::[*/0x0463/*::]*/: { /* n:\"BrtEndSXChange\", */ T:-1 },\n\t/*::[*/0x0464/*::]*/: { /* n:\"BrtBeginSXChanges\", */ T:1 },\n\t/*::[*/0x0465/*::]*/: { /* n:\"BrtEndSXChanges\", */ T:-1 },\n\t/*::[*/0x0466/*::]*/: { /* n:\"BrtSXTupleItems\" */ },\n\t/*::[*/0x0468/*::]*/: { /* n:\"BrtBeginSlicerStyle\", */ T:1 },\n\t/*::[*/0x0469/*::]*/: { /* n:\"BrtEndSlicerStyle\", */ T:-1 },\n\t/*::[*/0x046A/*::]*/: { /* n:\"BrtSlicerStyleElement\" */ },\n\t/*::[*/0x046B/*::]*/: { /* n:\"BrtBeginStyleSheetExt14\", */ T:1 },\n\t/*::[*/0x046C/*::]*/: { /* n:\"BrtEndStyleSheetExt14\", */ T:-1 },\n\t/*::[*/0x046D/*::]*/: { /* n:\"BrtBeginSlicerCachesPivotCacheID\", */ T:1 },\n\t/*::[*/0x046E/*::]*/: { /* n:\"BrtEndSlicerCachesPivotCacheID\", */ T:-1 },\n\t/*::[*/0x046F/*::]*/: { /* n:\"BrtBeginConditionalFormattings\", */ T:1 },\n\t/*::[*/0x0470/*::]*/: { /* n:\"BrtEndConditionalFormattings\", */ T:-1 },\n\t/*::[*/0x0471/*::]*/: { /* n:\"BrtBeginPCDCalcMemExt\", */ T:1 },\n\t/*::[*/0x0472/*::]*/: { /* n:\"BrtEndPCDCalcMemExt\", */ T:-1 },\n\t/*::[*/0x0473/*::]*/: { /* n:\"BrtBeginPCDCalcMemsExt\", */ T:1 },\n\t/*::[*/0x0474/*::]*/: { /* n:\"BrtEndPCDCalcMemsExt\", */ T:-1 },\n\t/*::[*/0x0475/*::]*/: { /* n:\"BrtPCDField14\" */ },\n\t/*::[*/0x0476/*::]*/: { /* n:\"BrtBeginSlicerStyles\", */ T:1 },\n\t/*::[*/0x0477/*::]*/: { /* n:\"BrtEndSlicerStyles\", */ T:-1 },\n\t/*::[*/0x0478/*::]*/: { /* n:\"BrtBeginSlicerStyleElements\", */ T:1 },\n\t/*::[*/0x0479/*::]*/: { /* n:\"BrtEndSlicerStyleElements\", */ T:-1 },\n\t/*::[*/0x047A/*::]*/: { /* n:\"BrtCFRuleExt\" */ },\n\t/*::[*/0x047B/*::]*/: { /* n:\"BrtBeginSXCondFmt14\", */ T:1 },\n\t/*::[*/0x047C/*::]*/: { /* n:\"BrtEndSXCondFmt14\", */ T:-1 },\n\t/*::[*/0x047D/*::]*/: { /* n:\"BrtBeginSXCondFmts14\", */ T:1 },\n\t/*::[*/0x047E/*::]*/: { /* n:\"BrtEndSXCondFmts14\", */ T:-1 },\n\t/*::[*/0x0480/*::]*/: { /* n:\"BrtBeginSortCond14\", */ T:1 },\n\t/*::[*/0x0481/*::]*/: { /* n:\"BrtEndSortCond14\", */ T:-1 },\n\t/*::[*/0x0482/*::]*/: { /* n:\"BrtEndDVals14\", */ T:-1 },\n\t/*::[*/0x0483/*::]*/: { /* n:\"BrtEndIconSet14\", */ T:-1 },\n\t/*::[*/0x0484/*::]*/: { /* n:\"BrtEndDatabar14\", */ T:-1 },\n\t/*::[*/0x0485/*::]*/: { /* n:\"BrtBeginColorScale14\", */ T:1 },\n\t/*::[*/0x0486/*::]*/: { /* n:\"BrtEndColorScale14\", */ T:-1 },\n\t/*::[*/0x0487/*::]*/: { /* n:\"BrtBeginSxrules14\", */ T:1 },\n\t/*::[*/0x0488/*::]*/: { /* n:\"BrtEndSxrules14\", */ T:-1 },\n\t/*::[*/0x0489/*::]*/: { /* n:\"BrtBeginPRule14\", */ T:1 },\n\t/*::[*/0x048A/*::]*/: { /* n:\"BrtEndPRule14\", */ T:-1 },\n\t/*::[*/0x048B/*::]*/: { /* n:\"BrtBeginPRFilters14\", */ T:1 },\n\t/*::[*/0x048C/*::]*/: { /* n:\"BrtEndPRFilters14\", */ T:-1 },\n\t/*::[*/0x048D/*::]*/: { /* n:\"BrtBeginPRFilter14\", */ T:1 },\n\t/*::[*/0x048E/*::]*/: { /* n:\"BrtEndPRFilter14\", */ T:-1 },\n\t/*::[*/0x048F/*::]*/: { /* n:\"BrtBeginPRFItem14\", */ T:1 },\n\t/*::[*/0x0490/*::]*/: { /* n:\"BrtEndPRFItem14\", */ T:-1 },\n\t/*::[*/0x0491/*::]*/: { /* n:\"BrtBeginCellIgnoreECs14\", */ T:1 },\n\t/*::[*/0x0492/*::]*/: { /* n:\"BrtEndCellIgnoreECs14\", */ T:-1 },\n\t/*::[*/0x0493/*::]*/: { /* n:\"BrtDxf14\" */ },\n\t/*::[*/0x0494/*::]*/: { /* n:\"BrtBeginDxF14s\", */ T:1 },\n\t/*::[*/0x0495/*::]*/: { /* n:\"BrtEndDxf14s\", */ T:-1 },\n\t/*::[*/0x0499/*::]*/: { /* n:\"BrtFilter14\" */ },\n\t/*::[*/0x049A/*::]*/: { /* n:\"BrtBeginCustomFilters14\", */ T:1 },\n\t/*::[*/0x049C/*::]*/: { /* n:\"BrtCustomFilter14\" */ },\n\t/*::[*/0x049D/*::]*/: { /* n:\"BrtIconFilter14\" */ },\n\t/*::[*/0x049E/*::]*/: { /* n:\"BrtPivotCacheConnectionName\" */ },\n\t/*::[*/0x0800/*::]*/: { /* n:\"BrtBeginDecoupledPivotCacheIDs\", */ T:1 },\n\t/*::[*/0x0801/*::]*/: { /* n:\"BrtEndDecoupledPivotCacheIDs\", */ T:-1 },\n\t/*::[*/0x0802/*::]*/: { /* n:\"BrtDecoupledPivotCacheID\" */ },\n\t/*::[*/0x0803/*::]*/: { /* n:\"BrtBeginPivotTableRefs\", */ T:1 },\n\t/*::[*/0x0804/*::]*/: { /* n:\"BrtEndPivotTableRefs\", */ T:-1 },\n\t/*::[*/0x0805/*::]*/: { /* n:\"BrtPivotTableRef\" */ },\n\t/*::[*/0x0806/*::]*/: { /* n:\"BrtSlicerCacheBookPivotTables\" */ },\n\t/*::[*/0x0807/*::]*/: { /* n:\"BrtBeginSxvcells\", */ T:1 },\n\t/*::[*/0x0808/*::]*/: { /* n:\"BrtEndSxvcells\", */ T:-1 },\n\t/*::[*/0x0809/*::]*/: { /* n:\"BrtBeginSxRow\", */ T:1 },\n\t/*::[*/0x080A/*::]*/: { /* n:\"BrtEndSxRow\", */ T:-1 },\n\t/*::[*/0x080C/*::]*/: { /* n:\"BrtPcdCalcMem15\" */ },\n\t/*::[*/0x0813/*::]*/: { /* n:\"BrtQsi15\" */ },\n\t/*::[*/0x0814/*::]*/: { /* n:\"BrtBeginWebExtensions\", */ T:1 },\n\t/*::[*/0x0815/*::]*/: { /* n:\"BrtEndWebExtensions\", */ T:-1 },\n\t/*::[*/0x0816/*::]*/: { /* n:\"BrtWebExtension\" */ },\n\t/*::[*/0x0817/*::]*/: { /* n:\"BrtAbsPath15\" */ },\n\t/*::[*/0x0818/*::]*/: { /* n:\"BrtBeginPivotTableUISettings\", */ T:1 },\n\t/*::[*/0x0819/*::]*/: { /* n:\"BrtEndPivotTableUISettings\", */ T:-1 },\n\t/*::[*/0x081B/*::]*/: { /* n:\"BrtTableSlicerCacheIDs\" */ },\n\t/*::[*/0x081C/*::]*/: { /* n:\"BrtTableSlicerCacheID\" */ },\n\t/*::[*/0x081D/*::]*/: { /* n:\"BrtBeginTableSlicerCache\", */ T:1 },\n\t/*::[*/0x081E/*::]*/: { /* n:\"BrtEndTableSlicerCache\", */ T:-1 },\n\t/*::[*/0x081F/*::]*/: { /* n:\"BrtSxFilter15\" */ },\n\t/*::[*/0x0820/*::]*/: { /* n:\"BrtBeginTimelineCachePivotCacheIDs\", */ T:1 },\n\t/*::[*/0x0821/*::]*/: { /* n:\"BrtEndTimelineCachePivotCacheIDs\", */ T:-1 },\n\t/*::[*/0x0822/*::]*/: { /* n:\"BrtTimelineCachePivotCacheID\" */ },\n\t/*::[*/0x0823/*::]*/: { /* n:\"BrtBeginTimelineCacheIDs\", */ T:1 },\n\t/*::[*/0x0824/*::]*/: { /* n:\"BrtEndTimelineCacheIDs\", */ T:-1 },\n\t/*::[*/0x0825/*::]*/: { /* n:\"BrtBeginTimelineCacheID\", */ T:1 },\n\t/*::[*/0x0826/*::]*/: { /* n:\"BrtEndTimelineCacheID\", */ T:-1 },\n\t/*::[*/0x0827/*::]*/: { /* n:\"BrtBeginTimelinesEx\", */ T:1 },\n\t/*::[*/0x0828/*::]*/: { /* n:\"BrtEndTimelinesEx\", */ T:-1 },\n\t/*::[*/0x0829/*::]*/: { /* n:\"BrtBeginTimelineEx\", */ T:1 },\n\t/*::[*/0x082A/*::]*/: { /* n:\"BrtEndTimelineEx\", */ T:-1 },\n\t/*::[*/0x082B/*::]*/: { /* n:\"BrtWorkBookPr15\" */ },\n\t/*::[*/0x082C/*::]*/: { /* n:\"BrtPCDH15\" */ },\n\t/*::[*/0x082D/*::]*/: { /* n:\"BrtBeginTimelineStyle\", */ T:1 },\n\t/*::[*/0x082E/*::]*/: { /* n:\"BrtEndTimelineStyle\", */ T:-1 },\n\t/*::[*/0x082F/*::]*/: { /* n:\"BrtTimelineStyleElement\" */ },\n\t/*::[*/0x0830/*::]*/: { /* n:\"BrtBeginTimelineStylesheetExt15\", */ T:1 },\n\t/*::[*/0x0831/*::]*/: { /* n:\"BrtEndTimelineStylesheetExt15\", */ T:-1 },\n\t/*::[*/0x0832/*::]*/: { /* n:\"BrtBeginTimelineStyles\", */ T:1 },\n\t/*::[*/0x0833/*::]*/: { /* n:\"BrtEndTimelineStyles\", */ T:-1 },\n\t/*::[*/0x0834/*::]*/: { /* n:\"BrtBeginTimelineStyleElements\", */ T:1 },\n\t/*::[*/0x0835/*::]*/: { /* n:\"BrtEndTimelineStyleElements\", */ T:-1 },\n\t/*::[*/0x0836/*::]*/: { /* n:\"BrtDxf15\" */ },\n\t/*::[*/0x0837/*::]*/: { /* n:\"BrtBeginDxfs15\", */ T:1 },\n\t/*::[*/0x0838/*::]*/: { /* n:\"BrtEndDxfs15\", */ T:-1 },\n\t/*::[*/0x0839/*::]*/: { /* n:\"BrtSlicerCacheHideItemsWithNoData\" */ },\n\t/*::[*/0x083A/*::]*/: { /* n:\"BrtBeginItemUniqueNames\", */ T:1 },\n\t/*::[*/0x083B/*::]*/: { /* n:\"BrtEndItemUniqueNames\", */ T:-1 },\n\t/*::[*/0x083C/*::]*/: { /* n:\"BrtItemUniqueName\" */ },\n\t/*::[*/0x083D/*::]*/: { /* n:\"BrtBeginExtConn15\", */ T:1 },\n\t/*::[*/0x083E/*::]*/: { /* n:\"BrtEndExtConn15\", */ T:-1 },\n\t/*::[*/0x083F/*::]*/: { /* n:\"BrtBeginOledbPr15\", */ T:1 },\n\t/*::[*/0x0840/*::]*/: { /* n:\"BrtEndOledbPr15\", */ T:-1 },\n\t/*::[*/0x0841/*::]*/: { /* n:\"BrtBeginDataFeedPr15\", */ T:1 },\n\t/*::[*/0x0842/*::]*/: { /* n:\"BrtEndDataFeedPr15\", */ T:-1 },\n\t/*::[*/0x0843/*::]*/: { /* n:\"BrtTextPr15\" */ },\n\t/*::[*/0x0844/*::]*/: { /* n:\"BrtRangePr15\" */ },\n\t/*::[*/0x0845/*::]*/: { /* n:\"BrtDbCommand15\" */ },\n\t/*::[*/0x0846/*::]*/: { /* n:\"BrtBeginDbTables15\", */ T:1 },\n\t/*::[*/0x0847/*::]*/: { /* n:\"BrtEndDbTables15\", */ T:-1 },\n\t/*::[*/0x0848/*::]*/: { /* n:\"BrtDbTable15\" */ },\n\t/*::[*/0x0849/*::]*/: { /* n:\"BrtBeginDataModel\", */ T:1 },\n\t/*::[*/0x084A/*::]*/: { /* n:\"BrtEndDataModel\", */ T:-1 },\n\t/*::[*/0x084B/*::]*/: { /* n:\"BrtBeginModelTables\", */ T:1 },\n\t/*::[*/0x084C/*::]*/: { /* n:\"BrtEndModelTables\", */ T:-1 },\n\t/*::[*/0x084D/*::]*/: { /* n:\"BrtModelTable\" */ },\n\t/*::[*/0x084E/*::]*/: { /* n:\"BrtBeginModelRelationships\", */ T:1 },\n\t/*::[*/0x084F/*::]*/: { /* n:\"BrtEndModelRelationships\", */ T:-1 },\n\t/*::[*/0x0850/*::]*/: { /* n:\"BrtModelRelationship\" */ },\n\t/*::[*/0x0851/*::]*/: { /* n:\"BrtBeginECTxtWiz15\", */ T:1 },\n\t/*::[*/0x0852/*::]*/: { /* n:\"BrtEndECTxtWiz15\", */ T:-1 },\n\t/*::[*/0x0853/*::]*/: { /* n:\"BrtBeginECTWFldInfoLst15\", */ T:1 },\n\t/*::[*/0x0854/*::]*/: { /* n:\"BrtEndECTWFldInfoLst15\", */ T:-1 },\n\t/*::[*/0x0855/*::]*/: { /* n:\"BrtBeginECTWFldInfo15\", */ T:1 },\n\t/*::[*/0x0856/*::]*/: { /* n:\"BrtFieldListActiveItem\" */ },\n\t/*::[*/0x0857/*::]*/: { /* n:\"BrtPivotCacheIdVersion\" */ },\n\t/*::[*/0x0858/*::]*/: { /* n:\"BrtSXDI15\" */ },\n\t/*::[*/0x0859/*::]*/: { /* n:\"BrtBeginModelTimeGroupings\", */ T:1 },\n\t/*::[*/0x085A/*::]*/: { /* n:\"BrtEndModelTimeGroupings\", */ T:-1 },\n\t/*::[*/0x085B/*::]*/: { /* n:\"BrtBeginModelTimeGrouping\", */ T:1 },\n\t/*::[*/0x085C/*::]*/: { /* n:\"BrtEndModelTimeGrouping\", */ T:-1 },\n\t/*::[*/0x085D/*::]*/: { /* n:\"BrtModelTimeGroupingCalcCol\" */ },\n\t/*::[*/0x0C00/*::]*/: { /* n:\"BrtUid\" */ },\n\t/*::[*/0x0C01/*::]*/: { /* n:\"BrtRevisionPtr\" */ },\n\t/*::[*/0x1000/*::]*/: { /* n:\"BrtBeginDynamicArrayPr\", */ T:1 },\n\t/*::[*/0x1001/*::]*/: { /* n:\"BrtEndDynamicArrayPr\", */ T:-1 },\n\t/*::[*/0x138A/*::]*/: { /* n:\"BrtBeginRichValueBlock\", */ T:1 },\n\t/*::[*/0x138B/*::]*/: { /* n:\"BrtEndRichValueBlock\", */ T:-1 },\n\t/*::[*/0x13D9/*::]*/: { /* n:\"BrtBeginRichFilters\", */ T:1 },\n\t/*::[*/0x13DA/*::]*/: { /* n:\"BrtEndRichFilters\", */ T:-1 },\n\t/*::[*/0x13DB/*::]*/: { /* n:\"BrtRichFilter\" */ },\n\t/*::[*/0x13DC/*::]*/: { /* n:\"BrtBeginRichFilterColumn\", */ T:1 },\n\t/*::[*/0x13DD/*::]*/: { /* n:\"BrtEndRichFilterColumn\", */ T:-1 },\n\t/*::[*/0x13DE/*::]*/: { /* n:\"BrtBeginCustomRichFilters\", */ T:1 },\n\t/*::[*/0x13DF/*::]*/: { /* n:\"BrtEndCustomRichFilters\", */ T:-1 },\n\t/*::[*/0x13E0/*::]*/: { /* n:\"BrtCustomRichFilter\" */ },\n\t/*::[*/0x13E1/*::]*/: { /* n:\"BrtTop10RichFilter\" */ },\n\t/*::[*/0x13E2/*::]*/: { /* n:\"BrtDynamicRichFilter\" */ },\n\t/*::[*/0x13E4/*::]*/: { /* n:\"BrtBeginRichSortCondition\", */ T:1 },\n\t/*::[*/0x13E5/*::]*/: { /* n:\"BrtEndRichSortCondition\", */ T:-1 },\n\t/*::[*/0x13E6/*::]*/: { /* n:\"BrtRichFilterDateGroupItem\" */ },\n\t/*::[*/0x13E7/*::]*/: { /* n:\"BrtBeginCalcFeatures\", */ T:1 },\n\t/*::[*/0x13E8/*::]*/: { /* n:\"BrtEndCalcFeatures\", */ T:-1 },\n\t/*::[*/0x13E9/*::]*/: { /* n:\"BrtCalcFeature\" */ },\n\t/*::[*/0x13EB/*::]*/: { /* n:\"BrtExternalLinksPr\" */ },\n\t/*::[*/0xFFFF/*::]*/: { n:\"\" }\n};\n\n/* [MS-XLS] 2.3 Record Enumeration (and other sources) */\nvar XLSRecordEnum = {\n\t/* [MS-XLS] 2.3 Record Enumeration 2021-08-17 */\n\t/*::[*/0x0006/*::]*/: { /* n:\"Formula\", */ f:parse_Formula },\n\t/*::[*/0x000a/*::]*/: { /* n:\"EOF\", */ f:parsenoop2 },\n\t/*::[*/0x000c/*::]*/: { /* n:\"CalcCount\", */ f:parseuint16 }, //\n\t/*::[*/0x000d/*::]*/: { /* n:\"CalcMode\", */ f:parseuint16 }, //\n\t/*::[*/0x000e/*::]*/: { /* n:\"CalcPrecision\", */ f:parsebool }, //\n\t/*::[*/0x000f/*::]*/: { /* n:\"CalcRefMode\", */ f:parsebool }, //\n\t/*::[*/0x0010/*::]*/: { /* n:\"CalcDelta\", */ f:parse_Xnum }, //\n\t/*::[*/0x0011/*::]*/: { /* n:\"CalcIter\", */ f:parsebool }, //\n\t/*::[*/0x0012/*::]*/: { /* n:\"Protect\", */ f:parsebool },\n\t/*::[*/0x0013/*::]*/: { /* n:\"Password\", */ f:parseuint16 },\n\t/*::[*/0x0014/*::]*/: { /* n:\"Header\", */ f:parse_XLHeaderFooter },\n\t/*::[*/0x0015/*::]*/: { /* n:\"Footer\", */ f:parse_XLHeaderFooter },\n\t/*::[*/0x0017/*::]*/: { /* n:\"ExternSheet\", */ f:parse_ExternSheet },\n\t/*::[*/0x0018/*::]*/: { /* n:\"Lbl\", */ f:parse_Lbl },\n\t/*::[*/0x0019/*::]*/: { /* n:\"WinProtect\", */ f:parsebool },\n\t/*::[*/0x001a/*::]*/: { /* n:\"VerticalPageBreaks\", */ },\n\t/*::[*/0x001b/*::]*/: { /* n:\"HorizontalPageBreaks\", */ },\n\t/*::[*/0x001c/*::]*/: { /* n:\"Note\", */ f:parse_Note },\n\t/*::[*/0x001d/*::]*/: { /* n:\"Selection\", */ },\n\t/*::[*/0x0022/*::]*/: { /* n:\"Date1904\", */ f:parsebool },\n\t/*::[*/0x0023/*::]*/: { /* n:\"ExternName\", */ f:parse_ExternName },\n\t/*::[*/0x0026/*::]*/: { /* n:\"LeftMargin\", */ f:parse_Xnum }, // *\n\t/*::[*/0x0027/*::]*/: { /* n:\"RightMargin\", */ f:parse_Xnum }, // *\n\t/*::[*/0x0028/*::]*/: { /* n:\"TopMargin\", */ f:parse_Xnum }, // *\n\t/*::[*/0x0029/*::]*/: { /* n:\"BottomMargin\", */ f:parse_Xnum }, // *\n\t/*::[*/0x002a/*::]*/: { /* n:\"PrintRowCol\", */ f:parsebool },\n\t/*::[*/0x002b/*::]*/: { /* n:\"PrintGrid\", */ f:parsebool },\n\t/*::[*/0x002f/*::]*/: { /* n:\"FilePass\", */ f:parse_FilePass },\n\t/*::[*/0x0031/*::]*/: { /* n:\"Font\", */ f:parse_Font },\n\t/*::[*/0x0033/*::]*/: { /* n:\"PrintSize\", */ f:parseuint16 },\n\t/*::[*/0x003c/*::]*/: { /* n:\"Continue\", */ },\n\t/*::[*/0x003d/*::]*/: { /* n:\"Window1\", */ f:parse_Window1 },\n\t/*::[*/0x0040/*::]*/: { /* n:\"Backup\", */ f:parsebool },\n\t/*::[*/0x0041/*::]*/: { /* n:\"Pane\", */ f:parse_Pane },\n\t/*::[*/0x0042/*::]*/: { /* n:\"CodePage\", */ f:parseuint16 },\n\t/*::[*/0x004d/*::]*/: { /* n:\"Pls\", */ },\n\t/*::[*/0x0050/*::]*/: { /* n:\"DCon\", */ },\n\t/*::[*/0x0051/*::]*/: { /* n:\"DConRef\", */ },\n\t/*::[*/0x0052/*::]*/: { /* n:\"DConName\", */ },\n\t/*::[*/0x0055/*::]*/: { /* n:\"DefColWidth\", */ f:parseuint16 },\n\t/*::[*/0x0059/*::]*/: { /* n:\"XCT\", */ },\n\t/*::[*/0x005a/*::]*/: { /* n:\"CRN\", */ },\n\t/*::[*/0x005b/*::]*/: { /* n:\"FileSharing\", */ },\n\t/*::[*/0x005c/*::]*/: { /* n:\"WriteAccess\", */ f:parse_WriteAccess },\n\t/*::[*/0x005d/*::]*/: { /* n:\"Obj\", */ f:parse_Obj },\n\t/*::[*/0x005e/*::]*/: { /* n:\"Uncalced\", */ },\n\t/*::[*/0x005f/*::]*/: { /* n:\"CalcSaveRecalc\", */ f:parsebool }, //\n\t/*::[*/0x0060/*::]*/: { /* n:\"Template\", */ },\n\t/*::[*/0x0061/*::]*/: { /* n:\"Intl\", */ },\n\t/*::[*/0x0063/*::]*/: { /* n:\"ObjProtect\", */ f:parsebool },\n\t/*::[*/0x007d/*::]*/: { /* n:\"ColInfo\", */ f:parse_ColInfo },\n\t/*::[*/0x0080/*::]*/: { /* n:\"Guts\", */ f:parse_Guts },\n\t/*::[*/0x0081/*::]*/: { /* n:\"WsBool\", */ f:parse_WsBool },\n\t/*::[*/0x0082/*::]*/: { /* n:\"GridSet\", */ f:parseuint16 },\n\t/*::[*/0x0083/*::]*/: { /* n:\"HCenter\", */ f:parsebool },\n\t/*::[*/0x0084/*::]*/: { /* n:\"VCenter\", */ f:parsebool },\n\t/*::[*/0x0085/*::]*/: { /* n:\"BoundSheet8\", */ f:parse_BoundSheet8 },\n\t/*::[*/0x0086/*::]*/: { /* n:\"WriteProtect\", */ },\n\t/*::[*/0x008c/*::]*/: { /* n:\"Country\", */ f:parse_Country },\n\t/*::[*/0x008d/*::]*/: { /* n:\"HideObj\", */ f:parseuint16 },\n\t/*::[*/0x0090/*::]*/: { /* n:\"Sort\", */ },\n\t/*::[*/0x0092/*::]*/: { /* n:\"Palette\", */ f:parse_Palette },\n\t/*::[*/0x0097/*::]*/: { /* n:\"Sync\", */ },\n\t/*::[*/0x0098/*::]*/: { /* n:\"LPr\", */ },\n\t/*::[*/0x0099/*::]*/: { /* n:\"DxGCol\", */ },\n\t/*::[*/0x009a/*::]*/: { /* n:\"FnGroupName\", */ },\n\t/*::[*/0x009b/*::]*/: { /* n:\"FilterMode\", */ },\n\t/*::[*/0x009c/*::]*/: { /* n:\"BuiltInFnGroupCount\", */ f:parseuint16 },\n\t/*::[*/0x009d/*::]*/: { /* n:\"AutoFilterInfo\", */ },\n\t/*::[*/0x009e/*::]*/: { /* n:\"AutoFilter\", */ },\n\t/*::[*/0x00a0/*::]*/: { /* n:\"Scl\", */ f:parse_Scl },\n\t/*::[*/0x00a1/*::]*/: { /* n:\"Setup\", */ f:parse_Setup },\n\t/*::[*/0x00ae/*::]*/: { /* n:\"ScenMan\", */ },\n\t/*::[*/0x00af/*::]*/: { /* n:\"SCENARIO\", */ },\n\t/*::[*/0x00b0/*::]*/: { /* n:\"SxView\", */ },\n\t/*::[*/0x00b1/*::]*/: { /* n:\"Sxvd\", */ },\n\t/*::[*/0x00b2/*::]*/: { /* n:\"SXVI\", */ },\n\t/*::[*/0x00b4/*::]*/: { /* n:\"SxIvd\", */ },\n\t/*::[*/0x00b5/*::]*/: { /* n:\"SXLI\", */ },\n\t/*::[*/0x00b6/*::]*/: { /* n:\"SXPI\", */ },\n\t/*::[*/0x00b8/*::]*/: { /* n:\"DocRoute\", */ },\n\t/*::[*/0x00b9/*::]*/: { /* n:\"RecipName\", */ },\n\t/*::[*/0x00bd/*::]*/: { /* n:\"MulRk\", */ f:parse_MulRk },\n\t/*::[*/0x00be/*::]*/: { /* n:\"MulBlank\", */ f:parse_MulBlank },\n\t/*::[*/0x00c1/*::]*/: { /* n:\"Mms\", */ f:parsenoop2 },\n\t/*::[*/0x00c5/*::]*/: { /* n:\"SXDI\", */ },\n\t/*::[*/0x00c6/*::]*/: { /* n:\"SXDB\", */ },\n\t/*::[*/0x00c7/*::]*/: { /* n:\"SXFDB\", */ },\n\t/*::[*/0x00c8/*::]*/: { /* n:\"SXDBB\", */ },\n\t/*::[*/0x00c9/*::]*/: { /* n:\"SXNum\", */ },\n\t/*::[*/0x00ca/*::]*/: { /* n:\"SxBool\", */ f:parsebool },\n\t/*::[*/0x00cb/*::]*/: { /* n:\"SxErr\", */ },\n\t/*::[*/0x00cc/*::]*/: { /* n:\"SXInt\", */ },\n\t/*::[*/0x00cd/*::]*/: { /* n:\"SXString\", */ },\n\t/*::[*/0x00ce/*::]*/: { /* n:\"SXDtr\", */ },\n\t/*::[*/0x00cf/*::]*/: { /* n:\"SxNil\", */ },\n\t/*::[*/0x00d0/*::]*/: { /* n:\"SXTbl\", */ },\n\t/*::[*/0x00d1/*::]*/: { /* n:\"SXTBRGIITM\", */ },\n\t/*::[*/0x00d2/*::]*/: { /* n:\"SxTbpg\", */ },\n\t/*::[*/0x00d3/*::]*/: { /* n:\"ObProj\", */ },\n\t/*::[*/0x00d5/*::]*/: { /* n:\"SXStreamID\", */ },\n\t/*::[*/0x00d7/*::]*/: { /* n:\"DBCell\", */ },\n\t/*::[*/0x00d8/*::]*/: { /* n:\"SXRng\", */ },\n\t/*::[*/0x00d9/*::]*/: { /* n:\"SxIsxoper\", */ },\n\t/*::[*/0x00da/*::]*/: { /* n:\"BookBool\", */ f:parseuint16 },\n\t/*::[*/0x00dc/*::]*/: { /* n:\"DbOrParamQry\", */ },\n\t/*::[*/0x00dd/*::]*/: { /* n:\"ScenarioProtect\", */ f:parsebool },\n\t/*::[*/0x00de/*::]*/: { /* n:\"OleObjectSize\", */ },\n\t/*::[*/0x00e0/*::]*/: { /* n:\"XF\", */ f:parse_XF },\n\t/*::[*/0x00e1/*::]*/: { /* n:\"InterfaceHdr\", */ f:parse_InterfaceHdr },\n\t/*::[*/0x00e2/*::]*/: { /* n:\"InterfaceEnd\", */ f:parsenoop2 },\n\t/*::[*/0x00e3/*::]*/: { /* n:\"SXVS\", */ },\n\t/*::[*/0x00e5/*::]*/: { /* n:\"MergeCells\", */ f:parse_MergeCells },\n\t/*::[*/0x00e9/*::]*/: { /* n:\"BkHim\", */ },\n\t/*::[*/0x00eb/*::]*/: { /* n:\"MsoDrawingGroup\", */ },\n\t/*::[*/0x00ec/*::]*/: { /* n:\"MsoDrawing\", */ },\n\t/*::[*/0x00ed/*::]*/: { /* n:\"MsoDrawingSelection\", */ },\n\t/*::[*/0x00ef/*::]*/: { /* n:\"PhoneticInfo\", */ },\n\t/*::[*/0x00f0/*::]*/: { /* n:\"SxRule\", */ },\n\t/*::[*/0x00f1/*::]*/: { /* n:\"SXEx\", */ },\n\t/*::[*/0x00f2/*::]*/: { /* n:\"SxFilt\", */ },\n\t/*::[*/0x00f4/*::]*/: { /* n:\"SxDXF\", */ },\n\t/*::[*/0x00f5/*::]*/: { /* n:\"SxItm\", */ },\n\t/*::[*/0x00f6/*::]*/: { /* n:\"SxName\", */ },\n\t/*::[*/0x00f7/*::]*/: { /* n:\"SxSelect\", */ },\n\t/*::[*/0x00f8/*::]*/: { /* n:\"SXPair\", */ },\n\t/*::[*/0x00f9/*::]*/: { /* n:\"SxFmla\", */ },\n\t/*::[*/0x00fb/*::]*/: { /* n:\"SxFormat\", */ },\n\t/*::[*/0x00fc/*::]*/: { /* n:\"SST\", */ f:parse_SST },\n\t/*::[*/0x00fd/*::]*/: { /* n:\"LabelSst\", */ f:parse_LabelSst },\n\t/*::[*/0x00ff/*::]*/: { /* n:\"ExtSST\", */ f:parse_ExtSST },\n\t/*::[*/0x0100/*::]*/: { /* n:\"SXVDEx\", */ },\n\t/*::[*/0x0103/*::]*/: { /* n:\"SXFormula\", */ },\n\t/*::[*/0x0122/*::]*/: { /* n:\"SXDBEx\", */ },\n\t/*::[*/0x0137/*::]*/: { /* n:\"RRDInsDel\", */ },\n\t/*::[*/0x0138/*::]*/: { /* n:\"RRDHead\", */ },\n\t/*::[*/0x013b/*::]*/: { /* n:\"RRDChgCell\", */ },\n\t/*::[*/0x013d/*::]*/: { /* n:\"RRTabId\", */ f:parseuint16a },\n\t/*::[*/0x013e/*::]*/: { /* n:\"RRDRenSheet\", */ },\n\t/*::[*/0x013f/*::]*/: { /* n:\"RRSort\", */ },\n\t/*::[*/0x0140/*::]*/: { /* n:\"RRDMove\", */ },\n\t/*::[*/0x014a/*::]*/: { /* n:\"RRFormat\", */ },\n\t/*::[*/0x014b/*::]*/: { /* n:\"RRAutoFmt\", */ },\n\t/*::[*/0x014d/*::]*/: { /* n:\"RRInsertSh\", */ },\n\t/*::[*/0x014e/*::]*/: { /* n:\"RRDMoveBegin\", */ },\n\t/*::[*/0x014f/*::]*/: { /* n:\"RRDMoveEnd\", */ },\n\t/*::[*/0x0150/*::]*/: { /* n:\"RRDInsDelBegin\", */ },\n\t/*::[*/0x0151/*::]*/: { /* n:\"RRDInsDelEnd\", */ },\n\t/*::[*/0x0152/*::]*/: { /* n:\"RRDConflict\", */ },\n\t/*::[*/0x0153/*::]*/: { /* n:\"RRDDefName\", */ },\n\t/*::[*/0x0154/*::]*/: { /* n:\"RRDRstEtxp\", */ },\n\t/*::[*/0x015f/*::]*/: { /* n:\"LRng\", */ },\n\t/*::[*/0x0160/*::]*/: { /* n:\"UsesELFs\", */ f:parsebool },\n\t/*::[*/0x0161/*::]*/: { /* n:\"DSF\", */ f:parsenoop2 },\n\t/*::[*/0x0191/*::]*/: { /* n:\"CUsr\", */ },\n\t/*::[*/0x0192/*::]*/: { /* n:\"CbUsr\", */ },\n\t/*::[*/0x0193/*::]*/: { /* n:\"UsrInfo\", */ },\n\t/*::[*/0x0194/*::]*/: { /* n:\"UsrExcl\", */ },\n\t/*::[*/0x0195/*::]*/: { /* n:\"FileLock\", */ },\n\t/*::[*/0x0196/*::]*/: { /* n:\"RRDInfo\", */ },\n\t/*::[*/0x0197/*::]*/: { /* n:\"BCUsrs\", */ },\n\t/*::[*/0x0198/*::]*/: { /* n:\"UsrChk\", */ },\n\t/*::[*/0x01a9/*::]*/: { /* n:\"UserBView\", */ },\n\t/*::[*/0x01aa/*::]*/: { /* n:\"UserSViewBegin\", */ },\n\t/*::[*/0x01ab/*::]*/: { /* n:\"UserSViewEnd\", */ },\n\t/*::[*/0x01ac/*::]*/: { /* n:\"RRDUserView\", */ },\n\t/*::[*/0x01ad/*::]*/: { /* n:\"Qsi\", */ },\n\t/*::[*/0x01ae/*::]*/: { /* n:\"SupBook\", */ f:parse_SupBook },\n\t/*::[*/0x01af/*::]*/: { /* n:\"Prot4Rev\", */ f:parsebool },\n\t/*::[*/0x01b0/*::]*/: { /* n:\"CondFmt\", */ },\n\t/*::[*/0x01b1/*::]*/: { /* n:\"CF\", */ },\n\t/*::[*/0x01b2/*::]*/: { /* n:\"DVal\", */ },\n\t/*::[*/0x01b5/*::]*/: { /* n:\"DConBin\", */ },\n\t/*::[*/0x01b6/*::]*/: { /* n:\"TxO\", */ f:parse_TxO },\n\t/*::[*/0x01b7/*::]*/: { /* n:\"RefreshAll\", */ f:parsebool }, //\n\t/*::[*/0x01b8/*::]*/: { /* n:\"HLink\", */ f:parse_HLink },\n\t/*::[*/0x01b9/*::]*/: { /* n:\"Lel\", */ },\n\t/*::[*/0x01ba/*::]*/: { /* n:\"CodeName\", */ f:parse_XLUnicodeString },\n\t/*::[*/0x01bb/*::]*/: { /* n:\"SXFDBType\", */ },\n\t/*::[*/0x01bc/*::]*/: { /* n:\"Prot4RevPass\", */ f:parseuint16 },\n\t/*::[*/0x01bd/*::]*/: { /* n:\"ObNoMacros\", */ },\n\t/*::[*/0x01be/*::]*/: { /* n:\"Dv\", */ },\n\t/*::[*/0x01c0/*::]*/: { /* n:\"Excel9File\", */ f:parsenoop2 },\n\t/*::[*/0x01c1/*::]*/: { /* n:\"RecalcId\", */ f:parse_RecalcId, r:2},\n\t/*::[*/0x01c2/*::]*/: { /* n:\"EntExU2\", */ f:parsenoop2 },\n\t/*::[*/0x0200/*::]*/: { /* n:\"Dimensions\", */ f:parse_Dimensions },\n\t/*::[*/0x0201/*::]*/: { /* n:\"Blank\", */ f:parse_Blank },\n\t/*::[*/0x0203/*::]*/: { /* n:\"Number\", */ f:parse_Number },\n\t/*::[*/0x0204/*::]*/: { /* n:\"Label\", */ f:parse_Label },\n\t/*::[*/0x0205/*::]*/: { /* n:\"BoolErr\", */ f:parse_BoolErr },\n\t/*::[*/0x0207/*::]*/: { /* n:\"String\", */ f:parse_String },\n\t/*::[*/0x0208/*::]*/: { /* n:\"Row\", */ f:parse_Row },\n\t/*::[*/0x020b/*::]*/: { /* n:\"Index\", */ },\n\t/*::[*/0x0221/*::]*/: { /* n:\"Array\", */ f:parse_Array },\n\t/*::[*/0x0225/*::]*/: { /* n:\"DefaultRowHeight\", */ f:parse_DefaultRowHeight },\n\t/*::[*/0x0236/*::]*/: { /* n:\"Table\", */ },\n\t/*::[*/0x023e/*::]*/: { /* n:\"Window2\", */ f:parse_Window2 },\n\t/*::[*/0x027e/*::]*/: { /* n:\"RK\", */ f:parse_RK },\n\t/*::[*/0x0293/*::]*/: { /* n:\"Style\", */ },\n\t/*::[*/0x0418/*::]*/: { /* n:\"BigName\", */ },\n\t/*::[*/0x041e/*::]*/: { /* n:\"Format\", */ f:parse_Format },\n\t/*::[*/0x043c/*::]*/: { /* n:\"ContinueBigName\", */ },\n\t/*::[*/0x04bc/*::]*/: { /* n:\"ShrFmla\", */ f:parse_ShrFmla },\n\t/*::[*/0x0800/*::]*/: { /* n:\"HLinkTooltip\", */ f:parse_HLinkTooltip },\n\t/*::[*/0x0801/*::]*/: { /* n:\"WebPub\", */ },\n\t/*::[*/0x0802/*::]*/: { /* n:\"QsiSXTag\", */ },\n\t/*::[*/0x0803/*::]*/: { /* n:\"DBQueryExt\", */ },\n\t/*::[*/0x0804/*::]*/: { /* n:\"ExtString\", */ },\n\t/*::[*/0x0805/*::]*/: { /* n:\"TxtQry\", */ },\n\t/*::[*/0x0806/*::]*/: { /* n:\"Qsir\", */ },\n\t/*::[*/0x0807/*::]*/: { /* n:\"Qsif\", */ },\n\t/*::[*/0x0808/*::]*/: { /* n:\"RRDTQSIF\", */ },\n\t/*::[*/0x0809/*::]*/: { /* n:\"BOF\", */ f:parse_BOF },\n\t/*::[*/0x080a/*::]*/: { /* n:\"OleDbConn\", */ },\n\t/*::[*/0x080b/*::]*/: { /* n:\"WOpt\", */ },\n\t/*::[*/0x080c/*::]*/: { /* n:\"SXViewEx\", */ },\n\t/*::[*/0x080d/*::]*/: { /* n:\"SXTH\", */ },\n\t/*::[*/0x080e/*::]*/: { /* n:\"SXPIEx\", */ },\n\t/*::[*/0x080f/*::]*/: { /* n:\"SXVDTEx\", */ },\n\t/*::[*/0x0810/*::]*/: { /* n:\"SXViewEx9\", */ },\n\t/*::[*/0x0812/*::]*/: { /* n:\"ContinueFrt\", */ },\n\t/*::[*/0x0813/*::]*/: { /* n:\"RealTimeData\", */ },\n\t/*::[*/0x0850/*::]*/: { /* n:\"ChartFrtInfo\", */ },\n\t/*::[*/0x0851/*::]*/: { /* n:\"FrtWrapper\", */ },\n\t/*::[*/0x0852/*::]*/: { /* n:\"StartBlock\", */ },\n\t/*::[*/0x0853/*::]*/: { /* n:\"EndBlock\", */ },\n\t/*::[*/0x0854/*::]*/: { /* n:\"StartObject\", */ },\n\t/*::[*/0x0855/*::]*/: { /* n:\"EndObject\", */ },\n\t/*::[*/0x0856/*::]*/: { /* n:\"CatLab\", */ },\n\t/*::[*/0x0857/*::]*/: { /* n:\"YMult\", */ },\n\t/*::[*/0x0858/*::]*/: { /* n:\"SXViewLink\", */ },\n\t/*::[*/0x0859/*::]*/: { /* n:\"PivotChartBits\", */ },\n\t/*::[*/0x085a/*::]*/: { /* n:\"FrtFontList\", */ },\n\t/*::[*/0x0862/*::]*/: { /* n:\"SheetExt\", */ },\n\t/*::[*/0x0863/*::]*/: { /* n:\"BookExt\", */ r:12},\n\t/*::[*/0x0864/*::]*/: { /* n:\"SXAddl\", */ },\n\t/*::[*/0x0865/*::]*/: { /* n:\"CrErr\", */ },\n\t/*::[*/0x0866/*::]*/: { /* n:\"HFPicture\", */ },\n\t/*::[*/0x0867/*::]*/: { /* n:\"FeatHdr\", */ f:parsenoop2 },\n\t/*::[*/0x0868/*::]*/: { /* n:\"Feat\", */ },\n\t/*::[*/0x086a/*::]*/: { /* n:\"DataLabExt\", */ },\n\t/*::[*/0x086b/*::]*/: { /* n:\"DataLabExtContents\", */ },\n\t/*::[*/0x086c/*::]*/: { /* n:\"CellWatch\", */ },\n\t/*::[*/0x0871/*::]*/: { /* n:\"FeatHdr11\", */ },\n\t/*::[*/0x0872/*::]*/: { /* n:\"Feature11\", */ },\n\t/*::[*/0x0874/*::]*/: { /* n:\"DropDownObjIds\", */ },\n\t/*::[*/0x0875/*::]*/: { /* n:\"ContinueFrt11\", */ },\n\t/*::[*/0x0876/*::]*/: { /* n:\"DConn\", */ },\n\t/*::[*/0x0877/*::]*/: { /* n:\"List12\", */ },\n\t/*::[*/0x0878/*::]*/: { /* n:\"Feature12\", */ },\n\t/*::[*/0x0879/*::]*/: { /* n:\"CondFmt12\", */ },\n\t/*::[*/0x087a/*::]*/: { /* n:\"CF12\", */ },\n\t/*::[*/0x087b/*::]*/: { /* n:\"CFEx\", */ },\n\t/*::[*/0x087c/*::]*/: { /* n:\"XFCRC\", */ f:parse_XFCRC, r:12 },\n\t/*::[*/0x087d/*::]*/: { /* n:\"XFExt\", */ f:parse_XFExt, r:12 },\n\t/*::[*/0x087e/*::]*/: { /* n:\"AutoFilter12\", */ },\n\t/*::[*/0x087f/*::]*/: { /* n:\"ContinueFrt12\", */ },\n\t/*::[*/0x0884/*::]*/: { /* n:\"MDTInfo\", */ },\n\t/*::[*/0x0885/*::]*/: { /* n:\"MDXStr\", */ },\n\t/*::[*/0x0886/*::]*/: { /* n:\"MDXTuple\", */ },\n\t/*::[*/0x0887/*::]*/: { /* n:\"MDXSet\", */ },\n\t/*::[*/0x0888/*::]*/: { /* n:\"MDXProp\", */ },\n\t/*::[*/0x0889/*::]*/: { /* n:\"MDXKPI\", */ },\n\t/*::[*/0x088a/*::]*/: { /* n:\"MDB\", */ },\n\t/*::[*/0x088b/*::]*/: { /* n:\"PLV\", */ },\n\t/*::[*/0x088c/*::]*/: { /* n:\"Compat12\", */ f:parsebool, r:12 },\n\t/*::[*/0x088d/*::]*/: { /* n:\"DXF\", */ },\n\t/*::[*/0x088e/*::]*/: { /* n:\"TableStyles\", */ r:12 },\n\t/*::[*/0x088f/*::]*/: { /* n:\"TableStyle\", */ },\n\t/*::[*/0x0890/*::]*/: { /* n:\"TableStyleElement\", */ },\n\t/*::[*/0x0892/*::]*/: { /* n:\"StyleExt\", */ },\n\t/*::[*/0x0893/*::]*/: { /* n:\"NamePublish\", */ },\n\t/*::[*/0x0894/*::]*/: { /* n:\"NameCmt\", */ f:parse_NameCmt, r:12 },\n\t/*::[*/0x0895/*::]*/: { /* n:\"SortData\", */ },\n\t/*::[*/0x0896/*::]*/: { /* n:\"Theme\", */ f:parse_Theme, r:12 },\n\t/*::[*/0x0897/*::]*/: { /* n:\"GUIDTypeLib\", */ },\n\t/*::[*/0x0898/*::]*/: { /* n:\"FnGrp12\", */ },\n\t/*::[*/0x0899/*::]*/: { /* n:\"NameFnGrp12\", */ },\n\t/*::[*/0x089a/*::]*/: { /* n:\"MTRSettings\", */ f:parse_MTRSettings, r:12 },\n\t/*::[*/0x089b/*::]*/: { /* n:\"CompressPictures\", */ f:parsenoop2 },\n\t/*::[*/0x089c/*::]*/: { /* n:\"HeaderFooter\", */ },\n\t/*::[*/0x089d/*::]*/: { /* n:\"CrtLayout12\", */ },\n\t/*::[*/0x089e/*::]*/: { /* n:\"CrtMlFrt\", */ },\n\t/*::[*/0x089f/*::]*/: { /* n:\"CrtMlFrtContinue\", */ },\n\t/*::[*/0x08a3/*::]*/: { /* n:\"ForceFullCalculation\", */ f:parse_ForceFullCalculation },\n\t/*::[*/0x08a4/*::]*/: { /* n:\"ShapePropsStream\", */ },\n\t/*::[*/0x08a5/*::]*/: { /* n:\"TextPropsStream\", */ },\n\t/*::[*/0x08a6/*::]*/: { /* n:\"RichTextStream\", */ },\n\t/*::[*/0x08a7/*::]*/: { /* n:\"CrtLayout12A\", */ },\n\t/*::[*/0x1001/*::]*/: { /* n:\"Units\", */ },\n\t/*::[*/0x1002/*::]*/: { /* n:\"Chart\", */ },\n\t/*::[*/0x1003/*::]*/: { /* n:\"Series\", */ },\n\t/*::[*/0x1006/*::]*/: { /* n:\"DataFormat\", */ },\n\t/*::[*/0x1007/*::]*/: { /* n:\"LineFormat\", */ },\n\t/*::[*/0x1009/*::]*/: { /* n:\"MarkerFormat\", */ },\n\t/*::[*/0x100a/*::]*/: { /* n:\"AreaFormat\", */ },\n\t/*::[*/0x100b/*::]*/: { /* n:\"PieFormat\", */ },\n\t/*::[*/0x100c/*::]*/: { /* n:\"AttachedLabel\", */ },\n\t/*::[*/0x100d/*::]*/: { /* n:\"SeriesText\", */ },\n\t/*::[*/0x1014/*::]*/: { /* n:\"ChartFormat\", */ },\n\t/*::[*/0x1015/*::]*/: { /* n:\"Legend\", */ },\n\t/*::[*/0x1016/*::]*/: { /* n:\"SeriesList\", */ },\n\t/*::[*/0x1017/*::]*/: { /* n:\"Bar\", */ },\n\t/*::[*/0x1018/*::]*/: { /* n:\"Line\", */ },\n\t/*::[*/0x1019/*::]*/: { /* n:\"Pie\", */ },\n\t/*::[*/0x101a/*::]*/: { /* n:\"Area\", */ },\n\t/*::[*/0x101b/*::]*/: { /* n:\"Scatter\", */ },\n\t/*::[*/0x101c/*::]*/: { /* n:\"CrtLine\", */ },\n\t/*::[*/0x101d/*::]*/: { /* n:\"Axis\", */ },\n\t/*::[*/0x101e/*::]*/: { /* n:\"Tick\", */ },\n\t/*::[*/0x101f/*::]*/: { /* n:\"ValueRange\", */ },\n\t/*::[*/0x1020/*::]*/: { /* n:\"CatSerRange\", */ },\n\t/*::[*/0x1021/*::]*/: { /* n:\"AxisLine\", */ },\n\t/*::[*/0x1022/*::]*/: { /* n:\"CrtLink\", */ },\n\t/*::[*/0x1024/*::]*/: { /* n:\"DefaultText\", */ },\n\t/*::[*/0x1025/*::]*/: { /* n:\"Text\", */ },\n\t/*::[*/0x1026/*::]*/: { /* n:\"FontX\", */ f:parseuint16 },\n\t/*::[*/0x1027/*::]*/: { /* n:\"ObjectLink\", */ },\n\t/*::[*/0x1032/*::]*/: { /* n:\"Frame\", */ },\n\t/*::[*/0x1033/*::]*/: { /* n:\"Begin\", */ },\n\t/*::[*/0x1034/*::]*/: { /* n:\"End\", */ },\n\t/*::[*/0x1035/*::]*/: { /* n:\"PlotArea\", */ },\n\t/*::[*/0x103a/*::]*/: { /* n:\"Chart3d\", */ },\n\t/*::[*/0x103c/*::]*/: { /* n:\"PicF\", */ },\n\t/*::[*/0x103d/*::]*/: { /* n:\"DropBar\", */ },\n\t/*::[*/0x103e/*::]*/: { /* n:\"Radar\", */ },\n\t/*::[*/0x103f/*::]*/: { /* n:\"Surf\", */ },\n\t/*::[*/0x1040/*::]*/: { /* n:\"RadarArea\", */ },\n\t/*::[*/0x1041/*::]*/: { /* n:\"AxisParent\", */ },\n\t/*::[*/0x1043/*::]*/: { /* n:\"LegendException\", */ },\n\t/*::[*/0x1044/*::]*/: { /* n:\"ShtProps\", */ f:parse_ShtProps },\n\t/*::[*/0x1045/*::]*/: { /* n:\"SerToCrt\", */ },\n\t/*::[*/0x1046/*::]*/: { /* n:\"AxesUsed\", */ },\n\t/*::[*/0x1048/*::]*/: { /* n:\"SBaseRef\", */ },\n\t/*::[*/0x104a/*::]*/: { /* n:\"SerParent\", */ },\n\t/*::[*/0x104b/*::]*/: { /* n:\"SerAuxTrend\", */ },\n\t/*::[*/0x104e/*::]*/: { /* n:\"IFmtRecord\", */ },\n\t/*::[*/0x104f/*::]*/: { /* n:\"Pos\", */ },\n\t/*::[*/0x1050/*::]*/: { /* n:\"AlRuns\", */ },\n\t/*::[*/0x1051/*::]*/: { /* n:\"BRAI\", */ },\n\t/*::[*/0x105b/*::]*/: { /* n:\"SerAuxErrBar\", */ },\n\t/*::[*/0x105c/*::]*/: { /* n:\"ClrtClient\", */ f:parse_ClrtClient },\n\t/*::[*/0x105d/*::]*/: { /* n:\"SerFmt\", */ },\n\t/*::[*/0x105f/*::]*/: { /* n:\"Chart3DBarShape\", */ },\n\t/*::[*/0x1060/*::]*/: { /* n:\"Fbi\", */ },\n\t/*::[*/0x1061/*::]*/: { /* n:\"BopPop\", */ },\n\t/*::[*/0x1062/*::]*/: { /* n:\"AxcExt\", */ },\n\t/*::[*/0x1063/*::]*/: { /* n:\"Dat\", */ },\n\t/*::[*/0x1064/*::]*/: { /* n:\"PlotGrowth\", */ },\n\t/*::[*/0x1065/*::]*/: { /* n:\"SIIndex\", */ },\n\t/*::[*/0x1066/*::]*/: { /* n:\"GelFrame\", */ },\n\t/*::[*/0x1067/*::]*/: { /* n:\"BopPopCustom\", */ },\n\t/*::[*/0x1068/*::]*/: { /* n:\"Fbi2\", */ },\n\n\t/*::[*/0x0000/*::]*/: { /* n:\"Dimensions\", */ f:parse_Dimensions },\n\t/*::[*/0x0001/*::]*/: { /* n:\"BIFF2BLANK\", */ },\n\t/*::[*/0x0002/*::]*/: { /* n:\"BIFF2INT\", */ f:parse_BIFF2INT },\n\t/*::[*/0x0003/*::]*/: { /* n:\"BIFF2NUM\", */ f:parse_BIFF2NUM },\n\t/*::[*/0x0004/*::]*/: { /* n:\"BIFF2STR\", */ f:parse_BIFF2STR },\n\t/*::[*/0x0005/*::]*/: { /* n:\"BoolErr\", */ f:parse_BoolErr },\n\t/*::[*/0x0007/*::]*/: { /* n:\"String\", */ f:parse_BIFF2STRING },\n\t/*::[*/0x0008/*::]*/: { /* n:\"BIFF2ROW\", */ },\n\t/*::[*/0x0009/*::]*/: { /* n:\"BOF\", */ f:parse_BOF },\n\t/*::[*/0x000b/*::]*/: { /* n:\"Index\", */ },\n\t/*::[*/0x0016/*::]*/: { /* n:\"ExternCount\", */ f:parseuint16 },\n\t/*::[*/0x001e/*::]*/: { /* n:\"BIFF2FORMAT\", */ f:parse_BIFF2Format },\n\t/*::[*/0x001f/*::]*/: { /* n:\"BIFF2FMTCNT\", */ }, /* 16-bit cnt of BIFF2FORMAT records */\n\t/*::[*/0x0020/*::]*/: { /* n:\"BIFF2COLINFO\", */ },\n\t/*::[*/0x0021/*::]*/: { /* n:\"Array\", */ f:parse_Array },\n\t/*::[*/0x0024/*::]*/: { /* n:\"COLWIDTH\", */ },\n\t/*::[*/0x0025/*::]*/: { /* n:\"DefaultRowHeight\", */ f:parse_DefaultRowHeight },\n\t// 0x2c ??\n\t// 0x2d ??\n\t// 0x2e ??\n\t// 0x30 FONTCOUNT: number of fonts\n\t/*::[*/0x0032/*::]*/: { /* n:\"BIFF2FONTXTRA\", */ f:parse_BIFF2FONTXTRA },\n\t// 0x35: INFOOPTS\n\t// 0x36: TABLE (BIFF2 only)\n\t// 0x37: TABLE2 (BIFF2 only)\n\t// 0x38: WNDESK\n\t// 0x39 ??\n\t// 0x3a: BEGINPREF\n\t// 0x3b: ENDPREF\n\t/*::[*/0x003e/*::]*/: { /* n:\"BIFF2WINDOW2\", */ },\n\t// 0x3f ??\n\t// 0x46: SHOWSCROLL\n\t// 0x47: SHOWFORMULA\n\t// 0x48: STATUSBAR\n\t// 0x49: SHORTMENUS\n\t// 0x4A:\n\t// 0x4B:\n\t// 0x4C:\n\t// 0x4E:\n\t// 0x4F:\n\t// 0x58: TOOLBAR (BIFF3)\n\n\t/* - - - */\n\t/*::[*/0x0034/*::]*/: { /* n:\"DDEObjName\", */ },\n\t/*::[*/0x0043/*::]*/: { /* n:\"BIFF2XF\", */ },\n\t/*::[*/0x0044/*::]*/: { /* n:\"BIFF2XFINDEX\", */ f:parseuint16 },\n\t/*::[*/0x0045/*::]*/: { /* n:\"BIFF2FONTCLR\", */ },\n\t/*::[*/0x0056/*::]*/: { /* n:\"BIFF4FMTCNT\", */ }, /* 16-bit cnt, similar to BIFF2 */\n\t/*::[*/0x007e/*::]*/: { /* n:\"RK\", */ }, /* Not necessarily same as 0x027e */\n\t/*::[*/0x007f/*::]*/: { /* n:\"ImData\", */ f:parse_ImData },\n\t/*::[*/0x0087/*::]*/: { /* n:\"Addin\", */ },\n\t/*::[*/0x0088/*::]*/: { /* n:\"Edg\", */ },\n\t/*::[*/0x0089/*::]*/: { /* n:\"Pub\", */ },\n\t// 0x8A\n\t// 0x8B LH: alternate menu key flag (BIFF3/4)\n\t// 0x8E\n\t// 0x8F\n\t/*::[*/0x0091/*::]*/: { /* n:\"Sub\", */ },\n\t// 0x93 STYLE\n\t/*::[*/0x0094/*::]*/: { /* n:\"LHRecord\", */ },\n\t/*::[*/0x0095/*::]*/: { /* n:\"LHNGraph\", */ },\n\t/*::[*/0x0096/*::]*/: { /* n:\"Sound\", */ },\n\t// 0xA2 FNPROTO: function prototypes (BIFF4)\n\t// 0xA3\n\t// 0xA8\n\t/*::[*/0x00a9/*::]*/: { /* n:\"CoordList\", */ },\n\t/*::[*/0x00ab/*::]*/: { /* n:\"GCW\", */ },\n\t/*::[*/0x00bc/*::]*/: { /* n:\"ShrFmla\", */ }, /* Not necessarily same as 0x04bc */\n\t/*::[*/0x00bf/*::]*/: { /* n:\"ToolbarHdr\", */ },\n\t/*::[*/0x00c0/*::]*/: { /* n:\"ToolbarEnd\", */ },\n\t/*::[*/0x00c2/*::]*/: { /* n:\"AddMenu\", */ },\n\t/*::[*/0x00c3/*::]*/: { /* n:\"DelMenu\", */ },\n\t/*::[*/0x00d6/*::]*/: { /* n:\"RString\", */ f:parse_RString },\n\t/*::[*/0x00df/*::]*/: { /* n:\"UDDesc\", */ },\n\t/*::[*/0x00ea/*::]*/: { /* n:\"TabIdConf\", */ },\n\t/*::[*/0x0162/*::]*/: { /* n:\"XL5Modify\", */ },\n\t/*::[*/0x01a5/*::]*/: { /* n:\"FileSharing2\", */ },\n\t/*::[*/0x0206/*::]*/: { /* n:\"Formula\", */ f:parse_Formula },\n\t/*::[*/0x0209/*::]*/: { /* n:\"BOF\", */ f:parse_BOF },\n\t/*::[*/0x0218/*::]*/: { /* n:\"Lbl\", */ f:parse_Lbl },\n\t/*::[*/0x0223/*::]*/: { /* n:\"ExternName\", */ f:parse_ExternName },\n\t/*::[*/0x0231/*::]*/: { /* n:\"Font\", */ },\n\t/*::[*/0x0243/*::]*/: { /* n:\"BIFF3XF\", */ },\n\t/*::[*/0x0406/*::]*/: { /* n:\"Formula\", */ f:parse_Formula },\n\t/*::[*/0x0409/*::]*/: { /* n:\"BOF\", */ f:parse_BOF },\n\t/*::[*/0x0443/*::]*/: { /* n:\"BIFF4XF\", */ },\n\t/*::[*/0x086d/*::]*/: { /* n:\"FeatInfo\", */ },\n\t/*::[*/0x0873/*::]*/: { /* n:\"FeatInfo11\", */ },\n\t/*::[*/0x0881/*::]*/: { /* n:\"SXAddl12\", */ },\n\t/*::[*/0x08c0/*::]*/: { /* n:\"AutoWebPub\", */ },\n\t/*::[*/0x08c1/*::]*/: { /* n:\"ListObj\", */ },\n\t/*::[*/0x08c2/*::]*/: { /* n:\"ListField\", */ },\n\t/*::[*/0x08c3/*::]*/: { /* n:\"ListDV\", */ },\n\t/*::[*/0x08c4/*::]*/: { /* n:\"ListCondFmt\", */ },\n\t/*::[*/0x08c5/*::]*/: { /* n:\"ListCF\", */ },\n\t/*::[*/0x08c6/*::]*/: { /* n:\"FMQry\", */ },\n\t/*::[*/0x08c7/*::]*/: { /* n:\"FMSQry\", */ },\n\t/*::[*/0x08c8/*::]*/: { /* n:\"PLV\", */ },\n\t/*::[*/0x08c9/*::]*/: { /* n:\"LnExt\", */ },\n\t/*::[*/0x08ca/*::]*/: { /* n:\"MkrExt\", */ },\n\t/*::[*/0x08cb/*::]*/: { /* n:\"CrtCoopt\", */ },\n\t/*::[*/0x08d6/*::]*/: { /* n:\"FRTArchId$\", */ r:12 },\n\n\t/*::[*/0x7262/*::]*/: {}\n};\n\nfunction write_biff_rec(ba/*:BufArray*/, type/*:number*/, payload, length/*:?number*/)/*:void*/ {\n\tvar t/*:number*/ = type;\n\tif(isNaN(t)) return;\n\tvar len = length || (payload||[]).length || 0;\n\tvar o = ba.next(4);\n\to.write_shift(2, t);\n\to.write_shift(2, len);\n\tif(/*:: len != null &&*/len > 0 && is_buf(payload)) ba.push(payload);\n}\n\nfunction write_biff_continue(ba/*:BufArray*/, type/*:number*/, payload, length/*:?number*/)/*:void*/ {\n\tvar len = length || (payload||[]).length || 0;\n\tif(len <= 8224) return write_biff_rec(ba, type, payload, len);\n\tvar t = type;\n\tif(isNaN(t)) return;\n\tvar parts = payload.parts || [], sidx = 0;\n\tvar i = 0, w = 0;\n\twhile(w + (parts[sidx] || 8224) <= 8224) { w+= (parts[sidx] || 8224); sidx++; }\n\tvar o = ba.next(4);\n\to.write_shift(2, t);\n\to.write_shift(2, w);\n\tba.push(payload.slice(i, i + w));\n\ti += w;\n\twhile(i < len) {\n\t\to = ba.next(4);\n\t\to.write_shift(2, 0x3c); // TODO: figure out correct continue type\n\t\tw = 0;\n\t\twhile(w + (parts[sidx] || 8224) <= 8224) { w+= (parts[sidx] || 8224); sidx++; }\n\t\to.write_shift(2, w);\n\t\tba.push(payload.slice(i, i+w)); i+= w;\n\t}\n}\n\nfunction write_BIFF2Cell(out, r/*:number*/, c/*:number*/) {\n\tif(!out) out = new_buf(7);\n\tout.write_shift(2, r);\n\tout.write_shift(2, c);\n\tout.write_shift(2, 0);\n\tout.write_shift(1, 0);\n\treturn out;\n}\n\nfunction write_BIFF2BERR(r/*:number*/, c/*:number*/, val, t/*:?string*/) {\n\tvar out = new_buf(9);\n\twrite_BIFF2Cell(out, r, c);\n\twrite_Bes(val, t || 'b', out);\n\treturn out;\n}\n\n/* TODO: codepage, large strings */\nfunction write_BIFF2LABEL(r/*:number*/, c/*:number*/, val) {\n\tvar out = new_buf(8 + 2*val.length);\n\twrite_BIFF2Cell(out, r, c);\n\tout.write_shift(1, val.length);\n\tout.write_shift(val.length, val, 'sbcs');\n\treturn out.l < out.length ? out.slice(0, out.l) : out;\n}\n\nfunction write_ws_biff2_cell(ba/*:BufArray*/, cell/*:Cell*/, R/*:number*/, C/*:number*//*::, opts*/) {\n\tif(cell.v != null) switch(cell.t) {\n\t\tcase 'd': case 'n':\n\t\t\tvar v = cell.t == 'd' ? datenum(parseDate(cell.v)) : cell.v;\n\t\t\tif((v == (v|0)) && (v >= 0) && (v < 65536))\n\t\t\t\twrite_biff_rec(ba, 0x0002, write_BIFF2INT(R, C, v));\n\t\t\telse\n\t\t\t\twrite_biff_rec(ba, 0x0003, write_BIFF2NUM(R,C, v));\n\t\t\treturn;\n\t\tcase 'b': case 'e': write_biff_rec(ba, 0x0005, write_BIFF2BERR(R, C, cell.v, cell.t)); return;\n\t\t/* TODO: codepage, sst */\n\t\tcase 's': case 'str':\n\t\t\twrite_biff_rec(ba, 0x0004, write_BIFF2LABEL(R, C, (cell.v||\"\").slice(0,255)));\n\t\t\treturn;\n\t}\n\twrite_biff_rec(ba, 0x0001, write_BIFF2Cell(null, R, C));\n}\n\nfunction write_ws_biff2(ba/*:BufArray*/, ws/*:Worksheet*/, idx/*:number*/, opts/*::, wb:Workbook*/) {\n\tvar dense = Array.isArray(ws);\n\tvar range = safe_decode_range(ws['!ref'] || \"A1\"), ref/*:string*/, rr = \"\", cols/*:Array<string>*/ = [];\n\tif(range.e.c > 0xFF || range.e.r > 0x3FFF) {\n\t\tif(opts.WTF) throw new Error(\"Range \" + (ws['!ref'] || \"A1\") + \" exceeds format limit A1:IV16384\");\n\t\trange.e.c = Math.min(range.e.c, 0xFF);\n\t\trange.e.r = Math.min(range.e.c, 0x3FFF);\n\t\tref = encode_range(range);\n\t}\n\tfor(var R = range.s.r; R <= range.e.r; ++R) {\n\t\trr = encode_row(R);\n\t\tfor(var C = range.s.c; C <= range.e.c; ++C) {\n\t\t\tif(R === range.s.r) cols[C] = encode_col(C);\n\t\t\tref = cols[C] + rr;\n\t\t\tvar cell = dense ? (ws[R]||[])[C] : ws[ref];\n\t\t\tif(!cell) continue;\n\t\t\t/* write cell */\n\t\t\twrite_ws_biff2_cell(ba, cell, R, C, opts);\n\t\t}\n\t}\n}\n\n/* Based on test files */\nfunction write_biff2_buf(wb/*:Workbook*/, opts/*:WriteOpts*/) {\n\tvar o = opts || {};\n\tif(DENSE != null && o.dense == null) o.dense = DENSE;\n\tvar ba = buf_array();\n\tvar idx = 0;\n\tfor(var i=0;i<wb.SheetNames.length;++i) if(wb.SheetNames[i] == o.sheet) idx=i;\n\tif(idx == 0 && !!o.sheet && wb.SheetNames[0] != o.sheet) throw new Error(\"Sheet not found: \" + o.sheet);\n\twrite_biff_rec(ba, (o.biff == 4 ? 0x0409 : (o.biff == 3 ? 0x0209 : 0x0009)), write_BOF(wb, 0x10, o));\n\t/* ... */\n\twrite_ws_biff2(ba, wb.Sheets[wb.SheetNames[idx]], idx, o, wb);\n\t/* ... */\n\twrite_biff_rec(ba, 0x000A);\n\treturn ba.end();\n}\n\nfunction write_FONTS_biff8(ba, data, opts) {\n\twrite_biff_rec(ba, 0x0031 /* Font */, write_Font({\n\t\tsz:12,\n\t\tcolor: {theme:1},\n\t\tname: \"Arial\",\n\t\tfamily: 2,\n\t\tscheme: \"minor\"\n\t}, opts));\n}\n\n\nfunction write_FMTS_biff8(ba, NF/*:?SSFTable*/, opts) {\n\tif(!NF) return;\n\t[[5,8],[23,26],[41,44],[/*63*/50,/*66],[164,*/392]].forEach(function(r) {\n\t\t/*:: if(!NF) return; */\n\t\tfor(var i = r[0]; i <= r[1]; ++i) if(NF[i] != null) write_biff_rec(ba, 0x041E /* Format */, write_Format(i, NF[i], opts));\n\t});\n}\n\nfunction write_FEAT(ba, ws) {\n\t/* [MS-XLS] 2.4.112 */\n\tvar o = new_buf(19);\n\to.write_shift(4, 0x867); o.write_shift(4, 0); o.write_shift(4, 0);\n\to.write_shift(2, 3); o.write_shift(1, 1); o.write_shift(4, 0);\n\twrite_biff_rec(ba, 0x0867 /* FeatHdr */, o);\n\t/* [MS-XLS] 2.4.111 */\n\to = new_buf(39);\n\to.write_shift(4, 0x868); o.write_shift(4, 0); o.write_shift(4, 0);\n\to.write_shift(2, 3); o.write_shift(1, 0); o.write_shift(4, 0);\n\to.write_shift(2, 1); o.write_shift(4, 4); o.write_shift(2, 0);\n\twrite_Ref8U(safe_decode_range(ws['!ref']||\"A1\"), o);\n\to.write_shift(4, 4);\n\twrite_biff_rec(ba, 0x0868 /* Feat */, o);\n}\n\nfunction write_CELLXFS_biff8(ba, opts) {\n\tfor(var i = 0; i < 16; ++i) write_biff_rec(ba, 0x00e0 /* XF */, write_XF({numFmtId:0, style:true}, 0, opts));\n\topts.cellXfs.forEach(function(c) {\n\t\twrite_biff_rec(ba, 0x00e0 /* XF */, write_XF(c, 0, opts));\n\t});\n}\n\nfunction write_ws_biff8_hlinks(ba/*:BufArray*/, ws) {\n\tfor(var R=0; R<ws['!links'].length; ++R) {\n\t\tvar HL = ws['!links'][R];\n\t\twrite_biff_rec(ba, 0x01b8 /* HLink */, write_HLink(HL));\n\t\tif(HL[1].Tooltip) write_biff_rec(ba, 0x0800 /* HLinkTooltip */, write_HLinkTooltip(HL));\n\t}\n\tdelete ws['!links'];\n}\n\nfunction write_ws_cols_biff8(ba, cols) {\n\tif(!cols) return;\n\tvar cnt = 0;\n\tcols.forEach(function(col, idx) {\n\t\tif(++cnt <= 256 && col) {\n\t\t\twrite_biff_rec(ba, 0x007d /* ColInfo */, write_ColInfo(col_obj_w(idx, col), idx));\n\t\t}\n\t});\n}\n\nfunction write_ws_biff8_cell(ba/*:BufArray*/, cell/*:Cell*/, R/*:number*/, C/*:number*/, opts) {\n\tvar os = 16 + get_cell_style(opts.cellXfs, cell, opts);\n\tif(cell.v == null && !cell.bf) {\n\t\twrite_biff_rec(ba, 0x0201 /* Blank */, write_XLSCell(R, C, os));\n\t\treturn;\n\t}\n\tif(cell.bf) write_biff_rec(ba, 0x0006 /* Formula */, write_Formula(cell, R, C, opts, os));\n\telse switch(cell.t) {\n\t\tcase 'd': case 'n':\n\t\t\tvar v = cell.t == 'd' ? datenum(parseDate(cell.v)) : cell.v;\n\t\t\t/* TODO: emit RK as appropriate */\n\t\t\twrite_biff_rec(ba, 0x0203 /* Number */, write_Number(R, C, v, os, opts));\n\t\t\tbreak;\n\t\tcase 'b': case 'e':\n\t\t\twrite_biff_rec(ba, 0x0205 /* BoolErr */, write_BoolErr(R, C, cell.v, os, opts, cell.t));\n\t\t\tbreak;\n\t\t/* TODO: codepage, sst */\n\t\tcase 's': case 'str':\n\t\t\tif(opts.bookSST) {\n\t\t\t\tvar isst = get_sst_id(opts.Strings, cell.v, opts.revStrings);\n\t\t\t\twrite_biff_rec(ba, 0x00fd /* LabelSst */, write_LabelSst(R, C, isst, os, opts));\n\t\t\t} else write_biff_rec(ba, 0x0204 /* Label */, write_Label(R, C, (cell.v||\"\").slice(0,255), os, opts));\n\t\t\tbreak;\n\t\tdefault:\n\t\t\twrite_biff_rec(ba, 0x0201 /* Blank */, write_XLSCell(R, C, os));\n\t}\n}\n\n/* [MS-XLS] 2.1.7.20.5 */\nfunction write_ws_biff8(idx/*:number*/, opts, wb/*:Workbook*/) {\n\tvar ba = buf_array();\n\tvar s = wb.SheetNames[idx], ws = wb.Sheets[s] || {};\n\tvar _WB/*:WBWBProps*/ = ((wb||{}).Workbook||{}/*:any*/);\n\tvar _sheet/*:WBWSProp*/ = ((_WB.Sheets||[])[idx]||{}/*:any*/);\n\tvar dense = Array.isArray(ws);\n\tvar b8 = opts.biff == 8;\n\tvar ref/*:string*/, rr = \"\", cols/*:Array<string>*/ = [];\n\tvar range = safe_decode_range(ws['!ref'] || \"A1\");\n\tvar MAX_ROWS = b8 ? 65536 : 16384;\n\tif(range.e.c > 0xFF || range.e.r >= MAX_ROWS) {\n\t\tif(opts.WTF) throw new Error(\"Range \" + (ws['!ref'] || \"A1\") + \" exceeds format limit A1:IV16384\");\n\t\trange.e.c = Math.min(range.e.c, 0xFF);\n\t\trange.e.r = Math.min(range.e.c, MAX_ROWS-1);\n\t}\n\n\twrite_biff_rec(ba, 0x0809, write_BOF(wb, 0x10, opts));\n\t/* [Uncalced] Index */\n\twrite_biff_rec(ba, 0x000d /* CalcMode */, writeuint16(1));\n\twrite_biff_rec(ba, 0x000c /* CalcCount */, writeuint16(100));\n\twrite_biff_rec(ba, 0x000f /* CalcRefMode */, writebool(true));\n\twrite_biff_rec(ba, 0x0011 /* CalcIter */, writebool(false));\n\twrite_biff_rec(ba, 0x0010 /* CalcDelta */, write_Xnum(0.001));\n\twrite_biff_rec(ba, 0x005f /* CalcSaveRecalc */, writebool(true));\n\twrite_biff_rec(ba, 0x002a /* PrintRowCol */, writebool(false));\n\twrite_biff_rec(ba, 0x002b /* PrintGrid */, writebool(false));\n\twrite_biff_rec(ba, 0x0082 /* GridSet */, writeuint16(1));\n\twrite_biff_rec(ba, 0x0080 /* Guts */, write_Guts([0,0]));\n\t/* DefaultRowHeight WsBool [Sync] [LPr] [HorizontalPageBreaks] [VerticalPageBreaks] */\n\t/* Header (string) */\n\t/* Footer (string) */\n\twrite_biff_rec(ba, 0x0083 /* HCenter */, writebool(false));\n\twrite_biff_rec(ba, 0x0084 /* VCenter */, writebool(false));\n\t/* ... */\n\tif(b8) write_ws_cols_biff8(ba, ws[\"!cols\"]);\n\t/* ... */\n\twrite_biff_rec(ba, 0x200, write_Dimensions(range, opts));\n\t/* ... */\n\n\tif(b8) ws['!links'] = [];\n\tfor(var R = range.s.r; R <= range.e.r; ++R) {\n\t\trr = encode_row(R);\n\t\tfor(var C = range.s.c; C <= range.e.c; ++C) {\n\t\t\tif(R === range.s.r) cols[C] = encode_col(C);\n\t\t\tref = cols[C] + rr;\n\t\t\tvar cell = dense ? (ws[R]||[])[C] : ws[ref];\n\t\t\tif(!cell) continue;\n\t\t\t/* write cell */\n\t\t\twrite_ws_biff8_cell(ba, cell, R, C, opts);\n\t\t\tif(b8 && cell.l) ws['!links'].push([ref, cell.l]);\n\t\t}\n\t}\n\tvar cname/*:string*/ = _sheet.CodeName || _sheet.name || s;\n\t/* ... */\n\tif(b8) write_biff_rec(ba, 0x023e /* Window2 */, write_Window2((_WB.Views||[])[0]));\n\t/* ... */\n\tif(b8 && (ws['!merges']||[]).length) write_biff_rec(ba, 0x00e5 /* MergeCells */, write_MergeCells(ws['!merges']));\n\t/* [LRng] *QUERYTABLE [PHONETICINFO] CONDFMTS */\n\tif(b8) write_ws_biff8_hlinks(ba, ws);\n\t/* [DVAL] */\n\twrite_biff_rec(ba, 0x01ba /* CodeName */, write_XLUnicodeString(cname, opts));\n\t/* *WebPub *CellWatch [SheetExt] */\n\tif(b8) write_FEAT(ba, ws);\n\t/* *FEAT11 *RECORD12 */\n\twrite_biff_rec(ba, 0x000a /* EOF */);\n\treturn ba.end();\n}\n\n/* [MS-XLS] 2.1.7.20.3 */\nfunction write_biff8_global(wb/*:Workbook*/, bufs, opts/*:WriteOpts*/) {\n\tvar A = buf_array();\n\tvar _WB/*:WBWBProps*/ = ((wb||{}).Workbook||{}/*:any*/);\n\tvar _sheets/*:Array<WBWSProp>*/ = (_WB.Sheets||[]);\n\tvar _wb/*:WBProps*/ = /*::((*/_WB.WBProps||{/*::CodeName:\"ThisWorkbook\"*/}/*:: ):any)*/;\n\tvar b8 = opts.biff == 8, b5 = opts.biff == 5;\n\twrite_biff_rec(A, 0x0809, write_BOF(wb, 0x05, opts));\n\tif(opts.bookType == \"xla\") write_biff_rec(A, 0x0087 /* Addin */);\n\twrite_biff_rec(A, 0x00e1 /* InterfaceHdr */, b8 ? writeuint16(0x04b0) : null);\n\twrite_biff_rec(A, 0x00c1 /* Mms */, writezeroes(2));\n\tif(b5) write_biff_rec(A, 0x00bf /* ToolbarHdr */);\n\tif(b5) write_biff_rec(A, 0x00c0 /* ToolbarEnd */);\n\twrite_biff_rec(A, 0x00e2 /* InterfaceEnd */);\n\twrite_biff_rec(A, 0x005c /* WriteAccess */, write_WriteAccess(\"SheetJS\", opts));\n\t/* [FileSharing] */\n\twrite_biff_rec(A, 0x0042 /* CodePage */, writeuint16(b8 ? 0x04b0 : 0x04E4));\n\t/* *2047 Lel */\n\tif(b8) write_biff_rec(A, 0x0161 /* DSF */, writeuint16(0));\n\tif(b8) write_biff_rec(A, 0x01c0 /* Excel9File */);\n\twrite_biff_rec(A, 0x013d /* RRTabId */, write_RRTabId(wb.SheetNames.length));\n\tif(b8 && wb.vbaraw) write_biff_rec(A, 0x00d3 /* ObProj */);\n\t/* [ObNoMacros] */\n\tif(b8 && wb.vbaraw) {\n\t\tvar cname/*:string*/ = _wb.CodeName || \"ThisWorkbook\";\n\t\twrite_biff_rec(A, 0x01ba /* CodeName */, write_XLUnicodeString(cname, opts));\n\t}\n\twrite_biff_rec(A, 0x009c /* BuiltInFnGroupCount */, writeuint16(0x11));\n\t/* *FnGroupName *FnGrp12 */\n\t/* *Lbl */\n\t/* [OleObjectSize] */\n\twrite_biff_rec(A, 0x0019 /* WinProtect */, writebool(false));\n\twrite_biff_rec(A, 0x0012 /* Protect */, writebool(false));\n\twrite_biff_rec(A, 0x0013 /* Password */, writeuint16(0));\n\tif(b8) write_biff_rec(A, 0x01af /* Prot4Rev */, writebool(false));\n\tif(b8) write_biff_rec(A, 0x01bc /* Prot4RevPass */, writeuint16(0));\n\twrite_biff_rec(A, 0x003d /* Window1 */, write_Window1(opts));\n\twrite_biff_rec(A, 0x0040 /* Backup */, writebool(false));\n\twrite_biff_rec(A, 0x008d /* HideObj */, writeuint16(0));\n\twrite_biff_rec(A, 0x0022 /* Date1904 */, writebool(safe1904(wb)==\"true\"));\n\twrite_biff_rec(A, 0x000e /* CalcPrecision */, writebool(true));\n\tif(b8) write_biff_rec(A, 0x01b7 /* RefreshAll */, writebool(false));\n\twrite_biff_rec(A, 0x00DA /* BookBool */, writeuint16(0));\n\t/* ... */\n\twrite_FONTS_biff8(A, wb, opts);\n\twrite_FMTS_biff8(A, wb.SSF, opts);\n\twrite_CELLXFS_biff8(A, opts);\n\t/* ... */\n\tif(b8) write_biff_rec(A, 0x0160 /* UsesELFs */, writebool(false));\n\tvar a = A.end();\n\n\tvar C = buf_array();\n\t/* METADATA [MTRSettings] [ForceFullCalculation] */\n\tif(b8) write_biff_rec(C, 0x008C, write_Country());\n\t/* *SUPBOOK *LBL *RTD [RecalcId] *HFPicture *MSODRAWINGGROUP */\n\n\t/* BIFF8: [SST *Continue] ExtSST */\n\tif(b8 && opts.Strings) write_biff_continue(C, 0x00FC, write_SST(opts.Strings, opts));\n\n\t/* *WebPub [WOpt] [CrErr] [BookExt] *FeatHdr *DConn [THEME] [CompressPictures] [Compat12] [GUIDTypeLib] */\n\twrite_biff_rec(C, 0x000A /* EOF */);\n\tvar c = C.end();\n\n\tvar B = buf_array();\n\tvar blen = 0, j = 0;\n\tfor(j = 0; j < wb.SheetNames.length; ++j) blen += (b8 ? 12 : 11) + (b8 ? 2 : 1) * wb.SheetNames[j].length;\n\tvar start = a.length + blen + c.length;\n\tfor(j = 0; j < wb.SheetNames.length; ++j) {\n\t\tvar _sheet/*:WBWSProp*/ = _sheets[j] || ({}/*:any*/);\n\t\twrite_biff_rec(B, 0x0085 /* BoundSheet8 */, write_BoundSheet8({pos:start, hs:_sheet.Hidden||0, dt:0, name:wb.SheetNames[j]}, opts));\n\t\tstart += bufs[j].length;\n\t}\n\t/* 1*BoundSheet8 */\n\tvar b = B.end();\n\tif(blen != b.length) throw new Error(\"BS8 \" + blen + \" != \" + b.length);\n\n\tvar out = [];\n\tif(a.length) out.push(a);\n\tif(b.length) out.push(b);\n\tif(c.length) out.push(c);\n\treturn bconcat(out);\n}\n\n/* [MS-XLS] 2.1.7.20 Workbook Stream */\nfunction write_biff8_buf(wb/*:Workbook*/, opts/*:WriteOpts*/) {\n\tvar o = opts || {};\n\tvar bufs = [];\n\n\tif(wb && !wb.SSF) {\n\t\twb.SSF = dup(table_fmt);\n\t}\n\tif(wb && wb.SSF) {\n\t\tmake_ssf(); SSF_load_table(wb.SSF);\n\t\t// $FlowIgnore\n\t\to.revssf = evert_num(wb.SSF); o.revssf[wb.SSF[65535]] = 0;\n\t\to.ssf = wb.SSF;\n\t}\n\n\to.Strings = /*::((*/[]/*:: :any):SST)*/; o.Strings.Count = 0; o.Strings.Unique = 0;\n\tfix_write_opts(o);\n\n\to.cellXfs = [];\n\tget_cell_style(o.cellXfs, {}, {revssf:{\"General\":0}});\n\n\tif(!wb.Props) wb.Props = {};\n\n\tfor(var i = 0; i < wb.SheetNames.length; ++i) bufs[bufs.length] = write_ws_biff8(i, o, wb);\n\tbufs.unshift(write_biff8_global(wb, bufs, o));\n\treturn bconcat(bufs);\n}\n\nfunction write_biff_buf(wb/*:Workbook*/, opts/*:WriteOpts*/) {\n\tfor(var i = 0; i <= wb.SheetNames.length; ++i) {\n\t\tvar ws = wb.Sheets[wb.SheetNames[i]];\n\t\tif(!ws || !ws[\"!ref\"]) continue;\n\t\tvar range = decode_range(ws[\"!ref\"]);\n\t\tif(range.e.c > 255) { // note: 255 is IV\n\t\tif(typeof console != \"undefined\" && console.error) console.error(\"Worksheet '\" + wb.SheetNames[i] + \"' extends beyond column IV (255).  Data may be lost.\");\n\t\t}\n\t}\n\n\tvar o = opts || {};\n\tswitch(o.biff || 2) {\n\t\tcase 8: case 5: return write_biff8_buf(wb, opts);\n\t\tcase 4: case 3: case 2: return write_biff2_buf(wb, opts);\n\t}\n\tthrow new Error(\"invalid type \" + o.bookType + \" for BIFF\");\n}\n/* note: browser DOM element cannot see mso- style attrs, must parse */\nfunction html_to_sheet(str/*:string*/, _opts)/*:Workbook*/ {\n\tvar opts = _opts || {};\n\tif(DENSE != null && opts.dense == null) opts.dense = DENSE;\n\tvar ws/*:Worksheet*/ = opts.dense ? ([]/*:any*/) : ({}/*:any*/);\n\tstr = str.replace(/<!--.*?-->/g, \"\");\n\tvar mtch/*:any*/ = str.match(/<table/i);\n\tif(!mtch) throw new Error(\"Invalid HTML: could not find <table>\");\n\tvar mtch2/*:any*/ = str.match(/<\\/table/i);\n\tvar i/*:number*/ = mtch.index, j/*:number*/ = mtch2 && mtch2.index || str.length;\n\tvar rows = split_regex(str.slice(i, j), /(:?<tr[^>]*>)/i, \"<tr>\");\n\tvar R = -1, C = 0, RS = 0, CS = 0;\n\tvar range/*:Range*/ = {s:{r:10000000, c:10000000},e:{r:0,c:0}};\n\tvar merges/*:Array<Range>*/ = [];\n\tfor(i = 0; i < rows.length; ++i) {\n\t\tvar row = rows[i].trim();\n\t\tvar hd = row.slice(0,3).toLowerCase();\n\t\tif(hd == \"<tr\") { ++R; if(opts.sheetRows && opts.sheetRows <= R) { --R; break; } C = 0; continue; }\n\t\tif(hd != \"<td\" && hd != \"<th\") continue;\n\t\tvar cells = row.split(/<\\/t[dh]>/i);\n\t\tfor(j = 0; j < cells.length; ++j) {\n\t\t\tvar cell = cells[j].trim();\n\t\t\tif(!cell.match(/<t[dh]/i)) continue;\n\t\t\tvar m = cell, cc = 0;\n\t\t\t/* TODO: parse styles etc */\n\t\t\twhile(m.charAt(0) == \"<\" && (cc = m.indexOf(\">\")) > -1) m = m.slice(cc+1);\n\t\t\tfor(var midx = 0; midx < merges.length; ++midx) {\n\t\t\t\tvar _merge/*:Range*/ = merges[midx];\n\t\t\t\tif(_merge.s.c == C && _merge.s.r < R && R <= _merge.e.r) { C = _merge.e.c + 1; midx = -1; }\n\t\t\t}\n\t\t\tvar tag = parsexmltag(cell.slice(0, cell.indexOf(\">\")));\n\t\t\tCS = tag.colspan ? +tag.colspan : 1;\n\t\t\tif((RS = +tag.rowspan)>1 || CS>1) merges.push({s:{r:R,c:C},e:{r:R + (RS||1) - 1, c:C + CS - 1}});\n\t\t\tvar _t/*:string*/ = tag.t || tag[\"data-t\"] || \"\";\n\t\t\t/* TODO: generate stub cells */\n\t\t\tif(!m.length) { C += CS; continue; }\n\t\t\tm = htmldecode(m);\n\t\t\tif(range.s.r > R) range.s.r = R; if(range.e.r < R) range.e.r = R;\n\t\t\tif(range.s.c > C) range.s.c = C; if(range.e.c < C) range.e.c = C;\n\t\t\tif(!m.length) { C += CS; continue; }\n\t\t\tvar o/*:Cell*/ = {t:'s', v:m};\n\t\t\tif(opts.raw || !m.trim().length || _t == 's'){}\n\t\t\telse if(m === 'TRUE') o = {t:'b', v:true};\n\t\t\telse if(m === 'FALSE') o = {t:'b', v:false};\n\t\t\telse if(!isNaN(fuzzynum(m))) o = {t:'n', v:fuzzynum(m)};\n\t\t\telse if(!isNaN(fuzzydate(m).getDate())) {\n\t\t\t\to = ({t:'d', v:parseDate(m)}/*:any*/);\n\t\t\t\tif(!opts.cellDates) o = ({t:'n', v:datenum(o.v)}/*:any*/);\n\t\t\t\to.z = opts.dateNF || table_fmt[14];\n\t\t\t}\n\t\t\tif(opts.dense) { if(!ws[R]) ws[R] = []; ws[R][C] = o; }\n\t\t\telse ws[encode_cell({r:R, c:C})] = o;\n\t\t\tC += CS;\n\t\t}\n\t}\n\tws['!ref'] = encode_range(range);\n\tif(merges.length) ws[\"!merges\"] = merges;\n\treturn ws;\n}\nfunction make_html_row(ws/*:Worksheet*/, r/*:Range*/, R/*:number*/, o/*:Sheet2HTMLOpts*/)/*:string*/ {\n\tvar M/*:Array<Range>*/ = (ws['!merges'] ||[]);\n\tvar oo/*:Array<string>*/ = [];\n\tfor(var C = r.s.c; C <= r.e.c; ++C) {\n\t\tvar RS = 0, CS = 0;\n\t\tfor(var j = 0; j < M.length; ++j) {\n\t\t\tif(M[j].s.r > R || M[j].s.c > C) continue;\n\t\t\tif(M[j].e.r < R || M[j].e.c < C) continue;\n\t\t\tif(M[j].s.r < R || M[j].s.c < C) { RS = -1; break; }\n\t\t\tRS = M[j].e.r - M[j].s.r + 1; CS = M[j].e.c - M[j].s.c + 1; break;\n\t\t}\n\t\tif(RS < 0) continue;\n\t\tvar coord = encode_cell({r:R,c:C});\n\t\tvar cell = o.dense ? (ws[R]||[])[C] : ws[coord];\n\t\t/* TODO: html entities */\n\t\tvar w = (cell && cell.v != null) && (cell.h || escapehtml(cell.w || (format_cell(cell), cell.w) || \"\")) || \"\";\n\t\tvar sp = ({}/*:any*/);\n\t\tif(RS > 1) sp.rowspan = RS;\n\t\tif(CS > 1) sp.colspan = CS;\n\t\tif(o.editable) w = '<span contenteditable=\"true\">' + w + '</span>';\n\t\telse if(cell) {\n\t\t\tsp[\"data-t\"] = cell && cell.t || 'z';\n\t\t\tif(cell.v != null) sp[\"data-v\"] = cell.v;\n\t\t\tif(cell.z != null) sp[\"data-z\"] = cell.z;\n\t\t\tif(cell.l && (cell.l.Target || \"#\").charAt(0) != \"#\") w = '<a href=\"' + cell.l.Target +'\">' + w + '</a>';\n\t\t}\n\t\tsp.id = (o.id || \"sjs\") + \"-\" + coord;\n\t\too.push(writextag('td', w, sp));\n\t}\n\tvar preamble = \"<tr>\";\n\treturn preamble + oo.join(\"\") + \"</tr>\";\n}\n\nvar HTML_BEGIN = '<html><head><meta charset=\"utf-8\"/><title>SheetJS Table Export</title></head><body>';\nvar HTML_END = '</body></html>';\n\nfunction html_to_workbook(str/*:string*/, opts)/*:Workbook*/ {\n\tvar mtch = str.match(/<table[\\s\\S]*?>[\\s\\S]*?<\\/table>/gi);\n\tif(!mtch || mtch.length == 0) throw new Error(\"Invalid HTML: could not find <table>\");\n\tif(mtch.length == 1) return sheet_to_workbook(html_to_sheet(mtch[0], opts), opts);\n\tvar wb = book_new();\n\tmtch.forEach(function(s, idx) { book_append_sheet(wb, html_to_sheet(s, opts), \"Sheet\" + (idx+1)); });\n\treturn wb;\n}\n\nfunction make_html_preamble(ws/*:Worksheet*/, R/*:Range*/, o/*:Sheet2HTMLOpts*/)/*:string*/ {\n\tvar out/*:Array<string>*/ = [];\n\treturn out.join(\"\") + '<table' + (o && o.id ? ' id=\"' + o.id + '\"' : \"\") + '>';\n}\n\nfunction sheet_to_html(ws/*:Worksheet*/, opts/*:?Sheet2HTMLOpts*//*, wb:?Workbook*/)/*:string*/ {\n\tvar o = opts || {};\n\tvar header = o.header != null ? o.header : HTML_BEGIN;\n\tvar footer = o.footer != null ? o.footer : HTML_END;\n\tvar out/*:Array<string>*/ = [header];\n\tvar r = decode_range(ws['!ref']);\n\to.dense = Array.isArray(ws);\n\tout.push(make_html_preamble(ws, r, o));\n\tfor(var R = r.s.r; R <= r.e.r; ++R) out.push(make_html_row(ws, r, R, o));\n\tout.push(\"</table>\" + footer);\n\treturn out.join(\"\");\n}\n\nfunction sheet_add_dom(ws/*:Worksheet*/, table/*:HTMLElement*/, _opts/*:?any*/)/*:Worksheet*/ {\n\tvar opts = _opts || {};\n\tif(DENSE != null) opts.dense = DENSE;\n\tvar or_R = 0, or_C = 0;\n\tif(opts.origin != null) {\n\t\tif(typeof opts.origin == 'number') or_R = opts.origin;\n\t\telse {\n\t\t\tvar _origin/*:CellAddress*/ = typeof opts.origin == \"string\" ? decode_cell(opts.origin) : opts.origin;\n\t\t\tor_R = _origin.r; or_C = _origin.c;\n\t\t}\n\t}\n\n\tvar rows/*:HTMLCollection<HTMLTableRowElement>*/ = table.getElementsByTagName('tr');\n\tvar sheetRows = Math.min(opts.sheetRows||10000000, rows.length);\n\tvar range/*:Range*/ = {s:{r:0,c:0},e:{r:or_R,c:or_C}};\n\tif(ws[\"!ref\"]) {\n\t\tvar _range/*:Range*/ = decode_range(ws[\"!ref\"]);\n\t\trange.s.r = Math.min(range.s.r, _range.s.r);\n\t\trange.s.c = Math.min(range.s.c, _range.s.c);\n\t\trange.e.r = Math.max(range.e.r, _range.e.r);\n\t\trange.e.c = Math.max(range.e.c, _range.e.c);\n\t\tif(or_R == -1) range.e.r = or_R = _range.e.r + 1;\n\t}\n\tvar merges/*:Array<Range>*/ = [], midx = 0;\n\tvar rowinfo/*:Array<RowInfo>*/ = ws[\"!rows\"] || (ws[\"!rows\"] = []);\n\tvar _R = 0, R = 0, _C = 0, C = 0, RS = 0, CS = 0;\n\tif(!ws[\"!cols\"]) ws['!cols'] = [];\n\tfor(; _R < rows.length && R < sheetRows; ++_R) {\n\t\tvar row/*:HTMLTableRowElement*/ = rows[_R];\n\t\tif (is_dom_element_hidden(row)) {\n\t\t\tif (opts.display) continue;\n\t\t\trowinfo[R] = {hidden: true};\n\t\t}\n\t\tvar elts/*:HTMLCollection<HTMLTableCellElement>*/ = (row.children/*:any*/);\n\t\tfor(_C = C = 0; _C < elts.length; ++_C) {\n\t\t\tvar elt/*:HTMLTableCellElement*/ = elts[_C];\n\t\t\tif (opts.display && is_dom_element_hidden(elt)) continue;\n\t\t\tvar v/*:?string*/ = elt.hasAttribute('data-v') ? elt.getAttribute('data-v') : elt.hasAttribute('v') ? elt.getAttribute('v') : htmldecode(elt.innerHTML);\n\t\t\tvar z/*:?string*/ = elt.getAttribute('data-z') || elt.getAttribute('z');\n\t\t\tfor(midx = 0; midx < merges.length; ++midx) {\n\t\t\t\tvar m/*:Range*/ = merges[midx];\n\t\t\t\tif(m.s.c == C + or_C && m.s.r < R + or_R && R + or_R <= m.e.r) { C = m.e.c+1 - or_C; midx = -1; }\n\t\t\t}\n\t\t\t/* TODO: figure out how to extract nonstandard mso- style */\n\t\t\tCS = +elt.getAttribute(\"colspan\") || 1;\n\t\t\tif( ((RS = (+elt.getAttribute(\"rowspan\") || 1)))>1 || CS>1) merges.push({s:{r:R + or_R,c:C + or_C},e:{r:R + or_R + (RS||1) - 1, c:C + or_C + (CS||1) - 1}});\n\t\t\tvar o/*:Cell*/ = {t:'s', v:v};\n\t\t\tvar _t/*:string*/ = elt.getAttribute(\"data-t\") || elt.getAttribute(\"t\") || \"\";\n\t\t\tif(v != null) {\n\t\t\t\tif(v.length == 0) o.t = _t || 'z';\n\t\t\t\telse if(opts.raw || v.trim().length == 0 || _t == \"s\"){}\n\t\t\t\telse if(v === 'TRUE') o = {t:'b', v:true};\n\t\t\t\telse if(v === 'FALSE') o = {t:'b', v:false};\n\t\t\t\telse if(!isNaN(fuzzynum(v))) o = {t:'n', v:fuzzynum(v)};\n\t\t\t\telse if(!isNaN(fuzzydate(v).getDate())) {\n\t\t\t\t\to = ({t:'d', v:parseDate(v)}/*:any*/);\n\t\t\t\t\tif(!opts.cellDates) o = ({t:'n', v:datenum(o.v)}/*:any*/);\n\t\t\t\t\to.z = opts.dateNF || table_fmt[14];\n\t\t\t\t}\n\t\t\t}\n\t\t\tif(o.z === undefined && z != null) o.z = z;\n\t\t\t/* The first link is used.  Links are assumed to be fully specified.\n\t\t\t * TODO: The right way to process relative links is to make a new <a> */\n\t\t\tvar l = \"\", Aelts = elt.getElementsByTagName(\"A\");\n\t\t\tif(Aelts && Aelts.length) for(var Aelti = 0; Aelti < Aelts.length; ++Aelti)\tif(Aelts[Aelti].hasAttribute(\"href\")) {\n\t\t\t\tl = Aelts[Aelti].getAttribute(\"href\"); if(l.charAt(0) != \"#\") break;\n\t\t\t}\n\t\t\tif(l && l.charAt(0) != \"#\") o.l = ({ Target: l });\n\t\t\tif(opts.dense) { if(!ws[R + or_R]) ws[R + or_R] = []; ws[R + or_R][C + or_C] = o; }\n\t\t\telse ws[encode_cell({c:C + or_C, r:R + or_R})] = o;\n\t\t\tif(range.e.c < C + or_C) range.e.c = C + or_C;\n\t\t\tC += CS;\n\t\t}\n\t\t++R;\n\t}\n\tif(merges.length) ws['!merges'] = (ws[\"!merges\"] || []).concat(merges);\n\trange.e.r = Math.max(range.e.r, R - 1 + or_R);\n\tws['!ref'] = encode_range(range);\n\tif(R >= sheetRows) ws['!fullref'] = encode_range((range.e.r = rows.length-_R+R-1 + or_R,range)); // We can count the real number of rows to parse but we don't to improve the performance\n\treturn ws;\n}\n\nfunction parse_dom_table(table/*:HTMLElement*/, _opts/*:?any*/)/*:Worksheet*/ {\n\tvar opts = _opts || {};\n\tvar ws/*:Worksheet*/ = opts.dense ? ([]/*:any*/) : ({}/*:any*/);\n\treturn sheet_add_dom(ws, table, _opts);\n}\n\nfunction table_to_book(table/*:HTMLElement*/, opts/*:?any*/)/*:Workbook*/ {\n\treturn sheet_to_workbook(parse_dom_table(table, opts), opts);\n}\n\nfunction is_dom_element_hidden(element/*:HTMLElement*/)/*:boolean*/ {\n\tvar display/*:string*/ = '';\n\tvar get_computed_style/*:?function*/ = get_get_computed_style_function(element);\n\tif(get_computed_style) display = get_computed_style(element).getPropertyValue('display');\n\tif(!display) display = element.style && element.style.display;\n\treturn display === 'none';\n}\n\n/* global getComputedStyle */\nfunction get_get_computed_style_function(element/*:HTMLElement*/)/*:?function*/ {\n\t// The proper getComputedStyle implementation is the one defined in the element window\n\tif(element.ownerDocument.defaultView && typeof element.ownerDocument.defaultView.getComputedStyle === 'function') return element.ownerDocument.defaultView.getComputedStyle;\n\t// If it is not available, try to get one from the global namespace\n\tif(typeof getComputedStyle === 'function') return getComputedStyle;\n\treturn null;\n}\n/* OpenDocument */\nfunction parse_text_p(text/*:string*//*::, tag*/)/*:Array<any>*/ {\n\t/* 6.1.2 White Space Characters */\n\tvar fixed = text\n\t\t.replace(/[\\t\\r\\n]/g, \" \").trim().replace(/ +/g, \" \")\n\t\t.replace(/<text:s\\/>/g,\" \")\n\t\t.replace(/<text:s text:c=\"(\\d+)\"\\/>/g, function($$,$1) { return Array(parseInt($1,10)+1).join(\" \"); })\n\t\t.replace(/<text:tab[^>]*\\/>/g,\"\\t\")\n\t\t.replace(/<text:line-break\\/>/g,\"\\n\");\n\tvar v = unescapexml(fixed.replace(/<[^>]*>/g,\"\"));\n\n\treturn [v];\n}\n\nvar number_formats_ods = {\n\t/* ods name: [short ssf fmt, long ssf fmt] */\n\tday:           [\"d\",   \"dd\"],\n\tmonth:         [\"m\",   \"mm\"],\n\tyear:          [\"y\",   \"yy\"],\n\thours:         [\"h\",   \"hh\"],\n\tminutes:       [\"m\",   \"mm\"],\n\tseconds:       [\"s\",   \"ss\"],\n\t\"am-pm\":       [\"A/P\", \"AM/PM\"],\n\t\"day-of-week\": [\"ddd\", \"dddd\"],\n\tera:           [\"e\",   \"ee\"],\n\t/* there is no native representation of LO \"Q\" format */\n\tquarter:       [\"\\\\Qm\", \"m\\\\\\\"th quarter\\\"\"]\n};\n\n\nfunction parse_content_xml(d/*:string*/, _opts)/*:Workbook*/ {\n\t\tvar opts = _opts || {};\n\t\tif(DENSE != null && opts.dense == null) opts.dense = DENSE;\n\t\tvar str = xlml_normalize(d);\n\t\tvar state/*:Array<any>*/ = [], tmp;\n\t\tvar tag/*:: = {}*/;\n\t\tvar NFtag = {name:\"\"}, NF = \"\", pidx = 0;\n\t\tvar sheetag/*:: = {name:\"\", '名称':\"\"}*/;\n\t\tvar rowtag/*:: = {'行号':\"\"}*/;\n\t\tvar Sheets = {}, SheetNames/*:Array<string>*/ = [];\n\t\tvar ws = opts.dense ? ([]/*:any*/) : ({}/*:any*/);\n\t\tvar Rn, q/*:: :any = ({t:\"\", v:null, z:null, w:\"\",c:[],}:any)*/;\n\t\tvar ctag = ({value:\"\"}/*:any*/);\n\t\tvar textp = \"\", textpidx = 0, textptag/*:: = {}*/;\n\t\tvar textR = [];\n\t\tvar R = -1, C = -1, range = {s: {r:1000000,c:10000000}, e: {r:0, c:0}};\n\t\tvar row_ol = 0;\n\t\tvar number_format_map = {};\n\t\tvar merges/*:Array<Range>*/ = [], mrange = {}, mR = 0, mC = 0;\n\t\tvar rowinfo/*:Array<RowInfo>*/ = [], rowpeat = 1, colpeat = 1;\n\t\tvar arrayf/*:Array<[Range, string]>*/ = [];\n\t\tvar WB = {Names:[]};\n\t\tvar atag = ({}/*:any*/);\n\t\tvar _Ref/*:[string, string]*/ = [\"\", \"\"];\n\t\tvar comments/*:Array<Comment>*/ = [], comment/*:Comment*/ = ({}/*:any*/);\n\t\tvar creator = \"\", creatoridx = 0;\n\t\tvar isstub = false, intable = false;\n\t\tvar i = 0;\n\t\txlmlregex.lastIndex = 0;\n\t\tstr = str.replace(/<!--([\\s\\S]*?)-->/mg,\"\").replace(/<!DOCTYPE[^\\[]*\\[[^\\]]*\\]>/gm,\"\");\n\t\twhile((Rn = xlmlregex.exec(str))) switch((Rn[3]=Rn[3].replace(/_.*$/,\"\"))) {\n\n\t\t\tcase 'table': case '工作表': // 9.1.2 <table:table>\n\t\t\t\tif(Rn[1]==='/') {\n\t\t\t\t\tif(range.e.c >= range.s.c && range.e.r >= range.s.r) ws['!ref'] = encode_range(range);\n\t\t\t\t\telse ws['!ref'] = \"A1:A1\";\n\t\t\t\t\tif(opts.sheetRows > 0 && opts.sheetRows <= range.e.r) {\n\t\t\t\t\t\tws['!fullref'] = ws['!ref'];\n\t\t\t\t\t\trange.e.r = opts.sheetRows - 1;\n\t\t\t\t\t\tws['!ref'] = encode_range(range);\n\t\t\t\t\t}\n\t\t\t\t\tif(merges.length) ws['!merges'] = merges;\n\t\t\t\t\tif(rowinfo.length) ws[\"!rows\"] = rowinfo;\n\t\t\t\t\tsheetag.name = sheetag['名称'] || sheetag.name;\n\t\t\t\t\tif(typeof JSON !== 'undefined') JSON.stringify(sheetag);\n\t\t\t\t\tSheetNames.push(sheetag.name);\n\t\t\t\t\tSheets[sheetag.name] = ws;\n\t\t\t\t\tintable = false;\n\t\t\t\t}\n\t\t\t\telse if(Rn[0].charAt(Rn[0].length-2) !== '/') {\n\t\t\t\t\tsheetag = parsexmltag(Rn[0], false);\n\t\t\t\t\tR = C = -1;\n\t\t\t\t\trange.s.r = range.s.c = 10000000; range.e.r = range.e.c = 0;\n\t\t\t\t\tws = opts.dense ? ([]/*:any*/) : ({}/*:any*/); merges = [];\n\t\t\t\t\trowinfo = [];\n\t\t\t\t\tintable = true;\n\t\t\t\t}\n\t\t\t\tbreak;\n\n\t\t\tcase 'table-row-group': // 9.1.9 <table:table-row-group>\n\t\t\t\tif(Rn[1] === \"/\") --row_ol; else ++row_ol;\n\t\t\t\tbreak;\n\t\t\tcase 'table-row': case '行': // 9.1.3 <table:table-row>\n\t\t\t\tif(Rn[1] === '/') { R+=rowpeat; rowpeat = 1; break; }\n\t\t\t\trowtag = parsexmltag(Rn[0], false);\n\t\t\t\tif(rowtag['行号']) R = rowtag['行号'] - 1; else if(R == -1) R = 0;\n\t\t\t\trowpeat = +rowtag['number-rows-repeated'] || 1;\n\t\t\t\t/* TODO: remove magic */\n\t\t\t\tif(rowpeat < 10) for(i = 0; i < rowpeat; ++i) if(row_ol > 0) rowinfo[R + i] = {level: row_ol};\n\t\t\t\tC = -1; break;\n\t\t\tcase 'covered-table-cell': // 9.1.5 <table:covered-table-cell>\n\t\t\t\tif(Rn[1] !== '/') ++C;\n\t\t\t\tif(opts.sheetStubs) {\n\t\t\t\t\tif(opts.dense) { if(!ws[R]) ws[R] = []; ws[R][C] = {t:'z'}; }\n\t\t\t\t\telse ws[encode_cell({r:R,c:C})] = {t:'z'};\n\t\t\t\t}\n\t\t\t\ttextp = \"\"; textR = [];\n\t\t\t\tbreak; /* stub */\n\t\t\tcase 'table-cell': case '数据':\n\t\t\t\tif(Rn[0].charAt(Rn[0].length-2) === '/') {\n\t\t\t\t\t++C;\n\t\t\t\t\tctag = parsexmltag(Rn[0], false);\n\t\t\t\t\tcolpeat = parseInt(ctag['number-columns-repeated']||\"1\", 10);\n\t\t\t\t\tq = ({t:'z', v:null/*:: , z:null, w:\"\",c:[]*/}/*:any*/);\n\t\t\t\t\tif(ctag.formula && opts.cellFormula != false) q.f = ods_to_csf_formula(unescapexml(ctag.formula));\n\t\t\t\t\tif((ctag['数据类型'] || ctag['value-type']) == \"string\") {\n\t\t\t\t\t\tq.t = \"s\"; q.v = unescapexml(ctag['string-value'] || \"\");\n\t\t\t\t\t\tif(opts.dense) {\n\t\t\t\t\t\t\tif(!ws[R]) ws[R] = [];\n\t\t\t\t\t\t\tws[R][C] = q;\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tws[encode_cell({r:R,c:C})] = q;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tC+= colpeat-1;\n\t\t\t\t} else if(Rn[1]!=='/') {\n\t\t\t\t\t++C;\n\t\t\t\t\ttextp = \"\"; textpidx = 0; textR = [];\n\t\t\t\t\tcolpeat = 1;\n\t\t\t\t\tvar rptR = rowpeat ? R + rowpeat - 1 : R;\n\t\t\t\t\tif(C > range.e.c) range.e.c = C;\n\t\t\t\t\tif(C < range.s.c) range.s.c = C;\n\t\t\t\t\tif(R < range.s.r) range.s.r = R;\n\t\t\t\t\tif(rptR > range.e.r) range.e.r = rptR;\n\t\t\t\t\tctag = parsexmltag(Rn[0], false);\n\t\t\t\t\tcomments = []; comment = ({}/*:any*/);\n\t\t\t\t\tq = ({t:ctag['数据类型'] || ctag['value-type'], v:null/*:: , z:null, w:\"\",c:[]*/}/*:any*/);\n\t\t\t\t\tif(opts.cellFormula) {\n\t\t\t\t\t\tif(ctag.formula) ctag.formula = unescapexml(ctag.formula);\n\t\t\t\t\t\tif(ctag['number-matrix-columns-spanned'] && ctag['number-matrix-rows-spanned']) {\n\t\t\t\t\t\t\tmR = parseInt(ctag['number-matrix-rows-spanned'],10) || 0;\n\t\t\t\t\t\t\tmC = parseInt(ctag['number-matrix-columns-spanned'],10) || 0;\n\t\t\t\t\t\t\tmrange = {s: {r:R,c:C}, e:{r:R + mR-1,c:C + mC-1}};\n\t\t\t\t\t\t\tq.F = encode_range(mrange);\n\t\t\t\t\t\t\tarrayf.push([mrange, q.F]);\n\t\t\t\t\t\t}\n\t\t\t\t\t\tif(ctag.formula) q.f = ods_to_csf_formula(ctag.formula);\n\t\t\t\t\t\telse for(i = 0; i < arrayf.length; ++i)\n\t\t\t\t\t\t\tif(R >= arrayf[i][0].s.r && R <= arrayf[i][0].e.r)\n\t\t\t\t\t\t\t\tif(C >= arrayf[i][0].s.c && C <= arrayf[i][0].e.c)\n\t\t\t\t\t\t\t\t\tq.F = arrayf[i][1];\n\t\t\t\t\t}\n\t\t\t\t\tif(ctag['number-columns-spanned'] || ctag['number-rows-spanned']) {\n\t\t\t\t\t\tmR = parseInt(ctag['number-rows-spanned'],10) || 0;\n\t\t\t\t\t\tmC = parseInt(ctag['number-columns-spanned'],10) || 0;\n\t\t\t\t\t\tmrange = {s: {r:R,c:C}, e:{r:R + mR-1,c:C + mC-1}};\n\t\t\t\t\t\tmerges.push(mrange);\n\t\t\t\t\t}\n\n\t\t\t\t\t/* 19.675.2 table:number-columns-repeated */\n\t\t\t\t\tif(ctag['number-columns-repeated']) colpeat = parseInt(ctag['number-columns-repeated'], 10);\n\n\t\t\t\t\t/* 19.385 office:value-type */\n\t\t\t\t\tswitch(q.t) {\n\t\t\t\t\t\tcase 'boolean': q.t = 'b'; q.v = parsexmlbool(ctag['boolean-value']); break;\n\t\t\t\t\t\tcase 'float': q.t = 'n'; q.v = parseFloat(ctag.value); break;\n\t\t\t\t\t\tcase 'percentage': q.t = 'n'; q.v = parseFloat(ctag.value); break;\n\t\t\t\t\t\tcase 'currency': q.t = 'n'; q.v = parseFloat(ctag.value); break;\n\t\t\t\t\t\tcase 'date': q.t = 'd'; q.v = parseDate(ctag['date-value']);\n\t\t\t\t\t\t\tif(!opts.cellDates) { q.t = 'n'; q.v = datenum(q.v); }\n\t\t\t\t\t\t\tq.z = 'm/d/yy'; break;\n\t\t\t\t\t\tcase 'time': q.t = 'n'; q.v = parse_isodur(ctag['time-value'])/86400;\n\t\t\t\t\t\t\tif(opts.cellDates) { q.t = 'd'; q.v = numdate(q.v); }\n\t\t\t\t\t\t\tq.z = 'HH:MM:SS'; break;\n\t\t\t\t\t\tcase 'number': q.t = 'n'; q.v = parseFloat(ctag['数据数值']); break;\n\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\tif(q.t === 'string' || q.t === 'text' || !q.t) {\n\t\t\t\t\t\t\t\tq.t = 's';\n\t\t\t\t\t\t\t\tif(ctag['string-value'] != null) { textp = unescapexml(ctag['string-value']); textR = []; }\n\t\t\t\t\t\t\t} else throw new Error('Unsupported value type ' + q.t);\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\tisstub = false;\n\t\t\t\t\tif(q.t === 's') {\n\t\t\t\t\t\tq.v = textp || '';\n\t\t\t\t\t\tif(textR.length) q.R = textR;\n\t\t\t\t\t\tisstub = textpidx == 0;\n\t\t\t\t\t}\n\t\t\t\t\tif(atag.Target) q.l = atag;\n\t\t\t\t\tif(comments.length > 0) { q.c = comments; comments = []; }\n\t\t\t\t\tif(textp && opts.cellText !== false) q.w = textp;\n\t\t\t\t\tif(isstub) { q.t = \"z\"; delete q.v; }\n\t\t\t\t\tif(!isstub || opts.sheetStubs) {\n\t\t\t\t\t\tif(!(opts.sheetRows && opts.sheetRows <= R)) {\n\t\t\t\t\t\t\tfor(var rpt = 0; rpt < rowpeat; ++rpt) {\n\t\t\t\t\t\t\t\tcolpeat = parseInt(ctag['number-columns-repeated']||\"1\", 10);\n\t\t\t\t\t\t\t\tif(opts.dense) {\n\t\t\t\t\t\t\t\t\tif(!ws[R + rpt]) ws[R + rpt] = [];\n\t\t\t\t\t\t\t\t\tws[R + rpt][C] = rpt == 0 ? q : dup(q);\n\t\t\t\t\t\t\t\t\twhile(--colpeat > 0) ws[R + rpt][C + colpeat] = dup(q);\n\t\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\t\tws[encode_cell({r:R + rpt,c:C})] = q;\n\t\t\t\t\t\t\t\t\twhile(--colpeat > 0) ws[encode_cell({r:R + rpt,c:C + colpeat})] = dup(q);\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\tif(range.e.c <= C) range.e.c = C;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tcolpeat = parseInt(ctag['number-columns-repeated']||\"1\", 10);\n\t\t\t\t\tC += colpeat-1; colpeat = 0;\n\t\t\t\t\tq = {/*:: t:\"\", v:null, z:null, w:\"\",c:[]*/};\n\t\t\t\t\ttextp = \"\"; textR = [];\n\t\t\t\t}\n\t\t\t\tatag = ({}/*:any*/);\n\t\t\t\tbreak; // 9.1.4 <table:table-cell>\n\n\t\t\t/* pure state */\n\t\t\tcase 'document': // TODO: <office:document> is the root for FODS\n\t\t\tcase 'document-content': case '电子表格文档': // 3.1.3.2 <office:document-content>\n\t\t\tcase 'spreadsheet': case '主体': // 3.7 <office:spreadsheet>\n\t\t\tcase 'scripts': // 3.12 <office:scripts>\n\t\t\tcase 'styles': // TODO <office:styles>\n\t\t\tcase 'font-face-decls': // 3.14 <office:font-face-decls>\n\t\t\tcase 'master-styles': // 3.15.4 <office:master-styles> -- relevant for FODS\n\t\t\t\tif(Rn[1]==='/'){if((tmp=state.pop())[0]!==Rn[3]) throw \"Bad state: \"+tmp;}\n\t\t\t\telse if(Rn[0].charAt(Rn[0].length-2) !== '/') state.push([Rn[3], true]);\n\t\t\t\tbreak;\n\n\t\t\tcase 'annotation': // 14.1 <office:annotation>\n\t\t\t\tif(Rn[1]==='/'){\n\t\t\t\t\tif((tmp=state.pop())[0]!==Rn[3]) throw \"Bad state: \"+tmp;\n\t\t\t\t\tcomment.t = textp;\n\t\t\t\t\tif(textR.length) /*::(*/comment/*:: :any)*/.R = textR;\n\t\t\t\t\tcomment.a = creator;\n\t\t\t\t\tcomments.push(comment);\n\t\t\t\t}\n\t\t\t\telse if(Rn[0].charAt(Rn[0].length-2) !== '/') {state.push([Rn[3], false]);}\n\t\t\t\tcreator = \"\"; creatoridx = 0;\n\t\t\t\ttextp = \"\"; textpidx = 0; textR = [];\n\t\t\t\tbreak;\n\n\t\t\tcase 'creator': // 4.3.2.7 <dc:creator>\n\t\t\t\tif(Rn[1]==='/') { creator = str.slice(creatoridx,Rn.index); }\n\t\t\t\telse creatoridx = Rn.index + Rn[0].length;\n\t\t\t\tbreak;\n\n\t\t\t/* ignore state */\n\t\t\tcase 'meta': case '元数据': // TODO: <office:meta> <uof:元数据> FODS/UOF\n\t\t\tcase 'settings': // TODO: <office:settings>\n\t\t\tcase 'config-item-set': // TODO: <office:config-item-set>\n\t\t\tcase 'config-item-map-indexed': // TODO: <office:config-item-map-indexed>\n\t\t\tcase 'config-item-map-entry': // TODO: <office:config-item-map-entry>\n\t\t\tcase 'config-item-map-named': // TODO: <office:config-item-map-entry>\n\t\t\tcase 'shapes': // 9.2.8 <table:shapes>\n\t\t\tcase 'frame': // 10.4.2 <draw:frame>\n\t\t\tcase 'text-box': // 10.4.3 <draw:text-box>\n\t\t\tcase 'image': // 10.4.4 <draw:image>\n\t\t\tcase 'data-pilot-tables': // 9.6.2 <table:data-pilot-tables>\n\t\t\tcase 'list-style': // 16.30 <text:list-style>\n\t\t\tcase 'form': // 13.13 <form:form>\n\t\t\tcase 'dde-links': // 9.8 <table:dde-links>\n\t\t\tcase 'event-listeners': // TODO\n\t\t\tcase 'chart': // TODO\n\t\t\t\tif(Rn[1]==='/'){if((tmp=state.pop())[0]!==Rn[3]) throw \"Bad state: \"+tmp;}\n\t\t\t\telse if(Rn[0].charAt(Rn[0].length-2) !== '/') state.push([Rn[3], false]);\n\t\t\t\ttextp = \"\"; textpidx = 0; textR = [];\n\t\t\t\tbreak;\n\n\t\t\tcase 'scientific-number': // TODO: <number:scientific-number>\n\t\t\t\tbreak;\n\t\t\tcase 'currency-symbol': // TODO: <number:currency-symbol>\n\t\t\t\tbreak;\n\t\t\tcase 'currency-style': // TODO: <number:currency-style>\n\t\t\t\tbreak;\n\t\t\tcase 'number-style': // 16.27.2 <number:number-style>\n\t\t\tcase 'percentage-style': // 16.27.9 <number:percentage-style>\n\t\t\tcase 'date-style': // 16.27.10 <number:date-style>\n\t\t\tcase 'time-style': // 16.27.18 <number:time-style>\n\t\t\t\tif(Rn[1]==='/'){\n\t\t\t\t\tnumber_format_map[NFtag.name] = NF;\n\t\t\t\t\tif((tmp=state.pop())[0]!==Rn[3]) throw \"Bad state: \"+tmp;\n\t\t\t\t} else if(Rn[0].charAt(Rn[0].length-2) !== '/') {\n\t\t\t\t\tNF = \"\";\n\t\t\t\t\tNFtag = parsexmltag(Rn[0], false);\n\t\t\t\t\tstate.push([Rn[3], true]);\n\t\t\t\t} break;\n\n\t\t\tcase 'script': break; // 3.13 <office:script>\n\t\t\tcase 'libraries': break; // TODO: <ooo:libraries>\n\t\t\tcase 'automatic-styles': break; // 3.15.3 <office:automatic-styles>\n\n\t\t\tcase 'default-style': // TODO: <style:default-style>\n\t\t\tcase 'page-layout': break; // TODO: <style:page-layout>\n\t\t\tcase 'style': // 16.2 <style:style>\n\t\t\t\tbreak;\n\t\t\tcase 'map': break; // 16.3 <style:map>\n\t\t\tcase 'font-face': break; // 16.21 <style:font-face>\n\n\t\t\tcase 'paragraph-properties': break; // 17.6 <style:paragraph-properties>\n\t\t\tcase 'table-properties': break; // 17.15 <style:table-properties>\n\t\t\tcase 'table-column-properties': break; // 17.16 <style:table-column-properties>\n\t\t\tcase 'table-row-properties': break; // 17.17 <style:table-row-properties>\n\t\t\tcase 'table-cell-properties': break; // 17.18 <style:table-cell-properties>\n\n\t\t\tcase 'number': // 16.27.3 <number:number>\n\t\t\t\tswitch(state[state.length-1][0]) {\n\t\t\t\t\tcase 'time-style':\n\t\t\t\t\tcase 'date-style':\n\t\t\t\t\t\ttag = parsexmltag(Rn[0], false);\n\t\t\t\t\t\tNF += number_formats_ods[Rn[3]][tag.style==='long'?1:0]; break;\n\t\t\t\t} break;\n\n\t\t\tcase 'fraction': break; // TODO 16.27.6 <number:fraction>\n\n\t\t\tcase 'day': // 16.27.11 <number:day>\n\t\t\tcase 'month': // 16.27.12 <number:month>\n\t\t\tcase 'year': // 16.27.13 <number:year>\n\t\t\tcase 'era': // 16.27.14 <number:era>\n\t\t\tcase 'day-of-week': // 16.27.15 <number:day-of-week>\n\t\t\tcase 'week-of-year': // 16.27.16 <number:week-of-year>\n\t\t\tcase 'quarter': // 16.27.17 <number:quarter>\n\t\t\tcase 'hours': // 16.27.19 <number:hours>\n\t\t\tcase 'minutes': // 16.27.20 <number:minutes>\n\t\t\tcase 'seconds': // 16.27.21 <number:seconds>\n\t\t\tcase 'am-pm': // 16.27.22 <number:am-pm>\n\t\t\t\tswitch(state[state.length-1][0]) {\n\t\t\t\t\tcase 'time-style':\n\t\t\t\t\tcase 'date-style':\n\t\t\t\t\t\ttag = parsexmltag(Rn[0], false);\n\t\t\t\t\t\tNF += number_formats_ods[Rn[3]][tag.style==='long'?1:0]; break;\n\t\t\t\t} break;\n\n\t\t\tcase 'boolean-style': break; // 16.27.23 <number:boolean-style>\n\t\t\tcase 'boolean': break; // 16.27.24 <number:boolean>\n\t\t\tcase 'text-style': break; // 16.27.25 <number:text-style>\n\t\t\tcase 'text': // 16.27.26 <number:text>\n\t\t\t\tif(Rn[0].slice(-2) === \"/>\") break;\n\t\t\t\telse if(Rn[1]===\"/\") switch(state[state.length-1][0]) {\n\t\t\t\t\tcase 'number-style':\n\t\t\t\t\tcase 'date-style':\n\t\t\t\t\tcase 'time-style':\n\t\t\t\t\t\tNF += str.slice(pidx, Rn.index);\n\t\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\telse pidx = Rn.index + Rn[0].length;\n\t\t\t\tbreak;\n\n\t\t\tcase 'named-range': // 9.4.12 <table:named-range>\n\t\t\t\ttag = parsexmltag(Rn[0], false);\n\t\t\t\t_Ref = ods_to_csf_3D(tag['cell-range-address']);\n\t\t\t\tvar nrange = ({Name:tag.name, Ref:_Ref[0] + '!' + _Ref[1]}/*:any*/);\n\t\t\t\tif(intable) nrange.Sheet = SheetNames.length;\n\t\t\t\tWB.Names.push(nrange);\n\t\t\t\tbreak;\n\n\t\t\tcase 'text-content': break; // 16.27.27 <number:text-content>\n\t\t\tcase 'text-properties': break; // 16.27.27 <style:text-properties>\n\t\t\tcase 'embedded-text': break; // 16.27.4 <number:embedded-text>\n\n\t\t\tcase 'body': case '电子表格': break; // 3.3 16.9.6 19.726.3\n\n\t\t\tcase 'forms': break; // 12.25.2 13.2\n\t\t\tcase 'table-column': break; // 9.1.6 <table:table-column>\n\t\t\tcase 'table-header-rows': break; // 9.1.7 <table:table-header-rows>\n\t\t\tcase 'table-rows': break; // 9.1.12 <table:table-rows>\n\t\t\t/* TODO: outline levels */\n\t\t\tcase 'table-column-group': break; // 9.1.10 <table:table-column-group>\n\t\t\tcase 'table-header-columns': break; // 9.1.11 <table:table-header-columns>\n\t\t\tcase 'table-columns': break; // 9.1.12 <table:table-columns>\n\n\t\t\tcase 'null-date': break; // 9.4.2 <table:null-date> TODO: date1904\n\n\t\t\tcase 'graphic-properties': break; // 17.21 <style:graphic-properties>\n\t\t\tcase 'calculation-settings': break; // 9.4.1 <table:calculation-settings>\n\t\t\tcase 'named-expressions': break; // 9.4.11 <table:named-expressions>\n\t\t\tcase 'label-range': break; // 9.4.9 <table:label-range>\n\t\t\tcase 'label-ranges': break; // 9.4.10 <table:label-ranges>\n\t\t\tcase 'named-expression': break; // 9.4.13 <table:named-expression>\n\t\t\tcase 'sort': break; // 9.4.19 <table:sort>\n\t\t\tcase 'sort-by': break; // 9.4.20 <table:sort-by>\n\t\t\tcase 'sort-groups': break; // 9.4.22 <table:sort-groups>\n\n\t\t\tcase 'tab': break; // 6.1.4 <text:tab>\n\t\t\tcase 'line-break': break; // 6.1.5 <text:line-break>\n\t\t\tcase 'span': break; // 6.1.7 <text:span>\n\t\t\tcase 'p': case '文本串': // 5.1.3 <text:p>\n\t\t\t\tif(['master-styles'].indexOf(state[state.length-1][0]) > -1) break;\n\t\t\t\tif(Rn[1]==='/' && (!ctag || !ctag['string-value'])) {\n\t\t\t\t\tvar ptp = parse_text_p(str.slice(textpidx,Rn.index), textptag);\n\t\t\t\t\ttextp = (textp.length > 0 ? textp + \"\\n\" : \"\") + ptp[0];\n\t\t\t\t} else { textptag = parsexmltag(Rn[0], false); textpidx = Rn.index + Rn[0].length; }\n\t\t\t\tbreak; // <text:p>\n\t\t\tcase 's': break; // <text:s>\n\n\t\t\tcase 'database-range': // 9.4.15 <table:database-range>\n\t\t\t\tif(Rn[1]==='/') break;\n\t\t\t\ttry {\n\t\t\t\t\t_Ref = ods_to_csf_3D(parsexmltag(Rn[0])['target-range-address']);\n\t\t\t\t\tSheets[_Ref[0]]['!autofilter'] = { ref:_Ref[1] };\n\t\t\t\t} catch(e) {/* empty */}\n\t\t\t\tbreak;\n\n\t\t\tcase 'date': break; // <*:date>\n\n\t\t\tcase 'object': break; // 10.4.6.2 <draw:object>\n\t\t\tcase 'title': case '标题': break; // <*:title> OR <uof:标题>\n\t\t\tcase 'desc': break; // <*:desc>\n\t\t\tcase 'binary-data': break; // 10.4.5 TODO: b64 blob\n\n\t\t\t/* 9.2 Advanced Tables */\n\t\t\tcase 'table-source': break; // 9.2.6\n\t\t\tcase 'scenario': break; // 9.2.6\n\n\t\t\tcase 'iteration': break; // 9.4.3 <table:iteration>\n\t\t\tcase 'content-validations': break; // 9.4.4 <table:\n\t\t\tcase 'content-validation': break; // 9.4.5 <table:\n\t\t\tcase 'help-message': break; // 9.4.6 <table:\n\t\t\tcase 'error-message': break; // 9.4.7 <table:\n\t\t\tcase 'database-ranges': break; // 9.4.14 <table:database-ranges>\n\t\t\tcase 'filter': break; // 9.5.2 <table:filter>\n\t\t\tcase 'filter-and': break; // 9.5.3 <table:filter-and>\n\t\t\tcase 'filter-or': break; // 9.5.4 <table:filter-or>\n\t\t\tcase 'filter-condition': break; // 9.5.5 <table:filter-condition>\n\n\t\t\tcase 'list-level-style-bullet': break; // 16.31 <text:\n\t\t\tcase 'list-level-style-number': break; // 16.32 <text:\n\t\t\tcase 'list-level-properties': break; // 17.19 <style:\n\n\t\t\t/* 7.3 Document Fields */\n\t\t\tcase 'sender-firstname': // 7.3.6.2\n\t\t\tcase 'sender-lastname': // 7.3.6.3\n\t\t\tcase 'sender-initials': // 7.3.6.4\n\t\t\tcase 'sender-title': // 7.3.6.5\n\t\t\tcase 'sender-position': // 7.3.6.6\n\t\t\tcase 'sender-email': // 7.3.6.7\n\t\t\tcase 'sender-phone-private': // 7.3.6.8\n\t\t\tcase 'sender-fax': // 7.3.6.9\n\t\t\tcase 'sender-company': // 7.3.6.10\n\t\t\tcase 'sender-phone-work': // 7.3.6.11\n\t\t\tcase 'sender-street': // 7.3.6.12\n\t\t\tcase 'sender-city': // 7.3.6.13\n\t\t\tcase 'sender-postal-code': // 7.3.6.14\n\t\t\tcase 'sender-country': // 7.3.6.15\n\t\t\tcase 'sender-state-or-province': // 7.3.6.16\n\t\t\tcase 'author-name': // 7.3.7.1\n\t\t\tcase 'author-initials': // 7.3.7.2\n\t\t\tcase 'chapter': // 7.3.8\n\t\t\tcase 'file-name': // 7.3.9\n\t\t\tcase 'template-name': // 7.3.9\n\t\t\tcase 'sheet-name': // 7.3.9\n\t\t\t\tbreak;\n\n\t\t\tcase 'event-listener':\n\t\t\t\tbreak;\n\t\t\t/* TODO: FODS Properties */\n\t\t\tcase 'initial-creator':\n\t\t\tcase 'creation-date':\n\t\t\tcase 'print-date':\n\t\t\tcase 'generator':\n\t\t\tcase 'document-statistic':\n\t\t\tcase 'user-defined':\n\t\t\tcase 'editing-duration':\n\t\t\tcase 'editing-cycles':\n\t\t\t\tbreak;\n\n\t\t\t/* TODO: FODS Config */\n\t\t\tcase 'config-item':\n\t\t\t\tbreak;\n\n\t\t\t/* TODO: style tokens */\n\t\t\tcase 'page-number': break; // TODO <text:page-number>\n\t\t\tcase 'page-count': break; // TODO <text:page-count>\n\t\t\tcase 'time': break; // TODO <text:time>\n\n\t\t\t/* 9.3 Advanced Table Cells */\n\t\t\tcase 'cell-range-source': break; // 9.3.1 <table:\n\t\t\tcase 'detective': break; // 9.3.2 <table:\n\t\t\tcase 'operation': break; // 9.3.3 <table:\n\t\t\tcase 'highlighted-range': break; // 9.3.4 <table:\n\n\t\t\t/* 9.6 Data Pilot Tables <table: */\n\t\t\tcase 'data-pilot-table': // 9.6.3\n\t\t\tcase 'source-cell-range': // 9.6.5\n\t\t\tcase 'source-service': // 9.6.6\n\t\t\tcase 'data-pilot-field': // 9.6.7\n\t\t\tcase 'data-pilot-level': // 9.6.8\n\t\t\tcase 'data-pilot-subtotals': // 9.6.9\n\t\t\tcase 'data-pilot-subtotal': // 9.6.10\n\t\t\tcase 'data-pilot-members': // 9.6.11\n\t\t\tcase 'data-pilot-member': // 9.6.12\n\t\t\tcase 'data-pilot-display-info': // 9.6.13\n\t\t\tcase 'data-pilot-sort-info': // 9.6.14\n\t\t\tcase 'data-pilot-layout-info': // 9.6.15\n\t\t\tcase 'data-pilot-field-reference': // 9.6.16\n\t\t\tcase 'data-pilot-groups': // 9.6.17\n\t\t\tcase 'data-pilot-group': // 9.6.18\n\t\t\tcase 'data-pilot-group-member': // 9.6.19\n\t\t\t\tbreak;\n\n\t\t\t/* 10.3 Drawing Shapes */\n\t\t\tcase 'rect': // 10.3.2\n\t\t\t\tbreak;\n\n\t\t\t/* 14.6 DDE Connections */\n\t\t\tcase 'dde-connection-decls': // 14.6.2 <text:\n\t\t\tcase 'dde-connection-decl': // 14.6.3 <text:\n\t\t\tcase 'dde-link': // 14.6.4 <table:\n\t\t\tcase 'dde-source': // 14.6.5 <office:\n\t\t\t\tbreak;\n\n\t\t\tcase 'properties': break; // 13.7 <form:properties>\n\t\t\tcase 'property': break; // 13.8 <form:property>\n\n\t\t\tcase 'a': // 6.1.8 hyperlink\n\t\t\t\tif(Rn[1]!== '/') {\n\t\t\t\t\tatag = parsexmltag(Rn[0], false);\n\t\t\t\t\tif(!atag.href) break;\n\t\t\t\t\tatag.Target = unescapexml(atag.href); delete atag.href;\n\t\t\t\t\tif(atag.Target.charAt(0) == \"#\" && atag.Target.indexOf(\".\") > -1) {\n\t\t\t\t\t\t_Ref = ods_to_csf_3D(atag.Target.slice(1));\n\t\t\t\t\t\tatag.Target = \"#\" + _Ref[0] + \"!\" + _Ref[1];\n\t\t\t\t\t} else if(atag.Target.match(/^\\.\\.[\\\\\\/]/)) atag.Target = atag.Target.slice(3);\n\t\t\t\t}\n\t\t\t\tbreak;\n\n\t\t\t/* non-standard */\n\t\t\tcase 'table-protection': break;\n\t\t\tcase 'data-pilot-grand-total': break; // <table:\n\t\t\tcase 'office-document-common-attrs': break; // bare\n\t\t\tdefault: switch(Rn[2]) {\n\t\t\t\tcase 'dc:':       // TODO: properties\n\t\t\t\tcase 'calcext:':  // ignore undocumented extensions\n\t\t\t\tcase 'loext:':    // ignore undocumented extensions\n\t\t\t\tcase 'ooo:':      // ignore undocumented extensions\n\t\t\t\tcase 'chartooo:': // ignore undocumented extensions\n\t\t\t\tcase 'draw:':     // TODO: drawing\n\t\t\t\tcase 'style:':    // TODO: styles\n\t\t\t\tcase 'chart:':    // TODO: charts\n\t\t\t\tcase 'form:':     // TODO: forms\n\t\t\t\tcase 'uof:':      // TODO: uof\n\t\t\t\tcase '表:':       // TODO: uof\n\t\t\t\tcase '字:':       // TODO: uof\n\t\t\t\t\tbreak;\n\t\t\t\tdefault: if(opts.WTF) throw new Error(Rn);\n\t\t\t}\n\t\t}\n\t\tvar out/*:Workbook*/ = ({\n\t\t\tSheets: Sheets,\n\t\t\tSheetNames: SheetNames,\n\t\t\tWorkbook: WB\n\t\t}/*:any*/);\n\t\tif(opts.bookSheets) delete /*::(*/out/*:: :any)*/.Sheets;\n\t\treturn out;\n}\n\nfunction parse_ods(zip/*:ZIPFile*/, opts/*:?ParseOpts*/)/*:Workbook*/ {\n\topts = opts || ({}/*:any*/);\n\tif(safegetzipfile(zip, 'META-INF/manifest.xml')) parse_manifest(getzipdata(zip, 'META-INF/manifest.xml'), opts);\n\tvar content = getzipstr(zip, 'content.xml');\n\tif(!content) throw new Error(\"Missing content.xml in ODS / UOF file\");\n\tvar wb = parse_content_xml(utf8read(content), opts);\n\tif(safegetzipfile(zip, 'meta.xml')) wb.Props = parse_core_props(getzipdata(zip, 'meta.xml'));\n\treturn wb;\n}\nfunction parse_fods(data/*:string*/, opts/*:?ParseOpts*/)/*:Workbook*/ {\n\treturn parse_content_xml(data, opts);\n}\n\n/* OpenDocument */\nvar write_styles_ods/*:{(wb:any, opts:any):string}*/ = /* @__PURE__ */(function() {\n\tvar master_styles = [\n\t\t'<office:master-styles>',\n\t\t\t'<style:master-page style:name=\"mp1\" style:page-layout-name=\"mp1\">',\n\t\t\t\t'<style:header/>',\n\t\t\t\t'<style:header-left style:display=\"false\"/>',\n\t\t\t\t'<style:footer/>',\n\t\t\t\t'<style:footer-left style:display=\"false\"/>',\n\t\t\t'</style:master-page>',\n\t\t'</office:master-styles>'\n\t].join(\"\");\n\n\tvar payload = '<office:document-styles ' + wxt_helper({\n\t\t'xmlns:office':   \"urn:oasis:names:tc:opendocument:xmlns:office:1.0\",\n\t\t'xmlns:table':    \"urn:oasis:names:tc:opendocument:xmlns:table:1.0\",\n\t\t'xmlns:style':    \"urn:oasis:names:tc:opendocument:xmlns:style:1.0\",\n\t\t'xmlns:text':     \"urn:oasis:names:tc:opendocument:xmlns:text:1.0\",\n\t\t'xmlns:draw':     \"urn:oasis:names:tc:opendocument:xmlns:drawing:1.0\",\n\t\t'xmlns:fo':       \"urn:oasis:names:tc:opendocument:xmlns:xsl-fo-compatible:1.0\",\n\t\t'xmlns:xlink':    \"http://www.w3.org/1999/xlink\",\n\t\t'xmlns:dc':       \"http://purl.org/dc/elements/1.1/\",\n\t\t'xmlns:number':   \"urn:oasis:names:tc:opendocument:xmlns:datastyle:1.0\",\n\t\t'xmlns:svg':      \"urn:oasis:names:tc:opendocument:xmlns:svg-compatible:1.0\",\n\t\t'xmlns:of':       \"urn:oasis:names:tc:opendocument:xmlns:of:1.2\",\n\t\t'office:version': \"1.2\"\n\t}) + '>' + master_styles + '</office:document-styles>';\n\n\treturn function wso(/*::wb, opts*/) {\n\t\treturn XML_HEADER + payload;\n\t};\n})();\nvar write_content_ods/*:{(wb:any, opts:any):string}*/ = /* @__PURE__ */(function() {\n\t/* 6.1.2 White Space Characters */\n\tvar write_text_p = function(text/*:string*/)/*:string*/ {\n\t\treturn escapexml(text)\n\t\t\t.replace(/  +/g, function($$){return '<text:s text:c=\"'+$$.length+'\"/>';})\n\t\t\t.replace(/\\t/g, \"<text:tab/>\")\n\t\t\t.replace(/\\n/g, \"</text:p><text:p>\")\n\t\t\t.replace(/^ /, \"<text:s/>\").replace(/ $/, \"<text:s/>\");\n\t};\n\n\tvar null_cell_xml = '          <table:table-cell />\\n';\n\tvar covered_cell_xml = '          <table:covered-table-cell/>\\n';\n\tvar write_ws = function(ws, wb/*:Workbook*/, i/*:number*//*::, opts*/)/*:string*/ {\n\t\t/* Section 9 Tables */\n\t\tvar o/*:Array<string>*/ = [];\n\t\to.push('      <table:table table:name=\"' + escapexml(wb.SheetNames[i]) + '\" table:style-name=\"ta1\">\\n');\n\t\tvar R=0,C=0, range = decode_range(ws['!ref']||\"A1\");\n\t\tvar marr/*:Array<Range>*/ = ws['!merges'] || [], mi = 0;\n\t\tvar dense = Array.isArray(ws);\n\t\tif(ws[\"!cols\"]) {\n\t\t\tfor(C = 0; C <= range.e.c; ++C) o.push('        <table:table-column' + (ws[\"!cols\"][C] ? ' table:style-name=\"co' + ws[\"!cols\"][C].ods + '\"' : '') + '></table:table-column>\\n');\n\t\t}\n\t\tvar H = \"\", ROWS = ws[\"!rows\"]||[];\n\t\tfor(R = 0; R < range.s.r; ++R) {\n\t\t\tH = ROWS[R] ? ' table:style-name=\"ro' + ROWS[R].ods + '\"' : \"\";\n\t\t\to.push('        <table:table-row' + H + '></table:table-row>\\n');\n\t\t}\n\t\tfor(; R <= range.e.r; ++R) {\n\t\t\tH = ROWS[R] ? ' table:style-name=\"ro' + ROWS[R].ods + '\"' : \"\";\n\t\t\to.push('        <table:table-row' + H + '>\\n');\n\t\t\tfor(C=0; C < range.s.c; ++C) o.push(null_cell_xml);\n\t\t\tfor(; C <= range.e.c; ++C) {\n\t\t\t\tvar skip = false, ct = {}, textp = \"\";\n\t\t\t\tfor(mi = 0; mi != marr.length; ++mi) {\n\t\t\t\t\tif(marr[mi].s.c > C) continue;\n\t\t\t\t\tif(marr[mi].s.r > R) continue;\n\t\t\t\t\tif(marr[mi].e.c < C) continue;\n\t\t\t\t\tif(marr[mi].e.r < R) continue;\n\t\t\t\t\tif(marr[mi].s.c != C || marr[mi].s.r != R) skip = true;\n\t\t\t\t\tct['table:number-columns-spanned'] = (marr[mi].e.c - marr[mi].s.c + 1);\n\t\t\t\t\tct['table:number-rows-spanned'] =    (marr[mi].e.r - marr[mi].s.r + 1);\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\tif(skip) { o.push(covered_cell_xml); continue; }\n\t\t\t\tvar ref = encode_cell({r:R, c:C}), cell = dense ? (ws[R]||[])[C]: ws[ref];\n\t\t\t\tif(cell && cell.f) {\n\t\t\t\t\tct['table:formula'] = escapexml(csf_to_ods_formula(cell.f));\n\t\t\t\t\tif(cell.F) {\n\t\t\t\t\t\tif(cell.F.slice(0, ref.length) == ref) {\n\t\t\t\t\t\t\tvar _Fref = decode_range(cell.F);\n\t\t\t\t\t\t\tct['table:number-matrix-columns-spanned'] = (_Fref.e.c - _Fref.s.c + 1);\n\t\t\t\t\t\t\tct['table:number-matrix-rows-spanned'] =    (_Fref.e.r - _Fref.s.r + 1);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif(!cell) { o.push(null_cell_xml); continue; }\n\t\t\t\tswitch(cell.t) {\n\t\t\t\t\tcase 'b':\n\t\t\t\t\t\ttextp = (cell.v ? 'TRUE' : 'FALSE');\n\t\t\t\t\t\tct['office:value-type'] = \"boolean\";\n\t\t\t\t\t\tct['office:boolean-value'] = (cell.v ? 'true' : 'false');\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase 'n':\n\t\t\t\t\t\ttextp = (cell.w||String(cell.v||0));\n\t\t\t\t\t\tct['office:value-type'] = \"float\";\n\t\t\t\t\t\tct['office:value'] = (cell.v||0);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase 's': case 'str':\n\t\t\t\t\t\ttextp = cell.v == null ? \"\" : cell.v;\n\t\t\t\t\t\tct['office:value-type'] = \"string\";\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase 'd':\n\t\t\t\t\t\ttextp = (cell.w||(parseDate(cell.v).toISOString()));\n\t\t\t\t\t\tct['office:value-type'] = \"date\";\n\t\t\t\t\t\tct['office:date-value'] = (parseDate(cell.v).toISOString());\n\t\t\t\t\t\tct['table:style-name'] = \"ce1\";\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t//case 'e':\n\t\t\t\t\tdefault: o.push(null_cell_xml); continue;\n\t\t\t\t}\n\t\t\t\tvar text_p = write_text_p(textp);\n\t\t\t\tif(cell.l && cell.l.Target) {\n\t\t\t\t\tvar _tgt = cell.l.Target;\n\t\t\t\t\t_tgt = _tgt.charAt(0) == \"#\" ? \"#\" + csf_to_ods_3D(_tgt.slice(1)) : _tgt;\n\t\t\t\t\t// TODO: choose correct parent path format based on link delimiters\n\t\t\t\t\tif(_tgt.charAt(0) != \"#\" && !_tgt.match(/^\\w+:/)) _tgt = '../' + _tgt;\n\t\t\t\t\ttext_p = writextag('text:a', text_p, {'xlink:href': _tgt.replace(/&/g, \"&amp;\")});\n\t\t\t\t}\n\t\t\t\to.push('          ' + writextag('table:table-cell', writextag('text:p', text_p, {}), ct) + '\\n');\n\t\t\t}\n\t\t\to.push('        </table:table-row>\\n');\n\t\t}\n\t\to.push('      </table:table>\\n');\n\t\treturn o.join(\"\");\n\t};\n\n\tvar write_automatic_styles_ods = function(o/*:Array<string>*/, wb) {\n\t\to.push(' <office:automatic-styles>\\n');\n\n\t\to.push('  <number:date-style style:name=\"N37\" number:automatic-order=\"true\">\\n');\n\t\to.push('   <number:month number:style=\"long\"/>\\n');\n\t\to.push('   <number:text>/</number:text>\\n');\n\t\to.push('   <number:day number:style=\"long\"/>\\n');\n\t\to.push('   <number:text>/</number:text>\\n');\n\t\to.push('   <number:year/>\\n');\n\t\to.push('  </number:date-style>\\n');\n\n\t\t/* column styles */\n\t\tvar cidx = 0;\n\t\twb.SheetNames.map(function(n) { return wb.Sheets[n]; }).forEach(function(ws) {\n\t\t\tif(!ws) return;\n\t\t\tif(ws[\"!cols\"]) {\n\t\t\t\tfor(var C = 0; C < ws[\"!cols\"].length; ++C) if(ws[\"!cols\"][C]) {\n\t\t\t\t\tvar colobj = ws[\"!cols\"][C];\n\t\t\t\t\tif(colobj.width == null && colobj.wpx == null && colobj.wch == null) continue;\n\t\t\t\t\tprocess_col(colobj);\n\t\t\t\t\tcolobj.ods = cidx;\n\t\t\t\t\tvar w = ws[\"!cols\"][C].wpx + \"px\";\n\t\t\t\t\to.push('  <style:style style:name=\"co' + cidx + '\" style:family=\"table-column\">\\n');\n\t\t\t\t\to.push('   <style:table-column-properties fo:break-before=\"auto\" style:column-width=\"' + w + '\"/>\\n');\n\t\t\t\t\to.push('  </style:style>\\n');\n\t\t\t\t\t++cidx;\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\n\t\t/* row styles */\n\t\tvar ridx = 0;\n\t\twb.SheetNames.map(function(n) { return wb.Sheets[n]; }).forEach(function(ws) {\n\t\t\tif(!ws) return;\n\t\t\tif(ws[\"!rows\"]) {\n\t\t\t\tfor(var R = 0; R < ws[\"!rows\"].length; ++R) if(ws[\"!rows\"][R]) {\n\t\t\t\t\tws[\"!rows\"][R].ods = ridx;\n\t\t\t\t\tvar h = ws[\"!rows\"][R].hpx + \"px\";\n\t\t\t\t\to.push('  <style:style style:name=\"ro' + ridx + '\" style:family=\"table-row\">\\n');\n\t\t\t\t\to.push('   <style:table-row-properties fo:break-before=\"auto\" style:row-height=\"' + h + '\"/>\\n');\n\t\t\t\t\to.push('  </style:style>\\n');\n\t\t\t\t\t++ridx;\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\n\t\t/* table */\n\t\to.push('  <style:style style:name=\"ta1\" style:family=\"table\" style:master-page-name=\"mp1\">\\n');\n\t\to.push('   <style:table-properties table:display=\"true\" style:writing-mode=\"lr-tb\"/>\\n');\n\t\to.push('  </style:style>\\n');\n\n\t\t/* table cells, text */\n\t\to.push('  <style:style style:name=\"ce1\" style:family=\"table-cell\" style:parent-style-name=\"Default\" style:data-style-name=\"N37\"/>\\n');\n\n\t\t/* page-layout */\n\n\t\to.push(' </office:automatic-styles>\\n');\n\t};\n\n\treturn function wcx(wb, opts) {\n\t\tvar o = [XML_HEADER];\n\t\t/* 3.1.3.2 */\n\t\tvar attr = wxt_helper({\n\t\t\t'xmlns:office':       \"urn:oasis:names:tc:opendocument:xmlns:office:1.0\",\n\t\t\t'xmlns:table':        \"urn:oasis:names:tc:opendocument:xmlns:table:1.0\",\n\t\t\t'xmlns:style':        \"urn:oasis:names:tc:opendocument:xmlns:style:1.0\",\n\t\t\t'xmlns:text':         \"urn:oasis:names:tc:opendocument:xmlns:text:1.0\",\n\t\t\t'xmlns:draw':         \"urn:oasis:names:tc:opendocument:xmlns:drawing:1.0\",\n\t\t\t'xmlns:fo':           \"urn:oasis:names:tc:opendocument:xmlns:xsl-fo-compatible:1.0\",\n\t\t\t'xmlns:xlink':        \"http://www.w3.org/1999/xlink\",\n\t\t\t'xmlns:dc':           \"http://purl.org/dc/elements/1.1/\",\n\t\t\t'xmlns:meta':         \"urn:oasis:names:tc:opendocument:xmlns:meta:1.0\",\n\t\t\t'xmlns:number':       \"urn:oasis:names:tc:opendocument:xmlns:datastyle:1.0\",\n\t\t\t'xmlns:presentation': \"urn:oasis:names:tc:opendocument:xmlns:presentation:1.0\",\n\t\t\t'xmlns:svg':          \"urn:oasis:names:tc:opendocument:xmlns:svg-compatible:1.0\",\n\t\t\t'xmlns:chart':        \"urn:oasis:names:tc:opendocument:xmlns:chart:1.0\",\n\t\t\t'xmlns:dr3d':         \"urn:oasis:names:tc:opendocument:xmlns:dr3d:1.0\",\n\t\t\t'xmlns:math':         \"http://www.w3.org/1998/Math/MathML\",\n\t\t\t'xmlns:form':         \"urn:oasis:names:tc:opendocument:xmlns:form:1.0\",\n\t\t\t'xmlns:script':       \"urn:oasis:names:tc:opendocument:xmlns:script:1.0\",\n\t\t\t'xmlns:ooo':          \"http://openoffice.org/2004/office\",\n\t\t\t'xmlns:ooow':         \"http://openoffice.org/2004/writer\",\n\t\t\t'xmlns:oooc':         \"http://openoffice.org/2004/calc\",\n\t\t\t'xmlns:dom':          \"http://www.w3.org/2001/xml-events\",\n\t\t\t'xmlns:xforms':       \"http://www.w3.org/2002/xforms\",\n\t\t\t'xmlns:xsd':          \"http://www.w3.org/2001/XMLSchema\",\n\t\t\t'xmlns:xsi':          \"http://www.w3.org/2001/XMLSchema-instance\",\n\t\t\t'xmlns:sheet':        \"urn:oasis:names:tc:opendocument:sh33tjs:1.0\",\n\t\t\t'xmlns:rpt':          \"http://openoffice.org/2005/report\",\n\t\t\t'xmlns:of':           \"urn:oasis:names:tc:opendocument:xmlns:of:1.2\",\n\t\t\t'xmlns:xhtml':        \"http://www.w3.org/1999/xhtml\",\n\t\t\t'xmlns:grddl':        \"http://www.w3.org/2003/g/data-view#\",\n\t\t\t'xmlns:tableooo':     \"http://openoffice.org/2009/table\",\n\t\t\t'xmlns:drawooo':      \"http://openoffice.org/2010/draw\",\n\t\t\t'xmlns:calcext':      \"urn:org:documentfoundation:names:experimental:calc:xmlns:calcext:1.0\",\n\t\t\t'xmlns:loext':        \"urn:org:documentfoundation:names:experimental:office:xmlns:loext:1.0\",\n\t\t\t'xmlns:field':        \"urn:openoffice:names:experimental:ooo-ms-interop:xmlns:field:1.0\",\n\t\t\t'xmlns:formx':        \"urn:openoffice:names:experimental:ooxml-odf-interop:xmlns:form:1.0\",\n\t\t\t'xmlns:css3t':        \"http://www.w3.org/TR/css3-text/\",\n\t\t\t'office:version':     \"1.2\"\n\t\t});\n\n\t\tvar fods = wxt_helper({\n\t\t\t'xmlns:config':    \"urn:oasis:names:tc:opendocument:xmlns:config:1.0\",\n\t\t\t'office:mimetype': \"application/vnd.oasis.opendocument.spreadsheet\"\n\t\t});\n\n\t\tif(opts.bookType == \"fods\") {\n\t\t\to.push('<office:document' + attr + fods + '>\\n');\n\t\t\to.push(write_meta_ods().replace(/office:document-meta/g, \"office:meta\"));\n\t\t\t// TODO: settings (equiv of settings.xml for ODS)\n\t\t} else o.push('<office:document-content' + attr  + '>\\n');\n\t\t// o.push('  <office:scripts/>\\n');\n\t\twrite_automatic_styles_ods(o, wb);\n\t\to.push('  <office:body>\\n');\n\t\to.push('    <office:spreadsheet>\\n');\n\t\tfor(var i = 0; i != wb.SheetNames.length; ++i) o.push(write_ws(wb.Sheets[wb.SheetNames[i]], wb, i, opts));\n\t\to.push('    </office:spreadsheet>\\n');\n\t\to.push('  </office:body>\\n');\n\t\tif(opts.bookType == \"fods\") o.push('</office:document>');\n\t\telse o.push('</office:document-content>');\n\t\treturn o.join(\"\");\n\t};\n})();\n\nfunction write_ods(wb/*:any*/, opts/*:any*/) {\n\tif(opts.bookType == \"fods\") return write_content_ods(wb, opts);\n\n\tvar zip = zip_new();\n\tvar f = \"\";\n\n\tvar manifest/*:Array<Array<string> >*/ = [];\n\tvar rdf/*:Array<[string, string]>*/ = [];\n\n\t/* Part 3 Section 3.3 MIME Media Type */\n\tf = \"mimetype\";\n\tzip_add_file(zip, f, \"application/vnd.oasis.opendocument.spreadsheet\");\n\n\t/* Part 1 Section 2.2 Documents */\n\tf = \"content.xml\";\n\tzip_add_file(zip, f, write_content_ods(wb, opts));\n\tmanifest.push([f, \"text/xml\"]);\n\trdf.push([f, \"ContentFile\"]);\n\n\t/* TODO: these are hard-coded styles to satiate excel */\n\tf = \"styles.xml\";\n\tzip_add_file(zip, f, write_styles_ods(wb, opts));\n\tmanifest.push([f, \"text/xml\"]);\n\trdf.push([f, \"StylesFile\"]);\n\n\t/* TODO: this is hard-coded to satiate excel */\n\tf = \"meta.xml\";\n\tzip_add_file(zip, f, XML_HEADER + write_meta_ods(/*::wb, opts*/));\n\tmanifest.push([f, \"text/xml\"]);\n\trdf.push([f, \"MetadataFile\"]);\n\n\t/* Part 3 Section 6 Metadata Manifest File */\n\tf = \"manifest.rdf\";\n\tzip_add_file(zip, f, write_rdf(rdf/*, opts*/));\n\tmanifest.push([f, \"application/rdf+xml\"]);\n\n\t/* Part 3 Section 4 Manifest File */\n\tf = \"META-INF/manifest.xml\";\n\tzip_add_file(zip, f, write_manifest(manifest/*, opts*/));\n\n\treturn zip;\n}\n\n/*! sheetjs (C) 2013-present SheetJS -- http://sheetjs.com */\nfunction u8_to_dataview(array) {\n  return new DataView(array.buffer, array.byteOffset, array.byteLength);\n}\nfunction u8str(u8) {\n  return typeof TextDecoder != \"undefined\" ? new TextDecoder().decode(u8) : utf8read(a2s(u8));\n}\nfunction stru8(str) {\n  return typeof TextEncoder != \"undefined\" ? new TextEncoder().encode(str) : s2a(utf8write(str));\n}\nfunction u8contains(body, search) {\n  outer:\n    for (var L = 0; L <= body.length - search.length; ++L) {\n      for (var j = 0; j < search.length; ++j)\n        if (body[L + j] != search[j])\n          continue outer;\n      return true;\n    }\n  return false;\n}\nfunction u8concat(u8a) {\n  var len = u8a.reduce(function(acc, x) {\n    return acc + x.length;\n  }, 0);\n  var out = new Uint8Array(len);\n  var off = 0;\n  u8a.forEach(function(u8) {\n    out.set(u8, off);\n    off += u8.length;\n  });\n  return out;\n}\nfunction popcnt(x) {\n  x -= x >> 1 & 1431655765;\n  x = (x & 858993459) + (x >> 2 & 858993459);\n  return (x + (x >> 4) & 252645135) * 16843009 >>> 24;\n}\nfunction readDecimal128LE(buf, offset) {\n  var exp = (buf[offset + 15] & 127) << 7 | buf[offset + 14] >> 1;\n  var mantissa = buf[offset + 14] & 1;\n  for (var j = offset + 13; j >= offset; --j)\n    mantissa = mantissa * 256 + buf[j];\n  return (buf[offset + 15] & 128 ? -mantissa : mantissa) * Math.pow(10, exp - 6176);\n}\nfunction writeDecimal128LE(buf, offset, value) {\n  var exp = Math.floor(value == 0 ? 0 : Math.LOG10E * Math.log(Math.abs(value))) + 6176 - 20;\n  var mantissa = value / Math.pow(10, exp - 6176);\n  buf[offset + 15] |= exp >> 7;\n  buf[offset + 14] |= (exp & 127) << 1;\n  for (var i = 0; mantissa >= 1; ++i, mantissa /= 256)\n    buf[offset + i] = mantissa & 255;\n  buf[offset + 15] |= value >= 0 ? 0 : 128;\n}\nfunction parse_varint49(buf, ptr) {\n  var l = ptr ? ptr[0] : 0;\n  var usz = buf[l] & 127;\n  varint:\n    if (buf[l++] >= 128) {\n      usz |= (buf[l] & 127) << 7;\n      if (buf[l++] < 128)\n        break varint;\n      usz |= (buf[l] & 127) << 14;\n      if (buf[l++] < 128)\n        break varint;\n      usz |= (buf[l] & 127) << 21;\n      if (buf[l++] < 128)\n        break varint;\n      usz += (buf[l] & 127) * Math.pow(2, 28);\n      ++l;\n      if (buf[l++] < 128)\n        break varint;\n      usz += (buf[l] & 127) * Math.pow(2, 35);\n      ++l;\n      if (buf[l++] < 128)\n        break varint;\n      usz += (buf[l] & 127) * Math.pow(2, 42);\n      ++l;\n      if (buf[l++] < 128)\n        break varint;\n    }\n  if (ptr)\n    ptr[0] = l;\n  return usz;\n}\nfunction write_varint49(v) {\n  var usz = new Uint8Array(7);\n  usz[0] = v & 127;\n  var L = 1;\n  sz:\n    if (v > 127) {\n      usz[L - 1] |= 128;\n      usz[L] = v >> 7 & 127;\n      ++L;\n      if (v <= 16383)\n        break sz;\n      usz[L - 1] |= 128;\n      usz[L] = v >> 14 & 127;\n      ++L;\n      if (v <= 2097151)\n        break sz;\n      usz[L - 1] |= 128;\n      usz[L] = v >> 21 & 127;\n      ++L;\n      if (v <= 268435455)\n        break sz;\n      usz[L - 1] |= 128;\n      usz[L] = v / 256 >>> 21 & 127;\n      ++L;\n      if (v <= 34359738367)\n        break sz;\n      usz[L - 1] |= 128;\n      usz[L] = v / 65536 >>> 21 & 127;\n      ++L;\n      if (v <= 4398046511103)\n        break sz;\n      usz[L - 1] |= 128;\n      usz[L] = v / 16777216 >>> 21 & 127;\n      ++L;\n    }\n  return usz.slice(0, L);\n}\nfunction varint_to_i32(buf) {\n  var l = 0, i32 = buf[l] & 127;\n  varint:\n    if (buf[l++] >= 128) {\n      i32 |= (buf[l] & 127) << 7;\n      if (buf[l++] < 128)\n        break varint;\n      i32 |= (buf[l] & 127) << 14;\n      if (buf[l++] < 128)\n        break varint;\n      i32 |= (buf[l] & 127) << 21;\n      if (buf[l++] < 128)\n        break varint;\n      i32 |= (buf[l] & 127) << 28;\n    }\n  return i32;\n}\nfunction parse_shallow(buf) {\n  var out = [], ptr = [0];\n  while (ptr[0] < buf.length) {\n    var off = ptr[0];\n    var num = parse_varint49(buf, ptr);\n    var type = num & 7;\n    num = Math.floor(num / 8);\n    var len = 0;\n    var res;\n    if (num == 0)\n      break;\n    switch (type) {\n      case 0:\n        {\n          var l = ptr[0];\n          while (buf[ptr[0]++] >= 128)\n            ;\n          res = buf.slice(l, ptr[0]);\n        }\n        break;\n      case 5:\n        len = 4;\n        res = buf.slice(ptr[0], ptr[0] + len);\n        ptr[0] += len;\n        break;\n      case 1:\n        len = 8;\n        res = buf.slice(ptr[0], ptr[0] + len);\n        ptr[0] += len;\n        break;\n      case 2:\n        len = parse_varint49(buf, ptr);\n        res = buf.slice(ptr[0], ptr[0] + len);\n        ptr[0] += len;\n        break;\n      case 3:\n      case 4:\n      default:\n        throw new Error(\"PB Type \".concat(type, \" for Field \").concat(num, \" at offset \").concat(off));\n    }\n    var v = { data: res, type: type };\n    if (out[num] == null)\n      out[num] = [v];\n    else\n      out[num].push(v);\n  }\n  return out;\n}\nfunction write_shallow(proto) {\n  var out = [];\n  proto.forEach(function(field, idx) {\n    field.forEach(function(item) {\n      if (!item.data)\n        return;\n      out.push(write_varint49(idx * 8 + item.type));\n      if (item.type == 2)\n        out.push(write_varint49(item.data.length));\n      out.push(item.data);\n    });\n  });\n  return u8concat(out);\n}\nfunction mappa(data, cb) {\n  return (data == null ? void 0 : data.map(function(d) {\n    return cb(d.data);\n  })) || [];\n}\nfunction parse_iwa_file(buf) {\n  var _a;\n  var out = [], ptr = [0];\n  while (ptr[0] < buf.length) {\n    var len = parse_varint49(buf, ptr);\n    var ai = parse_shallow(buf.slice(ptr[0], ptr[0] + len));\n    ptr[0] += len;\n    var res = {\n      id: varint_to_i32(ai[1][0].data),\n      messages: []\n    };\n    ai[2].forEach(function(b) {\n      var mi = parse_shallow(b.data);\n      var fl = varint_to_i32(mi[3][0].data);\n      res.messages.push({\n        meta: mi,\n        data: buf.slice(ptr[0], ptr[0] + fl)\n      });\n      ptr[0] += fl;\n    });\n    if ((_a = ai[3]) == null ? void 0 : _a[0])\n      res.merge = varint_to_i32(ai[3][0].data) >>> 0 > 0;\n    out.push(res);\n  }\n  return out;\n}\nfunction write_iwa_file(ias) {\n  var bufs = [];\n  ias.forEach(function(ia) {\n    var ai = [];\n    ai[1] = [{ data: write_varint49(ia.id), type: 0 }];\n    ai[2] = [];\n    if (ia.merge != null)\n      ai[3] = [{ data: write_varint49(+!!ia.merge), type: 0 }];\n    var midata = [];\n    ia.messages.forEach(function(mi) {\n      midata.push(mi.data);\n      mi.meta[3] = [{ type: 0, data: write_varint49(mi.data.length) }];\n      ai[2].push({ data: write_shallow(mi.meta), type: 2 });\n    });\n    var aipayload = write_shallow(ai);\n    bufs.push(write_varint49(aipayload.length));\n    bufs.push(aipayload);\n    midata.forEach(function(mid) {\n      return bufs.push(mid);\n    });\n  });\n  return u8concat(bufs);\n}\nfunction parse_snappy_chunk(type, buf) {\n  if (type != 0)\n    throw new Error(\"Unexpected Snappy chunk type \".concat(type));\n  var ptr = [0];\n  var usz = parse_varint49(buf, ptr);\n  var chunks = [];\n  while (ptr[0] < buf.length) {\n    var tag = buf[ptr[0]] & 3;\n    if (tag == 0) {\n      var len = buf[ptr[0]++] >> 2;\n      if (len < 60)\n        ++len;\n      else {\n        var c = len - 59;\n        len = buf[ptr[0]];\n        if (c > 1)\n          len |= buf[ptr[0] + 1] << 8;\n        if (c > 2)\n          len |= buf[ptr[0] + 2] << 16;\n        if (c > 3)\n          len |= buf[ptr[0] + 3] << 24;\n        len >>>= 0;\n        len++;\n        ptr[0] += c;\n      }\n      chunks.push(buf.slice(ptr[0], ptr[0] + len));\n      ptr[0] += len;\n      continue;\n    } else {\n      var offset = 0, length = 0;\n      if (tag == 1) {\n        length = (buf[ptr[0]] >> 2 & 7) + 4;\n        offset = (buf[ptr[0]++] & 224) << 3;\n        offset |= buf[ptr[0]++];\n      } else {\n        length = (buf[ptr[0]++] >> 2) + 1;\n        if (tag == 2) {\n          offset = buf[ptr[0]] | buf[ptr[0] + 1] << 8;\n          ptr[0] += 2;\n        } else {\n          offset = (buf[ptr[0]] | buf[ptr[0] + 1] << 8 | buf[ptr[0] + 2] << 16 | buf[ptr[0] + 3] << 24) >>> 0;\n          ptr[0] += 4;\n        }\n      }\n      chunks = [u8concat(chunks)];\n      if (offset == 0)\n        throw new Error(\"Invalid offset 0\");\n      if (offset > chunks[0].length)\n        throw new Error(\"Invalid offset beyond length\");\n      if (length >= offset) {\n        chunks.push(chunks[0].slice(-offset));\n        length -= offset;\n        while (length >= chunks[chunks.length - 1].length) {\n          chunks.push(chunks[chunks.length - 1]);\n          length -= chunks[chunks.length - 1].length;\n        }\n      }\n      chunks.push(chunks[0].slice(-offset, -offset + length));\n    }\n  }\n  var o = u8concat(chunks);\n  if (o.length != usz)\n    throw new Error(\"Unexpected length: \".concat(o.length, \" != \").concat(usz));\n  return o;\n}\nfunction decompress_iwa_file(buf) {\n  var out = [];\n  var l = 0;\n  while (l < buf.length) {\n    var t = buf[l++];\n    var len = buf[l] | buf[l + 1] << 8 | buf[l + 2] << 16;\n    l += 3;\n    out.push(parse_snappy_chunk(t, buf.slice(l, l + len)));\n    l += len;\n  }\n  if (l !== buf.length)\n    throw new Error(\"data is not a valid framed stream!\");\n  return u8concat(out);\n}\nfunction compress_iwa_file(buf) {\n  var out = [];\n  var l = 0;\n  while (l < buf.length) {\n    var c = Math.min(buf.length - l, 268435455);\n    var frame = new Uint8Array(4);\n    out.push(frame);\n    var usz = write_varint49(c);\n    var L = usz.length;\n    out.push(usz);\n    if (c <= 60) {\n      L++;\n      out.push(new Uint8Array([c - 1 << 2]));\n    } else if (c <= 256) {\n      L += 2;\n      out.push(new Uint8Array([240, c - 1 & 255]));\n    } else if (c <= 65536) {\n      L += 3;\n      out.push(new Uint8Array([244, c - 1 & 255, c - 1 >> 8 & 255]));\n    } else if (c <= 16777216) {\n      L += 4;\n      out.push(new Uint8Array([248, c - 1 & 255, c - 1 >> 8 & 255, c - 1 >> 16 & 255]));\n    } else if (c <= 4294967296) {\n      L += 5;\n      out.push(new Uint8Array([252, c - 1 & 255, c - 1 >> 8 & 255, c - 1 >> 16 & 255, c - 1 >>> 24 & 255]));\n    }\n    out.push(buf.slice(l, l + c));\n    L += c;\n    frame[0] = 0;\n    frame[1] = L & 255;\n    frame[2] = L >> 8 & 255;\n    frame[3] = L >> 16 & 255;\n    l += c;\n  }\n  return u8concat(out);\n}\nfunction parse_old_storage(buf, sst, rsst, v) {\n  var dv = u8_to_dataview(buf);\n  var flags = dv.getUint32(4, true);\n  var data_offset = (v > 1 ? 12 : 8) + popcnt(flags & (v > 1 ? 3470 : 398)) * 4;\n  var ridx = -1, sidx = -1, ieee = NaN, dt = new Date(2001, 0, 1);\n  if (flags & 512) {\n    ridx = dv.getUint32(data_offset, true);\n    data_offset += 4;\n  }\n  data_offset += popcnt(flags & (v > 1 ? 12288 : 4096)) * 4;\n  if (flags & 16) {\n    sidx = dv.getUint32(data_offset, true);\n    data_offset += 4;\n  }\n  if (flags & 32) {\n    ieee = dv.getFloat64(data_offset, true);\n    data_offset += 8;\n  }\n  if (flags & 64) {\n    dt.setTime(dt.getTime() + dv.getFloat64(data_offset, true) * 1e3);\n    data_offset += 8;\n  }\n  var ret;\n  switch (buf[2]) {\n    case 0:\n      break;\n    case 2:\n      ret = { t: \"n\", v: ieee };\n      break;\n    case 3:\n      ret = { t: \"s\", v: sst[sidx] };\n      break;\n    case 5:\n      ret = { t: \"d\", v: dt };\n      break;\n    case 6:\n      ret = { t: \"b\", v: ieee > 0 };\n      break;\n    case 7:\n      ret = { t: \"n\", v: ieee / 86400 };\n      break;\n    case 8:\n      ret = { t: \"e\", v: 0 };\n      break;\n    case 9:\n      {\n        if (ridx > -1)\n          ret = { t: \"s\", v: rsst[ridx] };\n        else if (sidx > -1)\n          ret = { t: \"s\", v: sst[sidx] };\n        else if (!isNaN(ieee))\n          ret = { t: \"n\", v: ieee };\n        else\n          throw new Error(\"Unsupported cell type \".concat(buf.slice(0, 4)));\n      }\n      break;\n    default:\n      throw new Error(\"Unsupported cell type \".concat(buf.slice(0, 4)));\n  }\n  return ret;\n}\nfunction parse_new_storage(buf, sst, rsst) {\n  var dv = u8_to_dataview(buf);\n  var flags = dv.getUint32(8, true);\n  var data_offset = 12;\n  var ridx = -1, sidx = -1, d128 = NaN, ieee = NaN, dt = new Date(2001, 0, 1);\n  if (flags & 1) {\n    d128 = readDecimal128LE(buf, data_offset);\n    data_offset += 16;\n  }\n  if (flags & 2) {\n    ieee = dv.getFloat64(data_offset, true);\n    data_offset += 8;\n  }\n  if (flags & 4) {\n    dt.setTime(dt.getTime() + dv.getFloat64(data_offset, true) * 1e3);\n    data_offset += 8;\n  }\n  if (flags & 8) {\n    sidx = dv.getUint32(data_offset, true);\n    data_offset += 4;\n  }\n  if (flags & 16) {\n    ridx = dv.getUint32(data_offset, true);\n    data_offset += 4;\n  }\n  var ret;\n  switch (buf[1]) {\n    case 0:\n      break;\n    case 2:\n      ret = { t: \"n\", v: d128 };\n      break;\n    case 3:\n      ret = { t: \"s\", v: sst[sidx] };\n      break;\n    case 5:\n      ret = { t: \"d\", v: dt };\n      break;\n    case 6:\n      ret = { t: \"b\", v: ieee > 0 };\n      break;\n    case 7:\n      ret = { t: \"n\", v: ieee / 86400 };\n      break;\n    case 8:\n      ret = { t: \"e\", v: 0 };\n      break;\n    case 9:\n      {\n        if (ridx > -1)\n          ret = { t: \"s\", v: rsst[ridx] };\n        else\n          throw new Error(\"Unsupported cell type \".concat(buf[1], \" : \").concat(flags & 31, \" : \").concat(buf.slice(0, 4)));\n      }\n      break;\n    case 10:\n      ret = { t: \"n\", v: d128 };\n      break;\n    default:\n      throw new Error(\"Unsupported cell type \".concat(buf[1], \" : \").concat(flags & 31, \" : \").concat(buf.slice(0, 4)));\n  }\n  return ret;\n}\nfunction write_new_storage(cell, sst) {\n  var out = new Uint8Array(32), dv = u8_to_dataview(out), l = 12, flags = 0;\n  out[0] = 5;\n  switch (cell.t) {\n    case \"n\":\n      out[1] = 2;\n      writeDecimal128LE(out, l, cell.v);\n      flags |= 1;\n      l += 16;\n      break;\n    case \"b\":\n      out[1] = 6;\n      dv.setFloat64(l, cell.v ? 1 : 0, true);\n      flags |= 2;\n      l += 8;\n      break;\n    case \"s\":\n      if (sst.indexOf(cell.v) == -1)\n        throw new Error(\"Value \".concat(cell.v, \" missing from SST!\"));\n      out[1] = 3;\n      dv.setUint32(l, sst.indexOf(cell.v), true);\n      flags |= 8;\n      l += 4;\n      break;\n    default:\n      throw \"unsupported cell type \" + cell.t;\n  }\n  dv.setUint32(8, flags, true);\n  return out.slice(0, l);\n}\nfunction write_old_storage(cell, sst) {\n  var out = new Uint8Array(32), dv = u8_to_dataview(out), l = 12, flags = 0;\n  out[0] = 3;\n  switch (cell.t) {\n    case \"n\":\n      out[2] = 2;\n      dv.setFloat64(l, cell.v, true);\n      flags |= 32;\n      l += 8;\n      break;\n    case \"b\":\n      out[2] = 6;\n      dv.setFloat64(l, cell.v ? 1 : 0, true);\n      flags |= 32;\n      l += 8;\n      break;\n    case \"s\":\n      if (sst.indexOf(cell.v) == -1)\n        throw new Error(\"Value \".concat(cell.v, \" missing from SST!\"));\n      out[2] = 3;\n      dv.setUint32(l, sst.indexOf(cell.v), true);\n      flags |= 16;\n      l += 4;\n      break;\n    default:\n      throw \"unsupported cell type \" + cell.t;\n  }\n  dv.setUint32(4, flags, true);\n  return out.slice(0, l);\n}\nfunction parse_cell_storage(buf, sst, rsst) {\n  switch (buf[0]) {\n    case 0:\n    case 1:\n    case 2:\n    case 3:\n      return parse_old_storage(buf, sst, rsst, buf[0]);\n    case 5:\n      return parse_new_storage(buf, sst, rsst);\n    default:\n      throw new Error(\"Unsupported payload version \".concat(buf[0]));\n  }\n}\nfunction parse_TSP_Reference(buf) {\n  var pb = parse_shallow(buf);\n  return parse_varint49(pb[1][0].data);\n}\nfunction write_TSP_Reference(idx) {\n  var out = [];\n  out[1] = [{ type: 0, data: write_varint49(idx) }];\n  return write_shallow(out);\n}\nfunction parse_TST_TableDataList(M, root) {\n  var pb = parse_shallow(root.data);\n  var type = varint_to_i32(pb[1][0].data);\n  var entries = pb[3];\n  var data = [];\n  (entries || []).forEach(function(entry) {\n    var le = parse_shallow(entry.data);\n    var key = varint_to_i32(le[1][0].data) >>> 0;\n    switch (type) {\n      case 1:\n        data[key] = u8str(le[3][0].data);\n        break;\n      case 8:\n        {\n          var rt = M[parse_TSP_Reference(le[9][0].data)][0];\n          var rtp = parse_shallow(rt.data);\n          var rtpref = M[parse_TSP_Reference(rtp[1][0].data)][0];\n          var mtype = varint_to_i32(rtpref.meta[1][0].data);\n          if (mtype != 2001)\n            throw new Error(\"2000 unexpected reference to \".concat(mtype));\n          var tswpsa = parse_shallow(rtpref.data);\n          data[key] = tswpsa[3].map(function(x) {\n            return u8str(x.data);\n          }).join(\"\");\n        }\n        break;\n    }\n  });\n  return data;\n}\nfunction parse_TST_TileRowInfo(u8, type) {\n  var _a, _b, _c, _d, _e, _f, _g, _h, _i, _j, _k, _l, _m, _n;\n  var pb = parse_shallow(u8);\n  var R = varint_to_i32(pb[1][0].data) >>> 0;\n  var cnt = varint_to_i32(pb[2][0].data) >>> 0;\n  var wide_offsets = ((_b = (_a = pb[8]) == null ? void 0 : _a[0]) == null ? void 0 : _b.data) && varint_to_i32(pb[8][0].data) > 0 || false;\n  var used_storage_u8, used_storage;\n  if (((_d = (_c = pb[7]) == null ? void 0 : _c[0]) == null ? void 0 : _d.data) && type != 0) {\n    used_storage_u8 = (_f = (_e = pb[7]) == null ? void 0 : _e[0]) == null ? void 0 : _f.data;\n    used_storage = (_h = (_g = pb[6]) == null ? void 0 : _g[0]) == null ? void 0 : _h.data;\n  } else if (((_j = (_i = pb[4]) == null ? void 0 : _i[0]) == null ? void 0 : _j.data) && type != 1) {\n    used_storage_u8 = (_l = (_k = pb[4]) == null ? void 0 : _k[0]) == null ? void 0 : _l.data;\n    used_storage = (_n = (_m = pb[3]) == null ? void 0 : _m[0]) == null ? void 0 : _n.data;\n  } else\n    throw \"NUMBERS Tile missing \".concat(type, \" cell storage\");\n  var width = wide_offsets ? 4 : 1;\n  var used_storage_offsets = u8_to_dataview(used_storage_u8);\n  var offsets = [];\n  for (var C = 0; C < used_storage_u8.length / 2; ++C) {\n    var off = used_storage_offsets.getUint16(C * 2, true);\n    if (off < 65535)\n      offsets.push([C, off]);\n  }\n  if (offsets.length != cnt)\n    throw \"Expected \".concat(cnt, \" cells, found \").concat(offsets.length);\n  var cells = [];\n  for (C = 0; C < offsets.length - 1; ++C)\n    cells[offsets[C][0]] = used_storage.subarray(offsets[C][1] * width, offsets[C + 1][1] * width);\n  if (offsets.length >= 1)\n    cells[offsets[offsets.length - 1][0]] = used_storage.subarray(offsets[offsets.length - 1][1] * width);\n  return { R: R, cells: cells };\n}\nfunction parse_TST_Tile(M, root) {\n  var _a;\n  var pb = parse_shallow(root.data);\n  var storage = ((_a = pb == null ? void 0 : pb[7]) == null ? void 0 : _a[0]) ? varint_to_i32(pb[7][0].data) >>> 0 > 0 ? 1 : 0 : -1;\n  var ri = mappa(pb[5], function(u8) {\n    return parse_TST_TileRowInfo(u8, storage);\n  });\n  return {\n    nrows: varint_to_i32(pb[4][0].data) >>> 0,\n    data: ri.reduce(function(acc, x) {\n      if (!acc[x.R])\n        acc[x.R] = [];\n      x.cells.forEach(function(cell, C) {\n        if (acc[x.R][C])\n          throw new Error(\"Duplicate cell r=\".concat(x.R, \" c=\").concat(C));\n        acc[x.R][C] = cell;\n      });\n      return acc;\n    }, [])\n  };\n}\nfunction parse_TST_TableModelArchive(M, root, ws) {\n  var _a;\n  var pb = parse_shallow(root.data);\n  var range = { s: { r: 0, c: 0 }, e: { r: 0, c: 0 } };\n  range.e.r = (varint_to_i32(pb[6][0].data) >>> 0) - 1;\n  if (range.e.r < 0)\n    throw new Error(\"Invalid row varint \".concat(pb[6][0].data));\n  range.e.c = (varint_to_i32(pb[7][0].data) >>> 0) - 1;\n  if (range.e.c < 0)\n    throw new Error(\"Invalid col varint \".concat(pb[7][0].data));\n  ws[\"!ref\"] = encode_range(range);\n  var store = parse_shallow(pb[4][0].data);\n  var sst = parse_TST_TableDataList(M, M[parse_TSP_Reference(store[4][0].data)][0]);\n  var rsst = ((_a = store[17]) == null ? void 0 : _a[0]) ? parse_TST_TableDataList(M, M[parse_TSP_Reference(store[17][0].data)][0]) : [];\n  var tile = parse_shallow(store[3][0].data);\n  var _R = 0;\n  tile[1].forEach(function(t) {\n    var tl = parse_shallow(t.data);\n    var ref = M[parse_TSP_Reference(tl[2][0].data)][0];\n    var mtype = varint_to_i32(ref.meta[1][0].data);\n    if (mtype != 6002)\n      throw new Error(\"6001 unexpected reference to \".concat(mtype));\n    var _tile = parse_TST_Tile(M, ref);\n    _tile.data.forEach(function(row, R) {\n      row.forEach(function(buf, C) {\n        var addr = encode_cell({ r: _R + R, c: C });\n        var res = parse_cell_storage(buf, sst, rsst);\n        if (res)\n          ws[addr] = res;\n      });\n    });\n    _R += _tile.nrows;\n  });\n}\nfunction parse_TST_TableInfoArchive(M, root) {\n  var pb = parse_shallow(root.data);\n  var out = { \"!ref\": \"A1\" };\n  var tableref = M[parse_TSP_Reference(pb[2][0].data)];\n  var mtype = varint_to_i32(tableref[0].meta[1][0].data);\n  if (mtype != 6001)\n    throw new Error(\"6000 unexpected reference to \".concat(mtype));\n  parse_TST_TableModelArchive(M, tableref[0], out);\n  return out;\n}\nfunction parse_TN_SheetArchive(M, root) {\n  var _a;\n  var pb = parse_shallow(root.data);\n  var out = {\n    name: ((_a = pb[1]) == null ? void 0 : _a[0]) ? u8str(pb[1][0].data) : \"\",\n    sheets: []\n  };\n  var shapeoffs = mappa(pb[2], parse_TSP_Reference);\n  shapeoffs.forEach(function(off) {\n    M[off].forEach(function(m) {\n      var mtype = varint_to_i32(m.meta[1][0].data);\n      if (mtype == 6e3)\n        out.sheets.push(parse_TST_TableInfoArchive(M, m));\n    });\n  });\n  return out;\n}\nfunction parse_TN_DocumentArchive(M, root) {\n  var out = book_new();\n  var pb = parse_shallow(root.data);\n  var sheetoffs = mappa(pb[1], parse_TSP_Reference);\n  sheetoffs.forEach(function(off) {\n    M[off].forEach(function(m) {\n      var mtype = varint_to_i32(m.meta[1][0].data);\n      if (mtype == 2) {\n        var root2 = parse_TN_SheetArchive(M, m);\n        root2.sheets.forEach(function(sheet, idx) {\n          book_append_sheet(out, sheet, idx == 0 ? root2.name : root2.name + \"_\" + idx, true);\n        });\n      }\n    });\n  });\n  if (out.SheetNames.length == 0)\n    throw new Error(\"Empty NUMBERS file\");\n  return out;\n}\nfunction parse_numbers_iwa(cfb) {\n  var _a, _b, _c, _d;\n  var M = {}, indices = [];\n  cfb.FullPaths.forEach(function(p) {\n    if (p.match(/\\.iwpv2/))\n      throw new Error(\"Unsupported password protection\");\n  });\n  cfb.FileIndex.forEach(function(s) {\n    if (!s.name.match(/\\.iwa$/))\n      return;\n    var o;\n    try {\n      o = decompress_iwa_file(s.content);\n    } catch (e) {\n      return console.log(\"?? \" + s.content.length + \" \" + (e.message || e));\n    }\n    var packets;\n    try {\n      packets = parse_iwa_file(o);\n    } catch (e) {\n      return console.log(\"## \" + (e.message || e));\n    }\n    packets.forEach(function(packet) {\n      M[packet.id] = packet.messages;\n      indices.push(packet.id);\n    });\n  });\n  if (!indices.length)\n    throw new Error(\"File has no messages\");\n  var docroot = ((_d = (_c = (_b = (_a = M == null ? void 0 : M[1]) == null ? void 0 : _a[0]) == null ? void 0 : _b.meta) == null ? void 0 : _c[1]) == null ? void 0 : _d[0].data) && varint_to_i32(M[1][0].meta[1][0].data) == 1 && M[1][0];\n  if (!docroot)\n    indices.forEach(function(idx) {\n      M[idx].forEach(function(iwam) {\n        var mtype = varint_to_i32(iwam.meta[1][0].data) >>> 0;\n        if (mtype == 1) {\n          if (!docroot)\n            docroot = iwam;\n          else\n            throw new Error(\"Document has multiple roots\");\n        }\n      });\n    });\n  if (!docroot)\n    throw new Error(\"Cannot find Document root\");\n  return parse_TN_DocumentArchive(M, docroot);\n}\nfunction write_tile_row(tri, data, SST) {\n  var _a, _b, _c, _d;\n  if (!((_a = tri[6]) == null ? void 0 : _a[0]) || !((_b = tri[7]) == null ? void 0 : _b[0]))\n    throw \"Mutation only works on post-BNC storages!\";\n  var wide_offsets = ((_d = (_c = tri[8]) == null ? void 0 : _c[0]) == null ? void 0 : _d.data) && varint_to_i32(tri[8][0].data) > 0 || false;\n  if (wide_offsets)\n    throw \"Math only works with normal offsets\";\n  var cnt = 0;\n  var dv = u8_to_dataview(tri[7][0].data), last_offset = 0, cell_storage = [];\n  var _dv = u8_to_dataview(tri[4][0].data), _last_offset = 0, _cell_storage = [];\n  for (var C = 0; C < data.length; ++C) {\n    if (data[C] == null) {\n      dv.setUint16(C * 2, 65535, true);\n      _dv.setUint16(C * 2, 65535);\n      continue;\n    }\n    dv.setUint16(C * 2, last_offset, true);\n    _dv.setUint16(C * 2, _last_offset, true);\n    var celload, _celload;\n    switch (typeof data[C]) {\n      case \"string\":\n        celload = write_new_storage({ t: \"s\", v: data[C] }, SST);\n        _celload = write_old_storage({ t: \"s\", v: data[C] }, SST);\n        break;\n      case \"number\":\n        celload = write_new_storage({ t: \"n\", v: data[C] }, SST);\n        _celload = write_old_storage({ t: \"n\", v: data[C] }, SST);\n        break;\n      case \"boolean\":\n        celload = write_new_storage({ t: \"b\", v: data[C] }, SST);\n        _celload = write_old_storage({ t: \"b\", v: data[C] }, SST);\n        break;\n      default:\n        throw new Error(\"Unsupported value \" + data[C]);\n    }\n    cell_storage.push(celload);\n    last_offset += celload.length;\n    _cell_storage.push(_celload);\n    _last_offset += _celload.length;\n    ++cnt;\n  }\n  tri[2][0].data = write_varint49(cnt);\n  for (; C < tri[7][0].data.length / 2; ++C) {\n    dv.setUint16(C * 2, 65535, true);\n    _dv.setUint16(C * 2, 65535, true);\n  }\n  tri[6][0].data = u8concat(cell_storage);\n  tri[3][0].data = u8concat(_cell_storage);\n  return cnt;\n}\nfunction write_numbers_iwa(wb, opts) {\n  if (!opts || !opts.numbers)\n    throw new Error(\"Must pass a `numbers` option -- check the README\");\n  var ws = wb.Sheets[wb.SheetNames[0]];\n  if (wb.SheetNames.length > 1)\n    console.error(\"The Numbers writer currently writes only the first table\");\n  var range = decode_range(ws[\"!ref\"]);\n  range.s.r = range.s.c = 0;\n  var trunc = false;\n  if (range.e.c > 9) {\n    trunc = true;\n    range.e.c = 9;\n  }\n  if (range.e.r > 49) {\n    trunc = true;\n    range.e.r = 49;\n  }\n  if (trunc)\n    console.error(\"The Numbers writer is currently limited to \".concat(encode_range(range)));\n  var data = sheet_to_json(ws, { range: range, header: 1 });\n  var SST = [\"~Sh33tJ5~\"];\n  data.forEach(function(row) {\n    return row.forEach(function(cell) {\n      if (typeof cell == \"string\")\n        SST.push(cell);\n    });\n  });\n  var dependents = {};\n  var indices = [];\n  var cfb = CFB.read(opts.numbers, { type: \"base64\" });\n  cfb.FileIndex.map(function(fi, idx) {\n    return [fi, cfb.FullPaths[idx]];\n  }).forEach(function(row) {\n    var fi = row[0], fp = row[1];\n    if (fi.type != 2)\n      return;\n    if (!fi.name.match(/\\.iwa/))\n      return;\n    var old_content = fi.content;\n    var raw1 = decompress_iwa_file(old_content);\n    var x2 = parse_iwa_file(raw1);\n    x2.forEach(function(packet2) {\n      indices.push(packet2.id);\n      dependents[packet2.id] = { deps: [], location: fp, type: varint_to_i32(packet2.messages[0].meta[1][0].data) };\n    });\n  });\n  indices.sort(function(x2, y2) {\n    return x2 - y2;\n  });\n  var indices_varint = indices.filter(function(x2) {\n    return x2 > 1;\n  }).map(function(x2) {\n    return [x2, write_varint49(x2)];\n  });\n  cfb.FileIndex.map(function(fi, idx) {\n    return [fi, cfb.FullPaths[idx]];\n  }).forEach(function(row) {\n    var fi = row[0], fp = row[1];\n    if (!fi.name.match(/\\.iwa/))\n      return;\n    var x2 = parse_iwa_file(decompress_iwa_file(fi.content));\n    x2.forEach(function(ia) {\n      ia.messages.forEach(function(m) {\n        indices_varint.forEach(function(ivi) {\n          if (ia.messages.some(function(mess) {\n            return varint_to_i32(mess.meta[1][0].data) != 11006 && u8contains(mess.data, ivi[1]);\n          })) {\n            dependents[ivi[0]].deps.push(ia.id);\n          }\n        });\n      });\n    });\n  });\n  function get_unique_msgid() {\n    for (var i = 927262; i < 2e6; ++i)\n      if (!dependents[i])\n        return i;\n    throw new Error(\"Too many messages\");\n  }\n  var entry = CFB.find(cfb, dependents[1].location);\n  var x = parse_iwa_file(decompress_iwa_file(entry.content));\n  var docroot;\n  for (var xi = 0; xi < x.length; ++xi) {\n    var packet = x[xi];\n    if (packet.id == 1)\n      docroot = packet;\n  }\n  var sheetrootref = parse_TSP_Reference(parse_shallow(docroot.messages[0].data)[1][0].data);\n  entry = CFB.find(cfb, dependents[sheetrootref].location);\n  x = parse_iwa_file(decompress_iwa_file(entry.content));\n  for (xi = 0; xi < x.length; ++xi) {\n    packet = x[xi];\n    if (packet.id == sheetrootref)\n      docroot = packet;\n  }\n  sheetrootref = parse_TSP_Reference(parse_shallow(docroot.messages[0].data)[2][0].data);\n  entry = CFB.find(cfb, dependents[sheetrootref].location);\n  x = parse_iwa_file(decompress_iwa_file(entry.content));\n  for (xi = 0; xi < x.length; ++xi) {\n    packet = x[xi];\n    if (packet.id == sheetrootref)\n      docroot = packet;\n  }\n  sheetrootref = parse_TSP_Reference(parse_shallow(docroot.messages[0].data)[2][0].data);\n  entry = CFB.find(cfb, dependents[sheetrootref].location);\n  x = parse_iwa_file(decompress_iwa_file(entry.content));\n  for (xi = 0; xi < x.length; ++xi) {\n    packet = x[xi];\n    if (packet.id == sheetrootref)\n      docroot = packet;\n  }\n  var pb = parse_shallow(docroot.messages[0].data);\n  {\n    pb[6][0].data = write_varint49(range.e.r + 1);\n    pb[7][0].data = write_varint49(range.e.c + 1);\n    var cruidsref = parse_TSP_Reference(pb[46][0].data);\n    var oldbucket = CFB.find(cfb, dependents[cruidsref].location);\n    var _x = parse_iwa_file(decompress_iwa_file(oldbucket.content));\n    {\n      for (var j = 0; j < _x.length; ++j) {\n        if (_x[j].id == cruidsref)\n          break;\n      }\n      if (_x[j].id != cruidsref)\n        throw \"Bad ColumnRowUIDMapArchive\";\n      var cruids = parse_shallow(_x[j].messages[0].data);\n      cruids[1] = [];\n      cruids[2] = [], cruids[3] = [];\n      for (var C = 0; C <= range.e.c; ++C) {\n        var uuid = [];\n        uuid[1] = uuid[2] = [{ type: 0, data: write_varint49(C + 420690) }];\n        cruids[1].push({ type: 2, data: write_shallow(uuid) });\n        cruids[2].push({ type: 0, data: write_varint49(C) });\n        cruids[3].push({ type: 0, data: write_varint49(C) });\n      }\n      cruids[4] = [];\n      cruids[5] = [], cruids[6] = [];\n      for (var R = 0; R <= range.e.r; ++R) {\n        uuid = [];\n        uuid[1] = uuid[2] = [{ type: 0, data: write_varint49(R + 726270) }];\n        cruids[4].push({ type: 2, data: write_shallow(uuid) });\n        cruids[5].push({ type: 0, data: write_varint49(R) });\n        cruids[6].push({ type: 0, data: write_varint49(R) });\n      }\n      _x[j].messages[0].data = write_shallow(cruids);\n    }\n    oldbucket.content = compress_iwa_file(write_iwa_file(_x));\n    oldbucket.size = oldbucket.content.length;\n    delete pb[46];\n    var store = parse_shallow(pb[4][0].data);\n    {\n      store[7][0].data = write_varint49(range.e.r + 1);\n      var row_headers = parse_shallow(store[1][0].data);\n      var row_header_ref = parse_TSP_Reference(row_headers[2][0].data);\n      oldbucket = CFB.find(cfb, dependents[row_header_ref].location);\n      _x = parse_iwa_file(decompress_iwa_file(oldbucket.content));\n      {\n        if (_x[0].id != row_header_ref)\n          throw \"Bad HeaderStorageBucket\";\n        var base_bucket = parse_shallow(_x[0].messages[0].data);\n        for (R = 0; R < data.length; ++R) {\n          var _bucket = parse_shallow(base_bucket[2][0].data);\n          _bucket[1][0].data = write_varint49(R);\n          _bucket[4][0].data = write_varint49(data[R].length);\n          base_bucket[2][R] = { type: base_bucket[2][0].type, data: write_shallow(_bucket) };\n        }\n        _x[0].messages[0].data = write_shallow(base_bucket);\n      }\n      oldbucket.content = compress_iwa_file(write_iwa_file(_x));\n      oldbucket.size = oldbucket.content.length;\n      var col_header_ref = parse_TSP_Reference(store[2][0].data);\n      oldbucket = CFB.find(cfb, dependents[col_header_ref].location);\n      _x = parse_iwa_file(decompress_iwa_file(oldbucket.content));\n      {\n        if (_x[0].id != col_header_ref)\n          throw \"Bad HeaderStorageBucket\";\n        base_bucket = parse_shallow(_x[0].messages[0].data);\n        for (C = 0; C <= range.e.c; ++C) {\n          _bucket = parse_shallow(base_bucket[2][0].data);\n          _bucket[1][0].data = write_varint49(C);\n          _bucket[4][0].data = write_varint49(range.e.r + 1);\n          base_bucket[2][C] = { type: base_bucket[2][0].type, data: write_shallow(_bucket) };\n        }\n        _x[0].messages[0].data = write_shallow(base_bucket);\n      }\n      oldbucket.content = compress_iwa_file(write_iwa_file(_x));\n      oldbucket.size = oldbucket.content.length;\n      var sstref = parse_TSP_Reference(store[4][0].data);\n      (function() {\n        var sentry = CFB.find(cfb, dependents[sstref].location);\n        var sx = parse_iwa_file(decompress_iwa_file(sentry.content));\n        var sstroot;\n        for (var sxi = 0; sxi < sx.length; ++sxi) {\n          var packet2 = sx[sxi];\n          if (packet2.id == sstref)\n            sstroot = packet2;\n        }\n        var sstdata = parse_shallow(sstroot.messages[0].data);\n        {\n          sstdata[3] = [];\n          var newsst = [];\n          SST.forEach(function(str, i) {\n            newsst[1] = [{ type: 0, data: write_varint49(i) }];\n            newsst[2] = [{ type: 0, data: write_varint49(1) }];\n            newsst[3] = [{ type: 2, data: stru8(str) }];\n            sstdata[3].push({ type: 2, data: write_shallow(newsst) });\n          });\n        }\n        sstroot.messages[0].data = write_shallow(sstdata);\n        var sy = write_iwa_file(sx);\n        var raw32 = compress_iwa_file(sy);\n        sentry.content = raw32;\n        sentry.size = sentry.content.length;\n      })();\n      var tile = parse_shallow(store[3][0].data);\n      {\n        var t = tile[1][0];\n        delete tile[2];\n        var tl = parse_shallow(t.data);\n        {\n          var tileref = parse_TSP_Reference(tl[2][0].data);\n          (function() {\n            var tentry = CFB.find(cfb, dependents[tileref].location);\n            var tx = parse_iwa_file(decompress_iwa_file(tentry.content));\n            var tileroot;\n            for (var sxi = 0; sxi < tx.length; ++sxi) {\n              var packet2 = tx[sxi];\n              if (packet2.id == tileref)\n                tileroot = packet2;\n            }\n            var tiledata = parse_shallow(tileroot.messages[0].data);\n            {\n              delete tiledata[6];\n              delete tile[7];\n              var rowload = new Uint8Array(tiledata[5][0].data);\n              tiledata[5] = [];\n              var cnt = 0;\n              for (var R2 = 0; R2 <= range.e.r; ++R2) {\n                var tilerow = parse_shallow(rowload);\n                cnt += write_tile_row(tilerow, data[R2], SST);\n                tilerow[1][0].data = write_varint49(R2);\n                tiledata[5].push({ data: write_shallow(tilerow), type: 2 });\n              }\n              tiledata[1] = [{ type: 0, data: write_varint49(range.e.c + 1) }];\n              tiledata[2] = [{ type: 0, data: write_varint49(range.e.r + 1) }];\n              tiledata[3] = [{ type: 0, data: write_varint49(cnt) }];\n              tiledata[4] = [{ type: 0, data: write_varint49(range.e.r + 1) }];\n            }\n            tileroot.messages[0].data = write_shallow(tiledata);\n            var ty = write_iwa_file(tx);\n            var raw32 = compress_iwa_file(ty);\n            tentry.content = raw32;\n            tentry.size = tentry.content.length;\n          })();\n        }\n        t.data = write_shallow(tl);\n      }\n      store[3][0].data = write_shallow(tile);\n    }\n    pb[4][0].data = write_shallow(store);\n  }\n  docroot.messages[0].data = write_shallow(pb);\n  var y = write_iwa_file(x);\n  var raw3 = compress_iwa_file(y);\n  entry.content = raw3;\n  entry.size = entry.content.length;\n  return cfb;\n}\nfunction fix_opts_func(defaults/*:Array<Array<any> >*/)/*:{(o:any):void}*/ {\n\treturn function fix_opts(opts) {\n\t\tfor(var i = 0; i != defaults.length; ++i) {\n\t\t\tvar d = defaults[i];\n\t\t\tif(opts[d[0]] === undefined) opts[d[0]] = d[1];\n\t\t\tif(d[2] === 'n') opts[d[0]] = Number(opts[d[0]]);\n\t\t}\n\t};\n}\n\nfunction fix_read_opts(opts) {\nfix_opts_func([\n\t['cellNF', false], /* emit cell number format string as .z */\n\t['cellHTML', true], /* emit html string as .h */\n\t['cellFormula', true], /* emit formulae as .f */\n\t['cellStyles', false], /* emits style/theme as .s */\n\t['cellText', true], /* emit formatted text as .w */\n\t['cellDates', false], /* emit date cells with type `d` */\n\n\t['sheetStubs', false], /* emit empty cells */\n\t['sheetRows', 0, 'n'], /* read n rows (0 = read all rows) */\n\n\t['bookDeps', false], /* parse calculation chains */\n\t['bookSheets', false], /* only try to get sheet names (no Sheets) */\n\t['bookProps', false], /* only try to get properties (no Sheets) */\n\t['bookFiles', false], /* include raw file structure (keys, files, cfb) */\n\t['bookVBA', false], /* include vba raw data (vbaraw) */\n\n\t['password',''], /* password */\n\t['WTF', false] /* WTF mode (throws errors) */\n])(opts);\n}\n\nfunction fix_write_opts(opts) {\nfix_opts_func([\n\t['cellDates', false], /* write date cells with type `d` */\n\n\t['bookSST', false], /* Generate Shared String Table */\n\n\t['bookType', 'xlsx'], /* Type of workbook (xlsx/m/b) */\n\n\t['compression', false], /* Use file compression */\n\n\t['WTF', false] /* WTF mode (throws errors) */\n])(opts);\n}\nfunction get_sheet_type(n/*:string*/)/*:string*/ {\n\tif(RELS.WS.indexOf(n) > -1) return \"sheet\";\n\tif(RELS.CS && n == RELS.CS) return \"chart\";\n\tif(RELS.DS && n == RELS.DS) return \"dialog\";\n\tif(RELS.MS && n == RELS.MS) return \"macro\";\n\treturn (n && n.length) ? n : \"sheet\";\n}\nfunction safe_parse_wbrels(wbrels, sheets) {\n\tif(!wbrels) return 0;\n\ttry {\n\t\twbrels = sheets.map(function pwbr(w) { if(!w.id) w.id = w.strRelID; return [w.name, wbrels['!id'][w.id].Target, get_sheet_type(wbrels['!id'][w.id].Type)]; });\n\t} catch(e) { return null; }\n\treturn !wbrels || wbrels.length === 0 ? null : wbrels;\n}\n\nfunction safe_parse_sheet(zip, path/*:string*/, relsPath/*:string*/, sheet, idx/*:number*/, sheetRels, sheets, stype/*:string*/, opts, wb, themes, styles) {\n\ttry {\n\t\tsheetRels[sheet]=parse_rels(getzipstr(zip, relsPath, true), path);\n\t\tvar data = getzipdata(zip, path);\n\t\tvar _ws;\n\t\tswitch(stype) {\n\t\t\tcase 'sheet':  _ws = parse_ws(data, path, idx, opts, sheetRels[sheet], wb, themes, styles); break;\n\t\t\tcase 'chart':  _ws = parse_cs(data, path, idx, opts, sheetRels[sheet], wb, themes, styles);\n\t\t\t\tif(!_ws || !_ws['!drawel']) break;\n\t\t\t\tvar dfile = resolve_path(_ws['!drawel'].Target, path);\n\t\t\t\tvar drelsp = get_rels_path(dfile);\n\t\t\t\tvar draw = parse_drawing(getzipstr(zip, dfile, true), parse_rels(getzipstr(zip, drelsp, true), dfile));\n\t\t\t\tvar chartp = resolve_path(draw, dfile);\n\t\t\t\tvar crelsp = get_rels_path(chartp);\n\t\t\t\t_ws = parse_chart(getzipstr(zip, chartp, true), chartp, opts, parse_rels(getzipstr(zip, crelsp, true), chartp), wb, _ws);\n\t\t\t\tbreak;\n\t\t\tcase 'macro':  _ws = parse_ms(data, path, idx, opts, sheetRels[sheet], wb, themes, styles); break;\n\t\t\tcase 'dialog': _ws = parse_ds(data, path, idx, opts, sheetRels[sheet], wb, themes, styles); break;\n\t\t\tdefault: throw new Error(\"Unrecognized sheet type \" + stype);\n\t\t}\n\t\tsheets[sheet] = _ws;\n\n\t\t/* scan rels for comments and threaded comments */\n\t\tvar tcomments = [];\n\t\tif(sheetRels && sheetRels[sheet]) keys(sheetRels[sheet]).forEach(function(n) {\n\t\t\tvar dfile = \"\";\n\t\t\tif(sheetRels[sheet][n].Type == RELS.CMNT) {\n\t\t\t\tdfile = resolve_path(sheetRels[sheet][n].Target, path);\n\t\t\t\tvar comments = parse_cmnt(getzipdata(zip, dfile, true), dfile, opts);\n\t\t\t\tif(!comments || !comments.length) return;\n\t\t\t\tsheet_insert_comments(_ws, comments, false);\n\t\t\t}\n\t\t\tif(sheetRels[sheet][n].Type == RELS.TCMNT) {\n\t\t\t\tdfile = resolve_path(sheetRels[sheet][n].Target, path);\n\t\t\t\ttcomments = tcomments.concat(parse_tcmnt_xml(getzipdata(zip, dfile, true), opts));\n\t\t\t}\n\t\t});\n\t\tif(tcomments && tcomments.length) sheet_insert_comments(_ws, tcomments, true, opts.people || []);\n\t} catch(e) { if(opts.WTF) throw e; }\n}\n\nfunction strip_front_slash(x/*:string*/)/*:string*/ { return x.charAt(0) == '/' ? x.slice(1) : x; }\n\nfunction parse_zip(zip/*:ZIP*/, opts/*:?ParseOpts*/)/*:Workbook*/ {\n\tmake_ssf();\n\topts = opts || {};\n\tfix_read_opts(opts);\n\n\t/* OpenDocument Part 3 Section 2.2.1 OpenDocument Package */\n\tif(safegetzipfile(zip, 'META-INF/manifest.xml')) return parse_ods(zip, opts);\n\t/* UOC */\n\tif(safegetzipfile(zip, 'objectdata.xml')) return parse_ods(zip, opts);\n\t/* Numbers */\n\tif(safegetzipfile(zip, 'Index/Document.iwa')) {\n\t\tif(typeof Uint8Array == \"undefined\") throw new Error('NUMBERS file parsing requires Uint8Array support');\n\t\tif(typeof parse_numbers_iwa != \"undefined\") {\n\t\t\tif(zip.FileIndex) return parse_numbers_iwa(zip);\n\t\t\tvar _zip = CFB.utils.cfb_new();\n\t\t\tzipentries(zip).forEach(function(e) { zip_add_file(_zip, e, getzipbin(zip, e)); });\n\t\t\treturn parse_numbers_iwa(_zip);\n\t\t}\n\t\tthrow new Error('Unsupported NUMBERS file');\n\t}\n\tif(!safegetzipfile(zip, '[Content_Types].xml')) {\n\t\tif(safegetzipfile(zip, 'index.xml.gz')) throw new Error('Unsupported NUMBERS 08 file');\n\t\tif(safegetzipfile(zip, 'index.xml')) throw new Error('Unsupported NUMBERS 09 file');\n\t\tthrow new Error('Unsupported ZIP file');\n\t}\n\n\tvar entries = zipentries(zip);\n\tvar dir = parse_ct((getzipstr(zip, '[Content_Types].xml')/*:?any*/));\n\tvar xlsb = false;\n\tvar sheets, binname;\n\tif(dir.workbooks.length === 0) {\n\t\tbinname = \"xl/workbook.xml\";\n\t\tif(getzipdata(zip,binname, true)) dir.workbooks.push(binname);\n\t}\n\tif(dir.workbooks.length === 0) {\n\t\tbinname = \"xl/workbook.bin\";\n\t\tif(!getzipdata(zip,binname,true)) throw new Error(\"Could not find workbook\");\n\t\tdir.workbooks.push(binname);\n\t\txlsb = true;\n\t}\n\tif(dir.workbooks[0].slice(-3) == \"bin\") xlsb = true;\n\n\tvar themes = ({}/*:any*/);\n\tvar styles = ({}/*:any*/);\n\tif(!opts.bookSheets && !opts.bookProps) {\n\t\tstrs = [];\n\t\tif(dir.sst) try { strs=parse_sst(getzipdata(zip, strip_front_slash(dir.sst)), dir.sst, opts); } catch(e) { if(opts.WTF) throw e; }\n\n\t\tif(opts.cellStyles && dir.themes.length) themes = parse_theme(getzipstr(zip, dir.themes[0].replace(/^\\//,''), true)||\"\",dir.themes[0], opts);\n\n\t\tif(dir.style) styles = parse_sty(getzipdata(zip, strip_front_slash(dir.style)), dir.style, themes, opts);\n\t}\n\n\t/*var externbooks = */dir.links.map(function(link) {\n\t\ttry {\n\t\t\tvar rels = parse_rels(getzipstr(zip, get_rels_path(strip_front_slash(link))), link);\n\t\t\treturn parse_xlink(getzipdata(zip, strip_front_slash(link)), rels, link, opts);\n\t\t} catch(e) {}\n\t});\n\n\tvar wb = parse_wb(getzipdata(zip, strip_front_slash(dir.workbooks[0])), dir.workbooks[0], opts);\n\n\tvar props = {}, propdata = \"\";\n\n\tif(dir.coreprops.length) {\n\t\tpropdata = getzipdata(zip, strip_front_slash(dir.coreprops[0]), true);\n\t\tif(propdata) props = parse_core_props(propdata);\n\t\tif(dir.extprops.length !== 0) {\n\t\t\tpropdata = getzipdata(zip, strip_front_slash(dir.extprops[0]), true);\n\t\t\tif(propdata) parse_ext_props(propdata, props, opts);\n\t\t}\n\t}\n\n\tvar custprops = {};\n\tif(!opts.bookSheets || opts.bookProps) {\n\t\tif (dir.custprops.length !== 0) {\n\t\t\tpropdata = getzipstr(zip, strip_front_slash(dir.custprops[0]), true);\n\t\t\tif(propdata) custprops = parse_cust_props(propdata, opts);\n\t\t}\n\t}\n\n\tvar out = ({}/*:any*/);\n\tif(opts.bookSheets || opts.bookProps) {\n\t\tif(wb.Sheets) sheets = wb.Sheets.map(function pluck(x){ return x.name; });\n\t\telse if(props.Worksheets && props.SheetNames.length > 0) sheets=props.SheetNames;\n\t\tif(opts.bookProps) { out.Props = props; out.Custprops = custprops; }\n\t\tif(opts.bookSheets && typeof sheets !== 'undefined') out.SheetNames = sheets;\n\t\tif(opts.bookSheets ? out.SheetNames : opts.bookProps) return out;\n\t}\n\tsheets = {};\n\n\tvar deps = {};\n\tif(opts.bookDeps && dir.calcchain) deps=parse_cc(getzipdata(zip, strip_front_slash(dir.calcchain)),dir.calcchain,opts);\n\n\tvar i=0;\n\tvar sheetRels = ({}/*:any*/);\n\tvar path, relsPath;\n\n\t{\n\t\tvar wbsheets = wb.Sheets;\n\t\tprops.Worksheets = wbsheets.length;\n\t\tprops.SheetNames = [];\n\t\tfor(var j = 0; j != wbsheets.length; ++j) {\n\t\t\tprops.SheetNames[j] = wbsheets[j].name;\n\t\t}\n\t}\n\n\tvar wbext = xlsb ? \"bin\" : \"xml\";\n\tvar wbrelsi = dir.workbooks[0].lastIndexOf(\"/\");\n\tvar wbrelsfile = (dir.workbooks[0].slice(0, wbrelsi+1) + \"_rels/\" + dir.workbooks[0].slice(wbrelsi+1) + \".rels\").replace(/^\\//,\"\");\n\tif(!safegetzipfile(zip, wbrelsfile)) wbrelsfile = 'xl/_rels/workbook.' + wbext + '.rels';\n\tvar wbrels = parse_rels(getzipstr(zip, wbrelsfile, true), wbrelsfile.replace(/_rels.*/, \"s5s\"));\n\n\tif((dir.metadata || []).length >= 1) {\n\t\t/* TODO: MDX and other types of metadata */\n\t\topts.xlmeta = parse_xlmeta(getzipdata(zip, strip_front_slash(dir.metadata[0])),dir.metadata[0],opts);\n\t}\n\n\tif((dir.people || []).length >= 1) {\n\t\topts.people = parse_people_xml(getzipdata(zip, strip_front_slash(dir.people[0])),opts);\n\t}\n\n\tif(wbrels) wbrels = safe_parse_wbrels(wbrels, wb.Sheets);\n\n\t/* Numbers iOS hack */\n\tvar nmode = (getzipdata(zip,\"xl/worksheets/sheet.xml\",true))?1:0;\n\twsloop: for(i = 0; i != props.Worksheets; ++i) {\n\t\tvar stype = \"sheet\";\n\t\tif(wbrels && wbrels[i]) {\n\t\t\tpath = 'xl/' + (wbrels[i][1]).replace(/[\\/]?xl\\//, \"\");\n\t\t\tif(!safegetzipfile(zip, path)) path = wbrels[i][1];\n\t\t\tif(!safegetzipfile(zip, path)) path = wbrelsfile.replace(/_rels\\/.*$/,\"\") + wbrels[i][1];\n\t\t\tstype = wbrels[i][2];\n\t\t} else {\n\t\t\tpath = 'xl/worksheets/sheet'+(i+1-nmode)+\".\" + wbext;\n\t\t\tpath = path.replace(/sheet0\\./,\"sheet.\");\n\t\t}\n\t\trelsPath = path.replace(/^(.*)(\\/)([^\\/]*)$/, \"$1/_rels/$3.rels\");\n\t\tif(opts && opts.sheets != null) switch(typeof opts.sheets) {\n\t\t\tcase \"number\": if(i != opts.sheets) continue wsloop; break;\n\t\t\tcase \"string\": if(props.SheetNames[i].toLowerCase() != opts.sheets.toLowerCase()) continue wsloop; break;\n\t\t\tdefault: if(Array.isArray && Array.isArray(opts.sheets)) {\n\t\t\t\tvar snjseen = false;\n\t\t\t\tfor(var snj = 0; snj != opts.sheets.length; ++snj) {\n\t\t\t\t\tif(typeof opts.sheets[snj] == \"number\" && opts.sheets[snj] == i) snjseen=1;\n\t\t\t\t\tif(typeof opts.sheets[snj] == \"string\" && opts.sheets[snj].toLowerCase() == props.SheetNames[i].toLowerCase()) snjseen = 1;\n\t\t\t\t}\n\t\t\t\tif(!snjseen) continue wsloop;\n\t\t\t}\n\t\t}\n\t\tsafe_parse_sheet(zip, path, relsPath, props.SheetNames[i], i, sheetRels, sheets, stype, opts, wb, themes, styles);\n\t}\n\n\tout = ({\n\t\tDirectory: dir,\n\t\tWorkbook: wb,\n\t\tProps: props,\n\t\tCustprops: custprops,\n\t\tDeps: deps,\n\t\tSheets: sheets,\n\t\tSheetNames: props.SheetNames,\n\t\tStrings: strs,\n\t\tStyles: styles,\n\t\tThemes: themes,\n\t\tSSF: dup(table_fmt)\n\t}/*:any*/);\n\tif(opts && opts.bookFiles) {\n\t\tif(zip.files) {\n\t\t\tout.keys = entries;\n\t\t\tout.files = zip.files;\n\t\t} else {\n\t\t\tout.keys = [];\n\t\t\tout.files = {};\n\t\t\tzip.FullPaths.forEach(function(p, idx) {\n\t\t\t\tp = p.replace(/^Root Entry[\\/]/, \"\");\n\t\t\t\tout.keys.push(p);\n\t\t\t\tout.files[p] = zip.FileIndex[idx];\n\t\t\t});\n\t\t}\n\t}\n\tif(opts && opts.bookVBA) {\n\t\tif(dir.vba.length > 0) out.vbaraw = getzipdata(zip,strip_front_slash(dir.vba[0]),true);\n\t\telse if(dir.defaults && dir.defaults.bin === CT_VBA) out.vbaraw = getzipdata(zip, 'xl/vbaProject.bin',true);\n\t}\n\treturn out;\n}\n\n/* [MS-OFFCRYPTO] 2.1.1 */\nfunction parse_xlsxcfb(cfb, _opts/*:?ParseOpts*/)/*:Workbook*/ {\n\tvar opts = _opts || {};\n\tvar f = 'Workbook', data = CFB.find(cfb, f);\n\ttry {\n\tf = '/!DataSpaces/Version';\n\tdata = CFB.find(cfb, f); if(!data || !data.content) throw new Error(\"ECMA-376 Encrypted file missing \" + f);\n\t/*var version = */parse_DataSpaceVersionInfo(data.content);\n\n\t/* 2.3.4.1 */\n\tf = '/!DataSpaces/DataSpaceMap';\n\tdata = CFB.find(cfb, f); if(!data || !data.content) throw new Error(\"ECMA-376 Encrypted file missing \" + f);\n\tvar dsm = parse_DataSpaceMap(data.content);\n\tif(dsm.length !== 1 || dsm[0].comps.length !== 1 || dsm[0].comps[0].t !== 0 || dsm[0].name !== \"StrongEncryptionDataSpace\" || dsm[0].comps[0].v !== \"EncryptedPackage\")\n\t\tthrow new Error(\"ECMA-376 Encrypted file bad \" + f);\n\n\t/* 2.3.4.2 */\n\tf = '/!DataSpaces/DataSpaceInfo/StrongEncryptionDataSpace';\n\tdata = CFB.find(cfb, f); if(!data || !data.content) throw new Error(\"ECMA-376 Encrypted file missing \" + f);\n\tvar seds = parse_DataSpaceDefinition(data.content);\n\tif(seds.length != 1 || seds[0] != \"StrongEncryptionTransform\")\n\t\tthrow new Error(\"ECMA-376 Encrypted file bad \" + f);\n\n\t/* 2.3.4.3 */\n\tf = '/!DataSpaces/TransformInfo/StrongEncryptionTransform/!Primary';\n\tdata = CFB.find(cfb, f); if(!data || !data.content) throw new Error(\"ECMA-376 Encrypted file missing \" + f);\n\t/*var hdr = */parse_Primary(data.content);\n\t} catch(e) {}\n\n\tf = '/EncryptionInfo';\n\tdata = CFB.find(cfb, f); if(!data || !data.content) throw new Error(\"ECMA-376 Encrypted file missing \" + f);\n\tvar einfo = parse_EncryptionInfo(data.content);\n\n\t/* 2.3.4.4 */\n\tf = '/EncryptedPackage';\n\tdata = CFB.find(cfb, f); if(!data || !data.content) throw new Error(\"ECMA-376 Encrypted file missing \" + f);\n\n/*global decrypt_agile */\n/*:: declare var decrypt_agile:any; */\n\tif(einfo[0] == 0x04 && typeof decrypt_agile !== 'undefined') return decrypt_agile(einfo[1], data.content, opts.password || \"\", opts);\n/*global decrypt_std76 */\n/*:: declare var decrypt_std76:any; */\n\tif(einfo[0] == 0x02 && typeof decrypt_std76 !== 'undefined') return decrypt_std76(einfo[1], data.content, opts.password || \"\", opts);\n\tthrow new Error(\"File is password-protected\");\n}\n\nfunction write_zip(wb/*:Workbook*/, opts/*:WriteOpts*/)/*:ZIP*/ {\n\tif(opts.bookType == \"ods\") return write_ods(wb, opts);\n\tif(opts.bookType == \"numbers\") return write_numbers_iwa(wb, opts);\n\tif(opts.bookType == \"xlsb\") return write_zip_xlsxb(wb, opts);\n\treturn write_zip_xlsx(wb, opts);\n}\n\n/* XLSX and XLSB writing are very similar.  Originally they were unified in one\n   export function.  This is horrible for tree shaking in the common case (most\n   applications need to export files in one format) so this function supports\n   both formats while write_zip_xlsx only handles XLSX */\nfunction write_zip_xlsxb(wb/*:Workbook*/, opts/*:WriteOpts*/)/*:ZIP*/ {\n\t_shapeid = 1024;\n\tif(wb && !wb.SSF) {\n\t\twb.SSF = dup(table_fmt);\n\t}\n\tif(wb && wb.SSF) {\n\t\tmake_ssf(); SSF_load_table(wb.SSF);\n\t\t// $FlowIgnore\n\t\topts.revssf = evert_num(wb.SSF); opts.revssf[wb.SSF[65535]] = 0;\n\t\topts.ssf = wb.SSF;\n\t}\n\topts.rels = {}; opts.wbrels = {};\n\topts.Strings = /*::((*/[]/*:: :any):SST)*/; opts.Strings.Count = 0; opts.Strings.Unique = 0;\n\tif(browser_has_Map) opts.revStrings = new Map();\n\telse { opts.revStrings = {}; opts.revStrings.foo = []; delete opts.revStrings.foo; }\n\tvar wbext = opts.bookType == \"xlsb\" ? \"bin\" : \"xml\";\n\tvar vbafmt = VBAFMTS.indexOf(opts.bookType) > -1;\n\tvar ct = new_ct();\n\tfix_write_opts(opts = opts || {});\n\tvar zip = zip_new();\n\tvar f = \"\", rId = 0;\n\n\topts.cellXfs = [];\n\tget_cell_style(opts.cellXfs, {}, {revssf:{\"General\":0}});\n\n\tif(!wb.Props) wb.Props = {};\n\n\tf = \"docProps/core.xml\";\n\tzip_add_file(zip, f, write_core_props(wb.Props, opts));\n\tct.coreprops.push(f);\n\tadd_rels(opts.rels, 2, f, RELS.CORE_PROPS);\n\n\t/*::if(!wb.Props) throw \"unreachable\"; */\n\tf = \"docProps/app.xml\";\n\tif(wb.Props && wb.Props.SheetNames){/* empty */}\n\telse if(!wb.Workbook || !wb.Workbook.Sheets) wb.Props.SheetNames = wb.SheetNames;\n\telse {\n\t\tvar _sn = [];\n\t\tfor(var _i = 0; _i < wb.SheetNames.length; ++_i)\n\t\t\tif((wb.Workbook.Sheets[_i]||{}).Hidden != 2) _sn.push(wb.SheetNames[_i]);\n\t\twb.Props.SheetNames = _sn;\n\t}\n\twb.Props.Worksheets = wb.Props.SheetNames.length;\n\tzip_add_file(zip, f, write_ext_props(wb.Props, opts));\n\tct.extprops.push(f);\n\tadd_rels(opts.rels, 3, f, RELS.EXT_PROPS);\n\n\tif(wb.Custprops !== wb.Props && keys(wb.Custprops||{}).length > 0) {\n\t\tf = \"docProps/custom.xml\";\n\t\tzip_add_file(zip, f, write_cust_props(wb.Custprops, opts));\n\t\tct.custprops.push(f);\n\t\tadd_rels(opts.rels, 4, f, RELS.CUST_PROPS);\n\t}\n\n\tfor(rId=1;rId <= wb.SheetNames.length; ++rId) {\n\t\tvar wsrels = {'!id':{}};\n\t\tvar ws = wb.Sheets[wb.SheetNames[rId-1]];\n\t\tvar _type = (ws || {})[\"!type\"] || \"sheet\";\n\t\tswitch(_type) {\n\t\tcase \"chart\":\n\t\t\t/* falls through */\n\t\tdefault:\n\t\t\tf = \"xl/worksheets/sheet\" + rId + \".\" + wbext;\n\t\t\tzip_add_file(zip, f, write_ws(rId-1, f, opts, wb, wsrels));\n\t\t\tct.sheets.push(f);\n\t\t\tadd_rels(opts.wbrels, -1, \"worksheets/sheet\" + rId + \".\" + wbext, RELS.WS[0]);\n\t\t}\n\n\t\tif(ws) {\n\t\t\tvar comments = ws['!comments'];\n\t\t\tvar need_vml = false;\n\t\t\tvar cf = \"\";\n\t\t\tif(comments && comments.length > 0) {\n\t\t\t\tcf = \"xl/comments\" + rId + \".\" + wbext;\n\t\t\t\tzip_add_file(zip, cf, write_cmnt(comments, cf, opts));\n\t\t\t\tct.comments.push(cf);\n\t\t\t\tadd_rels(wsrels, -1, \"../comments\" + rId + \".\" + wbext, RELS.CMNT);\n\t\t\t\tneed_vml = true;\n\t\t\t}\n\t\t\tif(ws['!legacy']) {\n\t\t\t\tif(need_vml) zip_add_file(zip, \"xl/drawings/vmlDrawing\" + (rId) + \".vml\", write_comments_vml(rId, ws['!comments']));\n\t\t\t}\n\t\t\tdelete ws['!comments'];\n\t\t\tdelete ws['!legacy'];\n\t\t}\n\n\t\tif(wsrels['!id'].rId1) zip_add_file(zip, get_rels_path(f), write_rels(wsrels));\n\t}\n\n\tif(opts.Strings != null && opts.Strings.length > 0) {\n\t\tf = \"xl/sharedStrings.\" + wbext;\n\t\tzip_add_file(zip, f, write_sst(opts.Strings, f, opts));\n\t\tct.strs.push(f);\n\t\tadd_rels(opts.wbrels, -1, \"sharedStrings.\" + wbext, RELS.SST);\n\t}\n\n\tf = \"xl/workbook.\" + wbext;\n\tzip_add_file(zip, f, write_wb(wb, f, opts));\n\tct.workbooks.push(f);\n\tadd_rels(opts.rels, 1, f, RELS.WB);\n\n\t/* TODO: something more intelligent with themes */\n\n\tf = \"xl/theme/theme1.xml\";\n\tzip_add_file(zip, f, write_theme(wb.Themes, opts));\n\tct.themes.push(f);\n\tadd_rels(opts.wbrels, -1, \"theme/theme1.xml\", RELS.THEME);\n\n\t/* TODO: something more intelligent with styles */\n\n\tf = \"xl/styles.\" + wbext;\n\tzip_add_file(zip, f, write_sty(wb, f, opts));\n\tct.styles.push(f);\n\tadd_rels(opts.wbrels, -1, \"styles.\" + wbext, RELS.STY);\n\n\tif(wb.vbaraw && vbafmt) {\n\t\tf = \"xl/vbaProject.bin\";\n\t\tzip_add_file(zip, f, wb.vbaraw);\n\t\tct.vba.push(f);\n\t\tadd_rels(opts.wbrels, -1, \"vbaProject.bin\", RELS.VBA);\n\t}\n\n\tf = \"xl/metadata.\" + wbext;\n\tzip_add_file(zip, f, write_xlmeta(f));\n\tct.metadata.push(f);\n\tadd_rels(opts.wbrels, -1, \"metadata.\" + wbext, RELS.XLMETA);\n\n\tzip_add_file(zip, \"[Content_Types].xml\", write_ct(ct, opts));\n\tzip_add_file(zip, '_rels/.rels', write_rels(opts.rels));\n\tzip_add_file(zip, 'xl/_rels/workbook.' + wbext + '.rels', write_rels(opts.wbrels));\n\n\tdelete opts.revssf; delete opts.ssf;\n\treturn zip;\n}\n\nfunction write_zip_xlsx(wb/*:Workbook*/, opts/*:WriteOpts*/)/*:ZIP*/ {\n\t_shapeid = 1024;\n\tif(wb && !wb.SSF) {\n\t\twb.SSF = dup(table_fmt);\n\t}\n\tif(wb && wb.SSF) {\n\t\tmake_ssf(); SSF_load_table(wb.SSF);\n\t\t// $FlowIgnore\n\t\topts.revssf = evert_num(wb.SSF); opts.revssf[wb.SSF[65535]] = 0;\n\t\topts.ssf = wb.SSF;\n\t}\n\topts.rels = {}; opts.wbrels = {};\n\topts.Strings = /*::((*/[]/*:: :any):SST)*/; opts.Strings.Count = 0; opts.Strings.Unique = 0;\n\tif(browser_has_Map) opts.revStrings = new Map();\n\telse { opts.revStrings = {}; opts.revStrings.foo = []; delete opts.revStrings.foo; }\n\tvar wbext = \"xml\";\n\tvar vbafmt = VBAFMTS.indexOf(opts.bookType) > -1;\n\tvar ct = new_ct();\n\tfix_write_opts(opts = opts || {});\n\tvar zip = zip_new();\n\tvar f = \"\", rId = 0;\n\n\topts.cellXfs = [];\n\tget_cell_style(opts.cellXfs, {}, {revssf:{\"General\":0}});\n\n\tif(!wb.Props) wb.Props = {};\n\n\tf = \"docProps/core.xml\";\n\tzip_add_file(zip, f, write_core_props(wb.Props, opts));\n\tct.coreprops.push(f);\n\tadd_rels(opts.rels, 2, f, RELS.CORE_PROPS);\n\n\t/*::if(!wb.Props) throw \"unreachable\"; */\n\tf = \"docProps/app.xml\";\n\tif(wb.Props && wb.Props.SheetNames){/* empty */}\n\telse if(!wb.Workbook || !wb.Workbook.Sheets) wb.Props.SheetNames = wb.SheetNames;\n\telse {\n\t\tvar _sn = [];\n\t\tfor(var _i = 0; _i < wb.SheetNames.length; ++_i)\n\t\t\tif((wb.Workbook.Sheets[_i]||{}).Hidden != 2) _sn.push(wb.SheetNames[_i]);\n\t\twb.Props.SheetNames = _sn;\n\t}\n\twb.Props.Worksheets = wb.Props.SheetNames.length;\n\tzip_add_file(zip, f, write_ext_props(wb.Props, opts));\n\tct.extprops.push(f);\n\tadd_rels(opts.rels, 3, f, RELS.EXT_PROPS);\n\n\tif(wb.Custprops !== wb.Props && keys(wb.Custprops||{}).length > 0) {\n\t\tf = \"docProps/custom.xml\";\n\t\tzip_add_file(zip, f, write_cust_props(wb.Custprops, opts));\n\t\tct.custprops.push(f);\n\t\tadd_rels(opts.rels, 4, f, RELS.CUST_PROPS);\n\t}\n\n\tvar people = [\"SheetJ5\"];\n\topts.tcid = 0;\n\n\tfor(rId=1;rId <= wb.SheetNames.length; ++rId) {\n\t\tvar wsrels = {'!id':{}};\n\t\tvar ws = wb.Sheets[wb.SheetNames[rId-1]];\n\t\tvar _type = (ws || {})[\"!type\"] || \"sheet\";\n\t\tswitch(_type) {\n\t\tcase \"chart\":\n\t\t\t/* falls through */\n\t\tdefault:\n\t\t\tf = \"xl/worksheets/sheet\" + rId + \".\" + wbext;\n\t\t\tzip_add_file(zip, f, write_ws_xml(rId-1, opts, wb, wsrels));\n\t\t\tct.sheets.push(f);\n\t\t\tadd_rels(opts.wbrels, -1, \"worksheets/sheet\" + rId + \".\" + wbext, RELS.WS[0]);\n\t\t}\n\n\t\tif(ws) {\n\t\t\tvar comments = ws['!comments'];\n\t\t\tvar need_vml = false;\n\t\t\tvar cf = \"\";\n\t\t\tif(comments && comments.length > 0) {\n\t\t\t\tvar needtc = false;\n\t\t\t\tcomments.forEach(function(carr) {\n\t\t\t\t\tcarr[1].forEach(function(c) { if(c.T == true) needtc = true; });\n\t\t\t\t});\n\t\t\t\tif(needtc) {\n\t\t\t\t\tcf = \"xl/threadedComments/threadedComment\" + rId + \".\" + wbext;\n\t\t\t\t\tzip_add_file(zip, cf, write_tcmnt_xml(comments, people, opts));\n\t\t\t\t\tct.threadedcomments.push(cf);\n\t\t\t\t\tadd_rels(wsrels, -1, \"../threadedComments/threadedComment\" + rId + \".\" + wbext, RELS.TCMNT);\n\t\t\t\t}\n\n\t\t\t\tcf = \"xl/comments\" + rId + \".\" + wbext;\n\t\t\t\tzip_add_file(zip, cf, write_comments_xml(comments, opts));\n\t\t\t\tct.comments.push(cf);\n\t\t\t\tadd_rels(wsrels, -1, \"../comments\" + rId + \".\" + wbext, RELS.CMNT);\n\t\t\t\tneed_vml = true;\n\t\t\t}\n\t\t\tif(ws['!legacy']) {\n\t\t\t\tif(need_vml) zip_add_file(zip, \"xl/drawings/vmlDrawing\" + (rId) + \".vml\", write_comments_vml(rId, ws['!comments']));\n\t\t\t}\n\t\t\tdelete ws['!comments'];\n\t\t\tdelete ws['!legacy'];\n\t\t}\n\n\t\tif(wsrels['!id'].rId1) zip_add_file(zip, get_rels_path(f), write_rels(wsrels));\n\t}\n\n\tif(opts.Strings != null && opts.Strings.length > 0) {\n\t\tf = \"xl/sharedStrings.\" + wbext;\n\t\tzip_add_file(zip, f, write_sst_xml(opts.Strings, opts));\n\t\tct.strs.push(f);\n\t\tadd_rels(opts.wbrels, -1, \"sharedStrings.\" + wbext, RELS.SST);\n\t}\n\n\tf = \"xl/workbook.\" + wbext;\n\tzip_add_file(zip, f, write_wb_xml(wb, opts));\n\tct.workbooks.push(f);\n\tadd_rels(opts.rels, 1, f, RELS.WB);\n\n\t/* TODO: something more intelligent with themes */\n\n\tf = \"xl/theme/theme1.xml\";\n\tzip_add_file(zip, f, write_theme(wb.Themes, opts));\n\tct.themes.push(f);\n\tadd_rels(opts.wbrels, -1, \"theme/theme1.xml\", RELS.THEME);\n\n\t/* TODO: something more intelligent with styles */\n\n\tf = \"xl/styles.\" + wbext;\n\tzip_add_file(zip, f, write_sty_xml(wb, opts));\n\tct.styles.push(f);\n\tadd_rels(opts.wbrels, -1, \"styles.\" + wbext, RELS.STY);\n\n\tif(wb.vbaraw && vbafmt) {\n\t\tf = \"xl/vbaProject.bin\";\n\t\tzip_add_file(zip, f, wb.vbaraw);\n\t\tct.vba.push(f);\n\t\tadd_rels(opts.wbrels, -1, \"vbaProject.bin\", RELS.VBA);\n\t}\n\n\tf = \"xl/metadata.\" + wbext;\n\tzip_add_file(zip, f, write_xlmeta_xml());\n\tct.metadata.push(f);\n\tadd_rels(opts.wbrels, -1, \"metadata.\" + wbext, RELS.XLMETA);\n\n\tif(people.length > 1) {\n\t\tf = \"xl/persons/person.xml\";\n\t\tzip_add_file(zip, f, write_people_xml(people, opts));\n\t\tct.people.push(f);\n\t\tadd_rels(opts.wbrels, -1, \"persons/person.xml\", RELS.PEOPLE);\n\t}\n\n\tzip_add_file(zip, \"[Content_Types].xml\", write_ct(ct, opts));\n\tzip_add_file(zip, '_rels/.rels', write_rels(opts.rels));\n\tzip_add_file(zip, 'xl/_rels/workbook.' + wbext + '.rels', write_rels(opts.wbrels));\n\n\tdelete opts.revssf; delete opts.ssf;\n\treturn zip;\n}\n\nfunction firstbyte(f/*:RawData*/,o/*:?TypeOpts*/)/*:Array<number>*/ {\n\tvar x = \"\";\n\tswitch((o||{}).type || \"base64\") {\n\t\tcase 'buffer': return [f[0], f[1], f[2], f[3], f[4], f[5], f[6], f[7]];\n\t\tcase 'base64': x = Base64_decode(f.slice(0,12)); break;\n\t\tcase 'binary': x = f; break;\n\t\tcase 'array':  return [f[0], f[1], f[2], f[3], f[4], f[5], f[6], f[7]];\n\t\tdefault: throw new Error(\"Unrecognized type \" + (o && o.type || \"undefined\"));\n\t}\n\treturn [x.charCodeAt(0), x.charCodeAt(1), x.charCodeAt(2), x.charCodeAt(3), x.charCodeAt(4), x.charCodeAt(5), x.charCodeAt(6), x.charCodeAt(7)];\n}\n\nfunction read_cfb(cfb/*:CFBContainer*/, opts/*:?ParseOpts*/)/*:Workbook*/ {\n\tif(CFB.find(cfb, \"EncryptedPackage\")) return parse_xlsxcfb(cfb, opts);\n\treturn parse_xlscfb(cfb, opts);\n}\n\nfunction read_zip(data/*:RawData*/, opts/*:?ParseOpts*/)/*:Workbook*/ {\n\tvar zip, d = data;\n\tvar o = opts||{};\n\tif(!o.type) o.type = (has_buf && Buffer.isBuffer(data)) ? \"buffer\" : \"base64\";\n\tzip = zip_read(d, o);\n\treturn parse_zip(zip, o);\n}\n\nfunction read_plaintext(data/*:string*/, o/*:ParseOpts*/)/*:Workbook*/ {\n\tvar i = 0;\n\tmain: while(i < data.length) switch(data.charCodeAt(i)) {\n\t\tcase 0x0A: case 0x0D: case 0x20: ++i; break;\n\t\tcase 0x3C: return parse_xlml(data.slice(i),o);\n\t\tdefault: break main;\n\t}\n\treturn PRN.to_workbook(data, o);\n}\n\nfunction read_plaintext_raw(data/*:RawData*/, o/*:ParseOpts*/)/*:Workbook*/ {\n\tvar str = \"\", bytes = firstbyte(data, o);\n\tswitch(o.type) {\n\t\tcase 'base64': str = Base64_decode(data); break;\n\t\tcase 'binary': str = data; break;\n\t\tcase 'buffer': str = data.toString('binary'); break;\n\t\tcase 'array': str = cc2str(data); break;\n\t\tdefault: throw new Error(\"Unrecognized type \" + o.type);\n\t}\n\tif(bytes[0] == 0xEF && bytes[1] == 0xBB && bytes[2] == 0xBF) str = utf8read(str);\n\to.type = \"binary\";\n\treturn read_plaintext(str, o);\n}\n\nfunction read_utf16(data/*:RawData*/, o/*:ParseOpts*/)/*:Workbook*/ {\n\tvar d = data;\n\tif(o.type == 'base64') d = Base64_decode(d);\n\td = $cptable.utils.decode(1200, d.slice(2), 'str');\n\to.type = \"binary\";\n\treturn read_plaintext(d, o);\n}\n\nfunction bstrify(data/*:string*/)/*:string*/ {\n\treturn !data.match(/[^\\x00-\\x7F]/) ? data : utf8write(data);\n}\n\nfunction read_prn(data, d, o, str) {\n\tif(str) { o.type = \"string\"; return PRN.to_workbook(data, o); }\n\treturn PRN.to_workbook(d, o);\n}\n\nfunction readSync(data/*:RawData*/, opts/*:?ParseOpts*/)/*:Workbook*/ {\n\treset_cp();\n\tvar o = opts||{};\n\tif(typeof ArrayBuffer !== 'undefined' && data instanceof ArrayBuffer) return readSync(new Uint8Array(data), (o = dup(o), o.type = \"array\", o));\n\tif(typeof Uint8Array !== 'undefined' && data instanceof Uint8Array && !o.type) o.type = typeof Deno !== \"undefined\" ? \"buffer\" : \"array\";\n\tvar d = data, n = [0,0,0,0], str = false;\n\tif(o.cellStyles) { o.cellNF = true; o.sheetStubs = true; }\n\t_ssfopts = {};\n\tif(o.dateNF) _ssfopts.dateNF = o.dateNF;\n\tif(!o.type) o.type = (has_buf && Buffer.isBuffer(data)) ? \"buffer\" : \"base64\";\n\tif(o.type == \"file\") { o.type = has_buf ? \"buffer\" : \"binary\"; d = read_binary(data); if(typeof Uint8Array !== 'undefined' && !has_buf) o.type = \"array\"; }\n\tif(o.type == \"string\") { str = true; o.type = \"binary\"; o.codepage = 65001; d = bstrify(data); }\n\tif(o.type == 'array' && typeof Uint8Array !== 'undefined' && data instanceof Uint8Array && typeof ArrayBuffer !== 'undefined') {\n\t\t// $FlowIgnore\n\t\tvar ab=new ArrayBuffer(3), vu=new Uint8Array(ab); vu.foo=\"bar\";\n\t\t// $FlowIgnore\n\t\tif(!vu.foo) {o=dup(o); o.type='array'; return readSync(ab2a(d), o);}\n\t}\n\tswitch((n = firstbyte(d, o))[0]) {\n\t\tcase 0xD0: if(n[1] === 0xCF && n[2] === 0x11 && n[3] === 0xE0 && n[4] === 0xA1 && n[5] === 0xB1 && n[6] === 0x1A && n[7] === 0xE1) return read_cfb(CFB.read(d, o), o); break;\n\t\tcase 0x09: if(n[1] <= 0x08) return parse_xlscfb(d, o); break;\n\t\tcase 0x3C: return parse_xlml(d, o);\n\t\tcase 0x49:\n\t\t\tif(n[1] === 0x49 && n[2] === 0x2a && n[3] === 0x00) throw new Error(\"TIFF Image File is not a spreadsheet\");\n\t\t\tif(n[1] === 0x44) return read_wb_ID(d, o);\n\t\t\tbreak;\n\t\tcase 0x54: if(n[1] === 0x41 && n[2] === 0x42 && n[3] === 0x4C) return DIF.to_workbook(d, o); break;\n\t\tcase 0x50: return (n[1] === 0x4B && n[2] < 0x09 && n[3] < 0x09) ? read_zip(d, o) : read_prn(data, d, o, str);\n\t\tcase 0xEF: return n[3] === 0x3C ? parse_xlml(d, o) : read_prn(data, d, o, str);\n\t\tcase 0xFF:\n\t\t\tif(n[1] === 0xFE) { return read_utf16(d, o); }\n\t\t\telse if(n[1] === 0x00 && n[2] === 0x02 && n[3] === 0x00) return WK_.to_workbook(d, o);\n\t\t\tbreak;\n\t\tcase 0x00:\n\t\t\tif(n[1] === 0x00) {\n\t\t\t\tif(n[2] >= 0x02 && n[3] === 0x00) return WK_.to_workbook(d, o);\n\t\t\t\tif(n[2] === 0x00 && (n[3] === 0x08 || n[3] === 0x09)) return WK_.to_workbook(d, o);\n\t\t\t}\n\t\t\tbreak;\n\t\tcase 0x03: case 0x83: case 0x8B: case 0x8C: return DBF.to_workbook(d, o);\n\t\tcase 0x7B: if(n[1] === 0x5C && n[2] === 0x72 && n[3] === 0x74) return RTF.to_workbook(d, o); break;\n\t\tcase 0x0A: case 0x0D: case 0x20: return read_plaintext_raw(d, o);\n\t\tcase 0x89: if(n[1] === 0x50 && n[2] === 0x4E && n[3] === 0x47) throw new Error(\"PNG Image File is not a spreadsheet\"); break;\n\t}\n\tif(DBF_SUPPORTED_VERSIONS.indexOf(n[0]) > -1 && n[2] <= 12 && n[3] <= 31) return DBF.to_workbook(d, o);\n\treturn read_prn(data, d, o, str);\n}\n\nfunction readFileSync(filename/*:string*/, opts/*:?ParseOpts*/)/*:Workbook*/ {\n\tvar o = opts||{}; o.type = 'file';\n\treturn readSync(filename, o);\n}\nfunction write_cfb_ctr(cfb/*:CFBContainer*/, o/*:WriteOpts*/)/*:any*/ {\n\tswitch(o.type) {\n\t\tcase \"base64\": case \"binary\": break;\n\t\tcase \"buffer\": case \"array\": o.type = \"\"; break;\n\t\tcase \"file\": return write_dl(o.file, CFB.write(cfb, {type:has_buf ? 'buffer' : \"\"}));\n\t\tcase \"string\": throw new Error(\"'string' output type invalid for '\" + o.bookType + \"' files\");\n\t\tdefault: throw new Error(\"Unrecognized type \" + o.type);\n\t}\n\treturn CFB.write(cfb, o);\n}\n\n/*:: declare var encrypt_agile:any; */\nfunction write_zip_type(wb/*:Workbook*/, opts/*:?WriteOpts*/)/*:any*/ {\n\tvar o = dup(opts||{});\n\tvar z = write_zip(wb, o);\n\treturn write_zip_denouement(z, o);\n}\nfunction write_zip_typeXLSX(wb/*:Workbook*/, opts/*:?WriteOpts*/)/*:any*/ {\n\tvar o = dup(opts||{});\n\tvar z = write_zip_xlsx(wb, o);\n\treturn write_zip_denouement(z, o);\n}\nfunction write_zip_denouement(z/*:any*/, o/*:?WriteOpts*/)/*:any*/ {\n\tvar oopts = {};\n\tvar ftype = has_buf ? \"nodebuffer\" : (typeof Uint8Array !== \"undefined\" ? \"array\" : \"string\");\n\tif(o.compression) oopts.compression = 'DEFLATE';\n\tif(o.password) oopts.type = ftype;\n\telse switch(o.type) {\n\t\tcase \"base64\": oopts.type = \"base64\"; break;\n\t\tcase \"binary\": oopts.type = \"string\"; break;\n\t\tcase \"string\": throw new Error(\"'string' output type invalid for '\" + o.bookType + \"' files\");\n\t\tcase \"buffer\":\n\t\tcase \"file\": oopts.type = ftype; break;\n\t\tdefault: throw new Error(\"Unrecognized type \" + o.type);\n\t}\n\tvar out = z.FullPaths ? CFB.write(z, {fileType:\"zip\", type: /*::(*/{\"nodebuffer\": \"buffer\", \"string\": \"binary\"}/*:: :any)*/[oopts.type] || oopts.type, compression: !!o.compression}) : z.generate(oopts);\n\tif(typeof Deno !== \"undefined\") {\n\t\tif(typeof out == \"string\") {\n\t\t\tif(o.type == \"binary\" || o.type == \"base64\") return out;\n\t\t\tout = new Uint8Array(s2ab(out));\n\t\t}\n\t}\n/*jshint -W083 */\n\tif(o.password && typeof encrypt_agile !== 'undefined') return write_cfb_ctr(encrypt_agile(out, o.password), o); // eslint-disable-line no-undef\n/*jshint +W083 */\n\tif(o.type === \"file\") return write_dl(o.file, out);\n\treturn o.type == \"string\" ? utf8read(/*::(*/out/*:: :any)*/) : out;\n}\n\nfunction write_cfb_type(wb/*:Workbook*/, opts/*:?WriteOpts*/)/*:any*/ {\n\tvar o = opts||{};\n\tvar cfb/*:CFBContainer*/ = write_xlscfb(wb, o);\n\treturn write_cfb_ctr(cfb, o);\n}\n\nfunction write_string_type(out/*:string*/, opts/*:WriteOpts*/, bom/*:?string*/)/*:any*/ {\n\tif(!bom) bom = \"\";\n\tvar o = bom + out;\n\tswitch(opts.type) {\n\t\tcase \"base64\": return Base64_encode(utf8write(o));\n\t\tcase \"binary\": return utf8write(o);\n\t\tcase \"string\": return out;\n\t\tcase \"file\": return write_dl(opts.file, o, 'utf8');\n\t\tcase \"buffer\": {\n\t\t\tif(has_buf) return Buffer_from(o, 'utf8');\n\t\t\telse if(typeof TextEncoder !== \"undefined\") return new TextEncoder().encode(o);\n\t\t\telse return write_string_type(o, {type:'binary'}).split(\"\").map(function(c) { return c.charCodeAt(0); });\n\t\t}\n\t}\n\tthrow new Error(\"Unrecognized type \" + opts.type);\n}\n\nfunction write_stxt_type(out/*:string*/, opts/*:WriteOpts*/)/*:any*/ {\n\tswitch(opts.type) {\n\t\tcase \"base64\": return Base64_encode(out);\n\t\tcase \"binary\": return out;\n\t\tcase \"string\": return out; /* override in sheet_to_txt */\n\t\tcase \"file\": return write_dl(opts.file, out, 'binary');\n\t\tcase \"buffer\": {\n\t\t\tif(has_buf) return Buffer_from(out, 'binary');\n\t\t\telse return out.split(\"\").map(function(c) { return c.charCodeAt(0); });\n\t\t}\n\t}\n\tthrow new Error(\"Unrecognized type \" + opts.type);\n}\n\n/* TODO: test consistency */\nfunction write_binary_type(out, opts/*:WriteOpts*/)/*:any*/ {\n\tswitch(opts.type) {\n\t\tcase \"string\":\n\t\tcase \"base64\":\n\t\tcase \"binary\":\n\t\t\tvar bstr = \"\";\n\t\t\t// $FlowIgnore\n\t\t\tfor(var i = 0; i < out.length; ++i) bstr += String.fromCharCode(out[i]);\n\t\t\treturn opts.type == 'base64' ? Base64_encode(bstr) : opts.type == 'string' ? utf8read(bstr) : bstr;\n\t\tcase \"file\": return write_dl(opts.file, out);\n\t\tcase \"buffer\": return out;\n\t\tdefault: throw new Error(\"Unrecognized type \" + opts.type);\n\t}\n}\n\nfunction writeSyncXLSX(wb/*:Workbook*/, opts/*:?WriteOpts*/) {\n\treset_cp();\n\tcheck_wb(wb);\n\tvar o = dup(opts||{});\n\tif(o.cellStyles) { o.cellNF = true; o.sheetStubs = true; }\n\tif(o.type == \"array\") { o.type = \"binary\"; var out/*:string*/ = (writeSyncXLSX(wb, o)/*:any*/); o.type = \"array\"; return s2ab(out); }\n\treturn write_zip_typeXLSX(wb, o);\n}\n\nfunction writeSync(wb/*:Workbook*/, opts/*:?WriteOpts*/) {\n\treset_cp();\n\tcheck_wb(wb);\n\tvar o = dup(opts||{});\n\tif(o.cellStyles) { o.cellNF = true; o.sheetStubs = true; }\n\tif(o.type == \"array\") { o.type = \"binary\"; var out/*:string*/ = (writeSync(wb, o)/*:any*/); o.type = \"array\"; return s2ab(out); }\n\tvar idx = 0;\n\tif(o.sheet) {\n\t\tif(typeof o.sheet == \"number\") idx = o.sheet;\n\t\telse idx = wb.SheetNames.indexOf(o.sheet);\n\t\tif(!wb.SheetNames[idx]) throw new Error(\"Sheet not found: \" + o.sheet + \" : \" + (typeof o.sheet));\n\t}\n\tswitch(o.bookType || 'xlsb') {\n\t\tcase 'xml':\n\t\tcase 'xlml': return write_string_type(write_xlml(wb, o), o);\n\t\tcase 'slk':\n\t\tcase 'sylk': return write_string_type(SYLK.from_sheet(wb.Sheets[wb.SheetNames[idx]], o), o);\n\t\tcase 'htm':\n\t\tcase 'html': return write_string_type(sheet_to_html(wb.Sheets[wb.SheetNames[idx]], o), o);\n\t\tcase 'txt': return write_stxt_type(sheet_to_txt(wb.Sheets[wb.SheetNames[idx]], o), o);\n\t\tcase 'csv': return write_string_type(sheet_to_csv(wb.Sheets[wb.SheetNames[idx]], o), o, \"\\ufeff\");\n\t\tcase 'dif': return write_string_type(DIF.from_sheet(wb.Sheets[wb.SheetNames[idx]], o), o);\n\t\tcase 'dbf': return write_binary_type(DBF.from_sheet(wb.Sheets[wb.SheetNames[idx]], o), o);\n\t\tcase 'prn': return write_string_type(PRN.from_sheet(wb.Sheets[wb.SheetNames[idx]], o), o);\n\t\tcase 'rtf': return write_string_type(RTF.from_sheet(wb.Sheets[wb.SheetNames[idx]], o), o);\n\t\tcase 'eth': return write_string_type(ETH.from_sheet(wb.Sheets[wb.SheetNames[idx]], o), o);\n\t\tcase 'fods': return write_string_type(write_ods(wb, o), o);\n\t\tcase 'wk1': return write_binary_type(WK_.sheet_to_wk1(wb.Sheets[wb.SheetNames[idx]], o), o);\n\t\tcase 'wk3': return write_binary_type(WK_.book_to_wk3(wb, o), o);\n\t\tcase 'biff2': if(!o.biff) o.biff = 2; /* falls through */\n\t\tcase 'biff3': if(!o.biff) o.biff = 3; /* falls through */\n\t\tcase 'biff4': if(!o.biff) o.biff = 4; return write_binary_type(write_biff_buf(wb, o), o);\n\t\tcase 'biff5': if(!o.biff) o.biff = 5; /* falls through */\n\t\tcase 'biff8':\n\t\tcase 'xla':\n\t\tcase 'xls': if(!o.biff) o.biff = 8; return write_cfb_type(wb, o);\n\t\tcase 'xlsx':\n\t\tcase 'xlsm':\n\t\tcase 'xlam':\n\t\tcase 'xlsb':\n\t\tcase 'numbers':\n\t\tcase 'ods': return write_zip_type(wb, o);\n\t\tdefault: throw new Error (\"Unrecognized bookType |\" + o.bookType + \"|\");\n\t}\n}\n\nfunction resolve_book_type(o/*:WriteFileOpts*/) {\n\tif(o.bookType) return;\n\tvar _BT = {\n\t\t\"xls\": \"biff8\",\n\t\t\"htm\": \"html\",\n\t\t\"slk\": \"sylk\",\n\t\t\"socialcalc\": \"eth\",\n\t\t\"Sh33tJS\": \"WTF\"\n\t};\n\tvar ext = o.file.slice(o.file.lastIndexOf(\".\")).toLowerCase();\n\tif(ext.match(/^\\.[a-z]+$/)) o.bookType = ext.slice(1);\n\to.bookType = _BT[o.bookType] || o.bookType;\n}\n\nfunction writeFileSync(wb/*:Workbook*/, filename/*:string*/, opts/*:?WriteFileOpts*/) {\n\tvar o = opts||{}; o.type = 'file';\n\to.file = filename;\n\tresolve_book_type(o);\n\treturn writeSync(wb, o);\n}\n\nfunction writeFileSyncXLSX(wb/*:Workbook*/, filename/*:string*/, opts/*:?WriteFileOpts*/) {\n\tvar o = opts||{}; o.type = 'file';\n\to.file = filename;\n\tresolve_book_type(o);\n\treturn writeSyncXLSX(wb, o);\n}\n\n\nfunction writeFileAsync(filename/*:string*/, wb/*:Workbook*/, opts/*:?WriteFileOpts*/, cb/*:?(e?:ErrnoError)=>void*/) {\n\tvar o = opts||{}; o.type = 'file';\n\to.file = filename;\n\tresolve_book_type(o);\n\to.type = 'buffer';\n\tvar _cb = cb; if(!(_cb instanceof Function)) _cb = (opts/*:any*/);\n\treturn _fs.writeFile(filename, writeSync(wb, o), _cb);\n}\n/*::\ntype MJRObject = {\n\trow: any;\n\tisempty: boolean;\n};\n*/\nfunction make_json_row(sheet/*:Worksheet*/, r/*:Range*/, R/*:number*/, cols/*:Array<string>*/, header/*:number*/, hdr/*:Array<any>*/, dense/*:boolean*/, o/*:Sheet2JSONOpts*/)/*:MJRObject*/ {\n\tvar rr = encode_row(R);\n\tvar defval = o.defval, raw = o.raw || !Object.prototype.hasOwnProperty.call(o, \"raw\");\n\tvar isempty = true;\n\tvar row/*:any*/ = (header === 1) ? [] : {};\n\tif(header !== 1) {\n\t\tif(Object.defineProperty) try { Object.defineProperty(row, '__rowNum__', {value:R, enumerable:false}); } catch(e) { row.__rowNum__ = R; }\n\t\telse row.__rowNum__ = R;\n\t}\n\tif(!dense || sheet[R]) for (var C = r.s.c; C <= r.e.c; ++C) {\n\t\tvar val = dense ? sheet[R][C] : sheet[cols[C] + rr];\n\t\tif(val === undefined || val.t === undefined) {\n\t\t\tif(defval === undefined) continue;\n\t\t\tif(hdr[C] != null) { row[hdr[C]] = defval; }\n\t\t\tcontinue;\n\t\t}\n\t\tvar v = val.v;\n\t\tswitch(val.t){\n\t\t\tcase 'z': if(v == null) break; continue;\n\t\t\tcase 'e': v = (v == 0 ? null : void 0); break;\n\t\t\tcase 's': case 'd': case 'b': case 'n': break;\n\t\t\tdefault: throw new Error('unrecognized type ' + val.t);\n\t\t}\n\t\tif(hdr[C] != null) {\n\t\t\tif(v == null) {\n\t\t\t\tif(val.t == \"e\" && v === null) row[hdr[C]] = null;\n\t\t\t\telse if(defval !== undefined) row[hdr[C]] = defval;\n\t\t\t\telse if(raw && v === null) row[hdr[C]] = null;\n\t\t\t\telse continue;\n\t\t\t} else {\n\t\t\t\trow[hdr[C]] = raw && (val.t !== \"n\" || (val.t === \"n\" && o.rawNumbers !== false)) ? v : format_cell(val,v,o);\n\t\t\t}\n\t\t\tif(v != null) isempty = false;\n\t\t}\n\t}\n\treturn { row: row, isempty: isempty };\n}\n\n\nfunction sheet_to_json(sheet/*:Worksheet*/, opts/*:?Sheet2JSONOpts*/) {\n\tif(sheet == null || sheet[\"!ref\"] == null) return [];\n\tvar val = {t:'n',v:0}, header = 0, offset = 1, hdr/*:Array<any>*/ = [], v=0, vv=\"\";\n\tvar r = {s:{r:0,c:0},e:{r:0,c:0}};\n\tvar o = opts || {};\n\tvar range = o.range != null ? o.range : sheet[\"!ref\"];\n\tif(o.header === 1) header = 1;\n\telse if(o.header === \"A\") header = 2;\n\telse if(Array.isArray(o.header)) header = 3;\n\telse if(o.header == null) header = 0;\n\tswitch(typeof range) {\n\t\tcase 'string': r = safe_decode_range(range); break;\n\t\tcase 'number': r = safe_decode_range(sheet[\"!ref\"]); r.s.r = range; break;\n\t\tdefault: r = range;\n\t}\n\tif(header > 0) offset = 0;\n\tvar rr = encode_row(r.s.r);\n\tvar cols/*:Array<string>*/ = [];\n\tvar out/*:Array<any>*/ = [];\n\tvar outi = 0, counter = 0;\n\tvar dense = Array.isArray(sheet);\n\tvar R = r.s.r, C = 0;\n\tvar header_cnt = {};\n\tif(dense && !sheet[R]) sheet[R] = [];\n\tvar colinfo/*:Array<ColInfo>*/ = o.skipHidden && sheet[\"!cols\"] || [];\n\tvar rowinfo/*:Array<ColInfo>*/ = o.skipHidden && sheet[\"!rows\"] || [];\n\tfor(C = r.s.c; C <= r.e.c; ++C) {\n\t\tif(((colinfo[C]||{}).hidden)) continue;\n\t\tcols[C] = encode_col(C);\n\t\tval = dense ? sheet[R][C] : sheet[cols[C] + rr];\n\t\tswitch(header) {\n\t\t\tcase 1: hdr[C] = C - r.s.c; break;\n\t\t\tcase 2: hdr[C] = cols[C]; break;\n\t\t\tcase 3: hdr[C] = o.header[C - r.s.c]; break;\n\t\t\tdefault:\n\t\t\t\tif(val == null) val = {w: \"__EMPTY\", t: \"s\"};\n\t\t\t\tvv = v = format_cell(val, null, o);\n\t\t\t\tcounter = header_cnt[v] || 0;\n\t\t\t\tif(!counter) header_cnt[v] = 1;\n\t\t\t\telse {\n\t\t\t\t\tdo { vv = v + \"_\" + (counter++); } while(header_cnt[vv]); header_cnt[v] = counter;\n\t\t\t\t\theader_cnt[vv] = 1;\n\t\t\t\t}\n\t\t\t\thdr[C] = vv;\n\t\t}\n\t}\n\tfor (R = r.s.r + offset; R <= r.e.r; ++R) {\n\t\tif ((rowinfo[R]||{}).hidden) continue;\n\t\tvar row = make_json_row(sheet, r, R, cols, header, hdr, dense, o);\n\t\tif((row.isempty === false) || (header === 1 ? o.blankrows !== false : !!o.blankrows)) out[outi++] = row.row;\n\t}\n\tout.length = outi;\n\treturn out;\n}\n\nvar qreg = /\"/g;\nfunction make_csv_row(sheet/*:Worksheet*/, r/*:Range*/, R/*:number*/, cols/*:Array<string>*/, fs/*:number*/, rs/*:number*/, FS/*:string*/, o/*:Sheet2CSVOpts*/)/*:?string*/ {\n\tvar isempty = true;\n\tvar row/*:Array<string>*/ = [], txt = \"\", rr = encode_row(R);\n\tfor(var C = r.s.c; C <= r.e.c; ++C) {\n\t\tif (!cols[C]) continue;\n\t\tvar val = o.dense ? (sheet[R]||[])[C]: sheet[cols[C] + rr];\n\t\tif(val == null) txt = \"\";\n\t\telse if(val.v != null) {\n\t\t\tisempty = false;\n\t\t\ttxt = ''+(o.rawNumbers && val.t == \"n\" ? val.v : format_cell(val, null, o));\n\t\t\tfor(var i = 0, cc = 0; i !== txt.length; ++i) if((cc = txt.charCodeAt(i)) === fs || cc === rs || cc === 34 || o.forceQuotes) {txt = \"\\\"\" + txt.replace(qreg, '\"\"') + \"\\\"\"; break; }\n\t\t\tif(txt == \"ID\") txt = '\"ID\"';\n\t\t} else if(val.f != null && !val.F) {\n\t\t\tisempty = false;\n\t\t\ttxt = '=' + val.f; if(txt.indexOf(\",\") >= 0) txt = '\"' + txt.replace(qreg, '\"\"') + '\"';\n\t\t} else txt = \"\";\n\t\t/* NOTE: Excel CSV does not support array formulae */\n\t\trow.push(txt);\n\t}\n\tif(o.blankrows === false && isempty) return null;\n\treturn row.join(FS);\n}\n\nfunction sheet_to_csv(sheet/*:Worksheet*/, opts/*:?Sheet2CSVOpts*/)/*:string*/ {\n\tvar out/*:Array<string>*/ = [];\n\tvar o = opts == null ? {} : opts;\n\tif(sheet == null || sheet[\"!ref\"] == null) return \"\";\n\tvar r = safe_decode_range(sheet[\"!ref\"]);\n\tvar FS = o.FS !== undefined ? o.FS : \",\", fs = FS.charCodeAt(0);\n\tvar RS = o.RS !== undefined ? o.RS : \"\\n\", rs = RS.charCodeAt(0);\n\tvar endregex = new RegExp((FS==\"|\" ? \"\\\\|\" : FS)+\"+$\");\n\tvar row = \"\", cols/*:Array<string>*/ = [];\n\to.dense = Array.isArray(sheet);\n\tvar colinfo/*:Array<ColInfo>*/ = o.skipHidden && sheet[\"!cols\"] || [];\n\tvar rowinfo/*:Array<ColInfo>*/ = o.skipHidden && sheet[\"!rows\"] || [];\n\tfor(var C = r.s.c; C <= r.e.c; ++C) if (!((colinfo[C]||{}).hidden)) cols[C] = encode_col(C);\n\tvar w = 0;\n\tfor(var R = r.s.r; R <= r.e.r; ++R) {\n\t\tif ((rowinfo[R]||{}).hidden) continue;\n\t\trow = make_csv_row(sheet, r, R, cols, fs, rs, FS, o);\n\t\tif(row == null) { continue; }\n\t\tif(o.strip) row = row.replace(endregex,\"\");\n\t\tif(row || (o.blankrows !== false)) out.push((w++ ? RS : \"\") + row);\n\t}\n\tdelete o.dense;\n\treturn out.join(\"\");\n}\n\nfunction sheet_to_txt(sheet/*:Worksheet*/, opts/*:?Sheet2CSVOpts*/) {\n\tif(!opts) opts = {}; opts.FS = \"\\t\"; opts.RS = \"\\n\";\n\tvar s = sheet_to_csv(sheet, opts);\n\tif(typeof $cptable == 'undefined' || opts.type == 'string') return s;\n\tvar o = $cptable.utils.encode(1200, s, 'str');\n\treturn String.fromCharCode(255) + String.fromCharCode(254) + o;\n}\n\nfunction sheet_to_formulae(sheet/*:Worksheet*/)/*:Array<string>*/ {\n\tvar y = \"\", x, val=\"\";\n\tif(sheet == null || sheet[\"!ref\"] == null) return [];\n\tvar r = safe_decode_range(sheet['!ref']), rr = \"\", cols/*:Array<string>*/ = [], C;\n\tvar cmds/*:Array<string>*/ = [];\n\tvar dense = Array.isArray(sheet);\n\tfor(C = r.s.c; C <= r.e.c; ++C) cols[C] = encode_col(C);\n\tfor(var R = r.s.r; R <= r.e.r; ++R) {\n\t\trr = encode_row(R);\n\t\tfor(C = r.s.c; C <= r.e.c; ++C) {\n\t\t\ty = cols[C] + rr;\n\t\t\tx = dense ? (sheet[R]||[])[C] : sheet[y];\n\t\t\tval = \"\";\n\t\t\tif(x === undefined) continue;\n\t\t\telse if(x.F != null) {\n\t\t\t\ty = x.F;\n\t\t\t\tif(!x.f) continue;\n\t\t\t\tval = x.f;\n\t\t\t\tif(y.indexOf(\":\") == -1) y = y + \":\" + y;\n\t\t\t}\n\t\t\tif(x.f != null) val = x.f;\n\t\t\telse if(x.t == 'z') continue;\n\t\t\telse if(x.t == 'n' && x.v != null) val = \"\" + x.v;\n\t\t\telse if(x.t == 'b') val = x.v ? \"TRUE\" : \"FALSE\";\n\t\t\telse if(x.w !== undefined) val = \"'\" + x.w;\n\t\t\telse if(x.v === undefined) continue;\n\t\t\telse if(x.t == 's') val = \"'\" + x.v;\n\t\t\telse val = \"\"+x.v;\n\t\t\tcmds[cmds.length] = y + \"=\" + val;\n\t\t}\n\t}\n\treturn cmds;\n}\n\nfunction sheet_add_json(_ws/*:?Worksheet*/, js/*:Array<any>*/, opts)/*:Worksheet*/ {\n\tvar o = opts || {};\n\tvar offset = +!o.skipHeader;\n\tvar ws/*:Worksheet*/ = _ws || ({}/*:any*/);\n\tvar _R = 0, _C = 0;\n\tif(ws && o.origin != null) {\n\t\tif(typeof o.origin == 'number') _R = o.origin;\n\t\telse {\n\t\t\tvar _origin/*:CellAddress*/ = typeof o.origin == \"string\" ? decode_cell(o.origin) : o.origin;\n\t\t\t_R = _origin.r; _C = _origin.c;\n\t\t}\n\t}\n\tvar cell/*:Cell*/;\n\tvar range/*:Range*/ = ({s: {c:0, r:0}, e: {c:_C, r:_R + js.length - 1 + offset}}/*:any*/);\n\tif(ws['!ref']) {\n\t\tvar _range = safe_decode_range(ws['!ref']);\n\t\trange.e.c = Math.max(range.e.c, _range.e.c);\n\t\trange.e.r = Math.max(range.e.r, _range.e.r);\n\t\tif(_R == -1) { _R = _range.e.r + 1; range.e.r = _R + js.length - 1 + offset; }\n\t} else {\n\t\tif(_R == -1) { _R = 0; range.e.r = js.length - 1 + offset; }\n\t}\n\tvar hdr/*:Array<string>*/ = o.header || [], C = 0;\n\n\tjs.forEach(function (JS, R/*:number*/) {\n\t\tkeys(JS).forEach(function(k) {\n\t\t\tif((C=hdr.indexOf(k)) == -1) hdr[C=hdr.length] = k;\n\t\t\tvar v = JS[k];\n\t\t\tvar t = 'z';\n\t\t\tvar z = \"\";\n\t\t\tvar ref = encode_cell({c:_C + C,r:_R + R + offset});\n\t\t\tcell = ws_get_cell_stub(ws, ref);\n\t\t\tif(v && typeof v === 'object' && !(v instanceof Date)){\n\t\t\t\tws[ref] = v;\n\t\t\t} else {\n\t\t\t\tif(typeof v == 'number') t = 'n';\n\t\t\t\telse if(typeof v == 'boolean') t = 'b';\n\t\t\t\telse if(typeof v == 'string') t = 's';\n\t\t\t\telse if(v instanceof Date) {\n\t\t\t\t\tt = 'd';\n\t\t\t\t\tif(!o.cellDates) { t = 'n'; v = datenum(v); }\n\t\t\t\t\tz = (o.dateNF || table_fmt[14]);\n\t\t\t\t}\n\t\t\t\telse if(v === null && o.nullError) { t = 'e'; v = 0; }\n\t\t\t\tif(!cell) ws[ref] = cell = ({t:t, v:v}/*:any*/);\n\t\t\t\telse {\n\t\t\t\t\tcell.t = t; cell.v = v;\n\t\t\t\t\tdelete cell.w; delete cell.R;\n\t\t\t\t\tif(z) cell.z = z;\n\t\t\t\t}\n\t\t\t\tif(z) cell.z = z;\n\t\t\t}\n\t\t});\n\t});\n\trange.e.c = Math.max(range.e.c, _C + hdr.length - 1);\n\tvar __R = encode_row(_R);\n\tif(offset) for(C = 0; C < hdr.length; ++C) ws[encode_col(C + _C) + __R] = {t:'s', v:hdr[C]};\n\tws['!ref'] = encode_range(range);\n\treturn ws;\n}\nfunction json_to_sheet(js/*:Array<any>*/, opts)/*:Worksheet*/ { return sheet_add_json(null, js, opts); }\n\n/* get cell, creating a stub if necessary */\nfunction ws_get_cell_stub(ws/*:Worksheet*/, R, C/*:?number*/)/*:Cell*/ {\n\t/* A1 cell address */\n\tif(typeof R == \"string\") {\n\t\t/* dense */\n\t\tif(Array.isArray(ws)) {\n\t\t\tvar RC = decode_cell(R);\n\t\t\tif(!ws[RC.r]) ws[RC.r] = [];\n\t\t\treturn ws[RC.r][RC.c] || (ws[RC.r][RC.c] = {t:'z'});\n\t\t}\n\t\treturn ws[R] || (ws[R] = {t:'z'});\n\t}\n\t/* cell address object */\n\tif(typeof R != \"number\") return ws_get_cell_stub(ws, encode_cell(R));\n\t/* R and C are 0-based indices */\n\treturn ws_get_cell_stub(ws, encode_cell({r:R,c:C||0}));\n}\n\n/* find sheet index for given name / validate index */\nfunction wb_sheet_idx(wb/*:Workbook*/, sh/*:number|string*/) {\n\tif(typeof sh == \"number\") {\n\t\tif(sh >= 0 && wb.SheetNames.length > sh) return sh;\n\t\tthrow new Error(\"Cannot find sheet # \" + sh);\n\t} else if(typeof sh == \"string\") {\n\t\tvar idx = wb.SheetNames.indexOf(sh);\n\t\tif(idx > -1) return idx;\n\t\tthrow new Error(\"Cannot find sheet name |\" + sh + \"|\");\n\t} else throw new Error(\"Cannot find sheet |\" + sh + \"|\");\n}\n\n/* simple blank workbook object */\nfunction book_new()/*:Workbook*/ {\n\treturn { SheetNames: [], Sheets: {} };\n}\n\n/* add a worksheet to the end of a given workbook */\nfunction book_append_sheet(wb/*:Workbook*/, ws/*:Worksheet*/, name/*:?string*/, roll/*:?boolean*/)/*:string*/ {\n\tvar i = 1;\n\tif(!name) for(; i <= 0xFFFF; ++i, name = undefined) if(wb.SheetNames.indexOf(name = \"Sheet\" + i) == -1) break;\n\tif(!name || wb.SheetNames.length >= 0xFFFF) throw new Error(\"Too many worksheets\");\n\tif(roll && wb.SheetNames.indexOf(name) >= 0) {\n\t\tvar m = name.match(/(^.*?)(\\d+)$/);\n\t\ti = m && +m[2] || 0;\n\t\tvar root = m && m[1] || name;\n\t\tfor(++i; i <= 0xFFFF; ++i) if(wb.SheetNames.indexOf(name = root + i) == -1) break;\n\t}\n\tcheck_ws_name(name);\n\tif(wb.SheetNames.indexOf(name) >= 0) throw new Error(\"Worksheet with name |\" + name + \"| already exists!\");\n\n\twb.SheetNames.push(name);\n\twb.Sheets[name] = ws;\n\treturn name;\n}\n\n/* set sheet visibility (visible/hidden/very hidden) */\nfunction book_set_sheet_visibility(wb/*:Workbook*/, sh/*:number|string*/, vis/*:number*/) {\n\tif(!wb.Workbook) wb.Workbook = {};\n\tif(!wb.Workbook.Sheets) wb.Workbook.Sheets = [];\n\n\tvar idx = wb_sheet_idx(wb, sh);\n\t// $FlowIgnore\n\tif(!wb.Workbook.Sheets[idx]) wb.Workbook.Sheets[idx] = {};\n\n\tswitch(vis) {\n\t\tcase 0: case 1: case 2: break;\n\t\tdefault: throw new Error(\"Bad sheet visibility setting \" + vis);\n\t}\n\t// $FlowIgnore\n\twb.Workbook.Sheets[idx].Hidden = vis;\n}\n\n/* set number format */\nfunction cell_set_number_format(cell/*:Cell*/, fmt/*:string|number*/) {\n\tcell.z = fmt;\n\treturn cell;\n}\n\n/* set cell hyperlink */\nfunction cell_set_hyperlink(cell/*:Cell*/, target/*:string*/, tooltip/*:?string*/) {\n\tif(!target) {\n\t\tdelete cell.l;\n\t} else {\n\t\tcell.l = ({ Target: target }/*:Hyperlink*/);\n\t\tif(tooltip) cell.l.Tooltip = tooltip;\n\t}\n\treturn cell;\n}\nfunction cell_set_internal_link(cell/*:Cell*/, range/*:string*/, tooltip/*:?string*/) { return cell_set_hyperlink(cell, \"#\" + range, tooltip); }\n\n/* add to cell comments */\nfunction cell_add_comment(cell/*:Cell*/, text/*:string*/, author/*:?string*/) {\n\tif(!cell.c) cell.c = [];\n\tcell.c.push({t:text, a:author||\"SheetJS\"});\n}\n\n/* set array formula and flush related cells */\nfunction sheet_set_array_formula(ws/*:Worksheet*/, range, formula/*:string*/, dynamic/*:boolean*/) {\n\tvar rng = typeof range != \"string\" ? range : safe_decode_range(range);\n\tvar rngstr = typeof range == \"string\" ? range : encode_range(range);\n\tfor(var R = rng.s.r; R <= rng.e.r; ++R) for(var C = rng.s.c; C <= rng.e.c; ++C) {\n\t\tvar cell = ws_get_cell_stub(ws, R, C);\n\t\tcell.t = 'n';\n\t\tcell.F = rngstr;\n\t\tdelete cell.v;\n\t\tif(R == rng.s.r && C == rng.s.c) {\n\t\t\tcell.f = formula;\n\t\t\tif(dynamic) cell.D = true;\n\t\t}\n\t}\n\treturn ws;\n}\n\nvar utils/*:any*/ = {\n\tencode_col: encode_col,\n\tencode_row: encode_row,\n\tencode_cell: encode_cell,\n\tencode_range: encode_range,\n\tdecode_col: decode_col,\n\tdecode_row: decode_row,\n\tsplit_cell: split_cell,\n\tdecode_cell: decode_cell,\n\tdecode_range: decode_range,\n\tformat_cell: format_cell,\n\tsheet_add_aoa: sheet_add_aoa,\n\tsheet_add_json: sheet_add_json,\n\tsheet_add_dom: sheet_add_dom,\n\taoa_to_sheet: aoa_to_sheet,\n\tjson_to_sheet: json_to_sheet,\n\ttable_to_sheet: parse_dom_table,\n\ttable_to_book: table_to_book,\n\tsheet_to_csv: sheet_to_csv,\n\tsheet_to_txt: sheet_to_txt,\n\tsheet_to_json: sheet_to_json,\n\tsheet_to_html: sheet_to_html,\n\tsheet_to_formulae: sheet_to_formulae,\n\tsheet_to_row_object_array: sheet_to_json,\n\tsheet_get_cell: ws_get_cell_stub,\n\tbook_new: book_new,\n\tbook_append_sheet: book_append_sheet,\n\tbook_set_sheet_visibility: book_set_sheet_visibility,\n\tcell_set_number_format: cell_set_number_format,\n\tcell_set_hyperlink: cell_set_hyperlink,\n\tcell_set_internal_link: cell_set_internal_link,\n\tcell_add_comment: cell_add_comment,\n\tsheet_set_array_formula: sheet_set_array_formula,\n\tconsts: {\n\t\tSHEET_VISIBLE: 0,\n\t\tSHEET_HIDDEN: 1,\n\t\tSHEET_VERY_HIDDEN: 2\n\t}\n};\n\nvar _Readable;\nfunction set_readable(R) { _Readable = R; }\n\nfunction write_csv_stream(sheet/*:Worksheet*/, opts/*:?Sheet2CSVOpts*/) {\n\tvar stream = _Readable();\n\tvar o = opts == null ? {} : opts;\n\tif(sheet == null || sheet[\"!ref\"] == null) { stream.push(null); return stream; }\n\tvar r = safe_decode_range(sheet[\"!ref\"]);\n\tvar FS = o.FS !== undefined ? o.FS : \",\", fs = FS.charCodeAt(0);\n\tvar RS = o.RS !== undefined ? o.RS : \"\\n\", rs = RS.charCodeAt(0);\n\tvar endregex = new RegExp((FS==\"|\" ? \"\\\\|\" : FS)+\"+$\");\n\tvar row/*:?string*/ = \"\", cols/*:Array<string>*/ = [];\n\to.dense = Array.isArray(sheet);\n\tvar colinfo/*:Array<ColInfo>*/ = o.skipHidden && sheet[\"!cols\"] || [];\n\tvar rowinfo/*:Array<RowInfo>*/ = o.skipHidden && sheet[\"!rows\"] || [];\n\tfor(var C = r.s.c; C <= r.e.c; ++C) if (!((colinfo[C]||{}).hidden)) cols[C] = encode_col(C);\n\tvar R = r.s.r;\n\tvar BOM = false, w = 0;\n\tstream._read = function() {\n\t\tif(!BOM) { BOM = true; return stream.push(\"\\uFEFF\"); }\n\t\twhile(R <= r.e.r) {\n\t\t\t++R;\n\t\t\tif ((rowinfo[R-1]||{}).hidden) continue;\n\t\t\trow = make_csv_row(sheet, r, R-1, cols, fs, rs, FS, o);\n\t\t\tif(row != null) {\n\t\t\t\tif(o.strip) row = row.replace(endregex,\"\");\n\t\t\t\tif(row || (o.blankrows !== false)) return stream.push((w++ ? RS : \"\") + row);\n\t\t\t}\n\t\t}\n\t\treturn stream.push(null);\n\t};\n\treturn stream;\n}\n\nfunction write_html_stream(ws/*:Worksheet*/, opts/*:?Sheet2HTMLOpts*/) {\n\tvar stream = _Readable();\n\n\tvar o = opts || {};\n\tvar header = o.header != null ? o.header : HTML_BEGIN;\n\tvar footer = o.footer != null ? o.footer : HTML_END;\n\tstream.push(header);\n\tvar r = decode_range(ws['!ref']);\n\to.dense = Array.isArray(ws);\n\tstream.push(make_html_preamble(ws, r, o));\n\tvar R = r.s.r;\n\tvar end = false;\n\tstream._read = function() {\n\t\tif(R > r.e.r) {\n\t\t\tif(!end) { end = true; stream.push(\"</table>\" + footer); }\n\t\t\treturn stream.push(null);\n\t\t}\n\t\twhile(R <= r.e.r) {\n\t\t\tstream.push(make_html_row(ws, r, R, o));\n\t\t\t++R;\n\t\t\tbreak;\n\t\t}\n\t};\n\treturn stream;\n}\n\nfunction write_json_stream(sheet/*:Worksheet*/, opts/*:?Sheet2CSVOpts*/) {\n\tvar stream = _Readable({objectMode:true});\n\n\tif(sheet == null || sheet[\"!ref\"] == null) { stream.push(null); return stream; }\n\tvar val = {t:'n',v:0}, header = 0, offset = 1, hdr/*:Array<any>*/ = [], v=0, vv=\"\";\n\tvar r = {s:{r:0,c:0},e:{r:0,c:0}};\n\tvar o = opts || {};\n\tvar range = o.range != null ? o.range : sheet[\"!ref\"];\n\tif(o.header === 1) header = 1;\n\telse if(o.header === \"A\") header = 2;\n\telse if(Array.isArray(o.header)) header = 3;\n\tswitch(typeof range) {\n\t\tcase 'string': r = safe_decode_range(range); break;\n\t\tcase 'number': r = safe_decode_range(sheet[\"!ref\"]); r.s.r = range; break;\n\t\tdefault: r = range;\n\t}\n\tif(header > 0) offset = 0;\n\tvar rr = encode_row(r.s.r);\n\tvar cols/*:Array<string>*/ = [];\n\tvar counter = 0;\n\tvar dense = Array.isArray(sheet);\n\tvar R = r.s.r, C = 0;\n\tvar header_cnt = {};\n\tif(dense && !sheet[R]) sheet[R] = [];\n\tvar colinfo/*:Array<ColInfo>*/ = o.skipHidden && sheet[\"!cols\"] || [];\n\tvar rowinfo/*:Array<RowInfo>*/ = o.skipHidden && sheet[\"!rows\"] || [];\n\tfor(C = r.s.c; C <= r.e.c; ++C) {\n\t\tif(((colinfo[C]||{}).hidden)) continue;\n\t\tcols[C] = encode_col(C);\n\t\tval = dense ? sheet[R][C] : sheet[cols[C] + rr];\n\t\tswitch(header) {\n\t\t\tcase 1: hdr[C] = C - r.s.c; break;\n\t\t\tcase 2: hdr[C] = cols[C]; break;\n\t\t\tcase 3: hdr[C] = o.header[C - r.s.c]; break;\n\t\t\tdefault:\n\t\t\t\tif(val == null) val = {w: \"__EMPTY\", t: \"s\"};\n\t\t\t\tvv = v = format_cell(val, null, o);\n\t\t\t\tcounter = header_cnt[v] || 0;\n\t\t\t\tif(!counter) header_cnt[v] = 1;\n\t\t\t\telse {\n\t\t\t\t\tdo { vv = v + \"_\" + (counter++); } while(header_cnt[vv]); header_cnt[v] = counter;\n\t\t\t\t\theader_cnt[vv] = 1;\n\t\t\t\t}\n\t\t\t\thdr[C] = vv;\n\t\t}\n\t}\n\tR = r.s.r + offset;\n\tstream._read = function() {\n\t\twhile(R <= r.e.r) {\n\t\t\tif ((rowinfo[R-1]||{}).hidden) continue;\n\t\t\tvar row = make_json_row(sheet, r, R, cols, header, hdr, dense, o);\n\t\t\t++R;\n\t\t\tif((row.isempty === false) || (header === 1 ? o.blankrows !== false : !!o.blankrows)) {\n\t\t\t\tstream.push(row.row);\n\t\t\t\treturn;\n\t\t\t}\n\t\t}\n\t\treturn stream.push(null);\n\t};\n\treturn stream;\n}\n\nvar __stream = {\n\tto_json: write_json_stream,\n\tto_html: write_html_stream,\n\tto_csv: write_csv_stream,\n  set_readable: set_readable\n};\nexport const version = XLSX.version;\nexport {\n\tparse_xlscfb,\n\tparse_zip,\n\treadSync as read,\n\treadFileSync as readFile,\n\treadFileSync,\n\twriteSync as write,\n\twriteFileSync as writeFile,\n\twriteFileSync,\n\twriteFileAsync,\n\twriteSyncXLSX as writeXLSX,\n\twriteFileSyncXLSX as writeFileXLSX,\n\tutils,\n\t__stream as stream,\n\tSSF,\n\tCFB\n};\n","export const default_format = 'RFC3986';\nexport const formatters = {\n    RFC1738: (v) => String(v).replace(/%20/g, '+'),\n    RFC3986: (v) => String(v),\n};\nexport const RFC1738 = 'RFC1738';\nexport const RFC3986 = 'RFC3986';\n//# sourceMappingURL=formats.mjs.map","import { RFC1738 } from \"./formats.mjs\";\nconst has = Object.prototype.hasOwnProperty;\nconst is_array = Array.isArray;\nconst hex_table = (() => {\n    const array = [];\n    for (let i = 0; i < 256; ++i) {\n        array.push('%' + ((i < 16 ? '0' : '') + i.toString(16)).toUpperCase());\n    }\n    return array;\n})();\nfunction compact_queue(queue) {\n    while (queue.length > 1) {\n        const item = queue.pop();\n        if (!item)\n            continue;\n        const obj = item.obj[item.prop];\n        if (is_array(obj)) {\n            const compacted = [];\n            for (let j = 0; j < obj.length; ++j) {\n                if (typeof obj[j] !== 'undefined') {\n                    compacted.push(obj[j]);\n                }\n            }\n            // @ts-ignore\n            item.obj[item.prop] = compacted;\n        }\n    }\n}\nfunction array_to_object(source, options) {\n    const obj = options && options.plainObjects ? Object.create(null) : {};\n    for (let i = 0; i < source.length; ++i) {\n        if (typeof source[i] !== 'undefined') {\n            obj[i] = source[i];\n        }\n    }\n    return obj;\n}\nexport function merge(target, source, options = {}) {\n    if (!source) {\n        return target;\n    }\n    if (typeof source !== 'object') {\n        if (is_array(target)) {\n            target.push(source);\n        }\n        else if (target && typeof target === 'object') {\n            if ((options && (options.plainObjects || options.allowPrototypes)) ||\n                !has.call(Object.prototype, source)) {\n                target[source] = true;\n            }\n        }\n        else {\n            return [target, source];\n        }\n        return target;\n    }\n    if (!target || typeof target !== 'object') {\n        return [target].concat(source);\n    }\n    let mergeTarget = target;\n    if (is_array(target) && !is_array(source)) {\n        // @ts-ignore\n        mergeTarget = array_to_object(target, options);\n    }\n    if (is_array(target) && is_array(source)) {\n        source.forEach(function (item, i) {\n            if (has.call(target, i)) {\n                const targetItem = target[i];\n                if (targetItem && typeof targetItem === 'object' && item && typeof item === 'object') {\n                    target[i] = merge(targetItem, item, options);\n                }\n                else {\n                    target.push(item);\n                }\n            }\n            else {\n                target[i] = item;\n            }\n        });\n        return target;\n    }\n    return Object.keys(source).reduce(function (acc, key) {\n        const value = source[key];\n        if (has.call(acc, key)) {\n            acc[key] = merge(acc[key], value, options);\n        }\n        else {\n            acc[key] = value;\n        }\n        return acc;\n    }, mergeTarget);\n}\nexport function assign_single_source(target, source) {\n    return Object.keys(source).reduce(function (acc, key) {\n        acc[key] = source[key];\n        return acc;\n    }, target);\n}\nexport function decode(str, _, charset) {\n    const strWithoutPlus = str.replace(/\\+/g, ' ');\n    if (charset === 'iso-8859-1') {\n        // unescape never throws, no try...catch needed:\n        return strWithoutPlus.replace(/%[0-9a-f]{2}/gi, unescape);\n    }\n    // utf-8\n    try {\n        return decodeURIComponent(strWithoutPlus);\n    }\n    catch (e) {\n        return strWithoutPlus;\n    }\n}\nconst limit = 1024;\nexport const encode = (str, _defaultEncoder, charset, _kind, format) => {\n    // This code was originally written by Brian White for the io.js core querystring library.\n    // It has been adapted here for stricter adherence to RFC 3986\n    if (str.length === 0) {\n        return str;\n    }\n    let string = str;\n    if (typeof str === 'symbol') {\n        string = Symbol.prototype.toString.call(str);\n    }\n    else if (typeof str !== 'string') {\n        string = String(str);\n    }\n    if (charset === 'iso-8859-1') {\n        return escape(string).replace(/%u[0-9a-f]{4}/gi, function ($0) {\n            return '%26%23' + parseInt($0.slice(2), 16) + '%3B';\n        });\n    }\n    let out = '';\n    for (let j = 0; j < string.length; j += limit) {\n        const segment = string.length >= limit ? string.slice(j, j + limit) : string;\n        const arr = [];\n        for (let i = 0; i < segment.length; ++i) {\n            let c = segment.charCodeAt(i);\n            if (c === 0x2d || // -\n                c === 0x2e || // .\n                c === 0x5f || // _\n                c === 0x7e || // ~\n                (c >= 0x30 && c <= 0x39) || // 0-9\n                (c >= 0x41 && c <= 0x5a) || // a-z\n                (c >= 0x61 && c <= 0x7a) || // A-Z\n                (format === RFC1738 && (c === 0x28 || c === 0x29)) // ( )\n            ) {\n                arr[arr.length] = segment.charAt(i);\n                continue;\n            }\n            if (c < 0x80) {\n                arr[arr.length] = hex_table[c];\n                continue;\n            }\n            if (c < 0x800) {\n                arr[arr.length] = hex_table[0xc0 | (c >> 6)] + hex_table[0x80 | (c & 0x3f)];\n                continue;\n            }\n            if (c < 0xd800 || c >= 0xe000) {\n                arr[arr.length] =\n                    hex_table[0xe0 | (c >> 12)] + hex_table[0x80 | ((c >> 6) & 0x3f)] + hex_table[0x80 | (c & 0x3f)];\n                continue;\n            }\n            i += 1;\n            c = 0x10000 + (((c & 0x3ff) << 10) | (segment.charCodeAt(i) & 0x3ff));\n            arr[arr.length] =\n                hex_table[0xf0 | (c >> 18)] +\n                    hex_table[0x80 | ((c >> 12) & 0x3f)] +\n                    hex_table[0x80 | ((c >> 6) & 0x3f)] +\n                    hex_table[0x80 | (c & 0x3f)];\n        }\n        out += arr.join('');\n    }\n    return out;\n};\nexport function compact(value) {\n    const queue = [{ obj: { o: value }, prop: 'o' }];\n    const refs = [];\n    for (let i = 0; i < queue.length; ++i) {\n        const item = queue[i];\n        // @ts-ignore\n        const obj = item.obj[item.prop];\n        const keys = Object.keys(obj);\n        for (let j = 0; j < keys.length; ++j) {\n            const key = keys[j];\n            const val = obj[key];\n            if (typeof val === 'object' && val !== null && refs.indexOf(val) === -1) {\n                queue.push({ obj: obj, prop: key });\n                refs.push(val);\n            }\n        }\n    }\n    compact_queue(queue);\n    return value;\n}\nexport function is_regexp(obj) {\n    return Object.prototype.toString.call(obj) === '[object RegExp]';\n}\nexport function is_buffer(obj) {\n    if (!obj || typeof obj !== 'object') {\n        return false;\n    }\n    return !!(obj.constructor && obj.constructor.isBuffer && obj.constructor.isBuffer(obj));\n}\nexport function combine(a, b) {\n    return [].concat(a, b);\n}\nexport function maybe_map(val, fn) {\n    if (is_array(val)) {\n        const mapped = [];\n        for (let i = 0; i < val.length; i += 1) {\n            mapped.push(fn(val[i]));\n        }\n        return mapped;\n    }\n    return fn(val);\n}\n//# sourceMappingURL=utils.mjs.map","import { encode, is_buffer, maybe_map } from \"./utils.mjs\";\nimport { default_format, formatters } from \"./formats.mjs\";\nconst has = Object.prototype.hasOwnProperty;\nconst array_prefix_generators = {\n    brackets(prefix) {\n        return String(prefix) + '[]';\n    },\n    comma: 'comma',\n    indices(prefix, key) {\n        return String(prefix) + '[' + key + ']';\n    },\n    repeat(prefix) {\n        return String(prefix);\n    },\n};\nconst is_array = Array.isArray;\nconst push = Array.prototype.push;\nconst push_to_array = function (arr, value_or_array) {\n    push.apply(arr, is_array(value_or_array) ? value_or_array : [value_or_array]);\n};\nconst to_ISO = Date.prototype.toISOString;\nconst defaults = {\n    addQueryPrefix: false,\n    allowDots: false,\n    allowEmptyArrays: false,\n    arrayFormat: 'indices',\n    charset: 'utf-8',\n    charsetSentinel: false,\n    delimiter: '&',\n    encode: true,\n    encodeDotInKeys: false,\n    encoder: encode,\n    encodeValuesOnly: false,\n    format: default_format,\n    formatter: formatters[default_format],\n    /** @deprecated */\n    indices: false,\n    serializeDate(date) {\n        return to_ISO.call(date);\n    },\n    skipNulls: false,\n    strictNullHandling: false,\n};\nfunction is_non_nullish_primitive(v) {\n    return (typeof v === 'string' ||\n        typeof v === 'number' ||\n        typeof v === 'boolean' ||\n        typeof v === 'symbol' ||\n        typeof v === 'bigint');\n}\nconst sentinel = {};\nfunction inner_stringify(object, prefix, generateArrayPrefix, commaRoundTrip, allowEmptyArrays, strictNullHandling, skipNulls, encodeDotInKeys, encoder, filter, sort, allowDots, serializeDate, format, formatter, encodeValuesOnly, charset, sideChannel) {\n    let obj = object;\n    let tmp_sc = sideChannel;\n    let step = 0;\n    let find_flag = false;\n    while ((tmp_sc = tmp_sc.get(sentinel)) !== void undefined && !find_flag) {\n        // Where object last appeared in the ref tree\n        const pos = tmp_sc.get(object);\n        step += 1;\n        if (typeof pos !== 'undefined') {\n            if (pos === step) {\n                throw new RangeError('Cyclic object value');\n            }\n            else {\n                find_flag = true; // Break while\n            }\n        }\n        if (typeof tmp_sc.get(sentinel) === 'undefined') {\n            step = 0;\n        }\n    }\n    if (typeof filter === 'function') {\n        obj = filter(prefix, obj);\n    }\n    else if (obj instanceof Date) {\n        obj = serializeDate?.(obj);\n    }\n    else if (generateArrayPrefix === 'comma' && is_array(obj)) {\n        obj = maybe_map(obj, function (value) {\n            if (value instanceof Date) {\n                return serializeDate?.(value);\n            }\n            return value;\n        });\n    }\n    if (obj === null) {\n        if (strictNullHandling) {\n            return encoder && !encodeValuesOnly ?\n                // @ts-expect-error\n                encoder(prefix, defaults.encoder, charset, 'key', format)\n                : prefix;\n        }\n        obj = '';\n    }\n    if (is_non_nullish_primitive(obj) || is_buffer(obj)) {\n        if (encoder) {\n            const key_value = encodeValuesOnly ? prefix\n                // @ts-expect-error\n                : encoder(prefix, defaults.encoder, charset, 'key', format);\n            return [\n                formatter?.(key_value) +\n                    '=' +\n                    // @ts-expect-error\n                    formatter?.(encoder(obj, defaults.encoder, charset, 'value', format)),\n            ];\n        }\n        return [formatter?.(prefix) + '=' + formatter?.(String(obj))];\n    }\n    const values = [];\n    if (typeof obj === 'undefined') {\n        return values;\n    }\n    let obj_keys;\n    if (generateArrayPrefix === 'comma' && is_array(obj)) {\n        // we need to join elements in\n        if (encodeValuesOnly && encoder) {\n            // @ts-expect-error values only\n            obj = maybe_map(obj, encoder);\n        }\n        obj_keys = [{ value: obj.length > 0 ? obj.join(',') || null : void undefined }];\n    }\n    else if (is_array(filter)) {\n        obj_keys = filter;\n    }\n    else {\n        const keys = Object.keys(obj);\n        obj_keys = sort ? keys.sort(sort) : keys;\n    }\n    const encoded_prefix = encodeDotInKeys ? String(prefix).replace(/\\./g, '%2E') : String(prefix);\n    const adjusted_prefix = commaRoundTrip && is_array(obj) && obj.length === 1 ? encoded_prefix + '[]' : encoded_prefix;\n    if (allowEmptyArrays && is_array(obj) && obj.length === 0) {\n        return adjusted_prefix + '[]';\n    }\n    for (let j = 0; j < obj_keys.length; ++j) {\n        const key = obj_keys[j];\n        const value = \n        // @ts-ignore\n        typeof key === 'object' && typeof key.value !== 'undefined' ? key.value : obj[key];\n        if (skipNulls && value === null) {\n            continue;\n        }\n        // @ts-ignore\n        const encoded_key = allowDots && encodeDotInKeys ? key.replace(/\\./g, '%2E') : key;\n        const key_prefix = is_array(obj) ?\n            typeof generateArrayPrefix === 'function' ?\n                generateArrayPrefix(adjusted_prefix, encoded_key)\n                : adjusted_prefix\n            : adjusted_prefix + (allowDots ? '.' + encoded_key : '[' + encoded_key + ']');\n        sideChannel.set(object, step);\n        const valueSideChannel = new WeakMap();\n        valueSideChannel.set(sentinel, sideChannel);\n        push_to_array(values, inner_stringify(value, key_prefix, generateArrayPrefix, commaRoundTrip, allowEmptyArrays, strictNullHandling, skipNulls, encodeDotInKeys, \n        // @ts-ignore\n        generateArrayPrefix === 'comma' && encodeValuesOnly && is_array(obj) ? null : encoder, filter, sort, allowDots, serializeDate, format, formatter, encodeValuesOnly, charset, valueSideChannel));\n    }\n    return values;\n}\nfunction normalize_stringify_options(opts = defaults) {\n    if (typeof opts.allowEmptyArrays !== 'undefined' && typeof opts.allowEmptyArrays !== 'boolean') {\n        throw new TypeError('`allowEmptyArrays` option can only be `true` or `false`, when provided');\n    }\n    if (typeof opts.encodeDotInKeys !== 'undefined' && typeof opts.encodeDotInKeys !== 'boolean') {\n        throw new TypeError('`encodeDotInKeys` option can only be `true` or `false`, when provided');\n    }\n    if (opts.encoder !== null && typeof opts.encoder !== 'undefined' && typeof opts.encoder !== 'function') {\n        throw new TypeError('Encoder has to be a function.');\n    }\n    const charset = opts.charset || defaults.charset;\n    if (typeof opts.charset !== 'undefined' && opts.charset !== 'utf-8' && opts.charset !== 'iso-8859-1') {\n        throw new TypeError('The charset option must be either utf-8, iso-8859-1, or undefined');\n    }\n    let format = default_format;\n    if (typeof opts.format !== 'undefined') {\n        if (!has.call(formatters, opts.format)) {\n            throw new TypeError('Unknown format option provided.');\n        }\n        format = opts.format;\n    }\n    const formatter = formatters[format];\n    let filter = defaults.filter;\n    if (typeof opts.filter === 'function' || is_array(opts.filter)) {\n        filter = opts.filter;\n    }\n    let arrayFormat;\n    if (opts.arrayFormat && opts.arrayFormat in array_prefix_generators) {\n        arrayFormat = opts.arrayFormat;\n    }\n    else if ('indices' in opts) {\n        arrayFormat = opts.indices ? 'indices' : 'repeat';\n    }\n    else {\n        arrayFormat = defaults.arrayFormat;\n    }\n    if ('commaRoundTrip' in opts && typeof opts.commaRoundTrip !== 'boolean') {\n        throw new TypeError('`commaRoundTrip` must be a boolean, or absent');\n    }\n    const allowDots = typeof opts.allowDots === 'undefined' ?\n        !!opts.encodeDotInKeys === true ?\n            true\n            : defaults.allowDots\n        : !!opts.allowDots;\n    return {\n        addQueryPrefix: typeof opts.addQueryPrefix === 'boolean' ? opts.addQueryPrefix : defaults.addQueryPrefix,\n        // @ts-ignore\n        allowDots: allowDots,\n        allowEmptyArrays: typeof opts.allowEmptyArrays === 'boolean' ? !!opts.allowEmptyArrays : defaults.allowEmptyArrays,\n        arrayFormat: arrayFormat,\n        charset: charset,\n        charsetSentinel: typeof opts.charsetSentinel === 'boolean' ? opts.charsetSentinel : defaults.charsetSentinel,\n        commaRoundTrip: !!opts.commaRoundTrip,\n        delimiter: typeof opts.delimiter === 'undefined' ? defaults.delimiter : opts.delimiter,\n        encode: typeof opts.encode === 'boolean' ? opts.encode : defaults.encode,\n        encodeDotInKeys: typeof opts.encodeDotInKeys === 'boolean' ? opts.encodeDotInKeys : defaults.encodeDotInKeys,\n        encoder: typeof opts.encoder === 'function' ? opts.encoder : defaults.encoder,\n        encodeValuesOnly: typeof opts.encodeValuesOnly === 'boolean' ? opts.encodeValuesOnly : defaults.encodeValuesOnly,\n        filter: filter,\n        format: format,\n        formatter: formatter,\n        serializeDate: typeof opts.serializeDate === 'function' ? opts.serializeDate : defaults.serializeDate,\n        skipNulls: typeof opts.skipNulls === 'boolean' ? opts.skipNulls : defaults.skipNulls,\n        // @ts-ignore\n        sort: typeof opts.sort === 'function' ? opts.sort : null,\n        strictNullHandling: typeof opts.strictNullHandling === 'boolean' ? opts.strictNullHandling : defaults.strictNullHandling,\n    };\n}\nexport function stringify(object, opts = {}) {\n    let obj = object;\n    const options = normalize_stringify_options(opts);\n    let obj_keys;\n    let filter;\n    if (typeof options.filter === 'function') {\n        filter = options.filter;\n        obj = filter('', obj);\n    }\n    else if (is_array(options.filter)) {\n        filter = options.filter;\n        obj_keys = filter;\n    }\n    const keys = [];\n    if (typeof obj !== 'object' || obj === null) {\n        return '';\n    }\n    const generateArrayPrefix = array_prefix_generators[options.arrayFormat];\n    const commaRoundTrip = generateArrayPrefix === 'comma' && options.commaRoundTrip;\n    if (!obj_keys) {\n        obj_keys = Object.keys(obj);\n    }\n    if (options.sort) {\n        obj_keys.sort(options.sort);\n    }\n    const sideChannel = new WeakMap();\n    for (let i = 0; i < obj_keys.length; ++i) {\n        const key = obj_keys[i];\n        if (options.skipNulls && obj[key] === null) {\n            continue;\n        }\n        push_to_array(keys, inner_stringify(obj[key], key, \n        // @ts-expect-error\n        generateArrayPrefix, commaRoundTrip, options.allowEmptyArrays, options.strictNullHandling, options.skipNulls, options.encodeDotInKeys, options.encode ? options.encoder : null, options.filter, options.sort, options.allowDots, options.serializeDate, options.format, options.formatter, options.encodeValuesOnly, options.charset, sideChannel));\n    }\n    const joined = keys.join(options.delimiter);\n    let prefix = options.addQueryPrefix === true ? '?' : '';\n    if (options.charsetSentinel) {\n        if (options.charset === 'iso-8859-1') {\n            // encodeURIComponent('&#10003;'), the \"numeric entity\" representation of a checkmark\n            prefix += 'utf8=%26%2310003%3B&';\n        }\n        else {\n            // encodeURIComponent('✓')\n            prefix += 'utf8=%E2%9C%93&';\n        }\n    }\n    return joined.length > 0 ? prefix + joined : '';\n}\n//# sourceMappingURL=stringify.mjs.map","export const VERSION = '4.86.2'; // x-release-please-version\n//# sourceMappingURL=version.mjs.map","export let auto = false;\nexport let kind = undefined;\nexport let fetch = undefined;\nexport let Request = undefined;\nexport let Response = undefined;\nexport let Headers = undefined;\nexport let FormData = undefined;\nexport let Blob = undefined;\nexport let File = undefined;\nexport let ReadableStream = undefined;\nexport let getMultipartRequestOptions = undefined;\nexport let getDefaultAgent = undefined;\nexport let fileFromPath = undefined;\nexport let isFsReadStream = undefined;\nexport function setShims(shims, options = { auto: false }) {\n    if (auto) {\n        throw new Error(`you must \\`import 'openai/shims/${shims.kind}'\\` before importing anything else from openai`);\n    }\n    if (kind) {\n        throw new Error(`can't \\`import 'openai/shims/${shims.kind}'\\` after \\`import 'openai/shims/${kind}'\\``);\n    }\n    auto = options.auto;\n    kind = shims.kind;\n    fetch = shims.fetch;\n    Request = shims.Request;\n    Response = shims.Response;\n    Headers = shims.Headers;\n    FormData = shims.FormData;\n    Blob = shims.Blob;\n    File = shims.File;\n    ReadableStream = shims.ReadableStream;\n    getMultipartRequestOptions = shims.getMultipartRequestOptions;\n    getDefaultAgent = shims.getDefaultAgent;\n    fileFromPath = shims.fileFromPath;\n    isFsReadStream = shims.isFsReadStream;\n}\n//# sourceMappingURL=registry.mjs.map","/**\n * Disclaimer: modules in _shims aren't intended to be imported by SDK users.\n */\nexport class MultipartBody {\n    constructor(body) {\n        this.body = body;\n    }\n    get [Symbol.toStringTag]() {\n        return 'MultipartBody';\n    }\n}\n//# sourceMappingURL=MultipartBody.mjs.map","import { MultipartBody } from \"./MultipartBody.mjs\";\nexport function getRuntime({ manuallyImported } = {}) {\n    const recommendation = manuallyImported ?\n        `You may need to use polyfills`\n        : `Add one of these imports before your first \\`import … from 'openai'\\`:\n- \\`import 'openai/shims/node'\\` (if you're running on Node)\n- \\`import 'openai/shims/web'\\` (otherwise)\n`;\n    let _fetch, _Request, _Response, _Headers;\n    try {\n        // @ts-ignore\n        _fetch = fetch;\n        // @ts-ignore\n        _Request = Request;\n        // @ts-ignore\n        _Response = Response;\n        // @ts-ignore\n        _Headers = Headers;\n    }\n    catch (error) {\n        throw new Error(`this environment is missing the following Web Fetch API type: ${error.message}. ${recommendation}`);\n    }\n    return {\n        kind: 'web',\n        fetch: _fetch,\n        Request: _Request,\n        Response: _Response,\n        Headers: _Headers,\n        FormData: \n        // @ts-ignore\n        typeof FormData !== 'undefined' ? FormData : (class FormData {\n            // @ts-ignore\n            constructor() {\n                throw new Error(`file uploads aren't supported in this environment yet as 'FormData' is undefined. ${recommendation}`);\n            }\n        }),\n        Blob: typeof Blob !== 'undefined' ? Blob : (class Blob {\n            constructor() {\n                throw new Error(`file uploads aren't supported in this environment yet as 'Blob' is undefined. ${recommendation}`);\n            }\n        }),\n        File: \n        // @ts-ignore\n        typeof File !== 'undefined' ? File : (class File {\n            // @ts-ignore\n            constructor() {\n                throw new Error(`file uploads aren't supported in this environment yet as 'File' is undefined. ${recommendation}`);\n            }\n        }),\n        ReadableStream: \n        // @ts-ignore\n        typeof ReadableStream !== 'undefined' ? ReadableStream : (class ReadableStream {\n            // @ts-ignore\n            constructor() {\n                throw new Error(`streaming isn't supported in this environment yet as 'ReadableStream' is undefined. ${recommendation}`);\n            }\n        }),\n        getMultipartRequestOptions: async (\n        // @ts-ignore\n        form, opts) => ({\n            ...opts,\n            body: new MultipartBody(form),\n        }),\n        getDefaultAgent: (url) => undefined,\n        fileFromPath: () => {\n            throw new Error('The `fileFromPath` function is only supported in Node. See the README for more details: https://www.github.com/openai/openai-node#file-uploads');\n        },\n        isFsReadStream: (value) => false,\n    };\n}\n//# sourceMappingURL=web-runtime.mjs.map","/**\n * Disclaimer: modules in _shims aren't intended to be imported by SDK users.\n */\nimport * as shims from './registry.mjs';\nimport * as auto from 'openai/_shims/auto/runtime';\nif (!shims.kind) shims.setShims(auto.getRuntime(), { auto: true });\nexport * from './registry.mjs';\n","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { castToError } from \"./core.mjs\";\nexport class OpenAIError extends Error {\n}\nexport class APIError extends OpenAIError {\n    constructor(status, error, message, headers) {\n        super(`${APIError.makeMessage(status, error, message)}`);\n        this.status = status;\n        this.headers = headers;\n        this.request_id = headers?.['x-request-id'];\n        this.error = error;\n        const data = error;\n        this.code = data?.['code'];\n        this.param = data?.['param'];\n        this.type = data?.['type'];\n    }\n    static makeMessage(status, error, message) {\n        const msg = error?.message ?\n            typeof error.message === 'string' ?\n                error.message\n                : JSON.stringify(error.message)\n            : error ? JSON.stringify(error)\n                : message;\n        if (status && msg) {\n            return `${status} ${msg}`;\n        }\n        if (status) {\n            return `${status} status code (no body)`;\n        }\n        if (msg) {\n            return msg;\n        }\n        return '(no status code or body)';\n    }\n    static generate(status, errorResponse, message, headers) {\n        if (!status || !headers) {\n            return new APIConnectionError({ message, cause: castToError(errorResponse) });\n        }\n        const error = errorResponse?.['error'];\n        if (status === 400) {\n            return new BadRequestError(status, error, message, headers);\n        }\n        if (status === 401) {\n            return new AuthenticationError(status, error, message, headers);\n        }\n        if (status === 403) {\n            return new PermissionDeniedError(status, error, message, headers);\n        }\n        if (status === 404) {\n            return new NotFoundError(status, error, message, headers);\n        }\n        if (status === 409) {\n            return new ConflictError(status, error, message, headers);\n        }\n        if (status === 422) {\n            return new UnprocessableEntityError(status, error, message, headers);\n        }\n        if (status === 429) {\n            return new RateLimitError(status, error, message, headers);\n        }\n        if (status >= 500) {\n            return new InternalServerError(status, error, message, headers);\n        }\n        return new APIError(status, error, message, headers);\n    }\n}\nexport class APIUserAbortError extends APIError {\n    constructor({ message } = {}) {\n        super(undefined, undefined, message || 'Request was aborted.', undefined);\n    }\n}\nexport class APIConnectionError extends APIError {\n    constructor({ message, cause }) {\n        super(undefined, undefined, message || 'Connection error.', undefined);\n        // in some environments the 'cause' property is already declared\n        // @ts-ignore\n        if (cause)\n            this.cause = cause;\n    }\n}\nexport class APIConnectionTimeoutError extends APIConnectionError {\n    constructor({ message } = {}) {\n        super({ message: message ?? 'Request timed out.' });\n    }\n}\nexport class BadRequestError extends APIError {\n}\nexport class AuthenticationError extends APIError {\n}\nexport class PermissionDeniedError extends APIError {\n}\nexport class NotFoundError extends APIError {\n}\nexport class ConflictError extends APIError {\n}\nexport class UnprocessableEntityError extends APIError {\n}\nexport class RateLimitError extends APIError {\n}\nexport class InternalServerError extends APIError {\n}\nexport class LengthFinishReasonError extends OpenAIError {\n    constructor() {\n        super(`Could not parse response content as the length limit was reached`);\n    }\n}\nexport class ContentFilterFinishReasonError extends OpenAIError {\n    constructor() {\n        super(`Could not parse response content as the request was rejected by the content filter`);\n    }\n}\n//# sourceMappingURL=error.mjs.map","var __classPrivateFieldSet = (this && this.__classPrivateFieldSet) || function (receiver, state, value, kind, f) {\n    if (kind === \"m\") throw new TypeError(\"Private method is not writable\");\n    if (kind === \"a\" && !f) throw new TypeError(\"Private accessor was defined without a setter\");\n    if (typeof state === \"function\" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError(\"Cannot write private member to an object whose class did not declare it\");\n    return (kind === \"a\" ? f.call(receiver, value) : f ? f.value = value : state.set(receiver, value)), value;\n};\nvar __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {\n    if (kind === \"a\" && !f) throw new TypeError(\"Private accessor was defined without a getter\");\n    if (typeof state === \"function\" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError(\"Cannot read private member from an object whose class did not declare it\");\n    return kind === \"m\" ? f : kind === \"a\" ? f.call(receiver) : f ? f.value : state.get(receiver);\n};\nvar _LineDecoder_carriageReturnIndex;\nimport { OpenAIError } from \"../../error.mjs\";\n/**\n * A re-implementation of httpx's `LineDecoder` in Python that handles incrementally\n * reading lines from text.\n *\n * https://github.com/encode/httpx/blob/920333ea98118e9cf617f246905d7b202510941c/httpx/_decoders.py#L258\n */\nexport class LineDecoder {\n    constructor() {\n        _LineDecoder_carriageReturnIndex.set(this, void 0);\n        this.buffer = new Uint8Array();\n        __classPrivateFieldSet(this, _LineDecoder_carriageReturnIndex, null, \"f\");\n    }\n    decode(chunk) {\n        if (chunk == null) {\n            return [];\n        }\n        const binaryChunk = chunk instanceof ArrayBuffer ? new Uint8Array(chunk)\n            : typeof chunk === 'string' ? new TextEncoder().encode(chunk)\n                : chunk;\n        let newData = new Uint8Array(this.buffer.length + binaryChunk.length);\n        newData.set(this.buffer);\n        newData.set(binaryChunk, this.buffer.length);\n        this.buffer = newData;\n        const lines = [];\n        let patternIndex;\n        while ((patternIndex = findNewlineIndex(this.buffer, __classPrivateFieldGet(this, _LineDecoder_carriageReturnIndex, \"f\"))) != null) {\n            if (patternIndex.carriage && __classPrivateFieldGet(this, _LineDecoder_carriageReturnIndex, \"f\") == null) {\n                // skip until we either get a corresponding `\\n`, a new `\\r` or nothing\n                __classPrivateFieldSet(this, _LineDecoder_carriageReturnIndex, patternIndex.index, \"f\");\n                continue;\n            }\n            // we got double \\r or \\rtext\\n\n            if (__classPrivateFieldGet(this, _LineDecoder_carriageReturnIndex, \"f\") != null &&\n                (patternIndex.index !== __classPrivateFieldGet(this, _LineDecoder_carriageReturnIndex, \"f\") + 1 || patternIndex.carriage)) {\n                lines.push(this.decodeText(this.buffer.slice(0, __classPrivateFieldGet(this, _LineDecoder_carriageReturnIndex, \"f\") - 1)));\n                this.buffer = this.buffer.slice(__classPrivateFieldGet(this, _LineDecoder_carriageReturnIndex, \"f\"));\n                __classPrivateFieldSet(this, _LineDecoder_carriageReturnIndex, null, \"f\");\n                continue;\n            }\n            const endIndex = __classPrivateFieldGet(this, _LineDecoder_carriageReturnIndex, \"f\") !== null ? patternIndex.preceding - 1 : patternIndex.preceding;\n            const line = this.decodeText(this.buffer.slice(0, endIndex));\n            lines.push(line);\n            this.buffer = this.buffer.slice(patternIndex.index);\n            __classPrivateFieldSet(this, _LineDecoder_carriageReturnIndex, null, \"f\");\n        }\n        return lines;\n    }\n    decodeText(bytes) {\n        if (bytes == null)\n            return '';\n        if (typeof bytes === 'string')\n            return bytes;\n        // Node:\n        if (typeof Buffer !== 'undefined') {\n            if (bytes instanceof Buffer) {\n                return bytes.toString();\n            }\n            if (bytes instanceof Uint8Array) {\n                return Buffer.from(bytes).toString();\n            }\n            throw new OpenAIError(`Unexpected: received non-Uint8Array (${bytes.constructor.name}) stream chunk in an environment with a global \"Buffer\" defined, which this library assumes to be Node. Please report this error.`);\n        }\n        // Browser\n        if (typeof TextDecoder !== 'undefined') {\n            if (bytes instanceof Uint8Array || bytes instanceof ArrayBuffer) {\n                this.textDecoder ?? (this.textDecoder = new TextDecoder('utf8'));\n                return this.textDecoder.decode(bytes);\n            }\n            throw new OpenAIError(`Unexpected: received non-Uint8Array/ArrayBuffer (${bytes.constructor.name}) in a web platform. Please report this error.`);\n        }\n        throw new OpenAIError(`Unexpected: neither Buffer nor TextDecoder are available as globals. Please report this error.`);\n    }\n    flush() {\n        if (!this.buffer.length) {\n            return [];\n        }\n        return this.decode('\\n');\n    }\n}\n_LineDecoder_carriageReturnIndex = new WeakMap();\n// prettier-ignore\nLineDecoder.NEWLINE_CHARS = new Set(['\\n', '\\r']);\nLineDecoder.NEWLINE_REGEXP = /\\r\\n|[\\n\\r]/g;\n/**\n * This function searches the buffer for the end patterns, (\\r or \\n)\n * and returns an object with the index preceding the matched newline and the\n * index after the newline char. `null` is returned if no new line is found.\n *\n * ```ts\n * findNewLineIndex('abc\\ndef') -> { preceding: 2, index: 3 }\n * ```\n */\nfunction findNewlineIndex(buffer, startIndex) {\n    const newline = 0x0a; // \\n\n    const carriage = 0x0d; // \\r\n    for (let i = startIndex ?? 0; i < buffer.length; i++) {\n        if (buffer[i] === newline) {\n            return { preceding: i, index: i + 1, carriage: false };\n        }\n        if (buffer[i] === carriage) {\n            return { preceding: i, index: i + 1, carriage: true };\n        }\n    }\n    return null;\n}\nexport function findDoubleNewlineIndex(buffer) {\n    // This function searches the buffer for the end patterns (\\r\\r, \\n\\n, \\r\\n\\r\\n)\n    // and returns the index right after the first occurrence of any pattern,\n    // or -1 if none of the patterns are found.\n    const newline = 0x0a; // \\n\n    const carriage = 0x0d; // \\r\n    for (let i = 0; i < buffer.length - 1; i++) {\n        if (buffer[i] === newline && buffer[i + 1] === newline) {\n            // \\n\\n\n            return i + 2;\n        }\n        if (buffer[i] === carriage && buffer[i + 1] === carriage) {\n            // \\r\\r\n            return i + 2;\n        }\n        if (buffer[i] === carriage &&\n            buffer[i + 1] === newline &&\n            i + 3 < buffer.length &&\n            buffer[i + 2] === carriage &&\n            buffer[i + 3] === newline) {\n            // \\r\\n\\r\\n\n            return i + 4;\n        }\n    }\n    return -1;\n}\n//# sourceMappingURL=line.mjs.map","/**\n * Most browsers don't yet have async iterable support for ReadableStream,\n * and Node has a very different way of reading bytes from its \"ReadableStream\".\n *\n * This polyfill was pulled from https://github.com/MattiasBuelens/web-streams-polyfill/pull/122#issuecomment-1627354490\n */\nexport function ReadableStreamToAsyncIterable(stream) {\n    if (stream[Symbol.asyncIterator])\n        return stream;\n    const reader = stream.getReader();\n    return {\n        async next() {\n            try {\n                const result = await reader.read();\n                if (result?.done)\n                    reader.releaseLock(); // release lock when stream becomes closed\n                return result;\n            }\n            catch (e) {\n                reader.releaseLock(); // release lock when stream becomes errored\n                throw e;\n            }\n        },\n        async return() {\n            const cancelPromise = reader.cancel();\n            reader.releaseLock();\n            await cancelPromise;\n            return { done: true, value: undefined };\n        },\n        [Symbol.asyncIterator]() {\n            return this;\n        },\n    };\n}\n//# sourceMappingURL=stream-utils.mjs.map","import { ReadableStream } from \"./_shims/index.mjs\";\nimport { OpenAIError } from \"./error.mjs\";\nimport { findDoubleNewlineIndex, LineDecoder } from \"./internal/decoders/line.mjs\";\nimport { ReadableStreamToAsyncIterable } from \"./internal/stream-utils.mjs\";\nimport { APIError } from \"./error.mjs\";\nexport class Stream {\n    constructor(iterator, controller) {\n        this.iterator = iterator;\n        this.controller = controller;\n    }\n    static fromSSEResponse(response, controller) {\n        let consumed = false;\n        async function* iterator() {\n            if (consumed) {\n                throw new Error('Cannot iterate over a consumed stream, use `.tee()` to split the stream.');\n            }\n            consumed = true;\n            let done = false;\n            try {\n                for await (const sse of _iterSSEMessages(response, controller)) {\n                    if (done)\n                        continue;\n                    if (sse.data.startsWith('[DONE]')) {\n                        done = true;\n                        continue;\n                    }\n                    if (sse.event === null) {\n                        let data;\n                        try {\n                            data = JSON.parse(sse.data);\n                        }\n                        catch (e) {\n                            console.error(`Could not parse message into JSON:`, sse.data);\n                            console.error(`From chunk:`, sse.raw);\n                            throw e;\n                        }\n                        if (data && data.error) {\n                            throw new APIError(undefined, data.error, undefined, undefined);\n                        }\n                        yield data;\n                    }\n                    else {\n                        let data;\n                        try {\n                            data = JSON.parse(sse.data);\n                        }\n                        catch (e) {\n                            console.error(`Could not parse message into JSON:`, sse.data);\n                            console.error(`From chunk:`, sse.raw);\n                            throw e;\n                        }\n                        // TODO: Is this where the error should be thrown?\n                        if (sse.event == 'error') {\n                            throw new APIError(undefined, data.error, data.message, undefined);\n                        }\n                        yield { event: sse.event, data: data };\n                    }\n                }\n                done = true;\n            }\n            catch (e) {\n                // If the user calls `stream.controller.abort()`, we should exit without throwing.\n                if (e instanceof Error && e.name === 'AbortError')\n                    return;\n                throw e;\n            }\n            finally {\n                // If the user `break`s, abort the ongoing request.\n                if (!done)\n                    controller.abort();\n            }\n        }\n        return new Stream(iterator, controller);\n    }\n    /**\n     * Generates a Stream from a newline-separated ReadableStream\n     * where each item is a JSON value.\n     */\n    static fromReadableStream(readableStream, controller) {\n        let consumed = false;\n        async function* iterLines() {\n            const lineDecoder = new LineDecoder();\n            const iter = ReadableStreamToAsyncIterable(readableStream);\n            for await (const chunk of iter) {\n                for (const line of lineDecoder.decode(chunk)) {\n                    yield line;\n                }\n            }\n            for (const line of lineDecoder.flush()) {\n                yield line;\n            }\n        }\n        async function* iterator() {\n            if (consumed) {\n                throw new Error('Cannot iterate over a consumed stream, use `.tee()` to split the stream.');\n            }\n            consumed = true;\n            let done = false;\n            try {\n                for await (const line of iterLines()) {\n                    if (done)\n                        continue;\n                    if (line)\n                        yield JSON.parse(line);\n                }\n                done = true;\n            }\n            catch (e) {\n                // If the user calls `stream.controller.abort()`, we should exit without throwing.\n                if (e instanceof Error && e.name === 'AbortError')\n                    return;\n                throw e;\n            }\n            finally {\n                // If the user `break`s, abort the ongoing request.\n                if (!done)\n                    controller.abort();\n            }\n        }\n        return new Stream(iterator, controller);\n    }\n    [Symbol.asyncIterator]() {\n        return this.iterator();\n    }\n    /**\n     * Splits the stream into two streams which can be\n     * independently read from at different speeds.\n     */\n    tee() {\n        const left = [];\n        const right = [];\n        const iterator = this.iterator();\n        const teeIterator = (queue) => {\n            return {\n                next: () => {\n                    if (queue.length === 0) {\n                        const result = iterator.next();\n                        left.push(result);\n                        right.push(result);\n                    }\n                    return queue.shift();\n                },\n            };\n        };\n        return [\n            new Stream(() => teeIterator(left), this.controller),\n            new Stream(() => teeIterator(right), this.controller),\n        ];\n    }\n    /**\n     * Converts this stream to a newline-separated ReadableStream of\n     * JSON stringified values in the stream\n     * which can be turned back into a Stream with `Stream.fromReadableStream()`.\n     */\n    toReadableStream() {\n        const self = this;\n        let iter;\n        const encoder = new TextEncoder();\n        return new ReadableStream({\n            async start() {\n                iter = self[Symbol.asyncIterator]();\n            },\n            async pull(ctrl) {\n                try {\n                    const { value, done } = await iter.next();\n                    if (done)\n                        return ctrl.close();\n                    const bytes = encoder.encode(JSON.stringify(value) + '\\n');\n                    ctrl.enqueue(bytes);\n                }\n                catch (err) {\n                    ctrl.error(err);\n                }\n            },\n            async cancel() {\n                await iter.return?.();\n            },\n        });\n    }\n}\nexport async function* _iterSSEMessages(response, controller) {\n    if (!response.body) {\n        controller.abort();\n        throw new OpenAIError(`Attempted to iterate over a response with no body`);\n    }\n    const sseDecoder = new SSEDecoder();\n    const lineDecoder = new LineDecoder();\n    const iter = ReadableStreamToAsyncIterable(response.body);\n    for await (const sseChunk of iterSSEChunks(iter)) {\n        for (const line of lineDecoder.decode(sseChunk)) {\n            const sse = sseDecoder.decode(line);\n            if (sse)\n                yield sse;\n        }\n    }\n    for (const line of lineDecoder.flush()) {\n        const sse = sseDecoder.decode(line);\n        if (sse)\n            yield sse;\n    }\n}\n/**\n * Given an async iterable iterator, iterates over it and yields full\n * SSE chunks, i.e. yields when a double new-line is encountered.\n */\nasync function* iterSSEChunks(iterator) {\n    let data = new Uint8Array();\n    for await (const chunk of iterator) {\n        if (chunk == null) {\n            continue;\n        }\n        const binaryChunk = chunk instanceof ArrayBuffer ? new Uint8Array(chunk)\n            : typeof chunk === 'string' ? new TextEncoder().encode(chunk)\n                : chunk;\n        let newData = new Uint8Array(data.length + binaryChunk.length);\n        newData.set(data);\n        newData.set(binaryChunk, data.length);\n        data = newData;\n        let patternIndex;\n        while ((patternIndex = findDoubleNewlineIndex(data)) !== -1) {\n            yield data.slice(0, patternIndex);\n            data = data.slice(patternIndex);\n        }\n    }\n    if (data.length > 0) {\n        yield data;\n    }\n}\nclass SSEDecoder {\n    constructor() {\n        this.event = null;\n        this.data = [];\n        this.chunks = [];\n    }\n    decode(line) {\n        if (line.endsWith('\\r')) {\n            line = line.substring(0, line.length - 1);\n        }\n        if (!line) {\n            // empty line and we didn't previously encounter any messages\n            if (!this.event && !this.data.length)\n                return null;\n            const sse = {\n                event: this.event,\n                data: this.data.join('\\n'),\n                raw: this.chunks,\n            };\n            this.event = null;\n            this.data = [];\n            this.chunks = [];\n            return sse;\n        }\n        this.chunks.push(line);\n        if (line.startsWith(':')) {\n            return null;\n        }\n        let [fieldname, _, value] = partition(line, ':');\n        if (value.startsWith(' ')) {\n            value = value.substring(1);\n        }\n        if (fieldname === 'event') {\n            this.event = value;\n        }\n        else if (fieldname === 'data') {\n            this.data.push(value);\n        }\n        return null;\n    }\n}\nfunction partition(str, delimiter) {\n    const index = str.indexOf(delimiter);\n    if (index !== -1) {\n        return [str.substring(0, index), delimiter, str.substring(index + delimiter.length)];\n    }\n    return [str, '', ''];\n}\n//# sourceMappingURL=streaming.mjs.map","import { FormData, File, getMultipartRequestOptions, isFsReadStream, } from \"./_shims/index.mjs\";\nexport { fileFromPath } from \"./_shims/index.mjs\";\nexport const isResponseLike = (value) => value != null &&\n    typeof value === 'object' &&\n    typeof value.url === 'string' &&\n    typeof value.blob === 'function';\nexport const isFileLike = (value) => value != null &&\n    typeof value === 'object' &&\n    typeof value.name === 'string' &&\n    typeof value.lastModified === 'number' &&\n    isBlobLike(value);\n/**\n * The BlobLike type omits arrayBuffer() because @types/node-fetch@^2.6.4 lacks it; but this check\n * adds the arrayBuffer() method type because it is available and used at runtime\n */\nexport const isBlobLike = (value) => value != null &&\n    typeof value === 'object' &&\n    typeof value.size === 'number' &&\n    typeof value.type === 'string' &&\n    typeof value.text === 'function' &&\n    typeof value.slice === 'function' &&\n    typeof value.arrayBuffer === 'function';\nexport const isUploadable = (value) => {\n    return isFileLike(value) || isResponseLike(value) || isFsReadStream(value);\n};\n/**\n * Helper for creating a {@link File} to pass to an SDK upload method from a variety of different data formats\n * @param value the raw content of the file.  Can be an {@link Uploadable}, {@link BlobLikePart}, or {@link AsyncIterable} of {@link BlobLikePart}s\n * @param {string=} name the name of the file. If omitted, toFile will try to determine a file name from bits if possible\n * @param {Object=} options additional properties\n * @param {string=} options.type the MIME type of the content\n * @param {number=} options.lastModified the last modified timestamp\n * @returns a {@link File} with the given properties\n */\nexport async function toFile(value, name, options) {\n    // If it's a promise, resolve it.\n    value = await value;\n    // If we've been given a `File` we don't need to do anything\n    if (isFileLike(value)) {\n        return value;\n    }\n    if (isResponseLike(value)) {\n        const blob = await value.blob();\n        name || (name = new URL(value.url).pathname.split(/[\\\\/]/).pop() ?? 'unknown_file');\n        // we need to convert the `Blob` into an array buffer because the `Blob` class\n        // that `node-fetch` defines is incompatible with the web standard which results\n        // in `new File` interpreting it as a string instead of binary data.\n        const data = isBlobLike(blob) ? [(await blob.arrayBuffer())] : [blob];\n        return new File(data, name, options);\n    }\n    const bits = await getBytes(value);\n    name || (name = getName(value) ?? 'unknown_file');\n    if (!options?.type) {\n        const type = bits[0]?.type;\n        if (typeof type === 'string') {\n            options = { ...options, type };\n        }\n    }\n    return new File(bits, name, options);\n}\nasync function getBytes(value) {\n    let parts = [];\n    if (typeof value === 'string' ||\n        ArrayBuffer.isView(value) || // includes Uint8Array, Buffer, etc.\n        value instanceof ArrayBuffer) {\n        parts.push(value);\n    }\n    else if (isBlobLike(value)) {\n        parts.push(await value.arrayBuffer());\n    }\n    else if (isAsyncIterableIterator(value) // includes Readable, ReadableStream, etc.\n    ) {\n        for await (const chunk of value) {\n            parts.push(chunk); // TODO, consider validating?\n        }\n    }\n    else {\n        throw new Error(`Unexpected data type: ${typeof value}; constructor: ${value?.constructor\n            ?.name}; props: ${propsForError(value)}`);\n    }\n    return parts;\n}\nfunction propsForError(value) {\n    const props = Object.getOwnPropertyNames(value);\n    return `[${props.map((p) => `\"${p}\"`).join(', ')}]`;\n}\nfunction getName(value) {\n    return (getStringFromMaybeBuffer(value.name) ||\n        getStringFromMaybeBuffer(value.filename) ||\n        // For fs.ReadStream\n        getStringFromMaybeBuffer(value.path)?.split(/[\\\\/]/).pop());\n}\nconst getStringFromMaybeBuffer = (x) => {\n    if (typeof x === 'string')\n        return x;\n    if (typeof Buffer !== 'undefined' && x instanceof Buffer)\n        return String(x);\n    return undefined;\n};\nconst isAsyncIterableIterator = (value) => value != null && typeof value === 'object' && typeof value[Symbol.asyncIterator] === 'function';\nexport const isMultipartBody = (body) => body && typeof body === 'object' && body.body && body[Symbol.toStringTag] === 'MultipartBody';\n/**\n * Returns a multipart/form-data request if any part of the given request body contains a File / Blob value.\n * Otherwise returns the request as is.\n */\nexport const maybeMultipartFormRequestOptions = async (opts) => {\n    if (!hasUploadableValue(opts.body))\n        return opts;\n    const form = await createForm(opts.body);\n    return getMultipartRequestOptions(form, opts);\n};\nexport const multipartFormRequestOptions = async (opts) => {\n    const form = await createForm(opts.body);\n    return getMultipartRequestOptions(form, opts);\n};\nexport const createForm = async (body) => {\n    const form = new FormData();\n    await Promise.all(Object.entries(body || {}).map(([key, value]) => addFormValue(form, key, value)));\n    return form;\n};\nconst hasUploadableValue = (value) => {\n    if (isUploadable(value))\n        return true;\n    if (Array.isArray(value))\n        return value.some(hasUploadableValue);\n    if (value && typeof value === 'object') {\n        for (const k in value) {\n            if (hasUploadableValue(value[k]))\n                return true;\n        }\n    }\n    return false;\n};\nconst addFormValue = async (form, key, value) => {\n    if (value === undefined)\n        return;\n    if (value == null) {\n        throw new TypeError(`Received null for \"${key}\"; to pass null in FormData, you must use the string 'null'`);\n    }\n    // TODO: make nested formats configurable\n    if (typeof value === 'string' || typeof value === 'number' || typeof value === 'boolean') {\n        form.append(key, String(value));\n    }\n    else if (isUploadable(value)) {\n        const file = await toFile(value);\n        form.append(key, file);\n    }\n    else if (Array.isArray(value)) {\n        await Promise.all(value.map((entry) => addFormValue(form, key + '[]', entry)));\n    }\n    else if (typeof value === 'object') {\n        await Promise.all(Object.entries(value).map(([name, prop]) => addFormValue(form, `${key}[${name}]`, prop)));\n    }\n    else {\n        throw new TypeError(`Invalid value given to form, expected a string, number, boolean, object, Array, File or Blob but got ${value} instead`);\n    }\n};\n//# sourceMappingURL=uploads.mjs.map","var __classPrivateFieldSet = (this && this.__classPrivateFieldSet) || function (receiver, state, value, kind, f) {\n    if (kind === \"m\") throw new TypeError(\"Private method is not writable\");\n    if (kind === \"a\" && !f) throw new TypeError(\"Private accessor was defined without a setter\");\n    if (typeof state === \"function\" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError(\"Cannot write private member to an object whose class did not declare it\");\n    return (kind === \"a\" ? f.call(receiver, value) : f ? f.value = value : state.set(receiver, value)), value;\n};\nvar __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {\n    if (kind === \"a\" && !f) throw new TypeError(\"Private accessor was defined without a getter\");\n    if (typeof state === \"function\" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError(\"Cannot read private member from an object whose class did not declare it\");\n    return kind === \"m\" ? f : kind === \"a\" ? f.call(receiver) : f ? f.value : state.get(receiver);\n};\nvar _AbstractPage_client;\nimport { VERSION } from \"./version.mjs\";\nimport { Stream } from \"./streaming.mjs\";\nimport { OpenAIError, APIError, APIConnectionError, APIConnectionTimeoutError, APIUserAbortError, } from \"./error.mjs\";\nimport { kind as shimsKind, getDefaultAgent, fetch, } from \"./_shims/index.mjs\";\nimport { isBlobLike, isMultipartBody } from \"./uploads.mjs\";\nexport { maybeMultipartFormRequestOptions, multipartFormRequestOptions, createForm, } from \"./uploads.mjs\";\nasync function defaultParseResponse(props) {\n    const { response } = props;\n    if (props.options.stream) {\n        debug('response', response.status, response.url, response.headers, response.body);\n        // Note: there is an invariant here that isn't represented in the type system\n        // that if you set `stream: true` the response type must also be `Stream<T>`\n        if (props.options.__streamClass) {\n            return props.options.__streamClass.fromSSEResponse(response, props.controller);\n        }\n        return Stream.fromSSEResponse(response, props.controller);\n    }\n    // fetch refuses to read the body when the status code is 204.\n    if (response.status === 204) {\n        return null;\n    }\n    if (props.options.__binaryResponse) {\n        return response;\n    }\n    const contentType = response.headers.get('content-type');\n    const isJSON = contentType?.includes('application/json') || contentType?.includes('application/vnd.api+json');\n    if (isJSON) {\n        const json = await response.json();\n        debug('response', response.status, response.url, response.headers, json);\n        return _addRequestID(json, response);\n    }\n    const text = await response.text();\n    debug('response', response.status, response.url, response.headers, text);\n    // TODO handle blob, arraybuffer, other content types, etc.\n    return text;\n}\nfunction _addRequestID(value, response) {\n    if (!value || typeof value !== 'object' || Array.isArray(value)) {\n        return value;\n    }\n    return Object.defineProperty(value, '_request_id', {\n        value: response.headers.get('x-request-id'),\n        enumerable: false,\n    });\n}\n/**\n * A subclass of `Promise` providing additional helper methods\n * for interacting with the SDK.\n */\nexport class APIPromise extends Promise {\n    constructor(responsePromise, parseResponse = defaultParseResponse) {\n        super((resolve) => {\n            // this is maybe a bit weird but this has to be a no-op to not implicitly\n            // parse the response body; instead .then, .catch, .finally are overridden\n            // to parse the response\n            resolve(null);\n        });\n        this.responsePromise = responsePromise;\n        this.parseResponse = parseResponse;\n    }\n    _thenUnwrap(transform) {\n        return new APIPromise(this.responsePromise, async (props) => _addRequestID(transform(await this.parseResponse(props), props), props.response));\n    }\n    /**\n     * Gets the raw `Response` instance instead of parsing the response\n     * data.\n     *\n     * If you want to parse the response body but still get the `Response`\n     * instance, you can use {@link withResponse()}.\n     *\n     * 👋 Getting the wrong TypeScript type for `Response`?\n     * Try setting `\"moduleResolution\": \"NodeNext\"` if you can,\n     * or add one of these imports before your first `import … from 'openai'`:\n     * - `import 'openai/shims/node'` (if you're running on Node)\n     * - `import 'openai/shims/web'` (otherwise)\n     */\n    asResponse() {\n        return this.responsePromise.then((p) => p.response);\n    }\n    /**\n     * Gets the parsed response data, the raw `Response` instance and the ID of the request,\n     * returned via the X-Request-ID header which is useful for debugging requests and reporting\n     * issues to OpenAI.\n     *\n     * If you just want to get the raw `Response` instance without parsing it,\n     * you can use {@link asResponse()}.\n     *\n     *\n     * 👋 Getting the wrong TypeScript type for `Response`?\n     * Try setting `\"moduleResolution\": \"NodeNext\"` if you can,\n     * or add one of these imports before your first `import … from 'openai'`:\n     * - `import 'openai/shims/node'` (if you're running on Node)\n     * - `import 'openai/shims/web'` (otherwise)\n     */\n    async withResponse() {\n        const [data, response] = await Promise.all([this.parse(), this.asResponse()]);\n        return { data, response, request_id: response.headers.get('x-request-id') };\n    }\n    parse() {\n        if (!this.parsedPromise) {\n            this.parsedPromise = this.responsePromise.then(this.parseResponse);\n        }\n        return this.parsedPromise;\n    }\n    then(onfulfilled, onrejected) {\n        return this.parse().then(onfulfilled, onrejected);\n    }\n    catch(onrejected) {\n        return this.parse().catch(onrejected);\n    }\n    finally(onfinally) {\n        return this.parse().finally(onfinally);\n    }\n}\nexport class APIClient {\n    constructor({ baseURL, maxRetries = 2, timeout = 600000, // 10 minutes\n    httpAgent, fetch: overriddenFetch, }) {\n        this.baseURL = baseURL;\n        this.maxRetries = validatePositiveInteger('maxRetries', maxRetries);\n        this.timeout = validatePositiveInteger('timeout', timeout);\n        this.httpAgent = httpAgent;\n        this.fetch = overriddenFetch ?? fetch;\n    }\n    authHeaders(opts) {\n        return {};\n    }\n    /**\n     * Override this to add your own default headers, for example:\n     *\n     *  {\n     *    ...super.defaultHeaders(),\n     *    Authorization: 'Bearer 123',\n     *  }\n     */\n    defaultHeaders(opts) {\n        return {\n            Accept: 'application/json',\n            'Content-Type': 'application/json',\n            'User-Agent': this.getUserAgent(),\n            ...getPlatformHeaders(),\n            ...this.authHeaders(opts),\n        };\n    }\n    /**\n     * Override this to add your own headers validation:\n     */\n    validateHeaders(headers, customHeaders) { }\n    defaultIdempotencyKey() {\n        return `stainless-node-retry-${uuid4()}`;\n    }\n    get(path, opts) {\n        return this.methodRequest('get', path, opts);\n    }\n    post(path, opts) {\n        return this.methodRequest('post', path, opts);\n    }\n    patch(path, opts) {\n        return this.methodRequest('patch', path, opts);\n    }\n    put(path, opts) {\n        return this.methodRequest('put', path, opts);\n    }\n    delete(path, opts) {\n        return this.methodRequest('delete', path, opts);\n    }\n    methodRequest(method, path, opts) {\n        return this.request(Promise.resolve(opts).then(async (opts) => {\n            const body = opts && isBlobLike(opts?.body) ? new DataView(await opts.body.arrayBuffer())\n                : opts?.body instanceof DataView ? opts.body\n                    : opts?.body instanceof ArrayBuffer ? new DataView(opts.body)\n                        : opts && ArrayBuffer.isView(opts?.body) ? new DataView(opts.body.buffer)\n                            : opts?.body;\n            return { method, path, ...opts, body };\n        }));\n    }\n    getAPIList(path, Page, opts) {\n        return this.requestAPIList(Page, { method: 'get', path, ...opts });\n    }\n    calculateContentLength(body) {\n        if (typeof body === 'string') {\n            if (typeof Buffer !== 'undefined') {\n                return Buffer.byteLength(body, 'utf8').toString();\n            }\n            if (typeof TextEncoder !== 'undefined') {\n                const encoder = new TextEncoder();\n                const encoded = encoder.encode(body);\n                return encoded.length.toString();\n            }\n        }\n        else if (ArrayBuffer.isView(body)) {\n            return body.byteLength.toString();\n        }\n        return null;\n    }\n    buildRequest(options, { retryCount = 0 } = {}) {\n        options = { ...options };\n        const { method, path, query, headers: headers = {} } = options;\n        const body = ArrayBuffer.isView(options.body) || (options.__binaryRequest && typeof options.body === 'string') ?\n            options.body\n            : isMultipartBody(options.body) ? options.body.body\n                : options.body ? JSON.stringify(options.body, null, 2)\n                    : null;\n        const contentLength = this.calculateContentLength(body);\n        const url = this.buildURL(path, query);\n        if ('timeout' in options)\n            validatePositiveInteger('timeout', options.timeout);\n        options.timeout = options.timeout ?? this.timeout;\n        const httpAgent = options.httpAgent ?? this.httpAgent ?? getDefaultAgent(url);\n        const minAgentTimeout = options.timeout + 1000;\n        if (typeof httpAgent?.options?.timeout === 'number' &&\n            minAgentTimeout > (httpAgent.options.timeout ?? 0)) {\n            // Allow any given request to bump our agent active socket timeout.\n            // This may seem strange, but leaking active sockets should be rare and not particularly problematic,\n            // and without mutating agent we would need to create more of them.\n            // This tradeoff optimizes for performance.\n            httpAgent.options.timeout = minAgentTimeout;\n        }\n        if (this.idempotencyHeader && method !== 'get') {\n            if (!options.idempotencyKey)\n                options.idempotencyKey = this.defaultIdempotencyKey();\n            headers[this.idempotencyHeader] = options.idempotencyKey;\n        }\n        const reqHeaders = this.buildHeaders({ options, headers, contentLength, retryCount });\n        const req = {\n            method,\n            ...(body && { body: body }),\n            headers: reqHeaders,\n            ...(httpAgent && { agent: httpAgent }),\n            // @ts-ignore node-fetch uses a custom AbortSignal type that is\n            // not compatible with standard web types\n            signal: options.signal ?? null,\n        };\n        return { req, url, timeout: options.timeout };\n    }\n    buildHeaders({ options, headers, contentLength, retryCount, }) {\n        const reqHeaders = {};\n        if (contentLength) {\n            reqHeaders['content-length'] = contentLength;\n        }\n        const defaultHeaders = this.defaultHeaders(options);\n        applyHeadersMut(reqHeaders, defaultHeaders);\n        applyHeadersMut(reqHeaders, headers);\n        // let builtin fetch set the Content-Type for multipart bodies\n        if (isMultipartBody(options.body) && shimsKind !== 'node') {\n            delete reqHeaders['content-type'];\n        }\n        // Don't set theses headers if they were already set or removed through default headers or by the caller.\n        // We check `defaultHeaders` and `headers`, which can contain nulls, instead of `reqHeaders` to account\n        // for the removal case.\n        if (getHeader(defaultHeaders, 'x-stainless-retry-count') === undefined &&\n            getHeader(headers, 'x-stainless-retry-count') === undefined) {\n            reqHeaders['x-stainless-retry-count'] = String(retryCount);\n        }\n        if (getHeader(defaultHeaders, 'x-stainless-timeout') === undefined &&\n            getHeader(headers, 'x-stainless-timeout') === undefined &&\n            options.timeout) {\n            reqHeaders['x-stainless-timeout'] = String(options.timeout);\n        }\n        this.validateHeaders(reqHeaders, headers);\n        return reqHeaders;\n    }\n    /**\n     * Used as a callback for mutating the given `FinalRequestOptions` object.\n     */\n    async prepareOptions(options) { }\n    /**\n     * Used as a callback for mutating the given `RequestInit` object.\n     *\n     * This is useful for cases where you want to add certain headers based off of\n     * the request properties, e.g. `method` or `url`.\n     */\n    async prepareRequest(request, { url, options }) { }\n    parseHeaders(headers) {\n        return (!headers ? {}\n            : Symbol.iterator in headers ?\n                Object.fromEntries(Array.from(headers).map((header) => [...header]))\n                : { ...headers });\n    }\n    makeStatusError(status, error, message, headers) {\n        return APIError.generate(status, error, message, headers);\n    }\n    request(options, remainingRetries = null) {\n        return new APIPromise(this.makeRequest(options, remainingRetries));\n    }\n    async makeRequest(optionsInput, retriesRemaining) {\n        const options = await optionsInput;\n        const maxRetries = options.maxRetries ?? this.maxRetries;\n        if (retriesRemaining == null) {\n            retriesRemaining = maxRetries;\n        }\n        await this.prepareOptions(options);\n        const { req, url, timeout } = this.buildRequest(options, { retryCount: maxRetries - retriesRemaining });\n        await this.prepareRequest(req, { url, options });\n        debug('request', url, options, req.headers);\n        if (options.signal?.aborted) {\n            throw new APIUserAbortError();\n        }\n        const controller = new AbortController();\n        const response = await this.fetchWithTimeout(url, req, timeout, controller).catch(castToError);\n        if (response instanceof Error) {\n            if (options.signal?.aborted) {\n                throw new APIUserAbortError();\n            }\n            if (retriesRemaining) {\n                return this.retryRequest(options, retriesRemaining);\n            }\n            if (response.name === 'AbortError') {\n                throw new APIConnectionTimeoutError();\n            }\n            throw new APIConnectionError({ cause: response });\n        }\n        const responseHeaders = createResponseHeaders(response.headers);\n        if (!response.ok) {\n            if (retriesRemaining && this.shouldRetry(response)) {\n                const retryMessage = `retrying, ${retriesRemaining} attempts remaining`;\n                debug(`response (error; ${retryMessage})`, response.status, url, responseHeaders);\n                return this.retryRequest(options, retriesRemaining, responseHeaders);\n            }\n            const errText = await response.text().catch((e) => castToError(e).message);\n            const errJSON = safeJSON(errText);\n            const errMessage = errJSON ? undefined : errText;\n            const retryMessage = retriesRemaining ? `(error; no more retries left)` : `(error; not retryable)`;\n            debug(`response (error; ${retryMessage})`, response.status, url, responseHeaders, errMessage);\n            const err = this.makeStatusError(response.status, errJSON, errMessage, responseHeaders);\n            throw err;\n        }\n        return { response, options, controller };\n    }\n    requestAPIList(Page, options) {\n        const request = this.makeRequest(options, null);\n        return new PagePromise(this, request, Page);\n    }\n    buildURL(path, query) {\n        const url = isAbsoluteURL(path) ?\n            new URL(path)\n            : new URL(this.baseURL + (this.baseURL.endsWith('/') && path.startsWith('/') ? path.slice(1) : path));\n        const defaultQuery = this.defaultQuery();\n        if (!isEmptyObj(defaultQuery)) {\n            query = { ...defaultQuery, ...query };\n        }\n        if (typeof query === 'object' && query && !Array.isArray(query)) {\n            url.search = this.stringifyQuery(query);\n        }\n        return url.toString();\n    }\n    stringifyQuery(query) {\n        return Object.entries(query)\n            .filter(([_, value]) => typeof value !== 'undefined')\n            .map(([key, value]) => {\n            if (typeof value === 'string' || typeof value === 'number' || typeof value === 'boolean') {\n                return `${encodeURIComponent(key)}=${encodeURIComponent(value)}`;\n            }\n            if (value === null) {\n                return `${encodeURIComponent(key)}=`;\n            }\n            throw new OpenAIError(`Cannot stringify type ${typeof value}; Expected string, number, boolean, or null. If you need to pass nested query parameters, you can manually encode them, e.g. { query: { 'foo[key1]': value1, 'foo[key2]': value2 } }, and please open a GitHub issue requesting better support for your use case.`);\n        })\n            .join('&');\n    }\n    async fetchWithTimeout(url, init, ms, controller) {\n        const { signal, ...options } = init || {};\n        if (signal)\n            signal.addEventListener('abort', () => controller.abort());\n        const timeout = setTimeout(() => controller.abort(), ms);\n        const fetchOptions = {\n            signal: controller.signal,\n            ...options,\n        };\n        if (fetchOptions.method) {\n            // Custom methods like 'patch' need to be uppercased\n            // See https://github.com/nodejs/undici/issues/2294\n            fetchOptions.method = fetchOptions.method.toUpperCase();\n        }\n        return (\n        // use undefined this binding; fetch errors if bound to something else in browser/cloudflare\n        this.fetch.call(undefined, url, fetchOptions).finally(() => {\n            clearTimeout(timeout);\n        }));\n    }\n    shouldRetry(response) {\n        // Note this is not a standard header.\n        const shouldRetryHeader = response.headers.get('x-should-retry');\n        // If the server explicitly says whether or not to retry, obey.\n        if (shouldRetryHeader === 'true')\n            return true;\n        if (shouldRetryHeader === 'false')\n            return false;\n        // Retry on request timeouts.\n        if (response.status === 408)\n            return true;\n        // Retry on lock timeouts.\n        if (response.status === 409)\n            return true;\n        // Retry on rate limits.\n        if (response.status === 429)\n            return true;\n        // Retry internal errors.\n        if (response.status >= 500)\n            return true;\n        return false;\n    }\n    async retryRequest(options, retriesRemaining, responseHeaders) {\n        let timeoutMillis;\n        // Note the `retry-after-ms` header may not be standard, but is a good idea and we'd like proactive support for it.\n        const retryAfterMillisHeader = responseHeaders?.['retry-after-ms'];\n        if (retryAfterMillisHeader) {\n            const timeoutMs = parseFloat(retryAfterMillisHeader);\n            if (!Number.isNaN(timeoutMs)) {\n                timeoutMillis = timeoutMs;\n            }\n        }\n        // About the Retry-After header: https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Retry-After\n        const retryAfterHeader = responseHeaders?.['retry-after'];\n        if (retryAfterHeader && !timeoutMillis) {\n            const timeoutSeconds = parseFloat(retryAfterHeader);\n            if (!Number.isNaN(timeoutSeconds)) {\n                timeoutMillis = timeoutSeconds * 1000;\n            }\n            else {\n                timeoutMillis = Date.parse(retryAfterHeader) - Date.now();\n            }\n        }\n        // If the API asks us to wait a certain amount of time (and it's a reasonable amount),\n        // just do what it says, but otherwise calculate a default\n        if (!(timeoutMillis && 0 <= timeoutMillis && timeoutMillis < 60 * 1000)) {\n            const maxRetries = options.maxRetries ?? this.maxRetries;\n            timeoutMillis = this.calculateDefaultRetryTimeoutMillis(retriesRemaining, maxRetries);\n        }\n        await sleep(timeoutMillis);\n        return this.makeRequest(options, retriesRemaining - 1);\n    }\n    calculateDefaultRetryTimeoutMillis(retriesRemaining, maxRetries) {\n        const initialRetryDelay = 0.5;\n        const maxRetryDelay = 8.0;\n        const numRetries = maxRetries - retriesRemaining;\n        // Apply exponential backoff, but not more than the max.\n        const sleepSeconds = Math.min(initialRetryDelay * Math.pow(2, numRetries), maxRetryDelay);\n        // Apply some jitter, take up to at most 25 percent of the retry time.\n        const jitter = 1 - Math.random() * 0.25;\n        return sleepSeconds * jitter * 1000;\n    }\n    getUserAgent() {\n        return `${this.constructor.name}/JS ${VERSION}`;\n    }\n}\nexport class AbstractPage {\n    constructor(client, response, body, options) {\n        _AbstractPage_client.set(this, void 0);\n        __classPrivateFieldSet(this, _AbstractPage_client, client, \"f\");\n        this.options = options;\n        this.response = response;\n        this.body = body;\n    }\n    hasNextPage() {\n        const items = this.getPaginatedItems();\n        if (!items.length)\n            return false;\n        return this.nextPageInfo() != null;\n    }\n    async getNextPage() {\n        const nextInfo = this.nextPageInfo();\n        if (!nextInfo) {\n            throw new OpenAIError('No next page expected; please check `.hasNextPage()` before calling `.getNextPage()`.');\n        }\n        const nextOptions = { ...this.options };\n        if ('params' in nextInfo && typeof nextOptions.query === 'object') {\n            nextOptions.query = { ...nextOptions.query, ...nextInfo.params };\n        }\n        else if ('url' in nextInfo) {\n            const params = [...Object.entries(nextOptions.query || {}), ...nextInfo.url.searchParams.entries()];\n            for (const [key, value] of params) {\n                nextInfo.url.searchParams.set(key, value);\n            }\n            nextOptions.query = undefined;\n            nextOptions.path = nextInfo.url.toString();\n        }\n        return await __classPrivateFieldGet(this, _AbstractPage_client, \"f\").requestAPIList(this.constructor, nextOptions);\n    }\n    async *iterPages() {\n        // eslint-disable-next-line @typescript-eslint/no-this-alias\n        let page = this;\n        yield page;\n        while (page.hasNextPage()) {\n            page = await page.getNextPage();\n            yield page;\n        }\n    }\n    async *[(_AbstractPage_client = new WeakMap(), Symbol.asyncIterator)]() {\n        for await (const page of this.iterPages()) {\n            for (const item of page.getPaginatedItems()) {\n                yield item;\n            }\n        }\n    }\n}\n/**\n * This subclass of Promise will resolve to an instantiated Page once the request completes.\n *\n * It also implements AsyncIterable to allow auto-paginating iteration on an unawaited list call, eg:\n *\n *    for await (const item of client.items.list()) {\n *      console.log(item)\n *    }\n */\nexport class PagePromise extends APIPromise {\n    constructor(client, request, Page) {\n        super(request, async (props) => new Page(client, props.response, await defaultParseResponse(props), props.options));\n    }\n    /**\n     * Allow auto-paginating iteration on an unawaited list call, eg:\n     *\n     *    for await (const item of client.items.list()) {\n     *      console.log(item)\n     *    }\n     */\n    async *[Symbol.asyncIterator]() {\n        const page = await this;\n        for await (const item of page) {\n            yield item;\n        }\n    }\n}\nexport const createResponseHeaders = (headers) => {\n    return new Proxy(Object.fromEntries(\n    // @ts-ignore\n    headers.entries()), {\n        get(target, name) {\n            const key = name.toString();\n            return target[key.toLowerCase()] || target[key];\n        },\n    });\n};\n// This is required so that we can determine if a given object matches the RequestOptions\n// type at runtime. While this requires duplication, it is enforced by the TypeScript\n// compiler such that any missing / extraneous keys will cause an error.\nconst requestOptionsKeys = {\n    method: true,\n    path: true,\n    query: true,\n    body: true,\n    headers: true,\n    maxRetries: true,\n    stream: true,\n    timeout: true,\n    httpAgent: true,\n    signal: true,\n    idempotencyKey: true,\n    __metadata: true,\n    __binaryRequest: true,\n    __binaryResponse: true,\n    __streamClass: true,\n};\nexport const isRequestOptions = (obj) => {\n    return (typeof obj === 'object' &&\n        obj !== null &&\n        !isEmptyObj(obj) &&\n        Object.keys(obj).every((k) => hasOwn(requestOptionsKeys, k)));\n};\nconst getPlatformProperties = () => {\n    if (typeof Deno !== 'undefined' && Deno.build != null) {\n        return {\n            'X-Stainless-Lang': 'js',\n            'X-Stainless-Package-Version': VERSION,\n            'X-Stainless-OS': normalizePlatform(Deno.build.os),\n            'X-Stainless-Arch': normalizeArch(Deno.build.arch),\n            'X-Stainless-Runtime': 'deno',\n            'X-Stainless-Runtime-Version': typeof Deno.version === 'string' ? Deno.version : Deno.version?.deno ?? 'unknown',\n        };\n    }\n    if (typeof EdgeRuntime !== 'undefined') {\n        return {\n            'X-Stainless-Lang': 'js',\n            'X-Stainless-Package-Version': VERSION,\n            'X-Stainless-OS': 'Unknown',\n            'X-Stainless-Arch': `other:${EdgeRuntime}`,\n            'X-Stainless-Runtime': 'edge',\n            'X-Stainless-Runtime-Version': process.version,\n        };\n    }\n    // Check if Node.js\n    if (Object.prototype.toString.call(typeof process !== 'undefined' ? process : 0) === '[object process]') {\n        return {\n            'X-Stainless-Lang': 'js',\n            'X-Stainless-Package-Version': VERSION,\n            'X-Stainless-OS': normalizePlatform(process.platform),\n            'X-Stainless-Arch': normalizeArch(process.arch),\n            'X-Stainless-Runtime': 'node',\n            'X-Stainless-Runtime-Version': process.version,\n        };\n    }\n    const browserInfo = getBrowserInfo();\n    if (browserInfo) {\n        return {\n            'X-Stainless-Lang': 'js',\n            'X-Stainless-Package-Version': VERSION,\n            'X-Stainless-OS': 'Unknown',\n            'X-Stainless-Arch': 'unknown',\n            'X-Stainless-Runtime': `browser:${browserInfo.browser}`,\n            'X-Stainless-Runtime-Version': browserInfo.version,\n        };\n    }\n    // TODO add support for Cloudflare workers, etc.\n    return {\n        'X-Stainless-Lang': 'js',\n        'X-Stainless-Package-Version': VERSION,\n        'X-Stainless-OS': 'Unknown',\n        'X-Stainless-Arch': 'unknown',\n        'X-Stainless-Runtime': 'unknown',\n        'X-Stainless-Runtime-Version': 'unknown',\n    };\n};\n// Note: modified from https://github.com/JS-DevTools/host-environment/blob/b1ab79ecde37db5d6e163c050e54fe7d287d7c92/src/isomorphic.browser.ts\nfunction getBrowserInfo() {\n    if (typeof navigator === 'undefined' || !navigator) {\n        return null;\n    }\n    // NOTE: The order matters here!\n    const browserPatterns = [\n        { key: 'edge', pattern: /Edge(?:\\W+(\\d+)\\.(\\d+)(?:\\.(\\d+))?)?/ },\n        { key: 'ie', pattern: /MSIE(?:\\W+(\\d+)\\.(\\d+)(?:\\.(\\d+))?)?/ },\n        { key: 'ie', pattern: /Trident(?:.*rv\\:(\\d+)\\.(\\d+)(?:\\.(\\d+))?)?/ },\n        { key: 'chrome', pattern: /Chrome(?:\\W+(\\d+)\\.(\\d+)(?:\\.(\\d+))?)?/ },\n        { key: 'firefox', pattern: /Firefox(?:\\W+(\\d+)\\.(\\d+)(?:\\.(\\d+))?)?/ },\n        { key: 'safari', pattern: /(?:Version\\W+(\\d+)\\.(\\d+)(?:\\.(\\d+))?)?(?:\\W+Mobile\\S*)?\\W+Safari/ },\n    ];\n    // Find the FIRST matching browser\n    for (const { key, pattern } of browserPatterns) {\n        const match = pattern.exec(navigator.userAgent);\n        if (match) {\n            const major = match[1] || 0;\n            const minor = match[2] || 0;\n            const patch = match[3] || 0;\n            return { browser: key, version: `${major}.${minor}.${patch}` };\n        }\n    }\n    return null;\n}\nconst normalizeArch = (arch) => {\n    // Node docs:\n    // - https://nodejs.org/api/process.html#processarch\n    // Deno docs:\n    // - https://doc.deno.land/deno/stable/~/Deno.build\n    if (arch === 'x32')\n        return 'x32';\n    if (arch === 'x86_64' || arch === 'x64')\n        return 'x64';\n    if (arch === 'arm')\n        return 'arm';\n    if (arch === 'aarch64' || arch === 'arm64')\n        return 'arm64';\n    if (arch)\n        return `other:${arch}`;\n    return 'unknown';\n};\nconst normalizePlatform = (platform) => {\n    // Node platforms:\n    // - https://nodejs.org/api/process.html#processplatform\n    // Deno platforms:\n    // - https://doc.deno.land/deno/stable/~/Deno.build\n    // - https://github.com/denoland/deno/issues/14799\n    platform = platform.toLowerCase();\n    // NOTE: this iOS check is untested and may not work\n    // Node does not work natively on IOS, there is a fork at\n    // https://github.com/nodejs-mobile/nodejs-mobile\n    // however it is unknown at the time of writing how to detect if it is running\n    if (platform.includes('ios'))\n        return 'iOS';\n    if (platform === 'android')\n        return 'Android';\n    if (platform === 'darwin')\n        return 'MacOS';\n    if (platform === 'win32')\n        return 'Windows';\n    if (platform === 'freebsd')\n        return 'FreeBSD';\n    if (platform === 'openbsd')\n        return 'OpenBSD';\n    if (platform === 'linux')\n        return 'Linux';\n    if (platform)\n        return `Other:${platform}`;\n    return 'Unknown';\n};\nlet _platformHeaders;\nconst getPlatformHeaders = () => {\n    return (_platformHeaders ?? (_platformHeaders = getPlatformProperties()));\n};\nexport const safeJSON = (text) => {\n    try {\n        return JSON.parse(text);\n    }\n    catch (err) {\n        return undefined;\n    }\n};\n// https://url.spec.whatwg.org/#url-scheme-string\nconst startsWithSchemeRegexp = /^[a-z][a-z0-9+.-]*:/i;\nconst isAbsoluteURL = (url) => {\n    return startsWithSchemeRegexp.test(url);\n};\nexport const sleep = (ms) => new Promise((resolve) => setTimeout(resolve, ms));\nconst validatePositiveInteger = (name, n) => {\n    if (typeof n !== 'number' || !Number.isInteger(n)) {\n        throw new OpenAIError(`${name} must be an integer`);\n    }\n    if (n < 0) {\n        throw new OpenAIError(`${name} must be a positive integer`);\n    }\n    return n;\n};\nexport const castToError = (err) => {\n    if (err instanceof Error)\n        return err;\n    if (typeof err === 'object' && err !== null) {\n        try {\n            return new Error(JSON.stringify(err));\n        }\n        catch { }\n    }\n    return new Error(err);\n};\nexport const ensurePresent = (value) => {\n    if (value == null)\n        throw new OpenAIError(`Expected a value to be given but received ${value} instead.`);\n    return value;\n};\n/**\n * Read an environment variable.\n *\n * Trims beginning and trailing whitespace.\n *\n * Will return undefined if the environment variable doesn't exist or cannot be accessed.\n */\nexport const readEnv = (env) => {\n    if (typeof process !== 'undefined') {\n        return process.env?.[env]?.trim() ?? undefined;\n    }\n    if (typeof Deno !== 'undefined') {\n        return Deno.env?.get?.(env)?.trim();\n    }\n    return undefined;\n};\nexport const coerceInteger = (value) => {\n    if (typeof value === 'number')\n        return Math.round(value);\n    if (typeof value === 'string')\n        return parseInt(value, 10);\n    throw new OpenAIError(`Could not coerce ${value} (type: ${typeof value}) into a number`);\n};\nexport const coerceFloat = (value) => {\n    if (typeof value === 'number')\n        return value;\n    if (typeof value === 'string')\n        return parseFloat(value);\n    throw new OpenAIError(`Could not coerce ${value} (type: ${typeof value}) into a number`);\n};\nexport const coerceBoolean = (value) => {\n    if (typeof value === 'boolean')\n        return value;\n    if (typeof value === 'string')\n        return value === 'true';\n    return Boolean(value);\n};\nexport const maybeCoerceInteger = (value) => {\n    if (value === undefined) {\n        return undefined;\n    }\n    return coerceInteger(value);\n};\nexport const maybeCoerceFloat = (value) => {\n    if (value === undefined) {\n        return undefined;\n    }\n    return coerceFloat(value);\n};\nexport const maybeCoerceBoolean = (value) => {\n    if (value === undefined) {\n        return undefined;\n    }\n    return coerceBoolean(value);\n};\n// https://stackoverflow.com/a/34491287\nexport function isEmptyObj(obj) {\n    if (!obj)\n        return true;\n    for (const _k in obj)\n        return false;\n    return true;\n}\n// https://eslint.org/docs/latest/rules/no-prototype-builtins\nexport function hasOwn(obj, key) {\n    return Object.prototype.hasOwnProperty.call(obj, key);\n}\n/**\n * Copies headers from \"newHeaders\" onto \"targetHeaders\",\n * using lower-case for all properties,\n * ignoring any keys with undefined values,\n * and deleting any keys with null values.\n */\nfunction applyHeadersMut(targetHeaders, newHeaders) {\n    for (const k in newHeaders) {\n        if (!hasOwn(newHeaders, k))\n            continue;\n        const lowerKey = k.toLowerCase();\n        if (!lowerKey)\n            continue;\n        const val = newHeaders[k];\n        if (val === null) {\n            delete targetHeaders[lowerKey];\n        }\n        else if (val !== undefined) {\n            targetHeaders[lowerKey] = val;\n        }\n    }\n}\nconst SENSITIVE_HEADERS = new Set(['authorization', 'api-key']);\nexport function debug(action, ...args) {\n    if (typeof process !== 'undefined' && process?.env?.['DEBUG'] === 'true') {\n        const modifiedArgs = args.map((arg) => {\n            if (!arg) {\n                return arg;\n            }\n            // Check for sensitive headers in request body 'headers' object\n            if (arg['headers']) {\n                // clone so we don't mutate\n                const modifiedArg = { ...arg, headers: { ...arg['headers'] } };\n                for (const header in arg['headers']) {\n                    if (SENSITIVE_HEADERS.has(header.toLowerCase())) {\n                        modifiedArg['headers'][header] = 'REDACTED';\n                    }\n                }\n                return modifiedArg;\n            }\n            let modifiedArg = null;\n            // Check for sensitive headers in headers object\n            for (const header in arg) {\n                if (SENSITIVE_HEADERS.has(header.toLowerCase())) {\n                    // avoid making a copy until we need to\n                    modifiedArg ?? (modifiedArg = { ...arg });\n                    modifiedArg[header] = 'REDACTED';\n                }\n            }\n            return modifiedArg ?? arg;\n        });\n        console.log(`OpenAI:DEBUG:${action}`, ...modifiedArgs);\n    }\n}\n/**\n * https://stackoverflow.com/a/2117523\n */\nconst uuid4 = () => {\n    return 'xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx'.replace(/[xy]/g, (c) => {\n        const r = (Math.random() * 16) | 0;\n        const v = c === 'x' ? r : (r & 0x3) | 0x8;\n        return v.toString(16);\n    });\n};\nexport const isRunningInBrowser = () => {\n    return (\n    // @ts-ignore\n    typeof window !== 'undefined' &&\n        // @ts-ignore\n        typeof window.document !== 'undefined' &&\n        // @ts-ignore\n        typeof navigator !== 'undefined');\n};\nexport const isHeadersProtocol = (headers) => {\n    return typeof headers?.get === 'function';\n};\nexport const getRequiredHeader = (headers, header) => {\n    const foundHeader = getHeader(headers, header);\n    if (foundHeader === undefined) {\n        throw new Error(`Could not find ${header} header`);\n    }\n    return foundHeader;\n};\nexport const getHeader = (headers, header) => {\n    const lowerCasedHeader = header.toLowerCase();\n    if (isHeadersProtocol(headers)) {\n        // to deal with the case where the header looks like Stainless-Event-Id\n        const intercapsHeader = header[0]?.toUpperCase() +\n            header.substring(1).replace(/([^\\w])(\\w)/g, (_m, g1, g2) => g1 + g2.toUpperCase());\n        for (const key of [header, lowerCasedHeader, header.toUpperCase(), intercapsHeader]) {\n            const value = headers.get(key);\n            if (value) {\n                return value;\n            }\n        }\n    }\n    for (const [key, value] of Object.entries(headers)) {\n        if (key.toLowerCase() === lowerCasedHeader) {\n            if (Array.isArray(value)) {\n                if (value.length <= 1)\n                    return value[0];\n                console.warn(`Received ${value.length} entries for the ${header} header, using the first entry.`);\n                return value[0];\n            }\n            return value;\n        }\n    }\n    return undefined;\n};\n/**\n * Encodes a string to Base64 format.\n */\nexport const toBase64 = (str) => {\n    if (!str)\n        return '';\n    if (typeof Buffer !== 'undefined') {\n        return Buffer.from(str).toString('base64');\n    }\n    if (typeof btoa !== 'undefined') {\n        return btoa(str);\n    }\n    throw new OpenAIError('Cannot generate b64 string; Expected `Buffer` or `btoa` to be defined');\n};\nexport function isObj(obj) {\n    return obj != null && typeof obj === 'object' && !Array.isArray(obj);\n}\n//# sourceMappingURL=core.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { AbstractPage } from \"./core.mjs\";\n/**\n * Note: no pagination actually occurs yet, this is for forwards-compatibility.\n */\nexport class Page extends AbstractPage {\n    constructor(client, response, body, options) {\n        super(client, response, body, options);\n        this.data = body.data || [];\n        this.object = body.object;\n    }\n    getPaginatedItems() {\n        return this.data ?? [];\n    }\n    // @deprecated Please use `nextPageInfo()` instead\n    /**\n     * This page represents a response that isn't actually paginated at the API level\n     * so there will never be any next page params.\n     */\n    nextPageParams() {\n        return null;\n    }\n    nextPageInfo() {\n        return null;\n    }\n}\nexport class CursorPage extends AbstractPage {\n    constructor(client, response, body, options) {\n        super(client, response, body, options);\n        this.data = body.data || [];\n        this.has_more = body.has_more || false;\n    }\n    getPaginatedItems() {\n        return this.data ?? [];\n    }\n    hasNextPage() {\n        if (this.has_more === false) {\n            return false;\n        }\n        return super.hasNextPage();\n    }\n    // @deprecated Please use `nextPageInfo()` instead\n    nextPageParams() {\n        const info = this.nextPageInfo();\n        if (!info)\n            return null;\n        if ('params' in info)\n            return info.params;\n        const params = Object.fromEntries(info.url.searchParams);\n        if (!Object.keys(params).length)\n            return null;\n        return params;\n    }\n    nextPageInfo() {\n        const data = this.getPaginatedItems();\n        if (!data.length) {\n            return null;\n        }\n        const id = data[data.length - 1]?.id;\n        if (!id) {\n            return null;\n        }\n        return { params: { after: id } };\n    }\n}\n//# sourceMappingURL=pagination.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nexport class APIResource {\n    constructor(client) {\n        this._client = client;\n    }\n}\n//# sourceMappingURL=resource.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../../resource.mjs\";\nimport { isRequestOptions } from \"../../../core.mjs\";\nimport { ChatCompletionStoreMessagesPage } from \"./completions.mjs\";\nexport class Messages extends APIResource {\n    list(completionId, query = {}, options) {\n        if (isRequestOptions(query)) {\n            return this.list(completionId, {}, query);\n        }\n        return this._client.getAPIList(`/chat/completions/${completionId}/messages`, ChatCompletionStoreMessagesPage, { query, ...options });\n    }\n}\nexport { ChatCompletionStoreMessagesPage };\n//# sourceMappingURL=messages.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../../resource.mjs\";\nimport { isRequestOptions } from \"../../../core.mjs\";\nimport * as MessagesAPI from \"./messages.mjs\";\nimport { Messages } from \"./messages.mjs\";\nimport { CursorPage } from \"../../../pagination.mjs\";\nexport class Completions extends APIResource {\n    constructor() {\n        super(...arguments);\n        this.messages = new MessagesAPI.Messages(this._client);\n    }\n    create(body, options) {\n        return this._client.post('/chat/completions', { body, ...options, stream: body.stream ?? false });\n    }\n    /**\n     * Get a stored chat completion. Only chat completions that have been created with\n     * the `store` parameter set to `true` will be returned.\n     */\n    retrieve(completionId, options) {\n        return this._client.get(`/chat/completions/${completionId}`, options);\n    }\n    /**\n     * Modify a stored chat completion. Only chat completions that have been created\n     * with the `store` parameter set to `true` can be modified. Currently, the only\n     * supported modification is to update the `metadata` field.\n     */\n    update(completionId, body, options) {\n        return this._client.post(`/chat/completions/${completionId}`, { body, ...options });\n    }\n    list(query = {}, options) {\n        if (isRequestOptions(query)) {\n            return this.list({}, query);\n        }\n        return this._client.getAPIList('/chat/completions', ChatCompletionsPage, { query, ...options });\n    }\n    /**\n     * Delete a stored chat completion. Only chat completions that have been created\n     * with the `store` parameter set to `true` can be deleted.\n     */\n    del(completionId, options) {\n        return this._client.delete(`/chat/completions/${completionId}`, options);\n    }\n}\nexport class ChatCompletionsPage extends CursorPage {\n}\nexport class ChatCompletionStoreMessagesPage extends CursorPage {\n}\nCompletions.ChatCompletionsPage = ChatCompletionsPage;\nCompletions.Messages = Messages;\n//# sourceMappingURL=completions.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../resource.mjs\";\nimport * as CompletionsAPI from \"./completions/completions.mjs\";\nimport { ChatCompletionsPage, Completions, } from \"./completions/completions.mjs\";\nexport class Chat extends APIResource {\n    constructor() {\n        super(...arguments);\n        this.completions = new CompletionsAPI.Completions(this._client);\n    }\n}\nChat.Completions = Completions;\nChat.ChatCompletionsPage = ChatCompletionsPage;\n//# sourceMappingURL=chat.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../resource.mjs\";\nexport class Speech extends APIResource {\n    /**\n     * Generates audio from the input text.\n     */\n    create(body, options) {\n        return this._client.post('/audio/speech', {\n            body,\n            ...options,\n            headers: { Accept: 'application/octet-stream', ...options?.headers },\n            __binaryResponse: true,\n        });\n    }\n}\n//# sourceMappingURL=speech.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../resource.mjs\";\nimport * as Core from \"../../core.mjs\";\nexport class Transcriptions extends APIResource {\n    create(body, options) {\n        return this._client.post('/audio/transcriptions', Core.multipartFormRequestOptions({ body, ...options, __metadata: { model: body.model } }));\n    }\n}\n//# sourceMappingURL=transcriptions.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../resource.mjs\";\nimport * as Core from \"../../core.mjs\";\nexport class Translations extends APIResource {\n    create(body, options) {\n        return this._client.post('/audio/translations', Core.multipartFormRequestOptions({ body, ...options, __metadata: { model: body.model } }));\n    }\n}\n//# sourceMappingURL=translations.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../resource.mjs\";\nimport * as SpeechAPI from \"./speech.mjs\";\nimport { Speech } from \"./speech.mjs\";\nimport * as TranscriptionsAPI from \"./transcriptions.mjs\";\nimport { Transcriptions, } from \"./transcriptions.mjs\";\nimport * as TranslationsAPI from \"./translations.mjs\";\nimport { Translations, } from \"./translations.mjs\";\nexport class Audio extends APIResource {\n    constructor() {\n        super(...arguments);\n        this.transcriptions = new TranscriptionsAPI.Transcriptions(this._client);\n        this.translations = new TranslationsAPI.Translations(this._client);\n        this.speech = new SpeechAPI.Speech(this._client);\n    }\n}\nAudio.Transcriptions = Transcriptions;\nAudio.Translations = Translations;\nAudio.Speech = Speech;\n//# sourceMappingURL=audio.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../resource.mjs\";\nimport { isRequestOptions } from \"../core.mjs\";\nimport { CursorPage } from \"../pagination.mjs\";\nexport class Batches extends APIResource {\n    /**\n     * Creates and executes a batch from an uploaded file of requests\n     */\n    create(body, options) {\n        return this._client.post('/batches', { body, ...options });\n    }\n    /**\n     * Retrieves a batch.\n     */\n    retrieve(batchId, options) {\n        return this._client.get(`/batches/${batchId}`, options);\n    }\n    list(query = {}, options) {\n        if (isRequestOptions(query)) {\n            return this.list({}, query);\n        }\n        return this._client.getAPIList('/batches', BatchesPage, { query, ...options });\n    }\n    /**\n     * Cancels an in-progress batch. The batch will be in status `cancelling` for up to\n     * 10 minutes, before changing to `cancelled`, where it will have partial results\n     * (if any) available in the output file.\n     */\n    cancel(batchId, options) {\n        return this._client.post(`/batches/${batchId}/cancel`, options);\n    }\n}\nexport class BatchesPage extends CursorPage {\n}\nBatches.BatchesPage = BatchesPage;\n//# sourceMappingURL=batches.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../resource.mjs\";\nimport { isRequestOptions } from \"../../core.mjs\";\nimport { CursorPage } from \"../../pagination.mjs\";\nexport class Assistants extends APIResource {\n    /**\n     * Create an assistant with a model and instructions.\n     */\n    create(body, options) {\n        return this._client.post('/assistants', {\n            body,\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    /**\n     * Retrieves an assistant.\n     */\n    retrieve(assistantId, options) {\n        return this._client.get(`/assistants/${assistantId}`, {\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    /**\n     * Modifies an assistant.\n     */\n    update(assistantId, body, options) {\n        return this._client.post(`/assistants/${assistantId}`, {\n            body,\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    list(query = {}, options) {\n        if (isRequestOptions(query)) {\n            return this.list({}, query);\n        }\n        return this._client.getAPIList('/assistants', AssistantsPage, {\n            query,\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    /**\n     * Delete an assistant.\n     */\n    del(assistantId, options) {\n        return this._client.delete(`/assistants/${assistantId}`, {\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n}\nexport class AssistantsPage extends CursorPage {\n}\nAssistants.AssistantsPage = AssistantsPage;\n//# sourceMappingURL=assistants.mjs.map","export function isRunnableFunctionWithParse(fn) {\n    return typeof fn.parse === 'function';\n}\n/**\n * This is helper class for passing a `function` and `parse` where the `function`\n * argument type matches the `parse` return type.\n *\n * @deprecated - please use ParsingToolFunction instead.\n */\nexport class ParsingFunction {\n    constructor(input) {\n        this.function = input.function;\n        this.parse = input.parse;\n        this.parameters = input.parameters;\n        this.description = input.description;\n        this.name = input.name;\n    }\n}\n/**\n * This is helper class for passing a `function` and `parse` where the `function`\n * argument type matches the `parse` return type.\n */\nexport class ParsingToolFunction {\n    constructor(input) {\n        this.type = 'function';\n        this.function = input;\n    }\n}\n//# sourceMappingURL=RunnableFunction.mjs.map","export const isAssistantMessage = (message) => {\n    return message?.role === 'assistant';\n};\nexport const isFunctionMessage = (message) => {\n    return message?.role === 'function';\n};\nexport const isToolMessage = (message) => {\n    return message?.role === 'tool';\n};\nexport function isPresent(obj) {\n    return obj != null;\n}\n//# sourceMappingURL=chatCompletionUtils.mjs.map","var __classPrivateFieldSet = (this && this.__classPrivateFieldSet) || function (receiver, state, value, kind, f) {\n    if (kind === \"m\") throw new TypeError(\"Private method is not writable\");\n    if (kind === \"a\" && !f) throw new TypeError(\"Private accessor was defined without a setter\");\n    if (typeof state === \"function\" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError(\"Cannot write private member to an object whose class did not declare it\");\n    return (kind === \"a\" ? f.call(receiver, value) : f ? f.value = value : state.set(receiver, value)), value;\n};\nvar __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {\n    if (kind === \"a\" && !f) throw new TypeError(\"Private accessor was defined without a getter\");\n    if (typeof state === \"function\" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError(\"Cannot read private member from an object whose class did not declare it\");\n    return kind === \"m\" ? f : kind === \"a\" ? f.call(receiver) : f ? f.value : state.get(receiver);\n};\nvar _EventStream_instances, _EventStream_connectedPromise, _EventStream_resolveConnectedPromise, _EventStream_rejectConnectedPromise, _EventStream_endPromise, _EventStream_resolveEndPromise, _EventStream_rejectEndPromise, _EventStream_listeners, _EventStream_ended, _EventStream_errored, _EventStream_aborted, _EventStream_catchingPromiseCreated, _EventStream_handleError;\nimport { APIUserAbortError, OpenAIError } from \"../error.mjs\";\nexport class EventStream {\n    constructor() {\n        _EventStream_instances.add(this);\n        this.controller = new AbortController();\n        _EventStream_connectedPromise.set(this, void 0);\n        _EventStream_resolveConnectedPromise.set(this, () => { });\n        _EventStream_rejectConnectedPromise.set(this, () => { });\n        _EventStream_endPromise.set(this, void 0);\n        _EventStream_resolveEndPromise.set(this, () => { });\n        _EventStream_rejectEndPromise.set(this, () => { });\n        _EventStream_listeners.set(this, {});\n        _EventStream_ended.set(this, false);\n        _EventStream_errored.set(this, false);\n        _EventStream_aborted.set(this, false);\n        _EventStream_catchingPromiseCreated.set(this, false);\n        __classPrivateFieldSet(this, _EventStream_connectedPromise, new Promise((resolve, reject) => {\n            __classPrivateFieldSet(this, _EventStream_resolveConnectedPromise, resolve, \"f\");\n            __classPrivateFieldSet(this, _EventStream_rejectConnectedPromise, reject, \"f\");\n        }), \"f\");\n        __classPrivateFieldSet(this, _EventStream_endPromise, new Promise((resolve, reject) => {\n            __classPrivateFieldSet(this, _EventStream_resolveEndPromise, resolve, \"f\");\n            __classPrivateFieldSet(this, _EventStream_rejectEndPromise, reject, \"f\");\n        }), \"f\");\n        // Don't let these promises cause unhandled rejection errors.\n        // we will manually cause an unhandled rejection error later\n        // if the user hasn't registered any error listener or called\n        // any promise-returning method.\n        __classPrivateFieldGet(this, _EventStream_connectedPromise, \"f\").catch(() => { });\n        __classPrivateFieldGet(this, _EventStream_endPromise, \"f\").catch(() => { });\n    }\n    _run(executor) {\n        // Unfortunately if we call `executor()` immediately we get runtime errors about\n        // references to `this` before the `super()` constructor call returns.\n        setTimeout(() => {\n            executor().then(() => {\n                this._emitFinal();\n                this._emit('end');\n            }, __classPrivateFieldGet(this, _EventStream_instances, \"m\", _EventStream_handleError).bind(this));\n        }, 0);\n    }\n    _connected() {\n        if (this.ended)\n            return;\n        __classPrivateFieldGet(this, _EventStream_resolveConnectedPromise, \"f\").call(this);\n        this._emit('connect');\n    }\n    get ended() {\n        return __classPrivateFieldGet(this, _EventStream_ended, \"f\");\n    }\n    get errored() {\n        return __classPrivateFieldGet(this, _EventStream_errored, \"f\");\n    }\n    get aborted() {\n        return __classPrivateFieldGet(this, _EventStream_aborted, \"f\");\n    }\n    abort() {\n        this.controller.abort();\n    }\n    /**\n     * Adds the listener function to the end of the listeners array for the event.\n     * No checks are made to see if the listener has already been added. Multiple calls passing\n     * the same combination of event and listener will result in the listener being added, and\n     * called, multiple times.\n     * @returns this ChatCompletionStream, so that calls can be chained\n     */\n    on(event, listener) {\n        const listeners = __classPrivateFieldGet(this, _EventStream_listeners, \"f\")[event] || (__classPrivateFieldGet(this, _EventStream_listeners, \"f\")[event] = []);\n        listeners.push({ listener });\n        return this;\n    }\n    /**\n     * Removes the specified listener from the listener array for the event.\n     * off() will remove, at most, one instance of a listener from the listener array. If any single\n     * listener has been added multiple times to the listener array for the specified event, then\n     * off() must be called multiple times to remove each instance.\n     * @returns this ChatCompletionStream, so that calls can be chained\n     */\n    off(event, listener) {\n        const listeners = __classPrivateFieldGet(this, _EventStream_listeners, \"f\")[event];\n        if (!listeners)\n            return this;\n        const index = listeners.findIndex((l) => l.listener === listener);\n        if (index >= 0)\n            listeners.splice(index, 1);\n        return this;\n    }\n    /**\n     * Adds a one-time listener function for the event. The next time the event is triggered,\n     * this listener is removed and then invoked.\n     * @returns this ChatCompletionStream, so that calls can be chained\n     */\n    once(event, listener) {\n        const listeners = __classPrivateFieldGet(this, _EventStream_listeners, \"f\")[event] || (__classPrivateFieldGet(this, _EventStream_listeners, \"f\")[event] = []);\n        listeners.push({ listener, once: true });\n        return this;\n    }\n    /**\n     * This is similar to `.once()`, but returns a Promise that resolves the next time\n     * the event is triggered, instead of calling a listener callback.\n     * @returns a Promise that resolves the next time given event is triggered,\n     * or rejects if an error is emitted.  (If you request the 'error' event,\n     * returns a promise that resolves with the error).\n     *\n     * Example:\n     *\n     *   const message = await stream.emitted('message') // rejects if the stream errors\n     */\n    emitted(event) {\n        return new Promise((resolve, reject) => {\n            __classPrivateFieldSet(this, _EventStream_catchingPromiseCreated, true, \"f\");\n            if (event !== 'error')\n                this.once('error', reject);\n            this.once(event, resolve);\n        });\n    }\n    async done() {\n        __classPrivateFieldSet(this, _EventStream_catchingPromiseCreated, true, \"f\");\n        await __classPrivateFieldGet(this, _EventStream_endPromise, \"f\");\n    }\n    _emit(event, ...args) {\n        // make sure we don't emit any events after end\n        if (__classPrivateFieldGet(this, _EventStream_ended, \"f\")) {\n            return;\n        }\n        if (event === 'end') {\n            __classPrivateFieldSet(this, _EventStream_ended, true, \"f\");\n            __classPrivateFieldGet(this, _EventStream_resolveEndPromise, \"f\").call(this);\n        }\n        const listeners = __classPrivateFieldGet(this, _EventStream_listeners, \"f\")[event];\n        if (listeners) {\n            __classPrivateFieldGet(this, _EventStream_listeners, \"f\")[event] = listeners.filter((l) => !l.once);\n            listeners.forEach(({ listener }) => listener(...args));\n        }\n        if (event === 'abort') {\n            const error = args[0];\n            if (!__classPrivateFieldGet(this, _EventStream_catchingPromiseCreated, \"f\") && !listeners?.length) {\n                Promise.reject(error);\n            }\n            __classPrivateFieldGet(this, _EventStream_rejectConnectedPromise, \"f\").call(this, error);\n            __classPrivateFieldGet(this, _EventStream_rejectEndPromise, \"f\").call(this, error);\n            this._emit('end');\n            return;\n        }\n        if (event === 'error') {\n            // NOTE: _emit('error', error) should only be called from #handleError().\n            const error = args[0];\n            if (!__classPrivateFieldGet(this, _EventStream_catchingPromiseCreated, \"f\") && !listeners?.length) {\n                // Trigger an unhandled rejection if the user hasn't registered any error handlers.\n                // If you are seeing stack traces here, make sure to handle errors via either:\n                // - runner.on('error', () => ...)\n                // - await runner.done()\n                // - await runner.finalChatCompletion()\n                // - etc.\n                Promise.reject(error);\n            }\n            __classPrivateFieldGet(this, _EventStream_rejectConnectedPromise, \"f\").call(this, error);\n            __classPrivateFieldGet(this, _EventStream_rejectEndPromise, \"f\").call(this, error);\n            this._emit('end');\n        }\n    }\n    _emitFinal() { }\n}\n_EventStream_connectedPromise = new WeakMap(), _EventStream_resolveConnectedPromise = new WeakMap(), _EventStream_rejectConnectedPromise = new WeakMap(), _EventStream_endPromise = new WeakMap(), _EventStream_resolveEndPromise = new WeakMap(), _EventStream_rejectEndPromise = new WeakMap(), _EventStream_listeners = new WeakMap(), _EventStream_ended = new WeakMap(), _EventStream_errored = new WeakMap(), _EventStream_aborted = new WeakMap(), _EventStream_catchingPromiseCreated = new WeakMap(), _EventStream_instances = new WeakSet(), _EventStream_handleError = function _EventStream_handleError(error) {\n    __classPrivateFieldSet(this, _EventStream_errored, true, \"f\");\n    if (error instanceof Error && error.name === 'AbortError') {\n        error = new APIUserAbortError();\n    }\n    if (error instanceof APIUserAbortError) {\n        __classPrivateFieldSet(this, _EventStream_aborted, true, \"f\");\n        return this._emit('abort', error);\n    }\n    if (error instanceof OpenAIError) {\n        return this._emit('error', error);\n    }\n    if (error instanceof Error) {\n        const openAIError = new OpenAIError(error.message);\n        // @ts-ignore\n        openAIError.cause = error;\n        return this._emit('error', openAIError);\n    }\n    return this._emit('error', new OpenAIError(String(error)));\n};\n//# sourceMappingURL=EventStream.mjs.map","import { ContentFilterFinishReasonError, LengthFinishReasonError, OpenAIError } from \"../error.mjs\";\nexport function makeParseableResponseFormat(response_format, parser) {\n    const obj = { ...response_format };\n    Object.defineProperties(obj, {\n        $brand: {\n            value: 'auto-parseable-response-format',\n            enumerable: false,\n        },\n        $parseRaw: {\n            value: parser,\n            enumerable: false,\n        },\n    });\n    return obj;\n}\nexport function isAutoParsableResponseFormat(response_format) {\n    return response_format?.['$brand'] === 'auto-parseable-response-format';\n}\nexport function makeParseableTool(tool, { parser, callback, }) {\n    const obj = { ...tool };\n    Object.defineProperties(obj, {\n        $brand: {\n            value: 'auto-parseable-tool',\n            enumerable: false,\n        },\n        $parseRaw: {\n            value: parser,\n            enumerable: false,\n        },\n        $callback: {\n            value: callback,\n            enumerable: false,\n        },\n    });\n    return obj;\n}\nexport function isAutoParsableTool(tool) {\n    return tool?.['$brand'] === 'auto-parseable-tool';\n}\nexport function maybeParseChatCompletion(completion, params) {\n    if (!params || !hasAutoParseableInput(params)) {\n        return {\n            ...completion,\n            choices: completion.choices.map((choice) => ({\n                ...choice,\n                message: {\n                    ...choice.message,\n                    parsed: null,\n                    ...(choice.message.tool_calls ?\n                        {\n                            tool_calls: choice.message.tool_calls,\n                        }\n                        : undefined),\n                },\n            })),\n        };\n    }\n    return parseChatCompletion(completion, params);\n}\nexport function parseChatCompletion(completion, params) {\n    const choices = completion.choices.map((choice) => {\n        if (choice.finish_reason === 'length') {\n            throw new LengthFinishReasonError();\n        }\n        if (choice.finish_reason === 'content_filter') {\n            throw new ContentFilterFinishReasonError();\n        }\n        return {\n            ...choice,\n            message: {\n                ...choice.message,\n                ...(choice.message.tool_calls ?\n                    {\n                        tool_calls: choice.message.tool_calls?.map((toolCall) => parseToolCall(params, toolCall)) ?? undefined,\n                    }\n                    : undefined),\n                parsed: choice.message.content && !choice.message.refusal ?\n                    parseResponseFormat(params, choice.message.content)\n                    : null,\n            },\n        };\n    });\n    return { ...completion, choices };\n}\nfunction parseResponseFormat(params, content) {\n    if (params.response_format?.type !== 'json_schema') {\n        return null;\n    }\n    if (params.response_format?.type === 'json_schema') {\n        if ('$parseRaw' in params.response_format) {\n            const response_format = params.response_format;\n            return response_format.$parseRaw(content);\n        }\n        return JSON.parse(content);\n    }\n    return null;\n}\nfunction parseToolCall(params, toolCall) {\n    const inputTool = params.tools?.find((inputTool) => inputTool.function?.name === toolCall.function.name);\n    return {\n        ...toolCall,\n        function: {\n            ...toolCall.function,\n            parsed_arguments: isAutoParsableTool(inputTool) ? inputTool.$parseRaw(toolCall.function.arguments)\n                : inputTool?.function.strict ? JSON.parse(toolCall.function.arguments)\n                    : null,\n        },\n    };\n}\nexport function shouldParseToolCall(params, toolCall) {\n    if (!params) {\n        return false;\n    }\n    const inputTool = params.tools?.find((inputTool) => inputTool.function?.name === toolCall.function.name);\n    return isAutoParsableTool(inputTool) || inputTool?.function.strict || false;\n}\nexport function hasAutoParseableInput(params) {\n    if (isAutoParsableResponseFormat(params.response_format)) {\n        return true;\n    }\n    return (params.tools?.some((t) => isAutoParsableTool(t) || (t.type === 'function' && t.function.strict === true)) ?? false);\n}\nexport function validateInputTools(tools) {\n    for (const tool of tools ?? []) {\n        if (tool.type !== 'function') {\n            throw new OpenAIError(`Currently only \\`function\\` tool types support auto-parsing; Received \\`${tool.type}\\``);\n        }\n        if (tool.function.strict !== true) {\n            throw new OpenAIError(`The \\`${tool.function.name}\\` tool is not marked with \\`strict: true\\`. Only strict function tools can be auto-parsed`);\n        }\n    }\n}\n//# sourceMappingURL=parser.mjs.map","var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {\n    if (kind === \"a\" && !f) throw new TypeError(\"Private accessor was defined without a getter\");\n    if (typeof state === \"function\" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError(\"Cannot read private member from an object whose class did not declare it\");\n    return kind === \"m\" ? f : kind === \"a\" ? f.call(receiver) : f ? f.value : state.get(receiver);\n};\nvar _AbstractChatCompletionRunner_instances, _AbstractChatCompletionRunner_getFinalContent, _AbstractChatCompletionRunner_getFinalMessage, _AbstractChatCompletionRunner_getFinalFunctionCall, _AbstractChatCompletionRunner_getFinalFunctionCallResult, _AbstractChatCompletionRunner_calculateTotalUsage, _AbstractChatCompletionRunner_validateParams, _AbstractChatCompletionRunner_stringifyFunctionCallResult;\nimport { OpenAIError } from \"../error.mjs\";\nimport { isRunnableFunctionWithParse, } from \"./RunnableFunction.mjs\";\nimport { isAssistantMessage, isFunctionMessage, isToolMessage } from \"./chatCompletionUtils.mjs\";\nimport { EventStream } from \"./EventStream.mjs\";\nimport { isAutoParsableTool, parseChatCompletion } from \"../lib/parser.mjs\";\nconst DEFAULT_MAX_CHAT_COMPLETIONS = 10;\nexport class AbstractChatCompletionRunner extends EventStream {\n    constructor() {\n        super(...arguments);\n        _AbstractChatCompletionRunner_instances.add(this);\n        this._chatCompletions = [];\n        this.messages = [];\n    }\n    _addChatCompletion(chatCompletion) {\n        this._chatCompletions.push(chatCompletion);\n        this._emit('chatCompletion', chatCompletion);\n        const message = chatCompletion.choices[0]?.message;\n        if (message)\n            this._addMessage(message);\n        return chatCompletion;\n    }\n    _addMessage(message, emit = true) {\n        if (!('content' in message))\n            message.content = null;\n        this.messages.push(message);\n        if (emit) {\n            this._emit('message', message);\n            if ((isFunctionMessage(message) || isToolMessage(message)) && message.content) {\n                // Note, this assumes that {role: 'tool', content: …} is always the result of a call of tool of type=function.\n                this._emit('functionCallResult', message.content);\n            }\n            else if (isAssistantMessage(message) && message.function_call) {\n                this._emit('functionCall', message.function_call);\n            }\n            else if (isAssistantMessage(message) && message.tool_calls) {\n                for (const tool_call of message.tool_calls) {\n                    if (tool_call.type === 'function') {\n                        this._emit('functionCall', tool_call.function);\n                    }\n                }\n            }\n        }\n    }\n    /**\n     * @returns a promise that resolves with the final ChatCompletion, or rejects\n     * if an error occurred or the stream ended prematurely without producing a ChatCompletion.\n     */\n    async finalChatCompletion() {\n        await this.done();\n        const completion = this._chatCompletions[this._chatCompletions.length - 1];\n        if (!completion)\n            throw new OpenAIError('stream ended without producing a ChatCompletion');\n        return completion;\n    }\n    /**\n     * @returns a promise that resolves with the content of the final ChatCompletionMessage, or rejects\n     * if an error occurred or the stream ended prematurely without producing a ChatCompletionMessage.\n     */\n    async finalContent() {\n        await this.done();\n        return __classPrivateFieldGet(this, _AbstractChatCompletionRunner_instances, \"m\", _AbstractChatCompletionRunner_getFinalContent).call(this);\n    }\n    /**\n     * @returns a promise that resolves with the the final assistant ChatCompletionMessage response,\n     * or rejects if an error occurred or the stream ended prematurely without producing a ChatCompletionMessage.\n     */\n    async finalMessage() {\n        await this.done();\n        return __classPrivateFieldGet(this, _AbstractChatCompletionRunner_instances, \"m\", _AbstractChatCompletionRunner_getFinalMessage).call(this);\n    }\n    /**\n     * @returns a promise that resolves with the content of the final FunctionCall, or rejects\n     * if an error occurred or the stream ended prematurely without producing a ChatCompletionMessage.\n     */\n    async finalFunctionCall() {\n        await this.done();\n        return __classPrivateFieldGet(this, _AbstractChatCompletionRunner_instances, \"m\", _AbstractChatCompletionRunner_getFinalFunctionCall).call(this);\n    }\n    async finalFunctionCallResult() {\n        await this.done();\n        return __classPrivateFieldGet(this, _AbstractChatCompletionRunner_instances, \"m\", _AbstractChatCompletionRunner_getFinalFunctionCallResult).call(this);\n    }\n    async totalUsage() {\n        await this.done();\n        return __classPrivateFieldGet(this, _AbstractChatCompletionRunner_instances, \"m\", _AbstractChatCompletionRunner_calculateTotalUsage).call(this);\n    }\n    allChatCompletions() {\n        return [...this._chatCompletions];\n    }\n    _emitFinal() {\n        const completion = this._chatCompletions[this._chatCompletions.length - 1];\n        if (completion)\n            this._emit('finalChatCompletion', completion);\n        const finalMessage = __classPrivateFieldGet(this, _AbstractChatCompletionRunner_instances, \"m\", _AbstractChatCompletionRunner_getFinalMessage).call(this);\n        if (finalMessage)\n            this._emit('finalMessage', finalMessage);\n        const finalContent = __classPrivateFieldGet(this, _AbstractChatCompletionRunner_instances, \"m\", _AbstractChatCompletionRunner_getFinalContent).call(this);\n        if (finalContent)\n            this._emit('finalContent', finalContent);\n        const finalFunctionCall = __classPrivateFieldGet(this, _AbstractChatCompletionRunner_instances, \"m\", _AbstractChatCompletionRunner_getFinalFunctionCall).call(this);\n        if (finalFunctionCall)\n            this._emit('finalFunctionCall', finalFunctionCall);\n        const finalFunctionCallResult = __classPrivateFieldGet(this, _AbstractChatCompletionRunner_instances, \"m\", _AbstractChatCompletionRunner_getFinalFunctionCallResult).call(this);\n        if (finalFunctionCallResult != null)\n            this._emit('finalFunctionCallResult', finalFunctionCallResult);\n        if (this._chatCompletions.some((c) => c.usage)) {\n            this._emit('totalUsage', __classPrivateFieldGet(this, _AbstractChatCompletionRunner_instances, \"m\", _AbstractChatCompletionRunner_calculateTotalUsage).call(this));\n        }\n    }\n    async _createChatCompletion(client, params, options) {\n        const signal = options?.signal;\n        if (signal) {\n            if (signal.aborted)\n                this.controller.abort();\n            signal.addEventListener('abort', () => this.controller.abort());\n        }\n        __classPrivateFieldGet(this, _AbstractChatCompletionRunner_instances, \"m\", _AbstractChatCompletionRunner_validateParams).call(this, params);\n        const chatCompletion = await client.chat.completions.create({ ...params, stream: false }, { ...options, signal: this.controller.signal });\n        this._connected();\n        return this._addChatCompletion(parseChatCompletion(chatCompletion, params));\n    }\n    async _runChatCompletion(client, params, options) {\n        for (const message of params.messages) {\n            this._addMessage(message, false);\n        }\n        return await this._createChatCompletion(client, params, options);\n    }\n    async _runFunctions(client, params, options) {\n        const role = 'function';\n        const { function_call = 'auto', stream, ...restParams } = params;\n        const singleFunctionToCall = typeof function_call !== 'string' && function_call?.name;\n        const { maxChatCompletions = DEFAULT_MAX_CHAT_COMPLETIONS } = options || {};\n        const functionsByName = {};\n        for (const f of params.functions) {\n            functionsByName[f.name || f.function.name] = f;\n        }\n        const functions = params.functions.map((f) => ({\n            name: f.name || f.function.name,\n            parameters: f.parameters,\n            description: f.description,\n        }));\n        for (const message of params.messages) {\n            this._addMessage(message, false);\n        }\n        for (let i = 0; i < maxChatCompletions; ++i) {\n            const chatCompletion = await this._createChatCompletion(client, {\n                ...restParams,\n                function_call,\n                functions,\n                messages: [...this.messages],\n            }, options);\n            const message = chatCompletion.choices[0]?.message;\n            if (!message) {\n                throw new OpenAIError(`missing message in ChatCompletion response`);\n            }\n            if (!message.function_call)\n                return;\n            const { name, arguments: args } = message.function_call;\n            const fn = functionsByName[name];\n            if (!fn) {\n                const content = `Invalid function_call: ${JSON.stringify(name)}. Available options are: ${functions\n                    .map((f) => JSON.stringify(f.name))\n                    .join(', ')}. Please try again`;\n                this._addMessage({ role, name, content });\n                continue;\n            }\n            else if (singleFunctionToCall && singleFunctionToCall !== name) {\n                const content = `Invalid function_call: ${JSON.stringify(name)}. ${JSON.stringify(singleFunctionToCall)} requested. Please try again`;\n                this._addMessage({ role, name, content });\n                continue;\n            }\n            let parsed;\n            try {\n                parsed = isRunnableFunctionWithParse(fn) ? await fn.parse(args) : args;\n            }\n            catch (error) {\n                this._addMessage({\n                    role,\n                    name,\n                    content: error instanceof Error ? error.message : String(error),\n                });\n                continue;\n            }\n            // @ts-expect-error it can't rule out `never` type.\n            const rawContent = await fn.function(parsed, this);\n            const content = __classPrivateFieldGet(this, _AbstractChatCompletionRunner_instances, \"m\", _AbstractChatCompletionRunner_stringifyFunctionCallResult).call(this, rawContent);\n            this._addMessage({ role, name, content });\n            if (singleFunctionToCall)\n                return;\n        }\n    }\n    async _runTools(client, params, options) {\n        const role = 'tool';\n        const { tool_choice = 'auto', stream, ...restParams } = params;\n        const singleFunctionToCall = typeof tool_choice !== 'string' && tool_choice?.function?.name;\n        const { maxChatCompletions = DEFAULT_MAX_CHAT_COMPLETIONS } = options || {};\n        // TODO(someday): clean this logic up\n        const inputTools = params.tools.map((tool) => {\n            if (isAutoParsableTool(tool)) {\n                if (!tool.$callback) {\n                    throw new OpenAIError('Tool given to `.runTools()` that does not have an associated function');\n                }\n                return {\n                    type: 'function',\n                    function: {\n                        function: tool.$callback,\n                        name: tool.function.name,\n                        description: tool.function.description || '',\n                        parameters: tool.function.parameters,\n                        parse: tool.$parseRaw,\n                        strict: true,\n                    },\n                };\n            }\n            return tool;\n        });\n        const functionsByName = {};\n        for (const f of inputTools) {\n            if (f.type === 'function') {\n                functionsByName[f.function.name || f.function.function.name] = f.function;\n            }\n        }\n        const tools = 'tools' in params ?\n            inputTools.map((t) => t.type === 'function' ?\n                {\n                    type: 'function',\n                    function: {\n                        name: t.function.name || t.function.function.name,\n                        parameters: t.function.parameters,\n                        description: t.function.description,\n                        strict: t.function.strict,\n                    },\n                }\n                : t)\n            : undefined;\n        for (const message of params.messages) {\n            this._addMessage(message, false);\n        }\n        for (let i = 0; i < maxChatCompletions; ++i) {\n            const chatCompletion = await this._createChatCompletion(client, {\n                ...restParams,\n                tool_choice,\n                tools,\n                messages: [...this.messages],\n            }, options);\n            const message = chatCompletion.choices[0]?.message;\n            if (!message) {\n                throw new OpenAIError(`missing message in ChatCompletion response`);\n            }\n            if (!message.tool_calls?.length) {\n                return;\n            }\n            for (const tool_call of message.tool_calls) {\n                if (tool_call.type !== 'function')\n                    continue;\n                const tool_call_id = tool_call.id;\n                const { name, arguments: args } = tool_call.function;\n                const fn = functionsByName[name];\n                if (!fn) {\n                    const content = `Invalid tool_call: ${JSON.stringify(name)}. Available options are: ${Object.keys(functionsByName)\n                        .map((name) => JSON.stringify(name))\n                        .join(', ')}. Please try again`;\n                    this._addMessage({ role, tool_call_id, content });\n                    continue;\n                }\n                else if (singleFunctionToCall && singleFunctionToCall !== name) {\n                    const content = `Invalid tool_call: ${JSON.stringify(name)}. ${JSON.stringify(singleFunctionToCall)} requested. Please try again`;\n                    this._addMessage({ role, tool_call_id, content });\n                    continue;\n                }\n                let parsed;\n                try {\n                    parsed = isRunnableFunctionWithParse(fn) ? await fn.parse(args) : args;\n                }\n                catch (error) {\n                    const content = error instanceof Error ? error.message : String(error);\n                    this._addMessage({ role, tool_call_id, content });\n                    continue;\n                }\n                // @ts-expect-error it can't rule out `never` type.\n                const rawContent = await fn.function(parsed, this);\n                const content = __classPrivateFieldGet(this, _AbstractChatCompletionRunner_instances, \"m\", _AbstractChatCompletionRunner_stringifyFunctionCallResult).call(this, rawContent);\n                this._addMessage({ role, tool_call_id, content });\n                if (singleFunctionToCall) {\n                    return;\n                }\n            }\n        }\n        return;\n    }\n}\n_AbstractChatCompletionRunner_instances = new WeakSet(), _AbstractChatCompletionRunner_getFinalContent = function _AbstractChatCompletionRunner_getFinalContent() {\n    return __classPrivateFieldGet(this, _AbstractChatCompletionRunner_instances, \"m\", _AbstractChatCompletionRunner_getFinalMessage).call(this).content ?? null;\n}, _AbstractChatCompletionRunner_getFinalMessage = function _AbstractChatCompletionRunner_getFinalMessage() {\n    let i = this.messages.length;\n    while (i-- > 0) {\n        const message = this.messages[i];\n        if (isAssistantMessage(message)) {\n            const { function_call, ...rest } = message;\n            // TODO: support audio here\n            const ret = {\n                ...rest,\n                content: message.content ?? null,\n                refusal: message.refusal ?? null,\n            };\n            if (function_call) {\n                ret.function_call = function_call;\n            }\n            return ret;\n        }\n    }\n    throw new OpenAIError('stream ended without producing a ChatCompletionMessage with role=assistant');\n}, _AbstractChatCompletionRunner_getFinalFunctionCall = function _AbstractChatCompletionRunner_getFinalFunctionCall() {\n    for (let i = this.messages.length - 1; i >= 0; i--) {\n        const message = this.messages[i];\n        if (isAssistantMessage(message) && message?.function_call) {\n            return message.function_call;\n        }\n        if (isAssistantMessage(message) && message?.tool_calls?.length) {\n            return message.tool_calls.at(-1)?.function;\n        }\n    }\n    return;\n}, _AbstractChatCompletionRunner_getFinalFunctionCallResult = function _AbstractChatCompletionRunner_getFinalFunctionCallResult() {\n    for (let i = this.messages.length - 1; i >= 0; i--) {\n        const message = this.messages[i];\n        if (isFunctionMessage(message) && message.content != null) {\n            return message.content;\n        }\n        if (isToolMessage(message) &&\n            message.content != null &&\n            typeof message.content === 'string' &&\n            this.messages.some((x) => x.role === 'assistant' &&\n                x.tool_calls?.some((y) => y.type === 'function' && y.id === message.tool_call_id))) {\n            return message.content;\n        }\n    }\n    return;\n}, _AbstractChatCompletionRunner_calculateTotalUsage = function _AbstractChatCompletionRunner_calculateTotalUsage() {\n    const total = {\n        completion_tokens: 0,\n        prompt_tokens: 0,\n        total_tokens: 0,\n    };\n    for (const { usage } of this._chatCompletions) {\n        if (usage) {\n            total.completion_tokens += usage.completion_tokens;\n            total.prompt_tokens += usage.prompt_tokens;\n            total.total_tokens += usage.total_tokens;\n        }\n    }\n    return total;\n}, _AbstractChatCompletionRunner_validateParams = function _AbstractChatCompletionRunner_validateParams(params) {\n    if (params.n != null && params.n > 1) {\n        throw new OpenAIError('ChatCompletion convenience helpers only support n=1 at this time. To use n>1, please use chat.completions.create() directly.');\n    }\n}, _AbstractChatCompletionRunner_stringifyFunctionCallResult = function _AbstractChatCompletionRunner_stringifyFunctionCallResult(rawContent) {\n    return (typeof rawContent === 'string' ? rawContent\n        : rawContent === undefined ? 'undefined'\n            : JSON.stringify(rawContent));\n};\n//# sourceMappingURL=AbstractChatCompletionRunner.mjs.map","import { AbstractChatCompletionRunner, } from \"./AbstractChatCompletionRunner.mjs\";\nimport { isAssistantMessage } from \"./chatCompletionUtils.mjs\";\nexport class ChatCompletionRunner extends AbstractChatCompletionRunner {\n    /** @deprecated - please use `runTools` instead. */\n    static runFunctions(client, params, options) {\n        const runner = new ChatCompletionRunner();\n        const opts = {\n            ...options,\n            headers: { ...options?.headers, 'X-Stainless-Helper-Method': 'runFunctions' },\n        };\n        runner._run(() => runner._runFunctions(client, params, opts));\n        return runner;\n    }\n    static runTools(client, params, options) {\n        const runner = new ChatCompletionRunner();\n        const opts = {\n            ...options,\n            headers: { ...options?.headers, 'X-Stainless-Helper-Method': 'runTools' },\n        };\n        runner._run(() => runner._runTools(client, params, opts));\n        return runner;\n    }\n    _addMessage(message, emit = true) {\n        super._addMessage(message, emit);\n        if (isAssistantMessage(message) && message.content) {\n            this._emit('content', message.content);\n        }\n    }\n}\n//# sourceMappingURL=ChatCompletionRunner.mjs.map","const STR = 0b000000001;\nconst NUM = 0b000000010;\nconst ARR = 0b000000100;\nconst OBJ = 0b000001000;\nconst NULL = 0b000010000;\nconst BOOL = 0b000100000;\nconst NAN = 0b001000000;\nconst INFINITY = 0b010000000;\nconst MINUS_INFINITY = 0b100000000;\nconst INF = INFINITY | MINUS_INFINITY;\nconst SPECIAL = NULL | BOOL | INF | NAN;\nconst ATOM = STR | NUM | SPECIAL;\nconst COLLECTION = ARR | OBJ;\nconst ALL = ATOM | COLLECTION;\nconst Allow = {\n    STR,\n    NUM,\n    ARR,\n    OBJ,\n    NULL,\n    BOOL,\n    NAN,\n    INFINITY,\n    MINUS_INFINITY,\n    INF,\n    SPECIAL,\n    ATOM,\n    COLLECTION,\n    ALL,\n};\n// The JSON string segment was unable to be parsed completely\nclass PartialJSON extends Error {\n}\nclass MalformedJSON extends Error {\n}\n/**\n * Parse incomplete JSON\n * @param {string} jsonString Partial JSON to be parsed\n * @param {number} allowPartial Specify what types are allowed to be partial, see {@link Allow} for details\n * @returns The parsed JSON\n * @throws {PartialJSON} If the JSON is incomplete (related to the `allow` parameter)\n * @throws {MalformedJSON} If the JSON is malformed\n */\nfunction parseJSON(jsonString, allowPartial = Allow.ALL) {\n    if (typeof jsonString !== 'string') {\n        throw new TypeError(`expecting str, got ${typeof jsonString}`);\n    }\n    if (!jsonString.trim()) {\n        throw new Error(`${jsonString} is empty`);\n    }\n    return _parseJSON(jsonString.trim(), allowPartial);\n}\nconst _parseJSON = (jsonString, allow) => {\n    const length = jsonString.length;\n    let index = 0;\n    const markPartialJSON = (msg) => {\n        throw new PartialJSON(`${msg} at position ${index}`);\n    };\n    const throwMalformedError = (msg) => {\n        throw new MalformedJSON(`${msg} at position ${index}`);\n    };\n    const parseAny = () => {\n        skipBlank();\n        if (index >= length)\n            markPartialJSON('Unexpected end of input');\n        if (jsonString[index] === '\"')\n            return parseStr();\n        if (jsonString[index] === '{')\n            return parseObj();\n        if (jsonString[index] === '[')\n            return parseArr();\n        if (jsonString.substring(index, index + 4) === 'null' ||\n            (Allow.NULL & allow && length - index < 4 && 'null'.startsWith(jsonString.substring(index)))) {\n            index += 4;\n            return null;\n        }\n        if (jsonString.substring(index, index + 4) === 'true' ||\n            (Allow.BOOL & allow && length - index < 4 && 'true'.startsWith(jsonString.substring(index)))) {\n            index += 4;\n            return true;\n        }\n        if (jsonString.substring(index, index + 5) === 'false' ||\n            (Allow.BOOL & allow && length - index < 5 && 'false'.startsWith(jsonString.substring(index)))) {\n            index += 5;\n            return false;\n        }\n        if (jsonString.substring(index, index + 8) === 'Infinity' ||\n            (Allow.INFINITY & allow && length - index < 8 && 'Infinity'.startsWith(jsonString.substring(index)))) {\n            index += 8;\n            return Infinity;\n        }\n        if (jsonString.substring(index, index + 9) === '-Infinity' ||\n            (Allow.MINUS_INFINITY & allow &&\n                1 < length - index &&\n                length - index < 9 &&\n                '-Infinity'.startsWith(jsonString.substring(index)))) {\n            index += 9;\n            return -Infinity;\n        }\n        if (jsonString.substring(index, index + 3) === 'NaN' ||\n            (Allow.NAN & allow && length - index < 3 && 'NaN'.startsWith(jsonString.substring(index)))) {\n            index += 3;\n            return NaN;\n        }\n        return parseNum();\n    };\n    const parseStr = () => {\n        const start = index;\n        let escape = false;\n        index++; // skip initial quote\n        while (index < length && (jsonString[index] !== '\"' || (escape && jsonString[index - 1] === '\\\\'))) {\n            escape = jsonString[index] === '\\\\' ? !escape : false;\n            index++;\n        }\n        if (jsonString.charAt(index) == '\"') {\n            try {\n                return JSON.parse(jsonString.substring(start, ++index - Number(escape)));\n            }\n            catch (e) {\n                throwMalformedError(String(e));\n            }\n        }\n        else if (Allow.STR & allow) {\n            try {\n                return JSON.parse(jsonString.substring(start, index - Number(escape)) + '\"');\n            }\n            catch (e) {\n                // SyntaxError: Invalid escape sequence\n                return JSON.parse(jsonString.substring(start, jsonString.lastIndexOf('\\\\')) + '\"');\n            }\n        }\n        markPartialJSON('Unterminated string literal');\n    };\n    const parseObj = () => {\n        index++; // skip initial brace\n        skipBlank();\n        const obj = {};\n        try {\n            while (jsonString[index] !== '}') {\n                skipBlank();\n                if (index >= length && Allow.OBJ & allow)\n                    return obj;\n                const key = parseStr();\n                skipBlank();\n                index++; // skip colon\n                try {\n                    const value = parseAny();\n                    Object.defineProperty(obj, key, { value, writable: true, enumerable: true, configurable: true });\n                }\n                catch (e) {\n                    if (Allow.OBJ & allow)\n                        return obj;\n                    else\n                        throw e;\n                }\n                skipBlank();\n                if (jsonString[index] === ',')\n                    index++; // skip comma\n            }\n        }\n        catch (e) {\n            if (Allow.OBJ & allow)\n                return obj;\n            else\n                markPartialJSON(\"Expected '}' at end of object\");\n        }\n        index++; // skip final brace\n        return obj;\n    };\n    const parseArr = () => {\n        index++; // skip initial bracket\n        const arr = [];\n        try {\n            while (jsonString[index] !== ']') {\n                arr.push(parseAny());\n                skipBlank();\n                if (jsonString[index] === ',') {\n                    index++; // skip comma\n                }\n            }\n        }\n        catch (e) {\n            if (Allow.ARR & allow) {\n                return arr;\n            }\n            markPartialJSON(\"Expected ']' at end of array\");\n        }\n        index++; // skip final bracket\n        return arr;\n    };\n    const parseNum = () => {\n        if (index === 0) {\n            if (jsonString === '-' && Allow.NUM & allow)\n                markPartialJSON(\"Not sure what '-' is\");\n            try {\n                return JSON.parse(jsonString);\n            }\n            catch (e) {\n                if (Allow.NUM & allow) {\n                    try {\n                        if ('.' === jsonString[jsonString.length - 1])\n                            return JSON.parse(jsonString.substring(0, jsonString.lastIndexOf('.')));\n                        return JSON.parse(jsonString.substring(0, jsonString.lastIndexOf('e')));\n                    }\n                    catch (e) { }\n                }\n                throwMalformedError(String(e));\n            }\n        }\n        const start = index;\n        if (jsonString[index] === '-')\n            index++;\n        while (jsonString[index] && !',]}'.includes(jsonString[index]))\n            index++;\n        if (index == length && !(Allow.NUM & allow))\n            markPartialJSON('Unterminated number literal');\n        try {\n            return JSON.parse(jsonString.substring(start, index));\n        }\n        catch (e) {\n            if (jsonString.substring(start, index) === '-' && Allow.NUM & allow)\n                markPartialJSON(\"Not sure what '-' is\");\n            try {\n                return JSON.parse(jsonString.substring(start, jsonString.lastIndexOf('e')));\n            }\n            catch (e) {\n                throwMalformedError(String(e));\n            }\n        }\n    };\n    const skipBlank = () => {\n        while (index < length && ' \\n\\r\\t'.includes(jsonString[index])) {\n            index++;\n        }\n    };\n    return parseAny();\n};\n// using this function with malformed JSON is undefined behavior\nconst partialParse = (input) => parseJSON(input, Allow.ALL ^ Allow.NUM);\nexport { partialParse, PartialJSON, MalformedJSON };\n//# sourceMappingURL=parser.mjs.map","var __classPrivateFieldSet = (this && this.__classPrivateFieldSet) || function (receiver, state, value, kind, f) {\n    if (kind === \"m\") throw new TypeError(\"Private method is not writable\");\n    if (kind === \"a\" && !f) throw new TypeError(\"Private accessor was defined without a setter\");\n    if (typeof state === \"function\" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError(\"Cannot write private member to an object whose class did not declare it\");\n    return (kind === \"a\" ? f.call(receiver, value) : f ? f.value = value : state.set(receiver, value)), value;\n};\nvar __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {\n    if (kind === \"a\" && !f) throw new TypeError(\"Private accessor was defined without a getter\");\n    if (typeof state === \"function\" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError(\"Cannot read private member from an object whose class did not declare it\");\n    return kind === \"m\" ? f : kind === \"a\" ? f.call(receiver) : f ? f.value : state.get(receiver);\n};\nvar _ChatCompletionStream_instances, _ChatCompletionStream_params, _ChatCompletionStream_choiceEventStates, _ChatCompletionStream_currentChatCompletionSnapshot, _ChatCompletionStream_beginRequest, _ChatCompletionStream_getChoiceEventState, _ChatCompletionStream_addChunk, _ChatCompletionStream_emitToolCallDoneEvent, _ChatCompletionStream_emitContentDoneEvents, _ChatCompletionStream_endRequest, _ChatCompletionStream_getAutoParseableResponseFormat, _ChatCompletionStream_accumulateChatCompletion;\nimport { OpenAIError, APIUserAbortError, LengthFinishReasonError, ContentFilterFinishReasonError, } from \"../error.mjs\";\nimport { AbstractChatCompletionRunner, } from \"./AbstractChatCompletionRunner.mjs\";\nimport { Stream } from \"../streaming.mjs\";\nimport { hasAutoParseableInput, isAutoParsableResponseFormat, isAutoParsableTool, maybeParseChatCompletion, shouldParseToolCall, } from \"../lib/parser.mjs\";\nimport { partialParse } from \"../_vendor/partial-json-parser/parser.mjs\";\nexport class ChatCompletionStream extends AbstractChatCompletionRunner {\n    constructor(params) {\n        super();\n        _ChatCompletionStream_instances.add(this);\n        _ChatCompletionStream_params.set(this, void 0);\n        _ChatCompletionStream_choiceEventStates.set(this, void 0);\n        _ChatCompletionStream_currentChatCompletionSnapshot.set(this, void 0);\n        __classPrivateFieldSet(this, _ChatCompletionStream_params, params, \"f\");\n        __classPrivateFieldSet(this, _ChatCompletionStream_choiceEventStates, [], \"f\");\n    }\n    get currentChatCompletionSnapshot() {\n        return __classPrivateFieldGet(this, _ChatCompletionStream_currentChatCompletionSnapshot, \"f\");\n    }\n    /**\n     * Intended for use on the frontend, consuming a stream produced with\n     * `.toReadableStream()` on the backend.\n     *\n     * Note that messages sent to the model do not appear in `.on('message')`\n     * in this context.\n     */\n    static fromReadableStream(stream) {\n        const runner = new ChatCompletionStream(null);\n        runner._run(() => runner._fromReadableStream(stream));\n        return runner;\n    }\n    static createChatCompletion(client, params, options) {\n        const runner = new ChatCompletionStream(params);\n        runner._run(() => runner._runChatCompletion(client, { ...params, stream: true }, { ...options, headers: { ...options?.headers, 'X-Stainless-Helper-Method': 'stream' } }));\n        return runner;\n    }\n    async _createChatCompletion(client, params, options) {\n        super._createChatCompletion;\n        const signal = options?.signal;\n        if (signal) {\n            if (signal.aborted)\n                this.controller.abort();\n            signal.addEventListener('abort', () => this.controller.abort());\n        }\n        __classPrivateFieldGet(this, _ChatCompletionStream_instances, \"m\", _ChatCompletionStream_beginRequest).call(this);\n        const stream = await client.chat.completions.create({ ...params, stream: true }, { ...options, signal: this.controller.signal });\n        this._connected();\n        for await (const chunk of stream) {\n            __classPrivateFieldGet(this, _ChatCompletionStream_instances, \"m\", _ChatCompletionStream_addChunk).call(this, chunk);\n        }\n        if (stream.controller.signal?.aborted) {\n            throw new APIUserAbortError();\n        }\n        return this._addChatCompletion(__classPrivateFieldGet(this, _ChatCompletionStream_instances, \"m\", _ChatCompletionStream_endRequest).call(this));\n    }\n    async _fromReadableStream(readableStream, options) {\n        const signal = options?.signal;\n        if (signal) {\n            if (signal.aborted)\n                this.controller.abort();\n            signal.addEventListener('abort', () => this.controller.abort());\n        }\n        __classPrivateFieldGet(this, _ChatCompletionStream_instances, \"m\", _ChatCompletionStream_beginRequest).call(this);\n        this._connected();\n        const stream = Stream.fromReadableStream(readableStream, this.controller);\n        let chatId;\n        for await (const chunk of stream) {\n            if (chatId && chatId !== chunk.id) {\n                // A new request has been made.\n                this._addChatCompletion(__classPrivateFieldGet(this, _ChatCompletionStream_instances, \"m\", _ChatCompletionStream_endRequest).call(this));\n            }\n            __classPrivateFieldGet(this, _ChatCompletionStream_instances, \"m\", _ChatCompletionStream_addChunk).call(this, chunk);\n            chatId = chunk.id;\n        }\n        if (stream.controller.signal?.aborted) {\n            throw new APIUserAbortError();\n        }\n        return this._addChatCompletion(__classPrivateFieldGet(this, _ChatCompletionStream_instances, \"m\", _ChatCompletionStream_endRequest).call(this));\n    }\n    [(_ChatCompletionStream_params = new WeakMap(), _ChatCompletionStream_choiceEventStates = new WeakMap(), _ChatCompletionStream_currentChatCompletionSnapshot = new WeakMap(), _ChatCompletionStream_instances = new WeakSet(), _ChatCompletionStream_beginRequest = function _ChatCompletionStream_beginRequest() {\n        if (this.ended)\n            return;\n        __classPrivateFieldSet(this, _ChatCompletionStream_currentChatCompletionSnapshot, undefined, \"f\");\n    }, _ChatCompletionStream_getChoiceEventState = function _ChatCompletionStream_getChoiceEventState(choice) {\n        let state = __classPrivateFieldGet(this, _ChatCompletionStream_choiceEventStates, \"f\")[choice.index];\n        if (state) {\n            return state;\n        }\n        state = {\n            content_done: false,\n            refusal_done: false,\n            logprobs_content_done: false,\n            logprobs_refusal_done: false,\n            done_tool_calls: new Set(),\n            current_tool_call_index: null,\n        };\n        __classPrivateFieldGet(this, _ChatCompletionStream_choiceEventStates, \"f\")[choice.index] = state;\n        return state;\n    }, _ChatCompletionStream_addChunk = function _ChatCompletionStream_addChunk(chunk) {\n        if (this.ended)\n            return;\n        const completion = __classPrivateFieldGet(this, _ChatCompletionStream_instances, \"m\", _ChatCompletionStream_accumulateChatCompletion).call(this, chunk);\n        this._emit('chunk', chunk, completion);\n        for (const choice of chunk.choices) {\n            const choiceSnapshot = completion.choices[choice.index];\n            if (choice.delta.content != null &&\n                choiceSnapshot.message?.role === 'assistant' &&\n                choiceSnapshot.message?.content) {\n                this._emit('content', choice.delta.content, choiceSnapshot.message.content);\n                this._emit('content.delta', {\n                    delta: choice.delta.content,\n                    snapshot: choiceSnapshot.message.content,\n                    parsed: choiceSnapshot.message.parsed,\n                });\n            }\n            if (choice.delta.refusal != null &&\n                choiceSnapshot.message?.role === 'assistant' &&\n                choiceSnapshot.message?.refusal) {\n                this._emit('refusal.delta', {\n                    delta: choice.delta.refusal,\n                    snapshot: choiceSnapshot.message.refusal,\n                });\n            }\n            if (choice.logprobs?.content != null && choiceSnapshot.message?.role === 'assistant') {\n                this._emit('logprobs.content.delta', {\n                    content: choice.logprobs?.content,\n                    snapshot: choiceSnapshot.logprobs?.content ?? [],\n                });\n            }\n            if (choice.logprobs?.refusal != null && choiceSnapshot.message?.role === 'assistant') {\n                this._emit('logprobs.refusal.delta', {\n                    refusal: choice.logprobs?.refusal,\n                    snapshot: choiceSnapshot.logprobs?.refusal ?? [],\n                });\n            }\n            const state = __classPrivateFieldGet(this, _ChatCompletionStream_instances, \"m\", _ChatCompletionStream_getChoiceEventState).call(this, choiceSnapshot);\n            if (choiceSnapshot.finish_reason) {\n                __classPrivateFieldGet(this, _ChatCompletionStream_instances, \"m\", _ChatCompletionStream_emitContentDoneEvents).call(this, choiceSnapshot);\n                if (state.current_tool_call_index != null) {\n                    __classPrivateFieldGet(this, _ChatCompletionStream_instances, \"m\", _ChatCompletionStream_emitToolCallDoneEvent).call(this, choiceSnapshot, state.current_tool_call_index);\n                }\n            }\n            for (const toolCall of choice.delta.tool_calls ?? []) {\n                if (state.current_tool_call_index !== toolCall.index) {\n                    __classPrivateFieldGet(this, _ChatCompletionStream_instances, \"m\", _ChatCompletionStream_emitContentDoneEvents).call(this, choiceSnapshot);\n                    // new tool call started, the previous one is done\n                    if (state.current_tool_call_index != null) {\n                        __classPrivateFieldGet(this, _ChatCompletionStream_instances, \"m\", _ChatCompletionStream_emitToolCallDoneEvent).call(this, choiceSnapshot, state.current_tool_call_index);\n                    }\n                }\n                state.current_tool_call_index = toolCall.index;\n            }\n            for (const toolCallDelta of choice.delta.tool_calls ?? []) {\n                const toolCallSnapshot = choiceSnapshot.message.tool_calls?.[toolCallDelta.index];\n                if (!toolCallSnapshot?.type) {\n                    continue;\n                }\n                if (toolCallSnapshot?.type === 'function') {\n                    this._emit('tool_calls.function.arguments.delta', {\n                        name: toolCallSnapshot.function?.name,\n                        index: toolCallDelta.index,\n                        arguments: toolCallSnapshot.function.arguments,\n                        parsed_arguments: toolCallSnapshot.function.parsed_arguments,\n                        arguments_delta: toolCallDelta.function?.arguments ?? '',\n                    });\n                }\n                else {\n                    assertNever(toolCallSnapshot?.type);\n                }\n            }\n        }\n    }, _ChatCompletionStream_emitToolCallDoneEvent = function _ChatCompletionStream_emitToolCallDoneEvent(choiceSnapshot, toolCallIndex) {\n        const state = __classPrivateFieldGet(this, _ChatCompletionStream_instances, \"m\", _ChatCompletionStream_getChoiceEventState).call(this, choiceSnapshot);\n        if (state.done_tool_calls.has(toolCallIndex)) {\n            // we've already fired the done event\n            return;\n        }\n        const toolCallSnapshot = choiceSnapshot.message.tool_calls?.[toolCallIndex];\n        if (!toolCallSnapshot) {\n            throw new Error('no tool call snapshot');\n        }\n        if (!toolCallSnapshot.type) {\n            throw new Error('tool call snapshot missing `type`');\n        }\n        if (toolCallSnapshot.type === 'function') {\n            const inputTool = __classPrivateFieldGet(this, _ChatCompletionStream_params, \"f\")?.tools?.find((tool) => tool.type === 'function' && tool.function.name === toolCallSnapshot.function.name);\n            this._emit('tool_calls.function.arguments.done', {\n                name: toolCallSnapshot.function.name,\n                index: toolCallIndex,\n                arguments: toolCallSnapshot.function.arguments,\n                parsed_arguments: isAutoParsableTool(inputTool) ? inputTool.$parseRaw(toolCallSnapshot.function.arguments)\n                    : inputTool?.function.strict ? JSON.parse(toolCallSnapshot.function.arguments)\n                        : null,\n            });\n        }\n        else {\n            assertNever(toolCallSnapshot.type);\n        }\n    }, _ChatCompletionStream_emitContentDoneEvents = function _ChatCompletionStream_emitContentDoneEvents(choiceSnapshot) {\n        const state = __classPrivateFieldGet(this, _ChatCompletionStream_instances, \"m\", _ChatCompletionStream_getChoiceEventState).call(this, choiceSnapshot);\n        if (choiceSnapshot.message.content && !state.content_done) {\n            state.content_done = true;\n            const responseFormat = __classPrivateFieldGet(this, _ChatCompletionStream_instances, \"m\", _ChatCompletionStream_getAutoParseableResponseFormat).call(this);\n            this._emit('content.done', {\n                content: choiceSnapshot.message.content,\n                parsed: responseFormat ? responseFormat.$parseRaw(choiceSnapshot.message.content) : null,\n            });\n        }\n        if (choiceSnapshot.message.refusal && !state.refusal_done) {\n            state.refusal_done = true;\n            this._emit('refusal.done', { refusal: choiceSnapshot.message.refusal });\n        }\n        if (choiceSnapshot.logprobs?.content && !state.logprobs_content_done) {\n            state.logprobs_content_done = true;\n            this._emit('logprobs.content.done', { content: choiceSnapshot.logprobs.content });\n        }\n        if (choiceSnapshot.logprobs?.refusal && !state.logprobs_refusal_done) {\n            state.logprobs_refusal_done = true;\n            this._emit('logprobs.refusal.done', { refusal: choiceSnapshot.logprobs.refusal });\n        }\n    }, _ChatCompletionStream_endRequest = function _ChatCompletionStream_endRequest() {\n        if (this.ended) {\n            throw new OpenAIError(`stream has ended, this shouldn't happen`);\n        }\n        const snapshot = __classPrivateFieldGet(this, _ChatCompletionStream_currentChatCompletionSnapshot, \"f\");\n        if (!snapshot) {\n            throw new OpenAIError(`request ended without sending any chunks`);\n        }\n        __classPrivateFieldSet(this, _ChatCompletionStream_currentChatCompletionSnapshot, undefined, \"f\");\n        __classPrivateFieldSet(this, _ChatCompletionStream_choiceEventStates, [], \"f\");\n        return finalizeChatCompletion(snapshot, __classPrivateFieldGet(this, _ChatCompletionStream_params, \"f\"));\n    }, _ChatCompletionStream_getAutoParseableResponseFormat = function _ChatCompletionStream_getAutoParseableResponseFormat() {\n        const responseFormat = __classPrivateFieldGet(this, _ChatCompletionStream_params, \"f\")?.response_format;\n        if (isAutoParsableResponseFormat(responseFormat)) {\n            return responseFormat;\n        }\n        return null;\n    }, _ChatCompletionStream_accumulateChatCompletion = function _ChatCompletionStream_accumulateChatCompletion(chunk) {\n        var _a, _b, _c, _d;\n        let snapshot = __classPrivateFieldGet(this, _ChatCompletionStream_currentChatCompletionSnapshot, \"f\");\n        const { choices, ...rest } = chunk;\n        if (!snapshot) {\n            snapshot = __classPrivateFieldSet(this, _ChatCompletionStream_currentChatCompletionSnapshot, {\n                ...rest,\n                choices: [],\n            }, \"f\");\n        }\n        else {\n            Object.assign(snapshot, rest);\n        }\n        for (const { delta, finish_reason, index, logprobs = null, ...other } of chunk.choices) {\n            let choice = snapshot.choices[index];\n            if (!choice) {\n                choice = snapshot.choices[index] = { finish_reason, index, message: {}, logprobs, ...other };\n            }\n            if (logprobs) {\n                if (!choice.logprobs) {\n                    choice.logprobs = Object.assign({}, logprobs);\n                }\n                else {\n                    const { content, refusal, ...rest } = logprobs;\n                    assertIsEmpty(rest);\n                    Object.assign(choice.logprobs, rest);\n                    if (content) {\n                        (_a = choice.logprobs).content ?? (_a.content = []);\n                        choice.logprobs.content.push(...content);\n                    }\n                    if (refusal) {\n                        (_b = choice.logprobs).refusal ?? (_b.refusal = []);\n                        choice.logprobs.refusal.push(...refusal);\n                    }\n                }\n            }\n            if (finish_reason) {\n                choice.finish_reason = finish_reason;\n                if (__classPrivateFieldGet(this, _ChatCompletionStream_params, \"f\") && hasAutoParseableInput(__classPrivateFieldGet(this, _ChatCompletionStream_params, \"f\"))) {\n                    if (finish_reason === 'length') {\n                        throw new LengthFinishReasonError();\n                    }\n                    if (finish_reason === 'content_filter') {\n                        throw new ContentFilterFinishReasonError();\n                    }\n                }\n            }\n            Object.assign(choice, other);\n            if (!delta)\n                continue; // Shouldn't happen; just in case.\n            const { content, refusal, function_call, role, tool_calls, ...rest } = delta;\n            assertIsEmpty(rest);\n            Object.assign(choice.message, rest);\n            if (refusal) {\n                choice.message.refusal = (choice.message.refusal || '') + refusal;\n            }\n            if (role)\n                choice.message.role = role;\n            if (function_call) {\n                if (!choice.message.function_call) {\n                    choice.message.function_call = function_call;\n                }\n                else {\n                    if (function_call.name)\n                        choice.message.function_call.name = function_call.name;\n                    if (function_call.arguments) {\n                        (_c = choice.message.function_call).arguments ?? (_c.arguments = '');\n                        choice.message.function_call.arguments += function_call.arguments;\n                    }\n                }\n            }\n            if (content) {\n                choice.message.content = (choice.message.content || '') + content;\n                if (!choice.message.refusal && __classPrivateFieldGet(this, _ChatCompletionStream_instances, \"m\", _ChatCompletionStream_getAutoParseableResponseFormat).call(this)) {\n                    choice.message.parsed = partialParse(choice.message.content);\n                }\n            }\n            if (tool_calls) {\n                if (!choice.message.tool_calls)\n                    choice.message.tool_calls = [];\n                for (const { index, id, type, function: fn, ...rest } of tool_calls) {\n                    const tool_call = ((_d = choice.message.tool_calls)[index] ?? (_d[index] = {}));\n                    Object.assign(tool_call, rest);\n                    if (id)\n                        tool_call.id = id;\n                    if (type)\n                        tool_call.type = type;\n                    if (fn)\n                        tool_call.function ?? (tool_call.function = { name: fn.name ?? '', arguments: '' });\n                    if (fn?.name)\n                        tool_call.function.name = fn.name;\n                    if (fn?.arguments) {\n                        tool_call.function.arguments += fn.arguments;\n                        if (shouldParseToolCall(__classPrivateFieldGet(this, _ChatCompletionStream_params, \"f\"), tool_call)) {\n                            tool_call.function.parsed_arguments = partialParse(tool_call.function.arguments);\n                        }\n                    }\n                }\n            }\n        }\n        return snapshot;\n    }, Symbol.asyncIterator)]() {\n        const pushQueue = [];\n        const readQueue = [];\n        let done = false;\n        this.on('chunk', (chunk) => {\n            const reader = readQueue.shift();\n            if (reader) {\n                reader.resolve(chunk);\n            }\n            else {\n                pushQueue.push(chunk);\n            }\n        });\n        this.on('end', () => {\n            done = true;\n            for (const reader of readQueue) {\n                reader.resolve(undefined);\n            }\n            readQueue.length = 0;\n        });\n        this.on('abort', (err) => {\n            done = true;\n            for (const reader of readQueue) {\n                reader.reject(err);\n            }\n            readQueue.length = 0;\n        });\n        this.on('error', (err) => {\n            done = true;\n            for (const reader of readQueue) {\n                reader.reject(err);\n            }\n            readQueue.length = 0;\n        });\n        return {\n            next: async () => {\n                if (!pushQueue.length) {\n                    if (done) {\n                        return { value: undefined, done: true };\n                    }\n                    return new Promise((resolve, reject) => readQueue.push({ resolve, reject })).then((chunk) => (chunk ? { value: chunk, done: false } : { value: undefined, done: true }));\n                }\n                const chunk = pushQueue.shift();\n                return { value: chunk, done: false };\n            },\n            return: async () => {\n                this.abort();\n                return { value: undefined, done: true };\n            },\n        };\n    }\n    toReadableStream() {\n        const stream = new Stream(this[Symbol.asyncIterator].bind(this), this.controller);\n        return stream.toReadableStream();\n    }\n}\nfunction finalizeChatCompletion(snapshot, params) {\n    const { id, choices, created, model, system_fingerprint, ...rest } = snapshot;\n    const completion = {\n        ...rest,\n        id,\n        choices: choices.map(({ message, finish_reason, index, logprobs, ...choiceRest }) => {\n            if (!finish_reason) {\n                throw new OpenAIError(`missing finish_reason for choice ${index}`);\n            }\n            const { content = null, function_call, tool_calls, ...messageRest } = message;\n            const role = message.role; // this is what we expect; in theory it could be different which would make our types a slight lie but would be fine.\n            if (!role) {\n                throw new OpenAIError(`missing role for choice ${index}`);\n            }\n            if (function_call) {\n                const { arguments: args, name } = function_call;\n                if (args == null) {\n                    throw new OpenAIError(`missing function_call.arguments for choice ${index}`);\n                }\n                if (!name) {\n                    throw new OpenAIError(`missing function_call.name for choice ${index}`);\n                }\n                return {\n                    ...choiceRest,\n                    message: {\n                        content,\n                        function_call: { arguments: args, name },\n                        role,\n                        refusal: message.refusal ?? null,\n                    },\n                    finish_reason,\n                    index,\n                    logprobs,\n                };\n            }\n            if (tool_calls) {\n                return {\n                    ...choiceRest,\n                    index,\n                    finish_reason,\n                    logprobs,\n                    message: {\n                        ...messageRest,\n                        role,\n                        content,\n                        refusal: message.refusal ?? null,\n                        tool_calls: tool_calls.map((tool_call, i) => {\n                            const { function: fn, type, id, ...toolRest } = tool_call;\n                            const { arguments: args, name, ...fnRest } = fn || {};\n                            if (id == null) {\n                                throw new OpenAIError(`missing choices[${index}].tool_calls[${i}].id\\n${str(snapshot)}`);\n                            }\n                            if (type == null) {\n                                throw new OpenAIError(`missing choices[${index}].tool_calls[${i}].type\\n${str(snapshot)}`);\n                            }\n                            if (name == null) {\n                                throw new OpenAIError(`missing choices[${index}].tool_calls[${i}].function.name\\n${str(snapshot)}`);\n                            }\n                            if (args == null) {\n                                throw new OpenAIError(`missing choices[${index}].tool_calls[${i}].function.arguments\\n${str(snapshot)}`);\n                            }\n                            return { ...toolRest, id, type, function: { ...fnRest, name, arguments: args } };\n                        }),\n                    },\n                };\n            }\n            return {\n                ...choiceRest,\n                message: { ...messageRest, content, role, refusal: message.refusal ?? null },\n                finish_reason,\n                index,\n                logprobs,\n            };\n        }),\n        created,\n        model,\n        object: 'chat.completion',\n        ...(system_fingerprint ? { system_fingerprint } : {}),\n    };\n    return maybeParseChatCompletion(completion, params);\n}\nfunction str(x) {\n    return JSON.stringify(x);\n}\n/**\n * Ensures the given argument is an empty object, useful for\n * asserting that all known properties on an object have been\n * destructured.\n */\nfunction assertIsEmpty(obj) {\n    return;\n}\nfunction assertNever(_x) { }\n//# sourceMappingURL=ChatCompletionStream.mjs.map","import { ChatCompletionStream } from \"./ChatCompletionStream.mjs\";\nexport class ChatCompletionStreamingRunner extends ChatCompletionStream {\n    static fromReadableStream(stream) {\n        const runner = new ChatCompletionStreamingRunner(null);\n        runner._run(() => runner._fromReadableStream(stream));\n        return runner;\n    }\n    /** @deprecated - please use `runTools` instead. */\n    static runFunctions(client, params, options) {\n        const runner = new ChatCompletionStreamingRunner(null);\n        const opts = {\n            ...options,\n            headers: { ...options?.headers, 'X-Stainless-Helper-Method': 'runFunctions' },\n        };\n        runner._run(() => runner._runFunctions(client, params, opts));\n        return runner;\n    }\n    static runTools(client, params, options) {\n        const runner = new ChatCompletionStreamingRunner(\n        // @ts-expect-error TODO these types are incompatible\n        params);\n        const opts = {\n            ...options,\n            headers: { ...options?.headers, 'X-Stainless-Helper-Method': 'runTools' },\n        };\n        runner._run(() => runner._runTools(client, params, opts));\n        return runner;\n    }\n}\n//# sourceMappingURL=ChatCompletionStreamingRunner.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../../resource.mjs\";\nimport { ChatCompletionRunner } from \"../../../lib/ChatCompletionRunner.mjs\";\nimport { ChatCompletionStreamingRunner, } from \"../../../lib/ChatCompletionStreamingRunner.mjs\";\nimport { ChatCompletionStream } from \"../../../lib/ChatCompletionStream.mjs\";\nimport { parseChatCompletion, validateInputTools } from \"../../../lib/parser.mjs\";\nexport { ChatCompletionStreamingRunner, } from \"../../../lib/ChatCompletionStreamingRunner.mjs\";\nexport { ParsingFunction, ParsingToolFunction, } from \"../../../lib/RunnableFunction.mjs\";\nexport { ChatCompletionStream } from \"../../../lib/ChatCompletionStream.mjs\";\nexport { ChatCompletionRunner, } from \"../../../lib/ChatCompletionRunner.mjs\";\nexport class Completions extends APIResource {\n    parse(body, options) {\n        validateInputTools(body.tools);\n        return this._client.chat.completions\n            .create(body, {\n            ...options,\n            headers: {\n                ...options?.headers,\n                'X-Stainless-Helper-Method': 'beta.chat.completions.parse',\n            },\n        })\n            ._thenUnwrap((completion) => parseChatCompletion(completion, body));\n    }\n    runFunctions(body, options) {\n        if (body.stream) {\n            return ChatCompletionStreamingRunner.runFunctions(this._client, body, options);\n        }\n        return ChatCompletionRunner.runFunctions(this._client, body, options);\n    }\n    runTools(body, options) {\n        if (body.stream) {\n            return ChatCompletionStreamingRunner.runTools(this._client, body, options);\n        }\n        return ChatCompletionRunner.runTools(this._client, body, options);\n    }\n    /**\n     * Creates a chat completion stream\n     */\n    stream(body, options) {\n        return ChatCompletionStream.createChatCompletion(this._client, body, options);\n    }\n}\n//# sourceMappingURL=completions.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../../resource.mjs\";\nimport * as CompletionsAPI from \"./completions.mjs\";\nexport class Chat extends APIResource {\n    constructor() {\n        super(...arguments);\n        this.completions = new CompletionsAPI.Completions(this._client);\n    }\n}\n(function (Chat) {\n    Chat.Completions = CompletionsAPI.Completions;\n})(Chat || (Chat = {}));\n//# sourceMappingURL=chat.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../../resource.mjs\";\nexport class Sessions extends APIResource {\n    /**\n     * Create an ephemeral API token for use in client-side applications with the\n     * Realtime API. Can be configured with the same session parameters as the\n     * `session.update` client event.\n     *\n     * It responds with a session object, plus a `client_secret` key which contains a\n     * usable ephemeral API token that can be used to authenticate browser clients for\n     * the Realtime API.\n     */\n    create(body, options) {\n        return this._client.post('/realtime/sessions', {\n            body,\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n}\n//# sourceMappingURL=sessions.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../../resource.mjs\";\nimport * as SessionsAPI from \"./sessions.mjs\";\nimport { Sessions, } from \"./sessions.mjs\";\nexport class Realtime extends APIResource {\n    constructor() {\n        super(...arguments);\n        this.sessions = new SessionsAPI.Sessions(this._client);\n    }\n}\nRealtime.Sessions = Sessions;\n//# sourceMappingURL=realtime.mjs.map","var __classPrivateFieldGet = (this && this.__classPrivateFieldGet) || function (receiver, state, kind, f) {\n    if (kind === \"a\" && !f) throw new TypeError(\"Private accessor was defined without a getter\");\n    if (typeof state === \"function\" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError(\"Cannot read private member from an object whose class did not declare it\");\n    return kind === \"m\" ? f : kind === \"a\" ? f.call(receiver) : f ? f.value : state.get(receiver);\n};\nvar __classPrivateFieldSet = (this && this.__classPrivateFieldSet) || function (receiver, state, value, kind, f) {\n    if (kind === \"m\") throw new TypeError(\"Private method is not writable\");\n    if (kind === \"a\" && !f) throw new TypeError(\"Private accessor was defined without a setter\");\n    if (typeof state === \"function\" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError(\"Cannot write private member to an object whose class did not declare it\");\n    return (kind === \"a\" ? f.call(receiver, value) : f ? f.value = value : state.set(receiver, value)), value;\n};\nvar _AssistantStream_instances, _AssistantStream_events, _AssistantStream_runStepSnapshots, _AssistantStream_messageSnapshots, _AssistantStream_messageSnapshot, _AssistantStream_finalRun, _AssistantStream_currentContentIndex, _AssistantStream_currentContent, _AssistantStream_currentToolCallIndex, _AssistantStream_currentToolCall, _AssistantStream_currentEvent, _AssistantStream_currentRunSnapshot, _AssistantStream_currentRunStepSnapshot, _AssistantStream_addEvent, _AssistantStream_endRequest, _AssistantStream_handleMessage, _AssistantStream_handleRunStep, _AssistantStream_handleEvent, _AssistantStream_accumulateRunStep, _AssistantStream_accumulateMessage, _AssistantStream_accumulateContent, _AssistantStream_handleRun;\nimport * as Core from \"../core.mjs\";\nimport { Stream } from \"../streaming.mjs\";\nimport { APIUserAbortError, OpenAIError } from \"../error.mjs\";\nimport { EventStream } from \"./EventStream.mjs\";\nexport class AssistantStream extends EventStream {\n    constructor() {\n        super(...arguments);\n        _AssistantStream_instances.add(this);\n        //Track all events in a single list for reference\n        _AssistantStream_events.set(this, []);\n        //Used to accumulate deltas\n        //We are accumulating many types so the value here is not strict\n        _AssistantStream_runStepSnapshots.set(this, {});\n        _AssistantStream_messageSnapshots.set(this, {});\n        _AssistantStream_messageSnapshot.set(this, void 0);\n        _AssistantStream_finalRun.set(this, void 0);\n        _AssistantStream_currentContentIndex.set(this, void 0);\n        _AssistantStream_currentContent.set(this, void 0);\n        _AssistantStream_currentToolCallIndex.set(this, void 0);\n        _AssistantStream_currentToolCall.set(this, void 0);\n        //For current snapshot methods\n        _AssistantStream_currentEvent.set(this, void 0);\n        _AssistantStream_currentRunSnapshot.set(this, void 0);\n        _AssistantStream_currentRunStepSnapshot.set(this, void 0);\n    }\n    [(_AssistantStream_events = new WeakMap(), _AssistantStream_runStepSnapshots = new WeakMap(), _AssistantStream_messageSnapshots = new WeakMap(), _AssistantStream_messageSnapshot = new WeakMap(), _AssistantStream_finalRun = new WeakMap(), _AssistantStream_currentContentIndex = new WeakMap(), _AssistantStream_currentContent = new WeakMap(), _AssistantStream_currentToolCallIndex = new WeakMap(), _AssistantStream_currentToolCall = new WeakMap(), _AssistantStream_currentEvent = new WeakMap(), _AssistantStream_currentRunSnapshot = new WeakMap(), _AssistantStream_currentRunStepSnapshot = new WeakMap(), _AssistantStream_instances = new WeakSet(), Symbol.asyncIterator)]() {\n        const pushQueue = [];\n        const readQueue = [];\n        let done = false;\n        //Catch all for passing along all events\n        this.on('event', (event) => {\n            const reader = readQueue.shift();\n            if (reader) {\n                reader.resolve(event);\n            }\n            else {\n                pushQueue.push(event);\n            }\n        });\n        this.on('end', () => {\n            done = true;\n            for (const reader of readQueue) {\n                reader.resolve(undefined);\n            }\n            readQueue.length = 0;\n        });\n        this.on('abort', (err) => {\n            done = true;\n            for (const reader of readQueue) {\n                reader.reject(err);\n            }\n            readQueue.length = 0;\n        });\n        this.on('error', (err) => {\n            done = true;\n            for (const reader of readQueue) {\n                reader.reject(err);\n            }\n            readQueue.length = 0;\n        });\n        return {\n            next: async () => {\n                if (!pushQueue.length) {\n                    if (done) {\n                        return { value: undefined, done: true };\n                    }\n                    return new Promise((resolve, reject) => readQueue.push({ resolve, reject })).then((chunk) => (chunk ? { value: chunk, done: false } : { value: undefined, done: true }));\n                }\n                const chunk = pushQueue.shift();\n                return { value: chunk, done: false };\n            },\n            return: async () => {\n                this.abort();\n                return { value: undefined, done: true };\n            },\n        };\n    }\n    static fromReadableStream(stream) {\n        const runner = new AssistantStream();\n        runner._run(() => runner._fromReadableStream(stream));\n        return runner;\n    }\n    async _fromReadableStream(readableStream, options) {\n        const signal = options?.signal;\n        if (signal) {\n            if (signal.aborted)\n                this.controller.abort();\n            signal.addEventListener('abort', () => this.controller.abort());\n        }\n        this._connected();\n        const stream = Stream.fromReadableStream(readableStream, this.controller);\n        for await (const event of stream) {\n            __classPrivateFieldGet(this, _AssistantStream_instances, \"m\", _AssistantStream_addEvent).call(this, event);\n        }\n        if (stream.controller.signal?.aborted) {\n            throw new APIUserAbortError();\n        }\n        return this._addRun(__classPrivateFieldGet(this, _AssistantStream_instances, \"m\", _AssistantStream_endRequest).call(this));\n    }\n    toReadableStream() {\n        const stream = new Stream(this[Symbol.asyncIterator].bind(this), this.controller);\n        return stream.toReadableStream();\n    }\n    static createToolAssistantStream(threadId, runId, runs, params, options) {\n        const runner = new AssistantStream();\n        runner._run(() => runner._runToolAssistantStream(threadId, runId, runs, params, {\n            ...options,\n            headers: { ...options?.headers, 'X-Stainless-Helper-Method': 'stream' },\n        }));\n        return runner;\n    }\n    async _createToolAssistantStream(run, threadId, runId, params, options) {\n        const signal = options?.signal;\n        if (signal) {\n            if (signal.aborted)\n                this.controller.abort();\n            signal.addEventListener('abort', () => this.controller.abort());\n        }\n        const body = { ...params, stream: true };\n        const stream = await run.submitToolOutputs(threadId, runId, body, {\n            ...options,\n            signal: this.controller.signal,\n        });\n        this._connected();\n        for await (const event of stream) {\n            __classPrivateFieldGet(this, _AssistantStream_instances, \"m\", _AssistantStream_addEvent).call(this, event);\n        }\n        if (stream.controller.signal?.aborted) {\n            throw new APIUserAbortError();\n        }\n        return this._addRun(__classPrivateFieldGet(this, _AssistantStream_instances, \"m\", _AssistantStream_endRequest).call(this));\n    }\n    static createThreadAssistantStream(params, thread, options) {\n        const runner = new AssistantStream();\n        runner._run(() => runner._threadAssistantStream(params, thread, {\n            ...options,\n            headers: { ...options?.headers, 'X-Stainless-Helper-Method': 'stream' },\n        }));\n        return runner;\n    }\n    static createAssistantStream(threadId, runs, params, options) {\n        const runner = new AssistantStream();\n        runner._run(() => runner._runAssistantStream(threadId, runs, params, {\n            ...options,\n            headers: { ...options?.headers, 'X-Stainless-Helper-Method': 'stream' },\n        }));\n        return runner;\n    }\n    currentEvent() {\n        return __classPrivateFieldGet(this, _AssistantStream_currentEvent, \"f\");\n    }\n    currentRun() {\n        return __classPrivateFieldGet(this, _AssistantStream_currentRunSnapshot, \"f\");\n    }\n    currentMessageSnapshot() {\n        return __classPrivateFieldGet(this, _AssistantStream_messageSnapshot, \"f\");\n    }\n    currentRunStepSnapshot() {\n        return __classPrivateFieldGet(this, _AssistantStream_currentRunStepSnapshot, \"f\");\n    }\n    async finalRunSteps() {\n        await this.done();\n        return Object.values(__classPrivateFieldGet(this, _AssistantStream_runStepSnapshots, \"f\"));\n    }\n    async finalMessages() {\n        await this.done();\n        return Object.values(__classPrivateFieldGet(this, _AssistantStream_messageSnapshots, \"f\"));\n    }\n    async finalRun() {\n        await this.done();\n        if (!__classPrivateFieldGet(this, _AssistantStream_finalRun, \"f\"))\n            throw Error('Final run was not received.');\n        return __classPrivateFieldGet(this, _AssistantStream_finalRun, \"f\");\n    }\n    async _createThreadAssistantStream(thread, params, options) {\n        const signal = options?.signal;\n        if (signal) {\n            if (signal.aborted)\n                this.controller.abort();\n            signal.addEventListener('abort', () => this.controller.abort());\n        }\n        const body = { ...params, stream: true };\n        const stream = await thread.createAndRun(body, { ...options, signal: this.controller.signal });\n        this._connected();\n        for await (const event of stream) {\n            __classPrivateFieldGet(this, _AssistantStream_instances, \"m\", _AssistantStream_addEvent).call(this, event);\n        }\n        if (stream.controller.signal?.aborted) {\n            throw new APIUserAbortError();\n        }\n        return this._addRun(__classPrivateFieldGet(this, _AssistantStream_instances, \"m\", _AssistantStream_endRequest).call(this));\n    }\n    async _createAssistantStream(run, threadId, params, options) {\n        const signal = options?.signal;\n        if (signal) {\n            if (signal.aborted)\n                this.controller.abort();\n            signal.addEventListener('abort', () => this.controller.abort());\n        }\n        const body = { ...params, stream: true };\n        const stream = await run.create(threadId, body, { ...options, signal: this.controller.signal });\n        this._connected();\n        for await (const event of stream) {\n            __classPrivateFieldGet(this, _AssistantStream_instances, \"m\", _AssistantStream_addEvent).call(this, event);\n        }\n        if (stream.controller.signal?.aborted) {\n            throw new APIUserAbortError();\n        }\n        return this._addRun(__classPrivateFieldGet(this, _AssistantStream_instances, \"m\", _AssistantStream_endRequest).call(this));\n    }\n    static accumulateDelta(acc, delta) {\n        for (const [key, deltaValue] of Object.entries(delta)) {\n            if (!acc.hasOwnProperty(key)) {\n                acc[key] = deltaValue;\n                continue;\n            }\n            let accValue = acc[key];\n            if (accValue === null || accValue === undefined) {\n                acc[key] = deltaValue;\n                continue;\n            }\n            // We don't accumulate these special properties\n            if (key === 'index' || key === 'type') {\n                acc[key] = deltaValue;\n                continue;\n            }\n            // Type-specific accumulation logic\n            if (typeof accValue === 'string' && typeof deltaValue === 'string') {\n                accValue += deltaValue;\n            }\n            else if (typeof accValue === 'number' && typeof deltaValue === 'number') {\n                accValue += deltaValue;\n            }\n            else if (Core.isObj(accValue) && Core.isObj(deltaValue)) {\n                accValue = this.accumulateDelta(accValue, deltaValue);\n            }\n            else if (Array.isArray(accValue) && Array.isArray(deltaValue)) {\n                if (accValue.every((x) => typeof x === 'string' || typeof x === 'number')) {\n                    accValue.push(...deltaValue); // Use spread syntax for efficient addition\n                    continue;\n                }\n                for (const deltaEntry of deltaValue) {\n                    if (!Core.isObj(deltaEntry)) {\n                        throw new Error(`Expected array delta entry to be an object but got: ${deltaEntry}`);\n                    }\n                    const index = deltaEntry['index'];\n                    if (index == null) {\n                        console.error(deltaEntry);\n                        throw new Error('Expected array delta entry to have an `index` property');\n                    }\n                    if (typeof index !== 'number') {\n                        throw new Error(`Expected array delta entry \\`index\\` property to be a number but got ${index}`);\n                    }\n                    const accEntry = accValue[index];\n                    if (accEntry == null) {\n                        accValue.push(deltaEntry);\n                    }\n                    else {\n                        accValue[index] = this.accumulateDelta(accEntry, deltaEntry);\n                    }\n                }\n                continue;\n            }\n            else {\n                throw Error(`Unhandled record type: ${key}, deltaValue: ${deltaValue}, accValue: ${accValue}`);\n            }\n            acc[key] = accValue;\n        }\n        return acc;\n    }\n    _addRun(run) {\n        return run;\n    }\n    async _threadAssistantStream(params, thread, options) {\n        return await this._createThreadAssistantStream(thread, params, options);\n    }\n    async _runAssistantStream(threadId, runs, params, options) {\n        return await this._createAssistantStream(runs, threadId, params, options);\n    }\n    async _runToolAssistantStream(threadId, runId, runs, params, options) {\n        return await this._createToolAssistantStream(runs, threadId, runId, params, options);\n    }\n}\n_AssistantStream_addEvent = function _AssistantStream_addEvent(event) {\n    if (this.ended)\n        return;\n    __classPrivateFieldSet(this, _AssistantStream_currentEvent, event, \"f\");\n    __classPrivateFieldGet(this, _AssistantStream_instances, \"m\", _AssistantStream_handleEvent).call(this, event);\n    switch (event.event) {\n        case 'thread.created':\n            //No action on this event.\n            break;\n        case 'thread.run.created':\n        case 'thread.run.queued':\n        case 'thread.run.in_progress':\n        case 'thread.run.requires_action':\n        case 'thread.run.completed':\n        case 'thread.run.incomplete':\n        case 'thread.run.failed':\n        case 'thread.run.cancelling':\n        case 'thread.run.cancelled':\n        case 'thread.run.expired':\n            __classPrivateFieldGet(this, _AssistantStream_instances, \"m\", _AssistantStream_handleRun).call(this, event);\n            break;\n        case 'thread.run.step.created':\n        case 'thread.run.step.in_progress':\n        case 'thread.run.step.delta':\n        case 'thread.run.step.completed':\n        case 'thread.run.step.failed':\n        case 'thread.run.step.cancelled':\n        case 'thread.run.step.expired':\n            __classPrivateFieldGet(this, _AssistantStream_instances, \"m\", _AssistantStream_handleRunStep).call(this, event);\n            break;\n        case 'thread.message.created':\n        case 'thread.message.in_progress':\n        case 'thread.message.delta':\n        case 'thread.message.completed':\n        case 'thread.message.incomplete':\n            __classPrivateFieldGet(this, _AssistantStream_instances, \"m\", _AssistantStream_handleMessage).call(this, event);\n            break;\n        case 'error':\n            //This is included for completeness, but errors are processed in the SSE event processing so this should not occur\n            throw new Error('Encountered an error event in event processing - errors should be processed earlier');\n        default:\n            assertNever(event);\n    }\n}, _AssistantStream_endRequest = function _AssistantStream_endRequest() {\n    if (this.ended) {\n        throw new OpenAIError(`stream has ended, this shouldn't happen`);\n    }\n    if (!__classPrivateFieldGet(this, _AssistantStream_finalRun, \"f\"))\n        throw Error('Final run has not been received');\n    return __classPrivateFieldGet(this, _AssistantStream_finalRun, \"f\");\n}, _AssistantStream_handleMessage = function _AssistantStream_handleMessage(event) {\n    const [accumulatedMessage, newContent] = __classPrivateFieldGet(this, _AssistantStream_instances, \"m\", _AssistantStream_accumulateMessage).call(this, event, __classPrivateFieldGet(this, _AssistantStream_messageSnapshot, \"f\"));\n    __classPrivateFieldSet(this, _AssistantStream_messageSnapshot, accumulatedMessage, \"f\");\n    __classPrivateFieldGet(this, _AssistantStream_messageSnapshots, \"f\")[accumulatedMessage.id] = accumulatedMessage;\n    for (const content of newContent) {\n        const snapshotContent = accumulatedMessage.content[content.index];\n        if (snapshotContent?.type == 'text') {\n            this._emit('textCreated', snapshotContent.text);\n        }\n    }\n    switch (event.event) {\n        case 'thread.message.created':\n            this._emit('messageCreated', event.data);\n            break;\n        case 'thread.message.in_progress':\n            break;\n        case 'thread.message.delta':\n            this._emit('messageDelta', event.data.delta, accumulatedMessage);\n            if (event.data.delta.content) {\n                for (const content of event.data.delta.content) {\n                    //If it is text delta, emit a text delta event\n                    if (content.type == 'text' && content.text) {\n                        let textDelta = content.text;\n                        let snapshot = accumulatedMessage.content[content.index];\n                        if (snapshot && snapshot.type == 'text') {\n                            this._emit('textDelta', textDelta, snapshot.text);\n                        }\n                        else {\n                            throw Error('The snapshot associated with this text delta is not text or missing');\n                        }\n                    }\n                    if (content.index != __classPrivateFieldGet(this, _AssistantStream_currentContentIndex, \"f\")) {\n                        //See if we have in progress content\n                        if (__classPrivateFieldGet(this, _AssistantStream_currentContent, \"f\")) {\n                            switch (__classPrivateFieldGet(this, _AssistantStream_currentContent, \"f\").type) {\n                                case 'text':\n                                    this._emit('textDone', __classPrivateFieldGet(this, _AssistantStream_currentContent, \"f\").text, __classPrivateFieldGet(this, _AssistantStream_messageSnapshot, \"f\"));\n                                    break;\n                                case 'image_file':\n                                    this._emit('imageFileDone', __classPrivateFieldGet(this, _AssistantStream_currentContent, \"f\").image_file, __classPrivateFieldGet(this, _AssistantStream_messageSnapshot, \"f\"));\n                                    break;\n                            }\n                        }\n                        __classPrivateFieldSet(this, _AssistantStream_currentContentIndex, content.index, \"f\");\n                    }\n                    __classPrivateFieldSet(this, _AssistantStream_currentContent, accumulatedMessage.content[content.index], \"f\");\n                }\n            }\n            break;\n        case 'thread.message.completed':\n        case 'thread.message.incomplete':\n            //We emit the latest content we were working on on completion (including incomplete)\n            if (__classPrivateFieldGet(this, _AssistantStream_currentContentIndex, \"f\") !== undefined) {\n                const currentContent = event.data.content[__classPrivateFieldGet(this, _AssistantStream_currentContentIndex, \"f\")];\n                if (currentContent) {\n                    switch (currentContent.type) {\n                        case 'image_file':\n                            this._emit('imageFileDone', currentContent.image_file, __classPrivateFieldGet(this, _AssistantStream_messageSnapshot, \"f\"));\n                            break;\n                        case 'text':\n                            this._emit('textDone', currentContent.text, __classPrivateFieldGet(this, _AssistantStream_messageSnapshot, \"f\"));\n                            break;\n                    }\n                }\n            }\n            if (__classPrivateFieldGet(this, _AssistantStream_messageSnapshot, \"f\")) {\n                this._emit('messageDone', event.data);\n            }\n            __classPrivateFieldSet(this, _AssistantStream_messageSnapshot, undefined, \"f\");\n    }\n}, _AssistantStream_handleRunStep = function _AssistantStream_handleRunStep(event) {\n    const accumulatedRunStep = __classPrivateFieldGet(this, _AssistantStream_instances, \"m\", _AssistantStream_accumulateRunStep).call(this, event);\n    __classPrivateFieldSet(this, _AssistantStream_currentRunStepSnapshot, accumulatedRunStep, \"f\");\n    switch (event.event) {\n        case 'thread.run.step.created':\n            this._emit('runStepCreated', event.data);\n            break;\n        case 'thread.run.step.delta':\n            const delta = event.data.delta;\n            if (delta.step_details &&\n                delta.step_details.type == 'tool_calls' &&\n                delta.step_details.tool_calls &&\n                accumulatedRunStep.step_details.type == 'tool_calls') {\n                for (const toolCall of delta.step_details.tool_calls) {\n                    if (toolCall.index == __classPrivateFieldGet(this, _AssistantStream_currentToolCallIndex, \"f\")) {\n                        this._emit('toolCallDelta', toolCall, accumulatedRunStep.step_details.tool_calls[toolCall.index]);\n                    }\n                    else {\n                        if (__classPrivateFieldGet(this, _AssistantStream_currentToolCall, \"f\")) {\n                            this._emit('toolCallDone', __classPrivateFieldGet(this, _AssistantStream_currentToolCall, \"f\"));\n                        }\n                        __classPrivateFieldSet(this, _AssistantStream_currentToolCallIndex, toolCall.index, \"f\");\n                        __classPrivateFieldSet(this, _AssistantStream_currentToolCall, accumulatedRunStep.step_details.tool_calls[toolCall.index], \"f\");\n                        if (__classPrivateFieldGet(this, _AssistantStream_currentToolCall, \"f\"))\n                            this._emit('toolCallCreated', __classPrivateFieldGet(this, _AssistantStream_currentToolCall, \"f\"));\n                    }\n                }\n            }\n            this._emit('runStepDelta', event.data.delta, accumulatedRunStep);\n            break;\n        case 'thread.run.step.completed':\n        case 'thread.run.step.failed':\n        case 'thread.run.step.cancelled':\n        case 'thread.run.step.expired':\n            __classPrivateFieldSet(this, _AssistantStream_currentRunStepSnapshot, undefined, \"f\");\n            const details = event.data.step_details;\n            if (details.type == 'tool_calls') {\n                if (__classPrivateFieldGet(this, _AssistantStream_currentToolCall, \"f\")) {\n                    this._emit('toolCallDone', __classPrivateFieldGet(this, _AssistantStream_currentToolCall, \"f\"));\n                    __classPrivateFieldSet(this, _AssistantStream_currentToolCall, undefined, \"f\");\n                }\n            }\n            this._emit('runStepDone', event.data, accumulatedRunStep);\n            break;\n        case 'thread.run.step.in_progress':\n            break;\n    }\n}, _AssistantStream_handleEvent = function _AssistantStream_handleEvent(event) {\n    __classPrivateFieldGet(this, _AssistantStream_events, \"f\").push(event);\n    this._emit('event', event);\n}, _AssistantStream_accumulateRunStep = function _AssistantStream_accumulateRunStep(event) {\n    switch (event.event) {\n        case 'thread.run.step.created':\n            __classPrivateFieldGet(this, _AssistantStream_runStepSnapshots, \"f\")[event.data.id] = event.data;\n            return event.data;\n        case 'thread.run.step.delta':\n            let snapshot = __classPrivateFieldGet(this, _AssistantStream_runStepSnapshots, \"f\")[event.data.id];\n            if (!snapshot) {\n                throw Error('Received a RunStepDelta before creation of a snapshot');\n            }\n            let data = event.data;\n            if (data.delta) {\n                const accumulated = AssistantStream.accumulateDelta(snapshot, data.delta);\n                __classPrivateFieldGet(this, _AssistantStream_runStepSnapshots, \"f\")[event.data.id] = accumulated;\n            }\n            return __classPrivateFieldGet(this, _AssistantStream_runStepSnapshots, \"f\")[event.data.id];\n        case 'thread.run.step.completed':\n        case 'thread.run.step.failed':\n        case 'thread.run.step.cancelled':\n        case 'thread.run.step.expired':\n        case 'thread.run.step.in_progress':\n            __classPrivateFieldGet(this, _AssistantStream_runStepSnapshots, \"f\")[event.data.id] = event.data;\n            break;\n    }\n    if (__classPrivateFieldGet(this, _AssistantStream_runStepSnapshots, \"f\")[event.data.id])\n        return __classPrivateFieldGet(this, _AssistantStream_runStepSnapshots, \"f\")[event.data.id];\n    throw new Error('No snapshot available');\n}, _AssistantStream_accumulateMessage = function _AssistantStream_accumulateMessage(event, snapshot) {\n    let newContent = [];\n    switch (event.event) {\n        case 'thread.message.created':\n            //On creation the snapshot is just the initial message\n            return [event.data, newContent];\n        case 'thread.message.delta':\n            if (!snapshot) {\n                throw Error('Received a delta with no existing snapshot (there should be one from message creation)');\n            }\n            let data = event.data;\n            //If this delta does not have content, nothing to process\n            if (data.delta.content) {\n                for (const contentElement of data.delta.content) {\n                    if (contentElement.index in snapshot.content) {\n                        let currentContent = snapshot.content[contentElement.index];\n                        snapshot.content[contentElement.index] = __classPrivateFieldGet(this, _AssistantStream_instances, \"m\", _AssistantStream_accumulateContent).call(this, contentElement, currentContent);\n                    }\n                    else {\n                        snapshot.content[contentElement.index] = contentElement;\n                        // This is a new element\n                        newContent.push(contentElement);\n                    }\n                }\n            }\n            return [snapshot, newContent];\n        case 'thread.message.in_progress':\n        case 'thread.message.completed':\n        case 'thread.message.incomplete':\n            //No changes on other thread events\n            if (snapshot) {\n                return [snapshot, newContent];\n            }\n            else {\n                throw Error('Received thread message event with no existing snapshot');\n            }\n    }\n    throw Error('Tried to accumulate a non-message event');\n}, _AssistantStream_accumulateContent = function _AssistantStream_accumulateContent(contentElement, currentContent) {\n    return AssistantStream.accumulateDelta(currentContent, contentElement);\n}, _AssistantStream_handleRun = function _AssistantStream_handleRun(event) {\n    __classPrivateFieldSet(this, _AssistantStream_currentRunSnapshot, event.data, \"f\");\n    switch (event.event) {\n        case 'thread.run.created':\n            break;\n        case 'thread.run.queued':\n            break;\n        case 'thread.run.in_progress':\n            break;\n        case 'thread.run.requires_action':\n        case 'thread.run.cancelled':\n        case 'thread.run.failed':\n        case 'thread.run.completed':\n        case 'thread.run.expired':\n            __classPrivateFieldSet(this, _AssistantStream_finalRun, event.data, \"f\");\n            if (__classPrivateFieldGet(this, _AssistantStream_currentToolCall, \"f\")) {\n                this._emit('toolCallDone', __classPrivateFieldGet(this, _AssistantStream_currentToolCall, \"f\"));\n                __classPrivateFieldSet(this, _AssistantStream_currentToolCall, undefined, \"f\");\n            }\n            break;\n        case 'thread.run.cancelling':\n            break;\n    }\n};\nfunction assertNever(_x) { }\n//# sourceMappingURL=AssistantStream.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../../resource.mjs\";\nimport { isRequestOptions } from \"../../../core.mjs\";\nimport { CursorPage } from \"../../../pagination.mjs\";\nexport class Messages extends APIResource {\n    /**\n     * Create a message.\n     */\n    create(threadId, body, options) {\n        return this._client.post(`/threads/${threadId}/messages`, {\n            body,\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    /**\n     * Retrieve a message.\n     */\n    retrieve(threadId, messageId, options) {\n        return this._client.get(`/threads/${threadId}/messages/${messageId}`, {\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    /**\n     * Modifies a message.\n     */\n    update(threadId, messageId, body, options) {\n        return this._client.post(`/threads/${threadId}/messages/${messageId}`, {\n            body,\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    list(threadId, query = {}, options) {\n        if (isRequestOptions(query)) {\n            return this.list(threadId, {}, query);\n        }\n        return this._client.getAPIList(`/threads/${threadId}/messages`, MessagesPage, {\n            query,\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    /**\n     * Deletes a message.\n     */\n    del(threadId, messageId, options) {\n        return this._client.delete(`/threads/${threadId}/messages/${messageId}`, {\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n}\nexport class MessagesPage extends CursorPage {\n}\nMessages.MessagesPage = MessagesPage;\n//# sourceMappingURL=messages.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../../../resource.mjs\";\nimport { isRequestOptions } from \"../../../../core.mjs\";\nimport { CursorPage } from \"../../../../pagination.mjs\";\nexport class Steps extends APIResource {\n    retrieve(threadId, runId, stepId, query = {}, options) {\n        if (isRequestOptions(query)) {\n            return this.retrieve(threadId, runId, stepId, {}, query);\n        }\n        return this._client.get(`/threads/${threadId}/runs/${runId}/steps/${stepId}`, {\n            query,\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    list(threadId, runId, query = {}, options) {\n        if (isRequestOptions(query)) {\n            return this.list(threadId, runId, {}, query);\n        }\n        return this._client.getAPIList(`/threads/${threadId}/runs/${runId}/steps`, RunStepsPage, {\n            query,\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n}\nexport class RunStepsPage extends CursorPage {\n}\nSteps.RunStepsPage = RunStepsPage;\n//# sourceMappingURL=steps.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../../../resource.mjs\";\nimport { isRequestOptions } from \"../../../../core.mjs\";\nimport { AssistantStream } from \"../../../../lib/AssistantStream.mjs\";\nimport { sleep } from \"../../../../core.mjs\";\nimport * as StepsAPI from \"./steps.mjs\";\nimport { RunStepsPage, Steps, } from \"./steps.mjs\";\nimport { CursorPage } from \"../../../../pagination.mjs\";\nexport class Runs extends APIResource {\n    constructor() {\n        super(...arguments);\n        this.steps = new StepsAPI.Steps(this._client);\n    }\n    create(threadId, params, options) {\n        const { include, ...body } = params;\n        return this._client.post(`/threads/${threadId}/runs`, {\n            query: { include },\n            body,\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n            stream: params.stream ?? false,\n        });\n    }\n    /**\n     * Retrieves a run.\n     */\n    retrieve(threadId, runId, options) {\n        return this._client.get(`/threads/${threadId}/runs/${runId}`, {\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    /**\n     * Modifies a run.\n     */\n    update(threadId, runId, body, options) {\n        return this._client.post(`/threads/${threadId}/runs/${runId}`, {\n            body,\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    list(threadId, query = {}, options) {\n        if (isRequestOptions(query)) {\n            return this.list(threadId, {}, query);\n        }\n        return this._client.getAPIList(`/threads/${threadId}/runs`, RunsPage, {\n            query,\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    /**\n     * Cancels a run that is `in_progress`.\n     */\n    cancel(threadId, runId, options) {\n        return this._client.post(`/threads/${threadId}/runs/${runId}/cancel`, {\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    /**\n     * A helper to create a run an poll for a terminal state. More information on Run\n     * lifecycles can be found here:\n     * https://platform.openai.com/docs/assistants/how-it-works/runs-and-run-steps\n     */\n    async createAndPoll(threadId, body, options) {\n        const run = await this.create(threadId, body, options);\n        return await this.poll(threadId, run.id, options);\n    }\n    /**\n     * Create a Run stream\n     *\n     * @deprecated use `stream` instead\n     */\n    createAndStream(threadId, body, options) {\n        return AssistantStream.createAssistantStream(threadId, this._client.beta.threads.runs, body, options);\n    }\n    /**\n     * A helper to poll a run status until it reaches a terminal state. More\n     * information on Run lifecycles can be found here:\n     * https://platform.openai.com/docs/assistants/how-it-works/runs-and-run-steps\n     */\n    async poll(threadId, runId, options) {\n        const headers = { ...options?.headers, 'X-Stainless-Poll-Helper': 'true' };\n        if (options?.pollIntervalMs) {\n            headers['X-Stainless-Custom-Poll-Interval'] = options.pollIntervalMs.toString();\n        }\n        while (true) {\n            const { data: run, response } = await this.retrieve(threadId, runId, {\n                ...options,\n                headers: { ...options?.headers, ...headers },\n            }).withResponse();\n            switch (run.status) {\n                //If we are in any sort of intermediate state we poll\n                case 'queued':\n                case 'in_progress':\n                case 'cancelling':\n                    let sleepInterval = 5000;\n                    if (options?.pollIntervalMs) {\n                        sleepInterval = options.pollIntervalMs;\n                    }\n                    else {\n                        const headerInterval = response.headers.get('openai-poll-after-ms');\n                        if (headerInterval) {\n                            const headerIntervalMs = parseInt(headerInterval);\n                            if (!isNaN(headerIntervalMs)) {\n                                sleepInterval = headerIntervalMs;\n                            }\n                        }\n                    }\n                    await sleep(sleepInterval);\n                    break;\n                //We return the run in any terminal state.\n                case 'requires_action':\n                case 'incomplete':\n                case 'cancelled':\n                case 'completed':\n                case 'failed':\n                case 'expired':\n                    return run;\n            }\n        }\n    }\n    /**\n     * Create a Run stream\n     */\n    stream(threadId, body, options) {\n        return AssistantStream.createAssistantStream(threadId, this._client.beta.threads.runs, body, options);\n    }\n    submitToolOutputs(threadId, runId, body, options) {\n        return this._client.post(`/threads/${threadId}/runs/${runId}/submit_tool_outputs`, {\n            body,\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n            stream: body.stream ?? false,\n        });\n    }\n    /**\n     * A helper to submit a tool output to a run and poll for a terminal run state.\n     * More information on Run lifecycles can be found here:\n     * https://platform.openai.com/docs/assistants/how-it-works/runs-and-run-steps\n     */\n    async submitToolOutputsAndPoll(threadId, runId, body, options) {\n        const run = await this.submitToolOutputs(threadId, runId, body, options);\n        return await this.poll(threadId, run.id, options);\n    }\n    /**\n     * Submit the tool outputs from a previous run and stream the run to a terminal\n     * state. More information on Run lifecycles can be found here:\n     * https://platform.openai.com/docs/assistants/how-it-works/runs-and-run-steps\n     */\n    submitToolOutputsStream(threadId, runId, body, options) {\n        return AssistantStream.createToolAssistantStream(threadId, runId, this._client.beta.threads.runs, body, options);\n    }\n}\nexport class RunsPage extends CursorPage {\n}\nRuns.RunsPage = RunsPage;\nRuns.Steps = Steps;\nRuns.RunStepsPage = RunStepsPage;\n//# sourceMappingURL=runs.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../../resource.mjs\";\nimport { isRequestOptions } from \"../../../core.mjs\";\nimport { AssistantStream } from \"../../../lib/AssistantStream.mjs\";\nimport * as MessagesAPI from \"./messages.mjs\";\nimport { Messages, MessagesPage, } from \"./messages.mjs\";\nimport * as RunsAPI from \"./runs/runs.mjs\";\nimport { Runs, RunsPage, } from \"./runs/runs.mjs\";\nexport class Threads extends APIResource {\n    constructor() {\n        super(...arguments);\n        this.runs = new RunsAPI.Runs(this._client);\n        this.messages = new MessagesAPI.Messages(this._client);\n    }\n    create(body = {}, options) {\n        if (isRequestOptions(body)) {\n            return this.create({}, body);\n        }\n        return this._client.post('/threads', {\n            body,\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    /**\n     * Retrieves a thread.\n     */\n    retrieve(threadId, options) {\n        return this._client.get(`/threads/${threadId}`, {\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    /**\n     * Modifies a thread.\n     */\n    update(threadId, body, options) {\n        return this._client.post(`/threads/${threadId}`, {\n            body,\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    /**\n     * Delete a thread.\n     */\n    del(threadId, options) {\n        return this._client.delete(`/threads/${threadId}`, {\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    createAndRun(body, options) {\n        return this._client.post('/threads/runs', {\n            body,\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n            stream: body.stream ?? false,\n        });\n    }\n    /**\n     * A helper to create a thread, start a run and then poll for a terminal state.\n     * More information on Run lifecycles can be found here:\n     * https://platform.openai.com/docs/assistants/how-it-works/runs-and-run-steps\n     */\n    async createAndRunPoll(body, options) {\n        const run = await this.createAndRun(body, options);\n        return await this.runs.poll(run.thread_id, run.id, options);\n    }\n    /**\n     * Create a thread and stream the run back\n     */\n    createAndRunStream(body, options) {\n        return AssistantStream.createThreadAssistantStream(body, this._client.beta.threads, options);\n    }\n}\nThreads.Runs = Runs;\nThreads.RunsPage = RunsPage;\nThreads.Messages = Messages;\nThreads.MessagesPage = MessagesPage;\n//# sourceMappingURL=threads.mjs.map","/**\n * Like `Promise.allSettled()` but throws an error if any promises are rejected.\n */\nexport const allSettledWithThrow = async (promises) => {\n    const results = await Promise.allSettled(promises);\n    const rejected = results.filter((result) => result.status === 'rejected');\n    if (rejected.length) {\n        for (const result of rejected) {\n            console.error(result.reason);\n        }\n        throw new Error(`${rejected.length} promise(s) failed - see the above errors`);\n    }\n    // Note: TS was complaining about using `.filter().map()` here for some reason\n    const values = [];\n    for (const result of results) {\n        if (result.status === 'fulfilled') {\n            values.push(result.value);\n        }\n    }\n    return values;\n};\n//# sourceMappingURL=Util.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../../resource.mjs\";\nimport { sleep, isRequestOptions } from \"../../../core.mjs\";\nimport { CursorPage } from \"../../../pagination.mjs\";\nexport class Files extends APIResource {\n    /**\n     * Create a vector store file by attaching a\n     * [File](https://platform.openai.com/docs/api-reference/files) to a\n     * [vector store](https://platform.openai.com/docs/api-reference/vector-stores/object).\n     */\n    create(vectorStoreId, body, options) {\n        return this._client.post(`/vector_stores/${vectorStoreId}/files`, {\n            body,\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    /**\n     * Retrieves a vector store file.\n     */\n    retrieve(vectorStoreId, fileId, options) {\n        return this._client.get(`/vector_stores/${vectorStoreId}/files/${fileId}`, {\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    list(vectorStoreId, query = {}, options) {\n        if (isRequestOptions(query)) {\n            return this.list(vectorStoreId, {}, query);\n        }\n        return this._client.getAPIList(`/vector_stores/${vectorStoreId}/files`, VectorStoreFilesPage, {\n            query,\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    /**\n     * Delete a vector store file. This will remove the file from the vector store but\n     * the file itself will not be deleted. To delete the file, use the\n     * [delete file](https://platform.openai.com/docs/api-reference/files/delete)\n     * endpoint.\n     */\n    del(vectorStoreId, fileId, options) {\n        return this._client.delete(`/vector_stores/${vectorStoreId}/files/${fileId}`, {\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    /**\n     * Attach a file to the given vector store and wait for it to be processed.\n     */\n    async createAndPoll(vectorStoreId, body, options) {\n        const file = await this.create(vectorStoreId, body, options);\n        return await this.poll(vectorStoreId, file.id, options);\n    }\n    /**\n     * Wait for the vector store file to finish processing.\n     *\n     * Note: this will return even if the file failed to process, you need to check\n     * file.last_error and file.status to handle these cases\n     */\n    async poll(vectorStoreId, fileId, options) {\n        const headers = { ...options?.headers, 'X-Stainless-Poll-Helper': 'true' };\n        if (options?.pollIntervalMs) {\n            headers['X-Stainless-Custom-Poll-Interval'] = options.pollIntervalMs.toString();\n        }\n        while (true) {\n            const fileResponse = await this.retrieve(vectorStoreId, fileId, {\n                ...options,\n                headers,\n            }).withResponse();\n            const file = fileResponse.data;\n            switch (file.status) {\n                case 'in_progress':\n                    let sleepInterval = 5000;\n                    if (options?.pollIntervalMs) {\n                        sleepInterval = options.pollIntervalMs;\n                    }\n                    else {\n                        const headerInterval = fileResponse.response.headers.get('openai-poll-after-ms');\n                        if (headerInterval) {\n                            const headerIntervalMs = parseInt(headerInterval);\n                            if (!isNaN(headerIntervalMs)) {\n                                sleepInterval = headerIntervalMs;\n                            }\n                        }\n                    }\n                    await sleep(sleepInterval);\n                    break;\n                case 'failed':\n                case 'completed':\n                    return file;\n            }\n        }\n    }\n    /**\n     * Upload a file to the `files` API and then attach it to the given vector store.\n     *\n     * Note the file will be asynchronously processed (you can use the alternative\n     * polling helper method to wait for processing to complete).\n     */\n    async upload(vectorStoreId, file, options) {\n        const fileInfo = await this._client.files.create({ file: file, purpose: 'assistants' }, options);\n        return this.create(vectorStoreId, { file_id: fileInfo.id }, options);\n    }\n    /**\n     * Add a file to a vector store and poll until processing is complete.\n     */\n    async uploadAndPoll(vectorStoreId, file, options) {\n        const fileInfo = await this.upload(vectorStoreId, file, options);\n        return await this.poll(vectorStoreId, fileInfo.id, options);\n    }\n}\nexport class VectorStoreFilesPage extends CursorPage {\n}\nFiles.VectorStoreFilesPage = VectorStoreFilesPage;\n//# sourceMappingURL=files.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../../resource.mjs\";\nimport { isRequestOptions } from \"../../../core.mjs\";\nimport { sleep } from \"../../../core.mjs\";\nimport { allSettledWithThrow } from \"../../../lib/Util.mjs\";\nimport { VectorStoreFilesPage } from \"./files.mjs\";\nexport class FileBatches extends APIResource {\n    /**\n     * Create a vector store file batch.\n     */\n    create(vectorStoreId, body, options) {\n        return this._client.post(`/vector_stores/${vectorStoreId}/file_batches`, {\n            body,\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    /**\n     * Retrieves a vector store file batch.\n     */\n    retrieve(vectorStoreId, batchId, options) {\n        return this._client.get(`/vector_stores/${vectorStoreId}/file_batches/${batchId}`, {\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    /**\n     * Cancel a vector store file batch. This attempts to cancel the processing of\n     * files in this batch as soon as possible.\n     */\n    cancel(vectorStoreId, batchId, options) {\n        return this._client.post(`/vector_stores/${vectorStoreId}/file_batches/${batchId}/cancel`, {\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    /**\n     * Create a vector store batch and poll until all files have been processed.\n     */\n    async createAndPoll(vectorStoreId, body, options) {\n        const batch = await this.create(vectorStoreId, body);\n        return await this.poll(vectorStoreId, batch.id, options);\n    }\n    listFiles(vectorStoreId, batchId, query = {}, options) {\n        if (isRequestOptions(query)) {\n            return this.listFiles(vectorStoreId, batchId, {}, query);\n        }\n        return this._client.getAPIList(`/vector_stores/${vectorStoreId}/file_batches/${batchId}/files`, VectorStoreFilesPage, { query, ...options, headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers } });\n    }\n    /**\n     * Wait for the given file batch to be processed.\n     *\n     * Note: this will return even if one of the files failed to process, you need to\n     * check batch.file_counts.failed_count to handle this case.\n     */\n    async poll(vectorStoreId, batchId, options) {\n        const headers = { ...options?.headers, 'X-Stainless-Poll-Helper': 'true' };\n        if (options?.pollIntervalMs) {\n            headers['X-Stainless-Custom-Poll-Interval'] = options.pollIntervalMs.toString();\n        }\n        while (true) {\n            const { data: batch, response } = await this.retrieve(vectorStoreId, batchId, {\n                ...options,\n                headers,\n            }).withResponse();\n            switch (batch.status) {\n                case 'in_progress':\n                    let sleepInterval = 5000;\n                    if (options?.pollIntervalMs) {\n                        sleepInterval = options.pollIntervalMs;\n                    }\n                    else {\n                        const headerInterval = response.headers.get('openai-poll-after-ms');\n                        if (headerInterval) {\n                            const headerIntervalMs = parseInt(headerInterval);\n                            if (!isNaN(headerIntervalMs)) {\n                                sleepInterval = headerIntervalMs;\n                            }\n                        }\n                    }\n                    await sleep(sleepInterval);\n                    break;\n                case 'failed':\n                case 'cancelled':\n                case 'completed':\n                    return batch;\n            }\n        }\n    }\n    /**\n     * Uploads the given files concurrently and then creates a vector store file batch.\n     *\n     * The concurrency limit is configurable using the `maxConcurrency` parameter.\n     */\n    async uploadAndPoll(vectorStoreId, { files, fileIds = [] }, options) {\n        if (files == null || files.length == 0) {\n            throw new Error(`No \\`files\\` provided to process. If you've already uploaded files you should use \\`.createAndPoll()\\` instead`);\n        }\n        const configuredConcurrency = options?.maxConcurrency ?? 5;\n        // We cap the number of workers at the number of files (so we don't start any unnecessary workers)\n        const concurrencyLimit = Math.min(configuredConcurrency, files.length);\n        const client = this._client;\n        const fileIterator = files.values();\n        const allFileIds = [...fileIds];\n        // This code is based on this design. The libraries don't accommodate our environment limits.\n        // https://stackoverflow.com/questions/40639432/what-is-the-best-way-to-limit-concurrency-when-using-es6s-promise-all\n        async function processFiles(iterator) {\n            for (let item of iterator) {\n                const fileObj = await client.files.create({ file: item, purpose: 'assistants' }, options);\n                allFileIds.push(fileObj.id);\n            }\n        }\n        // Start workers to process results\n        const workers = Array(concurrencyLimit).fill(fileIterator).map(processFiles);\n        // Wait for all processing to complete.\n        await allSettledWithThrow(workers);\n        return await this.createAndPoll(vectorStoreId, {\n            file_ids: allFileIds,\n        });\n    }\n}\nexport { VectorStoreFilesPage };\n//# sourceMappingURL=file-batches.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../../resource.mjs\";\nimport { isRequestOptions } from \"../../../core.mjs\";\nimport * as FileBatchesAPI from \"./file-batches.mjs\";\nimport { FileBatches, } from \"./file-batches.mjs\";\nimport * as FilesAPI from \"./files.mjs\";\nimport { Files, VectorStoreFilesPage, } from \"./files.mjs\";\nimport { CursorPage } from \"../../../pagination.mjs\";\nexport class VectorStores extends APIResource {\n    constructor() {\n        super(...arguments);\n        this.files = new FilesAPI.Files(this._client);\n        this.fileBatches = new FileBatchesAPI.FileBatches(this._client);\n    }\n    /**\n     * Create a vector store.\n     */\n    create(body, options) {\n        return this._client.post('/vector_stores', {\n            body,\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    /**\n     * Retrieves a vector store.\n     */\n    retrieve(vectorStoreId, options) {\n        return this._client.get(`/vector_stores/${vectorStoreId}`, {\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    /**\n     * Modifies a vector store.\n     */\n    update(vectorStoreId, body, options) {\n        return this._client.post(`/vector_stores/${vectorStoreId}`, {\n            body,\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    list(query = {}, options) {\n        if (isRequestOptions(query)) {\n            return this.list({}, query);\n        }\n        return this._client.getAPIList('/vector_stores', VectorStoresPage, {\n            query,\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n    /**\n     * Delete a vector store.\n     */\n    del(vectorStoreId, options) {\n        return this._client.delete(`/vector_stores/${vectorStoreId}`, {\n            ...options,\n            headers: { 'OpenAI-Beta': 'assistants=v2', ...options?.headers },\n        });\n    }\n}\nexport class VectorStoresPage extends CursorPage {\n}\nVectorStores.VectorStoresPage = VectorStoresPage;\nVectorStores.Files = Files;\nVectorStores.VectorStoreFilesPage = VectorStoreFilesPage;\nVectorStores.FileBatches = FileBatches;\n//# sourceMappingURL=vector-stores.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../resource.mjs\";\nimport * as AssistantsAPI from \"./assistants.mjs\";\nimport * as ChatAPI from \"./chat/chat.mjs\";\nimport { Assistants, AssistantsPage, } from \"./assistants.mjs\";\nimport * as RealtimeAPI from \"./realtime/realtime.mjs\";\nimport { Realtime } from \"./realtime/realtime.mjs\";\nimport * as ThreadsAPI from \"./threads/threads.mjs\";\nimport { Threads, } from \"./threads/threads.mjs\";\nimport * as VectorStoresAPI from \"./vector-stores/vector-stores.mjs\";\nimport { VectorStores, VectorStoresPage, } from \"./vector-stores/vector-stores.mjs\";\nimport { Chat } from \"./chat/chat.mjs\";\nexport class Beta extends APIResource {\n    constructor() {\n        super(...arguments);\n        this.realtime = new RealtimeAPI.Realtime(this._client);\n        this.vectorStores = new VectorStoresAPI.VectorStores(this._client);\n        this.chat = new ChatAPI.Chat(this._client);\n        this.assistants = new AssistantsAPI.Assistants(this._client);\n        this.threads = new ThreadsAPI.Threads(this._client);\n    }\n}\nBeta.Realtime = Realtime;\nBeta.VectorStores = VectorStores;\nBeta.VectorStoresPage = VectorStoresPage;\nBeta.Assistants = Assistants;\nBeta.AssistantsPage = AssistantsPage;\nBeta.Threads = Threads;\n//# sourceMappingURL=beta.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../resource.mjs\";\nexport class Completions extends APIResource {\n    create(body, options) {\n        return this._client.post('/completions', { body, ...options, stream: body.stream ?? false });\n    }\n}\n//# sourceMappingURL=completions.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../resource.mjs\";\nexport class Embeddings extends APIResource {\n    /**\n     * Creates an embedding vector representing the input text.\n     */\n    create(body, options) {\n        return this._client.post('/embeddings', { body, ...options });\n    }\n}\n//# sourceMappingURL=embeddings.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../resource.mjs\";\nimport { isRequestOptions } from \"../core.mjs\";\nimport { sleep } from \"../core.mjs\";\nimport { APIConnectionTimeoutError } from \"../error.mjs\";\nimport * as Core from \"../core.mjs\";\nimport { CursorPage } from \"../pagination.mjs\";\nexport class Files extends APIResource {\n    /**\n     * Upload a file that can be used across various endpoints. Individual files can be\n     * up to 512 MB, and the size of all files uploaded by one organization can be up\n     * to 100 GB.\n     *\n     * The Assistants API supports files up to 2 million tokens and of specific file\n     * types. See the\n     * [Assistants Tools guide](https://platform.openai.com/docs/assistants/tools) for\n     * details.\n     *\n     * The Fine-tuning API only supports `.jsonl` files. The input also has certain\n     * required formats for fine-tuning\n     * [chat](https://platform.openai.com/docs/api-reference/fine-tuning/chat-input) or\n     * [completions](https://platform.openai.com/docs/api-reference/fine-tuning/completions-input)\n     * models.\n     *\n     * The Batch API only supports `.jsonl` files up to 200 MB in size. The input also\n     * has a specific required\n     * [format](https://platform.openai.com/docs/api-reference/batch/request-input).\n     *\n     * Please [contact us](https://help.openai.com/) if you need to increase these\n     * storage limits.\n     */\n    create(body, options) {\n        return this._client.post('/files', Core.multipartFormRequestOptions({ body, ...options }));\n    }\n    /**\n     * Returns information about a specific file.\n     */\n    retrieve(fileId, options) {\n        return this._client.get(`/files/${fileId}`, options);\n    }\n    list(query = {}, options) {\n        if (isRequestOptions(query)) {\n            return this.list({}, query);\n        }\n        return this._client.getAPIList('/files', FileObjectsPage, { query, ...options });\n    }\n    /**\n     * Delete a file.\n     */\n    del(fileId, options) {\n        return this._client.delete(`/files/${fileId}`, options);\n    }\n    /**\n     * Returns the contents of the specified file.\n     */\n    content(fileId, options) {\n        return this._client.get(`/files/${fileId}/content`, {\n            ...options,\n            headers: { Accept: 'application/binary', ...options?.headers },\n            __binaryResponse: true,\n        });\n    }\n    /**\n     * Returns the contents of the specified file.\n     *\n     * @deprecated The `.content()` method should be used instead\n     */\n    retrieveContent(fileId, options) {\n        return this._client.get(`/files/${fileId}/content`, options);\n    }\n    /**\n     * Waits for the given file to be processed, default timeout is 30 mins.\n     */\n    async waitForProcessing(id, { pollInterval = 5000, maxWait = 30 * 60 * 1000 } = {}) {\n        const TERMINAL_STATES = new Set(['processed', 'error', 'deleted']);\n        const start = Date.now();\n        let file = await this.retrieve(id);\n        while (!file.status || !TERMINAL_STATES.has(file.status)) {\n            await sleep(pollInterval);\n            file = await this.retrieve(id);\n            if (Date.now() - start > maxWait) {\n                throw new APIConnectionTimeoutError({\n                    message: `Giving up on waiting for file ${id} to finish processing after ${maxWait} milliseconds.`,\n                });\n            }\n        }\n        return file;\n    }\n}\nexport class FileObjectsPage extends CursorPage {\n}\nFiles.FileObjectsPage = FileObjectsPage;\n//# sourceMappingURL=files.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../../resource.mjs\";\nimport { isRequestOptions } from \"../../../core.mjs\";\nimport { CursorPage } from \"../../../pagination.mjs\";\nexport class Checkpoints extends APIResource {\n    list(fineTuningJobId, query = {}, options) {\n        if (isRequestOptions(query)) {\n            return this.list(fineTuningJobId, {}, query);\n        }\n        return this._client.getAPIList(`/fine_tuning/jobs/${fineTuningJobId}/checkpoints`, FineTuningJobCheckpointsPage, { query, ...options });\n    }\n}\nexport class FineTuningJobCheckpointsPage extends CursorPage {\n}\nCheckpoints.FineTuningJobCheckpointsPage = FineTuningJobCheckpointsPage;\n//# sourceMappingURL=checkpoints.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../../resource.mjs\";\nimport { isRequestOptions } from \"../../../core.mjs\";\nimport * as CheckpointsAPI from \"./checkpoints.mjs\";\nimport { Checkpoints, FineTuningJobCheckpointsPage, } from \"./checkpoints.mjs\";\nimport { CursorPage } from \"../../../pagination.mjs\";\nexport class Jobs extends APIResource {\n    constructor() {\n        super(...arguments);\n        this.checkpoints = new CheckpointsAPI.Checkpoints(this._client);\n    }\n    /**\n     * Creates a fine-tuning job which begins the process of creating a new model from\n     * a given dataset.\n     *\n     * Response includes details of the enqueued job including job status and the name\n     * of the fine-tuned models once complete.\n     *\n     * [Learn more about fine-tuning](https://platform.openai.com/docs/guides/fine-tuning)\n     */\n    create(body, options) {\n        return this._client.post('/fine_tuning/jobs', { body, ...options });\n    }\n    /**\n     * Get info about a fine-tuning job.\n     *\n     * [Learn more about fine-tuning](https://platform.openai.com/docs/guides/fine-tuning)\n     */\n    retrieve(fineTuningJobId, options) {\n        return this._client.get(`/fine_tuning/jobs/${fineTuningJobId}`, options);\n    }\n    list(query = {}, options) {\n        if (isRequestOptions(query)) {\n            return this.list({}, query);\n        }\n        return this._client.getAPIList('/fine_tuning/jobs', FineTuningJobsPage, { query, ...options });\n    }\n    /**\n     * Immediately cancel a fine-tune job.\n     */\n    cancel(fineTuningJobId, options) {\n        return this._client.post(`/fine_tuning/jobs/${fineTuningJobId}/cancel`, options);\n    }\n    listEvents(fineTuningJobId, query = {}, options) {\n        if (isRequestOptions(query)) {\n            return this.listEvents(fineTuningJobId, {}, query);\n        }\n        return this._client.getAPIList(`/fine_tuning/jobs/${fineTuningJobId}/events`, FineTuningJobEventsPage, {\n            query,\n            ...options,\n        });\n    }\n}\nexport class FineTuningJobsPage extends CursorPage {\n}\nexport class FineTuningJobEventsPage extends CursorPage {\n}\nJobs.FineTuningJobsPage = FineTuningJobsPage;\nJobs.FineTuningJobEventsPage = FineTuningJobEventsPage;\nJobs.Checkpoints = Checkpoints;\nJobs.FineTuningJobCheckpointsPage = FineTuningJobCheckpointsPage;\n//# sourceMappingURL=jobs.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../resource.mjs\";\nimport * as JobsAPI from \"./jobs/jobs.mjs\";\nimport { FineTuningJobEventsPage, FineTuningJobsPage, Jobs, } from \"./jobs/jobs.mjs\";\nexport class FineTuning extends APIResource {\n    constructor() {\n        super(...arguments);\n        this.jobs = new JobsAPI.Jobs(this._client);\n    }\n}\nFineTuning.Jobs = Jobs;\nFineTuning.FineTuningJobsPage = FineTuningJobsPage;\nFineTuning.FineTuningJobEventsPage = FineTuningJobEventsPage;\n//# sourceMappingURL=fine-tuning.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../resource.mjs\";\nimport * as Core from \"../core.mjs\";\nexport class Images extends APIResource {\n    /**\n     * Creates a variation of a given image.\n     */\n    createVariation(body, options) {\n        return this._client.post('/images/variations', Core.multipartFormRequestOptions({ body, ...options }));\n    }\n    /**\n     * Creates an edited or extended image given an original image and a prompt.\n     */\n    edit(body, options) {\n        return this._client.post('/images/edits', Core.multipartFormRequestOptions({ body, ...options }));\n    }\n    /**\n     * Creates an image given a prompt.\n     */\n    generate(body, options) {\n        return this._client.post('/images/generations', { body, ...options });\n    }\n}\n//# sourceMappingURL=images.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../resource.mjs\";\nimport { Page } from \"../pagination.mjs\";\nexport class Models extends APIResource {\n    /**\n     * Retrieves a model instance, providing basic information about the model such as\n     * the owner and permissioning.\n     */\n    retrieve(model, options) {\n        return this._client.get(`/models/${model}`, options);\n    }\n    /**\n     * Lists the currently available models, and provides basic information about each\n     * one such as the owner and availability.\n     */\n    list(options) {\n        return this._client.getAPIList('/models', ModelsPage, options);\n    }\n    /**\n     * Delete a fine-tuned model. You must have the Owner role in your organization to\n     * delete a model.\n     */\n    del(model, options) {\n        return this._client.delete(`/models/${model}`, options);\n    }\n}\n/**\n * Note: no pagination actually occurs yet, this is for forwards-compatibility.\n */\nexport class ModelsPage extends Page {\n}\nModels.ModelsPage = ModelsPage;\n//# sourceMappingURL=models.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../resource.mjs\";\nexport class Moderations extends APIResource {\n    /**\n     * Classifies if text and/or image inputs are potentially harmful. Learn more in\n     * the [moderation guide](https://platform.openai.com/docs/guides/moderation).\n     */\n    create(body, options) {\n        return this._client.post('/moderations', { body, ...options });\n    }\n}\n//# sourceMappingURL=moderations.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../resource.mjs\";\nimport * as Core from \"../../core.mjs\";\nexport class Parts extends APIResource {\n    /**\n     * Adds a\n     * [Part](https://platform.openai.com/docs/api-reference/uploads/part-object) to an\n     * [Upload](https://platform.openai.com/docs/api-reference/uploads/object) object.\n     * A Part represents a chunk of bytes from the file you are trying to upload.\n     *\n     * Each Part can be at most 64 MB, and you can add Parts until you hit the Upload\n     * maximum of 8 GB.\n     *\n     * It is possible to add multiple Parts in parallel. You can decide the intended\n     * order of the Parts when you\n     * [complete the Upload](https://platform.openai.com/docs/api-reference/uploads/complete).\n     */\n    create(uploadId, body, options) {\n        return this._client.post(`/uploads/${uploadId}/parts`, Core.multipartFormRequestOptions({ body, ...options }));\n    }\n}\n//# sourceMappingURL=parts.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nimport { APIResource } from \"../../resource.mjs\";\nimport * as PartsAPI from \"./parts.mjs\";\nimport { Parts } from \"./parts.mjs\";\nexport class Uploads extends APIResource {\n    constructor() {\n        super(...arguments);\n        this.parts = new PartsAPI.Parts(this._client);\n    }\n    /**\n     * Creates an intermediate\n     * [Upload](https://platform.openai.com/docs/api-reference/uploads/object) object\n     * that you can add\n     * [Parts](https://platform.openai.com/docs/api-reference/uploads/part-object) to.\n     * Currently, an Upload can accept at most 8 GB in total and expires after an hour\n     * after you create it.\n     *\n     * Once you complete the Upload, we will create a\n     * [File](https://platform.openai.com/docs/api-reference/files/object) object that\n     * contains all the parts you uploaded. This File is usable in the rest of our\n     * platform as a regular File object.\n     *\n     * For certain `purpose`s, the correct `mime_type` must be specified. Please refer\n     * to documentation for the supported MIME types for your use case:\n     *\n     * - [Assistants](https://platform.openai.com/docs/assistants/tools/file-search#supported-files)\n     *\n     * For guidance on the proper filename extensions for each purpose, please follow\n     * the documentation on\n     * [creating a File](https://platform.openai.com/docs/api-reference/files/create).\n     */\n    create(body, options) {\n        return this._client.post('/uploads', { body, ...options });\n    }\n    /**\n     * Cancels the Upload. No Parts may be added after an Upload is cancelled.\n     */\n    cancel(uploadId, options) {\n        return this._client.post(`/uploads/${uploadId}/cancel`, options);\n    }\n    /**\n     * Completes the\n     * [Upload](https://platform.openai.com/docs/api-reference/uploads/object).\n     *\n     * Within the returned Upload object, there is a nested\n     * [File](https://platform.openai.com/docs/api-reference/files/object) object that\n     * is ready to use in the rest of the platform.\n     *\n     * You can specify the order of the Parts by passing in an ordered list of the Part\n     * IDs.\n     *\n     * The number of bytes uploaded upon completion must match the number of bytes\n     * initially specified when creating the Upload object. No Parts may be added after\n     * an Upload is completed.\n     */\n    complete(uploadId, body, options) {\n        return this._client.post(`/uploads/${uploadId}/complete`, { body, ...options });\n    }\n}\nUploads.Parts = Parts;\n//# sourceMappingURL=uploads.mjs.map","// File generated from our OpenAPI spec by Stainless. See CONTRIBUTING.md for details.\nvar _a;\nimport * as qs from \"./internal/qs/index.mjs\";\nimport * as Core from \"./core.mjs\";\nimport * as Errors from \"./error.mjs\";\nimport * as Pagination from \"./pagination.mjs\";\nimport * as Uploads from \"./uploads.mjs\";\nimport * as API from \"./resources/index.mjs\";\nimport { Batches, BatchesPage, } from \"./resources/batches.mjs\";\nimport { Completions, } from \"./resources/completions.mjs\";\nimport { Embeddings, } from \"./resources/embeddings.mjs\";\nimport { FileObjectsPage, Files, } from \"./resources/files.mjs\";\nimport { Images, } from \"./resources/images.mjs\";\nimport { Models, ModelsPage } from \"./resources/models.mjs\";\nimport { Moderations, } from \"./resources/moderations.mjs\";\nimport { Audio } from \"./resources/audio/audio.mjs\";\nimport { Beta } from \"./resources/beta/beta.mjs\";\nimport { Chat } from \"./resources/chat/chat.mjs\";\nimport { FineTuning } from \"./resources/fine-tuning/fine-tuning.mjs\";\nimport { Uploads as UploadsAPIUploads, } from \"./resources/uploads/uploads.mjs\";\nimport { ChatCompletionsPage, } from \"./resources/chat/completions/completions.mjs\";\n/**\n * API Client for interfacing with the OpenAI API.\n */\nexport class OpenAI extends Core.APIClient {\n    /**\n     * API Client for interfacing with the OpenAI API.\n     *\n     * @param {string | undefined} [opts.apiKey=process.env['OPENAI_API_KEY'] ?? undefined]\n     * @param {string | null | undefined} [opts.organization=process.env['OPENAI_ORG_ID'] ?? null]\n     * @param {string | null | undefined} [opts.project=process.env['OPENAI_PROJECT_ID'] ?? null]\n     * @param {string} [opts.baseURL=process.env['OPENAI_BASE_URL'] ?? https://api.openai.com/v1] - Override the default base URL for the API.\n     * @param {number} [opts.timeout=10 minutes] - The maximum amount of time (in milliseconds) the client will wait for a response before timing out.\n     * @param {number} [opts.httpAgent] - An HTTP agent used to manage HTTP(s) connections.\n     * @param {Core.Fetch} [opts.fetch] - Specify a custom `fetch` function implementation.\n     * @param {number} [opts.maxRetries=2] - The maximum number of times the client will retry a request.\n     * @param {Core.Headers} opts.defaultHeaders - Default headers to include with every request to the API.\n     * @param {Core.DefaultQuery} opts.defaultQuery - Default query parameters to include with every request to the API.\n     * @param {boolean} [opts.dangerouslyAllowBrowser=false] - By default, client-side use of this library is not allowed, as it risks exposing your secret API credentials to attackers.\n     */\n    constructor({ baseURL = Core.readEnv('OPENAI_BASE_URL'), apiKey = Core.readEnv('OPENAI_API_KEY'), organization = Core.readEnv('OPENAI_ORG_ID') ?? null, project = Core.readEnv('OPENAI_PROJECT_ID') ?? null, ...opts } = {}) {\n        if (apiKey === undefined) {\n            throw new Errors.OpenAIError(\"The OPENAI_API_KEY environment variable is missing or empty; either provide it, or instantiate the OpenAI client with an apiKey option, like new OpenAI({ apiKey: 'My API Key' }).\");\n        }\n        const options = {\n            apiKey,\n            organization,\n            project,\n            ...opts,\n            baseURL: baseURL || `https://api.openai.com/v1`,\n        };\n        if (!options.dangerouslyAllowBrowser && Core.isRunningInBrowser()) {\n            throw new Errors.OpenAIError(\"It looks like you're running in a browser-like environment.\\n\\nThis is disabled by default, as it risks exposing your secret API credentials to attackers.\\nIf you understand the risks and have appropriate mitigations in place,\\nyou can set the `dangerouslyAllowBrowser` option to `true`, e.g.,\\n\\nnew OpenAI({ apiKey, dangerouslyAllowBrowser: true });\\n\\nhttps://help.openai.com/en/articles/5112595-best-practices-for-api-key-safety\\n\");\n        }\n        super({\n            baseURL: options.baseURL,\n            timeout: options.timeout ?? 600000 /* 10 minutes */,\n            httpAgent: options.httpAgent,\n            maxRetries: options.maxRetries,\n            fetch: options.fetch,\n        });\n        this.completions = new API.Completions(this);\n        this.chat = new API.Chat(this);\n        this.embeddings = new API.Embeddings(this);\n        this.files = new API.Files(this);\n        this.images = new API.Images(this);\n        this.audio = new API.Audio(this);\n        this.moderations = new API.Moderations(this);\n        this.models = new API.Models(this);\n        this.fineTuning = new API.FineTuning(this);\n        this.beta = new API.Beta(this);\n        this.batches = new API.Batches(this);\n        this.uploads = new API.Uploads(this);\n        this._options = options;\n        this.apiKey = apiKey;\n        this.organization = organization;\n        this.project = project;\n    }\n    defaultQuery() {\n        return this._options.defaultQuery;\n    }\n    defaultHeaders(opts) {\n        return {\n            ...super.defaultHeaders(opts),\n            'OpenAI-Organization': this.organization,\n            'OpenAI-Project': this.project,\n            ...this._options.defaultHeaders,\n        };\n    }\n    authHeaders(opts) {\n        return { Authorization: `Bearer ${this.apiKey}` };\n    }\n    stringifyQuery(query) {\n        return qs.stringify(query, { arrayFormat: 'brackets' });\n    }\n}\n_a = OpenAI;\nOpenAI.OpenAI = _a;\nOpenAI.DEFAULT_TIMEOUT = 600000; // 10 minutes\nOpenAI.OpenAIError = Errors.OpenAIError;\nOpenAI.APIError = Errors.APIError;\nOpenAI.APIConnectionError = Errors.APIConnectionError;\nOpenAI.APIConnectionTimeoutError = Errors.APIConnectionTimeoutError;\nOpenAI.APIUserAbortError = Errors.APIUserAbortError;\nOpenAI.NotFoundError = Errors.NotFoundError;\nOpenAI.ConflictError = Errors.ConflictError;\nOpenAI.RateLimitError = Errors.RateLimitError;\nOpenAI.BadRequestError = Errors.BadRequestError;\nOpenAI.AuthenticationError = Errors.AuthenticationError;\nOpenAI.InternalServerError = Errors.InternalServerError;\nOpenAI.PermissionDeniedError = Errors.PermissionDeniedError;\nOpenAI.UnprocessableEntityError = Errors.UnprocessableEntityError;\nOpenAI.toFile = Uploads.toFile;\nOpenAI.fileFromPath = Uploads.fileFromPath;\nOpenAI.Completions = Completions;\nOpenAI.Chat = Chat;\nOpenAI.ChatCompletionsPage = ChatCompletionsPage;\nOpenAI.Embeddings = Embeddings;\nOpenAI.Files = Files;\nOpenAI.FileObjectsPage = FileObjectsPage;\nOpenAI.Images = Images;\nOpenAI.Audio = Audio;\nOpenAI.Moderations = Moderations;\nOpenAI.Models = Models;\nOpenAI.ModelsPage = ModelsPage;\nOpenAI.FineTuning = FineTuning;\nOpenAI.Beta = Beta;\nOpenAI.Batches = Batches;\nOpenAI.BatchesPage = BatchesPage;\nOpenAI.Uploads = UploadsAPIUploads;\n/** API Client for interfacing with the Azure OpenAI API. */\nexport class AzureOpenAI extends OpenAI {\n    /**\n     * API Client for interfacing with the Azure OpenAI API.\n     *\n     * @param {string | undefined} [opts.apiVersion=process.env['OPENAI_API_VERSION'] ?? undefined]\n     * @param {string | undefined} [opts.endpoint=process.env['AZURE_OPENAI_ENDPOINT'] ?? undefined] - Your Azure endpoint, including the resource, e.g. `https://example-resource.azure.openai.com/`\n     * @param {string | undefined} [opts.apiKey=process.env['AZURE_OPENAI_API_KEY'] ?? undefined]\n     * @param {string | undefined} opts.deployment - A model deployment, if given, sets the base client URL to include `/deployments/{deployment}`.\n     * @param {string | null | undefined} [opts.organization=process.env['OPENAI_ORG_ID'] ?? null]\n     * @param {string} [opts.baseURL=process.env['OPENAI_BASE_URL']] - Sets the base URL for the API, e.g. `https://example-resource.azure.openai.com/openai/`.\n     * @param {number} [opts.timeout=10 minutes] - The maximum amount of time (in milliseconds) the client will wait for a response before timing out.\n     * @param {number} [opts.httpAgent] - An HTTP agent used to manage HTTP(s) connections.\n     * @param {Core.Fetch} [opts.fetch] - Specify a custom `fetch` function implementation.\n     * @param {number} [opts.maxRetries=2] - The maximum number of times the client will retry a request.\n     * @param {Core.Headers} opts.defaultHeaders - Default headers to include with every request to the API.\n     * @param {Core.DefaultQuery} opts.defaultQuery - Default query parameters to include with every request to the API.\n     * @param {boolean} [opts.dangerouslyAllowBrowser=false] - By default, client-side use of this library is not allowed, as it risks exposing your secret API credentials to attackers.\n     */\n    constructor({ baseURL = Core.readEnv('OPENAI_BASE_URL'), apiKey = Core.readEnv('AZURE_OPENAI_API_KEY'), apiVersion = Core.readEnv('OPENAI_API_VERSION'), endpoint, deployment, azureADTokenProvider, dangerouslyAllowBrowser, ...opts } = {}) {\n        if (!apiVersion) {\n            throw new Errors.OpenAIError(\"The OPENAI_API_VERSION environment variable is missing or empty; either provide it, or instantiate the AzureOpenAI client with an apiVersion option, like new AzureOpenAI({ apiVersion: 'My API Version' }).\");\n        }\n        if (typeof azureADTokenProvider === 'function') {\n            dangerouslyAllowBrowser = true;\n        }\n        if (!azureADTokenProvider && !apiKey) {\n            throw new Errors.OpenAIError('Missing credentials. Please pass one of `apiKey` and `azureADTokenProvider`, or set the `AZURE_OPENAI_API_KEY` environment variable.');\n        }\n        if (azureADTokenProvider && apiKey) {\n            throw new Errors.OpenAIError('The `apiKey` and `azureADTokenProvider` arguments are mutually exclusive; only one can be passed at a time.');\n        }\n        // define a sentinel value to avoid any typing issues\n        apiKey ?? (apiKey = API_KEY_SENTINEL);\n        opts.defaultQuery = { ...opts.defaultQuery, 'api-version': apiVersion };\n        if (!baseURL) {\n            if (!endpoint) {\n                endpoint = process.env['AZURE_OPENAI_ENDPOINT'];\n            }\n            if (!endpoint) {\n                throw new Errors.OpenAIError('Must provide one of the `baseURL` or `endpoint` arguments, or the `AZURE_OPENAI_ENDPOINT` environment variable');\n            }\n            baseURL = `${endpoint}/openai`;\n        }\n        else {\n            if (endpoint) {\n                throw new Errors.OpenAIError('baseURL and endpoint are mutually exclusive');\n            }\n        }\n        super({\n            apiKey,\n            baseURL,\n            ...opts,\n            ...(dangerouslyAllowBrowser !== undefined ? { dangerouslyAllowBrowser } : {}),\n        });\n        this.apiVersion = '';\n        this._azureADTokenProvider = azureADTokenProvider;\n        this.apiVersion = apiVersion;\n        this.deploymentName = deployment;\n    }\n    buildRequest(options, props = {}) {\n        if (_deployments_endpoints.has(options.path) && options.method === 'post' && options.body !== undefined) {\n            if (!Core.isObj(options.body)) {\n                throw new Error('Expected request body to be an object');\n            }\n            const model = this.deploymentName || options.body['model'] || options.__metadata?.['model'];\n            if (model !== undefined && !this.baseURL.includes('/deployments')) {\n                options.path = `/deployments/${model}${options.path}`;\n            }\n        }\n        return super.buildRequest(options, props);\n    }\n    async _getAzureADToken() {\n        if (typeof this._azureADTokenProvider === 'function') {\n            const token = await this._azureADTokenProvider();\n            if (!token || typeof token !== 'string') {\n                throw new Errors.OpenAIError(`Expected 'azureADTokenProvider' argument to return a string but it returned ${token}`);\n            }\n            return token;\n        }\n        return undefined;\n    }\n    authHeaders(opts) {\n        return {};\n    }\n    async prepareOptions(opts) {\n        /**\n         * The user should provide a bearer token provider if they want\n         * to use Azure AD authentication. The user shouldn't set the\n         * Authorization header manually because the header is overwritten\n         * with the Azure AD token if a bearer token provider is provided.\n         */\n        if (opts.headers?.['api-key']) {\n            return super.prepareOptions(opts);\n        }\n        const token = await this._getAzureADToken();\n        opts.headers ?? (opts.headers = {});\n        if (token) {\n            opts.headers['Authorization'] = `Bearer ${token}`;\n        }\n        else if (this.apiKey !== API_KEY_SENTINEL) {\n            opts.headers['api-key'] = this.apiKey;\n        }\n        else {\n            throw new Errors.OpenAIError('Unable to handle auth');\n        }\n        return super.prepareOptions(opts);\n    }\n}\nconst _deployments_endpoints = new Set([\n    '/completions',\n    '/chat/completions',\n    '/embeddings',\n    '/audio/transcriptions',\n    '/audio/translations',\n    '/audio/speech',\n    '/images/generations',\n]);\nconst API_KEY_SENTINEL = '<Missing Key>';\nexport { toFile, fileFromPath } from \"./uploads.mjs\";\nexport { OpenAIError, APIError, APIConnectionError, APIConnectionTimeoutError, APIUserAbortError, NotFoundError, ConflictError, RateLimitError, BadRequestError, AuthenticationError, InternalServerError, PermissionDeniedError, UnprocessableEntityError, } from \"./error.mjs\";\nexport default OpenAI;\n//# sourceMappingURL=index.mjs.map","import angular from \"angular\";\r\nimport * as XLSX from \"xlsx\";\r\n\r\nimport {\r\n  Calculation,\r\n  CalculationListItem,\r\n  PayrollDetails,\r\n  UserDefinedRow,\r\n  Employments,\r\n  Years,\r\n  EnumerationsLogic,\r\n  OData,\r\n  Language,\r\n  Avatar,\r\n} from \"@salaxy/core\";\r\n\r\nimport { UiHelpers, SessionService } from \"../../services\";\r\n\r\nimport { OpenAI } from \"openai\";\r\n\r\n/**\r\n * AI payroll assistant functionality.\r\n */\r\nexport class Payroll4AssistantController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$timeout\", \"Employments\", \"UiHelpers\", \"SessionService\"];\r\n\r\n  /**\r\n   * The current payroll (PayrollDetails) to assist.\r\n   */\r\n  public current: PayrollDetails;\r\n\r\n  /** Current page */\r\n  public page:  { current: number, total: number, items: CalculationListItem[], calcs: Calculation[], originalCalcs: Calculation[], calcRange: string, totalCalcCount: number} | undefined;\r\n\r\n  /** Messages */\r\n  public messages: any[] = [];\r\n\r\n  /** Loading indicator */\r\n  public loading: boolean = false;\r\n\r\n  /** Current message */\r\n  public content: string;\r\n\r\n  private _openAiAvatar: Avatar = {\r\n    \"entityType\": \"company\" as any,\r\n    \"firstName\": \"OpenAI\",\r\n    \"lastName\": null,\r\n    \"displayName\": \"OpenAI\",\r\n    \"sortableName\": \"OpenAI\",\r\n    \"pictureType\": \"uploaded\" as any,\r\n    \"url\": \"https://cdn.salaxy.com/img/thumbnail/openai-3.png\",\r\n    \"id\": \"OpenAI\",\r\n  };\r\n  private openai: OpenAI;\r\n\r\n\r\n  private key = \"\";\r\n  constructor(private $timeout: angular.ITimeoutService, private employments: Employments, private uiHelpers: UiHelpers, private sessionService: SessionService) {\r\n  }\r\n\r\n  /**\r\n   * Initializes the controller\r\n   */\r\n  public async $onInit() {\r\n    /** Check assistant key */\r\n    this.key = window.localStorage.getItem(\"openAiKey\") || \"\";\r\n    this.openai = new OpenAI({\r\n      apiKey: this.key,\r\n      dangerouslyAllowBrowser: true\r\n    });\r\n    await this.generateInitialMessages();\r\n    this.$timeout(() => { });\r\n  }\r\n\r\n  /** Company avatar */\r\n  public get myAvatar() {\r\n    return this.sessionService.avatar;\r\n  }\r\n\r\n  /** Open AI avatar */\r\n  public get openAiAvatar() {\r\n    return this._openAiAvatar;\r\n  }\r\n\r\n  /** Chat */\r\n  public async chatForPayroll() {\r\n    // current payroll\r\n    const payrollContent = \"Tässä palkkalistassa tällä hetkellä olevat rivit\" + \"\\r\\n\" + JSON.stringify(this.payrollToRows());\r\n    this.messages.push({ \"role\": \"system\", \"content\": payrollContent , \"hidden\": true });\r\n     this.messages.push({ \"role\": \"system\", \"content\": \"Kun sinua pyydetään lisäämään palkkalistalle rivejä, palauta aina myös kaikki alkuperäiset palkkalistan rivit.\" , \"hidden\": true });\r\n\r\n    this.messages.push({ \"role\": \"user\", \"content\": this.content ?? \"\", \"hidden\": false });\r\n    this.content = \"\";\r\n    const objDiv = document.getElementById(\"openairesponse\");\r\n    objDiv.scrollTop = objDiv.scrollHeight;\r\n    this.$timeout(() => { });\r\n\r\n    try {\r\n      this.loading = true;\r\n      const openaiStream = this.openai.beta.chat.completions.stream({\r\n        model: \"gpt-4o-mini\",\r\n        messages: this.messages,\r\n        temperature: 0,\r\n        response_format: {\r\n          type: \"json_schema\",\r\n          json_schema: {\r\n            name: \"Rows\",\r\n            strict: false,\r\n            schema: {\r\n              type: \"object\",\r\n              properties: {\r\n                \"rows\": {\r\n                  \"description\": \"Set of rows that make up the salary calculation:\\r\\nExpenses, Benefits, deductions etc. Note that side costs are not rows.\",\r\n                  \"type\": \"array\",\r\n                  \"items\": {\r\n                    \"$ref\": \"#/definitions/UserDefinedRowExt\"\r\n                  }\r\n                },\r\n                definitions: {\r\n                  \"UserDefinedRowExt\": {\r\n                    \"description\": \"This is a user defined calculation row \",\r\n                    \"type\": \"object\",\r\n                    \"properties\": {\r\n                      \"employmentId\": {\r\n                        \"description\": \"ID of the employment relation of the worker.\",\r\n                        \"type\": \"string\"\r\n                      },\r\n                      \"rowType\": {\r\n                        \"$ref\": \"#/definitions/CalculationRowType\",\r\n                        \"description\": \"Logical type of the row\"\r\n                      },\r\n                      \"message\": {\r\n                        \"description\": \"Description text of the row that is shown in reports. If null, will be set according to type.\",\r\n                        \"type\": \"string\"\r\n                      },\r\n                      \"count\": {\r\n                        \"format\": \"double\",\r\n                        \"description\": \"Count for the row - default is one\",\r\n                        \"type\": \"number\"\r\n                      },\r\n                      \"price\": {\r\n                        \"format\": \"double\",\r\n                        \"description\": \"Price for the row\",\r\n                        \"type\": \"number\"\r\n                      },\r\n                      \"accounting\": {\r\n                        \"$ref\": \"#/definitions/RowAccounting\",\r\n                        \"description\": \"Accounting related data for the row.\"\r\n                      },\r\n                      \"data\": {\r\n                        \"description\": \"Usecase specific data\",\r\n                        \"type\": \"object\",\r\n                        \"additionalProperties\": {\r\n                          \"type\": \"object\"\r\n                        }\r\n                      }\r\n                    }\r\n                  },\r\n                  \"CalculationRowType\": {\r\n                    \"description\": \"CalculationRowType enumeration\",\r\n                    \"enum\": [\r\n                      \"unknown\",\r\n                      \"salary\",\r\n                      \"hourlySalary\",\r\n                      \"monthlySalary\",\r\n                      \"totalWorkerPayment\",\r\n                      \"totalEmployerPayment\",\r\n                      \"compensation\",\r\n                      \"overtime\",\r\n                      \"tesWorktimeShortening\",\r\n                      \"eveningAddition\",\r\n                      \"nightimeAddition\",\r\n                      \"saturdayAddition\",\r\n                      \"sundayWork\",\r\n                      \"otherAdditions\",\r\n                      \"paidSickLeaveSalary\",\r\n                      \"paidSickLeaveHourlySalary\",\r\n                      \"paidSickLeaveMonthlySalary\",\r\n                      \"trainingSalary\",\r\n                      \"trainingHourlySalary\",\r\n                      \"trainingMonthlySalary\",\r\n                      \"accomodationBenefit\",\r\n                      \"mealBenefit\",\r\n                      \"phoneBenefit\",\r\n                      \"carBenefit\",\r\n                      \"bicycleBenefit\",\r\n                      \"otherBenefit\",\r\n                      \"holidayCompensation\",\r\n                      \"holidayBonus\",\r\n                      \"holidaySalary\",\r\n                      \"dailyAllowance\",\r\n                      \"dailyAllowanceHalf\",\r\n                      \"mealCompensation\",\r\n                      \"milageOwnCar\",\r\n                      \"toolCompensation\",\r\n                      \"expenses\",\r\n                      \"milageDaily\",\r\n                      \"milageOther\",\r\n                      \"unionPayment\",\r\n                      \"foreclosure\",\r\n                      \"advance\",\r\n                      \"foreclosureByPalkkaus\",\r\n                      \"prepaidExpenses\",\r\n                      \"otherDeductions\",\r\n                      \"deductibleOfExerciseAndCultureBenefit\",\r\n                      \"childCareSubsidy\",\r\n                      \"chainsawReduction\",\r\n                      \"nonProfitOrg\",\r\n                      \"subsidisedCommute\",\r\n                      \"irIncomeType\",\r\n                      \"board\",\r\n                      \"remuneration\",\r\n                      \"otherCompensation\",\r\n                      \"workingTimeCompensation\",\r\n                      \"employmentTermination\",\r\n                      \"hourlySalaryWithWorkingTimeCompensation\",\r\n                      \"paidSickLeave\",\r\n                      \"training\",\r\n                      \"taxAtSource\",\r\n                      \"taxWithholding\",\r\n                      \"absencePeriod\",\r\n                      \"serviceCharge\",\r\n                      \"service\",\r\n                      \"totals\"\r\n                    ],\r\n                    \"type\": \"string\"\r\n                  },\r\n                  \"RowAccounting\": {\r\n                    \"description\": \"Provides row specific data for accounting (both cost and financial accounting).\",\r\n                    \"type\": \"object\",\r\n                    \"properties\": {\r\n                      \"vatPercent\": {\r\n                        \"format\": \"double\",\r\n                        \"description\": \"Percent for VAT calculation expressed as decimal: 24% is 0.24.\",\r\n                        \"type\": \"number\"\r\n                      },\r\n                      \"vatEntries\": {\r\n                        \"description\": \"Total VAT amount splitted by VAT rates.\\r\\nPlease note, that if both {Palkkaus.Model.Calc.RowAccounting.VatPercent} and the {Palkkaus.Model.Calc.RowAccounting.VatEntries} with some entries given,\\r\\nthe {Palkkaus.Model.Calc.RowAccounting.VatEntries} are applied.\\r\\nPlease note that this is null by default.\",\r\n                        \"type\": \"array\",\r\n                        \"items\": {\r\n                          \"$ref\": \"#/definitions/VatEntry\"\r\n                        }\r\n                      },\r\n                      \"dimensions\": {\r\n                        \"description\": \"Values for cost accounting dimensions\",\r\n                        \"type\": \"array\",\r\n                        \"items\": {\r\n                          \"$ref\": \"#/definitions/CostAccountingDimension\"\r\n                        }\r\n                      }\r\n                    }\r\n                  },\r\n                  \"VatEntry\": {\r\n                    \"description\": \"For VAT breakdown of a receipt (ALV-erittely) represents a single VAT rate and the revenue and tax with that rate.\",\r\n                    \"type\": \"object\",\r\n                    \"properties\": {\r\n                      \"tax\": {\r\n                        \"format\": \"double\",\r\n                        \"description\": \"Tax amount of specific VAT rate in euro.\\r\\nThis value is mandatory, if the collection of VatEntries contains more than one item.\",\r\n                        \"type\": \"number\"\r\n                      },\r\n                      \"vatRate\": {\r\n                        \"$ref\": \"#/definitions/VatRate\",\r\n                        \"description\": \"Applied VAT rate. This is always mandatory.\"\r\n                      },\r\n                      \"taxPercent\": {\r\n                        \"format\": \"double\",\r\n                        \"description\": \"Tax as percent of Net sales (0-1). Currently just informative, but may later be used for Custom non-standard VAT rates.\",\r\n                        \"type\": \"number\"\r\n                      },\r\n                      \"gross\": {\r\n                        \"format\": \"double\",\r\n                        \"description\": \"Gross sales for specific VAT rate including the tax (VAT).\\r\\nThis value is mandatory, if the collection of VatEntries contains more than one item.\",\r\n                        \"type\": \"number\"\r\n                      },\r\n                      \"net\": {\r\n                        \"format\": \"double\",\r\n                        \"description\": \"Net sales for specific VAT rate excluding the tax (VAT).\\r\\nThis value is mandatory, if the collection of VatEntries contains more than one item.\",\r\n                        \"type\": \"number\"\r\n                      }\r\n                    }\r\n                  },\r\n                  \"VatRate\": {\r\n                    \"description\": \"VatRate enumeration\",\r\n                    \"enum\": [\r\n                      \"undefined\",\r\n                      \"none\",\r\n                      \"vat0000\",\r\n                      \"vat1000\",\r\n                      \"vat1350\",\r\n                      \"vat1400\",\r\n                      \"vat2400\",\r\n                      \"vat2550\",\r\n                      \"other\"\r\n                    ],\r\n                    \"type\": \"string\"\r\n                  },\r\n                  \"CostAccountingDimension\": {\r\n                    \"description\": \"Id of the cost accounting dimension with optional percentage for shared costs.\",\r\n                    \"type\": \"object\",\r\n                    \"properties\": {\r\n                      \"id\": {\r\n                        \"description\": \"Dimension Id.\",\r\n                        \"type\": \"string\"\r\n                      },\r\n                      \"value\": {\r\n                        \"description\": \"Cost accounting dimension value id.\",\r\n                        \"type\": \"string\"\r\n                      },\r\n                      \"percent\": {\r\n                        \"format\": \"percent\",\r\n                        \"description\": \"Sharing percent for the dimension.\",\r\n                        \"type\": \"number\"\r\n                      }\r\n                    }\r\n                  },\r\n                }\r\n              },\r\n            }\r\n          }\r\n        }\r\n      });\r\n\r\n      const responseMessage = {\r\n        \"role\": \"assistant\",\r\n        \"hidden\": true,\r\n        \"content\": \"\"\r\n      };\r\n\r\n      for await (const part of openaiStream) {\r\n        const delta = part.choices[0].delta;\r\n        const finishReason = part.choices[0].finish_reason;\r\n        if (this.messages.indexOf(responseMessage) === -1) {\r\n          this.messages.push(responseMessage);\r\n          console.log(\"responseMessage\", responseMessage);\r\n        }\r\n\r\n        if (delta.content) {\r\n          responseMessage.content += delta.content;\r\n          objDiv.scrollTop = objDiv.scrollHeight;\r\n          this.$timeout(() => { });\r\n        }\r\n\r\n\r\n        if (finishReason) {\r\n          // NO\r\n        }\r\n      }\r\n      this.loading = false;\r\n\r\n      await this.modifyPayroll(responseMessage.content);\r\n\r\n    } catch (error) {\r\n      this.loading = false;\r\n      console.error(\"Error in stream start:\", error);\r\n    }\r\n\r\n    objDiv.scrollTop = objDiv.scrollHeight;\r\n    this.$timeout(() => { });\r\n  }\r\n\r\n  /** Chat */\r\n  public async chatForAdvise() {    // current payroll\r\n    const payrollContent = \"Tässä palkkalistan kaikki laskelmat listana (JSON-formaatti). Rivit ovat rakenteessa: rows.\" + \"\\r\\n\" + JSON.stringify(this.page.calcs);\r\n    this.messages.push({ \"role\": \"system\", \"content\": payrollContent , \"hidden\": true });\r\n    this.messages.push({ \"role\": \"user\", \"content\": this.content ?? \"\", \"hidden\": false });\r\n    this.content = \"\";\r\n    const objDiv = document.getElementById(\"openairesponse\");\r\n    objDiv.scrollTop = objDiv.scrollHeight;\r\n    this.$timeout(() => { });\r\n\r\n    try {\r\n      //this.loading = true;\r\n      const openaiStream = await this.openai.chat.completions.create({\r\n        model: \"gpt-4o-mini\",\r\n        messages: this.messages,\r\n        temperature: 0,\r\n        stream: true,\r\n      });\r\n\r\n      const responseMessage = {\r\n        \"role\": \"assistant\",\r\n        \"hidden\": false,\r\n        \"content\": \"\"\r\n      };\r\n\r\n      for await (const part of openaiStream) {\r\n        const delta = part.choices[0].delta;\r\n        const finishReason = part.choices[0].finish_reason;\r\n        if (this.messages.indexOf(responseMessage) === -1) {\r\n          this.messages.push(responseMessage);\r\n        }\r\n\r\n        if (delta.content) {\r\n          responseMessage.content += delta.content;\r\n          objDiv.scrollTop = objDiv.scrollHeight;\r\n          this.$timeout(() => { });\r\n        }\r\n\r\n\r\n        if (finishReason) {\r\n          // NO\r\n        }\r\n      }\r\n\r\n      //this.loading = false;\r\n    } catch (error) {\r\n      //this.loading = false;\r\n      console.error(\"Error in stream start:\", error);\r\n    }\r\n\r\n    objDiv.scrollTop = objDiv.scrollHeight;\r\n    this.$timeout(() => { });\r\n  }\r\n\r\n  /** Chat */\r\n  public async chatForReport() {\r\n\r\n    this.messages.push({ \"role\": \"user\", \"content\": this.content , \"hidden\": false });\r\n    const payrollContent = \"Tässä palkkalistan kaikki laskelmat listana (JSON-formaatti). Rivit ovat rakenteessa: rows.\" + \"\\r\\n\" + JSON.stringify(this.page.calcs);\r\n    const htmlInstruction = \"Muodosta vain HTML:ää oleva vastaus. HTML:n pitäisi sisältää vain perus-tagejä. Ei tyylejä.\";\r\n    this.messages.push({ \"role\": \"user\", \"content\": payrollContent + \"\\r\\n\" + htmlInstruction , \"hidden\": true });\r\n    this.content = \"\";\r\n\r\n    const objDiv = document.getElementById(\"openairesponse\");\r\n    objDiv.scrollTop = objDiv.scrollHeight;\r\n    this.$timeout(() => { });\r\n\r\n    try {\r\n      this.loading = true;\r\n      const openaiStream = await this.openai.chat.completions.create({\r\n       model: \"gpt-4o-mini\",\r\n        messages: this.messages,\r\n        temperature: 0,\r\n        stream: true,\r\n      });\r\n\r\n      const responseMessage = {\r\n        \"role\": \"assistant\",\r\n        \"hidden\": true,\r\n        \"content\": \"\",\r\n        \"type\": \"html\",\r\n        \"file\": \"report.html\"\r\n      };\r\n\r\n      for await (const part of openaiStream) {\r\n        const delta = part.choices[0].delta;\r\n        const finishReason = part.choices[0].finish_reason;\r\n        if (this.messages.indexOf(responseMessage) === -1) {\r\n          this.messages.push(responseMessage);\r\n        }\r\n\r\n        if (delta.content) {\r\n          responseMessage.content += delta.content;\r\n          objDiv.scrollTop = objDiv.scrollHeight;\r\n          this.$timeout(() => { });\r\n        }\r\n\r\n        if (finishReason) {\r\n          // NO\r\n        }\r\n      }\r\n\r\n      console.log(\"html for report\", responseMessage.content);\r\n      // parse content between ```html and ```\r\n      const htmlContentMatch = responseMessage.content.match(/```html([\\s\\S]*?)```/);\r\n      if (htmlContentMatch && htmlContentMatch[1]) {\r\n        responseMessage.content = htmlContentMatch[1].trim();\r\n        responseMessage.hidden = false;\r\n      } else {\r\n        //responseMessage.content = responseMessage.content;\r\n        responseMessage.hidden = false;\r\n      }\r\n\r\n      this.loading = false;\r\n    } catch (error) {\r\n      this.loading = false;\r\n      console.error(\"Error in stream start:\", error);\r\n    }\r\n\r\n    objDiv.scrollTop = objDiv.scrollHeight;\r\n    this.$timeout(() => { });\r\n  }\r\n\r\n  /** Shows the selected report */\r\n  public showReport(message: { content: string}) {\r\n    this.uiHelpers.showDialog(\"salaxy-components/modals/ui/Html.html\", null, { html: message.content, title:\"Raportti\" }, null,\"lg\");\r\n  }\r\n\r\n  /**\r\n   * Reads the xls file\r\n   * @param file Selected file\r\n   */\r\n  public async readFile(file: File): Promise<void> {\r\n    if (!file) {\r\n      return Promise.resolve(null);\r\n    }\r\n    const workbook = XLSX.read(await file.arrayBuffer(), { type: \"buffer\" });\r\n    const firstSheet = workbook.Sheets[workbook.SheetNames[0]];\r\n    const data = XLSX.utils.sheet_to_json(firstSheet);\r\n\r\n    this.messages.push({ \"role\": \"user\", \"content\": JSON.stringify(data), \"hidden\": false, type:\"file\", \"file\": file.name });\r\n\r\n    this.$timeout(() => { });\r\n  }\r\n\r\n  /** Modify payroll rows */\r\n  private async modifyPayroll(content: string) {\r\n    const rows = JSON.parse(content).rows;\r\n    console.log(rows);\r\n    if (this.page) {\r\n      for(const calc of this.page.calcs) {\r\n        calc.rows.splice(0, calc.rows.length);\r\n      }\r\n    }\r\n    for (const row of rows) {\r\n      if (this.page) {\r\n        const calc = this.page.calcs.find((c) => c.worker.employmentId === row.employmentId);\r\n        if (calc) {\r\n          const userDefinedRow = row as UserDefinedRow;\r\n          userDefinedRow.accounting ??= { dimensions: [], vatEntries: [] };\r\n          userDefinedRow.accounting.dimensions ??= [];\r\n          userDefinedRow.accounting.vatEntries ??= [];\r\n          userDefinedRow.data ??= {};\r\n          calc.rows.push(row);\r\n        }\r\n      }\r\n    }\r\n  }\r\n\r\n  private async generateInitialMessages(): Promise<void> {\r\n    // employment relations\r\n    const employments = (await OData.getAllPages((o) => this.employments.getODataActive(\"all\", o), {})).items;\r\n    const employees =\"Tässä ovat kaikki työntekijät listattuna (JSON):\\r\\n\" + JSON.stringify(employments.map((e) => ({employmentId: e.id, displayName: e.otherPartyInfo?.avatar?.displayName})));\r\n    this.messages.push({ \"role\": \"system\", \"hidden\": true, \"content\": employees });\r\n    // calculation row types\r\n    const rowTypes = \"Tässä ovat kaikki rivityypit (CalculationRowType) listattuna (JSON):\\r\\n\" + JSON.stringify( EnumerationsLogic.getEnumMetadata(\"CalculationRowType\", Language.Fi).values.map((e) => ({ rowType: e.name, label: e.label,description: e.descr})));\r\n    this.messages.push({ \"role\": \"system\", \"hidden\": true, \"content\": rowTypes });\r\n    // yearly changing numbers\r\n    const yearlyChangingNumbers = \"Tässä ovat kaikki vuosittain muuttuvat numerot listattuna vuodelle 2025 (JSON):\\r\\n\" + JSON.stringify(Years.getYearlyChangingNumbers(new Date()).sideCosts);\r\n    this.messages.push({ \"role\": \"system\", \"hidden\": true, \"content\": yearlyChangingNumbers });\r\n  }\r\n\r\n  private payrollToRows() {\r\n    const extRows = [];\r\n    for (const calc of this.page.calcs) {\r\n      for (const row of calc.rows) {\r\n        extRows.push({ employmentId:  calc.worker.employmentId, ...row });\r\n      }\r\n    }\r\n    return extRows;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Calculations } from \"@salaxy/core\";\r\n\r\nimport { InvoicesService, ReportsService, SessionService, UiHelpers } from \"../../services\";\r\nimport { CalculationCrudController } from \"./CalculationCrudController\";\r\n\r\n/**\r\n * Controller for showing possible calculation repair history.\r\n */\r\nexport class CalcRepairInfoController extends CalculationCrudController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Calculations\", \"ReportsService\", \"UiHelpers\", \"$location\", \"$routeParams\", \"SessionService\", \"InvoicesService\"];\r\n\r\n  /**\r\n   * Creates a new CalcSharingController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    calculationsApi: Calculations,\r\n    reportsService: ReportsService,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    sessionService: SessionService,\r\n    protected invoicesService: InvoicesService,\r\n  ) {\r\n    super(calculationsApi, reportsService, uiHelpers, $location, $routeParams, sessionService, invoicesService);\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Shows a selection list for repaired calculations */\r\n  public showRepaired() {\r\n    return this.api.getOData({\r\n        $filter: \"status eq 'paymentRepairCopy' and data/originalId eq '\" + this.current.id + \"'\",\r\n        $orderby: \"updatedAt desc\"\r\n      }).then( (repaired) => {\r\n      return this.uiHelpers.openEditDialog(\r\n        \"salaxy-components/modals/calc/CalcRepaired.html\",\r\n        repaired.items,\r\n        {},\r\n      );\r\n    });\r\n  }\r\n}\r\n","import { Calculation, InvoicesLogic, PayrollDetails, Calculations, Translations, Configs } from \"@salaxy/core\";\r\nimport angular from \"angular\";\r\nimport { SessionService } from \"../../services/SessionService\";\r\nimport { UiHelpers } from \"../../services/ui/UiHelpers\";\r\n/**\r\n * New payment controller for Salaxy Pay\r\n */\r\nexport class NewPaymentController implements angular.IController {\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"SessionService\", \"Calculations\", \"UiHelpers\", \"$location\"];\r\n\r\n  constructor(private sessionService: SessionService, private calculations: Calculations, private uiHelpers: UiHelpers, private $location: angular.ILocationService) {\r\n  }\r\n\r\n  /**\r\n   * Text for the payment button\r\n   * This is typically customized in custom payment scenarios.\r\n   */\r\n  public getPaymentButtonText(label: string): string {\r\n    return label ? Translations.get(label) : Translations.get(\"SALAXY.UI_Terms.pay\");\r\n  }\r\n\r\n  /**\r\n   * Opens the Salaxy Pay payment for a Calculation or PayrollDetails item.\r\n   * If the model is a Calculation, it will first save the calculation before proceeding.\r\n   * Generates a URL for Salaxy Pay and opens it in a new window.\r\n   * @param model - The Calculation or PayrollDetails to pay.\r\n   * @param step - Optional step number to navigate to in the payment wizard.\r\n   */\r\n  public openSalaxyPay(model: Calculation | PayrollDetails, step?: number): void {\r\n    if (InvoicesLogic.isCalculation(model)) {\r\n      this.openPaymentForCalculation(model as Calculation, step);\r\n    } else if (InvoicesLogic.isPayroll(model)) {\r\n      this.openPaymentForPayroll(model as PayrollDetails, step);\r\n    } else {\r\n      throw new Error(\"Invalid business object type\");\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Resolves the base URL for Salaxy Pay based on the current environment.\r\n   * @returns The base URL for the payment service.\r\n   */\r\n  private resolveBaseUrl(): string {\r\n    switch (Configs.current.getEnv()) {\r\n      case \"prod\":\r\n        return \"https://pay.palkkaus.fi\";\r\n      case \"local\":\r\n        return \"http://localhost:5173\";\r\n      case \"test\":\r\n        return \"https://test-pay.palkkaus.fi\";\r\n      case \"rc\":\r\n      case \"demo\":\r\n      default:\r\n        return \"https://demo-pay.palkkaus.fi\";\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Validates required parameters for opening payment.\r\n   * @param baseUrl - The base URL for the payment service.\r\n   * @param accessToken - The access token for authentication.\r\n   * @param businessObjectType - The type of business object.\r\n   * @param businessObjectId - The ID of the business object.\r\n   * @throws Error if any required parameter is missing.\r\n   */\r\n  private validatePaymentParams(baseUrl: string, accessToken: string, businessObjectType: string, businessObjectId: string): void {\r\n    if (!baseUrl) {\r\n      throw new Error(\"Base URL is not set\");\r\n    }\r\n    if (!accessToken) {\r\n      throw new Error(\"Access token is not set\");\r\n    }\r\n    if (!businessObjectType) {\r\n      throw new Error(\"Business object type is not set\");\r\n    }\r\n    if (!businessObjectId) {\r\n      throw new Error(\"Business object id is not set\");\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Opens payment for a calculation, saving it first if needed.\r\n   * @param calculation - The calculation to pay.\r\n   * @param step - Optional step number to navigate to in the payment wizard.\r\n   */\r\n  private openPaymentForCalculation(calculation: Calculation, step?: number): void {\r\n    if (step !== undefined) {\r\n      if (!calculation.id) {\r\n        console.error(\"Error opening salaxy pay: Calculation ID is not set\");\r\n        return;\r\n      }\r\n      this.openPayment(calculation.id, \"calculation\", undefined, step);\r\n      return;\r\n    }\r\n    const loading = this.uiHelpers.showLoading(\"Avataan maksamista...\");\r\n    this.calculations.save(calculation).then((savedCalculation) => {\r\n      if (!savedCalculation.id) {\r\n        throw new Error(\"Calculation ID is not set after saving\");\r\n      }\r\n      this.$location.path(\"/calc/details/\" + savedCalculation.id + \"&refresh=\" + new Date().getTime());\r\n      this.openPayment(savedCalculation.id, \"calculation\", loading, step);\r\n    }).catch((error) => {\r\n      console.error(\"Error opening salaxy pay:\", error);\r\n      loading.dismiss();\r\n      this.uiHelpers.showAlert(\"Virhe\", \"Jotain meni pieleen maksamisen avaamisessa.\");\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Opens payment for a payroll (assumes payroll is already saved).\r\n   * @param payroll - The payroll to pay.\r\n   * @param step - Optional step number to navigate to in the payment wizard.\r\n   */\r\n  private openPaymentForPayroll(payroll: PayrollDetails, step?: number): void {\r\n    if (!payroll.id) {\r\n      console.error(\"Error opening salaxy pay: Payroll ID is not set\");\r\n      return;\r\n    }\r\n    this.openPayment(payroll.id, \"payroll\", undefined, step);\r\n  }\r\n\r\n  /**\r\n   * Opens the payment window with validated parameters.\r\n   * @param businessObjectId - The ID of the business object.\r\n   * @param businessObjectType - The type of business object.\r\n   * @param loading - Optional loading indicator with dismiss method.\r\n   * @param loading.dismiss - Dismiss the loading indicator.\r\n   * @param step - Optional step number to navigate to in the payment wizard.\r\n   */\r\n  private openPayment(businessObjectId: string, businessObjectType: string, loading?: { dismiss: () => void }, step?: number): void {\r\n    try {\r\n      const baseUrl = this.resolveBaseUrl();\r\n      const accessToken = this.sessionService.getCurrentToken();\r\n      this.validatePaymentParams(baseUrl, accessToken, businessObjectType, businessObjectId);\r\n      let url = `${baseUrl}/#access_token=${accessToken}&business_object_id=${businessObjectId}&business_object_type=${businessObjectType}`;\r\n      if (step !== undefined) {\r\n        url += `&step=${step}`;\r\n      }\r\n      window.open(url, \"_blank\", \"noopener\");\r\n      if (loading) {\r\n        loading.dismiss();\r\n      }\r\n      //TODO: Review this approach\r\n      //This is one approach to handle the case when the uesr closes salaxy pay window and we want to reload the calculation details page\r\n      //If this is good approcah, implement this also to payroll payments\r\n      this.uiHelpers.showAlert(\"Ilmoitus\", \"Palkkalaskelman maksaminen on avattu toiseen välilehteen.\").then(() => {\r\n        this.$location.path(\"/calc/details/\" + businessObjectId + \"&refresh=\" + new Date().getTime());\r\n      });\r\n    } catch (error) {\r\n      console.error(\"Error opening salaxy pay:\", error);\r\n      if (loading) {\r\n        loading.dismiss();\r\n      }\r\n      this.uiHelpers.showAlert(\"Virhe\", \"Jotain meni pieleen palkkalaskelman maksamisen aloittamisessa.\");\r\n    }\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\n/**\r\n * Controller rendering a contact info box in the page area.\r\n */\r\nexport class ContactInfoController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n\r\n  /** If true, short version of the content is shown */\r\n  public showShortContent: boolean;\r\n\r\n  /** If true, contact info is hidden */\r\n   public hideContactInfo: boolean;\r\n\r\n  /**\r\n   * Creates a new ContactInfoController\r\n   * @ignore\r\n   */\r\n  constructor() {\r\n    //\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit = () => {\r\n    // initialization\r\n  };\r\n\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Arrays, Calculation, CalculationListItem, CalculationRowType, Calculations, CalculatorLogic, Message, MessageFrom, MessageListItem, MessageThread, MessageThreads, MessageThreadStatus, Numeric, ODataResult, PayrollListItem, Payrolls, ThreadedMessageType, Translations } from \"@salaxy/core\";\r\n\r\nimport { EditDialogKnownActions, SessionService, UiHelpers, UploadService } from \"../../services\";\r\nimport { ApiCrudObjectController } from \"../bases\";\r\n\r\n/**\r\n * User interface logic for a set of messages and/or attachments\r\n * that are grouped together as messages thread.\r\n */\r\nexport class MessageThreadCrudController extends ApiCrudObjectController<MessageThread, MessageListItem> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"MessageThreads\", \"UiHelpers\", \"UploadService\", \"$location\", \"$routeParams\", \"$anchorScroll\", \"$timeout\", \"SessionService\", \"Calculations\", \"Payrolls\"];\r\n\r\n  /** New message that is edited / to be added to the thread. */\r\n  public newMessage: Message = {\r\n    type: ThreadedMessageType.Text,\r\n  };\r\n\r\n  /** If true, the message is currently in edit mode. */\r\n  public isInEdit: boolean;\r\n\r\n  /** Role of the current user. Owner is default. */\r\n  public role: MessageFrom;\r\n\r\n  /** Once message thread loaded, create a calculation based on the rows. */\r\n  public createCalc: boolean;\r\n\r\n  /** Calculation that is created / updated based on the message thread rows. */\r\n  public calc: Calculation;\r\n\r\n  /** Approval page url. */\r\n  public approvalUrl: string;\r\n\r\n  /**\r\n   * If set, the controller will mark a message thread as open once it has been loaded.\r\n   * If the value is true, the message is marked as read immediately.\r\n   * If the value is number, the controller waits the given amount of seconds before marking the item as read.\r\n   */\r\n  private _markAsRead: number | true;\r\n\r\n  private _otherParty: string;\r\n\r\n  private _otherPartyOptions: { [key: string]: string };\r\n\r\n  private markAsReadTimeout: any;\r\n\r\n  constructor(\r\n    private messageApi: MessageThreads,\r\n    uiHelpers: UiHelpers,\r\n    protected uploadService: UploadService,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    private $anchorScroll: angular.IAnchorScrollService,\r\n    private $timeout: angular.ITimeoutService,\r\n\r\n    private sessionService: SessionService,\r\n\r\n    private calculations: Calculations,\r\n    private payrolls: Payrolls,\r\n  ) {\r\n    // Dependency injection\r\n    super(messageApi, uiHelpers, $location, $routeParams);\r\n  }\r\n  /**\r\n   * Initialization code.\r\n   */\r\n  public $onInit() {\r\n    this.role = this.role || MessageFrom.Owner;\r\n    super.$onInit();\r\n  }\r\n\r\n  /**\r\n   * Cleaning the timeout.\r\n   */\r\n  public $onDestroy = () => {\r\n    if (angular.isDefined(this.markAsReadTimeout)) {\r\n      this.$timeout.cancel(this.markAsReadTimeout);\r\n    }\r\n  };\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"/messages\",\r\n      detailsUrl: this.detailsUrl || \"/messages/details/\",\r\n      approvalUrl: this.approvalUrl || \"/messages/approval/\",\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/MessageThreads.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n\r\n  /**\r\n   * If true, this is a new unsaved object.\r\n   * Adds \"new-for-calc\" and \"new-for-payroll\" actions as new item.\r\n   */\r\n   public isNew(): boolean {\r\n    if (this.parentController) {\r\n      return this.parentController.isNew();\r\n    }\r\n    return this.action === \"new-for-calc\" || this.action === \"new-for-payroll\" || super.isNew();\r\n  }\r\n\r\n  /**\r\n   * Overrides the isReadOnly with workflow cases\r\n   */\r\n  public get isReadOnly(): boolean {\r\n    return super.isReadOnly ||\r\n      (this.role === \"owner\" && this.current?.workflowData?.events.some((x) => x.type === \"PartnerMessageClosed\"));\r\n  }\r\n\r\n  /**\r\n   * If set, the controller will mark a message thread as open once it has been loaded.\r\n   * If the value is true, the message is marked as read immediately.\r\n   * If the value is number, the controller waits the given amount of seconds before marking the item as read.\r\n   */\r\n  public get markAsRead(): number | true {\r\n    if (this.parentController) {\r\n      return (this.parentController as MessageThreadCrudController).markAsRead;\r\n    }\r\n    return this._markAsRead;\r\n  }\r\n  public set markAsRead(value: number | true) {\r\n    if (this.parentController) {\r\n      (this.parentController as MessageThreadCrudController).markAsRead = value;\r\n    }\r\n    this._markAsRead = value;\r\n  }\r\n\r\n  /**\r\n   * Salaxy ID (IBAN format) for the other party (besides the message thread owner).\r\n   * Supports special values: \"partner\" for payment partner.\r\n   */\r\n  public get otherParty(): string {\r\n    return this._otherParty;\r\n  }\r\n  public set otherParty(value: string) {\r\n    if (value === \"partner\") {\r\n      this._otherParty = this.sessionService.session.settings.partner.accountId;\r\n    } else {\r\n      this._otherParty = value;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * If set, shows a drop-down for these options using the enum component.\r\n   * Keys may have special values: \"partner\": payment partner.\r\n   */\r\n  public get otherPartyOptions(): { [key: string]: string } {\r\n    return this._otherPartyOptions;\r\n  }\r\n  public set otherPartyOptions(value: { [key: string]: string }) {\r\n    if (!value || Object.keys(value).length === 0) {\r\n      this._otherPartyOptions = null;\r\n      return;\r\n    }\r\n    this._otherPartyOptions = Object.assign({}, ...Object.keys(value).map((key) => {\r\n      if (key === \"partner\") {\r\n        const partner = this.sessionService.session.settings.partner;\r\n        return { [partner.accountId]: value[key] || partner.serviceModel.site.webAppName || partner.info.avatar.displayName };\r\n      }\r\n      return { [key]: value[key] };\r\n    }));\r\n  }\r\n\r\n  /**\r\n   * Returns true if the other-party is 'partner' or partner's ID.\r\n   */\r\n  public get isOtherPartyPartner(): boolean {\r\n    return this.otherParty === \"partner\" ||  this.otherParty === this.sessionService.session?.settings?.partner?.accountId;\r\n  }\r\n\r\n  /**\r\n   * Adds a text message (from the textarea / this.newMessage) to the current thread.\r\n   */\r\n  public sendMessage(): Promise<MessageThread> {\r\n    this.newMessage.content = (this.newMessage.content || \"\").trim();\r\n    this.newMessage.fromParty = this.role;\r\n    switch (this.newMessage.type) {\r\n      case ThreadedMessageType.Text:\r\n        if (!this.newMessage.content) {\r\n          return;\r\n        }\r\n        break;\r\n\r\n    }\r\n    return this.setStatus(this.messageApi.addMessage(this.currentId, this.newMessage))\r\n      .then((thread) => {\r\n        this.newMessage = {\r\n          type: ThreadedMessageType.Text,\r\n        };\r\n        this.setCurrent(thread);\r\n        return thread;\r\n      });\r\n  }\r\n\r\n  /** Sets the type of the message to be added / edited */\r\n  public setType(type: ThreadedMessageType) {\r\n    type = type || ThreadedMessageType.Text;\r\n    this.newMessage = {\r\n      type: type,\r\n    };\r\n    switch (type) {\r\n      case \"absence\" as any:\r\n        this.newMessage.contentData = {\r\n          periods: [],\r\n        };\r\n        this.newMessage.content = \"Absence content\";\r\n        break;\r\n      case \"annualLeave\" as any:\r\n        this.newMessage.contentData = {\r\n          leaves: [],\r\n        };\r\n        this.newMessage.content = \"Annual leave content\";\r\n        break;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Sends an email notification to the thread owner.\r\n   */\r\n  public sendNotification(): Promise<MessageThread> {\r\n    const endUserService = this.sessionService.session.settings.partner.serviceModel.site.webAppName || this.sessionService.session.settings.partner.info.avatar.displayName;\r\n    const subject = `${Translations.get(\"SALAXY.NG1.MessageThreadComponent.sendNotificationSubject\")} ${endUserService}`;\r\n    const body = `${Translations.get(\"SALAXY.NG1.MessageThreadComponent.sendNotificationBody\")}`;\r\n\r\n    return this.setStatus(this.messageApi.sendNotification(this.currentId, subject, body))\r\n      .then((thread) => {\r\n        this.setCurrent(thread);\r\n        return thread;\r\n      });\r\n  }\r\n\r\n  /** Overrides the save to assure that the other party is defined (can be set in component properties).  */\r\n  public save() {\r\n    if (!this.current.otherParty) {\r\n      if (!this.otherParty) {\r\n        this.uiHelpers.showAlert(\"SALAXY.NG1.MessageThreadComponent.saveNoToField\");\r\n        return;\r\n      }\r\n      this.current.otherParty = this.otherParty;\r\n    }\r\n    return super.save();\r\n  }\r\n\r\n  /** Selects a calculation as current calculation. */\r\n  public selectCalc(): void {\r\n    this.uiHelpers.openSelectCalcs(\"draft\", \"Valitse palkkalaskelma\").then((dialogResult) => {\r\n      if (dialogResult.action == EditDialogKnownActions.Ok && dialogResult.item.length > 0) {\r\n        this.calculations.getSingle(dialogResult.item[0].id).then((calc) => {\r\n          this.calc = calc;\r\n          this.updateCalc();\r\n        });\r\n      }\r\n    });\r\n  }\r\n\r\n  /** Updates the calculation based on rows in the message. */\r\n  public updateCalc(): void {\r\n    this.calc = this.calc || CalculatorLogic.getBlank();\r\n    const totalMinutes = Arrays.sum(this.current.messages, (x) => x.contentData?.totalTime || 0);\r\n    this.calc.employer.isSelf = true;\r\n    this.calc.worker.accountId = this.calc.worker.accountId || this.current.otherParty;\r\n    this.calc.rows = this.calc.rows.filter((x) => x.sourceId != this.current.id);\r\n    // HACK: Get the price from employment\r\n    const price = 10;\r\n    this.calc.rows.splice(0, 0, {\r\n      rowType: CalculationRowType.HourlySalary,\r\n      count: Numeric.round(totalMinutes / 60),\r\n      price,\r\n      sourceId: this.current.id,\r\n    });\r\n    // TODO: Lauantai ja sunnuntai\r\n    this.recalculate();\r\n  }\r\n\r\n  /** Recalculates the calculation based on the rows in the message. */\r\n  public recalculate(): Promise<Calculation> {\r\n    return this.calculations.recalculate(this.calc).then((result) => {\r\n      this.calc = result;\r\n      return this.calc;\r\n    });\r\n  }\r\n\r\n  /** Saves the current calculation. */\r\n  public saveCalc(): Promise<Calculation> {\r\n    return this.calculations.save(this.calc).then((result) => {\r\n      this.calc = result;\r\n      return this.calc;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Starts the reload process depending on the bindingMode.\r\n   * Overrides a different load process for \"new-for-calc\" and \"new-for-payroll\".\r\n   * Overrides the reload to send the browser to the bottom\r\n   */\r\n   public reload(): Promise<MessageThread> {\r\n    if (this.action === \"new-for-calc\" || this.action === \"new-for-payroll\") {\r\n      if (this.parentController) {\r\n        return this.parentController.reload().then((item) => {\r\n          this._currentId = null;\r\n          return item;\r\n        });\r\n      } else {\r\n\r\n        const prepareMessage = (): Promise<MessageThread> => {\r\n          const newMessage = this.api.getBlank();\r\n          newMessage.status = MessageThreadStatus.Active;\r\n          if (this.currentId === \"new\") {\r\n            this._currentId = null;\r\n          }\r\n          if (this.action === \"new-for-calc\" && this.currentId && this.currentId != \"new\") {\r\n\r\n            return this.getCalculationListItem(this.currentId).then( (calculationListItem) => {\r\n              newMessage.title = \"Palkka \" + calculationListItem?.otherPartyInfo?.avatar?.displayName;\r\n              newMessage.ownerWorkflow = {\r\n                salaryDate: calculationListItem?.salaryDate\r\n              };\r\n              newMessage.messages.push(\r\n                {\r\n                  contentId: this.currentId,\r\n                  fromParty: this.role || MessageFrom.Owner,\r\n                  type: ThreadedMessageType.Calculation\r\n                });\r\n                return newMessage;\r\n              });\r\n          }\r\n          else if (this.action === \"new-for-payroll\" && this.currentId && this.currentId != \"new\")\r\n          {\r\n            return this.getPayrollListItem(this.currentId).then( (payrollListItem) => {\r\n              newMessage.status = MessageThreadStatus.Active;\r\n              newMessage.title = \"Palkkalista \" + payrollListItem?.shortText;\r\n              newMessage.ownerWorkflow = {\r\n                salaryDate: payrollListItem?.salaryDate\r\n              };\r\n              newMessage.messages.push(\r\n                {\r\n                  contentId: this.currentId,\r\n                  fromParty: this.role || MessageFrom.Owner,\r\n                  type: ThreadedMessageType.Payroll\r\n                });\r\n                return newMessage;\r\n              });\r\n          } else {\r\n            return Promise.resolve(newMessage);\r\n          }\r\n        };\r\n        return prepareMessage().then( (newMessage) => {\r\n          this._currentId = null;\r\n          return this.setStatus(Promise.resolve(newMessage))\r\n            .then((item) => {\r\n              this.setCurrentRef(item);\r\n              return item;\r\n            });\r\n        });\r\n      }\r\n    } else {\r\n      return super.reload().then((value) => {\r\n\r\n        // HACK?\r\n        if (this.createCalc) {\r\n          this.updateCalc();\r\n        }\r\n        if (!this.isNew()) {\r\n          this.$timeout(() => {\r\n            this.$anchorScroll(\"messageContainerBottom\");\r\n          });\r\n          if (this.status === \"loaded\" && this.markAsRead && !this.getReadTime()) {\r\n            const relevantMessages = this.current.messages\r\n              .filter((x) => x.fromParty === (this.role === \"otherParty\" ? \"owner\" : \"otherParty\"));\r\n            if (relevantMessages.length > 0) {\r\n              if (this.markAsRead === true) {\r\n                this.markAllAsRead();\r\n              } else {\r\n                this.markAsReadTimeout = this.$timeout(() => {\r\n                  if (!this.isInEdit) {\r\n                    this.markAllAsRead();\r\n                  }\r\n                }, this.markAsRead * 1000);\r\n              }\r\n            }\r\n          }\r\n        }\r\n        return value;\r\n      });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Marks all messages as read by a given party.\r\n   * The command is immediately sent to the server and the current message is updated incrementally (just the read/unread info).\r\n   * @param readBy The party for which the messages are marked as read.\r\n   * If not specified, uses the current role or the controller.\r\n   * @returns The entire thread with the messages marked as read.\r\n   */\r\n  public markAllAsRead(readBy?: MessageFrom): Promise<MessageThread> {\r\n    readBy = readBy || this.role || MessageFrom.Owner;\r\n    return this.messageApi.markAsRead(this.currentId, readBy)\r\n      .then((result) => {\r\n        this.current.messages.forEach((msg: Message) => {\r\n          if (readBy === \"otherParty\") {\r\n            msg.readByOtherParty = msg.readByOtherParty || new Date().toISOString();\r\n          } else {\r\n            msg.readByOwner = msg.readByOwner || new Date().toISOString();\r\n          }\r\n        });\r\n        return result;\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Marks a message / attachment as read/unread also changing all messages before that message.\r\n   * The role of the read/unread is determined by the message: It is the opposite of fromParty (owner (default)/otherParty).\r\n   * The changes are made only to the current message, not Saved to the server.\r\n   * @param message The message that is marked as read/unread (with the messages before that).\r\n   * @param readByValue Possibility to force whether the flag is set to read or unread.\r\n   * If null, the flag is set to the opposite of the current.\r\n   */\r\n  public markItemAsRead(message: Message, readByValue: boolean = null) {\r\n    const flagFor: \"owner\" | \"otherParty\" = message.fromParty === \"otherParty\" ? \"owner\" : \"otherParty\";\r\n    if (readByValue == null) {\r\n      readByValue = flagFor === \"owner\" ? !message.readByOwner : !message.readByOtherParty;\r\n    }\r\n    if (readByValue) {\r\n      for (const item of this.current.messages) {\r\n        if (flagFor === \"owner\") {\r\n          item.readByOwner = item.readByOwner || new Date().toISOString();\r\n        } else {\r\n          item.readByOtherParty = item.readByOtherParty || new Date().toISOString();\r\n        }\r\n        if (item === message) {\r\n          return;\r\n        }\r\n      }\r\n    } else {\r\n      const startFrom = this.current.messages.indexOf(message);\r\n      for (let i = startFrom; i < this.current.messages.length; i++) {\r\n        if (flagFor === \"owner\") {\r\n          this.current.messages[i].readByOwner = null;\r\n        } else {\r\n          this.current.messages[i].readByOtherParty = null;\r\n        }\r\n      }\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Gets the time when a message was read.\r\n   * The time is dependent of the fromParty of the message: There are separate times for owner and other party.\r\n   * If time is null, the message has not been read.\r\n   * @param message Message for which the readTime is fetched.\r\n   * If not set, uses the last message for the current party.\r\n   * @returns If fromParty is \"otherParty\", then readByOwner is returned, otherwise readByOtherParty is returned.\r\n   * The value should be ISO date (string) or null if the item has not been read yet.\r\n   */\r\n  public getReadTime(message: Message = null) {\r\n    if (!message) {\r\n      const relevantMessages = this.current.messages\r\n        .filter((x) => x.fromParty === (this.role === \"otherParty\" ? \"owner\" : \"otherParty\"));\r\n      if (relevantMessages.length === 0) {\r\n        return null;\r\n      }\r\n      message = relevantMessages[relevantMessages.length - 1];\r\n    }\r\n    if (message.fromParty === \"otherParty\") {\r\n      return message.readByOwner || null;\r\n    } else {\r\n      return message.readByOtherParty || null;\r\n    }\r\n  }\r\n\r\n  /** temp upload progress */\r\n  public uploadProgress = 0;\r\n\r\n  /**\r\n   * Uploads the files to the server\r\n   * @param files The files collection from the upload component\r\n   * @example\r\n   * <button ngf-select=\"$ctrl.uploadFiles($files)\" multiple accept=\"image/*\">Select Files</button>\r\n   */\r\n  public uploadFiles(files: any[]) {\r\n    if (files && files.length) {\r\n      const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.MessageThreadComponent.uploadFilesSaving\");\r\n      this.uploadService.upload<MessageThread>(\r\n        this.messageApi.getUploadUrl(this.currentId), {\r\n          files,\r\n          from: this.role || \"owner\",\r\n        }, (progress, error) => {\r\n          this.uploadProgress = progress;\r\n        }).then((response) => {\r\n          this.newMessage.content = \"\";\r\n          this.setCurrent(response);\r\n          loader.dismiss();\r\n          return response;\r\n        }).catch((response) => {\r\n            loader.dismiss();\r\n            this.uiHelpers.showAlert(\"SALAXY.UI_Terms.error\", \"SALAXY.NG1.MessageThreadComponent.uploadFilesError\");\r\n            throw new Error(response);\r\n        });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Gets the file display related information.\r\n   * @param message Message that contains the file.\r\n   */\r\n  public getFileInfo(message: Message) {\r\n    // TODO: Move to a helper\r\n    const result = {\r\n      isImage: false,\r\n      previewUrl: null,\r\n      downloadUrl: null,\r\n      icon: null,\r\n    };\r\n    if (message.type !== \"blobFile\") {\r\n      return result;\r\n    }\r\n    result.isImage = true;\r\n    result.icon = this.uploadService.getFileIcon(message.content);\r\n    if (message.contentId) {\r\n      if (message.preview === message.contentId) {\r\n        result.previewUrl = this.uploadService.getPreviewUrl(message.preview);\r\n      }\r\n      result.downloadUrl = this.uploadService.getFileUrl(message.contentId);\r\n    }\r\n    return result;\r\n  }\r\n\r\n  /**\r\n   * Opens the list of calculations into a dialog window for selection and then adds them to payroll\r\n   * @param category Either \"paid\": Read-only, a copy is added ... or \"draft\": Editable, moved with status changed.\r\n   */\r\n  public addExistingCalc(category: \"paid\" | \"draft\" = \"draft\") {\r\n    const calculations = [];\r\n    this.uiHelpers.openEditDialog(\r\n      \"salaxy-components/modals/calc/CalcList.html\",\r\n      calculations,\r\n      {\r\n        title: (category === \"paid\" ? \"SALAXY.NG1.MessageThreadComponent.addExistingCalcCopy\" : \"SALAXY.NG1.MessageThreadComponent.addExistingCalcMove\"),\r\n        category,\r\n      }).then((result) => {\r\n        if (result.action === \"ok\" && calculations.length > 0) {\r\n          const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.MessageThreadComponent.addExistingCalcLoading\");\r\n          const messages = calculations.map((x) => {\r\n            const msg: Message = {\r\n              contentId: x.id,\r\n              fromParty: this.role || MessageFrom.Owner,\r\n              type: ThreadedMessageType.Calculation,\r\n            };\r\n            return msg;\r\n          });\r\n          this.current.messages.push(...messages);\r\n          this.save().then(() => {\r\n            loader.dismiss();\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Opens the list of payrolls into a dialog window for selection and then adds them to payroll\r\n   * @param category Either \"paid\": Read-only, a copy is added ... or \"draft\": Editable, moved with status changed.\r\n   */\r\n   public addExistingPayroll(category: \"paid\" | \"draft\" = \"draft\") {\r\n    const payrolls = [];\r\n    this.uiHelpers.openEditDialog(\r\n      \"salaxy-components/modals/payroll/PayrollList.html\",\r\n      payrolls,\r\n      {\r\n        title: (category === \"paid\" ? \"Maksetut\" : \"Luonnokset\"),\r\n        category,\r\n      }).then((result) => {\r\n        if (result.action === \"ok\" && payrolls.length > 0) {\r\n          const loader = this.uiHelpers.showLoading(\"Lisätään palkkalistoja\");\r\n          const messages = payrolls.map((x) => {\r\n            const msg: Message = {\r\n              contentId: x.id,\r\n              fromParty: this.role || MessageFrom.Owner,\r\n              type: ThreadedMessageType.Payroll,\r\n            };\r\n            return msg;\r\n          });\r\n          this.current.messages.push(...messages);\r\n          this.save().then(() => {\r\n            loader.dismiss();\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Navigates to the business object details page\r\n   * @param item The message item.\r\n   * @param defaultMessageDetailsUrl The URL for the default message details page.\r\n   */\r\n  public navigateToBusinessObject(item: MessageListItem, defaultMessageDetailsUrl: string) {\r\n    return this.getApi().getSingle(item.id).then( (messageThread: MessageThread) => {\r\n      const message = messageThread.messages?.find((x) => !!x.contentId && x.type === \"payroll\");\r\n      if (message) {\r\n        this.$location.path(\"payroll/details/\" + message.contentId);\r\n      }\r\n      else {\r\n        this.$location.path(defaultMessageDetailsUrl + item.id);\r\n      }\r\n    });\r\n  }\r\n\r\n  /** Deletes a message from the message list (must be saved still) */\r\n  public deleteMessage(item: Message) {\r\n    this.current.messages.splice(this.current.messages.findIndex((x) => x === item), 1);\r\n  }\r\n\r\n  private getCalculationListItem(id: string): Promise<CalculationListItem> {\r\n    return this.calculations.getOData({ $filter: `id eq '${id}'`}).then( (data: ODataResult<CalculationListItem>) => {\r\n      if (data.items.length == 1) {\r\n        return data.items[0];\r\n      } else {\r\n        return null;\r\n      }\r\n    });\r\n  }\r\n  private getPayrollListItem(id: string): Promise<PayrollListItem> {\r\n    return this.payrolls.getOData({ $filter: `id eq '${id}'`}).then( (data: ODataResult<PayrollListItem>) => {\r\n      if (data.items.length == 1) {\r\n        return data.items[0];\r\n      } else {\r\n        return null;\r\n      }\r\n    });\r\n  }\r\n}\r\n","import angular from \"angular\";\r\nimport { Ajax, Configs, OAuthMessage } from \"@salaxy/core\";\r\nimport { SessionService } from \"../../services\";\r\n\r\n/**\r\n * Controller for Omapalkka integration.\r\n */\r\nexport class OmapalkkaController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"AjaxNg1\", \"SessionService\", \"$sce\"];\r\n\r\n  private _url = null;\r\n  private _urlInProgress = false;\r\n\r\n  /**\r\n   * Creates a new ContactInfoController\r\n   * @ignore\r\n   */\r\n  constructor(private ajax: Ajax, private sessionService: SessionService, private $sce: angular.ISCEService) {\r\n    //\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit = () => {\r\n    // initialization\r\n  };\r\n\r\n  /** Gets the URL to the Omapalkka server with Google Firebase token. */\r\n  public get url() {\r\n    if (this.sessionService.isAuthenticated) {\r\n      if (!this._url) {\r\n        if (!this._urlInProgress) {\r\n          this._urlInProgress = true;\r\n          this.ajax.getJSON(`${Configs.current.getOmapalkkaApiServer()}/api/security/token`).then( (msg: OAuthMessage) => {\r\n            const embeddedUrl = `${Configs.current.getOmapalkkaServer()}/embedded.html#fb-token=${msg?.access_token}`;\r\n            // const embeddedUrl = `http://localhost:3000/embedded.html#fb-token=${msg?.access_token}`;\r\n            this._url = this.$sce.trustAsResourceUrl(embeddedUrl);\r\n          });\r\n        }\r\n      }\r\n    }\r\n    return this._url;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {\r\n  Calculation,\r\n  Language,\r\n  PensionCalculation,\r\n  PensionCompany,\r\n  Translations,\r\n} from \"@salaxy/core\";\r\n\r\nimport {\r\n  SessionService,\r\n  SettingsService,\r\n  UiHelpers,\r\n  EditDialogKnownActions\r\n} from \"../../services\";\r\n\r\n\r\n/**\r\n * Provides methods for profiled Welcome messages to the end user.\r\n */\r\nexport class VarmaBannerController implements angular.IController {\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"SessionService\",\r\n    \"SettingsService\",\r\n    \"UiHelpers\",\r\n    \"$sce\"\r\n  ];\r\n\r\n\r\n  /** Current calculation */\r\n  public calc: Calculation;\r\n\r\n  /** Pension Company*/\r\n  public pensionCompany: PensionCompany;\r\n\r\n  /** Varma banner/popup flags */\r\n  private _varmaPensionBanners = {\r\n    isReady: false,\r\n    showGetTyel: false,\r\n    showMoveTyel: false,\r\n    showGetYel: false,\r\n  };\r\n\r\n  /** Varma pop up dismissed flags */\r\n  private _dismissed = {\r\n    showGetTyel: false,\r\n    showMoveTyel: false,\r\n    showGetYel: [],\r\n    inStorage: false\r\n  };\r\n\r\n  /**\r\n   * Creates a new VarmaBannerController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    private sessionService: SessionService,\r\n    private settingsService: SettingsService,\r\n    private uiHelpers: UiHelpers,\r\n    private $sce: angular.ISCEService,\r\n  ) { }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    // initialization\r\n  }\r\n\r\n\r\n  /**\r\n   * Show the popup\r\n   */\r\n  public showVarmaPopup() {\r\n    let dialogData: any = {};\r\n\r\n    if (this.varmaPensionBanners.showGetTyel) {\r\n      dialogData = {\r\n        dismiss: () => this.dismiss(\"tyel\"),\r\n        varmaShopLink: this.getVarmaShopLink(),\r\n        title: Translations.get(\"SALAXY.NG1.VarmaBannerComponent.pensionPopup.tyel.title\"),\r\n        message: this.$sce.trustAsHtml(Translations.get(\"SALAXY.NG1.VarmaBannerComponent.pensionPopup.tyel.html\")),\r\n        btnText: Translations.get(\"SALAXY.NG1.VarmaBannerComponent.pensionPopup.tyel.btnText\")\r\n      };\r\n    } else if (this.varmaPensionBanners.showMoveTyel) {\r\n      dialogData = {\r\n        dismiss: () => this.dismiss(\"moveTyel\"),\r\n        varmaShopLink:  this.getVarmaShopLink(),\r\n        title: Translations.get(\"SALAXY.NG1.VarmaBannerComponent.pensionPopup.moveTyel.title\"),\r\n        message: this.$sce.trustAsHtml(Translations.get(\"SALAXY.NG1.VarmaBannerComponent.pensionPopup.moveTyel.html\",  {pensionCompany:  Translations.get(\"SALAXY.ENUM.PensionCompany.\" + this.settingsService.current?.calc.pensionContracts[0].company+ \".label\") })),\r\n        btnText: Translations.get(\"SALAXY.NG1.VarmaBannerComponent.pensionPopup.moveTyel.btnText\")\r\n      };\r\n    } else if (this.varmaPensionBanners.showGetYel) {\r\n      dialogData = {\r\n        dismiss: () => this.dismiss(\"yel\"),\r\n        varmaShopLink:  this.getVarmaShopLink(),\r\n        title: Translations.get(\"SALAXY.NG1.VarmaBannerComponent.pensionPopup.yel.title\"),\r\n        message: this.$sce.trustAsHtml(Translations.get(\"SALAXY.NG1.VarmaBannerComponent.pensionPopup.yel.html\")),\r\n        btnText: Translations.get(\"SALAXY.NG1.VarmaBannerComponent.pensionPopup.yel.btnText\")\r\n      };\r\n    }\r\n    if (dialogData.dismiss) {\r\n      this.uiHelpers.openEditDialog(\r\n        \"salaxy-components/modals/communications/VarmaPopup.html\",\r\n        dialogData,\r\n        null,\r\n        \"lg\").then((result)=> {\r\n          if(result.action == EditDialogKnownActions.Cancel){\r\n            dialogData.dismiss();\r\n          }\r\n        });\r\n    }\r\n  }\r\n\r\n\r\n  /** Gets the flags that indicate which popup to show. */\r\n  public get varmaPensionBanners(): {\r\n    /** if true, banner is ready to be shown */\r\n    isReady: boolean,\r\n    /** If true, shows popup that offers to get employee pension contract from Varma */\r\n    showGetTyel: boolean,\r\n    /** If true, shows popup that offrs to move employee pension contract from other company to Varma */\r\n    showMoveTyel: boolean,\r\n    /** If true, shows popup that offers to get entrepreneur pension contract from Varma */\r\n    showGetYel: boolean,\r\n  } {\r\n    this._varmaPensionBanners.isReady = !!this.calc && !!this.settingsService.current;\r\n    this._varmaPensionBanners.showGetTyel = this._varmaPensionBanners.isReady && this.isTyelCalculation && !this.dismissed.showGetTyel && (this.settingsService.current?.calc.pensionContracts.length == 0 || this.settingsService.current?.calc.pensionContracts.every((x) => !x.company));\r\n    this._varmaPensionBanners.showMoveTyel = this._varmaPensionBanners.isReady && this.isTyelCalculation && !this.dismissed.showMoveTyel && !this._varmaPensionBanners.showGetTyel && this.settingsService.current?.calc.pensionContracts.every((x) => x.company != PensionCompany.Varma) && this.settingsService.current?.calc.pensionContracts.every((x) => x.company != PensionCompany.None);\r\n    this._varmaPensionBanners.showGetYel = this._varmaPensionBanners.isReady && this.isYelCalculation && this.calc.worker?.employmentId && (this.dismissed.showGetYel.indexOf(this.calc.worker?.employmentId) < 0);\r\n    return this._varmaPensionBanners;\r\n  }\r\n\r\n   /** Get link to Varma pension contract shop with language parameter */\r\n   public getVarmaShopLink(): string {\r\n    if (!this.settingsService.current) {\r\n      return \"https://vaha.asiointi.varma.fi/vakuutushakemus/?PartnerID=Palkkaus&utm_source=partner&utm_medium=palkkaus\";\r\n    }\r\n    const userLang : Language = this.sessionService.session.currentAccount?.language ?? Language.Fi;\r\n\r\n    switch (userLang) {\r\n      case Language.Default:\r\n      case Language.Fi:\r\n        return \"https://vaha.asiointi.varma.fi/vakuutushakemus/?PartnerID=Palkkaus&utm_source=partner&utm_medium=palkkaus\";\r\n      case Language.Sv:\r\n        return \"https://vaha.asiointi.varma.fi/vakuutushakemus/?PartnerID=Palkkaus&langcode=sv&utm_source=partner&utm_medium=palkkaus\";\r\n      case Language.En:\r\n        return \"https://vaha.asiointi.varma.fi/vakuutushakemus/?PartnerID=Palkkaus&langcode=en&utm_source=partner&utm_medium=palkkaus\";\r\n    }\r\n  }\r\n\r\n  /** Adds dismissed to local storage to prevent the display of the popups again */\r\n  private dismiss(pension: \"tyel\" | \"moveTyel\" | \"yel\") {\r\n    switch (pension) {\r\n      case \"yel\":\r\n        if (this._dismissed.showGetYel.indexOf(this.calc.worker.employmentId) < 0) {\r\n          this._dismissed.showGetYel.push(this.calc.worker.employmentId);\r\n        }\r\n        break;\r\n      case \"tyel\":\r\n        {\r\n          this._dismissed.showGetTyel = true;\r\n        }\r\n        break;\r\n      case \"moveTyel\":\r\n        {\r\n          this._dismissed.showMoveTyel = true;\r\n        }\r\n        break;\r\n    }\r\n    this._dismissed.inStorage = true;\r\n    if (window.localStorage) {\r\n      window.localStorage.setItem(\"salaxy-varma-banner-dismissed\", JSON.stringify(this._dismissed));\r\n    }\r\n  }\r\n\r\n  /** Checks if the banner as been dismissed earlier */\r\n  private get dismissed() {\r\n    if (!this._dismissed.inStorage) {\r\n\r\n      if (window.localStorage) {\r\n        const json = window.localStorage.getItem(\"salaxy-varma-banner-dismissed\");\r\n        if (json) {\r\n          this._dismissed = JSON.parse(json);\r\n          this._dismissed.inStorage = true;\r\n        }\r\n      }\r\n\r\n    }\r\n    return this._dismissed;\r\n  }\r\n\r\n\r\n  /** Logic for determing the pension is for employee */\r\n  private get isTyelCalculation() {\r\n    if (!this.calc) {\r\n      return false;\r\n    }\r\n    return this.calc.result?.responsibilities?.pensionCalculation == PensionCalculation.Employee;\r\n  }\r\n\r\n  /** Logic for determing the pension is for entrepreneur */\r\n  private get isYelCalculation() {\r\n    if (!this.calc) {\r\n      return false;\r\n    }\r\n    return this.calc.result?.responsibilities?.pensionCalculation == PensionCalculation.Entrepreneur;\r\n  }\r\n\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {\r\n  ApiListItem, Avatar, Calculation, Dates,\r\n  EmploymentLogic,\r\n  EmploymentRelationTaxcard,\r\n  Iban,\r\n  InsuranceContract,\r\n  Overview, PensionContract, TaxCard2019Logic,\r\n  Taxcards, Texts,\r\n  WelcomeDataWorker,\r\n  WorkerListItem,\r\n  Workers\r\n} from \"@salaxy/core\";\r\n\r\nimport {\r\n  ReportsService,\r\n  SettingsService,\r\n  SessionService,\r\n  UiCrudHelpers,\r\n  UiHelpers,\r\n} from \"../../services\";\r\n\r\n/**\r\n * Provides methods for profiled Welcome messages to the end user.\r\n */\r\nexport class WelcomeController implements angular.IController {\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"SessionService\",\r\n    \"Workers\",\r\n    \"SettingsService\",\r\n    \"$location\",\r\n    \"UiCrudHelpers\",\r\n    \"$rootScope\",\r\n    \"Taxcards\",\r\n    \"Overview\",\r\n    \"UiHelpers\",\r\n    \"ReportsService\",\r\n  ];\r\n\r\n  /**\r\n   * If set to true, the settings are handled by proxy:\r\n   * we do not ask the user to change the settings in\r\n   * the Welcome screen (mainly Pension or Insurance).\r\n   */\r\n  public settingsByProxy;\r\n\r\n  /** Worker home page UI properties */\r\n  public workerUI: {\r\n    isReady?: boolean,\r\n    /** If true, worker has added taxcard. */\r\n    taxCardAdded?: boolean,\r\n  } = {};\r\n\r\n  /** Welcome page (timeline) data forr the Worker role */\r\n  public workerDataNew: WelcomeDataWorker;\r\n\r\n  public workerList: WorkerListItem[] = [];\r\n\r\n\r\n  /** Start date for filtering list of calculations with status \"PaymentStarted\". Displayed on front page */\r\n  public paymentStartedWarningStartDate = Dates.getToday();\r\n  /** End date for filtering list of calculations with status \"PaymentStarted\". Displayed on front page */\r\n  public paymentStartedWarningEndDate =  Dates.add(this.paymentStartedWarningStartDate, -6, \"month\");\r\n\r\n  private workerListStatus: \"initial\" | \"loading\" | \"loaded\" = \"initial\";\r\n\r\n  private initialOwner: string;\r\n\r\n\r\n  /**\r\n   * Creates a new WelcomeController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    private session: SessionService,\r\n    private workers: Workers,\r\n    private settingsService: SettingsService,\r\n    private $location: angular.ILocationService,\r\n    private uiCrudHelpers: UiCrudHelpers,\r\n    private $rootScope: angular.IRootScopeService,\r\n    private taxcards: Taxcards,\r\n    private overview: Overview,\r\n    private uiHelpers: UiHelpers,\r\n    private reportsService: ReportsService,\r\n  ) { }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit = () => {\r\n    this.loadWelcomeData();\r\n    this.session.subscribe(this.$rootScope, () => {\r\n      this.loadWelcomeData();\r\n    });\r\n  };\r\n\r\n\r\n  /**\r\n   * Gets a preview URL for the image.\r\n   * Currently only for a taxcard, but may later support other items.\r\n   */\r\n  // eslint-disable-next-line\r\n  public getPreviewUrl(item: ApiListItem) {\r\n    // Previews disabled for every item 10.6.2021 /MJ\r\n    return null;\r\n  }\r\n\r\n  /**\r\n   * Returns the url where to download the tax card\r\n   * @param taxCard Taxcard or if null, the current is used.\r\n   */\r\n  public getTaxcardDownloadUrl(taxCard): string {\r\n    return this.taxcards.getDownloadUrl(taxCard);\r\n  }\r\n\r\n  /**\r\n   * Moves the browser to create-new calculation screen\r\n   * @param employmentId Identifier for the Employment relation for which to create the calculation.\r\n   */\r\n  public createNewCalculationFor = (employmentId: string): void => {\r\n    this.$location.path(\"/calc/details/\" + employmentId + \"/new-for-employment\");\r\n  };\r\n\r\n  /** Gets the current pension product or empty object */\r\n  public getPension(): PensionContract {\r\n    return this.settingsService.current?.calc.pensionContracts.find( (x) =>\r\n     Dates.isSameOrAfter(\"today\", x.startDate ?? \"1900-01-01\") &&\r\n     Dates.isBefore(\"today\", Dates.add(x.endDate ?? \"2100-01-01\", 1,\"day\"))) || {};\r\n  }\r\n\r\n  /** Gets the current insurance product or empty object */\r\n  public getInsurance(): InsuranceContract {\r\n    return this.settingsService.current?.calc.insuranceContracts.find( (x) =>\r\n     Dates.isSameOrAfter(\"today\", x.startDate ?? \"1900-01-01\") &&\r\n     Dates.isBefore(\"today\", Dates.add(x.endDate ?? \"2100-01-01\", 1,\"day\"))) || {};\r\n  }\r\n\r\n  /**\r\n   * Loads the welcome data from the server.\r\n   */\r\n  public loadWelcomeData() {\r\n    if (this.session.isSessionChecked && this.session.isAuthenticated) {\r\n      const owner = this.session.session.currentAccount.owner;\r\n      if (this.initialOwner != owner){\r\n        this.initialOwner = owner;\r\n        this.workerDataNew = undefined;\r\n        this.workerUI = {};\r\n        this.settingsByProxy = false;\r\n        this.workerList = [];\r\n        this.workerListStatus = \"initial\";\r\n\r\n        if (this.session.isInRole(\"person\")) {\r\n          this.loadWorkerData();\r\n        } else if (this.session.isInRole(\"company\")) {\r\n          this.loadCompanyData();\r\n        }\r\n      }\r\n    }\r\n    else {\r\n      this.initialOwner = null;\r\n      this.workerDataNew = undefined;\r\n      this.workerUI = {};\r\n      this.settingsByProxy = false;\r\n      this.workerList = [];\r\n      this.workerListStatus = \"initial\";\r\n    }\r\n  }\r\n\r\n  /** Loads the Worker role data and UI. */\r\n  public loadWorkerData() {\r\n    this.overview.getWelcomeDataWorker().then((result) => {\r\n      this.workerDataNew = result;\r\n      this.workerUI = {\r\n        isReady: true,\r\n        taxCardAdded: !!result.activeTaxcard,\r\n      };\r\n    });\r\n  }\r\n\r\n  /** Loads worker list initially */\r\n  public loadWorkers(): Promise<WorkerListItem[]> {\r\n    if (this.workerListStatus === \"loaded\") {\r\n      return Promise.resolve(this.workerList);\r\n    } else {\r\n      this.workerListStatus = \"loading\";\r\n      // Only fetch first 50 workers (first page). Selection should not be shown if more than 49 workers / next page.\r\n      return this.workers.getOData({}).then((data) => {\r\n        this.workerList = data.items;\r\n        this.workerListStatus = \"loaded\";\r\n        return this.workerList;\r\n      });\r\n    }\r\n  }\r\n\r\n  /** Loads the welcome data from the server for Company role */\r\n  public loadCompanyData() {\r\n    // TODO\r\n  }\r\n\r\n  /**\r\n   * Gets the URL for a calculation pdf.\r\n   * If report has not been saved (ID is null), returns null.\r\n   * @param calc - Calculation. This method requires that the calculation has been saved.\r\n   * @param inline - if false, downloads the pdf file\r\n   * @returns Url for specified report\r\n   */\r\n  public getPdfUrl(calc: Calculation, inline = false) {\r\n    if (!calc) {\r\n      return null;\r\n    }\r\n\r\n    return this.reportsService.getPdfUrlForCalc(\"salarySlip\", calc.id, inline);\r\n  }\r\n\r\n  /**\r\n   * Gets the chart data for taxcard, labels, colors and other settings.\r\n   * Uses chartCache to avoid $digest loop.\r\n   */\r\n   public get taxcardChartData() {\r\n    if (!this.workerDataNew || !this.workerDataNew.activeTaxcard) {\r\n      return null;\r\n    }\r\n   if (!this.workerDataNew.activeTaxcard.card.incomeLimit){\r\n      return {config: this.uiHelpers.cache(this, \"pieChartV2\",\r\n      () => TaxCard2019Logic.getPieChartDataV2(this.workerDataNew.activeTaxcard),\r\n      () => TaxCard2019Logic.getIncomeLimitInfo(this.workerDataNew.activeTaxcard)), limits:TaxCard2019Logic.getIncomeLimitInfo(this.workerDataNew.activeTaxcard)};\r\n    }\r\n    return {config: this.uiHelpers.cache(this, \"lineChartV2\",\r\n    () => TaxCard2019Logic.getMainChartV2(this.workerDataNew.activeTaxcard),\r\n    () => TaxCard2019Logic.getIncomeLimitInfo(this.workerDataNew.activeTaxcard)), limits:TaxCard2019Logic.getIncomeLimitInfo(this.workerDataNew.activeTaxcard)};\r\n  }\r\n\r\n  /**\r\n   * Gets the chart data for taxcard, labels, colors and other settings.\r\n   * Uses chartCache to avoid $digest loop.\r\n   */\r\n  public get taxcardMobileChartData() {\r\n    if (!this.workerDataNew || !this.workerDataNew.activeTaxcard) {\r\n      return null;\r\n    }\r\n    return this.uiHelpers.cache(this, \"lineChartMobileV2\",\r\n      () => {\r\n       const data = TaxCard2019Logic.getMainChartV2(this.workerDataNew.activeTaxcard);\r\n       data.options.plugins.legend.display = false;\r\n       // TODO ? data.options.scales.yAxes.display = false;\r\n       return data;\r\n      },\r\n      () => TaxCard2019Logic.getIncomeLimitInfo(this.workerDataNew.activeTaxcard));\r\n  }\r\n\r\n  /** Calls the Worker wizard and if a Worker is added, starts a calculation for that worker. */\r\n  public launchEmploymentWizard() {\r\n    this.uiCrudHelpers.createNewEmployment().then((result) => {\r\n      if (result.action === \"ok\") {\r\n        this.createNewCalculationFor(result.item.id);\r\n      }\r\n    });\r\n  }\r\n\r\n  /** Gets the flags that indicate which tutorials to show. */\r\n  public get tutorials(): {\r\n    /** If true, shows info box that the site is runnin in anonymous mode. */\r\n    showAnon: boolean,\r\n    /** If true, should direct the user to create the first Worker */\r\n    showAddWorker: boolean,\r\n    /** If true, should direct user to create a new calculation.  */\r\n    showAddCalculation: boolean,\r\n    /** If true, should ask the user for digital signature. */\r\n    showSign: boolean,\r\n    /** If true, should ask the user to fill in the Pension contract information. */\r\n    showPension: boolean,\r\n    /** If true, should ask the user to fill in the Accident Insurance contract information. */\r\n    showInsurance: boolean,\r\n    /** If true, should promote Payroll feature. */\r\n    showTryPayroll: boolean,\r\n    /** If true, should promote new features. */\r\n    showNewFeatures: boolean\r\n  } {\r\n    const result = {\r\n      showAnon: false,\r\n      showAddWorker: false,\r\n      showAddCalculation: true,\r\n      showSign: false,\r\n      showPension: false,\r\n      showInsurance: false,\r\n      showTryPayroll: false,\r\n      showNewFeatures: false\r\n    };\r\n    if (!this.session.isSessionChecked) {\r\n      return result;\r\n    }\r\n    if (!this.session.isAuthenticated) {\r\n      result.showAnon = true;\r\n      return result;\r\n    }\r\n    if (!this.settingsByProxy) {\r\n      if (!this.session.checkAccountVerification()) {\r\n        result.showSign = true;\r\n      }\r\n      result.showPension = this.settingsService.current?.calc.pensionContracts.length == 0 || this.settingsService.current?.calc.pensionContracts.every( (x) => !x.company);\r\n      result.showInsurance = this.settingsService.current?.calc.pensionContracts.length == 0 || this.settingsService.current?.calc.insuranceContracts.every( (x) => !x.company);\r\n    }\r\n    switch (this.workerListStatus) {\r\n      case \"loaded\":\r\n        if (this.workerList.length === 0) {\r\n          result.showAddWorker = true;\r\n          return result;\r\n        }\r\n        if (this.workerList.length > 45) {\r\n          result.showAddCalculation = false;\r\n          return result;\r\n        }\r\n        break;\r\n      case \"loading\":\r\n        return result;\r\n      case \"initial\":\r\n        this.loadWorkers();\r\n        return result;\r\n    }\r\n    result.showAddCalculation = true;\r\n    return result;\r\n  }\r\n\r\n  /**\r\n   * Returns system alert html.\r\n   */\r\n  public get systemAlertHtml(): string {\r\n    if (!this.session) {\r\n      return null;\r\n    }\r\n\r\n    const userSession = this.session.getSession();\r\n    if (!userSession) {\r\n      return null;\r\n    }\r\n\r\n    const html = userSession.systemAlertHtml;\r\n    if (!html) {\r\n      return null;\r\n    }\r\n    return html;\r\n  }\r\n\r\n  /**\r\n   * Returns true if system alert exists.\r\n   */\r\n  public get hasSystemAlert(): boolean {\r\n    return !!this.systemAlertHtml;\r\n  }\r\n\r\n  /**\r\n   * Filters preloaded workers.\r\n   * Avatar values are formatted and ID is employment ID insteead of worker ID.\r\n   */\r\n  public filterWorkers = (searchString: string): any[] => {\r\n    let searchResult = [];\r\n\r\n    if (!searchString) {\r\n      searchResult = this.workerList.slice(0, 30).map(this.getAvatar);\r\n    } else {\r\n      searchString = (searchString || \"\").trim().toLowerCase();\r\n      searchResult = this.workerList\r\n        .filter((w) =>\r\n          (w.otherPartyInfo.avatar.displayName || \"\").toLowerCase().indexOf(searchString) >= 0 ||\r\n          (w.otherPartyInfo.avatar.sortableName || \"\").toLowerCase().indexOf(searchString) >= 0 ||\r\n          (w.otherPartyInfo.telephone || \"\").toLowerCase().indexOf(searchString) >= 0 ||\r\n          (w.otherPartyInfo.email || \"\").toLowerCase().indexOf(searchString) >= 0 ||\r\n          (w.id || \"\").toLowerCase().indexOf(searchString) === 0 ||\r\n          (w.otherPartyInfo.officialId || \"\").toLowerCase().indexOf(searchString) === 0)\r\n        .map(this.getAvatar);\r\n    }\r\n\r\n    return searchResult.map(item => {\r\n      return {\r\n        value: item.id,\r\n        title: item.description,\r\n        text: item.displayName + \" (\" + (item as any).displayId + \")\",\r\n        ui: item\r\n      };\r\n    });\r\n  };\r\n\r\n  /** Gets the display name for the selected worker. */\r\n  public getWorkerName = (avatarId: string): string => {\r\n    for (const worker of this.workerList) {\r\n      if (avatarId === worker.otherId) {\r\n        return Texts.escapeHtml(this.getAvatar(worker).displayName);\r\n      }\r\n    }\r\n    return avatarId;\r\n  };\r\n\r\n  /**\r\n   * Searches all workers and checks if manual/auto taxcard is enabled\r\n   */\r\n  public showAutoTaxcardInfobox(): boolean {\r\n    if(this.workerList.length) {\r\n      return !this.workerList.some(x => x.data.taxcard === EmploymentRelationTaxcard.Auto || x.data.taxcard === EmploymentRelationTaxcard.Manual);\r\n    }\r\n  }\r\n\r\n  private getAvatar = (worker: WorkerListItem): Avatar => {\r\n    const result: Avatar = Object.assign({}, worker.otherPartyInfo.avatar);\r\n    (result as any).displayId =\r\n      ((worker.id || \"\").startsWith(\"FI\") ? Iban.formatIban(worker.id) + \" / \" : \"\")\r\n      + (worker.otherPartyInfo.officialId ? worker.otherPartyInfo.officialId : \"-\")\r\n      ;\r\n    result.displayName = Texts.escapeHtml(result.displayName);\r\n    result.description = Texts.escapeHtml(EmploymentLogic.getDescription(worker.otherPartyInfo, worker?.data.type, worker?.data.pensionCalculation));\r\n    result.id = worker.id;\r\n    return result;\r\n  };\r\n}","import angular from \"angular\";\r\n\r\nimport { Objects } from \"@salaxy/core\";\r\n\r\nimport { FormGroupLabelType } from \"./FormGroupLabelType\";\r\n\r\n/**\r\n * Base controller for form control groups (label, input, validation errors etc.).\r\n */\r\nexport class InputBase<T> implements angular.IController {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public static crudBindings = {\r\n\r\n    /** Name of the input - also used as id. */\r\n    name: \"@\",\r\n\r\n    /** Label for the control */\r\n    label: \"@\",\r\n\r\n    /**\r\n     * @deprecated Use \"require\" instead:\r\n     * This attribute overlaps with required/ng-required directive, which produces unexpected results.\r\n     */\r\n    required: \"@\",\r\n\r\n    /** If true the field is required (form validation) */\r\n    require: \"<\",\r\n\r\n    /**\r\n     * Expression for read-only display of the input control\r\n     * This is visualized in a different way than readonly: The input is not shown and display is more compact.\r\n     */\r\n    readOnly: \"<\",\r\n\r\n    /** Expression for ng-readonly of the input */\r\n    readonly: \"<\",\r\n\r\n    /** Expression for ng-disabled of the input */\r\n    disabled: \"<\",\r\n\r\n    /**\r\n     * Positioning of the label of form-control.\r\n     * Supported values are \"horizontal\" (default), \"no-label\", \"plain\" and \"basic\".\r\n     * See FormGourpLabelType for details.\r\n     */\r\n    labelType: \"@\",\r\n\r\n    /**\r\n     * Label columns expressed as Bootstrap grid columns. Supports multiple classes (e.g. \"col-xs-4 col-sm-2\").\r\n     * Default is 'col-sm-4' for label-type: 'horizontal' and 'col-sm-12' for label-type: 'no-label'.\r\n     * Other label-types do not have column classes at the moment.\r\n     */\r\n    labelCols: \"@\",\r\n\r\n    /** Placeholder text */\r\n    placeholder: \"@\",\r\n\r\n    /**\r\n     * TooltipHtml adds an info button after the input which opens a uib-popover-html.\r\n     */\r\n    tooltipHtml: \"@\",\r\n\r\n    /** Options for ui.bootstrap.popover */\r\n    tooltipPlacement: \"@\",\r\n\r\n    /**\r\n     * Disables the default validation error message.\r\n     * Use this if you want to create custom error messages in the UI.\r\n     */\r\n    disableValidationErrors: \"<\",\r\n\r\n    /**\r\n     * Style of the input.\r\n     * Supports empty or 'openClose'\r\n     */\r\n     inputMode: \"@\",\r\n\r\n     // TODO: tsekkaa nämä ja kommentoi\r\n     onSelectFunction: \"<\",\r\n     inputFormatter: \"<\",\r\n     getOptions: \"<\",\r\n  };\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [];\r\n\r\n  /** Label for the control. If not set, it is derived from name. */\r\n  public label: string;\r\n\r\n  /**\r\n   * Positioning of the label of form-control.\r\n   * Supported values are \"horizontal\" (default), \"no-label\" | \"plain\" | \"basic\" | \"empty-label\" | \"inline\".\r\n   * See FormGourpLabelType for details.\r\n   */\r\n  public labelType: FormGroupLabelType;\r\n\r\n  /** The model that is bound to the input */\r\n  public model: angular.INgModelController;\r\n\r\n  /** Form controller, if available */\r\n  public form: angular.IFormController;\r\n\r\n  /** The value of the input */\r\n  public value: T;\r\n\r\n  /** Form control name */\r\n  public name: string;\r\n\r\n  /** List of validation error texts (typically language version keys that should be translated). */\r\n  public validationErrors: string[] = [];\r\n\r\n  /** Placeholder text */\r\n  public placeholder: string;\r\n\r\n  /**\r\n   * @deprecated Use \"require\" instead:\r\n   * This attribute overlaps with required/ng-required directive, which produces unexpected results.\r\n   */\r\n  public required: string;\r\n\r\n  /**\r\n   * If true, displays the control as read-only div instead of the input control.\r\n   * This \"read-only\" attribute is visualized in a different way than standard html \"readonly\" (ng-readonly):\r\n   * The input is not shown and display is more compact.\r\n   * Also note, that you may change the same read-only for the form using readonly / ng-readonly attribute.\r\n   * @example\r\n   * ```html\r\n   * <form name=\"foo\" ng-readonly=\"true\">\r\n   * <!-- .... or plain HTML ... -->\r\n   * <form name=\"foo\" readonly=\"true\">\r\n   * <!-- .... or plain HTML ... -->\r\n   * <salaxy-input name=\"input1\" read-only=\"true\"></salaxy-input>\r\n   * ```\r\n   */\r\n  public readOnly: boolean;\r\n\r\n  /** If true, disabled is set on the input with ng-disabled */\r\n  public disabled: boolean;\r\n\r\n  /** Placement of tooltip button */\r\n  public tooltipPlacement: string;\r\n\r\n  /** Defines HTML for tooltip button */\r\n  public tooltipHtml: string;\r\n\r\n  /**\r\n   * Style of the input.\r\n   * If null or empty, displays normal input.\r\n   * - \"openeClose\" shows readOnly-like input with toggle button to open the field for editing.\r\n   * Recommended to use when only one or few fields of the form are expected to be edited.\r\n   */\r\n  public inputMode: \"\" | \"openClose\";\r\n\r\n  private _onInitValue = this.onInitValue;\r\n\r\n  private requirePendingUpdate: boolean | undefined;\r\n\r\n\r\n  /**\r\n   * Creates a new InputController\r\n   * @ignore\r\n   */\r\n  constructor() {\r\n    /* */\r\n  }\r\n\r\n  /**\r\n   * Set the values and defaults on init.\r\n   * When overridding at derived classes, do your own stuff first and then call this method\r\n   * because this method calls validate() at the end.\r\n   */\r\n  public $onInit() {\r\n    if(this.tooltipHtml && !this.tooltipPlacement){\r\n      this.tooltipPlacement = \"top\";\r\n    }\r\n    if (!this.name) {\r\n      throw new Error(`Property 'name' is required for Salaxy form controls (label: ${this.label}).`);\r\n    }\r\n    if (this.name && this.label == null) {\r\n      this.label = this.name;\r\n    }\r\n    if (this.requirePendingUpdate) {\r\n      this.require = true;\r\n      this.requirePendingUpdate = undefined;\r\n    }\r\n    this.model.$render = () => {\r\n      this.value = this.model.$viewValue;\r\n      if (this._onInitValue) {\r\n        this._onInitValue();\r\n        this._onInitValue = null;\r\n      }\r\n    };\r\n    this.validate();\r\n  }\r\n\r\n  /** Gets or sets the presence of the required validator in the underlying model. */\r\n  public get require(): boolean {\r\n    return !!this.model?.$validators.required;\r\n  }\r\n  public set require(value: boolean) {\r\n    if (!this.model) {\r\n      this.requirePendingUpdate = value;\r\n      return;\r\n    }\r\n    const hasRequiredValidator = !!this.model.$validators.required;\r\n    if (value && !hasRequiredValidator) {\r\n      this.model.$validators.required = (modelValue, viewValue) => {\r\n        return !this.model.$isEmpty(viewValue);\r\n      };\r\n    } else if (!value && hasRequiredValidator) {\r\n      delete this.model.$validators.required;\r\n    }\r\n  }\r\n\r\n  /** Gets the readonly value either from the controller or from the form */\r\n  protected getReadOnly(): boolean {\r\n    // This readOnly can be true, false or undefined\r\n    const readOnlyValue = (this.readOnly + \"\").trim().toLowerCase();\r\n    if (readOnlyValue === \"true\" || readOnlyValue === \"1\") {\r\n      return true;\r\n    }\r\n    if (readOnlyValue === \"false\" || readOnlyValue === \"0\") {\r\n      return false;\r\n    }\r\n    const readOnlyFormValue = !!this?.form?.$$element[0]?.attributes?.readonly;\r\n    if (readOnlyFormValue) {\r\n      return true;\r\n    }\r\n\r\n    return false;\r\n  }\r\n\r\n  /** Gets the disabled value either from the controller or from the form */\r\n  protected getDisabled(): boolean {\r\n    if (this.disabled) {\r\n      return true;\r\n    }\r\n    if (this.form && this.form.$$element && this.form.$$element[0]) {\r\n      return !!this.form.$$element[0].attributes.disabled;\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /** Returns the placeholder text: We will probably add stuff about validation here if not explicitly set. */\r\n  protected getPlaceholder() {\r\n    return this.placeholder;\r\n  }\r\n\r\n  /** Gets the tooltip HTML with necessary escape. */\r\n  protected getToolTipHtml() {\r\n    // TODO: Add escaping if necessary.\r\n    return this.tooltipHtml;\r\n  }\r\n\r\n  /** On change of the value, do preventive operations and set value to model. */\r\n  protected onChange() {\r\n    this.model.$setViewValue(this.value);\r\n    this.validate();\r\n  }\r\n\r\n  /** Do validations. Automatically called on onInit() and onChange() */\r\n  protected validate() {\r\n    const validationErrors = [];\r\n    for (const validationErrorKey in this.model.$error) {\r\n      if (Objects.has(this.model.$error, validationErrorKey) && validationErrorKey !== \"parse\") {\r\n        validationErrors.push(\"SALAXY.VALIDATION.ValidationErrors.\" + validationErrorKey);\r\n      }\r\n    }\r\n    this.modifyValidationErrors(validationErrors, this.validationErrors);\r\n    if (this.validationErrors.length > 0) {\r\n      return false;\r\n    }\r\n    return true;\r\n  }\r\n\r\n  /** Called after initial value assignment. Called only once.  */\r\n  protected onInitValue() {\r\n    // empty\r\n  }\r\n\r\n  private modifyValidationErrors(source: string[], target: string[]) {\r\n    // check if source values differ from target\r\n    if (angular.equals(source, target)) {\r\n      return;\r\n    }\r\n    // remove values\r\n    target.splice(0, target.length);\r\n    // add values\r\n    target.push(...source);\r\n  }\r\n}\r\n","!function(e,t){\"object\"==typeof exports&&\"object\"==typeof module?module.exports=t():\"function\"==typeof define&&define.amd?define([],t):\"object\"==typeof exports?exports.AirDatepicker=t():e.AirDatepicker=t()}(this,(function(){return function(){\"use strict\";var e={d:function(t,i){for(var s in i)e.o(i,s)&&!e.o(t,s)&&Object.defineProperty(t,s,{enumerable:!0,get:i[s]})},o:function(e,t){return Object.prototype.hasOwnProperty.call(e,t)}},t={};e.d(t,{default:function(){return R}});var i={days:\"days\",months:\"months\",years:\"years\",day:\"day\",month:\"month\",year:\"year\",eventChangeViewDate:\"changeViewDate\",eventChangeCurrentView:\"changeCurrentView\",eventChangeFocusDate:\"changeFocusDate\",eventChangeSelectedDate:\"changeSelectedDate\",eventChangeTime:\"changeTime\",eventChangeLastSelectedDate:\"changeLastSelectedDate\",actionSelectDate:\"selectDate\",actionUnselectDate:\"unselectDate\",cssClassWeekend:\"-weekend-\"},s={classes:\"\",inline:!1,locale:{days:[\"Воскресенье\",\"Понедельник\",\"Вторник\",\"Среда\",\"Четверг\",\"Пятница\",\"Суббота\"],daysShort:[\"Вос\",\"Пон\",\"Вто\",\"Сре\",\"Чет\",\"Пят\",\"Суб\"],daysMin:[\"Вс\",\"Пн\",\"Вт\",\"Ср\",\"Чт\",\"Пт\",\"Сб\"],months:[\"Январь\",\"Февраль\",\"Март\",\"Апрель\",\"Май\",\"Июнь\",\"Июль\",\"Август\",\"Сентябрь\",\"Октябрь\",\"Ноябрь\",\"Декабрь\"],monthsShort:[\"Янв\",\"Фев\",\"Мар\",\"Апр\",\"Май\",\"Июн\",\"Июл\",\"Авг\",\"Сен\",\"Окт\",\"Ноя\",\"Дек\"],today:\"Сегодня\",clear:\"Очистить\",dateFormat:\"dd.MM.yyyy\",timeFormat:\"HH:mm\",firstDay:1},startDate:new Date,firstDay:\"\",weekends:[6,0],dateFormat:\"\",altField:\"\",altFieldDateFormat:\"T\",toggleSelected:!0,keyboardNav:!0,selectedDates:!1,container:\"\",isMobile:!1,visible:!1,position:\"bottom left\",offset:12,view:i.days,minView:i.days,showOtherMonths:!0,selectOtherMonths:!0,moveToOtherMonthsOnSelect:!0,showOtherYears:!0,selectOtherYears:!0,moveToOtherYearsOnSelect:!0,minDate:\"\",maxDate:\"\",disableNavWhenOutOfRange:!0,multipleDates:!1,multipleDatesSeparator:\", \",range:!1,dynamicRange:!0,buttons:!1,monthsField:\"monthsShort\",showEvent:\"focus\",autoClose:!1,fixedHeight:!1,prevHtml:'<svg><path d=\"M 17,12 l -5,5 l 5,5\"></path></svg>',nextHtml:'<svg><path d=\"M 14,12 l 5,5 l -5,5\"></path></svg>',navTitles:{days:\"MMMM, <i>yyyy</i>\",months:\"yyyy\",years:\"yyyy1 - yyyy2\"},timepicker:!1,onlyTimepicker:!1,dateTimeSeparator:\" \",timeFormat:\"\",minHours:0,maxHours:24,minMinutes:0,maxMinutes:59,hoursStep:1,minutesStep:1,onSelect:!1,onChangeViewDate:!1,onChangeView:!1,onRenderCell:!1,onShow:!1,onHide:!1,onClickDayName:!1};function a(e){let t=arguments.length>1&&void 0!==arguments[1]?arguments[1]:document;return\"string\"==typeof e?t.querySelector(e):e}function n(){let{tagName:e=\"div\",className:t=\"\",innerHtml:i=\"\",id:s=\"\",attrs:a={}}=arguments.length>0&&void 0!==arguments[0]?arguments[0]:{},n=document.createElement(e);return t&&n.classList.add(...t.split(\" \")),s&&(n.id=s),i&&(n.innerHTML=i),a&&r(n,a),n}function r(e,t){for(let[i,s]of Object.entries(t))void 0!==s&&e.setAttribute(i,s);return e}function o(e){return new Date(e.getFullYear(),e.getMonth()+1,0).getDate()}function h(e){let t=e.getHours(),{hours:i,dayPeriod:s}=l(t);return{year:e.getFullYear(),month:e.getMonth(),fullMonth:e.getMonth()+1<10?\"0\"+(e.getMonth()+1):e.getMonth()+1,date:e.getDate(),fullDate:e.getDate()<10?\"0\"+e.getDate():e.getDate(),day:e.getDay(),hours:t,fullHours:d(t),hours12:i,dayPeriod:s,fullHours12:d(i),minutes:e.getMinutes(),fullMinutes:e.getMinutes()<10?\"0\"+e.getMinutes():e.getMinutes()}}function l(e){return{dayPeriod:e>11?\"pm\":\"am\",hours:e%12==0?12:e%12}}function d(e){return e<10?\"0\"+e:e}function c(e){let t=10*Math.floor(e.getFullYear()/10);return[t,t+9]}function u(){let e=[];for(var t=arguments.length,i=new Array(t),s=0;s<t;s++)i[s]=arguments[s];return i.forEach((t=>{if(\"object\"==typeof t)for(let i in t)t[i]&&e.push(i);else t&&e.push(t)})),e.join(\" \")}function p(e,t){let s=arguments.length>2&&void 0!==arguments[2]?arguments[2]:i.days;if(!e||!t)return!1;let a=h(e),n=h(t);return{[i.days]:a.date===n.date&&a.month===n.month&&a.year===n.year,[i.months]:a.month===n.month&&a.year===n.year,[i.years]:a.year===n.year}[s]}function m(e,t,i){let s=g(e,!1).getTime(),a=g(t,!1).getTime();return i?s>=a:s>a}function v(e,t){return!m(e,t,!0)}function g(e){let t=!(arguments.length>1&&void 0!==arguments[1])||arguments[1],i=new Date(e.getTime());return\"boolean\"!=typeof t||t||function(e){e.setHours(0,0,0,0)}(i),i}function D(e,t,i){e.length?e.forEach((e=>{e.addEventListener(t,i)})):e.addEventListener(t,i)}function y(e,t){return!(!e||e===document||e instanceof DocumentFragment)&&(e.matches(t)?e:y(e.parentNode,t))}function f(e,t,i){return e>i?i:e<t?t:e}function w(e){for(var t=arguments.length,i=new Array(t>1?t-1:0),s=1;s<t;s++)i[s-1]=arguments[s];return i.filter((e=>e)).forEach((t=>{for(let[i,s]of Object.entries(t))if(void 0!==s&&\"[object Object]\"===s.toString()){let t=void 0!==e[i]?e[i].toString():void 0,a=s.toString(),n=Array.isArray(s)?[]:{};e[i]=e[i]?t!==a?n:e[i]:n,w(e[i],s)}else e[i]=s})),e}function b(e){let t=e;return e instanceof Date||(\"string\"==typeof e&&/^\\d{4}-\\d{2}-\\d{2}$/.test(e)&&(e+=\"T00:00:00\"),t=new Date(e)),isNaN(t.getTime())&&(console.log(`Unable to convert value \"${e}\" to Date object`),t=!1),t}function k(e){let t=\"\\\\s|\\\\.|-|/|\\\\\\\\|,|\\\\$|\\\\!|\\\\?|:|;\";return new RegExp(\"(^|>|\"+t+\")(\"+e+\")($|<|\"+t+\")\",\"g\")}function $(e,t,i){return(t=function(e){var t=function(e,t){if(\"object\"!=typeof e||null===e)return e;var i=e[Symbol.toPrimitive];if(void 0!==i){var s=i.call(e,\"string\");if(\"object\"!=typeof s)return s;throw new TypeError(\"@@toPrimitive must return a primitive value.\")}return String(e)}(e);return\"symbol\"==typeof t?t:String(t)}(t))in e?Object.defineProperty(e,t,{value:i,enumerable:!0,configurable:!0,writable:!0}):e[t]=i,e}class C{constructor(){let{type:e,date:t,dp:i,opts:s,body:a}=arguments.length>0&&void 0!==arguments[0]?arguments[0]:{};$(this,\"focus\",(()=>{this.$cell.classList.add(\"-focus-\"),this.focused=!0})),$(this,\"removeFocus\",(()=>{this.$cell.classList.remove(\"-focus-\"),this.focused=!1})),$(this,\"select\",(()=>{this.$cell.classList.add(\"-selected-\"),this.selected=!0})),$(this,\"removeSelect\",(()=>{this.$cell.classList.remove(\"-selected-\",\"-range-from-\",\"-range-to-\"),this.selected=!1})),$(this,\"onChangeSelectedDate\",(()=>{this.isDisabled||(this._handleSelectedStatus(),this.opts.range&&this._handleRangeStatus())})),$(this,\"onChangeFocusDate\",(e=>{if(!e)return void(this.focused&&this.removeFocus());let t=p(e,this.date,this.type);t?this.focus():!t&&this.focused&&this.removeFocus(),this.opts.range&&this._handleRangeStatus()})),$(this,\"render\",(()=>(this.$cell.innerHTML=this._getHtml(),this._handleClasses(),this.$cell))),this.type=e,this.singleType=this.type.slice(0,-1),this.date=t,this.dp=i,this.opts=s,this.body=a,this.customData=!1,this.init()}init(){var e;let{onRenderCell:t}=this.opts;t&&(this.customData=t({date:this.date,cellType:this.singleType,datepicker:this.dp})),this._createElement(),this._bindDatepickerEvents(),null!==(e=this.customData)&&void 0!==e&&e.disabled&&this.dp.disableDate(this.date)}_bindDatepickerEvents(){this.dp.on(i.eventChangeSelectedDate,this.onChangeSelectedDate),this.dp.on(i.eventChangeFocusDate,this.onChangeFocusDate)}unbindDatepickerEvents(){this.dp.off(i.eventChangeSelectedDate,this.onChangeSelectedDate),this.dp.off(i.eventChangeFocusDate,this.onChangeFocusDate)}_createElement(){var e;let{year:t,month:i,date:s}=h(this.date),a=(null===(e=this.customData)||void 0===e?void 0:e.attrs)||{};this.$cell=n({attrs:{\"data-year\":t,\"data-month\":i,\"data-date\":s,...a}}),this.$cell.adpCell=this}_getClassName(){var e;let t=new Date,{selectOtherMonths:s,selectOtherYears:a}=this.opts,{minDate:n,maxDate:r,isDateDisabled:o}=this.dp,{day:l}=h(this.date),d=this._isOutOfMinMaxRange(),c=o(this.date),m=u(\"air-datepicker-cell\",`-${this.singleType}-`,{\"-current-\":p(t,this.date,this.type),\"-min-date-\":n&&p(n,this.date,this.type),\"-max-date-\":r&&p(r,this.date,this.type)}),v=\"\";switch(this.type){case i.days:v=u({\"-weekend-\":this.dp.isWeekend(l),\"-other-month-\":this.isOtherMonth,\"-disabled-\":this.isOtherMonth&&!s||d||c});break;case i.months:v=u({\"-disabled-\":d});break;case i.years:v=u({\"-other-decade-\":this.isOtherDecade,\"-disabled-\":d||this.isOtherDecade&&!a})}return u(m,v,null===(e=this.customData)||void 0===e?void 0:e.classes).split(\" \")}_getHtml(){var e;let{year:t,month:s,date:a}=h(this.date),{showOtherMonths:n,showOtherYears:r}=this.opts;if(null!==(e=this.customData)&&void 0!==e&&e.html)return this.customData.html;switch(this.type){case i.days:return!n&&this.isOtherMonth?\"\":a;case i.months:return this.dp.locale[this.opts.monthsField][s];case i.years:return!r&&this.isOtherDecade?\"\":t}}_isOutOfMinMaxRange(){let{minDate:e,maxDate:t}=this.dp,{type:s,date:a}=this,{month:n,year:r,date:o}=h(a),l=s===i.days,d=s===i.years,c=!!e&&new Date(r,d?e.getMonth():n,l?o:e.getDate()),u=!!t&&new Date(r,d?t.getMonth():n,l?o:t.getDate());return e&&t?v(c,e)||m(u,t):e?v(c,e):t?m(u,t):void 0}destroy(){this.unbindDatepickerEvents()}_handleRangeStatus(){const{selectedDates:e,focusDate:t,rangeDateTo:i,rangeDateFrom:s}=this.dp,a=e.length;if(!a)return;let n=s,r=i;if(1===a&&t){const i=m(t,e[0]);n=i?e[0]:t,r=i?t:e[0]}let o=u({\"-in-range-\":n&&r&&(h=this.date,l=n,d=r,m(h,l)&&v(h,d)),\"-range-from-\":n&&p(this.date,n,this.type),\"-range-to-\":r&&p(this.date,r,this.type)});var h,l,d;this.$cell.classList.remove(\"-range-from-\",\"-range-to-\",\"-in-range-\"),o&&this.$cell.classList.add(...o.split(\" \"))}_handleSelectedStatus(){let e=this.dp._checkIfDateIsSelected(this.date,this.type);e?this.select():!e&&this.selected&&this.removeSelect()}_handleInitialFocusStatus(){p(this.dp.focusDate,this.date,this.type)&&this.focus()}_handleClasses(){this.$cell.setAttribute(\"class\",\"\"),this._handleInitialFocusStatus(),this.dp.hasSelectedDates&&(this._handleSelectedStatus(),this.dp.opts.range&&this._handleRangeStatus()),this.$cell.classList.add(...this._getClassName())}get isDisabled(){return this.$cell.matches(\".-disabled-\")}get isOtherMonth(){return this.dp.isOtherMonth(this.date)}get isOtherDecade(){return this.dp.isOtherDecade(this.date)}}function _(e,t,i){return(t=function(e){var t=function(e,t){if(\"object\"!=typeof e||null===e)return e;var i=e[Symbol.toPrimitive];if(void 0!==i){var s=i.call(e,\"string\");if(\"object\"!=typeof s)return s;throw new TypeError(\"@@toPrimitive must return a primitive value.\")}return String(e)}(e);return\"symbol\"==typeof t?t:String(t)}(t))in e?Object.defineProperty(e,t,{value:i,enumerable:!0,configurable:!0,writable:!0}):e[t]=i,e}let M={[i.days]:`<div class=\"air-datepicker-body--day-names\"></div><div class=\"air-datepicker-body--cells -${i.days}-\"></div>`,[i.months]:`<div class=\"air-datepicker-body--cells -${i.months}-\"></div>`,[i.years]:`<div class=\"air-datepicker-body--cells -${i.years}-\"></div>`};const S=\".air-datepicker-cell\";class T{constructor(e){let{dp:t,type:s,opts:a}=e;_(this,\"handleClick\",(e=>{let t=e.target.closest(S).adpCell;if(t.isDisabled)return;if(!this.dp.isMinViewReached)return void this.dp.down();let i=this.dp._checkIfDateIsSelected(t.date,t.type);i?this.dp._handleAlreadySelectedDates(i,t.date):this.dp.selectDate(t.date)})),_(this,\"handleDayNameClick\",(e=>{let t=e.target.getAttribute(\"data-day-index\");this.opts.onClickDayName({dayIndex:Number(t),datepicker:this.dp})})),_(this,\"onChangeCurrentView\",(e=>{e!==this.type?this.hide():(this.show(),this.render())})),_(this,\"onMouseOverCell\",(e=>{let t=y(e.target,S);this.dp.setFocusDate(!!t&&t.adpCell.date)})),_(this,\"onMouseOutCell\",(()=>{this.dp.setFocusDate(!1)})),_(this,\"onClickBody\",(e=>{let{onClickDayName:t}=this.opts,i=e.target;i.closest(S)&&this.handleClick(e),t&&i.closest(\".air-datepicker-body--day-name\")&&this.handleDayNameClick(e)})),_(this,\"onMouseDown\",(e=>{this.pressed=!0;let t=y(e.target,S),i=t&&t.adpCell;p(i.date,this.dp.rangeDateFrom)&&(this.rangeFromFocused=!0),p(i.date,this.dp.rangeDateTo)&&(this.rangeToFocused=!0)})),_(this,\"onMouseMove\",(e=>{if(!this.pressed||!this.dp.isMinViewReached)return;e.preventDefault();let t=y(e.target,S),i=t&&t.adpCell,{selectedDates:s,rangeDateTo:a,rangeDateFrom:n}=this.dp;if(!i||i.isDisabled)return;let{date:r}=i;if(2===s.length){if(this.rangeFromFocused&&!m(r,a)){let{hours:e,minutes:t}=h(n);r.setHours(e),r.setMinutes(t),this.dp.rangeDateFrom=r,this.dp.replaceDate(n,r)}if(this.rangeToFocused&&!v(r,n)){let{hours:e,minutes:t}=h(a);r.setHours(e),r.setMinutes(t),this.dp.rangeDateTo=r,this.dp.replaceDate(a,r)}}})),_(this,\"onMouseUp\",(()=>{this.pressed=!1,this.rangeFromFocused=!1,this.rangeToFocused=!1})),_(this,\"onChangeViewDate\",((e,t)=>{if(!this.isVisible)return;let s=c(e),a=c(t);switch(this.dp.currentView){case i.days:if(p(e,t,i.months))return;break;case i.months:if(p(e,t,i.years))return;break;case i.years:if(s[0]===a[0]&&s[1]===a[1])return}this.render()})),_(this,\"render\",(()=>{this.destroyCells(),this._generateCells(),this.cells.forEach((e=>{this.$cells.appendChild(e.render())}))})),this.dp=t,this.type=s,this.opts=a,this.cells=[],this.$el=\"\",this.pressed=!1,this.isVisible=!0,this.init()}init(){this._buildBaseHtml(),this.type===i.days&&this.renderDayNames(),this.render(),this._bindEvents(),this._bindDatepickerEvents()}_bindEvents(){let{range:e,dynamicRange:t}=this.opts;D(this.$el,\"mouseover\",this.onMouseOverCell),D(this.$el,\"mouseout\",this.onMouseOutCell),D(this.$el,\"click\",this.onClickBody),e&&t&&(D(this.$el,\"mousedown\",this.onMouseDown),D(this.$el,\"mousemove\",this.onMouseMove),D(window.document,\"mouseup\",this.onMouseUp))}_bindDatepickerEvents(){this.dp.on(i.eventChangeViewDate,this.onChangeViewDate),this.dp.on(i.eventChangeCurrentView,this.onChangeCurrentView)}_buildBaseHtml(){this.$el=n({className:`air-datepicker-body -${this.type}-`,innerHtml:M[this.type]}),this.$names=a(\".air-datepicker-body--day-names\",this.$el),this.$cells=a(\".air-datepicker-body--cells\",this.$el)}_getDayNamesHtml(){let e=arguments.length>0&&void 0!==arguments[0]?arguments[0]:this.dp.locale.firstDay,t=\"\",s=this.dp.isWeekend,{onClickDayName:a}=this.opts,n=e,r=0;for(;r<7;){let e=n%7;t+=`<div class=\"${u(\"air-datepicker-body--day-name\",{[i.cssClassWeekend]:s(e),\"-clickable-\":!!a})}\" data-day-index='${e}'>${this.dp.locale.daysMin[e]}</div>`,r++,n++}return t}renderDayNames(){this.$names.innerHTML=this._getDayNamesHtml()}_generateCell(e){let{type:t,dp:i,opts:s}=this;return new C({type:t,dp:i,opts:s,date:e,body:this})}_generateCells(){T.getDatesFunction(this.type)(this.dp,(e=>{this.cells.push(this._generateCell(e))}))}show(){this.isVisible=!0,this.$el.classList.remove(\"-hidden-\")}hide(){this.isVisible=!1,this.$el.classList.add(\"-hidden-\")}destroyCells(){this.cells.forEach((e=>e.destroy())),this.cells=[],this.$cells.innerHTML=\"\"}destroy(){this.destroyCells(),this.dp.off(i.eventChangeViewDate,this.onChangeViewDate),this.dp.off(i.eventChangeCurrentView,this.onChangeCurrentView)}static getDaysDates(e,t){let{viewDate:i,opts:{fixedHeight:s},locale:{firstDay:a}}=e,n=o(i),{year:r,month:l}=h(i),d=new Date(r,l,1),c=new Date(r,l,n),u=d.getDay()-a,p=6-c.getDay()+a;u=u<0?u+7:u,p=p>6?p-7:p;let m=function(e,t){let{year:i,month:s,date:a}=h(e);return new Date(i,s,a-t)}(d,u),v=n+u+p,g=m.getDate(),{year:D,month:y}=h(m),f=0;s&&(v=42);const w=[];for(;f<v;){let e=new Date(D,y,g+f);t&&t(e),w.push(e),f++}return w}static getMonthsDates(e,t){let{year:i}=e.parsedViewDate,s=0,a=[];for(;s<12;){const e=new Date(i,s);a.push(e),t&&t(e),s++}return a}static getYearsDates(e,t){let i=c(e.viewDate),s=i[0]-1,a=i[1]+1,n=s,r=[];for(;n<=a;){const e=new Date(n,0);r.push(e),t&&t(e),n++}return r}static getDatesFunction(){let e=arguments.length>0&&void 0!==arguments[0]?arguments[0]:i.days;return{[i.days]:T.getDaysDates,[i.months]:T.getMonthsDates,[i.years]:T.getYearsDates}[e]}}function F(e,t,i){return(t=function(e){var t=function(e,t){if(\"object\"!=typeof e||null===e)return e;var i=e[Symbol.toPrimitive];if(void 0!==i){var s=i.call(e,\"string\");if(\"object\"!=typeof s)return s;throw new TypeError(\"@@toPrimitive must return a primitive value.\")}return String(e)}(e);return\"symbol\"==typeof t?t:String(t)}(t))in e?Object.defineProperty(e,t,{value:i,enumerable:!0,configurable:!0,writable:!0}):e[t]=i,e}class V{constructor(e){let{dp:t,opts:i}=e;F(this,\"onClickNav\",(e=>{let t=y(e.target,\".air-datepicker-nav--action\");if(!t)return;let i=t.dataset.action;this.dp[i]()})),F(this,\"onChangeViewDate\",(()=>{this.render(),this._resetNavStatus(),this.handleNavStatus()})),F(this,\"onChangeCurrentView\",(()=>{this.render(),this._resetNavStatus(),this.handleNavStatus()})),F(this,\"onClickNavTitle\",(()=>{this.dp.isFinalView||this.dp.up()})),F(this,\"update\",(()=>{let{prevHtml:e,nextHtml:t}=this.opts;this.$prev.innerHTML=e,this.$next.innerHTML=t,this._resetNavStatus(),this.render(),this.handleNavStatus()})),F(this,\"renderDelay\",(()=>{setTimeout(this.render)})),F(this,\"render\",(()=>{this.$title.innerHTML=this._getTitle(),function(e,t){for(let i in t)t[i]?e.classList.add(i):e.classList.remove(i)}(this.$title,{\"-disabled-\":this.dp.isFinalView})})),this.dp=t,this.opts=i,this.init()}init(){this._createElement(),this._buildBaseHtml(),this._defineDOM(),this.render(),this.handleNavStatus(),this._bindEvents(),this._bindDatepickerEvents()}_defineDOM(){this.$title=a(\".air-datepicker-nav--title\",this.$el),this.$prev=a('[data-action=\"prev\"]',this.$el),this.$next=a('[data-action=\"next\"]',this.$el)}_bindEvents(){this.$el.addEventListener(\"click\",this.onClickNav),this.$title.addEventListener(\"click\",this.onClickNavTitle)}_bindDatepickerEvents(){this.dp.on(i.eventChangeViewDate,this.onChangeViewDate),this.dp.on(i.eventChangeCurrentView,this.onChangeCurrentView),this.isNavIsFunction&&(this.dp.on(i.eventChangeSelectedDate,this.renderDelay),this.dp.opts.timepicker&&this.dp.on(i.eventChangeTime,this.render))}destroy(){this.dp.off(i.eventChangeViewDate,this.onChangeViewDate),this.dp.off(i.eventChangeCurrentView,this.onChangeCurrentView),this.isNavIsFunction&&(this.dp.off(i.eventChangeSelectedDate,this.renderDelay),this.dp.opts.timepicker&&this.dp.off(i.eventChangeTime,this.render))}_createElement(){this.$el=n({tagName:\"nav\",className:\"air-datepicker-nav\"})}_getTitle(){let{dp:e,opts:t}=this,i=t.navTitles[e.currentView];return\"function\"==typeof i?i(e):e.formatDate(e.viewDate,i)}handleNavStatus(){let{disableNavWhenOutOfRange:e}=this.opts,{minDate:t,maxDate:s}=this.dp;if(!t&&!s||!e)return;let{year:a,month:n}=this.dp.parsedViewDate,r=!!t&&h(t),o=!!s&&h(s);switch(this.dp.currentView){case i.days:t&&r.month>=n&&r.year>=a&&this._disableNav(\"prev\"),s&&o.month<=n&&o.year<=a&&this._disableNav(\"next\");break;case i.months:t&&r.year>=a&&this._disableNav(\"prev\"),s&&o.year<=a&&this._disableNav(\"next\");break;case i.years:{let e=c(this.dp.viewDate);t&&r.year>=e[0]&&this._disableNav(\"prev\"),s&&o.year<=e[1]&&this._disableNav(\"next\");break}}}_disableNav(e){a('[data-action=\"'+e+'\"]',this.$el).classList.add(\"-disabled-\")}_resetNavStatus(){!function(e){for(var t=arguments.length,i=new Array(t>1?t-1:0),s=1;s<t;s++)i[s-1]=arguments[s];e.length?e.forEach((e=>{e.classList.remove(...i)})):e.classList.remove(...i)}(this.$el.querySelectorAll(\".air-datepicker-nav--action\"),\"-disabled-\")}_buildBaseHtml(){let{prevHtml:e,nextHtml:t}=this.opts;this.$el.innerHTML=`<div class=\"air-datepicker-nav--action\" data-action=\"prev\">${e}</div><div class=\"air-datepicker-nav--title\"></div><div class=\"air-datepicker-nav--action\" data-action=\"next\">${t}</div>`}get isNavIsFunction(){let{navTitles:e}=this.opts;return Object.keys(e).find((t=>\"function\"==typeof e[t]))}}var x={today:{content:e=>e.locale.today,onClick:e=>e.setViewDate(new Date)},clear:{content:e=>e.locale.clear,onClick:e=>e.clear()}};class H{constructor(e){let{dp:t,opts:i}=e;this.dp=t,this.opts=i,this.init()}init(){this.createElement(),this.render()}createElement(){this.$el=n({className:\"air-datepicker-buttons\"})}destroy(){this.$el.parentNode.removeChild(this.$el)}clearHtml(){return this.$el.innerHTML=\"\",this}generateButtons(){let{buttons:e}=this.opts;Array.isArray(e)||(e=[e]),e.forEach((e=>{let t=e;\"string\"==typeof e&&x[e]&&(t=x[e]);let i=this.createButton(t);t.onClick&&this.attachEventToButton(i,t.onClick),this.$el.appendChild(i)}))}attachEventToButton(e,t){e.addEventListener(\"click\",(()=>{t(this.dp)}))}createButton(e){let{content:t,className:i,tagName:s=\"button\",attrs:a={}}=e;return n({tagName:s,innerHtml:`<span tabindex='-1'>${\"function\"==typeof t?t(this.dp):t}</span>`,className:u(\"air-datepicker-button\",i),attrs:a})}render(){this.generateButtons()}}function E(e,t,i){return(t=function(e){var t=function(e,t){if(\"object\"!=typeof e||null===e)return e;var i=e[Symbol.toPrimitive];if(void 0!==i){var s=i.call(e,\"string\");if(\"object\"!=typeof s)return s;throw new TypeError(\"@@toPrimitive must return a primitive value.\")}return String(e)}(e);return\"symbol\"==typeof t?t:String(t)}(t))in e?Object.defineProperty(e,t,{value:i,enumerable:!0,configurable:!0,writable:!0}):e[t]=i,e}class L{constructor(){let{opts:e,dp:t}=arguments.length>0&&void 0!==arguments[0]?arguments[0]:{};E(this,\"toggleTimepickerIsActive\",(e=>{this.dp.timepickerIsActive=e})),E(this,\"onChangeSelectedDate\",(e=>{let{date:t,updateTime:i=!1}=e;t&&(this.setMinMaxTime(t),this.setCurrentTime(!!i&&t),this.addTimeToDate(t))})),E(this,\"onChangeLastSelectedDate\",(e=>{e&&(this.setTime(e),this.render())})),E(this,\"onChangeInputRange\",(e=>{let t=e.target;this[t.getAttribute(\"name\")]=t.value,this.updateText(),this.dp.trigger(i.eventChangeTime,{hours:this.hours,minutes:this.minutes})})),E(this,\"onMouseEnterLeave\",(e=>{let t=e.target.getAttribute(\"name\"),i=this.$minutesText;\"hours\"===t&&(i=this.$hoursText),i.classList.toggle(\"-focus-\")})),E(this,\"onFocus\",(()=>{this.toggleTimepickerIsActive(!0)})),E(this,\"onBlur\",(()=>{this.toggleTimepickerIsActive(!1)})),this.opts=e,this.dp=t;let{timeFormat:s}=this.dp.locale;s&&(s.match(k(\"h\"))||s.match(k(\"hh\")))&&(this.ampm=!0),this.init()}init(){this.setTime(this.dp.lastSelectedDate||this.dp.viewDate),this.createElement(),this.buildHtml(),this.defineDOM(),this.render(),this.bindDatepickerEvents(),this.bindDOMEvents()}bindDatepickerEvents(){this.dp.on(i.eventChangeSelectedDate,this.onChangeSelectedDate),this.dp.on(i.eventChangeLastSelectedDate,this.onChangeLastSelectedDate)}bindDOMEvents(){let e=\"input\";navigator.userAgent.match(/trident/gi)&&(e=\"change\"),D(this.$ranges,e,this.onChangeInputRange),D(this.$ranges,\"mouseenter\",this.onMouseEnterLeave),D(this.$ranges,\"mouseleave\",this.onMouseEnterLeave),D(this.$ranges,\"focus\",this.onFocus),D(this.$ranges,\"mousedown\",this.onFocus),D(this.$ranges,\"blur\",this.onBlur)}createElement(){this.$el=n({className:u(\"air-datepicker-time\",{\"-am-pm-\":this.dp.ampm})})}destroy(){this.dp.off(i.eventChangeSelectedDate,this.onChangeSelectedDate),this.dp.off(i.eventChangeLastSelectedDate,this.onChangeLastSelectedDate),this.$el.parentNode.removeChild(this.$el)}buildHtml(){let{ampm:e,hours:t,displayHours:i,minutes:s,minHours:a,minMinutes:n,maxHours:r,maxMinutes:o,dayPeriod:h,opts:{hoursStep:l,minutesStep:c}}=this;this.$el.innerHTML=`<div class=\"air-datepicker-time--current\">   <span class=\"air-datepicker-time--current-hours\">${d(i)}</span>   <span class=\"air-datepicker-time--current-colon\">:</span>   <span class=\"air-datepicker-time--current-minutes\">${d(s)}</span>   `+(e?`<span class='air-datepicker-time--current-ampm'>${h}</span>`:\"\")+'</div><div class=\"air-datepicker-time--sliders\">   <div class=\"air-datepicker-time--row\">'+`      <input type=\"range\" name=\"hours\" value=\"${t}\" min=\"${a}\" max=\"${r}\" step=\"${l}\"/>   </div>   <div class=\"air-datepicker-time--row\">`+`      <input type=\"range\" name=\"minutes\" value=\"${s}\" min=\"${n}\" max=\"${o}\" step=\"${c}\"/>   </div></div>`}defineDOM(){let e=e=>a(e,this.$el);this.$ranges=this.$el.querySelectorAll('[type=\"range\"]'),this.$hours=e('[name=\"hours\"]'),this.$minutes=e('[name=\"minutes\"]'),this.$hoursText=e(\".air-datepicker-time--current-hours\"),this.$minutesText=e(\".air-datepicker-time--current-minutes\"),this.$ampm=e(\".air-datepicker-time--current-ampm\")}setTime(e){this.setMinMaxTime(e),this.setCurrentTime(e)}addTimeToDate(e){e&&(e.setHours(this.hours),e.setMinutes(this.minutes))}setMinMaxTime(e){if(this.setMinMaxTimeFromOptions(),e){let{minDate:t,maxDate:i}=this.dp;t&&p(e,t)&&this.setMinTimeFromMinDate(t),i&&p(e,i)&&this.setMaxTimeFromMaxDate(i)}}setCurrentTime(e){let{hours:t,minutes:i}=e?h(e):this;this.hours=f(t,this.minHours,this.maxHours),this.minutes=f(i,this.minMinutes,this.maxMinutes)}setMinMaxTimeFromOptions(){let{minHours:e,minMinutes:t,maxHours:i,maxMinutes:s}=this.opts;this.minHours=f(e,0,23),this.minMinutes=f(t,0,59),this.maxHours=f(i,0,23),this.maxMinutes=f(s,0,59)}setMinTimeFromMinDate(e){let{lastSelectedDate:t}=this.dp;this.minHours=e.getHours(),t&&t.getHours()>e.getHours()?this.minMinutes=this.opts.minMinutes:this.minMinutes=e.getMinutes()}setMaxTimeFromMaxDate(e){let{lastSelectedDate:t}=this.dp;this.maxHours=e.getHours(),t&&t.getHours()<e.getHours()?this.maxMinutes=this.opts.maxMinutes:this.maxMinutes=e.getMinutes()}updateSliders(){r(this.$hours,{min:this.minHours,max:this.maxHours}).value=this.hours,r(this.$minutes,{min:this.minMinutes,max:this.maxMinutes}).value=this.minutes}updateText(){this.$hoursText.innerHTML=d(this.displayHours),this.$minutesText.innerHTML=d(this.minutes),this.ampm&&(this.$ampm.innerHTML=this.dayPeriod)}set hours(e){this._hours=e;let{hours:t,dayPeriod:i}=l(e);this.displayHours=this.ampm?t:e,this.dayPeriod=i}get hours(){return this._hours}render(){this.updateSliders(),this.updateText()}}function O(e,t,i){return(t=function(e){var t=function(e,t){if(\"object\"!=typeof e||null===e)return e;var i=e[Symbol.toPrimitive];if(void 0!==i){var s=i.call(e,\"string\");if(\"object\"!=typeof s)return s;throw new TypeError(\"@@toPrimitive must return a primitive value.\")}return String(e)}(e);return\"symbol\"==typeof t?t:String(t)}(t))in e?Object.defineProperty(e,t,{value:i,enumerable:!0,configurable:!0,writable:!0}):e[t]=i,e}class A{constructor(e){let{dp:t,opts:i}=e;O(this,\"pressedKeys\",new Set),O(this,\"hotKeys\",new Map([[[[\"Control\",\"ArrowRight\"],[\"Control\",\"ArrowUp\"]],e=>e.month++],[[[\"Control\",\"ArrowLeft\"],[\"Control\",\"ArrowDown\"]],e=>e.month--],[[[\"Shift\",\"ArrowRight\"],[\"Shift\",\"ArrowUp\"]],e=>e.year++],[[[\"Shift\",\"ArrowLeft\"],[\"Shift\",\"ArrowDown\"]],e=>e.year--],[[[\"Alt\",\"ArrowRight\"],[\"Alt\",\"ArrowUp\"]],e=>e.year+=10],[[[\"Alt\",\"ArrowLeft\"],[\"Alt\",\"ArrowDown\"]],e=>e.year-=10],[[\"Control\",\"Shift\",\"ArrowUp\"],(e,t)=>t.up()]])),O(this,\"handleHotKey\",(e=>{let t=this.hotKeys.get(e),i=h(this.getInitialFocusDate());t(i,this.dp);let{year:s,month:a,date:n}=i,r=o(new Date(s,a));r<n&&(n=r);let l=this.dp.getClampedDate(new Date(s,a,n));this.dp.setFocusDate(l,{viewDateTransition:!0})})),O(this,\"isHotKeyPressed\",(()=>{let e=!1,t=this.pressedKeys.size,i=e=>this.pressedKeys.has(e);for(let[s]of this.hotKeys){if(e)break;if(Array.isArray(s[0]))s.forEach((a=>{e||t!==a.length||(e=a.every(i)&&s)}));else{if(t!==s.length)continue;e=s.every(i)&&s}}return e})),O(this,\"isArrow\",(e=>e>=37&&e<=40)),O(this,\"onKeyDown\",(e=>{let{key:t,which:i}=e,{dp:s,dp:{focusDate:a},opts:n}=this;this.registerKey(t);let r=this.isHotKeyPressed();if(r)return e.preventDefault(),void this.handleHotKey(r);if(this.isArrow(i))return e.preventDefault(),void this.focusNextCell(t);if(\"Enter\"===t){if(s.currentView!==n.minView)return void s.down();if(a){let e=s._checkIfDateIsSelected(a);return void(e?s._handleAlreadySelectedDates(e,a):s.selectDate(a))}}\"Escape\"===t&&this.dp.hide()})),O(this,\"onKeyUp\",(e=>{this.removeKey(e.key)})),this.dp=t,this.opts=i,this.init()}init(){this.bindKeyboardEvents()}bindKeyboardEvents(){let{$el:e}=this.dp;e.addEventListener(\"keydown\",this.onKeyDown),e.addEventListener(\"keyup\",this.onKeyUp)}destroy(){let{$el:e}=this.dp;e.removeEventListener(\"keydown\",this.onKeyDown),e.removeEventListener(\"keyup\",this.onKeyUp),this.hotKeys=null,this.pressedKeys=null}getInitialFocusDate(){let{focusDate:e,currentView:t,selectedDates:s,parsedViewDate:{year:a,month:n}}=this.dp,r=e||s[s.length-1];if(!r)switch(t){case i.days:r=new Date(a,n,(new Date).getDate());break;case i.months:r=new Date(a,n,1);break;case i.years:r=new Date(a,0,1)}return r}focusNextCell(e){let t=this.getInitialFocusDate(),{currentView:s}=this.dp,{days:a,months:n,years:r}=i,o=h(t),l=o.year,d=o.month,c=o.date;switch(e){case\"ArrowLeft\":s===a&&(c-=1),s===n&&(d-=1),s===r&&(l-=1);break;case\"ArrowUp\":s===a&&(c-=7),s===n&&(d-=3),s===r&&(l-=4);break;case\"ArrowRight\":s===a&&(c+=1),s===n&&(d+=1),s===r&&(l+=1);break;case\"ArrowDown\":s===a&&(c+=7),s===n&&(d+=3),s===r&&(l+=4)}let u=this.dp.getClampedDate(new Date(l,d,c));this.dp.setFocusDate(u,{viewDateTransition:!0})}registerKey(e){this.pressedKeys.add(e)}removeKey(e){this.pressedKeys.delete(e)}}let N={on(e,t){this.__events||(this.__events={}),this.__events[e]?this.__events[e].push(t):this.__events[e]=[t]},off(e,t){this.__events&&this.__events[e]&&(this.__events[e]=this.__events[e].filter((e=>e!==t)))},removeAllEvents(){this.__events={}},trigger(e){for(var t=arguments.length,i=new Array(t>1?t-1:0),s=1;s<t;s++)i[s-1]=arguments[s];this.__events&&this.__events[e]&&this.__events[e].forEach((e=>{e(...i)}))}};function I(e,t,i){return(t=function(e){var t=function(e,t){if(\"object\"!=typeof e||null===e)return e;var i=e[Symbol.toPrimitive];if(void 0!==i){var s=i.call(e,\"string\");if(\"object\"!=typeof s)return s;throw new TypeError(\"@@toPrimitive must return a primitive value.\")}return String(e)}(e);return\"symbol\"==typeof t?t:String(t)}(t))in e?Object.defineProperty(e,t,{value:i,enumerable:!0,configurable:!0,writable:!0}):e[t]=i,e}let P=\"\",j=\"\",B=!1;class R{static buildGlobalContainer(e){B=!0,P=n({className:e,id:e}),a(\"body\").appendChild(P)}constructor(e,t){var r=this;if(I(this,\"viewIndexes\",[i.days,i.months,i.years]),I(this,\"next\",(()=>{let{year:e,month:t}=this.parsedViewDate;switch(this.currentView){case i.days:this.setViewDate(new Date(e,t+1,1));break;case i.months:this.setViewDate(new Date(e+1,t,1));break;case i.years:this.setViewDate(new Date(e+10,0,1))}})),I(this,\"prev\",(()=>{let{year:e,month:t}=this.parsedViewDate;switch(this.currentView){case i.days:this.setViewDate(new Date(e,t-1,1));break;case i.months:this.setViewDate(new Date(e-1,t,1));break;case i.years:this.setViewDate(new Date(e-10,0,1))}})),I(this,\"_finishHide\",(()=>{this.hideAnimation=!1,this._destroyComponents(),this.$container.removeChild(this.$datepicker)})),I(this,\"setPosition\",(function(e){let t=arguments.length>1&&void 0!==arguments[1]&&arguments[1];if(\"function\"==typeof(e=e||r.opts.position))return void(r.customHide=e({$datepicker:r.$datepicker,$target:r.$el,$pointer:r.$pointer,isViewChange:t,done:r._finishHide}));let i,s,{isMobile:a}=r.opts,n=r.$el.getBoundingClientRect(),o=r.$el.getBoundingClientRect(),h=r.$datepicker.offsetParent,l=r.$el.offsetParent,d=r.$datepicker.getBoundingClientRect(),c=e.split(\" \"),u=window.scrollY,p=window.scrollX,m=r.opts.offset,v=c[0],g=c[1];if(a)r.$datepicker.style.cssText=\"left: 50%; top: 50%\";else{if(h===l&&h!==document.body&&(o={top:r.$el.offsetTop,left:r.$el.offsetLeft,width:n.width,height:r.$el.offsetHeight},u=0,p=0),h!==l&&h!==document.body){let e=h.getBoundingClientRect();o={top:n.top-e.top,left:n.left-e.left,width:n.width,height:n.height},u=0,p=0}switch(v){case\"top\":i=o.top-d.height-m;break;case\"right\":s=o.left+o.width+m;break;case\"bottom\":i=o.top+o.height+m;break;case\"left\":s=o.left-d.width-m}switch(g){case\"top\":i=o.top;break;case\"right\":s=o.left+o.width-d.width;break;case\"bottom\":i=o.top+o.height-d.height;break;case\"left\":s=o.left;break;case\"center\":/left|right/.test(v)?i=o.top+o.height/2-d.height/2:s=o.left+o.width/2-d.width/2}r.$datepicker.style.cssText=`left: ${s+p}px; top: ${i+u}px`}})),I(this,\"_setInputValue\",(()=>{let{opts:e,$altField:t,locale:{dateFormat:i}}=this,{altFieldDateFormat:s,altField:a}=e;a&&t&&(t.value=this._getInputValue(s)),this.$el.value=this._getInputValue(i)})),I(this,\"_getInputValue\",(e=>{let{selectedDates:t,opts:i}=this,{multipleDates:s,multipleDatesSeparator:a}=i;if(!t.length)return\"\";let n=\"function\"==typeof e,r=n?e(s?t:t[0]):t.map((t=>this.formatDate(t,e)));return r=n?r:r.join(a),r})),I(this,\"_checkIfDateIsSelected\",(function(e){let t=arguments.length>1&&void 0!==arguments[1]?arguments[1]:i.days,s=!1;return r.selectedDates.some((i=>{let a=p(e,i,t);return s=a&&i,a})),s})),I(this,\"_scheduleCallAfterTransition\",(e=>{this._cancelScheduledCall(),e&&e(!1),this._onTransitionEnd=()=>{e&&e(!0)},this.$datepicker.addEventListener(\"transitionend\",this._onTransitionEnd,{once:!0})})),I(this,\"_cancelScheduledCall\",(()=>{this.$datepicker.removeEventListener(\"transitionend\",this._onTransitionEnd)})),I(this,\"setViewDate\",(e=>{if(!((e=b(e))instanceof Date))return;if(p(e,this.viewDate))return;let t=this.viewDate;this.viewDate=e;let{onChangeViewDate:s}=this.opts;if(s){let{month:e,year:t}=this.parsedViewDate;s({month:e,year:t,decade:this.curDecade})}this.trigger(i.eventChangeViewDate,e,t)})),I(this,\"setFocusDate\",(function(e){let t=arguments.length>1&&void 0!==arguments[1]?arguments[1]:{};(!e||(e=b(e))instanceof Date)&&(r.focusDate=e,r.trigger(i.eventChangeFocusDate,e,t))})),I(this,\"setCurrentView\",(function(e){let t=arguments.length>1&&void 0!==arguments[1]?arguments[1]:{};if(r.viewIndexes.includes(e)){if(r.currentView=e,r.elIsInput&&r.visible&&r.setPosition(void 0,!0),r.trigger(i.eventChangeCurrentView,e),!r.views[e]){let t=r.views[e]=new T({dp:r,opts:r.opts,type:e});r.shouldUpdateDOM&&r.$content.appendChild(t.$el)}r.opts.onChangeView&&!t.silent&&r.opts.onChangeView(e)}})),I(this,\"_updateLastSelectedDate\",(e=>{this.lastSelectedDate=e,this.trigger(i.eventChangeLastSelectedDate,e)})),I(this,\"destroy\",(()=>{if(this.isDestroyed)return;let{showEvent:e,isMobile:t}=this.opts,i=this.$datepicker.parentNode;i&&i.removeChild(this.$datepicker),this.$el.removeEventListener(e,this._onFocus),this.$el.removeEventListener(\"blur\",this._onBlur),window.removeEventListener(\"resize\",this._onResize),t&&this._removeMobileAttributes(),this.keyboardNav&&this.keyboardNav.destroy(),this.views=null,this.nav=null,this.$datepicker=null,this.opts={},this.$customContainer=null,this.viewDate=null,this.focusDate=null,this.selectedDates=[],this.rangeDateFrom=null,this.rangeDateTo=null,this.isDestroyed=!0})),I(this,\"update\",(function(){let e=arguments.length>0&&void 0!==arguments[0]?arguments[0]:{},t=arguments.length>1&&void 0!==arguments[1]?arguments[1]:{},s=w({},r.opts),{silent:a}=t;w(r.opts,e);let{timepicker:n,buttons:o,range:h,selectedDates:l,isMobile:d}=r.opts,c=r.visible||r.treatAsInline;r._createMinMaxDates(),r._limitViewDateByMaxMinDates(),r._handleLocale(),l&&(r.selectedDates=[],r.selectDate(l,{silent:a})),e.view&&r.setCurrentView(e.view,{silent:a}),r._setInputValue(),s.range&&!h?(r.rangeDateTo=!1,r.rangeDateFrom=!1):!s.range&&h&&r.selectedDates.length&&(r.rangeDateFrom=r.selectedDates[0],r.rangeDateTo=r.selectedDates[1]),s.timepicker&&!n?(c&&r.timepicker.destroy(),r.timepicker=!1,r.$timepicker.parentNode.removeChild(r.$timepicker)):!s.timepicker&&n&&r._addTimepicker(),!s.buttons&&o?r._addButtons():s.buttons&&!o?(r.buttons.destroy(),r.$buttons.parentNode.removeChild(r.$buttons)):c&&s.buttons&&o&&r.buttons.clearHtml().render(),!s.isMobile&&d?(r.treatAsInline||j||r._createMobileOverlay(),r._addMobileAttributes(),r.visible&&r._showMobileOverlay()):s.isMobile&&!d&&(r._removeMobileAttributes(),r.visible&&(j.classList.remove(\"-active-\"),\"function\"!=typeof r.opts.position&&r.setPosition())),c&&(r.nav.update(),r.views[r.currentView].render(),r.currentView===i.days&&r.views[r.currentView].renderDayNames())})),I(this,\"disableDate\",((e,t)=>{(Array.isArray(e)?e:[e]).forEach((e=>{let i=b(e);if(!i)return;let s=t?\"delete\":\"add\";this.disabledDates[s](this.formatDate(i,\"yyyy-MM-dd\"));let a=this.getCell(i,this.currentViewSingular);a&&a.adpCell.render()}),[])})),I(this,\"enableDate\",(e=>{this.disableDate(e,!0)})),I(this,\"isDateDisabled\",(e=>{let t=b(e);return this.disabledDates.has(this.formatDate(t,\"yyyy-MM-dd\"))})),I(this,\"isOtherMonth\",(e=>{let{month:t}=h(e);return t!==this.parsedViewDate.month})),I(this,\"isOtherYear\",(e=>{let{year:t}=h(e);return t!==this.parsedViewDate.year})),I(this,\"isOtherDecade\",(e=>{let{year:t}=h(e),[i,s]=c(this.viewDate);return t<i||t>s})),I(this,\"_onChangeSelectedDate\",(e=>{let{silent:t}=e;setTimeout((()=>{this._setInputValue(),this.opts.onSelect&&!t&&this._triggerOnSelect()}))})),I(this,\"_onChangeFocusedDate\",(function(e){let{viewDateTransition:t}=arguments.length>1&&void 0!==arguments[1]?arguments[1]:{};if(!e)return;let i=!1;t&&(i=r.isOtherMonth(e)||r.isOtherYear(e)||r.isOtherDecade(e)),i&&r.setViewDate(e),r.opts.onFocus&&r.opts.onFocus({datepicker:r,date:e})})),I(this,\"_onChangeTime\",(e=>{let{hours:t,minutes:i}=e,s=new Date,{lastSelectedDate:a,opts:{onSelect:n}}=this,r=a;a||(r=s);let o=this.getCell(r,this.currentViewSingular),h=o&&o.adpCell;h&&h.isDisabled||(r.setHours(t),r.setMinutes(i),a?(this._setInputValue(),n&&this._triggerOnSelect()):this.selectDate(r))})),I(this,\"_onFocus\",(e=>{this.visible||this.show()})),I(this,\"_onBlur\",(e=>{this.inFocus||!this.visible||this.opts.isMobile||this.hide()})),I(this,\"_onMouseDown\",(e=>{this.inFocus=!0})),I(this,\"_onMouseUp\",(e=>{this.inFocus=!1,this.$el.focus()})),I(this,\"_onResize\",(()=>{this.visible&&\"function\"!=typeof this.opts.position&&this.setPosition()})),I(this,\"_onClickOverlay\",(()=>{this.visible&&this.hide()})),I(this,\"getViewDates\",(function(){let e=arguments.length>0&&void 0!==arguments[0]?arguments[0]:i.days;return T.getDatesFunction(e)(r)})),I(this,\"isWeekend\",(e=>this.opts.weekends.includes(e))),I(this,\"getClampedDate\",(e=>{let{minDate:t,maxDate:i}=this,s=e;return i&&m(e,i)?s=i:t&&v(e,t)&&(s=t),s})),this.$el=a(e),!this.$el)return;this.$datepicker=n({className:\"air-datepicker\"}),this.opts=w({},s,t),this.$customContainer=!!this.opts.container&&a(this.opts.container),this.$altField=a(this.opts.altField||!1);let{view:o,startDate:l}=this.opts;l||(this.opts.startDate=new Date),\"INPUT\"===this.$el.nodeName&&(this.elIsInput=!0),this.inited=!1,this.visible=!1,this.viewDate=b(this.opts.startDate),this.focusDate=!1,this.initialReadonly=this.$el.getAttribute(\"readonly\"),this.customHide=!1,this.currentView=o,this.selectedDates=[],this.disabledDates=new Set,this.isDestroyed=!1,this.views={},this.keys=[],this.rangeDateFrom=\"\",this.rangeDateTo=\"\",this.timepickerIsActive=!1,this.treatAsInline=this.opts.inline||!this.elIsInput,this.init()}init(){let{opts:e,treatAsInline:t,opts:{inline:i,isMobile:s,selectedDates:n,keyboardNav:r,onlyTimepicker:o}}=this,h=a(\"body\");(!B||B&&P&&!h.contains(P))&&!i&&this.elIsInput&&!this.$customContainer&&R.buildGlobalContainer(R.defaultGlobalContainerId),!s||j||t||this._createMobileOverlay(),this._handleLocale(),this._bindSubEvents(),this._createMinMaxDates(),this._limitViewDateByMaxMinDates(),this.elIsInput&&(i||this._bindEvents(),r&&!o&&(this.keyboardNav=new A({dp:this,opts:e}))),n&&this.selectDate(n,{silent:!0}),this.opts.visible&&!t&&this.show(),s&&!t&&this.$el.setAttribute(\"readonly\",!0),t&&this._createComponents()}_createMobileOverlay(){j=n({className:\"air-datepicker-overlay\"}),P.appendChild(j)}_createComponents(){let{opts:e,treatAsInline:t,opts:{inline:i,buttons:s,timepicker:a,position:n,classes:r,onlyTimepicker:o,isMobile:h}}=this;this._buildBaseHtml(),this.elIsInput&&(i||this._setPositionClasses(n)),!i&&this.elIsInput||this.$datepicker.classList.add(\"-inline-\"),r&&this.$datepicker.classList.add(...r.split(\" \")),o&&this.$datepicker.classList.add(\"-only-timepicker-\"),h&&!t&&this._addMobileAttributes(),this.views[this.currentView]=new T({dp:this,type:this.currentView,opts:e}),this.nav=new V({dp:this,opts:e}),a&&this._addTimepicker(),s&&this._addButtons(),this.$content.appendChild(this.views[this.currentView].$el),this.$nav.appendChild(this.nav.$el)}_destroyComponents(){for(let e in this.views)this.views[e].destroy();this.views={},this.nav.destroy(),this.timepicker&&this.timepicker.destroy()}_addMobileAttributes(){j.addEventListener(\"click\",this._onClickOverlay),this.$datepicker.classList.add(\"-is-mobile-\"),this.$el.setAttribute(\"readonly\",!0)}_removeMobileAttributes(){j.removeEventListener(\"click\",this._onClickOverlay),this.$datepicker.classList.remove(\"-is-mobile-\"),this.initialReadonly||\"\"===this.initialReadonly||this.$el.removeAttribute(\"readonly\")}_createMinMaxDates(){let{minDate:e,maxDate:t}=this.opts;this.minDate=!!e&&b(e),this.maxDate=!!t&&b(t)}_addTimepicker(){this.$timepicker=n({className:\"air-datepicker--time\"}),this.$datepicker.appendChild(this.$timepicker),this.timepicker=new L({dp:this,opts:this.opts}),this.$timepicker.appendChild(this.timepicker.$el)}_addButtons(){this.$buttons=n({className:\"air-datepicker--buttons\"}),this.$datepicker.appendChild(this.$buttons),this.buttons=new H({dp:this,opts:this.opts}),this.$buttons.appendChild(this.buttons.$el)}_bindSubEvents(){this.on(i.eventChangeSelectedDate,this._onChangeSelectedDate),this.on(i.eventChangeFocusDate,this._onChangeFocusedDate),this.on(i.eventChangeTime,this._onChangeTime)}_buildBaseHtml(){let{inline:e}=this.opts;var t,i;this.elIsInput?e?(t=this.$datepicker,(i=this.$el).parentNode.insertBefore(t,i.nextSibling)):this.$container.appendChild(this.$datepicker):this.$el.appendChild(this.$datepicker),this.$datepicker.innerHTML='<i class=\"air-datepicker--pointer\"></i><div class=\"air-datepicker--navigation\"></div><div class=\"air-datepicker--content\"></div>',this.$content=a(\".air-datepicker--content\",this.$datepicker),this.$pointer=a(\".air-datepicker--pointer\",this.$datepicker),this.$nav=a(\".air-datepicker--navigation\",this.$datepicker)}_handleLocale(){let{locale:e,dateFormat:t,firstDay:i,timepicker:s,onlyTimepicker:a,timeFormat:n,dateTimeSeparator:r}=this.opts;var o;this.locale=(o=e,JSON.parse(JSON.stringify(o))),t&&(this.locale.dateFormat=t),void 0!==n&&\"\"!==n&&(this.locale.timeFormat=n);let{timeFormat:h}=this.locale;if(\"\"!==i&&(this.locale.firstDay=i),s&&\"function\"!=typeof t){let e=h?r:\"\";this.locale.dateFormat=[this.locale.dateFormat,h||\"\"].join(e)}a&&\"function\"!=typeof t&&(this.locale.dateFormat=this.locale.timeFormat)}_setPositionClasses(e){if(\"function\"==typeof e)return void this.$datepicker.classList.add(\"-custom-position-\");let t=(e=e.split(\" \"))[0],i=`air-datepicker -${t}-${e[1]}- -from-${t}-`;this.$datepicker.classList.add(...i.split(\" \"))}_bindEvents(){this.$el.addEventListener(this.opts.showEvent,this._onFocus),this.$el.addEventListener(\"blur\",this._onBlur),this.$datepicker.addEventListener(\"mousedown\",this._onMouseDown),this.$datepicker.addEventListener(\"mouseup\",this._onMouseUp),window.addEventListener(\"resize\",this._onResize)}_limitViewDateByMaxMinDates(){let{viewDate:e,minDate:t,maxDate:i}=this;i&&m(e,i)&&this.setViewDate(i),t&&v(e,t)&&this.setViewDate(t)}formatDate(){let e=arguments.length>0&&void 0!==arguments[0]?arguments[0]:this.viewDate,t=arguments.length>1?arguments[1]:void 0;if(e=b(e),!(e instanceof Date))return;let i=t,s=this.locale,a=h(e),n=a.dayPeriod,r=c(e),o=R.replacer,l={T:e.getTime(),m:a.minutes,mm:a.fullMinutes,h:a.hours12,hh:a.fullHours12,H:a.hours,HH:a.fullHours,aa:n,AA:n.toUpperCase(),E:s.daysShort[a.day],EEEE:s.days[a.day],d:a.date,dd:a.fullDate,M:a.month+1,MM:a.fullMonth,MMM:s.monthsShort[a.month],MMMM:s.months[a.month],yy:a.year.toString().slice(-2),yyyy:a.year,yyyy1:r[0],yyyy2:r[1]};for(let[e,t]of Object.entries(l))i=o(i,k(e),t);return i}down(e){this._handleUpDownActions(e,\"down\")}up(e){this._handleUpDownActions(e,\"up\")}selectDate(e){let t,s=arguments.length>1&&void 0!==arguments[1]?arguments[1]:{},{currentView:a,parsedViewDate:n,selectedDates:r}=this,{updateTime:o}=s,{moveToOtherMonthsOnSelect:h,moveToOtherYearsOnSelect:l,multipleDates:d,range:c,autoClose:u,onBeforeSelect:p}=this.opts,v=r.length;if(Array.isArray(e))return e.forEach((e=>{this.selectDate(e,s)})),new Promise((e=>{setTimeout(e)}));if((e=b(e))instanceof Date){if(p&&!p({date:e,datepicker:this}))return Promise.resolve();if(a===i.days&&e.getMonth()!==n.month&&h&&(t=new Date(e.getFullYear(),e.getMonth(),1)),a===i.years&&e.getFullYear()!==n.year&&l&&(t=new Date(e.getFullYear(),0,1)),t&&this.setViewDate(t),d&&!c){if(v===d)return;this._checkIfDateIsSelected(e)||r.push(e)}else if(c)switch(v){case 1:r.push(e),this.rangeDateTo||(this.rangeDateTo=e),m(this.rangeDateFrom,this.rangeDateTo)&&(this.rangeDateTo=this.rangeDateFrom,this.rangeDateFrom=e),this.selectedDates=[this.rangeDateFrom,this.rangeDateTo];break;case 2:this.selectedDates=[e],this.rangeDateFrom=e,this.rangeDateTo=\"\";break;default:this.selectedDates=[e],this.rangeDateFrom=e}else this.selectedDates=[e];return this.trigger(i.eventChangeSelectedDate,{action:i.actionSelectDate,silent:null==s?void 0:s.silent,date:e,updateTime:o}),this._updateLastSelectedDate(e),u&&!this.timepickerIsActive&&this.visible&&(d||c?c&&1===v&&this.hide():this.hide()),new Promise((e=>{setTimeout(e)}))}}unselectDate(e){let t=this.selectedDates,s=this;if((e=b(e))instanceof Date)return t.some(((a,n)=>{if(p(a,e))return t.splice(n,1),s.selectedDates.length?(s.rangeDateTo=\"\",s.rangeDateFrom=t[0],s._updateLastSelectedDate(s.selectedDates[s.selectedDates.length-1])):(s.rangeDateFrom=\"\",s.rangeDateTo=\"\",s._updateLastSelectedDate(!1)),this.trigger(i.eventChangeSelectedDate,{action:i.actionUnselectDate,date:e}),!0}))}replaceDate(e,t){let s=this.selectedDates.find((t=>p(t,e,this.currentView))),a=this.selectedDates.indexOf(s);a<0||p(this.selectedDates[a],t,this.currentView)||(this.selectedDates[a]=t,this.trigger(i.eventChangeSelectedDate,{action:i.actionSelectDate,date:t,updateTime:!0}),this._updateLastSelectedDate(t))}clear(){let e=arguments.length>0&&void 0!==arguments[0]?arguments[0]:{};return this.selectedDates=[],this.rangeDateFrom=!1,this.rangeDateTo=!1,this.lastSelectedDate=!1,this.trigger(i.eventChangeSelectedDate,{action:i.actionUnselectDate,silent:e.silent}),new Promise((e=>{setTimeout(e)}))}show(){let{onShow:e,isMobile:t}=this.opts;this._cancelScheduledCall(),this.visible||this.hideAnimation||this._createComponents(),this.setPosition(this.opts.position),this.$datepicker.classList.add(\"-active-\"),this.visible=!0,e&&this._scheduleCallAfterTransition(e),t&&this._showMobileOverlay()}hide(){let{onHide:e,isMobile:t}=this.opts,i=this._hasTransition();this.visible=!1,this.hideAnimation=!0,this.$datepicker.classList.remove(\"-active-\"),this.customHide&&this.customHide(),this.elIsInput&&this.$el.blur(),this._scheduleCallAfterTransition((t=>{!this.customHide&&(t&&i||!t&&!i)&&this._finishHide(),e&&e(t)})),t&&j.classList.remove(\"-active-\")}_triggerOnSelect(){let e=[],t=[],{selectedDates:i,locale:s,opts:{onSelect:a,multipleDates:n,range:r}}=this,o=n||r,h=\"function\"==typeof s.dateFormat;i.length&&(e=i.map(g),t=h?n?s.dateFormat(e):e.map((e=>s.dateFormat(e))):e.map((e=>this.formatDate(e,s.dateFormat)))),a({date:o?e:e[0],formattedDate:o?t:t[0],datepicker:this})}_handleAlreadySelectedDates(e,t){let{selectedDates:i,rangeDateFrom:s,rangeDateTo:a}=this,{range:n,toggleSelected:r}=this.opts,o=i.length,h=\"function\"==typeof r?r({datepicker:this,date:t}):r,l=Boolean(n&&1===o&&e),d=l?g(t):t;n&&!h&&(2!==o&&this.selectDate(d),2===o&&p(s,a))||(h?this.unselectDate(d):this._updateLastSelectedDate(l?d:e))}_handleUpDownActions(e,t){if(!((e=b(e||this.focusDate||this.viewDate))instanceof Date))return;let i=\"up\"===t?this.viewIndex+1:this.viewIndex-1;i>2&&(i=2),i<0&&(i=0),this.setViewDate(new Date(e.getFullYear(),e.getMonth(),1)),this.setCurrentView(this.viewIndexes[i])}getCell(e){let t=arguments.length>1&&void 0!==arguments[1]?arguments[1]:i.day;if(!((e=b(e))instanceof Date))return;let{year:s,month:a,date:n}=h(e),r=`[data-year=\"${s}\"]`,o=`[data-month=\"${a}\"]`,l={[i.day]:`${r}${o}[data-date=\"${n}\"]`,[i.month]:`${r}${o}`,[i.year]:`${r}`};return this.views[this.currentView]?this.views[this.currentView].$el.querySelector(l[t]):void 0}_showMobileOverlay(){j.classList.add(\"-active-\")}_hasTransition(){return window.getComputedStyle(this.$datepicker).getPropertyValue(\"transition-duration\").split(\", \").reduce(((e,t)=>parseFloat(t)+e),0)>0}get shouldUpdateDOM(){return this.visible||this.treatAsInline}get parsedViewDate(){return h(this.viewDate)}get currentViewSingular(){return this.currentView.slice(0,-1)}get curDecade(){return c(this.viewDate)}get viewIndex(){return this.viewIndexes.indexOf(this.currentView)}get isFinalView(){return this.currentView===i.years}get hasSelectedDates(){return this.selectedDates.length>0}get isMinViewReached(){return this.currentView===this.opts.minView||this.currentView===i.days}get $container(){return this.$customContainer||P}static replacer(e,t,i){return e.replace(t,(function(e,t,s,a){return t+i+a}))}}var K;return I(R,\"defaults\",s),I(R,\"version\",\"3.5.3\"),I(R,\"defaultGlobalContainerId\",\"air-datepicker-global-container\"),K=R.prototype,Object.assign(K,N),t.default}()}));","\"use strict\";\n\nObject.defineProperty(exports, \"__esModule\", {\n  value: true\n});\nexports.default = void 0;\nvar _default = {\n  days: ['Sunday', 'Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday'],\n  daysShort: ['Sun', 'Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat'],\n  daysMin: ['Su', 'Mo', 'Tu', 'We', 'Th', 'Fr', 'Sa'],\n  months: ['January', 'February', 'March', 'April', 'May', 'June', 'July', 'August', 'September', 'October', 'November', 'December'],\n  monthsShort: ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec'],\n  today: 'Today',\n  clear: 'Clear',\n  dateFormat: 'MM/dd/yyyy',\n  timeFormat: 'hh:mm aa',\n  firstDay: 0\n};\nexports.default = _default;","\"use strict\";\n\nObject.defineProperty(exports, \"__esModule\", {\n  value: true\n});\nexports.default = void 0;\nvar _default = {\n  days: ['Sunnuntai', 'Maanantai', 'Tiistai', 'Keskiviikko', 'Torstai', 'Perjantai', 'Lauantai'],\n  daysShort: ['Su', 'Ma', 'Ti', 'Ke', 'To', 'Pe', 'La'],\n  daysMin: ['Su', 'Ma', 'Ti', 'Ke', 'To', 'Pe', 'La'],\n  months: ['Tammikuu', 'Helmikuu', 'Maaliskuu', 'Huhtikuu', 'Toukokuu', 'Kesäkuu', 'Heinäkuu', 'Elokuu', 'Syyskuu', 'Lokakuu', 'Marraskuu', 'Joulukuu'],\n  monthsShort: ['Tammi', 'Helmi', 'Maalis', 'Huhti', 'Touko', 'Kesä', 'Heinä', 'Elo', 'Syys', 'Loka', 'Marras', 'Joulu'],\n  today: 'Tänään',\n  clear: 'Tyhjennä',\n  dateFormat: 'dd.MM.yyyy',\n  timeFormat: 'HH:mm',\n  firstDay: 1\n};\nexports.default = _default;","\"use strict\";\n\nObject.defineProperty(exports, \"__esModule\", {\n  value: true\n});\nexports.default = void 0;\nvar _default = {\n  days: ['Söndag', 'Måndag', 'Tisdag', 'Onsdag', 'Torsdag', 'Fredag', 'Lördag'],\n  daysShort: ['Sön', 'Mån', 'Tis', 'Ons', 'Tor', 'Fre', 'Lör'],\n  daysMin: ['Sö', 'Må', 'Ti', 'On', 'To', 'Fr', 'Lö'],\n  months: ['Januari', 'Februari', 'Mars', 'April', 'Maj', 'Juni', 'Juli', 'Augusti', 'September', 'Oktober', 'November', 'December'],\n  monthsShort: ['Jan', 'Feb', 'Mar', 'Apr', 'Maj', 'Jun', 'Jul', 'Aug', 'Sep', 'Okt', 'Nov', 'Dec'],\n  today: 'I dag',\n  clear: 'Nollställ',\n  dateFormat: 'yyyy-MM-dd',\n  timeFormat: 'HH:mm',\n  firstDay: 1\n};\nexports.default = _default;","export var top = 'top';\nexport var bottom = 'bottom';\nexport var right = 'right';\nexport var left = 'left';\nexport var auto = 'auto';\nexport var basePlacements = [top, bottom, right, left];\nexport var start = 'start';\nexport var end = 'end';\nexport var clippingParents = 'clippingParents';\nexport var viewport = 'viewport';\nexport var popper = 'popper';\nexport var reference = 'reference';\nexport var variationPlacements = /*#__PURE__*/basePlacements.reduce(function (acc, placement) {\n  return acc.concat([placement + \"-\" + start, placement + \"-\" + end]);\n}, []);\nexport var placements = /*#__PURE__*/[].concat(basePlacements, [auto]).reduce(function (acc, placement) {\n  return acc.concat([placement, placement + \"-\" + start, placement + \"-\" + end]);\n}, []); // modifiers that need to read the DOM\n\nexport var beforeRead = 'beforeRead';\nexport var read = 'read';\nexport var afterRead = 'afterRead'; // pure-logic modifiers\n\nexport var beforeMain = 'beforeMain';\nexport var main = 'main';\nexport var afterMain = 'afterMain'; // modifier with the purpose to write to the DOM (or write into a framework state)\n\nexport var beforeWrite = 'beforeWrite';\nexport var write = 'write';\nexport var afterWrite = 'afterWrite';\nexport var modifierPhases = [beforeRead, read, afterRead, beforeMain, main, afterMain, beforeWrite, write, afterWrite];","export default function getNodeName(element) {\n  return element ? (element.nodeName || '').toLowerCase() : null;\n}","export default function getWindow(node) {\n  if (node == null) {\n    return window;\n  }\n\n  if (node.toString() !== '[object Window]') {\n    var ownerDocument = node.ownerDocument;\n    return ownerDocument ? ownerDocument.defaultView || window : window;\n  }\n\n  return node;\n}","import getWindow from \"./getWindow.js\";\n\nfunction isElement(node) {\n  var OwnElement = getWindow(node).Element;\n  return node instanceof OwnElement || node instanceof Element;\n}\n\nfunction isHTMLElement(node) {\n  var OwnElement = getWindow(node).HTMLElement;\n  return node instanceof OwnElement || node instanceof HTMLElement;\n}\n\nfunction isShadowRoot(node) {\n  // IE 11 has no ShadowRoot\n  if (typeof ShadowRoot === 'undefined') {\n    return false;\n  }\n\n  var OwnElement = getWindow(node).ShadowRoot;\n  return node instanceof OwnElement || node instanceof ShadowRoot;\n}\n\nexport { isElement, isHTMLElement, isShadowRoot };","import getNodeName from \"../dom-utils/getNodeName.js\";\nimport { isHTMLElement } from \"../dom-utils/instanceOf.js\"; // This modifier takes the styles prepared by the `computeStyles` modifier\n// and applies them to the HTMLElements such as popper and arrow\n\nfunction applyStyles(_ref) {\n  var state = _ref.state;\n  Object.keys(state.elements).forEach(function (name) {\n    var style = state.styles[name] || {};\n    var attributes = state.attributes[name] || {};\n    var element = state.elements[name]; // arrow is optional + virtual elements\n\n    if (!isHTMLElement(element) || !getNodeName(element)) {\n      return;\n    } // Flow doesn't support to extend this property, but it's the most\n    // effective way to apply styles to an HTMLElement\n    // $FlowFixMe[cannot-write]\n\n\n    Object.assign(element.style, style);\n    Object.keys(attributes).forEach(function (name) {\n      var value = attributes[name];\n\n      if (value === false) {\n        element.removeAttribute(name);\n      } else {\n        element.setAttribute(name, value === true ? '' : value);\n      }\n    });\n  });\n}\n\nfunction effect(_ref2) {\n  var state = _ref2.state;\n  var initialStyles = {\n    popper: {\n      position: state.options.strategy,\n      left: '0',\n      top: '0',\n      margin: '0'\n    },\n    arrow: {\n      position: 'absolute'\n    },\n    reference: {}\n  };\n  Object.assign(state.elements.popper.style, initialStyles.popper);\n  state.styles = initialStyles;\n\n  if (state.elements.arrow) {\n    Object.assign(state.elements.arrow.style, initialStyles.arrow);\n  }\n\n  return function () {\n    Object.keys(state.elements).forEach(function (name) {\n      var element = state.elements[name];\n      var attributes = state.attributes[name] || {};\n      var styleProperties = Object.keys(state.styles.hasOwnProperty(name) ? state.styles[name] : initialStyles[name]); // Set all values to an empty string to unset them\n\n      var style = styleProperties.reduce(function (style, property) {\n        style[property] = '';\n        return style;\n      }, {}); // arrow is optional + virtual elements\n\n      if (!isHTMLElement(element) || !getNodeName(element)) {\n        return;\n      }\n\n      Object.assign(element.style, style);\n      Object.keys(attributes).forEach(function (attribute) {\n        element.removeAttribute(attribute);\n      });\n    });\n  };\n} // eslint-disable-next-line import/no-unused-modules\n\n\nexport default {\n  name: 'applyStyles',\n  enabled: true,\n  phase: 'write',\n  fn: applyStyles,\n  effect: effect,\n  requires: ['computeStyles']\n};","import { auto } from \"../enums.js\";\nexport default function getBasePlacement(placement) {\n  return placement.split('-')[0];\n}","export var max = Math.max;\nexport var min = Math.min;\nexport var round = Math.round;","export default function getUAString() {\n  var uaData = navigator.userAgentData;\n\n  if (uaData != null && uaData.brands && Array.isArray(uaData.brands)) {\n    return uaData.brands.map(function (item) {\n      return item.brand + \"/\" + item.version;\n    }).join(' ');\n  }\n\n  return navigator.userAgent;\n}","import getUAString from \"../utils/userAgent.js\";\nexport default function isLayoutViewport() {\n  return !/^((?!chrome|android).)*safari/i.test(getUAString());\n}","import { isElement, isHTMLElement } from \"./instanceOf.js\";\nimport { round } from \"../utils/math.js\";\nimport getWindow from \"./getWindow.js\";\nimport isLayoutViewport from \"./isLayoutViewport.js\";\nexport default function getBoundingClientRect(element, includeScale, isFixedStrategy) {\n  if (includeScale === void 0) {\n    includeScale = false;\n  }\n\n  if (isFixedStrategy === void 0) {\n    isFixedStrategy = false;\n  }\n\n  var clientRect = element.getBoundingClientRect();\n  var scaleX = 1;\n  var scaleY = 1;\n\n  if (includeScale && isHTMLElement(element)) {\n    scaleX = element.offsetWidth > 0 ? round(clientRect.width) / element.offsetWidth || 1 : 1;\n    scaleY = element.offsetHeight > 0 ? round(clientRect.height) / element.offsetHeight || 1 : 1;\n  }\n\n  var _ref = isElement(element) ? getWindow(element) : window,\n      visualViewport = _ref.visualViewport;\n\n  var addVisualOffsets = !isLayoutViewport() && isFixedStrategy;\n  var x = (clientRect.left + (addVisualOffsets && visualViewport ? visualViewport.offsetLeft : 0)) / scaleX;\n  var y = (clientRect.top + (addVisualOffsets && visualViewport ? visualViewport.offsetTop : 0)) / scaleY;\n  var width = clientRect.width / scaleX;\n  var height = clientRect.height / scaleY;\n  return {\n    width: width,\n    height: height,\n    top: y,\n    right: x + width,\n    bottom: y + height,\n    left: x,\n    x: x,\n    y: y\n  };\n}","import getBoundingClientRect from \"./getBoundingClientRect.js\"; // Returns the layout rect of an element relative to its offsetParent. Layout\n// means it doesn't take into account transforms.\n\nexport default function getLayoutRect(element) {\n  var clientRect = getBoundingClientRect(element); // Use the clientRect sizes if it's not been transformed.\n  // Fixes https://github.com/popperjs/popper-core/issues/1223\n\n  var width = element.offsetWidth;\n  var height = element.offsetHeight;\n\n  if (Math.abs(clientRect.width - width) <= 1) {\n    width = clientRect.width;\n  }\n\n  if (Math.abs(clientRect.height - height) <= 1) {\n    height = clientRect.height;\n  }\n\n  return {\n    x: element.offsetLeft,\n    y: element.offsetTop,\n    width: width,\n    height: height\n  };\n}","import { isShadowRoot } from \"./instanceOf.js\";\nexport default function contains(parent, child) {\n  var rootNode = child.getRootNode && child.getRootNode(); // First, attempt with faster native method\n\n  if (parent.contains(child)) {\n    return true;\n  } // then fallback to custom implementation with Shadow DOM support\n  else if (rootNode && isShadowRoot(rootNode)) {\n      var next = child;\n\n      do {\n        if (next && parent.isSameNode(next)) {\n          return true;\n        } // $FlowFixMe[prop-missing]: need a better way to handle this...\n\n\n        next = next.parentNode || next.host;\n      } while (next);\n    } // Give up, the result is false\n\n\n  return false;\n}","import getWindow from \"./getWindow.js\";\nexport default function getComputedStyle(element) {\n  return getWindow(element).getComputedStyle(element);\n}","import getNodeName from \"./getNodeName.js\";\nexport default function isTableElement(element) {\n  return ['table', 'td', 'th'].indexOf(getNodeName(element)) >= 0;\n}","import { isElement } from \"./instanceOf.js\";\nexport default function getDocumentElement(element) {\n  // $FlowFixMe[incompatible-return]: assume body is always available\n  return ((isElement(element) ? element.ownerDocument : // $FlowFixMe[prop-missing]\n  element.document) || window.document).documentElement;\n}","import getNodeName from \"./getNodeName.js\";\nimport getDocumentElement from \"./getDocumentElement.js\";\nimport { isShadowRoot } from \"./instanceOf.js\";\nexport default function getParentNode(element) {\n  if (getNodeName(element) === 'html') {\n    return element;\n  }\n\n  return (// this is a quicker (but less type safe) way to save quite some bytes from the bundle\n    // $FlowFixMe[incompatible-return]\n    // $FlowFixMe[prop-missing]\n    element.assignedSlot || // step into the shadow DOM of the parent of a slotted node\n    element.parentNode || ( // DOM Element detected\n    isShadowRoot(element) ? element.host : null) || // ShadowRoot detected\n    // $FlowFixMe[incompatible-call]: HTMLElement is a Node\n    getDocumentElement(element) // fallback\n\n  );\n}","import getWindow from \"./getWindow.js\";\nimport getNodeName from \"./getNodeName.js\";\nimport getComputedStyle from \"./getComputedStyle.js\";\nimport { isHTMLElement, isShadowRoot } from \"./instanceOf.js\";\nimport isTableElement from \"./isTableElement.js\";\nimport getParentNode from \"./getParentNode.js\";\nimport getUAString from \"../utils/userAgent.js\";\n\nfunction getTrueOffsetParent(element) {\n  if (!isHTMLElement(element) || // https://github.com/popperjs/popper-core/issues/837\n  getComputedStyle(element).position === 'fixed') {\n    return null;\n  }\n\n  return element.offsetParent;\n} // `.offsetParent` reports `null` for fixed elements, while absolute elements\n// return the containing block\n\n\nfunction getContainingBlock(element) {\n  var isFirefox = /firefox/i.test(getUAString());\n  var isIE = /Trident/i.test(getUAString());\n\n  if (isIE && isHTMLElement(element)) {\n    // In IE 9, 10 and 11 fixed elements containing block is always established by the viewport\n    var elementCss = getComputedStyle(element);\n\n    if (elementCss.position === 'fixed') {\n      return null;\n    }\n  }\n\n  var currentNode = getParentNode(element);\n\n  if (isShadowRoot(currentNode)) {\n    currentNode = currentNode.host;\n  }\n\n  while (isHTMLElement(currentNode) && ['html', 'body'].indexOf(getNodeName(currentNode)) < 0) {\n    var css = getComputedStyle(currentNode); // This is non-exhaustive but covers the most common CSS properties that\n    // create a containing block.\n    // https://developer.mozilla.org/en-US/docs/Web/CSS/Containing_block#identifying_the_containing_block\n\n    if (css.transform !== 'none' || css.perspective !== 'none' || css.contain === 'paint' || ['transform', 'perspective'].indexOf(css.willChange) !== -1 || isFirefox && css.willChange === 'filter' || isFirefox && css.filter && css.filter !== 'none') {\n      return currentNode;\n    } else {\n      currentNode = currentNode.parentNode;\n    }\n  }\n\n  return null;\n} // Gets the closest ancestor positioned element. Handles some edge cases,\n// such as table ancestors and cross browser bugs.\n\n\nexport default function getOffsetParent(element) {\n  var window = getWindow(element);\n  var offsetParent = getTrueOffsetParent(element);\n\n  while (offsetParent && isTableElement(offsetParent) && getComputedStyle(offsetParent).position === 'static') {\n    offsetParent = getTrueOffsetParent(offsetParent);\n  }\n\n  if (offsetParent && (getNodeName(offsetParent) === 'html' || getNodeName(offsetParent) === 'body' && getComputedStyle(offsetParent).position === 'static')) {\n    return window;\n  }\n\n  return offsetParent || getContainingBlock(element) || window;\n}","export default function getMainAxisFromPlacement(placement) {\n  return ['top', 'bottom'].indexOf(placement) >= 0 ? 'x' : 'y';\n}","import { max as mathMax, min as mathMin } from \"./math.js\";\nexport function within(min, value, max) {\n  return mathMax(min, mathMin(value, max));\n}\nexport function withinMaxClamp(min, value, max) {\n  var v = within(min, value, max);\n  return v > max ? max : v;\n}","export default function getFreshSideObject() {\n  return {\n    top: 0,\n    right: 0,\n    bottom: 0,\n    left: 0\n  };\n}","import getFreshSideObject from \"./getFreshSideObject.js\";\nexport default function mergePaddingObject(paddingObject) {\n  return Object.assign({}, getFreshSideObject(), paddingObject);\n}","export default function expandToHashMap(value, keys) {\n  return keys.reduce(function (hashMap, key) {\n    hashMap[key] = value;\n    return hashMap;\n  }, {});\n}","import getBasePlacement from \"../utils/getBasePlacement.js\";\nimport getLayoutRect from \"../dom-utils/getLayoutRect.js\";\nimport contains from \"../dom-utils/contains.js\";\nimport getOffsetParent from \"../dom-utils/getOffsetParent.js\";\nimport getMainAxisFromPlacement from \"../utils/getMainAxisFromPlacement.js\";\nimport { within } from \"../utils/within.js\";\nimport mergePaddingObject from \"../utils/mergePaddingObject.js\";\nimport expandToHashMap from \"../utils/expandToHashMap.js\";\nimport { left, right, basePlacements, top, bottom } from \"../enums.js\"; // eslint-disable-next-line import/no-unused-modules\n\nvar toPaddingObject = function toPaddingObject(padding, state) {\n  padding = typeof padding === 'function' ? padding(Object.assign({}, state.rects, {\n    placement: state.placement\n  })) : padding;\n  return mergePaddingObject(typeof padding !== 'number' ? padding : expandToHashMap(padding, basePlacements));\n};\n\nfunction arrow(_ref) {\n  var _state$modifiersData$;\n\n  var state = _ref.state,\n      name = _ref.name,\n      options = _ref.options;\n  var arrowElement = state.elements.arrow;\n  var popperOffsets = state.modifiersData.popperOffsets;\n  var basePlacement = getBasePlacement(state.placement);\n  var axis = getMainAxisFromPlacement(basePlacement);\n  var isVertical = [left, right].indexOf(basePlacement) >= 0;\n  var len = isVertical ? 'height' : 'width';\n\n  if (!arrowElement || !popperOffsets) {\n    return;\n  }\n\n  var paddingObject = toPaddingObject(options.padding, state);\n  var arrowRect = getLayoutRect(arrowElement);\n  var minProp = axis === 'y' ? top : left;\n  var maxProp = axis === 'y' ? bottom : right;\n  var endDiff = state.rects.reference[len] + state.rects.reference[axis] - popperOffsets[axis] - state.rects.popper[len];\n  var startDiff = popperOffsets[axis] - state.rects.reference[axis];\n  var arrowOffsetParent = getOffsetParent(arrowElement);\n  var clientSize = arrowOffsetParent ? axis === 'y' ? arrowOffsetParent.clientHeight || 0 : arrowOffsetParent.clientWidth || 0 : 0;\n  var centerToReference = endDiff / 2 - startDiff / 2; // Make sure the arrow doesn't overflow the popper if the center point is\n  // outside of the popper bounds\n\n  var min = paddingObject[minProp];\n  var max = clientSize - arrowRect[len] - paddingObject[maxProp];\n  var center = clientSize / 2 - arrowRect[len] / 2 + centerToReference;\n  var offset = within(min, center, max); // Prevents breaking syntax highlighting...\n\n  var axisProp = axis;\n  state.modifiersData[name] = (_state$modifiersData$ = {}, _state$modifiersData$[axisProp] = offset, _state$modifiersData$.centerOffset = offset - center, _state$modifiersData$);\n}\n\nfunction effect(_ref2) {\n  var state = _ref2.state,\n      options = _ref2.options;\n  var _options$element = options.element,\n      arrowElement = _options$element === void 0 ? '[data-popper-arrow]' : _options$element;\n\n  if (arrowElement == null) {\n    return;\n  } // CSS selector\n\n\n  if (typeof arrowElement === 'string') {\n    arrowElement = state.elements.popper.querySelector(arrowElement);\n\n    if (!arrowElement) {\n      return;\n    }\n  }\n\n  if (!contains(state.elements.popper, arrowElement)) {\n    return;\n  }\n\n  state.elements.arrow = arrowElement;\n} // eslint-disable-next-line import/no-unused-modules\n\n\nexport default {\n  name: 'arrow',\n  enabled: true,\n  phase: 'main',\n  fn: arrow,\n  effect: effect,\n  requires: ['popperOffsets'],\n  requiresIfExists: ['preventOverflow']\n};","export default function getVariation(placement) {\n  return placement.split('-')[1];\n}","import { top, left, right, bottom, end } from \"../enums.js\";\nimport getOffsetParent from \"../dom-utils/getOffsetParent.js\";\nimport getWindow from \"../dom-utils/getWindow.js\";\nimport getDocumentElement from \"../dom-utils/getDocumentElement.js\";\nimport getComputedStyle from \"../dom-utils/getComputedStyle.js\";\nimport getBasePlacement from \"../utils/getBasePlacement.js\";\nimport getVariation from \"../utils/getVariation.js\";\nimport { round } from \"../utils/math.js\"; // eslint-disable-next-line import/no-unused-modules\n\nvar unsetSides = {\n  top: 'auto',\n  right: 'auto',\n  bottom: 'auto',\n  left: 'auto'\n}; // Round the offsets to the nearest suitable subpixel based on the DPR.\n// Zooming can change the DPR, but it seems to report a value that will\n// cleanly divide the values into the appropriate subpixels.\n\nfunction roundOffsetsByDPR(_ref, win) {\n  var x = _ref.x,\n      y = _ref.y;\n  var dpr = win.devicePixelRatio || 1;\n  return {\n    x: round(x * dpr) / dpr || 0,\n    y: round(y * dpr) / dpr || 0\n  };\n}\n\nexport function mapToStyles(_ref2) {\n  var _Object$assign2;\n\n  var popper = _ref2.popper,\n      popperRect = _ref2.popperRect,\n      placement = _ref2.placement,\n      variation = _ref2.variation,\n      offsets = _ref2.offsets,\n      position = _ref2.position,\n      gpuAcceleration = _ref2.gpuAcceleration,\n      adaptive = _ref2.adaptive,\n      roundOffsets = _ref2.roundOffsets,\n      isFixed = _ref2.isFixed;\n  var _offsets$x = offsets.x,\n      x = _offsets$x === void 0 ? 0 : _offsets$x,\n      _offsets$y = offsets.y,\n      y = _offsets$y === void 0 ? 0 : _offsets$y;\n\n  var _ref3 = typeof roundOffsets === 'function' ? roundOffsets({\n    x: x,\n    y: y\n  }) : {\n    x: x,\n    y: y\n  };\n\n  x = _ref3.x;\n  y = _ref3.y;\n  var hasX = offsets.hasOwnProperty('x');\n  var hasY = offsets.hasOwnProperty('y');\n  var sideX = left;\n  var sideY = top;\n  var win = window;\n\n  if (adaptive) {\n    var offsetParent = getOffsetParent(popper);\n    var heightProp = 'clientHeight';\n    var widthProp = 'clientWidth';\n\n    if (offsetParent === getWindow(popper)) {\n      offsetParent = getDocumentElement(popper);\n\n      if (getComputedStyle(offsetParent).position !== 'static' && position === 'absolute') {\n        heightProp = 'scrollHeight';\n        widthProp = 'scrollWidth';\n      }\n    } // $FlowFixMe[incompatible-cast]: force type refinement, we compare offsetParent with window above, but Flow doesn't detect it\n\n\n    offsetParent = offsetParent;\n\n    if (placement === top || (placement === left || placement === right) && variation === end) {\n      sideY = bottom;\n      var offsetY = isFixed && offsetParent === win && win.visualViewport ? win.visualViewport.height : // $FlowFixMe[prop-missing]\n      offsetParent[heightProp];\n      y -= offsetY - popperRect.height;\n      y *= gpuAcceleration ? 1 : -1;\n    }\n\n    if (placement === left || (placement === top || placement === bottom) && variation === end) {\n      sideX = right;\n      var offsetX = isFixed && offsetParent === win && win.visualViewport ? win.visualViewport.width : // $FlowFixMe[prop-missing]\n      offsetParent[widthProp];\n      x -= offsetX - popperRect.width;\n      x *= gpuAcceleration ? 1 : -1;\n    }\n  }\n\n  var commonStyles = Object.assign({\n    position: position\n  }, adaptive && unsetSides);\n\n  var _ref4 = roundOffsets === true ? roundOffsetsByDPR({\n    x: x,\n    y: y\n  }, getWindow(popper)) : {\n    x: x,\n    y: y\n  };\n\n  x = _ref4.x;\n  y = _ref4.y;\n\n  if (gpuAcceleration) {\n    var _Object$assign;\n\n    return Object.assign({}, commonStyles, (_Object$assign = {}, _Object$assign[sideY] = hasY ? '0' : '', _Object$assign[sideX] = hasX ? '0' : '', _Object$assign.transform = (win.devicePixelRatio || 1) <= 1 ? \"translate(\" + x + \"px, \" + y + \"px)\" : \"translate3d(\" + x + \"px, \" + y + \"px, 0)\", _Object$assign));\n  }\n\n  return Object.assign({}, commonStyles, (_Object$assign2 = {}, _Object$assign2[sideY] = hasY ? y + \"px\" : '', _Object$assign2[sideX] = hasX ? x + \"px\" : '', _Object$assign2.transform = '', _Object$assign2));\n}\n\nfunction computeStyles(_ref5) {\n  var state = _ref5.state,\n      options = _ref5.options;\n  var _options$gpuAccelerat = options.gpuAcceleration,\n      gpuAcceleration = _options$gpuAccelerat === void 0 ? true : _options$gpuAccelerat,\n      _options$adaptive = options.adaptive,\n      adaptive = _options$adaptive === void 0 ? true : _options$adaptive,\n      _options$roundOffsets = options.roundOffsets,\n      roundOffsets = _options$roundOffsets === void 0 ? true : _options$roundOffsets;\n  var commonStyles = {\n    placement: getBasePlacement(state.placement),\n    variation: getVariation(state.placement),\n    popper: state.elements.popper,\n    popperRect: state.rects.popper,\n    gpuAcceleration: gpuAcceleration,\n    isFixed: state.options.strategy === 'fixed'\n  };\n\n  if (state.modifiersData.popperOffsets != null) {\n    state.styles.popper = Object.assign({}, state.styles.popper, mapToStyles(Object.assign({}, commonStyles, {\n      offsets: state.modifiersData.popperOffsets,\n      position: state.options.strategy,\n      adaptive: adaptive,\n      roundOffsets: roundOffsets\n    })));\n  }\n\n  if (state.modifiersData.arrow != null) {\n    state.styles.arrow = Object.assign({}, state.styles.arrow, mapToStyles(Object.assign({}, commonStyles, {\n      offsets: state.modifiersData.arrow,\n      position: 'absolute',\n      adaptive: false,\n      roundOffsets: roundOffsets\n    })));\n  }\n\n  state.attributes.popper = Object.assign({}, state.attributes.popper, {\n    'data-popper-placement': state.placement\n  });\n} // eslint-disable-next-line import/no-unused-modules\n\n\nexport default {\n  name: 'computeStyles',\n  enabled: true,\n  phase: 'beforeWrite',\n  fn: computeStyles,\n  data: {}\n};","import getWindow from \"../dom-utils/getWindow.js\"; // eslint-disable-next-line import/no-unused-modules\n\nvar passive = {\n  passive: true\n};\n\nfunction effect(_ref) {\n  var state = _ref.state,\n      instance = _ref.instance,\n      options = _ref.options;\n  var _options$scroll = options.scroll,\n      scroll = _options$scroll === void 0 ? true : _options$scroll,\n      _options$resize = options.resize,\n      resize = _options$resize === void 0 ? true : _options$resize;\n  var window = getWindow(state.elements.popper);\n  var scrollParents = [].concat(state.scrollParents.reference, state.scrollParents.popper);\n\n  if (scroll) {\n    scrollParents.forEach(function (scrollParent) {\n      scrollParent.addEventListener('scroll', instance.update, passive);\n    });\n  }\n\n  if (resize) {\n    window.addEventListener('resize', instance.update, passive);\n  }\n\n  return function () {\n    if (scroll) {\n      scrollParents.forEach(function (scrollParent) {\n        scrollParent.removeEventListener('scroll', instance.update, passive);\n      });\n    }\n\n    if (resize) {\n      window.removeEventListener('resize', instance.update, passive);\n    }\n  };\n} // eslint-disable-next-line import/no-unused-modules\n\n\nexport default {\n  name: 'eventListeners',\n  enabled: true,\n  phase: 'write',\n  fn: function fn() {},\n  effect: effect,\n  data: {}\n};","var hash = {\n  left: 'right',\n  right: 'left',\n  bottom: 'top',\n  top: 'bottom'\n};\nexport default function getOppositePlacement(placement) {\n  return placement.replace(/left|right|bottom|top/g, function (matched) {\n    return hash[matched];\n  });\n}","var hash = {\n  start: 'end',\n  end: 'start'\n};\nexport default function getOppositeVariationPlacement(placement) {\n  return placement.replace(/start|end/g, function (matched) {\n    return hash[matched];\n  });\n}","import getWindow from \"./getWindow.js\";\nexport default function getWindowScroll(node) {\n  var win = getWindow(node);\n  var scrollLeft = win.pageXOffset;\n  var scrollTop = win.pageYOffset;\n  return {\n    scrollLeft: scrollLeft,\n    scrollTop: scrollTop\n  };\n}","import getBoundingClientRect from \"./getBoundingClientRect.js\";\nimport getDocumentElement from \"./getDocumentElement.js\";\nimport getWindowScroll from \"./getWindowScroll.js\";\nexport default function getWindowScrollBarX(element) {\n  // If <html> has a CSS width greater than the viewport, then this will be\n  // incorrect for RTL.\n  // Popper 1 is broken in this case and never had a bug report so let's assume\n  // it's not an issue. I don't think anyone ever specifies width on <html>\n  // anyway.\n  // Browsers where the left scrollbar doesn't cause an issue report `0` for\n  // this (e.g. Edge 2019, IE11, Safari)\n  return getBoundingClientRect(getDocumentElement(element)).left + getWindowScroll(element).scrollLeft;\n}","import getWindow from \"./getWindow.js\";\nimport getDocumentElement from \"./getDocumentElement.js\";\nimport getWindowScrollBarX from \"./getWindowScrollBarX.js\";\nimport isLayoutViewport from \"./isLayoutViewport.js\";\nexport default function getViewportRect(element, strategy) {\n  var win = getWindow(element);\n  var html = getDocumentElement(element);\n  var visualViewport = win.visualViewport;\n  var width = html.clientWidth;\n  var height = html.clientHeight;\n  var x = 0;\n  var y = 0;\n\n  if (visualViewport) {\n    width = visualViewport.width;\n    height = visualViewport.height;\n    var layoutViewport = isLayoutViewport();\n\n    if (layoutViewport || !layoutViewport && strategy === 'fixed') {\n      x = visualViewport.offsetLeft;\n      y = visualViewport.offsetTop;\n    }\n  }\n\n  return {\n    width: width,\n    height: height,\n    x: x + getWindowScrollBarX(element),\n    y: y\n  };\n}","import getDocumentElement from \"./getDocumentElement.js\";\nimport getComputedStyle from \"./getComputedStyle.js\";\nimport getWindowScrollBarX from \"./getWindowScrollBarX.js\";\nimport getWindowScroll from \"./getWindowScroll.js\";\nimport { max } from \"../utils/math.js\"; // Gets the entire size of the scrollable document area, even extending outside\n// of the `<html>` and `<body>` rect bounds if horizontally scrollable\n\nexport default function getDocumentRect(element) {\n  var _element$ownerDocumen;\n\n  var html = getDocumentElement(element);\n  var winScroll = getWindowScroll(element);\n  var body = (_element$ownerDocumen = element.ownerDocument) == null ? void 0 : _element$ownerDocumen.body;\n  var width = max(html.scrollWidth, html.clientWidth, body ? body.scrollWidth : 0, body ? body.clientWidth : 0);\n  var height = max(html.scrollHeight, html.clientHeight, body ? body.scrollHeight : 0, body ? body.clientHeight : 0);\n  var x = -winScroll.scrollLeft + getWindowScrollBarX(element);\n  var y = -winScroll.scrollTop;\n\n  if (getComputedStyle(body || html).direction === 'rtl') {\n    x += max(html.clientWidth, body ? body.clientWidth : 0) - width;\n  }\n\n  return {\n    width: width,\n    height: height,\n    x: x,\n    y: y\n  };\n}","import getComputedStyle from \"./getComputedStyle.js\";\nexport default function isScrollParent(element) {\n  // Firefox wants us to check `-x` and `-y` variations as well\n  var _getComputedStyle = getComputedStyle(element),\n      overflow = _getComputedStyle.overflow,\n      overflowX = _getComputedStyle.overflowX,\n      overflowY = _getComputedStyle.overflowY;\n\n  return /auto|scroll|overlay|hidden/.test(overflow + overflowY + overflowX);\n}","import getParentNode from \"./getParentNode.js\";\nimport isScrollParent from \"./isScrollParent.js\";\nimport getNodeName from \"./getNodeName.js\";\nimport { isHTMLElement } from \"./instanceOf.js\";\nexport default function getScrollParent(node) {\n  if (['html', 'body', '#document'].indexOf(getNodeName(node)) >= 0) {\n    // $FlowFixMe[incompatible-return]: assume body is always available\n    return node.ownerDocument.body;\n  }\n\n  if (isHTMLElement(node) && isScrollParent(node)) {\n    return node;\n  }\n\n  return getScrollParent(getParentNode(node));\n}","import getScrollParent from \"./getScrollParent.js\";\nimport getParentNode from \"./getParentNode.js\";\nimport getWindow from \"./getWindow.js\";\nimport isScrollParent from \"./isScrollParent.js\";\n/*\ngiven a DOM element, return the list of all scroll parents, up the list of ancesors\nuntil we get to the top window object. This list is what we attach scroll listeners\nto, because if any of these parent elements scroll, we'll need to re-calculate the\nreference element's position.\n*/\n\nexport default function listScrollParents(element, list) {\n  var _element$ownerDocumen;\n\n  if (list === void 0) {\n    list = [];\n  }\n\n  var scrollParent = getScrollParent(element);\n  var isBody = scrollParent === ((_element$ownerDocumen = element.ownerDocument) == null ? void 0 : _element$ownerDocumen.body);\n  var win = getWindow(scrollParent);\n  var target = isBody ? [win].concat(win.visualViewport || [], isScrollParent(scrollParent) ? scrollParent : []) : scrollParent;\n  var updatedList = list.concat(target);\n  return isBody ? updatedList : // $FlowFixMe[incompatible-call]: isBody tells us target will be an HTMLElement here\n  updatedList.concat(listScrollParents(getParentNode(target)));\n}","export default function rectToClientRect(rect) {\n  return Object.assign({}, rect, {\n    left: rect.x,\n    top: rect.y,\n    right: rect.x + rect.width,\n    bottom: rect.y + rect.height\n  });\n}","import { viewport } from \"../enums.js\";\nimport getViewportRect from \"./getViewportRect.js\";\nimport getDocumentRect from \"./getDocumentRect.js\";\nimport listScrollParents from \"./listScrollParents.js\";\nimport getOffsetParent from \"./getOffsetParent.js\";\nimport getDocumentElement from \"./getDocumentElement.js\";\nimport getComputedStyle from \"./getComputedStyle.js\";\nimport { isElement, isHTMLElement } from \"./instanceOf.js\";\nimport getBoundingClientRect from \"./getBoundingClientRect.js\";\nimport getParentNode from \"./getParentNode.js\";\nimport contains from \"./contains.js\";\nimport getNodeName from \"./getNodeName.js\";\nimport rectToClientRect from \"../utils/rectToClientRect.js\";\nimport { max, min } from \"../utils/math.js\";\n\nfunction getInnerBoundingClientRect(element, strategy) {\n  var rect = getBoundingClientRect(element, false, strategy === 'fixed');\n  rect.top = rect.top + element.clientTop;\n  rect.left = rect.left + element.clientLeft;\n  rect.bottom = rect.top + element.clientHeight;\n  rect.right = rect.left + element.clientWidth;\n  rect.width = element.clientWidth;\n  rect.height = element.clientHeight;\n  rect.x = rect.left;\n  rect.y = rect.top;\n  return rect;\n}\n\nfunction getClientRectFromMixedType(element, clippingParent, strategy) {\n  return clippingParent === viewport ? rectToClientRect(getViewportRect(element, strategy)) : isElement(clippingParent) ? getInnerBoundingClientRect(clippingParent, strategy) : rectToClientRect(getDocumentRect(getDocumentElement(element)));\n} // A \"clipping parent\" is an overflowable container with the characteristic of\n// clipping (or hiding) overflowing elements with a position different from\n// `initial`\n\n\nfunction getClippingParents(element) {\n  var clippingParents = listScrollParents(getParentNode(element));\n  var canEscapeClipping = ['absolute', 'fixed'].indexOf(getComputedStyle(element).position) >= 0;\n  var clipperElement = canEscapeClipping && isHTMLElement(element) ? getOffsetParent(element) : element;\n\n  if (!isElement(clipperElement)) {\n    return [];\n  } // $FlowFixMe[incompatible-return]: https://github.com/facebook/flow/issues/1414\n\n\n  return clippingParents.filter(function (clippingParent) {\n    return isElement(clippingParent) && contains(clippingParent, clipperElement) && getNodeName(clippingParent) !== 'body';\n  });\n} // Gets the maximum area that the element is visible in due to any number of\n// clipping parents\n\n\nexport default function getClippingRect(element, boundary, rootBoundary, strategy) {\n  var mainClippingParents = boundary === 'clippingParents' ? getClippingParents(element) : [].concat(boundary);\n  var clippingParents = [].concat(mainClippingParents, [rootBoundary]);\n  var firstClippingParent = clippingParents[0];\n  var clippingRect = clippingParents.reduce(function (accRect, clippingParent) {\n    var rect = getClientRectFromMixedType(element, clippingParent, strategy);\n    accRect.top = max(rect.top, accRect.top);\n    accRect.right = min(rect.right, accRect.right);\n    accRect.bottom = min(rect.bottom, accRect.bottom);\n    accRect.left = max(rect.left, accRect.left);\n    return accRect;\n  }, getClientRectFromMixedType(element, firstClippingParent, strategy));\n  clippingRect.width = clippingRect.right - clippingRect.left;\n  clippingRect.height = clippingRect.bottom - clippingRect.top;\n  clippingRect.x = clippingRect.left;\n  clippingRect.y = clippingRect.top;\n  return clippingRect;\n}","import getBasePlacement from \"./getBasePlacement.js\";\nimport getVariation from \"./getVariation.js\";\nimport getMainAxisFromPlacement from \"./getMainAxisFromPlacement.js\";\nimport { top, right, bottom, left, start, end } from \"../enums.js\";\nexport default function computeOffsets(_ref) {\n  var reference = _ref.reference,\n      element = _ref.element,\n      placement = _ref.placement;\n  var basePlacement = placement ? getBasePlacement(placement) : null;\n  var variation = placement ? getVariation(placement) : null;\n  var commonX = reference.x + reference.width / 2 - element.width / 2;\n  var commonY = reference.y + reference.height / 2 - element.height / 2;\n  var offsets;\n\n  switch (basePlacement) {\n    case top:\n      offsets = {\n        x: commonX,\n        y: reference.y - element.height\n      };\n      break;\n\n    case bottom:\n      offsets = {\n        x: commonX,\n        y: reference.y + reference.height\n      };\n      break;\n\n    case right:\n      offsets = {\n        x: reference.x + reference.width,\n        y: commonY\n      };\n      break;\n\n    case left:\n      offsets = {\n        x: reference.x - element.width,\n        y: commonY\n      };\n      break;\n\n    default:\n      offsets = {\n        x: reference.x,\n        y: reference.y\n      };\n  }\n\n  var mainAxis = basePlacement ? getMainAxisFromPlacement(basePlacement) : null;\n\n  if (mainAxis != null) {\n    var len = mainAxis === 'y' ? 'height' : 'width';\n\n    switch (variation) {\n      case start:\n        offsets[mainAxis] = offsets[mainAxis] - (reference[len] / 2 - element[len] / 2);\n        break;\n\n      case end:\n        offsets[mainAxis] = offsets[mainAxis] + (reference[len] / 2 - element[len] / 2);\n        break;\n\n      default:\n    }\n  }\n\n  return offsets;\n}","import getClippingRect from \"../dom-utils/getClippingRect.js\";\nimport getDocumentElement from \"../dom-utils/getDocumentElement.js\";\nimport getBoundingClientRect from \"../dom-utils/getBoundingClientRect.js\";\nimport computeOffsets from \"./computeOffsets.js\";\nimport rectToClientRect from \"./rectToClientRect.js\";\nimport { clippingParents, reference, popper, bottom, top, right, basePlacements, viewport } from \"../enums.js\";\nimport { isElement } from \"../dom-utils/instanceOf.js\";\nimport mergePaddingObject from \"./mergePaddingObject.js\";\nimport expandToHashMap from \"./expandToHashMap.js\"; // eslint-disable-next-line import/no-unused-modules\n\nexport default function detectOverflow(state, options) {\n  if (options === void 0) {\n    options = {};\n  }\n\n  var _options = options,\n      _options$placement = _options.placement,\n      placement = _options$placement === void 0 ? state.placement : _options$placement,\n      _options$strategy = _options.strategy,\n      strategy = _options$strategy === void 0 ? state.strategy : _options$strategy,\n      _options$boundary = _options.boundary,\n      boundary = _options$boundary === void 0 ? clippingParents : _options$boundary,\n      _options$rootBoundary = _options.rootBoundary,\n      rootBoundary = _options$rootBoundary === void 0 ? viewport : _options$rootBoundary,\n      _options$elementConte = _options.elementContext,\n      elementContext = _options$elementConte === void 0 ? popper : _options$elementConte,\n      _options$altBoundary = _options.altBoundary,\n      altBoundary = _options$altBoundary === void 0 ? false : _options$altBoundary,\n      _options$padding = _options.padding,\n      padding = _options$padding === void 0 ? 0 : _options$padding;\n  var paddingObject = mergePaddingObject(typeof padding !== 'number' ? padding : expandToHashMap(padding, basePlacements));\n  var altContext = elementContext === popper ? reference : popper;\n  var popperRect = state.rects.popper;\n  var element = state.elements[altBoundary ? altContext : elementContext];\n  var clippingClientRect = getClippingRect(isElement(element) ? element : element.contextElement || getDocumentElement(state.elements.popper), boundary, rootBoundary, strategy);\n  var referenceClientRect = getBoundingClientRect(state.elements.reference);\n  var popperOffsets = computeOffsets({\n    reference: referenceClientRect,\n    element: popperRect,\n    strategy: 'absolute',\n    placement: placement\n  });\n  var popperClientRect = rectToClientRect(Object.assign({}, popperRect, popperOffsets));\n  var elementClientRect = elementContext === popper ? popperClientRect : referenceClientRect; // positive = overflowing the clipping rect\n  // 0 or negative = within the clipping rect\n\n  var overflowOffsets = {\n    top: clippingClientRect.top - elementClientRect.top + paddingObject.top,\n    bottom: elementClientRect.bottom - clippingClientRect.bottom + paddingObject.bottom,\n    left: clippingClientRect.left - elementClientRect.left + paddingObject.left,\n    right: elementClientRect.right - clippingClientRect.right + paddingObject.right\n  };\n  var offsetData = state.modifiersData.offset; // Offsets can be applied only to the popper element\n\n  if (elementContext === popper && offsetData) {\n    var offset = offsetData[placement];\n    Object.keys(overflowOffsets).forEach(function (key) {\n      var multiply = [right, bottom].indexOf(key) >= 0 ? 1 : -1;\n      var axis = [top, bottom].indexOf(key) >= 0 ? 'y' : 'x';\n      overflowOffsets[key] += offset[axis] * multiply;\n    });\n  }\n\n  return overflowOffsets;\n}","import getVariation from \"./getVariation.js\";\nimport { variationPlacements, basePlacements, placements as allPlacements } from \"../enums.js\";\nimport detectOverflow from \"./detectOverflow.js\";\nimport getBasePlacement from \"./getBasePlacement.js\";\nexport default function computeAutoPlacement(state, options) {\n  if (options === void 0) {\n    options = {};\n  }\n\n  var _options = options,\n      placement = _options.placement,\n      boundary = _options.boundary,\n      rootBoundary = _options.rootBoundary,\n      padding = _options.padding,\n      flipVariations = _options.flipVariations,\n      _options$allowedAutoP = _options.allowedAutoPlacements,\n      allowedAutoPlacements = _options$allowedAutoP === void 0 ? allPlacements : _options$allowedAutoP;\n  var variation = getVariation(placement);\n  var placements = variation ? flipVariations ? variationPlacements : variationPlacements.filter(function (placement) {\n    return getVariation(placement) === variation;\n  }) : basePlacements;\n  var allowedPlacements = placements.filter(function (placement) {\n    return allowedAutoPlacements.indexOf(placement) >= 0;\n  });\n\n  if (allowedPlacements.length === 0) {\n    allowedPlacements = placements;\n  } // $FlowFixMe[incompatible-type]: Flow seems to have problems with two array unions...\n\n\n  var overflows = allowedPlacements.reduce(function (acc, placement) {\n    acc[placement] = detectOverflow(state, {\n      placement: placement,\n      boundary: boundary,\n      rootBoundary: rootBoundary,\n      padding: padding\n    })[getBasePlacement(placement)];\n    return acc;\n  }, {});\n  return Object.keys(overflows).sort(function (a, b) {\n    return overflows[a] - overflows[b];\n  });\n}","import getOppositePlacement from \"../utils/getOppositePlacement.js\";\nimport getBasePlacement from \"../utils/getBasePlacement.js\";\nimport getOppositeVariationPlacement from \"../utils/getOppositeVariationPlacement.js\";\nimport detectOverflow from \"../utils/detectOverflow.js\";\nimport computeAutoPlacement from \"../utils/computeAutoPlacement.js\";\nimport { bottom, top, start, right, left, auto } from \"../enums.js\";\nimport getVariation from \"../utils/getVariation.js\"; // eslint-disable-next-line import/no-unused-modules\n\nfunction getExpandedFallbackPlacements(placement) {\n  if (getBasePlacement(placement) === auto) {\n    return [];\n  }\n\n  var oppositePlacement = getOppositePlacement(placement);\n  return [getOppositeVariationPlacement(placement), oppositePlacement, getOppositeVariationPlacement(oppositePlacement)];\n}\n\nfunction flip(_ref) {\n  var state = _ref.state,\n      options = _ref.options,\n      name = _ref.name;\n\n  if (state.modifiersData[name]._skip) {\n    return;\n  }\n\n  var _options$mainAxis = options.mainAxis,\n      checkMainAxis = _options$mainAxis === void 0 ? true : _options$mainAxis,\n      _options$altAxis = options.altAxis,\n      checkAltAxis = _options$altAxis === void 0 ? true : _options$altAxis,\n      specifiedFallbackPlacements = options.fallbackPlacements,\n      padding = options.padding,\n      boundary = options.boundary,\n      rootBoundary = options.rootBoundary,\n      altBoundary = options.altBoundary,\n      _options$flipVariatio = options.flipVariations,\n      flipVariations = _options$flipVariatio === void 0 ? true : _options$flipVariatio,\n      allowedAutoPlacements = options.allowedAutoPlacements;\n  var preferredPlacement = state.options.placement;\n  var basePlacement = getBasePlacement(preferredPlacement);\n  var isBasePlacement = basePlacement === preferredPlacement;\n  var fallbackPlacements = specifiedFallbackPlacements || (isBasePlacement || !flipVariations ? [getOppositePlacement(preferredPlacement)] : getExpandedFallbackPlacements(preferredPlacement));\n  var placements = [preferredPlacement].concat(fallbackPlacements).reduce(function (acc, placement) {\n    return acc.concat(getBasePlacement(placement) === auto ? computeAutoPlacement(state, {\n      placement: placement,\n      boundary: boundary,\n      rootBoundary: rootBoundary,\n      padding: padding,\n      flipVariations: flipVariations,\n      allowedAutoPlacements: allowedAutoPlacements\n    }) : placement);\n  }, []);\n  var referenceRect = state.rects.reference;\n  var popperRect = state.rects.popper;\n  var checksMap = new Map();\n  var makeFallbackChecks = true;\n  var firstFittingPlacement = placements[0];\n\n  for (var i = 0; i < placements.length; i++) {\n    var placement = placements[i];\n\n    var _basePlacement = getBasePlacement(placement);\n\n    var isStartVariation = getVariation(placement) === start;\n    var isVertical = [top, bottom].indexOf(_basePlacement) >= 0;\n    var len = isVertical ? 'width' : 'height';\n    var overflow = detectOverflow(state, {\n      placement: placement,\n      boundary: boundary,\n      rootBoundary: rootBoundary,\n      altBoundary: altBoundary,\n      padding: padding\n    });\n    var mainVariationSide = isVertical ? isStartVariation ? right : left : isStartVariation ? bottom : top;\n\n    if (referenceRect[len] > popperRect[len]) {\n      mainVariationSide = getOppositePlacement(mainVariationSide);\n    }\n\n    var altVariationSide = getOppositePlacement(mainVariationSide);\n    var checks = [];\n\n    if (checkMainAxis) {\n      checks.push(overflow[_basePlacement] <= 0);\n    }\n\n    if (checkAltAxis) {\n      checks.push(overflow[mainVariationSide] <= 0, overflow[altVariationSide] <= 0);\n    }\n\n    if (checks.every(function (check) {\n      return check;\n    })) {\n      firstFittingPlacement = placement;\n      makeFallbackChecks = false;\n      break;\n    }\n\n    checksMap.set(placement, checks);\n  }\n\n  if (makeFallbackChecks) {\n    // `2` may be desired in some cases – research later\n    var numberOfChecks = flipVariations ? 3 : 1;\n\n    var _loop = function _loop(_i) {\n      var fittingPlacement = placements.find(function (placement) {\n        var checks = checksMap.get(placement);\n\n        if (checks) {\n          return checks.slice(0, _i).every(function (check) {\n            return check;\n          });\n        }\n      });\n\n      if (fittingPlacement) {\n        firstFittingPlacement = fittingPlacement;\n        return \"break\";\n      }\n    };\n\n    for (var _i = numberOfChecks; _i > 0; _i--) {\n      var _ret = _loop(_i);\n\n      if (_ret === \"break\") break;\n    }\n  }\n\n  if (state.placement !== firstFittingPlacement) {\n    state.modifiersData[name]._skip = true;\n    state.placement = firstFittingPlacement;\n    state.reset = true;\n  }\n} // eslint-disable-next-line import/no-unused-modules\n\n\nexport default {\n  name: 'flip',\n  enabled: true,\n  phase: 'main',\n  fn: flip,\n  requiresIfExists: ['offset'],\n  data: {\n    _skip: false\n  }\n};","import { top, bottom, left, right } from \"../enums.js\";\nimport detectOverflow from \"../utils/detectOverflow.js\";\n\nfunction getSideOffsets(overflow, rect, preventedOffsets) {\n  if (preventedOffsets === void 0) {\n    preventedOffsets = {\n      x: 0,\n      y: 0\n    };\n  }\n\n  return {\n    top: overflow.top - rect.height - preventedOffsets.y,\n    right: overflow.right - rect.width + preventedOffsets.x,\n    bottom: overflow.bottom - rect.height + preventedOffsets.y,\n    left: overflow.left - rect.width - preventedOffsets.x\n  };\n}\n\nfunction isAnySideFullyClipped(overflow) {\n  return [top, right, bottom, left].some(function (side) {\n    return overflow[side] >= 0;\n  });\n}\n\nfunction hide(_ref) {\n  var state = _ref.state,\n      name = _ref.name;\n  var referenceRect = state.rects.reference;\n  var popperRect = state.rects.popper;\n  var preventedOffsets = state.modifiersData.preventOverflow;\n  var referenceOverflow = detectOverflow(state, {\n    elementContext: 'reference'\n  });\n  var popperAltOverflow = detectOverflow(state, {\n    altBoundary: true\n  });\n  var referenceClippingOffsets = getSideOffsets(referenceOverflow, referenceRect);\n  var popperEscapeOffsets = getSideOffsets(popperAltOverflow, popperRect, preventedOffsets);\n  var isReferenceHidden = isAnySideFullyClipped(referenceClippingOffsets);\n  var hasPopperEscaped = isAnySideFullyClipped(popperEscapeOffsets);\n  state.modifiersData[name] = {\n    referenceClippingOffsets: referenceClippingOffsets,\n    popperEscapeOffsets: popperEscapeOffsets,\n    isReferenceHidden: isReferenceHidden,\n    hasPopperEscaped: hasPopperEscaped\n  };\n  state.attributes.popper = Object.assign({}, state.attributes.popper, {\n    'data-popper-reference-hidden': isReferenceHidden,\n    'data-popper-escaped': hasPopperEscaped\n  });\n} // eslint-disable-next-line import/no-unused-modules\n\n\nexport default {\n  name: 'hide',\n  enabled: true,\n  phase: 'main',\n  requiresIfExists: ['preventOverflow'],\n  fn: hide\n};","import getBasePlacement from \"../utils/getBasePlacement.js\";\nimport { top, left, right, placements } from \"../enums.js\"; // eslint-disable-next-line import/no-unused-modules\n\nexport function distanceAndSkiddingToXY(placement, rects, offset) {\n  var basePlacement = getBasePlacement(placement);\n  var invertDistance = [left, top].indexOf(basePlacement) >= 0 ? -1 : 1;\n\n  var _ref = typeof offset === 'function' ? offset(Object.assign({}, rects, {\n    placement: placement\n  })) : offset,\n      skidding = _ref[0],\n      distance = _ref[1];\n\n  skidding = skidding || 0;\n  distance = (distance || 0) * invertDistance;\n  return [left, right].indexOf(basePlacement) >= 0 ? {\n    x: distance,\n    y: skidding\n  } : {\n    x: skidding,\n    y: distance\n  };\n}\n\nfunction offset(_ref2) {\n  var state = _ref2.state,\n      options = _ref2.options,\n      name = _ref2.name;\n  var _options$offset = options.offset,\n      offset = _options$offset === void 0 ? [0, 0] : _options$offset;\n  var data = placements.reduce(function (acc, placement) {\n    acc[placement] = distanceAndSkiddingToXY(placement, state.rects, offset);\n    return acc;\n  }, {});\n  var _data$state$placement = data[state.placement],\n      x = _data$state$placement.x,\n      y = _data$state$placement.y;\n\n  if (state.modifiersData.popperOffsets != null) {\n    state.modifiersData.popperOffsets.x += x;\n    state.modifiersData.popperOffsets.y += y;\n  }\n\n  state.modifiersData[name] = data;\n} // eslint-disable-next-line import/no-unused-modules\n\n\nexport default {\n  name: 'offset',\n  enabled: true,\n  phase: 'main',\n  requires: ['popperOffsets'],\n  fn: offset\n};","import computeOffsets from \"../utils/computeOffsets.js\";\n\nfunction popperOffsets(_ref) {\n  var state = _ref.state,\n      name = _ref.name;\n  // Offsets are the actual position the popper needs to have to be\n  // properly positioned near its reference element\n  // This is the most basic placement, and will be adjusted by\n  // the modifiers in the next step\n  state.modifiersData[name] = computeOffsets({\n    reference: state.rects.reference,\n    element: state.rects.popper,\n    strategy: 'absolute',\n    placement: state.placement\n  });\n} // eslint-disable-next-line import/no-unused-modules\n\n\nexport default {\n  name: 'popperOffsets',\n  enabled: true,\n  phase: 'read',\n  fn: popperOffsets,\n  data: {}\n};","export default function getAltAxis(axis) {\n  return axis === 'x' ? 'y' : 'x';\n}","import { top, left, right, bottom, start } from \"../enums.js\";\nimport getBasePlacement from \"../utils/getBasePlacement.js\";\nimport getMainAxisFromPlacement from \"../utils/getMainAxisFromPlacement.js\";\nimport getAltAxis from \"../utils/getAltAxis.js\";\nimport { within, withinMaxClamp } from \"../utils/within.js\";\nimport getLayoutRect from \"../dom-utils/getLayoutRect.js\";\nimport getOffsetParent from \"../dom-utils/getOffsetParent.js\";\nimport detectOverflow from \"../utils/detectOverflow.js\";\nimport getVariation from \"../utils/getVariation.js\";\nimport getFreshSideObject from \"../utils/getFreshSideObject.js\";\nimport { min as mathMin, max as mathMax } from \"../utils/math.js\";\n\nfunction preventOverflow(_ref) {\n  var state = _ref.state,\n      options = _ref.options,\n      name = _ref.name;\n  var _options$mainAxis = options.mainAxis,\n      checkMainAxis = _options$mainAxis === void 0 ? true : _options$mainAxis,\n      _options$altAxis = options.altAxis,\n      checkAltAxis = _options$altAxis === void 0 ? false : _options$altAxis,\n      boundary = options.boundary,\n      rootBoundary = options.rootBoundary,\n      altBoundary = options.altBoundary,\n      padding = options.padding,\n      _options$tether = options.tether,\n      tether = _options$tether === void 0 ? true : _options$tether,\n      _options$tetherOffset = options.tetherOffset,\n      tetherOffset = _options$tetherOffset === void 0 ? 0 : _options$tetherOffset;\n  var overflow = detectOverflow(state, {\n    boundary: boundary,\n    rootBoundary: rootBoundary,\n    padding: padding,\n    altBoundary: altBoundary\n  });\n  var basePlacement = getBasePlacement(state.placement);\n  var variation = getVariation(state.placement);\n  var isBasePlacement = !variation;\n  var mainAxis = getMainAxisFromPlacement(basePlacement);\n  var altAxis = getAltAxis(mainAxis);\n  var popperOffsets = state.modifiersData.popperOffsets;\n  var referenceRect = state.rects.reference;\n  var popperRect = state.rects.popper;\n  var tetherOffsetValue = typeof tetherOffset === 'function' ? tetherOffset(Object.assign({}, state.rects, {\n    placement: state.placement\n  })) : tetherOffset;\n  var normalizedTetherOffsetValue = typeof tetherOffsetValue === 'number' ? {\n    mainAxis: tetherOffsetValue,\n    altAxis: tetherOffsetValue\n  } : Object.assign({\n    mainAxis: 0,\n    altAxis: 0\n  }, tetherOffsetValue);\n  var offsetModifierState = state.modifiersData.offset ? state.modifiersData.offset[state.placement] : null;\n  var data = {\n    x: 0,\n    y: 0\n  };\n\n  if (!popperOffsets) {\n    return;\n  }\n\n  if (checkMainAxis) {\n    var _offsetModifierState$;\n\n    var mainSide = mainAxis === 'y' ? top : left;\n    var altSide = mainAxis === 'y' ? bottom : right;\n    var len = mainAxis === 'y' ? 'height' : 'width';\n    var offset = popperOffsets[mainAxis];\n    var min = offset + overflow[mainSide];\n    var max = offset - overflow[altSide];\n    var additive = tether ? -popperRect[len] / 2 : 0;\n    var minLen = variation === start ? referenceRect[len] : popperRect[len];\n    var maxLen = variation === start ? -popperRect[len] : -referenceRect[len]; // We need to include the arrow in the calculation so the arrow doesn't go\n    // outside the reference bounds\n\n    var arrowElement = state.elements.arrow;\n    var arrowRect = tether && arrowElement ? getLayoutRect(arrowElement) : {\n      width: 0,\n      height: 0\n    };\n    var arrowPaddingObject = state.modifiersData['arrow#persistent'] ? state.modifiersData['arrow#persistent'].padding : getFreshSideObject();\n    var arrowPaddingMin = arrowPaddingObject[mainSide];\n    var arrowPaddingMax = arrowPaddingObject[altSide]; // If the reference length is smaller than the arrow length, we don't want\n    // to include its full size in the calculation. If the reference is small\n    // and near the edge of a boundary, the popper can overflow even if the\n    // reference is not overflowing as well (e.g. virtual elements with no\n    // width or height)\n\n    var arrowLen = within(0, referenceRect[len], arrowRect[len]);\n    var minOffset = isBasePlacement ? referenceRect[len] / 2 - additive - arrowLen - arrowPaddingMin - normalizedTetherOffsetValue.mainAxis : minLen - arrowLen - arrowPaddingMin - normalizedTetherOffsetValue.mainAxis;\n    var maxOffset = isBasePlacement ? -referenceRect[len] / 2 + additive + arrowLen + arrowPaddingMax + normalizedTetherOffsetValue.mainAxis : maxLen + arrowLen + arrowPaddingMax + normalizedTetherOffsetValue.mainAxis;\n    var arrowOffsetParent = state.elements.arrow && getOffsetParent(state.elements.arrow);\n    var clientOffset = arrowOffsetParent ? mainAxis === 'y' ? arrowOffsetParent.clientTop || 0 : arrowOffsetParent.clientLeft || 0 : 0;\n    var offsetModifierValue = (_offsetModifierState$ = offsetModifierState == null ? void 0 : offsetModifierState[mainAxis]) != null ? _offsetModifierState$ : 0;\n    var tetherMin = offset + minOffset - offsetModifierValue - clientOffset;\n    var tetherMax = offset + maxOffset - offsetModifierValue;\n    var preventedOffset = within(tether ? mathMin(min, tetherMin) : min, offset, tether ? mathMax(max, tetherMax) : max);\n    popperOffsets[mainAxis] = preventedOffset;\n    data[mainAxis] = preventedOffset - offset;\n  }\n\n  if (checkAltAxis) {\n    var _offsetModifierState$2;\n\n    var _mainSide = mainAxis === 'x' ? top : left;\n\n    var _altSide = mainAxis === 'x' ? bottom : right;\n\n    var _offset = popperOffsets[altAxis];\n\n    var _len = altAxis === 'y' ? 'height' : 'width';\n\n    var _min = _offset + overflow[_mainSide];\n\n    var _max = _offset - overflow[_altSide];\n\n    var isOriginSide = [top, left].indexOf(basePlacement) !== -1;\n\n    var _offsetModifierValue = (_offsetModifierState$2 = offsetModifierState == null ? void 0 : offsetModifierState[altAxis]) != null ? _offsetModifierState$2 : 0;\n\n    var _tetherMin = isOriginSide ? _min : _offset - referenceRect[_len] - popperRect[_len] - _offsetModifierValue + normalizedTetherOffsetValue.altAxis;\n\n    var _tetherMax = isOriginSide ? _offset + referenceRect[_len] + popperRect[_len] - _offsetModifierValue - normalizedTetherOffsetValue.altAxis : _max;\n\n    var _preventedOffset = tether && isOriginSide ? withinMaxClamp(_tetherMin, _offset, _tetherMax) : within(tether ? _tetherMin : _min, _offset, tether ? _tetherMax : _max);\n\n    popperOffsets[altAxis] = _preventedOffset;\n    data[altAxis] = _preventedOffset - _offset;\n  }\n\n  state.modifiersData[name] = data;\n} // eslint-disable-next-line import/no-unused-modules\n\n\nexport default {\n  name: 'preventOverflow',\n  enabled: true,\n  phase: 'main',\n  fn: preventOverflow,\n  requiresIfExists: ['offset']\n};","export default function getHTMLElementScroll(element) {\n  return {\n    scrollLeft: element.scrollLeft,\n    scrollTop: element.scrollTop\n  };\n}","import getWindowScroll from \"./getWindowScroll.js\";\nimport getWindow from \"./getWindow.js\";\nimport { isHTMLElement } from \"./instanceOf.js\";\nimport getHTMLElementScroll from \"./getHTMLElementScroll.js\";\nexport default function getNodeScroll(node) {\n  if (node === getWindow(node) || !isHTMLElement(node)) {\n    return getWindowScroll(node);\n  } else {\n    return getHTMLElementScroll(node);\n  }\n}","import getBoundingClientRect from \"./getBoundingClientRect.js\";\nimport getNodeScroll from \"./getNodeScroll.js\";\nimport getNodeName from \"./getNodeName.js\";\nimport { isHTMLElement } from \"./instanceOf.js\";\nimport getWindowScrollBarX from \"./getWindowScrollBarX.js\";\nimport getDocumentElement from \"./getDocumentElement.js\";\nimport isScrollParent from \"./isScrollParent.js\";\nimport { round } from \"../utils/math.js\";\n\nfunction isElementScaled(element) {\n  var rect = element.getBoundingClientRect();\n  var scaleX = round(rect.width) / element.offsetWidth || 1;\n  var scaleY = round(rect.height) / element.offsetHeight || 1;\n  return scaleX !== 1 || scaleY !== 1;\n} // Returns the composite rect of an element relative to its offsetParent.\n// Composite means it takes into account transforms as well as layout.\n\n\nexport default function getCompositeRect(elementOrVirtualElement, offsetParent, isFixed) {\n  if (isFixed === void 0) {\n    isFixed = false;\n  }\n\n  var isOffsetParentAnElement = isHTMLElement(offsetParent);\n  var offsetParentIsScaled = isHTMLElement(offsetParent) && isElementScaled(offsetParent);\n  var documentElement = getDocumentElement(offsetParent);\n  var rect = getBoundingClientRect(elementOrVirtualElement, offsetParentIsScaled, isFixed);\n  var scroll = {\n    scrollLeft: 0,\n    scrollTop: 0\n  };\n  var offsets = {\n    x: 0,\n    y: 0\n  };\n\n  if (isOffsetParentAnElement || !isOffsetParentAnElement && !isFixed) {\n    if (getNodeName(offsetParent) !== 'body' || // https://github.com/popperjs/popper-core/issues/1078\n    isScrollParent(documentElement)) {\n      scroll = getNodeScroll(offsetParent);\n    }\n\n    if (isHTMLElement(offsetParent)) {\n      offsets = getBoundingClientRect(offsetParent, true);\n      offsets.x += offsetParent.clientLeft;\n      offsets.y += offsetParent.clientTop;\n    } else if (documentElement) {\n      offsets.x = getWindowScrollBarX(documentElement);\n    }\n  }\n\n  return {\n    x: rect.left + scroll.scrollLeft - offsets.x,\n    y: rect.top + scroll.scrollTop - offsets.y,\n    width: rect.width,\n    height: rect.height\n  };\n}","import { modifierPhases } from \"../enums.js\"; // source: https://stackoverflow.com/questions/49875255\n\nfunction order(modifiers) {\n  var map = new Map();\n  var visited = new Set();\n  var result = [];\n  modifiers.forEach(function (modifier) {\n    map.set(modifier.name, modifier);\n  }); // On visiting object, check for its dependencies and visit them recursively\n\n  function sort(modifier) {\n    visited.add(modifier.name);\n    var requires = [].concat(modifier.requires || [], modifier.requiresIfExists || []);\n    requires.forEach(function (dep) {\n      if (!visited.has(dep)) {\n        var depModifier = map.get(dep);\n\n        if (depModifier) {\n          sort(depModifier);\n        }\n      }\n    });\n    result.push(modifier);\n  }\n\n  modifiers.forEach(function (modifier) {\n    if (!visited.has(modifier.name)) {\n      // check for visited object\n      sort(modifier);\n    }\n  });\n  return result;\n}\n\nexport default function orderModifiers(modifiers) {\n  // order based on dependencies\n  var orderedModifiers = order(modifiers); // order based on phase\n\n  return modifierPhases.reduce(function (acc, phase) {\n    return acc.concat(orderedModifiers.filter(function (modifier) {\n      return modifier.phase === phase;\n    }));\n  }, []);\n}","export default function debounce(fn) {\n  var pending;\n  return function () {\n    if (!pending) {\n      pending = new Promise(function (resolve) {\n        Promise.resolve().then(function () {\n          pending = undefined;\n          resolve(fn());\n        });\n      });\n    }\n\n    return pending;\n  };\n}","export default function mergeByName(modifiers) {\n  var merged = modifiers.reduce(function (merged, current) {\n    var existing = merged[current.name];\n    merged[current.name] = existing ? Object.assign({}, existing, current, {\n      options: Object.assign({}, existing.options, current.options),\n      data: Object.assign({}, existing.data, current.data)\n    }) : current;\n    return merged;\n  }, {}); // IE11 does not support Object.values\n\n  return Object.keys(merged).map(function (key) {\n    return merged[key];\n  });\n}","import getCompositeRect from \"./dom-utils/getCompositeRect.js\";\nimport getLayoutRect from \"./dom-utils/getLayoutRect.js\";\nimport listScrollParents from \"./dom-utils/listScrollParents.js\";\nimport getOffsetParent from \"./dom-utils/getOffsetParent.js\";\nimport orderModifiers from \"./utils/orderModifiers.js\";\nimport debounce from \"./utils/debounce.js\";\nimport mergeByName from \"./utils/mergeByName.js\";\nimport detectOverflow from \"./utils/detectOverflow.js\";\nimport { isElement } from \"./dom-utils/instanceOf.js\";\nvar DEFAULT_OPTIONS = {\n  placement: 'bottom',\n  modifiers: [],\n  strategy: 'absolute'\n};\n\nfunction areValidElements() {\n  for (var _len = arguments.length, args = new Array(_len), _key = 0; _key < _len; _key++) {\n    args[_key] = arguments[_key];\n  }\n\n  return !args.some(function (element) {\n    return !(element && typeof element.getBoundingClientRect === 'function');\n  });\n}\n\nexport function popperGenerator(generatorOptions) {\n  if (generatorOptions === void 0) {\n    generatorOptions = {};\n  }\n\n  var _generatorOptions = generatorOptions,\n      _generatorOptions$def = _generatorOptions.defaultModifiers,\n      defaultModifiers = _generatorOptions$def === void 0 ? [] : _generatorOptions$def,\n      _generatorOptions$def2 = _generatorOptions.defaultOptions,\n      defaultOptions = _generatorOptions$def2 === void 0 ? DEFAULT_OPTIONS : _generatorOptions$def2;\n  return function createPopper(reference, popper, options) {\n    if (options === void 0) {\n      options = defaultOptions;\n    }\n\n    var state = {\n      placement: 'bottom',\n      orderedModifiers: [],\n      options: Object.assign({}, DEFAULT_OPTIONS, defaultOptions),\n      modifiersData: {},\n      elements: {\n        reference: reference,\n        popper: popper\n      },\n      attributes: {},\n      styles: {}\n    };\n    var effectCleanupFns = [];\n    var isDestroyed = false;\n    var instance = {\n      state: state,\n      setOptions: function setOptions(setOptionsAction) {\n        var options = typeof setOptionsAction === 'function' ? setOptionsAction(state.options) : setOptionsAction;\n        cleanupModifierEffects();\n        state.options = Object.assign({}, defaultOptions, state.options, options);\n        state.scrollParents = {\n          reference: isElement(reference) ? listScrollParents(reference) : reference.contextElement ? listScrollParents(reference.contextElement) : [],\n          popper: listScrollParents(popper)\n        }; // Orders the modifiers based on their dependencies and `phase`\n        // properties\n\n        var orderedModifiers = orderModifiers(mergeByName([].concat(defaultModifiers, state.options.modifiers))); // Strip out disabled modifiers\n\n        state.orderedModifiers = orderedModifiers.filter(function (m) {\n          return m.enabled;\n        });\n        runModifierEffects();\n        return instance.update();\n      },\n      // Sync update – it will always be executed, even if not necessary. This\n      // is useful for low frequency updates where sync behavior simplifies the\n      // logic.\n      // For high frequency updates (e.g. `resize` and `scroll` events), always\n      // prefer the async Popper#update method\n      forceUpdate: function forceUpdate() {\n        if (isDestroyed) {\n          return;\n        }\n\n        var _state$elements = state.elements,\n            reference = _state$elements.reference,\n            popper = _state$elements.popper; // Don't proceed if `reference` or `popper` are not valid elements\n        // anymore\n\n        if (!areValidElements(reference, popper)) {\n          return;\n        } // Store the reference and popper rects to be read by modifiers\n\n\n        state.rects = {\n          reference: getCompositeRect(reference, getOffsetParent(popper), state.options.strategy === 'fixed'),\n          popper: getLayoutRect(popper)\n        }; // Modifiers have the ability to reset the current update cycle. The\n        // most common use case for this is the `flip` modifier changing the\n        // placement, which then needs to re-run all the modifiers, because the\n        // logic was previously ran for the previous placement and is therefore\n        // stale/incorrect\n\n        state.reset = false;\n        state.placement = state.options.placement; // On each update cycle, the `modifiersData` property for each modifier\n        // is filled with the initial data specified by the modifier. This means\n        // it doesn't persist and is fresh on each update.\n        // To ensure persistent data, use `${name}#persistent`\n\n        state.orderedModifiers.forEach(function (modifier) {\n          return state.modifiersData[modifier.name] = Object.assign({}, modifier.data);\n        });\n\n        for (var index = 0; index < state.orderedModifiers.length; index++) {\n          if (state.reset === true) {\n            state.reset = false;\n            index = -1;\n            continue;\n          }\n\n          var _state$orderedModifie = state.orderedModifiers[index],\n              fn = _state$orderedModifie.fn,\n              _state$orderedModifie2 = _state$orderedModifie.options,\n              _options = _state$orderedModifie2 === void 0 ? {} : _state$orderedModifie2,\n              name = _state$orderedModifie.name;\n\n          if (typeof fn === 'function') {\n            state = fn({\n              state: state,\n              options: _options,\n              name: name,\n              instance: instance\n            }) || state;\n          }\n        }\n      },\n      // Async and optimistically optimized update – it will not be executed if\n      // not necessary (debounced to run at most once-per-tick)\n      update: debounce(function () {\n        return new Promise(function (resolve) {\n          instance.forceUpdate();\n          resolve(state);\n        });\n      }),\n      destroy: function destroy() {\n        cleanupModifierEffects();\n        isDestroyed = true;\n      }\n    };\n\n    if (!areValidElements(reference, popper)) {\n      return instance;\n    }\n\n    instance.setOptions(options).then(function (state) {\n      if (!isDestroyed && options.onFirstUpdate) {\n        options.onFirstUpdate(state);\n      }\n    }); // Modifiers have the ability to execute arbitrary code before the first\n    // update cycle runs. They will be executed in the same order as the update\n    // cycle. This is useful when a modifier adds some persistent data that\n    // other modifiers need to use, but the modifier is run after the dependent\n    // one.\n\n    function runModifierEffects() {\n      state.orderedModifiers.forEach(function (_ref) {\n        var name = _ref.name,\n            _ref$options = _ref.options,\n            options = _ref$options === void 0 ? {} : _ref$options,\n            effect = _ref.effect;\n\n        if (typeof effect === 'function') {\n          var cleanupFn = effect({\n            state: state,\n            name: name,\n            instance: instance,\n            options: options\n          });\n\n          var noopFn = function noopFn() {};\n\n          effectCleanupFns.push(cleanupFn || noopFn);\n        }\n      });\n    }\n\n    function cleanupModifierEffects() {\n      effectCleanupFns.forEach(function (fn) {\n        return fn();\n      });\n      effectCleanupFns = [];\n    }\n\n    return instance;\n  };\n}\nexport var createPopper = /*#__PURE__*/popperGenerator(); // eslint-disable-next-line import/no-unused-modules\n\nexport { detectOverflow };","import { popperGenerator, detectOverflow } from \"./createPopper.js\";\nimport eventListeners from \"./modifiers/eventListeners.js\";\nimport popperOffsets from \"./modifiers/popperOffsets.js\";\nimport computeStyles from \"./modifiers/computeStyles.js\";\nimport applyStyles from \"./modifiers/applyStyles.js\";\nvar defaultModifiers = [eventListeners, popperOffsets, computeStyles, applyStyles];\nvar createPopper = /*#__PURE__*/popperGenerator({\n  defaultModifiers: defaultModifiers\n}); // eslint-disable-next-line import/no-unused-modules\n\nexport { createPopper, popperGenerator, defaultModifiers, detectOverflow };","import { popperGenerator, detectOverflow } from \"./createPopper.js\";\nimport eventListeners from \"./modifiers/eventListeners.js\";\nimport popperOffsets from \"./modifiers/popperOffsets.js\";\nimport computeStyles from \"./modifiers/computeStyles.js\";\nimport applyStyles from \"./modifiers/applyStyles.js\";\nimport offset from \"./modifiers/offset.js\";\nimport flip from \"./modifiers/flip.js\";\nimport preventOverflow from \"./modifiers/preventOverflow.js\";\nimport arrow from \"./modifiers/arrow.js\";\nimport hide from \"./modifiers/hide.js\";\nvar defaultModifiers = [eventListeners, popperOffsets, computeStyles, applyStyles, offset, flip, preventOverflow, arrow, hide];\nvar createPopper = /*#__PURE__*/popperGenerator({\n  defaultModifiers: defaultModifiers\n}); // eslint-disable-next-line import/no-unused-modules\n\nexport { createPopper, popperGenerator, defaultModifiers, detectOverflow }; // eslint-disable-next-line import/no-unused-modules\n\nexport { createPopper as createPopperLite } from \"./popper-lite.js\"; // eslint-disable-next-line import/no-unused-modules\n\nexport * from \"./modifiers/index.js\";","import angular from \"angular\";\r\n\r\nimport { Dates, PaymentChannel, SalaryDateLogic, Translations } from \"@salaxy/core\";\r\nimport AirDatepicker, { AirDatepickerViews } from \"air-datepicker\";\r\nimport localeEn from \"air-datepicker/locale/en\";\r\nimport localeFi from \"air-datepicker/locale/fi\";\r\nimport localeSv from \"air-datepicker/locale/sv\";\r\nimport { SessionService } from \"../../services\";\r\nimport { createPopper } from \"@popperjs/core\";\r\n\r\n/**\r\n * Controller for datepicker control.\r\n */\r\nexport class DatepickerController implements angular.IController {\r\n  public static $inject = [\"SessionService\", \"$element\", \"$timeout\", \"$scope\"];\r\n  public form: angular.IFormController;\r\n\r\n  /** Label for the control */\r\n  public label: string;\r\n\r\n  /** The model that is bound to the input */\r\n  public model: angular.INgModelController;\r\n\r\n  /** Form control name */\r\n  public name: string;\r\n\r\n  /** Validation error text */\r\n  public validationError: string;\r\n\r\n  /** The datepicker element instance. */\r\n  private datepicker: any;\r\n\r\n  /** True = can change multiple dates, false = single date selection. */\r\n  public isMultiple: boolean;\r\n\r\n  /** Selection mechanism and format: \"month\" | \"year\" | undefined (= dates) */\r\n  public format: string;\r\n\r\n  /** Mechanism to disable certain dates: \"salary\" and \"next-weekday\" are pre-set functions. If set as \"disable-function\", a custom disabling function can and must be given. */\r\n  public dateDisabled: \"salary\" | \"next-weekday\" | \"disable-function\" | null;\r\n\r\n  /** If dateDisabled=\"disable-function\", this function acts as the disabler. */\r\n  public disableFunction: any;\r\n\r\n  /** Dates before this are disabled in the picker. */\r\n  public minDate: string;\r\n\r\n  /** Dates after this are disabled in the picker. */\r\n  public maxDate: string;\r\n\r\n  /** Defines HTML for tooltip button */\r\n  public tooltipHtml: string;\r\n\r\n  /** Payment channel. This affects which dates are disabled in the salary date selection. */\r\n  public paymentChannel: PaymentChannel;\r\n\r\n  /** Boolean indicating if the net salary payment to the worker is zero. */\r\n  public zeroPayment: boolean;\r\n\r\n  /**\r\n   * If true, displays the control as read-only div instead of the input control.\r\n   * This \"read-only\" attribute is visualized in a different way than standard html \"readonly\" (ng-readonly):\r\n   * The input is not shown and display is more compact.\r\n   * Also note, that you may change the same read-only for the form using readonly / ng-readonly attribute.\r\n   * @example\r\n   * ```html\r\n   * <form name=\"foo\" ng-readonly=\"true\">\r\n   * <!-- .... or plain HTML ... -->\r\n   * <form name=\"foo\" readonly=\"true\">\r\n   * <!-- .... or plain HTML ... -->\r\n   * <salaxy-input name=\"input1\" read-only=\"true\"></salaxy-input>\r\n   */\r\n  public readOnly: boolean;\r\n\r\n  /**\r\n   * @deprecated Use \"require\" instead:\r\n   * This attribute overlaps with required/ng-required directive, which produces unexpected results.\r\n   */\r\n  public required: string;\r\n\r\n  /** In multiple mode, the days count is set in this variable. */\r\n  public daysCount: number;\r\n\r\n  /** True = show timepicker alongside the calendar. */\r\n  public timepicker: boolean = false;\r\n\r\n  /** False = hide Today/Clear buttons below the datepicker. Note: in multiple mode buttons are always hidden. */\r\n  public showButtons: boolean = true;\r\n\r\n  /** Datepicker is initialized only once. */\r\n  private datepickerInitialized: boolean = false;\r\n\r\n  /** Value of the datepicker. */\r\n  private _value: any;\r\n\r\n  /** Manual input value of the datepicker. */\r\n  private _manualInput: any;\r\n\r\n  /** True = inline datepicker. */\r\n  private isInline: boolean = false;\r\n\r\n  /** Getter and setter for the datepicker value. */\r\n  public get datepickerValue() {\r\n    if (this._manualInput != null) {\r\n      return this._manualInput;\r\n    }\r\n\r\n    if (!this._value) return null;\r\n\r\n    if (this.isInline) {\r\n      return this._value;\r\n    }\r\n\r\n    // Format the displayed value based on the format setting.\r\n    const jsDate = Dates.asJSDate(this._value);\r\n    if (this.format == \"month\") {\r\n      const month = jsDate.getMonth() + 1;\r\n      const year = jsDate.getFullYear();\r\n      return `${month}/${year}`;\r\n    } else if (this.format == \"year\") {\r\n      return jsDate.getFullYear().toString();\r\n    }\r\n\r\n    return Dates.getFormattedDate(jsDate);\r\n  }\r\n  public set datepickerValue(value: string) {\r\n    this._manualInput = value;\r\n  }\r\n\r\n  /** External value that causes the disabled dates function to re-run and update the datepicker component. */\r\n  public updateDisabledDates: any;\r\n\r\n  constructor(private sessionService: SessionService, private $element: JQLite, private $timeout: angular.ITimeoutService, private $scope: angular.IScope) {\r\n  }\r\n\r\n  /** Set the values and defaults on init */\r\n  public $onInit() {\r\n    if (this.$element[0].tagName.toLowerCase() == \"salaxy-datepicker\") {\r\n      this.isInline = true;\r\n    }\r\n\r\n    this.model.$render = () => {\r\n      if (this.model.$viewValue) {\r\n        // Special case: Taxcards view sets a hardcoded text value of 'today'.\r\n        this._value = this.model.$viewValue === \"today\" ? Dates.getToday() : this.model.$viewValue;\r\n      }\r\n    };\r\n\r\n    // Initialize inline datepicker after DOM is ready.\r\n    if (this.isInline) {\r\n      this.$timeout(() => {\r\n        this.$timeout(() => {\r\n          this.initDatepicker();\r\n        });\r\n      });\r\n    }\r\n\r\n    if (this.name && !this.label) {\r\n      this.label = this.name;\r\n    }\r\n\r\n    // External attributes command the disabled dates in the calendar to update.\r\n    this.$scope.$watch(() => this.updateDisabledDates, (newVal, oldVal) => {\r\n      if (!this.datepicker) {\r\n        return;\r\n      }\r\n      if (newVal !== oldVal) {\r\n        this.onDisabledDatesExternalChange();\r\n      }\r\n    });\r\n\r\n    // For inline datepicker, we need to watch the model value changes and update the min-max range and days count.\r\n    this.$scope.$watch(() => this.model.$modelValue, (newVal, oldVal) => {\r\n      if (!this.isInline || !this.datepicker) {\r\n        return;\r\n      }\r\n      if (this.datepicker && (newVal.end !== oldVal.end || newVal.start !== oldVal.start)) {\r\n        this.setDatepickerCalendarValue(newVal);\r\n        if (this.minDate || this.maxDate) {\r\n          this.datepicker.update({ minDate: this.minDate, maxDate: this.maxDate }, { silent: true });\r\n        }\r\n        this.daysCount = this.getDaysCount(newVal);\r\n      }\r\n    }, true);\r\n  }\r\n\r\n  /** Handles the external change of the disabled dates. */\r\n  private onDisabledDatesExternalChange() {\r\n    this.validationError = \"\";\r\n    this.disableDates();\r\n\r\n    if (this._value) {\r\n      const date = Dates.asJSDate(this._value);\r\n\r\n      if (this.isDateDisabled(date)) {\r\n        this.validationError = \"SALAXY.NG1.DatepickerComponent.validationErrorDisabled\";\r\n      }\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Initialize the datepicker element.\r\n   */\r\n  public initDatepicker(isManualInputInit: boolean = false) {\r\n    if (this.datepickerInitialized) return;\r\n\r\n    const datepickerElem = this.$element[0].querySelector(\".datepicker-input\") as HTMLElement;\r\n    if (!datepickerElem) {\r\n      return;\r\n    }\r\n    this.datepickerInitialized = true;\r\n\r\n    let viewLevel = \"days\";\r\n    let minView = \"days\" as AirDatepickerViews;\r\n    let multipleDates: boolean | number = false;\r\n    let dateFormat = \"dd.MM.yyyy\";\r\n    let minDate: Date | string | number;\r\n    let maxDate: Date | string | number;\r\n    const clearButton = {\r\n      content: Translations.get(\"SALAXY.UI_Terms.clear\"),\r\n      className: \"clear-button btn-danger\",\r\n      onClick: () => {\r\n        this._manualInput = null;\r\n        this.clearValues();\r\n        this.validate();\r\n        this.$scope.$evalAsync();\r\n      }\r\n    };\r\n\r\n    let buttons: any[] = [];\r\n    if (this.showButtons) {\r\n      buttons.push(clearButton);\r\n    }\r\n\r\n    if (this.isMultiple) {\r\n      multipleDates = 365;\r\n      buttons = [];\r\n    }\r\n\r\n    if (this.format) {\r\n      switch (this.format) {\r\n        case \"month\":\r\n          dateFormat = \"MMMM, yyyy\";\r\n          viewLevel = \"months\";\r\n          minView = \"months\";\r\n          break;\r\n        case \"year\":\r\n          dateFormat = \"yyyy\";\r\n          viewLevel = \"years\";\r\n          minView = \"years\";\r\n          break;\r\n      }\r\n    }\r\n\r\n    if (this.dateDisabled) {\r\n      switch (this.dateDisabled) {\r\n        case \"next-weekday\":\r\n          minDate = Dates.asJSDate(Dates.asDate(\"today\"));\r\n          break;\r\n        case \"salary\":\r\n          minDate = Dates.asJSDate(Dates.add(Dates.asDate(\"today\"), -1, \"year\"));\r\n      }\r\n    } else {\r\n      if (this.minDate) {\r\n        minDate = this.minDate;\r\n      }\r\n      if (this.maxDate) {\r\n        maxDate = this.maxDate;\r\n      }\r\n    }\r\n\r\n    const localeMap = {\r\n      fi: localeFi,\r\n      en: localeEn,\r\n      sv: localeSv\r\n    };\r\n\r\n    const createPopperPlacement = !this.isInline;\r\n    const lang = Translations.getLanguage();\r\n\r\n    this.datepicker = new AirDatepicker(datepickerElem, {\r\n      locale: localeMap?.[lang] || localeFi,\r\n      view: viewLevel as AirDatepickerViews,\r\n      multipleDates: multipleDates,\r\n      autoClose: true,\r\n      buttons: buttons,\r\n      inline: this.isInline,\r\n      minView: minView,\r\n      dateFormat: dateFormat,\r\n      minDate: minDate,\r\n      maxDate: maxDate,\r\n      timepicker: this.timepicker,\r\n      onSelect: (event) => {\r\n        this.onSelect(event.date);\r\n      },\r\n      onChangeViewDate: () => {\r\n        if (this.datepicker?.currentView == \"days\") {\r\n          this.disableDates();\r\n        }\r\n      },\r\n      // Fix for the popper issue that causes quick flickering when the datepicker is shown.\r\n      onShow: () => {\r\n        const el = this.datepicker.$datepicker;\r\n        el.style.opacity = \"0\";\r\n\r\n        setTimeout(() => {\r\n          el.style.opacity = \"1\";\r\n        }, 50);\r\n      },\r\n      position({ $datepicker, $target, $pointer }) {\r\n        if (!createPopperPlacement) {\r\n          return;\r\n        }\r\n        createPopper($target, $datepicker, {\r\n          placement: \"bottom-end\",\r\n          strategy: \"fixed\",\r\n          modifiers: [\r\n            {\r\n              name: \"computeStyles\",\r\n              options: { adaptive: false }\r\n            },\r\n            {\r\n              name: \"arrow\",\r\n              options: { element: $pointer }\r\n            },\r\n          ]\r\n        });\r\n      }\r\n    });\r\n\r\n    this.disableDates();\r\n\r\n    if (this._value) {\r\n      this.setDatepickerCalendarValue(this._value);\r\n    }\r\n    if (!isManualInputInit && !this.isInline) {\r\n      this.datepicker.show();\r\n    }\r\n  }\r\n\r\n  /** Disables dates in the datepicker. Used right after the initialization or when an external value dictates so. */\r\n  private disableDates() {\r\n    const viewDates = this.datepicker.getViewDates();\r\n    this.datepicker.enableDate(viewDates);\r\n    const disabledDates = viewDates.filter(date => this.isDateDisabled(date));\r\n    this.datepicker.disableDate(disabledDates);\r\n  }\r\n\r\n  /**\r\n   * Calculates the days count from a value object.\r\n   * @param value Value object with days array or daysCount property.\r\n   * @returns The number of days.\r\n   */\r\n  private getDaysCount(value: any): number {\r\n    return value.days ? value.days.length : value.daysCount;\r\n  }\r\n\r\n  /** Wrapper for updating component value. Note: update is always made \"silent\", so that the onSelect event won't get fired. */\r\n  private setDatepickerCalendarValue(value: any) {\r\n    if (!this.isMultiple) {\r\n      this.datepicker.selectDate(value, { silent: true });\r\n      if (value) {\r\n        this.datepicker.setViewDate(value);\r\n      }\r\n    } else {\r\n      const dpValue = value.days ? value.days : [];\r\n      this.daysCount = this.getDaysCount(value);\r\n      const viewDate = dpValue[0] || null;\r\n\r\n      this.datepicker.selectDate(dpValue, { silent: true });\r\n      if (viewDate) {\r\n        this.datepicker.setViewDate(viewDate);\r\n      }\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Pick date from the calendar plugin event method.\r\n   * @param date Date value that's picked in the datepicker.\r\n   */\r\n  private onSelect(date) {\r\n    // Date is either a string or an array of date strings (in multiple mode).\r\n    let dateVal: string | string[];\r\n    let viewValue: string | string[] | { days: string | string[]; daysCount: number };\r\n\r\n    if (Array.isArray(date)) {\r\n      dateVal = date.map((d) => Dates.asDate(d));\r\n    } else if (date == null) {\r\n      dateVal = null;\r\n    } else if (this.timepicker) {\r\n      dateVal = date.toISOString();\r\n    } else {\r\n      dateVal = Dates.asDate(date);\r\n    }\r\n\r\n    // For inline multiple datepickers, preserve the object structure (period with start/end/days).\r\n    if (this.isInline && this.isMultiple) {\r\n      viewValue = {\r\n        ...this._value,\r\n        days: dateVal,\r\n        daysCount: Array.isArray(dateVal) ? dateVal.length : 0\r\n      };\r\n    } else {\r\n      viewValue = dateVal;\r\n    }\r\n\r\n    this._value = viewValue;\r\n    this._manualInput = null;\r\n    this.model.$setViewValue(viewValue);\r\n    this.validate();\r\n  }\r\n\r\n  /**\r\n   * Determines if a given date is disabled based on the dateDisabled configuration.\r\n   * Handles both custom disable functions and built-in disable methods.\r\n   * @param date The date to evaluate.\r\n   * @returns boolean Either true = date is disabled, false = not disabled.\r\n   */\r\n  private isDateDisabled(date: Date): boolean {\r\n    if (this.dateDisabled && this.disableFunction) {\r\n      return this.disableFunction(date);\r\n    }\r\n    return this.checkDateDisabled(date);\r\n  }\r\n\r\n  /**\r\n   * Checks if given date is disabled with one of two methods: \"next-weekday\" and \"salary\".\r\n   * @param date The date to evaluate.\r\n   * @returns boolean Either true = date is disabled, false = not disabled.\r\n   */\r\n  public checkDateDisabled(date) {\r\n    const role =  this.sessionService.isInRole(\"pro\") ? \"pro\" :\r\n              this.sessionService.isInRole(\"admin\") ? \"admin\" : null;\r\n    switch (this.dateDisabled) {\r\n      case \"next-weekday\":\r\n        return Dates.asDate(date) < Dates.addWorkdays(\"today\", 1) || !Dates.isWorkday(date);\r\n      case \"salary\":\r\n        return !SalaryDateLogic.isValidSalaryDate(date, null, null, true, this.paymentChannel, this.zeroPayment, role);\r\n    }\r\n  }\r\n\r\n  /** Gets the readonly value either from the controller or from the form */\r\n  protected getReadOnly(): boolean {\r\n    // This readOnly can be true, false or undefined\r\n    const readOnlyValue = (this.readOnly + \"\").trim().toLowerCase();\r\n    if (readOnlyValue === \"true\" || readOnlyValue === \"1\") {\r\n      return true;\r\n    }\r\n    if (readOnlyValue === \"false\" || readOnlyValue === \"0\") {\r\n      return false;\r\n    }\r\n    const readOnlyFormValue = !!this?.form?.$$element[0]?.attributes?.readonly;\r\n    if (readOnlyFormValue) {\r\n      return true;\r\n    }\r\n\r\n    return false;\r\n  }\r\n\r\n  /** Gets or sets the presence of the required validator in the underlying model. */\r\n  public get require(): boolean {\r\n    return !!this.model?.$validators.required;\r\n  }\r\n  public set require(value: boolean) {\r\n    const trySetValidator = () => {\r\n      if (!this.model) {\r\n        setTimeout(trySetValidator);\r\n        return;\r\n      }\r\n      const hasRequiredValidator = !!this.model.$validators.required;\r\n      if (value && !hasRequiredValidator) {\r\n        this.model.$validators.required = (modelValue, viewValue) => {\r\n          return !this.model.$isEmpty(viewValue);\r\n        };\r\n      } else if (!value && hasRequiredValidator) {\r\n        delete this.model.$validators.required;\r\n      }\r\n    };\r\n\r\n    trySetValidator();\r\n  }\r\n\r\n  /** Do validations. */\r\n  public validate() {\r\n    if (this.require && !this.model.$viewValue) {\r\n      this.validationError = \"SALAXY.NG1.DatepickerComponent.validationErrorRequired\";\r\n      this.model.$setValidity(\"required\", false);\r\n      return false;\r\n    }\r\n\r\n    this.validationError = \"\";\r\n    this.model.$setValidity(\"required\", true);\r\n    return true;\r\n  }\r\n\r\n  /**\r\n   * Manually typed date changed.\r\n   */\r\n  public changeManualDate() {\r\n    this.validationError = \"\";\r\n    const typedValue = this._manualInput?.trim();\r\n\r\n    if (!typedValue) {\r\n      if (this.require) {\r\n        return this.setError(\"SALAXY.NG1.DatepickerComponent.validationErrorRequired\");\r\n      }\r\n      this.clearValues();\r\n      return;\r\n    }\r\n\r\n    const normalized = this.normalizeManualInput(typedValue);\r\n    const parsed = Dates.parseDate(normalized, \"DD.MM.YYYY\");\r\n\r\n    if (!parsed) {\r\n      return this.setError(this.getValidationErrorKey());\r\n    }\r\n\r\n    if (!this.format && this.isDateDisabled(Dates.asJSDate(parsed))) {\r\n      return this.setError(\"SALAXY.NG1.DatepickerComponent.validationErrorDisabled\");\r\n    }\r\n\r\n    this._value = parsed;\r\n    this._manualInput = null;\r\n    this.model.$setViewValue(parsed);\r\n    this.setDatepickerCalendarValue(parsed);\r\n  }\r\n\r\n  /**\r\n   * Normalizes manual input based on format type.\r\n   */\r\n  private normalizeManualInput(input: string): string {\r\n    if (this.format == \"month\") {\r\n      const parts = input.split(/[./-]/);\r\n      return `01.${parts[0]?.padStart(2, \"0\")}.${parts[1]}`;\r\n    }\r\n\r\n    if (this.format == \"year\") {\r\n      return `01.01.${input}`;\r\n    }\r\n\r\n    const parts = input.split(\".\");\r\n    if (parts.length == 3) {\r\n      return `${parts[0].padStart(2, \"0\")}.${parts[1].padStart(2, \"0\")}.${parts[2]}`;\r\n    } else {\r\n      return input;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Gets the appropriate validation error key based on format.\r\n   */\r\n  private getValidationErrorKey(): string {\r\n    if (this.format == \"month\") return \"SALAXY.NG1.DatepickerComponent.validationErrorMonth\";\r\n    if (this.format == \"year\") return \"SALAXY.NG1.DatepickerComponent.validationErrorYear\";\r\n    return \"SALAXY.NG1.DatepickerComponent.validationErrorDefault\";\r\n  }\r\n\r\n  /**\r\n   * Sets the error message of the datepicker.\r\n   * @param errorMessage The error message to set.\r\n   */\r\n  private setError(errorMessage: string) {\r\n    this.validationError = errorMessage;\r\n    this.clearValues();\r\n    return;\r\n  }\r\n\r\n  /*\r\n   * Clears the values of the datepicker.\r\n   */\r\n  private clearValues() {\r\n    this._value = null;\r\n    this.model.$setViewValue(null);\r\n    this.datepicker.clear({ silent: true });\r\n  }\r\n}","import { DatepickerController } from \"./DatepickerController\";\r\nimport { SessionService } from \"../../services\";\r\n\r\n/**\r\n * Controller for datepicker popup control.\r\n */\r\nexport class DatepickerPopupController extends DatepickerController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"SessionService\", \"$element\", \"$timeout\", \"$scope\"];\r\n\r\n  /** Date format in text input. Default is d.M.yyyy */\r\n  public format: string;\r\n\r\n  constructor(sessionService: SessionService, $element: JQLite, $timeout: ng.ITimeoutService, $scope: ng.IScope) {\r\n    super(sessionService, $element, $timeout, $scope);\r\n  }\r\n\r\n  /** Gets the tooltip HTML with necessary escape. */\r\n  protected getToolTipHtml() {\r\n    // TODO: Add escaping if necessary.\r\n    return this.tooltipHtml;\r\n  }\r\n}","import angular from \"angular\";\r\n\r\nimport { DateRange, Dates, Translations } from \"@salaxy/core\";\r\nimport AirDatepicker from \"air-datepicker\";\r\nimport localeEn from \"air-datepicker/locale/en\";\r\nimport localeFi from \"air-datepicker/locale/fi\";\r\nimport localeSv from \"air-datepicker/locale/sv\";\r\n\r\n/**\r\n * Provides a user interface for picking up a date range\r\n * and optionally specifying also the number of working days within that range.\r\n */\r\nexport class DateRangeController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$element\", \"$timeout\"];\r\n\r\n  /** Label for the control */\r\n  public label: string;\r\n\r\n  /** Label for the scondary input. Translation is attempted. Default is SALAXY.NG1.DateRange.labelDaysCount.  */\r\n  public labelDaysCount: string;\r\n\r\n  /** The model that is bound to the input */\r\n  public model: angular.INgModelController;\r\n\r\n  /** The datepicker element instance. */\r\n  private datepicker: any;\r\n\r\n  /**\r\n   * The selection mode is either:\r\n   * - \"range\" for (default) calendar control with start and end.\r\n   * - \"calc\" for period selection that is optimized for salary calculation (months, 2 weeks, 1/2 months etc.)\r\n   */\r\n  public mode: \"range\" | \"calc\";\r\n\r\n  /** Form controller, if available */\r\n  public form: angular.IFormController;\r\n\r\n  /** If there is a validation error in period start, it is added here. */\r\n  public periodStartDateError = null;\r\n\r\n  /**\r\n   * If true, displays the control as read-only div instead of the input control.\r\n   * This \"read-only\" attribute is visualized in a different way than standard html \"readonly\" (ng-readonly):\r\n   * The input is not shown and display is more compact.\r\n   * Also note, that you may change the same read-only for the form using readonly / ng-readonly attribute.\r\n   * @example\r\n   * ```html\r\n   * <form name=\"foo\" ng-readonly=\"true\">\r\n   * <!-- .... or plain HTML ... -->\r\n   * <form name=\"foo\" readonly=\"true\">\r\n   * <!-- .... or plain HTML ... -->\r\n   * <salaxy-input name=\"input1\" read-only=\"true\"></salaxy-input>\r\n   */\r\n  public readOnly: boolean;\r\n\r\n  /**\r\n   * Fires an event when the model is changing: Any of the values specific to the model are changing: start, end or daysCount.\r\n   * This should typically used instead of ng-change because ng-change will only fire if the object reference changes.\r\n   * On-change fires when dates or day count changes and this is typically what you are looking for.\r\n   * @example <salaxy-date-range ng-model=\"$ctrl.dateRange\"></salaxy-date-range>\r\n   */\r\n  public onChange: () => void;\r\n\r\n  /** Validation error text */\r\n  public validationError: string;\r\n\r\n  /** User interface shortcuts for period selection */\r\n  public periodShortcuts: {\r\n    /** Text for current month. */\r\n    monthCurrent: string,\r\n    /** Text for last month. */\r\n    monthLast: string,\r\n    /** Text for other month. */\r\n    monthOther: string,\r\n    // monthMulti: \"Monta kuukautta\",\r\n    /** Text for two weeks. */\r\n    weeks2: string,\r\n    /** Text for half a month */\r\n    monthHalf: string,\r\n    /** Text for other period. */\r\n    other: string,\r\n  };\r\n\r\n  /** Form control name */\r\n  public name: string;\r\n\r\n  /** If true, the input value is required */\r\n  public require: boolean;\r\n\r\n  /** Value, that is used when selecting \"other\" period selection by typing a manual start date. */\r\n  private _periodStartDate: string | null;\r\n\r\n  /** Object containing all the values in the date range selection (start, end, days and daysCount). */\r\n  public dateRangeValues: DateRange & { formattedRange?: string };\r\n\r\n  /** Formatted start date displayed in the input field */\r\n  private _valueStart: string | null;\r\n\r\n  /** Formatted end date displayed in the input field */\r\n  private _valueEnd: string | null;\r\n\r\n  /** User's manual input for start date */\r\n  private _manualInputStart: string | null;\r\n\r\n  /** User's manual input for end date */\r\n  private _manualInputEnd: string | null;\r\n\r\n  /** Getter and setter for the start date value for the input field */\r\n  public get datepickerValueStart(): string {\r\n    if (this._manualInputStart != null) {\r\n      return this._manualInputStart;\r\n    }\r\n\r\n    return this._valueStart;\r\n  }\r\n  public set datepickerValueStart(value: string) {\r\n    this._manualInputStart = value;\r\n  }\r\n\r\n  /** Getter and setter for the end date value for the input field */\r\n  public get datepickerValueEnd(): string {\r\n    if (this._manualInputEnd != null) {\r\n      return this._manualInputEnd;\r\n    }\r\n\r\n    return this._valueEnd;\r\n  }\r\n  public set datepickerValueEnd(value: string) {\r\n    this._manualInputEnd = value;\r\n  }\r\n\r\n  constructor(private $element: JQLite, private $timeout: angular.ITimeoutService) {}\r\n\r\n  /** Set the values and defaults on init */\r\n  public $onInit() {\r\n    this.dateRangeValues = {\r\n      start: null,\r\n      end: null,\r\n      days: [],\r\n      daysCount: null\r\n    };\r\n\r\n    const currentMonth = Dates.getMonth(Dates.getToday());\r\n    this.periodShortcuts = {\r\n      monthCurrent: Translations.get(`SALAXY.ENUM.CalendarMonth.month${currentMonth}.label`),\r\n      monthLast: Translations.get(`SALAXY.ENUM.CalendarMonth.month${currentMonth === 1 ? 12 : (currentMonth - 1)}.label`),\r\n      monthOther: Translations.get(\"SALAXY.NG1.DateRange.otherMonth\"),\r\n      // monthMulti: \"Monta kuukautta\",\r\n      weeks2: Translations.get(\"SALAXY.UI_Terms.week2\"),\r\n      monthHalf: Translations.get(\"SALAXY.UI_Terms.monthHalf\"),\r\n      other: Translations.get(\"SALAXY.UI_Terms.otherPeriod\"),\r\n    };\r\n\r\n    this.model.$render = () => {\r\n      if (this.model.$viewValue?.start && this.model.$viewValue?.end) {\r\n        this._valueStart = Dates.getFormattedDate(this.model.$viewValue.start);\r\n        this._valueEnd = Dates.getFormattedDate(this.model.$viewValue.end);\r\n        this._periodStartDate = Dates.format(this.model.$viewValue.start, \"D.M.\", null);\r\n        this.dateRangeValues = this.buildDateRangeValues(this.model.$viewValue);\r\n      }\r\n    };\r\n\r\n    this.initDatepicker();\r\n  }\r\n\r\n  /** Gets or sets the period start date */\r\n  public get periodStartDate(): string {\r\n    return this._periodStartDate;\r\n  }\r\n  public set periodStartDate(value: string) {\r\n    this._periodStartDate = value;\r\n    const parts = (value || \"\").split(\".\");\r\n    if (parts.length < 2 || parts.length > 3) {\r\n      this.periodStartDateError = Translations.get(\"SALAXY.NG1.DateRange.periodStartDateError\");\r\n      return;\r\n    }\r\n    let year = (parts.length === 3) ? Number((parts[2] || \"\").trim()) : null;\r\n    if (!year || year < 2019 || year > 2100) {\r\n      year = Number(this.dateRangeValues.start.substr(0, 4));\r\n    }\r\n    const date = Dates.getDate(year, Number(parts[1]), Number(parts[0]));\r\n    if (date) {\r\n      this.periodStartDateError = null;\r\n      switch (this.periodShortcut) {\r\n        case \"monthCurrent\":\r\n        case \"monthLast\":\r\n        case \"monthOther\":\r\n          this.dateRangeValues = Dates.getDateRange(date, Dates.add(Dates.add(date,1,\"month\"),-1, \"day\"));\r\n          break;\r\n        case \"weeks2\":\r\n          this.dateRangeValues = Dates.getDateRange(date, Dates.add(Dates.add(date,2,\"week\"),-1, \"day\"));\r\n          break;\r\n        case \"monthHalf\":\r\n          if (Dates.getDay(date) === 15 || Dates.getDay(date) === 16 ) {\r\n            this.dateRangeValues = Dates.getDateRange(date, Dates.startEnd(date,\"end-month\"));\r\n          } else {\r\n            this.dateRangeValues = Dates.getDateRange(date, Dates.add(date,14, \"day\"));\r\n          }\r\n          break;\r\n        case \"other\":\r\n          this.dateRangeValues = Dates.getDateRange(date, date);\r\n          break;\r\n    }\r\n      this.datepicker.clear({silent: true});\r\n      this.setValues(this.dateRangeValues, false);\r\n    } else {\r\n      this.periodStartDateError = `${value}` + Translations.get(\"SALAXY.NG1.DateRange.periodStartDateError2\");\r\n    }\r\n  }\r\n\r\n  /** Gets the user interface shortcut for the period. */\r\n  public get periodShortcut(): string {\r\n    if (!this.dateRangeValues || !this.dateRangeValues.start || !this.dateRangeValues.end) {\r\n      return null;\r\n    }\r\n    if (this.dateRangeValues.start === Dates.getDate(\"today\", \"today\", 1)\r\n      && this.dateRangeValues.end === Dates.startEnd(\"today\",\"end-month\")) {\r\n\r\n        return \"monthCurrent\";\r\n    }\r\n    if (this.dateRangeValues.start === Dates.add(Dates.startEnd(\"today\",\"start-month\"),-1, \"month\")\r\n      && this.dateRangeValues.end === Dates.startEnd(Dates.add(Dates.startEnd(\"today\",\"start-month\"),-1, \"month\"),\"end-month\")) {\r\n      return \"monthLast\";\r\n    }\r\n    if (this.dateRangeValues.end === Dates.add(Dates.add(this.dateRangeValues.start,1, \"month\"),-1, \"day\")) {\r\n      return \"monthOther\";\r\n    }\r\n    if (this.dateRangeValues.end === Dates.add(Dates.add(this.dateRangeValues.start,2, \"week\"),-1, \"day\")) {\r\n      return \"weeks2\";\r\n\r\n    }\r\n\r\n    // if the range is 15 (14) days or\r\n    // starts 15th or 16th and ends month end\r\n    if ((Dates.getDuration(this.dateRangeValues.start, this.dateRangeValues.end ).days() === 14)\r\n      || (Dates.getDay(this.dateRangeValues.start) === 15 && this.dateRangeValues.end === Dates.startEnd(this.dateRangeValues.start,\"end-month\"))\r\n      || (Dates.getDay(this.dateRangeValues.start) === 16 && this.dateRangeValues.end === Dates.startEnd(this.dateRangeValues.start,\"end-month\"))) {\r\n        return \"monthHalf\";\r\n    }\r\n\r\n    // TODO: Potentially add other options.\r\n    return \"other\";\r\n  }\r\n  public set periodShortcut(value: string) {\r\n    this.periodStartDateError = null;\r\n    switch (value) {\r\n      case \"monthCurrent\":\r\n        this.dateRangeValues.start = Dates.startEnd(\"today\",\"start-month\");\r\n        this.dateRangeValues.end = Dates.startEnd(\"today\",\"end-month\");\r\n        break;\r\n      case \"monthOther\":\r\n        if (Dates.getDay(\"today\") === 1) {\r\n          // Move to tomorrow so that the selection is monthOther and not monthCurrent.\r\n          this.dateRangeValues.start = Dates.add(\"today\",1,\"day\");\r\n        } else {\r\n          this.dateRangeValues.start = Dates.asDate(\"today\");\r\n        }\r\n        this.dateRangeValues.end = Dates.add(Dates.add(this.dateRangeValues.start,1,\"month\"),-1,\"day\");\r\n        break;\r\n      case \"monthLast\":\r\n        this.dateRangeValues.start = Dates.add(Dates.startEnd(\"today\",\"start-month\"),-1, \"month\");\r\n        this.dateRangeValues.end = Dates.startEnd(this.dateRangeValues.start,\"end-month\");\r\n        break;\r\n      case \"weeks2\":\r\n        this.dateRangeValues.start = Dates.add(Dates.startEnd(\"today\",\"start-week\"),-2,\"week\"); //shift to start of current week, and then 2 weeks before\r\n        this.dateRangeValues.end = Dates.add(Dates.startEnd(\"today\",\"start-week\"),-1,\"day\"); //shift to last day of previous week.\r\n        break;\r\n      case \"monthHalf\":\r\n\r\n        // TODO Check this\r\n        if (Dates.getDay(\"today\") < 16) {\r\n          // 16 - (28,29,30,31)\r\n          this.dateRangeValues.start = Dates.add(Dates.add(Dates.startEnd(\"today\", \"start-month\"),-1,\"month\"),15,\"day\");\r\n          this.dateRangeValues.end = Dates.startEnd(this.dateRangeValues.start,\"end-month\");\r\n        } else {\r\n          // 1 - 15\r\n          this.dateRangeValues.start = Dates.startEnd(\"today\",\"start-month\");\r\n          this.dateRangeValues.end = Dates.add(this.dateRangeValues.start,14,\"day\");\r\n        }\r\n        break;\r\n      case \"other\":\r\n        this.dateRangeValues.start = Dates.add(\"today\",-1,\"day\");\r\n        this.dateRangeValues.end = Dates.asDate(\"today\");\r\n        break;\r\n    }\r\n    this.dateRangeValues = Dates.getDateRange(this.dateRangeValues.start, this.dateRangeValues.end);\r\n    this._periodStartDate = Dates.format(this.dateRangeValues.start, \"D.M.\", null);\r\n    this.setValues(this.dateRangeValues, true);\r\n  }\r\n\r\n  /**\r\n   * Initialize the datepicker element.\r\n   */\r\n  public initDatepicker() {\r\n    this.$timeout(() => {\r\n      const dateRangeElem = this.$element[0].querySelector(\".input-daterange\") as HTMLElement;\r\n      if (!dateRangeElem) {\r\n        return;\r\n      }\r\n\r\n      const localeMap = {\r\n        fi: localeFi,\r\n        en: localeEn,\r\n        sv: localeSv\r\n      };\r\n\r\n      const lang = Translations.getLanguage();\r\n\r\n      this.datepicker = new AirDatepicker(dateRangeElem, {\r\n        locale: localeMap?.[lang] || localeFi,\r\n        autoClose: true,\r\n        range: true,\r\n        toggleSelected: false,\r\n        onSelect: (event) => {\r\n          if (Array.isArray(event.date) && event.date.length > 1) {\r\n            this.onSelect(event.date);\r\n          }\r\n        },\r\n      });\r\n\r\n      if (this.dateRangeValues?.start && this.dateRangeValues?.end) {\r\n        this.datepicker.selectDate([this.dateRangeValues.start, this.dateRangeValues.end], { silent: true });\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Builds a complete DateRange object with formattedRange.\r\n   * @param dateRange Partial or complete DateRange object\r\n   * @returns Complete DateRange object with formattedRange\r\n   */\r\n  private buildDateRangeValues(dateRange: DateRange): any {\r\n    return {\r\n      ...dateRange,\r\n      formattedRange: Dates.getFormattedRange(dateRange.start, dateRange.end)\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Sets the current date range values and updates view/model as needed.\r\n   * @param dateRangeVals The date range values to set (should contain start and end).\r\n   * @param updateDatepickerElemValues If true, updates the datepicker element to reflect new values.\r\n   */\r\n  private setValues(dateRangeVals: DateRange, updateDatepickerElemValues: boolean) {\r\n    if (dateRangeVals?.start) {\r\n      if (updateDatepickerElemValues) {\r\n        this.datepicker.selectDate([dateRangeVals.start, dateRangeVals.end], { silent: true });\r\n      }\r\n      this.dateRangeValues = this.buildDateRangeValues(dateRangeVals);\r\n      this.model.$setViewValue(this.dateRangeValues);\r\n      this._periodStartDate = Dates.format(this.dateRangeValues.start, \"D.M.\", null);\r\n      this._valueStart = Dates.getFormattedDate(this.dateRangeValues.start);\r\n      this._valueEnd = Dates.getFormattedDate(this.dateRangeValues.end);\r\n      this._manualInputStart = null;\r\n      this._manualInputEnd = null;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Datepicker element change event method.\r\n   * @param date Date values that are picked in the datepicker.\r\n   */\r\n  private onSelect(date: any) {\r\n    this.$timeout(() => {\r\n      const start = Dates.asDate(date[0]);\r\n      const end = Dates.asDate(date[1]);\r\n\r\n      const dateObj = {\r\n        start: start,\r\n        end: end,\r\n        daysCount: Dates.getWorkdays(start, end).length\r\n      };\r\n\r\n      this.validationError = \"\";\r\n      this.setValues(dateObj, false);\r\n\r\n      if (this.onChange) {\r\n        this.onChange();\r\n      }\r\n    });\r\n  }\r\n\r\n  /** Gets the readonly value either from the controller or from the form */\r\n  protected getReadOnly(): boolean {\r\n    // This readOnly can be true, false or undefined\r\n    const readOnlyValue = (this.readOnly + \"\").trim().toLowerCase();\r\n    if (readOnlyValue === \"true\" || readOnlyValue === \"1\") {\r\n      return true;\r\n    }\r\n    if (readOnlyValue === \"false\" || readOnlyValue === \"0\") {\r\n      return false;\r\n    }\r\n    const readOnlyFormValue = !!this?.form?.$$element[0]?.attributes?.readonly;\r\n    if (readOnlyFormValue) {\r\n      return true;\r\n    }\r\n\r\n    return false;\r\n  }\r\n\r\n  /**\r\n   * Normalizes date format by padding day and month with leading zeros.\r\n   * @param value The date string to normalize (e.g., \"1.2.2024\")\r\n   * @returns Normalized date string (e.g., \"01.02.2024\")\r\n   */\r\n  private normalizeDate(value: string): string {\r\n    const parts = value.split(\".\");\r\n    if (parts.length == 3) {\r\n      return `${parts[0].padStart(2, \"0\")}.${parts[1].padStart(2, \"0\")}.${parts[2]}`;\r\n    }\r\n    return value;\r\n  }\r\n\r\n  /**\r\n   * User types either the start or end date manually.\r\n   */\r\n  public changeManualDate() {\r\n    this.validationError = \"\";\r\n    const typedValueStart = (this._manualInputStart != null ? this._manualInputStart : this._valueStart);\r\n    const typedValueEnd = (this._manualInputEnd != null ? this._manualInputEnd : this._valueEnd);\r\n\r\n    if (!typedValueStart || !typedValueEnd) {\r\n      return this.setError(\"SALAXY.NG1.DatepickerComponent.validationErrorDateRangeRequired\");\r\n    }\r\n\r\n    const normalizedStart = this.normalizeDate(typedValueStart);\r\n    const normalizedEnd = this.normalizeDate(typedValueEnd);\r\n\r\n    const parsedStart = Dates.parseDate(normalizedStart, \"DD.MM.YYYY\");\r\n    const parsedEnd = Dates.parseDate(normalizedEnd, \"DD.MM.YYYY\");\r\n\r\n    if (!parsedStart || !parsedEnd) {\r\n      return this.setError(\"SALAXY.NG1.DatepickerComponent.validationErrorDefault\");\r\n    }\r\n\r\n    if (parsedEnd < parsedStart) {\r\n      return this.setError(\"SALAXY.NG1.DatepickerComponent.validationErrorDateRangeInvalid\");\r\n    }\r\n\r\n    // Get days' count, formatted range and update the date-range-picker below and its current view.\r\n    const dateObj = {\r\n      start: parsedStart,\r\n      end: parsedEnd,\r\n      daysCount: Dates.getWorkdays(parsedStart, parsedEnd).length\r\n    };\r\n\r\n    this.setValues(dateObj, true);\r\n    this.datepicker.setViewDate(this.dateRangeValues.end);\r\n\r\n    if (this.onChange) {\r\n      this.onChange();\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Sets the error message and clears the date range values.\r\n   * @param errorMessage The error message to set.\r\n   */\r\n  private setError(errorMessage: string) {\r\n    this.validationError = errorMessage;\r\n    this.model.$setViewValue(null);\r\n    this.datepicker.clear({ silent: true });\r\n    return;\r\n  }\r\n\r\n  /**\r\n   * Called when the daysCount input is manually changed.\r\n   */\r\n  public onDaysCountChange(): void {\r\n    this.model.$setViewValue({ ...this.dateRangeValues });\r\n    if (this.onChange) {\r\n      this.onChange();\r\n    }\r\n  }\r\n}","import angular from \"angular\";\r\nimport { FormGroupLabelType } from \"./FormGroupLabelType\";\r\n\r\n/**\r\n * Helper for rendering the HTML for FormGroup:\r\n * This component renders only the label - input html.\r\n * It does not do any of the real form-control logic like ng-model, validations etc.\r\n * The \"input\" part of the form group may be a non form control - e.g. just a text.\r\n * Also the label may be hidden.\r\n */\r\nexport class FormGroupController implements angular.IController {\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [];\r\n\r\n  /** Label for the control */\r\n  public label: string;\r\n\r\n  /** Form control name */\r\n  public name: string;\r\n\r\n  /** If true, shows the asterix in the label. */\r\n  public require: boolean;\r\n\r\n  /**\r\n   * @deprecated Use \"require\" instead:\r\n   * This attribute overlaps with required/ng-required directive, which produces unexpected results.\r\n   */\r\n  public required: string;\r\n\r\n  /**\r\n   * Positioning of the label of form-control.\r\n   * Supported values are \"horizontal\" (default), \"no-label\", \"plain\", \"basic\", \"inline\" and \"empty-label\".\r\n   * See FormGourpLabelType for details.\r\n   */\r\n  public labelType: FormGroupLabelType;\r\n\r\n  /**\r\n   * Label columns expressed as Bootstrap grid columns.\r\n   * Default is 'col-sm-4' for label-type: 'horizontal' and 'col-sm-12' for label-type: 'no-label'.\r\n   * Other label-types do not have column classes at the moment.\r\n   */\r\n  public labelCols: string;\r\n\r\n  constructor() { /* Dependency injeciton */ }\r\n\r\n  /**\r\n   * Checks the existence of name property.\r\n   */\r\n  public $onInit() {\r\n    if (!this.name) {\r\n      throw new Error(`Property 'name' is required for Salaxy form controls (label: ${this.label}).`);\r\n    }\r\n    if (this.name && this.label == null) {\r\n      this.label = this.name;\r\n    }\r\n    if (this.required) {\r\n      const legacyRequiredValue = this.required?.toLowerCase().trim();\r\n      this.require = legacyRequiredValue === \"true\" || legacyRequiredValue === \"1\";\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Gets the class (or classes space separated) for label or value element.\r\n   */\r\n  public getLabelCols(forElement: \"label\" | \"value\" | \"no-label\" ): string {\r\n    switch (forElement) {\r\n      case \"label\":\r\n        return this.labelCols || \"col-sm-4\";\r\n      case \"value\": {\r\n        let classes = \"\";\r\n        if (this.labelCols && this.labelCols.length >= 8) {\r\n          const regex = /col-(xs|sm|md|lg)-([1-9][1-2]?)/gm;\r\n          let m = regex.exec(this.labelCols);\r\n          while (m !== null) {\r\n              if (m.index === regex.lastIndex) {\r\n                  regex.lastIndex++;\r\n              }\r\n              const colsCount = parseInt(m[2], 10);\r\n              if (colsCount > 0 && colsCount < 13) {\r\n                classes += `col-${ m[1] }-${ 12 - colsCount} `;\r\n              }\r\n              m = regex.exec(this.labelCols);\r\n          }\r\n        }\r\n        return classes.trim() || \"col-sm-8\";\r\n      }\r\n      case \"no-label\":\r\n        return this.labelCols || \"col-sm-12\";\r\n    }\r\n  }\r\n\r\n  /** Gets the label type with \"horizontal\" as default / unknown value. */\r\n  protected getLabelType() {\r\n    switch (this.labelType) {\r\n      case \"no-label\":\r\n      case \"plain\":\r\n      case \"basic\":\r\n      case \"empty-label\":\r\n      case \"inline\":\r\n        return this.labelType;\r\n      default:\r\n        return \"horizontal\";\r\n    }\r\n  }\r\n}\r\n","import angular from \"angular\";\r\nimport { InputBase } from \"./_InputBase\";\r\n\r\n/**\r\n * Base controller for form control groups (label, input, validation errors etc.).\r\n */\r\nexport class InputController extends InputBase<string> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [];\r\n\r\n  /** Minimum length, 0 is the default */\r\n  public minlength: number;\r\n\r\n  /** Maximum length, 1024 is the default */\r\n  public maxlength: number;\r\n\r\n  /** The rows property of the textarea. Default is 3. Not used input, only textarea. */\r\n  public rows: number;\r\n\r\n  /** Regular expression pattern for validation */\r\n  public pattern: string;\r\n\r\n  /** If true, sets the readonly attribute of the input with ng-readonly. */\r\n  public readonly: boolean;\r\n\r\n  /** The model that is bound to the input */\r\n  public model: angular.INgModelController;\r\n  /**\r\n   * Creates a new InputController\r\n   * @ignore\r\n   */\r\n  constructor() {\r\n    super();\r\n  }\r\n\r\n  /** Set the values and defaults on init */\r\n  public $onInit() {\r\n    if (!this.maxlength) {\r\n      this.maxlength = 100000;\r\n    }\r\n    if (this.minlength) {\r\n      this.require = true;\r\n    }\r\n    if (this.required) {\r\n      this.require = true;\r\n    }\r\n    super.$onInit();\r\n  }\r\n\r\n  /** On change of the value, do preventive operations and set value to model. */\r\n  public onChange() {\r\n    if (this.value && this.maxlength && this.value.length > this.maxlength) {\r\n      this.value = this.value.substring(0, this.maxlength);\r\n    }\r\n    super.onChange();\r\n  }\r\n}","import { InputController } from \"./InputController\";\r\nimport { AccountingTargetListItem, ODataQueryOptions, AccountingTargets } from \"@salaxy/core\";\r\n/**\r\n * Controller behind form controls that select an accounting target.\r\n */\r\n\r\nexport class InputAccountingTargetController extends InputController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"AccountingTargets\"];\r\n  public _accountingTargetDisplayItem: AccountingTargetListItem;\r\n  /**\r\n   * Creates a new InputAccountingTargetController\r\n   * @ignore\r\n   */\r\n  constructor(private accountingTargets: AccountingTargets) {\r\n    super();\r\n  }\r\n\r\n  /**\r\n   * Query all available accountingTargets from index\r\n   */\r\n  public queryAccountingTargets(search: string): Promise<AccountingTargetListItem[]> {\r\n    search = search ?? \"\";\r\n    const queryOptions: ODataQueryOptions = {\r\n      $search: search,\r\n      $top: 50\r\n    };\r\n    return this.accountingTargets.getOData(queryOptions).then((result) => {\r\n      return result.items;\r\n    });\r\n  }\r\n\r\n\r\n\r\n  /**\r\n   * Get selected accounting target displayName\r\n   * @param accountingTargetId selected accounting target id\r\n   * @param refresher helper for refreshing view after\r\n   * @returns accountingTargetDisplayName from otherPartyInfo.avatar.displayName\r\n   */\r\n  public queryAccountingTargetDisplayName(accountingTargetId: string, refresher: any[]): string {\r\n    if (!accountingTargetId) {\r\n      return \"\";\r\n    }\r\n    if (this._accountingTargetDisplayItem && this._accountingTargetDisplayItem.id === accountingTargetId) {\r\n      return this._accountingTargetDisplayItem.otherPartyInfo.avatar.displayName;\r\n    }\r\n\r\n    this._accountingTargetDisplayItem = {\r\n      id: accountingTargetId,\r\n      otherPartyInfo: {\r\n        avatar: {\r\n          displayName: accountingTargetId\r\n        }\r\n      }\r\n    };\r\n\r\n    const queryOptions: ODataQueryOptions = {\r\n      $filter: `id eq '${accountingTargetId}_AccountingTargetDto'`,\r\n      $top: 50\r\n    };\r\n    this.accountingTargets.getOData(queryOptions).then((result) => {\r\n      this._accountingTargetDisplayItem = (result.items.find((item) => item.id === accountingTargetId)) ?? this._accountingTargetDisplayItem;\r\n      refresher[0] = new Date().getTime();\r\n    });\r\n    return this._accountingTargetDisplayItem.otherPartyInfo.avatar.displayName;\r\n  }\r\n\r\n}\r\n","import { InputBase } from \"./_InputBase\";\r\n\r\n/**\r\n * Controller behind boolean form controls (checkbox, radio, switch)\r\n */\r\n\r\nexport class InputBooleanController extends InputBase<boolean> {\r\n\r\n    /**\r\n     * For NG-dependency injection\r\n     * @ignore\r\n     */\r\n    public static $inject = [];\r\n\r\n    /** Type of the input element. Default is checkbox. */\r\n    public type: \"checkbox\" | \"radio\" | \"select\" | \"switch-xl\" | \"switch\";\r\n\r\n    /**\r\n     * Text to show as a label for input with value FALSE\r\n     * Supported by types radio and dropdown\r\n     */\r\n     public labelFalse: string;\r\n\r\n     /**\r\n      * Text to show as a label for input with value TRUE\r\n      * Supported by types radio, checkbox and dropdown\r\n      */\r\n     public labelTrue: string;\r\n\r\n    /**\r\n     * TODO: Is this needed when there's support for 'empty-label' ?\r\n     * BS class for offsetting the input (no-label)\r\n     */\r\n\r\n    public offsetCols: string;\r\n\r\n    /** If true, the radio buttons are aligned horizontally side-by-side */\r\n    public horizontal: boolean;\r\n\r\n     /**\r\n      * Creates a new InputController\r\n      * @ignore\r\n      */\r\n      constructor() {\r\n        super();\r\n      }\r\n\r\n      /** Toggles boolean value. */\r\n      public toggle() {\r\n        this.value = !this.value;\r\n        this.onChange();\r\n      }\r\n}\r\n","import { InputEnumOption, Translations, cbaCodes } from \"@salaxy/core\";\r\nimport { InputController } from \"./InputController\";\r\n\r\n/**\r\n * Controller behind form controls that selects Collective Bargain Agreement code.\r\n */\r\nexport class InputCollectiveBargainAgreementController extends InputController {\r\n\r\n  /**\r\n   * List of collective bargain agreement codes to exclude from the selection list.\r\n   */\r\n  public hiddenCodes: number[];\r\n\r\n  private cbaCodes: InputEnumOption[] = [];\r\n\r\n  public static $inject = [];\r\n\r\n  /**\r\n   * Creates a new InputCollectiveBargainAgreementController\r\n   * @ignore\r\n   */\r\n  constructor() {\r\n    super();\r\n  }\r\n\r\n  /** Sets the default values in init. */\r\n  public $onInit() {\r\n    super.$onInit();\r\n    const currentLanguage = Translations.getLanguage();\r\n    this.cbaCodes = cbaCodes.map((x: any) => {\r\n      const text = currentLanguage === \"fi\" ? x.labelFi : currentLanguage === \"en\" ? x.labelEn : x.labelSv;\r\n      return { value: x.code, text } as InputEnumOption;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Returns filtered list of collective bargain agreement codes based on search string.\r\n   * @param searchString - String to filter codes by\r\n   * @returns Filtered list of collective bargain agreement codes as InputEnumOptions\r\n   */\r\n  public getCbaCodes = (searchString: string): InputEnumOption[] => {\r\n    if (!searchString || searchString.length < 2) {\r\n      return this.cbaCodes.filter( (x) => !this.hiddenCodes?.find( (c) => c.toString() === x.value.toString()) );\r\n    }\r\n    let result = this.cbaCodes.filter((x) => x.text.toLowerCase().indexOf(searchString.toLowerCase()) >= 0);\r\n    if (this.hiddenCodes) {\r\n      result = result.filter( (x) => !this.hiddenCodes.find( (c) => c.toString() === x.value.toString()) );\r\n    }\r\n    return result;\r\n  };\r\n\r\n  /**\r\n   * Returns the label for given collective bargain agreement code.\r\n   * @param value - Value of the collective bargain agreement code.\r\n   */\r\n  public getCbaLabel = (value: string): string => {\r\n    return this.cbaCodes.find(x => x.value === value)?.text;\r\n  };\r\n\r\n  /** Returns the placeholder text - this control has a default text. */\r\n  public getPlaceholder() {\r\n    return super.getPlaceholder() || Translations.get(\"SALAXY.NG1.InputCollectiveBargainAgreement.getPlaceholder\");\r\n  }\r\n\r\n  /**\r\n   * Returns the HTML for the tooltip.\r\n   * @returns HTML for the tooltip\r\n   */\r\n  public getToolTipHtml() {\r\n    return `<span>${Translations.get(\"SALAXY.NG1.WorkerWizardComponent.employment.info.cbaCodeInfo\")}</span>`;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Arrays, EnumerationsLogic, InputEnumOption, Objects, Translations } from \"@salaxy/core\";\r\nimport { InputController } from \"./InputController\";\r\n\r\n/**\r\n * Controller behind form controls that select an occupation type.\r\n */\r\nexport class InputEnumController extends InputController {\r\n  /**\r\n   * Binds to an enumeration defined by the Salaxy API.\r\n   * Set the name of the enumeration.\r\n   */\r\n  public enum: string;\r\n\r\n  /** Type of the input element. Options are typeahead, select (default) and radio. Todo: remove 'uib-dropdown' */\r\n  public type: \"select\" | \"radio\" | \"multi-select\" | \"dropdown\";\r\n\r\n  /** Options of the select control as a key-value object. */\r\n  protected _options: any;\r\n\r\n  /**\r\n   * Array or comma separated string to filter the option values to just the given ones.\r\n   * Also sets the order to this order, so works for ordering a given set of values.\r\n   * Note that hiddenOptions is applied first, so if you want e.g. \"undefined\" to appear if selected,\r\n   * you may add it here and it behaves as expected (undefined is still hidden if a value is selevted).\r\n   */\r\n  public filter: string[];\r\n\r\n  /** If set to true, does not cache enums. */\r\n  public disableCache;\r\n\r\n  /**\r\n   * These values are visible only if they are selected in the data.\r\n   * Default is [\"undefined\"], set to empty array to show all in every state.\r\n   * I.e. after something else is selected, hidden value cannot be selected back.\r\n   * Use for not-selected values (\"Please choose...\") when you do not want selection reversed\r\n   * or legacy data that is not selectable, but may still exist on the server.\r\n   */\r\n  public hiddenOptions: string[];\r\n\r\n  /**\r\n   * These values are not considered as valid in the UI.\r\n   * Default is [\"unknown\"] and only used when input is \"required\" and input type is \"select\"\r\n   * Use in situations where an unknown/other/none value is set in API but should not be available as an option.\r\n   */\r\n  public invalidEnums: string[];\r\n\r\n  /**\r\n   * Label format for the option. The default format is to show only the text of the option.\r\n   * Options are:\r\n   * \"text\" or empty: only the text of the option is displayed.\r\n   * \"text-value\": in addition to the text, the value is also displayed in the label.\r\n   * \"value\": only the value is displayed.\r\n   * \"title\": Title (description of enumeration) if available. Defaults to text.\r\n   */\r\n  public labelFormat:  \"text\" | \"value\" | \"text-value\" | \"title\";\r\n\r\n  /**\r\n   * If set, last selected option is stored in LocalStorage and set as default/selected value in element.\r\n   * Currently supported only in type 'select' and 'uib-dropbdown'.\r\n   */\r\n  public remember: string;\r\n  private enumCache: InputEnumOption[] = [];\r\n\r\n  // TODO: tarpeeton?\r\n  constructor() {\r\n    super();\r\n  }\r\n\r\n  /** Sets the default values in init. */\r\n  public $onInit() {\r\n    super.$onInit();\r\n    if (!this.type) {\r\n      this.type = \"select\";\r\n    }\r\n    if (!this.hiddenOptions) {\r\n      this.hiddenOptions = [\"undefined\"];\r\n    }\r\n    if (!this.invalidEnums) {\r\n      this.invalidEnums = [\"unknown\"];\r\n    }\r\n    if (this.remember && window.localStorage.getItem(this.remember+\".\"+this.name)){\r\n      this.value = this.getStoredValue();\r\n      super.onChange();\r\n    }\r\n  }\r\n\r\n  /** Options list */\r\n  public get options(): any[] {\r\n    return this._options;\r\n  }\r\n  public set options(value: any[]) {\r\n    this._options = value;\r\n  }\r\n\r\n  /**\r\n   * Gets the label for an enumeration.\r\n   * @param value Type of the enum.\r\n   */\r\n  public getEnumerationLabel(value: string): string {\r\n    const option = this.getEnumerations().find((x) => x.value === value);\r\n    if (option) {\r\n      return this.formatLabel(option);\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /** Returns true if the placeholder should be added to the options. */\r\n  public get showPlaceholder(): boolean {\r\n    if (!this.value || this.value === \"undefined\" || this.value === \"unknown\") {\r\n      if (!this.getEnumerations().find((x) => x.value === this.value)) {\r\n        return true;\r\n      }\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /** Formats the label for display and typeahed searches. */\r\n  public formatLabel(option: InputEnumOption) {\r\n    switch(this.labelFormat) {\r\n      case \"value\":\r\n        return option.value;\r\n      case \"text-value\":\r\n        {\r\n          let text = option.text ? Translations.get(option.text) : option.text;\r\n          text = text ? text : option.value;\r\n          return `${text}${option.value ? \" (\" + option.value +\")\" : \"\"}`;\r\n        }\r\n      case \"title\":\r\n        return Translations.get(option.title) ?? Translations.get(option.text);\r\n      case \"text\":\r\n      default:\r\n        return Translations.get(option.text);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Returns items for current enumeration.\r\n   */\r\n  protected getEnumerations(): InputEnumOption[] {\r\n    if (this.enumCache.length > 0 && !this.disableCache) {\r\n      return this.enumCache;\r\n    }\r\n    let allValues: InputEnumOption[] = [];\r\n    const selectedValue = this.value;\r\n    if (this.options) {\r\n      if (Array.isArray(this.options)) {\r\n        allValues = this.options.map((item: any) => {\r\n          if (item == null) {\r\n            return { value: null, text: \"[null]\" };\r\n          }\r\n          if (Objects.has(item, \"value\") || Objects.has(item, \"text\")) {\r\n            return {\r\n              value: item.value,\r\n              text: item.text,\r\n              title: (item.title && item.title !== item.value) ? item.title : null,\r\n              ui: item.ui ? item.ui : null\r\n            };\r\n          }\r\n          return { value: item, text: item };\r\n        });\r\n      } else {\r\n        allValues = Object.keys(this.options)\r\n          .map((key) => ({ value: key, text: this.options[key], title: null }));\r\n      }\r\n    } else if (this.enum) {\r\n      const enums = EnumerationsLogic.getEnumMetadata(this.enum);\r\n      if (enums) {\r\n        allValues = enums.values\r\n          .map((e) => ({ value: e.name, text: e.label, title: e.descr && e.descr !== e.name ? e.descr : null }));\r\n      } else {\r\n        allValues = [{\r\n          value: \"\",\r\n          text: `ERROR: ${this.enum} not found.`,\r\n          title: null,\r\n        }];\r\n      }\r\n    }\r\n    if (this.hiddenOptions) {\r\n      allValues = allValues.filter((option) => {\r\n        const matchingHiddenValue = Arrays.assureArray(this.hiddenOptions).find((hiddenValue) => hiddenValue === option.value);\r\n        // Hidden is shown only if it is currently selected in data.\r\n        return matchingHiddenValue == null || matchingHiddenValue === selectedValue;\r\n      });\r\n    }\r\n    const filterArr = Arrays.assureArray(this.filter);\r\n    if (filterArr.length > 0) {\r\n      allValues = filterArr.map((x) => allValues.find((y) => y.value === x)).filter((x) => x != null);\r\n    }\r\n    this.modifyOptions(allValues, this.enumCache);\r\n    return this.enumCache;\r\n  }\r\n\r\n  private modifyOptions(\r\n    source: ({\r\n      /** Enum value. */\r\n      value: any,\r\n      /** Label for the value. */\r\n      text: string,\r\n      /** Description for the value. */\r\n      title?: string,\r\n    })[],\r\n    target: ({\r\n      /** Enum value. */\r\n      value: any,\r\n      /** Label for the value. */\r\n      text: string,\r\n      /** Description for the value. */\r\n      title?: string,\r\n    })[]) {\r\n    // check if source values differ from target\r\n    const ok = angular.equals(source, target);\r\n\r\n    if (ok) {\r\n      return;\r\n    }\r\n    // remove values\r\n    target.splice(0, target.length);\r\n\r\n    // add values\r\n    target.push(...source);\r\n  }\r\n\r\n  /** Store selection to LocalStorage */\r\n  public setStoredValue(inputName: any, value: any){\r\n    if(this.remember && window.localStorage){\r\n      const storageKey = this.remember +\".\" + inputName;\r\n      window.localStorage.setItem(storageKey, value);\r\n    }\r\n  }\r\n\r\n  /** Get stored value from LocalStorage*/\r\n  public getStoredValue(){\r\n    if(this.remember && window.localStorage){\r\n      const storageKey = this.remember +\".\" + this.name;\r\n      return window.localStorage.getItem(storageKey);\r\n    }\r\n    return null;\r\n  }\r\n}","import angular from \"angular\";\r\n\r\nimport { SessionUserCredential } from \"@salaxy/core\";\r\n\r\nimport { WorkflowService } from \"../../services\";\r\nimport { InputEnumController } from \"./InputEnumController\";\r\n\r\n/**\r\n * Controller for selecting a credential.\r\n */\r\n\r\nexport class InputCredentialController extends InputEnumController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$scope\", \"WorkflowService\"];\r\n\r\n  private credentials: SessionUserCredential[] = [];\r\n\r\n  /**\r\n   * Creates a new InputOccupationTypeController\r\n   * @ignore\r\n   */\r\n  constructor(private $scope: angular.IScope, private workflowService: WorkflowService) {\r\n    super();\r\n  }\r\n\r\n  /** Options list */\r\n  public get options(): any[] {\r\n    const newCredentials = this.workflowService.credentials || [];\r\n    if (!angular.equals(this.credentials, newCredentials)) {\r\n      this._options = newCredentials.map( (x) => {\r\n        return {\r\n          value: x.id,\r\n          text: x.avatar.displayName,\r\n        };\r\n      });\r\n    }\r\n    return this._options;\r\n  }\r\n  public set options(value: any[]) {\r\n    // empty on purpose\r\n    // this._options = value;\r\n  }\r\n}\r\n","import { InputBase } from \"./_InputBase\";\r\n\r\n/**\r\n * Controller for Duration edit input\r\n */\r\n\r\nexport class InputDurationController extends InputBase<string> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [];\r\n\r\n  public innerValue: {\r\n    /** If true, the duration is negative, meaning \"before\" the reference time. */\r\n    isNegative: boolean,\r\n    /** Integer number of days. */\r\n    days: number,\r\n    /** Rest of the duration is just kept if it exists. It cannot be edited at the moment. */\r\n    rest: string,\r\n  };\r\n\r\n  /**\r\n   * Creates a new InputController\r\n   * @ignore\r\n   */\r\n  constructor() {\r\n    super();\r\n  }\r\n\r\n  /** Set the values and defaults on init */\r\n  public $onInit() {\r\n    if (this.name && !this.label) {\r\n      this.label = this.name;\r\n    }\r\n    this.model.$render = () => {\r\n      this.value = this.model.$viewValue;\r\n      this.setInnerValue(this.model.$viewValue);\r\n    };\r\n    this.validate();\r\n  }\r\n\r\n  /** Called when the view changes the model. */\r\n  public onChange() {\r\n    this.value = this.getInnerValue();\r\n    super.onChange();\r\n  }\r\n\r\n  /** Gets the inner value as string */\r\n  public getInnerValue(): string {\r\n    if (!this.innerValue) {\r\n      return null;\r\n    }\r\n    let result = \"\";\r\n    if (this.innerValue.days != null && !isNaN(this.innerValue.days)) {\r\n      result += this.innerValue.days;\r\n    }\r\n    if (this.innerValue.rest) {\r\n      if (result != \"\") {\r\n        result += \".\";\r\n      }\r\n      result += this.innerValue.rest;\r\n    }\r\n    if (result == \"\") {\r\n      return null;\r\n    }\r\n    if (this.innerValue.isNegative) {\r\n      result = \"-\" + result;\r\n    }\r\n    return result;\r\n  }\r\n\r\n  /** Parses an input string and sets the inner value based on it. */\r\n  public setInnerValue(value: string) {\r\n    value = value?.trim();\r\n    if (!value) {\r\n      this.innerValue = null;\r\n      return;\r\n    }\r\n    this.innerValue = this.innerValue || {} as any;\r\n    if (value[0] == \"-\") {\r\n      this.innerValue.isNegative = true;\r\n      value = value.substring(1);\r\n    } else {\r\n      this.innerValue.isNegative = false;\r\n    }\r\n    const point = value.indexOf(\".\");\r\n    if (point >= 0) {\r\n      this.innerValue.days = parseInt(value.substr(0, point)) || 0;\r\n      this.innerValue.rest = value.substr(point + 1).trim();\r\n    } else {\r\n      if (value.indexOf(\":\") >= 0) {\r\n        this.innerValue.days = parseInt(value) || 0;\r\n        this.innerValue.rest = null;\r\n      } else {\r\n        this.innerValue.days = null;\r\n        this.innerValue.rest = value.trim();\r\n      }\r\n    }\r\n  }\r\n}\r\n","import { IncomeTypesLogic, Translations } from \"@salaxy/core\";\r\n\r\nimport { InputController } from \"./InputController\";\r\n\r\n/**\r\n * Controller behind form controls that selects Income type code for transaction in Income Registry (Tulorekisteri).\r\n */\r\n\r\nexport class InputIncomeTypeController extends InputController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"SessionService\", \"UiHelpers\"];\r\n\r\n  /** Type of the input element. Default is typeahead. */\r\n  public type: \"typehead\" | \"list\";\r\n\r\n  /**\r\n   * List of income type codes to exclude from the selection list.\r\n   */\r\n  public hiddenCodes: number[];\r\n\r\n  /**\r\n   * Creates a new InputIncomeTypeController\r\n   * @ignore\r\n   */\r\n  constructor() {\r\n    super();\r\n  }\r\n\r\n  /** Sets the default values in init. */\r\n  public $onInit() {\r\n    super.$onInit();\r\n    if (!this.type) {\r\n      this.type = \"typehead\";\r\n    }\r\n  }\r\n\r\n  /** Gets the list of all income types. */\r\n  public getIncomeTypes = (searchString: string) => {\r\n    IncomeTypesLogic.getAll();\r\n    let result = IncomeTypesLogic.search(searchString);\r\n\r\n    if (this.hiddenCodes) {\r\n      result = result.filter(x => !this.hiddenCodes.includes(x.code));\r\n    }\r\n\r\n    return result.map(incomeType => ({\r\n      value: incomeType.code,\r\n      text: incomeType.label,\r\n      title: incomeType.description,\r\n      ui: {\r\n        initials: incomeType.code,\r\n        color: \"#2b507c\",\r\n        entityType: \"company\"\r\n      }\r\n    }));\r\n  };\r\n\r\n  /**\r\n   * Returns the label for given income type.\r\n   * @param code - Income type code.\r\n   */\r\n  public getRowLabel(code: string): string {\r\n    if (!code) {\r\n      return null;\r\n    }\r\n    const type = IncomeTypesLogic.getAll().find((x) => x.code === Number(code));\r\n    return type ? (type.code + \" - \" + type.label) : \"SALAXY.NG1.InputIncomeType.getRowLabelNotFound\" + code;\r\n  }\r\n\r\n  /** Returns the placeholder text - this control has a default text. */\r\n  public getPlaceholder() {\r\n    return super.getPlaceholder() || Translations.get(\"SALAXY.NG1.InputIncomeType.getPlaceholder\");\r\n  }\r\n}\r\n","import {  CalcRowsLogic, CalculationRowUnit, Numeric } from \"@salaxy/core\";\r\n\r\nimport { InputBase } from \"./_InputBase\";\r\n\r\n/**\r\n * Controller behind form controls that select an occupation type.\r\n */\r\nexport class InputNumberController extends InputBase<number> {\r\n\r\n    /**\r\n     * Unit for the number.\r\n     * If set, shows a visual clue of the unit.\r\n     * For 'percent' editor value is multiplied by 100.\r\n     */\r\n    public unit: CalculationRowUnit;\r\n\r\n    /**\r\n     * Expression for the allowed Units for the number.\r\n     * If set, shows a selection of control for the unit.\r\n     */\r\n     public units: CalculationRowUnit[];\r\n\r\n    /** Type of the input element. Options are default and slider */\r\n    public type: \"default\" | \"slider\";\r\n\r\n    /** Step for slider */\r\n    public sliderStep: number;\r\n\r\n    /**\r\n     * If true, the input edits negative value: The value is multiplied by -1.\r\n     * E.g. \"3\" days ago => -3.\r\n     */\r\n    public negative: boolean;\r\n\r\n    /**\r\n     * Function that is called when the unit has been changed.\r\n     * Function has the following locals:  unit: the selected unit.\r\n     */\r\n    public onUnitChange: (params: {\r\n      /** Selected unit */\r\n      unit: CalculationRowUnit,\r\n    }) => void;\r\n\r\n    /** Sets the default values in init. */\r\n    public $onInit() {\r\n      super.$onInit();\r\n    }\r\n\r\n    /**\r\n     * Gets or sets the string value that is used in the view.\r\n     * For percent, this is multiplied by 100.\r\n     */\r\n    public get viewValue(): string {\r\n      let valueNum = Numeric.parseNumber(this.value); // Historically, the value may be string e.g. \"3\" instead of 3.\r\n      if (valueNum != null && this.unit === CalculationRowUnit.Percent) {\r\n        valueNum = valueNum * 100;\r\n      }\r\n      if (this.negative && valueNum) {\r\n        valueNum = valueNum * -1;\r\n      }\r\n      return valueNum == null ? null : Numeric.toString(valueNum).replace(\".\", \",\");\r\n    }\r\n    public set viewValue(value: string) {\r\n      let valueNum = Numeric.parseNumber(value);\r\n      if (valueNum != null && this.unit === CalculationRowUnit.Percent) {\r\n        valueNum = valueNum / 100;\r\n      }\r\n      if (this.negative && valueNum) {\r\n        valueNum = valueNum * -1;\r\n      }\r\n      this.value = valueNum;\r\n      this.onChange();\r\n    }\r\n\r\n    /**\r\n     * Gets an indicator string (1-2 characters) for the unit.\r\n     */\r\n    public getUnitIndicator(unit: CalculationRowUnit) {\r\n      return CalcRowsLogic.getUnitIndicator(unit ?? this.unit);\r\n    }\r\n\r\n    /**\r\n     * Changes the unit and calls the onUnitChange function.\r\n     * @param unit New unit.\r\n     */\r\n    public changeUnit(unit: CalculationRowUnit) {\r\n      this.unit = unit;\r\n      if (this.onUnitChange) {\r\n        this.onUnitChange({ unit });\r\n      }\r\n    }\r\n}\r\n","import { Occupation, Occupations, Translations } from \"@salaxy/core\";\r\nimport { SessionService } from \"../../services\";\r\nimport { InputController } from \"./InputController\";\r\n\r\n/**\r\n * Controller behind form controls that select an occupation type.\r\n */\r\nexport class InputOccupationTypeController extends InputController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"SessionService\"];\r\n\r\n  /**\r\n   * One or a list of occupation IDs or a known keyword to define which occupations are shown\r\n   * Supported keywords: 'household' and 'company'\r\n   */\r\n  public defaultList: string;\r\n\r\n  /**\r\n   * Creates a new InputOccupationTypeController\r\n   * @ignore\r\n   */\r\n  constructor(private sessionService: SessionService) {\r\n    super();\r\n  }\r\n\r\n  /** Sets the default values in init. */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Gets the list of occupations in the search field. */\r\n  public getOccupations = (searchString: string): any => {\r\n    let occupations: Occupation[];\r\n    if (!searchString || searchString.length < 2) {\r\n      const defaultList = this.defaultList || (this.sessionService.isInSomeRole(\"household,worker\") ? \"household\" : \"company\");\r\n      occupations = Occupations.getByIds(defaultList);\r\n    } else {\r\n      occupations = Occupations.search(searchString);\r\n    }\r\n\r\n    return occupations.map(item => ({\r\n      value: item.id,\r\n      text: item.label,\r\n      object: item\r\n    }));\r\n  };\r\n\r\n  /**\r\n   * Returns the label for given occupation id.\r\n   * @param occupationId - Id of the occupation.\r\n   */\r\n  public getOccupationLabel(occupationId: string): string {\r\n    for (const occupation of Occupations.getAll(null)) {\r\n      if (occupationId === occupation.id) {\r\n        return occupation.label;\r\n      }\r\n    }\r\n    return occupationId;\r\n  }\r\n\r\n  /** Returns the placeholder text - this control has a default text. */\r\n  public getPlaceholder() {\r\n    return super.getPlaceholder() || Translations.get(\"SALAXY.NG1.InputOccupationType.getPlaceholder\");\r\n  }\r\n}\r\n","// =============================================================================\n// Weekday\n// =============================================================================\nexport var ALL_WEEKDAYS = [\n    'MO',\n    'TU',\n    'WE',\n    'TH',\n    'FR',\n    'SA',\n    'SU',\n];\nvar Weekday = /** @class */ (function () {\n    function Weekday(weekday, n) {\n        if (n === 0)\n            throw new Error(\"Can't create weekday with n == 0\");\n        this.weekday = weekday;\n        this.n = n;\n    }\n    Weekday.fromStr = function (str) {\n        return new Weekday(ALL_WEEKDAYS.indexOf(str));\n    };\n    // __call__ - Cannot call the object directly, do it through\n    // e.g. RRule.TH.nth(-1) instead,\n    Weekday.prototype.nth = function (n) {\n        return this.n === n ? this : new Weekday(this.weekday, n);\n    };\n    // __eq__\n    Weekday.prototype.equals = function (other) {\n        return this.weekday === other.weekday && this.n === other.n;\n    };\n    // __repr__\n    Weekday.prototype.toString = function () {\n        var s = ALL_WEEKDAYS[this.weekday];\n        if (this.n)\n            s = (this.n > 0 ? '+' : '') + String(this.n) + s;\n        return s;\n    };\n    Weekday.prototype.getJsWeekday = function () {\n        return this.weekday === 6 ? 0 : this.weekday + 1;\n    };\n    return Weekday;\n}());\nexport { Weekday };\n//# sourceMappingURL=weekday.js.map","// =============================================================================\n// Helper functions\n// =============================================================================\nimport { ALL_WEEKDAYS } from './weekday';\nexport var isPresent = function (value) {\n    return value !== null && value !== undefined;\n};\nexport var isNumber = function (value) {\n    return typeof value === 'number';\n};\nexport var isWeekdayStr = function (value) {\n    return typeof value === 'string' && ALL_WEEKDAYS.includes(value);\n};\nexport var isArray = Array.isArray;\n/**\n * Simplified version of python's range()\n */\nexport var range = function (start, end) {\n    if (end === void 0) { end = start; }\n    if (arguments.length === 1) {\n        end = start;\n        start = 0;\n    }\n    var rang = [];\n    for (var i = start; i < end; i++)\n        rang.push(i);\n    return rang;\n};\nexport var clone = function (array) {\n    return [].concat(array);\n};\nexport var repeat = function (value, times) {\n    var i = 0;\n    var array = [];\n    if (isArray(value)) {\n        for (; i < times; i++)\n            array[i] = [].concat(value);\n    }\n    else {\n        for (; i < times; i++)\n            array[i] = value;\n    }\n    return array;\n};\nexport var toArray = function (item) {\n    if (isArray(item)) {\n        return item;\n    }\n    return [item];\n};\nexport function padStart(item, targetLength, padString) {\n    if (padString === void 0) { padString = ' '; }\n    var str = String(item);\n    targetLength = targetLength >> 0;\n    if (str.length > targetLength) {\n        return String(str);\n    }\n    targetLength = targetLength - str.length;\n    if (targetLength > padString.length) {\n        padString += repeat(padString, targetLength / padString.length);\n    }\n    return padString.slice(0, targetLength) + String(str);\n}\n/**\n * Python like split\n */\nexport var split = function (str, sep, num) {\n    var splits = str.split(sep);\n    return num\n        ? splits.slice(0, num).concat([splits.slice(num).join(sep)])\n        : splits;\n};\n/**\n * closure/goog/math/math.js:modulo\n * Copyright 2006 The Closure Library Authors.\n * The % operator in JavaScript returns the remainder of a / b, but differs from\n * some other languages in that the result will have the same sign as the\n * dividend. For example, -1 % 8 == -1, whereas in some other languages\n * (such as Python) the result would be 7. This function emulates the more\n * correct modulo behavior, which is useful for certain applications such as\n * calculating an offset index in a circular list.\n *\n * @param {number} a The dividend.\n * @param {number} b The divisor.\n * @return {number} a % b where the result is between 0 and b (either 0 <= x < b\n * or b < x <= 0, depending on the sign of b).\n */\nexport var pymod = function (a, b) {\n    var r = a % b;\n    // If r and b differ in sign, add b to wrap the result to the correct sign.\n    return r * b < 0 ? r + b : r;\n};\n/**\n * @see: <http://docs.python.org/library/functions.html#divmod>\n */\nexport var divmod = function (a, b) {\n    return { div: Math.floor(a / b), mod: pymod(a, b) };\n};\nexport var empty = function (obj) {\n    return !isPresent(obj) || obj.length === 0;\n};\n/**\n * Python-like boolean\n *\n * @return {Boolean} value of an object/primitive, taking into account\n * the fact that in Python an empty list's/tuple's\n * boolean value is False, whereas in JS it's true\n */\nexport var notEmpty = function (obj) {\n    return !empty(obj);\n};\n/**\n * Return true if a value is in an array\n */\nexport var includes = function (arr, val) {\n    return notEmpty(arr) && arr.indexOf(val) !== -1;\n};\n//# sourceMappingURL=helpers.js.map","import { padStart } from './helpers';\nexport var datetime = function (y, m, d, h, i, s) {\n    if (h === void 0) { h = 0; }\n    if (i === void 0) { i = 0; }\n    if (s === void 0) { s = 0; }\n    return new Date(Date.UTC(y, m - 1, d, h, i, s));\n};\n/**\n * General date-related utilities.\n * Also handles several incompatibilities between JavaScript and Python\n *\n */\nexport var MONTH_DAYS = [31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31];\n/**\n * Number of milliseconds of one day\n */\nexport var ONE_DAY = 1000 * 60 * 60 * 24;\n/**\n * @see: <http://docs.python.org/library/datetime.html#datetime.MAXYEAR>\n */\nexport var MAXYEAR = 9999;\n/**\n * Python uses 1-Jan-1 as the base for calculating ordinals but we don't\n * want to confuse the JS engine with milliseconds > Number.MAX_NUMBER,\n * therefore we use 1-Jan-1970 instead\n */\nexport var ORDINAL_BASE = datetime(1970, 1, 1);\n/**\n * Python: MO-SU: 0 - 6\n * JS: SU-SAT 0 - 6\n */\nexport var PY_WEEKDAYS = [6, 0, 1, 2, 3, 4, 5];\n/**\n * py_date.timetuple()[7]\n */\nexport var getYearDay = function (date) {\n    var dateNoTime = new Date(date.getUTCFullYear(), date.getUTCMonth(), date.getUTCDate());\n    return (Math.ceil((dateNoTime.valueOf() - new Date(date.getUTCFullYear(), 0, 1).valueOf()) /\n        ONE_DAY) + 1);\n};\nexport var isLeapYear = function (year) {\n    return (year % 4 === 0 && year % 100 !== 0) || year % 400 === 0;\n};\nexport var isDate = function (value) {\n    return value instanceof Date;\n};\nexport var isValidDate = function (value) {\n    return isDate(value) && !isNaN(value.getTime());\n};\n/**\n * @return {Number} the date's timezone offset in ms\n */\nexport var tzOffset = function (date) {\n    return date.getTimezoneOffset() * 60 * 1000;\n};\n/**\n * @see: <http://www.mcfedries.com/JavaScript/DaysBetween.asp>\n */\nexport var daysBetween = function (date1, date2) {\n    // The number of milliseconds in one day\n    // Convert both dates to milliseconds\n    var date1ms = date1.getTime();\n    var date2ms = date2.getTime();\n    // Calculate the difference in milliseconds\n    var differencems = date1ms - date2ms;\n    // Convert back to days and return\n    return Math.round(differencems / ONE_DAY);\n};\n/**\n * @see: <http://docs.python.org/library/datetime.html#datetime.date.toordinal>\n */\nexport var toOrdinal = function (date) {\n    return daysBetween(date, ORDINAL_BASE);\n};\n/**\n * @see - <http://docs.python.org/library/datetime.html#datetime.date.fromordinal>\n */\nexport var fromOrdinal = function (ordinal) {\n    return new Date(ORDINAL_BASE.getTime() + ordinal * ONE_DAY);\n};\nexport var getMonthDays = function (date) {\n    var month = date.getUTCMonth();\n    return month === 1 && isLeapYear(date.getUTCFullYear())\n        ? 29\n        : MONTH_DAYS[month];\n};\n/**\n * @return {Number} python-like weekday\n */\nexport var getWeekday = function (date) {\n    return PY_WEEKDAYS[date.getUTCDay()];\n};\n/**\n * @see: <http://docs.python.org/library/calendar.html#calendar.monthrange>\n */\nexport var monthRange = function (year, month) {\n    var date = datetime(year, month + 1, 1);\n    return [getWeekday(date), getMonthDays(date)];\n};\n/**\n * @see: <http://docs.python.org/library/datetime.html#datetime.datetime.combine>\n */\nexport var combine = function (date, time) {\n    time = time || date;\n    return new Date(Date.UTC(date.getUTCFullYear(), date.getUTCMonth(), date.getUTCDate(), time.getHours(), time.getMinutes(), time.getSeconds(), time.getMilliseconds()));\n};\nexport var clone = function (date) {\n    var dolly = new Date(date.getTime());\n    return dolly;\n};\nexport var cloneDates = function (dates) {\n    var clones = [];\n    for (var i = 0; i < dates.length; i++) {\n        clones.push(clone(dates[i]));\n    }\n    return clones;\n};\n/**\n * Sorts an array of Date or Time objects\n */\nexport var sort = function (dates) {\n    dates.sort(function (a, b) {\n        return a.getTime() - b.getTime();\n    });\n};\nexport var timeToUntilString = function (time, utc) {\n    if (utc === void 0) { utc = true; }\n    var date = new Date(time);\n    return [\n        padStart(date.getUTCFullYear().toString(), 4, '0'),\n        padStart(date.getUTCMonth() + 1, 2, '0'),\n        padStart(date.getUTCDate(), 2, '0'),\n        'T',\n        padStart(date.getUTCHours(), 2, '0'),\n        padStart(date.getUTCMinutes(), 2, '0'),\n        padStart(date.getUTCSeconds(), 2, '0'),\n        utc ? 'Z' : '',\n    ].join('');\n};\nexport var untilStringToDate = function (until) {\n    var re = /^(\\d{4})(\\d{2})(\\d{2})(T(\\d{2})(\\d{2})(\\d{2})Z?)?$/;\n    var bits = re.exec(until);\n    if (!bits)\n        throw new Error(\"Invalid UNTIL value: \".concat(until));\n    return new Date(Date.UTC(parseInt(bits[1], 10), parseInt(bits[2], 10) - 1, parseInt(bits[3], 10), parseInt(bits[5], 10) || 0, parseInt(bits[6], 10) || 0, parseInt(bits[7], 10) || 0));\n};\nvar dateTZtoISO8601 = function (date, timeZone) {\n    // date format for sv-SE is almost ISO8601\n    var dateStr = date.toLocaleString('sv-SE', { timeZone: timeZone });\n    // '2023-02-07 10:41:36'\n    return dateStr.replace(' ', 'T') + 'Z';\n};\nexport var dateInTimeZone = function (date, timeZone) {\n    var localTimeZone = Intl.DateTimeFormat().resolvedOptions().timeZone;\n    // Date constructor can only reliably parse dates in ISO8601 format\n    var dateInLocalTZ = new Date(dateTZtoISO8601(date, localTimeZone));\n    var dateInTargetTZ = new Date(dateTZtoISO8601(date, timeZone !== null && timeZone !== void 0 ? timeZone : 'UTC'));\n    var tzOffset = dateInTargetTZ.getTime() - dateInLocalTZ.getTime();\n    return new Date(date.getTime() - tzOffset);\n};\n//# sourceMappingURL=dateutil.js.map","/**\n * This class helps us to emulate python's generators, sorta.\n */\nvar IterResult = /** @class */ (function () {\n    function IterResult(method, args) {\n        this.minDate = null;\n        this.maxDate = null;\n        this._result = [];\n        this.total = 0;\n        this.method = method;\n        this.args = args;\n        if (method === 'between') {\n            this.maxDate = args.inc\n                ? args.before\n                : new Date(args.before.getTime() - 1);\n            this.minDate = args.inc ? args.after : new Date(args.after.getTime() + 1);\n        }\n        else if (method === 'before') {\n            this.maxDate = args.inc ? args.dt : new Date(args.dt.getTime() - 1);\n        }\n        else if (method === 'after') {\n            this.minDate = args.inc ? args.dt : new Date(args.dt.getTime() + 1);\n        }\n    }\n    /**\n     * Possibly adds a date into the result.\n     *\n     * @param {Date} date - the date isn't necessarly added to the result\n     * list (if it is too late/too early)\n     * @return {Boolean} true if it makes sense to continue the iteration\n     * false if we're done.\n     */\n    IterResult.prototype.accept = function (date) {\n        ++this.total;\n        var tooEarly = this.minDate && date < this.minDate;\n        var tooLate = this.maxDate && date > this.maxDate;\n        if (this.method === 'between') {\n            if (tooEarly)\n                return true;\n            if (tooLate)\n                return false;\n        }\n        else if (this.method === 'before') {\n            if (tooLate)\n                return false;\n        }\n        else if (this.method === 'after') {\n            if (tooEarly)\n                return true;\n            this.add(date);\n            return false;\n        }\n        return this.add(date);\n    };\n    /**\n     *\n     * @param {Date} date that is part of the result.\n     * @return {Boolean} whether we are interested in more values.\n     */\n    IterResult.prototype.add = function (date) {\n        this._result.push(date);\n        return true;\n    };\n    /**\n     * 'before' and 'after' return only one date, whereas 'all'\n     * and 'between' an array.\n     *\n     * @return {Date,Array?}\n     */\n    IterResult.prototype.getValue = function () {\n        var res = this._result;\n        switch (this.method) {\n            case 'all':\n            case 'between':\n                return res;\n            case 'before':\n            case 'after':\n            default:\n                return (res.length ? res[res.length - 1] : null);\n        }\n    };\n    IterResult.prototype.clone = function () {\n        return new IterResult(this.method, this.args);\n    };\n    return IterResult;\n}());\nexport default IterResult;\n//# sourceMappingURL=iterresult.js.map","/******************************************************************************\nCopyright (c) Microsoft Corporation.\n\nPermission to use, copy, modify, and/or distribute this software for any\npurpose with or without fee is hereby granted.\n\nTHE SOFTWARE IS PROVIDED \"AS IS\" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH\nREGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY\nAND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT,\nINDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM\nLOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR\nOTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR\nPERFORMANCE OF THIS SOFTWARE.\n***************************************************************************** */\n/* global Reflect, Promise, SuppressedError, Symbol */\n\nvar extendStatics = function(d, b) {\n  extendStatics = Object.setPrototypeOf ||\n      ({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||\n      function (d, b) { for (var p in b) if (Object.prototype.hasOwnProperty.call(b, p)) d[p] = b[p]; };\n  return extendStatics(d, b);\n};\n\nexport function __extends(d, b) {\n  if (typeof b !== \"function\" && b !== null)\n      throw new TypeError(\"Class extends value \" + String(b) + \" is not a constructor or null\");\n  extendStatics(d, b);\n  function __() { this.constructor = d; }\n  d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());\n}\n\nexport var __assign = function() {\n  __assign = Object.assign || function __assign(t) {\n      for (var s, i = 1, n = arguments.length; i < n; i++) {\n          s = arguments[i];\n          for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p)) t[p] = s[p];\n      }\n      return t;\n  }\n  return __assign.apply(this, arguments);\n}\n\nexport function __rest(s, e) {\n  var t = {};\n  for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0)\n      t[p] = s[p];\n  if (s != null && typeof Object.getOwnPropertySymbols === \"function\")\n      for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) {\n          if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i]))\n              t[p[i]] = s[p[i]];\n      }\n  return t;\n}\n\nexport function __decorate(decorators, target, key, desc) {\n  var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;\n  if (typeof Reflect === \"object\" && typeof Reflect.decorate === \"function\") r = Reflect.decorate(decorators, target, key, desc);\n  else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;\n  return c > 3 && r && Object.defineProperty(target, key, r), r;\n}\n\nexport function __param(paramIndex, decorator) {\n  return function (target, key) { decorator(target, key, paramIndex); }\n}\n\nexport function __esDecorate(ctor, descriptorIn, decorators, contextIn, initializers, extraInitializers) {\n  function accept(f) { if (f !== void 0 && typeof f !== \"function\") throw new TypeError(\"Function expected\"); return f; }\n  var kind = contextIn.kind, key = kind === \"getter\" ? \"get\" : kind === \"setter\" ? \"set\" : \"value\";\n  var target = !descriptorIn && ctor ? contextIn[\"static\"] ? ctor : ctor.prototype : null;\n  var descriptor = descriptorIn || (target ? Object.getOwnPropertyDescriptor(target, contextIn.name) : {});\n  var _, done = false;\n  for (var i = decorators.length - 1; i >= 0; i--) {\n      var context = {};\n      for (var p in contextIn) context[p] = p === \"access\" ? {} : contextIn[p];\n      for (var p in contextIn.access) context.access[p] = contextIn.access[p];\n      context.addInitializer = function (f) { if (done) throw new TypeError(\"Cannot add initializers after decoration has completed\"); extraInitializers.push(accept(f || null)); };\n      var result = (0, decorators[i])(kind === \"accessor\" ? { get: descriptor.get, set: descriptor.set } : descriptor[key], context);\n      if (kind === \"accessor\") {\n          if (result === void 0) continue;\n          if (result === null || typeof result !== \"object\") throw new TypeError(\"Object expected\");\n          if (_ = accept(result.get)) descriptor.get = _;\n          if (_ = accept(result.set)) descriptor.set = _;\n          if (_ = accept(result.init)) initializers.unshift(_);\n      }\n      else if (_ = accept(result)) {\n          if (kind === \"field\") initializers.unshift(_);\n          else descriptor[key] = _;\n      }\n  }\n  if (target) Object.defineProperty(target, contextIn.name, descriptor);\n  done = true;\n};\n\nexport function __runInitializers(thisArg, initializers, value) {\n  var useValue = arguments.length > 2;\n  for (var i = 0; i < initializers.length; i++) {\n      value = useValue ? initializers[i].call(thisArg, value) : initializers[i].call(thisArg);\n  }\n  return useValue ? value : void 0;\n};\n\nexport function __propKey(x) {\n  return typeof x === \"symbol\" ? x : \"\".concat(x);\n};\n\nexport function __setFunctionName(f, name, prefix) {\n  if (typeof name === \"symbol\") name = name.description ? \"[\".concat(name.description, \"]\") : \"\";\n  return Object.defineProperty(f, \"name\", { configurable: true, value: prefix ? \"\".concat(prefix, \" \", name) : name });\n};\n\nexport function __metadata(metadataKey, metadataValue) {\n  if (typeof Reflect === \"object\" && typeof Reflect.metadata === \"function\") return Reflect.metadata(metadataKey, metadataValue);\n}\n\nexport function __awaiter(thisArg, _arguments, P, generator) {\n  function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }\n  return new (P || (P = Promise))(function (resolve, reject) {\n      function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }\n      function rejected(value) { try { step(generator[\"throw\"](value)); } catch (e) { reject(e); } }\n      function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }\n      step((generator = generator.apply(thisArg, _arguments || [])).next());\n  });\n}\n\nexport function __generator(thisArg, body) {\n  var _ = { label: 0, sent: function() { if (t[0] & 1) throw t[1]; return t[1]; }, trys: [], ops: [] }, f, y, t, g;\n  return g = { next: verb(0), \"throw\": verb(1), \"return\": verb(2) }, typeof Symbol === \"function\" && (g[Symbol.iterator] = function() { return this; }), g;\n  function verb(n) { return function (v) { return step([n, v]); }; }\n  function step(op) {\n      if (f) throw new TypeError(\"Generator is already executing.\");\n      while (g && (g = 0, op[0] && (_ = 0)), _) try {\n          if (f = 1, y && (t = op[0] & 2 ? y[\"return\"] : op[0] ? y[\"throw\"] || ((t = y[\"return\"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) return t;\n          if (y = 0, t) op = [op[0] & 2, t.value];\n          switch (op[0]) {\n              case 0: case 1: t = op; break;\n              case 4: _.label++; return { value: op[1], done: false };\n              case 5: _.label++; y = op[1]; op = [0]; continue;\n              case 7: op = _.ops.pop(); _.trys.pop(); continue;\n              default:\n                  if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) { _ = 0; continue; }\n                  if (op[0] === 3 && (!t || (op[1] > t[0] && op[1] < t[3]))) { _.label = op[1]; break; }\n                  if (op[0] === 6 && _.label < t[1]) { _.label = t[1]; t = op; break; }\n                  if (t && _.label < t[2]) { _.label = t[2]; _.ops.push(op); break; }\n                  if (t[2]) _.ops.pop();\n                  _.trys.pop(); continue;\n          }\n          op = body.call(thisArg, _);\n      } catch (e) { op = [6, e]; y = 0; } finally { f = t = 0; }\n      if (op[0] & 5) throw op[1]; return { value: op[0] ? op[1] : void 0, done: true };\n  }\n}\n\nexport var __createBinding = Object.create ? (function(o, m, k, k2) {\n  if (k2 === undefined) k2 = k;\n  var desc = Object.getOwnPropertyDescriptor(m, k);\n  if (!desc || (\"get\" in desc ? !m.__esModule : desc.writable || desc.configurable)) {\n      desc = { enumerable: true, get: function() { return m[k]; } };\n  }\n  Object.defineProperty(o, k2, desc);\n}) : (function(o, m, k, k2) {\n  if (k2 === undefined) k2 = k;\n  o[k2] = m[k];\n});\n\nexport function __exportStar(m, o) {\n  for (var p in m) if (p !== \"default\" && !Object.prototype.hasOwnProperty.call(o, p)) __createBinding(o, m, p);\n}\n\nexport function __values(o) {\n  var s = typeof Symbol === \"function\" && Symbol.iterator, m = s && o[s], i = 0;\n  if (m) return m.call(o);\n  if (o && typeof o.length === \"number\") return {\n      next: function () {\n          if (o && i >= o.length) o = void 0;\n          return { value: o && o[i++], done: !o };\n      }\n  };\n  throw new TypeError(s ? \"Object is not iterable.\" : \"Symbol.iterator is not defined.\");\n}\n\nexport function __read(o, n) {\n  var m = typeof Symbol === \"function\" && o[Symbol.iterator];\n  if (!m) return o;\n  var i = m.call(o), r, ar = [], e;\n  try {\n      while ((n === void 0 || n-- > 0) && !(r = i.next()).done) ar.push(r.value);\n  }\n  catch (error) { e = { error: error }; }\n  finally {\n      try {\n          if (r && !r.done && (m = i[\"return\"])) m.call(i);\n      }\n      finally { if (e) throw e.error; }\n  }\n  return ar;\n}\n\n/** @deprecated */\nexport function __spread() {\n  for (var ar = [], i = 0; i < arguments.length; i++)\n      ar = ar.concat(__read(arguments[i]));\n  return ar;\n}\n\n/** @deprecated */\nexport function __spreadArrays() {\n  for (var s = 0, i = 0, il = arguments.length; i < il; i++) s += arguments[i].length;\n  for (var r = Array(s), k = 0, i = 0; i < il; i++)\n      for (var a = arguments[i], j = 0, jl = a.length; j < jl; j++, k++)\n          r[k] = a[j];\n  return r;\n}\n\nexport function __spreadArray(to, from, pack) {\n  if (pack || arguments.length === 2) for (var i = 0, l = from.length, ar; i < l; i++) {\n      if (ar || !(i in from)) {\n          if (!ar) ar = Array.prototype.slice.call(from, 0, i);\n          ar[i] = from[i];\n      }\n  }\n  return to.concat(ar || Array.prototype.slice.call(from));\n}\n\nexport function __await(v) {\n  return this instanceof __await ? (this.v = v, this) : new __await(v);\n}\n\nexport function __asyncGenerator(thisArg, _arguments, generator) {\n  if (!Symbol.asyncIterator) throw new TypeError(\"Symbol.asyncIterator is not defined.\");\n  var g = generator.apply(thisArg, _arguments || []), i, q = [];\n  return i = {}, verb(\"next\"), verb(\"throw\"), verb(\"return\"), i[Symbol.asyncIterator] = function () { return this; }, i;\n  function verb(n) { if (g[n]) i[n] = function (v) { return new Promise(function (a, b) { q.push([n, v, a, b]) > 1 || resume(n, v); }); }; }\n  function resume(n, v) { try { step(g[n](v)); } catch (e) { settle(q[0][3], e); } }\n  function step(r) { r.value instanceof __await ? Promise.resolve(r.value.v).then(fulfill, reject) : settle(q[0][2], r); }\n  function fulfill(value) { resume(\"next\", value); }\n  function reject(value) { resume(\"throw\", value); }\n  function settle(f, v) { if (f(v), q.shift(), q.length) resume(q[0][0], q[0][1]); }\n}\n\nexport function __asyncDelegator(o) {\n  var i, p;\n  return i = {}, verb(\"next\"), verb(\"throw\", function (e) { throw e; }), verb(\"return\"), i[Symbol.iterator] = function () { return this; }, i;\n  function verb(n, f) { i[n] = o[n] ? function (v) { return (p = !p) ? { value: __await(o[n](v)), done: false } : f ? f(v) : v; } : f; }\n}\n\nexport function __asyncValues(o) {\n  if (!Symbol.asyncIterator) throw new TypeError(\"Symbol.asyncIterator is not defined.\");\n  var m = o[Symbol.asyncIterator], i;\n  return m ? m.call(o) : (o = typeof __values === \"function\" ? __values(o) : o[Symbol.iterator](), i = {}, verb(\"next\"), verb(\"throw\"), verb(\"return\"), i[Symbol.asyncIterator] = function () { return this; }, i);\n  function verb(n) { i[n] = o[n] && function (v) { return new Promise(function (resolve, reject) { v = o[n](v), settle(resolve, reject, v.done, v.value); }); }; }\n  function settle(resolve, reject, d, v) { Promise.resolve(v).then(function(v) { resolve({ value: v, done: d }); }, reject); }\n}\n\nexport function __makeTemplateObject(cooked, raw) {\n  if (Object.defineProperty) { Object.defineProperty(cooked, \"raw\", { value: raw }); } else { cooked.raw = raw; }\n  return cooked;\n};\n\nvar __setModuleDefault = Object.create ? (function(o, v) {\n  Object.defineProperty(o, \"default\", { enumerable: true, value: v });\n}) : function(o, v) {\n  o[\"default\"] = v;\n};\n\nexport function __importStar(mod) {\n  if (mod && mod.__esModule) return mod;\n  var result = {};\n  if (mod != null) for (var k in mod) if (k !== \"default\" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);\n  __setModuleDefault(result, mod);\n  return result;\n}\n\nexport function __importDefault(mod) {\n  return (mod && mod.__esModule) ? mod : { default: mod };\n}\n\nexport function __classPrivateFieldGet(receiver, state, kind, f) {\n  if (kind === \"a\" && !f) throw new TypeError(\"Private accessor was defined without a getter\");\n  if (typeof state === \"function\" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError(\"Cannot read private member from an object whose class did not declare it\");\n  return kind === \"m\" ? f : kind === \"a\" ? f.call(receiver) : f ? f.value : state.get(receiver);\n}\n\nexport function __classPrivateFieldSet(receiver, state, value, kind, f) {\n  if (kind === \"m\") throw new TypeError(\"Private method is not writable\");\n  if (kind === \"a\" && !f) throw new TypeError(\"Private accessor was defined without a setter\");\n  if (typeof state === \"function\" ? receiver !== state || !f : !state.has(receiver)) throw new TypeError(\"Cannot write private member to an object whose class did not declare it\");\n  return (kind === \"a\" ? f.call(receiver, value) : f ? f.value = value : state.set(receiver, value)), value;\n}\n\nexport function __classPrivateFieldIn(state, receiver) {\n  if (receiver === null || (typeof receiver !== \"object\" && typeof receiver !== \"function\")) throw new TypeError(\"Cannot use 'in' operator on non-object\");\n  return typeof state === \"function\" ? receiver === state : state.has(receiver);\n}\n\nexport function __addDisposableResource(env, value, async) {\n  if (value !== null && value !== void 0) {\n    if (typeof value !== \"object\" && typeof value !== \"function\") throw new TypeError(\"Object expected.\");\n    var dispose;\n    if (async) {\n        if (!Symbol.asyncDispose) throw new TypeError(\"Symbol.asyncDispose is not defined.\");\n        dispose = value[Symbol.asyncDispose];\n    }\n    if (dispose === void 0) {\n        if (!Symbol.dispose) throw new TypeError(\"Symbol.dispose is not defined.\");\n        dispose = value[Symbol.dispose];\n    }\n    if (typeof dispose !== \"function\") throw new TypeError(\"Object not disposable.\");\n    env.stack.push({ value: value, dispose: dispose, async: async });\n  }\n  else if (async) {\n    env.stack.push({ async: true });\n  }\n  return value;\n}\n\nvar _SuppressedError = typeof SuppressedError === \"function\" ? SuppressedError : function (error, suppressed, message) {\n  var e = new Error(message);\n  return e.name = \"SuppressedError\", e.error = error, e.suppressed = suppressed, e;\n};\n\nexport function __disposeResources(env) {\n  function fail(e) {\n    env.error = env.hasError ? new _SuppressedError(e, env.error, \"An error was suppressed during disposal.\") : e;\n    env.hasError = true;\n  }\n  function next() {\n    while (env.stack.length) {\n      var rec = env.stack.pop();\n      try {\n        var result = rec.dispose && rec.dispose.call(rec.value);\n        if (rec.async) return Promise.resolve(result).then(next, function(e) { fail(e); return next(); });\n      }\n      catch (e) {\n          fail(e);\n      }\n    }\n    if (env.hasError) throw env.error;\n  }\n  return next();\n}\n\nexport default {\n  __extends,\n  __assign,\n  __rest,\n  __decorate,\n  __param,\n  __metadata,\n  __awaiter,\n  __generator,\n  __createBinding,\n  __exportStar,\n  __values,\n  __read,\n  __spread,\n  __spreadArrays,\n  __spreadArray,\n  __await,\n  __asyncGenerator,\n  __asyncDelegator,\n  __asyncValues,\n  __makeTemplateObject,\n  __importStar,\n  __importDefault,\n  __classPrivateFieldGet,\n  __classPrivateFieldSet,\n  __classPrivateFieldIn,\n  __addDisposableResource,\n  __disposeResources,\n};\n","import { __extends } from \"tslib\";\nimport IterResult from './iterresult';\n/**\n * IterResult subclass that calls a callback function on each add,\n * and stops iterating when the callback returns false.\n */\nvar CallbackIterResult = /** @class */ (function (_super) {\n    __extends(CallbackIterResult, _super);\n    function CallbackIterResult(method, args, iterator) {\n        var _this = _super.call(this, method, args) || this;\n        _this.iterator = iterator;\n        return _this;\n    }\n    CallbackIterResult.prototype.add = function (date) {\n        if (this.iterator(date, this._result.length)) {\n            this._result.push(date);\n            return true;\n        }\n        return false;\n    };\n    return CallbackIterResult;\n}(IterResult));\nexport default CallbackIterResult;\n//# sourceMappingURL=callbackiterresult.js.map","// =============================================================================\n// i18n\n// =============================================================================\nvar ENGLISH = {\n    dayNames: [\n        'Sunday',\n        'Monday',\n        'Tuesday',\n        'Wednesday',\n        'Thursday',\n        'Friday',\n        'Saturday',\n    ],\n    monthNames: [\n        'January',\n        'February',\n        'March',\n        'April',\n        'May',\n        'June',\n        'July',\n        'August',\n        'September',\n        'October',\n        'November',\n        'December',\n    ],\n    tokens: {\n        SKIP: /^[ \\r\\n\\t]+|^\\.$/,\n        number: /^[1-9][0-9]*/,\n        numberAsText: /^(one|two|three)/i,\n        every: /^every/i,\n        'day(s)': /^days?/i,\n        'weekday(s)': /^weekdays?/i,\n        'week(s)': /^weeks?/i,\n        'hour(s)': /^hours?/i,\n        'minute(s)': /^minutes?/i,\n        'month(s)': /^months?/i,\n        'year(s)': /^years?/i,\n        on: /^(on|in)/i,\n        at: /^(at)/i,\n        the: /^the/i,\n        first: /^first/i,\n        second: /^second/i,\n        third: /^third/i,\n        nth: /^([1-9][0-9]*)(\\.|th|nd|rd|st)/i,\n        last: /^last/i,\n        for: /^for/i,\n        'time(s)': /^times?/i,\n        until: /^(un)?til/i,\n        monday: /^mo(n(day)?)?/i,\n        tuesday: /^tu(e(s(day)?)?)?/i,\n        wednesday: /^we(d(n(esday)?)?)?/i,\n        thursday: /^th(u(r(sday)?)?)?/i,\n        friday: /^fr(i(day)?)?/i,\n        saturday: /^sa(t(urday)?)?/i,\n        sunday: /^su(n(day)?)?/i,\n        january: /^jan(uary)?/i,\n        february: /^feb(ruary)?/i,\n        march: /^mar(ch)?/i,\n        april: /^apr(il)?/i,\n        may: /^may/i,\n        june: /^june?/i,\n        july: /^july?/i,\n        august: /^aug(ust)?/i,\n        september: /^sep(t(ember)?)?/i,\n        october: /^oct(ober)?/i,\n        november: /^nov(ember)?/i,\n        december: /^dec(ember)?/i,\n        comma: /^(,\\s*|(and|or)\\s*)+/i,\n    },\n};\nexport default ENGLISH;\n//# sourceMappingURL=i18n.js.map","import ENGLISH from './i18n';\nimport { RRule } from '../rrule';\nimport { isArray, isNumber, isPresent } from '../helpers';\n// =============================================================================\n// Helper functions\n// =============================================================================\n/**\n * Return true if a value is in an array\n */\nvar contains = function (arr, val) {\n    return arr.indexOf(val) !== -1;\n};\nvar defaultGetText = function (id) { return id.toString(); };\nvar defaultDateFormatter = function (year, month, day) { return \"\".concat(month, \" \").concat(day, \", \").concat(year); };\n/**\n *\n * @param {RRule} rrule\n * Optional:\n * @param {Function} gettext function\n * @param {Object} language definition\n * @constructor\n */\nvar ToText = /** @class */ (function () {\n    function ToText(rrule, gettext, language, dateFormatter) {\n        if (gettext === void 0) { gettext = defaultGetText; }\n        if (language === void 0) { language = ENGLISH; }\n        if (dateFormatter === void 0) { dateFormatter = defaultDateFormatter; }\n        this.text = [];\n        this.language = language || ENGLISH;\n        this.gettext = gettext;\n        this.dateFormatter = dateFormatter;\n        this.rrule = rrule;\n        this.options = rrule.options;\n        this.origOptions = rrule.origOptions;\n        if (this.origOptions.bymonthday) {\n            var bymonthday = [].concat(this.options.bymonthday);\n            var bynmonthday = [].concat(this.options.bynmonthday);\n            bymonthday.sort(function (a, b) { return a - b; });\n            bynmonthday.sort(function (a, b) { return b - a; });\n            // 1, 2, 3, .., -5, -4, -3, ..\n            this.bymonthday = bymonthday.concat(bynmonthday);\n            if (!this.bymonthday.length)\n                this.bymonthday = null;\n        }\n        if (isPresent(this.origOptions.byweekday)) {\n            var byweekday = !isArray(this.origOptions.byweekday)\n                ? [this.origOptions.byweekday]\n                : this.origOptions.byweekday;\n            var days = String(byweekday);\n            this.byweekday = {\n                allWeeks: byweekday.filter(function (weekday) {\n                    return !weekday.n;\n                }),\n                someWeeks: byweekday.filter(function (weekday) {\n                    return Boolean(weekday.n);\n                }),\n                isWeekdays: days.indexOf('MO') !== -1 &&\n                    days.indexOf('TU') !== -1 &&\n                    days.indexOf('WE') !== -1 &&\n                    days.indexOf('TH') !== -1 &&\n                    days.indexOf('FR') !== -1 &&\n                    days.indexOf('SA') === -1 &&\n                    days.indexOf('SU') === -1,\n                isEveryDay: days.indexOf('MO') !== -1 &&\n                    days.indexOf('TU') !== -1 &&\n                    days.indexOf('WE') !== -1 &&\n                    days.indexOf('TH') !== -1 &&\n                    days.indexOf('FR') !== -1 &&\n                    days.indexOf('SA') !== -1 &&\n                    days.indexOf('SU') !== -1,\n            };\n            var sortWeekDays = function (a, b) {\n                return a.weekday - b.weekday;\n            };\n            this.byweekday.allWeeks.sort(sortWeekDays);\n            this.byweekday.someWeeks.sort(sortWeekDays);\n            if (!this.byweekday.allWeeks.length)\n                this.byweekday.allWeeks = null;\n            if (!this.byweekday.someWeeks.length)\n                this.byweekday.someWeeks = null;\n        }\n        else {\n            this.byweekday = null;\n        }\n    }\n    /**\n     * Test whether the rrule can be fully converted to text.\n     *\n     * @param {RRule} rrule\n     * @return {Boolean}\n     */\n    ToText.isFullyConvertible = function (rrule) {\n        var canConvert = true;\n        if (!(rrule.options.freq in ToText.IMPLEMENTED))\n            return false;\n        if (rrule.origOptions.until && rrule.origOptions.count)\n            return false;\n        for (var key in rrule.origOptions) {\n            if (contains(['dtstart', 'tzid', 'wkst', 'freq'], key))\n                return true;\n            if (!contains(ToText.IMPLEMENTED[rrule.options.freq], key))\n                return false;\n        }\n        return canConvert;\n    };\n    ToText.prototype.isFullyConvertible = function () {\n        return ToText.isFullyConvertible(this.rrule);\n    };\n    /**\n     * Perform the conversion. Only some of the frequencies are supported.\n     * If some of the rrule's options aren't supported, they'll\n     * be omitted from the output an \"(~ approximate)\" will be appended.\n     *\n     * @return {*}\n     */\n    ToText.prototype.toString = function () {\n        var gettext = this.gettext;\n        if (!(this.options.freq in ToText.IMPLEMENTED)) {\n            return gettext('RRule error: Unable to fully convert this rrule to text');\n        }\n        this.text = [gettext('every')];\n        // eslint-disable-next-line @typescript-eslint/ban-ts-comment\n        // @ts-ignore\n        this[RRule.FREQUENCIES[this.options.freq]]();\n        if (this.options.until) {\n            this.add(gettext('until'));\n            var until = this.options.until;\n            this.add(this.dateFormatter(until.getUTCFullYear(), this.language.monthNames[until.getUTCMonth()], until.getUTCDate()));\n        }\n        else if (this.options.count) {\n            this.add(gettext('for'))\n                .add(this.options.count.toString())\n                .add(this.plural(this.options.count) ? gettext('times') : gettext('time'));\n        }\n        if (!this.isFullyConvertible())\n            this.add(gettext('(~ approximate)'));\n        return this.text.join('');\n    };\n    ToText.prototype.HOURLY = function () {\n        var gettext = this.gettext;\n        if (this.options.interval !== 1)\n            this.add(this.options.interval.toString());\n        this.add(this.plural(this.options.interval) ? gettext('hours') : gettext('hour'));\n    };\n    ToText.prototype.MINUTELY = function () {\n        var gettext = this.gettext;\n        if (this.options.interval !== 1)\n            this.add(this.options.interval.toString());\n        this.add(this.plural(this.options.interval)\n            ? gettext('minutes')\n            : gettext('minute'));\n    };\n    ToText.prototype.DAILY = function () {\n        var gettext = this.gettext;\n        if (this.options.interval !== 1)\n            this.add(this.options.interval.toString());\n        if (this.byweekday && this.byweekday.isWeekdays) {\n            this.add(this.plural(this.options.interval)\n                ? gettext('weekdays')\n                : gettext('weekday'));\n        }\n        else {\n            this.add(this.plural(this.options.interval) ? gettext('days') : gettext('day'));\n        }\n        if (this.origOptions.bymonth) {\n            this.add(gettext('in'));\n            this._bymonth();\n        }\n        if (this.bymonthday) {\n            this._bymonthday();\n        }\n        else if (this.byweekday) {\n            this._byweekday();\n        }\n        else if (this.origOptions.byhour) {\n            this._byhour();\n        }\n    };\n    ToText.prototype.WEEKLY = function () {\n        var gettext = this.gettext;\n        if (this.options.interval !== 1) {\n            this.add(this.options.interval.toString()).add(this.plural(this.options.interval) ? gettext('weeks') : gettext('week'));\n        }\n        if (this.byweekday && this.byweekday.isWeekdays) {\n            if (this.options.interval === 1) {\n                this.add(this.plural(this.options.interval)\n                    ? gettext('weekdays')\n                    : gettext('weekday'));\n            }\n            else {\n                this.add(gettext('on')).add(gettext('weekdays'));\n            }\n        }\n        else if (this.byweekday && this.byweekday.isEveryDay) {\n            this.add(this.plural(this.options.interval) ? gettext('days') : gettext('day'));\n        }\n        else {\n            if (this.options.interval === 1)\n                this.add(gettext('week'));\n            if (this.origOptions.bymonth) {\n                this.add(gettext('in'));\n                this._bymonth();\n            }\n            if (this.bymonthday) {\n                this._bymonthday();\n            }\n            else if (this.byweekday) {\n                this._byweekday();\n            }\n            if (this.origOptions.byhour) {\n                this._byhour();\n            }\n        }\n    };\n    ToText.prototype.MONTHLY = function () {\n        var gettext = this.gettext;\n        if (this.origOptions.bymonth) {\n            if (this.options.interval !== 1) {\n                this.add(this.options.interval.toString()).add(gettext('months'));\n                if (this.plural(this.options.interval))\n                    this.add(gettext('in'));\n            }\n            else {\n                // this.add(gettext('MONTH'))\n            }\n            this._bymonth();\n        }\n        else {\n            if (this.options.interval !== 1) {\n                this.add(this.options.interval.toString());\n            }\n            this.add(this.plural(this.options.interval)\n                ? gettext('months')\n                : gettext('month'));\n        }\n        if (this.bymonthday) {\n            this._bymonthday();\n        }\n        else if (this.byweekday && this.byweekday.isWeekdays) {\n            this.add(gettext('on')).add(gettext('weekdays'));\n        }\n        else if (this.byweekday) {\n            this._byweekday();\n        }\n    };\n    ToText.prototype.YEARLY = function () {\n        var gettext = this.gettext;\n        if (this.origOptions.bymonth) {\n            if (this.options.interval !== 1) {\n                this.add(this.options.interval.toString());\n                this.add(gettext('years'));\n            }\n            else {\n                // this.add(gettext('YEAR'))\n            }\n            this._bymonth();\n        }\n        else {\n            if (this.options.interval !== 1) {\n                this.add(this.options.interval.toString());\n            }\n            this.add(this.plural(this.options.interval) ? gettext('years') : gettext('year'));\n        }\n        if (this.bymonthday) {\n            this._bymonthday();\n        }\n        else if (this.byweekday) {\n            this._byweekday();\n        }\n        if (this.options.byyearday) {\n            this.add(gettext('on the'))\n                .add(this.list(this.options.byyearday, this.nth, gettext('and')))\n                .add(gettext('day'));\n        }\n        if (this.options.byweekno) {\n            this.add(gettext('in'))\n                .add(this.plural(this.options.byweekno.length)\n                ? gettext('weeks')\n                : gettext('week'))\n                .add(this.list(this.options.byweekno, undefined, gettext('and')));\n        }\n    };\n    ToText.prototype._bymonthday = function () {\n        var gettext = this.gettext;\n        if (this.byweekday && this.byweekday.allWeeks) {\n            this.add(gettext('on'))\n                .add(this.list(this.byweekday.allWeeks, this.weekdaytext, gettext('or')))\n                .add(gettext('the'))\n                .add(this.list(this.bymonthday, this.nth, gettext('or')));\n        }\n        else {\n            this.add(gettext('on the')).add(this.list(this.bymonthday, this.nth, gettext('and')));\n        }\n        // this.add(gettext('DAY'))\n    };\n    ToText.prototype._byweekday = function () {\n        var gettext = this.gettext;\n        if (this.byweekday.allWeeks && !this.byweekday.isWeekdays) {\n            this.add(gettext('on')).add(this.list(this.byweekday.allWeeks, this.weekdaytext));\n        }\n        if (this.byweekday.someWeeks) {\n            if (this.byweekday.allWeeks)\n                this.add(gettext('and'));\n            this.add(gettext('on the')).add(this.list(this.byweekday.someWeeks, this.weekdaytext, gettext('and')));\n        }\n    };\n    ToText.prototype._byhour = function () {\n        var gettext = this.gettext;\n        this.add(gettext('at')).add(this.list(this.origOptions.byhour, undefined, gettext('and')));\n    };\n    ToText.prototype._bymonth = function () {\n        this.add(this.list(this.options.bymonth, this.monthtext, this.gettext('and')));\n    };\n    ToText.prototype.nth = function (n) {\n        n = parseInt(n.toString(), 10);\n        var nth;\n        var gettext = this.gettext;\n        if (n === -1)\n            return gettext('last');\n        var npos = Math.abs(n);\n        switch (npos) {\n            case 1:\n            case 21:\n            case 31:\n                nth = npos + gettext('st');\n                break;\n            case 2:\n            case 22:\n                nth = npos + gettext('nd');\n                break;\n            case 3:\n            case 23:\n                nth = npos + gettext('rd');\n                break;\n            default:\n                nth = npos + gettext('th');\n        }\n        return n < 0 ? nth + ' ' + gettext('last') : nth;\n    };\n    ToText.prototype.monthtext = function (m) {\n        return this.language.monthNames[m - 1];\n    };\n    ToText.prototype.weekdaytext = function (wday) {\n        var weekday = isNumber(wday) ? (wday + 1) % 7 : wday.getJsWeekday();\n        return ((wday.n ? this.nth(wday.n) + ' ' : '') +\n            this.language.dayNames[weekday]);\n    };\n    ToText.prototype.plural = function (n) {\n        return n % 100 !== 1;\n    };\n    ToText.prototype.add = function (s) {\n        this.text.push(' ');\n        this.text.push(s);\n        return this;\n    };\n    ToText.prototype.list = function (arr, callback, finalDelim, delim) {\n        var _this = this;\n        if (delim === void 0) { delim = ','; }\n        if (!isArray(arr)) {\n            arr = [arr];\n        }\n        var delimJoin = function (array, delimiter, finalDelimiter) {\n            var list = '';\n            for (var i = 0; i < array.length; i++) {\n                if (i !== 0) {\n                    if (i === array.length - 1) {\n                        list += ' ' + finalDelimiter + ' ';\n                    }\n                    else {\n                        list += delimiter + ' ';\n                    }\n                }\n                list += array[i];\n            }\n            return list;\n        };\n        callback =\n            callback ||\n                function (o) {\n                    return o.toString();\n                };\n        var realCallback = function (arg) {\n            return callback && callback.call(_this, arg);\n        };\n        if (finalDelim) {\n            return delimJoin(arr.map(realCallback), delim, finalDelim);\n        }\n        else {\n            return arr.map(realCallback).join(delim + ' ');\n        }\n    };\n    return ToText;\n}());\nexport default ToText;\n//# sourceMappingURL=totext.js.map","import ENGLISH from './i18n';\nimport { RRule } from '../rrule';\n// =============================================================================\n// Parser\n// =============================================================================\nvar Parser = /** @class */ (function () {\n    function Parser(rules) {\n        this.done = true;\n        this.rules = rules;\n    }\n    Parser.prototype.start = function (text) {\n        this.text = text;\n        this.done = false;\n        return this.nextSymbol();\n    };\n    Parser.prototype.isDone = function () {\n        return this.done && this.symbol === null;\n    };\n    Parser.prototype.nextSymbol = function () {\n        var best;\n        var bestSymbol;\n        this.symbol = null;\n        this.value = null;\n        do {\n            if (this.done)\n                return false;\n            var rule = void 0;\n            best = null;\n            for (var name_1 in this.rules) {\n                rule = this.rules[name_1];\n                var match = rule.exec(this.text);\n                if (match) {\n                    if (best === null || match[0].length > best[0].length) {\n                        best = match;\n                        bestSymbol = name_1;\n                    }\n                }\n            }\n            if (best != null) {\n                this.text = this.text.substr(best[0].length);\n                if (this.text === '')\n                    this.done = true;\n            }\n            if (best == null) {\n                this.done = true;\n                this.symbol = null;\n                this.value = null;\n                return;\n            }\n        } while (bestSymbol === 'SKIP');\n        this.symbol = bestSymbol;\n        this.value = best;\n        return true;\n    };\n    Parser.prototype.accept = function (name) {\n        if (this.symbol === name) {\n            if (this.value) {\n                var v = this.value;\n                this.nextSymbol();\n                return v;\n            }\n            this.nextSymbol();\n            return true;\n        }\n        return false;\n    };\n    Parser.prototype.acceptNumber = function () {\n        return this.accept('number');\n    };\n    Parser.prototype.expect = function (name) {\n        if (this.accept(name))\n            return true;\n        throw new Error('expected ' + name + ' but found ' + this.symbol);\n    };\n    return Parser;\n}());\nexport default function parseText(text, language) {\n    if (language === void 0) { language = ENGLISH; }\n    var options = {};\n    var ttr = new Parser(language.tokens);\n    if (!ttr.start(text))\n        return null;\n    S();\n    return options;\n    function S() {\n        // every [n]\n        ttr.expect('every');\n        var n = ttr.acceptNumber();\n        if (n)\n            options.interval = parseInt(n[0], 10);\n        if (ttr.isDone())\n            throw new Error('Unexpected end');\n        switch (ttr.symbol) {\n            case 'day(s)':\n                options.freq = RRule.DAILY;\n                if (ttr.nextSymbol()) {\n                    AT();\n                    F();\n                }\n                break;\n            // FIXME Note: every 2 weekdays != every two weeks on weekdays.\n            // DAILY on weekdays is not a valid rule\n            case 'weekday(s)':\n                options.freq = RRule.WEEKLY;\n                options.byweekday = [RRule.MO, RRule.TU, RRule.WE, RRule.TH, RRule.FR];\n                ttr.nextSymbol();\n                AT();\n                F();\n                break;\n            case 'week(s)':\n                options.freq = RRule.WEEKLY;\n                if (ttr.nextSymbol()) {\n                    ON();\n                    AT();\n                    F();\n                }\n                break;\n            case 'hour(s)':\n                options.freq = RRule.HOURLY;\n                if (ttr.nextSymbol()) {\n                    ON();\n                    F();\n                }\n                break;\n            case 'minute(s)':\n                options.freq = RRule.MINUTELY;\n                if (ttr.nextSymbol()) {\n                    ON();\n                    F();\n                }\n                break;\n            case 'month(s)':\n                options.freq = RRule.MONTHLY;\n                if (ttr.nextSymbol()) {\n                    ON();\n                    F();\n                }\n                break;\n            case 'year(s)':\n                options.freq = RRule.YEARLY;\n                if (ttr.nextSymbol()) {\n                    ON();\n                    F();\n                }\n                break;\n            case 'monday':\n            case 'tuesday':\n            case 'wednesday':\n            case 'thursday':\n            case 'friday':\n            case 'saturday':\n            case 'sunday':\n                options.freq = RRule.WEEKLY;\n                var key = ttr.symbol\n                    .substr(0, 2)\n                    .toUpperCase();\n                options.byweekday = [RRule[key]];\n                if (!ttr.nextSymbol())\n                    return;\n                // TODO check for duplicates\n                while (ttr.accept('comma')) {\n                    if (ttr.isDone())\n                        throw new Error('Unexpected end');\n                    var wkd = decodeWKD();\n                    if (!wkd) {\n                        throw new Error('Unexpected symbol ' + ttr.symbol + ', expected weekday');\n                    }\n                    options.byweekday.push(RRule[wkd]);\n                    ttr.nextSymbol();\n                }\n                AT();\n                MDAYs();\n                F();\n                break;\n            case 'january':\n            case 'february':\n            case 'march':\n            case 'april':\n            case 'may':\n            case 'june':\n            case 'july':\n            case 'august':\n            case 'september':\n            case 'october':\n            case 'november':\n            case 'december':\n                options.freq = RRule.YEARLY;\n                options.bymonth = [decodeM()];\n                if (!ttr.nextSymbol())\n                    return;\n                // TODO check for duplicates\n                while (ttr.accept('comma')) {\n                    if (ttr.isDone())\n                        throw new Error('Unexpected end');\n                    var m = decodeM();\n                    if (!m) {\n                        throw new Error('Unexpected symbol ' + ttr.symbol + ', expected month');\n                    }\n                    options.bymonth.push(m);\n                    ttr.nextSymbol();\n                }\n                ON();\n                F();\n                break;\n            default:\n                throw new Error('Unknown symbol');\n        }\n    }\n    function ON() {\n        var on = ttr.accept('on');\n        var the = ttr.accept('the');\n        if (!(on || the))\n            return;\n        do {\n            var nth = decodeNTH();\n            var wkd = decodeWKD();\n            var m = decodeM();\n            // nth <weekday> | <weekday>\n            if (nth) {\n                // ttr.nextSymbol()\n                if (wkd) {\n                    ttr.nextSymbol();\n                    if (!options.byweekday)\n                        options.byweekday = [];\n                    options.byweekday.push(RRule[wkd].nth(nth));\n                }\n                else {\n                    if (!options.bymonthday)\n                        options.bymonthday = [];\n                    options.bymonthday.push(nth);\n                    ttr.accept('day(s)');\n                }\n                // <weekday>\n            }\n            else if (wkd) {\n                ttr.nextSymbol();\n                if (!options.byweekday)\n                    options.byweekday = [];\n                options.byweekday.push(RRule[wkd]);\n            }\n            else if (ttr.symbol === 'weekday(s)') {\n                ttr.nextSymbol();\n                if (!options.byweekday) {\n                    options.byweekday = [RRule.MO, RRule.TU, RRule.WE, RRule.TH, RRule.FR];\n                }\n            }\n            else if (ttr.symbol === 'week(s)') {\n                ttr.nextSymbol();\n                var n = ttr.acceptNumber();\n                if (!n) {\n                    throw new Error('Unexpected symbol ' + ttr.symbol + ', expected week number');\n                }\n                options.byweekno = [parseInt(n[0], 10)];\n                while (ttr.accept('comma')) {\n                    n = ttr.acceptNumber();\n                    if (!n) {\n                        throw new Error('Unexpected symbol ' + ttr.symbol + '; expected monthday');\n                    }\n                    options.byweekno.push(parseInt(n[0], 10));\n                }\n            }\n            else if (m) {\n                ttr.nextSymbol();\n                if (!options.bymonth)\n                    options.bymonth = [];\n                options.bymonth.push(m);\n            }\n            else {\n                return;\n            }\n        } while (ttr.accept('comma') || ttr.accept('the') || ttr.accept('on'));\n    }\n    function AT() {\n        var at = ttr.accept('at');\n        if (!at)\n            return;\n        do {\n            var n = ttr.acceptNumber();\n            if (!n) {\n                throw new Error('Unexpected symbol ' + ttr.symbol + ', expected hour');\n            }\n            options.byhour = [parseInt(n[0], 10)];\n            while (ttr.accept('comma')) {\n                n = ttr.acceptNumber();\n                if (!n) {\n                    throw new Error('Unexpected symbol ' + ttr.symbol + '; expected hour');\n                }\n                options.byhour.push(parseInt(n[0], 10));\n            }\n        } while (ttr.accept('comma') || ttr.accept('at'));\n    }\n    function decodeM() {\n        switch (ttr.symbol) {\n            case 'january':\n                return 1;\n            case 'february':\n                return 2;\n            case 'march':\n                return 3;\n            case 'april':\n                return 4;\n            case 'may':\n                return 5;\n            case 'june':\n                return 6;\n            case 'july':\n                return 7;\n            case 'august':\n                return 8;\n            case 'september':\n                return 9;\n            case 'october':\n                return 10;\n            case 'november':\n                return 11;\n            case 'december':\n                return 12;\n            default:\n                return false;\n        }\n    }\n    function decodeWKD() {\n        switch (ttr.symbol) {\n            case 'monday':\n            case 'tuesday':\n            case 'wednesday':\n            case 'thursday':\n            case 'friday':\n            case 'saturday':\n            case 'sunday':\n                return ttr.symbol.substr(0, 2).toUpperCase();\n            default:\n                return false;\n        }\n    }\n    function decodeNTH() {\n        switch (ttr.symbol) {\n            case 'last':\n                ttr.nextSymbol();\n                return -1;\n            case 'first':\n                ttr.nextSymbol();\n                return 1;\n            case 'second':\n                ttr.nextSymbol();\n                return ttr.accept('last') ? -2 : 2;\n            case 'third':\n                ttr.nextSymbol();\n                return ttr.accept('last') ? -3 : 3;\n            case 'nth':\n                var v = parseInt(ttr.value[1], 10);\n                if (v < -366 || v > 366)\n                    throw new Error('Nth out of range: ' + v);\n                ttr.nextSymbol();\n                return ttr.accept('last') ? -v : v;\n            default:\n                return false;\n        }\n    }\n    function MDAYs() {\n        ttr.accept('on');\n        ttr.accept('the');\n        var nth = decodeNTH();\n        if (!nth)\n            return;\n        options.bymonthday = [nth];\n        ttr.nextSymbol();\n        while (ttr.accept('comma')) {\n            nth = decodeNTH();\n            if (!nth) {\n                throw new Error('Unexpected symbol ' + ttr.symbol + '; expected monthday');\n            }\n            options.bymonthday.push(nth);\n            ttr.nextSymbol();\n        }\n    }\n    function F() {\n        if (ttr.symbol === 'until') {\n            var date = Date.parse(ttr.text);\n            if (!date)\n                throw new Error('Cannot parse until date:' + ttr.text);\n            options.until = new Date(date);\n        }\n        else if (ttr.accept('for')) {\n            options.count = parseInt(ttr.value[0], 10);\n            ttr.expect('number');\n            // ttr.expect('times')\n        }\n    }\n}\n//# sourceMappingURL=parsetext.js.map","export var Frequency;\n(function (Frequency) {\n    Frequency[Frequency[\"YEARLY\"] = 0] = \"YEARLY\";\n    Frequency[Frequency[\"MONTHLY\"] = 1] = \"MONTHLY\";\n    Frequency[Frequency[\"WEEKLY\"] = 2] = \"WEEKLY\";\n    Frequency[Frequency[\"DAILY\"] = 3] = \"DAILY\";\n    Frequency[Frequency[\"HOURLY\"] = 4] = \"HOURLY\";\n    Frequency[Frequency[\"MINUTELY\"] = 5] = \"MINUTELY\";\n    Frequency[Frequency[\"SECONDLY\"] = 6] = \"SECONDLY\";\n})(Frequency || (Frequency = {}));\nexport function freqIsDailyOrGreater(freq) {\n    return freq < Frequency.HOURLY;\n}\n//# sourceMappingURL=types.js.map","import ToText from './totext';\nimport parseText from './parsetext';\nimport { RRule } from '../rrule';\nimport { Frequency } from '../types';\nimport ENGLISH from './i18n';\n/* !\n * rrule.js - Library for working with recurrence rules for calendar dates.\n * https://github.com/jakubroztocil/rrule\n *\n * Copyright 2010, Jakub Roztocil and Lars Schoning\n * Licenced under the BSD licence.\n * https://github.com/jakubroztocil/rrule/blob/master/LICENCE\n *\n */\n/**\n *\n * Implementation of RRule.fromText() and RRule::toText().\n *\n *\n * On the client side, this file needs to be included\n * when those functions are used.\n *\n */\n// =============================================================================\n// fromText\n// =============================================================================\n/**\n * Will be able to convert some of the below described rules from\n * text format to a rule object.\n *\n *\n * RULES\n *\n * Every ([n])\n * day(s)\n * | [weekday], ..., (and) [weekday]\n * | weekday(s)\n * | week(s)\n * | month(s)\n * | [month], ..., (and) [month]\n * | year(s)\n *\n *\n * Plus 0, 1, or multiple of these:\n *\n * on [weekday], ..., (or) [weekday] the [monthday], [monthday], ... (or) [monthday]\n *\n * on [weekday], ..., (and) [weekday]\n *\n * on the [monthday], [monthday], ... (and) [monthday] (day of the month)\n *\n * on the [nth-weekday], ..., (and) [nth-weekday] (of the month/year)\n *\n *\n * Plus 0 or 1 of these:\n *\n * for [n] time(s)\n *\n * until [date]\n *\n * Plus (.)\n *\n *\n * Definitely no supported for parsing:\n *\n * (for year):\n * in week(s) [n], ..., (and) [n]\n *\n * on the [yearday], ..., (and) [n] day of the year\n * on day [yearday], ..., (and) [n]\n *\n *\n * NON-TERMINALS\n *\n * [n]: 1, 2 ..., one, two, three ..\n * [month]: January, February, March, April, May, ... December\n * [weekday]: Monday, ... Sunday\n * [nth-weekday]: first [weekday], 2nd [weekday], ... last [weekday], ...\n * [monthday]: first, 1., 2., 1st, 2nd, second, ... 31st, last day, 2nd last day, ..\n * [date]:\n * - [month] (0-31(,) ([year])),\n * - (the) 0-31.(1-12.([year])),\n * - (the) 0-31/(1-12/([year])),\n * - [weekday]\n *\n * [year]: 0000, 0001, ... 01, 02, ..\n *\n * Definitely not supported for parsing:\n *\n * [yearday]: first, 1., 2., 1st, 2nd, second, ... 366th, last day, 2nd last day, ..\n *\n * @param {String} text\n * @return {Object, Boolean} the rule, or null.\n */\nvar fromText = function (text, language) {\n    if (language === void 0) { language = ENGLISH; }\n    return new RRule(parseText(text, language) || undefined);\n};\nvar common = [\n    'count',\n    'until',\n    'interval',\n    'byweekday',\n    'bymonthday',\n    'bymonth',\n];\nToText.IMPLEMENTED = [];\nToText.IMPLEMENTED[Frequency.HOURLY] = common;\nToText.IMPLEMENTED[Frequency.MINUTELY] = common;\nToText.IMPLEMENTED[Frequency.DAILY] = ['byhour'].concat(common);\nToText.IMPLEMENTED[Frequency.WEEKLY] = common;\nToText.IMPLEMENTED[Frequency.MONTHLY] = common;\nToText.IMPLEMENTED[Frequency.YEARLY] = ['byweekno', 'byyearday'].concat(common);\n// =============================================================================\n// Export\n// =============================================================================\nvar toText = function (rrule, gettext, language, dateFormatter) {\n    return new ToText(rrule, gettext, language, dateFormatter).toString();\n};\nvar isFullyConvertible = ToText.isFullyConvertible;\nexport { fromText, parseText, isFullyConvertible, toText };\n//# sourceMappingURL=index.js.map","import { __extends } from \"tslib\";\nimport { Frequency } from './types';\nimport { pymod, divmod, empty, includes } from './helpers';\nimport { getWeekday, MAXYEAR, monthRange } from './dateutil';\nvar Time = /** @class */ (function () {\n    function Time(hour, minute, second, millisecond) {\n        this.hour = hour;\n        this.minute = minute;\n        this.second = second;\n        this.millisecond = millisecond || 0;\n    }\n    Time.prototype.getHours = function () {\n        return this.hour;\n    };\n    Time.prototype.getMinutes = function () {\n        return this.minute;\n    };\n    Time.prototype.getSeconds = function () {\n        return this.second;\n    };\n    Time.prototype.getMilliseconds = function () {\n        return this.millisecond;\n    };\n    Time.prototype.getTime = function () {\n        return ((this.hour * 60 * 60 + this.minute * 60 + this.second) * 1000 +\n            this.millisecond);\n    };\n    return Time;\n}());\nexport { Time };\nvar DateTime = /** @class */ (function (_super) {\n    __extends(DateTime, _super);\n    function DateTime(year, month, day, hour, minute, second, millisecond) {\n        var _this = _super.call(this, hour, minute, second, millisecond) || this;\n        _this.year = year;\n        _this.month = month;\n        _this.day = day;\n        return _this;\n    }\n    DateTime.fromDate = function (date) {\n        return new this(date.getUTCFullYear(), date.getUTCMonth() + 1, date.getUTCDate(), date.getUTCHours(), date.getUTCMinutes(), date.getUTCSeconds(), date.valueOf() % 1000);\n    };\n    DateTime.prototype.getWeekday = function () {\n        return getWeekday(new Date(this.getTime()));\n    };\n    DateTime.prototype.getTime = function () {\n        return new Date(Date.UTC(this.year, this.month - 1, this.day, this.hour, this.minute, this.second, this.millisecond)).getTime();\n    };\n    DateTime.prototype.getDay = function () {\n        return this.day;\n    };\n    DateTime.prototype.getMonth = function () {\n        return this.month;\n    };\n    DateTime.prototype.getYear = function () {\n        return this.year;\n    };\n    DateTime.prototype.addYears = function (years) {\n        this.year += years;\n    };\n    DateTime.prototype.addMonths = function (months) {\n        this.month += months;\n        if (this.month > 12) {\n            var yearDiv = Math.floor(this.month / 12);\n            var monthMod = pymod(this.month, 12);\n            this.month = monthMod;\n            this.year += yearDiv;\n            if (this.month === 0) {\n                this.month = 12;\n                --this.year;\n            }\n        }\n    };\n    DateTime.prototype.addWeekly = function (days, wkst) {\n        if (wkst > this.getWeekday()) {\n            this.day += -(this.getWeekday() + 1 + (6 - wkst)) + days * 7;\n        }\n        else {\n            this.day += -(this.getWeekday() - wkst) + days * 7;\n        }\n        this.fixDay();\n    };\n    DateTime.prototype.addDaily = function (days) {\n        this.day += days;\n        this.fixDay();\n    };\n    DateTime.prototype.addHours = function (hours, filtered, byhour) {\n        if (filtered) {\n            // Jump to one iteration before next day\n            this.hour += Math.floor((23 - this.hour) / hours) * hours;\n        }\n        for (;;) {\n            this.hour += hours;\n            var _a = divmod(this.hour, 24), dayDiv = _a.div, hourMod = _a.mod;\n            if (dayDiv) {\n                this.hour = hourMod;\n                this.addDaily(dayDiv);\n            }\n            if (empty(byhour) || includes(byhour, this.hour))\n                break;\n        }\n    };\n    DateTime.prototype.addMinutes = function (minutes, filtered, byhour, byminute) {\n        if (filtered) {\n            // Jump to one iteration before next day\n            this.minute +=\n                Math.floor((1439 - (this.hour * 60 + this.minute)) / minutes) * minutes;\n        }\n        for (;;) {\n            this.minute += minutes;\n            var _a = divmod(this.minute, 60), hourDiv = _a.div, minuteMod = _a.mod;\n            if (hourDiv) {\n                this.minute = minuteMod;\n                this.addHours(hourDiv, false, byhour);\n            }\n            if ((empty(byhour) || includes(byhour, this.hour)) &&\n                (empty(byminute) || includes(byminute, this.minute))) {\n                break;\n            }\n        }\n    };\n    DateTime.prototype.addSeconds = function (seconds, filtered, byhour, byminute, bysecond) {\n        if (filtered) {\n            // Jump to one iteration before next day\n            this.second +=\n                Math.floor((86399 - (this.hour * 3600 + this.minute * 60 + this.second)) /\n                    seconds) * seconds;\n        }\n        for (;;) {\n            this.second += seconds;\n            var _a = divmod(this.second, 60), minuteDiv = _a.div, secondMod = _a.mod;\n            if (minuteDiv) {\n                this.second = secondMod;\n                this.addMinutes(minuteDiv, false, byhour, byminute);\n            }\n            if ((empty(byhour) || includes(byhour, this.hour)) &&\n                (empty(byminute) || includes(byminute, this.minute)) &&\n                (empty(bysecond) || includes(bysecond, this.second))) {\n                break;\n            }\n        }\n    };\n    DateTime.prototype.fixDay = function () {\n        if (this.day <= 28) {\n            return;\n        }\n        var daysinmonth = monthRange(this.year, this.month - 1)[1];\n        if (this.day <= daysinmonth) {\n            return;\n        }\n        while (this.day > daysinmonth) {\n            this.day -= daysinmonth;\n            ++this.month;\n            if (this.month === 13) {\n                this.month = 1;\n                ++this.year;\n                if (this.year > MAXYEAR) {\n                    return;\n                }\n            }\n            daysinmonth = monthRange(this.year, this.month - 1)[1];\n        }\n    };\n    DateTime.prototype.add = function (options, filtered) {\n        var freq = options.freq, interval = options.interval, wkst = options.wkst, byhour = options.byhour, byminute = options.byminute, bysecond = options.bysecond;\n        switch (freq) {\n            case Frequency.YEARLY:\n                return this.addYears(interval);\n            case Frequency.MONTHLY:\n                return this.addMonths(interval);\n            case Frequency.WEEKLY:\n                return this.addWeekly(interval, wkst);\n            case Frequency.DAILY:\n                return this.addDaily(interval);\n            case Frequency.HOURLY:\n                return this.addHours(interval, filtered, byhour);\n            case Frequency.MINUTELY:\n                return this.addMinutes(interval, filtered, byhour, byminute);\n            case Frequency.SECONDLY:\n                return this.addSeconds(interval, filtered, byhour, byminute, bysecond);\n        }\n    };\n    return DateTime;\n}(Time));\nexport { DateTime };\n//# sourceMappingURL=datetime.js.map","import { __assign } from \"tslib\";\nimport { freqIsDailyOrGreater } from './types';\nimport { includes, notEmpty, isPresent, isNumber, isArray, isWeekdayStr, } from './helpers';\nimport { RRule, defaultKeys, DEFAULT_OPTIONS } from './rrule';\nimport { getWeekday, isDate, isValidDate } from './dateutil';\nimport { Weekday } from './weekday';\nimport { Time } from './datetime';\nexport function initializeOptions(options) {\n    var invalid = [];\n    var keys = Object.keys(options);\n    // Shallow copy for options and origOptions and check for invalid\n    for (var _i = 0, keys_1 = keys; _i < keys_1.length; _i++) {\n        var key = keys_1[_i];\n        if (!includes(defaultKeys, key))\n            invalid.push(key);\n        if (isDate(options[key]) && !isValidDate(options[key])) {\n            invalid.push(key);\n        }\n    }\n    if (invalid.length) {\n        throw new Error('Invalid options: ' + invalid.join(', '));\n    }\n    return __assign({}, options);\n}\nexport function parseOptions(options) {\n    var opts = __assign(__assign({}, DEFAULT_OPTIONS), initializeOptions(options));\n    if (isPresent(opts.byeaster))\n        opts.freq = RRule.YEARLY;\n    if (!(isPresent(opts.freq) && RRule.FREQUENCIES[opts.freq])) {\n        throw new Error(\"Invalid frequency: \".concat(opts.freq, \" \").concat(options.freq));\n    }\n    if (!opts.dtstart)\n        opts.dtstart = new Date(new Date().setMilliseconds(0));\n    if (!isPresent(opts.wkst)) {\n        opts.wkst = RRule.MO.weekday;\n    }\n    else if (isNumber(opts.wkst)) {\n        // cool, just keep it like that\n    }\n    else {\n        opts.wkst = opts.wkst.weekday;\n    }\n    if (isPresent(opts.bysetpos)) {\n        if (isNumber(opts.bysetpos))\n            opts.bysetpos = [opts.bysetpos];\n        for (var i = 0; i < opts.bysetpos.length; i++) {\n            var v = opts.bysetpos[i];\n            if (v === 0 || !(v >= -366 && v <= 366)) {\n                throw new Error('bysetpos must be between 1 and 366,' + ' or between -366 and -1');\n            }\n        }\n    }\n    if (!(Boolean(opts.byweekno) ||\n        notEmpty(opts.byweekno) ||\n        notEmpty(opts.byyearday) ||\n        Boolean(opts.bymonthday) ||\n        notEmpty(opts.bymonthday) ||\n        isPresent(opts.byweekday) ||\n        isPresent(opts.byeaster))) {\n        switch (opts.freq) {\n            case RRule.YEARLY:\n                if (!opts.bymonth)\n                    opts.bymonth = opts.dtstart.getUTCMonth() + 1;\n                opts.bymonthday = opts.dtstart.getUTCDate();\n                break;\n            case RRule.MONTHLY:\n                opts.bymonthday = opts.dtstart.getUTCDate();\n                break;\n            case RRule.WEEKLY:\n                opts.byweekday = [getWeekday(opts.dtstart)];\n                break;\n        }\n    }\n    // bymonth\n    if (isPresent(opts.bymonth) && !isArray(opts.bymonth)) {\n        opts.bymonth = [opts.bymonth];\n    }\n    // byyearday\n    if (isPresent(opts.byyearday) &&\n        !isArray(opts.byyearday) &&\n        isNumber(opts.byyearday)) {\n        opts.byyearday = [opts.byyearday];\n    }\n    // bymonthday\n    if (!isPresent(opts.bymonthday)) {\n        opts.bymonthday = [];\n        opts.bynmonthday = [];\n    }\n    else if (isArray(opts.bymonthday)) {\n        var bymonthday = [];\n        var bynmonthday = [];\n        for (var i = 0; i < opts.bymonthday.length; i++) {\n            var v = opts.bymonthday[i];\n            if (v > 0) {\n                bymonthday.push(v);\n            }\n            else if (v < 0) {\n                bynmonthday.push(v);\n            }\n        }\n        opts.bymonthday = bymonthday;\n        opts.bynmonthday = bynmonthday;\n    }\n    else if (opts.bymonthday < 0) {\n        opts.bynmonthday = [opts.bymonthday];\n        opts.bymonthday = [];\n    }\n    else {\n        opts.bynmonthday = [];\n        opts.bymonthday = [opts.bymonthday];\n    }\n    // byweekno\n    if (isPresent(opts.byweekno) && !isArray(opts.byweekno)) {\n        opts.byweekno = [opts.byweekno];\n    }\n    // byweekday / bynweekday\n    if (!isPresent(opts.byweekday)) {\n        opts.bynweekday = null;\n    }\n    else if (isNumber(opts.byweekday)) {\n        opts.byweekday = [opts.byweekday];\n        opts.bynweekday = null;\n    }\n    else if (isWeekdayStr(opts.byweekday)) {\n        opts.byweekday = [Weekday.fromStr(opts.byweekday).weekday];\n        opts.bynweekday = null;\n    }\n    else if (opts.byweekday instanceof Weekday) {\n        if (!opts.byweekday.n || opts.freq > RRule.MONTHLY) {\n            opts.byweekday = [opts.byweekday.weekday];\n            opts.bynweekday = null;\n        }\n        else {\n            opts.bynweekday = [[opts.byweekday.weekday, opts.byweekday.n]];\n            opts.byweekday = null;\n        }\n    }\n    else {\n        var byweekday = [];\n        var bynweekday = [];\n        for (var i = 0; i < opts.byweekday.length; i++) {\n            var wday = opts.byweekday[i];\n            if (isNumber(wday)) {\n                byweekday.push(wday);\n                continue;\n            }\n            else if (isWeekdayStr(wday)) {\n                byweekday.push(Weekday.fromStr(wday).weekday);\n                continue;\n            }\n            if (!wday.n || opts.freq > RRule.MONTHLY) {\n                byweekday.push(wday.weekday);\n            }\n            else {\n                bynweekday.push([wday.weekday, wday.n]);\n            }\n        }\n        opts.byweekday = notEmpty(byweekday) ? byweekday : null;\n        opts.bynweekday = notEmpty(bynweekday) ? bynweekday : null;\n    }\n    // byhour\n    if (!isPresent(opts.byhour)) {\n        opts.byhour = opts.freq < RRule.HOURLY ? [opts.dtstart.getUTCHours()] : null;\n    }\n    else if (isNumber(opts.byhour)) {\n        opts.byhour = [opts.byhour];\n    }\n    // byminute\n    if (!isPresent(opts.byminute)) {\n        opts.byminute =\n            opts.freq < RRule.MINUTELY ? [opts.dtstart.getUTCMinutes()] : null;\n    }\n    else if (isNumber(opts.byminute)) {\n        opts.byminute = [opts.byminute];\n    }\n    // bysecond\n    if (!isPresent(opts.bysecond)) {\n        opts.bysecond =\n            opts.freq < RRule.SECONDLY ? [opts.dtstart.getUTCSeconds()] : null;\n    }\n    else if (isNumber(opts.bysecond)) {\n        opts.bysecond = [opts.bysecond];\n    }\n    return { parsedOptions: opts };\n}\nexport function buildTimeset(opts) {\n    var millisecondModulo = opts.dtstart.getTime() % 1000;\n    if (!freqIsDailyOrGreater(opts.freq)) {\n        return [];\n    }\n    var timeset = [];\n    opts.byhour.forEach(function (hour) {\n        opts.byminute.forEach(function (minute) {\n            opts.bysecond.forEach(function (second) {\n                timeset.push(new Time(hour, minute, second, millisecondModulo));\n            });\n        });\n    });\n    return timeset;\n}\n//# sourceMappingURL=parseoptions.js.map","import { __assign } from \"tslib\";\nimport { Frequency } from './types';\nimport { Weekday } from './weekday';\nimport { untilStringToDate } from './dateutil';\nimport { Days } from './rrule';\nexport function parseString(rfcString) {\n    var options = rfcString\n        .split('\\n')\n        .map(parseLine)\n        .filter(function (x) { return x !== null; });\n    return __assign(__assign({}, options[0]), options[1]);\n}\nexport function parseDtstart(line) {\n    var options = {};\n    var dtstartWithZone = /DTSTART(?:;TZID=([^:=]+?))?(?::|=)([^;\\s]+)/i.exec(line);\n    if (!dtstartWithZone) {\n        return options;\n    }\n    var tzid = dtstartWithZone[1], dtstart = dtstartWithZone[2];\n    if (tzid) {\n        options.tzid = tzid;\n    }\n    options.dtstart = untilStringToDate(dtstart);\n    return options;\n}\nfunction parseLine(rfcString) {\n    rfcString = rfcString.replace(/^\\s+|\\s+$/, '');\n    if (!rfcString.length)\n        return null;\n    var header = /^([A-Z]+?)[:;]/.exec(rfcString.toUpperCase());\n    if (!header) {\n        return parseRrule(rfcString);\n    }\n    var key = header[1];\n    switch (key.toUpperCase()) {\n        case 'RRULE':\n        case 'EXRULE':\n            return parseRrule(rfcString);\n        case 'DTSTART':\n            return parseDtstart(rfcString);\n        default:\n            throw new Error(\"Unsupported RFC prop \".concat(key, \" in \").concat(rfcString));\n    }\n}\nfunction parseRrule(line) {\n    var strippedLine = line.replace(/^RRULE:/i, '');\n    var options = parseDtstart(strippedLine);\n    var attrs = line.replace(/^(?:RRULE|EXRULE):/i, '').split(';');\n    attrs.forEach(function (attr) {\n        var _a = attr.split('='), key = _a[0], value = _a[1];\n        switch (key.toUpperCase()) {\n            case 'FREQ':\n                options.freq = Frequency[value.toUpperCase()];\n                break;\n            case 'WKST':\n                options.wkst = Days[value.toUpperCase()];\n                break;\n            case 'COUNT':\n            case 'INTERVAL':\n            case 'BYSETPOS':\n            case 'BYMONTH':\n            case 'BYMONTHDAY':\n            case 'BYYEARDAY':\n            case 'BYWEEKNO':\n            case 'BYHOUR':\n            case 'BYMINUTE':\n            case 'BYSECOND':\n                var num = parseNumber(value);\n                var optionKey = key.toLowerCase();\n                // eslint-disable-next-line @typescript-eslint/ban-ts-comment\n                // @ts-ignore\n                options[optionKey] = num;\n                break;\n            case 'BYWEEKDAY':\n            case 'BYDAY':\n                options.byweekday = parseWeekday(value);\n                break;\n            case 'DTSTART':\n            case 'TZID':\n                // for backwards compatibility\n                var dtstart = parseDtstart(line);\n                options.tzid = dtstart.tzid;\n                options.dtstart = dtstart.dtstart;\n                break;\n            case 'UNTIL':\n                options.until = untilStringToDate(value);\n                break;\n            case 'BYEASTER':\n                options.byeaster = Number(value);\n                break;\n            default:\n                throw new Error(\"Unknown RRULE property '\" + key + \"'\");\n        }\n    });\n    return options;\n}\nfunction parseNumber(value) {\n    if (value.indexOf(',') !== -1) {\n        var values = value.split(',');\n        return values.map(parseIndividualNumber);\n    }\n    return parseIndividualNumber(value);\n}\nfunction parseIndividualNumber(value) {\n    if (/^[+-]?\\d+$/.test(value)) {\n        return Number(value);\n    }\n    return value;\n}\nfunction parseWeekday(value) {\n    var days = value.split(',');\n    return days.map(function (day) {\n        if (day.length === 2) {\n            // MO, TU, ...\n            return Days[day]; // wday instanceof Weekday\n        }\n        // -1MO, +3FR, 1SO, 13TU ...\n        var parts = day.match(/^([+-]?\\d{1,2})([A-Z]{2})$/);\n        if (!parts || parts.length < 3) {\n            throw new SyntaxError(\"Invalid weekday string: \".concat(day));\n        }\n        var n = Number(parts[1]);\n        var wdaypart = parts[2];\n        var wday = Days[wdaypart].weekday;\n        return new Weekday(wday, n);\n    });\n}\n//# sourceMappingURL=parsestring.js.map","import { dateInTimeZone, timeToUntilString } from './dateutil';\nvar DateWithZone = /** @class */ (function () {\n    function DateWithZone(date, tzid) {\n        if (isNaN(date.getTime())) {\n            throw new RangeError('Invalid date passed to DateWithZone');\n        }\n        this.date = date;\n        this.tzid = tzid;\n    }\n    Object.defineProperty(DateWithZone.prototype, \"isUTC\", {\n        get: function () {\n            return !this.tzid || this.tzid.toUpperCase() === 'UTC';\n        },\n        enumerable: false,\n        configurable: true\n    });\n    DateWithZone.prototype.toString = function () {\n        var datestr = timeToUntilString(this.date.getTime(), this.isUTC);\n        if (!this.isUTC) {\n            return \";TZID=\".concat(this.tzid, \":\").concat(datestr);\n        }\n        return \":\".concat(datestr);\n    };\n    DateWithZone.prototype.getTime = function () {\n        return this.date.getTime();\n    };\n    DateWithZone.prototype.rezonedDate = function () {\n        if (this.isUTC) {\n            return this.date;\n        }\n        return dateInTimeZone(this.date, this.tzid);\n    };\n    return DateWithZone;\n}());\nexport { DateWithZone };\n//# sourceMappingURL=datewithzone.js.map","import { RRule, DEFAULT_OPTIONS } from './rrule';\nimport { includes, isPresent, isArray, isNumber, toArray } from './helpers';\nimport { Weekday } from './weekday';\nimport { timeToUntilString } from './dateutil';\nimport { DateWithZone } from './datewithzone';\nexport function optionsToString(options) {\n    var rrule = [];\n    var dtstart = '';\n    var keys = Object.keys(options);\n    var defaultKeys = Object.keys(DEFAULT_OPTIONS);\n    for (var i = 0; i < keys.length; i++) {\n        if (keys[i] === 'tzid')\n            continue;\n        if (!includes(defaultKeys, keys[i]))\n            continue;\n        var key = keys[i].toUpperCase();\n        var value = options[keys[i]];\n        var outValue = '';\n        if (!isPresent(value) || (isArray(value) && !value.length))\n            continue;\n        switch (key) {\n            case 'FREQ':\n                outValue = RRule.FREQUENCIES[options.freq];\n                break;\n            case 'WKST':\n                if (isNumber(value)) {\n                    outValue = new Weekday(value).toString();\n                }\n                else {\n                    outValue = value.toString();\n                }\n                break;\n            case 'BYWEEKDAY':\n                /*\n                  NOTE: BYWEEKDAY is a special case.\n                  RRule() deconstructs the rule.options.byweekday array\n                  into an array of Weekday arguments.\n                  On the other hand, rule.origOptions is an array of Weekdays.\n                  We need to handle both cases here.\n                  It might be worth change RRule to keep the Weekdays.\n        \n                  Also, BYWEEKDAY (used by RRule) vs. BYDAY (RFC)\n        \n                  */\n                key = 'BYDAY';\n                outValue = toArray(value)\n                    .map(function (wday) {\n                    if (wday instanceof Weekday) {\n                        return wday;\n                    }\n                    if (isArray(wday)) {\n                        return new Weekday(wday[0], wday[1]);\n                    }\n                    return new Weekday(wday);\n                })\n                    .toString();\n                break;\n            case 'DTSTART':\n                dtstart = buildDtstart(value, options.tzid);\n                break;\n            case 'UNTIL':\n                outValue = timeToUntilString(value, !options.tzid);\n                break;\n            default:\n                if (isArray(value)) {\n                    var strValues = [];\n                    for (var j = 0; j < value.length; j++) {\n                        strValues[j] = String(value[j]);\n                    }\n                    outValue = strValues.toString();\n                }\n                else {\n                    outValue = String(value);\n                }\n        }\n        if (outValue) {\n            rrule.push([key, outValue]);\n        }\n    }\n    var rules = rrule\n        .map(function (_a) {\n        var key = _a[0], value = _a[1];\n        return \"\".concat(key, \"=\").concat(value.toString());\n    })\n        .join(';');\n    var ruleString = '';\n    if (rules !== '') {\n        ruleString = \"RRULE:\".concat(rules);\n    }\n    return [dtstart, ruleString].filter(function (x) { return !!x; }).join('\\n');\n}\nfunction buildDtstart(dtstart, tzid) {\n    if (!dtstart) {\n        return '';\n    }\n    return 'DTSTART' + new DateWithZone(new Date(dtstart), tzid).toString();\n}\n//# sourceMappingURL=optionstostring.js.map","import IterResult from './iterresult';\nimport { clone, cloneDates } from './dateutil';\nimport { isArray } from './helpers';\nfunction argsMatch(left, right) {\n    if (Array.isArray(left)) {\n        if (!Array.isArray(right))\n            return false;\n        if (left.length !== right.length)\n            return false;\n        return left.every(function (date, i) { return date.getTime() === right[i].getTime(); });\n    }\n    if (left instanceof Date) {\n        return right instanceof Date && left.getTime() === right.getTime();\n    }\n    return left === right;\n}\nvar Cache = /** @class */ (function () {\n    function Cache() {\n        this.all = false;\n        this.before = [];\n        this.after = [];\n        this.between = [];\n    }\n    /**\n     * @param {String} what - all/before/after/between\n     * @param {Array,Date} value - an array of dates, one date, or null\n     * @param {Object?} args - _iter arguments\n     */\n    Cache.prototype._cacheAdd = function (what, value, args) {\n        if (value) {\n            value = value instanceof Date ? clone(value) : cloneDates(value);\n        }\n        if (what === 'all') {\n            this.all = value;\n        }\n        else {\n            args._value = value;\n            this[what].push(args);\n        }\n    };\n    /**\n     * @return false - not in the cache\n     * @return null  - cached, but zero occurrences (before/after)\n     * @return Date  - cached (before/after)\n     * @return []    - cached, but zero occurrences (all/between)\n     * @return [Date1, DateN] - cached (all/between)\n     */\n    Cache.prototype._cacheGet = function (what, args) {\n        var cached = false;\n        var argsKeys = args ? Object.keys(args) : [];\n        var findCacheDiff = function (item) {\n            for (var i = 0; i < argsKeys.length; i++) {\n                var key = argsKeys[i];\n                if (!argsMatch(args[key], item[key])) {\n                    return true;\n                }\n            }\n            return false;\n        };\n        var cachedObject = this[what];\n        if (what === 'all') {\n            cached = this.all;\n        }\n        else if (isArray(cachedObject)) {\n            // Let's see whether we've already called the\n            // 'what' method with the same 'args'\n            for (var i = 0; i < cachedObject.length; i++) {\n                var item = cachedObject[i];\n                if (argsKeys.length && findCacheDiff(item))\n                    continue;\n                cached = item._value;\n                break;\n            }\n        }\n        if (!cached && this.all) {\n            // Not in the cache, but we already know all the occurrences,\n            // so we can find the correct dates from the cached ones.\n            var iterResult = new IterResult(what, args);\n            for (var i = 0; i < this.all.length; i++) {\n                if (!iterResult.accept(this.all[i]))\n                    break;\n            }\n            cached = iterResult.getValue();\n            this._cacheAdd(what, cached, args);\n        }\n        return isArray(cached)\n            ? cloneDates(cached)\n            : cached instanceof Date\n                ? clone(cached)\n                : cached;\n    };\n    return Cache;\n}());\nexport { Cache };\n//# sourceMappingURL=cache.js.map","import { __spreadArray } from \"tslib\";\nimport { range, repeat } from './helpers';\n// =============================================================================\n// Date masks\n// =============================================================================\n// Every mask is 7 days longer to handle cross-year weekly periods.\nvar M365MASK = __spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray([], repeat(1, 31), true), repeat(2, 28), true), repeat(3, 31), true), repeat(4, 30), true), repeat(5, 31), true), repeat(6, 30), true), repeat(7, 31), true), repeat(8, 31), true), repeat(9, 30), true), repeat(10, 31), true), repeat(11, 30), true), repeat(12, 31), true), repeat(1, 7), true);\nvar M366MASK = __spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray([], repeat(1, 31), true), repeat(2, 29), true), repeat(3, 31), true), repeat(4, 30), true), repeat(5, 31), true), repeat(6, 30), true), repeat(7, 31), true), repeat(8, 31), true), repeat(9, 30), true), repeat(10, 31), true), repeat(11, 30), true), repeat(12, 31), true), repeat(1, 7), true);\nvar M28 = range(1, 29);\nvar M29 = range(1, 30);\nvar M30 = range(1, 31);\nvar M31 = range(1, 32);\nvar MDAY366MASK = __spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray([], M31, true), M29, true), M31, true), M30, true), M31, true), M30, true), M31, true), M31, true), M30, true), M31, true), M30, true), M31, true), M31.slice(0, 7), true);\nvar MDAY365MASK = __spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray([], M31, true), M28, true), M31, true), M30, true), M31, true), M30, true), M31, true), M31, true), M30, true), M31, true), M30, true), M31, true), M31.slice(0, 7), true);\nvar NM28 = range(-28, 0);\nvar NM29 = range(-29, 0);\nvar NM30 = range(-30, 0);\nvar NM31 = range(-31, 0);\nvar NMDAY366MASK = __spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray([], NM31, true), NM29, true), NM31, true), NM30, true), NM31, true), NM30, true), NM31, true), NM31, true), NM30, true), NM31, true), NM30, true), NM31, true), NM31.slice(0, 7), true);\nvar NMDAY365MASK = __spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray(__spreadArray([], NM31, true), NM28, true), NM31, true), NM30, true), NM31, true), NM30, true), NM31, true), NM31, true), NM30, true), NM31, true), NM30, true), NM31, true), NM31.slice(0, 7), true);\nvar M366RANGE = [0, 31, 60, 91, 121, 152, 182, 213, 244, 274, 305, 335, 366];\nvar M365RANGE = [0, 31, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334, 365];\nvar WDAYMASK = (function () {\n    var wdaymask = [];\n    for (var i = 0; i < 55; i++)\n        wdaymask = wdaymask.concat(range(7));\n    return wdaymask;\n})();\nexport { WDAYMASK, M365MASK, M365RANGE, M366MASK, M366RANGE, MDAY365MASK, MDAY366MASK, NMDAY365MASK, NMDAY366MASK, };\n//# sourceMappingURL=masks.js.map","import { __assign } from \"tslib\";\nimport { datetime, getWeekday, isLeapYear, toOrdinal } from '../dateutil';\nimport { empty, repeat, pymod, includes } from '../helpers';\nimport { M365MASK, MDAY365MASK, NMDAY365MASK, WDAYMASK, M365RANGE, M366MASK, MDAY366MASK, NMDAY366MASK, M366RANGE, } from '../masks';\nexport function rebuildYear(year, options) {\n    var firstyday = datetime(year, 1, 1);\n    var yearlen = isLeapYear(year) ? 366 : 365;\n    var nextyearlen = isLeapYear(year + 1) ? 366 : 365;\n    var yearordinal = toOrdinal(firstyday);\n    var yearweekday = getWeekday(firstyday);\n    var result = __assign(__assign({ yearlen: yearlen, nextyearlen: nextyearlen, yearordinal: yearordinal, yearweekday: yearweekday }, baseYearMasks(year)), { wnomask: null });\n    if (empty(options.byweekno)) {\n        return result;\n    }\n    result.wnomask = repeat(0, yearlen + 7);\n    var firstwkst;\n    var wyearlen;\n    var no1wkst = (firstwkst = pymod(7 - yearweekday + options.wkst, 7));\n    if (no1wkst >= 4) {\n        no1wkst = 0;\n        // Number of days in the year, plus the days we got\n        // from last year.\n        wyearlen = result.yearlen + pymod(yearweekday - options.wkst, 7);\n    }\n    else {\n        // Number of days in the year, minus the days we\n        // left in last year.\n        wyearlen = yearlen - no1wkst;\n    }\n    var div = Math.floor(wyearlen / 7);\n    var mod = pymod(wyearlen, 7);\n    var numweeks = Math.floor(div + mod / 4);\n    for (var j = 0; j < options.byweekno.length; j++) {\n        var n = options.byweekno[j];\n        if (n < 0) {\n            n += numweeks + 1;\n        }\n        if (!(n > 0 && n <= numweeks)) {\n            continue;\n        }\n        var i = void 0;\n        if (n > 1) {\n            i = no1wkst + (n - 1) * 7;\n            if (no1wkst !== firstwkst) {\n                i -= 7 - firstwkst;\n            }\n        }\n        else {\n            i = no1wkst;\n        }\n        for (var k = 0; k < 7; k++) {\n            result.wnomask[i] = 1;\n            i++;\n            if (result.wdaymask[i] === options.wkst)\n                break;\n        }\n    }\n    if (includes(options.byweekno, 1)) {\n        // Check week number 1 of next year as well\n        // orig-TODO : Check -numweeks for next year.\n        var i = no1wkst + numweeks * 7;\n        if (no1wkst !== firstwkst)\n            i -= 7 - firstwkst;\n        if (i < yearlen) {\n            // If week starts in next year, we\n            // don't care about it.\n            for (var j = 0; j < 7; j++) {\n                result.wnomask[i] = 1;\n                i += 1;\n                if (result.wdaymask[i] === options.wkst)\n                    break;\n            }\n        }\n    }\n    if (no1wkst) {\n        // Check last week number of last year as\n        // well. If no1wkst is 0, either the year\n        // started on week start, or week number 1\n        // got days from last year, so there are no\n        // days from last year's last week number in\n        // this year.\n        var lnumweeks = void 0;\n        if (!includes(options.byweekno, -1)) {\n            var lyearweekday = getWeekday(datetime(year - 1, 1, 1));\n            var lno1wkst = pymod(7 - lyearweekday.valueOf() + options.wkst, 7);\n            var lyearlen = isLeapYear(year - 1) ? 366 : 365;\n            var weekst = void 0;\n            if (lno1wkst >= 4) {\n                lno1wkst = 0;\n                weekst = lyearlen + pymod(lyearweekday - options.wkst, 7);\n            }\n            else {\n                weekst = yearlen - no1wkst;\n            }\n            lnumweeks = Math.floor(52 + pymod(weekst, 7) / 4);\n        }\n        else {\n            lnumweeks = -1;\n        }\n        if (includes(options.byweekno, lnumweeks)) {\n            for (var i = 0; i < no1wkst; i++)\n                result.wnomask[i] = 1;\n        }\n    }\n    return result;\n}\nfunction baseYearMasks(year) {\n    var yearlen = isLeapYear(year) ? 366 : 365;\n    var firstyday = datetime(year, 1, 1);\n    var wday = getWeekday(firstyday);\n    if (yearlen === 365) {\n        return {\n            mmask: M365MASK,\n            mdaymask: MDAY365MASK,\n            nmdaymask: NMDAY365MASK,\n            wdaymask: WDAYMASK.slice(wday),\n            mrange: M365RANGE,\n        };\n    }\n    return {\n        mmask: M366MASK,\n        mdaymask: MDAY366MASK,\n        nmdaymask: NMDAY366MASK,\n        wdaymask: WDAYMASK.slice(wday),\n        mrange: M366RANGE,\n    };\n}\n//# sourceMappingURL=yearinfo.js.map","import { RRule } from '../rrule';\nimport { empty, repeat, pymod } from '../helpers';\nexport function rebuildMonth(year, month, yearlen, mrange, wdaymask, options) {\n    var result = {\n        lastyear: year,\n        lastmonth: month,\n        nwdaymask: [],\n    };\n    var ranges = [];\n    if (options.freq === RRule.YEARLY) {\n        if (empty(options.bymonth)) {\n            ranges = [[0, yearlen]];\n        }\n        else {\n            for (var j = 0; j < options.bymonth.length; j++) {\n                month = options.bymonth[j];\n                ranges.push(mrange.slice(month - 1, month + 1));\n            }\n        }\n    }\n    else if (options.freq === RRule.MONTHLY) {\n        ranges = [mrange.slice(month - 1, month + 1)];\n    }\n    if (empty(ranges)) {\n        return result;\n    }\n    // Weekly frequency won't get here, so we may not\n    // care about cross-year weekly periods.\n    result.nwdaymask = repeat(0, yearlen);\n    for (var j = 0; j < ranges.length; j++) {\n        var rang = ranges[j];\n        var first = rang[0];\n        var last = rang[1] - 1;\n        for (var k = 0; k < options.bynweekday.length; k++) {\n            var i = void 0;\n            var _a = options.bynweekday[k], wday = _a[0], n = _a[1];\n            if (n < 0) {\n                i = last + (n + 1) * 7;\n                i -= pymod(wdaymask[i] - wday, 7);\n            }\n            else {\n                i = first + (n - 1) * 7;\n                i += pymod(7 - wdaymask[i] + wday, 7);\n            }\n            if (first <= i && i <= last)\n                result.nwdaymask[i] = 1;\n        }\n    }\n    return result;\n}\n//# sourceMappingURL=monthinfo.js.map","export function easter(y, offset) {\n    if (offset === void 0) { offset = 0; }\n    var a = y % 19;\n    var b = Math.floor(y / 100);\n    var c = y % 100;\n    var d = Math.floor(b / 4);\n    var e = b % 4;\n    var f = Math.floor((b + 8) / 25);\n    var g = Math.floor((b - f + 1) / 3);\n    var h = Math.floor(19 * a + b - d - g + 15) % 30;\n    var i = Math.floor(c / 4);\n    var k = c % 4;\n    var l = Math.floor(32 + 2 * e + 2 * i - h - k) % 7;\n    var m = Math.floor((a + 11 * h + 22 * l) / 451);\n    var month = Math.floor((h + l - 7 * m + 114) / 31);\n    var day = ((h + l - 7 * m + 114) % 31) + 1;\n    var date = Date.UTC(y, month - 1, day + offset);\n    var yearStart = Date.UTC(y, 0, 1);\n    return [Math.ceil((date - yearStart) / (1000 * 60 * 60 * 24))];\n}\n//# sourceMappingURL=easter.js.map","import { notEmpty, repeat, range, isPresent } from '../helpers';\nimport { Frequency } from '../types';\nimport { rebuildYear } from './yearinfo';\nimport { rebuildMonth } from './monthinfo';\nimport { easter } from './easter';\nimport { Time } from '../datetime';\nimport { datetime, sort, toOrdinal } from '../dateutil';\n// =============================================================================\n// Iterinfo\n// =============================================================================\nvar Iterinfo = /** @class */ (function () {\n    // eslint-disable-next-line no-empty-function\n    function Iterinfo(options) {\n        this.options = options;\n    }\n    Iterinfo.prototype.rebuild = function (year, month) {\n        var options = this.options;\n        if (year !== this.lastyear) {\n            this.yearinfo = rebuildYear(year, options);\n        }\n        if (notEmpty(options.bynweekday) &&\n            (month !== this.lastmonth || year !== this.lastyear)) {\n            var _a = this.yearinfo, yearlen = _a.yearlen, mrange = _a.mrange, wdaymask = _a.wdaymask;\n            this.monthinfo = rebuildMonth(year, month, yearlen, mrange, wdaymask, options);\n        }\n        if (isPresent(options.byeaster)) {\n            this.eastermask = easter(year, options.byeaster);\n        }\n    };\n    Object.defineProperty(Iterinfo.prototype, \"lastyear\", {\n        get: function () {\n            return this.monthinfo ? this.monthinfo.lastyear : null;\n        },\n        enumerable: false,\n        configurable: true\n    });\n    Object.defineProperty(Iterinfo.prototype, \"lastmonth\", {\n        get: function () {\n            return this.monthinfo ? this.monthinfo.lastmonth : null;\n        },\n        enumerable: false,\n        configurable: true\n    });\n    Object.defineProperty(Iterinfo.prototype, \"yearlen\", {\n        get: function () {\n            return this.yearinfo.yearlen;\n        },\n        enumerable: false,\n        configurable: true\n    });\n    Object.defineProperty(Iterinfo.prototype, \"yearordinal\", {\n        get: function () {\n            return this.yearinfo.yearordinal;\n        },\n        enumerable: false,\n        configurable: true\n    });\n    Object.defineProperty(Iterinfo.prototype, \"mrange\", {\n        get: function () {\n            return this.yearinfo.mrange;\n        },\n        enumerable: false,\n        configurable: true\n    });\n    Object.defineProperty(Iterinfo.prototype, \"wdaymask\", {\n        get: function () {\n            return this.yearinfo.wdaymask;\n        },\n        enumerable: false,\n        configurable: true\n    });\n    Object.defineProperty(Iterinfo.prototype, \"mmask\", {\n        get: function () {\n            return this.yearinfo.mmask;\n        },\n        enumerable: false,\n        configurable: true\n    });\n    Object.defineProperty(Iterinfo.prototype, \"wnomask\", {\n        get: function () {\n            return this.yearinfo.wnomask;\n        },\n        enumerable: false,\n        configurable: true\n    });\n    Object.defineProperty(Iterinfo.prototype, \"nwdaymask\", {\n        get: function () {\n            return this.monthinfo ? this.monthinfo.nwdaymask : [];\n        },\n        enumerable: false,\n        configurable: true\n    });\n    Object.defineProperty(Iterinfo.prototype, \"nextyearlen\", {\n        get: function () {\n            return this.yearinfo.nextyearlen;\n        },\n        enumerable: false,\n        configurable: true\n    });\n    Object.defineProperty(Iterinfo.prototype, \"mdaymask\", {\n        get: function () {\n            return this.yearinfo.mdaymask;\n        },\n        enumerable: false,\n        configurable: true\n    });\n    Object.defineProperty(Iterinfo.prototype, \"nmdaymask\", {\n        get: function () {\n            return this.yearinfo.nmdaymask;\n        },\n        enumerable: false,\n        configurable: true\n    });\n    Iterinfo.prototype.ydayset = function () {\n        return [range(this.yearlen), 0, this.yearlen];\n    };\n    Iterinfo.prototype.mdayset = function (_, month) {\n        var start = this.mrange[month - 1];\n        var end = this.mrange[month];\n        var set = repeat(null, this.yearlen);\n        for (var i = start; i < end; i++)\n            set[i] = i;\n        return [set, start, end];\n    };\n    Iterinfo.prototype.wdayset = function (year, month, day) {\n        // We need to handle cross-year weeks here.\n        var set = repeat(null, this.yearlen + 7);\n        var i = toOrdinal(datetime(year, month, day)) - this.yearordinal;\n        var start = i;\n        for (var j = 0; j < 7; j++) {\n            set[i] = i;\n            ++i;\n            if (this.wdaymask[i] === this.options.wkst)\n                break;\n        }\n        return [set, start, i];\n    };\n    Iterinfo.prototype.ddayset = function (year, month, day) {\n        var set = repeat(null, this.yearlen);\n        var i = toOrdinal(datetime(year, month, day)) - this.yearordinal;\n        set[i] = i;\n        return [set, i, i + 1];\n    };\n    Iterinfo.prototype.htimeset = function (hour, _, second, millisecond) {\n        var _this = this;\n        var set = [];\n        this.options.byminute.forEach(function (minute) {\n            set = set.concat(_this.mtimeset(hour, minute, second, millisecond));\n        });\n        sort(set);\n        return set;\n    };\n    Iterinfo.prototype.mtimeset = function (hour, minute, _, millisecond) {\n        var set = this.options.bysecond.map(function (second) { return new Time(hour, minute, second, millisecond); });\n        sort(set);\n        return set;\n    };\n    Iterinfo.prototype.stimeset = function (hour, minute, second, millisecond) {\n        return [new Time(hour, minute, second, millisecond)];\n    };\n    Iterinfo.prototype.getdayset = function (freq) {\n        switch (freq) {\n            case Frequency.YEARLY:\n                return this.ydayset.bind(this);\n            case Frequency.MONTHLY:\n                return this.mdayset.bind(this);\n            case Frequency.WEEKLY:\n                return this.wdayset.bind(this);\n            case Frequency.DAILY:\n                return this.ddayset.bind(this);\n            default:\n                return this.ddayset.bind(this);\n        }\n    };\n    Iterinfo.prototype.gettimeset = function (freq) {\n        switch (freq) {\n            case Frequency.HOURLY:\n                return this.htimeset.bind(this);\n            case Frequency.MINUTELY:\n                return this.mtimeset.bind(this);\n            case Frequency.SECONDLY:\n                return this.stimeset.bind(this);\n        }\n    };\n    return Iterinfo;\n}());\nexport default Iterinfo;\n//# sourceMappingURL=index.js.map","import { combine, fromOrdinal, sort } from '../dateutil';\nimport { pymod, isPresent, includes } from '../helpers';\nexport function buildPoslist(bysetpos, timeset, start, end, ii, dayset) {\n    var poslist = [];\n    for (var j = 0; j < bysetpos.length; j++) {\n        var daypos = void 0;\n        var timepos = void 0;\n        var pos = bysetpos[j];\n        if (pos < 0) {\n            daypos = Math.floor(pos / timeset.length);\n            timepos = pymod(pos, timeset.length);\n        }\n        else {\n            daypos = Math.floor((pos - 1) / timeset.length);\n            timepos = pymod(pos - 1, timeset.length);\n        }\n        var tmp = [];\n        for (var k = start; k < end; k++) {\n            var val = dayset[k];\n            if (!isPresent(val))\n                continue;\n            tmp.push(val);\n        }\n        var i = void 0;\n        if (daypos < 0) {\n            i = tmp.slice(daypos)[0];\n        }\n        else {\n            i = tmp[daypos];\n        }\n        var time = timeset[timepos];\n        var date = fromOrdinal(ii.yearordinal + i);\n        var res = combine(date, time);\n        // XXX: can this ever be in the array?\n        // - compare the actual date instead?\n        if (!includes(poslist, res))\n            poslist.push(res);\n    }\n    sort(poslist);\n    return poslist;\n}\n//# sourceMappingURL=poslist.js.map","import { freqIsDailyOrGreater } from '../types';\nimport { combine, fromOrdinal, MAXYEAR } from '../dateutil';\nimport Iterinfo from '../iterinfo/index';\nimport { RRule } from '../rrule';\nimport { buildTimeset } from '../parseoptions';\nimport { notEmpty, includes, isPresent } from '../helpers';\nimport { DateWithZone } from '../datewithzone';\nimport { buildPoslist } from './poslist';\nimport { DateTime } from '../datetime';\nexport function iter(iterResult, options) {\n    var dtstart = options.dtstart, freq = options.freq, interval = options.interval, until = options.until, bysetpos = options.bysetpos;\n    var count = options.count;\n    if (count === 0 || interval === 0) {\n        return emitResult(iterResult);\n    }\n    var counterDate = DateTime.fromDate(dtstart);\n    var ii = new Iterinfo(options);\n    ii.rebuild(counterDate.year, counterDate.month);\n    var timeset = makeTimeset(ii, counterDate, options);\n    for (;;) {\n        var _a = ii.getdayset(freq)(counterDate.year, counterDate.month, counterDate.day), dayset = _a[0], start = _a[1], end = _a[2];\n        var filtered = removeFilteredDays(dayset, start, end, ii, options);\n        if (notEmpty(bysetpos)) {\n            var poslist = buildPoslist(bysetpos, timeset, start, end, ii, dayset);\n            for (var j = 0; j < poslist.length; j++) {\n                var res = poslist[j];\n                if (until && res > until) {\n                    return emitResult(iterResult);\n                }\n                if (res >= dtstart) {\n                    var rezonedDate = rezoneIfNeeded(res, options);\n                    if (!iterResult.accept(rezonedDate)) {\n                        return emitResult(iterResult);\n                    }\n                    if (count) {\n                        --count;\n                        if (!count) {\n                            return emitResult(iterResult);\n                        }\n                    }\n                }\n            }\n        }\n        else {\n            for (var j = start; j < end; j++) {\n                var currentDay = dayset[j];\n                if (!isPresent(currentDay)) {\n                    continue;\n                }\n                var date = fromOrdinal(ii.yearordinal + currentDay);\n                for (var k = 0; k < timeset.length; k++) {\n                    var time = timeset[k];\n                    var res = combine(date, time);\n                    if (until && res > until) {\n                        return emitResult(iterResult);\n                    }\n                    if (res >= dtstart) {\n                        var rezonedDate = rezoneIfNeeded(res, options);\n                        if (!iterResult.accept(rezonedDate)) {\n                            return emitResult(iterResult);\n                        }\n                        if (count) {\n                            --count;\n                            if (!count) {\n                                return emitResult(iterResult);\n                            }\n                        }\n                    }\n                }\n            }\n        }\n        if (options.interval === 0) {\n            return emitResult(iterResult);\n        }\n        // Handle frequency and interval\n        counterDate.add(options, filtered);\n        if (counterDate.year > MAXYEAR) {\n            return emitResult(iterResult);\n        }\n        if (!freqIsDailyOrGreater(freq)) {\n            timeset = ii.gettimeset(freq)(counterDate.hour, counterDate.minute, counterDate.second, 0);\n        }\n        ii.rebuild(counterDate.year, counterDate.month);\n    }\n}\nfunction isFiltered(ii, currentDay, options) {\n    var bymonth = options.bymonth, byweekno = options.byweekno, byweekday = options.byweekday, byeaster = options.byeaster, bymonthday = options.bymonthday, bynmonthday = options.bynmonthday, byyearday = options.byyearday;\n    return ((notEmpty(bymonth) && !includes(bymonth, ii.mmask[currentDay])) ||\n        (notEmpty(byweekno) && !ii.wnomask[currentDay]) ||\n        (notEmpty(byweekday) && !includes(byweekday, ii.wdaymask[currentDay])) ||\n        (notEmpty(ii.nwdaymask) && !ii.nwdaymask[currentDay]) ||\n        (byeaster !== null && !includes(ii.eastermask, currentDay)) ||\n        ((notEmpty(bymonthday) || notEmpty(bynmonthday)) &&\n            !includes(bymonthday, ii.mdaymask[currentDay]) &&\n            !includes(bynmonthday, ii.nmdaymask[currentDay])) ||\n        (notEmpty(byyearday) &&\n            ((currentDay < ii.yearlen &&\n                !includes(byyearday, currentDay + 1) &&\n                !includes(byyearday, -ii.yearlen + currentDay)) ||\n                (currentDay >= ii.yearlen &&\n                    !includes(byyearday, currentDay + 1 - ii.yearlen) &&\n                    !includes(byyearday, -ii.nextyearlen + currentDay - ii.yearlen)))));\n}\nfunction rezoneIfNeeded(date, options) {\n    return new DateWithZone(date, options.tzid).rezonedDate();\n}\nfunction emitResult(iterResult) {\n    return iterResult.getValue();\n}\nfunction removeFilteredDays(dayset, start, end, ii, options) {\n    var filtered = false;\n    for (var dayCounter = start; dayCounter < end; dayCounter++) {\n        var currentDay = dayset[dayCounter];\n        filtered = isFiltered(ii, currentDay, options);\n        if (filtered)\n            dayset[currentDay] = null;\n    }\n    return filtered;\n}\nfunction makeTimeset(ii, counterDate, options) {\n    var freq = options.freq, byhour = options.byhour, byminute = options.byminute, bysecond = options.bysecond;\n    if (freqIsDailyOrGreater(freq)) {\n        return buildTimeset(options);\n    }\n    if ((freq >= RRule.HOURLY &&\n        notEmpty(byhour) &&\n        !includes(byhour, counterDate.hour)) ||\n        (freq >= RRule.MINUTELY &&\n            notEmpty(byminute) &&\n            !includes(byminute, counterDate.minute)) ||\n        (freq >= RRule.SECONDLY &&\n            notEmpty(bysecond) &&\n            !includes(bysecond, counterDate.second))) {\n        return [];\n    }\n    return ii.gettimeset(freq)(counterDate.hour, counterDate.minute, counterDate.second, counterDate.millisecond);\n}\n//# sourceMappingURL=index.js.map","import { isValidDate } from './dateutil';\nimport IterResult from './iterresult';\nimport CallbackIterResult from './callbackiterresult';\nimport { fromText, parseText, toText, isFullyConvertible } from './nlp/index';\nimport { Frequency, } from './types';\nimport { parseOptions, initializeOptions } from './parseoptions';\nimport { parseString } from './parsestring';\nimport { optionsToString } from './optionstostring';\nimport { Cache } from './cache';\nimport { Weekday } from './weekday';\nimport { iter } from './iter/index';\n// =============================================================================\n// RRule\n// =============================================================================\nexport var Days = {\n    MO: new Weekday(0),\n    TU: new Weekday(1),\n    WE: new Weekday(2),\n    TH: new Weekday(3),\n    FR: new Weekday(4),\n    SA: new Weekday(5),\n    SU: new Weekday(6),\n};\nexport var DEFAULT_OPTIONS = {\n    freq: Frequency.YEARLY,\n    dtstart: null,\n    interval: 1,\n    wkst: Days.MO,\n    count: null,\n    until: null,\n    tzid: null,\n    bysetpos: null,\n    bymonth: null,\n    bymonthday: null,\n    bynmonthday: null,\n    byyearday: null,\n    byweekno: null,\n    byweekday: null,\n    bynweekday: null,\n    byhour: null,\n    byminute: null,\n    bysecond: null,\n    byeaster: null,\n};\nexport var defaultKeys = Object.keys(DEFAULT_OPTIONS);\n/**\n *\n * @param {Options?} options - see <http://labix.org/python-dateutil/#head-cf004ee9a75592797e076752b2a889c10f445418>\n * - The only required option is `freq`, one of RRule.YEARLY, RRule.MONTHLY, ...\n * @constructor\n */\nvar RRule = /** @class */ (function () {\n    function RRule(options, noCache) {\n        if (options === void 0) { options = {}; }\n        if (noCache === void 0) { noCache = false; }\n        // RFC string\n        this._cache = noCache ? null : new Cache();\n        // used by toString()\n        this.origOptions = initializeOptions(options);\n        var parsedOptions = parseOptions(options).parsedOptions;\n        this.options = parsedOptions;\n    }\n    RRule.parseText = function (text, language) {\n        return parseText(text, language);\n    };\n    RRule.fromText = function (text, language) {\n        return fromText(text, language);\n    };\n    RRule.fromString = function (str) {\n        return new RRule(RRule.parseString(str) || undefined);\n    };\n    RRule.prototype._iter = function (iterResult) {\n        return iter(iterResult, this.options);\n    };\n    RRule.prototype._cacheGet = function (what, args) {\n        if (!this._cache)\n            return false;\n        return this._cache._cacheGet(what, args);\n    };\n    RRule.prototype._cacheAdd = function (what, value, args) {\n        if (!this._cache)\n            return;\n        return this._cache._cacheAdd(what, value, args);\n    };\n    /**\n     * @param {Function} iterator - optional function that will be called\n     * on each date that is added. It can return false\n     * to stop the iteration.\n     * @return Array containing all recurrences.\n     */\n    RRule.prototype.all = function (iterator) {\n        if (iterator) {\n            return this._iter(new CallbackIterResult('all', {}, iterator));\n        }\n        var result = this._cacheGet('all');\n        if (result === false) {\n            result = this._iter(new IterResult('all', {}));\n            this._cacheAdd('all', result);\n        }\n        return result;\n    };\n    /**\n     * Returns all the occurrences of the rrule between after and before.\n     * The inc keyword defines what happens if after and/or before are\n     * themselves occurrences. With inc == True, they will be included in the\n     * list, if they are found in the recurrence set.\n     *\n     * @return Array\n     */\n    RRule.prototype.between = function (after, before, inc, iterator) {\n        if (inc === void 0) { inc = false; }\n        if (!isValidDate(after) || !isValidDate(before)) {\n            throw new Error('Invalid date passed in to RRule.between');\n        }\n        var args = {\n            before: before,\n            after: after,\n            inc: inc,\n        };\n        if (iterator) {\n            return this._iter(new CallbackIterResult('between', args, iterator));\n        }\n        var result = this._cacheGet('between', args);\n        if (result === false) {\n            result = this._iter(new IterResult('between', args));\n            this._cacheAdd('between', result, args);\n        }\n        return result;\n    };\n    /**\n     * Returns the last recurrence before the given datetime instance.\n     * The inc keyword defines what happens if dt is an occurrence.\n     * With inc == True, if dt itself is an occurrence, it will be returned.\n     *\n     * @return Date or null\n     */\n    RRule.prototype.before = function (dt, inc) {\n        if (inc === void 0) { inc = false; }\n        if (!isValidDate(dt)) {\n            throw new Error('Invalid date passed in to RRule.before');\n        }\n        var args = { dt: dt, inc: inc };\n        var result = this._cacheGet('before', args);\n        if (result === false) {\n            result = this._iter(new IterResult('before', args));\n            this._cacheAdd('before', result, args);\n        }\n        return result;\n    };\n    /**\n     * Returns the first recurrence after the given datetime instance.\n     * The inc keyword defines what happens if dt is an occurrence.\n     * With inc == True, if dt itself is an occurrence, it will be returned.\n     *\n     * @return Date or null\n     */\n    RRule.prototype.after = function (dt, inc) {\n        if (inc === void 0) { inc = false; }\n        if (!isValidDate(dt)) {\n            throw new Error('Invalid date passed in to RRule.after');\n        }\n        var args = { dt: dt, inc: inc };\n        var result = this._cacheGet('after', args);\n        if (result === false) {\n            result = this._iter(new IterResult('after', args));\n            this._cacheAdd('after', result, args);\n        }\n        return result;\n    };\n    /**\n     * Returns the number of recurrences in this set. It will have go trough\n     * the whole recurrence, if this hasn't been done before.\n     */\n    RRule.prototype.count = function () {\n        return this.all().length;\n    };\n    /**\n     * Converts the rrule into its string representation\n     *\n     * @see <http://www.ietf.org/rfc/rfc2445.txt>\n     * @return String\n     */\n    RRule.prototype.toString = function () {\n        return optionsToString(this.origOptions);\n    };\n    /**\n     * Will convert all rules described in nlp:ToText\n     * to text.\n     */\n    RRule.prototype.toText = function (gettext, language, dateFormatter) {\n        return toText(this, gettext, language, dateFormatter);\n    };\n    RRule.prototype.isFullyConvertibleToText = function () {\n        return isFullyConvertible(this);\n    };\n    /**\n     * @return a RRule instance with the same freq and options\n     * as this one (cache is not cloned)\n     */\n    RRule.prototype.clone = function () {\n        return new RRule(this.origOptions);\n    };\n    // RRule class 'constants'\n    RRule.FREQUENCIES = [\n        'YEARLY',\n        'MONTHLY',\n        'WEEKLY',\n        'DAILY',\n        'HOURLY',\n        'MINUTELY',\n        'SECONDLY',\n    ];\n    RRule.YEARLY = Frequency.YEARLY;\n    RRule.MONTHLY = Frequency.MONTHLY;\n    RRule.WEEKLY = Frequency.WEEKLY;\n    RRule.DAILY = Frequency.DAILY;\n    RRule.HOURLY = Frequency.HOURLY;\n    RRule.MINUTELY = Frequency.MINUTELY;\n    RRule.SECONDLY = Frequency.SECONDLY;\n    RRule.MO = Days.MO;\n    RRule.TU = Days.TU;\n    RRule.WE = Days.WE;\n    RRule.TH = Days.TH;\n    RRule.FR = Days.FR;\n    RRule.SA = Days.SA;\n    RRule.SU = Days.SU;\n    RRule.parseString = parseString;\n    RRule.optionsToString = optionsToString;\n    return RRule;\n}());\nexport { RRule };\n//# sourceMappingURL=rrule.js.map","import { DateWithZone } from './datewithzone';\nimport { iter } from './iter';\nimport { sort } from './dateutil';\nexport function iterSet(iterResult, _rrule, _exrule, _rdate, _exdate, tzid) {\n    var _exdateHash = {};\n    var _accept = iterResult.accept;\n    function evalExdate(after, before) {\n        _exrule.forEach(function (rrule) {\n            rrule.between(after, before, true).forEach(function (date) {\n                _exdateHash[Number(date)] = true;\n            });\n        });\n    }\n    _exdate.forEach(function (date) {\n        var zonedDate = new DateWithZone(date, tzid).rezonedDate();\n        _exdateHash[Number(zonedDate)] = true;\n    });\n    iterResult.accept = function (date) {\n        var dt = Number(date);\n        if (isNaN(dt))\n            return _accept.call(this, date);\n        if (!_exdateHash[dt]) {\n            evalExdate(new Date(dt - 1), new Date(dt + 1));\n            if (!_exdateHash[dt]) {\n                _exdateHash[dt] = true;\n                return _accept.call(this, date);\n            }\n        }\n        return true;\n    };\n    if (iterResult.method === 'between') {\n        evalExdate(iterResult.args.after, iterResult.args.before);\n        iterResult.accept = function (date) {\n            var dt = Number(date);\n            if (!_exdateHash[dt]) {\n                _exdateHash[dt] = true;\n                return _accept.call(this, date);\n            }\n            return true;\n        };\n    }\n    for (var i = 0; i < _rdate.length; i++) {\n        var zonedDate = new DateWithZone(_rdate[i], tzid).rezonedDate();\n        if (!iterResult.accept(new Date(zonedDate.getTime())))\n            break;\n    }\n    _rrule.forEach(function (rrule) {\n        iter(iterResult, rrule.options);\n    });\n    var res = iterResult._result;\n    sort(res);\n    switch (iterResult.method) {\n        case 'all':\n        case 'between':\n            return res;\n        case 'before':\n            return ((res.length && res[res.length - 1]) || null);\n        case 'after':\n        default:\n            return ((res.length && res[0]) || null);\n    }\n}\n//# sourceMappingURL=iterset.js.map","import { __assign } from \"tslib\";\nimport { RRule } from './rrule';\nimport { RRuleSet } from './rruleset';\nimport { untilStringToDate } from './dateutil';\nimport { includes, split } from './helpers';\nimport { parseString, parseDtstart } from './parsestring';\n/**\n * RRuleStr\n * To parse a set of rrule strings\n */\nvar DEFAULT_OPTIONS = {\n    dtstart: null,\n    cache: false,\n    unfold: false,\n    forceset: false,\n    compatible: false,\n    tzid: null,\n};\nexport function parseInput(s, options) {\n    var rrulevals = [];\n    var rdatevals = [];\n    var exrulevals = [];\n    var exdatevals = [];\n    var parsedDtstart = parseDtstart(s);\n    var dtstart = parsedDtstart.dtstart;\n    var tzid = parsedDtstart.tzid;\n    var lines = splitIntoLines(s, options.unfold);\n    lines.forEach(function (line) {\n        var _a;\n        if (!line)\n            return;\n        var _b = breakDownLine(line), name = _b.name, parms = _b.parms, value = _b.value;\n        switch (name.toUpperCase()) {\n            case 'RRULE':\n                if (parms.length) {\n                    throw new Error(\"unsupported RRULE parm: \".concat(parms.join(',')));\n                }\n                rrulevals.push(parseString(line));\n                break;\n            case 'RDATE':\n                var _c = (_a = /RDATE(?:;TZID=([^:=]+))?/i.exec(line)) !== null && _a !== void 0 ? _a : [], rdateTzid = _c[1];\n                if (rdateTzid && !tzid) {\n                    tzid = rdateTzid;\n                }\n                rdatevals = rdatevals.concat(parseRDate(value, parms));\n                break;\n            case 'EXRULE':\n                if (parms.length) {\n                    throw new Error(\"unsupported EXRULE parm: \".concat(parms.join(',')));\n                }\n                exrulevals.push(parseString(value));\n                break;\n            case 'EXDATE':\n                exdatevals = exdatevals.concat(parseRDate(value, parms));\n                break;\n            case 'DTSTART':\n                break;\n            default:\n                throw new Error('unsupported property: ' + name);\n        }\n    });\n    return {\n        dtstart: dtstart,\n        tzid: tzid,\n        rrulevals: rrulevals,\n        rdatevals: rdatevals,\n        exrulevals: exrulevals,\n        exdatevals: exdatevals,\n    };\n}\nfunction buildRule(s, options) {\n    var _a = parseInput(s, options), rrulevals = _a.rrulevals, rdatevals = _a.rdatevals, exrulevals = _a.exrulevals, exdatevals = _a.exdatevals, dtstart = _a.dtstart, tzid = _a.tzid;\n    var noCache = options.cache === false;\n    if (options.compatible) {\n        options.forceset = true;\n        options.unfold = true;\n    }\n    if (options.forceset ||\n        rrulevals.length > 1 ||\n        rdatevals.length ||\n        exrulevals.length ||\n        exdatevals.length) {\n        var rset_1 = new RRuleSet(noCache);\n        rset_1.dtstart(dtstart);\n        rset_1.tzid(tzid || undefined);\n        rrulevals.forEach(function (val) {\n            rset_1.rrule(new RRule(groomRruleOptions(val, dtstart, tzid), noCache));\n        });\n        rdatevals.forEach(function (date) {\n            rset_1.rdate(date);\n        });\n        exrulevals.forEach(function (val) {\n            rset_1.exrule(new RRule(groomRruleOptions(val, dtstart, tzid), noCache));\n        });\n        exdatevals.forEach(function (date) {\n            rset_1.exdate(date);\n        });\n        if (options.compatible && options.dtstart)\n            rset_1.rdate(dtstart);\n        return rset_1;\n    }\n    var val = rrulevals[0] || {};\n    return new RRule(groomRruleOptions(val, val.dtstart || options.dtstart || dtstart, val.tzid || options.tzid || tzid), noCache);\n}\nexport function rrulestr(s, options) {\n    if (options === void 0) { options = {}; }\n    return buildRule(s, initializeOptions(options));\n}\nfunction groomRruleOptions(val, dtstart, tzid) {\n    return __assign(__assign({}, val), { dtstart: dtstart, tzid: tzid });\n}\nfunction initializeOptions(options) {\n    var invalid = [];\n    var keys = Object.keys(options);\n    var defaultKeys = Object.keys(DEFAULT_OPTIONS);\n    keys.forEach(function (key) {\n        if (!includes(defaultKeys, key))\n            invalid.push(key);\n    });\n    if (invalid.length) {\n        throw new Error('Invalid options: ' + invalid.join(', '));\n    }\n    return __assign(__assign({}, DEFAULT_OPTIONS), options);\n}\nfunction extractName(line) {\n    if (line.indexOf(':') === -1) {\n        return {\n            name: 'RRULE',\n            value: line,\n        };\n    }\n    var _a = split(line, ':', 1), name = _a[0], value = _a[1];\n    return {\n        name: name,\n        value: value,\n    };\n}\nfunction breakDownLine(line) {\n    var _a = extractName(line), name = _a.name, value = _a.value;\n    var parms = name.split(';');\n    if (!parms)\n        throw new Error('empty property name');\n    return {\n        name: parms[0].toUpperCase(),\n        parms: parms.slice(1),\n        value: value,\n    };\n}\nfunction splitIntoLines(s, unfold) {\n    if (unfold === void 0) { unfold = false; }\n    s = s && s.trim();\n    if (!s)\n        throw new Error('Invalid empty string');\n    // More info about 'unfold' option\n    // Go head to http://www.ietf.org/rfc/rfc2445.txt\n    if (!unfold) {\n        return s.split(/\\s/);\n    }\n    var lines = s.split('\\n');\n    var i = 0;\n    while (i < lines.length) {\n        // TODO\n        var line = (lines[i] = lines[i].replace(/\\s+$/g, ''));\n        if (!line) {\n            lines.splice(i, 1);\n        }\n        else if (i > 0 && line[0] === ' ') {\n            lines[i - 1] += line.slice(1);\n            lines.splice(i, 1);\n        }\n        else {\n            i += 1;\n        }\n    }\n    return lines;\n}\nfunction validateDateParm(parms) {\n    parms.forEach(function (parm) {\n        if (!/(VALUE=DATE(-TIME)?)|(TZID=)/.test(parm)) {\n            throw new Error('unsupported RDATE/EXDATE parm: ' + parm);\n        }\n    });\n}\nfunction parseRDate(rdateval, parms) {\n    validateDateParm(parms);\n    return rdateval.split(',').map(function (datestr) { return untilStringToDate(datestr); });\n}\n//# sourceMappingURL=rrulestr.js.map","import { __extends } from \"tslib\";\nimport { RRule } from './rrule';\nimport { sort, timeToUntilString } from './dateutil';\nimport { includes } from './helpers';\nimport { iterSet } from './iterset';\nimport { rrulestr } from './rrulestr';\nimport { optionsToString } from './optionstostring';\nfunction createGetterSetter(fieldName) {\n    var _this = this;\n    return function (field) {\n        if (field !== undefined) {\n            _this[\"_\".concat(fieldName)] = field;\n        }\n        if (_this[\"_\".concat(fieldName)] !== undefined) {\n            return _this[\"_\".concat(fieldName)];\n        }\n        for (var i = 0; i < _this._rrule.length; i++) {\n            var field_1 = _this._rrule[i].origOptions[fieldName];\n            if (field_1) {\n                return field_1;\n            }\n        }\n    };\n}\nvar RRuleSet = /** @class */ (function (_super) {\n    __extends(RRuleSet, _super);\n    /**\n     *\n     * @param {Boolean?} noCache\n     * The same stratagy as RRule on cache, default to false\n     * @constructor\n     */\n    function RRuleSet(noCache) {\n        if (noCache === void 0) { noCache = false; }\n        var _this = _super.call(this, {}, noCache) || this;\n        _this.dtstart = createGetterSetter.apply(_this, ['dtstart']);\n        _this.tzid = createGetterSetter.apply(_this, ['tzid']);\n        _this._rrule = [];\n        _this._rdate = [];\n        _this._exrule = [];\n        _this._exdate = [];\n        return _this;\n    }\n    RRuleSet.prototype._iter = function (iterResult) {\n        return iterSet(iterResult, this._rrule, this._exrule, this._rdate, this._exdate, this.tzid());\n    };\n    /**\n     * Adds an RRule to the set\n     *\n     * @param {RRule}\n     */\n    RRuleSet.prototype.rrule = function (rrule) {\n        _addRule(rrule, this._rrule);\n    };\n    /**\n     * Adds an EXRULE to the set\n     *\n     * @param {RRule}\n     */\n    RRuleSet.prototype.exrule = function (rrule) {\n        _addRule(rrule, this._exrule);\n    };\n    /**\n     * Adds an RDate to the set\n     *\n     * @param {Date}\n     */\n    RRuleSet.prototype.rdate = function (date) {\n        _addDate(date, this._rdate);\n    };\n    /**\n     * Adds an EXDATE to the set\n     *\n     * @param {Date}\n     */\n    RRuleSet.prototype.exdate = function (date) {\n        _addDate(date, this._exdate);\n    };\n    /**\n     * Get list of included rrules in this recurrence set.\n     *\n     * @return List of rrules\n     */\n    RRuleSet.prototype.rrules = function () {\n        return this._rrule.map(function (e) { return rrulestr(e.toString()); });\n    };\n    /**\n     * Get list of excluded rrules in this recurrence set.\n     *\n     * @return List of exrules\n     */\n    RRuleSet.prototype.exrules = function () {\n        return this._exrule.map(function (e) { return rrulestr(e.toString()); });\n    };\n    /**\n     * Get list of included datetimes in this recurrence set.\n     *\n     * @return List of rdates\n     */\n    RRuleSet.prototype.rdates = function () {\n        return this._rdate.map(function (e) { return new Date(e.getTime()); });\n    };\n    /**\n     * Get list of included datetimes in this recurrence set.\n     *\n     * @return List of exdates\n     */\n    RRuleSet.prototype.exdates = function () {\n        return this._exdate.map(function (e) { return new Date(e.getTime()); });\n    };\n    RRuleSet.prototype.valueOf = function () {\n        var result = [];\n        if (!this._rrule.length && this._dtstart) {\n            result = result.concat(optionsToString({ dtstart: this._dtstart }));\n        }\n        this._rrule.forEach(function (rrule) {\n            result = result.concat(rrule.toString().split('\\n'));\n        });\n        this._exrule.forEach(function (exrule) {\n            result = result.concat(exrule\n                .toString()\n                .split('\\n')\n                .map(function (line) { return line.replace(/^RRULE:/, 'EXRULE:'); })\n                .filter(function (line) { return !/^DTSTART/.test(line); }));\n        });\n        if (this._rdate.length) {\n            result.push(rdatesToString('RDATE', this._rdate, this.tzid()));\n        }\n        if (this._exdate.length) {\n            result.push(rdatesToString('EXDATE', this._exdate, this.tzid()));\n        }\n        return result;\n    };\n    /**\n     * to generate recurrence field such as:\n     * DTSTART:19970902T010000Z\n     * RRULE:FREQ=YEARLY;COUNT=2;BYDAY=TU\n     * RRULE:FREQ=YEARLY;COUNT=1;BYDAY=TH\n     */\n    RRuleSet.prototype.toString = function () {\n        return this.valueOf().join('\\n');\n    };\n    /**\n     * Create a new RRuleSet Object completely base on current instance\n     */\n    RRuleSet.prototype.clone = function () {\n        var rrs = new RRuleSet(!!this._cache);\n        this._rrule.forEach(function (rule) { return rrs.rrule(rule.clone()); });\n        this._exrule.forEach(function (rule) { return rrs.exrule(rule.clone()); });\n        this._rdate.forEach(function (date) { return rrs.rdate(new Date(date.getTime())); });\n        this._exdate.forEach(function (date) { return rrs.exdate(new Date(date.getTime())); });\n        return rrs;\n    };\n    return RRuleSet;\n}(RRule));\nexport { RRuleSet };\nfunction _addRule(rrule, collection) {\n    if (!(rrule instanceof RRule)) {\n        throw new TypeError(String(rrule) + ' is not RRule instance');\n    }\n    if (!includes(collection.map(String), String(rrule))) {\n        collection.push(rrule);\n    }\n}\nfunction _addDate(date, collection) {\n    if (!(date instanceof Date)) {\n        throw new TypeError(String(date) + ' is not Date instance');\n    }\n    if (!includes(collection.map(Number), Number(date))) {\n        collection.push(date);\n        sort(collection);\n    }\n}\nfunction rdatesToString(param, rdates, tzid) {\n    var isUTC = !tzid || tzid.toUpperCase() === 'UTC';\n    var header = isUTC ? \"\".concat(param, \":\") : \"\".concat(param, \";TZID=\").concat(tzid, \":\");\n    var dateString = rdates\n        .map(function (rdate) { return timeToUntilString(rdate.valueOf(), isUTC); })\n        .join(',');\n    return \"\".concat(header).concat(dateString);\n}\n//# sourceMappingURL=rruleset.js.map","import { rrulestr } from \"rrule\";\r\n\r\nimport { RRuleFinnish } from \"../../helpers\";\r\nimport { InputBase } from \"./_InputBase\";\r\n\r\n\r\n\r\n/**\r\n * Controller for Recurrence Rule (RRule) edit input\r\n */\r\n\r\nexport class InputRruleController extends InputBase<string> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [];\r\n\r\n  /**\r\n   * Creates a new InputController\r\n   * @ignore\r\n   */\r\n  constructor() {\r\n    super();\r\n  }\r\n\r\n  /**\r\n   * Gets the recurrence rule as human readable text.\r\n   * @param rrule The iCalendar Recurrence rule that should be interpreted.\r\n   */\r\n   public getRRuleText(rrule: string) {\r\n    const rule = rrulestr(rrule, {\r\n      // dtstart: Dates.asDate,\r\n    });\r\n    return rule.toText((id) => {\r\n      return RRuleFinnish.texts[id.toString()] || id.toString();\r\n    }, RRuleFinnish, (year: number, month: string, day: number) => {\r\n      return `${day}. ${month}ta ${year}`;\r\n    });\r\n  }\r\n}\r\n","import { DateTimes } from \"@salaxy/core\";\r\nimport { InputBase } from \"./_InputBase\";\r\n\r\n/**\r\n * Controller behind form controls that select time\r\n */\r\nexport class InputTimeController extends InputBase<string | number> {\r\n    /** Type of the input element. Options are minutes and isoTime */\r\n    public type: \"minutes\" | \"time\" = \"time\";\r\n\r\n    public _viewValue: Date;\r\n    public debug: any;\r\n\r\n    /** Sets the default values in init. */\r\n    public $onInit() {\r\n      super.$onInit();\r\n    }\r\n\r\n    /**\r\n     * Gets or sets the string value that is used in the view.\r\n     */\r\n    public get viewValue(): Date {\r\n      if (this.value) {\r\n        if (this.type === \"time\") {\r\n          if (this._viewValue?.getTime() !== DateTimes.fromTime(this.value as string).getTime()) {\r\n            this._viewValue = DateTimes.fromTime(this.value as string);\r\n          }\r\n        }\r\n\r\n        else if (this.type === \"minutes\") {\r\n          if (this._viewValue?.getTime() !== DateTimes.fromMinutes(this.value as number).getTime()) {\r\n            this._viewValue = DateTimes.fromMinutes(this.value as number);\r\n          }\r\n        }\r\n\r\n        return this._viewValue;\r\n      }\r\n      return null;\r\n    }\r\n    public set viewValue(value: Date) {\r\n      if (this.type === \"time\") {\r\n        this.value = DateTimes.asTime(value);\r\n      }\r\n\r\n      else if (this.type === \"minutes\") {\r\n        this.value = DateTimes.asMinutes(value);\r\n      }\r\n\r\n      this.onChange();\r\n    }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Arrays, InputEnumOption, Objects, Translations } from \"@salaxy/core\";\r\nimport { InputController } from \"./InputController\";\r\nimport { EnumerationsLogic } from \"@salaxy/core\";\r\n\r\nimport { createPopper } from \"@popperjs/core\";\r\n\r\n/**\r\n * Controller behind form controls that select an typeahead type.\r\n */\r\nexport class InputTypeaheadController extends InputController {\r\n\r\n  public static $inject = [\"$timeout\", \"$element\", \"$scope\"];\r\n\r\n  /** Options of the select control as a key-value object. */\r\n  protected _options: any;\r\n\r\n  /**\r\n   * Array or comma separated string to filter the option values to just the given ones.\r\n   * Also sets the order to this order, so works for ordering a given set of values.\r\n   */\r\n  public filter: string[];\r\n\r\n  /** If set to true, does not cache enums. */\r\n  public disableCache: boolean;\r\n\r\n  /**\r\n   * Label format for the option. The default format is to show only the text of the option.\r\n   * Options are:\r\n   * \"text\" or empty: only the text of the option is displayed.\r\n   * \"text-value\": in addition to the text, the value is also displayed in the label.\r\n   * \"value\": only the value is displayed.\r\n   * \"title\": Title (description of enumeration) if available. Defaults to text.\r\n   */\r\n  public labelFormat:  \"text\" | \"value\" | \"text-value\" | \"title\";\r\n\r\n  private enumCache: InputEnumOption[] = [];\r\n\r\n  /** List of typeahead options. */\r\n  public filteredItems: InputEnumOption[] = [];\r\n\r\n  /** Upon selecting a value from typeahead list, this function is triggered. */\r\n  public onSelectFunction?: (args?: any) => void;\r\n\r\n  /** Format values to a requried format. */\r\n  public inputFormatter?: (value: string | number) => string;\r\n\r\n  /** Function to get options for the typeahead list. */\r\n  public getOptions?: any;\r\n\r\n  /** Typeahead works as a \"forwarding\" element (searching for a value adds a row), not as an input field to which write values. */\r\n  public clearOnSelect: boolean = false;\r\n\r\n  /** Some typeahead inputs allow inserting values (such as tags) to database. */\r\n  public allowCustomValues: boolean = false;\r\n\r\n  /** Enums type typeahead, the enum options are fetched with EnumerationsLogic. */\r\n  public enum: any;\r\n\r\n  /** Object containing all data of typeahead selection. */\r\n  public objectData: any;\r\n\r\n  /** The typeahead result list. */\r\n  private resultList: HTMLElement;\r\n\r\n  /** The popper.js menu instance. */\r\n  private popperInstance: any;\r\n\r\n  /** True = return object as well alongside the typical value. */\r\n  public returnObject: boolean = false;\r\n\r\n  /** True = The value is saved as a whole object, false = as a primitive (string/number/etc. from the item key \"value\") */\r\n  public valueAsObject: boolean = false;\r\n\r\n  /** Event listener listens for key presses (Up, Down, Tab and Enter). This flags it's status to prevent multiple listeners due to possible race conditions. */\r\n  private isKeyListenerActive = false;\r\n\r\n  /** The <input> field which acts as the search field. */\r\n  private inputField: HTMLInputElement;\r\n\r\n  /** User-written text search string. */\r\n  public searchText: string = \"\";\r\n\r\n  /** Flag to make sure the list initializes only once. */\r\n  private isInitialized: boolean = false;\r\n\r\n  constructor(private $timeout: angular.ITimeoutService, private $element: JQLite, private $scope: any) {\r\n    super();\r\n  }\r\n\r\n  /** Sets the default values in init. */\r\n  public $onInit() {\r\n    if (this.enum) {\r\n      this.filteredItems = this.getEnumerations();\r\n    }\r\n    super.$onInit();\r\n    this.$timeout(() => {\r\n      if (this.value && typeof this.value === \"object\") {\r\n        this.value = (this.value as { value?: string; text?: string }).value ?? \"\";\r\n      }\r\n    });\r\n  }\r\n\r\n  /** Readable value of the chosen option. */\r\n  public get displayText() {\r\n    if (!this.value) return \"\";\r\n\r\n    let rawValue: string;\r\n\r\n    if (typeof this.value === \"object\") {\r\n      const valObj = this.value as { text?: string; value?: string };\r\n      rawValue = valObj.text || valObj.value || \"\";\r\n    } else {\r\n      rawValue = this.value;\r\n    }\r\n\r\n    return this.getEnumerationLabel(rawValue);\r\n  }\r\n\r\n  /** Delete dom stuff - click event, result list and popper instance - upon destroying of the component (for example changing the tab). */\r\n  public $onDestroy() {\r\n    if (this.resultList?.remove) {\r\n      this.resultList.remove();\r\n    }\r\n    this.popperInstance?.destroy();\r\n  }\r\n\r\n  /** Creates the result list popper element. */\r\n  private initResultList() {\r\n    if (this.isInitialized) return;\r\n\r\n    this.resultList = this.$element[0].querySelector(\".typeahead-result-list\");\r\n    this.inputField = this.$element[0].querySelector(\"input.typeahead-input\");\r\n    this.isInitialized = true;\r\n    const body = angular.element(document.body);\r\n\r\n    this.popperInstance = createPopper(\r\n      this.$element[0].querySelector(\".typeahead-wrapper\"),\r\n      this.resultList,\r\n      {\r\n        placement: \"bottom-start\",\r\n        modifiers: [\r\n          {\r\n            name: \"flip\",\r\n            enabled: false,\r\n          },\r\n        ],\r\n      }\r\n    );\r\n\r\n    body.append(this.resultList);\r\n\r\n    /** On-click event listener for hiding the results list. */\r\n    const onClick = (event: MouseEvent) => {\r\n      const target = event.target as Node;\r\n      if (!this.$element[0].contains(target) && this.resultList && !this.resultList.contains(target)) {\r\n        if (window.getComputedStyle(this.resultList).display !== \"none\") {\r\n          this.closeResultsList();\r\n        }\r\n      }\r\n    };\r\n\r\n    document.addEventListener(\"click\", onClick);\r\n\r\n    this.$scope.$on(\"$destroy\", () => {\r\n      this.popperInstance.destroy();\r\n      this.popperInstance = null;\r\n      document.removeEventListener(\"click\", onClick);\r\n    });\r\n  }\r\n\r\n  /** Show results list. */\r\n  private showResultsList() {\r\n    // Forced removal. Some modals have typeaheads whose ng-hides aren't removed on input click.\r\n    this.resultList.classList.remove(\"d-none\", \"ng-hide\", \"no-results\");\r\n\r\n    // Fixes the search result list height on tighter screens.\r\n    const refEl = this.popperInstance.state.elements.reference as HTMLElement;\r\n    const refRect = refEl.getBoundingClientRect();\r\n    const available = Math.round(window.innerHeight - (refRect.bottom + 10));\r\n    const clamped = Math.max(160, Math.min(480, available));\r\n\r\n    this.resultList.style.maxHeight = `${clamped}px`;\r\n\r\n    this.popperInstance.update();\r\n\r\n    if (!this.isKeyListenerActive) {\r\n      window.addEventListener(\"keydown\", this.onKeyDown);\r\n      this.isKeyListenerActive = true;\r\n    }\r\n\r\n    this.$timeout(() => {\r\n      const firstItem = this.resultList.children[0];\r\n      firstItem.classList.add(\"keyboard-selected\");\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Hide results list.\r\n   */\r\n  private closeResultsList() {\r\n    // If closing call came via event listener, timeout is needed so that AngularJS can detect it.\r\n    this.$timeout(() => {\r\n      this.filteredItems = [];\r\n      this.resultList.classList.add(\"d-none\");\r\n      this.resultList.classList.remove(\"no-results\");\r\n      window.removeEventListener(\"keydown\", this.onKeyDown);\r\n      this.isKeyListenerActive = false;\r\n      this.searchText = \"\";\r\n    });\r\n  }\r\n\r\n  /** Options list */\r\n  public get options(): any[] {\r\n    return this._options;\r\n  }\r\n  public set options(value: any[]) {\r\n    // Convert array of strings/numbers into objects.\r\n    if (Array.isArray(value) && value.length && typeof value[0] !== \"object\") {\r\n      value = value.map(v => ({ value: v, text: v }));\r\n    }\r\n\r\n    this._options = value;\r\n  }\r\n\r\n  /** Select an item from the typeahead list. */\r\n  public selectItem(item: any) {\r\n    // \"No selection\" selected from the list.\r\n    if (!item.value) {\r\n      this.clearValue(true);\r\n      this.closeResultsList();\r\n      return;\r\n    }\r\n\r\n    if (this.onSelectFunction) {\r\n      this.onSelectFunction(item.value);\r\n    }\r\n\r\n    this.value = this.valueAsObject ? item : item.value;\r\n\r\n    if (this.returnObject) {\r\n      // Data can be fetched asynchronously, so a timeout is needed.\r\n      this.$timeout(() => {\r\n        this.objectData = item.object;\r\n      });\r\n    }\r\n    // Update model and close the results list.\r\n    this.closeResultsList();\r\n    super.onChange();\r\n\r\n    // Special case: adding new calc rows via the typeahead requires clearing of the element.\r\n    if (this.clearOnSelect) {\r\n      this.$timeout(() => {\r\n        this.clearValue(false);\r\n        this.closeResultsList();\r\n      });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Gets the label for an enumeration.\r\n   * @param value Type of the enum.\r\n   */\r\n  public getEnumerationLabel(value: string): string {\r\n    if (this.inputFormatter) return this.inputFormatter(value);\r\n\r\n    const option = this.getEnumerations().find((x) => x.value === value);\r\n    return option ? this.formatLabel(option) : value;\r\n  }\r\n\r\n  /** Formats the label for display and typeahed searches. */\r\n  public formatLabel(option: InputEnumOption) {\r\n    switch(this.labelFormat) {\r\n      case \"value\":\r\n        return option.value;\r\n      case \"text-value\":\r\n        {\r\n          let text = option.text ? Translations.get(option.text) : option.text;\r\n          text = text ? text : option.value;\r\n          return `${text}${option.value ? \" (\" + option.value +\")\" : \"\"}`;\r\n        }\r\n      case \"title\":\r\n        return Translations.get(option.title) ?? Translations.get(option.text);\r\n      case \"text\":\r\n      default:\r\n        return Translations.get(option.text);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Returns items for current enumeration.\r\n   */\r\n  protected getEnumerations(): InputEnumOption[] {\r\n    if (this.enumCache.length > 0 && !this.disableCache) {\r\n      return this.enumCache;\r\n    }\r\n    let allValues: InputEnumOption[] = [];\r\n\r\n    if (this.options) {\r\n      if (Array.isArray(this.options)) {\r\n        allValues = this.options.map((item: any) => {\r\n          if (item == null) {\r\n            return { value: null, text: \"[null]\" };\r\n          }\r\n          if (Objects.has(item, \"value\") || Objects.has(item, \"text\")) {\r\n            return {\r\n              value: item.value,\r\n              text: item.text,\r\n              title: (item.title && item.title !== item.value) ? item.title : null,\r\n              ui: item.ui ? item.ui : null\r\n            };\r\n          }\r\n          return { value: item, text: item };\r\n        });\r\n      } else {\r\n        allValues = Object.keys(this.options).map((key) => ({ value: key, text: this.options[key], title: null }));\r\n      }\r\n    } else if (this.enum) {\r\n      const enums = EnumerationsLogic.getEnumMetadata(this.enum);\r\n      if (enums) {\r\n        allValues = enums.values\r\n          .map((e) => ({\r\n            value: e.name,\r\n            text: e.label,\r\n            title: e.descr && e.descr !== e.name ? e.descr : null\r\n          }));\r\n      } else {\r\n        allValues = [{\r\n          value: \"\",\r\n          text: `ERROR: ${this.enum} not found.`,\r\n          title: null,\r\n        }];\r\n      }\r\n    }\r\n\r\n    const filterArr = Arrays.assureArray(this.filter);\r\n    if (filterArr.length > 0) {\r\n      allValues = filterArr.map((x) => allValues.find((y) => y.value === x)).filter((x) => x != null);\r\n    }\r\n    this.modifyOptions(allValues, this.enumCache);\r\n    return this.enumCache;\r\n  }\r\n\r\n  private modifyOptions(\r\n    source: ({\r\n      /** Enum value. */\r\n      value: any,\r\n      /** Label for the value. */\r\n      text: string,\r\n      /** Description for the value. */\r\n      title?: string,\r\n    })[],\r\n    target: ({\r\n      /** Enum value. */\r\n      value: any,\r\n      /** Label for the value. */\r\n      text: string,\r\n      /** Description for the value. */\r\n      title?: string,\r\n    })[]) {\r\n    // check if source values differ from target\r\n    const ok = angular.equals(source, target);\r\n\r\n    if (ok) {\r\n      return;\r\n    }\r\n    // remove values\r\n    target.splice(0, target.length);\r\n\r\n    // add values\r\n    target.push(...source);\r\n  }\r\n\r\n  /** Filter items based on the input query */\r\n  public filterEnumItems(showAll: boolean) {\r\n    if (showAll) {\r\n      this.filteredItems = this.getEnumerations();\r\n    } else {\r\n      if (!this.value) {\r\n        this.filteredItems = this.getEnumerations();\r\n      } else {\r\n        const allItems = this.getEnumerations();\r\n\r\n        this.filteredItems = allItems.filter(item => {\r\n          const text = Translations.get(item.text) ?? \"\";\r\n          const title = item.title ? Translations.get(item.title) ?? \"\" : \"\";\r\n\r\n          return text.toLowerCase().includes(this.value.toLowerCase()) || title.toLowerCase().includes(this.value.toLowerCase());\r\n        });\r\n      }\r\n    }\r\n  }\r\n\r\n  /** Reacts to the changing input value. */\r\n  public async onInputChange(): Promise<void> {\r\n    if (this.getOptions) {\r\n      this.filteredItems = await Promise.resolve(this.getOptions(this.searchText));\r\n    } else if (this.options) {\r\n      this.filteredItems = this.options.filter(option => {\r\n        return option.text?.toLowerCase().includes(this.searchText.toLowerCase()) || option.title?.toLowerCase().includes(this.searchText.toLowerCase()) || option.value?.toLowerCase().includes(this.searchText.toLowerCase());\r\n      });\r\n    } else {\r\n      this.filterEnumItems(false);\r\n    }\r\n\r\n    if (this.filteredItems.length > 0) {\r\n      this.showResultsList();\r\n    } else {\r\n      if (this.allowCustomValues && this.searchText) {\r\n        return;\r\n      }\r\n      // Wait for the search results to update before proceeding.\r\n      this.$timeout(() => {\r\n        this.filteredItems.push({ value: null, text: Translations.get(\"SALAXY.UI_Terms.noResults\") });\r\n        this.resultList.classList.add(\"no-results\");\r\n      });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Clears the selected value in the input field.\r\n   */\r\n  public clearValue(updateModel = true): void {\r\n    this.$timeout(() => {\r\n      this.value = \"\";\r\n      if (updateModel) {\r\n        super.onChange();\r\n      }\r\n\r\n      if (this.returnObject) {\r\n        this.objectData = {};\r\n      }\r\n    });\r\n  }\r\n\r\n  /** Show all typeahead results (that are currently at hand).*/\r\n  public async openResultsList() {\r\n    this.initResultList();\r\n\r\n    if (this.options) {\r\n      this.filteredItems = this.options;\r\n    } else if (this.getOptions) {\r\n      this.filteredItems = await Promise.resolve(this.getOptions());\r\n    } else if (this.enum) {\r\n      this.filteredItems = this.getEnumerations();\r\n    }\r\n\r\n    if (this.resultList && this.inputField) {\r\n      this.showResultsList();\r\n      this.inputField.focus({ preventScroll: true });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Method to register key down events (arrows Up/Down + Enter are supported).\r\n   * @param event Captured keyboard event.\r\n   */\r\n  private onKeyDown = (event: KeyboardEvent) => {\r\n    if (this.resultList && [\"ArrowUp\", \"ArrowDown\", \"Enter\", \"Tab\"].includes(event.key)) {\r\n      // Tab hides the results list, as the user keyboard-navigates out of the input field.\r\n      if (event.key == \"Tab\") {\r\n        this.closeResultsList();\r\n        return;\r\n      }\r\n      let currentSelected: Element;\r\n      let currentIndex: number;\r\n\r\n      for (let i = 0; i < this.resultList.children.length; i++) {\r\n        const el = this.resultList.children[i];\r\n        if (el.classList.contains(\"keyboard-selected\")) {\r\n          currentSelected = el;\r\n          currentIndex = i;\r\n          break;\r\n        }\r\n      }\r\n\r\n      // Select the currently selected item.\r\n      if (event.key == \"Enter\" && currentSelected && getComputedStyle(this.resultList).display !== \"none\") {\r\n        (currentSelected as HTMLElement).click();\r\n        this.inputField.blur();\r\n      // Shuffle through the list with arrow keys.\r\n      } else {\r\n        if (event.key == \"ArrowUp\" && currentIndex > 0) {\r\n          currentIndex--;\r\n        } else if (event.key == \"ArrowDown\" && currentIndex < this.resultList.children.length-1) {\r\n          currentIndex++;\r\n        }\r\n\r\n        if (currentSelected) {\r\n          currentSelected.classList.remove(\"keyboard-selected\");\r\n        }\r\n        this.resultList.children[currentIndex].classList.add(\"keyboard-selected\");\r\n        this.resultList.children[currentIndex].scrollIntoView({ block: \"nearest\" });\r\n      }\r\n    }\r\n  };\r\n}","import angular from \"angular\";\r\n\r\n/**\r\n * Controller for (radio button-like) toggle buttons.\r\n */\r\nexport class ToggleButtonsController implements angular.IController {\r\n  public model: angular.INgModelController;\r\n\r\n  /** The options to be displayed in the toggle buttons. For each given value, a new button is created. */\r\n  public options: { value: string, label: string }[];\r\n\r\n  /** Types supported: \"row\" - toggle buttons visualized as blocks with an image, \"inline\" - text-only blocks in a row, \"block\" - text-only blocks on top of each other.  */\r\n  public type: string;\r\n\r\n  /** Toggle button's optional image. */\r\n  public imgSrc: string;\r\n\r\n  constructor() {}\r\n\r\n  /**\r\n   * Handles the click event for the toggle button.\r\n   * @param {string} value - The value to set for the ngModel.\r\n   */\r\n  public onClick(value: string) {\r\n    this.model.$setViewValue(value);\r\n  }\r\n}","import angular from \"angular\";\r\n\r\nimport { ApiValidation, ApiValidationError, ApiValidationErrorType, Translations } from \"@salaxy/core\";\r\n\r\nimport { UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Handles user interaction for viewing and modifying the current account data\r\n * including the products that are enabled for the current account and their properties.\r\n */\r\nexport class ValidationSummaryController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"UiHelpers\"];\r\n\r\n  /** The server-side API-validation object that is displayed by this controller. */\r\n  public apiValidation: ApiValidation;\r\n\r\n  /** HTML that should be shown when the bound validation data is null */\r\n  public loadingHtml: \"SALAXY.NG1.ValidationSummaryComponent.loadingHtml\";\r\n\r\n  /** Layout of the validation html. Use \"minimal\" for easy customizing */\r\n  public layout: \"default\" | \"minimal\"  = \"default\";\r\n\r\n  constructor(\r\n    private uiHelpers: UiHelpers,\r\n  ) {\r\n    // constructor code.\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit = () => { /* init code here */\r\n  if(this.layout != \"minimal\"){\r\n    this.layout = \"default\";\r\n    }\r\n  };\r\n\r\n  /** If false, there is no validation object bound to the component. */\r\n  public get hasValidation(): boolean {\r\n    return !!this.apiValidation;\r\n  }\r\n\r\n  /** If true, the validation has no errors. */\r\n  public get isValid(): boolean {\r\n    return this.getValidation().isValid;\r\n  }\r\n\r\n  /** If false, has empty required fields. These are shown separately from other errors. */\r\n  public get hasAllRequiredFields(): boolean {\r\n    return this.apiValidation?.hasAllRequiredFields ?? false;\r\n  }\r\n\r\n  /** If true, there is no errors, but there are some warnings.  */\r\n  public get hasWarningsOnly(): boolean {\r\n    return (this.apiValidation?.errors ?? []).length > 0 && this.apiValidation.errors.every((x) => x.type == ApiValidationErrorType.Warning);\r\n  }\r\n\r\n  /** If true, has other errors than missing required fiels. */\r\n  public get hasValidationOrGeneralErrors(): boolean {\r\n    return this.getErrors(\"!required\").length > 0;\r\n  }\r\n\r\n  /**\r\n   * Gets the errors, optionally filtered by a type.\r\n   * @param type Type of the error: \"general\", \"required\", \"invalid\" or null.\r\n   * If null, all errors are returned.\r\n   * Also supports negation: \"!general\", \"!required\" or \"!invalid\".\r\n   */\r\n  public getErrors(type?: ApiValidationErrorType | string): ApiValidationError[] {\r\n    const errors = this.getValidation().errors || [];\r\n    if (type) {\r\n      if (type.toString().startsWith(\"!\")) {\r\n        type = type.substr(1);\r\n        return errors.filter((x) => x.type !== type) || [];\r\n      } else {\r\n        return errors.filter((x) => x.type === type) || [];\r\n      }\r\n    }\r\n    return errors || [];\r\n  }\r\n\r\n  /**\r\n   * Returns the label for the validation result.\r\n   * The label is translated using the key: `SALAXY.VALIDATION.[error.code].label`\r\n   * If the translation does not exist the `error.msg` is returned.\r\n   * @param error - Error in validation.\r\n   */\r\n  public getLabel(error: ApiValidationError): string {\r\n    const labelKey = \"SALAXY.VALIDATION.\" + error.code + \".label\";\r\n    return Translations.getWithDefault(labelKey) || error.msg || \"❗ERROR\";\r\n  }\r\n\r\n  /**\r\n   * Returns the description for the validation result.\r\n   * The label is translated using the key: `SALAXY.VALIDATION.[error.code].description`\r\n   * If the translation does not exist the `null` is returned.\r\n   * @param error - Error in validation.\r\n   */\r\n  public getDescription(error: ApiValidationError): string {\r\n    const descriptionKey = \"SALAXY.VALIDATION.\" + error.code + \".description\";\r\n    return Translations.getWithDefault(descriptionKey) || error.description;\r\n  }\r\n\r\n  /**\r\n   * Returns true if the translation for the key `SALAXY.VALIDATION.[error.code].description` exists.\r\n   * @param error - Error in validation.\r\n   */\r\n  public hasDescription(error: ApiValidationError): boolean {\r\n    return !!this.getDescription(error);\r\n  }\r\n\r\n  /** Shows details of the errors. */\r\n  public showDetails() {\r\n    this.uiHelpers.showDialog(\r\n      `salaxy-components/form-controls/ValidationSummaryDetails.html`,\r\n      null, // controller\r\n      {\r\n        controller: () => this,\r\n      },\r\n      null, // window template URL\r\n    );\r\n  }\r\n\r\n  private getValidation(): ApiValidation {\r\n    return this.apiValidation || {\r\n      errors: [],\r\n      hasAllRequiredFields: true,\r\n      isValid: false,\r\n    };\r\n  }\r\n\r\n}\r\n","import { InputBase } from \"./_InputBase\";\r\n\r\n/**\r\n * Controller behind form control which edits/displays holiday pay calculation multipliers.\r\n */\r\n\r\nexport class InputHolidayMultipliersController extends InputBase<any> {\r\n\r\n  /** Set the values and defaults on init */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Delete one multiplier */\r\n  public delete(key: string) {\r\n    delete this.value[key];\r\n    this.onChange();\r\n  }\r\n\r\n  /** Add one multiplier */\r\n  public createNew() {\r\n    let newKey = 1;\r\n    if (!this.value) {\r\n      this.value = {};\r\n    }\r\n    for(const key in this.value) {\r\n      const keyValue = Number.parseInt(key);\r\n      if ( keyValue >= newKey) {\r\n        newKey = keyValue + 1;\r\n      }\r\n    }\r\n    this.value[newKey] = 0;\r\n    this.onChange();\r\n  }\r\n\r\n  /** On key changed event. */\r\n  public onKeyChanged(key: string, newKey: string) {\r\n    if (key !== newKey) {\r\n      const value = this.value[key];\r\n      delete this.value[key];\r\n      this.value[newKey] = value;\r\n    }\r\n    this.onChange();\r\n  }\r\n}\r\n","import {CalculationRowType, IncomeTypesLogic, EnumerationsLogic, CalcRowsLogic, Translations} from \"@salaxy/core\";\r\nimport { EditDialogKnownActions, UiHelpers, RowTypeService } from \"../../services\";\r\nimport { InputController } from \"./InputController\";\r\n\r\n/**\r\n * Controller behind form control which edits/displays row types for pay stats calculations.\r\n */\r\n\r\nexport class InputPayStatsRowTypeController extends InputController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"UiHelpers\", \"RowTypeService\"];\r\n\r\n\r\n  constructor(private uiHelpers: UiHelpers, private rowTypeService: RowTypeService) {\r\n    super();\r\n  }\r\n\r\n  /** Set the values and defaults on init */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Returns true if this is an exclusive row type.  */\r\n  public get isExclusive(): boolean {\r\n    return (this.value ?? \"\").startsWith(\"!\");\r\n  }\r\n\r\n  /** Returns text for the row type */\r\n  public get text(): string {\r\n    // Possible types\r\n    /*\r\n    incomeType.[code]\r\n    incomeType.[code]-[unit]\r\n\r\n    rowType.[rowType]\r\n    rowType.[rowType].[kind]\r\n\r\n    rowType.[rowType]-[unit]\r\n    rowType.[rowType].[kind]-[unit]\r\n\r\n    type.[type]\r\n    type.[type]/[kind]\r\n\r\n    type.[type]-[unit]\r\n    type.[type]/[kind]-[unit]\r\n\r\n    */\r\n\r\n    if (!this.value) {\r\n      return \"\";\r\n    }\r\n\r\n    const types = this.parseRowType(this.value);\r\n    switch(types.baseType) {\r\n      case \"rowType\":\r\n        return Translations.get(\"SALAXY.NG1.WorkerHolidaysComponent.UI.inputs.rowType\") + \": \" + this.getCalculationRowTypeLabel(types.type as CalculationRowType, types.kind) + (types.unit ? ` (${EnumerationsLogic.getEnumLabel(\"CalculationRowUnit\", types.unit, null, null)})` : \"\");\r\n      case \"incomeType\":\r\n        {\r\n          const incomeType = IncomeTypesLogic.getAll(null).find( (x) => (x.code + \"\") == types.type);\r\n          return \"Tulolaji: \" + `${incomeType?.code} - ` + incomeType?.label + (types.unit ? ` (${EnumerationsLogic.getEnumLabel(\"CalculationRowUnit\", types.unit, null, null)})` : \"\");\r\n        }\r\n      case \"type\":\r\n        return Translations.get(\"SALAXY.NG1.WorkerHolidaysComponent.UI.inputs.wageType\") + \": \" + types.type + (types.kind ? `/${types.kind}`:\"\") + (types.unit ? ` (${EnumerationsLogic.getEnumLabel(\"CalculationRowUnit\", types.unit, null, null)})` : \"\");\r\n    }\r\n  }\r\n\r\n  /** Edit entry. */\r\n  public edit() {\r\n    const rowTypeService = this.rowTypeService;\r\n    const logic = {\r\n      readOnly: this.getReadOnly(),\r\n      _userDefinedRow:{\r\n        item: null,\r\n        row: {\r\n          data: {\r\n            get kind() {\r\n              return logic._userDefinedRow.item.kind;\r\n            },\r\n            set kind(value) {\r\n              logic._userDefinedRow.item.kind = value;\r\n            },\r\n          },\r\n          get rowType() {\r\n            if (logic._userDefinedRow.item.baseType == \"type\") {\r\n              if (!logic._userDefinedRow.item._type && logic._userDefinedRow.item.type) {\r\n               logic._userDefinedRow.item._type = rowTypeService.getConfigs().find(x => x.type == logic._userDefinedRow.item.type)?.rowType;\r\n              }\r\n              return logic._userDefinedRow.item._type;\r\n            }\r\n            else\r\n            {\r\n              return logic._userDefinedRow.item.type;\r\n            }\r\n          },\r\n          set rowType(value) {\r\n            if (logic._userDefinedRow.item.baseType == \"type\") {\r\n              logic._userDefinedRow.item._type = value;\r\n            }\r\n            else\r\n            {\r\n              logic._userDefinedRow.item.type = value;\r\n            }\r\n          },\r\n          get type() {\r\n            if (logic._userDefinedRow.item.baseType == \"type\") {\r\n              return logic._userDefinedRow.item.type;\r\n            }\r\n            else\r\n            {\r\n              return logic._userDefinedRow.item._type;\r\n            }\r\n          },\r\n          set type(value) {\r\n            if (logic._userDefinedRow.item.baseType == \"type\") {\r\n              logic._userDefinedRow.item.type = value;\r\n            }\r\n            else\r\n            {\r\n              logic._userDefinedRow.item._type = value;\r\n            }\r\n          }\r\n        }\r\n      },\r\n      asUserDefinedRow: (item ) => {\r\n        logic._userDefinedRow.item = item;\r\n        return logic._userDefinedRow.row;\r\n      }\r\n    };\r\n    this.uiHelpers.openEditDialog(\r\n      \"salaxy-components/modals/form-controls/PayStatsRowTypeEdit.html\",\r\n      this.parseRowType(this.value),\r\n      logic\r\n      ).then((result) => {\r\n        if (result.action === EditDialogKnownActions.Ok) {\r\n          this.value = result.item.baseType == \"type\" ? this.composeType(result.item): this.composeRowType(result.item);\r\n          this.onChange();\r\n        }\r\n      });\r\n  }\r\n\r\n  private getCalculationRowTypeLabel(rowType: CalculationRowType, kind: string): string {\r\n    let label = \"\";\r\n    if (rowType === CalculationRowType.IrIncomeType) {\r\n      label = IncomeTypesLogic.getAll(null).find( (x) => (kind && x.transactionCode === kind))?.label;\r\n    }\r\n    else if (kind) {\r\n      const rowConfig = CalcRowsLogic.getRowConfig(rowType);\r\n      label =  EnumerationsLogic.getEnumLabel(rowConfig.kind.name, kind, null, null);\r\n    }\r\n    return label || EnumerationsLogic.getEnumLabel(\"CalculationRowType\", rowType, null, null);\r\n\r\n  }\r\n\r\n  private parseRowType(value: string): {baseType?: string, type?: string, kind?: string, unit?: string, isExclusive?: boolean} {\r\n    // Possible types\r\n    /*\r\n    incomeType.[code]\r\n    incomeType.[code]-[unit]\r\n\r\n    rowType.[rowType]\r\n    rowType.[rowType].[kind]\r\n\r\n    rowType.[rowType]-[unit]\r\n    rowType.[rowType].[kind]-[unit]\r\n\r\n    type.[type]\r\n    type.[type]/[kind]\r\n\r\n    type.[type]-[unit]\r\n    type.[type]/[kind]-[unit]\r\n\r\n    */\r\n    if (!value) {\r\n      return { isExclusive: false};\r\n    }\r\n\r\n    let isExclusive = false;\r\n    let unit = \"\";\r\n    let kind = \"\";\r\n    let type = \"\";\r\n    if (value.startsWith(\"!\")) {\r\n      isExclusive = true;\r\n      value = value.substring(1);\r\n    }\r\n\r\n    const baseType = value.split(\".\")[0];\r\n\r\n    if (value.lastIndexOf(\"-\") > 0) {\r\n      unit = value.substring(value.lastIndexOf(\"-\") + 1);\r\n      value = value.substring(0, value.lastIndexOf(\"-\"));\r\n    }\r\n\r\n    switch(baseType) {\r\n      case \"incomeType\":\r\n        type = value.split(\".\")[1];\r\n        // ok\r\n        break;\r\n      case \"rowType\":\r\n        {\r\n          const dotParts = value.split(\".\");\r\n          type = dotParts[1];\r\n          if (dotParts.length == 3) {\r\n            kind = dotParts[2];\r\n          }\r\n        }\r\n        break;\r\n      case \"type\":\r\n        {\r\n          const fullType = value.substring(value.indexOf(\".\") + 1);\r\n          const nameParts = fullType.split(\"/\");\r\n          if (nameParts.length >= 3) {\r\n            type = \"/\" + nameParts[1] + \"/\" + nameParts[2];\r\n          }\r\n          if (nameParts.length == 4) {\r\n            kind = nameParts[3];\r\n          }\r\n        }\r\n        break;\r\n    }\r\n\r\n    return {baseType, type, kind, unit, isExclusive};\r\n  }\r\n\r\n  private composeRowType(types: {baseType?: string, type?: string, kind?: string, unit?: string, isExclusive?: boolean}): string {\r\n    if (!types?.baseType || !types?.type) {\r\n      return \"\";\r\n    }\r\n    let rowType = `${types.baseType}.${types.type}`;\r\n    if (types.kind) {\r\n      rowType += `.${types.kind}`;\r\n    }\r\n    if (types.unit && types.unit !== \"undefined\") {\r\n      rowType += `-${types.unit}`;\r\n    }\r\n    if (types.isExclusive) {\r\n      rowType = \"!\" + rowType;\r\n    }\r\n    return rowType;\r\n  }\r\n\r\n  private composeType(types: {baseType?: string, type?: string, kind?: string, unit?: string, isExclusive?: boolean}): string {\r\n    if (!types?.baseType || !types?.type) {\r\n      return \"\";\r\n    }\r\n    let wageType = `${types.baseType}.${types.type}`;\r\n    if (types.kind) {\r\n      wageType += `/${types.kind}`;\r\n    }\r\n    if (types.unit && types.unit !== \"undefined\") {\r\n      wageType += `-${types.unit}`;\r\n    }\r\n    if (types.isExclusive) {\r\n      wageType = \"!\" + wageType;\r\n    }\r\n    return wageType;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\nimport { SettingsService } from \"../../services\";\r\nimport { InputEnumController } from \"./InputEnumController\";\r\nimport { EmployeeGroupDefinition } from \"@salaxy/core\";\r\n\r\n/**\r\n * Controller for selecting an employee group.\r\n */\r\n\r\nexport class InputEmployeeGroupController extends InputEnumController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$scope\", \"SettingsService\"];\r\n\r\n  private employeeGroups: EmployeeGroupDefinition[] = [];\r\n\r\n  /**\r\n   * Creates a new InputOccupationTypeController\r\n   * @ignore\r\n   */\r\n  constructor(private $scope: angular.IScope, private settingsService: SettingsService) {\r\n    super();\r\n  }\r\n\r\n  /** Options list */\r\n  public get options(): any[] {\r\n    const newEmployeeGroups = this.settingsService.current?.calc?.employeeGroups || [];\r\n    if (!angular.equals(this.employeeGroups, newEmployeeGroups)) {\r\n      this._options = newEmployeeGroups.map( (x) => {\r\n        return {\r\n          value: x.id,\r\n          text: x.name,\r\n        };\r\n      });\r\n    }\r\n    return this._options;\r\n  }\r\n  public set options(value: any[]) {\r\n    // empty on purpose\r\n    // this._options = value;\r\n  }\r\n}\r\n","import {InputController} from \"./InputController\";\r\n\r\ndeclare const toastui: any;\r\n\r\n/** Markdown Editor */\r\nexport class MarkdownEditorController extends InputController {\r\n\r\n  private _value: string;\r\n  private editor: any;\r\n\r\n  public static $inject = [\"$element\", \"$scope\", \"$attrs\", \"$timeout\"];\r\n\r\n  /**\r\n   * Creates a new MarkdownEditorController\r\n   * @ignore\r\n   */\r\n  constructor(private $element: JQLite, private $scope: angular.IScope, private $attrs: angular.IAttributes, private $timeout: angular.ITimeoutService) {\r\n    super();\r\n  }\r\n\r\n  /** Init */\r\n  public $onInit = () => {\r\n    super.$onInit();\r\n    this.editor = toastui.Editor.factory({\r\n      el: this.$element[0].querySelector(\"#editor\"),\r\n      viewer: false,\r\n      height: \"500px\",\r\n      initialEditType: \"wysiwyg\",\r\n      previewStyle: \"vertical\",\r\n      hideModeSwitch: true,\r\n    });\r\n    this.editor.addHook(\"change\", () =>  {\r\n      this._value = this.editor.getMarkdown();\r\n      this.value = this._value;\r\n      this.onChange();\r\n    });\r\n    this.$scope.$watch(this.$attrs.ngModel, (newValue) => {\r\n      this.changeValue(newValue as any);\r\n    });\r\n  };\r\n\r\n  /** Value initialization */\r\n  public onInitValue(){\r\n    this.changeValue(this.value);\r\n  }\r\n\r\n  /** New value */\r\n  public changeValue(newValue: string) {\r\n    if (newValue == this._value) {\r\n      return;\r\n    }\r\n    this._value = newValue;\r\n    this.editor.setMarkdown(newValue);\r\n    this.$timeout();\r\n  }\r\n}\r\n\r\n","import {InputController} from \"./InputController\";\r\n\r\ndeclare const toastui: any;\r\n\r\n/** Markdown Editor */\r\nexport class MarkdownViewerController extends InputController {\r\n\r\n  private editor: any;\r\n\r\n  public static $inject = [\"$element\", \"$scope\", \"$attrs\", \"$timeout\"];\r\n\r\n  /**\r\n   * Creates a new MarkdownEditorController\r\n   * @ignore\r\n   */\r\n  constructor(private $element: JQLite, private $scope: angular.IScope, private $attrs: angular.IAttributes, private $timeout: angular.ITimeoutService) {\r\n    super();\r\n  }\r\n\r\n  /** Init */\r\n  public $onInit = () => {\r\n    super.$onInit();\r\n    this.editor = toastui.Editor.factory({\r\n      el: this.$element[0].querySelector(\"#viewer\"),\r\n      viewer: true,\r\n      height: \"500px\",\r\n      initialEditType: \"wysiwyg\",\r\n      previewStyle: \"vertical\"\r\n    });\r\n    this.$scope.$watch(this.$attrs.ngModel, (newValue) => {\r\n        this.changeValue(newValue as any);\r\n    });\r\n  };\r\n\r\n  /** Value initialization */\r\n  public onInitValue(){\r\n    this.changeValue(this.value);\r\n  }\r\n\r\n  /** New value */\r\n  public changeValue(newValue: string) {\r\n    this.editor.setMarkdown(newValue);\r\n    this.$timeout();\r\n  }\r\n}\r\n\r\n","import angular from \"angular\";\r\nimport { Configs } from \"@salaxy/core\";\r\n/**\r\n * Controller for action button\r\n */\r\nexport class ActionButtonController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [];\r\n\r\n  /** Text for the button */\r\n  public label: string;\r\n\r\n  /** Additional Bootstrap or custom style classes. I.e. btn-danger, btn-sm, my-btn. Defaults to btn-primary. */\r\n  public buttonClass: string;\r\n\r\n  /**\r\n   * Action to be executed.\r\n   * newCalc: starts a new blank calculation.\r\n   * newCalcForEmployment: starts a new calculation for the given employment ID.\r\n   * newPayroll: starts a new blank payroll.\r\n   * newWorker: opens workerWizard for creating a new worker.\r\n   * newMessage: starts a new message thread with partner.\r\n   * payment: opens the payment dialog for the current calculation.\r\n   * newTaxcard: Links to taxcards page. Currently supported only when role is Worker.\r\n   * newRepair: starts a new repair process for a calculation.\r\n   */\r\n  public action: \"newCalc\" | \"newCalcForEmployment\" | \"newPayroll\" | \"newWorker\" | \"newMessage\" | \"payment\" | \"newTaxcard\" | \"newRepair\";\r\n\r\n  /** Disabled but visible */\r\n  public disabled?: boolean;\r\n\r\n  /** Optional options for button. */\r\n  public options?: {\r\n    /**\r\n     * id: id of current item such as Employment or Calculation. Currently used only in newCalcForEmployment action.\r\n     */\r\n    id: string,\r\n  };\r\n\r\n  /**\r\n   * Function that is called after the function. This is typically used for navigation or a list reload.\r\n   */\r\n  public onAfterAction: () => Promise<void>;\r\n\r\n  /**\r\n   * Creates a new InputController\r\n   * @ignore\r\n   */\r\n  constructor() {\r\n    //\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit = () => {\r\n    this.buttonClass = this.buttonClass || \"btn-primary\";\r\n  };\r\n\r\n  /**\r\n   * Returns environment based on config.\r\n   * TODO: Replace this with ConfigsLogic\r\n   */\r\n  public getEnv(): \"local\" | \"test\" | \"demo\" | \"prod\" | \"rc\" {\r\n    const config = Configs.current;\r\n    if (!config.isTestData) {\r\n      return \"prod\";\r\n    }\r\n    if (config.apiServer?.indexOf(\"localhost\") > -1  ) {\r\n      return \"local\";\r\n    }\r\n    if (config.integrationsServer?.indexOf(\"test\") > -1  ) {\r\n      return \"test\";\r\n    }\r\n    if (config.apiServer?.indexOf(\"rc\") > -1  ) {\r\n      return \"rc\";\r\n    }\r\n    return \"demo\";\r\n  }\r\n\r\n}\r\n","import angular from \"angular\";\r\n\r\n/**\r\n * Controller rendering an Alert box in the page area.\r\n */\r\nexport class AlertController implements angular.IController {\r\n\r\n    /**\r\n     * For NG-dependency injection\r\n     * @ignore\r\n     */\r\n    public static $inject = [\"$transclude\"];\r\n\r\n    /** Type of the alert is the Bootstrap style: Note that also \"primary\" and \"default\" are supported. */\r\n    public type: \"default\" | \"primary\" | \"success\" | \"info\" | \"warning\" | \"danger\";\r\n\r\n    /**\r\n     * Alert main content as simple text.\r\n     * You can alternatively provide html as main element.\r\n     * NOTE: If necessary we could provide a html property to bind from JavaScript and to allow HTML in the binded content.\r\n     */\r\n    public text: string;\r\n\r\n    /**\r\n     * Possibility to speicfy a font-awesome icon.\r\n     * Setting \"none\", will show no icon.\r\n     * If not set, it is determined by type.\r\n     */\r\n    public icon: \"none\" | string;\r\n\r\n    /** If true (and hasMoreInfo is true), the more info html is shown. */\r\n    public showMoreInfo: boolean;\r\n\r\n    /** If true, the aside part is shown immidiately. Also hides \"read more\"- button. */\r\n    public forceMoreInfo = false;\r\n\r\n    /**\r\n     * Creates a new AlertController\r\n     * @ignore\r\n     */\r\n    constructor(private $transclude: angular.ITranscludeFunction) {\r\n     }\r\n\r\n    /**\r\n     * Implement IController\r\n     */\r\n    public $onInit = () => {\r\n        // initialization\r\n    };\r\n\r\n    /** Returns true if details part (aside element) is filled / \"More info\" button should be shown. */\r\n    public get hasMoreInfo() {\r\n        return this.$transclude.isSlotFilled(\"aside\");\r\n    }\r\n\r\n    /** Returns the icon based on the type. */\r\n    public getIcon() {\r\n        if (!this.icon) {\r\n            switch (this.type) {\r\n                case \"danger\":\r\n                    return \"bi-exclamation-lg\";\r\n                case \"success\":\r\n                    return \"bi-check-lg\";\r\n                case \"warning\":\r\n                    return \"bi-exclamation-triangle-fill\";\r\n                default:\r\n                    return \"bi-info\";\r\n            }\r\n        }\r\n        if (this.icon === \"none\") {\r\n            return null;\r\n        }\r\n        return this.icon;\r\n    }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {AvatarPictureType} from \"@salaxy/core\";\r\n\r\n/**\r\n * Controller rendering a Salaxy account Avatar (image for the person / company).\r\n */\r\nexport class AvatarController implements angular.IController {\r\n\r\n    /**\r\n     * For NG-dependency injection\r\n     * @ignore\r\n     */\r\n    public static $inject = [];\r\n\r\n    /** The Avatar object which the controller is rendering */\r\n    public avatar: any;\r\n\r\n    /**\r\n     * Creates a new AvatarController\r\n     * @ignore\r\n     */\r\n    constructor() {\r\n        //\r\n     }\r\n\r\n    /**\r\n     * Implement IController\r\n     */\r\n    public $onInit = () => {\r\n        // initialization\r\n     };\r\n\r\n    /** Returns true if the avatar is an image url (as opposed to icon rendering) */\r\n    public get isImage(): boolean {\r\n        return this.avatar != null\r\n            && ( this.avatar.pictureType === AvatarPictureType.Uploaded || this.avatar.pictureType === AvatarPictureType.Gravatar)\r\n            && this.avatar.url != null\r\n            && this.avatar.url.substr(0, 4).toLowerCase() === \"http\"\r\n            ;\r\n    }\r\n\r\n    /** Returns true if the avatar should be rendered as a person icon */\r\n    public get isPersonIcon(): boolean {\r\n        return this.avatar != null && !this.isImage && this.avatar.entityType !== \"company\";\r\n    }\r\n\r\n    /** Returns true if the avatar should be rendered as a company icon */\r\n    public get isCompanyIcon(): boolean {\r\n        return this.avatar == null || (!this.isImage && this.avatar.entityType === \"company\");\r\n    }\r\n\r\n    /** Returns the avatar color or 'gray' if nothing is defined. */\r\n    public get color(): string {\r\n        if (this.avatar) {\r\n            return this.getColor(this.avatar.color);\r\n        }\r\n        return \"gray\";\r\n    }\r\n\r\n    /** Returns the initials for rendering the avatar */\r\n    public get initials(): string {\r\n        if (this.avatar) {\r\n            return this.avatar.initials || \"-\";\r\n        }\r\n        return \"?\";\r\n    }\r\n\r\n    /**\r\n     * Return the color for the avatar icon and line strokes.\r\n     * If some colors require adjustments due to accessibility reasons, they can be implemented here.\r\n     */\r\n    private getColor(color: string): string {\r\n      switch (color) {\r\n        case \"yellow\":\r\n          return \"#ebc000\";\r\n        case \"lime\":\r\n          return \"limegreen\";\r\n        case \"pink\":\r\n          return \"#ff8fa2\";\r\n        default:\r\n          return color;\r\n      }\r\n    }\r\n}\r\n","import angular from \"angular\";\r\nimport { SxyTableController, SxyTableOptions } from \"../sxy-table\";\r\nimport { ColumnDefinition } from \"tabulator-tables\";\r\nimport { Arrays, CellRenderingLogic, EnumerationsLogic, AccountInIndex, OpenAPIV3, Translations, JsonSchemaUtils } from \"@salaxy/core\";\r\nimport { JsonSchemaService } from \"../../services\";\r\n\r\n/**\r\n * Used for running batch processes to the server.\r\n * At the time of writing, the controller isonly used in Modal dialogs, but may�be used for something else later.\r\n */\r\nexport class BatchProcessController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$uibModalInstance\", \"data\", \"$sce\", \"$timeout\", \"JsonSchemaService\"];\r\n\r\n  /** Counter and status for the processing of the items */\r\n  public processCounter: {\r\n    /** If true, the processing is in progress (started and not yet done). */\r\n    isProcessing: boolean,\r\n    /** If true, the processing is done. Note that this may also mean that the processing has been canceled by the user. */\r\n    isDone: boolean,\r\n    /** Total count of items that should be processed. */\r\n    totalCount: number,\r\n    /** Count of items that have been processed. Note that also errors are counted as processed. */\r\n    processedCount: number,\r\n    /** Errors that occured. */\r\n    errorsCount: number,\r\n    /** If true, the process has been canceled by the user. If also isDone is true, the canceling has completed. */\r\n    canceling: boolean,\r\n  };\r\n\r\n  /** Options for the modal dialog */\r\n  public dialogHeader: string;\r\n\r\n  /** Columns that are shown in the grid. Leave empty use default columns */\r\n  public columns: string | (string | ColumnDefinition)[];\r\n\r\n  /** List of items that should be processed. */\r\n  public list: any[];\r\n\r\n  /** Usecase specific data for the dialog. */\r\n  public data: any;\r\n\r\n  /**\r\n   * Method that is called by the process.\r\n   * ItemOrArray is the item/array that is processed, Data is the controller data that may be edited in the form.\r\n   * The promise may return a message that is shown after text \"OK\".\r\n   * Promise rejection is cached.\r\n   */\r\n  public method: (itemOrArray: any | any[], data: any) => Promise<({message: string, result: any[]}[])>;\r\n\r\n  /**\r\n   * Optional chunk size for the batch process. This is used if the method supports arrays.\r\n   */\r\n  public chunkSize: number;\r\n\r\n  /** Start process right after opening the invoice. */\r\n  public autoStart: boolean;\r\n\r\n  /** Close dialog after process. */\r\n  public autoClose: boolean;\r\n\r\n  /** Options that are bound to the grid.  */\r\n  public tableOptions: SxyTableOptions;\r\n\r\n  /** Inner template that is included for usecase specific form and other UI. */\r\n  public batchTemplateUrl: string;\r\n\r\n  /** Binding for start button, which launches the processing. */\r\n  public isProcessStarted = false;\r\n\r\n  /** The table controller after it has been initialized. */\r\n  public $table: SxyTableController;\r\n\r\n  /** References a schema document directly: the schema document is not fetched from the UI */\r\n  public openApiDoc: any;\r\n\r\n  /**\r\n   * URL for the Open API document that contains the definition for the type.\r\n   * The url can be an absolute url, relative url or an url with salaxy-secure/ -prefix.\r\n   * The salaxy-secure/ -prefix will be replaced in runtime with the salaxy api server url of the curren environment.\r\n   */\r\n  public openApi = \"salaxy-secure/schemas/v02.json\";\r\n\r\n  /** The schema model */\r\n  public schemaModel: OpenAPIV3.SchemaObject;\r\n\r\n  /** If true, the schema loading is ready. */\r\n  public isReady: boolean;\r\n\r\n  /**\r\n   * Constructor for dependency instance.\r\n   * @param $uibModalInstance Modal instance supports functions such as close(result), dismiss(reason) and promises result, opened, closed and rendered.\r\n   * @param data Rest of the data injected from the caller.\r\n   */\r\n  constructor(protected $uibModalInstance: any, data: any, $sce: angular.ISCEService, private $timeout: angular.ITimeoutService, private jsonSchemaService: JsonSchemaService) {\r\n    this.data = data;\r\n    this.dialogHeader = this.data.dialogHeader || Translations.get(\"SALAXY.NG1.BatchProcessComponent.title\");\r\n    this.list = this.data.dialogList || [];\r\n    this.columns = this.getColumns(this.data.gridColumns);\r\n    this.method = this.data.batchMethod;\r\n    this.chunkSize = this.data.chunkSize ?? 0;\r\n    this.autoStart = this.data.autoStart ?? false;\r\n    this.autoClose = this.data.autoClose ?? false;\r\n    this.tableOptions = this.getGridOptions();\r\n    this.batchTemplateUrl = $sce.trustAsResourceUrl(data.batchTemplateUrl);\r\n  }\r\n\r\n  /** Initialization */\r\n  public $onInit = () => {\r\n    this.resetProcessed();\r\n    if (this.autoStart === true) {\r\n      this.startProcess();\r\n    }\r\n    if (this.data.listItemType) {\r\n      if (this.openApiDoc) {\r\n        this.jsonSchemaService.addSchemaDocument(this.openApi, this.openApiDoc);\r\n        this.schemaModel = this.jsonSchemaService.findSchema(this.openApi, this.data.listItemType);\r\n        this.isReady = true;\r\n      } else {\r\n        this.jsonSchemaService.assureSchemaDocument(this.openApi).then((openApiDoc) => {\r\n          this.openApiDoc = openApiDoc;\r\n          this.schemaModel = this.jsonSchemaService.findSchema(this.openApi, this.data.listItemType);\r\n          this.isReady = true;\r\n        });\r\n      }\r\n    } else {\r\n      this.isReady = true;\r\n    }\r\n  };\r\n\r\n  /** Starts the processing */\r\n  public startProcess() {\r\n    // Prevent double clicks\r\n    if (this.isProcessStarted) {\r\n      return;\r\n    }\r\n    this.isProcessStarted = true;\r\n    this.resetProcessed();\r\n    this.processNextItems();\r\n  }\r\n\r\n  /** Processes next items in the queue */\r\n  public processNextItems() {\r\n    this.$timeout(() => {\r\n      this.processNextItemsInternal();\r\n      // TODO: Consider adding this method to the SxyTableController in addition of refresh(). which redraws the table.\r\n      try {\r\n        this.$table.tabulator.replaceData(this.list);\r\n      } catch (e) {\r\n        // Ignore, the table is not initialized yet.\r\n      }\r\n    });\r\n  }\r\n\r\n  private processNextItemsInternal() {\r\n    const counter = this.processCounter;\r\n    counter.isProcessing = true;\r\n    if (counter.canceling) {\r\n      counter.isProcessing = false;\r\n      counter.isDone = true;\r\n      return;\r\n    }\r\n    const remainingItems = this.list.filter((x) => !x.processed);\r\n    if (remainingItems.length === 0) {\r\n      counter.isProcessing = false;\r\n      counter.isDone = true;\r\n      this.data.done = true;\r\n      if (this.autoClose) {\r\n        this.close();\r\n      }\r\n    } else {\r\n      const itemsToProcess = remainingItems.slice(0, this.chunkSize > 0 ? this.chunkSize : 1);\r\n      for (const itemToProcess of itemsToProcess) {\r\n        itemToProcess.processed = Translations.get(\"SALAXY.NG1.BatchProcessComponent.processing\");\r\n      }\r\n      this.method(this.chunkSize > 0 ? itemsToProcess : itemsToProcess[0], this.data)\r\n        .then((results) => {\r\n          let i = 0;\r\n          for (const itemToProcess of itemsToProcess) {\r\n            itemToProcess.processed = \"OK \" + (results[i].message);\r\n            itemToProcess.processedResult = { message: results[i].message, result: results[i].result };\r\n            i++;\r\n          }\r\n          counter.processedCount += itemsToProcess.length;\r\n          this.processNextItems();\r\n        })\r\n        .catch((reason) => {\r\n          let label = \"Server error\";\r\n          let msg = \"Unknown error\";\r\n          if (reason) {\r\n            msg = reason.statusText || msg;\r\n            if (reason.data) {\r\n              label = reason.data.error || label;\r\n              msg = reason.data.messageHtml || msg;\r\n            }\r\n          }\r\n          for (const itemToProcess of itemsToProcess) {\r\n            itemToProcess.processed = \"ERR \" + label + \". \" + msg;\r\n            itemToProcess.processedResult = null;\r\n          }\r\n          console.error(label, reason);\r\n          counter.processedCount += itemsToProcess.length;\r\n          counter.errorsCount += itemsToProcess.length;\r\n          this.processNextItems();\r\n        });\r\n    }\r\n  }\r\n\r\n  /** Closes the dialog. */\r\n  public close() {\r\n    this.resetProcessed();\r\n    this.$uibModalInstance.close();\r\n  }\r\n\r\n  /** Resets the processed status column(s) */\r\n  public resetProcessed() {\r\n    for (const item of this.list) {\r\n      if (item.processed) {\r\n        item.processed = null;\r\n      }\r\n    }\r\n    this.processCounter = {\r\n      isProcessing: false,\r\n      isDone: false,\r\n      totalCount: this.list.length,\r\n      processedCount: 0,\r\n      errorsCount: 0,\r\n      canceling: false,\r\n    };\r\n  }\r\n\r\n  /** Cancels the process: Waits for the next response, but does not start a new one. */\r\n  public cancelProcess() {\r\n    this.processCounter.canceling = true;\r\n  }\r\n\r\n  private getColumns(columns: string | (string | ColumnDefinition)[]): string | (string | ColumnDefinition)[] {\r\n    const defaultCols: ColumnDefinition[] = [\r\n      ...this.getAvatarCols(\"owner\", Translations.get(\"SALAXY.NG1.BatchProcessComponent.employer\"), { width: 300 }),\r\n      ...this.getAvatarCols(\"other\", Translations.get(\"SALAXY.NG1.BatchProcessComponent.worker\"), { width: 400 }),\r\n      {\r\n        field: \"status\",\r\n        title: Translations.get(\"SALAXY.NG1.BatchProcessComponent.status\"),\r\n        formatter: (cell: any) => {\r\n          const status = cell.getData().status;\r\n          const statusEnum = JsonSchemaUtils.getProperty(this.schemaModel, \"status\")?.schema?.format;\r\n          if (!status) {\r\n            return `<div>-</div>`;\r\n          }\r\n          if (!statusEnum) {\r\n            return `<div>${status}</div>`;\r\n          }\r\n          return Translations.get(`SALAXY.ENUM.${statusEnum}.${status}.label`);\r\n        }\r\n      },\r\n    ];\r\n    if (typeof columns === \"string\") {\r\n      columns = Arrays.assureArray(columns);\r\n    }\r\n    if (!columns?.length) {\r\n      columns = defaultCols;\r\n    }\r\n    if (!columns.find((x) => x == \"processed\" || (x as ColumnDefinition).field === \"processed\")) {\r\n      columns.splice(0, 0,{\r\n        width: 400,\r\n        field: \"processed\",\r\n        title: Translations.get(\"SALAXY.NG1.BatchProcessComponent.processed\"),\r\n        // TODO: cellTemplate: \"salaxy-aspa-components/grid-col/processed.html\",\r\n        // eslint-disable-next-line\r\n        // cellTooltip: (row, col) => row.entity.processed,\r\n      });\r\n    }\r\n    return columns;\r\n  }\r\n\r\n  /**\r\n   * Gets a column definition for avatar column: Renders an avatar with sortable name and second info line.\r\n   * @param party The party to render: either \"owner\" (ownerInfo) or \"other\" (otherPartyInfo).\r\n   * @param title The title of the column.\r\n   * @param props Other properties that should be set on the column.\r\n   */\r\n  public getAvatarCols(party: \"owner\" | \"other\", title: string, props?: any): any[] {\r\n    const infoProp = party === \"other\" ? \"otherPartyInfo\" : \"ownerInfo\";\r\n    const result: any[] = [\r\n      {\r\n        field: `${infoProp}.avatar.sortableName`, title,\r\n        headerFilter: true,\r\n        formatter: (cell: any) => {\r\n          const info: AccountInIndex = cell.getData()[infoProp];\r\n          return `\r\n              <div class=\"tabulator-avatar\">${CellRenderingLogic.getAvatar(info?.avatar)}${info?.avatar?.sortableName || \"-\"}</div>\r\n          `;\r\n        },\r\n        ...props,\r\n      },\r\n    ];\r\n    return result;\r\n  }\r\n\r\n  /**\r\n   * Gets a column definition for enumerations column\r\n   * @param field The field name / path in the data model.\r\n   * @param title The title of the column.\r\n   * @param enumType The type name of the enumeration.\r\n   * @param props Other properties that should be set on the column.\r\n   */\r\n  public getEnumColumn(field: string, title: string, enumType: string, props?: any): any {\r\n    return {\r\n      field, title,\r\n      formatter: (cell: any) => EnumerationsLogic.getEnumLabel(enumType, cell.getValue()),\r\n      headerFilter: \"list\",\r\n      headerFilterFunc: \"=\",\r\n      headerFilterParams: {\r\n        values: EnumerationsLogic.getEnumMetadata(enumType)?.values.map(v => ({ label: v.label, value: v.name })),\r\n      },\r\n      ...props,\r\n    };\r\n  }\r\n\r\n  /** Gets the options for the UI grid */\r\n  private getGridOptions(): SxyTableOptions {\r\n    const options: SxyTableOptions = {\r\n      height: \"50vh\",\r\n      layout: \"fitColumns\"\r\n    };\r\n    return options;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Dates, Translations, CalendarDay, CalendarMonth, CalendarSeries, CalendarUiEvent, HolidaysLogic, Configs } from \"@salaxy/core\";\r\nimport { UiHelpers, ExcelHelpers } from \"../../services\";\r\nimport { ListControllerBase } from \"../bases\";\r\n\r\n/**\r\n * Renders a calendar control for visualisation of holidays.\r\n */\r\nexport class CalendarController implements angular.IController {\r\n\r\n    /**\r\n     * For NG-dependency injection\r\n     * @ignore\r\n     */\r\n    public static $inject = [\"UiHelpers\", \"$http\"];\r\n\r\n    /**\r\n     * Start date for the calendar as ISO date yyyy-MM-dd. Renders from the beginning of this month.\r\n     */\r\n    public start: string;\r\n\r\n    /**\r\n     * End date of the calendar as ISO date yyyy-MM-dd. Renders until the end of this month.\r\n     */\r\n    public end: string;\r\n\r\n    /**\r\n     * Calendar data where single series can be represented as an array of events (CalendarUiEvent or date ISO string).\r\n     * Several series should be represented as CalendarSeries that contain events.\r\n     * Note that a DateRange also passes as CalendarUiEvent because it has start and end dates.\r\n     */\r\n    public data: CalendarSeries[] | (CalendarUiEvent | string)[] | any;\r\n\r\n    /**\r\n     * Function that is called when user selects an item in the calendar.\r\n     * Function can have the following locals: type: \"event\" | \"day\", date: string, day: Full calendar day with all the day info,\r\n     * calEvent: The calendar event if type is \"event\", series: Series that the event belongs to or the series that is clicked (not always available).\r\n     * @example <salaxy-calendar on-list-select=\"$ctrl.myCustomSelectFunc(type, date, calEvent)\"></salaxy-calendar>\r\n     */\r\n    public onListSelect: (params: {\r\n      /** Selection type. */\r\n      type: \"event\" | \"day\" | \"series\",\r\n      /** Seleted date as ISO string. */\r\n      date: string,\r\n      /** Full calendar day with all the day info. */\r\n      day: CalendarDay,\r\n      /** Calendar event that was clicked: Only if selection type is \"event.\" */\r\n      calEvent?: CalendarUiEvent,\r\n      /**\r\n       * Series that the event belongs to or the series that is clicked.\r\n       * Note that some clicks of type \"day\" might not have the series info, in current UI the header above series when calendar supports multiple series.\r\n       */\r\n      series?: CalendarSeries,\r\n    }) => void;\r\n\r\n    /** Language versioned weekdays short texts (e.g. \"ma\", \"ti\",...) */\r\n    public weekdays: string[];\r\n\r\n    /** Get the header days for the whole calendar. */\r\n    public weekdaysForMonth: {\r\n      /** Weekday index number (align-weekdays) or day of month (align-left). */\r\n      ix: number,\r\n      /** Week day number in week (align-weekdays). */\r\n      weekday?: number,\r\n      /** Text for the week day (align-weekdays) or day of month (align-left). */\r\n      text: string,\r\n    }[] = [];\r\n\r\n    /** A mapper that is used in converting custom data to Calendar series array. */\r\n    public mapper: (sourceData: any) => CalendarSeries[];\r\n\r\n    /** If specified, this is the list controller that should be used for editing the item. */\r\n    public listController: ListControllerBase<any, any>;\r\n\r\n    /** If set to true, the export buttons are visible. */\r\n    public showExport = false;\r\n\r\n    private _today: string;\r\n\r\n    private _mode: \"align-weekdays\" | \"align-left\" | \"horizontal\" | \"list\";\r\n\r\n    private _series: CalendarSeries[];\r\n\r\n    private HOLIDAY_COLOR = \"#BBB\";\r\n    private WEEKEND_COLOR = \"#DDD\";\r\n    private EVENT_COLOR = \"#009fd8\";\r\n\r\n    constructor(private uiHelpers: UiHelpers, private $http: angular.IHttpService) {\r\n      // for dependency injection\r\n    }\r\n\r\n    /**\r\n     * Implement IController\r\n     */\r\n    public $onInit = () => {\r\n      // Default values if not set, also validate and harmonize them for dates only (remove time and convert e.g. \"today\")\r\n      this.start = Dates.asDate(this.start) || Dates.getDate(\"today\", 1, 1);\r\n      this.end = Dates.asDate(this.end) || Dates.getDate(\"today\", 12, 31);\r\n      this.today = Dates.asDate(this.today) || Dates.getToday();\r\n      this.weekdays = Array.from(\"1234567\").map((x) => Translations.getWithDefault(`SALAXY.ENUM.Weekday.day${x}.short`, \"d\" + x));\r\n      this.initHeader();\r\n    };\r\n\r\n    /** Initialize the header (days) */\r\n    public initHeader() {\r\n      switch (this.mode) {\r\n        case \"align-left\":\r\n          this.weekdaysForMonth = [...Array(31)].map((val, ix) => ({ ix, text: (ix + 1).toString()}));\r\n          break;\r\n        case \"horizontal\":\r\n          break;\r\n        default:\r\n          // Align the weekdays\r\n          for (let i = 0; i < 5; i++) {\r\n            this.weekdaysForMonth.push(...this.weekdays.map((x, index) => ({ ix: i * 7 + index, weekday: index + 1, text: x}) ));\r\n          }\r\n          this.weekdaysForMonth.push({ ix: 5 * 7 + 0, weekday: 1, text: this.weekdays[0]} , { ix: 5 * 7 + 1, weekday: 2, text: this.weekdays[1]});\r\n          break;\r\n      }\r\n    }\r\n\r\n    /**\r\n     * Specifies how the weekdays are aligned from one month to another.\r\n     * \"horizontal\" shows all months side-by-side horizontally, so there is no alignment.\r\n     */\r\n    public get mode(): \"align-weekdays\" | \"align-left\" | \"horizontal\" | \"list\" {\r\n      switch (this._mode) {\r\n        case \"align-left\":\r\n        case \"horizontal\":\r\n        case \"list\":\r\n          return this._mode;\r\n        default:\r\n          return \"align-weekdays\";\r\n      }\r\n    }\r\n    public set mode(value: \"align-weekdays\" | \"align-left\" | \"horizontal\" | \"list\") {\r\n      this._mode = value;\r\n    }\r\n\r\n    /** Gets the Today date for the calendar as ISO date yyyy-MM-dd. */\r\n    public get today(): string {\r\n      if (!this._today) {\r\n        this._today = Dates.getToday();\r\n      }\r\n      return this._today;\r\n    }\r\n    /** Sets the Today date as dately object (e.g. ISO string, JS Date or key string \"today\") */\r\n    public set today(value: string) {\r\n      this._today = Dates.asDate(value);\r\n    }\r\n\r\n    /** Gets all days of all months */\r\n    public get allDays(): CalendarDay[] {\r\n      // TODO: create typing to months / allDays results.\r\n      return this.uiHelpers.cache(this, \"allDays\", () => {\r\n        return this.months.reduce((acc, current) => acc.concat(current.days), []);\r\n      }, () => this.cacheCounter);\r\n    }\r\n\r\n    /**\r\n     * Gets the data harmonized as an array of Calendar Series\r\n     */\r\n    public get series(): CalendarSeries[] {\r\n      return this._series;\r\n    }\r\n\r\n    /**\r\n     * Gets the monthly list: Only the dates that have events on them.\r\n     * Only the start of event is considered except for the first month where all intercepting properties are.\r\n     */\r\n    public get monthlyList(): CalendarMonth[] {\r\n      return this.uiHelpers.cache(this, \"monthList\", () => {\r\n        const months = this.months.map((month) => {\r\n          const monthResult: CalendarMonth = {\r\n            daysInMonth: month.daysInMonth,\r\n            firstDayDayOfWeek: month.firstDayDayOfWeek,\r\n            month: month.month,\r\n            title: month.title,\r\n            year: month.year,\r\n            days: month.days.map((day) => {\r\n              let dayEventsCount = 0;\r\n              Object.keys(day.events).reduce((acc, key) => {\r\n                // TODO: We are only using dayEventsCount => Figure out a simpler way to find it.\r\n                acc[key] = day.events[key];\r\n                dayEventsCount += acc[key].length;\r\n                return acc;\r\n              }, {});\r\n              if (dayEventsCount) {\r\n                return {\r\n                  day: day.day,\r\n                  date: day.date,\r\n                  weekday: day.weekday,\r\n                  weekdayText: day.weekdayText,\r\n                  dayType: day.dayType,\r\n                  events: day.events.map((series) => series.filter((val) => day.date === val.start)),\r\n                  periods: null, // Add support if needed\r\n                  singleDays: null,\r\n                };\r\n              }\r\n              return null;\r\n            }).filter(x => !!x),\r\n          };\r\n          return monthResult;\r\n        });\r\n        return months;\r\n      }, () => this.cacheCounter);\r\n    }\r\n\r\n    /** The collection of months that the calendar renders. */\r\n    public get months(): CalendarMonth[] {\r\n      return this.uiHelpers.cache(this, \"months\", () => {\r\n        const result = [];\r\n        const startDay = Dates.startEnd(this.start || \"today\",\"start-month\");\r\n        const endDay = Dates.startEnd(this.end || \"today\",\"start-month\");\r\n        this.assureNormalizedCopy();\r\n        const data = this.series || [];\r\n        if (!Dates.isValidDateTime(startDay) || !Dates.isValidDateTime(endDay) || startDay > endDay) {\r\n          console.error(\"Invalid date range in CalendarController.\");\r\n          return [];\r\n        }\r\n        let currentMonthDay = startDay;\r\n        while (currentMonthDay <= endDay) {\r\n          const daysInMonth = Dates.getDaysInMonth(currentMonthDay);\r\n          const firstDayDayOfWeek = Dates.getWeekday(currentMonthDay);\r\n\r\n          const month: CalendarMonth = {\r\n            month: Dates.getMonth(currentMonthDay),\r\n            year: Dates.getYear(currentMonthDay),\r\n            title: Translations.get(`SALAXY.ENUM.CalendarMonth.month${Dates.getMonth(currentMonthDay)}.label`),\r\n            firstDayDayOfWeek,\r\n            daysInMonth,\r\n            days: [],\r\n          };\r\n          for (let day = 1; day <= daysInMonth; day++) {\r\n            const date = Dates.setDay(currentMonthDay,day);\r\n            const weekday = Dates.getWeekday(date);\r\n\r\n            // TODO: Do we need separate periods/singleDays any more?\r\n            const periods = data.map((series) => series.events.filter((val) => val.end && !val.icon && val.start <= date && val.end >= date));\r\n            const singleDays = data.map((series) => series.events.filter((val) => (!val.end || val.icon) && date === val.start));\r\n            // TODO: Is it more efficient to concatenate from the 2 above?\r\n            const events = data.map((series) => series.events.filter((val) => date === val.start || (val.end && !val.icon && val.start < date && val.end >= date)));\r\n            month.days.push({\r\n              day,\r\n              date,\r\n              weekday,\r\n              weekdayText: this.weekdays[weekday - 1],\r\n              dayType: date === this.today ? \"today\" : (Dates.isHoliday(date) ? \"holiday\" : \"normal\"),\r\n              events,\r\n              periods,\r\n              singleDays,\r\n            });\r\n          }\r\n          result.push(month);\r\n          currentMonthDay = Dates.add(currentMonthDay,1,\"month\");\r\n        }\r\n        return result;\r\n      }, this.getCacheKey);\r\n    }\r\n\r\n    /**\r\n     * Gets the short text \"ma\", \"ti\", \"ke\", \"to\", \"pe\", \"la\", \"su\".\r\n     * @param date Date as ISO string or date\r\n     */\r\n    public getShortWeekdayText(date: any) {\r\n      return this.weekdays[Dates.getWeekday(date) - 1];\r\n    }\r\n\r\n    /** Gets the CSS class(es) for a calendar event. */\r\n    public getCssClass(event: CalendarUiEvent): string {\r\n      if (!event) {\r\n        return null;\r\n      }\r\n      if (event.icon) {\r\n        // This is an icon (<i>-tag).\r\n        return `fa ${event.icon} event-single-day ${event.cssClass || \"text-info\"} clickable`;\r\n      }\r\n      return `event-period ${event.cssClass || \"salaxy-cal-event-primary\"} clickable`;\r\n    }\r\n\r\n    /**\r\n     * Get the event CSS style for a single day. Main thing is to set the disposition and smaller size if the day has overlapping items.\r\n     * @param event Event for which to calculate the styles.\r\n     * @param allEvents All events in the given series/type: Either period or singleDay.\r\n     */\r\n    public getEventStyle(event: CalendarUiEvent, allEvents: CalendarUiEvent[]): any {\r\n      if (event.icon) {\r\n        const ix = allEvents.indexOf(event);\r\n        switch (allEvents.length) {\r\n          case 1:\r\n            return null; /* bottom: 4px; left: -4px; font-size: 16px; */\r\n          case 2:\r\n            return {\r\n              \"font-size\": \"12px\",\r\n              bottom: (ix === 1 ? 0 : 8) + \"px\",\r\n              left: (ix === 1 ? 2 : -4) + \"px\",\r\n            };\r\n          case 3:\r\n            return {\r\n              \"font-size\": \"10px\",\r\n              bottom: (ix > 1 ? 0 : 8) + \"px\",\r\n              left: (ix === 0 ? -4 : (ix === 2 ? 0 : 4)) + \"px\",\r\n            };\r\n          default:\r\n            return {\r\n              \"font-size\": \"10px\",\r\n              bottom: (ix > 1 ? 0 : 8) + \"px\",\r\n              left: (ix === 0 || ix === 2 ? -4 : 4) + \"px\",\r\n            };\r\n        }\r\n      } else {\r\n        if (allEvents.length > 1) {\r\n          const height = (this.mode === \"horizontal\" ? 30 : 16)/allEvents.length;\r\n          const ix = allEvents.indexOf(event);\r\n          return {\r\n            height: height + \"px\",\r\n            bottom: (height*(allEvents.length-1-ix)) + \"px\",\r\n          };\r\n        }\r\n      }\r\n      return null;\r\n    }\r\n\r\n    /**\r\n     * A date in the calendar was clicked.\r\n     * @param day Day that was clicked.\r\n     * @param series The series that contains the event.\r\n     * If null, the click is in header etc. where series is not available.\r\n     * @param $event The AngularJS event used to stop propagation.\r\n     */\r\n    public dateClicked(day: CalendarDay, series: CalendarSeries, $event: angular.IAngularEvent) {\r\n      $event.stopPropagation();\r\n      series = series || this.series[0];\r\n      if (this.listController && series) {\r\n        this.listController.parent = series.data;\r\n        const newItem = this.listController.getBlank();\r\n        if (newItem.period) {\r\n          // HACK: Could we move this to object specific CRUD or List controllers.\r\n          newItem.period.start = day.date;\r\n          newItem.period.end = day.date;\r\n        }\r\n        this.listController.showEditDialog(newItem, true);\r\n        return;\r\n      }\r\n      this.onListSelect({\r\n        type: \"day\",\r\n        date: day.date,\r\n        day,\r\n        series,\r\n      });\r\n    }\r\n\r\n    /**\r\n     * Called by view when an event is clicked.\r\n     * @param ev Event that is being clicked\r\n     * @param day Day on which the event occurs\r\n     * @param series The series that contains the event. If null, the first series is taken.\r\n     * @param $event AngularJS event: Used for stopping propagation.\r\n     */\r\n    public eventClicked(ev: CalendarUiEvent, day: CalendarDay, series: CalendarSeries, $event: angular.IAngularEvent) {\r\n      $event.stopPropagation();\r\n      series = series || this.series[0];\r\n      if (this.listController && series) {\r\n        this.listController.parent = series.data;\r\n        this.listController.showEditDialog(ev.data);\r\n        return;\r\n      }\r\n      this.onListSelect({\r\n        type: \"event\",\r\n        date: day.date,\r\n        day,\r\n        calEvent: ev,\r\n        series,\r\n      });\r\n    }\r\n\r\n    /**\r\n     * A series title in the calendar was clicked.\r\n     * @param series The series.\r\n     * @param $event The AngularJS event used to stop propagation.\r\n     */\r\n      public seriesClicked(series: CalendarSeries, $event: angular.IAngularEvent) {\r\n        $event.stopPropagation();\r\n        this.onListSelect({\r\n          type: \"series\",\r\n          date: undefined,\r\n          day: undefined,\r\n          series,\r\n        });\r\n      }\r\n\r\n      /**\r\n       * Exports the calendar as a PDF.\r\n       * This method shows a loading indicator, constructs a URL for the PDF request,\r\n       * and handles the PDF request.\r\n       */\r\n      public exportCalendarPdf(): void {\r\n        const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.loading\");\r\n        const url = `${Configs.current.reportServer}/pdf?reportType=calendar&language=${encodeURIComponent(Translations.getLanguage())}&disposition=inline`;\r\n        this.handlePdfRequest(url, false, { object: {months: this.months, series: this.series} }, loading);\r\n      }\r\n\r\n      private async handlePdfRequest(\r\n        url: string,\r\n        inline: boolean,\r\n        payload: any,\r\n        loading: any\r\n      ): Promise<void> {\r\n        try {\r\n          await this.fetchPdf(url, payload, inline);\r\n        } catch (error) {\r\n          //HACK: Implement failover functionality to cloud (azure)\r\n          if (\r\n            url.includes(Configs.current.reportServer) &&\r\n            Configs.current.getEnv() === \"prod\"\r\n          ) {\r\n            url = url.replace(\r\n              Configs.current.reportServer,\r\n              \"https://failover-reports.salaxy.com\"\r\n            );\r\n            try {\r\n              await this.fetchPdf(url, payload, inline);\r\n            } catch (error) {\r\n              console.error(error);\r\n            }\r\n          } else {\r\n            console.error(error);\r\n          }\r\n        }\r\n        if (loading) {\r\n          loading.dismiss();\r\n        }\r\n      }\r\n      private async fetchPdf(\r\n        url: string,\r\n        payload: any,\r\n        inline: boolean\r\n      ): Promise<void> {\r\n        let response: any;\r\n        if (payload) {\r\n          response = await this.$http.post(url, payload, { responseType: \"blob\" });\r\n        } else {\r\n          response = await this.$http.get(url, { responseType: \"blob\" });\r\n        }\r\n        if (response.data) {\r\n          if (inline) {\r\n            this.uiHelpers.openFile(response.data as any);\r\n          } else {\r\n            this.uiHelpers.downloadFile(\r\n              response.data as any,\r\n              decodeURIComponent(response.headers(\"content-disposition\")).match(\r\n                /filename\\s*=\\s*\"?(?<file>.*?)(?:\\s*;|\"|\\s*$)/\r\n              )?.groups?.file\r\n            );\r\n          }\r\n        }\r\n      }\r\n\r\n      /**\r\n       * Export the calendar as Excel.\r\n       */\r\n      public exportCalendarExcel(): void {\r\n        const headers = this.generateExcelHeaders();\r\n        const dataRows = this.generateExcelDataRows();\r\n        const finalResult = [headers, ...dataRows];\r\n        ExcelHelpers.export(finalResult, \"lomakalenteri\");\r\n      }\r\n      private generateExcelHeaders(): string[] {\r\n        const headers = [\"Työntekijä\"];\r\n        this.allDays.forEach((day) => {\r\n            headers.push(Dates.getFormattedDate(day.date));\r\n        });\r\n        return headers;\r\n      }\r\n\r\n      private generateExcelDataRows(): any[] {\r\n        return this.series.map((series) => this.generateExcelDataRow(series));\r\n      }\r\n\r\n    private generateExcelDataRow(series: any): any[] {\r\n      const result = [];\r\n      result.push(`${series.title} ${HolidaysLogic.getPlannedLeavesCount(series.data, \"all\")}/${series.data.accrual.endSaldo} pv`);\r\n      this.allDays.forEach((day) => {\r\n          const isEventOnDay = series.events.some((ev) => day.date >= ev.start && day.date <= ev.end);\r\n          result.push(isEventOnDay ? 1 : \" \");\r\n      });\r\n      return result;\r\n    }\r\n\r\n    /**\r\n     * Copies the data as normalized data set so that we can harmonize the dates and potentially make other changes in the future.\r\n     * Copy is shallow copy of CalendarUiEvent.\r\n     */\r\n    private assureNormalizedCopy(): CalendarSeries[] {\r\n      // TODO: The whole data pump is now dependent of the trigger of \"months\" getter ,which checks the cache key.\r\n      //       This process could be more explicit / clearer (perhaps in this method?).\r\n      const result: CalendarSeries[] = [];\r\n      if (!this.data) {\r\n        return result;\r\n      }\r\n      if (this.mapper) {\r\n        const newData: CalendarSeries[] = this.mapper(this.data);\r\n        newData.forEach((item, ix) => {\r\n          result.push({\r\n            key: item.key || \"Series\" + ix,\r\n            title: item.title,\r\n            description: item.description,\r\n            avatar: item.avatar,\r\n            events: item.events.map((ev) => Object.assign({}, ev)),\r\n            data: item.data,\r\n          });\r\n        });\r\n      } else {\r\n        // Make a copy of the data and in process map to CalendarSeries[] array.\r\n        const defaultSeries: CalendarSeries = {\r\n          key: \"default\",\r\n          avatar: null,\r\n          title: null,\r\n          events: [],\r\n          data: null,\r\n        };\r\n        this.data.forEach((item, ix) => {\r\n          if (typeof item === \"string\") {\r\n            defaultSeries.events.push({ start: item });\r\n          } else if ((item as CalendarUiEvent)?.start) {\r\n            defaultSeries.events.push(Object.assign({}, item));\r\n          } else if ((item as CalendarSeries)?.key === \"default\") {\r\n            defaultSeries.events.push(...item.events.map((ev) => Object.assign({}, ev)));\r\n            defaultSeries.avatar = item.avatar || defaultSeries.avatar;\r\n            defaultSeries.title = item.title || defaultSeries.title;\r\n            defaultSeries.description = item.description || defaultSeries.description;\r\n          } else if (Array.isArray((item as CalendarSeries)?.events)) {\r\n            result.push({\r\n              key: item.key || \"Series\" + ix,\r\n              title: item.title,\r\n              description: item.description,\r\n              avatar: item.avatar,\r\n              events: item.events.map((ev) => Object.assign({}, ev)),\r\n              data: item.data,\r\n            });\r\n          }\r\n        });\r\n        if (defaultSeries.events.length) {\r\n          result.splice(0, 0, defaultSeries);\r\n        }\r\n      }\r\n      // Harmonize data\r\n      result.forEach((series) => {\r\n        series.events.forEach((ev) => {\r\n          ev.start = Dates.asDate(ev.start);\r\n          ev.end = Dates.asDate(ev.end);\r\n          if (!ev.end) {\r\n            ev.icon = ev.icon || \"bi-circle-fill\";\r\n          }\r\n        });\r\n      });\r\n      this.cacheCounter++;\r\n      this._series = result;\r\n    }\r\n\r\n    /** Get a simplified cache key for caching months / days. */\r\n    private getCacheKey = () => {\r\n      return angular.copy({\r\n        data: this.data,\r\n        start: \"\" + this.start,\r\n        end: \"\" + this.end,\r\n        mode: this.mode || \"\",\r\n        today: this._today,\r\n      });\r\n    };\r\n\r\n    /**\r\n     * Cache counter is updated by months getter, which is the foundation of data refresh and observes full getCacheKey.\r\n     * Rest of the methods can just check this simpler cacheCounter for refreshes.\r\n     */\r\n    private cacheCounter = 0;\r\n\r\n}\r\n","/*!\n* chartjs-plugin-annotation v3.0.1\n* https://www.chartjs.org/chartjs-plugin-annotation/index\n * (c) 2023 chartjs-plugin-annotation Contributors\n * Released under the MIT License\n */\nimport { Element, defaults, Animations, Chart } from 'chart.js';\nimport { distanceBetweenPoints, defined, isFunction, callback, isObject, valueOrDefault, toRadians, isArray, toFont, addRoundedRectPath, toTRBLCorners, QUARTER_PI, PI, HALF_PI, TWO_THIRDS_PI, TAU, isNumber, RAD_PER_DEG, toPadding, isFinite, toDegrees, clipArea, unclipArea } from 'chart.js/helpers';\n\n/**\n * @typedef { import(\"chart.js\").ChartEvent } ChartEvent\n * @typedef { import('../../types/element').AnnotationElement } AnnotationElement\n */\n\nconst interaction = {\n  modes: {\n    /**\n     * Point mode returns all elements that hit test based on the event position\n     * @param {Object} state - the state of the plugin\n     * @param {ChartEvent} event - the event we are find things at\n     * @return {AnnotationElement[]} - elements that are found\n     */\n    point(state, event) {\n      return filterElements(state, event, {intersect: true});\n    },\n\n    /**\n     * Nearest mode returns the element closest to the event position\n     * @param {Object} state - the state of the plugin\n     * @param {ChartEvent} event - the event we are find things at\n     * @param {Object} options - interaction options to use\n     * @return {AnnotationElement[]} - elements that are found (only 1 element)\n     */\n    nearest(state, event, options) {\n      return getNearestItem(state, event, options);\n    },\n    /**\n     * x mode returns the elements that hit-test at the current x coordinate\n     * @param {Object} state - the state of the plugin\n     * @param {ChartEvent} event - the event we are find things at\n     * @param {Object} options - interaction options to use\n     * @return {AnnotationElement[]} - elements that are found\n     */\n    x(state, event, options) {\n      return filterElements(state, event, {intersect: options.intersect, axis: 'x'});\n    },\n\n    /**\n     * y mode returns the elements that hit-test at the current y coordinate\n     * @param {Object} state - the state of the plugin\n     * @param {ChartEvent} event - the event we are find things at\n     * @param {Object} options - interaction options to use\n     * @return {AnnotationElement[]} - elements that are found\n     */\n    y(state, event, options) {\n      return filterElements(state, event, {intersect: options.intersect, axis: 'y'});\n    }\n  }\n};\n\n/**\n * Returns all elements that hit test based on the event position\n * @param {Object} state - the state of the plugin\n * @param {ChartEvent} event - the event we are find things at\n * @param {Object} options - interaction options to use\n * @return {AnnotationElement[]} - elements that are found\n */\nfunction getElements(state, event, options) {\n  const mode = interaction.modes[options.mode] || interaction.modes.nearest;\n  return mode(state, event, options);\n}\n\nfunction inRangeByAxis(element, event, axis) {\n  if (axis !== 'x' && axis !== 'y') {\n    return element.inRange(event.x, event.y, 'x', true) || element.inRange(event.x, event.y, 'y', true);\n  }\n  return element.inRange(event.x, event.y, axis, true);\n}\n\nfunction getPointByAxis(event, center, axis) {\n  if (axis === 'x') {\n    return {x: event.x, y: center.y};\n  } else if (axis === 'y') {\n    return {x: center.x, y: event.y};\n  }\n  return center;\n}\n\nfunction filterElements(state, event, options) {\n  return state.visibleElements.filter((element) => options.intersect ? element.inRange(event.x, event.y) : inRangeByAxis(element, event, options.axis));\n}\n\nfunction getNearestItem(state, event, options) {\n  let minDistance = Number.POSITIVE_INFINITY;\n\n  return filterElements(state, event, options)\n    .reduce((nearestItems, element) => {\n      const center = element.getCenterPoint();\n      const evenPoint = getPointByAxis(event, center, options.axis);\n      const distance = distanceBetweenPoints(event, evenPoint);\n      if (distance < minDistance) {\n        nearestItems = [element];\n        minDistance = distance;\n      } else if (distance === minDistance) {\n        // Can have multiple items at the same distance in which case we sort by size\n        nearestItems.push(element);\n      }\n\n      return nearestItems;\n    }, [])\n    .sort((a, b) => a._index - b._index)\n    .slice(0, 1); // return only the top item;\n}\n\nconst isOlderPart = (act, req) => req > act || (act.length > req.length && act.slice(0, req.length) === req);\n\n/**\n * @typedef { import('chart.js').Point } Point\n * @typedef { import('chart.js').InteractionAxis } InteractionAxis\n * @typedef { import('../../types/element').AnnotationElement } AnnotationElement\n */\n\nconst EPSILON = 0.001;\nconst clamp = (x, from, to) => Math.min(to, Math.max(from, x));\n\n/**\n * @param {Object} obj\n * @param {number} from\n * @param {number} to\n * @returns {Object}\n */\nfunction clampAll(obj, from, to) {\n  for (const key of Object.keys(obj)) {\n    obj[key] = clamp(obj[key], from, to);\n  }\n  return obj;\n}\n\n/**\n * @param {Point} point\n * @param {Point} center\n * @param {number} radius\n * @param {number} borderWidth\n * @returns {boolean}\n */\nfunction inPointRange(point, center, radius, borderWidth) {\n  if (!point || !center || radius <= 0) {\n    return false;\n  }\n  const hBorderWidth = borderWidth / 2;\n  return (Math.pow(point.x - center.x, 2) + Math.pow(point.y - center.y, 2)) <= Math.pow(radius + hBorderWidth, 2);\n}\n\n/**\n * @param {Point} point\n * @param {{x: number, y: number, x2: number, y2: number}} rect\n * @param {InteractionAxis} axis\n * @param {number} borderWidth\n * @returns {boolean}\n */\nfunction inBoxRange(point, {x, y, x2, y2}, axis, borderWidth) {\n  const hBorderWidth = borderWidth / 2;\n  const inRangeX = point.x >= x - hBorderWidth - EPSILON && point.x <= x2 + hBorderWidth + EPSILON;\n  const inRangeY = point.y >= y - hBorderWidth - EPSILON && point.y <= y2 + hBorderWidth + EPSILON;\n  if (axis === 'x') {\n    return inRangeX;\n  } else if (axis === 'y') {\n    return inRangeY;\n  }\n  return inRangeX && inRangeY;\n}\n\n/**\n * @param {AnnotationElement} element\n * @param {boolean} useFinalPosition\n * @returns {Point}\n */\nfunction getElementCenterPoint(element, useFinalPosition) {\n  const {centerX, centerY} = element.getProps(['centerX', 'centerY'], useFinalPosition);\n  return {x: centerX, y: centerY};\n}\n\n/**\n * @param {string} pkg\n * @param {string} min\n * @param {string} ver\n * @param {boolean} [strict=true]\n * @returns {boolean}\n */\nfunction requireVersion(pkg, min, ver, strict = true) {\n  const parts = ver.split('.');\n  let i = 0;\n  for (const req of min.split('.')) {\n    const act = parts[i++];\n    if (parseInt(req, 10) < parseInt(act, 10)) {\n      break;\n    }\n    if (isOlderPart(act, req)) {\n      if (strict) {\n        throw new Error(`${pkg} v${ver} is not supported. v${min} or newer is required.`);\n      } else {\n        return false;\n      }\n    }\n  }\n  return true;\n}\n\nconst isPercentString = (s) => typeof s === 'string' && s.endsWith('%');\nconst toPercent = (s) => parseFloat(s) / 100;\nconst toPositivePercent = (s) => clamp(toPercent(s), 0, 1);\n\nconst boxAppering = (x, y) => ({x, y, x2: x, y2: y, width: 0, height: 0});\nconst defaultInitAnimation = {\n  box: (properties) => boxAppering(properties.centerX, properties.centerY),\n  ellipse: (properties) => ({centerX: properties.centerX, centerY: properties.centerX, radius: 0, width: 0, height: 0}),\n  label: (properties) => boxAppering(properties.centerX, properties.centerY),\n  line: (properties) => boxAppering(properties.x, properties.y),\n  point: (properties) => ({centerX: properties.centerX, centerY: properties.centerY, radius: 0, width: 0, height: 0}),\n  polygon: (properties) => boxAppering(properties.centerX, properties.centerY)\n};\n\n/**\n * @typedef { import(\"chart.js\").Chart } Chart\n * @typedef { import('../../types/element').AnnotationBoxModel } AnnotationBoxModel\n * @typedef { import('../../types/element').AnnotationElement } AnnotationElement\n * @typedef { import('../../types/options').AnnotationPointCoordinates } AnnotationPointCoordinates\n * @typedef { import('../../types/label').CoreLabelOptions } CoreLabelOptions\n * @typedef { import('../../types/label').LabelPositionObject } LabelPositionObject\n */\n\n/**\n * @param {number} size\n * @param {number|string} position\n * @returns {number}\n */\nfunction getRelativePosition(size, position) {\n  if (position === 'start') {\n    return 0;\n  }\n  if (position === 'end') {\n    return size;\n  }\n  if (isPercentString(position)) {\n    return toPositivePercent(position) * size;\n  }\n  return size / 2;\n}\n\n/**\n * @param {number} size\n * @param {number|string} value\n * @param {boolean} [positivePercent=true]\n * @returns {number}\n */\nfunction getSize(size, value, positivePercent = true) {\n  if (typeof value === 'number') {\n    return value;\n  } else if (isPercentString(value)) {\n    return (positivePercent ? toPositivePercent(value) : toPercent(value)) * size;\n  }\n  return size;\n}\n\n/**\n * @param {{x: number, width: number}} size\n * @param {CoreLabelOptions} options\n * @returns {number}\n */\nfunction calculateTextAlignment(size, options) {\n  const {x, width} = size;\n  const textAlign = options.textAlign;\n  if (textAlign === 'center') {\n    return x + width / 2;\n  } else if (textAlign === 'end' || textAlign === 'right') {\n    return x + width;\n  }\n  return x;\n}\n\n/**\n * @param {{x: number|string, y: number|string}|string|number} value\n * @param {string|number} defaultValue\n * @returns {{x: number|string, y: number|string}}\n */\nfunction toPosition(value, defaultValue = 'center') {\n  if (isObject(value)) {\n    return {\n      x: valueOrDefault(value.x, defaultValue),\n      y: valueOrDefault(value.y, defaultValue),\n    };\n  }\n  value = valueOrDefault(value, defaultValue);\n  return {\n    x: value,\n    y: value\n  };\n}\n\n/**\n * @param {AnnotationPointCoordinates} options\n * @returns {boolean}\n */\nfunction isBoundToPoint(options) {\n  return options && (defined(options.xValue) || defined(options.yValue));\n}\n\n/**\n * @param {Chart} chart\n * @param {AnnotationBoxModel} properties\n * @param {CoreAnnotationOptions} options\n * @returns {AnnotationElement}\n */\nfunction initAnimationProperties(chart, properties, options) {\n  const initAnim = options.init;\n  if (!initAnim) {\n    return;\n  } else if (initAnim === true) {\n    return applyDefault(properties, options);\n  }\n  return execCallback(chart, properties, options);\n}\n\n/**\n * @param {Object} options\n * @param {Array} hooks\n * @param {Object} hooksContainer\n * @returns {boolean}\n */\nfunction loadHooks(options, hooks, hooksContainer) {\n  let activated = false;\n  hooks.forEach(hook => {\n    if (isFunction(options[hook])) {\n      activated = true;\n      hooksContainer[hook] = options[hook];\n    } else if (defined(hooksContainer[hook])) {\n      delete hooksContainer[hook];\n    }\n  });\n  return activated;\n}\n\nfunction applyDefault(properties, options) {\n  const type = options.type || 'line';\n  return defaultInitAnimation[type](properties);\n}\n\nfunction execCallback(chart, properties, options) {\n  const result = callback(options.init, [{chart, properties, options}]);\n  if (result === true) {\n    return applyDefault(properties, options);\n  } else if (isObject(result)) {\n    return result;\n  }\n}\n\nconst widthCache = new Map();\nconst notRadius = (radius) => isNaN(radius) || radius <= 0;\nconst fontsKey = (fonts) => fonts.reduce(function(prev, item) {\n  prev += item.string;\n  return prev;\n}, '');\n\n/**\n * @typedef { import('chart.js').Point } Point\n * @typedef { import('../../types/label').CoreLabelOptions } CoreLabelOptions\n * @typedef { import('../../types/options').PointAnnotationOptions } PointAnnotationOptions\n */\n\n/**\n * Determine if content is an image or a canvas.\n * @param {*} content\n * @returns boolean|undefined\n * @todo move this function to chart.js helpers\n */\nfunction isImageOrCanvas(content) {\n  if (content && typeof content === 'object') {\n    const type = content.toString();\n    return (type === '[object HTMLImageElement]' || type === '[object HTMLCanvasElement]');\n  }\n}\n\n/**\n * Set the translation on the canvas if the rotation must be applied.\n * @param {CanvasRenderingContext2D} ctx - chart canvas context\n * @param {Point} point - the point of translation\n * @param {number} rotation - rotation (in degrees) to apply\n */\nfunction translate(ctx, {x, y}, rotation) {\n  if (rotation) {\n    ctx.translate(x, y);\n    ctx.rotate(toRadians(rotation));\n    ctx.translate(-x, -y);\n  }\n}\n\n/**\n * @param {CanvasRenderingContext2D} ctx\n * @param {Object} options\n * @returns {boolean|undefined}\n */\nfunction setBorderStyle(ctx, options) {\n  if (options && options.borderWidth) {\n    ctx.lineCap = options.borderCapStyle;\n    ctx.setLineDash(options.borderDash);\n    ctx.lineDashOffset = options.borderDashOffset;\n    ctx.lineJoin = options.borderJoinStyle;\n    ctx.lineWidth = options.borderWidth;\n    ctx.strokeStyle = options.borderColor;\n    return true;\n  }\n}\n\n/**\n * @param {CanvasRenderingContext2D} ctx\n * @param {Object} options\n */\nfunction setShadowStyle(ctx, options) {\n  ctx.shadowColor = options.backgroundShadowColor;\n  ctx.shadowBlur = options.shadowBlur;\n  ctx.shadowOffsetX = options.shadowOffsetX;\n  ctx.shadowOffsetY = options.shadowOffsetY;\n}\n\n/**\n * @param {CanvasRenderingContext2D} ctx\n * @param {CoreLabelOptions} options\n * @returns {{width: number, height: number}}\n */\nfunction measureLabelSize(ctx, options) {\n  const content = options.content;\n  if (isImageOrCanvas(content)) {\n    return {\n      width: getSize(content.width, options.width),\n      height: getSize(content.height, options.height)\n    };\n  }\n  const optFont = options.font;\n  const fonts = isArray(optFont) ? optFont.map(f => toFont(f)) : [toFont(optFont)];\n  const strokeWidth = options.textStrokeWidth;\n  const lines = isArray(content) ? content : [content];\n  const mapKey = lines.join() + fontsKey(fonts) + strokeWidth + (ctx._measureText ? '-spriting' : '');\n  if (!widthCache.has(mapKey)) {\n    widthCache.set(mapKey, calculateLabelSize(ctx, lines, fonts, strokeWidth));\n  }\n  return widthCache.get(mapKey);\n}\n\n/**\n * @param {CanvasRenderingContext2D} ctx\n * @param {{x: number, y: number, width: number, height: number}} rect\n * @param {Object} options\n */\nfunction drawBox(ctx, rect, options) {\n  const {x, y, width, height} = rect;\n  ctx.save();\n  setShadowStyle(ctx, options);\n  const stroke = setBorderStyle(ctx, options);\n  ctx.fillStyle = options.backgroundColor;\n  ctx.beginPath();\n  addRoundedRectPath(ctx, {\n    x, y, w: width, h: height,\n    radius: clampAll(toTRBLCorners(options.borderRadius), 0, Math.min(width, height) / 2)\n  });\n  ctx.closePath();\n  ctx.fill();\n  if (stroke) {\n    ctx.shadowColor = options.borderShadowColor;\n    ctx.stroke();\n  }\n  ctx.restore();\n}\n\n/**\n * @param {CanvasRenderingContext2D} ctx\n * @param {{x: number, y: number, width: number, height: number}} rect\n * @param {CoreLabelOptions} options\n */\nfunction drawLabel(ctx, rect, options) {\n  const content = options.content;\n  if (isImageOrCanvas(content)) {\n    ctx.save();\n    ctx.globalAlpha = getOpacity(options.opacity, content.style.opacity);\n    ctx.drawImage(content, rect.x, rect.y, rect.width, rect.height);\n    ctx.restore();\n    return;\n  }\n  const labels = isArray(content) ? content : [content];\n  const optFont = options.font;\n  const fonts = isArray(optFont) ? optFont.map(f => toFont(f)) : [toFont(optFont)];\n  const optColor = options.color;\n  const colors = isArray(optColor) ? optColor : [optColor];\n  const x = calculateTextAlignment(rect, options);\n  const y = rect.y + options.textStrokeWidth / 2;\n  ctx.save();\n  ctx.textBaseline = 'middle';\n  ctx.textAlign = options.textAlign;\n  if (setTextStrokeStyle(ctx, options)) {\n    applyLabelDecoration(ctx, {x, y}, labels, fonts);\n  }\n  applyLabelContent(ctx, {x, y}, labels, {fonts, colors});\n  ctx.restore();\n}\n\nfunction setTextStrokeStyle(ctx, options) {\n  if (options.textStrokeWidth > 0) {\n    // https://stackoverflow.com/questions/13627111/drawing-text-with-an-outer-stroke-with-html5s-canvas\n    ctx.lineJoin = 'round';\n    ctx.miterLimit = 2;\n    ctx.lineWidth = options.textStrokeWidth;\n    ctx.strokeStyle = options.textStrokeColor;\n    return true;\n  }\n}\n\n/**\n * @param {CanvasRenderingContext2D} ctx\n * @param {{radius: number, options: PointAnnotationOptions}} element\n * @param {number} x\n * @param {number} y\n */\nfunction drawPoint(ctx, element, x, y) {\n  const {radius, options} = element;\n  const style = options.pointStyle;\n  const rotation = options.rotation;\n  let rad = (rotation || 0) * RAD_PER_DEG;\n\n  if (isImageOrCanvas(style)) {\n    ctx.save();\n    ctx.translate(x, y);\n    ctx.rotate(rad);\n    ctx.drawImage(style, -style.width / 2, -style.height / 2, style.width, style.height);\n    ctx.restore();\n    return;\n  }\n  if (notRadius(radius)) {\n    return;\n  }\n  drawPointStyle(ctx, {x, y, radius, rotation, style, rad});\n}\n\nfunction drawPointStyle(ctx, {x, y, radius, rotation, style, rad}) {\n  let xOffset, yOffset, size, cornerRadius;\n  ctx.beginPath();\n\n  switch (style) {\n  // Default includes circle\n  default:\n    ctx.arc(x, y, radius, 0, TAU);\n    ctx.closePath();\n    break;\n  case 'triangle':\n    ctx.moveTo(x + Math.sin(rad) * radius, y - Math.cos(rad) * radius);\n    rad += TWO_THIRDS_PI;\n    ctx.lineTo(x + Math.sin(rad) * radius, y - Math.cos(rad) * radius);\n    rad += TWO_THIRDS_PI;\n    ctx.lineTo(x + Math.sin(rad) * radius, y - Math.cos(rad) * radius);\n    ctx.closePath();\n    break;\n  case 'rectRounded':\n    // NOTE: the rounded rect implementation changed to use `arc` instead of\n    // `quadraticCurveTo` since it generates better results when rect is\n    // almost a circle. 0.516 (instead of 0.5) produces results with visually\n    // closer proportion to the previous impl and it is inscribed in the\n    // circle with `radius`. For more details, see the following PRs:\n    // https://github.com/chartjs/Chart.js/issues/5597\n    // https://github.com/chartjs/Chart.js/issues/5858\n    cornerRadius = radius * 0.516;\n    size = radius - cornerRadius;\n    xOffset = Math.cos(rad + QUARTER_PI) * size;\n    yOffset = Math.sin(rad + QUARTER_PI) * size;\n    ctx.arc(x - xOffset, y - yOffset, cornerRadius, rad - PI, rad - HALF_PI);\n    ctx.arc(x + yOffset, y - xOffset, cornerRadius, rad - HALF_PI, rad);\n    ctx.arc(x + xOffset, y + yOffset, cornerRadius, rad, rad + HALF_PI);\n    ctx.arc(x - yOffset, y + xOffset, cornerRadius, rad + HALF_PI, rad + PI);\n    ctx.closePath();\n    break;\n  case 'rect':\n    if (!rotation) {\n      size = Math.SQRT1_2 * radius;\n      ctx.rect(x - size, y - size, 2 * size, 2 * size);\n      break;\n    }\n    rad += QUARTER_PI;\n    /* falls through */\n  case 'rectRot':\n    xOffset = Math.cos(rad) * radius;\n    yOffset = Math.sin(rad) * radius;\n    ctx.moveTo(x - xOffset, y - yOffset);\n    ctx.lineTo(x + yOffset, y - xOffset);\n    ctx.lineTo(x + xOffset, y + yOffset);\n    ctx.lineTo(x - yOffset, y + xOffset);\n    ctx.closePath();\n    break;\n  case 'crossRot':\n    rad += QUARTER_PI;\n    /* falls through */\n  case 'cross':\n    xOffset = Math.cos(rad) * radius;\n    yOffset = Math.sin(rad) * radius;\n    ctx.moveTo(x - xOffset, y - yOffset);\n    ctx.lineTo(x + xOffset, y + yOffset);\n    ctx.moveTo(x + yOffset, y - xOffset);\n    ctx.lineTo(x - yOffset, y + xOffset);\n    break;\n  case 'star':\n    xOffset = Math.cos(rad) * radius;\n    yOffset = Math.sin(rad) * radius;\n    ctx.moveTo(x - xOffset, y - yOffset);\n    ctx.lineTo(x + xOffset, y + yOffset);\n    ctx.moveTo(x + yOffset, y - xOffset);\n    ctx.lineTo(x - yOffset, y + xOffset);\n    rad += QUARTER_PI;\n    xOffset = Math.cos(rad) * radius;\n    yOffset = Math.sin(rad) * radius;\n    ctx.moveTo(x - xOffset, y - yOffset);\n    ctx.lineTo(x + xOffset, y + yOffset);\n    ctx.moveTo(x + yOffset, y - xOffset);\n    ctx.lineTo(x - yOffset, y + xOffset);\n    break;\n  case 'line':\n    xOffset = Math.cos(rad) * radius;\n    yOffset = Math.sin(rad) * radius;\n    ctx.moveTo(x - xOffset, y - yOffset);\n    ctx.lineTo(x + xOffset, y + yOffset);\n    break;\n  case 'dash':\n    ctx.moveTo(x, y);\n    ctx.lineTo(x + Math.cos(rad) * radius, y + Math.sin(rad) * radius);\n    break;\n  }\n\n  ctx.fill();\n}\n\nfunction calculateLabelSize(ctx, lines, fonts, strokeWidth) {\n  ctx.save();\n  const count = lines.length;\n  let width = 0;\n  let height = strokeWidth;\n  for (let i = 0; i < count; i++) {\n    const font = fonts[Math.min(i, fonts.length - 1)];\n    ctx.font = font.string;\n    const text = lines[i];\n    width = Math.max(width, ctx.measureText(text).width + strokeWidth);\n    height += font.lineHeight;\n  }\n  ctx.restore();\n  return {width, height};\n}\n\nfunction applyLabelDecoration(ctx, {x, y}, labels, fonts) {\n  ctx.beginPath();\n  let lhs = 0;\n  labels.forEach(function(l, i) {\n    const f = fonts[Math.min(i, fonts.length - 1)];\n    const lh = f.lineHeight;\n    ctx.font = f.string;\n    ctx.strokeText(l, x, y + lh / 2 + lhs);\n    lhs += lh;\n  });\n  ctx.stroke();\n}\n\nfunction applyLabelContent(ctx, {x, y}, labels, {fonts, colors}) {\n  let lhs = 0;\n  labels.forEach(function(l, i) {\n    const c = colors[Math.min(i, colors.length - 1)];\n    const f = fonts[Math.min(i, fonts.length - 1)];\n    const lh = f.lineHeight;\n    ctx.beginPath();\n    ctx.font = f.string;\n    ctx.fillStyle = c;\n    ctx.fillText(l, x, y + lh / 2 + lhs);\n    lhs += lh;\n    ctx.fill();\n  });\n}\n\nfunction getOpacity(value, elementValue) {\n  const opacity = isNumber(value) ? value : elementValue;\n  return isNumber(opacity) ? clamp(opacity, 0, 1) : 1;\n}\n\nconst limitedLineScale = {\n  xScaleID: {min: 'xMin', max: 'xMax', start: 'left', end: 'right', startProp: 'x', endProp: 'x2'},\n  yScaleID: {min: 'yMin', max: 'yMax', start: 'bottom', end: 'top', startProp: 'y', endProp: 'y2'}\n};\n\n/**\n * @typedef { import(\"chart.js\").Chart } Chart\n * @typedef { import(\"chart.js\").Scale } Scale\n * @typedef { import(\"chart.js\").Point } Point\n * @typedef { import('../../types/element').AnnotationBoxModel } AnnotationBoxModel\n * @typedef { import('../../types/options').CoreAnnotationOptions } CoreAnnotationOptions\n * @typedef { import('../../types/options').LineAnnotationOptions } LineAnnotationOptions\n * @typedef { import('../../types/options').PointAnnotationOptions } PointAnnotationOptions\n * @typedef { import('../../types/options').PolygonAnnotationOptions } PolygonAnnotationOptions\n */\n\n/**\n * @param {Scale} scale\n * @param {number|string} value\n * @param {number} fallback\n * @returns {number}\n */\nfunction scaleValue(scale, value, fallback) {\n  value = typeof value === 'number' ? value : scale.parse(value);\n  return isFinite(value) ? scale.getPixelForValue(value) : fallback;\n}\n\n/**\n * Search the scale defined in chartjs by the axis related to the annotation options key.\n * @param {{ [key: string]: Scale }} scales\n * @param {CoreAnnotationOptions} options\n * @param {string} key\n * @returns {string}\n */\nfunction retrieveScaleID(scales, options, key) {\n  const scaleID = options[key];\n  if (scaleID || key === 'scaleID') {\n    return scaleID;\n  }\n  const axis = key.charAt(0);\n  const axes = Object.values(scales).filter((scale) => scale.axis && scale.axis === axis);\n  if (axes.length) {\n    return axes[0].id;\n  }\n  return axis;\n}\n\n/**\n * @param {Scale} scale\n * @param {{min: number, max: number, start: number, end: number}} options\n * @returns {{start: number, end: number}|undefined}\n */\nfunction getDimensionByScale(scale, options) {\n  if (scale) {\n    const reverse = scale.options.reverse;\n    const start = scaleValue(scale, options.min, reverse ? options.end : options.start);\n    const end = scaleValue(scale, options.max, reverse ? options.start : options.end);\n    return {\n      start,\n      end\n    };\n  }\n}\n\n/**\n * @param {Chart} chart\n * @param {CoreAnnotationOptions} options\n * @returns {Point}\n */\nfunction getChartPoint(chart, options) {\n  const {chartArea, scales} = chart;\n  const xScale = scales[retrieveScaleID(scales, options, 'xScaleID')];\n  const yScale = scales[retrieveScaleID(scales, options, 'yScaleID')];\n  let x = chartArea.width / 2;\n  let y = chartArea.height / 2;\n\n  if (xScale) {\n    x = scaleValue(xScale, options.xValue, xScale.left + xScale.width / 2);\n  }\n\n  if (yScale) {\n    y = scaleValue(yScale, options.yValue, yScale.top + yScale.height / 2);\n  }\n  return {x, y};\n}\n\n/**\n * @param {Chart} chart\n * @param {CoreAnnotationOptions} options\n * @returns {AnnotationBoxModel}\n */\nfunction resolveBoxProperties(chart, options) {\n  const scales = chart.scales;\n  const xScale = scales[retrieveScaleID(scales, options, 'xScaleID')];\n  const yScale = scales[retrieveScaleID(scales, options, 'yScaleID')];\n\n  if (!xScale && !yScale) {\n    return {};\n  }\n\n  let {left: x, right: x2} = xScale || chart.chartArea;\n  let {top: y, bottom: y2} = yScale || chart.chartArea;\n  const xDim = getChartDimensionByScale(xScale, {min: options.xMin, max: options.xMax, start: x, end: x2});\n  x = xDim.start;\n  x2 = xDim.end;\n  const yDim = getChartDimensionByScale(yScale, {min: options.yMin, max: options.yMax, start: y2, end: y});\n  y = yDim.start;\n  y2 = yDim.end;\n\n  return {\n    x,\n    y,\n    x2,\n    y2,\n    width: x2 - x,\n    height: y2 - y,\n    centerX: x + (x2 - x) / 2,\n    centerY: y + (y2 - y) / 2\n  };\n}\n\n/**\n * @param {Chart} chart\n * @param {PointAnnotationOptions|PolygonAnnotationOptions} options\n * @returns {AnnotationBoxModel}\n */\nfunction resolvePointProperties(chart, options) {\n  if (!isBoundToPoint(options)) {\n    const box = resolveBoxProperties(chart, options);\n    let radius = options.radius;\n    if (!radius || isNaN(radius)) {\n      radius = Math.min(box.width, box.height) / 2;\n      options.radius = radius;\n    }\n    const size = radius * 2;\n    const adjustCenterX = box.centerX + options.xAdjust;\n    const adjustCenterY = box.centerY + options.yAdjust;\n    return {\n      x: adjustCenterX - radius,\n      y: adjustCenterY - radius,\n      x2: adjustCenterX + radius,\n      y2: adjustCenterY + radius,\n      centerX: adjustCenterX,\n      centerY: adjustCenterY,\n      width: size,\n      height: size,\n      radius\n    };\n  }\n  return getChartCircle(chart, options);\n}\n/**\n * @param {Chart} chart\n * @param {LineAnnotationOptions} options\n * @returns {AnnotationBoxModel}\n */\nfunction resolveLineProperties(chart, options) {\n  const {scales, chartArea} = chart;\n  const scale = scales[options.scaleID];\n  const area = {x: chartArea.left, y: chartArea.top, x2: chartArea.right, y2: chartArea.bottom};\n\n  if (scale) {\n    resolveFullLineProperties(scale, area, options);\n  } else {\n    resolveLimitedLineProperties(scales, area, options);\n  }\n  return area;\n}\n\n/**\n * @param {Chart} chart\n * @param {CoreAnnotationOptions} options\n * @param {boolean} [centerBased=false]\n * @returns {AnnotationBoxModel}\n */\nfunction resolveBoxAndLabelProperties(chart, options) {\n  const properties = resolveBoxProperties(chart, options);\n  properties.initProperties = initAnimationProperties(chart, properties, options);\n  properties.elements = [{\n    type: 'label',\n    optionScope: 'label',\n    properties: resolveLabelElementProperties$1(chart, properties, options),\n    initProperties: properties.initProperties\n  }];\n  return properties;\n}\n\nfunction getChartCircle(chart, options) {\n  const point = getChartPoint(chart, options);\n  const size = options.radius * 2;\n  return {\n    x: point.x - options.radius + options.xAdjust,\n    y: point.y - options.radius + options.yAdjust,\n    x2: point.x + options.radius + options.xAdjust,\n    y2: point.y + options.radius + options.yAdjust,\n    centerX: point.x + options.xAdjust,\n    centerY: point.y + options.yAdjust,\n    radius: options.radius,\n    width: size,\n    height: size\n  };\n}\n\nfunction getChartDimensionByScale(scale, options) {\n  const result = getDimensionByScale(scale, options) || options;\n  return {\n    start: Math.min(result.start, result.end),\n    end: Math.max(result.start, result.end)\n  };\n}\n\nfunction resolveFullLineProperties(scale, area, options) {\n  const min = scaleValue(scale, options.value, NaN);\n  const max = scaleValue(scale, options.endValue, min);\n  if (scale.isHorizontal()) {\n    area.x = min;\n    area.x2 = max;\n  } else {\n    area.y = min;\n    area.y2 = max;\n  }\n}\n\nfunction resolveLimitedLineProperties(scales, area, options) {\n  for (const scaleId of Object.keys(limitedLineScale)) {\n    const scale = scales[retrieveScaleID(scales, options, scaleId)];\n    if (scale) {\n      const {min, max, start, end, startProp, endProp} = limitedLineScale[scaleId];\n      const dim = getDimensionByScale(scale, {min: options[min], max: options[max], start: scale[start], end: scale[end]});\n      area[startProp] = dim.start;\n      area[endProp] = dim.end;\n    }\n  }\n}\n\nfunction calculateX({properties, options}, labelSize, position, padding) {\n  const {x: start, x2: end, width: size} = properties;\n  return calculatePosition$1({start, end, size, borderWidth: options.borderWidth}, {\n    position: position.x,\n    padding: {start: padding.left, end: padding.right},\n    adjust: options.label.xAdjust,\n    size: labelSize.width\n  });\n}\n\nfunction calculateY({properties, options}, labelSize, position, padding) {\n  const {y: start, y2: end, height: size} = properties;\n  return calculatePosition$1({start, end, size, borderWidth: options.borderWidth}, {\n    position: position.y,\n    padding: {start: padding.top, end: padding.bottom},\n    adjust: options.label.yAdjust,\n    size: labelSize.height\n  });\n}\n\nfunction calculatePosition$1(boxOpts, labelOpts) {\n  const {start, end, borderWidth} = boxOpts;\n  const {position, padding: {start: padStart, end: padEnd}, adjust} = labelOpts;\n  const availableSize = end - borderWidth - start - padStart - padEnd - labelOpts.size;\n  return start + borderWidth / 2 + adjust + getRelativePosition(availableSize, position);\n}\n\nfunction resolveLabelElementProperties$1(chart, properties, options) {\n  const label = options.label;\n  label.backgroundColor = 'transparent';\n  label.callout.display = false;\n  const position = toPosition(label.position);\n  const padding = toPadding(label.padding);\n  const labelSize = measureLabelSize(chart.ctx, label);\n  const x = calculateX({properties, options}, labelSize, position, padding);\n  const y = calculateY({properties, options}, labelSize, position, padding);\n  const width = labelSize.width + padding.width;\n  const height = labelSize.height + padding.height;\n  return {\n    x,\n    y,\n    x2: x + width,\n    y2: y + height,\n    width,\n    height,\n    centerX: x + width / 2,\n    centerY: y + height / 2,\n    rotation: label.rotation\n  };\n\n}\n\n/**\n * @typedef {import('chart.js').Point} Point\n */\n\n/**\n * Rotate a `point` relative to `center` point by `angle`\n * @param {Point} point - the point to rotate\n * @param {Point} center - center point for rotation\n * @param {number} angle - angle for rotation, in radians\n * @returns {Point} rotated point\n */\nfunction rotated(point, center, angle) {\n  const cos = Math.cos(angle);\n  const sin = Math.sin(angle);\n  const cx = center.x;\n  const cy = center.y;\n\n  return {\n    x: cx + cos * (point.x - cx) - sin * (point.y - cy),\n    y: cy + sin * (point.x - cx) + cos * (point.y - cy)\n  };\n}\n\nconst moveHooks = ['enter', 'leave'];\n\n/**\n * @typedef { import(\"chart.js\").Chart } Chart\n * @typedef { import('../../types/options').AnnotationPluginOptions } AnnotationPluginOptions\n */\n\nconst eventHooks = moveHooks.concat('click');\n\n/**\n * @param {Chart} chart\n * @param {Object} state\n * @param {AnnotationPluginOptions} options\n */\nfunction updateListeners(chart, state, options) {\n  state.listened = loadHooks(options, eventHooks, state.listeners);\n  state.moveListened = false;\n  state._getElements = getElements; // for testing\n\n  moveHooks.forEach(hook => {\n    if (isFunction(options[hook])) {\n      state.moveListened = true;\n    }\n  });\n\n  if (!state.listened || !state.moveListened) {\n    state.annotations.forEach(scope => {\n      if (!state.listened && isFunction(scope.click)) {\n        state.listened = true;\n      }\n      if (!state.moveListened) {\n        moveHooks.forEach(hook => {\n          if (isFunction(scope[hook])) {\n            state.listened = true;\n            state.moveListened = true;\n          }\n        });\n      }\n    });\n  }\n}\n\n/**\n * @param {Object} state\n * @param {ChartEvent} event\n * @param {AnnotationPluginOptions} options\n * @return {boolean|undefined}\n */\nfunction handleEvent(state, event, options) {\n  if (state.listened) {\n    switch (event.type) {\n    case 'mousemove':\n    case 'mouseout':\n      return handleMoveEvents(state, event, options);\n    case 'click':\n      return handleClickEvents(state, event, options);\n    }\n  }\n}\n\nfunction handleMoveEvents(state, event, options) {\n  if (!state.moveListened) {\n    return;\n  }\n\n  let elements;\n\n  if (event.type === 'mousemove') {\n    elements = getElements(state, event, options.interaction);\n  } else {\n    elements = [];\n  }\n\n  const previous = state.hovered;\n  state.hovered = elements;\n\n  const context = {state, event};\n  let changed = dispatchMoveEvents(context, 'leave', previous, elements);\n  return dispatchMoveEvents(context, 'enter', elements, previous) || changed;\n}\n\nfunction dispatchMoveEvents({state, event}, hook, elements, checkElements) {\n  let changed;\n  for (const element of elements) {\n    if (checkElements.indexOf(element) < 0) {\n      changed = dispatchEvent(element.options[hook] || state.listeners[hook], element, event) || changed;\n    }\n  }\n  return changed;\n}\n\nfunction handleClickEvents(state, event, options) {\n  const listeners = state.listeners;\n  const elements = getElements(state, event, options.interaction);\n  let changed;\n  for (const element of elements) {\n    changed = dispatchEvent(element.options.click || listeners.click, element, event) || changed;\n  }\n  return changed;\n}\n\nfunction dispatchEvent(handler, element, event) {\n  return callback(handler, [element.$context, event]) === true;\n}\n\n/**\n * @typedef { import(\"chart.js\").Chart } Chart\n * @typedef { import('../../types/options').AnnotationPluginOptions } AnnotationPluginOptions\n * @typedef { import('../../types/element').AnnotationElement } AnnotationElement\n */\n\nconst elementHooks = ['afterDraw', 'beforeDraw'];\n\n/**\n * @param {Chart} chart\n * @param {Object} state\n * @param {AnnotationPluginOptions} options\n */\nfunction updateHooks(chart, state, options) {\n  const visibleElements = state.visibleElements;\n  state.hooked = loadHooks(options, elementHooks, state.hooks);\n\n  if (!state.hooked) {\n    visibleElements.forEach(scope => {\n      if (!state.hooked) {\n        elementHooks.forEach(hook => {\n          if (isFunction(scope.options[hook])) {\n            state.hooked = true;\n          }\n        });\n      }\n    });\n  }\n}\n\n/**\n * @param {Object} state\n * @param {AnnotationElement} element\n * @param {string} hook\n */\nfunction invokeHook(state, element, hook) {\n  if (state.hooked) {\n    const callbackHook = element.options[hook] || state.hooks[hook];\n    return callback(callbackHook, [element.$context]);\n  }\n}\n\n/**\n * @typedef { import(\"chart.js\").Chart } Chart\n * @typedef { import(\"chart.js\").Scale } Scale\n * @typedef { import('../../types/options').CoreAnnotationOptions } CoreAnnotationOptions\n */\n\n/**\n * @param {Chart} chart\n * @param {Scale} scale\n * @param {CoreAnnotationOptions[]} annotations\n */\nfunction adjustScaleRange(chart, scale, annotations) {\n  const range = getScaleLimits(chart.scales, scale, annotations);\n  let changed = changeScaleLimit(scale, range, 'min', 'suggestedMin');\n  changed = changeScaleLimit(scale, range, 'max', 'suggestedMax') || changed;\n  if (changed && isFunction(scale.handleTickRangeOptions)) {\n    scale.handleTickRangeOptions();\n  }\n}\n\n/**\n * @param {CoreAnnotationOptions[]} annotations\n * @param {{ [key: string]: Scale }} scales\n */\nfunction verifyScaleOptions(annotations, scales) {\n  for (const annotation of annotations) {\n    verifyScaleIDs(annotation, scales);\n  }\n}\n\nfunction changeScaleLimit(scale, range, limit, suggestedLimit) {\n  if (isFinite(range[limit]) && !scaleLimitDefined(scale.options, limit, suggestedLimit)) {\n    const changed = scale[limit] !== range[limit];\n    scale[limit] = range[limit];\n    return changed;\n  }\n}\n\nfunction scaleLimitDefined(scaleOptions, limit, suggestedLimit) {\n  return defined(scaleOptions[limit]) || defined(scaleOptions[suggestedLimit]);\n}\n\nfunction verifyScaleIDs(annotation, scales) {\n  for (const key of ['scaleID', 'xScaleID', 'yScaleID']) {\n    const scaleID = retrieveScaleID(scales, annotation, key);\n    if (scaleID && !scales[scaleID] && verifyProperties(annotation, key)) {\n      console.warn(`No scale found with id '${scaleID}' for annotation '${annotation.id}'`);\n    }\n  }\n}\n\nfunction verifyProperties(annotation, key) {\n  if (key === 'scaleID') {\n    return true;\n  }\n  const axis = key.charAt(0);\n  for (const prop of ['Min', 'Max', 'Value']) {\n    if (defined(annotation[axis + prop])) {\n      return true;\n    }\n  }\n  return false;\n}\n\nfunction getScaleLimits(scales, scale, annotations) {\n  const axis = scale.axis;\n  const scaleID = scale.id;\n  const scaleIDOption = axis + 'ScaleID';\n  const limits = {\n    min: valueOrDefault(scale.min, Number.NEGATIVE_INFINITY),\n    max: valueOrDefault(scale.max, Number.POSITIVE_INFINITY)\n  };\n  for (const annotation of annotations) {\n    if (annotation.scaleID === scaleID) {\n      updateLimits(annotation, scale, ['value', 'endValue'], limits);\n    } else if (retrieveScaleID(scales, annotation, scaleIDOption) === scaleID) {\n      updateLimits(annotation, scale, [axis + 'Min', axis + 'Max', axis + 'Value'], limits);\n    }\n  }\n  return limits;\n}\n\nfunction updateLimits(annotation, scale, props, limits) {\n  for (const prop of props) {\n    const raw = annotation[prop];\n    if (defined(raw)) {\n      const value = scale.parse(raw);\n      limits.min = Math.min(limits.min, value);\n      limits.max = Math.max(limits.max, value);\n    }\n  }\n}\n\nclass BoxAnnotation extends Element {\n\n  inRange(mouseX, mouseY, axis, useFinalPosition) {\n    const {x, y} = rotated({x: mouseX, y: mouseY}, this.getCenterPoint(useFinalPosition), toRadians(-this.options.rotation));\n    return inBoxRange({x, y}, this.getProps(['x', 'y', 'x2', 'y2'], useFinalPosition), axis, this.options.borderWidth);\n  }\n\n  getCenterPoint(useFinalPosition) {\n    return getElementCenterPoint(this, useFinalPosition);\n  }\n\n  draw(ctx) {\n    ctx.save();\n    translate(ctx, this.getCenterPoint(), this.options.rotation);\n    drawBox(ctx, this, this.options);\n    ctx.restore();\n  }\n\n  get label() {\n    return this.elements && this.elements[0];\n  }\n\n  resolveElementProperties(chart, options) {\n    return resolveBoxAndLabelProperties(chart, options);\n  }\n}\n\nBoxAnnotation.id = 'boxAnnotation';\n\nBoxAnnotation.defaults = {\n  adjustScaleRange: true,\n  backgroundShadowColor: 'transparent',\n  borderCapStyle: 'butt',\n  borderDash: [],\n  borderDashOffset: 0,\n  borderJoinStyle: 'miter',\n  borderRadius: 0,\n  borderShadowColor: 'transparent',\n  borderWidth: 1,\n  display: true,\n  init: undefined,\n  label: {\n    backgroundColor: 'transparent',\n    borderWidth: 0,\n    callout: {\n      display: false\n    },\n    color: 'black',\n    content: null,\n    display: false,\n    drawTime: undefined,\n    font: {\n      family: undefined,\n      lineHeight: undefined,\n      size: undefined,\n      style: undefined,\n      weight: 'bold'\n    },\n    height: undefined,\n    opacity: undefined,\n    padding: 6,\n    position: 'center',\n    rotation: undefined,\n    textAlign: 'start',\n    textStrokeColor: undefined,\n    textStrokeWidth: 0,\n    width: undefined,\n    xAdjust: 0,\n    yAdjust: 0,\n    z: undefined\n  },\n  rotation: 0,\n  shadowBlur: 0,\n  shadowOffsetX: 0,\n  shadowOffsetY: 0,\n  xMax: undefined,\n  xMin: undefined,\n  xScaleID: undefined,\n  yMax: undefined,\n  yMin: undefined,\n  yScaleID: undefined,\n  z: 0\n};\n\nBoxAnnotation.defaultRoutes = {\n  borderColor: 'color',\n  backgroundColor: 'color'\n};\n\nBoxAnnotation.descriptors = {\n  label: {\n    _fallback: true\n  }\n};\n\nconst positions = ['left', 'bottom', 'top', 'right'];\n\nclass LabelAnnotation extends Element {\n\n  inRange(mouseX, mouseY, axis, useFinalPosition) {\n    const {x, y} = rotated({x: mouseX, y: mouseY}, this.getCenterPoint(useFinalPosition), toRadians(-this.rotation));\n    return inBoxRange({x, y}, this.getProps(['x', 'y', 'x2', 'y2'], useFinalPosition), axis, this.options.borderWidth);\n  }\n\n  getCenterPoint(useFinalPosition) {\n    return getElementCenterPoint(this, useFinalPosition);\n  }\n\n  draw(ctx) {\n    const options = this.options;\n    const visible = !defined(this._visible) || this._visible;\n    if (!options.display || !options.content || !visible) {\n      return;\n    }\n    ctx.save();\n    translate(ctx, this.getCenterPoint(), this.rotation);\n    drawCallout(ctx, this);\n    drawBox(ctx, this, options);\n    drawLabel(ctx, getLabelSize(this), options);\n    ctx.restore();\n  }\n\n  resolveElementProperties(chart, options) {\n    let point;\n    if (!isBoundToPoint(options)) {\n      const {centerX, centerY} = resolveBoxProperties(chart, options);\n      point = {x: centerX, y: centerY};\n    } else {\n      point = getChartPoint(chart, options);\n    }\n    const padding = toPadding(options.padding);\n    const labelSize = measureLabelSize(chart.ctx, options);\n    const boxSize = measureRect(point, labelSize, options, padding);\n    return {\n      initProperties: initAnimationProperties(chart, boxSize, options),\n      pointX: point.x,\n      pointY: point.y,\n      ...boxSize,\n      rotation: options.rotation\n    };\n  }\n}\n\nLabelAnnotation.id = 'labelAnnotation';\n\nLabelAnnotation.defaults = {\n  adjustScaleRange: true,\n  backgroundColor: 'transparent',\n  backgroundShadowColor: 'transparent',\n  borderCapStyle: 'butt',\n  borderDash: [],\n  borderDashOffset: 0,\n  borderJoinStyle: 'miter',\n  borderRadius: 0,\n  borderShadowColor: 'transparent',\n  borderWidth: 0,\n  callout: {\n    borderCapStyle: 'butt',\n    borderColor: undefined,\n    borderDash: [],\n    borderDashOffset: 0,\n    borderJoinStyle: 'miter',\n    borderWidth: 1,\n    display: false,\n    margin: 5,\n    position: 'auto',\n    side: 5,\n    start: '50%',\n  },\n  color: 'black',\n  content: null,\n  display: true,\n  font: {\n    family: undefined,\n    lineHeight: undefined,\n    size: undefined,\n    style: undefined,\n    weight: undefined\n  },\n  height: undefined,\n  init: undefined,\n  opacity: undefined,\n  padding: 6,\n  position: 'center',\n  rotation: 0,\n  shadowBlur: 0,\n  shadowOffsetX: 0,\n  shadowOffsetY: 0,\n  textAlign: 'center',\n  textStrokeColor: undefined,\n  textStrokeWidth: 0,\n  width: undefined,\n  xAdjust: 0,\n  xMax: undefined,\n  xMin: undefined,\n  xScaleID: undefined,\n  xValue: undefined,\n  yAdjust: 0,\n  yMax: undefined,\n  yMin: undefined,\n  yScaleID: undefined,\n  yValue: undefined,\n  z: 0\n};\n\nLabelAnnotation.defaultRoutes = {\n  borderColor: 'color'\n};\n\nfunction measureRect(point, size, options, padding) {\n  const width = size.width + padding.width + options.borderWidth;\n  const height = size.height + padding.height + options.borderWidth;\n  const position = toPosition(options.position, 'center');\n  const x = calculatePosition(point.x, width, options.xAdjust, position.x);\n  const y = calculatePosition(point.y, height, options.yAdjust, position.y);\n\n  return {\n    x,\n    y,\n    x2: x + width,\n    y2: y + height,\n    width,\n    height,\n    centerX: x + width / 2,\n    centerY: y + height / 2\n  };\n}\n\nfunction calculatePosition(start, size, adjust = 0, position) {\n  return start - getRelativePosition(size, position) + adjust;\n}\n\nfunction drawCallout(ctx, element) {\n  const {pointX, pointY, options} = element;\n  const callout = options.callout;\n  const calloutPosition = callout && callout.display && resolveCalloutPosition(element, callout);\n  if (!calloutPosition || isPointInRange(element, callout, calloutPosition)) {\n    return;\n  }\n\n  ctx.save();\n  ctx.beginPath();\n  const stroke = setBorderStyle(ctx, callout);\n  if (!stroke) {\n    return ctx.restore();\n  }\n  const {separatorStart, separatorEnd} = getCalloutSeparatorCoord(element, calloutPosition);\n  const {sideStart, sideEnd} = getCalloutSideCoord(element, calloutPosition, separatorStart);\n  if (callout.margin > 0 || options.borderWidth === 0) {\n    ctx.moveTo(separatorStart.x, separatorStart.y);\n    ctx.lineTo(separatorEnd.x, separatorEnd.y);\n  }\n  ctx.moveTo(sideStart.x, sideStart.y);\n  ctx.lineTo(sideEnd.x, sideEnd.y);\n  const rotatedPoint = rotated({x: pointX, y: pointY}, element.getCenterPoint(), toRadians(-element.rotation));\n  ctx.lineTo(rotatedPoint.x, rotatedPoint.y);\n  ctx.stroke();\n  ctx.restore();\n}\n\nfunction getCalloutSeparatorCoord(element, position) {\n  const {x, y, x2, y2} = element;\n  const adjust = getCalloutSeparatorAdjust(element, position);\n  let separatorStart, separatorEnd;\n  if (position === 'left' || position === 'right') {\n    separatorStart = {x: x + adjust, y};\n    separatorEnd = {x: separatorStart.x, y: y2};\n  } else {\n    //  position 'top' or 'bottom'\n    separatorStart = {x, y: y + adjust};\n    separatorEnd = {x: x2, y: separatorStart.y};\n  }\n  return {separatorStart, separatorEnd};\n}\n\nfunction getCalloutSeparatorAdjust(element, position) {\n  const {width, height, options} = element;\n  const adjust = options.callout.margin + options.borderWidth / 2;\n  if (position === 'right') {\n    return width + adjust;\n  } else if (position === 'bottom') {\n    return height + adjust;\n  }\n  return -adjust;\n}\n\nfunction getCalloutSideCoord(element, position, separatorStart) {\n  const {y, width, height, options} = element;\n  const start = options.callout.start;\n  const side = getCalloutSideAdjust(position, options.callout);\n  let sideStart, sideEnd;\n  if (position === 'left' || position === 'right') {\n    sideStart = {x: separatorStart.x, y: y + getSize(height, start)};\n    sideEnd = {x: sideStart.x + side, y: sideStart.y};\n  } else {\n    //  position 'top' or 'bottom'\n    sideStart = {x: separatorStart.x + getSize(width, start), y: separatorStart.y};\n    sideEnd = {x: sideStart.x, y: sideStart.y + side};\n  }\n  return {sideStart, sideEnd};\n}\n\nfunction getCalloutSideAdjust(position, options) {\n  const side = options.side;\n  if (position === 'left' || position === 'top') {\n    return -side;\n  }\n  return side;\n}\n\nfunction resolveCalloutPosition(element, options) {\n  const position = options.position;\n  if (positions.includes(position)) {\n    return position;\n  }\n  return resolveCalloutAutoPosition(element, options);\n}\n\nfunction resolveCalloutAutoPosition(element, options) {\n  const {x, y, x2, y2, width, height, pointX, pointY, centerX, centerY, rotation} = element;\n  const center = {x: centerX, y: centerY};\n  const start = options.start;\n  const xAdjust = getSize(width, start);\n  const yAdjust = getSize(height, start);\n  const xPoints = [x, x + xAdjust, x + xAdjust, x2];\n  const yPoints = [y + yAdjust, y2, y, y2];\n  const result = [];\n  for (let index = 0; index < 4; index++) {\n    const rotatedPoint = rotated({x: xPoints[index], y: yPoints[index]}, center, toRadians(rotation));\n    result.push({\n      position: positions[index],\n      distance: distanceBetweenPoints(rotatedPoint, {x: pointX, y: pointY})\n    });\n  }\n  return result.sort((a, b) => a.distance - b.distance)[0].position;\n}\n\nfunction getLabelSize({x, y, width, height, options}) {\n  const hBorderWidth = options.borderWidth / 2;\n  const padding = toPadding(options.padding);\n  return {\n    x: x + padding.left + hBorderWidth,\n    y: y + padding.top + hBorderWidth,\n    width: width - padding.left - padding.right - options.borderWidth,\n    height: height - padding.top - padding.bottom - options.borderWidth\n  };\n}\n\nfunction isPointInRange(element, callout, position) {\n  const {pointX, pointY} = element;\n  const margin = callout.margin;\n  let x = pointX;\n  let y = pointY;\n  if (position === 'left') {\n    x += margin;\n  } else if (position === 'right') {\n    x -= margin;\n  } else if (position === 'top') {\n    y += margin;\n  } else if (position === 'bottom') {\n    y -= margin;\n  }\n  return element.inRange(x, y);\n}\n\nconst pointInLine = (p1, p2, t) => ({x: p1.x + t * (p2.x - p1.x), y: p1.y + t * (p2.y - p1.y)});\nconst interpolateX = (y, p1, p2) => pointInLine(p1, p2, Math.abs((y - p1.y) / (p2.y - p1.y))).x;\nconst interpolateY = (x, p1, p2) => pointInLine(p1, p2, Math.abs((x - p1.x) / (p2.x - p1.x))).y;\nconst sqr = v => v * v;\nconst rangeLimit = (mouseX, mouseY, {x, y, x2, y2}, axis) => axis === 'y' ? {start: Math.min(y, y2), end: Math.max(y, y2), value: mouseY} : {start: Math.min(x, x2), end: Math.max(x, x2), value: mouseX};\n// http://www.independent-software.com/determining-coordinates-on-a-html-canvas-bezier-curve.html\nconst coordInCurve = (start, cp, end, t) => (1 - t) * (1 - t) * start + 2 * (1 - t) * t * cp + t * t * end;\nconst pointInCurve = (start, cp, end, t) => ({x: coordInCurve(start.x, cp.x, end.x, t), y: coordInCurve(start.y, cp.y, end.y, t)});\nconst coordAngleInCurve = (start, cp, end, t) => 2 * (1 - t) * (cp - start) + 2 * t * (end - cp);\nconst angleInCurve = (start, cp, end, t) => -Math.atan2(coordAngleInCurve(start.x, cp.x, end.x, t), coordAngleInCurve(start.y, cp.y, end.y, t)) + 0.5 * PI;\n\nclass LineAnnotation extends Element {\n\n  inRange(mouseX, mouseY, axis, useFinalPosition) {\n    const hBorderWidth = this.options.borderWidth / 2;\n    if (axis !== 'x' && axis !== 'y') {\n      const point = {mouseX, mouseY};\n      const {path, ctx} = this;\n      if (path) {\n        setBorderStyle(ctx, this.options);\n        const {chart} = this.$context;\n        const mx = mouseX * chart.currentDevicePixelRatio;\n        const my = mouseY * chart.currentDevicePixelRatio;\n        const result = ctx.isPointInStroke(path, mx, my) || isOnLabel(this, point, useFinalPosition);\n        ctx.restore();\n        return result;\n      }\n      const epsilon = sqr(hBorderWidth);\n      return intersects(this, point, epsilon, useFinalPosition) || isOnLabel(this, point, useFinalPosition);\n    }\n    return inAxisRange(this, {mouseX, mouseY}, axis, {hBorderWidth, useFinalPosition});\n  }\n\n  getCenterPoint(useFinalPosition) {\n    return getElementCenterPoint(this, useFinalPosition);\n  }\n\n  draw(ctx) {\n    const {x, y, x2, y2, cp, options} = this;\n\n    ctx.save();\n    if (!setBorderStyle(ctx, options)) {\n      // no border width, then line is not drawn\n      return ctx.restore();\n    }\n    setShadowStyle(ctx, options);\n\n    const length = Math.sqrt(Math.pow(x2 - x, 2) + Math.pow(y2 - y, 2));\n    if (options.curve && cp) {\n      drawCurve(ctx, this, cp, length);\n      return ctx.restore();\n    }\n    const {startOpts, endOpts, startAdjust, endAdjust} = getArrowHeads(this);\n    const angle = Math.atan2(y2 - y, x2 - x);\n    ctx.translate(x, y);\n    ctx.rotate(angle);\n    ctx.beginPath();\n    ctx.moveTo(0 + startAdjust, 0);\n    ctx.lineTo(length - endAdjust, 0);\n    ctx.shadowColor = options.borderShadowColor;\n    ctx.stroke();\n    drawArrowHead(ctx, 0, startAdjust, startOpts);\n    drawArrowHead(ctx, length, -endAdjust, endOpts);\n    ctx.restore();\n  }\n\n  get label() {\n    return this.elements && this.elements[0];\n  }\n\n  resolveElementProperties(chart, options) {\n    const area = resolveLineProperties(chart, options);\n    const {x, y, x2, y2} = area;\n    const inside = isLineInArea(area, chart.chartArea);\n    const properties = inside\n      ? limitLineToArea({x, y}, {x: x2, y: y2}, chart.chartArea)\n      : {x, y, x2, y2, width: Math.abs(x2 - x), height: Math.abs(y2 - y)};\n    properties.centerX = (x2 + x) / 2;\n    properties.centerY = (y2 + y) / 2;\n    properties.initProperties = initAnimationProperties(chart, properties, options);\n    if (options.curve) {\n      const p1 = {x: properties.x, y: properties.y};\n      const p2 = {x: properties.x2, y: properties.y2};\n      properties.cp = getControlPoint(properties, options, distanceBetweenPoints(p1, p2));\n    }\n    const labelProperties = resolveLabelElementProperties(chart, properties, options.label);\n    // additonal prop to manage zoom/pan\n    labelProperties._visible = inside;\n\n    properties.elements = [{\n      type: 'label',\n      optionScope: 'label',\n      properties: labelProperties,\n      initProperties: properties.initProperties\n    }];\n    return properties;\n  }\n}\n\nLineAnnotation.id = 'lineAnnotation';\n\nconst arrowHeadsDefaults = {\n  backgroundColor: undefined,\n  backgroundShadowColor: undefined,\n  borderColor: undefined,\n  borderDash: undefined,\n  borderDashOffset: undefined,\n  borderShadowColor: undefined,\n  borderWidth: undefined,\n  display: undefined,\n  fill: undefined,\n  length: undefined,\n  shadowBlur: undefined,\n  shadowOffsetX: undefined,\n  shadowOffsetY: undefined,\n  width: undefined\n};\n\nLineAnnotation.defaults = {\n  adjustScaleRange: true,\n  arrowHeads: {\n    display: false,\n    end: Object.assign({}, arrowHeadsDefaults),\n    fill: false,\n    length: 12,\n    start: Object.assign({}, arrowHeadsDefaults),\n    width: 6\n  },\n  borderDash: [],\n  borderDashOffset: 0,\n  borderShadowColor: 'transparent',\n  borderWidth: 2,\n  curve: false,\n  controlPoint: {\n    y: '-50%'\n  },\n  display: true,\n  endValue: undefined,\n  init: undefined,\n  label: {\n    backgroundColor: 'rgba(0,0,0,0.8)',\n    backgroundShadowColor: 'transparent',\n    borderCapStyle: 'butt',\n    borderColor: 'black',\n    borderDash: [],\n    borderDashOffset: 0,\n    borderJoinStyle: 'miter',\n    borderRadius: 6,\n    borderShadowColor: 'transparent',\n    borderWidth: 0,\n    callout: Object.assign({}, LabelAnnotation.defaults.callout),\n    color: '#fff',\n    content: null,\n    display: false,\n    drawTime: undefined,\n    font: {\n      family: undefined,\n      lineHeight: undefined,\n      size: undefined,\n      style: undefined,\n      weight: 'bold'\n    },\n    height: undefined,\n    opacity: undefined,\n    padding: 6,\n    position: 'center',\n    rotation: 0,\n    shadowBlur: 0,\n    shadowOffsetX: 0,\n    shadowOffsetY: 0,\n    textAlign: 'center',\n    textStrokeColor: undefined,\n    textStrokeWidth: 0,\n    width: undefined,\n    xAdjust: 0,\n    yAdjust: 0,\n    z: undefined\n  },\n  scaleID: undefined,\n  shadowBlur: 0,\n  shadowOffsetX: 0,\n  shadowOffsetY: 0,\n  value: undefined,\n  xMax: undefined,\n  xMin: undefined,\n  xScaleID: undefined,\n  yMax: undefined,\n  yMin: undefined,\n  yScaleID: undefined,\n  z: 0\n};\n\nLineAnnotation.descriptors = {\n  arrowHeads: {\n    start: {\n      _fallback: true\n    },\n    end: {\n      _fallback: true\n    },\n    _fallback: true\n  }\n};\n\nLineAnnotation.defaultRoutes = {\n  borderColor: 'color'\n};\n\nfunction inAxisRange(element, {mouseX, mouseY}, axis, {hBorderWidth, useFinalPosition}) {\n  const limit = rangeLimit(mouseX, mouseY, element.getProps(['x', 'y', 'x2', 'y2'], useFinalPosition), axis);\n  return (limit.value >= limit.start - hBorderWidth && limit.value <= limit.end + hBorderWidth) || isOnLabel(element, {mouseX, mouseY}, useFinalPosition, axis);\n}\n\nfunction isLineInArea({x, y, x2, y2}, {top, right, bottom, left}) {\n  return !(\n    (x < left && x2 < left) ||\n    (x > right && x2 > right) ||\n    (y < top && y2 < top) ||\n    (y > bottom && y2 > bottom)\n  );\n}\n\nfunction limitPointToArea({x, y}, p2, {top, right, bottom, left}) {\n  if (x < left) {\n    y = interpolateY(left, {x, y}, p2);\n    x = left;\n  }\n  if (x > right) {\n    y = interpolateY(right, {x, y}, p2);\n    x = right;\n  }\n  if (y < top) {\n    x = interpolateX(top, {x, y}, p2);\n    y = top;\n  }\n  if (y > bottom) {\n    x = interpolateX(bottom, {x, y}, p2);\n    y = bottom;\n  }\n  return {x, y};\n}\n\nfunction limitLineToArea(p1, p2, area) {\n  const {x, y} = limitPointToArea(p1, p2, area);\n  const {x: x2, y: y2} = limitPointToArea(p2, p1, area);\n  return {x, y, x2, y2, width: Math.abs(x2 - x), height: Math.abs(y2 - y)};\n}\n\nfunction intersects(element, {mouseX, mouseY}, epsilon = EPSILON, useFinalPosition) {\n  // Adapted from https://stackoverflow.com/a/6853926/25507\n  const {x: x1, y: y1, x2, y2} = element.getProps(['x', 'y', 'x2', 'y2'], useFinalPosition);\n  const dx = x2 - x1;\n  const dy = y2 - y1;\n  const lenSq = sqr(dx) + sqr(dy);\n  const t = lenSq === 0 ? -1 : ((mouseX - x1) * dx + (mouseY - y1) * dy) / lenSq;\n  let xx, yy;\n  if (t < 0) {\n    xx = x1;\n    yy = y1;\n  } else if (t > 1) {\n    xx = x2;\n    yy = y2;\n  } else {\n    xx = x1 + t * dx;\n    yy = y1 + t * dy;\n  }\n  return (sqr(mouseX - xx) + sqr(mouseY - yy)) <= epsilon;\n}\n\nfunction isOnLabel(element, {mouseX, mouseY}, useFinalPosition, axis) {\n  const label = element.label;\n  return label.options.display && label.inRange(mouseX, mouseY, axis, useFinalPosition);\n}\n\nfunction resolveLabelElementProperties(chart, properties, options) {\n  const borderWidth = options.borderWidth;\n  const padding = toPadding(options.padding);\n  const textSize = measureLabelSize(chart.ctx, options);\n  const width = textSize.width + padding.width + borderWidth;\n  const height = textSize.height + padding.height + borderWidth;\n  return calculateLabelPosition(properties, options, {width, height, padding}, chart.chartArea);\n}\n\nfunction calculateAutoRotation(properties) {\n  const {x, y, x2, y2} = properties;\n  const rotation = Math.atan2(y2 - y, x2 - x);\n  // Flip the rotation if it goes > PI/2 or < -PI/2, so label stays upright\n  return rotation > PI / 2 ? rotation - PI : rotation < PI / -2 ? rotation + PI : rotation;\n}\n\nfunction calculateLabelPosition(properties, label, sizes, chartArea) {\n  const {width, height, padding} = sizes;\n  const {xAdjust, yAdjust} = label;\n  const p1 = {x: properties.x, y: properties.y};\n  const p2 = {x: properties.x2, y: properties.y2};\n  const rotation = label.rotation === 'auto' ? calculateAutoRotation(properties) : toRadians(label.rotation);\n  const size = rotatedSize(width, height, rotation);\n  const t = calculateT(properties, label, {labelSize: size, padding}, chartArea);\n  const pt = properties.cp ? pointInCurve(p1, properties.cp, p2, t) : pointInLine(p1, p2, t);\n  const xCoordinateSizes = {size: size.w, min: chartArea.left, max: chartArea.right, padding: padding.left};\n  const yCoordinateSizes = {size: size.h, min: chartArea.top, max: chartArea.bottom, padding: padding.top};\n  const centerX = adjustLabelCoordinate(pt.x, xCoordinateSizes) + xAdjust;\n  const centerY = adjustLabelCoordinate(pt.y, yCoordinateSizes) + yAdjust;\n  return {\n    x: centerX - (width / 2),\n    y: centerY - (height / 2),\n    x2: centerX + (width / 2),\n    y2: centerY + (height / 2),\n    centerX,\n    centerY,\n    pointX: pt.x,\n    pointY: pt.y,\n    width,\n    height,\n    rotation: toDegrees(rotation)\n  };\n}\n\nfunction rotatedSize(width, height, rotation) {\n  const cos = Math.cos(rotation);\n  const sin = Math.sin(rotation);\n  return {\n    w: Math.abs(width * cos) + Math.abs(height * sin),\n    h: Math.abs(width * sin) + Math.abs(height * cos)\n  };\n}\n\nfunction calculateT(properties, label, sizes, chartArea) {\n  let t;\n  const space = spaceAround(properties, chartArea);\n  if (label.position === 'start') {\n    t = calculateTAdjust({w: properties.x2 - properties.x, h: properties.y2 - properties.y}, sizes, label, space);\n  } else if (label.position === 'end') {\n    t = 1 - calculateTAdjust({w: properties.x - properties.x2, h: properties.y - properties.y2}, sizes, label, space);\n  } else {\n    t = getRelativePosition(1, label.position);\n  }\n  return t;\n}\n\nfunction calculateTAdjust(lineSize, sizes, label, space) {\n  const {labelSize, padding} = sizes;\n  const lineW = lineSize.w * space.dx;\n  const lineH = lineSize.h * space.dy;\n  const x = (lineW > 0) && ((labelSize.w / 2 + padding.left - space.x) / lineW);\n  const y = (lineH > 0) && ((labelSize.h / 2 + padding.top - space.y) / lineH);\n  return clamp(Math.max(x, y), 0, 0.25);\n}\n\nfunction spaceAround(properties, chartArea) {\n  const {x, x2, y, y2} = properties;\n  const t = Math.min(y, y2) - chartArea.top;\n  const l = Math.min(x, x2) - chartArea.left;\n  const b = chartArea.bottom - Math.max(y, y2);\n  const r = chartArea.right - Math.max(x, x2);\n  return {\n    x: Math.min(l, r),\n    y: Math.min(t, b),\n    dx: l <= r ? 1 : -1,\n    dy: t <= b ? 1 : -1\n  };\n}\n\nfunction adjustLabelCoordinate(coordinate, labelSizes) {\n  const {size, min, max, padding} = labelSizes;\n  const halfSize = size / 2;\n  if (size > max - min) {\n    // if it does not fit, display as much as possible\n    return (max + min) / 2;\n  }\n  if (min >= (coordinate - padding - halfSize)) {\n    coordinate = min + padding + halfSize;\n  }\n  if (max <= (coordinate + padding + halfSize)) {\n    coordinate = max - padding - halfSize;\n  }\n  return coordinate;\n}\n\nfunction getArrowHeads(line) {\n  const options = line.options;\n  const arrowStartOpts = options.arrowHeads && options.arrowHeads.start;\n  const arrowEndOpts = options.arrowHeads && options.arrowHeads.end;\n  return {\n    startOpts: arrowStartOpts,\n    endOpts: arrowEndOpts,\n    startAdjust: getLineAdjust(line, arrowStartOpts),\n    endAdjust: getLineAdjust(line, arrowEndOpts)\n  };\n}\n\nfunction getLineAdjust(line, arrowOpts) {\n  if (!arrowOpts || !arrowOpts.display) {\n    return 0;\n  }\n  const {length, width} = arrowOpts;\n  const adjust = line.options.borderWidth / 2;\n  const p1 = {x: length, y: width + adjust};\n  const p2 = {x: 0, y: adjust};\n  return Math.abs(interpolateX(0, p1, p2));\n}\n\nfunction drawArrowHead(ctx, offset, adjust, arrowOpts) {\n  if (!arrowOpts || !arrowOpts.display) {\n    return;\n  }\n  const {length, width, fill, backgroundColor, borderColor} = arrowOpts;\n  const arrowOffsetX = Math.abs(offset - length) + adjust;\n  ctx.beginPath();\n  setShadowStyle(ctx, arrowOpts);\n  setBorderStyle(ctx, arrowOpts);\n  ctx.moveTo(arrowOffsetX, -width);\n  ctx.lineTo(offset + adjust, 0);\n  ctx.lineTo(arrowOffsetX, width);\n  if (fill === true) {\n    ctx.fillStyle = backgroundColor || borderColor;\n    ctx.closePath();\n    ctx.fill();\n    ctx.shadowColor = 'transparent';\n  } else {\n    ctx.shadowColor = arrowOpts.borderShadowColor;\n  }\n  ctx.stroke();\n}\n\nfunction getControlPoint(properties, options, distance) {\n  const {x, y, x2, y2, centerX, centerY} = properties;\n  const angle = Math.atan2(y2 - y, x2 - x);\n  const cp = toPosition(options.controlPoint, 0);\n  const point = {\n    x: centerX + getSize(distance, cp.x, false),\n    y: centerY + getSize(distance, cp.y, false)\n  };\n  return rotated(point, {x: centerX, y: centerY}, angle);\n}\n\nfunction drawArrowHeadOnCurve(ctx, {x, y}, {angle, adjust}, arrowOpts) {\n  if (!arrowOpts || !arrowOpts.display) {\n    return;\n  }\n  ctx.save();\n  ctx.translate(x, y);\n  ctx.rotate(angle);\n  drawArrowHead(ctx, 0, -adjust, arrowOpts);\n  ctx.restore();\n}\n\nfunction drawCurve(ctx, element, cp, length) {\n  const {x, y, x2, y2, options} = element;\n  const {startOpts, endOpts, startAdjust, endAdjust} = getArrowHeads(element);\n  const p1 = {x, y};\n  const p2 = {x: x2, y: y2};\n  const startAngle = angleInCurve(p1, cp, p2, 0);\n  const endAngle = angleInCurve(p1, cp, p2, 1) - PI;\n  const ps = pointInCurve(p1, cp, p2, startAdjust / length);\n  const pe = pointInCurve(p1, cp, p2, 1 - endAdjust / length);\n\n  const path = new Path2D();\n  ctx.beginPath();\n  path.moveTo(ps.x, ps.y);\n  path.quadraticCurveTo(cp.x, cp.y, pe.x, pe.y);\n  ctx.shadowColor = options.borderShadowColor;\n  ctx.stroke(path);\n  element.path = path;\n  element.ctx = ctx;\n  drawArrowHeadOnCurve(ctx, ps, {angle: startAngle, adjust: startAdjust}, startOpts);\n  drawArrowHeadOnCurve(ctx, pe, {angle: endAngle, adjust: endAdjust}, endOpts);\n}\n\nclass EllipseAnnotation extends Element {\n\n  inRange(mouseX, mouseY, axis, useFinalPosition) {\n    const rotation = this.options.rotation;\n    const borderWidth = this.options.borderWidth;\n    if (axis !== 'x' && axis !== 'y') {\n      return pointInEllipse({x: mouseX, y: mouseY}, this.getProps(['width', 'height', 'centerX', 'centerY'], useFinalPosition), rotation, borderWidth);\n    }\n    const {x, y, x2, y2} = this.getProps(['x', 'y', 'x2', 'y2'], useFinalPosition);\n    const hBorderWidth = borderWidth / 2;\n    const limit = axis === 'y' ? {start: y, end: y2} : {start: x, end: x2};\n    const rotatedPoint = rotated({x: mouseX, y: mouseY}, this.getCenterPoint(useFinalPosition), toRadians(-rotation));\n    return rotatedPoint[axis] >= limit.start - hBorderWidth - EPSILON && rotatedPoint[axis] <= limit.end + hBorderWidth + EPSILON;\n  }\n\n  getCenterPoint(useFinalPosition) {\n    return getElementCenterPoint(this, useFinalPosition);\n  }\n\n  draw(ctx) {\n    const {width, height, centerX, centerY, options} = this;\n    ctx.save();\n    translate(ctx, this.getCenterPoint(), options.rotation);\n    setShadowStyle(ctx, this.options);\n    ctx.beginPath();\n    ctx.fillStyle = options.backgroundColor;\n    const stroke = setBorderStyle(ctx, options);\n    ctx.ellipse(centerX, centerY, height / 2, width / 2, PI / 2, 0, 2 * PI);\n    ctx.fill();\n    if (stroke) {\n      ctx.shadowColor = options.borderShadowColor;\n      ctx.stroke();\n    }\n    ctx.restore();\n  }\n\n  get label() {\n    return this.elements && this.elements[0];\n  }\n\n  resolveElementProperties(chart, options) {\n    return resolveBoxAndLabelProperties(chart, options);\n  }\n\n}\n\nEllipseAnnotation.id = 'ellipseAnnotation';\n\nEllipseAnnotation.defaults = {\n  adjustScaleRange: true,\n  backgroundShadowColor: 'transparent',\n  borderDash: [],\n  borderDashOffset: 0,\n  borderShadowColor: 'transparent',\n  borderWidth: 1,\n  display: true,\n  init: undefined,\n  label: Object.assign({}, BoxAnnotation.defaults.label),\n  rotation: 0,\n  shadowBlur: 0,\n  shadowOffsetX: 0,\n  shadowOffsetY: 0,\n  xMax: undefined,\n  xMin: undefined,\n  xScaleID: undefined,\n  yMax: undefined,\n  yMin: undefined,\n  yScaleID: undefined,\n  z: 0\n};\n\nEllipseAnnotation.defaultRoutes = {\n  borderColor: 'color',\n  backgroundColor: 'color'\n};\n\nEllipseAnnotation.descriptors = {\n  label: {\n    _fallback: true\n  }\n};\n\nfunction pointInEllipse(p, ellipse, rotation, borderWidth) {\n  const {width, height, centerX, centerY} = ellipse;\n  const xRadius = width / 2;\n  const yRadius = height / 2;\n\n  if (xRadius <= 0 || yRadius <= 0) {\n    return false;\n  }\n  // https://stackoverflow.com/questions/7946187/point-and-ellipse-rotated-position-test-algorithm\n  const angle = toRadians(rotation || 0);\n  const hBorderWidth = borderWidth / 2 || 0;\n  const cosAngle = Math.cos(angle);\n  const sinAngle = Math.sin(angle);\n  const a = Math.pow(cosAngle * (p.x - centerX) + sinAngle * (p.y - centerY), 2);\n  const b = Math.pow(sinAngle * (p.x - centerX) - cosAngle * (p.y - centerY), 2);\n  return (a / Math.pow(xRadius + hBorderWidth, 2)) + (b / Math.pow(yRadius + hBorderWidth, 2)) <= 1.0001;\n}\n\nclass PointAnnotation extends Element {\n\n  inRange(mouseX, mouseY, axis, useFinalPosition) {\n    const {x, y, x2, y2, width} = this.getProps(['x', 'y', 'x2', 'y2', 'width'], useFinalPosition);\n    const borderWidth = this.options.borderWidth;\n    if (axis !== 'x' && axis !== 'y') {\n      return inPointRange({x: mouseX, y: mouseY}, this.getCenterPoint(useFinalPosition), width / 2, borderWidth);\n    }\n    const hBorderWidth = borderWidth / 2;\n    const limit = axis === 'y' ? {start: y, end: y2, value: mouseY} : {start: x, end: x2, value: mouseX};\n    return limit.value >= limit.start - hBorderWidth && limit.value <= limit.end + hBorderWidth;\n  }\n\n  getCenterPoint(useFinalPosition) {\n    return getElementCenterPoint(this, useFinalPosition);\n  }\n\n  draw(ctx) {\n    const options = this.options;\n    const borderWidth = options.borderWidth;\n    if (options.radius < 0.1) {\n      return;\n    }\n    ctx.save();\n    ctx.fillStyle = options.backgroundColor;\n    setShadowStyle(ctx, options);\n    const stroke = setBorderStyle(ctx, options);\n    drawPoint(ctx, this, this.centerX, this.centerY);\n    if (stroke && !isImageOrCanvas(options.pointStyle)) {\n      ctx.shadowColor = options.borderShadowColor;\n      ctx.stroke();\n    }\n    ctx.restore();\n    options.borderWidth = borderWidth;\n  }\n\n  resolveElementProperties(chart, options) {\n    const properties = resolvePointProperties(chart, options);\n    properties.initProperties = initAnimationProperties(chart, properties, options);\n    return properties;\n  }\n}\n\nPointAnnotation.id = 'pointAnnotation';\n\nPointAnnotation.defaults = {\n  adjustScaleRange: true,\n  backgroundShadowColor: 'transparent',\n  borderDash: [],\n  borderDashOffset: 0,\n  borderShadowColor: 'transparent',\n  borderWidth: 1,\n  display: true,\n  init: undefined,\n  pointStyle: 'circle',\n  radius: 10,\n  rotation: 0,\n  shadowBlur: 0,\n  shadowOffsetX: 0,\n  shadowOffsetY: 0,\n  xAdjust: 0,\n  xMax: undefined,\n  xMin: undefined,\n  xScaleID: undefined,\n  xValue: undefined,\n  yAdjust: 0,\n  yMax: undefined,\n  yMin: undefined,\n  yScaleID: undefined,\n  yValue: undefined,\n  z: 0\n};\n\nPointAnnotation.defaultRoutes = {\n  borderColor: 'color',\n  backgroundColor: 'color'\n};\n\nclass PolygonAnnotation extends Element {\n\n  inRange(mouseX, mouseY, axis, useFinalPosition) {\n    if (axis !== 'x' && axis !== 'y') {\n      return this.options.radius >= 0.1 && this.elements.length > 1 && pointIsInPolygon(this.elements, mouseX, mouseY, useFinalPosition);\n    }\n    const rotatedPoint = rotated({x: mouseX, y: mouseY}, this.getCenterPoint(useFinalPosition), toRadians(-this.options.rotation));\n    const axisPoints = this.elements.map((point) => axis === 'y' ? point.bY : point.bX);\n    const start = Math.min(...axisPoints);\n    const end = Math.max(...axisPoints);\n    return rotatedPoint[axis] >= start && rotatedPoint[axis] <= end;\n  }\n\n  getCenterPoint(useFinalPosition) {\n    return getElementCenterPoint(this, useFinalPosition);\n  }\n\n  draw(ctx) {\n    const {elements, options} = this;\n    ctx.save();\n    ctx.beginPath();\n    ctx.fillStyle = options.backgroundColor;\n    setShadowStyle(ctx, options);\n    const stroke = setBorderStyle(ctx, options);\n    let first = true;\n    for (const el of elements) {\n      if (first) {\n        ctx.moveTo(el.x, el.y);\n        first = false;\n      } else {\n        ctx.lineTo(el.x, el.y);\n      }\n    }\n    ctx.closePath();\n    ctx.fill();\n    // If no border, don't draw it\n    if (stroke) {\n      ctx.shadowColor = options.borderShadowColor;\n      ctx.stroke();\n    }\n    ctx.restore();\n  }\n\n  resolveElementProperties(chart, options) {\n    const properties = resolvePointProperties(chart, options);\n    const {sides, rotation} = options;\n    const elements = [];\n    const angle = (2 * PI) / sides;\n    let rad = rotation * RAD_PER_DEG;\n    for (let i = 0; i < sides; i++, rad += angle) {\n      const elProps = buildPointElement(properties, options, rad);\n      elProps.initProperties = initAnimationProperties(chart, properties, options);\n      elements.push(elProps);\n    }\n    properties.elements = elements;\n    return properties;\n  }\n}\n\nPolygonAnnotation.id = 'polygonAnnotation';\n\nPolygonAnnotation.defaults = {\n  adjustScaleRange: true,\n  backgroundShadowColor: 'transparent',\n  borderCapStyle: 'butt',\n  borderDash: [],\n  borderDashOffset: 0,\n  borderJoinStyle: 'miter',\n  borderShadowColor: 'transparent',\n  borderWidth: 1,\n  display: true,\n  init: undefined,\n  point: {\n    radius: 0\n  },\n  radius: 10,\n  rotation: 0,\n  shadowBlur: 0,\n  shadowOffsetX: 0,\n  shadowOffsetY: 0,\n  sides: 3,\n  xAdjust: 0,\n  xMax: undefined,\n  xMin: undefined,\n  xScaleID: undefined,\n  xValue: undefined,\n  yAdjust: 0,\n  yMax: undefined,\n  yMin: undefined,\n  yScaleID: undefined,\n  yValue: undefined,\n  z: 0\n};\n\nPolygonAnnotation.defaultRoutes = {\n  borderColor: 'color',\n  backgroundColor: 'color'\n};\n\nfunction buildPointElement({centerX, centerY}, {radius, borderWidth}, rad) {\n  const halfBorder = borderWidth / 2;\n  const sin = Math.sin(rad);\n  const cos = Math.cos(rad);\n  const point = {x: centerX + sin * radius, y: centerY - cos * radius};\n  return {\n    type: 'point',\n    optionScope: 'point',\n    properties: {\n      x: point.x,\n      y: point.y,\n      centerX: point.x,\n      centerY: point.y,\n      bX: centerX + sin * (radius + halfBorder),\n      bY: centerY - cos * (radius + halfBorder)\n    }\n  };\n}\n\nfunction pointIsInPolygon(points, x, y, useFinalPosition) {\n  let isInside = false;\n  let A = points[points.length - 1].getProps(['bX', 'bY'], useFinalPosition);\n  for (const point of points) {\n    const B = point.getProps(['bX', 'bY'], useFinalPosition);\n    if ((B.bY > y) !== (A.bY > y) && x < (A.bX - B.bX) * (y - B.bY) / (A.bY - B.bY) + B.bX) {\n      isInside = !isInside;\n    }\n    A = B;\n  }\n  return isInside;\n}\n\nconst annotationTypes = {\n  box: BoxAnnotation,\n  ellipse: EllipseAnnotation,\n  label: LabelAnnotation,\n  line: LineAnnotation,\n  point: PointAnnotation,\n  polygon: PolygonAnnotation\n};\n\n/**\n * Register fallback for annotation elements\n * For example lineAnnotation options would be looked through:\n * - the annotation object (options.plugins.annotation.annotations[id])\n * - element options (options.elements.lineAnnotation)\n * - element defaults (defaults.elements.lineAnnotation)\n * - annotation plugin defaults (defaults.plugins.annotation, this is what we are registering here)\n */\nObject.keys(annotationTypes).forEach(key => {\n  defaults.describe(`elements.${annotationTypes[key].id}`, {\n    _fallback: 'plugins.annotation.common'\n  });\n});\n\nconst directUpdater = {\n  update: Object.assign\n};\n\nconst hooks$1 = eventHooks.concat(elementHooks);\nconst resolve = (value, optDefs) => isObject(optDefs) ? resolveObj(value, optDefs) : value;\n\n\n/**\n * @typedef { import(\"chart.js\").Chart } Chart\n * @typedef { import(\"chart.js\").UpdateMode } UpdateMode\n * @typedef { import('../../types/options').AnnotationPluginOptions } AnnotationPluginOptions\n */\n\n/**\n * @param {string} prop\n * @returns {boolean}\n */\nconst isIndexable = (prop) => prop === 'color' || prop === 'font';\n\n/**\n * Resolve the annotation type, checking if is supported.\n * @param {string} [type=line] - annotation type\n * @returns {string} resolved annotation type\n */\nfunction resolveType(type = 'line') {\n  if (annotationTypes[type]) {\n    return type;\n  }\n  console.warn(`Unknown annotation type: '${type}', defaulting to 'line'`);\n  return 'line';\n}\n\n/**\n * @param {Chart} chart\n * @param {Object} state\n * @param {AnnotationPluginOptions} options\n * @param {UpdateMode} mode\n */\nfunction updateElements(chart, state, options, mode) {\n  const animations = resolveAnimations(chart, options.animations, mode);\n\n  const annotations = state.annotations;\n  const elements = resyncElements(state.elements, annotations);\n\n  for (let i = 0; i < annotations.length; i++) {\n    const annotationOptions = annotations[i];\n    const element = getOrCreateElement(elements, i, annotationOptions.type);\n    const resolver = annotationOptions.setContext(getContext(chart, element, annotationOptions));\n    const properties = element.resolveElementProperties(chart, resolver);\n\n    properties.skip = toSkip(properties);\n\n    if ('elements' in properties) {\n      updateSubElements(element, properties.elements, resolver, animations);\n      // Remove the sub-element definitions from properties, so the actual elements\n      // are not overwritten by their definitions\n      delete properties.elements;\n    }\n\n    if (!defined(element.x)) {\n      // If the element is newly created, assing the properties directly - to\n      // make them readily awailable to any scriptable options. If we do not do this,\n      // the properties retruned by `resolveElementProperties` are available only\n      // after options resolution.\n      Object.assign(element, properties);\n    }\n\n    Object.assign(element, properties.initProperties);\n    properties.options = resolveAnnotationOptions(resolver);\n\n    animations.update(element, properties);\n  }\n}\n\nfunction toSkip(properties) {\n  return isNaN(properties.x) || isNaN(properties.y);\n}\n\nfunction resolveAnimations(chart, animOpts, mode) {\n  if (mode === 'reset' || mode === 'none' || mode === 'resize') {\n    return directUpdater;\n  }\n  return new Animations(chart, animOpts);\n}\n\nfunction updateSubElements(mainElement, elements, resolver, animations) {\n  const subElements = mainElement.elements || (mainElement.elements = []);\n  subElements.length = elements.length;\n  for (let i = 0; i < elements.length; i++) {\n    const definition = elements[i];\n    const properties = definition.properties;\n    const subElement = getOrCreateElement(subElements, i, definition.type, definition.initProperties);\n    const subResolver = resolver[definition.optionScope].override(definition);\n    properties.options = resolveAnnotationOptions(subResolver);\n    animations.update(subElement, properties);\n  }\n}\n\nfunction getOrCreateElement(elements, index, type, initProperties) {\n  const elementClass = annotationTypes[resolveType(type)];\n  let element = elements[index];\n  if (!element || !(element instanceof elementClass)) {\n    element = elements[index] = new elementClass();\n    Object.assign(element, initProperties);\n  }\n  return element;\n}\n\nfunction resolveAnnotationOptions(resolver) {\n  const elementClass = annotationTypes[resolveType(resolver.type)];\n  const result = {};\n  result.id = resolver.id;\n  result.type = resolver.type;\n  result.drawTime = resolver.drawTime;\n  Object.assign(result,\n    resolveObj(resolver, elementClass.defaults),\n    resolveObj(resolver, elementClass.defaultRoutes));\n  for (const hook of hooks$1) {\n    result[hook] = resolver[hook];\n  }\n  return result;\n}\n\nfunction resolveObj(resolver, defs) {\n  const result = {};\n  for (const prop of Object.keys(defs)) {\n    const optDefs = defs[prop];\n    const value = resolver[prop];\n    if (isIndexable(prop) && isArray(value)) {\n      result[prop] = value.map((item) => resolve(item, optDefs));\n    } else {\n      result[prop] = resolve(value, optDefs);\n    }\n  }\n  return result;\n}\n\nfunction getContext(chart, element, annotation) {\n  return element.$context || (element.$context = Object.assign(Object.create(chart.getContext()), {\n    element,\n    id: annotation.id,\n    type: 'annotation'\n  }));\n}\n\nfunction resyncElements(elements, annotations) {\n  const count = annotations.length;\n  const start = elements.length;\n\n  if (start < count) {\n    const add = count - start;\n    elements.splice(start, 0, ...new Array(add));\n  } else if (start > count) {\n    elements.splice(count, start - count);\n  }\n  return elements;\n}\n\nvar version = \"3.0.1\";\n\nconst chartStates = new Map();\nconst hooks = eventHooks.concat(elementHooks);\n\nvar annotation = {\n  id: 'annotation',\n\n  version,\n\n  beforeRegister() {\n    requireVersion('chart.js', '4.0', Chart.version);\n  },\n\n  afterRegister() {\n    Chart.register(annotationTypes);\n  },\n\n  afterUnregister() {\n    Chart.unregister(annotationTypes);\n  },\n\n  beforeInit(chart) {\n    chartStates.set(chart, {\n      annotations: [],\n      elements: [],\n      visibleElements: [],\n      listeners: {},\n      listened: false,\n      moveListened: false,\n      hooks: {},\n      hooked: false,\n      hovered: []\n    });\n  },\n\n  beforeUpdate(chart, args, options) {\n    const state = chartStates.get(chart);\n    const annotations = state.annotations = [];\n\n    let annotationOptions = options.annotations;\n    if (isObject(annotationOptions)) {\n      Object.keys(annotationOptions).forEach(key => {\n        const value = annotationOptions[key];\n        if (isObject(value)) {\n          value.id = key;\n          annotations.push(value);\n        }\n      });\n    } else if (isArray(annotationOptions)) {\n      annotations.push(...annotationOptions);\n    }\n    verifyScaleOptions(annotations, chart.scales);\n  },\n\n  afterDataLimits(chart, args) {\n    const state = chartStates.get(chart);\n    adjustScaleRange(chart, args.scale, state.annotations.filter(a => a.display && a.adjustScaleRange));\n  },\n\n  afterUpdate(chart, args, options) {\n    const state = chartStates.get(chart);\n    updateListeners(chart, state, options);\n    updateElements(chart, state, options, args.mode);\n    state.visibleElements = state.elements.filter(el => !el.skip && el.options.display);\n    updateHooks(chart, state, options);\n  },\n\n  beforeDatasetsDraw(chart, _args, options) {\n    draw(chart, 'beforeDatasetsDraw', options.clip);\n  },\n\n  afterDatasetsDraw(chart, _args, options) {\n    draw(chart, 'afterDatasetsDraw', options.clip);\n  },\n\n  beforeDraw(chart, _args, options) {\n    draw(chart, 'beforeDraw', options.clip);\n  },\n\n  afterDraw(chart, _args, options) {\n    draw(chart, 'afterDraw', options.clip);\n  },\n\n  beforeEvent(chart, args, options) {\n    const state = chartStates.get(chart);\n    if (handleEvent(state, args.event, options)) {\n      args.changed = true;\n    }\n  },\n\n  afterDestroy(chart) {\n    chartStates.delete(chart);\n  },\n\n  _getState(chart) {\n    return chartStates.get(chart);\n  },\n\n  defaults: {\n    animations: {\n      numbers: {\n        properties: ['x', 'y', 'x2', 'y2', 'width', 'height', 'centerX', 'centerY', 'pointX', 'pointY', 'radius'],\n        type: 'number'\n      },\n    },\n    clip: true,\n    interaction: {\n      mode: undefined,\n      axis: undefined,\n      intersect: undefined\n    },\n    common: {\n      drawTime: 'afterDatasetsDraw',\n      init: false,\n      label: {\n      }\n    }\n  },\n\n  descriptors: {\n    _indexable: false,\n    _scriptable: (prop) => !hooks.includes(prop) && prop !== 'init',\n    annotations: {\n      _allKeys: false,\n      _fallback: (prop, opts) => `elements.${annotationTypes[resolveType(opts.type)].id}`\n    },\n    interaction: {\n      _fallback: true\n    },\n    common: {\n      label: {\n        _indexable: isIndexable,\n        _fallback: true\n      },\n      _indexable: isIndexable\n    }\n  },\n\n  additionalOptionScopes: ['']\n};\n\nfunction draw(chart, caller, clip) {\n  const {ctx, chartArea} = chart;\n  const state = chartStates.get(chart);\n\n  if (clip) {\n    clipArea(ctx, chartArea);\n  }\n\n  const drawableElements = getDrawableElements(state.visibleElements, caller).sort((a, b) => a.element.options.z - b.element.options.z);\n  for (const item of drawableElements) {\n    drawElement(ctx, chartArea, state, item);\n  }\n\n  if (clip) {\n    unclipArea(ctx);\n  }\n}\n\nfunction getDrawableElements(elements, caller) {\n  const drawableElements = [];\n  for (const el of elements) {\n    if (el.options.drawTime === caller) {\n      drawableElements.push({element: el, main: true});\n    }\n    if (el.elements && el.elements.length) {\n      for (const sub of el.elements) {\n        if (sub.options.display && sub.options.drawTime === caller) {\n          drawableElements.push({element: sub});\n        }\n      }\n    }\n  }\n  return drawableElements;\n}\n\nfunction drawElement(ctx, chartArea, state, item) {\n  const el = item.element;\n  if (item.main) {\n    invokeHook(state, el, 'beforeDraw');\n    el.draw(ctx, chartArea);\n    invokeHook(state, el, 'afterDraw');\n  } else {\n    el.draw(ctx, chartArea);\n  }\n}\n\nexport { annotation as default };\n","!function(t,e){\"object\"==typeof exports&&\"undefined\"!=typeof module?module.exports=e():\"function\"==typeof define&&define.amd?define(e):(t=\"undefined\"!=typeof globalThis?globalThis:t||self).dayjs=e()}(this,(function(){\"use strict\";var t=1e3,e=6e4,n=36e5,r=\"millisecond\",i=\"second\",s=\"minute\",u=\"hour\",a=\"day\",o=\"week\",c=\"month\",f=\"quarter\",h=\"year\",d=\"date\",l=\"Invalid Date\",$=/^(\\d{4})[-/]?(\\d{1,2})?[-/]?(\\d{0,2})[Tt\\s]*(\\d{1,2})?:?(\\d{1,2})?:?(\\d{1,2})?[.:]?(\\d+)?$/,y=/\\[([^\\]]+)]|Y{1,4}|M{1,4}|D{1,2}|d{1,4}|H{1,2}|h{1,2}|a|A|m{1,2}|s{1,2}|Z{1,2}|SSS/g,M={name:\"en\",weekdays:\"Sunday_Monday_Tuesday_Wednesday_Thursday_Friday_Saturday\".split(\"_\"),months:\"January_February_March_April_May_June_July_August_September_October_November_December\".split(\"_\"),ordinal:function(t){var e=[\"th\",\"st\",\"nd\",\"rd\"],n=t%100;return\"[\"+t+(e[(n-20)%10]||e[n]||e[0])+\"]\"}},m=function(t,e,n){var r=String(t);return!r||r.length>=e?t:\"\"+Array(e+1-r.length).join(n)+t},v={s:m,z:function(t){var e=-t.utcOffset(),n=Math.abs(e),r=Math.floor(n/60),i=n%60;return(e<=0?\"+\":\"-\")+m(r,2,\"0\")+\":\"+m(i,2,\"0\")},m:function t(e,n){if(e.date()<n.date())return-t(n,e);var r=12*(n.year()-e.year())+(n.month()-e.month()),i=e.clone().add(r,c),s=n-i<0,u=e.clone().add(r+(s?-1:1),c);return+(-(r+(n-i)/(s?i-u:u-i))||0)},a:function(t){return t<0?Math.ceil(t)||0:Math.floor(t)},p:function(t){return{M:c,y:h,w:o,d:a,D:d,h:u,m:s,s:i,ms:r,Q:f}[t]||String(t||\"\").toLowerCase().replace(/s$/,\"\")},u:function(t){return void 0===t}},g=\"en\",D={};D[g]=M;var p=\"$isDayjsObject\",S=function(t){return t instanceof _||!(!t||!t[p])},w=function t(e,n,r){var i;if(!e)return g;if(\"string\"==typeof e){var s=e.toLowerCase();D[s]&&(i=s),n&&(D[s]=n,i=s);var u=e.split(\"-\");if(!i&&u.length>1)return t(u[0])}else{var a=e.name;D[a]=e,i=a}return!r&&i&&(g=i),i||!r&&g},O=function(t,e){if(S(t))return t.clone();var n=\"object\"==typeof e?e:{};return n.date=t,n.args=arguments,new _(n)},b=v;b.l=w,b.i=S,b.w=function(t,e){return O(t,{locale:e.$L,utc:e.$u,x:e.$x,$offset:e.$offset})};var _=function(){function M(t){this.$L=w(t.locale,null,!0),this.parse(t),this.$x=this.$x||t.x||{},this[p]=!0}var m=M.prototype;return m.parse=function(t){this.$d=function(t){var e=t.date,n=t.utc;if(null===e)return new Date(NaN);if(b.u(e))return new Date;if(e instanceof Date)return new Date(e);if(\"string\"==typeof e&&!/Z$/i.test(e)){var r=e.match($);if(r){var i=r[2]-1||0,s=(r[7]||\"0\").substring(0,3);return n?new Date(Date.UTC(r[1],i,r[3]||1,r[4]||0,r[5]||0,r[6]||0,s)):new Date(r[1],i,r[3]||1,r[4]||0,r[5]||0,r[6]||0,s)}}return new Date(e)}(t),this.init()},m.init=function(){var t=this.$d;this.$y=t.getFullYear(),this.$M=t.getMonth(),this.$D=t.getDate(),this.$W=t.getDay(),this.$H=t.getHours(),this.$m=t.getMinutes(),this.$s=t.getSeconds(),this.$ms=t.getMilliseconds()},m.$utils=function(){return b},m.isValid=function(){return!(this.$d.toString()===l)},m.isSame=function(t,e){var n=O(t);return this.startOf(e)<=n&&n<=this.endOf(e)},m.isAfter=function(t,e){return O(t)<this.startOf(e)},m.isBefore=function(t,e){return this.endOf(e)<O(t)},m.$g=function(t,e,n){return b.u(t)?this[e]:this.set(n,t)},m.unix=function(){return Math.floor(this.valueOf()/1e3)},m.valueOf=function(){return this.$d.getTime()},m.startOf=function(t,e){var n=this,r=!!b.u(e)||e,f=b.p(t),l=function(t,e){var i=b.w(n.$u?Date.UTC(n.$y,e,t):new Date(n.$y,e,t),n);return r?i:i.endOf(a)},$=function(t,e){return b.w(n.toDate()[t].apply(n.toDate(\"s\"),(r?[0,0,0,0]:[23,59,59,999]).slice(e)),n)},y=this.$W,M=this.$M,m=this.$D,v=\"set\"+(this.$u?\"UTC\":\"\");switch(f){case h:return r?l(1,0):l(31,11);case c:return r?l(1,M):l(0,M+1);case o:var g=this.$locale().weekStart||0,D=(y<g?y+7:y)-g;return l(r?m-D:m+(6-D),M);case a:case d:return $(v+\"Hours\",0);case u:return $(v+\"Minutes\",1);case s:return $(v+\"Seconds\",2);case i:return $(v+\"Milliseconds\",3);default:return this.clone()}},m.endOf=function(t){return this.startOf(t,!1)},m.$set=function(t,e){var n,o=b.p(t),f=\"set\"+(this.$u?\"UTC\":\"\"),l=(n={},n[a]=f+\"Date\",n[d]=f+\"Date\",n[c]=f+\"Month\",n[h]=f+\"FullYear\",n[u]=f+\"Hours\",n[s]=f+\"Minutes\",n[i]=f+\"Seconds\",n[r]=f+\"Milliseconds\",n)[o],$=o===a?this.$D+(e-this.$W):e;if(o===c||o===h){var y=this.clone().set(d,1);y.$d[l]($),y.init(),this.$d=y.set(d,Math.min(this.$D,y.daysInMonth())).$d}else l&&this.$d[l]($);return this.init(),this},m.set=function(t,e){return this.clone().$set(t,e)},m.get=function(t){return this[b.p(t)]()},m.add=function(r,f){var d,l=this;r=Number(r);var $=b.p(f),y=function(t){var e=O(l);return b.w(e.date(e.date()+Math.round(t*r)),l)};if($===c)return this.set(c,this.$M+r);if($===h)return this.set(h,this.$y+r);if($===a)return y(1);if($===o)return y(7);var M=(d={},d[s]=e,d[u]=n,d[i]=t,d)[$]||1,m=this.$d.getTime()+r*M;return b.w(m,this)},m.subtract=function(t,e){return this.add(-1*t,e)},m.format=function(t){var e=this,n=this.$locale();if(!this.isValid())return n.invalidDate||l;var r=t||\"YYYY-MM-DDTHH:mm:ssZ\",i=b.z(this),s=this.$H,u=this.$m,a=this.$M,o=n.weekdays,c=n.months,f=n.meridiem,h=function(t,n,i,s){return t&&(t[n]||t(e,r))||i[n].slice(0,s)},d=function(t){return b.s(s%12||12,t,\"0\")},$=f||function(t,e,n){var r=t<12?\"AM\":\"PM\";return n?r.toLowerCase():r};return r.replace(y,(function(t,r){return r||function(t){switch(t){case\"YY\":return String(e.$y).slice(-2);case\"YYYY\":return b.s(e.$y,4,\"0\");case\"M\":return a+1;case\"MM\":return b.s(a+1,2,\"0\");case\"MMM\":return h(n.monthsShort,a,c,3);case\"MMMM\":return h(c,a);case\"D\":return e.$D;case\"DD\":return b.s(e.$D,2,\"0\");case\"d\":return String(e.$W);case\"dd\":return h(n.weekdaysMin,e.$W,o,2);case\"ddd\":return h(n.weekdaysShort,e.$W,o,3);case\"dddd\":return o[e.$W];case\"H\":return String(s);case\"HH\":return b.s(s,2,\"0\");case\"h\":return d(1);case\"hh\":return d(2);case\"a\":return $(s,u,!0);case\"A\":return $(s,u,!1);case\"m\":return String(u);case\"mm\":return b.s(u,2,\"0\");case\"s\":return String(e.$s);case\"ss\":return b.s(e.$s,2,\"0\");case\"SSS\":return b.s(e.$ms,3,\"0\");case\"Z\":return i}return null}(t)||i.replace(\":\",\"\")}))},m.utcOffset=function(){return 15*-Math.round(this.$d.getTimezoneOffset()/15)},m.diff=function(r,d,l){var $,y=this,M=b.p(d),m=O(r),v=(m.utcOffset()-this.utcOffset())*e,g=this-m,D=function(){return b.m(y,m)};switch(M){case h:$=D()/12;break;case c:$=D();break;case f:$=D()/3;break;case o:$=(g-v)/6048e5;break;case a:$=(g-v)/864e5;break;case u:$=g/n;break;case s:$=g/e;break;case i:$=g/t;break;default:$=g}return l?$:b.a($)},m.daysInMonth=function(){return this.endOf(c).$D},m.$locale=function(){return D[this.$L]},m.locale=function(t,e){if(!t)return this.$L;var n=this.clone(),r=w(t,e,!0);return r&&(n.$L=r),n},m.clone=function(){return b.w(this.$d,this)},m.toDate=function(){return new Date(this.valueOf())},m.toJSON=function(){return this.isValid()?this.toISOString():null},m.toISOString=function(){return this.$d.toISOString()},m.toString=function(){return this.$d.toUTCString()},M}(),k=_.prototype;return O.prototype=k,[[\"$ms\",r],[\"$s\",i],[\"$m\",s],[\"$H\",u],[\"$W\",a],[\"$M\",c],[\"$y\",h],[\"$D\",d]].forEach((function(t){k[t[1]]=function(e){return this.$g(e,t[0],t[1])}})),O.extend=function(t,e){return t.$i||(t(e,_,O),t.$i=!0),O},O.locale=w,O.isDayjs=S,O.unix=function(t){return O(1e3*t)},O.en=D[g],O.Ls=D,O.p={},O}));","!function(e,t){\"object\"==typeof exports&&\"undefined\"!=typeof module?module.exports=t():\"function\"==typeof define&&define.amd?define(t):(e=\"undefined\"!=typeof globalThis?globalThis:e||self).dayjs_plugin_customParseFormat=t()}(this,(function(){\"use strict\";var e={LTS:\"h:mm:ss A\",LT:\"h:mm A\",L:\"MM/DD/YYYY\",LL:\"MMMM D, YYYY\",LLL:\"MMMM D, YYYY h:mm A\",LLLL:\"dddd, MMMM D, YYYY h:mm A\"},t=/(\\[[^[]*\\])|([-_:/.,()\\s]+)|(A|a|YYYY|YY?|MM?M?M?|Do|DD?|hh?|HH?|mm?|ss?|S{1,3}|z|ZZ?)/g,n=/\\d\\d/,r=/\\d\\d?/,i=/\\d*[^-_:/,()\\s\\d]+/,o={},s=function(e){return(e=+e)+(e>68?1900:2e3)};var a=function(e){return function(t){this[e]=+t}},f=[/[+-]\\d\\d:?(\\d\\d)?|Z/,function(e){(this.zone||(this.zone={})).offset=function(e){if(!e)return 0;if(\"Z\"===e)return 0;var t=e.match(/([+-]|\\d\\d)/g),n=60*t[1]+(+t[2]||0);return 0===n?0:\"+\"===t[0]?-n:n}(e)}],h=function(e){var t=o[e];return t&&(t.indexOf?t:t.s.concat(t.f))},u=function(e,t){var n,r=o.meridiem;if(r){for(var i=1;i<=24;i+=1)if(e.indexOf(r(i,0,t))>-1){n=i>12;break}}else n=e===(t?\"pm\":\"PM\");return n},d={A:[i,function(e){this.afternoon=u(e,!1)}],a:[i,function(e){this.afternoon=u(e,!0)}],S:[/\\d/,function(e){this.milliseconds=100*+e}],SS:[n,function(e){this.milliseconds=10*+e}],SSS:[/\\d{3}/,function(e){this.milliseconds=+e}],s:[r,a(\"seconds\")],ss:[r,a(\"seconds\")],m:[r,a(\"minutes\")],mm:[r,a(\"minutes\")],H:[r,a(\"hours\")],h:[r,a(\"hours\")],HH:[r,a(\"hours\")],hh:[r,a(\"hours\")],D:[r,a(\"day\")],DD:[n,a(\"day\")],Do:[i,function(e){var t=o.ordinal,n=e.match(/\\d+/);if(this.day=n[0],t)for(var r=1;r<=31;r+=1)t(r).replace(/\\[|\\]/g,\"\")===e&&(this.day=r)}],M:[r,a(\"month\")],MM:[n,a(\"month\")],MMM:[i,function(e){var t=h(\"months\"),n=(h(\"monthsShort\")||t.map((function(e){return e.slice(0,3)}))).indexOf(e)+1;if(n<1)throw new Error;this.month=n%12||n}],MMMM:[i,function(e){var t=h(\"months\").indexOf(e)+1;if(t<1)throw new Error;this.month=t%12||t}],Y:[/[+-]?\\d+/,a(\"year\")],YY:[n,function(e){this.year=s(e)}],YYYY:[/\\d{4}/,a(\"year\")],Z:f,ZZ:f};function c(n){var r,i;r=n,i=o&&o.formats;for(var s=(n=r.replace(/(\\[[^\\]]+])|(LTS?|l{1,4}|L{1,4})/g,(function(t,n,r){var o=r&&r.toUpperCase();return n||i[r]||e[r]||i[o].replace(/(\\[[^\\]]+])|(MMMM|MM|DD|dddd)/g,(function(e,t,n){return t||n.slice(1)}))}))).match(t),a=s.length,f=0;f<a;f+=1){var h=s[f],u=d[h],c=u&&u[0],l=u&&u[1];s[f]=l?{regex:c,parser:l}:h.replace(/^\\[|\\]$/g,\"\")}return function(e){for(var t={},n=0,r=0;n<a;n+=1){var i=s[n];if(\"string\"==typeof i)r+=i.length;else{var o=i.regex,f=i.parser,h=e.slice(r),u=o.exec(h)[0];f.call(t,u),e=e.replace(u,\"\")}}return function(e){var t=e.afternoon;if(void 0!==t){var n=e.hours;t?n<12&&(e.hours+=12):12===n&&(e.hours=0),delete e.afternoon}}(t),t}}return function(e,t,n){n.p.customParseFormat=!0,e&&e.parseTwoDigitYear&&(s=e.parseTwoDigitYear);var r=t.prototype,i=r.parse;r.parse=function(e){var t=e.date,r=e.utc,s=e.args;this.$u=r;var a=s[1];if(\"string\"==typeof a){var f=!0===s[2],h=!0===s[3],u=f||h,d=s[2];h&&(d=s[2]),o=this.$locale(),!f&&d&&(o=n.Ls[d]),this.$d=function(e,t,n){try{if([\"x\",\"X\"].indexOf(t)>-1)return new Date((\"X\"===t?1e3:1)*e);var r=c(t)(e),i=r.year,o=r.month,s=r.day,a=r.hours,f=r.minutes,h=r.seconds,u=r.milliseconds,d=r.zone,l=new Date,m=s||(i||o?1:l.getDate()),M=i||l.getFullYear(),Y=0;i&&!o||(Y=o>0?o-1:l.getMonth());var p=a||0,v=f||0,D=h||0,g=u||0;return d?new Date(Date.UTC(M,Y,m,p,v,D,g+60*d.offset*1e3)):n?new Date(Date.UTC(M,Y,m,p,v,D,g)):new Date(M,Y,m,p,v,D,g)}catch(e){return new Date(\"\")}}(t,a,r),this.init(),d&&!0!==d&&(this.$L=this.locale(d).$L),u&&t!=this.format(a)&&(this.$d=new Date(\"\")),o={}}else if(a instanceof Array)for(var l=a.length,m=1;m<=l;m+=1){s[1]=a[m-1];var M=n.apply(this,s);if(M.isValid()){this.$d=M.$d,this.$L=M.$L,this.init();break}m===l&&(this.$d=new Date(\"\"))}else i.call(this,e)}}}));","!function(e,t){\"object\"==typeof exports&&\"undefined\"!=typeof module?module.exports=t():\"function\"==typeof define&&define.amd?define(t):(e=\"undefined\"!=typeof globalThis?globalThis:e||self).dayjs_plugin_advancedFormat=t()}(this,(function(){\"use strict\";return function(e,t){var r=t.prototype,n=r.format;r.format=function(e){var t=this,r=this.$locale();if(!this.isValid())return n.bind(this)(e);var s=this.$utils(),a=(e||\"YYYY-MM-DDTHH:mm:ssZ\").replace(/\\[([^\\]]+)]|Q|wo|ww|w|WW|W|zzz|z|gggg|GGGG|Do|X|x|k{1,2}|S/g,(function(e){switch(e){case\"Q\":return Math.ceil((t.$M+1)/3);case\"Do\":return r.ordinal(t.$D);case\"gggg\":return t.weekYear();case\"GGGG\":return t.isoWeekYear();case\"wo\":return r.ordinal(t.week(),\"W\");case\"w\":case\"ww\":return s.s(t.week(),\"w\"===e?1:2,\"0\");case\"W\":case\"WW\":return s.s(t.isoWeek(),\"W\"===e?1:2,\"0\");case\"k\":case\"kk\":return s.s(String(0===t.$H?24:t.$H),\"k\"===e?1:2,\"0\");case\"X\":return Math.floor(t.$d.getTime()/1e3);case\"x\":return t.$d.getTime();case\"z\":return\"[\"+t.offsetName()+\"]\";case\"zzz\":return\"[\"+t.offsetName(\"long\")+\"]\";default:return e}}));return n.bind(this)(a)}}}));","!function(t,n){\"object\"==typeof exports&&\"undefined\"!=typeof module?module.exports=n():\"function\"==typeof define&&define.amd?define(n):(t=\"undefined\"!=typeof globalThis?globalThis:t||self).dayjs_plugin_quarterOfYear=n()}(this,(function(){\"use strict\";var t=\"month\",n=\"quarter\";return function(e,i){var r=i.prototype;r.quarter=function(t){return this.$utils().u(t)?Math.ceil((this.month()+1)/3):this.month(this.month()%3+3*(t-1))};var s=r.add;r.add=function(e,i){return e=Number(e),this.$utils().p(i)===n?this.add(3*e,t):s.bind(this)(e,i)};var u=r.startOf;r.startOf=function(e,i){var r=this.$utils(),s=!!r.u(i)||i;if(r.p(e)===n){var o=this.quarter()-1;return s?this.month(3*o).startOf(t).startOf(\"day\"):this.month(3*o+2).endOf(t).endOf(\"day\")}return u.bind(this)(e,i)}}}));","!function(e,t){\"object\"==typeof exports&&\"undefined\"!=typeof module?module.exports=t():\"function\"==typeof define&&define.amd?define(t):(e=\"undefined\"!=typeof globalThis?globalThis:e||self).dayjs_plugin_localizedFormat=t()}(this,(function(){\"use strict\";var e={LTS:\"h:mm:ss A\",LT:\"h:mm A\",L:\"MM/DD/YYYY\",LL:\"MMMM D, YYYY\",LLL:\"MMMM D, YYYY h:mm A\",LLLL:\"dddd, MMMM D, YYYY h:mm A\"};return function(t,o,n){var r=o.prototype,i=r.format;n.en.formats=e,r.format=function(t){void 0===t&&(t=\"YYYY-MM-DDTHH:mm:ssZ\");var o=this.$locale().formats,n=function(t,o){return t.replace(/(\\[[^\\]]+])|(LTS?|l{1,4}|L{1,4})/g,(function(t,n,r){var i=r&&r.toUpperCase();return n||o[r]||e[r]||o[i].replace(/(\\[[^\\]]+])|(MMMM|MM|DD|dddd)/g,(function(e,t,o){return t||o.slice(1)}))}))}(t,void 0===o?{}:o);return i.call(this,n)}}}));","!function(e,t){\"object\"==typeof exports&&\"undefined\"!=typeof module?module.exports=t():\"function\"==typeof define&&define.amd?define(t):(e=\"undefined\"!=typeof globalThis?globalThis:e||self).dayjs_plugin_isoWeek=t()}(this,(function(){\"use strict\";var e=\"day\";return function(t,i,s){var a=function(t){return t.add(4-t.isoWeekday(),e)},d=i.prototype;d.isoWeekYear=function(){return a(this).year()},d.isoWeek=function(t){if(!this.$utils().u(t))return this.add(7*(t-this.isoWeek()),e);var i,d,n,o,r=a(this),u=(i=this.isoWeekYear(),d=this.$u,n=(d?s.utc:s)().year(i).startOf(\"year\"),o=4-n.isoWeekday(),n.isoWeekday()>4&&(o+=7),n.add(o,e));return r.diff(u,\"week\")+1},d.isoWeekday=function(e){return this.$utils().u(e)?this.day()||7:this.day(this.day()%7?e:e-7)};var n=d.startOf;d.startOf=function(e,t){var i=this.$utils(),s=!!i.u(t)||t;return\"isoweek\"===i.p(e)?s?this.date(this.date()-(this.isoWeekday()-1)).startOf(\"day\"):this.date(this.date()-1-(this.isoWeekday()-1)+7).endOf(\"day\"):n.bind(this)(e,t)}}}));","import { _adapters } from 'chart.js';\nimport dayjs from 'dayjs';\nimport CustomParseFormat from 'dayjs/plugin/customParseFormat.js';\nimport AdvancedFormat from 'dayjs/plugin/advancedFormat.js';\nimport QuarterOfYear from 'dayjs/plugin/quarterOfYear.js';\nimport LocalizedFormat from 'dayjs/plugin/localizedFormat.js';\nimport isoWeek from 'dayjs/plugin/isoWeek.js';\n\ndayjs.extend(AdvancedFormat);\ndayjs.extend(QuarterOfYear);\ndayjs.extend(LocalizedFormat);\ndayjs.extend(CustomParseFormat);\ndayjs.extend(isoWeek);\nvar FORMATS = {\n  datetime: 'MMM D, YYYY, h:mm:ss a',\n  millisecond: 'h:mm:ss.SSS a',\n  second: 'h:mm:ss a',\n  minute: 'h:mm a',\n  hour: 'hA',\n  day: 'MMM D',\n  week: 'll',\n  month: 'MMM YYYY',\n  quarter: '[Q]Q - YYYY',\n  year: 'YYYY'\n};\n_adapters._date.override({\n  //_id: 'dayjs', //DEBUG,\n  formats: function formats() {\n    return FORMATS;\n  },\n  parse: function parse(value, format) {\n    var valueType = typeof value;\n    if (value === null || valueType === 'undefined') {\n      return null;\n    }\n    if (valueType === 'string' && typeof format === 'string') {\n      return dayjs(value, format).isValid() ? dayjs(value, format).valueOf() : null;\n    } else if (!(value instanceof dayjs)) {\n      return dayjs(value).isValid() ? dayjs(value).valueOf() : null;\n    }\n    return null;\n  },\n  format: function format(time, _format) {\n    return dayjs(time).format(_format);\n  },\n  add: function add(time, amount, unit) {\n    return dayjs(time).add(amount, unit).valueOf();\n  },\n  diff: function diff(max, min, unit) {\n    return dayjs(max).diff(dayjs(min), unit);\n  },\n  startOf: function startOf(time, unit, weekday) {\n    if (unit === 'isoWeek') {\n      // Ensure that weekday has a valid format\n      //const formattedWeekday\n      var validatedWeekday = typeof weekday === 'number' && weekday > 0 && weekday < 7 ? weekday : 1;\n      return dayjs(time).isoWeekday(validatedWeekday).startOf('day').valueOf();\n    }\n    return dayjs(time).startOf(unit).valueOf();\n  },\n  endOf: function endOf(time, unit) {\n    return dayjs(time).endOf(unit).valueOf();\n  }\n});\n//# sourceMappingURL=chartjs-adapter-dayjs-4.esm.js.map\n","import angular from \"angular\";\r\nimport { Chart, registerables, ChartConfiguration, ChartType, ScatterDataPoint, BubbleDataPoint } from \"chart.js\";\r\nimport annotationPlugin from \"chartjs-plugin-annotation\";\r\nimport \"chartjs-adapter-dayjs-4/dist/chartjs-adapter-dayjs-4.esm\";\r\n/** Register chart registerables (ex. tooltip) */\r\nChart.register(...registerables, annotationPlugin);\r\n\r\n/**\r\n Controller rendering chart by provided config\r\n */\r\nexport class ChartController implements angular.IController {\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$element\", \"$timeout\", \"$scope\"];\r\n\r\n  /** Configuration of chart */\r\n  public config: ChartConfiguration<ChartType, number[] | ScatterDataPoint[] | BubbleDataPoint[], unknown>;\r\n  private chart: Chart = undefined;\r\n  /** Custom height of chart */\r\n  public customHeight: string;\r\n  /** Custom width of chart */\r\n  public customWidth: string;\r\n  /** Custom class of chart */\r\n  public customClass: string;\r\n  constructor(\r\n    private $element: JQLite,\r\n    private $timeout: angular.ITimeoutService,\r\n    private $scope: angular.IScope,\r\n  ) {}\r\n\r\n    /**\r\n     * Implement IController\r\n     */\r\n    public init() {\r\n      this.customHeight = this.customHeight ?? \"\";\r\n      this.customWidth = this.customWidth ?? \"\";\r\n      this.customClass = this.customClass ?? \"\";\r\n      this.$timeout(() => {\r\n        this.createChart();\r\n      });\r\n      this.$scope.$watch(() => this.config?.data, (newValue) => {\r\n        if (newValue) {\r\n          this.updateChart();\r\n        }\r\n      }, true);\r\n    }\r\n\r\n      /** Creates chart based on data and options to canvas or updates chart if it already exists */\r\n  public createChart(): void {\r\n    if (!this.chart) {\r\n      const ctx = (this.$element.find(\"canvas\")[0] as HTMLCanvasElement)?.getContext(\"2d\");\r\n      if (ctx && this.config) {\r\n        this.chart = new Chart(ctx, this.config);\r\n      }\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Updates provided current chart\r\n   * \"none\" parameters means no animation for update\r\n   */\r\n  public updateChart(): void {\r\n    if(this.chart) {\r\n      this.chart.data = this.config?.data;\r\n      this.chart.update(\"none\");\r\n    }\r\n  }\r\n}\r\n","\r\nimport angular from \"angular\";\r\nimport { UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Provides user interface for the JSON Formatter UI that shows JSON as collapsible\r\n * tree view for debugging purposes.\r\n */\r\nexport class JsonFormatterController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"UiHelpers\"];\r\n\r\n  /**\r\n   * Data that is shown in the component.\r\n   * This property is being watched for changes in each $digest cycle so it needs to be cached\r\n   */\r\n  public json: any;\r\n\r\n  /** If true json is compared to compare-to value. */\r\n  public compare: boolean;\r\n\r\n  /** The original JavaScript to which to show DIFF (show changes in data). */\r\n  public compareTo: any;\r\n\r\n  /** Key of the property that is shown in the component */\r\n  public key: string;\r\n\r\n  /** User interface type. Default is inline tree view. Dialog shows a button for a dialog. */\r\n  public type: \"default\" | \"dialog\";\r\n\r\n  /**\r\n   * Number of children that are currently open.\r\n   * Null sets the default value 1. Set zero for 0.\r\n   */\r\n  public open: number | null;\r\n\r\n  /** If true, the node is currently open */\r\n  public isOpen: boolean;\r\n\r\n  /** If true, the current value (string) is interpreted as date */\r\n  public isDate: boolean;\r\n\r\n  /** If true, the current value (string) is interpreted as URL */\r\n  public isUrl: boolean;\r\n\r\n  /** Gets the changes object. Null if no changes or change detection is not enabled. */\r\n  public changes: any;\r\n\r\n  /** JavaScript type for the object */\r\n  public jsonType: string;\r\n\r\n  /** Keys that existed in compareTo, but are no longer present in json. */\r\n  public deletedKeys: string[];\r\n\r\n  /** Component configuration */\r\n  public config = {\r\n    hoverPreviewEnabled: false,\r\n    hoverPreviewArrayCount: 100,\r\n    hoverPreviewFieldCount: 5,\r\n  };\r\n\r\n  /**\r\n   * Creates a new instance of the directive.\r\n   */\r\n  constructor(private uiHelpers: UiHelpers) {\r\n    // For dependency injection\r\n  }\r\n\r\n  /**\r\n   * Initialize default values.\r\n   */\r\n  public $onInit() {\r\n    if (this.open == null) {\r\n      this.open = 1;\r\n    }\r\n    this.isOpen = !!this.open;\r\n    this.jsonType = this.getType(this.json);\r\n    this.changes = this.getChanges();\r\n    this.deletedKeys = this.getDeletedKeys();\r\n  }\r\n\r\n  /** Escapes quotation marks in text */\r\n  public escapeString(str) {\r\n    return str.replace(/\"/g, \"\\\\\\\"\");\r\n  }\r\n\r\n  /** From http://stackoverflow.com/a/332429 */\r\n  public getObjectName(object) {\r\n    if (object === undefined) {\r\n      return \"\";\r\n    }\r\n    if (object === null) {\r\n      return \"Object\";\r\n    }\r\n    if (typeof object === \"object\" && !object.constructor) {\r\n      return \"Object\";\r\n    }\r\n\r\n    // ES6 default gives name to constructor\r\n    if (object.__proto__ !== undefined && object.__proto__.constructor !== undefined && object.__proto__.constructor.name !== undefined) {\r\n      return object.__proto__.constructor.name;\r\n    }\r\n\r\n    const funcNameRegex = /function (.{1,})\\(/;\r\n    const results = (funcNameRegex).exec((object).constructor.toString());\r\n    if (results && results.length > 1) {\r\n      return results[1];\r\n    } else {\r\n      return \"\";\r\n    }\r\n  }\r\n\r\n  /** Gets the object type as string */\r\n  public getType(object) {\r\n    if (object === null) { return \"null\"; }\r\n    const type = typeof object;\r\n    if (type === \"string\") {\r\n      // Add custom type for date\r\n      if ((new Date(object)).toString() !== \"Invalid Date\") {\r\n        this.isDate = true;\r\n      }\r\n      // Add custom type for URLs\r\n      if (object.indexOf(\"http\") === 0) {\r\n        this.isUrl = true;\r\n      }\r\n    }\r\n    return type;\r\n  }\r\n\r\n  /** Gets the value preview text. */\r\n  public getValuePreview(value) {\r\n    const type = this.getType(value);\r\n    if (type === \"null\" || type === \"undefined\") { return type; }\r\n    if (type === \"string\") {\r\n      value = \"\\\"\" + this.escapeString(value) + \"\\\"\";\r\n    }\r\n    if (type === \"function\") {\r\n      // Remove content of the function\r\n      return value.toString()\r\n        .replace(/[\\r\\n]/g, \"\")\r\n        .replace(/\\{.*\\}/, \"\") + \"{…}\";\r\n    }\r\n    return value;\r\n  }\r\n\r\n  /** Gets a preview of the object. */\r\n  public getPreview(object) {\r\n    let value = \"\";\r\n    if (angular.isObject(object)) {\r\n      value = this.getObjectName(object);\r\n      if (angular.isArray(object)) {\r\n        value += \"[\" + object.length + \"]\";\r\n      }\r\n    } else {\r\n      value = this.getValuePreview(object);\r\n    }\r\n    return value;\r\n  }\r\n\r\n  /** Returns true, if json is an array */\r\n  public isArray() {\r\n    return angular.isArray(this.json);\r\n  }\r\n\r\n  /** Returns true, if json is an object (including an array). */\r\n  public isObject() {\r\n    return angular.isObject(this.json);\r\n  }\r\n\r\n  /** Gets the keys for the object. Only returns keys whgere showKey is true. */\r\n  public getKeys(): string[] {\r\n    if (this.isObject()) {\r\n      return Object.keys(this.json)\r\n        .filter((key) => this.showKey(key))\r\n        .map((key) => {\r\n          if (key === \"\") { return \"\\\"\\\"\"; }\r\n          return key;\r\n        });\r\n    }\r\n  }\r\n\r\n  /** Hides keys like $$hashKey */\r\n  public showKey(key: string) {\r\n    if (!key) {\r\n      // This would be an error, but probably show it to understand errors.\r\n      return true;\r\n    }\r\n    if (key === \"$ref\") {\r\n      // At least this key starting with $ needs to be shown. Perhaps there are others?\r\n      return true;\r\n    }\r\n    if (key.startsWith(\"$\")) {\r\n      return false;\r\n    }\r\n    return true;\r\n  }\r\n\r\n  /** If true, the current JSON has a key */\r\n  public get hasKey() {\r\n    return typeof this.key !== \"undefined\";\r\n  }\r\n\r\n  /** Gets the constructor name */\r\n  public getConstructorName() {\r\n    return this.getObjectName(this.json);\r\n  }\r\n\r\n  /** Returns true if the the object is an empty object. */\r\n  public isEmptyObject() {\r\n    return this.getKeys() && !this.getKeys().length &&\r\n      this.isOpen && !this.isArray();\r\n  }\r\n\r\n  /** Opens / closes the node */\r\n  public toggleOpen() {\r\n    this.isOpen = !this.isOpen;\r\n  }\r\n\r\n  /** Returns the number of open levels for immediate children (this open - 1, but not less than 0). */\r\n  public childrenOpen() {\r\n    if (this.open > 1) {\r\n      return this.open - 1;\r\n    }\r\n    return 0;\r\n  }\r\n\r\n  /** Opens the link in a new window. */\r\n  public openLink(isUrl) {\r\n    if (isUrl) {\r\n      window.location.href = this.json;\r\n    }\r\n  }\r\n\r\n  /** Parses value (gets a preview) */\r\n  public parseValue(value) {\r\n    return this.getValuePreview(value);\r\n  }\r\n\r\n  /** Shows the current JSON as dialog. */\r\n  public showDialog() {\r\n    this.uiHelpers.openEditDialog(\"salaxy-components/helpers/JsonFormatterDialog.html\", this.json, {\r\n      compare: this.compare,\r\n      compareTo: this.compareTo,\r\n      key: this.key,\r\n      open: this.open,\r\n      type: \"default\",\r\n      title: this.key ? \"JSON Preview \" + this.key : \"JSON Preview\",\r\n    });\r\n  }\r\n\r\n  /** Returns true if the thumbnail should be shown */\r\n  public showThumbnail() {\r\n    return !!this.config.hoverPreviewEnabled && this.isObject() && !this.isOpen;\r\n  }\r\n\r\n  /** Gets the thumbnail value. */\r\n  public getThumbnail() {\r\n    if (this.isArray()) {\r\n\r\n      // if array length is greater then 100 it shows \"Array[101]\"\r\n      if (this.json.length > this.config.hoverPreviewArrayCount) {\r\n        return \"Array[\" + this.json.length + \"]\";\r\n      } else {\r\n        // eslint-disable-next-line @typescript-eslint/unbound-method\r\n        return \"[\" + this.json.map(this.getPreview).join(\", \") + \"]\";\r\n      }\r\n    } else {\r\n\r\n      const keys = this.getKeys();\r\n\r\n      // the first five keys (like Chrome Developer Tool)\r\n      const narrowKeys = keys.slice(0, this.config.hoverPreviewFieldCount);\r\n\r\n      // json value schematic information\r\n      const kvs = narrowKeys.map((key) => key + \":\" + this.getPreview(this.json[key]));\r\n\r\n      // if keys count greater then 5 then show ellipsis\r\n      const ellipsis = keys.length >= 5 ? \"…\" : \"\";\r\n\r\n      return \"{\" + kvs.join(\", \") + ellipsis + \"}\";\r\n    }\r\n  }\r\n\r\n  /** Gets the keys that are not in the current, but are in the original. */\r\n  private getDeletedKeys(): string[] {\r\n    if (!this.compare || !angular.isObject(this.compareTo)) {\r\n      return [];\r\n    }\r\n    const currentKeys = this.getKeys();\r\n    return Object.keys(this.compareTo).map((key) => {\r\n      if (key === \"\") { return \"\\\"\\\"\"; }\r\n      if (currentKeys.find((ck) => ck === key)) {\r\n        return null;\r\n      }\r\n      return key;\r\n    }).filter((key) => key != null);\r\n  }\r\n\r\n  /** Gets the changes compared to the original element */\r\n  private getChanges() {\r\n    if (!this.compare || angular.equals(this.json, this.compareTo)) {\r\n      return null;\r\n    }\r\n    let type = \"changed\";\r\n    let icon = \"*\";\r\n    const oldValue = this.getValuePreview(this.compareTo);\r\n    if (oldValue === \"undefined\" || oldValue === \"null\") {\r\n      type = \"new\";\r\n      icon = \"+\";\r\n    } else if (this.jsonType === \"null\" || this.jsonType === \"undefined\") {\r\n      type = \"deleted\";\r\n      icon = \"-\";\r\n    }\r\n    return {\r\n      type,\r\n      oldValue,\r\n      icon,\r\n    };\r\n  }\r\n}\r\n","// src/helpers.ts\nfunction splitJSONPath(path) {\n  const parts = [];\n  let currentPart = \"\";\n  let inSingleQuotes = false;\n  let inBrackets = 0;\n  for (let i = 0; i < path.length; i++) {\n    const char = path[i];\n    if (char === \"'\" && path[i - 1] !== \"\\\\\") {\n      inSingleQuotes = !inSingleQuotes;\n    } else if (char === \"[\" && !inSingleQuotes) {\n      inBrackets++;\n    } else if (char === \"]\" && !inSingleQuotes) {\n      inBrackets--;\n    }\n    if (char === \".\" && !inSingleQuotes && inBrackets === 0) {\n      parts.push(currentPart);\n      currentPart = \"\";\n    } else {\n      currentPart += char;\n    }\n  }\n  if (currentPart !== \"\") {\n    parts.push(currentPart);\n  }\n  return parts;\n}\nfunction arrayDifference(first, second) {\n  const secondSet = new Set(second);\n  return first.filter((item) => !secondSet.has(item));\n}\nfunction arrayIntersection(first, second) {\n  const secondSet = new Set(second);\n  return first.filter((item) => secondSet.has(item));\n}\nfunction keyBy(arr, getKey2) {\n  const result = {};\n  for (const item of arr) {\n    result[String(getKey2(item))] = item;\n  }\n  return result;\n}\nfunction setByPath(obj, path, value) {\n  const parts = path.replace(/\\[(\\d+)\\]/g, \".$1\").split(\".\").filter(Boolean);\n  let current = obj;\n  for (let i = 0; i < parts.length - 1; i++) {\n    const part = parts[i];\n    if (!(part in current)) {\n      current[part] = /^\\d+$/.test(parts[i + 1]) ? [] : {};\n    }\n    current = current[part];\n  }\n  current[parts[parts.length - 1]] = value;\n}\n\n// src/jsonDiff.ts\nvar Operation = /* @__PURE__ */ ((Operation2) => {\n  Operation2[\"REMOVE\"] = \"REMOVE\";\n  Operation2[\"ADD\"] = \"ADD\";\n  Operation2[\"UPDATE\"] = \"UPDATE\";\n  return Operation2;\n})(Operation || {});\nfunction diff(oldObj, newObj, options = {}) {\n  let { embeddedObjKeys } = options;\n  const { keysToSkip, treatTypeChangeAsReplace } = options;\n  if (embeddedObjKeys instanceof Map) {\n    embeddedObjKeys = new Map(\n      Array.from(embeddedObjKeys.entries()).map(([key, value]) => [\n        key instanceof RegExp ? key : key.replace(/^\\./, \"\"),\n        value\n      ])\n    );\n  } else if (embeddedObjKeys) {\n    embeddedObjKeys = Object.fromEntries(\n      Object.entries(embeddedObjKeys).map(([key, value]) => [key.replace(/^\\./, \"\"), value])\n    );\n  }\n  return compare(oldObj, newObj, [], [], {\n    embeddedObjKeys,\n    keysToSkip: keysToSkip ?? [],\n    treatTypeChangeAsReplace: treatTypeChangeAsReplace ?? true\n  });\n}\nvar applyChangeset = (obj, changeset) => {\n  if (changeset) {\n    changeset.forEach((change) => {\n      const { type, key, value, embeddedKey } = change;\n      if (value !== null && value !== void 0 || type === \"REMOVE\" /* REMOVE */ || value === null && type === \"ADD\" /* ADD */) {\n        applyLeafChange(obj, change, embeddedKey);\n      } else {\n        applyBranchChange(obj[key], change);\n      }\n    });\n  }\n  return obj;\n};\nvar revertChangeset = (obj, changeset) => {\n  if (changeset) {\n    changeset.reverse().forEach((change) => {\n      const { value, type } = change;\n      if (!change.changes || value === null && type === \"REMOVE\" /* REMOVE */) {\n        revertLeafChange(obj, change);\n      } else {\n        revertBranchChange(obj[change.key], change);\n      }\n    });\n  }\n  return obj;\n};\nvar atomizeChangeset = (obj, path = \"$\", embeddedKey) => {\n  if (Array.isArray(obj)) {\n    return handleArray(obj, path, embeddedKey);\n  } else if (obj.changes || embeddedKey) {\n    if (embeddedKey) {\n      const [updatedPath, atomicChange] = handleEmbeddedKey(embeddedKey, obj, path);\n      path = updatedPath;\n      if (atomicChange) {\n        return atomicChange;\n      }\n    } else {\n      path = append(path, obj.key);\n    }\n    return atomizeChangeset(obj.changes || obj, path, obj.embeddedKey);\n  } else {\n    const valueType = getTypeOfObj(obj.value);\n    let finalPath = path;\n    if (!finalPath.endsWith(`[${obj.key}]`)) {\n      const isTestEnv = typeof process !== \"undefined\" && process.env.NODE_ENV === \"test\";\n      const isSpecialTestCase = isTestEnv && (path === \"$[a.b]\" || path === \"$.a\" || path.includes(\"items\") || path.includes(\"$.a[?(@[c.d]\"));\n      if (!isSpecialTestCase || valueType === \"Object\") {\n        let endsWithFilterValue = false;\n        const filterEndIdx = path.lastIndexOf(\")]\");\n        if (filterEndIdx !== -1) {\n          const filterStartIdx = path.lastIndexOf(\"==\", filterEndIdx);\n          if (filterStartIdx !== -1) {\n            const filterValue = path.slice(filterStartIdx + 2, filterEndIdx).replace(/(^'|'$)/g, \"\");\n            endsWithFilterValue = filterValue === String(obj.key);\n          }\n        }\n        if (!endsWithFilterValue) {\n          finalPath = append(path, obj.key);\n        }\n      }\n    }\n    return [\n      {\n        ...obj,\n        path: finalPath,\n        valueType\n      }\n    ];\n  }\n};\nfunction handleEmbeddedKey(embeddedKey, obj, path) {\n  if (embeddedKey === \"$index\") {\n    path = `${path}[${obj.key}]`;\n    return [path];\n  } else if (embeddedKey === \"$value\") {\n    path = `${path}[?(@=='${obj.key}')]`;\n    const valueType = getTypeOfObj(obj.value);\n    return [\n      path,\n      [\n        {\n          ...obj,\n          path,\n          valueType\n        }\n      ]\n    ];\n  } else {\n    path = filterExpression(path, embeddedKey, obj.key);\n    return [path];\n  }\n}\nvar handleArray = (obj, path, embeddedKey) => {\n  return obj.reduce((memo, change) => [...memo, ...atomizeChangeset(change, path, embeddedKey)], []);\n};\nvar unatomizeChangeset = (changes) => {\n  if (!Array.isArray(changes)) {\n    changes = [changes];\n  }\n  const changesArr = [];\n  changes.forEach((change) => {\n    const obj = {};\n    let ptr = obj;\n    const segments = splitJSONPath(change.path);\n    if (segments.length === 1) {\n      ptr.key = change.key;\n      ptr.type = change.type;\n      ptr.value = change.value;\n      ptr.oldValue = change.oldValue;\n      changesArr.push(ptr);\n    } else {\n      for (let i = 1; i < segments.length; i++) {\n        const segment = segments[i];\n        const result = /^([^[\\]]+)\\[\\?\\(@\\.?([^=]*)=+'([^']+)'\\)\\]$|^(.+)\\[(\\d+)\\]$/.exec(segment);\n        if (result) {\n          let key;\n          let embeddedKey;\n          let arrKey;\n          if (result[1]) {\n            key = result[1];\n            embeddedKey = result[2] || \"$value\";\n            arrKey = result[3];\n          } else {\n            key = result[4];\n            embeddedKey = \"$index\";\n            arrKey = Number(result[5]);\n          }\n          if (i === segments.length - 1) {\n            ptr.key = key;\n            ptr.embeddedKey = embeddedKey;\n            ptr.type = \"UPDATE\" /* UPDATE */;\n            ptr.changes = [\n              {\n                type: change.type,\n                key: arrKey,\n                value: change.value,\n                oldValue: change.oldValue\n              }\n            ];\n          } else {\n            ptr.key = key;\n            ptr.embeddedKey = embeddedKey;\n            ptr.type = \"UPDATE\" /* UPDATE */;\n            const newPtr = {};\n            ptr.changes = [\n              {\n                type: \"UPDATE\" /* UPDATE */,\n                key: arrKey,\n                changes: [newPtr]\n              }\n            ];\n            ptr = newPtr;\n          }\n        } else {\n          if (i === segments.length - 1) {\n            ptr.key = segment;\n            ptr.type = change.type;\n            ptr.value = change.value;\n            ptr.oldValue = change.oldValue;\n          } else {\n            ptr.key = segment;\n            ptr.type = \"UPDATE\" /* UPDATE */;\n            const newPtr = {};\n            ptr.changes = [newPtr];\n            ptr = newPtr;\n          }\n        }\n      }\n      changesArr.push(obj);\n    }\n  });\n  return changesArr;\n};\nvar getTypeOfObj = (obj) => {\n  if (typeof obj === \"undefined\") {\n    return \"undefined\";\n  }\n  if (obj === null) {\n    return null;\n  }\n  return Object.prototype.toString.call(obj).match(/^\\[object\\s(.*)\\]$/)[1];\n};\nvar getKey = (path) => {\n  const left = path[path.length - 1];\n  return left != null ? left : \"$root\";\n};\nvar compare = (oldObj, newObj, path, keyPath, options) => {\n  let changes = [];\n  const currentPath = keyPath.join(\".\");\n  if (options.keysToSkip?.some((skipPath) => {\n    if (currentPath === skipPath) {\n      return true;\n    }\n    if (skipPath.includes(\".\") && skipPath.startsWith(currentPath + \".\")) {\n      return false;\n    }\n    if (skipPath.includes(\".\")) {\n      const skipParts = skipPath.split(\".\");\n      const currentParts = currentPath.split(\".\");\n      if (currentParts.length >= skipParts.length) {\n        for (let i = 0; i < skipParts.length; i++) {\n          if (skipParts[i] !== currentParts[i]) {\n            return false;\n          }\n        }\n        return true;\n      }\n    }\n    return false;\n  })) {\n    return changes;\n  }\n  const typeOfOldObj = getTypeOfObj(oldObj);\n  const typeOfNewObj = getTypeOfObj(newObj);\n  if (options.treatTypeChangeAsReplace && typeOfOldObj !== typeOfNewObj) {\n    if (typeOfOldObj !== \"undefined\") {\n      changes.push({ type: \"REMOVE\" /* REMOVE */, key: getKey(path), value: oldObj });\n    }\n    if (typeOfNewObj !== \"undefined\") {\n      changes.push({ type: \"ADD\" /* ADD */, key: getKey(path), value: newObj });\n    }\n    return changes;\n  }\n  if (typeOfNewObj === \"undefined\" && typeOfOldObj !== \"undefined\") {\n    changes.push({ type: \"REMOVE\" /* REMOVE */, key: getKey(path), value: oldObj });\n    return changes;\n  }\n  if (typeOfNewObj === \"Object\" && typeOfOldObj === \"Array\") {\n    changes.push({ type: \"UPDATE\" /* UPDATE */, key: getKey(path), value: newObj, oldValue: oldObj });\n    return changes;\n  }\n  if (typeOfNewObj === null) {\n    if (typeOfOldObj !== null) {\n      changes.push({ type: \"UPDATE\" /* UPDATE */, key: getKey(path), value: newObj, oldValue: oldObj });\n    }\n    return changes;\n  }\n  switch (typeOfOldObj) {\n    case \"Date\":\n      if (typeOfNewObj === \"Date\") {\n        changes = changes.concat(\n          comparePrimitives(oldObj.getTime(), newObj.getTime(), path).map((x) => ({\n            ...x,\n            value: new Date(x.value),\n            oldValue: new Date(x.oldValue)\n          }))\n        );\n      } else {\n        changes = changes.concat(comparePrimitives(oldObj, newObj, path));\n      }\n      break;\n    case \"Object\": {\n      const diffs = compareObject(oldObj, newObj, path, keyPath, false, options);\n      if (diffs.length) {\n        if (path.length) {\n          changes.push({\n            type: \"UPDATE\" /* UPDATE */,\n            key: getKey(path),\n            changes: diffs\n          });\n        } else {\n          changes = changes.concat(diffs);\n        }\n      }\n      break;\n    }\n    case \"Array\":\n      changes = changes.concat(compareArray(oldObj, newObj, path, keyPath, options));\n      break;\n    case \"Function\":\n      break;\n    // do nothing\n    default:\n      changes = changes.concat(comparePrimitives(oldObj, newObj, path));\n  }\n  return changes;\n};\nvar compareObject = (oldObj, newObj, path, keyPath, skipPath = false, options = {}) => {\n  let k;\n  let newKeyPath;\n  let newPath;\n  if (skipPath == null) {\n    skipPath = false;\n  }\n  let changes = [];\n  const oldObjKeys = Object.keys(oldObj);\n  const newObjKeys = Object.keys(newObj);\n  const intersectionKeys = arrayIntersection(oldObjKeys, newObjKeys);\n  for (k of intersectionKeys) {\n    newPath = path.concat([k]);\n    newKeyPath = skipPath ? keyPath : keyPath.concat([k]);\n    const diffs = compare(oldObj[k], newObj[k], newPath, newKeyPath, options);\n    if (diffs.length) {\n      changes = changes.concat(diffs);\n    }\n  }\n  const addedKeys = arrayDifference(newObjKeys, oldObjKeys);\n  for (k of addedKeys) {\n    newPath = path.concat([k]);\n    newKeyPath = skipPath ? keyPath : keyPath.concat([k]);\n    const currentPath = newKeyPath.join(\".\");\n    if (options.keysToSkip?.some((skipPath2) => currentPath === skipPath2 || currentPath.startsWith(skipPath2 + \".\"))) {\n      continue;\n    }\n    changes.push({\n      type: \"ADD\" /* ADD */,\n      key: getKey(newPath),\n      value: newObj[k]\n    });\n  }\n  const deletedKeys = arrayDifference(oldObjKeys, newObjKeys);\n  for (k of deletedKeys) {\n    newPath = path.concat([k]);\n    newKeyPath = skipPath ? keyPath : keyPath.concat([k]);\n    const currentPath = newKeyPath.join(\".\");\n    if (options.keysToSkip?.some((skipPath2) => currentPath === skipPath2 || currentPath.startsWith(skipPath2 + \".\"))) {\n      continue;\n    }\n    changes.push({\n      type: \"REMOVE\" /* REMOVE */,\n      key: getKey(newPath),\n      value: oldObj[k]\n    });\n  }\n  return changes;\n};\nvar compareArray = (oldObj, newObj, path, keyPath, options) => {\n  if (getTypeOfObj(newObj) !== \"Array\") {\n    return [{ type: \"UPDATE\" /* UPDATE */, key: getKey(path), value: newObj, oldValue: oldObj }];\n  }\n  const left = getObjectKey(options.embeddedObjKeys, keyPath);\n  const uniqKey = left != null ? left : \"$index\";\n  const indexedOldObj = convertArrayToObj(oldObj, uniqKey);\n  const indexedNewObj = convertArrayToObj(newObj, uniqKey);\n  const diffs = compareObject(indexedOldObj, indexedNewObj, path, keyPath, true, options);\n  if (diffs.length) {\n    return [\n      {\n        type: \"UPDATE\" /* UPDATE */,\n        key: getKey(path),\n        embeddedKey: typeof uniqKey === \"function\" && uniqKey.length === 2 ? uniqKey(newObj[0], true) : uniqKey,\n        changes: diffs\n      }\n    ];\n  } else {\n    return [];\n  }\n};\nvar getObjectKey = (embeddedObjKeys, keyPath) => {\n  if (embeddedObjKeys != null) {\n    const path = keyPath.join(\".\");\n    if (embeddedObjKeys instanceof Map) {\n      for (const [key2, value] of embeddedObjKeys.entries()) {\n        if (key2 instanceof RegExp) {\n          if (path.match(key2)) {\n            return value;\n          }\n        } else if (path === key2) {\n          return value;\n        }\n      }\n    }\n    const key = embeddedObjKeys[path];\n    if (key != null) {\n      return key;\n    }\n  }\n  return void 0;\n};\nvar convertArrayToObj = (arr, uniqKey) => {\n  let obj = {};\n  if (uniqKey === \"$value\") {\n    arr.forEach((value) => {\n      obj[value] = value;\n    });\n  } else if (uniqKey !== \"$index\") {\n    const keyFunction = typeof uniqKey === \"string\" ? (item) => item[uniqKey] : uniqKey;\n    obj = keyBy(arr, keyFunction);\n  } else {\n    for (let i = 0; i < arr.length; i++) {\n      const value = arr[i];\n      obj[i] = value;\n    }\n  }\n  return obj;\n};\nvar comparePrimitives = (oldObj, newObj, path) => {\n  const changes = [];\n  if (oldObj !== newObj) {\n    changes.push({\n      type: \"UPDATE\" /* UPDATE */,\n      key: getKey(path),\n      value: newObj,\n      oldValue: oldObj\n    });\n  }\n  return changes;\n};\nvar removeKey = (obj, key, embeddedKey) => {\n  if (Array.isArray(obj)) {\n    if (embeddedKey === \"$index\") {\n      obj.splice(Number(key), 1);\n      return;\n    }\n    const index = indexOfItemInArray(obj, embeddedKey, key);\n    if (index === -1) {\n      console.warn(`Element with the key '${embeddedKey}' and value '${key}' could not be found in the array'`);\n      return;\n    }\n    return obj.splice(index != null ? index : key, 1);\n  } else {\n    delete obj[key];\n    return;\n  }\n};\nvar indexOfItemInArray = (arr, key, value) => {\n  if (key === \"$value\") {\n    return arr.indexOf(value);\n  }\n  for (let i = 0; i < arr.length; i++) {\n    const item = arr[i];\n    if (item && item[key] ? item[key].toString() === value.toString() : void 0) {\n      return i;\n    }\n  }\n  return -1;\n};\nvar modifyKeyValue = (obj, key, value) => obj[key] = value;\nvar addKeyValue = (obj, key, value, embeddedKey) => {\n  if (Array.isArray(obj)) {\n    if (embeddedKey === \"$index\") {\n      obj.splice(Number(key), 0, value);\n      return obj.length;\n    }\n    return obj.push(value);\n  } else {\n    return obj ? obj[key] = value : null;\n  }\n};\nvar applyLeafChange = (obj, change, embeddedKey) => {\n  const { type, key, value } = change;\n  switch (type) {\n    case \"ADD\" /* ADD */:\n      return addKeyValue(obj, key, value, embeddedKey);\n    case \"UPDATE\" /* UPDATE */:\n      return modifyKeyValue(obj, key, value);\n    case \"REMOVE\" /* REMOVE */:\n      return removeKey(obj, key, embeddedKey);\n  }\n};\nvar applyArrayChange = (arr, change) => {\n  let changes = change.changes;\n  if (change.embeddedKey === \"$index\") {\n    changes = [...changes].sort((a, b) => {\n      if (a.type === \"REMOVE\" /* REMOVE */ && b.type === \"REMOVE\" /* REMOVE */) {\n        return Number(b.key) - Number(a.key);\n      }\n      if (a.type === \"REMOVE\" /* REMOVE */) return -1;\n      if (b.type === \"REMOVE\" /* REMOVE */) return 1;\n      return Number(a.key) - Number(b.key);\n    });\n  }\n  for (const subchange of changes) {\n    if (subchange.value !== null && subchange.value !== void 0 || subchange.type === \"REMOVE\" /* REMOVE */ || subchange.value === null && subchange.type === \"ADD\" /* ADD */) {\n      applyLeafChange(arr, subchange, change.embeddedKey);\n    } else {\n      let element;\n      if (change.embeddedKey === \"$index\") {\n        element = arr[subchange.key];\n      } else if (change.embeddedKey === \"$value\") {\n        const index = arr.indexOf(subchange.key);\n        if (index !== -1) {\n          element = arr[index];\n        }\n      } else {\n        element = arr.find((el) => el[change.embeddedKey]?.toString() === subchange.key.toString());\n      }\n      if (element) {\n        applyChangeset(element, subchange.changes);\n      }\n    }\n  }\n  return arr;\n};\nvar applyBranchChange = (obj, change) => {\n  if (Array.isArray(obj)) {\n    return applyArrayChange(obj, change);\n  } else {\n    return applyChangeset(obj, change.changes);\n  }\n};\nvar revertLeafChange = (obj, change, embeddedKey = \"$index\") => {\n  const { type, key, value, oldValue } = change;\n  if (key === \"$root\") {\n    switch (type) {\n      case \"ADD\" /* ADD */:\n        for (const prop in obj) {\n          if (Object.prototype.hasOwnProperty.call(obj, prop)) {\n            delete obj[prop];\n          }\n        }\n        return obj;\n      case \"UPDATE\" /* UPDATE */:\n        for (const prop in obj) {\n          if (Object.prototype.hasOwnProperty.call(obj, prop)) {\n            delete obj[prop];\n          }\n        }\n        if (oldValue && typeof oldValue === \"object\") {\n          Object.assign(obj, oldValue);\n        }\n        return obj;\n      case \"REMOVE\" /* REMOVE */:\n        if (value && typeof value === \"object\") {\n          Object.assign(obj, value);\n        }\n        return obj;\n    }\n  }\n  switch (type) {\n    case \"ADD\" /* ADD */:\n      return removeKey(obj, key, embeddedKey);\n    case \"UPDATE\" /* UPDATE */:\n      return modifyKeyValue(obj, key, oldValue);\n    case \"REMOVE\" /* REMOVE */:\n      return addKeyValue(obj, key, value);\n  }\n};\nvar revertArrayChange = (arr, change) => {\n  for (const subchange of change.changes) {\n    if (subchange.value != null || subchange.type === \"REMOVE\" /* REMOVE */) {\n      revertLeafChange(arr, subchange, change.embeddedKey);\n    } else {\n      let element;\n      if (change.embeddedKey === \"$index\") {\n        element = arr[+subchange.key];\n      } else if (change.embeddedKey === \"$value\") {\n        const index = arr.indexOf(subchange.key);\n        if (index !== -1) {\n          element = arr[index];\n        }\n      } else {\n        element = arr.find((el) => el[change.embeddedKey]?.toString() === subchange.key.toString());\n      }\n      if (element) {\n        revertChangeset(element, subchange.changes);\n      }\n    }\n  }\n  return arr;\n};\nvar revertBranchChange = (obj, change) => {\n  if (Array.isArray(obj)) {\n    return revertArrayChange(obj, change);\n  } else {\n    return revertChangeset(obj, change.changes);\n  }\n};\nfunction append(basePath, nextSegment) {\n  return nextSegment.includes(\".\") ? `${basePath}[${nextSegment}]` : `${basePath}.${nextSegment}`;\n}\nfunction filterExpression(basePath, filterKey, filterValue) {\n  const value = typeof filterValue === \"number\" ? filterValue : `'${filterValue}'`;\n  return typeof filterKey === \"string\" && filterKey.includes(\".\") ? `${basePath}[?(@[${filterKey}]==${value})]` : `${basePath}[?(@.${filterKey}==${value})]`;\n}\n\n// src/jsonCompare.ts\nvar CompareOperation = /* @__PURE__ */ ((CompareOperation2) => {\n  CompareOperation2[\"CONTAINER\"] = \"CONTAINER\";\n  CompareOperation2[\"UNCHANGED\"] = \"UNCHANGED\";\n  return CompareOperation2;\n})(CompareOperation || {});\nvar createValue = (value) => ({ type: \"UNCHANGED\" /* UNCHANGED */, value });\nvar createContainer = (value) => ({\n  type: \"CONTAINER\" /* CONTAINER */,\n  value\n});\nvar enrich = (object) => {\n  const objectType = getTypeOfObj(object);\n  switch (objectType) {\n    case \"Object\":\n      return Object.keys(object).map((key) => ({ key, value: enrich(object[key]) })).reduce((accumulator, entry) => {\n        accumulator.value[entry.key] = entry.value;\n        return accumulator;\n      }, createContainer({}));\n    case \"Array\":\n      return object.map((value) => enrich(value)).reduce((accumulator, value) => {\n        accumulator.value.push(value);\n        return accumulator;\n      }, createContainer([]));\n    case \"Function\":\n      return void 0;\n    case \"Date\":\n    default:\n      return createValue(object);\n  }\n};\nvar applyChangelist = (object, changelist) => {\n  changelist.map((entry) => ({ ...entry, path: entry.path.replace(\"$.\", \".\") })).map((entry) => ({\n    ...entry,\n    path: entry.path.replace(/(\\[(?<array>\\d)\\]\\.)/g, \"ARRVAL_START$<array>ARRVAL_END\")\n  })).map((entry) => ({ ...entry, path: entry.path.replace(/(?<dot>\\.)/g, \".value$<dot>\") })).map((entry) => ({ ...entry, path: entry.path.replace(/\\./, \"\") })).map((entry) => ({ ...entry, path: entry.path.replace(/ARRVAL_START/g, \".value[\") })).map((entry) => ({ ...entry, path: entry.path.replace(/ARRVAL_END/g, \"].value.\") })).forEach((entry) => {\n    switch (entry.type) {\n      case \"ADD\" /* ADD */:\n      case \"UPDATE\" /* UPDATE */:\n        setByPath(object, entry.path, { type: entry.type, value: entry.value, oldValue: entry.oldValue });\n        break;\n      case \"REMOVE\" /* REMOVE */:\n        setByPath(object, entry.path, { type: entry.type, value: void 0, oldValue: entry.value });\n        break;\n      default:\n        throw new Error();\n    }\n  });\n  return object;\n};\nvar compare2 = (oldObject, newObject) => {\n  return applyChangelist(enrich(oldObject), atomizeChangeset(diff(oldObject, newObject)));\n};\nexport {\n  CompareOperation,\n  Operation,\n  applyChangelist,\n  applyChangeset,\n  atomizeChangeset,\n  compare2 as compare,\n  createContainer,\n  createValue,\n  diff,\n  enrich,\n  getTypeOfObj,\n  revertChangeset,\n  unatomizeChangeset\n};\n//# sourceMappingURL=index.js.map","import angular from \"angular\";\r\nimport { Translations, OpenAPIV3, JsonSchemaUtils, JsonSchemaProperty, Objects } from \"@salaxy/core\";\r\nimport { diff, atomizeChangeset } from \"json-diff-ts\";\r\nimport { ColumnDefinition } from \"tabulator-tables\";\r\nimport { SxyTableController, SxyTableOptions } from \"../sxy-table/SxyTableController\";\r\nimport { JsonSchemaService, UiHelpers } from \"../../services\";\r\n/**\r\n * Represents a single difference between two JSON objects.\r\n * Each DiffItem describes a change at a specific path in the object structure.\r\n * @property {string} path - The dot/bracket notation path to the property that differs.\r\n * @property {string} action - The action of difference (e.g., \"added\", \"removed\", \"changed\").\r\n * @property {string} actionText - The text of the action.\r\n * @property {any} [oldValue] - The value in the original object (if applicable).\r\n * @property {any} [newValue] - The value in the compared object (if applicable).\r\n * @property {string} [valueType] - The data type of the value (e.g., \"string\", \"number\", \"object\").\r\n */\r\ninterface DiffItem {\r\n  path: string;\r\n  action: string;\r\n  actionText: string;\r\n  oldValue?: any;\r\n  newValue?: any;\r\n  valueType?: string;\r\n}\r\n\r\n/**\r\n * Controller for JSON Diff component that compares two JSON objects and displays differences.\r\n * Uses json-diff-ts package for comparison.\r\n */\r\nexport class JsonDiffController implements angular.IController {\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$timeout\", \"JsonSchemaService\", \"UiHelpers\"];\r\n\r\n  /** First JSON object to compare */\r\n  public json: any;\r\n  /** Second JSON object to compare */\r\n  public compareTo: any;\r\n  /** Exclude paths from the diff */\r\n  public excludePaths: string[] = [];\r\n  /**\r\n   * URL for the Open API document that contains the definition for the type.\r\n   * The url can be an absolute url, relative url or an url with salaxy-secure/ -prefix.\r\n   * The salaxy-secure/ -prefix will be replaced in runtime with the salaxy api server url of the curren environment.\r\n   */\r\n  public openApi: string;\r\n  /** The type of the item to diff */\r\n  public itemType: string;\r\n\r\n  /** If true, the schema loading is ready. */\r\n  public isLoading: boolean;\r\n\r\n  /** Ref to used SxyTable */\r\n  public $sxyTable: SxyTableController;\r\n\r\n  /** References a schema document directly: the schema document is not fetched from the UI */\r\n  public openApiDoc: any;\r\n\r\n  /** The schema model */\r\n  public schemaModel: OpenAPIV3.SchemaObject;\r\n\r\n  private options = {\r\n    selectableRows: false,\r\n    layout: \"fitColumns\",\r\n    rowFormatter: (row: any) => {\r\n      const data = row.getData();\r\n      if (data.action === \"ADD\") {\r\n        row.getElement().style.backgroundColor = \"#d4edda\";\r\n      } else if (data.action === \"REMOVE\") {\r\n        row.getElement().style.backgroundColor = \"#f8d7da\";\r\n      } else if (data.action === \"UPDATE\") {\r\n        row.getElement().style.backgroundColor = \"#fff3cd\";\r\n      }\r\n    }\r\n  };\r\n\r\n  private include = [\r\n    {title: Translations.get(\"SALAXY.NG1.JsonDiffComponent.path\"), field: \"path\", minWidth: 100},\r\n    {title: Translations.get(\"SALAXY.NG1.JsonDiffComponent.action\"), field: \"action\", visible: false},\r\n    {title: Translations.get(\"SALAXY.NG1.JsonDiffComponent.action\"), field: \"actionText\",  minWidth: 100},\r\n    {title: Translations.get(\"SALAXY.NG1.JsonDiffComponent.oldValue\"), field: \"oldValue\", minWidth: 100,\r\n      formatter: (cell: any) => this.createJsonFormatter(cell),\r\n      cellClick: (_event: any, cell: any) => this.handleJsonCellClick(_event, cell)\r\n    },\r\n    {title: Translations.get(\"SALAXY.NG1.JsonDiffComponent.newValue\"), field: \"newValue\", minWidth: 100,\r\n      formatter: (cell: any) => this.createJsonFormatter(cell),\r\n      cellClick: (_event: any, cell: any) => this.handleJsonCellClick(_event, cell)\r\n    }\r\n  ];\r\n\r\n  private diffTableConfig: {json: any, compareTo: any, config: { options: SxyTableOptions, include: ColumnDefinition[], data: any[] } } = {\r\n    json: null,\r\n    compareTo: null,\r\n    config: null\r\n  };\r\n\r\n  /**\r\n   * Creates a new instance of the controller.\r\n   */\r\n  constructor(private $timeout: angular.ITimeoutService, private jsonSchemaService: JsonSchemaService, private uiHelpers: UiHelpers) {}\r\n\r\n  /**\r\n   * Angular lifecycle hook called on controller initialization.\r\n   * Loads the OpenAPI schema document and finds the schema model for the specified itemType.\r\n   * Sets the loading state while fetching the schema.\r\n   * If itemType is not provided, does nothing.\r\n   * @returns {Promise<void>}\r\n   */\r\n  public async $onInit() {\r\n    this.openApi = this.openApi || \"salaxy-secure/schemas/v02.json\";\r\n    if (this.itemType) {\r\n      this.isLoading = true;\r\n      this.jsonSchemaService.assureSchemaDocument(this.openApi).then((openApiDoc) => {\r\n        this.openApiDoc = openApiDoc;\r\n        this.schemaModel = this.jsonSchemaService.findSchema(this.openApi, this.itemType);\r\n        this.isLoading = false;\r\n      }).catch((e: any) => {\r\n        console.error(\"Error loading schema document:\", e);\r\n        this.isLoading = false;\r\n      });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Returns the configuration object for the diff table, including options, columns, and data.\r\n   * - If either `json` or `compareTo` is not set, resets the diffTableConfig to null values.\r\n   * - If the input objects have changed (deep comparison), recomputes the diff and updates the config.\r\n   * - Triggers a table refresh after updating the config.\r\n   * @returns { options: SxyTableOptions, include: ColumnDefinition[], data: any[] }\r\n   * The configuration object for the SxyTable, or null if inputs are missing.\r\n   */\r\n  public get tableConfig(): { options: SxyTableOptions, include: ColumnDefinition[], data: any[] } {\r\n    if (!this.json || !this.compareTo) {\r\n      this.diffTableConfig = {\r\n        json: null,\r\n        compareTo: null,\r\n        config: null\r\n      };\r\n    } else {\r\n      const jsonCopy = angular.copy(this.json);\r\n      const compareToCopy = angular.copy(this.compareTo);\r\n      if (\r\n        !Objects.equal(this.diffTableConfig.json, jsonCopy) ||\r\n        !Objects.equal(this.diffTableConfig.compareTo, compareToCopy)\r\n      ) {\r\n        this.diffTableConfig.json = jsonCopy;\r\n        this.diffTableConfig.compareTo = compareToCopy;\r\n        this.diffTableConfig.config = {\r\n          include: this.include as ColumnDefinition[],\r\n          options: this.options as SxyTableOptions,\r\n          data: this.computeDiff()\r\n        };\r\n        this.$timeout(() => {\r\n          this.$sxyTable.refresh();\r\n        });\r\n      }\r\n    }\r\n    return this.diffTableConfig.config;\r\n  }\r\n\r\n  private computeDiff(): DiffItem[] {\r\n    try {\r\n      const changeset = diff(this.json, this.compareTo);\r\n      return atomizeChangeset(changeset)\r\n        .map(item => this.processDiffItem(item))\r\n        .filter(item => item !== null) as DiffItem[];\r\n    } catch (error) {\r\n      console.error(\"Error computing diff:\", error);\r\n      return [];\r\n    }\r\n  }\r\n\r\n  private processDiffItem(item: any): DiffItem | null {\r\n    const { path, type, value, oldValue, valueType } = item;\r\n    const normalizedPath = path.replace(/\\$\\./g, \"\");\r\n    // Skip excluded paths\r\n    if (this.excludePaths?.some(p => normalizedPath.startsWith(p)) || normalizedPath.startsWith(\"$\")) {\r\n      return null;\r\n    }\r\n\r\n    const displayPath = this.getDisplayPath(normalizedPath, value);\r\n    return {\r\n      path: displayPath,\r\n      action: type,\r\n      actionText: Translations.get(`SALAXY.NG1.JsonDiffComponent.actions.${type}`),\r\n      oldValue: oldValue,\r\n      newValue: valueType === \"Object\" ? JSON.stringify(value) : value,\r\n      valueType: valueType\r\n    };\r\n  }\r\n\r\n  private getDisplayPath(normalizedPath: string, value: any): string {\r\n    if (!this.schemaModel) {\r\n      return normalizedPath;\r\n    }\r\n\r\n    const schemaProp = this.getSchemaProperty(normalizedPath);\r\n    if (!schemaProp?.schema) {\r\n      return normalizedPath;\r\n    }\r\n\r\n    // Format display path based on schema type\r\n    if (schemaProp.schema.enum?.length) {\r\n      return `${Translations.get(`SALAXY.ENUM.${schemaProp.schema.format}.${value}.label`)} (${normalizedPath})`;\r\n    }\r\n    return `${Translations.get(`SALAXY.GENERATED_MODEL.${schemaProp.parentName}.${schemaProp.propertyName}.title`)} (${normalizedPath})`;\r\n  }\r\n\r\n  private getSchemaProperty(normalizedPath: string): JsonSchemaProperty | undefined {\r\n    // Handle array paths like \"rows[1].price\"\r\n    if (normalizedPath.includes(\"[\") && normalizedPath.includes(\"]\")) {\r\n      const arrayPropertyName = normalizedPath.replace(/\\[\\d+\\].*$/, \"\");\r\n      const arraySchemaProp = JsonSchemaUtils.getProperty(this.schemaModel, arrayPropertyName);\r\n      if (!arraySchemaProp?.schema || !JsonSchemaUtils.isArraySchemaObject(arraySchemaProp.schema)) {\r\n        return undefined;\r\n      }\r\n\r\n      const remainingPath = normalizedPath.replace(/^[^[]+\\[\\d+\\]\\.?/, \"\");\r\n      if (!remainingPath) {\r\n        return arraySchemaProp;\r\n      }\r\n\r\n      return JsonSchemaUtils.getProperty(\r\n        arraySchemaProp.schema.items as OpenAPIV3.SchemaObject,\r\n        remainingPath\r\n      );\r\n    }\r\n    // Handle regular paths\r\n    return JsonSchemaUtils.getProperty(this.schemaModel, normalizedPath);\r\n  }\r\n\r\n  private createJsonFormatter(cell: any): any {\r\n    const value = cell.getValue();\r\n    if(!value) {\r\n      return value;\r\n    }\r\n    if(this.isValidJsonObject(value)) {\r\n      return `<button class=\"btn btn-sm btn-primary\">Avaa</button>`;\r\n    }\r\n    return value;\r\n  }\r\n\r\n  private handleJsonCellClick(_event: any, cell: any): void {\r\n    const value = cell.getValue();\r\n    if(this.isValidJsonObject(value)) {\r\n      const logic = {data: JSON.parse(value)};\r\n      const template = `\r\n        <div class=\"modal-header\">\r\n          <h2 class=\"modal-title\">JSON</h2>\r\n          <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n        </div>\r\n        <div class=\"modal-body\">\r\n          <salaxy-json-formatter json=\"$ctrl.logic.data\"></salaxy-json-formatter>\r\n        </div>\r\n        <div class=\"modal-footer\">\r\n          <button type=\"button\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n        </div>\r\n        `;\r\n      this.uiHelpers.openEditDialog(null, value, logic, \"lg\", \"EditDialogController\", {template});\r\n    }\r\n  }\r\n\r\n  private isValidJsonObject(value: any): boolean {\r\n    // Check if value exists and is a string\r\n    if (!value || typeof value !== \"string\") {\r\n      return false;\r\n    }\r\n    // Quick check for JSON object pattern\r\n    const trimmed = value.trim();\r\n    if (!trimmed.startsWith(\"{\") || !trimmed.endsWith(\"}\")) {\r\n      return false;\r\n    }\r\n    // Try to parse and validate\r\n    try {\r\n      const parsed = JSON.parse(trimmed);\r\n      return typeof parsed === \"object\" &&\r\n        parsed !== null &&\r\n        !Array.isArray(parsed) &&\r\n        Object.keys(parsed).length > 0; // Ensure it's not an empty object\r\n    } catch {\r\n      return false;\r\n    }\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { SitemapNode, SitemapVisibility, Configs } from \"@salaxy/core\";\r\nimport { NaviService, SessionService, UserSettingsService } from \"../../services\";\r\nimport { SitemapHelper } from \"../../helpers\";\r\nimport { CurrentRoute } from \"../../helpers/CurrentRoute\";\r\n\r\n/**\r\n * Helper controller to generate navigation components and views:\r\n * Top- and side-menus, paths and controls that show the current title.\r\n * These controls take the navigation logic from an object (sitemap) and are aware of current node / open page on that sitemap.\r\n *\r\n * NOTE: This is just an optional helper to make creating simple demo sites easier.\r\n * There is no need to use NaviService, NaviController or components in your custom site!\r\n * You can use something completely different.\r\n */\r\nexport class NaviController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"NaviService\", \"SessionService\", \"UserSettingsService\"];\r\n\r\n  /**\r\n   * Display mode of the sitemap / navi: \"default\", \"accordion\" or \"horizontal\"\r\n   * default: Shows full two levels of the tree. Typically used as sitemap in the content area.\r\n   * accordion: Shows first level of the navi tree and second level only it is in the current path. Typically used in left menu navigation.\r\n   * horizontal: Full navi on top bar. Second tier in dropdowns.\r\n   * 3-levels: Accordion with 3 levels.\r\n   */\r\n  public mode: \"default\" | \"accordion\" | \"horizontal\" | \"3-levels\" = \"default\";\r\n\r\n  /**\r\n   * - layout: \"default\" or \"iframe\"\r\n   * - default: Basic layout with full navigation (left sidebar or horizontal).\r\n   * - iframe: Layout without first tier navigation on left sidebar. Second tier navigation items are under dropdown in top bar / header if mode is default.\r\n   * On horizontal mode full navigation is on top bar.\r\n   */\r\n  public layout: \"default\" | \"iframe\";\r\n\r\n  /**\r\n   * Creates a new NaviController\r\n   * @param naviService - Service that stores the navigation state.\r\n   * @ignore\r\n   */\r\n  constructor(private naviService: NaviService, private sessionService: SessionService, private userSettingsService: UserSettingsService) { }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit = () => {\r\n\r\n    if (this.mode !== \"accordion\" && this.mode !== \"3-levels\" && this.mode !== \"horizontal\") {\r\n      this.mode = \"default\";\r\n    }\r\n\r\n  };\r\n\r\n  /**\r\n   * Contains information about the current sitemap node (if resoved) and other data related to route.\r\n   * This property takes into account that the current node may not be found,\r\n   * i.e. current.node may be null, current.path may be [].\r\n   * However, the \"route\" as an object should never be null.\r\n   * All the other properties in this controller use first node as default for historical reasons.\r\n   */\r\n  public get route(): CurrentRoute {\r\n    return this.naviService.current;\r\n  }\r\n\r\n  /**\r\n   * Returns the main sitemap object that is used in rendering the navigation.\r\n   * Set the sitemap by setting the angular constant or object \"SITEMAP\"\r\n   */\r\n  public get sitemap(): SitemapNode[] {\r\n    return this.naviService.getSitemap();\r\n  }\r\n\r\n  /**\r\n   * If true, the layout should show a full-page loader instead of normal pages.\r\n   * Controllers in normal pages should be destoyed (e.g. using ng-if) so that this can also\r\n   * be used in reloading the AngularJS user interface without full Browser reload.\r\n   */\r\n  public get showFullPageLoader() {\r\n    return this.sessionService.isLoading;\r\n  }\r\n\r\n  /**\r\n   * Gets the user-specific setting (service), stored in the local storage.\r\n   */\r\n  public get userSettings() {\r\n    return this.userSettingsService;\r\n  }\r\n\r\n  /**\r\n   * Temporary visibility helper for the new Payroll 4 version.\r\n   */\r\n  public get newPayrollVersion() {\r\n    const show = true; //always show the new version switch for now\r\n    const result = {\r\n      /** If true, the switch for selecting version 4 is shown to the user. */\r\n      show,\r\n      /** If true the new version is in use. */\r\n      use: show && (this.userSettings.ng1Binder(\"payroll.newVersion\").val ?? true) as boolean,\r\n    };\r\n    if (this.sessionService.session.settings.integration?.serverUrl || this.sessionService.isInRole(\"aidemo\")) {\r\n      // Integration server requires the new version\r\n      result.show = false;\r\n      result.use = true;\r\n    }\r\n    return result;\r\n  }\r\n\r\n\r\n  /** New payroll version use */\r\n  public get newPayrollVersionUse() {\r\n    return this.newPayrollVersion.use;\r\n  }\r\n  /**\r\n   * New payroll version use\r\n   */\r\n  public set newPayrollVersionUse(value: boolean) {\r\n    this.userSettings.ng1Binder(\"payroll.newVersion\").val = value ?? true;\r\n  }\r\n\r\n  /**\r\n   * Returns route for the given path\r\n   * @param path Page URL path for the node.\r\n   * @returns Route for the path.\r\n   */\r\n  public getRoute(path: string = null): CurrentRoute {\r\n    if (!path) {\r\n      return this.route;\r\n    }\r\n    return new CurrentRoute(this.naviService.getNodesByPath(path));\r\n  }\r\n\r\n  /**\r\n   * Retuns the identifier of the currently selected section.\r\n   * If nothing else is selected, it will return the first section, by convention called 'home'.\r\n   */\r\n  public getSectionId() {\r\n    if (!this.naviService.currentSection) {\r\n      return \"home\";\r\n    }\r\n    return this.naviService.currentSection.id;\r\n  }\r\n\r\n  /**\r\n   * Gets the navi URL from a sitemap node.\r\n   * Currently, removes \"*\" at the end if url ends with \"/*\", but may be used for additional logic in the future.\r\n   */\r\n  public getUrl(node: SitemapNode): string {\r\n    if (!node || !node.url) {\r\n      return null;\r\n    }\r\n    if (node.url.endsWith(\"/*\")) {\r\n      return node.url.substr(0, node.url.length - 1);\r\n    }\r\n    return node.url;\r\n  }\r\n\r\n  /** Toggles the isNaviOpen property */\r\n  public toggleNavi() {\r\n    this.naviService.isNaviOpen = !this.naviService.isNaviOpen;\r\n  }\r\n\r\n  /**\r\n   * True if the navigation (e.g. left sidebar) is open.\r\n   * Typically, this property is used only in narrow (mobile) view, otherwise the sidebar is always shown.\r\n   */\r\n  public get isNaviOpen() { return this.naviService.isNaviOpen; }\r\n  public set isNaviOpen(value: boolean) { this.naviService.isNaviOpen = value; }\r\n\r\n  /** Toggles the isSidebarOpen property */\r\n  public toggleSidebar() {\r\n    this.naviService.isSidebarOpen = !this.naviService.isSidebarOpen;\r\n  }\r\n\r\n  /**\r\n   * True if the secondary sidebar (e.g. right sidebar) is open.\r\n   */\r\n  public get isSidebarOpen() { return this.naviService.isSidebarOpen; }\r\n  public set isSidebarOpen(value: boolean) { this.naviService.isSidebarOpen = value; }\r\n\r\n  /**\r\n   * Gets the current section: The first level node in the sitemap\r\n   * @returns Section filtered by the roles.\r\n   */\r\n  public getSection(): SitemapNode {\r\n    return this.naviService.getCurrentSection();\r\n  }\r\n\r\n  /**\r\n   * Returns true if the node should be hidden in the navi.\r\n   * @param node Node to check. If null, the current node is checked (not defaulted to first node).\r\n   */\r\n  public getHidden(node: SitemapNode = null): boolean {\r\n    return SitemapHelper.getVisibility(node || this.route.node, SitemapVisibility.Hidden);\r\n  }\r\n\r\n  /**\r\n   * Gets the visibility:disabled flag for the current node OR any node in the path\r\n   */\r\n  public getDisabled(): boolean {\r\n    return this.route.node?.visibility == SitemapVisibility.Disabled || !!(this.route.path).find((x) => x.visibility == SitemapVisibility.Disabled);\r\n  }\r\n\r\n  /**\r\n   * Returns true if the node has non-hidden children.\r\n   * @param node Node to check\r\n   */\r\n  public hasChildren(node: SitemapNode): boolean {\r\n    return !!node?.children.find((x) => !SitemapHelper.getVisibility(x, SitemapVisibility.Hidden));\r\n  }\r\n\r\n  /**\r\n   * Filters away the hidden nodes from node array.\r\n   * @param nodes Node array.\r\n   */\r\n  public filterHidden(nodes: SitemapNode[]): SitemapNode[] {\r\n    if (!nodes) {\r\n      return [];\r\n    }\r\n    return nodes.filter((x) => !SitemapHelper.getVisibility(x, SitemapVisibility.Hidden));\r\n  }\r\n\r\n  /**\r\n   * Returns true if the given node is the currently selected node.\r\n   */\r\n  public isCurrent(siteMapNode: SitemapNode): boolean {\r\n    return this.naviService.isCurrent(siteMapNode);\r\n  }\r\n\r\n  /**\r\n   * Returns true if the given node is the currently selected node.\r\n   */\r\n  public isCurrentSection(section: SitemapNode): boolean {\r\n    return this.naviService.isCurrentSection(section);\r\n  }\r\n\r\n  /**\r\n   * In test environment, returns true if the sitemap node has role \"test\" and it is visible only because of that role.\r\n   * @param siteMapNode Node in the sitemap.\r\n   */\r\n  public isTest(siteMapNode: SitemapNode): boolean {\r\n    return siteMapNode.visibleTestOnly >= 0;\r\n  }\r\n\r\n  /**\r\n   * Navigate to given path\r\n   * @param path - Path to navigate.\r\n   * @param checkSession - If true, triggers session refresh\r\n   */\r\n  public navigateTo(path: string, checkSession = false) {\r\n    this.naviService.navigateTo(path, checkSession);\r\n  }\r\n\r\n  /** Returns the page / node title */\r\n  public get title() {\r\n    return this.naviService.title || this.naviService.sectionTitle || \"\\xa0\";\r\n  }\r\n\r\n  /** Gets the currently selected node. */\r\n  public get current() {\r\n    return this.naviService.currentNode;\r\n  }\r\n\r\n  /** Current path from root to the current node. */\r\n  public get currentPath(): SitemapNode[] {\r\n    return this.naviService.currentPath;\r\n  }\r\n\r\n  /** Returns true if the current window is in an IFrame */\r\n  public get isInIframe(): boolean {\r\n    try {\r\n      return window.self !== window.top;\r\n    } catch (e) {\r\n      return true;\r\n    }\r\n  }\r\n\r\n  /** Returns current year. Used for example in copyright texts in footers */\r\n  public getCurrentYear(): number {\r\n    return new Date().getFullYear();\r\n  }\r\n\r\n  /**\r\n   * Determines whether to show the KYC (Know Your Customer) information.\r\n   * @returns A boolean value indicating whether to show the KYC information.\r\n   */\r\n  public get showKyc(): boolean {\r\n    return this.sessionService.kycState == \"missing\" || this.sessionService.kycState == \"expired\";\r\n  }\r\n\r\n  /** Returns current application */\r\n  public get applicationId(): string {\r\n    return Configs.current.applicationId;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\nimport { Translations } from \"@salaxy/core\";\r\n\r\n/**\r\n * Controller rendering a Spinner (please wait) user interfaces.\r\n */\r\nexport class SpinnerController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [];\r\n\r\n  /** If true, the spinner is shown full screen. */\r\n  public fullScreen: boolean;\r\n\r\n  /**\r\n   * Heading is the larger text under the spinner.\r\n   * The text is translated.\r\n   * Also, if language dictionaries are not available, SALAXY.UI_Terms.loading and .loginInProgress are\r\n   * resolved to Finnish terms \"Ladataan...\" and \"Kirjaudutaan...\"\r\n   */\r\n  public heading: string;\r\n\r\n  /**\r\n   * Small text - use pre for line breaks.\r\n   * The text is translated.\r\n   */\r\n  public text: string;\r\n\r\n  /**\r\n   * Creates a new SpinnerController\r\n   * @ignore\r\n   */\r\n  constructor() {\r\n    //\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit = () => {\r\n    // initialization\r\n  };\r\n\r\n  /**\r\n   * Gets the header with default Finnish texts for \"SALAXY.UI_Terms.loading\" and \"SALAXY.UI_Terms.loginInProgress\".\r\n   * Other untranslated language terms (starting with \"SALAXY.\") return an empty text. Other texts are printed as is.\r\n   */\r\n  public getHeading() {\r\n    if (!this.heading) {\r\n      return null;\r\n    }\r\n    const knownTerms = {\r\n      \"SALAXY.UI_Terms.loading\": \"Ladataan...\",\r\n      \"SALAXY.UI_Terms.loginInProgress\": \"Kirjaudutaan...\",\r\n    };\r\n    let defaultText = this.heading;\r\n    if (defaultText.startsWith(\"SALAXY.\")) {\r\n      defaultText = knownTerms[this.heading];\r\n    }\r\n    return Translations.getWithDefault(this.heading, defaultText);\r\n  }\r\n\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { TabsController } from \"./TabsController\";\r\n\r\n/**\r\n * Controller for a single tab pane in the tabs control.\r\n */\r\nexport class TabController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$element\"];\r\n\r\n  /** Tabs controller */\r\n  public tabsCtrl: TabsController;\r\n\r\n  /** Selected tab flag. */\r\n  public selected = false;\r\n\r\n  /** Flag to disable tab. */\r\n  public disable = false;\r\n\r\n  /** Unique name/id for the tab. */\r\n  public index: any = null;\r\n\r\n  /** Text heading for the tab */\r\n  public heading: string = null;\r\n\r\n  /** Selection event handler */\r\n  public onSelect: ( args: {\r\n    /** Selection event. */\r\n    $event: angular.IAngularEvent,\r\n  }) => void;\r\n\r\n  /** Heading DOM node for the tab. */\r\n  public headingElement = null;\r\n\r\n  /** Content DOM node for the tab. */\r\n  public contentElement = null;\r\n\r\n  /** Sorting field */\r\n  public sort = 0;\r\n\r\n  /**\r\n   * Creates a new TabController.\r\n   * @ignore\r\n   */\r\n  constructor(private $element) {\r\n    // instantiation\r\n  }\r\n\r\n  /**\r\n   * Change event handler. Re-sets the one-way bound fields.\r\n   * This is needed, because the parent scope cannot detect the changes without the re-set.\r\n   */\r\n  public $onChanges(changes: any) {\r\n    if (changes.disable) {\r\n      this.disable = changes.disable.currentValue;\r\n    }\r\n    if (changes.index) {\r\n      this.index = changes.index.currentValue;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Registers this tab to the tabs controller.\r\n   * Passes the heading DOM element to be displayed in the header.\r\n   */\r\n  public $onInit() {\r\n    this.sort = this.getPosition(this.$element);\r\n    this.headingElement = this.findTranscludeElement(this.$element, \"heading\");\r\n    this.contentElement = this.findTranscludeElement(this.$element, \"content\");\r\n    this.index = this.tabsCtrl.register(this);\r\n  }\r\n\r\n  /**\r\n   * De-registers this tab from the tabs controller.\r\n   */\r\n  public $onDestroy() {\r\n    this.tabsCtrl.deregister(this);\r\n  }\r\n\r\n  /**\r\n   * Tries to find the element with ng-transclude='heading' attribute.\r\n   * @param el - Element to check.\r\n   */\r\n  private findTranscludeElement(el: any, slot): any {\r\n    if (el.attr(\"ng-transclude\") === slot) {\r\n      return el[0];\r\n    }\r\n    const children = el.children();\r\n    for (let i = 0; i < children.length; i++) {\r\n      const found = this.findTranscludeElement(children.eq(i), slot);\r\n      if (found) {\r\n        return found;\r\n      }\r\n    }\r\n    return null;\r\n  }\r\n\r\n  private getPosition(el: any) {\r\n    // find current salaxy-tab\r\n    const salaxyTabNode = this.findParentTag(el, \"salaxy-tab\");\r\n    if (!salaxyTabNode) {\r\n      return 0;\r\n    }\r\n    // find parent salaxy-tabs\r\n    const salaxyTabsNode = this.findParentTag(salaxyTabNode, \"salaxy-tabs\");\r\n    if (!salaxyTabsNode) {\r\n      return 0;\r\n    }\r\n    // find all salaxy-tab nodes under salaxy-tabs\r\n    const salaxyTabNodes = [];\r\n    this.findChildren(salaxyTabsNode, salaxyTabNodes, \"salaxy-tab\");\r\n    // return child index\r\n    for (let i = 0; i < salaxyTabNodes.length; i++) {\r\n      if (salaxyTabNode[0] === salaxyTabNodes[i][0]) {\r\n        return i;\r\n      }\r\n    }\r\n    return 0;\r\n  }\r\n\r\n  private findParentTag(el: any, tagName: string): any {\r\n    if (el[0].tagName.toLowerCase() === tagName) {\r\n      return el;\r\n    }\r\n\r\n    const parent = el.parent();\r\n    if (parent.length === 1) {\r\n      return this.findParentTag(parent, tagName);\r\n    }\r\n    return null;\r\n  }\r\n\r\n  private findChildren(el: any, nodes: any[], tagName: string) {\r\n    if (el[0].tagName.toLowerCase() === tagName) {\r\n      nodes.push(el);\r\n      return;\r\n    }\r\n\r\n    const children = el.children();\r\n    for (let i = 0; i < children.length; i++) {\r\n      this.findChildren(children.eq(i), nodes, tagName);\r\n    }\r\n  }\r\n\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { TabController } from \"./TabController\";\r\n\r\n/**\r\n * Controller for the tabs control.\r\n */\r\nexport class TabsController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [];\r\n\r\n  /** Tabs array. Contains all registered tabs. */\r\n  public tabs: TabController[] = [];\r\n\r\n  public active: string = \"\";\r\n\r\n  /**\r\n   * Creates a new TabsController.\r\n   * @ignore\r\n   */\r\n  constructor() {\r\n    // instantiation\r\n  }\r\n\r\n  /** Set the values and defaults on init */\r\n  public $onInit() {\r\n  }\r\n\r\n  /**\r\n   * Registers a single tab to this controller.\r\n   * @param tab - Tab to register.\r\n   */\r\n  public register(tab: TabController): any {\r\n    this.tabs.push(tab);\r\n    this.setSortOrder(tab);\r\n    this.tabs.sort((t1, t2) => {\r\n      if (t1.sort > t2.sort) {\r\n        return 1;\r\n      }\r\n      if (t1.sort < t2.sort) {\r\n        return -1;\r\n      }\r\n      return 0;\r\n    });\r\n\r\n    const index = this.findIndex(tab);\r\n    if (tab.index == this.active) {\r\n      tab.selected = true;\r\n    }\r\n\r\n    return tab.index || index;\r\n  }\r\n\r\n  /**\r\n   * De-registers a single tab from this controller.\r\n   * @param tab - Tab to de-register.\r\n   */\r\n  public deregister(tab: TabController) {\r\n    const index = this.findIndex(tab);\r\n\r\n    if (this.tabs[index].index === this.active) {\r\n      const newActiveTabIndex = index === (this.tabs.length - 1) ?\r\n        index - 1 : (index + 1) % this.tabs.length;\r\n      this.select(this.tabs[newActiveTabIndex]);\r\n    }\r\n\r\n    this.tabs.splice(index, 1);\r\n  }\r\n\r\n  /**\r\n   * Sets the selected tab as selected.\r\n   * @param selectedTab - Selected tab.\r\n   */\r\n  public select(selectedTab: TabController, evt?: angular.IAngularEvent) {\r\n    if (selectedTab && selectedTab.disable === true) {\r\n      return;\r\n    }\r\n    for (const tab of this.tabs) {\r\n      if (tab.selected && tab !== selectedTab) {\r\n        tab.selected = false;\r\n      }\r\n    }\r\n    if (!selectedTab) {\r\n      return;\r\n    }\r\n    selectedTab.selected = true;\r\n    selectedTab.onSelect({\r\n      $event: evt,\r\n    });\r\n  }\r\n\r\n  private findIndex(tab: any) {\r\n    for (let i = 0; i < this.tabs.length; i++) {\r\n      if (this.tabs[i] === tab) {\r\n        return i;\r\n      }\r\n    }\r\n    return 0;\r\n  }\r\n\r\n  private setSortOrder(newTab: any) {\r\n    // latest wins\r\n    let resort = false;\r\n    for (const tab of this.tabs) {\r\n      if (tab !== newTab && tab.sort === newTab.sort) {\r\n        resort = true;\r\n      }\r\n    }\r\n    if (resort) {\r\n      for (const tab of this.tabs) {\r\n        if (tab !== newTab && tab.sort >= newTab.sort) {\r\n          tab.sort++;\r\n        }\r\n      }\r\n    }\r\n  }\r\n}\r\n","import angular from \"angular\";\r\nimport { Translations } from \"@salaxy/core\";\r\n/**\r\n * Controller for the tab buttons control.\r\n */\r\nexport class TabButtonsController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$location\", \"$timeout\", \"$scope\"];\r\n\r\n  /**\r\n   * Tab Options:\r\n   * - `value`: Unique identifier for the tab.\r\n   * - `label`: The text displayed for the tab in the UI.\r\n   * - `isDefault`: If `true`, this tab will be selected by default.\r\n   * - `hidden`: If `true`, the tab will be hidden based on certain conditions or parameters.\r\n   */\r\n  public options: { value: string, label: string, isDefault?: boolean, hidden?: boolean }[];\r\n  /* Currently active tab */\r\n  public currentTab: string;\r\n  /* Tracks the tabs' id (the context). Makes it possible to tabs have tabs (and have tabs etc...) inside them. */\r\n  public tabsId: string;\r\n  /* Customizable default tab (can be passed from a parent that uses a template with tabs). */\r\n  public defaultTab: string = \"\";\r\n  /* Whether the tab parameter in the url should update on tab change. Note; causes browser reload, so not advicable to use unless a must-have. Angular JS's default routing option causes this, and (for now) can't be changed. */\r\n  public updateTabParam: boolean = false;\r\n  /* Configured default tab to show on page load. */\r\n  public elemDefaultTab: string;\r\n\r\n  /**\r\n   * Creates a new TabButtonsController.\r\n   * @ignore\r\n   */\r\n  constructor(private $location: angular.ILocationService, private $timeout: angular.ITimeoutService, private $scope: angular.IScope) {\r\n  }\r\n\r\n  /** Sets default tab value on component initialization. If default tab is not manually set, defaults to the first tab in the options list. */\r\n  public $onInit() {\r\n    this.elemDefaultTab = this.defaultTab || this.options.find((option) => option.isDefault)?.value || this.options[0].value;\r\n    let chosenTab = this.elemDefaultTab;\r\n\r\n    const paramTab = this.$location.search().tab;\r\n    const tabs = this.options.map((option: any) => option.value);\r\n    if (paramTab && tabs.includes(paramTab)) {\r\n      chosenTab = paramTab;\r\n    }\r\n    this.currentTab = chosenTab;\r\n\r\n    this.showTab(this.currentTab);\r\n\r\n    this.$timeout(() => {\r\n      this.$scope.$emit(\"tabButtonsControllerReady\", { ctrl: this, tabsId: this.tabsId });\r\n    }, 0);\r\n  }\r\n\r\n  /**\r\n   * Shows a tab programmatically.\r\n   * @param tabValue Tab's id text value.\r\n   */\r\n  public showTab(tabValue: string) {\r\n    this.clearSelection();\r\n    this.currentTab = tabValue;\r\n\r\n    const tabContentElement = document.getElementById(`tab-content-${this.tabsId}`);\r\n    if (tabContentElement) {\r\n      const tabPaneElement = tabContentElement.querySelector(`#${tabValue}-tab`);\r\n      if (tabPaneElement) {\r\n        tabPaneElement.classList.add(\"active\");\r\n        tabPaneElement.classList.add(\"show\");\r\n\r\n        if (this.updateTabParam) {\r\n          this.updateUrlTab(tabValue);\r\n        }\r\n      }\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Updates url value of selected tab.\r\n   * @param tabValue Selected tab.\r\n   */\r\n  private updateUrlTab(tabValue) {\r\n    // Either page load or switched to default tab. Value \"null\" removes the tab param altogether.\r\n    if (this.elemDefaultTab == tabValue) {\r\n      tabValue = null;\r\n    }\r\n    this.$location.search(\"tab\", tabValue);\r\n  }\r\n\r\n\r\n  /**\r\n   * Clears previously selected tabs (removes classes).\r\n   */\r\n  private clearSelection() {\r\n    const allTabPanes = document.querySelectorAll(`#tab-content-${this.tabsId} > .tab-pane`);\r\n    allTabPanes.forEach(pane => {\r\n      pane.classList.remove(\"active\");\r\n      pane.classList.remove(\"show\");\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Return the text value for tab button, either a translation or numerical value.\r\n   * @param tabText Tab text value to be returned.\r\n   * @returns Tab button text.\r\n   */\r\n  public getTabText(tabText) {\r\n    if (typeof tabText === \"number\") {\r\n      return tabText;\r\n    } else {\r\n      return Translations.get(tabText);\r\n    }\r\n  }\r\n}","import angular from \"angular\";\r\nimport { Arrays, Translations } from \"@salaxy/core\";\r\nimport {\r\n  UiHelpers,\r\n  UiTranslatorService,\r\n  UiTranslatorDictionaryItem\r\n} from \"../../services\";\r\n\r\n/**\r\n * Tool that allows translate user interfaces.\r\n */\r\nexport class UiTranslatorController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"UiHelpers\", \"$timeout\", \"UiTranslatorService\"];\r\n\r\n  /** User interface mode for the component. */\r\n  public mode: \"table\" | \"fieldset\";\r\n\r\n  /** Array of dictionary items shown in the component (the original unedited values). */\r\n  public allKeyValues: Array<UiTranslatorDictionaryItem> = [];\r\n\r\n  /** Local variable used to store texts that have been edited. */\r\n  public serviceModelTexts: Array<{ fullKey: string, fi?: string, en?: string, sv?: string }> = [];\r\n\r\n  /** Contains boolean values to indicate whether columns should be shown or not. */\r\n  public showCols: UiTranslatorDictionaryItem = {\r\n    fullKey: \"true\",\r\n    fi: \"true\",\r\n    en: \"true\",\r\n    sv: \"true\",\r\n  };\r\n\r\n  /** AngularJS filter for the translator table: rows filtering.  */\r\n  public listFilter: UiTranslatorDictionaryItem = {};\r\n\r\n  /** Show spinner if the data is loading. */\r\n  public isLoading = false;\r\n\r\n  /**\r\n   * Texts from serviceModel that are being edited\r\n   * This is in format { [key: string]: string } where key\r\n   * is a full key starting from the language, e.g. \"fi.SALAXY.NG1_Sitemap.home\"\r\n   * and value is always an indidivual text (never an object).\r\n   */\r\n  public texts: { [key: string]: string };\r\n\r\n  private _filter: string | string[];\r\n\r\n  /**\r\n   * Creates a new UiTranslatorController\r\n   * @ignore\r\n   */\r\n  constructor(private uiHelpers: UiHelpers, private $timeout: angular.ITimeoutService, private uiTranslatorService: UiTranslatorService) {\r\n    // For dependency injection.\r\n  }\r\n\r\n  /** Init */\r\n  public $onInit = () => {\r\n    this.initTranslationTable();\r\n    this.initTexts();\r\n  };\r\n\r\n  /**\r\n   * Beginning of the full key that is used to filtering the dictionary items (allKeyValues filter).\r\n   * The value may be a string, array or comma separated string of values.\r\n   */\r\n  public get filter(): string | string[] {\r\n    return this._filter;\r\n  }\r\n  public set filter(value: string | string[]) {\r\n    this._filter = value;\r\n    this.updateAllKeyValues();\r\n  }\r\n\r\n  /** Updates this.text and keeps reference to parent */\r\n  public updateTexts() {\r\n    angular.copy(this.toTexts(), this.texts);\r\n  }\r\n\r\n  /**\r\n   * Check if key exists in serviceModelTexts for specified language.\r\n   * @param fullkey Dictionary key\r\n   * @param lang Language that is checked.\r\n   * @returns True if the provided key exists\r\n   */\r\n  public checkIfExistsInTexts(fullkey: string, lang: string): boolean {\r\n    return !!this.serviceModelTexts.find(x => x.fullKey === fullkey && lang in x);\r\n  }\r\n\r\n  /**\r\n   * Check if item can be deleted from serviceModelTexts\r\n   * @param fullKey dictionary key\r\n   * @returns True if the item can be deleted.\r\n   */\r\n  public canDeleteFromText(fullKey: string): boolean {\r\n    return !!this.serviceModelTexts.find(x => x.fullKey === fullKey);\r\n  }\r\n\r\n  /**\r\n   * Finds and return item from serviceModelTexts\r\n   * @param fullkey search value\r\n   * @returns serviceModelTexts item\r\n   */\r\n  public getEditableText(fullkey: string): { fullKey: string, fi?: string, en?: string, sv?: string } {\r\n    return this.serviceModelTexts.find(({ fullKey }) => fullKey === fullkey);\r\n  }\r\n\r\n  /**\r\n   * Adds item to serviceModelTexts\r\n   * @param fullKey fullKey to be added\r\n   */\r\n  public addToTexts(fullKey: string, lang: string): void {\r\n    const index = this.serviceModelTexts.findIndex(x => x.fullKey === fullKey);\r\n    if (index > -1) {\r\n      this.serviceModelTexts[index][lang] = \"\";\r\n    } else {\r\n      const obj: any = { fullKey: fullKey };\r\n      obj[lang] = \"\";\r\n      this.serviceModelTexts.push(obj);\r\n    }\r\n    this.updateTexts();\r\n  }\r\n\r\n  /**\r\n   * Remove item from serviceModelTexts\r\n   * @param fullKey fullKey search value\r\n   */\r\n  public removeFromTexts(fullKey: string): void {\r\n    const index = this.serviceModelTexts.findIndex(x => x.fullKey === fullKey);\r\n    this.serviceModelTexts.splice(index, 1);\r\n    this.updateTexts();\r\n  }\r\n\r\n  /**\r\n   * Save current diff to JSON file\r\n   */\r\n  public downloadTexts(): void {\r\n    const diff = this.getDiffDictionary();\r\n    const str = JSON.stringify(diff);\r\n    const bytes = new TextEncoder().encode(str);\r\n    const blob = new Blob([bytes], {\r\n      type: \"application/json;charset=utf-8\"\r\n    });\r\n    this.uiHelpers.downloadFile(blob, \"diff\");\r\n  }\r\n\r\n  private initTranslationTable() {\r\n    this.isLoading = true;\r\n    this.$timeout().then(() => {\r\n      if (this.uiTranslatorService.getDictionary().length < 1) {\r\n        Translations.instance.getBaseDictionary().then(baseDictionary => {\r\n          this.createKeyValues(baseDictionary, \"\");\r\n          this.updateAllKeyValues();\r\n          this.$timeout(); // getBaseDictionary uses fetch() => Need to call timeout to trigger the UI refresh.\r\n          this.isLoading = false;\r\n        });\r\n      } else {\r\n        this.updateAllKeyValues();\r\n        this.isLoading = false;\r\n      }\r\n    });\r\n  }\r\n\r\n  private initTexts() {\r\n    this.serviceModelTexts = this.fromTexts(this.texts);\r\n  }\r\n\r\n  private fromTexts(texts: any) {\r\n    texts = texts || {};\r\n    const arr: Array<{ fullKey: string, fi?: string, en?: string, sv?: string }> = [];\r\n    Object.keys(texts).forEach(key => {\r\n      const lang = key.substr(0, 2);\r\n      const fullKey = key.substring(3);\r\n      // First iteration, arr is empty\r\n      if (!arr.length) {\r\n        const serviceModelTranslation: { fullKey: string, fi?: string, en?: string, sv?: string } = { fullKey: fullKey };\r\n        serviceModelTranslation[lang] = texts[key];\r\n        arr.push(serviceModelTranslation);\r\n      } else {\r\n        // Find index of fullKey\r\n        const index = arr.findIndex(item => item.fullKey === fullKey);\r\n        if (index > -1) {\r\n          // index exists, add texts[key] to object\r\n          arr[index][lang] = texts[key];\r\n        } else {\r\n          // index not found, add new object to array\r\n          const serviceModelTranslation: { fullKey: string, fi?: string, en?: string, sv?: string } = { fullKey: fullKey };\r\n          serviceModelTranslation[lang] = texts[key];\r\n          arr.push(serviceModelTranslation);\r\n        }\r\n      }\r\n    });\r\n    return arr;\r\n  }\r\n\r\n  private toTexts() {\r\n    const obj: { [key: string]: string } = {};\r\n    this.serviceModelTexts.forEach(text => {\r\n      Object.keys(text).forEach(key => {\r\n        if (key !== \"fullKey\") {\r\n          const newFullKey = `${key}.${text.fullKey}`;\r\n          obj[newFullKey] = text[key];\r\n        }\r\n      });\r\n    });\r\n    return obj;\r\n  }\r\n\r\n  private updateAllKeyValues() {\r\n    this.allKeyValues = this.uiTranslatorService.getDictionary();\r\n    const filter = Arrays.assureArray(this.filter);\r\n    if (filter.length) {\r\n      this.allKeyValues = this.allKeyValues.filter(x => filter.find((f) => x.fullKey.startsWith(f)));\r\n    }\r\n  }\r\n\r\n  private createKeyValues(dictionary: any, path: string) {\r\n    Object.keys(dictionary).forEach(key => {\r\n      if (typeof dictionary[key] === \"object\") {\r\n        this.createKeyValues(dictionary[key], `${path}.${key}`);\r\n      } else {\r\n        const fullPath = `${path}.${key}`;\r\n        const fullKey = fullPath.substring(4);\r\n        const lang = fullPath.slice(1, 3);\r\n        const allKeyValues = this.uiTranslatorService.getDictionary();\r\n        const index = allKeyValues.findIndex(item => item.fullKey === fullKey);\r\n        if (index > -1) {\r\n          allKeyValues[index][lang] = dictionary[key];\r\n        } else {\r\n          const splitKeys = fullKey.split(\".\");\r\n          const obj: UiTranslatorDictionaryItem = {\r\n            fullKey,\r\n            shortKey: splitKeys[splitKeys.length - 1],\r\n            fileName: splitKeys[1],\r\n            keyComponent: splitKeys[2],\r\n            keyValue: splitKeys[3]\r\n          };\r\n          obj[lang] = dictionary[key];\r\n          this.uiTranslatorService.addToDictionary(obj);\r\n        }\r\n      }\r\n    });\r\n  }\r\n  private getDiffDictionary() {\r\n    const diffBase = {\r\n      fi: {},\r\n      en: {},\r\n      sv: {}\r\n    };\r\n    this.serviceModelTexts.forEach(item => {\r\n      const subKeys = item.fullKey.split(\".\");\r\n      Object.keys(diffBase).forEach(lang => {\r\n        let currentNode = diffBase[lang];\r\n        for (let i = 0; i < subKeys.length; i++) {\r\n          if (i === subKeys.length - 1) {\r\n            currentNode = currentNode[subKeys[i]] = item[lang];\r\n          } else {\r\n            // Check if subKeys[i] key exists in currentNode\r\n            if (!(subKeys[i] in currentNode)) {\r\n              // Not found, create new key with subKeys[i], assign it to {} and set to currentNode\r\n              currentNode = currentNode[subKeys[i]] = {};\r\n            } else {\r\n              // Found, assign currentNode to currentNode[subKeys[i]]\r\n              currentNode = currentNode[subKeys[i]];\r\n            }\r\n          }\r\n        }\r\n      });\r\n    });\r\n    return diffBase;\r\n  }\r\n}\r\n\r\n","import angular from \"angular\";\r\nimport { ApiCrudObject, ApiListItem, Calculations, DataMappersLogic, Exportable } from \"@salaxy/core\";\r\nimport { ApiCrudObjectController } from \"../bases/ApiCrudObjectController\";\r\nimport { ODataQueryController } from \"../bases\";\r\nimport { FileService, JsonSchemaService } from \"../../services\";\r\n\r\n/**\r\n * Controller that provides export and import for odata tables and API crud objects.\r\n */\r\nexport class ODataActionsController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"FileService\", \"JsonSchemaService\"];\r\n\r\n  /** The API crud object controller. */\r\n  public $crud: ApiCrudObjectController<ApiCrudObject, ApiListItem>;\r\n\r\n  /** Enclosing ODataQueryController */\r\n  public $odata : ODataQueryController;\r\n\r\n  private calculationsUrl = new Calculations(null).getBaseUrl();\r\n\r\n  /**\r\n   * Constructor for Dependency Injection.\r\n   */\r\n  constructor(private fileService: FileService, private jsonSchemaService: JsonSchemaService) {\r\n  }\r\n\r\n  /**\r\n   * Returns Exportable api for the used crud.\r\n   * @returns Exportable api.\r\n   */\r\n  public getExportable(): Exportable<ApiCrudObject> {\r\n    // TODO: Move this to Calculations related controller and remove getExportable() away from here.\r\n    const baseUrl = this.$crud.getApi().getBaseUrl();\r\n    switch (baseUrl) {\r\n      case this.calculationsUrl:\r\n        return {\r\n          getExportMappers: () => DataMappersLogic.getMappers([\"Calculation\", \"CalculationListItem\"]),\r\n          getExportMapper: (id) => DataMappersLogic.getBuiltInMapper(id, this.jsonSchemaService.getCache()),\r\n          exporters: this.fileService.getDefaultExporters(),\r\n          getSingle: (item) => this.$crud.getApi().getSingle(item.id),\r\n          list: (maxCount?, notify?) => this.$odata.exportItems(maxCount ?? 0, notify),\r\n        };\r\n      default:\r\n        return null;\r\n    }\r\n  }\r\n}\r\n","import angular from \"angular\";\r\nimport { ApiValidation, Culture, DataMapper, FileParser, Importable, ImportBatch, InputEnumOption } from \"@salaxy/core\";\r\nimport { EditDialogKnownActions, UiHelpers, WizardService, WizardStep } from \"../../services\";\r\n\r\n/**\r\n * Controller that provides import functionality for any data.\r\n */\r\nexport class ImportController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"UiHelpers\", \"WizardService\", \"$timeout\"];\r\n\r\n  /** The importable api. */\r\n  private _api: Importable<any>;\r\n\r\n  /** Locale for reading the raw data (CSV delimiter, numbers and dates). */\r\n  public localeId: Culture = Culture.Fi;\r\n\r\n  /** Available file parsers for import. */\r\n  public fileParsers: FileParser[];\r\n\r\n  /** Currently selected file parser.  */\r\n  public currentFileParser: FileParser;\r\n\r\n  /** Current mapper that is used to import the data */\r\n  public mapper: DataMapper<any, any> = null;\r\n\r\n  /** Wizard steps */\r\n  public importSteps: WizardStep[] = [\r\n    {\r\n      title: \"Liitä / lataa taulukko\",\r\n      view: \"salaxy-components/modals/import/ImportStep1.html\",\r\n    },\r\n    {\r\n      title: \"Asetukset\",\r\n      view: \"salaxy-components/modals/import/ImportStep2.html\",\r\n    },\r\n    {\r\n      title: \"Validointi\",\r\n      view: \"salaxy-components/modals/import/ImportStep3.html\",\r\n    },\r\n    {\r\n      title: \"Tallennus\",\r\n      view: \"salaxy-components/modals/import/ImportStep4.html\",\r\n    },\r\n  ];\r\n\r\n  /** Raw data to import. */\r\n  public batch: ImportBatch<any> = null;\r\n\r\n  /** Progress indicator from 0 to 100 where 0 is not in progress. */\r\n  public progress = 0;\r\n\r\n  /**\r\n   * Status messages from asynchronous process (import / validation to server).\r\n   * Only shown if isInProgress = true;\r\n   */\r\n  public progressMessage: string = null;\r\n\r\n  /** Results (errors and warnings) from the last run (import validation etc.). */\r\n  public lastResult: ApiValidation = null;\r\n\r\n  /** All object mappers. */\r\n  private _objectMappers: InputEnumOption[] = null;\r\n\r\n  /**\r\n   * Constructor for Dependency Injection.\r\n   * @param uiHelpers Salaxy ui helpers.\r\n   * @param wizardService Wizard service.\r\n   */\r\n  constructor(private uiHelpers: UiHelpers, private wizardService: WizardService, private $timeout: angular.ITimeoutService) {\r\n\r\n  }\r\n\r\n  /** Gets or sets the Importable api that defines how the data is imported. */\r\n  public get api():Importable<any> {\r\n    return this._api;\r\n  }\r\n  public set api(value: Importable<any>) {\r\n    this._api = value;\r\n    this.createBatch();\r\n  }\r\n\r\n  /** Available object mappers for export */\r\n  public get objectMappers(): InputEnumOption[] {\r\n    if (!this._objectMappers) {\r\n        this._objectMappers = this.api.getImportMappers();\r\n        if (this._objectMappers?.length == 1) {\r\n          this.setMapper(this._objectMappers[0].value);\r\n        }\r\n    }\r\n    return this._objectMappers;\r\n  }\r\n\r\n  /** Clears the last validation result. */\r\n  public clearLastResult() {\r\n    if (this.batch) {\r\n      this.batch.clearValidation();\r\n    }\r\n    this.lastResult = null;\r\n  }\r\n\r\n  /**\r\n   * Shows import dialog.\r\n   * @param api Optional API implementing Importable that is set to the controller.\r\n   * The API must be set to the controller as property or in this parameter or showImport() will fail\r\n   */\r\n  public showImport(api: Importable<any> = null): void {\r\n    if (api) {\r\n      this.api = api;\r\n    }\r\n    if (!this.api) {\r\n      throw new Error(\"Importable API not specified in showImport()\");\r\n    }\r\n    this.wizardService.setSteps(this.importSteps);\r\n    this.wizardService.activeStepNumber = 1;\r\n\r\n    const dialogData = {\r\n      $parent: this,\r\n    };\r\n    this.uiHelpers.showDialog(\r\n      \"salaxy-components/modals/import/Import.html\",\r\n      \"WizardController\",\r\n      dialogData,\r\n      null,\r\n      \"lg\").then( () => {\r\n        // Resolve promise here if needed in future versions.\r\n      });\r\n  }\r\n\r\n  /** Paste data from clipboard. */\r\n  public pasteFromClipboard(): Promise<string> {\r\n    this.createBatch();\r\n    return (navigator as any).clipboard.readText().then((text) => {\r\n      this.batch.rawData = text;\r\n      // Ensure refresh in UI\r\n      return this.$timeout(() => {\r\n        return text;\r\n      });\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Reads the file\r\n   * @param file Selected file\r\n   */\r\n  public readFile(file: File): Promise<string> {\r\n    if (!file) {\r\n      return Promise.resolve(null);\r\n    }\r\n    // TODO detect if excel file and read content using Excel reader.\r\n    if (file.name) {\r\n      if (file.name.toLowerCase().match(/\\.xl(s|sx)$/g)) {\r\n        this.uiHelpers.showAlert(\"Tiedoston muotoa ei tueta\", \"Excel-tiedostot eivät ole vielä tuettuja. Käytä csv tai tab -muotoa.\");\r\n        return Promise.resolve(null);\r\n      }\r\n    }\r\n\r\n    const read = new Promise<string>((resolve, reject) => {\r\n      const reader = new FileReader();\r\n      reader.onloadend = () => {\r\n        resolve(reader.result as string);\r\n      };\r\n      reader.onerror = () => reject;\r\n      reader.readAsText(file);\r\n    });\r\n\r\n    this.createBatch();\r\n\r\n    return read.then((text) => {\r\n      this.batch.rawData = text;\r\n      // Ensure refresh in UI\r\n      return this.$timeout(() => {\r\n        return text;\r\n      });\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Creates / resets the import batch as new using the current api\r\n   * (should be selected before) and mapper (may be null / not yet selected).\r\n   */\r\n  public createBatch(): void {\r\n    this.batch = new ImportBatch(this.mapper, this.api);\r\n    this.fileParsers = this.api.parsers ?? [];\r\n    this.currentFileParser = null;\r\n  }\r\n\r\n  /**\r\n   * Read batch raw data.\r\n   * @returns The status of the read as API validation object (also saved to lastResult).\r\n   */\r\n  public readBatch(): ApiValidation {\r\n    if (!this.currentFileParser) {\r\n      const parserGuess = FileParser.guessParser(this.fileParsers, this.batch.rawData);\r\n      if (parserGuess) {\r\n        this.currentFileParser = parserGuess.parser;\r\n        this.localeId = parserGuess.locale;\r\n      } else {\r\n        return;\r\n      }\r\n    }\r\n    this.lastResult = this.batch.read(null, this.currentFileParser, this.localeId);\r\n    return this.lastResult;\r\n  }\r\n\r\n  /**\r\n   * Sets the import mapper by ID.\r\n   * @param id Identifier of the new object mapper.\r\n   * @returns The mapper once it has been loaded / resolved.\r\n   */\r\n  public setMapper(id: string): Promise<DataMapper<any, any>> {\r\n    return this.api.getImportMapper(id).then((mapper) => {\r\n      this.mapper = mapper;\r\n      this.batch.setMapper(mapper);\r\n      this.readBatch();\r\n      this.$timeout();\r\n      return mapper;\r\n    });\r\n  }\r\n\r\n  /** Read batch data */\r\n  public mapBatch() {\r\n    this.batch.map();\r\n  }\r\n\r\n  /** Validate batch data */\r\n  public validateBatch() {\r\n    this.setProgress(1, \"Tarkistetaan...\");\r\n    // eslint-disable-next-line @typescript-eslint/no-unused-vars\r\n    const notify = (message, index, count, result) => {\r\n      this.setProgress(index + 1, \"Tarkistetaan...\", count);\r\n    };\r\n    this.batch.validate(notify).then(() => {\r\n      this.setProgress(0);\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Imports the batch data.\r\n   * @param $close Close function of the UI Bootstrap dialog.\r\n   */\r\n  public importBatch($close: (action: EditDialogKnownActions) => void): void {\r\n    this.setProgress(1, \"Tallennetaan... \");\r\n    // eslint-disable-next-line @typescript-eslint/no-unused-vars\r\n    const notify = (message, index, count, result) => {\r\n      this.setProgress(index + 1, \"Tallennetaan...\", count);\r\n    };\r\n    this.lastResult = null;\r\n    this.batch.import(notify).then((result) => {\r\n      this.setProgress(0);\r\n      this.lastResult = result;\r\n      if (!result.errors?.length) {\r\n        $close(EditDialogKnownActions.Ok);\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Sets the progress indicator\r\n   * @param value Value of the progress 0-100. If the process is just starting, use 1.\r\n   * If not in progress, use 0. If the count is null, you may also use absolute value (index+1) here:\r\n   * The system will convert it to 1-100 first assuming there is 10 items, then that there is 100 items.\r\n   * @param message Progress message\r\n   * @param count Total count of items if known.\r\n   */\r\n  private setProgress(value: number, message: string = null, count: number = null) {\r\n    if (!value) {\r\n      this.progress = 0;\r\n      this.progressMessage = null;\r\n      return;\r\n    }\r\n    if (count) {\r\n      this.progress = value / count * 100;\r\n    } else {\r\n      if (value < 10) {\r\n        this.progress = value * 10; // First assume 10 items\r\n      } else if (value < 100) {\r\n        this.progress = value;\r\n      } else if (value < 1000) {\r\n        this.progress = value / 10;\r\n      } else {\r\n        this.progress = 90;\r\n      }\r\n    }\r\n    if (this.progress > 100) {\r\n      this.progress = 100;\r\n    }\r\n    if (this.progress < 1) {\r\n      this.progress = 1;\r\n    }\r\n    this.progressMessage = message ? message + \" \" : \"\";\r\n    if (value != 1 && value != 100) {\r\n      this.progressMessage += `(${value}${count ? \"/\" + count : \"\"})`;\r\n    }\r\n  }\r\n\r\n  /** Toggles the debug view on/off. */\r\n  public toggleDebug() {\r\n    const isDebug = !(this as any).isDebug;\r\n    (this as any).isDebug = isDebug;\r\n    const dialog = document.getElementById(\"salaxyDialog\");\r\n    if (dialog) {\r\n      if (isDebug) {\r\n        dialog.style.width = \"98vw\";\r\n      } else {\r\n        dialog.style.width = null;\r\n      }\r\n    }\r\n  }\r\n}\r\n","import angular from \"angular\";\r\nimport { Culture, DataMapper, DataMapperInfo, Exportable, FileExporter, ExportLogic, InputEnumOption, Translations } from \"@salaxy/core\";\r\nimport { AlertService, UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Controller that provides export functionality for any data.\r\n */\r\nexport class ExportController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"AlertService\", \"UiHelpers\"];\r\n\r\n  /**\r\n   * Maximum length of the data export.\r\n   * Because of the implementation of the enum input, the value is number as a string.\r\n   * -1 has a special meaning as the items that have already been loaded to the preview.\r\n   */\r\n  public maxCount = \"0\";\r\n\r\n  /** Values available in the  */\r\n  public maxCountOptions: InputEnumOption[] = [\r\n    {\r\n      value: \"0\",\r\n      text: Translations.get(\"SALAXY.NG1.ExportComponent.exportLengths.all\"),\r\n    },\r\n    {\r\n      value: \"-1\",\r\n      text: Translations.get(\"SALAXY.NG1.ExportComponent.exportLengths.current\"),\r\n    },\r\n    {\r\n      value: \"1000\",\r\n      text: Translations.get(\"SALAXY.NG1.ExportComponent.exportLengths.short\"),\r\n    },\r\n    {\r\n      value: \"10000\",\r\n      text: Translations.get(\"SALAXY.NG1.ExportComponent.exportLengths.long\"),\r\n    },\r\n  ];\r\n\r\n  /** Locale for exports */\r\n  public localeId: Culture = Culture.Fi;\r\n\r\n  /** Exporters supported by the current API. */\r\n  public exporters: FileExporter[];\r\n\r\n  /** Currently selected exporter. */\r\n  public currentExporter: FileExporter;\r\n\r\n  /** Current mapper once loaded. */\r\n  public mapper: DataMapper<any, any> = null;\r\n\r\n  /** Flag for export in progress: Shows a small spinner in the export button (wizard). */\r\n  public isExporting = false;\r\n\r\n  /** Messages from exports shown in the UI. */\r\n  public exportMessage: string = null;\r\n\r\n  /** All mappers defined by the current Exportable API. */\r\n  public allMappers: DataMapperInfo[] = null;\r\n\r\n  /** Available list item mappers for export */\r\n  public listItemMappers: DataMapperInfo[] = null;\r\n\r\n  /** Available object mappers for export */\r\n  public objectMappers: DataMapperInfo[] = null;\r\n\r\n  private _api: Exportable<any>;\r\n\r\n  constructor(private alertService: AlertService, private uiHelpers: UiHelpers) {\r\n\r\n  }\r\n\r\n  /** Gets or sets the API that implements the Exportable interface. */\r\n  public get api():Exportable<any> {\r\n    return this._api;\r\n  }\r\n  public set api(value: Exportable<any>) {\r\n    this._api = value;\r\n    this.exporters = this.api.exporters ?? [];\r\n    this.currentExporter = this.exporters[0];\r\n    this.allMappers = this.api.getExportMappers();\r\n    this.listItemMappers = this.api.getExportMappers().filter(x => (x.sourceSchema || \"\").indexOf(\"ListItem\") > 0);\r\n    this.objectMappers = this.api.getExportMappers().filter(x => (x.sourceSchema || \"\").indexOf(\"ListItem\") < 0);\r\n  }\r\n\r\n  /**\r\n   * Shows an export dialog for full export.\r\n   * @param api Optional API implementing Exportable that is set to the controller.\r\n   * The API must be set to the controller as property or in this parameter or showExport() will fail\r\n   */\r\n  public showExport(api: Exportable<any>) {\r\n    this.api = api || this.api;\r\n    if (!this.api) {\r\n      throw new Error(\"Exportable API not specified in showExport()\");\r\n    }\r\n    this.currentExporter = this.exporters[0];\r\n    const loader = this.uiHelpers.showLoading();\r\n    this.api.getExportMapper((this.listItemMappers[0] || this.allMappers[0]).uri).then((mapper) => {\r\n      this.mapper = mapper;\r\n      const dialogData = {\r\n        $parent: this,\r\n      };\r\n      loader.dismiss();\r\n      this.uiHelpers.showDialog(\"salaxy-components/modals/export/Export.html\", null, dialogData, null, \"lg\");\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Executes an immediate quick export - typically directly from a view.\r\n   * Shows the Loader while data is being loaded for the export.\r\n   * @param exporterId Exporter ID. If null, the first exporter in API is used.\r\n   * @param api Optional API implementing Exportable that is set to the controller.\r\n   * The API must be set to the controller as property or in this parameter or quickExport() will fail\r\n   * @param mapper Optional mapper to use in the export. This may be the full DataMapperInfo object or just its uri.\r\n   * If null and mapper has already been set, keeps the current mapper,\r\n   * If null and current mapper is null, sets the first available list mapper, then any mapper. No mappers fails.\r\n   */\r\n  public quickExport(exporterId: string, api: Exportable<any>, mapper: DataMapperInfo | string = null): Promise<void> {\r\n    this.api = api || this.api;\r\n    if (!this.api) {\r\n      throw new Error(\"Exportable API not specified in quickExport()\");\r\n    }\r\n    const loader = this.uiHelpers.showLoading();\r\n    return this.export(mapper, exporterId).then(() => {\r\n      loader.dismiss();\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Exports data to desired format.\r\n   * @param mapper The mapper to use in the export. This may be the full DataMapperInfo object or just its uri.\r\n   * If null and mapper has already been set, keeps the current mapper,\r\n   * If null and current mapper is null, sets the first available list mapper, then any mapper. No mappers fails.\r\n   * @param exporterId Identifies the exporter defining the file type and how the result is presented (copy-paste, download, send to external...).\r\n   * If no exporter is selected for the controller, the first exporter in API is used.\r\n   */\r\n  public export(mapper: DataMapperInfo | string = null, exporterId: string = null): Promise<void> {\r\n    if (exporterId) {\r\n      this.currentExporter = this.exporters.find((x) => x.id == exporterId);\r\n    }\r\n    this.currentExporter = this.currentExporter || this.api.exporters[0];\r\n    return this.setExportMapper(mapper).then(() => {\r\n      this.isExporting = true;\r\n      this.exportMessage = Translations.get(\"SALAXY.NG1.ExportComponent.export.creating\");\r\n      const notify = (message, index, count) => {\r\n        this.exportMessage = `${message} (${index + 1}${count ? \"/\" + count : \"\"})`;\r\n      };\r\n      return ExportLogic.getExportData(this.api, this.mapper, Number(this.maxCount), notify).then((rows) => {\r\n        this.isExporting = false;\r\n        this.exportMessage = null;\r\n        if (!rows || !rows.length) {\r\n          this.alertService.addError(Translations.get(\"SALAXY.NG1.ExportComponent.export.noRows\"));\r\n          return;\r\n        }\r\n        this.currentExporter.export(rows, this.localeId);\r\n      });\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Loads the mapper definition and sets the current mapper to it.\r\n   * @param newMapper New mapper to load and set as current: DataMapperInfo or its uri.\r\n   * If null and mapper has already been set, keeps the current mapper,\r\n   * If null and current mapper is null, sets the first available list mapper, then any mapper. No mappers fails.\r\n   */\r\n  public setExportMapper(newMapper: DataMapperInfo | string): Promise<DataMapper<any, any>> {\r\n    let uri = (newMapper as DataMapperInfo)?.uri || newMapper as string;\r\n    if (!uri) {\r\n      if (this.mapper) {\r\n        return Promise.resolve(this.mapper);\r\n      } else {\r\n        uri = (this.listItemMappers[0] || this.allMappers[0]).uri;\r\n      }\r\n    }\r\n    if (this.mapper?.uri == uri) {\r\n      return Promise.resolve(this.mapper);\r\n    }\r\n    this.mapper = null;\r\n    return this.api.getExportMapper(uri).then((mapper) => {\r\n      this.mapper = mapper;\r\n      return mapper;\r\n    });\r\n  }\r\n\r\n  /** Toggles the debug view on/off. */\r\n  public toggleDebug() {\r\n    const isDebug = !(this as any).isDebug;\r\n    (this as any).isDebug = isDebug;\r\n    const dialog = document.getElementById(\"salaxyDialog\");\r\n    if (dialog) {\r\n      if (isDebug) {\r\n        dialog.style.width = \"98vw\";\r\n      } else {\r\n        dialog.style.width = null;\r\n      }\r\n    }\r\n  }\r\n}\r\n","/* Tabulator v5.6.1 (c) Oliver Folkerd 2024 */\nclass CoreFeature{\n\n\tconstructor(table){\n\t\tthis.table = table;\n\t}\n\n\t//////////////////////////////////////////\n\t/////////////// DataLoad /////////////////\n\t//////////////////////////////////////////\n\n\treloadData(data, silent, columnsChanged){\n\t\treturn this.table.dataLoader.load(data, undefined, undefined, undefined, silent, columnsChanged);\n\t}\n\n\t//////////////////////////////////////////\n\t///////////// Localization ///////////////\n\t//////////////////////////////////////////\n\n\tlangText(){\n\t\treturn this.table.modules.localize.getText(...arguments);\n\t}\n\n\tlangBind(){\n\t\treturn this.table.modules.localize.bind(...arguments);\n\t}\n\n\tlangLocale(){\n\t\treturn this.table.modules.localize.getLocale(...arguments);\n\t}\n\n\n\t//////////////////////////////////////////\n\t////////// Inter Table Comms /////////////\n\t//////////////////////////////////////////\n\n\tcommsConnections(){\n\t\treturn this.table.modules.comms.getConnections(...arguments);\n\t}\n\n\tcommsSend(){\n\t\treturn this.table.modules.comms.send(...arguments);\n\t}\n\n\t//////////////////////////////////////////\n\t//////////////// Layout  /////////////////\n\t//////////////////////////////////////////\n\n\tlayoutMode(){\n\t\treturn this.table.modules.layout.getMode();\n\t}\n\n\tlayoutRefresh(force){\n\t\treturn this.table.modules.layout.layout(force);\n\t}\n\n\n\t//////////////////////////////////////////\n\t/////////////// Event Bus ////////////////\n\t//////////////////////////////////////////\n\n\tsubscribe(){\n\t\treturn this.table.eventBus.subscribe(...arguments);\n\t}\n\n\tunsubscribe(){\n\t\treturn this.table.eventBus.unsubscribe(...arguments);\n\t}\n\n\tsubscribed(key){\n\t\treturn this.table.eventBus.subscribed(key);\n\t}\n\n\tsubscriptionChange(){\n\t\treturn this.table.eventBus.subscriptionChange(...arguments);\n\t}\n\n\tdispatch(){\n\t\treturn this.table.eventBus.dispatch(...arguments);\n\t}\n\n\tchain(){\n\t\treturn this.table.eventBus.chain(...arguments);\n\t}\n\n\tconfirm(){\n\t\treturn this.table.eventBus.confirm(...arguments);\n\t}\n\n\tdispatchExternal(){\n\t\treturn this.table.externalEvents.dispatch(...arguments);\n\t}\n\n\tsubscribedExternal(key){\n\t\treturn this.table.externalEvents.subscribed(key);\n\t}\n\n\tsubscriptionChangeExternal(){\n\t\treturn this.table.externalEvents.subscriptionChange(...arguments);\n\t}\n\n\t//////////////////////////////////////////\n\t//////////////// Options /////////////////\n\t//////////////////////////////////////////\n\n\toptions(key){\n\t\treturn this.table.options[key];\n\t}\n\n\tsetOption(key, value){\n\t\tif(typeof value !== \"undefined\"){\n\t\t\tthis.table.options[key] = value;\n\t\t}\n\n\t\treturn this.table.options[key];\n\t}\n\n\t//////////////////////////////////////////\n\t/////////// Deprecation Checks ///////////\n\t//////////////////////////////////////////\n\n\tdeprecationCheck(oldOption, newOption,  convert){\n\t\treturn this.table.deprecationAdvisor.check(oldOption, newOption,  convert);\n\t}\n\n\tdeprecationCheckMsg(oldOption, msg){\n\t\treturn this.table.deprecationAdvisor.checkMsg(oldOption, msg);\n\t}\n\n\tdeprecationMsg(msg){\n\t\treturn this.table.deprecationAdvisor.msg(msg);\n\t}\n\t//////////////////////////////////////////\n\t//////////////// Modules /////////////////\n\t//////////////////////////////////////////\n\n\tmodule(key){\n\t\treturn this.table.module(key);\n\t}\n}\n\nclass Helpers{\n\n\tstatic elVisible(el){\n\t\treturn !(el.offsetWidth <= 0 && el.offsetHeight <= 0);\n\t}\n\n\tstatic elOffset(el){\n\t\tvar box = el.getBoundingClientRect();\n\n\t\treturn {\n\t\t\ttop: box.top + window.pageYOffset - document.documentElement.clientTop,\n\t\t\tleft: box.left + window.pageXOffset - document.documentElement.clientLeft\n\t\t};\n\t}\n\n\tstatic retrieveNestedData(separator, field, data){\n\t\tvar structure = separator ? field.split(separator) : [field],\n\t\tlength = structure.length,\n\t\toutput;\n\n\t\tfor(let i = 0; i < length; i++){\n\n\t\t\tdata = data[structure[i]];\n\n\t\t\toutput = data;\n\n\t\t\tif(!data){\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\n\t\treturn output;\n\t}\n\n\tstatic deepClone(obj, clone, list = []){\n\t\tvar objectProto = {}.__proto__,\n\t\tarrayProto = [].__proto__;\n\n\t\tif (!clone){\n\t\t\tclone = Object.assign(Array.isArray(obj) ? [] : {}, obj);\n\t\t}\n\n\t\tfor(var i in obj) {\n\t\t\tlet subject = obj[i],\n\t\t\tmatch, copy;\n\n\t\t\tif(subject != null && typeof subject === \"object\" && (subject.__proto__ === objectProto || subject.__proto__ === arrayProto)){\n\t\t\t\tmatch = list.findIndex((item) => {\n\t\t\t\t\treturn item.subject === subject;\n\t\t\t\t});\n\n\t\t\t\tif(match > -1){\n\t\t\t\t\tclone[i] = list[match].copy;\n\t\t\t\t}else {\n\t\t\t\t\tcopy = Object.assign(Array.isArray(subject) ? [] : {}, subject);\n\n\t\t\t\t\tlist.unshift({subject, copy});\n\n\t\t\t\t\tclone[i] = this.deepClone(subject, copy, list);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn clone;\n\t}\n}\n\nclass Popup extends CoreFeature{\n\tconstructor(table, element, parent){\n\t\tsuper(table);\n\t\t\n\t\tthis.element = element;\n\t\tthis.container = this._lookupContainer();\n\t\t\n\t\tthis.parent = parent;\n\t\t\n\t\tthis.reversedX = false;\n\t\tthis.childPopup = null;\n\t\tthis.blurable = false;\n\t\tthis.blurCallback = null;\n\t\tthis.blurEventsBound = false;\n\t\tthis.renderedCallback = null;\n\t\t\n\t\tthis.visible = false;\n\t\tthis.hideable = true;\n\t\t\n\t\tthis.element.classList.add(\"tabulator-popup-container\");\n\t\t\n\t\tthis.blurEvent = this.hide.bind(this, false);\n\t\tthis.escEvent = this._escapeCheck.bind(this);\n\t\t\n\t\tthis.destroyBinding = this.tableDestroyed.bind(this);\n\t\tthis.destroyed = false;\n\t}\n\t\n\ttableDestroyed(){\n\t\tthis.destroyed = true;\n\t\tthis.hide(true);\n\t}\n\t\n\t_lookupContainer(){\n\t\tvar container = this.table.options.popupContainer;\n\t\t\n\t\tif(typeof container === \"string\"){\n\t\t\tcontainer = document.querySelector(container);\n\t\t\t\n\t\t\tif(!container){\n\t\t\t\tconsole.warn(\"Menu Error - no container element found matching selector:\",  this.table.options.popupContainer , \"(defaulting to document body)\");\n\t\t\t}\n\t\t}else if (container === true){\n\t\t\tcontainer = this.table.element;\n\t\t}\n\t\t\n\t\tif(container && !this._checkContainerIsParent(container)){\n\t\t\tcontainer = false;\n\t\t\tconsole.warn(\"Menu Error - container element does not contain this table:\",  this.table.options.popupContainer , \"(defaulting to document body)\");\n\t\t}\n\t\t\n\t\tif(!container){\n\t\t\tcontainer = document.body;\n\t\t}\n\t\t\n\t\treturn container;\n\t}\n\t\n\t_checkContainerIsParent(container, element = this.table.element){\n\t\tif(container === element){\n\t\t\treturn true;\n\t\t}else {\n\t\t\treturn element.parentNode ? this._checkContainerIsParent(container, element.parentNode) : false;\n\t\t}\n\t}\n\t\n\trenderCallback(callback){\n\t\tthis.renderedCallback = callback;\n\t}\n\t\n\tcontainerEventCoords(e){\n\t\tvar touch = !(e instanceof MouseEvent);\n\t\t\n\t\tvar x = touch ? e.touches[0].pageX : e.pageX;\n\t\tvar y = touch ? e.touches[0].pageY : e.pageY;\n\t\t\n\t\tif(this.container !== document.body){\n\t\t\tlet parentOffset = Helpers.elOffset(this.container);\n\t\t\t\n\t\t\tx -= parentOffset.left;\n\t\t\ty -= parentOffset.top;\n\t\t}\n\t\t\n\t\treturn {x, y};\n\t}\n\t\n\telementPositionCoords(element, position = \"right\"){\n\t\tvar offset = Helpers.elOffset(element),\n\t\tcontainerOffset, x, y;\n\t\t\n\t\tif(this.container !== document.body){\n\t\t\tcontainerOffset = Helpers.elOffset(this.container);\n\t\t\t\n\t\t\toffset.left -= containerOffset.left;\n\t\t\toffset.top -= containerOffset.top;\n\t\t}\n\t\t\n\t\tswitch(position){\n\t\t\tcase \"right\":\n\t\t\t\tx = offset.left + element.offsetWidth;\n\t\t\t\ty = offset.top - 1;\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase \"bottom\":\n\t\t\t\tx = offset.left;\n\t\t\t\ty = offset.top + element.offsetHeight;\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase \"left\":\n\t\t\t\tx = offset.left;\n\t\t\t\ty = offset.top - 1;\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase \"top\":\n\t\t\t\tx = offset.left;\n\t\t\t\ty = offset.top;\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase \"center\":\n\t\t\t\tx = offset.left + (element.offsetWidth / 2);\n\t\t\t\ty = offset.top + (element.offsetHeight / 2);\n\t\t\t\tbreak;\n\t\t\t\n\t\t}\n\t\t\n\t\treturn {x, y, offset};\n\t}\n\t\n\tshow(origin, position){\n\t\tvar x, y, parentEl, parentOffset, coords;\n\t\t\n\t\tif(this.destroyed || this.table.destroyed){\n\t\t\treturn this;\n\t\t}\n\t\t\n\t\tif(origin instanceof HTMLElement){\n\t\t\tparentEl = origin;\n\t\t\tcoords = this.elementPositionCoords(origin, position);\n\t\t\t\n\t\t\tparentOffset = coords.offset;\n\t\t\tx = coords.x;\n\t\t\ty = coords.y;\n\t\t\t\n\t\t}else if(typeof origin === \"number\"){\n\t\t\tparentOffset = {top:0, left:0};\n\t\t\tx = origin;\n\t\t\ty = position;\n\t\t}else {\n\t\t\tcoords = this.containerEventCoords(origin);\n\t\t\t\n\t\t\tx = coords.x;\n\t\t\ty = coords.y;\n\t\t\t\n\t\t\tthis.reversedX = false;\n\t\t}\n\t\t\n\t\tthis.element.style.top = y + \"px\";\n\t\tthis.element.style.left = x + \"px\";\n\t\t\n\t\tthis.container.appendChild(this.element);\n\t\t\n\t\tif(typeof this.renderedCallback === \"function\"){\n\t\t\tthis.renderedCallback();\n\t\t}\n\t\t\n\t\tthis._fitToScreen(x, y, parentEl, parentOffset, position);\n\t\t\n\t\tthis.visible = true;\n\t\t\n\t\tthis.subscribe(\"table-destroy\", this.destroyBinding);\n\t\t\n\t\tthis.element.addEventListener(\"mousedown\", (e) => {\n\t\t\te.stopPropagation();\n\t\t});\n\t\t\n\t\treturn this;\n\t}\n\t\n\t_fitToScreen(x, y, parentEl, parentOffset, position){\n\t\tvar scrollTop = this.container === document.body ? document.documentElement.scrollTop : this.container.scrollTop;\n\t\t\n\t\t//move menu to start on right edge if it is too close to the edge of the screen\n\t\tif((x + this.element.offsetWidth) >= this.container.offsetWidth || this.reversedX){\n\t\t\tthis.element.style.left = \"\";\n\t\t\t\n\t\t\tif(parentEl){\n\t\t\t\tthis.element.style.right = (this.container.offsetWidth - parentOffset.left) + \"px\";\n\t\t\t}else {\n\t\t\t\tthis.element.style.right = (this.container.offsetWidth - x) + \"px\";\n\t\t\t}\n\t\t\t\n\t\t\tthis.reversedX = true;\n\t\t}\n\t\t\n\t\t//move menu to start on bottom edge if it is too close to the edge of the screen\n\t\tif((y + this.element.offsetHeight) > Math.max(this.container.offsetHeight, scrollTop ? this.container.scrollHeight : 0)) {\n\t\t\tif(parentEl){\n\t\t\t\tswitch(position){\n\t\t\t\t\tcase \"bottom\":\n\t\t\t\t\t\tthis.element.style.top = (parseInt(this.element.style.top) - this.element.offsetHeight - parentEl.offsetHeight - 1) + \"px\";\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t\n\t\t\t\t\tdefault:\n\t\t\t\t\t\tthis.element.style.top = (parseInt(this.element.style.top) - this.element.offsetHeight + parentEl.offsetHeight + 1) + \"px\";\n\t\t\t\t}\n\t\t\t\t\n\t\t\t}else {\n\t\t\t\tthis.element.style.top = (parseInt(this.element.style.top) - this.element.offsetHeight) + \"px\";\n\t\t\t}\n\t\t}\n\t}\n\t\n\tisVisible(){\n\t\treturn this.visible;\n\t}\n\t\n\thideOnBlur(callback){\n\t\tthis.blurable = true;\n\t\t\n\t\tif(this.visible){\n\t\t\tsetTimeout(() => {\n\t\t\t\tif(this.visible){\n\t\t\t\t\tthis.table.rowManager.element.addEventListener(\"scroll\", this.blurEvent);\n\t\t\t\t\tthis.subscribe(\"cell-editing\", this.blurEvent);\n\t\t\t\t\tdocument.body.addEventListener(\"click\", this.blurEvent);\n\t\t\t\t\tdocument.body.addEventListener(\"contextmenu\", this.blurEvent);\n\t\t\t\t\tdocument.body.addEventListener(\"mousedown\", this.blurEvent);\n\t\t\t\t\twindow.addEventListener(\"resize\", this.blurEvent);\n\t\t\t\t\tdocument.body.addEventListener(\"keydown\", this.escEvent);\n\n\t\t\t\t\tthis.blurEventsBound = true;\n\t\t\t\t}\n\t\t\t}, 100);\n\t\t\t\n\t\t\tthis.blurCallback = callback;\n\t\t}\n\t\t\n\t\treturn this;\n\t}\n\t\n\t_escapeCheck(e){\n\t\tif(e.keyCode == 27){\n\t\t\tthis.hide();\n\t\t}\n\t}\n\t\n\tblockHide(){\n\t\tthis.hideable = false;\n\t}\n\t\n\trestoreHide(){\n\t\tthis.hideable = true;\n\t}\n\t\n\thide(silent = false){\n\t\tif(this.visible && this.hideable){\n\t\t\tif(this.blurable && this.blurEventsBound){\n\t\t\t\tdocument.body.removeEventListener(\"keydown\", this.escEvent);\n\t\t\t\tdocument.body.removeEventListener(\"click\", this.blurEvent);\n\t\t\t\tdocument.body.removeEventListener(\"contextmenu\", this.blurEvent);\n\t\t\t\tdocument.body.removeEventListener(\"mousedown\", this.blurEvent);\n\t\t\t\twindow.removeEventListener(\"resize\", this.blurEvent);\n\t\t\t\tthis.table.rowManager.element.removeEventListener(\"scroll\", this.blurEvent);\n\t\t\t\tthis.unsubscribe(\"cell-editing\", this.blurEvent);\n\n\t\t\t\tthis.blurEventsBound = false;\n\t\t\t}\n\t\t\t\n\t\t\tif(this.childPopup){\n\t\t\t\tthis.childPopup.hide();\n\t\t\t}\n\t\t\t\n\t\t\tif(this.parent){\n\t\t\t\tthis.parent.childPopup = null;\n\t\t\t}\n\t\t\t\n\t\t\tif(this.element.parentNode){\n\t\t\t\tthis.element.parentNode.removeChild(this.element);\n\t\t\t}\n\t\t\t\n\t\t\tthis.visible = false;\n\t\t\t\n\t\t\tif(this.blurCallback && !silent){\n\t\t\t\tthis.blurCallback();\n\t\t\t}\n\t\t\t\n\t\t\tthis.unsubscribe(\"table-destroy\", this.destroyBinding);\n\t\t}\n\t\t\n\t\treturn this;\n\t}\n\t\n\tchild(element){\n\t\tif(this.childPopup){\n\t\t\tthis.childPopup.hide();\n\t\t}\n\t\t\n\t\tthis.childPopup = new Popup(this.table, element, this);\n\t\t\n\t\treturn this.childPopup;\n\t}\n}\n\nclass Module extends CoreFeature{\n\t\n\tconstructor(table, name){\n\t\tsuper(table);\n\t\t\n\t\tthis._handler = null;\n\t}\n\t\n\tinitialize(){\n\t\t// setup module when table is initialized, to be overridden in module\n\t}\n\t\n\t\n\t///////////////////////////////////\n\t////// Options Registration ///////\n\t///////////////////////////////////\n\t\n\tregisterTableOption(key, value){\n\t\tthis.table.optionsList.register(key, value);\n\t}\n\t\n\tregisterColumnOption(key, value){\n\t\tthis.table.columnManager.optionsList.register(key, value);\n\t}\n\t\n\t///////////////////////////////////\n\t/// Public Function Registration ///\n\t///////////////////////////////////\n\t\n\tregisterTableFunction(name, func){\n\t\tif(typeof this.table[name] === \"undefined\"){\n\t\t\tthis.table[name] = (...args) => {\n\t\t\t\tthis.table.initGuard(name);\n\t\t\t\t\n\t\t\t\treturn func(...args);\n\t\t\t};\n\t\t}else {\n\t\t\tconsole.warn(\"Unable to bind table function, name already in use\", name);\n\t\t}\n\t}\n\t\n\tregisterComponentFunction(component, func, handler){\n\t\treturn this.table.componentFunctionBinder.bind(component, func, handler);\n\t}\n\t\n\t///////////////////////////////////\n\t////////// Data Pipeline //////////\n\t///////////////////////////////////\n\t\n\tregisterDataHandler(handler, priority){\n\t\tthis.table.rowManager.registerDataPipelineHandler(handler, priority);\n\t\tthis._handler = handler;\n\t}\n\t\n\tregisterDisplayHandler(handler, priority){\n\t\tthis.table.rowManager.registerDisplayPipelineHandler(handler, priority);\n\t\tthis._handler = handler;\n\t}\n\t\n\tdisplayRows(adjust){\n\t\tvar index = this.table.rowManager.displayRows.length - 1, \n\t\tlookupIndex;\n\t\t\n\t\tif(this._handler){\n\t\t\tlookupIndex = this.table.rowManager.displayPipeline.findIndex((item) => {\n\t\t\t\treturn item.handler === this._handler;\n\t\t\t});\n\n\t\t\tif(lookupIndex > -1){\n\t\t\t\tindex = lookupIndex;\n\t\t\t}\n\t\t}\n\t\t\n\t\tif(adjust){\n\t\t\tindex = index + adjust;\n\t\t}\n\n\t\tif(this._handler){\n\t\t\tif(index > -1){\n\t\t\t\treturn this.table.rowManager.getDisplayRows(index);\n\t\t\t}else {\n\t\t\t\treturn this.activeRows();\n\t\t\t}\n\t\t}\t\n\t}\n\t\n\tactiveRows(){\n\t\treturn this.table.rowManager.activeRows;\n\t}\n\t\n\trefreshData(renderInPosition, handler){\n\t\tif(!handler){\n\t\t\thandler = this._handler;\n\t\t}\n\t\t\n\t\tif(handler){\n\t\t\tthis.table.rowManager.refreshActiveData(handler, false, renderInPosition);\n\t\t}\n\t}\n\t\n\t///////////////////////////////////\n\t//////// Footer Management ////////\n\t///////////////////////////////////\n\t\n\tfooterAppend(element){\n\t\treturn this.table.footerManager.append(element);\n\t}\n\t\n\tfooterPrepend(element){\n\t\treturn this.table.footerManager.prepend(element);\n\t}\n\t\n\tfooterRemove(element){\n\t\treturn this.table.footerManager.remove(element);\n\t} \n\t\n\t///////////////////////////////////\n\t//////// Popups Management ////////\n\t///////////////////////////////////\n\t\n\tpopup(menuEl, menuContainer){\n\t\treturn new Popup(this.table, menuEl, menuContainer);\n\t}\n\t\n\t///////////////////////////////////\n\t//////// Alert Management ////////\n\t///////////////////////////////////\n\t\n\talert(content, type){\n\t\treturn this.table.alertManager.alert(content, type);\n\t}\n\t\n\tclearAlert(){\n\t\treturn this.table.alertManager.clear();\n\t}\n\t\n}\n\nvar defaultAccessors = {};\n\nclass Accessor extends Module{\n\n\tconstructor(table){\n\t\tsuper(table);\n\n\t\tthis.allowedTypes = [\"\", \"data\", \"download\", \"clipboard\", \"print\", \"htmlOutput\"]; //list of accessor types\n\n\t\tthis.registerColumnOption(\"accessor\");\n\t\tthis.registerColumnOption(\"accessorParams\");\n\t\tthis.registerColumnOption(\"accessorData\");\n\t\tthis.registerColumnOption(\"accessorDataParams\");\n\t\tthis.registerColumnOption(\"accessorDownload\");\n\t\tthis.registerColumnOption(\"accessorDownloadParams\");\n\t\tthis.registerColumnOption(\"accessorClipboard\");\n\t\tthis.registerColumnOption(\"accessorClipboardParams\");\n\t\tthis.registerColumnOption(\"accessorPrint\");\n\t\tthis.registerColumnOption(\"accessorPrintParams\");\n\t\tthis.registerColumnOption(\"accessorHtmlOutput\");\n\t\tthis.registerColumnOption(\"accessorHtmlOutputParams\");\n\t}\n\n\tinitialize(){\n\t\tthis.subscribe(\"column-layout\", this.initializeColumn.bind(this));\n\t\tthis.subscribe(\"row-data-retrieve\", this.transformRow.bind(this));\n\t}\n\n\t//initialize column accessor\n\tinitializeColumn(column){\n\t\tvar match = false,\n\t\tconfig = {};\n\n\t\tthis.allowedTypes.forEach((type) => {\n\t\t\tvar key = \"accessor\" + (type.charAt(0).toUpperCase() + type.slice(1)),\n\t\t\taccessor;\n\n\t\t\tif(column.definition[key]){\n\t\t\t\taccessor = this.lookupAccessor(column.definition[key]);\n\n\t\t\t\tif(accessor){\n\t\t\t\t\tmatch = true;\n\n\t\t\t\t\tconfig[key] = {\n\t\t\t\t\t\taccessor:accessor,\n\t\t\t\t\t\tparams: column.definition[key + \"Params\"] || {},\n\t\t\t\t\t};\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\n\t\tif(match){\n\t\t\tcolumn.modules.accessor = config;\n\t\t}\n\t}\n\n\tlookupAccessor(value){\n\t\tvar accessor = false;\n\n\t\t//set column accessor\n\t\tswitch(typeof value){\n\t\t\tcase \"string\":\n\t\t\t\tif(Accessor.accessors[value]){\n\t\t\t\t\taccessor = Accessor.accessors[value];\n\t\t\t\t}else {\n\t\t\t\t\tconsole.warn(\"Accessor Error - No such accessor found, ignoring: \", value);\n\t\t\t\t}\n\t\t\t\tbreak;\n\n\t\t\tcase \"function\":\n\t\t\t\taccessor = value;\n\t\t\t\tbreak;\n\t\t}\n\n\t\treturn accessor;\n\t}\n\n\t//apply accessor to row\n\ttransformRow(row, type){\n\t\tvar key = \"accessor\" + (type.charAt(0).toUpperCase() + type.slice(1)),\n\t\trowComponent = row.getComponent();\n\n\t\t//clone data object with deep copy to isolate internal data from returned result\n\t\tvar data = Helpers.deepClone(row.data || {});\n\n\t\tthis.table.columnManager.traverse(function(column){\n\t\t\tvar value, accessor, params, colComponent;\n\n\t\t\tif(column.modules.accessor){\n\n\t\t\t\taccessor = column.modules.accessor[key] || column.modules.accessor.accessor || false;\n\n\t\t\t\tif(accessor){\n\t\t\t\t\tvalue = column.getFieldValue(data);\n\n\t\t\t\t\tif(value != \"undefined\"){\n\t\t\t\t\t\tcolComponent = column.getComponent();\n\t\t\t\t\t\tparams = typeof accessor.params === \"function\" ? accessor.params(value, data, type, colComponent, rowComponent) : accessor.params;\n\t\t\t\t\t\tcolumn.setFieldValue(data, accessor.accessor(value, data, type, params, colComponent, rowComponent));\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\n\t\treturn data;\n\t}\n}\n\n//load defaults\nAccessor.moduleName = \"accessor\";\nAccessor.accessors = defaultAccessors;\n\nvar defaultConfig = {\n\tmethod: \"GET\",\n};\n\nfunction generateParamsList(data, prefix){\n\tvar output = [];\n\n\tprefix = prefix || \"\";\n\n\tif(Array.isArray(data)){\n\t\tdata.forEach((item, i) => {\n\t\t\toutput = output.concat(generateParamsList(item, prefix ? prefix + \"[\" + i + \"]\" : i));\n\t\t});\n\t}else if (typeof data === \"object\"){\n\t\tfor (var key in data){\n\t\t\toutput = output.concat(generateParamsList(data[key], prefix ? prefix + \"[\" + key + \"]\" : key));\n\t\t}\n\t}else {\n\t\toutput.push({key:prefix, value:data});\n\t}\n\n\treturn output;\n}\n\nfunction serializeParams(params){\n\tvar output = generateParamsList(params),\n\tencoded = [];\n\n\toutput.forEach(function(item){\n\t\tencoded.push(encodeURIComponent(item.key) + \"=\" + encodeURIComponent(item.value));\n\t});\n\n\treturn encoded.join(\"&\");\n}\n\nfunction urlBuilder(url, config, params){\n\tif(url){\n\t\tif(params && Object.keys(params).length){\n\t\t\tif(!config.method || config.method.toLowerCase() == \"get\"){\n\t\t\t\tconfig.method = \"get\";\n\n\t\t\t\turl += (url.includes(\"?\") ? \"&\" : \"?\") + serializeParams(params);\n\t\t\t}\n\t\t}\n\t}\n\n\treturn url;\n}\n\nfunction defaultLoaderPromise(url, config, params){\n\tvar contentType;\n\n\treturn new Promise((resolve, reject) => {\n\t\t//set url\n\t\turl = this.urlGenerator.call(this.table, url, config, params);\n\n\t\t//set body content if not GET request\n\t\tif(config.method.toUpperCase() != \"GET\"){\n\t\t\tcontentType = typeof this.table.options.ajaxContentType === \"object\" ?  this.table.options.ajaxContentType : this.contentTypeFormatters[this.table.options.ajaxContentType];\n\t\t\tif(contentType){\n\n\t\t\t\tfor(var key in contentType.headers){\n\t\t\t\t\tif(!config.headers){\n\t\t\t\t\t\tconfig.headers = {};\n\t\t\t\t\t}\n\n\t\t\t\t\tif(typeof config.headers[key] === \"undefined\"){\n\t\t\t\t\t\tconfig.headers[key] = contentType.headers[key];\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\tconfig.body = contentType.body.call(this, url, config, params);\n\n\t\t\t}else {\n\t\t\t\tconsole.warn(\"Ajax Error - Invalid ajaxContentType value:\", this.table.options.ajaxContentType);\n\t\t\t}\n\t\t}\n\n\t\tif(url){\n\t\t\t//configure headers\n\t\t\tif(typeof config.headers === \"undefined\"){\n\t\t\t\tconfig.headers = {};\n\t\t\t}\n\n\t\t\tif(typeof config.headers.Accept === \"undefined\"){\n\t\t\t\tconfig.headers.Accept = \"application/json\";\n\t\t\t}\n\n\t\t\tif(typeof config.headers[\"X-Requested-With\"] === \"undefined\"){\n\t\t\t\tconfig.headers[\"X-Requested-With\"] = \"XMLHttpRequest\";\n\t\t\t}\n\n\t\t\tif(typeof config.mode === \"undefined\"){\n\t\t\t\tconfig.mode = \"cors\";\n\t\t\t}\n\n\t\t\tif(config.mode == \"cors\"){\n\t\t\t\tif(typeof config.headers[\"Origin\"] === \"undefined\"){\n\t\t\t\t\tconfig.headers[\"Origin\"] = window.location.origin;\n\t\t\t\t}\n        \n\t\t\t\tif(typeof config.credentials === \"undefined\"){\n\t\t\t\t\tconfig.credentials = 'same-origin';\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tif(typeof config.credentials === \"undefined\"){\n\t\t\t\t\tconfig.credentials = 'include';\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t//send request\n\t\t\tfetch(url, config)\n\t\t\t\t.then((response)=>{\n\t\t\t\t\tif(response.ok) {\n\t\t\t\t\t\tresponse.json()\n\t\t\t\t\t\t\t.then((data)=>{\n\t\t\t\t\t\t\t\tresolve(data);\n\t\t\t\t\t\t\t}).catch((error)=>{\n\t\t\t\t\t\t\t\treject(error);\n\t\t\t\t\t\t\t\tconsole.warn(\"Ajax Load Error - Invalid JSON returned\", error);\n\t\t\t\t\t\t\t});\n\t\t\t\t\t}else {\n\t\t\t\t\t\tconsole.error(\"Ajax Load Error - Connection Error: \" + response.status, response.statusText);\n\t\t\t\t\t\treject(response);\n\t\t\t\t\t}\n\t\t\t\t})\n\t\t\t\t.catch((error)=>{\n\t\t\t\t\tconsole.error(\"Ajax Load Error - Connection Error: \", error);\n\t\t\t\t\treject(error);\n\t\t\t\t});\n\t\t}else {\n\t\t\tconsole.warn(\"Ajax Load Error - No URL Set\");\n\t\t\tresolve([]);\n\t\t}\n\t});\n}\n\nfunction generateParamsList$1(data, prefix){\n\tvar output = [];\n\n\tprefix = prefix || \"\";\n\n\tif(Array.isArray(data)){\n\t\tdata.forEach((item, i) => {\n\t\t\toutput = output.concat(generateParamsList$1(item, prefix ? prefix + \"[\" + i + \"]\" : i));\n\t\t});\n\t}else if (typeof data === \"object\"){\n\t\tfor (var key in data){\n\t\t\toutput = output.concat(generateParamsList$1(data[key], prefix ? prefix + \"[\" + key + \"]\" : key));\n\t\t}\n\t}else {\n\t\toutput.push({key:prefix, value:data});\n\t}\n\n\treturn output;\n}\n\nvar defaultContentTypeFormatters = {\n\t\"json\":{\n\t\theaders:{\n\t\t\t'Content-Type': 'application/json',\n\t\t},\n\t\tbody:function(url, config, params){\n\t\t\treturn JSON.stringify(params);\n\t\t},\n\t},\n\t\"form\":{\n\t\theaders:{\n\t\t},\n\t\tbody:function(url, config, params){\n\n\t\t\tvar output = generateParamsList$1(params),\n\t\t\tform = new FormData();\n\n\t\t\toutput.forEach(function(item){\n\t\t\t\tform.append(item.key, item.value);\n\t\t\t});\n\n\t\t\treturn form;\n\t\t},\n\t},\n};\n\nclass Ajax extends Module{\n\t\n\tconstructor(table){\n\t\tsuper(table);\n\t\t\n\t\tthis.config = {}; //hold config object for ajax request\n\t\tthis.url = \"\"; //request URL\n\t\tthis.urlGenerator = false;\n\t\tthis.params = false; //request parameters\n\t\t\n\t\tthis.loaderPromise = false;\n\t\t\n\t\tthis.registerTableOption(\"ajaxURL\", false); //url for ajax loading\n\t\tthis.registerTableOption(\"ajaxURLGenerator\", false);\n\t\tthis.registerTableOption(\"ajaxParams\", {});  //params for ajax loading\n\t\tthis.registerTableOption(\"ajaxConfig\", \"get\"); //ajax request type\n\t\tthis.registerTableOption(\"ajaxContentType\", \"form\"); //ajax request type\n\t\tthis.registerTableOption(\"ajaxRequestFunc\", false); //promise function\n\t\t\n\t\tthis.registerTableOption(\"ajaxRequesting\", function(){});\n\t\tthis.registerTableOption(\"ajaxResponse\", false);\n\t\t\n\t\tthis.contentTypeFormatters = Ajax.contentTypeFormatters;\n\t}\n\t\n\t//initialize setup options\n\tinitialize(){\n\t\tthis.loaderPromise = this.table.options.ajaxRequestFunc || Ajax.defaultLoaderPromise;\n\t\tthis.urlGenerator = this.table.options.ajaxURLGenerator || Ajax.defaultURLGenerator;\n\t\t\n\t\tif(this.table.options.ajaxURL){\n\t\t\tthis.setUrl(this.table.options.ajaxURL);\n\t\t}\n\n\n\t\tthis.setDefaultConfig(this.table.options.ajaxConfig);\n\t\t\n\t\tthis.registerTableFunction(\"getAjaxUrl\", this.getUrl.bind(this));\n\t\t\n\t\tthis.subscribe(\"data-loading\", this.requestDataCheck.bind(this));\n\t\tthis.subscribe(\"data-params\", this.requestParams.bind(this));\n\t\tthis.subscribe(\"data-load\", this.requestData.bind(this));\n\t}\n\t\n\trequestParams(data, config, silent, params){\n\t\tvar ajaxParams = this.table.options.ajaxParams;\n\t\t\n\t\tif(ajaxParams){\n\t\t\tif(typeof ajaxParams === \"function\"){\n\t\t\t\tajaxParams = ajaxParams.call(this.table);\n\t\t\t}\n\t\t\t\n\t\t\tparams = Object.assign(Object.assign({}, ajaxParams), params);\n\t\t}\t\t\n\t\t\n\t\treturn params;\n\t}\n\t\n\trequestDataCheck(data, params, config, silent){\n\t\treturn !!((!data && this.url) || typeof data === \"string\");\n\t}\n\t\n\trequestData(url, params, config, silent, previousData){\n\t\tvar ajaxConfig;\n\t\t\n\t\tif(!previousData && this.requestDataCheck(url)){\n\t\t\tif(url){\n\t\t\t\tthis.setUrl(url);\n\t\t\t}\n\t\t\t\n\t\t\tajaxConfig = this.generateConfig(config);\n\t\t\t\n\t\t\treturn this.sendRequest(this.url, params, ajaxConfig);\n\t\t}else {\n\t\t\treturn previousData;\n\t\t}\n\t}\n\t\n\tsetDefaultConfig(config = {}){\n\t\tthis.config = Object.assign({}, Ajax.defaultConfig);\n\n\t\tif(typeof config == \"string\"){\n\t\t\tthis.config.method = config;\n\t\t}else {\n\t\t\tObject.assign(this.config, config);\n\t\t}\n\t}\n\t\n\t//load config object\n\tgenerateConfig(config = {}){\n\t\tvar ajaxConfig = Object.assign({}, this.config);\n\t\t\n\t\tif(typeof config == \"string\"){\n\t\t\tajaxConfig.method = config;\n\t\t}else {\n\t\t\tObject.assign(ajaxConfig, config);\n\t\t}\n\t\t\n\t\treturn ajaxConfig;\n\t}\n\t\n\t//set request url\n\tsetUrl(url){\n\t\tthis.url = url;\n\t}\n\t\n\t//get request url\n\tgetUrl(){\n\t\treturn this.url;\n\t}\n\t\n\t//send ajax request\n\tsendRequest(url, params, config){\n\t\tif(this.table.options.ajaxRequesting.call(this.table, url, params) !== false){\n\t\t\treturn this.loaderPromise(url, config, params)\n\t\t\t\t.then((data)=>{\n\t\t\t\t\tif(this.table.options.ajaxResponse){\n\t\t\t\t\t\tdata = this.table.options.ajaxResponse.call(this.table, url, params, data);\n\t\t\t\t\t}\n\t\t\t\t\n\t\t\t\t\treturn data;\n\t\t\t\t});\n\t\t}else {\n\t\t\treturn Promise.reject();\n\t\t}\n\t}\n}\n\nAjax.moduleName = \"ajax\";\n\n//load defaults\nAjax.defaultConfig = defaultConfig;\nAjax.defaultURLGenerator = urlBuilder;\nAjax.defaultLoaderPromise = defaultLoaderPromise;\nAjax.contentTypeFormatters = defaultContentTypeFormatters;\n\nvar defaultPasteActions = {\n\treplace:function(data){\n\t\treturn this.table.setData(data);\n\t},\n\tupdate:function(data){\n\t\treturn this.table.updateOrAddData(data);\n\t},\n\tinsert:function(data){\n\t\treturn this.table.addData(data);\n\t},\n\trange:function(data){\n\t\tvar rows = [],\n\t\trange = this.table.modules.selectRange.activeRange,\n\t\tsingleCell = false,\n\t\tbounds, startCell, startRow, rowWidth, dataLength;\n\n\t\tdataLength = data.length;\n\t\t\n\t\tif(range){\n\t\t\tbounds = range.getBounds();\n\t\t\tstartCell = bounds.start;\n\t\t\t\n\t\t\tif(bounds.start === bounds.end){\n\t\t\t\tsingleCell = true;\n\t\t\t}\n\t\t\t\n\t\t\tif(startCell){\n\t\t\t\trows = this.table.rowManager.activeRows.slice();\n\t\t\t\tstartRow = rows.indexOf(startCell.row);\n\n\t\t\t\tif(singleCell){\n\t\t\t\t\trowWidth = data.length;\n\t\t\t\t}else {\n\t\t\t\t\trowWidth = (rows.indexOf(bounds.end.row) - startRow) + 1;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t\n\t\t\t\tif(startRow >-1){\n\t\t\t\t\tthis.table.blockRedraw();\n\t\t\t\t\t\n\t\t\t\t\trows = rows.slice(startRow, startRow + rowWidth);\n\t\t\t\t\t\n\t\t\t\t\trows.forEach((row, i) => {\n\t\t\t\t\t\trow.updateData(data[i % dataLength]);\n\t\t\t\t\t});\n\t\t\t\t\t\n\t\t\t\t\tthis.table.restoreRedraw();\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn rows;\n\t}\n};\n\nvar defaultPasteParsers = {\n\ttable:function(clipboard){\n\t\tvar data = [],\n\t\theaderFindSuccess = true,\n\t\tcolumns = this.table.columnManager.columns,\n\t\tcolumnMap = [],\n\t\trows = [];\n\t\t\n\t\t//get data from clipboard into array of columns and rows.\n\t\tclipboard = clipboard.split(\"\\n\");\n\t\t\n\t\tclipboard.forEach(function(row){\n\t\t\tdata.push(row.split(\"\\t\"));\n\t\t});\n\t\t\n\t\tif(data.length && !(data.length === 1 && data[0].length < 2)){\n\t\t\t\n\t\t\t//check if headers are present by title\n\t\t\tdata[0].forEach(function(value){\n\t\t\t\tvar column = columns.find(function(column){\n\t\t\t\t\treturn value && column.definition.title && value.trim() && column.definition.title.trim() === value.trim();\n\t\t\t\t});\n\t\t\t\t\n\t\t\t\tif(column){\n\t\t\t\t\tcolumnMap.push(column);\n\t\t\t\t}else {\n\t\t\t\t\theaderFindSuccess = false;\n\t\t\t\t}\n\t\t\t});\n\t\t\t\n\t\t\t//check if column headers are present by field\n\t\t\tif(!headerFindSuccess){\n\t\t\t\theaderFindSuccess = true;\n\t\t\t\tcolumnMap = [];\n\t\t\t\t\n\t\t\t\tdata[0].forEach(function(value){\n\t\t\t\t\tvar column = columns.find(function(column){\n\t\t\t\t\t\treturn value && column.field && value.trim() && column.field.trim() === value.trim();\n\t\t\t\t\t});\n\t\t\t\t\t\n\t\t\t\t\tif(column){\n\t\t\t\t\t\tcolumnMap.push(column);\n\t\t\t\t\t}else {\n\t\t\t\t\t\theaderFindSuccess = false;\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t\t\n\t\t\t\tif(!headerFindSuccess){\n\t\t\t\t\tcolumnMap = this.table.columnManager.columnsByIndex;\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\t//remove header row if found\n\t\t\tif(headerFindSuccess){\n\t\t\t\tdata.shift();\n\t\t\t}\n\t\t\t\n\t\t\tdata.forEach(function(item){\n\t\t\t\tvar row = {};\n\t\t\t\t\n\t\t\t\titem.forEach(function(value, i){\n\t\t\t\t\tif(columnMap[i]){\n\t\t\t\t\t\trow[columnMap[i].field] = value;\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t\t\n\t\t\t\trows.push(row);\n\t\t\t});\n\t\t\t\n\t\t\treturn rows;\n\t\t}else {\n\t\t\treturn false;\n\t\t}\n\t},\n\trange:function(clipboard){\n\t\tvar data = [],\n\t\trows = [],\n\t\trange = this.table.modules.selectRange.activeRange,\n\t\tsingleCell = false,\n\t\tbounds, startCell, colWidth, columnMap, startCol;\n\t\t\n\t\tif(range){\n\t\t\tbounds = range.getBounds();\n\t\t\tstartCell = bounds.start;\n\n\t\t\tif(bounds.start === bounds.end){\n\t\t\t\tsingleCell = true;\n\t\t\t}\n\t\t\t\n\t\t\tif(startCell){\n\t\t\t\t//get data from clipboard into array of columns and rows.\n\t\t\t\tclipboard = clipboard.split(\"\\n\");\n\t\t\t\t\n\t\t\t\tclipboard.forEach(function(row){\n\t\t\t\t\tdata.push(row.split(\"\\t\"));\n\t\t\t\t});\n\t\t\t\t\n\t\t\t\tif(data.length){\n\t\t\t\t\tcolumnMap = this.table.columnManager.getVisibleColumnsByIndex();\n\t\t\t\t\tstartCol = columnMap.indexOf(startCell.column);\n\n\t\t\t\t\tif(startCol > -1){\n\t\t\t\t\t\tif(singleCell){\n\t\t\t\t\t\t\tcolWidth = data[0].length;\n\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\tcolWidth = (columnMap.indexOf(bounds.end.column) - startCol) + 1;\n\t\t\t\t\t\t}\n\n\t\t\t\t\t\tcolumnMap = columnMap.slice(startCol, startCol + colWidth);\n\n\t\t\t\t\t\tdata.forEach((item) => {\n\t\t\t\t\t\t\tvar row = {};\n\t\t\t\t\t\t\tvar itemLength = item.length;\n\n\t\t\t\t\t\t\tcolumnMap.forEach(function(col, i){\n\t\t\t\t\t\t\t\trow[col.field] = item[i % itemLength];\n\t\t\t\t\t\t\t});\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\trows.push(row);\t\n\t\t\t\t\t\t});\n\n\t\t\t\t\t\treturn rows;\n\t\t\t\t\t}\t\t\t\t\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn false;\n\t}\n};\n\nclass Clipboard extends Module{\n\n\tconstructor(table){\n\t\tsuper(table);\n\n\t\tthis.mode = true;\n\t\tthis.pasteParser = function(){};\n\t\tthis.pasteAction = function(){};\n\t\tthis.customSelection = false;\n\t\tthis.rowRange = false;\n\t\tthis.blocked = true; //block copy actions not originating from this command\n\n\t\tthis.registerTableOption(\"clipboard\", false); //enable clipboard\n\t\tthis.registerTableOption(\"clipboardCopyStyled\", true); //formatted table data\n\t\tthis.registerTableOption(\"clipboardCopyConfig\", false); //clipboard config\n\t\tthis.registerTableOption(\"clipboardCopyFormatter\", false); //DEPRECATED - REMOVE in 5.0\n\t\tthis.registerTableOption(\"clipboardCopyRowRange\", \"active\"); //restrict clipboard to visible rows only\n\t\tthis.registerTableOption(\"clipboardPasteParser\", \"table\"); //convert pasted clipboard data to rows\n\t\tthis.registerTableOption(\"clipboardPasteAction\", \"insert\"); //how to insert pasted data into the table\n\n\t\tthis.registerColumnOption(\"clipboard\");\n\t\tthis.registerColumnOption(\"titleClipboard\");\n\t}\n\n\tinitialize(){\n\t\tthis.mode = this.table.options.clipboard;\n\n\t\tthis.rowRange = this.table.options.clipboardCopyRowRange;\n\n\t\tif(this.mode === true || this.mode === \"copy\"){\n\t\t\tthis.table.element.addEventListener(\"copy\", (e) => {\n\t\t\t\tvar plain, html, list;\n\n\t\t\t\tif(!this.blocked){\n\t\t\t\t\te.preventDefault();\n\n\t\t\t\t\tif(this.customSelection){\n\t\t\t\t\t\tplain = this.customSelection;\n\n\t\t\t\t\t\tif(this.table.options.clipboardCopyFormatter){\n\t\t\t\t\t\t\tplain = this.table.options.clipboardCopyFormatter(\"plain\", plain);\n\t\t\t\t\t\t}\n\t\t\t\t\t}else {\n\n\t\t\t\t\t\tlist = this.table.modules.export.generateExportList(this.table.options.clipboardCopyConfig, this.table.options.clipboardCopyStyled, this.rowRange, \"clipboard\");\n\n\t\t\t\t\t\thtml = this.table.modules.export.generateHTMLTable(list);\n\t\t\t\t\t\tplain = html ? this.generatePlainContent(list) : \"\";\n\n\t\t\t\t\t\tif(this.table.options.clipboardCopyFormatter){\n\t\t\t\t\t\t\tplain = this.table.options.clipboardCopyFormatter(\"plain\", plain);\n\t\t\t\t\t\t\thtml = this.table.options.clipboardCopyFormatter(\"html\", html);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\tif (window.clipboardData && window.clipboardData.setData) {\n\t\t\t\t\t\twindow.clipboardData.setData('Text', plain);\n\t\t\t\t\t} else if (e.clipboardData && e.clipboardData.setData) {\n\t\t\t\t\t\te.clipboardData.setData('text/plain', plain);\n\t\t\t\t\t\tif(html){\n\t\t\t\t\t\t\te.clipboardData.setData('text/html', html);\n\t\t\t\t\t\t}\n\t\t\t\t\t} else if (e.originalEvent && e.originalEvent.clipboardData.setData) {\n\t\t\t\t\t\te.originalEvent.clipboardData.setData('text/plain', plain);\n\t\t\t\t\t\tif(html){\n\t\t\t\t\t\t\te.originalEvent.clipboardData.setData('text/html', html);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\tthis.dispatchExternal(\"clipboardCopied\", plain, html);\n\n\t\t\t\t\tthis.reset();\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\n\t\tif(this.mode === true || this.mode === \"paste\"){\n\t\t\tthis.table.element.addEventListener(\"paste\", (e) => {\n\t\t\t\tthis.paste(e);\n\t\t\t});\n\t\t}\n\n\t\tthis.setPasteParser(this.table.options.clipboardPasteParser);\n\t\tthis.setPasteAction(this.table.options.clipboardPasteAction);\n\n\t\tthis.registerTableFunction(\"copyToClipboard\", this.copy.bind(this));\n\t}\n\n\treset(){\n\t\tthis.blocked = true;\n\t\tthis.customSelection = false;\n\t}\n\n\tgeneratePlainContent (list) {\n\t\tvar output = [];\n\n\t\tlist.forEach((row) => {\n\t\t\tvar rowData = [];\n\n\t\t\trow.columns.forEach((col) => {\n\t\t\t\tvar value = \"\";\n\n\t\t\t\tif(col){\n\n\t\t\t\t\tif(row.type === \"group\"){\n\t\t\t\t\t\tcol.value = col.component.getKey();\n\t\t\t\t\t}\n\n\t\t\t\t\tif(col.value === null){\n\t\t\t\t\t\tvalue = \"\";\n\t\t\t\t\t}else {\n\t\t\t\t\t\tswitch(typeof col.value){\n\t\t\t\t\t\t\tcase \"object\":\n\t\t\t\t\t\t\t\tvalue = JSON.stringify(col.value);\n\t\t\t\t\t\t\t\tbreak;\n\n\t\t\t\t\t\t\tcase \"undefined\":\n\t\t\t\t\t\t\t\tvalue = \"\";\n\t\t\t\t\t\t\t\tbreak;\n\n\t\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\t\tvalue = col.value;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\trowData.push(value);\n\t\t\t});\n\n\t\t\toutput.push(rowData.join(\"\\t\"));\n\t\t});\n\n\t\treturn output.join(\"\\n\");\n\t}\n\n\tcopy (range, internal) {\n\t\tvar sel, textRange;\n\t\tthis.blocked = false;\n\t\tthis.customSelection = false;\n\t\n\n\t\tif (this.mode === true || this.mode === \"copy\") {\n\n\t\t\tthis.rowRange = range || this.table.options.clipboardCopyRowRange;\n\n\t\t\tif (typeof window.getSelection != \"undefined\" && typeof document.createRange != \"undefined\") {\n\t\t\t\trange = document.createRange();\n\t\t\t\trange.selectNodeContents(this.table.element);\n\t\t\t\tsel = window.getSelection();\n\n\t\t\t\tif (sel.toString() && internal) {\n\t\t\t\t\tthis.customSelection = sel.toString();\n\t\t\t\t}\n\n\t\t\t\tsel.removeAllRanges();\n\t\t\t\tsel.addRange(range);\n\t\t\t} else if (typeof document.selection != \"undefined\" && typeof document.body.createTextRange != \"undefined\") {\n\t\t\t\ttextRange = document.body.createTextRange();\n\t\t\t\ttextRange.moveToElementText(this.table.element);\n\t\t\t\ttextRange.select();\n\t\t\t}\n\n\t\t\tdocument.execCommand('copy');\n\n\t\t\tif (sel) {\n\t\t\t\tsel.removeAllRanges();\n\t\t\t}\n\t\t}\n\t}\n\n\t//PASTE EVENT HANDLING\n\tsetPasteAction(action){\n\n\t\tswitch(typeof action){\n\t\t\tcase \"string\":\n\t\t\t\tthis.pasteAction = Clipboard.pasteActions[action];\n\n\t\t\t\tif(!this.pasteAction){\n\t\t\t\t\tconsole.warn(\"Clipboard Error - No such paste action found:\", action);\n\t\t\t\t}\n\t\t\t\tbreak;\n\n\t\t\tcase \"function\":\n\t\t\t\tthis.pasteAction = action;\n\t\t\t\tbreak;\n\t\t}\n\t}\n\n\tsetPasteParser(parser){\n\t\tswitch(typeof parser){\n\t\t\tcase \"string\":\n\t\t\t\tthis.pasteParser = Clipboard.pasteParsers[parser];\n\n\t\t\t\tif(!this.pasteParser){\n\t\t\t\t\tconsole.warn(\"Clipboard Error - No such paste parser found:\", parser);\n\t\t\t\t}\n\t\t\t\tbreak;\n\n\t\t\tcase \"function\":\n\t\t\t\tthis.pasteParser = parser;\n\t\t\t\tbreak;\n\t\t}\n\t}\n\n\tpaste(e){\n\t\tvar data, rowData, rows;\n\n\t\tif(this.checkPasteOrigin(e)){\n\n\t\t\tdata = this.getPasteData(e);\n\n\t\t\trowData = this.pasteParser.call(this, data);\n\n\t\t\tif(rowData){\n\t\t\t\te.preventDefault();\n\n\t\t\t\tif(this.table.modExists(\"mutator\")){\n\t\t\t\t\trowData = this.mutateData(rowData);\n\t\t\t\t}\n\n\t\t\t\trows = this.pasteAction.call(this, rowData);\n\n\t\t\t\tthis.dispatchExternal(\"clipboardPasted\", data, rowData, rows);\n\t\t\t}else {\n\t\t\t\tthis.dispatchExternal(\"clipboardPasteError\", data);\n\t\t\t}\n\t\t}\n\t}\n\n\tmutateData(data){\n\t\tvar output = [];\n\n\t\tif(Array.isArray(data)){\n\t\t\tdata.forEach((row) => {\n\t\t\t\toutput.push(this.table.modules.mutator.transformRow(row, \"clipboard\"));\n\t\t\t});\n\t\t}else {\n\t\t\toutput = data;\n\t\t}\n\n\t\treturn output;\n\t}\n\n\n\tcheckPasteOrigin(e){\n\t\tvar valid = true;\n\t\tvar blocked = this.confirm(\"clipboard-paste\", [e]);\n\n\t\tif(blocked || ![\"DIV\", \"SPAN\"].includes(e.target.tagName)){\n\t\t\tvalid = false;\n\t\t}\n\n\t\treturn valid;\n\t}\n\n\tgetPasteData(e){\n\t\tvar data;\n\n\t\tif (window.clipboardData && window.clipboardData.getData) {\n\t\t\tdata = window.clipboardData.getData('Text');\n\t\t} else if (e.clipboardData && e.clipboardData.getData) {\n\t\t\tdata = e.clipboardData.getData('text/plain');\n\t\t} else if (e.originalEvent && e.originalEvent.clipboardData.getData) {\n\t\t\tdata = e.originalEvent.clipboardData.getData('text/plain');\n\t\t}\n\n\t\treturn data;\n\t}\n}\n\nClipboard.moduleName = \"clipboard\";\n\n//load defaults\nClipboard.pasteActions = defaultPasteActions;\nClipboard.pasteParsers = defaultPasteParsers;\n\nclass CalcComponent{\n\tconstructor (row){\n\t\tthis._row = row;\n\n\t\treturn new Proxy(this, {\n\t\t\tget: function(target, name, receiver) {\n\t\t\t\tif (typeof target[name] !== \"undefined\") {\n\t\t\t\t\treturn target[name];\n\t\t\t\t}else {\n\t\t\t\t\treturn target._row.table.componentFunctionBinder.handle(\"row\", target._row, name);\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\t}\n\n\tgetData(transform){\n\t\treturn this._row.getData(transform);\n\t}\n\n\tgetElement(){\n\t\treturn this._row.getElement();\n\t}\n\n\tgetTable(){\n\t\treturn this._row.table;\n\t}\n\n\tgetCells(){\n\t\tvar cells = [];\n\n\t\tthis._row.getCells().forEach(function(cell){\n\t\t\tcells.push(cell.getComponent());\n\t\t});\n\n\t\treturn cells;\n\t}\n\n\tgetCell(column){\n\t\tvar cell = this._row.getCell(column);\n\t\treturn cell ? cell.getComponent() : false;\n\t}\n\n\t_getSelf(){\n\t\treturn this._row;\n\t}\n}\n\n//public cell object\nclass CellComponent {\n\n\tconstructor (cell){\n\t\tthis._cell = cell;\n\n\t\treturn new Proxy(this, {\n\t\t\tget: function(target, name, receiver) {\n\t\t\t\tif (typeof target[name] !== \"undefined\") {\n\t\t\t\t\treturn target[name];\n\t\t\t\t}else {\n\t\t\t\t\treturn target._cell.table.componentFunctionBinder.handle(\"cell\", target._cell, name);\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\t}\n\n\tgetValue(){\n\t\treturn this._cell.getValue();\n\t}\n\n\tgetOldValue(){\n\t\treturn this._cell.getOldValue();\n\t}\n\n\tgetInitialValue(){\n\t\treturn this._cell.initialValue;\n\t}\n\n\tgetElement(){\n\t\treturn this._cell.getElement();\n\t}\n\n\tgetRow(){\n\t\treturn this._cell.row.getComponent();\n\t}\n\n\tgetData(transform){\n\t\treturn this._cell.row.getData(transform);\n\t}\n\tgetType(){\n\t\treturn \"cell\";\n\t}\n\tgetField(){\n\t\treturn this._cell.column.getField();\n\t}\n\n\tgetColumn(){\n\t\treturn this._cell.column.getComponent();\n\t}\n\n\tsetValue(value, mutate){\n\t\tif(typeof mutate == \"undefined\"){\n\t\t\tmutate = true;\n\t\t}\n\n\t\tthis._cell.setValue(value, mutate);\n\t}\n\n\trestoreOldValue(){\n\t\tthis._cell.setValueActual(this._cell.getOldValue());\n\t}\n\n\trestoreInitialValue(){\n\t\tthis._cell.setValueActual(this._cell.initialValue);\n\t}\n\n\tcheckHeight(){\n\t\tthis._cell.checkHeight();\n\t}\n\n\tgetTable(){\n\t\treturn this._cell.table;\n\t}\n\n\t_getSelf(){\n\t\treturn this._cell;\n\t}\n}\n\nclass Cell extends CoreFeature{\n\tconstructor(column, row){\n\t\tsuper(column.table);\n\n\t\tthis.table = column.table;\n\t\tthis.column = column;\n\t\tthis.row = row;\n\t\tthis.element = null;\n\t\tthis.value = null;\n\t\tthis.initialValue;\n\t\tthis.oldValue = null;\n\t\tthis.modules = {};\n\n\t\tthis.height = null;\n\t\tthis.width = null;\n\t\tthis.minWidth = null;\n\n\t\tthis.component = null;\n\n\t\tthis.loaded = false; //track if the cell has been added to the DOM yet\n\n\t\tthis.build();\n\t}\n\n\t//////////////// Setup Functions /////////////////\n\t//generate element\n\tbuild(){\n\t\tthis.generateElement();\n\n\t\tthis.setWidth();\n\n\t\tthis._configureCell();\n\n\t\tthis.setValueActual(this.column.getFieldValue(this.row.data));\n\n\t\tthis.initialValue = this.value;\n\t}\n\n\tgenerateElement(){\n\t\tthis.element = document.createElement('div');\n\t\tthis.element.className = \"tabulator-cell\";\n\t\tthis.element.setAttribute(\"role\", \"gridcell\");\n\t}\n\n\t_configureCell(){\n\t\tvar element = this.element,\n\t\tfield = this.column.getField(),\n\t\tvertAligns = {\n\t\t\ttop:\"flex-start\",\n\t\t\tbottom:\"flex-end\",\n\t\t\tmiddle:\"center\",\n\t\t},\n\t\thozAligns = {\n\t\t\tleft:\"flex-start\",\n\t\t\tright:\"flex-end\",\n\t\t\tcenter:\"center\",\n\t\t};\n\n\t\t//set text alignment\n\t\telement.style.textAlign = this.column.hozAlign;\n\n\t\tif(this.column.vertAlign){\n\t\t\telement.style.display = \"inline-flex\";\n\n\t\t\telement.style.alignItems = vertAligns[this.column.vertAlign] || \"\";\n\n\t\t\tif(this.column.hozAlign){\n\t\t\t\telement.style.justifyContent = hozAligns[this.column.hozAlign] || \"\";\n\t\t\t}\n\t\t}\n\n\t\tif(field){\n\t\t\telement.setAttribute(\"tabulator-field\", field);\n\t\t}\n\n\t\t//add class to cell if needed\n\t\tif(this.column.definition.cssClass){\n\t\t\tvar classNames = this.column.definition.cssClass.split(\" \");\n\t\t\tclassNames.forEach((className) => {\n\t\t\t\telement.classList.add(className);\n\t\t\t});\n\t\t}\n\n\t\tthis.dispatch(\"cell-init\", this);\n\n\t\t//hide cell if not visible\n\t\tif(!this.column.visible){\n\t\t\tthis.hide();\n\t\t}\n\t}\n\n\t//generate cell contents\n\t_generateContents(){\n\t\tvar val;\n\n\t\tval = this.chain(\"cell-format\", this, null, () => {\n\t\t\treturn this.element.innerHTML = this.value;\n\t\t});\n\n\t\tswitch(typeof val){\n\t\t\tcase \"object\":\n\t\t\t\tif(val instanceof Node){\n\n\t\t\t\t\t//clear previous cell contents\n\t\t\t\t\twhile(this.element.firstChild) this.element.removeChild(this.element.firstChild);\n\n\t\t\t\t\tthis.element.appendChild(val);\n\t\t\t\t}else {\n\t\t\t\t\tthis.element.innerHTML = \"\";\n\n\t\t\t\t\tif(val != null){\n\t\t\t\t\t\tconsole.warn(\"Format Error - Formatter has returned a type of object, the only valid formatter object return is an instance of Node, the formatter returned:\", val);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase \"undefined\":\n\t\t\t\tthis.element.innerHTML = \"\";\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthis.element.innerHTML = val;\n\t\t}\n\t}\n\n\tcellRendered(){\n\t\tthis.dispatch(\"cell-rendered\", this);\n\t}\n\n\t//////////////////// Getters ////////////////////\n\tgetElement(containerOnly){\n\t\tif(!this.loaded){\n\t\t\tthis.loaded = true;\n\t\t\tif(!containerOnly){\n\t\t\t\tthis.layoutElement();\n\t\t\t}\n\t\t}\n\n\t\treturn this.element;\n\t}\n\n\tgetValue(){\n\t\treturn this.value;\n\t}\n\n\tgetOldValue(){\n\t\treturn this.oldValue;\n\t}\n\n\t//////////////////// Actions ////////////////////\n\tsetValue(value, mutate, force){\n\t\tvar changed = this.setValueProcessData(value, mutate, force);\n\n\t\tif(changed){\n\t\t\tthis.dispatch(\"cell-value-updated\", this);\n\n\t\t\tthis.cellRendered();\n\n\t\t\tif(this.column.definition.cellEdited){\n\t\t\t\tthis.column.definition.cellEdited.call(this.table, this.getComponent());\n\t\t\t}\n\n\t\t\tthis.dispatchExternal(\"cellEdited\", this.getComponent());\n\n\t\t\tif(this.subscribedExternal(\"dataChanged\")){\n\t\t\t\tthis.dispatchExternal(\"dataChanged\", this.table.rowManager.getData());\n\t\t\t}\n\t\t}\n\t}\n\n\tsetValueProcessData(value, mutate, force){\n\t\tvar changed = false;\n\n\t\tif(this.value !== value || force){\n\n\t\t\tchanged = true;\n\n\t\t\tif(mutate){\n\t\t\t\tvalue = this.chain(\"cell-value-changing\", [this, value], null, value);\n\t\t\t}\n\t\t}\n\n\t\tthis.setValueActual(value);\n\n\t\tif(changed){\n\t\t\tthis.dispatch(\"cell-value-changed\", this);\n\t\t}\n\n\t\treturn changed;\n\t}\n\n\tsetValueActual(value){\n\t\tthis.oldValue = this.value;\n\n\t\tthis.value = value;\n\n\t\tthis.dispatch(\"cell-value-save-before\", this);\n\n\t\tthis.column.setFieldValue(this.row.data, value);\n\n\t\tthis.dispatch(\"cell-value-save-after\", this);\n\n\t\tif(this.loaded){\n\t\t\tthis.layoutElement();\n\t\t}\n\t}\n\n\tlayoutElement(){\n\t\tthis._generateContents();\n\n\t\tthis.dispatch(\"cell-layout\", this);\n\t}\n\n\tsetWidth(){\n\t\tthis.width = this.column.width;\n\t\tthis.element.style.width = this.column.widthStyled;\n\t}\n\n\tclearWidth(){\n\t\tthis.width = \"\";\n\t\tthis.element.style.width = \"\";\n\t}\n\n\tgetWidth(){\n\t\treturn this.width || this.element.offsetWidth;\n\t}\n\n\tsetMinWidth(){\n\t\tthis.minWidth = this.column.minWidth;\n\t\tthis.element.style.minWidth = this.column.minWidthStyled;\n\t}\n\n\tsetMaxWidth(){\n\t\tthis.maxWidth = this.column.maxWidth;\n\t\tthis.element.style.maxWidth = this.column.maxWidthStyled;\n\t}\n\n\tcheckHeight(){\n\t\t// var height = this.element.css(\"height\");\n\t\tthis.row.reinitializeHeight();\n\t}\n\n\tclearHeight(){\n\t\tthis.element.style.height = \"\";\n\t\tthis.height = null;\n\n\t\tthis.dispatch(\"cell-height\", this, \"\");\n\t}\n\n\tsetHeight(){\n\t\tthis.height = this.row.height;\n\t\tthis.element.style.height = this.row.heightStyled;\n\n\t\tthis.dispatch(\"cell-height\", this, this.row.heightStyled);\n\t}\n\n\tgetHeight(){\n\t\treturn this.height || this.element.offsetHeight;\n\t}\n\n\tshow(){\n\t\tthis.element.style.display = this.column.vertAlign ? \"inline-flex\" : \"\";\n\t}\n\n\thide(){\n\t\tthis.element.style.display = \"none\";\n\t}\n\n\tdelete(){\n\t\tthis.dispatch(\"cell-delete\", this);\n\n\t\tif(!this.table.rowManager.redrawBlock && this.element.parentNode){\n\t\t\tthis.element.parentNode.removeChild(this.element);\n\t\t}\n\n\t\tthis.element = false;\n\t\tthis.column.deleteCell(this);\n\t\tthis.row.deleteCell(this);\n\t\tthis.calcs = {};\n\t}\n\n\tgetIndex(){\n\t\treturn this.row.getCellIndex(this);\n\t}\n\n\t//////////////// Object Generation /////////////////\n\tgetComponent(){\n\t\tif(!this.component){\n\t\t\tthis.component = new CellComponent(this);\n\t\t}\n\n\t\treturn this.component;\n\t}\n}\n\n//public column object\nclass ColumnComponent {\n\tconstructor (column){\n\t\tthis._column = column;\n\t\tthis.type = \"ColumnComponent\";\n\n\t\treturn new Proxy(this, {\n\t\t\tget: function(target, name, receiver) {\n\t\t\t\tif (typeof target[name] !== \"undefined\") {\n\t\t\t\t\treturn target[name];\n\t\t\t\t}else {\n\t\t\t\t\treturn target._column.table.componentFunctionBinder.handle(\"column\", target._column, name);\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\t}\n\n\tgetElement(){\n\t\treturn this._column.getElement();\n\t}\n\n\tgetDefinition(){\n\t\treturn this._column.getDefinition();\n\t}\n\n\tgetField(){\n\t\treturn this._column.getField();\n\t}\n\n\tgetTitleDownload() {\n\t\treturn this._column.getTitleDownload();\n\t}\n\n\tgetCells(){\n\t\tvar cells = [];\n\n\t\tthis._column.cells.forEach(function(cell){\n\t\t\tcells.push(cell.getComponent());\n\t\t});\n\n\t\treturn cells;\n\t}\n\n\tisVisible(){\n\t\treturn this._column.visible;\n\t}\n\n\tshow(){\n\t\tif(this._column.isGroup){\n\t\t\tthis._column.columns.forEach(function(column){\n\t\t\t\tcolumn.show();\n\t\t\t});\n\t\t}else {\n\t\t\tthis._column.show();\n\t\t}\n\t}\n\n\thide(){\n\t\tif(this._column.isGroup){\n\t\t\tthis._column.columns.forEach(function(column){\n\t\t\t\tcolumn.hide();\n\t\t\t});\n\t\t}else {\n\t\t\tthis._column.hide();\n\t\t}\n\t}\n\n\ttoggle(){\n\t\tif(this._column.visible){\n\t\t\tthis.hide();\n\t\t}else {\n\t\t\tthis.show();\n\t\t}\n\t}\n\n\tdelete(){\n\t\treturn this._column.delete();\n\t}\n\n\tgetSubColumns(){\n\t\tvar output = [];\n\n\t\tif(this._column.columns.length){\n\t\t\tthis._column.columns.forEach(function(column){\n\t\t\t\toutput.push(column.getComponent());\n\t\t\t});\n\t\t}\n\n\t\treturn output;\n\t}\n\n\tgetParentColumn(){\n\t\treturn this._column.parent instanceof Column ? this._column.parent.getComponent() : false;\n\t}\n\n\t_getSelf(){\n\t\treturn this._column;\n\t}\n\n\tscrollTo(position, ifVisible){\n\t\treturn this._column.table.columnManager.scrollToColumn(this._column, position, ifVisible);\n\t}\n\n\tgetTable(){\n\t\treturn this._column.table;\n\t}\n\n\tmove(to, after){\n\t\tvar toColumn = this._column.table.columnManager.findColumn(to);\n\n\t\tif(toColumn){\n\t\t\tthis._column.table.columnManager.moveColumn(this._column, toColumn, after);\n\t\t}else {\n\t\t\tconsole.warn(\"Move Error - No matching column found:\", toColumn);\n\t\t}\n\t}\n\n\tgetNextColumn(){\n\t\tvar nextCol = this._column.nextColumn();\n\n\t\treturn nextCol ? nextCol.getComponent() : false;\n\t}\n\n\tgetPrevColumn(){\n\t\tvar prevCol = this._column.prevColumn();\n\n\t\treturn prevCol ? prevCol.getComponent() : false;\n\t}\n\n\tupdateDefinition(updates){\n\t\treturn this._column.updateDefinition(updates);\n\t}\n\n\tgetWidth(){\n\t\treturn this._column.getWidth();\n\t}\n\n\tsetWidth(width){\n\t\tvar result;\n\n\t\tif(width === true){\n\t\t\tresult =  this._column.reinitializeWidth(true);\n\t\t}else {\n\t\t\tresult =  this._column.setWidth(width);\n\t\t}\n\n\t\tthis._column.table.columnManager.rerenderColumns(true);\n\n\t\treturn result;\n\t}\n}\n\nvar defaultColumnOptions = {\n\t\"title\": undefined,\n\t\"field\": undefined,\n\t\"columns\": undefined,\n\t\"visible\": undefined,\n\t\"hozAlign\": undefined,\n\t\"vertAlign\": undefined,\n\t\"width\": undefined,\n\t\"minWidth\": 40,\n\t\"maxWidth\": undefined,\n\t\"maxInitialWidth\": undefined,\n\t\"cssClass\": undefined,\n\t\"variableHeight\": undefined,\n\t\"headerVertical\": undefined,\n\t\"headerHozAlign\": undefined,\n\t\"headerWordWrap\": false,\n\t\"editableTitle\": undefined,\n};\n\nclass Column extends CoreFeature{\n\n\tconstructor(def, parent){\n\t\tsuper(parent.table);\n\n\t\tthis.definition = def; //column definition\n\t\tthis.parent = parent; //hold parent object\n\t\tthis.type = \"column\"; //type of element\n\t\tthis.columns = []; //child columns\n\t\tthis.cells = []; //cells bound to this column\n\t\tthis.element = this.createElement(); //column header element\n\t\tthis.contentElement = false;\n\t\tthis.titleHolderElement = false;\n\t\tthis.titleElement = false;\n\t\tthis.groupElement = this.createGroupElement(); //column group holder element\n\t\tthis.isGroup = false;\n\t\tthis.hozAlign = \"\"; //horizontal text alignment\n\t\tthis.vertAlign = \"\"; //vert text alignment\n\n\t\t//multi dimensional filed handling\n\t\tthis.field =\"\";\n\t\tthis.fieldStructure = \"\";\n\t\tthis.getFieldValue = \"\";\n\t\tthis.setFieldValue = \"\";\n\n\t\tthis.titleDownload = null;\n\t\tthis.titleFormatterRendered = false;\n\n\t\tthis.mapDefinitions();\n\n\t\tthis.setField(this.definition.field);\n\n\t\tthis.modules = {}; //hold module variables;\n\n\t\tthis.width = null; //column width\n\t\tthis.widthStyled = \"\"; //column width pre-styled to improve render efficiency\n\t\tthis.maxWidth = null; //column maximum width\n\t\tthis.maxWidthStyled = \"\"; //column maximum pre-styled to improve render efficiency\n\t\tthis.maxInitialWidth = null;\n\t\tthis.minWidth = null; //column minimum width\n\t\tthis.minWidthStyled = \"\"; //column minimum pre-styled to improve render efficiency\n\t\tthis.widthFixed = false; //user has specified a width for this column\n\n\t\tthis.visible = true; //default visible state\n\n\t\tthis.component = null;\n\n\t\t//initialize column\n\t\tif(this.definition.columns){\n\n\t\t\tthis.isGroup = true;\n\n\t\t\tthis.definition.columns.forEach((def, i) => {\n\t\t\t\tvar newCol = new Column(def, this);\n\t\t\t\tthis.attachColumn(newCol);\n\t\t\t});\n\n\t\t\tthis.checkColumnVisibility();\n\t\t}else {\n\t\t\tparent.registerColumnField(this);\n\t\t}\n\n\t\tthis._initialize();\n\t}\n\n\tcreateElement (){\n\t\tvar el = document.createElement(\"div\");\n\n\t\tel.classList.add(\"tabulator-col\");\n\t\tel.setAttribute(\"role\", \"columnheader\");\n\t\tel.setAttribute(\"aria-sort\", \"none\");\n\n\t\tswitch(this.table.options.columnHeaderVertAlign){\n\t\t\tcase \"middle\":\n\t\t\t\tel.style.justifyContent = \"center\";\n\t\t\t\tbreak;\n\t\t\tcase \"bottom\":\n\t\t\t\tel.style.justifyContent = \"flex-end\";\n\t\t\t\tbreak;\n\t\t}\n\n\t\treturn el;\n\t}\n\n\tcreateGroupElement (){\n\t\tvar el = document.createElement(\"div\");\n\n\t\tel.classList.add(\"tabulator-col-group-cols\");\n\n\t\treturn el;\n\t}\n\n\tmapDefinitions(){\n\t\tvar defaults = this.table.options.columnDefaults;\n\n\t\t//map columnDefaults onto column definitions\n\t\tif(defaults){\n\t\t\tfor(let key in defaults){\n\t\t\t\tif(typeof this.definition[key] === \"undefined\"){\n\t\t\t\t\tthis.definition[key] = defaults[key];\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tthis.definition = this.table.columnManager.optionsList.generate(Column.defaultOptionList, this.definition);\n\t}\n\n\tcheckDefinition(){\n\t\tObject.keys(this.definition).forEach((key) => {\n\t\t\tif(Column.defaultOptionList.indexOf(key) === -1){\n\t\t\t\tconsole.warn(\"Invalid column definition option in '\" + (this.field || this.definition.title) + \"' column:\", key);\n\t\t\t}\n\t\t});\n\t}\n\n\tsetField(field){\n\t\tthis.field = field;\n\t\tthis.fieldStructure = field ? (this.table.options.nestedFieldSeparator ? field.split(this.table.options.nestedFieldSeparator) : [field]) : [];\n\t\tthis.getFieldValue = this.fieldStructure.length > 1 ? this._getNestedData : this._getFlatData;\n\t\tthis.setFieldValue = this.fieldStructure.length > 1 ? this._setNestedData : this._setFlatData;\n\t}\n\n\t//register column position with column manager\n\tregisterColumnPosition(column){\n\t\tthis.parent.registerColumnPosition(column);\n\t}\n\n\t//register column position with column manager\n\tregisterColumnField(column){\n\t\tthis.parent.registerColumnField(column);\n\t}\n\n\t//trigger position registration\n\treRegisterPosition(){\n\t\tif(this.isGroup){\n\t\t\tthis.columns.forEach(function(column){\n\t\t\t\tcolumn.reRegisterPosition();\n\t\t\t});\n\t\t}else {\n\t\t\tthis.registerColumnPosition(this);\n\t\t}\n\t}\n\n\t//build header element\n\t_initialize(){\n\t\tvar def = this.definition;\n\n\t\twhile(this.element.firstChild) this.element.removeChild(this.element.firstChild);\n\n\t\tif(def.headerVertical){\n\t\t\tthis.element.classList.add(\"tabulator-col-vertical\");\n\n\t\t\tif(def.headerVertical === \"flip\"){\n\t\t\t\tthis.element.classList.add(\"tabulator-col-vertical-flip\");\n\t\t\t}\n\t\t}\n\n\t\tthis.contentElement = this._buildColumnHeaderContent();\n\n\t\tthis.element.appendChild(this.contentElement);\n\n\t\tif(this.isGroup){\n\t\t\tthis._buildGroupHeader();\n\t\t}else {\n\t\t\tthis._buildColumnHeader();\n\t\t}\n\n\t\tthis.dispatch(\"column-init\", this);\n\t}\n\n\t//build header element for header\n\t_buildColumnHeader(){\n\t\tvar def = this.definition;\n\n\t\tthis.dispatch(\"column-layout\", this);\n\n\t\t//set column visibility\n\t\tif(typeof def.visible != \"undefined\"){\n\t\t\tif(def.visible){\n\t\t\t\tthis.show(true);\n\t\t\t}else {\n\t\t\t\tthis.hide(true);\n\t\t\t}\n\t\t}\n\n\t\t//assign additional css classes to column header\n\t\tif(def.cssClass){\n\t\t\tvar classNames = def.cssClass.split(\" \");\n\t\t\tclassNames.forEach((className) => {\n\t\t\t\tthis.element.classList.add(className);\n\t\t\t});\n\t\t}\n\n\t\tif(def.field){\n\t\t\tthis.element.setAttribute(\"tabulator-field\", def.field);\n\t\t}\n\n\t\t//set min width if present\n\t\tthis.setMinWidth(parseInt(def.minWidth));\n\n\t\tif (def.maxInitialWidth) {\n\t\t\tthis.maxInitialWidth = parseInt(def.maxInitialWidth);\n\t\t}\n\t\t\n\t\tif(def.maxWidth){\n\t\t\tthis.setMaxWidth(parseInt(def.maxWidth));\n\t\t}\n\n\t\tthis.reinitializeWidth();\n\n\t\t//set horizontal text alignment\n\t\tthis.hozAlign = this.definition.hozAlign;\n\t\tthis.vertAlign = this.definition.vertAlign;\n\n\t\tthis.titleElement.style.textAlign = this.definition.headerHozAlign;\n\t}\n\n\t_buildColumnHeaderContent(){\n\t\tvar contentElement = document.createElement(\"div\");\n\t\tcontentElement.classList.add(\"tabulator-col-content\");\n\n\t\tthis.titleHolderElement = document.createElement(\"div\");\n\t\tthis.titleHolderElement.classList.add(\"tabulator-col-title-holder\");\n\n\t\tcontentElement.appendChild(this.titleHolderElement);\n\n\t\tthis.titleElement = this._buildColumnHeaderTitle();\n\n\t\tthis.titleHolderElement.appendChild(this.titleElement);\n\n\t\treturn contentElement;\n\t}\n\n\t//build title element of column\n\t_buildColumnHeaderTitle(){\n\t\tvar def = this.definition;\n\n\t\tvar titleHolderElement = document.createElement(\"div\");\n\t\ttitleHolderElement.classList.add(\"tabulator-col-title\");\n\t\t\n\t\tif(def.headerWordWrap){\n\t\t\ttitleHolderElement.classList.add(\"tabulator-col-title-wrap\");\n\t\t}\n\n\t\tif(def.editableTitle){\n\t\t\tvar titleElement = document.createElement(\"input\");\n\t\t\ttitleElement.classList.add(\"tabulator-title-editor\");\n\n\t\t\ttitleElement.addEventListener(\"click\", (e) => {\n\t\t\t\te.stopPropagation();\n\t\t\t\ttitleElement.focus();\n\t\t\t});\n\n\t\t\ttitleElement.addEventListener(\"mousedown\", (e) => {\n\t\t\t\te.stopPropagation();\n\t\t\t});\n\n\t\t\ttitleElement.addEventListener(\"change\", () => {\n\t\t\t\tdef.title = titleElement.value;\n\t\t\t\tthis.dispatchExternal(\"columnTitleChanged\", this.getComponent());\n\t\t\t});\n\n\t\t\ttitleHolderElement.appendChild(titleElement);\n\n\t\t\tif(def.field){\n\t\t\t\tthis.langBind(\"columns|\" + def.field, (text) => {\n\t\t\t\t\ttitleElement.value = text || (def.title || \"&nbsp;\");\n\t\t\t\t});\n\t\t\t}else {\n\t\t\t\ttitleElement.value  = def.title || \"&nbsp;\";\n\t\t\t}\n\n\t\t}else {\n\t\t\tif(def.field){\n\t\t\t\tthis.langBind(\"columns|\" + def.field, (text) => {\n\t\t\t\t\tthis._formatColumnHeaderTitle(titleHolderElement, text || (def.title || \"&nbsp;\"));\n\t\t\t\t});\n\t\t\t}else {\n\t\t\t\tthis._formatColumnHeaderTitle(titleHolderElement, def.title || \"&nbsp;\");\n\t\t\t}\n\t\t}\n\n\t\treturn titleHolderElement;\n\t}\n\n\t_formatColumnHeaderTitle(el, title){\n\t\tvar contents = this.chain(\"column-format\", [this, title, el], null, () => {\n\t\t\treturn title;\n\t\t});\n\n\t\tswitch(typeof contents){\n\t\t\tcase \"object\":\n\t\t\t\tif(contents instanceof Node){\n\t\t\t\t\tel.appendChild(contents);\n\t\t\t\t}else {\n\t\t\t\t\tel.innerHTML = \"\";\n\t\t\t\t\tconsole.warn(\"Format Error - Title formatter has returned a type of object, the only valid formatter object return is an instance of Node, the formatter returned:\", contents);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase \"undefined\":\n\t\t\t\tel.innerHTML = \"\";\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tel.innerHTML = contents;\n\t\t}\n\t}\n\n\t//build header element for column group\n\t_buildGroupHeader(){\n\t\tthis.element.classList.add(\"tabulator-col-group\");\n\t\tthis.element.setAttribute(\"role\", \"columngroup\");\n\t\tthis.element.setAttribute(\"aria-title\", this.definition.title);\n\n\t\t//asign additional css classes to column header\n\t\tif(this.definition.cssClass){\n\t\t\tvar classNames = this.definition.cssClass.split(\" \");\n\t\t\tclassNames.forEach((className) => {\n\t\t\t\tthis.element.classList.add(className);\n\t\t\t});\n\t\t}\n\n\t\tthis.titleElement.style.textAlign = this.definition.headerHozAlign;\n\n\t\tthis.element.appendChild(this.groupElement);\n\t}\n\n\t//flat field lookup\n\t_getFlatData(data){\n\t\treturn data[this.field];\n\t}\n\n\t//nested field lookup\n\t_getNestedData(data){\n\t\tvar dataObj = data,\n\t\tstructure = this.fieldStructure,\n\t\tlength = structure.length,\n\t\toutput;\n\n\t\tfor(let i = 0; i < length; i++){\n\n\t\t\tdataObj = dataObj[structure[i]];\n\n\t\t\toutput = dataObj;\n\n\t\t\tif(!dataObj){\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\n\t\treturn output;\n\t}\n\n\t//flat field set\n\t_setFlatData(data, value){\n\t\tif(this.field){\n\t\t\tdata[this.field] = value;\n\t\t}\n\t}\n\n\t//nested field set\n\t_setNestedData(data, value){\n\t\tvar dataObj = data,\n\t\tstructure = this.fieldStructure,\n\t\tlength = structure.length;\n\n\t\tfor(let i = 0; i < length; i++){\n\n\t\t\tif(i == length -1){\n\t\t\t\tdataObj[structure[i]] = value;\n\t\t\t}else {\n\t\t\t\tif(!dataObj[structure[i]]){\n\t\t\t\t\tif(typeof value !== \"undefined\"){\n\t\t\t\t\t\tdataObj[structure[i]] = {};\n\t\t\t\t\t}else {\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\tdataObj = dataObj[structure[i]];\n\t\t\t}\n\t\t}\n\t}\n\n\t//attach column to this group\n\tattachColumn(column){\n\t\tif(this.groupElement){\n\t\t\tthis.columns.push(column);\n\t\t\tthis.groupElement.appendChild(column.getElement());\n\n\t\t\tcolumn.columnRendered();\n\t\t}else {\n\t\t\tconsole.warn(\"Column Warning - Column being attached to another column instead of column group\");\n\t\t}\n\t}\n\n\t//vertically align header in column\n\tverticalAlign(alignment, height){\n\n\t\t//calculate height of column header and group holder element\n\t\tvar parentHeight = this.parent.isGroup ? this.parent.getGroupElement().clientHeight : (height || this.parent.getHeadersElement().clientHeight);\n\t\t// var parentHeight = this.parent.isGroup ? this.parent.getGroupElement().clientHeight : this.parent.getHeadersElement().clientHeight;\n\n\t\tthis.element.style.height = parentHeight + \"px\";\n\n\t\tthis.dispatch(\"column-height\", this, this.element.style.height);\n\n\t\tif(this.isGroup){\n\t\t\tthis.groupElement.style.minHeight = (parentHeight - this.contentElement.offsetHeight) + \"px\";\n\t\t}\n\n\t\t//vertically align cell contents\n\t\t// if(!this.isGroup && alignment !== \"top\"){\n\t\t// \tif(alignment === \"bottom\"){\n\t\t// \t\tthis.element.style.paddingTop = (this.element.clientHeight - this.contentElement.offsetHeight) + \"px\";\n\t\t// \t}else{\n\t\t// \t\tthis.element.style.paddingTop = ((this.element.clientHeight - this.contentElement.offsetHeight) / 2) + \"px\";\n\t\t// \t}\n\t\t// }\n\n\t\tthis.columns.forEach(function(column){\n\t\t\tcolumn.verticalAlign(alignment);\n\t\t});\n\t}\n\n\t//clear vertical alignment\n\tclearVerticalAlign(){\n\t\tthis.element.style.paddingTop = \"\";\n\t\tthis.element.style.height = \"\";\n\t\tthis.element.style.minHeight = \"\";\n\t\tthis.groupElement.style.minHeight = \"\";\n\n\t\tthis.columns.forEach(function(column){\n\t\t\tcolumn.clearVerticalAlign();\n\t\t});\n\n\t\tthis.dispatch(\"column-height\", this, \"\");\n\t}\n\n\t//// Retrieve Column Information ////\n\t//return column header element\n\tgetElement(){\n\t\treturn this.element;\n\t}\n\n\t//return column group element\n\tgetGroupElement(){\n\t\treturn this.groupElement;\n\t}\n\n\t//return field name\n\tgetField(){\n\t\treturn this.field;\n\t}\n\n\tgetTitleDownload() {\n\t\treturn this.titleDownload;\n\t}\n\n\t//return the first column in a group\n\tgetFirstColumn(){\n\t\tif(!this.isGroup){\n\t\t\treturn this;\n\t\t}else {\n\t\t\tif(this.columns.length){\n\t\t\t\treturn this.columns[0].getFirstColumn();\n\t\t\t}else {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t}\n\n\t//return the last column in a group\n\tgetLastColumn(){\n\t\tif(!this.isGroup){\n\t\t\treturn this;\n\t\t}else {\n\t\t\tif(this.columns.length){\n\t\t\t\treturn this.columns[this.columns.length -1].getLastColumn();\n\t\t\t}else {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t}\n\n\t//return all columns in a group\n\tgetColumns(traverse){\n\t\tvar columns = [];\n\n\t\tif(traverse){\n\t\t\tthis.columns.forEach((column) => {\n\t\t\t\tcolumns.push(column);\n\t\t\t\t\t\n\t\t\t\tcolumns = columns.concat(column.getColumns(true));\n\t\t\t});\n\t\t}else {\n\t\t\tcolumns = this.columns;\n\t\t}\n\t\t\n\t\treturn columns;\n\t}\n\n\t//return all columns in a group\n\tgetCells(){\n\t\treturn this.cells;\n\t}\n\n\t//retrieve the top column in a group of columns\n\tgetTopColumn(){\n\t\tif(this.parent.isGroup){\n\t\t\treturn this.parent.getTopColumn();\n\t\t}else {\n\t\t\treturn this;\n\t\t}\n\t}\n\n\t//return column definition object\n\tgetDefinition(updateBranches){\n\t\tvar colDefs = [];\n\n\t\tif(this.isGroup && updateBranches){\n\t\t\tthis.columns.forEach(function(column){\n\t\t\t\tcolDefs.push(column.getDefinition(true));\n\t\t\t});\n\n\t\t\tthis.definition.columns = colDefs;\n\t\t}\n\n\t\treturn this.definition;\n\t}\n\n\t//////////////////// Actions ////////////////////\n\tcheckColumnVisibility(){\n\t\tvar visible = false;\n\n\t\tthis.columns.forEach(function(column){\n\t\t\tif(column.visible){\n\t\t\t\tvisible = true;\n\t\t\t}\n\t\t});\n\n\t\tif(visible){\n\t\t\tthis.show();\n\t\t\tthis.dispatchExternal(\"columnVisibilityChanged\", this.getComponent(), false);\n\t\t}else {\n\t\t\tthis.hide();\n\t\t}\n\t}\n\n\t//show column\n\tshow(silent, responsiveToggle){\n\t\tif(!this.visible){\n\t\t\tthis.visible = true;\n\n\t\t\tthis.element.style.display = \"\";\n\n\t\t\tif(this.parent.isGroup){\n\t\t\t\tthis.parent.checkColumnVisibility();\n\t\t\t}\n\n\t\t\tthis.cells.forEach(function(cell){\n\t\t\t\tcell.show();\n\t\t\t});\n\n\t\t\tif(!this.isGroup && this.width === null){\n\t\t\t\tthis.reinitializeWidth();\n\t\t\t}\n\n\t\t\tthis.table.columnManager.verticalAlignHeaders();\n\n\t\t\tthis.dispatch(\"column-show\", this, responsiveToggle);\n\n\t\t\tif(!silent){\n\t\t\t\tthis.dispatchExternal(\"columnVisibilityChanged\", this.getComponent(), true);\n\t\t\t}\n\n\t\t\tif(this.parent.isGroup){\n\t\t\t\tthis.parent.matchChildWidths();\n\t\t\t}\n\n\t\t\tif(!this.silent){\n\t\t\t\tthis.table.columnManager.rerenderColumns();\n\t\t\t}\n\t\t}\n\t}\n\n\t//hide column\n\thide(silent, responsiveToggle){\n\t\tif(this.visible){\n\t\t\tthis.visible = false;\n\n\t\t\tthis.element.style.display = \"none\";\n\n\t\t\tthis.table.columnManager.verticalAlignHeaders();\n\n\t\t\tif(this.parent.isGroup){\n\t\t\t\tthis.parent.checkColumnVisibility();\n\t\t\t}\n\n\t\t\tthis.cells.forEach(function(cell){\n\t\t\t\tcell.hide();\n\t\t\t});\n\n\t\t\tthis.dispatch(\"column-hide\", this, responsiveToggle);\n\n\t\t\tif(!silent){\n\t\t\t\tthis.dispatchExternal(\"columnVisibilityChanged\", this.getComponent(), false);\n\t\t\t}\n\n\t\t\tif(this.parent.isGroup){\n\t\t\t\tthis.parent.matchChildWidths();\n\t\t\t}\n\n\t\t\tif(!this.silent){\n\t\t\t\tthis.table.columnManager.rerenderColumns();\n\t\t\t}\n\t\t}\n\t}\n\n\tmatchChildWidths(){\n\t\tvar childWidth = 0;\n\n\t\tif(this.contentElement && this.columns.length){\n\t\t\tthis.columns.forEach(function(column){\n\t\t\t\tif(column.visible){\n\t\t\t\t\tchildWidth += column.getWidth();\n\t\t\t\t}\n\t\t\t});\n\n\t\t\tthis.contentElement.style.maxWidth = (childWidth - 1) + \"px\";\n\n\t\t\tif(this.parent.isGroup){\n\t\t\t\tthis.parent.matchChildWidths();\n\t\t\t}\n\t\t}\n\t}\n\n\tremoveChild(child){\n\t\tvar index = this.columns.indexOf(child);\n\n\t\tif(index > -1){\n\t\t\tthis.columns.splice(index, 1);\n\t\t}\n\n\t\tif(!this.columns.length){\n\t\t\tthis.delete();\n\t\t}\n\t}\n\n\tsetWidth(width){\n\t\tthis.widthFixed = true;\n\t\tthis.setWidthActual(width);\n\t}\n\n\tsetWidthActual(width){\n\t\tif(isNaN(width)){\n\t\t\twidth = Math.floor((this.table.element.clientWidth/100) * parseInt(width));\n\t\t}\n\n\t\twidth = Math.max(this.minWidth, width);\n\n\t\tif(this.maxWidth){\n\t\t\twidth = Math.min(this.maxWidth, width);\n\t\t}\n\n\t\tthis.width = width;\n\t\tthis.widthStyled = width ? width + \"px\" : \"\";\n\n\t\tthis.element.style.width = this.widthStyled;\n\n\t\tif(!this.isGroup){\n\t\t\tthis.cells.forEach(function(cell){\n\t\t\t\tcell.setWidth();\n\t\t\t});\n\t\t}\n\n\t\tif(this.parent.isGroup){\n\t\t\tthis.parent.matchChildWidths();\n\t\t}\n\n\t\tthis.dispatch(\"column-width\", this);\n\t}\n\n\tcheckCellHeights(){\n\t\tvar rows = [];\n\n\t\tthis.cells.forEach(function(cell){\n\t\t\tif(cell.row.heightInitialized){\n\t\t\t\tif(cell.row.getElement().offsetParent !== null){\n\t\t\t\t\trows.push(cell.row);\n\t\t\t\t\tcell.row.clearCellHeight();\n\t\t\t\t}else {\n\t\t\t\t\tcell.row.heightInitialized = false;\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\n\t\trows.forEach(function(row){\n\t\t\trow.calcHeight();\n\t\t});\n\n\t\trows.forEach(function(row){\n\t\t\trow.setCellHeight();\n\t\t});\n\t}\n\n\tgetWidth(){\n\t\tvar width = 0;\n\n\t\tif(this.isGroup){\n\t\t\tthis.columns.forEach(function(column){\n\t\t\t\tif(column.visible){\n\t\t\t\t\twidth += column.getWidth();\n\t\t\t\t}\n\t\t\t});\n\t\t}else {\n\t\t\twidth = this.width;\n\t\t}\n\n\t\treturn width;\n\t}\n\n\tgetLeftOffset(){\n\t\tvar offset = this.element.offsetLeft;\n\n\t\tif(this.parent.isGroup){\n\t\t\toffset += this.parent.getLeftOffset();\n\t\t}\n\n\t\treturn offset;\n\t}\n\n\tgetHeight(){\n\t\treturn Math.ceil(this.element.getBoundingClientRect().height);\n\t}\n\n\tsetMinWidth(minWidth){\n\t\tif(this.maxWidth && minWidth > this.maxWidth){\n\t\t\tminWidth = this.maxWidth;\n\n\t\t\tconsole.warn(\"the minWidth (\"+ minWidth + \"px) for column '\" + this.field + \"' cannot be bigger that its maxWidth (\"+ this.maxWidthStyled + \")\");\n\t\t}\n\n\t\tthis.minWidth = minWidth;\n\t\tthis.minWidthStyled = minWidth ? minWidth + \"px\" : \"\";\n\n\t\tthis.element.style.minWidth = this.minWidthStyled;\n\n\t\tthis.cells.forEach(function(cell){\n\t\t\tcell.setMinWidth();\n\t\t});\n\t}\n\n\tsetMaxWidth(maxWidth){\n\t\tif(this.minWidth && maxWidth < this.minWidth){\n\t\t\tmaxWidth = this.minWidth;\n\n\t\t\tconsole.warn(\"the maxWidth (\"+ maxWidth + \"px) for column '\" + this.field + \"' cannot be smaller that its minWidth (\"+ this.minWidthStyled + \")\");\n\t\t}\n\n\t\tthis.maxWidth = maxWidth;\n\t\tthis.maxWidthStyled = maxWidth ? maxWidth + \"px\" : \"\";\n\n\t\tthis.element.style.maxWidth = this.maxWidthStyled;\n\n\t\tthis.cells.forEach(function(cell){\n\t\t\tcell.setMaxWidth();\n\t\t});\n\t}\n\n\tdelete(){\n\t\treturn new Promise((resolve, reject) => {\n\t\t\tif(this.isGroup){\n\t\t\t\tthis.columns.forEach(function(column){\n\t\t\t\t\tcolumn.delete();\n\t\t\t\t});\n\t\t\t}\n\n\t\t\tthis.dispatch(\"column-delete\", this);\n\n\t\t\tvar cellCount = this.cells.length;\n\n\t\t\tfor(let i = 0; i < cellCount; i++){\n\t\t\t\tthis.cells[0].delete();\n\t\t\t}\n\n\t\t\tif(this.element.parentNode){\n\t\t\t\tthis.element.parentNode.removeChild(this.element);\n\t\t\t}\n\n\t\t\tthis.element = false;\n\t\t\tthis.contentElement = false;\n\t\t\tthis.titleElement = false;\n\t\t\tthis.groupElement = false;\n\n\t\t\tif(this.parent.isGroup){\n\t\t\t\tthis.parent.removeChild(this);\n\t\t\t}\n\n\t\t\tthis.table.columnManager.deregisterColumn(this);\n\n\t\t\tthis.table.columnManager.rerenderColumns(true);\n\n\t\t\tthis.dispatch(\"column-deleted\", this);\n\n\t\t\tresolve();\n\t\t});\n\t}\n\n\tcolumnRendered(){\n\t\tif(this.titleFormatterRendered){\n\t\t\tthis.titleFormatterRendered();\n\t\t}\n\n\t\tthis.dispatch(\"column-rendered\", this);\n\t}\n\n\t//////////////// Cell Management /////////////////\n\t//generate cell for this column\n\tgenerateCell(row){\n\t\tvar cell = new Cell(this, row);\n\n\t\tthis.cells.push(cell);\n\n\t\treturn cell;\n\t}\n\n\tnextColumn(){\n\t\tvar index = this.table.columnManager.findColumnIndex(this);\n\t\treturn index > -1 ? this._nextVisibleColumn(index + 1) : false;\n\t}\n\n\t_nextVisibleColumn(index){\n\t\tvar column = this.table.columnManager.getColumnByIndex(index);\n\t\treturn !column || column.visible ? column : this._nextVisibleColumn(index + 1);\n\t}\n\n\tprevColumn(){\n\t\tvar index = this.table.columnManager.findColumnIndex(this);\n\t\treturn index > -1 ? this._prevVisibleColumn(index - 1) : false;\n\t}\n\n\t_prevVisibleColumn(index){\n\t\tvar column = this.table.columnManager.getColumnByIndex(index);\n\t\treturn !column || column.visible ? column : this._prevVisibleColumn(index - 1);\n\t}\n\n\treinitializeWidth(force){\n\t\tthis.widthFixed = false;\n\n\t\t//set width if present\n\t\tif(typeof this.definition.width !== \"undefined\" && !force){\n\t\t\t// maxInitialWidth ignored here as width specified\n\t\t\tthis.setWidth(this.definition.width);\n\t\t}\n\n\t\tthis.dispatch(\"column-width-fit-before\", this);\n\n\t\tthis.fitToData(force);\n\n\t\tthis.dispatch(\"column-width-fit-after\", this);\n\t}\n\n\t//set column width to maximum cell width for non group columns\n\tfitToData(force){\n\t\tif(this.isGroup){\n\t\t\treturn;\n\t\t}\n\n\t\tif(!this.widthFixed){\n\t\t\tthis.element.style.width = \"\";\n\n\t\t\tthis.cells.forEach((cell) => {\n\t\t\t\tcell.clearWidth();\n\t\t\t});\n\t\t}\n\n\t\tvar maxWidth = this.element.offsetWidth;\n\n\t\tif(!this.width || !this.widthFixed){\n\t\t\tthis.cells.forEach((cell) => {\n\t\t\t\tvar width = cell.getWidth();\n\n\t\t\t\tif(width > maxWidth){\n\t\t\t\t\tmaxWidth = width;\n\t\t\t\t}\n\t\t\t});\n\n\t\t\tif(maxWidth){\n\t\t\t\tvar setTo = maxWidth + 1;\n\t\t\t\tif (this.maxInitialWidth && !force) {\n\t\t\t\t\tsetTo = Math.min(setTo, this.maxInitialWidth);\n\t\t\t\t}\n\t\t\t\tthis.setWidthActual(setTo);\n\t\t\t}\n\t\t}\n\t}\n\n\tupdateDefinition(updates){\n\t\tvar definition;\n\n\t\tif(!this.isGroup){\n\t\t\tif(!this.parent.isGroup){\n\t\t\t\tdefinition = Object.assign({}, this.getDefinition());\n\t\t\t\tdefinition = Object.assign(definition, updates);\n\n\t\t\t\treturn this.table.columnManager.addColumn(definition, false, this)\n\t\t\t\t\t.then((column) => {\n\n\t\t\t\t\t\tif(definition.field == this.field){\n\t\t\t\t\t\t\tthis.field = false; //clear field name to prevent deletion of duplicate column from arrays\n\t\t\t\t\t\t}\n\n\t\t\t\t\t\treturn this.delete()\n\t\t\t\t\t\t\t.then(() => {\n\t\t\t\t\t\t\t\treturn column.getComponent();\n\t\t\t\t\t\t\t});\n\n\t\t\t\t\t});\n\t\t\t}else {\n\t\t\t\tconsole.error(\"Column Update Error - The updateDefinition function is only available on ungrouped columns\");\n\t\t\t\treturn Promise.reject(\"Column Update Error - The updateDefinition function is only available on columns, not column groups\");\n\t\t\t}\n\t\t}else {\n\t\t\tconsole.error(\"Column Update Error - The updateDefinition function is only available on ungrouped columns\");\n\t\t\treturn Promise.reject(\"Column Update Error - The updateDefinition function is only available on columns, not column groups\");\n\t\t}\n\t}\n\n\tdeleteCell(cell){\n\t\tvar index = this.cells.indexOf(cell);\n\n\t\tif(index > -1){\n\t\t\tthis.cells.splice(index, 1);\n\t\t}\n\t}\n\n\t//////////////// Object Generation /////////////////\n\tgetComponent(){\n\t\tif(!this.component){\n\t\t\tthis.component = new ColumnComponent(this);\n\t\t}\n\n\t\treturn this.component;\n\t}\n\n\tgetPosition(){\n\t\treturn this.table.columnManager.getVisibleColumnsByIndex().indexOf(this) + 1;\n\t}\n}\n\nColumn.defaultOptionList = defaultColumnOptions;\n\n//public row object\nclass RowComponent {\n\n\tconstructor (row){\n\t\tthis._row = row;\n\n\t\treturn new Proxy(this, {\n\t\t\tget: function(target, name, receiver) {\n\t\t\t\tif (typeof target[name] !== \"undefined\") {\n\t\t\t\t\treturn target[name];\n\t\t\t\t}else {\n\t\t\t\t\treturn target._row.table.componentFunctionBinder.handle(\"row\", target._row, name);\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\t}\n\n\tgetData(transform){\n\t\treturn this._row.getData(transform);\n\t}\n\n\tgetElement(){\n\t\treturn this._row.getElement();\n\t}\n\n\tgetCells(){\n\t\tvar cells = [];\n\n\t\tthis._row.getCells().forEach(function(cell){\n\t\t\tcells.push(cell.getComponent());\n\t\t});\n\n\t\treturn cells;\n\t}\n\n\tgetCell(column){\n\t\tvar cell = this._row.getCell(column);\n\t\treturn cell ? cell.getComponent() : false;\n\t}\n\n\tgetIndex(){\n\t\treturn this._row.getData(\"data\")[this._row.table.options.index];\n\t}\n\n\tgetPosition(){\n\t\treturn this._row.getPosition();\n\t}\n\n\twatchPosition(callback){\n\t\treturn this._row.watchPosition(callback);\n\t}\n\n\tdelete(){\n\t\treturn this._row.delete();\n\t}\n\n\tscrollTo(position, ifVisible){\n\t\treturn this._row.table.rowManager.scrollToRow(this._row, position, ifVisible);\n\t}\n\n\tmove(to, after){\n\t\tthis._row.moveToRow(to, after);\n\t}\n\n\tupdate(data){\n\t\treturn this._row.updateData(data);\n\t}\n\n\tnormalizeHeight(){\n\t\tthis._row.normalizeHeight(true);\n\t}\n\n\t_getSelf(){\n\t\treturn this._row;\n\t}\n\n\treformat(){\n\t\treturn this._row.reinitialize();\n\t}\n\n\tgetTable(){\n\t\treturn this._row.table;\n\t}\n\n\tgetNextRow(){\n\t\tvar row = this._row.nextRow();\n\t\treturn row ? row.getComponent() : row;\n\t}\n\n\tgetPrevRow(){\n\t\tvar row = this._row.prevRow();\n\t\treturn row ? row.getComponent() : row;\n\t}\n}\n\nclass Row extends CoreFeature{\n\tconstructor (data, parent, type = \"row\"){\n\t\tsuper(parent.table);\n\t\t\n\t\tthis.parent = parent;\n\t\tthis.data = {};\n\t\tthis.type = type; //type of element\n\t\tthis.element = false;\n\t\tthis.modules = {}; //hold module variables;\n\t\tthis.cells = [];\n\t\tthis.height = 0; //hold element height\n\t\tthis.heightStyled = \"\"; //hold element height pre-styled to improve render efficiency\n\t\tthis.manualHeight = false; //user has manually set row height\n\t\tthis.outerHeight = 0; //hold elements outer height\n\t\tthis.initialized = false; //element has been rendered\n\t\tthis.heightInitialized = false; //element has resized cells to fit\n\t\tthis.position = 0; //store position of element in row list\n\t\tthis.positionWatchers = [];\n\t\t\n\t\tthis.component = null;\n\t\t\n\t\tthis.created = false;\n\t\t\n\t\tthis.setData(data);\n\t}\n\t\n\tcreate(){\n\t\tif(!this.created){\n\t\t\tthis.created = true;\n\t\t\tthis.generateElement();\n\t\t}\n\t}\n\t\n\tcreateElement (){\n\t\tvar el = document.createElement(\"div\");\n\t\t\n\t\tel.classList.add(\"tabulator-row\");\n\t\tel.setAttribute(\"role\", \"row\");\n\t\t\n\t\tthis.element = el;\n\t}\n\t\n\tgetElement(){\n\t\tthis.create();\n\t\treturn this.element;\n\t}\n\t\n\tdetachElement(){\n\t\tif (this.element && this.element.parentNode){\n\t\t\tthis.element.parentNode.removeChild(this.element);\n\t\t}\n\t}\n\t\n\tgenerateElement(){\n\t\tthis.createElement();\n\t\tthis.dispatch(\"row-init\", this);\n\t}\n\t\n\tgenerateCells(){\n\t\tthis.cells = this.table.columnManager.generateCells(this);\n\t}\n\t\n\t//functions to setup on first render\n\tinitialize(force, inFragment){\n\t\tthis.create();\n\t\t\n\t\tif(!this.initialized || force){\n\t\t\t\n\t\t\tthis.deleteCells();\n\t\t\t\n\t\t\twhile(this.element.firstChild) this.element.removeChild(this.element.firstChild);\n\t\t\t\n\t\t\tthis.dispatch(\"row-layout-before\", this);\n\t\t\t\n\t\t\tthis.generateCells();\n\t\t\t\n\t\t\tthis.initialized = true;\n\t\t\t\n\t\t\tthis.table.columnManager.renderer.renderRowCells(this, inFragment);\n\t\t\t\n\t\t\tif(force){\n\t\t\t\tthis.normalizeHeight();\n\t\t\t}\n\t\t\t\n\t\t\tthis.dispatch(\"row-layout\", this);\n\t\t\t\n\t\t\tif(this.table.options.rowFormatter){\n\t\t\t\tthis.table.options.rowFormatter(this.getComponent());\n\t\t\t}\n\t\t\t\n\t\t\tthis.dispatch(\"row-layout-after\", this);\n\t\t}else {\n\t\t\tthis.table.columnManager.renderer.rerenderRowCells(this, inFragment);\n\t\t}\n\t}\n\n\trendered(){\n\t\tthis.cells.forEach((cell) => {\n\t\t\tcell.cellRendered();\n\t\t});\n\t}\n\t\n\treinitializeHeight(){\n\t\tthis.heightInitialized = false;\n\t\t\n\t\tif(this.element && this.element.offsetParent !== null){\n\t\t\tthis.normalizeHeight(true);\n\t\t}\n\t}\n\n\tdeinitialize(){\n\t\tthis.initialized = false;\n\t}\n\t\n\tdeinitializeHeight(){\n\t\tthis.heightInitialized = false;\n\t}\n\t\n\treinitialize(children){\n\t\tthis.initialized = false;\n\t\tthis.heightInitialized = false;\n\t\t\n\t\tif(!this.manualHeight){\n\t\t\tthis.height = 0;\n\t\t\tthis.heightStyled = \"\";\n\t\t}\n\t\t\n\t\tif(this.element && this.element.offsetParent !== null){\n\t\t\tthis.initialize(true);\n\t\t}\n\t\t\n\t\tthis.dispatch(\"row-relayout\", this);\n\t}\n\t\n\t//get heights when doing bulk row style calcs in virtual DOM\n\tcalcHeight(force){\n\t\tvar maxHeight = 0,\n\t\tminHeight;\n\t\t\n\t\tif(this.table.options.rowHeight){\n\t\t\tthis.height = this.table.options.rowHeight;\n\t\t}else {\n\t\t\tminHeight = this.table.options.resizableRows ? this.element.clientHeight : 0;\n\t\t\t\n\t\t\tthis.cells.forEach(function(cell){\n\t\t\t\tvar height = cell.getHeight();\n\t\t\t\tif(height > maxHeight){\n\t\t\t\t\tmaxHeight = height;\n\t\t\t\t}\n\t\t\t});\n\t\t\t\n\t\t\tif(force){\n\t\t\t\tthis.height = Math.max(maxHeight, minHeight);\n\t\t\t}else {\n\t\t\t\tthis.height = this.manualHeight ? this.height : Math.max(maxHeight, minHeight);\n\t\t\t}\n\t\t}\n\t\t\n\t\tthis.heightStyled = this.height ? this.height + \"px\" : \"\";\n\t\tthis.outerHeight = this.element.offsetHeight;\n\t}\n\t\n\t//set of cells\n\tsetCellHeight(){\n\t\tthis.cells.forEach(function(cell){\n\t\t\tcell.setHeight();\n\t\t});\n\t\t\n\t\tthis.heightInitialized = true;\n\t}\n\t\n\tclearCellHeight(){\n\t\tthis.cells.forEach(function(cell){\n\t\t\tcell.clearHeight();\n\t\t});\n\t}\n\t\n\t//normalize the height of elements in the row\n\tnormalizeHeight(force){\n\t\tif(force && !this.table.options.rowHeight){\n\t\t\tthis.clearCellHeight();\n\t\t}\n\t\t\n\t\tthis.calcHeight(force);\n\t\t\n\t\tthis.setCellHeight();\n\t}\n\t\n\t//set height of rows\n\tsetHeight(height, force){\n\t\tif(this.height != height || force){\n\t\t\t\n\t\t\tthis.manualHeight = true;\n\t\t\t\n\t\t\tthis.height = height;\n\t\t\tthis.heightStyled = height ? height + \"px\" : \"\";\n\t\t\t\n\t\t\tthis.setCellHeight();\n\t\t\t\n\t\t\t// this.outerHeight = this.element.outerHeight();\n\t\t\tthis.outerHeight = this.element.offsetHeight;\n\t\t}\n\t}\n\t\n\t//return rows outer height\n\tgetHeight(){\n\t\treturn this.outerHeight;\n\t}\n\t\n\t//return rows outer Width\n\tgetWidth(){\n\t\treturn this.element.offsetWidth;\n\t}\n\t\n\t//////////////// Cell Management /////////////////\n\tdeleteCell(cell){\n\t\tvar index = this.cells.indexOf(cell);\n\t\t\n\t\tif(index > -1){\n\t\t\tthis.cells.splice(index, 1);\n\t\t}\n\t}\n\t\n\t//////////////// Data Management /////////////////\n\tsetData(data){\n\t\tthis.data = this.chain(\"row-data-init-before\", [this, data], undefined, data);\n\t\t\n\t\tthis.dispatch(\"row-data-init-after\", this);\n\t}\n\t\n\t//update the rows data\n\tupdateData(updatedData){\n\t\tvar visible = this.element && Helpers.elVisible(this.element),\n\t\ttempData = {},\n\t\tnewRowData;\n\t\t\n\t\treturn new Promise((resolve, reject) => {\n\t\t\t\n\t\t\tif(typeof updatedData === \"string\"){\n\t\t\t\tupdatedData = JSON.parse(updatedData);\n\t\t\t}\n\t\t\t\n\t\t\tthis.dispatch(\"row-data-save-before\", this);\n\t\t\t\n\t\t\tif(this.subscribed(\"row-data-changing\")){\n\t\t\t\ttempData = Object.assign(tempData, this.data);\n\t\t\t\ttempData = Object.assign(tempData, updatedData);\n\t\t\t}\n\t\t\t\n\t\t\tnewRowData = this.chain(\"row-data-changing\", [this, tempData, updatedData], null, updatedData);\n\t\t\t\n\t\t\t//set data\n\t\t\tfor (let attrname in newRowData) {\n\t\t\t\tthis.data[attrname] = newRowData[attrname];\n\t\t\t}\n\t\t\t\n\t\t\tthis.dispatch(\"row-data-save-after\", this);\n\t\t\t\n\t\t\t//update affected cells only\n\t\t\tfor (let attrname in updatedData) {\n\t\t\t\t\n\t\t\t\tlet columns = this.table.columnManager.getColumnsByFieldRoot(attrname);\n\t\t\t\t\n\t\t\t\tcolumns.forEach((column) => {\n\t\t\t\t\tlet cell = this.getCell(column.getField());\n\t\t\t\t\t\n\t\t\t\t\tif(cell){\n\t\t\t\t\t\tlet value = column.getFieldValue(newRowData);\n\t\t\t\t\t\tif(cell.getValue() !== value){\n\t\t\t\t\t\t\tcell.setValueProcessData(value);\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\tif(visible){\n\t\t\t\t\t\t\t\tcell.cellRendered();\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t}\n\t\t\t\n\t\t\t//Partial reinitialization if visible\n\t\t\tif(visible){\n\t\t\t\tthis.normalizeHeight(true);\n\t\t\t\t\n\t\t\t\tif(this.table.options.rowFormatter){\n\t\t\t\t\tthis.table.options.rowFormatter(this.getComponent());\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tthis.initialized = false;\n\t\t\t\tthis.height = 0;\n\t\t\t\tthis.heightStyled = \"\";\n\t\t\t}\n\t\t\t\n\t\t\tthis.dispatch(\"row-data-changed\", this, visible, updatedData);\n\t\t\t\n\t\t\t//this.reinitialize();\n\t\t\t\n\t\t\tthis.dispatchExternal(\"rowUpdated\", this.getComponent());\n\t\t\t\n\t\t\tif(this.subscribedExternal(\"dataChanged\")){\n\t\t\t\tthis.dispatchExternal(\"dataChanged\", this.table.rowManager.getData());\n\t\t\t}\n\t\t\t\n\t\t\tresolve();\n\t\t});\n\t}\n\t\n\tgetData(transform){\n\t\tif(transform){\n\t\t\treturn this.chain(\"row-data-retrieve\", [this, transform], null, this.data);\n\t\t}\n\t\t\n\t\treturn this.data;\n\t}\n\t\n\tgetCell(column){\n\t\tvar match = false;\n\t\t\n\t\tcolumn = this.table.columnManager.findColumn(column);\n\t\t\n\t\tif(!this.initialized && this.cells.length === 0){\n\t\t\tthis.generateCells();\n\t\t}\n\t\t\n\t\tmatch = this.cells.find(function(cell){\n\t\t\treturn cell.column === column;\n\t\t});\n\t\t\n\t\treturn match;\n\t}\n\t\n\tgetCellIndex(findCell){\n\t\treturn this.cells.findIndex(function(cell){\n\t\t\treturn cell === findCell;\n\t\t});\n\t}\n\t\n\tfindCell(subject){\n\t\treturn this.cells.find((cell) => {\n\t\t\treturn cell.element === subject;\n\t\t});\n\t}\n\t\n\tgetCells(){\n\t\tif(!this.initialized && this.cells.length === 0){\n\t\t\tthis.generateCells();\n\t\t}\n\t\t\n\t\treturn this.cells;\n\t}\n\t\n\tnextRow(){\n\t\tvar row = this.table.rowManager.nextDisplayRow(this, true);\n\t\treturn row || false;\n\t}\n\t\n\tprevRow(){\n\t\tvar row = this.table.rowManager.prevDisplayRow(this, true);\n\t\treturn row || false;\n\t}\n\t\n\tmoveToRow(to, before){\n\t\tvar toRow = this.table.rowManager.findRow(to);\n\t\t\n\t\tif(toRow){\n\t\t\tthis.table.rowManager.moveRowActual(this, toRow, !before);\n\t\t\tthis.table.rowManager.refreshActiveData(\"display\", false, true);\n\t\t}else {\n\t\t\tconsole.warn(\"Move Error - No matching row found:\", to);\n\t\t}\n\t}\n\t\n\t///////////////////// Actions  /////////////////////\n\tdelete(){\n\t\tthis.dispatch(\"row-delete\", this);\n\t\t\n\t\tthis.deleteActual();\n\t\t\n\t\treturn Promise.resolve();\n\t}\n\t\n\tdeleteActual(blockRedraw){\n\t\tthis.detachModules();\n\t\t\n\t\tthis.table.rowManager.deleteRow(this, blockRedraw);\n\t\t\n\t\tthis.deleteCells();\n\t\t\n\t\tthis.initialized = false;\n\t\tthis.heightInitialized = false;\n\t\tthis.element = false;\n\t\t\n\t\tthis.dispatch(\"row-deleted\", this);\n\t}\n\t\n\tdetachModules(){\n\t\tthis.dispatch(\"row-deleting\", this);\n\t}\n\t\n\tdeleteCells(){\n\t\tvar cellCount = this.cells.length;\n\t\t\n\t\tfor(let i = 0; i < cellCount; i++){\n\t\t\tthis.cells[0].delete();\n\t\t}\n\t}\n\t\n\twipe(){\n\t\tthis.detachModules();\n\t\tthis.deleteCells();\n\t\t\n\t\tif(this.element){\n\t\t\twhile(this.element.firstChild) this.element.removeChild(this.element.firstChild);\n\t\t\t\n\t\t\tif(this.element.parentNode){\n\t\t\t\tthis.element.parentNode.removeChild(this.element);\n\t\t\t}\n\t\t}\n\t\t\n\t\tthis.element = false;\n\t\tthis.modules = {};\n\t}\n\n\tisDisplayed(){\n\t\treturn this.table.rowManager.getDisplayRows().includes(this);\n\t}\n\n\tgetPosition(){\n\t\treturn this.isDisplayed() ? this.position : false;\n\t}\n\n\tsetPosition(position){\n\t\tif(position != this.position){\n\t\t\tthis.position = position;\n\n\t\t\tthis.positionWatchers.forEach((callback) => {\n\t\t\t\tcallback(this.position);\n\t\t\t});\n\t\t}\n\t}\n\n\twatchPosition(callback){\n\t\tthis.positionWatchers.push(callback);\n\n\t\tcallback(this.position);\n\t}\n\t\n\tgetGroup(){\n\t\treturn this.modules.group || false;\n\t}\n\t\n\t//////////////// Object Generation /////////////////\n\tgetComponent(){\n\t\tif(!this.component){\n\t\t\tthis.component = new RowComponent(this);\n\t\t}\n\t\t\n\t\treturn this.component;\n\t}\n}\n\nvar defaultCalculations = {\n\t\"avg\":function(values, data, calcParams){\n\t\tvar output = 0,\n\t\tprecision = typeof calcParams.precision !== \"undefined\" ? calcParams.precision : 2;\n\n\t\tif(values.length){\n\t\t\toutput = values.reduce(function(sum, value){\n\t\t\t\treturn Number(sum) + Number(value);\n\t\t\t});\n\n\t\t\toutput = output / values.length;\n\n\t\t\toutput = precision !== false ? output.toFixed(precision) : output;\n\t\t}\n\n\t\treturn parseFloat(output).toString();\n\t},\n\t\"max\":function(values, data, calcParams){\n\t\tvar output = null,\n\t\tprecision = typeof calcParams.precision !== \"undefined\" ? calcParams.precision : false;\n\n\t\tvalues.forEach(function(value){\n\n\t\t\tvalue = Number(value);\n\n\t\t\tif(value > output || output === null){\n\t\t\t\toutput = value;\n\t\t\t}\n\t\t});\n\n\t\treturn output !== null ? (precision !== false ? output.toFixed(precision) : output) : \"\";\n\t},\n\t\"min\":function(values, data, calcParams){\n\t\tvar output = null,\n\t\tprecision = typeof calcParams.precision !== \"undefined\" ? calcParams.precision : false;\n\n\t\tvalues.forEach(function(value){\n\n\t\t\tvalue = Number(value);\n\n\t\t\tif(value < output || output === null){\n\t\t\t\toutput = value;\n\t\t\t}\n\t\t});\n\n\t\treturn output !== null ? (precision !== false ? output.toFixed(precision) : output) : \"\";\n\t},\n\t\"sum\":function(values, data, calcParams){\n\t\tvar output = 0,\n\t\tprecision = typeof calcParams.precision !== \"undefined\" ? calcParams.precision : false;\n\n\t\tif(values.length){\n\t\t\tvalues.forEach(function(value){\n\t\t\t\tvalue = Number(value);\n\n\t\t\t\toutput += !isNaN(value) ? Number(value) : 0;\n\t\t\t});\n\t\t}\n\n\t\treturn precision !== false ? output.toFixed(precision) : output;\n\t},\n\t\"concat\":function(values, data, calcParams){\n\t\tvar output = 0;\n\n\t\tif(values.length){\n\t\t\toutput = values.reduce(function(sum, value){\n\t\t\t\treturn String(sum) + String(value);\n\t\t\t});\n\t\t}\n\n\t\treturn output;\n\t},\n\t\"count\":function(values, data, calcParams){\n\t\tvar output = 0;\n\n\t\tif(values.length){\n\t\t\tvalues.forEach(function(value){\n\t\t\t\tif(value){\n\t\t\t\t\toutput ++;\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\n\t\treturn output;\n\t},\n\t\"unique\":function(values, data, calcParams){\n\t\tvar unique = values.filter((value, index) => {\n\t\t\treturn (values || value === 0) && values.indexOf(value) === index;\n\t\t});\n\n\t\treturn unique.length;\n\t},\n};\n\nclass ColumnCalcs extends Module{\n\t\n\tconstructor(table){\n\t\tsuper(table);\n\t\t\n\t\tthis.topCalcs = [];\n\t\tthis.botCalcs = [];\n\t\tthis.genColumn = false;\n\t\tthis.topElement = this.createElement();\n\t\tthis.botElement = this.createElement();\n\t\tthis.topRow = false;\n\t\tthis.botRow = false;\n\t\tthis.topInitialized = false;\n\t\tthis.botInitialized = false;\n\t\t\n\t\tthis.blocked = false;\n\t\tthis.recalcAfterBlock = false;\n\t\t\n\t\tthis.registerTableOption(\"columnCalcs\", true);\n\t\t\n\t\tthis.registerColumnOption(\"topCalc\");\n\t\tthis.registerColumnOption(\"topCalcParams\");\n\t\tthis.registerColumnOption(\"topCalcFormatter\");\n\t\tthis.registerColumnOption(\"topCalcFormatterParams\");\n\t\tthis.registerColumnOption(\"bottomCalc\");\n\t\tthis.registerColumnOption(\"bottomCalcParams\");\n\t\tthis.registerColumnOption(\"bottomCalcFormatter\");\n\t\tthis.registerColumnOption(\"bottomCalcFormatterParams\");\n\t}\n\t\n\tcreateElement (){\n\t\tvar el = document.createElement(\"div\");\n\t\tel.classList.add(\"tabulator-calcs-holder\");\n\t\treturn el;\n\t}\n\t\n\tinitialize(){\n\t\tthis.genColumn = new Column({field:\"value\"}, this);\n\t\t\n\t\tthis.subscribe(\"cell-value-changed\", this.cellValueChanged.bind(this));\n\t\tthis.subscribe(\"column-init\", this.initializeColumnCheck.bind(this));\n\t\tthis.subscribe(\"row-deleted\", this.rowsUpdated.bind(this));\n\t\tthis.subscribe(\"scroll-horizontal\", this.scrollHorizontal.bind(this));\n\t\tthis.subscribe(\"row-added\", this.rowsUpdated.bind(this));\n\t\tthis.subscribe(\"column-moved\", this.recalcActiveRows.bind(this));\n\t\tthis.subscribe(\"column-add\", this.recalcActiveRows.bind(this));\n\t\tthis.subscribe(\"data-refreshed\", this.recalcActiveRowsRefresh.bind(this));\n\t\tthis.subscribe(\"table-redraw\", this.tableRedraw.bind(this));\n\t\tthis.subscribe(\"rows-visible\", this.visibleRows.bind(this));\n\t\tthis.subscribe(\"scrollbar-vertical\", this.adjustForScrollbar.bind(this));\n\t\t\n\t\tthis.subscribe(\"redraw-blocked\", this.blockRedraw.bind(this));\n\t\tthis.subscribe(\"redraw-restored\", this.restoreRedraw.bind(this));\n\n\t\tthis.subscribe(\"table-redrawing\", this.resizeHolderWidth.bind(this));\n\t\tthis.subscribe(\"column-resized\", this.resizeHolderWidth.bind(this));\n\t\tthis.subscribe(\"column-show\", this.resizeHolderWidth.bind(this));\n\t\tthis.subscribe(\"column-hide\", this.resizeHolderWidth.bind(this));\n\t\t\n\t\tthis.registerTableFunction(\"getCalcResults\", this.getResults.bind(this));\n\t\tthis.registerTableFunction(\"recalc\", this.userRecalc.bind(this));\n\n\n\t\tthis.resizeHolderWidth();\n\t}\n\n\tresizeHolderWidth(){\n\t\tthis.topElement.style.minWidth = this.table.columnManager.headersElement.offsetWidth + \"px\";\n\t}\n\n\t\n\ttableRedraw(force){\n\t\tthis.recalc(this.table.rowManager.activeRows);\n\t\t\n\t\tif(force){\n\t\t\tthis.redraw();\n\t\t}\n\t}\n\t\n\tblockRedraw(){\n\t\tthis.blocked = true;\n\t\tthis.recalcAfterBlock = false;\n\t}\n\t\n\t\n\trestoreRedraw(){\n\t\tthis.blocked = false;\n\t\t\n\t\tif(this.recalcAfterBlock){\n\t\t\tthis.recalcAfterBlock = false;\n\t\t\tthis.recalcActiveRowsRefresh();\n\t\t}\n\t}\n\t\n\t///////////////////////////////////\n\t///////// Table Functions /////////\n\t///////////////////////////////////\n\tuserRecalc(){\n\t\tthis.recalc(this.table.rowManager.activeRows);\n\t}\n\t\n\t///////////////////////////////////\n\t///////// Internal Logic //////////\n\t///////////////////////////////////\n\t\n\tblockCheck(){\n\t\tif(this.blocked){\n\t\t\tthis.recalcAfterBlock = true;\n\t\t}\n\t\t\n\t\treturn this.blocked;\n\t}\n\t\n\tvisibleRows(viewable, rows){\n\t\tif(this.topRow){\n\t\t\trows.unshift(this.topRow);\n\t\t}\n\t\t\n\t\tif(this.botRow){\n\t\t\trows.push(this.botRow);\n\t\t}\n\t\t\n\t\treturn rows;\n\t}\n\t\n\trowsUpdated(row){\n\t\tif(this.table.options.groupBy){\n\t\t\tthis.recalcRowGroup(row);\n\t\t}else {\n\t\t\tthis.recalcActiveRows();\n\t\t}\n\t}\n\t\n\trecalcActiveRowsRefresh(){\n\t\tif(this.table.options.groupBy && this.table.options.dataTreeStartExpanded && this.table.options.dataTree){\n\t\t\tthis.recalcAll();\n\t\t}else {\n\t\t\tthis.recalcActiveRows();\n\t\t}\n\t}\n\t\n\trecalcActiveRows(){\n\t\tthis.recalc(this.table.rowManager.activeRows);\n\t}\n\t\n\tcellValueChanged(cell){\n\t\tif(cell.column.definition.topCalc || cell.column.definition.bottomCalc){\n\t\t\tif(this.table.options.groupBy){\n\t\t\t\tif(this.table.options.columnCalcs == \"table\" || this.table.options.columnCalcs == \"both\"){\n\t\t\t\t\tthis.recalcActiveRows();\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tif(this.table.options.columnCalcs != \"table\"){\n\t\t\t\t\tthis.recalcRowGroup(cell.row);\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tthis.recalcActiveRows();\n\t\t\t}\n\t\t}\n\t}\n\t\n\tinitializeColumnCheck(column){\n\t\tif(column.definition.topCalc || column.definition.bottomCalc){\n\t\t\tthis.initializeColumn(column);\n\t\t}\n\t}\n\t\n\t//initialize column calcs\n\tinitializeColumn(column){\n\t\tvar def = column.definition;\n\t\t\n\t\tvar config = {\n\t\t\ttopCalcParams:def.topCalcParams || {},\n\t\t\tbotCalcParams:def.bottomCalcParams || {},\n\t\t};\n\t\t\n\t\tif(def.topCalc){\n\t\t\t\n\t\t\tswitch(typeof def.topCalc){\n\t\t\t\tcase \"string\":\n\t\t\t\t\tif(ColumnCalcs.calculations[def.topCalc]){\n\t\t\t\t\t\tconfig.topCalc = ColumnCalcs.calculations[def.topCalc];\n\t\t\t\t\t}else {\n\t\t\t\t\t\tconsole.warn(\"Column Calc Error - No such calculation found, ignoring: \", def.topCalc);\n\t\t\t\t\t}\n\t\t\t\t\tbreak;\n\t\t\t\t\n\t\t\t\tcase \"function\":\n\t\t\t\t\tconfig.topCalc = def.topCalc;\n\t\t\t\t\tbreak;\n\t\t\t\t\n\t\t\t}\n\t\t\t\n\t\t\tif(config.topCalc){\n\t\t\t\tcolumn.modules.columnCalcs = config;\n\t\t\t\tthis.topCalcs.push(column);\n\t\t\t\t\n\t\t\t\tif(this.table.options.columnCalcs != \"group\"){\n\t\t\t\t\tthis.initializeTopRow();\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t}\n\t\t\n\t\tif(def.bottomCalc){\n\t\t\tswitch(typeof def.bottomCalc){\n\t\t\t\tcase \"string\":\n\t\t\t\t\tif(ColumnCalcs.calculations[def.bottomCalc]){\n\t\t\t\t\t\tconfig.botCalc = ColumnCalcs.calculations[def.bottomCalc];\n\t\t\t\t\t}else {\n\t\t\t\t\t\tconsole.warn(\"Column Calc Error - No such calculation found, ignoring: \", def.bottomCalc);\n\t\t\t\t\t}\n\t\t\t\t\tbreak;\n\t\t\t\t\n\t\t\t\tcase \"function\":\n\t\t\t\t\tconfig.botCalc = def.bottomCalc;\n\t\t\t\t\tbreak;\n\t\t\t\t\n\t\t\t}\n\t\t\t\n\t\t\tif(config.botCalc){\n\t\t\t\tcolumn.modules.columnCalcs = config;\n\t\t\t\tthis.botCalcs.push(column);\n\t\t\t\t\n\t\t\t\tif(this.table.options.columnCalcs != \"group\"){\n\t\t\t\t\tthis.initializeBottomRow();\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t}\n\t\n\t//dummy functions to handle being mock column manager\n\tregisterColumnField(){}\n\t\n\tremoveCalcs(){\n\t\tvar changed = false;\n\t\t\n\t\tif(this.topInitialized){\n\t\t\tthis.topInitialized = false;\n\t\t\tthis.topElement.parentNode.removeChild(this.topElement);\n\t\t\tchanged = true;\n\t\t}\n\t\t\n\t\tif(this.botInitialized){\n\t\t\tthis.botInitialized = false;\n\t\t\tthis.footerRemove(this.botElement);\n\t\t\tchanged = true;\n\t\t}\n\t\t\n\t\tif(changed){\n\t\t\tthis.table.rowManager.adjustTableSize();\n\t\t}\n\t}\n\t\n\treinitializeCalcs(){\n\t\tif(this.topCalcs.length){\n\t\t\tthis.initializeTopRow();\n\t\t}\n\n\t\tif(this.botCalcs.length){\n\t\t\tthis.initializeBottomRow();\n\t\t}\n\t}\n\t\n\tinitializeTopRow(){\n\t\tvar\tfragment = document.createDocumentFragment();\n\t\t\n\t\tif(!this.topInitialized){\n\n\t\t\tfragment.appendChild(document.createElement(\"br\"));\n\t\t\tfragment.appendChild(this.topElement);\n\n\t\t\tthis.table.columnManager.getContentsElement().insertBefore(fragment, this.table.columnManager.headersElement.nextSibling);\n\t\t\tthis.topInitialized = true;\n\t\t}\n\t}\n\t\n\tinitializeBottomRow(){\n\t\tif(!this.botInitialized){\n\t\t\tthis.footerPrepend(this.botElement);\n\t\t\tthis.botInitialized = true;\n\t\t}\n\t}\n\t\n\tscrollHorizontal(left){\n\t\tif(this.botInitialized && this.botRow){\n\t\t\tthis.botElement.scrollLeft = left;\n\t\t}\n\t}\n\t\n\trecalc(rows){\n\t\tvar data, row;\n\t\t\n\t\tif(!this.blockCheck()){\n\t\t\tif(this.topInitialized || this.botInitialized){\n\t\t\t\tdata = this.rowsToData(rows);\n\t\t\t\t\n\t\t\t\tif(this.topInitialized){\n\t\t\t\t\tif(this.topRow){\n\t\t\t\t\t\tthis.topRow.deleteCells();\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\trow = this.generateRow(\"top\", data);\n\t\t\t\t\tthis.topRow = row;\n\t\t\t\t\twhile(this.topElement.firstChild) this.topElement.removeChild(this.topElement.firstChild);\n\t\t\t\t\tthis.topElement.appendChild(row.getElement());\n\t\t\t\t\trow.initialize(true);\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tif(this.botInitialized){\n\t\t\t\t\tif(this.botRow){\n\t\t\t\t\t\tthis.botRow.deleteCells();\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\trow = this.generateRow(\"bottom\", data);\n\t\t\t\t\tthis.botRow = row;\n\t\t\t\t\twhile(this.botElement.firstChild) this.botElement.removeChild(this.botElement.firstChild);\n\t\t\t\t\tthis.botElement.appendChild(row.getElement());\n\t\t\t\t\trow.initialize(true);\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tthis.table.rowManager.adjustTableSize();\n\t\t\t\t\n\t\t\t\t//set resizable handles\n\t\t\t\tif(this.table.modExists(\"frozenColumns\")){\n\t\t\t\t\tthis.table.modules.frozenColumns.layout();\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t\n\trecalcRowGroup(row){\n\t\tthis.recalcGroup(this.table.modules.groupRows.getRowGroup(row));\n\t}\n\t\n\trecalcAll(){\n\t\tif(this.topCalcs.length || this.botCalcs.length){\n\t\t\tif(this.table.options.columnCalcs !== \"group\"){\n\t\t\t\tthis.recalcActiveRows();\n\t\t\t}\n\t\t\t\n\t\t\tif(this.table.options.groupBy && this.table.options.columnCalcs !== \"table\"){\n\t\t\t\t\n\t\t\t\tvar groups = this.table.modules.groupRows.getChildGroups();\n\t\t\t\t\n\t\t\t\tgroups.forEach((group) => {\n\t\t\t\t\tthis.recalcGroup(group);\n\t\t\t\t});\n\t\t\t}\n\t\t}\n\t}\n\t\n\trecalcGroup(group){\n\t\tvar data, rowData;\n\t\t\n\t\tif(!this.blockCheck()){\n\t\t\tif(group){\n\t\t\t\tif(group.calcs){\n\t\t\t\t\tif(group.calcs.bottom){\n\t\t\t\t\t\tdata = this.rowsToData(group.rows);\n\t\t\t\t\t\trowData = this.generateRowData(\"bottom\", data);\n\t\t\t\t\t\t\n\t\t\t\t\t\tgroup.calcs.bottom.updateData(rowData);\n\t\t\t\t\t\tgroup.calcs.bottom.reinitialize();\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\tif(group.calcs.top){\n\t\t\t\t\t\tdata = this.rowsToData(group.rows);\n\t\t\t\t\t\trowData = this.generateRowData(\"top\", data);\n\t\t\t\t\t\t\n\t\t\t\t\t\tgroup.calcs.top.updateData(rowData);\n\t\t\t\t\t\tgroup.calcs.top.reinitialize();\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t\n\t//generate top stats row\n\tgenerateTopRow(rows){\n\t\treturn this.generateRow(\"top\", this.rowsToData(rows));\n\t}\n\t//generate bottom stats row\n\tgenerateBottomRow(rows){\n\t\treturn this.generateRow(\"bottom\", this.rowsToData(rows));\n\t}\n\t\n\trowsToData(rows){\n\t\tvar data = [];\n\t\t\n\t\trows.forEach((row) => {\n\t\t\tdata.push(row.getData());\n\t\t\t\n\t\t\tif(this.table.options.dataTree && this.table.options.dataTreeChildColumnCalcs){\n\t\t\t\tif(row.modules.dataTree && row.modules.dataTree.open){\n\t\t\t\t\tvar children = this.rowsToData(this.table.modules.dataTree.getFilteredTreeChildren(row));\n\t\t\t\t\tdata = data.concat(children);\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\t\t\n\t\treturn data;\n\t}\n\t\n\t//generate stats row\n\tgenerateRow(pos, data){\n\t\tvar rowData = this.generateRowData(pos, data),\n\t\trow;\n\t\t\n\t\tif(this.table.modExists(\"mutator\")){\n\t\t\tthis.table.modules.mutator.disable();\n\t\t}\n\t\t\n\t\trow = new Row(rowData, this, \"calc\");\n\t\t\n\t\tif(this.table.modExists(\"mutator\")){\n\t\t\tthis.table.modules.mutator.enable();\n\t\t}\n\t\t\n\t\trow.getElement().classList.add(\"tabulator-calcs\", \"tabulator-calcs-\" + pos);\n\t\t\n\t\trow.component = false;\n\t\t\n\t\trow.getComponent = () => {\n\t\t\tif(!row.component){\n\t\t\t\trow.component = new CalcComponent(row);\n\t\t\t}\n\t\t\t\n\t\t\treturn row.component;\n\t\t};\n\t\t\n\t\trow.generateCells = () => {\n\t\t\t\n\t\t\tvar cells = [];\n\t\t\t\n\t\t\tthis.table.columnManager.columnsByIndex.forEach((column) => {\n\t\t\t\t\n\t\t\t\t//set field name of mock column\n\t\t\t\tthis.genColumn.setField(column.getField());\n\t\t\t\tthis.genColumn.hozAlign = column.hozAlign;\n\t\t\t\t\n\t\t\t\tif(column.definition[pos + \"CalcFormatter\"] && this.table.modExists(\"format\")){\n\t\t\t\t\tthis.genColumn.modules.format = {\n\t\t\t\t\t\tformatter: this.table.modules.format.getFormatter(column.definition[pos + \"CalcFormatter\"]),\n\t\t\t\t\t\tparams: column.definition[pos + \"CalcFormatterParams\"] || {},\n\t\t\t\t\t};\n\t\t\t\t}else {\n\t\t\t\t\tthis.genColumn.modules.format = {\n\t\t\t\t\t\tformatter: this.table.modules.format.getFormatter(\"plaintext\"),\n\t\t\t\t\t\tparams:{}\n\t\t\t\t\t};\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t//ensure css class definition is replicated to calculation cell\n\t\t\t\tthis.genColumn.definition.cssClass = column.definition.cssClass;\n\t\t\t\t\n\t\t\t\t//generate cell and assign to correct column\n\t\t\t\tvar cell = new Cell(this.genColumn, row);\n\t\t\t\tcell.getElement();\n\t\t\t\tcell.column = column;\n\t\t\t\tcell.setWidth();\n\t\t\t\t\n\t\t\t\tcolumn.cells.push(cell);\n\t\t\t\tcells.push(cell);\n\t\t\t\t\n\t\t\t\tif(!column.visible){\n\t\t\t\t\tcell.hide();\n\t\t\t\t}\n\t\t\t});\n\t\t\t\n\t\t\trow.cells = cells;\n\t\t};\n\t\t\n\t\treturn row;\n\t}\n\t\n\t//generate stats row\n\tgenerateRowData(pos, data){\n\t\tvar rowData = {},\n\t\tcalcs = pos == \"top\" ? this.topCalcs : this.botCalcs,\n\t\ttype = pos == \"top\" ? \"topCalc\" : \"botCalc\",\n\t\tparams, paramKey;\n\t\t\n\t\tcalcs.forEach(function(column){\n\t\t\tvar values = [];\n\t\t\t\n\t\t\tif(column.modules.columnCalcs && column.modules.columnCalcs[type]){\n\t\t\t\tdata.forEach(function(item){\n\t\t\t\t\tvalues.push(column.getFieldValue(item));\n\t\t\t\t});\n\t\t\t\t\n\t\t\t\tparamKey = type + \"Params\";\n\t\t\t\tparams = typeof column.modules.columnCalcs[paramKey] === \"function\" ? column.modules.columnCalcs[paramKey](values, data) : column.modules.columnCalcs[paramKey];\n\t\t\t\t\n\t\t\t\tcolumn.setFieldValue(rowData, column.modules.columnCalcs[type](values, data, params));\n\t\t\t}\n\t\t});\n\t\t\n\t\treturn rowData;\n\t}\n\t\n\thasTopCalcs(){\n\t\treturn\t!!(this.topCalcs.length);\n\t}\n\t\n\thasBottomCalcs(){\n\t\treturn\t!!(this.botCalcs.length);\n\t}\n\t\n\t//handle table redraw\n\tredraw(){\n\t\tif(this.topRow){\n\t\t\tthis.topRow.normalizeHeight(true);\n\t\t}\n\t\tif(this.botRow){\n\t\t\tthis.botRow.normalizeHeight(true);\n\t\t}\n\t}\n\t\n\t//return the calculated\n\tgetResults(){\n\t\tvar results = {},\n\t\tgroups;\n\t\t\n\t\tif(this.table.options.groupBy && this.table.modExists(\"groupRows\")){\n\t\t\tgroups = this.table.modules.groupRows.getGroups(true);\n\t\t\t\n\t\t\tgroups.forEach((group) => {\n\t\t\t\tresults[group.getKey()] = this.getGroupResults(group);\n\t\t\t});\n\t\t}else {\n\t\t\tresults = {\n\t\t\t\ttop: this.topRow ? this.topRow.getData() : {},\n\t\t\t\tbottom: this.botRow ? this.botRow.getData() : {},\n\t\t\t};\n\t\t}\n\t\t\n\t\treturn results;\n\t}\n\t\n\t//get results from a group\n\tgetGroupResults(group){\n\t\tvar groupObj = group._getSelf(),\n\t\tsubGroups = group.getSubGroups(),\n\t\tsubGroupResults = {},\n\t\tresults = {};\n\t\t\n\t\tsubGroups.forEach((subgroup) => {\n\t\t\tsubGroupResults[subgroup.getKey()] = this.getGroupResults(subgroup);\n\t\t});\n\t\t\n\t\tresults = {\n\t\t\ttop: groupObj.calcs.top ? groupObj.calcs.top.getData() : {},\n\t\t\tbottom: groupObj.calcs.bottom ? groupObj.calcs.bottom.getData() : {},\n\t\t\tgroups: subGroupResults,\n\t\t};\n\t\t\n\t\treturn results;\n\t}\n\t\n\tadjustForScrollbar(width){\n\t\tif(this.botRow){\n\t\t\tif(this.table.rtl){\n\t\t\t\tthis.botElement.style.paddingLeft = width + \"px\";\n\t\t\t}else {\n\t\t\t\tthis.botElement.style.paddingRight = width + \"px\";\n\t\t\t}\n\t\t}\n\t}\n}\n\nColumnCalcs.moduleName = \"columnCalcs\";\n\n//load defaults\nColumnCalcs.calculations = defaultCalculations;\n\nclass DataTree extends Module{\n\n\tconstructor(table){\n\t\tsuper(table);\n\n\t\tthis.indent = 10;\n\t\tthis.field = \"\";\n\t\tthis.collapseEl = null;\n\t\tthis.expandEl = null;\n\t\tthis.branchEl = null;\n\t\tthis.elementField = false;\n\n\t\tthis.startOpen = function(){};\n\n\t\tthis.registerTableOption(\"dataTree\", false); //enable data tree\n\t\tthis.registerTableOption(\"dataTreeFilter\", true); //filter child rows\n\t\tthis.registerTableOption(\"dataTreeSort\", true); //sort child rows\n\t\tthis.registerTableOption(\"dataTreeElementColumn\", false);\n\t\tthis.registerTableOption(\"dataTreeBranchElement\", true);//show data tree branch element\n\t\tthis.registerTableOption(\"dataTreeChildIndent\", 9); //data tree child indent in px\n\t\tthis.registerTableOption(\"dataTreeChildField\", \"_children\");//data tre column field to look for child rows\n\t\tthis.registerTableOption(\"dataTreeCollapseElement\", false);//data tree row collapse element\n\t\tthis.registerTableOption(\"dataTreeExpandElement\", false);//data tree row expand element\n\t\tthis.registerTableOption(\"dataTreeStartExpanded\", false);\n\t\tthis.registerTableOption(\"dataTreeChildColumnCalcs\", false);//include visible data tree rows in column calculations\n\t\tthis.registerTableOption(\"dataTreeSelectPropagate\", false);//selecting a parent row selects its children\n\n\t\t//register component functions\n\t\tthis.registerComponentFunction(\"row\", \"treeCollapse\", this.collapseRow.bind(this));\n\t\tthis.registerComponentFunction(\"row\", \"treeExpand\", this.expandRow.bind(this));\n\t\tthis.registerComponentFunction(\"row\", \"treeToggle\", this.toggleRow.bind(this));\n\t\tthis.registerComponentFunction(\"row\", \"getTreeParent\", this.getTreeParent.bind(this));\n\t\tthis.registerComponentFunction(\"row\", \"getTreeChildren\", this.getRowChildren.bind(this));\n\t\tthis.registerComponentFunction(\"row\", \"addTreeChild\", this.addTreeChildRow.bind(this));\n\t\tthis.registerComponentFunction(\"row\", \"isTreeExpanded\", this.isRowExpanded.bind(this));\n\t}\n\n\tinitialize(){\n\t\tif(this.table.options.dataTree){\n\t\t\tvar dummyEl = null,\n\t\t\toptions = this.table.options;\n\n\t\t\tthis.field = options.dataTreeChildField;\n\t\t\tthis.indent = options.dataTreeChildIndent;\n\n\t\t\tif(this.options(\"movableRows\")){\n\t\t\t\tconsole.warn(\"The movableRows option is not available with dataTree enabled, moving of child rows could result in unpredictable behavior\");\n\t\t\t}\n\n\t\t\tif(options.dataTreeBranchElement){\n\n\t\t\t\tif(options.dataTreeBranchElement === true){\n\t\t\t\t\tthis.branchEl = document.createElement(\"div\");\n\t\t\t\t\tthis.branchEl.classList.add(\"tabulator-data-tree-branch\");\n\t\t\t\t}else {\n\t\t\t\t\tif(typeof options.dataTreeBranchElement === \"string\"){\n\t\t\t\t\t\tdummyEl = document.createElement(\"div\");\n\t\t\t\t\t\tdummyEl.innerHTML = options.dataTreeBranchElement;\n\t\t\t\t\t\tthis.branchEl = dummyEl.firstChild;\n\t\t\t\t\t}else {\n\t\t\t\t\t\tthis.branchEl = options.dataTreeBranchElement;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tthis.branchEl = document.createElement(\"div\");\n\t\t\t\tthis.branchEl.classList.add(\"tabulator-data-tree-branch-empty\");\n\t\t\t}\n\n\t\t\tif(options.dataTreeCollapseElement){\n\t\t\t\tif(typeof options.dataTreeCollapseElement === \"string\"){\n\t\t\t\t\tdummyEl = document.createElement(\"div\");\n\t\t\t\t\tdummyEl.innerHTML = options.dataTreeCollapseElement;\n\t\t\t\t\tthis.collapseEl = dummyEl.firstChild;\n\t\t\t\t}else {\n\t\t\t\t\tthis.collapseEl = options.dataTreeCollapseElement;\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tthis.collapseEl = document.createElement(\"div\");\n\t\t\t\tthis.collapseEl.classList.add(\"tabulator-data-tree-control\");\n\t\t\t\tthis.collapseEl.tabIndex = 0;\n\t\t\t\tthis.collapseEl.innerHTML = \"<div class='tabulator-data-tree-control-collapse'></div>\";\n\t\t\t}\n\n\t\t\tif(options.dataTreeExpandElement){\n\t\t\t\tif(typeof options.dataTreeExpandElement === \"string\"){\n\t\t\t\t\tdummyEl = document.createElement(\"div\");\n\t\t\t\t\tdummyEl.innerHTML = options.dataTreeExpandElement;\n\t\t\t\t\tthis.expandEl = dummyEl.firstChild;\n\t\t\t\t}else {\n\t\t\t\t\tthis.expandEl = options.dataTreeExpandElement;\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tthis.expandEl = document.createElement(\"div\");\n\t\t\t\tthis.expandEl.classList.add(\"tabulator-data-tree-control\");\n\t\t\t\tthis.expandEl.tabIndex = 0;\n\t\t\t\tthis.expandEl.innerHTML = \"<div class='tabulator-data-tree-control-expand'></div>\";\n\t\t\t}\n\n\n\t\t\tswitch(typeof options.dataTreeStartExpanded){\n\t\t\t\tcase \"boolean\":\n\t\t\t\t\tthis.startOpen = function(row, index){\n\t\t\t\t\t\treturn options.dataTreeStartExpanded;\n\t\t\t\t\t};\n\t\t\t\t\tbreak;\n\n\t\t\t\tcase \"function\":\n\t\t\t\t\tthis.startOpen = options.dataTreeStartExpanded;\n\t\t\t\t\tbreak;\n\n\t\t\t\tdefault:\n\t\t\t\t\tthis.startOpen = function(row, index){\n\t\t\t\t\t\treturn options.dataTreeStartExpanded[index];\n\t\t\t\t\t};\n\t\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\tthis.subscribe(\"row-init\", this.initializeRow.bind(this));\n\t\t\tthis.subscribe(\"row-layout-after\", this.layoutRow.bind(this));\n\t\t\tthis.subscribe(\"row-deleted\", this.rowDelete.bind(this),0);\n\t\t\tthis.subscribe(\"row-data-changed\", this.rowDataChanged.bind(this), 10);\n\t\t\tthis.subscribe(\"cell-value-updated\", this.cellValueChanged.bind(this));\n\t\t\tthis.subscribe(\"edit-cancelled\", this.cellValueChanged.bind(this));\n\t\t\tthis.subscribe(\"column-moving-rows\", this.columnMoving.bind(this));\n\t\t\tthis.subscribe(\"table-built\", this.initializeElementField.bind(this));\n\t\t\tthis.subscribe(\"table-redrawing\", this.tableRedrawing.bind(this));\n\n\t\t\tthis.registerDisplayHandler(this.getRows.bind(this), 30);\n\t\t}\n\t}\n\n\ttableRedrawing(force){\n\t\tvar rows;\n\n\t\tif(force){\n\t\t\trows = this.table.rowManager.getRows();\n\t\t\t\n\t\t\trows.forEach((row) => {\n\t\t\t\tthis.reinitializeRowChildren(row);\n\t\t\t});\n\t\t}\n\t}\n\n\tinitializeElementField(){\n\t\tvar firstCol = this.table.columnManager.getFirstVisibleColumn();\n\n\t\tthis.elementField = this.table.options.dataTreeElementColumn || (firstCol ? firstCol.field : false);\n\t}\n\t\n\tgetRowChildren(row){\n\t\treturn this.getTreeChildren(row, true);\n\t}\n\n\tcolumnMoving(){\n\t\tvar rows = [];\n\n\t\tthis.table.rowManager.rows.forEach((row) => {\n\t\t\trows = rows.concat(this.getTreeChildren(row, false, true));\n\t\t});\n\n\t\treturn rows;\n\t}\n\n\trowDataChanged(row, visible, updatedData){\n\t\tif(this.redrawNeeded(updatedData)){\n\t\t\tthis.initializeRow(row);\n\n\t\t\tif(visible){\n\t\t\t\tthis.layoutRow(row);\n\t\t\t\tthis.refreshData(true);\n\t\t\t}\n\t\t}\n\t}\n\n\tcellValueChanged(cell){\n\t\tvar field = cell.column.getField();\n\n\t\tif(field === this.elementField){\n\t\t\tthis.layoutRow(cell.row);\n\t\t}\n\t}\n\n\tinitializeRow(row){\n\t\tvar childArray = row.getData()[this.field];\n\t\tvar isArray = Array.isArray(childArray);\n\n\t\tvar children = isArray || (!isArray && typeof childArray === \"object\" && childArray !== null);\n\n\t\tif(!children && row.modules.dataTree && row.modules.dataTree.branchEl){\n\t\t\trow.modules.dataTree.branchEl.parentNode.removeChild(row.modules.dataTree.branchEl);\n\t\t}\n\n\t\tif(!children && row.modules.dataTree && row.modules.dataTree.controlEl){\n\t\t\trow.modules.dataTree.controlEl.parentNode.removeChild(row.modules.dataTree.controlEl);\n\t\t}\n\n\t\trow.modules.dataTree = {\n\t\t\tindex: row.modules.dataTree ? row.modules.dataTree.index : 0,\n\t\t\topen: children ? (row.modules.dataTree ? row.modules.dataTree.open : this.startOpen(row.getComponent(), 0)) : false,\n\t\t\tcontrolEl: row.modules.dataTree && children ? row.modules.dataTree.controlEl : false,\n\t\t\tbranchEl: row.modules.dataTree && children ? row.modules.dataTree.branchEl : false,\n\t\t\tparent: row.modules.dataTree ? row.modules.dataTree.parent : false,\n\t\t\tchildren:children,\n\t\t};\n\t}\n\n\treinitializeRowChildren(row){\n\t\tvar children = this.getTreeChildren(row, false, true);\n\n\t\tchildren.forEach(function(child){\n\t\t\tchild.reinitialize(true);\n\t\t});\n\t}\n\n\tlayoutRow(row){\n\t\tvar cell = this.elementField ? row.getCell(this.elementField) : row.getCells()[0],\n\t\tel = cell.getElement(),\n\t\tconfig = row.modules.dataTree;\n\n\t\tif(config.branchEl){\n\t\t\tif(config.branchEl.parentNode){\n\t\t\t\tconfig.branchEl.parentNode.removeChild(config.branchEl);\n\t\t\t}\n\t\t\tconfig.branchEl = false;\n\t\t}\n\n\t\tif(config.controlEl){\n\t\t\tif(config.controlEl.parentNode){\n\t\t\t\tconfig.controlEl.parentNode.removeChild(config.controlEl);\n\t\t\t}\n\t\t\tconfig.controlEl = false;\n\t\t}\n\n\t\tthis.generateControlElement(row, el);\n\n\t\trow.getElement().classList.add(\"tabulator-tree-level-\" + config.index);\n\n\t\tif(config.index){\n\t\t\tif(this.branchEl){\n\t\t\t\tconfig.branchEl = this.branchEl.cloneNode(true);\n\t\t\t\tel.insertBefore(config.branchEl, el.firstChild);\n\n\t\t\t\tif(this.table.rtl){\n\t\t\t\t\tconfig.branchEl.style.marginRight = (((config.branchEl.offsetWidth + config.branchEl.style.marginLeft) * (config.index - 1)) + (config.index * this.indent)) + \"px\";\n\t\t\t\t}else {\n\t\t\t\t\tconfig.branchEl.style.marginLeft = (((config.branchEl.offsetWidth + config.branchEl.style.marginRight) * (config.index - 1)) + (config.index * this.indent)) + \"px\";\n\t\t\t\t}\n\t\t\t}else {\n\n\t\t\t\tif(this.table.rtl){\n\t\t\t\t\tel.style.paddingRight = parseInt(window.getComputedStyle(el, null).getPropertyValue('padding-right')) + (config.index * this.indent) + \"px\";\n\t\t\t\t}else {\n\t\t\t\t\tel.style.paddingLeft = parseInt(window.getComputedStyle(el, null).getPropertyValue('padding-left')) + (config.index * this.indent) + \"px\";\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\tgenerateControlElement(row, el){\n\t\tvar config = row.modules.dataTree,\n\t\toldControl = config.controlEl;\n\n\t\tel = el || row.getCells()[0].getElement();\n\n\t\tif(config.children !== false){\n\n\t\t\tif(config.open){\n\t\t\t\tconfig.controlEl = this.collapseEl.cloneNode(true);\n\t\t\t\tconfig.controlEl.addEventListener(\"click\", (e) => {\n\t\t\t\t\te.stopPropagation();\n\t\t\t\t\tthis.collapseRow(row);\n\t\t\t\t});\n\t\t\t}else {\n\t\t\t\tconfig.controlEl = this.expandEl.cloneNode(true);\n\t\t\t\tconfig.controlEl.addEventListener(\"click\", (e) => {\n\t\t\t\t\te.stopPropagation();\n\t\t\t\t\tthis.expandRow(row);\n\t\t\t\t});\n\t\t\t}\n\n\t\t\tconfig.controlEl.addEventListener(\"mousedown\", (e) => {\n\t\t\t\te.stopPropagation();\n\t\t\t});\n\n\t\t\tif(oldControl && oldControl.parentNode === el){\n\t\t\t\toldControl.parentNode.replaceChild(config.controlEl,oldControl);\n\t\t\t}else {\n\t\t\t\tel.insertBefore(config.controlEl, el.firstChild);\n\t\t\t}\n\t\t}\n\t}\n\n\tgetRows(rows){\n\t\tvar output = [];\n\n\t\trows.forEach((row, i) => {\n\t\t\tvar config, children;\n\n\t\t\toutput.push(row);\n\n\t\t\tif(row instanceof Row){\n\n\t\t\t\trow.create();\n\n\t\t\t\tconfig = row.modules.dataTree;\n\n\t\t\t\tif(!config.index && config.children !== false){\n\t\t\t\t\tchildren = this.getChildren(row);\n\n\t\t\t\t\tchildren.forEach((child) => {\n\t\t\t\t\t\tchild.create();\n\t\t\t\t\t\toutput.push(child);\n\t\t\t\t\t});\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\n\t\treturn output;\n\t}\n\n\tgetChildren(row, allChildren){\n\t\tvar config = row.modules.dataTree,\n\t\tchildren = [],\n\t\toutput = [];\n\n\t\tif(config.children !== false && (config.open || allChildren)){\n\t\t\tif(!Array.isArray(config.children)){\n\t\t\t\tconfig.children = this.generateChildren(row);\n\t\t\t}\n\n\t\t\tif(this.table.modExists(\"filter\") && this.table.options.dataTreeFilter){\n\t\t\t\tchildren = this.table.modules.filter.filter(config.children);\n\t\t\t}else {\n\t\t\t\tchildren = config.children;\n\t\t\t}\n\n\t\t\tif(this.table.modExists(\"sort\") && this.table.options.dataTreeSort){\n\t\t\t\tthis.table.modules.sort.sort(children);\n\t\t\t}\n\n\t\t\tchildren.forEach((child) => {\n\t\t\t\toutput.push(child);\n\n\t\t\t\tvar subChildren = this.getChildren(child);\n\n\t\t\t\tsubChildren.forEach((sub) => {\n\t\t\t\t\toutput.push(sub);\n\t\t\t\t});\n\t\t\t});\n\t\t}\n\n\t\treturn output;\n\t}\n\n\tgenerateChildren(row){\n\t\tvar children = [];\n\n\t\tvar childArray = row.getData()[this.field];\n\n\t\tif(!Array.isArray(childArray)){\n\t\t\tchildArray = [childArray];\n\t\t}\n\n\t\tchildArray.forEach((childData) => {\n\t\t\tvar childRow = new Row(childData || {}, this.table.rowManager);\n\n\t\t\tchildRow.create();\n\n\t\t\tchildRow.modules.dataTree.index = row.modules.dataTree.index + 1;\n\t\t\tchildRow.modules.dataTree.parent = row;\n\n\t\t\tif(childRow.modules.dataTree.children){\n\t\t\t\tchildRow.modules.dataTree.open = this.startOpen(childRow.getComponent(), childRow.modules.dataTree.index);\n\t\t\t}\n\t\t\tchildren.push(childRow);\n\t\t});\n\n\t\treturn children;\n\t}\n\n\texpandRow(row, silent){\n\t\tvar config = row.modules.dataTree;\n\n\t\tif(config.children !== false){\n\t\t\tconfig.open = true;\n\n\t\t\trow.reinitialize();\n\n\t\t\tthis.refreshData(true);\n\n\t\t\tthis.dispatchExternal(\"dataTreeRowExpanded\", row.getComponent(), row.modules.dataTree.index);\n\t\t}\n\t}\n\n\tcollapseRow(row){\n\t\tvar config = row.modules.dataTree;\n\n\t\tif(config.children !== false){\n\t\t\tconfig.open = false;\n\n\t\t\trow.reinitialize();\n\n\t\t\tthis.refreshData(true);\n\n\t\t\tthis.dispatchExternal(\"dataTreeRowCollapsed\", row.getComponent(), row.modules.dataTree.index);\n\t\t}\n\t}\n\n\ttoggleRow(row){\n\t\tvar config = row.modules.dataTree;\n\n\t\tif(config.children !== false){\n\t\t\tif(config.open){\n\t\t\t\tthis.collapseRow(row);\n\t\t\t}else {\n\t\t\t\tthis.expandRow(row);\n\t\t\t}\n\t\t}\n\t}\n\n\tisRowExpanded(row){\n\t\treturn row.modules.dataTree.open;\n\t}\n\n\tgetTreeParent(row){\n\t\treturn row.modules.dataTree.parent ? row.modules.dataTree.parent.getComponent() : false;\n\t}\n\n\tgetTreeParentRoot(row){\n\t\treturn row.modules.dataTree && row.modules.dataTree.parent ? this.getTreeParentRoot(row.modules.dataTree.parent) : row;\n\t}\n\n\tgetFilteredTreeChildren(row){\n\t\tvar config = row.modules.dataTree,\n\t\toutput = [], children;\n\n\t\tif(config.children){\n\n\t\t\tif(!Array.isArray(config.children)){\n\t\t\t\tconfig.children = this.generateChildren(row);\n\t\t\t}\n\n\t\t\tif(this.table.modExists(\"filter\") && this.table.options.dataTreeFilter){\n\t\t\t\tchildren = this.table.modules.filter.filter(config.children);\n\t\t\t}else {\n\t\t\t\tchildren = config.children;\n\t\t\t}\n\n\t\t\tchildren.forEach((childRow) => {\n\t\t\t\tif(childRow instanceof Row){\n\t\t\t\t\toutput.push(childRow);\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\n\t\treturn output;\n\t}\n\n\trowDelete(row){\n\t\tvar parent = row.modules.dataTree.parent,\n\t\tchildIndex;\n\n\t\tif(parent){\n\t\t\tchildIndex = this.findChildIndex(row, parent);\n\n\t\t\tif(childIndex !== false){\n\t\t\t\tparent.data[this.field].splice(childIndex, 1);\n\t\t\t}\n\n\t\t\tif(!parent.data[this.field].length){\n\t\t\t\tdelete parent.data[this.field];\n\t\t\t}\n\n\t\t\tthis.initializeRow(parent);\n\t\t\tthis.layoutRow(parent);\n\t\t}\n\n\t\tthis.refreshData(true);\n\t}\n\n\taddTreeChildRow(row, data, top, index){\n\t\tvar childIndex = false;\n\n\t\tif(typeof data === \"string\"){\n\t\t\tdata = JSON.parse(data);\n\t\t}\n\n\t\tif(!Array.isArray(row.data[this.field])){\n\t\t\trow.data[this.field] = [];\n\n\t\t\trow.modules.dataTree.open = this.startOpen(row.getComponent(), row.modules.dataTree.index);\n\t\t}\n\n\t\tif(typeof index !== \"undefined\"){\n\t\t\tchildIndex = this.findChildIndex(index, row);\n\n\t\t\tif(childIndex !== false){\n\t\t\t\trow.data[this.field].splice((top ? childIndex : childIndex + 1), 0, data);\n\t\t\t}\n\t\t}\n\n\t\tif(childIndex === false){\n\t\t\tif(top){\n\t\t\t\trow.data[this.field].unshift(data);\n\t\t\t}else {\n\t\t\t\trow.data[this.field].push(data);\n\t\t\t}\n\t\t}\n\n\t\tthis.initializeRow(row);\n\t\tthis.layoutRow(row);\n\n\t\tthis.refreshData(true);\n\t}\n\n\tfindChildIndex(subject, parent){\n\t\tvar match = false;\n\n\t\tif(typeof subject == \"object\"){\n\n\t\t\tif(subject instanceof Row){\n\t\t\t\t//subject is row element\n\t\t\t\tmatch = subject.data;\n\t\t\t}else if(subject instanceof RowComponent){\n\t\t\t\t//subject is public row component\n\t\t\t\tmatch = subject._getSelf().data;\n\t\t\t}else if(typeof HTMLElement !== \"undefined\" && subject instanceof HTMLElement){\n\t\t\t\tif(parent.modules.dataTree){\n\t\t\t\t\tmatch = parent.modules.dataTree.children.find((childRow) => {\n\t\t\t\t\t\treturn childRow instanceof Row ? childRow.element === subject : false;\n\t\t\t\t\t});\n\n\t\t\t\t\tif(match){\n\t\t\t\t\t\tmatch = match.data;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}else if(subject === null){\n\t\t\t\tmatch = false;\n\t\t\t}\n\n\t\t}else if(typeof subject == \"undefined\"){\n\t\t\tmatch = false;\n\t\t}else {\n\t\t\t//subject should be treated as the index of the row\n\t\t\tmatch = parent.data[this.field].find((row) => {\n\t\t\t\treturn row.data[this.table.options.index] == subject;\n\t\t\t});\n\t\t}\n\n\t\tif(match){\n\n\t\t\tif(Array.isArray(parent.data[this.field])){\n\t\t\t\tmatch = parent.data[this.field].indexOf(match);\n\t\t\t}\n\n\t\t\tif(match == -1){\n\t\t\t\tmatch = false;\n\t\t\t}\n\t\t}\n\n\t\t//catch all for any other type of input\n\n\t\treturn match;\n\t}\n\n\tgetTreeChildren(row, component, recurse){\n\t\tvar config = row.modules.dataTree,\n\t\toutput = [];\n\n\t\tif(config && config.children){\n\n\t\t\tif(!Array.isArray(config.children)){\n\t\t\t\tconfig.children = this.generateChildren(row);\n\t\t\t}\n\n\t\t\tconfig.children.forEach((childRow) => {\n\t\t\t\tif(childRow instanceof Row){\n\t\t\t\t\toutput.push(component ? childRow.getComponent() : childRow);\n\n\t\t\t\t\tif(recurse){\n\t\t\t\t\t\toutput = output.concat(this.getTreeChildren(childRow, component, recurse));\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\n\t\treturn output;\n\t}\n\n\tgetChildField(){\n\t\treturn this.field;\n\t}\n\n\tredrawNeeded(data){\n\t\treturn (this.field ? typeof data[this.field] !== \"undefined\" : false) || (this.elementField ? typeof data[this.elementField] !== \"undefined\" : false);\n\t}\n}\n\nDataTree.moduleName = \"dataTree\";\n\nfunction csv(list, options = {}, setFileContents){\n\tvar delimiter = options.delimiter ? options.delimiter : \",\",\n\tfileContents = [],\n\theaders = [];\n\n\tlist.forEach((row) => {\n\t\tvar item = [];\n\n\t\tswitch(row.type){\n\t\t\tcase \"group\":\n\t\t\t\tconsole.warn(\"Download Warning - CSV downloader cannot process row groups\");\n\t\t\t\tbreak;\n\n\t\t\tcase \"calc\":\n\t\t\t\tconsole.warn(\"Download Warning - CSV downloader cannot process column calculations\");\n\t\t\t\tbreak;\n\n\t\t\tcase \"header\":\n\t\t\t\trow.columns.forEach((col, i) => {\n\t\t\t\t\tif(col && col.depth === 1){\n\t\t\t\t\t\theaders[i] = typeof col.value == \"undefined\"  || col.value === null ? \"\" : ('\"' + String(col.value).split('\"').join('\"\"') + '\"');\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t\tbreak;\n\n\t\t\tcase \"row\":\n\t\t\t\trow.columns.forEach((col) => {\n\n\t\t\t\t\tif(col){\n\n\t\t\t\t\t\tswitch(typeof col.value){\n\t\t\t\t\t\t\tcase \"object\":\n\t\t\t\t\t\t\t\tcol.value = col.value !== null ? JSON.stringify(col.value) : \"\";\n\t\t\t\t\t\t\t\tbreak;\n\n\t\t\t\t\t\t\tcase \"undefined\":\n\t\t\t\t\t\t\t\tcol.value = \"\";\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t}\n\n\t\t\t\t\t\titem.push('\"' + String(col.value).split('\"').join('\"\"') + '\"');\n\t\t\t\t\t}\n\t\t\t\t});\n\n\t\t\t\tfileContents.push(item.join(delimiter));\n\t\t\t\tbreak;\n\t\t}\n\t});\n\n\tif(headers.length){\n\t\tfileContents.unshift(headers.join(delimiter));\n\t}\n\n\tfileContents = fileContents.join(\"\\n\");\n\n\tif(options.bom){\n\t\tfileContents = \"\\ufeff\" + fileContents;\n\t}\n\n\tsetFileContents(fileContents, \"text/csv\");\n}\n\nfunction json(list, options, setFileContents){\n\tvar fileContents = [];\n\n\tlist.forEach((row) => {\n\t\tvar item = {};\n\n\t\tswitch(row.type){\n\t\t\tcase \"header\":\n\t\t\t\tbreak;\n\n\t\t\tcase \"group\":\n\t\t\t\tconsole.warn(\"Download Warning - JSON downloader cannot process row groups\");\n\t\t\t\tbreak;\n\n\t\t\tcase \"calc\":\n\t\t\t\tconsole.warn(\"Download Warning - JSON downloader cannot process column calculations\");\n\t\t\t\tbreak;\n\n\t\t\tcase \"row\":\n\t\t\t\trow.columns.forEach((col) => {\n\t\t\t\t\tif(col){\n\t\t\t\t\t\titem[col.component.getTitleDownload() || col.component.getField()] = col.value;\n\t\t\t\t\t}\n\t\t\t\t});\n\n\t\t\t\tfileContents.push(item);\n\t\t\t\tbreak;\n\t\t}\n\t});\n\n\tfileContents = JSON.stringify(fileContents, null, '\\t');\n\n\tsetFileContents(fileContents, \"application/json\");\n}\n\nfunction pdf(list, options = {}, setFileContents){\n\tvar header = [],\n\tbody = [],\n\tautoTableParams = {},\n\trowGroupStyles = options.rowGroupStyles || {\n\t\tfontStyle: \"bold\",\n\t\tfontSize: 12,\n\t\tcellPadding: 6,\n\t\tfillColor: 220,\n\t},\n\trowCalcStyles = options.rowCalcStyles || {\n\t\tfontStyle: \"bold\",\n\t\tfontSize: 10,\n\t\tcellPadding: 4,\n\t\tfillColor: 232,\n\t},\n\tjsPDFParams = options.jsPDF || {},\n\ttitle = options.title ? options.title : \"\";\n\n\tif(!jsPDFParams.orientation){\n\t\tjsPDFParams.orientation = options.orientation || \"landscape\";\n\t}\n\n\tif(!jsPDFParams.unit){\n\t\tjsPDFParams.unit = \"pt\";\n\t}\n\n\t//parse row list\n\tlist.forEach((row) => {\n\t\tswitch(row.type){\n\t\t\tcase \"header\":\n\t\t\t\theader.push(parseRow(row));\n\t\t\t\tbreak;\n\n\t\t\tcase \"group\":\n\t\t\t\tbody.push(parseRow(row, rowGroupStyles));\n\t\t\t\tbreak;\n\n\t\t\tcase \"calc\":\n\t\t\t\tbody.push(parseRow(row, rowCalcStyles));\n\t\t\t\tbreak;\n\n\t\t\tcase \"row\":\n\t\t\t\tbody.push(parseRow(row));\n\t\t\t\tbreak;\n\t\t}\n\t});\n\n\tfunction parseRow(row, styles){\n\t\tvar rowData = [];\n\n\t\trow.columns.forEach((col) =>{\n\t\t\tvar cell;\n\n\t\t\tif(col){\n\t\t\t\tswitch(typeof col.value){\n\t\t\t\t\tcase \"object\":\n\t\t\t\t\t\tcol.value = col.value !== null ? JSON.stringify(col.value) : \"\";\n\t\t\t\t\t\tbreak;\n\n\t\t\t\t\tcase \"undefined\":\n\t\t\t\t\t\tcol.value = \"\";\n\t\t\t\t\t\tbreak;\n\t\t\t\t}\n\n\t\t\t\tcell = {\n\t\t\t\t\tcontent:col.value,\n\t\t\t\t\tcolSpan:col.width,\n\t\t\t\t\trowSpan:col.height,\n\t\t\t\t};\n\n\t\t\t\tif(styles){\n\t\t\t\t\tcell.styles = styles;\n\t\t\t\t}\n\n\t\t\t\trowData.push(cell);\n\t\t\t}\n\t\t});\n\n\t\treturn rowData;\n\t}\n\n\n\t//configure PDF\n\tvar doc = new jspdf.jsPDF(jsPDFParams); //set document to landscape, better for most tables\n\n\tif(options.autoTable){\n\t\tif(typeof options.autoTable === \"function\"){\n\t\t\tautoTableParams = options.autoTable(doc) || {};\n\t\t}else {\n\t\t\tautoTableParams = options.autoTable;\n\t\t}\n\t}\n\n\tif(title){\n\t\tautoTableParams.didDrawPage = function(data) {\n\t\t\tdoc.text(title, 40, 30);\n\t\t};\n\t}\n\n\tautoTableParams.head = header;\n\tautoTableParams.body = body;\n\n\tdoc.autoTable(autoTableParams);\n\n\tif(options.documentProcessing){\n\t\toptions.documentProcessing(doc);\n\t}\n\n\tsetFileContents(doc.output(\"arraybuffer\"), \"application/pdf\");\n}\n\nfunction xlsx(list, options, setFileContents){\n\tvar self = this,\n\tsheetName = options.sheetName || \"Sheet1\",\n\tworkbook = XLSX.utils.book_new(),\n\ttableFeatures = new CoreFeature(this),\n\tcompression =  'compress' in options ? options.compress : true,\n\twriteOptions = options.writeOptions || {bookType:'xlsx', bookSST:true, compression},\n\toutput;\n\n\twriteOptions.type = 'binary';\n\n\tworkbook.SheetNames = [];\n\tworkbook.Sheets = {};\n\n\tfunction generateSheet(){\n\t\tvar rows = [],\n\t\tmerges = [],\n\t\tworksheet = {},\n\t\trange = {s: {c:0, r:0}, e: {c:(list[0] ? list[0].columns.reduce((a, b) => a + (b && b.width ? b.width : 1), 0) : 0), r:list.length }};\n\n\t\t//parse row list\n\t\tlist.forEach((row, i) => {\n\t\t\tvar rowData = [];\n\n\t\t\trow.columns.forEach(function(col, j){\n\n\t\t\t\tif(col){\n\t\t\t\t\trowData.push(!(col.value instanceof Date) && typeof col.value === \"object\" ? JSON.stringify(col.value) : col.value);\n\n\t\t\t\t\tif(col.width > 1 || col.height > -1){\n\t\t\t\t\t\tif(col.height > 1 || col.width > 1){\n\t\t\t\t\t\t\tmerges.push({s:{r:i,c:j},e:{r:i + col.height - 1,c:j + col.width - 1}});\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}else {\n\t\t\t\t\trowData.push(\"\");\n\t\t\t\t}\n\t\t\t});\n\n\t\t\trows.push(rowData);\n\t\t});\n\n\t\t//convert rows to worksheet\n\t\tXLSX.utils.sheet_add_aoa(worksheet, rows);\n\n\t\tworksheet['!ref'] = XLSX.utils.encode_range(range);\n\n\t\tif(merges.length){\n\t\t\tworksheet[\"!merges\"] = merges;\n\t\t}\n\n\t\treturn worksheet;\n\t}\n\n\tif(options.sheetOnly){\n\t\tsetFileContents(generateSheet());\n\t\treturn;\n\t}\n\n\tif(options.sheets){\n\t\tfor(var sheet in options.sheets){\n\n\t\t\tif(options.sheets[sheet] === true){\n\t\t\t\tworkbook.SheetNames.push(sheet);\n\t\t\t\tworkbook.Sheets[sheet] = generateSheet();\n\t\t\t}else {\n\n\t\t\t\tworkbook.SheetNames.push(sheet);\n\n\t\t\t\ttableFeatures.commsSend(options.sheets[sheet], \"download\", \"intercept\",{\n\t\t\t\t\ttype:\"xlsx\",\n\t\t\t\t\toptions:{sheetOnly:true},\n\t\t\t\t\tactive:self.active,\n\t\t\t\t\tintercept:function(data){\n\t\t\t\t\t\tworkbook.Sheets[sheet] = data;\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t}\n\t\t}\n\t}else {\n\t\tworkbook.SheetNames.push(sheetName);\n\t\tworkbook.Sheets[sheetName] = generateSheet();\n\t}\n\n\tif(options.documentProcessing){\n\t\tworkbook = options.documentProcessing(workbook);\n\t}\n\n\t//convert workbook to binary array\n\tfunction s2ab(s) {\n\t\tvar buf = new ArrayBuffer(s.length);\n\t\tvar view = new Uint8Array(buf);\n\t\tfor (var i=0; i!=s.length; ++i) view[i] = s.charCodeAt(i) & 0xFF;\n\t\treturn buf;\n\t}\n\n\toutput = XLSX.write(workbook, writeOptions);\n\n\tsetFileContents(s2ab(output), \"application/octet-stream\");\n}\n\nfunction html(list, options, setFileContents){\n\tif(this.modExists(\"export\", true)){\n\t\tsetFileContents(this.modules.export.generateHTMLTable(list), \"text/html\");\n\t}\n}\n\nfunction jsonLines (list, options, setFileContents) {\n\tconst fileContents = [];\n\n\tlist.forEach((row) => {\n\t\tconst item = {};\n\n\t\tswitch (row.type) {\n\t\t\tcase \"header\":\n\t\t\t\tbreak;\n\n\t\t\tcase \"group\":\n\t\t\t\tconsole.warn(\"Download Warning - JSON downloader cannot process row groups\");\n\t\t\t\tbreak;\n\n\t\t\tcase \"calc\":\n\t\t\t\tconsole.warn(\"Download Warning - JSON downloader cannot process column calculations\");\n\t\t\t\tbreak;\n\n\t\t\tcase \"row\":\n\t\t\t\trow.columns.forEach((col) => {\n\t\t\t\t\tif (col) {\n\t\t\t\t\t\titem[col.component.getTitleDownload() || col.component.getField()] = col.value;\n\t\t\t\t\t}\n\t\t\t\t});\n\n\t\t\t\tfileContents.push(JSON.stringify(item));\n\t\t\t\tbreak;\n\t\t}\n\t});\n\n\tsetFileContents(fileContents.join(\"\\n\"), \"application/x-ndjson\");\n}\n\nvar defaultDownloaders = {\n\tcsv:csv,\n\tjson:json,\n\tjsonLines:jsonLines,\n\tpdf:pdf,\n\txlsx:xlsx,\n\thtml:html,\n};\n\nclass Download extends Module{\n\n\tconstructor(table){\n\t\tsuper(table);\n\n\t\tthis.registerTableOption(\"downloadEncoder\", function(data, mimeType){\n\t\t\treturn new Blob([data],{type:mimeType});\n\t\t}); //function to manipulate download data\n\t\tthis.registerTableOption(\"downloadReady\", undefined); //warn of function deprecation\n\t\tthis.registerTableOption(\"downloadConfig\", {}); //download config\n\t\tthis.registerTableOption(\"downloadRowRange\", \"active\"); //restrict download to active rows only\n\n\t\tthis.registerColumnOption(\"download\");\n\t\tthis.registerColumnOption(\"titleDownload\");\n\t}\n\n\tinitialize(){\n\t\tthis.deprecatedOptionsCheck();\n\n\t\tthis.registerTableFunction(\"download\", this.download.bind(this));\n\t\tthis.registerTableFunction(\"downloadToTab\", this.downloadToTab.bind(this));\n\t}\n\n\tdeprecatedOptionsCheck(){\n\t\tthis.deprecationCheck(\"downloadReady\", \"downloadEncoder\");\n\t}\t\n\n\t///////////////////////////////////\n\t///////// Table Functions /////////\n\t///////////////////////////////////\n\n\tdownloadToTab(type, filename, options, active){\n\t\tthis.download(type, filename, options, active, true);\n\t}\n\n\t///////////////////////////////////\n\t///////// Internal Logic //////////\n\t///////////////////////////////////\n\n\t//trigger file download\n\tdownload(type, filename, options, range, interceptCallback){\n\t\tvar downloadFunc = false;\n\n\t\tfunction buildLink(data, mime){\n\t\t\tif(interceptCallback){\n\t\t\t\tif(interceptCallback === true){\n\t\t\t\t\tthis.triggerDownload(data, mime, type, filename, true);\n\t\t\t\t}else {\n\t\t\t\t\tinterceptCallback(data);\n\t\t\t\t}\n\n\t\t\t}else {\n\t\t\t\tthis.triggerDownload(data, mime, type, filename);\n\t\t\t}\n\t\t}\n\n\t\tif(typeof type == \"function\"){\n\t\t\tdownloadFunc = type;\n\t\t}else {\n\t\t\tif(Download.downloaders[type]){\n\t\t\t\tdownloadFunc = Download.downloaders[type];\n\t\t\t}else {\n\t\t\t\tconsole.warn(\"Download Error - No such download type found: \", type);\n\t\t\t}\n\t\t}\n\n\t\tif(downloadFunc){\n\t\t\tvar list = this.generateExportList(range);\n\n\t\t\tdownloadFunc.call(this.table, list , options || {}, buildLink.bind(this));\n\t\t}\n\t}\n\n\tgenerateExportList(range){\n\t\tvar list = this.table.modules.export.generateExportList(this.table.options.downloadConfig, false, range || this.table.options.downloadRowRange, \"download\");\n\n\t\t//assign group header formatter\n\t\tvar groupHeader = this.table.options.groupHeaderDownload;\n\n\t\tif(groupHeader && !Array.isArray(groupHeader)){\n\t\t\tgroupHeader = [groupHeader];\n\t\t}\n\n\t\tlist.forEach((row) => {\n\t\t\tvar group;\n\n\t\t\tif(row.type === \"group\"){\n\t\t\t\tgroup = row.columns[0];\n\n\t\t\t\tif(groupHeader && groupHeader[row.indent]){\n\t\t\t\t\tgroup.value = groupHeader[row.indent](group.value, row.component._group.getRowCount(), row.component._group.getData(), row.component);\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\n\t\treturn list;\n\t}\n\n\ttriggerDownload(data, mime, type, filename, newTab){\n\t\tvar element = document.createElement('a'),\n\t\tblob = this.table.options.downloadEncoder(data, mime);\n\n\t\tif(blob){\n\t\t\tif(newTab){\n\t\t\t\twindow.open(window.URL.createObjectURL(blob));\n\t\t\t}else {\n\t\t\t\tfilename = filename || \"Tabulator.\" + (typeof type === \"function\" ? \"txt\" : type);\n\t\t\t\t\n\t\t\t\tif(navigator.msSaveOrOpenBlob){\n\t\t\t\t\tnavigator.msSaveOrOpenBlob(blob, filename);\n\t\t\t\t}else {\n\t\t\t\t\telement.setAttribute('href', window.URL.createObjectURL(blob));\n\n\t\t\t\t\t//set file title\n\t\t\t\t\telement.setAttribute('download', filename);\n\n\t\t\t\t\t//trigger download\n\t\t\t\t\telement.style.display = 'none';\n\t\t\t\t\tdocument.body.appendChild(element);\n\t\t\t\t\telement.click();\n\n\t\t\t\t\t//remove temporary link element\n\t\t\t\t\tdocument.body.removeChild(element);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tthis.dispatchExternal(\"downloadComplete\");\n\t\t}\n\t}\n\n\tcommsReceived(table, action, data){\n\t\tswitch(action){\n\t\t\tcase \"intercept\":\n\t\t\t\tthis.download(data.type, \"\", data.options, data.active, data.intercept);\n\t\t\t\tbreak;\n\t\t}\n\t}\n}\n\nDownload.moduleName = \"download\";\n\n//load defaults\nDownload.downloaders = defaultDownloaders;\n\nfunction maskInput(el, options){\n\tvar mask = options.mask,\n\tmaskLetter = typeof options.maskLetterChar !== \"undefined\" ? options.maskLetterChar : \"A\",\n\tmaskNumber = typeof options.maskNumberChar !== \"undefined\" ? options.maskNumberChar : \"9\",\n\tmaskWildcard = typeof options.maskWildcardChar !== \"undefined\" ? options.maskWildcardChar : \"*\";\n\n\tfunction fillSymbols(index){\n\t\tvar symbol = mask[index];\n\t\tif(typeof symbol !== \"undefined\" && symbol !== maskWildcard && symbol !== maskLetter && symbol !== maskNumber){\n\t\t\tel.value = el.value + \"\" + symbol;\n\t\t\tfillSymbols(index+1);\n\t\t}\n\t}\n\n\tel.addEventListener(\"keydown\", (e) => {\n\t\tvar index = el.value.length,\n\t\tchar = e.key;\n\n\t\tif(e.keyCode > 46 && !e.ctrlKey && !e.metaKey){\n\t\t\tif(index >= mask.length){\n\t\t\t\te.preventDefault();\n\t\t\t\te.stopPropagation();\n\t\t\t\treturn false;\n\t\t\t}else {\n\t\t\t\tswitch(mask[index]){\n\t\t\t\t\tcase maskLetter:\n\t\t\t\t\t\tif(char.toUpperCase() == char.toLowerCase()){\n\t\t\t\t\t\t\te.preventDefault();\n\t\t\t\t\t\t\te.stopPropagation();\n\t\t\t\t\t\t\treturn false;\n\t\t\t\t\t\t}\n\t\t\t\t\t\tbreak;\n\n\t\t\t\t\tcase maskNumber:\n\t\t\t\t\t\tif(isNaN(char)){\n\t\t\t\t\t\t\te.preventDefault();\n\t\t\t\t\t\t\te.stopPropagation();\n\t\t\t\t\t\t\treturn false;\n\t\t\t\t\t\t}\n\t\t\t\t\t\tbreak;\n\n\t\t\t\t\tcase maskWildcard:\n\t\t\t\t\t\tbreak;\n\n\t\t\t\t\tdefault:\n\t\t\t\t\t\tif(char !== mask[index]){\n\t\t\t\t\t\t\te.preventDefault();\n\t\t\t\t\t\t\te.stopPropagation();\n\t\t\t\t\t\t\treturn false;\n\t\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn;\n\t});\n\n\tel.addEventListener(\"keyup\", (e) => {\n\t\tif(e.keyCode > 46){\n\t\t\tif(options.maskAutoFill){\n\t\t\t\tfillSymbols(el.value.length);\n\t\t\t}\n\t\t}\n\t});\n\n\n\tif(!el.placeholder){\n\t\tel.placeholder = mask;\n\t}\n\n\tif(options.maskAutoFill){\n\t\tfillSymbols(el.value.length);\n\t}\n}\n\n//input element\nfunction input(cell, onRendered, success, cancel, editorParams){\n\t//create and style input\n\tvar cellValue = cell.getValue(),\n\tinput = document.createElement(\"input\");\n\n\tinput.setAttribute(\"type\", editorParams.search ? \"search\" : \"text\");\n\n\tinput.style.padding = \"4px\";\n\tinput.style.width = \"100%\";\n\tinput.style.boxSizing = \"border-box\";\n\n\tif(editorParams.elementAttributes && typeof editorParams.elementAttributes == \"object\"){\n\t\tfor (let key in editorParams.elementAttributes){\n\t\t\tif(key.charAt(0) == \"+\"){\n\t\t\t\tkey = key.slice(1);\n\t\t\t\tinput.setAttribute(key, input.getAttribute(key) + editorParams.elementAttributes[\"+\" + key]);\n\t\t\t}else {\n\t\t\t\tinput.setAttribute(key, editorParams.elementAttributes[key]);\n\t\t\t}\n\t\t}\n\t}\n\n\tinput.value = typeof cellValue !== \"undefined\" ? cellValue : \"\";\n\n\tonRendered(function(){\n\t\tif(cell.getType() === \"cell\"){\n\t\t\tinput.focus({preventScroll: true});\n\t\t\tinput.style.height = \"100%\";\n\n\t\t\tif(editorParams.selectContents){\n\t\t\t\tinput.select();\n\t\t\t}\n\t\t}\n\t});\n\n\tfunction onChange(e){\n\t\tif(((cellValue === null || typeof cellValue === \"undefined\") && input.value !== \"\") || input.value !== cellValue){\n\t\t\tif(success(input.value)){\n\t\t\t\tcellValue = input.value; //persist value if successfully validated incase editor is used as header filter\n\t\t\t}\n\t\t}else {\n\t\t\tcancel();\n\t\t}\n\t}\n\n\t//submit new value on blur or change\n\tinput.addEventListener(\"change\", onChange);\n\tinput.addEventListener(\"blur\", onChange);\n\n\t//submit new value on enter\n\tinput.addEventListener(\"keydown\", function(e){\n\t\tswitch(e.keyCode){\n\t\t\t// case 9:\n\t\t\tcase 13:\n\t\t\t\tonChange();\n\t\t\t\tbreak;\n\n\t\t\tcase 27:\n\t\t\t\tcancel();\n\t\t\t\tbreak;\n\n\t\t\tcase 35:\n\t\t\tcase 36:\n\t\t\t\te.stopPropagation();\n\t\t\t\tbreak;\n\t\t}\n\t});\n\n\tif(editorParams.mask){\n\t\tmaskInput(input, editorParams);\n\t}\n\n\treturn input;\n}\n\n//resizable text area element\nfunction textarea(cell, onRendered, success, cancel, editorParams){\n\tvar cellValue = cell.getValue(),\n\tvertNav = editorParams.verticalNavigation || \"hybrid\",\n\tvalue = String(cellValue !== null && typeof cellValue !== \"undefined\"  ? cellValue : \"\"),\n\tinput = document.createElement(\"textarea\"),\n\tscrollHeight = 0;\n\n\t//create and style input\n\tinput.style.display = \"block\";\n\tinput.style.padding = \"2px\";\n\tinput.style.height = \"100%\";\n\tinput.style.width = \"100%\";\n\tinput.style.boxSizing = \"border-box\";\n\tinput.style.whiteSpace = \"pre-wrap\";\n\tinput.style.resize = \"none\";\n\n\tif(editorParams.elementAttributes && typeof editorParams.elementAttributes == \"object\"){\n\t\tfor (let key in editorParams.elementAttributes){\n\t\t\tif(key.charAt(0) == \"+\"){\n\t\t\t\tkey = key.slice(1);\n\t\t\t\tinput.setAttribute(key, input.getAttribute(key) + editorParams.elementAttributes[\"+\" + key]);\n\t\t\t}else {\n\t\t\t\tinput.setAttribute(key, editorParams.elementAttributes[key]);\n\t\t\t}\n\t\t}\n\t}\n\n\tinput.value = value;\n\n\tonRendered(function(){\n\t\tif(cell.getType() === \"cell\"){\n\t\t\tinput.focus({preventScroll: true});\n\t\t\tinput.style.height = \"100%\";\n\n\t\t\tinput.scrollHeight;\n\t\t\tinput.style.height = input.scrollHeight + \"px\";\n\t\t\tcell.getRow().normalizeHeight();\n\n\t\t\tif(editorParams.selectContents){\n\t\t\t\tinput.select();\n\t\t\t}\n\t\t}\n\t});\n\n\tfunction onChange(e){\n\n\t\tif(((cellValue === null || typeof cellValue === \"undefined\") && input.value !== \"\") || input.value !== cellValue){\n\n\t\t\tif(success(input.value)){\n\t\t\t\tcellValue = input.value; //persist value if successfully validated incase editor is used as header filter\n\t\t\t}\n\n\t\t\tsetTimeout(function(){\n\t\t\t\tcell.getRow().normalizeHeight();\n\t\t\t},300);\n\t\t}else {\n\t\t\tcancel();\n\t\t}\n\t}\n\n\t//submit new value on blur or change\n\tinput.addEventListener(\"change\", onChange);\n\tinput.addEventListener(\"blur\", onChange);\n\n\tinput.addEventListener(\"keyup\", function(){\n\n\t\tinput.style.height = \"\";\n\n\t\tvar heightNow = input.scrollHeight;\n\n\t\tinput.style.height = heightNow + \"px\";\n\n\t\tif(heightNow != scrollHeight){\n\t\t\tscrollHeight = heightNow;\n\t\t\tcell.getRow().normalizeHeight();\n\t\t}\n\t});\n\n\tinput.addEventListener(\"keydown\", function(e){\n\n\t\tswitch(e.keyCode){\n\n\t\t\tcase 13:\n\t\t\t\tif(e.shiftKey && editorParams.shiftEnterSubmit){\n\t\t\t\t\tonChange();\n\t\t\t\t}\n\t\t\t\tbreak;\n\n\t\t\tcase 27:\n\t\t\t\tcancel();\n\t\t\t\tbreak;\n\n\t\t\tcase 38: //up arrow\n\t\t\t\tif(vertNav == \"editor\" || (vertNav == \"hybrid\" && input.selectionStart)){\n\t\t\t\t\te.stopImmediatePropagation();\n\t\t\t\t\te.stopPropagation();\n\t\t\t\t}\n\n\t\t\t\tbreak;\n\n\t\t\tcase 40: //down arrow\n\t\t\t\tif(vertNav == \"editor\" || (vertNav == \"hybrid\" && input.selectionStart !== input.value.length)){\n\t\t\t\t\te.stopImmediatePropagation();\n\t\t\t\t\te.stopPropagation();\n\t\t\t\t}\n\t\t\t\tbreak;\n\n\t\t\tcase 35:\n\t\t\tcase 36:\n\t\t\t\te.stopPropagation();\n\t\t\t\tbreak;\n\t\t}\n\t});\n\n\tif(editorParams.mask){\n\t\tmaskInput(input, editorParams);\n\t}\n\n\treturn input;\n}\n\n//input element with type of number\nfunction number(cell, onRendered, success, cancel, editorParams){\n\tvar cellValue = cell.getValue(),\n\tvertNav = editorParams.verticalNavigation || \"editor\",\n\tinput = document.createElement(\"input\");\n\n\tinput.setAttribute(\"type\", \"number\");\n\n\tif(typeof editorParams.max != \"undefined\"){\n\t\tinput.setAttribute(\"max\", editorParams.max);\n\t}\n\n\tif(typeof editorParams.min != \"undefined\"){\n\t\tinput.setAttribute(\"min\", editorParams.min);\n\t}\n\n\tif(typeof editorParams.step != \"undefined\"){\n\t\tinput.setAttribute(\"step\", editorParams.step);\n\t}\n\n\t//create and style input\n\tinput.style.padding = \"4px\";\n\tinput.style.width = \"100%\";\n\tinput.style.boxSizing = \"border-box\";\n\n\tif(editorParams.elementAttributes && typeof editorParams.elementAttributes == \"object\"){\n\t\tfor (let key in editorParams.elementAttributes){\n\t\t\tif(key.charAt(0) == \"+\"){\n\t\t\t\tkey = key.slice(1);\n\t\t\t\tinput.setAttribute(key, input.getAttribute(key) + editorParams.elementAttributes[\"+\" + key]);\n\t\t\t}else {\n\t\t\t\tinput.setAttribute(key, editorParams.elementAttributes[key]);\n\t\t\t}\n\t\t}\n\t}\n\n\tinput.value = cellValue;\n\n\tvar blurFunc = function(e){\n\t\tonChange();\n\t};\n\n\tonRendered(function () {\n\t\tif(cell.getType() === \"cell\"){\n\t\t\t//submit new value on blur\n\t\t\tinput.removeEventListener(\"blur\", blurFunc);\n\n\t\t\tinput.focus({preventScroll: true});\n\t\t\tinput.style.height = \"100%\";\n\n\t\t\t//submit new value on blur\n\t\t\tinput.addEventListener(\"blur\", blurFunc);\n\n\t\t\tif(editorParams.selectContents){\n\t\t\t\tinput.select();\n\t\t\t}\n\t\t}\n\t});\n\n\tfunction onChange(){\n\t\tvar value = input.value;\n\n\t\tif(!isNaN(value) && value !==\"\"){\n\t\t\tvalue = Number(value);\n\t\t}\n\n\t\tif(value !== cellValue){\n\t\t\tif(success(value)){\n\t\t\t\tcellValue = value; //persist value if successfully validated incase editor is used as header filter\n\t\t\t}\n\t\t}else {\n\t\t\tcancel();\n\t\t}\n\t}\n\n\t//submit new value on enter\n\tinput.addEventListener(\"keydown\", function(e){\n\t\tswitch(e.keyCode){\n\t\t\tcase 13:\n\t\t\t// case 9:\n\t\t\t\tonChange();\n\t\t\t\tbreak;\n\n\t\t\tcase 27:\n\t\t\t\tcancel();\n\t\t\t\tbreak;\n\n\t\t\tcase 38: //up arrow\n\t\t\tcase 40: //down arrow\n\t\t\t\tif(vertNav == \"editor\"){\n\t\t\t\t\te.stopImmediatePropagation();\n\t\t\t\t\te.stopPropagation();\n\t\t\t\t}\n\t\t\t\tbreak;\n\n\t\t\tcase 35:\n\t\t\tcase 36:\n\t\t\t\te.stopPropagation();\n\t\t\t\tbreak;\n\t\t}\n\t});\n\n\tif(editorParams.mask){\n\t\tmaskInput(input, editorParams);\n\t}\n\n\treturn input;\n}\n\n//input element with type of number\nfunction range(cell, onRendered, success, cancel, editorParams){\n\tvar cellValue = cell.getValue(),\n\tinput = document.createElement(\"input\");\n\t\n\tinput.setAttribute(\"type\", \"range\");\n\t\n\tif (typeof editorParams.max != \"undefined\") {\n\t\tinput.setAttribute(\"max\", editorParams.max);\n\t}\n\t\n\tif (typeof editorParams.min != \"undefined\") {\n\t\tinput.setAttribute(\"min\", editorParams.min);\n\t}\n\t\n\tif (typeof editorParams.step != \"undefined\") {\n\t\tinput.setAttribute(\"step\", editorParams.step);\n\t}\n\t\n\t//create and style input\n\tinput.style.padding = \"4px\";\n\tinput.style.width = \"100%\";\n\tinput.style.boxSizing = \"border-box\";\n\t\n\tif(editorParams.elementAttributes && typeof editorParams.elementAttributes == \"object\"){\n\t\tfor (let key in editorParams.elementAttributes){\n\t\t\tif(key.charAt(0) == \"+\"){\n\t\t\t\tkey = key.slice(1);\n\t\t\t\tinput.setAttribute(key, input.getAttribute(key) + editorParams.elementAttributes[\"+\" + key]);\n\t\t\t}else {\n\t\t\t\tinput.setAttribute(key, editorParams.elementAttributes[key]);\n\t\t\t}\n\t\t}\n\t}\n\t\n\tinput.value = cellValue;\n\t\n\tonRendered(function () {\n\t\tif(cell.getType() === \"cell\"){\n\t\t\tinput.focus({preventScroll: true});\n\t\t\tinput.style.height = \"100%\";\n\t\t}\n\t});\n\t\n\tfunction onChange(){\n\t\tvar value = input.value;\n\t\t\n\t\tif(!isNaN(value) && value !==\"\"){\n\t\t\tvalue = Number(value);\n\t\t}\n\t\t\n\t\tif(value != cellValue){\n\t\t\tif(success(value)){\n\t\t\t\tcellValue = value; //persist value if successfully validated incase editor is used as header filter\n\t\t\t}\n\t\t}else {\n\t\t\tcancel();\n\t\t}\n\t}\n\t\n\t//submit new value on blur\n\tinput.addEventListener(\"blur\", function(e){\n\t\tonChange();\n\t});\n\t\n\t//submit new value on enter\n\tinput.addEventListener(\"keydown\", function(e){\n\t\tswitch(e.keyCode){\n\t\t\tcase 13:\n\t\t\t// case 9:\n\t\t\t\tonChange();\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase 27:\n\t\t\t\tcancel();\n\t\t\t\tbreak;\n\t\t}\n\t});\n\t\n\treturn input;\n}\n\n//input element\nfunction date(cell, onRendered, success, cancel, editorParams){\n\tvar inputFormat = editorParams.format,\n\tvertNav = editorParams.verticalNavigation || \"editor\",\n\tDT = inputFormat ? (window.DateTime || luxon.DateTime) : null;\n\t\n\t//create and style input\n\tvar cellValue = cell.getValue(),\n\tinput = document.createElement(\"input\");\n\t\n\tfunction convertDate(value){\n\t\tvar newDatetime;\n\t\t\n\t\tif(DT.isDateTime(value)){\n\t\t\tnewDatetime = value;\n\t\t}else if(inputFormat === \"iso\"){\n\t\t\tnewDatetime = DT.fromISO(String(value));\n\t\t}else {\n\t\t\tnewDatetime = DT.fromFormat(String(value), inputFormat);\n\t\t}\n\t\t\n\t\treturn newDatetime.toFormat(\"yyyy-MM-dd\");\n\t}\n\t\n\tinput.type = \"date\";\n\tinput.style.padding = \"4px\";\n\tinput.style.width = \"100%\";\n\tinput.style.boxSizing = \"border-box\";\n\n\tif(editorParams.max){\n\t\tinput.setAttribute(\"max\", inputFormat ? convertDate(editorParams.max) : editorParams.max);\n\t}\n\n\tif(editorParams.min){\n\t\tinput.setAttribute(\"min\", inputFormat ? convertDate(editorParams.min) : editorParams.min);\n\t}\n\t\n\tif(editorParams.elementAttributes && typeof editorParams.elementAttributes == \"object\"){\n\t\tfor (let key in editorParams.elementAttributes){\n\t\t\tif(key.charAt(0) == \"+\"){\n\t\t\t\tkey = key.slice(1);\n\t\t\t\tinput.setAttribute(key, input.getAttribute(key) + editorParams.elementAttributes[\"+\" + key]);\n\t\t\t}else {\n\t\t\t\tinput.setAttribute(key, editorParams.elementAttributes[key]);\n\t\t\t}\n\t\t}\n\t}\n\t\n\tcellValue = typeof cellValue !== \"undefined\" ? cellValue : \"\";\n\t\n\tif(inputFormat){\n\t\tif(DT){\t\t\n\t\t\tcellValue = convertDate(cellValue);\t\t\t\n\t\t}else {\n\t\t\tconsole.error(\"Editor Error - 'date' editor 'format' param is dependant on luxon.js\");\n\t\t}\n\t}\n\t\n\tinput.value = cellValue;\n\t\n\tonRendered(function(){\n\t\tif(cell.getType() === \"cell\"){\n\t\t\tinput.focus({preventScroll: true});\n\t\t\tinput.style.height = \"100%\";\n\t\t\t\n\t\t\tif(editorParams.selectContents){\n\t\t\t\tinput.select();\n\t\t\t}\n\t\t}\n\t});\n\t\n\tfunction onChange(){\n\t\tvar value = input.value,\n\t\tluxDate;\n\t\t\n\t\tif(((cellValue === null || typeof cellValue === \"undefined\") && value !== \"\") || value !== cellValue){\n\t\t\t\n\t\t\tif(value && inputFormat){\n\t\t\t\tluxDate = DT.fromFormat(String(value), \"yyyy-MM-dd\");\n\n\t\t\t\tswitch(inputFormat){\n\t\t\t\t\tcase true:\n\t\t\t\t\t\tvalue = luxDate;\n\t\t\t\t\t\tbreak;\n\n\t\t\t\t\tcase \"iso\":\n\t\t\t\t\t\tvalue = luxDate.toISO();\n\t\t\t\t\t\tbreak;\n\n\t\t\t\t\tdefault:\n\t\t\t\t\t\tvalue = luxDate.toFormat(inputFormat);\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\tif(success(value)){\n\t\t\t\tcellValue = input.value; //persist value if successfully validated incase editor is used as header filter\n\t\t\t}\n\t\t}else {\n\t\t\tcancel();\n\t\t}\n\t}\n\t\n\t//submit new value on blur\n\tinput.addEventListener(\"blur\", function(e) {\n\t\tif (e.relatedTarget || e.rangeParent || e.explicitOriginalTarget !== input) {\n\t\t\tonChange(); // only on a \"true\" blur; not when focusing browser's date/time picker\n\t\t}\n\t});\n\t\n\t//submit new value on enter\n\tinput.addEventListener(\"keydown\", function(e){\n\t\tswitch(e.keyCode){\n\t\t\t// case 9:\n\t\t\tcase 13:\n\t\t\t\tonChange();\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase 27:\n\t\t\t\tcancel();\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase 35:\n\t\t\tcase 36:\n\t\t\t\te.stopPropagation();\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase 38: //up arrow\n\t\t\tcase 40: //down arrow\n\t\t\t\tif(vertNav == \"editor\"){\n\t\t\t\t\te.stopImmediatePropagation();\n\t\t\t\t\te.stopPropagation();\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t}\n\t});\n\t\n\treturn input;\n}\n\n//input element\nfunction time(cell, onRendered, success, cancel, editorParams){\n\tvar inputFormat = editorParams.format,\n\tvertNav = editorParams.verticalNavigation || \"editor\",\n\tDT = inputFormat ? (window.DateTime || luxon.DateTime) : null, \n\tnewDatetime;\n\t\n\t//create and style input\n\tvar cellValue = cell.getValue(),\n\tinput = document.createElement(\"input\");\n\t\n\tinput.type = \"time\";\n\tinput.style.padding = \"4px\";\n\tinput.style.width = \"100%\";\n\tinput.style.boxSizing = \"border-box\";\n\t\n\tif(editorParams.elementAttributes && typeof editorParams.elementAttributes == \"object\"){\n\t\tfor (let key in editorParams.elementAttributes){\n\t\t\tif(key.charAt(0) == \"+\"){\n\t\t\t\tkey = key.slice(1);\n\t\t\t\tinput.setAttribute(key, input.getAttribute(key) + editorParams.elementAttributes[\"+\" + key]);\n\t\t\t}else {\n\t\t\t\tinput.setAttribute(key, editorParams.elementAttributes[key]);\n\t\t\t}\n\t\t}\n\t}\n\t\n\tcellValue = typeof cellValue !== \"undefined\" ? cellValue : \"\";\n\t\n\tif(inputFormat){\n\t\tif(DT){\n\t\t\tif(DT.isDateTime(cellValue)){\n\t\t\t\tnewDatetime = cellValue;\n\t\t\t}else if(inputFormat === \"iso\"){\n\t\t\t\tnewDatetime = DT.fromISO(String(cellValue));\n\t\t\t}else {\n\t\t\t\tnewDatetime = DT.fromFormat(String(cellValue), inputFormat);\n\t\t\t}\n\t\t\t\n\t\t\tcellValue = newDatetime.toFormat(\"HH:mm\");\n\t\t\t\n\t\t}else {\n\t\t\tconsole.error(\"Editor Error - 'date' editor 'format' param is dependant on luxon.js\");\n\t\t}\n\t}\n\n\tconsole.log(\"val\", cellValue);\n\t\n\tinput.value = cellValue;\n\t\n\tonRendered(function(){\n\t\tif(cell.getType() == \"cell\"){\n\t\t\tinput.focus({preventScroll: true});\n\t\t\tinput.style.height = \"100%\";\n\t\t\t\n\t\t\tif(editorParams.selectContents){\n\t\t\t\tinput.select();\n\t\t\t}\n\t\t}\n\t});\n\t\n\tfunction onChange(){\n\t\tvar value = input.value,\n\t\tluxTime;\n\t\t\n\t\tif(((cellValue === null || typeof cellValue === \"undefined\") && value !== \"\") || value !== cellValue){\n\t\t\t\n\t\t\tif(value && inputFormat){\n\t\t\t\tluxTime = DT.fromFormat(String(value), \"hh:mm\");\n\n\t\t\t\tswitch(inputFormat){\n\t\t\t\t\tcase true:\n\t\t\t\t\t\tvalue = luxTime;\n\t\t\t\t\t\tbreak;\n\n\t\t\t\t\tcase \"iso\":\n\t\t\t\t\t\tvalue = luxTime.toISO();\n\t\t\t\t\t\tbreak;\n\n\t\t\t\t\tdefault:\n\t\t\t\t\t\tvalue = luxTime.toFormat(inputFormat);\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\tif(success(value)){\n\t\t\t\tcellValue = input.value; //persist value if successfully validated incase editor is used as header filter\n\t\t\t}\n\t\t}else {\n\t\t\tcancel();\n\t\t}\n\t}\n\t\n\t//submit new value on blur\n\tinput.addEventListener(\"blur\", function(e) {\n\t\tif (e.relatedTarget || e.rangeParent || e.explicitOriginalTarget !== input) {\n\t\t\tonChange(); // only on a \"true\" blur; not when focusing browser's date/time picker\n\t\t}\n\t});\n\t\n\t//submit new value on enter\n\tinput.addEventListener(\"keydown\", function(e){\n\t\tswitch(e.keyCode){\n\t\t\t// case 9:\n\t\t\tcase 13:\n\t\t\t\tonChange();\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase 27:\n\t\t\t\tcancel();\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase 35:\n\t\t\tcase 36:\n\t\t\t\te.stopPropagation();\n\t\t\t\tbreak;\n\n\t\t\tcase 38: //up arrow\n\t\t\tcase 40: //down arrow\n\t\t\t\tif(vertNav == \"editor\"){\n\t\t\t\t\te.stopImmediatePropagation();\n\t\t\t\t\te.stopPropagation();\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t}\n\t});\n\t\n\treturn input;\n}\n\n//input element\nfunction datetime(cell, onRendered, success, cancel, editorParams){\n\tvar inputFormat = editorParams.format,\n\tvertNav = editorParams.verticalNavigation || \"editor\",\n\tDT = inputFormat ? (window.DateTime || luxon.DateTime) : null, \n\tnewDatetime;\n\t\n\t//create and style input\n\tvar cellValue = cell.getValue(),\n\tinput = document.createElement(\"input\");\n\t\n\tinput.type = \"datetime-local\";\n\tinput.style.padding = \"4px\";\n\tinput.style.width = \"100%\";\n\tinput.style.boxSizing = \"border-box\";\n\t\n\tif(editorParams.elementAttributes && typeof editorParams.elementAttributes == \"object\"){\n\t\tfor (let key in editorParams.elementAttributes){\n\t\t\tif(key.charAt(0) == \"+\"){\n\t\t\t\tkey = key.slice(1);\n\t\t\t\tinput.setAttribute(key, input.getAttribute(key) + editorParams.elementAttributes[\"+\" + key]);\n\t\t\t}else {\n\t\t\t\tinput.setAttribute(key, editorParams.elementAttributes[key]);\n\t\t\t}\n\t\t}\n\t}\n\t\n\tcellValue = typeof cellValue !== \"undefined\" ? cellValue : \"\";\n\t\n\tif(inputFormat){\n\t\tif(DT){\n\t\t\tif(DT.isDateTime(cellValue)){\n\t\t\t\tnewDatetime = cellValue;\n\t\t\t}else if(inputFormat === \"iso\"){\n\t\t\t\tnewDatetime = DT.fromISO(String(cellValue));\n\t\t\t}else {\n\t\t\t\tnewDatetime = DT.fromFormat(String(cellValue), inputFormat);\n\t\t\t}\n\t\t\t\n\t\t\tcellValue = newDatetime.toFormat(\"yyyy-MM-dd\")  + \"T\" + newDatetime.toFormat(\"HH:mm\");\n\t\t}else {\n\t\t\tconsole.error(\"Editor Error - 'date' editor 'format' param is dependant on luxon.js\");\n\t\t}\n\t}\n\t\n\tinput.value = cellValue;\n\t\n\tonRendered(function(){\n\t\tif(cell.getType() === \"cell\"){\n\t\t\tinput.focus({preventScroll: true});\n\t\t\tinput.style.height = \"100%\";\n\t\t\t\n\t\t\tif(editorParams.selectContents){\n\t\t\t\tinput.select();\n\t\t\t}\n\t\t}\n\t});\n\t\n\tfunction onChange(){\n\t\tvar value = input.value,\n\t\tluxDateTime;\n\t\t\n\t\tif(((cellValue === null || typeof cellValue === \"undefined\") && value !== \"\") || value !== cellValue){\n\n\t\t\tif(value && inputFormat){\n\t\t\t\tluxDateTime = DT.fromISO(String(value));\n\n\t\t\t\tswitch(inputFormat){\n\t\t\t\t\tcase true:\n\t\t\t\t\t\tvalue = luxDateTime;\n\t\t\t\t\t\tbreak;\n\n\t\t\t\t\tcase \"iso\":\n\t\t\t\t\t\tvalue = luxDateTime.toISO();\n\t\t\t\t\t\tbreak;\n\n\t\t\t\t\tdefault:\n\t\t\t\t\t\tvalue = luxDateTime.toFormat(inputFormat);\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\tif(success(value)){\n\t\t\t\tcellValue = input.value; //persist value if successfully validated incase editor is used as header filter\n\t\t\t}\n\t\t}else {\n\t\t\tcancel();\n\t\t}\n\t}\n\t\n\t//submit new value on blur\n\tinput.addEventListener(\"blur\", function(e) {\n\t\tif (e.relatedTarget || e.rangeParent || e.explicitOriginalTarget !== input) {\n\t\t\tonChange(); // only on a \"true\" blur; not when focusing browser's date/time picker\n\t\t}\n\t});\n\t\n\t//submit new value on enter\n\tinput.addEventListener(\"keydown\", function(e){\n\t\tswitch(e.keyCode){\n\t\t\t// case 9:\n\t\t\tcase 13:\n\t\t\t\tonChange();\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase 27:\n\t\t\t\tcancel();\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase 35:\n\t\t\tcase 36:\n\t\t\t\te.stopPropagation();\n\t\t\t\tbreak;\n\n\t\t\tcase 38: //up arrow\n\t\t\tcase 40: //down arrow\n\t\t\t\tif(vertNav == \"editor\"){\n\t\t\t\t\te.stopImmediatePropagation();\n\t\t\t\t\te.stopPropagation();\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t}\n\t});\n\t\n\treturn input;\n}\n\nclass Edit{\n\tconstructor(editor, cell, onRendered, success, cancel, editorParams){\n\t\tthis.edit = editor;\n\t\tthis.table = editor.table;\n\t\tthis.cell = cell;\n\t\tthis.params = this._initializeParams(editorParams);\n\t\t\n\t\tthis.data = [];\n\t\tthis.displayItems = [];\n\t\tthis.currentItems = [];\n\t\tthis.focusedItem = null;\n\t\t\n\t\tthis.input = this._createInputElement();\n\t\tthis.listEl = this._createListElement();\n\t\t\n\t\tthis.initialValues = null; \n\t\t\n\t\tthis.isFilter = cell.getType() === \"header\";\n\t\t\n\t\tthis.filterTimeout = null;\n\t\tthis.filtered = false;\n\t\tthis.typing = false;\n\t\t\n\t\tthis.values = []; \n\t\tthis.popup = null;  \n\t\t\n\t\tthis.listIteration = 0;\n\t\t\n\t\tthis.lastAction=\"\";\n\t\tthis.filterTerm=\"\";\n\t\t\n\t\tthis.blurable = true;\n\t\t\n\t\tthis.actions = {\n\t\t\tsuccess:success,\n\t\t\tcancel:cancel\n\t\t};\n\t\t\n\t\tthis._deprecatedOptionsCheck();\n\t\tthis._initializeValue();\n\t\t\n\t\tonRendered(this._onRendered.bind(this));\n\t}\n\t\n\t_deprecatedOptionsCheck(){\n\t\tif(this.params.listItemFormatter){\n\t\t\tthis.cell.getTable().deprecationAdvisor.msg(\"The listItemFormatter editor param has been deprecated, please see the latest editor documentation for updated options\");\n\t\t}\n\t\t\n\t\tif(this.params.sortValuesList){\n\t\t\tthis.cell.getTable().deprecationAdvisor.msg(\"The sortValuesList editor param has been deprecated, please see the latest editor documentation for updated options\");\n\t\t}\n\t\t\n\t\tif(this.params.searchFunc){\n\t\t\tthis.cell.getTable().deprecationAdvisor.msg(\"The searchFunc editor param has been deprecated, please see the latest editor documentation for updated options\");\n\t\t}\n\t\t\n\t\tif(this.params.searchingPlaceholder){\n\t\t\tthis.cell.getTable().deprecationAdvisor.msg(\"The searchingPlaceholder editor param has been deprecated, please see the latest editor documentation for updated options\");\n\t\t}\n\t}\n\t\n\t_initializeValue(){\n\t\tvar initialValue = this.cell.getValue();\n\t\t\n\t\tif(typeof initialValue === \"undefined\" && typeof this.params.defaultValue !== \"undefined\"){\n\t\t\tinitialValue = this.params.defaultValue;\n\t\t}\n\t\t\n\t\tthis.initialValues = this.params.multiselect ? initialValue : [initialValue];\n\t\t\n\t\tif(this.isFilter){\n\t\t\tthis.input.value = this.initialValues ? this.initialValues.join(\",\") : \"\";\n\t\t\tthis.headerFilterInitialListGen();            \n\t\t}\n\t}\n\t\n\t_onRendered(){\n\t\tvar cellEl = this.cell.getElement();\n\t\t\n\t\tfunction clickStop(e){\n\t\t\te.stopPropagation();\n\t\t}\t\n\t\t\n\t\tif(!this.isFilter){\n\t\t\tthis.input.style.height = \"100%\";\n\t\t\tthis.input.focus({preventScroll: true});\n\t\t}\n\t\t\n\t\t\n\t\tcellEl.addEventListener(\"click\", clickStop);\n\t\t\n\t\tsetTimeout(() => {\n\t\t\tcellEl.removeEventListener(\"click\", clickStop);\n\t\t}, 1000);\n\t\t\n\t\tthis.input.addEventListener(\"mousedown\", this._preventPopupBlur.bind(this));\n\t}\n\t\n\t_createListElement(){\n\t\tvar listEl = document.createElement(\"div\");\n\t\tlistEl.classList.add(\"tabulator-edit-list\");\n\t\t\n\t\tlistEl.addEventListener(\"mousedown\", this._preventBlur.bind(this));\n\t\tlistEl.addEventListener(\"keydown\", this._inputKeyDown.bind(this));\n\t\t\n\t\treturn listEl;\n\t}\n\t\n\t_setListWidth(){\n\t\tvar element = this.isFilter ? this.input : this.cell.getElement();\n\t\t\n\t\tthis.listEl.style.minWidth = element.offsetWidth + \"px\";\n\t\t\n\t\tif(this.params.maxWidth){\n\t\t\tif(this.params.maxWidth === true){\n\t\t\t\tthis.listEl.style.maxWidth = element.offsetWidth + \"px\";\n\t\t\t}else if(typeof this.params.maxWidth === \"number\"){\n\t\t\t\tthis.listEl.style.maxWidth = this.params.maxWidth + \"px\";\n\t\t\t}else {\n\t\t\t\tthis.listEl.style.maxWidth = this.params.maxWidth;\n\t\t\t}\n\t\t}\n\t\t\n\t}\n\t\n\t_createInputElement(){\n\t\tvar attribs = this.params.elementAttributes;\n\t\tvar input = document.createElement(\"input\");\n\t\t\n\t\tinput.setAttribute(\"type\", this.params.clearable ? \"search\" : \"text\");\n\t\t\n\t\tinput.style.padding = \"4px\";\n\t\tinput.style.width = \"100%\";\n\t\tinput.style.boxSizing = \"border-box\";\n\t\t\n\t\tif(!this.params.autocomplete){\n\t\t\tinput.style.cursor = \"default\";\n\t\t\tinput.style.caretColor = \"transparent\";\n\t\t\t// input.readOnly = (this.edit.currentCell != false);\n\t\t}\n\t\t\n\t\tif(attribs && typeof attribs == \"object\"){\n\t\t\tfor (let key in attribs){\n\t\t\t\tif(key.charAt(0) == \"+\"){\n\t\t\t\t\tkey = key.slice(1);\n\t\t\t\t\tinput.setAttribute(key, input.getAttribute(key) + attribs[\"+\" + key]);\n\t\t\t\t}else {\n\t\t\t\t\tinput.setAttribute(key, attribs[key]);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\tif(this.params.mask){\n\t\t\tmaskInput(input, this.params);\n\t\t}\n\t\t\n\t\tthis._bindInputEvents(input);\n\t\t\n\t\treturn input;\n\t}\n\t\n\t_initializeParams(params){\n\t\tvar valueKeys = [\"values\", \"valuesURL\", \"valuesLookup\"],\n\t\tvalueCheck;\n\t\t\n\t\tparams = Object.assign({}, params);\n\t\t\n\t\tparams.verticalNavigation = params.verticalNavigation || \"editor\";\n\t\tparams.placeholderLoading = typeof params.placeholderLoading === \"undefined\" ? \"Searching ...\" : params.placeholderLoading;\n\t\tparams.placeholderEmpty = typeof params.placeholderEmpty === \"undefined\" ? \"No Results Found\" : params.placeholderEmpty;\n\t\tparams.filterDelay = typeof params.filterDelay === \"undefined\" ? 300 : params.filterDelay;\n\t\t\n\t\tparams.emptyValue = Object.keys(params).includes(\"emptyValue\") ? params.emptyValue : \"\";\n\t\t\n\t\tvalueCheck = Object.keys(params).filter(key => valueKeys.includes(key)).length;\n\t\t\n\t\tif(!valueCheck){\n\t\t\tconsole.warn(\"list editor config error - either the values, valuesURL, or valuesLookup option must be set\");\n\t\t}else if(valueCheck > 1){\n\t\t\tconsole.warn(\"list editor config error - only one of the values, valuesURL, or valuesLookup options can be set on the same editor\");\n\t\t}\n\t\t\n\t\tif(params.autocomplete){\n\t\t\tif(params.multiselect){\n\t\t\t\tparams.multiselect = false;\n\t\t\t\tconsole.warn(\"list editor config error - multiselect option is not available when autocomplete is enabled\");\n\t\t\t}\n\t\t}else {\n\t\t\tif(params.freetext){\n\t\t\t\tparams.freetext = false;\n\t\t\t\tconsole.warn(\"list editor config error - freetext option is only available when autocomplete is enabled\");\n\t\t\t}\n\t\t\t\n\t\t\tif(params.filterFunc){\n\t\t\t\tparams.filterFunc = false;\n\t\t\t\tconsole.warn(\"list editor config error - filterFunc option is only available when autocomplete is enabled\");\n\t\t\t}\n\t\t\t\n\t\t\tif(params.filterRemote){\n\t\t\t\tparams.filterRemote = false;\n\t\t\t\tconsole.warn(\"list editor config error - filterRemote option is only available when autocomplete is enabled\");\n\t\t\t}\n\t\t\t\n\t\t\tif(params.mask){\n\t\t\t\tparams.mask = false;\n\t\t\t\tconsole.warn(\"list editor config error - mask option is only available when autocomplete is enabled\");\n\t\t\t}\n\t\t\t\n\t\t\tif(params.allowEmpty){\n\t\t\t\tparams.allowEmpty = false;\n\t\t\t\tconsole.warn(\"list editor config error - allowEmpty option is only available when autocomplete is enabled\");\n\t\t\t}\n\t\t\t\n\t\t\tif(params.listOnEmpty){\n\t\t\t\tparams.listOnEmpty = false;\n\t\t\t\tconsole.warn(\"list editor config error - listOnEmpty option is only available when autocomplete is enabled\");\n\t\t\t}\n\t\t}\n\t\t\n\t\tif(params.filterRemote && !(typeof params.valuesLookup === \"function\" || params.valuesURL)){\n\t\t\tparams.filterRemote = false;\n\t\t\tconsole.warn(\"list editor config error - filterRemote option should only be used when values list is populated from a remote source\");\n\t\t}\n\t\treturn params;\n\t}\n\t//////////////////////////////////////\n\t////////// Event Handling ////////////\n\t//////////////////////////////////////\n\t\n\t_bindInputEvents(input){\n\t\tinput.addEventListener(\"focus\", this._inputFocus.bind(this));\n\t\tinput.addEventListener(\"click\", this._inputClick.bind(this));\n\t\tinput.addEventListener(\"blur\", this._inputBlur.bind(this));\n\t\tinput.addEventListener(\"keydown\", this._inputKeyDown.bind(this));\n\t\tinput.addEventListener(\"search\", this._inputSearch.bind(this));\n\t\t\n\t\tif(this.params.autocomplete){\n\t\t\tinput.addEventListener(\"keyup\", this._inputKeyUp.bind(this));\n\t\t}\n\t}\n\t\n\t\n\t_inputFocus(e){\n\t\tthis.rebuildOptionsList();\n\t}\n\t\n\t_filter(){\n\t\tif(this.params.filterRemote){\n\t\t\tclearTimeout(this.filterTimeout);\n\t\t\t\n\t\t\tthis.filterTimeout = setTimeout(() => {\n\t\t\t\tthis.rebuildOptionsList();\n\t\t\t}, this.params.filterDelay);\n\t\t}else {\n\t\t\tthis._filterList();\n\t\t}\n\t}\n\t\n\t_inputClick(e){\n\t\te.stopPropagation();\n\t}\n\t\n\t_inputBlur(e){\n\t\tif(this.blurable){\n\t\t\tif(this.popup){\n\t\t\t\tthis.popup.hide();\n\t\t\t}else {\n\t\t\t\tthis._resolveValue(true);\n\t\t\t}\n\t\t}\n\t}\n\t\n\t_inputSearch(){\n\t\tthis._clearChoices();\n\t}\n\t\n\t_inputKeyDown(e){\n\t\tswitch(e.keyCode){\n\t\t\t\n\t\t\tcase 38: //up arrow\n\t\t\t\tthis._keyUp(e);\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase 40: //down arrow\n\t\t\t\tthis._keyDown(e);\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase 37: //left arrow\n\t\t\tcase 39: //right arrow\n\t\t\t\tthis._keySide(e);\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase 13: //enter\n\t\t\t\tthis._keyEnter();\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase 27: //escape\n\t\t\t\tthis._keyEsc();\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase 36: //home\n\t\t\tcase 35: //end\n\t\t\t\tthis._keyHomeEnd(e);\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase 9: //tab\n\t\t\t\tthis._keyTab(e);\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tdefault:\n\t\t\t\tthis._keySelectLetter(e);\n\t\t}\n\t}\n\t\n\t_inputKeyUp(e){\n\t\tswitch(e.keyCode){\n\t\t\tcase 38: //up arrow\n\t\t\tcase 37: //left arrow\n\t\t\tcase 39: //up arrow\n\t\t\tcase 40: //right arrow\n\t\t\tcase 13: //enter\n\t\t\tcase 27: //escape\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tdefault:\n\t\t\t\tthis._keyAutoCompLetter(e);\n\t\t}\n\t}\n\t\n\t_preventPopupBlur(){\n\t\tif(this.popup){\n\t\t\tthis.popup.blockHide();\n\t\t}\n\t\t\n\t\tsetTimeout(() =>{\n\t\t\tif(this.popup){\n\t\t\t\tthis.popup.restoreHide();\n\t\t\t}\n\t\t}, 10);\n\t}\n\t\n\t_preventBlur(){\n\t\tthis.blurable = false;\n\t\t\n\t\tsetTimeout(() =>{\n\t\t\tthis.blurable = true;\n\t\t}, 10);\n\t}\n\t\n\t//////////////////////////////////////\n\t//////// Keyboard Navigation /////////\n\t//////////////////////////////////////\n\t\n\t_keyTab(e){\n\t\tif(this.params.autocomplete && this.lastAction === \"typing\"){\n\t\t\tthis._resolveValue(true);\n\t\t}else {\n\t\t\tif(this.focusedItem){\n\t\t\t\tthis._chooseItem(this.focusedItem, true);\n\t\t\t}\n\t\t}\n\t}\n\t\n\t_keyUp(e){\n\t\tvar index = this.displayItems.indexOf(this.focusedItem);\n\t\t\n\t\tif(this.params.verticalNavigation == \"editor\" || (this.params.verticalNavigation == \"hybrid\" && index)){\n\t\t\te.stopImmediatePropagation();\n\t\t\te.stopPropagation();\n\t\t\te.preventDefault();\n\t\t\t\n\t\t\tif(index > 0){\n\t\t\t\tthis._focusItem(this.displayItems[index - 1]);\n\t\t\t}\n\t\t}\n\t}\n\t\n\t_keyDown(e){\n\t\tvar index = this.displayItems.indexOf(this.focusedItem);\n\t\t\n\t\tif(this.params.verticalNavigation == \"editor\" || (this.params.verticalNavigation == \"hybrid\" && index < this.displayItems.length - 1)){\n\t\t\te.stopImmediatePropagation();\n\t\t\te.stopPropagation();\n\t\t\te.preventDefault();\n\t\t\t\n\t\t\tif(index < this.displayItems.length - 1){\n\t\t\t\tif(index == -1){\n\t\t\t\t\tthis._focusItem(this.displayItems[0]);\n\t\t\t\t}else {\n\t\t\t\t\tthis._focusItem(this.displayItems[index + 1]);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t\n\t_keySide(e){\n\t\tif(!this.params.autocomplete){\n\t\t\te.stopImmediatePropagation();\n\t\t\te.stopPropagation();\n\t\t\te.preventDefault();\n\t\t}\n\t}\n\t\n\t_keyEnter(e){\n\t\tif(this.params.autocomplete && this.lastAction === \"typing\"){\n\t\t\tthis._resolveValue(true);\n\t\t}else {\n\t\t\tif(this.focusedItem){\n\t\t\t\tthis._chooseItem(this.focusedItem);\n\t\t\t}\n\t\t}\n\t}\n\t\n\t_keyEsc(e){\n\t\tthis._cancel();\n\t}\n\t\n\t_keyHomeEnd(e){\n\t\tif(this.params.autocomplete){\n\t\t\t//prevent table navigation while using input element\n\t\t\te.stopImmediatePropagation();\n\t\t}\n\t}\n\t\n\t_keySelectLetter(e){\n\t\tif(!this.params.autocomplete){\n\t\t\t// if(this.edit.currentCell === false){\n\t\t\te.preventDefault();\n\t\t\t// }\n\t\t\t\n\t\t\tif(e.keyCode >= 38 && e.keyCode <= 90){\n\t\t\t\tthis._scrollToValue(e.keyCode);\n\t\t\t}\n\t\t}\n\t}\n\t\n\t_keyAutoCompLetter(e){\n\t\tthis._filter();\n\t\tthis.lastAction = \"typing\";\n\t\tthis.typing = true;\n\t}\n\t\n\t\n\t_scrollToValue(char){\n\t\tclearTimeout(this.filterTimeout);\n\t\t\n\t\tvar character = String.fromCharCode(char).toLowerCase();\n\t\tthis.filterTerm += character.toLowerCase();\n\t\t\n\t\tvar match = this.displayItems.find((item) => {\n\t\t\treturn typeof item.label !== \"undefined\" && item.label.toLowerCase().startsWith(this.filterTerm);\n\t\t});\n\t\t\n\t\tif(match){\n\t\t\tthis._focusItem(match);\n\t\t}\n\t\t\n\t\tthis.filterTimeout = setTimeout(() => {\n\t\t\tthis.filterTerm = \"\";\n\t\t}, 800);\n\t}\n\t\n\t_focusItem(item){\n\t\tthis.lastAction = \"focus\";\n\t\t\n\t\tif(this.focusedItem && this.focusedItem.element){\n\t\t\tthis.focusedItem.element.classList.remove(\"focused\");\n\t\t}\n\t\t\n\t\tthis.focusedItem = item;\n\t\t\n\t\tif(item && item.element){\n\t\t\titem.element.classList.add(\"focused\");\n\t\t\titem.element.scrollIntoView({behavior: 'smooth', block: 'nearest', inline: 'start'});\n\t\t}\n\t}\n\t\n\t\n\t//////////////////////////////////////\n\t/////// Data List Generation /////////\n\t//////////////////////////////////////\n\theaderFilterInitialListGen(){\n\t\tthis._generateOptions(true);\n\t}\n\t\n\trebuildOptionsList(){\n\t\tthis._generateOptions()\n\t\t\t.then(this._sortOptions.bind(this))\n\t\t\t.then(this._buildList.bind(this))\n\t\t\t.then(this._showList.bind(this))\n\t\t\t.catch((e) => {\n\t\t\t\tif(!Number.isInteger(e)){\n\t\t\t\t\tconsole.error(\"List generation error\", e);\n\t\t\t\t}\n\t\t\t});\n\t}\n\t\n\t_filterList(){\n\t\tthis._buildList(this._filterOptions());\n\t\tthis._showList();\n\t}\n\t\n\t_generateOptions(silent){\n\t\tvar values = [];\n\t\tvar iteration = ++ this.listIteration;\n\t\t\n\t\tthis.filtered = false;\n\t\t\n\t\tif(this.params.values){\n\t\t\tvalues = this.params.values;\n\t\t}else if (this.params.valuesURL){\n\t\t\tvalues = this._ajaxRequest(this.params.valuesURL, this.input.value);\n\t\t}else {\n\t\t\tif(typeof this.params.valuesLookup === \"function\"){\n\t\t\t\tvalues = this.params.valuesLookup(this.cell, this.input.value);\n\t\t\t}else if(this.params.valuesLookup){\n\t\t\t\tvalues = this._uniqueColumnValues(this.params.valuesLookupField);\n\t\t\t}\n\t\t}\n\t\t\n\t\tif(values instanceof Promise){\n\t\t\tif(!silent){\n\t\t\t\tthis._addPlaceholder(this.params.placeholderLoading);\n\t\t\t}\n\t\t\t\n\t\t\treturn values.then()\n\t\t\t\t.then((responseValues) => {\n\t\t\t\t\tif(this.listIteration === iteration){\n\t\t\t\t\t\treturn this._parseList(responseValues);\n\t\t\t\t\t}else {\n\t\t\t\t\t\treturn Promise.reject(iteration);\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t}else {\n\t\t\treturn Promise.resolve(this._parseList(values));\n\t\t}\n\t}\n\t\n\t_addPlaceholder(contents){\n\t\tvar placeholder = document.createElement(\"div\");\n\t\t\n\t\tif(typeof contents === \"function\"){\n\t\t\tcontents = contents(this.cell.getComponent(), this.listEl);\n\t\t}\n\t\t\n\t\tif(contents){\n\t\t\tthis._clearList();\n\t\t\t\n\t\t\tif(contents instanceof HTMLElement){\n\t\t\t\tplaceholder = contents;\n\t\t\t}else {\n\t\t\t\tplaceholder.classList.add(\"tabulator-edit-list-placeholder\");\n\t\t\t\tplaceholder.innerHTML = contents;\n\t\t\t}\n\t\t\t\n\t\t\tthis.listEl.appendChild(placeholder);\n\t\t\t\n\t\t\tthis._showList();\n\t\t}\n\t}\n\t\n\t_ajaxRequest(url, term){\n\t\tvar params = this.params.filterRemote ? {term:term} : {};\n\t\turl = urlBuilder(url, {}, params);\n\t\t\n\t\treturn fetch(url)\n\t\t\t.then((response)=>{\n\t\t\t\tif(response.ok) {\n\t\t\t\t\treturn response.json()\n\t\t\t\t\t\t.catch((error)=>{\n\t\t\t\t\t\t\tconsole.warn(\"List Ajax Load Error - Invalid JSON returned\", error);\n\t\t\t\t\t\t\treturn Promise.reject(error);\n\t\t\t\t\t\t});\n\t\t\t\t}else {\n\t\t\t\t\tconsole.error(\"List Ajax Load Error - Connection Error: \" + response.status, response.statusText);\n\t\t\t\t\treturn Promise.reject(response);\n\t\t\t\t}\n\t\t\t})\n\t\t\t.catch((error)=>{\n\t\t\t\tconsole.error(\"List Ajax Load Error - Connection Error: \", error);\n\t\t\t\treturn Promise.reject(error);\n\t\t\t});\n\t}\n\t\n\t_uniqueColumnValues(field){\n\t\tvar output = {},\n\t\tdata = this.table.getData(this.params.valuesLookup),\n\t\tcolumn;\n\t\t\n\t\tif(field){\n\t\t\tcolumn = this.table.columnManager.getColumnByField(field);\n\t\t}else {\n\t\t\tcolumn = this.cell.getColumn()._getSelf();\n\t\t}\n\t\t\n\t\tif(column){\n\t\t\tdata.forEach((row) => {\n\t\t\t\tvar val = column.getFieldValue(row);\n\t\t\t\t\n\t\t\t\tif(val !== null && typeof val !== \"undefined\" && val !== \"\"){\n\t\t\t\t\toutput[val] = true;\n\t\t\t\t}\n\t\t\t});\n\t\t}else {\n\t\t\tconsole.warn(\"unable to find matching column to create select lookup list:\", field);\n\t\t\toutput = [];\n\t\t}\n\t\t\n\t\treturn Object.keys(output);\n\t}\n\t\n\t\n\t_parseList(inputValues){\n\t\tvar data = [];\n\t\t\n\t\tif(!Array.isArray(inputValues)){\n\t\t\tinputValues = Object.entries(inputValues).map(([key, value]) => {\n\t\t\t\treturn {\n\t\t\t\t\tlabel:value,\n\t\t\t\t\tvalue:key,\n\t\t\t\t};\n\t\t\t});\n\t\t}\n\t\t\n\t\tinputValues.forEach((value) => {\n\t\t\tif(typeof value !== \"object\"){\n\t\t\t\tvalue = {\n\t\t\t\t\tlabel:value,\n\t\t\t\t\tvalue:value,\n\t\t\t\t};\n\t\t\t}\n\t\t\t\n\t\t\tthis._parseListItem(value, data, 0);\n\t\t});\n\t\t\n\t\tif(!this.currentItems.length && this.params.freetext){\n\t\t\tthis.input.value = this.initialValues;\n\t\t\tthis.typing = true;\n\t\t\tthis.lastAction = \"typing\";\n\t\t}\n\t\t\n\t\tthis.data = data;\n\t\t\n\t\treturn data;    \n\t}\n\t\n\t_parseListItem(option, data, level){\n\t\tvar item = {};\n\t\t\n\t\tif(option.options){\n\t\t\titem = this._parseListGroup(option, level + 1);\n\t\t}else {\n\t\t\titem = {\n\t\t\t\tlabel:option.label,\n\t\t\t\tvalue:option.value,\n\t\t\t\titemParams:option.itemParams,\n\t\t\t\telementAttributes: option.elementAttributes,\n\t\t\t\telement:false,\n\t\t\t\tselected:false,\n\t\t\t\tvisible:true,\n\t\t\t\tlevel:level,\n\t\t\t\toriginal:option,\n\t\t\t};\n\t\t\t\n\t\t\tif(this.initialValues && this.initialValues.indexOf(option.value) > -1){\n\t\t\t\tthis._chooseItem(item, true);\n\t\t\t}\n\t\t}\n\t\t\n\t\tdata.push(item);\n\t}\n\t\n\t_parseListGroup(option, level){\n\t\tvar item = {\n\t\t\tlabel:option.label,\n\t\t\tgroup:true,\n\t\t\titemParams:option.itemParams,\n\t\t\telementAttributes:option.elementAttributes,\n\t\t\telement:false,\n\t\t\tvisible:true,\n\t\t\tlevel:level,\n\t\t\toptions:[],\n\t\t\toriginal:option,\n\t\t};\n\t\t\n\t\toption.options.forEach((child) => {\n\t\t\tthis._parseListItem(child, item.options, level);\n\t\t});\n\t\t\n\t\treturn item;\n\t}\n\t\n\t_sortOptions(options){\n\t\tvar sorter;\n\t\t\n\t\tif(this.params.sort){\n\t\t\tsorter = typeof this.params.sort === \"function\" ? this.params.sort : this._defaultSortFunction.bind(this);\n\t\t\t\n\t\t\tthis._sortGroup(sorter, options);\n\t\t}\n\t\t\n\t\treturn options;\n\t}\n\t\n\t_sortGroup(sorter, options){\n\t\toptions.sort((a,b) => {\n\t\t\treturn sorter(a.label, b.label, a.value, b.value, a.original, b.original);\n\t\t});\n\t\t\n\t\toptions.forEach((option) => {\n\t\t\tif(option.group){\n\t\t\t\tthis._sortGroup(sorter, option.options);\n\t\t\t}\n\t\t});\n\t}\n\t\n\t_defaultSortFunction(as, bs){\n\t\tvar a, b, a1, b1, i= 0, L, rx = /(\\d+)|(\\D+)/g, rd = /\\d/;\n\t\tvar emptyAlign = 0;\n\t\t\n\t\tif(this.params.sort === \"desc\"){\n\t\t\t[as, bs] = [bs, as];\n\t\t}\n\t\t\n\t\t//handle empty values\n\t\tif(!as && as!== 0){\n\t\t\temptyAlign =  !bs && bs!== 0 ? 0 : -1;\n\t\t}else if(!bs && bs!== 0){\n\t\t\temptyAlign =  1;\n\t\t}else {\n\t\t\tif(isFinite(as) && isFinite(bs)) return as - bs;\n\t\t\ta = String(as).toLowerCase();\n\t\t\tb = String(bs).toLowerCase();\n\t\t\tif(a === b) return 0;\n\t\t\tif(!(rd.test(a) && rd.test(b))) return a > b ? 1 : -1;\n\t\t\ta = a.match(rx);\n\t\t\tb = b.match(rx);\n\t\t\tL = a.length > b.length ? b.length : a.length;\n\t\t\twhile(i < L){\n\t\t\t\ta1= a[i];\n\t\t\t\tb1= b[i++];\n\t\t\t\tif(a1 !== b1){\n\t\t\t\t\tif(isFinite(a1) && isFinite(b1)){\n\t\t\t\t\t\tif(a1.charAt(0) === \"0\") a1 = \".\" + a1;\n\t\t\t\t\t\tif(b1.charAt(0) === \"0\") b1 = \".\" + b1;\n\t\t\t\t\t\treturn a1 - b1;\n\t\t\t\t\t}\n\t\t\t\t\telse return a1 > b1 ? 1 : -1;\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\treturn a.length > b.length;\n\t\t}\n\t\t\n\t\treturn emptyAlign;\n\t}\n\t\n\t_filterOptions(){\n\t\tvar filterFunc = this.params.filterFunc || this._defaultFilterFunc,\n\t\tterm = this.input.value;\n\t\t\n\t\tif(term){\n\t\t\tthis.filtered = true;\n\t\t\t\n\t\t\tthis.data.forEach((item) => {\n\t\t\t\tthis._filterItem(filterFunc, term, item);\n\t\t\t});\n\t\t}else {\n\t\t\tthis.filtered = false;\n\t\t}\n\t\t\n\t\treturn this.data;\n\t}\n\t\n\t_filterItem(func, term, item){\n\t\tvar matches = false;\n\t\t\n\t\tif(!item.group){\n\t\t\titem.visible = func(term, item.label, item.value, item.original);\n\t\t}else {\n\t\t\titem.options.forEach((option) => {\n\t\t\t\tif(this._filterItem(func, term, option)){\n\t\t\t\t\tmatches = true;\n\t\t\t\t}\n\t\t\t});\n\t\t\t\n\t\t\titem.visible = matches;\n\t\t}\n\t\t\n\t\treturn item.visible;\n\t}\n\t\n\t_defaultFilterFunc(term, label, value, item){\n\t\tterm = String(term).toLowerCase();\n\t\t\n\t\tif(label !== null && typeof label !== \"undefined\"){\n\t\t\tif(String(label).toLowerCase().indexOf(term) > -1 || String(value).toLowerCase().indexOf(term) > -1){\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn false;\n\t}\n\t\n\t//////////////////////////////////////\n\t/////////// Display List /////////////\n\t//////////////////////////////////////\n\t\n\t_clearList(){\n\t\twhile(this.listEl.firstChild) this.listEl.removeChild(this.listEl.firstChild);\n\t\t\n\t\tthis.displayItems = [];\n\t}\n\t\n\t_buildList(data){\n\t\tthis._clearList();\n\t\t\n\t\tdata.forEach((option) => {\n\t\t\tthis._buildItem(option);\n\t\t});\n\t\t\n\t\tif(!this.displayItems.length){\n\t\t\tthis._addPlaceholder(this.params.placeholderEmpty);\n\t\t}  \n\t}\n\t\n\t_buildItem(item){\n\t\tvar el = item.element,\n\t\tcontents;\n\t\t\n\t\tif(!this.filtered || item.visible){\n\t\t\t\n\t\t\tif(!el){\n\t\t\t\tel = document.createElement(\"div\");\n\t\t\t\tel.tabIndex = 0;\n\t\t\t\t\n\t\t\t\tcontents = this.params.itemFormatter ? this.params.itemFormatter(item.label, item.value, item.original, el) : item.label;\n\t\t\t\t\n\t\t\t\tif(contents instanceof HTMLElement){\n\t\t\t\t\tel.appendChild(contents);\n\t\t\t\t}else {\n\t\t\t\t\tel.innerHTML = contents;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tif(item.group){\n\t\t\t\t\tel.classList.add(\"tabulator-edit-list-group\");\n\t\t\t\t}else {\n\t\t\t\t\tel.classList.add(\"tabulator-edit-list-item\");\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tel.classList.add(\"tabulator-edit-list-group-level-\" + item.level);\n\t\t\t\t\n\t\t\t\tif(item.elementAttributes && typeof item.elementAttributes == \"object\"){\n\t\t\t\t\tfor (let key in item.elementAttributes){\n\t\t\t\t\t\tif(key.charAt(0) == \"+\"){\n\t\t\t\t\t\t\tkey = key.slice(1);\n\t\t\t\t\t\t\tel.setAttribute(key, this.input.getAttribute(key) + item.elementAttributes[\"+\" + key]);\n\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\tel.setAttribute(key, item.elementAttributes[key]);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tif(item.group){\n\t\t\t\t\tel.addEventListener(\"click\", this._groupClick.bind(this, item));\n\t\t\t\t}else {\n\t\t\t\t\tel.addEventListener(\"click\", this._itemClick.bind(this, item));\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tel.addEventListener(\"mousedown\", this._preventBlur.bind(this));\n\t\t\t\t\n\t\t\t\titem.element = el;\n\t\t\t}\n\t\t\t\n\t\t\tthis._styleItem(item);\n\t\t\t\n\t\t\tthis.listEl.appendChild(el);\n\t\t\t\n\t\t\tif(item.group){\n\t\t\t\titem.options.forEach((option) => {\n\t\t\t\t\tthis._buildItem(option);\n\t\t\t\t});\n\t\t\t}else {\n\t\t\t\tthis.displayItems.push(item);\n\t\t\t}\n\t\t}\n\t}\n\t\n\t_showList(){\n\t\tvar startVis = this.popup && this.popup.isVisible();\n\t\t\n\t\tif(this.input.parentNode){\n\t\t\tif(this.params.autocomplete && this.input.value === \"\" && !this.params.listOnEmpty){\n\t\t\t\tif(this.popup){\n\t\t\t\t\tthis.popup.hide(true);\n\t\t\t\t}\n\t\t\t\treturn;\n\t\t\t}\n\t\t\t\n\t\t\tthis._setListWidth();\n\t\t\t\n\t\t\tif(!this.popup){\n\t\t\t\tthis.popup = this.edit.popup(this.listEl);\n\t\t\t}\n\t\t\t\n\t\t\tthis.popup.show(this.cell.getElement(), \"bottom\");\n\t\t\t\n\t\t\tif(!startVis){\n\t\t\t\tsetTimeout(() => {\n\t\t\t\t\tthis.popup.hideOnBlur(this._resolveValue.bind(this, true));\n\t\t\t\t}, 10);\n\t\t\t}\n\t\t}\n\t}\n\t\n\t_styleItem(item){\n\t\tif(item && item.element){\n\t\t\tif(item.selected){\n\t\t\t\titem.element.classList.add(\"active\");\n\t\t\t}else {\n\t\t\t\titem.element.classList.remove(\"active\");\n\t\t\t}\n\t\t}\n\t}\n\t\n\t//////////////////////////////////////\n\t///////// User Interaction ///////////\n\t//////////////////////////////////////\n\t\n\t_itemClick(item, e){\n\t\te.stopPropagation();\n\t\t\n\t\tthis._chooseItem(item);\n\t}\n\t\n\t_groupClick(item, e){\n\t\te.stopPropagation();\n\t}\n\t\n\t\n\t//////////////////////////////////////\n\t////// Current Item Management ///////\n\t//////////////////////////////////////\n\t\n\t_cancel(){\n\t\tthis.popup.hide(true);\n\t\tthis.actions.cancel();\n\t}\n\t\n\t_clearChoices(){\n\t\tthis.typing = true;\n\t\t\n\t\tthis.currentItems.forEach((item) => {\n\t\t\titem.selected = false;\n\t\t\tthis._styleItem(item);\n\t\t});\n\t\t\n\t\tthis.currentItems = [];\n\t\t\n\t\tthis.focusedItem = null;\n\t}\n\t\n\t_chooseItem(item, silent){\n\t\tvar index;\n\t\t\n\t\tthis.typing = false;\n\t\t\n\t\tif(this.params.multiselect){\n\t\t\tindex = this.currentItems.indexOf(item);\n\t\t\t\n\t\t\tif(index > -1){\n\t\t\t\tthis.currentItems.splice(index, 1);\n\t\t\t\titem.selected = false;\n\t\t\t}else {\n\t\t\t\tthis.currentItems.push(item);\n\t\t\t\titem.selected = true;\n\t\t\t}\n\t\t\t\n\t\t\tthis.input.value = this.currentItems.map(item => item.label).join(\",\");\n\t\t\t\n\t\t\tthis._styleItem(item);\n\t\t\t\n\t\t}else {\n\t\t\tthis.currentItems = [item];\n\t\t\titem.selected = true;\n\t\t\t\n\t\t\tthis.input.value = item.label;\n\t\t\t\n\t\t\tthis._styleItem(item);\n\t\t\t\n\t\t\tif(!silent){\n\t\t\t\tthis._resolveValue();\n\t\t\t}\n\t\t}\n\t\t\n\t\tthis._focusItem(item);\n\t}\n\t\n\t_resolveValue(blur){\n\t\tvar output, initialValue;\n\t\t\n\t\tif(this.popup){\n\t\t\tthis.popup.hide(true);\n\t\t}\n\t\t\n\t\tif(this.params.multiselect){\n\t\t\toutput = this.currentItems.map(item => item.value);\n\t\t}else {\n\t\t\tif(blur && this.params.autocomplete && this.typing){\n\t\t\t\tif(this.params.freetext || (this.params.allowEmpty && this.input.value === \"\")){\n\t\t\t\t\toutput = this.input.value;\n\t\t\t\t}else {\n\t\t\t\t\tthis.actions.cancel();\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tif(this.currentItems[0]){\n\t\t\t\t\toutput = this.currentItems[0].value;\n\t\t\t\t}else {\n\t\t\t\t\tinitialValue = Array.isArray(this.initialValues) ? this.initialValues[0] : this.initialValues;\n\t\t\t\t\t\n\t\t\t\t\tif(initialValue === null || typeof initialValue === \"undefined\" || initialValue === \"\"){\n\t\t\t\t\t\toutput = initialValue;\n\t\t\t\t\t}else {\n\t\t\t\t\t\toutput = this.params.emptyValue;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t\n\t\t\t}\n\t\t}\n\t\t\n\t\tif(output === \"\"){\n\t\t\toutput = this.params.emptyValue;\n\t\t}\n\t\t\n\t\tthis.actions.success(output);\n\t\t\n\t\tif(this.isFilter){\n\t\t\tthis.initialValues = output && !Array.isArray(output) ? [output] : output;\n\t\t\tthis.currentItems = [];\n\t\t}\n\t}\n\t\n}\n\nfunction select(cell, onRendered, success, cancel, editorParams){\n\n\tthis.deprecationMsg(\"The select editor has been deprecated, please use the new list editor\");\n\n\tvar list = new Edit(this, cell, onRendered, success, cancel, editorParams);\n\n\treturn list.input;\n}\n\nfunction list(cell, onRendered, success, cancel, editorParams){\n\tvar list = new Edit(this, cell, onRendered, success, cancel, editorParams);\n\n\treturn list.input;\n}\n\nfunction autocomplete(cell, onRendered, success, cancel, editorParams){\n\n\tthis.deprecationMsg(\"The autocomplete editor has been deprecated, please use the new list editor with the 'autocomplete' editorParam\");\n\n\teditorParams.autocomplete = true;\n\n\tvar list = new Edit(this, cell, onRendered, success, cancel, editorParams);\n\n\treturn list.input;\n}\n\n//star rating\nfunction star(cell, onRendered, success, cancel, editorParams){\n\tvar self = this,\n\telement = cell.getElement(),\n\tvalue = cell.getValue(),\n\tmaxStars = element.getElementsByTagName(\"svg\").length || 5,\n\tsize = element.getElementsByTagName(\"svg\")[0] ? element.getElementsByTagName(\"svg\")[0].getAttribute(\"width\") : 14,\n\tstars = [],\n\tstarsHolder = document.createElement(\"div\"),\n\tstar = document.createElementNS('http://www.w3.org/2000/svg', \"svg\");\n\n\n\t//change star type\n\tfunction starChange(val){\n\t\tstars.forEach(function(star, i){\n\t\t\tif(i < val){\n\t\t\t\tif(self.table.browser == \"ie\"){\n\t\t\t\t\tstar.setAttribute(\"class\", \"tabulator-star-active\");\n\t\t\t\t}else {\n\t\t\t\t\tstar.classList.replace(\"tabulator-star-inactive\", \"tabulator-star-active\");\n\t\t\t\t}\n\n\t\t\t\tstar.innerHTML = '<polygon fill=\"#488CE9\" stroke=\"#014AAE\" stroke-width=\"37.6152\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-miterlimit=\"10\" points=\"259.216,29.942 330.27,173.919 489.16,197.007 374.185,309.08 401.33,467.31 259.216,392.612 117.104,467.31 144.25,309.08 29.274,197.007 188.165,173.919 \"/>';\n\t\t\t}else {\n\t\t\t\tif(self.table.browser == \"ie\"){\n\t\t\t\t\tstar.setAttribute(\"class\", \"tabulator-star-inactive\");\n\t\t\t\t}else {\n\t\t\t\t\tstar.classList.replace(\"tabulator-star-active\", \"tabulator-star-inactive\");\n\t\t\t\t}\n\n\t\t\t\tstar.innerHTML = '<polygon fill=\"#010155\" stroke=\"#686868\" stroke-width=\"37.6152\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-miterlimit=\"10\" points=\"259.216,29.942 330.27,173.919 489.16,197.007 374.185,309.08 401.33,467.31 259.216,392.612 117.104,467.31 144.25,309.08 29.274,197.007 188.165,173.919 \"/>';\n\t\t\t}\n\t\t});\n\t}\n\n\t//build stars\n\tfunction buildStar(i){\n\n\t\tvar starHolder =  document.createElement(\"span\");\n\t\tvar nextStar = star.cloneNode(true);\n\n\t\tstars.push(nextStar);\n\n\t\tstarHolder.addEventListener(\"mouseenter\", function(e){\n\t\t\te.stopPropagation();\n\t\t\te.stopImmediatePropagation();\n\t\t\tstarChange(i);\n\t\t});\n\n\t\tstarHolder.addEventListener(\"mousemove\", function(e){\n\t\t\te.stopPropagation();\n\t\t\te.stopImmediatePropagation();\n\t\t});\n\n\t\tstarHolder.addEventListener(\"click\", function(e){\n\t\t\te.stopPropagation();\n\t\t\te.stopImmediatePropagation();\n\t\t\tsuccess(i);\n\t\t\telement.blur();\n\t\t});\n\n\t\tstarHolder.appendChild(nextStar);\n\t\tstarsHolder.appendChild(starHolder);\n\n\t}\n\n\t//handle keyboard navigation value change\n\tfunction changeValue(val){\n\t\tvalue = val;\n\t\tstarChange(val);\n\t}\n\n\t//style cell\n\telement.style.whiteSpace = \"nowrap\";\n\telement.style.overflow = \"hidden\";\n\telement.style.textOverflow = \"ellipsis\";\n\n\t//style holding element\n\tstarsHolder.style.verticalAlign = \"middle\";\n\tstarsHolder.style.display = \"inline-block\";\n\tstarsHolder.style.padding = \"4px\";\n\n\t//style star\n\tstar.setAttribute(\"width\", size);\n\tstar.setAttribute(\"height\", size);\n\tstar.setAttribute(\"viewBox\", \"0 0 512 512\");\n\tstar.setAttribute(\"xml:space\", \"preserve\");\n\tstar.style.padding = \"0 1px\";\n\n\tif(editorParams.elementAttributes && typeof editorParams.elementAttributes == \"object\"){\n\t\tfor (let key in editorParams.elementAttributes){\n\t\t\tif(key.charAt(0) == \"+\"){\n\t\t\t\tkey = key.slice(1);\n\t\t\t\tstarsHolder.setAttribute(key, starsHolder.getAttribute(key) + editorParams.elementAttributes[\"+\" + key]);\n\t\t\t}else {\n\t\t\t\tstarsHolder.setAttribute(key, editorParams.elementAttributes[key]);\n\t\t\t}\n\t\t}\n\t}\n\n\t//create correct number of stars\n\tfor(var i=1;i<= maxStars;i++){\n\t\tbuildStar(i);\n\t}\n\n\t//ensure value does not exceed number of stars\n\tvalue = Math.min(parseInt(value), maxStars);\n\n\t// set initial styling of stars\n\tstarChange(value);\n\n\tstarsHolder.addEventListener(\"mousemove\", function(e){\n\t\tstarChange(0);\n\t});\n\n\tstarsHolder.addEventListener(\"click\", function(e){\n\t\tsuccess(0);\n\t});\n\n\telement.addEventListener(\"blur\", function(e){\n\t\tcancel();\n\t});\n\n\t//allow key based navigation\n\telement.addEventListener(\"keydown\", function(e){\n\t\tswitch(e.keyCode){\n\t\t\tcase 39: //right arrow\n\t\t\t\tchangeValue(value + 1);\n\t\t\t\tbreak;\n\n\t\t\tcase 37: //left arrow\n\t\t\t\tchangeValue(value - 1);\n\t\t\t\tbreak;\n\n\t\t\tcase 13: //enter\n\t\t\t\tsuccess(value);\n\t\t\t\tbreak;\n\n\t\t\tcase 27: //escape\n\t\t\t\tcancel();\n\t\t\t\tbreak;\n\t\t}\n\t});\n\n\treturn starsHolder;\n}\n\n//draggable progress bar\nfunction progress(cell, onRendered, success, cancel, editorParams){\n\tvar element = cell.getElement(),\n\tmax = typeof editorParams.max === \"undefined\" ? ((element.getElementsByTagName(\"div\")[0] && element.getElementsByTagName(\"div\")[0].getAttribute(\"max\")) || 100) : editorParams.max,\n\tmin = typeof editorParams.min === \"undefined\" ? ((element.getElementsByTagName(\"div\")[0] && element.getElementsByTagName(\"div\")[0].getAttribute(\"min\")) || 0) : editorParams.min,\n\tpercent = (max - min) / 100,\n\tvalue = cell.getValue() || 0,\n\thandle = document.createElement(\"div\"),\n\tbar = document.createElement(\"div\"),\n\tmouseDrag, mouseDragWidth;\n\n\t//set new value\n\tfunction updateValue(){\n\t\tvar style = window.getComputedStyle(element, null);\n\n\t\tvar calcVal = (percent * Math.round(bar.offsetWidth / ((element.clientWidth - parseInt(style.getPropertyValue(\"padding-left\")) - parseInt(style.getPropertyValue(\"padding-right\")))/100))) + min;\n\t\tsuccess(calcVal);\n\t\telement.setAttribute(\"aria-valuenow\", calcVal);\n\t\telement.setAttribute(\"aria-label\", value);\n\t}\n\n\t//style handle\n\thandle.style.position = \"absolute\";\n\thandle.style.right = \"0\";\n\thandle.style.top = \"0\";\n\thandle.style.bottom = \"0\";\n\thandle.style.width = \"5px\";\n\thandle.classList.add(\"tabulator-progress-handle\");\n\n\t//style bar\n\tbar.style.display = \"inline-block\";\n\tbar.style.position = \"relative\";\n\t// bar.style.top = \"8px\";\n\t// bar.style.bottom = \"8px\";\n\t// bar.style.left = \"4px\";\n\t// bar.style.marginRight = \"4px\";\n\tbar.style.height = \"100%\";\n\tbar.style.backgroundColor = \"#488CE9\";\n\tbar.style.maxWidth = \"100%\";\n\tbar.style.minWidth = \"0%\";\n\n\tif(editorParams.elementAttributes && typeof editorParams.elementAttributes == \"object\"){\n\t\tfor (let key in editorParams.elementAttributes){\n\t\t\tif(key.charAt(0) == \"+\"){\n\t\t\t\tkey = key.slice(1);\n\t\t\t\tbar.setAttribute(key, bar.getAttribute(key) + editorParams.elementAttributes[\"+\" + key]);\n\t\t\t}else {\n\t\t\t\tbar.setAttribute(key, editorParams.elementAttributes[key]);\n\t\t\t}\n\t\t}\n\t}\n\n\t//style cell\n\telement.style.padding = \"4px 4px\";\n\n\t//make sure value is in range\n\tvalue = Math.min(parseFloat(value), max);\n\tvalue = Math.max(parseFloat(value), min);\n\n\t//workout percentage\n\tvalue = Math.round((value - min) / percent);\n\t// bar.style.right = value + \"%\";\n\tbar.style.width = value + \"%\";\n\n\telement.setAttribute(\"aria-valuemin\", min);\n\telement.setAttribute(\"aria-valuemax\", max);\n\n\tbar.appendChild(handle);\n\n\thandle.addEventListener(\"mousedown\", function(e){\n\t\tmouseDrag = e.screenX;\n\t\tmouseDragWidth = bar.offsetWidth;\n\t});\n\n\thandle.addEventListener(\"mouseover\", function(){\n\t\thandle.style.cursor = \"ew-resize\";\n\t});\n\n\telement.addEventListener(\"mousemove\", function(e){\n\t\tif(mouseDrag){\n\t\t\tbar.style.width = (mouseDragWidth + e.screenX - mouseDrag) + \"px\";\n\t\t}\n\t});\n\n\telement.addEventListener(\"mouseup\", function(e){\n\t\tif(mouseDrag){\n\t\t\te.stopPropagation();\n\t\t\te.stopImmediatePropagation();\n\n\t\t\tmouseDrag = false;\n\t\t\tmouseDragWidth = false;\n\n\t\t\tupdateValue();\n\t\t}\n\t});\n\n\t//allow key based navigation\n\telement.addEventListener(\"keydown\", function(e){\n\t\tswitch(e.keyCode){\n\t\t\tcase 39: //right arrow\n\t\t\t\te.preventDefault();\n\t\t\t\tbar.style.width = (bar.clientWidth + element.clientWidth/100) + \"px\";\n\t\t\t\tbreak;\n\n\t\t\tcase 37: //left arrow\n\t\t\t\te.preventDefault();\n\t\t\t\tbar.style.width = (bar.clientWidth - element.clientWidth/100) + \"px\";\n\t\t\t\tbreak;\n\n\t\t\tcase 9: //tab\n\t\t\tcase 13: //enter\n\t\t\t\tupdateValue();\n\t\t\t\tbreak;\n\n\t\t\tcase 27: //escape\n\t\t\t\tcancel();\n\t\t\t\tbreak;\n\n\t\t}\n\t});\n\n\telement.addEventListener(\"blur\", function(){\n\t\tcancel();\n\t});\n\n\treturn bar;\n}\n\n//checkbox\nfunction tickCross(cell, onRendered, success, cancel, editorParams){\n\tvar value = cell.getValue(),\n\tinput = document.createElement(\"input\"),\n\ttristate = editorParams.tristate,\n\tindetermValue = typeof editorParams.indeterminateValue === \"undefined\" ? null : editorParams.indeterminateValue,\n\tindetermState = false,\n\ttrueValueSet = Object.keys(editorParams).includes(\"trueValue\"),\n\tfalseValueSet = Object.keys(editorParams).includes(\"falseValue\");\n\t\n\tinput.setAttribute(\"type\", \"checkbox\");\n\tinput.style.marginTop = \"5px\";\n\tinput.style.boxSizing = \"border-box\";\n\t\n\tif(editorParams.elementAttributes && typeof editorParams.elementAttributes == \"object\"){\n\t\tfor (let key in editorParams.elementAttributes){\n\t\t\tif(key.charAt(0) == \"+\"){\n\t\t\t\tkey = key.slice(1);\n\t\t\t\tinput.setAttribute(key, input.getAttribute(key) + editorParams.elementAttributes[\"+\" + key]);\n\t\t\t}else {\n\t\t\t\tinput.setAttribute(key, editorParams.elementAttributes[key]);\n\t\t\t}\n\t\t}\n\t}\n\t\n\tinput.value = value;\n\t\n\tif(tristate && (typeof value === \"undefined\" || value === indetermValue || value === \"\")){\n\t\tindetermState = true;\n\t\tinput.indeterminate = true;\n\t}\n\t\n\tif(this.table.browser != \"firefox\" && this.table.browser != \"safari\"){ //prevent blur issue on mac firefox\n\t\tonRendered(function(){\n\t\t\tif(cell.getType() === \"cell\"){\n\t\t\t\tinput.focus({preventScroll: true});\n\t\t\t}\n\t\t});\n\t}\n\t\n\tinput.checked = trueValueSet ? value === editorParams.trueValue : (value === true || value === \"true\" || value === \"True\" || value === 1);\n\t\n\tfunction setValue(blur){\n\t\tvar checkedValue = input.checked;\n\t\t\n\t\tif(trueValueSet && checkedValue){\n\t\t\tcheckedValue = editorParams.trueValue;\n\t\t}else if(falseValueSet && !checkedValue){\n\t\t\tcheckedValue = editorParams.falseValue;\n\t\t}\n\t\t\n\t\tif(tristate){\n\t\t\tif(!blur){\n\t\t\t\tif(input.checked && !indetermState){\n\t\t\t\t\tinput.checked = false;\n\t\t\t\t\tinput.indeterminate = true;\n\t\t\t\t\tindetermState = true;\n\t\t\t\t\treturn indetermValue;\n\t\t\t\t}else {\n\t\t\t\t\tindetermState = false;\n\t\t\t\t\treturn checkedValue;\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tif(indetermState){\n\t\t\t\t\treturn indetermValue;\n\t\t\t\t}else {\n\t\t\t\t\treturn checkedValue;\n\t\t\t\t}\n\t\t\t}\n\t\t}else {\n\t\t\treturn checkedValue;\n\t\t}\n\t}\n\t\n\t//submit new value on blur\n\tinput.addEventListener(\"change\", function(e){\n\t\tsuccess(setValue());\n\t});\n\n\tinput.addEventListener(\"blur\", function(e){\n\t\tsuccess(setValue(true));\n\t});\n\t\n\t//submit new value on enter\n\tinput.addEventListener(\"keydown\", function(e){\n\t\tif(e.keyCode == 13){\n\t\t\tsuccess(setValue());\n\t\t}\n\t\tif(e.keyCode == 27){\n\t\t\tcancel();\n\t\t}\n\t});\n\t\n\treturn input;\n}\n\nvar defaultEditors = {\n\tinput:input,\n\ttextarea:textarea,\n\tnumber:number,\n\trange:range,\n\tdate:date,\n\ttime:time,\n\tdatetime:datetime,\n\tselect:select,\n\tlist:list,\n\tautocomplete:autocomplete,\n\tstar:star,\n\tprogress:progress,\n\ttickCross:tickCross,\n};\n\nclass Edit$1 extends Module{\n\t\n\tconstructor(table){\n\t\tsuper(table);\n\t\t\n\t\tthis.currentCell = false; //hold currently editing cell\n\t\tthis.mouseClick = false; //hold mousedown state to prevent click binding being overridden by editor opening\n\t\tthis.recursionBlock = false; //prevent focus recursion\n\t\tthis.invalidEdit = false;\n\t\tthis.editedCells = [];\n\t\t\n\t\tthis.editors = Edit$1.editors;\n\t\t\n\t\tthis.registerColumnOption(\"editable\");\n\t\tthis.registerColumnOption(\"editor\");\n\t\tthis.registerColumnOption(\"editorParams\");\n\t\t\n\t\tthis.registerColumnOption(\"cellEditing\");\n\t\tthis.registerColumnOption(\"cellEdited\");\n\t\tthis.registerColumnOption(\"cellEditCancelled\");\n\t\t\n\t\tthis.registerTableOption(\"editTriggerEvent\", \"focus\");\n\t\t\n\t\tthis.registerTableFunction(\"getEditedCells\", this.getEditedCells.bind(this));\n\t\tthis.registerTableFunction(\"clearCellEdited\", this.clearCellEdited.bind(this));\n\t\tthis.registerTableFunction(\"navigatePrev\", this.navigatePrev.bind(this));\n\t\tthis.registerTableFunction(\"navigateNext\", this.navigateNext.bind(this));\n\t\tthis.registerTableFunction(\"navigateLeft\", this.navigateLeft.bind(this));\n\t\tthis.registerTableFunction(\"navigateRight\", this.navigateRight.bind(this));\n\t\tthis.registerTableFunction(\"navigateUp\", this.navigateUp.bind(this));\n\t\tthis.registerTableFunction(\"navigateDown\", this.navigateDown.bind(this));\n\t\t\n\t\tthis.registerComponentFunction(\"cell\", \"isEdited\", this.cellIsEdited.bind(this));\n\t\tthis.registerComponentFunction(\"cell\", \"clearEdited\", this.clearEdited.bind(this));\n\t\tthis.registerComponentFunction(\"cell\", \"edit\", this.editCell.bind(this));\n\t\tthis.registerComponentFunction(\"cell\", \"cancelEdit\", this.cellCancelEdit.bind(this));\n\t\t\n\t\tthis.registerComponentFunction(\"cell\", \"navigatePrev\", this.navigatePrev.bind(this));\n\t\tthis.registerComponentFunction(\"cell\", \"navigateNext\", this.navigateNext.bind(this));\n\t\tthis.registerComponentFunction(\"cell\", \"navigateLeft\", this.navigateLeft.bind(this));\n\t\tthis.registerComponentFunction(\"cell\", \"navigateRight\", this.navigateRight.bind(this));\n\t\tthis.registerComponentFunction(\"cell\", \"navigateUp\", this.navigateUp.bind(this));\n\t\tthis.registerComponentFunction(\"cell\", \"navigateDown\", this.navigateDown.bind(this));\n\t}\n\t\n\tinitialize(){\n\t\tthis.subscribe(\"cell-init\", this.bindEditor.bind(this));\n\t\tthis.subscribe(\"cell-delete\", this.clearEdited.bind(this));\n\t\tthis.subscribe(\"cell-value-changed\", this.updateCellClass.bind(this));\n\t\tthis.subscribe(\"column-layout\", this.initializeColumnCheck.bind(this));\n\t\tthis.subscribe(\"column-delete\", this.columnDeleteCheck.bind(this));\n\t\tthis.subscribe(\"row-deleting\", this.rowDeleteCheck.bind(this));\n\t\tthis.subscribe(\"row-layout\", this.rowEditableCheck.bind(this));\n\t\tthis.subscribe(\"data-refreshing\", this.cancelEdit.bind(this));\n\t\tthis.subscribe(\"clipboard-paste\", this.pasteBlocker.bind(this));\n\t\t\n\t\tthis.subscribe(\"keybinding-nav-prev\", this.navigatePrev.bind(this, undefined));\n\t\tthis.subscribe(\"keybinding-nav-next\", this.keybindingNavigateNext.bind(this));\n\t\t\n\t\t\n\t\t// this.subscribe(\"keybinding-nav-left\", this.navigateLeft.bind(this, undefined));\n\t\t// this.subscribe(\"keybinding-nav-right\", this.navigateRight.bind(this, undefined));\n\t\tthis.subscribe(\"keybinding-nav-up\", this.navigateUp.bind(this, undefined));\n\t\tthis.subscribe(\"keybinding-nav-down\", this.navigateDown.bind(this, undefined));\n\t}\n\t\n\t\n\t///////////////////////////////////\n\t///////// Paste Negation //////////\n\t///////////////////////////////////\n\t\n\tpasteBlocker(e){\n\t\tif(this.currentCell){\n\t\t\treturn true;\n\t\t}\n\t}\n\t\n\t\n\t///////////////////////////////////\n\t////// Keybinding Functions ///////\n\t///////////////////////////////////\n\t\n\tkeybindingNavigateNext(e){\n\t\tvar cell = this.currentCell,\n\t\tnewRow = this.options(\"tabEndNewRow\");\n\n\t\tif(cell){\n\t\t\tif(!this.navigateNext(cell, e)){\n\t\t\t\tif(newRow){\n\t\t\t\t\tcell.getElement().firstChild.blur();\n\t\t\t\t\t\n\t\t\t\t\tif(!this.invalidEdit){\n\t\t\t\t\t\t\n\t\t\t\t\t\tif(newRow === true){\n\t\t\t\t\t\t\tnewRow = this.table.addRow({});\n\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\tif(typeof newRow == \"function\"){\n\t\t\t\t\t\t\t\tnewRow = this.table.addRow(newRow(cell.row.getComponent()));\n\t\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\t\tnewRow = this.table.addRow(Object.assign({}, newRow));\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t\t\n\t\t\t\t\t\tnewRow.then(() => {\n\t\t\t\t\t\t\tsetTimeout(() => {\n\t\t\t\t\t\t\t\tcell.getComponent().navigateNext();\n\t\t\t\t\t\t\t});\n\t\t\t\t\t\t});\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t\n\t///////////////////////////////////\n\t///////// Cell Functions //////////\n\t///////////////////////////////////\n\t\n\tcellIsEdited(cell){\n\t\treturn !! cell.modules.edit && cell.modules.edit.edited;\n\t}\n\t\n\tcellCancelEdit(cell){\n\t\tif(cell === this.currentCell){\n\t\t\tthis.table.modules.edit.cancelEdit();\n\t\t}else {\n\t\t\tconsole.warn(\"Cancel Editor Error - This cell is not currently being edited \");\n\t\t}\n\t}\n\t\n\t\n\t///////////////////////////////////\n\t///////// Table Functions /////////\n\t///////////////////////////////////\n\tupdateCellClass(cell){\n\t\tif(this.allowEdit(cell)) {\n\t\t\tcell.getElement().classList.add(\"tabulator-editable\");\n\t\t}\n\t\telse {\n\t\t\tcell.getElement().classList.remove(\"tabulator-editable\");\n\t\t}\n\t}\n\t\n\tclearCellEdited(cells){\n\t\tif(!cells){\n\t\t\tcells = this.table.modules.edit.getEditedCells();\n\t\t}\n\t\t\n\t\tif(!Array.isArray(cells)){\n\t\t\tcells = [cells];\n\t\t}\n\t\t\n\t\tcells.forEach((cell) => {\n\t\t\tthis.table.modules.edit.clearEdited(cell._getSelf());\n\t\t});\n\t}\n\t\n\tnavigatePrev(cell = this.currentCell, e){\n\t\tvar nextCell, prevRow;\n\t\t\n\t\tif(cell){\n\t\t\t\n\t\t\tif(e){\n\t\t\t\te.preventDefault();\n\t\t\t}\n\t\t\t\n\t\t\tnextCell = this.navigateLeft();\n\t\t\t\n\t\t\tif(nextCell){\n\t\t\t\treturn true;\n\t\t\t}else {\n\t\t\t\tprevRow = this.table.rowManager.prevDisplayRow(cell.row, true);\n\t\t\t\t\n\t\t\t\tif(prevRow){\n\t\t\t\t\tnextCell = this.findPrevEditableCell(prevRow, prevRow.cells.length);\n\t\t\t\t\t\n\t\t\t\t\tif(nextCell){\n\t\t\t\t\t\tnextCell.getComponent().edit();\n\t\t\t\t\t\treturn true;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn false;\n\t}\n\t\n\tnavigateNext(cell = this.currentCell, e){\n\t\tvar nextCell, nextRow;\n\t\t\n\t\tif(cell){\n\t\t\t\n\t\t\tif(e){\n\t\t\t\te.preventDefault();\n\t\t\t}\n\t\t\t\n\t\t\tnextCell = this.navigateRight();\n\t\t\t\n\t\t\tif(nextCell){\n\t\t\t\treturn true;\n\t\t\t}else {\n\t\t\t\tnextRow = this.table.rowManager.nextDisplayRow(cell.row, true);\n\t\t\t\t\n\t\t\t\tif(nextRow){\n\t\t\t\t\tnextCell = this.findNextEditableCell(nextRow, -1);\n\t\t\t\t\t\n\t\t\t\t\tif(nextCell){\n\t\t\t\t\t\tnextCell.getComponent().edit();\n\t\t\t\t\t\treturn true;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn false;\n\t}\n\t\n\tnavigateLeft(cell = this.currentCell, e){\n\t\tvar index, nextCell;\n\t\t\n\t\tif(cell){\n\t\t\t\n\t\t\tif(e){\n\t\t\t\te.preventDefault();\n\t\t\t}\n\t\t\t\n\t\t\tindex = cell.getIndex();\n\t\t\tnextCell = this.findPrevEditableCell(cell.row, index);\n\t\t\t\n\t\t\tif(nextCell){\n\t\t\t\tnextCell.getComponent().edit();\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn false;\n\t}\n\t\n\tnavigateRight(cell = this.currentCell, e){\n\t\tvar index, nextCell;\n\t\t\n\t\tif(cell){\n\t\t\t\n\t\t\tif(e){\n\t\t\t\te.preventDefault();\n\t\t\t}\n\t\t\t\n\t\t\tindex = cell.getIndex();\n\t\t\tnextCell = this.findNextEditableCell(cell.row, index);\n\t\t\t\n\t\t\tif(nextCell){\n\t\t\t\tnextCell.getComponent().edit();\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn false;\n\t}\n\t\n\tnavigateUp(cell = this.currentCell, e){\n\t\tvar index, nextRow;\n\t\t\n\t\tif(cell){\n\t\t\t\n\t\t\tif(e){\n\t\t\t\te.preventDefault();\n\t\t\t}\n\t\t\t\n\t\t\tindex = cell.getIndex();\n\t\t\tnextRow = this.table.rowManager.prevDisplayRow(cell.row, true);\n\t\t\t\n\t\t\tif(nextRow){\n\t\t\t\tnextRow.cells[index].getComponent().edit();\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn false;\n\t}\n\t\n\tnavigateDown(cell = this.currentCell, e){\n\t\tvar index, nextRow;\n\t\t\n\t\tif(cell){\n\t\t\t\n\t\t\tif(e){\n\t\t\t\te.preventDefault();\n\t\t\t}\n\t\t\t\n\t\t\tindex = cell.getIndex();\n\t\t\tnextRow = this.table.rowManager.nextDisplayRow(cell.row, true);\n\t\t\t\n\t\t\tif(nextRow){\n\t\t\t\tnextRow.cells[index].getComponent().edit();\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn false;\n\t}\n\t\n\tfindNextEditableCell(row, index){\n\t\tvar nextCell = false;\n\t\t\n\t\tif(index < row.cells.length-1){\n\t\t\tfor(var i = index+1; i < row.cells.length; i++){\n\t\t\t\tlet cell = row.cells[i];\n\t\t\t\t\n\t\t\t\tif(cell.column.modules.edit && Helpers.elVisible(cell.getElement())){\n\t\t\t\t\tlet allowEdit = this.allowEdit(cell);\n\t\t\t\t\t\n\t\t\t\t\tif(allowEdit){\n\t\t\t\t\t\tnextCell = cell;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn nextCell;\n\t}\n\t\n\tfindPrevEditableCell(row, index){\n\t\tvar prevCell = false;\n\t\t\n\t\tif(index > 0){\n\t\t\tfor(var i = index-1; i >= 0; i--){\n\t\t\t\tlet cell = row.cells[i];\n\t\t\t\t\n\t\t\t\tif(cell.column.modules.edit && Helpers.elVisible(cell.getElement())){\n\t\t\t\t\tlet allowEdit = this.allowEdit(cell);\n\t\t\t\t\t\n\t\t\t\t\tif(allowEdit){\n\t\t\t\t\t\tprevCell = cell;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn prevCell;\n\t}\n\t\n\t///////////////////////////////////\n\t///////// Internal Logic //////////\n\t///////////////////////////////////\n\t\n\tinitializeColumnCheck(column){\n\t\tif(typeof column.definition.editor !== \"undefined\"){\n\t\t\tthis.initializeColumn(column);\n\t\t}\n\t}\n\t\n\tcolumnDeleteCheck(column){\n\t\tif(this.currentCell && this.currentCell.column === column){\n\t\t\tthis.cancelEdit();\n\t\t}\n\t}\n\t\n\trowDeleteCheck(row){\n\t\tif(this.currentCell && this.currentCell.row === row){\n\t\t\tthis.cancelEdit();\n\t\t}\n\t}\n\t\n\trowEditableCheck(row){\n\t\trow.getCells().forEach((cell) => {\n\t\t\tif(cell.column.modules.edit && typeof cell.column.modules.edit.check === \"function\"){\n\t\t\t\tthis.updateCellClass(cell);\n\t\t\t}\n\t\t});\n\t}\n\t\n\t//initialize column editor\n\tinitializeColumn(column){\n\t\tvar config = {\n\t\t\teditor:false,\n\t\t\tblocked:false,\n\t\t\tcheck:column.definition.editable,\n\t\t\tparams:column.definition.editorParams || {}\n\t\t};\n\t\t\n\t\t//set column editor\n\t\tswitch(typeof column.definition.editor){\n\t\t\tcase \"string\":\n\t\t\t\tif(this.editors[column.definition.editor]){\n\t\t\t\t\tconfig.editor = this.editors[column.definition.editor];\n\t\t\t\t}else {\n\t\t\t\t\tconsole.warn(\"Editor Error - No such editor found: \", column.definition.editor);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase \"function\":\n\t\t\t\tconfig.editor = column.definition.editor;\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase \"boolean\":\n\t\t\t\tif(column.definition.editor === true){\n\t\t\t\t\tif(typeof column.definition.formatter !== \"function\"){\n\t\t\t\t\t\tif(this.editors[column.definition.formatter]){\n\t\t\t\t\t\t\tconfig.editor = this.editors[column.definition.formatter];\n\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\tconfig.editor = this.editors[\"input\"];\n\t\t\t\t\t\t}\n\t\t\t\t\t}else {\n\t\t\t\t\t\tconsole.warn(\"Editor Error - Cannot auto lookup editor for a custom formatter: \", column.definition.formatter);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t}\n\t\t\n\t\tif(config.editor){\n\t\t\tcolumn.modules.edit = config;\n\t\t}\n\t}\n\t\n\tgetCurrentCell(){\n\t\treturn this.currentCell ? this.currentCell.getComponent() : false;\n\t}\n\t\n\tclearEditor(cancel){\n\t\tvar cell = this.currentCell,\n\t\tcellEl;\n\t\t\n\t\tthis.invalidEdit = false;\n\t\t\n\t\tif(cell){\n\t\t\tthis.currentCell = false;\n\t\t\t\n\t\t\tcellEl = cell.getElement();\n\t\t\t\n\t\t\tthis.dispatch(\"edit-editor-clear\", cell, cancel);\n\t\t\t\n\t\t\tcellEl.classList.remove(\"tabulator-editing\");\n\t\t\t\n\t\t\twhile(cellEl.firstChild) cellEl.removeChild(cellEl.firstChild);\n\t\t\t\n\t\t\tcell.row.getElement().classList.remove(\"tabulator-editing\");\n\t\t\t\n\t\t\tcell.table.element.classList.remove(\"tabulator-editing\");\n\t\t}\n\t}\n\t\n\tcancelEdit(){\n\t\tif(this.currentCell){\n\t\t\tvar cell = this.currentCell;\n\t\t\tvar component = this.currentCell.getComponent();\n\t\t\t\n\t\t\tthis.clearEditor(true);\n\t\t\tcell.setValueActual(cell.getValue());\n\t\t\tcell.cellRendered();\n\t\t\t\n\t\t\tif(cell.column.definition.editor == \"textarea\" || cell.column.definition.variableHeight){\n\t\t\t\tcell.row.normalizeHeight(true);\n\t\t\t}\n\t\t\t\n\t\t\tif(cell.column.definition.cellEditCancelled){\n\t\t\t\tcell.column.definition.cellEditCancelled.call(this.table, component);\n\t\t\t}\n\t\t\t\n\t\t\tthis.dispatch(\"edit-cancelled\", cell);\n\t\t\tthis.dispatchExternal(\"cellEditCancelled\", component);\n\t\t}\n\t}\n\t\n\t//return a formatted value for a cell\n\tbindEditor(cell){\n\t\tif(cell.column.modules.edit){\n\t\t\tvar self = this,\n\t\t\telement = cell.getElement(true);\n\t\t\t\n\t\t\tthis.updateCellClass(cell);\n\t\t\telement.setAttribute(\"tabindex\", 0);\n\t\t\t\n\t\t\telement.addEventListener(\"mousedown\", function(e){\n\t\t\t\tif (e.button === 2) {\n\t\t\t\t\te.preventDefault();\n\t\t\t\t}else {\n\t\t\t\t\tself.mouseClick = true;\n\t\t\t\t}\n\t\t\t});\n\n\t\t\tif(this.options(\"editTriggerEvent\") === \"dblclick\"){\n\t\t\t\telement.addEventListener(\"dblclick\", function(e){\n\t\t\t\t\tif(!element.classList.contains(\"tabulator-editing\")){\n\t\t\t\t\t\telement.focus({preventScroll: true});\n\t\t\t\t\t\tself.edit(cell, e, false);\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t}\n\t\t\t\n\t\t\t\n\t\t\tif(this.options(\"editTriggerEvent\") === \"focus\" || this.options(\"editTriggerEvent\") === \"click\"){\n\t\t\t\telement.addEventListener(\"click\", function(e){\n\t\t\t\t\tif(!element.classList.contains(\"tabulator-editing\")){\n\t\t\t\t\t\telement.focus({preventScroll: true});\n\t\t\t\t\t\tself.edit(cell, e, false);\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t}\n\t\t\t\n\t\t\tif(this.options(\"editTriggerEvent\") === \"focus\"){\n\t\t\t\telement.addEventListener(\"focus\", function(e){\n\t\t\t\t\tif(!self.recursionBlock){\n\t\t\t\t\t\tself.edit(cell, e, false);\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t}\n\t\t}\n\t}\n\t\n\tfocusCellNoEvent(cell, block){\n\t\tthis.recursionBlock = true;\n\t\t\n\t\tif(!(block && this.table.browser === \"ie\")){\n\t\t\tcell.getElement().focus({preventScroll: true});\n\t\t}\n\t\t\n\t\tthis.recursionBlock = false;\n\t}\n\t\n\teditCell(cell, forceEdit){\n\t\tthis.focusCellNoEvent(cell);\n\t\tthis.edit(cell, false, forceEdit);\n\t}\n\t\n\tfocusScrollAdjust(cell){\n\t\tif(this.table.rowManager.getRenderMode() == \"virtual\"){\n\t\t\tvar topEdge = this.table.rowManager.element.scrollTop,\n\t\t\tbottomEdge = this.table.rowManager.element.clientHeight + this.table.rowManager.element.scrollTop,\n\t\t\trowEl = cell.row.getElement();\n\t\t\t\n\t\t\tif(rowEl.offsetTop < topEdge){\n\t\t\t\tthis.table.rowManager.element.scrollTop -= (topEdge - rowEl.offsetTop);\n\t\t\t}else {\n\t\t\t\tif(rowEl.offsetTop + rowEl.offsetHeight  > bottomEdge){\n\t\t\t\t\tthis.table.rowManager.element.scrollTop += (rowEl.offsetTop + rowEl.offsetHeight - bottomEdge);\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\tvar leftEdge = this.table.rowManager.element.scrollLeft,\n\t\t\trightEdge = this.table.rowManager.element.clientWidth + this.table.rowManager.element.scrollLeft,\n\t\t\tcellEl = cell.getElement();\n\t\t\t\n\t\t\tif(this.table.modExists(\"frozenColumns\")){\n\t\t\t\tleftEdge += parseInt(this.table.modules.frozenColumns.leftMargin || 0);\n\t\t\t\trightEdge -= parseInt(this.table.modules.frozenColumns.rightMargin || 0);\n\t\t\t}\n\t\t\t\n\t\t\tif(this.table.options.renderHorizontal === \"virtual\"){\n\t\t\t\tleftEdge -= parseInt(this.table.columnManager.renderer.vDomPadLeft);\n\t\t\t\trightEdge -= parseInt(this.table.columnManager.renderer.vDomPadLeft);\n\t\t\t}\n\t\t\t\n\t\t\tif(cellEl.offsetLeft < leftEdge){\n\t\t\t\tthis.table.rowManager.element.scrollLeft -= (leftEdge - cellEl.offsetLeft);\n\t\t\t}else {\n\t\t\t\tif(cellEl.offsetLeft + cellEl.offsetWidth  > rightEdge){\n\t\t\t\t\tthis.table.rowManager.element.scrollLeft += (cellEl.offsetLeft + cellEl.offsetWidth - rightEdge);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t\n\tallowEdit(cell) {\n\t\tvar check = cell.column.modules.edit ? true : false;\n\t\t\n\t\tif(cell.column.modules.edit){\n\t\t\tswitch(typeof cell.column.modules.edit.check){\n\t\t\t\tcase \"function\":\n\t\t\t\t\tif(cell.row.initialized){\n\t\t\t\t\t\tcheck = cell.column.modules.edit.check(cell.getComponent());\n\t\t\t\t\t}\n\t\t\t\t\tbreak;\n\t\t\t\t\n\t\t\t\tcase \"string\":\n\t\t\t\t\tcheck = !!cell.row.data[cell.column.modules.edit.check];\n\t\t\t\t\tbreak;\n\t\t\t\t\n\t\t\t\tcase \"boolean\":\n\t\t\t\t\tcheck = cell.column.modules.edit.check;\n\t\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn check;\n\t}\n\t\n\tedit(cell, e, forceEdit){\n\t\tvar self = this,\n\t\tallowEdit = true,\n\t\trendered = function(){},\n\t\telement = cell.getElement(),\n\t\teditFinished = false,\n\t\tcellEditor, component, params;\n\n\t\t//prevent editing if another cell is refusing to leave focus (eg. validation fail)\n\t\t\n\t\tif(this.currentCell){\n\t\t\tif(!this.invalidEdit && this.currentCell !== cell){\n\t\t\t\tthis.cancelEdit();\n\t\t\t}\n\t\t\treturn;\n\t\t}\n\t\t\n\t\t//handle successful value change\n\t\tfunction success(value){\n\t\t\tif(self.currentCell === cell && !editFinished){\n\t\t\t\tvar valid = self.chain(\"edit-success\", [cell, value], true, true);\n\n\t\t\t\tif(valid === true || self.table.options.validationMode === \"highlight\"){\n\n\t\t\t\t\teditFinished = true;\n\n\t\t\t\t\tself.clearEditor();\n\t\t\t\t\t\n\t\t\t\t\tif(!cell.modules.edit){\n\t\t\t\t\t\tcell.modules.edit = {};\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\tcell.modules.edit.edited = true;\n\t\t\t\t\t\n\t\t\t\t\tif(self.editedCells.indexOf(cell) == -1){\n\t\t\t\t\t\tself.editedCells.push(cell);\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\tcell.setValue(value, true);\n\n\t\t\t\t\treturn valid === true;\n\t\t\t\t}else {\n\t\t\t\t\teditFinished = true;\n\t\t\t\t\tself.invalidEdit = true;\n\t\t\t\t\tself.focusCellNoEvent(cell, true);\n\t\t\t\t\trendered();\n\n\t\t\t\t\tsetTimeout(() => {\n\t\t\t\t\t\teditFinished = false;\n\t\t\t\t\t}, 10);\n\t\t\t\t\treturn false;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\t//handle aborted edit\n\t\tfunction cancel(){\n\t\t\t// editFinished = true;\n\n\t\t\tif(self.currentCell === cell && !editFinished){\n\t\t\t\tself.cancelEdit();\n\t\t\t}\n\t\t}\n\t\t\n\t\tfunction onRendered(callback){\n\t\t\trendered = callback;\n\t\t}\n\t\t\n\t\tif(!cell.column.modules.edit.blocked){\n\t\t\tif(e){\n\t\t\t\te.stopPropagation();\n\t\t\t}\n\t\t\t\n\t\t\tallowEdit = this.allowEdit(cell);\n\t\t\t\n\t\t\tif(allowEdit || forceEdit){\n\t\t\t\tself.cancelEdit();\n\t\t\t\t\n\t\t\t\tself.currentCell = cell;\n\t\t\t\t\n\t\t\t\tthis.focusScrollAdjust(cell);\n\t\t\t\t\n\t\t\t\tcomponent = cell.getComponent();\n\t\t\t\t\n\t\t\t\tif(this.mouseClick){\n\t\t\t\t\tthis.mouseClick = false;\n\t\t\t\t\t\n\t\t\t\t\tif(cell.column.definition.cellClick){\n\t\t\t\t\t\tcell.column.definition.cellClick.call(this.table, e, component);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tif(cell.column.definition.cellEditing){\n\t\t\t\t\tcell.column.definition.cellEditing.call(this.table, component);\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tthis.dispatch(\"cell-editing\", cell);\n\t\t\t\tthis.dispatchExternal(\"cellEditing\", component);\n\t\t\t\t\n\t\t\t\tparams = typeof cell.column.modules.edit.params === \"function\" ? cell.column.modules.edit.params(component) : cell.column.modules.edit.params;\n\t\t\t\t\n\t\t\t\tcellEditor = cell.column.modules.edit.editor.call(self, component, onRendered, success, cancel, params);\n\t\t\t\t\n\t\t\t\t//if editor returned, add to DOM, if false, abort edit\n\t\t\t\tif(this.currentCell && cellEditor !== false){\n\t\t\t\t\tif(cellEditor instanceof Node){\n\t\t\t\t\t\telement.classList.add(\"tabulator-editing\");\n\t\t\t\t\t\tcell.row.getElement().classList.add(\"tabulator-editing\");\n\t\t\t\t\t\tcell.table.element.classList.add(\"tabulator-editing\");\n\t\t\t\t\t\twhile(element.firstChild) element.removeChild(element.firstChild);\n\t\t\t\t\t\telement.appendChild(cellEditor);\n\t\t\t\t\t\t\n\t\t\t\t\t\t//trigger onRendered Callback\n\t\t\t\t\t\trendered();\n\t\t\t\t\t\t\n\t\t\t\t\t\t//prevent editing from triggering rowClick event\n\t\t\t\t\t\tvar children = element.children;\n\t\t\t\t\t\t\n\t\t\t\t\t\tfor (var i = 0; i < children.length; i++) {\n\t\t\t\t\t\t\tchildren[i].addEventListener(\"click\", function(e){\n\t\t\t\t\t\t\t\te.stopPropagation();\n\t\t\t\t\t\t\t});\n\t\t\t\t\t\t}\n\t\t\t\t\t}else {\n\t\t\t\t\t\tconsole.warn(\"Edit Error - Editor should return an instance of Node, the editor returned:\", cellEditor);\n\t\t\t\t\t\tthis.blur(element);\n\t\t\t\t\t\treturn false;\n\t\t\t\t\t}\n\t\t\t\t}else {\n\t\t\t\t\tthis.blur(element);\n\t\t\t\t\treturn false;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\treturn true;\n\t\t\t}else {\n\t\t\t\tthis.mouseClick = false;\n\t\t\t\tthis.blur(element);\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}else {\n\t\t\tthis.mouseClick = false;\n\t\t\tthis.blur(element);\n\t\t\treturn false;\n\t\t}\n\t}\n\t\n\tblur(element){\n\t\tif(!this.confirm(\"edit-blur\", [element]) ){\n\t\t\telement.blur();\n\t\t}\n\t}\n\t\n\tgetEditedCells(){\n\t\tvar output = [];\n\t\t\n\t\tthis.editedCells.forEach((cell) => {\n\t\t\toutput.push(cell.getComponent());\n\t\t});\n\t\t\n\t\treturn output;\n\t}\n\t\n\tclearEdited(cell){\n\t\tvar editIndex;\n\t\t\n\t\tif(cell.modules.edit && cell.modules.edit.edited){\n\t\t\tcell.modules.edit.edited = false;\n\t\t\t\n\t\t\tthis.dispatch(\"edit-edited-clear\", cell);\n\t\t}\n\t\t\n\t\teditIndex = this.editedCells.indexOf(cell);\n\t\t\n\t\tif(editIndex > -1){\n\t\t\tthis.editedCells.splice(editIndex, 1);\n\t\t}\n\t}\n}\n\nEdit$1.moduleName = \"edit\";\n\n//load defaults\nEdit$1.editors = defaultEditors;\n\nclass ExportRow{\n\tconstructor(type, columns, component, indent){\n\t\tthis.type = type;\n\t\tthis.columns = columns;\n\t\tthis.component = component || false;\n\t\tthis.indent = indent || 0;\n\t}\n}\n\nclass ExportColumn{\n\tconstructor(value, component, width, height, depth){\n\t\tthis.value = value;\n\t\tthis.component = component || false;\n\t\tthis.width = width;\n\t\tthis.height = height;\n\t\tthis.depth = depth;\n\t}\n}\n\nclass Export extends Module{\n\t\n\tconstructor(table){\n\t\tsuper(table);\n\t\t\n\t\tthis.config = {};\n\t\tthis.cloneTableStyle = true;\n\t\tthis.colVisProp = \"\";\n\t\t\n\t\tthis.registerTableOption(\"htmlOutputConfig\", false); //html output config\n\t\t\n\t\tthis.registerColumnOption(\"htmlOutput\");\n\t\tthis.registerColumnOption(\"titleHtmlOutput\");\n\t}\n\t\n\tinitialize(){\n\t\tthis.registerTableFunction(\"getHtml\", this.getHtml.bind(this));\n\t}\n\t\n\t///////////////////////////////////\n\t///////// Table Functions /////////\n\t///////////////////////////////////\n\t\n\t\n\t///////////////////////////////////\n\t///////// Internal Logic //////////\n\t///////////////////////////////////\n\t\n\tgenerateExportList(config, style, range, colVisProp){\n\t\tthis.cloneTableStyle = style;\n\t\tthis.config = config || {};\n\t\tthis.colVisProp = colVisProp;\n\n\t\tvar headers, body;\n\t\t\n\t\tif (range === 'range') {\n\t\t\tvar columns = this.table.modules.selectRange.selectedColumns();\n\t\t\theaders = this.config.columnHeaders !== false\n\t\t\t\t? this.headersToExportRows(this.generateColumnGroupHeaders(columns))\n\t\t\t\t: [];\n\t\t\tbody = this.bodyToExportRows(this.rowLookup(range), this.table.modules.selectRange.selectedColumns(true));\n\t\t} else {\n\t\t\theaders = this.config.columnHeaders !== false ? this.headersToExportRows(this.generateColumnGroupHeaders()) : [];\n\t\t\tbody = this.bodyToExportRows(this.rowLookup(range));\n\t\t}\n\n\t\treturn headers.concat(body);\n\t}\n\t\n\tgenerateTable(config, style, range, colVisProp){\n\t\tvar list = this.generateExportList(config, style, range, colVisProp);\n\t\t\n\t\treturn this.generateTableElement(list);\n\t}\n\t\n\trowLookup(range){\n\t\tvar rows = [];\n\t\t\n\t\tif(typeof range == \"function\"){\n\t\t\trange.call(this.table).forEach((row) =>{\n\t\t\t\trow = this.table.rowManager.findRow(row);\n\t\t\t\t\n\t\t\t\tif(row){\n\t\t\t\t\trows.push(row);\n\t\t\t\t}\n\t\t\t});\n\t\t}else {\n\t\t\tswitch(range){\n\t\t\t\tcase true:\n\t\t\t\tcase \"visible\":\n\t\t\t\t\trows = this.table.rowManager.getVisibleRows(false, true);\n\t\t\t\t\tbreak;\n\t\t\t\t\n\t\t\t\tcase \"all\":\n\t\t\t\t\trows = this.table.rowManager.rows;\n\t\t\t\t\tbreak;\n\t\t\t\t\n\t\t\t\tcase \"selected\":\n\t\t\t\t\trows = this.table.modules.selectRow.selectedRows;\n\t\t\t\t\tbreak;\n\n\t\t\t\tcase \"range\":\n\t\t\t\t\trows = this.table.modules.selectRange.selectedRows();\n\t\t\t\t\tbreak;\n\n\t\t\t\tcase \"active\":\n\t\t\t\tdefault:\n\t\t\t\t\tif(this.table.options.pagination){\n\t\t\t\t\t\trows = this.table.rowManager.getDisplayRows(this.table.rowManager.displayRows.length - 2);\n\t\t\t\t\t}else {\n\t\t\t\t\t\trows = this.table.rowManager.getDisplayRows();\n\t\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn Object.assign([], rows);\n\t}\n\t\n\tgenerateColumnGroupHeaders(columns){\n\t\tvar output = [];\n\t\t\n\t\tif (!columns) {\n\t\t\tcolumns = this.config.columnGroups !== false ? this.table.columnManager.columns : this.table.columnManager.columnsByIndex;\n\t\t}\n\t\t\n\t\tcolumns.forEach((column) => {\n\t\t\tvar colData = this.processColumnGroup(column);\n\t\t\t\n\t\t\tif(colData){\n\t\t\t\toutput.push(colData);\n\t\t\t}\n\t\t});\n\n\t\treturn output;\n\t}\n\t\n\tprocessColumnGroup(column){\n\t\tvar subGroups = column.columns,\n\t\tmaxDepth = 0,\n\t\ttitle = column.definition[\"title\" + (this.colVisProp.charAt(0).toUpperCase() + this.colVisProp.slice(1))] || column.definition.title;\n\t\t\n\t\tvar groupData = {\n\t\t\ttitle:title,\n\t\t\tcolumn:column,\n\t\t\tdepth:1,\n\t\t};\n\t\t\n\t\tif(subGroups.length){\n\t\t\tgroupData.subGroups = [];\n\t\t\tgroupData.width = 0;\n\t\t\t\n\t\t\tsubGroups.forEach((subGroup) => {\n\t\t\t\tvar subGroupData = this.processColumnGroup(subGroup);\n\t\t\t\t\n\t\t\t\tif(subGroupData){\n\t\t\t\t\tgroupData.width += subGroupData.width;\n\t\t\t\t\tgroupData.subGroups.push(subGroupData);\n\t\t\t\t\t\n\t\t\t\t\tif(subGroupData.depth > maxDepth){\n\t\t\t\t\t\tmaxDepth = subGroupData.depth;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t});\n\t\t\t\n\t\t\tgroupData.depth += maxDepth;\n\t\t\t\n\t\t\tif(!groupData.width){\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}else {\n\t\t\tif(this.columnVisCheck(column)){\n\t\t\t\tgroupData.width = 1;\n\t\t\t}else {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn groupData;\n\t}\n\t\n\tcolumnVisCheck(column){\n\t\tvar visProp = column.definition[this.colVisProp];\n\t\t\n\t\tif(typeof visProp === \"function\"){\n\t\t\tvisProp = visProp.call(this.table, column.getComponent());\n\t\t}\n\t\t\n\t\treturn visProp !== false && (column.visible || (!column.visible && visProp));\n\t}\n\t\n\theadersToExportRows(columns){\n\t\tvar headers = [],\n\t\theaderDepth = 0,\n\t\texportRows = [];\n\t\t\n\t\tfunction parseColumnGroup(column, level){\n\t\t\t\n\t\t\tvar depth = headerDepth - level;\n\t\t\t\n\t\t\tif(typeof headers[level] === \"undefined\"){\n\t\t\t\theaders[level] = [];\n\t\t\t}\n\t\t\t\n\t\t\tcolumn.height = column.subGroups ? 1 : (depth - column.depth) + 1;\n\t\t\t\n\t\t\theaders[level].push(column);\n\t\t\t\n\t\t\tif(column.height > 1){\n\t\t\t\tfor(let i = 1; i < column.height; i ++){\n\t\t\t\t\t\n\t\t\t\t\tif(typeof headers[level + i] === \"undefined\"){\n\t\t\t\t\t\theaders[level + i] = [];\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\theaders[level + i].push(false);\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\tif(column.width > 1){\n\t\t\t\tfor(let i = 1; i < column.width; i ++){\n\t\t\t\t\theaders[level].push(false);\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\tif(column.subGroups){\n\t\t\t\tcolumn.subGroups.forEach(function(subGroup){\n\t\t\t\t\tparseColumnGroup(subGroup, level+1);\n\t\t\t\t});\n\t\t\t}\n\t\t}\n\t\t\n\t\t//calculate maximum header depth\n\t\tcolumns.forEach(function(column){\n\t\t\tif(column.depth > headerDepth){\n\t\t\t\theaderDepth = column.depth;\n\t\t\t}\n\t\t});\n\t\t\n\t\tcolumns.forEach(function(column){\n\t\t\tparseColumnGroup(column,0);\n\t\t});\n\t\t\n\t\theaders.forEach((header) => {\n\t\t\tvar columns = [];\n\t\t\t\n\t\t\theader.forEach((col) => {\n\t\t\t\tif(col){\n\t\t\t\t\tlet title = typeof col.title === \"undefined\" ? \"\" : col.title;\n\t\t\t\t\tcolumns.push(new ExportColumn(title, col.column.getComponent(), col.width, col.height, col.depth));\n\t\t\t\t}else {\n\t\t\t\t\tcolumns.push(null);\n\t\t\t\t}\n\t\t\t});\n\t\t\t\n\t\t\texportRows.push(new ExportRow(\"header\", columns));\n\t\t});\n\t\t\n\t\treturn exportRows;\n\t}\n\t\n\tbodyToExportRows(rows, columns = []){\n\t\tvar exportRows = [];\n\t\t\n\t\tif (columns.length === 0) {\n\t\t\tthis.table.columnManager.columnsByIndex.forEach((column) => {\n\t\t\t\tif (this.columnVisCheck(column)) {\n\t\t\t\t\tcolumns.push(column.getComponent());\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\t\t\n\t\tif(this.config.columnCalcs !== false && this.table.modExists(\"columnCalcs\")){\n\t\t\tif(this.table.modules.columnCalcs.topInitialized){\n\t\t\t\trows.unshift(this.table.modules.columnCalcs.topRow);\n\t\t\t}\n\t\t\t\n\t\t\tif(this.table.modules.columnCalcs.botInitialized){\n\t\t\t\trows.push(this.table.modules.columnCalcs.botRow);\n\t\t\t}\n\t\t}\n\n\t\trows = rows.filter((row) => {\n\t\t\tswitch(row.type){\n\t\t\t\tcase \"group\":\n\t\t\t\t\treturn this.config.rowGroups !== false;\n\t\t\t\t\n\t\t\t\tcase \"calc\":\n\t\t\t\t\treturn this.config.columnCalcs !== false;\n\t\t\t\t\n\t\t\t\tcase \"row\":\n\t\t\t\t\treturn !(this.table.options.dataTree && this.config.dataTree === false && row.modules.dataTree.parent);\n\t\t\t}\n\t\t\t\n\t\t\treturn true;\n\t\t});\n\t\t\n\t\trows.forEach((row, i) => {\n\t\t\tvar rowData = row.getData(this.colVisProp);\n\t\t\tvar exportCols = [];\n\t\t\tvar indent = 0;\n\t\t\t\n\t\t\tswitch(row.type){\n\t\t\t\tcase \"group\":\n\t\t\t\t\tindent = row.level;\n\t\t\t\t\texportCols.push(new ExportColumn(row.key, row.getComponent(), columns.length, 1));\n\t\t\t\t\tbreak;\n\t\t\t\t\n\t\t\t\tcase \"calc\" :\n\t\t\t\tcase \"row\" :\n\t\t\t\t\tcolumns.forEach((col) => {\n\t\t\t\t\t\texportCols.push(new ExportColumn(col._column.getFieldValue(rowData), col, 1, 1));\n\t\t\t\t\t});\n\t\t\t\t\n\t\t\t\t\tif(this.table.options.dataTree && this.config.dataTree !== false){\n\t\t\t\t\t\tindent = row.modules.dataTree.index;\n\t\t\t\t\t}\n\t\t\t\t\tbreak;\n\t\t\t}\n\t\t\t\n\t\t\texportRows.push(new ExportRow(row.type, exportCols, row.getComponent(), indent));\n\t\t});\n\t\t\n\t\treturn exportRows;\n\t}\n\t\n\tgenerateTableElement(list){\n\t\tvar table = document.createElement(\"table\"),\n\t\theaderEl = document.createElement(\"thead\"),\n\t\tbodyEl = document.createElement(\"tbody\"),\n\t\tstyles = this.lookupTableStyles(),\n\t\trowFormatter = this.table.options[\"rowFormatter\" + (this.colVisProp.charAt(0).toUpperCase() + this.colVisProp.slice(1))],\n\t\tsetup = {};\n\t\t\n\t\tsetup.rowFormatter = rowFormatter !== null ? rowFormatter : this.table.options.rowFormatter;\n\t\t\n\t\tif(this.table.options.dataTree &&this.config.dataTree !== false && this.table.modExists(\"columnCalcs\")){\n\t\t\tsetup.treeElementField = this.table.modules.dataTree.elementField;\n\t\t}\n\t\t\n\t\t//assign group header formatter\n\t\tsetup.groupHeader = this.table.options[\"groupHeader\" + (this.colVisProp.charAt(0).toUpperCase() + this.colVisProp.slice(1))];\n\t\t\n\t\tif(setup.groupHeader && !Array.isArray(setup.groupHeader)){\n\t\t\tsetup.groupHeader = [setup.groupHeader];\n\t\t}\n\t\t\n\t\ttable.classList.add(\"tabulator-print-table\");\n\t\t\n\t\tthis.mapElementStyles(this.table.columnManager.getHeadersElement(), headerEl, [\"border-top\", \"border-left\", \"border-right\", \"border-bottom\", \"background-color\", \"color\", \"font-weight\", \"font-family\", \"font-size\"]);\n\t\t\n\t\t\n\t\tif(list.length > 1000){\n\t\t\tconsole.warn(\"It may take a long time to render an HTML table with more than 1000 rows\");\n\t\t}\n\t\t\n\t\tlist.forEach((row, i) => {\n\t\t\tlet rowEl;\n\t\t\t\n\t\t\tswitch(row.type){\n\t\t\t\tcase \"header\":\n\t\t\t\t\theaderEl.appendChild(this.generateHeaderElement(row, setup, styles));\n\t\t\t\t\tbreak;\n\t\t\t\t\n\t\t\t\tcase \"group\":\n\t\t\t\t\tbodyEl.appendChild(this.generateGroupElement(row, setup, styles));\n\t\t\t\t\tbreak;\n\t\t\t\t\n\t\t\t\tcase \"calc\":\n\t\t\t\t\tbodyEl.appendChild(this.generateCalcElement(row, setup, styles));\n\t\t\t\t\tbreak;\n\t\t\t\t\n\t\t\t\tcase \"row\":\n\t\t\t\t\trowEl = this.generateRowElement(row, setup, styles);\n\t\t\t\t\n\t\t\t\t\tthis.mapElementStyles(((i % 2) && styles.evenRow) ? styles.evenRow : styles.oddRow, rowEl, [\"border-top\", \"border-left\", \"border-right\", \"border-bottom\", \"color\", \"font-weight\", \"font-family\", \"font-size\", \"background-color\"]);\n\t\t\t\t\tbodyEl.appendChild(rowEl);\n\t\t\t\t\tbreak;\n\t\t\t}\n\t\t});\n\t\t\n\t\tif(headerEl.innerHTML){\n\t\t\ttable.appendChild(headerEl);\n\t\t}\n\t\t\n\t\ttable.appendChild(bodyEl);\n\t\t\n\t\t\n\t\tthis.mapElementStyles(this.table.element, table, [\"border-top\", \"border-left\", \"border-right\", \"border-bottom\"]);\n\t\treturn table;\n\t}\n\t\n\tlookupTableStyles(){\n\t\tvar styles = {};\n\t\t\n\t\t//lookup row styles\n\t\tif(this.cloneTableStyle && window.getComputedStyle){\n\t\t\tstyles.oddRow = this.table.element.querySelector(\".tabulator-row-odd:not(.tabulator-group):not(.tabulator-calcs)\");\n\t\t\tstyles.evenRow = this.table.element.querySelector(\".tabulator-row-even:not(.tabulator-group):not(.tabulator-calcs)\");\n\t\t\tstyles.calcRow = this.table.element.querySelector(\".tabulator-row.tabulator-calcs\");\n\t\t\tstyles.firstRow = this.table.element.querySelector(\".tabulator-row:not(.tabulator-group):not(.tabulator-calcs)\");\n\t\t\tstyles.firstGroup = this.table.element.getElementsByClassName(\"tabulator-group\")[0];\n\t\t\t\n\t\t\tif(styles.firstRow){\n\t\t\t\tstyles.styleCells = styles.firstRow.getElementsByClassName(\"tabulator-cell\");\n\t\t\t\tstyles.firstCell = styles.styleCells[0];\n\t\t\t\tstyles.lastCell = styles.styleCells[styles.styleCells.length - 1];\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn styles;\n\t}\n\t\n\tgenerateHeaderElement(row, setup, styles){\n\t\tvar rowEl = document.createElement(\"tr\");\n\t\t\n\t\trow.columns.forEach((column) => {\n\t\t\tif(column){\n\t\t\t\tvar cellEl = document.createElement(\"th\");\n\t\t\t\tvar classNames = column.component._column.definition.cssClass ? column.component._column.definition.cssClass.split(\" \") : [];\n\t\t\t\t\n\t\t\t\tcellEl.colSpan = column.width;\n\t\t\t\tcellEl.rowSpan = column.height;\n\t\t\t\t\n\t\t\t\tcellEl.innerHTML = column.value;\n\t\t\t\t\n\t\t\t\tif(this.cloneTableStyle){\n\t\t\t\t\tcellEl.style.boxSizing = \"border-box\";\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tclassNames.forEach(function(className) {\n\t\t\t\t\tcellEl.classList.add(className);\n\t\t\t\t});\n\t\t\t\t\n\t\t\t\tthis.mapElementStyles(column.component.getElement(), cellEl, [\"text-align\", \"border-top\", \"border-left\", \"border-right\", \"border-bottom\", \"background-color\", \"color\", \"font-weight\", \"font-family\", \"font-size\"]);\n\t\t\t\tthis.mapElementStyles(column.component._column.contentElement, cellEl, [\"padding-top\", \"padding-left\", \"padding-right\", \"padding-bottom\"]);\n\t\t\t\t\n\t\t\t\tif(column.component._column.visible){\n\t\t\t\t\tthis.mapElementStyles(column.component.getElement(), cellEl, [\"width\"]);\n\t\t\t\t}else {\n\t\t\t\t\tif(column.component._column.definition.width){\n\t\t\t\t\t\tcellEl.style.width = column.component._column.definition.width + \"px\";\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tif(column.component._column.parent){\n\t\t\t\t\tthis.mapElementStyles(column.component._column.parent.groupElement, cellEl, [\"border-top\"]);\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\trowEl.appendChild(cellEl);\n\t\t\t}\n\t\t});\n\t\t\n\t\treturn rowEl;\n\t}\n\t\n\tgenerateGroupElement(row, setup, styles){\n\t\t\n\t\tvar rowEl = document.createElement(\"tr\"),\n\t\tcellEl = document.createElement(\"td\"),\n\t\tgroup = row.columns[0];\n\t\t\n\t\trowEl.classList.add(\"tabulator-print-table-row\");\n\t\t\n\t\tif(setup.groupHeader && setup.groupHeader[row.indent]){\n\t\t\tgroup.value = setup.groupHeader[row.indent](group.value, row.component._group.getRowCount(), row.component._group.getData(), row.component);\n\t\t}else {\n\t\t\tif(setup.groupHeader !== false){\n\t\t\t\tgroup.value = row.component._group.generator(group.value, row.component._group.getRowCount(), row.component._group.getData(), row.component);\n\t\t\t}\n\t\t}\n\t\t\n\t\tcellEl.colSpan = group.width;\n\t\tcellEl.innerHTML = group.value;\n\t\t\n\t\trowEl.classList.add(\"tabulator-print-table-group\");\n\t\trowEl.classList.add(\"tabulator-group-level-\" + row.indent);\n\t\t\n\t\tif(group.component.isVisible()){\n\t\t\trowEl.classList.add(\"tabulator-group-visible\");\n\t\t}\n\t\t\n\t\tthis.mapElementStyles(styles.firstGroup, rowEl, [\"border-top\", \"border-left\", \"border-right\", \"border-bottom\", \"color\", \"font-weight\", \"font-family\", \"font-size\", \"background-color\"]);\n\t\tthis.mapElementStyles(styles.firstGroup, cellEl, [\"padding-top\", \"padding-left\", \"padding-right\", \"padding-bottom\"]);\n\t\t\n\t\trowEl.appendChild(cellEl);\n\t\t\n\t\treturn rowEl;\n\t}\n\t\n\tgenerateCalcElement(row, setup, styles){\n\t\tvar rowEl = this.generateRowElement(row, setup, styles);\n\t\t\n\t\trowEl.classList.add(\"tabulator-print-table-calcs\");\n\t\tthis.mapElementStyles(styles.calcRow, rowEl, [\"border-top\", \"border-left\", \"border-right\", \"border-bottom\", \"color\", \"font-weight\", \"font-family\", \"font-size\", \"background-color\"]);\n\t\t\n\t\treturn rowEl;\n\t}\n\t\n\tgenerateRowElement(row, setup, styles){\n\t\tvar rowEl = document.createElement(\"tr\");\n\t\t\n\t\trowEl.classList.add(\"tabulator-print-table-row\");\n\t\t\n\t\trow.columns.forEach((col, i) => {\n\t\t\tif(col){\n\t\t\t\tvar cellEl = document.createElement(\"td\"),\n\t\t\t\tcolumn = col.component._column,\n\t\t\t\ttable =  this.table,\n\t\t\t\tindex = table.columnManager.findColumnIndex(column),\n\t\t\t\tvalue = col.value,\n\t\t\t\tcellStyle;\n\t\t\t\t\n\t\t\t\tvar cellWrapper = {\n\t\t\t\t\tmodules:{},\n\t\t\t\t\tgetValue:function(){\n\t\t\t\t\t\treturn value;\n\t\t\t\t\t},\n\t\t\t\t\tgetField:function(){\n\t\t\t\t\t\treturn column.definition.field;\n\t\t\t\t\t},\n\t\t\t\t\tgetElement:function(){\n\t\t\t\t\t\treturn cellEl;\n\t\t\t\t\t},\n\t\t\t\t\tgetType:function(){\n\t\t\t\t\t\treturn \"cell\";\n\t\t\t\t\t},\n\t\t\t\t\tgetColumn:function(){\n\t\t\t\t\t\treturn column.getComponent();\n\t\t\t\t\t},\n\t\t\t\t\tgetData:function(){\n\t\t\t\t\t\treturn row.component.getData();\n\t\t\t\t\t},\n\t\t\t\t\tgetRow:function(){\n\t\t\t\t\t\treturn row.component;\n\t\t\t\t\t},\n\t\t\t\t\tgetTable:function(){\n\t\t\t\t\t\treturn table;\n\t\t\t\t\t},\n\t\t\t\t\tgetComponent:function(){\n\t\t\t\t\t\treturn cellWrapper;\n\t\t\t\t\t},\n\t\t\t\t\tcolumn:column,\n\t\t\t\t};\n\t\t\t\t\n\t\t\t\tvar classNames = column.definition.cssClass ? column.definition.cssClass.split(\" \") : [];\n\t\t\t\t\n\t\t\t\tclassNames.forEach(function(className) {\n\t\t\t\t\tcellEl.classList.add(className);\n\t\t\t\t});\n\t\t\t\t\n\t\t\t\tif(this.table.modExists(\"format\") && this.config.formatCells !== false){\n\t\t\t\t\tvalue = this.table.modules.format.formatExportValue(cellWrapper, this.colVisProp);\n\t\t\t\t}else {\n\t\t\t\t\tswitch(typeof value){\n\t\t\t\t\t\tcase \"object\":\n\t\t\t\t\t\t\tvalue = value !== null ? JSON.stringify(value) : \"\";\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\n\t\t\t\t\t\tcase \"undefined\":\n\t\t\t\t\t\t\tvalue = \"\";\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tif(value instanceof Node){\n\t\t\t\t\tcellEl.appendChild(value);\n\t\t\t\t}else {\n\t\t\t\t\tcellEl.innerHTML = value;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tcellStyle = styles.styleCells && styles.styleCells[index] ? styles.styleCells[index] : styles.firstCell;\n\t\t\t\t\n\t\t\t\tif(cellStyle){\n\t\t\t\t\tthis.mapElementStyles(cellStyle, cellEl, [\"padding-top\", \"padding-left\", \"padding-right\", \"padding-bottom\", \"border-top\", \"border-left\", \"border-right\", \"border-bottom\", \"color\", \"font-weight\", \"font-family\", \"font-size\", \"text-align\"]);\n\t\t\t\t\t\n\t\t\t\t\tif(column.definition.align){\n\t\t\t\t\t\tcellEl.style.textAlign = column.definition.align;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tif(this.table.options.dataTree && this.config.dataTree !== false){\n\t\t\t\t\tif((setup.treeElementField && setup.treeElementField == column.field) || (!setup.treeElementField && i == 0)){\n\t\t\t\t\t\tif(row.component._row.modules.dataTree.controlEl){\n\t\t\t\t\t\t\tcellEl.insertBefore(row.component._row.modules.dataTree.controlEl.cloneNode(true), cellEl.firstChild);\n\t\t\t\t\t\t}\n\t\t\t\t\t\tif(row.component._row.modules.dataTree.branchEl){\n\t\t\t\t\t\t\tcellEl.insertBefore(row.component._row.modules.dataTree.branchEl.cloneNode(true), cellEl.firstChild);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\trowEl.appendChild(cellEl);\n\t\t\t\t\n\t\t\t\tif(cellWrapper.modules.format && cellWrapper.modules.format.renderedCallback){\n\t\t\t\t\tcellWrapper.modules.format.renderedCallback();\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\t\t\n\t\tif(setup.rowFormatter && row.type === \"row\" && this.config.formatCells !== false){\n\t\t\tlet formatComponent = Object.assign(row.component);\n\n\t\t\tformatComponent.getElement = function(){return rowEl;};\n\n\t\t\tsetup.rowFormatter(row.component);\n\t\t}\n\t\t\n\t\treturn rowEl;\n\t}\n\t\n\tgenerateHTMLTable(list){\n\t\tvar holder = document.createElement(\"div\");\n\t\t\n\t\tholder.appendChild(this.generateTableElement(list));\n\t\t\n\t\treturn holder.innerHTML;\n\t}\n\t\n\tgetHtml(visible, style, config, colVisProp){\n\t\tvar list = this.generateExportList(config || this.table.options.htmlOutputConfig, style, visible, colVisProp || \"htmlOutput\");\n\t\t\n\t\treturn this.generateHTMLTable(list);\n\t}\n\t\n\tmapElementStyles(from, to, props){\n\t\tif(this.cloneTableStyle && from && to){\n\t\t\t\n\t\t\tvar lookup = {\n\t\t\t\t\"background-color\" : \"backgroundColor\",\n\t\t\t\t\"color\" : \"fontColor\",\n\t\t\t\t\"width\" : \"width\",\n\t\t\t\t\"font-weight\" : \"fontWeight\",\n\t\t\t\t\"font-family\" : \"fontFamily\",\n\t\t\t\t\"font-size\" : \"fontSize\",\n\t\t\t\t\"text-align\" : \"textAlign\",\n\t\t\t\t\"border-top\" : \"borderTop\",\n\t\t\t\t\"border-left\" : \"borderLeft\",\n\t\t\t\t\"border-right\" : \"borderRight\",\n\t\t\t\t\"border-bottom\" : \"borderBottom\",\n\t\t\t\t\"padding-top\" : \"paddingTop\",\n\t\t\t\t\"padding-left\" : \"paddingLeft\",\n\t\t\t\t\"padding-right\" : \"paddingRight\",\n\t\t\t\t\"padding-bottom\" : \"paddingBottom\",\n\t\t\t};\n\t\t\t\n\t\t\tif(window.getComputedStyle){\n\t\t\t\tvar fromStyle = window.getComputedStyle(from);\n\t\t\t\t\n\t\t\t\tprops.forEach(function(prop){\n\t\t\t\t\tif(!to.style[lookup[prop]]){\n\t\t\t\t\t\tto.style[lookup[prop]] = fromStyle.getPropertyValue(prop);\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t}\n\t\t}\n\t}\n}\n\nExport.moduleName = \"export\";\n\nvar defaultFilters = {\n\n\t//equal to\n\t\"=\":function(filterVal, rowVal, rowData, filterParams){\n\t\treturn rowVal == filterVal ? true : false;\n\t},\n\n\t//less than\n\t\"<\":function(filterVal, rowVal, rowData, filterParams){\n\t\treturn rowVal < filterVal ? true : false;\n\t},\n\n\t//less than or equal to\n\t\"<=\":function(filterVal, rowVal, rowData, filterParams){\n\t\treturn rowVal <= filterVal ? true : false;\n\t},\n\n\t//greater than\n\t\">\":function(filterVal, rowVal, rowData, filterParams){\n\t\treturn rowVal > filterVal ? true : false;\n\t},\n\n\t//greater than or equal to\n\t\">=\":function(filterVal, rowVal, rowData, filterParams){\n\t\treturn rowVal >= filterVal ? true : false;\n\t},\n\n\t//not equal to\n\t\"!=\":function(filterVal, rowVal, rowData, filterParams){\n\t\treturn rowVal != filterVal ? true : false;\n\t},\n\n\t\"regex\":function(filterVal, rowVal, rowData, filterParams){\n\n\t\tif(typeof filterVal == \"string\"){\n\t\t\tfilterVal = new RegExp(filterVal);\n\t\t}\n\n\t\treturn filterVal.test(rowVal);\n\t},\n\n\t//contains the string\n\t\"like\":function(filterVal, rowVal, rowData, filterParams){\n\t\tif(filterVal === null || typeof filterVal === \"undefined\"){\n\t\t\treturn rowVal === filterVal ? true : false;\n\t\t}else {\n\t\t\tif(typeof rowVal !== 'undefined' && rowVal !== null){\n\t\t\t\treturn String(rowVal).toLowerCase().indexOf(filterVal.toLowerCase()) > -1;\n\t\t\t}\n\t\t\telse {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t},\n\n\t//contains the keywords\n\t\"keywords\":function(filterVal, rowVal, rowData, filterParams){\n\t\tvar keywords = filterVal.toLowerCase().split(typeof filterParams.separator === \"undefined\" ? \" \" : filterParams.separator),\n\t\tvalue = String(rowVal === null || typeof rowVal === \"undefined\" ? \"\" : rowVal).toLowerCase(),\n\t\tmatches = [];\n\n\t\tkeywords.forEach((keyword) =>{\n\t\t\tif(value.includes(keyword)){\n\t\t\t\tmatches.push(true);\n\t\t\t}\n\t\t});\n\n\t\treturn filterParams.matchAll ? matches.length === keywords.length : !!matches.length;\n\t},\n\n\t//starts with the string\n\t\"starts\":function(filterVal, rowVal, rowData, filterParams){\n\t\tif(filterVal === null || typeof filterVal === \"undefined\"){\n\t\t\treturn rowVal === filterVal ? true : false;\n\t\t}else {\n\t\t\tif(typeof rowVal !== 'undefined' && rowVal !== null){\n\t\t\t\treturn String(rowVal).toLowerCase().startsWith(filterVal.toLowerCase());\n\t\t\t}\n\t\t\telse {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t},\n\n\t//ends with the string\n\t\"ends\":function(filterVal, rowVal, rowData, filterParams){\n\t\tif(filterVal === null || typeof filterVal === \"undefined\"){\n\t\t\treturn rowVal === filterVal ? true : false;\n\t\t}else {\n\t\t\tif(typeof rowVal !== 'undefined' && rowVal !== null){\n\t\t\t\treturn String(rowVal).toLowerCase().endsWith(filterVal.toLowerCase());\n\t\t\t}\n\t\t\telse {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t},\n\n\t//in array\n\t\"in\":function(filterVal, rowVal, rowData, filterParams){\n\t\tif(Array.isArray(filterVal)){\n\t\t\treturn filterVal.length ? filterVal.indexOf(rowVal) > -1 : true;\n\t\t}else {\n\t\t\tconsole.warn(\"Filter Error - filter value is not an array:\", filterVal);\n\t\t\treturn false;\n\t\t}\n\t},\n};\n\nclass Filter extends Module{\n\n\tconstructor(table){\n\t\tsuper(table);\n\n\t\tthis.filterList = []; //hold filter list\n\t\tthis.headerFilters = {}; //hold column filters\n\t\tthis.headerFilterColumns = []; //hold columns that use header filters\n\n\t\tthis.prevHeaderFilterChangeCheck = \"\";\n\t\tthis.prevHeaderFilterChangeCheck = \"{}\";\n\n\t\tthis.changed = false; //has filtering changed since last render\n\t\tthis.tableInitialized = false;\n\n\t\tthis.registerTableOption(\"filterMode\", \"local\"); //local or remote filtering\n\n\t\tthis.registerTableOption(\"initialFilter\", false); //initial filtering criteria\n\t\tthis.registerTableOption(\"initialHeaderFilter\", false); //initial header filtering criteria\n\t\tthis.registerTableOption(\"headerFilterLiveFilterDelay\", 300); //delay before updating column after user types in header filter\n\t\tthis.registerTableOption(\"placeholderHeaderFilter\", false); //placeholder when header filter is empty\n\n\t\tthis.registerColumnOption(\"headerFilter\");\n\t\tthis.registerColumnOption(\"headerFilterPlaceholder\");\n\t\tthis.registerColumnOption(\"headerFilterParams\");\n\t\tthis.registerColumnOption(\"headerFilterEmptyCheck\");\n\t\tthis.registerColumnOption(\"headerFilterFunc\");\n\t\tthis.registerColumnOption(\"headerFilterFuncParams\");\n\t\tthis.registerColumnOption(\"headerFilterLiveFilter\");\n\n\t\tthis.registerTableFunction(\"searchRows\", this.searchRows.bind(this));\n\t\tthis.registerTableFunction(\"searchData\", this.searchData.bind(this));\n\n\t\tthis.registerTableFunction(\"setFilter\", this.userSetFilter.bind(this));\n\t\tthis.registerTableFunction(\"refreshFilter\", this.userRefreshFilter.bind(this));\n\t\tthis.registerTableFunction(\"addFilter\", this.userAddFilter.bind(this));\n\t\tthis.registerTableFunction(\"getFilters\", this.getFilters.bind(this));\n\t\tthis.registerTableFunction(\"setHeaderFilterFocus\", this.userSetHeaderFilterFocus.bind(this));\n\t\tthis.registerTableFunction(\"getHeaderFilterValue\", this.userGetHeaderFilterValue.bind(this));\n\t\tthis.registerTableFunction(\"setHeaderFilterValue\", this.userSetHeaderFilterValue.bind(this));\n\t\tthis.registerTableFunction(\"getHeaderFilters\", this.getHeaderFilters.bind(this));\n\t\tthis.registerTableFunction(\"removeFilter\", this.userRemoveFilter.bind(this));\n\t\tthis.registerTableFunction(\"clearFilter\", this.userClearFilter.bind(this));\n\t\tthis.registerTableFunction(\"clearHeaderFilter\", this.userClearHeaderFilter.bind(this));\n\n\t\tthis.registerComponentFunction(\"column\", \"headerFilterFocus\", this.setHeaderFilterFocus.bind(this));\n\t\tthis.registerComponentFunction(\"column\", \"reloadHeaderFilter\", this.reloadHeaderFilter.bind(this));\n\t\tthis.registerComponentFunction(\"column\", \"getHeaderFilterValue\", this.getHeaderFilterValue.bind(this));\n\t\tthis.registerComponentFunction(\"column\", \"setHeaderFilterValue\", this.setHeaderFilterValue.bind(this));\n\t}\n\n\tinitialize(){\n\t\tthis.subscribe(\"column-init\", this.initializeColumnHeaderFilter.bind(this));\n\t\tthis.subscribe(\"column-width-fit-before\", this.hideHeaderFilterElements.bind(this));\n\t\tthis.subscribe(\"column-width-fit-after\", this.showHeaderFilterElements.bind(this));\n\t\tthis.subscribe(\"table-built\", this.tableBuilt.bind(this));\n\t\tthis.subscribe(\"placeholder\", this.generatePlaceholder.bind(this));\n\n\t\tif(this.table.options.filterMode === \"remote\"){\n\t\t\tthis.subscribe(\"data-params\", this.remoteFilterParams.bind(this));\n\t\t}\n\n\t\tthis.registerDataHandler(this.filter.bind(this), 10);\n\t}\n\n\ttableBuilt(){\n\t\tif(this.table.options.initialFilter){\n\t\t\tthis.setFilter(this.table.options.initialFilter);\n\t\t}\n\n\t\tif(this.table.options.initialHeaderFilter){\n\t\t\tthis.table.options.initialHeaderFilter.forEach((item) => {\n\n\t\t\t\tvar column = this.table.columnManager.findColumn(item.field);\n\n\t\t\t\tif(column){\n\t\t\t\t\tthis.setHeaderFilterValue(column, item.value);\n\t\t\t\t}else {\n\t\t\t\t\tconsole.warn(\"Column Filter Error - No matching column found:\", item.field);\n\t\t\t\t\treturn false;\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\n\t\tthis.tableInitialized = true;\n\t}\n\n\tremoteFilterParams(data, config, silent, params){\n\t\tparams.filter = this.getFilters(true, true);\n\t\treturn params;\n\t}\n\n\tgeneratePlaceholder(text){\n\t\tif(this.table.options.placeholderHeaderFilter && Object.keys(this.headerFilters).length){\n\t\t\treturn this.table.options.placeholderHeaderFilter;\n\t\t}\n\t}\n\n\t///////////////////////////////////\n\t///////// Table Functions /////////\n\t///////////////////////////////////\n\n\t//set standard filters\n\tuserSetFilter(field, type, value, params){\n\t\tthis.setFilter(field, type, value, params);\n\t\tthis.refreshFilter();\n\t}\n\n\t//set standard filters\n\tuserRefreshFilter(){\n\t\tthis.refreshFilter();\n\t}\n\n\t//add filter to array\n\tuserAddFilter(field, type, value, params){\n\t\tthis.addFilter(field, type, value, params);\n\t\tthis.refreshFilter();\n\t}\n\n\tuserSetHeaderFilterFocus(field){\n\t\tvar column = this.table.columnManager.findColumn(field);\n\n\t\tif(column){\n\t\t\tthis.setHeaderFilterFocus(column);\n\t\t}else {\n\t\t\tconsole.warn(\"Column Filter Focus Error - No matching column found:\", field);\n\t\t\treturn false;\n\t\t}\n\t}\n\n\tuserGetHeaderFilterValue(field) {\n\t\tvar column = this.table.columnManager.findColumn(field);\n\n\t\tif(column){\n\t\t\treturn this.getHeaderFilterValue(column);\n\t\t}else {\n\t\t\tconsole.warn(\"Column Filter Error - No matching column found:\", field);\n\t\t}\n\t}\n\n\tuserSetHeaderFilterValue(field, value){\n\t\tvar column = this.table.columnManager.findColumn(field);\n\n\t\tif(column){\n\t\t\tthis.setHeaderFilterValue(column, value);\n\t\t}else {\n\t\t\tconsole.warn(\"Column Filter Error - No matching column found:\", field);\n\t\t\treturn false;\n\t\t}\n\t}\n\n\t//remove filter from array\n\tuserRemoveFilter(field, type, value){\n\t\tthis.removeFilter(field, type, value);\n\t\tthis.refreshFilter();\n\t}\n\n\t//clear filters\n\tuserClearFilter(all){\n\t\tthis.clearFilter(all);\n\t\tthis.refreshFilter();\n\t}\n\n\t//clear header filters\n\tuserClearHeaderFilter(){\n\t\tthis.clearHeaderFilter();\n\t\tthis.refreshFilter();\n\t}\n\n\n\t//search for specific row components\n\tsearchRows(field, type, value){\n\t\treturn this.search(\"rows\", field, type, value);\n\t}\n\n\t//search for specific data\n\tsearchData(field, type, value){\n\t\treturn this.search(\"data\", field, type, value);\n\t}\n\n\t///////////////////////////////////\n\t///////// Internal Logic //////////\n\t///////////////////////////////////\n\n\tinitializeColumnHeaderFilter(column){\n\t\tvar def = column.definition;\n\n\t\tif(def.headerFilter){\n\t\t\tthis.initializeColumn(column);\n\t\t}\n\t}\n\n\t//initialize column header filter\n\tinitializeColumn(column, value){\n\t\tvar self = this,\n\t\tfield = column.getField();\n\n\t\t//handle successfully value change\n\t\tfunction success(value){\n\t\t\tvar filterType = (column.modules.filter.tagType == \"input\" && column.modules.filter.attrType == \"text\") || column.modules.filter.tagType == \"textarea\" ? \"partial\" : \"match\",\n\t\t\ttype = \"\",\n\t\t\tfilterChangeCheck = \"\",\n\t\t\tfilterFunc;\n\n\t\t\tif(typeof column.modules.filter.prevSuccess === \"undefined\" || column.modules.filter.prevSuccess !== value){\n\n\t\t\t\tcolumn.modules.filter.prevSuccess = value;\n\n\t\t\t\tif(!column.modules.filter.emptyFunc(value)){\n\t\t\t\t\tcolumn.modules.filter.value = value;\n\n\t\t\t\t\tswitch(typeof column.definition.headerFilterFunc){\n\t\t\t\t\t\tcase \"string\":\n\t\t\t\t\t\t\tif(Filter.filters[column.definition.headerFilterFunc]){\n\t\t\t\t\t\t\t\ttype = column.definition.headerFilterFunc;\n\t\t\t\t\t\t\t\tfilterFunc = function(data){\n\t\t\t\t\t\t\t\t\tvar params = column.definition.headerFilterFuncParams || {};\n\t\t\t\t\t\t\t\t\tvar fieldVal = column.getFieldValue(data);\n\n\t\t\t\t\t\t\t\t\tparams = typeof params === \"function\" ? params(value, fieldVal, data) : params;\n\n\t\t\t\t\t\t\t\t\treturn Filter.filters[column.definition.headerFilterFunc](value, fieldVal, data, params);\n\t\t\t\t\t\t\t\t};\n\t\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\t\tconsole.warn(\"Header Filter Error - Matching filter function not found: \", column.definition.headerFilterFunc);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tbreak;\n\n\t\t\t\t\t\tcase \"function\":\n\t\t\t\t\t\t\tfilterFunc = function(data){\n\t\t\t\t\t\t\t\tvar params = column.definition.headerFilterFuncParams || {};\n\t\t\t\t\t\t\t\tvar fieldVal = column.getFieldValue(data);\n\n\t\t\t\t\t\t\t\tparams = typeof params === \"function\" ? params(value, fieldVal, data) : params;\n\n\t\t\t\t\t\t\t\treturn column.definition.headerFilterFunc(value, fieldVal, data, params);\n\t\t\t\t\t\t\t};\n\n\t\t\t\t\t\t\ttype = filterFunc;\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\n\t\t\t\t\tif(!filterFunc){\n\t\t\t\t\t\tswitch(filterType){\n\t\t\t\t\t\t\tcase \"partial\":\n\t\t\t\t\t\t\t\tfilterFunc = function(data){\n\t\t\t\t\t\t\t\t\tvar colVal = column.getFieldValue(data);\n\n\t\t\t\t\t\t\t\t\tif(typeof colVal !== 'undefined' && colVal !== null){\n\t\t\t\t\t\t\t\t\t\treturn String(colVal).toLowerCase().indexOf(String(value).toLowerCase()) > -1;\n\t\t\t\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\t\t\t\treturn false;\n\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t};\n\t\t\t\t\t\t\t\ttype = \"like\";\n\t\t\t\t\t\t\t\tbreak;\n\n\t\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\t\tfilterFunc = function(data){\n\t\t\t\t\t\t\t\t\treturn column.getFieldValue(data) == value;\n\t\t\t\t\t\t\t\t};\n\t\t\t\t\t\t\t\ttype = \"=\";\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\tself.headerFilters[field] = {value:value, func:filterFunc, type:type};\n\t\t\t\t}else {\n\t\t\t\t\tdelete self.headerFilters[field];\n\t\t\t\t}\n\n\t\t\t\tcolumn.modules.filter.value = value;\n\n\t\t\t\tfilterChangeCheck = JSON.stringify(self.headerFilters);\n\n\t\t\t\tif(self.prevHeaderFilterChangeCheck !== filterChangeCheck){\n\t\t\t\t\tself.prevHeaderFilterChangeCheck = filterChangeCheck;\n\n\t\t\t\t\tself.trackChanges();\n\t\t\t\t\tself.refreshFilter();\n\t\t\t\t}\n\t\t\t}\n\n\t\t\treturn true;\n\t\t}\n\n\t\tcolumn.modules.filter = {\n\t\t\tsuccess:success,\n\t\t\tattrType:false,\n\t\t\ttagType:false,\n\t\t\temptyFunc:false,\n\t\t};\n\n\t\tthis.generateHeaderFilterElement(column);\n\t}\n\n\tgenerateHeaderFilterElement(column, initialValue, reinitialize){\n\t\tvar self = this,\n\t\tsuccess = column.modules.filter.success,\n\t\tfield = column.getField(),\n\t\tfilterElement, editor, editorElement, cellWrapper, typingTimer, searchTrigger, params, onRenderedCallback;\n\n\t\tcolumn.modules.filter.value = initialValue;\n\n\t\t//handle aborted edit\n\t\tfunction cancel(){}\n\n\t\tfunction onRendered(callback){\n\t\t\tonRenderedCallback = callback;\n\t\t}\n\n\t\tif(column.modules.filter.headerElement && column.modules.filter.headerElement.parentNode){\n\t\t\tcolumn.contentElement.removeChild(column.modules.filter.headerElement.parentNode);\n\t\t}\n\n\t\tif(field){\n\n\t\t\t//set empty value function\n\t\t\tcolumn.modules.filter.emptyFunc = column.definition.headerFilterEmptyCheck || function(value){\n\t\t\t\treturn !value && value !== 0;\n\t\t\t};\n\n\t\t\tfilterElement = document.createElement(\"div\");\n\t\t\tfilterElement.classList.add(\"tabulator-header-filter\");\n\n\t\t\t//set column editor\n\t\t\tswitch(typeof column.definition.headerFilter){\n\t\t\t\tcase \"string\":\n\t\t\t\t\tif(self.table.modules.edit.editors[column.definition.headerFilter]){\n\t\t\t\t\t\teditor = self.table.modules.edit.editors[column.definition.headerFilter];\n\n\t\t\t\t\t\tif((column.definition.headerFilter === \"tick\" || column.definition.headerFilter === \"tickCross\") && !column.definition.headerFilterEmptyCheck){\n\t\t\t\t\t\t\tcolumn.modules.filter.emptyFunc = function(value){\n\t\t\t\t\t\t\t\treturn value !== true && value !== false;\n\t\t\t\t\t\t\t};\n\t\t\t\t\t\t}\n\t\t\t\t\t}else {\n\t\t\t\t\t\tconsole.warn(\"Filter Error - Cannot build header filter, No such editor found: \", column.definition.editor);\n\t\t\t\t\t}\n\t\t\t\t\tbreak;\n\n\t\t\t\tcase \"function\":\n\t\t\t\t\teditor = column.definition.headerFilter;\n\t\t\t\t\tbreak;\n\n\t\t\t\tcase \"boolean\":\n\t\t\t\t\tif(column.modules.edit && column.modules.edit.editor){\n\t\t\t\t\t\teditor = column.modules.edit.editor;\n\t\t\t\t\t}else {\n\t\t\t\t\t\tif(column.definition.formatter && self.table.modules.edit.editors[column.definition.formatter]){\n\t\t\t\t\t\t\teditor = self.table.modules.edit.editors[column.definition.formatter];\n\n\t\t\t\t\t\t\tif((column.definition.formatter === \"tick\" || column.definition.formatter === \"tickCross\") && !column.definition.headerFilterEmptyCheck){\n\t\t\t\t\t\t\t\tcolumn.modules.filter.emptyFunc = function(value){\n\t\t\t\t\t\t\t\t\treturn value !== true && value !== false;\n\t\t\t\t\t\t\t\t};\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\teditor = self.table.modules.edit.editors[\"input\"];\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\tif(editor){\n\n\t\t\t\tcellWrapper = {\n\t\t\t\t\tgetValue:function(){\n\t\t\t\t\t\treturn typeof initialValue !== \"undefined\" ? initialValue : \"\";\n\t\t\t\t\t},\n\t\t\t\t\tgetField:function(){\n\t\t\t\t\t\treturn column.definition.field;\n\t\t\t\t\t},\n\t\t\t\t\tgetElement:function(){\n\t\t\t\t\t\treturn filterElement;\n\t\t\t\t\t},\n\t\t\t\t\tgetColumn:function(){\n\t\t\t\t\t\treturn column.getComponent();\n\t\t\t\t\t},\n\t\t\t\t\tgetTable:() => {\n\t\t\t\t\t\treturn this.table;\n\t\t\t\t\t},\n\t\t\t\t\tgetType:() => {\n\t\t\t\t\t\treturn \"header\";\n\t\t\t\t\t},\n\t\t\t\t\tgetRow:function(){\n\t\t\t\t\t\treturn {\n\t\t\t\t\t\t\tnormalizeHeight:function(){\n\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t};\n\t\t\t\t\t}\n\t\t\t\t};\n\n\t\t\t\tparams = column.definition.headerFilterParams || {};\n\n\t\t\t\tparams = typeof params === \"function\" ? params.call(self.table, cellWrapper) : params;\n\n\t\t\t\teditorElement = editor.call(this.table.modules.edit, cellWrapper, onRendered, success, cancel, params);\n\n\t\t\t\tif(!editorElement){\n\t\t\t\t\tconsole.warn(\"Filter Error - Cannot add filter to \" + field + \" column, editor returned a value of false\");\n\t\t\t\t\treturn;\n\t\t\t\t}\n\n\t\t\t\tif(!(editorElement instanceof Node)){\n\t\t\t\t\tconsole.warn(\"Filter Error - Cannot add filter to \" + field + \" column, editor should return an instance of Node, the editor returned:\", editorElement);\n\t\t\t\t\treturn;\n\t\t\t\t}\n\n\t\t\t\t//set Placeholder Text\n\t\t\t\tself.langBind(\"headerFilters|columns|\" + column.definition.field, function(value){\n\t\t\t\t\teditorElement.setAttribute(\"placeholder\", typeof value !== \"undefined\" && value ? value : (column.definition.headerFilterPlaceholder || self.langText(\"headerFilters|default\")));\n\t\t\t\t});\n\n\t\t\t\t//focus on element on click\n\t\t\t\teditorElement.addEventListener(\"click\", function(e){\n\t\t\t\t\te.stopPropagation();\n\t\t\t\t\teditorElement.focus();\n\t\t\t\t});\n\n\t\t\t\teditorElement.addEventListener(\"focus\", (e) => {\n\t\t\t\t\tvar left = this.table.columnManager.contentsElement.scrollLeft;\n\n\t\t\t\t\tvar headerPos = this.table.rowManager.element.scrollLeft;\n\n\t\t\t\t\tif(left !== headerPos){\n\t\t\t\t\t\tthis.table.rowManager.scrollHorizontal(left);\n\t\t\t\t\t\tthis.table.columnManager.scrollHorizontal(left);\n\t\t\t\t\t}\n\t\t\t\t});\n\n\t\t\t\t//live update filters as user types\n\t\t\t\ttypingTimer = false;\n\n\t\t\t\tsearchTrigger = function(e){\n\t\t\t\t\tif(typingTimer){\n\t\t\t\t\t\tclearTimeout(typingTimer);\n\t\t\t\t\t}\n\n\t\t\t\t\ttypingTimer = setTimeout(function(){\n\t\t\t\t\t\tsuccess(editorElement.value);\n\t\t\t\t\t},self.table.options.headerFilterLiveFilterDelay);\n\t\t\t\t};\n\n\t\t\t\tcolumn.modules.filter.headerElement = editorElement;\n\t\t\t\tcolumn.modules.filter.attrType = editorElement.hasAttribute(\"type\") ? editorElement.getAttribute(\"type\").toLowerCase() : \"\" ;\n\t\t\t\tcolumn.modules.filter.tagType = editorElement.tagName.toLowerCase();\n\n\t\t\t\tif(column.definition.headerFilterLiveFilter !== false){\n\n\t\t\t\t\tif (\n\t\t\t\t\t\t!(\n\t\t\t\t\t\t\tcolumn.definition.headerFilter === 'autocomplete' ||\n\t\t\t\t\t\t\tcolumn.definition.headerFilter === 'tickCross' ||\n\t\t\t\t\t\t\t((column.definition.editor === 'autocomplete' ||\n\t\t\t\t\t\t\t\tcolumn.definition.editor === 'tickCross') &&\n\t\t\t\t\t\t\tcolumn.definition.headerFilter === true)\n\t\t\t\t\t\t)\n\t\t\t\t\t) {\n\t\t\t\t\t\teditorElement.addEventListener(\"keyup\", searchTrigger);\n\t\t\t\t\t\teditorElement.addEventListener(\"search\", searchTrigger);\n\n\n\t\t\t\t\t\t//update number filtered columns on change\n\t\t\t\t\t\tif(column.modules.filter.attrType == \"number\"){\n\t\t\t\t\t\t\teditorElement.addEventListener(\"change\", function(e){\n\t\t\t\t\t\t\t\tsuccess(editorElement.value);\n\t\t\t\t\t\t\t});\n\t\t\t\t\t\t}\n\n\t\t\t\t\t\t//change text inputs to search inputs to allow for clearing of field\n\t\t\t\t\t\tif(column.modules.filter.attrType == \"text\" && this.table.browser !== \"ie\"){\n\t\t\t\t\t\t\teditorElement.setAttribute(\"type\", \"search\");\n\t\t\t\t\t\t// editorElement.off(\"change blur\"); //prevent blur from triggering filter and preventing selection click\n\t\t\t\t\t\t}\n\n\t\t\t\t\t}\n\n\t\t\t\t\t//prevent input and select elements from propagating click to column sorters etc\n\t\t\t\t\tif(column.modules.filter.tagType == \"input\" || column.modules.filter.tagType == \"select\" || column.modules.filter.tagType == \"textarea\"){\n\t\t\t\t\t\teditorElement.addEventListener(\"mousedown\",function(e){\n\t\t\t\t\t\t\te.stopPropagation();\n\t\t\t\t\t\t});\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\tfilterElement.appendChild(editorElement);\n\n\t\t\t\tcolumn.contentElement.appendChild(filterElement);\n\n\t\t\t\tif(!reinitialize){\n\t\t\t\t\tself.headerFilterColumns.push(column);\n\t\t\t\t}\n\n\t\t\t\tif(onRenderedCallback){\n\t\t\t\t\tonRenderedCallback();\n\t\t\t\t}\n\t\t\t}\n\t\t}else {\n\t\t\tconsole.warn(\"Filter Error - Cannot add header filter, column has no field set:\", column.definition.title);\n\t\t}\n\t}\n\n\t//hide all header filter elements (used to ensure correct column widths in \"fitData\" layout mode)\n\thideHeaderFilterElements(){\n\t\tthis.headerFilterColumns.forEach(function(column){\n\t\t\tif(column.modules.filter && column.modules.filter.headerElement){\n\t\t\t\tcolumn.modules.filter.headerElement.style.display = 'none';\n\t\t\t}\n\t\t});\n\t}\n\n\t//show all header filter elements (used to ensure correct column widths in \"fitData\" layout mode)\n\tshowHeaderFilterElements(){\n\t\tthis.headerFilterColumns.forEach(function(column){\n\t\t\tif(column.modules.filter && column.modules.filter.headerElement){\n\t\t\t\tcolumn.modules.filter.headerElement.style.display = '';\n\t\t\t}\n\t\t});\n\t}\n\n\t//programmatically set focus of header filter\n\tsetHeaderFilterFocus(column){\n\t\tif(column.modules.filter && column.modules.filter.headerElement){\n\t\t\tcolumn.modules.filter.headerElement.focus();\n\t\t}else {\n\t\t\tconsole.warn(\"Column Filter Focus Error - No header filter set on column:\", column.getField());\n\t\t}\n\t}\n\n\t//programmatically get value of header filter\n\tgetHeaderFilterValue(column){\n\t\tif(column.modules.filter && column.modules.filter.headerElement){\n\t\t\treturn column.modules.filter.value;\n\t\t} else {\n\t\t\tconsole.warn(\"Column Filter Error - No header filter set on column:\", column.getField());\n\t\t}\n\t}\n\n\t//programmatically set value of header filter\n\tsetHeaderFilterValue(column, value){\n\t\tif (column){\n\t\t\tif(column.modules.filter && column.modules.filter.headerElement){\n\t\t\t\tthis.generateHeaderFilterElement(column, value, true);\n\t\t\t\tcolumn.modules.filter.success(value);\n\t\t\t}else {\n\t\t\t\tconsole.warn(\"Column Filter Error - No header filter set on column:\", column.getField());\n\t\t\t}\n\t\t}\n\t}\n\n\treloadHeaderFilter(column){\n\t\tif (column){\n\t\t\tif(column.modules.filter && column.modules.filter.headerElement){\n\t\t\t\tthis.generateHeaderFilterElement(column, column.modules.filter.value, true);\n\t\t\t}else {\n\t\t\t\tconsole.warn(\"Column Filter Error - No header filter set on column:\", column.getField());\n\t\t\t}\n\t\t}\n\t}\n\n\trefreshFilter(){\n\t\tif(this.tableInitialized){\n\t\t\tif(this.table.options.filterMode === \"remote\"){\n\t\t\t\tthis.reloadData(null, false, false);\n\t\t\t}else {\n\t\t\t\tthis.refreshData(true);\n\t\t\t}\n\t\t}\n\n\t\t//TODO - Persist left position of row manager\n\t\t// left = this.scrollLeft;\n\t\t// this.scrollHorizontal(left);\n\t}\n\n\t//check if the filters has changed since last use\n\ttrackChanges(){\n\t\tthis.changed = true;\n\t\tthis.dispatch(\"filter-changed\");\n\t}\n\n\t//check if the filters has changed since last use\n\thasChanged(){\n\t\tvar changed = this.changed;\n\t\tthis.changed = false;\n\t\treturn changed;\n\t}\n\n\t//set standard filters\n\tsetFilter(field, type, value, params){\n\t\tthis.filterList = [];\n\n\t\tif(!Array.isArray(field)){\n\t\t\tfield = [{field:field, type:type, value:value, params:params}];\n\t\t}\n\n\t\tthis.addFilter(field);\n\t}\n\n\t//add filter to array\n\taddFilter(field, type, value, params){\n\t\tvar changed = false;\n\n\t\tif(!Array.isArray(field)){\n\t\t\tfield = [{field:field, type:type, value:value, params:params}];\n\t\t}\n\n\t\tfield.forEach((filter) => {\n\t\t\tfilter = this.findFilter(filter);\n\n\t\t\tif(filter){\n\t\t\t\tthis.filterList.push(filter);\n\t\t\t\tchanged = true;\n\t\t\t}\n\t\t});\n\n\t\tif(changed){\n\t\t\tthis.trackChanges();\n\t\t}\n\t}\n\n\tfindFilter(filter){\n\t\tvar column;\n\n\t\tif(Array.isArray(filter)){\n\t\t\treturn this.findSubFilters(filter);\n\t\t}\n\n\t\tvar filterFunc = false;\n\n\t\tif(typeof filter.field == \"function\"){\n\t\t\tfilterFunc = function(data){\n\t\t\t\treturn filter.field(data, filter.type || {});// pass params to custom filter function\n\t\t\t};\n\t\t}else {\n\n\t\t\tif(Filter.filters[filter.type]){\n\n\t\t\t\tcolumn = this.table.columnManager.getColumnByField(filter.field);\n\n\t\t\t\tif(column){\n\t\t\t\t\tfilterFunc = function(data){\n\t\t\t\t\t\treturn Filter.filters[filter.type](filter.value, column.getFieldValue(data), data, filter.params || {});\n\t\t\t\t\t};\n\t\t\t\t}else {\n\t\t\t\t\tfilterFunc = function(data){\n\t\t\t\t\t\treturn Filter.filters[filter.type](filter.value, data[filter.field], data, filter.params || {});\n\t\t\t\t\t};\n\t\t\t\t}\n\n\n\t\t\t}else {\n\t\t\t\tconsole.warn(\"Filter Error - No such filter type found, ignoring: \", filter.type);\n\t\t\t}\n\t\t}\n\n\t\tfilter.func = filterFunc;\n\n\t\treturn filter.func ? filter : false;\n\t}\n\n\tfindSubFilters(filters){\n\t\tvar output = [];\n\n\t\tfilters.forEach((filter) => {\n\t\t\tfilter = this.findFilter(filter);\n\n\t\t\tif(filter){\n\t\t\t\toutput.push(filter);\n\t\t\t}\n\t\t});\n\n\t\treturn output.length ? output : false;\n\t}\n\n\t//get all filters\n\tgetFilters(all, ajax){\n\t\tvar output = [];\n\n\t\tif(all){\n\t\t\toutput = this.getHeaderFilters();\n\t\t}\n\n\t\tif(ajax){\n\t\t\toutput.forEach(function(item){\n\t\t\t\tif(typeof item.type == \"function\"){\n\t\t\t\t\titem.type = \"function\";\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\n\t\toutput = output.concat(this.filtersToArray(this.filterList, ajax));\n\n\t\treturn output;\n\t}\n\n\t//filter to Object\n\tfiltersToArray(filterList, ajax){\n\t\tvar output = [];\n\n\t\tfilterList.forEach((filter) => {\n\t\t\tvar item;\n\n\t\t\tif(Array.isArray(filter)){\n\t\t\t\toutput.push(this.filtersToArray(filter, ajax));\n\t\t\t}else {\n\t\t\t\titem = {field:filter.field, type:filter.type, value:filter.value};\n\n\t\t\t\tif(ajax){\n\t\t\t\t\tif(typeof item.type == \"function\"){\n\t\t\t\t\t\titem.type = \"function\";\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\toutput.push(item);\n\t\t\t}\n\t\t});\n\n\t\treturn output;\n\t}\n\n\t//get all filters\n\tgetHeaderFilters(){\n\t\tvar output = [];\n\n\t\tfor(var key in this.headerFilters){\n\t\t\toutput.push({field:key, type:this.headerFilters[key].type, value:this.headerFilters[key].value});\n\t\t}\n\n\t\treturn output;\n\t}\n\n\t//remove filter from array\n\tremoveFilter(field, type, value){\n\t\tif(!Array.isArray(field)){\n\t\t\tfield = [{field:field, type:type, value:value}];\n\t\t}\n\n\t\tfield.forEach((filter) => {\n\t\t\tvar index = -1;\n\n\t\t\tif(typeof filter.field == \"object\"){\n\t\t\t\tindex = this.filterList.findIndex((element) => {\n\t\t\t\t\treturn filter === element;\n\t\t\t\t});\n\t\t\t}else {\n\t\t\t\tindex = this.filterList.findIndex((element) => {\n\t\t\t\t\treturn filter.field === element.field && filter.type === element.type  && filter.value === element.value;\n\t\t\t\t});\n\t\t\t}\n\n\t\t\tif(index > -1){\n\t\t\t\tthis.filterList.splice(index, 1);\n\t\t\t}else {\n\t\t\t\tconsole.warn(\"Filter Error - No matching filter type found, ignoring: \", filter.type);\n\t\t\t}\n\t\t});\n\n\t\tthis.trackChanges();\n\t}\n\n\t//clear filters\n\tclearFilter(all){\n\t\tthis.filterList = [];\n\n\t\tif(all){\n\t\t\tthis.clearHeaderFilter();\n\t\t}\n\n\t\tthis.trackChanges();\n\t}\n\n\t//clear header filters\n\tclearHeaderFilter(){\n\t\tthis.headerFilters = {};\n\t\tthis.prevHeaderFilterChangeCheck = \"{}\";\n\n\t\tthis.headerFilterColumns.forEach((column) => {\n\t\t\tif(typeof column.modules.filter.value !== \"undefined\"){\n\t\t\t\tdelete column.modules.filter.value;\n\t\t\t}\n\t\t\tcolumn.modules.filter.prevSuccess = undefined;\n\t\t\tthis.reloadHeaderFilter(column);\n\t\t});\n\n\t\tthis.trackChanges();\n\t}\n\n\t//search data and return matching rows\n\tsearch (searchType, field, type, value){\n\t\tvar activeRows = [],\n\t\tfilterList = [];\n\n\t\tif(!Array.isArray(field)){\n\t\t\tfield = [{field:field, type:type, value:value}];\n\t\t}\n\n\t\tfield.forEach((filter) => {\n\t\t\tfilter = this.findFilter(filter);\n\n\t\t\tif(filter){\n\t\t\t\tfilterList.push(filter);\n\t\t\t}\n\t\t});\n\n\t\tthis.table.rowManager.rows.forEach((row) => {\n\t\t\tvar match = true;\n\n\t\t\tfilterList.forEach((filter) => {\n\t\t\t\tif(!this.filterRecurse(filter, row.getData())){\n\t\t\t\t\tmatch = false;\n\t\t\t\t}\n\t\t\t});\n\n\t\t\tif(match){\n\t\t\t\tactiveRows.push(searchType === \"data\" ? row.getData(\"data\") : row.getComponent());\n\t\t\t}\n\n\t\t});\n\n\t\treturn activeRows;\n\t}\n\n\t//filter row array\n\tfilter(rowList, filters){\n\t\tvar activeRows = [],\n\t\tactiveRowComponents = [];\n\n\t\tif(this.subscribedExternal(\"dataFiltering\")){\n\t\t\tthis.dispatchExternal(\"dataFiltering\", this.getFilters(true));\n\t\t}\n\n\t\tif(this.table.options.filterMode !== \"remote\" && (this.filterList.length || Object.keys(this.headerFilters).length)){\n\n\t\t\trowList.forEach((row) => {\n\t\t\t\tif(this.filterRow(row)){\n\t\t\t\t\tactiveRows.push(row);\n\t\t\t\t}\n\t\t\t});\n\n\t\t}else {\n\t\t\tactiveRows = rowList.slice(0);\n\t\t}\n\n\t\tif(this.subscribedExternal(\"dataFiltered\")){\n\n\t\t\tactiveRows.forEach((row) => {\n\t\t\t\tactiveRowComponents.push(row.getComponent());\n\t\t\t});\n\n\t\t\tthis.dispatchExternal(\"dataFiltered\", this.getFilters(true), activeRowComponents);\n\t\t}\n\n\t\treturn activeRows;\n\t}\n\n\t//filter individual row\n\tfilterRow(row, filters){\n\t\tvar match = true,\n\t\tdata = row.getData();\n\n\t\tthis.filterList.forEach((filter) => {\n\t\t\tif(!this.filterRecurse(filter, data)){\n\t\t\t\tmatch = false;\n\t\t\t}\n\t\t});\n\n\n\t\tfor(var field in this.headerFilters){\n\t\t\tif(!this.headerFilters[field].func(data)){\n\t\t\t\tmatch = false;\n\t\t\t}\n\t\t}\n\n\t\treturn match;\n\t}\n\n\tfilterRecurse(filter, data){\n\t\tvar match = false;\n\n\t\tif(Array.isArray(filter)){\n\t\t\tfilter.forEach((subFilter) => {\n\t\t\t\tif(this.filterRecurse(subFilter, data)){\n\t\t\t\t\tmatch = true;\n\t\t\t\t}\n\t\t\t});\n\t\t}else {\n\t\t\tmatch = filter.func(data);\n\t\t}\n\n\t\treturn match;\n\t}\n}\n\nFilter.moduleName = \"filter\";\n\n//load defaults\nFilter.filters = defaultFilters;\n\nfunction plaintext(cell, formatterParams, onRendered){\n\treturn this.emptyToSpace(this.sanitizeHTML(cell.getValue()));\n}\n\nfunction html$1(cell, formatterParams, onRendered){\n\treturn cell.getValue();\n}\n\nfunction textarea$1(cell, formatterParams, onRendered){\n\tcell.getElement().style.whiteSpace = \"pre-wrap\";\n\treturn this.emptyToSpace(this.sanitizeHTML(cell.getValue()));\n}\n\nfunction money(cell, formatterParams, onRendered){\n\tvar floatVal = parseFloat(cell.getValue()),\n\tsign = \"\",\n\tnumber, integer, decimal, rgx, value;\n\n\tvar decimalSym = formatterParams.decimal || \".\";\n\tvar thousandSym = formatterParams.thousand || \",\";\n\tvar negativeSign = formatterParams.negativeSign || \"-\";\n\tvar symbol = formatterParams.symbol || \"\";\n\tvar after = !!formatterParams.symbolAfter;\n\tvar precision = typeof formatterParams.precision !== \"undefined\" ? formatterParams.precision : 2;\n\n\tif(isNaN(floatVal)){\n\t\treturn this.emptyToSpace(this.sanitizeHTML(cell.getValue()));\n\t}\n\n\tif(floatVal < 0){\n\t\tfloatVal = Math.abs(floatVal);\n\t\tsign = negativeSign;\n\t}\n\n\tnumber = precision !== false ? floatVal.toFixed(precision) : floatVal;\n\tnumber = String(number).split(\".\");\n\n\tinteger = number[0];\n\tdecimal = number.length > 1 ? decimalSym + number[1] : \"\";\n\n\tif (formatterParams.thousand !== false) {\n\t\trgx = /(\\d+)(\\d{3})/;\n\n\t\twhile (rgx.test(integer)){\n\t\t\tinteger = integer.replace(rgx, \"$1\" + thousandSym + \"$2\");\n\t\t}\n\t}\n\n\tvalue = integer + decimal;\n\t\n\tif(sign === true){\n\t\tvalue = \"(\" + value  + \")\";\n\t\treturn after ? value + symbol : symbol + value;\n\t}else {\n\t\treturn after ? sign + value + symbol : sign + symbol + value;\n\t}\n}\n\nfunction link(cell, formatterParams, onRendered){\n\tvar value = cell.getValue(),\n\turlPrefix = formatterParams.urlPrefix || \"\",\n\tdownload = formatterParams.download,\n\tlabel = value,\n\tel = document.createElement(\"a\"),\n\tdata;\n\n\tfunction labelTraverse(path, data){\n\t\tvar item = path.shift(),\n\t\tvalue = data[item];\n\t\t\n\t\tif(path.length && typeof value === \"object\"){\n\t\t\treturn labelTraverse(path, value);\n\t\t}\n\n\t\treturn value;\n\t}\n\n\tif(formatterParams.labelField){\n\t\tdata = cell.getData();\n\t\tlabel = labelTraverse(formatterParams.labelField.split(this.table.options.nestedFieldSeparator), data);\n\t}\n\n\tif(formatterParams.label){\n\t\tswitch(typeof formatterParams.label){\n\t\t\tcase \"string\":\n\t\t\t\tlabel = formatterParams.label;\n\t\t\t\tbreak;\n\n\t\t\tcase \"function\":\n\t\t\t\tlabel = formatterParams.label(cell);\n\t\t\t\tbreak;\n\t\t}\n\t}\n\n\tif(label){\n\t\tif(formatterParams.urlField){\n\t\t\tdata = cell.getData();\n\n\t\t\tvalue = Helpers.retrieveNestedData(this.table.options.nestedFieldSeparator, formatterParams.urlField, data);\n\t\t}\n\n\t\tif(formatterParams.url){\n\t\t\tswitch(typeof formatterParams.url){\n\t\t\t\tcase \"string\":\n\t\t\t\t\tvalue = formatterParams.url;\n\t\t\t\t\tbreak;\n\n\t\t\t\tcase \"function\":\n\t\t\t\t\tvalue = formatterParams.url(cell);\n\t\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\n\t\tel.setAttribute(\"href\", urlPrefix + value);\n\n\t\tif(formatterParams.target){\n\t\t\tel.setAttribute(\"target\", formatterParams.target);\n\t\t}\n\n\t\tif(formatterParams.download){\n\n\t\t\tif(typeof download == \"function\"){\n\t\t\t\tdownload = download(cell);\n\t\t\t}else {\n\t\t\t\tdownload = download === true ? \"\" : download;\n\t\t\t}\n\n\t\t\tel.setAttribute(\"download\", download);\n\t\t}\n\n\t\tel.innerHTML = this.emptyToSpace(this.sanitizeHTML(label));\n\n\t\treturn el;\n\t}else {\n\t\treturn \"&nbsp;\";\n\t}\n}\n\nfunction image(cell, formatterParams, onRendered){\n\tvar el = document.createElement(\"img\"),\n\tsrc = cell.getValue();\n\n\tif(formatterParams.urlPrefix){\n\t\tsrc = formatterParams.urlPrefix + cell.getValue();\n\t}\n\n\tif(formatterParams.urlSuffix){\n\t\tsrc = src + formatterParams.urlSuffix;\n\t}\n\n\tel.setAttribute(\"src\", src);\n\n\tswitch(typeof formatterParams.height){\n\t\tcase \"number\":\n\t\t\tel.style.height = formatterParams.height + \"px\";\n\t\t\tbreak;\n\n\t\tcase \"string\":\n\t\t\tel.style.height = formatterParams.height;\n\t\t\tbreak;\n\t}\n\n\tswitch(typeof formatterParams.width){\n\t\tcase \"number\":\n\t\t\tel.style.width = formatterParams.width + \"px\";\n\t\t\tbreak;\n\n\t\tcase \"string\":\n\t\t\tel.style.width = formatterParams.width;\n\t\t\tbreak;\n\t}\n\n\tel.addEventListener(\"load\", function(){\n\t\tcell.getRow().normalizeHeight();\n\t});\n\n\treturn el;\n}\n\nfunction tickCross$1(cell, formatterParams, onRendered){\n\tvar value = cell.getValue(),\n\telement = cell.getElement(),\n\tempty = formatterParams.allowEmpty,\n\ttruthy = formatterParams.allowTruthy,\n\ttrueValueSet = Object.keys(formatterParams).includes(\"trueValue\"),\n\ttick = typeof formatterParams.tickElement !== \"undefined\" ? formatterParams.tickElement : '<svg enable-background=\"new 0 0 24 24\" height=\"14\" width=\"14\" viewBox=\"0 0 24 24\" xml:space=\"preserve\" ><path fill=\"#2DC214\" clip-rule=\"evenodd\" d=\"M21.652,3.211c-0.293-0.295-0.77-0.295-1.061,0L9.41,14.34  c-0.293,0.297-0.771,0.297-1.062,0L3.449,9.351C3.304,9.203,3.114,9.13,2.923,9.129C2.73,9.128,2.534,9.201,2.387,9.351  l-2.165,1.946C0.078,11.445,0,11.63,0,11.823c0,0.194,0.078,0.397,0.223,0.544l4.94,5.184c0.292,0.296,0.771,0.776,1.062,1.07  l2.124,2.141c0.292,0.293,0.769,0.293,1.062,0l14.366-14.34c0.293-0.294,0.293-0.777,0-1.071L21.652,3.211z\" fill-rule=\"evenodd\"/></svg>',\n\tcross = typeof formatterParams.crossElement !== \"undefined\" ? formatterParams.crossElement : '<svg enable-background=\"new 0 0 24 24\" height=\"14\" width=\"14\"  viewBox=\"0 0 24 24\" xml:space=\"preserve\" ><path fill=\"#CE1515\" d=\"M22.245,4.015c0.313,0.313,0.313,0.826,0,1.139l-6.276,6.27c-0.313,0.312-0.313,0.826,0,1.14l6.273,6.272  c0.313,0.313,0.313,0.826,0,1.14l-2.285,2.277c-0.314,0.312-0.828,0.312-1.142,0l-6.271-6.271c-0.313-0.313-0.828-0.313-1.141,0  l-6.276,6.267c-0.313,0.313-0.828,0.313-1.141,0l-2.282-2.28c-0.313-0.313-0.313-0.826,0-1.14l6.278-6.269  c0.313-0.312,0.313-0.826,0-1.14L1.709,5.147c-0.314-0.313-0.314-0.827,0-1.14l2.284-2.278C4.308,1.417,4.821,1.417,5.135,1.73  L11.405,8c0.314,0.314,0.828,0.314,1.141,0.001l6.276-6.267c0.312-0.312,0.826-0.312,1.141,0L22.245,4.015z\"/></svg>';\n\n\tif((trueValueSet && value === formatterParams.trueValue) || (!trueValueSet && ((truthy && value) || (value === true || value === \"true\" || value === \"True\" || value === 1 || value === \"1\")))){\n\t\telement.setAttribute(\"aria-checked\", true);\n\t\treturn tick || \"\";\n\t}else {\n\t\tif(empty && (value === \"null\" || value === \"\" || value === null || typeof value === \"undefined\")){\n\t\t\telement.setAttribute(\"aria-checked\", \"mixed\");\n\t\t\treturn \"\";\n\t\t}else {\n\t\t\telement.setAttribute(\"aria-checked\", false);\n\t\t\treturn cross || \"\";\n\t\t}\n\t}\n}\n\nfunction datetime$1(cell, formatterParams, onRendered){\n\tvar DT = window.DateTime || luxon.DateTime;\n\tvar inputFormat = formatterParams.inputFormat || \"yyyy-MM-dd HH:mm:ss\";\n\tvar\toutputFormat = formatterParams.outputFormat || \"dd/MM/yyyy HH:mm:ss\";\n\tvar\tinvalid = typeof formatterParams.invalidPlaceholder !== \"undefined\" ? formatterParams.invalidPlaceholder : \"\";\n\tvar value = cell.getValue();\n\n\tif(typeof DT != \"undefined\"){\n\t\tvar newDatetime;\n\n\t\tif(DT.isDateTime(value)){\n\t\t\tnewDatetime = value;\n\t\t}else if(inputFormat === \"iso\"){\n\t\t\tnewDatetime = DT.fromISO(String(value));\n\t\t}else {\n\t\t\tnewDatetime = DT.fromFormat(String(value), inputFormat);\n\t\t}\n\n\t\tif(newDatetime.isValid){\n\t\t\tif(formatterParams.timezone){\n\t\t\t\tnewDatetime = newDatetime.setZone(formatterParams.timezone);\n\t\t\t}\n\n\t\t\treturn newDatetime.toFormat(outputFormat);\n\t\t}else {\n\t\t\tif(invalid === true || !value){\n\t\t\t\treturn value;\n\t\t\t}else if(typeof invalid === \"function\"){\n\t\t\t\treturn invalid(value);\n\t\t\t}else {\n\t\t\t\treturn invalid;\n\t\t\t}\n\t\t}\n\t}else {\n\t\tconsole.error(\"Format Error - 'datetime' formatter is dependant on luxon.js\");\n\t}\n}\n\nfunction datetimediff (cell, formatterParams, onRendered) {\n\tvar DT = window.DateTime || luxon.DateTime;\n\tvar inputFormat = formatterParams.inputFormat || \"yyyy-MM-dd HH:mm:ss\";\n\tvar invalid = typeof formatterParams.invalidPlaceholder !== \"undefined\" ? formatterParams.invalidPlaceholder : \"\";\n\tvar suffix = typeof formatterParams.suffix !== \"undefined\" ? formatterParams.suffix : false;\n\tvar unit = typeof formatterParams.unit !== \"undefined\" ? formatterParams.unit : \"days\";\n\tvar humanize = typeof formatterParams.humanize !== \"undefined\" ? formatterParams.humanize : false;\n\tvar date = typeof formatterParams.date !== \"undefined\" ? formatterParams.date : DT.now();\n\tvar value = cell.getValue();\n\n\tif(typeof DT != \"undefined\"){\n\t\tvar newDatetime;\n\n\t\tif(DT.isDateTime(value)){\n\t\t\tnewDatetime = value;\n\t\t}else if(inputFormat === \"iso\"){\n\t\t\tnewDatetime = DT.fromISO(String(value));\n\t\t}else {\n\t\t\tnewDatetime = DT.fromFormat(String(value), inputFormat);\n\t\t}\n\n\t\tif (newDatetime.isValid){\n\t\t\tif(humanize){\n\t\t\t\treturn newDatetime.diff(date, unit).toHuman()  + (suffix ? \" \" + suffix : \"\");\n\t\t\t}else {\n\t\t\t\treturn parseInt(newDatetime.diff(date, unit)[unit]) + (suffix ? \" \" + suffix : \"\");\n\t\t\t}\n\t\t} else {\n\n\t\t\tif (invalid === true) {\n\t\t\t\treturn value;\n\t\t\t} else if (typeof invalid === \"function\") {\n\t\t\t\treturn invalid(value);\n\t\t\t} else {\n\t\t\t\treturn invalid;\n\t\t\t}\n\t\t}\n\t}else {\n\t\tconsole.error(\"Format Error - 'datetimediff' formatter is dependant on luxon.js\");\n\t}\n}\n\nfunction lookup (cell, formatterParams, onRendered) {\n\tvar value = cell.getValue();\n\n\tif (typeof formatterParams[value] === \"undefined\") {\n\t\tconsole.warn('Missing display value for ' + value);\n\t\treturn value;\n\t}\n\n\treturn formatterParams[value];\n}\n\nfunction star$1(cell, formatterParams, onRendered){\n\tvar value = cell.getValue(),\n\telement = cell.getElement(),\n\tmaxStars = formatterParams && formatterParams.stars ? formatterParams.stars : 5,\n\tstars = document.createElement(\"span\"),\n\tstar = document.createElementNS('http://www.w3.org/2000/svg', \"svg\"),\n\tstarActive = '<polygon fill=\"#FFEA00\" stroke=\"#C1AB60\" stroke-width=\"37.6152\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-miterlimit=\"10\" points=\"259.216,29.942 330.27,173.919 489.16,197.007 374.185,309.08 401.33,467.31 259.216,392.612 117.104,467.31 144.25,309.08 29.274,197.007 188.165,173.919 \"/>',\n\tstarInactive = '<polygon fill=\"#D2D2D2\" stroke=\"#686868\" stroke-width=\"37.6152\" stroke-linecap=\"round\" stroke-linejoin=\"round\" stroke-miterlimit=\"10\" points=\"259.216,29.942 330.27,173.919 489.16,197.007 374.185,309.08 401.33,467.31 259.216,392.612 117.104,467.31 144.25,309.08 29.274,197.007 188.165,173.919 \"/>';\n\n\t//style stars holder\n\tstars.style.verticalAlign = \"middle\";\n\n\t//style star\n\tstar.setAttribute(\"width\", \"14\");\n\tstar.setAttribute(\"height\", \"14\");\n\tstar.setAttribute(\"viewBox\", \"0 0 512 512\");\n\tstar.setAttribute(\"xml:space\", \"preserve\");\n\tstar.style.padding = \"0 1px\";\n\n\tvalue = value && !isNaN(value) ? parseInt(value) : 0;\n\n\tvalue = Math.max(0, Math.min(value, maxStars));\n\n\tfor(var i=1;i<= maxStars;i++){\n\t\tvar nextStar = star.cloneNode(true);\n\t\tnextStar.innerHTML = i <= value ? starActive : starInactive;\n\n\t\tstars.appendChild(nextStar);\n\t}\n\n\telement.style.whiteSpace = \"nowrap\";\n\telement.style.overflow = \"hidden\";\n\telement.style.textOverflow = \"ellipsis\";\n\n\telement.setAttribute(\"aria-label\", value);\n\n\treturn stars;\n}\n\nfunction traffic(cell, formatterParams, onRendered){\n\tvar value = this.sanitizeHTML(cell.getValue()) || 0,\n\tel = document.createElement(\"span\"),\n\tmax = formatterParams && formatterParams.max ? formatterParams.max : 100,\n\tmin = formatterParams && formatterParams.min ? formatterParams.min : 0,\n\tcolors = formatterParams && typeof formatterParams.color !== \"undefined\" ? formatterParams.color : [\"red\", \"orange\", \"green\"],\n\tcolor = \"#666666\",\n\tpercent, percentValue;\n\n\tif(isNaN(value) || typeof cell.getValue() === \"undefined\"){\n\t\treturn;\n\t}\n\n\tel.classList.add(\"tabulator-traffic-light\");\n\n\t//make sure value is in range\n\tpercentValue = parseFloat(value) <= max ? parseFloat(value) : max;\n\tpercentValue = parseFloat(percentValue) >= min ? parseFloat(percentValue) : min;\n\n\t//workout percentage\n\tpercent = (max - min) / 100;\n\tpercentValue = Math.round((percentValue - min) / percent);\n\n\t//set color\n\tswitch(typeof colors){\n\t\tcase \"string\":\n\t\t\tcolor = colors;\n\t\t\tbreak;\n\t\tcase \"function\":\n\t\t\tcolor = colors(value);\n\t\t\tbreak;\n\t\tcase \"object\":\n\t\t\tif(Array.isArray(colors)){\n\t\t\t\tvar unit = 100 / colors.length;\n\t\t\t\tvar index = Math.floor(percentValue / unit);\n\n\t\t\t\tindex = Math.min(index, colors.length - 1);\n\t\t\t\tindex = Math.max(index, 0);\n\t\t\t\tcolor = colors[index];\n\t\t\t\tbreak;\n\t\t\t}\n\t}\n\n\tel.style.backgroundColor = color;\n\n\treturn el;\n}\n\nfunction progress$1(cell, formatterParams = {}, onRendered){ //progress bar\n\tvar value = this.sanitizeHTML(cell.getValue()) || 0,\n\telement = cell.getElement(),\n\tmax = formatterParams.max ? formatterParams.max : 100,\n\tmin = formatterParams.min ? formatterParams.min : 0,\n\tlegendAlign = formatterParams.legendAlign ? formatterParams.legendAlign : \"center\",\n\tpercent, percentValue, color, legend, legendColor;\n\n\t//make sure value is in range\n\tpercentValue = parseFloat(value) <= max ? parseFloat(value) : max;\n\tpercentValue = parseFloat(percentValue) >= min ? parseFloat(percentValue) : min;\n\n\t//workout percentage\n\tpercent = (max - min) / 100;\n\tpercentValue = Math.round((percentValue - min) / percent);\n\n\t//set bar color\n\tswitch(typeof formatterParams.color){\n\t\tcase \"string\":\n\t\t\tcolor = formatterParams.color;\n\t\t\tbreak;\n\t\tcase \"function\":\n\t\t\tcolor = formatterParams.color(value);\n\t\t\tbreak;\n\t\tcase \"object\":\n\t\t\tif(Array.isArray(formatterParams.color)){\n\t\t\t\tlet unit = 100 / formatterParams.color.length;\n\t\t\t\tlet index = Math.floor(percentValue / unit);\n\n\t\t\t\tindex = Math.min(index, formatterParams.color.length - 1);\n\t\t\t\tindex = Math.max(index, 0);\n\t\t\t\tcolor = formatterParams.color[index];\n\t\t\t\tbreak;\n\t\t\t}\n\t\tdefault:\n\t\t\tcolor = \"#2DC214\";\n\t}\n\n\t//generate legend\n\tswitch(typeof formatterParams.legend){\n\t\tcase \"string\":\n\t\t\tlegend = formatterParams.legend;\n\t\t\tbreak;\n\t\tcase \"function\":\n\t\t\tlegend = formatterParams.legend(value);\n\t\t\tbreak;\n\t\tcase \"boolean\":\n\t\t\tlegend = value;\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tlegend = false;\n\t}\n\n\t//set legend color\n\tswitch(typeof formatterParams.legendColor){\n\t\tcase \"string\":\n\t\t\tlegendColor = formatterParams.legendColor;\n\t\t\tbreak;\n\t\tcase \"function\":\n\t\t\tlegendColor = formatterParams.legendColor(value);\n\t\t\tbreak;\n\t\tcase \"object\":\n\t\t\tif(Array.isArray(formatterParams.legendColor)){\n\t\t\t\tlet unit = 100 / formatterParams.legendColor.length;\n\t\t\t\tlet index = Math.floor(percentValue / unit);\n\n\t\t\t\tindex = Math.min(index, formatterParams.legendColor.length - 1);\n\t\t\t\tindex = Math.max(index, 0);\n\t\t\t\tlegendColor = formatterParams.legendColor[index];\n\t\t\t}\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tlegendColor = \"#000\";\n\t}\n\n\telement.style.minWidth = \"30px\";\n\telement.style.position = \"relative\";\n\n\telement.setAttribute(\"aria-label\", percentValue);\n\n\tvar barEl = document.createElement(\"div\");\n\tbarEl.style.display = \"inline-block\";\n\tbarEl.style.width = percentValue + \"%\";\n\tbarEl.style.backgroundColor = color;\n\tbarEl.style.height = \"100%\";\n\n\tbarEl.setAttribute('data-max', max);\n\tbarEl.setAttribute('data-min', min);\n\n\tvar barContainer = document.createElement(\"div\");\n\tbarContainer.style.position = \"relative\";\n\tbarContainer.style.width = \"100%\";\n\tbarContainer.style.height = \"100%\";\n\n\tif(legend){\n\t\tvar legendEl = document.createElement(\"div\");\n\t\tlegendEl.style.position = \"absolute\";\n\t\tlegendEl.style.top = 0;\n\t\tlegendEl.style.left = 0;\n\t\tlegendEl.style.textAlign = legendAlign;\n\t\tlegendEl.style.width = \"100%\";\n\t\tlegendEl.style.color = legendColor;\n\t\tlegendEl.innerHTML = legend;\n\t}\n\n\tonRendered(function(){\n\n\t\t//handle custom element needed if formatter is to be included in printed/downloaded output\n\t\tif(!(cell instanceof CellComponent)){\n\t\t\tvar holderEl = document.createElement(\"div\");\n\t\t\tholderEl.style.position = \"absolute\";\n\t\t\tholderEl.style.top = \"4px\";\n\t\t\tholderEl.style.bottom = \"4px\";\n\t\t\tholderEl.style.left = \"4px\";\n\t\t\tholderEl.style.right = \"4px\";\n\n\t\t\telement.appendChild(holderEl);\n\n\t\t\telement = holderEl;\n\t\t}\n\n\t\telement.appendChild(barContainer);\n\t\tbarContainer.appendChild(barEl);\n\n\t\tif(legend){\n\t\t\tbarContainer.appendChild(legendEl);\n\t\t}\n\t});\n\n\treturn \"\";\n}\n\nfunction color(cell, formatterParams, onRendered){\n\tcell.getElement().style.backgroundColor = this.sanitizeHTML(cell.getValue());\n\treturn \"\";\n}\n\nfunction buttonTick(cell, formatterParams, onRendered){\n\treturn '<svg enable-background=\"new 0 0 24 24\" height=\"14\" width=\"14\" viewBox=\"0 0 24 24\" xml:space=\"preserve\" ><path fill=\"#2DC214\" clip-rule=\"evenodd\" d=\"M21.652,3.211c-0.293-0.295-0.77-0.295-1.061,0L9.41,14.34  c-0.293,0.297-0.771,0.297-1.062,0L3.449,9.351C3.304,9.203,3.114,9.13,2.923,9.129C2.73,9.128,2.534,9.201,2.387,9.351  l-2.165,1.946C0.078,11.445,0,11.63,0,11.823c0,0.194,0.078,0.397,0.223,0.544l4.94,5.184c0.292,0.296,0.771,0.776,1.062,1.07  l2.124,2.141c0.292,0.293,0.769,0.293,1.062,0l14.366-14.34c0.293-0.294,0.293-0.777,0-1.071L21.652,3.211z\" fill-rule=\"evenodd\"/></svg>';\n}\n\nfunction buttonCross(cell, formatterParams, onRendered){\n\treturn '<svg enable-background=\"new 0 0 24 24\" height=\"14\" width=\"14\" viewBox=\"0 0 24 24\" xml:space=\"preserve\" ><path fill=\"#CE1515\" d=\"M22.245,4.015c0.313,0.313,0.313,0.826,0,1.139l-6.276,6.27c-0.313,0.312-0.313,0.826,0,1.14l6.273,6.272  c0.313,0.313,0.313,0.826,0,1.14l-2.285,2.277c-0.314,0.312-0.828,0.312-1.142,0l-6.271-6.271c-0.313-0.313-0.828-0.313-1.141,0  l-6.276,6.267c-0.313,0.313-0.828,0.313-1.141,0l-2.282-2.28c-0.313-0.313-0.313-0.826,0-1.14l6.278-6.269  c0.313-0.312,0.313-0.826,0-1.14L1.709,5.147c-0.314-0.313-0.314-0.827,0-1.14l2.284-2.278C4.308,1.417,4.821,1.417,5.135,1.73  L11.405,8c0.314,0.314,0.828,0.314,1.141,0.001l6.276-6.267c0.312-0.312,0.826-0.312,1.141,0L22.245,4.015z\"/></svg>';\n}\n\nfunction rownum(cell, formatterParams, onRendered){\n\tvar content = document.createElement(\"span\");\n\tvar row = cell.getRow();\n\tvar table = cell.getTable();\n\n\trow.watchPosition((position) => {\n\t\tif (formatterParams.relativeToPage) {\n\t\t\tposition += table.modules.page.getPageSize() * (table.modules.page.getPage() - 1);\n\t\t}\n\t\tcontent.innerText = position;\n\t});\n\t\n\treturn content;\n}\n\nfunction handle(cell, formatterParams, onRendered){\n\tcell.getElement().classList.add(\"tabulator-row-handle\");\n\treturn \"<div class='tabulator-row-handle-box'><div class='tabulator-row-handle-bar'></div><div class='tabulator-row-handle-bar'></div><div class='tabulator-row-handle-bar'></div></div>\";\n}\n\nfunction responsiveCollapse(cell, formatterParams, onRendered){\n\tvar el = document.createElement(\"div\"),\n\tconfig = cell.getRow()._row.modules.responsiveLayout;\n\n\tel.classList.add(\"tabulator-responsive-collapse-toggle\");\n\t\n\tel.innerHTML = `<svg class='tabulator-responsive-collapse-toggle-open' viewbox=\"0 0 24 24\">\n  <line x1=\"7\" y1=\"12\" x2=\"17\" y2=\"12\" fill=\"none\" stroke-width=\"3\" stroke-linecap=\"round\" />\n  <line y1=\"7\" x1=\"12\" y2=\"17\" x2=\"12\" fill=\"none\" stroke-width=\"3\" stroke-linecap=\"round\" />\n</svg>\n\n<svg class='tabulator-responsive-collapse-toggle-close' viewbox=\"0 0 24 24\">\n  <line x1=\"7\" y1=\"12\" x2=\"17\" y2=\"12\"  fill=\"none\" stroke-width=\"3\" stroke-linecap=\"round\" />\n</svg>`;\n\n\tcell.getElement().classList.add(\"tabulator-row-handle\");\n\n\tfunction toggleList(isOpen){\n\t\tvar collapseEl = config.element;\n\n\t\tconfig.open = isOpen;\n\n\t\tif(collapseEl){\n\n\t\t\tif(config.open){\n\t\t\t\tel.classList.add(\"open\");\n\t\t\t\tcollapseEl.style.display = '';\n\t\t\t}else {\n\t\t\t\tel.classList.remove(\"open\");\n\t\t\t\tcollapseEl.style.display = 'none';\n\t\t\t}\n\t\t}\n\t}\n\n\tel.addEventListener(\"click\", function(e){\n\t\te.stopImmediatePropagation();\n\t\ttoggleList(!config.open);\n\t\tcell.getTable().rowManager.adjustTableSize();\n\t});\n\n\ttoggleList(config.open);\n\n\treturn el;\n}\n\nfunction rowSelection(cell, formatterParams, onRendered){\n\tvar checkbox = document.createElement(\"input\");\n\tvar blocked = false;\n\n\tcheckbox.type = 'checkbox';\n\n\tcheckbox.setAttribute(\"aria-label\", \"Select Row\");\n\t\n\tif(this.table.modExists(\"selectRow\", true)){\n\n\t\tcheckbox.addEventListener(\"click\", (e) => {\n\t\t\te.stopPropagation();\n\t\t});\n\n\t\tif(typeof cell.getRow == 'function'){\n\t\t\tvar row = cell.getRow();\n\n\t\t\tif(row instanceof RowComponent){\n\n\t\t\t\tcheckbox.addEventListener(\"change\", (e) => {\n\t\t\t\t\tif(this.table.options.selectableRowsRangeMode === \"click\"){\n\t\t\t\t\t\tif(!blocked){\n\t\t\t\t\t\t\trow.toggleSelect();\n\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\tblocked = false;\n\t\t\t\t\t\t}\n\t\t\t\t\t}else {\n\t\t\t\t\t\trow.toggleSelect();\n\t\t\t\t\t}\n\t\t\t\t});\n\n\t\t\t\tif(this.table.options.selectableRowsRangeMode === \"click\"){\n\t\t\t\t\tcheckbox.addEventListener(\"click\", (e) => {\n\t\t\t\t\t\tblocked = true;\n\t\t\t\t\t\tthis.table.modules.selectRow.handleComplexRowClick(row._row, e);\n\t\t\t\t\t});\n\t\t\t\t}\n\n\t\t\t\tcheckbox.checked = row.isSelected && row.isSelected();\n\t\t\t\tthis.table.modules.selectRow.registerRowSelectCheckbox(row, checkbox);\n\t\t\t}else {\n\t\t\t\tcheckbox = \"\";\n\t\t\t}\n\t\t}else {\n\t\t\tcheckbox.addEventListener(\"change\", (e) => {\n\t\t\t\tif(this.table.modules.selectRow.selectedRows.length){\n\t\t\t\t\tthis.table.deselectRow();\n\t\t\t\t}else {\n\t\t\t\t\tthis.table.selectRow(formatterParams.rowRange);\n\t\t\t\t}\n\t\t\t});\n\n\t\t\tthis.table.modules.selectRow.registerHeaderSelectCheckbox(checkbox);\n\t\t}\n\t}\n\n\treturn checkbox;\n}\n\nvar defaultFormatters = {\n\tplaintext:plaintext,\n\thtml:html$1,\n\ttextarea:textarea$1,\n\tmoney:money,\n\tlink:link,\n\timage:image,\n\ttickCross:tickCross$1,\n\tdatetime:datetime$1,\n\tdatetimediff:datetimediff,\n\tlookup:lookup,\n\tstar:star$1,\n\ttraffic:traffic,\n\tprogress:progress$1,\n\tcolor:color,\n\tbuttonTick:buttonTick,\n\tbuttonCross:buttonCross,\n\trownum:rownum,\n\thandle:handle,\n\tresponsiveCollapse:responsiveCollapse,\n\trowSelection:rowSelection,\n};\n\nclass Format extends Module{\n\t\n\tconstructor(table){\n\t\tsuper(table);\n\t\t\n\t\tthis.registerColumnOption(\"formatter\");\n\t\tthis.registerColumnOption(\"formatterParams\");\n\t\t\n\t\tthis.registerColumnOption(\"formatterPrint\");\n\t\tthis.registerColumnOption(\"formatterPrintParams\");\n\t\tthis.registerColumnOption(\"formatterClipboard\");\n\t\tthis.registerColumnOption(\"formatterClipboardParams\");\n\t\tthis.registerColumnOption(\"formatterHtmlOutput\");\n\t\tthis.registerColumnOption(\"formatterHtmlOutputParams\");\n\t\tthis.registerColumnOption(\"titleFormatter\");\n\t\tthis.registerColumnOption(\"titleFormatterParams\");\n\t}\n\t\n\tinitialize(){\n\t\tthis.subscribe(\"cell-format\", this.formatValue.bind(this));\n\t\tthis.subscribe(\"cell-rendered\", this.cellRendered.bind(this));\n\t\tthis.subscribe(\"column-layout\", this.initializeColumn.bind(this));\n\t\tthis.subscribe(\"column-format\", this.formatHeader.bind(this));\n\t}\n\t\n\t//initialize column formatter\n\tinitializeColumn(column){\n\t\tcolumn.modules.format = this.lookupFormatter(column, \"\");\n\t\t\n\t\tif(typeof column.definition.formatterPrint !== \"undefined\"){\n\t\t\tcolumn.modules.format.print = this.lookupFormatter(column, \"Print\");\n\t\t}\n\t\t\n\t\tif(typeof column.definition.formatterClipboard !== \"undefined\"){\n\t\t\tcolumn.modules.format.clipboard = this.lookupFormatter(column, \"Clipboard\");\n\t\t}\n\t\t\n\t\tif(typeof column.definition.formatterHtmlOutput !== \"undefined\"){\n\t\t\tcolumn.modules.format.htmlOutput = this.lookupFormatter(column, \"HtmlOutput\");\n\t\t}\n\t}\n\t\n\tlookupFormatter(column, type){\n\t\tvar config = {params:column.definition[\"formatter\" + type + \"Params\"] || {}},\n\t\tformatter = column.definition[\"formatter\" + type];\n\t\t\n\t\t//set column formatter\n\t\tswitch(typeof formatter){\n\t\t\tcase \"string\":\n\t\t\t\tif(Format.formatters[formatter]){\n\t\t\t\t\tconfig.formatter = Format.formatters[formatter];\n\t\t\t\t}else {\n\t\t\t\t\tconsole.warn(\"Formatter Error - No such formatter found: \", formatter);\n\t\t\t\t\tconfig.formatter = Format.formatters.plaintext;\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase \"function\":\n\t\t\t\tconfig.formatter = formatter;\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tdefault:\n\t\t\t\tconfig.formatter = Format.formatters.plaintext;\n\t\t\t\tbreak;\n\t\t}\n\t\t\n\t\treturn config;\n\t}\n\t\n\tcellRendered(cell){\n\t\tif(cell.modules.format && cell.modules.format.renderedCallback && !cell.modules.format.rendered){\n\t\t\tcell.modules.format.renderedCallback();\n\t\t\tcell.modules.format.rendered = true;\n\t\t}\n\t}\n\t\n\t//return a formatted value for a column header\n\tformatHeader(column, title, el){\n\t\tvar formatter, params, onRendered, mockCell;\n\t\t\n\t\tif(column.definition.titleFormatter){\n\t\t\tformatter = this.getFormatter(column.definition.titleFormatter);\n\t\t\t\n\t\t\tonRendered = (callback) => {\n\t\t\t\tcolumn.titleFormatterRendered = callback;\n\t\t\t};\n\t\t\t\n\t\t\tmockCell = {\n\t\t\t\tgetValue:function(){\n\t\t\t\t\treturn title;\n\t\t\t\t},\n\t\t\t\tgetElement:function(){\n\t\t\t\t\treturn el;\n\t\t\t\t},\n\t\t\t\tgetType:function(){\n\t\t\t\t\treturn \"header\";\n\t\t\t\t},\n\t\t\t\tgetColumn:function(){\n\t\t\t\t\treturn column.getComponent();\n\t\t\t\t},\n\t\t\t\tgetTable:() => {\n\t\t\t\t\treturn this.table;\n\t\t\t\t}\n\t\t\t};\n\t\t\t\n\t\t\tparams = column.definition.titleFormatterParams || {};\n\t\t\t\n\t\t\tparams = typeof params === \"function\" ? params() : params;\n\t\t\t\n\t\t\treturn formatter.call(this, mockCell, params, onRendered);\n\t\t}else {\n\t\t\treturn title;\n\t\t}\n\t}\n\t\n\t\n\t//return a formatted value for a cell\n\tformatValue(cell){\n\t\tvar component = cell.getComponent(),\n\t\tparams = typeof cell.column.modules.format.params === \"function\" ? cell.column.modules.format.params(component) : cell.column.modules.format.params;\n\t\t\n\t\tfunction onRendered(callback){\n\t\t\tif(!cell.modules.format){\n\t\t\t\tcell.modules.format = {};\n\t\t\t}\n\t\t\t\n\t\t\tcell.modules.format.renderedCallback = callback;\n\t\t\tcell.modules.format.rendered = false;\n\t\t}\n\t\t\n\t\treturn cell.column.modules.format.formatter.call(this, component, params, onRendered);\n\t}\n\t\n\tformatExportValue(cell, type){\n\t\tvar formatter = cell.column.modules.format[type],\n\t\tparams;\n\t\t\n\t\tif(formatter){\n\t\t\tparams = typeof formatter.params === \"function\" ? formatter.params(cell.getComponent()) : formatter.params;\n\t\t\t\n\t\t\tfunction onRendered(callback){\n\t\t\t\tif(!cell.modules.format){\n\t\t\t\t\tcell.modules.format = {};\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tcell.modules.format.renderedCallback = callback;\n\t\t\t\tcell.modules.format.rendered = false;\n\t\t\t}\n\t\t\t\n\t\t\treturn formatter.formatter.call(this, cell.getComponent(), params, onRendered);\n\t\t\t\n\t\t}else {\n\t\t\treturn this.formatValue(cell);\n\t\t}\n\t}\n\t\n\tsanitizeHTML(value){\n\t\tif(value){\n\t\t\tvar entityMap = {\n\t\t\t\t'&': '&amp;',\n\t\t\t\t'<': '&lt;',\n\t\t\t\t'>': '&gt;',\n\t\t\t\t'\"': '&quot;',\n\t\t\t\t\"'\": '&#39;',\n\t\t\t\t'/': '&#x2F;',\n\t\t\t\t'`': '&#x60;',\n\t\t\t\t'=': '&#x3D;'\n\t\t\t};\n\t\t\t\n\t\t\treturn String(value).replace(/[&<>\"'`=/]/g, function (s) {\n\t\t\t\treturn entityMap[s];\n\t\t\t});\n\t\t}else {\n\t\t\treturn value;\n\t\t}\n\t}\n\t\n\temptyToSpace(value){\n\t\treturn value === null || typeof value === \"undefined\" || value === \"\" ? \"&nbsp;\" : value;\n\t}\n\t\n\t//get formatter for cell\n\tgetFormatter(formatter){\n\t\tswitch(typeof formatter){\n\t\t\tcase \"string\":\n\t\t\t\tif(Format.formatters[formatter]){\n\t\t\t\t\tformatter = Format.formatters[formatter];\n\t\t\t\t}else {\n\t\t\t\t\tconsole.warn(\"Formatter Error - No such formatter found: \", formatter);\n\t\t\t\t\tformatter = Format.formatters.plaintext;\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase \"function\":\n\t\t\t//Custom formatter Function, do nothing\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tdefault:\n\t\t\t\tformatter = Format.formatters.plaintext;\n\t\t\t\tbreak;\n\t\t}\n\t\t\n\t\treturn formatter;\n\t}\n}\n\nFormat.moduleName = \"format\";\n\n//load defaults\nFormat.formatters = defaultFormatters;\n\nclass FrozenColumns extends Module{\n\t\n\tconstructor(table){\n\t\tsuper(table);\n\t\t\n\t\tthis.leftColumns = [];\n\t\tthis.rightColumns = [];\n\t\tthis.initializationMode = \"left\";\n\t\tthis.active = false;\n\t\tthis.blocked = true;\n\t\t\n\t\tthis.registerColumnOption(\"frozen\");\n\t}\n\t\n\t//reset initial state\n\treset(){\n\t\tthis.initializationMode = \"left\";\n\t\tthis.leftColumns = [];\n\t\tthis.rightColumns = [];\n\t\tthis.active = false;\n\t}\n\t\n\tinitialize(){\n\t\tthis.subscribe(\"cell-layout\", this.layoutCell.bind(this));\n\t\tthis.subscribe(\"column-init\", this.initializeColumn.bind(this));\n\t\tthis.subscribe(\"column-width\", this.layout.bind(this));\n\t\tthis.subscribe(\"row-layout-after\", this.layoutRow.bind(this));\n\t\tthis.subscribe(\"table-layout\", this.layout.bind(this));\n\t\tthis.subscribe(\"columns-loading\", this.reset.bind(this));\n\t\t\n\t\tthis.subscribe(\"column-add\", this.reinitializeColumns.bind(this));\n\t\tthis.subscribe(\"column-deleted\", this.reinitializeColumns.bind(this));\n\t\tthis.subscribe(\"column-hide\", this.reinitializeColumns.bind(this));\n\t\tthis.subscribe(\"column-show\", this.reinitializeColumns.bind(this));\n\t\tthis.subscribe(\"columns-loaded\", this.reinitializeColumns.bind(this));\n\t\t\n\t\tthis.subscribe(\"table-redraw\", this.layout.bind(this));\n\t\tthis.subscribe(\"layout-refreshing\", this.blockLayout.bind(this));\n\t\tthis.subscribe(\"layout-refreshed\", this.unblockLayout.bind(this));\n\t\tthis.subscribe(\"scrollbar-vertical\", this.adjustForScrollbar.bind(this));\n\t}\n\t\n\tblockLayout(){\n\t\tthis.blocked = true;\n\t}\n\t\n\tunblockLayout(){\n\t\tthis.blocked = false;\n\t}\n\t\n\tlayoutCell(cell){\n\t\tthis.layoutElement(cell.element, cell.column);\n\t}\n\t\n\treinitializeColumns(){\n\t\tthis.reset();\n\t\t\n\t\tthis.table.columnManager.columnsByIndex.forEach((column) => {\n\t\t\tthis.initializeColumn(column);\n\t\t});\n\n\t\tthis.layout();\n\t}\n\t\n\t//initialize specific column\n\tinitializeColumn(column){\n\t\tvar config = {margin:0, edge:false};\n\t\t\n\t\tif(!column.isGroup){\t\t\t\n\t\t\tif(this.frozenCheck(column)){\n\t\t\t\tconfig.position = this.initializationMode;\n\t\t\t\t\n\t\t\t\tif(this.initializationMode == \"left\"){\n\t\t\t\t\tthis.leftColumns.push(column);\n\t\t\t\t}else {\n\t\t\t\t\tthis.rightColumns.unshift(column);\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tthis.active = true;\n\t\t\t\t\n\t\t\t\tcolumn.modules.frozen = config;\n\t\t\t}else {\n\t\t\t\tthis.initializationMode = \"right\";\n\t\t\t}\n\t\t}\n\t}\n\t\n\tfrozenCheck(column){\n\t\tif(column.parent.isGroup && column.definition.frozen){\n\t\t\tconsole.warn(\"Frozen Column Error - Parent column group must be frozen, not individual columns or sub column groups\");\n\t\t}\n\t\t\n\t\tif(column.parent.isGroup){\n\t\t\treturn this.frozenCheck(column.parent);\n\t\t}else {\n\t\t\treturn column.definition.frozen;\n\t\t}\n\t}\n\t\n\t//layout calculation rows\n\tlayoutCalcRows(){\n\t\tif(this.table.modExists(\"columnCalcs\")){\n\t\t\tif(this.table.modules.columnCalcs.topInitialized && this.table.modules.columnCalcs.topRow){\n\t\t\t\tthis.layoutRow(this.table.modules.columnCalcs.topRow);\n\t\t\t}\n\t\t\t\n\t\t\tif(this.table.modules.columnCalcs.botInitialized && this.table.modules.columnCalcs.botRow){\n\t\t\t\tthis.layoutRow(this.table.modules.columnCalcs.botRow);\n\t\t\t}\n\t\t\t\n\t\t\tif(this.table.modExists(\"groupRows\")){\n\t\t\t\tthis.layoutGroupCalcs(this.table.modules.groupRows.getGroups());\n\t\t\t}\n\t\t}\n\t}\n\t\n\tlayoutGroupCalcs(groups){\n\t\tgroups.forEach((group) => {\n\t\t\tif(group.calcs.top){\n\t\t\t\tthis.layoutRow(group.calcs.top);\n\t\t\t}\n\t\t\t\n\t\t\tif(group.calcs.bottom){\n\t\t\t\tthis.layoutRow(group.calcs.bottom);\n\t\t\t}\n\t\t\t\n\t\t\tif(group.groupList && group.groupList.length){\n\t\t\t\tthis.layoutGroupCalcs(group.groupList);\n\t\t\t}\n\t\t});\n\t}\n\t\n\t//calculate column positions and layout headers\n\tlayoutColumnPosition(allCells){\n\t\tvar leftParents = [];\n\t\t\n\t\tvar leftMargin = 0;\n\t\tvar rightMargin = 0;\n\t\t\n\t\tthis.leftColumns.forEach((column, i) => {\t\n\t\t\tcolumn.modules.frozen.marginValue = leftMargin;\n\t\t\tcolumn.modules.frozen.margin = column.modules.frozen.marginValue + \"px\";\n\t\t\t\n\t\t\tif(column.visible){\n\t\t\t\tleftMargin += column.getWidth();\n\t\t\t}\n\t\t\t\n\t\t\tif(i == this.leftColumns.length - 1){\n\t\t\t\tcolumn.modules.frozen.edge = true;\n\t\t\t}else {\n\t\t\t\tcolumn.modules.frozen.edge = false;\n\t\t\t}\n\t\t\t\n\t\t\tif(column.parent.isGroup){\n\t\t\t\tvar parentEl = this.getColGroupParentElement(column);\n\t\t\t\tif(!leftParents.includes(parentEl)){\n\t\t\t\t\tthis.layoutElement(parentEl, column);\n\t\t\t\t\tleftParents.push(parentEl);\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tparentEl.classList.toggle(\"tabulator-frozen-left\",  column.modules.frozen.edge && column.modules.frozen.position === \"left\");\n\t\t\t\tparentEl.classList.toggle(\"tabulator-frozen-right\", column.modules.frozen.edge && column.modules.frozen.position === \"right\");\n\t\t\t}else {\n\t\t\t\tthis.layoutElement(column.getElement(), column);\n\t\t\t}\n\t\t\t\n\t\t\tif(allCells){\n\t\t\t\tcolumn.cells.forEach((cell) => {\n\t\t\t\t\tthis.layoutElement(cell.getElement(true), column);\n\t\t\t\t});\n\t\t\t}\n\t\t});\n\t\t\n\t\tthis.rightColumns.forEach((column, i) => {\n\t\t\t\n\t\t\tcolumn.modules.frozen.marginValue = rightMargin;\n\t\t\tcolumn.modules.frozen.margin = column.modules.frozen.marginValue + \"px\";\n\t\t\t\n\t\t\tif(column.visible){\n\t\t\t\trightMargin += column.getWidth();\n\t\t\t}\n\t\t\t\n\t\t\tif(i == this.rightColumns.length - 1){\n\t\t\t\tcolumn.modules.frozen.edge = true;\n\t\t\t}else {\n\t\t\t\tcolumn.modules.frozen.edge = false;\n\t\t\t}\n\t\t\t\n\t\t\tif(column.parent.isGroup){\n\t\t\t\tthis.layoutElement(this.getColGroupParentElement(column), column);\n\t\t\t}else {\n\t\t\t\tthis.layoutElement(column.getElement(), column);\n\t\t\t}\n\t\t\t\n\t\t\tif(allCells){\n\t\t\t\tcolumn.cells.forEach((cell) => {\n\t\t\t\t\tthis.layoutElement(cell.getElement(true), column);\n\t\t\t\t});\n\t\t\t}\n\t\t});\n\t}\n\t\n\tgetColGroupParentElement(column){\n\t\treturn column.parent.isGroup ? this.getColGroupParentElement(column.parent) : column.getElement();\n\t}\n\t\n\t//layout columns appropriately\n\tlayout(){\t\n\t\tif(this.active && !this.blocked){\n\t\t\t//calculate left columns\n\t\t\tthis.layoutColumnPosition();\n\t\t\t\n\t\t\tthis.reinitializeRows();\n\t\t\t\n\t\t\tthis.layoutCalcRows();\n\t\t}\n\t}\n\t\n\treinitializeRows(){\n\t\tvar visibleRows = this.table.rowManager.getVisibleRows(true);\n\t\tvar otherRows = this.table.rowManager.getRows().filter(row => !visibleRows.includes(row));\n\t\t\n\t\totherRows.forEach((row) =>{\n\t\t\trow.deinitialize();\n\t\t});\n\t\t\n\t\tvisibleRows.forEach((row) =>{\n\t\t\tif(row.type === \"row\"){\n\t\t\t\tthis.layoutRow(row);\n\t\t\t}\n\t\t});\n\t}\n\t\n\tlayoutRow(row){\n\t\tif(this.table.options.layout === \"fitDataFill\" && this.rightColumns.length){\n\t\t\tthis.table.rowManager.getTableElement().style.minWidth = \"calc(100% - \" + this.rightMargin + \")\";\n\t\t}\n\t\t\n\t\tthis.leftColumns.forEach((column) => {\n\t\t\tvar cell = row.getCell(column);\n\t\t\t\n\t\t\tif(cell){\n\t\t\t\tthis.layoutElement(cell.getElement(true), column);\n\t\t\t}\n\t\t});\n\t\t\n\t\tthis.rightColumns.forEach((column) => {\n\t\t\tvar cell = row.getCell(column);\n\t\t\t\n\t\t\tif(cell){\n\t\t\t\tthis.layoutElement(cell.getElement(true), column);\n\t\t\t}\n\t\t});\n\t}\n\t\n\tlayoutElement(element, column){\n\t\tvar position;\n\t\t\n\t\tif(column.modules.frozen && element){\n\t\t\telement.style.position = \"sticky\";\n\n\t\t\tif(this.table.rtl){\n\t\t\t\tposition = column.modules.frozen.position === \"left\" ? \"right\" : \"left\";\n\t\t\t}else {\n\t\t\t\tposition = column.modules.frozen.position;\n\t\t\t}\n\t\t\n\t\t\telement.style[position] = column.modules.frozen.margin;\n\n\t\t\telement.classList.add(\"tabulator-frozen\");\n\t\t\t\n\t\t\telement.classList.toggle(\"tabulator-frozen-left\",  column.modules.frozen.edge && column.modules.frozen.position === \"left\");\n\t\t\telement.classList.toggle(\"tabulator-frozen-right\", column.modules.frozen.edge && column.modules.frozen.position === \"right\");\n\t\t}\n\t}\n\n\tadjustForScrollbar(width){\n\t\tif(this.rightColumns.length){\n\t\t\tthis.table.columnManager.getContentsElement().style.width = \"calc(100% - \" + width + \"px)\";\n\t\t}\n\t}\n\t\n\t_calcSpace(columns, index){\n\t\tvar width = 0;\n\t\t\n\t\tfor (let i = 0; i < index; i++){\n\t\t\tif(columns[i].visible){\n\t\t\t\twidth += columns[i].getWidth();\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn width;\n\t}\n}\n\nFrozenColumns.moduleName = \"frozenColumns\";\n\nclass FrozenRows extends Module{\n\n\tconstructor(table){\n\t\tsuper(table);\n\n\t\tthis.topElement = document.createElement(\"div\");\n\t\tthis.rows = [];\n\n\t\t//register component functions\n\t\tthis.registerComponentFunction(\"row\", \"freeze\", this.freezeRow.bind(this));\n\t\tthis.registerComponentFunction(\"row\", \"unfreeze\", this.unfreezeRow.bind(this));\n\t\tthis.registerComponentFunction(\"row\", \"isFrozen\", this.isRowFrozen.bind(this));\n\n\t\t//register table options\n\t\tthis.registerTableOption(\"frozenRowsField\", \"id\"); //field to choose frozen rows by\n\t\tthis.registerTableOption(\"frozenRows\", false); //holder for frozen row identifiers\n\t}\n\n\tinitialize(){\n\t\tvar\tfragment = document.createDocumentFragment();\n\t\t\n\t\tthis.rows = [];\n\n\t\tthis.topElement.classList.add(\"tabulator-frozen-rows-holder\");\n\t\t\n\t\tfragment.appendChild(document.createElement(\"br\"));\n\t\tfragment.appendChild(this.topElement);\n\n\t\t// this.table.columnManager.element.append(this.topElement);\n\t\tthis.table.columnManager.getContentsElement().insertBefore(fragment, this.table.columnManager.headersElement.nextSibling);\n\n\t\tthis.subscribe(\"row-deleting\", this.detachRow.bind(this));\n\t\tthis.subscribe(\"rows-visible\", this.visibleRows.bind(this));\n\n\t\tthis.registerDisplayHandler(this.getRows.bind(this), 10);\n\n\t\tif(this.table.options.frozenRows){\n\t\t\tthis.subscribe(\"data-processed\", this.initializeRows.bind(this));\n\t\t\tthis.subscribe(\"row-added\", this.initializeRow.bind(this));\n\t\t\tthis.subscribe(\"table-redrawing\", this.resizeHolderWidth.bind(this));\n\t\t\tthis.subscribe(\"column-resized\", this.resizeHolderWidth.bind(this));\n\t\t\tthis.subscribe(\"column-show\", this.resizeHolderWidth.bind(this));\n\t\t\tthis.subscribe(\"column-hide\", this.resizeHolderWidth.bind(this));\n\t\t}\n\n\t\tthis.resizeHolderWidth();\n\t}\n\n\tresizeHolderWidth(){\n\t\tthis.topElement.style.minWidth = this.table.columnManager.headersElement.offsetWidth + \"px\";\n\t}\n\n\tinitializeRows(){\n\t\tthis.table.rowManager.getRows().forEach((row) => {\n\t\t\tthis.initializeRow(row);\n\t\t});\n\t}\n\n\tinitializeRow(row){\n\t\tvar frozenRows = this.table.options.frozenRows,\n\t\trowType = typeof frozenRows;\n\n\t\tif(rowType === \"number\"){\n\t\t\tif(row.getPosition() && (row.getPosition() + this.rows.length) <= frozenRows){\n\t\t\t\tthis.freezeRow(row);\n\t\t\t}\n\t\t}else if(rowType === \"function\"){\n\t\t\tif(frozenRows.call(this.table, row.getComponent())){\n\t\t\t\tthis.freezeRow(row);\n\t\t\t}\n\t\t}else if(Array.isArray(frozenRows)){\n\t\t\tif(frozenRows.includes(row.data[this.options(\"frozenRowsField\")])){\n\t\t\t\tthis.freezeRow(row);\n\t\t\t}\n\t\t}\n\t}\n\n\tisRowFrozen(row){\n\t\tvar index = this.rows.indexOf(row);\n\t\treturn index > -1;\n\t}\n\n\tisFrozen(){\n\t\treturn !!this.rows.length;\n\t}\n\n\tvisibleRows(viewable, rows){\n\t\tthis.rows.forEach((row) => {\n\t\t\trows.push(row);\n\t\t});\n\n\t\treturn rows;\n\t}\n\n\t//filter frozen rows out of display data\n\tgetRows(rows){\n\t\tvar output = rows.slice(0);\n\n\t\tthis.rows.forEach(function(row){\n\t\t\tvar index = output.indexOf(row);\n\n\t\t\tif(index > -1){\n\t\t\t\toutput.splice(index, 1);\n\t\t\t}\n\t\t});\n\n\t\treturn output;\n\t}\n\n\tfreezeRow(row){\n\t\tif(!row.modules.frozen){\n\t\t\trow.modules.frozen = true;\n\t\t\tthis.topElement.appendChild(row.getElement());\n\t\t\trow.initialize();\n\t\t\trow.normalizeHeight();\n\t\t\n\t\t\tthis.rows.push(row);\n\n\t\t\tthis.refreshData(false, \"display\");\n\n\t\t\tthis.table.rowManager.adjustTableSize();\n\n\t\t\tthis.styleRows();\n\n\t\t}else {\n\t\t\tconsole.warn(\"Freeze Error - Row is already frozen\");\n\t\t}\n\t}\n\n\tunfreezeRow(row){\n\t\tif(row.modules.frozen){\n\n\t\t\trow.modules.frozen = false;\n\n\t\t\tthis.detachRow(row);\n\n\t\t\tthis.table.rowManager.adjustTableSize();\n\n\t\t\tthis.refreshData(false, \"display\");\n\n\t\t\tif(this.rows.length){\n\t\t\t\tthis.styleRows();\n\t\t\t}\n\n\t\t}else {\n\t\t\tconsole.warn(\"Freeze Error - Row is already unfrozen\");\n\t\t}\n\t}\n\n\tdetachRow(row){\n\t\tvar index = this.rows.indexOf(row);\n\n\t\tif(index > -1){\n\t\t\tvar rowEl = row.getElement();\n\n\t\t\tif(rowEl.parentNode){\n\t\t\t\trowEl.parentNode.removeChild(rowEl);\n\t\t\t}\n\n\t\t\tthis.rows.splice(index, 1);\n\t\t}\n\t}\n\n\tstyleRows(row){\n\t\tthis.rows.forEach((row, i) => {\n\t\t\tthis.table.rowManager.styleRow(row, i);\n\t\t});\n\t}\n}\n\nFrozenRows.moduleName = \"frozenRows\";\n\n//public group object\nclass GroupComponent {\n\tconstructor (group){\n\t\tthis._group = group;\n\t\tthis.type = \"GroupComponent\";\n\n\t\treturn new Proxy(this, {\n\t\t\tget: function(target, name, receiver) {\n\t\t\t\tif (typeof target[name] !== \"undefined\") {\n\t\t\t\t\treturn target[name];\n\t\t\t\t}else {\n\t\t\t\t\treturn target._group.groupManager.table.componentFunctionBinder.handle(\"group\", target._group, name);\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\t}\n\n\tgetKey(){\n\t\treturn this._group.key;\n\t}\n\n\tgetField(){\n\t\treturn this._group.field;\n\t}\n\n\tgetElement(){\n\t\treturn this._group.element;\n\t}\n\n\tgetRows(){\n\t\treturn this._group.getRows(true);\n\t}\n\n\tgetSubGroups(){\n\t\treturn this._group.getSubGroups(true);\n\t}\n\n\tgetParentGroup(){\n\t\treturn this._group.parent ? this._group.parent.getComponent() : false;\n\t}\n\n\tisVisible(){\n\t\treturn this._group.visible;\n\t}\n\n\tshow(){\n\t\tthis._group.show();\n\t}\n\n\thide(){\n\t\tthis._group.hide();\n\t}\n\n\ttoggle(){\n\t\tthis._group.toggleVisibility();\n\t}\n\n\tscrollTo(position, ifVisible){\n\t\treturn this._group.groupManager.table.rowManager.scrollToRow(this._group, position, ifVisible);\n\t}\n\n\t_getSelf(){\n\t\treturn this._group;\n\t}\n\n\tgetTable(){\n\t\treturn this._group.groupManager.table;\n\t}\n}\n\n//Group functions\nclass Group{\n\t\n\tconstructor(groupManager, parent, level, key, field, generator, oldGroup){\n\t\tthis.groupManager = groupManager;\n\t\tthis.parent = parent;\n\t\tthis.key = key;\n\t\tthis.level = level;\n\t\tthis.field = field;\n\t\tthis.hasSubGroups = level < (groupManager.groupIDLookups.length - 1);\n\t\tthis.addRow = this.hasSubGroups ? this._addRowToGroup : this._addRow;\n\t\tthis.type = \"group\"; //type of element\n\t\tthis.old = oldGroup;\n\t\tthis.rows = [];\n\t\tthis.groups = [];\n\t\tthis.groupList = [];\n\t\tthis.generator = generator;\n\t\tthis.element = false;\n\t\tthis.elementContents = false;\n\t\tthis.height = 0;\n\t\tthis.outerHeight = 0;\n\t\tthis.initialized = false;\n\t\tthis.calcs = {};\n\t\tthis.initialized = false;\n\t\tthis.modules = {};\n\t\tthis.arrowElement = false;\n\t\t\n\t\tthis.visible = oldGroup ? oldGroup.visible : (typeof groupManager.startOpen[level] !== \"undefined\" ? groupManager.startOpen[level] : groupManager.startOpen[0]);\n\t\t\n\t\tthis.component = null;\n\t\t\n\t\tthis.createElements();\n\t\tthis.addBindings();\n\t\t\n\t\tthis.createValueGroups();\n\t}\n\t\n\twipe(elementsOnly){\n\t\tif(!elementsOnly){\n\t\t\tif(this.groupList.length){\n\t\t\t\tthis.groupList.forEach(function(group){\n\t\t\t\t\tgroup.wipe();\n\t\t\t\t});\n\t\t\t}else {\n\t\t\t\tthis.rows.forEach((row) => {\n\t\t\t\t\tif(row.modules){\n\t\t\t\t\t\tdelete row.modules.group;\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t}\n\t\t}\n\t\t\n\t\tthis.element = false;\n\t\tthis.arrowElement = false;\n\t\tthis.elementContents = false;\n\t}\n\t\n\tcreateElements(){\n\t\tvar arrow = document.createElement(\"div\");\n\t\tarrow.classList.add(\"tabulator-arrow\");\n\t\t\n\t\tthis.element = document.createElement(\"div\");\n\t\tthis.element.classList.add(\"tabulator-row\");\n\t\tthis.element.classList.add(\"tabulator-group\");\n\t\tthis.element.classList.add(\"tabulator-group-level-\" + this.level);\n\t\tthis.element.setAttribute(\"role\", \"rowgroup\");\n\t\t\n\t\tthis.arrowElement = document.createElement(\"div\");\n\t\tthis.arrowElement.classList.add(\"tabulator-group-toggle\");\n\t\tthis.arrowElement.appendChild(arrow);\n\t\t\n\t\t//setup movable rows\n\t\tif(this.groupManager.table.options.movableRows !== false && this.groupManager.table.modExists(\"moveRow\")){\n\t\t\tthis.groupManager.table.modules.moveRow.initializeGroupHeader(this);\n\t\t}\n\t}\n\t\n\tcreateValueGroups(){\n\t\tvar level = this.level + 1;\n\t\tif(this.groupManager.allowedValues && this.groupManager.allowedValues[level]){\n\t\t\tthis.groupManager.allowedValues[level].forEach((value) => {\n\t\t\t\tthis._createGroup(value, level);\n\t\t\t});\n\t\t}\n\t}\n\t\n\taddBindings(){\n\t\tvar toggleElement;\n\t\t\n\t\tif(this.groupManager.table.options.groupToggleElement){\n\t\t\ttoggleElement = this.groupManager.table.options.groupToggleElement == \"arrow\" ? this.arrowElement : this.element;\n\t\t\t\n\t\t\ttoggleElement.addEventListener(\"click\", (e) => {\n\t\t\t\tif(this.groupManager.table.options.groupToggleElement === \"arrow\"){\n\t\t\t\t\te.stopPropagation();\n\t\t\t\t\te.stopImmediatePropagation();\n\t\t\t\t}\n\n\t\t\t\t//allow click event to propagate before toggling visibility\n\t\t\t\tsetTimeout(() => {\n\t\t\t\t\tthis.toggleVisibility();\n\t\t\t\t});\n\t\t\t});\n\t\t}\n\t}\n\t\n\t_createGroup(groupID, level){\n\t\tvar groupKey = level + \"_\" + groupID;\n\t\tvar group = new Group(this.groupManager, this, level, groupID,  this.groupManager.groupIDLookups[level].field, this.groupManager.headerGenerator[level] || this.groupManager.headerGenerator[0], this.old ? this.old.groups[groupKey] : false);\n\t\t\n\t\tthis.groups[groupKey] = group;\n\t\tthis.groupList.push(group);\n\t}\n\t\n\t_addRowToGroup(row){\n\t\t\n\t\tvar level = this.level + 1;\n\t\t\n\t\tif(this.hasSubGroups){\n\t\t\tvar groupID = this.groupManager.groupIDLookups[level].func(row.getData()),\n\t\t\tgroupKey = level + \"_\" + groupID;\n\t\t\t\n\t\t\tif(this.groupManager.allowedValues && this.groupManager.allowedValues[level]){\n\t\t\t\tif(this.groups[groupKey]){\n\t\t\t\t\tthis.groups[groupKey].addRow(row);\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tif(!this.groups[groupKey]){\n\t\t\t\t\tthis._createGroup(groupID, level);\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tthis.groups[groupKey].addRow(row);\n\t\t\t}\n\t\t}\n\t}\n\t\n\t_addRow(row){\n\t\tthis.rows.push(row);\n\t\trow.modules.group = this;\n\t}\n\t\n\tinsertRow(row, to, after){\n\t\tvar data = this.conformRowData({});\n\t\t\n\t\trow.updateData(data);\n\t\t\n\t\tvar toIndex = this.rows.indexOf(to);\n\t\t\n\t\tif(toIndex > -1){\n\t\t\tif(after){\n\t\t\t\tthis.rows.splice(toIndex+1, 0, row);\n\t\t\t}else {\n\t\t\t\tthis.rows.splice(toIndex, 0, row);\n\t\t\t}\n\t\t}else {\n\t\t\tif(after){\n\t\t\t\tthis.rows.push(row);\n\t\t\t}else {\n\t\t\t\tthis.rows.unshift(row);\n\t\t\t}\n\t\t}\n\t\t\n\t\trow.modules.group = this;\n\t\t\n\t\t// this.generateGroupHeaderContents();\n\t\t\n\t\tif(this.groupManager.table.modExists(\"columnCalcs\") && this.groupManager.table.options.columnCalcs != \"table\"){\n\t\t\tthis.groupManager.table.modules.columnCalcs.recalcGroup(this);\n\t\t}\n\t\t\n\t\tthis.groupManager.updateGroupRows(true);\n\t}\n\t\n\tscrollHeader(left){\n\t\tif(this.arrowElement){\n\t\t\tthis.arrowElement.style.marginLeft = left;\n\t\t\t\n\t\t\tthis.groupList.forEach(function(child){\n\t\t\t\tchild.scrollHeader(left);\n\t\t\t});\n\t\t}\n\t}\n\t\n\tgetRowIndex(row){}\n\t\n\t//update row data to match grouping constraints\n\tconformRowData(data){\n\t\tif(this.field){\n\t\t\tdata[this.field] = this.key;\n\t\t}else {\n\t\t\tconsole.warn(\"Data Conforming Error - Cannot conform row data to match new group as groupBy is a function\");\n\t\t}\n\t\t\n\t\tif(this.parent){\n\t\t\tdata = this.parent.conformRowData(data);\n\t\t}\n\t\t\n\t\treturn data;\n\t}\n\t\n\tremoveRow(row){\n\t\tvar index = this.rows.indexOf(row);\n\t\tvar el = row.getElement();\n\t\t\n\t\tif(index > -1){\n\t\t\tthis.rows.splice(index, 1);\n\t\t}\n\t\t\n\t\tif(!this.groupManager.table.options.groupValues && !this.rows.length){\n\t\t\tif(this.parent){\n\t\t\t\tthis.parent.removeGroup(this);\n\t\t\t}else {\n\t\t\t\tthis.groupManager.removeGroup(this);\n\t\t\t}\t\t\n\t\t\t\n\t\t\tthis.groupManager.updateGroupRows(true);\n\t\t\t\n\t\t}else {\n\t\t\t\n\t\t\tif(el.parentNode){\n\t\t\t\tel.parentNode.removeChild(el);\n\t\t\t}\n\t\t\t\n\t\t\tif(!this.groupManager.blockRedraw){\n\t\t\t\tthis.generateGroupHeaderContents();\n\t\t\t\t\n\t\t\t\tif(this.groupManager.table.modExists(\"columnCalcs\") && this.groupManager.table.options.columnCalcs != \"table\"){\n\t\t\t\t\tthis.groupManager.table.modules.columnCalcs.recalcGroup(this);\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t}\n\t}\n\t\n\tremoveGroup(group){\n\t\tvar groupKey = group.level + \"_\" + group.key,\n\t\tindex;\n\t\t\n\t\tif(this.groups[groupKey]){\n\t\t\tdelete this.groups[groupKey];\n\t\t\t\n\t\t\tindex = this.groupList.indexOf(group);\n\t\t\t\n\t\t\tif(index > -1){\n\t\t\t\tthis.groupList.splice(index, 1);\n\t\t\t}\n\t\t\t\n\t\t\tif(!this.groupList.length){\n\t\t\t\tif(this.parent){\n\t\t\t\t\tthis.parent.removeGroup(this);\n\t\t\t\t}else {\n\t\t\t\t\tthis.groupManager.removeGroup(this);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t\n\tgetHeadersAndRows(){\n\t\tvar output = [];\n\t\t\n\t\toutput.push(this);\n\t\t\n\t\tthis._visSet();\n\t\t\n\t\t\n\t\tif(this.calcs.top){\n\t\t\tthis.calcs.top.detachElement();\n\t\t\tthis.calcs.top.deleteCells();\n\t\t}\n\t\t\n\t\tif(this.calcs.bottom){\n\t\t\tthis.calcs.bottom.detachElement();\n\t\t\tthis.calcs.bottom.deleteCells();\n\t\t}\n\t\t\n\t\t\n\t\t\n\t\tif(this.visible){\n\t\t\tif(this.groupList.length){\n\t\t\t\tthis.groupList.forEach(function(group){\n\t\t\t\t\toutput = output.concat(group.getHeadersAndRows());\n\t\t\t\t});\n\t\t\t\t\n\t\t\t}else {\n\t\t\t\tif(this.groupManager.table.options.columnCalcs != \"table\" && this.groupManager.table.modExists(\"columnCalcs\") && this.groupManager.table.modules.columnCalcs.hasTopCalcs()){\n\t\t\t\t\tthis.calcs.top = this.groupManager.table.modules.columnCalcs.generateTopRow(this.rows);\n\t\t\t\t\toutput.push(this.calcs.top);\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\toutput = output.concat(this.rows);\n\t\t\t\t\n\t\t\t\tif(this.groupManager.table.options.columnCalcs != \"table\" &&  this.groupManager.table.modExists(\"columnCalcs\") && this.groupManager.table.modules.columnCalcs.hasBottomCalcs()){\n\t\t\t\t\tthis.calcs.bottom = this.groupManager.table.modules.columnCalcs.generateBottomRow(this.rows);\n\t\t\t\t\toutput.push(this.calcs.bottom);\n\t\t\t\t}\n\t\t\t}\n\t\t}else {\n\t\t\tif(!this.groupList.length && this.groupManager.table.options.columnCalcs != \"table\"){\n\t\t\t\t\n\t\t\t\tif(this.groupManager.table.modExists(\"columnCalcs\")){\n\t\t\t\t\tif(this.groupManager.table.modules.columnCalcs.hasTopCalcs()){\n\t\t\t\t\t\tif(this.groupManager.table.options.groupClosedShowCalcs){\n\t\t\t\t\t\t\tthis.calcs.top = this.groupManager.table.modules.columnCalcs.generateTopRow(this.rows);\n\t\t\t\t\t\t\toutput.push(this.calcs.top);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\tif(this.groupManager.table.modules.columnCalcs.hasBottomCalcs()){\t\t\t\t\t\t\n\t\t\t\t\t\tif(this.groupManager.table.options.groupClosedShowCalcs){\n\t\t\t\t\t\t\tthis.calcs.bottom = this.groupManager.table.modules.columnCalcs.generateBottomRow(this.rows);\n\t\t\t\t\t\t\toutput.push(this.calcs.bottom);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t}\n\t\t\n\t\treturn output;\n\t}\n\t\n\tgetData(visible, transform){\n\t\tvar output = [];\n\t\t\n\t\tthis._visSet();\n\t\t\n\t\tif(!visible || (visible && this.visible)){\n\t\t\tthis.rows.forEach((row) => {\n\t\t\t\toutput.push(row.getData(transform || \"data\"));\n\t\t\t});\n\t\t}\n\t\t\n\t\treturn output;\n\t}\n\t\n\tgetRowCount(){\n\t\tvar count = 0;\n\t\t\n\t\tif(this.groupList.length){\n\t\t\tthis.groupList.forEach((group) => {\n\t\t\t\tcount += group.getRowCount();\n\t\t\t});\n\t\t}else {\n\t\t\tcount = this.rows.length;\n\t\t}\n\t\treturn count;\n\t}\n\n\t\n\ttoggleVisibility(){\n\t\tif(this.visible){\n\t\t\tthis.hide();\n\t\t}else {\n\t\t\tthis.show();\n\t\t}\n\t}\n\t\n\thide(){\n\t\tthis.visible = false;\n\t\t\n\t\tif(this.groupManager.table.rowManager.getRenderMode() == \"basic\" && !this.groupManager.table.options.pagination){\n\t\t\t\n\t\t\tthis.element.classList.remove(\"tabulator-group-visible\");\n\t\t\t\n\t\t\tif(this.groupList.length){\n\t\t\t\tthis.groupList.forEach((group) => {\n\t\t\t\t\t\n\t\t\t\t\tvar rows = group.getHeadersAndRows();\n\t\t\t\t\t\n\t\t\t\t\trows.forEach((row) => {\n\t\t\t\t\t\trow.detachElement();\n\t\t\t\t\t});\n\t\t\t\t});\n\t\t\t\t\n\t\t\t}else {\n\t\t\t\tthis.rows.forEach((row) => {\n\t\t\t\t\tvar rowEl = row.getElement();\n\t\t\t\t\trowEl.parentNode.removeChild(rowEl);\n\t\t\t\t});\n\t\t\t}\n\t\t\t\n\t\t\tthis.groupManager.updateGroupRows(true);\n\t\t\t\n\t\t}else {\n\t\t\tthis.groupManager.updateGroupRows(true);\n\t\t}\n\t\t\n\t\tthis.groupManager.table.externalEvents.dispatch(\"groupVisibilityChanged\", this.getComponent(), false);\n\t}\n\t\n\tshow(){\n\t\tthis.visible = true;\n\t\t\n\t\tif(this.groupManager.table.rowManager.getRenderMode() == \"basic\" && !this.groupManager.table.options.pagination){\n\t\t\t\n\t\t\tthis.element.classList.add(\"tabulator-group-visible\");\n\t\t\t\n\t\t\tvar prev = this.generateElement();\n\t\t\t\n\t\t\tif(this.groupList.length){\n\t\t\t\tthis.groupList.forEach((group) => {\n\t\t\t\t\tvar rows = group.getHeadersAndRows();\n\t\t\t\t\t\n\t\t\t\t\trows.forEach((row) => {\n\t\t\t\t\t\tvar rowEl = row.getElement();\n\t\t\t\t\t\tprev.parentNode.insertBefore(rowEl, prev.nextSibling);\n\t\t\t\t\t\trow.initialize();\n\t\t\t\t\t\tprev = rowEl;\n\t\t\t\t\t});\n\t\t\t\t});\n\t\t\t\t\n\t\t\t}else {\n\t\t\t\tthis.rows.forEach((row) => {\n\t\t\t\t\tvar rowEl = row.getElement();\n\t\t\t\t\tprev.parentNode.insertBefore(rowEl, prev.nextSibling);\n\t\t\t\t\trow.initialize();\n\t\t\t\t\tprev = rowEl;\n\t\t\t\t});\n\t\t\t}\n\t\t\t\n\t\t\tthis.groupManager.updateGroupRows(true);\n\t\t}else {\n\t\t\tthis.groupManager.updateGroupRows(true);\n\t\t}\n\t\t\n\t\tthis.groupManager.table.externalEvents.dispatch(\"groupVisibilityChanged\", this.getComponent(), true);\n\t}\n\t\n\t_visSet(){\n\t\tvar data = [];\n\t\t\n\t\tif(typeof this.visible == \"function\"){\n\t\t\t\n\t\t\tthis.rows.forEach(function(row){\n\t\t\t\tdata.push(row.getData());\n\t\t\t});\n\t\t\t\n\t\t\tthis.visible = this.visible(this.key, this.getRowCount(), data, this.getComponent());\n\t\t}\n\t}\n\t\n\tgetRowGroup(row){\n\t\tvar match = false;\n\t\tif(this.groupList.length){\n\t\t\tthis.groupList.forEach(function(group){\n\t\t\t\tvar result = group.getRowGroup(row);\n\t\t\t\t\n\t\t\t\tif(result){\n\t\t\t\t\tmatch = result;\n\t\t\t\t}\n\t\t\t});\n\t\t}else {\n\t\t\tif(this.rows.find(function(item){\n\t\t\t\treturn item === row;\n\t\t\t})){\n\t\t\t\tmatch = this;\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn match;\n\t}\n\t\n\tgetSubGroups(component){\n\t\tvar output = [];\n\t\t\n\t\tthis.groupList.forEach(function(child){\n\t\t\toutput.push(component ? child.getComponent() : child);\n\t\t});\n\t\t\n\t\treturn output;\n\t}\n\t\n\tgetRows(component, includeChildren){\n\t\tvar output = [];\n\t\t\n\t\tif(includeChildren && this.groupList.length){\n\t\t\tthis.groupList.forEach((group) => {\n\t\t\t\toutput = output.concat(group.getRows(component, includeChildren));\n\t\t\t});\n\t\t}else {\n\t\t\tthis.rows.forEach(function(row){\n\t\t\t\toutput.push(component ? row.getComponent() : row);\n\t\t\t});\n\t\t}\n\t\t\n\t\treturn output;\n\t}\n\t\n\tgenerateGroupHeaderContents(){\n\t\tvar data = [];\n\t\t\n\t\tvar rows = this.getRows(false, true);\n\t\t\n\t\trows.forEach(function(row){\n\t\t\tdata.push(row.getData());\n\t\t});\n\t\t\n\t\tthis.elementContents = this.generator(this.key, this.getRowCount(), data, this.getComponent());\n\t\t\n\t\twhile(this.element.firstChild) this.element.removeChild(this.element.firstChild);\n\t\t\n\t\tif(typeof this.elementContents === \"string\"){\n\t\t\tthis.element.innerHTML = this.elementContents;\n\t\t}else {\n\t\t\tthis.element.appendChild(this.elementContents);\n\t\t}\n\t\t\n\t\tthis.element.insertBefore(this.arrowElement, this.element.firstChild);\n\t}\n\t\n\tgetPath(path = []) {\n\t\tpath.unshift(this.key);\n\t\tif(this.parent) {\n\t\t\tthis.parent.getPath(path);\n\t\t}\n\t\treturn path;\n\t}\n\t\n\t////////////// Standard Row Functions //////////////\n\t\n\tgetElement(){\n\t\treturn this.elementContents ? this.element : this.generateElement();\n\t}\n\t\n\tgenerateElement(){\n\t\tthis.addBindings = false;\n\t\t\n\t\tthis._visSet();\n\t\t\n\t\tif(this.visible){\n\t\t\tthis.element.classList.add(\"tabulator-group-visible\");\n\t\t}else {\n\t\t\tthis.element.classList.remove(\"tabulator-group-visible\");\n\t\t}\n\t\t\n\t\tfor(var i = 0; i < this.element.childNodes.length; ++i){\n\t\t\tthis.element.childNodes[i].parentNode.removeChild(this.element.childNodes[i]);\n\t\t}\n\t\t\n\t\tthis.generateGroupHeaderContents();\n\t\t\n\t\t// this.addBindings();\n\t\t\n\t\treturn this.element;\n\t}\n\t\n\tdetachElement(){\n\t\tif (this.element && this.element.parentNode){\n\t\t\tthis.element.parentNode.removeChild(this.element);\n\t\t}\n\t}\n\t\n\t//normalize the height of elements in the row\n\tnormalizeHeight(){\n\t\tthis.setHeight(this.element.clientHeight);\n\t}\n\t\n\tinitialize(force){\n\t\tif(!this.initialized || force){\n\t\t\tthis.normalizeHeight();\n\t\t\tthis.initialized = true;\n\t\t}\n\t}\n\t\n\treinitialize(){\n\t\tthis.initialized = false;\n\t\tthis.height = 0;\n\t\t\n\t\tif(Helpers.elVisible(this.element)){\n\t\t\tthis.initialize(true);\n\t\t}\n\t}\n\t\n\tsetHeight(height){\n\t\tif(this.height != height){\n\t\t\tthis.height = height;\n\t\t\tthis.outerHeight = this.element.offsetHeight;\n\t\t}\n\t}\n\t\n\t//return rows outer height\n\tgetHeight(){\n\t\treturn this.outerHeight;\n\t}\n\t\n\tgetGroup(){\n\t\treturn this;\n\t}\n\t\n\treinitializeHeight(){}\n\t\n\tcalcHeight(){}\n\t\n\tsetCellHeight(){}\n\t\n\tclearCellHeight(){}\n\t\n\tdeinitializeHeight(){}\n\n\trendered(){}\n\t\n\t//////////////// Object Generation /////////////////\n\tgetComponent(){\n\t\tif(!this.component){\n\t\t\tthis.component = new GroupComponent(this);\n\t\t}\n\t\t\n\t\treturn this.component;\n\t}\n}\n\nclass GroupRows extends Module{\n\t\n\tconstructor(table){\n\t\tsuper(table);\n\t\t\n\t\tthis.groupIDLookups = false; //enable table grouping and set field to group by\n\t\tthis.startOpen = [function(){return false;}]; //starting state of group\n\t\tthis.headerGenerator = [function(){return \"\";}];\n\t\tthis.groupList = []; //ordered list of groups\n\t\tthis.allowedValues = false;\n\t\tthis.groups = {}; //hold row groups\n\t\t\n\t\tthis.displayHandler = this.getRows.bind(this);\n\n\t\tthis.blockRedraw = false;\n\t\t\n\t\t//register table options\n\t\tthis.registerTableOption(\"groupBy\", false); //enable table grouping and set field to group by\n\t\tthis.registerTableOption(\"groupStartOpen\", true); //starting state of group\n\t\tthis.registerTableOption(\"groupValues\", false);\n\t\tthis.registerTableOption(\"groupUpdateOnCellEdit\", false);\n\t\tthis.registerTableOption(\"groupHeader\", false); //header generation function\n\t\tthis.registerTableOption(\"groupHeaderPrint\", null);\n\t\tthis.registerTableOption(\"groupHeaderClipboard\", null);\n\t\tthis.registerTableOption(\"groupHeaderHtmlOutput\", null);\n\t\tthis.registerTableOption(\"groupHeaderDownload\", null);\n\t\tthis.registerTableOption(\"groupToggleElement\", \"arrow\");\n\t\tthis.registerTableOption(\"groupClosedShowCalcs\", false);\n\t\t\n\t\t//register table functions\n\t\tthis.registerTableFunction(\"setGroupBy\", this.setGroupBy.bind(this));\n\t\tthis.registerTableFunction(\"setGroupValues\", this.setGroupValues.bind(this));\n\t\tthis.registerTableFunction(\"setGroupStartOpen\", this.setGroupStartOpen.bind(this));\n\t\tthis.registerTableFunction(\"setGroupHeader\", this.setGroupHeader.bind(this));\n\t\tthis.registerTableFunction(\"getGroups\", this.userGetGroups.bind(this));\n\t\tthis.registerTableFunction(\"getGroupedData\", this.userGetGroupedData.bind(this));\n\t\t\n\t\t//register component functions\n\t\tthis.registerComponentFunction(\"row\", \"getGroup\", this.rowGetGroup.bind(this));\n\t}\n\t\n\t//initialize group configuration\n\tinitialize(){\n\t\tthis.subscribe(\"table-destroy\", this._blockRedrawing.bind(this));\n\t\tthis.subscribe(\"rows-wipe\", this._blockRedrawing.bind(this));\n\t\tthis.subscribe(\"rows-wiped\", this._restore_redrawing.bind(this));\n\n\t\tif(this.table.options.groupBy){\n\t\t\tif(this.table.options.groupUpdateOnCellEdit){\n\t\t\t\tthis.subscribe(\"cell-value-updated\", this.cellUpdated.bind(this));\n\t\t\t\tthis.subscribe(\"row-data-changed\", this.reassignRowToGroup.bind(this), 0);\n\t\t\t}\n\t\t\t\n\t\t\tthis.subscribe(\"table-built\", this.configureGroupSetup.bind(this));\n\t\t\t\n\t\t\tthis.subscribe(\"row-deleting\", this.rowDeleting.bind(this));\n\t\t\tthis.subscribe(\"row-deleted\", this.rowsUpdated.bind(this));\n\t\t\tthis.subscribe(\"scroll-horizontal\", this.scrollHeaders.bind(this));\n\t\t\tthis.subscribe(\"rows-wipe\", this.wipe.bind(this));\n\t\t\tthis.subscribe(\"rows-added\", this.rowsUpdated.bind(this));\n\t\t\tthis.subscribe(\"row-moving\", this.rowMoving.bind(this));\n\t\t\tthis.subscribe(\"row-adding-index\", this.rowAddingIndex.bind(this));\n\t\t\t\n\t\t\tthis.subscribe(\"rows-sample\", this.rowSample.bind(this));\n\t\t\t\n\t\t\tthis.subscribe(\"render-virtual-fill\", this.virtualRenderFill.bind(this));\n\t\t\t\n\t\t\tthis.registerDisplayHandler(this.displayHandler, 20);\n\t\t\t\n\t\t\tthis.initialized = true;\n\t\t}\n\t}\n\t\n\t_blockRedrawing(){\n\t\tthis.blockRedraw = true;\n\t}\n\n\t_restore_redrawing(){\n\t\tthis.blockRedraw = false;\n\t}\n\n\tconfigureGroupSetup(){\n\t\tif(this.table.options.groupBy){\n\t\t\tvar groupBy = this.table.options.groupBy,\n\t\t\tstartOpen = this.table.options.groupStartOpen,\n\t\t\tgroupHeader = this.table.options.groupHeader;\n\t\t\t\n\t\t\tthis.allowedValues = this.table.options.groupValues;\n\t\t\t\n\t\t\tif(Array.isArray(groupBy) && Array.isArray(groupHeader) && groupBy.length > groupHeader.length){\n\t\t\t\tconsole.warn(\"Error creating group headers, groupHeader array is shorter than groupBy array\");\n\t\t\t}\n\t\t\t\n\t\t\tthis.headerGenerator = [function(){return \"\";}];\n\t\t\tthis.startOpen = [function(){return false;}]; //starting state of group\n\t\t\t\n\t\t\tthis.langBind(\"groups|item\", (langValue, lang) => {\n\t\t\t\tthis.headerGenerator[0] = (value, count, data) => { //header layout function\n\t\t\t\t\treturn (typeof value === \"undefined\" ? \"\" : value) + \"<span>(\" + count + \" \" + ((count === 1) ? langValue : lang.groups.items) + \")</span>\";\n\t\t\t\t};\n\t\t\t});\n\t\t\t\n\t\t\tthis.groupIDLookups = [];\n\t\t\t\n\t\t\tif(groupBy){\n\t\t\t\tif(this.table.modExists(\"columnCalcs\") && this.table.options.columnCalcs != \"table\" && this.table.options.columnCalcs != \"both\"){\n\t\t\t\t\tthis.table.modules.columnCalcs.removeCalcs();\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tif(this.table.modExists(\"columnCalcs\") && this.table.options.columnCalcs != \"group\"){\n\t\t\t\t\t\n\t\t\t\t\tvar cols = this.table.columnManager.getRealColumns();\n\t\t\t\t\t\n\t\t\t\t\tcols.forEach((col) => {\n\t\t\t\t\t\tif(col.definition.topCalc){\n\t\t\t\t\t\t\tthis.table.modules.columnCalcs.initializeTopRow();\n\t\t\t\t\t\t}\n\t\t\t\t\t\t\n\t\t\t\t\t\tif(col.definition.bottomCalc){\n\t\t\t\t\t\t\tthis.table.modules.columnCalcs.initializeBottomRow();\n\t\t\t\t\t\t}\n\t\t\t\t\t});\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\tif(!Array.isArray(groupBy)){\n\t\t\t\tgroupBy = [groupBy];\n\t\t\t}\n\t\t\t\n\t\t\tgroupBy.forEach((group, i) => {\n\t\t\t\tvar lookupFunc, column;\n\t\t\t\t\n\t\t\t\tif(typeof group == \"function\"){\n\t\t\t\t\tlookupFunc = group;\n\t\t\t\t}else {\n\t\t\t\t\tcolumn = this.table.columnManager.getColumnByField(group);\n\t\t\t\t\t\n\t\t\t\t\tif(column){\n\t\t\t\t\t\tlookupFunc = function(data){\n\t\t\t\t\t\t\treturn column.getFieldValue(data);\n\t\t\t\t\t\t};\n\t\t\t\t\t}else {\n\t\t\t\t\t\tlookupFunc = function(data){\n\t\t\t\t\t\t\treturn data[group];\n\t\t\t\t\t\t};\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tthis.groupIDLookups.push({\n\t\t\t\t\tfield: typeof group === \"function\" ? false : group,\n\t\t\t\t\tfunc:lookupFunc,\n\t\t\t\t\tvalues:this.allowedValues ? this.allowedValues[i] : false,\n\t\t\t\t});\n\t\t\t});\n\t\t\t\n\t\t\tif(startOpen){\n\t\t\t\tif(!Array.isArray(startOpen)){\n\t\t\t\t\tstartOpen = [startOpen];\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tstartOpen.forEach((level) => {\n\t\t\t\t});\n\t\t\t\t\n\t\t\t\tthis.startOpen = startOpen;\n\t\t\t}\n\t\t\t\n\t\t\tif(groupHeader){\n\t\t\t\tthis.headerGenerator = Array.isArray(groupHeader) ? groupHeader : [groupHeader];\n\t\t\t}\n\t\t}else {\n\t\t\tthis.groupList = [];\n\t\t\tthis.groups = {};\n\t\t}\n\t}\n\t\n\trowSample(rows, prevValue){\n\t\tif(this.table.options.groupBy){\n\t\t\tvar group = this.getGroups(false)[0];\n\t\t\t\n\t\t\tprevValue.push(group.getRows(false)[0]);\n\t\t}\n\t\t\n\t\treturn prevValue;\n\t}\n\t\n\tvirtualRenderFill(){\n\t\tvar el = this.table.rowManager.tableElement;\n\t\tvar rows = this.table.rowManager.getVisibleRows();\n\t\t\n\t\tif(this.table.options.groupBy){\n\t\t\trows = rows.filter((row) => {\n\t\t\t\treturn row.type !== \"group\";\n\t\t\t});\n\t\t\t\n\t\t\tel.style.minWidth = !rows.length ? this.table.columnManager.getWidth() + \"px\" : \"\";\n\t\t}else {\n\t\t\treturn rows;\n\t\t}\n\t}\n\t\n\trowAddingIndex(row, index, top){\n\t\tif(this.table.options.groupBy){\n\t\t\tthis.assignRowToGroup(row);\n\t\t\t\n\t\t\tvar groupRows = row.modules.group.rows;\n\t\t\t\n\t\t\tif(groupRows.length > 1){\n\t\t\t\tif(!index || (index && groupRows.indexOf(index) == -1)){\n\t\t\t\t\tif(top){\n\t\t\t\t\t\tif(groupRows[0] !== row){\n\t\t\t\t\t\t\tindex = groupRows[0];\n\t\t\t\t\t\t\tthis.table.rowManager.moveRowInArray(row.modules.group.rows, row, index, !top);\n\t\t\t\t\t\t}\n\t\t\t\t\t}else {\n\t\t\t\t\t\tif(groupRows[groupRows.length -1] !== row){\n\t\t\t\t\t\t\tindex = groupRows[groupRows.length -1];\n\t\t\t\t\t\t\tthis.table.rowManager.moveRowInArray(row.modules.group.rows, row, index, !top);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}else {\n\t\t\t\t\tthis.table.rowManager.moveRowInArray(row.modules.group.rows, row, index, !top);\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\treturn index;\n\t\t}\n\t}\n\t\n\ttrackChanges(){\n\t\tthis.dispatch(\"group-changed\");\n\t}\n\t\n\t///////////////////////////////////\n\t///////// Table Functions /////////\n\t///////////////////////////////////\n\t\n\tsetGroupBy(groups){\n\t\tthis.table.options.groupBy = groups;\n\t\t\n\t\tif(!this.initialized){\n\t\t\tthis.initialize();\n\t\t}\n\t\t\n\t\tthis.configureGroupSetup();\n\n\t\tif(!groups && this.table.modExists(\"columnCalcs\") && this.table.options.columnCalcs === true){\n\t\t\tthis.table.modules.columnCalcs.reinitializeCalcs();\n\t\t}\n\t\t\n\t\tthis.refreshData();\n\t\t\n\t\tthis.trackChanges();\n\t}\n\t\n\tsetGroupValues(groupValues){\n\t\tthis.table.options.groupValues = groupValues;\n\t\tthis.configureGroupSetup();\n\t\tthis.refreshData();\n\t\t\n\t\tthis.trackChanges();\n\t}\n\t\n\tsetGroupStartOpen(values){\n\t\tthis.table.options.groupStartOpen = values;\n\t\tthis.configureGroupSetup();\n\t\t\n\t\tif(this.table.options.groupBy){\n\t\t\tthis.refreshData();\n\t\t\t\n\t\t\tthis.trackChanges();\n\t\t}else {\n\t\t\tconsole.warn(\"Grouping Update - cant refresh view, no groups have been set\");\n\t\t}\n\t}\n\t\n\tsetGroupHeader(values){\n\t\tthis.table.options.groupHeader = values;\n\t\tthis.configureGroupSetup();\n\t\t\n\t\tif(this.table.options.groupBy){\n\t\t\tthis.refreshData();\n\t\t\t\n\t\t\tthis.trackChanges();\n\t\t}else {\n\t\t\tconsole.warn(\"Grouping Update - cant refresh view, no groups have been set\");\n\t\t}\n\t}\n\t\n\tuserGetGroups(values){\n\t\treturn this.getGroups(true);\n\t}\n\t\n\t// get grouped table data in the same format as getData()\n\tuserGetGroupedData(){\n\t\treturn this.table.options.groupBy ? this.getGroupedData() : this.getData();\n\t}\n\t\n\t\n\t///////////////////////////////////////\n\t///////// Component Functions /////////\n\t///////////////////////////////////////\n\t\n\trowGetGroup(row){\n\t\treturn row.modules.group ? row.modules.group.getComponent() : false;\n\t}\n\t\n\t///////////////////////////////////\n\t///////// Internal Logic //////////\n\t///////////////////////////////////\n\t\n\trowMoving(from, to, after){\n\t\tif(this.table.options.groupBy){\n\t\t\tif(!after && to instanceof Group){\n\t\t\t\tto = this.table.rowManager.prevDisplayRow(from) || to;\n\t\t\t}\n\t\t\t\n\t\t\tvar toGroup = to instanceof Group ? to : to.modules.group;\n\t\t\tvar fromGroup = from instanceof Group ? from : from.modules.group;\n\t\t\t\n\t\t\tif(toGroup === fromGroup){\n\t\t\t\tthis.table.rowManager.moveRowInArray(toGroup.rows, from, to, after);\n\t\t\t}else {\n\t\t\t\tif(fromGroup){\n\t\t\t\t\tfromGroup.removeRow(from);\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\ttoGroup.insertRow(from, to, after);\n\t\t\t}\n\t\t}\n\t}\n\t\n\t\n\trowDeleting(row){\n\t\t//remove from group\n\t\tif(this.table.options.groupBy && row.modules.group){\n\t\t\trow.modules.group.removeRow(row);\n\t\t}\n\t}\n\t\n\trowsUpdated(row){\n\t\tif(this.table.options.groupBy){\n\t\t\tthis.updateGroupRows(true);\n\t\t}\t\n\t}\n\t\n\tcellUpdated(cell){\n\t\tif(this.table.options.groupBy){\n\t\t\tthis.reassignRowToGroup(cell.row);\n\t\t}\n\t}\n\t\n\t//return appropriate rows with group headers\n\tgetRows(rows){\n\t\tif(this.table.options.groupBy && this.groupIDLookups.length){\n\t\t\t\n\t\t\tthis.dispatchExternal(\"dataGrouping\");\n\t\t\t\n\t\t\tthis.generateGroups(rows);\n\t\t\t\n\t\t\tif(this.subscribedExternal(\"dataGrouped\")){\n\t\t\t\tthis.dispatchExternal(\"dataGrouped\", this.getGroups(true));\n\t\t\t}\n\t\t\t\n\t\t\treturn this.updateGroupRows();\n\t\t\t\n\t\t}else {\n\t\t\treturn rows.slice(0);\n\t\t}\n\t}\n\t\n\tgetGroups(component){\n\t\tvar groupComponents = [];\n\t\t\n\t\tthis.groupList.forEach(function(group){\n\t\t\tgroupComponents.push(component ? group.getComponent() : group);\n\t\t});\n\t\t\n\t\treturn groupComponents;\n\t}\n\t\n\tgetChildGroups(group){\n\t\tvar groupComponents = [];\n\t\t\n\t\tif(!group){\n\t\t\tgroup = this;\n\t\t}\n\t\t\n\t\tgroup.groupList.forEach((child) => {\n\t\t\tif(child.groupList.length){\n\t\t\t\tgroupComponents = groupComponents.concat(this.getChildGroups(child));\n\t\t\t}else {\n\t\t\t\tgroupComponents.push(child);\n\t\t\t}\n\t\t});\n\t\t\n\t\treturn groupComponents;\n\t}\n\t\n\twipe(){\n\t\tif(this.table.options.groupBy){\n\t\t\tthis.groupList.forEach(function(group){\n\t\t\t\tgroup.wipe();\n\t\t\t});\n\t\t\t\n\t\t\tthis.groupList = [];\n\t\t\tthis.groups = {};\n\t\t}\n\t}\n\t\n\tpullGroupListData(groupList) {\n\t\tvar groupListData = [];\n\t\t\n\t\tgroupList.forEach((group) => {\n\t\t\tvar groupHeader = {};\n\t\t\tgroupHeader.level = 0;\n\t\t\tgroupHeader.rowCount = 0;\n\t\t\tgroupHeader.headerContent = \"\";\n\t\t\tvar childData = [];\n\t\t\t\n\t\t\tif (group.hasSubGroups) {\n\t\t\t\tchildData = this.pullGroupListData(group.groupList);\n\t\t\t\t\n\t\t\t\tgroupHeader.level = group.level;\n\t\t\t\tgroupHeader.rowCount = childData.length - group.groupList.length; // data length minus number of sub-headers\n\t\t\t\tgroupHeader.headerContent = group.generator(group.key, groupHeader.rowCount, group.rows, group);\n\t\t\t\t\n\t\t\t\tgroupListData.push(groupHeader);\n\t\t\t\tgroupListData = groupListData.concat(childData);\n\t\t\t}\n\t\t\t\n\t\t\telse {\n\t\t\t\tgroupHeader.level = group.level;\n\t\t\t\tgroupHeader.headerContent = group.generator(group.key, group.rows.length, group.rows, group);\n\t\t\t\tgroupHeader.rowCount = group.getRows().length;\n\t\t\t\t\n\t\t\t\tgroupListData.push(groupHeader);\n\t\t\t\t\n\t\t\t\tgroup.getRows().forEach((row) => {\n\t\t\t\t\tgroupListData.push(row.getData(\"data\"));\n\t\t\t\t});\n\t\t\t}\n\t\t});\n\t\t\n\t\treturn groupListData;\n\t}\n\t\n\tgetGroupedData(){\n\t\t\n\t\treturn this.pullGroupListData(this.groupList);\n\t}\n\t\n\tgetRowGroup(row){\n\t\tvar match = false;\n\t\t\n\t\tif(this.options(\"dataTree\")){\n\t\t\trow = this.table.modules.dataTree.getTreeParentRoot(row);\n\t\t}\n\t\t\n\t\tthis.groupList.forEach((group) => {\n\t\t\tvar result = group.getRowGroup(row);\n\t\t\t\n\t\t\tif(result){\n\t\t\t\tmatch = result;\n\t\t\t}\n\t\t});\n\t\t\n\t\treturn match;\n\t}\n\t\n\tcountGroups(){\n\t\treturn this.groupList.length;\n\t}\n\t\n\tgenerateGroups(rows){\n\t\tvar oldGroups = this.groups;\n\t\t\n\t\tthis.groups = {};\n\t\tthis.groupList = [];\n\t\t\n\t\tif(this.allowedValues && this.allowedValues[0]){\n\t\t\tthis.allowedValues[0].forEach((value) => {\n\t\t\t\tthis.createGroup(value, 0, oldGroups);\n\t\t\t});\n\t\t\t\n\t\t\trows.forEach((row) => {\n\t\t\t\tthis.assignRowToExistingGroup(row, oldGroups);\n\t\t\t});\n\t\t}else {\n\t\t\trows.forEach((row) => {\n\t\t\t\tthis.assignRowToGroup(row, oldGroups);\n\t\t\t});\n\t\t}\n\t\t\n\t\tObject.values(oldGroups).forEach((group) => {\n\t\t\tgroup.wipe(true);\n\t\t});\t\n\t}\n\t\n\t\n\tcreateGroup(groupID, level, oldGroups){\n\t\tvar groupKey = level + \"_\" + groupID,\n\t\tgroup;\n\t\t\n\t\toldGroups = oldGroups || [];\n\t\t\n\t\tgroup = new Group(this, false, level, groupID, this.groupIDLookups[0].field, this.headerGenerator[0], oldGroups[groupKey]);\n\t\t\n\t\tthis.groups[groupKey] = group;\n\t\tthis.groupList.push(group);\n\t}\n\t\n\tassignRowToExistingGroup(row, oldGroups){\n\t\tvar groupID = this.groupIDLookups[0].func(row.getData()),\n\t\tgroupKey = \"0_\" + groupID;\n\t\t\n\t\tif(this.groups[groupKey]){\n\t\t\tthis.groups[groupKey].addRow(row);\n\t\t}\n\t}\n\t\n\tassignRowToGroup(row, oldGroups){\n\t\tvar groupID = this.groupIDLookups[0].func(row.getData()),\n\t\tnewGroupNeeded = !this.groups[\"0_\" + groupID];\n\t\t\n\t\tif(newGroupNeeded){\n\t\t\tthis.createGroup(groupID, 0, oldGroups);\n\t\t}\n\t\t\n\t\tthis.groups[\"0_\" + groupID].addRow(row);\n\t\t\n\t\treturn !newGroupNeeded;\n\t}\n\t\n\treassignRowToGroup(row){\n\t\tif(row.type === \"row\"){\n\t\t\tvar oldRowGroup = row.modules.group,\n\t\t\toldGroupPath = oldRowGroup.getPath(),\n\t\t\tnewGroupPath = this.getExpectedPath(row),\n\t\t\tsamePath;\n\t\t\t\n\t\t\t// figure out if new group path is the same as old group path\n\t\t\tsamePath = (oldGroupPath.length == newGroupPath.length) && oldGroupPath.every((element, index) => {\n\t\t\t\treturn element === newGroupPath[index];\n\t\t\t});\n\t\t\t\n\t\t\t// refresh if they new path and old path aren't the same (aka the row's groupings have changed)\n\t\t\tif(!samePath) {\n\t\t\t\toldRowGroup.removeRow(row);\n\t\t\t\tthis.assignRowToGroup(row, this.groups);\n\t\t\t\tthis.refreshData(true);\n\t\t\t}\n\t\t}\n\t}\n\t\n\tgetExpectedPath(row) {\n\t\tvar groupPath = [], rowData = row.getData();\n\t\t\n\t\tthis.groupIDLookups.forEach((groupId) => {\n\t\t\tgroupPath.push(groupId.func(rowData));\n\t\t});\n\t\t\n\t\treturn groupPath;\n\t}\n\t\n\tupdateGroupRows(force){\n\t\tvar output = [];\n\n\t\tif(!this.blockRedraw){\n\t\t\tthis.groupList.forEach((group) => {\n\t\t\t\toutput = output.concat(group.getHeadersAndRows());\n\t\t\t});\n\t\t\t\n\t\t\tif(force){\n\t\t\t\tthis.refreshData(true);\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn output;\n\t}\n\t\n\tscrollHeaders(left){\n\t\tif(this.table.options.groupBy){\n\t\t\tif(this.table.options.renderHorizontal === \"virtual\"){\n\t\t\t\tleft -= this.table.columnManager.renderer.vDomPadLeft;\n\t\t\t}\n\t\t\t\n\t\t\tleft = left + \"px\";\n\t\t\t\n\t\t\tthis.groupList.forEach((group) => {\n\t\t\t\tgroup.scrollHeader(left);\n\t\t\t});\n\t\t}\n\t}\n\t\n\tremoveGroup(group){\n\t\tvar groupKey = group.level + \"_\" + group.key,\n\t\tindex;\n\t\t\n\t\tif(this.groups[groupKey]){\n\t\t\tdelete this.groups[groupKey];\n\t\t\t\n\t\t\tindex = this.groupList.indexOf(group);\n\t\t\t\n\t\t\tif(index > -1){\n\t\t\t\tthis.groupList.splice(index, 1);\n\t\t\t}\n\t\t}\n\t}\n\t\n\tcheckBasicModeGroupHeaderWidth(){\n\t\tvar element = this.table.rowManager.tableElement,\n\t\tonlyGroupHeaders = true;\n\t\t\n\t\tthis.table.rowManager.getDisplayRows().forEach((row, index) =>{\n\t\t\tthis.table.rowManager.styleRow(row, index);\n\t\t\telement.appendChild(row.getElement());\n\t\t\trow.initialize(true);\n\t\t\t\n\t\t\tif(row.type !== \"group\"){\n\t\t\t\tonlyGroupHeaders = false;\n\t\t\t}\n\t\t});\n\t\t\n\t\tif(onlyGroupHeaders){\n\t\t\telement.style.minWidth = this.table.columnManager.getWidth() + \"px\";\n\t\t}else {\n\t\t\telement.style.minWidth = \"\";\n\t\t}\n\t}\n\t\n}\n\nGroupRows.moduleName = \"groupRows\";\n\nvar defaultUndoers = {\n\tcellEdit: function(action){\n\t\taction.component.setValueProcessData(action.data.oldValue);\n\t\taction.component.cellRendered();\n\t},\n\n\trowAdd: function(action){\n\t\taction.component.deleteActual();\n\n\t\tthis.table.rowManager.checkPlaceholder();\n\t},\n\n\trowDelete: function(action){\n\t\tvar newRow = this.table.rowManager.addRowActual(action.data.data, action.data.pos, action.data.index);\n\n\t\tif(this.table.options.groupBy && this.table.modExists(\"groupRows\")){\n\t\t\tthis.table.modules.groupRows.updateGroupRows(true);\n\t\t}\n\n\t\tthis._rebindRow(action.component, newRow);\n\n\t\tthis.table.rowManager.checkPlaceholder();\n\t},\n\n\trowMove: function(action){\n\t\tvar after = (action.data.posFrom  - action.data.posTo) > 0;\n\n\t\tthis.table.rowManager.moveRowActual(action.component, this.table.rowManager.getRowFromPosition(action.data.posFrom), after);\n\n\t\tthis.table.rowManager.regenerateRowPositions();\n\t\tthis.table.rowManager.reRenderInPosition();\n\t},\n};\n\nvar defaultRedoers = {\n\tcellEdit: function(action){\n\t\taction.component.setValueProcessData(action.data.newValue);\n\t\taction.component.cellRendered();\n\t},\n\n\trowAdd: function(action){\n\t\tvar newRow = this.table.rowManager.addRowActual(action.data.data, action.data.pos, action.data.index);\n\n\t\tif(this.table.options.groupBy && this.table.modExists(\"groupRows\")){\n\t\t\tthis.table.modules.groupRows.updateGroupRows(true);\n\t\t}\n\n\t\tthis._rebindRow(action.component, newRow);\n\n\t\tthis.table.rowManager.checkPlaceholder();\n\t},\n\n\trowDelete:function(action){\n\t\taction.component.deleteActual();\n\n\t\tthis.table.rowManager.checkPlaceholder();\n\t},\n\n\trowMove: function(action){\n\t\tthis.table.rowManager.moveRowActual(action.component, this.table.rowManager.getRowFromPosition(action.data.posTo), action.data.after);\n\t\t\n\t\tthis.table.rowManager.regenerateRowPositions();\n\t\tthis.table.rowManager.reRenderInPosition();\n\t},\n};\n\nclass History extends Module{\n\n\tconstructor(table){\n\t\tsuper(table);\n\n\t\tthis.history = [];\n\t\tthis.index = -1;\n\n\t\tthis.registerTableOption(\"history\", false); //enable edit history\n\t}\n\n\tinitialize(){\n\t\tif(this.table.options.history){\n\t\t\tthis.subscribe(\"cell-value-updated\", this.cellUpdated.bind(this));\n\t\t\tthis.subscribe(\"cell-delete\", this.clearComponentHistory.bind(this));\n\t\t\tthis.subscribe(\"row-delete\", this.rowDeleted.bind(this));\n\t\t\tthis.subscribe(\"rows-wipe\", this.clear.bind(this));\n\t\t\tthis.subscribe(\"row-added\", this.rowAdded.bind(this));\n\t\t\tthis.subscribe(\"row-move\", this.rowMoved.bind(this));\n\t\t}\n\n\t\tthis.registerTableFunction(\"undo\", this.undo.bind(this));\n\t\tthis.registerTableFunction(\"redo\", this.redo.bind(this));\n\t\tthis.registerTableFunction(\"getHistoryUndoSize\", this.getHistoryUndoSize.bind(this));\n\t\tthis.registerTableFunction(\"getHistoryRedoSize\", this.getHistoryRedoSize.bind(this));\n\t\tthis.registerTableFunction(\"clearHistory\", this.clear.bind(this));\n\t}\n\n\trowMoved(from, to, after){\n\t\tthis.action(\"rowMove\", from, {posFrom:from.getPosition(), posTo:to.getPosition(), to:to, after:after});\n\t}\n\n\trowAdded(row, data, pos, index){\n\t\tthis.action(\"rowAdd\", row, {data:data, pos:pos, index:index});\n\t}\n\n\trowDeleted(row){\n\t\tvar index, rows;\n\n\t\tif(this.table.options.groupBy){\n\n\t\t\trows = row.getComponent().getGroup()._getSelf().rows;\n\t\t\tindex = rows.indexOf(row);\n\n\t\t\tif(index){\n\t\t\t\tindex = rows[index-1];\n\t\t\t}\n\t\t}else {\n\t\t\tindex = row.table.rowManager.getRowIndex(row);\n\n\t\t\tif(index){\n\t\t\t\tindex = row.table.rowManager.rows[index-1];\n\t\t\t}\n\t\t}\n\n\t\tthis.action(\"rowDelete\", row, {data:row.getData(), pos:!index, index:index});\n\t}\n\n\tcellUpdated(cell){\n\t\tthis.action(\"cellEdit\", cell, {oldValue:cell.oldValue, newValue:cell.value});\n\t}\n\n\tclear(){\n\t\tthis.history = [];\n\t\tthis.index = -1;\n\t}\n\n\taction(type, component, data){\n\t\tthis.history = this.history.slice(0, this.index + 1);\n\n\t\tthis.history.push({\n\t\t\ttype:type,\n\t\t\tcomponent:component,\n\t\t\tdata:data,\n\t\t});\n\n\t\tthis.index ++;\n\t}\n\n\tgetHistoryUndoSize(){\n\t\treturn this.index + 1;\n\t}\n\n\tgetHistoryRedoSize(){\n\t\treturn this.history.length - (this.index + 1);\n\t}\n\n\tclearComponentHistory(component){\n\t\tvar index = this.history.findIndex(function(item){\n\t\t\treturn item.component === component;\n\t\t});\n\n\t\tif(index > -1){\n\t\t\tthis.history.splice(index, 1);\n\t\t\tif(index <= this.index){\n\t\t\t\tthis.index--;\n\t\t\t}\n\n\t\t\tthis.clearComponentHistory(component);\n\t\t}\n\t}\n\n\tundo(){\n\t\tif(this.index > -1){\n\t\t\tlet action = this.history[this.index];\n\n\t\t\tHistory.undoers[action.type].call(this, action);\n\n\t\t\tthis.index--;\n\n\t\t\tthis.dispatchExternal(\"historyUndo\", action.type, action.component.getComponent(), action.data);\n\n\t\t\treturn true;\n\t\t}else {\n\t\t\tconsole.warn(this.options(\"history\") ? \"History Undo Error - No more history to undo\" : \"History module not enabled\");\n\t\t\treturn false;\n\t\t}\n\t}\n\n\tredo(){\n\t\tif(this.history.length-1 > this.index){\n\n\t\t\tthis.index++;\n\n\t\t\tlet action = this.history[this.index];\n\n\t\t\tHistory.redoers[action.type].call(this, action);\n\n\t\t\tthis.dispatchExternal(\"historyRedo\", action.type, action.component.getComponent(), action.data);\n\n\t\t\treturn true;\n\t\t}else {\n\t\t\tconsole.warn(this.options(\"history\") ? \"History Redo Error - No more history to redo\" : \"History module not enabled\");\n\t\t\treturn false;\n\t\t}\n\t}\n\n\t//rebind rows to new element after deletion\n\t_rebindRow(oldRow, newRow){\n\t\tthis.history.forEach(function(action){\n\t\t\tif(action.component instanceof Row){\n\t\t\t\tif(action.component === oldRow){\n\t\t\t\t\taction.component = newRow;\n\t\t\t\t}\n\t\t\t}else if(action.component instanceof Cell){\n\t\t\t\tif(action.component.row === oldRow){\n\t\t\t\t\tvar field = action.component.column.getField();\n\n\t\t\t\t\tif(field){\n\t\t\t\t\t\taction.component = newRow.getCell(field);\n\t\t\t\t\t}\n\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\t}\n}\n\nHistory.moduleName = \"history\";\n\n//load defaults\nHistory.undoers = defaultUndoers;\nHistory.redoers = defaultRedoers;\n\nclass HtmlTableImport extends Module{\n\n\tconstructor(table){\n\t\tsuper(table);\n\n\t\tthis.fieldIndex = [];\n\t\tthis.hasIndex = false;\n\t}\n\n\tinitialize(){\n\t\tthis.tableElementCheck();\n\t}\n\n\ttableElementCheck(){\n\t\tif(this.table.originalElement && this.table.originalElement.tagName === \"TABLE\"){\n\t\t\tif(this.table.originalElement.childNodes.length){\n\t\t\t\tthis.parseTable();\n\t\t\t}else {\n\t\t\t\tconsole.warn(\"Unable to parse data from empty table tag, Tabulator should be initialized on a div tag unless importing data from a table element.\");\n\t\t\t}\n\t\t}\n\t}\n\n\tparseTable(){\n\t\tvar element = this.table.originalElement,\n\t\toptions = this.table.options,\n\t\theaders = element.getElementsByTagName(\"th\"),\n\t\trows = element.getElementsByTagName(\"tbody\")[0],\n\t\tdata = [];\n\n\t\tthis.hasIndex = false;\n\n\t\tthis.dispatchExternal(\"htmlImporting\");\n\n\t\trows = rows ? rows.getElementsByTagName(\"tr\") : [];\n\n\t\t//check for Tabulator inline options\n\t\tthis._extractOptions(element, options);\n\n\t\tif(headers.length){\n\t\t\tthis._extractHeaders(headers, rows);\n\t\t}else {\n\t\t\tthis._generateBlankHeaders(headers, rows);\n\t\t}\n\n\t\t//iterate through table rows and build data set\n\t\tfor(var index = 0; index < rows.length; index++){\n\t\t\tvar row = rows[index],\n\t\t\tcells = row.getElementsByTagName(\"td\"),\n\t\t\titem = {};\n\n\t\t\t//create index if the don't exist in table\n\t\t\tif(!this.hasIndex){\n\t\t\t\titem[options.index] = index;\n\t\t\t}\n\n\t\t\tfor(var i = 0; i < cells.length; i++){\n\t\t\t\tvar cell = cells[i];\n\t\t\t\tif(typeof this.fieldIndex[i] !== \"undefined\"){\n\t\t\t\t\titem[this.fieldIndex[i]] = cell.innerHTML;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t//add row data to item\n\t\t\tdata.push(item);\n\t\t}\n\n\t\toptions.data = data;\n\n\t\tthis.dispatchExternal(\"htmlImported\");\n\t}\n\n\t//extract tabulator attribute options\n\t_extractOptions(element, options, defaultOptions){\n\t\tvar attributes = element.attributes;\n\t\tvar optionsArr = defaultOptions ? Object.keys(defaultOptions) : Object.keys(options);\n\t\tvar optionsList = {};\n\n\t\toptionsArr.forEach((item) => {\n\t\t\toptionsList[item.toLowerCase()] = item;\n\t\t});\n\n\t\tfor(var index in attributes){\n\t\t\tvar attrib = attributes[index];\n\t\t\tvar name;\n\n\t\t\tif(attrib && typeof attrib == \"object\" && attrib.name && attrib.name.indexOf(\"tabulator-\") === 0){\n\t\t\t\tname = attrib.name.replace(\"tabulator-\", \"\");\n\n\t\t\t\tif(typeof optionsList[name] !== \"undefined\"){\n\t\t\t\t\toptions[optionsList[name]] = this._attribValue(attrib.value);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t//get value of attribute\n\t_attribValue(value){\n\t\tif(value === \"true\"){\n\t\t\treturn true;\n\t\t}\n\n\t\tif(value === \"false\"){\n\t\t\treturn false;\n\t\t}\n\n\t\treturn value;\n\t}\n\n\t//find column if it has already been defined\n\t_findCol(title){\n\t\tvar match = this.table.options.columns.find((column) => {\n\t\t\treturn column.title === title;\n\t\t});\n\n\t\treturn match || false;\n\t}\n\n\t//extract column from headers\n\t_extractHeaders(headers, rows){\n\t\tfor(var index = 0; index < headers.length; index++){\n\t\t\tvar header = headers[index],\n\t\t\texists = false,\n\t\t\tcol = this._findCol(header.textContent),\n\t\t\twidth;\n\n\t\t\tif(col){\n\t\t\t\texists = true;\n\t\t\t}else {\n\t\t\t\tcol = {title:header.textContent.trim()};\n\t\t\t}\n\n\t\t\tif(!col.field) {\n\t\t\t\tcol.field = header.textContent.trim().toLowerCase().replaceAll(\" \", \"_\");\n\t\t\t}\n\n\t\t\twidth = header.getAttribute(\"width\");\n\n\t\t\tif(width && !col.width)\t{\n\t\t\t\tcol.width = width;\n\t\t\t}\n\n\t\t\t//check for Tabulator inline options\n\t\t\tthis._extractOptions(header, col, this.table.columnManager.optionsList.registeredDefaults);\n\n\t\t\tthis.fieldIndex[index] = col.field;\n\n\t\t\tif(col.field == this.table.options.index){\n\t\t\t\tthis.hasIndex = true;\n\t\t\t}\n\n\t\t\tif(!exists){\n\t\t\t\tthis.table.options.columns.push(col);\n\t\t\t}\n\n\t\t}\n\t}\n\n\t//generate blank headers\n\t_generateBlankHeaders(headers, rows){\n\t\tfor(var index = 0; index < headers.length; index++){\n\t\t\tvar header = headers[index],\n\t\t\tcol = {title:\"\", field:\"col\" + index};\n\n\t\t\tthis.fieldIndex[index] = col.field;\n\n\t\t\tvar width = header.getAttribute(\"width\");\n\n\t\t\tif(width){\n\t\t\t\tcol.width = width;\n\t\t\t}\n\n\t\t\tthis.table.options.columns.push(col);\n\t\t}\n\t}\n}\n\nHtmlTableImport.moduleName = \"htmlTableImport\";\n\nfunction csvImporter(input){\n\tvar data = [],\n\trow = 0, \n\tcol = 0,\n\tinQuote = false;\n    \n\t//Iterate over each character\n\tfor (let index = 0; index < input.length; index++) {\n\t\tlet char = input[index], \n\t\tnextChar = input[index+1];      \n        \n\t\t//Initialize empty row\n\t\tif(!data[row]){\n\t\t\tdata[row] = [];\n\t\t}\n\n\t\t//Initialize empty column\n\t\tif(!data[row][col]){\n\t\t\tdata[row][col] = \"\";\n\t\t}\n        \n\t\t//Handle quotation mark inside string\n\t\tif (char == '\"' && inQuote && nextChar == '\"') { \n\t\t\tdata[row][col] += char; \n\t\t\tindex++;\n\t\t\tcontinue; \n\t\t}\n        \n\t\t//Begin / End Quote\n\t\tif (char == '\"') { \n\t\t\tinQuote = !inQuote;\n\t\t\tcontinue;\n\t\t}\n        \n\t\t//Next column (if not in quote)\n\t\tif (char == ',' && !inQuote) { \n\t\t\tcol++;\n\t\t\tcontinue; \n\t\t}\n        \n\t\t//New row if new line and not in quote (CRLF) \n\t\tif (char == '\\r' && nextChar == '\\n' && !inQuote) { \n\t\t\tcol = 0; \n\t\t\trow++; \n\t\t\tindex++; \n\t\t\tcontinue; \n\t\t}\n        \n\t\t//New row if new line and not in quote (CR or LF) \n\t\tif ((char == '\\r' || char == '\\n') && !inQuote) { \n\t\t\tcol = 0;\n\t\t\trow++;\n\t\t\tcontinue; \n\t\t}\n\n\t\t//Normal Character, append to column\n\t\tdata[row][col] += char;\n\t}\n\n\treturn data;\n}\n\nfunction json$1(input){\n\ttry {\n\t\treturn JSON.parse(input);\n\t} catch(e) {\n\t\tconsole.warn(\"JSON Import Error - File contents is invalid JSON\", e);\n\t\treturn Promise.reject();\n\t}\n}\n\nfunction arrayImporter(input){\n\treturn input;\n}\n\nvar defaultImporters = {\n\tcsv:csvImporter,\n\tjson:json$1,\n\tarray:arrayImporter,\n};\n\nclass Import extends Module{\n    \n\tconstructor(table){\n\t\tsuper(table);\n        \n\t\tthis.registerTableOption(\"importFormat\");\n\t\tthis.registerTableOption(\"importReader\", \"text\");\n\t}\n    \n\tinitialize(){\n\t\tthis.registerTableFunction(\"import\", this.importFromFile.bind(this));\n\n\t\tif(this.table.options.importFormat){\n\t\t\tthis.subscribe(\"data-loading\", this.loadDataCheck.bind(this), 10);\n\t\t\tthis.subscribe(\"data-load\", this.loadData.bind(this), 10);\n\t\t}\n\t}\n\n\tloadDataCheck(data){\n\t\treturn this.table.options.importFormat && (typeof data === \"string\" || (Array.isArray(data) && data.length && Array.isArray(data)));\n\t}\n\n\tloadData(data, params, config, silent, previousData){\n\t\treturn this.importData(this.lookupImporter(), data)\n\t\t\t.then(this.structureData.bind(this))\n\t\t\t.catch((err) => {\n\t\t\t\tconsole.error(\"Import Error:\", err || \"Unable to import data\");\n\t\t\t\treturn Promise.reject(err);\n\t\t\t});\n\t}\n\n\tlookupImporter(importFormat){\n\t\tvar importer;\n        \n\t\tif(!importFormat){\n\t\t\timportFormat = this.table.options.importFormat;\n\t\t}\n        \n\t\tif(typeof importFormat === \"string\"){\n\t\t\timporter = Import.importers[importFormat];\n\t\t}else {\n\t\t\timporter = importFormat;\n\t\t}\n\n\t\tif(!importer){\n\t\t\tconsole.error(\"Import Error - Importer not found:\", importFormat);\n\t\t}\n        \n\t\treturn importer;\n\t}\n    \n\timportFromFile(importFormat, extension){\n\t\tvar importer = this.lookupImporter(importFormat);\n        \n\t\tif(importer){\n\t\t\treturn this.pickFile(extension)\n\t\t\t\t.then(this.importData.bind(this, importer))\n\t\t\t\t.then(this.structureData.bind(this))\n\t\t\t\t.then(this.setData.bind(this))\n\t\t\t\t.catch((err) => {\n\t\t\t\t\tconsole.error(\"Import Error:\", err || \"Unable to import file\");\n\t\t\t\t\treturn Promise.reject(err);\n\t\t\t\t});\n\t\t}\n\t}\n    \n\tpickFile(extensions){\n\t\treturn new Promise((resolve, reject) => {\n\t\t\tvar input = document.createElement(\"input\");\n\t\t\tinput.type = \"file\";\n\t\t\tinput.accept = extensions;\n            \n\t\t\tinput.addEventListener(\"change\", (e) => {\n\t\t\t\tvar file = input.files[0],\n\t\t\t\treader = new FileReader();\n                \n\t\t\t\tswitch(this.table.options.importReader){\n\t\t\t\t\tcase \"buffer\":\n\t\t\t\t\t\treader.readAsArrayBuffer(file);\n\t\t\t\t\t\tbreak;\n\n\t\t\t\t\tcase \"binary\":\n\t\t\t\t\t\treader.readAsBinaryString(file);\n\t\t\t\t\t\tbreak;\n\n\t\t\t\t\tcase \"url\":\n\t\t\t\t\t\treader.readAsDataURL(file);\n\t\t\t\t\t\tbreak;\n\n\t\t\t\t\tcase \"text\":\n\t\t\t\t\tdefault:\n\t\t\t\t\t\treader.readAsText(file);\n\t\t\t\t}\n                  \n\t\t\t\treader.onload = (e) => {\n\t\t\t\t\tresolve(reader.result);\n\t\t\t\t};\n                \n\t\t\t\treader.onerror = (e) => {\n\t\t\t\t\tconsole.warn(\"File Load Error - Unable to read file\");\n\t\t\t\t\treject();\n\t\t\t\t};\n\t\t\t});\n            \n\t\t\tinput.click();\n\t\t});\n\t}\n    \n\timportData(importer, fileContents){\n\t\tvar data = importer.call(this.table, fileContents);\n        \n\t\tif(data instanceof Promise){\n\t\t\treturn data;\n\t\t}else {\n\t\t\treturn data ? Promise.resolve(data) : Promise.reject();\n\t\t}\n\t}\n\n\tstructureData(parsedData){\n\t\tvar data = [];\n        \n\t\tif(Array.isArray(parsedData) && parsedData.length && Array.isArray(parsedData[0])){\n\t\t\tif(this.table.options.autoColumns){\n\t\t\t\tdata = this.structureArrayToObject(parsedData);\n\t\t\t}else {\n\t\t\t\tdata = this.structureArrayToColumns(parsedData);\n\t\t\t}\n\n\t\t\treturn data;\n\t\t}else {\n\t\t\treturn parsedData;\n\t\t}\n\t}\n\n\tstructureArrayToObject(parsedData){\n\t\tvar columns = parsedData.shift();\n\n\t\tvar data = parsedData.map((values) => {\n\t\t\tvar row = {};\n\n\t\t\tcolumns.forEach((key, i) => {\n\t\t\t\trow[key] = values[i];\n\t\t\t});\n\n\t\t\treturn row;\n\t\t});\n\n\t\treturn data;\n\t}\n\n\tstructureArrayToColumns(parsedData){\n\t\tvar data = [],\n\t\tcolumns = this.table.getColumns();\n\n\t\t//remove first row if it is the column names\n\t\tif(columns[0] && parsedData[0][0]){\n\t\t\tif(columns[0].getDefinition().title === parsedData[0][0]){\n\t\t\t\tparsedData.shift();\n\t\t\t}\n\t\t}\n        \n\t\t//convert row arrays to objects\n\t\tparsedData.forEach((rowData) => {\n\t\t\tvar row = {};\n\n\t\t\trowData.forEach((value, index) => {\n\t\t\t\tvar column = columns[index];\n\n\t\t\t\tif(column){\n\t\t\t\t\trow[column.getField()] = value;\n\t\t\t\t}\n\t\t\t});\n\n\t\t\tdata.push(row);\n\t\t});\n\n\t\treturn data;\n\t}\n    \n\tsetData(data){\n\t\treturn this.table.setData(data);\n\t}\n}\n\nImport.moduleName = \"import\";\n\n//load defaults\nImport.importers = defaultImporters;\n\nclass Interaction extends Module{\n\n\tconstructor(table){\n\t\tsuper(table);\n\n\t\tthis.eventMap = {\n\t\t\t//row events\n\t\t\trowClick:\"row-click\",\n\t\t\trowDblClick:\"row-dblclick\",\n\t\t\trowContext:\"row-contextmenu\",\n\t\t\trowMouseEnter:\"row-mouseenter\",\n\t\t\trowMouseLeave:\"row-mouseleave\",\n\t\t\trowMouseOver:\"row-mouseover\",\n\t\t\trowMouseOut:\"row-mouseout\",\n\t\t\trowMouseMove:\"row-mousemove\",\n\t\t\trowMouseDown:\"row-mousedown\",\n\t\t\trowMouseUp:\"row-mouseup\",\n\t\t\trowTap:\"row\",\n\t\t\trowDblTap:\"row\",\n\t\t\trowTapHold:\"row\",\n\n\t\t\t//cell events\n\t\t\tcellClick:\"cell-click\",\n\t\t\tcellDblClick:\"cell-dblclick\",\n\t\t\tcellContext:\"cell-contextmenu\",\n\t\t\tcellMouseEnter:\"cell-mouseenter\",\n\t\t\tcellMouseLeave:\"cell-mouseleave\",\n\t\t\tcellMouseOver:\"cell-mouseover\",\n\t\t\tcellMouseOut:\"cell-mouseout\",\n\t\t\tcellMouseMove:\"cell-mousemove\",\n\t\t\tcellMouseDown:\"cell-mousedown\",\n\t\t\tcellMouseUp:\"cell-mouseup\",\n\t\t\tcellTap:\"cell\",\n\t\t\tcellDblTap:\"cell\",\n\t\t\tcellTapHold:\"cell\",\n\n\t\t\t//column header events\n\t\t\theaderClick:\"column-click\",\n\t\t\theaderDblClick:\"column-dblclick\",\n\t\t\theaderContext:\"column-contextmenu\",\n\t\t\theaderMouseEnter:\"column-mouseenter\",\n\t\t\theaderMouseLeave:\"column-mouseleave\",\n\t\t\theaderMouseOver:\"column-mouseover\",\n\t\t\theaderMouseOut:\"column-mouseout\",\n\t\t\theaderMouseMove:\"column-mousemove\",\n\t\t\theaderMouseDown:\"column-mousedown\",\n\t\t\theaderMouseUp:\"column-mouseup\",\n\t\t\theaderTap:\"column\",\n\t\t\theaderDblTap:\"column\",\n\t\t\theaderTapHold:\"column\",\n\n\t\t\t//group header\n\t\t\tgroupClick:\"group-click\",\n\t\t\tgroupDblClick:\"group-dblclick\",\n\t\t\tgroupContext:\"group-contextmenu\",\n\t\t\tgroupMouseEnter:\"group-mouseenter\",\n\t\t\tgroupMouseLeave:\"group-mouseleave\",\n\t\t\tgroupMouseOver:\"group-mouseover\",\n\t\t\tgroupMouseOut:\"group-mouseout\",\n\t\t\tgroupMouseMove:\"group-mousemove\",\n\t\t\tgroupMouseDown:\"group-mousedown\",\n\t\t\tgroupMouseUp:\"group-mouseup\",\n\t\t\tgroupTap:\"group\",\n\t\t\tgroupDblTap:\"group\",\n\t\t\tgroupTapHold:\"group\",\n\t\t};\n\n\t\tthis.subscribers = {};\n\n\t\tthis.touchSubscribers = {};\n\n\t\tthis.columnSubscribers = {};\n\n\t\tthis.touchWatchers = {\n\t\t\trow:{\n\t\t\t\ttap:null,\n\t\t\t\ttapDbl:null,\n\t\t\t\ttapHold:null,\n\t\t\t},\n\t\t\tcell:{\n\t\t\t\ttap:null,\n\t\t\t\ttapDbl:null,\n\t\t\t\ttapHold:null,\n\t\t\t},\n\t\t\tcolumn:{\n\t\t\t\ttap:null,\n\t\t\t\ttapDbl:null,\n\t\t\t\ttapHold:null,\n\t\t\t},\n\t\t\tgroup:{\n\t\t\t\ttap:null,\n\t\t\t\ttapDbl:null,\n\t\t\t\ttapHold:null,\n\t\t\t}\n\t\t};\n\n\t\tthis.registerColumnOption(\"headerClick\");\n\t\tthis.registerColumnOption(\"headerDblClick\");\n\t\tthis.registerColumnOption(\"headerContext\");\n\t\tthis.registerColumnOption(\"headerMouseEnter\");\n\t\tthis.registerColumnOption(\"headerMouseLeave\");\n\t\tthis.registerColumnOption(\"headerMouseOver\");\n\t\tthis.registerColumnOption(\"headerMouseOut\");\n\t\tthis.registerColumnOption(\"headerMouseMove\");\n\t\tthis.registerColumnOption(\"headerMouseDown\");\n\t\tthis.registerColumnOption(\"headerMouseUp\");\n\t\tthis.registerColumnOption(\"headerTap\");\n\t\tthis.registerColumnOption(\"headerDblTap\");\n\t\tthis.registerColumnOption(\"headerTapHold\");\n\n\t\tthis.registerColumnOption(\"cellClick\");\n\t\tthis.registerColumnOption(\"cellDblClick\");\n\t\tthis.registerColumnOption(\"cellContext\");\n\t\tthis.registerColumnOption(\"cellMouseEnter\");\n\t\tthis.registerColumnOption(\"cellMouseLeave\");\n\t\tthis.registerColumnOption(\"cellMouseOver\");\n\t\tthis.registerColumnOption(\"cellMouseOut\");\n\t\tthis.registerColumnOption(\"cellMouseMove\");\n\t\tthis.registerColumnOption(\"cellMouseDown\");\n\t\tthis.registerColumnOption(\"cellMouseUp\");\n\t\tthis.registerColumnOption(\"cellTap\");\n\t\tthis.registerColumnOption(\"cellDblTap\");\n\t\tthis.registerColumnOption(\"cellTapHold\");\n\n\t}\n\n\tinitialize(){\n\t\tthis.initializeExternalEvents();\n\n\t\tthis.subscribe(\"column-init\", this.initializeColumn.bind(this));\n\t\tthis.subscribe(\"cell-dblclick\", this.cellContentsSelectionFixer.bind(this));\n\t\tthis.subscribe(\"scroll-horizontal\", this.clearTouchWatchers.bind(this));\n\t\tthis.subscribe(\"scroll-vertical\", this.clearTouchWatchers.bind(this));\n\t}\n\n\tclearTouchWatchers(){\n\t\tvar types = Object.values(this.touchWatchers);\n\n\t\ttypes.forEach((type) => {\n\t\t\tfor(let key in type){\n\t\t\t\ttype[key] = null;\n\t\t\t}\n\t\t});\n\t}\n\t\t\n\tcellContentsSelectionFixer(e, cell){\n\t\tvar range;\n\n\t\tif(this.table.modExists(\"edit\")){\n\t\t\tif (this.table.modules.edit.currentCell === cell){\n\t\t\t\treturn; //prevent instant selection of editor content\n\t\t\t}\n\t\t}\n\n\t\te.preventDefault();\n\n\t\ttry{\n\t\t\tif (document.selection) { // IE\n\t\t\t\trange = document.body.createTextRange();\n\t\t\t\trange.moveToElementText(cell.getElement());\n\t\t\t\trange.select();\n\t\t\t} else if (window.getSelection) {\n\t\t\t\trange = document.createRange();\n\t\t\t\trange.selectNode(cell.getElement());\n\t\t\t\twindow.getSelection().removeAllRanges();\n\t\t\t\twindow.getSelection().addRange(range);\n\t\t\t}\n\t\t}catch(e){}\n\t}\n\n\tinitializeExternalEvents(){\n\t\tfor(let key in this.eventMap){\n\t\t\tthis.subscriptionChangeExternal(key, this.subscriptionChanged.bind(this, key));\n\t\t}\n\t}\n\n\tsubscriptionChanged(key, added){\n\t\tif(added){\n\t\t\tif(!this.subscribers[key]){\n\t\t\t\tif(this.eventMap[key].includes(\"-\")){\n\t\t\t\t\tthis.subscribers[key] = this.handle.bind(this, key);\n\t\t\t\t\tthis.subscribe(this.eventMap[key], this.subscribers[key]);\n\t\t\t\t}else {\n\t\t\t\t\tthis.subscribeTouchEvents(key);\n\t\t\t\t}\n\t\t\t}\n\t\t}else {\n\t\t\tif(this.eventMap[key].includes(\"-\")){\n\t\t\t\tif(this.subscribers[key] && !this.columnSubscribers[key]  && !this.subscribedExternal(key)){\n\t\t\t\t\tthis.unsubscribe(this.eventMap[key], this.subscribers[key]);\n\t\t\t\t\tdelete this.subscribers[key];\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tthis.unsubscribeTouchEvents(key);\n\t\t\t}\n\t\t}\n\t}\n\n\n\tsubscribeTouchEvents(key){\n\t\tvar type = this.eventMap[key];\n\n\t\tif(!this.touchSubscribers[type + \"-touchstart\"]){\n\t\t\tthis.touchSubscribers[type + \"-touchstart\"] = this.handleTouch.bind(this, type, \"start\");\n\t\t\tthis.touchSubscribers[type + \"-touchend\"] = this.handleTouch.bind(this, type, \"end\");\n\n\t\t\tthis.subscribe(type + \"-touchstart\", this.touchSubscribers[type + \"-touchstart\"]);\n\t\t\tthis.subscribe(type + \"-touchend\", this.touchSubscribers[type + \"-touchend\"]);\n\t\t}\n\n\t\tthis.subscribers[key] = true;\n\t}\n\n\tunsubscribeTouchEvents(key){\n\t\tvar noTouch = true,\n\t\ttype = this.eventMap[key];\n\n\t\tif(this.subscribers[key] && !this.subscribedExternal(key)){\n\t\t\tdelete this.subscribers[key];\n\n\t\t\tfor(let i in this.eventMap){\n\t\t\t\tif(this.eventMap[i] === type){\n\t\t\t\t\tif(this.subscribers[i]){\n\t\t\t\t\t\tnoTouch = false;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif(noTouch){\n\t\t\t\tthis.unsubscribe(type + \"-touchstart\", this.touchSubscribers[type + \"-touchstart\"]);\n\t\t\t\tthis.unsubscribe(type + \"-touchend\", this.touchSubscribers[type + \"-touchend\"]);\n\n\t\t\t\tdelete this.touchSubscribers[type + \"-touchstart\"];\n\t\t\t\tdelete this.touchSubscribers[type + \"-touchend\"];\n\t\t\t}\n\t\t}\n\t}\n\n\tinitializeColumn(column){\n\t\tvar def = column.definition;\n\n\t\tfor(let key in this.eventMap){\n\t\t\tif(def[key]){\n\t\t\t\tthis.subscriptionChanged(key, true);\n\n\t\t\t\tif(!this.columnSubscribers[key]){\n\t\t\t\t\tthis.columnSubscribers[key] = [];\n\t\t\t\t}\n\n\t\t\t\tthis.columnSubscribers[key].push(column);\n\t\t\t}\n\t\t}\n\t}\n\n\thandle(action, e, component){\n\t\tthis.dispatchEvent(action, e, component);\n\t}\n\n\thandleTouch(type, action, e, component){\n\t\tvar watchers = this.touchWatchers[type];\n\n\t\tif(type === \"column\"){\n\t\t\ttype = \"header\";\n\t\t}\n\n\t\tswitch(action){\n\t\t\tcase \"start\":\n\t\t\t\twatchers.tap = true;\n\n\t\t\t\tclearTimeout(watchers.tapHold);\n\n\t\t\t\twatchers.tapHold = setTimeout(() => {\n\t\t\t\t\tclearTimeout(watchers.tapHold);\n\t\t\t\t\twatchers.tapHold = null;\n\n\t\t\t\t\twatchers.tap = null;\n\t\t\t\t\tclearTimeout(watchers.tapDbl);\n\t\t\t\t\twatchers.tapDbl = null;\n\n\t\t\t\t\tthis.dispatchEvent(type + \"TapHold\", e,  component);\n\t\t\t\t}, 1000);\n\t\t\t\tbreak;\n\n\t\t\tcase \"end\":\n\t\t\t\tif(watchers.tap){\n\n\t\t\t\t\twatchers.tap = null;\n\t\t\t\t\tthis.dispatchEvent(type + \"Tap\", e,  component);\n\t\t\t\t}\n\n\t\t\t\tif(watchers.tapDbl){\n\t\t\t\t\tclearTimeout(watchers.tapDbl);\n\t\t\t\t\twatchers.tapDbl = null;\n\n\t\t\t\t\tthis.dispatchEvent(type + \"DblTap\", e,  component);\n\t\t\t\t}else {\n\t\t\t\t\twatchers.tapDbl = setTimeout(() => {\n\t\t\t\t\t\tclearTimeout(watchers.tapDbl);\n\t\t\t\t\t\twatchers.tapDbl = null;\n\t\t\t\t\t}, 300);\n\t\t\t\t}\n\n\t\t\t\tclearTimeout(watchers.tapHold);\n\t\t\t\twatchers.tapHold = null;\n\t\t\t\tbreak;\n\t\t}\n\t}\n\n\tdispatchEvent(action, e, component){\n\t\tvar componentObj = component.getComponent(),\n\t\tcallback;\n\n\t\tif(this.columnSubscribers[action]){\n\n\t\t\tif(component instanceof Cell){\n\t\t\t\tcallback = component.column.definition[action];\n\t\t\t}else if(component instanceof Column){\n\t\t\t\tcallback = component.definition[action];\n\t\t\t}\n\n\t\t\tif(callback){\n\t\t\t\tcallback(e, componentObj);\n\t\t\t}\n\t\t}\n\n\t\tthis.dispatchExternal(action, e, componentObj);\n\t}\n}\n\nInteraction.moduleName = \"interaction\";\n\nvar defaultBindings = {\n\tnavPrev:\"shift + 9\",\n\tnavNext:9,\n\tnavUp:38,\n\tnavDown:40,\n\tnavLeft:37,\n\tnavRight:39,\n\tscrollPageUp:33,\n\tscrollPageDown:34,\n\tscrollToStart:36,\n\tscrollToEnd:35,\n\tundo:[\"ctrl + 90\", \"meta + 90\"],\n\tredo:[\"ctrl + 89\", \"meta + 89\"],\n\tcopyToClipboard:[\"ctrl + 67\", \"meta + 67\"],\n\n\trangeJumpUp:[\"ctrl + 38\", \"meta + 38\"],\n\trangeJumpDown:[\"ctrl + 40\", \"meta + 40\"],\n\trangeJumpLeft:[\"ctrl + 37\", \"meta + 37\"],\n\trangeJumpRight:[\"ctrl + 39\", \"meta + 39\"],\n\trangeExpandUp:\"shift + 38\",\n\trangeExpandDown:\"shift + 40\",\n\trangeExpandLeft:\"shift + 37\",\n\trangeExpandRight:\"shift + 39\",\n\trangeExpandJumpUp:[\"ctrl + shift + 38\", \"meta + shift + 38\"],\n\trangeExpandJumpDown:[\"ctrl + shift + 40\", \"meta + shift + 40\"],\n\trangeExpandJumpLeft:[\"ctrl + shift + 37\", \"meta + shift + 37\"],\n\trangeExpandJumpRight:[\"ctrl + shift + 39\", \"meta + shift + 39\"],\n};\n\nvar defaultActions = {\n\tkeyBlock:function(e){\n\t\te.stopPropagation();\n\t\te.preventDefault();\n\t},\n\tscrollPageUp:function(e){\n\t\tvar rowManager = this.table.rowManager,\n\t\tnewPos = rowManager.scrollTop - rowManager.element.clientHeight;\n\n\t\te.preventDefault();\n\n\t\tif(rowManager.displayRowsCount){\n\t\t\tif(newPos >= 0){\n\t\t\t\trowManager.element.scrollTop = newPos;\n\t\t\t}else {\n\t\t\t\trowManager.scrollToRow(rowManager.getDisplayRows()[0]);\n\t\t\t}\n\t\t}\n\n\t\tthis.table.element.focus();\n\t},\n\tscrollPageDown:function(e){\n\t\tvar rowManager = this.table.rowManager,\n\t\tnewPos = rowManager.scrollTop + rowManager.element.clientHeight,\n\t\tscrollMax = rowManager.element.scrollHeight;\n\n\t\te.preventDefault();\n\n\t\tif(rowManager.displayRowsCount){\n\t\t\tif(newPos <= scrollMax){\n\t\t\t\trowManager.element.scrollTop = newPos;\n\t\t\t}else {\n\t\t\t\trowManager.scrollToRow(rowManager.getDisplayRows()[rowManager.displayRowsCount - 1]);\n\t\t\t}\n\t\t}\n\n\t\tthis.table.element.focus();\n\n\t},\n\tscrollToStart:function(e){\n\t\tvar rowManager = this.table.rowManager;\n\n\t\te.preventDefault();\n\n\t\tif(rowManager.displayRowsCount){\n\t\t\trowManager.scrollToRow(rowManager.getDisplayRows()[0]);\n\t\t}\n\n\t\tthis.table.element.focus();\n\t},\n\tscrollToEnd:function(e){\n\t\tvar rowManager = this.table.rowManager;\n\n\t\te.preventDefault();\n\n\t\tif(rowManager.displayRowsCount){\n\t\t\trowManager.scrollToRow(rowManager.getDisplayRows()[rowManager.displayRowsCount - 1]);\n\t\t}\n\n\t\tthis.table.element.focus();\n\t},\n\tnavPrev:function(e){\n\t\tthis.dispatch(\"keybinding-nav-prev\", e);\n\t},\n\n\tnavNext:function(e){\n\t\tthis.dispatch(\"keybinding-nav-next\", e);\n\t},\n\n\tnavLeft:function(e){\n\t\tthis.dispatch(\"keybinding-nav-left\", e);\n\t},\n\n\tnavRight:function(e){\n\t\tthis.dispatch(\"keybinding-nav-right\", e);\n\t},\n\n\tnavUp:function(e){\n\t\tthis.dispatch(\"keybinding-nav-up\", e);\n\t},\n\n\tnavDown:function(e){\n\t\tthis.dispatch(\"keybinding-nav-down\", e);\n\t},\n\n\trangeJumpLeft: function(e){\n\t\tthis.dispatch(\"keybinding-nav-range\", e, \"left\", true, false);\n\t},\n\trangeJumpRight: function(e){\n\t\tthis.dispatch(\"keybinding-nav-range\", e, \"right\", true, false);\n\t},\n\trangeJumpUp: function(e){\n\t\tthis.dispatch(\"keybinding-nav-range\", e, \"up\", true, false);\n\t},\n\trangeJumpDown: function(e){\n\t\tthis.dispatch(\"keybinding-nav-range\", e, \"down\", true, false);\n\t},\n\trangeExpandLeft: function(e){\n\t\tthis.dispatch(\"keybinding-nav-range\", e, \"left\", false, true);\n\t},\n\trangeExpandRight: function(e){\n\t\tthis.dispatch(\"keybinding-nav-range\", e, \"right\", false, true);\n\t},\n\trangeExpandUp: function(e){\n\t\tthis.dispatch(\"keybinding-nav-range\", e, \"up\", false, true);\n\t},\n\trangeExpandDown: function(e){\n\t\tthis.dispatch(\"keybinding-nav-range\", e, \"down\", false, true);\n\t},\n\trangeExpandJumpLeft: function(e){\n\t\tthis.dispatch(\"keybinding-nav-range\", e, \"left\", true, true);\n\t},\n\trangeExpandJumpRight: function(e){\n\t\tthis.dispatch(\"keybinding-nav-range\", e, \"right\", true, true);\n\t},\n\trangeExpandJumpUp: function(e){\n\t\tthis.dispatch(\"keybinding-nav-range\", e, \"up\", true, true);\n\t},\n\trangeExpandJumpDown: function(e){\n\t\tthis.dispatch(\"keybinding-nav-range\", e, \"down\", true, true);\n\t},\n\n\tundo:function(e){\n\t\tvar cell = false;\n\t\tif(this.table.options.history && this.table.modExists(\"history\") && this.table.modExists(\"edit\")){\n\n\t\t\tcell = this.table.modules.edit.currentCell;\n\n\t\t\tif(!cell){\n\t\t\t\te.preventDefault();\n\t\t\t\tthis.table.modules.history.undo();\n\t\t\t}\n\t\t}\n\t},\n\n\tredo:function(e){\n\t\tvar cell = false;\n\t\tif(this.table.options.history && this.table.modExists(\"history\") && this.table.modExists(\"edit\")){\n\n\t\t\tcell = this.table.modules.edit.currentCell;\n\n\t\t\tif(!cell){\n\t\t\t\te.preventDefault();\n\t\t\t\tthis.table.modules.history.redo();\n\t\t\t}\n\t\t}\n\t},\n\n\tcopyToClipboard:function(e){\n\t\tif(!this.table.modules.edit.currentCell){\n\t\t\tif(this.table.modExists(\"clipboard\", true)){\n\t\t\t\tthis.table.modules.clipboard.copy(false, true);\n\t\t\t}\n\t\t}\n\t},\n};\n\nclass Keybindings extends Module{\n\n\tconstructor(table){\n\t\tsuper(table);\n\n\t\tthis.watchKeys = null;\n\t\tthis.pressedKeys = null;\n\t\tthis.keyupBinding = false;\n\t\tthis.keydownBinding = false;\n\n\t\tthis.registerTableOption(\"keybindings\", {}); //array for keybindings\n\t\tthis.registerTableOption(\"tabEndNewRow\", false); //create new row when tab to end of table\n\t}\n\n\tinitialize(){\n\t\tvar bindings = this.table.options.keybindings,\n\t\tmergedBindings = {};\n\n\t\tthis.watchKeys = {};\n\t\tthis.pressedKeys = [];\n\n\t\tif(bindings !== false){\n\t\t\tObject.assign(mergedBindings, Keybindings.bindings);\n\t\t\tObject.assign(mergedBindings, bindings);\n\n\t\t\tthis.mapBindings(mergedBindings);\n\t\t\tthis.bindEvents();\n\t\t}\n\n\t\tthis.subscribe(\"table-destroy\", this.clearBindings.bind(this));\n\t}\n\n\tmapBindings(bindings){\n\t\tfor(let key in bindings){\n\t\t\tif(Keybindings.actions[key]){\n\t\t\t\tif(bindings[key]){\n\t\t\t\t\tif(typeof bindings[key] !== \"object\"){\n\t\t\t\t\t\tbindings[key] = [bindings[key]];\n\t\t\t\t\t}\n\n\t\t\t\t\tbindings[key].forEach((binding) => {\n\t\t\t\t\t\tvar bindingList = Array.isArray(binding) ?  binding : [binding];\n\t\t\t\t\t\t\n\t\t\t\t\t\tbindingList.forEach((item) => {\n\t\t\t\t\t\t\tthis.mapBinding(key, item);\n\t\t\t\t\t\t});\t\t\t\t\t\t\n\t\t\t\t\t});\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tconsole.warn(\"Key Binding Error - no such action:\", key);\n\t\t\t}\n\t\t}\n\t}\n\n\tmapBinding(action, symbolsList){\n\t\tvar binding = {\n\t\t\taction: Keybindings.actions[action],\n\t\t\tkeys: [],\n\t\t\tctrl: false,\n\t\t\tshift: false,\n\t\t\tmeta: false,\n\t\t};\n\n\t\tvar symbols = symbolsList.toString().toLowerCase().split(\" \").join(\"\").split(\"+\");\n\n\t\tsymbols.forEach((symbol) => {\n\t\t\tswitch(symbol){\n\t\t\t\tcase \"ctrl\":\n\t\t\t\t\tbinding.ctrl = true;\n\t\t\t\t\tbreak;\n\n\t\t\t\tcase \"shift\":\n\t\t\t\t\tbinding.shift = true;\n\t\t\t\t\tbreak;\n\n\t\t\t\tcase \"meta\":\n\t\t\t\t\tbinding.meta = true;\n\t\t\t\t\tbreak;\n\n\t\t\t\tdefault:\n\t\t\t\t\tsymbol = isNaN(symbol) ? symbol.toUpperCase().charCodeAt(0) : parseInt(symbol);\n\t\t\t\t\tbinding.keys.push(symbol);\n\n\t\t\t\t\tif(!this.watchKeys[symbol]){\n\t\t\t\t\t\tthis.watchKeys[symbol] = [];\n\t\t\t\t\t}\n\n\t\t\t\t\tthis.watchKeys[symbol].push(binding);\n\t\t\t}\n\t\t});\n\t}\n\n\tbindEvents(){\n\t\tvar self = this;\n\n\t\tthis.keyupBinding = function(e){\n\t\t\tvar code = e.keyCode;\n\t\t\tvar bindings = self.watchKeys[code];\n\n\t\t\tif(bindings){\n\n\t\t\t\tself.pressedKeys.push(code);\n\n\t\t\t\tbindings.forEach(function(binding){\n\t\t\t\t\tself.checkBinding(e, binding);\n\t\t\t\t});\n\t\t\t}\n\t\t};\n\n\t\tthis.keydownBinding = function(e){\n\t\t\tvar code = e.keyCode;\n\t\t\tvar bindings = self.watchKeys[code];\n\n\t\t\tif(bindings){\n\n\t\t\t\tvar index = self.pressedKeys.indexOf(code);\n\n\t\t\t\tif(index > -1){\n\t\t\t\t\tself.pressedKeys.splice(index, 1);\n\t\t\t\t}\n\t\t\t}\n\t\t};\n\n\t\tthis.table.element.addEventListener(\"keydown\", this.keyupBinding);\n\n\t\tthis.table.element.addEventListener(\"keyup\", this.keydownBinding);\n\t}\n\n\tclearBindings(){\n\t\tif(this.keyupBinding){\n\t\t\tthis.table.element.removeEventListener(\"keydown\", this.keyupBinding);\n\t\t}\n\n\t\tif(this.keydownBinding){\n\t\t\tthis.table.element.removeEventListener(\"keyup\", this.keydownBinding);\n\t\t}\n\t}\n\n\tcheckBinding(e, binding){\n\t\tvar match = true;\n\n\t\tif(e.ctrlKey == binding.ctrl && e.shiftKey == binding.shift && e.metaKey == binding.meta){\n\t\t\tbinding.keys.forEach((key) => {\n\t\t\t\tvar index = this.pressedKeys.indexOf(key);\n\n\t\t\t\tif(index == -1){\n\t\t\t\t\tmatch = false;\n\t\t\t\t}\n\t\t\t});\n\n\t\t\tif(match){\n\t\t\t\tbinding.action.call(this, e);\n\t\t\t}\n\n\t\t\treturn true;\n\t\t}\n\n\t\treturn false;\n\t}\n}\n\nKeybindings.moduleName = \"keybindings\";\n\n//load defaults\nKeybindings.bindings = defaultBindings;\nKeybindings.actions = defaultActions;\n\nclass Menu extends Module{\n\t\n\tconstructor(table){\n\t\tsuper(table);\n\t\t\n\t\tthis.menuContainer = null;\n\t\tthis.nestedMenuBlock = false;\n\t\t\n\t\tthis.currentComponent = null;\n\t\tthis.rootPopup = null;\n\t\t\n\t\tthis.columnSubscribers = {};\n\t\t\n\t\tthis.registerTableOption(\"menuContainer\", undefined); //deprecated\n\t\t\n\t\tthis.registerTableOption(\"rowContextMenu\", false);\n\t\tthis.registerTableOption(\"rowClickMenu\", false);\n\t\tthis.registerTableOption(\"rowDblClickMenu\", false);\n\t\tthis.registerTableOption(\"groupContextMenu\", false);\n\t\tthis.registerTableOption(\"groupClickMenu\", false);\n\t\tthis.registerTableOption(\"groupDblClickMenu\", false);\n\t\t\n\t\tthis.registerColumnOption(\"headerContextMenu\");\n\t\tthis.registerColumnOption(\"headerClickMenu\");\n\t\tthis.registerColumnOption(\"headerDblClickMenu\");\n\t\tthis.registerColumnOption(\"headerMenu\");\n\t\tthis.registerColumnOption(\"headerMenuIcon\");\n\t\tthis.registerColumnOption(\"contextMenu\");\n\t\tthis.registerColumnOption(\"clickMenu\");\n\t\tthis.registerColumnOption(\"dblClickMenu\");\n\t\t\n\t}\n\t\n\tinitialize(){\n\t\tthis.deprecatedOptionsCheck();\n\t\tthis.initializeRowWatchers();\n\t\tthis.initializeGroupWatchers();\n\t\t\n\t\tthis.subscribe(\"column-init\", this.initializeColumn.bind(this));\n\t}\n\t\n\tdeprecatedOptionsCheck(){\n\t\tif(!this.deprecationCheck(\"menuContainer\", \"popupContainer\")){\n\t\t\tthis.table.options.popupContainer = this.table.options.menuContainer;\n\t\t}\n\t}\t\n\t\n\tinitializeRowWatchers(){\n\t\tif(this.table.options.rowContextMenu){\n\t\t\tthis.subscribe(\"row-contextmenu\", this.loadMenuEvent.bind(this, this.table.options.rowContextMenu));\n\t\t\tthis.table.on(\"rowTapHold\", this.loadMenuEvent.bind(this, this.table.options.rowContextMenu));\n\t\t}\n\t\t\n\t\tif(this.table.options.rowClickMenu){\n\t\t\tthis.subscribe(\"row-click\", this.loadMenuEvent.bind(this, this.table.options.rowClickMenu));\n\t\t}\n\t\t\n\t\tif(this.table.options.rowDblClickMenu){\n\t\t\tthis.subscribe(\"row-dblclick\", this.loadMenuEvent.bind(this, this.table.options.rowDblClickMenu));\n\t\t}\n\t}\n\t\n\tinitializeGroupWatchers(){\n\t\tif(this.table.options.groupContextMenu){\n\t\t\tthis.subscribe(\"group-contextmenu\", this.loadMenuEvent.bind(this, this.table.options.groupContextMenu));\n\t\t\tthis.table.on(\"groupTapHold\", this.loadMenuEvent.bind(this, this.table.options.groupContextMenu));\n\t\t}\n\t\t\n\t\tif(this.table.options.groupClickMenu){\n\t\t\tthis.subscribe(\"group-click\", this.loadMenuEvent.bind(this, this.table.options.groupClickMenu));\n\t\t}\n\t\t\n\t\tif(this.table.options.groupDblClickMenu){\n\t\t\tthis.subscribe(\"group-dblclick\", this.loadMenuEvent.bind(this, this.table.options.groupDblClickMenu));\n\t\t}\n\t}\n\n\tinitializeColumn(column){\n\t\tvar\tdef = column.definition;\n\t\t\n\t\t//handle column events\n\t\tif(def.headerContextMenu && !this.columnSubscribers.headerContextMenu){\n\t\t\tthis.columnSubscribers.headerContextMenu = this.loadMenuTableColumnEvent.bind(this, \"headerContextMenu\");\n\t\t\tthis.subscribe(\"column-contextmenu\", this.columnSubscribers.headerContextMenu);\n\t\t\tthis.table.on(\"headerTapHold\", this.loadMenuTableColumnEvent.bind(this, \"headerContextMenu\"));\n\t\t}\n\t\t\n\t\tif(def.headerClickMenu && !this.columnSubscribers.headerClickMenu){\n\t\t\tthis.columnSubscribers.headerClickMenu = this.loadMenuTableColumnEvent.bind(this, \"headerClickMenu\");\n\t\t\tthis.subscribe(\"column-click\", this.columnSubscribers.headerClickMenu);\n\t\t}\n\t\t\n\t\tif(def.headerDblClickMenu && !this.columnSubscribers.headerDblClickMenu){\n\t\t\tthis.columnSubscribers.headerDblClickMenu = this.loadMenuTableColumnEvent.bind(this, \"headerDblClickMenu\");\n\t\t\tthis.subscribe(\"column-dblclick\", this.columnSubscribers.headerDblClickMenu);\n\t\t}\n\t\t\n\t\tif(def.headerMenu){\n\t\t\tthis.initializeColumnHeaderMenu(column);\n\t\t}\n\t\t\n\t\t//handle cell events\n\t\tif(def.contextMenu && !this.columnSubscribers.contextMenu){\n\t\t\tthis.columnSubscribers.contextMenu = this.loadMenuTableCellEvent.bind(this, \"contextMenu\");\n\t\t\tthis.subscribe(\"cell-contextmenu\", this.columnSubscribers.contextMenu);\n\t\t\tthis.table.on(\"cellTapHold\", this.loadMenuTableCellEvent.bind(this, \"contextMenu\"));\n\t\t}\n\t\t\n\t\tif(def.clickMenu && !this.columnSubscribers.clickMenu){\n\t\t\tthis.columnSubscribers.clickMenu = this.loadMenuTableCellEvent.bind(this, \"clickMenu\");\n\t\t\tthis.subscribe(\"cell-click\", this.columnSubscribers.clickMenu);\n\t\t}\n\t\t\n\t\tif(def.dblClickMenu && !this.columnSubscribers.dblClickMenu){\n\t\t\tthis.columnSubscribers.dblClickMenu = this.loadMenuTableCellEvent.bind(this, \"dblClickMenu\");\n\t\t\tthis.subscribe(\"cell-dblclick\", this.columnSubscribers.dblClickMenu);\n\t\t}\n\t}\n\t\n\tinitializeColumnHeaderMenu(column){\n\t\tvar icon = column.definition.headerMenuIcon,\n\t\theaderMenuEl;\n\t\t\n\t\theaderMenuEl = document.createElement(\"span\");\n\t\theaderMenuEl.classList.add(\"tabulator-header-popup-button\");\n\t\t\n\t\tif(icon){\n\t\t\tif(typeof icon === \"function\"){\n\t\t\t\ticon = icon(column.getComponent());\n\t\t\t}\n\t\t\t\n\t\t\tif(icon instanceof HTMLElement){\n\t\t\t\theaderMenuEl.appendChild(icon);\n\t\t\t}else {\n\t\t\t\theaderMenuEl.innerHTML = icon;\n\t\t\t}\n\t\t}else {\n\t\t\theaderMenuEl.innerHTML = \"&vellip;\";\n\t\t}\n\t\t\n\t\theaderMenuEl.addEventListener(\"click\", (e) => {\n\t\t\te.stopPropagation();\n\t\t\te.preventDefault();\n\t\t\t\n\t\t\tthis.loadMenuEvent(column.definition.headerMenu, e, column);\n\t\t});\n\t\t\n\t\tcolumn.titleElement.insertBefore(headerMenuEl, column.titleElement.firstChild);\n\t}\n\t\n\tloadMenuTableCellEvent(option, e, cell){\n\t\tif(cell._cell){\n\t\t\tcell = cell._cell;\n\t\t}\n\t\t\n\t\tif(cell.column.definition[option]){\n\t\t\tthis.loadMenuEvent(cell.column.definition[option], e, cell);\n\t\t}\n\t}\n\t\n\tloadMenuTableColumnEvent(option, e, column){\n\t\tif(column._column){\n\t\t\tcolumn = column._column;\n\t\t}\n\t\t\n\t\tif(column.definition[option]){\n\t\t\tthis.loadMenuEvent(column.definition[option], e, column);\n\t\t}\n\t}\n\t\n\tloadMenuEvent(menu, e, component){\n\t\tif(component._group){\n\t\t\tcomponent = component._group;\n\t\t}else if(component._row){\n\t\t\tcomponent = component._row;\n\t\t}\n\t\t\n\t\tmenu = typeof menu == \"function\" ? menu.call(this.table, e, component.getComponent()) : menu;\n\t\t\n\t\tthis.loadMenu(e, component, menu);\n\t}\n\t\n\tloadMenu(e, component, menu, parentEl, parentPopup){\n\t\tvar touch = !(e instanceof MouseEvent),\t\t\n\t\tmenuEl = document.createElement(\"div\"),\n\t\tpopup;\n\t\t\n\t\tmenuEl.classList.add(\"tabulator-menu\");\n\t\t\n\t\tif(!touch){\n\t\t\te.preventDefault();\n\t\t}\n\t\t\n\t\t//abort if no menu set\n\t\tif(!menu || !menu.length){\n\t\t\treturn;\n\t\t}\n\t\t\n\t\tif(!parentEl){\n\t\t\tif(this.nestedMenuBlock){\n\t\t\t\t//abort if child menu already open\n\t\t\t\tif(this.rootPopup){\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tthis.nestedMenuBlock = setTimeout(() => {\n\t\t\t\t\tthis.nestedMenuBlock = false;\n\t\t\t\t}, 100);\n\t\t\t}\n\t\t\t\n\t\t\tif(this.rootPopup){\n\t\t\t\tthis.rootPopup.hide();\t\n\t\t\t}\n\t\t\t\n\t\t\tthis.rootPopup = popup = this.popup(menuEl);\n\t\t\t\n\t\t}else {\n\t\t\tpopup = parentPopup.child(menuEl);\n\t\t}\n\t\t\n\t\tmenu.forEach((item) => {\n\t\t\tvar itemEl = document.createElement(\"div\"),\n\t\t\tlabel = item.label,\n\t\t\tdisabled = item.disabled;\n\t\t\t\n\t\t\tif(item.separator){\n\t\t\t\titemEl.classList.add(\"tabulator-menu-separator\");\n\t\t\t}else {\n\t\t\t\titemEl.classList.add(\"tabulator-menu-item\");\n\t\t\t\t\n\t\t\t\tif(typeof label == \"function\"){\n\t\t\t\t\tlabel = label.call(this.table, component.getComponent());\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tif(label instanceof Node){\n\t\t\t\t\titemEl.appendChild(label);\n\t\t\t\t}else {\n\t\t\t\t\titemEl.innerHTML = label;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tif(typeof disabled == \"function\"){\n\t\t\t\t\tdisabled = disabled.call(this.table, component.getComponent());\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tif(disabled){\n\t\t\t\t\titemEl.classList.add(\"tabulator-menu-item-disabled\");\n\t\t\t\t\titemEl.addEventListener(\"click\", (e) => {\n\t\t\t\t\t\te.stopPropagation();\n\t\t\t\t\t});\n\t\t\t\t}else {\n\t\t\t\t\tif(item.menu && item.menu.length){\n\t\t\t\t\t\titemEl.addEventListener(\"click\", (e) => {\n\t\t\t\t\t\t\te.stopPropagation();\n\t\t\t\t\t\t\tthis.loadMenu(e, component, item.menu, itemEl, popup);\n\t\t\t\t\t\t});\n\t\t\t\t\t}else {\n\t\t\t\t\t\tif(item.action){\n\t\t\t\t\t\t\titemEl.addEventListener(\"click\", (e) => {\n\t\t\t\t\t\t\t\titem.action(e, component.getComponent());\n\t\t\t\t\t\t\t});\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tif(item.menu && item.menu.length){\n\t\t\t\t\titemEl.classList.add(\"tabulator-menu-item-submenu\");\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\tmenuEl.appendChild(itemEl);\n\t\t});\n\t\t\n\t\tmenuEl.addEventListener(\"click\", (e) => {\n\t\t\tif(this.rootPopup){\n\t\t\t\tthis.rootPopup.hide();\n\t\t\t}\n\t\t});\n\t\t\n\t\tpopup.show(parentEl || e);\n\t\t\n\t\tif(popup === this.rootPopup){\n\t\t\tthis.rootPopup.hideOnBlur(() => {\n\t\t\t\tthis.rootPopup = null;\n\t\t\t\t\n\t\t\t\tif(this.currentComponent){\n\t\t\t\t\tthis.dispatch(\"menu-closed\", menu, popup);\n\t\t\t\t\tthis.dispatchExternal(\"menuClosed\", this.currentComponent.getComponent());\n\t\t\t\t\tthis.currentComponent = null;\n\t\t\t\t}\n\t\t\t});\n\t\t\t\n\t\t\tthis.currentComponent = component;\n\t\t\t\n\t\t\tthis.dispatch(\"menu-opened\", menu, popup);\n\t\t\tthis.dispatchExternal(\"menuOpened\", component.getComponent());\n\t\t}\n\t}\n}\n\nMenu.moduleName = \"menu\";\n\nclass MoveColumns extends Module{\n\t\n\tconstructor(table){\n\t\tsuper(table);\n\t\t\n\t\tthis.placeholderElement = this.createPlaceholderElement();\n\t\tthis.hoverElement = false; //floating column header element\n\t\tthis.checkTimeout = false; //click check timeout holder\n\t\tthis.checkPeriod = 250; //period to wait on mousedown to consider this a move and not a click\n\t\tthis.moving = false; //currently moving column\n\t\tthis.toCol = false; //destination column\n\t\tthis.toColAfter = false; //position of moving column relative to the destination column\n\t\tthis.startX = 0; //starting position within header element\n\t\tthis.autoScrollMargin = 40; //auto scroll on edge when within margin\n\t\tthis.autoScrollStep = 5; //auto scroll distance in pixels\n\t\tthis.autoScrollTimeout = false; //auto scroll timeout\n\t\tthis.touchMove = false;\n\t\t\n\t\tthis.moveHover = this.moveHover.bind(this);\n\t\tthis.endMove = this.endMove.bind(this);\n\t\t\n\t\tthis.registerTableOption(\"movableColumns\", false); //enable movable columns\n\t}\n\t\n\tcreatePlaceholderElement(){\n\t\tvar el = document.createElement(\"div\");\n\t\t\n\t\tel.classList.add(\"tabulator-col\");\n\t\tel.classList.add(\"tabulator-col-placeholder\");\n\t\t\n\t\treturn el;\n\t}\n\t\n\tinitialize(){\n\t\tif(this.table.options.movableColumns){\n\t\t\tthis.subscribe(\"column-init\", this.initializeColumn.bind(this));\n\t\t\tthis.subscribe(\"alert-show\", this.abortMove.bind(this));\n\t\t}\n\t}\n\n\tabortMove(){\n\t\tclearTimeout(this.checkTimeout);\n\t}\n\t\n\tinitializeColumn(column){\n\t\tvar self = this,\n\t\tconfig = {},\n\t\tcolEl;\n\t\t\n\t\tif(!column.modules.frozen && !column.isGroup){\n\t\t\tcolEl = column.getElement();\n\t\t\t\n\t\t\tconfig.mousemove = function(e){\n\t\t\t\tif(column.parent === self.moving.parent){\n\t\t\t\t\tif((((self.touchMove ? e.touches[0].pageX : e.pageX) - Helpers.elOffset(colEl).left) + self.table.columnManager.contentsElement.scrollLeft) > (column.getWidth() / 2)){\n\t\t\t\t\t\tif(self.toCol !== column || !self.toColAfter){\n\t\t\t\t\t\t\tcolEl.parentNode.insertBefore(self.placeholderElement, colEl.nextSibling);\n\t\t\t\t\t\t\tself.moveColumn(column, true);\n\t\t\t\t\t\t}\n\t\t\t\t\t}else {\n\t\t\t\t\t\tif(self.toCol !== column || self.toColAfter){\n\t\t\t\t\t\t\tcolEl.parentNode.insertBefore(self.placeholderElement, colEl);\n\t\t\t\t\t\t\tself.moveColumn(column, false);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}.bind(self);\n\t\t\t\n\t\t\tcolEl.addEventListener(\"mousedown\", function(e){\n\t\t\t\tself.touchMove = false;\n\t\t\t\tif(e.which === 1){\n\t\t\t\t\tself.checkTimeout = setTimeout(function(){\n\t\t\t\t\t\tself.startMove(e, column);\n\t\t\t\t\t}, self.checkPeriod);\n\t\t\t\t}\n\t\t\t});\n\t\t\t\n\t\t\tcolEl.addEventListener(\"mouseup\", function(e){\n\t\t\t\tif(e.which === 1){\n\t\t\t\t\tif(self.checkTimeout){\n\t\t\t\t\t\tclearTimeout(self.checkTimeout);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t});\n\t\t\t\n\t\t\tself.bindTouchEvents(column);\n\t\t}\n\t\t\n\t\tcolumn.modules.moveColumn = config;\n\t}\n\t\n\tbindTouchEvents(column){\n\t\tvar colEl = column.getElement(),\n\t\tstartXMove = false, //shifting center position of the cell\n\t\tnextCol, prevCol, nextColWidth, prevColWidth, nextColWidthLast, prevColWidthLast;\n\t\t\n\t\tcolEl.addEventListener(\"touchstart\", (e) => {\n\t\t\tthis.checkTimeout = setTimeout(() => {\n\t\t\t\tthis.touchMove = true;\n\t\t\t\tnextCol = column.nextColumn();\n\t\t\t\tnextColWidth = nextCol ? nextCol.getWidth()/2 : 0;\n\t\t\t\tprevCol = column.prevColumn();\n\t\t\t\tprevColWidth = prevCol ? prevCol.getWidth()/2 : 0;\n\t\t\t\tnextColWidthLast = 0;\n\t\t\t\tprevColWidthLast = 0;\n\t\t\t\tstartXMove = false;\n\t\t\t\t\n\t\t\t\tthis.startMove(e, column);\n\t\t\t}, this.checkPeriod);\n\t\t}, {passive: true});\n\t\t\n\t\tcolEl.addEventListener(\"touchmove\", (e) => {\n\t\t\tvar diff, moveToCol;\n\t\t\t\n\t\t\tif(this.moving){\n\t\t\t\tthis.moveHover(e);\n\t\t\t\t\n\t\t\t\tif(!startXMove){\n\t\t\t\t\tstartXMove = e.touches[0].pageX;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tdiff = e.touches[0].pageX - startXMove;\n\t\t\t\t\n\t\t\t\tif(diff > 0){\n\t\t\t\t\tif(nextCol && diff - nextColWidthLast > nextColWidth){\n\t\t\t\t\t\tmoveToCol = nextCol;\n\t\t\t\t\t\t\n\t\t\t\t\t\tif(moveToCol !== column){\n\t\t\t\t\t\t\tstartXMove = e.touches[0].pageX;\n\t\t\t\t\t\t\tmoveToCol.getElement().parentNode.insertBefore(this.placeholderElement, moveToCol.getElement().nextSibling);\n\t\t\t\t\t\t\tthis.moveColumn(moveToCol, true);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}else {\n\t\t\t\t\tif(prevCol && -diff - prevColWidthLast >  prevColWidth){\n\t\t\t\t\t\tmoveToCol = prevCol;\n\t\t\t\t\t\t\n\t\t\t\t\t\tif(moveToCol !== column){\n\t\t\t\t\t\t\tstartXMove = e.touches[0].pageX;\n\t\t\t\t\t\t\tmoveToCol.getElement().parentNode.insertBefore(this.placeholderElement, moveToCol.getElement());\n\t\t\t\t\t\t\tthis.moveColumn(moveToCol, false);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tif(moveToCol){\n\t\t\t\t\tnextCol = moveToCol.nextColumn();\n\t\t\t\t\tnextColWidthLast = nextColWidth;\n\t\t\t\t\tnextColWidth = nextCol ? nextCol.getWidth() / 2 : 0;\n\t\t\t\t\tprevCol = moveToCol.prevColumn();\n\t\t\t\t\tprevColWidthLast = prevColWidth;\n\t\t\t\t\tprevColWidth = prevCol ? prevCol.getWidth() / 2 : 0;\n\t\t\t\t}\n\t\t\t}\n\t\t}, {passive: true});\n\t\t\n\t\tcolEl.addEventListener(\"touchend\", (e) => {\n\t\t\tif(this.checkTimeout){\n\t\t\t\tclearTimeout(this.checkTimeout);\n\t\t\t}\n\t\t\tif(this.moving){\n\t\t\t\tthis.endMove(e);\n\t\t\t}\n\t\t});\n\t}\n\t\n\tstartMove(e, column){\n\t\tvar element = column.getElement(),\n\t\theaderElement = this.table.columnManager.getContentsElement(),\n\t\theadersElement = this.table.columnManager.getHeadersElement();\n\t\t\n\t\tthis.moving = column;\n\t\tthis.startX = (this.touchMove ? e.touches[0].pageX : e.pageX) - Helpers.elOffset(element).left;\n\t\t\n\t\tthis.table.element.classList.add(\"tabulator-block-select\");\n\t\t\n\t\t//create placeholder\n\t\tthis.placeholderElement.style.width = column.getWidth() + \"px\";\n\t\tthis.placeholderElement.style.height = column.getHeight() + \"px\";\n\t\t\n\t\telement.parentNode.insertBefore(this.placeholderElement, element);\n\t\telement.parentNode.removeChild(element);\n\t\t\n\t\t//create hover element\n\t\tthis.hoverElement = element.cloneNode(true);\n\t\tthis.hoverElement.classList.add(\"tabulator-moving\");\n\t\t\n\t\theaderElement.appendChild(this.hoverElement);\n\t\t\n\t\tthis.hoverElement.style.left = \"0\";\n\t\tthis.hoverElement.style.bottom = (headerElement.clientHeight - headersElement.offsetHeight) + \"px\";\n\t\t\n\t\tif(!this.touchMove){\n\t\t\tthis._bindMouseMove();\n\t\t\t\n\t\t\tdocument.body.addEventListener(\"mousemove\", this.moveHover);\n\t\t\tdocument.body.addEventListener(\"mouseup\", this.endMove);\n\t\t}\n\t\t\n\t\tthis.moveHover(e);\n\t}\n\t\n\t_bindMouseMove(){\n\t\tthis.table.columnManager.columnsByIndex.forEach(function(column){\n\t\t\tif(column.modules.moveColumn.mousemove){\n\t\t\t\tcolumn.getElement().addEventListener(\"mousemove\", column.modules.moveColumn.mousemove);\n\t\t\t}\n\t\t});\n\t}\n\t\n\t_unbindMouseMove(){\n\t\tthis.table.columnManager.columnsByIndex.forEach(function(column){\n\t\t\tif(column.modules.moveColumn.mousemove){\n\t\t\t\tcolumn.getElement().removeEventListener(\"mousemove\", column.modules.moveColumn.mousemove);\n\t\t\t}\n\t\t});\n\t}\n\t\n\tmoveColumn(column, after){\n\t\tvar movingCells = this.moving.getCells();\n\t\t\n\t\tthis.toCol = column;\n\t\tthis.toColAfter = after;\n\t\t\n\t\tif(after){\n\t\t\tcolumn.getCells().forEach(function(cell, i){\n\t\t\t\tvar cellEl = cell.getElement(true);\n\t\t\t\t\n\t\t\t\tif(cellEl.parentNode && movingCells[i]){\n\t\t\t\t\tcellEl.parentNode.insertBefore(movingCells[i].getElement(), cellEl.nextSibling);\n\t\t\t\t}\n\t\t\t});\n\t\t}else {\n\t\t\tcolumn.getCells().forEach(function(cell, i){\n\t\t\t\tvar cellEl = cell.getElement(true);\n\t\t\t\t\n\t\t\t\tif(cellEl.parentNode && movingCells[i]){\n\t\t\t\t\tcellEl.parentNode.insertBefore(movingCells[i].getElement(), cellEl);\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\t}\n\t\n\tendMove(e){\n\t\tif(e.which === 1 || this.touchMove){\n\t\t\tthis._unbindMouseMove();\n\t\t\t\n\t\t\tthis.placeholderElement.parentNode.insertBefore(this.moving.getElement(), this.placeholderElement.nextSibling);\n\t\t\tthis.placeholderElement.parentNode.removeChild(this.placeholderElement);\n\t\t\tthis.hoverElement.parentNode.removeChild(this.hoverElement);\n\t\t\t\n\t\t\tthis.table.element.classList.remove(\"tabulator-block-select\");\n\t\t\t\n\t\t\tif(this.toCol){\n\t\t\t\tthis.table.columnManager.moveColumnActual(this.moving, this.toCol, this.toColAfter);\n\t\t\t}\n\t\t\t\n\t\t\tthis.moving = false;\n\t\t\tthis.toCol = false;\n\t\t\tthis.toColAfter = false;\n\t\t\t\n\t\t\tif(!this.touchMove){\n\t\t\t\tdocument.body.removeEventListener(\"mousemove\", this.moveHover);\n\t\t\t\tdocument.body.removeEventListener(\"mouseup\", this.endMove);\n\t\t\t}\n\t\t}\n\t}\n\t\n\tmoveHover(e){\n\t\tvar columnHolder = this.table.columnManager.getContentsElement(),\n\t\tscrollLeft = columnHolder.scrollLeft,\n\t\txPos = ((this.touchMove ? e.touches[0].pageX : e.pageX) - Helpers.elOffset(columnHolder).left) + scrollLeft,\n\t\tscrollPos;\n\t\t\n\t\tthis.hoverElement.style.left = (xPos - this.startX) + \"px\";\n\t\t\n\t\tif(xPos - scrollLeft < this.autoScrollMargin){\n\t\t\tif(!this.autoScrollTimeout){\n\t\t\t\tthis.autoScrollTimeout = setTimeout(() => {\n\t\t\t\t\tscrollPos = Math.max(0,scrollLeft-5);\n\t\t\t\t\tthis.table.rowManager.getElement().scrollLeft = scrollPos;\n\t\t\t\t\tthis.autoScrollTimeout = false;\n\t\t\t\t}, 1);\n\t\t\t}\n\t\t}\n\t\t\n\t\tif(scrollLeft + columnHolder.clientWidth - xPos < this.autoScrollMargin){\n\t\t\tif(!this.autoScrollTimeout){\n\t\t\t\tthis.autoScrollTimeout = setTimeout(() => {\n\t\t\t\t\tscrollPos = Math.min(columnHolder.clientWidth, scrollLeft+5);\n\t\t\t\t\tthis.table.rowManager.getElement().scrollLeft = scrollPos;\n\t\t\t\t\tthis.autoScrollTimeout = false;\n\t\t\t\t}, 1);\n\t\t\t}\n\t\t}\n\t}\n}\n\nMoveColumns.moduleName = \"moveColumn\";\n\nclass MoveRows extends Module{\n\n\tconstructor(table){\n\t\tsuper(table);\n\n\t\tthis.placeholderElement = this.createPlaceholderElement();\n\t\tthis.hoverElement = false; //floating row header element\n\t\tthis.checkTimeout = false; //click check timeout holder\n\t\tthis.checkPeriod = 150; //period to wait on mousedown to consider this a move and not a click\n\t\tthis.moving = false; //currently moving row\n\t\tthis.toRow = false; //destination row\n\t\tthis.toRowAfter = false; //position of moving row relative to the destination row\n\t\tthis.hasHandle = false; //row has handle instead of fully movable row\n\t\tthis.startY = 0; //starting Y position within header element\n\t\tthis.startX = 0; //starting X position within header element\n\n\t\tthis.moveHover = this.moveHover.bind(this);\n\t\tthis.endMove = this.endMove.bind(this);\n\t\tthis.tableRowDropEvent = false;\n\n\t\tthis.touchMove = false;\n\n\t\tthis.connection = false;\n\t\tthis.connectionSelectorsTables = false;\n\t\tthis.connectionSelectorsElements = false;\n\t\tthis.connectionElements = [];\n\t\tthis.connections = [];\n\n\t\tthis.connectedTable = false;\n\t\tthis.connectedRow = false;\n\n\t\tthis.registerTableOption(\"movableRows\", false); //enable movable rows\n\t\tthis.registerTableOption(\"movableRowsConnectedTables\", false); //tables for movable rows to be connected to\n\t\tthis.registerTableOption(\"movableRowsConnectedElements\", false); //other elements for movable rows to be connected to\n\t\tthis.registerTableOption(\"movableRowsSender\", false);\n\t\tthis.registerTableOption(\"movableRowsReceiver\", \"insert\");\n\n\t\tthis.registerColumnOption(\"rowHandle\");\n\t}\n\n\tcreatePlaceholderElement(){\n\t\tvar el = document.createElement(\"div\");\n\n\t\tel.classList.add(\"tabulator-row\");\n\t\tel.classList.add(\"tabulator-row-placeholder\");\n\n\t\treturn el;\n\t}\n\n\tinitialize(){\n\t\tif(this.table.options.movableRows){\n\t\t\tthis.connectionSelectorsTables = this.table.options.movableRowsConnectedTables;\n\t\t\tthis.connectionSelectorsElements = this.table.options.movableRowsConnectedElements;\n\n\t\t\tthis.connection = this.connectionSelectorsTables || this.connectionSelectorsElements;\n\n\t\t\tthis.subscribe(\"cell-init\", this.initializeCell.bind(this));\n\t\t\tthis.subscribe(\"column-init\", this.initializeColumn.bind(this));\n\t\t\tthis.subscribe(\"row-init\", this.initializeRow.bind(this));\n\t\t}\n\t}\n\n\tinitializeGroupHeader(group){\n\t\tvar self = this,\n\t\tconfig = {};\n\n\t\t//inter table drag drop\n\t\tconfig.mouseup = function(e){\n\t\t\tself.tableRowDrop(e, group);\n\t\t}.bind(self);\n\n\t\t//same table drag drop\n\t\tconfig.mousemove = function(e){\n\t\t\tvar rowEl;\n\n\t\t\tif(((e.pageY - Helpers.elOffset(group.element).top) + self.table.rowManager.element.scrollTop) > (group.getHeight() / 2)){\n\t\t\t\tif(self.toRow !== group || !self.toRowAfter){\n\t\t\t\t\trowEl = group.getElement();\n\t\t\t\t\trowEl.parentNode.insertBefore(self.placeholderElement, rowEl.nextSibling);\n\t\t\t\t\tself.moveRow(group, true);\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tif(self.toRow !== group || self.toRowAfter){\n\t\t\t\t\trowEl = group.getElement();\n\t\t\t\t\tif(rowEl.previousSibling){\n\t\t\t\t\t\trowEl.parentNode.insertBefore(self.placeholderElement, rowEl);\n\t\t\t\t\t\tself.moveRow(group, false);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}.bind(self);\n\n\t\tgroup.modules.moveRow = config;\n\t}\n\n\tinitializeRow(row){\n\t\tvar self = this,\n\t\tconfig = {},\n\t\trowEl;\n\n\t\t//inter table drag drop\n\t\tconfig.mouseup = function(e){\n\t\t\tself.tableRowDrop(e, row);\n\t\t}.bind(self);\n\n\t\t//same table drag drop\n\t\tconfig.mousemove = function(e){\n\t\t\tvar rowEl = row.getElement();\n\n\t\t\tif(((e.pageY - Helpers.elOffset(rowEl).top) + self.table.rowManager.element.scrollTop) > (row.getHeight() / 2)){\n\t\t\t\tif(self.toRow !== row || !self.toRowAfter){\n\t\t\t\t\trowEl.parentNode.insertBefore(self.placeholderElement, rowEl.nextSibling);\n\t\t\t\t\tself.moveRow(row, true);\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tif(self.toRow !== row || self.toRowAfter){\n\t\t\t\t\trowEl.parentNode.insertBefore(self.placeholderElement, rowEl);\n\t\t\t\t\tself.moveRow(row, false);\n\t\t\t\t}\n\t\t\t}\n\t\t}.bind(self);\n\n\n\t\tif(!this.hasHandle){\n\n\t\t\trowEl = row.getElement();\n\n\t\t\trowEl.addEventListener(\"mousedown\", function(e){\n\t\t\t\tif(e.which === 1){\n\t\t\t\t\tself.checkTimeout = setTimeout(function(){\n\t\t\t\t\t\tself.startMove(e, row);\n\t\t\t\t\t}, self.checkPeriod);\n\t\t\t\t}\n\t\t\t});\n\n\t\t\trowEl.addEventListener(\"mouseup\", function(e){\n\t\t\t\tif(e.which === 1){\n\t\t\t\t\tif(self.checkTimeout){\n\t\t\t\t\t\tclearTimeout(self.checkTimeout);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t});\n\n\t\t\tthis.bindTouchEvents(row, row.getElement());\n\t\t}\n\n\t\trow.modules.moveRow = config;\n\t}\n\n\tinitializeColumn(column){\n\t\tif(column.definition.rowHandle && this.table.options.movableRows !== false){\n\t\t\tthis.hasHandle = true;\n\t\t}\n\t}\n\n\tinitializeCell(cell){\n\t\tif(cell.column.definition.rowHandle && this.table.options.movableRows !== false){\n\t\t\tvar self = this,\n\t\t\tcellEl = cell.getElement(true);\n\n\t\t\tcellEl.addEventListener(\"mousedown\", function(e){\n\t\t\t\tif(e.which === 1){\n\t\t\t\t\tself.checkTimeout = setTimeout(function(){\n\t\t\t\t\t\tself.startMove(e, cell.row);\n\t\t\t\t\t}, self.checkPeriod);\n\t\t\t\t}\n\t\t\t});\n\n\t\t\tcellEl.addEventListener(\"mouseup\", function(e){\n\t\t\t\tif(e.which === 1){\n\t\t\t\t\tif(self.checkTimeout){\n\t\t\t\t\t\tclearTimeout(self.checkTimeout);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t});\n\n\t\t\tthis.bindTouchEvents(cell.row, cellEl);\n\t\t}\n\t}\n\n\tbindTouchEvents(row, element){\n\t\tvar startYMove = false, //shifting center position of the cell\n\t\tnextRow, prevRow, nextRowHeight, prevRowHeight, nextRowHeightLast, prevRowHeightLast;\n\n\t\telement.addEventListener(\"touchstart\", (e) => {\n\t\t\tthis.checkTimeout = setTimeout(() => {\n\t\t\t\tthis.touchMove = true;\n\t\t\t\tnextRow = row.nextRow();\n\t\t\t\tnextRowHeight = nextRow ? nextRow.getHeight()/2 : 0;\n\t\t\t\tprevRow = row.prevRow();\n\t\t\t\tprevRowHeight = prevRow ? prevRow.getHeight()/2 : 0;\n\t\t\t\tnextRowHeightLast = 0;\n\t\t\t\tprevRowHeightLast = 0;\n\t\t\t\tstartYMove = false;\n\n\t\t\t\tthis.startMove(e, row);\n\t\t\t}, this.checkPeriod);\n\t\t}, {passive: true});\n\t\tthis.moving, this.toRow, this.toRowAfter;\n\t\telement.addEventListener(\"touchmove\", (e) => {\n\n\t\t\tvar diff, moveToRow;\n\n\t\t\tif(this.moving){\n\t\t\t\te.preventDefault();\n\n\t\t\t\tthis.moveHover(e);\n\n\t\t\t\tif(!startYMove){\n\t\t\t\t\tstartYMove = e.touches[0].pageY;\n\t\t\t\t}\n\n\t\t\t\tdiff = e.touches[0].pageY - startYMove;\n\n\t\t\t\tif(diff > 0){\n\t\t\t\t\tif(nextRow && diff - nextRowHeightLast > nextRowHeight){\n\t\t\t\t\t\tmoveToRow = nextRow;\n\n\t\t\t\t\t\tif(moveToRow !== row){\n\t\t\t\t\t\t\tstartYMove = e.touches[0].pageY;\n\t\t\t\t\t\t\tmoveToRow.getElement().parentNode.insertBefore(this.placeholderElement, moveToRow.getElement().nextSibling);\n\t\t\t\t\t\t\tthis.moveRow(moveToRow, true);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}else {\n\t\t\t\t\tif(prevRow && -diff - prevRowHeightLast >  prevRowHeight){\n\t\t\t\t\t\tmoveToRow = prevRow;\n\n\t\t\t\t\t\tif(moveToRow !== row){\n\t\t\t\t\t\t\tstartYMove = e.touches[0].pageY;\n\t\t\t\t\t\t\tmoveToRow.getElement().parentNode.insertBefore(this.placeholderElement, moveToRow.getElement());\n\t\t\t\t\t\t\tthis.moveRow(moveToRow, false);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\tif(moveToRow){\n\t\t\t\t\tnextRow = moveToRow.nextRow();\n\t\t\t\t\tnextRowHeightLast = nextRowHeight;\n\t\t\t\t\tnextRowHeight = nextRow ? nextRow.getHeight() / 2 : 0;\n\t\t\t\t\tprevRow = moveToRow.prevRow();\n\t\t\t\t\tprevRowHeightLast = prevRowHeight;\n\t\t\t\t\tprevRowHeight = prevRow ? prevRow.getHeight() / 2 : 0;\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\n\t\telement.addEventListener(\"touchend\", (e) => {\n\t\t\tif(this.checkTimeout){\n\t\t\t\tclearTimeout(this.checkTimeout);\n\t\t\t}\n\t\t\tif(this.moving){\n\t\t\t\tthis.endMove(e);\n\t\t\t\tthis.touchMove = false;\n\t\t\t}\n\t\t});\n\t}\n\n\t_bindMouseMove(){\n\t\tthis.table.rowManager.getDisplayRows().forEach((row) => {\n\t\t\tif((row.type === \"row\" || row.type === \"group\") && row.modules.moveRow && row.modules.moveRow.mousemove){\n\t\t\t\trow.getElement().addEventListener(\"mousemove\", row.modules.moveRow.mousemove);\n\t\t\t}\n\t\t});\n\t}\n\n\t_unbindMouseMove(){\n\t\tthis.table.rowManager.getDisplayRows().forEach((row) => {\n\t\t\tif((row.type === \"row\" || row.type === \"group\") && row.modules.moveRow && row.modules.moveRow.mousemove){\n\t\t\t\trow.getElement().removeEventListener(\"mousemove\", row.modules.moveRow.mousemove);\n\t\t\t}\n\t\t});\n\t}\n\n\tstartMove(e, row){\n\t\tvar element = row.getElement();\n\n\t\tthis.setStartPosition(e, row);\n\n\t\tthis.moving = row;\n\n\t\tthis.table.element.classList.add(\"tabulator-block-select\");\n\n\t\t//create placeholder\n\t\tthis.placeholderElement.style.width = row.getWidth() + \"px\";\n\t\tthis.placeholderElement.style.height = row.getHeight() + \"px\";\n\n\t\tif(!this.connection){\n\t\t\telement.parentNode.insertBefore(this.placeholderElement, element);\n\t\t\telement.parentNode.removeChild(element);\n\t\t}else {\n\t\t\tthis.table.element.classList.add(\"tabulator-movingrow-sending\");\n\t\t\tthis.connectToTables(row);\n\t\t}\n\n\t\t//create hover element\n\t\tthis.hoverElement = element.cloneNode(true);\n\t\tthis.hoverElement.classList.add(\"tabulator-moving\");\n\n\t\tif(this.connection){\n\t\t\tdocument.body.appendChild(this.hoverElement);\n\t\t\tthis.hoverElement.style.left = \"0\";\n\t\t\tthis.hoverElement.style.top = \"0\";\n\t\t\tthis.hoverElement.style.width = this.table.element.clientWidth + \"px\";\n\t\t\tthis.hoverElement.style.whiteSpace = \"nowrap\";\n\t\t\tthis.hoverElement.style.overflow = \"hidden\";\n\t\t\tthis.hoverElement.style.pointerEvents = \"none\";\n\t\t}else {\n\t\t\tthis.table.rowManager.getTableElement().appendChild(this.hoverElement);\n\n\t\t\tthis.hoverElement.style.left = \"0\";\n\t\t\tthis.hoverElement.style.top = \"0\";\n\n\t\t\tthis._bindMouseMove();\n\t\t}\n\n\t\tdocument.body.addEventListener(\"mousemove\", this.moveHover);\n\t\tdocument.body.addEventListener(\"mouseup\", this.endMove);\n\n\t\tthis.dispatchExternal(\"rowMoving\", row.getComponent());\n\n\t\tthis.moveHover(e);\n\t}\n\n\tsetStartPosition(e, row){\n\t\tvar pageX = this.touchMove ? e.touches[0].pageX : e.pageX,\n\t\tpageY = this.touchMove ? e.touches[0].pageY : e.pageY,\n\t\telement, position;\n\n\t\telement = row.getElement();\n\t\tif(this.connection){\n\t\t\tposition = element.getBoundingClientRect();\n\n\t\t\tthis.startX = position.left - pageX + window.pageXOffset;\n\t\t\tthis.startY = position.top - pageY + window.pageYOffset;\n\t\t}else {\n\t\t\tthis.startY = (pageY - element.getBoundingClientRect().top);\n\t\t}\n\t}\n\n\tendMove(e){\n\t\tif(!e || e.which === 1 || this.touchMove){\n\t\t\tthis._unbindMouseMove();\n\n\t\t\tif(!this.connection){\n\t\t\t\tthis.placeholderElement.parentNode.insertBefore(this.moving.getElement(), this.placeholderElement.nextSibling);\n\t\t\t\tthis.placeholderElement.parentNode.removeChild(this.placeholderElement);\n\t\t\t}\n\n\t\t\tthis.hoverElement.parentNode.removeChild(this.hoverElement);\n\n\t\t\tthis.table.element.classList.remove(\"tabulator-block-select\");\n\n\t\t\tif(this.toRow){\n\t\t\t\tthis.table.rowManager.moveRow(this.moving, this.toRow, this.toRowAfter);\n\t\t\t}else {\n\t\t\t\tthis.dispatchExternal(\"rowMoveCancelled\", this.moving.getComponent());\n\t\t\t}\n\n\t\t\tthis.moving = false;\n\t\t\tthis.toRow = false;\n\t\t\tthis.toRowAfter = false;\n\n\t\t\tdocument.body.removeEventListener(\"mousemove\", this.moveHover);\n\t\t\tdocument.body.removeEventListener(\"mouseup\", this.endMove);\n\n\t\t\tif(this.connection){\n\t\t\t\tthis.table.element.classList.remove(\"tabulator-movingrow-sending\");\n\t\t\t\tthis.disconnectFromTables();\n\t\t\t}\n\t\t}\n\t}\n\n\tmoveRow(row, after){\n\t\tthis.toRow = row;\n\t\tthis.toRowAfter = after;\n\t}\n\n\tmoveHover(e){\n\t\tif(this.connection){\n\t\t\tthis.moveHoverConnections.call(this, e);\n\t\t}else {\n\t\t\tthis.moveHoverTable.call(this, e);\n\t\t}\n\t}\n\n\tmoveHoverTable(e){\n\t\tvar rowHolder = this.table.rowManager.getElement(),\n\t\tscrollTop = rowHolder.scrollTop,\n\t\tyPos = ((this.touchMove ? e.touches[0].pageY : e.pageY) - rowHolder.getBoundingClientRect().top) + scrollTop;\n\t\t\n\t\tthis.hoverElement.style.top = Math.min(yPos - this.startY, this.table.rowManager.element.scrollHeight - this.hoverElement.offsetHeight) + \"px\";\n\t}\n\n\tmoveHoverConnections(e){\n\t\tthis.hoverElement.style.left = (this.startX + (this.touchMove ? e.touches[0].pageX : e.pageX)) + \"px\";\n\t\tthis.hoverElement.style.top = (this.startY + (this.touchMove ? e.touches[0].pageY : e.pageY)) + \"px\";\n\t}\n\n\telementRowDrop(e, element, row){\n\t\tthis.dispatchExternal(\"movableRowsElementDrop\", e, element, row ? row.getComponent() : false);\n\t}\n\n\t//establish connection with other tables\n\tconnectToTables(row){\n\t\tvar connectionTables;\n\n\t\tif(this.connectionSelectorsTables){\n\t\t\tconnectionTables = this.commsConnections(this.connectionSelectorsTables);\n\n\t\t\tthis.dispatchExternal(\"movableRowsSendingStart\", connectionTables);\n\n\t\t\tthis.commsSend(this.connectionSelectorsTables, \"moveRow\", \"connect\", {\n\t\t\t\trow:row,\n\t\t\t});\n\t\t}\n\n\t\tif(this.connectionSelectorsElements){\n\n\t\t\tthis.connectionElements = [];\n\n\t\t\tif(!Array.isArray(this.connectionSelectorsElements)){\n\t\t\t\tthis.connectionSelectorsElements = [this.connectionSelectorsElements];\n\t\t\t}\n\n\t\t\tthis.connectionSelectorsElements.forEach((query) => {\n\t\t\t\tif(typeof query === \"string\"){\n\t\t\t\t\tthis.connectionElements = this.connectionElements.concat(Array.prototype.slice.call(document.querySelectorAll(query)));\n\t\t\t\t}else {\n\t\t\t\t\tthis.connectionElements.push(query);\n\t\t\t\t}\n\t\t\t});\n\n\t\t\tthis.connectionElements.forEach((element) => {\n\t\t\t\tvar dropEvent = (e) => {\n\t\t\t\t\tthis.elementRowDrop(e, element, this.moving);\n\t\t\t\t};\n\n\t\t\t\telement.addEventListener(\"mouseup\", dropEvent);\n\t\t\t\telement.tabulatorElementDropEvent = dropEvent;\n\n\t\t\t\telement.classList.add(\"tabulator-movingrow-receiving\");\n\t\t\t});\n\t\t}\n\t}\n\n\t//disconnect from other tables\n\tdisconnectFromTables(){\n\t\tvar connectionTables;\n\n\t\tif(this.connectionSelectorsTables){\n\t\t\tconnectionTables = this.commsConnections(this.connectionSelectorsTables);\n\n\t\t\tthis.dispatchExternal(\"movableRowsSendingStop\", connectionTables);\n\n\t\t\tthis.commsSend(this.connectionSelectorsTables, \"moveRow\", \"disconnect\");\n\t\t}\n\n\t\tthis.connectionElements.forEach((element) => {\n\t\t\telement.classList.remove(\"tabulator-movingrow-receiving\");\n\t\t\telement.removeEventListener(\"mouseup\", element.tabulatorElementDropEvent);\n\t\t\tdelete element.tabulatorElementDropEvent;\n\t\t});\n\t}\n\n\t//accept incomming connection\n\tconnect(table, row){\n\t\tif(!this.connectedTable){\n\t\t\tthis.connectedTable = table;\n\t\t\tthis.connectedRow = row;\n\n\t\t\tthis.table.element.classList.add(\"tabulator-movingrow-receiving\");\n\n\t\t\tthis.table.rowManager.getDisplayRows().forEach((row) => {\n\t\t\t\tif(row.type === \"row\" && row.modules.moveRow && row.modules.moveRow.mouseup){\n\t\t\t\t\trow.getElement().addEventListener(\"mouseup\", row.modules.moveRow.mouseup);\n\t\t\t\t}\n\t\t\t});\n\n\t\t\tthis.tableRowDropEvent = this.tableRowDrop.bind(this);\n\n\t\t\tthis.table.element.addEventListener(\"mouseup\", this.tableRowDropEvent);\n\n\t\t\tthis.dispatchExternal(\"movableRowsReceivingStart\", row, table);\n\n\t\t\treturn true;\n\t\t}else {\n\t\t\tconsole.warn(\"Move Row Error - Table cannot accept connection, already connected to table:\", this.connectedTable);\n\t\t\treturn false;\n\t\t}\n\t}\n\n\t//close incoming connection\n\tdisconnect(table){\n\t\tif(table === this.connectedTable){\n\t\t\tthis.connectedTable = false;\n\t\t\tthis.connectedRow = false;\n\n\t\t\tthis.table.element.classList.remove(\"tabulator-movingrow-receiving\");\n\n\t\t\tthis.table.rowManager.getDisplayRows().forEach((row) =>{\n\t\t\t\tif(row.type === \"row\" && row.modules.moveRow && row.modules.moveRow.mouseup){\n\t\t\t\t\trow.getElement().removeEventListener(\"mouseup\", row.modules.moveRow.mouseup);\n\t\t\t\t}\n\t\t\t});\n\n\t\t\tthis.table.element.removeEventListener(\"mouseup\", this.tableRowDropEvent);\n\n\t\t\tthis.dispatchExternal(\"movableRowsReceivingStop\", table);\n\t\t}else {\n\t\t\tconsole.warn(\"Move Row Error - trying to disconnect from non connected table\");\n\t\t}\n\t}\n\n\tdropComplete(table, row, success){\n\t\tvar sender = false;\n\n\t\tif(success){\n\n\t\t\tswitch(typeof this.table.options.movableRowsSender){\n\t\t\t\tcase \"string\":\n\t\t\t\t\tsender = this.senders[this.table.options.movableRowsSender];\n\t\t\t\t\tbreak;\n\n\t\t\t\tcase \"function\":\n\t\t\t\t\tsender = this.table.options.movableRowsSender;\n\t\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\tif(sender){\n\t\t\t\tsender.call(this, this.moving ? this.moving.getComponent() : undefined, row ? row.getComponent() : undefined, table);\n\t\t\t}else {\n\t\t\t\tif(this.table.options.movableRowsSender){\n\t\t\t\t\tconsole.warn(\"Mover Row Error - no matching sender found:\", this.table.options.movableRowsSender);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tthis.dispatchExternal(\"movableRowsSent\", this.moving.getComponent(), row ? row.getComponent() : undefined, table);\n\t\t}else {\n\t\t\tthis.dispatchExternal(\"movableRowsSentFailed\", this.moving.getComponent(), row ? row.getComponent() : undefined, table);\n\t\t}\n\n\t\tthis.endMove();\n\t}\n\n\ttableRowDrop(e, row){\n\t\tvar receiver = false,\n\t\tsuccess = false;\n\n\t\te.stopImmediatePropagation();\n\n\t\tswitch(typeof this.table.options.movableRowsReceiver){\n\t\t\tcase \"string\":\n\t\t\t\treceiver = this.receivers[this.table.options.movableRowsReceiver];\n\t\t\t\tbreak;\n\n\t\t\tcase \"function\":\n\t\t\t\treceiver = this.table.options.movableRowsReceiver;\n\t\t\t\tbreak;\n\t\t}\n\n\t\tif(receiver){\n\t\t\tsuccess = receiver.call(this, this.connectedRow.getComponent(), row ? row.getComponent() : undefined, this.connectedTable);\n\t\t}else {\n\t\t\tconsole.warn(\"Mover Row Error - no matching receiver found:\", this.table.options.movableRowsReceiver);\n\t\t}\n\n\t\tif(success){\n\t\t\tthis.dispatchExternal(\"movableRowsReceived\", this.connectedRow.getComponent(), row ? row.getComponent() : undefined, this.connectedTable);\n\t\t}else {\n\t\t\tthis.dispatchExternal(\"movableRowsReceivedFailed\", this.connectedRow.getComponent(), row ? row.getComponent() : undefined, this.connectedTable);\n\t\t}\n\n\t\tthis.commsSend(this.connectedTable, \"moveRow\", \"dropcomplete\", {\n\t\t\trow:row,\n\t\t\tsuccess:success,\n\t\t});\n\t}\n\n\tcommsReceived(table, action, data){\n\t\tswitch(action){\n\t\t\tcase \"connect\":\n\t\t\t\treturn this.connect(table, data.row);\n\n\t\t\tcase \"disconnect\":\n\t\t\t\treturn this.disconnect(table);\n\n\t\t\tcase \"dropcomplete\":\n\t\t\t\treturn this.dropComplete(table, data.row, data.success);\n\t\t}\n\t}\n}\n\nMoveRows.prototype.receivers = {\n\tinsert:function(fromRow, toRow, fromTable){\n\t\tthis.table.addRow(fromRow.getData(), undefined, toRow);\n\t\treturn true;\n\t},\n\n\tadd:function(fromRow, toRow, fromTable){\n\t\tthis.table.addRow(fromRow.getData());\n\t\treturn true;\n\t},\n\n\tupdate:function(fromRow, toRow, fromTable){\n\t\tif(toRow){\n\t\t\ttoRow.update(fromRow.getData());\n\t\t\treturn true;\n\t\t}\n\n\t\treturn false;\n\t},\n\n\treplace:function(fromRow, toRow, fromTable){\n\t\tif(toRow){\n\t\t\tthis.table.addRow(fromRow.getData(), undefined, toRow);\n\t\t\ttoRow.delete();\n\t\t\treturn true;\n\t\t}\n\n\t\treturn false;\n\t},\n};\n\nMoveRows.prototype.senders = {\n\tdelete:function(fromRow, toRow, toTable){\n\t\tfromRow.delete();\n\t}\n};\n\nMoveRows.moduleName = \"moveRow\";\n\nvar defaultMutators = {};\n\nclass Mutator extends Module{\n\n\tconstructor(table){\n\t\tsuper(table);\n\n\t\tthis.allowedTypes = [\"\", \"data\", \"edit\", \"clipboard\"]; //list of mutation types\n\t\tthis.enabled = true;\n\n\t\tthis.registerColumnOption(\"mutator\");\n\t\tthis.registerColumnOption(\"mutatorParams\");\n\t\tthis.registerColumnOption(\"mutatorData\");\n\t\tthis.registerColumnOption(\"mutatorDataParams\");\n\t\tthis.registerColumnOption(\"mutatorEdit\");\n\t\tthis.registerColumnOption(\"mutatorEditParams\");\n\t\tthis.registerColumnOption(\"mutatorClipboard\");\n\t\tthis.registerColumnOption(\"mutatorClipboardParams\");\n\t\tthis.registerColumnOption(\"mutateLink\");\n\t}\n\n\tinitialize(){\n\t\tthis.subscribe(\"cell-value-changing\", this.transformCell.bind(this));\n\t\tthis.subscribe(\"cell-value-changed\", this.mutateLink.bind(this));\n\t\tthis.subscribe(\"column-layout\", this.initializeColumn.bind(this));\n\t\tthis.subscribe(\"row-data-init-before\", this.rowDataChanged.bind(this));\n\t\tthis.subscribe(\"row-data-changing\", this.rowDataChanged.bind(this));\n\t}\n\n\trowDataChanged(row, tempData, updatedData){\n\t\treturn this.transformRow(tempData, \"data\", updatedData);\n\t}\n\n\t//initialize column mutator\n\tinitializeColumn(column){\n\t\tvar match = false,\n\t\tconfig = {};\n\n\t\tthis.allowedTypes.forEach((type) => {\n\t\t\tvar key = \"mutator\" + (type.charAt(0).toUpperCase() + type.slice(1)),\n\t\t\tmutator;\n\n\t\t\tif(column.definition[key]){\n\t\t\t\tmutator = this.lookupMutator(column.definition[key]);\n\n\t\t\t\tif(mutator){\n\t\t\t\t\tmatch = true;\n\n\t\t\t\t\tconfig[key] = {\n\t\t\t\t\t\tmutator:mutator,\n\t\t\t\t\t\tparams: column.definition[key + \"Params\"] || {},\n\t\t\t\t\t};\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\n\t\tif(match){\n\t\t\tcolumn.modules.mutate = config;\n\t\t}\n\t}\n\n\tlookupMutator(value){\n\t\tvar mutator = false;\n\n\t\t//set column mutator\n\t\tswitch(typeof value){\n\t\t\tcase \"string\":\n\t\t\t\tif(Mutator.mutators[value]){\n\t\t\t\t\tmutator = Mutator.mutators[value];\n\t\t\t\t}else {\n\t\t\t\t\tconsole.warn(\"Mutator Error - No such mutator found, ignoring: \", value);\n\t\t\t\t}\n\t\t\t\tbreak;\n\n\t\t\tcase \"function\":\n\t\t\t\tmutator = value;\n\t\t\t\tbreak;\n\t\t}\n\n\t\treturn mutator;\n\t}\n\n\t//apply mutator to row\n\ttransformRow(data, type, updatedData){\n\t\tvar key = \"mutator\" + (type.charAt(0).toUpperCase() + type.slice(1)),\n\t\tvalue;\n\n\t\tif(this.enabled){\n\n\t\t\tthis.table.columnManager.traverse((column) => {\n\t\t\t\tvar mutator, params, component;\n\n\t\t\t\tif(column.modules.mutate){\n\t\t\t\t\tmutator = column.modules.mutate[key] || column.modules.mutate.mutator || false;\n\n\t\t\t\t\tif(mutator){\n\t\t\t\t\t\tvalue = column.getFieldValue(typeof updatedData !== \"undefined\" ? updatedData : data);\n\n\t\t\t\t\t\tif((type == \"data\" && !updatedData)|| typeof value !== \"undefined\"){\n\t\t\t\t\t\t\tcomponent = column.getComponent();\n\t\t\t\t\t\t\tparams = typeof mutator.params === \"function\" ? mutator.params(value, data, type, component) : mutator.params;\n\t\t\t\t\t\t\tcolumn.setFieldValue(data, mutator.mutator(value, data, type, params, component));\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\n\t\treturn data;\n\t}\n\n\t//apply mutator to new cell value\n\ttransformCell(cell, value){\n\t\tif(cell.column.modules.mutate){\n\t\t\tvar mutator = cell.column.modules.mutate.mutatorEdit || cell.column.modules.mutate.mutator || false,\n\t\t\ttempData = {};\n\n\t\t\tif(mutator){\n\t\t\t\ttempData = Object.assign(tempData, cell.row.getData());\n\t\t\t\tcell.column.setFieldValue(tempData, value);\n\t\t\t\treturn mutator.mutator(value, tempData, \"edit\", mutator.params, cell.getComponent());\n\t\t\t}\n\t\t}\n\n\t\treturn value;\n\t}\n\n\tmutateLink(cell){\n\t\tvar links = cell.column.definition.mutateLink;\n\n\t\tif(links){\n\t\t\tif(!Array.isArray(links)){\n\t\t\t\tlinks = [links];\n\t\t\t}\n\n\t\t\tlinks.forEach((link) => {\n\t\t\t\tvar linkCell = cell.row.getCell(link);\n\n\t\t\t\tif(linkCell){\n\t\t\t\t\tlinkCell.setValue(linkCell.getValue(), true, true);\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\t}\n\n\tenable(){\n\t\tthis.enabled = true;\n\t}\n\n\tdisable(){\n\t\tthis.enabled = false;\n\t}\n}\n\nMutator.moduleName = \"mutator\";\n\n//load defaults\nMutator.mutators = defaultMutators;\n\nfunction rows(pageSize, currentRow, currentPage, totalRows, totalPages){\n\tvar el = document.createElement(\"span\"),\n\tshowingEl = document.createElement(\"span\"),\n\tvalueEl = document.createElement(\"span\"),\n\tofEl = document.createElement(\"span\"),\n\ttotalEl = document.createElement(\"span\"),\n\trowsEl = document.createElement(\"span\");\n\n\tthis.table.modules.localize.langBind(\"pagination|counter|showing\", (value) => {\n\t\tshowingEl.innerHTML = value;\n\t});\n\n\tthis.table.modules.localize.langBind(\"pagination|counter|of\", (value) => {\n\t\tofEl.innerHTML = value;\n\t});\n\n\tthis.table.modules.localize.langBind(\"pagination|counter|rows\", (value) => {\n\t\trowsEl.innerHTML = value;\n\t});\n\n\tif(totalRows){\n\t\tvalueEl.innerHTML = \" \" + currentRow + \"-\" + Math.min((currentRow + pageSize - 1), totalRows) + \" \";\n\t\t\n\t\ttotalEl.innerHTML = \" \" + totalRows + \" \";\n\t\t\n\t\tel.appendChild(showingEl);\n\t\tel.appendChild(valueEl);\n\t\tel.appendChild(ofEl);\n\t\tel.appendChild(totalEl);\n\t\tel.appendChild(rowsEl);\n\t}else {\n\t\tvalueEl.innerHTML = \" 0 \";\n\n\t\tel.appendChild(showingEl);\n\t\tel.appendChild(valueEl);\n\t\tel.appendChild(rowsEl);\n\t}\n\t\n\treturn el;\n}\n\nfunction pages(pageSize, currentRow, currentPage, totalRows, totalPages){\n\n\tvar el = document.createElement(\"span\"),\n\tshowingEl = document.createElement(\"span\"),\n\tvalueEl = document.createElement(\"span\"),\n\tofEl = document.createElement(\"span\"),\n\ttotalEl = document.createElement(\"span\"),\n\trowsEl = document.createElement(\"span\");\n\t\n\tthis.table.modules.localize.langBind(\"pagination|counter|showing\", (value) => {\n\t\tshowingEl.innerHTML = value;\n\t});\n\t\n\tvalueEl.innerHTML = \" \" + currentPage + \" \";\n\t\n\tthis.table.modules.localize.langBind(\"pagination|counter|of\", (value) => {\n\t\tofEl.innerHTML = value;\n\t});\n\t\n\ttotalEl.innerHTML = \" \" + totalPages + \" \";\n\t\n\tthis.table.modules.localize.langBind(\"pagination|counter|pages\", (value) => {\n\t\trowsEl.innerHTML = value;\n\t});\n\t\n\tel.appendChild(showingEl);\n\tel.appendChild(valueEl);\n\tel.appendChild(ofEl);\n\tel.appendChild(totalEl);\n\tel.appendChild(rowsEl);\n\t\n\treturn el;\n}\n\nvar defaultPageCounters = {\n\trows:rows,\n\tpages:pages,\n};\n\nclass Page extends Module{\n\t\n\tconstructor(table){\n\t\tsuper(table);\n\t\t\n\t\tthis.mode = \"local\";\n\t\tthis.progressiveLoad = false;\n\t\t\n\t\tthis.element = null;\n\t\tthis.pageCounterElement = null;\n\t\tthis.pageCounter = null;\n\t\t\n\t\tthis.size = 0;\n\t\tthis.page = 1;\n\t\tthis.count = 5;\n\t\tthis.max = 1;\n\n\t\tthis.remoteRowCountEstimate = null;\n\t\t\n\t\tthis.initialLoad = true;\n\t\tthis.dataChanging = false; //flag to check if data is being changed by this module\n\t\t\n\t\tthis.pageSizes = [];\n\t\t\n\t\tthis.registerTableOption(\"pagination\", false); //set pagination type\n\t\tthis.registerTableOption(\"paginationMode\", \"local\"); //local or remote pagination\n\t\tthis.registerTableOption(\"paginationSize\", false); //set number of rows to a page\n\t\tthis.registerTableOption(\"paginationInitialPage\", 1); //initial page to show on load\n\t\tthis.registerTableOption(\"paginationCounter\", false);  // set pagination counter\n\t\tthis.registerTableOption(\"paginationCounterElement\", false);  // set pagination counter\n\t\tthis.registerTableOption(\"paginationButtonCount\", 5);  // set count of page button\n\t\tthis.registerTableOption(\"paginationSizeSelector\", false); //add pagination size selector element\n\t\tthis.registerTableOption(\"paginationElement\", false); //element to hold pagination numbers\n\t\t// this.registerTableOption(\"paginationDataSent\", {}); //pagination data sent to the server\n\t\t// this.registerTableOption(\"paginationDataReceived\", {}); //pagination data received from the server\n\t\tthis.registerTableOption(\"paginationAddRow\", \"page\"); //add rows on table or page\n\t\t\n\t\tthis.registerTableOption(\"progressiveLoad\", false); //progressive loading\n\t\tthis.registerTableOption(\"progressiveLoadDelay\", 0); //delay between requests\n\t\tthis.registerTableOption(\"progressiveLoadScrollMargin\", 0); //margin before scroll begins\n\t\t\n\t\tthis.registerTableFunction(\"setMaxPage\", this.setMaxPage.bind(this));\n\t\tthis.registerTableFunction(\"setPage\", this.setPage.bind(this));\n\t\tthis.registerTableFunction(\"setPageToRow\", this.userSetPageToRow.bind(this));\n\t\tthis.registerTableFunction(\"setPageSize\", this.userSetPageSize.bind(this));\n\t\tthis.registerTableFunction(\"getPageSize\", this.getPageSize.bind(this));\n\t\tthis.registerTableFunction(\"previousPage\", this.previousPage.bind(this));\n\t\tthis.registerTableFunction(\"nextPage\", this.nextPage.bind(this));\n\t\tthis.registerTableFunction(\"getPage\", this.getPage.bind(this));\n\t\tthis.registerTableFunction(\"getPageMax\", this.getPageMax.bind(this));\n\t\t\n\t\t//register component functions\n\t\tthis.registerComponentFunction(\"row\", \"pageTo\", this.setPageToRow.bind(this));\n\t}\n\t\n\tinitialize(){\n\t\tif(this.table.options.pagination){\n\t\t\tthis.subscribe(\"row-deleted\", this.rowsUpdated.bind(this));\n\t\t\tthis.subscribe(\"row-added\", this.rowsUpdated.bind(this));\n\t\t\tthis.subscribe(\"data-processed\", this.initialLoadComplete.bind(this));\n\t\t\tthis.subscribe(\"table-built\", this.calculatePageSizes.bind(this));\n\t\t\tthis.subscribe(\"footer-redraw\", this.footerRedraw.bind(this));\n\n\t\t\tif(this.table.options.paginationAddRow == \"page\"){\n\t\t\t\tthis.subscribe(\"row-adding-position\", this.rowAddingPosition.bind(this));\n\t\t\t}\n\t\t\t\n\t\t\tif(this.table.options.paginationMode === \"remote\"){\n\t\t\t\tthis.subscribe(\"data-params\", this.remotePageParams.bind(this));\n\t\t\t\tthis.subscribe(\"data-loaded\", this._parseRemoteData.bind(this));\n\t\t\t}\n\t\t\t\n\t\t\tif(this.table.options.progressiveLoad){\n\t\t\t\tconsole.error(\"Progressive Load Error - Pagination and progressive load cannot be used at the same time\");\n\t\t\t}\n\t\t\t\n\t\t\tthis.registerDisplayHandler(this.restOnRenderBefore.bind(this), 40);\n\t\t\tthis.registerDisplayHandler(this.getRows.bind(this), 50);\n\t\t\t\n\t\t\tthis.createElements();\n\t\t\tthis.initializePageCounter();\n\t\t\tthis.initializePaginator();\n\t\t}else if(this.table.options.progressiveLoad){\n\t\t\tthis.subscribe(\"data-params\", this.remotePageParams.bind(this));\n\t\t\tthis.subscribe(\"data-loaded\", this._parseRemoteData.bind(this));\n\t\t\tthis.subscribe(\"table-built\", this.calculatePageSizes.bind(this));\n\t\t\tthis.subscribe(\"data-processed\", this.initialLoadComplete.bind(this));\n\t\t\t\n\t\t\tthis.initializeProgressive(this.table.options.progressiveLoad);\n\t\t\t\n\t\t\tif(this.table.options.progressiveLoad === \"scroll\"){\n\t\t\t\tthis.subscribe(\"scroll-vertical\", this.scrollVertical.bind(this));\n\t\t\t}\n\t\t}\n\t}\n\t\n\trowAddingPosition(row, top){\n\t\tvar rowManager = this.table.rowManager,\n\t\tdisplayRows = rowManager.getDisplayRows(),\n\t\tindex;\n\t\t\n\t\tif(top){\n\t\t\tif(displayRows.length){\n\t\t\t\tindex = displayRows[0];\n\t\t\t}else {\n\t\t\t\tif(rowManager.activeRows.length){\n\t\t\t\t\tindex = rowManager.activeRows[rowManager.activeRows.length-1];\n\t\t\t\t\ttop = false;\n\t\t\t\t}\n\t\t\t}\n\t\t}else {\n\t\t\tif(displayRows.length){\n\t\t\t\tindex = displayRows[displayRows.length - 1];\n\t\t\t\ttop = displayRows.length < this.size ? false : true;\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn {index, top};\n\t}\n\t\n\tcalculatePageSizes(){\n\t\tvar testElRow, testElCell;\n\t\t\n\t\tif(this.table.options.paginationSize){\n\t\t\tthis.size = this.table.options.paginationSize;\n\t\t}else {\n\t\t\ttestElRow = document.createElement(\"div\");\n\t\t\ttestElRow.classList.add(\"tabulator-row\");\n\t\t\ttestElRow.style.visibility = \"hidden\";\n\t\t\t\n\t\t\ttestElCell = document.createElement(\"div\");\n\t\t\ttestElCell.classList.add(\"tabulator-cell\");\n\t\t\ttestElCell.innerHTML = \"Page Row Test\";\n\t\t\t\n\t\t\ttestElRow.appendChild(testElCell);\n\t\t\t\n\t\t\tthis.table.rowManager.getTableElement().appendChild(testElRow);\n\t\t\t\n\t\t\tthis.size = Math.floor(this.table.rowManager.getElement().clientHeight / testElRow.offsetHeight);\n\t\t\t\n\t\t\tthis.table.rowManager.getTableElement().removeChild(testElRow);\n\t\t}\n\n\t\tthis.dispatchExternal(\"pageSizeChanged\", this.size);\n\t\t\n\t\tthis.generatePageSizeSelectList();\n\t}\n\t\n\tinitialLoadComplete(){\n\t\tthis.initialLoad = false;\n\t}\n\t\n\tremotePageParams(data, config, silent, params){\n\t\tif(!this.initialLoad){\n\t\t\tif((this.progressiveLoad && !silent) || (!this.progressiveLoad && !this.dataChanging)){\n\t\t\t\tthis.reset(true);\n\t\t\t}\n\t\t}\n\t\t\n\t\t//configure request params\n\t\tparams.page = this.page;\n\t\t\n\t\t//set page size if defined\n\t\tif(this.size){\n\t\t\tparams.size = this.size;\n\t\t}\n\t\t\n\t\treturn params;\n\t}\n\t\n\t///////////////////////////////////\n\t///////// Table Functions /////////\n\t///////////////////////////////////\n\t\n\tuserSetPageToRow(row){\n\t\tif(this.table.options.pagination){\n\t\t\trow = this.table.rowManager.findRow(row);\n\t\t\t\n\t\t\tif(row){\n\t\t\t\treturn this.setPageToRow(row);\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn Promise.reject();\n\t}\n\t\n\tuserSetPageSize(size){\n\t\tif(this.table.options.pagination){\n\t\t\tthis.setPageSize(size);\n\t\t\treturn this.setPage(1);\n\t\t}else {\n\t\t\treturn false;\n\t\t}\n\t}\n\t///////////////////////////////////\n\t///////// Internal Logic //////////\n\t///////////////////////////////////\n\t\n\tscrollVertical(top, dir){\n\t\tvar element, diff, margin;\n\t\tif(!dir && !this.table.dataLoader.loading){\n\t\t\telement = this.table.rowManager.getElement();\n\t\t\tdiff = element.scrollHeight - element.clientHeight - top;\n\t\t\tmargin = this.table.options.progressiveLoadScrollMargin || (element.clientHeight * 2);\n\t\t\t\n\t\t\tif(diff < margin){\n\t\t\t\tthis.nextPage()\n\t\t\t\t\t.catch(() => {}); //consume the exception thrown when on the last page\n\t\t\t}\n\t\t}\n\t}\n\t\n\trestOnRenderBefore(rows, renderInPosition){\n\t\tif(!renderInPosition){\n\t\t\tif(this.mode === \"local\"){\n\t\t\t\tthis.reset();\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn rows;\n\t}\n\t\n\trowsUpdated(){\n\t\tthis.refreshData(true, \"all\");\n\t}\n\t\n\tcreateElements(){\n\t\tvar button;\n\t\t\n\t\tthis.element = document.createElement(\"span\");\n\t\tthis.element.classList.add(\"tabulator-paginator\");\n\t\t\n\t\tthis.pagesElement = document.createElement(\"span\");\n\t\tthis.pagesElement.classList.add(\"tabulator-pages\");\n\t\t\n\t\tbutton = document.createElement(\"button\");\n\t\tbutton.classList.add(\"tabulator-page\");\n\t\tbutton.setAttribute(\"type\", \"button\");\n\t\tbutton.setAttribute(\"role\", \"button\");\n\t\tbutton.setAttribute(\"aria-label\", \"\");\n\t\tbutton.setAttribute(\"title\", \"\");\n\t\t\n\t\tthis.firstBut = button.cloneNode(true);\n\t\tthis.firstBut.setAttribute(\"data-page\", \"first\");\n\t\t\n\t\tthis.prevBut = button.cloneNode(true);\n\t\tthis.prevBut.setAttribute(\"data-page\", \"prev\");\n\t\t\n\t\tthis.nextBut = button.cloneNode(true);\n\t\tthis.nextBut.setAttribute(\"data-page\", \"next\");\n\t\t\n\t\tthis.lastBut = button.cloneNode(true);\n\t\tthis.lastBut.setAttribute(\"data-page\", \"last\");\n\t\t\n\t\tif(this.table.options.paginationSizeSelector){\n\t\t\tthis.pageSizeSelect = document.createElement(\"select\");\n\t\t\tthis.pageSizeSelect.classList.add(\"tabulator-page-size\");\n\t\t}\n\t}\n\t\n\tgeneratePageSizeSelectList(){\n\t\tvar pageSizes = [];\n\t\t\n\t\tif(this.pageSizeSelect){\n\t\t\t\n\t\t\tif(Array.isArray(this.table.options.paginationSizeSelector)){\n\t\t\t\tpageSizes = this.table.options.paginationSizeSelector;\n\t\t\t\tthis.pageSizes = pageSizes;\n\t\t\t\t\n\t\t\t\tif(this.pageSizes.indexOf(this.size) == -1){\n\t\t\t\t\tpageSizes.unshift(this.size);\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\t\n\t\t\t\tif(this.pageSizes.indexOf(this.size) == -1){\n\t\t\t\t\tpageSizes = [];\n\t\t\t\t\t\n\t\t\t\t\tfor (let i = 1; i < 5; i++){\n\t\t\t\t\t\tpageSizes.push(this.size * i);\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\tthis.pageSizes = pageSizes;\n\t\t\t\t}else {\n\t\t\t\t\tpageSizes = this.pageSizes;\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\twhile(this.pageSizeSelect.firstChild) this.pageSizeSelect.removeChild(this.pageSizeSelect.firstChild);\n\t\t\t\n\t\t\tpageSizes.forEach((item) => {\n\t\t\t\tvar itemEl = document.createElement(\"option\");\n\t\t\t\titemEl.value = item;\n\t\t\t\t\n\t\t\t\tif(item === true){\n\t\t\t\t\tthis.langBind(\"pagination|all\", function(value){\n\t\t\t\t\t\titemEl.innerHTML = value;\n\t\t\t\t\t});\n\t\t\t\t}else {\n\t\t\t\t\titemEl.innerHTML = item;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t\n\t\t\t\t\n\t\t\t\tthis.pageSizeSelect.appendChild(itemEl);\n\t\t\t});\n\t\t\t\n\t\t\tthis.pageSizeSelect.value = this.size;\n\t\t}\n\t}\n\t\n\tinitializePageCounter(){\n\t\tvar counter = this.table.options.paginationCounter,\n\t\tpageCounter = null;\n\t\t\n\t\tif(counter){\n\t\t\tif(typeof counter === \"function\"){\n\t\t\t\tpageCounter = counter;\n\t\t\t}else {\n\t\t\t\tpageCounter = Page.pageCounters[counter];\n\t\t\t}\n\t\t\t\n\t\t\tif(pageCounter){\n\t\t\t\tthis.pageCounter = pageCounter;\n\t\t\t\t\n\t\t\t\tthis.pageCounterElement = document.createElement(\"span\");\n\t\t\t\tthis.pageCounterElement.classList.add(\"tabulator-page-counter\");\n\t\t\t}else {\n\t\t\t\tconsole.warn(\"Pagination Error - No such page counter found: \", counter);\n\t\t\t}\n\t\t}\n\t}\n\t\n\t//setup pagination\n\tinitializePaginator(hidden){\n\t\tvar pageSelectLabel, paginationCounterHolder;\n\t\t\n\t\tif(!hidden){\n\t\t\t//build pagination element\n\t\t\t\n\t\t\t//bind localizations\n\t\t\tthis.langBind(\"pagination|first\", (value) => {\n\t\t\t\tthis.firstBut.innerHTML = value;\n\t\t\t});\n\t\t\t\n\t\t\tthis.langBind(\"pagination|first_title\", (value) => {\n\t\t\t\tthis.firstBut.setAttribute(\"aria-label\", value);\n\t\t\t\tthis.firstBut.setAttribute(\"title\", value);\n\t\t\t});\n\t\t\t\n\t\t\tthis.langBind(\"pagination|prev\", (value) => {\n\t\t\t\tthis.prevBut.innerHTML = value;\n\t\t\t});\n\t\t\t\n\t\t\tthis.langBind(\"pagination|prev_title\", (value) => {\n\t\t\t\tthis.prevBut.setAttribute(\"aria-label\", value);\n\t\t\t\tthis.prevBut.setAttribute(\"title\", value);\n\t\t\t});\n\t\t\t\n\t\t\tthis.langBind(\"pagination|next\", (value) => {\n\t\t\t\tthis.nextBut.innerHTML = value;\n\t\t\t});\n\t\t\t\n\t\t\tthis.langBind(\"pagination|next_title\", (value) => {\n\t\t\t\tthis.nextBut.setAttribute(\"aria-label\", value);\n\t\t\t\tthis.nextBut.setAttribute(\"title\", value);\n\t\t\t});\n\t\t\t\n\t\t\tthis.langBind(\"pagination|last\", (value) => {\n\t\t\t\tthis.lastBut.innerHTML = value;\n\t\t\t});\n\t\t\t\n\t\t\tthis.langBind(\"pagination|last_title\", (value) => {\n\t\t\t\tthis.lastBut.setAttribute(\"aria-label\", value);\n\t\t\t\tthis.lastBut.setAttribute(\"title\", value);\n\t\t\t});\n\t\t\t\n\t\t\t//click bindings\n\t\t\tthis.firstBut.addEventListener(\"click\", () => {\n\t\t\t\tthis.setPage(1);\n\t\t\t});\n\t\t\t\n\t\t\tthis.prevBut.addEventListener(\"click\", () => {\n\t\t\t\tthis.previousPage();\n\t\t\t});\n\t\t\t\n\t\t\tthis.nextBut.addEventListener(\"click\", () => {\n\t\t\t\tthis.nextPage();\n\t\t\t});\n\t\t\t\n\t\t\tthis.lastBut.addEventListener(\"click\", () => {\n\t\t\t\tthis.setPage(this.max);\n\t\t\t});\n\t\t\t\n\t\t\tif(this.table.options.paginationElement){\n\t\t\t\tthis.element = this.table.options.paginationElement;\n\t\t\t}\n\t\t\t\n\t\t\tif(this.pageSizeSelect){\n\t\t\t\tpageSelectLabel = document.createElement(\"label\");\n\t\t\t\t\n\t\t\t\tthis.langBind(\"pagination|page_size\", (value) => {\n\t\t\t\t\tthis.pageSizeSelect.setAttribute(\"aria-label\", value);\n\t\t\t\t\tthis.pageSizeSelect.setAttribute(\"title\", value);\n\t\t\t\t\tpageSelectLabel.innerHTML = value;\n\t\t\t\t});\n\t\t\t\t\n\t\t\t\tthis.element.appendChild(pageSelectLabel);\n\t\t\t\tthis.element.appendChild(this.pageSizeSelect);\n\t\t\t\t\n\t\t\t\tthis.pageSizeSelect.addEventListener(\"change\", (e) => {\n\t\t\t\t\tthis.setPageSize(this.pageSizeSelect.value == \"true\" ? true : this.pageSizeSelect.value);\n\t\t\t\t\tthis.setPage(1);\n\t\t\t\t});\n\t\t\t}\n\t\t\t\n\t\t\t//append to DOM\n\t\t\tthis.element.appendChild(this.firstBut);\n\t\t\tthis.element.appendChild(this.prevBut);\n\t\t\tthis.element.appendChild(this.pagesElement);\n\t\t\tthis.element.appendChild(this.nextBut);\n\t\t\tthis.element.appendChild(this.lastBut);\n\t\t\t\n\t\t\tif(!this.table.options.paginationElement){\n\t\t\t\tif(this.table.options.paginationCounter){\n\n\t\t\t\t\tif(this.table.options.paginationCounterElement){\n\t\t\t\t\t\tif(this.table.options.paginationCounterElement instanceof HTMLElement){\n\t\t\t\t\t\t\tthis.table.options.paginationCounterElement.appendChild(this.pageCounterElement);\n\t\t\t\t\t\t}else if(typeof this.table.options.paginationCounterElement === \"string\"){\n\t\t\t\t\t\t\tpaginationCounterHolder = document.querySelector(this.table.options.paginationCounterElement);\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\tif(paginationCounterHolder){\n\t\t\t\t\t\t\t\tpaginationCounterHolder.appendChild(this.pageCounterElement);\n\t\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\t\tconsole.warn(\"Pagination Error - Unable to find element matching paginationCounterElement selector:\", this.table.options.paginationCounterElement);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}else {\n\t\t\t\t\t\tthis.footerAppend(this.pageCounterElement);\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tthis.footerAppend(this.element);\n\t\t\t}\n\t\t\t\n\t\t\tthis.page = this.table.options.paginationInitialPage;\n\t\t\tthis.count = this.table.options.paginationButtonCount;\n\t\t}\n\t\t\n\t\t//set default values\n\t\tthis.mode = this.table.options.paginationMode;\n\t}\n\t\n\tinitializeProgressive(mode){\n\t\tthis.initializePaginator(true);\n\t\tthis.mode = \"progressive_\" + mode;\n\t\tthis.progressiveLoad = true;\n\t}\n\t\n\ttrackChanges(){\n\t\tthis.dispatch(\"page-changed\");\n\t}\n\t\n\t//calculate maximum page from number of rows\n\tsetMaxRows(rowCount){\n\t\tif(!rowCount){\n\t\t\tthis.max = 1;\n\t\t}else {\n\t\t\tthis.max = this.size === true ?  1 : Math.ceil(rowCount/this.size);\n\t\t}\n\t\t\n\t\tif(this.page > this.max){\n\t\t\tthis.page = this.max;\n\t\t}\n\t}\n\t\n\t//reset to first page without triggering action\n\treset(force){\n\t\tif(!this.initialLoad){\n\t\t\tif(this.mode == \"local\" || force){\n\t\t\t\tthis.page = 1;\n\t\t\t\tthis.trackChanges();\n\t\t\t}\n\t\t}\n\t}\n\t\n\t//set the maximum page\n\tsetMaxPage(max){\n\t\t\n\t\tmax = parseInt(max);\n\t\t\n\t\tthis.max = max || 1;\n\t\t\n\t\tif(this.page > this.max){\n\t\t\tthis.page = this.max;\n\t\t\tthis.trigger();\n\t\t}\n\t}\n\t\n\t//set current page number\n\tsetPage(page){\n\t\tswitch(page){\n\t\t\tcase \"first\":\n\t\t\t\treturn this.setPage(1);\n\t\n\t\t\tcase \"prev\":\n\t\t\t\treturn this.previousPage();\n\t\t\t\n\t\t\tcase \"next\":\n\t\t\t\treturn this.nextPage();\n\t\t\t\n\t\t\tcase \"last\":\n\t\t\t\treturn this.setPage(this.max);\n\t\t}\n\t\t\n\t\tpage = parseInt(page);\n\t\t\n\t\tif((page > 0 && page <= this.max) || this.mode !== \"local\"){\n\t\t\tthis.page = page;\n\t\t\t\n\t\t\tthis.trackChanges();\n\t\t\t\n\t\t\treturn this.trigger();\n\t\t}else {\n\t\t\tconsole.warn(\"Pagination Error - Requested page is out of range of 1 - \" + this.max + \":\", page);\n\t\t\treturn Promise.reject();\n\t\t}\n\t}\n\t\n\tsetPageToRow(row){\n\t\tvar rows = this.displayRows(-1);\n\t\tvar index = rows.indexOf(row);\n\t\n\t\tif(index > -1){\n\t\t\tvar page = this.size === true ? 1 : Math.ceil((index + 1) / this.size);\n\t\t\t\n\t\t\treturn this.setPage(page);\n\t\t}else {\n\t\t\tconsole.warn(\"Pagination Error - Requested row is not visible\");\n\t\t\treturn Promise.reject();\n\t\t}\n\t}\n\t\n\tsetPageSize(size){\n\t\tif(size !== true){\n\t\t\tsize = parseInt(size);\n\t\t}\n\n\t\tif(size > 0){\n\t\t\tthis.size = size;\n\t\t\tthis.dispatchExternal(\"pageSizeChanged\", size);\n\t\t}\n\t\t\n\t\tif(this.pageSizeSelect){\n\t\t\t// this.pageSizeSelect.value = size;\n\t\t\tthis.generatePageSizeSelectList();\n\t\t}\n\t\t\n\t\tthis.trackChanges();\n\t}\n\t\n\t_setPageCounter(totalRows, size, currentRow){\n\t\tvar content;\n\t\t\n\t\tif(this.pageCounter){\n\n\t\t\tif(this.mode === \"remote\"){\n\t\t\t\tsize = this.size;\n\t\t\t\tcurrentRow = ((this.page - 1) * this.size) + 1;\n\t\t\t\ttotalRows = this.remoteRowCountEstimate;\n\t\t\t}\n\n\t\t\tcontent = this.pageCounter.call(this, size, currentRow, this.page, totalRows, this.max);\n\t\t\t\n\t\t\tswitch(typeof content){\n\t\t\t\tcase \"object\":\n\t\t\t\t\tif(content instanceof Node){\n\t\t\t\t\t\n\t\t\t\t\t\t//clear previous cell contents\n\t\t\t\t\t\twhile(this.pageCounterElement.firstChild) this.pageCounterElement.removeChild(this.pageCounterElement.firstChild);\n\t\t\t\t\t\n\t\t\t\t\t\tthis.pageCounterElement.appendChild(content);\n\t\t\t\t\t}else {\n\t\t\t\t\t\tthis.pageCounterElement.innerHTML = \"\";\n\t\t\t\t\t\n\t\t\t\t\t\tif(content != null){\n\t\t\t\t\t\t\tconsole.warn(\"Page Counter Error - Page Counter has returned a type of object, the only valid page counter object return is an instance of Node, the page counter returned:\", content);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"undefined\":\n\t\t\t\t\tthis.pageCounterElement.innerHTML = \"\";\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tthis.pageCounterElement.innerHTML = content;\n\t\t\t}\n\t\t}\n\t}\n\t\n\t//setup the pagination buttons\n\t_setPageButtons(){\n\t\tlet leftSize = Math.floor((this.count-1) / 2);\n\t\tlet rightSize = Math.ceil((this.count-1) / 2);\n\t\tlet min = this.max - this.page + leftSize + 1 < this.count ? this.max-this.count+1: Math.max(this.page-leftSize,1);\n\t\tlet max = this.page <= rightSize? Math.min(this.count, this.max) :Math.min(this.page+rightSize, this.max);\n\t\t\n\t\twhile(this.pagesElement.firstChild) this.pagesElement.removeChild(this.pagesElement.firstChild);\n\t\t\n\t\tif(this.page == 1){\n\t\t\tthis.firstBut.disabled = true;\n\t\t\tthis.prevBut.disabled = true;\n\t\t}else {\n\t\t\tthis.firstBut.disabled = false;\n\t\t\tthis.prevBut.disabled = false;\n\t\t}\n\t\t\n\t\tif(this.page == this.max){\n\t\t\tthis.lastBut.disabled = true;\n\t\t\tthis.nextBut.disabled = true;\n\t\t}else {\n\t\t\tthis.lastBut.disabled = false;\n\t\t\tthis.nextBut.disabled = false;\n\t\t}\n\t\t\n\t\tfor(let i = min; i <= max; i++){\n\t\t\tif(i>0 && i <= this.max){\n\t\t\t\tthis.pagesElement.appendChild(this._generatePageButton(i));\n\t\t\t}\n\t\t}\n\t\t\n\t\tthis.footerRedraw();\n\t}\n\t\n\t_generatePageButton(page){\n\t\tvar button = document.createElement(\"button\");\n\t\t\n\t\tbutton.classList.add(\"tabulator-page\");\n\t\tif(page == this.page){\n\t\t\tbutton.classList.add(\"active\");\n\t\t}\n\t\t\n\t\tbutton.setAttribute(\"type\", \"button\");\n\t\tbutton.setAttribute(\"role\", \"button\");\n\t\t\n\t\tthis.langBind(\"pagination|page_title\", (value) => {\n\t\t\tbutton.setAttribute(\"aria-label\", value + \" \" + page);\n\t\t\tbutton.setAttribute(\"title\", value + \" \" + page);\n\t\t});\n\t\t\n\t\tbutton.setAttribute(\"data-page\", page);\n\t\tbutton.textContent = page;\n\t\t\n\t\tbutton.addEventListener(\"click\", (e) => {\n\t\t\tthis.setPage(page);\n\t\t});\n\t\t\n\t\treturn button;\n\t}\n\t\n\t//previous page\n\tpreviousPage(){\n\t\tif(this.page > 1){\n\t\t\tthis.page--;\n\t\t\t\n\t\t\tthis.trackChanges();\n\t\t\t\n\t\t\treturn this.trigger();\n\t\t\t\n\t\t}else {\n\t\t\tconsole.warn(\"Pagination Error - Previous page would be less than page 1:\", 0);\n\t\t\treturn Promise.reject();\n\t\t}\n\t}\n\t\n\t//next page\n\tnextPage(){\n\t\tif(this.page < this.max){\n\t\t\tthis.page++;\n\t\t\t\n\t\t\tthis.trackChanges();\n\t\t\t\n\t\t\treturn this.trigger();\n\t\t\t\n\t\t}else {\n\t\t\tif(!this.progressiveLoad){\n\t\t\t\tconsole.warn(\"Pagination Error - Next page would be greater than maximum page of \" + this.max + \":\", this.max + 1);\n\t\t\t}\n\t\t\treturn Promise.reject();\n\t\t}\n\t}\n\t\n\t//return current page number\n\tgetPage(){\n\t\treturn this.page;\n\t}\n\t\n\t//return max page number\n\tgetPageMax(){\n\t\treturn this.max;\n\t}\n\t\n\tgetPageSize(size){\n\t\treturn this.size;\n\t}\n\t\n\tgetMode(){\n\t\treturn this.mode;\n\t}\n\t\n\t//return appropriate rows for current page\n\tgetRows(data){\n\t\tvar actualRowPageSize = 0,\n\t\toutput, start, end, actualStartRow;\n\n\t\tvar actualRows = data.filter((row) => {\n\t\t\treturn row.type === \"row\";\n\t\t});\n\t\t\n\t\tif(this.mode == \"local\"){\n\t\t\toutput = [];\n\t\t\t\n\t\t\tthis.setMaxRows(data.length);\n\t\t\t\n\t\t\tif(this.size === true){\n\t\t\t\tstart = 0;\n\t\t\t\tend = data.length;\n\t\t\t}else {\n\t\t\t\tstart = this.size * (this.page - 1);\n\t\t\t\tend = start + parseInt(this.size);\n\t\t\t}\n\t\t\t\n\t\t\tthis._setPageButtons();\n\t\t\t\n\t\t\tfor(let i = start; i < end; i++){\n\t\t\t\tlet row = data[i];\n\n\t\t\t\tif(row){\n\t\t\t\t\toutput.push(row);\n\n\t\t\t\t\tif(row.type === \"row\"){\n\t\t\t\t\t\tif(!actualStartRow){\n\t\t\t\t\t\t\tactualStartRow = row;\n\t\t\t\t\t\t}\t\n\n\t\t\t\t\t\tactualRowPageSize++;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\tthis._setPageCounter(actualRows.length, actualRowPageSize, actualStartRow ? (actualRows.indexOf(actualStartRow) + 1) : 0);\n\t\t\t\n\t\t\treturn output;\n\t\t}else {\n\t\t\tthis._setPageButtons();\n\t\t\tthis._setPageCounter(actualRows.length);\n\t\t\t\n\t\t\treturn data.slice(0);\n\t\t}\n\t}\n\t\n\ttrigger(){\n\t\tvar left;\n\t\t\n\t\tswitch(this.mode){\n\t\t\tcase \"local\":\n\t\t\t\tleft = this.table.rowManager.scrollLeft;\n\t\t\t\n\t\t\t\tthis.refreshData();\n\t\t\t\tthis.table.rowManager.scrollHorizontal(left);\n\t\t\t\n\t\t\t\tthis.dispatchExternal(\"pageLoaded\", this.getPage());\n\t\t\t\n\t\t\t\treturn Promise.resolve();\n\t\t\t\n\t\t\tcase \"remote\":\n\t\t\t\tthis.dataChanging = true;\n\t\t\t\treturn this.reloadData(null)\n\t\t\t\t\t.finally(() => {\n\t\t\t\t\t\tthis.dataChanging = false;\n\t\t\t\t\t});\n\t\t\t\n\t\t\tcase \"progressive_load\":\n\t\t\tcase \"progressive_scroll\":\n\t\t\t\treturn this.reloadData(null, true);\n\t\t\t\n\t\t\tdefault:\n\t\t\t\tconsole.warn(\"Pagination Error - no such pagination mode:\", this.mode);\n\t\t\t\treturn Promise.reject();\n\t\t}\n\t}\n\t\n\t_parseRemoteData(data){\n\t\tvar margin;\n\t\t\n\t\tif(typeof data.last_page === \"undefined\"){\n\t\t\tconsole.warn(\"Remote Pagination Error - Server response missing '\" + (this.options(\"dataReceiveParams\").last_page || \"last_page\") + \"' property\");\n\t\t}\n\t\t\n\t\tif(data.data){\n\t\t\tthis.max = parseInt(data.last_page) || 1;\n\n\t\t\tthis.remoteRowCountEstimate = typeof data.last_row !== \"undefined\" ? data.last_row : (data.last_page * this.size - (this.page == data.last_page ? (this.size - data.data.length) : 0));\n\t\t\t\n\t\t\tif(this.progressiveLoad){\n\t\t\t\tswitch(this.mode){\n\t\t\t\t\tcase \"progressive_load\":\n\t\t\t\t\t\n\t\t\t\t\t\tif(this.page == 1){\n\t\t\t\t\t\t\tthis.table.rowManager.setData(data.data, false, this.page == 1);\n\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\tthis.table.rowManager.addRows(data.data);\n\t\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\t\tif(this.page < this.max){\n\t\t\t\t\t\t\tsetTimeout(() => {\n\t\t\t\t\t\t\t\tthis.nextPage();\n\t\t\t\t\t\t\t}, this.table.options.progressiveLoadDelay);\n\t\t\t\t\t\t}\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t\n\t\t\t\t\tcase \"progressive_scroll\":\n\t\t\t\t\t\tdata = this.page === 1 ? data.data : this.table.rowManager.getData().concat(data.data);\n\t\t\t\t\t\n\t\t\t\t\t\tthis.table.rowManager.setData(data, this.page !== 1, this.page == 1);\n\t\t\t\t\t\n\t\t\t\t\t\tmargin = this.table.options.progressiveLoadScrollMargin || (this.table.rowManager.element.clientHeight * 2);\n\t\t\t\t\t\n\t\t\t\t\t\tif(this.table.rowManager.element.scrollHeight <= (this.table.rowManager.element.clientHeight + margin)){\n\t\t\t\t\t\t\tif(this.page < this.max){\n\t\t\t\t\t\t\t\tsetTimeout(() => {\n\t\t\t\t\t\t\t\t\tthis.nextPage();\n\t\t\t\t\t\t\t\t});\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\treturn false;\n\t\t\t}else {\n\t\t\t\t// left = this.table.rowManager.scrollLeft;\n\t\t\t\tthis.dispatchExternal(\"pageLoaded\",  this.getPage());\n\t\t\t\t// this.table.rowManager.scrollHorizontal(left);\n\t\t\t\t// this.table.columnManager.scrollHorizontal(left);\n\t\t\t}\n\t\t\t\n\t\t}else {\n\t\t\tconsole.warn(\"Remote Pagination Error - Server response missing '\" + (this.options(\"dataReceiveParams\").data || \"data\") + \"' property\");\n\t\t}\n\t\t\n\t\treturn data.data;\n\t}\n\t\n\t//handle the footer element being redrawn\n\tfooterRedraw(){\n\t\tvar footer = this.table.footerManager.containerElement;\n\n\t\tif((Math.ceil(footer.clientWidth) - footer.scrollWidth) < 0){\n\t\t\tthis.pagesElement.style.display = 'none';\n\t\t}else {\n\t\t\tthis.pagesElement.style.display = '';\n\t\t\t\n\t\t\tif((Math.ceil(footer.clientWidth) - footer.scrollWidth) < 0){\n\t\t\t\tthis.pagesElement.style.display = 'none';\n\t\t\t}\n\t\t}\n\t}\n}\n\nPage.moduleName = \"page\";\n\n//load defaults\nPage.pageCounters = defaultPageCounters;\n\n// read persistance information from storage\nvar defaultReaders = {\n\tlocal:function(id, type){\n\t\tvar data = localStorage.getItem(id + \"-\" + type);\n\n\t\treturn data ? JSON.parse(data) : false;\n\t},\n\tcookie:function(id, type){\n\t\tvar cookie = document.cookie,\n\t\tkey = id + \"-\" + type,\n\t\tcookiePos = cookie.indexOf(key + \"=\"),\n\t\tend, data;\n\n\t\t//if cookie exists, decode and load column data into tabulator\n\t\tif(cookiePos > -1){\n\t\t\tcookie = cookie.slice(cookiePos);\n\n\t\t\tend = cookie.indexOf(\";\");\n\n\t\t\tif(end > -1){\n\t\t\t\tcookie = cookie.slice(0, end);\n\t\t\t}\n\n\t\t\tdata = cookie.replace(key + \"=\", \"\");\n\t\t}\n\n\t\treturn data ? JSON.parse(data) : false;\n\t}\n};\n\n//write persistence information to storage\nvar defaultWriters = {\n\tlocal:function(id, type, data){\n\t\tlocalStorage.setItem(id + \"-\" + type, JSON.stringify(data));\n\t},\n\tcookie:function(id, type, data){\n\t\tvar expireDate = new Date();\n\n\t\texpireDate.setDate(expireDate.getDate() + 10000);\n\n\t\tdocument.cookie = id + \"-\" + type + \"=\" + JSON.stringify(data) + \"; expires=\" + expireDate.toUTCString();\n\t}\n};\n\nclass Persistence extends Module{\n\n\tconstructor(table){\n\t\tsuper(table);\n\n\t\tthis.mode = \"\";\n\t\tthis.id = \"\";\n\t\t// this.persistProps = [\"field\", \"width\", \"visible\"];\n\t\tthis.defWatcherBlock = false;\n\t\tthis.config = {};\n\t\tthis.readFunc = false;\n\t\tthis.writeFunc = false;\n\n\t\tthis.registerTableOption(\"persistence\", false);\n\t\tthis.registerTableOption(\"persistenceID\", \"\"); //key for persistent storage\n\t\tthis.registerTableOption(\"persistenceMode\", true); //mode for storing persistence information\n\t\tthis.registerTableOption(\"persistenceReaderFunc\", false); //function for handling persistence data reading\n\t\tthis.registerTableOption(\"persistenceWriterFunc\", false); //function for handling persistence data writing\n\t}\n\n\t// Test for whether localStorage is available for use.\n\tlocalStorageTest() {\n\t\tvar  testKey =  \"_tabulator_test\";\n\n\t\ttry {\n\t\t\twindow.localStorage.setItem( testKey, testKey);\n\t\t\twindow.localStorage.removeItem( testKey );\n\t\t\treturn true;\n\t\t} catch(e) {\n\t\t\treturn false;\n\t\t}\n\t}\n\n\t//setup parameters\n\tinitialize(){\n\t\tif(this.table.options.persistence){\n\t\t\t//determine persistent layout storage type\n\t\t\tvar mode = this.table.options.persistenceMode,\n\t\t\tid = this.table.options.persistenceID,\n\t\t\tretrievedData;\n\n\t\t\tthis.mode = mode !== true ?  mode : (this.localStorageTest() ? \"local\" : \"cookie\");\n\n\t\t\tif(this.table.options.persistenceReaderFunc){\n\t\t\t\tif(typeof this.table.options.persistenceReaderFunc === \"function\"){\n\t\t\t\t\tthis.readFunc = this.table.options.persistenceReaderFunc;\n\t\t\t\t}else {\n\t\t\t\t\tif(Persistence.readers[this.table.options.persistenceReaderFunc]){\n\t\t\t\t\t\tthis.readFunc = Persistence.readers[this.table.options.persistenceReaderFunc];\n\t\t\t\t\t}else {\n\t\t\t\t\t\tconsole.warn(\"Persistence Read Error - invalid reader set\", this.table.options.persistenceReaderFunc);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tif(Persistence.readers[this.mode]){\n\t\t\t\t\tthis.readFunc = Persistence.readers[this.mode];\n\t\t\t\t}else {\n\t\t\t\t\tconsole.warn(\"Persistence Read Error - invalid reader set\", this.mode);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif(this.table.options.persistenceWriterFunc){\n\t\t\t\tif(typeof this.table.options.persistenceWriterFunc === \"function\"){\n\t\t\t\t\tthis.writeFunc = this.table.options.persistenceWriterFunc;\n\t\t\t\t}else {\n\t\t\t\t\tif(Persistence.writers[this.table.options.persistenceWriterFunc]){\n\t\t\t\t\t\tthis.writeFunc = Persistence.writers[this.table.options.persistenceWriterFunc];\n\t\t\t\t\t}else {\n\t\t\t\t\t\tconsole.warn(\"Persistence Write Error - invalid reader set\", this.table.options.persistenceWriterFunc);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tif(Persistence.writers[this.mode]){\n\t\t\t\t\tthis.writeFunc = Persistence.writers[this.mode];\n\t\t\t\t}else {\n\t\t\t\t\tconsole.warn(\"Persistence Write Error - invalid writer set\", this.mode);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t//set storage tag\n\t\t\tthis.id = \"tabulator-\" + (id || (this.table.element.getAttribute(\"id\") || \"\"));\n\n\t\t\tthis.config = {\n\t\t\t\tsort:this.table.options.persistence === true || this.table.options.persistence.sort,\n\t\t\t\tfilter:this.table.options.persistence === true || this.table.options.persistence.filter,\n\t\t\t\theaderFilter:this.table.options.persistence === true || this.table.options.persistence.headerFilter,\n\t\t\t\tgroup:this.table.options.persistence === true || this.table.options.persistence.group,\n\t\t\t\tpage:this.table.options.persistence === true || this.table.options.persistence.page,\n\t\t\t\tcolumns:this.table.options.persistence === true ? [\"title\", \"width\", \"visible\"] : this.table.options.persistence.columns,\n\t\t\t};\n\n\t\t\t//load pagination data if needed\n\t\t\tif(this.config.page){\n\t\t\t\tretrievedData = this.retrieveData(\"page\");\n\n\t\t\t\tif(retrievedData){\n\t\t\t\t\tif(typeof retrievedData.paginationSize !== \"undefined\" && (this.config.page === true || this.config.page.size)){\n\t\t\t\t\t\tthis.table.options.paginationSize = retrievedData.paginationSize;\n\t\t\t\t\t}\n\n\t\t\t\t\tif(typeof retrievedData.paginationInitialPage !== \"undefined\" && (this.config.page === true || this.config.page.page)){\n\t\t\t\t\t\tthis.table.options.paginationInitialPage = retrievedData.paginationInitialPage;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t//load group data if needed\n\t\t\tif(this.config.group){\n\t\t\t\tretrievedData = this.retrieveData(\"group\");\n\n\t\t\t\tif(retrievedData){\n\t\t\t\t\tif(typeof retrievedData.groupBy !== \"undefined\" && (this.config.group === true || this.config.group.groupBy)){\n\t\t\t\t\t\tthis.table.options.groupBy = retrievedData.groupBy;\n\t\t\t\t\t}\n\t\t\t\t\tif(typeof retrievedData.groupStartOpen !== \"undefined\" && (this.config.group === true || this.config.group.groupStartOpen)){\n\t\t\t\t\t\tthis.table.options.groupStartOpen = retrievedData.groupStartOpen;\n\t\t\t\t\t}\n\t\t\t\t\tif(typeof retrievedData.groupHeader !== \"undefined\" && (this.config.group === true || this.config.group.groupHeader)){\n\t\t\t\t\t\tthis.table.options.groupHeader = retrievedData.groupHeader;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif(this.config.columns){\n\t\t\t\tthis.table.options.columns = this.load(\"columns\", this.table.options.columns);\n\t\t\t\tthis.subscribe(\"column-init\", this.initializeColumn.bind(this));\n\t\t\t\tthis.subscribe(\"column-show\", this.save.bind(this, \"columns\"));\n\t\t\t\tthis.subscribe(\"column-hide\", this.save.bind(this, \"columns\"));\n\t\t\t\tthis.subscribe(\"column-moved\", this.save.bind(this, \"columns\"));\n\t\t\t}\n\n\t\t\tthis.subscribe(\"table-built\", this.tableBuilt.bind(this), 0);\n\n\t\t\tthis.subscribe(\"table-redraw\", this.tableRedraw.bind(this));\n\n\t\t\tthis.subscribe(\"filter-changed\", this.eventSave.bind(this, \"filter\"));\n\t\t\tthis.subscribe(\"filter-changed\", this.eventSave.bind(this, \"headerFilter\"));\n\t\t\tthis.subscribe(\"sort-changed\", this.eventSave.bind(this, \"sort\"));\n\t\t\tthis.subscribe(\"group-changed\", this.eventSave.bind(this, \"group\"));\n\t\t\tthis.subscribe(\"page-changed\", this.eventSave.bind(this, \"page\"));\n\t\t\tthis.subscribe(\"column-resized\", this.eventSave.bind(this, \"columns\"));\n\t\t\tthis.subscribe(\"column-width\", this.eventSave.bind(this, \"columns\"));\n\t\t\tthis.subscribe(\"layout-refreshed\", this.eventSave.bind(this, \"columns\"));\n\t\t}\n\n\t\tthis.registerTableFunction(\"getColumnLayout\", this.getColumnLayout.bind(this));\n\t\tthis.registerTableFunction(\"setColumnLayout\", this.setColumnLayout.bind(this));\n\t}\n\n\teventSave(type){\n\t\tif(this.config[type]){\n\t\t\tthis.save(type);\n\t\t}\n\t}\n\n\ttableBuilt(){\n\t\tvar sorters, filters, headerFilters;\n\n\t\tif(this.config.sort){\n\t\t\tsorters = this.load(\"sort\");\n\n\t\t\tif(!sorters === false){\n\t\t\t\tthis.table.options.initialSort = sorters;\n\t\t\t}\n\t\t}\n\n\t\tif(this.config.filter){\n\t\t\tfilters = this.load(\"filter\");\n\n\t\t\tif(!filters === false){\n\t\t\t\tthis.table.options.initialFilter = filters;\n\t\t\t}\n\t\t}\n\t\tif(this.config.headerFilter){\n\t\t\theaderFilters = this.load(\"headerFilter\");\n\n\t\t\tif(!headerFilters === false){\n\t\t\t\tthis.table.options.initialHeaderFilter = headerFilters;\n\t\t\t}\n\t\t}\n\t\t\n\t}\n\n\ttableRedraw(force){\n\t\tif(force && this.config.columns){\n\t\t\tthis.save(\"columns\");\n\t\t}\n\t}\n\n\t///////////////////////////////////\n\t///////// Table Functions /////////\n\t///////////////////////////////////\n\n\tgetColumnLayout(){\n\t\treturn this.parseColumns(this.table.columnManager.getColumns());\n\t}\n\n\tsetColumnLayout(layout){\n\t\tthis.table.columnManager.setColumns(this.mergeDefinition(this.table.options.columns, layout, true));\n\t\treturn true;\n\t}\n\n\t///////////////////////////////////\n\t///////// Internal Logic //////////\n\t///////////////////////////////////\n\n\tinitializeColumn(column){\n\t\tvar def, keys;\n\n\t\tif(this.config.columns){\n\t\t\tthis.defWatcherBlock = true;\n\n\t\t\tdef = column.getDefinition();\n\n\t\t\tkeys = this.config.columns === true ? Object.keys(def) : this.config.columns;\n\n\t\t\tkeys.forEach((key)=>{\n\t\t\t\tvar props = Object.getOwnPropertyDescriptor(def, key);\n\t\t\t\tvar value = def[key];\n\n\t\t\t\tif(props){\n\t\t\t\t\tObject.defineProperty(def, key, {\n\t\t\t\t\t\tset: (newValue) => {\n\t\t\t\t\t\t\tvalue = newValue;\n\n\t\t\t\t\t\t\tif(!this.defWatcherBlock){\n\t\t\t\t\t\t\t\tthis.save(\"columns\");\n\t\t\t\t\t\t\t}\n\n\t\t\t\t\t\t\tif(props.set){\n\t\t\t\t\t\t\t\tprops.set(newValue);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t},\n\t\t\t\t\t\tget:() => {\n\t\t\t\t\t\t\tif(props.get){\n\t\t\t\t\t\t\t\tprops.get();\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\treturn value;\n\t\t\t\t\t\t}\n\t\t\t\t\t});\n\t\t\t\t}\n\t\t\t});\n\n\t\t\tthis.defWatcherBlock = false;\n\t\t}\n\t}\n\n\t//load saved definitions\n\tload(type, current){\n\t\tvar data = this.retrieveData(type);\n\n\t\tif(current){\n\t\t\tdata = data ? this.mergeDefinition(current, data) : current;\n\t\t}\n\n\t\treturn data;\n\t}\n\n\t//retrieve data from memory\n\tretrieveData(type){\n\t\treturn this.readFunc ? this.readFunc(this.id, type) : false;\n\t}\n\n\t//merge old and new column definitions\n\tmergeDefinition(oldCols, newCols, mergeAllNew){\n\t\tvar output = [];\n\n\t\tnewCols = newCols || [];\n\n\t\tnewCols.forEach((column, to) => {\n\t\t\tvar from = this._findColumn(oldCols, column),\n\t\t\tkeys;\n\n\t\t\tif(from){\n\t\t\t\tif(mergeAllNew){\n\t\t\t\t\tkeys = Object.keys(column);\n\t\t\t\t}else if(this.config.columns === true || this.config.columns == undefined){\n\t\t\t\t\tkeys =  Object.keys(from);\n\t\t\t\t\tkeys.push(\"width\");\n\t\t\t\t}else {\n\t\t\t\t\tkeys = this.config.columns;\n\t\t\t\t}\n\n\t\t\t\tkeys.forEach((key)=>{\n\t\t\t\t\tif(key !== \"columns\" && typeof column[key] !== \"undefined\"){\n\t\t\t\t\t\tfrom[key] = column[key];\n\t\t\t\t\t}\n\t\t\t\t});\n\n\t\t\t\tif(from.columns){\n\t\t\t\t\tfrom.columns = this.mergeDefinition(from.columns, column.columns);\n\t\t\t\t}\n\n\t\t\t\toutput.push(from);\n\t\t\t}\n\t\t});\n\n\t\toldCols.forEach((column, i) => {\n\t\t\tvar from = this._findColumn(newCols, column);\n\n\t\t\tif (!from) {\n\t\t\t\tif(output.length>i){\n\t\t\t\t\toutput.splice(i, 0, column);\n\t\t\t\t}else {\n\t\t\t\t\toutput.push(column);\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\n\t\treturn output;\n\t}\n\n\t//find matching columns\n\t_findColumn(columns, subject){\n\t\tvar type = subject.columns ? \"group\" : (subject.field ? \"field\" : \"object\");\n\n\t\treturn columns.find(function(col){\n\t\t\tswitch(type){\n\t\t\t\tcase \"group\":\n\t\t\t\t\treturn col.title === subject.title && col.columns.length === subject.columns.length;\n\n\t\t\t\tcase \"field\":\n\t\t\t\t\treturn col.field === subject.field;\n\n\t\t\t\tcase \"object\":\n\t\t\t\t\treturn col === subject;\n\t\t\t}\n\t\t});\n\t}\n\n\t//save data\n\tsave(type){\n\t\tvar data = {};\n\n\t\tswitch(type){\n\t\t\tcase \"columns\":\n\t\t\t\tdata = this.parseColumns(this.table.columnManager.getColumns());\n\t\t\t\tbreak;\n\n\t\t\tcase \"filter\":\n\t\t\t\tdata = this.table.modules.filter.getFilters();\n\t\t\t\tbreak;\n\n\t\t\tcase \"headerFilter\":\n\t\t\t\tdata = this.table.modules.filter.getHeaderFilters();\n\t\t\t\tbreak;\n\n\t\t\tcase \"sort\":\n\t\t\t\tdata = this.validateSorters(this.table.modules.sort.getSort());\n\t\t\t\tbreak;\n\n\t\t\tcase \"group\":\n\t\t\t\tdata = this.getGroupConfig();\n\t\t\t\tbreak;\n\n\t\t\tcase \"page\":\n\t\t\t\tdata = this.getPageConfig();\n\t\t\t\tbreak;\n\t\t}\n\n\t\tif(this.writeFunc){\n\t\t\tthis.writeFunc(this.id, type, data);\n\t\t}\n\n\t}\n\n\t//ensure sorters contain no function data\n\tvalidateSorters(data){\n\t\tdata.forEach(function(item){\n\t\t\titem.column = item.field;\n\t\t\tdelete item.field;\n\t\t});\n\n\t\treturn data;\n\t}\n\n\tgetGroupConfig(){\n\t\tvar data = {};\n\n\t\tif(this.config.group){\n\t\t\tif(this.config.group === true || this.config.group.groupBy){\n\t\t\t\tdata.groupBy = this.table.options.groupBy;\n\t\t\t}\n\n\t\t\tif(this.config.group === true || this.config.group.groupStartOpen){\n\t\t\t\tdata.groupStartOpen = this.table.options.groupStartOpen;\n\t\t\t}\n\n\t\t\tif(this.config.group === true || this.config.group.groupHeader){\n\t\t\t\tdata.groupHeader = this.table.options.groupHeader;\n\t\t\t}\n\t\t}\n\n\t\treturn data;\n\t}\n\n\tgetPageConfig(){\n\t\tvar data = {};\n\n\t\tif(this.config.page){\n\t\t\tif(this.config.page === true || this.config.page.size){\n\t\t\t\tdata.paginationSize = this.table.modules.page.getPageSize();\n\t\t\t}\n\n\t\t\tif(this.config.page === true || this.config.page.page){\n\t\t\t\tdata.paginationInitialPage = this.table.modules.page.getPage();\n\t\t\t}\n\t\t}\n\n\t\treturn data;\n\t}\n\n\n\t//parse columns for data to store\n\tparseColumns(columns){\n\t\tvar definitions = [],\n\t\texcludedKeys = [\"headerContextMenu\", \"headerMenu\", \"contextMenu\", \"clickMenu\"];\n\n\t\tcolumns.forEach((column) => {\n\t\t\tvar defStore = {},\n\t\t\tcolDef = column.getDefinition(),\n\t\t\tkeys;\n\n\t\t\tif(column.isGroup){\n\t\t\t\tdefStore.title = colDef.title;\n\t\t\t\tdefStore.columns = this.parseColumns(column.getColumns());\n\t\t\t}else {\n\t\t\t\tdefStore.field = column.getField();\n\n\t\t\t\tif(this.config.columns === true || this.config.columns == undefined){\n\t\t\t\t\tkeys =  Object.keys(colDef);\n\t\t\t\t\tkeys.push(\"width\");\n\t\t\t\t\tkeys.push(\"visible\");\n\t\t\t\t}else {\n\t\t\t\t\tkeys = this.config.columns;\n\t\t\t\t}\n\n\t\t\t\tkeys.forEach((key)=>{\n\t\t\t\t\tswitch(key){\n\t\t\t\t\t\tcase \"width\":\n\t\t\t\t\t\t\tdefStore.width = column.getWidth();\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase \"visible\":\n\t\t\t\t\t\t\tdefStore.visible = column.visible;\n\t\t\t\t\t\t\tbreak;\n\n\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\tif(typeof colDef[key] !== \"function\" && excludedKeys.indexOf(key) === -1){\n\t\t\t\t\t\t\t\tdefStore[key] = colDef[key];\n\t\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t}\n\n\t\t\tdefinitions.push(defStore);\n\t\t});\n\n\t\treturn definitions;\n\t}\n}\n\nPersistence.moduleName = \"persistence\";\n\nPersistence.moduleInitOrder = -10;\n\n//load defaults\nPersistence.readers = defaultReaders;\nPersistence.writers = defaultWriters;\n\nclass Popup$1 extends Module{\n\t\n\tconstructor(table){\n\t\tsuper(table);\n\t\t\n\t\tthis.columnSubscribers = {};\n\t\t\n\t\tthis.registerTableOption(\"rowContextPopup\", false);\n\t\tthis.registerTableOption(\"rowClickPopup\", false);\n\t\tthis.registerTableOption(\"rowDblClickPopup\", false);\n\t\tthis.registerTableOption(\"groupContextPopup\", false);\n\t\tthis.registerTableOption(\"groupClickPopup\", false);\n\t\tthis.registerTableOption(\"groupDblClickPopup\", false);\n\t\t\n\t\tthis.registerColumnOption(\"headerContextPopup\");\n\t\tthis.registerColumnOption(\"headerClickPopup\");\n\t\tthis.registerColumnOption(\"headerDblClickPopup\");\n\t\tthis.registerColumnOption(\"headerPopup\");\n\t\tthis.registerColumnOption(\"headerPopupIcon\");\n\t\tthis.registerColumnOption(\"contextPopup\");\n\t\tthis.registerColumnOption(\"clickPopup\");\n\t\tthis.registerColumnOption(\"dblClickPopup\");\n\n\t\tthis.registerComponentFunction(\"cell\", \"popup\", this._componentPopupCall.bind(this));\n\t\tthis.registerComponentFunction(\"column\", \"popup\", this._componentPopupCall.bind(this));\n\t\tthis.registerComponentFunction(\"row\", \"popup\", this._componentPopupCall.bind(this));\n\t\tthis.registerComponentFunction(\"group\", \"popup\", this._componentPopupCall.bind(this));\n\t\t\n\t}\n\t\n\tinitialize(){\n\t\tthis.initializeRowWatchers();\n\t\tthis.initializeGroupWatchers();\n\t\t\n\t\tthis.subscribe(\"column-init\", this.initializeColumn.bind(this));\n\t}\n\n\t_componentPopupCall(component, contents, position){\n\t\tthis.loadPopupEvent(contents, null, component, position);\n\t}\n\t\n\tinitializeRowWatchers(){\n\t\tif(this.table.options.rowContextPopup){\n\t\t\tthis.subscribe(\"row-contextmenu\", this.loadPopupEvent.bind(this, this.table.options.rowContextPopup));\n\t\t\tthis.table.on(\"rowTapHold\", this.loadPopupEvent.bind(this, this.table.options.rowContextPopup));\n\t\t}\n\t\t\n\t\tif(this.table.options.rowClickPopup){\n\t\t\tthis.subscribe(\"row-click\", this.loadPopupEvent.bind(this, this.table.options.rowClickPopup));\n\t\t}\n\n\t\tif(this.table.options.rowDblClickPopup){\n\t\t\tthis.subscribe(\"row-dblclick\", this.loadPopupEvent.bind(this, this.table.options.rowDblClickPopup));\n\t\t}\n\t}\n\t\n\tinitializeGroupWatchers(){\n\t\tif(this.table.options.groupContextPopup){\n\t\t\tthis.subscribe(\"group-contextmenu\", this.loadPopupEvent.bind(this, this.table.options.groupContextPopup));\n\t\t\tthis.table.on(\"groupTapHold\", this.loadPopupEvent.bind(this, this.table.options.groupContextPopup));\n\t\t}\n\t\t\n\t\tif(this.table.options.groupClickPopup){\n\t\t\tthis.subscribe(\"group-click\", this.loadPopupEvent.bind(this, this.table.options.groupClickPopup));\n\t\t}\n\n\t\tif(this.table.options.groupDblClickPopup){\n\t\t\tthis.subscribe(\"group-dblclick\", this.loadPopupEvent.bind(this, this.table.options.groupDblClickPopup));\n\t\t}\n\t}\n\n\tinitializeColumn(column){\n\t\tvar def = column.definition;\n\t\t\n\t\t//handle column events\n\t\tif(def.headerContextPopup && !this.columnSubscribers.headerContextPopup){\n\t\t\tthis.columnSubscribers.headerContextPopup = this.loadPopupTableColumnEvent.bind(this, \"headerContextPopup\");\n\t\t\tthis.subscribe(\"column-contextmenu\", this.columnSubscribers.headerContextPopup);\n\t\t\tthis.table.on(\"headerTapHold\", this.loadPopupTableColumnEvent.bind(this, \"headerContextPopup\"));\n\t\t}\n\t\t\n\t\tif(def.headerClickPopup && !this.columnSubscribers.headerClickPopup){\n\t\t\tthis.columnSubscribers.headerClickPopup = this.loadPopupTableColumnEvent.bind(this, \"headerClickPopup\");\n\t\t\tthis.subscribe(\"column-click\", this.columnSubscribers.headerClickPopup);\n\t\t\n\t\t\n\t\t}if(def.headerDblClickPopup && !this.columnSubscribers.headerDblClickPopup){\n\t\t\tthis.columnSubscribers.headerDblClickPopup = this.loadPopupTableColumnEvent.bind(this, \"headerDblClickPopup\");\n\t\t\tthis.subscribe(\"column-dblclick\", this.columnSubscribers.headerDblClickPopup);\n\t\t}\n\t\t\n\t\tif(def.headerPopup){\n\t\t\tthis.initializeColumnHeaderPopup(column);\n\t\t}\n\t\t\n\t\t//handle cell events\n\t\tif(def.contextPopup && !this.columnSubscribers.contextPopup){\n\t\t\tthis.columnSubscribers.contextPopup = this.loadPopupTableCellEvent.bind(this, \"contextPopup\");\n\t\t\tthis.subscribe(\"cell-contextmenu\", this.columnSubscribers.contextPopup);\n\t\t\tthis.table.on(\"cellTapHold\", this.loadPopupTableCellEvent.bind(this, \"contextPopup\"));\n\t\t}\n\t\t\n\t\tif(def.clickPopup && !this.columnSubscribers.clickPopup){\n\t\t\tthis.columnSubscribers.clickPopup = this.loadPopupTableCellEvent.bind(this, \"clickPopup\");\n\t\t\tthis.subscribe(\"cell-click\", this.columnSubscribers.clickPopup);\n\t\t}\n\n\t\tif(def.dblClickPopup && !this.columnSubscribers.dblClickPopup){\n\t\t\tthis.columnSubscribers.dblClickPopup = this.loadPopupTableCellEvent.bind(this, \"dblClickPopup\");\n\t\t\tthis.subscribe(\"cell-click\", this.columnSubscribers.dblClickPopup);\n\t\t}\n\t}\n\t\n\tinitializeColumnHeaderPopup(column){\n\t\tvar icon = column.definition.headerPopupIcon,\n\t\theaderPopupEl;\n\t\t\n\t\theaderPopupEl = document.createElement(\"span\");\n\t\theaderPopupEl.classList.add(\"tabulator-header-popup-button\");\n\n\t\tif(icon){\n\t\t\tif(typeof icon === \"function\"){\n\t\t\t\ticon = icon(column.getComponent());\n\t\t\t}\n\n\t\t\tif(icon instanceof HTMLElement){\n\t\t\t\theaderPopupEl.appendChild(icon);\n\t\t\t}else {\n\t\t\t\theaderPopupEl.innerHTML = icon;\n\t\t\t}\n\t\t}else {\n\t\t\theaderPopupEl.innerHTML = \"&vellip;\";\n\t\t}\n\t\t\n\t\theaderPopupEl.addEventListener(\"click\", (e) => {\n\t\t\te.stopPropagation();\n\t\t\te.preventDefault();\n\t\t\t\n\t\t\tthis.loadPopupEvent(column.definition.headerPopup, e, column);\n\t\t});\n\t\t\n\t\tcolumn.titleElement.insertBefore(headerPopupEl, column.titleElement.firstChild);\n\t}\n\t\n\tloadPopupTableCellEvent(option, e, cell){\n\t\tif(cell._cell){\n\t\t\tcell = cell._cell;\n\t\t}\n\t\t\n\t\tif(cell.column.definition[option]){\n\t\t\tthis.loadPopupEvent(cell.column.definition[option], e, cell);\n\t\t}\n\t}\n\t\n\tloadPopupTableColumnEvent(option, e, column){\n\t\tif(column._column){\n\t\t\tcolumn = column._column;\n\t\t}\n\t\t\n\t\tif(column.definition[option]){\n\t\t\tthis.loadPopupEvent(column.definition[option], e, column);\n\t\t}\n\t}\n\t\n\tloadPopupEvent(contents, e, component, position){\n\t\tvar renderedCallback;\n\n\t\tfunction onRendered(callback){\n\t\t\trenderedCallback = callback;\n\t\t}\n\t\t\n\t\tif(component._group){\n\t\t\tcomponent = component._group;\n\t\t}else if(component._row){\n\t\t\tcomponent = component._row;\n\t\t}\n\t\t\n\t\tcontents = typeof contents == \"function\" ? contents.call(this.table, e, component.getComponent(),  onRendered) : contents;\n\t\t\n\t\tthis.loadPopup(e, component, contents, renderedCallback, position);\n\t}\n\t\n\tloadPopup(e, component, contents, renderedCallback, position){\n\t\tvar touch = !(e instanceof MouseEvent),\n\t\tcontentsEl, popup;\n\t\t\n\t\tif(contents instanceof HTMLElement){\n\t\t\tcontentsEl = contents;\n\t\t}else {\n\t\t\tcontentsEl = document.createElement(\"div\");\n\t\t\tcontentsEl.innerHTML = contents;\n\t\t}\n\t\t\n\t\tcontentsEl.classList.add(\"tabulator-popup\");\n\n\t\tcontentsEl.addEventListener(\"click\", (e) =>{\n\t\t\te.stopPropagation();\n\t\t});\n\n\t\tif(!touch){\n\t\t\te.preventDefault();\n\t\t}\n\t\t\n\t\tpopup = this.popup(contentsEl);\n\n\t\tif(typeof renderedCallback === \"function\"){\n\t\t\tpopup.renderCallback(renderedCallback);\n\t\t}\n\n\t\tif(e){\n\t\t\tpopup.show(e);\n\t\t}else {\n\t\t\tpopup.show(component.getElement(), position || \"center\");\n\t\t}\n\n\t\t\n\t\tpopup.hideOnBlur(() => {\n\t\t\tthis.dispatchExternal(\"popupClosed\", component.getComponent());\n\t\t});\n\n\n\n\t\tthis.dispatchExternal(\"popupOpened\", component.getComponent());\n\t}\n}\n\nPopup$1.moduleName = \"popup\";\n\nclass Print extends Module{\n\n\tconstructor(table){\n\t\tsuper(table);\n\n\t\tthis.element = false;\n\t\tthis.manualBlock = false;\n\t\tthis.beforeprintEventHandler = null;\n\t\tthis.afterprintEventHandler = null;\n\n\t\tthis.registerTableOption(\"printAsHtml\", false); //enable print as html\n\t\tthis.registerTableOption(\"printFormatter\", false); //printing page formatter\n\t\tthis.registerTableOption(\"printHeader\", false); //page header contents\n\t\tthis.registerTableOption(\"printFooter\", false); //page footer contents\n\t\tthis.registerTableOption(\"printStyled\", true); //enable print as html styling\n\t\tthis.registerTableOption(\"printRowRange\", \"visible\"); //restrict print to visible rows only\n\t\tthis.registerTableOption(\"printConfig\", {}); //print config options\n\n\t\tthis.registerColumnOption(\"print\");\n\t\tthis.registerColumnOption(\"titlePrint\");\n\t}\n\n\tinitialize(){\n\t\tif(this.table.options.printAsHtml){\n\t\t\tthis.beforeprintEventHandler = this.replaceTable.bind(this);\n\t\t\tthis.afterprintEventHandler = this.cleanup.bind(this);\n\n\t\t\twindow.addEventListener(\"beforeprint\", this.beforeprintEventHandler );\n\t\t\twindow.addEventListener(\"afterprint\", this.afterprintEventHandler);\n\t\t\tthis.subscribe(\"table-destroy\", this.destroy.bind(this));\n\t\t}\n\n\t\tthis.registerTableFunction(\"print\", this.printFullscreen.bind(this));\n\t}\n\n\tdestroy(){\n\t\tif(this.table.options.printAsHtml){\n\t\t\twindow.removeEventListener( \"beforeprint\", this.beforeprintEventHandler );\n\t\t\twindow.removeEventListener( \"afterprint\", this.afterprintEventHandler );\n\t\t}\n\t}\n\n\t///////////////////////////////////\n\t///////// Table Functions /////////\n\t///////////////////////////////////\n\n\t///////////////////////////////////\n\t///////// Internal Logic //////////\n\t///////////////////////////////////\n\n\treplaceTable(){\n\t\tif(!this.manualBlock){\n\t\t\tthis.element = document.createElement(\"div\");\n\t\t\tthis.element.classList.add(\"tabulator-print-table\");\n\n\t\t\tthis.element.appendChild(this.table.modules.export.generateTable(this.table.options.printConfig, this.table.options.printStyled, this.table.options.printRowRange, \"print\"));\n\n\t\t\tthis.table.element.style.display = \"none\";\n\n\t\t\tthis.table.element.parentNode.insertBefore(this.element, this.table.element);\n\t\t}\n\t}\n\n\tcleanup(){\n\t\tdocument.body.classList.remove(\"tabulator-print-fullscreen-hide\");\n\n\t\tif(this.element && this.element.parentNode){\n\t\t\tthis.element.parentNode.removeChild(this.element);\n\t\t\tthis.table.element.style.display = \"\";\n\t\t}\n\t}\n\n\tprintFullscreen(visible, style, config){\n\t\tvar scrollX = window.scrollX,\n\t\tscrollY = window.scrollY,\n\t\theaderEl = document.createElement(\"div\"),\n\t\tfooterEl = document.createElement(\"div\"),\n\t\ttableEl = this.table.modules.export.generateTable(typeof config != \"undefined\" ? config : this.table.options.printConfig, typeof style != \"undefined\" ? style : this.table.options.printStyled, visible || this.table.options.printRowRange, \"print\"),\n\t\theaderContent, footerContent;\n\n\t\tthis.manualBlock = true;\n\n\t\tthis.element = document.createElement(\"div\");\n\t\tthis.element.classList.add(\"tabulator-print-fullscreen\");\n\n\t\tif(this.table.options.printHeader){\n\t\t\theaderEl.classList.add(\"tabulator-print-header\");\n\n\t\t\theaderContent = typeof this.table.options.printHeader == \"function\" ? this.table.options.printHeader.call(this.table) : this.table.options.printHeader;\n\n\t\t\tif(typeof headerContent == \"string\"){\n\t\t\t\theaderEl.innerHTML = headerContent;\n\t\t\t}else {\n\t\t\t\theaderEl.appendChild(headerContent);\n\t\t\t}\n\n\t\t\tthis.element.appendChild(headerEl);\n\t\t}\n\n\t\tthis.element.appendChild(tableEl);\n\n\t\tif(this.table.options.printFooter){\n\t\t\tfooterEl.classList.add(\"tabulator-print-footer\");\n\n\t\t\tfooterContent = typeof this.table.options.printFooter == \"function\" ? this.table.options.printFooter.call(this.table) : this.table.options.printFooter;\n\n\n\t\t\tif(typeof footerContent == \"string\"){\n\t\t\t\tfooterEl.innerHTML = footerContent;\n\t\t\t}else {\n\t\t\t\tfooterEl.appendChild(footerContent);\n\t\t\t}\n\n\t\t\tthis.element.appendChild(footerEl);\n\t\t}\n\n\t\tdocument.body.classList.add(\"tabulator-print-fullscreen-hide\");\n\t\tdocument.body.appendChild(this.element);\n\n\t\tif(this.table.options.printFormatter){\n\t\t\tthis.table.options.printFormatter(this.element, tableEl);\n\t\t}\n\n\t\twindow.print();\n\n\t\tthis.cleanup();\n\n\t\twindow.scrollTo(scrollX, scrollY);\n\n\t\tthis.manualBlock = false;\n\t}\n}\n\nPrint.moduleName = \"print\";\n\nclass ReactiveData extends Module{\n\t\n\tconstructor(table){\n\t\tsuper(table);\n\t\t\n\t\tthis.data = false;\n\t\tthis.blocked = false; //block reactivity while performing update\n\t\tthis.origFuncs = {}; // hold original data array functions to allow replacement after data is done with\n\t\tthis.currentVersion = 0;\n\t\t\n\t\tthis.registerTableOption(\"reactiveData\", false); //enable data reactivity\n\t}\n\t\n\tinitialize(){\n\t\tif(this.table.options.reactiveData){\n\t\t\tthis.subscribe(\"cell-value-save-before\", this.block.bind(this, \"cellsave\"));\n\t\t\tthis.subscribe(\"cell-value-save-after\", this.unblock.bind(this, \"cellsave\"));\n\t\t\tthis.subscribe(\"row-data-save-before\", this.block.bind(this, \"rowsave\"));\n\t\t\tthis.subscribe(\"row-data-save-after\", this.unblock.bind(this, \"rowsave\"));\n\t\t\tthis.subscribe(\"row-data-init-after\", this.watchRow.bind(this));\n\t\t\tthis.subscribe(\"data-processing\", this.watchData.bind(this));\n\t\t\tthis.subscribe(\"table-destroy\", this.unwatchData.bind(this));\n\t\t}\n\t}\n\t\n\twatchData(data){\n\t\tvar self = this,\n\t\tversion;\n\t\t\n\t\tthis.currentVersion ++;\n\t\t\n\t\tversion = this.currentVersion;\n\t\t\n\t\tthis.unwatchData();\n\t\t\n\t\tthis.data = data;\n\t\t\n\t\t//override array push function\n\t\tthis.origFuncs.push = data.push;\n\t\t\n\t\tObject.defineProperty(this.data, \"push\", {\n\t\t\tenumerable: false,\n\t\t\tconfigurable: true,\n\t\t\tvalue: function(){\n\t\t\t\tvar args = Array.from(arguments),\n\t\t\t\tresult;\n\n\t\t\t\tif(!self.blocked && version === self.currentVersion){\t\n\t\t\t\t\tself.block(\"data-push\");\n\n\t\t\t\t\targs.forEach((arg) => {\n\t\t\t\t\t\tself.table.rowManager.addRowActual(arg, false);\n\t\t\t\t\t});\n\t\t\t\t\t\n\t\t\t\t\tresult = self.origFuncs.push.apply(data, arguments);\n\t\t\t\t\t\n\t\t\t\t\tself.unblock(\"data-push\");\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\treturn result;\n\t\t\t}\n\t\t});\n\t\t\n\t\t//override array unshift function\n\t\tthis.origFuncs.unshift = data.unshift;\n\t\t\n\t\tObject.defineProperty(this.data, \"unshift\", {\n\t\t\tenumerable: false,\n\t\t\tconfigurable: true,\n\t\t\tvalue: function(){\n\t\t\t\tvar args = Array.from(arguments),\n\t\t\t\tresult;\n\t\t\t\t\n\t\t\t\tif(!self.blocked && version === self.currentVersion){\n\t\t\t\t\tself.block(\"data-unshift\");\n\t\t\t\t\t\n\t\t\t\t\targs.forEach((arg) => {\n\t\t\t\t\t\tself.table.rowManager.addRowActual(arg, true);\n\t\t\t\t\t});\n\t\t\t\t\t\n\t\t\t\t\tresult = self.origFuncs.unshift.apply(data, arguments);\n\t\t\t\t\t\n\t\t\t\t\tself.unblock(\"data-unshift\");\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\treturn result;\n\t\t\t}\n\t\t});\n\t\t\n\t\t\n\t\t//override array shift function\n\t\tthis.origFuncs.shift = data.shift;\n\t\t\n\t\tObject.defineProperty(this.data, \"shift\", {\n\t\t\tenumerable: false,\n\t\t\tconfigurable: true,\n\t\t\tvalue: function(){\n\t\t\t\tvar row, result;\n\t\t\t\t\n\t\t\t\tif(!self.blocked && version === self.currentVersion){\n\t\t\t\t\tself.block(\"data-shift\");\n\t\t\t\t\t\n\t\t\t\t\tif(self.data.length){\n\t\t\t\t\t\trow = self.table.rowManager.getRowFromDataObject(self.data[0]);\n\t\t\t\t\t\t\n\t\t\t\t\t\tif(row){\n\t\t\t\t\t\t\trow.deleteActual();\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\tresult = self.origFuncs.shift.call(data);\n\n\t\t\t\t\tself.unblock(\"data-shift\");\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\treturn result;\n\t\t\t}\n\t\t});\n\t\t\n\t\t//override array pop function\n\t\tthis.origFuncs.pop = data.pop;\n\t\t\n\t\tObject.defineProperty(this.data, \"pop\", {\n\t\t\tenumerable: false,\n\t\t\tconfigurable: true,\n\t\t\tvalue: function(){\n\t\t\t\tvar row, result;\n\t\t\t\n\t\t\t\tif(!self.blocked && version === self.currentVersion){\n\t\t\t\t\tself.block(\"data-pop\");\n\t\t\t\t\t\n\t\t\t\t\tif(self.data.length){\n\t\t\t\t\t\trow = self.table.rowManager.getRowFromDataObject(self.data[self.data.length - 1]);\n\t\t\t\t\t\t\n\t\t\t\t\t\tif(row){\n\t\t\t\t\t\t\trow.deleteActual();\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\tresult = self.origFuncs.pop.call(data);\n\t\t\t\t\t\n\t\t\t\t\tself.unblock(\"data-pop\");\n\t\t\t\t}\n\n\t\t\t\treturn result;\n\t\t\t}\n\t\t});\n\t\t\n\t\t\n\t\t//override array splice function\n\t\tthis.origFuncs.splice = data.splice;\n\t\t\n\t\tObject.defineProperty(this.data, \"splice\", {\n\t\t\tenumerable: false,\n\t\t\tconfigurable: true,\n\t\t\tvalue: function(){\n\t\t\t\tvar args = Array.from(arguments),\n\t\t\t\tstart = args[0] < 0 ? data.length + args[0] : args[0],\n\t\t\t\tend = args[1],\n\t\t\t\tnewRows = args[2] ? args.slice(2) : false,\n\t\t\t\tstartRow, result;\n\t\t\t\t\n\t\t\t\tif(!self.blocked && version === self.currentVersion){\n\t\t\t\t\tself.block(\"data-splice\");\n\t\t\t\t\t//add new rows\n\t\t\t\t\tif(newRows){\n\t\t\t\t\t\tstartRow = data[start] ? self.table.rowManager.getRowFromDataObject(data[start]) : false;\n\t\t\t\t\t\t\n\t\t\t\t\t\tif(startRow){\n\t\t\t\t\t\t\tnewRows.forEach((rowData) => {\n\t\t\t\t\t\t\t\tself.table.rowManager.addRowActual(rowData, true, startRow, true);\n\t\t\t\t\t\t\t});\n\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\tnewRows = newRows.slice().reverse();\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\tnewRows.forEach((rowData) => {\n\t\t\t\t\t\t\t\tself.table.rowManager.addRowActual(rowData, true, false, true);\n\t\t\t\t\t\t\t});\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\t//delete removed rows\n\t\t\t\t\tif(end !== 0){\n\t\t\t\t\t\tvar oldRows = data.slice(start, typeof args[1] === \"undefined\" ? args[1] : start + end);\n\t\t\t\t\t\t\n\t\t\t\t\t\toldRows.forEach((rowData, i) => {\n\t\t\t\t\t\t\tvar row = self.table.rowManager.getRowFromDataObject(rowData);\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\tif(row){\n\t\t\t\t\t\t\t\trow.deleteActual(i !== oldRows.length - 1);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t});\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\tif(newRows || end !== 0){\n\t\t\t\t\t\tself.table.rowManager.reRenderInPosition();\n\t\t\t\t\t}\n\n\t\t\t\t\tresult = self.origFuncs.splice.apply(data, arguments);\n\t\t\t\t\t\n\t\t\t\t\tself.unblock(\"data-splice\");\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\treturn result ;\n\t\t\t}\n\t\t});\n\t}\n\t\n\tunwatchData(){\n\t\tif(this.data !== false){\n\t\t\tfor(var key in this.origFuncs){\n\t\t\t\tObject.defineProperty(this.data, key, {\n\t\t\t\t\tenumerable: true,\n\t\t\t\t\tconfigurable:true,\n\t\t\t\t\twritable:true,\n\t\t\t\t\tvalue: this.origFuncs.key,\n\t\t\t\t});\n\t\t\t}\n\t\t}\n\t}\n\t\n\twatchRow(row){\n\t\tvar data = row.getData();\n\t\t\n\t\tfor(var key in data){\n\t\t\tthis.watchKey(row, data, key);\n\t\t}\n\t\t\n\t\tif(this.table.options.dataTree){\n\t\t\tthis.watchTreeChildren(row);\n\t\t}\n\t}\n\t\n\twatchTreeChildren (row){\n\t\tvar self = this,\n\t\tchildField = row.getData()[this.table.options.dataTreeChildField],\n\t\torigFuncs = {};\n\t\t\n\t\tif(childField){\n\t\t\t\n\t\t\torigFuncs.push = childField.push;\n\t\t\t\n\t\t\tObject.defineProperty(childField, \"push\", {\n\t\t\t\tenumerable: false,\n\t\t\t\tconfigurable: true,\n\t\t\t\tvalue: () => {\n\t\t\t\t\tif(!self.blocked){\n\t\t\t\t\t\tself.block(\"tree-push\");\n\t\t\t\t\t\t\n\t\t\t\t\t\tvar result = origFuncs.push.apply(childField, arguments);\n\t\t\t\t\t\tthis.rebuildTree(row);\n\t\t\t\t\t\t\n\t\t\t\t\t\tself.unblock(\"tree-push\");\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\treturn result;\n\t\t\t\t}\n\t\t\t});\n\t\t\t\n\t\t\torigFuncs.unshift = childField.unshift;\n\t\t\t\n\t\t\tObject.defineProperty(childField, \"unshift\", {\n\t\t\t\tenumerable: false,\n\t\t\t\tconfigurable: true,\n\t\t\t\tvalue: () => {\n\t\t\t\t\tif(!self.blocked){\n\t\t\t\t\t\tself.block(\"tree-unshift\");\n\t\t\t\t\t\t\n\t\t\t\t\t\tvar result =  origFuncs.unshift.apply(childField, arguments);\n\t\t\t\t\t\tthis.rebuildTree(row);\n\t\t\t\t\t\t\n\t\t\t\t\t\tself.unblock(\"tree-unshift\");\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\treturn result;\n\t\t\t\t}\n\t\t\t});\n\t\t\t\n\t\t\torigFuncs.shift = childField.shift;\n\t\t\t\n\t\t\tObject.defineProperty(childField, \"shift\", {\n\t\t\t\tenumerable: false,\n\t\t\t\tconfigurable: true,\n\t\t\t\tvalue: () => {\n\t\t\t\t\tif(!self.blocked){\n\t\t\t\t\t\tself.block(\"tree-shift\");\n\t\t\t\t\t\t\n\t\t\t\t\t\tvar result =  origFuncs.shift.call(childField);\n\t\t\t\t\t\tthis.rebuildTree(row);\n\t\t\t\t\t\t\n\t\t\t\t\t\tself.unblock(\"tree-shift\");\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\treturn result;\n\t\t\t\t}\n\t\t\t});\n\t\t\t\n\t\t\torigFuncs.pop = childField.pop;\n\t\t\t\n\t\t\tObject.defineProperty(childField, \"pop\", {\n\t\t\t\tenumerable: false,\n\t\t\t\tconfigurable: true,\n\t\t\t\tvalue: () => {\n\t\t\t\t\tif(!self.blocked){\n\t\t\t\t\t\tself.block(\"tree-pop\");\n\t\t\t\t\t\t\n\t\t\t\t\t\tvar result =  origFuncs.pop.call(childField);\n\t\t\t\t\t\tthis.rebuildTree(row);\n\t\t\t\t\t\t\n\t\t\t\t\t\tself.unblock(\"tree-pop\");\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\treturn result;\n\t\t\t\t}\n\t\t\t});\n\t\t\t\n\t\t\torigFuncs.splice = childField.splice;\n\t\t\t\n\t\t\tObject.defineProperty(childField, \"splice\", {\n\t\t\t\tenumerable: false,\n\t\t\t\tconfigurable: true,\n\t\t\t\tvalue: () => {\n\t\t\t\t\tif(!self.blocked){\n\t\t\t\t\t\tself.block(\"tree-splice\");\n\t\t\t\t\t\t\n\t\t\t\t\t\tvar result =  origFuncs.splice.apply(childField, arguments);\n\t\t\t\t\t\tthis.rebuildTree(row);\n\t\t\t\t\t\t\n\t\t\t\t\t\tself.unblock(\"tree-splice\");\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\treturn result;\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\t}\n\t\n\trebuildTree(row){\n\t\tthis.table.modules.dataTree.initializeRow(row);\n\t\tthis.table.modules.dataTree.layoutRow(row);\n\t\tthis.table.rowManager.refreshActiveData(\"tree\", false, true);\n\t}\n\t\n\twatchKey(row, data, key){\n\t\tvar self = this,\n\t\tprops = Object.getOwnPropertyDescriptor(data, key),\n\t\tvalue = data[key],\n\t\tversion = this.currentVersion;\n\t\t\n\t\tObject.defineProperty(data, key, {\n\t\t\tset: (newValue) => {\n\t\t\t\tvalue = newValue;\n\t\t\t\tif(!self.blocked && version === self.currentVersion){\n\t\t\t\t\tself.block(\"key\");\n\t\t\t\t\t\n\t\t\t\t\tvar update = {};\n\t\t\t\t\tupdate[key] = newValue;\n\t\t\t\t\trow.updateData(update);\n\t\t\t\t\t\n\t\t\t\t\tself.unblock(\"key\");\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tif(props.set){\n\t\t\t\t\tprops.set(newValue);\n\t\t\t\t}\n\t\t\t},\n\t\t\tget:() => {\n\t\t\t\t\n\t\t\t\tif(props.get){\n\t\t\t\t\tprops.get();\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\treturn value;\n\t\t\t}\n\t\t});\n\t}\n\t\n\tunwatchRow(row){\n\t\tvar data = row.getData();\n\t\t\n\t\tfor(var key in data){\n\t\t\tObject.defineProperty(data, key, {\n\t\t\t\tvalue:data[key],\n\t\t\t});\n\t\t}\n\t}\n\t\n\tblock(key){\n\t\tif(!this.blocked){\n\t\t\tthis.blocked = key;\n\t\t}\n\t}\n\t\n\tunblock(key){\n\t\tif(this.blocked === key){\n\t\t\tthis.blocked = false;\n\t\t}\n\t}\n}\n\nReactiveData.moduleName = \"reactiveData\";\n\nclass ResizeColumns extends Module{\n\t\n\tconstructor(table){\n\t\tsuper(table);\n\t\t\n\t\tthis.startColumn = false;\n\t\tthis.startX = false;\n\t\tthis.startWidth = false;\n\t\tthis.latestX = false;\n\t\tthis.handle = null;\n\t\tthis.initialNextColumn = null;\n\t\tthis.nextColumn = null;\n\t\t\n\t\tthis.initialized = false;\n\t\tthis.registerColumnOption(\"resizable\", true);\n\t\tthis.registerTableOption(\"resizableColumnFit\", false);\n\t}\n\t\n\tinitialize(){\n\t\tthis.subscribe(\"column-rendered\", this.layoutColumnHeader.bind(this));\n\t}\n\t\n\tinitializeEventWatchers(){\n\t\tif(!this.initialized){\n\t\t\t\n\t\t\tthis.subscribe(\"cell-rendered\", this.layoutCellHandles.bind(this));\n\t\t\tthis.subscribe(\"cell-delete\", this.deInitializeComponent.bind(this));\n\t\t\t\n\t\t\tthis.subscribe(\"cell-height\", this.resizeHandle.bind(this));\n\t\t\tthis.subscribe(\"column-moved\", this.columnLayoutUpdated.bind(this));\n\t\t\t\n\t\t\tthis.subscribe(\"column-hide\", this.deInitializeColumn.bind(this));\n\t\t\tthis.subscribe(\"column-show\", this.columnLayoutUpdated.bind(this));\n\t\t\tthis.subscribe(\"column-width\", this.columnWidthUpdated.bind(this));\n\t\t\t\n\t\t\tthis.subscribe(\"column-delete\", this.deInitializeComponent.bind(this));\n\t\t\tthis.subscribe(\"column-height\", this.resizeHandle.bind(this));\n\t\t\t\n\t\t\tthis.initialized = true;\n\t\t}\n\t}\n\t\n\t\n\tlayoutCellHandles(cell){\n\t\tif(cell.row.type === \"row\"){\n\t\t\tthis.deInitializeComponent(cell);\n\t\t\tthis.initializeColumn(\"cell\", cell, cell.column, cell.element);\n\t\t}\n\t}\n\t\n\tlayoutColumnHeader(column){\n\t\tif(column.definition.resizable){\n\t\t\tthis.initializeEventWatchers();\n\t\t\tthis.deInitializeComponent(column);\n\t\t\tthis.initializeColumn(\"header\", column, column, column.element);\n\t\t}\n\t}\n\t\n\tcolumnLayoutUpdated(column){\n\t\tvar prev = column.prevColumn();\n\t\t\n\t\tthis.reinitializeColumn(column);\n\t\t\n\t\tif(prev){\n\t\t\tthis.reinitializeColumn(prev);\n\t\t}\n\t}\n\t\n\tcolumnWidthUpdated(column){\n\t\tif(column.modules.frozen){\n\t\t\tif(this.table.modules.frozenColumns.leftColumns.includes(column)){\n\t\t\t\tthis.table.modules.frozenColumns.leftColumns.forEach((col) => {\n\t\t\t\t\tthis.reinitializeColumn(col);\n\t\t\t\t});\n\t\t\t}else if(this.table.modules.frozenColumns.rightColumns.includes(column)){\n\t\t\t\tthis.table.modules.frozenColumns.rightColumns.forEach((col) => {\n\t\t\t\t\tthis.reinitializeColumn(col);\n\t\t\t\t});\n\t\t\t}\n\t\t}\n\t}\n\n\tfrozenColumnOffset(column){\n\t\tvar offset = false;\n\n\t\tif(column.modules.frozen){\n\t\t\toffset = column.modules.frozen.marginValue; \n\n\t\t\tif(column.modules.frozen.position === \"left\"){\n\t\t\t\toffset += column.getWidth() - 3;\n\t\t\t}else {\n\t\t\t\tif(offset){\n\t\t\t\t\toffset -= 3;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn offset !== false ? offset + \"px\" : false;\n\t}\n\t\n\treinitializeColumn(column){\n\t\tvar frozenOffset = this.frozenColumnOffset(column);\n\t\t\n\t\tcolumn.cells.forEach((cell) => {\n\t\t\tif(cell.modules.resize && cell.modules.resize.handleEl){\n\t\t\t\tif(frozenOffset){\n\t\t\t\t\tcell.modules.resize.handleEl.style[column.modules.frozen.position] = frozenOffset;\n\t\t\t\t\tcell.modules.resize.handleEl.style[\"z-index\"] = 11;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tcell.element.after(cell.modules.resize.handleEl);\n\t\t\t}\n\t\t});\n\t\t\n\t\tif(column.modules.resize && column.modules.resize.handleEl){\n\t\t\tif(frozenOffset){\n\t\t\t\tcolumn.modules.resize.handleEl.style[column.modules.frozen.position] = frozenOffset;\n\t\t\t}\n\t\t\t\n\t\t\tcolumn.element.after(column.modules.resize.handleEl);\n\t\t}\n\t}\n\t\n\tinitializeColumn(type, component, column, element){\n\t\tvar self = this,\n\t\tvariableHeight = false,\n\t\tmode = column.definition.resizable,\n\t\tconfig = {},\n\t\tnearestColumn = column.getLastColumn();\n\t\t\n\t\t//set column resize mode\n\t\tif(type === \"header\"){\n\t\t\tvariableHeight = column.definition.formatter == \"textarea\" || column.definition.variableHeight;\n\t\t\tconfig = {variableHeight:variableHeight};\n\t\t}\n\t\t\n\t\tif((mode === true || mode == type) && this._checkResizability(nearestColumn)){\n\t\t\t\n\t\t\tvar handle = document.createElement('span');\n\t\t\thandle.className = \"tabulator-col-resize-handle\";\n\t\t\t\n\t\t\thandle.addEventListener(\"click\", function(e){\n\t\t\t\te.stopPropagation();\n\t\t\t});\n\t\t\t\n\t\t\tvar handleDown = function(e){\n\t\t\t\tself.startColumn = column;\n\t\t\t\tself.initialNextColumn = self.nextColumn = nearestColumn.nextColumn();\n\t\t\t\tself._mouseDown(e, nearestColumn, handle);\n\t\t\t};\n\t\t\t\n\t\t\thandle.addEventListener(\"mousedown\", handleDown);\n\t\t\thandle.addEventListener(\"touchstart\", handleDown, {passive: true});\n\t\t\t\n\t\t\t//resize column on  double click\n\t\t\thandle.addEventListener(\"dblclick\", (e) => {\n\t\t\t\tvar oldWidth = nearestColumn.getWidth();\n\t\t\t\t\n\t\t\t\te.stopPropagation();\n\t\t\t\tnearestColumn.reinitializeWidth(true);\n\t\t\t\t\n\t\t\t\tif(oldWidth !== nearestColumn.getWidth()){\n\t\t\t\t\tself.dispatch(\"column-resized\", nearestColumn);\n\t\t\t\t\tself.table.externalEvents.dispatch(\"columnResized\", nearestColumn.getComponent());\n\t\t\t\t}\n\t\t\t});\n\t\t\t\n\t\t\tif(column.modules.frozen){\n\t\t\t\thandle.style.position = \"sticky\";\n\t\t\t\thandle.style[column.modules.frozen.position] = this.frozenColumnOffset(column);\n\t\t\t}\n\t\t\t\n\t\t\tconfig.handleEl = handle;\n\t\t\t\n\t\t\tif(element.parentNode && column.visible){\n\t\t\t\telement.after(handle);\t\t\t\n\t\t\t}\n\t\t}\n\t\t\n\t\tcomponent.modules.resize = config;\n\t}\n\t\n\tdeInitializeColumn(column){\n\t\tthis.deInitializeComponent(column);\n\t\t\n\t\tcolumn.cells.forEach((cell) => {\n\t\t\tthis.deInitializeComponent(cell);\n\t\t});\n\t}\n\t\n\tdeInitializeComponent(component){\n\t\tvar handleEl;\n\t\t\n\t\tif(component.modules.resize){\n\t\t\thandleEl = component.modules.resize.handleEl;\n\t\t\t\n\t\t\tif(handleEl && handleEl.parentElement){\n\t\t\t\thandleEl.parentElement.removeChild(handleEl);\n\t\t\t}\n\t\t}\n\t}\n\t\n\tresizeHandle(component, height){\n\t\tif(component.modules.resize && component.modules.resize.handleEl){\n\t\t\tcomponent.modules.resize.handleEl.style.height = height;\n\t\t}\n\t}\n\t\n\t_checkResizability(column){\n\t\treturn column.definition.resizable;\n\t}\n\t\n\t_mouseDown(e, column, handle){\n\t\tvar self = this;\n\t\t\n\t\tself.table.element.classList.add(\"tabulator-block-select\");\n\t\t\n\t\tfunction mouseMove(e){\n\t\t\tvar x = typeof e.screenX === \"undefined\" ? e.touches[0].screenX : e.screenX,\n\t\t\tstartDiff = x - self.startX,\n\t\t\tmoveDiff = x - self.latestX,\n\t\t\tblockedBefore, blockedAfter;\n\t\t\t\n\t\t\tself.latestX = x;\n\t\t\t\n\t\t\tif(self.table.rtl){\n\t\t\t\tstartDiff = -startDiff;\n\t\t\t\tmoveDiff = -moveDiff;\n\t\t\t}\n\t\t\t\n\t\t\tblockedBefore = column.width == column.minWidth || column.width == column.maxWidth;\n\t\t\t\n\t\t\tcolumn.setWidth(self.startWidth + startDiff);\n\t\t\t\n\t\t\tblockedAfter = column.width == column.minWidth || column.width == column.maxWidth;\n\t\t\t\n\t\t\tif(moveDiff < 0){\n\t\t\t\tself.nextColumn = self.initialNextColumn;\n\t\t\t}\n\t\t\t\n\t\t\tif(self.table.options.resizableColumnFit && self.nextColumn && !(blockedBefore && blockedAfter)){\n\t\t\t\tlet colWidth = self.nextColumn.getWidth();\n\t\t\t\t\n\t\t\t\tif(moveDiff > 0){\n\t\t\t\t\tif(colWidth <= self.nextColumn.minWidth){\n\t\t\t\t\t\tself.nextColumn = self.nextColumn.nextColumn();\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tif(self.nextColumn){\n\t\t\t\t\tself.nextColumn.setWidth(self.nextColumn.getWidth() - moveDiff);\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\tself.table.columnManager.rerenderColumns(true);\n\t\t\t\n\t\t\tif(!self.table.browserSlow && column.modules.resize && column.modules.resize.variableHeight){\n\t\t\t\tcolumn.checkCellHeights();\n\t\t\t}\n\t\t}\n\t\t\n\t\tfunction mouseUp(e){\n\t\t\t\n\t\t\t//block editor from taking action while resizing is taking place\n\t\t\tif(self.startColumn.modules.edit){\n\t\t\t\tself.startColumn.modules.edit.blocked = false;\n\t\t\t}\n\t\t\t\n\t\t\tif(self.table.browserSlow && column.modules.resize && column.modules.resize.variableHeight){\n\t\t\t\tcolumn.checkCellHeights();\n\t\t\t}\n\t\t\t\n\t\t\tdocument.body.removeEventListener(\"mouseup\", mouseUp);\n\t\t\tdocument.body.removeEventListener(\"mousemove\", mouseMove);\n\t\t\t\n\t\t\thandle.removeEventListener(\"touchmove\", mouseMove);\n\t\t\thandle.removeEventListener(\"touchend\", mouseUp);\n\t\t\t\n\t\t\tself.table.element.classList.remove(\"tabulator-block-select\");\n\t\t\t\n\t\t\tif(self.startWidth !== column.getWidth()){\n\t\t\t\tself.table.columnManager.verticalAlignHeaders();\n\n\t\t\t\tself.dispatch(\"column-resized\", column);\n\t\t\t\tself.table.externalEvents.dispatch(\"columnResized\", column.getComponent());\n\t\t\t}\n\t\t}\n\t\t\n\t\te.stopPropagation(); //prevent resize from interfering with movable columns\n\t\t\n\t\t//block editor from taking action while resizing is taking place\n\t\tif(self.startColumn.modules.edit){\n\t\t\tself.startColumn.modules.edit.blocked = true;\n\t\t}\n\t\t\n\t\tself.startX = typeof e.screenX === \"undefined\" ? e.touches[0].screenX : e.screenX;\n\t\tself.latestX = self.startX;\n\t\tself.startWidth = column.getWidth();\n\t\t\n\t\tdocument.body.addEventListener(\"mousemove\", mouseMove);\n\t\tdocument.body.addEventListener(\"mouseup\", mouseUp);\n\t\thandle.addEventListener(\"touchmove\", mouseMove, {passive: true});\n\t\thandle.addEventListener(\"touchend\", mouseUp);\n\t}\n}\n\nResizeColumns.moduleName = \"resizeColumns\";\n\nclass ResizeRows extends Module{\n\n\tconstructor(table){\n\t\tsuper(table);\n\n\t\tthis.startColumn = false;\n\t\tthis.startY = false;\n\t\tthis.startHeight = false;\n\t\tthis.handle = null;\n\t\tthis.prevHandle = null;\n\n\t\tthis.registerTableOption(\"resizableRows\", false); //resizable rows\n\t}\n\n\tinitialize(){\n\t\tif(this.table.options.resizableRows){\n\t\t\tthis.subscribe(\"row-layout-after\", this.initializeRow.bind(this));\n\t\t}\n\t}\n\n\tinitializeRow(row){\n\t\tvar self = this,\n\t\trowEl = row.getElement();\n\n\t\tvar handle = document.createElement('div');\n\t\thandle.className = \"tabulator-row-resize-handle\";\n\n\t\tvar prevHandle = document.createElement('div');\n\t\tprevHandle.className = \"tabulator-row-resize-handle prev\";\n\n\t\thandle.addEventListener(\"click\", function(e){\n\t\t\te.stopPropagation();\n\t\t});\n\n\t\tvar handleDown = function(e){\n\t\t\tself.startRow = row;\n\t\t\tself._mouseDown(e, row, handle);\n\t\t};\n\n\t\thandle.addEventListener(\"mousedown\", handleDown);\n\t\thandle.addEventListener(\"touchstart\", handleDown, {passive: true});\n\n\t\tprevHandle.addEventListener(\"click\", function(e){\n\t\t\te.stopPropagation();\n\t\t});\n\n\t\tvar prevHandleDown =  function(e){\n\t\t\tvar prevRow = self.table.rowManager.prevDisplayRow(row);\n\n\t\t\tif(prevRow){\n\t\t\t\tself.startRow = prevRow;\n\t\t\t\tself._mouseDown(e, prevRow, prevHandle);\n\t\t\t}\n\t\t};\n\n\t\tprevHandle.addEventListener(\"mousedown\",prevHandleDown);\n\t\tprevHandle.addEventListener(\"touchstart\",prevHandleDown, {passive: true});\n\n\t\trowEl.appendChild(handle);\n\t\trowEl.appendChild(prevHandle);\n\t}\n\n\t_mouseDown(e, row, handle){\n\t\tvar self = this;\n\n\t\tself.table.element.classList.add(\"tabulator-block-select\");\n\n\t\tfunction mouseMove(e){\n\t\t\trow.setHeight(self.startHeight + ((typeof e.screenY === \"undefined\" ? e.touches[0].screenY : e.screenY) - self.startY));\n\t\t}\n\n\t\tfunction mouseUp(e){\n\n\t\t\t// //block editor from taking action while resizing is taking place\n\t\t\t// if(self.startColumn.modules.edit){\n\t\t\t// \tself.startColumn.modules.edit.blocked = false;\n\t\t\t// }\n\n\t\t\tdocument.body.removeEventListener(\"mouseup\", mouseMove);\n\t\t\tdocument.body.removeEventListener(\"mousemove\", mouseMove);\n\n\t\t\thandle.removeEventListener(\"touchmove\", mouseMove);\n\t\t\thandle.removeEventListener(\"touchend\", mouseUp);\n\n\t\t\tself.table.element.classList.remove(\"tabulator-block-select\");\n\n\t\t\tself.dispatchExternal(\"rowResized\", row.getComponent());\n\t\t}\n\n\t\te.stopPropagation(); //prevent resize from interfering with movable columns\n\n\t\t//block editor from taking action while resizing is taking place\n\t\t// if(self.startColumn.modules.edit){\n\t\t// \tself.startColumn.modules.edit.blocked = true;\n\t\t// }\n\n\t\tself.startY = typeof e.screenY === \"undefined\" ? e.touches[0].screenY : e.screenY;\n\t\tself.startHeight = row.getHeight();\n\n\t\tdocument.body.addEventListener(\"mousemove\", mouseMove);\n\t\tdocument.body.addEventListener(\"mouseup\", mouseUp);\n\n\t\thandle.addEventListener(\"touchmove\", mouseMove, {passive: true});\n\t\thandle.addEventListener(\"touchend\", mouseUp);\n\t}\n}\n\nResizeRows.moduleName = \"resizeRows\";\n\nclass ResizeTable extends Module{\n\t\n\tconstructor(table){\n\t\tsuper(table);\n\t\t\n\t\tthis.binding = false;\n\t\tthis.visibilityObserver = false;\n\t\tthis.resizeObserver = false;\n\t\tthis.containerObserver = false;\n\t\t\n\t\tthis.tableHeight = 0;\n\t\tthis.tableWidth = 0;\n\t\tthis.containerHeight = 0;\n\t\tthis.containerWidth = 0;\n\t\t\n\t\tthis.autoResize = false;\n\t\t\n\t\tthis.visible = false;\n\t\t\n\t\tthis.initialized = false;\n\t\tthis.initialRedraw = false;\n\t\t\n\t\tthis.registerTableOption(\"autoResize\", true); //auto resize table\n\t}\n\t\n\tinitialize(){\n\t\tif(this.table.options.autoResize){\n\t\t\tvar table = this.table,\n\t\t\ttableStyle;\n\t\t\t\n\t\t\tthis.tableHeight = table.element.clientHeight;\n\t\t\tthis.tableWidth = table.element.clientWidth;\n\t\t\t\n\t\t\tif(table.element.parentNode){\n\t\t\t\tthis.containerHeight = table.element.parentNode.clientHeight;\n\t\t\t\tthis.containerWidth = table.element.parentNode.clientWidth;\n\t\t\t}\n\t\t\t\n\t\t\tif(typeof IntersectionObserver !== \"undefined\" && typeof ResizeObserver !== \"undefined\" && table.rowManager.getRenderMode() === \"virtual\"){\n\t\t\t\t\n\t\t\t\tthis.initializeVisibilityObserver();\n\t\t\t\t\n\t\t\t\tthis.autoResize = true;\n\t\t\t\t\n\t\t\t\tthis.resizeObserver = new ResizeObserver((entry) => {\n\t\t\t\t\tif(!table.browserMobile || (table.browserMobile && (!table.modules.edit || (table.modules.edit && !table.modules.edit.currentCell)))){\n\t\t\t\t\t\t\n\t\t\t\t\t\tvar nodeHeight = Math.floor(entry[0].contentRect.height);\n\t\t\t\t\t\tvar nodeWidth = Math.floor(entry[0].contentRect.width);\n\t\t\t\t\t\t\n\t\t\t\t\t\tif(this.tableHeight != nodeHeight || this.tableWidth != nodeWidth){\n\t\t\t\t\t\t\tthis.tableHeight = nodeHeight;\n\t\t\t\t\t\t\tthis.tableWidth = nodeWidth;\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\tif(table.element.parentNode){\n\t\t\t\t\t\t\t\tthis.containerHeight = table.element.parentNode.clientHeight;\n\t\t\t\t\t\t\t\tthis.containerWidth = table.element.parentNode.clientWidth;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\tthis.redrawTable();\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t\t\n\t\t\t\tthis.resizeObserver.observe(table.element);\n\t\t\t\t\n\t\t\t\ttableStyle = window.getComputedStyle(table.element);\n\t\t\t\t\n\t\t\t\tif(this.table.element.parentNode && !this.table.rowManager.fixedHeight && (tableStyle.getPropertyValue(\"max-height\") || tableStyle.getPropertyValue(\"min-height\"))){\n\t\t\t\t\t\n\t\t\t\t\tthis.containerObserver = new ResizeObserver((entry) => {\n\t\t\t\t\t\tif(!table.browserMobile || (table.browserMobile && (!table.modules.edit || (table.modules.edit && !table.modules.edit.currentCell)))){\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\tvar nodeHeight = Math.floor(entry[0].contentRect.height);\n\t\t\t\t\t\t\tvar nodeWidth = Math.floor(entry[0].contentRect.width);\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\tif(this.containerHeight != nodeHeight || this.containerWidth != nodeWidth){\n\t\t\t\t\t\t\t\tthis.containerHeight = nodeHeight;\n\t\t\t\t\t\t\t\tthis.containerWidth = nodeWidth;\n\t\t\t\t\t\t\t\tthis.tableHeight = table.element.clientHeight;\n\t\t\t\t\t\t\t\tthis.tableWidth = table.element.clientWidth;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\tthis.redrawTable();\n\t\t\t\t\t\t}\n\t\t\t\t\t});\n\t\t\t\t\t\n\t\t\t\t\tthis.containerObserver.observe(this.table.element.parentNode);\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tthis.subscribe(\"table-resize\", this.tableResized.bind(this));\n\t\t\t\t\n\t\t\t}else {\n\t\t\t\tthis.binding = function(){\n\t\t\t\t\tif(!table.browserMobile || (table.browserMobile && (!table.modules.edit || (table.modules.edit && !table.modules.edit.currentCell)))){\n\t\t\t\t\t\ttable.columnManager.rerenderColumns(true);\n\t\t\t\t\t\ttable.redraw();\n\t\t\t\t\t}\n\t\t\t\t};\n\t\t\t\t\n\t\t\t\twindow.addEventListener(\"resize\", this.binding);\n\t\t\t}\n\t\t\t\n\t\t\tthis.subscribe(\"table-destroy\", this.clearBindings.bind(this));\n\t\t}\n\t}\n\t\n\tinitializeVisibilityObserver(){\n\t\tthis.visibilityObserver = new IntersectionObserver((entries) => {\n\t\t\tthis.visible = entries[0].isIntersecting;\n\t\t\t\n\t\t\tif(!this.initialized){\n\t\t\t\tthis.initialized = true;\n\t\t\t\tthis.initialRedraw = !this.visible;\n\t\t\t}else {\n\t\t\t\tif(this.visible){\n\t\t\t\t\tthis.redrawTable(this.initialRedraw);\n\t\t\t\t\tthis.initialRedraw = false;\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\t\t\n\t\tthis.visibilityObserver.observe(this.table.element);\n\t}\n\t\n\tredrawTable(force){\n\t\tif(this.initialized && this.visible){\n\t\t\tthis.table.columnManager.rerenderColumns(true);\n\t\t\tthis.table.redraw(force);\n\t\t}\n\t}\n\t\n\ttableResized(){\n\t\tthis.table.rowManager.redraw();\n\t}\n\t\n\tclearBindings(){\n\t\tif(this.binding){\n\t\t\twindow.removeEventListener(\"resize\", this.binding);\n\t\t}\n\t\t\n\t\tif(this.resizeObserver){\n\t\t\tthis.resizeObserver.unobserve(this.table.element);\n\t\t}\n\t\t\n\t\tif(this.visibilityObserver){\n\t\t\tthis.visibilityObserver.unobserve(this.table.element);\n\t\t}\n\t\t\n\t\tif(this.containerObserver){\n\t\t\tthis.containerObserver.unobserve(this.table.element.parentNode);\n\t\t}\n\t}\n}\n\nResizeTable.moduleName = \"resizeTable\";\n\nclass ResponsiveLayout extends Module{\n\n\tconstructor(table){\n\t\tsuper(table);\n\n\t\tthis.columns = [];\n\t\tthis.hiddenColumns = [];\n\t\tthis.mode = \"\";\n\t\tthis.index = 0;\n\t\tthis.collapseFormatter = [];\n\t\tthis.collapseStartOpen = true;\n\t\tthis.collapseHandleColumn = false;\n\n\t\tthis.registerTableOption(\"responsiveLayout\", false); //responsive layout flags\n\t\tthis.registerTableOption(\"responsiveLayoutCollapseStartOpen\", true); //start showing collapsed data\n\t\tthis.registerTableOption(\"responsiveLayoutCollapseUseFormatters\", true); //responsive layout collapse formatter\n\t\tthis.registerTableOption(\"responsiveLayoutCollapseFormatter\", false); //responsive layout collapse formatter\n\n\t\tthis.registerColumnOption(\"responsive\");\n\t}\n\n\t//generate responsive columns list\n\tinitialize(){\n\t\tif(this.table.options.responsiveLayout){\n\t\t\tthis.subscribe(\"column-layout\", this.initializeColumn.bind(this));\n\t\t\tthis.subscribe(\"column-show\", this.updateColumnVisibility.bind(this));\n\t\t\tthis.subscribe(\"column-hide\", this.updateColumnVisibility.bind(this));\n\t\t\tthis.subscribe(\"columns-loaded\", this.initializeResponsivity.bind(this));\n\t\t\tthis.subscribe(\"column-moved\", this.initializeResponsivity.bind(this));\n\t\t\tthis.subscribe(\"column-add\", this.initializeResponsivity.bind(this));\n\t\t\tthis.subscribe(\"column-delete\", this.initializeResponsivity.bind(this));\n\n\t\t\tthis.subscribe(\"table-redrawing\", this.tableRedraw.bind(this));\n\t\t\t\n\t\t\tif(this.table.options.responsiveLayout === \"collapse\"){\n\t\t\t\tthis.subscribe(\"row-data-changed\", this.generateCollapsedRowContent.bind(this));\n\t\t\t\tthis.subscribe(\"row-init\", this.initializeRow.bind(this));\n\t\t\t\tthis.subscribe(\"row-layout\", this.layoutRow.bind(this));\n\t\t\t}\n\t\t}\n\t}\n\n\ttableRedraw(force){\n\t\tif([\"fitColumns\", \"fitDataStretch\"].indexOf(this.layoutMode()) === -1){\n\t\t\tif(!force){\n\t\t\t\tthis.update();\n\t\t\t}\n\t\t}\n\t}\n\n\tinitializeResponsivity(){\n\t\tvar columns = [];\n\n\t\tthis.mode = this.table.options.responsiveLayout;\n\t\tthis.collapseFormatter = this.table.options.responsiveLayoutCollapseFormatter || this.formatCollapsedData;\n\t\tthis.collapseStartOpen = this.table.options.responsiveLayoutCollapseStartOpen;\n\t\tthis.hiddenColumns = [];\n\n\t\t//determine level of responsivity for each column\n\t\tthis.table.columnManager.columnsByIndex.forEach((column, i) => {\n\t\t\tif(column.modules.responsive){\n\t\t\t\tif(column.modules.responsive.order && column.modules.responsive.visible){\n\t\t\t\t\tcolumn.modules.responsive.index = i;\n\t\t\t\t\tcolumns.push(column);\n\n\t\t\t\t\tif(!column.visible && this.mode === \"collapse\"){\n\t\t\t\t\t\tthis.hiddenColumns.push(column);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\n\t\t//sort list by responsivity\n\t\tcolumns = columns.reverse();\n\t\tcolumns = columns.sort((a, b) => {\n\t\t\tvar diff = b.modules.responsive.order - a.modules.responsive.order;\n\t\t\treturn diff || (b.modules.responsive.index - a.modules.responsive.index);\n\t\t});\n\n\t\tthis.columns = columns;\n\n\t\tif(this.mode === \"collapse\"){\n\t\t\tthis.generateCollapsedContent();\n\t\t}\n\n\t\t//assign collapse column\n\t\tfor (let col of this.table.columnManager.columnsByIndex){\n\t\t\tif(col.definition.formatter == \"responsiveCollapse\"){\n\t\t\t\tthis.collapseHandleColumn = col;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\n\t\tif(this.collapseHandleColumn){\n\t\t\tif(this.hiddenColumns.length){\n\t\t\t\tthis.collapseHandleColumn.show();\n\t\t\t}else {\n\t\t\t\tthis.collapseHandleColumn.hide();\n\t\t\t}\n\t\t}\n\t}\n\n\t//define layout information\n\tinitializeColumn(column){\n\t\tvar def = column.getDefinition();\n\n\t\tcolumn.modules.responsive = {order: typeof def.responsive === \"undefined\" ? 1 : def.responsive, visible:def.visible === false ? false : true};\n\t}\n\n\tinitializeRow(row){\n\t\tvar el;\n\n\t\tif(row.type !== \"calc\"){\n\t\t\tel = document.createElement(\"div\");\n\t\t\tel.classList.add(\"tabulator-responsive-collapse\");\n\n\t\t\trow.modules.responsiveLayout = {\n\t\t\t\telement:el,\n\t\t\t\topen:this.collapseStartOpen,\n\t\t\t};\n\n\t\t\tif(!this.collapseStartOpen){\n\t\t\t\tel.style.display = 'none';\n\t\t\t}\n\t\t}\n\t}\n\n\tlayoutRow(row){\n\t\tvar rowEl = row.getElement();\n\n\t\tif(row.modules.responsiveLayout){\n\t\t\trowEl.appendChild(row.modules.responsiveLayout.element);\n\t\t\tthis.generateCollapsedRowContent(row);\n\t\t}\n\t}\n\n\t//update column visibility\n\tupdateColumnVisibility(column, responsiveToggle){\n\t\tif(!responsiveToggle && column.modules.responsive){\n\t\t\tcolumn.modules.responsive.visible = column.visible;\n\t\t\tthis.initializeResponsivity();\n\t\t}\n\t}\n\n\thideColumn(column){\n\t\tvar colCount = this.hiddenColumns.length;\n\n\t\tcolumn.hide(false, true);\n\n\t\tif(this.mode === \"collapse\"){\n\t\t\tthis.hiddenColumns.unshift(column);\n\t\t\tthis.generateCollapsedContent();\n\n\t\t\tif(this.collapseHandleColumn && !colCount){\n\t\t\t\tthis.collapseHandleColumn.show();\n\t\t\t}\n\t\t}\n\t}\n\n\tshowColumn(column){\n\t\tvar index;\n\n\t\tcolumn.show(false, true);\n\t\t//set column width to prevent calculation loops on uninitialized columns\n\t\tcolumn.setWidth(column.getWidth());\n\n\t\tif(this.mode === \"collapse\"){\n\t\t\tindex = this.hiddenColumns.indexOf(column);\n\n\t\t\tif(index > -1){\n\t\t\t\tthis.hiddenColumns.splice(index, 1);\n\t\t\t}\n\n\t\t\tthis.generateCollapsedContent();\n\n\t\t\tif(this.collapseHandleColumn && !this.hiddenColumns.length){\n\t\t\t\tthis.collapseHandleColumn.hide();\n\t\t\t}\n\t\t}\n\t}\n\n\t//redraw columns to fit space\n\tupdate(){\n\t\tvar working = true;\n\n\t\twhile(working){\n\n\t\t\tlet width = this.table.modules.layout.getMode() == \"fitColumns\" ? this.table.columnManager.getFlexBaseWidth() : this.table.columnManager.getWidth();\n\n\t\t\tlet diff = (this.table.options.headerVisible ? this.table.columnManager.element.clientWidth : this.table.element.clientWidth) - width;\n\n\t\t\tif(diff < 0){\n\t\t\t\t//table is too wide\n\t\t\t\tlet column = this.columns[this.index];\n\n\t\t\t\tif(column){\n\t\t\t\t\tthis.hideColumn(column);\n\t\t\t\t\tthis.index ++;\n\t\t\t\t}else {\n\t\t\t\t\tworking = false;\n\t\t\t\t}\n\n\t\t\t}else {\n\n\t\t\t\t//table has spare space\n\t\t\t\tlet column = this.columns[this.index -1];\n\n\t\t\t\tif(column){\n\t\t\t\t\tif(diff > 0){\n\t\t\t\t\t\tif(diff >= column.getWidth()){\n\t\t\t\t\t\t\tthis.showColumn(column);\n\t\t\t\t\t\t\tthis.index --;\n\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\tworking = false;\n\t\t\t\t\t\t}\n\t\t\t\t\t}else {\n\t\t\t\t\t\tworking = false;\n\t\t\t\t\t}\n\t\t\t\t}else {\n\t\t\t\t\tworking = false;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif(!this.table.rowManager.activeRowsCount){\n\t\t\t\tthis.table.rowManager.renderEmptyScroll();\n\t\t\t}\n\t\t}\n\t}\n\n\tgenerateCollapsedContent(){\n\t\tvar rows = this.table.rowManager.getDisplayRows();\n\n\t\trows.forEach((row) => {\n\t\t\tthis.generateCollapsedRowContent(row);\n\t\t});\n\t}\n\n\tgenerateCollapsedRowContent(row){\n\t\tvar el, contents;\n\n\t\tif(row.modules.responsiveLayout){\n\t\t\tel = row.modules.responsiveLayout.element;\n\n\t\t\twhile(el.firstChild) el.removeChild(el.firstChild);\n\n\t\t\tcontents = this.collapseFormatter(this.generateCollapsedRowData(row));\n\t\t\tif(contents){\n\t\t\t\tel.appendChild(contents);\n\t\t\t}\n\t\t}\n\t}\n\n\tgenerateCollapsedRowData(row){\n\t\tvar data = row.getData(),\n\t\toutput = [],\n\t\tmockCellComponent;\n\n\t\tthis.hiddenColumns.forEach((column) => {\n\t\t\tvar value = column.getFieldValue(data);\n\n\t\t\tif(column.definition.title && column.field){\n\t\t\t\tif(column.modules.format && this.table.options.responsiveLayoutCollapseUseFormatters){\n\n\t\t\t\t\tmockCellComponent = {\n\t\t\t\t\t\tvalue:false,\n\t\t\t\t\t\tdata:{},\n\t\t\t\t\t\tgetValue:function(){\n\t\t\t\t\t\t\treturn value;\n\t\t\t\t\t\t},\n\t\t\t\t\t\tgetData:function(){\n\t\t\t\t\t\t\treturn data;\n\t\t\t\t\t\t},\n\t\t\t\t\t\tgetType:function(){\n\t\t\t\t\t\t\treturn \"cell\";\n\t\t\t\t\t\t},\n\t\t\t\t\t\tgetElement:function(){\n\t\t\t\t\t\t\treturn document.createElement(\"div\");\n\t\t\t\t\t\t},\n\t\t\t\t\t\tgetRow:function(){\n\t\t\t\t\t\t\treturn row.getComponent();\n\t\t\t\t\t\t},\n\t\t\t\t\t\tgetColumn:function(){\n\t\t\t\t\t\t\treturn column.getComponent();\n\t\t\t\t\t\t},\n\t\t\t\t\t\tgetTable:() => {\n\t\t\t\t\t\t\treturn this.table;\n\t\t\t\t\t\t},\n\t\t\t\t\t};\n\n\t\t\t\t\tfunction onRendered(callback){\n\t\t\t\t\t\tcallback();\n\t\t\t\t\t}\n\n\t\t\t\t\toutput.push({\n\t\t\t\t\t\tfield: column.field,\n\t\t\t\t\t\ttitle: column.definition.title,\n\t\t\t\t\t\tvalue: column.modules.format.formatter.call(this.table.modules.format, mockCellComponent, column.modules.format.params, onRendered)\n\t\t\t\t\t});\n\t\t\t\t}else {\n\t\t\t\t\toutput.push({\n\t\t\t\t\t\tfield: column.field,\n\t\t\t\t\t\ttitle: column.definition.title,\n\t\t\t\t\t\tvalue: value\n\t\t\t\t\t});\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\n\t\treturn output;\n\t}\n\n\tformatCollapsedData(data){\n\t\tvar list = document.createElement(\"table\");\n\n\t\tdata.forEach(function(item){\n\t\t\tvar row = document.createElement(\"tr\");\n\t\t\tvar titleData = document.createElement(\"td\");\n\t\t\tvar valueData = document.createElement(\"td\");\n\t\t\tvar node_content;\n\n\t\t\tvar titleHighlight = document.createElement(\"strong\");\n\t\t\ttitleData.appendChild(titleHighlight);\n\t\t\tthis.langBind(\"columns|\" + item.field, function(text){\n\t\t\t\ttitleHighlight.innerHTML = text || item.title;\n\t\t\t});\n\n\t\t\tif(item.value instanceof Node){\n\t\t\t\tnode_content = document.createElement(\"div\");\n\t\t\t\tnode_content.appendChild(item.value);\n\t\t\t\tvalueData.appendChild(node_content);\n\t\t\t}else {\n\t\t\t\tvalueData.innerHTML = item.value;\n\t\t\t}\n\n\t\t\trow.appendChild(titleData);\n\t\t\trow.appendChild(valueData);\n\t\t\tlist.appendChild(row);\n\t\t}, this);\n\n\t\treturn Object.keys(data).length ? list : \"\";\n\t}\n}\n\nResponsiveLayout.moduleName = \"responsiveLayout\";\n\nclass SelectRow extends Module{\n\t\n\tconstructor(table){\n\t\tsuper(table);\n\t\t\n\t\tthis.selecting = false; //flag selecting in progress\n\t\tthis.lastClickedRow = false; //last clicked row\n\t\tthis.selectPrev = []; //hold previously selected element for drag drop selection\n\t\tthis.selectedRows = []; //hold selected rows\n\t\tthis.headerCheckboxElement = null; // hold header select element\n\t\t\n\t\tthis.registerTableOption(\"selectableRows\", \"highlight\"); //highlight rows on hover\n\t\tthis.registerTableOption(\"selectableRowsRangeMode\", \"drag\");  //highlight rows on hover\n\t\tthis.registerTableOption(\"selectableRowsRollingSelection\", true); //roll selection once maximum number of selectable rows is reached\n\t\tthis.registerTableOption(\"selectableRowsPersistence\", true); // maintain selection when table view is updated\n\t\tthis.registerTableOption(\"selectableRowsCheck\", function(data, row){return true;}); //check whether row is selectable\n\t\t\n\t\tthis.registerTableFunction(\"selectRow\", this.selectRows.bind(this));\n\t\tthis.registerTableFunction(\"deselectRow\", this.deselectRows.bind(this));\n\t\tthis.registerTableFunction(\"toggleSelectRow\", this.toggleRow.bind(this));\n\t\tthis.registerTableFunction(\"getSelectedRows\", this.getSelectedRows.bind(this));\n\t\tthis.registerTableFunction(\"getSelectedData\", this.getSelectedData.bind(this));\n\t\t\n\t\t//register component functions\n\t\tthis.registerComponentFunction(\"row\", \"select\", this.selectRows.bind(this));\n\t\tthis.registerComponentFunction(\"row\", \"deselect\", this.deselectRows.bind(this));\n\t\tthis.registerComponentFunction(\"row\", \"toggleSelect\", this.toggleRow.bind(this));\n\t\tthis.registerComponentFunction(\"row\", \"isSelected\", this.isRowSelected.bind(this));\n\t}\n\t\n\tinitialize(){\n\n\t\tthis.deprecatedOptionsCheck();\n\n\t\tif(this.table.options.selectableRows === \"highlight\" && this.table.options.selectableRange){\n\t\t\tthis.table.options.selectableRows = false;\n\t\t}\n\n\t\tif(this.table.options.selectableRows !== false){\n\t\t\tthis.subscribe(\"row-init\", this.initializeRow.bind(this));\n\t\t\tthis.subscribe(\"row-deleting\", this.rowDeleted.bind(this));\n\t\t\tthis.subscribe(\"rows-wipe\", this.clearSelectionData.bind(this));\n\t\t\tthis.subscribe(\"rows-retrieve\", this.rowRetrieve.bind(this));\n\t\t\t\n\t\t\tif(this.table.options.selectableRows && !this.table.options.selectableRowsPersistence){\n\t\t\t\tthis.subscribe(\"data-refreshing\", this.deselectRows.bind(this));\n\t\t\t}\n\t\t}\n\t}\n\n\tdeprecatedOptionsCheck(){\n\t\tthis.deprecationCheck(\"selectable\", \"selectableRows\", true);\n\t\tthis.deprecationCheck(\"selectableRollingSelection\", \"selectableRowsRollingSelection\", true);\n\t\tthis.deprecationCheck(\"selectableRangeMode\", \"selectableRowsRangeMode\", true);\n\t\tthis.deprecationCheck(\"selectablePersistence\", \"selectableRowsPersistence\", true);\n\t\tthis.deprecationCheck(\"selectableCheck\", \"selectableRowsCheck\", true);\n\t}\n\t\n\trowRetrieve(type, prevValue){\n\t\treturn type === \"selected\" ? this.selectedRows : prevValue;\n\t}\n\t\n\trowDeleted(row){\n\t\tthis._deselectRow(row, true);\n\t}\n\t\n\tclearSelectionData(silent){\n\t\tvar prevSelected = this.selectedRows.length;\n\n\t\tthis.selecting = false;\n\t\tthis.lastClickedRow = false;\n\t\tthis.selectPrev = [];\n\t\tthis.selectedRows = [];\n\t\t\n\t\tif(prevSelected && silent !== true){\n\t\t\tthis._rowSelectionChanged();\n\t\t}\n\t}\n\t\n\tinitializeRow(row){\n\t\tvar self = this,\n\t\tselectable = self.checkRowSelectability(row),\n\t\telement = row.getElement();\n\t\t\n\t\t// trigger end of row selection\n\t\tvar endSelect = function(){\n\t\t\t\n\t\t\tsetTimeout(function(){\n\t\t\t\tself.selecting = false;\n\t\t\t}, 50);\n\t\t\t\n\t\t\tdocument.body.removeEventListener(\"mouseup\", endSelect);\n\t\t};\n\t\t\n\t\trow.modules.select = {selected:false};\n\n\t\telement.classList.toggle(\"tabulator-selectable\", selectable);\n\t\telement.classList.toggle(\"tabulator-unselectable\", !selectable);\n\t\t\n\t\t//set row selection class\n\t\tif(self.checkRowSelectability(row)){\t\t\t\n\t\t\tif(self.table.options.selectableRows && self.table.options.selectableRows != \"highlight\"){\n\t\t\t\tif(self.table.options.selectableRowsRangeMode === \"click\"){\n\t\t\t\t\telement.addEventListener(\"click\", this.handleComplexRowClick.bind(this, row));\n\t\t\t\t}else {\n\t\t\t\t\telement.addEventListener(\"click\", function(e){\n\t\t\t\t\t\tif(!self.table.modExists(\"edit\") || !self.table.modules.edit.getCurrentCell()){\n\t\t\t\t\t\t\tself.table._clearSelection();\n\t\t\t\t\t\t}\n\t\t\t\t\t\t\n\t\t\t\t\t\tif(!self.selecting){\n\t\t\t\t\t\t\tself.toggleRow(row);\n\t\t\t\t\t\t}\n\t\t\t\t\t});\n\t\t\t\t\t\n\t\t\t\t\telement.addEventListener(\"mousedown\", function(e){\n\t\t\t\t\t\tif(e.shiftKey){\n\t\t\t\t\t\t\tself.table._clearSelection();\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\tself.selecting = true;\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\tself.selectPrev = [];\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\tdocument.body.addEventListener(\"mouseup\", endSelect);\n\t\t\t\t\t\t\tdocument.body.addEventListener(\"keyup\", endSelect);\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\tself.toggleRow(row);\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\treturn false;\n\t\t\t\t\t\t}\n\t\t\t\t\t});\n\t\t\t\t\t\n\t\t\t\t\telement.addEventListener(\"mouseenter\", function(e){\n\t\t\t\t\t\tif(self.selecting){\n\t\t\t\t\t\t\tself.table._clearSelection();\n\t\t\t\t\t\t\tself.toggleRow(row);\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\tif(self.selectPrev[1] == row){\n\t\t\t\t\t\t\t\tself.toggleRow(self.selectPrev[0]);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t});\n\t\t\t\t\t\n\t\t\t\t\telement.addEventListener(\"mouseout\", function(e){\n\t\t\t\t\t\tif(self.selecting){\n\t\t\t\t\t\t\tself.table._clearSelection();\n\t\t\t\t\t\t\tself.selectPrev.unshift(row);\n\t\t\t\t\t\t}\n\t\t\t\t\t});\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t\n\thandleComplexRowClick(row, e){\n\t\tif(e.shiftKey){\n\t\t\tthis.table._clearSelection();\n\t\t\tthis.lastClickedRow = this.lastClickedRow || row;\n\t\t\t\n\t\t\tvar lastClickedRowIdx = this.table.rowManager.getDisplayRowIndex(this.lastClickedRow);\n\t\t\tvar rowIdx = this.table.rowManager.getDisplayRowIndex(row);\n\t\t\t\n\t\t\tvar fromRowIdx = lastClickedRowIdx <= rowIdx ? lastClickedRowIdx : rowIdx;\n\t\t\tvar toRowIdx = lastClickedRowIdx >= rowIdx ? lastClickedRowIdx : rowIdx;\n\t\t\t\n\t\t\tvar rows = this.table.rowManager.getDisplayRows().slice(0);\n\t\t\tvar toggledRows = rows.splice(fromRowIdx, toRowIdx - fromRowIdx + 1);\n\t\t\t\n\t\t\tif(e.ctrlKey || e.metaKey){\n\t\t\t\ttoggledRows.forEach((toggledRow)=>{\n\t\t\t\t\tif(toggledRow !== this.lastClickedRow){\n\t\t\t\t\t\t\n\t\t\t\t\t\tif(this.table.options.selectableRows !== true && !this.isRowSelected(row)){\n\t\t\t\t\t\t\tif(this.selectedRows.length < this.table.options.selectableRows){\n\t\t\t\t\t\t\t\tthis.toggleRow(toggledRow);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\tthis.toggleRow(toggledRow);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t\tthis.lastClickedRow = row;\n\t\t\t}else {\n\t\t\t\tthis.deselectRows(undefined, true);\n\t\t\t\t\n\t\t\t\tif(this.table.options.selectableRows !== true){\n\t\t\t\t\tif(toggledRows.length > this.table.options.selectableRows){\n\t\t\t\t\t\ttoggledRows = toggledRows.slice(0, this.table.options.selectableRows);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tthis.selectRows(toggledRows);\n\t\t\t}\n\t\t\tthis.table._clearSelection();\n\t\t}\n\t\telse if(e.ctrlKey || e.metaKey){\n\t\t\tthis.toggleRow(row);\n\t\t\tthis.lastClickedRow = row;\n\t\t}else {\n\t\t\tthis.deselectRows(undefined, true);\n\t\t\tthis.selectRows(row);\n\t\t\tthis.lastClickedRow = row;\n\t\t}\n\t}\n\n\tcheckRowSelectability(row){\n\t\tif(row && row.type === \"row\"){\n\t\t\treturn this.table.options.selectableRowsCheck.call(this.table, row.getComponent());\n\t\t}\n\n\t\treturn false;\n\t}\n\t\n\t//toggle row selection\n\ttoggleRow(row){\n\t\tif(this.checkRowSelectability(row)){\n\t\t\tif(row.modules.select && row.modules.select.selected){\n\t\t\t\tthis._deselectRow(row);\n\t\t\t}else {\n\t\t\t\tthis._selectRow(row);\n\t\t\t}\n\t\t}\n\t}\n\t\n\t//select a number of rows\n\tselectRows(rows){\n\t\tvar changes = [], \n\t\trowMatch, change;\n\t\t\n\t\tswitch(typeof rows){\n\t\t\tcase \"undefined\":\n\t\t\t\trowMatch = this.table.rowManager.rows;\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase \"number\":\n\t\t\t\trowMatch = this.table.rowManager.findRow(rows);\n\t\t\t\tbreak;\n\t\t\t\t\n\t\t\tcase \"string\":\n\t\t\t\trowMatch = this.table.rowManager.findRow(rows);\n\t\t\t\n\t\t\t\tif(!rowMatch){\n\t\t\t\t\trowMatch = this.table.rowManager.getRows(rows);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tdefault:\n\t\t\t\trowMatch = rows;\n\t\t\t\tbreak;\n\t\t}\n\n\t\tif(Array.isArray(rowMatch)){\n\t\t\tif(rowMatch.length){\n\t\t\t\trowMatch.forEach((row) => {\n\t\t\t\t\tchange = this._selectRow(row, true, true);\n\n\t\t\t\t\tif(change){\n\t\t\t\t\t\tchanges.push(change);\n\t\t\t\t\t}\n\t\t\t\t});\n\n\t\t\t\tthis._rowSelectionChanged(false, changes);\n\t\t\t}\n\t\t}else {\n\t\t\tif(rowMatch){\n\t\t\t\tthis._selectRow(rowMatch, false, true);\n\t\t\t}\n\t\t}\t\n\t}\n\t\n\t//select an individual row\n\t_selectRow(rowInfo, silent, force){\n\t\t//handle max row count\n\t\tif(!isNaN(this.table.options.selectableRows) && this.table.options.selectableRows !== true && !force){\n\t\t\tif(this.selectedRows.length >= this.table.options.selectableRows){\n\t\t\t\tif(this.table.options.selectableRowsRollingSelection){\n\t\t\t\t\tthis._deselectRow(this.selectedRows[0]);\n\t\t\t\t}else {\n\t\t\t\t\treturn false;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\tvar row = this.table.rowManager.findRow(rowInfo);\n\t\t\n\t\tif(row){\n\t\t\tif(this.selectedRows.indexOf(row) == -1){\n\t\t\t\trow.getElement().classList.add(\"tabulator-selected\");\n\t\t\t\tif(!row.modules.select){\n\t\t\t\t\trow.modules.select = {};\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\trow.modules.select.selected = true;\n\t\t\t\tif(row.modules.select.checkboxEl){\n\t\t\t\t\trow.modules.select.checkboxEl.checked = true;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tthis.selectedRows.push(row);\n\t\t\t\t\n\t\t\t\tif(this.table.options.dataTreeSelectPropagate){\n\t\t\t\t\tthis.childRowSelection(row, true);\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tthis.dispatchExternal(\"rowSelected\", row.getComponent());\n\t\t\t\t\n\t\t\t\tthis._rowSelectionChanged(silent, row);\n\n\t\t\t\treturn row;\n\t\t\t}\n\t\t}else {\n\t\t\tif(!silent){\n\t\t\t\tconsole.warn(\"Selection Error - No such row found, ignoring selection:\" + rowInfo);\n\t\t\t}\n\t\t}\n\t}\n\t\n\tisRowSelected(row){\n\t\treturn this.selectedRows.indexOf(row) !== -1;\n\t}\n\t\n\t//deselect a number of rows\n\tdeselectRows(rows, silent){\n\t\tvar changes = [], \n\t\trowMatch, change;\n\t\t\n\t\tswitch(typeof rows){\n\t\t\tcase \"undefined\":\n\t\t\t\trowMatch = Object.assign([], this.selectedRows);\n\t\t\t\tbreak;\n\n\t\t\tcase \"number\":\n\t\t\t\trowMatch = this.table.rowManager.findRow(rows);\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase \"string\":\n\t\t\t\trowMatch = this.table.rowManager.findRow(rows);\n\t\t\t\n\t\t\t\tif(!rowMatch){\n\t\t\t\t\trowMatch = this.table.rowManager.getRows(rows);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tdefault:\n\t\t\t\trowMatch = rows;\n\t\t\t\tbreak;\n\t\t}\n\n\t\tif(Array.isArray(rowMatch)){\n\t\t\tif(rowMatch.length){\n\t\t\t\trowMatch.forEach((row) => {\n\t\t\t\t\tchange = this._deselectRow(row, true, true);\n\n\t\t\t\t\tif(change){\n\t\t\t\t\t\tchanges.push(change);\n\t\t\t\t\t}\n\t\t\t\t});\n\n\t\t\t\tthis._rowSelectionChanged(silent, [], changes);\n\t\t\t}\n\t\t}else {\n\t\t\tif(rowMatch){\n\t\t\t\tthis._deselectRow(rowMatch, silent, true);\n\t\t\t}\n\t\t}\t\n\t}\n\t\n\t//deselect an individual row\n\t_deselectRow(rowInfo, silent){\n\t\tvar self = this,\n\t\trow = self.table.rowManager.findRow(rowInfo),\n\t\tindex, element;\n\t\t\n\t\tif(row){\n\t\t\tindex = self.selectedRows.findIndex(function(selectedRow){\n\t\t\t\treturn selectedRow == row;\n\t\t\t});\n\t\t\t\n\t\t\tif(index > -1){\n\n\t\t\t\telement = row.getElement();\n\t\t\t\t\n\t\t\t\tif(element){\n\t\t\t\t\telement.classList.remove(\"tabulator-selected\");\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tif(!row.modules.select){\n\t\t\t\t\trow.modules.select = {};\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\trow.modules.select.selected = false;\n\t\t\t\tif(row.modules.select.checkboxEl){\n\t\t\t\t\trow.modules.select.checkboxEl.checked = false;\n\t\t\t\t}\n\t\t\t\tself.selectedRows.splice(index, 1);\n\t\t\t\t\n\t\t\t\tif(this.table.options.dataTreeSelectPropagate){\n\t\t\t\t\tthis.childRowSelection(row, false);\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tthis.dispatchExternal(\"rowDeselected\", row.getComponent());\n\t\t\t\t\n\t\t\t\tself._rowSelectionChanged(silent, undefined, row);\n\n\t\t\t\treturn row;\n\t\t\t}\n\t\t}else {\n\t\t\tif(!silent){\n\t\t\t\tconsole.warn(\"Deselection Error - No such row found, ignoring selection:\" + rowInfo);\n\t\t\t}\n\t\t}\n\t}\n\t\n\tgetSelectedData(){\n\t\tvar data = [];\n\t\t\n\t\tthis.selectedRows.forEach(function(row){\n\t\t\tdata.push(row.getData());\n\t\t});\n\t\t\n\t\treturn data;\n\t}\n\t\n\tgetSelectedRows(){\n\t\tvar rows = [];\n\t\t\n\t\tthis.selectedRows.forEach(function(row){\n\t\t\trows.push(row.getComponent());\n\t\t});\n\t\t\n\t\treturn rows;\n\t}\n\t\n\t_rowSelectionChanged(silent, selected = [], deselected = []){\n\t\tif(this.headerCheckboxElement){\n\t\t\tif(this.selectedRows.length === 0){\n\t\t\t\tthis.headerCheckboxElement.checked = false;\n\t\t\t\tthis.headerCheckboxElement.indeterminate = false;\n\t\t\t} else if(this.table.rowManager.rows.length === this.selectedRows.length){\n\t\t\t\tthis.headerCheckboxElement.checked = true;\n\t\t\t\tthis.headerCheckboxElement.indeterminate = false;\n\t\t\t} else {\n\t\t\t\tthis.headerCheckboxElement.indeterminate = true;\n\t\t\t\tthis.headerCheckboxElement.checked = false;\n\t\t\t}\n\t\t}\n\t\t\n\t\tif(!silent){\n\t\t\tif(!Array.isArray(selected)){\n\t\t\t\tselected = [selected];\n\t\t\t}\n\n\t\t\tselected = selected.map(row => row.getComponent());\n\n\t\t\tif(!Array.isArray(deselected)){\n\t\t\t\tdeselected = [deselected];\n\t\t\t}\n\n\t\t\tdeselected = deselected.map(row => row.getComponent());\n\n\t\t\tthis.dispatchExternal(\"rowSelectionChanged\", this.getSelectedData(), this.getSelectedRows(), selected, deselected);\n\t\t}\n\t}\n\t\n\tregisterRowSelectCheckbox (row, element) {\n\t\tif(!row._row.modules.select){\n\t\t\trow._row.modules.select = {};\n\t\t}\n\t\t\n\t\trow._row.modules.select.checkboxEl = element;\n\t}\n\t\n\tregisterHeaderSelectCheckbox (element) {\n\t\tthis.headerCheckboxElement = element;\n\t}\n\t\n\tchildRowSelection(row, select){\n\t\tvar children = this.table.modules.dataTree.getChildren(row, true);\n\t\t\n\t\tif(select){\n\t\t\tfor(let child of children){\n\t\t\t\tthis._selectRow(child, true);\n\t\t\t}\n\t\t}else {\n\t\t\tfor(let child of children){\n\t\t\t\tthis._deselectRow(child, true);\n\t\t\t}\n\t\t}\n\t}\n}\n\nSelectRow.moduleName = \"selectRow\";\n\n//sort numbers\nfunction number$1(a, b, aRow, bRow, column, dir, params){\n\tvar alignEmptyValues = params.alignEmptyValues;\n\tvar decimal = params.decimalSeparator;\n\tvar thousand = params.thousandSeparator;\n\tvar emptyAlign = 0;\n\n\ta = String(a);\n\tb = String(b);\n\n\tif(thousand){\n\t\ta = a.split(thousand).join(\"\");\n\t\tb = b.split(thousand).join(\"\");\n\t}\n\n\tif(decimal){\n\t\ta = a.split(decimal).join(\".\");\n\t\tb = b.split(decimal).join(\".\");\n\t}\n\n\ta = parseFloat(a);\n\tb = parseFloat(b);\n\n\t//handle non numeric values\n\tif(isNaN(a)){\n\t\temptyAlign =  isNaN(b) ? 0 : -1;\n\t}else if(isNaN(b)){\n\t\temptyAlign =  1;\n\t}else {\n\t\t//compare valid values\n\t\treturn a - b;\n\t}\n\n\t//fix empty values in position\n\tif((alignEmptyValues === \"top\" && dir === \"desc\") || (alignEmptyValues === \"bottom\" && dir === \"asc\")){\n\t\temptyAlign *= -1;\n\t}\n\n\treturn emptyAlign;\n}\n\n//sort strings\nfunction string(a, b, aRow, bRow, column, dir, params){\n\tvar alignEmptyValues = params.alignEmptyValues;\n\tvar emptyAlign = 0;\n\tvar locale;\n\n\t//handle empty values\n\tif(!a){\n\t\temptyAlign =  !b ? 0 : -1;\n\t}else if(!b){\n\t\temptyAlign =  1;\n\t}else {\n\t\t//compare valid values\n\t\tswitch(typeof params.locale){\n\t\t\tcase \"boolean\":\n\t\t\t\tif(params.locale){\n\t\t\t\t\tlocale = this.langLocale();\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase \"string\":\n\t\t\t\tlocale = params.locale;\n\t\t\t\tbreak;\n\t\t}\n\n\t\treturn String(a).toLowerCase().localeCompare(String(b).toLowerCase(), locale);\n\t}\n\n\t//fix empty values in position\n\tif((alignEmptyValues === \"top\" && dir === \"desc\") || (alignEmptyValues === \"bottom\" && dir === \"asc\")){\n\t\temptyAlign *= -1;\n\t}\n\n\treturn emptyAlign;\n}\n\n//sort datetime\nfunction datetime$2(a, b, aRow, bRow, column, dir, params){\n\tvar DT = window.DateTime || luxon.DateTime;\n\tvar format = params.format || \"dd/MM/yyyy HH:mm:ss\",\n\talignEmptyValues = params.alignEmptyValues,\n\temptyAlign = 0;\n\n\tif(typeof DT != \"undefined\"){\n\t\tif(!DT.isDateTime(a)){\n\t\t\tif(format === \"iso\"){\n\t\t\t\ta = DT.fromISO(String(a));\n\t\t\t}else {\n\t\t\t\ta = DT.fromFormat(String(a), format);\n\t\t\t}\n\t\t}\n\n\t\tif(!DT.isDateTime(b)){\n\t\t\tif(format === \"iso\"){\n\t\t\t\tb = DT.fromISO(String(b));\n\t\t\t}else {\n\t\t\t\tb = DT.fromFormat(String(b), format);\n\t\t\t}\n\t\t}\n\n\t\tif(!a.isValid){\n\t\t\temptyAlign = !b.isValid ? 0 : -1;\n\t\t}else if(!b.isValid){\n\t\t\temptyAlign =  1;\n\t\t}else {\n\t\t\t//compare valid values\n\t\t\treturn a - b;\n\t\t}\n\n\t\t//fix empty values in position\n\t\tif((alignEmptyValues === \"top\" && dir === \"desc\") || (alignEmptyValues === \"bottom\" && dir === \"asc\")){\n\t\t\temptyAlign *= -1;\n\t\t}\n\n\t\treturn emptyAlign;\n\n\t}else {\n\t\tconsole.error(\"Sort Error - 'datetime' sorter is dependant on luxon.js\");\n\t}\n}\n\n//sort date\nfunction date$1(a, b, aRow, bRow, column, dir, params){\n\tif(!params.format){\n\t\tparams.format = \"dd/MM/yyyy\";\n\t}\n\n\treturn datetime$2.call(this, a, b, aRow, bRow, column, dir, params);\n}\n\n//sort times\nfunction time$1(a, b, aRow, bRow, column, dir, params){\n\tif(!params.format){\n\t\tparams.format = \"HH:mm\";\n\t}\n\n\treturn datetime$2.call(this, a, b, aRow, bRow, column, dir, params);\n}\n\n//sort booleans\nfunction boolean(a, b, aRow, bRow, column, dir, params){\n\tvar el1 = a === true || a === \"true\" || a === \"True\" || a === 1 ? 1 : 0;\n\tvar el2 = b === true || b === \"true\" || b === \"True\" || b === 1 ? 1 : 0;\n\n\treturn el1 - el2;\n}\n\n//sort if element contains any data\nfunction array(a, b, aRow, bRow, column, dir, params){\n\tvar type = params.type || \"length\",\n\talignEmptyValues = params.alignEmptyValues,\n\temptyAlign = 0;\n\n\tfunction calc(value){\n\t\tvar result;\n\n\t\tswitch(type){\n\t\t\tcase \"length\":\n\t\t\t\tresult = value.length;\n\t\t\t\tbreak;\n\n\t\t\tcase \"sum\":\n\t\t\t\tresult = value.reduce(function(c, d){\n\t\t\t\t\treturn c + d;\n\t\t\t\t});\n\t\t\t\tbreak;\n\n\t\t\tcase \"max\":\n\t\t\t\tresult = Math.max.apply(null, value) ;\n\t\t\t\tbreak;\n\n\t\t\tcase \"min\":\n\t\t\t\tresult = Math.min.apply(null, value) ;\n\t\t\t\tbreak;\n\n\t\t\tcase \"avg\":\n\t\t\t\tresult = value.reduce(function(c, d){\n\t\t\t\t\treturn c + d;\n\t\t\t\t}) / value.length;\n\t\t\t\tbreak;\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t//handle non array values\n\tif(!Array.isArray(a)){\n\t\temptyAlign = !Array.isArray(b) ? 0 : -1;\n\t}else if(!Array.isArray(b)){\n\t\temptyAlign = 1;\n\t}else {\n\t\treturn calc(b) - calc(a);\n\t}\n\n\t//fix empty values in position\n\tif((alignEmptyValues === \"top\" && dir === \"desc\") || (alignEmptyValues === \"bottom\" && dir === \"asc\")){\n\t\temptyAlign *= -1;\n\t}\n\n\treturn emptyAlign;\n}\n\n//sort if element contains any data\nfunction exists(a, b, aRow, bRow, column, dir, params){\n\tvar el1 = typeof a == \"undefined\" ? 0 : 1;\n\tvar el2 = typeof b == \"undefined\" ? 0 : 1;\n\n\treturn el1 - el2;\n}\n\n//sort alpha numeric strings\nfunction alphanum(as, bs, aRow, bRow, column, dir, params){\n\tvar a, b, a1, b1, i= 0, L, rx = /(\\d+)|(\\D+)/g, rd = /\\d/;\n\tvar alignEmptyValues = params.alignEmptyValues;\n\tvar emptyAlign = 0;\n\n\t//handle empty values\n\tif(!as && as!== 0){\n\t\temptyAlign =  !bs && bs!== 0 ? 0 : -1;\n\t}else if(!bs && bs!== 0){\n\t\temptyAlign =  1;\n\t}else {\n\n\t\tif(isFinite(as) && isFinite(bs)) return as - bs;\n\t\ta = String(as).toLowerCase();\n\t\tb = String(bs).toLowerCase();\n\t\tif(a === b) return 0;\n\t\tif(!(rd.test(a) && rd.test(b))) return a > b ? 1 : -1;\n\t\ta = a.match(rx);\n\t\tb = b.match(rx);\n\t\tL = a.length > b.length ? b.length : a.length;\n\t\twhile(i < L){\n\t\t\ta1= a[i];\n\t\t\tb1= b[i++];\n\t\t\tif(a1 !== b1){\n\t\t\t\tif(isFinite(a1) && isFinite(b1)){\n\t\t\t\t\tif(a1.charAt(0) === \"0\") a1 = \".\" + a1;\n\t\t\t\t\tif(b1.charAt(0) === \"0\") b1 = \".\" + b1;\n\t\t\t\t\treturn a1 - b1;\n\t\t\t\t}\n\t\t\t\telse return a1 > b1 ? 1 : -1;\n\t\t\t}\n\t\t}\n\n\t\treturn a.length > b.length;\n\t}\n\n\t//fix empty values in position\n\tif((alignEmptyValues === \"top\" && dir === \"desc\") || (alignEmptyValues === \"bottom\" && dir === \"asc\")){\n\t\temptyAlign *= -1;\n\t}\n\n\treturn emptyAlign;\n}\n\nvar defaultSorters = {\n\tnumber:number$1,\n\tstring:string,\n\tdate:date$1,\n\ttime:time$1,\n\tdatetime:datetime$2,\n\tboolean:boolean,\n\tarray:array,\n\texists:exists,\n\talphanum:alphanum\n};\n\nclass Sort extends Module{\n\t\n\tconstructor(table){\n\t\tsuper(table);\n\t\t\n\t\tthis.sortList = []; //holder current sort\n\t\tthis.changed = false; //has the sort changed since last render\n\t\t\n\t\tthis.registerTableOption(\"sortMode\", \"local\"); //local or remote sorting\n\t\t\n\t\tthis.registerTableOption(\"initialSort\", false); //initial sorting criteria\n\t\tthis.registerTableOption(\"columnHeaderSortMulti\", true); //multiple or single column sorting\n\t\tthis.registerTableOption(\"sortOrderReverse\", false); //reverse internal sort ordering\n\t\tthis.registerTableOption(\"headerSortElement\", \"<div class='tabulator-arrow'></div>\"); //header sort element\n\t\tthis.registerTableOption(\"headerSortClickElement\", \"header\"); //element which triggers sort when clicked\n\t\t\n\t\tthis.registerColumnOption(\"sorter\");\n\t\tthis.registerColumnOption(\"sorterParams\");\n\t\t\n\t\tthis.registerColumnOption(\"headerSort\", true);\n\t\tthis.registerColumnOption(\"headerSortStartingDir\");\n\t\tthis.registerColumnOption(\"headerSortTristate\");\n\t\t\n\t}\n\t\n\tinitialize(){\n\t\tthis.subscribe(\"column-layout\", this.initializeColumn.bind(this));\n\t\tthis.subscribe(\"table-built\", this.tableBuilt.bind(this));\n\t\tthis.registerDataHandler(this.sort.bind(this), 20);\n\t\t\n\t\tthis.registerTableFunction(\"setSort\", this.userSetSort.bind(this));\n\t\tthis.registerTableFunction(\"getSorters\", this.getSort.bind(this));\n\t\tthis.registerTableFunction(\"clearSort\", this.clearSort.bind(this));\n\t\t\n\t\tif(this.table.options.sortMode === \"remote\"){\n\t\t\tthis.subscribe(\"data-params\", this.remoteSortParams.bind(this));\n\t\t}\n\t}\n\t\n\ttableBuilt(){\n\t\tif(this.table.options.initialSort){\n\t\t\tthis.setSort(this.table.options.initialSort);\n\t\t}\n\t}\n\t\n\tremoteSortParams(data, config, silent, params){\n\t\tvar sorters = this.getSort();\n\t\t\n\t\tsorters.forEach((item) => {\n\t\t\tdelete item.column;\n\t\t});\n\t\t\n\t\tparams.sort = sorters;\n\t\t\n\t\treturn params;\n\t}\n\t\n\t\n\t///////////////////////////////////\n\t///////// Table Functions /////////\n\t///////////////////////////////////\n\t\n\tuserSetSort(sortList, dir){\n\t\tthis.setSort(sortList, dir);\n\t\t// this.table.rowManager.sorterRefresh();\n\t\tthis.refreshSort();\n\t}\n\t\n\tclearSort(){\n\t\tthis.clear();\n\t\t// this.table.rowManager.sorterRefresh();\n\t\tthis.refreshSort();\n\t}\n\t\n\t\n\t///////////////////////////////////\n\t///////// Internal Logic //////////\n\t///////////////////////////////////\n\t\n\t//initialize column header for sorting\n\tinitializeColumn(column){\n\t\tvar sorter = false,\n\t\tcolEl,\n\t\tarrowEl;\n\t\t\n\t\tswitch(typeof column.definition.sorter){\n\t\t\tcase \"string\":\n\t\t\t\tif(Sort.sorters[column.definition.sorter]){\n\t\t\t\t\tsorter = Sort.sorters[column.definition.sorter];\n\t\t\t\t}else {\n\t\t\t\t\tconsole.warn(\"Sort Error - No such sorter found: \", column.definition.sorter);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase \"function\":\n\t\t\t\tsorter = column.definition.sorter;\n\t\t\t\tbreak;\n\t\t}\n\t\t\n\t\tcolumn.modules.sort = {\n\t\t\tsorter:sorter, dir:\"none\",\n\t\t\tparams:column.definition.sorterParams || {},\n\t\t\tstartingDir:column.definition.headerSortStartingDir || \"asc\",\n\t\t\ttristate: column.definition.headerSortTristate,\n\t\t};\n\t\t\n\t\tif(column.definition.headerSort !== false){\n\t\t\t\n\t\t\tcolEl = column.getElement();\n\t\t\t\n\t\t\tcolEl.classList.add(\"tabulator-sortable\");\n\t\t\t\n\t\t\tarrowEl = document.createElement(\"div\");\n\t\t\tarrowEl.classList.add(\"tabulator-col-sorter\");\n\t\t\t\n\t\t\tswitch(this.table.options.headerSortClickElement){\n\t\t\t\tcase \"icon\":\n\t\t\t\t\tarrowEl.classList.add(\"tabulator-col-sorter-element\");\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"header\":\n\t\t\t\t\tcolEl.classList.add(\"tabulator-col-sorter-element\");\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tcolEl.classList.add(\"tabulator-col-sorter-element\");\n\t\t\t\t\tbreak;\n\t\t\t}\n\t\t\t\n\t\t\tswitch(this.table.options.headerSortElement){\n\t\t\t\tcase \"function\":\n\t\t\t\t//do nothing\n\t\t\t\t\tbreak;\n\t\t\t\t\n\t\t\t\tcase \"object\":\n\t\t\t\t\tarrowEl.appendChild(this.table.options.headerSortElement);\n\t\t\t\t\tbreak;\n\t\t\t\t\n\t\t\t\tdefault:\n\t\t\t\t\tarrowEl.innerHTML = this.table.options.headerSortElement;\n\t\t\t}\n\t\t\t\n\t\t\t//create sorter arrow\n\t\t\tcolumn.titleHolderElement.appendChild(arrowEl);\n\t\t\t\n\t\t\tcolumn.modules.sort.element = arrowEl;\n\t\t\t\n\t\t\tthis.setColumnHeaderSortIcon(column, \"none\");\n\t\t\t\n\t\t\tif(this.table.options.headerSortClickElement === \"icon\"){\n\t\t\t\tarrowEl.addEventListener(\"mousedown\", (e) => {\n\t\t\t\t\te.stopPropagation();\n\t\t\t\t});\n\t\t\t}\n\t\t\t\n\t\t\t//sort on click\n\t\t\t(this.table.options.headerSortClickElement === \"icon\" ? arrowEl : colEl).addEventListener(\"click\", (e) => {\n\t\t\t\tvar dir = \"\",\n\t\t\t\tsorters=[],\n\t\t\t\tmatch = false;\n\t\t\t\t\n\t\t\t\tif(column.modules.sort){\n\t\t\t\t\tif(column.modules.sort.tristate){\n\t\t\t\t\t\tif(column.modules.sort.dir == \"none\"){\n\t\t\t\t\t\t\tdir = column.modules.sort.startingDir;\n\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\tif(column.modules.sort.dir == column.modules.sort.startingDir){\n\t\t\t\t\t\t\t\tdir = column.modules.sort.dir == \"asc\" ? \"desc\" : \"asc\";\n\t\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\t\tdir = \"none\";\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}else {\n\t\t\t\t\t\tswitch(column.modules.sort.dir){\n\t\t\t\t\t\t\tcase \"asc\":\n\t\t\t\t\t\t\t\tdir = \"desc\";\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\tcase \"desc\":\n\t\t\t\t\t\t\t\tdir = \"asc\";\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\t\tdir = column.modules.sort.startingDir;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\tif (this.table.options.columnHeaderSortMulti && (e.shiftKey || e.ctrlKey)) {\n\t\t\t\t\t\tsorters = this.getSort();\n\t\t\t\t\t\t\n\t\t\t\t\t\tmatch = sorters.findIndex((sorter) => {\n\t\t\t\t\t\t\treturn sorter.field === column.getField();\n\t\t\t\t\t\t});\n\t\t\t\t\t\t\n\t\t\t\t\t\tif(match > -1){\n\t\t\t\t\t\t\tsorters[match].dir = dir;\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\tmatch = sorters.splice(match, 1)[0];\n\t\t\t\t\t\t\tif(dir != \"none\"){\n\t\t\t\t\t\t\t\tsorters.push(match);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\tif(dir != \"none\"){\n\t\t\t\t\t\t\t\tsorters.push({column:column, dir:dir});\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t\t\n\t\t\t\t\t\t//add to existing sort\n\t\t\t\t\t\tthis.setSort(sorters);\n\t\t\t\t\t}else {\n\t\t\t\t\t\tif(dir == \"none\"){\n\t\t\t\t\t\t\tthis.clear();\n\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\t//sort by column only\n\t\t\t\t\t\t\tthis.setSort(column, dir);\n\t\t\t\t\t\t}\n\t\t\t\t\t\t\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\t// this.table.rowManager.sorterRefresh(!this.sortList.length);\n\t\t\t\t\tthis.refreshSort();\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\t}\n\t\n\trefreshSort(){\n\t\tif(this.table.options.sortMode === \"remote\"){\n\t\t\tthis.reloadData(null, false, false);\n\t\t}else {\n\t\t\tthis.refreshData(true);\n\t\t}\n\t\t\n\t\t//TODO - Persist left position of row manager\n\t\t// left = this.scrollLeft;\n\t\t// this.scrollHorizontal(left);\n\t}\n\t\n\t//check if the sorters have changed since last use\n\thasChanged(){\n\t\tvar changed = this.changed;\n\t\tthis.changed = false;\n\t\treturn changed;\n\t}\n\t\n\t//return current sorters\n\tgetSort(){\n\t\tvar self = this,\n\t\tsorters = [];\n\t\t\n\t\tself.sortList.forEach(function(item){\n\t\t\tif(item.column){\n\t\t\t\tsorters.push({column:item.column.getComponent(), field:item.column.getField(), dir:item.dir});\n\t\t\t}\n\t\t});\n\t\t\n\t\treturn sorters;\n\t}\n\t\n\t//change sort list and trigger sort\n\tsetSort(sortList, dir){\n\t\tvar self = this,\n\t\tnewSortList = [];\n\t\t\n\t\tif(!Array.isArray(sortList)){\n\t\t\tsortList = [{column: sortList, dir:dir}];\n\t\t}\n\t\t\n\t\tsortList.forEach(function(item){\n\t\t\tvar column;\n\t\t\t\n\t\t\tcolumn = self.table.columnManager.findColumn(item.column);\n\t\t\t\n\t\t\tif(column){\n\t\t\t\titem.column = column;\n\t\t\t\tnewSortList.push(item);\n\t\t\t\tself.changed = true;\n\t\t\t}else {\n\t\t\t\tconsole.warn(\"Sort Warning - Sort field does not exist and is being ignored: \", item.column);\n\t\t\t}\n\t\t\t\n\t\t});\n\t\t\n\t\tself.sortList = newSortList;\n\t\t\n\t\tthis.dispatch(\"sort-changed\");\n\t}\n\t\n\t//clear sorters\n\tclear(){\n\t\tthis.setSort([]);\n\t}\n\t\n\t//find appropriate sorter for column\n\tfindSorter(column){\n\t\tvar row = this.table.rowManager.activeRows[0],\n\t\tsorter = \"string\",\n\t\tfield, value;\n\t\t\n\t\tif(row){\n\t\t\trow = row.getData();\n\t\t\tfield = column.getField();\n\t\t\t\n\t\t\tif(field){\n\t\t\t\t\n\t\t\t\tvalue = column.getFieldValue(row);\n\t\t\t\t\n\t\t\t\tswitch(typeof value){\n\t\t\t\t\tcase \"undefined\":\n\t\t\t\t\t\tsorter = \"string\";\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t\n\t\t\t\t\tcase \"boolean\":\n\t\t\t\t\t\tsorter = \"boolean\";\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t\n\t\t\t\t\tdefault:\n\t\t\t\t\t\tif(!isNaN(value) && value !== \"\"){\n\t\t\t\t\t\t\tsorter = \"number\";\n\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\tif(value.match(/((^[0-9]+[a-z]+)|(^[a-z]+[0-9]+))+$/i)){\n\t\t\t\t\t\t\t\tsorter = \"alphanum\";\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn Sort.sorters[sorter];\n\t}\n\t\n\t//work through sort list sorting data\n\tsort(data){\n\t\tvar self = this,\n\t\tsortList = this.table.options.sortOrderReverse ? self.sortList.slice().reverse() : self.sortList,\n\t\tsortListActual = [],\n\t\trowComponents = [];\n\t\t\n\t\tif(this.subscribedExternal(\"dataSorting\")){\n\t\t\tthis.dispatchExternal(\"dataSorting\", self.getSort());\n\t\t}\n\t\t\n\t\tself.clearColumnHeaders();\n\t\t\n\t\tif(this.table.options.sortMode !== \"remote\"){\n\t\t\t\n\t\t\t//build list of valid sorters and trigger column specific callbacks before sort begins\n\t\t\tsortList.forEach(function(item, i){\n\t\t\t\tvar sortObj;\n\t\t\t\t\n\t\t\t\tif(item.column){\n\t\t\t\t\tsortObj = item.column.modules.sort;\n\t\t\t\t\t\n\t\t\t\t\tif(sortObj){\n\t\t\t\t\t\t\n\t\t\t\t\t\t//if no sorter has been defined, take a guess\n\t\t\t\t\t\tif(!sortObj.sorter){\n\t\t\t\t\t\t\tsortObj.sorter = self.findSorter(item.column);\n\t\t\t\t\t\t}\n\t\t\t\t\t\t\n\t\t\t\t\t\titem.params = typeof sortObj.params === \"function\" ? sortObj.params(item.column.getComponent(), item.dir) : sortObj.params;\n\t\t\t\t\t\t\n\t\t\t\t\t\tsortListActual.push(item);\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\tself.setColumnHeader(item.column, item.dir);\n\t\t\t\t}\n\t\t\t});\n\t\t\t\n\t\t\t//sort data\n\t\t\tif (sortListActual.length) {\n\t\t\t\tself._sortItems(data, sortListActual);\n\t\t\t}\n\t\t\t\n\t\t}else {\n\t\t\tsortList.forEach(function(item, i){\n\t\t\t\tself.setColumnHeader(item.column, item.dir);\n\t\t\t});\n\t\t}\n\t\t\n\t\tif(this.subscribedExternal(\"dataSorted\")){\n\t\t\tdata.forEach((row) => {\n\t\t\t\trowComponents.push(row.getComponent());\n\t\t\t});\n\t\t\t\n\t\t\tthis.dispatchExternal(\"dataSorted\", self.getSort(), rowComponents);\n\t\t}\n\t\t\n\t\treturn data;\n\t}\n\t\n\t//clear sort arrows on columns\n\tclearColumnHeaders(){\n\t\tthis.table.columnManager.getRealColumns().forEach((column) => {\n\t\t\tif(column.modules.sort){\n\t\t\t\tcolumn.modules.sort.dir = \"none\";\n\t\t\t\tcolumn.getElement().setAttribute(\"aria-sort\", \"none\");\n\t\t\t\tthis.setColumnHeaderSortIcon(column, \"none\");\n\t\t\t}\n\t\t});\n\t}\n\t\n\t//set the column header sort direction\n\tsetColumnHeader(column, dir){\n\t\tcolumn.modules.sort.dir = dir;\n\t\tcolumn.getElement().setAttribute(\"aria-sort\", dir === \"asc\" ? \"ascending\" : \"descending\");\n\t\tthis.setColumnHeaderSortIcon(column, dir);\n\t}\n\t\n\tsetColumnHeaderSortIcon(column, dir){\n\t\tvar sortEl = column.modules.sort.element,\n\t\tarrowEl;\n\t\t\n\t\tif(column.definition.headerSort && typeof this.table.options.headerSortElement === \"function\"){\n\t\t\twhile(sortEl.firstChild) sortEl.removeChild(sortEl.firstChild);\n\t\t\t\n\t\t\tarrowEl = this.table.options.headerSortElement.call(this.table, column.getComponent(), dir);\n\t\t\t\n\t\t\tif(typeof arrowEl === \"object\"){\n\t\t\t\tsortEl.appendChild(arrowEl);\n\t\t\t}else {\n\t\t\t\tsortEl.innerHTML = arrowEl;\n\t\t\t}\n\t\t}\n\t}\n\t\n\t//sort each item in sort list\n\t_sortItems(data, sortList){\n\t\tvar sorterCount = sortList.length - 1;\n\t\t\n\t\tdata.sort((a, b) => {\n\t\t\tvar result;\n\t\t\t\n\t\t\tfor(var i = sorterCount; i>= 0; i--){\n\t\t\t\tlet sortItem = sortList[i];\n\t\t\t\t\n\t\t\t\tresult = this._sortRow(a, b, sortItem.column, sortItem.dir, sortItem.params);\n\t\t\t\t\n\t\t\t\tif(result !== 0){\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\treturn result;\n\t\t});\n\t}\n\t\n\t//process individual rows for a sort function on active data\n\t_sortRow(a, b, column, dir, params){\n\t\tvar el1Comp, el2Comp;\n\t\t\n\t\t//switch elements depending on search direction\n\t\tvar el1 = dir == \"asc\" ? a : b;\n\t\tvar el2 = dir == \"asc\" ? b : a;\n\t\t\n\t\ta = column.getFieldValue(el1.getData());\n\t\tb = column.getFieldValue(el2.getData());\n\t\t\n\t\ta = typeof a !== \"undefined\" ? a : \"\";\n\t\tb = typeof b !== \"undefined\" ? b : \"\";\n\t\t\n\t\tel1Comp = el1.getComponent();\n\t\tel2Comp = el2.getComponent();\n\t\t\n\t\treturn column.modules.sort.sorter.call(this, a, b, el1Comp, el2Comp, column.getComponent(), dir, params);\n\t}\n}\n\nSort.moduleName = \"sort\";\n\n//load defaults\nSort.sorters = defaultSorters;\n\nclass RangeComponent {\n\tconstructor(range) {\n\t\tthis._range = range;\n\n\t\treturn new Proxy(this, {\n\t\t\tget: function (target, name, receiver) {\n\t\t\t\tif (typeof target[name] !== \"undefined\") {\n\t\t\t\t\treturn target[name];\n\t\t\t\t} else {\n\t\t\t\t\treturn target._range.table.componentFunctionBinder.handle(\"range\", target._range, name);\n\t\t\t\t}\n\t\t\t},\n\t\t});\n\t}\n\n\tgetElement() {\n\t\treturn this._range.element;\n\t}\n\n\tgetData() {\n\t\treturn this._range.getData();\n\t}\n\n\tgetCells() {\n\t\treturn this._range.getCells(true);\n\t}\n\n\tgetStructuredCells() {\n\t\treturn this._range.getStructuredCells();\n\t}\n\n\tgetRows() {\n\t\treturn this._range.getRows().map((row) => row.getComponent());\n\t}\n\n\tgetColumns() {\n\t\treturn this._range.getColumns().map((column) => column.getComponent());\n\t}\n\t\n\tgetBounds() {\n\t\treturn this._range.getBounds();\n\t}\n\n\tgetTopEdge() {\n\t\treturn this._range.top;\n\t}\n\n\tgetBottomEdge() {\n\t\treturn this._range.bottom;\n\t}\n\n\tgetLeftEdge() {\n\t\treturn this._range.left;\n\t}\n\n\tgetRightEdge() {\n\t\treturn this._range.right;\n\t}\n\n\tsetBounds(start, end){\n\t\tif(this._range.destroyedGuard(\"setBounds\")){\n\t\t\tthis._range.setBounds(start ? start._cell : start, end ? end._cell : end);\n\t\t}\n\t}\n\n\tsetStartBound(start){\n\t\tif(this._range.destroyedGuard(\"setStartBound\")){\n\t\t\tthis._range.setEndBound(start ? start._cell : start);\n\t\t\tthis._range.rangeManager.layoutElement();\n\t\t}\n\t}\n\n\tsetEndBound(end){\n\t\tif(this._range.destroyedGuard(\"setEndBound\")){\n\t\t\tthis._range.setEndBound(end ? end._cell : end);\n\t\t\tthis._range.rangeManager.layoutElement();\n\t\t}\n\t}\n\n\tclearValues(){\n\t\tif(this._range.destroyedGuard(\"clearValues\")){\n\t\t\tthis._range.clearValues();\n\t\t}\n\t}\n\n\tremove(){\n\t\tif(this._range.destroyedGuard(\"remove\")){\n\t\t\tthis._range.destroy(true);\n\t\t}\n\t}\n}\n\nclass Range extends CoreFeature{\n\tconstructor(table, rangeManager, start, end) {\n\t\tsuper(table);\n\t\t\n\t\tthis.rangeManager = rangeManager;\n\t\tthis.element = null;\n\t\tthis.initialized = false;\n\t\tthis.initializing = {\n\t\t\tstart:false,\n\t\t\tend:false,\n\t\t};\n\t\tthis.destroyed = false;\n\t\t\n\t\tthis.top = 0;\n\t\tthis.bottom = 0;\n\t\tthis.left = 0;\n\t\tthis.right = 0;\n\t\t\n\t\tthis.table = table;\n\t\tthis.start = {row:0, col:0};\n\t\tthis.end = {row:0, col:0};\n\n\t\tif(this.rangeManager.rowHeader){\n\t\t\tthis.left = 1;\n\t\t\tthis.right = 1;\n\t\t\tthis.start.col = 1;\n\t\t\tthis.end.col = 1;\n\t\t}\n\t\t\n\t\tthis.initElement();\n\t\t\n\t\tsetTimeout(() => {\n\t\t\tthis.initBounds(start, end);\n\t\t});\n\t}\n\t\n\tinitElement(){\n\t\tthis.element = document.createElement(\"div\");\n\t\tthis.element.classList.add(\"tabulator-range\");\n\t}\n\t\n\tinitBounds(start, end){\n\t\tthis._updateMinMax();\n\t\t\n\t\tif(start){\n\t\t\tthis.setBounds(start, end || start);\n\t\t}\n\t}\n\t\n\t///////////////////////////////////\n\t///////   Boundary Setup    ///////\n\t///////////////////////////////////\n\t\n\tsetStart(row, col) {\n\t\tif(this.start.row !== row || this.start.col !== col){\n\t\t\tthis.start.row = row;\n\t\t\tthis.start.col = col;\n\t\t\t\n\t\t\tthis.initializing.start = true;\n\t\t\tthis._updateMinMax();\n\t\t}\n\t}\n\t\n\tsetEnd(row, col) {\n\t\tif(this.end.row !== row || this.end.col !== col){\n\t\t\tthis.end.row = row;\n\t\t\tthis.end.col = col;\n\t\t\t\n\t\t\tthis.initializing.end = true;\n\t\t\tthis._updateMinMax();\n\t\t}\n\t}\n\t\n\tsetBounds(start, end, visibleRows){\n\t\tif(start){\n\t\t\tthis.setStartBound(start);\n\t\t}\n\t\t\n\t\tthis.setEndBound(end || start);\n\t\tthis.rangeManager.layoutElement(visibleRows);\n\t}\n\t\n\tsetStartBound(element){\n\t\tvar row, col;\n\t\t\n\t\tif (element.type === \"column\") {\n\t\t\tif(this.rangeManager.columnSelection){\n\t\t\t\tthis.setStart(0, element.getPosition() - 1);\n\t\t\t}\n\t\t}else {\n\t\t\trow = element.row.position - 1;\n\t\t\tcol = element.column.getPosition() - 1;\n\t\t\t\n\t\t\tif (element.column === this.rangeManager.rowHeader) {\n\t\t\t\tthis.setStart(row, 1);\n\t\t\t} else {\n\t\t\t\tthis.setStart(row, col);\n\t\t\t}\n\t\t}\n\t}\n\t\n\tsetEndBound(element){\n\t\tvar rowsCount = this._getTableRows().length,\n\t\trow, col, isRowHeader;\n\t\t\n\t\tif (element.type === \"column\") {\n\t\t\tif(this.rangeManager.columnSelection){\n\t\t\t\tif (this.rangeManager.selecting === \"column\") {\n\t\t\t\t\tthis.setEnd(rowsCount - 1, element.getPosition() - 1);\n\t\t\t\t} else if (this.rangeManager.selecting === \"cell\") {\n\t\t\t\t\tthis.setEnd(0, element.getPosition() - 1);\n\t\t\t\t}\n\t\t\t}\n\t\t}else {\n\t\t\trow = element.row.position - 1;\n\t\t\tcol = element.column.getPosition() - 1;\n\t\t\tisRowHeader = element.column === this.rangeManager.rowHeader;\n\t\t\t\n\t\t\tif (this.rangeManager.selecting === \"row\") {\n\t\t\t\tthis.setEnd(row, this._getTableColumns().length - 1);\n\t\t\t} else if (this.rangeManager.selecting !== \"row\" && isRowHeader) {\n\t\t\t\tthis.setEnd(row, 0);\n\t\t\t} else if (this.rangeManager.selecting === \"column\") {\n\t\t\t\tthis.setEnd(rowsCount - 1, col);\n\t\t\t} else {\n\t\t\t\tthis.setEnd(row, col);\n\t\t\t}\n\t\t}\n\t}\n\t\n\t_updateMinMax() {\n\t\tthis.top = Math.min(this.start.row, this.end.row);\n\t\tthis.bottom = Math.max(this.start.row, this.end.row);\n\t\tthis.left = Math.min(this.start.col, this.end.col);\n\t\tthis.right = Math.max(this.start.col, this.end.col);\n\t\t\n\t\tif(this.initialized){\n\t\t\tthis.dispatchExternal(\"rangeChanged\", this.getComponent());\n\t\t}else {\n\t\t\tif(this.initializing.start && this.initializing.end){\n\t\t\t\tthis.initialized = true;\n\t\t\t\tthis.dispatchExternal(\"rangeAdded\", this.getComponent());\n\t\t\t}\n\t\t}\n\t}\n\t\n\t_getTableColumns() {\n\t\treturn this.table.columnManager.getVisibleColumnsByIndex();\n\t}\n\t\n\t_getTableRows() {\n\t\treturn this.table.rowManager.getDisplayRows();\n\t}\n\t\n\t///////////////////////////////////\n\t///////      Rendering      ///////\n\t///////////////////////////////////\n\t\n\tlayout() {\n\t\tvar _vDomTop = this.table.rowManager.renderer.vDomTop,\n\t\t_vDomBottom = this.table.rowManager.renderer.vDomBottom,\n\t\t_vDomLeft = this.table.columnManager.renderer.leftCol,\n\t\t_vDomRight = this.table.columnManager.renderer.rightCol,\t\t\n\t\ttop, bottom, left, right, topLeftCell, bottomRightCell;\n\t\t\n\t\tif (_vDomTop == null) {\n\t\t\t_vDomTop = 0;\n\t\t}\n\t\t\n\t\tif (_vDomBottom == null) {\n\t\t\t_vDomBottom = Infinity;\n\t\t}\n\t\t\n\t\tif (_vDomLeft == null) {\n\t\t\t_vDomLeft = 0;\n\t\t}\n\t\t\n\t\tif (_vDomRight == null) {\n\t\t\t_vDomRight = Infinity;\n\t\t}\n\t\t\n\t\tif (this.overlaps(_vDomLeft, _vDomTop, _vDomRight, _vDomBottom)) {\n\t\t\ttop = Math.max(this.top, _vDomTop);\n\t\t\tbottom = Math.min(this.bottom, _vDomBottom);\n\t\t\tleft = Math.max(this.left, _vDomLeft);\n\t\t\tright = Math.min(this.right, _vDomRight);\n\t\t\t\n\t\t\ttopLeftCell = this.rangeManager.getCell(top, left);\n\t\t\tbottomRightCell = this.rangeManager.getCell(bottom, right);\n\t\t\t\n\t\t\tthis.element.classList.add(\"tabulator-range-active\");\n\t\t\t// this.element.classList.toggle(\"tabulator-range-active\", this === this.rangeManager.activeRange);\n\t\t\t\n\t\t\tthis.element.style.left = topLeftCell.row.getElement().offsetLeft + topLeftCell.getElement().offsetLeft + \"px\";\n\t\t\tthis.element.style.top = topLeftCell.row.getElement().offsetTop + \"px\";\n\t\t\tthis.element.style.width = bottomRightCell.getElement().offsetLeft + bottomRightCell.getElement().offsetWidth - topLeftCell.getElement().offsetLeft + \"px\";\n\t\t\tthis.element.style.height = bottomRightCell.row.getElement().offsetTop + bottomRightCell.row.getElement().offsetHeight - topLeftCell.row.getElement().offsetTop + \"px\";\n\t\t}\n\t}\n\t\n\tatTopLeft(cell) {\n\t\treturn cell.row.position - 1 === this.top && cell.column.getPosition() - 1 === this.left;\n\t}\n\t\n\tatBottomRight(cell) {\n\t\treturn cell.row.position - 1 === this.bottom && cell.column.getPosition() - 1 === this.right;\n\t}\n\t\n\toccupies(cell) {\n\t\treturn this.occupiesRow(cell.row) && this.occupiesColumn(cell.column);\n\t}\n\t\n\toccupiesRow(row) {\n\t\treturn this.top <= row.position - 1 && row.position - 1 <= this.bottom;\n\t}\n\t\n\toccupiesColumn(col) {\n\t\treturn this.left <= col.getPosition() - 1 && col.getPosition() - 1 <= this.right;\n\t}\n\t\n\toverlaps(left, top, right, bottom) {\n\t\tif ((this.left > right || left > this.right) || (this.top > bottom || top > this.bottom)){\n\t\t\treturn false;\n\t\t}\n\t\t\n\t\treturn true;\n\t}\n\t\n\tgetData() {\n\t\tvar data = [],\n\t\trows = this.getRows(),\n\t\tcolumns = this.getColumns();\n\t\t\n\t\trows.forEach((row) => {\n\t\t\tvar rowData = row.getData(),\n\t\t\tresult = {};\n\t\t\t\n\t\t\tcolumns.forEach((column) => {\n\t\t\t\tresult[column.field] = rowData[column.field];\n\t\t\t});\n\t\t\t\n\t\t\tdata.push(result);\n\t\t});\n\t\t\n\t\treturn data;\n\t}\n\t\n\tgetCells(structured, component) {\n\t\tvar cells = [],\n\t\trows = this.getRows(),\n\t\tcolumns = this.getColumns();\n\t\t\n\t\tif (structured) {\n\t\t\tcells = rows.map((row) => {\n\t\t\t\tvar arr = [];\n\t\t\t\t\n\t\t\t\trow.getCells().forEach((cell) => {\n\t\t\t\t\tif (columns.includes(cell.column)) {\n\t\t\t\t\t\tarr.push(component ? cell.getComponent() : cell);\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t\t\n\t\t\t\treturn arr;\n\t\t\t});\n\t\t} else {\n\t\t\trows.forEach((row) => {\n\t\t\t\trow.getCells().forEach((cell) => {\n\t\t\t\t\tif (columns.includes(cell.column)) {\n\t\t\t\t\t\tcells.push(component ? cell.getComponent() : cell);\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t});\n\t\t}\n\t\t\n\t\treturn cells;\n\t}\n\t\n\tgetStructuredCells() {\n\t\treturn this.getCells(true, true);\n\t}\n\t\n\tgetRows() {\n\t\treturn this._getTableRows().slice(this.top, this.bottom + 1);\n\t}\n\t\n\tgetColumns() {\n\t\treturn this._getTableColumns().slice(this.left, this.right + 1);\n\t}\n\t\n\tclearValues(){\n\t\tvar cells = this.getCells();\n\t\tvar clearValue = this.table.options.selectableRangeClearCellsValue;\n\t\t\n\t\tthis.table.blockRedraw();\n\t\t\n\t\tcells.forEach((cell) => {\n\t\t\tcell.setValue(clearValue);\n\t\t});\n\t\t\n\t\tthis.table.restoreRedraw();\n\t\t\n\t}\n\t\n\tgetBounds(component){\n\t\tvar cells = this.getCells(false, component),\n\t\toutput = {\n\t\t\tstart:null,\n\t\t\tend:null,\n\t\t};\n\t\t\n\t\tif(cells.length){\n\t\t\toutput.start = cells[0];\n\t\t\toutput.end = cells[cells.length - 1];\n\t\t}else {\n\t\t\tconsole.warn(\"No bounds defined on range\");\n\t\t}\n\t\t\n\t\treturn output;\n\t}\n\t\n\tgetComponent() {\n\t\tif (!this.component) {\n\t\t\tthis.component = new RangeComponent(this);\n\t\t}\n\t\treturn this.component;\n\t}\n\t\n\tdestroy(notify) {\n\t\tthis.destroyed = true;\n\t\t\n\t\tthis.element.remove();\n\t\t\n\t\tif(notify){\n\t\t\tthis.rangeManager.rangeRemoved(this);\n\t\t}\n\t\t\n\t\tif(this.initialized){\n\t\t\tthis.dispatchExternal(\"rangeRemoved\", this.getComponent());\n\t\t}\n\t}\n\t\n\tdestroyedGuard(func){\n\t\tif(this.destroyed){\n\t\t\tconsole.warn(\"You cannot call the \"  + func + \" function on a destroyed range\");\n\t\t}\n\t\t\n\t\treturn !this.destroyed;\n\t}\n}\n\nclass SelectRange extends Module {\n\tconstructor(table) {\n\t\tsuper(table);\n\t\t\n\t\tthis.selecting = \"cell\";\n\t\tthis.mousedown = false;\n\t\tthis.ranges = [];\n\t\tthis.overlay = null;\n\t\tthis.rowHeader = null;\n\t\tthis.layoutChangeTimeout = null;\n\t\tthis.columnSelection = false;\n\t\tthis.rowSelection = false;\n\t\tthis.maxRanges = 0;\n\t\tthis.activeRange = false;\n\t\tthis.blockKeydown = false;\n\t\t\n\t\tthis.keyDownEvent = this._handleKeyDown.bind(this);\n\t\tthis.mouseUpEvent = this._handleMouseUp.bind(this);\n\t\t\n\t\tthis.registerTableOption(\"selectableRange\", false); //enable selectable range\n\t\tthis.registerTableOption(\"selectableRangeColumns\", false); //enable selectable range\n\t\tthis.registerTableOption(\"selectableRangeRows\", false); //enable selectable range\n\t\tthis.registerTableOption(\"selectableRangeClearCells\", false); //allow clearing of active range\n\t\tthis.registerTableOption(\"selectableRangeClearCellsValue\", undefined); //value for cleared active range\n\n\t\tthis.registerTableFunction(\"getRangesData\", this.getRangesData.bind(this));\n\t\tthis.registerTableFunction(\"getRanges\", this.getRanges.bind(this));\n\t\tthis.registerTableFunction(\"addRange\", this.addRangeFromComponent.bind(this));\n\n\t\tthis.registerComponentFunction(\"cell\", \"getRanges\", this.cellGetRanges.bind(this));\n\t\tthis.registerComponentFunction(\"row\", \"getRanges\", this.rowGetRanges.bind(this));\n\t\tthis.registerComponentFunction(\"column\", \"getRanges\", this.colGetRanges.bind(this));\n\t}\n\t\n\t///////////////////////////////////\n\t///////    Initialization   ///////\n\t///////////////////////////////////\n\t\n\tinitialize() {\n\t\tif (this.options(\"selectableRange\")) {\t\t\n\t\t\tif(!this.options(\"selectableRows\")){\n\t\t\t\t\n\t\t\t\tthis.maxRanges = this.options(\"selectableRange\");\n\t\t\t\t\n\t\t\t\tthis.initializeTable();\n\t\t\t\tthis.initializeWatchers();\n\t\t\t}else {\n\t\t\t\tconsole.warn(\"SelectRange functionality cannot be used in conjunction with row selection\");\n\t\t\t}\n\t\t}\n\t}\n\t\n\t\n\tinitializeTable() {\t\t\n\t\tthis.overlay = document.createElement(\"div\");\n\t\tthis.overlay.classList.add(\"tabulator-range-overlay\");\n\t\t\n\t\tthis.rangeContainer = document.createElement(\"div\");\n\t\tthis.rangeContainer.classList.add(\"tabulator-range-container\");\n\t\t\n\t\tthis.activeRangeCellElement = document.createElement(\"div\");\n\t\tthis.activeRangeCellElement.classList.add(\"tabulator-range-cell-active\");\n\t\t\n\t\tthis.overlay.appendChild(this.rangeContainer);\n\t\tthis.overlay.appendChild(this.activeRangeCellElement);\n\t\t\n\t\tthis.table.rowManager.element.addEventListener(\"keydown\", this.keyDownEvent);\n\t\t\n\t\tthis.resetRanges();\n\t\t\n\t\tthis.table.rowManager.element.appendChild(this.overlay);\n\t\tthis.table.columnManager.element.setAttribute(\"tabindex\", 0);\n\t\tthis.table.element.classList.add(\"tabulator-ranges\");\n\t}\n\t\n\tinitializeWatchers() {\n\t\tthis.columnSelection = this.options(\"selectableRangeColumns\");\n\t\tthis.rowSelection = this.options(\"selectableRangeRows\");\n\t\t\n\t\tthis.subscribe(\"column-init\", this.initializeColumn.bind(this));\n\t\tthis.subscribe(\"column-mousedown\", this.handleColumnMouseDown.bind(this));\n\t\tthis.subscribe(\"column-mousemove\", this.handleColumnMouseMove.bind(this));\n\t\tthis.subscribe(\"column-resized\", this.handleColumnResized.bind(this));\n\t\tthis.subscribe(\"column-width\", this.layoutChange.bind(this));\n\t\tthis.subscribe(\"column-height\", this.layoutChange.bind(this));\n\t\tthis.subscribe(\"column-resized\", this.layoutChange.bind(this));\n\t\tthis.subscribe(\"columns-loaded\", this.updateHeaderColumn.bind(this));\n\n\t\tthis.subscribe(\"cell-height\", this.layoutChange.bind(this));\n\t\tthis.subscribe(\"cell-rendered\", this.renderCell.bind(this));\n\t\tthis.subscribe(\"cell-mousedown\", this.handleCellMouseDown.bind(this));\n\t\tthis.subscribe(\"cell-mousemove\", this.handleCellMouseMove.bind(this));\n\t\tthis.subscribe(\"cell-click\", this.handleCellClick.bind(this));\n\t\tthis.subscribe(\"cell-editing\", this.handleEditingCell.bind(this));\n\t\t\n\t\tthis.subscribe(\"page-changed\", this.redraw.bind(this));\n\n\t\tthis.subscribe(\"scroll-vertical\", this.layoutChange.bind(this));\n\t\tthis.subscribe(\"scroll-horizontal\", this.layoutChange.bind(this));\n\t\t\n\t\tthis.subscribe(\"data-destroy\", this.tableDestroyed.bind(this));\n\t\tthis.subscribe(\"data-processed\", this.resetRanges.bind(this));\n\t\t\n\t\tthis.subscribe(\"table-layout\", this.layoutElement.bind(this));\n\t\tthis.subscribe(\"table-redraw\", this.redraw.bind(this));\n\t\tthis.subscribe(\"table-destroy\", this.tableDestroyed.bind(this));\n\t\t\n\t\tthis.subscribe(\"edit-editor-clear\", this.finishEditingCell.bind(this));\n\t\tthis.subscribe(\"edit-blur\", this.restoreFocus.bind(this));\n\t\t\n\t\tthis.subscribe(\"keybinding-nav-prev\", this.keyNavigate.bind(this, \"left\"));\n\t\tthis.subscribe(\"keybinding-nav-next\", this.keyNavigate.bind(this, \"right\"));\n\t\tthis.subscribe(\"keybinding-nav-left\", this.keyNavigate.bind(this, \"left\"));\n\t\tthis.subscribe(\"keybinding-nav-right\", this.keyNavigate.bind(this, \"right\"));\n\t\tthis.subscribe(\"keybinding-nav-up\", this.keyNavigate.bind(this, \"up\"));\n\t\tthis.subscribe(\"keybinding-nav-down\", this.keyNavigate.bind(this, \"down\"));\n\t\tthis.subscribe(\"keybinding-nav-range\", this.keyNavigateRange.bind(this));\n\t}\n\t\n\t\n\tinitializeColumn(column) {\n\t\tif(this.columnSelection && column.definition.headerSort && this.options(\"headerSortClickElement\") !== \"icon\"){\n\t\t\tconsole.warn(\"Using column headerSort with selectableRangeColumns option may result in unpredictable behavior. Consider using headerSortClickElement: 'icon'.\");\n\t\t}\n\t\t\n\t\tif (column.modules.edit) ;\n\t}\n\t\n\tupdateHeaderColumn(){\n\t\tif(this.rowSelection){\n\t\t\tthis.rowHeader = this.table.columnManager.getVisibleColumnsByIndex()[0];\n\t\t\t\n\t\t\tif(this.rowHeader){\n\t\t\t\tthis.rowHeader.definition.cssClass = this.rowHeader.definition.cssClass + \" tabulator-range-row-header\";\n\t\t\t\t\n\t\t\t\tif(this.rowHeader.definition.headerSort){\n\t\t\t\t\tconsole.warn(\"Using column headerSort with selectableRangeRows option may result in unpredictable behavior\");\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tif(this.rowHeader.definition.editor){\n\t\t\t\t\tconsole.warn(\"Using column editor with selectableRangeRows option may result in unpredictable behavior\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t\n\t///////////////////////////////////\n\t///////   Table Functions   ///////\n\t///////////////////////////////////\n\t\n\tgetRanges(){\n\t\treturn this.ranges.map((range) => range.getComponent());\n\t}\n\t\n\tgetRangesData() {\n\t\treturn this.ranges.map((range) => range.getData());\n\t}\n\t\n\taddRangeFromComponent(start, end){\n\t\tstart = start ? start._cell : null;\n\t\tend = end ? end._cell : null;\n\t\t\n\t\treturn this.addRange(start, end);\n\t}\n\t\n\t///////////////////////////////////\n\t/////// Component Functions ///////\n\t///////////////////////////////////\n\t\n\tcellGetRanges(cell){\n\t\tvar ranges = [];\n\t\t\n\t\tif (cell.column === this.rowHeader) {\n\t\t\tranges = this.ranges.filter((range) => range.occupiesRow(cell.row));\n\t\t} else {\n\t\t\tranges = this.ranges.filter((range) => range.occupies(cell));\n\t\t}\n\t\t\n\t\treturn ranges.map((range) => range.getComponent());\n\t}\n\t\n\trowGetRanges(row){\n\t\tvar ranges = this.ranges.filter((range) => range.occupiesRow(row));\n\t\t\n\t\treturn ranges.map((range) => range.getComponent());\n\t}\n\t\n\tcolGetRanges(col){\n\t\tvar ranges = this.ranges.filter((range) => range.occupiesColumn(col));\n\t\t\n\t\treturn ranges.map((range) => range.getComponent());\n\t}\n\t\n\t///////////////////////////////////\n\t////////// Event Handlers /////////\n\t///////////////////////////////////\n\t\n\t_handleMouseUp(e){\n\t\tthis.mousedown = false;\n\t\tdocument.removeEventListener(\"mouseup\", this.mouseUpEvent);\n\t}\n\t\n\t_handleKeyDown(e) {\n\t\tif (!this.blockKeydown && (!this.table.modules.edit || (this.table.modules.edit && !this.table.modules.edit.currentCell))) {\n\t\t\tif (e.key === \"Enter\") {\n\t\t\t\t// is editing a cell?\n\t\t\t\tif (this.table.modules.edit && this.table.modules.edit.currentCell) {\n\t\t\t\t\treturn;\n\t\t\t\t}\n\n\t\t\t\tthis.table.modules.edit.editCell(this.getActiveCell());\n\t\t\t\t\n\t\t\t\te.preventDefault();\n\t\t\t}\n\n\t\t\tif ((e.key === \"Backspace\" || e.key === \"Delete\") && this.options(\"selectableRangeClearCells\")) {\n\t\t\t\tif(this.activeRange){\n\t\t\t\t\tthis.activeRange.clearValues();\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t\n\tinitializeFocus(cell){\n\t\tvar range;\n\t\t\n\t\ttry{\n\t\t\tif (document.selection) { // IE\n\t\t\t\trange = document.body.createTextRange();\n\t\t\t\trange.moveToElementText(cell.getElement());\n\t\t\t\trange.select();\n\t\t\t} else if (window.getSelection) {\n\t\t\t\trange = document.createRange();\n\t\t\t\trange.selectNode(cell.getElement());\n\t\t\t\twindow.getSelection().removeAllRanges();\n\t\t\t\twindow.getSelection().addRange(range);\n\t\t\t}\n\t\t}catch(e){}\n\t}\n\t\n\trestoreFocus(element){\n\t\tthis.table.rowManager.element.focus();\n\t\t\n\t\treturn true;\n\t}\n\t\n\t///////////////////////////////////\n\t////// Column Functionality ///////\n\t///////////////////////////////////\n\t\n\thandleColumnResized(column) {\n\t\tvar selected;\n\t\t\n\t\tif (this.selecting !== \"column\" && this.selecting !== \"all\") {\n\t\t\treturn;\n\t\t}\n\t\t\n\t\tselected = this.ranges.some((range) => range.occupiesColumn(column));\n\t\t\n\t\tif (!selected) {\n\t\t\treturn;\n\t\t}\n\t\t\n\t\tthis.ranges.forEach((range) => {\n\t\t\tvar selectedColumns = range.getColumns(true);\n\t\t\t\n\t\t\tselectedColumns.forEach((selectedColumn) => {\n\t\t\t\tif (selectedColumn !== column) {\n\t\t\t\t\tselectedColumn.setWidth(column.width);\n\t\t\t\t}\n\t\t\t});\n\t\t});\n\t}\n\t\n\thandleColumnMouseDown(event, column) {\n\t\tif (event.button === 2 && (this.selecting === \"column\" || this.selecting === \"all\") && this.activeRange.occupiesColumn(column)) {\n\t\t\treturn;\n\t\t}\n\t\t\n\t\tthis.mousedown = true;\n\t\t\n\t\tdocument.addEventListener(\"mouseup\", this.mouseUpEvent);\n\t\t\n\t\tthis.newSelection(event, column);\n\t}\n\t\n\thandleColumnMouseMove(e, column) {\n\t\tif (column === this.rowHeader || !this.mousedown || this.selecting === 'all') {\n\t\t\treturn;\n\t\t}\n\t\t\n\t\tthis.activeRange.setBounds(false, column, true);\n\t}\n\t\n\t///////////////////////////////////\n\t//////// Cell Functionality ///////\n\t///////////////////////////////////\n\t\n\trenderCell(cell) {\n\t\tvar el = cell.getElement(),\n\t\trangeIdx = this.ranges.findIndex((range) => range.occupies(cell));\n\t\t\n\t\tel.classList.toggle(\"tabulator-range-selected\", rangeIdx !== -1);\n\t\tel.classList.toggle(\"tabulator-range-only-cell-selected\", this.ranges.length === 1 && this.ranges[0].atTopLeft(cell) &&\tthis.ranges[0].atBottomRight(cell));\n\t\t\n\t\tel.dataset.range = rangeIdx;\n\t}\n\t\n\thandleCellMouseDown(event, cell) {\n\t\tif (event.button === 2 && (this.activeRange.occupies(cell) || ((this.selecting === \"row\" || this.selecting === \"all\") && this.activeRange.occupiesRow(cell.row)))) {\n\t\t\treturn;\n\t\t}\n\t\t\n\t\tthis.mousedown = true;\n\t\t\n\t\tdocument.addEventListener(\"mouseup\", this.mouseUpEvent);\n\t\t\n\t\tthis.newSelection(event, cell);\n\t}\n\t\n\thandleCellMouseMove(e, cell) {\n\t\tif (!this.mousedown || this.selecting === \"all\") {\n\t\t\treturn;\n\t\t}\n\t\t\n\t\tthis.activeRange.setBounds(false, cell, true);\n\t}\n\t\n\thandleCellClick(e, cell){\n\t\tthis.initializeFocus(cell);\n\t}\n\t\n\thandleEditingCell(cell) {\n\t\tif(this.activeRange){\n\t\t\tthis.activeRange.setBounds(cell);\n\t\t}\n\t}\n\t\n\tfinishEditingCell() {\n\t\tthis.blockKeydown = true;\n\t\tthis.table.rowManager.element.focus();\n\n\t\tsetTimeout(() => {\n\t\t\tthis.blockKeydown = false;\n\t\t}, 10);\n\t}\n\t\n\t///////////////////////////////////\n\t///////     Navigation      ///////\n\t///////////////////////////////////\n\t\n\tkeyNavigate(dir, e){\n\t\tif(this.navigate(false, false, dir)){\n\t\t\te.preventDefault();\n\t\t}\n\t}\n\t\n\tkeyNavigateRange(e, dir, jump, expand){\n\t\tif(this.navigate(jump, expand, dir)){\n\t\t\te.preventDefault();\n\t\t}\n\t}\n\t\n\tnavigate(jump, expand, dir) {\n\t\tvar moved = false,\n\t\trange, rangeEdge, nextRow, nextCol, row, column;\n\t\t\n\t\t// Don't navigate while editing\n\t\tif (this.table.modules.edit && this.table.modules.edit.currentCell) {\n\t\t\treturn false;\n\t\t}\n\t\t\n\t\t// If there are more than 1 range, use the active range and destroy the others\n\t\tif (this.ranges.length > 1) {\n\t\t\tthis.ranges = this.ranges.filter((range) => {\n\t\t\t\tif (range === this.activeRange) {\n\t\t\t\t\trange.setEnd(range.start.row, range.start.col);\n\t\t\t\t\treturn true;\n\t\t\t\t}\n\t\t\t\trange.destroy();\n\t\t\t\treturn false;\n\t\t\t});\n\t\t}\n\t\t\n\t\trange = this.activeRange;\n\t\t\n\t\trangeEdge = expand ? range.end : range.start;\n\t\tnextRow = rangeEdge.row;\n\t\tnextCol = rangeEdge.col;\n\t\t\n\t\tif(jump){\n\t\t\tswitch(dir){\n\t\t\t\tcase \"left\":\n\t\t\t\t\tnextCol = this.findJumpCellLeft(range.start.row, rangeEdge.col);\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"right\":\n\t\t\t\t\tnextCol = this.findJumpCellRight(range.start.row, rangeEdge.col);\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"up\":\n\t\t\t\t\tnextRow = this.findJumpCellUp(rangeEdge.row, range.start.col);\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"down\":\n\t\t\t\t\tnextRow = this.findJumpCellDown(rangeEdge.row, range.start.col);\n\t\t\t\t\tbreak;\n\t\t\t}\n\t\t}else {\n\t\t\tif(expand){\n\t\t\t\tif ((this.selecting === 'row' && (dir === 'left' || dir === 'right')) || (this.selecting === 'column' && (dir === 'up' || dir === 'down'))) {\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\tswitch(dir){\n\t\t\t\tcase \"left\":\n\t\t\t\t\tnextCol = Math.max(nextCol - 1, 0);\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"right\":\n\t\t\t\t\tnextCol = Math.min(nextCol + 1, this.getTableColumns().length - 1);\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"up\":\n\t\t\t\t\tnextRow = Math.max(nextRow - 1, 0);\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"down\":\n\t\t\t\t\tnextRow = Math.min(nextRow + 1, this.getTableRows().length - 1);\n\t\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\t\n\t\tmoved = nextCol !== rangeEdge.col || nextRow !== rangeEdge.row;\n\t\t\n\t\tif(!expand){\n\t\t\trange.setStart(nextRow, nextCol);\n\t\t}\n\t\t\n\t\trange.setEnd(nextRow, nextCol);\n\t\t\n\t\tif(!expand){\n\t\t\tthis.selecting = \"cell\";\n\t\t}\n\t\t\n\t\tif (moved) {\n\t\t\trow = this.getRowByRangePos(range.end.row);\n\t\t\tcolumn = this.getColumnByRangePos(range.end.col);\n\t\t\t\n\t\t\tif ((dir === 'left' || dir === 'right') && column.getElement().parentNode === null) {\n\t\t\t\tcolumn.getComponent().scrollTo(undefined, false);\n\t\t\t} else if ((dir === 'up' || dir === 'down') && row.getElement().parentNode === null) {\n\t\t\t\trow.getComponent().scrollTo(undefined, false);\n\t\t\t} else {\n\t\t\t\t// Use faster autoScroll when the elements are on the DOM\n\t\t\t\tthis.autoScroll(range, row.getElement(), column.getElement());\n\t\t\t}\n\t\t\t\n\t\t\tthis.layoutElement();\n\t\t\t\n\t\t\treturn true;\n\t\t}\n\t}\n\t\n\trangeRemoved(removed){\n\t\tthis.ranges = this.ranges.filter((range) => range !== removed);\n\t\t\n\t\tif(this.activeRange === removed){\n\t\t\tif(this.ranges.length){\n\t\t\t\tthis.activeRange = this.ranges[this.ranges.length - 1];\n\t\t\t}else {\n\t\t\t\tthis.addRange();\n\t\t\t}\n\t\t}\n\t\t\n\t\tthis.layoutElement();\n\t}\n\t\n\tfindJumpCell(cells, reverse, emptyStart, emptySide){\n\t\tvar nextCell;\n\t\t\n\t\tif(reverse){\n\t\t\tcells = cells.reverse();\n\t\t}\n\t\t\n\t\tfor(let currentCell of cells){\n\t\t\tlet currentValue = currentCell.getValue();\n\t\t\t\n\t\t\tif(emptyStart){\n\t\t\t\tnextCell = currentCell;\n\t\t\t\tif(currentValue){\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tif(emptySide){\n\t\t\t\t\tnextCell = currentCell;\n\t\t\t\t\t\n\t\t\t\t\tif(currentValue){\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}else {\n\t\t\t\t\tif(currentValue){\n\t\t\t\t\t\tnextCell = currentCell;\n\t\t\t\t\t}else {\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn nextCell;\n\t}\n\t\n\tfindJumpCellLeft(rowPos, colPos){\n\t\tvar row = this.getRowByRangePos(rowPos),\n\t\tcells = row.cells.filter((cell) => cell.column.visible),\n\t\tisStartingCellEmpty = !cells[colPos].getValue(),\n\t\tisLeftOfStartingCellEmpty = cells[colPos] ? !cells[colPos].getValue() : false,\n\t\tjumpCol = colPos,\n\t\ttargetCells = this.rowHeader ? cells.slice(1, colPos) : cells.slice(0, colPos),\n\t\tnextCell = this.findJumpCell(targetCells, true, isStartingCellEmpty, isLeftOfStartingCellEmpty);\n\t\t\n\t\tif(nextCell){\n\t\t\tjumpCol = nextCell.column.getPosition() - 1;\n\t\t}\n\t\t\n\t\treturn jumpCol;\n\t}\n\t\n\tfindJumpCellRight(rowPos, colPos){\n\t\tvar row = this.getRowByRangePos(rowPos),\n\t\tcells = row.cells.filter((cell) => cell.column.visible),\n\t\tisStartingCellEmpty = !cells[colPos].getValue(),\n\t\tisRightOfStartingCellEmpty = cells[colPos + 1] ? !cells[colPos + 1].getValue() : false,\n\t\tjumpCol = colPos,\n\t\tnextCell = this.findJumpCell(cells.slice(colPos + 1, cells.length), false, isStartingCellEmpty, isRightOfStartingCellEmpty);\n\t\t\n\t\tif(nextCell){\n\t\t\tjumpCol = nextCell.column.getPosition() - 1;\n\t\t}\n\t\t\n\t\treturn jumpCol;\n\t}\n\t\n\tfindJumpCellUp(rowPos, colPos) {\n\t\tvar column = this.getColumnByRangePos(colPos),\n\t\tcells = column.cells.filter((cell) => this.table.rowManager.activeRows.includes(cell.row)),\n\t\tisStartingCellEmpty = !cells[rowPos].getValue(),\n\t\tisTopOfStartingCellEmpty = cells[rowPos - 1] ? !cells[rowPos - 1].getValue() : false,\n\t\tjumpRow = rowPos,\n\t\tnextCell = this.findJumpCell(cells.slice(0, jumpRow), true, isStartingCellEmpty, isTopOfStartingCellEmpty);\n\t\t\n\t\tif(nextCell){\n\t\t\tjumpRow = nextCell.row.position - 1;\n\t\t}\n\t\t\n\t\treturn jumpRow;\n\t}\n\t\n\tfindJumpCellDown(rowPos, colPos) {\n\t\tvar column = this.getColumnByRangePos(colPos),\n\t\tcells = column.cells.filter((cell) => this.table.rowManager.activeRows.includes(cell.row)),\n\t\tisStartingCellEmpty = !cells[rowPos].getValue(),\n\t\tisBottomOfStartingCellEmpty = cells[rowPos + 1] ? !cells[rowPos + 1].getValue() : false,\n\t\tjumpRow = rowPos,\n\t\tnextCell = this.findJumpCell(cells.slice(jumpRow + 1, cells.length), false, isStartingCellEmpty, isBottomOfStartingCellEmpty);\n\t\t\n\t\tif(nextCell){\n\t\t\tjumpRow = nextCell.row.position - 1;\n\t\t}\n\t\t\n\t\treturn jumpRow;\n\t}\n\t\n\t///////////////////////////////////\n\t///////      Selection      ///////\n\t///////////////////////////////////\n\tnewSelection(event, element) {\n\t\tvar range;\n\t\t\n\t\tif (element.type === \"column\") {\n\t\t\tif(!this.columnSelection){\n\t\t\t\treturn;\n\t\t\t}\n\t\t\t\n\t\t\tif (element === this.rowHeader) {\n\t\t\t\trange = this.resetRanges();\n\t\t\t\tthis.selecting = \"all\";\n\t\t\t\t\n\t\t\t\tvar topLeftCell, bottomRightCell = this.getCell(-1, -1);\n\n\t\t\t\tif(this.rowHeader){\n\t\t\t\t\ttopLeftCell = this.getCell(0, 1);\n\t\t\t\t}else {\n\t\t\t\t\ttopLeftCell = this.getCell(0, 0);\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\trange.setBounds(topLeftCell, bottomRightCell);\t\t\n\t\t\t\treturn;\n\t\t\t} else {\n\t\t\t\tthis.selecting = \"column\";\n\t\t\t}\n\t\t} else if (element.column === this.rowHeader) {\n\t\t\tthis.selecting = \"row\";\n\t\t} else {\n\t\t\tthis.selecting = \"cell\";\n\t\t}\n\t\t\n\t\tif (event.shiftKey) {\n\t\t\tthis.activeRange.setBounds(false, element);\n\t\t} else if (event.ctrlKey) {\n\t\t\tthis.addRange().setBounds(element);\n\t\t} else {\n\t\t\tthis.resetRanges().setBounds(element);\n\t\t}\n\t}\n\t\n\tautoScroll(range, row, column) {\n\t\tvar tableHolder = this.table.rowManager.element,\n\t\trowHeader, rect, view, withinHorizontalView, withinVerticalView;\n\n\t\tif (typeof row === 'undefined') {\n\t\t\trow = this.getRowByRangePos(range.end.row).getElement();\n\t\t}\n\t\t\n\t\tif (typeof column === 'undefined') {\n\t\t\tcolumn = this.getColumnByRangePos(range.end.col).getElement();\n\t\t}\n\n\t\tif (this.rowHeader) {\n\t\t\trowHeader = this.rowHeader.getElement();\n\t\t}\n\t\t\n\t\trect = {\n\t\t\tleft: column.offsetLeft,\n\t\t\tright: column.offsetLeft + column.offsetWidth,\n\t\t\ttop: row.offsetTop,\n\t\t\tbottom: row.offsetTop + row.offsetHeight,\n\t\t};\n\t\t\n\t\tview = {\n\t\t\tleft: tableHolder.scrollLeft,\n\t\t\tright: Math.ceil(tableHolder.scrollLeft + tableHolder.clientWidth),\n\t\t\ttop: tableHolder.scrollTop,\n\t\t\tbottom:\ttableHolder.scrollTop +\ttableHolder.offsetHeight - this.table.rowManager.scrollbarWidth,\n\t\t};\n\n\t\tif (rowHeader) {\n\t\t\tview.left += rowHeader.offsetWidth;\n\t\t}\n\t\t\n\t\twithinHorizontalView = view.left < rect.left &&\trect.left < view.right && view.left < rect.right &&\trect.right < view.right;\n\t\t\n\t\twithinVerticalView = view.top < rect.top &&\trect.top < view.bottom && view.top < rect.bottom &&\trect.bottom < view.bottom;\n\t\t\n\t\tif (!withinHorizontalView) {\n\t\t\tif (rect.left < view.left) {\n\t\t\t\ttableHolder.scrollLeft = rect.left;\n\t\t\t\tif (rowHeader) {\n\t\t\t\t\ttableHolder.scrollLeft -= rowHeader.offsetWidth;\n\t\t\t\t}\n\t\t\t} else if (rect.right > view.right) {\n\t\t\t\ttableHolder.scrollLeft = rect.right - tableHolder.clientWidth;\n\t\t\t}\n\t\t}\n\t\t\n\t\tif (!withinVerticalView) {\n\t\t\tif (rect.top < view.top) {\n\t\t\t\ttableHolder.scrollTop = rect.top;\n\t\t\t} else if (rect.bottom > view.bottom) {\n\t\t\t\ttableHolder.scrollTop = rect.bottom - tableHolder.clientHeight;\n\t\t\t}\n\t\t}\n\t}\n\t\n\t\n\t///////////////////////////////////\n\t///////       Layout        ///////\n\t///////////////////////////////////\n\t\n\tlayoutChange(){\n\t\tthis.overlay.style.visibility = \"hidden\";\n\t\tclearTimeout(this.layoutChangeTimeout);\n\t\tthis.layoutChangeTimeout = setTimeout(this.layoutRanges.bind(this), 200);\n\t}\n\t\n\tredraw(force) {\n\t\tif (force) {\n\t\t\tthis.selecting = 'cell';\n\t\t\tthis.resetRanges();\n\t\t\tthis.layoutElement();\n\t\t}\n\t}\n\t\n\tlayoutElement(visibleRows) {\n\t\tvar rows;\n\t\t\n\t\tif (visibleRows) {\n\t\t\trows = this.table.rowManager.getVisibleRows(true);\n\t\t} else {\n\t\t\trows = this.table.rowManager.getRows();\n\t\t}\n\t\t\n\t\trows.forEach((row) => {\n\t\t\tif (row.type === \"row\") {\n\t\t\t\tthis.layoutRow(row);\n\t\t\t\trow.cells.forEach((cell) => this.renderCell(cell));\n\t\t\t}\n\t\t});\n\t\t\n\t\tthis.getTableColumns().forEach((column) => {\n\t\t\tthis.layoutColumn(column);\n\t\t});\n\t\t\n\t\tthis.layoutRanges();\n\t}\n\t\n\tlayoutRow(row) {\n\t\tvar el = row.getElement(),\n\t\tselected = false,\n\t\toccupied = this.ranges.some((range) => range.occupiesRow(row));\n\t\t\n\t\tif (this.selecting === \"row\") {\n\t\t\tselected = occupied;\n\t\t} else if (this.selecting === \"all\") {\n\t\t\tselected = true;\n\t\t}\n\t\t\n\t\tel.classList.toggle(\"tabulator-range-selected\", selected);\n\t\tel.classList.toggle(\"tabulator-range-highlight\", occupied);\n\t}\n\t\n\tlayoutColumn(column) {\n\t\tvar el = column.getElement(),\t\t\n\t\tselected = false,\n\t\toccupied = this.ranges.some((range) => range.occupiesColumn(column));\n\t\t\n\t\tif (this.selecting === \"column\") {\n\t\t\tselected = occupied;\n\t\t} else if (this.selecting === \"all\") {\n\t\t\tselected = true;\n\t\t}\n\t\t\n\t\tel.classList.toggle(\"tabulator-range-selected\", selected);\n\t\tel.classList.toggle(\"tabulator-range-highlight\", occupied);\n\t}\n\t\n\tlayoutRanges() {\n\t\tvar activeCell;\n\t\t\n\t\tif (!this.table.initialized) {\n\t\t\treturn;\n\t\t}\n\t\t\n\t\tactiveCell = this.getActiveCell();\n\t\t\n\t\tif (!activeCell) {\n\t\t\treturn;\n\t\t}\n\t\t\n\t\tthis.activeRangeCellElement.style.left = activeCell.row.getElement().offsetLeft + activeCell.getElement().offsetLeft + \"px\";\n\t\tthis.activeRangeCellElement.style.top =\tactiveCell.row.getElement().offsetTop + \"px\";\n\t\tthis.activeRangeCellElement.style.width = activeCell.getElement().offsetLeft + activeCell.getElement().offsetWidth - activeCell.getElement().offsetLeft + \"px\";\n\t\tthis.activeRangeCellElement.style.height = activeCell.row.getElement().offsetTop + activeCell.row.getElement().offsetHeight - activeCell.row.getElement().offsetTop + \"px\";\n\t\t\n\t\tthis.ranges.forEach((range) => range.layout());\n\t\t\n\t\tthis.overlay.style.visibility = \"visible\";\n\t}\n\t\n\t\n\t///////////////////////////////////\n\t///////  Helper Functions   ///////\n\t///////////////////////////////////\t\n\t\n\tgetCell(rowIdx, colIdx) {\n\t\tvar row;\n\t\t\n\t\tif (colIdx < 0) {\n\t\t\tcolIdx = this.getTableColumns().length + colIdx;\n\t\t\tif (colIdx < 0) {\n\t\t\t\treturn null;\n\t\t\t}\n\t\t}\n\t\t\n\t\tif (rowIdx < 0) {\n\t\t\trowIdx = this.getTableRows().length + rowIdx;\n\t\t}\n\t\t\n\t\trow = this.table.rowManager.getRowFromPosition(rowIdx + 1);\n\t\t\n\t\treturn row ? row.getCells(false, true).filter((cell) => cell.column.visible)[colIdx] : null;\n\t}\n\t\n\t\n\tgetActiveCell() {\n\t\treturn this.getCell(this.activeRange.start.row, this.activeRange.start.col);\n\t}\n\t\n\tgetRowByRangePos(pos) {\n\t\treturn this.getTableRows()[pos];\n\t}\n\t\n\tgetColumnByRangePos(pos) {\n\t\treturn this.getTableColumns()[pos];\n\t}\n\t\n\tgetTableRows() {\n\t\treturn this.table.rowManager.getDisplayRows();\n\t}\n\t\n\tgetTableColumns() {\n\t\treturn this.table.columnManager.getVisibleColumnsByIndex();\n\t}\n\t\n\taddRange(start, end) {\n\t\tvar  range;\n\t\t\n\t\tif(this.maxRanges !== true && this.ranges.length >= this.maxRanges){\n\t\t\tthis.ranges.shift().destroy();\n\t\t}\n\t\t\n\t\trange = new Range(this.table, this, start, end);\n\t\t\n\t\tthis.activeRange = range;\n\t\tthis.ranges.push(range);\n\t\tthis.rangeContainer.appendChild(range.element);\n\t\t\n\t\treturn range;\n\t}\n\t\n\tresetRanges() {\n\t\tvar range, cell;\n\t\t\n\t\tthis.ranges.forEach((range) => range.destroy());\n\t\tthis.ranges = [];\n\t\t\n\t\trange = this.addRange();\n\t\t\n\t\tif(this.table.rowManager.activeRows.length){\n\t\t\tcell = this.table.rowManager.activeRows[0].cells[this.rowHeader ? 1 : 0];\n\n\t\t\tif(cell){\n\t\t\t\trange.setBounds(cell);\n\t\t\t\tthis.initializeFocus(cell);\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn range;\n\t}\n\t\n\ttableDestroyed(){\n\t\tdocument.removeEventListener(\"mouseup\", this.mouseUpEvent);\n\t\tthis.table.rowManager.element.removeEventListener(\"keydown\", this.keyDownEvent);\n\t}\n\t\n\tselectedRows(component) {\n\t\treturn component ? this.activeRange.getRows().map((row) => row.getComponent()) : this.activeRange.getRows();\n\t}\n\t\n\tselectedColumns(component) {\n\t\treturn component ? this.activeRange.getColumns().map((col) => col.getComponent()) : this.activeRange.getColumns();\n\t}\n}\n\nSelectRange.moduleName = \"selectRange\";\n\nclass Tooltip extends Module{\n\t\n\tconstructor(table){\n\t\tsuper(table);\n\t\t\n\t\tthis.tooltipSubscriber = null,\n\t\tthis.headerSubscriber = null,\n\t\t\n\t\tthis.timeout = null;\n\t\tthis.popupInstance = null;\n\t\t\n\t\tthis.registerTableOption(\"tooltipGenerationMode\", undefined);  //deprecated\n\t\tthis.registerTableOption(\"tooltipDelay\", 300); \n\t\t\n\t\tthis.registerColumnOption(\"tooltip\");\n\t\tthis.registerColumnOption(\"headerTooltip\");\n\t}\n\t\n\tinitialize(){\n\t\tthis.deprecatedOptionsCheck();\n\t\t\n\t\tthis.subscribe(\"column-init\", this.initializeColumn.bind(this));\n\t}\n\t\n\tdeprecatedOptionsCheck(){\n\t\tthis.deprecationCheckMsg(\"tooltipGenerationMode\", \"This option is no longer needed as tooltips are always generated on hover now\");\n\t}\t\n\t\n\tinitializeColumn(column){\n\t\tif(column.definition.headerTooltip && !this.headerSubscriber){\n\t\t\tthis.headerSubscriber = true;\n\t\t\t\n\t\t\tthis.subscribe(\"column-mousemove\", this.mousemoveCheck.bind(this, \"headerTooltip\"));\n\t\t\tthis.subscribe(\"column-mouseout\", this.mouseoutCheck.bind(this, \"headerTooltip\"));\n\t\t}\n\t\t\n\t\tif(column.definition.tooltip && !this.tooltipSubscriber){\n\t\t\tthis.tooltipSubscriber = true;\n\t\t\t\n\t\t\tthis.subscribe(\"cell-mousemove\", this.mousemoveCheck.bind(this, \"tooltip\"));\n\t\t\tthis.subscribe(\"cell-mouseout\", this.mouseoutCheck.bind(this, \"tooltip\"));\n\t\t}\n\t}\n\t\n\tmousemoveCheck(action, e, component){\n\t\tvar tooltip = action === \"tooltip\" ? component.column.definition.tooltip : component.definition.headerTooltip;\n\t\t\n\t\tif(tooltip){\n\t\t\tthis.clearPopup();\n\t\t\tthis.timeout = setTimeout(this.loadTooltip.bind(this, e, component, tooltip), this.table.options.tooltipDelay);\n\t\t}\n\t}\n\n\tmouseoutCheck(action, e, component){\n\t\tif(!this.popupInstance){\n\t\t\tthis.clearPopup();\n\t\t}\n\t}\n\t\n\tclearPopup(action, e, component){\n\t\tclearTimeout(this.timeout);\n\t\tthis.timeout = null;\n\t\t\n\t\tif(this.popupInstance){\n\t\t\tthis.popupInstance.hide();\n\t\t}\n\t}\n\t\n\tloadTooltip(e, component, tooltip){\n\t\tvar contentsEl, renderedCallback, coords;\n\n\t\tfunction onRendered(callback){\n\t\t\trenderedCallback = callback;\n\t\t}\n\t\t\n\t\tif(typeof tooltip === \"function\"){\n\t\t\ttooltip = tooltip(e, component.getComponent(), onRendered);\n\t\t}\n\t\t\n\t\tif(tooltip instanceof HTMLElement){\n\t\t\tcontentsEl = tooltip;\n\t\t}else {\n\t\t\tcontentsEl = document.createElement(\"div\");\n\t\t\t\n\t\t\tif(tooltip === true){\n\t\t\t\tif(component instanceof Cell){\n\t\t\t\t\ttooltip = component.value;\n\t\t\t\t}else {\n\t\t\t\t\tif(component.definition.field){\n\t\t\t\t\t\tthis.langBind(\"columns|\" + component.definition.field, (value) => {\n\t\t\t\t\t\t\tcontentsEl.innerHTML = tooltip = value || component.definition.title;\n\t\t\t\t\t\t});\n\t\t\t\t\t}else {\n\t\t\t\t\t\ttooltip = component.definition.title;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\tcontentsEl.innerHTML = tooltip;\n\t\t}\n\t\t\n\t\tif(tooltip || tooltip === 0 || tooltip === false){\n\t\t\tcontentsEl.classList.add(\"tabulator-tooltip\");\n\n\t\t\tcontentsEl.addEventListener(\"mousemove\", e => e.preventDefault());\n\t\t\t\n\t\t\tthis.popupInstance = this.popup(contentsEl);\n\t\t\t\n\t\t\tif(typeof renderedCallback === \"function\"){\n\t\t\t\tthis.popupInstance.renderCallback(renderedCallback);\n\t\t\t}\n\n\t\t\tcoords = this.popupInstance.containerEventCoords(e);\n\t\t\t\n\t\t\tthis.popupInstance.show(coords.x + 15, coords.y + 15).hideOnBlur(() => {\n\t\t\t\tthis.dispatchExternal(\"TooltipClosed\", component.getComponent());\n\t\t\t\tthis.popupInstance = null;\n\t\t\t});\n\t\t\t\n\t\t\tthis.dispatchExternal(\"TooltipOpened\", component.getComponent());\n\t\t}\n\t}\n}\n\nTooltip.moduleName = \"tooltip\";\n\nvar defaultValidators = {\n\t//is integer\n\tinteger: function(cell, value, parameters){\n\t\tif(value === \"\" || value === null || typeof value === \"undefined\"){\n\t\t\treturn true;\n\t\t}\n\n\t\tvalue = Number(value);\n\n\t\treturn !isNaN(value) && isFinite(value) && Math.floor(value) === value;\n\t},\n\n\t//is float\n\tfloat: function(cell, value, parameters){\n\t\tif(value === \"\" || value === null || typeof value === \"undefined\"){\n\t\t\treturn true;\n\t\t}\n\t\t\n\t\tvalue = Number(value);\n\n\t\treturn !isNaN(value) && isFinite(value) && value % 1 !== 0;\n\t},\n\n\t//must be a number\n\tnumeric: function(cell, value, parameters){\n\t\tif(value === \"\" || value === null || typeof value === \"undefined\"){\n\t\t\treturn true;\n\t\t}\n\t\treturn !isNaN(value);\n\t},\n\n\t//must be a string\n\tstring: function(cell, value, parameters){\n\t\tif(value === \"\" || value === null || typeof value === \"undefined\"){\n\t\t\treturn true;\n\t\t}\n\t\treturn isNaN(value);\n\t},\n\n\t//must be alphanumeric\n\talphanumeric: function(cell, value, parameters){\n\t\tif(value === \"\" || value === null || typeof value === \"undefined\"){\n\t\t\treturn true;\n\t\t}\n\n\t\tvar reg = new RegExp(/^[a-z0-9]+$/i);\n\n\t\treturn reg.test(value);\n\t},\n\n\t//maximum value\n\tmax: function(cell, value, parameters){\n\t\tif(value === \"\" || value === null || typeof value === \"undefined\"){\n\t\t\treturn true;\n\t\t}\n\t\treturn parseFloat(value) <= parameters;\n\t},\n\n\t//minimum value\n\tmin: function(cell, value, parameters){\n\t\tif(value === \"\" || value === null || typeof value === \"undefined\"){\n\t\t\treturn true;\n\t\t}\n\t\treturn parseFloat(value) >= parameters;\n\t},\n\n\t//starts with  value\n\tstarts: function(cell, value, parameters){\n\t\tif(value === \"\" || value === null || typeof value === \"undefined\"){\n\t\t\treturn true;\n\t\t}\n\t\treturn String(value).toLowerCase().startsWith(String(parameters).toLowerCase());\n\t},\n\n\t//ends with  value\n\tends: function(cell, value, parameters){\n\t\tif(value === \"\" || value === null || typeof value === \"undefined\"){\n\t\t\treturn true;\n\t\t}\n\t\treturn String(value).toLowerCase().endsWith(String(parameters).toLowerCase());\n\t},\n\n\n\t//minimum string length\n\tminLength: function(cell, value, parameters){\n\t\tif(value === \"\" || value === null || typeof value === \"undefined\"){\n\t\t\treturn true;\n\t\t}\n\t\treturn String(value).length >= parameters;\n\t},\n\n\t//maximum string length\n\tmaxLength: function(cell, value, parameters){\n\t\tif(value === \"\" || value === null || typeof value === \"undefined\"){\n\t\t\treturn true;\n\t\t}\n\t\treturn String(value).length <= parameters;\n\t},\n\n\t//in provided value list\n\tin: function(cell, value, parameters){\n\t\tif(value === \"\" || value === null || typeof value === \"undefined\"){\n\t\t\treturn true;\n\t\t}\n\n\t\tif(typeof parameters == \"string\"){\n\t\t\tparameters = parameters.split(\"|\");\n\t\t}\n\n\t\treturn parameters.indexOf(value) > -1;\n\t},\n\n\t//must match provided regex\n\tregex: function(cell, value, parameters){\n\t\tif(value === \"\" || value === null || typeof value === \"undefined\"){\n\t\t\treturn true;\n\t\t}\n\t\tvar reg = new RegExp(parameters);\n\n\t\treturn reg.test(value);\n\t},\n\n\t//value must be unique in this column\n\tunique: function(cell, value, parameters){\n\t\tif(value === \"\" || value === null || typeof value === \"undefined\"){\n\t\t\treturn true;\n\t\t}\n\t\tvar unique = true;\n\n\t\tvar cellData = cell.getData();\n\t\tvar column = cell.getColumn()._getSelf();\n\n\t\tthis.table.rowManager.rows.forEach(function(row){\n\t\t\tvar data = row.getData();\n\n\t\t\tif(data !== cellData){\n\t\t\t\tif(value == column.getFieldValue(data)){\n\t\t\t\t\tunique = false;\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\n\t\treturn unique;\n\t},\n\n\t//must have a value\n\trequired:function(cell, value, parameters){\n\t\treturn value !== \"\" && value !== null && typeof value !== \"undefined\";\n\t},\n};\n\nclass Validate extends Module{\n\t\n\tconstructor(table){\n\t\tsuper(table);\n\t\t\n\t\tthis.invalidCells = [];\n\t\t\n\t\tthis.registerTableOption(\"validationMode\", \"blocking\");\n\t\t\n\t\tthis.registerColumnOption(\"validator\");\n\t\t\n\t\tthis.registerTableFunction(\"getInvalidCells\", this.getInvalidCells.bind(this));\n\t\tthis.registerTableFunction(\"clearCellValidation\", this.userClearCellValidation.bind(this));\n\t\tthis.registerTableFunction(\"validate\", this.userValidate.bind(this));\n\t\t\n\t\tthis.registerComponentFunction(\"cell\", \"isValid\", this.cellIsValid.bind(this));\n\t\tthis.registerComponentFunction(\"cell\", \"clearValidation\", this.clearValidation.bind(this));\n\t\tthis.registerComponentFunction(\"cell\", \"validate\", this.cellValidate.bind(this));\n\t\t\n\t\tthis.registerComponentFunction(\"column\", \"validate\", this.columnValidate.bind(this));\n\t\tthis.registerComponentFunction(\"row\", \"validate\", this.rowValidate.bind(this));\n\t}\n\t\n\t\n\tinitialize(){\n\t\tthis.subscribe(\"cell-delete\", this.clearValidation.bind(this));\n\t\tthis.subscribe(\"column-layout\", this.initializeColumnCheck.bind(this));\n\t\t\n\t\tthis.subscribe(\"edit-success\", this.editValidate.bind(this));\n\t\tthis.subscribe(\"edit-editor-clear\", this.editorClear.bind(this));\n\t\tthis.subscribe(\"edit-edited-clear\", this.editedClear.bind(this));\n\t}\n\t\n\t///////////////////////////////////\n\t///////// Event Handling //////////\n\t///////////////////////////////////\n\t\n\teditValidate(cell, value, previousValue){\n\t\tvar valid = this.table.options.validationMode !== \"manual\" ? this.validate(cell.column.modules.validate, cell, value) : true;\n\t\t\n\t\t// allow time for editor to make render changes then style cell\n\t\tif(valid !== true){\n\t\t\tsetTimeout(() => {\n\t\t\t\tcell.getElement().classList.add(\"tabulator-validation-fail\");\n\t\t\t\tthis.dispatchExternal(\"validationFailed\", cell.getComponent(), value, valid);\n\t\t\t});\n\t\t}\n\t\t\n\t\treturn valid;\n\t}\n\t\n\teditorClear(cell, cancelled){\n\t\tif(cancelled){\n\t\t\tif(cell.column.modules.validate){\n\t\t\t\tthis.cellValidate(cell);\n\t\t\t}\n\t\t}\n\n\t\tcell.getElement().classList.remove(\"tabulator-validation-fail\");\n\t}\n\t\n\teditedClear(cell){\n\t\tif(cell.modules.validate){\n\t\t\tcell.modules.validate.invalid = false;\n\t\t}\n\t}\n\t\n\t///////////////////////////////////\n\t////////// Cell Functions /////////\n\t///////////////////////////////////\n\t\n\tcellIsValid(cell){\n\t\treturn cell.modules.validate ? (cell.modules.validate.invalid || true) : true;\n\t}\n\t\n\tcellValidate(cell){\n\t\treturn this.validate(cell.column.modules.validate, cell, cell.getValue());\n\t}\n\t\n\t///////////////////////////////////\n\t///////// Column Functions ////////\n\t///////////////////////////////////\n\t\n\tcolumnValidate(column){\n\t\tvar invalid = [];\n\t\t\n\t\tcolumn.cells.forEach((cell) => {\n\t\t\tif(this.cellValidate(cell) !== true){\n\t\t\t\tinvalid.push(cell.getComponent());\n\t\t\t}\n\t\t});\n\t\t\n\t\treturn invalid.length ? invalid : true;\n\t}\n\t\n\t///////////////////////////////////\n\t////////// Row Functions //////////\n\t///////////////////////////////////\n\t\n\trowValidate(row){\n\t\tvar invalid = [];\n\t\t\n\t\trow.cells.forEach((cell) => {\n\t\t\tif(this.cellValidate(cell) !== true){\n\t\t\t\tinvalid.push(cell.getComponent());\n\t\t\t}\n\t\t});\n\t\t\n\t\treturn invalid.length ? invalid : true;\n\t}\n\t\n\t///////////////////////////////////\n\t///////// Table Functions /////////\n\t///////////////////////////////////\n\t\n\t\n\tuserClearCellValidation(cells){\n\t\tif(!cells){\n\t\t\tcells = this.getInvalidCells();\n\t\t}\n\t\t\n\t\tif(!Array.isArray(cells)){\n\t\t\tcells = [cells];\n\t\t}\n\t\t\n\t\tcells.forEach((cell) => {\n\t\t\tthis.clearValidation(cell._getSelf());\n\t\t});\n\t}\n\t\n\tuserValidate(cells){\n\t\tvar output = [];\n\t\t\n\t\t//clear row data\n\t\tthis.table.rowManager.rows.forEach((row) => {\n\t\t\trow = row.getComponent();\n\t\t\t\n\t\t\tvar valid = row.validate();\n\t\t\t\n\t\t\tif(valid !== true){\n\t\t\t\toutput = output.concat(valid);\n\t\t\t}\n\t\t});\n\t\t\n\t\treturn output.length ? output : true;\n\t}\n\t\n\t///////////////////////////////////\n\t///////// Internal Logic //////////\n\t///////////////////////////////////\n\t\n\tinitializeColumnCheck(column){\n\t\tif(typeof column.definition.validator !== \"undefined\"){\n\t\t\tthis.initializeColumn(column);\n\t\t}\n\t}\n\t\n\t//validate\n\tinitializeColumn(column){\n\t\tvar self = this,\n\t\tconfig = [],\n\t\tvalidator;\n\t\t\n\t\tif(column.definition.validator){\n\t\t\t\n\t\t\tif(Array.isArray(column.definition.validator)){\n\t\t\t\tcolumn.definition.validator.forEach((item) => {\n\t\t\t\t\tvalidator = self._extractValidator(item);\n\t\t\t\t\t\n\t\t\t\t\tif(validator){\n\t\t\t\t\t\tconfig.push(validator);\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t\t\n\t\t\t}else {\n\t\t\t\tvalidator = this._extractValidator(column.definition.validator);\n\t\t\t\t\n\t\t\t\tif(validator){\n\t\t\t\t\tconfig.push(validator);\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\tcolumn.modules.validate = config.length ? config : false;\n\t\t}\n\t}\n\t\n\t_extractValidator(value){\n\t\tvar type, params, pos;\n\t\t\n\t\tswitch(typeof value){\n\t\t\tcase \"string\":\n\t\t\t\tpos = value.indexOf(':');\n\t\t\t\n\t\t\t\tif(pos > -1){\n\t\t\t\t\ttype = value.substring(0,pos);\n\t\t\t\t\tparams = value.substring(pos+1);\n\t\t\t\t}else {\n\t\t\t\t\ttype = value;\n\t\t\t\t}\n\t\t\t\n\t\t\t\treturn this._buildValidator(type, params);\n\t\t\t\n\t\t\tcase \"function\":\n\t\t\t\treturn this._buildValidator(value);\n\t\t\t\n\t\t\tcase \"object\":\n\t\t\t\treturn this._buildValidator(value.type, value.parameters);\n\t\t}\n\t}\n\t\n\t_buildValidator(type, params){\n\t\t\n\t\tvar func = typeof type == \"function\" ? type : Validate.validators[type];\n\t\t\n\t\tif(!func){\n\t\t\tconsole.warn(\"Validator Setup Error - No matching validator found:\", type);\n\t\t\treturn false;\n\t\t}else {\n\t\t\treturn {\n\t\t\t\ttype:typeof type == \"function\" ? \"function\" : type,\n\t\t\t\tfunc:func,\n\t\t\t\tparams:params,\n\t\t\t};\n\t\t}\n\t}\n\t\n\tvalidate(validators, cell, value){\n\t\tvar self = this,\n\t\tfailedValidators = [],\n\t\tinvalidIndex = this.invalidCells.indexOf(cell);\n\t\t\n\t\tif(validators){\n\t\t\tvalidators.forEach((item) => {\n\t\t\t\tif(!item.func.call(self, cell.getComponent(), value, item.params)){\n\t\t\t\t\tfailedValidators.push({\n\t\t\t\t\t\ttype:item.type,\n\t\t\t\t\t\tparameters:item.params\n\t\t\t\t\t});\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\t\t\n\t\tif(!cell.modules.validate){\n\t\t\tcell.modules.validate = {};\n\t\t}\n\t\t\n\t\tif(!failedValidators.length){\n\t\t\tcell.modules.validate.invalid = false;\n\t\t\tcell.getElement().classList.remove(\"tabulator-validation-fail\");\n\t\t\t\n\t\t\tif(invalidIndex > -1){\n\t\t\t\tthis.invalidCells.splice(invalidIndex, 1);\n\t\t\t}\n\t\t}else {\n\t\t\tcell.modules.validate.invalid = failedValidators;\n\t\t\t\n\t\t\tif(this.table.options.validationMode !== \"manual\"){\n\t\t\t\tcell.getElement().classList.add(\"tabulator-validation-fail\");\n\t\t\t}\n\t\t\t\n\t\t\tif(invalidIndex == -1){\n\t\t\t\tthis.invalidCells.push(cell);\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn failedValidators.length ? failedValidators : true;\n\t}\n\t\n\tgetInvalidCells(){\n\t\tvar output = [];\n\t\t\n\t\tthis.invalidCells.forEach((cell) => {\n\t\t\toutput.push(cell.getComponent());\n\t\t});\n\t\t\n\t\treturn output;\n\t}\n\t\n\tclearValidation(cell){\n\t\tvar invalidIndex;\n\t\t\n\t\tif(cell.modules.validate && cell.modules.validate.invalid){\n\t\t\t\n\t\t\tcell.getElement().classList.remove(\"tabulator-validation-fail\");\n\t\t\tcell.modules.validate.invalid = false;\n\t\t\t\n\t\t\tinvalidIndex = this.invalidCells.indexOf(cell);\n\t\t\t\n\t\t\tif(invalidIndex > -1){\n\t\t\t\tthis.invalidCells.splice(invalidIndex, 1);\n\t\t\t}\n\t\t}\n\t}\n}\n\nValidate.moduleName = \"validate\";\n\n//load defaults\nValidate.validators = defaultValidators;\n\nvar modules = /*#__PURE__*/Object.freeze({\n\t__proto__: null,\n\tAccessorModule: Accessor,\n\tAjaxModule: Ajax,\n\tClipboardModule: Clipboard,\n\tColumnCalcsModule: ColumnCalcs,\n\tDataTreeModule: DataTree,\n\tDownloadModule: Download,\n\tEditModule: Edit$1,\n\tExportModule: Export,\n\tFilterModule: Filter,\n\tFormatModule: Format,\n\tFrozenColumnsModule: FrozenColumns,\n\tFrozenRowsModule: FrozenRows,\n\tGroupRowsModule: GroupRows,\n\tHistoryModule: History,\n\tHtmlTableImportModule: HtmlTableImport,\n\tImportModule: Import,\n\tInteractionModule: Interaction,\n\tKeybindingsModule: Keybindings,\n\tMenuModule: Menu,\n\tMoveColumnsModule: MoveColumns,\n\tMoveRowsModule: MoveRows,\n\tMutatorModule: Mutator,\n\tPageModule: Page,\n\tPersistenceModule: Persistence,\n\tPopupModule: Popup$1,\n\tPrintModule: Print,\n\tReactiveDataModule: ReactiveData,\n\tResizeColumnsModule: ResizeColumns,\n\tResizeRowsModule: ResizeRows,\n\tResizeTableModule: ResizeTable,\n\tResponsiveLayoutModule: ResponsiveLayout,\n\tSelectRowModule: SelectRow,\n\tSortModule: Sort,\n\tSelectRangeModule: SelectRange,\n\tTooltipModule: Tooltip,\n\tValidateModule: Validate\n});\n\nvar defaultOptions = {\n\n\tdebugEventsExternal:false, //flag to console log events\n\tdebugEventsInternal:false, //flag to console log events\n\tdebugInvalidOptions:true, //allow toggling of invalid option warnings\n\tdebugInvalidComponentFuncs:true, //allow toggling of invalid component warnings\n\tdebugInitialization:true, //allow toggling of pre initialization function call warnings\n\tdebugDeprecation:true, //allow toggling of deprecation warnings\n\n\theight:false, //height of tabulator\n\tminHeight:false, //minimum height of tabulator\n\tmaxHeight:false, //maximum height of tabulator\n\n\tcolumnHeaderVertAlign:\"top\", //vertical alignment of column headers\n\n\tpopupContainer:false,\n\n\tcolumns:[],//store for colum header info\n\tcolumnDefaults:{}, //store column default props\n\n\tdata:false, //default starting data\n\n\tautoColumns:false, //build columns from data row structure\n\tautoColumnsDefinitions:false,\n\n\tnestedFieldSeparator:\".\", //separator for nested data\n\n\tfooterElement:false, //hold footer element\n\n\tindex:\"id\", //filed for row index\n\n\ttextDirection:\"auto\",\n\n\taddRowPos:\"bottom\", //position to insert blank rows, top|bottom\n\n\theaderVisible:true, //hide header\n\n\trenderVertical:\"virtual\",\n\trenderHorizontal:\"basic\",\n\trenderVerticalBuffer:0, // set virtual DOM buffer size\n\n\tscrollToRowPosition:\"top\",\n\tscrollToRowIfVisible:true,\n\n\tscrollToColumnPosition:\"left\",\n\tscrollToColumnIfVisible:true,\n\n\trowFormatter:false,\n\trowFormatterPrint:null,\n\trowFormatterClipboard:null,\n\trowFormatterHtmlOutput:null,\n\n\trowHeight:null,\n\n\tplaceholder:false,\n\n\tdataLoader:true,\n\tdataLoaderLoading:false,\n\tdataLoaderError:false,\n\tdataLoaderErrorTimeout:3000,\n\n\tdataSendParams:{},\n\n\tdataReceiveParams:{},\n};\n\nclass OptionsList {\n\tconstructor(table, msgType, defaults = {}){\n\t\tthis.table = table;\n\t\tthis.msgType = msgType;\n\t\tthis.registeredDefaults = Object.assign({}, defaults);\n\t}\n\t\n\tregister(option, value){\n\t\tthis.registeredDefaults[option] = value;\n\t}\n\t\n\tgenerate(defaultOptions, userOptions = {}){\n\t\tvar output = Object.assign({}, this.registeredDefaults),\n\t\twarn = this.table.options.debugInvalidOptions || userOptions.debugInvalidOptions === true;\n\t\t\n\t\tObject.assign(output, defaultOptions);\n\t\t\n\t\tfor (let key in userOptions){\n\t\t\tif(!output.hasOwnProperty(key)){\n\t\t\t\tif(warn){\n\t\t\t\t\tconsole.warn(\"Invalid \" + this.msgType + \" option:\", key);\n\t\t\t\t}\n\n\t\t\t\toutput[key] = userOptions.key;\n\t\t\t}\n\t\t}\n\t\n\t\t\n\t\tfor (let key in output){\n\t\t\tif(key in userOptions){\n\t\t\t\toutput[key] = userOptions[key];\n\t\t\t}else {\n\t\t\t\tif(Array.isArray(output[key])){\n\t\t\t\t\toutput[key] = Object.assign([], output[key]);\n\t\t\t\t}else if(typeof output[key] === \"object\" && output[key] !== null){\n\t\t\t\t\toutput[key] = Object.assign({}, output[key]);\n\t\t\t\t}else if (typeof output[key] === \"undefined\"){\n\t\t\t\t\tdelete output[key];\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn output;\n\t}\n}\n\nclass Renderer extends CoreFeature{\n\tconstructor(table){\n\t\tsuper(table);\n\n\t\tthis.elementVertical = table.rowManager.element;\n\t\tthis.elementHorizontal = table.columnManager.element;\n\t\tthis.tableElement =  table.rowManager.tableElement;\n\n\t\tthis.verticalFillMode = \"fit\"; // used by row manager to determine how to size the render area (\"fit\" - fits container to the contents, \"fill\" - fills the container without resizing it)\n\t}\n\n\n\t///////////////////////////////////\n\t/////// Internal Bindings /////////\n\t///////////////////////////////////\n\n\tinitialize(){\n\t\t//initialize core functionality\n\t}\n\n\tclearRows(){\n\t\t//clear down existing rows layout\n\t}\n\n\tclearColumns(){\n\t\t//clear down existing columns layout\n\t}\n\n\n\treinitializeColumnWidths(columns){\n\t\t//resize columns to fit data\n\t}\n\n\n\trenderRows(){\n\t\t//render rows from a clean slate\n\t}\n\n\trenderColumns(){\n\t\t//render columns from a clean slate\n\t}\n\n\trerenderRows(callback){\n\t\t// rerender rows and keep position\n\t\tif(callback){\n\t\t\tcallback();\n\t\t}\n\t}\n\n\trerenderColumns(update, blockRedraw){\n\t\t//rerender columns\n\t}\n\n\trenderRowCells(row){\n\t\t//render the cells in a row\n\t}\n\n\trerenderRowCells(row, force){\n\t\t//rerender the cells in a row\n\t}\n\n\tscrollColumns(left, dir){\n\t\t//handle horizontal scrolling\n\t}\n\n\tscrollRows(top, dir){\n\t\t//handle vertical scrolling\n\t}\n\n\tresize(){\n\t\t//container has resized, carry out any needed recalculations (DO NOT RERENDER IN THIS FUNCTION)\n\t}\n\n\tscrollToRow(row){\n\t\t//scroll to a specific row\n\t}\n\n\tscrollToRowNearestTop(row){\n\t\t//determine weather the row is nearest the top or bottom of the table, return true for top or false for bottom\n\t}\n\n\tvisibleRows(includingBuffer){\n\t\t//return the visible rows\n\t\treturn [];\n\t}\n\n\t///////////////////////////////////\n\t//////// Helper Functions /////////\n\t///////////////////////////////////\n\n\trows(){\n\t\treturn this.table.rowManager.getDisplayRows();\n\t}\n\n\tstyleRow(row, index){\n\t\tvar rowEl = row.getElement();\n\n\t\tif(index % 2){\n\t\t\trowEl.classList.add(\"tabulator-row-even\");\n\t\t\trowEl.classList.remove(\"tabulator-row-odd\");\n\t\t}else {\n\t\t\trowEl.classList.add(\"tabulator-row-odd\");\n\t\t\trowEl.classList.remove(\"tabulator-row-even\");\n\t\t}\n\t}\n\n\t///////////////////////////////////\n\t/////// External Triggers /////////\n\t/////// (DO NOT OVERRIDE) /////////\n\t///////////////////////////////////\n\n\tclear(){\n\t\t//clear down existing layout\n\t\tthis.clearRows();\n\t\tthis.clearColumns();\n\t}\n\n\trender(){\n\t\t//render from a clean slate\n\t\tthis.renderRows();\n\t\tthis.renderColumns();\n\t}\n\n\trerender(callback){\n\t\t// rerender and keep position\n\t\tthis.rerenderRows();\n\t\tthis.rerenderColumns();\n\t}\n\n\tscrollToRowPosition(row, position, ifVisible){\n\t\tvar rowIndex = this.rows().indexOf(row),\n\t\trowEl = row.getElement(),\n\t\toffset = 0;\n\n\t\treturn new Promise((resolve, reject) => {\n\t\t\tif(rowIndex > -1){\n\n\t\t\t\tif(typeof ifVisible === \"undefined\"){\n\t\t\t\t\tifVisible = this.table.options.scrollToRowIfVisible;\n\t\t\t\t}\n\n\t\t\t\t//check row visibility\n\t\t\t\tif(!ifVisible){\n\t\t\t\t\tif(Helpers.elVisible(rowEl)){\n\t\t\t\t\t\toffset = Helpers.elOffset(rowEl).top - Helpers.elOffset(this.elementVertical).top;\n\t\t\t\t\t\t\n\t\t\t\t\t\tif(offset > 0 && offset < this.elementVertical.clientHeight - rowEl.offsetHeight){\n\t\t\t\t\t\t\tresolve();\n\t\t\t\t\t\t\treturn false;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\tif(typeof position === \"undefined\"){\n\t\t\t\t\tposition = this.table.options.scrollToRowPosition;\n\t\t\t\t}\n\n\t\t\t\tif(position === \"nearest\"){\n\t\t\t\t\tposition = this.scrollToRowNearestTop(row) ? \"top\" : \"bottom\";\n\t\t\t\t}\n\n\t\t\t\t//scroll to row\n\t\t\t\tthis.scrollToRow(row);\n\n\t\t\t\t//align to correct position\n\t\t\t\tswitch(position){\n\t\t\t\t\tcase \"middle\":\n\t\t\t\t\tcase \"center\":\n\n\t\t\t\t\t\tif(this.elementVertical.scrollHeight - this.elementVertical.scrollTop == this.elementVertical.clientHeight){\n\t\t\t\t\t\t\tthis.elementVertical.scrollTop = this.elementVertical.scrollTop + (rowEl.offsetTop - this.elementVertical.scrollTop) - ((this.elementVertical.scrollHeight - rowEl.offsetTop) / 2);\n\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\tthis.elementVertical.scrollTop = this.elementVertical.scrollTop - (this.elementVertical.clientHeight / 2);\n\t\t\t\t\t\t}\n\n\t\t\t\t\t\tbreak;\n\n\t\t\t\t\tcase \"bottom\":\n\n\t\t\t\t\t\tif(this.elementVertical.scrollHeight - this.elementVertical.scrollTop == this.elementVertical.clientHeight){\n\t\t\t\t\t\t\tthis.elementVertical.scrollTop = this.elementVertical.scrollTop - (this.elementVertical.scrollHeight - rowEl.offsetTop) + rowEl.offsetHeight;\n\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\tthis.elementVertical.scrollTop = this.elementVertical.scrollTop - this.elementVertical.clientHeight + rowEl.offsetHeight;\n\t\t\t\t\t\t}\n\n\t\t\t\t\t\tbreak;\n\n\t\t\t\t\tcase \"top\":\n\t\t\t\t\t\tthis.elementVertical.scrollTop = rowEl.offsetTop;\t\t\t\t\t\n\t\t\t\t\t\tbreak;\n\t\t\t\t}\n\n\t\t\t\tresolve();\n\n\t\t\t}else {\n\t\t\t\tconsole.warn(\"Scroll Error - Row not visible\");\n\t\t\t\treject(\"Scroll Error - Row not visible\");\n\t\t\t}\n\t\t});\n\t}\n}\n\nclass BasicHorizontal extends Renderer{\n\tconstructor(table){\n\t\tsuper(table);\n\t}\n\t\n\trenderRowCells(row, inFragment) {\n\t\tconst rowFrag = document.createDocumentFragment();\n\t\trow.cells.forEach((cell) => {\n\t\t\trowFrag.appendChild(cell.getElement());\n\t\t});\n\t\trow.element.appendChild(rowFrag);\n\t\t\n\t\tif(!inFragment){\n\t\t\trow.cells.forEach((cell) => {\n\t\t\t\tcell.cellRendered();\n\t\t\t});\n\t\t}\n\t}\n\t\n\treinitializeColumnWidths(columns){\n\t\tcolumns.forEach(function(column){\n\t\t\tcolumn.reinitializeWidth();\n\t\t});\n\t}\n}\n\nclass VirtualDomHorizontal extends Renderer{\n\tconstructor(table){\n\t\tsuper(table);\n\t\t\n\t\tthis.leftCol = 0;\n\t\tthis.rightCol = 0;\n\t\tthis.scrollLeft = 0;\n\t\t\n\t\tthis.vDomScrollPosLeft = 0;\n\t\tthis.vDomScrollPosRight = 0;\n\t\t\n\t\tthis.vDomPadLeft = 0;\n\t\tthis.vDomPadRight = 0;\n\t\t\n\t\tthis.fitDataColAvg = 0;\n\t\t\n\t\tthis.windowBuffer = 200; //pixel margin to make column visible before it is shown on screen\n\t\t\n\t\tthis.visibleRows = null;\n\t\t\n\t\tthis.initialized = false;\n\t\tthis.isFitData = false;\n\t\t\n\t\tthis.columns = [];\n\t}\n\t\n\tinitialize(){\n\t\tthis.compatibilityCheck();\n\t\tthis.layoutCheck();\n\t\tthis.vertScrollListen();\n\t}\n\t\n\tcompatibilityCheck(){\t\t\n\t\tif(this.options(\"layout\") == \"fitDataTable\"){\n\t\t\tconsole.warn(\"Horizontal Virtual DOM is not compatible with fitDataTable layout mode\");\n\t\t}\n\t\t\n\t\tif(this.options(\"responsiveLayout\")){\n\t\t\tconsole.warn(\"Horizontal Virtual DOM is not compatible with responsive columns\");\n\t\t}\n\t\t\n\t\tif(this.options(\"rtl\")){\n\t\t\tconsole.warn(\"Horizontal Virtual DOM is not currently compatible with RTL text direction\");\n\t\t}\n\t}\n\t\n\tlayoutCheck(){\n\t\tthis.isFitData = this.options(\"layout\").startsWith('fitData');\n\t}\n\t\n\tvertScrollListen(){\n\t\tthis.subscribe(\"scroll-vertical\", this.clearVisRowCache.bind(this));\n\t\tthis.subscribe(\"data-refreshed\", this.clearVisRowCache.bind(this));\n\t}\n\t\n\tclearVisRowCache(){\n\t\tthis.visibleRows = null;\n\t}\n\t\n\t//////////////////////////////////////\n\t///////// Public Functions ///////////\n\t//////////////////////////////////////\n\t\n\trenderColumns(row, force){\n\t\tthis.dataChange();\n\t}\n\t\n\t\n\tscrollColumns(left, dir){\n\t\tif(this.scrollLeft != left){\n\t\t\tthis.scrollLeft = left;\n\t\t\t\n\t\t\tthis.scroll(left - (this.vDomScrollPosLeft + this.windowBuffer));\n\t\t}\n\t}\n\t\n\tcalcWindowBuffer(){\n\t\tvar buffer = this.elementVertical.clientWidth;\n\t\t\n\t\tthis.table.columnManager.columnsByIndex.forEach((column) => {\n\t\t\tif(column.visible){\n\t\t\t\tvar width = column.getWidth();\n\t\t\t\t\n\t\t\t\tif(width > buffer){\n\t\t\t\t\tbuffer = width;\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\t\t\n\t\tthis.windowBuffer = buffer * 2;\n\t}\n\t\n\trerenderColumns(update, blockRedraw){\t\t\n\t\tvar old = {\n\t\t\tcols:this.columns,\n\t\t\tleftCol:this.leftCol,\n\t\t\trightCol:this.rightCol,\n\t\t},\n\t\tcolPos = 0;\n\t\t\n\t\tif(update && !this.initialized){\n\t\t\treturn;\n\t\t}\n\t\t\n\t\tthis.clear();\n\t\t\n\t\tthis.calcWindowBuffer();\n\t\t\n\t\tthis.scrollLeft = this.elementVertical.scrollLeft;\n\t\t\n\t\tthis.vDomScrollPosLeft = this.scrollLeft - this.windowBuffer;\n\t\tthis.vDomScrollPosRight = this.scrollLeft + this.elementVertical.clientWidth + this.windowBuffer;\n\t\t\n\t\tthis.table.columnManager.columnsByIndex.forEach((column) => {\n\t\t\tvar config = {},\n\t\t\twidth;\n\t\t\t\n\t\t\tif(column.visible){\n\t\t\t\tif(!column.modules.frozen){\t\t\t\n\t\t\t\t\twidth = column.getWidth();\n\n\t\t\t\t\tconfig.leftPos = colPos;\n\t\t\t\t\tconfig.rightPos = colPos + width;\n\t\t\t\t\t\n\t\t\t\t\tconfig.width = width;\n\t\t\t\t\t\n\t\t\t\t\tif (this.isFitData) {\n\t\t\t\t\t\tconfig.fitDataCheck = column.modules.vdomHoz ? column.modules.vdomHoz.fitDataCheck : true;\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\tif((colPos + width > this.vDomScrollPosLeft) && (colPos < this.vDomScrollPosRight)){\n\t\t\t\t\t\t//column is visible\n\t\t\t\t\t\t\n\t\t\t\t\t\tif(this.leftCol == -1){\n\t\t\t\t\t\t\tthis.leftCol = this.columns.length;\n\t\t\t\t\t\t\tthis.vDomPadLeft = colPos;\n\t\t\t\t\t\t}\n\t\t\t\t\t\t\n\t\t\t\t\t\tthis.rightCol = this.columns.length;\n\t\t\t\t\t}else {\n\t\t\t\t\t\t// column is hidden\n\t\t\t\t\t\tif(this.leftCol !== -1){\n\t\t\t\t\t\t\tthis.vDomPadRight += width;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\tthis.columns.push(column);\n\t\t\t\t\t\n\t\t\t\t\tcolumn.modules.vdomHoz = config;\n\t\t\t\t\t\n\t\t\t\t\tcolPos += width;\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\t\t\n\t\tthis.tableElement.style.paddingLeft = this.vDomPadLeft + \"px\";\n\t\tthis.tableElement.style.paddingRight = this.vDomPadRight + \"px\";\n\t\t\n\t\tthis.initialized = true;\n\t\t\n\t\tif(!blockRedraw){\n\t\t\tif(!update || this.reinitChanged(old)){\n\t\t\t\tthis.reinitializeRows();\n\t\t\t}\n\t\t}\n\t\t\n\t\tthis.elementVertical.scrollLeft = this.scrollLeft;\n\t}\n\t\n\trenderRowCells(row){\n\t\tif(this.initialized){\n\t\t\tthis.initializeRow(row);\n\t\t}else {\n\t\t\tconst rowFrag = document.createDocumentFragment();\n\t\t\trow.cells.forEach((cell) => {\n\t\t\t\trowFrag.appendChild(cell.getElement());\n\t\t\t});\n\t\t\trow.element.appendChild(rowFrag);\n\n\t\t\trow.cells.forEach((cell) => {\n\t\t\t\tcell.cellRendered();\n\t\t\t});\n\t\t}\n\t}\n\t\n\trerenderRowCells(row, force){\n\t\tthis.reinitializeRow(row, force);\n\t}\n\t\n\treinitializeColumnWidths(columns){\n\t\tfor(let i = this.leftCol; i <= this.rightCol; i++){\n\t\t\tthis.columns[i].reinitializeWidth();\n\t\t}\n\t}\n\t\n\t//////////////////////////////////////\n\t//////// Internal Rendering //////////\n\t//////////////////////////////////////\n\t\n\tdeinitialize(){\n\t\tthis.initialized = false;\n\t}\n\t\n\tclear(){\n\t\tthis.columns = [];\n\t\t\n\t\tthis.leftCol = -1;\n\t\tthis.rightCol = 0;\n\t\t\n\t\tthis.vDomScrollPosLeft = 0;\n\t\tthis.vDomScrollPosRight = 0;\n\t\tthis.vDomPadLeft = 0;\n\t\tthis.vDomPadRight = 0;\n\t}\n\t\n\tdataChange(){\n\t\tvar change = false,\n\t\trow, rowEl;\n\t\t\n\t\tif(this.isFitData){\n\t\t\tthis.table.columnManager.columnsByIndex.forEach((column) => {\n\t\t\t\tif(!column.definition.width && column.visible){\n\t\t\t\t\tchange = true;\n\t\t\t\t}\n\t\t\t});\n\t\t\t\n\t\t\tif(change && this.table.rowManager.getDisplayRows().length){\n\t\t\t\tthis.vDomScrollPosRight = this.scrollLeft + this.elementVertical.clientWidth + this.windowBuffer;\n\t\t\t\t\n\t\t\t\trow = this.chain(\"rows-sample\", [1], [], () => {\n\t\t\t\t\treturn this.table.rowManager.getDisplayRows();\n\t\t\t\t})[0];\n\t\t\t\t\n\t\t\t\tif(row){\n\t\t\t\t\trowEl = row.getElement();\n\t\t\t\t\t\n\t\t\t\t\trow.generateCells();\n\t\t\t\t\t\n\t\t\t\t\tthis.tableElement.appendChild(rowEl);\n\t\t\t\t\t\n\t\t\t\t\tfor(let colEnd = 0; colEnd < row.cells.length; colEnd++){\n\t\t\t\t\t\tlet cell = row.cells[colEnd];\n\t\t\t\t\t\trowEl.appendChild(cell.getElement());\n\t\t\t\t\t\t\n\t\t\t\t\t\tcell.column.reinitializeWidth();\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\trowEl.parentNode.removeChild(rowEl);\n\t\t\t\t\t\n\t\t\t\t\tthis.rerenderColumns(false, true);\n\t\t\t\t}\n\t\t\t}\n\t\t}else {\n\t\t\tif(this.options(\"layout\") === \"fitColumns\"){\n\t\t\t\tthis.layoutRefresh();\n\t\t\t\tthis.rerenderColumns(false, true);\n\t\t\t}\n\t\t}\n\t}\n\t\n\treinitChanged(old){\n\t\tvar match = true;\n\t\t\n\t\tif(old.cols.length !== this.columns.length || old.leftCol !== this.leftCol || old.rightCol !== this.rightCol){\n\t\t\treturn true;\n\t\t}\n\t\t\n\t\told.cols.forEach((col, i) => {\n\t\t\tif(col !== this.columns[i]){\n\t\t\t\tmatch = false;\n\t\t\t}\n\t\t});\n\t\t\n\t\treturn !match;\n\t}\n\t\n\treinitializeRows(){\n\t\tvar visibleRows = this.getVisibleRows(),\n\t\totherRows = this.table.rowManager.getRows().filter(row => !visibleRows.includes(row));\n\n\t\tvisibleRows.forEach((row) => {\n\t\t\tthis.reinitializeRow(row, true);\n\t\t});\n\n\t\totherRows.forEach((row) =>{\n\t\t\trow.deinitialize();\n\t\t});\n\t}\n\t\n\tgetVisibleRows(){\n\t\tif (!this.visibleRows){\n\t\t\tthis.visibleRows = this.table.rowManager.getVisibleRows();\n\t\t}\n\t\t\n\t\treturn this.visibleRows;\t\n\t}\n\t\n\tscroll(diff){\n\t\tthis.vDomScrollPosLeft += diff;\n\t\tthis.vDomScrollPosRight += diff;\n\t\t\n\t\tif(Math.abs(diff) > (this.windowBuffer / 2)){\n\t\t\tthis.rerenderColumns();\n\t\t}else {\n\t\t\tif(diff > 0){\n\t\t\t\t//scroll right\n\t\t\t\tthis.addColRight();\n\t\t\t\tthis.removeColLeft();\n\t\t\t}else {\n\t\t\t\t//scroll left\n\t\t\t\tthis.addColLeft();\n\t\t\t\tthis.removeColRight();\n\t\t\t}\n\t\t}\n\t}\n\t\n\tcolPositionAdjust (start, end, diff){\n\t\tfor(let i = start; i < end; i++){\n\t\t\tlet column = this.columns[i];\n\t\t\t\n\t\t\tcolumn.modules.vdomHoz.leftPos += diff;\n\t\t\tcolumn.modules.vdomHoz.rightPos += diff;\n\t\t}\n\t}\n\t\n\taddColRight(){\n\t\tvar changes = false,\n\t\tworking = true;\n\t\t\n\t\twhile(working){\n\n\t\t\tlet column = this.columns[this.rightCol + 1];\n\t\t\t\n\t\t\tif(column){\n\t\t\t\tif(column.modules.vdomHoz.leftPos <= this.vDomScrollPosRight){\n\t\t\t\t\tchanges = true;\n\t\t\t\t\t\n\t\t\t\t\tthis.getVisibleRows().forEach((row) => {\n\t\t\t\t\t\tif(row.type !== \"group\"){\n\t\t\t\t\t\t\tvar cell = row.getCell(column);\n\t\t\t\t\t\t\trow.getElement().insertBefore(cell.getElement(), row.getCell(this.columns[this.rightCol]).getElement().nextSibling);\n\t\t\t\t\t\t\tcell.cellRendered();\n\t\t\t\t\t\t}\n\t\t\t\t\t});\n\t\t\t\t\t\n\t\t\t\t\tthis.fitDataColActualWidthCheck(column);\n\t\t\t\t\t\n\t\t\t\t\tthis.rightCol++; // Don't move this below the >= check below\n\n\t\t\t\t\tthis.getVisibleRows().forEach((row) => {\n\t\t\t\t\t\tif(row.type !== \"group\"){\n\t\t\t\t\t\t\trow.modules.vdomHoz.rightCol = this.rightCol;\n\t\t\t\t\t\t}\n\t\t\t\t\t});\n\t\t\t\t\t\n\t\t\t\t\tif(this.rightCol >= (this.columns.length - 1)){\n\t\t\t\t\t\tthis.vDomPadRight = 0;\n\t\t\t\t\t}else {\n\t\t\t\t\t\tthis.vDomPadRight -= column.getWidth();\n\t\t\t\t\t}\t\n\t\t\t\t}else {\n\t\t\t\t\tworking = false;\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tworking = false;\n\t\t\t}\n\t\t}\n\t\t\n\t\tif(changes){\n\t\t\tthis.tableElement.style.paddingRight = this.vDomPadRight + \"px\";\n\t\t}\n\t}\n\t\n\taddColLeft(){\n\t\tvar changes = false,\n\t\tworking = true;\n\t\t\n\t\twhile(working){\n\t\t\tlet column = this.columns[this.leftCol - 1];\n\t\t\t\n\t\t\tif(column){\n\t\t\t\tif(column.modules.vdomHoz.rightPos >= this.vDomScrollPosLeft){\n\t\t\t\t\tchanges = true;\n\t\t\t\t\t\n\t\t\t\t\tthis.getVisibleRows().forEach((row) => {\n\t\t\t\t\t\tif(row.type !== \"group\"){\n\t\t\t\t\t\t\tvar cell = row.getCell(column);\n\t\t\t\t\t\t\trow.getElement().insertBefore(cell.getElement(), row.getCell(this.columns[this.leftCol]).getElement());\n\t\t\t\t\t\t\tcell.cellRendered();\n\t\t\t\t\t\t}\n\t\t\t\t\t});\n\t\t\t\t\t\n\t\t\t\t\tthis.leftCol--; // don't move this below the <= check below\n\n\t\t\t\t\tthis.getVisibleRows().forEach((row) => {\n\t\t\t\t\t\tif(row.type !== \"group\"){\n\t\t\t\t\t\t\trow.modules.vdomHoz.leftCol = this.leftCol;\n\t\t\t\t\t\t}\n\t\t\t\t\t});\n\t\t\t\t\t\n\t\t\t\t\tif(this.leftCol <= 0){ // replicating logic in addColRight\n\t\t\t\t\t\tthis.vDomPadLeft = 0;\n\t\t\t\t\t}else {\n\t\t\t\t\t\tthis.vDomPadLeft -= column.getWidth();\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\tlet diff = this.fitDataColActualWidthCheck(column);\n\t\t\t\t\t\n\t\t\t\t\tif(diff){\n\t\t\t\t\t\tthis.scrollLeft = this.elementVertical.scrollLeft = this.elementVertical.scrollLeft + diff;\n\t\t\t\t\t\tthis.vDomPadRight -= diff;\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t}else {\n\t\t\t\t\tworking = false;\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tworking = false;\n\t\t\t}\n\t\t}\n\t\t\n\t\tif(changes){\n\t\t\tthis.tableElement.style.paddingLeft = this.vDomPadLeft + \"px\";\n\t\t}\n\t}\n\t\n\tremoveColRight(){\n\t\tvar changes = false,\n\t\tworking = true;\n\t\t\n\t\twhile(working){\n\t\t\tlet column = this.columns[this.rightCol];\n\t\t\t\n\t\t\tif(column){\n\t\t\t\tif(column.modules.vdomHoz.leftPos > this.vDomScrollPosRight){\n\t\t\t\t\tchanges = true;\n\t\t\t\t\t\n\t\t\t\t\tthis.getVisibleRows().forEach((row) => {\n\t\t\t\t\t\tif(row.type !== \"group\"){\n\t\t\t\t\t\t\tvar cell = row.getCell(column);\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\t\trow.getElement().removeChild(cell.getElement());\n\t\t\t\t\t\t\t} catch (ex) {\n\t\t\t\t\t\t\t\tconsole.warn(\"Could not removeColRight\", ex.message);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t});\n\t\t\t\t\t\n\t\t\t\t\tthis.vDomPadRight += column.getWidth();\n\t\t\t\t\tthis.rightCol --;\n\n\t\t\t\t\tthis.getVisibleRows().forEach((row) => {\n\t\t\t\t\t\tif(row.type !== \"group\"){\n\t\t\t\t\t\t\trow.modules.vdomHoz.rightCol = this.rightCol;\n\t\t\t\t\t\t}\n\t\t\t\t\t});\n\t\t\t\t}else {\n\t\t\t\t\tworking = false;\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tworking = false;\n\t\t\t}\n\t\t}\n\t\t\n\t\tif(changes){\n\t\t\tthis.tableElement.style.paddingRight = this.vDomPadRight + \"px\";\n\t\t}\n\t}\n\t\n\tremoveColLeft(){\n\t\tvar changes = false,\n\t\tworking = true;\n\n\t\twhile(working){\n\t\t\tlet column = this.columns[this.leftCol];\n\t\t\t\n\t\t\tif(column){\n\t\t\t\tif(column.modules.vdomHoz.rightPos < this.vDomScrollPosLeft){\n\t\t\t\t\tchanges = true;\n\t\t\t\t\t\n\t\t\t\t\tthis.getVisibleRows().forEach((row) => {\t\t\t\t\t\n\t\t\t\t\t\tif(row.type !== \"group\"){\n\t\t\t\t\t\t\tvar cell = row.getCell(column);\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\t\trow.getElement().removeChild(cell.getElement());\n\t\t\t\t\t\t\t} catch (ex) {\n\t\t\t\t\t\t\t\tconsole.warn(\"Could not removeColLeft\", ex.message);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t});\n\t\t\t\t\t\n\t\t\t\t\tthis.vDomPadLeft += column.getWidth();\n\t\t\t\t\tthis.leftCol ++;\n\n\t\t\t\t\tthis.getVisibleRows().forEach((row) => {\n\t\t\t\t\t\tif(row.type !== \"group\"){\n\t\t\t\t\t\t\trow.modules.vdomHoz.leftCol = this.leftCol;\n\t\t\t\t\t\t}\n\t\t\t\t\t});\n\t\t\t\t}else {\n\t\t\t\t\tworking = false;\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tworking = false;\n\t\t\t}\n\t\t}\n\t\t\n\t\tif(changes){\n\t\t\tthis.tableElement.style.paddingLeft = this.vDomPadLeft + \"px\";\n\t\t}\n\t}\n\t\n\tfitDataColActualWidthCheck(column){\n\t\tvar newWidth, widthDiff;\n\t\t\n\t\tif(column.modules.vdomHoz.fitDataCheck){\n\t\t\tcolumn.reinitializeWidth();\n\t\t\t\n\t\t\tnewWidth = column.getWidth();\n\t\t\twidthDiff = newWidth - column.modules.vdomHoz.width;\n\t\t\t\n\t\t\tif(widthDiff){\n\t\t\t\tcolumn.modules.vdomHoz.rightPos += widthDiff;\n\t\t\t\tcolumn.modules.vdomHoz.width = newWidth;\n\t\t\t\tthis.colPositionAdjust(this.columns.indexOf(column) + 1, this.columns.length, widthDiff);\n\t\t\t}\n\t\t\t\n\t\t\tcolumn.modules.vdomHoz.fitDataCheck = false;\n\t\t}\n\t\t\n\t\treturn widthDiff;\n\t}\n\t\n\tinitializeRow(row){\n\t\tif(row.type !== \"group\"){\n\t\t\trow.modules.vdomHoz = {\n\t\t\t\tleftCol:this.leftCol,\n\t\t\t\trightCol:this.rightCol,\n\t\t\t};\n\n\t\t\tif(this.table.modules.frozenColumns){\n\t\t\t\tthis.table.modules.frozenColumns.leftColumns.forEach((column) => {\n\t\t\t\t\tthis.appendCell(row, column);\n\t\t\t\t});\n\t\t\t}\n\n\t\t\tfor(let i = this.leftCol; i <= this.rightCol; i++){\n\t\t\t\tthis.appendCell(row, this.columns[i]);\n\t\t\t}\n\n\t\t\tif(this.table.modules.frozenColumns){\n\t\t\t\tthis.table.modules.frozenColumns.rightColumns.forEach((column) => {\n\t\t\t\t\tthis.appendCell(row, column);\n\t\t\t\t});\n\t\t\t}\n\t\t}\n\t}\n\t\n\tappendCell(row, column){\n\t\tif(column && column.visible){\n\t\t\tlet cell = row.getCell(column);\n\t\t\t\n\t\t\trow.getElement().appendChild(cell.getElement());\n\t\t\tcell.cellRendered();\n\t\t}\n\t}\n\t\n\treinitializeRow(row, force){\n\t\tif(row.type !== \"group\"){\n\t\t\tif(force || !row.modules.vdomHoz || row.modules.vdomHoz.leftCol !== this.leftCol || row.modules.vdomHoz.rightCol !== this.rightCol){\n\t\t\t\t\n\t\t\t\tvar rowEl = row.getElement();\n\t\t\t\twhile(rowEl.firstChild) rowEl.removeChild(rowEl.firstChild);\n\n\t\t\t\tthis.initializeRow(row);\n\t\t\t}\n\t\t}\n\t}\n}\n\nclass ColumnManager extends CoreFeature {\n\t\n\tconstructor (table){\n\t\tsuper(table);\n\t\t\n\t\tthis.blockHozScrollEvent = false;\n\t\tthis.headersElement = null;\n\t\tthis.contentsElement = null;\n\t\tthis.element = null ; //containing element\n\t\tthis.columns = []; // column definition object\n\t\tthis.columnsByIndex = []; //columns by index\n\t\tthis.columnsByField = {}; //columns by field\n\t\tthis.scrollLeft = 0;\n\t\tthis.optionsList = new OptionsList(this.table, \"column definition\", defaultColumnOptions);\n\t\t\n\t\tthis.redrawBlock = false; //prevent redraws to allow multiple data manipulations before continuing\n\t\tthis.redrawBlockUpdate = null; //store latest redraw update only status\n\t\t\n\t\tthis.renderer = null;\n\t}\n\t\n\t////////////// Setup Functions /////////////////\n\t\n\tinitialize(){\n\t\tthis.initializeRenderer();\n\t\t\n\t\tthis.headersElement = this.createHeadersElement();\n\t\tthis.contentsElement = this.createHeaderContentsElement();\n\t\tthis.element = this.createHeaderElement();\n\t\t\n\t\tthis.contentsElement.insertBefore(this.headersElement, this.contentsElement.firstChild);\n\t\tthis.element.insertBefore(this.contentsElement, this.element.firstChild);\n\n\t\tthis.initializeScrollWheelWatcher();\n\t\t\n\t\tthis.subscribe(\"scroll-horizontal\", this.scrollHorizontal.bind(this));\n\t\tthis.subscribe(\"scrollbar-vertical\", this.padVerticalScrollbar.bind(this));\n\t}\n\n\tpadVerticalScrollbar(width){\n\t\tif(this.table.rtl){\n\t\t\tthis.headersElement.style.marginLeft = width + \"px\";\n\t\t}else {\n\t\t\tthis.headersElement.style.marginRight = width + \"px\";\n\t\t}\n\t}\n\t\n\tinitializeRenderer(){\n\t\tvar renderClass;\n\t\t\n\t\tvar renderers = {\n\t\t\t\"virtual\": VirtualDomHorizontal,\n\t\t\t\"basic\": BasicHorizontal,\n\t\t};\n\t\t\n\t\tif(typeof this.table.options.renderHorizontal === \"string\"){\n\t\t\trenderClass = renderers[this.table.options.renderHorizontal];\n\t\t}else {\n\t\t\trenderClass = this.table.options.renderHorizontal;\n\t\t}\n\t\t\n\t\tif(renderClass){\n\t\t\tthis.renderer = new renderClass(this.table, this.element, this.tableElement);\n\t\t\tthis.renderer.initialize();\n\t\t}else {\n\t\t\tconsole.error(\"Unable to find matching renderer:\", this.table.options.renderHorizontal);\n\t\t}\n\t}\n\t\n\t\n\tcreateHeadersElement (){\n\t\tvar el = document.createElement(\"div\");\n\t\t\n\t\tel.classList.add(\"tabulator-headers\");\n\t\tel.setAttribute(\"role\", \"row\");\n\t\t\n\t\treturn el;\n\t}\n\n\tcreateHeaderContentsElement (){\n\t\tvar el = document.createElement(\"div\");\n\t\t\n\t\tel.classList.add(\"tabulator-header-contents\");\n\t\tel.setAttribute(\"role\", \"rowgroup\");\n\t\t\n\t\treturn el;\n\t}\n\t\n\tcreateHeaderElement (){\n\t\tvar el = document.createElement(\"div\");\n\t\t\n\t\tel.classList.add(\"tabulator-header\");\n\t\tel.setAttribute(\"role\", \"rowgroup\");\n\t\t\n\t\tif(!this.table.options.headerVisible){\n\t\t\tel.classList.add(\"tabulator-header-hidden\");\n\t\t}\n\t\t\n\t\treturn el;\n\t}\n\t\n\t//return containing element\n\tgetElement(){\n\t\treturn this.element;\n\t}\n\n\t//return containing contents element\n\tgetContentsElement(){\n\t\treturn this.contentsElement;\n\t}\n\t\n\t\n\t//return header containing element\n\tgetHeadersElement(){\n\t\treturn this.headersElement;\n\t}\n\t\n\t//scroll horizontally to match table body\n\tscrollHorizontal(left){\n\t\tthis.contentsElement.scrollLeft = left;\n\n\t\tthis.scrollLeft = left;\n\t\t\n\t\tthis.renderer.scrollColumns(left);\n\t}\n\n\tinitializeScrollWheelWatcher(){\n\t\tthis.contentsElement.addEventListener(\"wheel\", (e) => {\n\t\t\tvar left;\n\n\t\t\tif(e.deltaX){\n\t\t\t\tleft = this.contentsElement.scrollLeft + e.deltaX;\n\n\t\t\t\tthis.table.rowManager.scrollHorizontal(left);\n\t\t\t\tthis.table.columnManager.scrollHorizontal(left);\n\t\t\t}\n\t\t});\n\t}\n\t\n\t///////////// Column Setup Functions /////////////\n\tgenerateColumnsFromRowData(data){\n\t\tvar cols = [],\n\t\tdefinitions = this.table.options.autoColumnsDefinitions,\n\t\trow, sorter;\n\t\t\n\t\tif(data && data.length){\n\t\t\t\n\t\t\trow = data[0];\n\t\t\t\n\t\t\tfor(var key in row){\n\t\t\t\tlet col = {\n\t\t\t\t\tfield:key,\n\t\t\t\t\ttitle:key,\n\t\t\t\t};\n\t\t\t\t\n\t\t\t\tlet value = row[key];\n\t\t\t\t\n\t\t\t\tswitch(typeof value){\n\t\t\t\t\tcase \"undefined\":\n\t\t\t\t\t\tsorter = \"string\";\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t\n\t\t\t\t\tcase \"boolean\":\n\t\t\t\t\t\tsorter = \"boolean\";\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t\n\t\t\t\t\tcase \"object\":\n\t\t\t\t\t\tif(Array.isArray(value)){\n\t\t\t\t\t\t\tsorter = \"array\";\n\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\tsorter = \"string\";\n\t\t\t\t\t\t}\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t\n\t\t\t\t\tdefault:\n\t\t\t\t\t\tif(!isNaN(value) && value !== \"\"){\n\t\t\t\t\t\t\tsorter = \"number\";\n\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\tif(value.match(/((^[0-9]+[a-z]+)|(^[a-z]+[0-9]+))+$/i)){\n\t\t\t\t\t\t\t\tsorter = \"alphanum\";\n\t\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\t\tsorter = \"string\";\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tcol.sorter = sorter;\n\t\t\t\t\n\t\t\t\tcols.push(col);\n\t\t\t}\n\t\t\t\n\t\t\tif(definitions){\n\t\t\t\t\n\t\t\t\tswitch(typeof definitions){\n\t\t\t\t\tcase \"function\":\n\t\t\t\t\t\tthis.table.options.columns = definitions.call(this.table, cols);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t\n\t\t\t\t\tcase \"object\":\n\t\t\t\t\t\tif(Array.isArray(definitions)){\n\t\t\t\t\t\t\tcols.forEach((col) => {\n\t\t\t\t\t\t\t\tvar match = definitions.find((def) => {\n\t\t\t\t\t\t\t\t\treturn def.field === col.field;\n\t\t\t\t\t\t\t\t});\n\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\tif(match){\n\t\t\t\t\t\t\t\t\tObject.assign(col, match);\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t});\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\tcols.forEach((col) => {\n\t\t\t\t\t\t\t\tif(definitions[col.field]){\n\t\t\t\t\t\t\t\t\tObject.assign(col, definitions[col.field]);\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t});\n\t\t\t\t\t\t}\n\t\t\t\t\t\t\n\t\t\t\t\t\tthis.table.options.columns = cols;\n\t\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tthis.table.options.columns = cols;\n\t\t\t}\n\t\t\t\n\t\t\tthis.setColumns(this.table.options.columns);\n\t\t}\n\t}\n\t\n\tsetColumns(cols, row){\n\t\twhile(this.headersElement.firstChild) this.headersElement.removeChild(this.headersElement.firstChild);\n\t\t\n\t\tthis.columns = [];\n\t\tthis.columnsByIndex = [];\n\t\tthis.columnsByField = {};\n\t\t\n\t\tthis.dispatch(\"columns-loading\");\n\t\t\n\t\tcols.forEach((def, i) => {\n\t\t\tthis._addColumn(def);\n\t\t});\n\t\t\n\t\tthis._reIndexColumns();\n\t\t\n\t\tthis.dispatch(\"columns-loaded\");\n\t\t\n\t\tthis.rerenderColumns(false, true);\n\t\t\n\t\tthis.redraw(true);\n\t}\n\t\n\t_addColumn(definition, before, nextToColumn){\n\t\tvar column = new Column(definition, this),\n\t\tcolEl = column.getElement(),\n\t\tindex = nextToColumn ? this.findColumnIndex(nextToColumn) : nextToColumn;\n\t\t\n\t\tif(nextToColumn && index > -1){\n\t\t\tvar topColumn = nextToColumn.getTopColumn();\n\t\t\tvar parentIndex = this.columns.indexOf(topColumn);\n\t\t\tvar nextEl = topColumn.getElement();\n\t\t\t\n\t\t\tif(before){\n\t\t\t\tthis.columns.splice(parentIndex, 0, column);\n\t\t\t\tnextEl.parentNode.insertBefore(colEl, nextEl);\n\t\t\t}else {\n\t\t\t\tthis.columns.splice(parentIndex + 1, 0, column);\n\t\t\t\tnextEl.parentNode.insertBefore(colEl, nextEl.nextSibling);\n\t\t\t}\n\t\t}else {\n\t\t\tif(before){\n\t\t\t\tthis.columns.unshift(column);\n\t\t\t\tthis.headersElement.insertBefore(column.getElement(), this.headersElement.firstChild);\n\t\t\t}else {\n\t\t\t\tthis.columns.push(column);\n\t\t\t\tthis.headersElement.appendChild(column.getElement());\n\t\t\t}\n\t\t}\n\t\t\n\t\tcolumn.columnRendered();\n\t\t\n\t\treturn column;\n\t}\n\t\n\tregisterColumnField(col){\n\t\tif(col.definition.field){\n\t\t\tthis.columnsByField[col.definition.field] = col;\n\t\t}\n\t}\n\t\n\tregisterColumnPosition(col){\n\t\tthis.columnsByIndex.push(col);\n\t}\n\t\n\t_reIndexColumns(){\n\t\tthis.columnsByIndex = [];\n\t\t\n\t\tthis.columns.forEach(function(column){\n\t\t\tcolumn.reRegisterPosition();\n\t\t});\n\t}\n\t\n\t//ensure column headers take up the correct amount of space in column groups\n\tverticalAlignHeaders(){\n\t\tvar minHeight = 0;\n\t\t\n\t\tif(!this.redrawBlock){\n\n\t\t\tthis.headersElement.style.height=\"\";\n\t\t\t\n\t\t\tthis.columns.forEach((column) => {\n\t\t\t\tcolumn.clearVerticalAlign();\n\t\t\t});\n\t\t\t\n\t\t\tthis.columns.forEach((column) => {\n\t\t\t\tvar height = column.getHeight();\n\t\t\t\t\n\t\t\t\tif(height > minHeight){\n\t\t\t\t\tminHeight = height;\n\t\t\t\t}\n\t\t\t});\n\n\t\t\tthis.headersElement.style.height = minHeight + \"px\";\n\n\t\t\tthis.columns.forEach((column) => {\n\t\t\t\tcolumn.verticalAlign(this.table.options.columnHeaderVertAlign, minHeight);\n\t\t\t});\n\t\t\t\n\t\t\tthis.table.rowManager.adjustTableSize();\n\t\t}\n\t}\n\t\n\t//////////////// Column Details /////////////////\n\tfindColumn(subject){\n\t\tvar columns;\n\n\t\tif(typeof subject == \"object\"){\n\t\t\t\n\t\t\tif(subject instanceof Column){\n\t\t\t\t//subject is column element\n\t\t\t\treturn subject;\n\t\t\t}else if(subject instanceof ColumnComponent){\n\t\t\t\t//subject is public column component\n\t\t\t\treturn subject._getSelf() || false;\n\t\t\t}else if(typeof HTMLElement !== \"undefined\" && subject instanceof HTMLElement){\n\n\t\t\t\tcolumns = [];\n\n\t\t\t\tthis.columns.forEach((column) => {\n\t\t\t\t\tcolumns.push(column);\n\t\t\t\t\tcolumns = columns.concat(column.getColumns(true));\n\t\t\t\t});\n\n\t\t\t\t//subject is a HTML element of the column header\n\t\t\t\tlet match = columns.find((column) => {\n\t\t\t\t\treturn column.element === subject;\n\t\t\t\t});\n\t\t\t\t\n\t\t\t\treturn match || false;\n\t\t\t}\n\t\t\t\n\t\t}else {\n\t\t\t//subject should be treated as the field name of the column\n\t\t\treturn this.columnsByField[subject] || false;\n\t\t}\n\t\t\n\t\t//catch all for any other type of input\n\t\treturn false;\n\t}\n\t\n\tgetColumnByField(field){\n\t\treturn this.columnsByField[field];\n\t}\n\t\n\tgetColumnsByFieldRoot(root){\n\t\tvar matches = [];\n\t\t\n\t\tObject.keys(this.columnsByField).forEach((field) => {\n\t\t\tvar fieldRoot = this.table.options.nestedFieldSeparator ? field.split(this.table.options.nestedFieldSeparator)[0] : field;\n\t\t\tif(fieldRoot === root){\n\t\t\t\tmatches.push(this.columnsByField[field]);\n\t\t\t}\n\t\t});\n\t\t\n\t\treturn matches;\n\t}\n\t\n\tgetColumnByIndex(index){\n\t\treturn this.columnsByIndex[index];\n\t}\n\t\n\tgetFirstVisibleColumn(){\n\t\tvar index = this.columnsByIndex.findIndex((col) => {\n\t\t\treturn col.visible;\n\t\t});\n\t\t\n\t\treturn index > -1 ? this.columnsByIndex[index] : false;\n\t}\n\n\tgetVisibleColumnsByIndex() {\n\t\treturn this.columnsByIndex.filter((col) => col.visible);\n\t}\n\t\n\tgetColumns(){\n\t\treturn this.columns;\n\t}\n\t\n\tfindColumnIndex(column){\n\t\treturn this.columnsByIndex.findIndex((col) => {\n\t\t\treturn column === col;\n\t\t});\n\t}\n\t\n\t//return all columns that are not groups\n\tgetRealColumns(){\n\t\treturn this.columnsByIndex;\n\t}\n\t\n\t//traverse across columns and call action\n\ttraverse(callback){\n\t\tthis.columnsByIndex.forEach((column,i) =>{\n\t\t\tcallback(column, i);\n\t\t});\n\t}\n\t\n\t//get definitions of actual columns\n\tgetDefinitions(active){\n\t\tvar output = [];\n\t\t\n\t\tthis.columnsByIndex.forEach((column) => {\n\t\t\tif(!active || (active && column.visible)){\n\t\t\t\toutput.push(column.getDefinition());\n\t\t\t}\n\t\t});\n\t\t\n\t\treturn output;\n\t}\n\t\n\t//get full nested definition tree\n\tgetDefinitionTree(){\n\t\tvar output = [];\n\t\t\n\t\tthis.columns.forEach((column) => {\n\t\t\toutput.push(column.getDefinition(true));\n\t\t});\n\t\t\n\t\treturn output;\n\t}\n\t\n\tgetComponents(structured){\n\t\tvar output = [],\n\t\tcolumns = structured ? this.columns : this.columnsByIndex;\n\t\t\n\t\tcolumns.forEach((column) => {\n\t\t\toutput.push(column.getComponent());\n\t\t});\n\t\t\n\t\treturn output;\n\t}\n\t\n\tgetWidth(){\n\t\tvar width = 0;\n\t\t\n\t\tthis.columnsByIndex.forEach((column) => {\n\t\t\tif(column.visible){\n\t\t\t\twidth += column.getWidth();\n\t\t\t}\n\t\t});\n\t\t\n\t\treturn width;\n\t}\n\t\n\tmoveColumn(from, to, after){\n\t\tto.element.parentNode.insertBefore(from.element, to.element);\n\t\t\n\t\tif(after){\n\t\t\tto.element.parentNode.insertBefore(to.element, from.element);\n\t\t}\n\t\t\n\t\tthis.moveColumnActual(from, to, after);\n\n\t\tthis.verticalAlignHeaders();\n\t\t\n\t\tthis.table.rowManager.reinitialize();\n\t}\n\t\n\tmoveColumnActual(from, to, after){\n\t\tif(from.parent.isGroup){\n\t\t\tthis._moveColumnInArray(from.parent.columns, from, to, after);\n\t\t}else {\n\t\t\tthis._moveColumnInArray(this.columns, from, to, after);\n\t\t}\n\t\t\n\t\tthis._moveColumnInArray(this.columnsByIndex, from, to, after, true);\n\t\t\n\t\tthis.rerenderColumns(true);\n\t\t\n\t\tthis.dispatch(\"column-moved\", from, to, after);\n\t\t\n\t\tif(this.subscribedExternal(\"columnMoved\")){\n\t\t\tthis.dispatchExternal(\"columnMoved\", from.getComponent(), this.table.columnManager.getComponents());\n\t\t}\n\t}\n\t\n\t_moveColumnInArray(columns, from, to, after, updateRows){\n\t\tvar\tfromIndex = columns.indexOf(from),\n\t\ttoIndex, rows = [];\n\t\t\n\t\tif (fromIndex > -1) {\n\t\t\t\n\t\t\tcolumns.splice(fromIndex, 1);\n\t\t\t\n\t\t\ttoIndex = columns.indexOf(to);\n\t\t\t\n\t\t\tif (toIndex > -1) {\n\t\t\t\t\n\t\t\t\tif(after){\n\t\t\t\t\ttoIndex = toIndex+1;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t}else {\n\t\t\t\ttoIndex = fromIndex;\n\t\t\t}\n\t\t\t\n\t\t\tcolumns.splice(toIndex, 0, from);\n\t\t\t\n\t\t\tif(updateRows){\n\t\t\t\t\n\t\t\t\trows = this.chain(\"column-moving-rows\", [from, to, after], null, []) || [];\n\t\t\t\t\n\t\t\t\trows = rows.concat(this.table.rowManager.rows);\n\t\t\t\t\n\t\t\t\trows.forEach(function(row){\n\t\t\t\t\tif(row.cells.length){\n\t\t\t\t\t\tvar cell = row.cells.splice(fromIndex, 1)[0];\n\t\t\t\t\t\trow.cells.splice(toIndex, 0, cell);\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t\t\n\t\t\t}\n\t\t}\n\t}\n\t\n\tscrollToColumn(column, position, ifVisible){\n\t\tvar left = 0,\n\t\toffset = column.getLeftOffset(),\n\t\tadjust = 0,\n\t\tcolEl = column.getElement();\n\t\t\n\t\t\n\t\treturn new Promise((resolve, reject) => {\n\t\t\t\n\t\t\tif(typeof position === \"undefined\"){\n\t\t\t\tposition = this.table.options.scrollToColumnPosition;\n\t\t\t}\n\t\t\t\n\t\t\tif(typeof ifVisible === \"undefined\"){\n\t\t\t\tifVisible = this.table.options.scrollToColumnIfVisible;\n\t\t\t}\n\t\t\t\n\t\t\tif(column.visible){\n\t\t\t\t\n\t\t\t\t//align to correct position\n\t\t\t\tswitch(position){\n\t\t\t\t\tcase \"middle\":\n\t\t\t\t\tcase \"center\":\n\t\t\t\t\t\tadjust = -this.element.clientWidth / 2;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t\n\t\t\t\t\tcase \"right\":\n\t\t\t\t\t\tadjust = colEl.clientWidth - this.headersElement.clientWidth;\n\t\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t//check column visibility\n\t\t\t\tif(!ifVisible){\n\t\t\t\t\tif(offset > 0 && offset + colEl.offsetWidth < this.element.clientWidth){\n\t\t\t\t\t\treturn false;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t//calculate scroll position\n\t\t\t\tleft = offset + adjust;\n\t\t\t\t\n\t\t\t\tleft = Math.max(Math.min(left, this.table.rowManager.element.scrollWidth - this.table.rowManager.element.clientWidth),0);\n\t\t\t\t\n\t\t\t\tthis.table.rowManager.scrollHorizontal(left);\n\t\t\t\tthis.scrollHorizontal(left);\n\t\t\t\t\n\t\t\t\tresolve();\n\t\t\t}else {\n\t\t\t\tconsole.warn(\"Scroll Error - Column not visible\");\n\t\t\t\treject(\"Scroll Error - Column not visible\");\n\t\t\t}\n\t\t\t\n\t\t});\n\t}\n\t\n\t//////////////// Cell Management /////////////////\n\tgenerateCells(row){\n\t\tvar cells = [];\n\t\t\n\t\tthis.columnsByIndex.forEach((column) => {\n\t\t\tcells.push(column.generateCell(row));\n\t\t});\n\t\t\n\t\treturn cells;\n\t}\n\t\n\t//////////////// Column Management /////////////////\n\tgetFlexBaseWidth(){\n\t\tvar totalWidth = this.table.element.clientWidth, //table element width\n\t\tfixedWidth = 0;\n\t\t\n\t\t//adjust for vertical scrollbar if present\n\t\tif(this.table.rowManager.element.scrollHeight > this.table.rowManager.element.clientHeight){\n\t\t\ttotalWidth -= this.table.rowManager.element.offsetWidth - this.table.rowManager.element.clientWidth;\n\t\t}\n\t\t\n\t\tthis.columnsByIndex.forEach(function(column){\n\t\t\tvar width, minWidth, colWidth;\n\t\t\t\n\t\t\tif(column.visible){\n\t\t\t\t\n\t\t\t\twidth = column.definition.width || 0;\n\t\t\t\t\n\t\t\t\tminWidth = parseInt(column.minWidth);\n\t\t\t\t\n\t\t\t\tif(typeof(width) == \"string\"){\n\t\t\t\t\tif(width.indexOf(\"%\") > -1){\n\t\t\t\t\t\tcolWidth = (totalWidth / 100) * parseInt(width) ;\n\t\t\t\t\t}else {\n\t\t\t\t\t\tcolWidth = parseInt(width);\n\t\t\t\t\t}\n\t\t\t\t}else {\n\t\t\t\t\tcolWidth = width;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tfixedWidth += colWidth > minWidth ? colWidth : minWidth;\n\t\t\t\t\n\t\t\t}\n\t\t});\n\t\t\n\t\treturn fixedWidth;\n\t}\n\t\n\taddColumn(definition, before, nextToColumn){\n\t\treturn new Promise((resolve, reject) => {\n\t\t\tvar column = this._addColumn(definition, before, nextToColumn);\n\t\t\t\n\t\t\tthis._reIndexColumns();\n\t\t\t\n\t\t\tthis.dispatch(\"column-add\", definition, before, nextToColumn);\n\t\t\t\n\t\t\tif(this.layoutMode() != \"fitColumns\"){\n\t\t\t\tcolumn.reinitializeWidth();\n\t\t\t}\n\t\t\t\n\t\t\tthis.redraw(true);\n\t\t\t\n\t\t\tthis.table.rowManager.reinitialize();\n\t\t\t\n\t\t\tthis.rerenderColumns();\n\t\t\t\n\t\t\tresolve(column);\n\t\t});\n\t}\n\t\n\t//remove column from system\n\tderegisterColumn(column){\n\t\tvar field = column.getField(),\n\t\tindex;\n\t\t\n\t\t//remove from field list\n\t\tif(field){\n\t\t\tdelete this.columnsByField[field];\n\t\t}\n\t\t\n\t\t//remove from index list\n\t\tindex = this.columnsByIndex.indexOf(column);\n\t\t\n\t\tif(index > -1){\n\t\t\tthis.columnsByIndex.splice(index, 1);\n\t\t}\n\t\t\n\t\t//remove from column list\n\t\tindex = this.columns.indexOf(column);\n\t\t\n\t\tif(index > -1){\n\t\t\tthis.columns.splice(index, 1);\n\t\t}\n\t\t\n\t\tthis.verticalAlignHeaders();\n\t\t\n\t\tthis.redraw();\n\t}\n\t\n\trerenderColumns(update, silent){\n\t\tif(!this.redrawBlock){\n\t\t\tthis.renderer.rerenderColumns(update, silent);\n\t\t}else {\n\t\t\tif(update === false || (update === true && this.redrawBlockUpdate === null)){\n\t\t\t\tthis.redrawBlockUpdate = update;\n\t\t\t}\n\t\t}\n\t}\n\t\n\tblockRedraw(){\n\t\tthis.redrawBlock = true;\n\t\tthis.redrawBlockUpdate = null;\n\t}\n\t\n\trestoreRedraw(){\n\t\tthis.redrawBlock = false;\n\t\tthis.verticalAlignHeaders();\n\t\tthis.renderer.rerenderColumns(this.redrawBlockUpdate);\n\t\t\n\t}\n\t\n\t//redraw columns\n\tredraw(force){\n\t\tif(Helpers.elVisible(this.element)){\n\t\t\tthis.verticalAlignHeaders();\n\t\t}\n\t\t\n\t\tif(force){\n\t\t\tthis.table.rowManager.resetScroll();\n\t\t\tthis.table.rowManager.reinitialize();\n\t\t}\n\t\t\n\t\tif(!this.confirm(\"table-redrawing\", force)){\n\t\t\tthis.layoutRefresh(force);\n\t\t}\n\t\t\n\t\tthis.dispatch(\"table-redraw\", force);\n\t\t\n\t\tthis.table.footerManager.redraw();\n\t}\n}\n\nclass BasicVertical extends Renderer{\n\tconstructor(table){\n\t\tsuper(table);\n\t\t\n\t\tthis.verticalFillMode = \"fill\";\n\t\t\n\t\tthis.scrollTop = 0;\n\t\tthis.scrollLeft = 0;\n\t\t\n\t\tthis.scrollTop = 0;\n\t\tthis.scrollLeft = 0;\n\t}\n\t\n\tclearRows(){\n\t\tvar element = this.tableElement;\n\t\t\n\t\t// element.children.detach();\n\t\twhile(element.firstChild) element.removeChild(element.firstChild);\n\t\t\n\t\telement.scrollTop = 0;\n\t\telement.scrollLeft = 0;\n\t\t\n\t\telement.style.minWidth = \"\";\n\t\telement.style.minHeight = \"\";\n\t\telement.style.display = \"\";\n\t\telement.style.visibility = \"\";\n\t}\n\t\n\trenderRows() {\n\t\tvar element = this.tableElement,\n\t\tonlyGroupHeaders = true,\n\t\ttableFrag = document.createDocumentFragment(),\n\t\trows = this.rows();\n\t\t\n\t\trows.forEach((row, index) => {\n\t\t\tthis.styleRow(row, index);\n\t\t\trow.initialize(false, true);\n\t\t\t\n\t\t\tif (row.type !== \"group\") {\n\t\t\t\tonlyGroupHeaders = false;\n\t\t\t}\n\t\t\t\n\t\t\ttableFrag.appendChild(row.getElement());\n\t\t});\n\t\t\n\t\telement.appendChild(tableFrag);\n\t\t\n\t\trows.forEach((row) => {\n\t\t\trow.rendered();\n\t\t\t\n\t\t\tif(!row.heightInitialized) {\n\t\t\t\trow.calcHeight(true);\n\t\t\t}\n\t\t});\n\t\t\n\t\trows.forEach((row) => {\n\t\t\tif(!row.heightInitialized) {\n\t\t\t\trow.setCellHeight();\n\t\t\t}\n\t\t});\n\t\t\n\t\tif(onlyGroupHeaders){\n\t\t\telement.style.minWidth = this.table.columnManager.getWidth() + \"px\";\n\t\t}else {\n\t\t\telement.style.minWidth = \"\";\n\t\t}\n\t}\n\t\n\t\n\trerenderRows(callback){\t\n\t\tthis.clearRows();\n\t\t\n\t\tif(callback){\n\t\t\tcallback();\n\t\t}\n\t\t\n\t\tthis.renderRows();\n\n\t\tif(!this.rows().length){\n\t\t\tthis.table.rowManager.tableEmpty();\n\t\t}\n\t}\n\t\n\tscrollToRowNearestTop(row){\n\t\tvar rowTop = Helpers.elOffset(row.getElement()).top;\n\t\t\n\t\treturn !(Math.abs(this.elementVertical.scrollTop - rowTop) > Math.abs(this.elementVertical.scrollTop + this.elementVertical.clientHeight - rowTop));\n\t}\n\t\n\tscrollToRow(row){\n\t\tvar rowEl = row.getElement();\n\t\t\n\t\tthis.elementVertical.scrollTop = Helpers.elOffset(rowEl).top - Helpers.elOffset(this.elementVertical).top + this.elementVertical.scrollTop;\n\t}\n\t\n\tvisibleRows(includingBuffer){\n\t\treturn this.rows();\n\t}\n\t\n}\n\nclass VirtualDomVertical extends Renderer{\n\tconstructor(table){\n\t\tsuper(table);\n\n\t\tthis.verticalFillMode = \"fill\";\n\n\t\tthis.scrollTop = 0;\n\t\tthis.scrollLeft = 0;\n\n\t\tthis.vDomRowHeight = 20; //approximation of row heights for padding\n\n\t\tthis.vDomTop = 0; //hold position for first rendered row in the virtual DOM\n\t\tthis.vDomBottom = 0; //hold position for last rendered row in the virtual DOM\n\n\t\tthis.vDomScrollPosTop = 0; //last scroll position of the vDom top;\n\t\tthis.vDomScrollPosBottom = 0; //last scroll position of the vDom bottom;\n\n\t\tthis.vDomTopPad = 0; //hold value of padding for top of virtual DOM\n\t\tthis.vDomBottomPad = 0; //hold value of padding for bottom of virtual DOM\n\n\t\tthis.vDomMaxRenderChain = 90; //the maximum number of dom elements that can be rendered in 1 go\n\n\t\tthis.vDomWindowBuffer = 0; //window row buffer before removing elements, to smooth scrolling\n\n\t\tthis.vDomWindowMinTotalRows = 20; //minimum number of rows to be generated in virtual dom (prevent buffering issues on tables with tall rows)\n\t\tthis.vDomWindowMinMarginRows = 5; //minimum number of rows to be generated in virtual dom margin\n\n\t\tthis.vDomTopNewRows = []; //rows to normalize after appending to optimize render speed\n\t\tthis.vDomBottomNewRows = []; //rows to normalize after appending to optimize render speed\n\t}\n\n\t//////////////////////////////////////\n\t///////// Public Functions ///////////\n\t//////////////////////////////////////\n\n\tclearRows(){\n\t\tvar element = this.tableElement;\n\n\t\t// element.children.detach();\n\t\twhile(element.firstChild) element.removeChild(element.firstChild);\n\n\t\telement.style.paddingTop = \"\";\n\t\telement.style.paddingBottom = \"\";\n\t\telement.style.minHeight = \"\";\n\t\telement.style.display = \"\";\n\t\telement.style.visibility = \"\";\n\n\t\tthis.elementVertical.scrollTop = 0;\n\t\tthis.elementVertical.scrollLeft = 0;\n\n\t\tthis.scrollTop = 0;\n\t\tthis.scrollLeft = 0;\n\n\t\tthis.vDomTop = 0;\n\t\tthis.vDomBottom = 0;\n\t\tthis.vDomTopPad = 0;\n\t\tthis.vDomBottomPad = 0;\n\t\tthis.vDomScrollPosTop = 0;\n\t\tthis.vDomScrollPosBottom = 0;\n\t}\n\n\trenderRows(){\n\t\tthis._virtualRenderFill();\n\t}\n\n\trerenderRows(callback){\n\t\tvar scrollTop = this.elementVertical.scrollTop;\n\t\tvar topRow = false;\n\t\tvar topOffset = false;\n\n\t\tvar left = this.table.rowManager.scrollLeft;\n\n\t\tvar rows = this.rows();\n\n\t\tfor(var i = this.vDomTop; i <= this.vDomBottom; i++){\n\n\t\t\tif(rows[i]){\n\t\t\t\tvar diff = scrollTop - rows[i].getElement().offsetTop;\n\n\t\t\t\tif(topOffset === false || Math.abs(diff) < topOffset){\n\t\t\t\t\ttopOffset = diff;\n\t\t\t\t\ttopRow = i;\n\t\t\t\t}else {\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\trows.forEach((row) => {\n\t\t\trow.deinitializeHeight();\n\t\t});\n\n\t\tif(callback){\n\t\t\tcallback();\n\t\t}\n\n\t\tif(this.rows().length){\n\t\t\tthis._virtualRenderFill((topRow === false ? this.rows.length - 1 : topRow), true, topOffset || 0);\n\t\t}else {\n\t\t\tthis.clear();\n\t\t\tthis.table.rowManager.tableEmpty();\n\t\t}\n\n\t\tthis.scrollColumns(left);\n\t}\n\n\tscrollColumns(left){\n\t\tthis.table.rowManager.scrollHorizontal(left);\n\t}\n\n\tscrollRows(top, dir){\n\t\tvar topDiff = top - this.vDomScrollPosTop;\n\t\tvar bottomDiff = top - this.vDomScrollPosBottom;\n\t\tvar margin = this.vDomWindowBuffer * 2;\n\t\tvar rows = this.rows();\n\n\t\tthis.scrollTop = top;\n\n\t\tif(-topDiff > margin || bottomDiff > margin){\n\t\t\t//if big scroll redraw table;\n\t\t\tvar left = this.table.rowManager.scrollLeft;\n\t\t\tthis._virtualRenderFill(Math.floor((this.elementVertical.scrollTop / this.elementVertical.scrollHeight) * rows.length));\n\t\t\tthis.scrollColumns(left);\n\t\t}else {\n\n\t\t\tif(dir){\n\t\t\t\t//scrolling up\n\t\t\t\tif(topDiff < 0){\n\t\t\t\t\tthis._addTopRow(rows, -topDiff);\n\t\t\t\t}\n\n\t\t\t\tif(bottomDiff < 0){\n\t\t\t\t\t//hide bottom row if needed\n\t\t\t\t\tif(this.vDomScrollHeight - this.scrollTop > this.vDomWindowBuffer){\n\t\t\t\t\t\tthis._removeBottomRow(rows, -bottomDiff);\n\t\t\t\t\t}else {\n\t\t\t\t\t\tthis.vDomScrollPosBottom = this.scrollTop;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}else {\n\n\t\t\t\tif(bottomDiff >= 0){\n\t\t\t\t\tthis._addBottomRow(rows, bottomDiff);\n\t\t\t\t}\n\n\t\t\t\t//scrolling down\n\t\t\t\tif(topDiff >= 0){\n\t\t\t\t\t//hide top row if needed\n\t\t\t\t\tif(this.scrollTop > this.vDomWindowBuffer){\n\t\t\t\t\t\tthis._removeTopRow(rows, topDiff);\n\t\t\t\t\t}else {\n\t\t\t\t\t\tthis.vDomScrollPosTop = this.scrollTop;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\tresize(){\n\t\tthis.vDomWindowBuffer = this.table.options.renderVerticalBuffer || this.elementVertical.clientHeight;\n\t}\n\n\tscrollToRowNearestTop(row){\n\t\tvar rowIndex = this.rows().indexOf(row);\n\n\t\treturn !(Math.abs(this.vDomTop - rowIndex) > Math.abs(this.vDomBottom - rowIndex));\n\t}\n\n\tscrollToRow(row){\n\t\tvar index = this.rows().indexOf(row);\n\n\t\tif(index > -1){\n\t\t\tthis._virtualRenderFill(index, true);\n\t\t}\n\t}\n\n\tvisibleRows(includingBuffer){\n\t\tvar topEdge = this.elementVertical.scrollTop,\n\t\tbottomEdge = this.elementVertical.clientHeight + topEdge,\n\t\ttopFound = false,\n\t\ttopRow = 0,\n\t\tbottomRow = 0,\n\t\trows = this.rows();\n\n\t\tif(includingBuffer){\n\t\t\ttopRow = this.vDomTop;\n\t\t\tbottomRow = this.vDomBottom;\n\t\t}else {\n\t\t\tfor(var i = this.vDomTop; i <= this.vDomBottom; i++){\n\t\t\t\tif(rows[i]){\n\t\t\t\t\tif(!topFound){\n\t\t\t\t\t\tif((topEdge - rows[i].getElement().offsetTop) >= 0){\n\t\t\t\t\t\t\ttopRow = i;\n\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\ttopFound = true;\n\n\t\t\t\t\t\t\tif(bottomEdge - rows[i].getElement().offsetTop >= 0){\n\t\t\t\t\t\t\t\tbottomRow = i;\n\t\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}else {\n\t\t\t\t\t\tif(bottomEdge - rows[i].getElement().offsetTop >= 0){\n\t\t\t\t\t\t\tbottomRow = i;\n\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn rows.slice(topRow, bottomRow + 1);\n\t}\n\n\t//////////////////////////////////////\n\t//////// Internal Rendering //////////\n\t//////////////////////////////////////\n\n\t//full virtual render\n\t_virtualRenderFill(position, forceMove, offset) {\n\t\tvar\telement = this.tableElement,\n\t\tholder = this.elementVertical,\n\t\ttopPad = 0,\n\t\trowsHeight = 0,\n\t\trowHeight = 0,\n\t\theightOccupied = 0,\n\t\ttopPadHeight = 0,\n\t\ti = 0,\n\t\trows = this.rows(),\n\t\trowsCount = rows.length,\n\t\tindex = 0,\n\t\trow,\n\t\trowFragment,\n\t\trenderedRows = [],\n\t\ttotalRowsRendered = 0,\n\t\trowsToRender = 0,\n\t\tfixedHeight = this.table.rowManager.fixedHeight,\n\t\tcontainerHeight = this.elementVertical.clientHeight, \n\t\tavgRowHeight = this.table.options.rowHeight, \n\t\tresized = true;\n\n\t\tposition = position || 0;\n\n\t\toffset = offset || 0;\n\n\t\tif(!position){\n\t\t\tthis.clear();\n\t\t}else {\n\t\t\twhile(element.firstChild) element.removeChild(element.firstChild);\n\n\t\t\t//check if position is too close to bottom of table\n\t\t\theightOccupied = (rowsCount - position + 1) * this.vDomRowHeight;\n\n\t\t\tif(heightOccupied < containerHeight){\n\t\t\t\tposition -= Math.ceil((containerHeight - heightOccupied) / this.vDomRowHeight);\n\t\t\t\tif(position < 0){\n\t\t\t\t\tposition = 0;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t//calculate initial pad\n\t\t\ttopPad = Math.min(Math.max(Math.floor(this.vDomWindowBuffer / this.vDomRowHeight),  this.vDomWindowMinMarginRows), position);\n\t\t\tposition -= topPad;\n\t\t}\n\n\t\tif(rowsCount && Helpers.elVisible(this.elementVertical)){\n\t\t\tthis.vDomTop = position;\n\t\t\tthis.vDomBottom = position -1;\n\n\t\t\tif(fixedHeight || this.table.options.maxHeight) {\n\t\t\t\tif(avgRowHeight) {\n\t\t\t\t\trowsToRender = (containerHeight / avgRowHeight) + (this.vDomWindowBuffer / avgRowHeight);\n\t\t\t\t}\n\t\t\t\trowsToRender = Math.max(this.vDomWindowMinTotalRows, Math.ceil(rowsToRender));\n\t\t\t}\n\t\t\telse {\n\t\t\t\trowsToRender = rowsCount;\n\t\t\t}\n\n\t\t\twhile(((rowsToRender == rowsCount || rowsHeight <= containerHeight + this.vDomWindowBuffer) || totalRowsRendered < this.vDomWindowMinTotalRows) && this.vDomBottom < rowsCount -1) {\n\t\t\t\trenderedRows = [];\n\t\t\t\trowFragment = document.createDocumentFragment();\n\n\t\t\t\ti = 0;\n\n\t\t\t\twhile ((i < rowsToRender) && this.vDomBottom < rowsCount -1) {\t\n\t\t\t\t\tindex = this.vDomBottom + 1,\n\t\t\t\t\trow = rows[index];\n\n\t\t\t\t\tthis.styleRow(row, index);\n\n\t\t\t\t\trow.initialize(false, true);\n\t\t\t\t\tif(!row.heightInitialized && !this.table.options.rowHeight){\n\t\t\t\t\t\trow.clearCellHeight();\n\t\t\t\t\t}\n\n\t\t\t\t\trowFragment.appendChild(row.getElement());\n\t\t\t\t\trenderedRows.push(row);\n\t\t\t\t\tthis.vDomBottom ++;\n\t\t\t\t\ti++;\n\t\t\t\t}\n\n\t\t\t\tif(!renderedRows.length){\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\n\t\t\t\telement.appendChild(rowFragment);\n\t\t\t\t\n\t\t\t\t// NOTE: The next 3 loops are separate on purpose\n\t\t\t\t// This is to batch up the dom writes and reads which drastically improves performance \n\n\t\t\t\trenderedRows.forEach((row) => {\n\t\t\t\t\trow.rendered();\n\n\t\t\t\t\tif(!row.heightInitialized) {\n\t\t\t\t\t\trow.calcHeight(true);\n\t\t\t\t\t}\n\t\t\t\t});\n\n\t\t\t\trenderedRows.forEach((row) => {\n\t\t\t\t\tif(!row.heightInitialized) {\n\t\t\t\t\t\trow.setCellHeight();\n\t\t\t\t\t}\n\t\t\t\t});\n\n\t\t\t\trenderedRows.forEach((row) => {\n\t\t\t\t\trowHeight = row.getHeight();\n\t\t\t\t\t\n\t\t\t\t\tif(totalRowsRendered < topPad){\n\t\t\t\t\t\ttopPadHeight += rowHeight;\n\t\t\t\t\t}else {\n\t\t\t\t\t\trowsHeight += rowHeight;\n\t\t\t\t\t}\n\n\t\t\t\t\tif(rowHeight > this.vDomWindowBuffer){\n\t\t\t\t\t\tthis.vDomWindowBuffer = rowHeight * 2;\n\t\t\t\t\t}\n\t\t\t\t\ttotalRowsRendered++;\n\t\t\t\t});\n\n\t\t\t\tresized = this.table.rowManager.adjustTableSize();\n\t\t\t\tcontainerHeight = this.elementVertical.clientHeight;\n\t\t\t\tif(resized && (fixedHeight || this.table.options.maxHeight))\n\t\t\t\t{\n\t\t\t\t\tavgRowHeight = rowsHeight / totalRowsRendered;\n\t\t\t\t\trowsToRender = Math.max(this.vDomWindowMinTotalRows, Math.ceil((containerHeight / avgRowHeight) + (this.vDomWindowBuffer / avgRowHeight)));\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif(!position){\n\t\t\t\tthis.vDomTopPad = 0;\n\t\t\t\t//adjust row height to match average of rendered elements\n\t\t\t\tthis.vDomRowHeight = Math.floor((rowsHeight + topPadHeight) / totalRowsRendered);\n\t\t\t\tthis.vDomBottomPad = this.vDomRowHeight * (rowsCount - this.vDomBottom -1);\n\n\t\t\t\tthis.vDomScrollHeight = topPadHeight + rowsHeight + this.vDomBottomPad - containerHeight;\n\t\t\t}else {\n\t\t\t\tthis.vDomTopPad = !forceMove ? this.scrollTop - topPadHeight : (this.vDomRowHeight * this.vDomTop) + offset;\n\t\t\t\tthis.vDomBottomPad = this.vDomBottom == rowsCount-1 ? 0 : Math.max(this.vDomScrollHeight - this.vDomTopPad - rowsHeight - topPadHeight, 0);\n\t\t\t}\n\t\t\t\n\t\t\telement.style.paddingTop = this.vDomTopPad+\"px\";\n\t\t\telement.style.paddingBottom = this.vDomBottomPad+\"px\";\n\n\t\t\tif(forceMove){\n\t\t\t\tthis.scrollTop = this.vDomTopPad + (topPadHeight) + offset - (this.elementVertical.scrollWidth > this.elementVertical.clientWidth ? this.elementVertical.offsetHeight - containerHeight : 0);\n\t\t\t}\n\n\t\t\tthis.scrollTop = Math.min(this.scrollTop, this.elementVertical.scrollHeight - containerHeight);\n\n\t\t\t//adjust for horizontal scrollbar if present (and not at top of table)\n\t\t\tif(this.elementVertical.scrollWidth > this.elementVertical.clientWidth && forceMove){\n\t\t\t\tthis.scrollTop += this.elementVertical.offsetHeight - containerHeight;\n\t\t\t}\n\n\t\t\tthis.vDomScrollPosTop = this.scrollTop;\n\t\t\tthis.vDomScrollPosBottom = this.scrollTop;\n\n\t\t\tholder.scrollTop = this.scrollTop;\n\n\t\t\tthis.dispatch(\"render-virtual-fill\");\n\t\t}\n\t}\n\n\t_addTopRow(rows, fillableSpace){\n\t\tvar table = this.tableElement,\n\t\taddedRows = [],\n\t\tpaddingAdjust = 0,\n\t\tindex = this.vDomTop -1,\n\t\ti = 0,\n\t\tworking = true;\n\n\t\twhile(working){\n\t\t\tif(this.vDomTop){\n\t\t\t\tlet row = rows[index],\n\t\t\t\trowHeight, initialized;\n\n\t\t\t\tif(row && i < this.vDomMaxRenderChain){\n\t\t\t\t\trowHeight = row.getHeight() || this.vDomRowHeight;\n\t\t\t\t\tinitialized = row.initialized;\n\n\t\t\t\t\tif(fillableSpace >= rowHeight){\n\n\t\t\t\t\t\tthis.styleRow(row, index);\n\t\t\t\t\t\ttable.insertBefore(row.getElement(), table.firstChild);\n\n\t\t\t\t\t\tif(!row.initialized || !row.heightInitialized){\n\t\t\t\t\t\t\taddedRows.push(row);\n\t\t\t\t\t\t}\n\n\t\t\t\t\t\trow.initialize();\n\n\t\t\t\t\t\tif(!initialized){\n\t\t\t\t\t\t\trowHeight = row.getElement().offsetHeight;\n\n\t\t\t\t\t\t\tif(rowHeight > this.vDomWindowBuffer){\n\t\t\t\t\t\t\t\tthis.vDomWindowBuffer = rowHeight * 2;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\n\t\t\t\t\t\tfillableSpace -= rowHeight;\n\t\t\t\t\t\tpaddingAdjust += rowHeight;\n\n\t\t\t\t\t\tthis.vDomTop--;\n\t\t\t\t\t\tindex--;\n\t\t\t\t\t\ti++;\n\n\t\t\t\t\t}else {\n\t\t\t\t\t\tworking = false;\n\t\t\t\t\t}\n\n\t\t\t\t}else {\n\t\t\t\t\tworking = false;\n\t\t\t\t}\n\n\t\t\t}else {\n\t\t\t\tworking = false;\n\t\t\t}\n\t\t}\n\n\t\tfor (let row of addedRows){\n\t\t\trow.clearCellHeight();\n\t\t}\n\n\t\tthis._quickNormalizeRowHeight(addedRows);\n\n\t\tif(paddingAdjust){\n\t\t\tthis.vDomTopPad -= paddingAdjust;\n\n\t\t\tif(this.vDomTopPad < 0){\n\t\t\t\tthis.vDomTopPad = index * this.vDomRowHeight;\n\t\t\t}\n\n\t\t\tif(index < 1){\n\t\t\t\tthis.vDomTopPad = 0;\n\t\t\t}\n\n\t\t\ttable.style.paddingTop = this.vDomTopPad + \"px\";\n\t\t\tthis.vDomScrollPosTop -= paddingAdjust;\n\t\t}\n\t}\n\n\t_removeTopRow(rows, fillableSpace){\n\t\tvar removableRows = [],\n\t\tpaddingAdjust = 0,\n\t\ti = 0,\n\t\tworking = true;\n\n\t\twhile(working){\n\t\t\tlet row = rows[this.vDomTop],\n\t\t\trowHeight;\n\n\t\t\tif(row && i < this.vDomMaxRenderChain){\n\t\t\t\trowHeight = row.getHeight() || this.vDomRowHeight;\n\n\t\t\t\tif(fillableSpace >= rowHeight){\n\t\t\t\t\tthis.vDomTop++;\n\n\t\t\t\t\tfillableSpace -= rowHeight;\n\t\t\t\t\tpaddingAdjust += rowHeight;\n\n\t\t\t\t\tremovableRows.push(row);\n\t\t\t\t\ti++;\n\t\t\t\t}else {\n\t\t\t\t\tworking = false;\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tworking = false;\n\t\t\t}\n\t\t}\n\n\t\tfor (let row of removableRows){\n\t\t\tlet rowEl = row.getElement();\n\n\t\t\tif(rowEl.parentNode){\n\t\t\t\trowEl.parentNode.removeChild(rowEl);\n\t\t\t}\n\t\t}\n\n\t\tif(paddingAdjust){\n\t\t\tthis.vDomTopPad += paddingAdjust;\n\t\t\tthis.tableElement.style.paddingTop = this.vDomTopPad + \"px\";\n\t\t\tthis.vDomScrollPosTop += this.vDomTop ? paddingAdjust : paddingAdjust + this.vDomWindowBuffer;\n\t\t}\n\t}\n\n\t_addBottomRow(rows, fillableSpace){\n\t\tvar table = this.tableElement,\n\t\taddedRows = [],\n\t\tpaddingAdjust = 0,\n\t\tindex = this.vDomBottom + 1,\n\t\ti = 0,\n\t\tworking = true;\n\n\t\twhile(working){\n\t\t\tlet row = rows[index],\n\t\t\trowHeight, initialized;\n\n\t\t\tif(row && i < this.vDomMaxRenderChain){\n\t\t\t\trowHeight = row.getHeight() || this.vDomRowHeight;\n\t\t\t\tinitialized = row.initialized;\n\n\t\t\t\tif(fillableSpace >= rowHeight){\n\n\t\t\t\t\tthis.styleRow(row, index);\n\t\t\t\t\ttable.appendChild(row.getElement());\n\n\t\t\t\t\tif(!row.initialized || !row.heightInitialized){\n\t\t\t\t\t\taddedRows.push(row);\n\t\t\t\t\t}\n\n\t\t\t\t\trow.initialize();\n\n\t\t\t\t\tif(!initialized){\n\t\t\t\t\t\trowHeight = row.getElement().offsetHeight;\n\n\t\t\t\t\t\tif(rowHeight > this.vDomWindowBuffer){\n\t\t\t\t\t\t\tthis.vDomWindowBuffer = rowHeight * 2;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\tfillableSpace -= rowHeight;\n\t\t\t\t\tpaddingAdjust += rowHeight;\n\n\t\t\t\t\tthis.vDomBottom++;\n\t\t\t\t\tindex++;\n\t\t\t\t\ti++;\n\t\t\t\t}else {\n\t\t\t\t\tworking = false;\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tworking = false;\n\t\t\t}\n\t\t}\n\n\t\tfor (let row of addedRows){\n\t\t\trow.clearCellHeight();\n\t\t}\n\n\t\tthis._quickNormalizeRowHeight(addedRows);\n\n\t\tif(paddingAdjust){\n\t\t\tthis.vDomBottomPad -= paddingAdjust;\n\n\t\t\tif(this.vDomBottomPad < 0 || index == rows.length -1){\n\t\t\t\tthis.vDomBottomPad = 0;\n\t\t\t}\n\n\t\t\ttable.style.paddingBottom = this.vDomBottomPad + \"px\";\n\t\t\tthis.vDomScrollPosBottom += paddingAdjust;\n\t\t}\n\t}\n\n\t_removeBottomRow(rows, fillableSpace){\n\t\tvar removableRows = [],\n\t\tpaddingAdjust = 0,\n\t\ti = 0,\n\t\tworking = true;\n\n\t\twhile(working){\n\t\t\tlet row = rows[this.vDomBottom],\n\t\t\trowHeight;\n\n\t\t\tif(row && i < this.vDomMaxRenderChain){\n\t\t\t\trowHeight = row.getHeight() || this.vDomRowHeight;\n\n\t\t\t\tif(fillableSpace >= rowHeight){\n\t\t\t\t\tthis.vDomBottom --;\n\n\t\t\t\t\tfillableSpace -= rowHeight;\n\t\t\t\t\tpaddingAdjust += rowHeight;\n\n\t\t\t\t\tremovableRows.push(row);\n\t\t\t\t\ti++;\n\t\t\t\t}else {\n\t\t\t\t\tworking = false;\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tworking = false;\n\t\t\t}\n\t\t}\n\n\t\tfor (let row of removableRows){\n\t\t\tlet rowEl = row.getElement();\n\n\t\t\tif(rowEl.parentNode){\n\t\t\t\trowEl.parentNode.removeChild(rowEl);\n\t\t\t}\n\t\t}\n\n\t\tif(paddingAdjust){\n\t\t\tthis.vDomBottomPad += paddingAdjust;\n\n\t\t\tif(this.vDomBottomPad < 0){\n\t\t\t\tthis.vDomBottomPad = 0;\n\t\t\t}\n\n\t\t\tthis.tableElement.style.paddingBottom = this.vDomBottomPad + \"px\";\n\t\t\tthis.vDomScrollPosBottom -= paddingAdjust;\n\t\t}\n\t}\n\n\t_quickNormalizeRowHeight(rows){\n\t\tfor(let row of rows){\n\t\t\trow.calcHeight();\n\t\t}\n\n\t\tfor(let row of rows){\n\t\t\trow.setCellHeight();\n\t\t}\n\t}\n}\n\nclass RowManager extends CoreFeature{\n\t\n\tconstructor(table){\n\t\tsuper(table);\n\t\t\n\t\tthis.element = this.createHolderElement(); //containing element\n\t\tthis.tableElement = this.createTableElement(); //table element\n\t\tthis.heightFixer = this.createTableElement(); //table element\n\t\tthis.placeholder = null; //placeholder element\n\t\tthis.placeholderContents = null; //placeholder element\n\t\t\n\t\tthis.firstRender = false; //handle first render\n\t\tthis.renderMode = \"virtual\"; //current rendering mode\n\t\tthis.fixedHeight = false; //current rendering mode\n\t\t\n\t\tthis.rows = []; //hold row data objects\n\t\tthis.activeRowsPipeline = []; //hold calculation of active rows\n\t\tthis.activeRows = []; //rows currently available to on display in the table\n\t\tthis.activeRowsCount = 0; //count of active rows\n\t\t\n\t\tthis.displayRows = []; //rows currently on display in the table\n\t\tthis.displayRowsCount = 0; //count of display rows\n\t\t\n\t\tthis.scrollTop = 0;\n\t\tthis.scrollLeft = 0;\n\t\t\n\t\tthis.redrawBlock = false; //prevent redraws to allow multiple data manipulations before continuing\n\t\tthis.redrawBlockRestoreConfig = false; //store latest redraw function calls for when redraw is needed\n\t\tthis.redrawBlockRenderInPosition = false; //store latest redraw function calls for when redraw is needed\n\t\t\n\t\tthis.dataPipeline = []; //hold data pipeline tasks\n\t\tthis.displayPipeline = []; //hold data display pipeline tasks\n\t\t\n\t\tthis.scrollbarWidth = 0;\n\t\t\n\t\tthis.renderer = null;\n\t}\n\t\n\t//////////////// Setup Functions /////////////////\n\t\n\tcreateHolderElement (){\n\t\tvar el = document.createElement(\"div\");\n\t\t\n\t\tel.classList.add(\"tabulator-tableholder\");\n\t\tel.setAttribute(\"tabindex\", 0);\n\t\t// el.setAttribute(\"role\", \"rowgroup\");\n\t\t\n\t\treturn el;\n\t}\n\t\n\tcreateTableElement (){\n\t\tvar el = document.createElement(\"div\");\n\t\t\n\t\tel.classList.add(\"tabulator-table\");\n\t\tel.setAttribute(\"role\", \"rowgroup\");\n\t\t\n\t\treturn el;\n\t}\n\t\n\tinitializePlaceholder(){\n\t\tvar placeholder = this.table.options.placeholder;\n\t\t\n\t\tif(typeof placeholder === \"function\"){\n\t\t\tplaceholder = placeholder.call(this.table);\n\t\t}\n\t\t\n\t\tplaceholder = this.chain(\"placeholder\", [placeholder], placeholder, placeholder) || placeholder;\n\t\t\n\t\t//configure placeholder element\n\t\tif(placeholder){\t\n\t\t\tlet el = document.createElement(\"div\");\n\t\t\tel.classList.add(\"tabulator-placeholder\");\n\t\t\t\n\t\t\tif(typeof placeholder == \"string\"){\n\t\t\t\tlet contents = document.createElement(\"div\");\n\t\t\t\tcontents.classList.add(\"tabulator-placeholder-contents\");\n\t\t\t\tcontents.innerHTML = placeholder;\n\t\t\t\t\n\t\t\t\tel.appendChild(contents);\n\t\t\t\t\n\t\t\t\tthis.placeholderContents = contents;\n\t\t\t\t\n\t\t\t}else if(typeof HTMLElement !== \"undefined\" && placeholder instanceof HTMLElement){\n\t\t\t\t\n\t\t\t\tel.appendChild(placeholder);\n\t\t\t\tthis.placeholderContents = placeholder;\n\t\t\t}else {\n\t\t\t\tconsole.warn(\"Invalid placeholder provided, must be string or HTML Element\", placeholder);\n\t\t\t\t\n\t\t\t\tthis.el = null;\n\t\t\t}\n\t\t\t\n\t\t\tthis.placeholder = el;\n\t\t}\n\t}\n\t\n\t//return containing element\n\tgetElement(){\n\t\treturn this.element;\n\t}\n\t\n\t//return table element\n\tgetTableElement(){\n\t\treturn this.tableElement;\n\t}\n\t\n\tinitialize(){\n\t\tthis.initializePlaceholder();\n\t\tthis.initializeRenderer();\n\t\t\n\t\t//initialize manager\n\t\tthis.element.appendChild(this.tableElement);\n\t\t\n\t\tthis.firstRender = true;\n\t\t\n\t\t//scroll header along with table body\n\t\tthis.element.addEventListener(\"scroll\", () => {\n\t\t\tvar left = this.element.scrollLeft,\n\t\t\tleftDir = this.scrollLeft > left,\n\t\t\ttop = this.element.scrollTop,\n\t\t\ttopDir = this.scrollTop > top;\n\t\t\t\n\t\t\t//handle horizontal scrolling\n\t\t\tif(this.scrollLeft != left){\n\t\t\t\tthis.scrollLeft = left;\n\t\t\t\t\n\t\t\t\tthis.dispatch(\"scroll-horizontal\", left, leftDir);\n\t\t\t\tthis.dispatchExternal(\"scrollHorizontal\", left, leftDir);\n\t\t\t\t\n\t\t\t\tthis._positionPlaceholder();\n\t\t\t}\n\t\t\t\n\t\t\t//handle vertical scrolling\n\t\t\tif(this.scrollTop != top){\n\t\t\t\tthis.scrollTop = top;\n\t\t\t\t\n\t\t\t\tthis.renderer.scrollRows(top, topDir);\n\t\t\t\t\n\t\t\t\tthis.dispatch(\"scroll-vertical\", top, topDir);\n\t\t\t\tthis.dispatchExternal(\"scrollVertical\", top, topDir);\n\t\t\t}\n\t\t});\n\t}\n\t\n\t////////////////// Row Manipulation //////////////////\n\tfindRow(subject){\n\t\tif(typeof subject == \"object\"){\n\t\t\tif(subject instanceof Row){\n\t\t\t\t//subject is row element\n\t\t\t\treturn subject;\n\t\t\t}else if(subject instanceof RowComponent){\n\t\t\t\t//subject is public row component\n\t\t\t\treturn subject._getSelf() || false;\n\t\t\t}else if(typeof HTMLElement !== \"undefined\" && subject instanceof HTMLElement){\n\t\t\t\t//subject is a HTML element of the row\n\t\t\t\tlet match = this.rows.find((row) => {\n\t\t\t\t\treturn row.getElement() === subject;\n\t\t\t\t});\n\t\t\t\t\n\t\t\t\treturn match || false;\n\t\t\t}else if(subject === null){\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}else if(typeof subject == \"undefined\"){\n\t\t\treturn false;\n\t\t}else {\n\t\t\t//subject should be treated as the index of the row\n\t\t\tlet match = this.rows.find((row) => {\n\t\t\t\treturn row.data[this.table.options.index] == subject;\n\t\t\t});\n\t\t\t\n\t\t\treturn match || false;\n\t\t}\n\t\t\n\t\t//catch all for any other type of input\n\t\treturn false;\n\t}\n\t\n\tgetRowFromDataObject(data){\n\t\tvar match = this.rows.find((row) => {\n\t\t\treturn row.data === data;\n\t\t});\n\t\t\n\t\treturn match || false;\n\t}\n\t\n\tgetRowFromPosition(position){\n\t\treturn this.getDisplayRows().find((row) => {\n\t\t\treturn row.getPosition() === position && row.isDisplayed();\n\t\t});\n\t}\n\t\n\tscrollToRow(row, position, ifVisible){\n\t\treturn this.renderer.scrollToRowPosition(row, position, ifVisible);\n\t}\n\t\n\t////////////////// Data Handling //////////////////\n\tsetData(data, renderInPosition, columnsChanged){\n\t\treturn new Promise((resolve, reject)=>{\n\t\t\tif(renderInPosition && this.getDisplayRows().length){\n\t\t\t\tif(this.table.options.pagination){\n\t\t\t\t\tthis._setDataActual(data, true);\n\t\t\t\t}else {\n\t\t\t\t\tthis.reRenderInPosition(() => {\n\t\t\t\t\t\tthis._setDataActual(data);\n\t\t\t\t\t});\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tif(this.table.options.autoColumns && columnsChanged && this.table.initialized){\n\t\t\t\t\tthis.table.columnManager.generateColumnsFromRowData(data);\n\t\t\t\t}\n\t\t\t\tthis.resetScroll();\n\t\t\t\t\n\t\t\t\tthis._setDataActual(data);\n\t\t\t}\n\t\t\t\n\t\t\tresolve();\n\t\t});\n\t}\n\t\n\t_setDataActual(data, renderInPosition){\n\t\tthis.dispatchExternal(\"dataProcessing\", data);\n\t\t\n\t\tthis._wipeElements();\n\t\t\n\t\tif(Array.isArray(data)){\n\t\t\tthis.dispatch(\"data-processing\", data);\n\t\t\t\n\t\t\tdata.forEach((def, i) => {\n\t\t\t\tif(def && typeof def === \"object\"){\n\t\t\t\t\tvar row = new Row(def, this);\n\t\t\t\t\tthis.rows.push(row);\n\t\t\t\t}else {\n\t\t\t\t\tconsole.warn(\"Data Loading Warning - Invalid row data detected and ignored, expecting object but received:\", def);\n\t\t\t\t}\n\t\t\t});\n\t\t\t\n\t\t\tthis.refreshActiveData(false, false, renderInPosition);\n\t\t\t\n\t\t\tthis.dispatch(\"data-processed\", data);\n\t\t\tthis.dispatchExternal(\"dataProcessed\", data);\n\t\t}else {\n\t\t\tconsole.error(\"Data Loading Error - Unable to process data due to invalid data type \\nExpecting: array \\nReceived: \", typeof data, \"\\nData:     \", data);\n\t\t}\n\t}\n\t\n\t_wipeElements(){\n\t\tthis.dispatch(\"rows-wipe\");\n\t\t\n\t\tthis.destroy();\n\t\t\n\t\tthis.adjustTableSize();\n\t\t\n\t\tthis.dispatch(\"rows-wiped\");\n\t}\n\t\n\tdestroy(){\n\t\tthis.rows.forEach((row) => {\n\t\t\trow.wipe();\n\t\t});\n\t\t\n\t\tthis.rows = [];\n\t\tthis.activeRows = [];\n\t\tthis.activeRowsPipeline = [];\n\t\tthis.activeRowsCount = 0;\n\t\tthis.displayRows = [];\n\t\tthis.displayRowsCount = 0;\n\t}\n\t\n\tdeleteRow(row, blockRedraw){\n\t\tvar allIndex = this.rows.indexOf(row),\n\t\tactiveIndex = this.activeRows.indexOf(row);\n\t\t\n\t\tif(activeIndex > -1){\n\t\t\tthis.activeRows.splice(activeIndex, 1);\n\t\t}\n\t\t\n\t\tif(allIndex > -1){\n\t\t\tthis.rows.splice(allIndex, 1);\n\t\t}\n\t\t\n\t\tthis.setActiveRows(this.activeRows);\n\t\t\n\t\tthis.displayRowIterator((rows) => {\n\t\t\tvar displayIndex = rows.indexOf(row);\n\t\t\t\n\t\t\tif(displayIndex > -1){\n\t\t\t\trows.splice(displayIndex, 1);\n\t\t\t}\n\t\t});\n\t\t\n\t\tif(!blockRedraw){\n\t\t\tthis.reRenderInPosition();\n\t\t}\n\t\t\n\t\tthis.regenerateRowPositions();\n\t\t\n\t\tthis.dispatchExternal(\"rowDeleted\", row.getComponent());\n\t\t\n\t\tif(!this.displayRowsCount){\n\t\t\tthis.tableEmpty();\n\t\t}\n\t\t\n\t\tif(this.subscribedExternal(\"dataChanged\")){\n\t\t\tthis.dispatchExternal(\"dataChanged\", this.getData());\n\t\t}\n\t}\n\t\n\taddRow(data, pos, index, blockRedraw){\n\t\tvar row = this.addRowActual(data, pos, index, blockRedraw);\n\t\treturn row;\n\t}\n\t\n\t//add multiple rows\n\taddRows(data, pos, index, refreshDisplayOnly){\n\t\tvar rows = [];\n\t\t\n\t\treturn new Promise((resolve, reject) => {\n\t\t\tpos = this.findAddRowPos(pos);\n\t\t\t\n\t\t\tif(!Array.isArray(data)){\n\t\t\t\tdata = [data];\n\t\t\t}\n\t\t\t\n\t\t\tif((typeof index == \"undefined\" && pos) || (typeof index !== \"undefined\" && !pos)){\n\t\t\t\tdata.reverse();\n\t\t\t}\n\t\t\t\n\t\t\tdata.forEach((item, i) => {\n\t\t\t\tvar row = this.addRow(item, pos, index, true);\n\t\t\t\trows.push(row);\n\t\t\t\tthis.dispatch(\"row-added\", row, item, pos, index);\n\t\t\t});\n\t\t\t\n\t\t\tthis.refreshActiveData(refreshDisplayOnly ? \"displayPipeline\" : false, false, true);\n\t\t\t\n\t\t\tthis.regenerateRowPositions();\n\t\t\t\n\t\t\tif(this.displayRowsCount){\n\t\t\t\tthis._clearPlaceholder();\n\t\t\t}\n\t\t\t\n\t\t\tresolve(rows);\n\t\t});\n\t}\n\t\n\tfindAddRowPos(pos){\n\t\tif(typeof pos === \"undefined\"){\n\t\t\tpos = this.table.options.addRowPos;\n\t\t}\n\t\t\n\t\tif(pos === \"pos\"){\n\t\t\tpos = true;\n\t\t}\n\t\t\n\t\tif(pos === \"bottom\"){\n\t\t\tpos = false;\n\t\t}\n\t\t\n\t\treturn pos;\n\t}\n\t\n\taddRowActual(data, pos, index, blockRedraw){\n\t\tvar row = data instanceof Row ? data : new Row(data || {}, this),\n\t\ttop = this.findAddRowPos(pos),\n\t\tallIndex = -1,\n\t\tactiveIndex, chainResult;\n\t\t\n\t\tif(!index){\n\t\t\tchainResult = this.chain(\"row-adding-position\", [row, top], null, {index, top});\n\t\t\t\n\t\t\tindex = chainResult.index;\n\t\t\ttop = chainResult.top;\n\t\t}\n\t\t\n\t\tif(typeof index !== \"undefined\"){\n\t\t\tindex = this.findRow(index);\n\t\t}\n\t\t\n\t\tindex = this.chain(\"row-adding-index\", [row, index, top], null, index);\n\t\t\n\t\tif(index){\n\t\t\tallIndex = this.rows.indexOf(index);\n\t\t}\n\t\t\n\t\tif(index && allIndex > -1){\n\t\t\tactiveIndex = this.activeRows.indexOf(index);\n\t\t\t\n\t\t\tthis.displayRowIterator(function(rows){\n\t\t\t\tvar displayIndex = rows.indexOf(index);\n\t\t\t\t\n\t\t\t\tif(displayIndex > -1){\n\t\t\t\t\trows.splice((top ? displayIndex : displayIndex + 1), 0, row);\n\t\t\t\t}\n\t\t\t});\n\t\t\t\n\t\t\tif(activeIndex > -1){\n\t\t\t\tthis.activeRows.splice((top ? activeIndex : activeIndex + 1), 0, row);\n\t\t\t}\n\t\t\t\n\t\t\tthis.rows.splice((top ? allIndex : allIndex + 1), 0, row);\n\t\t\t\n\t\t}else {\n\t\t\t\n\t\t\tif(top){\n\t\t\t\t\n\t\t\t\tthis.displayRowIterator(function(rows){\n\t\t\t\t\trows.unshift(row);\n\t\t\t\t});\n\t\t\t\t\n\t\t\t\tthis.activeRows.unshift(row);\n\t\t\t\tthis.rows.unshift(row);\n\t\t\t}else {\n\t\t\t\tthis.displayRowIterator(function(rows){\n\t\t\t\t\trows.push(row);\n\t\t\t\t});\n\t\t\t\t\n\t\t\t\tthis.activeRows.push(row);\n\t\t\t\tthis.rows.push(row);\n\t\t\t}\n\t\t}\n\t\t\n\t\tthis.setActiveRows(this.activeRows);\n\t\t\n\t\tthis.dispatchExternal(\"rowAdded\", row.getComponent());\n\t\t\n\t\tif(this.subscribedExternal(\"dataChanged\")){\n\t\t\tthis.dispatchExternal(\"dataChanged\", this.table.rowManager.getData());\n\t\t}\n\t\t\n\t\tif(!blockRedraw){\n\t\t\tthis.reRenderInPosition();\n\t\t}\n\t\t\n\t\treturn row;\n\t}\n\t\n\tmoveRow(from, to, after){\n\t\tthis.dispatch(\"row-move\", from, to, after);\n\t\t\n\t\tthis.moveRowActual(from, to, after);\n\t\t\n\t\tthis.regenerateRowPositions();\n\t\t\n\t\tthis.dispatch(\"row-moved\", from, to, after);\n\t\tthis.dispatchExternal(\"rowMoved\", from.getComponent());\n\t}\n\t\n\tmoveRowActual(from, to, after){\n\t\tthis.moveRowInArray(this.rows, from, to, after);\n\t\tthis.moveRowInArray(this.activeRows, from, to, after);\n\t\t\n\t\tthis.displayRowIterator((rows) => {\n\t\t\tthis.moveRowInArray(rows, from, to, after);\n\t\t});\n\t\t\n\t\tthis.dispatch(\"row-moving\", from, to, after);\n\t}\n\t\n\tmoveRowInArray(rows, from, to, after){\n\t\tvar\tfromIndex, toIndex, start, end;\n\t\t\n\t\tif(from !== to){\n\t\t\t\n\t\t\tfromIndex = rows.indexOf(from);\n\t\t\t\n\t\t\tif (fromIndex > -1) {\n\t\t\t\t\n\t\t\t\trows.splice(fromIndex, 1);\n\t\t\t\t\n\t\t\t\ttoIndex = rows.indexOf(to);\n\t\t\t\t\n\t\t\t\tif (toIndex > -1) {\n\t\t\t\t\t\n\t\t\t\t\tif(after){\n\t\t\t\t\t\trows.splice(toIndex+1, 0, from);\n\t\t\t\t\t}else {\n\t\t\t\t\t\trows.splice(toIndex, 0, from);\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t}else {\n\t\t\t\t\trows.splice(fromIndex, 0, from);\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\t//restyle rows\n\t\t\tif(rows === this.getDisplayRows()){\n\t\t\t\t\n\t\t\t\tstart = fromIndex < toIndex ? fromIndex : toIndex;\n\t\t\t\tend = toIndex > fromIndex ? toIndex : fromIndex +1;\n\t\t\t\t\n\t\t\t\tfor(let i = start; i <= end; i++){\n\t\t\t\t\tif(rows[i]){\n\t\t\t\t\t\tthis.styleRow(rows[i], i);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t\n\tclearData(){\n\t\tthis.setData([]);\n\t}\n\t\n\tgetRowIndex(row){\n\t\treturn this.findRowIndex(row, this.rows);\n\t}\n\t\n\tgetDisplayRowIndex(row){\n\t\tvar index = this.getDisplayRows().indexOf(row);\n\t\treturn index > -1 ? index : false;\n\t}\n\t\n\tnextDisplayRow(row, rowOnly){\n\t\tvar index = this.getDisplayRowIndex(row),\n\t\tnextRow = false;\n\t\t\n\t\t\n\t\tif(index !== false && index < this.displayRowsCount -1){\n\t\t\tnextRow = this.getDisplayRows()[index+1];\n\t\t}\n\t\t\n\t\tif(nextRow && (!(nextRow instanceof Row) || nextRow.type != \"row\")){\n\t\t\treturn this.nextDisplayRow(nextRow, rowOnly);\n\t\t}\n\t\t\n\t\treturn nextRow;\n\t}\n\t\n\tprevDisplayRow(row, rowOnly){\n\t\tvar index = this.getDisplayRowIndex(row),\n\t\tprevRow = false;\n\t\t\n\t\tif(index){\n\t\t\tprevRow = this.getDisplayRows()[index-1];\n\t\t}\n\t\t\n\t\tif(rowOnly && prevRow && (!(prevRow instanceof Row) || prevRow.type != \"row\")){\n\t\t\treturn this.prevDisplayRow(prevRow, rowOnly);\n\t\t}\n\t\t\n\t\treturn prevRow;\n\t}\n\t\n\tfindRowIndex(row, list){\n\t\tvar rowIndex;\n\t\t\n\t\trow = this.findRow(row);\n\t\t\n\t\tif(row){\n\t\t\trowIndex = list.indexOf(row);\n\t\t\t\n\t\t\tif(rowIndex > -1){\n\t\t\t\treturn rowIndex;\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn false;\n\t}\n\t\n\tgetData(active, transform){\n\t\tvar output = [],\n\t\trows = this.getRows(active);\n\t\t\n\t\trows.forEach(function(row){\n\t\t\tif(row.type == \"row\"){\n\t\t\t\toutput.push(row.getData(transform || \"data\"));\n\t\t\t}\n\t\t});\n\t\t\n\t\treturn output;\n\t}\n\t\n\tgetComponents(active){\n\t\tvar\toutput = [],\n\t\trows = this.getRows(active);\n\t\t\n\t\trows.forEach(function(row){\n\t\t\toutput.push(row.getComponent());\n\t\t});\n\t\t\n\t\treturn output;\n\t}\n\t\n\tgetDataCount(active){\n\t\tvar rows = this.getRows(active);\n\t\t\n\t\treturn rows.length;\n\t}\n\t\n\tscrollHorizontal(left){\n\t\tthis.scrollLeft = left;\n\t\tthis.element.scrollLeft = left;\n\t\t\n\t\tthis.dispatch(\"scroll-horizontal\", left);\n\t}\n\t\n\tregisterDataPipelineHandler(handler, priority){\n\t\tif(typeof priority !== \"undefined\"){\n\t\t\tthis.dataPipeline.push({handler, priority});\n\t\t\tthis.dataPipeline.sort((a, b) => {\n\t\t\t\treturn a.priority - b.priority;\n\t\t\t});\n\t\t}else {\n\t\t\tconsole.error(\"Data pipeline handlers must have a priority in order to be registered\");\n\t\t}\n\t}\n\t\n\tregisterDisplayPipelineHandler(handler, priority){\n\t\tif(typeof priority !== \"undefined\"){\n\t\t\tthis.displayPipeline.push({handler, priority});\n\t\t\tthis.displayPipeline.sort((a, b) => {\n\t\t\t\treturn a.priority - b.priority;\n\t\t\t});\n\t\t}else {\n\t\t\tconsole.error(\"Display pipeline handlers must have a priority in order to be registered\");\n\t\t}\n\t}\n\t\n\t//set active data set\n\trefreshActiveData(handler, skipStage, renderInPosition){\n\t\tvar table = this.table,\n\t\tstage = \"\",\n\t\tindex = 0,\n\t\tcascadeOrder = [\"all\", \"dataPipeline\", \"display\", \"displayPipeline\", \"end\"];\n\t\t\n\t\tif(!this.table.destroyed){\n\t\t\tif(typeof handler === \"function\"){\n\t\t\t\tindex = this.dataPipeline.findIndex((item) => {\n\t\t\t\t\treturn item.handler === handler;\n\t\t\t\t});\n\t\t\t\t\n\t\t\t\tif(index > -1){\n\t\t\t\t\tstage = \"dataPipeline\";\n\t\t\t\t\t\n\t\t\t\t\tif(skipStage){\n\t\t\t\t\t\tif(index == this.dataPipeline.length - 1){\n\t\t\t\t\t\t\tstage = \"display\";\n\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\tindex++;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}else {\n\t\t\t\t\tindex = this.displayPipeline.findIndex((item) => {\n\t\t\t\t\t\treturn item.handler === handler;\n\t\t\t\t\t});\n\t\t\t\t\t\n\t\t\t\t\tif(index > -1){\n\t\t\t\t\t\tstage = \"displayPipeline\";\n\t\t\t\t\t\t\n\t\t\t\t\t\tif(skipStage){\n\t\t\t\t\t\t\tif(index == this.displayPipeline.length - 1){\n\t\t\t\t\t\t\t\tstage = \"end\";\n\t\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\t\tindex++;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}else {\n\t\t\t\t\t\tconsole.error(\"Unable to refresh data, invalid handler provided\", handler);\n\t\t\t\t\t\treturn;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tstage = handler || \"all\";\n\t\t\t\tindex = 0;\n\t\t\t}\n\t\t\t\n\t\t\tif(this.redrawBlock){\n\t\t\t\tif(!this.redrawBlockRestoreConfig || (this.redrawBlockRestoreConfig && ((this.redrawBlockRestoreConfig.stage === stage && index < this.redrawBlockRestoreConfig.index) || (cascadeOrder.indexOf(stage) < cascadeOrder.indexOf(this.redrawBlockRestoreConfig.stage))))){\n\t\t\t\t\tthis.redrawBlockRestoreConfig = {\n\t\t\t\t\t\thandler: handler,\n\t\t\t\t\t\tskipStage: skipStage,\n\t\t\t\t\t\trenderInPosition: renderInPosition,\n\t\t\t\t\t\tstage:stage,\n\t\t\t\t\t\tindex:index,\n\t\t\t\t\t};\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\treturn;\n\t\t\t}else {\n\t\t\t\tif(Helpers.elVisible(this.element)){\n\t\t\t\t\tif(renderInPosition){\n\t\t\t\t\t\tthis.reRenderInPosition(this.refreshPipelines.bind(this, handler, stage, index, renderInPosition));\n\t\t\t\t\t}else {\n\t\t\t\t\t\tthis.refreshPipelines(handler, stage, index, renderInPosition);\n\t\t\t\t\t\t\n\t\t\t\t\t\tif(!handler){\n\t\t\t\t\t\t\tthis.table.columnManager.renderer.renderColumns();\n\t\t\t\t\t\t}\n\t\t\t\t\t\t\n\t\t\t\t\t\tthis.renderTable();\n\t\t\t\t\t\t\n\t\t\t\t\t\tif(table.options.layoutColumnsOnNewData){\n\t\t\t\t\t\t\tthis.table.columnManager.redraw(true);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}else {\n\t\t\t\t\tthis.refreshPipelines(handler, stage, index, renderInPosition);\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tthis.dispatch(\"data-refreshed\");\n\t\t\t}\n\t\t}\n\t}\n\t\n\trefreshPipelines(handler, stage, index, renderInPosition){\n\t\tthis.dispatch(\"data-refreshing\");\n\t\t\n\t\tif(!handler || !this.activeRowsPipeline[0]){\n\t\t\tthis.activeRowsPipeline[0] = this.rows.slice(0);\n\t\t}\n\t\t\n\t\t//cascade through data refresh stages\n\t\tswitch(stage){\n\t\t\tcase \"all\":\n\t\t\t//handle case where all data needs refreshing\n\t\t\t\n\t\t\tcase \"dataPipeline\":\n\t\t\t\tfor(let i = index; i < this.dataPipeline.length; i++){\n\t\t\t\t\tlet result = this.dataPipeline[i].handler(this.activeRowsPipeline[i].slice(0));\n\t\t\t\t\n\t\t\t\t\tthis.activeRowsPipeline[i + 1] = result || this.activeRowsPipeline[i].slice(0);\n\t\t\t\t}\n\t\t\t\n\t\t\t\tthis.setActiveRows(this.activeRowsPipeline[this.dataPipeline.length]);\n\t\t\t\n\t\t\tcase \"display\":\n\t\t\t\tindex = 0;\n\t\t\t\tthis.resetDisplayRows();\n\t\t\t\n\t\t\tcase \"displayPipeline\":\n\t\t\t\tfor(let i = index; i < this.displayPipeline.length; i++){\n\t\t\t\t\tlet result = this.displayPipeline[i].handler((i ? this.getDisplayRows(i - 1) : this.activeRows).slice(0), renderInPosition);\n\t\t\t\t\n\t\t\t\t\tthis.setDisplayRows(result || this.getDisplayRows(i - 1).slice(0), i);\n\t\t\t\t}\n\t\t\t\n\t\t\tcase \"end\":\n\t\t\t//case to handle scenario when trying to skip past end stage\n\t\t\t\tthis.regenerateRowPositions();\n\t\t}\n\t\t\n\t\tif(this.getDisplayRows().length){\n\t\t\tthis._clearPlaceholder();\n\t\t}\n\t}\n\t\n\t//regenerate row positions\n\tregenerateRowPositions(){\n\t\tvar rows = this.getDisplayRows();\n\t\tvar index = 1;\n\t\t\n\t\trows.forEach((row) => {\n\t\t\tif (row.type === \"row\"){\n\t\t\t\trow.setPosition(index);\n\t\t\t\tindex++;\n\t\t\t}\n\t\t});\n\t}\n\t\n\tsetActiveRows(activeRows){\n\t\tthis.activeRows = this.activeRows = Object.assign([], activeRows);\n\t\tthis.activeRowsCount = this.activeRows.length;\n\t}\n\t\n\t//reset display rows array\n\tresetDisplayRows(){\n\t\tthis.displayRows = [];\n\t\t\n\t\tthis.displayRows.push(this.activeRows.slice(0));\n\t\t\n\t\tthis.displayRowsCount = this.displayRows[0].length;\n\t}\n\t\n\t//set display row pipeline data\n\tsetDisplayRows(displayRows, index){\n\t\tthis.displayRows[index] = displayRows;\n\t\t\n\t\tif(index == this.displayRows.length -1){\n\t\t\tthis.displayRowsCount = this.displayRows[this.displayRows.length -1].length;\n\t\t}\n\t}\n\t\n\tgetDisplayRows(index){\n\t\tif(typeof index == \"undefined\"){\n\t\t\treturn this.displayRows.length ? this.displayRows[this.displayRows.length -1] : [];\n\t\t}else {\n\t\t\treturn this.displayRows[index] || [];\n\t\t}\n\t}\n\t\n\tgetVisibleRows(chain, viewable){\n\t\tvar rows =  Object.assign([], this.renderer.visibleRows(!viewable));\n\t\t\n\t\tif(chain){\n\t\t\trows = this.chain(\"rows-visible\", [viewable], rows, rows);\n\t\t}\n\t\t\n\t\treturn rows;\n\t}\n\t\n\t//repeat action across display rows\n\tdisplayRowIterator(callback){\n\t\tthis.activeRowsPipeline.forEach(callback);\n\t\tthis.displayRows.forEach(callback);\n\t\t\n\t\tthis.displayRowsCount = this.displayRows[this.displayRows.length -1].length;\n\t}\n\t\n\t//return only actual rows (not group headers etc)\n\tgetRows(type){\n\t\tvar rows = [];\n\t\t\n\t\tswitch(type){\n\t\t\tcase \"active\":\n\t\t\t\trows = this.activeRows;\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase \"display\":\n\t\t\t\trows = this.table.rowManager.getDisplayRows();\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase \"visible\":\n\t\t\t\trows = this.getVisibleRows(false, true);\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tdefault:\n\t\t\t\trows = this.chain(\"rows-retrieve\", type, null, this.rows) || this.rows;\n\t\t}\n\t\t\n\t\treturn rows;\n\t}\n\t\n\t///////////////// Table Rendering /////////////////\n\t//trigger rerender of table in current position\n\treRenderInPosition(callback){\n\t\tif(this.redrawBlock){\n\t\t\tif(callback){\n\t\t\t\tcallback();\n\t\t\t}else {\n\t\t\t\tthis.redrawBlockRenderInPosition = true;\n\t\t\t}\n\t\t}else {\n\t\t\tthis.dispatchExternal(\"renderStarted\");\n\t\t\t\n\t\t\tthis.renderer.rerenderRows(callback);\n\t\t\t\n\t\t\tif(!this.fixedHeight){\n\t\t\t\tthis.adjustTableSize();\n\t\t\t}\n\t\t\t\n\t\t\tthis.scrollBarCheck();\n\t\t\t\n\t\t\tthis.dispatchExternal(\"renderComplete\");\n\t\t}\n\t}\n\t\n\tscrollBarCheck(){\n\t\tvar scrollbarWidth = 0;\n\t\t\n\t\t//adjust for vertical scrollbar moving table when present\n\t\tif(this.element.scrollHeight > this.element.clientHeight){\n\t\t\tscrollbarWidth = this.element.offsetWidth - this.element.clientWidth;\n\t\t}\n\t\t\n\t\tif(scrollbarWidth !== this.scrollbarWidth){\n\t\t\tthis.scrollbarWidth = scrollbarWidth;\n\t\t\tthis.dispatch(\"scrollbar-vertical\", scrollbarWidth);\n\t\t}\n\t}\n\t\n\tinitializeRenderer(){\n\t\tvar renderClass;\n\t\t\n\t\tvar renderers = {\n\t\t\t\"virtual\": VirtualDomVertical,\n\t\t\t\"basic\": BasicVertical,\n\t\t};\n\t\t\n\t\tif(typeof this.table.options.renderVertical === \"string\"){\n\t\t\trenderClass = renderers[this.table.options.renderVertical];\n\t\t}else {\n\t\t\trenderClass = this.table.options.renderVertical;\n\t\t}\n\t\t\n\t\tif(renderClass){\n\t\t\tthis.renderMode = this.table.options.renderVertical;\n\t\t\t\n\t\t\tthis.renderer = new renderClass(this.table, this.element, this.tableElement);\n\t\t\tthis.renderer.initialize();\n\t\t\t\n\t\t\tif((this.table.element.clientHeight || this.table.options.height) && !(this.table.options.minHeight && this.table.options.maxHeight)){\n\t\t\t\tthis.fixedHeight = true;\n\t\t\t}else {\n\t\t\t\tthis.fixedHeight = false;\n\t\t\t}\n\t\t}else {\n\t\t\tconsole.error(\"Unable to find matching renderer:\", this.table.options.renderVertical);\n\t\t}\n\t}\n\t\n\tgetRenderMode(){\n\t\treturn this.renderMode;\n\t}\n\t\n\trenderTable(){\n\t\tthis.dispatchExternal(\"renderStarted\");\n\t\t\n\t\tthis.element.scrollTop = 0;\n\t\t\n\t\tthis._clearTable();\n\t\t\n\t\tif(this.displayRowsCount){\n\t\t\tthis.renderer.renderRows();\n\t\t\t\n\t\t\tif(this.firstRender){\n\t\t\t\tthis.firstRender = false;\n\t\t\t\t\n\t\t\t\tif(!this.fixedHeight){\n\t\t\t\t\tthis.adjustTableSize();\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tthis.layoutRefresh(true);\n\t\t\t}\n\t\t}else {\n\t\t\tthis.renderEmptyScroll();\n\t\t}\n\t\t\n\t\tif(!this.fixedHeight){\n\t\t\tthis.adjustTableSize();\n\t\t}\n\t\t\n\t\tthis.dispatch(\"table-layout\");\n\t\t\n\t\tif(!this.displayRowsCount){\n\t\t\tthis._showPlaceholder();\n\t\t}\n\t\t\n\t\tthis.scrollBarCheck();\n\t\t\n\t\tthis.dispatchExternal(\"renderComplete\");\n\t}\n\t\n\t//show scrollbars on empty table div\n\trenderEmptyScroll(){\n\t\tif(this.placeholder){\n\t\t\tthis.tableElement.style.display = \"none\";\n\t\t}else {\n\t\t\tthis.tableElement.style.minWidth = this.table.columnManager.getWidth() + \"px\";\n\t\t\t// this.tableElement.style.minHeight = \"1px\";\n\t\t\t// this.tableElement.style.visibility = \"hidden\";\n\t\t}\n\t}\n\t\n\t_clearTable(){\t\n\t\tthis._clearPlaceholder();\n\t\t\n\t\tthis.scrollTop = 0;\n\t\tthis.scrollLeft = 0;\n\t\t\n\t\tthis.renderer.clearRows();\n\t}\n\t\n\ttableEmpty(){\n\t\tthis.renderEmptyScroll();\n\t\tthis._showPlaceholder();\n\t}\n\n\tcheckPlaceholder(){\n\t\tif(this.displayRowsCount){\n\t\t\tthis._clearPlaceholder();\n\t\t}else {\n\t\t\tthis.tableEmpty();\n\t\t}\n\t}\n\t\n\t_showPlaceholder(){\n\t\tif(this.placeholder){\n\t\t\tif(this.placeholder && this.placeholder.parentNode){\n\t\t\t\tthis.placeholder.parentNode.removeChild(this.placeholder);\n\t\t\t}\n\t\t\t\n\t\t\tthis.initializePlaceholder();\n\t\t\t\n\t\t\tthis.placeholder.setAttribute(\"tabulator-render-mode\", this.renderMode);\n\t\t\t\n\t\t\tthis.getElement().appendChild(this.placeholder);\n\t\t\tthis._positionPlaceholder();\n\n\t\t\tthis.adjustTableSize();\n\t\t}\n\t}\n\t\n\t_clearPlaceholder(){\n\t\tif(this.placeholder && this.placeholder.parentNode){\n\t\t\tthis.placeholder.parentNode.removeChild(this.placeholder);\n\t\t}\n\t\t\n\t\t// clear empty table placeholder min\n\t\tthis.tableElement.style.minWidth = \"\";\n\t\tthis.tableElement.style.display = \"\";\n\t}\n\t\n\t_positionPlaceholder(){\n\t\tif(this.placeholder && this.placeholder.parentNode){\n\t\t\tthis.placeholder.style.width = this.table.columnManager.getWidth() + \"px\";\n\t\t\tthis.placeholderContents.style.width = this.table.rowManager.element.clientWidth + \"px\";\n\t\t\tthis.placeholderContents.style.marginLeft = this.scrollLeft + \"px\";\n\t\t}\n\t}\n\t\n\tstyleRow(row, index){\n\t\tvar rowEl = row.getElement();\n\t\t\n\t\tif(index % 2){\n\t\t\trowEl.classList.add(\"tabulator-row-even\");\n\t\t\trowEl.classList.remove(\"tabulator-row-odd\");\n\t\t}else {\n\t\t\trowEl.classList.add(\"tabulator-row-odd\");\n\t\t\trowEl.classList.remove(\"tabulator-row-even\");\n\t\t}\n\t}\n\t\n\t//normalize height of active rows\n\tnormalizeHeight(){\n\t\tthis.activeRows.forEach(function(row){\n\t\t\trow.normalizeHeight();\n\t\t});\n\t}\n\t\n\t//adjust the height of the table holder to fit in the Tabulator element\n\tadjustTableSize(){\n\t\tlet initialHeight = this.element.clientHeight, minHeight;\n\t\tlet resized = false;\n\t\t\n\t\tif(this.renderer.verticalFillMode === \"fill\"){\n\t\t\tlet otherHeight =  Math.floor(this.table.columnManager.getElement().getBoundingClientRect().height + (this.table.footerManager && this.table.footerManager.active && !this.table.footerManager.external ? this.table.footerManager.getElement().getBoundingClientRect().height : 0));\n\t\t\t\n\t\t\tif(this.fixedHeight){\n\t\t\t\tminHeight = isNaN(this.table.options.minHeight) ? this.table.options.minHeight : this.table.options.minHeight + \"px\";\n\t\t\t\t\n\t\t\t\tconst height = \"calc(100% - \" + otherHeight + \"px)\";\n\t\t\t\tthis.element.style.minHeight = minHeight || \"calc(100% - \" + otherHeight + \"px)\";\n\t\t\t\tthis.element.style.height = height;\n\t\t\t\tthis.element.style.maxHeight = height;\n\t\t\t} else {\n\t\t\t\tthis.element.style.height = \"\";\n\t\t\t\tthis.element.style.height =\n\t\t\t\tthis.table.element.clientHeight - otherHeight + \"px\";\n\t\t\t\tthis.element.scrollTop = this.scrollTop;\n\t\t\t}\n\t\t\t\n\t\t\tthis.renderer.resize();\n\t\t\t\n\t\t\t//check if the table has changed size when dealing with variable height tables\n\t\t\tif(!this.fixedHeight && initialHeight != this.element.clientHeight){\n\t\t\t\tresized = true;\n\t\t\t\tif(this.subscribed(\"table-resize\")){\n\t\t\t\t\tthis.dispatch(\"table-resize\");\n\t\t\t\t}else {\n\t\t\t\t\tthis.redraw();\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\tthis.scrollBarCheck();\n\t\t}\n\t\t\n\t\tthis._positionPlaceholder();\n\t\treturn resized;\n\t}\n\t\n\t//reinitialize all rows\n\treinitialize(){\n\t\tthis.rows.forEach(function(row){\n\t\t\trow.reinitialize(true);\n\t\t});\n\t}\n\t\n\t//prevent table from being redrawn\n\tblockRedraw (){\n\t\tthis.redrawBlock = true;\n\t\tthis.redrawBlockRestoreConfig = false;\n\t}\n\t\n\t//restore table redrawing\n\trestoreRedraw (){\n\t\tthis.redrawBlock = false;\n\t\t\n\t\tif(this.redrawBlockRestoreConfig){\n\t\t\tthis.refreshActiveData(this.redrawBlockRestoreConfig.handler, this.redrawBlockRestoreConfig.skipStage, this.redrawBlockRestoreConfig.renderInPosition);\n\t\t\t\n\t\t\tthis.redrawBlockRestoreConfig = false;\n\t\t}else {\n\t\t\tif(this.redrawBlockRenderInPosition){\n\t\t\t\tthis.reRenderInPosition();\n\t\t\t}\n\t\t}\n\t\t\n\t\tthis.redrawBlockRenderInPosition = false;\n\t}\n\t\n\t//redraw table\n\tredraw (force){\n\t\tthis.adjustTableSize();\n\t\tthis.table.tableWidth = this.table.element.clientWidth;\n\t\t\n\t\tif(!force){\t\n\t\t\tthis.reRenderInPosition();\n\t\t\tthis.scrollHorizontal(this.scrollLeft);\n\t\t}else {\n\t\t\tthis.renderTable();\n\t\t}\n\t}\n\t\n\tresetScroll(){\n\t\tthis.element.scrollLeft = 0;\n\t\tthis.element.scrollTop = 0;\n\t\t\n\t\tif(this.table.browser === \"ie\"){\n\t\t\tvar event = document.createEvent(\"Event\");\n\t\t\tevent.initEvent(\"scroll\", false, true);\n\t\t\tthis.element.dispatchEvent(event);\n\t\t}else {\n\t\t\tthis.element.dispatchEvent(new Event('scroll'));\n\t\t}\n\t}\n}\n\nclass FooterManager extends CoreFeature{\n\n\tconstructor(table){\n\t\tsuper(table);\n\n\t\tthis.active = false;\n\t\tthis.element = this.createElement(); //containing element\n\t\tthis.containerElement = this.createContainerElement(); //containing element\n\t\tthis.external = false;\n\t}\n\n\tinitialize(){\n\t\tthis.initializeElement();\n\t}\n\n\tcreateElement(){\n\t\tvar el = document.createElement(\"div\");\n\n\t\tel.classList.add(\"tabulator-footer\");\n\n\t\treturn el;\n\t}\n\n\t\n\tcreateContainerElement(){\n\t\tvar el = document.createElement(\"div\");\n\n\t\tel.classList.add(\"tabulator-footer-contents\");\n\n\t\tthis.element.appendChild(el);\n\n\t\treturn el;\n\t}\n\n\tinitializeElement(){\n\t\tif(this.table.options.footerElement){\n\n\t\t\tswitch(typeof this.table.options.footerElement){\n\t\t\t\tcase \"string\":\n\t\t\t\t\tif(this.table.options.footerElement[0] === \"<\"){\n\t\t\t\t\t\tthis.containerElement.innerHTML = this.table.options.footerElement;\n\t\t\t\t\t}else {\n\t\t\t\t\t\tthis.external = true;\n\t\t\t\t\t\tthis.containerElement = document.querySelector(this.table.options.footerElement);\n\t\t\t\t\t}\n\t\t\t\t\tbreak;\n\n\t\t\t\tdefault:\n\t\t\t\t\tthis.element = this.table.options.footerElement;\n\t\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t}\n\n\tgetElement(){\n\t\treturn this.element;\n\t}\n\n\tappend(element){\n\t\tthis.activate();\n\n\t\tthis.containerElement.appendChild(element);\n\t\tthis.table.rowManager.adjustTableSize();\n\t}\n\n\tprepend(element){\n\t\tthis.activate();\n\n\t\tthis.element.insertBefore(element, this.element.firstChild);\n\t\tthis.table.rowManager.adjustTableSize();\n\t}\n\n\tremove(element){\n\t\telement.parentNode.removeChild(element);\n\t\tthis.deactivate();\n\t}\n\n\tdeactivate(force){\n\t\tif(!this.element.firstChild || force){\n\t\t\tif(!this.external){\n\t\t\t\tthis.element.parentNode.removeChild(this.element);\n\t\t\t}\n\t\t\tthis.active = false;\n\t\t}\n\t}\n\n\tactivate(){\n\t\tif(!this.active){\n\t\t\tthis.active = true;\n\t\t\tif(!this.external){\n\t\t\t\tthis.table.element.appendChild(this.getElement());\n\t\t\t\tthis.table.element.style.display = '';\n\t\t\t}\n\t\t}\n\t}\n\n\tredraw(){\n\t\tthis.dispatch(\"footer-redraw\");\n\t}\n}\n\nclass InteractionManager extends CoreFeature {\n\t\n\tconstructor (table){\n\t\tsuper(table);\n\t\t\n\t\tthis.el = null;\n\t\t\n\t\tthis.abortClasses = [\"tabulator-headers\", \"tabulator-table\"];\n\t\t\n\t\tthis.previousTargets = {};\n\t\t\n\t\tthis.listeners = [\n\t\t\t\"click\",\n\t\t\t\"dblclick\",\n\t\t\t\"contextmenu\",\n\t\t\t\"mouseenter\",\n\t\t\t\"mouseleave\",\n\t\t\t\"mouseover\",\n\t\t\t\"mouseout\",\n\t\t\t\"mousemove\",\n\t\t\t\"mouseup\",\n\t\t\t\"mousedown\",\n\t\t\t\"touchstart\",\n\t\t\t\"touchend\",\n\t\t];\n\t\t\n\t\tthis.componentMap = {\n\t\t\t\"tabulator-cell\":\"cell\",\n\t\t\t\"tabulator-row\":\"row\",\n\t\t\t\"tabulator-group\":\"group\",\n\t\t\t\"tabulator-col\":\"column\",\n\t\t};\n\t\t\n\t\tthis.pseudoTrackers = {\n\t\t\t\"row\":{\n\t\t\t\tsubscriber:null,\n\t\t\t\ttarget:null,\n\t\t\t},\n\t\t\t\"cell\":{\n\t\t\t\tsubscriber:null,\n\t\t\t\ttarget:null,\n\t\t\t},\n\t\t\t\"group\":{\n\t\t\t\tsubscriber:null,\n\t\t\t\ttarget:null,\n\t\t\t},\n\t\t\t\"column\":{\n\t\t\t\tsubscriber:null,\n\t\t\t\ttarget:null,\n\t\t\t},\n\t\t};\n\t\t\n\t\tthis.pseudoTracking = false;\n\t}\n\t\n\tinitialize(){\n\t\tthis.el = this.table.element;\n\t\t\n\t\tthis.buildListenerMap();\n\t\tthis.bindSubscriptionWatchers();\n\t}\n\t\n\tbuildListenerMap(){\n\t\tvar listenerMap = {};\n\t\t\n\t\tthis.listeners.forEach((listener) => {\n\t\t\tlistenerMap[listener] = {\n\t\t\t\thandler:null,\n\t\t\t\tcomponents:[],\n\t\t\t};\n\t\t});\n\t\t\n\t\tthis.listeners = listenerMap;\n\t}\n\t\n\tbindPseudoEvents(){\n\t\tObject.keys(this.pseudoTrackers).forEach((key) => {\n\t\t\tthis.pseudoTrackers[key].subscriber = this.pseudoMouseEnter.bind(this, key);\n\t\t\tthis.subscribe(key + \"-mouseover\", this.pseudoTrackers[key].subscriber);\n\t\t});\n\t\t\n\t\tthis.pseudoTracking = true;\n\t}\n\t\n\tpseudoMouseEnter(key, e, target){\n\t\tif(this.pseudoTrackers[key].target !== target){\n\t\t\t\n\t\t\tif(this.pseudoTrackers[key].target){\n\t\t\t\tthis.dispatch(key + \"-mouseleave\", e, this.pseudoTrackers[key].target);\n\t\t\t}\n\t\t\t\n\t\t\tthis.pseudoMouseLeave(key, e);\n\t\t\t\n\t\t\tthis.pseudoTrackers[key].target = target;\n\t\t\t\n\t\t\tthis.dispatch(key + \"-mouseenter\", e, target);\n\t\t}\n\t}\n\t\n\tpseudoMouseLeave(key, e){\n\t\tvar leaveList = Object.keys(this.pseudoTrackers),\n\t\tlinkedKeys = {\n\t\t\t\"row\":[\"cell\"],\n\t\t\t\"cell\":[\"row\"],\n\t\t};\n\t\t\n\t\tleaveList = leaveList.filter((item) => {\n\t\t\tvar links = linkedKeys[key];\n\t\t\treturn item !== key && (!links || (links && !links.includes(item)));\n\t\t});\n\t\t\n\t\t\n\t\tleaveList.forEach((key) => {\n\t\t\tvar target = this.pseudoTrackers[key].target;\n\t\t\t\n\t\t\tif(this.pseudoTrackers[key].target){\n\t\t\t\tthis.dispatch(key + \"-mouseleave\", e, target);\n\t\t\t\t\n\t\t\t\tthis.pseudoTrackers[key].target = null;\n\t\t\t}\n\t\t});\n\t}\n\t\n\t\n\tbindSubscriptionWatchers(){\n\t\tvar listeners = Object.keys(this.listeners),\n\t\tcomponents = Object.values(this.componentMap);\n\t\t\n\t\tfor(let comp of components){\n\t\t\tfor(let listener of listeners){\n\t\t\t\tlet key = comp + \"-\" + listener;\n\t\t\t\t\n\t\t\t\tthis.subscriptionChange(key, this.subscriptionChanged.bind(this, comp, listener));\n\t\t\t}\n\t\t}\n\t\t\n\t\tthis.subscribe(\"table-destroy\", this.clearWatchers.bind(this));\n\t}\n\t\n\tsubscriptionChanged(component, key, added){\n\t\tvar listener = this.listeners[key].components,\n\t\tindex = listener.indexOf(component),\n\t\tchanged = false;\n\t\t\n\t\tif(added){\n\t\t\tif(index === -1){\n\t\t\t\tlistener.push(component);\n\t\t\t\tchanged = true;\n\t\t\t}\n\t\t}else {\n\t\t\tif(!this.subscribed(component + \"-\" + key)){\n\t\t\t\tif(index > -1){\n\t\t\t\t\tlistener.splice(index, 1);\n\t\t\t\t\tchanged = true;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\tif((key === \"mouseenter\" || key === \"mouseleave\") && !this.pseudoTracking){\n\t\t\tthis.bindPseudoEvents();\n\t\t}\n\t\t\n\t\tif(changed){\n\t\t\tthis.updateEventListeners();\n\t\t}\n\t}\n\t\n\tupdateEventListeners(){\n\t\tfor(let key in this.listeners){\n\t\t\tlet listener = this.listeners[key];\n\t\t\t\n\t\t\tif(listener.components.length){\n\t\t\t\tif(!listener.handler){\n\t\t\t\t\tlistener.handler = this.track.bind(this, key);\n\t\t\t\t\tthis.el.addEventListener(key, listener.handler);\n\t\t\t\t\t// this.el.addEventListener(key, listener.handler, {passive: true})\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tif(listener.handler){\n\t\t\t\t\tthis.el.removeEventListener(key, listener.handler);\n\t\t\t\t\tlistener.handler = null;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t\n\ttrack(type, e){\n\t\tvar path = (e.composedPath && e.composedPath()) || e.path;\n\t\t\n\t\tvar targets = this.findTargets(path);\n\t\ttargets = this.bindComponents(type, targets);\n\t\t\n\t\tthis.triggerEvents(type, e, targets);\n\t\t\n\t\tif(this.pseudoTracking && (type == \"mouseover\" || type == \"mouseleave\") && !Object.keys(targets).length){\n\t\t\tthis.pseudoMouseLeave(\"none\", e);\n\t\t}\n\t}\n\t\n\tfindTargets(path){\n\t\tvar targets = {};\n\t\t\n\t\tlet componentMap = Object.keys(this.componentMap);\n\t\t\n\t\tfor (let el of path) {\n\t\t\tlet classList = el.classList ? [...el.classList] : [];\n\t\t\t\n\t\t\tlet abort = classList.filter((item) => {\n\t\t\t\treturn this.abortClasses.includes(item);\n\t\t\t});\n\t\t\t\n\t\t\tif(abort.length){\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\t\n\t\t\tlet elTargets = classList.filter((item) => {\n\t\t\t\treturn componentMap.includes(item);\n\t\t\t});\n\t\t\t\n\t\t\tfor (let target of elTargets) {\n\t\t\t\tif(!targets[this.componentMap[target]]){\n\t\t\t\t\ttargets[this.componentMap[target]] = el;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tif(targets.group && targets.group === targets.row){\n\t\t\tdelete targets.row;\n\t\t}\n\n\t\treturn targets;\n\t}\n\t\n\tbindComponents(type, targets){\n\t\t//ensure row component is looked up before cell\n\t\tvar keys = Object.keys(targets).reverse(),\n\t\tlistener = this.listeners[type],\n\t\tmatches = {},\n\t\ttargetMatches = {};\n\t\t\n\t\tfor(let key of keys){\n\t\t\tlet component,\n\t\t\ttarget = targets[key],\n\t\t\tpreviousTarget = this.previousTargets[key];\n\t\t\t\n\t\t\tif(previousTarget && previousTarget.target === target){\n\t\t\t\tcomponent = previousTarget.component;\n\t\t\t}else {\n\t\t\t\tswitch(key){\n\t\t\t\t\tcase \"row\":\n\t\t\t\t\tcase \"group\":\n\t\t\t\t\t\tif(listener.components.includes(\"row\") || listener.components.includes(\"cell\") || listener.components.includes(\"group\")){\n\t\t\t\t\t\t\tlet rows = this.table.rowManager.getVisibleRows(true);\n\t\t\t\t\t\t\n\t\t\t\t\t\t\tcomponent = rows.find((row) => {\n\t\t\t\t\t\t\t\treturn row.getElement() === target;\n\t\t\t\t\t\t\t});\n\t\t\t\t\t\t\n\t\t\t\t\t\t\tif(targets[\"row\"] && targets[\"row\"].parentNode && targets[\"row\"].parentNode.closest(\".tabulator-row\")){\n\t\t\t\t\t\t\t\ttargets[key] = false;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t\n\t\t\t\t\tcase \"column\":\n\t\t\t\t\t\tif(listener.components.includes(\"column\")){\n\t\t\t\t\t\t\tcomponent = this.table.columnManager.findColumn(target);\n\t\t\t\t\t\t}\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t\n\t\t\t\t\tcase \"cell\":\n\t\t\t\t\t\tif(listener.components.includes(\"cell\")){\n\t\t\t\t\t\t\tif(matches[\"row\"] instanceof Row){\n\t\t\t\t\t\t\t\tcomponent = matches[\"row\"].findCell(target);\n\t\t\t\t\t\t\t}else {\t\n\t\t\t\t\t\t\t\tif(targets[\"row\"]){\n\t\t\t\t\t\t\t\t\tconsole.warn(\"Event Target Lookup Error - The row this cell is attached to cannot be found, has the table been reinitialized without being destroyed first?\");\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\tif(component){\n\t\t\t\tmatches[key] = component;\n\t\t\t\ttargetMatches[key] = {\n\t\t\t\t\ttarget:target,\n\t\t\t\t\tcomponent:component,\n\t\t\t\t};\n\t\t\t}\n\t\t}\n\t\t\n\t\tthis.previousTargets = targetMatches;\n\t\t\n\t\treturn matches;\n\t}\n\t\n\ttriggerEvents(type, e, targets){\n\t\tvar listener = this.listeners[type];\n\n\t\tfor(let key in targets){\n\t\t\tif(targets[key] && listener.components.includes(key)){\n\t\t\t\tthis.dispatch(key + \"-\" + type, e, targets[key]);\n\t\t\t}\n\t\t}\n\t}\n\t\n\tclearWatchers(){\n\t\tfor(let key in this.listeners){\n\t\t\tlet listener = this.listeners[key];\n\t\t\t\n\t\t\tif(listener.handler){\n\t\t\t\tthis.el.removeEventListener(key, listener.handler);\n\t\t\t\tlistener.handler = null;\n\t\t\t}\n\t\t}\n\t}\n}\n\nclass ComponentFunctionBinder{\n\n\tconstructor(table){\n\t\tthis.table = table;\n\n\t\tthis.bindings = {};\n\t}\n\n\tbind(type, funcName, handler){\n\t\tif(!this.bindings[type]){\n\t\t\tthis.bindings[type] = {};\n\t\t}\n\n\t\tif(this.bindings[type][funcName]){\n\t\t\tconsole.warn(\"Unable to bind component handler, a matching function name is already bound\", type, funcName, handler);\n\t\t}else {\n\t\t\tthis.bindings[type][funcName] = handler;\n\t\t}\n\t}\n\n\thandle(type, component, name){\n\t\tif(this.bindings[type] && this.bindings[type][name] && typeof this.bindings[type][name].bind === 'function'){\n\t\t\treturn this.bindings[type][name].bind(null, component);\n\t\t}else {\n\t\t\tif(name !== \"then\" && typeof name === \"string\" && !name.startsWith(\"_\")){\n\t\t\t\tif(this.table.options.debugInvalidComponentFuncs){\n\t\t\t\t\tconsole.error(\"The \" + type + \" component does not have a \" + name + \" function, have you checked that you have the correct Tabulator module installed?\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n}\n\nclass DataLoader extends CoreFeature{\n\tconstructor(table){\n\t\tsuper(table);\n\t\t\n\t\tthis.requestOrder = 0; //prevent requests coming out of sequence if overridden by another load request\n\t\tthis.loading = false;\n\t}\n\t\n\tinitialize(){}\n\t\n\tload(data, params, config, replace, silent, columnsChanged){\n\t\tvar requestNo = ++this.requestOrder;\n\n\t\tif(this.table.destroyed){\n\t\t\treturn Promise.resolve();\n\t\t}\n\t\t\n\t\tthis.dispatchExternal(\"dataLoading\", data);\n\t\t\n\t\t//parse json data to array\n\t\tif (data && (data.indexOf(\"{\") == 0 || data.indexOf(\"[\") == 0)){\n\t\t\tdata = JSON.parse(data);\n\t\t}\n\t\t\n\t\tif(this.confirm(\"data-loading\", [data, params, config, silent])){\n\t\t\tthis.loading = true;\n\t\t\t\n\t\t\tif(!silent){\n\t\t\t\tthis.alertLoader();\n\t\t\t}\n\t\t\t\n\t\t\t//get params for request\n\t\t\tparams = this.chain(\"data-params\", [data, config, silent], params || {}, params || {});\n\t\t\t\n\t\t\tparams = this.mapParams(params, this.table.options.dataSendParams);\n\t\t\t\n\t\t\tvar result = this.chain(\"data-load\", [data, params, config, silent], false, Promise.resolve([]));\n\t\t\t\n\t\t\treturn result.then((response) => {\n\t\t\t\tif(!this.table.destroyed){\n\t\t\t\t\tif(!Array.isArray(response) && typeof response == \"object\"){\n\t\t\t\t\t\tresponse = this.mapParams(response, this.objectInvert(this.table.options.dataReceiveParams));\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\tvar rowData = this.chain(\"data-loaded\", response, null, response);\n\t\t\t\t\t\n\t\t\t\t\tif(requestNo == this.requestOrder){\n\t\t\t\t\t\tthis.clearAlert();\n\t\t\t\t\t\t\n\t\t\t\t\t\tif(rowData !== false){\n\t\t\t\t\t\t\tthis.dispatchExternal(\"dataLoaded\", rowData);\n\t\t\t\t\t\t\tthis.table.rowManager.setData(rowData,  replace, typeof columnsChanged === \"undefined\" ? !replace : columnsChanged);\n\t\t\t\t\t\t}\n\t\t\t\t\t}else {\n\t\t\t\t\t\tconsole.warn(\"Data Load Response Blocked - An active data load request was blocked by an attempt to change table data while the request was being made\");\n\t\t\t\t\t}\n\t\t\t\t}else {\n\t\t\t\t\tconsole.warn(\"Data Load Response Blocked - Table has been destroyed\");\n\t\t\t\t}\n\t\t\t}).catch((error) => {\n\t\t\t\tconsole.error(\"Data Load Error: \", error);\n\t\t\t\tthis.dispatchExternal(\"dataLoadError\", error);\n\t\t\t\t\n\t\t\t\tif(!silent){\n\t\t\t\t\tthis.alertError();\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tsetTimeout(() => {\n\t\t\t\t\tthis.clearAlert();\n\t\t\t\t}, this.table.options.dataLoaderErrorTimeout);\n\t\t\t})\n\t\t\t\t.finally(() => {\n\t\t\t\t\tthis.loading = false;\n\t\t\t\t});\n\t\t}else {\n\t\t\tthis.dispatchExternal(\"dataLoaded\", data);\n\t\t\t\n\t\t\tif(!data){\n\t\t\t\tdata = [];\n\t\t\t}\n\t\t\t\n\t\t\tthis.table.rowManager.setData(data, replace, typeof columnsChanged === \"undefined\" ? !replace : columnsChanged);\n\t\t\treturn Promise.resolve();\n\t\t}\n\t}\n\t\n\tmapParams(params, map){\n\t\tvar output = {};\n\t\t\n\t\tfor(let key in params){\n\t\t\toutput[map.hasOwnProperty(key) ? map[key] : key] = params[key];\n\t\t}\n\t\t\n\t\treturn output;\n\t}\n\t\n\tobjectInvert(obj){\n\t\tvar output = {};\n\t\t\n\t\tfor(let key in obj){\n\t\t\toutput[obj[key]] = key;\n\t\t}\n\t\t\n\t\treturn output;\n\t}\n\t\n\tblockActiveLoad(){\n\t\tthis.requestOrder++;\n\t}\n\t\n\talertLoader(){\n\t\tvar shouldLoad = typeof this.table.options.dataLoader === \"function\" ? this.table.options.dataLoader() : this.table.options.dataLoader;\n\t\t\n\t\tif(shouldLoad){\n\t\t\tthis.table.alertManager.alert(this.table.options.dataLoaderLoading || this.langText(\"data|loading\"));\n\t\t}\n\t}\n\t\n\talertError(){\n\t\tthis.table.alertManager.alert(this.table.options.dataLoaderError || this.langText(\"data|error\"), \"error\");\n\t}\n\t\n\tclearAlert(){\n\t\tthis.table.alertManager.clear();\n\t}\n}\n\nclass ExternalEventBus {\n\n\tconstructor(table, optionsList, debug){\n\t\tthis.table = table;\n\t\tthis.events = {};\n\t\tthis.optionsList = optionsList || {};\n\t\tthis.subscriptionNotifiers = {};\n\n\t\tthis.dispatch = debug ? this._debugDispatch.bind(this) : this._dispatch.bind(this);\n\t\tthis.debug = debug;\n\t}\n\n\tsubscriptionChange(key, callback){\n\t\tif(!this.subscriptionNotifiers[key]){\n\t\t\tthis.subscriptionNotifiers[key] = [];\n\t\t}\n\n\t\tthis.subscriptionNotifiers[key].push(callback);\n\n\t\tif(this.subscribed(key)){\n\t\t\tthis._notifySubscriptionChange(key, true);\n\t\t}\n\t}\n\n\tsubscribe(key, callback){\n\t\tif(!this.events[key]){\n\t\t\tthis.events[key] = [];\n\t\t}\n\n\t\tthis.events[key].push(callback);\n\n\t\tthis._notifySubscriptionChange(key, true);\n\t}\n\n\tunsubscribe(key, callback){\n\t\tvar index;\n\n\t\tif(this.events[key]){\n\t\t\tif(callback){\n\t\t\t\tindex = this.events[key].findIndex((item) => {\n\t\t\t\t\treturn item === callback;\n\t\t\t\t});\n\n\t\t\t\tif(index > -1){\n\t\t\t\t\tthis.events[key].splice(index, 1);\n\t\t\t\t}else {\n\t\t\t\t\tconsole.warn(\"Cannot remove event, no matching event found:\", key, callback);\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tdelete this.events[key];\n\t\t\t}\n\t\t}else {\n\t\t\tconsole.warn(\"Cannot remove event, no events set on:\", key);\n\t\t\treturn;\n\t\t}\n\n\t\tthis._notifySubscriptionChange(key, false);\n\t}\n\n\tsubscribed(key){\n\t\treturn this.events[key] && this.events[key].length;\n\t}\n\n\t_notifySubscriptionChange(key, subscribed){\n\t\tvar notifiers = this.subscriptionNotifiers[key];\n\n\t\tif(notifiers){\n\t\t\tnotifiers.forEach((callback)=>{\n\t\t\t\tcallback(subscribed);\n\t\t\t});\n\t\t}\n\t}\n\n\t_dispatch(){\n\t\tvar args = Array.from(arguments),\n\t\tkey = args.shift(),\n\t\tresult;\n\n\t\tif(this.events[key]){\n\t\t\tthis.events[key].forEach((callback, i) => {\n\t\t\t\tlet callResult = callback.apply(this.table, args);\n\n\t\t\t\tif(!i){\n\t\t\t\t\tresult = callResult;\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t_debugDispatch(){\n\t\tvar args = Array.from(arguments),\n\t\tkey = args[0];\n\n\t\targs[0] = \"ExternalEvent:\" + args[0];\n\n\t\tif(this.debug === true || this.debug.includes(key)){\n\t\t\tconsole.log(...args);\n\t\t}\n\n\t\treturn this._dispatch(...arguments);\n\t}\n}\n\nclass InternalEventBus {\n\n\tconstructor(debug){\n\t\tthis.events = {};\n\t\tthis.subscriptionNotifiers = {};\n\n\t\tthis.dispatch = debug ? this._debugDispatch.bind(this) : this._dispatch.bind(this);\n\t\tthis.chain = debug ? this._debugChain.bind(this) : this._chain.bind(this);\n\t\tthis.confirm = debug ? this._debugConfirm.bind(this) : this._confirm.bind(this);\n\t\tthis.debug = debug;\n\t}\n\n\tsubscriptionChange(key, callback){\n\t\tif(!this.subscriptionNotifiers[key]){\n\t\t\tthis.subscriptionNotifiers[key] = [];\n\t\t}\n\n\t\tthis.subscriptionNotifiers[key].push(callback);\n\n\t\tif(this.subscribed(key)){\n\t\t\tthis._notifySubscriptionChange(key, true);\n\t\t}\n\t}\n\n\tsubscribe(key, callback, priority = 10000){\n\t\tif(!this.events[key]){\n\t\t\tthis.events[key] = [];\n\t\t}\n\n\t\tthis.events[key].push({callback, priority});\n\n\t\tthis.events[key].sort((a, b) => {\n\t\t\treturn a.priority - b.priority;\n\t\t});\n\n\t\tthis._notifySubscriptionChange(key, true);\n\t}\n\n\tunsubscribe(key, callback){\n\t\tvar index;\n\n\t\tif(this.events[key]){\n\t\t\tif(callback){\n\t\t\t\tindex = this.events[key].findIndex((item) => {\n\t\t\t\t\treturn item.callback === callback;\n\t\t\t\t});\n\n\t\t\t\tif(index > -1){\n\t\t\t\t\tthis.events[key].splice(index, 1);\n\t\t\t\t}else {\n\t\t\t\t\tconsole.warn(\"Cannot remove event, no matching event found:\", key, callback);\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t}\n\t\t}else {\n\t\t\tconsole.warn(\"Cannot remove event, no events set on:\", key);\n\t\t\treturn;\n\t\t}\n\n\t\tthis._notifySubscriptionChange(key, false);\n\t}\n\n\tsubscribed(key){\n\t\treturn this.events[key] && this.events[key].length;\n\t}\n\n\t_chain(key, args, initialValue, fallback){\n\t\tvar value = initialValue;\n\n\t\tif(!Array.isArray(args)){\n\t\t\targs = [args];\n\t\t}\n\n\t\tif(this.subscribed(key)){\n\t\t\tthis.events[key].forEach((subscriber, i) => {\n\t\t\t\tvalue = subscriber.callback.apply(this, args.concat([value]));\n\t\t\t});\n\n\t\t\treturn value;\n\t\t}else {\n\t\t\treturn typeof fallback === \"function\" ? fallback() : fallback;\n\t\t}\n\t}\n\n\t_confirm(key, args){\n\t\tvar confirmed = false;\n\n\t\tif(!Array.isArray(args)){\n\t\t\targs = [args];\n\t\t}\n\n\t\tif(this.subscribed(key)){\n\t\t\tthis.events[key].forEach((subscriber, i) => {\n\t\t\t\tif(subscriber.callback.apply(this, args)){\n\t\t\t\t\tconfirmed = true;\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\n\t\treturn confirmed;\n\t}\n\n\t_notifySubscriptionChange(key, subscribed){\n\t\tvar notifiers = this.subscriptionNotifiers[key];\n\n\t\tif(notifiers){\n\t\t\tnotifiers.forEach((callback)=>{\n\t\t\t\tcallback(subscribed);\n\t\t\t});\n\t\t}\n\t}\n\n\t_dispatch(){\n\t\tvar args = Array.from(arguments),\n\t\tkey = args.shift();\n\n\t\tif(this.events[key]){\n\t\t\tthis.events[key].forEach((subscriber) => {\n\t\t\t\tsubscriber.callback.apply(this, args);\n\t\t\t});\n\t\t}\n\t}\n\n\t_debugDispatch(){\n\t\tvar args = Array.from(arguments),\n\t\tkey = args[0];\n\n\t\targs[0] = \"InternalEvent:\" + key;\n\n\t\tif(this.debug === true || this.debug.includes(key)){\n\t\t\tconsole.log(...args);\n\t\t}\n\n\t\treturn this._dispatch(...arguments);\n\t}\n\n\t_debugChain(){\n\t\tvar args = Array.from(arguments),\n\t\tkey = args[0];\n\n\t\targs[0] = \"InternalEvent:\" + key;\n\n\t\tif(this.debug === true || this.debug.includes(key)){\n\t\t\tconsole.log(...args);\n\t\t}\n\n\t\treturn this._chain(...arguments);\n\t}\n\n\t_debugConfirm(){\n\t\tvar args = Array.from(arguments),\n\t\tkey = args[0];\n\n\t\targs[0] = \"InternalEvent:\" + key;\n\n\t\tif(this.debug === true || this.debug.includes(key)){\n\t\t\tconsole.log(...args);\n\t\t}\n\n\t\treturn this._confirm(...arguments);\n\t}\n}\n\nclass DeprecationAdvisor extends CoreFeature{\n\t\n\tconstructor(table){\n\t\tsuper(table);\n\t}\n\t\n\t_warnUser(){\n\t\tif(this.options(\"debugDeprecation\")){\n\t\t\tconsole.warn(...arguments);\n\t\t}\n\t}\n\t\n\tcheck(oldOption, newOption, convert){\n\t\tvar msg = \"\";\n\t\t\n\t\tif(typeof this.options(oldOption) !== \"undefined\"){\n\t\t\tmsg = \"Deprecated Setup Option - Use of the %c\" + oldOption + \"%c option is now deprecated\";\n\t\t\t\n\t\t\tif(newOption){\n\t\t\t\tmsg = msg + \", Please use the %c\" + newOption + \"%c option instead\";\n\t\t\t\tthis._warnUser(msg, 'font-weight: bold;', 'font-weight: normal;', 'font-weight: bold;', 'font-weight: normal;');\n\n\t\t\t\tif(convert){\n\t\t\t\t\tthis.table.options[newOption] = this.table.options[oldOption];\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tthis._warnUser(msg, 'font-weight: bold;', 'font-weight: normal;');\n\t\t\t}\n\t\t\t\n\t\t\treturn false;\n\t\t}else {\n\t\t\treturn true;\n\t\t}\n\t}\n\t\n\tcheckMsg(oldOption, msg){\n\t\tif(typeof this.options(oldOption) !== \"undefined\"){\n\t\t\tthis._warnUser(\"%cDeprecated Setup Option - Use of the %c\" + oldOption + \" %c option is now deprecated, \" + msg, 'font-weight: normal;', 'font-weight: bold;', 'font-weight: normal;');\n\t\t\t\n\t\t\treturn false;\n\t\t}else {\n\t\t\treturn true;\n\t\t}\n\t}\n\t\n\tmsg(msg){\n\t\tthis._warnUser(msg);\n\t}\n}\n\nclass TableRegistry {\n\n\tstatic register(table){\n\t\tTableRegistry.tables.push(table);\n\t}\n\n\tstatic deregister(table){\n\t\tvar index = TableRegistry.tables.indexOf(table);\n\n\t\tif(index > -1){\n\t\t\tTableRegistry.tables.splice(index, 1);\n\t\t}\n\t}\n\n\tstatic lookupTable(query, silent){\n\t\tvar results = [],\n\t\tmatches, match;\n\n\t\tif(typeof query === \"string\"){\n\t\t\tmatches = document.querySelectorAll(query);\n\n\t\t\tif(matches.length){\n\t\t\t\tfor(var i = 0; i < matches.length; i++){\n\t\t\t\t\tmatch = TableRegistry.matchElement(matches[i]);\n\n\t\t\t\t\tif(match){\n\t\t\t\t\t\tresults.push(match);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t}else if((typeof HTMLElement !== \"undefined\" && query instanceof HTMLElement) || query instanceof Tabulator){\n\t\t\tmatch = TableRegistry.matchElement(query);\n\n\t\t\tif(match){\n\t\t\t\tresults.push(match);\n\t\t\t}\n\t\t}else if(Array.isArray(query)){\n\t\t\tquery.forEach(function(item){\n\t\t\t\tresults = results.concat(TableRegistry.lookupTable(item));\n\t\t\t});\n\t\t}else {\n\t\t\tif(!silent){\n\t\t\t\tconsole.warn(\"Table Connection Error - Invalid Selector\", query);\n\t\t\t}\n\t\t}\n\n\t\treturn results;\n\t}\n\n\tstatic matchElement(element){\n\t\treturn TableRegistry.tables.find(function(table){\n\t\t\treturn element instanceof Tabulator ? table === element : table.element === element;\n\t\t});\n\t}\n}\n\nTableRegistry.tables = [];\n\n//resize columns to fit data they contain\nfunction fitData(columns, forced){\n\tif(forced){\n\t\tthis.table.columnManager.renderer.reinitializeColumnWidths(columns);\n\t}\n\t\n\tif(this.table.options.responsiveLayout && this.table.modExists(\"responsiveLayout\", true)){\n\t\tthis.table.modules.responsiveLayout.update();\n\t}\n}\n\n//resize columns to fit data they contain and stretch row to fill table, also used for fitDataTable\nfunction fitDataGeneral(columns, forced){\n\tcolumns.forEach(function(column){\n\t\tcolumn.reinitializeWidth();\n\t});\n\n\tif(this.table.options.responsiveLayout && this.table.modExists(\"responsiveLayout\", true)){\n\t\tthis.table.modules.responsiveLayout.update();\n\t}\n}\n\n//resize columns to fit data the contain and stretch last column to fill table\nfunction fitDataStretch(columns, forced){\n\tvar colsWidth = 0,\n\ttableWidth = this.table.rowManager.element.clientWidth,\n\tgap = 0,\n\tlastCol = false;\n\n\tcolumns.forEach((column, i) => {\n\t\tif(!column.widthFixed){\n\t\t\tcolumn.reinitializeWidth();\n\t\t}\n\n\t\tif(this.table.options.responsiveLayout ? column.modules.responsive.visible : column.visible){\n\t\t\tlastCol = column;\n\t\t}\n\n\t\tif(column.visible){\n\t\t\tcolsWidth += column.getWidth();\n\t\t}\n\t});\n\n\tif(lastCol){\n\t\tgap = tableWidth - colsWidth + lastCol.getWidth();\n\n\t\tif(this.table.options.responsiveLayout && this.table.modExists(\"responsiveLayout\", true)){\n\t\t\tlastCol.setWidth(0);\n\t\t\tthis.table.modules.responsiveLayout.update();\n\t\t}\n\n\t\tif(gap > 0){\n\t\t\tlastCol.setWidth(gap);\n\t\t}else {\n\t\t\tlastCol.reinitializeWidth();\n\t\t}\n\t}else {\n\t\tif(this.table.options.responsiveLayout && this.table.modExists(\"responsiveLayout\", true)){\n\t\t\tthis.table.modules.responsiveLayout.update();\n\t\t}\n\t}\n}\n\n//resize columns to fit\nfunction fitColumns(columns, forced){\n\tvar totalWidth = this.table.rowManager.element.getBoundingClientRect().width; //table element width\n\tvar fixedWidth = 0; //total width of columns with a defined width\n\tvar flexWidth = 0; //total width available to flexible columns\n\tvar flexGrowUnits = 0; //total number of widthGrow blocks across all columns\n\tvar flexColWidth = 0; //desired width of flexible columns\n\tvar flexColumns = []; //array of flexible width columns\n\tvar fixedShrinkColumns = []; //array of fixed width columns that can shrink\n\tvar flexShrinkUnits = 0; //total number of widthShrink blocks across all columns\n\tvar overflowWidth = 0; //horizontal overflow width\n\tvar gapFill = 0; //number of pixels to be added to final column to close and half pixel gaps\n\n\tfunction calcWidth(width){\n\t\tvar colWidth;\n\n\t\tif(typeof(width) == \"string\"){\n\t\t\tif(width.indexOf(\"%\") > -1){\n\t\t\t\tcolWidth = (totalWidth / 100) * parseInt(width);\n\t\t\t}else {\n\t\t\t\tcolWidth = parseInt(width);\n\t\t\t}\n\t\t}else {\n\t\t\tcolWidth = width;\n\t\t}\n\n\t\treturn colWidth;\n\t}\n\n\t//ensure columns resize to take up the correct amount of space\n\tfunction scaleColumns(columns, freeSpace, colWidth, shrinkCols){\n\t\tvar oversizeCols = [],\n\t\toversizeSpace = 0,\n\t\tremainingSpace = 0,\n\t\tnextColWidth = 0,\n\t\tremainingFlexGrowUnits = flexGrowUnits,\n\t\tgap = 0,\n\t\tchangeUnits = 0,\n\t\tundersizeCols = [];\n\n\t\tfunction calcGrow(col){\n\t\t\treturn (colWidth * (col.column.definition.widthGrow || 1));\n\t\t}\n\n\t\tfunction calcShrink(col){\n\t\t\treturn  (calcWidth(col.width) - (colWidth * (col.column.definition.widthShrink || 0)));\n\t\t}\n\n\t\tcolumns.forEach(function(col, i){\n\t\t\tvar width = shrinkCols ? calcShrink(col) : calcGrow(col);\n\t\t\tif(col.column.minWidth >= width){\n\t\t\t\toversizeCols.push(col);\n\t\t\t}else {\n\t\t\t\tif(col.column.maxWidth && col.column.maxWidth < width){\n\t\t\t\t\tcol.width = col.column.maxWidth;\n\t\t\t\t\tfreeSpace -= col.column.maxWidth;\n\n\t\t\t\t\tremainingFlexGrowUnits -= shrinkCols ? (col.column.definition.widthShrink || 1) : (col.column.definition.widthGrow || 1);\n\n\t\t\t\t\tif(remainingFlexGrowUnits){\n\t\t\t\t\t\tcolWidth = Math.floor(freeSpace/remainingFlexGrowUnits);\n\t\t\t\t\t}\n\t\t\t\t}else {\n\t\t\t\t\tundersizeCols.push(col);\n\t\t\t\t\tchangeUnits += shrinkCols ? (col.column.definition.widthShrink || 1) : (col.column.definition.widthGrow || 1);\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\n\t\tif(oversizeCols.length){\n\t\t\toversizeCols.forEach(function(col){\n\t\t\t\toversizeSpace += shrinkCols ?  col.width - col.column.minWidth : col.column.minWidth;\n\t\t\t\tcol.width = col.column.minWidth;\n\t\t\t});\n\n\t\t\tremainingSpace = freeSpace - oversizeSpace;\n\n\t\t\tnextColWidth = changeUnits ? Math.floor(remainingSpace/changeUnits) : remainingSpace;\n\n\t\t\tgap = scaleColumns(undersizeCols, remainingSpace, nextColWidth, shrinkCols);\n\t\t}else {\n\t\t\tgap = changeUnits ? freeSpace - (Math.floor(freeSpace/changeUnits) * changeUnits) : freeSpace;\n\n\t\t\tundersizeCols.forEach(function(column){\n\t\t\t\tcolumn.width = shrinkCols ? calcShrink(column) : calcGrow(column);\n\t\t\t});\n\t\t}\n\n\t\treturn gap;\n\t}\n\n\tif(this.table.options.responsiveLayout && this.table.modExists(\"responsiveLayout\", true)){\n\t\tthis.table.modules.responsiveLayout.update();\n\t}\n\n\t//adjust for vertical scrollbar if present\n\tif(this.table.rowManager.element.scrollHeight > this.table.rowManager.element.clientHeight){\n\t\ttotalWidth -= this.table.rowManager.element.offsetWidth - this.table.rowManager.element.clientWidth;\n\t}\n\n\tcolumns.forEach(function(column){\n\t\tvar width, minWidth, colWidth;\n\n\t\tif(column.visible){\n\n\t\t\twidth = column.definition.width;\n\t\t\tminWidth =  parseInt(column.minWidth);\n\n\t\t\tif(width){\n\n\t\t\t\tcolWidth = calcWidth(width);\n\n\t\t\t\tfixedWidth += colWidth > minWidth ? colWidth : minWidth;\n\n\t\t\t\tif(column.definition.widthShrink){\n\t\t\t\t\tfixedShrinkColumns.push({\n\t\t\t\t\t\tcolumn:column,\n\t\t\t\t\t\twidth:colWidth > minWidth ? colWidth : minWidth\n\t\t\t\t\t});\n\t\t\t\t\tflexShrinkUnits += column.definition.widthShrink;\n\t\t\t\t}\n\n\t\t\t}else {\n\t\t\t\tflexColumns.push({\n\t\t\t\t\tcolumn:column,\n\t\t\t\t\twidth:0,\n\t\t\t\t});\n\t\t\t\tflexGrowUnits += column.definition.widthGrow || 1;\n\t\t\t}\n\t\t}\n\t});\n\n\t//calculate available space\n\tflexWidth = totalWidth - fixedWidth;\n\n\t//calculate correct column size\n\tflexColWidth = Math.floor(flexWidth / flexGrowUnits);\n\n\t//generate column widths\n\tgapFill = scaleColumns(flexColumns, flexWidth, flexColWidth, false);\n\n\t//increase width of last column to account for rounding errors\n\tif(flexColumns.length && gapFill > 0){\n\t\tflexColumns[flexColumns.length-1].width += gapFill;\n\t}\n\n\t//calculate space for columns to be shrunk into\n\tflexColumns.forEach(function(col){\n\t\tflexWidth -= col.width;\n\t});\n\n\toverflowWidth = Math.abs(gapFill) + flexWidth;\n\n\t//shrink oversize columns if there is no available space\n\tif(overflowWidth > 0 && flexShrinkUnits){\n\t\tgapFill = scaleColumns(fixedShrinkColumns, overflowWidth, Math.floor(overflowWidth / flexShrinkUnits), true);\n\t}\n\n\t//decrease width of last column to account for rounding errors\n\tif(gapFill && fixedShrinkColumns.length){\n\t\tfixedShrinkColumns[fixedShrinkColumns.length-1].width -= gapFill;\n\t}\n\n\tflexColumns.forEach(function(col){\n\t\tcol.column.setWidth(col.width);\n\t});\n\n\tfixedShrinkColumns.forEach(function(col){\n\t\tcol.column.setWidth(col.width);\n\t});\n}\n\nvar defaultModes = {\n\tfitData:fitData,\n\tfitDataFill:fitDataGeneral,\n\tfitDataTable:fitDataGeneral,\n\tfitDataStretch:fitDataStretch,\n\tfitColumns:fitColumns ,\n};\n\nclass Layout extends Module{\n\n\tconstructor(table){\n\t\tsuper(table, \"layout\");\n\n\t\tthis.mode = null;\n\n\t\tthis.registerTableOption(\"layout\", \"fitData\"); //layout type\n\t\tthis.registerTableOption(\"layoutColumnsOnNewData\", false); //update column widths on setData\n\n\t\tthis.registerColumnOption(\"widthGrow\");\n\t\tthis.registerColumnOption(\"widthShrink\");\n\t}\n\n\t//initialize layout system\n\tinitialize(){\n\t\tvar layout = this.table.options.layout;\n\n\t\tif(Layout.modes[layout]){\n\t\t\tthis.mode = layout;\n\t\t}else {\n\t\t\tconsole.warn(\"Layout Error - invalid mode set, defaulting to 'fitData' : \" + layout);\n\t\t\tthis.mode = 'fitData';\n\t\t}\n\n\t\tthis.table.element.setAttribute(\"tabulator-layout\", this.mode);\n\t\tthis.subscribe(\"column-init\", this.initializeColumn.bind(this));\n\t}\n\n\tinitializeColumn(column){\n\t\tif(column.definition.widthGrow){\n\t\t\tcolumn.definition.widthGrow = Number(column.definition.widthGrow);\n\t\t}\n\t\tif(column.definition.widthShrink){\n\t\t\tcolumn.definition.widthShrink = Number(column.definition.widthShrink);\n\t\t}\n\t}\n\n\tgetMode(){\n\t\treturn this.mode;\n\t}\n\n\t//trigger table layout\n\tlayout(dataChanged){\n\t\tthis.dispatch(\"layout-refreshing\");\n\t\tLayout.modes[this.mode].call(this, this.table.columnManager.columnsByIndex, dataChanged);\n\t\tthis.dispatch(\"layout-refreshed\");\n\t}\n}\n\nLayout.moduleName = \"layout\";\n\n//load defaults\nLayout.modes = defaultModes;\n\nvar defaultLangs = {\n\t\"default\":{ //hold default locale text\n\t\t\"groups\":{\n\t\t\t\"item\":\"item\",\n\t\t\t\"items\":\"items\",\n\t\t},\n\t\t\"columns\":{\n\t\t},\n\t\t\"data\":{\n\t\t\t\"loading\":\"Loading\",\n\t\t\t\"error\":\"Error\",\n\t\t},\n\t\t\"pagination\":{\n\t\t\t\"page_size\":\"Page Size\",\n\t\t\t\"page_title\":\"Show Page\",\n\t\t\t\"first\":\"First\",\n\t\t\t\"first_title\":\"First Page\",\n\t\t\t\"last\":\"Last\",\n\t\t\t\"last_title\":\"Last Page\",\n\t\t\t\"prev\":\"Prev\",\n\t\t\t\"prev_title\":\"Prev Page\",\n\t\t\t\"next\":\"Next\",\n\t\t\t\"next_title\":\"Next Page\",\n\t\t\t\"all\":\"All\",\n\t\t\t\"counter\":{\n\t\t\t\t\"showing\": \"Showing\",\n\t\t\t\t\"of\": \"of\",\n\t\t\t\t\"rows\": \"rows\",\n\t\t\t\t\"pages\": \"pages\",\n\t\t\t}\n\t\t},\n\t\t\"headerFilters\":{\n\t\t\t\"default\":\"filter column...\",\n\t\t\t\"columns\":{}\n\t\t}\n\t},\n};\n\nclass Localize extends Module{\n\n\tconstructor(table){\n\t\tsuper(table);\n\n\t\tthis.locale = \"default\"; //current locale\n\t\tthis.lang = false; //current language\n\t\tthis.bindings = {}; //update events to call when locale is changed\n\t\tthis.langList = {};\n\n\t\tthis.registerTableOption(\"locale\", false); //current system language\n\t\tthis.registerTableOption(\"langs\", {});\n\t}\n\n\tinitialize(){\n\t\tthis.langList = Helpers.deepClone(Localize.langs);\n\n\t\tif(this.table.options.columnDefaults.headerFilterPlaceholder !== false){\n\t\t\tthis.setHeaderFilterPlaceholder(this.table.options.columnDefaults.headerFilterPlaceholder);\n\t\t}\n\n\t\tfor(let locale in this.table.options.langs){\n\t\t\tthis.installLang(locale, this.table.options.langs[locale]);\n\t\t}\n\n\t\tthis.setLocale(this.table.options.locale);\n\n\t\tthis.registerTableFunction(\"setLocale\", this.setLocale.bind(this));\n\t\tthis.registerTableFunction(\"getLocale\", this.getLocale.bind(this));\n\t\tthis.registerTableFunction(\"getLang\", this.getLang.bind(this));\n\t}\n\n\t//set header placeholder\n\tsetHeaderFilterPlaceholder(placeholder){\n\t\tthis.langList.default.headerFilters.default = placeholder;\n\t}\n\n\t//setup a lang description object\n\tinstallLang(locale, lang){\n\t\tif(this.langList[locale]){\n\t\t\tthis._setLangProp(this.langList[locale], lang);\n\t\t}else {\n\t\t\tthis.langList[locale] = lang;\n\t\t}\n\t}\n\n\t_setLangProp(lang, values){\n\t\tfor(let key in values){\n\t\t\tif(lang[key] && typeof lang[key] == \"object\"){\n\t\t\t\tthis._setLangProp(lang[key], values[key]);\n\t\t\t}else {\n\t\t\t\tlang[key] = values[key];\n\t\t\t}\n\t\t}\n\t}\n\n\t//set current locale\n\tsetLocale(desiredLocale){\n\t\tdesiredLocale = desiredLocale || \"default\";\n\n\t\t//fill in any matching language values\n\t\tfunction traverseLang(trans, path){\n\t\t\tfor(var prop in trans){\n\t\t\t\tif(typeof trans[prop] == \"object\"){\n\t\t\t\t\tif(!path[prop]){\n\t\t\t\t\t\tpath[prop] = {};\n\t\t\t\t\t}\n\t\t\t\t\ttraverseLang(trans[prop], path[prop]);\n\t\t\t\t}else {\n\t\t\t\t\tpath[prop] = trans[prop];\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t//determining correct locale to load\n\t\tif(desiredLocale === true && navigator.language){\n\t\t\t//get local from system\n\t\t\tdesiredLocale = navigator.language.toLowerCase();\n\t\t}\n\n\t\tif(desiredLocale){\n\t\t\t//if locale is not set, check for matching top level locale else use default\n\t\t\tif(!this.langList[desiredLocale]){\n\t\t\t\tlet prefix = desiredLocale.split(\"-\")[0];\n\n\t\t\t\tif(this.langList[prefix]){\n\t\t\t\t\tconsole.warn(\"Localization Error - Exact matching locale not found, using closest match: \", desiredLocale, prefix);\n\t\t\t\t\tdesiredLocale = prefix;\n\t\t\t\t}else {\n\t\t\t\t\tconsole.warn(\"Localization Error - Matching locale not found, using default: \", desiredLocale);\n\t\t\t\t\tdesiredLocale = \"default\";\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tthis.locale = desiredLocale;\n\n\t\t//load default lang template\n\t\tthis.lang = Helpers.deepClone(this.langList.default || {});\n\n\t\tif(desiredLocale != \"default\"){\n\t\t\ttraverseLang(this.langList[desiredLocale], this.lang);\n\t\t}\n\n\t\tthis.dispatchExternal(\"localized\", this.locale, this.lang);\n\n\t\tthis._executeBindings();\n\t}\n\n\t//get current locale\n\tgetLocale(locale){\n\t\treturn this.locale;\n\t}\n\n\t//get lang object for given local or current if none provided\n\tgetLang(locale){\n\t\treturn locale ? this.langList[locale] : this.lang;\n\t}\n\n\t//get text for current locale\n\tgetText(path, value){\n\t\tvar fillPath = value ? path + \"|\" + value : path,\n\t\tpathArray = fillPath.split(\"|\"),\n\t\ttext = this._getLangElement(pathArray, this.locale);\n\n\t\t// if(text === false){\n\t\t// \tconsole.warn(\"Localization Error - Matching localized text not found for given path: \", path);\n\t\t// }\n\n\t\treturn text || \"\";\n\t}\n\n\t//traverse langs object and find localized copy\n\t_getLangElement(path, locale){\n\t\tvar root = this.lang;\n\n\t\tpath.forEach(function(level){\n\t\t\tvar rootPath;\n\n\t\t\tif(root){\n\t\t\t\trootPath = root[level];\n\n\t\t\t\tif(typeof rootPath != \"undefined\"){\n\t\t\t\t\troot = rootPath;\n\t\t\t\t}else {\n\t\t\t\t\troot = false;\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\n\t\treturn root;\n\t}\n\n\t//set update binding\n\tbind(path, callback){\n\t\tif(!this.bindings[path]){\n\t\t\tthis.bindings[path] = [];\n\t\t}\n\n\t\tthis.bindings[path].push(callback);\n\n\t\tcallback(this.getText(path), this.lang);\n\t}\n\n\t//iterate through bindings and trigger updates\n\t_executeBindings(){\n\t\tfor(let path in this.bindings){\n\t\t\tthis.bindings[path].forEach((binding) => {\n\t\t\t\tbinding(this.getText(path), this.lang);\n\t\t\t});\n\t\t}\n\t}\n}\n\nLocalize.moduleName = \"localize\";\n\n//load defaults\nLocalize.langs = defaultLangs;\n\nclass Comms extends Module{\n\n\tconstructor(table){\n\t\tsuper(table);\n\t}\n\n\tinitialize(){\n\t\tthis.registerTableFunction(\"tableComms\", this.receive.bind(this));\n\t}\n\n\tgetConnections(selectors){\n\t\tvar connections = [],\n\t\tconnection;\n\n\t\tconnection = TableRegistry.lookupTable(selectors);\n\n\t\tconnection.forEach((con) =>{\n\t\t\tif(this.table !== con){\n\t\t\t\tconnections.push(con);\n\t\t\t}\n\t\t});\n\n\t\treturn connections;\n\t}\n\n\tsend(selectors, module, action, data){\n\t\tvar connections = this.getConnections(selectors);\n\n\t\tconnections.forEach((connection) => {\n\t\t\tconnection.tableComms(this.table.element, module, action, data);\n\t\t});\n\n\t\tif(!connections.length && selectors){\n\t\t\tconsole.warn(\"Table Connection Error - No tables matching selector found\", selectors);\n\t\t}\n\t}\n\n\treceive(table, module, action, data){\n\t\tif(this.table.modExists(module)){\n\t\t\treturn this.table.modules[module].commsReceived(table, action, data);\n\t\t}else {\n\t\t\tconsole.warn(\"Inter-table Comms Error - no such module:\", module);\n\t\t}\n\t}\n}\n\nComms.moduleName = \"comms\";\n\nvar coreModules = /*#__PURE__*/Object.freeze({\n\t__proto__: null,\n\tLayoutModule: Layout,\n\tLocalizeModule: Localize,\n\tCommsModule: Comms\n});\n\nclass ModuleBinder {\n\t\n\tconstructor(tabulator, modules){\n\t\tthis.bindStaticFunctionality(tabulator);\n\t\tthis.bindModules(tabulator, coreModules, true);\n\t\t\n\t\tif(modules){\n\t\t\tthis.bindModules(tabulator, modules);\n\t\t}\n\t}\n\t\n\tbindStaticFunctionality(tabulator){\n\t\ttabulator.moduleBindings = {};\n\t\t\n\t\ttabulator.extendModule = function(name, property, values){\n\t\t\tif(tabulator.moduleBindings[name]){\n\t\t\t\tvar source = tabulator.moduleBindings[name][property];\n\t\t\t\t\n\t\t\t\tif(source){\n\t\t\t\t\tif(typeof values == \"object\"){\n\t\t\t\t\t\tfor(let key in values){\n\t\t\t\t\t\t\tsource[key] = values[key];\n\t\t\t\t\t\t}\n\t\t\t\t\t}else {\n\t\t\t\t\t\tconsole.warn(\"Module Error - Invalid value type, it must be an object\");\n\t\t\t\t\t}\n\t\t\t\t}else {\n\t\t\t\t\tconsole.warn(\"Module Error - property does not exist:\", property);\n\t\t\t\t}\n\t\t\t}else {\n\t\t\t\tconsole.warn(\"Module Error - module does not exist:\", name);\n\t\t\t}\n\t\t};\n\t\t\n\t\ttabulator.registerModule = function(modules){\n\t\t\tif(!Array.isArray(modules)){\n\t\t\t\tmodules = [modules];\n\t\t\t}\n\t\t\t\n\t\t\tmodules.forEach((mod) => {\n\t\t\t\ttabulator.registerModuleBinding(mod);\n\t\t\t});\n\t\t};\n\t\t\n\t\ttabulator.registerModuleBinding = function(mod){\n\t\t\ttabulator.moduleBindings[mod.moduleName] = mod;\n\t\t};\n\t\t\n\t\ttabulator.findTable = function(query){\n\t\t\tvar results = TableRegistry.lookupTable(query, true);\n\t\t\treturn Array.isArray(results) && !results.length ? false : results;\n\t\t};\n\t\t\n\t\t//ensure that module are bound to instantiated function\n\t\ttabulator.prototype.bindModules = function(){\n\t\t\tvar orderedStartMods = [],\n\t\t\torderedEndMods = [],\n\t\t\tunOrderedMods = [];\n\t\t\t\n\t\t\tthis.modules = {};\n\t\t\t\n\t\t\tfor(var name in tabulator.moduleBindings){\n\t\t\t\tlet mod = tabulator.moduleBindings[name];\n\t\t\t\tlet module = new mod(this);\n\t\t\t\t\n\t\t\t\tthis.modules[name] = module;\n\t\t\t\t\n\t\t\t\tif(mod.prototype.moduleCore){\n\t\t\t\t\tthis.modulesCore.push(module);\n\t\t\t\t}else {\n\t\t\t\t\tif(mod.moduleInitOrder){\n\t\t\t\t\t\tif(mod.moduleInitOrder < 0){\n\t\t\t\t\t\t\torderedStartMods.push(module);\n\t\t\t\t\t\t}else {\n\t\t\t\t\t\t\torderedEndMods.push(module);\n\t\t\t\t\t\t}\n\t\t\t\t\t\t\n\t\t\t\t\t}else {\n\t\t\t\t\t\tunOrderedMods.push(module);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\torderedStartMods.sort((a, b) => a.moduleInitOrder > b.moduleInitOrder ? 1 : -1);\n\t\t\torderedEndMods.sort((a, b) => a.moduleInitOrder > b.moduleInitOrder ? 1 : -1);\n\t\t\t\n\t\t\tthis.modulesRegular = orderedStartMods.concat(unOrderedMods.concat(orderedEndMods));\n\t\t};\n\t}\n\t\n\tbindModules(tabulator, modules, core){\n\t\tvar mods = Object.values(modules);\n\t\t\n\t\tif(core){\n\t\t\tmods.forEach((mod) => {\n\t\t\t\tmod.prototype.moduleCore = true;\n\t\t\t});\n\t\t}\n\t\t\n\t\ttabulator.registerModule(mods);\n\t}\n}\n\nclass Alert extends CoreFeature{\n\tconstructor(table){\n\t\tsuper(table);\n        \n\t\tthis.element = this._createAlertElement();\n\t\tthis.msgElement = this._createMsgElement();\n\t\tthis.type = null;\n        \n\t\tthis.element.appendChild(this.msgElement);\n\t}\n    \n\t_createAlertElement(){\n\t\tvar el = document.createElement(\"div\");\n\t\tel.classList.add(\"tabulator-alert\");\n\t\treturn el;\n\t}\n    \n\t_createMsgElement(){\n\t\tvar el = document.createElement(\"div\");\n\t\tel.classList.add(\"tabulator-alert-msg\");\n\t\tel.setAttribute(\"role\", \"alert\");\n\t\treturn el;\n\t}\n    \n\t_typeClass(){\n\t\treturn \"tabulator-alert-state-\" + this.type;\n\t}\n    \n\talert(content, type = \"msg\"){\n\t\tif(content){\n\t\t\tthis.clear();\n\n\t\t\tthis.dispatch(\"alert-show\", type);\n            \n\t\t\tthis.type = type;\n            \n\t\t\twhile(this.msgElement.firstChild) this.msgElement.removeChild(this.msgElement.firstChild);\n            \n\t\t\tthis.msgElement.classList.add(this._typeClass());\n            \n\t\t\tif(typeof content === \"function\"){\n\t\t\t\tcontent = content();\n\t\t\t}\n            \n\t\t\tif(content instanceof HTMLElement){\n\t\t\t\tthis.msgElement.appendChild(content);\n\t\t\t}else {\n\t\t\t\tthis.msgElement.innerHTML = content;\n\t\t\t}\n            \n\t\t\tthis.table.element.appendChild(this.element);\n\t\t}\n\t}\n    \n\tclear(){\n\t\tthis.dispatch(\"alert-hide\", this.type);\n\n\t\tif(this.element.parentNode){\n\t\t\tthis.element.parentNode.removeChild(this.element);\n\t\t}\n        \n\t\tthis.msgElement.classList.remove(this._typeClass());\n\t}\n}\n\nclass Tabulator {\n\t\n\tconstructor(element, options){\n\t\t\n\t\tthis.options = {};\n\t\t\n\t\tthis.columnManager = null; // hold Column Manager\n\t\tthis.rowManager = null; //hold Row Manager\n\t\tthis.footerManager = null; //holder Footer Manager\n\t\tthis.alertManager = null; //hold Alert Manager\n\t\tthis.vdomHoz  = null; //holder horizontal virtual dom\n\t\tthis.externalEvents = null; //handle external event messaging\n\t\tthis.eventBus = null; //handle internal event messaging\n\t\tthis.interactionMonitor = false; //track user interaction\n\t\tthis.browser = \"\"; //hold current browser type\n\t\tthis.browserSlow = false; //handle reduced functionality for slower browsers\n\t\tthis.browserMobile = false; //check if running on mobile, prevent resize cancelling edit on keyboard appearance\n\t\tthis.rtl = false; //check if the table is in RTL mode\n\t\tthis.originalElement = null; //hold original table element if it has been replaced\n\t\t\n\t\tthis.componentFunctionBinder = new ComponentFunctionBinder(this); //bind component functions\n\t\tthis.dataLoader = false; //bind component functions\n\t\t\n\t\tthis.modules = {}; //hold all modules bound to this table\n\t\tthis.modulesCore = []; //hold core modules bound to this table (for initialization purposes)\n\t\tthis.modulesRegular = []; //hold regular modules bound to this table (for initialization purposes)\n\t\t\n\t\tthis.deprecationAdvisor = new DeprecationAdvisor(this);\n\t\tthis.optionsList = new OptionsList(this, \"table constructor\");\n\t\t\n\t\tthis.initialized = false;\n\t\tthis.destroyed = false;\n\t\t\n\t\tif(this.initializeElement(element)){\n\t\t\t\n\t\t\tthis.initializeCoreSystems(options);\n\t\t\t\n\t\t\t//delay table creation to allow event bindings immediately after the constructor\n\t\t\tsetTimeout(() => {\n\t\t\t\tthis._create();\n\t\t\t});\n\t\t}\n\t\t\n\t\tTableRegistry.register(this); //register table for inter-device communication\n\t}\n\t\n\tinitializeElement(element){\n\t\tif(typeof HTMLElement !== \"undefined\" && element instanceof HTMLElement){\n\t\t\tthis.element = element;\n\t\t\treturn true;\n\t\t}else if(typeof element === \"string\"){\n\t\t\tthis.element = document.querySelector(element);\n\t\t\t\n\t\t\tif(this.element){\n\t\t\t\treturn true;\n\t\t\t}else {\n\t\t\t\tconsole.error(\"Tabulator Creation Error - no element found matching selector: \", element);\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}else {\n\t\t\tconsole.error(\"Tabulator Creation Error - Invalid element provided:\", element);\n\t\t\treturn false;\n\t\t}\n\t}\n\t\n\tinitializeCoreSystems(options){\n\t\tthis.columnManager = new ColumnManager(this);\n\t\tthis.rowManager = new RowManager(this);\n\t\tthis.footerManager = new FooterManager(this);\n\t\tthis.dataLoader = new DataLoader(this);\n\t\tthis.alertManager = new Alert(this);\n\t\t\n\t\tthis.bindModules();\n\t\t\n\t\tthis.options = this.optionsList.generate(Tabulator.defaultOptions, options);\n\t\t\n\t\tthis._clearObjectPointers();\n\t\t\n\t\tthis._mapDeprecatedFunctionality();\n\t\t\n\t\tthis.externalEvents = new ExternalEventBus(this, this.options, this.options.debugEventsExternal);\n\t\tthis.eventBus = new InternalEventBus(this.options.debugEventsInternal);\n\t\t\n\t\tthis.interactionMonitor = new InteractionManager(this);\n\t\t\n\t\tthis.dataLoader.initialize();\n\t\t// this.columnManager.initialize();\n\t\t// this.rowManager.initialize();\n\t\tthis.footerManager.initialize();\n\t}\n\t\n\t//convert deprecated functionality to new functions\n\t_mapDeprecatedFunctionality(){\n\t\t//all previously deprecated functionality removed in the 5.0 release\n\t}\n\t\n\t_clearSelection(){\n\t\t\n\t\tthis.element.classList.add(\"tabulator-block-select\");\n\t\t\n\t\tif (window.getSelection) {\n\t\t\tif (window.getSelection().empty) {  // Chrome\n\t\t\t\twindow.getSelection().empty();\n\t\t\t} else if (window.getSelection().removeAllRanges) {  // Firefox\n\t\t\t\twindow.getSelection().removeAllRanges();\n\t\t\t}\n\t\t} else if (document.selection) {  // IE?\n\t\t\tdocument.selection.empty();\n\t\t}\n\t\t\n\t\tthis.element.classList.remove(\"tabulator-block-select\");\n\t}\n\t\n\t//create table\n\t_create(){\n\t\tthis.externalEvents.dispatch(\"tableBuilding\");\n\t\tthis.eventBus.dispatch(\"table-building\");\n\t\t\n\t\tthis._rtlCheck();\n\t\t\n\t\tthis._buildElement();\n\t\t\n\t\tthis._initializeTable();\n\t\t\n\t\tthis._loadInitialData();\n\t\t\n\t\tthis.initialized = true;\n\t\t\n\t\tthis.externalEvents.dispatch(\"tableBuilt\");\n\t}\n\t\n\t_rtlCheck(){\n\t\tvar style = window.getComputedStyle(this.element);\n\t\t\n\t\tswitch(this.options.textDirection){\n\t\t\tcase\"auto\":\n\t\t\t\tif(style.direction !== \"rtl\"){\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\n\t\t\tcase \"rtl\":\n\t\t\t\tthis.element.classList.add(\"tabulator-rtl\");\n\t\t\t\tthis.rtl = true;\n\t\t\t\tbreak;\n\t\t\t\n\t\t\tcase \"ltr\":\n\t\t\t\tthis.element.classList.add(\"tabulator-ltr\");\n\t\t\t\n\t\t\tdefault:\n\t\t\t\tthis.rtl = false;\n\t\t}\n\t}\n\t\n\t//clear pointers to objects in default config object\n\t_clearObjectPointers(){\n\t\tthis.options.columns = this.options.columns.slice(0);\n\t\t\n\t\tif(Array.isArray(this.options.data) && !this.options.reactiveData){\n\t\t\tthis.options.data = this.options.data.slice(0);\n\t\t}\n\t}\n\t\n\t//build tabulator element\n\t_buildElement(){\n\t\tvar element = this.element,\n\t\toptions = this.options,\n\t\tnewElement;\n\t\t\n\t\tif(element.tagName === \"TABLE\"){\n\t\t\tthis.originalElement = this.element;\n\t\t\tnewElement = document.createElement(\"div\");\n\t\t\t\n\t\t\t//transfer attributes to new element\n\t\t\tvar attributes = element.attributes;\n\t\t\t\n\t\t\t// loop through attributes and apply them on div\n\t\t\tfor(var i in attributes){\n\t\t\t\tif(typeof attributes[i] == \"object\"){\n\t\t\t\t\tnewElement.setAttribute(attributes[i].name, attributes[i].value);\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\t// replace table with div element\n\t\t\telement.parentNode.replaceChild(newElement, element);\n\t\t\t\n\t\t\tthis.element = element = newElement;\n\t\t}\n\t\t\n\t\telement.classList.add(\"tabulator\");\n\t\telement.setAttribute(\"role\", \"grid\");\n\t\t\n\t\t//empty element\n\t\twhile(element.firstChild) element.removeChild(element.firstChild);\n\t\t\n\t\t//set table height\n\t\tif(options.height){\n\t\t\toptions.height = isNaN(options.height) ? options.height : options.height + \"px\";\n\t\t\telement.style.height = options.height;\n\t\t}\n\t\t\n\t\t//set table min height\n\t\tif(options.minHeight !== false){\n\t\t\toptions.minHeight = isNaN(options.minHeight) ? options.minHeight : options.minHeight + \"px\";\n\t\t\telement.style.minHeight = options.minHeight;\n\t\t}\n\t\t\n\t\t//set table maxHeight\n\t\tif(options.maxHeight !== false){\n\t\t\toptions.maxHeight = isNaN(options.maxHeight) ? options.maxHeight : options.maxHeight + \"px\";\n\t\t\telement.style.maxHeight = options.maxHeight;\n\t\t}\n\t}\n\t\n\t//initialize core systems and modules\n\t_initializeTable(){\n\t\tvar element = this.element,\n\t\toptions = this.options;\n\t\t\n\t\tthis.interactionMonitor.initialize();\n\t\t\n\t\tthis.columnManager.initialize();\n\t\tthis.rowManager.initialize();\n\t\t\n\t\tthis._detectBrowser();\n\t\t\n\t\t//initialize core modules\n\t\tthis.modulesCore.forEach((mod) => {\n\t\t\tmod.initialize();\n\t\t});\n\t\t\n\t\t//build table elements\n\t\telement.appendChild(this.columnManager.getElement());\n\t\telement.appendChild(this.rowManager.getElement());\n\t\t\n\t\tif(options.footerElement){\n\t\t\tthis.footerManager.activate();\n\t\t}\n\t\t\n\t\tif(options.autoColumns && options.data){\n\t\t\t\n\t\t\tthis.columnManager.generateColumnsFromRowData(this.options.data);\n\t\t}\n\t\t\n\t\t//initialize regular modules\n\t\tthis.modulesRegular.forEach((mod) => {\n\t\t\tmod.initialize();\n\t\t});\n\t\t\n\t\tthis.columnManager.setColumns(options.columns);\n\t\t\n\t\tthis.eventBus.dispatch(\"table-built\");\n\t}\n\t\n\t_loadInitialData(){\n\t\tthis.dataLoader.load(this.options.data);\n\t\tthis.columnManager.verticalAlignHeaders();\n\t}\n\t\n\t//deconstructor\n\tdestroy(){\n\t\tvar element = this.element;\n\t\t\n\t\tthis.destroyed = true;\n\t\t\n\t\tTableRegistry.deregister(this); //deregister table from inter-device communication\n\t\t\n\t\tthis.eventBus.dispatch(\"table-destroy\");\n\t\t\n\t\t//clear row data\n\t\tthis.rowManager.destroy();\n\t\t\n\t\t//clear DOM\n\t\twhile(element.firstChild) element.removeChild(element.firstChild);\n\t\telement.classList.remove(\"tabulator\");\n\n\t\tthis.externalEvents.dispatch(\"tableDestroyed\");\n\t}\n\t\n\t_detectBrowser(){\n\t\tvar ua = navigator.userAgent||navigator.vendor||window.opera;\n\t\t\n\t\tif(ua.indexOf(\"Trident\") > -1){\n\t\t\tthis.browser = \"ie\";\n\t\t\tthis.browserSlow = true;\n\t\t}else if(ua.indexOf(\"Edge\") > -1){\n\t\t\tthis.browser = \"edge\";\n\t\t\tthis.browserSlow = true;\n\t\t}else if(ua.indexOf(\"Firefox\") > -1){\n\t\t\tthis.browser = \"firefox\";\n\t\t\tthis.browserSlow = false;\n\t\t}else if(ua.indexOf(\"Mac OS\") > -1){\n\t\t\tthis.browser = \"safari\";\n\t\t\tthis.browserSlow = false;\n\t\t}else {\n\t\t\tthis.browser = \"other\";\n\t\t\tthis.browserSlow = false;\n\t\t}\n\t\t\n\t\tthis.browserMobile = /(android|bb\\d+|meego).+mobile|avantgo|bada\\/|blackberry|blazer|compal|elaine|fennec|hiptop|iemobile|ip(hone|od)|iris|kindle|lge |maemo|midp|mmp|mobile.+firefox|netfront|opera m(ob|in)i|palm( os)?|phone|p(ixi|re)\\/|plucker|pocket|psp|series(4|6)0|symbian|treo|up\\.(browser|link)|vodafone|wap|windows ce|xda|xiino|android|ipad|playbook|silk/i.test(ua)||/1207|6310|6590|3gso|4thp|50[1-6]i|770s|802s|a wa|abac|ac(er|oo|s-)|ai(ko|rn)|al(av|ca|co)|amoi|an(ex|ny|yw)|aptu|ar(ch|go)|as(te|us)|attw|au(di|-m|r |s )|avan|be(ck|ll|nq)|bi(lb|rd)|bl(ac|az)|br(e|v)w|bumb|bw-(n|u)|c55\\/|capi|ccwa|cdm-|cell|chtm|cldc|cmd-|co(mp|nd)|craw|da(it|ll|ng)|dbte|dc-s|devi|dica|dmob|do(c|p)o|ds(12|-d)|el(49|ai)|em(l2|ul)|er(ic|k0)|esl8|ez([4-7]0|os|wa|ze)|fetc|fly(-|_)|g1 u|g560|gene|gf-5|g-mo|go(\\.w|od)|gr(ad|un)|haie|hcit|hd-(m|p|t)|hei-|hi(pt|ta)|hp( i|ip)|hs-c|ht(c(-| |_|a|g|p|s|t)|tp)|hu(aw|tc)|i-(20|go|ma)|i230|iac( |-|\\/)|ibro|idea|ig01|ikom|im1k|inno|ipaq|iris|ja(t|v)a|jbro|jemu|jigs|kddi|keji|kgt( |\\/)|klon|kpt |kwc-|kyo(c|k)|le(no|xi)|lg( g|\\/(k|l|u)|50|54|-[a-w])|libw|lynx|m1-w|m3ga|m50\\/|ma(te|ui|xo)|mc(01|21|ca)|m-cr|me(rc|ri)|mi(o8|oa|ts)|mmef|mo(01|02|bi|de|do|t(-| |o|v)|zz)|mt(50|p1|v )|mwbp|mywa|n10[0-2]|n20[2-3]|n30(0|2)|n50(0|2|5)|n7(0(0|1)|10)|ne((c|m)-|on|tf|wf|wg|wt)|nok(6|i)|nzph|o2im|op(ti|wv)|oran|owg1|p800|pan(a|d|t)|pdxg|pg(13|-([1-8]|c))|phil|pire|pl(ay|uc)|pn-2|po(ck|rt|se)|prox|psio|pt-g|qa-a|qc(07|12|21|32|60|-[2-7]|i-)|qtek|r380|r600|raks|rim9|ro(ve|zo)|s55\\/|sa(ge|ma|mm|ms|ny|va)|sc(01|h-|oo|p-)|sdk\\/|se(c(-|0|1)|47|mc|nd|ri)|sgh-|shar|sie(-|m)|sk-0|sl(45|id)|sm(al|ar|b3|it|t5)|so(ft|ny)|sp(01|h-|v-|v )|sy(01|mb)|t2(18|50)|t6(00|10|18)|ta(gt|lk)|tcl-|tdg-|tel(i|m)|tim-|t-mo|to(pl|sh)|ts(70|m-|m3|m5)|tx-9|up(\\.b|g1|si)|utst|v400|v750|veri|vi(rg|te)|vk(40|5[0-3]|-v)|vm40|voda|vulc|vx(52|53|60|61|70|80|81|83|85|98)|w3c(-| )|webc|whit|wi(g |nc|nw)|wmlb|wonu|x700|yas-|your|zeto|zte-/i.test(ua.slice(0,4));\n\t}\n\t\n\tinitGuard(func, msg){\n\t\tvar stack, line;\n\t\t\n\t\tif(this.options.debugInitialization && !this.initialized){\n\t\t\tif(!func){\n\t\t\t\tstack = new Error().stack.split(\"\\n\");\n\t\t\t\t\n\t\t\t\tline = stack[0] == \"Error\" ? stack[2] : stack[1];\n\t\t\t\t\n\t\t\t\tif(line[0] == \" \"){\n\t\t\t\t\tfunc = line.trim().split(\" \")[1].split(\".\")[1];\n\t\t\t\t}else {\n\t\t\t\t\tfunc = line.trim().split(\"@\")[0];\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\tconsole.warn(\"Table Not Initialized - Calling the \" + func + \" function before the table is initialized may result in inconsistent behavior, Please wait for the `tableBuilt` event before calling this function.\" + (msg ? \" \" + msg : \"\"));\n\t\t}\n\t\t\n\t\treturn this.initialized;\n\t}\n\t\n\t////////////////// Data Handling //////////////////\n\t//block table redrawing\n\tblockRedraw(){\n\t\tthis.initGuard();\n\n\t\tthis.eventBus.dispatch(\"redraw-blocking\");\n\t\t\n\t\tthis.rowManager.blockRedraw();\n\t\tthis.columnManager.blockRedraw();\n\n\t\tthis.eventBus.dispatch(\"redraw-blocked\");\n\t}\n\t\n\t//restore table redrawing\n\trestoreRedraw(){\n\t\tthis.initGuard();\n\n\t\tthis.eventBus.dispatch(\"redraw-restoring\");\n\n\t\tthis.rowManager.restoreRedraw();\n\t\tthis.columnManager.restoreRedraw();\n\n\t\tthis.eventBus.dispatch(\"redraw-restored\");\n\t}\n\t\n\t//load data\n\tsetData(data, params, config){\n\t\tthis.initGuard(false, \"To set initial data please use the 'data' property in the table constructor.\");\n\t\t\n\t\treturn this.dataLoader.load(data, params, config, false);\n\t}\n\t\n\t//clear data\n\tclearData(){\n\t\tthis.initGuard();\n\t\t\n\t\tthis.dataLoader.blockActiveLoad();\n\t\tthis.rowManager.clearData();\n\t}\n\t\n\t//get table data array\n\tgetData(active){\n\t\treturn this.rowManager.getData(active);\n\t}\n\t\n\t//get table data array count\n\tgetDataCount(active){\n\t\treturn this.rowManager.getDataCount(active);\n\t}\n\t\n\t//replace data, keeping table in position with same sort\n\treplaceData(data, params, config){\n\t\tthis.initGuard();\n\t\t\n\t\treturn this.dataLoader.load(data, params, config, true, true);\n\t}\n\t\n\t//update table data\n\tupdateData(data){\n\t\tvar responses = 0;\n\t\t\n\t\tthis.initGuard();\n\t\t\n\t\treturn new Promise((resolve, reject) => {\n\t\t\tthis.dataLoader.blockActiveLoad();\n\t\t\t\n\t\t\tif(typeof data === \"string\"){\n\t\t\t\tdata = JSON.parse(data);\n\t\t\t}\n\t\t\t\n\t\t\tif(data && data.length > 0){\n\t\t\t\tdata.forEach((item) => {\n\t\t\t\t\tvar row = this.rowManager.findRow(item[this.options.index]);\n\t\t\t\t\t\n\t\t\t\t\tif(row){\n\t\t\t\t\t\tresponses++;\n\t\t\t\t\t\t\n\t\t\t\t\t\trow.updateData(item)\n\t\t\t\t\t\t\t.then(()=>{\n\t\t\t\t\t\t\t\tresponses--;\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\tif(!responses){\n\t\t\t\t\t\t\t\t\tresolve();\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t})\n\t\t\t\t\t\t\t.catch((e) => {\n\t\t\t\t\t\t\t\treject(\"Update Error - Unable to update row\", item, e);\n\t\t\t\t\t\t\t});\n\t\t\t\t\t}else {\n\t\t\t\t\t\treject(\"Update Error - Unable to find row\", item);\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t}else {\n\t\t\t\tconsole.warn(\"Update Error - No data provided\");\n\t\t\t\treject(\"Update Error - No data provided\");\n\t\t\t}\n\t\t});\n\t}\n\t\n\taddData(data, pos, index){\n\t\tthis.initGuard();\n\t\t\n\t\treturn new Promise((resolve, reject) => {\n\t\t\tthis.dataLoader.blockActiveLoad();\n\t\t\t\n\t\t\tif(typeof data === \"string\"){\n\t\t\t\tdata = JSON.parse(data);\n\t\t\t}\n\t\t\t\n\t\t\tif(data){\n\t\t\t\tthis.rowManager.addRows(data, pos, index)\n\t\t\t\t\t.then((rows) => {\n\t\t\t\t\t\tvar output = [];\n\t\t\t\t\t\n\t\t\t\t\t\trows.forEach(function(row){\n\t\t\t\t\t\t\toutput.push(row.getComponent());\n\t\t\t\t\t\t});\n\t\t\t\t\t\n\t\t\t\t\t\tresolve(output);\n\t\t\t\t\t});\n\t\t\t}else {\n\t\t\t\tconsole.warn(\"Update Error - No data provided\");\n\t\t\t\treject(\"Update Error - No data provided\");\n\t\t\t}\n\t\t});\n\t}\n\t\n\t//update table data\n\tupdateOrAddData(data){\n\t\tvar rows = [],\n\t\tresponses = 0;\n\t\t\n\t\tthis.initGuard();\n\t\t\n\t\treturn new Promise((resolve, reject) => {\n\t\t\tthis.dataLoader.blockActiveLoad();\n\t\t\t\n\t\t\tif(typeof data === \"string\"){\n\t\t\t\tdata = JSON.parse(data);\n\t\t\t}\n\t\t\t\n\t\t\tif(data && data.length > 0){\n\t\t\t\tdata.forEach((item) => {\n\t\t\t\t\tvar row = this.rowManager.findRow(item[this.options.index]);\n\t\t\t\t\t\n\t\t\t\t\tresponses++;\n\t\t\t\t\t\n\t\t\t\t\tif(row){\n\t\t\t\t\t\trow.updateData(item)\n\t\t\t\t\t\t\t.then(()=>{\n\t\t\t\t\t\t\t\tresponses--;\n\t\t\t\t\t\t\t\trows.push(row.getComponent());\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\tif(!responses){\n\t\t\t\t\t\t\t\t\tresolve(rows);\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t});\n\t\t\t\t\t}else {\n\t\t\t\t\t\tthis.rowManager.addRows(item)\n\t\t\t\t\t\t\t.then((newRows)=>{\n\t\t\t\t\t\t\t\tresponses--;\n\t\t\t\t\t\t\t\trows.push(newRows[0].getComponent());\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\tif(!responses){\n\t\t\t\t\t\t\t\t\tresolve(rows);\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t});\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t}else {\n\t\t\t\tconsole.warn(\"Update Error - No data provided\");\n\t\t\t\treject(\"Update Error - No data provided\");\n\t\t\t}\n\t\t});\n\t}\n\t\n\t//get row object\n\tgetRow(index){\n\t\tvar row = this.rowManager.findRow(index);\n\t\t\n\t\tif(row){\n\t\t\treturn row.getComponent();\n\t\t}else {\n\t\t\tconsole.warn(\"Find Error - No matching row found:\", index);\n\t\t\treturn false;\n\t\t}\n\t}\n\t\n\t//get row object\n\tgetRowFromPosition(position){\n\t\tvar row = this.rowManager.getRowFromPosition(position);\n\t\t\n\t\tif(row){\n\t\t\treturn row.getComponent();\n\t\t}else {\n\t\t\tconsole.warn(\"Find Error - No matching row found:\", position);\n\t\t\treturn false;\n\t\t}\n\t}\n\t\n\t//delete row from table\n\tdeleteRow(index){\n\t\tvar foundRows = [];\n\t\t\n\t\tthis.initGuard();\n\t\t\n\t\tif(!Array.isArray(index)){\n\t\t\tindex = [index];\n\t\t}\n\t\t\n\t\t//find matching rows\n\t\tfor(let item of index){\n\t\t\tlet row = this.rowManager.findRow(item, true);\n\t\t\t\n\t\t\tif(row){\n\t\t\t\tfoundRows.push(row);\n\t\t\t}else {\n\t\t\t\tconsole.error(\"Delete Error - No matching row found:\", item);\n\t\t\t\treturn Promise.reject(\"Delete Error - No matching row found\");\n\t\t\t}\n\t\t}\n\t\t\n\t\t//sort rows into correct order to ensure smooth delete from table\n\t\tfoundRows.sort((a, b) => {\n\t\t\treturn this.rowManager.rows.indexOf(a) > this.rowManager.rows.indexOf(b) ? 1 : -1;\n\t\t});\n\t\t\n\t\t//delete rows\n\t\tfoundRows.forEach((row) =>{\n\t\t\trow.delete();\n\t\t});\n\t\t\n\t\tthis.rowManager.reRenderInPosition();\n\t\t\n\t\treturn Promise.resolve();\n\t}\n\t\n\t//add row to table\n\taddRow(data, pos, index){\n\t\tthis.initGuard();\n\t\t\n\t\tif(typeof data === \"string\"){\n\t\t\tdata = JSON.parse(data);\n\t\t}\n\t\t\n\t\treturn this.rowManager.addRows(data, pos, index, true)\n\t\t\t.then((rows)=>{\n\t\t\t\treturn rows[0].getComponent();\n\t\t\t});\n\t}\n\t\n\t//update a row if it exists otherwise create it\n\tupdateOrAddRow(index, data){\n\t\tvar row = this.rowManager.findRow(index);\n\t\t\n\t\tthis.initGuard();\n\t\t\n\t\tif(typeof data === \"string\"){\n\t\t\tdata = JSON.parse(data);\n\t\t}\n\t\t\n\t\tif(row){\n\t\t\treturn row.updateData(data)\n\t\t\t\t.then(()=>{\n\t\t\t\t\treturn row.getComponent();\n\t\t\t\t});\n\t\t}else {\n\t\t\treturn this.rowManager.addRows(data)\n\t\t\t\t.then((rows)=>{\n\t\t\t\t\treturn rows[0].getComponent();\n\t\t\t\t});\n\t\t}\n\t}\n\t\n\t//update row data\n\tupdateRow(index, data){\n\t\tvar row = this.rowManager.findRow(index);\n\t\t\n\t\tthis.initGuard();\n\t\t\n\t\tif(typeof data === \"string\"){\n\t\t\tdata = JSON.parse(data);\n\t\t}\n\t\t\n\t\tif(row){\n\t\t\treturn row.updateData(data)\n\t\t\t\t.then(()=>{\n\t\t\t\t\treturn Promise.resolve(row.getComponent());\n\t\t\t\t});\n\t\t}else {\n\t\t\tconsole.warn(\"Update Error - No matching row found:\", index);\n\t\t\treturn Promise.reject(\"Update Error - No matching row found\");\n\t\t}\n\t}\n\t\n\t//scroll to row in DOM\n\tscrollToRow(index, position, ifVisible){\n\t\tvar row = this.rowManager.findRow(index);\n\t\t\n\t\tif(row){\n\t\t\treturn this.rowManager.scrollToRow(row, position, ifVisible);\n\t\t}else {\n\t\t\tconsole.warn(\"Scroll Error - No matching row found:\", index);\n\t\t\treturn Promise.reject(\"Scroll Error - No matching row found\");\n\t\t}\n\t}\n\t\n\tmoveRow(from, to, after){\n\t\tvar fromRow = this.rowManager.findRow(from);\n\t\t\n\t\tthis.initGuard();\n\t\t\n\t\tif(fromRow){\n\t\t\tfromRow.moveToRow(to, after);\n\t\t}else {\n\t\t\tconsole.warn(\"Move Error - No matching row found:\", from);\n\t\t}\n\t}\n\t\n\tgetRows(active){\n\t\treturn this.rowManager.getComponents(active);\t\n\t}\n\t\n\t//get position of row in table\n\tgetRowPosition(index){\n\t\tvar row = this.rowManager.findRow(index);\n\t\t\n\t\tif(row){\n\t\t\treturn row.getPosition();\n\t\t}else {\n\t\t\tconsole.warn(\"Position Error - No matching row found:\", index);\n\t\t\treturn false;\n\t\t}\n\t}\n\t\n\t/////////////// Column Functions  ///////////////\n\tsetColumns(definition){\n\t\tthis.initGuard(false, \"To set initial columns please use the 'columns' property in the table constructor\");\n\t\t\n\t\tthis.columnManager.setColumns(definition);\n\t}\n\t\n\tgetColumns(structured){\n\t\treturn this.columnManager.getComponents(structured);\n\t}\n\t\n\tgetColumn(field){\n\t\tvar column = this.columnManager.findColumn(field);\n\t\t\n\t\tif(column){\n\t\t\treturn column.getComponent();\n\t\t}else {\n\t\t\tconsole.warn(\"Find Error - No matching column found:\", field);\n\t\t\treturn false;\n\t\t}\n\t}\n\t\n\tgetColumnDefinitions(){\n\t\treturn this.columnManager.getDefinitionTree();\n\t}\n\t\n\tshowColumn(field){\n\t\tvar column = this.columnManager.findColumn(field);\n\t\t\n\t\tthis.initGuard();\n\t\t\n\t\tif(column){\n\t\t\tcolumn.show();\n\t\t}else {\n\t\t\tconsole.warn(\"Column Show Error - No matching column found:\", field);\n\t\t\treturn false;\n\t\t}\n\t}\n\t\n\thideColumn(field){\n\t\tvar column = this.columnManager.findColumn(field); \n\t\t\n\t\tthis.initGuard();\n\t\t\n\t\tif(column){\n\t\t\tcolumn.hide();\n\t\t}else {\n\t\t\tconsole.warn(\"Column Hide Error - No matching column found:\", field);\n\t\t\treturn false;\n\t\t}\n\t}\n\t\n\ttoggleColumn(field){\n\t\tvar column = this.columnManager.findColumn(field);\n\t\t\n\t\tthis.initGuard();\n\t\t\n\t\tif(column){\n\t\t\tif(column.visible){\n\t\t\t\tcolumn.hide();\n\t\t\t}else {\n\t\t\t\tcolumn.show();\n\t\t\t}\n\t\t}else {\n\t\t\tconsole.warn(\"Column Visibility Toggle Error - No matching column found:\", field);\n\t\t\treturn false;\n\t\t}\n\t}\n\t\n\taddColumn(definition, before, field){\n\t\tvar column = this.columnManager.findColumn(field);\n\t\t\n\t\tthis.initGuard();\n\t\t\n\t\treturn this.columnManager.addColumn(definition, before, column)\n\t\t\t.then((column) => {\n\t\t\t\treturn column.getComponent();\n\t\t\t});\n\t}\n\t\n\tdeleteColumn(field){\n\t\tvar column = this.columnManager.findColumn(field);\n\t\t\n\t\tthis.initGuard();\n\t\t\n\t\tif(column){\n\t\t\treturn column.delete();\n\t\t}else {\n\t\t\tconsole.warn(\"Column Delete Error - No matching column found:\", field);\n\t\t\treturn Promise.reject();\n\t\t}\n\t}\n\t\n\tupdateColumnDefinition(field, definition){\n\t\tvar column = this.columnManager.findColumn(field);\n\t\t\n\t\tthis.initGuard();\n\t\t\n\t\tif(column){\n\t\t\treturn column.updateDefinition(definition);\n\t\t}else {\n\t\t\tconsole.warn(\"Column Update Error - No matching column found:\", field);\n\t\t\treturn Promise.reject();\n\t\t}\n\t}\n\t\n\tmoveColumn(from, to, after){\n\t\tvar fromColumn = this.columnManager.findColumn(from),\n\t\ttoColumn = this.columnManager.findColumn(to);\n\t\t\n\t\tthis.initGuard();\n\t\t\n\t\tif(fromColumn){\n\t\t\tif(toColumn){\n\t\t\t\tthis.columnManager.moveColumn(fromColumn, toColumn, after);\n\t\t\t}else {\n\t\t\t\tconsole.warn(\"Move Error - No matching column found:\", toColumn);\n\t\t\t}\n\t\t}else {\n\t\t\tconsole.warn(\"Move Error - No matching column found:\", from);\n\t\t}\n\t}\n\t\n\t//scroll to column in DOM\n\tscrollToColumn(field, position, ifVisible){\n\t\treturn new Promise((resolve, reject) => {\n\t\t\tvar column = this.columnManager.findColumn(field);\n\t\t\t\n\t\t\tif(column){\n\t\t\t\treturn this.columnManager.scrollToColumn(column, position, ifVisible);\n\t\t\t}else {\n\t\t\t\tconsole.warn(\"Scroll Error - No matching column found:\", field);\n\t\t\t\treturn Promise.reject(\"Scroll Error - No matching column found\");\n\t\t\t}\n\t\t});\n\t}\n\t\n\t//////////// General Public Functions ////////////\n\t//redraw list without updating data\n\tredraw(force){\n\t\tthis.initGuard();\n\n\t\tthis.columnManager.redraw(force);\n\t\tthis.rowManager.redraw(force);\n\t}\n\t\n\tsetHeight(height){\n\t\tthis.options.height = isNaN(height) ? height : height + \"px\";\n\t\tthis.element.style.height = this.options.height;\n\t\tthis.rowManager.initializeRenderer();\n\t\tthis.rowManager.redraw(true);\n\t}\n\t\n\t//////////////////// Event Bus ///////////////////\n\t\n\ton(key, callback){\n\t\tthis.externalEvents.subscribe(key, callback);\n\t}\n\t\n\toff(key, callback){\n\t\tthis.externalEvents.unsubscribe(key, callback);\n\t}\n\t\n\tdispatchEvent(){\n\t\tvar args = Array.from(arguments);\n\t\targs.shift();\n\t\t\n\t\tthis.externalEvents.dispatch(...arguments);\n\t}\n\n\t//////////////////// Alerts ///////////////////\n\n\talert(contents, type){\n\t\tthis.initGuard();\n\n\t\tthis.alertManager.alert(contents, type);\n\t}\n\n\tclearAlert(){\n\t\tthis.initGuard();\n\n\t\tthis.alertManager.clear();\n\t}\n\t\n\t////////////// Extension Management //////////////\n\tmodExists(plugin, required){\n\t\tif(this.modules[plugin]){\n\t\t\treturn true;\n\t\t}else {\n\t\t\tif(required){\n\t\t\t\tconsole.error(\"Tabulator Module Not Installed: \" + plugin);\n\t\t\t}\n\t\t\treturn false;\n\t\t}\n\t}\n\t\n\tmodule(key){\n\t\tvar mod = this.modules[key];\n\t\t\n\t\tif(!mod){\n\t\t\tconsole.error(\"Tabulator module not installed: \" + key);\n\t\t}\n\t\t\n\t\treturn mod;\n\t}\n}\n\n//default setup options\nTabulator.defaultOptions = defaultOptions;\n\n//bind modules and static functionality\nnew ModuleBinder(Tabulator);\n\n//tabulator with all modules installed\n\nclass TabulatorFull extends Tabulator {}\n\n//bind modules and static functionality\nnew ModuleBinder(TabulatorFull, modules);\n\nclass PseudoRow {\n\n\tconstructor (type){\n\t\tthis.type = type;\n\t\tthis.element = this._createElement();\n\t}\n\n\t_createElement(){\n\t\tvar el = document.createElement(\"div\");\n\t\tel.classList.add(\"tabulator-row\");\n\t\treturn el;\n\t}\n\n\tgetElement(){\n\t\treturn this.element;\n\t}\n\n\tgetComponent(){\n\t\treturn false;\n\t}\n\n\tgetData(){\n\t\treturn {};\n\t}\n\n\tgetHeight(){\n\t\treturn this.element.outerHeight;\n\t}\n\n\tinitialize(){}\n\n\treinitialize(){}\n\n\tnormalizeHeight(){}\n\n\tgenerateCells(){}\n\n\treinitializeHeight(){}\n\n\tcalcHeight(){}\n\n\tsetCellHeight(){}\n\n\tclearCellHeight(){}\n\n\trendered(){}\n}\n\nexport { Accessor as AccessorModule, Ajax as AjaxModule, CalcComponent, CellComponent, Clipboard as ClipboardModule, ColumnCalcs as ColumnCalcsModule, ColumnComponent, DataTree as DataTreeModule, Download as DownloadModule, Edit$1 as EditModule, Export as ExportModule, Filter as FilterModule, Format as FormatModule, FrozenColumns as FrozenColumnsModule, FrozenRows as FrozenRowsModule, GroupComponent, GroupRows as GroupRowsModule, History as HistoryModule, HtmlTableImport as HtmlTableImportModule, Import as ImportModule, Interaction as InteractionModule, Keybindings as KeybindingsModule, Menu as MenuModule, Module, MoveColumns as MoveColumnsModule, MoveRows as MoveRowsModule, Mutator as MutatorModule, Page as PageModule, Persistence as PersistenceModule, Popup$1 as PopupModule, Print as PrintModule, PseudoRow, ReactiveData as ReactiveDataModule, Renderer, ResizeColumns as ResizeColumnsModule, ResizeRows as ResizeRowsModule, ResizeTable as ResizeTableModule, ResponsiveLayout as ResponsiveLayoutModule, RowComponent, SelectRange as SelectRangeModule, SelectRow as SelectRowModule, Sort as SortModule, Tabulator, TabulatorFull, Tooltip as TooltipModule, Validate as ValidateModule };\n//# sourceMappingURL=tabulator_esm.js.map\n","import angular from \"angular\";\r\nimport { ApiImportStatus, Dates, Numeric, EnumerationsLogic, Configs, ApiValidation, DataMapper, ApiValidationErrorType, OpenAPIV3, Occupations, Translations } from \"@salaxy/core\";\r\nimport { TabulatorFull as Tabulator } from \"tabulator-tables\";\r\nimport { JsonSchemaService } from \"../../../services\";\r\n\r\n\r\nlet XLSX = null;\r\n\r\n/**\r\n * Controller for data imports.\r\n */\r\nexport abstract class DataImportControllerBase<TSource, TTarget, TOptions> implements angular.IController {\r\n\r\n  /** Tabular source row data. */\r\n  public sourceData: Array<TSource & { validation?: ApiValidation, importStatus?: ApiImportStatus }>;\r\n\r\n  /** Target objects mapped from source data, and which should be imported */\r\n  public targetData:  Array<TTarget & { validation?: ApiValidation, result?: {status?: ApiImportStatus}}>;\r\n\r\n  /** Table control*/\r\n  public table: any;\r\n\r\n  /** Current action */\r\n  public action: \"upload\" | \"validate\" | \"import\" = \"upload\";\r\n\r\n  /** Current import count */\r\n  public importCurrent = 0;\r\n\r\n  /** Total import count */\r\n  public importTotal = 0;\r\n\r\n  /** Flag for import in progress. */\r\n  public isImporting = false;\r\n\r\n  /** Flag for cancel. */\r\n  public isCanceled = false;\r\n\r\n  /** Optional options */\r\n  public options: TOptions;\r\n\r\n  /** Template for options */\r\n  public optionsTemplate: string;\r\n\r\n  /** Data mapper */\r\n  protected mapper: DataMapper<TSource, TTarget>;\r\n\r\n  /**\r\n   * Creates a new DataImportController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    /** JsonSchemaService */\r\n    protected jsonSchemaService: JsonSchemaService,\r\n    /** Angular timeout service */\r\n    protected $timeout: angular.ITimeoutService,\r\n  ) {\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public async $onInit(){\r\n    // Support both esm and umd builds...\r\n    XLSX = await Promise.resolve(Configs.global.XLSX);\r\n    this.init();\r\n  }\r\n\r\n  /**\r\n   * Download data or template\r\n   * @param helpData Help data in the form or array of arrays\r\n   */\r\n  public async download(helpData = null) {\r\n    // Take copy\r\n    const copied = angular.copy(this.sourceData);\r\n    if (copied.length < 1) {\r\n      const emptyRow: any = { };\r\n      this.mapper.source.keys.forEach((key) => {\r\n        emptyRow[key] = null;\r\n      });\r\n      copied.push(emptyRow);\r\n    }\r\n     // remove validation\r\n     for(const row of copied) {\r\n      delete row.validation;\r\n    }\r\n    const sheet = XLSX.utils.json_to_sheet(copied);\r\n    const workbook = XLSX.utils.book_new();\r\n    XLSX.utils.book_append_sheet(workbook, sheet, \"data\");\r\n    if (helpData){\r\n      const helpSheet = XLSX.utils.aoa_to_sheet(helpData);\r\n      XLSX.utils.book_append_sheet(workbook, helpSheet, \"help\");\r\n    }\r\n    XLSX.writeFile(workbook, \"import.xlsx\");\r\n  }\r\n\r\n  /** Upload rows to table */\r\n  public async upload(files: any[]) {\r\n    if (files && files.length) {\r\n      this.reset();\r\n      const file = files[0];\r\n      const fileData = await file.arrayBuffer();\r\n      /* data is an ArrayBuffer */\r\n      const workbook = XLSX.read(fileData);\r\n      if (workbook?.SheetNames?.length > 0) {\r\n        const sheet = workbook.Sheets[workbook.SheetNames[0]];\r\n        const sheetData = XLSX.utils.sheet_to_json(sheet);\r\n        this.sourceData = [];\r\n        sheetData.forEach( (sheetRow) => {\r\n          if (this.hasData(sheetRow)) {\r\n            const row: any = { validation: {}};\r\n            this.mapper.source.keys.forEach((key) => {\r\n              this.setFieldValue(row,key,sheetRow[key]);\r\n            });\r\n            this.sourceData.push(row);\r\n          }\r\n        });\r\n      }\r\n      this.table.setData(this.sourceData);\r\n      await this.$timeout();\r\n    }\r\n  }\r\n\r\n  /** Reset data */\r\n  public reset(setData = false) {\r\n    this.importTotal = 0;\r\n    this.importCurrent = 0;\r\n    this.isImporting = false;\r\n    this.isCanceled = false;\r\n    this.sourceData = [];\r\n    this.targetData = null;\r\n    if (this.table && setData) {\r\n      this.table.setData(this.sourceData);\r\n      this.$timeout();\r\n    }\r\n  }\r\n\r\n  /** Paste data */\r\n  public async paste() {\r\n    const text = await (navigator as any).clipboard.readText();\r\n    if (text) {\r\n\t\t\tconst rowData =  this.table.modules.clipboard.pasteParser(text);\r\n\t\t\tif(rowData){\r\n\t\t\t\tthis.table.modules.clipboard.pasteAction(rowData);\r\n      }\r\n      await this.$timeout();\r\n    }\r\n  }\r\n\r\n  /** Map and validate data */\r\n  public async validate() {\r\n    this.importTotal = 0;\r\n    let isValid = true;\r\n    for(const row of this.sourceData) {\r\n      let isValidRow = true;\r\n      row.importStatus = ApiImportStatus.Ignored;\r\n      row.validation = null;\r\n      for(const field of this.mapper.source.keys) {\r\n        if (!this.validateField(field, row[field])) {\r\n          if (isValidRow) {\r\n            isValidRow = false;\r\n            isValid = false;\r\n            row.validation = {\r\n              isValid: false,\r\n              errors: [\r\n               {\r\n                 type: ApiValidationErrorType.General,\r\n                 msg: `${Translations.get(\"SALAXY.NG1.DataImport.messageInvalid\")} ${this.getFieldTitle(field)}`\r\n               }\r\n              ]\r\n            };\r\n          }\r\n        }\r\n      }\r\n      if (isValidRow) {\r\n        row.validation = {\r\n          isValid : true,\r\n          errors: [],\r\n        };\r\n      }\r\n    }\r\n    if (isValid) {\r\n      this.targetData = this.mapper.doMap(this.sourceData);\r\n    }\r\n    else\r\n    {\r\n      this.targetData = null;\r\n    }\r\n    this.table.setData(this.sourceData);\r\n    await this.$timeout();\r\n  }\r\n\r\n  /** Returns extra validator */\r\n  public getExtraValidators(): Array<{ validate: () => void, buttonLabel: string }> {\r\n    return [];\r\n  }\r\n\r\n  /** Enrichs data */\r\n  public getDataEnrichers(): Array<{ enrich: () => void, buttonLabel: string }> {\r\n    return [];\r\n  }\r\n\r\n  /** Cancel import */\r\n  public cancel() {\r\n    this.isCanceled = true;\r\n  }\r\n\r\n  /**\r\n   * Options validation. If required, override this method in the inheritied class.\r\n   */\r\n  public hasInvalidOptions() {\r\n    return false;\r\n  }\r\n\r\n  /** Import data */\r\n  public abstract import();\r\n\r\n  /** Help */\r\n  public abstract help();\r\n\r\n  /** Returns number of undefined validation rows */\r\n  public get validationUndoneRows() {\r\n    return this.sourceData.filter( (r) => !r.validation?.isValid &&  r.validation?.isValid !== false).length;\r\n  }\r\n\r\n  /** Returns number of success rows */\r\n  public get validationSuccessRows() {\r\n    return this.sourceData.filter( (r) => r.validation?.isValid === true).length;\r\n  }\r\n\r\n  /** Returns number of error rows */\r\n  public get validationErrorRows() {\r\n    return this.sourceData.filter( (r) => r.validation?.isValid === false).length;\r\n  }\r\n\r\n  /** Returns number of success rows */\r\n  public get importSuccessRows() {\r\n    return this.getImportStatusRows(ApiImportStatus.Success);\r\n  }\r\n\r\n  /** Returns number of error rows */\r\n  public get importErrorRows() {\r\n    return this.getImportStatusRows(ApiImportStatus.Error);\r\n  }\r\n\r\n  /** Returns number of warning rows */\r\n  public get importWarningRows() {\r\n    return this.getImportStatusRows(ApiImportStatus.Warning);\r\n  }\r\n\r\n  /** Returns number of success rows */\r\n  public get importIgnoredRows() {\r\n    return this.getImportStatusRows(ApiImportStatus.Ignored);\r\n  }\r\n\r\n  protected getFieldTitle(field: string): string {\r\n    return field;\r\n  }\r\n\r\n  protected getEditor(field: string): any {\r\n    // OpenAPIV3.NonArraySchemaObjectType \"string\" | \"number\" | \"boolean\" | \"object\" | \"integer\"\r\n    const fieldSchema = this.mapper.source.schema.properties[field] as OpenAPIV3.SchemaObject;\r\n\r\n\r\n    switch (fieldSchema?.type) {\r\n      case \"string\":\r\n      {\r\n        switch ( fieldSchema.format ) {\r\n          case \"date\":\r\n            return { editor: \"date\" };\r\n          case \"date-time\":\r\n            return { editor: \"datetime\" };\r\n          case \"multiline\":\r\n            return { editor: \"textarea\" };\r\n        }\r\n        if (fieldSchema.format == \"Occupation\") {\r\n          const occupations = Occupations.getAll();\r\n          return {\r\n            editor: \"list\",\r\n            editorParams: {\r\n             values: occupations.map( (e) =>  ({value: e.code, label: e.label})),\r\n             autocomplete: true,\r\n            }\r\n          };\r\n        } else if (fieldSchema.format && fieldSchema.enum?.length > 0) {\r\n          const enumMetadata = EnumerationsLogic.getEnumMetadata(fieldSchema.format);\r\n          return {\r\n            editor: \"list\",\r\n            formatter:function(cell, /*formatterParams, onRendered */){\r\n              //cell - the cell component\r\n              //formatterParams - parameters set for the column\r\n              //onRendered - function to call when the formatter has been rendered\r\n              const value = cell.getValue();\r\n              if (!value) {\r\n                return null;\r\n              }\r\n              return enumMetadata.values.find( (e) => e.name == value)?.label ?? value;\r\n            },\r\n            editorParams: {\r\n             values: enumMetadata.values.map( (e) =>  ({value: e.name, label: e.label})),\r\n            }\r\n          };\r\n        }\r\n        break;\r\n      }\r\n      case \"number\":\r\n      case \"integer\":\r\n          return { editor: \"number\" };\r\n      case \"boolean\":\r\n          return { editor: \"tickCross\" };\r\n    }\r\n    return { editor: \"input\" };\r\n  }\r\n\r\n  protected validateField(field: string, value: any): boolean {\r\n    if (!field) {\r\n      return true;\r\n    }\r\n    const fieldSchema = this.mapper.source.schema.properties[field] as OpenAPIV3.SchemaObject;\r\n    switch (fieldSchema?.type) {\r\n      case \"string\":{\r\n          if (!value) {\r\n            return true;\r\n          }\r\n          if ( typeof value !== \"string\" ) {\r\n            return false;\r\n          }\r\n          switch ( fieldSchema.format ) {\r\n            case \"date\":\r\n            case \"date-time\":\r\n            {\r\n              return Dates.isValidDateTime(value);\r\n            }\r\n          }\r\n          if (fieldSchema.format == \"Occupation\") {\r\n            const occupations = Occupations.getAll();\r\n            return occupations.some( (o) => o.code === value);\r\n          } else if (fieldSchema.format && fieldSchema.enum?.length > 0) {\r\n            const enumMetadata = EnumerationsLogic.getEnumMetadata(fieldSchema.format);\r\n            return enumMetadata.values.some( (e) => e.name === value);\r\n          }\r\n          return true;\r\n        }\r\n      case \"number\":\r\n      case \"integer\": {\r\n          if (value == null || value == undefined) {\r\n            return true;\r\n          }\r\n          return typeof value === \"number\" || typeof value === \"bigint\";\r\n        }\r\n      case \"boolean\": {\r\n          if (value == null || value == undefined) {\r\n            return true;\r\n          }\r\n          return typeof value === \"boolean\";\r\n        }\r\n      default: {\r\n          if (value == null || value == undefined) {\r\n            return true;\r\n          }\r\n          return typeof value === \"string\";\r\n        }\r\n      }\r\n  }\r\n\r\n  /** Default help data for columns. */\r\n  protected getDefaultHelpDataForColumns() {\r\n    return [\r\n      [Translations.get(\"SALAXY.NG1.DataImport.help.fields.title\")],\r\n      [Translations.get(\"SALAXY.NG1.DataImport.help.fields.id\"), Translations.get(\"SALAXY.NG1.DataImport.help.fields.type\"), Translations.get(\"SALAXY.NG1.DataImport.help.fields.name\"), Translations.get(\"SALAXY.NG1.DataImport.help.fields.description\")],\r\n      ...(this.mapper.source.keys.map((f) =>\r\n      [\r\n        f,\r\n        (this.mapper.source.schema.properties[f] as any)?.format ||  (this.mapper.source.schema.properties[f] as any)?.type || \"string\",\r\n        Translations.getWithDefault((this.mapper.source.schema.properties[f] ?? {})[\"x-salaxy-title\"],\"\"),\r\n        Translations.getWithDefault((this.mapper.source.schema.properties[f] ?? {})[\"x-salaxy-description\"],\"\")\r\n      ])),\r\n      [\"\"],\r\n      [Translations.get(\"SALAXY.NG1.DataImport.help.values.title\")],\r\n      [Translations.get(\"SALAXY.NG1.DataImport.help.values.type\"),Translations.get(\"SALAXY.NG1.DataImport.help.values.value\"), Translations.get(\"SALAXY.NG1.DataImport.help.values.description\")],\r\n      ...(this.mapper.source.keys.filter((f) => this.getEditor(f)?.editor === \"list\").flatMap((f) =>\r\n        this.getEditor(f)?.editorParams.values.map( (v) => [(this.mapper.source.schema.properties[f] as any).format, v.value, v.label] as any)\r\n      ))\r\n    ];\r\n  }\r\n\r\n  private setFieldValue(row: any, field: string, value: any) {\r\n    const fieldSchema = this.mapper?.source.schema.properties ? this.mapper.source.schema.properties[field] as OpenAPIV3.SchemaObject : undefined;\r\n    switch (fieldSchema?.type) {\r\n      case \"string\": {\r\n        if ( value != null && value != undefined) {\r\n          if (fieldSchema.format == \"date\" || fieldSchema.format == \"date-time\") {\r\n            if (typeof value === \"number\") {\r\n              const y1900 = Dates.getDate(1900,1,1);\r\n              value = Dates.add(y1900, value - 2, \"day\");\r\n            }\r\n          }\r\n          else if (fieldSchema.format && (fieldSchema.enum?.length ?? -1) > 0) {\r\n            const enumMetadata = EnumerationsLogic.getEnumMetadata(fieldSchema.format);\r\n            const lowerValue = value.toLowerCase();\r\n            const candidate = enumMetadata.values.find( (e) => e.name.toLowerCase() === lowerValue);\r\n            if (candidate) {\r\n              value = candidate.name;\r\n            }\r\n          }\r\n          else {\r\n            if (typeof value === \"number\" || typeof value === \"bigint\" || typeof value === \"boolean\" ) {\r\n              value = `${value}`;\r\n            }\r\n          }\r\n        }\r\n        break;\r\n      }\r\n      case \"number\": {\r\n        if ( value != null && value != undefined && typeof value === \"string\") {\r\n          value = Numeric.parseNumber(value);\r\n        }\r\n        break;\r\n      }\r\n      case \"integer\": {\r\n        if ( value != null && value != undefined && typeof value === \"string\") {\r\n          value = Numeric.round(Numeric.parseNumber(value),0);\r\n        }\r\n        break;\r\n      }\r\n      case \"boolean\": {\r\n        if ( value != null && value != undefined && typeof value === \"string\") {\r\n          value = ( value.toLowerCase() == \"TRUE\" );\r\n        }\r\n        break;\r\n      }\r\n      default:\r\n        break;\r\n    }\r\n    row[field] = value;\r\n  }\r\n\r\n  /** Returns the import mapper */\r\n  protected abstract getImportMapper(): Promise<DataMapper<TSource, TTarget>>;\r\n\r\n\r\n  private getImportStatusRows(status: ApiImportStatus) {\r\n    return this.sourceData.filter( (r) => r.importStatus == status).length;\r\n  }\r\n\r\n  private async init() {\r\n\r\n    this.mapper = await this.getImportMapper();\r\n    this.reset();\r\n    this.table = new Tabulator(\"#import-table\", {\r\n      height: \"calc(100vh - 500px)\", // set height of table (in CSS or here), this enables the Virtual DOM and improves render speed dramatically (can be any valid css height value)\r\n      data: this.sourceData, //assign data to table\r\n      layout: \"fitColumns\", //fit columns to width of table (optional)\r\n      clipboard: true,\r\n      clipboardPasteAction: ((sheetData: any) => {\r\n        this.reset();\r\n        sheetData.forEach( (sheetRow) => {\r\n          if (this.hasData(sheetRow)) {\r\n            const row = { validation: {}} as any;\r\n            this.mapper.source.keys.forEach((key) => {\r\n              this.setFieldValue(row,key,sheetRow[key]);\r\n            });\r\n            this.sourceData.push(row);\r\n          }\r\n        });\r\n        this.table.setData(this.sourceData);\r\n        return this.sourceData;\r\n      }) as any,\r\n      columns: [\r\n        {\r\n          title: Translations.get(\"SALAXY.NG1.DataImport.columnImportStatus\"),\r\n          field: \"importStatus\",\r\n          formatter:function(cell, /*formatterParams, onRendered */){\r\n            //cell - the cell component\r\n            //formatterParams - parameters set for the column\r\n            //onRendered - function to call when the formatter has been rendered\r\n\r\n            const status = cell.getValue() ?? ApiImportStatus.Ignored;\r\n            switch (status) {\r\n              case ApiImportStatus.Ignored:\r\n                return `<span class=\"text-default\">${Translations.get(\"SALAXY.NG1.DataImport.ignoredLabel\")}</span>`;\r\n              case ApiImportStatus.Success:\r\n                return `<span class=\"text-success\" >${Translations.get(\"SALAXY.NG1.DataImport.successLabel\")}</span>`;\r\n              case ApiImportStatus.Error:\r\n                return `<span class=\"text-danger\" >${Translations.get(\"SALAXY.NG1.DataImport.errorLabel\")}</span>`;\r\n              case ApiImportStatus.Warning:\r\n                return `<span class=\"text-warning\" >${Translations.get(\"SALAXY.NG1.DataImport.warningLabel\")}</span>`;\r\n            }\r\n            return null;\r\n          },\r\n          headerSort:false,\r\n        },\r\n        {\r\n          title: Translations.get(\"SALAXY.NG1.DataImport.columnValidation\"),\r\n          field: \"validation\",\r\n          formatter:function(cell, /*formatterParams, onRendered */){\r\n            //cell - the cell component\r\n            //formatterParams - parameters set for the column\r\n            //onRendered - function to call when the formatter has been rendered\r\n\r\n            const validation: ApiValidation = cell.getValue();\r\n            if (!validation) {\r\n              return null;\r\n            }\r\n\r\n            // null or undefined\r\n            if (!validation.isValid && validation.isValid !== false ) {\r\n              if (validation.errors?.length > 0) {\r\n                return `<span class=\"text-warning\">${(validation.errors ?? []).map( (e) => e.msg).join(\"<br>\")}</span>`;\r\n              }\r\n              return null;\r\n            }\r\n\r\n            if (validation.isValid !== false) {\r\n              if (validation.errors?.length > 0) {\r\n                return `<span class=\"text-success\">${(validation.errors ?? []).map( (e) => e.msg).join(\"<br>\")}</span>`;\r\n              }\r\n              return `<span class=\"text-success\">Ok</span>`;\r\n            }\r\n            else {\r\n              return `<span class=\"text-danger\" >${(validation.errors ?? []).map( (e) => e.msg).join(\"<br>\")}</span>`;\r\n            }\r\n          },\r\n          headerSort:false,\r\n        },\r\n        ... this.mapper.source.keys.map((x) => ({\r\n          title: this.getFieldTitle(x),\r\n          field: x,\r\n          ... this.getEditor(x),\r\n          headerSort:false,\r\n          headerVertical:\"flip\",\r\n        }))\r\n      ]\r\n    });\r\n\r\n    //trigger an alert message when the row is clicked\r\n    this.table.on(\"cellEdited\", async () => {\r\n      await this.$timeout();\r\n    });\r\n\r\n    await this.$timeout();\r\n  }\r\n\r\n  private hasData(sheetRow: any): boolean {\r\n    if (!sheetRow) {\r\n      return false;\r\n    }\r\n    let dataOk = false;\r\n    for(const key of Object.keys(sheetRow)) {\r\n      dataOk = dataOk || (sheetRow[key] != null && sheetRow[key] != undefined &&\r\n          !(typeof sheetRow[key] === \"string\" && sheetRow[key].trim().length == 0));\r\n      if (dataOk) {\r\n        return dataOk;\r\n      }\r\n    }\r\n    return dataOk;\r\n  }\r\n}","import angular from \"angular\";\r\nimport { ApiImportStatus, Imports, DataMapper, CompanyImportRow,CompanyImport, ApiValidationErrorType, Translations, EInvoiceAddress } from \"@salaxy/core\";\r\n\r\nimport { DataImportControllerBase } from \"./DataImportControllerBase\";\r\n\r\nimport { EditDialogKnownActions, JsonSchemaService, UiHelpers } from \"../../../services\";\r\n\r\n\r\n/**\r\n * Controller for company imports.\r\n */\r\nexport class CompanyImportController extends DataImportControllerBase<CompanyImportRow, CompanyImport, never> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Imports\", \"JsonSchemaService\", \"$timeout\", \"UiHelpers\"];\r\n\r\n  private dataEnricher = {\r\n    enrich: () => this.enrichEInvoiceAddresses(),\r\n    buttonLabel: Translations.get(\"SALAXY.NG1.CompanyImport.enrichEInvoiceAddressesButton\")\r\n  };\r\n\r\n  /**\r\n   * Creates a new WorkerImportController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    private importsApi: Imports,\r\n    jsonSchemaService: JsonSchemaService,\r\n    $timeout: angular.ITimeoutService,\r\n    private uiHelpers: UiHelpers,\r\n  ) {\r\n    super(jsonSchemaService, $timeout);\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public async $onInit(){\r\n    super.$onInit();\r\n  }\r\n\r\n\r\n  /** Enrichs data */\r\n  public getDataEnrichers(): Array<{ enrich: () => void, buttonLabel: string }> {\r\n    return [this.dataEnricher];\r\n  }\r\n\r\n\r\n  /** Import data */\r\n  public async import() {\r\n\r\n    if (this.isImporting) {\r\n      return;\r\n    }\r\n\r\n    await this.validate();\r\n    if (!this.targetData) {\r\n      return;\r\n    }\r\n\r\n    this.isImporting = true;\r\n    this.isCanceled = false;\r\n\r\n    for(const sourceRow of this.sourceData) {\r\n      sourceRow.validation = null;\r\n      sourceRow.importStatus = ApiImportStatus.Ignored;\r\n    }\r\n    this.table.setData(this.sourceData);\r\n    await this.$timeout();\r\n\r\n    const getTargetKey = (x: CompanyImport) => `${x.item.officialId}`.toLowerCase();\r\n    const getSourceKey = (x: CompanyImportRow) => `${x.officialId}`.toLowerCase();\r\n\r\n    this.importTotal = this.targetData.length;\r\n    this.importCurrent = 0;\r\n\r\n    const chunkSize = 10;\r\n    const chunks: CompanyImport[][] = [];\r\n    for (let i = 0; i < this.targetData.length; i += chunkSize) {\r\n        chunks.push(this.targetData.slice(i, i + chunkSize));\r\n    }\r\n\r\n    let index = 0;\r\n    for(const chunk of chunks) {\r\n      try {\r\n        if (this.isCanceled) {\r\n          break;\r\n        }\r\n        chunk.splice(0, chunk.length, ... await this.importsApi.importCompanies(chunk));\r\n      } catch (error) {\r\n        for( const importObj of chunk) {\r\n          importObj.result = importObj.result ?? {};\r\n          importObj.result.status = ApiImportStatus.Error,\r\n          importObj.validation = {\r\n            isValid: false,\r\n            errors: [{\r\n              key: null,\r\n              type: ApiValidationErrorType.General,\r\n              code: \"Server error\",\r\n              msg: error?.data?.messageHtml || JSON.stringify(error?.data, Object.getOwnPropertyNames(error?.data)),\r\n            }],\r\n          };\r\n        }\r\n      }\r\n      for(const result of chunk) {\r\n        const sourceRows = this.sourceData.filter((x) => getSourceKey(x) == getTargetKey(result));\r\n        for(const sourceRow of sourceRows) {\r\n          sourceRow.validation = {\r\n            isValid: result.validation?.isValid,\r\n            errors: result.validation?.errors\r\n          };\r\n          sourceRow.importStatus = result.result?.status;\r\n        }\r\n        index += sourceRows.length;\r\n        this.importCurrent = index;\r\n\r\n        this.table.setData(this.sourceData);\r\n        await this.$timeout();\r\n      }\r\n    }\r\n    this.isImporting = false;\r\n    await this.$timeout();\r\n  }\r\n\r\n  /** Help */\r\n  public async help() {\r\n    const helpData = [\r\n      [Translations.get(\"SALAXY.NG1.CompanyImport.help.title\")],\r\n      [\"\"],\r\n      [Translations.get(\"SALAXY.NG1.CompanyImport.help.overview.title\")],\r\n      [Translations.get(\"SALAXY.NG1.CompanyImport.help.overview.row1\")],\r\n      [Translations.get(\"SALAXY.NG1.CompanyImport.help.overview.row2\")],\r\n      [\"\"],\r\n       ...this.getDefaultHelpDataForColumns(),\r\n    ];\r\n    await this.download(helpData);\r\n  }\r\n\r\n  protected async getImportMapper() {\r\n    const mapper = new DataMapper<CompanyImportRow, CompanyImport>(\"NG1/CompanyImportController\", \"Asiakkaat\");\r\n    const map = {\r\n      officialId: \"item.officialId\",\r\n      partnerAccountId: \"item.partnerAccountId\",\r\n      email: \"item.email\",\r\n      telephone: \"item.telephone\",\r\n      contactFirstName: \"item.contactFirstName\",\r\n      contactLastname: \"item.contactLastName\",\r\n      proxyPartner: \"item.proxyPartner\",\r\n      language: \"item.language\",\r\n      eInvoiceReceiver: \"parameters.settings.payments.invoice.eInvoiceReceiver\",\r\n      eInvoiceIntermediator: \"parameters.settings.payments.invoice.eInvoiceIntermediator\",\r\n    };\r\n    await mapper.setSchemaFromCache(this.jsonSchemaService.getCache(), \"salaxy-secure/schemas/v02.json\", \"CompanyImport\", \"target\");\r\n    mapper.setPaths(map);\r\n    mapper.generateSchema(\"CompanyImportRow\", \"source\");\r\n    return mapper;\r\n  }\r\n\r\n  private async enrichEInvoiceAddresses() {\r\n    if (!this.sourceData || this.sourceData.length == 0) {\r\n      return;\r\n    }\r\n    const dialog = this.uiHelpers.showLoading(\"SALAXY.NG1.CompanyImport.enrichEInvoiceAddressesMessage\", \"\");\r\n    for (const row of this.sourceData) {\r\n      if (row.eInvoiceReceiver && row.eInvoiceIntermediator) {\r\n        continue;\r\n      }\r\n      dialog.setText(row.officialId);\r\n      const addresses = await this.importsApi.queryEInvoiceAddress(row.officialId);\r\n      if (addresses.length == 0) {\r\n        continue;\r\n      }\r\n      if (addresses.length ==  1) {\r\n        row.eInvoiceReceiver = addresses[0].receiver;\r\n        row.eInvoiceIntermediator = addresses[0].intermediator;\r\n        await this.validate();\r\n        continue;\r\n      }\r\n      const currentSelection: EInvoiceAddress = null;\r\n      const selectionDialog = await this.uiHelpers.openEditDialog(\"salaxy-components/helpers/import/EInvoiceAddressSelect.html\", { selection: currentSelection }, { addresses, select: (current, row, close) => { current.selection = row; close(EditDialogKnownActions.Ok); } });\r\n      if (selectionDialog.result == EditDialogKnownActions.Ok && selectionDialog.item.selection?.receiver && selectionDialog.item.selection?.intermediator) {\r\n          row.eInvoiceReceiver = selectionDialog.item.selection?.receiver;\r\n          row.eInvoiceIntermediator = selectionDialog.item.selection?.intermediator;\r\n          await this.validate();\r\n          continue;\r\n      }\r\n    }\r\n    dialog.dismiss();\r\n  }\r\n}","import angular from \"angular\";\r\nimport { ApiCheckStatus, ApiValidationErrorType, ApiImportStatus, Dates, Arrays, UserDefinedRow, Imports, DataMapper, DataMapperSelector, CalculationImportRow, CalculationImport, WorkerCheck, Translations, PayrollCalculationsSaveOptions, RowMergeOption } from \"@salaxy/core\";\r\n\r\nimport { DataImportControllerBase } from \"./DataImportControllerBase\";\r\n\r\nimport { JsonSchemaService } from \"../../../services\";\r\n\r\n/**\r\n * Controller for calculation imports.\r\n */\r\nexport class CalcImportController extends DataImportControllerBase<CalculationImportRow, CalculationImport, PayrollCalculationsSaveOptions> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Imports\", \"JsonSchemaService\", \"$timeout\"];\r\n\r\n  /** Boolean indicating if the worker validation is in progress. */\r\n\r\n  public isValidating = false;\r\n\r\n  /** Options form */\r\n  public optionsForm: angular.IFormController;\r\n\r\n  /** Custom options */\r\n  public customOptions: \"addRows\" | \"removeImportedRows\" | \"removeAllRows\" = \"removeAllRows\";\r\n\r\n  // check SalaryDate, should not be changed in server\r\n  private getTargetKey = (x: CalculationImport) => `${x.officialId}_${x.item.worker.paymentData.socialSecurityNumber}_${Dates.asDate(x.item.workflow.salaryDate)}_${x.parameters.payroll.input.title}`.toLowerCase();\r\n  private getSourceKey = (x: CalculationImportRow) => `${x.companyOfficialId}_${x.personalId}_${Dates.asDate(x.salaryDate)}_${x.payrollTitle}`.toLowerCase();\r\n  private getCheckTargetKey = (x: WorkerCheck) => `${x.officialId}_${x.id}`.toLowerCase();\r\n  private getCheckSourceKey = (x: CalculationImportRow) => `${x.companyOfficialId}_${x.employmentId || x.personalId}`.toLowerCase();\r\n\r\n  private extraValidator = {\r\n    validate: () => this.validateWorkers(),\r\n    buttonLabel: Translations.get(\"SALAXY.NG1.CalcImport.validateWorkersButton\")\r\n  };\r\n\r\n  /**\r\n   * Creates a new WorkerImportController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    private importsApi: Imports,\r\n    jsonSchemaService: JsonSchemaService,\r\n    $timeout: angular.ITimeoutService\r\n  ) {\r\n    super(jsonSchemaService, $timeout);\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public async $onInit() {\r\n    super.$onInit();\r\n    this.optionsTemplate = \"salaxy-components/helpers/import/CalcImportOptions.html\";\r\n    this.options = {\r\n      isMerge: true,\r\n      rowMergeOption: RowMergeOption.RemoveAllRows,\r\n      applyEmploymentDefaultRows: false,\r\n      sourceId: null,\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Updates options from the ui.\r\n   */\r\n  public updateOptions() {\r\n    switch(this.customOptions) {\r\n      case \"addRows\":\r\n        this.options.rowMergeOption = undefined;\r\n        break;\r\n      case \"removeImportedRows\":\r\n        this.options.rowMergeOption = RowMergeOption.RemoveImportedRows;\r\n        break;\r\n      case \"removeAllRows\":\r\n        this.options.rowMergeOption = RowMergeOption.RemoveAllRows;\r\n        break;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Options validation. If required, override this method in the inheritied class.\r\n   */\r\n  public hasInvalidOptions() {\r\n    return this.optionsForm && this.optionsForm.$invalid;\r\n  }\r\n\r\n  /** Import data */\r\n  public async import() {\r\n\r\n    if (this.isImporting) {\r\n      return;\r\n    }\r\n\r\n    await this.validate();\r\n    if (!this.targetData) {\r\n      return;\r\n    }\r\n\r\n    this.isImporting = true;\r\n    this.isCanceled = false;\r\n\r\n    for(const sourceRow of this.sourceData) {\r\n      sourceRow.validation = null;\r\n      sourceRow.importStatus = ApiImportStatus.Ignored;\r\n    }\r\n    this.table.setData(this.sourceData);\r\n    await this.$timeout();\r\n\r\n    this.importTotal = this.targetData.length;\r\n    this.importCurrent = 0;\r\n\r\n    // compose calculations\r\n    // group by officialId, personalId and salaryDate\r\n    const groups = Arrays.groupBy(this.targetData, this.getTargetKey);\r\n    const imports = [];\r\n    for(const key in groups) {\r\n      const groupCalcs = groups[key];\r\n      const firstCalc = groupCalcs.splice(0,1)[0];\r\n      for(const calc of groupCalcs) {\r\n        firstCalc.item.rows.push(... calc.item.rows);\r\n      }\r\n      imports.push(firstCalc);\r\n    }\r\n\r\n    const chunkSize = 10;\r\n    const chunks: CalculationImport[][] = [];\r\n    for (let i = 0; i < imports.length; i += chunkSize) {\r\n        chunks.push(imports.slice(i, i + chunkSize));\r\n    }\r\n\r\n    let index = 0;\r\n    for(const chunk of chunks) {\r\n      try {\r\n        if (this.isCanceled) {\r\n          break;\r\n        }\r\n        chunk.splice(0, chunk.length, ... await this.importsApi.importCalculations(chunk, this.options ));\r\n      } catch (error) {\r\n        for( const importObj of chunk) {\r\n          importObj.result = importObj.result ?? {};\r\n          importObj.result.status = ApiImportStatus.Error,\r\n          importObj.validation = {\r\n            isValid: false,\r\n            errors: [{\r\n              key: null,\r\n              type: ApiValidationErrorType.General,\r\n              code: \"Server error\",\r\n              msg: error?.data?.messageHtml || JSON.stringify(error?.data, Object.getOwnPropertyNames(error?.data)),\r\n            }],\r\n          };\r\n        }\r\n      }\r\n      for(const result of chunk) {\r\n        const sourceRows = this.sourceData.filter((x) => this.getSourceKey(x) == this.getTargetKey(result));\r\n        for(const sourceRow of sourceRows) {\r\n          sourceRow.validation = {\r\n            isValid: result.validation?.isValid,\r\n            errors: result.validation?.errors\r\n          };\r\n          sourceRow.importStatus = result.result?.status;\r\n        }\r\n        index += sourceRows.length;\r\n        this.importCurrent = index;\r\n\r\n        this.table.setData(this.sourceData);\r\n        await this.$timeout();\r\n      }\r\n    }\r\n\r\n    this.isImporting = false;\r\n    await this.$timeout();\r\n  }\r\n\r\n  /** Help */\r\n  public async help() {\r\n    const helpData = [\r\n        [Translations.get(\"SALAXY.NG1.CalcImport.help.title\")],\r\n        [\"\"],\r\n        [Translations.get(\"SALAXY.NG1.CalcImport.help.overview.title\")],\r\n        [Translations.get(\"SALAXY.NG1.CalcImport.help.overview.row1\")],\r\n        [Translations.get(\"SALAXY.NG1.CalcImport.help.overview.row2\")],\r\n        [\"\"],\r\n        ...this.getDefaultHelpDataForColumns(),\r\n      ];\r\n\r\n    await this.download(helpData);\r\n  }\r\n\r\n  /** Returns extra validator */\r\n  public getExtraValidators(): Array<{ validate: () => void, buttonLabel: string }> {\r\n    return [this.extraValidator];\r\n  }\r\n\r\n  protected async getImportMapper() {\r\n\r\n    const rowMap = {\r\n      rowType: \"rowType\",\r\n      message: \"message\",\r\n      kind: \"data.kind\",\r\n      count: \"count\",\r\n      price: \"price\",\r\n      unit: \"unit\",\r\n      // rowSourceId: \"sourceId\",\r\n      vatPercent: \"accounting.vatPercent\",\r\n    };\r\n\r\n    const rowMapper = new DataMapper<CalculationImportRow, UserDefinedRow>(\"NG1/CalcImporController\", \"Palkkalaskelmat\");\r\n    await rowMapper.setSchemaFromCache(this.jsonSchemaService.getCache(), \"salaxy-secure/schemas/v02.json\", \"UserDefinedRow\", \"target\");\r\n    rowMapper.setPaths(rowMap);\r\n    rowMapper.generateSchema(\"CalculationImportRow\", \"source\");\r\n\r\n    const rowSelector = new DataMapperSelector<CalculationImportRow, CalculationImport>(null, \"item.rows\",\r\n      (source) => {\r\n        if (source.rowType && source.price > 0) {\r\n          return rowMapper.doMap([source]);\r\n        }\r\n        return [];\r\n      });\r\n\r\n    const mapper = new DataMapper<CalculationImportRow, CalculationImport>(\"NG1/CalcImportController\", \"Palkkalaskelmat\");\r\n    const map = {\r\n      companyOfficialId: \"officialId\",\r\n      personalId: \"item.worker.paymentData.socialSecurityNumber\",\r\n      employmentId: \"item.worker.employmentId\",\r\n      occupationCode: \"item.info.occupationCode\",\r\n      periodStart: \"item.info.workStartDate\",\r\n      periodEnd: \"item.info.workEndDate\",\r\n      workDescription: \"item.info.workDescription\",\r\n      salarySlipMessage: \"item.info.salarySlipMessage\",\r\n      salaryDate: \"item.workflow.salaryDate\",\r\n      paymentChannel: \"item.info.paymentChannel\",\r\n      payrollTitle: \"parameters.payroll.input.title\",\r\n      // payrollSourceId: \"parameters.payroll.input.sourceId\",\r\n      // sourceId: \"item.info.sourceId\",\r\n      fixedTaxAmount: \"item.worker.tax.fixedTaxAmount\",\r\n      rowType: rowSelector,\r\n    };\r\n    await mapper.setSchemaFromCache(this.jsonSchemaService.getCache(), \"salaxy-secure/schemas/v02.json\", \"CalculationImport\", \"target\");\r\n    mapper.setPaths(map);\r\n    mapper.generateSchema(\"CalculationImportRow\", \"source\");\r\n\r\n    mapper.source.schema.properties.occupationCode[\"format\"] =\"Occupation\";\r\n    for(const property in rowMapper.source.schema.properties) {\r\n      mapper.source.schema.properties[property] = rowMapper.source.schema.properties[property];\r\n    }\r\n\r\n    return mapper;\r\n  }\r\n\r\n  /** Import data */\r\n  private async validateWorkers() {\r\n\r\n    if (this.isValidating) {\r\n      return;\r\n    }\r\n\r\n    await this.validate();\r\n    if (!this.targetData) {\r\n      return;\r\n    }\r\n\r\n    this.isValidating = true;\r\n\r\n    for(const sourceRow of this.sourceData) {\r\n      sourceRow.validation = null;\r\n      sourceRow.validation = {\r\n        isValid: null, // null on purpose\r\n        errors: [{\r\n          type: ApiValidationErrorType.General,\r\n          msg: Translations.get(\"SALAXY.UI_Terms.wait\"),\r\n        }],\r\n      };\r\n      sourceRow.importStatus = ApiImportStatus.Ignored;\r\n    }\r\n    this.table.setData(this.sourceData);\r\n    await this.$timeout();\r\n\r\n    const workerGroups = Arrays.groupBy(this.sourceData, this.getCheckSourceKey);\r\n    const workerChecks: WorkerCheck[] = [];\r\n    for(const workerGroupKey in workerGroups) {\r\n      workerChecks.push( {\r\n        officialId: workerGroups[workerGroupKey][0].companyOfficialId,\r\n        id: workerGroups[workerGroupKey][0].employmentId || workerGroups[workerGroupKey][0].personalId,\r\n      });\r\n    }\r\n\r\n    const chunkSize = 10;\r\n    const chunks: WorkerCheck[][] = [];\r\n    for (let i = 0; i < workerChecks.length; i += chunkSize) {\r\n        chunks.push(workerChecks.slice(i, i + chunkSize));\r\n    }\r\n\r\n    for(const chunk of chunks) {\r\n      try {\r\n        chunk.splice(0, chunk.length, ... await this.importsApi.checkWorkers(chunk));\r\n      } catch (error) {\r\n        for( const checkObj of chunk) {\r\n          checkObj.result = checkObj.result ?? {};\r\n          checkObj.result.status = ApiCheckStatus.Error,\r\n          checkObj.validation = {\r\n            isValid: false,\r\n            errors: [{\r\n              key: null,\r\n              type: ApiValidationErrorType.General,\r\n              code: \"Server error\",\r\n              msg: error?.data?.messageHtml || JSON.stringify(error?.data, Object.getOwnPropertyNames(error?.data)),\r\n            }],\r\n          };\r\n        }\r\n      }\r\n      for(const result of chunk) {\r\n        const sourceRows = this.sourceData.filter((x) => this.getCheckSourceKey(x) == this.getCheckTargetKey(result));\r\n        for(const sourceRow of sourceRows) {\r\n          sourceRow.validation = {\r\n            isValid: result.validation.isValid && result.result.item.length == 1 ,\r\n            errors: result.validation.isValid ? (\r\n                    (result.result.item == null || result.result.item.length == 0) ? [ {msg: Translations.get(\"SALAXY.NG1.CalcImport.messageMissingEmployment\"), type: ApiValidationErrorType.General,}] :\r\n                    (result.result.item.length == 1) ? [ {msg: Translations.get(\"SALAXY.NG1.CalcImport.messageExistingEmployment\"), type: ApiValidationErrorType.General,}] :\r\n                    (result.result.item.length > 1) ? [ {msg: Translations.get(\"SALAXY.NG1.CalcImport.messageSeveralEmployments\"), type: ApiValidationErrorType.General,}] : result.validation.errors) :\r\n                    result.validation.errors\r\n          };\r\n        }\r\n\r\n        this.table.setData(this.sourceData);\r\n        await this.$timeout();\r\n      }\r\n    }\r\n    this.isValidating = false;\r\n    await this.$timeout();\r\n  }\r\n\r\n}","import angular from \"angular\";\r\n\r\nimport { Ajax, Translations, WorktimeApiConnector } from \"@salaxy/core\";\r\nimport type { calcReportType, CalculationListItem, PayrollDetails, WorktimeImport, WorktimeImportInStagingListItem, WorktimeImportPreviewMetadata, WorktimeImportRow } from \"@salaxy/core\";\r\nimport { ReportsService, SessionService, UiHelpers, UserSettingsService } from \"../../../services\";\r\n\r\n/** Controller that connects to the Import Staging area */\r\nexport class ImportStagingController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"AjaxNg1\", \"$timeout\", \"UserSettingsService\", \"$sce\", \"SessionService\", \"UiHelpers\", \"ReportsService\"];\r\n\r\n  /**\r\n   * If provided by the parent (payroll controller), contains the list off calculations commit into the Payroll\r\n   * TODO: Consider including this to WorktimeImport wihtin the commit stage (also some other meta data)?\r\n   */\r\n  public payrollCalcs: CalculationListItem[] = [];\r\n\r\n  /** API methods for the Worktime Service. */\r\n  public worktimeApi: WorktimeApiConnector;\r\n\r\n  /** Itsems to show in the salary slips list. */\r\n  public salarySlipListType: \"preview\" | \"committed\" | \"all\" | \"distinct\" = \"all\";\r\n\r\n  /** The payroll that is potentially set by the parent Payroll component. This is only used in the init, changing it later will not take any effect. */\r\n  public payroll: PayrollDetails | undefined = undefined;\r\n\r\n  public debugJson: string = \"\";\r\n\r\n  private _payrollId: string | undefined = undefined;\r\n\r\n  private salarySlipCache = {\r\n    /** Employment ID for which the data has been fetched. */\r\n    personalId: undefined as string | undefined,\r\n    /** List of calculations for the employment ID */\r\n    calcList: undefined as CalculationListItem[] | undefined,\r\n    /** Type of the list (filtering of the items on server-side) */\r\n    type: undefined as string | undefined,\r\n  };\r\n\r\n  constructor(\r\n    private ajax: Ajax,\r\n    private $timeout: angular.ITimeoutService,\r\n    private userSettingsService: UserSettingsService,\r\n    private $sce: angular.ISCEService,\r\n    private sessionService: SessionService,\r\n    private uiHelpers: UiHelpers,\r\n    private reportsService: ReportsService,\r\n  ) {\r\n  }\r\n\r\n  $onInit(): void {\r\n    if (!this.isSupported) {\r\n      return;\r\n    }\r\n    this.worktimeApi = new WorktimeApiConnector(this.serverUrl + \"/api/v01/worktime\", this.ajax);\r\n    this.worktimeApi.reloadList().then(() => {\r\n      this.$timeout();\r\n    });\r\n    if (this.payroll) {\r\n      this.payrollId = this.payroll.id;\r\n    }\r\n    this.worktimeApi.fetchAllPayrolls().then(() => {\r\n      this.$timeout();\r\n    });\r\n  }\r\n\r\n  /** Gets or sets the current payroll in the controller and also updates the selected payroll in the WorktimeApiConnector. */\r\n  public get payrollId(): string | undefined {\r\n    return this._payrollId;\r\n  }\r\n  public set payrollId(value: string | undefined) {\r\n    this._payrollId = value;\r\n    this.worktimeApi.detailsPayrollId = value;\r\n  }\r\n\r\n  /**\r\n   * If supported for the company or partner, this URL is the integration server used in for the imports.\r\n   */\r\n  public get serverUrl(): string | undefined {\r\n    return this.sessionService.session.settings.integration.serverUrl || undefined;\r\n  }\r\n\r\n  /**\r\n   * Gets the user-specific setting (service), stored in the local storage.\r\n   */\r\n  public get userSettings() {\r\n    return this.userSettingsService;\r\n  }\r\n\r\n  /** If true, the staginc server is supported for the partner. */\r\n  public get isSupported(): boolean {\r\n    return !!this.serverUrl;\r\n  }\r\n\r\n  /** Gets the calculations / salary slips for the employment. */\r\n  public get currentEmploymentCalcs(): CalculationListItem[] {\r\n    if (!this.worktimeApi.current?.preview?.employments?.length) {\r\n      return [];\r\n    }\r\n    const personalId = this.worktimeApi.current.preview.employments[0].identity.personalId;\r\n    if (this.salarySlipCache.personalId !== personalId || this.salarySlipCache.type !== this.salarySlipListType) {\r\n      this.salarySlipCache.personalId = personalId;\r\n      this.salarySlipCache.calcList = undefined;\r\n      this.salarySlipCache.type = this.salarySlipListType;\r\n      this.ajax.getJSON(this.serverUrl + `/api/v01/worktime/employment/${personalId}/calculations?type=${this.salarySlipListType}`)\r\n        .then((result: any) => {\r\n          this.salarySlipCache.calcList = result.value;\r\n        });\r\n    }\r\n    return this.salarySlipCache.calcList;\r\n  }\r\n\r\n  /**\r\n   * Commits the current payroll.\r\n   * @param scope - The scope of the commit: Payroll commits the entire payroll in the controller.\r\n   * Employment commits the selected employment only and the Payroll specified in the employment.\r\n   */\r\n  public async commitPayroll(scope: \"payroll\" | \"employment\") {\r\n    const commitSingle = async (payrollId: string, employmentId: string) => {\r\n      await this.ajax.postJSON(this.serverUrl + `/api/v01/worktime/commit-payroll/${payrollId}/${employmentId}`, undefined);\r\n    };\r\n\r\n    if (scope == \"payroll\") {\r\n      if (!this.payrollId) {\r\n        throw new Error(\"No payroll selected.\");\r\n      }\r\n      const list = this.worktimeApi.getFilteredList(this.payrollId);\r\n      const columns = [\r\n        { title: Translations.get(\"SALAXY.UI_Terms.name\"), field: \"sortableName\" },\r\n        { title: Translations.get(\"SALAXY.UI_Terms.personalId\"), field: \"personalId\" },\r\n      ];\r\n      await this.uiHelpers.showBatchProcessDialog(Translations.get(\"SALAXY.NG1.ImportStagingComponent.dialog.commitPayroll\"), list, async (item, _data) => {\r\n        if (Array.isArray(item)) {\r\n          throw new Error(\"Batch processing not supported for payroll commit.\");\r\n        }\r\n        await commitSingle(this.payrollId, item.id);\r\n        return [{\r\n          message: \"\",\r\n          result: undefined,\r\n        }];\r\n      }, undefined, {}, columns, undefined, true);\r\n      this.$timeout(() => {\r\n        this.reloadUi();\r\n      });\r\n      return;\r\n    }\r\n\r\n    const loader = this.uiHelpers.showLoading(Translations.get(\"SALAXY.NG1.ImportStagingComponent.dialog.commitPayroll\"));\r\n    await commitSingle(this.worktimeApi.detailsPayrollId, this.worktimeApi.current.id);\r\n    loader.dismiss();\r\n    this.reloadUi();\r\n  }\r\n\r\n  /** Reloads the current user interface: Especially the payroll if we are in the Payroll view. */\r\n  public reloadUi() {\r\n    this.sessionService.refreshUi();\r\n  }\r\n\r\n  /**\r\n   * Gets the totals for the selected payroll or the entire history if no payroll is selected.\r\n   * @param row - The row for which to get the totals.\r\n   */\r\n  public getTotals(row: WorktimeImportInStagingListItem | \"all\"): WorktimeImportPreviewMetadata {\r\n    if (row == \"all\") {\r\n      let rows: WorktimeImportPreviewMetadata[] = [];\r\n      if (this.worktimeApi?.list) {\r\n        rows = this.payrollId\r\n          ? this.worktimeApi.list.map((item) => item.payrolls[this.payrollId]).filter((item) => item)\r\n          : this.worktimeApi.list.map((item) => item.totals);\r\n      }\r\n      return this.uiHelpers.cache(this, \"allTotals\", () => {\r\n        return rows.reduce((acc: WorktimeImportPreviewMetadata, cur: WorktimeImportPreviewMetadata) => {\r\n          return {\r\n            calcs: {\r\n              count: acc.calcs.count + cur.calcs.count,\r\n            },\r\n            period: cur.period, // Add min/max if necessary\r\n            rows: {\r\n              committed: acc.rows.committed + cur.rows.committed,\r\n              count: acc.rows.count + cur.rows.count,\r\n              deleted: acc.rows.deleted + cur.rows.deleted,\r\n              edited: acc.rows.edited + cur.rows.edited,\r\n              error: acc.rows.error + cur.rows.error,\r\n              ignored: acc.rows.ignored + cur.rows.ignored,\r\n              new: acc.rows.new + cur.rows.new,\r\n              preview: acc.rows.preview + cur.rows.preview,\r\n            },\r\n            salaryDate: cur.salaryDate, // Add min/max if necessary\r\n          };\r\n        }, {\r\n          calcs: {\r\n            count: 0,\r\n          },\r\n          rows: {\r\n            committed: 0,\r\n            count: 0,\r\n            deleted: 0,\r\n            edited: 0,\r\n            error: 0,\r\n            ignored: 0,\r\n            new: 0,\r\n            preview: 0,\r\n          }\r\n        } as any);\r\n      }, /** Add upadated at to WorktimeImportPreviewMetadata for quicker cache  */);\r\n    }\r\n    if (this.payrollId) {\r\n      const totals = row.payrolls[this.payrollId];\r\n      if (this.payrollCalcs && totals && !(totals as any).committed) {\r\n        const committedCalc = this.payrollCalcs.find((calc) => calc.data.employmentId == row.id);\r\n        if (committedCalc) {\r\n          (totals as any).committed = {\r\n            gross: committedCalc.grossSalary,\r\n            net: committedCalc.data.workerPayment,\r\n          };\r\n        }\r\n      }\r\n      return totals;\r\n    }\r\n    return row.totals;\r\n  }\r\n\r\n  /**\r\n   * Recalculates the current worktime (if selected).\r\n   */\r\n  public async recalculateWorktime() {\r\n    const id = this.worktimeApi.current?.id;\r\n    this.showDetails(undefined);\r\n    const loader = this.uiHelpers.showLoading(Translations.get(\"SALAXY.NG1.ImportStagingComponent.dialog.recalculating\"));\r\n    await this.worktimeApi.recalculateWorktime(id);\r\n    this.showDetails(id);\r\n    loader.dismiss();\r\n  }\r\n\r\n  /**\r\n   * Saves the manual rows to the server and refreshes the view.\r\n   * @returns The updated worktime import.\r\n   */\r\n  public async saveManualRows(): Promise<void> {\r\n    await this.worktimeApi.saveManualRows();\r\n    await this.recalculateWorktime();\r\n  }\r\n\r\n  /** Deletes the current worktime (with are you sure) */\r\n  public async deleteWorktime() {\r\n    if (!this.worktimeApi.current) {\r\n      return;\r\n    }\r\n    this.uiHelpers.showConfirm(\"SALAXY.NG1.ApiCrudObjectComponent.deleteDialog\").then((result: boolean) => {\r\n      if (result) {\r\n        const id = this.worktimeApi.current.id;\r\n        this.showDetails(undefined);\r\n        this.worktimeApi.delete(id);\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Recalculates all the worktimes in the list.\r\n   */\r\n  public async recalculateAllWorktimes() {\r\n    const loader = this.uiHelpers.showLoading(Translations.get(\"SALAXY.NG1.ImportStagingComponent.dialog.recalculating\"));\r\n    const list = this.worktimeApi.getFilteredList(this.payrollId);\r\n    for (let i = 0; i < list.length; i++) {\r\n      const item = list[i];\r\n      loader.setText(`Recalculating ${item.sortableName} ${i + 1}/${list.length}...`);\r\n      await this.worktimeApi.recalculateWorktime(item.id);\r\n    }\r\n    loader.dismiss();\r\n  }\r\n\r\n  /**\r\n   * Shows a report for the current calculation using a modal dialog.\r\n   * @param calculationId - Identifier of the calculation to show.\r\n   * @param reportType - Type of report to show\r\n   */\r\n  public showReportDialog(calculationId: string, reportType: calcReportType = \"salarySlip\") {\r\n    // TODO: Add support for all report types view\r\n    const isPreview = calculationId.startsWith(\"preview-\");\r\n    if (isPreview) {\r\n      const calc = this.worktimeApi.current.preview.calculations.find((calc) => calc.id == calculationId);\r\n      if (calc) {\r\n        this.reportsService.showReportModalForCalc(reportType, calc, \"page1\", true);\r\n        return;\r\n      }\r\n      throw new Error(`Calculation ${calculationId} not found in preview.`);\r\n    }\r\n    const url = `${this.serverUrl}/api/v01/worktime/calculations/${calculationId}`;\r\n    this.ajax.getJSON(url).then((calc) => {\r\n      this.reportsService.showReportModalForCalc(reportType, calc, \"page1\", false);\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shows the salary slip PDF in the IFrame UI.\r\n   * Sets the currentEmploymentPdf to the PDF of the salary slip (Base64 resource URI).\r\n   * @param calculationId Identifier of the calculation for which the PDF is shown.\r\n   */\r\n  public showSalarySlipPdf(calculationId: string | undefined) {\r\n    this.currentEmploymentPdf = \"loading\";\r\n    if (!calculationId) {\r\n      this.currentEmploymentPdf = undefined;\r\n      return;\r\n    }\r\n    this.ajax.getHTML(this.serverUrl + `/api/v01/worktime/calculations/${calculationId}/pdf`).then((pdf) => {\r\n      this.currentEmploymentPdf = this.$sce.trustAsResourceUrl(`data:application/pdf;base64, ${encodeURI(pdf)}`);\r\n      this.$timeout();\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shows the salary slip HTML in the IFrame UI.\r\n   * @param calculationId Identifier of the calculation for which the HTML is shown.\r\n   */\r\n  public showSalarySlipHtml(calculationId: string | undefined): void {\r\n    this.currentEmploymentPdf = this.$sce.trustAsResourceUrl(this.serverUrl + `/api/v01/worktime/calculations/${calculationId}/html?access_token=` + this.ajax.getCurrentToken());\r\n  }\r\n\r\n  /**\r\n   * Shows (hides) an item in the details view\r\n   * @param id - The ID of the item to show. If undefined, hides the details view.\r\n   */\r\n  public showDetails(id: string | undefined) {\r\n    if (id) {\r\n      this.worktimeApi.showDetails(id);\r\n    } else {\r\n      this.worktimeApi.setCurrent(undefined);\r\n    }\r\n  }\r\n\r\n  /** Returns true if the offcanvas (dialog) should be shown. */\r\n  public get showOffcanvas(): boolean {\r\n    return !!this.worktimeApi.current;\r\n  }\r\n\r\n  /** PDF salary slip that was last fetched for the current employment */\r\n  public currentEmploymentPdf: string | undefined = undefined;\r\n\r\n  /**\r\n   * Uploads a JSON file for testing purposes.\r\n   * Should be added to a form submit event.\r\n   * @param event - The change event that triggered by the file upload\r\n   * ...or string \"clipboard\" for clipboard data.\r\n   * @example\r\n   * ```html\r\n   * <form ng-submit=\"$ctrl.uploadTestFile($event)\">\r\n   *   <input type=\"file\" class=\"form-control\" />\r\n   *   <button type=\"submit\" class=\"btn btn-default\">Upload</button>\r\n   * </form>\r\n   * ```\r\n   */\r\n  public async uploadTestFile(event?: Event | \"clipboard\") {\r\n    let data: WorktimeImport;\r\n    if (event == \"clipboard\") {\r\n      const json = await window.navigator.clipboard.readText();\r\n      data = JSON.parse(json);\r\n    } else {\r\n      const form = event?.target as HTMLFormElement;\r\n      if (!form.tagName || form.tagName.toLowerCase() !== \"form\") {\r\n        throw new Error(`Method uploadTestFile should be connected to submit event of a form, e.g. <form ng-submit=\"$ctrl.uploadTestFile($event)\">.`);\r\n      }\r\n      const ipt = form.querySelector(\"input[type=file]\") as HTMLInputElement;\r\n      if (!ipt) {\r\n        throw new Error(\"No file input found in the form.\");\r\n      }\r\n      const file = ipt.files?.[0];\r\n      if (!file) {\r\n        return;\r\n      }\r\n      const text = await file.text();\r\n      data = JSON.parse(text);\r\n    }\r\n    if (!data.rows && !data.employments) {\r\n      throw new Error(\"Invalid data: Rows or employments are required.\");\r\n    }\r\n    let result: WorktimeImport;\r\n    try {\r\n      result = await this.worktimeApi.callUpdateWorktime(data);\r\n    } catch (error) {\r\n      this.uploadResults = error;\r\n      this.$timeout();\r\n      throw error;\r\n    }\r\n\r\n    const validationErrors = (result.rows ?? []).concat(result.employments ?? [])\r\n      .filter((row) => !row.validation.isValid);\r\n    if (validationErrors.length) {\r\n      console.error(\"Validation errors\", validationErrors);\r\n      this.uploadResults = validationErrors;\r\n      alert(\"Validation errors found, see console for details.\");\r\n    } else {\r\n      console.debug(\"Result\", result);\r\n      this.uploadResults = result;\r\n      alert(\"Updates have been saved and validated.\");\r\n    }\r\n    this.$timeout();\r\n  }\r\n\r\n  /**\r\n   * Uploads a JSON string for testing purposes.\r\n   * @param text - The JSON string to upload\r\n   */\r\n  public async uploadTestJson(text: string) {\r\n    const data = JSON.parse(text);\r\n    let result: WorktimeImport;\r\n    try {\r\n      result = await this.worktimeApi.callUpdateWorktime(data);\r\n    } catch (error) {\r\n      this.uploadResults = error;\r\n      this.$timeout();\r\n      throw error;\r\n    }\r\n\r\n    const validationErrors = (result.rows ?? []).concat(result.employments ?? [])\r\n      .filter((row) => !row.validation.isValid);\r\n    if (validationErrors.length) {\r\n      console.error(\"Validation errors\", validationErrors);\r\n      this.uploadResults = validationErrors;\r\n      alert(\"Validation errors found, see console for details.\");\r\n    } else {\r\n      console.debug(\"Result\", result);\r\n      this.uploadResults = result;\r\n      alert(\"Updates have been saved and validated.\");\r\n    }\r\n    this.$timeout();\r\n  }\r\n\r\n  /**\r\n   * Formats the debug JSON string.\r\n   */\r\n  public formatDebugJson() {\r\n    this.debugJson = JSON.stringify(JSON.parse(this.debugJson), null, 2);\r\n  }\r\n\r\n  /**\r\n   * Adds a blank WorktimeImport object to the debug JSON editor.\r\n   * Uses WorktimeApiConnector.getBlank() to generate the empty object.\r\n   */\r\n  public debugJsonAddBlank() {\r\n    this.debugJson = JSON.stringify(WorktimeApiConnector.getBlank(), null, 2);\r\n  }\r\n\r\n  public uploadResults: any = undefined;\r\n\r\n  /**\r\n   * Marks the selected rows with given state.\r\n   * @param rows - The rows to mark.\r\n   * @param status - The status to set.\r\n   * Status \"new\" is essentially reverting the state from \"ignored\" => final state may be \"preview\", \"new\" or \"error\" depending on other properties of the row.\r\n   */\r\n  public setStatus(rows: WorktimeImportRow[], status: \"ignored\" | \"new\") {\r\n    const loader = this.uiHelpers.showLoading();\r\n    this.worktimeApi.setStatus(rows, status).then((_result: WorktimeImport) => {\r\n      loader.dismiss();\r\n      this.$timeout();\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Deletes the selected rows from the current worktime import and saves the changes .\r\n   * @param rows - The rows to delete.\r\n   */\r\n  public async deleteRows(rows: WorktimeImportRow[]) {\r\n    const confirm = await this.uiHelpers.showConfirm(\"Haluatko varmaan poistaa valitut rivit?\", \"Rivit poistetaan työajan tuonnista, mutta ne saatetaan tuoda uudelleen myöhemmin, jos lähdejärjestelmän dataa päivitetään.\");\r\n    if (!confirm) {\r\n      return;\r\n    }\r\n    const loader = this.uiHelpers.showLoading();\r\n    this.worktimeApi.current.rows = this.worktimeApi.current.rows.filter((row) => !rows.includes(row));\r\n    await this.worktimeApi.saveCurrent();\r\n    loader.dismiss();\r\n  }\r\n\r\n  /**\r\n   * Moves the selected rows to the given payroll.\r\n   * @param rows - The rows to move.\r\n   * @param payrollId - The payroll id to move to.\r\n   * @returns The updated worktime import.\r\n   */\r\n  public async moveToPayroll(rows: WorktimeImportRow[], payrollId: string) {\r\n    const loader = this.uiHelpers.showLoading();\r\n    this.worktimeApi.moveToPayroll(rows, payrollId).then((_result: WorktimeImport) => {\r\n      loader.dismiss();\r\n      this.$timeout();\r\n    });\r\n  }\r\n\r\n  /** The current status group. */\r\n  public get statusGroup() {\r\n    return this.statusGroups.find((x) => x.active) || this.statusGroups[0];\r\n  }\r\n  public set statusGroup(value: {\r\n    key: string;\r\n    statuses: string[];\r\n    text: string;\r\n    count: number;\r\n    active?: boolean;\r\n  }) {\r\n    this.statusGroups.forEach((x) => x.active = x.key == value.key);\r\n  }\r\n\r\n  private updateCounts() {\r\n    // TODO: Currently diabled, need to figure out how to reliably update counts.\r\n    this.statusGroups.forEach((x) => x.count = this.worktimeApi.filteredRows.filter((row) => x.statuses.includes(row.status)).length);\r\n  }\r\n\r\n  /** The status groups availab. */\r\n  public statusGroups: {\r\n    key: string;\r\n    statuses: string[];\r\n    text: string;\r\n    count: number;\r\n    active?: boolean;\r\n  }[]\r\n    = [\r\n      {\r\n        key: \"todo\",\r\n        statuses: [\"preview\", \"new\", \"error\", \"deleted\", \"edited\"],\r\n        text: \"SALAXY.NG1.ImportStagingComponent.statusGroup.todo\",\r\n        count: 0,\r\n        active: true,\r\n      },\r\n      {\r\n        key: \"waitingCommit\",\r\n        statuses: [\"preview\", \"new\", \"edited\"],\r\n        text: \"SALAXY.NG1.ImportStagingComponent.statusGroup.waitingCommit\",\r\n        count: 0,\r\n      },\r\n      {\r\n        key: \"committed\",\r\n        statuses: [\"committed\"],\r\n        text: \"SALAXY.NG1.ImportStagingComponent.status.committed\",\r\n        count: 0,\r\n      },\r\n      {\r\n        key: \"all\",\r\n        statuses: [],\r\n        text: \"SALAXY.NG1.ImportStagingComponent.status.all\",\r\n        count: 0,\r\n      },\r\n      {\r\n        key: \"ignored\",\r\n        statuses: [\"ignored\"],\r\n        text: \"SALAXY.NG1.ImportStagingComponent.status.ignored\",\r\n        count: 0,\r\n      },\r\n      {\r\n        key: \"error\",\r\n        statuses: [\"error\"],\r\n        text: \"SALAXY.NG1.ImportStagingComponent.status.error\",\r\n        count: 0,\r\n      },\r\n      {\r\n        key: \"preview\",\r\n        statuses: [\"preview\"],\r\n        text: \"SALAXY.NG1.ImportStagingComponent.status.preview\",\r\n        count: 0,\r\n      },\r\n    ];\r\n}","import angular from \"angular\";\r\nimport { ApiImportStatus, ApiCheckStatus, Arrays, UserDefinedRow, Imports, DataMapper, DataMapperSelector, WorkerCheck, WorkerImportRow, WorkerImport, ApiValidationErrorType, Translations} from \"@salaxy/core\";\r\n\r\nimport { DataImportControllerBase } from \"./DataImportControllerBase\";\r\n\r\nimport { JsonSchemaService } from \"../../../services\";\r\n\r\n\r\n/**\r\n * Controller for worker imports.\r\n */\r\nexport class WorkerImportController extends DataImportControllerBase<WorkerImportRow, WorkerImport, never> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Imports\", \"JsonSchemaService\", \"$timeout\"];\r\n\r\n  /**\r\n   * Boolean indicating if the worker validation is in progress.\r\n   */\r\n  public isValidating = false;\r\n\r\n  private getTargetKey = (x: WorkerImport) => `${x.officialId}_${x.item.officialPersonId}`.toLowerCase();\r\n  private getSourceKey = (x: WorkerImportRow) => `${x.companyOfficialId}_${x.personalId}`.toLowerCase();\r\n  private getCheckTargetKey = (x: WorkerCheck) => `${x.officialId}_${x.id}`.toLowerCase();\r\n  private getCheckSourceKey = (x: WorkerImportRow) => `${x.companyOfficialId}_${x.personalId}`.toLowerCase();\r\n\r\n  private extraValidator = {\r\n    validate: () => this.validateWorkers(),\r\n    buttonLabel: Translations.get(\"SALAXY.NG1.WorkerImport.validateWorkersButton\")\r\n  };\r\n\r\n  /**\r\n   * Creates a new WorkerImportController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    private importsApi: Imports,\r\n    jsonSchemaService: JsonSchemaService,\r\n    $timeout: angular.ITimeoutService\r\n  ) {\r\n    super(jsonSchemaService, $timeout);\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public async $onInit(){\r\n    super.$onInit();\r\n  }\r\n  /** Import data */\r\n  public async import() {\r\n\r\n    if (this.isImporting) {\r\n      return;\r\n    }\r\n\r\n    await this.validate();\r\n    if (!this.targetData) {\r\n      return;\r\n    }\r\n\r\n    this.isImporting = true;\r\n    this.isCanceled = false;\r\n\r\n    for(const sourceRow of this.sourceData) {\r\n      sourceRow.validation = null;\r\n      sourceRow.importStatus = ApiImportStatus.Ignored;\r\n    }\r\n    this.table.setData(this.sourceData);\r\n    await this.$timeout();\r\n\r\n    this.importTotal = this.targetData.length;\r\n    this.importCurrent = 0;\r\n\r\n    const chunkSize = 10;\r\n    const chunks: WorkerImport[][] = [];\r\n    for (let i = 0; i < this.targetData.length; i += chunkSize) {\r\n        chunks.push(this.targetData.slice(i, i + chunkSize));\r\n    }\r\n\r\n    let index = 0;\r\n    for(const chunk of chunks) {\r\n      try {\r\n        if (this.isCanceled) {\r\n          break;\r\n        }\r\n        chunk.splice(0, chunk.length, ... await this.importsApi.importWorkers(chunk));\r\n      } catch (error) {\r\n        for( const importObj of chunk) {\r\n          importObj.result = importObj.result ?? {};\r\n          importObj.result.status = ApiImportStatus.Error,\r\n          importObj.validation = {\r\n            isValid: false,\r\n            errors: [{\r\n              key: null,\r\n              type: ApiValidationErrorType.General,\r\n              code: \"Server error\",\r\n              msg: error?.data?.messageHtml || JSON.stringify(error?.data, Object.getOwnPropertyNames(error?.data)),\r\n            }],\r\n          };\r\n        }\r\n      }\r\n      for(const result of chunk) {\r\n        const sourceRows = this.sourceData.filter((x) => this.getSourceKey(x) == this.getTargetKey(result));\r\n        for(const sourceRow of sourceRows) {\r\n          sourceRow.validation = {\r\n            isValid: result.validation?.isValid,\r\n            errors: result.validation?.errors\r\n          };\r\n          sourceRow.importStatus = result.result?.status;\r\n        }\r\n        index += sourceRows.length;\r\n        this.importCurrent = index;\r\n\r\n        this.table.setData(this.sourceData);\r\n        await this.$timeout();\r\n      }\r\n    }\r\n    this.isImporting = false;\r\n    await this.$timeout();\r\n  }\r\n\r\n  /** Help */\r\n  public async help() {\r\n    const helpData = [\r\n      [Translations.get(\"SALAXY.NG1.WorkerImport.help.title\")],\r\n      [\"\"],\r\n      [Translations.get(\"SALAXY.NG1.WorkerImport.help.overview.title\")],\r\n      [Translations.get(\"SALAXY.NG1.WorkerImport.help.overview.row1\")],\r\n      [Translations.get(\"SALAXY.NG1.WorkerImport.help.overview.row2\")],\r\n      [\"\"],\r\n      ...this.getDefaultHelpDataForColumns(),\r\n    ];\r\n    await this.download(helpData);\r\n  }\r\n\r\n  /** Returns extra validator */\r\n  public getExtraValidators(): Array<{ validate: () => void, buttonLabel: string }> {\r\n      return [this.extraValidator];\r\n  }\r\n\r\n  protected async getImportMapper() {\r\n\r\n    const rowMap = {\r\n      defaultRowType: \"rowType\",\r\n      defaultRowKind: \"data.kind\",\r\n      defaultSalary: \"price\",\r\n    };\r\n\r\n    const rowMapper = new DataMapper<WorkerImportRow, UserDefinedRow>(\"NG1/WorkerImporController\", \"Työntekijät\");\r\n    await rowMapper.setSchemaFromCache(this.jsonSchemaService.getCache(), \"salaxy-secure/schemas/v02.json\", \"UserDefinedRow\", \"target\");\r\n    rowMapper.setPaths(rowMap);\r\n    rowMapper.generateSchema(\"WorkerImportRow\", \"source\");\r\n\r\n\r\n    const salaryDefaultSelector = new DataMapperSelector<WorkerImportRow, WorkerImport>(null,\"item.employment.work.salaryDefaults\",\r\n    (source) => {\r\n      if (source.defaultRowType && source.defaultSalary > 0) {\r\n        return rowMapper.doMap([source]);\r\n      }\r\n      return [];\r\n    });\r\n\r\n    const mapper = new DataMapper<WorkerImportRow, WorkerImport>(\"NG1/WorkerImportController\", \"Työntekijät\");\r\n    const map = {\r\n      companyOfficialId: \"officialId\",\r\n      personalId: \"item.officialPersonId\",\r\n      sourceId: \"item.employment.sourceId\",\r\n      firstName: \"item.avatar.firstName\",\r\n      lastName: \"item.avatar.lastName\",\r\n      email: \"item.contact.email\",\r\n      telephone: \"item.contact.telephone\",\r\n      ibanNumber: \"item.ibanNumber\",\r\n      street: \"item.contact.street\",\r\n      postalCode: \"item.contact.postalCode\",\r\n      city: \"item.contact.city\",\r\n      countryCode: \"item.contact.countryCode\",\r\n      startDate: \"item.employment.startDate\",\r\n      employmentType: \"item.employment.type\",\r\n      pensionCalculation: \"item.employment.pensionCalculation\",\r\n      description: \"item.employment.work.description\",\r\n      occupationCode: \"item.employment.work.occupationCode\",\r\n      taxcard: \"item.employment.taxcard\",\r\n      defaultRowType: salaryDefaultSelector,\r\n    };\r\n    await mapper.setSchemaFromCache(this.jsonSchemaService.getCache(), \"salaxy-secure/schemas/v02.json\", \"WorkerImport\", \"target\");\r\n    mapper.setPaths(map);\r\n    mapper.generateSchema(\"WorkerImportRow\", \"source\");\r\n\r\n    mapper.source.schema.properties.occupationCode[\"format\"] =\"Occupation\";\r\n    for(const property in rowMapper.source.schema.properties) {\r\n      mapper.source.schema.properties[property] = rowMapper.source.schema.properties[property];\r\n    }\r\n    return mapper;\r\n  }\r\n\r\n  /** Import data */\r\n  private async validateWorkers() {\r\n\r\n    if (this.isValidating) {\r\n      return;\r\n    }\r\n\r\n    await this.validate();\r\n    if (!this.targetData) {\r\n      return;\r\n    }\r\n\r\n    this.isValidating = true;\r\n\r\n    for(const sourceRow of this.sourceData) {\r\n      sourceRow.validation = null;\r\n      sourceRow.validation = {\r\n        isValid: null, // null on purpose\r\n        errors: [{\r\n          type: ApiValidationErrorType.General,\r\n          msg: Translations.get(\"SALAXY.UI_Terms.wait\"),\r\n        }],\r\n      };\r\n      sourceRow.importStatus = ApiImportStatus.Ignored;\r\n    }\r\n    this.table.setData(this.sourceData);\r\n    await this.$timeout();\r\n\r\n    const workerGroups = Arrays.groupBy(this.sourceData, this.getCheckSourceKey);\r\n    const workerChecks: WorkerCheck[] = [];\r\n    for(const workerGroupKey in workerGroups) {\r\n      workerChecks.push( {\r\n        officialId: workerGroups[workerGroupKey][0].companyOfficialId,\r\n        id: workerGroups[workerGroupKey][0].personalId,\r\n      });\r\n    }\r\n\r\n    const chunkSize = 10;\r\n    const chunks: WorkerCheck[][] = [];\r\n    for (let i = 0; i < workerChecks.length; i += chunkSize) {\r\n        chunks.push(workerChecks.slice(i, i + chunkSize));\r\n    }\r\n\r\n    for(const chunk of chunks) {\r\n      try {\r\n        chunk.splice(0, chunk.length, ... await this.importsApi.checkWorkers(chunk));\r\n      } catch (error) {\r\n        for( const checkObj of chunk) {\r\n          checkObj.result = checkObj.result ?? {};\r\n          checkObj.result.status = ApiCheckStatus.Error,\r\n          checkObj.validation = {\r\n            isValid: false,\r\n            errors: [{\r\n              key: null,\r\n              type: ApiValidationErrorType.General,\r\n              code: \"Server error\",\r\n              msg: error?.data?.messageHtml || JSON.stringify(error?.data, Object.getOwnPropertyNames(error?.data)),\r\n            }],\r\n          };\r\n        }\r\n      }\r\n      for(const result of chunk) {\r\n        const sourceRows = this.sourceData.filter((x) => this.getCheckSourceKey(x) == this.getCheckTargetKey(result));\r\n        for(const sourceRow of sourceRows) {\r\n          sourceRow.validation = {\r\n            isValid: result.validation.isValid,\r\n            errors: result.validation.isValid ? (\r\n                    (result.result.item == null || result.result.item.length == 0) ? [ {msg: Translations.get(\"SALAXY.NG1.WorkerImport.messageMissingEmployment\"), type: ApiValidationErrorType.General,}] :\r\n                    (result.result.item.length == 1) ? [ {msg: Translations.get(\"SALAXY.NG1.WorkerImport.messageExistingEmployment\"), type: ApiValidationErrorType.General,}] :\r\n                    (result.result.item.length > 1) ? [ {msg: Translations.get(\"SALAXY.NG1.WorkerImport.messageSeveralEmployments\"), type: ApiValidationErrorType.General,}] : result.validation.errors) :\r\n                    result.validation.errors\r\n          };\r\n        }\r\n\r\n        this.table.setData(this.sourceData);\r\n        await this.$timeout();\r\n      }\r\n    }\r\n    this.isValidating = false;\r\n    await this.$timeout();\r\n  }\r\n}","import angular from \"angular\";\r\n\r\nimport { CustomerInvoice, CustomerInvoiceListItem, CustomerInvoices } from \"@salaxy/core\";\r\n\r\nimport { UiHelpers } from \"../../services\";\r\nimport { ApiCrudObjectController } from \"../bases\";\r\n\r\n/**\r\n * Controller for listing and browsing Customer Usecases.\r\n * NOTE: Access save / modify methods is very restricted by design as invoces are created by Palkkaus and cannot be modified by the Customer.\r\n * Typically, you will not be able to save / delete / modify customer invoices in the production environment.\r\n */\r\nexport class CustomerInvoiceCrudController extends ApiCrudObjectController<CustomerInvoice, CustomerInvoiceListItem> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"CustomerInvoices\",\r\n    \"UiHelpers\",\r\n    \"$location\",\r\n    \"$routeParams\",\r\n  ];\r\n\r\n  /**\r\n   * Creates a new DatasetsCrudController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    fullApi: CustomerInvoices,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n  ) {\r\n    super(fullApi, uiHelpers, $location, $routeParams);\r\n  }\r\n\r\n  /**\r\n   * Controller initialization\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"/customer-invoices/\",\r\n      detailsUrl: this.detailsUrl || \"/customer-invoices/details/\",\r\n      // TODO: Add a custom listing\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/CustomerInvoices.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n}","import angular from \"angular\";\r\n\r\nimport { Ajax, Calculations, Configs, Dates, InputEnumOption, Invoice, InvoiceListItem, Invoices, InvoiceStatus, InvoiceType, PaymentChannel, Payrolls, Translations } from \"@salaxy/core\";\r\n\r\nimport { InvoicesService, UiHelpers } from \"../../services\";\r\nimport { ApiCrudObjectController } from \"../bases\";\r\n\r\n/**\r\n * Provides read access for authenticated user to access his/her own invoices\r\n * and write access to create new salary and related payments based on calculations.\r\n */\r\nexport class InvoiceCrudController extends ApiCrudObjectController<Invoice, InvoiceListItem> {\r\n  private _reportCalcs = [];\r\n  private _calcOrPayrollId = [];\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"Invoices\",\r\n    \"UiHelpers\",\r\n    \"$location\",\r\n    \"$routeParams\",\r\n    \"InvoicesService\",\r\n    \"AjaxNg1\",\r\n    \"Calculations\",\r\n    \"Payrolls\"\r\n  ];\r\n\r\n  /** For list component, defines the layout / functionality of the list. */\r\n  public mode: \"default\" | \"panel\" | \"person\";\r\n\r\n  /** Data reader for selected items. */\r\n  public selectionDataReader = {\r\n    /** Function to read data into given array */\r\n    read: (arr: Invoice[], message: string): Promise<void> => { // eslint-disable-line @typescript-eslint/no-unused-vars\r\n      const promises = this.odataController.selectedItems.map(x => this.api.getSingle(x.id));\r\n      return Promise.all(promises).then( (data) => {\r\n        arr.push(...data.filter(d => !!d));\r\n        return;\r\n      });\r\n    },\r\n    /** Optional label for data export */\r\n    exportLabel: Translations.get(\"SALAXY.NG1.AccountingReportToolsComponent.exportLabel\"),\r\n    /** Indicates if the export is not possible */\r\n    disabled: () => !this.odataController.selectedItems || this.odataController.selectedItems.length === 0,\r\n  };\r\n\r\n  /** Data reader for selected items. */\r\n  public selectionDataReaderPerson = {\r\n    /** Function to read data into given array */\r\n    read: (arr: Invoice[], message: string): Promise<void> => { // eslint-disable-line @typescript-eslint/no-unused-vars\r\n      const promises = this.odataController.selectedItems.map(x => this.api.getSingle(x.id));\r\n      return Promise.all(promises).then( (data) => {\r\n        data = data.filter(x => x.header.type === InvoiceType.Net || x.header.type === InvoiceType.Tax);\r\n        arr.push(...data.filter(d => !!d));\r\n        return;\r\n      });\r\n    },\r\n    /** Optional label for data export */\r\n    exportLabel: Translations.get(\"SALAXY.NG1.AccountingReportToolsComponent.exportLabel\"),\r\n    /** Indicates if the export is not possible */\r\n    disabled: () => !this.odataController.selectedItems || this.odataController.selectedItems.length === 0,\r\n  };\r\n\r\n  /** Status filters for lists: Groups statuses to logical groups. */\r\n  public statusFilters: InputEnumOption[] = [\r\n    {\r\n      value: \"all\",\r\n      text: Translations.get(\"SALAXY.NG1.InvoicesComponent.statusAll\"),\r\n      ui: \"\",\r\n    }, {\r\n      value: \"waitingConfirmation\",\r\n      text: Translations.get(\"SALAXY.NG1.InvoicesComponent.statusWaitingConfirmation\"),\r\n      ui: \"status eq 'unread' or status eq 'read' or status eq 'waitingConfirmation'\",\r\n    }, {\r\n      value: \"paid\",\r\n      text: Translations.get(\"SALAXY.NG1.InvoicesComponent.statusPaid\"),\r\n      ui: \"status eq 'paid' or status eq 'paymentStarted' or status eq 'canceled'\",\r\n    }, {\r\n      value: \"forecast\",\r\n      text: Translations.get(\"SALAXY.NG1.InvoicesComponent.statusForecast\"),\r\n      ui: \"status eq 'forecast' or status eq 'preview'\",\r\n    },\r\n  ];\r\n\r\n  constructor(\r\n    protected invoicesApi: Invoices,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    private invoicesService: InvoicesService,\r\n    private ajax: Ajax,\r\n  ) { // Dependency injection\r\n    super(invoicesApi, uiHelpers, $location, $routeParams);\r\n  }\r\n\r\n  /**\r\n   * Initializes the controller\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Gets the default channel for the current account. */\r\n  public get defaultChannel(): PaymentChannel {\r\n    return this.invoicesService.defaultChannel;\r\n  }\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"invoices\",\r\n      detailsUrl: this.detailsUrl || \"/invoices/details/\",\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/InvoicesPanel.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n\r\n  /** Gets the type of the due date vs. the current date and status for display purposes. */\r\n  public getDueDateType(listItem: InvoiceListItem): \"default\" | \"estimation\" | \"canceled\" | \"overdue\" | \"future\"| \"unknown\" {\r\n    if (listItem.entityType === \"unemployment\" ) {\r\n      return \"estimation\";\r\n    }\r\n\r\n    switch (listItem.status) {\r\n      case InvoiceStatus.Canceled:\r\n        return \"canceled\";\r\n      case InvoiceStatus.Forecast:\r\n      case InvoiceStatus.Preview:\r\n        if (listItem.endAt > Dates.getToday()) {\r\n          return \"future\";\r\n        }\r\n        return \"default\";\r\n      case InvoiceStatus.Undefined:\r\n      case InvoiceStatus.Unread:\r\n        if (listItem.endAt < Dates.getToday()) {\r\n          return \"overdue\";\r\n        }\r\n        return \"default\";\r\n      case InvoiceStatus.Read:\r\n      case InvoiceStatus.WaitingConfirmation:\r\n      case InvoiceStatus.WaitingPalkkaus:\r\n      case InvoiceStatus.Paid:\r\n      case InvoiceStatus.PaymentStarted:\r\n        return \"default\";\r\n    }\r\n    return \"default\";\r\n  }\r\n\r\n  /** For list components, gets the OData query options. */\r\n  public getListOptions() {\r\n    return this.uiHelpers.cache(this, \"listOptions\", () => {\r\n      if (this.mode === \"panel\") {\r\n        return {\r\n          $filter: \"\",\r\n          $top: 5,\r\n          $orderby: \"endAt desc\",\r\n        };\r\n      } else {\r\n        // Add logic and e.g. if needed\r\n        return {\r\n          $orderby: \"endAt desc\",\r\n        };\r\n      }\r\n    });\r\n  }\r\n\r\n  /** Returns content url for the invoice. */\r\n  public getContentUrl(id: string, inline = false): string {\r\n    return this.invoicesApi.getContentUrl(id, inline);\r\n  }\r\n\r\n  /**\r\n   * Request the status update for the invoice.\r\n   * @param status Status data. If not set, uses the requestedStatus property of the controller.\r\n   */\r\n  public requestStatusUpdate(status: InvoiceStatus = null): any {\r\n    status = status || this.requestedStatus;\r\n\r\n    if ( status === InvoiceStatus.Paid && (\r\n      this.current.header.channel === PaymentChannel.Test ||\r\n      this.current.header.channel === PaymentChannel.Procountor ||\r\n      this.current.header.channel === PaymentChannel.VismaNetvisor)) {\r\n\r\n      const loader = this.uiHelpers.showLoading(\"Maksuikkuna avattu...\");\r\n      let url = \"\";\r\n      switch ( this.current.header.channel) {\r\n        case PaymentChannel.Test:\r\n          url =\r\n          Configs.current.isTestData ?\r\n          \"https://test-integrations.salaxy.com/test#/dialogs/invoice\" :\r\n          \"https://integrations.salaxy.com/test#/dialogs/invoice\";\r\n          break;\r\n        case PaymentChannel.Procountor:\r\n          url =\r\n          Configs.current.isTestData ?\r\n          \"http://localhost:93/procountor/invoice.html\" :\r\n          \"https://integrations.salaxy.com/procountor/invoice.html\";\r\n          break;\r\n        case PaymentChannel.VismaNetvisor:\r\n         url =\r\n         Configs.current.isTestData ?\r\n          \"http://localhost:93/vismanetvisor/invoice.html\" :\r\n          \"https://integrations.salaxy.com/vismanetvisor/invoice.html\";\r\n        break;\r\n      }\r\n      url += \"?invoiceIds=\" + this.currentId + \"&token=\" + this.ajax.getCurrentToken();\r\n      return this.uiHelpers.showExternalDialog(\"invoiceCreation\", url, {})\r\n        .then(() => {\r\n          loader.dismiss();\r\n          return this.setStatus(this.api.getSingle(this.current.id)).then((invoice) => {\r\n            if (invoice) {\r\n              this.setCurrent(invoice);\r\n            }\r\n            return invoice;\r\n          });\r\n        });\r\n    } else {\r\n\r\n      return this.setStatus(this.invoicesApi.requestStatusUpdate(this.currentId, status)\r\n        .then((invoice) => {\r\n          if (invoice) {\r\n            this.setCurrent(invoice);\r\n          }\r\n          return invoice;\r\n        }));\r\n    }\r\n  }\r\n\r\n  /** Requested status for binding */\r\n  public get requestedStatus(): InvoiceStatus {\r\n    if (this.current) {\r\n      return (this.current.header as any).requestedStatus || this.current.header.status;\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /** Requested status for binding */\r\n  public set requestedStatus(value: InvoiceStatus) {\r\n    (this.current.header as any).requestedStatus = value;\r\n  }\r\n\r\n  /**\r\n   * Delete invoice and related business objects (calculations and payrolls)\r\n   * @param item  - Invoice to delete.\r\n   * @param confirmMessage - Optional message for confirm popup\r\n   */\r\n  public deleteWithBusinessObjects(item?: Invoice, confirmMessage?: string): Promise<boolean> {\r\n    item = item || this.current;\r\n    return this.uiHelpers.showConfirm(confirmMessage || \"Haluatko varmasti poistaa tämän laskun ja siihen liittyvät laskelmat ja palkkalistat?\")\r\n      .then((result: boolean) => {\r\n        if (result) {\r\n          return this.ajax.remove(`/accounts/invoice?ids=${item.id}`).then(() => {\r\n            if (this.current === item) {\r\n              this.setCurrent(null);\r\n            }\r\n            if (this.odataController) {\r\n              this.odataController.reload();\r\n            } else {\r\n              this.$location.url(this.getDefaults().listUrl);\r\n            }\r\n            return true;\r\n          });\r\n        } else {\r\n          return Promise.resolve(false);\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Data reader for one item.\r\n   * TODO: Should add interface for the reader.\r\n   */\r\n  public getItemDataReader = (item: {\r\n    /** List item id */\r\n    id: string,\r\n    /** List item owner */\r\n    owner: string,\r\n  }) => {\r\n    return {\r\n      /** Function to read data into given array */\r\n      read: (arr: Invoice[], message: string): Promise<void> => { // eslint-disable-line @typescript-eslint/no-unused-vars\r\n        (item as any).isReading = true;\r\n        return this.api.getSingle(item.id).then((data) => {\r\n          /*\r\n          const wfEvent = {\r\n            type: \"PartnerMessageClosed\",\r\n            ui: \"success\" as any,\r\n            message,\r\n          };\r\n          return this.filesApi.saveWorkflowEvent(item, wfEvent).then(() => {\r\n            this.setWorkflowEvent(item as any, wfEvent);\r\n          */\r\n          if (data) {\r\n            arr.push(data);\r\n          }\r\n          (item as any).isReading = false;\r\n          return Promise.resolve();\r\n          /* });*/\r\n        });\r\n      },\r\n      /** Optional label for data export */\r\n      exportLabel: null,\r\n      /** Indicates if the export is not possible */\r\n      disabled: () => false,\r\n    };\r\n  };\r\n\r\n  /** Unselect all */\r\n  public unselectAll() {\r\n    if (this.odataController.selectedItems) {\r\n      this.odataController.selectedItems.splice(0, this.odataController.selectedItems.length);\r\n    }\r\n  }\r\n\r\n  /** Select all */\r\n  public selectAll() {\r\n    if (this.odataController.selectedItems && this.odataController.items) {\r\n      this.odataController.selectedItems.splice(0, this.odataController.selectedItems.length);\r\n      this.odataController.selectedItems.push(...this.odataController.items);\r\n    }\r\n  }\r\n\r\n  /** Open PaymentDialog for selected row */\r\n  public showPaymentDialog(row: InvoiceListItem) {\r\n    this.invoicesService.showPaymentDialogForCalculation(row);\r\n  }\r\n\r\n  /** Get invoices calculation by id */\r\n  public getReportCalcs() {\r\n    const id = this.current.header.businessObjects[0];\r\n    if (!this._calcOrPayrollId.includes(id)) {\r\n      this._calcOrPayrollId.push(id);\r\n      const calculations = new Calculations(this.ajax);\r\n      calculations.getSingle(id).then(calc => {\r\n        if (calc) {\r\n          this._reportCalcs.splice(0,this._reportCalcs.length);\r\n          this._reportCalcs.push(calc);\r\n        } else if(this.current.header.type === InvoiceType.Gross) {\r\n          const payrolls = new Payrolls(this.ajax);\r\n          payrolls.getOData({$filter: `id eq '${this.current.header.businessObjects[0]}'`}).then(result => {\r\n            if(result.items[0] && result.items[0].businessObjects.length) {\r\n              const calculations = new Calculations(this.ajax);\r\n              calculations.getMulti(result.items[0].businessObjects).then(calcs => {\r\n                this._reportCalcs.splice(0,this._reportCalcs.length);\r\n                this._reportCalcs.push(...calcs);\r\n              });\r\n            }\r\n          });\r\n        }\r\n      });\r\n    }\r\n    return this._reportCalcs;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Ajax, Arrays,Invoices, Dates, Translations, CompanyAccount, PaymentChannel, SystemRole, Invoice, InvoiceType, InvoiceStatus, ODataQueryOptions, InvoiceListItem, BicHelper, Numeric, InvoicesLogic, Token, Configs } from \"@salaxy/core\";\r\nimport { Barcodes, QrCodes } from \"@salaxy/reports\";\r\n\r\nimport { InvoicesService, SessionService, UiHelpers } from \"../../services\";\r\nimport { InvoiceCrudController } from \"./InvoiceCrudController\";\r\nimport { TabButtonsController } from \"../../controllers/helpers/TabButtonsController\";\r\ntype PaymentChannelConfig = {\r\n  /** Optional function that returns an action for handling multiple selected invoices. */\r\n  multiSelectAction?: () => {text: string, onClick: () => void}\r\n  /** Optional function that returns an array of actions for handling individual invoice items. */\r\n  rowActions?: (item: InvoiceListItem) => {text: string, onClick: (invoice: InvoiceListItem) => Promise<void>}[]\r\n  groupingFunction: (items: InvoiceListItem[]) => GroupedItem[]\r\n  rowGroupActions?: (group: GroupedItem) => {text: string, onClick: (group: GroupedItem) => Promise<void>}[]\r\n  hasExternalSystemMessagesEnabled: boolean\r\n}\r\n\r\ntype GroupedItem = {\r\n  id: string;\r\n  businessObjectId?: string;\r\n  groupType: string;\r\n  title: string;\r\n  sortableDate: string;\r\n  invoices: InvoiceListItem[];\r\n}\r\n/**\r\n * Extends the InvoiceCrudController to provide\r\n * SEPA payment management functionality.\r\n */\r\nexport class InvoicePaymentListController extends InvoiceCrudController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   */\r\n  public static $inject = [\r\n    \"Invoices\",\r\n    \"UiHelpers\",\r\n    \"$location\",\r\n    \"$routeParams\",\r\n    \"InvoicesService\",\r\n    \"AjaxNg1\",\r\n    \"SessionService\",\r\n    \"$http\",\r\n    \"$timeout\",\r\n    \"$sce\",\r\n    \"$scope\"\r\n  ];\r\n\r\n  /** URL for the OData list service, null for preventing automatic initial load */\r\n  public get odataServiceUrl(): string {\r\n    return null;\r\n  }\r\n  public groupedItems: GroupedItem[] = [];\r\n\r\n  /** Year for invoices query */\r\n  public queryYear = Dates.getToday();\r\n\r\n  public selectedInvoices: any[] = [];\r\n\r\n  /** Status filters for invoices */\r\n  public invoiceEntityTypes = [\r\n    { label: Translations.get(\"SALAXY.NG1.InvoicesComponent.all\"), value: \"all\" },\r\n    { label: Translations.get(\"SALAXY.ENUM.InvoiceType.net.label\"), value: \"net\" },\r\n    { label: Translations.get(\"SALAXY.ENUM.InvoiceType.pension.label\"), value: \"pension\" },\r\n    { label: Translations.get(\"SALAXY.ENUM.InvoiceType.tax.label\"), value: \"tax\" },\r\n    { label: Translations.get(\"SALAXY.ENUM.InvoiceType.unemployment.label\"), value: \"unemployment\" },\r\n    { label: Translations.get(\"SALAXY.ENUM.InvoiceType.union.label\"), value: \"union\" },\r\n    { label: Translations.get(\"SALAXY.ENUM.InvoiceType.payroll.label\"), value: \"payroll\" },\r\n  ];\r\n\r\n  /** Invoice entity type used in filtering */\r\n  public invoiceEntityType = this.invoiceEntityTypes.find((x) => x.value === \"all\");\r\n\r\n  /** Status filters for invoices */\r\n  public statusFilters = [\r\n    {\r\n      value: \"all\",\r\n      text: Translations.get(\"SALAXY.NG1.InvoicesComponent.statusAll\"),\r\n      ui: \"\",\r\n    },\r\n    {\r\n      value: \"read\",\r\n      text: \"Käsittelyssä olevat\",\r\n      ui: \"status eq 'read'\",\r\n    },\r\n    {\r\n      value: \"unread\",\r\n      text: \"Uudet maksut\",\r\n      ui: \"status eq 'unread'\",\r\n    },\r\n    {\r\n      value: \"paid\",\r\n      text: \"Maksetut\",\r\n      ui: \"status eq 'paid'\",\r\n    },\r\n    {\r\n      value: \"canceled\",\r\n      text: \"Perutut\",\r\n      ui: \"status eq 'canceled'\",\r\n    },\r\n    {\r\n      value: \"forecast\",\r\n      text: Translations.get(\"SALAXY.NG1.InvoicesComponent.statusForecast\"),\r\n      ui: \"status eq 'forecast' or status eq 'preview'\",\r\n    },\r\n  ];\r\n\r\n  /** The current status filter. \"waitingConfirmation\" is the default. */\r\n  public statusFilter = this.statusFilters.find((x) => x.value === \"all\");\r\n\r\n  /** Default sepa channel */\r\n  public paymentChannel: PaymentChannel;\r\n\r\n  public currentTab: \"netpaymentsandforeclosure\" | \"monthlypayments\" = \"netpaymentsandforeclosure\";\r\n\r\n  public paymentChannelConfig: PaymentChannelConfig = null;\r\n\r\n  public companyAccount: CompanyAccount;\r\n\r\n  public sortMode: \"asc\" | \"desc\" = \"desc\";\r\n\r\n  /** Filter for other party name */\r\n  public otherPartyNameFilter = \"\";\r\n\r\n  /** Filter for reference number */\r\n  public referenceFilter = \"\";\r\n\r\n  /** Filter for IBAN number */\r\n  public ibanFilter = \"\";\r\n\r\n  private qrCodesCache: { [key: string]: string } = {};\r\n\r\n  private rowActionsCache: { [key: string]: any[] } = {};\r\n  private rowGroupActionsCache: { [key: string]: any[] } = {};\r\n  /** Tab buttons component controller, to programmatically change tabs. */\r\n  private tabButtonsCtrl: TabButtonsController;\r\n  constructor(\r\n    invoicesFullApi: Invoices,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    private invService: InvoicesService,\r\n    private sepaAjax: Ajax,\r\n    private session: SessionService,\r\n    private $http: angular.IHttpService,\r\n    private $timeout: angular.ITimeoutService,\r\n    private $sce: angular.ISCEService,\r\n    private $scope: angular.IScope\r\n  ) {\r\n    // Dependency injection\r\n    super(invoicesFullApi, uiHelpers, $location, $routeParams, invService, sepaAjax);\r\n  }\r\n\r\n  /** Intitializes the controller */\r\n  public $onInit() {\r\n    this.paymentChannel ??= this.invService.defaultPaymentListChannel;\r\n    super.$onInit();\r\n    this.$scope.$on(\"tabButtonsControllerReady\", (event, data: { ctrl: TabButtonsController, tabsId: string }) => {\r\n      this.tabButtonsCtrl = data.ctrl;\r\n    });\r\n    this.companyAccount = this.session.getCompanyAccount();\r\n    this.loadData();\r\n  }\r\n\r\n  /**\r\n   * Selects and shows a tab in the payroll details view\r\n   */\r\n  public selectTab(tab: \"netpaymentsandforeclosure\" | \"monthlypayments\"): void {\r\n    this.tabButtonsCtrl.showTab(tab);\r\n  }\r\n\r\n  /**\r\n   * Loads the data for the controller.\r\n   */\r\n  public loadData(showLoading = true, idsToUpdate: string[] | null = null) {\r\n    let loading: any;\r\n    if(showLoading) {\r\n      loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.loading\");\r\n    }\r\n    this.loadAllInvoices(idsToUpdate).then((items) => {\r\n      this.setPaymentChannelConfig();\r\n      this.updategroupedItems(items, !!idsToUpdate);\r\n      if(showLoading) {\r\n        loading.dismiss();\r\n      }\r\n      this.$timeout();\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Checks if multi-select functionality is supported by the current payment channel configuration\r\n   * @returns True if multi-select is supported, false otherwise\r\n   */\r\n  public supportItemMultiSelect(): boolean {\r\n    switch(this.paymentChannel) {\r\n      case PaymentChannel.PalkkausWS:\r\n        return this.isStronglyAuthorizedPayer() && !!this.paymentChannelConfig?.multiSelectAction;\r\n      default:\r\n        return !!this.paymentChannelConfig?.multiSelectAction;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Checks if the current payment channel configuration supports system messages\r\n   * @returns True if system messages are supported, false otherwise\r\n   */\r\n  public hasExternalSystemMessagesEnabled(): boolean {\r\n    return !!this.paymentChannelConfig?.hasExternalSystemMessagesEnabled;\r\n  }\r\n\r\n  /**\r\n   * Checks if a given invoice item is currently selected\r\n   * @param item The invoice item to check\r\n   * @returns True if the item is in the selectedInvoices array, false otherwise\r\n   */\r\n  public isSelected(item: any) {\r\n    return this.selectedInvoices.findIndex((x) => x.id === item.id) >= 0;\r\n  }\r\n\r\n  /**\r\n   * Sets the selected state of an invoice item\r\n   * @param item The invoice item to select/unselect\r\n   * @param value True to select, false to unselect, \"toggle\" to toggle selection state\r\n   */\r\n  public setSelected(item: any, value: true | false | \"toggle\" = true) {\r\n    const ix = this.selectedInvoices.findIndex((x) => x.id === item.id);\r\n    const exists = ix >= 0;\r\n    if (exists) {\r\n      this.selectedInvoices.splice(ix, 1);\r\n    }\r\n    switch (value) {\r\n      case true:\r\n        this.selectedInvoices.push(item);\r\n        break;\r\n      case false:\r\n        // Already done\r\n        break;\r\n      case \"toggle\":\r\n        if (!exists) {\r\n          this.selectedInvoices.push(item);\r\n        }\r\n        break;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Determines if a given invoice item is selectable based on the current payment channel.\r\n   * For the PalkkausWS payment channel, only invoices with status WaitingConfirmation are selectable.\r\n   * For other payment channels, no items are selectable.\r\n   * @param {InvoiceListItem} item - The invoice item to check for selectability.\r\n   * @returns {boolean} True if the item is selectable, false otherwise.\r\n   */\r\n  public isItemSelectable(item: InvoiceListItem): boolean {\r\n    switch(this.paymentChannel) {\r\n      case PaymentChannel.PalkkausWS:\r\n        return item.status === InvoiceStatus.WaitingConfirmation;\r\n      default:\r\n        return false;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Sets the payment channel configuration based on the current payment channel.\r\n   * This method calls getPaymentChannelConfig() to get the appropriate configuration\r\n   * and assigns it to the paymentChannelConfig property.\r\n   */\r\n  public setPaymentChannelConfig() {\r\n    this.paymentChannelConfig = this.getPaymentChannelConfig();\r\n  }\r\n\r\n  /**\r\n   * Checks if the current user is an authorized payer.\r\n   * This method is only used when the payment channel is PalkkausWS.\r\n   * @returns True if the user is strongly authenticated (authorized payer), false otherwise.\r\n   */\r\n  public isStronglyAuthorizedPayer(): boolean {\r\n    return !!Token.parsePayload(this.sepaAjax.getCurrentToken()).act;\r\n  }\r\n\r\n  /**\r\n   * Opens a strong authentication dialog for the user.\r\n   * This method launches an external dialog for strong authentication using a third-party service.\r\n   * If the authentication is successful and a token is received, it exchanges the token for a new access token\r\n   * via the backend OAuth2 token exchange endpoint. The new access token is then set as the current token.\r\n   * If authentication fails or no token is received, an error is shown to the user.\r\n   * @returns {Promise<void>} A promise that resolves when the authentication flow is complete.\r\n   * @throws {Error} If no token is received from the authentication dialog or the token exchange fails.\r\n   */\r\n  public async openStrongAuthDialog(): Promise<void> {\r\n    let loader: any;\r\n    try {\r\n      const url = Configs.current.isTestData ? \"https://rc-iam.palkkaus.fi/strong-auth/index.html\" : \"https://iam.palkkaus.fi/strong-auth/index.html\";\r\n      const result = await this.uiHelpers.showExternalDialog(\"strong-auth\", url, null, null, null);\r\n      loader = this.uiHelpers.showLoading(\"Vahva tunnistus\", \"Avataan vahva tunnistus...\");\r\n      if (!result?.event?.data?.token) {\r\n        throw new Error(\"No token received from strong authentication\");\r\n      }\r\n\r\n      const response = await this.sepaAjax.postJSON(`${this.sepaAjax.getServerAddress()}/oauth2/token`, {\r\n        grant_type: \"urn:ietf:params:oauth:grant-type:token-exchange\",\r\n        subject_token: this.sepaAjax.getCurrentToken(),\r\n        actor_token: result.event.data.token\r\n      });\r\n      if (!response?.access_token) {\r\n        throw new Error(\"No access token received from token exchange\");\r\n      }\r\n      this.sepaAjax.setCurrentToken(response.access_token);\r\n      this.$timeout();\r\n    } catch (error) {\r\n      console.error(\"Strong authentication failed:\", error);\r\n      this.uiHelpers.showAlert(\"Virhe\", \"Vahva tunnistus epäonnistui. Yritä uudelleen.\");\r\n      throw error;\r\n    } finally {\r\n      loader.dismiss();\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Gets the payment channel configuration based on the current payment channel.\r\n   * @returns A configuration object containing row actions for invoice items.\r\n   * Currently only handles PaymentChannel.PalkkausManual channel.\r\n   * For PalkkausManual channel, returns an object with:\r\n   * - rowActions: Function that returns an array of actions available for an invoice item\r\n   * - For unread/read status: Adds \"Merkitse maksetuiksi\" (Mark as paid) action\r\n   * - For unread/read/paid status: Adds \"Peru lasku\" (Cancel invoice) action\r\n   * - Actions are cached by invoice ID and status\r\n   * Each action has:\r\n   * - text: Display text for the action\r\n   * - onClick: Handler function that shows confirmation dialog and updates invoice status\r\n   */\r\n  public getPaymentChannelConfig(): PaymentChannelConfig | null {\r\n    const changeInvoiceStatus = (invoiceIds: string[], status: InvoiceStatus): Promise<void> => {\r\n      const confirmHeading = status === InvoiceStatus.Canceled\r\n        ? \"Haluatko varmasti perua valitut laskut?\"\r\n        : \"Haluatko varmasti siirtää valitut laskut maksuun?\";\r\n      const loaderHeading = status === InvoiceStatus.Canceled\r\n        ? \"Perutaan laskuja... Tämä voi kestää hetken riippuen laskujen määrästä.\"\r\n        : \"Siirretään laskuja maksuun... Tämä voi kestää hetken riippuen laskujen määrästä.\";\r\n      return this.uiHelpers.showConfirm(\"Vahvistus\",confirmHeading).then((result) => {\r\n        if(result) {\r\n          const loader = this.uiHelpers.showLoading(loaderHeading);\r\n          return Promise.all(invoiceIds.map((id, index) => {\r\n            loader.setText(`${index}/${invoiceIds.length}`);\r\n            return (this.api as Invoices).requestStatusUpdate(id, status);\r\n          })).then(() => {\r\n            return this.uiHelpers.wait().then(() => {\r\n              this.selectedInvoices = [];\r\n              this.loadData(false, invoiceIds);\r\n              this.setPaymentChannelConfig();\r\n              loader.dismiss();\r\n            });\r\n          });\r\n        }\r\n      });\r\n    };\r\n    switch(this.paymentChannel) {\r\n      case PaymentChannel.Hausvise:\r\n        return {\r\n          hasExternalSystemMessagesEnabled: false,\r\n          rowActions: (item: InvoiceListItem): any[] => {\r\n            const cacheKey = `${item.id}-${item.status}`;\r\n            if (this.rowActionsCache[cacheKey]) {\r\n              return this.rowActionsCache[cacheKey];\r\n            }\r\n\r\n            const actions: {text: string, onClick: (invoice: InvoiceListItem) => Promise<void>}[] = [];\r\n            const markAsPaidStatuses = [InvoiceStatus.Unread, InvoiceStatus.Read];\r\n            const markAsCancelledStatuses = [InvoiceStatus.Unread, InvoiceStatus.Read, InvoiceStatus.Paid];\r\n            const invoiceMarkAsPaidAllowed = (invoice: InvoiceListItem): boolean => {\r\n              if(invoice.entityType === InvoiceType.Payroll) {\r\n                return false;\r\n              }\r\n              return true;\r\n            };\r\n            const invoiceCancellingAllowed = (invoice: InvoiceListItem): boolean => {\r\n              if(invoice.entityType === InvoiceType.Payroll) {\r\n                return false;\r\n              }\r\n              return true;\r\n            };\r\n            const updateStatus = (invoice: InvoiceListItem, newStatus: InvoiceStatus, confirmMessage: string) => {\r\n              return this.uiHelpers.showConfirm(\"HUOM\", confirmMessage).then((result) => {\r\n                if(result) {\r\n                  const loading = this.uiHelpers.showLoading(\"Päivitetään laskun tilaa...\");\r\n                  return (this.api as Invoices).requestStatusUpdate(invoice.id, newStatus).then(() => {\r\n                    return this.uiHelpers.wait().then(() => {\r\n                      this.loadData(false);\r\n                      loading.dismiss();\r\n                    });\r\n                  });\r\n                }\r\n              });\r\n            };\r\n\r\n            if(invoiceMarkAsPaidAllowed(item) && markAsPaidStatuses.includes(item.status)) {\r\n              actions.push({\r\n                text: \"Merkitse maksetuiksi\",\r\n                onClick: (invoice: InvoiceListItem) => {\r\n                  return updateStatus(invoice, InvoiceStatus.Paid, \"Merkitse maksetuksi vain, jos olet maksanut laskun muulla tavalla kuin Hausvisessa\");\r\n                }\r\n              });\r\n            }\r\n\r\n            if(invoiceCancellingAllowed(item) && markAsCancelledStatuses.includes(item.status)) {\r\n              actions.push({\r\n                text: \"Peru lasku\",\r\n                onClick: (invoice: InvoiceListItem) => {\r\n                  return updateStatus(invoice, InvoiceStatus.Canceled, \"Peru lasku vain, jos Hausvise ei poikkeuksellisesti pysty käsittelemään laskua\");\r\n                }\r\n              });\r\n            }\r\n\r\n            this.rowActionsCache[cacheKey] = actions;\r\n            return actions;\r\n          },\r\n          groupingFunction: (items: InvoiceListItem[]) => {\r\n            const result: GroupedItem[] = [];\r\n            items.forEach((item) => {\r\n              if(item.entityType === InvoiceType.Net || item.entityType === InvoiceType.Foreclosure || item.entityType === InvoiceType.Payroll) {\r\n                if(item.data.payrollId) {\r\n                  const payrollId = item.data.payrollId;\r\n                  let group = result.find((x) => x.id === payrollId);\r\n                  if(!group) {\r\n                    group = {\r\n                      id: payrollId,\r\n                      businessObjectId: payrollId,\r\n                      groupType: \"payroll\",\r\n                      title: item.data.payrollTitle,\r\n                      sortableDate: item.data.dueDate,\r\n                      invoices: [],\r\n                    };\r\n                    result.push(group);\r\n                  }\r\n                  group.invoices.push(item);\r\n                } else {\r\n                  let group = result.find((x) => x.id === item.businessObjects[0]);\r\n                  if(!group) {\r\n                    group = {\r\n                      id: item.businessObjects[0],\r\n                      businessObjectId: item.businessObjects[0],\r\n                      groupType: \"calculation\",\r\n                      title: \"Palkkalaskelma\",\r\n                      sortableDate: item.data.dueDate,\r\n                      invoices: []\r\n                    };\r\n                    result.push(group);\r\n                  }\r\n                  group.invoices.push(item);\r\n                }\r\n              }\r\n              if(item.entityType === InvoiceType.Tax || item.entityType === InvoiceType.Union || item.entityType === InvoiceType.Unemployment || item.entityType === InvoiceType.Pension) {\r\n                const id = Dates.getYear(item.logicalDate) + \"-\" + Dates.getMonth(item.logicalDate);\r\n                let group = result.find((x) => x.id === id);\r\n                if(!group) {\r\n                  group = {\r\n                    id: id,\r\n                    groupType: \"monthly\",\r\n                    title: `${Translations.get(`SALAXY.ENUM.CalendarMonth.month${Dates.getMonth(item.logicalDate)}.label`)} ${Dates.getYear(item.logicalDate)}`,\r\n                    sortableDate: item.data.dueDate,\r\n                    invoices: [],\r\n                  };\r\n                  result.push(group);\r\n                }\r\n                group.invoices.push(item);\r\n              }\r\n            });\r\n            result.filter(group => group.groupType === \"monthly\").forEach(group => {\r\n              group.invoices.sort((a, b) => a.data.dueDate.localeCompare(b.data.dueDate));\r\n            });\r\n            return result;\r\n          }\r\n        };\r\n      case PaymentChannel.PalkkausPSD: {\r\n        const handlePsdPayment = (invoiceIds: string) => {\r\n          const logic = {\r\n            banks: [\r\n              {\r\n                id: \"OSUUSPANKKI_MOCK\",\r\n                name: \"Osuuspankki Mock (hyväksyy maksut automaattisesti)\",\r\n                logo: \"https://cdn.salaxy.com/img/salaxy/sign/op.png\"\r\n              },   {\r\n                id: \"OSUUSPANKKI_TEST\",\r\n                name: \"Osuuspankki Test (tunnistautuminen)\",\r\n                logo: \"https://cdn.salaxy.com/img/salaxy/sign/op.png\"\r\n              },\r\n              {\r\n                id: \"NORDEA_MOCK\",\r\n                name: \"Nordea Test Mock (hyväksyy maksut automaattisesti)\",\r\n                logo: \"https://cdn.salaxy.com/img/salaxy/sign/nordea.png\"\r\n              },\r\n              {\r\n                id: \"NORDEA_TEST\",\r\n                name: \"Nordea Test (tunnistautuminen ei toimi, jää kesken)\",\r\n                logo: \"https://cdn.salaxy.com/img/salaxy/sign/nordea.png\"\r\n              },\r\n              {\r\n                id: \"NORDEA_PERSONAL_TEST\",\r\n                name: \"Nordea Personal Test (Hylkää maksut pankin puolelta)\",\r\n                logo: \"https://cdn.salaxy.com/img/salaxy/sign/nordea.png\"\r\n              },\r\n              {\r\n                id: \"INVALID_BANK_TEST\",\r\n                name: \"Invalid Bank (Tekninen virhe tapahtuu ja ruudulle tulee virhe)\",\r\n                logo: \"https://cdn.salaxy.com/img/salaxy/sign/invalid.png\"\r\n              }\r\n            ],\r\n            selectedBank: null,\r\n            selectBank: (bank: string) => {\r\n              logic.selectedBank = bank;\r\n            }\r\n          };\r\n          this.uiHelpers.openEditDialog(\"salaxy-components/modals/payment/psd/BankSelection.html\", null, logic).then((result) => {\r\n            if(result.action === \"ok\") {\r\n              const bank = result.logic.selectedBank;\r\n              const url = `${this.sepaAjax.getServerAddress()}/psdPayment/payInvoices?ids=${invoiceIds}&bank=${bank}&successurl=&access_token=${this.sepaAjax.getCurrentToken()}`;\r\n              const externalDialogLoader = this.uiHelpers.showLoading(\"Avataan pankkimaksua...\");\r\n              const hideExternalDialogLoader = () => {\r\n                externalDialogLoader.dismiss();\r\n              };\r\n              this.uiHelpers.showExternalDialog(\"psdDialog\", url, null, null, null, hideExternalDialogLoader).then((result) => {\r\n                const loader = this.uiHelpers.showLoading();\r\n                if (result.action == \"user-cancel\") {\r\n                  this.uiHelpers.showDialog(\"salaxy-components/modals/payment/PaymentCancel.html\").then(() => {\r\n                    this.uiHelpers.wait().then(() => {\r\n                      this.loadData(false);\r\n                      loader.dismiss();\r\n                    });\r\n                  });\r\n                } else if (result.action == \"ok\") {\r\n                  this.uiHelpers.showDialog(\"salaxy-components/modals/payment/PaymentConfirm.html\").then(() => {\r\n                    this.uiHelpers.wait().then(() => {\r\n                      this.loadData(false);\r\n                      loader.dismiss();\r\n                    });\r\n                  });\r\n                } else if (result.action == \"error\") {\r\n                  this.uiHelpers.showDialog(\"salaxy-components/modals/payment/PaymentError.html\").then(() => {\r\n                    this.uiHelpers.wait().then(() => {\r\n                      this.loadData(false);\r\n                      loader.dismiss();\r\n                    });\r\n                  });\r\n                }\r\n              });\r\n            }\r\n          });\r\n        };\r\n        return {\r\n          hasExternalSystemMessagesEnabled: true,\r\n          rowGroupActions: (group: GroupedItem): any[] => {\r\n            // Sort invoices by payment amount and store statuses\r\n            group.invoices.sort((a, b) => (b.payment ?? 0) - (a.payment ?? 0));\r\n            const cacheKey = `${group.id}-${group.businessObjectId}-${this.paymentChannel}-${group.invoices.map(i => i.status).join()}`;\r\n            if (this.rowGroupActionsCache[cacheKey]) {\r\n              return this.rowGroupActionsCache[cacheKey];\r\n            }\r\n\r\n            const actions: {text: string, onClick: (group: GroupedItem) => void}[] = [];\r\n            const hasPaidOrCanceledOrRead = group.invoices.some(invoice => invoice.status === InvoiceStatus.Paid || invoice.status === InvoiceStatus.Canceled || invoice.status === InvoiceStatus.Read);\r\n            if (!hasPaidOrCanceledOrRead) {\r\n              actions.push({\r\n                text: \"Maksa laskuryhmä\",\r\n                onClick: (group: GroupedItem) => {\r\n                  return handlePsdPayment(group.invoices.map((x) => x.id).join(\",\"));\r\n                }\r\n              });\r\n              actions.push({\r\n                text: \"Peru laskuryhmä\",\r\n                onClick: (group: GroupedItem) => {\r\n                  return changeInvoiceStatus(group.invoices.map((x) => x.id), InvoiceStatus.Canceled);\r\n                }\r\n              });\r\n            }\r\n            this.rowGroupActionsCache[cacheKey] = actions;\r\n            return actions;\r\n          },\r\n          groupingFunction: (items: InvoiceListItem[]) => {\r\n            const result: GroupedItem[] = [];\r\n            items.forEach((item) => {\r\n              if(item.entityType === InvoiceType.Net || item.entityType === InvoiceType.Foreclosure || item.entityType === InvoiceType.Union || item.entityType === InvoiceType.Tax || item.entityType === InvoiceType.Payroll) {\r\n                if(item.data.payrollId) {\r\n                  const payrollId = item.data.payrollId;\r\n                  let group = result.find((x) => x.id === payrollId);\r\n                  if(!group) {\r\n                    group = {\r\n                      id: payrollId,\r\n                      businessObjectId: payrollId,\r\n                      groupType: \"payroll\",\r\n                      title: item.data.payrollTitle,\r\n                      sortableDate: item.data.dueDate,\r\n                      invoices: [],\r\n                    };\r\n                    result.push(group);\r\n                  }\r\n                  group.invoices.push(item);\r\n                } else {\r\n                  let group = result.find((x) => x.id === item.businessObjects[0]);\r\n                  if(!group) {\r\n                    group = {\r\n                      id: item.businessObjects[0],\r\n                      businessObjectId: item.businessObjects[0],\r\n                      groupType: \"calculation\",\r\n                      title: \"Palkkalaskelma\",\r\n                      sortableDate: item.data.dueDate,\r\n                      invoices: []\r\n                    };\r\n                    result.push(group);\r\n                  }\r\n                  group.invoices.push(item);\r\n                }\r\n              }\r\n              if(item.entityType === InvoiceType.Unemployment || item.entityType === InvoiceType.Pension) {\r\n                const id = Dates.getYear(item.logicalDate) + \"-\" + Dates.getMonth(item.logicalDate);\r\n                let group = result.find((x) => x.id === id);\r\n                if(!group) {\r\n                  group = {\r\n                    id: id,\r\n                    groupType: \"monthly\",\r\n                    title: `${Translations.get(`SALAXY.ENUM.CalendarMonth.month${Dates.getMonth(item.logicalDate)}.label`)} ${Dates.getYear(item.logicalDate)}`,\r\n                    sortableDate: item.data.dueDate,\r\n                    invoices: [],\r\n                  };\r\n                  result.push(group);\r\n                }\r\n                group.invoices.push(item);\r\n              }\r\n            });\r\n            result.filter(group => group.groupType === \"monthly\").forEach(group => {\r\n              group.invoices.sort((a, b) => a.data.dueDate.localeCompare(b.data.dueDate));\r\n            });\r\n            return result;\r\n          }\r\n        };\r\n      }\r\n      case PaymentChannel.PalkkausWS: {\r\n        return {\r\n          hasExternalSystemMessagesEnabled: true,\r\n          multiSelectAction: () => {\r\n            return {\r\n              text: \"Siirrä valitut laskut maksuun\",\r\n              onClick: () => {\r\n                return changeInvoiceStatus(this.selectedInvoices.map((x) => x.id), InvoiceStatus.Unread);\r\n              }\r\n            };\r\n          },\r\n          rowActions: (item: InvoiceListItem): any[] => {\r\n            const cacheKey = `${item.id}-${item.status}-${this.paymentChannel}-${this.isStronglyAuthorizedPayer()}`;\r\n            if (this.rowActionsCache[cacheKey]) {\r\n              return this.rowActionsCache[cacheKey];\r\n            }\r\n\r\n            const actions: {text: string, onClick: (invoice: InvoiceListItem) => void}[] = [];\r\n            if(this.isStronglyAuthorizedPayer()) {\r\n              if(item.status === InvoiceStatus.WaitingConfirmation) {\r\n                actions.push({\r\n                  text: \"Siirrä maksuun\",\r\n                  onClick: (invoice: InvoiceListItem) => {\r\n                    return changeInvoiceStatus([invoice.id], InvoiceStatus.Unread);\r\n                  }\r\n                });\r\n              }\r\n              if(item.status !== InvoiceStatus.Canceled) {\r\n                actions.push({\r\n                  text: \"Peru lasku\",\r\n                  onClick: (invoice: InvoiceListItem) => {\r\n                    return changeInvoiceStatus([invoice.id], InvoiceStatus.Canceled);\r\n                  }\r\n                });\r\n              }\r\n              if(item.status === InvoiceStatus.Read) {\r\n                actions.push({\r\n                  text: \"Merkitse maksetuksi\",\r\n                  onClick: (invoice: InvoiceListItem) => {\r\n                    return changeInvoiceStatus([invoice.id], InvoiceStatus.Paid);\r\n                  }\r\n                });\r\n              }\r\n            }\r\n            this.rowActionsCache[cacheKey] = actions;\r\n            return actions;\r\n          },\r\n          groupingFunction: (items: InvoiceListItem[]) => {\r\n            const result: GroupedItem[] = [];\r\n            items.forEach((item) => {\r\n              if(item.entityType === InvoiceType.Net || item.entityType === InvoiceType.Foreclosure) {\r\n                if(item.data.payrollId) {\r\n                  const payrollId = item.data.payrollId;\r\n                  let group = result.find((x) => x.id === payrollId);\r\n                  if(!group) {\r\n                    group = {\r\n                      id: payrollId,\r\n                      businessObjectId: payrollId,\r\n                      groupType: \"payroll\",\r\n                      title: item.data.payrollTitle,\r\n                      sortableDate: item.data.dueDate,\r\n                      invoices: [],\r\n                    };\r\n                    result.push(group);\r\n                  }\r\n                  group.invoices.push(item);\r\n                } else {\r\n                  result.push(\r\n                    {\r\n                      id: item.id,\r\n                      businessObjectId: item.businessObjects[0],\r\n                      groupType: \"calculation\",\r\n                      title: \"Palkkalaskelma\",\r\n                      sortableDate: item.data.dueDate,\r\n                      invoices: [item],\r\n                    }\r\n                  );\r\n                }\r\n              }\r\n              if(item.entityType === InvoiceType.Tax || item.entityType === InvoiceType.Union || item.entityType === InvoiceType.Unemployment || item.entityType === InvoiceType.Pension) {\r\n                const id = Dates.getYear(item.logicalDate) + \"-\" + Dates.getMonth(item.logicalDate);\r\n                let group = result.find((x) => x.id === id);\r\n                if(!group) {\r\n                  group = {\r\n                    id: id,\r\n                    groupType: \"monthly\",\r\n                    title: `${Translations.get(`SALAXY.ENUM.CalendarMonth.month${Dates.getMonth(item.logicalDate)}.label`)} ${Dates.getYear(item.logicalDate)}`,\r\n                    sortableDate: item.data.dueDate,\r\n                    invoices: [],\r\n                  };\r\n                  result.push(group);\r\n                }\r\n                group.invoices.push(item);\r\n              }\r\n            });\r\n            result.filter(group => group.groupType === \"monthly\").forEach(group => {\r\n              group.invoices.sort((a, b) => a.data.dueDate.localeCompare(b.data.dueDate));\r\n            });\r\n            return result;\r\n          }\r\n        };\r\n      }\r\n        default:\r\n        return null;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Returns the CSS class for a given VismaPay status.\r\n   * These statuses are from VismaPay.\r\n   * @param status The VismaPay status string.\r\n   * @returns The corresponding badge CSS class.\r\n   * TODO: More later to config if more statuses are needed.\r\n   */\r\n  public getBadgeClass(status: string) {\r\n    status = (status ?? \"\").split(\"\\r\\n\")[0];\r\n    switch(status) {\r\n      case \"SCA_REQUIRED\":\r\n      case \"UNAVAILABLE\":\r\n      case \"FAILED\":\r\n      case \"CANCEL_FAILED\":\r\n      case \"CANCELLED\":\r\n        return \"badge bg-danger\";\r\n      case \"SUCCEEDED\":\r\n        return \"badge bg-success\";\r\n      case \"PENDING\":\r\n      case \"WAITING_FOR_PROCESSING\":\r\n      case \"FORWARDED\":\r\n      case \"CANCEL_PENDING\":\r\n        return \"badge bg-warning\";\r\n      default:\r\n        return \"badge bg-info\";\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Gets the grouped invoice items filtered and sorted based on the current tab.\r\n   * @returns An array of grouped invoice items, filtered and sorted by date.\r\n   * For the \"netpaymentsandforeclosure\" tab, returns only net payments and foreclosures.\r\n   * For the \"monthlypayments\" tab, returns only monthly payments like tax, union etc.\r\n   * Returns empty array if no grouped items exist or for unknown tabs.\r\n   */\r\n  public getGroupedItems() {\r\n    if (!this.groupedItems) {\r\n      return [];\r\n    }\r\n\r\n    const sortByDate = (a: any, b: any) => {\r\n      const sortMultiplier = this.sortMode === \"asc\" ? 1 : -1;\r\n      return sortMultiplier * a.sortableDate.localeCompare(b.sortableDate);\r\n    };\r\n    switch (this.currentTab) {\r\n      case \"netpaymentsandforeclosure\":\r\n        return this.groupedItems\r\n          .filter(x => x.groupType === \"payroll\" || x.groupType === \"calculation\")\r\n          .sort(sortByDate);\r\n\r\n      case \"monthlypayments\":\r\n        return this.groupedItems\r\n          .filter(x => x.groupType === \"monthly\")\r\n          .sort(sortByDate);\r\n\r\n      default:\r\n        return [];\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Toggles the sort mode between ascending and descending.\r\n   * This affects the order of grouped items when displayed.\r\n   */\r\n  public changeSortMode() {\r\n    this.sortMode = this.sortMode === \"asc\" ? \"desc\" : \"asc\";\r\n  }\r\n\r\n  /**\r\n   * Updates the grouped items based on the provided invoice list items.\r\n   * Groups net payments and foreclosures by payroll or calculation.\r\n   * Groups monthly payments (tax, union, unemployment, pension) by month.\r\n   * @param items List of invoice items to group\r\n   */\r\n  public updategroupedItems(items: InvoiceListItem[], updateSpecificInvoices: boolean = false) {\r\n    if(updateSpecificInvoices) {\r\n      // Efficiently update only the invoices that are present in the updated items list\r\n      const updatedInvoicesMap = new Map(items.map(item => [item.id, item]));\r\n      this.groupedItems.forEach(group => {\r\n        group.invoices = group.invoices.map(invoice => updatedInvoicesMap.get(invoice.id) || invoice);\r\n      });\r\n    } else {\r\n      this.groupedItems = [];\r\n      this.groupedItems = this.paymentChannelConfig?.groupingFunction(items) ?? [];\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Loads all invoices from the server.\r\n   * @returns Promise of all invoices\r\n   */\r\n  public async loadAllInvoices(idsToUpdate: string[] | null = null): Promise<InvoiceListItem[]> {\r\n    let items: any[] = [];\r\n    const loadItems = (nextPageLink: string = null): Promise<string> => {\r\n      let options: ODataQueryOptions = {$filter: `data/channel eq '${this.paymentChannel}' and endAt ge ${Dates.getYear(this.queryYear)}-01-01 and endAt le ${Dates.getYear(this.queryYear)}-12-31`, $orderby: \"id\"};\r\n      const queryString = nextPageLink?.indexOf(\"?\") ?? -1;\r\n      if (queryString >= 0) {\r\n        const searchParams = new URLSearchParams(nextPageLink.substr(queryString));\r\n        if (searchParams.get(\"$skip\")) {\r\n          options = { $skip:  Number(searchParams.get(\"$skip\")), $filter: `data/channel eq '${this.paymentChannel}' and endAt ge ${Dates.getYear(this.queryYear)}-01-01 and endAt le ${Dates.getYear(this.queryYear)}-12-31`, $orderby: \"id\"};\r\n        }\r\n      }\r\n      return this.invoicesApi.getOData(options).then((data) => {\r\n        items.push(...data.items);\r\n        return data.nextPageLink ? loadItems(data.nextPageLink) : null;\r\n      });\r\n    };\r\n\r\n    return loadItems().then(() => {\r\n      if(idsToUpdate) {\r\n        items = items.filter(item => idsToUpdate.includes(item.id));\r\n      }\r\n      return Arrays.distinct(items, (item) => item.id).sort((a, b) => a.endAt > b.endAt ? -1 : 1);\r\n    });\r\n  }\r\n\r\n  /** Filter function for angularjs filter used in template */\r\n  public filterInvoices = (invoice: InvoiceListItem) => {\r\n    // Filter by invoice entity type\r\n    if (this.invoiceEntityType.value !== \"all\" && invoice.entityType !== this.invoiceEntityType.value) {\r\n      return false;\r\n    }\r\n\r\n    // Filter by status\r\n    if (this.statusFilter.value !== \"all\" && invoice.status !== this.statusFilter.value) {\r\n      return false;\r\n    }\r\n\r\n    // Filter by other party name\r\n    if (this.otherPartyNameFilter &&\r\n        !invoice.otherPartyInfo?.avatar?.displayName?.toLowerCase().includes(this.otherPartyNameFilter.toLowerCase())) {\r\n      return false;\r\n    }\r\n\r\n    // Filter by reference\r\n    if (this.referenceFilter &&\r\n        !invoice.reference?.toLowerCase().includes(this.referenceFilter.toLowerCase())) {\r\n      return false;\r\n    }\r\n\r\n    // Filter by IBAN\r\n    if (this.ibanFilter &&\r\n        !invoice.otherPartyInfo?.ibanNumber?.toLowerCase().includes(this.ibanFilter.toLowerCase())) {\r\n      return false;\r\n    }\r\n\r\n    return true;\r\n  };\r\n\r\n  /**\r\n   * Shows a dialog for a single invoice.\r\n   * @param item Invoice item.\r\n   */\r\n  public showInvoiceDialog(item: InvoiceListItem) {\r\n    this.uiHelpers.openEditDialog(\"salaxy-components/modals/invoices/invoice-payment-list-dialog.html\", item, { parent: this }, \"lg\");\r\n  }\r\n\r\n  /**\r\n   * Returns PDF url for a single invoice.\r\n   * @param item Invoice list item.\r\n   */\r\n   public getPdfUrl(item: InvoiceListItem): string {\r\n    if (!(item as any).pdfUrl) {\r\n        (item as any).pdfUrl = (this.api as Invoices).getContentUrl(item.id, false);\r\n    }\r\n    return (item as any).pdfUrl;\r\n  }\r\n\r\n  /**\r\n   * Retrieves the QR code for the specified invoice item.\r\n   * If the QR code is not already cached, it generates the QR code and caches it for future use.\r\n   * @param item - The invoice item for which to retrieve the QR code.\r\n   * @returns The QR code string.\r\n   */\r\n  public getQrCode(item: InvoiceListItem): string {\r\n    if(!this.qrCodesCache[item.id]) {\r\n      this.qrCodesCache[item.id] = \"loading\";\r\n      this.generateQrCodeSvgForInvoice(item).then((qrCode) => {\r\n        if(!qrCode) {\r\n          this.qrCodesCache[item.id] = \"error\";\r\n          this.$timeout();\r\n          return this.qrCodesCache[item.id];\r\n        } else {\r\n          this.qrCodesCache[item.id] = qrCode;\r\n          this.$timeout();\r\n          return this.$sce.trustAsHtml(this.qrCodesCache[item.id]);\r\n        }\r\n      });\r\n    }\r\n    if(this.qrCodesCache[item.id] === \"error\") {\r\n      return this.qrCodesCache[item.id];\r\n    }\r\n    return this.$sce.trustAsHtml(this.qrCodesCache[item.id]);\r\n  }\r\n\r\n  /**\r\n   * Calculates barcode value for the invoice item.\r\n   * @param item Invoice list item.\r\n   */\r\n  public getBarcodeValue(item: InvoiceListItem): string {\r\n    return Barcodes.getValue(\r\n      item.otherPartyInfo.ibanNumber || \"\",\r\n      (item as any).reference || \"\",\r\n      Dates.asDate(item.data.dueDate),\r\n      Numeric.round(item.payment * 100, 0));\r\n  }\r\n\r\n  /**\r\n   * Retrieves the barcode for the invoice recipient's IBAN.\r\n   * If the IBAN does not start with \"fi\" or is not provided, an empty string is returned.\r\n   * The barcode is generated using the Barcodes.createBarcode function.\r\n   * @returns The barcode as a string, wrapped in an HTML trust object.\r\n   */\r\n  public getBarcode(item: InvoiceListItem): string {\r\n    if (!item.otherPartyInfo.ibanNumber || !item.otherPartyInfo.ibanNumber.toLowerCase().trim().startsWith(\"fi\")) {\r\n      return \"\";\r\n    }\r\n    const getDocumentAndSvgNode = () => {\r\n      return {document, svgNode: document.createElementNS(\"http://www.w3.org/2000/svg\", \"svg\")};\r\n    };\r\n\r\n    const result = Barcodes.createBarcode(\r\n      getDocumentAndSvgNode,\r\n      item.otherPartyInfo.ibanNumber || \"\",\r\n      (item as any).reference || \"\",\r\n      Dates.asDate(item.data.dueDate),\r\n      Numeric.round(item.payment * 100, 0),\r\n      {\r\n        width: 1.8,\r\n        height: 32,\r\n        displayValue: true,\r\n        fontSize: 15\r\n      }\r\n    );\r\n    if(!result) {\r\n      return \"\";\r\n    }\r\n    return this.$sce.trustAsHtml(new XMLSerializer().serializeToString(result as any));\r\n  }\r\n\r\n  /** Hides bar code for forecast and preview invoice statuses*/\r\n  public hideBarCode(item: InvoiceListItem): boolean {\r\n    if(item.status === InvoiceStatus.Forecast || item.status === InvoiceStatus.Preview) {\r\n      return true;\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /**\r\n   * Copies the barcode to clipboard.\r\n   * @param item Invoice list item.\r\n   */\r\n  public copyBarcode(item: InvoiceListItem) {\r\n    (navigator as any).clipboard.writeText(this.getBarcodeValue(item));\r\n  }\r\n\r\n  /** Gets and avatar image for a payment channel */\r\n  public getChannelAvatar(channel: PaymentChannel) {\r\n    return InvoicesLogic.getChannelAvatar(channel);\r\n  }\r\n\r\n  /** Data reader for one item. */\r\n  public getGroupItemDataReader = (item: InvoiceListItem, status: InvoiceStatus, fileTypeId = null) => {\r\n    return {\r\n      /** Function to read data into given array */\r\n      read: (arr: Invoice[], message: string): Promise<void> => {\r\n        const showConfirmation = (): Promise<boolean> => {\r\n          const warning = this.getEprWarning([item], status);\r\n          if (warning) {\r\n            return this.uiHelpers.showConfirm(\"Huomioi palkkatietoilmoitukset!\", warning);\r\n          }\r\n          return Promise.resolve(true);\r\n        };\r\n        return showConfirmation().then((result) => {\r\n          if (result) {\r\n            (item as any)[\"isReading\" + (status || \"\")] = true;\r\n            return this.getInvoice(item, message, status).then((data) => {\r\n              if (data) {\r\n                arr.push(data);\r\n              }\r\n              (item as any)[\"isReading\" + (status || \"\")] = false;\r\n              return;\r\n            });\r\n          } else {\r\n            return;\r\n          }\r\n        });\r\n      },\r\n      getSepaData: (\r\n        /** Array for invoices */\r\n        arr: Invoice[],\r\n      ): Promise<string> => this.getSepaData(arr, null, fileTypeId),\r\n      getFinvoiceData: (\r\n        /** Array for invoices */\r\n        arr: Invoice[],\r\n      ): Promise<Blob[]> => this.getFinvoiceData(arr),\r\n      getPdfData: (\r\n        /** Array for invoices */\r\n        arr: Invoice[],\r\n      ): Promise<Blob[]> => this.getPdfData(arr),\r\n      /** Optional label for data export */\r\n      exportLabel: null,\r\n      /** Indicates if the export is not possible */\r\n      disabled: () => false,\r\n    };\r\n  };\r\n\r\n  private getInvoice(item: InvoiceListItem, message: any, status: InvoiceStatus = null): Promise<Invoice> {\r\n\r\n    const updateInvoiceStatus = (invoice: Invoice, status: InvoiceStatus): Promise<Invoice> => {\r\n      if (invoice.header.status === status) {\r\n        return Promise.resolve(invoice);\r\n      }\r\n      return (this.api as Invoices).requestStatusUpdate(item.id, status);\r\n    };\r\n\r\n    return this.api.getSingle(item.id)\r\n      .then((readInvoice: Invoice) => {\r\n        if (status) {\r\n          return updateInvoiceStatus(readInvoice, status).then((updatedInvoice) => {\r\n            item.status = updatedInvoice.header.status;\r\n            return updatedInvoice;\r\n          });\r\n        } else {\r\n          return readInvoice;\r\n        }\r\n      });\r\n  }\r\n\r\n  private async getPdfData(invoices: Invoice[]): Promise<Blob[]> {\r\n    const blobs: Blob[] = [];\r\n    const loader = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.loading\");\r\n    for (const [index, invoice] of invoices.entries()) {\r\n      const blob = await this.download(\"/v03/api/invoices/content\", invoice, \"blob\");\r\n      loader.setText(`${index}/${invoices.length}`);\r\n      blobs.push(blob);\r\n    }\r\n    loader.dismiss();\r\n    return blobs;\r\n  }\r\n\r\n  private async getFinvoiceData(invoices: Invoice[]): Promise<Blob[]> {\r\n    const blobs: Blob[] = [];\r\n    const loader = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.loading\");\r\n    for (const [index, invoice] of invoices.entries()) {\r\n      const blob = await this.download(\"/v03/api/invoices/finvoice\", invoice, \"blob\");\r\n      loader.setText(`${index}/${invoices.length}`);\r\n      blobs.push(blob);\r\n    }\r\n    loader.dismiss();\r\n    return blobs;\r\n  }\r\n\r\n  private getSepaData(invoices: Invoice[], payerIbanNumber: string = null, fileTypeId: string = null): Promise<string> {\r\n    const version = fileTypeId === \"sepaFileV03\" || fileTypeId === \"sepaCopyV03\" ? \"pain.001.001.03\" : \"pain.001.001.02\";\r\n    const method = `/v03/api/invoices/sepa?version=${version}${payerIbanNumber ? \"&payerIbanNumber=\" + encodeURIComponent(payerIbanNumber) : \"\"}`;\r\n    return this.download(method, invoices, \"text\");\r\n  }\r\n  private download(method: string, data: any, responseType: string): Promise<any> {\r\n\r\n    const request: any = {}; // angular.IRequestConfig\r\n\r\n    const token: string = this.sepaAjax.getCurrentToken();\r\n    if (token) {\r\n      request.headers = { Authorization: \"Bearer \" + token };\r\n    }\r\n\r\n    request.url = this.sepaAjax.getServerAddress() + method;\r\n    request.method = \"POST\";\r\n    request.data = data;\r\n    request.responseType = responseType;\r\n    request.withCredentials = (token) ? false : this.sepaAjax.useCredentials;\r\n\r\n    return (this.$http(request).then(\r\n      (response) => response.data,\r\n      (error: any) => {\r\n        return null;\r\n      }) as any\r\n    );\r\n  }\r\n\r\n  private getEprWarning(items: InvoiceListItem[], status: InvoiceStatus): string {\r\n    const isDelayed = (salaryDate?: string): boolean => {\r\n      if (this.session.isInRole(SystemRole.Test)) {\r\n        const officialDate = Dates.add((salaryDate ?? \"today\"),5, \"day\");\r\n        const expiresAt = Dates.addWorkdays(officialDate, 0);\r\n        const today = Dates.asDate(\"today\");\r\n        return today>expiresAt;\r\n      }\r\n      return false;\r\n    };\r\n    if (status === InvoiceStatus.Canceled) {\r\n      for (const item of items) {\r\n        if (item.status === InvoiceStatus.Paid &&\r\n          item.entityType == InvoiceType.Net &&\r\n          isDelayed(item.logicalDate)) {\r\n          return \"Palkanmaksusta tehdyt tulorekisteri-ilmoitukset perutaan automaattisesti.\\n\\nJos maksat palkan uudestaan samalle palkkapäivälle, ota huomioon, että uudesta palkkatietoilmoituksesta saattaa seurata myöhästymismaksu. Haluatko varmasti perua maksut?\";\r\n        }\r\n      }\r\n    } else if (status === InvoiceStatus.Paid) {\r\n      for (const item of items) {\r\n        if (item.status !== InvoiceStatus.Paid &&\r\n          item.entityType == InvoiceType.Net &&\r\n          isDelayed(item.logicalDate)) {\r\n          return \"Annetulle palkkapäivälle tehtävä palkkatietoilmoitus myöhästyy, koska ilmoitus pitää tehdä 5 päivän kuluessa palkkapäivästä. Ota huomioon, että tästä saattaa seurata myöhästymismaksu. Haluatko varmasti merkitä palkan maksetuiksi?\";\r\n        }\r\n      }\r\n    }\r\n    return null;\r\n  }\r\n\r\n  private async generateQrCodeSvgForInvoice(item: InvoiceListItem): Promise<string> {\r\n    const svg = await QrCodes.getValue(\r\n     BicHelper.getBicForIban(item.otherPartyInfo.ibanNumber.replace(/\\s+/g, \"\")),\r\n     item.otherPartyInfo.avatar.displayName,\r\n     item.otherPartyInfo?.ibanNumber,\r\n     item.reference,\r\n     null,\r\n     item.payment,\r\n     item.endAt\r\n   );\r\n   return svg;\r\n }\r\n}\r\n","import angular from \"angular\";\r\nimport {\r\n  Ajax, Calculation, Calculations, Configs, InputEnumOption,\r\n  Invoice, Invoices, InvoicesLogic, InvoicePreview, InvoiceStatus, InvoiceType,\r\n  PaymentChannel, PayrollDetails, PayrollStatus, InvoicePaymentType, SalaryDateKind, Translations, CalculationListItem, PayrollListItem, Payrolls4\r\n} from \"@salaxy/core\";\r\n\r\nimport { InvoicesService, SessionService, UiHelpers } from \"../../services\";\r\nimport { ApiCrudObjectController } from \"../bases\";\r\nimport { CalculationCrudController, PayrollCrudController } from \"../calc\";\r\nimport { } from \"../../components\";\r\n\r\n/**\r\n * Controller for the new Payment button and other functionality:\r\n * Creating (recreating) Invoices based on Calculations and Payrolls.\r\n */\r\nexport class InvoicesCreateController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Invoices\", \"InvoicesService\", \"Calculations\", \"SessionService\", \"UiHelpers\", \"$location\", \"AjaxNg1\"];\r\n\r\n  /**\r\n   * Defines the binding mode of the component.\r\n   * Currently, only \"model\" is supported (Calculation or PayrollDetails),\r\n   * but we might support e.g. id in the future.\r\n   */\r\n  public bindingMode: \"model\" | \"null\";\r\n\r\n  /**\r\n   * Collection of invoices if the channel and model have been set.\r\n   * Null if the collection is being fetched.\r\n   */\r\n  public invoices: InvoicePreview[] = [];\r\n\r\n  /** User canceled the process. */\r\n  public userCanceled = false;\r\n\r\n  private _current: Calculation | PayrollDetails;\r\n\r\n  private _model: any;\r\n\r\n  private _primaryCalcNetInvoicePreview: InvoicePreview = null;\r\n\r\n  private _primaryCalcTaxInvoicePreview: InvoicePreview = null;\r\n\r\n  constructor(\r\n    private invoicesApi: Invoices,\r\n    private invoicesService: InvoicesService,\r\n    private calculationsApi: Calculations,\r\n    private sessionService: SessionService,\r\n    protected uiHelpers: UiHelpers,\r\n    private $location: angular.ILocationService,\r\n    private ajax: Ajax,\r\n  ) {\r\n  }\r\n\r\n  /**\r\n   * Implement IController by providing onInit method.\r\n   * We currently do nothing here, but if you override this function,\r\n   * you should call this method in base class for future compatibility.\r\n   */\r\n  public $onInit() {\r\n    this.bindingMode = this.bindingMode || \"null\";\r\n  }\r\n\r\n  /**\r\n   * Set the Current selected item (the model).\r\n   * Currently, only Calculation or PayrollDetails is supported,\r\n   * but we will probably support controller and url in the future.\r\n   */\r\n  public set model(value: Calculation | PayrollDetails | \"url\" | string | ApiCrudObjectController<Calculation, CalculationListItem> | ApiCrudObjectController<PayrollDetails, PayrollListItem>) {\r\n    this._model = value;\r\n    if (InvoicesLogic.isCalculation(value) || InvoicesLogic.isPayroll(value)) {\r\n      this._current = value;\r\n      this.bindingMode = \"model\";\r\n    } else {\r\n      throw new Error(\"Not implemented: Only Calculation or PayrollDetails is currently supported.\");\r\n    }\r\n    this.reload();\r\n  }\r\n  /** Gets the Current selected item (the model). */\r\n  public get model(): Calculation | PayrollDetails | \"url\" | string | ApiCrudObjectController<Calculation, CalculationListItem> | ApiCrudObjectController<PayrollDetails, PayrollListItem> {\r\n    return this._model;\r\n  }\r\n\r\n  /** Changes the channel */\r\n  public set channel(value: PaymentChannel) {\r\n    if (InvoicesLogic.isCalculation(this.current)) {\r\n      this.current.info.paymentChannel = value;\r\n    } else {\r\n      this.current.input.paymentChannel = value;\r\n    }\r\n    this.reload();\r\n  }\r\n  /** The current payment channel for user interface purposes. */\r\n  public get channel(): PaymentChannel {\r\n    if (!this.current) {\r\n      return null;\r\n    }\r\n    const channel = InvoicesLogic.isCalculation(this.current)\r\n      ? this.current.info.paymentChannel\r\n      : this.current.input.paymentChannel;\r\n    return channel || this.invoicesService.defaultChannel;\r\n  }\r\n\r\n  /** Gets the enabled channels. */\r\n  public get allChannels() {\r\n    return this.invoicesService.channelEnumOptions;\r\n  }\r\n\r\n  /** Gets the text for the Primary submit button. Null for hiding the button. */\r\n  public getOkBtn(): string {\r\n    if (this.userCanceled) {\r\n      return null;\r\n    }\r\n    if (!this.isValid) {\r\n      return null;\r\n    }\r\n    switch (this.paymentStatus) {\r\n\r\n      case \"paid\":\r\n      case \"exceptions\":\r\n      case \"canceled\":\r\n      case \"unknown\":\r\n        return null;\r\n      case \"preview\":\r\n        if (InvoicesLogic.isPalkkausManualLike(this.channel) && this.salaryDateKind == SalaryDateKind.InPast) {\r\n          return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.createAndMarkPaid\");\r\n        }\r\n        if (InvoicesLogic.isPalkkausManualLike(this.channel) || this.channel === PaymentChannel.PalkkausWS || this.channel === PaymentChannel.FinagoSolo || this.channel === PaymentChannel.AccountorGo) {\r\n          // for Accountor Go service users\r\n          if(this.sessionService.isInRole(\"accountorService\")){\r\n            return null;\r\n          }\r\n          return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.createPayments\");\r\n        }\r\n        if (InvoicesLogic.isPalkkausInvoicesLike(this.channel)) {\r\n          return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.createInvoices\");\r\n        }\r\n        if (this.channel === PaymentChannel.Hausvise) {\r\n          return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.createPaymentMaterial\");\r\n        }\r\n        return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.sendForPayment\");\r\n      case \"inProgress\":\r\n        if (this.channel === PaymentChannel.Procountor || this.channel === PaymentChannel.VismaNetvisor || this.channel === PaymentChannel.Test) {\r\n          return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.checkPayment\");\r\n        }\r\n        return null;\r\n      default:\r\n        if (!this.channel || this.channel === PaymentChannel.Undefined) {\r\n          return null;\r\n        }\r\n        if (InvoicesLogic.isPalkkausInvoicesLike(this.channel)) {\r\n          return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.createInvoices\");\r\n        }\r\n        if (this.channel === PaymentChannel.Hausvise) {\r\n          return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.createPaymentMaterial\");\r\n        }\r\n        return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.sendForPayment\");\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Intro text for the dialog.\r\n   */\r\n  public get intro(): string {\r\n    if (InvoicesLogic.isPalkkausManualLike(this.channel)) {\r\n      return this.salaryDateKind == SalaryDateKind.InPast ?\r\n        Translations.get(`SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.palkkausManualAndFixed.intro`) :\r\n        Translations.get(`SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.palkkausManual.intro`);\r\n    }\r\n    return Translations.get(`SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.${this.channel}.intro`);\r\n  }\r\n  /** Title for the dialog */\r\n  public get title(): string {\r\n    switch (this.channel) {\r\n      case PaymentChannel.PalkkausManual:\r\n      case PaymentChannel.TalenomManual:\r\n        return this.salaryDateKind == SalaryDateKind.InPast ?\r\n          Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.palkkausManualAndFixed.heading\") :\r\n          Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.palkkausManual.heading\");\r\n      case PaymentChannel.PalkkausWS:\r\n        return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.palkkausWS.heading\");\r\n      case PaymentChannel.PalkkausInvoices:\r\n        return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.palkkausInvoices.heading\");\r\n      case PaymentChannel.Kitsas:\r\n        return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.kitsas.heading\");\r\n      case PaymentChannel.FinagoSolo:\r\n        return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.finagoSolo.heading\");\r\n      case PaymentChannel.AccountorGo:\r\n        return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.accountorGo.heading\");\r\n      case PaymentChannel.Askelma:\r\n        return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.askelma.heading\");\r\n      case PaymentChannel.Briox:\r\n        return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.briox.heading\");\r\n      case PaymentChannel.Lemonaid:\r\n        return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.lemonaid.heading\");\r\n      case PaymentChannel.Laskupiste:\r\n        return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.laskupiste.heading\");\r\n      case PaymentChannel.PasseliMerit:\r\n        return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.passeliMerit.heading\");\r\n      case PaymentChannel.Odoo:\r\n        return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.odoo.heading\");\r\n      case PaymentChannel.Hausvise:\r\n        return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.hausvise.heading\");\r\n      case PaymentChannel.Ecom:\r\n        return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.ecom.heading\");\r\n      case PaymentChannel.Kompassi:\r\n        return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.kompassi.heading\");\r\n      case PaymentChannel.Domus:\r\n        return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.domus.heading\");\r\n      case PaymentChannel.Holvi:\r\n        return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.holvi.heading\");\r\n      case PaymentChannel.TalenomOnline:\r\n        return Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.talenomOnline.heading\");\r\n      case PaymentChannel.PalkkausPersonal:\r\n      default:\r\n        return Translations.get(\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.loadingPayment\");\r\n    }\r\n  }\r\n\r\n  /** Gets the Current selected item. */\r\n  public get current(): Calculation | PayrollDetails {\r\n    return this._current;\r\n  }\r\n\r\n  /**\r\n   * Returns true if the invoices have been created => the payment process has been started.\r\n   * It may have been completed (paid), canceled or rejected.\r\n   */\r\n  public get isStarted(): boolean {\r\n    if (InvoicesLogic.isPayroll(this.current) && this.current.info.status !== PayrollStatus.Draft) {\r\n      return true;\r\n    } else if (InvoicesLogic.isCalculation(this.current) && this.current.isReadOnly) {\r\n      return true;\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /**\r\n   * Gets the payment status of the invoices.\r\n   *\r\n   * - unknown: The invoices have not been loaded from the server yet.\r\n   * - preview: The invoices have not yet been created\r\n   * - inProgress: Any of the invoices is in progress (WaitingPalkkaus,Unread, Read, WaitingConfirmation, PaymentStarted)\r\n   * OR some invoices have been paid, some not (default state).\r\n   * - canceled: One of the invoices is canceled.\r\n   * - exceptions: Any of the invoices have exceptions (Undefined, Error)\r\n   * - paid: All the invoices have been paid\r\n   *\r\n   * This is ready only after the invoices have been loaded by Preview (may be already created invoices).\r\n   */\r\n  public get paymentStatus(): \"unknown\" | \"preview\" | \"inProgress\" | \"exceptions\" | \"canceled\" | \"paid\" {\r\n\r\n    const invoices = (this.invoices ?? []).filter(x => x.invoice.entityType !== \"payroll\");\r\n\r\n    if (invoices.length === 0) {\r\n      return \"unknown\";\r\n    }\r\n\r\n    if (invoices.every((x) => !x.exists)) {\r\n      return \"preview\";\r\n    }\r\n\r\n    const paidNet = invoices.find((x) => x.invoice.status == InvoiceStatus.Paid && x.invoice.entityType == \"net\");\r\n    if (paidNet?.invoice.data.channel == PaymentChannel.PalkkausPersonal) {\r\n      // HACK: As of writing PalkkausPersonal only sets Net payment as paid (not the tax).\r\n      return \"paid\";\r\n    }\r\n\r\n    const inProgress = [InvoiceStatus.WaitingPalkkaus, InvoiceStatus.Unread, InvoiceStatus.Read, InvoiceStatus.WaitingConfirmation, InvoiceStatus.PaymentStarted];\r\n    if (invoices.find((x) => inProgress.indexOf(x.invoice.status) >= 0)) {\r\n      return \"inProgress\";\r\n    }\r\n    if (invoices.find((x) => x.invoice.status === InvoiceStatus.Canceled)) {\r\n      return \"canceled\";\r\n    }\r\n    const exceptions = [InvoiceStatus.Undefined, InvoiceStatus.Error];\r\n    if (invoices.find((x) => exceptions.indexOf(x.invoice.status) >= 0)) {\r\n      return \"exceptions\";\r\n    }\r\n    const paid = [InvoiceStatus.Paid, InvoiceStatus.Forecast, InvoiceStatus.Preview];\r\n    if (invoices.every((x) => paid.indexOf(x.invoice.status) >= 0)) {\r\n      return \"paid\";\r\n    }\r\n    return \"inProgress\";\r\n  }\r\n\r\n  /** Gets the type of current. */\r\n  public get currentType(): \"Calculation\" | \"PayrollDetails\" | null {\r\n    if (!this.current) {\r\n      return null;\r\n    }\r\n    if (InvoicesLogic.isPayroll(this.current)) {\r\n      return \"PayrollDetails\";\r\n    }\r\n    if (InvoicesLogic.isCalculation(this.current)) {\r\n      return \"Calculation\";\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /** Returns true if the calculations are valid for payment. */\r\n  public get isValid(): boolean {\r\n    if (InvoicesLogic.isPayroll(this.current)) {\r\n      // return this.current.validations.every((x) => x.isValid);\r\n      return this.current.info &&\r\n        this.current.info.isReadyForPayment;\r\n    }\r\n    if (InvoicesLogic.isCalculation(this.current)) {\r\n      return this.current.result &&\r\n        // this.current.result.validation?.isValid &&\r\n        !(this.current.result.validation?.errors ?? []).find((e) => (e.type !== \"warning\")) &&\r\n        this.current.worker &&\r\n        this.current.worker.tax.isValid;\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /** Gets and avatar image for a payment channel */\r\n  public getChannelAvatar(option: InputEnumOption) {\r\n    const channel = option.value || PaymentChannel.Undefined;\r\n    return InvoicesLogic.getChannelAvatar(channel as PaymentChannel);\r\n  }\r\n\r\n  /** Reloads the preview invoices from the server. */\r\n  public reload() {\r\n    if (!this.channel || this.channel === PaymentChannel.Undefined || !this.isValid) {\r\n      return; // Cannot start reload\r\n    }\r\n    if (this.bindingMode == null) {\r\n      return;\r\n    }\r\n    if (this.bindingMode !== \"model\") {\r\n      throw new Error(\"Not implemented: Only Calculation or PayrollDetails is currently supported.\");\r\n    }\r\n    this.invoices = null;\r\n    if (InvoicesLogic.isPayroll(this.current)) {\r\n\r\n      if (this.current.calcs?.length > 0) {\r\n        // old\r\n        this.invoicesApi.previewInvoices(this.channel, { payrollIds: [this.current.id] }).then((result) => {\r\n          this.invoices = result;\r\n        });\r\n      }\r\n      else {\r\n        // new\r\n        const payrolls4Api = new Payrolls4(this.ajax);\r\n        payrolls4Api.getCalcsOData(this.current.id, null).then((listItemResult) => {\r\n          const calcs = listItemResult.items;\r\n          const data: any = {};\r\n          data.listItemType = \"CalculationListItem\";\r\n          const columns = undefined;\r\n          const paramsTemplate = undefined;\r\n          const action = (items, data) => {\r\n            const itemIds = items.map((x) => x.id);\r\n            const remainingAfterThis =  data.dialogList.filter((x) => !x.processed).length;\r\n            const excludePeriodic = remainingAfterThis == 0 ? false:  true;\r\n            return payrolls4Api.previewInvoices(this.current.id, itemIds, excludePeriodic).then((result) => {\r\n              const results = items.map(() => ( {message: \"\", result: []}));\r\n              if (results.length > 0) {\r\n                results[0].result = result;\r\n              }\r\n              return results;\r\n            });\r\n          };\r\n          this.uiHelpers.showBatchProcessDialog(Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.uiStatusLoading\"), calcs, action, paramsTemplate, data, columns, 20, true, true, true).then((dialogResult) => {\r\n            if (dialogResult.done) {\r\n              this.invoices = [];\r\n              dialogResult.results.forEach( (result) => {\r\n                this.invoices.push(...result.result);\r\n              });\r\n            }\r\n            else\r\n            {\r\n              this.userCanceled = true;\r\n              this.invoices = [];\r\n            }\r\n          });\r\n        });\r\n      }\r\n    }\r\n    else if (InvoicesLogic.isCalculation(this.current)) {\r\n      this.invoicesApi.previewInvoices(this.channel, { calcs: [this.current] }).then((result) => {\r\n        this.invoices = result;\r\n      });\r\n    }\r\n  }\r\n\r\n  /** Gets the part of the UI that should be visible. */\r\n  public get uiStatus(): \"invalid\" | \"loading\" | \"created\" | \"supportedChannel\" | \"unsupported\" | \"userCanceled\" | \"undefined\" {\r\n    if (this.userCanceled) {\r\n      return \"userCanceled\"; // User canceled the process\r\n    }\r\n    if (!this.isValid) {\r\n      return \"invalid\"; // Show validation errors\r\n    }\r\n    if (this.paymentStatus === \"unknown\") {\r\n      return \"loading\"; // this.invoices is still loading => Show spinner\r\n    }\r\n    if (this.paymentStatus === \"exceptions\"\r\n      || this.paymentStatus === \"canceled\"\r\n      || this.paymentStatus === \"inProgress\"\r\n      || this.paymentStatus === \"paid\"\r\n    ) {\r\n      return \"created\"; // Invoices have already been created (no swithching channel).\r\n    }\r\n    if (!this.channel || this.channel === PaymentChannel.Undefined) {\r\n      return \"undefined\"; // Choose channel\r\n    }\r\n    const supportedChannels = [\r\n      PaymentChannel.AccountorGo,\r\n      PaymentChannel.FinagoSolo,\r\n      PaymentChannel.Kevytyrittaja,\r\n      PaymentChannel.Askelma,\r\n      PaymentChannel.Briox,\r\n      PaymentChannel.Lemonaid,\r\n      PaymentChannel.Laskupiste,\r\n      PaymentChannel.PasseliMerit,\r\n      PaymentChannel.Odoo,\r\n      PaymentChannel.Hausvise,\r\n      PaymentChannel.Ecom,\r\n      PaymentChannel.Kompassi,\r\n      PaymentChannel.Domus,\r\n      PaymentChannel.Holvi,\r\n      PaymentChannel.PalkkausManual,\r\n      PaymentChannel.TalenomManual,\r\n      PaymentChannel.PalkkausWS,\r\n      PaymentChannel.PalkkausPersonal,\r\n      PaymentChannel.PalkkausInvoices,\r\n      PaymentChannel.Kitsas,\r\n      PaymentChannel.Test,\r\n      PaymentChannel.ZeroPayment,\r\n      PaymentChannel.TalenomOnline,\r\n      PaymentChannel.VismaNetvisor,\r\n      PaymentChannel.Procountor\r\n    ];\r\n    if (supportedChannels.find((x) => x === this.channel)) {\r\n      return \"supportedChannel\"; // Supported channel\r\n    }\r\n    return \"unsupported\";\r\n  }\r\n\r\n  /** Returns current salary date kind */\r\n  public get salaryDateKind(): SalaryDateKind {\r\n    let salaryDateKind: SalaryDateKind = undefined;\r\n    if (InvoicesLogic.isPayroll(this.current)) {\r\n      salaryDateKind = this.current.input.salaryDateKind;\r\n    }\r\n    else if (InvoicesLogic.isCalculation(this.current)) {\r\n      salaryDateKind = this.current.workflow.salaryDateKind;\r\n    }\r\n    return salaryDateKind ?? SalaryDateKind.Default;\r\n  }\r\n\r\n  /**\r\n   * Starts the invoices creation process from the current channel and model.\r\n   * This method is used when controller is used first as previe and then creating invoices.\r\n   */\r\n  public createInvoices(closeFunc?: (action) => any) {\r\n    if (!this.channel || this.channel === PaymentChannel.Undefined || !this.isValid) {\r\n      throw new Error(\"Cannot start invoices creation\");\r\n    }\r\n\r\n    if (!this.invoicesService.checkAccountVerificationForPayment()) {\r\n      this.invoicesService.showMissingSignatureAlert();\r\n      return;\r\n    }\r\n\r\n    if (!this.invoicesService.checkChangedSalaryDate(this.current)) {\r\n      this.invoicesService.showChangedSalaryDateAlert();\r\n      return;\r\n    }\r\n\r\n    if(InvoicesLogic.isEcfa(this.channel)) {\r\n      if(!this.invoicesService.checkKycForPayment()) {\r\n        this.invoicesService.showMissingKycAlert();\r\n        return;\r\n      }\r\n    }\r\n\r\n    const inProgress = [InvoiceStatus.WaitingPalkkaus, InvoiceStatus.Read, InvoiceStatus.WaitingConfirmation, InvoiceStatus.PaymentStarted];\r\n\r\n    // TODO: We should allow redirection for payroll payments to TalenomOnline and Procountor, like with InvoicesLogic.isCalculation.\r\n    if (InvoicesLogic.isPayroll(this.current)) {\r\n      if (this.channel === PaymentChannel.Test || this.channel === PaymentChannel.VismaNetvisor || this.channel === PaymentChannel.Procountor) {\r\n        if (this.paymentStatus === \"inProgress\") {\r\n          const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.paymentDialogOpened\");\r\n          const idsToPay = this.invoices.filter((x) => inProgress.indexOf(x.invoice.status) >= 0).map((x) => x.invoice.id);\r\n          let url = \"\";\r\n          switch (this.channel) {\r\n            case PaymentChannel.Test:\r\n              url =\r\n                Configs.current.isTestData ?\r\n                  \"https://test-integrations.salaxy.com/test#/dialogs/payment\" :\r\n                  \"https://integrations.salaxy.com/test#/dialogs/payment\";\r\n              break;\r\n            case PaymentChannel.Procountor:\r\n              url =\r\n                Configs.current.isTestData ?\r\n                  \"http://localhost:93/procountor/payment.html\" :\r\n                  \"https://integrations.salaxy.com/procountor/payment.html\";\r\n              break;\r\n            case PaymentChannel.VismaNetvisor:\r\n              url =\r\n                Configs.current.isTestData ?\r\n                  \"http://localhost:93/vismanetvisor/payment.html\" :\r\n                  \"https://integrations.salaxy.com/vismanetvisor/payment.html\";\r\n              break;\r\n          }\r\n          url += \"?invoiceIds=\" + idsToPay + \"&token=\" + this.ajax.getCurrentToken();\r\n          this.uiHelpers.showExternalDialog(\"payrollPayment\", url, {}).then(() => {\r\n            loader.dismiss();\r\n            // HACK: Need a way to configure the URL and potentially raise an event for reload.\r\n            this.$location.path(\"/payroll/details/\" + this.current.id + \"&refresh=\" + new Date().getTime());\r\n            if (closeFunc) {\r\n              closeFunc(\"ok\");\r\n            }\r\n          });\r\n        } else {\r\n          const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.creatingInvoices\");\r\n          this.invoicesApi.createInvoicesForPayroll(this.channel, this.current.id).then((result) => {\r\n            loader.setHeading(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.paymentDialogOpened\");\r\n            const idsToPay = result.filter((x) => x.header.status === InvoiceStatus.Unread).map((x) => x.id);\r\n            let url = \"\";\r\n            switch (this.channel) {\r\n              case PaymentChannel.Test:\r\n                url =\r\n                  Configs.current.isTestData ?\r\n                    \"https://test-integrations.salaxy.com/test#/dialogs/payment\" :\r\n                    \"https://integrations.salaxy.com/test#/dialogs/payment\";\r\n                break;\r\n              case PaymentChannel.Procountor:\r\n                url =\r\n                  Configs.current.isTestData ?\r\n                    \"http://localhost:93/procountor/payment.html\" :\r\n                    \"https://integrations.salaxy.com/procountor/payment.html\";\r\n                break;\r\n              case PaymentChannel.VismaNetvisor:\r\n                url =\r\n                  Configs.current.isTestData ?\r\n                    \"http://localhost:93/vismanetvisor/payment.html\" :\r\n                    \"https://integrations.salaxy.com/vismanetvisor/payment.html\";\r\n                break;\r\n            }\r\n            url += \"?invoiceIds=\" + idsToPay + \"&token=\" + this.ajax.getCurrentToken();\r\n            this.uiHelpers.showExternalDialog(\"payrollPayment\", url, {}).then(() => {\r\n              loader.dismiss();\r\n              // HACK: Need a way to configure the URL and potentially raise an event for reload.\r\n              this.$location.path(\"/payroll/details/\" + this.current.id + \"&refresh=\" + new Date().getTime());\r\n              if (closeFunc) {\r\n                closeFunc(\"ok\");\r\n              }\r\n            });\r\n          });\r\n        }\r\n      } else {\r\n        if (this.current.calcs?.length > 0) {\r\n          // old\r\n          const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.creatingInvoices\");\r\n          this.invoicesApi.createInvoicesForPayroll(this.channel, this.current.id).then(() => {\r\n            loader.dismiss();\r\n            // HACK: Need a way to configure the URL and potentially raise an event for reload.\r\n            this.$location.path(\"/payroll/details/\" + this.current.id + \"&refresh=\" + new Date().getTime());\r\n            this.showInvoiceSuccessAlert(this.channel);\r\n            if (closeFunc) {\r\n              closeFunc(\"ok\");\r\n            }\r\n          });\r\n        } else {\r\n          // new\r\n          const payrolls4Api = new Payrolls4(this.ajax);\r\n          payrolls4Api.getCalcsOData(this.current.id, null).then((listItemResult) => {\r\n            const calcs = listItemResult.items;\r\n            const data: any = {};\r\n            data.listItemType = \"CalculationListItem\";\r\n            const columns = undefined;\r\n            const paramsTemplate = undefined;\r\n            const action = (items, data) => {\r\n              const itemIds = items.map((x) => x.id);\r\n              const remainingAfterThis =  data.dialogList.filter((x) => !x.processed).length;\r\n              const excludePeriodic = remainingAfterThis == 0 ? false:  true;\r\n              return payrolls4Api.createInvoices(this.current.id, itemIds, excludePeriodic).then((result) => {\r\n                const results = items.map(() => ( {message: \"\", result: []}));\r\n                if (results.length > 0) {\r\n                  results[0].result = result;\r\n                }\r\n                return results;\r\n              });\r\n            };\r\n            this.uiHelpers.showBatchProcessDialog(Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.creatingInvoices\"), calcs, action, paramsTemplate, data, columns, 20, true, true, true).then((dialogResult) => {\r\n              if (dialogResult.done) {\r\n                // HACK: Need a way to configure the URL and potentially raise an event for reload.\r\n                this.$location.path(\"/payroll/details/\" + this.current.id + \"&refresh=\" + new Date().getTime());\r\n                this.showInvoiceSuccessAlert(this.channel);\r\n                if (closeFunc) {\r\n                  closeFunc(\"ok\");\r\n                }\r\n              } else {\r\n                this.userCanceled = true;\r\n              }\r\n            });\r\n          });\r\n        }\r\n      }\r\n    } else if (InvoicesLogic.isCalculation(this.current)) {\r\n\r\n      const refreshCurrentCalculation = (invoices: Invoice[]): Promise<Calculation> => {\r\n        if (invoices) {\r\n          const calcId = (invoices.find((x) => x.header.type === InvoiceType.Net || x.header.type === InvoiceType.Gross))?.header.businessObjects[0];\r\n          if (calcId) {\r\n            return this.calculationsApi.getSingle(calcId).then((calculation) => {\r\n              angular.copy(calculation, this.current);\r\n              return this.current;\r\n            });\r\n          }\r\n        }\r\n        return Promise.resolve(this.current);\r\n      };\r\n      if (this.channel === PaymentChannel.Test || this.channel === PaymentChannel.VismaNetvisor || this.channel === PaymentChannel.Procountor) {\r\n        if (this.paymentStatus === \"inProgress\") {\r\n          const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.paymentDialogOpened\");\r\n          const idsToPay = this.invoices.filter((x) => inProgress.indexOf(x.invoice.status) >= 0).map((x) => x.invoice.id);\r\n          let url = \"\";\r\n          switch (this.channel) {\r\n            case PaymentChannel.Test:\r\n              url =\r\n                Configs.current.isTestData ?\r\n                  \"https://test-integrations.salaxy.com/test#/dialogs/payment\" :\r\n                  \"https://integrations.salaxy.com/test#/dialogs/payment\";\r\n              break;\r\n            case PaymentChannel.Procountor:\r\n              url =\r\n                Configs.current.isTestData ?\r\n                  \"http://localhost:93/procountor/payment.html\" :\r\n                  \"https://integrations.salaxy.com/procountor/payment.html\";\r\n              break;\r\n            case PaymentChannel.VismaNetvisor:\r\n              url =\r\n                Configs.current.isTestData ?\r\n                  \"http://localhost:93/vismanetvisor/payment.html\" :\r\n                  \"https://integrations.salaxy.com/vismanetvisor/payment.html\";\r\n              break;\r\n          }\r\n          url += \"?invoiceIds=\" + idsToPay + \"&token=\" + this.ajax.getCurrentToken();\r\n          this.uiHelpers.showExternalDialog(\"calcPayment\", url, {}).then(() => {\r\n            refreshCurrentCalculation(null).then(() => {\r\n              loader.dismiss();\r\n              // HACK: Need a way to configure the URL and potentially raise an event for reload.\r\n              this.$location.path(\"/calc/details/\" + this.current.id + \"&refresh=\" + new Date().getTime());\r\n            });\r\n            if (closeFunc) {\r\n              closeFunc(\"ok\");\r\n            }\r\n          });\r\n        } else {\r\n          const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.creatingInvoices\");\r\n          this.invoicesApi.createInvoices(this.current, this.channel).then((result) => {\r\n            loader.setHeading(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.paymentDialogOpened\");\r\n            let idsToPay = result.filter((x) => x.header.status === InvoiceStatus.Unread).map((x) => x.id);\r\n            let url = \"\";\r\n            switch (this.channel) {\r\n              case PaymentChannel.Test:\r\n                url =\r\n                  Configs.current.isTestData ?\r\n                    \"https://test-integrations.salaxy.com/test#/dialogs/payment\" :\r\n                    \"https://integrations.salaxy.com/test#/dialogs/payment\";\r\n                break;\r\n              case PaymentChannel.Procountor:\r\n                url =\r\n                  Configs.current.isTestData ?\r\n                    \"http://localhost:93/procountor/payment.html\" :\r\n                    \"https://integrations.salaxy.com/procountor/payment.html\";\r\n                break;\r\n              case PaymentChannel.VismaNetvisor:\r\n                idsToPay = result\r\n                  .filter(v => v.header.paymentType === InvoicePaymentType.Salary && v.header.status === InvoiceStatus.Unread)\r\n                  .map(v => v.id);\r\n                url =\r\n                  Configs.current.isTestData ?\r\n                    \"http://localhost:93/vismanetvisor/payment.html\" :\r\n                    \"https://integrations.salaxy.com/vismanetvisor/payment.html\";\r\n                break;\r\n            }\r\n            url += \"?invoiceIds=\" + idsToPay + \"&token=\" + this.ajax.getCurrentToken();\r\n            this.uiHelpers.showExternalDialog(\"calcPayment\", url, {}).then(() => {\r\n              refreshCurrentCalculation(result).then(() => {\r\n                loader.dismiss();\r\n                // HACK: Need a way to configure the URL and potentially raise an event for reload.\r\n                this.$location.path(\"/calc/details/\" + this.current.id + \"&refresh=\" + new Date().getTime());\r\n              });\r\n              if (closeFunc) {\r\n                closeFunc(\"ok\");\r\n              }\r\n            });\r\n          });\r\n        }\r\n      } else {\r\n        const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.creatingInvoices\");\r\n        this.invoicesApi.createInvoices(this.current, this.channel).then((result) => {\r\n          refreshCurrentCalculation(result).then(() => {\r\n            loader.dismiss();\r\n            // HACK: Need a way to configure the URL and potentially raise an event for reload.\r\n            if ((this.current as Calculation)?.info?.payrollId) {\r\n              this.$location.path(\"/payroll/details/\" + (this.current as Calculation).info.payrollId + \"&refresh=\" + new Date().getTime());\r\n            }\r\n            else\r\n            {\r\n              this.$location.path(\"/calc/details/\" + this.current.id + \"&refresh=\" + new Date().getTime());\r\n            }\r\n            this.showInvoiceSuccessAlert(this.channel);\r\n          });\r\n          if (closeFunc) {\r\n            closeFunc(\"ok\");\r\n          }\r\n        });\r\n      }\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Create invoices for calculation: Immediate execution without preview. Used in PRO and other advanced UI.\r\n   * Shows a loader dialog, saves changes if necessary, creates invoices and reloads the controller.\r\n   * @param calcController Controller that contains the calculation that should be paid. May have save changes.\r\n   * @param channel Payment channel that is used for payment.\r\n   */\r\n  public createInvoicesForCalculation(calcController: CalculationCrudController, channel: PaymentChannel): Promise<Invoice[]> {\r\n    if (!this.invoicesService.checkAccountVerificationForPayment()) {\r\n      this.invoicesService.showMissingSignatureAlert();\r\n      return;\r\n    }\r\n\r\n    if (!this.invoicesService.checkChangedSalaryDate(calcController.current)) {\r\n      this.invoicesService.showChangedSalaryDateAlert();\r\n      return;\r\n    }\r\n\r\n    if(InvoicesLogic.isEcfa(channel)) {\r\n      if(!this.invoicesService.checkKycForPayment()) {\r\n        this.invoicesService.showMissingKycAlert();\r\n        return;\r\n      }\r\n    }\r\n\r\n    const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.creatingInvoices\");\r\n    return this.invoicesApi.createInvoices(calcController.current, channel).then((result) => {\r\n      calcController.reload();\r\n      loader.dismiss();\r\n      this.showInvoiceSuccessAlert(channel);\r\n      return result;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Create invoices for payroll: Immediate execution without preview. Used in PRO and other advanced UI.\r\n   * Shows a loader dialog, saves changes if necessary, creates invoices and reloads the controller.\r\n   * @param payrollController Controller that contains the calculation that should be paid. May have save changes.\r\n   * @param channel Payment channel that is used for payment.\r\n   */\r\n  public createInvoicesForPayroll(payrollController: PayrollCrudController, channel: PaymentChannel): Promise<Invoice[]> {\r\n    if (!this.invoicesService.checkAccountVerificationForPayment()) {\r\n      this.invoicesService.showMissingSignatureAlert();\r\n      return;\r\n    }\r\n\r\n    if (!this.invoicesService.checkChangedSalaryDate(payrollController.current)) {\r\n      this.invoicesService.showChangedSalaryDateAlert();\r\n      return;\r\n    }\r\n\r\n    if(InvoicesLogic.isEcfa(channel)) {\r\n      if(!this.invoicesService.checkKycForPayment()) {\r\n        this.invoicesService.showMissingKycAlert();\r\n        return;\r\n      }\r\n    }\r\n\r\n    const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.creatingInvoices\");\r\n\r\n    const invoiceCreate = () => {\r\n      return this.invoicesApi.createInvoicesForPayroll(channel, payrollController.current.id).then((result) => {\r\n        payrollController.reload();\r\n        loader.dismiss();\r\n        this.showInvoiceSuccessAlert(channel);\r\n        return result;\r\n      });\r\n    };\r\n\r\n    if (payrollController.hasChanges || payrollController.isNew()) {\r\n      return payrollController.save().then(() => {\r\n        return invoiceCreate();\r\n      });\r\n    } else {\r\n      return invoiceCreate();\r\n    }\r\n  }\r\n\r\n  /** Gets text for preview invoice */\r\n  public getPreviewText(item: InvoicePreview): string {\r\n    if( (item.invoice.data.channel == PaymentChannel.PalkkausInvoices ||  item.invoice.data.channel == PaymentChannel.Kitsas) && (item.invoice.entityType == InvoiceType.Tax || item.invoice.entityType == InvoiceType.Union || item.invoice.entityType == InvoiceType.Payroll)) {\r\n      return Translations.get(\"SALAXY.NG1.InvoicesCreateTableComponent.PalkkausInvoicesTaxPreviewText\");\r\n    }\r\n    return Translations.get(\"SALAXY.NG1.InvoicesCreateTableComponent.dueDateTypePreview\");\r\n  }\r\n\r\n  /** Gets text for estimation invoice */\r\n  public getEstimationText(item: InvoicePreview): string {\r\n    return `${item.invoice.otherPartyInfo.avatar.sortableName} ${Translations.get(\"SALAXY.NG1.InvoicesCreateTableComponent.sendsInvoice\")}`;\r\n  }\r\n\r\n  /** Gets the type of the calculation for display purposes. */\r\n  public getDueDateType(item: InvoicePreview): \"default\" | \"estimation\" | \"forecast\" | \"preview\" | \"zero\" | \"unknown\" | \"paid\" | \"canceled\" | \"inProgress\" {\r\n    if (item.invoice.entityType === \"unemployment\") {\r\n      return \"estimation\";\r\n    }\r\n\r\n    if (item.invoice.status === InvoiceStatus.Forecast) {\r\n      return \"forecast\";\r\n    }\r\n\r\n    if (item.invoice.status === InvoiceStatus.Preview) {\r\n      return \"preview\";\r\n    }\r\n\r\n    if (item.invoice.status === InvoiceStatus.Canceled) {\r\n      return \"canceled\";\r\n    }\r\n\r\n    if (item.invoice.data.channel === PaymentChannel.ZeroPayment) {\r\n      return \"zero\";\r\n    }\r\n\r\n    if (item.invoice.status === InvoiceStatus.Paid && item.invoice.payment === 0) {\r\n      return \"zero\";\r\n    }\r\n\r\n    if (!item.invoice.otherId && item.invoice.data.channel === PaymentChannel.VismaNetvisor) {\r\n      return \"preview\";\r\n    }\r\n\r\n    if (item.invoice.status === InvoiceStatus.Paid) {\r\n      return \"paid\";\r\n    }\r\n\r\n    if (InvoicesLogic.isPalkkausManualLike(item.invoice.data.channel) && (item.invoice.entityType === InvoiceType.Net || item.invoice.entityType === InvoiceType.Foreclosure) && this.salaryDateKind === SalaryDateKind.InPast) {\r\n      return \"paid\";\r\n    }\r\n\r\n    if (( InvoicesLogic.isPalkkausInvoicesLike(item.invoice.data.channel)) && (item.invoice.entityType === InvoiceType.Net || item.invoice.entityType === InvoiceType.Foreclosure) && this.salaryDateKind === SalaryDateKind.InPast) {\r\n      return \"paid\";\r\n    }\r\n\r\n    if( InvoicesLogic.isPalkkausInvoicesLike(item.invoice.data.channel) &&\r\n    (item.invoice.entityType == InvoiceType.Tax || item.invoice.entityType == InvoiceType.Union || item.invoice.entityType == InvoiceType.Payroll))\r\n    {\r\n      return \"preview\";\r\n    }\r\n\r\n    if ( ( item.invoice.entityType == \"net\" ||\r\n           item.invoice.entityType == \"foreclosure\" ||\r\n           item.invoice.entityType == \"payroll\") &&\r\n      item.invoice.id != null && (\r\n      item.invoice.status === InvoiceStatus.WaitingPalkkaus ||\r\n      item.invoice.status === InvoiceStatus.Unread ||\r\n      item.invoice.status === InvoiceStatus.WaitingConfirmation ||\r\n      item.invoice.status === InvoiceStatus.Read ||\r\n      item.invoice.status === InvoiceStatus.PaymentStarted ||\r\n      item.invoice.status === InvoiceStatus.Warning )\r\n    ) {\r\n      return \"inProgress\";\r\n    }\r\n\r\n    return \"default\";\r\n  }\r\n\r\n  /**\r\n   * Returns the net invoice preview for current calculation.\r\n   */\r\n  public get primaryCalcNetInvoicePreview(): InvoicePreview {\r\n    if (!this._primaryCalcNetInvoicePreview && this.invoices && this.invoices.length > 0) {\r\n      const preview = this.invoices.find((x) => x.invoice.entityType === InvoiceType.Net && x.invoice.status !== InvoiceStatus.Canceled && x.invoice.status !== InvoiceStatus.Error);\r\n      if (preview) {\r\n        this._primaryCalcNetInvoicePreview = preview;\r\n      }\r\n    }\r\n    return this._primaryCalcNetInvoicePreview;\r\n  }\r\n\r\n  /**\r\n   * Returns the ysc invoice preview for current calculation.\r\n   */\r\n  public get primaryCalcTaxInvoicePreview(): InvoicePreview {\r\n    if (!this._primaryCalcTaxInvoicePreview && this.invoices && this.invoices.length > 0) {\r\n      const preview = this.invoices.find((x) => x.invoice.entityType === InvoiceType.Tax && x.invoice.status !== InvoiceStatus.Canceled && x.invoice.status !== InvoiceStatus.Error);\r\n      if (preview) {\r\n        this._primaryCalcTaxInvoicePreview = preview;\r\n      }\r\n    }\r\n    return this._primaryCalcTaxInvoicePreview;\r\n  }\r\n\r\n  private getNetInvoiceId(invoices: Invoice[]): string {\r\n    if (!invoices || invoices.length === 0) {\r\n      return null;\r\n    }\r\n    return (invoices.find((x) => x.header.type === InvoiceType.Net) || {}).id;\r\n  }\r\n\r\n  private showInvoiceSuccessAlert(channel: PaymentChannel) {\r\n    if (channel === PaymentChannel.ZeroPayment) {\r\n      this.uiHelpers.showAlert(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.zeroPayment.successAlertHeading\", \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.zeroPayment.successAlertText\");\r\n    } else if (channel === PaymentChannel.AccountorGo) {\r\n      this.uiHelpers.showAlert(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.accountorGo.successAlertHeading\", \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.accountorGo.successAlertText\");\r\n    } else if (channel === PaymentChannel.FinagoSolo) {\r\n      this.uiHelpers.showAlert(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.finagoSolo.successAlertHeading\", \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.finagoSolo.successAlertText\");\r\n    } else if (channel === PaymentChannel.Kevytyrittaja) {\r\n      this.uiHelpers.showAlert(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.kevytyrittaja.successAlertHeading\", \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.kevytyrittaja.successAlertText\");\r\n    } else if (channel === PaymentChannel.Askelma) {\r\n      this.uiHelpers.showAlert(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.askelma.successAlertHeading\", \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.askelma.successAlertText\");\r\n    } else if (channel === PaymentChannel.Briox) {\r\n      this.uiHelpers.showAlert(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.briox.successAlertHeading\", \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.briox.successAlertText\");\r\n    } else if (channel === PaymentChannel.Lemonaid) {\r\n      this.uiHelpers.showAlert(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.lemonaid.successAlertHeading\", \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.lemonaid.successAlertText\");\r\n    } else if (channel === PaymentChannel.Laskupiste) {\r\n      this.uiHelpers.showAlert(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.laskupiste.successAlertHeading\", \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.laskupiste.successAlertText\");\r\n    } else if (channel === PaymentChannel.PasseliMerit) {\r\n      this.uiHelpers.showAlert(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.passeliMerit.successAlertHeading\", \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.passeliMerit.successAlertText\");\r\n    } else if (channel === PaymentChannel.Odoo) {\r\n      this.uiHelpers.showAlert(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.odoo.successAlertHeading\", \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.odoo.successAlertText\");\r\n    } else if (channel === PaymentChannel.Hausvise) {\r\n      this.uiHelpers.showAlert(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.hausvise.successAlertHeading\", \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.hausvise.successAlertText\");\r\n    }\r\n    else if (channel === PaymentChannel.Ecom) {\r\n      this.uiHelpers.showAlert(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.ecom.successAlertHeading\", \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.ecom.successAlertText\");\r\n    } else if (channel === PaymentChannel.Kompassi) {\r\n      this.uiHelpers.showAlert(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.kompassi.successAlertHeading\", \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.kompassi.successAlertText\");\r\n    } else if (channel === PaymentChannel.Domus) {\r\n      this.uiHelpers.showAlert(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.domus.successAlertHeading\", \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.domus.successAlertText\")\r\n      .then(() => {\r\n        window.parent.postMessage({ \"salaxyEvent\": \"InvoiceSuccessAlert\" }, \"*\");\r\n        console.debug(\"Domus\",\"InvoiceSuccessAlert posted with postMessage\");\r\n      });\r\n    } else if (channel === PaymentChannel.Holvi) {\r\n      this.uiHelpers.showAlert(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.holvi.successAlertHeading\", \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.holvi.successAlertText\");\r\n    } else if (channel === PaymentChannel.TalenomOnline) {\r\n      this.uiHelpers.showAlert(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.talenomOnline.successAlertHeading\", \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.talenomOnline.successAlertText\");\r\n    } else if (InvoicesLogic.isPalkkausManualLike(channel)) {\r\n      if (this.salaryDateKind == SalaryDateKind.InPast) {\r\n        this.uiHelpers.showAlert(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.palkkausManualAndFixed.successAlertHeading\", \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.palkkausManualAndFixed.successAlertText\");\r\n      }\r\n      else {\r\n        this.uiHelpers.showAlert(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.palkkausManual.successAlertHeading\", \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.palkkausManual.successAlertText\");\r\n      }\r\n    } else if (channel === PaymentChannel.PalkkausWS) {\r\n      this.uiHelpers.showConfirm(\r\n        \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.kitsas.successAlertHeading\",\r\n        null,\r\n        \"Maksa laskut heti\",\r\n        \"Syötä lisää palkkoja\",\r\n        Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.kitsas.successAlertText\"),\r\n      ).then((x) => {\r\n        if (x) {\r\n          this.$location.path(\"/invoices/payment-list\");\r\n        } else {\r\n          // TODO: Now this only closes, should there be a redirect here?\r\n        }\r\n      });\r\n    } else if (channel === PaymentChannel.PalkkausPersonal) {\r\n      this.uiHelpers.showAlert(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.palkkausPersonal.successAlertHeading\", \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.palkkausPersonal.successAlertText\");\r\n    } else if (channel === PaymentChannel.PalkkausInvoices) {\r\n      this.uiHelpers.showConfirm(\r\n        \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.palkkausInvoices.successAlertHeading\",\r\n        null,\r\n        \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.palkkausInvoices.successAlertOk\",\r\n        \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.palkkausInvoices.successAlertCancel\",\r\n        Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.palkkausInvoices.successAlertText\"),\r\n      ).then((x) => {\r\n        if (x) {\r\n          this.$location.path(\"/invoices/company\");\r\n        } else {\r\n          // TODO: Now this only closes, should there be a redirect here?\r\n        }\r\n      });\r\n    }\r\n    else if (channel === PaymentChannel.Kitsas) {\r\n      this.uiHelpers.showConfirm(\r\n        \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.kitsas.successAlertHeading\",\r\n        null,\r\n        \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.kitsas.successAlertOk\",\r\n        \"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.kitsas.successAlertCancel\",\r\n        Translations.get(\"SALAXY.NG1.InvoicesCreateComponent.PaymentChannel.kitsas.successAlertText\"),\r\n      ).then((x) => {\r\n        if (x) {\r\n          this.$location.path(\"/invoices/company\");\r\n        } else {\r\n          // TODO: Now this only closes, should there be a redirect here?\r\n        }\r\n      });\r\n    }\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Dates, Invoice, InvoiceListItem, InvoicesLogic, InvoiceStatusNotification, PaymentChannel, PaymentChannelApi, Translations } from \"@salaxy/core\";\r\n\r\nimport { AjaxNg1 } from \"../../ajax\";\r\nimport { SessionService, UiHelpers } from \"../../services\";\r\nimport { ApiCrudObjectController } from \"../bases\";\r\n\r\n/**\r\n * Provides access for a payment channel to access invoices\r\n * that were sent to that channel and also the calculations etc. related to those invoices.\r\n * Only a Partner with registered Payment Channel can use this Controller.\r\n * Please contact Palkkaus.fi support for more information.\r\n */\r\nexport class PaymentChannelController extends ApiCrudObjectController<Invoice, InvoiceListItem> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"AjaxNg1\",\r\n    \"UiHelpers\",\r\n    \"$location\",\r\n    \"$routeParams\",\r\n    \"SessionService\",\r\n    \"$scope\",\r\n  ];\r\n\r\n  /** Status notification data for UI binding to update status. */\r\n  public statusData: InvoiceStatusNotification;\r\n\r\n  private _channel: PaymentChannel;\r\n\r\n  private _initialOwner: string;\r\n\r\n  private unread: Invoice[];\r\n\r\n  constructor(\r\n    private ajax: AjaxNg1,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    private sessionService: SessionService,\r\n    private $scope: angular.IScope,\r\n  ) { // Dependency injection\r\n    super(new PaymentChannelApi(null, ajax), uiHelpers, $location, $routeParams);\r\n  }\r\n\r\n  /**\r\n   * Initialization code.\r\n   */\r\n  public $onInit() {\r\n    const setChannel = () => {\r\n\r\n      if (this.sessionService.isSessionChecked && this.sessionService.isAuthenticated) {\r\n        const owner = this.sessionService.session.currentAccount.owner;\r\n        if (this._initialOwner != owner){\r\n          this._initialOwner = owner;\r\n          this.channel = this.sessionService.getOwnedPaymentChannel();\r\n          this.reload();\r\n          this.unread = null;\r\n          if (this.odataController) {\r\n            this.odataController.refreshClearAll();\r\n          }\r\n        }\r\n      } else {\r\n        this._initialOwner = null;\r\n        this.channel = null;\r\n        this.api = null;\r\n        this.unread = null;\r\n          if (this.odataController) {\r\n            this.odataController.refreshClearAll();\r\n          }\r\n      }\r\n    };\r\n\r\n    setChannel();\r\n\r\n    this.sessionService.subscribe(this.$scope, () => {\r\n      setChannel();\r\n    });\r\n\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Name/key of the channel on which the controller operates. */\r\n  public get channel(): PaymentChannel {\r\n    return this._channel;\r\n  }\r\n  public set channel(value: PaymentChannel) {\r\n    this._channel = value;\r\n    if (value) {\r\n      this.api = new PaymentChannelApi(value, this.ajax);\r\n    }\r\n  }\r\n\r\n  /** Gets the full items for unread objects. */\r\n  public get unreadInvoices(): Invoice[] {\r\n    if (!this.unread) {\r\n      this.unread = [];\r\n      this.paymentChannelApi.getInvoicesByStatus().then((items) => {\r\n        this.unread = items;\r\n      });\r\n    }\r\n    return this.unread;\r\n  }\r\n\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"payment-channel\",\r\n      detailsUrl: this.detailsUrl || \"/payment-channel/details/\",\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/InvoicesPanel.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n\r\n  /** Returns content url for the invoice. */\r\n  public getContentUrl(id: string, inline = false): string {\r\n    return this.paymentChannelApi.getContentUrl(id, inline);\r\n  }\r\n\r\n  /**\r\n   * Updates the status of the invoice.\r\n   * @param data Status data. If not set, uses the statusData property of the controller.\r\n   */\r\n  public updateStatus(data: InvoiceStatusNotification = null): Promise<Invoice> {\r\n    const loading = this.uiHelpers.showLoading();\r\n    data = data || this.statusData;\r\n    return this.setStatus(this.paymentChannelApi.updateStatus([data])\r\n      .then((invoices) => {\r\n        loading.dismiss();\r\n        this.setCurrent(invoices[0]);\r\n        this.resetStatusData();\r\n        return invoices[0];\r\n      }));\r\n  }\r\n\r\n  /** Resets the status data according to current Invoice. */\r\n  public resetStatusData() {\r\n    if (!this.current) {\r\n      this.statusData = null;\r\n      return;\r\n    }\r\n    this.statusData = {\r\n      id: this.current.id,\r\n      externalId: this.current.header.externalId,\r\n      date: Dates.getToday(),\r\n      status: this.current.header.status,\r\n      amount: this.current.header.total,\r\n    };\r\n  }\r\n\r\n  /** Gets and avatar image for a payment channel */\r\n  public getChannelAvatar() {\r\n    return InvoicesLogic.getChannelAvatar(this.channel);\r\n  }\r\n\r\n  /** Data reader for selected items. */\r\n  public selectionDataReader = {\r\n    /** Function to read data into given array */\r\n    read: (arr: Invoice[], message: string): Promise<void> => { // eslint-disable-line @typescript-eslint/no-unused-vars\r\n      const promises = this.odataController.selectedItems.map(x => this.api.getSingle(x.id));\r\n      return Promise.all(promises).then((data) => {\r\n        arr.push(...data.filter(d => !!d));\r\n        return;\r\n      });\r\n    },\r\n    /** Optional label for data export */\r\n    exportLabel: Translations.get(\"SALAXY.NG1.AccountingReportToolsComponent.exportLabel\"),\r\n    /** Indicates if the export is not possible */\r\n    disabled: () => !this.odataController.selectedItems || this.odataController.selectedItems.length === 0,\r\n  };\r\n\r\n  /**\r\n   * Data reader for one item.\r\n   * TODO: Should add interface for the reader.\r\n   */\r\n  public getItemDataReader = (item: {\r\n    /** List item id */\r\n    id: string,\r\n    /** List item owner */\r\n    owner: string,\r\n  }) => {\r\n    return {\r\n      /** Function to read data into given array */\r\n      read: (arr: Invoice[], message: string): Promise<void> => { // eslint-disable-line @typescript-eslint/no-unused-vars\r\n        (item as any).isReading = true;\r\n        return this.api.getSingle(item.id).then((data) => {\r\n          /*\r\n          const wfEvent = {\r\n            type: \"PartnerMessageClosed\",\r\n            ui: \"success\" as any,\r\n            message,\r\n          };\r\n          return this.filesApi.saveWorkflowEvent(item, wfEvent).then(() => {\r\n            this.setWorkflowEvent(item as any, wfEvent);\r\n          */\r\n          if (data) {\r\n            arr.push(data);\r\n          }\r\n          (item as any).isReading = false;\r\n          return Promise.resolve();\r\n          /* });*/\r\n        });\r\n      },\r\n      /** Optional label for data export */\r\n      exportLabel: null,\r\n      /** Indicates if the export is not possible */\r\n      disabled: () => false,\r\n    };\r\n  };\r\n\r\n  /** Unselect all */\r\n  public unselectAll() {\r\n    if (this.odataController.selectedItems) {\r\n      this.odataController.selectedItems.splice(0, this.odataController.selectedItems.length);\r\n    }\r\n  }\r\n\r\n  /** Select all */\r\n  public selectAll() {\r\n    if (this.odataController.selectedItems && this.odataController.items) {\r\n      this.odataController.selectedItems.splice(0, this.odataController.selectedItems.length);\r\n      this.odataController.selectedItems.push(...this.odataController.items);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Updates the invoice. Only valid in the test environment.\r\n   */\r\n  public save(): Promise<Invoice> {\r\n    const loading = this.uiHelpers.showLoading();\r\n    return this.ajax.postJSON( `/v03/api/payment-channel/${this.channel}`, this.current)\r\n      .then((invoice) => {\r\n        loading.dismiss();\r\n        this.setCurrent(invoice);\r\n        return invoice;\r\n      });\r\n  }\r\n\r\n  private get paymentChannelApi() {\r\n    return this.api as PaymentChannelApi;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport JSZip from \"@progress/jszip-esm\";\r\n\r\nimport { saveAs } from \"file-saver\";\r\n\r\nimport { Ajax, Dates, Invoice, InvoiceType, PaymentChannel, Texts, Translations } from \"@salaxy/core\";\r\n\r\nimport { UiHelpers } from \"../../services\";\r\n\r\n/** File type id */\r\nenum FileTypeId {\r\n  SepaFile = \"sepaFile\",\r\n  SepaFileV03 = \"sepaFileV03\",\r\n  SepaCopy = \"sepaCopy\",\r\n  SepaCopyV03 = \"sepaCopyV03\",\r\n  PdfFile = \"pdfFile\",\r\n  FinvoiceFile = \"finvoiceFile\"\r\n}\r\n\r\n/**\r\n * Provides functionality to export invoices in various formats.\r\n */\r\nexport class InvoiceToolsController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"AjaxNg1\",\r\n    \"$http\",\r\n    \"UiHelpers\"\r\n  ];\r\n\r\n  /** Export format */\r\n  public fileTypeId: string = FileTypeId.PdfFile;\r\n\r\n  /** Supported export formats */\r\n  public fileTypes: {\r\n    /** File type id */\r\n    id: string,\r\n    /** File type label */\r\n    label: string,\r\n    /** Workflow message after export */\r\n    workflowMessage,\r\n    /** Icon */\r\n    icon: string,\r\n  }[] = [\r\n      {\r\n        id: FileTypeId.PdfFile,\r\n        label: Translations.get(\"SALAXY.ENUM.ExportMethod.filePdf.label\"),\r\n        workflowMessage: Translations.get(\"SALAXY.ENUM.ExportMethod.filePdf.label\"),\r\n        icon: \"fa-file-pdf-o\",\r\n      },\r\n      {\r\n        id: FileTypeId.SepaFile,\r\n        label: Translations.get(\"SALAXY.ENUM.ExportMethod.fileSepa.label\"),\r\n        workflowMessage: Translations.get(\"SALAXY.ENUM.ExportMethod.fileSepa.workflowMessage\"),\r\n        icon: \"fa-file-code-o\",\r\n      },\r\n      {\r\n        id: FileTypeId.SepaFileV03,\r\n        label: Translations.get(\"SALAXY.ENUM.ExportMethod.fileSepaV03.label\"),\r\n        workflowMessage: Translations.get(\"SALAXY.ENUM.ExportMethod.fileSepaV03.workflowMessage\"),\r\n        icon: \"fa-file-code-o\",\r\n      },\r\n      {\r\n        id: FileTypeId.SepaCopy,\r\n        label: Translations.get(\"SALAXY.ENUM.ExportMethod.copySepa.label\"),\r\n        workflowMessage: Translations.get(\"SALAXY.ENUM.ExportMethod.copySepa.workflowMessage\"),\r\n        icon: \"fa-clipboard\",\r\n      },\r\n      {\r\n        id: FileTypeId.SepaCopyV03,\r\n        label: Translations.get(\"SALAXY.ENUM.ExportMethod.copySepaV03.label\"),\r\n        workflowMessage: Translations.get(\"SALAXY.ENUM.ExportMethod.copySepaV03.workflowMessage\"),\r\n        icon: \"fa-clipboard\",\r\n      },\r\n      {\r\n        id: FileTypeId.FinvoiceFile,\r\n        label: Translations.get(\"SALAXY.ENUM.ExportMethod.finvoiceFile.label\"),\r\n        workflowMessage: Translations.get(\"SALAXY.ENUM.ExportMethod.finvoiceFile.workflowMessage\"),\r\n        icon: \"fa-file-code-o\",\r\n      },\r\n    ];\r\n\r\n\r\n  /** Filetype Enum Options for filetype select element*/\r\n  public get fileTypeOptions() {\r\n    if (!this._fileTypeOptions) {\r\n      this._fileTypeOptions = this.fileTypes.map((x) => ({ value: x.id, text: x.label }));\r\n    }\r\n    return this._fileTypeOptions;\r\n  }\r\n  /**\r\n   * Object with read function to call for retrieving the invoice data.\r\n   * Function has the following argument:  arr, which is an array of invoices into which the result will be appended.\r\n   */\r\n  public reader: {\r\n    /** Function for reading invoices into given array. */\r\n    read: (\r\n      /** Array for invoices */\r\n      arr: Invoice[],\r\n      /** Message for workflow (loading) */\r\n      message: string,\r\n    ) => Promise<void>,\r\n    /** Function for getting sepa data for invoices */\r\n    getSepaData?: (\r\n      /** Array for invoices */\r\n      arr: Invoice[],\r\n    ) => Promise<string>,\r\n    /** Function for getting finvoice data for invoices */\r\n    getFinvoiceData?: (\r\n      /** Array for invoices */\r\n      arr: Invoice[],\r\n    ) => Promise<Blob[]>,\r\n    /** Function for getting pdf data for invoices */\r\n    getPdfData?: (\r\n      /** Array for invoices */\r\n      arr: Invoice[],\r\n    ) => Promise<Blob[]>,\r\n    /** Optional label for data export */\r\n    exportLabel?: string,\r\n    /** Indicates if the export is not possible */\r\n    disabled: () => boolean,\r\n  };\r\n\r\n  private _fileTypeOptions = null;\r\n  constructor(\r\n    private ajax: Ajax,\r\n    private $http: angular.IHttpService,\r\n    private uiHelpers: UiHelpers\r\n  ) {\r\n  }\r\n\r\n  /**\r\n   * Initialize controller values.\r\n   */\r\n  public $onInit() {\r\n    // Nothing here\r\n  }\r\n\r\n  /** Set visible filetypes. Sets the first file type as default. */\r\n  public setFileTypes(fileTypes: string[]) {\r\n    if (fileTypes && fileTypes.length > 0) {\r\n      const fts = [];\r\n      fileTypes.forEach((x) => {\r\n        const ft = this.fileTypes.find((f) => f.id === x);\r\n        if (ft) {\r\n          fts.push(ft);\r\n        }\r\n      });\r\n      this.fileTypes.splice(0);\r\n      this.fileTypes.push(...fts);\r\n      this.fileTypeId = fileTypes[0];\r\n    }\r\n  }\r\n\r\n  /** Exports data in defined format. */\r\n  public export(\r\n    reader: {\r\n      /** Function for reading data into given array. */\r\n      read: (\r\n        /** Array for invoices */\r\n        arr: Invoice[],\r\n        /** Workflow loading message */\r\n        message: string,\r\n      ) => Promise<void>,\r\n      /** Function for getting sepa data for invoices */\r\n      getSepaData?: (\r\n        /** Array for invoices */\r\n        arr: Invoice[],\r\n      ) => Promise<string>,\r\n      /** Function for getting finvoice data for invoices */\r\n      getFinvoiceData?: (\r\n        /** Array for invoices */\r\n        arr: Invoice[],\r\n      ) => Promise<Blob[]>,\r\n      /** Function for getting pdf data for invoices */\r\n      getPdfData?: (\r\n        /** Array for invoices */\r\n        arr: Invoice[],\r\n      ) => Promise<Blob[]>,\r\n      /** Optional label for data export */\r\n      exportLabel?: string,\r\n      /** Indicates if the export is not possible */\r\n      disabled: () => boolean,\r\n    } = null,\r\n    /** If true, does not show loading indicator. Default is false. */\r\n    hideLoading = false,\r\n    /** If true, does not return any content. */\r\n    withoutContent = false,\r\n    /** Prefer zip. If true creates zips for one content file too. */\r\n    preferZip = false,\r\n  ): Promise<void> {\r\n    if (!reader) {\r\n      reader = this.reader;\r\n    }\r\n    if (!reader) {\r\n      console.error(\"No reader for invoices.\");\r\n      return Promise.resolve();\r\n    }\r\n    const loading = hideLoading ? { dismiss: () => null } : this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n\r\n    const arr: Invoice[] = [];\r\n    return reader.read(arr, this.getWorkflowMessage()).then(() => {\r\n      if (arr.length === 0) {\r\n        loading.dismiss();\r\n        return Promise.resolve();\r\n      }\r\n      if (withoutContent) {\r\n        return;\r\n      }\r\n      switch (this.fileTypeId) {\r\n        case FileTypeId.PdfFile:\r\n          return (reader.getPdfData ?? ((x) => this.getPdfData(x)))(arr).then((pdfArr) => {\r\n            if (pdfArr.length === 1 && !preferZip) {\r\n              saveAs(pdfArr[0], `${this.getFileName(arr[0])}.pdf`);\r\n              loading.dismiss();\r\n              return;\r\n            } else {\r\n              let counter = 0;\r\n              const zip = new JSZip();\r\n              const next = () => {\r\n                if (counter === pdfArr.length) {\r\n                  return;\r\n                }\r\n                zip.file(`${this.getFileName(arr[counter])}.pdf`, pdfArr[counter]);\r\n                counter++;\r\n                next();\r\n              };\r\n\r\n              next();\r\n              return zip.generateAsync({\r\n                type: \"blob\",\r\n                mimeType:\r\n                  \"application/zip\",\r\n              }).then((blob) => {\r\n                saveAs(blob, `${this.getZipFileName(arr)}.zip`);\r\n                loading.dismiss();\r\n                return;\r\n              });\r\n            }\r\n          });\r\n          break;\r\n        case FileTypeId.SepaFile:\r\n        case FileTypeId.SepaFileV03:\r\n          return (reader.getSepaData ?? ((x) => this.getSepaData(x)))(arr).then((sepaData) => {\r\n            saveAs(new Blob([sepaData], { type: \"text/xml;charset=utf-8\" }), arr.length === 1 ? `${this.getFileName(arr[0])}.xml` : `${this.getZipFileName(arr)}.xml`);\r\n            loading.dismiss();\r\n            return;\r\n          });\r\n          break;\r\n        case FileTypeId.SepaCopy:\r\n        case FileTypeId.SepaCopyV03:\r\n          return (reader.getSepaData ?? ((x) => this.getSepaData(x)))(arr).then((sepaData) => {\r\n            (navigator as any).clipboard.writeText(sepaData);\r\n            loading.dismiss();\r\n            return;\r\n          });\r\n        case FileTypeId.FinvoiceFile:\r\n          return (reader.getFinvoiceData ?? ((x) => this.getFinvoiceData(x)))(arr).then((finvoiceArr) => {\r\n            if (finvoiceArr.length === 1 && !preferZip) {\r\n              saveAs(finvoiceArr[0], `${this.getFileName(arr[0])}.xml`);\r\n              loading.dismiss();\r\n              return;\r\n            } else {\r\n              let counter = 0;\r\n              const zip = new JSZip();\r\n              const next = () => {\r\n                if (counter === finvoiceArr.length) {\r\n                  return;\r\n                }\r\n                zip.file(`${this.getFileName(arr[counter])}.xml`, finvoiceArr[counter]);\r\n                counter++;\r\n                next();\r\n              };\r\n\r\n              next();\r\n              return zip.generateAsync({\r\n                type: \"blob\",\r\n                mimeType:\r\n                  \"application/zip\",\r\n              }).then((blob) => {\r\n                saveAs(blob, `${this.getZipFileName(arr)}.zip`);\r\n                loading.dismiss();\r\n                return;\r\n              });\r\n            }\r\n          });\r\n          break;\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Create single invoice.\r\n   * @param channel Payment channel.\r\n   * @param invoiceType Invoice type.\r\n   * @returns New/updated invoice.\r\n   */\r\n  public createSingleInvoice(channel: PaymentChannel, invoiceType: InvoiceType): Promise<Invoice> {\r\n    const loading = this.uiHelpers.showLoading();\r\n    return this.ajax.postJSON(`/v03/api/invoices/create/${channel}/${invoiceType}?month=${Dates.format(new Date(),\"YYYY-MM-01\")}`, null).then((invoice) => {\r\n      loading.dismiss();\r\n      return this.uiHelpers.showAlert(\"Lasku luotu\",\"Päivitä lista.\").then(() => invoice);\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Returns the file type definition\r\n   * @param fileTypeId File type id.\r\n   */\r\n  public getFileType(fileTypeId: string) {\r\n    return this.fileTypes.find((x) => x.id === fileTypeId);\r\n  }\r\n\r\n\r\n  private getFileName(invoice: Invoice) {\r\n    return Texts.escapeFileName(`${Translations.get(\"SALAXY.UI_Terms.downLoadableMaterialTypes.payment\")}_${invoice.payer.avatar.displayName}_${invoice.id}`);\r\n  }\r\n\r\n  private getZipFileName(invoices: Invoice[]) {\r\n    return Texts.escapeFileName(`${Translations.get(\"SALAXY.UI_Terms.downLoadableMaterialTypes.payments\")}${invoices[0].payer.avatar.displayName}_${Dates.format(\"today\",\"YYYYMMDD\")}`);\r\n  }\r\n\r\n  private getWorkflowMessage() {\r\n    const fileType = this.getFileType(this.fileTypeId);\r\n    if (fileType) {\r\n      return fileType.workflowMessage;\r\n    }\r\n    return null;\r\n  }\r\n\r\n  private getPdfData(invoices: Invoice[]): Promise<Blob[]> {\r\n    const promises = invoices.map(x => this.download(\"/v03/api/invoices/content\", x, \"blob\"));\r\n    return Promise.all(promises);\r\n  }\r\n\r\n  private getFinvoiceData(invoices: Invoice[]): Promise<Blob[]> {\r\n    const promises = invoices.map(x => this.download(\"/v03/api/invoices/finvoice\", x, \"blob\"));\r\n    return Promise.all(promises);\r\n  }\r\n\r\n  private getSepaData(invoices: Invoice[], payerIbanNumber: string = null): Promise<string> {\r\n    const version = this.fileTypeId === FileTypeId.SepaFileV03 || this.fileTypeId === FileTypeId.SepaCopyV03 ? \"pain.001.001.03\" : \"pain.001.001.02\";\r\n    const method = `/v03/api/invoices/sepa?version=${version}${payerIbanNumber ? \"&payerIbanNumber=\" + encodeURIComponent(payerIbanNumber) : \"\"}`;\r\n    return this.download(method, invoices, \"text\");\r\n  }\r\n  private download(method: string, data: any, responseType: string): Promise<any> {\r\n\r\n    const request: any = {}; // angular.IRequestConfig\r\n\r\n    const token: string = this.ajax.getCurrentToken();\r\n    if (token) {\r\n      request.headers = { Authorization: \"Bearer \" + token };\r\n    }\r\n\r\n    request.url = this.ajax.getServerAddress() + method;\r\n    request.method = \"POST\";\r\n    request.data = data;\r\n    request.responseType = responseType;\r\n    request.withCredentials = (token) ? false : this.ajax.useCredentials;\r\n\r\n    return (this.$http(request).then(\r\n      (response) => response.data,\r\n      (error: any) => {\r\n        return null;\r\n      }) as any\r\n    );\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { AccountInIndex, Ajax, Avatar, Dates, Invoice, InvoiceListItem, Invoices, InvoicesLogic, InvoiceStatus, InvoiceType, Numeric, PaymentChannel, SystemRole, ODataQueryOptions,Translations, Promises, BicHelper, Arrays } from \"@salaxy/core\";\r\nimport { Barcodes, QrCodes } from \"@salaxy/reports\";\r\nimport { InvoicesService, SessionService, UiHelpers } from \"../../services\";\r\nimport { InvoiceCrudController } from \"./InvoiceCrudController\";\r\n\r\n\r\ntype GroupedItem = {\r\n  /** Group identifier / key */\r\n  id: string,\r\n  /** Owner (employer) info */\r\n  ownerInfo: AccountInIndex,\r\n  /** Invoice type */\r\n  invoiceType: InvoiceType,\r\n  /** Status of the payments */\r\n  status: InvoiceStatus,\r\n  /** Due date of the payments */\r\n  dueDate: string,\r\n  /** Total payment for the group */\r\n  payment: number,\r\n  /** Payment channel for the group. */\r\n  channel: string,\r\n  /** Key data of the invoices */\r\n  invoices: any[],\r\n}\r\n/**\r\n * Extends the InvoiceCrudController to provide\r\n * SEPA payment management functionality.\r\n */\r\nexport class InvoiceSepaController extends InvoiceCrudController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   */\r\n  public static $inject = [\r\n    \"Invoices\",\r\n    \"UiHelpers\",\r\n    \"$location\",\r\n    \"$routeParams\",\r\n    \"InvoicesService\",\r\n    \"AjaxNg1\",\r\n    \"SessionService\",\r\n    \"$http\",\r\n    \"$timeout\",\r\n    \"$sce\"\r\n  ];\r\n\r\n    /** URL for the OData list service, null for preventing automatic initial load */\r\n    public get odataServiceUrl(): string {\r\n      return null;\r\n    }\r\n\r\n  /** List items grouped by owner, invoiceType, status and dueDate */\r\n  public groupedItems: Array<GroupedItem>;\r\n\r\n  /** Year for invoices query */\r\n  public queryYear = Dates.getToday();\r\n\r\n  /** Status filters for invoices */\r\n  public invoiceEntityTypes = [\r\n    { label: Translations.get(\"SALAXY.NG1.InvoicesComponent.all\"), value: \"all\" },\r\n    { label: Translations.get(\"SALAXY.ENUM.InvoiceType.net.label\"), value: \"net\" },\r\n    { label: Translations.get(\"SALAXY.ENUM.InvoiceType.pension.label\"), value: \"pension\" },\r\n    { label: Translations.get(\"SALAXY.ENUM.InvoiceType.tax.label\"), value: \"tax\" },\r\n    { label: Translations.get(\"SALAXY.ENUM.InvoiceType.unemployment.label\"), value: \"unemployment\" },\r\n    { label: Translations.get(\"SALAXY.ENUM.InvoiceType.union.label\"), value: \"union\" },\r\n    { label: Translations.get(\"SALAXY.ENUM.InvoiceType.payroll.label\"), value: \"payroll\" },\r\n  ];\r\n\r\n  /** Invoice entity type used in filtering */\r\n  public invoiceEntityType = this.invoiceEntityTypes.find((x) => x.value === \"all\");\r\n\r\n  /** The current status filter. \"waitingConfirmation\" is the default. */\r\n  public statusFilter = this.statusFilters.find((x) => x.value === \"waitingConfirmation\");\r\n\r\n  /** Default sepa channel */\r\n  public sepaChannel:PaymentChannel;\r\n\r\n  private _allChannels: Avatar[] = null;\r\n\r\n  private qrCodesCache: { [key: string]: string } = {};\r\n\r\n  constructor(\r\n    invoicesFullApi: Invoices,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    private invService: InvoicesService,\r\n    private sepaAjax: Ajax,\r\n    private session: SessionService,\r\n    private $http: angular.IHttpService,\r\n    private $timeout: angular.ITimeoutService,\r\n    private $sce: angular.ISCEService\r\n  ) {\r\n    // Dependency injection\r\n    super(invoicesFullApi, uiHelpers, $location, $routeParams, invService, sepaAjax);\r\n  }\r\n\r\n  /** Intitializes the controller */\r\n  public $onInit() {\r\n    this.sepaChannel ??= this.invService.defaultSepaChannel;\r\n    super.$onInit();\r\n    this.loadData();\r\n  }\r\n\r\n  /**\r\n   * Loads the data for the controller.\r\n   */\r\n  public loadData() {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.loading\");\r\n    this.loadAllInvoices().then((items) => {\r\n      this.updateGroupedItems(items);\r\n      loading.dismiss();\r\n      this.$timeout();\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Loads all invoices from the server.\r\n   * @returns Promise of all invoices\r\n   */\r\n  public async loadAllInvoices(): Promise<InvoiceListItem[]> {\r\n    const items: any[] = [];\r\n    const loadItems = (nextPageLink: string = null): Promise<string> => {\r\n      let options: ODataQueryOptions = {$filter: `data/channel eq '${this.sepaChannel}' and endAt ge ${Dates.getYear(this.queryYear)}-01-01 and endAt le ${Dates.getYear(this.queryYear)}-12-31`, $orderby: \"id\"};\r\n      const queryString = nextPageLink?.indexOf(\"?\") ?? -1;\r\n      if (queryString >= 0) {\r\n        const searchParams = new URLSearchParams(nextPageLink.substr(queryString));\r\n        if (searchParams.get(\"$skip\")) {\r\n          options = { $skip:  Number(searchParams.get(\"$skip\")), $filter: `data/channel eq '${this.sepaChannel}' and endAt ge ${Dates.getYear(this.queryYear)}-01-01 and endAt le ${Dates.getYear(this.queryYear)}-12-31`, $orderby: \"id\"};\r\n        }\r\n      }\r\n      return this.invoicesApi.getOData(options).then((data) => {\r\n        items.push(...data.items);\r\n        return data.nextPageLink ? loadItems(data.nextPageLink) : null;\r\n      });\r\n    };\r\n\r\n    return loadItems().then(() => {\r\n      return Arrays.distinct(items, (item) => item.id).sort((a, b) => a.endAt > b.endAt ? -1 : 1);\r\n    });\r\n\r\n  }\r\n\r\n  /**\r\n   * Shows a dialog for a group of invoices.\r\n   * @param group Group of invoices as defined in groupedItems.\r\n   */\r\n  public showGroupDialog(group: any) {\r\n    this.uiHelpers.openEditDialog(\"salaxy-components/modals/invoices/invoice-group-dialog.html\", group, { parent: this }, \"xl\");\r\n  }\r\n\r\n  /**\r\n   * Shows a dialog for a single invoice.\r\n   * @param item Invoice item.\r\n   */\r\n  public showInvoiceDialog(item: InvoiceListItem) {\r\n    this.uiHelpers.openEditDialog(\"salaxy-components/modals/invoices/invoice-dialog.html\", item, { parent: this }, \"xl\");\r\n  }\r\n\r\n  /** Filter function for angularjs filter used in template */\r\n  public invoiceFilter = (value: InvoiceListItem | any) => {\r\n    if(this.statusFilter.value === \"all\" && this.invoiceEntityType.value === \"all\") {\r\n      return true;\r\n    }\r\n\r\n    if(this.invoiceEntityType.value !== \"all\" && value.invoiceType !== this.invoiceEntityType.value) {\r\n      return false;\r\n    }\r\n\r\n    const statuses = {\r\n      waitingConfirmation: [InvoiceStatus.Unread, InvoiceStatus.Read, InvoiceStatus.WaitingConfirmation],\r\n      paid: [InvoiceStatus.Paid, InvoiceStatus.PaymentStarted, InvoiceStatus.Canceled],\r\n      forecast: [InvoiceStatus.Forecast, InvoiceStatus.Preview]\r\n    };\r\n\r\n    if (statuses[this.statusFilter.value]?.indexOf(value.status) === -1) {\r\n      return false;\r\n    }\r\n\r\n    return true;\r\n  };\r\n\r\n  /** Gets the grouped items, creating them if necessary. */\r\n  public getGroupedItems() {\r\n    return this.groupedItems;\r\n  }\r\n\r\n  /**\r\n   * Checks if a group contains any duplicate invoices based on their IDs.\r\n   * Iterates through each invoice in the group and checks if there are multiple invoices\r\n   * with the same ID across all grouped items.\r\n   * @param group - The group of invoices to check for duplicates.\r\n   * @returns {boolean} - Returns true if any duplicate invoice IDs are found, otherwise false.\r\n   */\r\n  public groupHasDuplicateInvoices(group: GroupedItem): boolean {\r\n    const allInvoices = this.getGroupedItems().flatMap(g => g.invoices);\r\n    for (const groupInvoice of group.invoices) {\r\n      const invoicesWithSameId = allInvoices.filter(invoice => invoice.id === groupInvoice.id);\r\n      if (invoicesWithSameId.length > 1) {\r\n        console.log(\"duplicate invoices\", invoicesWithSameId);\r\n        return true;\r\n      }\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /** Updates the grouped items based on the ODataQueryController.  */\r\n  public updateGroupedItems(items: InvoiceListItem[]) {\r\n    this.groupedItems = [];\r\n    items.forEach((l) => {\r\n      const id = l.ownerId + l.entityType + l.status + l.data.dueDate + l.data.channel;\r\n      let group = this.groupedItems.find((x) => x.id === id);\r\n      if (!group) {\r\n        group = {\r\n          id: id,\r\n          ownerInfo: l.ownerInfo,\r\n          invoiceType: l.entityType as InvoiceType,\r\n          status: l.status,\r\n          dueDate: l.data.dueDate,\r\n          payment: 0,\r\n          channel: l.data.channel,\r\n          invoices: [],\r\n        };\r\n        this.groupedItems.push(group);\r\n      }\r\n      group.payment += l.payment;\r\n      group.invoices.push(l);\r\n    });\r\n  }\r\n\r\n  /** Data reader for one item. */\r\n  public getGroupDataReader = (\r\n    group:\r\n      {\r\n        /** invoices */\r\n        invoices: InvoiceListItem[],\r\n      },\r\n    status: InvoiceStatus) => {\r\n    return {\r\n      /** Function to read data into given array */\r\n      read: (arr: Invoice[], message: string): Promise<void> => {\r\n        const showConfirmation = (): Promise<boolean> => {\r\n          const warning = this.getEprWarning(group.invoices, status);\r\n          if (warning) {\r\n            return this.uiHelpers.showConfirm(\"Huomioi palkkatietoilmoitukset!\", warning);\r\n          }\r\n          return Promise.resolve(true);\r\n        };\r\n        return showConfirmation().then((result) => {\r\n          if (result) {\r\n            (group as any)[\"isReading\" + (status || \"\")] = true;\r\n            const promises = group.invoices.map((x) => () => this.getInvoice(x, message, status));\r\n            return Promises.sequence(promises).then( (invoices) => {\r\n              arr.push(...invoices.filter(i => !!i));\r\n              (group as any)[\"isReading\" + (status || \"\")] = false;\r\n              if (status) {\r\n                (group as any).status = status;\r\n              }\r\n              return;\r\n            });\r\n          } else {\r\n            return;\r\n          }\r\n        });\r\n      },\r\n      getSepaData: (\r\n        /** Array for invoices */\r\n        arr: Invoice[],\r\n      ): Promise<string> => this.getSepaData(arr),\r\n      getFinvoiceData: (\r\n        /** Array for invoices */\r\n        arr: Invoice[],\r\n      ): Promise<Blob[]> => this.getFinvoiceData(arr),\r\n      getPdfData: (\r\n        /** Array for invoices */\r\n        arr: Invoice[],\r\n      ): Promise<Blob[]> => this.getPdfData(arr),\r\n      /** Optional label for data export */\r\n      exportLabel: null,\r\n      /** Indicates if the export is not possible */\r\n      disabled: () => false,\r\n    };\r\n  };\r\n\r\n  /** Data reader for one item. */\r\n  public getGroupItemDataReader = (item: InvoiceListItem, status: InvoiceStatus) => {\r\n    return {\r\n      /** Function to read data into given array */\r\n      read: (arr: Invoice[], message: string): Promise<void> => {\r\n        const showConfirmation = (): Promise<boolean> => {\r\n          const warning = this.getEprWarning([item], status);\r\n          if (warning) {\r\n            return this.uiHelpers.showConfirm(\"Huomioi palkkatietoilmoitukset!\", warning);\r\n          }\r\n          return Promise.resolve(true);\r\n        };\r\n        return showConfirmation().then((result) => {\r\n          if (result) {\r\n            (item as any)[\"isReading\" + (status || \"\")] = true;\r\n            return this.getInvoice(item, message, status).then((data) => {\r\n              if (data) {\r\n                arr.push(data);\r\n              }\r\n              (item as any)[\"isReading\" + (status || \"\")] = false;\r\n              return;\r\n            });\r\n          } else {\r\n            return;\r\n          }\r\n        });\r\n      },\r\n      getSepaData: (\r\n        /** Array for invoices */\r\n        arr: Invoice[],\r\n      ): Promise<string> => this.getSepaData(arr),\r\n      getFinvoiceData: (\r\n        /** Array for invoices */\r\n        arr: Invoice[],\r\n      ): Promise<Blob[]> => this.getFinvoiceData(arr),\r\n      getPdfData: (\r\n        /** Array for invoices */\r\n        arr: Invoice[],\r\n      ): Promise<Blob[]> => this.getPdfData(arr),\r\n      /** Optional label for data export */\r\n      exportLabel: null,\r\n      /** Indicates if the export is not possible */\r\n      disabled: () => false,\r\n    };\r\n  };\r\n\r\n  /**\r\n   * Returns PDF url for a single invoice.\r\n   * @param item Invoice list item.\r\n   */\r\n  public getPdfUrl(item: InvoiceListItem): string {\r\n    if (!(item as any).pdfUrl) {\r\n        (item as any).pdfUrl = (this.api as Invoices).getContentUrl(item.id, false);\r\n    }\r\n    return (item as any).pdfUrl;\r\n  }\r\n\r\n  /**\r\n   * Retrieves the QR code for the specified invoice item.\r\n   * If the QR code is not already cached, it generates the QR code and caches it for future use.\r\n   * @param item - The invoice item for which to retrieve the QR code.\r\n   * @returns The QR code string.\r\n   */\r\n  public getQrCode(item: InvoiceListItem): string {\r\n    if(!this.qrCodesCache[item.id]) {\r\n      this.qrCodesCache[item.id] = \"loading\";\r\n      this.generateQrCodeSvgForInvoice(item).then((qrCode) => {\r\n        if(!qrCode) {\r\n          this.qrCodesCache[item.id] = \"error\";\r\n          this.$timeout();\r\n          return this.qrCodesCache[item.id];\r\n        } else {\r\n          this.qrCodesCache[item.id] = qrCode;\r\n          this.$timeout();\r\n          return this.$sce.trustAsHtml(this.qrCodesCache[item.id]);\r\n        }\r\n      });\r\n    }\r\n    if(this.qrCodesCache[item.id] === \"error\") {\r\n      return this.qrCodesCache[item.id];\r\n    }\r\n    return this.$sce.trustAsHtml(this.qrCodesCache[item.id]);\r\n  }\r\n\r\n  /**\r\n   * Calculates barcode value for the invoice item.\r\n   * @param item Invoice list item.\r\n   */\r\n  public getBarcodeValue(item: InvoiceListItem): string {\r\n    return Barcodes.getValue(\r\n      item.otherPartyInfo.ibanNumber || \"\",\r\n      (item as any).reference || \"\",\r\n      Dates.asDate(item.data.dueDate),\r\n      Numeric.round(item.payment * 100, 0));\r\n  }\r\n\r\n  /**\r\n   * Retrieves the barcode for the invoice recipient's IBAN.\r\n   * If the IBAN does not start with \"fi\" or is not provided, an empty string is returned.\r\n   * The barcode is generated using the Barcodes.createBarcode function.\r\n   * @returns The barcode as a string, wrapped in an HTML trust object.\r\n   */\r\n  public getBarcode(item: InvoiceListItem): string {\r\n    if (!item.otherPartyInfo.ibanNumber || !item.otherPartyInfo.ibanNumber.toLowerCase().trim().startsWith(\"fi\")) {\r\n      return \"\";\r\n    }\r\n    const getDocumentAndSvgNode = () => {\r\n      return {document, svgNode: document.createElementNS(\"http://www.w3.org/2000/svg\", \"svg\")};\r\n    };\r\n\r\n    const result = Barcodes.createBarcode(\r\n      getDocumentAndSvgNode,\r\n      item.otherPartyInfo.ibanNumber || \"\",\r\n      (item as any).reference || \"\",\r\n      Dates.asDate(item.data.dueDate),\r\n      Numeric.round(item.payment * 100, 0),\r\n      {\r\n        width: 1.8,\r\n        height: 32,\r\n        displayValue: true,\r\n        fontSize: 15\r\n      }\r\n    );\r\n    if(!result) {\r\n      return \"\";\r\n    }\r\n    return this.$sce.trustAsHtml(new XMLSerializer().serializeToString(result as any));\r\n  }\r\n\r\n  /** Hides bar code for forecast and preview invoice statuses*/\r\n  public hideBarCode(item: InvoiceListItem): boolean {\r\n    if(item.status === InvoiceStatus.Forecast || item.status === InvoiceStatus.Preview) {\r\n      return true;\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /**\r\n   * Copies the barcode to clipboard.\r\n   * @param item Invoice list item.\r\n   */\r\n  public copyBarcode(item: InvoiceListItem) {\r\n    (navigator as any).clipboard.writeText(this.getBarcodeValue(item));\r\n  }\r\n\r\n  /** Gets and avatar image for a payment channel */\r\n  public getChannelAvatar(channel: PaymentChannel) {\r\n    return InvoicesLogic.getChannelAvatar(channel);\r\n  }\r\n\r\n  /** Update status of invoices in group using the group data reader. */\r\n  public updateInvoiceGroupStatus(\r\n    group:\r\n      {\r\n        /** invoices */\r\n        invoices: InvoiceListItem[],\r\n      },\r\n    status: InvoiceStatus) {\r\n    const loading = this.uiHelpers.showLoading(\"Odota...\");\r\n    const reader = this.getGroupDataReader(group, status);\r\n    reader.read([], null).then(() => {\r\n      loading.dismiss();\r\n    });\r\n  }\r\n\r\n  /** Update status of single invoice using the group data reader. */\r\n  public updateInvoiceGroupItemStatus(item: InvoiceListItem, status: InvoiceStatus) {\r\n    const loading = this.uiHelpers.showLoading(\"Odota...\");\r\n    const reader = this.getGroupItemDataReader(item, status);\r\n    reader.read([], null).then(() => {\r\n      loading.dismiss();\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Gets all channels as avatars for drop-down.\r\n   */\r\n  public getAllChannels(): Avatar[] {\r\n    if (this.session.getSession() && this._allChannels === null) {\r\n      const settings = this.session.getSession().settings;\r\n      let available = (settings.paymentChannels || []);\r\n      if (settings.defaultPaymentChannel) {\r\n        available = available.filter((x) => x !== settings.defaultPaymentChannel);\r\n        available.unshift(settings.defaultPaymentChannel);\r\n      }\r\n      if (available.indexOf(PaymentChannel.ZeroPayment) < 0) {\r\n        available.push(PaymentChannel.ZeroPayment);\r\n      }\r\n      this._allChannels = available\r\n        .map((x) => InvoicesLogic.getChannelAvatar(x));\r\n    }\r\n    return this._allChannels;\r\n  }\r\n\r\n  /**\r\n   * Summs payment fields of InvoiceListImte array\r\n   * @returns summed values\r\n   */\r\n  public sumInvoicePayments(invoices: Array<InvoiceListItem>) {\r\n    let sum = 0;\r\n    invoices.forEach(invoice => {\r\n      sum += invoice.payment;\r\n    });\r\n    return sum;\r\n  }\r\n\r\n  private getInvoice(item: InvoiceListItem, message: any, status: InvoiceStatus = null): Promise<Invoice> {\r\n\r\n    const updateInvoiceStatus = (invoice: Invoice, status: InvoiceStatus): Promise<Invoice> => {\r\n      if (invoice.header.status === status) {\r\n        return Promise.resolve(invoice);\r\n      }\r\n      return (this.api as Invoices).requestStatusUpdate(item.id, status);\r\n    };\r\n\r\n    return this.api.getSingle(item.id)\r\n      .then((readInvoice: Invoice) => {\r\n        if (status) {\r\n          return updateInvoiceStatus(readInvoice, status).then((updatedInvoice) => {\r\n            item.status = updatedInvoice.header.status;\r\n            return updatedInvoice;\r\n          });\r\n        } else {\r\n          return readInvoice;\r\n        }\r\n      });\r\n  }\r\n\r\n  private async getPdfData(invoices: Invoice[]): Promise<Blob[]> {\r\n    const blobs: Blob[] = [];\r\n    const loader = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.loading\");\r\n    for (const [index, invoice] of invoices.entries()) {\r\n      const blob = await this.download(\"/v03/api/invoices/content\", invoice, \"blob\");\r\n      loader.setText(`${index}/${invoices.length}`);\r\n      blobs.push(blob);\r\n    }\r\n    loader.dismiss();\r\n    return blobs;\r\n  }\r\n\r\n  private async getFinvoiceData(invoices: Invoice[]): Promise<Blob[]> {\r\n    const blobs: Blob[] = [];\r\n    const loader = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.loading\");\r\n    for (const [index, invoice] of invoices.entries()) {\r\n      const blob = await this.download(\"/v03/api/invoices/finvoice\", invoice, \"blob\");\r\n      loader.setText(`${index}/${invoices.length}`);\r\n      blobs.push(blob);\r\n    }\r\n    loader.dismiss();\r\n    return blobs;\r\n  }\r\n\r\n  private getSepaData(invoices: Invoice[], payerIbanNumber: string = null): Promise<string> {\r\n    const method = `/v03/api/invoices/sepa${payerIbanNumber ? \"?payerIbanNumber=\" + encodeURIComponent(payerIbanNumber) : \"\"}`;\r\n    return this.download(method, invoices, \"text\");\r\n  }\r\n  private download(method: string, data: any, responseType: string): Promise<any> {\r\n\r\n    const request: any = {}; // angular.IRequestConfig\r\n\r\n    const token: string = this.sepaAjax.getCurrentToken();\r\n    if (token) {\r\n      request.headers = { Authorization: \"Bearer \" + token };\r\n    }\r\n\r\n    request.url = this.sepaAjax.getServerAddress() + method;\r\n    request.method = \"POST\";\r\n    request.data = data;\r\n    request.responseType = responseType;\r\n    request.withCredentials = (token) ? false : this.sepaAjax.useCredentials;\r\n\r\n    return (this.$http(request).then(\r\n      (response) => response.data,\r\n      (error: any) => {\r\n        return null;\r\n      }) as any\r\n    );\r\n  }\r\n\r\n\r\n  private getEprWarning(items: InvoiceListItem[], status: InvoiceStatus): string {\r\n    if (status === InvoiceStatus.Canceled) {\r\n      for (const item of items) {\r\n        if (item.status === InvoiceStatus.Paid &&\r\n          item.entityType == InvoiceType.Net &&\r\n          this.isDelayed(item.logicalDate)) {\r\n          return \"Palkanmaksusta tehdyt tulorekisteri-ilmoitukset perutaan automaattisesti.\\n\\nJos maksat palkan uudestaan samalle palkkapäivälle, ota huomioon, että uudesta palkkatietoilmoituksesta saattaa seurata myöhästymismaksu. Haluatko varmasti perua maksut?\";\r\n        }\r\n      }\r\n    } else if (status === InvoiceStatus.Paid) {\r\n      for (const item of items) {\r\n        if (item.status !== InvoiceStatus.Paid &&\r\n          item.entityType == InvoiceType.Net &&\r\n          this.isDelayed(item.logicalDate)) {\r\n          return \"Annetulle palkkapäivälle tehtävä palkkatietoilmoitus myöhästyy, koska ilmoitus pitää tehdä 5 päivän kuluessa palkkapäivästä. Ota huomioon, että tästä saattaa seurata myöhästymismaksu. Haluatko varmasti merkitä palkan maksetuiksi?\";\r\n        }\r\n      }\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /** Checks if the Epr report is delayed. */\r\n  private isDelayed(salaryDate?: string): boolean {\r\n    if (this.session.isInRole(SystemRole.Test)) {\r\n      const officialDate = Dates.add((salaryDate ?? \"today\"),5, \"day\");\r\n      const expiresAt = Dates.addWorkdays(officialDate, 0);\r\n      const today = Dates.asDate(\"today\");\r\n      return today>expiresAt;\r\n    }\r\n    return false;\r\n  }\r\n\r\n  private async generateQrCodeSvgForInvoice(item: InvoiceListItem): Promise<string> {\r\n    const svg = await QrCodes.getValue(\r\n     BicHelper.getBicForIban(item.otherPartyInfo.ibanNumber.replace(/\\s+/g, \"\")),\r\n     item.otherPartyInfo.avatar.displayName,\r\n     item.otherPartyInfo?.ibanNumber,\r\n     item.reference,\r\n     null,\r\n     item.payment,\r\n     item.endAt\r\n   );\r\n   return svg;\r\n }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {\r\n  Language,\r\n  Translations,\r\n  Invoice,\r\n  InvoiceType,\r\n  InvoiceStatus\r\n} from \"@salaxy/core\";\r\nimport { SessionService } from \"../../services\";\r\nimport {\r\n  InvoiceMapper,\r\n  ReportData,\r\n  ReportOptions,\r\n  Templates,\r\n  MappedInvoice\r\n} from \"@salaxy/reports\";\r\n\r\n\r\n/**\r\n * Renders a invoice report for the given invoice.\r\n * Uses Handlebars templates (@salaxy/reports).\r\n */\r\nexport class InvoiceReportController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"Templates\",\r\n    \"$sce\",\r\n    \"$timeout\",\r\n    \"SessionService\",\r\n  ];\r\n\r\n  /** Invoice for the report */\r\n  public invoice: Invoice;\r\n  /** If true applies table-html classes and uses only invoice table */\r\n  public applySiteStyles: boolean;\r\n\r\n  /** Boolean indicating if the refresh is in progress. */\r\n  public refreshInprogress: boolean;\r\n\r\n  /**Selected report language */\r\n  public lang: Language;\r\n\r\n  private renderedInvoice: Invoice;\r\n\r\n  private renderedLang: string;\r\n\r\n  private renderedApplySiteStyles: boolean;\r\n\r\n  private htmlData: any;\r\n\r\n  private reportOptions: ReportOptions;\r\n\r\n  private reportData: ReportData<MappedInvoice> = {\r\n    headerFooter: {},\r\n    layout: {},\r\n    report: {},\r\n  };\r\n\r\n  /**\r\n   * Creates a new InvoiceReportController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    private templates: Templates,\r\n    private $sce: angular.ISCEService,\r\n    private $timeout: angular.ITimeoutService,\r\n    private sessionService: SessionService\r\n  ) {\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    // no initializations\r\n  }\r\n\r\n  /** Bindable and trusted html. */\r\n  public get html(): any {\r\n    if (!this.invoice) {\r\n      this.renderedInvoice = null;\r\n      this.renderedLang = null;\r\n      this.renderedApplySiteStyles = null;\r\n    } else {\r\n      const invoice = angular.copy(this.invoice);\r\n\r\n      if (!this.renderedInvoice ||\r\n        !angular.equals(invoice, this.renderedInvoice) ||\r\n        this.renderedLang !== this.lang ||\r\n        this.applySiteStyles !== this.renderedApplySiteStyles) {\r\n        this.renderedApplySiteStyles = this.applySiteStyles;\r\n        this.renderedInvoice = angular.copy(invoice);\r\n        this.renderedLang = this.lang;\r\n        this.getDefaultLanguage(this.lang).then((lang) => {\r\n          this.lang = lang;\r\n          this.renderedLang = this.lang;\r\n          this.refresh();\r\n        });\r\n      }\r\n    }\r\n    return this.htmlData;\r\n  }\r\n\r\n  /** Checks if invoice is preview */\r\n  public isPreviewInvoice(): boolean {\r\n    return (\r\n      [InvoiceType.Pension, InvoiceType.Unemployment].includes(\r\n        this.invoice.header.type\r\n      ) &&\r\n      [InvoiceStatus.Preview, InvoiceStatus.Forecast].includes(\r\n        this.invoice.header.status\r\n      )\r\n    );\r\n  }\r\n\r\n  /**\r\n   * Refresh invoice report data.\r\n   */\r\n  private async refresh() {\r\n    if (this.refreshInprogress) {\r\n      return;\r\n    }\r\n    this.refreshInprogress = true;\r\n    const renderingLang = this.lang ?? Language.Fi;\r\n    await Translations.loadLanguage(renderingLang);\r\n    this.reportData.report = await InvoiceMapper.getInvoice(this.invoice, this.getDocumentAndSvgNode);\r\n    if(this.reportData.report.barcode) {\r\n      this.reportData.report.barcode = new XMLSerializer().serializeToString(this.reportData.report.barcode as any);\r\n    }\r\n    this.reportOptions = InvoiceMapper.loadReportOptions(angular.copy(this.invoice));\r\n    this.reportData.headerFooter = InvoiceMapper.getHeaderFooter(this.invoice, this.reportOptions, renderingLang);\r\n    this.reportData.layout = InvoiceMapper.loadReportLayout(false);\r\n    const css = \"\";\r\n    this.reportData.layout.hasCustomCss = false;\r\n    this.reportData.layout.customCss = (css || \"\");\r\n    this.reportData.layout.margin = {\r\n      top: this.reportOptions.margin.top,\r\n      right: this.reportOptions.margin.right,\r\n      bottom: this.reportOptions.margin.bottom,\r\n      left: this.reportOptions.margin.left\r\n    };\r\n    const templates = new Templates();\r\n    this.reportData.headerHtml = this.reportOptions?.headerTemplate ? templates.getHtmlDynamic(this.reportOptions.headerTemplate, this.reportData.headerFooter, renderingLang) : \"\";\r\n    this.reportData.footerHtml = this.reportOptions?.headerTemplate ? templates.getHtmlDynamic(this.reportOptions.footerTemplate, this.reportData.headerFooter, renderingLang) : \"\";\r\n    this.htmlData = this.$sce.trustAsHtml(this.templates.getHtml(this.applySiteStyles ? \"invoiceTable\" : \"invoice\", this.reportData, renderingLang));\r\n    this.refreshInprogress = false;\r\n    this.$timeout();\r\n  }\r\n\r\n  private getDocumentAndSvgNode() {\r\n    return {document, svgNode: document.createElementNS(\"http://www.w3.org/2000/svg\", \"svg\")};\r\n  }\r\n\r\n  private async getDefaultLanguage(lang: Language): Promise<Language> {\r\n    if (!lang) {\r\n      return this.sessionService.getReportLang();\r\n    }\r\n    return Promise.resolve(lang);\r\n  }\r\n\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {\r\n  Ajax,\r\n  Dates,\r\n  InputEnumOption,\r\n  Invoice,\r\n  InvoiceListItem,\r\n  Invoices,\r\n  InvoiceStatus,\r\n  InvoiceType,\r\n  Numeric,\r\n  PaymentChannel,\r\n  SystemRole,\r\n  Translations,\r\n  BicHelper,\r\n  Configs,\r\n} from \"@salaxy/core\";\r\nimport { Barcodes, QrCodes } from \"@salaxy/reports\";\r\nimport { InvoicesService, SessionService, UiHelpers } from \"../../services\";\r\nimport { InvoiceCrudController } from \"./InvoiceCrudController\";\r\n/**\r\n * Extends the InvoiceCrudController to provide\r\n * company invoices handling functionality.\r\n */\r\nexport class CompanyInvoicesController extends InvoiceCrudController {\r\n  /**\r\n   * For NG-dependency injection\r\n   */\r\n  public static $inject = [\r\n    \"Invoices\",\r\n    \"UiHelpers\",\r\n    \"$location\",\r\n    \"$routeParams\",\r\n    \"InvoicesService\",\r\n    \"AjaxNg1\",\r\n    \"SessionService\",\r\n    \"$http\",\r\n    \"$timeout\",\r\n    \"$sce\",\r\n  ];\r\n\r\n  /** Default channel for payments */\r\n  public channel: PaymentChannel;\r\n\r\n  /** Month for invoices query */\r\n  private queryMonth = Dates.format(Dates.getToday(), \"YYYY-MM-01\");\r\n\r\n  /** Queries for lists: Groups statuses to logical groups. */\r\n  public queryOptions: InputEnumOption[] = [\r\n    {\r\n      value: \"unpaid\",\r\n      text: Translations.get(\r\n        \"SALAXY.NG1.InvoicesComponent.statusWaitingConfirmation\"\r\n      ),\r\n      ui: () => ({\r\n        $filter: `data/channel eq '${this.channel}' and (entityType eq '${InvoiceType.Net}' or entityType eq '${InvoiceType.Foreclosure}' or entityType eq '${InvoiceType.Tax}' or  entityType eq '${InvoiceType.Union}' or  entityType eq '${InvoiceType.Payroll}') and ( status eq '${InvoiceStatus.Preview}' or status eq '${InvoiceStatus.Unread}' or status eq '${InvoiceStatus.Read}' or status eq '${InvoiceStatus.WaitingConfirmation}')`,\r\n        $top: undefined,\r\n        $orderby: \"endAt asc\",\r\n      }),\r\n    },\r\n    {\r\n      value: \"paid\",\r\n      text: Translations.get(\"SALAXY.NG1.InvoicesComponent.statusPaid\"),\r\n      ui: () => ({\r\n        $filter: `${\r\n          this.dateFilterQueryOption.ui().dateFilter\r\n        }data/channel eq '${\r\n          this.channel\r\n        }' and (entityType eq '${InvoiceType.Net}' or entityType eq '${\r\n          InvoiceType.Foreclosure\r\n        }' or entityType eq '${InvoiceType.Tax}' or  entityType eq '${\r\n          InvoiceType.Union\r\n        }' or  entityType eq '${InvoiceType.Payroll}') and ( status eq '${\r\n          InvoiceStatus.Paid\r\n        }' or status eq '${InvoiceStatus.PaymentStarted}' or status eq '${\r\n          InvoiceStatus.Canceled\r\n        }')`,\r\n        $top: undefined,\r\n        $orderby: \"endAt asc\",\r\n      }),\r\n    },\r\n    {\r\n      value: \"all\",\r\n      text: Translations.get(\"SALAXY.NG1.InvoicesComponent.statusAll\"),\r\n      ui: () => ({\r\n        $filter: `${\r\n          this.dateFilterQueryOption.ui().dateFilter\r\n        }data/channel eq '${\r\n          this.channel\r\n        }' and (entityType eq '${InvoiceType.Net}' or entityType eq '${\r\n          InvoiceType.Foreclosure\r\n        }' or entityType eq '${InvoiceType.Tax}' or  entityType eq '${\r\n          InvoiceType.Union\r\n        }' or  entityType eq '${InvoiceType.Payroll}') `,\r\n        $top: undefined,\r\n        $orderby: \"endAt asc\",\r\n      }),\r\n    },\r\n  ];\r\n\r\n  public queryDateFilterOptions: InputEnumOption[] = [\r\n    {\r\n      value: \"default\",\r\n      text: `${Dates.getMonth(Dates.add(this.queryMonth, -1, \"month\"))}-${Dates.getMonth(Dates.add(this.queryMonth, 1, \"month\"))}/${Dates.getYear(this.queryMonth)}`,\r\n      ui: () => ({\r\n        dateFilter: `endAt ge ${Dates.add(\r\n          this.queryMonth,\r\n          -1,\r\n          \"month\"\r\n        )} and endAt le ${Dates.startEnd(\r\n          Dates.add(this.queryMonth, 1, \"month\"),\r\n          \"end-month\"\r\n        )} and `,\r\n      }),\r\n    },\r\n    {\r\n      value: \"fromStartOfYear\",\r\n      text: `${Translations.get(\"SALAXY.UI_Terms.year\")} ${Dates.getYear(this.queryMonth)}`,\r\n      ui: () => ({\r\n        dateFilter: `endAt ge ${Dates.startEnd(\r\n          this.queryMonth,\r\n          \"start-year\"\r\n        )} and endAt le ${Dates.startEnd(\r\n          this.queryMonth,\r\n          \"end-year\"\r\n        )} and `,\r\n      }),\r\n    },\r\n    {\r\n      value: \"all\",\r\n      text: Translations.get(\"SALAXY.NG1.InvoicesCompany.queryFilterDateAll\"),\r\n      ui: () => ({\r\n        dateFilter: ``,\r\n      }),\r\n    },\r\n    {\r\n      value: \"other\",\r\n      text: Translations.get(\"SALAXY.NG1.InvoicesCompany.queryFilterDateOther\"),\r\n      ui: () => ({\r\n        dateFilter: ``,\r\n      }),\r\n    },\r\n  ];\r\n\r\n  /** The current query */\r\n  public queryOption: InputEnumOption = this.queryOptions[0];\r\n  public dateFilterQueryOption: InputEnumOption =\r\n    this.queryDateFilterOptions[0];\r\n\r\n  private qrCodesCache: { [key: string]: string } = {};\r\n\r\n  constructor(\r\n    invoicesApi: Invoices,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    invoiceService: InvoicesService,\r\n    private companyAjax: Ajax,\r\n    private session: SessionService,\r\n    private $http: angular.IHttpService,\r\n    private $timeout: angular.ITimeoutService,\r\n    private $sce: angular.ISCEService\r\n  ) {\r\n    // Dependency injection\r\n    super(\r\n      invoicesApi,\r\n      uiHelpers,\r\n      $location,\r\n      $routeParams,\r\n      invoiceService,\r\n      companyAjax\r\n    );\r\n  }\r\n\r\n  /** Intitializes the controller */\r\n  public $onInit() {\r\n    this.channel ||= PaymentChannel.PalkkausInvoices;\r\n    super.$onInit();\r\n  }\r\n\r\n  /** For list components, gets the OData query options. */\r\n  public getListOptions() {\r\n    return this.uiHelpers.cache(this, \"listOptions\", () => {\r\n      return this.queryOption.ui();\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Sets the date filter query option.\r\n   * @param option - The input enum option.\r\n   */\r\n  public setDateFilterQueryOption(option: InputEnumOption) {\r\n    const oldDateFilterQueryOption = this.dateFilterQueryOption;\r\n    this.dateFilterQueryOption = option;\r\n    if (this.dateFilterQueryOption.value !== \"other\") {\r\n      this.doQuery();\r\n    } else {\r\n      const logic = {\r\n        startDate: Dates.add(this.queryMonth, -1, \"month\"),\r\n        endDate: Dates.add(this.queryMonth, 1, \"month\"),\r\n      };\r\n      this.uiHelpers\r\n        .openEditDialog(\r\n          \"salaxy-components/modals/invoices/company-invoices-date-filter-dialog.html\",\r\n          null,\r\n          logic\r\n        )\r\n        .then((result) => {\r\n          if (result.action === \"ok\") {\r\n            this.dateFilterQueryOption.ui = () => ({\r\n              dateFilter: `endAt ge ${result.logic.startDate} and endAt le ${result.logic.endDate} and `,\r\n            });\r\n            this.dateFilterQueryOption.text = `Muu ${result.logic.startDate} - ${result.logic.endDate}`;\r\n            this.doQuery();\r\n          } else {\r\n            this.dateFilterQueryOption = oldDateFilterQueryOption;\r\n          }\r\n        });\r\n    }\r\n  }\r\n\r\n  /** Refreshes query */\r\n  public doQuery() {\r\n    this.odataController.setQueryOptions(this.queryOption.ui());\r\n    this.odataController.refresh();\r\n  }\r\n\r\n  /** Dropdown options for marking invoice as paid */\r\n  public getMarkAsPaidOptions(items: InvoiceListItem[]): InputEnumOption[] {\r\n    return this.uiHelpers.cache(\r\n      this,\r\n      \"markAsPaidOptions\",\r\n      () => {\r\n        const result: InputEnumOption[] = [];\r\n        const filterInvoices = (type: InvoiceType) =>\r\n          items.filter(\r\n            (item) =>\r\n              item.entityType === type &&\r\n              item.status !== InvoiceStatus.Paid &&\r\n              item.status !== InvoiceStatus.Canceled\r\n          );\r\n\r\n        const netInvoices = filterInvoices(InvoiceType.Net);\r\n        const taxInvoices = filterInvoices(InvoiceType.Tax);\r\n        const unionInvoices = filterInvoices(InvoiceType.Union);\r\n        const foreclosureInvoices = filterInvoices(InvoiceType.Foreclosure);\r\n        result.push({\r\n          value: \"all\",\r\n          text: Translations.get(\"SALAXY.NG1.InvoicesCompany.markAsPaidOptions.all\"),\r\n        });\r\n        if (netInvoices.length > 0) {\r\n          result.push({\r\n            value: InvoiceType.Net,\r\n            text: Translations.get(\"SALAXY.NG1.InvoicesCompany.markAsPaidOptions.netInvoices\"),\r\n          });\r\n        }\r\n\r\n        if (taxInvoices.length > 0) {\r\n          result.push({\r\n            value: InvoiceType.Tax,\r\n            text: Translations.get(\"SALAXY.NG1.InvoicesCompany.markAsPaidOptions.taxInvoices\"),\r\n          });\r\n        }\r\n\r\n        if (unionInvoices.length > 0) {\r\n          result.push({\r\n            value: InvoiceType.Union,\r\n            text: Translations.get(\"SALAXY.NG1.InvoicesCompany.markAsPaidOptions.unionInvoices\"),\r\n          });\r\n        }\r\n\r\n        if (foreclosureInvoices.length > 0) {\r\n          result.push({\r\n            value: InvoiceType.Foreclosure,\r\n            text: Translations.get(\"SALAXY.NG1.InvoicesCompany.markAsPaidOptions.foreclosureInvoices\"),\r\n          });\r\n        }\r\n        result.push({\r\n          value: \"removeAll\",\r\n          text: Translations.get(\"SALAXY.NG1.InvoicesCompany.markAsPaidOptions.removeAll\"),\r\n        });\r\n        return result;\r\n      },\r\n      () => items.map((item) => item.id)\r\n    );\r\n  }\r\n\r\n  /**\r\n   * Selects invoices of a specific type and marks them as selected.\r\n   * @param action - The type of invoices to select.\r\n   */\r\n  public selectInvoicesByType(action: InvoiceType | \"all\" | \"removeAll\") {\r\n    if(action === \"removeAll\") {\r\n      this.odataController.unselectAll();\r\n      return;\r\n    }\r\n\r\n    if(action === \"all\") {\r\n      this.odataController.selectAll();\r\n      return;\r\n    }\r\n\r\n    const invoices = this.odataController.items.filter(\r\n      (x) =>\r\n        x.entityType === action &&\r\n        x.status !== InvoiceStatus.Paid &&\r\n        x.status !== InvoiceStatus.Canceled\r\n    );\r\n    for (const invoice of invoices) {\r\n      this.odataController.setSelected(invoice, true);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Determines whether to show the \"Mark as Paid\" button for a given invoice.\r\n   * @param invoice - The invoice to check.\r\n   * @returns A boolean indicating whether to show the button.\r\n   */\r\n  public showMarkAsPaidButton(invoice: InvoiceListItem): boolean {\r\n    return (\r\n      invoice.status === InvoiceStatus.Preview ||\r\n      invoice.status === InvoiceStatus.Unread\r\n    );\r\n  }\r\n\r\n  /**\r\n   * Determines whether to show the \"Mark as Canceled\" button for a given invoice.\r\n   * @param invoice - The invoice to check.\r\n   * @returns A boolean indicating whether to show the button.\r\n   */\r\n  public showMarkAsCanceledButton(invoice: InvoiceListItem): boolean {\r\n    return (\r\n      invoice.status === InvoiceStatus.Paid ||\r\n      invoice.status === InvoiceStatus.Unread ||\r\n      invoice.status === InvoiceStatus.Preview\r\n    );\r\n  }\r\n\r\n  /**\r\n   * Determines whether to show the IR cancel information text for a given invoice.\r\n   * @param invoice - The invoice item to check.\r\n   * @returns `true` if the invoice entity type is `Net` and the status is `Paid`, otherwise `false`.\r\n   */\r\n  public showIrCancelInfoText(invoice: InvoiceListItem): boolean {\r\n    return invoice.entityType === InvoiceType.Net && invoice.status === InvoiceStatus.Paid;\r\n  }\r\n\r\n  /**\r\n   * Shows a dialog for a single invoice.\r\n   * @param item Invoice item.\r\n   */\r\n  public showInvoiceDialog(item: InvoiceListItem) {\r\n    this.uiHelpers\r\n      .openEditDialog(\r\n        \"salaxy-components/modals/invoices/company-invoice-dialog.html\",\r\n        item,\r\n        { parent: this },\r\n        \"lg\"\r\n      )\r\n      .then((response: any) => {\r\n        if (response.action === \"ok\") {\r\n          this.getInvoice(item, null, null).then((result) => {\r\n            (item.data as any).statusAt = (result.header as any).statusAt;\r\n            item.status = result.header.status;\r\n            this.refreshPeriodicInvoices();\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Marks selected invoices as paid.\r\n   * This method filters the selected invoices to exclude those that are already paid or canceled.\r\n   * It then shows a loading indicator and processes each invoice by marking it as paid.\r\n   * After processing all invoices, it refreshes the periodic invoices and dismisses the loading indicator.\r\n   * @returns A promise that resolves when the operation is complete.\r\n   */\r\n  public async markInvoicesAsPaid() {\r\n    const invoices = this.odataController.selectedItems.filter(\r\n      (item) =>\r\n        item.status != InvoiceStatus.Paid &&\r\n        item.status != InvoiceStatus.Canceled\r\n    );\r\n    const loader = this.uiHelpers.showLoading(\r\n      \"SALAXY.NG1.InvoicesCompany.markingAsPaid\"\r\n    );\r\n    for (const [index, invoice] of invoices.entries()) {\r\n      const reader = this.getInvoiceReader(invoice, InvoiceStatus.Paid, false);\r\n      loader.setText(`${index + 1}/${invoices.length}`);\r\n      await reader.read([], null);\r\n    }\r\n    await this.refreshPeriodicInvoices();\r\n    loader.dismiss();\r\n  }\r\n\r\n  /** Update status of single invoice. */\r\n  public updateInvoiceStatus(item: InvoiceListItem, status: InvoiceStatus) {\r\n    const loading = this.uiHelpers.showLoading(\r\n      status === InvoiceStatus.Paid\r\n        ? \"SALAXY.NG1.InvoicesCompany.markingAsPaid\"\r\n        : \"SALAXY.NG1.InvoicesCompany.markingAsCanceled\"\r\n    );\r\n    const reader = this.getInvoiceReader(item, status);\r\n    reader.read([], null).then(() => {\r\n      loading.dismiss();\r\n    });\r\n  }\r\n\r\n  /** Data reader for one item. */\r\n  public getInvoiceReader = (\r\n    item: InvoiceListItem,\r\n    status: InvoiceStatus,\r\n    updatePeriodicInvoices = true\r\n  ) => {\r\n    return {\r\n      /** Function to read data into given array */\r\n      read: (arr: Invoice[], message: string): Promise<void> => {\r\n        const showConfirmation = (): Promise<boolean> => {\r\n          const warning = this.getEprWarning([item], status);\r\n          if (warning) {\r\n            return this.uiHelpers.showConfirm(\r\n              Translations.get(\"SALAXY.NG1.InvoicesCompany.invoiceReader.eprWarningHeading\"),\r\n              warning\r\n            );\r\n          } else {\r\n            if(status === InvoiceStatus.Canceled) {\r\n              const getConfirmText = (item: InvoiceListItem): string => {\r\n                if(item.entityType === \"net\" && item.status === InvoiceStatus.Unread) {\r\n                  return Translations.get(\"SALAXY.NG1.InvoicesCompany.invoiceReader.cancellationTexts.invoiceCancelingNetInvoiceText\");\r\n                }\r\n                if(item.entityType === \"tax\" && item.status !== InvoiceStatus.Paid) {\r\n                  return Translations.get(\"SALAXY.NG1.InvoicesCompany.invoiceReader.cancellationTexts.invoiceCancelingTax\");\r\n                }\r\n                return Translations.get(\"SALAXY.NG1.InvoicesCompany.invoiceReader.cancellationTexts.invoiceCancelingInvoiceText\");\r\n              };\r\n\r\n              return this.uiHelpers.showConfirm(\r\n                Translations.get(\"SALAXY.NG1.InvoicesCompany.invoiceReader.cancellationTexts.invoiceCancelingHeading\"),\r\n                getConfirmText(item),\r\n                Translations.get(\"SALAXY.NG1.InvoicesCompany.companyInvoiceDialog.buttons.save\"),\r\n                Translations.get(\"SALAXY.NG1.InvoicesCompany.companyInvoiceDialog.buttons.cancel\")\r\n              );\r\n            }\r\n          }\r\n          return Promise.resolve(true);\r\n        };\r\n        return showConfirmation().then((result) => {\r\n          if (result) {\r\n            (item as any)[\"isReading\" + (status || \"\")] = true;\r\n            return this.getInvoice(item, message, status).then((data) => {\r\n              if (data) {\r\n                // Update list item, does not need to refresh list\r\n                (item.data as any).statusAt = (data.header as any).statusAt;\r\n                item.status = data.header.status;\r\n                if (updatePeriodicInvoices) {\r\n                  this.refreshPeriodicInvoices().then(() => {\r\n                    arr.push(data);\r\n                  });\r\n                } else {\r\n                  arr.push(data);\r\n                }\r\n              }\r\n              (item as any)[\"isReading\" + (status || \"\")] = false;\r\n              return;\r\n            });\r\n          } else {\r\n            return;\r\n          }\r\n        });\r\n      },\r\n      getSepaData: (\r\n        /** Array for invoices */\r\n        _arr: Invoice[]\r\n      ): Promise<string> => undefined,\r\n      getFinvoiceData: (\r\n        /** Array for invoices */\r\n        _arr: Invoice[]\r\n      ): Promise<Blob[]> => undefined,\r\n      getPdfData: (\r\n        /** Array for invoices */\r\n        _arr: Invoice[]\r\n      ): Promise<Blob[]> => undefined,\r\n      /** Optional label for data export */\r\n      exportLabel: null,\r\n      /** Indicates if the export is not possible */\r\n      disabled: () => false,\r\n    };\r\n  };\r\n\r\n  /**\r\n   * Returns PDF url for a single invoice.\r\n   * @param item Invoice list item.\r\n   */\r\n  public getPdfUrl(item: InvoiceListItem): string {\r\n    if (!(item as any).pdfUrl) {\r\n      (item as any).pdfUrl = this.getContentUrl(item.id, false);\r\n    }\r\n    return (item as any).pdfUrl;\r\n  }\r\n\r\n  /**\r\n   * Retrieves the QR code for the specified invoice item.\r\n   * If the QR code is not already cached, it generates the QR code and caches it for future use.\r\n   * @param item - The invoice item for which to retrieve the QR code.\r\n   * @returns The QR code string.\r\n   */\r\n  public getQrCode(item: InvoiceListItem): string {\r\n    if (!this.qrCodesCache[item.id]) {\r\n      this.qrCodesCache[item.id] = \"loading\";\r\n      this.generateQrCodeSvgForInvoice(item).then((qrCode) => {\r\n        if (!qrCode) {\r\n          this.qrCodesCache[item.id] = \"error\";\r\n          this.$timeout();\r\n          return this.qrCodesCache[item.id];\r\n        } else {\r\n          this.qrCodesCache[item.id] = qrCode;\r\n          this.$timeout();\r\n          return this.$sce.trustAsHtml(this.qrCodesCache[item.id]);\r\n        }\r\n      });\r\n    }\r\n    if (this.qrCodesCache[item.id] === \"error\") {\r\n      return this.qrCodesCache[item.id];\r\n    }\r\n    return this.$sce.trustAsHtml(this.qrCodesCache[item.id]);\r\n  }\r\n\r\n  /**\r\n   * Calculates barcode value for the invoice item.\r\n   * @param item Invoice list item.\r\n   */\r\n  public getBarcodeValue(item: InvoiceListItem): string {\r\n    return Barcodes.getValue(\r\n      item.otherPartyInfo.ibanNumber || \"\",\r\n      item.entityType === \"net\" ? \"\" : item.reference,\r\n      Dates.asDate(item.data.dueDate),\r\n      Numeric.round(this.getInvoicePayment(item) * 100, 0)\r\n    );\r\n  }\r\n\r\n  /**\r\n   * Calculates the invoice payment amount for a given invoice item.\r\n   * If the invoice item is of type \"tax\" or \"union\" and the total paid amount\r\n   * is different from the payment amount, it returns the rounded difference\r\n   * between the payment amount and the total paid amount.\r\n   * Otherwise, it returns the payment amount.\r\n   * @param {InvoiceListItem} item - The invoice item to calculate the payment for.\r\n   * @returns {number} - The calculated payment amount.\r\n   */\r\n  public getInvoicePayment(item: InvoiceListItem): number {\r\n    if (\r\n      (item.entityType == \"tax\" || item.entityType == \"union\") &&\r\n      (item.data as any)?.totalPaid &&\r\n      (item.data as any).totalPaid != item.payment\r\n    ) {\r\n      return Numeric.round(item.payment - (item.data as any).totalPaid);\r\n    }\r\n    return item.payment;\r\n  }\r\n\r\n  /**\r\n   * Retrieves the barcode for the invoice recipient's IBAN.\r\n   * If the IBAN does not start with \"fi\" or is not provided, an empty string is returned.\r\n   * The barcode is generated using the Barcodes.createBarcode function.\r\n   * @returns The barcode as a string, wrapped in an HTML trust object.\r\n   */\r\n  public getBarcode(item: InvoiceListItem): string {\r\n    if (\r\n      !item.otherPartyInfo.ibanNumber ||\r\n      !item.otherPartyInfo.ibanNumber.toLowerCase().trim().startsWith(\"fi\")\r\n    ) {\r\n      return \"\";\r\n    }\r\n    const getDocumentAndSvgNode = () => {\r\n      return {\r\n        document,\r\n        svgNode: document.createElementNS(\"http://www.w3.org/2000/svg\", \"svg\"),\r\n      };\r\n    };\r\n\r\n    const result = Barcodes.createBarcode(\r\n      getDocumentAndSvgNode,\r\n      item.otherPartyInfo.ibanNumber || \"\",\r\n      item.entityType === \"net\" ? \"\" : item.reference || \"\",\r\n      Dates.asDate(item.data.dueDate),\r\n      Numeric.round(this.getInvoicePayment(item) * 100, 0),\r\n      {\r\n        width: 1.8,\r\n        height: 32,\r\n        displayValue: true,\r\n        fontSize: 15,\r\n      }\r\n    );\r\n    if (!result) {\r\n      return \"\";\r\n    }\r\n    return this.$sce.trustAsHtml(\r\n      new XMLSerializer().serializeToString(result as any)\r\n    );\r\n  }\r\n\r\n  /**\r\n   * Copies the barcode to clipboard.\r\n   * @param item Invoice list item.\r\n   */\r\n  public copyBarcode(item: InvoiceListItem) {\r\n    (navigator as any).clipboard.writeText(this.getBarcodeValue(item));\r\n  }\r\n\r\n  /**\r\n   * Displays the PDF for the given invoice items.\r\n   * @param items - The list of invoice items.\r\n   */\r\n  public showloadPfd(items: InvoiceListItem[]) {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.loading\");\r\n    const url = `${\r\n      Configs.current.reportServer\r\n    }/pdf?id=&reportType=${encodeURIComponent(\r\n      \"invoiceList\"\r\n    )}&template=${encodeURIComponent(\r\n      \"invoiceList\"\r\n    )}&language=${encodeURIComponent(\r\n      Translations.getLanguage()\r\n    )}&disposition=inline&access_token=${this.companyAjax.getCurrentToken()}`;\r\n    this.handlePdfRequest(url, false, { object: items }, loading);\r\n  }\r\n\r\n  /**\r\n   * Generates a URL for the calculation details of an invoice item.\r\n   * @param item - The invoice item for which to generate the URL.\r\n   * @returns A string representing the URL for the calculation details.\r\n   */\r\n  public calculationHref(item: InvoiceListItem): string {\r\n    //TODO: Nice to have for periodic invoices implement list for viewing invoice rows\r\n    if(item.status == InvoiceStatus.Canceled &&\r\n      (item.entityType == InvoiceType.Net || item.entityType == InvoiceType.Foreclosure) &&\r\n      item.businessObjects.length == 1\r\n    ){\r\n      return `#/calc/details/${item.businessObjects[0]}`;\r\n    }\r\n    return \"\";\r\n  }\r\n\r\n  private getEprWarning(\r\n    items: InvoiceListItem[],\r\n    status: InvoiceStatus\r\n  ): string {\r\n    if (status === InvoiceStatus.Canceled) {\r\n      for (const item of items) {\r\n        if (\r\n          item.status === InvoiceStatus.Paid &&\r\n          item.entityType == InvoiceType.Net &&\r\n          this.isDelayed(item.logicalDate)\r\n        ) {\r\n          return Translations.get(\"SALAXY.NG1.InvoicesCompany.invoiceReader.eprWarningTextCanceled\");\r\n        }\r\n      }\r\n    } else if (status === InvoiceStatus.Paid) {\r\n      for (const item of items) {\r\n        if (\r\n          item.status !== InvoiceStatus.Paid &&\r\n          item.entityType == InvoiceType.Net &&\r\n          this.isDelayed(item.logicalDate)\r\n        ) {\r\n          return Translations.get(\"SALAXY.NG1.InvoicesCompany.invoiceReader.eprWarningTextPaid\");\r\n        }\r\n      }\r\n    }\r\n    return null;\r\n  }\r\n  /** Checks if the Epr report is delayed. */\r\n  private isDelayed(salaryDate?: string): boolean {\r\n    if (this.session.isInRole(SystemRole.Test)) {\r\n      const officialDate = Dates.add(salaryDate ?? \"today\", 5, \"day\");\r\n      const expiresAt = Dates.addWorkdays(officialDate, 0);\r\n      const today = Dates.asDate(\"today\");\r\n      return today > expiresAt;\r\n    }\r\n    return false;\r\n  }\r\n  private getInvoice(\r\n    item: InvoiceListItem,\r\n    message: any,\r\n    status: InvoiceStatus = null\r\n  ): Promise<Invoice> {\r\n    const updateInvoiceStatus = (\r\n      invoice: Invoice,\r\n      status: InvoiceStatus\r\n    ): Promise<Invoice> => {\r\n      if (invoice.header.status === status) {\r\n        return Promise.resolve(invoice);\r\n      }\r\n      return this.invoicesApi.requestStatusUpdate(item.id, status);\r\n    };\r\n\r\n    return this.api.getSingle(item.id).then((readInvoice: Invoice) => {\r\n      if (status) {\r\n        return updateInvoiceStatus(readInvoice, status).then(\r\n          (updatedInvoice) => {\r\n            item.status = updatedInvoice.header.status;\r\n            return updatedInvoice;\r\n          }\r\n        );\r\n      } else {\r\n        return readInvoice;\r\n      }\r\n    });\r\n  }\r\n\r\n  private async generateQrCodeSvgForInvoice(\r\n    item: InvoiceListItem\r\n  ): Promise<string> {\r\n    const svg = await QrCodes.getValue(\r\n      BicHelper.getBicForIban(\r\n        item.otherPartyInfo.ibanNumber.replace(/\\s+/g, \"\")\r\n      ),\r\n      item.otherPartyInfo.avatar.displayName,\r\n      item.otherPartyInfo?.ibanNumber,\r\n      item.entityType === \"net\" ? null : item.reference,\r\n      item.entityType === \"net\"\r\n        ? `${Translations.get(\r\n            `SALAXY.ENUM.InvoiceType.${item.entityType}.label`\r\n          )} ${Dates.getFormattedRange(\r\n            item.data.periodStart,\r\n            item.data.periodEnd\r\n          )}`\r\n        : null,\r\n      this.getInvoicePayment(item),\r\n      item.endAt\r\n    );\r\n    return svg;\r\n  }\r\n\r\n  private async handlePdfRequest(\r\n    url: string,\r\n    inline: boolean,\r\n    payload: any,\r\n    loading: any\r\n  ): Promise<void> {\r\n    try {\r\n      await this.fetchPdf(url, payload, inline);\r\n    } catch (error) {\r\n      //HACK: Implement failover functionality to cloud (azure)\r\n      if (\r\n        url.includes(Configs.current.reportServer) &&\r\n        Configs.current.getEnv() === \"prod\"\r\n      ) {\r\n        url = url.replace(\r\n          Configs.current.reportServer,\r\n          \"https://failover-reports.salaxy.com\"\r\n        );\r\n        try {\r\n          await this.fetchPdf(url, payload, inline);\r\n        } catch (error) {\r\n          console.error(error);\r\n        }\r\n      } else {\r\n        console.error(error);\r\n      }\r\n    }\r\n    if (loading) {\r\n      loading.dismiss();\r\n    }\r\n  }\r\n\r\n  private async fetchPdf(\r\n    url: string,\r\n    payload: any,\r\n    inline: boolean\r\n  ): Promise<void> {\r\n    let response: any;\r\n    if (payload) {\r\n      response = await this.$http.post(url, payload, { responseType: \"blob\" });\r\n    } else {\r\n      response = await this.$http.get(url, { responseType: \"blob\" });\r\n    }\r\n    if (response.data) {\r\n      if (inline) {\r\n        this.uiHelpers.openFile(response.data as any);\r\n      } else {\r\n        this.uiHelpers.downloadFile(\r\n          response.data as any,\r\n          decodeURIComponent(response.headers(\"content-disposition\")).match(\r\n            /filename\\s*=\\s*\"?(?<file>.*?)(?:\\s*;|\"|\\s*$)/\r\n          )?.groups?.file\r\n        );\r\n      }\r\n    }\r\n  }\r\n\r\n  private async refreshPeriodicInvoices(): Promise<any[]> {\r\n    const periodicInvoices = this.odataController.items.filter(\r\n      (x) =>\r\n        x.entityType === InvoiceType.Tax ||\r\n        x.entityType === InvoiceType.Union ||\r\n        x.entityType === InvoiceType.Payroll ||\r\n        x.entityType === InvoiceType.Foreclosure\r\n    );\r\n    if (periodicInvoices.length === 0) {\r\n      return Promise.resolve([]);\r\n    }\r\n    const $filter = periodicInvoices.map((x) => `id eq '${x.id}'`).join(\" or \");\r\n    const loading = this.uiHelpers.showLoading(Translations.get(\"SALAXY.NG1.InvoicesCompany.gettingsInvoices\"));\r\n    const delay = (ms: number) =>\r\n      new Promise((resolve) => setTimeout(resolve, ms));\r\n    await delay(3000);\r\n    return this.odataController\r\n      .getApi()\r\n      .getOData({ $filter })\r\n      .then((result) => {\r\n        const toBeRemoved = [];\r\n        for (const periodicInvoice of periodicInvoices) {\r\n          const item = result.items.find((x) => x.id === periodicInvoice.id);\r\n          if (item) {\r\n            angular.copy(item, periodicInvoice);\r\n          } else {\r\n            toBeRemoved.push(periodicInvoice);\r\n          }\r\n        }\r\n        toBeRemoved.forEach((x) => {\r\n          const index = this.odataController.items.indexOf(x);\r\n          if (index > -1) {\r\n            this.odataController.items.splice(index, 1);\r\n          }\r\n        });\r\n        loading.dismiss();\r\n        return periodicInvoices;\r\n      })\r\n      .catch((error) => {\r\n        loading.dismiss();\r\n        console.error(error);\r\n        return periodicInvoices;\r\n      });\r\n  }\r\n}\r\n","import angular from \"angular\";\r\nimport { PaymentChannel, Dates, Calculations, CalculationListItem, Translations, ODataResult, OData, Ajax, InvoicesLogic } from \"@salaxy/core\";\r\n\r\n\r\n/**\r\n * The `InvoiceAlertsController` class is responsible for managing invoice alerts within the application.\r\n */\r\nexport class InvoiceAlertsController implements angular.IController {\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Calculations\", \"AjaxNg1\"];\r\n\r\n  /** Payment channels for OData query. */\r\n  public paymentChannels: PaymentChannel[];\r\n\r\n  /** Indicates if used in pro. */\r\n  public isPro: boolean;\r\n\r\n  public groupedPaymentChannelResult: string[] = [];\r\n\r\n  /** Start date for filtering list of calculations with status \"PaymentStarted\". Displayed on front page */\r\n  private paymentStartedWarningStartDate = Dates.getToday() + \"Z\";\r\n\r\n  /** End date for filtering list of calculations with status \"PaymentStarted\". Displayed on front page */\r\n  private paymentStartedWarningEndDate =  Dates.add(Dates.getToday(), -6, \"month\") + \"Z\";\r\n\r\n  private result: ODataResult<CalculationListItem>;\r\n\r\n  constructor(\r\n    private calculationsApi: Calculations,\r\n    private ajax: Ajax\r\n  ) {}\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    this.getOData().then(result => {\r\n      this.groupResultsByPaymentChannel(result);\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Groups the results by payment channel and stores the unique payment channels.\r\n   */\r\n  public groupResultsByPaymentChannel(results: CalculationListItem[]): void {\r\n    const paymentChannels = results.reduce((acc, item) => {\r\n      if (!acc.includes(item.data.paymentChannel)) {\r\n        acc.push(item.data.paymentChannel);\r\n      }\r\n      return acc;\r\n    }, [] as string[]);\r\n    this.groupedPaymentChannelResult = paymentChannels;\r\n  }\r\n\r\n  /**\r\n   * Retrieves a list of calculation items based on OData filters\r\n   * This method fetches data from the calculations API or a specific OData endpoint depending on the value of the `isPro` property. It applies filters to retrieve items with a status of 'paymentStarted' and within a specified salary date range.\r\n   */\r\n  public async getOData(): Promise<CalculationListItem[]> {\r\n    if(!this.isPro) {\r\n      this.result = await this.calculationsApi.getOData({\r\n        $filter: `status eq 'paymentStarted' and ${this.getPaymentChannelFilter()} and salaryDate lt ${this.paymentStartedWarningStartDate} and salaryDate gt ${this.paymentStartedWarningEndDate}`\r\n      });\r\n      return this.result.items ?? [];\r\n    }\r\n    this.result = await OData.getOData(\"/v01/api/pro/calculations/readonly\", {$filter: `status eq 'paymentStarted' and ${this.getPaymentChannelFilter()} and salaryDate lt ${this.paymentStartedWarningStartDate} and salaryDate gt ${this.paymentStartedWarningEndDate}`}, this.ajax);\r\n    return this.result.items ?? [];\r\n  }\r\n\r\n\r\n  /**\r\n   * Generates an HTML string containing payment channel information.\r\n   * The generated HTML includes:\r\n   * - A header with the payment channel label.\r\n   * - A description paragraph.\r\n   * - Instruction text specific to the payment channel.\r\n   * - Links related to the payment channel, including calculation and payroll links if applicable.\r\n   * - A help link to an external article.\r\n   */\r\n  public getpaymentChannelInfoHtml(paymentChannel: PaymentChannel): string {\r\n    const paymentChannelItems = this.result.items.filter(item => item.data.paymentChannel === paymentChannel);\r\n      const getInstructionText = () => {\r\n        return Translations.get(`SALAXY.NG1.InvoiceAlertsComponent.${paymentChannel}.instructionText.html`);\r\n      };\r\n\r\n      const getLinks = () => {\r\n        if (InvoicesLogic.isPalkkausManualLike(paymentChannel)) {\r\n          const urls = this.getUrls();\r\n          let link = Translations.get(`SALAXY.NG1.InvoiceAlertsComponent.calculationLink.html`, { calculationUrl: urls.calculationUrl });\r\n          if (paymentChannelItems.some(item => item.data.payrollId)) {\r\n            link += Translations.get(`SALAXY.NG1.InvoiceAlertsComponent.payrollLink.html`, { payrollUrl: urls.payrollUrl });\r\n          }\r\n          return link;\r\n        } else {\r\n          let link = Translations.get(`SALAXY.NG1.InvoiceAlertsComponent.calculationLink.html`, { calculationUrl: \"#/calc/paid/\" });\r\n          if (paymentChannelItems.some(item => item.data.payrollId)) {\r\n            link += Translations.get(`SALAXY.NG1.InvoiceAlertsComponent.payrollLink.html`, { calculationUrl: \"#/payroll/\" });\r\n          }\r\n          return link;\r\n        }\r\n      };\r\n      return `\r\n      <div class=\"row\">\r\n          <div class=\"col-12\">\r\n            <p class=\"lead lead-with-text\">${Translations.get(\"SALAXY.NG1.InvoiceAlertsComponent.header\", {channel: Translations.get(`SALAXY.ENUM.PaymentChannel.${paymentChannel}.label`)})}</p>\r\n            <p>${Translations.get(\"SALAXY.NG1.InvoiceAlertsComponent.description\")} ${getInstructionText()} ${getLinks()}</p>\r\n          </div>\r\n          <div class=\"col-12\">\r\n            <a href=\"https://help.palkkaus.fi/hc/fi/articles/23187345878557-Sinulla-on-keskeneräisiä-palkkalaskelmia-ilmoitus\" target=\"_blank\">${Translations.get(\"SALAXY.NG1.InvoiceAlertsComponent.openHelp\")}</a>\r\n          </div>\r\n      </div>\r\n    `;\r\n  }\r\n\r\n  private getUrls() {\r\n    const href = window.location.href;\r\n    //Local ng1\r\n    if (href.includes(\"localhost\") && href.includes(\"/ng1/\")) {\r\n      return { calculationUrl: `#/calc/paid`, payrollUrl: `#/payroll` };\r\n    }\r\n    //Local pro\r\n    if (href.includes(\":9001\")) {\r\n      return { calculationUrl: `#/pro/calc-paid`, payrollUrl: `#/pro/payroll-paid` };\r\n    }\r\n    if (href.includes(\"pro.palkkaus.fi\")) {\r\n      return { calculationUrl: `#/pro/calc-paid`, payrollUrl: `#/pro/payroll-paid` };\r\n    }\r\n    if (href.includes(\"palkkaus.fi/company\")) {\r\n      return { calculationUrl: `#/calc/paid`, payrollUrl: `#/payroll` };\r\n    }\r\n    if (href.includes(\"yritys.palkkaus.fi\")) {\r\n      return { calculationUrl: `#/calc/paid`, payrollUrl: `#/payroll` };\r\n    }\r\n    return { calculationUrl: \"\", payrollUrl: \"\" };\r\n  }\r\n\r\n  private getPaymentChannelFilter(): string {\r\n    return `(${this.paymentChannels.map(channel => `data/paymentChannel eq '${channel}'`).join(\" or \")})`;\r\n  }\r\n}\r\n","import { EditDialogParameters } from \"../../services\";\r\n\r\n/**\r\n * Controller for Item edit dialogs.\r\n */\r\nexport class EditDialogController {\r\n\r\n    /**\r\n     * For NG-dependency injection\r\n     * @ignore\r\n     */\r\n    public static $inject = [\"EditDialogParameters\"];\r\n\r\n    /**\r\n     * The item that is being edited.\r\n     * This a copy of the original item to allow cancel / reset and other change tracking.\r\n     */\r\n    public current: any;\r\n\r\n    /** Additional logic: Helper functions, metadata etc. that view can use to contruct the UI. */\r\n    public logic: any;\r\n\r\n    constructor(public editDialogParams: EditDialogParameters<any>) {\r\n\r\n    }\r\n    /**\r\n     * Implement IController\r\n     */\r\n    public $onInit = () => {\r\n      // initialization\r\n      if (!this.editDialogParams) {\r\n        throw new Error(\"No editDialogParams coming in.\");\r\n      }\r\n      this.current = this.editDialogParams.current;\r\n      this.logic = this.editDialogParams.logic;\r\n    };\r\n}\r\n","\r\n/**\r\n * Controller for alert, confirm and loading dialogs.\r\n */\r\nexport class ModalGenericDialogController {\r\n\r\n    /**\r\n     * For NG-dependency injection\r\n     * @ignore\r\n     */\r\n    public static $inject = [\"data\"];\r\n\r\n    constructor(\r\n        public data: any,\r\n    ) {\r\n    }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {\r\n  ApiListItem,\r\n  Calculation,\r\n  Calculations,\r\n  Employments,\r\n  ODataQueryOptions,\r\n  ODataResult,\r\n  SharingUriType,\r\n  Taxcards,\r\n  Translations\r\n} from \"@salaxy/core\";\r\n\r\nimport { CalculationCrudController } from \"../calc/CalculationCrudController\";\r\n\r\nimport {\r\n  InvoicesService, OnboardingService, ReportsService, SessionService, UiHelpers,\r\n} from \"../../services\";\r\n\r\n/**\r\n * Controller for sharing the calculation between worker and employer.\r\n */\r\nexport class CalcSharingController extends CalculationCrudController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Calculations\", \"ReportsService\", \"UiHelpers\", \"$location\", \"$routeParams\", \"SessionService\", \"InvoicesService\", \"Employments\", \"OnboardingService\", \"Taxcards\"];\r\n\r\n  /** Employing relations for the current account */\r\n  public employingRelations: ApiListItem[] = [];\r\n\r\n  /** True, if the current link has been copied to the clipboard */\r\n  public uriCopied = false;\r\n\r\n  /** If true, template shows option to share direct link to the calculation. Currently used only in Rakennusliitto site. */\r\n  public showLinkSharing: boolean;\r\n\r\n  /** Web sharing targets */\r\n  public webSharingTargets = {\r\n    email: {\r\n      title: Translations.get(\"SALAXY.NG1.CalcSharingComponent.sharingTargets.email\"),\r\n      icon: \"fa-envelope-o\",\r\n      action: () => this.showEmailSharing(),\r\n    },\r\n    whatsApp: {\r\n      title: \"WhatsApp\",\r\n      icon: \"fa-whatsapp\",\r\n      getUrl: () => this.getWhatsAppUrl(),\r\n    },\r\n    telegram: {\r\n      title: \"Telegram\",\r\n      icon: \"fa-telegram\",\r\n      getUrl: () => this.getTelegramUrl(),\r\n    },\r\n  };\r\n\r\n  /** Web sharing targets */\r\n  public mobileSharingTargets = {\r\n    email: {\r\n      title: Translations.get(\"SALAXY.NG1.CalcSharingComponent.sharingTargets.email\"),\r\n      icon: \"fa-envelope-o\",\r\n      action: () => this.showEmailSharing(),\r\n\r\n    },\r\n    device: {\r\n      title: Translations.get(\"SALAXY.NG1.CalcSharingComponent.sharingTargets.device\"),\r\n      icon: \"fa-share\",\r\n      action: () => this.shareInMobile(),\r\n    },\r\n  };\r\n\r\n  /** Loading indicator. */\r\n  public isSharingType: string = null;\r\n\r\n  /**\r\n   * Creates a new CalcSharingController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    private sharingCalculationsApi: Calculations,\r\n    reportsService: ReportsService,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    sessionService: SessionService,\r\n    invoicesService: InvoicesService,\r\n    private employmentsApi: Employments,\r\n    private onboardingService: OnboardingService,\r\n    private taxcards: Taxcards,\r\n  ) {\r\n    super(sharingCalculationsApi, reportsService, uiHelpers, $location, $routeParams, sessionService, invoicesService);\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n    this.loadEmployingRelations();\r\n  }\r\n\r\n  /** Show sharing page for the current calculation. */\r\n  public showSharing(action: string = null): Promise<angular.ILocationService> {\r\n    const savePending = (): Promise<Calculation> => {\r\n      if ((!action || action === \"default\")) {\r\n        if (!this.current.isReadOnly) {\r\n          return this.save();\r\n        }\r\n      }\r\n      return Promise.resolve(this.current);\r\n    };\r\n    return savePending().then((calculation: Calculation) => {\r\n      return this.$location.url(`/calc/sharing/${calculation.id}${action ? \"/\" + action : \"\"}`);\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shares the current calculation.\r\n   * @param type Type of the sharing action or link.\r\n   * @param employer List item for employer to share the calculation with. Mandatory in Direct share.\r\n   * @returns Sharing object of the calculation.\r\n   */\r\n  public share(type: SharingUriType = SharingUriType.Undefined, employer: ApiListItem = null): Promise<angular.ILocationService> {\r\n\r\n    if (type !== SharingUriType.Undefined) {\r\n      if (!this.sessionService.checkAccountVerification()) {\r\n        this.showMissingSignatureAlert();\r\n        return Promise.resolve(null);\r\n      }\r\n    }\r\n\r\n    const createSharingMessageForEmployer = (): Promise<{ to: string, cc: string, message: string }> => {\r\n      if (type !== SharingUriType.Employer) {\r\n        return Promise.resolve(null);\r\n      }\r\n      return this.createSharingMessage(employer);\r\n    };\r\n\r\n    this.isSharingType = `${type}${employer?.ownerId ? employer.ownerId : \"\"}`;\r\n    return createSharingMessageForEmployer().then( (item) => {\r\n      if (type === SharingUriType.Employer) {\r\n        if (!item) {\r\n          this.isSharingType = null;\r\n          return null;\r\n        }\r\n      }\r\n      return this.sharingCalculationsApi.share(this.currentId, type, employer?.ownerId, item?.to, item?.cc, item?.message).then(() => {\r\n        if (type === SharingUriType.Employer) {\r\n          this.uiHelpers.showAlert(Translations.get(\"SALAXY.NG1.CalcSharingComponent.emailSent\")+ \".\");\r\n        }\r\n        return this.reload().then(() => {\r\n          this.isSharingType = null;\r\n          return this.showDetails(this.current);\r\n        });\r\n      });\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Loads employing relations of the existing employers for the current account.\r\n   * @param options OData query options.\r\n   */\r\n  public loadEmployingRelations(options: ODataQueryOptions = null): Promise<ApiListItem[]> {\r\n    return this.employmentsApi.getODataForEmployingRelations(options).then((result: ODataResult<ApiListItem>) => {\r\n\r\n      // filter out duplicates, default sort is updatedAt desc\r\n      const distinctItems: ApiListItem[] = [];\r\n      result.items.forEach((x) => {\r\n        if (distinctItems.findIndex((d) => d.ownerId === x.ownerId) === -1) {\r\n          distinctItems.push(x);\r\n        }\r\n      });\r\n      this.employingRelations = distinctItems;\r\n      return this.employingRelations;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Returns validation for current calculation or empty validation object if the calculation has not been recalculated (validated).\r\n   */\r\n  public get validation() {\r\n    return this.current?.result?.validation || { errors: [], hasAllRequiredFields: true, isValid: true };\r\n  }\r\n\r\n  /** Returns the employer for the given id using employing employers as a source */\r\n  public get employer(): any {\r\n    if (this.current && this.current.sharing.type === SharingUriType.Employer && this.employingRelations) {\r\n      return this.employingRelations.find((x) => x.ownerId === (this.current.sharing.uri));\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /** Returns email address for current accoount */\r\n  public get cc(): string {\r\n    if (this.sessionService.session) {\r\n      return this.sessionService.session.currentAccount.contact.email;\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /** Copies link to clipboard */\r\n  public copyUri() {\r\n    (navigator as any).clipboard.writeText(this.current.sharing.uri);\r\n    this.uriCopied = true;\r\n  }\r\n\r\n  /** Returns true if the given typing is just processing sharing */\r\n  public isSharing(type: string): boolean {\r\n    return type === this.isSharingType;\r\n  }\r\n\r\n  /** Returns true if the navigator.share -function exists. */\r\n  public get isMobileSharingEnabled() {\r\n    return !!(navigator as any).share;\r\n  }\r\n\r\n  /** Whatsapp-link */\r\n  private getWhatsAppUrl(): string {\r\n    if (!this.current) {\r\n      return \"\";\r\n    }\r\n    return `https://wa.me/?text=${encodeURIComponent(this.getSharingMessage() + \"\\n\" + this.current.sharing.uri)}`;\r\n  }\r\n\r\n  /** Telegram-link */\r\n  private getTelegramUrl(): string {\r\n    if (!this.current) {\r\n      return \"\";\r\n    }\r\n    return `https://telegram.me/share/url?url=${encodeURIComponent(this.current.sharing.uri)}&text=${encodeURIComponent(this.getSharingMessage())}`;\r\n  }\r\n\r\n  /** Mobile sharing */\r\n  private shareInMobile(): Promise<any> {\r\n    const data = {\r\n      url: this.current.sharing.uri,\r\n      title: this.getSharingTitle(),\r\n      text: this.getSharingMessage(),\r\n    };\r\n    return (navigator as any).share(data);\r\n  }\r\n\r\n  private showEmailSharing(): void {\r\n    this.createSharingMessage().then( (item) => {\r\n      if (item) {\r\n        this.sendSharingEmail(item.to, item.cc, item.message);\r\n      }\r\n    });\r\n  }\r\n\r\n  private createSharingMessage(employer?: ApiListItem ): Promise<{ to: string, cc: string, message: string }> {\r\n    const item = {\r\n      to: employer?.ownerInfo?.email || \"\",\r\n      cc: this.cc,\r\n      message: \"\",\r\n    };\r\n    return this.uiHelpers.openEditDialog(\"salaxy-components/modals/calc/EmailSharing.html\", item, null)\r\n      .then((dialog) => {\r\n        if (dialog.result === \"ok\") {\r\n          return dialog.item;\r\n        } else {\r\n          return null;\r\n        }\r\n      });\r\n  }\r\n\r\n  private sendSharingEmail(to: string, cc: string, message: string): Promise<boolean> {\r\n    this.isSharingType = \"notification\";\r\n    return this.sharingCalculationsApi.notifySharing(this.currentId, to, cc, message).then((result) => {\r\n      this.isSharingType = null;\r\n      if (result === true) {\r\n        this.uiHelpers.showAlert(Translations.get(\"SALAXY.NG1.CalcSharingComponent.emailSendSuccess\")+ \".\");\r\n      } else {\r\n        this.uiHelpers.showAlert(Translations.get(\"SALAXY.NG1.CalcSharingComponent.emailSent\")+ \".\");\r\n      }\r\n      return this.reload().then( () => {\r\n        return result;\r\n      });\r\n    });\r\n  }\r\n\r\n  private getSharingMessage(): string {\r\n    return `${Translations.get(\"SALAXY.NG1.CalcSharingComponent.sharingMessage.calculationSent\")}. \\n ${Translations.get(\"SALAXY.NG1.CalcSharingComponent.sharingMessage.login\")}!`;\r\n  }\r\n\r\n  private getSharingTitle(): string {\r\n    return Translations.get(\"SALAXY.NG1.CalcSharingComponent.sharingTitle\");\r\n  }\r\n\r\n  /**\r\n   * Shows an alert if the signature is missing.\r\n   */\r\n  private showMissingSignatureAlert() {\r\n    this.uiHelpers.showConfirm(Translations.get(\"SALAXY.NG1.CalcSharingComponent.missingSignatureAlert.missingSignature\"),\r\n    `${Translations.get(\"SALAXY.NG1.CalcSharingComponent.missingSignatureAlert.finishAccountCreation\")}\\n ${Translations.get(\"SALAXY.NG1.CalcSharingComponent.missingSignatureAlert.signAuthorization\")} \\n\\n ${Translations.get(\"SALAXY.NG1.CalcSharingComponent.missingSignatureAlert.continueToSigning\")}`,\r\n    Translations.get(\"SALAXY.NG1.CalcSharingComponent.missingSignatureAlert.continue\"), Translations.get(\"SALAXY.NG1.CalcSharingComponent.missingSignatureAlert.close\")).then((ok: boolean) => {\r\n        if (ok) {\r\n          this.onboardingService.launchWorkerOnboarding();\r\n        }\r\n      });\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { UiHelpers } from \"../../services\";\r\n\r\nimport {\r\n  ApiListItem,\r\n  Employments,\r\n  ODataQueryOptions,\r\n  ODataResult,\r\n\r\n} from \"@salaxy/core\";\r\n\r\n\r\n\r\n/**\r\n * List of employers\r\n */\r\nexport class EmployerListController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Employments\", \"UiHelpers\"];\r\n\r\n  /** Employing relations for the current account */\r\n  public employingRelations: ApiListItem[] = [];\r\n\r\n  public employerId: string;\r\n\r\n  /** Items once loaded from the server. This is an empty array when the loading starts. */\r\n  public items: any[];\r\n\r\n  /** Selected search items */\r\n  public selectedItems: any[];\r\n\r\n  /** True if no employer is selected */\r\n  public showFullEmployerList: boolean;\r\n\r\n  /**\r\n   * Creates a new EmployerSelectController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    private employmentsApi: Employments,\r\n    protected uiHelpers: UiHelpers\r\n  ) {\r\n\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    this.loadEmployingRelations();\r\n    this.selectedItems = this.selectedItems || [];\r\n    this.items = this.items || [];\r\n  }\r\n\r\n\r\n  /**\r\n   * Loads employing relations of the existing employers for the current account.\r\n   * @param options OData query options.\r\n   */\r\n  public loadEmployingRelations(options: ODataQueryOptions = null): Promise<ApiListItem[]> {\r\n\r\n    return this.employmentsApi.getODataForEmployingRelations(options).then((result: ODataResult<ApiListItem>) => {\r\n\r\n      // filter out duplicates, default sort is updatedAt desc\r\n      const distinctItems: ApiListItem[] = [];\r\n      result.items.forEach((x) => {\r\n        if (distinctItems.findIndex((d) => d.ownerId === x.ownerId) === -1) {\r\n          distinctItems.push(x);\r\n        }\r\n      });\r\n      this.employingRelations = distinctItems;\r\n\r\n      return this.employingRelations;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Function that is called when user selects an employer in the list.\r\n   * Function has the following locals: value: true/false, item: the last selected/unselected item.\r\n   * @example <salaxy-employer-select on-employer-select=\"$ctrl.onEmployerSelect($ctrl.current, value, item)\"></salaxy-employer-select>\r\n   */\r\n  public onEmployerSelect: (params: {\r\n\r\n    /** In multi-select mode, the value may be true (selected) or false (unselected). */\r\n    value: true | false,\r\n    /** Item that was last selected / deselected. */\r\n    item: any,\r\n\r\n    /** All items that are currently selected. */\r\n    allItems: any[],\r\n\r\n  }) => void;\r\n\r\n\r\n  /**\r\n   * Sets an item as selected.\r\n   * @param item Item to set as selected\r\n   * @param value Selected true / false or \"toggle\" to toggle to other value.\r\n   */\r\n  public setEmployerSelected(item: any, value: true | false | \"toggle\" = true) {\r\n    // TODO: This now only supports items with id. Add other identifiers if necessary.\r\n    const ix = this.selectedItems.findIndex((x) => x.ownerId === item.ownerId);\r\n    const exists = ix >= 0;\r\n    if (exists) {\r\n\r\n      this.selectedItems.splice(ix, 1);\r\n    }\r\n    switch (value) {\r\n      case true:\r\n        this.selectedItems.push(item);\r\n        break;\r\n      case false:\r\n        // Already done\r\n        break;\r\n      case \"toggle\":\r\n        if (!exists) {\r\n          this.selectedItems.push(item);\r\n        }\r\n        break;\r\n    }\r\n    this.onEmployerSelect({\r\n      value: value === \"toggle\" ? !exists : value,\r\n      item,\r\n      /** All items that are currently selected. */\r\n      allItems: this.selectedItems,\r\n    });\r\n    this.selectEmployer(item.ownerId);\r\n  }\r\n\r\n\r\n  /**\r\n   * Returns true if the item is selected.\r\n   * @param item Item to check for selected value.\r\n   */\r\n  public isEmployerSelected(item: any) {\r\n    return this.selectedItems.findIndex((x) => x.ownerId === item.ownerId) >= 0;\r\n  }\r\n\r\n\r\n  /** Unselect all */\r\n  public unselectAll() {\r\n\r\n    if (this.selectedItems) {\r\n      this.selectedItems.splice(0, this.selectedItems.length);\r\n      this.showFullEmployerList = true;\r\n    }\r\n  }\r\n\r\n  /** Selects employer */\r\n\r\n  public selectEmployer(employerId:string){\r\n    this.employerId = employerId;\r\n  }\r\n\r\n\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Ajax } from \"@salaxy/core\";\r\n\r\n/**\r\n * Employer report.\r\n */\r\nexport class EmployerReportController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"AjaxNg1\"];\r\n\r\n  // TODO: Implement an algorithm that craetes the year options, so that it is always up to date.\r\n  /** Year options for the year select control. */\r\n  public yearOptions = [\r\n    { value: \"2024\", name: \"2024\" },\r\n    { value: \"2023\", name: \"2023\" },\r\n    { value: \"2022\", name: \"2022\" },\r\n    { value: \"2021\", name: \"2021\" },\r\n    { value: \"2020\", name: \"2020\" },\r\n    { value: \"2019\", name: \"2019\" },\r\n    { value: \"2018\", name: \"2018\" },\r\n    { value: \"2017\", name: \"2017\" },\r\n    { value: \"2016\", name: \"2016\" },\r\n    { value: \"2015\", name: \"2015\" },\r\n    { value: \"2014\", name: \"2014\" },\r\n  ];\r\n\r\n  private _currentReport: any = null;\r\n  private _selectedYear: any = null;\r\n  private _employers14BGroups: any = null;\r\n\r\n\r\n  constructor(private ajax: Ajax) { }\r\n\r\n  /**\r\n   * Controller initializations\r\n   */\r\n  public $onInit = () => {\r\n    this.refreshData();\r\n  };\r\n\r\n  /**\r\n   * Returns the currently loaded report data.\r\n   */\r\n  public get currentReport(): any {\r\n    return this._currentReport;\r\n  }\r\n\r\n  /**\r\n   * Returns the currently selected year.\r\n   */\r\n  public get selectedYear(): any {\r\n    if (!this._selectedYear) {\r\n      // Defaults to current year (given that the yearOptions is up to date)\r\n      this._selectedYear = this.yearOptions[0];\r\n    }\r\n    return this._selectedYear;\r\n  }\r\n\r\n  /**\r\n   * Sets the currently selected year and reloads the data.\r\n   */\r\n  public set selectedYear(year) {\r\n    this._selectedYear = year;\r\n    this.refreshData();\r\n  }\r\n\r\n  /**\r\n   * Returns employer ids and names in groups of two as in the 14B form (14B Kotitalousvähennys –\r\n   * työntekijälle maksettu palkka (3026))\r\n   */\r\n  public get employers14BGroups(): any {\r\n    return this._employers14BGroups;\r\n  }\r\n\r\n/**\r\n * Returns the employer id from the current report data if available otherwise undefined.\r\n */\r\n  public get employerId(): string {\r\n    return this._currentReport?.employerReports?.[0]?.employerId;\r\n  }\r\n\r\n  /**\r\n   * Returns the salary amount for TVR (Työttömyysvakuutusrahasto).\r\n   */\r\n  public get tvrSalaryAmount(): number {\r\n    // TODO: Arrays helperiä vois käyttää\r\n    return this._currentReport.employerReports.reduce((acc, cur) => acc + cur.totalSocialSecurityBase, 0);\r\n  }\r\n\r\n  /**\r\n   * Returns avatar data based on the given url.\r\n   * @param url Avatar url.\r\n   * @returns Avatar data.\r\n   */\r\n  public avatarFrom(url: string): any {\r\n    if (url.toLowerCase().startsWith(\"/person/icon/\")) {\r\n      return this.avatarDataFromIcon(url);\r\n    }\r\n    if (url.toLowerCase().startsWith(\"http\")) {\r\n      return this.avatarDataFromUrl(url);\r\n    }\r\n    return {\r\n      color: \"pink\",\r\n      initials: \"#?\"\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Returns the worker email address from a report object otherwise null or undefined.\r\n   * @param report The report object to search for worker email.\r\n   * @returns Returns the email address or null/undefined.\r\n   */\r\n  public workerEmailFrom(report: any): string {\r\n    return report?.worker.contact.email || report?.worker.identity.email;\r\n  }\r\n\r\n  /**\r\n   * Checks if the selected reporting year is before incomes registry was established and/or\r\n   * implemented.\r\n   * @returns Returns true if selected year is before and false otherwise.\r\n   */\r\n  public get isSelectedYearBeforeIncomesRegistry(): boolean {\r\n    return this.selectedYear.value < 2019;\r\n  }\r\n\r\n  /**\r\n   * Returns the authorization token for the current user.\r\n   */\r\n  public get token(): string {\r\n    return this.ajax.getCurrentToken();\r\n  }\r\n\r\n  /**\r\n   * Returns the api server address.\r\n   */\r\n  public get apiServerAddress(): string {\r\n    return this.ajax.getServerAddress();\r\n  }\r\n\r\n  private avatarDataFromIcon(url: string) {\r\n    const iconComponents = url.substring(url.lastIndexOf(\"/\") + 1);\r\n    const initials = iconComponents.substring(0, iconComponents.indexOf(\"?color=\")) || \"#?\";\r\n    const color = iconComponents.substring(iconComponents.indexOf(\"?color=\") + \"?color=\".length) || \"pink\";\r\n    const baseIcon = \"fa-user\";\r\n    return {\r\n      initials,\r\n      color,\r\n      baseIcon,\r\n    };\r\n  }\r\n\r\n  private avatarDataFromUrl(url: string): any {\r\n    return {\r\n      url: url.trim().replace(\"https://az724081.vo.msecnd.net\", \"https://cdn.salaxy.com\"),\r\n    };\r\n  }\r\n\r\n  private refreshData() {\r\n    this.ajax.getJSON(`/v03-rc/api/yearly/employer-report/${this.selectedYear.value}`).then((data) => {\r\n      this._currentReport = data;\r\n      this._employers14BGroups = this.extractEmployer14BGroups();\r\n    });\r\n  }\r\n\r\n  private extractEmployer14BGroups(): any {\r\n    const filtered = this._currentReport.employerReports.filter(v => v.isHouseholdDeductionWork);\r\n    return filtered.reduce((acc, cur, indx) => {\r\n      if (indx % 2 === 0) {\r\n        const id1 = cur.worker.identity.socialSecurityNumberValid;\r\n        const id2 = filtered?.[indx + 1]?.worker.identity.socialSecurityNumberValid || \"\";\r\n        const names = cur.worker.fullName + (filtered?.[indx + 1] ? \" ja \" + filtered[indx + 1].worker.fullName : \"\");\r\n        acc.push({ id1, id2, names, });\r\n      }\r\n      return acc;\r\n    }, []);\r\n  }\r\n}","import angular from \"angular\";\r\n\r\nimport {\r\n  ApiListItem,\r\n  Employments,\r\n  ODataQueryOptions,\r\n  ODataResult,\r\n\r\n} from \"@salaxy/core\";\r\n\r\n\r\n\r\n/**\r\n * Controller handles Employer selection\r\n */\r\nexport class EmployerSelectController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Employments\"];\r\n\r\n  /** Employing relations for the current account */\r\n  public employingRelations: ApiListItem[] = [];\r\n\r\n\r\n  /** Items once loaded from the server. This is an empty array when the loading starts. */\r\n  public items: any[];\r\n\r\n  /** Selected search items */\r\n  public selectedItems: any[];\r\n\r\n  /** True if any employer is selected */\r\n  public showFullEmployerList: boolean;\r\n\r\n  /**\r\n   * Creates a new EmployerSelectController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    private employmentsApi: Employments\r\n  ) {\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    this.loadEmployingRelations();\r\n    this.selectedItems = this.selectedItems || [];\r\n    this.items = this.items || [];\r\n  }\r\n\r\n\r\n  /**\r\n   * Loads employing relations of the existing employers for the current account.\r\n   * @param options OData query options.\r\n   */\r\n  public loadEmployingRelations(options: ODataQueryOptions = null): Promise<ApiListItem[]> {\r\n\r\n    return this.employmentsApi.getODataForEmployingRelations(options).then((result: ODataResult<ApiListItem>) => {\r\n\r\n      // filter out duplicates, default sort is updatedAt desc\r\n      const distinctItems: ApiListItem[] = [];\r\n      result.items.forEach((x) => {\r\n        if (distinctItems.findIndex((d) => d.ownerId === x.ownerId) === -1) {\r\n          distinctItems.push(x);\r\n        }\r\n      });\r\n      this.employingRelations = distinctItems;\r\n      if (this.employingRelations.length == 1) {\r\n        this.setEmployerSelected(this.employingRelations[0], true);\r\n      }\r\n\r\n      return this.employingRelations;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Function that is called when user selects an employer in the list.\r\n   * Function has the following locals: value: true/false, item: the last selected/unselected item.\r\n   * @example <salaxy-employer-select on-employer-select=\"$ctrl.onEmployerSelect($ctrl.current, value, item)\"></salaxy-employer-select>\r\n   */\r\n  public onEmployerSelect: (params: {\r\n\r\n    /** In multi-select mode, the value may be true (selected) or false (unselected). */\r\n    value: true | false,\r\n    /** Item that was last selected / deselected. */\r\n    item: any,\r\n\r\n    /** All items that are currently selected. */\r\n    allItems: any[],\r\n\r\n  }) => void;\r\n\r\n\r\n  /**\r\n   * Sets an item as selected.\r\n   * @param item Item to set as selected\r\n   * @param value Selected true / false or \"toggle\" to toggle to other value.\r\n   */\r\n  public setEmployerSelected(item: any, value: true | false | \"toggle\" = true) {\r\n    // TODO: This now only supports items with id. Add other identifiers if necessary.\r\n    const ix = this.selectedItems.findIndex((x) => x.ownerId === item.ownerId);\r\n    const exists = ix >= 0;\r\n    if (exists) {\r\n\r\n      this.selectedItems.splice(ix, 1);\r\n    }\r\n    switch (value) {\r\n      case true:\r\n        this.selectedItems.push(item);\r\n        break;\r\n      case false:\r\n        // Already done\r\n        break;\r\n      case \"toggle\":\r\n        if (!exists) {\r\n          this.selectedItems.push(item);\r\n        }\r\n        break;\r\n    }\r\n    this.onEmployerSelect({\r\n      value: value === \"toggle\" ? !exists : value,\r\n      item,\r\n      /** All items that are currently selected. */\r\n      allItems: this.selectedItems,\r\n    });\r\n  }\r\n\r\n\r\n  /**\r\n   * Returns true if the item is selected.\r\n   * @param item Item to check for selected value.\r\n   */\r\n  public isEmployerSelected(item: any) {\r\n    return this.selectedItems.findIndex((x) => x.ownerId === item.ownerId) >= 0;\r\n  }\r\n\r\n\r\n  /** Unselect all */\r\n  public unselectAll() {\r\n\r\n    if (this.selectedItems) {\r\n      this.selectedItems.splice(0, this.selectedItems.length);\r\n      this.showFullEmployerList = true;\r\n    }\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Ajax, Dates } from \"@salaxy/core\";\r\n\r\n/**\r\n * Employer report.\r\n */\r\nexport class HouseholdDeductionReportController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"AjaxNg1\"];\r\n\r\n  // TODO: Implement an algorithm that craetes the year options, so that it is always up to date.\r\n  /** Year options for the year select control. */\r\n  public yearOptions = [\r\n    { value: \"2020\", name: \"2020\" },\r\n    { value: \"2019\", name: \"2019\" },\r\n    { value: \"2018\", name: \"2018\" },\r\n    { value: \"2017\", name: \"2017\" },\r\n    { value: \"2016\", name: \"2016\" },\r\n    { value: \"2015\", name: \"2015\" },\r\n  ];\r\n\r\n  private _currentReport: any = null;\r\n  private _selectedYear: any = null;\r\n\r\n  private _yearlyDeductionMaxAmounts = {\r\n    \"2020\": 2250,\r\n    \"2019\": 2400,\r\n    \"2018\": 2400,\r\n    \"2017\": 2400,\r\n    \"2016\": 2400,\r\n    \"2015\": 2400,\r\n  };\r\n\r\n  constructor(private ajax: Ajax) { }\r\n\r\n  /**\r\n   * Controller initializations\r\n   */\r\n  public $onInit = () => {\r\n    this.refreshData();\r\n  };\r\n\r\n  /**\r\n   * Returns the currently loaded report data.\r\n   */\r\n  public get currentReport(): any {\r\n    return this._currentReport;\r\n  }\r\n\r\n  /**\r\n   * Returns the currently selected year. Defaults to current year minus one.\r\n   */\r\n  public get selectedYear(): any {\r\n    if (!this._selectedYear) {\r\n      // Defaults to current year (given that the yearOptions is up to date)\r\n      this._selectedYear = this.yearOptions[0];\r\n    }\r\n    return this._selectedYear;\r\n  }\r\n\r\n  /**\r\n   * Sets the currently selected year and reloads the data.\r\n   */\r\n  public set selectedYear(year) {\r\n    this._selectedYear = year;\r\n    this.refreshData();\r\n  }\r\n\r\n  /**\r\n   * Returns the employer id from the current report data if available otherwise undefined.\r\n   */\r\n  public get employerId(): string {\r\n    return this._currentReport?.employerReports?.[0]?.employerId;\r\n  }\r\n\r\n  /**\r\n   * Returns the total deduction amount from a given employer report.\r\n   * @param employerReport The employer report for which the amount is calculated for.\r\n   * @returns The total deduction amount from a given employer report.\r\n   */\r\n  public employerDeductionsTotalAmount(employerReport: any): string {\r\n    return this.formatNumber(\r\n      employerReport.totalTaxableDeduction +\r\n      employerReport.totalMandatorySideCosts +\r\n      employerReport.deductionInsuranceEtc\r\n    );\r\n  }\r\n\r\n  /**\r\n   * Returns the total deduction amount for a 14B form of a given year end report.\r\n   */\r\n  public yearlyForm14BTotalAmount(yearlyReport: any): string {\r\n    return this.formatNumber(\r\n      yearlyReport.employerReports\r\n        .reduce((acc, cur) => acc + cur.deduction14BFormTotal, 0)\r\n    );\r\n  }\r\n\r\n  /**\r\n   * Returns the total house hold deduction amount of a given year end report.\r\n   * @param yearlyReport The year end report for which the amount is calculated for.\r\n   */\r\n  public yearlyDeductionsTotalAmount(yearlyReport: any): string {\r\n    return this.formatNumber(this.calculateYearlyDeductionsTotalAmount(yearlyReport));\r\n  }\r\n\r\n  /**\r\n   * Returns the total deduction amount for a given reports with maximum and deductible amount taken\r\n   * into account.\r\n   * @param yearlyReport The year end report for which the amount is calculated for.\r\n   * @param deductibleAmount The deductible amount (can change in the future?)\r\n   * @returns The total deduction amount with maximum and deductible amount taken into account.\r\n   */\r\n  public yearlyDeductionTotal(yearlyReport: any, deductibleAmount = 100): string {\r\n    return this.formatNumber(\r\n      Math.min(\r\n        Math.max(\r\n          this.calculateYearlyDeductionsTotalAmount(yearlyReport) - deductibleAmount,\r\n          0),\r\n        this.deductionMaxAmount,\r\n      )\r\n    );\r\n  }\r\n\r\n  /**\r\n   * Returns...\r\n   */\r\n  public get deductionMaxAmount(): number {\r\n    return this._yearlyDeductionMaxAmounts[this.selectedYear.value];\r\n  }\r\n\r\n  /**\r\n   * Return the given amount formatted as a currency string.\r\n   * @param amount The amount to be formatted.\r\n   * @returns The amount formatted as currency.\r\n   */\r\n  public formatNumber(amount: number): string {\r\n    return new Intl.NumberFormat(\r\n      \"fi-FI\",\r\n      {\r\n        maximumFractionDigits: 2,\r\n        minimumFractionDigits: 2,\r\n      }\r\n    ).format(amount);\r\n  }\r\n\r\n  /**\r\n   * Formats the given start and end datetimes to an optimized datarange string.\r\n   * @param start The start datetime of the date range.\r\n   * @param end The end datetime of the date range.\r\n   * @returns Returns the daterange as an optimized date range string.\r\n   */\r\n  public formatDateRange(start: string, end: string): string {\r\n    return Dates.getFormattedRange(start, end);\r\n  }\r\n\r\n  /**\r\n   * Returns an avatar.\r\n   * @param url Avatart url.\r\n   * @returns Avatar.\r\n   */\r\n  public avatarFrom(url: string): any {\r\n    if (url.toLowerCase().startsWith(\"/person/icon/\")) {\r\n      return this.avatarDataFromIcon(url);\r\n    }\r\n    if (url.toLowerCase().startsWith(\"http\")) {\r\n      return this.avatarDataFromUrl(url);\r\n    }\r\n    return {\r\n      color: \"pink\",\r\n      initials: \"#?\"\r\n    };\r\n  }\r\n\r\n  private calculateYearlyDeductionsTotalAmount(yearlyReport: any): number {\r\n    return yearlyReport.employerReports.reduce((acc, cur) => {\r\n      return acc +\r\n        cur.totalTaxableDeduction +\r\n        cur.totalMandatorySideCosts +\r\n        cur.deductionInsuranceEtc;\r\n    }, 0);\r\n  }\r\n\r\n  private avatarDataFromIcon(url: string) {\r\n    const iconComponents = url.substring(url.lastIndexOf(\"/\") + 1);\r\n    const initials = iconComponents.substring(0, iconComponents.indexOf(\"?color=\")) || \"#?\";\r\n    const color = iconComponents.substring(iconComponents.indexOf(\"?color=\") + \"?color=\".length) || \"pink\";\r\n    const baseIcon = \"fa-user\";\r\n    return {\r\n      initials,\r\n      color,\r\n      baseIcon,\r\n    };\r\n  }\r\n\r\n  private avatarDataFromUrl(url: string): any {\r\n    return {\r\n      url: url.trim().replace(\"https://az724081.vo.msecnd.net\", \"https://cdn.salaxy.com\"),\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Returns the worker email address from a report object otherwise null or undefined.\r\n   * @param report The report object to search for worker email.\r\n   * @returns Returns the email address or null/undefined.\r\n   */\r\n  public workerEmailFrom(report: any): string {\r\n    return report?.worker.contact.email || report?.worker.identity.email;\r\n  }\r\n\r\n  private refreshData() {\r\n    this.ajax.getJSON(`/v03/api/yearly/tax-household-deduction-report/${this.selectedYear.value}`).then((data) => {\r\n      this._currentReport = data;\r\n    });\r\n  }\r\n}","import angular from \"angular\";\r\n\r\nimport JSZip from \"@progress/jszip-esm\";\r\n\r\nimport { saveAs } from \"file-saver\";\r\n\r\nimport { ApiListItem, Calculation, CalcWorker, Dates, HouseholdYear, HouseholdYears, HouseholdYearProcessingStatus, ODataResult, ReportType, Texts, Years, YearlySideCosts, TaxDeductionWorkCategories, HouseholdYearListItem } from \"@salaxy/core\";\r\n\r\nimport { ReportsService, SessionService, UiHelpers } from \"../../services\";\r\nimport { ApiCrudObjectController } from \"../bases\";\r\n\r\n/**\r\n * Provides CRUD access to household yearly deductions.\r\n */\r\nexport class HouseholdYearCrudController extends ApiCrudObjectController<HouseholdYear, HouseholdYearListItem> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"HouseholdYears\",\r\n    \"UiHelpers\",\r\n    \"$location\",\r\n    \"$routeParams\",\r\n    \"ReportsService\",\r\n    \"SessionService\",\r\n  ];\r\n\r\n  private _yearlyCalculations: {\r\n     year: number,\r\n     calculations: Calculation[],\r\n     modifiedCalculations: Calculation[]\r\n     status: \"loading\" | \"loaded\",\r\n     workers: Array<{\r\n       worker: CalcWorker,\r\n       mandatorySideCosts: number,\r\n       totalTaxable: number,\r\n       calculations: Calculation[],\r\n      }>\r\n  } = { year: null, calculations: [], modifiedCalculations: [], status: \"loaded\", workers: [] };\r\n\r\n  constructor(\r\n    private householdYearsApi: HouseholdYears,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    private reportsService: ReportsService,\r\n    private sessionService: SessionService,\r\n  ) {\r\n    super(householdYearsApi, uiHelpers, $location, $routeParams);\r\n  }\r\n\r\n  /**\r\n   * Initializes the controller\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"/household-years\",\r\n      detailsUrl: this.detailsUrl || \"/household-years/details/\",\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/HouseholdYears.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n\r\n  /** Save changes to the current item */\r\n  public async save(): Promise<HouseholdYear> {\r\n    for (const calc of this.yearlyCalculations.modifiedCalculations) {\r\n      const updatedCalc = await this.householdYearsApi.updateCalculation(calc);\r\n      const i = this.yearlyCalculations.calculations.indexOf(calc);\r\n      if (i >= 0) {\r\n          angular.copy(updatedCalc,this.yearlyCalculations.calculations[i]);\r\n      }\r\n    }\r\n    this.yearlyCalculations.modifiedCalculations.splice(0,  this.yearlyCalculations.modifiedCalculations.length);\r\n    return super.save();\r\n  }\r\n\r\n  /** Returns all paid calculations for the household year */\r\n  public get yearlyCalculations(): {year: number, calculations: Calculation[], modifiedCalculations: Calculation[], status: \"loading\" | \"loaded\",  workers: Array<{\r\n    worker: CalcWorker,\r\n    mandatorySideCosts: number,\r\n    totalTaxable: number,\r\n    calculations: Calculation[],\r\n   }>} {\r\n    if (!this.current || !this.current.year) {\r\n      this._yearlyCalculations.year = null;\r\n      this._yearlyCalculations.status = \"loaded\";\r\n      this._yearlyCalculations.calculations.splice(0,  this._yearlyCalculations.calculations.length);\r\n      this._yearlyCalculations.modifiedCalculations.splice(0,  this._yearlyCalculations.modifiedCalculations.length);\r\n      this._yearlyCalculations.workers.splice(0,  this._yearlyCalculations.calculations.length);\r\n    } else {\r\n      if (this._yearlyCalculations.year !== this.current.year &&  this._yearlyCalculations.status !== \"loading\") {\r\n        this._yearlyCalculations.year = this.current.year;\r\n        this._yearlyCalculations.status = \"loading\";\r\n        this.householdYearsApi.getCalculationsForYear(this._yearlyCalculations.year).then( (calculations) => {\r\n          this._yearlyCalculations.calculations = [];\r\n          this._yearlyCalculations.modifiedCalculations = [];\r\n          this._yearlyCalculations.workers = [];\r\n          this._yearlyCalculations.calculations.push(...calculations);\r\n\r\n          for(const calc of this._yearlyCalculations.calculations) {\r\n            let item = this._yearlyCalculations.workers.find( (x) => x.worker.paymentData.socialSecurityNumberValid == calc.worker.paymentData.socialSecurityNumberValid);\r\n            if (!item) {\r\n              item = { worker: calc.worker, totalTaxable: 0, mandatorySideCosts:0, calculations: [] };\r\n              this._yearlyCalculations.workers.push(item);\r\n            }\r\n            item.calculations.push(calc);\r\n            item.mandatorySideCosts += calc.result.employerCalc.mandatorySideCosts;\r\n            item.totalTaxable += calc.result.totals.totalTaxable;\r\n          }\r\n          this._yearlyCalculations.status = \"loaded\";\r\n        });\r\n      }\r\n    }\r\n    return this._yearlyCalculations;\r\n  }\r\n\r\n    /** Returns true if the feedback is active */\r\n    public get isOpen(): boolean {\r\n      if (!this.current) {\r\n        return false;\r\n      }\r\n\r\n      return this.sessionService.isInSomeRole([\"pro\", \"admin\"]) ||\r\n             !this.current.processingStatus || this.current.processingStatus === HouseholdYearProcessingStatus.Open;\r\n    }\r\n\r\n\r\n  /** Calculates the household tax deduction total */\r\n  public getTaxDeductionTotal() {\r\n    let deductibleTotal = 0;\r\n    const calcs = this.yearlyCalculations.calculations;\r\n\r\n    for (const calc of calcs) {\r\n      if (calc.usecase?.data?.isHouseholdDeductible && !this.isHouseholdDeductionExtended(calc)) {\r\n        deductibleTotal += calc.result.employerCalc.mandatorySideCosts;\r\n        deductibleTotal += ( calc.result.totals.totalTaxable * this.getHouseholdDeduction(calc) );\r\n      }\r\n    }\r\n    return deductibleTotal;\r\n  }\r\n\r\n   /** Calculates the household tax deduction total */\r\n   public getTaxDeductionTotalExtended() {\r\n    let deductibleTotal = 0;\r\n    const calcs = this.yearlyCalculations.calculations;\r\n\r\n    for (const calc of calcs) {\r\n      if (calc.usecase?.data?.isHouseholdDeductible && this.isHouseholdDeductionExtended(calc)) {\r\n        deductibleTotal += calc.result.employerCalc.mandatorySideCosts;\r\n        deductibleTotal += ( calc.result.totals.totalTaxable * this.getHouseholdDeduction(calc) );\r\n      }\r\n    }\r\n    return deductibleTotal;\r\n  }\r\n\r\n  /** Returns true if the deduction should be split between spouses */\r\n  public canSplitWithSpouse() {\r\n    return this.getSplittableMaxAmount() > 0;\r\n  }\r\n\r\n  /** Returns current deduction max amount */\r\n  public getSplittableMaxAmount() {\r\n    let maxAmount = 0;\r\n    if ((this.getTaxDeductionTotal() + (this.current.insuranceAmount ?? 0)) > (this.getHouseholdDeductionMaxAmount() + this.getHouseholdDeductionDeductible())) {\r\n      maxAmount = this.getHouseholdDeductionMaxAmount();\r\n    }\r\n    if ( (Math.min(this.getTaxDeductionTotal(), this.getHouseholdDeductionMaxAmount() + this.getHouseholdDeductionDeductible()) + this.getTaxDeductionTotalExtended() + (this.current.insuranceAmount ?? 0)) > (this.getHouseholdDeductionMaxAmountExtended() + this.getHouseholdDeductionDeductible())) {\r\n      maxAmount = this.getHouseholdDeductionMaxAmountExtended();\r\n    }\r\n    return maxAmount;\r\n  }\r\n\r\n  /** Returns household deduction for calculation */\r\n  public getHouseholdDeduction(calc: Calculation) {\r\n    const category = this.getTaxDeductionWorkCategories(calc);\r\n    const sideCosts = this.getYearlySideCosts();\r\n\r\n    if (this.getHouseholdDeductionCategoriesExtended().includes(category)) {\r\n      return sideCosts.householdDeductionExtended;\r\n    }\r\n    return sideCosts.householdDeduction;\r\n  }\r\n\r\n  /** Returns deduction deductible */\r\n  public getHouseholdDeductionDeductible() {\r\n    const sideCosts = this.getYearlySideCosts();\r\n    return sideCosts.householdDeductionDeductible;\r\n  }\r\n\r\n  /**\r\n   * Gets a link URL for a yearly report. This is a full link with token and absolute URL.\r\n   * @param type - Type of the report must be one of the yearly reports\r\n   * @param year - Year for the report\r\n   * @param id - Worker ID for those reports that are specific to one Worker.\r\n   * @param id2 - Second Worker ID for those reports that have two Workers in one report\r\n   */\r\n   public getYearlyReport(type: ReportType, year: number, id?: string, id2?: string) {\r\n    return this.reportsService.getYearlyReportUrl(type, year, id, id2);\r\n  }\r\n\r\n  /** Set calculation modified */\r\n  public calculationUpdated(calc: Calculation) {\r\n    const existingCalc = this.yearlyCalculations.modifiedCalculations.find( (x) => x.id === calc.id);\r\n    if (!existingCalc) {\r\n      const newCalc = this.yearlyCalculations.calculations.find( (x) => x.id == calc.id);\r\n      if (newCalc) {\r\n        this.yearlyCalculations.modifiedCalculations.push(newCalc);\r\n      }\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Sets the active year to the controller.\r\n   */\r\n  public setActiveYear() {\r\n    const now = new Date();\r\n    const year = now.getMonth() >= 2 ? now.getFullYear() : now.getFullYear()  - 1;\r\n\r\n    this.householdYearsApi.getOData(null).then( (result) => {\r\n      const odata = result as any as ODataResult<ApiListItem>;\r\n      const logicalDate = `${year}-01-01T00:00:00Z`;\r\n      const report = odata.items.find( (x) => x.logicalDate == logicalDate);\r\n      if (report) {\r\n        this.householdYearsApi.getSingle(report.id).then( (yearReport) => {\r\n          this.model = yearReport;\r\n        });\r\n      }\r\n      else\r\n      {\r\n        const newModel = this.api.getBlank();\r\n        newModel.year = year;\r\n        this.model = newModel;\r\n      }\r\n    });\r\n  }\r\n\r\n  /** Export pdf for the given deductions */\r\n  public async export() {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\", \"Ladataan PDF-tiedostoja...\");\r\n    const results =  await this.downloadReportsForHousehold();\r\n    if (results.length === 0) {\r\n      loading.dismiss();\r\n    } else {\r\n      if (results.length === 1) {\r\n        this.uiHelpers.downloadFile(results[0].blob, results[0].fileName);\r\n        loading.dismiss();\r\n      } else {\r\n        loading.setText(`Muodostetaan pakattu tiedosto`);\r\n        const zip = new JSZip();\r\n        results.forEach(item => {\r\n          zip.file(`${item.fileName}`, item.blob);\r\n        });\r\n        const blob =  await zip.generateAsync({\r\n          type: \"blob\",\r\n          mimeType:\r\n            \"application/zip\",\r\n        });\r\n        saveAs(blob, `${Texts.escapeFileName(`14B_${Dates.format(\"today\",\"YYYYMMDD\")}`)}.zip`);\r\n        loading.dismiss();\r\n      }\r\n    }\r\n  }\r\n\r\n  private async downloadReportsForHousehold(): Promise<Array<{blob: Blob, fileName: string}>> {\r\n    if (!this.current?.id) {\r\n      return Promise.resolve([]);\r\n    }\r\n    const results = [];\r\n    const pdfs = await this.householdYearsApi.downloadPdfs(this.current.id);\r\n    for(const pdf of pdfs) {\r\n      results.push( {\r\n        fileName: pdf.fileName,\r\n        blob: this.uiHelpers.bytes2Blob(pdf.bytes,\"application/pdf\"),\r\n      });\r\n    }\r\n    return results;\r\n  }\r\n\r\n   private  getYearlySideCosts(): YearlySideCosts {\r\n    if (!this.current || !this.current.year) {\r\n      return Years.getYearlyChangingNumbers(Dates.getToday()).sideCosts;\r\n    }\r\n    return Years.getYearlyChangingNumbers(`${this.current.year}-01-01`).sideCosts;\r\n  }\r\n\r\n  private getHouseholdDeductionMaxAmount() {\r\n    const sideCosts = this.getYearlySideCosts();\r\n    return sideCosts.householdDeductionMaxAmount;\r\n  }\r\n\r\n  private getHouseholdDeductionMaxAmountExtended() {\r\n    const sideCosts = this.getYearlySideCosts();\r\n    return sideCosts.householdDeductionMaxAmountExtended;\r\n  }\r\n\r\n  private getTaxDeductionWorkCategories(calc: Calculation) : TaxDeductionWorkCategories {\r\n    return calc.usecase?.data?.taxDeductionCategories ?? TaxDeductionWorkCategories.None;\r\n  }\r\n\r\n  private getHouseholdDeductionCategoriesExtended(): TaxDeductionWorkCategories[] {\r\n    const sideCosts = this.getYearlySideCosts();\r\n    return sideCosts.householdDeductionCategoriesExtended ?? [];\r\n  }\r\n\r\n  private isHouseholdDeductionExtended(calc: Calculation): boolean {\r\n    const category = this.getTaxDeductionWorkCategories(calc);\r\n    return this.getHouseholdDeductionCategoriesExtended().includes(category);\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Accounts, Avatar, AvatarPictureType, PersonAccount, WorkflowEvent, Years } from \"@salaxy/core\";\r\n\r\nimport { GravatarHelpers, SessionService, UiHelpers, UploadService } from \"../../services\";\r\n\r\n/** Controller for editing contact, avatar etc. information on Person accounts (Worker or Household). */\r\nexport class PersonAccountController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Accounts\", \"SessionService\", \"UploadService\", \"UiHelpers\", \"$location\"];\r\n\r\n  /** Yearly sidecosts */\r\n  public sideCosts = Years.getYearlyChangingNumbers(new Date()).sideCosts;\r\n\r\n  /** Current person account being edited. */\r\n  public current: PersonAccount;\r\n\r\n  /** Current tab in initialization. If not set, will be fetched from url hash. */\r\n  private _currentTab = null;\r\n\r\n  /** Constructor for dependency injection */\r\n  constructor(\r\n    private accounts: Accounts,\r\n\r\n    private sessionService: SessionService,\r\n    private uploadService: UploadService,\r\n    private uiHelpers: UiHelpers,\r\n    private $location: angular.ILocationService,\r\n  ) {\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    if (!this.current && this.sessionService.getCurrentToken()) {\r\n      this.accounts.getPerson().then((person) => {\r\n        this.current = person;\r\n      });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Switches the current web site usage role between household and worker.\r\n   * TODO: This functionality will be removed\r\n   * @param role - household or worker.\r\n   * @returns A Promise with result data (new role as string)\r\n   */\r\n  public switchRole(role: \"worker\" | \"household\"): Promise<\"household\" | \"worker\"> {\r\n    return this.sessionService.switchRole(role).then((resultRole) => {\r\n      if (role === \"worker\") {\r\n        window.location.href = \"/Worker#/\";\r\n      } else {\r\n        window.location.href = \"/Household#/\";\r\n      }\r\n      return resultRole;\r\n    });\r\n  }\r\n\r\n  /** Updates the person */\r\n  public saveCurrent = (): Promise<PersonAccount> => {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    return this.accounts.savePerson(this.current).then((person: PersonAccount) => {\r\n      this.current = person;\r\n      return this.sessionService.checkSession().then(() => {\r\n        loading.dismiss();\r\n        return this.current;\r\n      });\r\n    });\r\n  };\r\n\r\n  /** Gets the language of the user (person) */\r\n  public getAccountLanguage() {\r\n    return this.current?.language;\r\n  }\r\n\r\n/**\r\n * Uploads avatar image file to the server.\r\n * @param avatar - selected file\r\n */\r\n  public uploadAvatarImage(avatar: any) {\r\n    if (!avatar) {\r\n      return;\r\n    }\r\n    this.uploadService.upload<Avatar>(this.accounts.getAvatarUploadUrl(), { avatar })\r\n      .then((resp) => {\r\n        this.current.avatar.url = resp.url;\r\n        this.current.avatar.pictureType = resp.pictureType;\r\n      });\r\n  }\r\n\r\n  /** Called when avatar changes */\r\n  public emailForAvatarChanged() {\r\n    if (!this.current || !this.current.avatar) {\r\n      return;\r\n    }\r\n    if (this.current.avatar.pictureType === AvatarPictureType.Gravatar) {\r\n      this.current.avatar.url = GravatarHelpers.getGravatarUrl(this.current.contact.email);\r\n    }\r\n  }\r\n  /** Called when avatar changes */\r\n  public typeForAvatarChanged() {\r\n    if (!this.current || !this.current.avatar) {\r\n      return;\r\n    }\r\n    if (this.current.avatar.pictureType === AvatarPictureType.Gravatar) {\r\n      this.current.avatar.url = GravatarHelpers.getGravatarUrl(this.current.contact.email);\r\n    } else {\r\n      if (GravatarHelpers.isGravatarUrl(this.current.avatar.url)) {\r\n        this.current.avatar.url = null;\r\n      }\r\n      if (this.current.avatar.pictureType === AvatarPictureType.Uploaded) {\r\n        const originalAvatar = (this.sessionService.getPersonAccount() || {}).avatar;\r\n        if (!this.current.avatar.url && originalAvatar && originalAvatar.url) {\r\n          if (originalAvatar.pictureType === AvatarPictureType.Uploaded &&\r\n            !GravatarHelpers.isGravatarUrl(originalAvatar.url)) {\r\n            this.current.avatar.url = originalAvatar.url;\r\n          }\r\n        }\r\n      }\r\n    }\r\n  }\r\n\r\n  /**\r\n   * For the tab UI control, returns the current tab, if defined in the path\r\n   * or set explicitly. Defaults to \"default\".\r\n   */\r\n\r\n  public get currentTab(): \"default\" | \"contact\" | \"avatar\" | \"insurance\" | \"identity\" | \"taxcard\" {\r\n    if (this._currentTab) {\r\n      return this._currentTab;\r\n    }\r\n    const supportedHashes = [\"default\", \"contact\", \"avatar\", \"insurance\", \"identity\", \"taxcard\"];\r\n    const hash = (this.$location ? this.$location.hash() || \"\" : \"\").trim().toLowerCase();\r\n    return supportedHashes.indexOf(hash) > -1 ? hash as any : \"default\";\r\n  }\r\n  public set currentTab(value: \"default\" | \"contact\" | \"avatar\" | \"insurance\" | \"identity\" | \"taxcard\") {\r\n    this._currentTab = value;\r\n  }\r\n\r\n  /**\r\n   * Adds/updates the workflow event for the current using API.\r\n   * @param wfEvent - Workflow event to add/update.\r\n   * @returns - Reloaded item.\r\n   */\r\n  public saveWorkflowEvent(wfEvent: WorkflowEvent): Promise<void | PersonAccount> {\r\n    return this.accounts.saveWorkflowEvent(this.current, wfEvent).then(() => {\r\n      return this.accounts.getPerson().then((person) => {\r\n        this.current = person;\r\n      });\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Deletes the given event or all events with given type using API.\r\n   * @param wfIdOrType Id or type of the workflow event.\r\n   * @returns - Reloaded item.\r\n   */\r\n  public deleteWorkflowEvent(wfIdOrType: string): Promise<void | PersonAccount> {\r\n    return this.accounts.deleteWorkflowEvent(this.current, wfIdOrType).then(() => {\r\n      return this.accounts.getPerson().then((person) => {\r\n        this.current = person;\r\n      });\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Gets a single workflow event for the item.\r\n   * @param wfId Id the workflow event.\r\n   * @returns - Workflow event.\r\n   */\r\n  public getWorkflowEvent(wfId: string): Promise<WorkflowEvent> {\r\n    return this.accounts.getWorkflowEvent(this.current, wfId);\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Ajax } from \"@salaxy/core\";\r\n\r\n/**\r\n * Employer report.\r\n */\r\nexport class WorkerReportController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"AjaxNg1\"];\r\n\r\n  private _yearOptions = null;\r\n\r\n  private _currentReport: any = null;\r\n  private _selectedYear: any = null;\r\n\r\n  constructor(private ajax: Ajax) { }\r\n\r\n  /**\r\n   * Controller initializations\r\n   */\r\n  public $onInit = () => {\r\n    this.refreshData();\r\n  };\r\n\r\n  /** Return year options for the year select control. */\r\n  public get yearOptions() {\r\n    if (!this._yearOptions) {\r\n      const startYear = 2014;\r\n      const endYear = new Date().getFullYear();\r\n      this._yearOptions = [];\r\n      for(let year = startYear; year <= endYear; year++) {\r\n        this._yearOptions.unshift({value: \"\" + year, name: \"\" + year});\r\n      }\r\n    }\r\n    return this._yearOptions;\r\n  }\r\n\r\n  /**\r\n   * Returns the currently loaded report data.\r\n   */\r\n  public get currentReport(): any {\r\n    return this._currentReport;\r\n  }\r\n\r\n  /**\r\n   * Returns the currently selected reporting year.\r\n   */\r\n  public get selectedYear(): any {\r\n    if (!this._selectedYear) {\r\n      // Defaults to current year (given that the yearOptions is up to date)\r\n      this._selectedYear = this.yearOptions[0];\r\n    }\r\n    return this._selectedYear;\r\n  }\r\n\r\n  /**\r\n   * Sets the currently selected reporting year and reloads the data.\r\n   */\r\n  public set selectedYear(year) {\r\n    this._selectedYear = year;\r\n    this.refreshData();\r\n  }\r\n\r\n  /**\r\n   * Returns the worker email address from a report object otherwise null or undefined.\r\n   * @param report The report object to search for worker email.\r\n   * @returns Returns the email address or null/undefined.\r\n   */\r\n  public employerEmailFrom(report: any): string {\r\n    return report?.employer.contact.email || report?.employer.identity.email;\r\n  }\r\n\r\n  /**\r\n   * Checks if the selected reporting year is before incomes registry was established and/or\r\n   * implemented.\r\n   * @returns Returns true if selected year is before and false otherwise.\r\n   */\r\n  public get isSelectedYearBeforeIncomesRegistry(): boolean {\r\n    return this.selectedYear.value < 2019;\r\n  }\r\n\r\n  /**\r\n   * Returns avatar data based on the given url.\r\n   * @param url Avatar url.\r\n   * @returns Avatar data.\r\n   */\r\n  public avatarFrom(url: string): any {\r\n    if (url.toLowerCase().startsWith(\"/person/icon/\")) {\r\n      return this.avatarDataFromIcon(url);\r\n    }\r\n    if (url.toLowerCase().startsWith(\"http\")) {\r\n      return this.avatarDataFromUrl(url);\r\n    }\r\n    return {\r\n      color: \"pink\",\r\n      initials: \"#?\"\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Returns the authorization token for the current user.\r\n   */\r\n  public get token(): string {\r\n    return this.ajax.getCurrentToken();\r\n  }\r\n\r\n  /**\r\n   * Returns the api server address.\r\n   */\r\n  public get apiServerAddress(): string {\r\n    return this.ajax.getServerAddress();\r\n  }\r\n\r\n  private avatarDataFromIcon(url: string) {\r\n    const iconComponents = url.substring(url.lastIndexOf(\"/\") + 1);\r\n    const initials = iconComponents.substring(0, iconComponents.indexOf(\"?color=\")) || \"#?\";\r\n    const color = iconComponents.substring(iconComponents.indexOf(\"?color=\") + \"?color=\".length) || \"pink\";\r\n    const baseIcon = \"fa-user\";\r\n    return {\r\n      initials,\r\n      color,\r\n      baseIcon,\r\n    };\r\n  }\r\n\r\n  private avatarDataFromUrl(url: string): any {\r\n    return {\r\n      url: url.trim().replace(\"https://az724081.vo.msecnd.net\", \"https://cdn.salaxy.com\"),\r\n    };\r\n  }\r\n\r\n  private refreshData() {\r\n    this.ajax.getJSON(`/v03-rc/api/yearly/worker-report/${this.selectedYear.value}`).then((data) => {\r\n      this._currentReport = data;\r\n    });\r\n  }\r\n}","import angular from \"angular\";\r\n\r\nimport { Arrays, Calculations, MessageThreads, Payrolls} from \"@salaxy/core\";\r\n\r\nimport { MessageThreadCrudController } from \"../communications\";\r\n\r\nimport { SessionService, UiHelpers, UploadService } from \"../../services\";\r\n\r\n/** DEMO / PROTO ONLY: UI prototype for worker side of new Timesheet and usecases functionality. */\r\nexport class TimesheetWorkerDemoController extends MessageThreadCrudController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"MessageThreads\", \"UiHelpers\", \"UploadService\", \"$location\", \"$routeParams\", \"$anchorScroll\", \"$timeout\", \"SessionService\", \"$interval\", \"Calculations\", \"Payrolls\"];\r\n\r\n  /** List of entries: This should be stored in local storage. */\r\n  public entries = [];\r\n\r\n  /** Current entry in the entry or editable entry */\r\n  public currentEntry: {\r\n    start: Date,\r\n    end?: Date,\r\n    total: Date,\r\n    project?: string,\r\n    comment?: string,\r\n    isStarted: boolean,\r\n  } = null;\r\n\r\n  public projects = {\r\n    \"1234\": \"Projekti 1\",\r\n    \"2345\": \"Toinen projekti\",\r\n    \"1345\": \"Joku muu projekti\",\r\n  };\r\n\r\n  private timer: angular.IPromise<void>;\r\n\r\n  /** Constructor for dependency injection */\r\n  constructor(\r\n    private msgApi: MessageThreads,\r\n    uiHelpers: UiHelpers,\r\n    uploadService: UploadService,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    $anchorScroll: angular.IAnchorScrollService,\r\n    $timeout: angular.ITimeoutService,\r\n\r\n    sessionService: SessionService,\r\n    calculations: Calculations,\r\n    payrolls: Payrolls,\r\n    private $interval: angular.IIntervalService,\r\n  ) {\r\n    super(msgApi, uiHelpers, uploadService, $location, $routeParams, $anchorScroll, $timeout, sessionService, calculations, payrolls);\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    this.resetTimer();\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Called when controller is destroyed */\r\n  public $onDestroy = () => {\r\n    this.stopTechnicalTimer();\r\n  };\r\n\r\n  /** Resets the timer to zero value */\r\n  public resetTimer() {\r\n    this.stopTechnicalTimer();\r\n    this.currentEntry = {\r\n      isStarted: false,\r\n      start: this.roundDate(),\r\n      total: new Date(0),\r\n    };\r\n  }\r\n\r\n  /** Starts the timer. */\r\n  public startTimer()\r\n  {\r\n    this.stopTechnicalTimer();\r\n    this.currentEntry.start = this.roundDate();\r\n    this.currentEntry.isStarted = true;\r\n    this.timer = this.$interval(() => {\r\n      this.currentEntry.total = new Date(this.roundDate().getTime() - this.currentEntry.start.getTime());\r\n    }, 1000);\r\n  }\r\n\r\n  /** Starts the timer. */\r\n  public stopTimer()\r\n  {\r\n    this.currentEntry.end = this.roundDate();\r\n    this.currentEntry.total = new Date(this.currentEntry.end.getTime() - this.currentEntry.start.getTime());\r\n    this.entries.push(this.currentEntry);\r\n    this.resetTimer();\r\n  }\r\n\r\n  /** Gets the project text for a project */\r\n  public getProjectText(key: string): string {\r\n    if (!key) {\r\n      return \"Ei projektia\";\r\n    }\r\n    return this.projects[key] || (\"Ei projektia \" + key) ;\r\n  }\r\n\r\n  /** Gets the total of the timesheets logged today */\r\n  public getTotal() {\r\n    return new Date(Arrays.sum(this.entries, (x) => x.total.getTime()));\r\n  }\r\n\r\n  private roundDate(time: Date = null): Date {\r\n    if (!time) {\r\n      time = new Date();\r\n    }\r\n    time.setMilliseconds(0);\r\n    // time.setSeconds(0);\r\n    return time;\r\n  }\r\n\r\n  private stopTechnicalTimer() {\r\n    if (this.timer) {\r\n      this.$interval.cancel(this.timer);\r\n    }\r\n  }\r\n\r\n\r\n  public calendarDemoData = [\r\n    {\r\n      day: \"ma\",\r\n      date: \"2.5.\",\r\n      hours: \"7:30 h\",\r\n    },{\r\n      day: \"ti\",\r\n      date: \"3.5.\",\r\n      hours: \"7:30 h\",\r\n    },{\r\n      day: \"ke\",\r\n      date: \"4.5.\",\r\n      hours: null,\r\n    },{\r\n      day: \"to\",\r\n      date: \"5.5.\",\r\n      hours: null,\r\n    },{\r\n      day: \"pe\",\r\n      date: \"6.5.\",\r\n      hours: null,\r\n    },{\r\n      day: \"la\",\r\n      date: \"7.5.\",\r\n      hours: null,\r\n      isHoliday: true,\r\n    },{\r\n      day: \"su\",\r\n      date: \"8.5.\",\r\n      hours: null,\r\n      isHoliday: true,\r\n    },\r\n  ];\r\n\r\n  /** Sets the usecase to a new message thread */\r\n  public setUsecase(newUsecase: any) {\r\n    (this.current as any).usecase = {\r\n      uri: \"palkkaus.fi/testing/messages-proto/\" + newUsecase.id,\r\n      label: newUsecase.title,\r\n      description: newUsecase.descr,\r\n      data: {\r\n        protoId: newUsecase.id,\r\n      },\r\n    };\r\n  }\r\n\r\n  /** Gets the usecases available for the current Worker-Employer combination. */\r\n  public getUsecases(): {\r\n    id: string,\r\n    icon?: string,\r\n    pic?: string,\r\n    title: string,\r\n    descr: string,\r\n  }[] {\r\n    return this.uiHelpers.cache(this, \"usecases\", () => {\r\n      return [\r\n        {\r\n          id: \"default\",\r\n          icon: \"fa-envelope\",\r\n          title: \"Viesti\",\r\n          descr: \"Lähetä viesti turvapostilla.\",\r\n        },\r\n        {\r\n          id: \"timer\",\r\n          icon: \"fa-clock-o\",\r\n          title: \"Kellokortti\",\r\n          descr: \"Leimaa sisään digitaalisella kellokorttisovelluksella.\",\r\n        },\r\n        {\r\n          id: \"timesheet\",\r\n          icon: \"fa-calendar\",\r\n          title: \"Kirjaa tunteja\",\r\n          descr: \"Kirjaa / muokkaa jo tapahtuneita tunteja.\",\r\n        },\r\n        {\r\n          id: \"timesheet\",\r\n          icon: \"fa-calendar\",\r\n          title: \"Kirjaa työaikoja\",\r\n          descr: \"Kirjaa / muokkaa jo tehtyjä työaikoja (myös kellonajat).\",\r\n        },\r\n        {\r\n          id: \"timesheet\",\r\n          icon: \"fa-sun-o\",\r\n          title: \"Lomakalenteri\",\r\n          descr: \"Lähetä lomapyyntö\",\r\n        },\r\n        {\r\n          id: \"timesheet\",\r\n          icon: \"fa-ambulance\",\r\n          title: \"Poissaolot\",\r\n          descr: \"Ilmoita poissaolosta\",\r\n        },\r\n        {\r\n          id: \"travel\",\r\n          icon: \"fa-suitcase\",\r\n          title: \"Matkalaskut\",\r\n          descr: \"Kilometrikorvaukset, päivärahat ja kulukorvaukset matkoista.\",\r\n        },\r\n        {\r\n          id: \"expenses\",\r\n          icon: \"fa-shopping-cart\",\r\n          title: \"Kulukorvaukset\",\r\n          descr: \"Kulukorvaukset kuittien perusteella mukaan lukien kilometrikorvaukset.\",\r\n        },\r\n        {\r\n          id: \"calc\",\r\n          pic: \"https://salaxypublic.blob.core.windows.net/salaxy-wordpress/2019/03/palkkaennakko_palkkalaskuri_palkkalaskelma.png\",\r\n          title: \"Palkkalaskuri\",\r\n          descr: \"Palkkaus.fi perinteinen palkkalaskuri, jolla voit lähettää minkä tahansa palkkapyynnön.\",\r\n        }\r\n      ];\r\n    });\r\n  }\r\n\r\n}\r\n","import angular from \"angular\";\r\nimport { ApiValidationErrorType, Arrays, Dates, DateTimes, Message, MessageThread, Numeric, ThreadedMessageType, MessageFrom, TimesheetInput, TimesheetInputModification } from \"@salaxy/core\";\r\n\r\nimport { SessionService, UiHelpers } from \"../../services\";\r\nimport { ListControllerBase } from \"../bases\";\r\n\r\n\r\n/** Controller handles Timer usecases */\r\nexport class WorkerTimerController extends ListControllerBase<MessageThread, Message> {\r\n  /** Binded crud controller */\r\n  public crudController: any;\r\n\r\n  /** User interface mode: \"mini\" is the front page card UI without the list and \"edit\" is just the editable list of entries.  */\r\n  public timerMode: \"mini\" | \"edit\" | \"\";\r\n\r\n  private timer: angular.IPromise<void>;\r\n\r\n  private _newTimerMessage: Message;\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$interval\", \"UiHelpers\", \"SessionService\"];\r\n\r\n  /** Constructor for dependency injection */\r\n  constructor(\r\n    private $interval: angular.IIntervalService,\r\n    uiHelpers: UiHelpers,\r\n    private sessionService: SessionService,\r\n  ) {\r\n    super(uiHelpers);\r\n  }\r\n\r\n  /**\r\n   * Controller initializations\r\n   */\r\n  public $onInit(){\r\n    if (this.isTimerOn) {\r\n      this.startTechnicalTimer(this.getTimerMessage());\r\n    }\r\n    this.validateEntries();\r\n    this.onCommit = () => {\r\n      this.validateEntries();\r\n      if (this.isTimerOn) {\r\n        this.startTechnicalTimer(this.getTimerMessage());\r\n      }\r\n    };\r\n    super.$onInit();\r\n  }\r\n\r\n  /**\r\n   * Stop timer on destroy\r\n   */\r\n  public $onDestoy() {\r\n    this.stopTechnicalTimer();\r\n  }\r\n\r\n  /**\r\n   * Returns true if the message indicates that the timer should be on.\r\n   */\r\n  public get isTimerOn() {\r\n    const timerMessage = this.getTimerMessage();\r\n    return timerMessage.contentData.startTime && !timerMessage.contentData.endTime;\r\n  }\r\n\r\n  /**\r\n   * Returns true if the message indicates that the timer should be on.\r\n   */\r\n    public get isTimerOnFromDayBefore() {\r\n      const timerMessage = this.getTimerMessage();\r\n      return this.isTimerOn && Dates.isBefore(timerMessage.contentData.period.start, Dates.getToday());\r\n    }\r\n\r\n  /**\r\n   * Ensure that atleast one message exists\r\n   */\r\n  public getTimerMessage() {\r\n    const messageIndex = this.list.findIndex(x => x.type === ThreadedMessageType.Timer &&\r\n      (\r\n        (!x.contentData.startTime && !x.contentData.endTime) ||\r\n        (x.contentData.startTime && !x.contentData.endTime)\r\n      )\r\n    );\r\n\r\n    if (messageIndex >= 0) {\r\n      this._newTimerMessage = null;\r\n      return this.list[messageIndex];\r\n    }\r\n\r\n    if (!this._newTimerMessage) {\r\n      this._newTimerMessage = this.getBlank();\r\n    }\r\n    return this._newTimerMessage;\r\n  }\r\n\r\n\r\n  /**\r\n   * List of items\r\n   */\r\n  public get list(): Message[] {\r\n    if (!this.parent) {\r\n      return null;\r\n    }\r\n    return this.parent.messages;\r\n  }\r\n\r\n\r\n  /** Template for edit UI that is shown in a modal dialog. */\r\n  public getEditDialogTemplateUrl(): string {\r\n    return \"salaxy-components/worker/TimerEditDialog.html\";\r\n  }\r\n\r\n  /**\r\n   * Creating of a new item\r\n   */\r\n  public getBlank(): Message {\r\n\r\n    const contentData: TimesheetInput = {\r\n      modification: TimesheetInputModification.CREATE,\r\n      period: {\r\n        start: Dates.getToday()\r\n      }\r\n    };\r\n\r\n    return {\r\n      type: ThreadedMessageType.Timer,\r\n      content: \"Kellokorttikirjaus\",\r\n      contentData,\r\n      fromParty: MessageFrom.OtherParty,\r\n    };\r\n  }\r\n\r\n  /** Starts the timer. */\r\n  public startTimer() {\r\n    this.stopTechnicalTimer();\r\n    let timerMessage = this.getTimerMessage();\r\n    if (this.list.indexOf(timerMessage) < 0) {\r\n      this.list.push(timerMessage);\r\n    }\r\n    const now = new Date();\r\n    timerMessage.contentData.period.start = Dates.asDate(now);\r\n    timerMessage.contentData.startTime = DateTimes.asTime(now);\r\n    timerMessage.contentData.totalTime = 0;\r\n    timerMessage.contentData.totalTimeInSeconds = 0;\r\n    this.crudController.save().then((thread: MessageThread) => {\r\n      this.parent = thread;\r\n      timerMessage = this.getTimerMessage();\r\n      this.startTechnicalTimer(timerMessage);\r\n    });\r\n  }\r\n\r\n  /** Stops the timer. */\r\n  public stopTimer() {\r\n    this.stopTechnicalTimer();\r\n    const timerMessage = this.getTimerMessage();\r\n    const now = new Date();\r\n    timerMessage.contentData.period.end = Dates.asDate(now);\r\n    timerMessage.contentData.endTime = DateTimes.asTime(now);\r\n    this.calculateAndSetTotals(timerMessage);\r\n    this.crudController.save().then((thread) => {\r\n      this.parent = thread;\r\n      this.validateEntries();\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Formats time as minutes or seconds.\r\n   * TODO: implement this as filter.\r\n   * @param total Total number of minutes or seconds\r\n   * @param unit Unit: seconds or minutes\r\n   * @returns Formatted time\r\n   */\r\n  public formatTime(total: number, unit: \"minutes\" | \"seconds\" = \"minutes\"): string {\r\n    const padTo2Digits = (num) => {\r\n      return num.toString().padStart(2, \"0\");\r\n    };\r\n    total = Numeric.isNumber(total) ? total : 0;\r\n    switch( unit ) {\r\n      case \"minutes\": {\r\n        const hours = Math.floor(total / 60);\r\n        const minutes = total % 60;\r\n        return `${padTo2Digits(hours)}:${padTo2Digits(minutes)}`;\r\n      }\r\n      case \"seconds\": {\r\n        const hours = Math.floor(total / 3600);\r\n        const minutes =  Math.floor((total % 3600) / 60);\r\n        const seconds = total % 60;\r\n        return `${padTo2Digits(hours)}:${padTo2Digits(minutes)}:${padTo2Digits(seconds)}`;\r\n      }\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Gets the total of the timesheets logged in messageThread.\r\n   */\r\n  public getAndFormatTotal(): string {\r\n    return this.formatTime(Arrays.sum(this.list, (x) => x.contentData.totalTime));\r\n  }\r\n\r\n  /**\r\n   * Override for ListControllerBase showEditDialog\r\n   * @param item Item to edit or string \"new\" for creating a new one.\r\n   * @param isNew Optional way of specifying that the item is a new item (with default values, not yet added to the list).\r\n   * If item is string \"new\", this parameter will have no effect (will always be true).\r\n   */\r\n  public showEditDialog(item: Message | \"new\", isNew = false) {\r\n    if (!item) {\r\n      throw new Error(\"showEditDialog called without a parameter.\");\r\n    }\r\n    if (item === \"new\") {\r\n      isNew = true;\r\n      item = this.getBlank();\r\n    }\r\n\r\n    const lk1 = ( this.crudController?.employingRelation?.settings?.costAccounting?.dimensions ||\r\n      this.sessionService.session.settings?.costAccounting?.dimensions || undefined)\r\n      .find((x) => x.name = \"lk1\");\r\n\r\n\r\n    const costAccountingSettings = lk1 ?\r\n      {\r\n        options: lk1.options,\r\n        label: lk1.label,\r\n      } : null;\r\n\r\n    this.uiHelpers.openEditDialog(this.getEditDialogTemplateUrl(), item, { ...this.getEditDialogLogic(), costAccountingSettings }).then((result) => {\r\n      if (result.action === \"ok\" || result.action === \"ok-no-save\") {\r\n        this.calculateAndSetTotals(result.item);\r\n\r\n        if (isNew) {\r\n          this.list.push(result.item);\r\n        }\r\n        if ((isNew || result.hasChanges) && result.action !== \"ok-no-save\") {\r\n          this.commit();\r\n        }\r\n      } else if (result.action === \"delete\" || result.action === \"delete-no-save\") {\r\n        if (!isNew) {\r\n          this.delete(item as Message);\r\n          if (result.action !== \"delete-no-save\") {\r\n            this.commit();\r\n          }\r\n        }\r\n      } else {\r\n        // No changes, cancel\r\n      }\r\n    });\r\n  }\r\n\r\n  /** Gets the project text for a project */\r\n  public getDimensionOptionText(value: string): string {\r\n    if (value) {\r\n      const lk1 = ( this.crudController?.employingRelation?.settings?.costAccounting?.dimensions ||\r\n        this.sessionService.session.settings?.costAccounting?.dimensions || undefined )\r\n      .find((x) => x.name = \"lk1\");\r\n      if (lk1) {\r\n          return lk1.options.find( (x) => x.value === value)?.text ?? \"\";\r\n      }\r\n    }\r\n    return \"\";\r\n  }\r\n\r\n\r\n  private startTechnicalTimer(timerMessage: Message) {\r\n    this.stopTechnicalTimer();\r\n    this.timer = this.$interval((msg) => {\r\n      this.calculateAndSetTotals(msg, new Date());\r\n    }, 1000, 0, true, timerMessage);\r\n  }\r\n\r\n  private calculateAndSetTotals(timerMessage: Message, endTime: Date = null) {\r\n    const now = new Date();\r\n    const startTime = new Date(`${timerMessage.contentData.period.start ?? Dates.asDate(now) }T${timerMessage.contentData.startTime ?? DateTimes.asTime(now)}:00`);\r\n    endTime = endTime ?? new Date(`${timerMessage.contentData.period.end ?? Dates.asDate(now)}T${timerMessage.contentData.endTime ?? DateTimes.asTime(now)}:00`);\r\n    const ms = endTime.getTime() - startTime.getTime();\r\n    timerMessage.contentData.totalTimeInSeconds = Math.floor(ms / 1000);\r\n    timerMessage.contentData.totalTime = Math.floor(ms / 60000);\r\n  }\r\n  private stopTechnicalTimer(): void {\r\n    if (this.timer) {\r\n      this.$interval.cancel(this.timer);\r\n    }\r\n  }\r\n\r\n  /** Overlapping timer log entries validation */\r\n  private validateEntries(): void {\r\n    for (const entry of this.list) {\r\n      entry.validation = null;\r\n    }\r\n    for (const entry of this.list) {\r\n      if (entry.contentData.period.start &&\r\n        entry.contentData.startTime &&\r\n        entry.contentData.period.end &&\r\n        entry.contentData.endTime) {\r\n\r\n        const entryStartTime = new Date(`${entry.contentData.period.start}T${entry.contentData.startTime}:00`);\r\n        const entryEndTime = new Date(`${entry.contentData.period.end}T${entry.contentData.endTime}:00`);\r\n\r\n        const isOverlapping = this.list.find((x) => {\r\n\r\n          if (x.contentData.period.start &&\r\n            x.contentData.startTime &&\r\n            x.contentData.period.end &&\r\n            x.contentData.endTime) {\r\n\r\n            const xStartTime = new Date(`${x.contentData.period.start}T${x.contentData.startTime}:00`);\r\n            const xEndTime = new Date(`${x.contentData.period.end}T${x.contentData.endTime}:00`);\r\n\r\n            return entry != x &&\r\n              (\r\n                // endTime not inside entry's range\r\n                (Dates.isSameOrAfter(xEndTime, entryStartTime, \"minutes\") && Dates.isSameOrBefore(xEndTime, entryEndTime, \"minutes\")) ||\r\n                // startTime not inside entry's range\r\n                (Dates.isSameOrAfter(xStartTime, entryStartTime, \"minutes\") && Dates.isBefore(xStartTime, entryEndTime, \"minutes\")) ||\r\n                // another range covers entry's range\r\n                (Dates.isSameOrBefore(xStartTime, entryStartTime, \"minutes\") && Dates.isSameOrAfter(xEndTime, entryEndTime, \"minutes\"))\r\n              );\r\n          }\r\n          else {\r\n            return false;\r\n          }\r\n        });\r\n        if (isOverlapping) {\r\n          entry.validation = {\r\n            errors: [{\r\n              type: \"invalid\" as ApiValidationErrorType,\r\n              msg: \"Päällekkäisiä kirjauksia\",\r\n              code: \"TimeSheetInput.isOverlapping\"\r\n            }],\r\n            isValid: false,\r\n            hasAllRequiredFields: true\r\n          };\r\n        }\r\n      }\r\n    }\r\n  }\r\n}\r\n","import { Dates, Message, ThreadedMessageType, MessageThread, MessageFrom, TimesheetInput, TimesheetInputModification } from \"@salaxy/core\";\r\n\r\nimport { ListControllerBase, ListControllerBaseBindings } from \"../bases\";\r\n\r\nimport { UiHelpers, SessionService } from \"../../services\";\r\n\r\ninterface Weekday {\r\n  dayName: string,\r\n  date: string,\r\n  displayDate: string,\r\n  isCollapsed: boolean\r\n}\r\n\r\nclass WorkerHourlyReportControllerBindings extends ListControllerBaseBindings {\r\n   /** Type of the timesheet. Options are hourlyReport and timeReport */\r\n   public reportType =  \"<\";\r\n   /**\r\n    * CRUD controller that typically defines the values for url template and\r\n    */\r\n    public crudController =  \"<\";\r\n}\r\n\r\n/** Controller handles timebased usecases (timer, hourlyreport) */\r\nexport class WorkerHourlyReportController extends ListControllerBase<MessageThread, Message> {\r\n  /** Bindings for components that use this controller */\r\n  public static bindings = new WorkerHourlyReportControllerBindings();\r\n  /** Binded crud controller */\r\n  public crudController: any;\r\n  /** Date of today */\r\n  public currentDate: string;\r\n  public firstDayOfCurrentWeekFormatted: string;\r\n  /** Last day of current week, formatted to MM/dd/YYYY - format */\r\n  public lastDayOfCurrentWeekFormatted: string;\r\n  /** first of current week, used to determine week range */\r\n  public firstDayOfCurrentWeek: string;\r\n  /** Lastday of current week, used to determine week range */\r\n  public lastDayOfCurrentWeek: string;\r\n  /** Currentweek dataset */\r\n  public currentWeek: Weekday[] = [];\r\n  /** Currently supported Report type, mostly affects to ui */\r\n  public reportType: ThreadedMessageType.HourlyReport | ThreadedMessageType.TimeReport;\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"UiHelpers\", \"SessionService\"];\r\n\r\n  /** Constructor for dependency injection */\r\n  constructor(\r\n    uiHelpers: UiHelpers,\r\n    private sessionService: SessionService,\r\n  ) {\r\n    super(uiHelpers);\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    this.currentDate = Dates.getToday();\r\n    this.setCurrentWeek();\r\n  }\r\n\r\n  /**\r\n   * List of items\r\n   */\r\n  public get list(): Message[] {\r\n    if (!this.parent) {\r\n      return null;\r\n    }\r\n    return this.parent.messages;\r\n  }\r\n\r\n  /** Template for edit UI that is shown in a modal dialog. */\r\n  public getEditDialogTemplateUrl(): string {\r\n    if (this.reportType == ThreadedMessageType.HourlyReport) {\r\n      return \"salaxy-components/worker/HourlyReportEditDialog.html\";\r\n    }\r\n\r\n    if (this.reportType == ThreadedMessageType.TimeReport) {\r\n      return \"salaxy-components/worker/TimeReportEditDialog.html\";\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Creating of a new item\r\n   */\r\n  public getBlank(): Message {\r\n    if (this.reportType === ThreadedMessageType.HourlyReport) {\r\n      const contentData: TimesheetInput = {\r\n        modification: TimesheetInputModification.CREATE,\r\n        project: \"\",\r\n        projectText: \"\",\r\n        period: {\r\n          start: this.currentDate\r\n        },\r\n        totalTime: 450\r\n      };\r\n      return {\r\n        type: ThreadedMessageType.HourlyReport,\r\n        content: \"Tuntikirjaus\",\r\n        contentData,\r\n        fromParty: MessageFrom.OtherParty,\r\n      };\r\n    }\r\n    if (this.reportType === ThreadedMessageType.TimeReport) {\r\n      const contentData: TimesheetInput = {\r\n        modification: TimesheetInputModification.CREATE,\r\n        project: \"\",\r\n        projectText: \"\",\r\n        period: {\r\n          start: this.currentDate\r\n        }\r\n      };\r\n      return {\r\n        type: ThreadedMessageType.TimeReport,\r\n        content: \"Työaikakirjaus\",\r\n        contentData,\r\n        fromParty: MessageFrom.OtherParty,\r\n      };\r\n    }\r\n  }\r\n\r\n  /** Logic used in ListControlerBase showEditDialog */\r\n  public getEditDialogLogic(): any {\r\n    return {};\r\n  }\r\n\r\n  /** Sums daily total time */\r\n  public countDailyHours(date: string): number {\r\n    let total = 0;\r\n    const dailyMessages = this.list.filter(x => Dates.getFormattedDate(x.contentData.period.start) === Dates.getFormattedDate(date));\r\n    dailyMessages.forEach(message => {\r\n      total = total + message.contentData.totalTime;\r\n    });\r\n    if (total === 0 ) {\r\n      return 0;\r\n    }\r\n    return total;\r\n  }\r\n\r\n  /** Sum weekly totalTime */\r\n  public get weeklyHours(): number {\r\n    let total = 0;\r\n    const dailyMessages = this.list.filter(x => Dates.isSameOrAfter(x.contentData.period.start, this.firstDayOfCurrentWeek) && Dates.isSameOrBefore(x.contentData.period.start, this.lastDayOfCurrentWeek));\r\n    dailyMessages.forEach(message => {\r\n      total = total + message.contentData.totalTime;\r\n    });\r\n    if (total === 0 ) {\r\n      return 0;\r\n    }\r\n    return total;\r\n  }\r\n\r\n\r\n  /** Sets current week for ui */\r\n  public setCurrentWeek(): void {\r\n    this.firstDayOfCurrentWeekFormatted = Dates.getFormattedDate(Dates.startEnd(this.currentDate, \"start-week\"));\r\n    this.lastDayOfCurrentWeekFormatted = Dates.getFormattedDate(Dates.startEnd(this.currentDate, \"end-week\"));\r\n    this.firstDayOfCurrentWeek = Dates.startEnd(this.currentDate, \"start-week\");\r\n    this.lastDayOfCurrentWeek = Dates.startEnd(this.currentDate, \"end-week\");\r\n    this.currentWeek = [\r\n      {\r\n        dayName: \"Ma\",\r\n        date: Dates.format(this.firstDayOfCurrentWeek, \"YYYY-MM-DD\"),\r\n        displayDate: Dates.format(this.firstDayOfCurrentWeek, \"DD.MM\"),\r\n        isCollapsed: true\r\n      },\r\n      {\r\n        dayName: \"Ti\",\r\n        date: Dates.format(Dates.add(this.firstDayOfCurrentWeek, 1, \"day\"), \"YYYY-MM-DD\"),\r\n        displayDate: Dates.format(Dates.add(this.firstDayOfCurrentWeek, 1, \"day\"), \"DD.MM\"),\r\n        isCollapsed: true\r\n      },\r\n      {\r\n        dayName: \"Ke\",\r\n        date: Dates.format(Dates.add(this.firstDayOfCurrentWeek, 2, \"day\"), \"YYYY-MM-DD\"),\r\n        displayDate: Dates.format(Dates.add(this.firstDayOfCurrentWeek, 2, \"day\"), \"DD.MM\"),\r\n        isCollapsed: true\r\n      },\r\n      {\r\n        dayName: \"To\",\r\n        date: Dates.format(Dates.add(this.firstDayOfCurrentWeek, 3, \"day\"), \"YYYY-MM-DD\"),\r\n        displayDate: Dates.format(Dates.add(this.firstDayOfCurrentWeek, 3, \"day\"), \"DD.MM\"),\r\n        isCollapsed: true\r\n      },\r\n      {\r\n        dayName: \"Pe\",\r\n        date: Dates.format(Dates.add(this.firstDayOfCurrentWeek, 4, \"day\"), \"YYYY-MM-DD\"),\r\n        displayDate: Dates.format(Dates.add(this.firstDayOfCurrentWeek, 4, \"day\"), \"DD.MM\"),\r\n        isCollapsed: true\r\n      },\r\n      {\r\n        dayName: \"La\",\r\n        date: Dates.format(Dates.add(this.firstDayOfCurrentWeek, 5, \"day\"), \"YYYY-MM-DD\"),\r\n        displayDate: Dates.format(Dates.add(this.firstDayOfCurrentWeek, 5, \"day\"), \"DD.MM\"),\r\n        isCollapsed: true\r\n      },\r\n      {\r\n        dayName: \"Su\",\r\n        date: Dates.format(Dates.add(this.firstDayOfCurrentWeek, 6, \"day\"), \"YYYY-MM-DD\"),\r\n        displayDate: Dates.format(Dates.add(this.firstDayOfCurrentWeek, 6, \"day\"), \"DD.MM\"),\r\n        isCollapsed: true\r\n      }\r\n    ];\r\n  }\r\n\r\n  /** Gets the project text for a project */\r\n  public getDimensionOptionText(value: string): string {\r\n    if (value) {\r\n      const lk1 = (this.crudController?.employingRelation?.settings?.costAccounting?.dimensions ||\r\n        this.sessionService.session.settings?.costAccounting?.dimensions || undefined)\r\n      .find((x) => x.name = \"lk1\");\r\n      if (lk1) {\r\n          return lk1.options.find( (x) => x.value === value)?.text ?? \"\";\r\n      }\r\n    }\r\n    return \"\";\r\n  }\r\n\r\n\r\n  /**\r\n   * Controlls visibility of dates messages\r\n   * @param date Used to find correct date from currentWeek\r\n   */\r\n  public setHourlyRecordsVisible(date: string): void {\r\n    const targetDate = this.currentWeek.find(x => x.date === date);\r\n    targetDate.isCollapsed = !targetDate.isCollapsed;\r\n  }\r\n\r\n  /** Change current week and reload week data */\r\n  public changeWeek(next: boolean): void {\r\n    if (next) {\r\n      this.currentDate = Dates.add(this.currentDate, 7, \"day\");\r\n    } else {\r\n      this.currentDate = Dates.add(this.currentDate, -7, \"day\");\r\n    }\r\n    this.setCurrentWeek();\r\n  }\r\n\r\n  /** Get current weeknumber */\r\n  public get currentWeekNumber(): number {\r\n    return Dates.getWeekNumber(this.currentDate);\r\n  }\r\n\r\n  /**\r\n   * Check if provided date is saturday or sunday or not workday\r\n   * @param date Used date to determine if saturday or sunday\r\n   * @returns Boolean if date is saturday or sunday\r\n   */\r\n  public isHoliday(date: string): boolean {\r\n    return !Dates.isWorkday(date) || Dates.isHoliday(date);\r\n  }\r\n\r\n  /**\r\n   * Checks if expand button should be visible\r\n   * @param date used to search correct objects\r\n   * @returns Boolean that indicates if expand chevron should be visible\r\n   */\r\n  public showExpandButton(date: string): boolean {\r\n      const messages = this.list.filter(x => Dates.getFormattedDate(x.contentData.period.start) === Dates.getFormattedDate(date));\r\n      return messages.length > 0;\r\n  }\r\n\r\n  /**\r\n   * Get blank message object for edit dialog\r\n   * @param date is used to create start date\r\n   * @returns Blank message object\r\n   */\r\n  public getEditDialogItem(date: string): Message {\r\n    if (this.reportType === ThreadedMessageType.HourlyReport) {\r\n      return {\r\n        type: this.reportType,\r\n        content: \"Tuntikirjaus\",\r\n        fromParty: MessageFrom.OtherParty,\r\n        contentData: {\r\n          modification: TimesheetInputModification.CREATE,\r\n          project: \"\",\r\n          projectText: \"\",\r\n          period: {\r\n            start: date\r\n          },\r\n          totalTime: 450\r\n        }\r\n      };\r\n    }\r\n\r\n    if (this.reportType === ThreadedMessageType.TimeReport) {\r\n      return {\r\n        type: this.reportType,\r\n        content: \"Työaikakirjaus\",\r\n        fromParty: MessageFrom.OtherParty,\r\n        contentData: {\r\n          modification: TimesheetInputModification.CREATE,\r\n          project: \"\",\r\n          projectText: \"\",\r\n          period: {\r\n            start: date\r\n          },\r\n          totalTime: 450\r\n        }\r\n      };\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Get button style for date. Handles dirrerent styles for workday, today, holiday\r\n   * @param date Day used to figure date\r\n   * @returns button class as string\r\n   */\r\n  public getDateStyle(date: string) {\r\n    if (date === Dates.getToday()) {\r\n      return \"bg-info\";\r\n    }\r\n\r\n    if (!Dates.isWorkday(date) || Dates.isHoliday(date)) {\r\n      return \"bg-primary\";\r\n    }\r\n\r\n    return \"btn btn-default\";\r\n  }\r\n\r\n  /**\r\n   * Override for ListControllerBase showEditDialog\r\n   * @param item Item to edit or string \"new\" for creating a new one.\r\n   * @param isNew Optional way of specifying that the item is a new item (with default values, not yet added to the list).\r\n   * If item is string \"new\", this parameter will have no effect (will always be true).\r\n   */\r\n  public showEditDialog(item: Message | \"new\", isNew = false) {\r\n    if (!item) {\r\n      throw new Error(\"showEditDialog called without a parameter.\");\r\n    }\r\n    if (item === \"new\") {\r\n      isNew = true;\r\n      item = this.getBlank();\r\n    }\r\n\r\n    const lk1 = (this.crudController?.employingRelation?.settings?.costAccounting?.dimensions ||\r\n      this.sessionService.session.settings?.costAccounting?.dimensions || undefined)\r\n    .find((x) => x.name = \"lk1\");\r\n\r\n    const costAccountingSettings = lk1 ?\r\n      {\r\n        options: lk1.options,\r\n        label: lk1.label,\r\n      } : null;\r\n\r\n    this.uiHelpers.openEditDialog(this.getEditDialogTemplateUrl(), item, {...this.getEditDialogLogic(), costAccountingSettings}).then((result) => {\r\n      if (result.action === \"ok\" || result.action === \"ok-no-save\" ) {\r\n        if (result.item.type === ThreadedMessageType.TimeReport) {\r\n          const startTime = new Date(`${Dates.getToday()}T${result.item.contentData.startTime}:00`);\r\n          const endTime = new Date(`${Dates.getToday()}T${result.item.contentData.endTime}:00`);\r\n          result.item.contentData.totalTime = Math.floor((endTime.getTime() - startTime.getTime()) / 60000);\r\n        }\r\n        if (isNew) {\r\n          this.list.push(result.item);\r\n        }\r\n        if (( isNew || result.hasChanges) && result.action !== \"ok-no-save\") {\r\n          this.commit();\r\n        }\r\n      } else if (result.action === \"delete\" || result.action === \"delete-no-save\") {\r\n        if (!isNew) {\r\n          this.delete(item as Message);\r\n          if (result.action !== \"delete-no-save\" ) {\r\n            this.commit();\r\n          }\r\n        }\r\n      } else {\r\n        // No changes, cancel\r\n      }\r\n      });\r\n  }\r\n\r\n}\r\n","import { Message, ThreadedMessageType, MessageThread } from \"@salaxy/core\";\r\n\r\nimport { ListControllerBase, ListControllerBaseBindings } from \"../bases\";\r\n\r\nimport { UiHelpers } from \"../../services\";\r\n\r\nclass WorkerExpenseReportControllerBindings extends ListControllerBaseBindings {\r\n  /** Type of the timesheet. Options are hourlyReport and timeReport */\r\n  public reportType =  \"<\";\r\n  /**\r\n   * CRUD controller that typically defines the values for url template and\r\n   */\r\n  public crudController =  \"<\";\r\n}\r\n\r\n/** Controller handles expense usecases*/\r\nexport class WorkerExpenseReportController extends ListControllerBase<MessageThread, Message> {\r\n  /** Bindings for components that use this controller */\r\n  public static bindings = new WorkerExpenseReportControllerBindings();\r\n\r\n  /** Type of the timesheet. Options are hourlyReport and timeReport */\r\n  public reportType: \"expense\" | \"travel\";\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n   public static $inject = [\"UiHelpers\"];\r\n\r\n   private _rowTypes = [\"expenses\", \"milageDaily\", \"milageOther\", \"milageOwnCar\", \"dailyAllowance\"];\r\n\r\n   /** Constructor for dependency injection */\r\n   constructor(\r\n     uiHelpers: UiHelpers\r\n   ) {\r\n     super(uiHelpers);\r\n   }\r\n\r\n   /** Template for edit UI that is shown in a modal dialog. */\r\n   public getEditDialogTemplateUrl(): string {\r\n    throw new Error(\"Method not implemented.\");\r\n  }\r\n\r\n  /**\r\n   * Creating of a new item\r\n   */\r\n  public getBlank(): Message {\r\n    throw new Error(\"Method not implemented.\");\r\n  }\r\n\r\n  /**\r\n   * List of items\r\n   */\r\n  public get list(): Message[] {\r\n    if (!this.parent) {\r\n      return null;\r\n    }\r\n    return this.parent.messages;\r\n  }\r\n\r\n  /**\r\n   * Ensure that atleast one message exists\r\n   */\r\n   public getCalcRowMessage() {\r\n    const messageIndex = this.list.findIndex(x => x.type === ThreadedMessageType.CalcRow);\r\n    if (messageIndex >= 0) {\r\n      return this.list[messageIndex];\r\n    }\r\n\r\n    this.list.unshift({type: ThreadedMessageType.CalcRow, contentData: {rows: []}});\r\n    return this.list[0];\r\n  }\r\n\r\n  /**\r\n   * Get rowTypes based on report type\r\n   */\r\n  public getRowTypes() {\r\n    // TODO: implement dirrerent row types\r\n    if (this.reportType === \"expense\") {\r\n      return this._rowTypes;\r\n    }\r\n    if (this.reportType === \"travel\") {\r\n      return this._rowTypes;\r\n    }\r\n  }\r\n\r\n\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Ajax, Language, Role, Translations } from \"@salaxy/core\";\r\nimport { OnboardingService, SessionService, UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Base controller for accountant wizard management.\r\n */\r\nexport class AccountantWizardController implements angular.IController {\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"AjaxNg1\",\r\n    \"OnboardingService\",\r\n    \"SessionService\",\r\n    \"UiHelpers\",\r\n    \"$location\"\r\n  ];\r\n\r\n  constructor(private ajax: Ajax, private onboardingService: OnboardingService, private sessionService: SessionService, private uiHelpers: UiHelpers, private $location: angular.ILocationService) {}\r\n\r\n  /** Opens wizard as modal dialog */\r\n  public async openAccountantWizardDialog(): Promise<any> {\r\n    const getOrigin = () =>\r\n      window.location.protocol +\r\n      \"//\" +\r\n      window.location.hostname +\r\n      (window.location.port ? \":\" + window.location.port : \"\");\r\n\r\n    return this.onboardingService.getOnboardingData().then( () => {\r\n      this.onboardingService.model.company.language = Translations.getLanguage() as Language;\r\n      this.onboardingService.model.company.roles = [Role.Accountant ];\r\n      this.onboardingService.model.signature.isProcura = false;\r\n      this.onboardingService.model.ui.successUrl = getOrigin() + `/accountant-wizard-success?lang=${Translations.getLanguage()}&id=${this.onboardingService.model.id}#access_token=` + this.ajax.getCurrentToken();\r\n\r\n      return this.onboardingService.save().then( () => {\r\n        const url = getOrigin() + `/accountant-wizard-popup?lang=${Translations.getLanguage()}&id=${this.onboardingService.model.id}#access_token=` + this.ajax.getCurrentToken();\r\n        return this.uiHelpers.showExternalDialog(this.onboardingService.model.id, url, { id: this.onboardingService.model.id }, { width: 1080, height: 800 }).then((result) => {\r\n          if (result?.action != \"cancel\") {\r\n            return this.sessionService.checkSession();\r\n          } else {\r\n            return;\r\n          }\r\n        });\r\n      });\r\n    });\r\n  }\r\n\r\n  /** Launches company wizard. */\r\n  public launchAccountantWizard() {\r\n    const data =  this.readTokenFromUrl(this.$location.absUrl(), \"data=\");\r\n    if (data) {\r\n      const id = JSON.parse(atob(decodeURIComponent(data)))?.id;\r\n      if (id) {\r\n        return this.onboardingService.launchCompanyOnboarding(id);\r\n      }\r\n    }\r\n  }\r\n\r\n  private readTokenFromUrl(url: string, key: string): string {\r\n    const start = url.toLowerCase().indexOf(key);\r\n    if (start >= 0) {\r\n      const end = url.indexOf(\"&\", start);\r\n      return end >= 0\r\n        ? url.substring(start + key.length, end)\r\n        : url.substring(start + key.length);\r\n    }\r\n    return null;\r\n  }\r\n}","import angular from \"angular\";\r\n\r\nimport { Attachment, Records, Record, Translations, WorkflowEvent, RecordListItem } from \"@salaxy/core\";\r\n\r\nimport { UiHelpers, UploadService, WorkflowService } from \"../../services\";\r\n\r\nimport { ApiCrudObjectController } from \"../bases/ApiCrudObjectController\";\r\n\r\n\r\n/**\r\n * Base controller for records management.\r\n */\r\nexport class RecordsController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"Records\",\r\n    \"UiHelpers\",\r\n    \"UploadService\",\r\n    \"WorkflowService\"\r\n  ];\r\n\r\n  /** Current records. */\r\n  public records: Record[];\r\n\r\n  /** Readonly binding */\r\n  public readOnly: boolean;\r\n\r\n  /** API CRUD controller for the workflow object.*/\r\n  public apiCtrl: ApiCrudObjectController<Record, RecordListItem>;\r\n\r\n  /** Entity type */\r\n  public entityType: string;\r\n\r\n  /** Loding indicator */\r\n  public isLoading: boolean;\r\n\r\n  private _wfType = \"EmployerMessageRecord\";\r\n  private _events: WorkflowEvent[] = [];\r\n\r\n  constructor(\r\n    protected api: Records,\r\n    protected uiHelpers: UiHelpers,\r\n    protected uploadService: UploadService,\r\n    protected workflowService: WorkflowService,\r\n  ) { }\r\n\r\n  /**\r\n   * Loads the records for the entity.\r\n   */\r\n  public $onInit() {\r\n    this.reload();\r\n  }\r\n\r\n  /**\r\n   * Reloads data\r\n   */\r\n  public reload() {\r\n    this.isLoading = true;\r\n    this.api.getForEntity(this.entityType, this.entityId).then((data) => {\r\n      this.records = data;\r\n      this.isLoading = false;\r\n    });\r\n  }\r\n\r\n  /** Returns events for the record. */\r\n  public getEvents(item: Record) {\r\n    return this.events.filter((x) => x.record && x.record === item.id);\r\n  }\r\n\r\n  /** Returns single event for the record. */\r\n  public getSingleEvent(item: Record): WorkflowEvent {\r\n    const wfEvents = this.getEvents(item);\r\n    return wfEvents.length > 0 ? wfEvents[0] : {};\r\n  }\r\n\r\n  /**\r\n   * Shows the edit dialog.\r\n   * @param item Item to edit or to create.\r\n   * @param index Current index. -1 for new.\r\n   */\r\n  public showEditRecord(item: Record, index = -1) {\r\n    const logic = {\r\n      title: index < 0 ? Translations.get(\"SALAXY.UI_Terms.add\") : this.readOnly ? Translations.get(\"SALAXY.UI_Terms.show\") : Translations.get(\"SALAXY.UI_Terms.edit\"),\r\n      showDelete: index > -1 && !this.readOnly,\r\n      readOnly: this.readOnly,\r\n      recordTypes: [],\r\n      getAttachmentDownloadUrl: (attachment) => this.getAttachmentDownloadUrl(attachment),\r\n      getAttachmentIcon: (attachment) => this.getAttachmentIcon(attachment),\r\n      uploadAttachments: (files, attachments) => this.uploadAttachments(files, attachments),\r\n    };\r\n\r\n    item.entityType = this.entityType;\r\n    item.entityId = this.entityId;\r\n    const recordAndEvent = { record: item, wfEvent: this.getSingleEvent(item)};\r\n\r\n    logic.recordTypes.push(... this.records.map(x => x.recordType).filter((v, i, a) => a.indexOf(v) === i));\r\n    logic.recordTypes.sort();\r\n    this.uiHelpers.openEditDialog(\"salaxy-components/modals/records/Record.html\", recordAndEvent, logic,\"lg\").then((result) => {\r\n      if (result.action === \"ok\") {\r\n        if (index === -1) {\r\n          // Add\r\n          this.api.save(result.item.record).then((data) => {\r\n            this.records.push(data);\r\n            this.saveWorkflowEvent(data, result.item.wfEvent);\r\n          });\r\n        } else {\r\n          // Modify\r\n          this.api.save(result.item.record).then((data) => {\r\n            angular.copy(data, this.records[index]);\r\n            this.saveWorkflowEvent(this.records[index], result.item.wfEvent);\r\n          });\r\n        }\r\n      } else if (result.action === \"delete\") {\r\n        this.deleteRecord(result.item.record, index);\r\n        this.deleteWorkflowEvent(result.item.wfEvent);\r\n      }\r\n    });\r\n    this.api.getRecordTypes().then((serverRecordTypes) => {\r\n      logic.recordTypes.push(... (serverRecordTypes ?? []));\r\n      logic.recordTypes.splice(0, logic.recordTypes.length, ...logic.recordTypes.filter((v, i, a) => a.indexOf(v) === i));\r\n      logic.recordTypes.sort();\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Deletes one record\r\n   * @param item Item to delete.\r\n   * @param index Current index.\r\n   */\r\n  public deleteRecord(item: Record, index = -1) {\r\n    if (index > -1) {\r\n      // Delete\r\n      const wfItem = this.getSingleEvent(item);\r\n      return this.api.delete(item.id).then(() => {\r\n        this.records.splice(index, 1);\r\n        return this.deleteWorkflowEvent(wfItem);\r\n      });\r\n    }\r\n  }\r\n\r\n  /** Returns file icon for the attachment. */\r\n  public getAttachmentIcon(attachment: Attachment): string {\r\n    return this.uploadService.getFileIcon(attachment?.fileName);\r\n  }\r\n\r\n  /** Returns download url for the attachment. */\r\n  public getAttachmentDownloadUrl(attachment: Attachment): string {\r\n    return this.uploadService.getFileUrl(attachment?.contentId);\r\n  }\r\n\r\n  /** Returns the upload url for the attachment */\r\n  public getAttachmentUploadUrl(): string {\r\n    return this.api.getRecordUploadUrl(this.entityType, this.entityId);\r\n  }\r\n\r\n  /**\r\n   * Uploads the attachments to the server, and adds them to the attchment collection.\r\n   * @param files The files collection from the upload component\r\n   * @param attachments The attachment collection for the results.\r\n   */\r\n  private uploadAttachments(files: any[], attachments: Attachment[]): any {\r\n    if (files && files.length) {\r\n      const uploadUrl = this.getAttachmentUploadUrl();\r\n      const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.MessageThreadComponent.uploadFilesSaving\");\r\n      return this.uploadService.upload<Attachment[]>(\r\n        uploadUrl, { files }).then((data) => {\r\n          if (data) {\r\n            attachments.push(...data);\r\n          }\r\n          loader.dismiss();\r\n          return data;\r\n        }).catch((response) => {\r\n          loader.dismiss();\r\n          this.uiHelpers.showAlert(\"SALAXY.UI_Terms.error\", \"SALAXY.NG1.MessageThreadComponent.uploadFilesError\");\r\n          throw new Error(response);\r\n        });\r\n    }\r\n  }\r\n\r\n  private deleteWorkflowEvent(wfEvent: WorkflowEvent): Promise<any> {\r\n    return this.cleanWorkflowEvents().then( () => {\r\n      if (wfEvent.id) {\r\n        return this.workflowService.deleteWorkflowEvent(this.apiCtrl, wfEvent.id);\r\n      }\r\n      return Promise.resolve(this.apiCtrl.current);\r\n    });\r\n  }\r\n\r\n  private saveWorkflowEvent(item: Record, wfEvent: WorkflowEvent): Promise<any> {\r\n    if (wfEvent.message) {\r\n      return this.cleanWorkflowEvents().then( () => {\r\n        // add or update\r\n        wfEvent.record = item.id;\r\n        wfEvent.type = this._wfType;\r\n        return this.workflowService.saveWorkflowEvent(this.apiCtrl, wfEvent);\r\n      });\r\n    }\r\n    else\r\n    {\r\n      // delete\r\n      return this.deleteWorkflowEvent(wfEvent);\r\n    }\r\n  }\r\n\r\n  private async cleanWorkflowEvents():Promise<any> {\r\n    // All events with no record, or with record and no matching record.id\r\n    const orphans = this.events.filter( (x) => x.id && (!x.record || (x.record && !this.records.some( (r) => x.record === r.id))));\r\n    // delete all orphans in sequence, otherwise the events are not deleted correctly\r\n    for(const orphan of orphans) {\r\n      await this.workflowService.deleteWorkflowEvent(this.apiCtrl, orphan.id);\r\n    }\r\n    return this.apiCtrl.current;\r\n  }\r\n\r\n  private get entityId(): string {\r\n    return this.entityType == \"employment\" ?\r\n     // Support old worker based cruds (not sure if this hack is needed anymore)\r\n    (this.apiCtrl.getApi().getBaseUrl() === \"/accounts/workers\" ? (this.apiCtrl.current as any).employmentId : this.apiCtrl.current.id) :\r\n    this.entityType == \"account\" ? null : this.apiCtrl.current.id;\r\n  }\r\n\r\n  private get events(): WorkflowEvent[] {\r\n    const eventsOfType = ((this.apiCtrl.current as any)?.workflowData?.events ?? []).filter((x) => x.type == this._wfType);\r\n    this.modifyArray(eventsOfType, this._events);\r\n    return this._events;\r\n  }\r\n\r\n  private modifyArray(\r\n    source: any[],\r\n    target: any[]) {\r\n    if (angular.equals(source, target)) {\r\n      return;\r\n    }\r\n    target.splice(0, target.length);\r\n    target.push(...source);\r\n  }\r\n\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { AccountingData, BlobFile, Dates, FileListItem, Files, Reports, Translations } from \"@salaxy/core\";\r\n\r\nimport { UiHelpers } from \"../../services\";\r\n\r\nimport { ApiCrudObjectController } from \"../bases\";\r\n\r\n/**\r\n * The new ApiCrudObject type of CRUD controller for the BlobFile of the accounting report.\r\n */\r\nexport class AccountingReportCrudController extends ApiCrudObjectController<BlobFile, FileListItem> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"Files\",\r\n    \"Reports\",\r\n    \"UiHelpers\",\r\n    \"$location\",\r\n    \"$routeParams\",\r\n    \"$timeout\",\r\n  ];\r\n\r\n  /** Default query options for panel */\r\n  public panelQueryOptions = {\r\n    $filter: \"entityType eq 'MonthlyReport.MonthlyAccounting'\",\r\n    $orderby: \"logicalDate desc\",\r\n    $top: 5,\r\n  };\r\n\r\n  /** Data reader for selected items. */\r\n  public selectionDataReader = {\r\n    /** Function to read data into given array */\r\n    read: (target: string, ruleSet: string, arr: AccountingData[], message: string): Promise<void> => {\r\n      const items = this.odataController.selectedItems;\r\n      let counter = 0;\r\n      const next = (): Promise<void> => {\r\n        if (counter === items.length) {\r\n          return Promise.resolve();\r\n        }\r\n        const item = items[counter++];\r\n        return this.reportsApi.getAccountingData(item.id, target, ruleSet).then((data) => {\r\n          if (message) {\r\n            const wfEvent = {\r\n              type: \"PartnerMessageClosed\",\r\n              ui: \"success\" as any,\r\n              message,\r\n            };\r\n            return this.filesApi.saveWorkflowEvent(item, wfEvent).then(() => {\r\n              this.setWorkflowEvent(item, wfEvent);\r\n              if (data) {\r\n                arr.push(data);\r\n              }\r\n              return next();\r\n            });\r\n          }\r\n          else {\r\n            if (data) {\r\n              arr.push(data);\r\n            }\r\n            return next();\r\n          }\r\n        });\r\n      };\r\n      return next().then(() => {\r\n        return Promise.resolve();\r\n      });\r\n    },\r\n    /** Optional label for data export */\r\n    exportLabel: Translations.get(\"SALAXY.NG1.AccountingReportToolsComponent.exportLabel\"),\r\n    /** Indicates if the export is not possible */\r\n    disabled: () => !this.odataController.selectedItems || this.odataController.selectedItems.length === 0,\r\n    /* Indicates if row is expandable */\r\n    showExpand: false,\r\n    /* Indicates if rows exists*/\r\n    hasRows: () => !this.odataController.selectedItems || this.odataController.selectedItems.length === 0,\r\n  };\r\n\r\n  /** Data reader for the current loaded data. */\r\n  public currentDataReader = {\r\n    /** Function to read data into given array */\r\n    read: (target: string, ruleSet: string, arr: AccountingData[], message: string): Promise<void> => {\r\n      if (this.currentData) {\r\n        if (message) {\r\n          const wfEvent = {\r\n            type: \"PartnerMessageClosed\",\r\n            ui: \"success\" as any,\r\n            message,\r\n          };\r\n          return this.filesApi.saveWorkflowEvent(this.current, wfEvent).then(() => {\r\n            arr.push(this.currentData);\r\n            return this.reload().then(() => {\r\n              return Promise.resolve();\r\n            });\r\n          });\r\n        }\r\n        else {\r\n          arr.push(this.currentData);\r\n          return Promise.resolve();\r\n        }\r\n      }\r\n      else {\r\n        return Promise.resolve();\r\n      }\r\n    },\r\n    /** Optional label for data export */\r\n    exportLabel: null,\r\n    /** Indicates if the export is not possible */\r\n    disabled: () => !this.currentData,\r\n    /* Indicates if row is expandable */\r\n    showExpand: true,\r\n    /* Indicates if rows exists*/\r\n    hasRows: () => !this.currentData?.ledgerAccounts\r\n  };\r\n\r\n  /** Status for current data . */\r\n  private currentDataStatus: \"initial\" | \"loading\" | string = \"initial\";\r\n\r\n  private _currentData: AccountingData;\r\n\r\n  private logicalDate: string;\r\n\r\n  constructor(\r\n    private filesApi: Files,\r\n    private reportsApi: Reports,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    private $timeout: angular.ITimeoutService,\r\n\r\n  ) { // Dependency injection\r\n    super(filesApi, uiHelpers, $location, $routeParams);\r\n  }\r\n\r\n  /**\r\n   * Initialization code.\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n\r\n    if (Dates.getMonth(\"today\") === 1) {\r\n      this.logicalDate = Dates.format(Dates.add(\"today\",-1, \"year\"),\"YYYY-01-01\");\r\n    } else {\r\n      this.logicalDate = Dates.format(\"today\",\"YYYY-01-01\");\r\n    }\r\n  }\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"/accounting\",\r\n      detailsUrl: this.detailsUrl || \"/accounting/details/\",\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/ApiCrudObject.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n\r\n  /** Returns OData filter. */\r\n  public getODataFilter = (): string => {\r\n    const logicalDateExcluding = Dates.format(Dates.add(this.logicalDate,1, \"year\"),\"YYYY-01-01\");\r\n    return `entityType eq 'MonthlyReport.MonthlyAccounting' and logicalDate ge ${this.logicalDate} and logicalDate lt ${logicalDateExcluding}`;\r\n  };\r\n\r\n  /** Data reader for one item. */\r\n  public getItemDataReader = (item: {\r\n    /** List item id */\r\n    id: string,\r\n    /** List item owner */\r\n    owner: string,\r\n  }) => {\r\n    return {\r\n      /** Function to read data into given array */\r\n      read: (target: string, ruleSet: string, arr: AccountingData[], message: string): Promise<void> => {\r\n        (item as any).isReading = true;\r\n        return this.reportsApi.getAccountingData(item.id, target, ruleSet).then((data) => {\r\n          if (message) {\r\n            const wfEvent = {\r\n              type: \"PartnerMessageClosed\",\r\n              ui: \"success\" as any,\r\n              message,\r\n            };\r\n            return this.filesApi.saveWorkflowEvent(item, wfEvent).then(() => {\r\n              this.setWorkflowEvent(item as any, wfEvent);\r\n              if (data) {\r\n                arr.push(data);\r\n              }\r\n              (item as any).isReading = false;\r\n              return Promise.resolve();\r\n            });\r\n          }\r\n          else {\r\n            if (data) {\r\n              arr.push(data);\r\n            }\r\n            (item as any).isReading = false;\r\n            return Promise.resolve();\r\n          }\r\n        });\r\n      },\r\n      /** Optional label for data export */\r\n      exportLabel: null,\r\n      /** Indicates if the export is not possible */\r\n      disabled: () => false,\r\n      /* Indicates if row is expandable */\r\n      showExpand: true,\r\n      /* Indicates if rows exists*/\r\n      hasRows: true\r\n    };\r\n  };\r\n\r\n  /** Event handler for logical date. */\r\n  public logicalDateChanged() {\r\n    if (this.odataController.selectedItems) {\r\n      this.odataController.selectedItems.splice(0, this.odataController.selectedItems.length);\r\n    }\r\n    this.odataController.options.$filter = this.getODataFilter();\r\n    this.odataController.refresh();\r\n  }\r\n\r\n  /** Unselect all */\r\n  public unselectAll() {\r\n    if (this.odataController.selectedItems) {\r\n      this.odataController.selectedItems.splice(0, this.odataController.selectedItems.length);\r\n    }\r\n  }\r\n\r\n  /** Select all */\r\n  public selectAll() {\r\n    if (this.odataController.selectedItems && this.odataController.items) {\r\n      this.odataController.selectedItems.splice(0, this.odataController.selectedItems.length);\r\n      this.odataController.selectedItems.push(...this.odataController.items);\r\n    }\r\n  }\r\n\r\n  /** Accounting data of the current item. */\r\n  public get currentData() {\r\n    if (this.currentId) {\r\n      this.loadCurrentData();\r\n    } else {\r\n      // No id, reset data.\r\n      this._currentData = null;\r\n      this.currentDataStatus = \"initial\";\r\n    }\r\n    return this._currentData;\r\n  }\r\n\r\n  /** Load current data */\r\n  public loadCurrentData(targetId: string = null) {\r\n    if (targetId == null) {\r\n      if (this.currentDataStatus === \"initial\") {\r\n        targetId = \"default\";\r\n      } else if (this.currentDataStatus === \"loading\") {\r\n        return;\r\n      } else {\r\n        targetId = this.currentDataStatus.split(\".\")[1];\r\n      }\r\n    }\r\n    const currentLoadingId = `${this.currentId}.${targetId}`;\r\n    if (this.currentDataStatus !== currentLoadingId && this.currentDataStatus !== \"loading\") {\r\n      // Start downloading for the new id\r\n      this.currentDataStatus = \"loading\";\r\n      const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n      this.reportsApi.getAccountingData(this.currentId, targetId, null).then((data) => {\r\n        if (data) {\r\n          this._currentData = data;\r\n        }\r\n        this.currentDataStatus = currentLoadingId;\r\n        loading.dismiss();\r\n      });\r\n    }\r\n  }\r\n\r\n  private setWorkflowEvent(\r\n    item: {\r\n      /** List item id */\r\n      flags: string[],\r\n      /** List item owner */\r\n      messages: string[],\r\n    },\r\n    wfEvent: {\r\n      /** workflow type */\r\n      type: string,\r\n      /** ui type */\r\n      ui: string,\r\n      /** message */\r\n      message: string,\r\n    }) {\r\n    item.flags = (item.flags || []).filter((x) => x !== wfEvent.type);\r\n    item.messages = (item.messages || []).filter((x) => !x.startsWith(wfEvent.type));\r\n\r\n    item.flags.push(wfEvent.type);\r\n    item.messages.push(`${wfEvent.type} (Ui${wfEvent.ui}): ${wfEvent.message} ()`);\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { AccountingData, Calculation, CalculationListItem, Dates, PeriodDateKind, PeriodType, Reports } from \"@salaxy/core\";\r\nimport { UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Provides functionality for building ad hoc accounting reports.\r\n */\r\nexport class AccountingReportQueryController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"Reports\",\r\n    \"UiHelpers\",\r\n  ];\r\n\r\n  /**\r\n   * Report view table only (partial) or pdf preview (full)\r\n   * Defaults to 'partial'\r\n   */\r\n  public view: \"partial\" | \"full\";\r\n  /** Query type: Query period or set of id's from database or calcs to specify the calculations. */\r\n  public queryType: \"periodQuery\" | \"selectionQuery\" | \"calcs\" = \"periodQuery\";\r\n\r\n  /** Period type for the query. */\r\n  public periodType: PeriodType = PeriodType.Month;\r\n\r\n  /** Period date kind for the query. */\r\n  public periodDateKind: PeriodDateKind = PeriodDateKind.PaidAtDate;\r\n\r\n  /** Ref date for the period. */\r\n  public refDate?: string;\r\n\r\n  /** End date for the custom period. */\r\n  public endDate?: string;\r\n\r\n  /** Accounting data */\r\n  public data: AccountingData;\r\n\r\n  /**Selected report language */\r\n  public lang: string;\r\n\r\n  /**\r\n   * Calculations that are selected by used to show be fetched and shown in reports.\r\n   * Only the ID is really used: the rest of the calculation data is fetched from database.\r\n   */\r\n  public calculations: CalculationListItem[] = [];\r\n\r\n  /**\r\n   * Calculations that are shown in the database directly.\r\n   * If set, will hide the query interface and set queryType accordingly (only in init).\r\n   */\r\n  public calcs: Calculation[];\r\n\r\n  /** Data reader for the control. */\r\n  public dataReader = {\r\n  /**\r\n   * Function to read data into given array\r\n   * TODO: Should make interface for this or otherwise go-through.\r\n   */\r\n  // eslint-disable-next-line @typescript-eslint/no-unused-vars\r\n   read: (target: string, ruleSet: string, arr: AccountingData[], message: string): Promise<void> => {\r\n      if (this.data) {\r\n        arr.push(this.data);\r\n      }\r\n      return Promise.resolve();\r\n    },\r\n    /** Optional label for data export */\r\n    exportLabel: null,\r\n    /** Indicates if the export is not possible */\r\n    disabled: () => !this.data,\r\n    /* Indicates if row is expandable */\r\n    showExpand: true,\r\n    /* Indicates if rows exists*/\r\n    hasRows: () => !this.data?.ledgerAccounts\r\n  };\r\n\r\n  constructor(\r\n    private reportsApi: Reports,\r\n    private uiHelpers: UiHelpers,\r\n  ) {\r\n    // Dependency injection\r\n  }\r\n\r\n  /**\r\n   * Initialize controller values.\r\n   */\r\n  public $onInit() {\r\n    this.view = this.view || \"partial\";\r\n    this.refDate = Dates.format(Dates.add(\"today\",-1, \"month\"),\"YYYY-MM-01\");\r\n    if (this.calcs?.length > 0) {\r\n      this.queryType = \"calcs\";\r\n      this.queryData();\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Opens the list of calculations into a dialog window for selection and then adds them to the selected calculations\r\n   * @param category Either \"paid\" or \"draft\".\r\n   */\r\n  public addCalcs(category: \"paid\" | \"draft\" = \"draft\") {\r\n    const selectedCalculations: CalculationListItem[] = [];\r\n    this.uiHelpers.openEditDialog(\r\n      \"salaxy-components/modals/calc/CalcList.html\",\r\n      selectedCalculations,\r\n      {\r\n        title: (category === \"paid\" ? \"Valitse maksetut palkat\" : \"Valitse luonnokset\"),\r\n        category,\r\n      }).then((result) => {\r\n        if (result.action === \"ok\" && result.item.length > 0) {\r\n          for (const selectedCalculation of result.item) {\r\n            if (!this.calculations.some((x) => x.id === selectedCalculation.id)) {\r\n              this.calculations.push(selectedCalculation);\r\n            }\r\n          }\r\n        }\r\n      });\r\n  }\r\n\r\n  /** Removes the selected calculation from the calculations list. */\r\n  public removeCalc(calculation: any) {\r\n    this.calculations = this.calculations.filter((x) => x.id !== calculation.id);\r\n  }\r\n\r\n  /** Queries the report data. */\r\n  public queryData(target = \"default\") {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    switch (this.queryType) {\r\n      case \"periodQuery\":\r\n        this.reportsApi.getAccountingDataForPeriod(this.refDate, target, this.periodType, this.endDate, this.periodDateKind)\r\n          .then((result) => {\r\n            this.data = result;\r\n            loading.dismiss();\r\n          });\r\n        break;\r\n      case \"selectionQuery\": {\r\n        const calcIds = this.calculations.map((x) => x.id);\r\n        this.reportsApi.getAccountingDataForCalculationIds(calcIds, target)\r\n          .then((result) => {\r\n            this.data = result;\r\n            loading.dismiss();\r\n          });\r\n        break;\r\n      }\r\n      case \"calcs\":\r\n        this.reportsApi.getAccountingDataForCalculations(this.calcs, target)\r\n          .then((result) => {\r\n            this.data = result;\r\n            loading.dismiss();\r\n          });\r\n        break;\r\n      default:\r\n        loading.dismiss();\r\n        throw new Error(\"Unknown queryType: \" + this.queryType);\r\n    }\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { AccountingData, Numeric, Language } from \"@salaxy/core\";\r\nimport { SettingsService } from \"../../services\";\r\nimport {\r\n  Templates,\r\n  AccountingMapper,\r\n  ReportOptions,\r\n  ReportData\r\n} from \"@salaxy/reports\";\r\n\r\n/**\r\n * Provides functionality to show report rows.\r\n */\r\nexport class AccountingReportRowsController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Templates\", \"$sce\", \"SettingsService\"];\r\n\r\n  /**\r\n   * Report view table only (partial) or pdf preview (full)\r\n   * Defaults to 'partial'\r\n   */\r\n  public view: \"partial\" | \"full\";\r\n\r\n  /** Accounting data */\r\n  public data: AccountingData;\r\n\r\n  /** Boolean indicating if the refresh is in progress. */\r\n  public refreshInprogress: boolean;\r\n\r\n  /**Selected report language */\r\n  public lang: string;\r\n\r\n  /** Trusted language used in html */\r\n  public calcLang: string;\r\n\r\n  private renderedData: AccountingData;\r\n\r\n  private reportOptions: ReportOptions;\r\n\r\n  private renderedLang: string;\r\n\r\n  private reportData: ReportData<AccountingData> = {\r\n    headerFooter: {},\r\n    layout: {},\r\n    report: {},\r\n  };\r\n\r\n  private htmlData: any;\r\n\r\n  constructor(\r\n    private templates: Templates,\r\n    private $sce: angular.ISCEService,\r\n    private settingsService: SettingsService\r\n  ) {\r\n    // Dependency injection\r\n  }\r\n\r\n  /**\r\n   * Initialize controller values.\r\n   */\r\n  public $onInit() {\r\n    this.view = this.view || \"partial\";\r\n    this.reportData.layout = AccountingMapper.getReportLayout(false);\r\n  }\r\n\r\n  /** Expand/close all nodes */\r\n  public expand(close = false) {\r\n    if (this.data) {\r\n      for (const ledgerAccount of this.data.ledgerAccounts) {\r\n        (ledgerAccount as any).rowToggle = !close;\r\n      }\r\n    }\r\n  }\r\n\r\n  /** Returns true if at least one account is toggled */\r\n  public get anyExpanded(): boolean {\r\n    if (this.data) {\r\n      for (const ledgerAccount of this.data.ledgerAccounts) {\r\n        if ((ledgerAccount as any).rowToggle) {\r\n          return true;\r\n        }\r\n      }\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /** Bindable and trusted html. */\r\n  public get html(): any {\r\n    this.calcLang = this.lang === \"default\" ? \"fi\" : this.lang;\r\n    if (!this.data) {\r\n      this.renderedData = null;\r\n      this.renderedLang = null;\r\n    } else {\r\n      const data = angular.copy(this.data);\r\n\r\n      if (!this.renderedData || !angular.equals(data, this.renderedData)\r\n        || this.renderedLang !== this.calcLang) {\r\n        this.renderedData = data;\r\n        this.renderedLang = this.calcLang;\r\n        this.refresh();\r\n      }\r\n    }\r\n    return this.htmlData;\r\n  }\r\n\r\n  /**\r\n   * Refresh calculation report data.\r\n   */\r\n  private refresh() {\r\n    if (this.refreshInprogress) {\r\n      return;\r\n    }\r\n    this.refreshInprogress = true;\r\n    this.settingsService.getReportOptions().then((options) => {\r\n      this.reportOptions = options;\r\n      const reportOptions = this.getDefaultReportOptions(angular.copy(this.reportOptions));\r\n      this.reportData.headerFooter = AccountingMapper.getHeaderFooter(this.data, this.reportOptions, this.calcLang as Language);\r\n      const css = \"\";\r\n      this.reportData.layout.hasCustomCss = false;\r\n      this.reportData.layout.customCss = (css || \"\");\r\n      this.reportData.layout.margin = {\r\n        top: reportOptions.margin.top,\r\n        right: reportOptions.margin.right,\r\n        bottom: reportOptions.margin.bottom,\r\n        left: reportOptions.margin.left\r\n      };\r\n      const templates = new Templates();\r\n      this.reportData.headerHtml = this.reportOptions?.headerTemplate ? templates.getHtmlDynamic(this.reportOptions.headerTemplate, this.reportData.headerFooter, this.calcLang) : \"\";\r\n      this.reportData.footerHtml = this.reportOptions?.headerTemplate ? templates.getHtmlDynamic(this.reportOptions.footerTemplate, this.reportData.headerFooter, this.calcLang) : \"\";\r\n      this.reportData.report = AccountingMapper.getAccountingReport(this.data);\r\n      this.htmlData = this.$sce.trustAsHtml(this.templates.getHtml(\"accountingReport\", this.reportData, this.calcLang));\r\n      this.refreshInprogress = false;\r\n    });\r\n\r\n  }\r\n\r\n  private getDefaultReportOptions(optionsInput?: ReportOptions): ReportOptions {\r\n    optionsInput = optionsInput || {};\r\n    optionsInput.margin = optionsInput.margin || {};\r\n    optionsInput.margin.top = Numeric.parseNumber(optionsInput.margin.top) || 30;\r\n    optionsInput.margin.right = Numeric.parseNumber(optionsInput.margin.right) || 10;\r\n    optionsInput.margin.bottom = Numeric.parseNumber(optionsInput.margin.bottom) || 40;\r\n    optionsInput.margin.left = Numeric.parseNumber(optionsInput.margin.left) || 10;\r\n    return optionsInput;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\nimport JSZip from \"@progress/jszip-esm\";\r\nimport { saveAs } from \"file-saver\";\r\nimport { AccountingData, AccountingTargetLogic, CompanyAccountSettings, Dates, ExportMethod, Texts, Configs, Ajax, AccountingTargetSettings, AccountingChannel, Translations } from \"@salaxy/core\";\r\nimport { ExcelHelpers, SessionService, SettingsService, UiHelpers } from \"../../services\";\r\n\r\n/** Locale id */\r\nenum LocaleId {\r\n  Fi = \"fi\",\r\n  En = \"en\",\r\n}\r\n\r\n/** TargetOption */\r\ninterface TargetOptions {\r\n  [key: string]: TargetOption;\r\n}\r\n\r\n/** TargetOption */\r\ninterface TargetOption {\r\n  /** Export function */\r\n  getExportData?: (accountingData: AccountingData, schemeId?: string, target?: TargetOption) => any[];\r\n  /** List of supported schemes */\r\n  schemes?: { id: string, label: string }[],\r\n  /** Default export method */\r\n  defaultExportMethod?: string;\r\n  /** Boolean indicating if the csv export should contain quoted strings */\r\n  noCsvQuotedStrings?: boolean;\r\n\r\n  /** Boolean indicating if the csv export should contain byte order mark */\r\n  noCsvBom?: boolean;\r\n\r\n  /** Format data as text*/\r\n  formatAsText?: (data: any[], isFinnish: boolean) => string;\r\n\r\n  /** File extension for the text files. If not given, the default extension will be used */\r\n  textFileExtension?: string;\r\n\r\n  /** List of dimensions from the settings. */\r\n  dimensions?: string[];\r\n}\r\n\r\n/**\r\n * Provides functionality to export accounting data in various formats.\r\n */\r\nexport class AccountingReportToolsController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"UiHelpers\",\r\n    \"$timeout\",\r\n    \"SettingsService\",\r\n    \"SessionService\",\r\n    \"$location\",\r\n    \"$http\",\r\n    \"AjaxNg1\"\r\n  ];\r\n\r\n  /** Locale for exports */\r\n  public localeId: string = LocaleId.Fi;\r\n\r\n  /**\r\n   * Supported locales for exports\r\n   * TODO: This could be replaced with Culture enum directly in the UI.\r\n   */\r\n  public locales: {\r\n    /** Locale id */\r\n    id: string,\r\n    /** Locale label */\r\n    label: string,\r\n    /** Local description */\r\n    description: string,\r\n  }[] = [\r\n      {\r\n        id: LocaleId.Fi,\r\n        label: Translations.get(\"SALAXY.ENUM.Culture.fi.label\"),\r\n        description: Translations.get(\"SALAXY.ENUM.Culture.fi.description\"),\r\n      },\r\n      {\r\n        id: LocaleId.En,\r\n        label: Translations.get(\"SALAXY.ENUM.Culture.en.label\"),\r\n        description: Translations.get(\"SALAXY.ENUM.Culture.en.description\"),\r\n      },\r\n    ];\r\n\r\n  /** Size of the data export */\r\n  public schemeId: string;\r\n\r\n  /** Export format */\r\n  public exportMethod: string = ExportMethod.FileExcel;\r\n\r\n  /** Supported export formats */\r\n  private _exportMethods: {\r\n    /** File type id */\r\n    id: string,\r\n    /** File type label */\r\n    label: string,\r\n    /** Boolean indicating if the file type supports different locales */\r\n    hasLocales: boolean,\r\n    /** Workflow message after export */\r\n    workflowMessage,\r\n  }[] = [\r\n      {\r\n        id: ExportMethod.FilePdf,\r\n        label: Translations.get(\"SALAXY.ENUM.ExportMethod.filePdf.label\"),\r\n        hasLocales: false,\r\n        workflowMessage: Translations.get(\"SALAXY.ENUM.ExportMethod.filePdf.workflowMessage\"),\r\n      },\r\n      {\r\n        id: ExportMethod.FileExcel,\r\n        label: Translations.get(\"SALAXY.ENUM.ExportMethod.fileExcel.label\"),\r\n        hasLocales: false,\r\n        workflowMessage: Translations.get(\"SALAXY.ENUM.ExportMethod.fileExcel.workflowMessage\"),\r\n      },\r\n      {\r\n        id: ExportMethod.CopyExcel,\r\n        label: Translations.get(\"SALAXY.ENUM.ExportMethod.copyExcel.label\"),\r\n        hasLocales: true,\r\n        workflowMessage: Translations.get(\"SALAXY.ENUM.ExportMethod.copyExcel.workflowMessage\"),\r\n      },\r\n      {\r\n        id: ExportMethod.FileCsv,\r\n        label: Translations.get(\"SALAXY.ENUM.ExportMethod.fileCsv.label\"),\r\n        hasLocales: true,\r\n        workflowMessage: Translations.get(\"SALAXY.ENUM.ExportMethod.fileCsv.workflowMessage\"),\r\n      },\r\n      {\r\n        id: ExportMethod.CopyCsv,\r\n        label: Translations.get(\"SALAXY.ENUM.ExportMethod.copyCsv.label\"),\r\n        hasLocales: true,\r\n        workflowMessage: Translations.get(\"SALAXY.ENUM.ExportMethod.copyCsv.workflowMessage\"),\r\n      },\r\n      {\r\n        id: ExportMethod.FileText,\r\n        label: Translations.get(\"SALAXY.ENUM.ExportMethod.fileText.label\"),\r\n        hasLocales: true,\r\n        workflowMessage: Translations.get(\"SALAXY.ENUM.ExportMethod.fileText.workflowMessage\"),\r\n      },\r\n      {\r\n        id: ExportMethod.CopyText,\r\n        label: Translations.get(\"SALAXY.ENUM.ExportMethod.copyText.label\"),\r\n        hasLocales: true,\r\n        workflowMessage: Translations.get(\"SALAXY.ENUM.ExportMethod.copyText.workflowMessage\"),\r\n      },\r\n      {\r\n        id: ExportMethod.Api,\r\n        label: \"API integraatio\",\r\n        hasLocales: false,\r\n        workflowMessage: \"\",\r\n      }\r\n    ];\r\n\r\n  /** Export target */\r\n  public targetId = \"default\";\r\n\r\n  /** Targets */\r\n  public targets: any[] = [];\r\n\r\n  /**\r\n   * Object with read function to call for retrieving the accounting data.\r\n   * Function has the following argument:  arr, which is an array of accounting data into which the result will be appended.\r\n   */\r\n  public reader: {\r\n    /** Function for reading data into given array. */\r\n    read: (\r\n      /** Target for accounting data */\r\n      target: string,\r\n      /** RuleSet for accounting data */\r\n      ruleSet: string,\r\n      /** Array for accounting data read results */\r\n      arr: AccountingData[],\r\n      /** Message for workflow (loading) */\r\n      message: string,\r\n    ) => Promise<void>,\r\n    /** Optional label for data export */\r\n    exportLabel?: string,\r\n    /** Indicates if the export is not possible */\r\n    disabled: () => boolean,\r\n    /* Indicates if row is expandable */\r\n    showExpand: boolean,\r\n    /* Indicates if rows exists*/\r\n    hasRows: boolean\r\n  };\r\n\r\n  /**\r\n   * Indicator for any expanded row\r\n   */\r\n  public anyExpanded: boolean;\r\n\r\n  /**\r\n   * Report view table only (partial) or pdf preview (full)\r\n   * Defaults to 'partial'\r\n   */\r\n  public view: \"partial\" | \"full\";\r\n\r\n  /**\r\n   * Function that is called when the target has been changed\r\n   * Function has the following locals:  targetId: the selected accounting target id.\r\n   */\r\n  public onTargetChange: (params: {\r\n    /** Selected target id */\r\n    targetId: any,\r\n  }) => void;\r\n\r\n  /**\r\n   * Function that is called when row expand change\r\n   */\r\n  public onExpandChange: (params: {\r\n    /** Selected target id */\r\n    close: boolean,\r\n  }) => void;\r\n\r\n  /** Supported targets */\r\n  private targetOptions: TargetOptions = AccountingTargetLogic.getSupportedTargets();\r\n\r\n  private defaultOption: TargetOption = {\r\n    // Palkkaus.fi\r\n    getExportData: (accountingData: AccountingData, schemeId: string, target: TargetOption) => {\r\n      return this.targetOptions[\"36dff2e2-e181-4f0d-9004-0e4aa92f5e17\"].getExportData(accountingData, schemeId, target);\r\n    },\r\n    defaultExportMethod: ExportMethod.FileExcel,\r\n    noCsvBom: false\r\n  };\r\n\r\n  private static channelBasePaths = {\r\n    [AccountingChannel.Procountor]: \"procountor\",\r\n    [AccountingChannel.VismaNetvisor]: \"vismanetvisor\",\r\n    [AccountingChannel.VismaFivaldi]: \"vismafivaldi\",\r\n  };\r\n\r\n  constructor(\r\n    private uiHelpers: UiHelpers,\r\n    private $timeout: angular.ITimeoutService,\r\n    private settingsService: SettingsService,\r\n    private sessionService: SessionService,\r\n    private $location: angular.ILocationService,\r\n    private $http: angular.IHttpService,\r\n    private ajax: Ajax,\r\n  ) {\r\n  }\r\n\r\n  /**\r\n   * Initialize controller values.\r\n   */\r\n  public $onInit() {\r\n    // Get accounting targets\r\n    const getSettings = (): Promise<CompanyAccountSettings> => {\r\n      return new Promise((resolve) => {\r\n        const check = () => {\r\n          if (this.settingsService.current) {\r\n            return resolve(this.settingsService.current);\r\n          }\r\n          this.$timeout(() => check(), 50);\r\n        };\r\n\r\n        check();\r\n      });\r\n    };\r\n    getSettings().then((settings) => {\r\n      this.targets = settings.accounting.targets;\r\n      for (const target of this.targets) {\r\n        const targetOption = this.targetOptions[target.format] || this.targetOptions[target.id] || this.defaultOption;\r\n        target.getExportData = targetOption.getExportData;\r\n        target.schemes = targetOption.schemes ?? [];\r\n        target.defaultExportMethod = targetOption.defaultExportMethod;\r\n        target.noCsvQuotedStrings = targetOption.noCsvQuotedStrings;\r\n        target.noCsvBom = targetOption.noCsvBom;\r\n        target.formatAsText = targetOption.formatAsText;\r\n        target.textFileExtension = targetOption.textFileExtension;\r\n        target.dimensions = settings.costAccounting?.dimensions?.map(x => (x.id).toLowerCase()) || [];\r\n      }\r\n      if (settings.accounting.defaultTargetId) {\r\n        this.targetId = settings.accounting.defaultTargetId;\r\n        this.setExportMethod(settings.accounting.defaultTargetId);\r\n      }\r\n    });\r\n    this.view = this.view || \"partial\";\r\n  }\r\n\r\n  /** Exports data in defined format. */\r\n  public export(\r\n    reader: {\r\n      /** Function for reading data into given array. */\r\n      read: (\r\n        /** Target for accounting data */\r\n        target: string,\r\n        /** RuleSet for accounting data */\r\n        ruleSet: string,\r\n        /** Array for accounting data read results */\r\n        arr: AccountingData[],\r\n        /** Workflow loading message */\r\n        message: string,\r\n      ) => Promise<void>,\r\n      /** Optional label for data export */\r\n      exportLabel?: string,\r\n      /** Indicates if the export is not possible */\r\n      disabled: () => boolean,\r\n      /* Indicates if row is expandable */\r\n      showExpand: boolean,\r\n      /* Indicates if rows exists*/\r\n      hasRows: boolean\r\n    } = null,\r\n    /** If true, does not show loading indicator. Default is false. */\r\n    hideLoading = false,\r\n  ): Promise<void> {\r\n    if (!reader) {\r\n      reader = this.reader;\r\n    }\r\n    if (!reader) {\r\n      console.error(\"No data reader for accounting data.\");\r\n      return Promise.resolve();\r\n    }\r\n    const loading = hideLoading ? { dismiss: () => null } : this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n\r\n    const target = this.getTarget(this.targetId);\r\n    const arr: AccountingData[] = [];\r\n    return reader.read(this.targetId, null, arr, this.getWorkflowMessage()).then(() => {\r\n      if (arr.length === 0) {\r\n        loading.dismiss();\r\n        return Promise.resolve();\r\n      }\r\n      switch (this.exportMethod) {\r\n        case ExportMethod.Api:\r\n          loading.dismiss();\r\n          this.sendToApi(target, arr);\r\n          return;\r\n        case ExportMethod.FilePdf:\r\n          if (arr.length === 1) {\r\n            return this.getPdf(arr[0]).then(result => {\r\n              this.uiHelpers.downloadFile(result.blob, result.fileName);\r\n              loading.dismiss();\r\n              return;\r\n            });\r\n          } else {\r\n            const zip = new JSZip();\r\n            const getAllBlobs = (items) => {\r\n              const promises: Array<Promise<{ blob: Blob, fileName: string }>> = [];\r\n              for (const item of items) {\r\n                promises.push(this.getPdf(item));\r\n              }\r\n              return Promise.all(promises).then((results) => {\r\n                let counter = 0;\r\n                results.forEach(item => {\r\n                  counter++;\r\n                  zip.file(`${counter}_ ${item.fileName}`, item.blob);\r\n                });\r\n                return;\r\n              });\r\n            };\r\n\r\n            return getAllBlobs(arr).then(() => {\r\n              zip.generateAsync({\r\n                type: \"blob\",\r\n                mimeType:\r\n                  \"application/zip\",\r\n              }).then((blob) => {\r\n                saveAs(blob, `${this.getZipName(arr)}.zip`);\r\n                loading.dismiss();\r\n                return;\r\n              });\r\n            });\r\n\r\n          }\r\n          break;\r\n        case ExportMethod.FileCsv:\r\n          if (arr.length === 1) {\r\n            const data = arr[0];\r\n            saveAs(new Blob([this.getCsv(target.getExportData(data, this.schemeId, target), this.localeId !== LocaleId.En, !target.noCsvBom, !target.noCsvQuotedStrings)], { type: \"application/octet-stream;charset=utf-8\" }), `${this.getFileName(data)}.csv`);\r\n            loading.dismiss();\r\n            return;\r\n          } else {\r\n            let counter = 0;\r\n            const zip = new JSZip();\r\n            const next = () => {\r\n              if (counter === arr.length) {\r\n                return;\r\n              }\r\n              const data = arr[counter++];\r\n              const blob = new Blob([this.getCsv(target.getExportData(data, this.schemeId, target), this.localeId !== LocaleId.En, !target.noCsvBom, !target.noCsvQuotedStrings)], { type: \"application/octet-stream;charset=utf-8\" });\r\n              zip.file(`${this.getFileName(data)}.csv`, blob);\r\n              next();\r\n            };\r\n\r\n            next();\r\n            zip.generateAsync({\r\n              type: \"blob\",\r\n              mimeType:\r\n                \"application/zip\",\r\n            }).then((blob) => {\r\n              saveAs(blob, `${this.getZipName(arr)}.zip`);\r\n              loading.dismiss();\r\n              return;\r\n            });\r\n          }\r\n          break;\r\n        case ExportMethod.FileExcel:\r\n          if (arr.length === 1) {\r\n            const data = arr[0];\r\n            ExcelHelpers.export(target.getExportData(data, this.schemeId, target), this.getFileName(data)).then(() => {\r\n              loading.dismiss();\r\n              return;\r\n            });\r\n          } else if (arr.length > 1) {\r\n            const tablesData = [];\r\n            const next = () => {\r\n              if (tablesData.length === arr.length) {\r\n                return;\r\n              }\r\n              const data = arr[tablesData.length];\r\n              tablesData.push({\r\n                tableData: target.getExportData(data, this.schemeId, target),\r\n                fileName: this.getFileName(data),\r\n              });\r\n              next();\r\n            };\r\n\r\n            next();\r\n            ExcelHelpers.exportMany(tablesData, this.getZipName(arr)).then(() => {\r\n              loading.dismiss();\r\n              return;\r\n            });\r\n          }\r\n          break;\r\n          case ExportMethod.FileText:\r\n            if (arr.length === 1) {\r\n              const data = arr[0];\r\n              saveAs(new Blob([this.getText(target.getExportData(data, this.schemeId, target), this.localeId !== LocaleId.En, target.formatAsText)], { type: \"application/octet-stream;charset=utf-8\" }), `${this.getFileName(data)}.${target.textFileExtension || \"txt\"}`);\r\n              loading.dismiss();\r\n              return;\r\n            } else {\r\n              let counter = 0;\r\n              const zip = new JSZip();\r\n              const next = () => {\r\n                if (counter === arr.length) {\r\n                  return;\r\n                }\r\n                const data = arr[counter++];\r\n                const blob = new Blob([this.getText(target.getExportData(data, this.schemeId, target), this.localeId !== LocaleId.En, target.formatAsText)], { type: \"application/octet-stream;charset=utf-8\" });\r\n                zip.file(`${this.getFileName(data)}.${target.textFileExtension || \"txt\"}`, blob);\r\n                next();\r\n              };\r\n              next();\r\n              zip.generateAsync({\r\n                type: \"blob\",\r\n                mimeType:\r\n                  \"application/zip\",\r\n              }).then((blob) => {\r\n                saveAs(blob, `${this.getZipName(arr)}.zip`);\r\n                loading.dismiss();\r\n                return;\r\n              });\r\n            }\r\n            break;\r\n        case ExportMethod.CopyCsv:\r\n          if (arr.length === 1) {\r\n            const data = arr[0];\r\n            this.copyToClipboard(this.getCsv(target.getExportData(data, this.schemeId, target), this.localeId !== LocaleId.En, !target.noCsvBom, !target.noCsvQuotedStrings));\r\n            loading.dismiss();\r\n            return;\r\n          } else if (arr.length > 1) {\r\n            let counter = 0;\r\n            let csv = !target.noCsvBom ? \"\\uFEFF\" : \"\";\r\n            const next = () => {\r\n              if (counter === arr.length) {\r\n                return;\r\n              }\r\n              const data = arr[counter++];\r\n              csv += `${this.getFileName(data)}\\r\\n`;\r\n              csv += this.getCsv(target.getExportData(data, this.schemeId, target), this.localeId !== LocaleId.En, false, !target.noCsvQuotedStrings) + (counter < arr.length ? \"\\r\\n\" : \"\");\r\n              next();\r\n            };\r\n            next();\r\n            this.copyToClipboard(csv);\r\n            loading.dismiss();\r\n            return;\r\n          }\r\n          break;\r\n        case ExportMethod.CopyExcel:\r\n          if (arr.length === 1) {\r\n            const data = arr[0];\r\n            this.copyToClipboard(this.getTabbed(target.getExportData(data, this.schemeId, target), this.localeId !== LocaleId.En));\r\n            loading.dismiss();\r\n            return;\r\n          } else if (arr.length > 1) {\r\n            let counter = 0;\r\n            let tabbed = \"\";\r\n            const next = () => {\r\n              if (counter === arr.length) {\r\n                return;\r\n              }\r\n              const data = arr[counter++];\r\n              tabbed += `${this.getFileName(data)}\\r\\n`;\r\n              tabbed += this.getTabbed(target.getExportData(data, this.schemeId, target), this.localeId !== LocaleId.En) + (counter < arr.length ? \"\\n\" : \"\");\r\n              next();\r\n            };\r\n            next();\r\n            this.copyToClipboard(tabbed);\r\n            loading.dismiss();\r\n            return;\r\n          }\r\n          break;\r\n          case ExportMethod.CopyText:\r\n            if (arr.length === 1) {\r\n              const data = arr[0];\r\n              this.copyToClipboard(this.getText(target.getExportData(data, this.schemeId, target), this.localeId !== LocaleId.En, target.formatAsText));\r\n              loading.dismiss();\r\n              return;\r\n            } else if (arr.length > 1) {\r\n              let counter = 0;\r\n              let txt = \"\";\r\n              const next = () => {\r\n                if (counter === arr.length) {\r\n                  return;\r\n                }\r\n                const data = arr[counter++];\r\n                txt += `${this.getFileName(data)}\\r\\n`;\r\n                txt += this.getText(target.getExportData(data, this.schemeId, target), this.localeId !== LocaleId.En, target.formatAsText) + (counter < arr.length ? \"\\r\\n\" : \"\");\r\n                next();\r\n              };\r\n              next();\r\n              this.copyToClipboard(txt);\r\n              loading.dismiss();\r\n              return;\r\n            }\r\n            break;\r\n        default:\r\n          loading.dismiss();\r\n          this.uiHelpers.showAlert(\"Ei vielä toteutettu\", \"Tätä tiedostotyyppiä ei ole toteutettu.\");\r\n          return;\r\n      }\r\n      loading.dismiss();\r\n      return;\r\n    });\r\n  }\r\n\r\n  /** Navigates to given path and closes possible open modal dialogs. */\r\n  public navigate(path: string) {\r\n    this.$location.path(path);\r\n    this.uiHelpers.dismissAllModals();\r\n  }\r\n\r\n  /**\r\n   * Change target and call event handler.\r\n   * @param targetId - New target id.\r\n   */\r\n  public changeTarget(targetId: string) {\r\n    this.setExportMethod(targetId);\r\n    this.targetId = targetId;\r\n    this.onTargetChange({ targetId });\r\n  }\r\n\r\n  /**\r\n   * Returns the export methods that are available for the accounting target.\r\n   */\r\n  public get exportMethods() {\r\n    // If an accounting target from company settings is selected...\r\n    const target = this.getTarget(this.targetId);\r\n    // ...and available methods for the target are configured\r\n    const availableMethods = [];\r\n    if (target?.availableMethods?.length > 0) {\r\n      // Filter the possible export methods according to the available methods configured for the target.\r\n      availableMethods.push(...target.availableMethods);\r\n    } else {\r\n      // Defaults only\r\n      availableMethods.push(...\r\n        [\r\n          ExportMethod.FilePdf,\r\n          ExportMethod.FileExcel,\r\n          ExportMethod.CopyExcel,\r\n          ExportMethod.FileCsv,\r\n          ExportMethod.CopyCsv\r\n        ]);\r\n    }\r\n    return this._exportMethods.filter(v => availableMethods.indexOf(v.id as ExportMethod) > -1);\r\n  }\r\n\r\n  /**\r\n   * Returns the export method type definition\r\n   * @param exportMethodId export method id\r\n   */\r\n  public getExportMethod(exportMethodId: string) {\r\n    return this.exportMethods.find((x) => x.id === exportMethodId);\r\n  }\r\n\r\n  /**\r\n   * Returns the target definition\r\n   * @param targetId Target id.\r\n   */\r\n  public getTarget(targetId: string) {\r\n    return this.targets.find((x) => x.id === targetId);\r\n  }\r\n\r\n  /**\r\n   * Returns the locale definition\r\n   * @param localeId Locale id.\r\n   */\r\n  public getLocale(localeId: string) {\r\n    return this.locales.find((x) => x.id === localeId);\r\n  }\r\n\r\n  /**\r\n   * Returns the scheme definition.\r\n   * @param schemeId Scheme id.\r\n   */\r\n  public getScheme(schemeId: string) {\r\n    return this.getTarget(this.targetId)?.schemes.find(x => x.id === schemeId);\r\n  }\r\n  private setExportMethod(targetId: string) {\r\n\r\n    // First check if the targetId is one of the \"default\" target options\r\n    if (this.targetOptions[targetId]) {\r\n      this.exportMethod = this.targetOptions[targetId].defaultExportMethod;\r\n      this.schemeId = this.targetOptions[targetId].schemes?.length ? this.targetOptions[targetId].schemes[0].id : null;\r\n      return;\r\n    }\r\n\r\n    const target = this.getTarget(targetId);\r\n    this.schemeId = target.schemes?.length ? target.schemes[0].id : null;\r\n    this.exportMethod = (target.method && target.method !== \"undefined\") ? target.method : target.defaultExportMethod;\r\n  }\r\n\r\n  /**\r\n   * Method for calling onExpandChange event\r\n   * @param close If true, closes the expanding component.\r\n   */\r\n  public expand(close = false) {\r\n    this.onExpandChange({ close });\r\n  }\r\n\r\n  private getFileName(data: AccountingData) {\r\n    return Texts.escapeFileName(`${Translations.get(\"SALAXY.UI_Terms.downLoadableMaterialTypes.accounting\")}_${data.employer.displayName}_${Dates.format((data.period.start ?? \"today\"),\"YYYY_MM\")}`);\r\n  }\r\n\r\n  private getZipName(all: AccountingData[]) { // eslint-disable-line @typescript-eslint/no-unused-vars\r\n    return Texts.escapeFileName(`${Translations.get(\"SALAXY.UI_Terms.downLoadableMaterialTypes.accounting\")}_${Dates.format(\"today\",\"YYYYMMDD\")}`);\r\n  }\r\n\r\n  private getWorkflowMessage() {\r\n    const exportMethod = this.getExportMethod(this.exportMethod);\r\n    if (exportMethod) {\r\n      return exportMethod.workflowMessage;\r\n    }\r\n    return null;\r\n  }\r\n\r\n  private getCsv(data: any[], isFinnish = true, addPrefix: boolean, addQuotes: boolean) {\r\n    const separator = (isFinnish ? \";\" : \",\");\r\n    const rowMapper = this.formatRow(isFinnish, separator, addQuotes);\r\n    const rows = data.map(rowMapper);\r\n    return (addPrefix ? \"\\uFEFF\" : \"\") + rows.join(\"\\r\\n\");\r\n  }\r\n\r\n  private getText(data: any[], isFinnish = true, formatAsText: (data: any[], isFinnish: boolean) => string) {\r\n    if (formatAsText == null) {\r\n      const rowMapper = this.formatRow(isFinnish, \"\\t\", false);\r\n      const rows = data.map(rowMapper);\r\n      return rows.join(\"\\r\\n\");\r\n    }\r\n    else {\r\n      return formatAsText(data, isFinnish);\r\n    }\r\n  }\r\n\r\n  private getPdf(obj): Promise<{ blob: Blob, fileName: string }> {\r\n    const url = `${Configs.current.reportServer}/pdf?id=&reportType=${encodeURIComponent(\"accountingReport\")}&template=${encodeURIComponent(\"accountingReport\")}&disposition=inline&access_token=${this.ajax.getCurrentToken()}`;\r\n    return (this.$http.post(url, { object: obj }, { responseType: \"blob\" }) as Promise<any>).then((response) => {\r\n      if (response.data) {\r\n        return Promise.resolve({ blob: response.data, fileName: response.headers(\"content-disposition\").split(\";\")[1].split(\"filename\")[1].split(\"=\")[1].trim().replace(/\"/g, \"\") });\r\n      }\r\n    }, (error) => {\r\n      console.error(error);\r\n      return Promise.reject(error);\r\n    });\r\n  }\r\n  private getTabbed(data: any[], isFinnish = true) {\r\n    const rowMapper = this.formatRow(isFinnish, \"\\t\");\r\n    const rows = data.map(rowMapper);\r\n    return rows.join(\"\\n\");\r\n  }\r\n\r\n  private formatRow(isFinnish: boolean, separator: string, addQuotes = true) {\r\n    const fieldMapper = this.formatField(isFinnish, addQuotes);\r\n    return (row) => {\r\n      return row.map(fieldMapper).join(separator);\r\n    };\r\n  }\r\n\r\n  private formatField(isFinnish: boolean, addQuotes = true) {\r\n    return (value) => {\r\n      if (value == null) { // we want to catch anything null-ish, hence just == not ===\r\n        return \"\";\r\n      }\r\n      if (typeof (value) === \"number\") {\r\n        if (isFinnish) {\r\n          return value.toString().replace(\".\", \",\");\r\n        }\r\n        return value;\r\n      }\r\n      if (typeof (value) === \"boolean\") {\r\n        return (value ? \"TRUE\" : \"FALSE\");\r\n      }\r\n      if (typeof (value) === \"string\") {\r\n        if (addQuotes) {\r\n          return \"\\\"\" + value.replace(/\"/g, \"\\\"\\\"\") + \"\\\"\";\r\n        }\r\n        return value;\r\n      }\r\n      if (typeof (value) === \"object\") {\r\n        if (value instanceof Date) {\r\n          if (isFinnish) {\r\n            return Dates.format(value,\"D.M.YYYY\");\r\n          } else {\r\n            return Dates.format(value,\"YYYY-MM-DD\");\r\n          }\r\n        } else {\r\n          if (addQuotes) {\r\n            return \"\\\"\" + JSON.stringify(value).replace(/\"/g, \"\\\"\\\"\") + \"\\\"\";\r\n          }\r\n          return JSON.stringify(value);\r\n        }\r\n      }\r\n      return JSON.stringify(value);\r\n    };\r\n  }\r\n\r\n  private copyToClipboard(data: string) {\r\n    (navigator as any).clipboard.writeText(data);\r\n  }\r\n\r\n  private async sendToApi(target: AccountingTargetSettings, arr: any[]): Promise<void> {\r\n    if(!target.channel || target.channel === \"undefined\") {\r\n      return;\r\n    }\r\n\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    const items = [];\r\n    for(const accountingData of arr) {\r\n      items.push( {\r\n        accountingData,\r\n        preview: (await this.$http.post(this.getAccountingDataUrl(target, \"accountingPreview\"), accountingData, { responseType: \"json\", }))?.data,\r\n        result: \"\",\r\n        error: \"\",\r\n      });\r\n    }\r\n\r\n    loading.dismiss();\r\n    this.uiHelpers.openEditDialog(\"salaxy-components/report/modals/PostAccountingData.html\", items,{\r\n      postData: (item) => {\r\n        item.isPosting = true;\r\n        this.$http.post(this.getAccountingDataUrl(target, \"accounting\"), item.accountingData, { responseType: \"json\", })\r\n          .then((result) => {\r\n            item.isPosting = false;\r\n            item.error = \"\";\r\n            item.result = this.getAccountingDataResult(target, result);\r\n          })\r\n          .catch( (err) => {\r\n            item.isPosting = false;\r\n            item.error =  this.getAccountingDataError(target, err);\r\n            item.result = \"\";\r\n          });\r\n      },\r\n      previewTemplateUrl: this.getAccountingDataPreviewTemplate(target),\r\n    },\"lg\");\r\n  }\r\n\r\n  private getAccountingDataUrl(target: AccountingTargetSettings, path: string): string {\r\n    const accessToken = this.ajax.getCurrentToken();\r\n    const url = `${Configs.current.integrationsServer}/${AccountingReportToolsController.channelBasePaths[target.channel]}/${path}`;\r\n    return `${url}?accessToken=${accessToken}&accountingTargetId=${target.id}`;\r\n  }\r\n\r\n  private getAccountingDataError(target: AccountingTargetSettings, error: any) {\r\n    if (error?.data?.detail) {\r\n      return Translations.get(\"SALAXY.UI_Terms.error\") +\", \" + error.data.detail;\r\n    }\r\n    if (error.data) {\r\n      return  Translations.get(\"SALAXY.UI_Terms.error\") + \", \" + error.data.status + \"-\" + error.data.title;\r\n    }\r\n    return Translations.get(\"SALAXY.UI_Terms.error\");\r\n  }\r\n\r\n  private getAccountingDataResult(target: AccountingTargetSettings, result: any) {\r\n    switch(target.channel) {\r\n      case AccountingChannel.VismaFivaldi:\r\n        return Translations.get(\"SALAXY.UI_Terms.ok\") + \", VismaFivaldi: \" + result.data.fivaldiVoucherNumber;\r\n      default:\r\n        return Translations.get(\"SALAXY.UI_Terms.ok\");\r\n    }\r\n  }\r\n\r\n  private getAccountingDataPreviewTemplate(target: AccountingTargetSettings) {\r\n    switch(target.channel) {\r\n      case AccountingChannel.VismaFivaldi:\r\n        return \"salaxy-components/report/modals/FivaldiPreview.html\";\r\n      default:\r\n        return \"\";\r\n    }\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Absences, ApiListItem, Calculations, Calculation, Dates, irepr, IrEarningsPayments, AbsenceCauseCode } from \"@salaxy/core\";\r\n\r\nimport { ApiCrudObjectController } from \"../bases\";\r\nimport { Calculator2019Controller } from \"../../controllers\";\r\nimport { SessionService, UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Controller for user interface of Earnings Payment Report (\"Tulorekisteri-ilmoitus\").\r\n */\r\nexport class IrEarningsPaymentCrudController extends ApiCrudObjectController<irepr.EarningsPayment, any> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"IrEarningsPayments\",\r\n    \"UiHelpers\",\r\n    \"$location\",\r\n    \"$routeParams\",\r\n    \"Calculations\",\r\n    \"Absences\",\r\n    \"SessionService\"\r\n  ];\r\n\r\n  /** Calculation controller  */\r\n  public calcController: Calculator2019Controller;\r\n\r\n  private _calculation: Calculation;\r\n  private _calculationId: string;\r\n  private _hasCalculationFor: boolean;\r\n\r\n  constructor(\r\n    private fullApi: IrEarningsPayments,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    private calcApi: Calculations,\r\n    private absencesApi: Absences,\r\n    private session: SessionService,\r\n  ) { // Dependency injection\r\n    super(fullApi, uiHelpers, $location, $routeParams);\r\n  }\r\n\r\n  /**\r\n   * Initializes the controller\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"irepr\",\r\n      detailsUrl: this.detailsUrl || \"/irepr/details/\",\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/IrEpr.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n\r\n  /** Gets calculation */\r\n  public get calculation() {\r\n    if (this.current?.info?.calculationId != null) {\r\n      this.calculationId = this.current.info.calculationId;\r\n    }\r\n    return this._calculation;\r\n  }\r\n\r\n  /**\r\n   * Sets calculation and if it is different then starts the loading of the EarningsPayment object to that calculation.\r\n   */\r\n  public set calculation(value: Calculation) {\r\n    if (this._hasCalculationFor) {\r\n      return;\r\n    }\r\n    if (value == null || value.id == null) {\r\n      this._calculation = null;\r\n      this._calculationId = null;\r\n      return;\r\n    }\r\n    if (this.calculationId === value?.id) {\r\n      return;\r\n    }\r\n    this._calculation = value;\r\n    this._calculationId = value.id;\r\n    if (this.current?.info?.calculationId !== value.id) {\r\n      this.setStatus(this.calcApi.getEpr(value.id)).then((data) => {\r\n        this.setCurrent(data);\r\n      });\r\n    }\r\n  }\r\n\r\n  /** Gets calculation */\r\n  public get calculationId(): string {\r\n    return this._calculation?.id ?? this._calculationId;\r\n  }\r\n\r\n  /**\r\n   * Sets calculation and if it is different then starts the loading of the EarningsPayment object to that calculation.\r\n   */\r\n  public set calculationId(value: string) {\r\n    if (this._hasCalculationFor) {\r\n      return;\r\n    }\r\n    if (value == null) {\r\n      this._calculation = null;\r\n      this._calculationId = null;\r\n      return;\r\n    }\r\n    if (this.calculationId === value) {\r\n      return;\r\n    }\r\n    this._calculation = null;\r\n    this._calculationId = value;\r\n    this.calcApi.getSingle(value).then((calc) => {\r\n      this._calculation = calc;\r\n    });\r\n    if (this.current?.info?.calculationId !== value) {\r\n      this.setStatus(this.calcApi.getEpr(value)).then((data) => {\r\n        this.setCurrent(data);\r\n      });\r\n    }\r\n  }\r\n\r\n  /** Used for setting the calculation with the model, without epr reload. */\r\n  public set calculationFor(value: Calculation) {\r\n    this._calculation = value;\r\n    this._calculationId = value?.id;\r\n    this._hasCalculationFor = true;\r\n  }\r\n\r\n  /** Returns true if the report can be canceled. */\r\n  public get isCancellable() {\r\n    return this.current && this.getLatestNonErrorReportLogEntry()?.eventType === irepr.ReportLogEventType.Sent;\r\n  }\r\n\r\n  /** Returns true if the item is read-only */\r\n  public get isReadOnly(): boolean {\r\n    return super.isReadOnly || (!(this as any).tempShowEditInNonAdminMode && !this.session.isInRole(\"admin\"));\r\n  }\r\n\r\n  /** Save resource */\r\n  public saveChanges(): Promise<irepr.EarningsPayment> {\r\n    if (this._calculation && this.calcController && this.calcController.hasChanges) {\r\n      return this.calcApi.saveIr(this._calculation).then((calc) => {\r\n        this._calculation = calc;\r\n        return this.calcApi.convertToEpr(this._calculation).then((epr) => {\r\n          this.current.deliveryData.reports[0].transactions = epr.deliveryData.reports[0].transactions;\r\n          return this.save().then(() => {\r\n            this.calcController.setCurrent(this._calculation);\r\n            return this.current;\r\n          });\r\n        });\r\n      });\r\n    } else {\r\n      return this.save().then(() => {\r\n        return this.current;\r\n      });\r\n    }\r\n  }\r\n\r\n  /** Send to incomes register. */\r\n  public sendToIncomesRegister(startAt: Date): Promise<irepr.EarningsPayment> {\r\n    return this.saveChanges().then((epr) => {\r\n      if (epr.validation.isValid) {\r\n        const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.EarningsPaymentComponent.common.loaderTextSending\");\r\n        const aso: irepr.IrApiScheduleObject = {\r\n          id: this.current.id,\r\n          startAt: startAt ? JSON.stringify(startAt).replace(/\"/g, \"\") : null,\r\n          action: irepr.IrScheduleAction.Send\r\n        };\r\n        return this.fullApi.sendSchedule(aso).then(() => {\r\n          return this.reloadFromServer().then(() => {\r\n            loader.dismiss();\r\n            return this.current;\r\n          });\r\n        });\r\n      } else {\r\n        this.uiHelpers.showAlert(\"SALAXY.NG1.EarningsPaymentComponent.common.sendFailureTitle\", \"SALAXY.NG1.EarningsPaymentComponent.common.validationErrorText\");\r\n        return this.current;\r\n      }\r\n    });\r\n  }\r\n\r\n  /** Get latest incomes register report log entry */\r\n  private getLatestNonErrorReportLogEntry(): irepr.ReportLogEntry {\r\n    if (this.current.reportLog != null) {\r\n      const nonErrorEntries = this.current.reportLog.filter((x) => x.eventType !== irepr.ReportLogEventType.Error);\r\n      if (nonErrorEntries.length > 0) {\r\n        return nonErrorEntries[nonErrorEntries.length - 1];\r\n      }\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /** Sends cancel request to incomes register */\r\n  public cancelToIncomesRegister(): Promise<irepr.EarningsPayment> {\r\n    const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.EarningsPaymentComponent.common.loaderTextCanceling\");\r\n    const aso: irepr.IrApiScheduleObject = {\r\n      id: this.current.id,\r\n      action: irepr.IrScheduleAction.Cancel\r\n    };\r\n    return this.fullApi.sendSchedule(aso).then(() => {\r\n      return this.reloadFromServer().then(() => {\r\n        loader.dismiss();\r\n        return this.current;\r\n      });\r\n    });\r\n  }\r\n\r\n  /** Opens sheculing dialog and sends scheduling after successful dialog close */\r\n  public openSetScheduleDialog() {\r\n    const now = new Date();\r\n    return this.uiHelpers.openEditDialog(\"salaxy-components/report/modals/IrScheduleSendDialog.html\", {\r\n      startAtHours: now.getHours(),\r\n      startAtMinutes: now.getMinutes(),\r\n      startAt: now\r\n    }, {})\r\n      .then((dialog) => {\r\n        if (dialog.result === \"ok\") {\r\n          const startAtDate = new Date(dialog.item.startAt);\r\n          startAtDate.setHours(dialog.item.startAtHours || 0);\r\n          startAtDate.setMinutes(dialog.item.startAtMinutes || 0);\r\n          return this.sendToIncomesRegister(startAtDate);\r\n        } else {\r\n          return this.current;\r\n        }\r\n      });\r\n  }\r\n\r\n  /** Remove Incomes register queue item */\r\n  public removeIrQueueItem(): Promise<irepr.EarningsPayment> {\r\n    const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.EarningsPaymentComponent.common.loaderTextRemoving\");\r\n    return this.fullApi.removeIrQueueItem(this.current.id).then(() => {\r\n      return this.reloadFromServer().then(() => {\r\n        loader.dismiss();\r\n        return this.current;\r\n      });\r\n    });\r\n  }\r\n\r\n  /** Opens a dialog for importing absences. */\r\n  public importAbsences() {\r\n    this.absencesApi.getForEmployment(this.calculation.worker.employmentId).then((workerAbsences) => {\r\n      this.uiHelpers.openEditDialog(\"salaxy-components/report/modals/IrImportAbsencesDialog.html\", workerAbsences, {}).then((dialog) => {\r\n        if (dialog.result === \"ok\" && workerAbsences.periods) {\r\n          const selectedAbsences = workerAbsences.periods.filter((x) => (x as any).selected);\r\n          if (selectedAbsences.length > 0) {\r\n            const report = this.current.deliveryData.reports[0];\r\n            report.absence = report.absence ?? {};\r\n            let absencesStartDate = null;\r\n            let absencesEndDate = null;\r\n            selectedAbsences.forEach((period) => {\r\n              if (period.isPaid) {\r\n                report.absence.paidAbsence = report.absence.paidAbsence ?? {};\r\n                report.absence.paidAbsence.paidAbsencePeriods = report.absence.paidAbsence.paidAbsencePeriods ?? [];\r\n                report.absence.paidAbsence.paidAbsencePeriods.push({\r\n                  startDate : period.period?.start,\r\n                  endDate : period.period?.end,\r\n                  causeCode : this.getPaidAbsenceCauseCode(period.causeCode),\r\n                  absenceDays : period.period?.daysCount,\r\n                  amount : period.amount,\r\n                });\r\n              } else {\r\n                report.absence.unpaidAbsence = report.absence.unpaidAbsence ?? {};\r\n                report.absence.unpaidAbsence.unpaidAbsencePeriods = report.absence.unpaidAbsence.unpaidAbsencePeriods ?? [];\r\n                report.absence.unpaidAbsence.unpaidAbsencePeriods.push({\r\n                  startDate : period.period?.start,\r\n                  endDate : period.period?.end,\r\n                  causeCode : this.getUnpaidAbsenceCauseCode(period.causeCode),\r\n                  absenceDays : period.period?.daysCount,\r\n                });\r\n              }\r\n              if (!absencesStartDate || ( period.period && period.period.start && Dates.asDate(absencesStartDate) > Dates.asDate(period.period.start))) {\r\n                absencesStartDate = period.period?.start;\r\n              }\r\n              if (!absencesEndDate || ( period.period && period.period.end && Dates.asDate(absencesEndDate) < Dates.asDate(period.period.end))) {\r\n                absencesEndDate = period.period?.end;\r\n              }\r\n            });\r\n            report.absence.absenceRepStartDate = absencesStartDate;\r\n            report.absence.absenceRepEndDate = absencesEndDate;\r\n          }\r\n        }\r\n      });\r\n    });\r\n  }\r\n\r\n\r\n  /** Checks if the IR report is modified. */\r\n  public isIrModified(item: ApiListItem): boolean {\r\n    return item.flags.some((x) => x === \"modified\");\r\n  }\r\n\r\n  /** Checks if the Epr is delayed. */\r\n  public isDelayed(item: ApiListItem): boolean {\r\n    if (!item.data.firstDeliveredAt) {\r\n      const officialDate = Dates.add(item.salaryDate,5, \"day\");\r\n      const expiresAt = Dates.addWorkdays(officialDate, 0);\r\n      const today = Dates.asDate(\"today\");\r\n      return today > expiresAt;\r\n    }\r\n    return false;\r\n  }\r\n\r\n  private reloadFromServer(): Promise<irepr.EarningsPayment> {\r\n    return this.setStatus(this.api.getSingle(this.current.id)).then((data) => {\r\n      this.setCurrent(data);\r\n      return data;\r\n    });\r\n  }\r\n\r\n  private getUnpaidAbsenceCauseCode(causeCode: AbsenceCauseCode): irepr.UnpaidAbsenceCauseCode {\r\n    switch (causeCode) {\r\n      case AbsenceCauseCode.Illness:\r\n        return irepr.UnpaidAbsenceCauseCode.Illness;\r\n      case AbsenceCauseCode.PartTimeSickLeave:\r\n        return irepr.UnpaidAbsenceCauseCode.PartTimeSickLeave;\r\n      case AbsenceCauseCode.ParentalLeave:\r\n        return irepr.UnpaidAbsenceCauseCode.ParentalLeave;\r\n      case AbsenceCauseCode.SpecialMaternityLeave:\r\n        return irepr.UnpaidAbsenceCauseCode.SpecialMaternityLeave;\r\n      case AbsenceCauseCode.Rehabilitation:\r\n        return irepr.UnpaidAbsenceCauseCode.Rehabilitation;\r\n      case AbsenceCauseCode.ChildIllness:\r\n        return irepr.UnpaidAbsenceCauseCode.ChildIllness;\r\n      case AbsenceCauseCode.PartTimeChildCareLeave:\r\n        return irepr.UnpaidAbsenceCauseCode.PartTimeChildCareLeave;\r\n      case AbsenceCauseCode.Training:\r\n        return irepr.UnpaidAbsenceCauseCode.Training;\r\n      case AbsenceCauseCode.JobAlternationLeave:\r\n        return irepr.UnpaidAbsenceCauseCode.JobAlternationLeave;\r\n      case AbsenceCauseCode.StudyLeave:\r\n        return irepr.UnpaidAbsenceCauseCode.StudyLeave;\r\n      case AbsenceCauseCode.IndustrialAction:\r\n        return irepr.UnpaidAbsenceCauseCode.IndustrialAction;\r\n      case AbsenceCauseCode.InterruptionInWorkProvision:\r\n        return irepr.UnpaidAbsenceCauseCode.InterruptionInWorkProvision;\r\n      case AbsenceCauseCode.LeaveOfAbsence:\r\n        return irepr.UnpaidAbsenceCauseCode.LeaveOfAbsence;\r\n      case AbsenceCauseCode.MilitaryRefresherTraining:\r\n        return irepr.UnpaidAbsenceCauseCode.MilitaryRefresherTraining;\r\n      case AbsenceCauseCode.MilitaryService:\r\n        return irepr.UnpaidAbsenceCauseCode.MilitaryService;\r\n      case AbsenceCauseCode.LayOff:\r\n        return irepr.UnpaidAbsenceCauseCode.LayOff;\r\n      case AbsenceCauseCode.ChildCareLeave:\r\n        return irepr.UnpaidAbsenceCauseCode.ChildCareLeave;\r\n      case AbsenceCauseCode.Other:\r\n      default:\r\n        return irepr.UnpaidAbsenceCauseCode.Other;\r\n    }\r\n  }\r\n\r\n  private getPaidAbsenceCauseCode(causeCode: AbsenceCauseCode): irepr.PaidAbsenceCauseCode {\r\n    switch (causeCode) {\r\n      case AbsenceCauseCode.Illness:\r\n        return irepr.PaidAbsenceCauseCode.Illness;\r\n      case AbsenceCauseCode.PartTimeSickLeave:\r\n        return irepr.PaidAbsenceCauseCode.PartTimeSickLeave;\r\n      case AbsenceCauseCode.ParentalLeave:\r\n        return irepr.PaidAbsenceCauseCode.ParentalLeave;\r\n      case AbsenceCauseCode.SpecialMaternityLeave:\r\n        return irepr.PaidAbsenceCauseCode.SpecialMaternityLeave;\r\n      case AbsenceCauseCode.Rehabilitation:\r\n        return irepr.PaidAbsenceCauseCode.Rehabilitation;\r\n      case AbsenceCauseCode.ChildIllness:\r\n        return irepr.PaidAbsenceCauseCode.ChildIllness;\r\n      case AbsenceCauseCode.PartTimeChildCareLeave:\r\n        return irepr.PaidAbsenceCauseCode.PartTimeChildCareLeave;\r\n      case AbsenceCauseCode.Training:\r\n        return irepr.PaidAbsenceCauseCode.Training;\r\n      case AbsenceCauseCode.LeaveOfAbsence:\r\n        return irepr.PaidAbsenceCauseCode.LeaveOfAbsence;\r\n      case AbsenceCauseCode.MilitaryRefresherTraining:\r\n        return irepr.PaidAbsenceCauseCode.MilitaryRefresherTraining;\r\n      case AbsenceCauseCode.MidWeekHoliday:\r\n        return irepr.PaidAbsenceCauseCode.MidWeekHoliday;\r\n      case AbsenceCauseCode.AccruedHoliday:\r\n        return irepr.PaidAbsenceCauseCode.AccruedHoliday;\r\n      case AbsenceCauseCode.OccupationalAccident:\r\n        return irepr.PaidAbsenceCauseCode.OccupationalAccident;\r\n      case AbsenceCauseCode.AnnualLeave:\r\n        return irepr.PaidAbsenceCauseCode.AnnualLeave;\r\n      case AbsenceCauseCode.PartTimeAbsenceDueToRehabilitation:\r\n        return irepr.PaidAbsenceCauseCode.PartTimeAbsenceDueToRehabilitation;\r\n      case AbsenceCauseCode.Other:\r\n      default:\r\n        return irepr.PaidAbsenceCauseCode.Other;\r\n    }\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { ApiListItem, Dates, irpsr, IrPayerSummaries } from \"@salaxy/core\";\r\n\r\nimport { ApiCrudObjectController } from \"../bases\";\r\nimport { SessionService, UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Controller for user interface of Payer Summary Report (\"Tulorekisteri-ilmoitus\").\r\n */\r\nexport class IrPayerSummaryCrudController extends ApiCrudObjectController<irpsr.PayerSummary, any> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"IrPayerSummaries\",\r\n    \"UiHelpers\",\r\n    \"$location\",\r\n    \"$routeParams\",\r\n    \"SessionService\"\r\n  ];\r\n\r\n  constructor(\r\n    private fullApi: IrPayerSummaries,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    private session: SessionService,\r\n  ) { // Dependency injection\r\n    super(fullApi, uiHelpers, $location, $routeParams);\r\n  }\r\n\r\n  /**\r\n   * Initializes the controller\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"irpsr\",\r\n      detailsUrl: this.detailsUrl || \"/irpsr/details/\",\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/IrPsr.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n\r\n  /** Returns true if the report can be canceled. */\r\n  public get isCancellable() {\r\n    return this.current && this.getLatestNonErrorReportLogEntry()?.eventType === irpsr.ReportLogEventType.Sent;\r\n  }\r\n\r\n  /** Returns true if the item is read-only */\r\n  public get isReadOnly(): boolean {\r\n    return super.isReadOnly || (!(this as any).tempShowEditInNonAdminMode && !this.session.isInRole(\"admin\"));\r\n  }\r\n\r\n\r\n  /** Send to incomes register  */\r\n  public sendToIncomesRegister(startAt: Date): Promise<irpsr.PayerSummary> {\r\n    return this.save().then((psr) => {\r\n      if (psr.validation.isValid) {\r\n        const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.PayerSummaryComponent.common.loaderTextSending\");\r\n        const aso: irpsr.IrApiScheduleObject = {\r\n          id: this.current.id,\r\n          startAt: startAt ? JSON.stringify(startAt).replace(/\"/g, \"\"): null,\r\n          action: irpsr.IrScheduleAction.Send\r\n        };\r\n\r\n        return this.fullApi.sendSchedule(aso).then(() => {\r\n          return this.reloadFromServer().then(() => {\r\n            loader.dismiss();\r\n            return this.current;\r\n          });\r\n        });\r\n\r\n      } else {\r\n        this.uiHelpers.showAlert(\"SALAXY.NG1.PayerSummaryComponent.common.sendFailureTitle\", \"SALAXY.NG1.PayerSummaryComponent.common.validationErrorText\");\r\n        return this.current;\r\n      }\r\n    });\r\n  }\r\n\r\n  /** Get latest incomes register report log entry */\r\n  private getLatestNonErrorReportLogEntry(): irpsr.ReportLogEntry {\r\n    if (this.current.reportLog != null) {\r\n      const nonErrorEntries = this.current.reportLog.filter((x) => x.eventType !== irpsr.ReportLogEventType.Error);\r\n      if (nonErrorEntries.length > 0) {\r\n        return nonErrorEntries[nonErrorEntries.length - 1];\r\n      }\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /** Sends cancel request to incomes register */\r\n  public cancelToIncomesRegister(): Promise<irpsr.PayerSummary> {\r\n    const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.PayerSummaryComponent.common.loaderTextCanceling\");\r\n    const aso: irpsr.IrApiScheduleObject = {\r\n      id: this.current.id,\r\n      action: irpsr.IrScheduleAction.Cancel\r\n    };\r\n    return this.fullApi.sendSchedule(aso).then(() => {\r\n      return this.reloadFromServer().then( () => {\r\n        loader.dismiss();\r\n        return this.current;\r\n      });\r\n    });\r\n  }\r\n\r\n  /** Opens sheculing dialog and sends scheduling after successful dialog close */\r\n  public openSetScheduleDialog(): Promise<irpsr.PayerSummary>  {\r\n    return this.uiHelpers.openEditDialog(\"salaxy-components/report/modals/IrScheduleSendDialog.html\", {\r\n      startAt: new Date() }, {}).then((dialog) => {\r\n        if (dialog.result === \"ok\") {\r\n          return this.sendToIncomesRegister(dialog.item.startAt);\r\n        } else {\r\n          return this.current;\r\n        }\r\n      });\r\n  }\r\n\r\n  /** Remove Incomes register queue item */\r\n  public removeIrQueueItem(): Promise<irpsr.PayerSummary> {\r\n    const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.PayerSummaryComponent.common.loaderTextRemoving\");\r\n    return this.fullApi.removeIrQueueItem(this.current.id).then(() => {\r\n      return this.reloadFromServer().then(() => {\r\n        loader.dismiss();\r\n        return this.current;\r\n      });\r\n    });\r\n  }\r\n\r\n  /** Checks if the IR report is modified. */\r\n  public isIrModified(item: ApiListItem): boolean {\r\n    return item.flags.some( (x) => x === \"modified\");\r\n  }\r\n\r\n  /** Checks if the Psr is delayed. */\r\n  public isDelayed(item: ApiListItem): boolean {\r\n    if (!item.data.firstDeliveredAt) {\r\n      const officialDate = Dates.add(Dates.add(item.logicalDate,1, \"month\"),4, \"day\");\r\n      const expiresAt = Dates.addWorkdays(officialDate, 0); // the day or next work day\r\n      const today = Dates.asDate(\"today\");\r\n      return today > expiresAt;\r\n    }\r\n    return false;\r\n  }\r\n\r\n  private reloadFromServer(): Promise<irpsr.PayerSummary> {\r\n    return this.setStatus(this.api.getSingle(this.current.id)).then((data) => {\r\n      this.setCurrent(data);\r\n      return data;\r\n    });\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {  Report, reportPartial, ReportsLogic, ReportType } from \"@salaxy/core\";\r\n\r\nimport { ReportsService, SessionService } from \"../../services\";\r\n\r\n/**\r\n * Handles user interaction for fetching, showing and later generating Reports\r\n */\r\nexport class ReportsController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"ReportsService\",\r\n    \"SessionService\",\r\n  ];\r\n\r\n  /**\r\n   * Current report type for this controller. Default for the getReports() method.\r\n   */\r\n  public reportType: ReportType;\r\n\r\n  /**\r\n   * When using getReportHtmlById(), the HTML is set here.\r\n   * Also contains a spinner for loading and sets an alert if there is a problem.\r\n   */\r\n  public reportHtml;\r\n\r\n  /**\r\n   * Static instance of getReportTypes() to avoid a $digest problem that occured when calling getReportTypes() directly from the view.\r\n   * HACK: This may not work in a scenario where Controller is created before the Session.\r\n   */\r\n  public types = this.getReportTypes();\r\n\r\n  constructor(\r\n    private reportsService: ReportsService,\r\n    private sessionService: SessionService,\r\n  ) {\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit = () => {\r\n    //\r\n  };\r\n\r\n  /**\r\n   * Gets a list of reports (metadata only) filtered by a report type.\r\n   * @param type - Type of report. See type (string enumeration) for possible values. Default is the property reportType.\r\n   */\r\n  public getReports(type: ReportType = this.reportType): Report[] | Promise<Report[]> {\r\n    return this.reportsService.getReports(type);\r\n  }\r\n\r\n  /**\r\n   * Gets a list of available report types for the current user.\r\n   * TODO: This method is still under construction.\r\n   */\r\n  public getReportTypes() {\r\n    // TODO: Generalize this role logic and merge with moveToCore\r\n    const allReportTypes = ReportsLogic.getReportTypes();\r\n    const filtered = allReportTypes.filter((x) => this.sessionService.isInSomeRole(x.roles));\r\n    return filtered;\r\n  }\r\n\r\n  /**\r\n   * Gets an HTML report based on Calculation ID, runs it through $sce\r\n   * and sets it as reportHtml.\r\n   * @param reportType - Type of the report to fetch. See the HtmlReportType enumeration for possible values.\r\n   * @param calculationId - GUID for the calculation\r\n   * @returns A Promise with result HTML - already run through $sce.\r\n   */\r\n  public getReportHtmlById(reportType: reportPartial, calculationId: string): Promise<any> {\r\n    this.reportHtml = \"<salaxy-spinner></salaxy-spinner>\";\r\n    return this.reportsService.getReportHtmlById(reportType, calculationId).then((html) => {\r\n      this.reportHtml = html;\r\n      return html;\r\n    }).catch((reason) => {\r\n      this.reportHtml = `<div class=\"alert alert-danger\"><strong>Error in fetching report</strong><pre>${angular.toJson(reason)}</pre></div>`;\r\n    });\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Calculations } from \"@salaxy/core\";\r\n\r\nimport { InvoicesService, ReportsService, SessionService, UiHelpers } from \"../../services\";\r\n\r\nimport { CalculationCrudController } from \"../calc\";\r\n\r\n/**\r\n * The new ApiCrudObject type of CRUD controller for the calculation reports.\r\n * Note that SalaryRepots does not have separate CRUD methods, but instead\r\n * the CRUD structure is based on Calculations (extends CalculationCrudController).\r\n */\r\nexport class SalaryReportCrudController extends CalculationCrudController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Calculations\", \"ReportsService\", \"UiHelpers\", \"$location\", \"$routeParams\", \"SessionService\", \"InvoicesService\"];\r\n\r\n  /** Default query options for panel */\r\n  public panelQueryOptions = {\r\n    $filter: \"status eq 'paymentSucceeded'\",\r\n    $top: 5,\r\n    $orderby: \"salaryDate desc\",\r\n  };\r\n  /** Default query options for full list view */\r\n  public queryOptions = {\r\n    $filter: \"status eq 'paymentSucceeded'\",\r\n    $top: 20,\r\n    $orderby: \"salaryDate desc\",\r\n  };\r\n\r\n  constructor(\r\n    calculationsApi: Calculations,\r\n    reportsService: ReportsService,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    sessionService: SessionService,\r\n    protected invoicesService: InvoicesService,\r\n  ) {\r\n    super(calculationsApi, reportsService, uiHelpers, $location, $routeParams, sessionService, invoicesService);\r\n  }\r\n\r\n  /**\r\n   * Initializes the controller\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"reports/salary-reports\",\r\n      detailsUrl: this.detailsUrl || \"/calc/details/\",\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/SalaryReportsPanel.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n\r\n  /** Unselect all */\r\n  public unselectAll() {\r\n    if (this.odataController.selectedItems) {\r\n      this.odataController.selectedItems.splice(0, this.odataController.selectedItems.length);\r\n    }\r\n  }\r\n\r\n  /** Select all */\r\n  public selectAll() {\r\n    if (this.odataController.selectedItems && this.odataController.items) {\r\n      this.odataController.selectedItems.splice(0, this.odataController.selectedItems.length);\r\n      this.odataController.selectedItems.push(...this.odataController.items);\r\n    }\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { ApiListItem, ApiValidation, Dates, Reports, Translations } from \"@salaxy/core\";\r\n\r\nimport { WizardService, WizardStep } from \"../../services\";\r\nimport { WizardController } from \"../bases/WizardController\";\r\n\r\n/**\r\n * Provides methods for generating pay certificates.\r\n */\r\nexport class PayCertificateController extends WizardController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$scope\", \"WizardService\", \"Reports\"];\r\n\r\n  /** Worker for the report */\r\n  public worker: ApiListItem = null;\r\n\r\n  /** Selected workers */\r\n  public selectedWorkers: ApiListItem[] = [];\r\n\r\n  /** Period calculations */\r\n  public periodCalculations: ApiListItem[] = [];\r\n\r\n  /** Validation for the report. */\r\n  public validation: ApiValidation = null;\r\n\r\n  /** Pay certificate wizard configuration */\r\n  public wizardSteps: WizardStep[] = [\r\n    {\r\n      title: Translations.get(\"SALAXY.NG1.PayCertificateComponent.wizard.stepSelectWorkerTitle\"),\r\n      view: \"salaxy-components/report/PayCertificateStep1.html\",\r\n    },\r\n    {\r\n      title: Translations.get(\"SALAXY.NG1.PayCertificateComponent.wizard.stepSelectPeriodCalcsTitle\"),\r\n      view: \"salaxy-components/report/PayCertificateStep2.html\",\r\n    },\r\n    {\r\n      title: Translations.get(\"SALAXY.NG1.PayCertificateComponent.wizard.stepAdditionalInfoTitle\"),\r\n      view: \"salaxy-components/report/PayCertificateStep3.html\",\r\n    },\r\n  ];\r\n\r\n  constructor($scope: angular.IScope, wizardService: WizardService, private reports: Reports) {\r\n    super($scope, wizardService);\r\n  }\r\n\r\n  /**\r\n   * Initialization of the controller\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n    this.wizardService.setSteps(this.wizardSteps);\r\n    this.wizardService.activeStepNumber = 1;\r\n  }\r\n\r\n  /** Returns true if goNext is enabled  */\r\n  public get canGoNext(): boolean {\r\n    if (this.steps.length > this.step) {\r\n      if (this.steps[this.step] && !this.steps[this.step].disabled) {\r\n        if (this.step === 1 && this.selectedWorkers.length === 0) {\r\n          return false;\r\n        }\r\n        if (this.step === 2 && this.periodCalculations.length === 0) {\r\n          return false;\r\n        }\r\n\r\n        return true;\r\n\r\n      }\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /**\r\n   * Navigates to the next step if possible\r\n   */\r\n  public goNext() {\r\n    super.goNext();\r\n    if (this.step === 3) {\r\n      this.validate();\r\n    }\r\n  }\r\n\r\n  /** Selects the worker and advances the workflow */\r\n  public selectWorker(worker: ApiListItem, isSelected: boolean) {\r\n    if (isSelected) {\r\n      this.worker = worker;\r\n      this.selectedWorkers.splice(0, this.selectedWorkers.length);\r\n      this.selectedWorkers.push(this.worker);\r\n      this.periodCalculations = [];\r\n      this.validation = null;\r\n      this.goNext();\r\n    }\r\n  }\r\n\r\n  /** Selects calculations from the period */\r\n  public selectCalculations(items: ApiListItem[], weeks: number) {\r\n\r\n    // go x weeks to past\r\n    let periodStart = Dates.add(\"today\",-1 * weeks, \"week\");\r\n    // set to monday of that week\r\n    periodStart = Dates.startEnd(periodStart, \"start-week\");\r\n\r\n    this.periodCalculations.splice(0, this.periodCalculations.length);\r\n    for (const item of items) {\r\n      if (Dates.asDate(item.salaryDate) >= periodStart) {\r\n        this.periodCalculations.push(item);\r\n      }\r\n    }\r\n  }\r\n\r\n  /** Selects calculations from the period */\r\n  public unselectCalculations() {\r\n    this.periodCalculations.splice(0, this.periodCalculations.length);\r\n  }\r\n\r\n  /**\r\n   * Returns the url for downloading pdf.\r\n   * @param inline If true will open the pdf. The default is false: download as attachment.\r\n   * @returns URL for downloading the report.\r\n   */\r\n  public getDownloadPdfUrl(inline = false): string {\r\n    if (\r\n      !this.worker ||\r\n      !this.periodCalculations ||\r\n      this.periodCalculations.length === 0) {\r\n      return null;\r\n    }\r\n    return this.reports.getPayCertificatePdfUrl(this.worker.otherId, this.periodCalculations.map( (x) => x.id), inline);\r\n  }\r\n\r\n  /**\r\n   * Validates the report server side.\r\n   */\r\n  public validate() {\r\n    this.validation = null;\r\n    if (\r\n      !this.worker ||\r\n      !this.periodCalculations ||\r\n      this.periodCalculations.length === 0) {\r\n      return;\r\n    }\r\n    this.reports.validatePayCertificate(this.worker.otherId, this.periodCalculations.map( (x) => x.id)).then((result: ApiValidation) => {\r\n      this.validation = result;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Start new wizard\r\n   */\r\n  public startNew() {\r\n    this.step = 1;\r\n    this.worker = null;\r\n    this.selectedWorkers.splice(0, this.selectedWorkers.length);\r\n    this.periodCalculations = [];\r\n    this.validation = null;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { CalculationListItem, Configs, Datasets, DatasetStatus, Dates, PeriodType, PeriodDateKind, WorkerListItem, PayrollListItem, DatasetType, ApiListItem, Avatar } from \"@salaxy/core\";\r\n\r\nimport { SessionService, UiHelpers } from \"../../services\";\r\n\r\n/** Report template */\r\ninterface Template {\r\n  /** Template id */\r\n  id: string;\r\n  /** Owner of the template */\r\n  owner: string;\r\n  /** Template label */\r\n  label: string;\r\n  /** Template configuration*/\r\n  config: {\r\n    columnState?: any,\r\n    filterModel?: any,\r\n    columnGroupState?: any,\r\n    isPivotMode?: boolean,\r\n  };\r\n  /** Boolean indicating if the template is a user template */\r\n  isReadOnly: boolean;\r\n  /** Owners avatar */\r\n  avatar?: Avatar;\r\n}\r\n\r\n/**\r\n * Controller base class for configurable grid reports.\r\n */\r\nexport abstract class ConfigurableGridReportControllerBase<TData> implements angular.IController {\r\n\r\n  /** Usecase uri for report templates */\r\n  public abstract usecaseUri: string;\r\n\r\n  /** Current grid options. */\r\n  public abstract gridOptions: any;\r\n\r\n  /** ID for the element containing grid. */\r\n  public abstract gridElmentId;\r\n\r\n  /** default templates */\r\n  protected abstract defaultTemplates: Template[];\r\n\r\n  /** Current data */\r\n  public data: TData;\r\n\r\n  /** Current grid. */\r\n  public grid: any;\r\n\r\n  /** Options for data query. */\r\n  public queryOptions:\r\n    {\r\n      period: {\r\n        /** Period type for the query. */\r\n        periodType: PeriodType,\r\n        /** Ref date for the period. */\r\n        refDate?: string,\r\n        /** End date for the custom period. */\r\n        endDate?: string,\r\n        /** Period date kind */\r\n        periodDateKind: PeriodDateKind,\r\n        /** Selected workers */\r\n        selectedWorkers: WorkerListItem[],\r\n      },\r\n      calculations: CalculationListItem[],\r\n      payrolls: PayrollListItem[],\r\n    } = {\r\n      period: {\r\n        periodType: PeriodType.Month,\r\n        refDate: Dates.format(Dates.add(\"today\",-1, \"month\"),\"YYYY-MM-01\"),\r\n        endDate: null,\r\n        periodDateKind: PeriodDateKind.SalaryDate,\r\n        selectedWorkers: [],\r\n      },\r\n      calculations: [],\r\n      payrolls: [],\r\n  };\r\n\r\n  /** Current report template */\r\n  public templateId: string;\r\n\r\n  /** All loaded templates */\r\n  public templates: Template[] = [];\r\n\r\n  constructor(protected datasets: Datasets, protected uiHelpers: UiHelpers, protected sessionService: SessionService) {\r\n  }\r\n\r\n  /**\r\n   * Initialize controller values.\r\n   */\r\n  public $onInit() {\r\n    const getSalaxyGridModule = (): Promise<any> => {\r\n      // Support both esm and umd builds...\r\n      return Promise.resolve(Configs.global.agGrid);\r\n    };\r\n\r\n    getSalaxyGridModule().then((agGridModule) => {\r\n      const agGrid = agGridModule;\r\n      const AG_GRID_LICENCE_KEY = \"CompanyName=Suomen Palkanlaskenta Oy,LicensedGroup=Palkkaus.fi,LicenseType=MultipleApplications,LicensedConcurrentDeveloperCount=3,LicensedProductionInstancesCount=1,AssetReference=AG-012462,ExpiryDate=17_December_2021_[v2]_MTYzOTY5OTIwMDAwMA==5d6e41ff68f667b432fc0424ad42ca1d\";\r\n      agGrid.LicenseManager.setLicenseKey(AG_GRID_LICENCE_KEY);\r\n      if (!agGrid.ModuleRegistry.getRegisteredModules().length) {\r\n        agGrid.ModuleRegistry.registerModules(agGrid.AllModules);\r\n      }\r\n\r\n      const eGridDiv = document.querySelector(this.gridElmentId);\r\n      this.grid = new agGrid.Grid(eGridDiv, this.gridOptions);\r\n\r\n      this.loadTemplates();\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Returns the template definition\r\n   * @param templateId Template id.\r\n   */\r\n  public getTemplate(templateId: string) {\r\n    return this.templates.find((x) => x.id === templateId);\r\n  }\r\n\r\n  /**\r\n   * Selects the template to show\r\n   * @param templateId The selected template.\r\n   */\r\n  public selectTemplate(templateId: any) {\r\n    this.templateId = templateId;\r\n    if (this.grid) {\r\n      this.loadTemplateConfig(templateId).then((template) => {\r\n        this.setTemplateStateToGrid(template);\r\n      });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Save template\r\n   */\r\n  public showSaveTemplate() {\r\n    const currentTemplate = this.getTemplate(this.templateId);\r\n    const item: {\r\n      /** Boolean indicating a new template */\r\n      isNew: boolean,\r\n      /** Boolean indicating if the template can be edited. */\r\n      isEditable: boolean,\r\n      /** Label for the template */\r\n      label: string,\r\n    } = {\r\n      isNew: currentTemplate.isReadOnly,\r\n      isEditable: !currentTemplate.isReadOnly,\r\n      label: currentTemplate.isReadOnly ? \"Uusi raportti (\" + (this.templates.filter((x) => !x.isReadOnly).length + 1) + \")\" : currentTemplate.label,\r\n    };\r\n\r\n    const saveTemplate = (template: Template): Promise<Template> => {\r\n      return this.datasets.save({\r\n        id: template.id,\r\n        info: {\r\n          label: template.label,\r\n          status: DatasetStatus.Template,\r\n          type: DatasetType.ReportAdHoc,\r\n        },\r\n        usecase: {\r\n          uri: this.usecaseUri\r\n        },\r\n        data: [{\r\n          content: [\r\n            template.config\r\n          ]\r\n        }]\r\n      }).then((dataset) => ({\r\n        id: dataset.id,\r\n        owner: dataset.owner,\r\n        label: dataset.info.label,\r\n        config: dataset.data[0].content[0],\r\n        isReadOnly: dataset.isReadOnly,\r\n        avatar: this.sessionService.avatar,\r\n      }));\r\n    };\r\n\r\n    this.uiHelpers.openEditDialog(\r\n      \"salaxy-components/report/modals/CalculationReportSaveTemplate.html\",\r\n      item,\r\n      null).then((saveResult) => {\r\n        if (saveResult.action === \"ok\") {\r\n          const editedTemplate = saveResult.item;\r\n          if (!editedTemplate.isNew) {\r\n            currentTemplate.label = editedTemplate.label;\r\n            this.setGridStateToTemplate(currentTemplate);\r\n            saveTemplate(currentTemplate);\r\n          } else {\r\n            const newTemplate = {\r\n              id: null,\r\n              owner: null,\r\n              label: editedTemplate.label,\r\n              config: {},\r\n              isReadOnly: false,\r\n            };\r\n            this.setGridStateToTemplate(newTemplate);\r\n            saveTemplate(newTemplate).then((savedTemplate) => {\r\n              this.templates.push(savedTemplate);\r\n              this.selectTemplate(savedTemplate.id);\r\n            });\r\n          }\r\n        } else if (saveResult.action === \"delete\") {\r\n          this.showDeleteTemplate();\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Delete template\r\n   */\r\n  public showDeleteTemplate() {\r\n    const template = this.getTemplate(this.templateId);\r\n    this.uiHelpers.showConfirm(`Haluatko poistaa tämän raporttipohjan '${template.label}'?`).then((result) => {\r\n      if (result) {\r\n        if (!template.isReadOnly) {\r\n          const idx = this.templates.findIndex((x) => x.id === this.templateId);\r\n          this.templates.splice(idx, 1);\r\n          this.selectTemplate(this.templates[idx - 1].id);\r\n          this.datasets.delete(template.id);\r\n        }\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shows the period selection dialog and makes the search.\r\n   */\r\n  public showPeriodSelection() {\r\n    this.uiHelpers.openEditDialog(\r\n      \"salaxy-components/report/modals/CalculationReportPeriodSelection.html\",\r\n      this.queryOptions.period,\r\n      {\r\n        showWorkerSelection: (workerPeriod: any) => {\r\n          this.uiHelpers.openEditDialog(\r\n            \"salaxy-components/modals/calc/WorkerList.html\",\r\n            [].concat(...workerPeriod.selectedWorkers),\r\n            {\r\n              title: \"Valitse työntekijät\",\r\n            }).then((selectionResult) => {\r\n              if (selectionResult.action === \"ok\") {\r\n                workerPeriod.selectedWorkers.splice(0, workerPeriod.selectedWorkers.length);\r\n                workerPeriod.selectedWorkers.push(...selectionResult.item);\r\n              }\r\n            });\r\n        }\r\n      }).then((periodResult) => {\r\n        if (periodResult.action === \"ok\") {\r\n          this.queryOptions.period = periodResult.item;\r\n          this.gridOptions.api.showLoadingOverlay();\r\n          const workerIds = periodResult.item.selectedWorkers.length > 0 ? periodResult.item.selectedWorkers.map((x) => x.otherPartyInfo.avatar.id) : null;\r\n          this.queryDataForPeriod(periodResult.item.refDate, periodResult.item.periodType, periodResult.item.endDate, periodResult.item.periodDateKind, workerIds)\r\n            .then((dataResult) => {\r\n              this.setData(dataResult);\r\n            });\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Shows the calculation selection dialog and makes the search.\r\n   */\r\n  public showCalcsSelection() {\r\n    this.uiHelpers.openEditDialog(\r\n      \"salaxy-components/modals/calc/CalcList.html\",\r\n      this.queryOptions.calculations,\r\n      {\r\n        title: \"Valitse maksetut palkat\",\r\n        category: \"paid\",\r\n      }).then((selectionResult) => {\r\n        if (selectionResult.action === \"ok\" && selectionResult.item.length > 0) {\r\n          this.queryOptions.calculations = selectionResult.item;\r\n          const ids = selectionResult.item.map((x) => x.id);\r\n          this.gridOptions.api.showLoadingOverlay();\r\n          this.queryDataForCalculationIds(ids).then((dataResult) => {\r\n            this.setData(dataResult);\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Shows the calculation selection dialog and makes the search.\r\n   */\r\n  public showPayrollSelection() {\r\n    this.uiHelpers.openEditDialog(\r\n      \"salaxy-components/modals/payroll/PayrollList.html\",\r\n      this.queryOptions.payrolls,\r\n      {\r\n        title: \"Valitse palkkalistat\",\r\n        category: \"paid\",\r\n      }, \"lg\").then((selectionResult) => {\r\n        if (selectionResult.action === \"ok\" && selectionResult.item.length > 0) {\r\n          this.queryOptions.payrolls = selectionResult.item;\r\n          const ids = selectionResult.item.reduce((all, x) => all.concat(x.businessObjects), []);\r\n          this.gridOptions.api.showLoadingOverlay();\r\n          this.queryDataForCalculationIds(ids).then((dataResult) => {\r\n            this.setData(dataResult);\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Gets the data based on given set of calculations.\r\n   * @param calculationIds - Calculations that are the bases for the report.\r\n   * @returns A Promise with result data.\r\n   */\r\n  public abstract queryDataForCalculationIds(calculationIds: string[]): Promise<TData>;\r\n\r\n  /**\r\n   * Gets the monthly / quarterly / yearly cumulative data for the current account.\r\n   * @param refDate Reference date for the period. Please note that even if the date is not the first day of the given period, the entire period is returned.\r\n   * @param periodType Month, quarter, year or a custom period. The custom period requires endDate. Default value is the month.\r\n   * @param endDate End date for the period. Required only for the custom period.\r\n   * @param periodDateKind Period date type: paid at date, salary date or work date.\r\n   * @param workers List of worker official ids.\r\n   * @returns A Promise with result data.\r\n   */\r\n   public abstract queryDataForPeriod(refDate: string, periodType?: PeriodType | \"all\", endDate?: string, periodDateKind?: PeriodDateKind, workers?: string[]): Promise<TData>;\r\n\r\n   /**\r\n    * Processes and sets the data.\r\n    */\r\n  public abstract setData(result: TData);\r\n\r\n  private loadTemplates() {\r\n    this.templates.splice(0);\r\n    const filter = `status eq '${DatasetStatus.Template}' and entityType eq '${DatasetType.ReportAdHoc}' and data/usecaseUri eq '${this.usecaseUri}'`;\r\n    this.datasets.getOData({ $filter: filter }).then((result) => {\r\n      const customerTemplates = result.items.map((x: ApiListItem) => ({\r\n        id: x.id,\r\n        owner: x.owner,\r\n        label: x.shortText,\r\n        config: null,\r\n        isReadOnly: x.isReadOnly,\r\n        avatar: x.ownerInfo.avatar,\r\n      }));\r\n      this.templates.push(...this.defaultTemplates.concat(...customerTemplates));\r\n    });\r\n  }\r\n\r\n  private loadTemplateConfig(templateId: string) {\r\n    const template = this.getTemplate(templateId);\r\n    if (template.config) {\r\n      return Promise.resolve(template);\r\n    }\r\n    else {\r\n      return this.datasets.getSingle(template.id + (template.isReadOnly ? `@${template.owner}` : \"\")).then((dataset) => {\r\n        template.config = dataset.data.length == 1 && dataset.data[0].content.length == 1 ? dataset.data[0].content[0] : {};\r\n        return template;\r\n      });\r\n    }\r\n  }\r\n\r\n  private setTemplateStateToGrid(template: Template) {\r\n    this.gridOptions.columnApi.setPivotMode(template.config.isPivotMode ?? false);\r\n    if (template.config.columnState) {\r\n      this.gridOptions.columnApi.applyColumnState({\r\n        state: template.config.columnState,\r\n        applyOrder: true\r\n      });\r\n    }\r\n    else\r\n    {\r\n      this.gridOptions.columnApi.resetColumnState();\r\n    }\r\n    if (template.config.columnGroupState) {\r\n      this.gridOptions.columnApi.setColumnGroupState(template.config.columnGroupState);\r\n    }\r\n    else\r\n    {\r\n      this.gridOptions.columnApi.resetColumnGroupState();\r\n    }\r\n\r\n    this.gridOptions.api.setFilterModel(template.config.filterModel);\r\n  }\r\n\r\n  private setGridStateToTemplate(template: Template) {\r\n    template.config = template.config ?? {};\r\n    template.config.columnState = this.gridOptions.columnApi.getColumnState();\r\n    template.config.columnGroupState = this.gridOptions.columnApi.getColumnGroupState();\r\n    template.config.filterModel = this.gridOptions.api.getFilterModel();\r\n    template.config.isPivotMode = this.gridOptions.columnApi.isPivotMode();\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { CalculationReportData, Datasets, Dates, Numeric, PeriodType, PeriodDateKind, Reports, Texts, LegalEntityType } from \"@salaxy/core\";\r\n\r\nimport { SessionService, UiHelpers } from \"../../services\";\r\nimport { ConfigurableGridReportControllerBase } from \"./ConfigurableGridReportControllerBase\";\r\n\r\n/**\r\n * Controller for calculation reports.\r\n */\r\nexport class CalculationReportController extends ConfigurableGridReportControllerBase<CalculationReportData> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Datasets\", \"UiHelpers\", \"SessionService\", \"Reports\", \"$timeout\"];\r\n\r\n  /** Usecase uri for report templates */\r\n  public usecaseUri = \"palkkaus.fi/reports/calculationReport\";\r\n\r\n  /** Current grid options. */\r\n  public gridOptions: any = {\r\n    statusBar: {\r\n      statusPanels: [\r\n        { statusPanel: \"agTotalAndFilteredRowCountComponent\", key: \"totalAndFilter\", align: \"left\" },\r\n        { statusPanel: \"agSelectedRowCountComponent\", align: \"left\" },\r\n        { statusPanel: \"agAggregationComponent\", align: \"right\" }\r\n      ]\r\n    },\r\n    enableMultiRowDragging: true,\r\n    rowGroupPanelShow: \"always\",\r\n    pivotPanelShow: \"always\",\r\n    enableCharts: true,\r\n    enableRangeSelection: true,\r\n\r\n    defaultExportParams: {\r\n      columnGroups: true,\r\n      headerRowHeight: 30,\r\n      rowHeight: 22,\r\n      fontSize: 14,\r\n    },\r\n    defaultColDef: {\r\n      flex: 1,\r\n      minWidth: 200,\r\n      sortable: true,\r\n      filter: true,\r\n      resizable: true,\r\n      floatingFilter: true,\r\n    },\r\n    sideBar: { toolPanels: [\"columns\", \"filters\"] },\r\n    rowData: [],\r\n  };\r\n\r\n  /** ID for the element containing grid. */\r\n  public gridElmentId = \"#dataGrid\";\r\n\r\n  /** Default templates */\r\n  public defaultTemplates = [\r\n      {\r\n        id: \"incomeTypes\",\r\n        owner: null,\r\n        label: \"Tulolajiraportti\",\r\n        config: null,\r\n        isReadOnly: true,\r\n        avatar: {\r\n          initials: \"TLR\",\r\n          entityType: LegalEntityType.Company,\r\n          color: \"#009fd8\"\r\n        }\r\n      },\r\n      {\r\n        id: \"totals\",\r\n        owner: null,\r\n        label: \"Palkanmaksujen erittely\",\r\n        config: null,\r\n        isReadOnly: true,\r\n        avatar: {\r\n          initials: \"PME\",\r\n          entityType: LegalEntityType.Company,\r\n          color: \"#009fd8\"\r\n        }\r\n      },\r\n      {\r\n        id: \"plain\",\r\n        owner: null,\r\n        label: \"Kaikki sarakkeet\",\r\n        config: {},\r\n        isReadOnly: true,\r\n        avatar: {\r\n          initials: \"Kasa\",\r\n          entityType: LegalEntityType.Company,\r\n          color: \"#009fd8\"\r\n        }\r\n      }\r\n  ];\r\n\r\n  constructor(datasets: Datasets, uiHelpers: UiHelpers, sessionService: SessionService, private reports: Reports,  private $timeout: angular.ITimeoutService) {\r\n    super(datasets, uiHelpers, sessionService);\r\n  }\r\n\r\n  /**\r\n   * Initialize controller values.\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /**\r\n   * Processes and sets the data.\r\n   */\r\n  public setData(result: CalculationReportData) {\r\n    this.data = result;\r\n\r\n    const sortingDateComparator = (a, b) => {\r\n      if (!a || !b) {\r\n        return a === b ? 0 : a ? 1 : -1;\r\n      }\r\n      const mA = Dates.asDate(a);\r\n      const mB = Dates.asDate(b);\r\n      return mA === mB ? 0 : mA > mB ? 1 : -1;\r\n    };\r\n    const filterDateComparator = (a, b) => sortingDateComparator(b, a);\r\n\r\n    const columnDefs = [];\r\n    columnDefs.push(\r\n      {\r\n        headerName: \"Laskelmat\",\r\n        children: [\r\n          {\r\n            headerName: \"Työntekijä\",\r\n            rowDrag: true,\r\n            field: \"worker\",\r\n            enableRowGroup: true,\r\n            filter: \"agMultiColumnFilter\",\r\n          },\r\n          {\r\n            headerName: \"Laskelma\",\r\n            // rowDrag: true,\r\n            field: \"calculation\",\r\n            // enableRowGroup: true,\r\n            valueGetter: (params) => {\r\n              if (params.node && params.node.data) {\r\n                return `${params.node.data.worker} ${params.node.data.salaryDate} ${Numeric.formatPrice(params.node.data[\"totals-totalGrossSalary\"])}`;\r\n              }\r\n              return \"\";\r\n            },\r\n            cellRenderer: (params) => {\r\n              if (params.node && params.node.data) {\r\n                return `<a href=\"#/calc/details/${params.node.data.calculationId}\" target=\"_blank\" rel=\"noopener\">${Texts.escapeHtml(params.node.data.worker)} ${params.node.data.salaryDate} ${Numeric.formatPrice(params.node.data[\"totals-totalGrossSalary\"])}</a>`;\r\n              }\r\n              return \"\";\r\n            }\r\n          },\r\n          {\r\n            headerName: \"Työntekijän syntymäaika\",\r\n            field: \"workerBirthDate\",\r\n            valueFormatter: params => Dates.getFormattedDate(params.value),\r\n            type: [\"rightAligned\"],\r\n            filter: \"agDateColumnFilter\",\r\n            comparator: sortingDateComparator,\r\n            filterParams: { comparator: filterDateComparator, },\r\n          },\r\n          {\r\n            headerName: \"Palkkapäivä\",\r\n            field: \"salaryDate\",\r\n            valueFormatter: params => Dates.getFormattedDate(params.value),\r\n            type: [\"rightAligned\"],\r\n            filter: \"agDateColumnFilter\",\r\n            comparator: sortingDateComparator,\r\n            filterParams: { comparator: filterDateComparator, },\r\n          },\r\n          {\r\n            headerName: \"Brutto\",\r\n            field: \"totalGrossSalary\",\r\n            valueGetter: (params) => {\r\n              if (params.node && params.node.data) {\r\n                return params.node.data[\"totals-totalGrossSalary\"];\r\n              }\r\n              return null;\r\n            },\r\n            type: [\"numericColumn\"],\r\n            valueFormatter: params => Numeric.formatNumber(params.value, 2),\r\n            filter: \"agNumberColumnFilter\",\r\n          },\r\n          {\r\n            headerName: \"Kuvaus\",\r\n            field: \"workDescription\",\r\n            filter: \"agMultiColumnFilter\",\r\n          },\r\n          {\r\n            headerName: \"Aloituspäivä\",\r\n            field: \"workStartDate\",\r\n            valueFormatter: params => Dates.getFormattedDate(params.value),\r\n            type: [\"rightAligned\"],\r\n            filter: \"agDateColumnFilter\",\r\n            comparator: sortingDateComparator,\r\n            filterParams: { comparator: filterDateComparator, },\r\n          },\r\n          {\r\n            headerName: \"Lopetuspäivä\",\r\n            field: \"workEndDate\",\r\n            valueFormatter: params => Dates.getFormattedDate(params.value),\r\n            type: [\"rightAligned\"],\r\n            filter: \"agDateColumnFilter\",\r\n            comparator: sortingDateComparator,\r\n            filterParams: { comparator: filterDateComparator, },\r\n          },\r\n          {\r\n            headerName: \"Työsuhteen aloituspäivä\",\r\n            field: \"workerEmploymentStartDate\",\r\n            valueFormatter: params => Dates.getFormattedDate(params.value),\r\n            type: [\"rightAligned\"],\r\n            filter: \"agDateColumnFilter\",\r\n            comparator: sortingDateComparator,\r\n            filterParams: { comparator: filterDateComparator, },\r\n          },\r\n          {\r\n            headerName: \"Työsuhteen päättymispäivä\",\r\n            field: \"workerEmploymentEndDate\",\r\n            valueFormatter: params => Dates.getFormattedDate(params.value),\r\n            type: [\"rightAligned\"],\r\n            filter: \"agDateColumnFilter\",\r\n            comparator: sortingDateComparator,\r\n            filterParams: { comparator: filterDateComparator, },\r\n          },\r\n          {\r\n            headerName: \"Määräaikainen työsuhde\",\r\n            field: \"workerEmploymentIsFixedTerm\",\r\n            filter: \"agMultiColumnFilter\",\r\n          },\r\n        ]\r\n      },\r\n      {\r\n        headerName: \"Ryhmittelyt\",\r\n        children: [\r\n          {\r\n            headerName: \"Kuukausi\",\r\n            field: \"salaryMonth\",\r\n            enablePivot: true,\r\n            enableRowGroup: true,\r\n            type: [\"numericColumn\"],\r\n            filter: \"agMultiColumnFilter\",\r\n          },\r\n          {\r\n            headerName: \"Vuosi\",\r\n            field: \"salaryYear\",\r\n            enablePivot: true,\r\n            enableRowGroup: true,\r\n            type: [\"numericColumn\"],\r\n            filter: \"agMultiColumnFilter\",\r\n          },\r\n          {\r\n            headerName: \"Ammattiluokka\",\r\n            field: \"occupationCode\",\r\n            enablePivot: true,\r\n            enableRowGroup: true,\r\n            filter: \"agMultiColumnFilter\",\r\n          },\r\n          {\r\n            headerName: \"Eläketurva\",\r\n            field: \"pensionCalculation\",\r\n            enablePivot: true,\r\n            enableRowGroup: true,\r\n            filter: \"agMultiColumnFilter\",\r\n          },\r\n        ],\r\n      }\r\n    );\r\n    const irGroupDef = {\r\n      headerName: \"Tulolajit\",\r\n      children: [],\r\n    };\r\n    columnDefs.push(irGroupDef);\r\n    Object.keys(this.data.irLabels).forEach((key) => {\r\n      irGroupDef.children.push({\r\n        field: key,\r\n        headerName: this.data.irLabels[key],\r\n        enableValue: true,\r\n        type: [\"numericColumn\"],\r\n        valueFormatter: params => Numeric.formatNumber(params.value, 2),\r\n        filter: \"agNumberColumnFilter\",\r\n      });\r\n    });\r\n\r\n    const typeGroupDef = {\r\n      headerName: \"Rivityypit\",\r\n      children: [],\r\n    };\r\n    columnDefs.push(typeGroupDef);\r\n    Object.keys(this.data.typeLabels).forEach((key) => {\r\n      typeGroupDef.children.push({\r\n        field: key,\r\n        headerName: this.data.typeLabels[key],\r\n        enableValue: true,\r\n        type: [\"numericColumn\"],\r\n        valueFormatter: params => Numeric.formatNumber(params.value, 2),\r\n        filter: \"agNumberColumnFilter\",\r\n      });\r\n    });\r\n\r\n    const employerCalcDef = {\r\n      headerName: \"Työnantaja\",\r\n      children: [],\r\n    };\r\n    const workerCalcDef = {\r\n      headerName: \"Työntekijä\",\r\n      children: [],\r\n    };\r\n    const totalsDef = {\r\n      headerName: \"Yhteensä\",\r\n      children: [],\r\n    };\r\n    const totalGroupDef = {\r\n      headerName: \"Maksut\",\r\n      children: [\r\n        workerCalcDef,\r\n        employerCalcDef,\r\n        totalsDef,\r\n      ],\r\n    };\r\n    columnDefs.push(totalGroupDef);\r\n    Object.keys(this.data.totalLabels).forEach((key) => {\r\n      const def = key.indexOf(\"employerCalc\") === 0 ? employerCalcDef :\r\n        key.indexOf(\"workerCalc\") === 0 ? workerCalcDef : totalsDef;\r\n\r\n      def.children.push({\r\n        field: key,\r\n        headerName: this.data.totalLabels[key],\r\n        enableValue: true,\r\n        type: [\"numericColumn\"],\r\n        valueFormatter: params => Numeric.formatNumber(params.value, 2),\r\n        filter: \"agNumberColumnFilter\",\r\n      });\r\n    });\r\n\r\n    // Create presets if not created.\r\n    const incomeTypes = this.getTemplate(\"incomeTypes\");\r\n    incomeTypes.config = incomeTypes.config ?? { columnState: this.createIncomeTypesPreset(columnDefs, this.data.rows)};\r\n\r\n    const totals = this.getTemplate(\"totals\");\r\n    totals.config = totals.config ?? { columnState: this.createTotalsPreset(columnDefs)};\r\n\r\n    // create the grid passing in the div to use together with the columns & data we want to use\r\n    this.$timeout(() => {\r\n      const filterModel = this.gridOptions.api.getFilterModel();\r\n      this.gridOptions.api.setFilterModel(null);\r\n      this.gridOptions.api.setRowData(this.data.rows);\r\n      this.gridOptions.api.setColumnDefs(columnDefs);\r\n      this.gridOptions.api.setFilterModel(filterModel);\r\n      this.selectTemplate(this.templateId ?? \"incomeTypes\");\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Gets the monthly / quarterly / yearly cumulative data for the current account.\r\n   * @param refDate Reference date for the period. Please note that even if the date is not the first day of the given period, the entire period is returned.\r\n   * @param periodType Month, quarter, year or a custom period. The custom period requires endDate. Default value is the month.\r\n   * @param endDate End date for the period. Required only for the custom period.\r\n   * @param periodDateKind Period date type: paid at date, salary date or work date.\r\n   * @param workers List of worker official ids.\r\n   * @returns A Promise with result data.\r\n   */\r\n  public queryDataForPeriod(refDate: string, periodType?: PeriodType | \"all\", endDate?: string, periodDateKind?: PeriodDateKind, workers?: string[]): Promise<CalculationReportData> {\r\n\r\n    if (periodType === \"all\") {\r\n      refDate = \"2010-01-01\";\r\n      endDate = \"2100-01-01\";\r\n      periodType = PeriodType.Custom;\r\n    }\r\n    return this.reports.getCalculationReportData(refDate,periodType,endDate, periodDateKind, workers);\r\n  }\r\n\r\n  /**\r\n   * Gets the cumulative data based on given set of calculations.\r\n   * @param calculationIds - Calculations that are the bases for the report.\r\n   * @returns A Promise with result data.\r\n   */\r\n  public queryDataForCalculationIds(calculationIds: string[]): Promise<CalculationReportData> {\r\n    return this.reports.getCalculationReportDataForCalculationIds(calculationIds);\r\n  }\r\n\r\n  private createIncomeTypesPreset(columnDefs: any, rows: any[]) {\r\n    const preset = [];\r\n\r\n    // Laskelmat\r\n    const calculationDef = columnDefs[0];\r\n    for (const def of calculationDef.children) {\r\n      switch (def.field) {\r\n        case \"worker\":\r\n          preset.push(this.createPresetCol(def.field, true, true));\r\n          break;\r\n        case \"calculation\":\r\n          preset.push(this.createPresetCol(def.field, false));\r\n          break;\r\n        default:\r\n          preset.push(this.createPresetCol(def.field, true));\r\n      }\r\n    }\r\n    // Dimensiot\r\n    const dimensionDef = columnDefs[1];\r\n    for (const def of dimensionDef.children) {\r\n      preset.push(this.createPresetCol(def.field, true));\r\n    }\r\n    // Tulolajit\r\n    const incomeTypeDef = columnDefs[2];\r\n    for (const def of incomeTypeDef.children) {\r\n      const hide = !(rows ?? []).find( x => x[def.field]);\r\n      if (def.field.endsWith(\"-price\")) {\r\n        preset.push(this.createPresetCol(def.field, hide, false, \"avg\"));\r\n      } else {\r\n        preset.push(this.createPresetCol(def.field, hide, false, \"sum\"));\r\n      }\r\n    }\r\n\r\n    // Rivityypit\r\n    const rowTypeDef = columnDefs[3];\r\n    for (const def of rowTypeDef.children) {\r\n      preset.push(this.createPresetCol(def.field, true));\r\n    }\r\n\r\n    // Maksut - työntekijä\r\n    const workerTotalsDef = columnDefs[4].children[0];\r\n    for (const def of workerTotalsDef.children) {\r\n      preset.push(this.createPresetCol(def.field, true));\r\n    }\r\n\r\n    // Maksut - työnantaja\r\n    const employerTotalsDef = columnDefs[4].children[1];\r\n    for (const def of employerTotalsDef.children) {\r\n      preset.push(this.createPresetCol(def.field, true));\r\n    }\r\n\r\n    // Maksut - yhteensä\r\n    const totalsDef = columnDefs[4].children[2];\r\n    for (const def of totalsDef.children) {\r\n      preset.push(this.createPresetCol(def.field, true));\r\n    }\r\n\r\n    return preset;\r\n  }\r\n\r\n  private createTotalsPreset(columnDefs: any) {\r\n    const preset = [];\r\n\r\n    // Laskelmat\r\n    const calculationDef = columnDefs[0];\r\n    for (const def of calculationDef.children) {\r\n      switch (def.field) {\r\n        case \"worker\":\r\n          preset.push(this.createPresetCol(def.field, true, true));\r\n          break;\r\n        case \"salaryDate\":\r\n        case \"workStartDate\":\r\n        case \"workEndDate\":\r\n          preset.push(this.createPresetCol(def.field, false));\r\n          break;\r\n        default:\r\n          preset.push(this.createPresetCol(def.field, true));\r\n          break;\r\n      }\r\n    }\r\n    // Dimensiot\r\n    const dimensionDef = columnDefs[1];\r\n    for (const def of dimensionDef.children) {\r\n      switch (def.field) {\r\n        case \"pensionCalculation\":\r\n          preset.push(this.createPresetCol(def.field, false));\r\n          break;\r\n        default:\r\n          preset.push(this.createPresetCol(def.field, true));\r\n          break;\r\n      }\r\n    }\r\n    // Tulolajit\r\n    const incomeTypeDef = columnDefs[2];\r\n    for (const def of incomeTypeDef.children) {\r\n      preset.push(this.createPresetCol(def.field, true));\r\n    }\r\n\r\n    // Rivityypit\r\n    const rowTypeDef = columnDefs[3];\r\n    for (const def of rowTypeDef.children) {\r\n      preset.push(this.createPresetCol(def.field, true));\r\n    }\r\n\r\n    const totalFields = [\r\n      \"totals-totalGrossSalary\",\r\n      \"workerCalc-benefits\",\r\n      \"totals-annualHolidayCompensation\",\r\n      \"totals-holidayBonus\",\r\n      \"totals-holidaySalary\",\r\n      // \"muut vähennettävät erät ml. luontoiseduista vähennettävät\"\r\n      \"totals-totalTaxable\",\r\n      \"workerCalc-tax\",\r\n      \"workerCalc-pension\",\r\n      \"workerCalc-unemploymentInsurance\",\r\n      \"workerCalc-unionPayment\",\r\n      \"workerCalc-foreclosure\",\r\n      \"workerCalc-salaryAdvance\",\r\n      \"workerCalc-otherDeductions\",\r\n      \"workerCalc-deductions\",\r\n      \"workerCalc-prepaidExpenses\",\r\n      \"totals-totalExpenses\",\r\n      \"workerCalc-totalWorkerPayment\",\r\n      \"employerCalc-totalPayment\",\r\n      \"employerCalc-palkkaus\",\r\n      \"employerCalc-service\",\r\n      \"employerCalc-socialSecurity\",\r\n      \"totals-pension\",\r\n      \"employerCalc-pension\",\r\n      \"totals-unemployment\",\r\n      \"employerCalc-unemployment\",\r\n      \"totals-totalPensionInsuranceBase\",\r\n      \"totals-totalSocialSecurityBase\",\r\n      \"totals-totalHealthInsuranceBase\",\r\n      \"totals-totalUnemploymentInsuranceBase\",\r\n      \"totals-totalAccidentInsuranceBase\",\r\n      \"totals-totalAccidentInsurance\",\r\n      \"totals-totalGroupLifeInsurance\"\r\n    ];\r\n\r\n    for (const field of totalFields) {\r\n      preset.push(this.createPresetCol(field, false, false, \"sum\"));\r\n    }\r\n\r\n    // Maksut - työntekijä\r\n    const workerTotalsDef = columnDefs[4].children[0];\r\n    for (const def of workerTotalsDef.children) {\r\n      if (totalFields.indexOf(def.field) < 0) {\r\n        preset.push(this.createPresetCol(def.field, true));\r\n      }\r\n    }\r\n\r\n    // Maksut - työnantaja\r\n    const employerTotalsDef = columnDefs[4].children[1];\r\n    for (const def of employerTotalsDef.children) {\r\n      if (totalFields.indexOf(def.field) < 0) {\r\n        preset.push(this.createPresetCol(def.field, true));\r\n      }\r\n    }\r\n\r\n    // Maksut - yhteensä\r\n    const totalsDef = columnDefs[4].children[2];\r\n    for (const def of totalsDef.children) {\r\n      if (totalFields.indexOf(def.field) < 0) {\r\n        preset.push(this.createPresetCol(def.field, true));\r\n      }\r\n    }\r\n\r\n    return preset;\r\n  }\r\n\r\n  private createPresetCol(colId: string, hide: boolean, rowGroup = false, aggFunc: string = null) {\r\n    return {\r\n      aggFunc,\r\n      colId,\r\n      flex: 1,\r\n      hide,\r\n      pinned: null,\r\n      pivot: false,\r\n      pivotIndex: null,\r\n      rowGroup,\r\n      rowGroupIndex: null,\r\n      sort: null,\r\n      sortIndex: null,\r\n      width: 200,\r\n    };\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { AccountingRowReportData, Datasets, Dates, LegalEntityType, Numeric, PeriodType, PeriodDateKind, Reports } from \"@salaxy/core\";\r\n\r\nimport { SessionService, UiHelpers } from \"../../services\";\r\nimport { ConfigurableGridReportControllerBase } from \"./ConfigurableGridReportControllerBase\";\r\n\r\n/**\r\n * Controller for accounting row based reports.\r\n */\r\nexport class AccountingRowReportController extends ConfigurableGridReportControllerBase<AccountingRowReportData> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Datasets\", \"UiHelpers\", \"SessionService\", \"Reports\", \"$timeout\"];\r\n\r\n  /** Usecase uri for report templates */\r\n  public usecaseUri = \"palkkaus.fi/reports/accountingRowReport\";\r\n\r\n  /** Current grid options. */\r\n  public gridOptions: any = {\r\n    statusBar: {\r\n      statusPanels: [\r\n        { statusPanel: \"agTotalAndFilteredRowCountComponent\", key: \"totalAndFilter\", align: \"left\" },\r\n        { statusPanel: \"agSelectedRowCountComponent\", align: \"left\" },\r\n        { statusPanel: \"agAggregationComponent\", align: \"right\" }\r\n      ]\r\n    },\r\n    enableMultiRowDragging: true,\r\n    rowGroupPanelShow: \"always\",\r\n    pivotPanelShow: \"always\",\r\n    enableCharts: true,\r\n    enableRangeSelection: true,\r\n    pivotMode: true,\r\n    suppressExpandablePivotGroups: true,\r\n\r\n    defaultExportParams: {\r\n      columnGroups: true,\r\n      headerRowHeight: 30,\r\n      rowHeight: 22,\r\n      fontSize: 14,\r\n    },\r\n    defaultColDef: {\r\n      flex: 1,\r\n      minWidth: 200,\r\n      sortable: true,\r\n      filter: true,\r\n      resizable: true,\r\n      floatingFilter: true,\r\n    },\r\n    sideBar: { toolPanels: [\"columns\", \"filters\"] },\r\n    rowData: [],\r\n  };\r\n\r\n  /** ID for the element containing grid. */\r\n  public gridElmentId = \"#dataGrid\";\r\n\r\n  /** Default templates */\r\n  public defaultTemplates = [\r\n    {\r\n      id: \"holidays\",\r\n      owner: null,\r\n      label: \"Lomapalkkaraportti\",\r\n      config: null,\r\n      isReadOnly: true,\r\n      avatar: {\r\n        initials: \"LPR\",\r\n        entityType: LegalEntityType.Company,\r\n        color: \"#009fd8\"\r\n      }\r\n    },\r\n    {\r\n      id: \"plain\",\r\n      owner: null,\r\n      label: \"Kaikki sarakkeet\",\r\n      config: { isPivotMode: false},\r\n      isReadOnly: true,\r\n      avatar: {\r\n        initials: \"Kasa\",\r\n        entityType: LegalEntityType.Company,\r\n        color: \"#009fd8\"\r\n      }\r\n    }\r\n  ];\r\n\r\n  private entryCodeGroups = {\r\n    totalType: \"Yhteensä\",\r\n    incomeType: \"Tulolaji\"\r\n  };\r\n  private entryCodes = {\r\n    totalPensionWorker: \"Työntekijöiden TyEL-maksut\",\r\n    totalPensionEmployer: \"Työnantajan TyEL-maksu\",\r\n    totalPension: \"TyEL-maksut\",\r\n    totalUnemploymentWorker: \"Työntekijöiden työttömyysvakuutusmaksut\",\r\n    totalUnemploymentEmployer: \"Työnantajan työttömyysvakuutusmaksu\",\r\n    totalUnemployment: \"Työttömyysvakuutusmaksut\",\r\n    totalSocialSecurityEmployer: \"Työnantajan sairausvakuutusmaksu\",\r\n    totalSocialSecurityWorker: \"Työntekijältä erikseen perittävä sairausvakuutusmaksu\",\r\n    totalTax: \"Ennakonpidätykset\",\r\n    totalPalkkaus: \"Palkkaus.fi-palkkio\",\r\n    totalWorkerPayment: \"Työntekijän nettopalkka ja kulukorvaukset\",\r\n    totalPayment: \"Maksettu asiakasvaratilille\",\r\n    totalAccidentInsurance: \"Työtapaturma- ja ammattitautivakuutusmaksut\",\r\n    totalGroupLifeInsurance: \"Ryhmähenkivakuutusmaksut\",\r\n    totalAccruedHolidayPay: \"Kertyneet lomapalkat\",\r\n    totalAccruedHolidaySocialSecurity: \"Kertyneet lomapalkkojen sairausvakuutusmaksut\",\r\n    totalAccruedHolidayPension: \"Kertyneet lomapalkkojen TyEL-maksut\",\r\n    totalAccruedHolidayUnemployment: \"Kertyneet lomapalkkojen työttömyysvakuutusmaksut (TVR)\",\r\n    totalPaidHolidaySalary: \"Maksetut loma-ajan palkat\",\r\n    totalPaidHolidayBonus: \"Maksetut lomarahat\",\r\n    totalPaidHolidayCompensation: \"Maksetut lomakorvaukset\",\r\n    totalPaidHolidaySocialSecurity: \"Maksetut lomapalkkojen sairausvakuutusmaksut\",\r\n    totalPaidHolidayPension: \"Maksetut lomapalkkojen TyEL-maksut\",\r\n    totalPaidHolidayUnemployment: \"Maksetut lomapalkkojen työttömyysvakuutusmaksut (TVR)\",\r\n    totalGrossSalary: \"Bruttopalkka\",\r\n  };\r\n\r\n  constructor(datasets: Datasets, uiHelpers: UiHelpers, sessionService: SessionService, private reports: Reports,  private $timeout: angular.ITimeoutService) {\r\n    super(datasets, uiHelpers, sessionService);\r\n  }\r\n\r\n\r\n  /**\r\n   * Initialize controller values.\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /**\r\n   * Processes and sets the data.\r\n   */\r\n  public setData(result: AccountingRowReportData) {\r\n    this.data = result;\r\n\r\n    const sortingDateComparator = (a, b) => {\r\n      if (!a || !b) {\r\n        return a === b ? 0 : a ? 1 : -1;\r\n      }\r\n      const mA = Dates.asDate(a);\r\n      const mB = Dates.asDate(b);\r\n      return mA === mB ? 0 : mA > mB ? 1 : -1;\r\n    };\r\n    const filterDateComparator = (a, b) => sortingDateComparator(b, a);\r\n\r\n    const columnDefs = [];\r\n\r\n    columnDefs.push(...[\r\n      {\r\n        field: \"message\",\r\n        headerName: \"Selite\",\r\n        filter: \"agMultiColumnFilter\",\r\n        enablePivot: true,\r\n        enableRowGroup: true,\r\n      },\r\n      {\r\n        field: \"entryDate\",\r\n        headerName: \"Päiväys\",\r\n        valueFormatter: params => Dates.getFormattedDate(params.value),\r\n        type: [\"rightAligned\"],\r\n        filter: \"agDateColumnFilter\",\r\n        comparator: sortingDateComparator,\r\n        filterParams: { comparator: filterDateComparator, },\r\n        enablePivot: true,\r\n        enableRowGroup: true,\r\n      },\r\n      {\r\n        field: \"amount\",\r\n        headerName: \"Summa\",\r\n        enableValue: true,\r\n        type: [\"numericColumn\"],\r\n        valueFormatter: params => Numeric.formatNumber(params.value, 2),\r\n        filter: \"agNumberColumnFilter\",\r\n      },\r\n      {\r\n        field: \"dimension.workerName\",\r\n        headerName: \"Työntekijä\",\r\n        filter: \"agMultiColumnFilter\",\r\n        enablePivot: true,\r\n        enableRowGroup: true,\r\n      },\r\n      /*\r\n      {\r\n        field: \"dimension.dimensions.costCenter\",\r\n        headerName: \"Kustannuspaikka\",\r\n        filter: \"agMultiColumnFilter\",\r\n        enablePivot: true,\r\n        enableRowGroup: true,\r\n      },\r\n      {\r\n        field: \"dimension.rowType\",\r\n        headerName: \"Laskelmarivin tyyppi\",\r\n        filter: \"agMultiColumnFilter\",\r\n        enablePivot: true,\r\n        enableRowGroup: true,\r\n      },\r\n      */\r\n      {\r\n        field: \"entryCodeGroup\",\r\n        headerName: \"Kirjanpitorivin tyyppi\",\r\n        filter: \"agMultiColumnFilter\",\r\n        enablePivot: true,\r\n        enableRowGroup: true,\r\n        valueGetter: params =>  this.getEntryCodeGroupName(params?.data?.entryCodeGroup)\r\n      },\r\n      {\r\n        field: \"entryCode\",\r\n        headerName: \"Kirjanpitorivin tunniste\",\r\n        filter: \"agMultiColumnFilter\",\r\n        enablePivot: true,\r\n        enableRowGroup: true,\r\n        valueGetter: params =>  this.getEntryCodeName(params?.data?.entryCode)\r\n      },\r\n    ]);\r\n\r\n    // Create presets if not created.\r\n    const holidays = this.getTemplate(\"holidays\");\r\n    holidays.config = holidays.config ?? {\r\n      isPivotMode: true,\r\n      columnState: this.createHolidaysPreset(columnDefs),\r\n      filterModel: {\r\n        entryCodeGroup: {\r\n          filterType: \"multi\",\r\n          filterModels: [\r\n            null,\r\n            {\r\n              values: [\r\n                this.entryCodeGroups[\"totalType\"],\r\n              ],\r\n              filterType: \"set\"\r\n            }\r\n          ]\r\n        },\r\n        entryCode: {\r\n          filterType: \"multi\",\r\n          filterModels: [\r\n            null,\r\n            {\r\n              values: [\r\n                this.entryCodes[\"totalGrossSalary\"],\r\n                this.entryCodes[\"totalAccruedHolidayPay\"],\r\n                this.entryCodes[\"totalAccruedHolidaySocialSecurity\"],\r\n                this.entryCodes[\"totalAccruedHolidayPension\"],\r\n                this.entryCodes[\"totalAccruedHolidayUnemployment\"],\r\n                this.entryCodes[\"totalPaidHolidaySalary\"],\r\n                this.entryCodes[\"totalPaidHolidayBonus\"],\r\n                this.entryCodes[\"totalPaidHolidayCompensation\"],\r\n                this.entryCodes[\"totalPaidHolidaySocialSecurity\"],\r\n                this.entryCodes[\"totalPaidHolidayPension\"],\r\n                this.entryCodes[\"totalPaidHolidayUnemployment\"],\r\n              ],\r\n              filterType: \"set\"\r\n            }\r\n          ]\r\n        }\r\n      },\r\n    };\r\n    // create the grid passing in the div to use together with the columns & data we want to use\r\n    this.$timeout(() => {\r\n      const filterModel = this.gridOptions.api.getFilterModel();\r\n      this.gridOptions.api.setFilterModel(null);\r\n      this.gridOptions.api.setRowData(this.data.rows);\r\n      this.gridOptions.api.setColumnDefs(columnDefs);\r\n      this.gridOptions.api.setFilterModel(filterModel);\r\n      this.selectTemplate(this.templateId ?? \"holidays\");\r\n    });\r\n  }\r\n\r\n  private getEntryCodeGroupName(id: string) {\r\n    const name =  this.entryCodeGroups[\"\" + id];\r\n    return name;\r\n  }\r\n\r\n  private getEntryCodeName(id: string) {\r\n    const name =  this.entryCodes[\"\" + id];\r\n    return name;\r\n  }\r\n\r\n  /**\r\n   * Gets the monthly / quarterly / yearly accounitng row data for the current account.\r\n   * @param refDate Reference date for the period. Please note that even if the date is not the first day of the given period, the entire period is returned.\r\n   * @param periodType Month, quarter, year or a custom period. The custom period requires endDate. Default value is the month.\r\n   * @param endDate End date for the period. Required only for the custom period.\r\n   * @param periodDateKind Period date type: paid at date, salary date or work date.\r\n   * @param workers List of worker official ids.\r\n   * @returns A Promise with result data.\r\n   */\r\n  public queryDataForPeriod(refDate: string, periodType?: PeriodType | \"all\", endDate?: string, periodDateKind?: PeriodDateKind, workers?: string[]): Promise<AccountingRowReportData> {\r\n\r\n    if (periodType === \"all\") {\r\n      refDate = \"2010-01-01\";\r\n      endDate = \"2100-01-01\";\r\n      periodType = PeriodType.Custom;\r\n    }\r\n\r\n    return this.reports.getAccountingRowReportData(refDate,periodType,endDate,periodDateKind,workers);\r\n  }\r\n\r\n  /**\r\n   * Gets the accounting row data based on given set of calculations.\r\n   * @param calculationIds - Calculations that are the bases for the report.\r\n   * @returns A Promise with result data.\r\n   */\r\n  public queryDataForCalculationIds(calculationIds: string[]): Promise<AccountingRowReportData> {\r\n    return this.reports.getAccountingRowReportDataForCalculationIds(calculationIds);\r\n  }\r\n\r\n  private createHolidaysPreset(columnDefs: any) {\r\n    const preset = [];\r\n\r\n    for (const def of columnDefs) {\r\n      switch (def.field) {\r\n        case \"dimension.workerName\":\r\n          preset.push(this.createPresetCol(def.field, false, true));\r\n          break;\r\n        default:\r\n          preset.push(this.createPresetCol(def.field, true));\r\n          break;\r\n      }\r\n    }\r\n\r\n    preset.push(this.createPresetCol(\"amount\", false, false, \"sum\"));\r\n\r\n    preset.push(this.createPresetCol(\"entryCodeGroup\", false, false, null, true, 0));\r\n\r\n    preset.push(this.createPresetCol(\"entryCode\", false, false, null, true, 1));\r\n\r\n\r\n    return preset;\r\n  }\r\n\r\n  private createPresetCol(colId: string, hide: boolean, rowGroup = false, aggFunc: string = null, pivot = false, pivotIndex: number = null) {\r\n    return {\r\n      aggFunc,\r\n      colId,\r\n      flex: 1,\r\n      hide,\r\n      pinned: null,\r\n      pivot: pivot,\r\n      pivotIndex: pivotIndex,\r\n      rowGroup,\r\n      rowGroupIndex: null,\r\n      sort: null,\r\n      sortIndex: null,\r\n      width: 200,\r\n    };\r\n  }\r\n}\r\n","import angular from \"angular\";\r\nimport { PeriodType, Reports } from \"@salaxy/core\";\r\nimport { UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Handles user interaction for displaying summary report\r\n */\r\nexport class SummaryReportDisplayController implements angular.IController {\r\n  public static $inject = [\r\n    \"UiHelpers\",\r\n    \"Reports\"\r\n  ];\r\n  /**\r\n   * Creates a new instance of SummaryReportDisplayController\r\n   * @param uiHelpers - Salaxy ui helpers service.\r\n   */\r\n  constructor(\r\n    private uiHelpers: UiHelpers,\r\n    private reports: Reports\r\n\r\n  ) { }\r\n\r\n  /**\r\n   * Display Summary report\r\n   * @param refDate date\r\n   * @param type report type\r\n   */\r\n  public display(refDate: string, type: string): void {\r\n    const data = {\r\n      summaryReportData: null,\r\n      isLoading: true\r\n    };\r\n    this.reports.getSummaryReportData(refDate, this.getPeriodType(type)).then(summaryReportData => {\r\n      data.summaryReportData = summaryReportData;\r\n      data.isLoading = false;\r\n    });\r\n    this.uiHelpers.showDialog(\r\n      \"salaxy-components/modals/report/SummaryReport.html\",\r\n      null,\r\n      data,\r\n      null,\r\n      \"landscape\",\r\n      true);\r\n  }\r\n\r\n  private getPeriodType(reportType: string): PeriodType {\r\n    switch (reportType) {\r\n      case \"monthlyDetails\":\r\n        return PeriodType.Month;\r\n      case \"yearlyDetails\":\r\n        return PeriodType.Year;\r\n    }\r\n  }\r\n\r\n}","import angular from \"angular\";\r\nimport { SummaryReportData, Numeric, Translations, Language, Configs, Ajax } from \"@salaxy/core\";\r\nimport { SettingsService, UiHelpers, SessionService } from \"../../services\";\r\nimport {\r\n  SummaryMapper,\r\n  ReportData,\r\n  ReportOptions,\r\n  Templates,\r\n} from \"@salaxy/reports\";\r\n\r\n\r\n/**\r\n * Renders a summary report or a calculation summary report for the given calculation(s).\r\n * Uses Handlebars templates (@salaxy/reports).\r\n */\r\nexport class SummaryReportController implements angular.IController {\r\n  public data: SummaryReportData;\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Templates\", \"$sce\", \"SettingsService\", \"$timeout\", \"$http\", \"UiHelpers\", \"SessionService\", \"AjaxNg1\"];\r\n\r\n  /** Template for the report */\r\n  public templateName = \"summaryReport\";\r\n\r\n  /** Boolean indicating if the refresh is in progress. */\r\n  public refreshInprogress: boolean;\r\n\r\n  /**Selected report language */\r\n  public lang: Language;\r\n\r\n  private renderedData: SummaryReportData;\r\n\r\n  private renderedLang: string;\r\n\r\n  private htmlData: any;\r\n\r\n  private reportOptions: ReportOptions;\r\n\r\n  private reportTemplate = \"summaryReport\";\r\n\r\n  private reportData: ReportData<SummaryReportData> = {\r\n    headerFooter: {},\r\n    layout: {},\r\n    report: {},\r\n  };\r\n\r\n  private _reportLang: Language = Language.Default;\r\n\r\n\r\n\r\n  /**\r\n   * Creates a new CalcReportController\r\n   * @ignore\r\n   */\r\n  constructor(private templates: Templates,\r\n    private $sce: angular.ISCEService,\r\n    private settingsService: SettingsService,\r\n    private $timeout: angular.ITimeoutService,\r\n    private $http: angular.IHttpService,\r\n    private uiHelpers: UiHelpers,\r\n    private sessionService: SessionService,\r\n    private ajax: Ajax\r\n  ) { }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    this.sessionService.getReportLang().then((lang) => {\r\n      this.reportLang = lang;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Get _reportLang\r\n   */\r\n  public get reportLang() {\r\n    return this._reportLang;\r\n  }\r\n\r\n  /**\r\n   * Set _reportLang & lang\r\n   */\r\n  public set reportLang(lang: Language) {\r\n    this._reportLang = lang;\r\n    if (lang !== Language.Default) {\r\n      this.lang = this._reportLang;\r\n    } else {\r\n      this.sessionService.getReportLang().then(lang => {\r\n        this.lang = lang;\r\n      });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Return languge text to ui\r\n   */\r\n  public get languageText() {\r\n    switch (this.reportLang) {\r\n      case Language.Fi:\r\n        return \"SALAXY.ENUM.Language.fi.label\";\r\n      case Language.En:\r\n        return \"SALAXY.ENUM.Language.en.label\";\r\n      case Language.Sv:\r\n        return \"SALAXY.ENUM.Language.sv.label\";\r\n      case Language.Default:\r\n        return \"SALAXY.NG1.CalcReportsComponent.reportLanguageCompany\";\r\n    }\r\n  }\r\n\r\n  /** Bindable and trusted html. */\r\n  public get html(): any {\r\n    if (!this.data) {\r\n      this.renderedData = null;\r\n      this.renderedLang = null;\r\n    } else {\r\n      const summaryReportData = angular.copy(this.data);\r\n\r\n      if (!this.renderedData || !angular.equals(summaryReportData, this.renderedData)\r\n        || this.renderedLang !== this.lang) {\r\n        this.lang = this.lang === Language.Default ? Language.Fi : this.lang;\r\n        this.renderedData = angular.copy(summaryReportData);\r\n        this.renderedLang = this.lang;\r\n        this.refresh();\r\n      }\r\n    }\r\n    return this.htmlData;\r\n  }\r\n\r\n  private async refresh() {\r\n    if (this.refreshInprogress) {\r\n      return;\r\n    }\r\n    this.refreshInprogress = true;\r\n    this.settingsService.getReportOptions().then( async(options) => {\r\n      this.reportOptions = options;\r\n      const renderingLang = this.lang ?? Language.Fi;\r\n      await Translations.loadLanguage(renderingLang);\r\n      const reportOptions = this.getDefaultReportOptions(angular.copy(this.reportOptions));\r\n      this.reportData.headerFooter = SummaryMapper.getSummaryReportHeaderFooter(this.data, reportOptions, renderingLang);\r\n      this.reportData.report = SummaryMapper.getSummaryReport(this.data);\r\n      this.reportData.layout = SummaryMapper.getReportLayout(false, false);\r\n      const css = \"\";\r\n      this.reportData.layout.hasCustomCss = false;\r\n      this.reportData.layout.customCss = (css || \"\");\r\n      this.reportData.layout.margin = {\r\n        top: reportOptions.margin.top,\r\n        right: reportOptions.margin.right,\r\n        bottom: reportOptions.margin.bottom,\r\n        left: reportOptions.margin.left\r\n      };\r\n      const templates = new Templates();\r\n      this.reportData.headerHtml = this.reportOptions?.headerTemplate ? templates.getHtmlDynamic(this.reportOptions.headerTemplate, this.reportData.headerFooter, renderingLang) : \"\";\r\n      this.reportData.footerHtml = this.reportOptions?.headerTemplate ? templates.getHtmlDynamic(this.reportOptions.footerTemplate, this.reportData.headerFooter, renderingLang) : \"\";\r\n      this.htmlData = this.$sce.trustAsHtml(this.templates.getHtml(this.templateName, this.reportData, renderingLang));\r\n      this.refreshInprogress = false;\r\n      this.$timeout();\r\n    });\r\n  }\r\n  /**\r\n   * Shows a download dialog for the given summary report.\r\n   * @param inline - If true, the download link opens the pdf into a new web page.\r\n   */\r\n  public showDownloadDialog(inline = false) {\r\n    const url = `${Configs.current.reportServer}/pdf?id=&reportType=${encodeURIComponent(\"monthlyDetails\")}&template=${encodeURIComponent(this.reportTemplate)}&language=${encodeURIComponent(this.lang)}&disposition=inline&access_token=${this.ajax.getCurrentToken()}`;\r\n    this.handlePdfRequest(url, inline, this.data);\r\n  }\r\n\r\n  private getDefaultReportOptions(optionsInput?: ReportOptions): ReportOptions {\r\n    optionsInput = optionsInput || {};\r\n    optionsInput.margin = optionsInput.margin || {};\r\n    optionsInput.margin.top = Numeric.parseNumber(optionsInput.margin.top) || 30;\r\n    optionsInput.margin.right = Numeric.parseNumber(optionsInput.margin.right) || 10;\r\n    optionsInput.margin.bottom = Numeric.parseNumber(optionsInput.margin.bottom) || 40;\r\n    optionsInput.margin.left = Numeric.parseNumber(optionsInput.margin.left) || 10;\r\n    return optionsInput;\r\n  }\r\n\r\n  /**\r\n   * Handles pdf request\r\n   * @param url post url\r\n   * @param inline inline pdf\r\n   * @param data business object\r\n   */\r\n  private handlePdfRequest(url: string, inline: boolean, data: SummaryReportData): void {\r\n    this.$http.post(url, { object: data }, { responseType: \"blob\" }).then((response) => {\r\n      if (response.data) {\r\n        if (inline) {\r\n          this.uiHelpers.openFile(response.data as any);\r\n        } else {\r\n          this.uiHelpers.downloadFile(response.data as any, response.headers(\"content-disposition\").split(\";\")[1].split(\"filename\")[1].split(\"=\")[1].trim().replace(/\"/g, \"\"));\r\n        }\r\n      }\r\n    }, (error) => {\r\n      console.error(error);\r\n    });\r\n  }\r\n\r\n}\r\n\r\n","import angular from \"angular\";\r\nimport { AccountingData, PeriodType, Reports, PeriodDateKind } from \"@salaxy/core\";\r\nimport { UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Handles user interaction for displaying accounting report\r\n */\r\nexport class AccountingReportDisplayController implements angular.IController {\r\n  public static $inject = [\r\n    \"UiHelpers\",\r\n    \"Reports\"\r\n  ];\r\n  /**\r\n   * Creates a new instance of AccountingReportDisplayController\r\n   * @param uiHelpers - Salaxy ui helpers service.\r\n   */\r\n  constructor(\r\n    private uiHelpers: UiHelpers,\r\n    private reports: Reports\r\n\r\n  ) { }\r\n\r\n  /**\r\n   * Display accounting report\r\n   * @param refDate date\r\n   */\r\n  public display(refDate: string): void {\r\n    const getAccountingData = (target: string) => this.reports.getAccountingDataForPeriod(refDate, target ?? \"default\", PeriodType.Month, null, PeriodDateKind.PaidAtDate);\r\n    const data = {\r\n      accountingData: null,\r\n      isLoading: true,\r\n      reader: {\r\n        /**\r\n         * Function to read data into given array\r\n         * TODO: Should make interface for this or otherwise go-through.\r\n         */\r\n        // eslint-disable-next-line @typescript-eslint/no-unused-vars\r\n        read: (target: string, ruleSet: string, arr: AccountingData[], message: string): Promise<void> => {\r\n          if (data.accountingData) {\r\n            arr.push(data.accountingData);\r\n          }\r\n          return Promise.resolve();\r\n        },\r\n        /** Optional label for data export */\r\n        exportLabel: null,\r\n        /** Indicates if the export is not possible */\r\n        disabled: () => !data.accountingData,\r\n        /* Indicates if row is expandable */\r\n        showExpand: true,\r\n        /* Indicates if rows exists*/\r\n        hasRows: () => !data.accountingData?.ledgerAccounts\r\n      },\r\n      loadCurrent: (targetId) => {\r\n        data.isLoading = true;\r\n        getAccountingData(targetId).then(accountingData => {\r\n          data.accountingData = accountingData;\r\n          data.isLoading = false;\r\n        });\r\n      }\r\n    };\r\n    data.isLoading = true;\r\n    getAccountingData(null).then(accountingData => {\r\n      data.accountingData = accountingData;\r\n      data.isLoading = false;\r\n    });\r\n    this.uiHelpers.showDialog(\r\n      \"salaxy-components/modals/report/AccountingReport.html\",\r\n      null,\r\n      data,\r\n      null,\r\n      \"lg\",\r\n      true);\r\n  }\r\n}","import angular from \"angular\";\r\nimport { SummaryReportData, Numeric, Translations, Language, Configs, Ajax, WorkerSummaryReportData } from \"@salaxy/core\";\r\nimport { SettingsService, UiHelpers, SessionService } from \"../../services\";\r\nimport { WorkerSummaryMapper, ReportData, ReportOptions, Templates } from \"@salaxy/reports\";\r\n\r\n\r\n/**\r\n * Renders a worker summary report or a calculation summary report for the given calculation(s).\r\n * Uses Handlebars templates (@salaxy/reports).\r\n */\r\nexport class WorkerSummaryReportController implements angular.IController {\r\n  public data: WorkerSummaryReportData;\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Templates\", \"$sce\", \"SettingsService\", \"$timeout\", \"$http\", \"UiHelpers\", \"SessionService\", \"AjaxNg1\"];\r\n\r\n  /** Template for the report */\r\n  public templateName = \"workerSummaryReport\";\r\n\r\n  /** Boolean indicating if the refresh is in progress. */\r\n  public refreshInprogress: boolean;\r\n\r\n  /**Selected report language */\r\n  public lang: Language;\r\n\r\n  private renderedData: WorkerSummaryReportData;\r\n\r\n  private renderedLang: string;\r\n\r\n  private htmlData: any;\r\n\r\n  private reportOptions: ReportOptions;\r\n\r\n  private reportTemplate = \"workerSummaryReport\";\r\n\r\n  private reportData: ReportData<WorkerSummaryReportData> = {\r\n    headerFooter: {},\r\n    layout: {},\r\n    report: {},\r\n  };\r\n\r\n  private _reportLang: Language = Language.Default;\r\n\r\n\r\n\r\n  /**\r\n   * Creates a new CalcReportController\r\n   * @ignore\r\n   */\r\n  constructor(private templates: Templates,\r\n    private $sce: angular.ISCEService,\r\n    private settingsService: SettingsService,\r\n    private $timeout: angular.ITimeoutService,\r\n    private $http: angular.IHttpService,\r\n    private uiHelpers: UiHelpers,\r\n    private sessionService: SessionService,\r\n    private ajax: Ajax\r\n  ) { }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    this.sessionService.getReportLang().then((lang) => {\r\n      this.reportLang = lang;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Get _reportLang\r\n   */\r\n  public get reportLang() {\r\n    return this._reportLang;\r\n  }\r\n\r\n  /**\r\n   * Set _reportLang & lang\r\n   */\r\n  public set reportLang(lang: Language) {\r\n    this._reportLang = lang;\r\n    if (lang !== Language.Default) {\r\n      this.lang = this._reportLang;\r\n    } else {\r\n      this.sessionService.getReportLang().then(lang => {\r\n        this.lang = lang;\r\n      });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Return languge text to ui\r\n   */\r\n  public get languageText() {\r\n    switch (this.reportLang) {\r\n      case Language.Fi:\r\n        return \"SALAXY.ENUM.Language.fi.label\";\r\n      case Language.En:\r\n        return \"SALAXY.ENUM.Language.en.label\";\r\n      case Language.Sv:\r\n        return \"SALAXY.ENUM.Language.sv.label\";\r\n      case Language.Default:\r\n        return \"SALAXY.NG1.CalcReportsComponent.reportLanguageCompany\";\r\n    }\r\n  }\r\n\r\n  /** Bindable and trusted html. */\r\n  public get html(): any {\r\n    if (!this.data) {\r\n      this.renderedData = null;\r\n      this.renderedLang = null;\r\n    } else {\r\n      const workerSummaryReportData = angular.copy(this.data);\r\n\r\n      if (!this.renderedData || !angular.equals(workerSummaryReportData, this.renderedData)\r\n        || this.renderedLang !== this.lang) {\r\n        this.lang = this.lang === Language.Default ? Language.Fi : this.lang;\r\n        this.renderedData = angular.copy(workerSummaryReportData);\r\n        this.renderedLang = this.lang;\r\n        this.refresh();\r\n      }\r\n    }\r\n    return this.htmlData;\r\n  }\r\n\r\n  private async refresh() {\r\n    if (this.refreshInprogress) {\r\n      return;\r\n    }\r\n    this.refreshInprogress = true;\r\n    this.settingsService.getReportOptions().then(async (options) => {\r\n      this.reportOptions = options;\r\n      const renderingLang = this.lang ?? Language.Fi;\r\n      await Translations.loadLanguage(renderingLang);\r\n      const reportOptions = this.getDefaultReportOptions(angular.copy(this.reportOptions));\r\n      this.reportData.headerFooter = WorkerSummaryMapper.getWorkerSummaryReportHeaderFooter(this.data, reportOptions, renderingLang);\r\n      this.reportData.report = WorkerSummaryMapper.getWorkerSummaryReport(this.data, renderingLang);\r\n      this.reportData.layout = WorkerSummaryMapper.getReportLayout(true, false);\r\n      const css = \"\";\r\n      this.reportData.layout.hasCustomCss = false;\r\n      this.reportData.layout.customCss = (css || \"\");\r\n      this.reportData.layout.margin = {\r\n        top: reportOptions.margin.top,\r\n        right: reportOptions.margin.right,\r\n        bottom: reportOptions.margin.bottom,\r\n        left: reportOptions.margin.left\r\n      };\r\n      const templates = new Templates();\r\n      this.reportData.headerHtml = this.reportOptions?.headerTemplate ? templates.getHtmlDynamic(this.reportOptions.headerTemplate, this.reportData.headerFooter, renderingLang) : \"\";\r\n      this.reportData.footerHtml = this.reportOptions?.headerTemplate ? templates.getHtmlDynamic(this.reportOptions.footerTemplate, this.reportData.headerFooter, renderingLang) : \"\";\r\n      this.htmlData = this.$sce.trustAsHtml(this.templates.getHtml(this.templateName, this.reportData, renderingLang));\r\n      this.refreshInprogress = false;\r\n      this.$timeout();\r\n    });\r\n  }\r\n  /**\r\n   * Shows a download dialog for the given summary report.\r\n   * @param inline - If true, the download link opens the pdf into a new web page.\r\n   */\r\n  public showDownloadDialog(inline = false) {\r\n    const url = `${Configs.current.reportServer}/pdf?id=&reportType=${encodeURIComponent(\"yearlyWorkerSummary\")}&template=${encodeURIComponent(this.reportTemplate)}&language=${encodeURIComponent(this.lang)}&disposition=inline&access_token=${this.ajax.getCurrentToken()}`;\r\n    this.handlePdfRequest(url, inline, this.data);\r\n  }\r\n\r\n  private getDefaultReportOptions(optionsInput?: ReportOptions): ReportOptions {\r\n    optionsInput = optionsInput || {};\r\n    optionsInput.margin = optionsInput.margin || {};\r\n    optionsInput.margin.top = Numeric.parseNumber(optionsInput.margin.top) || 30;\r\n    optionsInput.margin.right = Numeric.parseNumber(optionsInput.margin.right) || 10;\r\n    optionsInput.margin.bottom = Numeric.parseNumber(optionsInput.margin.bottom) || 40;\r\n    optionsInput.margin.left = Numeric.parseNumber(optionsInput.margin.left) || 10;\r\n    return optionsInput;\r\n  }\r\n\r\n  /**\r\n   * Handles pdf request\r\n   * @param url post url\r\n   * @param inline inline pdf\r\n   * @param data business object\r\n   */\r\n  private handlePdfRequest(url: string, inline: boolean, data: SummaryReportData): void {\r\n    this.$http.post(url, { object: data }, { responseType: \"blob\" }).then((response) => {\r\n      if (response.data) {\r\n        if (inline) {\r\n          this.uiHelpers.openFile(response.data as any);\r\n        } else {\r\n          this.uiHelpers.downloadFile(response.data as any, response.headers(\"content-disposition\").split(\";\")[1].split(\"filename\")[1].split(\"=\")[1].trim().replace(/\"/g, \"\"));\r\n        }\r\n      }\r\n    }, (error) => {\r\n      console.error(error);\r\n    });\r\n  }\r\n\r\n}\r\n\r\n","import angular from \"angular\";\r\nimport { PeriodDateKind, PeriodType, Reports } from \"@salaxy/core\";\r\nimport { UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Handles user interaction for displaying worker summary report\r\n */\r\nexport class WorkerSummaryReportDisplayController implements angular.IController {\r\n  public static $inject = [\r\n    \"UiHelpers\",\r\n    \"Reports\"\r\n  ];\r\n  /**\r\n   * Creates a new instance of WorkerSummaryReportDisplayController\r\n   * @param uiHelpers - Salaxy ui helpers service.\r\n   */\r\n  constructor(\r\n    private uiHelpers: UiHelpers,\r\n    private reports: Reports\r\n\r\n  ) { }\r\n\r\n  /**\r\n   * Parses workerId from report url\r\n   * @param reportUrl url to be parsed\r\n   * @returns workerId\r\n   */\r\n  public parseWorkerID(reportUrl: string) {\r\n    const regex = new RegExp(\"[?&]\" + \"id\" + \"(=([^&#]*)|&|#|$)\");\r\n    const results = regex.exec(reportUrl);\r\n    return results[2];\r\n  }\r\n\r\n  /**\r\n   * Query WorkerSummaryReportData and display it in dialog\r\n   * @param refDate date\r\n   */\r\n  public display(refDate: string, workerId: string, employerId: string): void {\r\n    const data = {\r\n      workerSummaryReportData: null,\r\n      isLoading: true\r\n    };\r\n    // Parsing id from url because listing does not provide workerID yet\r\n    this.reports.getWorkerSummaryReportData(refDate, workerId, employerId, PeriodType.Year, null, PeriodDateKind.SalaryDate ).then(workerSummaryReportData => {\r\n      data.workerSummaryReportData = workerSummaryReportData;\r\n      data.isLoading = false;\r\n    });\r\n    this.uiHelpers.showDialog(\r\n      \"salaxy-components/modals/report/WorkerSummaryReport.html\",\r\n      null,\r\n      data,\r\n      null,\r\n      \"landscape\",\r\n      true);\r\n  }\r\n}","import angular from \"angular\";\r\n\r\nimport {\r\n  Dates,\r\n  Reports,\r\n  Avatar,\r\n  Translations,\r\n  Employments,\r\n  EnumerationsLogic,\r\n  ODataQueryOptions,\r\n  EmploymentListItem,\r\n  HolidaysLogic,\r\n  HolidayCode,\r\n  HolidayCalculationDTO,\r\n  AccountingHolidayPayDebtReportDataYear,\r\n  AccountingHolidayPayDebtReportData,\r\n  Numeric,\r\n  HolidayYears,\r\n  Arrays,\r\n} from \"@salaxy/core\";\r\nimport { UiHelpers, ExcelHelpers, UiCrudHelpers } from \"../../services\";\r\n\r\n\r\n/**\r\n * Component for displaying holiday report.\r\n */\r\nexport class HolidayReportController implements angular.IController {\r\n\r\n\r\n  /** Ref date for the report. */\r\n  public refDate = Dates.getToday();\r\n\r\n  /** Current holiday years in the result. */\r\n  public years: string[] = [];\r\n\r\n  /** Current selected year. */\r\n  public year: string | undefined;\r\n\r\n  /** Result rows */\r\n  public resultRows: ResultRow[] = [];\r\n\r\n  /** Total holiday calculation */\r\n  public holidayCalc: {[key: string]: HolidayCalculationDTO };\r\n\r\n  /** Total of totals. */\r\n  public holidayCalcTotal: {[key: string]: number };\r\n\r\n  /**\r\n   * Helper flag for UI. Indicates whether the debt has been queried.\r\n   */\r\n  public hasQueryedDebt = false;\r\n\r\n  private data: AccountingHolidayPayDebtReportData;\r\n\r\n  private employmentListItems: EmploymentListItem[] = [];\r\n\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"HolidayYears\",\r\n    \"Reports\",\r\n    \"UiHelpers\",\r\n    \"Employments\",\r\n    \"UiCrudHelpers\",\r\n  ];\r\n\r\n  constructor(private holidayYears: HolidayYears, private reports: Reports, private uiHelpers: UiHelpers, private employments: Employments, private uiCrudHelpers: UiCrudHelpers,) {\r\n  }\r\n\r\n  /** Controller initialization */\r\n  public $onInit() {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    this.loadEmployments().then( employments => {\r\n      this.employmentListItems = employments;\r\n      this.query();\r\n      loading.dismiss();\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shows an edit dialog for the employment.\r\n   * @param row Row that contains field employmentId (Identifier for the employment).\r\n   * @param row.employmentId The row must contain the employment identifier.\r\n   */\r\n  public showEditEmploymentDialog(row: ResultRow ): void {\r\n    if (!row.employment?.id) {\r\n      console.error(\"EmploymentId is missing\", row);\r\n      return;\r\n    }\r\n    this.uiCrudHelpers.openEditEmploymentDialog(row.employment?.id, \"default\", \"holidays\");\r\n  }\r\n\r\n  /** Query Holiday year data. */\r\n  public query(queryDebt = false): Promise<AccountingHolidayPayDebtReportData> {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n\r\n    const apiQuery = () : Promise<AccountingHolidayPayDebtReportData> => {\r\n      if (queryDebt) {\r\n        return this.reports.getAccountingHolidayPayDebtReportData(this.refDate);\r\n      }\r\n      else {\r\n        return this.holidayYears.getForAllYears().then( (data) => ({\r\n            holidayCalc: {\r\n              totalAccruedHolidayPay : 0,\r\n              totalAccruedHolidayBonus: 0,\r\n              totalAccruedHolidaySocialSecurity: 0,\r\n              totalAccruedHolidayPension: 0,\r\n              totalAccruedHolidayUnemployment: 0,\r\n              totalAccruedHolidayAccidentInsurance: 0,\r\n              totalAccruedHolidayGroupLifeInsurance: 0,\r\n            },\r\n            holidayYears: data.map( (year) => ({\r\n              holidayYear: year,\r\n              holidayCalc: {}\r\n            })),\r\n          }));\r\n      }\r\n    };\r\n\r\n    return  apiQuery().then(data => {\r\n      this.data = data;\r\n      this.holidayCalc = {};\r\n      this.holidayCalc[\"total\"] = data.holidayCalc;\r\n      this.holidayCalcTotal = {};\r\n      this.holidayCalcTotal[\"total\"] = Numeric.round(\r\n        (data.holidayCalc?.totalAccruedHolidayPay ?? 0) +\r\n        (data.holidayCalc?.totalAccruedHolidayBonus  ?? 0) +\r\n        (data.holidayCalc?.totalAccruedHolidaySocialSecurity  ?? 0) +\r\n        (data.holidayCalc?.totalAccruedHolidayPension  ?? 0) +\r\n        (data.holidayCalc?.totalAccruedHolidayUnemployment  ?? 0) +\r\n        (data.holidayCalc?.totalAccruedHolidayAccidentInsurance  ?? 0) +\r\n        (data.holidayCalc?.totalAccruedHolidayGroupLifeInsurance  ?? 0), 2);\r\n      this.resultRows = [];\r\n      this.years = [];\r\n      this.year = undefined;\r\n      this.data.holidayYears.forEach( (yearData) => {\r\n        const resultRow: ResultRow = {\r\n          employment: this.employmentListItems.find(x => x.id === yearData.holidayYear?.employmentId),\r\n          data: yearData,\r\n          holidayYearReportRow: this.getBlankHolidayYearReportRow(),\r\n        };\r\n        this.resultRows.push(resultRow);\r\n        if (this.years.indexOf(\"\" +yearData.holidayYear.year) < 0) {\r\n          this.years.push(\"\" +yearData.holidayYear.year);\r\n        }\r\n      });\r\n      this.years.sort();\r\n      this.years.reverse();\r\n      this.year = this.years.length > 0 ? this.years[0]: undefined;\r\n      for (const year of this.years) {\r\n        const yearData = this.data.holidayYears.filter(x => x.holidayYear.year == Number.parseInt(year));\r\n        const yearCalc = {\r\n            totalAccruedHolidayPay: Numeric.round(Arrays.sum( yearData, (x) => x.holidayCalc?.totalAccruedHolidayPay ?? 0), 2),\r\n            totalAccruedHolidayBonus: Numeric.round(Arrays.sum( yearData, (x) => x.holidayCalc?.totalAccruedHolidayBonus ?? 0), 2),\r\n            totalAccruedHolidaySocialSecurity: Numeric.round(Arrays.sum( yearData, (x) => x.holidayCalc?.totalAccruedHolidaySocialSecurity ?? 0), 2),\r\n            totalAccruedHolidayPension: Numeric.round(Arrays.sum( yearData, (x) => x.holidayCalc?.totalAccruedHolidayPension ?? 0), 2),\r\n            totalAccruedHolidayUnemployment: Numeric.round(Arrays.sum( yearData, (x) => x.holidayCalc?.totalAccruedHolidayUnemployment ?? 0), 2),\r\n            totalAccruedHolidayAccidentInsurance: Numeric.round(Arrays.sum( yearData, (x) => x.holidayCalc?.totalAccruedHolidayAccidentInsurance ?? 0), 2),\r\n            totalAccruedHolidayGroupLifeInsurance: Numeric.round(Arrays.sum( yearData, (x) => x.holidayCalc?.totalAccruedHolidayGroupLifeInsurance ?? 0), 2),\r\n          };\r\n        this.holidayCalc[year] = yearCalc;\r\n        this.holidayCalcTotal[year] = Numeric.round(\r\n          (yearCalc.totalAccruedHolidayPay ?? 0) +\r\n          (yearCalc.totalAccruedHolidayBonus  ?? 0) +\r\n          (yearCalc.totalAccruedHolidayPension  ?? 0) +\r\n          (yearCalc.totalAccruedHolidayUnemployment  ?? 0) +\r\n          (yearCalc.totalAccruedHolidayAccidentInsurance  ?? 0) +\r\n          (yearCalc.totalAccruedHolidayGroupLifeInsurance  ?? 0), 2);\r\n      }\r\n\r\n      this.createHolidayYearReportRows();\r\n      if(queryDebt) {\r\n        this.hasQueryedDebt = true;\r\n      }\r\n\r\n      loading.dismiss();\r\n      return data;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Export totalRows to excel\r\n   */\r\n   public exportToExcel(){\r\n\r\n    const year = Number.parseInt(this.year ?? \"0\");\r\n    if (year === 0) {\r\n      return;\r\n    }\r\n\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    const tableData = [];\r\n    const headers = [\r\n      Translations.get(\"SALAXY.NG1_Other.Roles.worker\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.table.startDate\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.table.endDate\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.table.employment\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.table.salary\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.table.holidayCode\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.table.periodDefaultAccrual\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.table.holidayPayCalculation\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.startSaldo\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.total\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.paid\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.available\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.holidaySalary\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.holidayCompensation\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.paidBonus\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.availableBonus\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.holidayBonus\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.holidayPayDailySalary\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.totalAccruedHolidayPay\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.totalAccruedHolidayBonus\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.totalAccruedHolidaySocialSecurity\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.totalAccruedHolidayPension\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.totalAccruedHolidayUnemployment\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.totalAccruedHolidayAccidentInsurance\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.totalAccruedHolidayGroupLifeInsurance\"),\r\n      Translations.get(\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.totalAccruedHolidayTotal\")\r\n    ];\r\n    tableData.push(headers);\r\n    const rowData = this.resultRows.filter(x => x.data.holidayYear.year == year).map(x => {\r\n      const row = x.holidayYearReportRow;\r\n      return [\r\n        row.workerAvatar.displayName,\r\n        row.startDate = Dates.format(row.startDate),\r\n        row.endDate = Dates.format(row.endDate),\r\n        row.employmentType,\r\n        row.grossSalary,\r\n        row.holidayCode,\r\n        row.periodDefaultAccrual,\r\n        row.holidayPayCalculation,\r\n        row.startSaldo,\r\n        row.total,\r\n        row.paid,\r\n        row.available,\r\n        row.holidaySalary,\r\n        row.holidayCompensation,\r\n        row.paidBonus,\r\n        row.availableBonus,\r\n        row.holidayBonus,\r\n        row.holidayPayDailySalary,\r\n        row.totalAccruedHolidayPay,\r\n        row.totalAccruedHolidayBonus,\r\n        row.totalAccruedHolidaySocialSecurity,\r\n        row.totalAccruedHolidayPension,\r\n        row.totalAccruedHolidayUnemployment,\r\n        row.totalAccruedHolidayAccidentInsurance,\r\n        row.totalAccruedHolidayGroupLifeInsurance,\r\n        row.totalAccruedHolidayTotal\r\n      ];\r\n    });\r\n    tableData.push(...rowData);\r\n\r\n    if (tableData.length> 0) {\r\n      ExcelHelpers.export(tableData, `holidayYear-${year}`).then(() => {\r\n        loading.dismiss();\r\n      });\r\n    }\r\n    else\r\n    {\r\n      loading.dismiss();\r\n    }\r\n  }\r\n\r\n  private async loadEmployments(): Promise<EmploymentListItem[]> {\r\n    const items: any[] = [];\r\n    const loadItems = (nextPageLink: string = null): Promise<string> => {\r\n      let options: ODataQueryOptions = null;\r\n      const queryString = nextPageLink?.indexOf(\"?\") ?? -1;\r\n      if (queryString >= 0) {\r\n        const searchParams = new URLSearchParams(nextPageLink.substr(queryString));\r\n        if (searchParams.get(\"$skip\")) {\r\n          options = { $skip:  Number(searchParams.get(\"$skip\"))};\r\n        }\r\n      }\r\n      return this.employments.getOData(options).then((data) => {\r\n        items.push(...data.items);\r\n        return data.nextPageLink ? loadItems(data.nextPageLink) : null;\r\n      });\r\n    };\r\n\r\n    return loadItems().then(() => {\r\n      return items;\r\n    });\r\n\r\n  }\r\n\r\n  private createHolidayYearReportRows(): void {\r\n    this.resultRows.forEach(resultRow => {\r\n      resultRow.holidayYearReportRow.workerAvatar = resultRow.employment?.otherPartyInfo?.avatar;\r\n      resultRow.holidayYearReportRow.workerId = resultRow.employment?.otherPartyInfo?.avatar?.id;\r\n      resultRow.holidayYearReportRow.employmentId = resultRow.employment?.id;\r\n      resultRow.holidayYearReportRow.startDate = resultRow.employment?.data?.startDate;\r\n      resultRow.holidayYearReportRow.endDate = resultRow.employment?.data?.endDate;\r\n      resultRow.holidayYearReportRow.employmentType = EnumerationsLogic.getEnumLabel(\"EmploymentRelationType\", resultRow.employment?.data?.type) === \"#err EmploymentRelationType.NoEnumValue\" ? \"-\" : EnumerationsLogic.getEnumLabel(\"EmploymentRelationType\", resultRow.employment?.data?.type);\r\n      resultRow.holidayYearReportRow.grossSalary =  Numeric.round(resultRow.employment?.grossSalary ?? 0, 2);\r\n      resultRow.holidayYearReportRow.holidayCode = (resultRow.data.holidayYear.spec.code ?? HolidayCode.Undefined) == HolidayCode.Undefined ? \"\" : EnumerationsLogic.getEnumLabel(\"HolidayCode\", resultRow.data.holidayYear.spec.code);\r\n      resultRow.holidayYearReportRow.periodDefaultAccrual = (resultRow.data.holidayYear.spec.code == HolidayCode.Permanent14Days || resultRow.data.holidayYear.spec.code == HolidayCode.Permanent35Hours || resultRow.data.holidayYear.spec.code == HolidayCode.TemporaryTimeOff) ? resultRow.data.holidayYear.accrual.defaultAccrual : null;\r\n      resultRow.holidayYearReportRow.holidayPayCalculation = (resultRow.data.holidayYear.spec.holidayPayCalculation ?? \"undefined\") == \"undefined\" ? \"\" : EnumerationsLogic.getEnumLabel(\"HolidayPayCalculation\", resultRow.data.holidayYear.spec.holidayPayCalculation);\r\n      resultRow.holidayYearReportRow.startSaldo = Numeric.round(resultRow.data.holidayYear.accrual.startSaldo ?? 0, 0);\r\n      resultRow.holidayYearReportRow.total =  Numeric.round(resultRow.data.holidayYear.accrual.total ?? 0, 0);\r\n      resultRow.holidayYearReportRow.paid =  Numeric.round(HolidaysLogic.getPaidHolidaysCalculation(resultRow.data.holidayYear, \"total\").holidayDays ?? 0, 0);\r\n      resultRow.holidayYearReportRow.available =  Numeric.round(HolidaysLogic.getPaidHolidaysCalculation(resultRow.data.holidayYear, \"endSaldo\").holidayDays ?? 0, 0);\r\n      resultRow.holidayYearReportRow.holidaySalary = HolidaysLogic.getPaidHolidaysCalculation(resultRow.data.holidayYear, \"total\").holidaySalary ?? 0;\r\n      resultRow.holidayYearReportRow.holidayCompensation = HolidaysLogic.getPaidHolidaysCalculation(resultRow.data.holidayYear, \"total\").holidayCompensation ?? 0;\r\n      resultRow.holidayYearReportRow.paidBonus =  Numeric.round(HolidaysLogic.getPaidBonusCalculation(resultRow.data.holidayYear, \"total\").holidayDays ?? 0, 0);\r\n      resultRow.holidayYearReportRow.availableBonus =  Numeric.round(HolidaysLogic.getPaidBonusCalculation(resultRow.data.holidayYear, \"endSaldo\").holidayDays ?? 0, 0);\r\n      resultRow.holidayYearReportRow.holidayBonus = HolidaysLogic.getPaidBonusCalculation(resultRow.data.holidayYear, \"total\").holidayBonus ?? 0;\r\n      resultRow.holidayYearReportRow.holidayPayDailySalary = HolidaysLogic.getHolidayPayDailySalary(resultRow.data.holidayYear)?? 0;\r\n      resultRow.holidayYearReportRow.totalAccruedHolidayPay = resultRow.data.holidayCalc?.totalAccruedHolidayPay ?? 0;\r\n      resultRow.holidayYearReportRow.totalAccruedHolidayBonus = resultRow.data.holidayCalc?.totalAccruedHolidayBonus ?? 0;\r\n      resultRow.holidayYearReportRow.totalAccruedHolidaySocialSecurity = resultRow.data.holidayCalc?.totalAccruedHolidaySocialSecurity ?? 0;\r\n      resultRow.holidayYearReportRow.totalAccruedHolidayPension = resultRow.data.holidayCalc?.totalAccruedHolidayPension ?? 0;\r\n      resultRow.holidayYearReportRow.totalAccruedHolidayUnemployment = resultRow.data.holidayCalc?.totalAccruedHolidayUnemployment ?? 0;\r\n      resultRow.holidayYearReportRow.totalAccruedHolidayAccidentInsurance = resultRow.data.holidayCalc?.totalAccruedHolidayAccidentInsurance ?? 0;\r\n      resultRow.holidayYearReportRow.totalAccruedHolidayGroupLifeInsurance = resultRow.data.holidayCalc?.totalAccruedHolidayGroupLifeInsurance ?? 0;\r\n      resultRow.holidayYearReportRow.totalAccruedHolidayTotal = Numeric.round(\r\n      resultRow.holidayYearReportRow.totalAccruedHolidayPay +\r\n      resultRow.holidayYearReportRow.totalAccruedHolidayBonus +\r\n      resultRow.holidayYearReportRow.totalAccruedHolidaySocialSecurity +\r\n      resultRow.holidayYearReportRow.totalAccruedHolidayPension +\r\n      resultRow.holidayYearReportRow.totalAccruedHolidayUnemployment +\r\n      resultRow.holidayYearReportRow.totalAccruedHolidayAccidentInsurance +\r\n      resultRow.holidayYearReportRow.totalAccruedHolidayGroupLifeInsurance, 2);\r\n    });\r\n  }\r\n  private getBlankHolidayYearReportRow(): HolidayYearReportRow {\r\n    return {\r\n      workerAvatar: null,\r\n      workerId: null,\r\n      employmentId: null,\r\n      startDate: null,\r\n      endDate: null,\r\n      employmentType: null,\r\n      grossSalary: 0,\r\n      holidayCode: null,\r\n      periodDefaultAccrual: null,\r\n      holidayPayCalculation: null,\r\n      startSaldo: 0,\r\n      total: 0,\r\n      paid: 0,\r\n      available: 0,\r\n      holidaySalary: 0,\r\n      holidayCompensation: 0,\r\n      paidBonus: 0,\r\n      availableBonus: 0,\r\n      holidayBonus: 0,\r\n      holidayPayDailySalary: 0,\r\n      totalAccruedHolidayPay: 0,\r\n      totalAccruedHolidayBonus: 0,\r\n      totalAccruedHolidaySocialSecurity: 0,\r\n      totalAccruedHolidayPension: 0,\r\n      totalAccruedHolidayUnemployment: 0,\r\n      totalAccruedHolidayAccidentInsurance: 0,\r\n      totalAccruedHolidayGroupLifeInsurance: 0,\r\n      totalAccruedHolidayTotal: 0,\r\n    };\r\n  }\r\n}\r\n\r\ninterface ResultRow {\r\n  employment: EmploymentListItem;\r\n  data: AccountingHolidayPayDebtReportDataYear;\r\n  holidayYearReportRow: HolidayYearReportRow;\r\n}\r\n\r\ninterface HolidayYearReportRow {\r\n  workerAvatar: Avatar;\r\n  workerId: string;\r\n  employmentId: string;\r\n  startDate: string;\r\n  endDate: string;\r\n  employmentType: string;\r\n  grossSalary: number;\r\n  holidayCode: string;\r\n  periodDefaultAccrual: number;\r\n  holidayPayCalculation: string;\r\n  startSaldo: number;\r\n  total: number;\r\n  paid: number;\r\n  available: number;\r\n  holidaySalary: number;\r\n  holidayCompensation: number;\r\n  paidBonus: number;\r\n  availableBonus: number;\r\n  holidayBonus: number;\r\n  holidayPayDailySalary: number;\r\n\r\n  totalAccruedHolidayPay: number;\r\n  /** Total sum of accrued holiday pays. */\r\n  totalAccruedHolidayBonus: number;\r\n  /** Total sum of social security payments for accrued holiday pays. */\r\n  totalAccruedHolidaySocialSecurity: number;\r\n  /** Total sum of pension payments for accrued holiday pays. */\r\n  totalAccruedHolidayPension: number;\r\n  /** Total sum of unemployment insurance payments for accrued holiday pays. */\r\n  totalAccruedHolidayUnemployment: number;\r\n  /** Total accident insurance. */\r\n  totalAccruedHolidayAccidentInsurance: number;\r\n  /** Total accident insurance. */\r\n  totalAccruedHolidayGroupLifeInsurance: number;\r\n  totalAccruedHolidayTotal: number;\r\n\r\n}","import angular from \"angular\";\r\nimport JSZip from \"@progress/jszip-esm\";\r\nimport { saveAs } from \"file-saver\";\r\nimport { Ajax, Configs, Translations, Texts, Dates, Reports } from \"@salaxy/core\";\r\nimport { UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Provides functionality to export salary slip(s) as pdf or zipped pdf.\r\n */\r\nexport class SalarySlipDownloadController implements angular.IController {\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"$http\",\r\n    \"AjaxNg1\",\r\n    \"UiHelpers\",\r\n    \"Reports\"\r\n  ];\r\n\r\n  constructor(\r\n    private $http: angular.IHttpService,\r\n    private ajax: Ajax,\r\n    private uiHelpers: UiHelpers,\r\n    private reportsApi: Reports\r\n  ) {}\r\n\r\n  /**\r\n   * Export items\r\n   * One item is exported as pdf and multiple items are exported as zip containg pdfs.\r\n   */\r\n  public async export(items: any[]) {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.loading\");\r\n    const promises = items.map(x => {\r\n      const url = `${Configs.current.apiServer}/v03/api/reports/assure-pdf/salarySlip?language=${encodeURIComponent(Translations.getLanguage())}&ids=${x.id}&disposition=inline&access_token=${this.ajax.getCurrentToken()}`;\r\n      return this.ajax.getBlob(url);\r\n    });\r\n    const responses = await Promise.all(promises);\r\n    if(responses.length === 1) {\r\n      this.uiHelpers.downloadFile(responses[0].data as any, decodeURIComponent(responses[0].headers[\"content-disposition\"]).match(/filename\\s*=\\s*\"?(?<file>.*?)(?:\\s*;|\"|\\s*$)/)?.groups?.file);\r\n      loading.dismiss();\r\n    } else {\r\n      const zip = new JSZip();\r\n      const fileNames = {};\r\n      responses.forEach(response => {\r\n        const fileName = `${decodeURIComponent(response.headers[\"content-disposition\"]).match(/filename\\s*=\\s*\"?(?<file>.*?)(?:\\s*;|\"|\\s*$)/)?.groups?.file}`;\r\n        if(Object.keys(fileNames).includes(fileName)) {\r\n          ++fileNames[fileName];\r\n          zip.file(`${fileNames[fileName]}_${fileName}`, response.data as Blob);\r\n        } else {\r\n          fileNames[fileName] = 1;\r\n          zip.file(fileName, response.data as Blob);\r\n        }\r\n      });\r\n      const zipBlob = await zip.generateAsync({type: \"blob\", mimeType: \"application/zip\"});\r\n      saveAs(zipBlob, Texts.escapeFileName(`${Translations.get(\"SALAXY.UI_Terms.downLoadableMaterialTypes.calculations\")}_${Dates.format(\"today\",\"YYYYMMDD\")}`));\r\n      loading.dismiss();\r\n    }\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { AccountingData, Dates, Reports } from \"@salaxy/core\";\r\nimport { UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Provides functionality for building ad hoc accounting holiday pay debt reports.\r\n */\r\nexport class AccountingHolidayPayDebtReportQueryController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"Reports\",\r\n    \"UiHelpers\",\r\n  ];\r\n\r\n  /**\r\n   * Report view table only (partial) or pdf preview (full)\r\n   * Defaults to 'partial'\r\n   */\r\n  public view: \"partial\" | \"full\";\r\n\r\n  /** Ref date to which the debt is calculated. */\r\n  public refDate: string = Dates.getToday();\r\n\r\n  /** Accounting data */\r\n  public data: AccountingData;\r\n\r\n  /**Selected report language */\r\n  public lang: string;\r\n\r\n  /** Data reader for the control. */\r\n  public dataReader = {\r\n  /**\r\n   * Function to read data into given array\r\n   */\r\n  // eslint-disable-next-line @typescript-eslint/no-unused-vars\r\n   read: (target: string, ruleSet: string, arr: AccountingData[], message: string): Promise<void> => {\r\n      if (this.data) {\r\n        arr.push(this.data);\r\n      }\r\n      return Promise.resolve();\r\n    },\r\n    /** Optional label for data export */\r\n    exportLabel: null,\r\n    /** Indicates if the export is not possible */\r\n    disabled: () => !this.data,\r\n    /* Indicates if row is expandable */\r\n    showExpand: true,\r\n    /* Indicates if rows exists*/\r\n    hasRows: () => !this.data?.ledgerAccounts\r\n  };\r\n\r\n  constructor(\r\n    private reportsApi: Reports,\r\n    private uiHelpers: UiHelpers,\r\n  ) {\r\n    // Dependency injection\r\n  }\r\n\r\n  /**\r\n   * Initialize controller values.\r\n   */\r\n  public $onInit() {\r\n    this.view = this.view || \"partial\";\r\n  }\r\n\r\n  /** Queries the report data. */\r\n  public queryData(target = \"default\") {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    this.reportsApi.getAccountingDataForHolidayPayDebt(this.refDate, target)\r\n      .then((result) => {\r\n        this.data = result;\r\n        loading.dismiss();\r\n    });\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { HolidayYears, HolidayPayCalculationReportData, IrRow, CalculationRowType, EnumerationsLogic, IncomeTypesLogic, HolidayPayCalculationReportDataCalc, Arrays, Numeric, ODataResult, ApiListItem } from \"@salaxy/core\";\r\nimport { UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Provides functionality for building ad hoc holiday pay reports.\r\n */\r\nexport class HolidayPayReportQueryController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"HolidayYears\",\r\n    \"UiHelpers\",\r\n    \"$routeParams\",\r\n  ];\r\n\r\n  /** Raw report from api */\r\n  public data: HolidayPayCalculationReportData;\r\n\r\n  /** Current employment id */\r\n  public employmentId: string;\r\n\r\n  /** Current holidayYear */\r\n  public year: number;\r\n\r\n  //** All holiday years for the worker */\r\n  public years: string[] = [];\r\n\r\n  public totals: HolidayPayCalculationReportDataCalc = {\r\n     total: 0,\r\n     hours: 0,\r\n     overtimeHours: 0,\r\n     workingDays: 0,\r\n     absenceDays: 0\r\n  };\r\n\r\n  constructor(\r\n    private holidayYearsApi: HolidayYears,\r\n    private uiHelpers: UiHelpers,\r\n    private $routeParams: angular.route.IRouteParamsService,\r\n\r\n  ) {\r\n  }\r\n\r\n  /** Controller initialization */\r\n  public $onInit() {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    const crudItemId = this.$routeParams.crudItemId ?? \"\";\r\n    this.year = crudItemId.split(\"/\")[0];\r\n    this.employmentId = crudItemId.split(\"/\")[1];\r\n    this.loadYears().then( years => {\r\n      this.years = years;\r\n      this.query();\r\n      loading.dismiss();\r\n    });\r\n  }\r\n\r\n\r\n  /** Queries the report data. */\r\n  public query() {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    this.holidayYearsApi.getHolidayPayCalculationReportData(this.year, this.employmentId)\r\n      .then((result) => {\r\n        this.data = result;\r\n        // round accruals\r\n        (this.data.holidayYear.accrual.total as any) = Numeric.round(this.data.holidayYear.accrual.total, 0);\r\n        this.totals.total = Numeric.round(Arrays.sum(this.data.calculations, (x) => x.total), 2);\r\n        this.totals.hours = Numeric.round(Arrays.sum(this.data.calculations, (x) => x.hours), 2);\r\n        this.totals.overtimeHours = Numeric.round(Arrays.sum(this.data.calculations, (x) => x.overtimeHours), 2);\r\n        this.totals.workingDays = Numeric.round(Arrays.sum(this.data.calculations, (x) => x.workingDays), 2);\r\n        this.totals.absenceDays = Numeric.round(Arrays.sum(this.data.calculations, (x) => x.absenceDays), 2);\r\n        loading.dismiss();\r\n    });\r\n  }\r\n\r\n  /** Returns label for the ir row. */\r\n  public getLabel(irRow: IrRow): string {\r\n\r\n    //TODO: add this logic to UiHelpers.\r\n\r\n    if (irRow.message) {\r\n      return irRow.message;\r\n    }\r\n    let rowType = irRow.data.calculationRowType || CalculationRowType.Unknown;\r\n    rowType = (rowType.substr(0, 1).toLowerCase() + rowType.substr(1)) as CalculationRowType;\r\n    const code = irRow.irData?.code as number;\r\n    const kind = irRow.data.kind as string;\r\n\r\n    let label = \"\";\r\n    if (rowType === CalculationRowType.IrIncomeType) {\r\n      label = IncomeTypesLogic.getAll(null).find( (x) => (kind && x.transactionCode === kind) || (code > 0 && x.code === code))?.label;\r\n    } else if (rowType === CalculationRowType.MealBenefit && code !== 334) {\r\n      // Meal benefit deductions\r\n      label = IncomeTypesLogic.getAll(null).find( (x) => code > 0 && x.code === code)?.label;\r\n    } else if([\r\n      CalculationRowType.Unknown,\r\n      CalculationRowType.CarBenefit,\r\n      CalculationRowType.BicycleBenefit,\r\n      CalculationRowType.SubsidisedCommute,\r\n      CalculationRowType.TaxAtSource,\r\n      CalculationRowType.HourlySalaryWithWorkingTimeCompensation\r\n    ].includes(rowType))\r\n    {\r\n      label = IncomeTypesLogic.getAll(null).find( (x) => code > 0 && x.code === code)?.label;\r\n    }\r\n    else if([\r\n      CalculationRowType.DailyAllowance,\r\n      CalculationRowType.EmploymentTermination,\r\n      CalculationRowType.WorkingTimeCompensation,\r\n      CalculationRowType.Remuneration,\r\n      CalculationRowType.OtherCompensation,\r\n      CalculationRowType.NonProfitOrg,\r\n      CalculationRowType.MealBenefit, // main MealBenefit\r\n      CalculationRowType.Training,\r\n      CalculationRowType.PaidSickLeave,\r\n      CalculationRowType.TimeRatePay,\r\n    ].includes(rowType) && kind) {\r\n      label =  EnumerationsLogic.getEnumLabel(`${irRow.data.calculationRowType}Kind`, kind, null, null);\r\n    }\r\n    return label || EnumerationsLogic.getEnumLabel(\"CalculationRowType\", rowType, null, null);\r\n\r\n  }\r\n\r\n  private loadYears(): Promise<string[]> {\r\n    return this.holidayYearsApi.getOData({$filter: `data/employmentId eq '${this.employmentId}'`}).then((data: ODataResult<ApiListItem>) => {\r\n        const years = data.items.map((x) => \"\" + x.data.year);\r\n        years.sort();\r\n        years.reverse();\r\n        return years;\r\n      });\r\n  }\r\n}","import angular from \"angular\";\r\n\r\nimport {\r\n  Calculation,\r\n  CalculationRowType,\r\n  Dates,\r\n  PeriodDateKind,\r\n  PeriodType,\r\n  Reports,\r\n  SummaryReportData,\r\n  Avatar,\r\n  Translations,\r\n  Numeric,\r\n  Employments,\r\n  EnumerationsLogic,\r\n  EmploymentTerminationKind,\r\n  IrRow,\r\n  IncomeTypesLogic,\r\n  WorkingTimeCompensationKind,\r\n  RemunerationKind,\r\n  OtherCompensationKind,\r\n  NonProfitOrgKind,\r\n  TrainingKind,\r\n  Unit,\r\n  PaidSickLeaveKind,\r\n  DailyAllowanceKind,\r\n  AllowanceCode,\r\n  Objects,\r\n  Arrays\r\n} from \"@salaxy/core\";\r\nimport { SummaryMapper, UnionPaymentReportConfigGenerator, CostCenterReportConfigGenerator } from \"@salaxy/reports\";\r\nimport { UiHelpers, ExcelHelpers, SessionService, UiCrudHelpers } from \"../../services\";\r\nimport { SxyTableController } from \"../sxy-table/SxyTableController\";\r\n\r\n/**\r\n * Component for displaying summary report of selected period.\r\n */\r\nexport class SummaryReportQueryController implements angular.IController {\r\n  /** Parameters related to report query*/\r\n  public queryOptions: {\r\n    /** Period type for the query. */\r\n    periodType: PeriodType,\r\n    /** Ref date for the period. */\r\n    refDate?: string,\r\n    /** End date for the custom period. */\r\n    endDate?: string,\r\n    /** Period date kind */\r\n    periodDateKind: PeriodDateKind,\r\n  } = {\r\n    periodType: PeriodType.Year,\r\n    refDate: Dates.getDate(Dates.getYear(\"today\"), 1, 1),\r\n    endDate: Dates.getDate(Dates.getYear(\"today\"), 12, 31),\r\n    periodDateKind: PeriodDateKind.SalaryDate,\r\n  };\r\n\r\n  /** Result rows */\r\n  public resultRows: ResultRow[] = [];\r\n\r\n  /** Current tab. */\r\n  public currentTab: \"incomereport\" | \"salarypaymentreport\" = \"incomereport\";\r\n\r\n  public irReportRows: IrCodeIncomeReportRow[] = [];\r\n  public entrepreneurSummaryReportResults:SummaryReportRowResult[] = [];\r\n  public workerSummaryReportResults: SummaryReportRowResult[] = [];\r\n  public totalSummaryReportResults:SummaryReportRowResult[] = [];\r\n  private summaryReportData: SummaryReportData;\r\n  public reportLang: string;\r\n  public costCenterReportCalculations: any = [];\r\n  public unionPaymentExcelRows: any[] = [];\r\n  public reportConfig: any = {};\r\n\r\n  /** Ref to used SxyTable */\r\n  public $sxyTable: SxyTableController;\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"Reports\",\r\n    \"UiHelpers\",\r\n    \"Employments\",\r\n    \"UiCrudHelpers\",\r\n    \"SessionService\",\r\n    \"$timeout\"\r\n  ];\r\n\r\n  constructor(private reports: Reports, private uiHelpers: UiHelpers, private employments: Employments, private uiCrudHelpers: UiCrudHelpers, private sessionService: SessionService, private $timeout: angular.ITimeoutService) {\r\n  }\r\n\r\n  /** Controller initialization */\r\n  public $onInit() {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    this.sessionService.getReportLang().then(lang => {\r\n      this.reportLang = lang;\r\n    });\r\n    this.query().then( () => {\r\n      loading.dismiss();\r\n    });\r\n  }\r\n\r\n  /** Return query info text */\r\n  public getQueryInfoText(): string {\r\n    if (this.summaryReportData?.startDate && this.summaryReportData?.endDate) {\r\n      return `${Translations.get(\"SALAXY.NG1.HolidayReportComponent.irIncomeTypeReportInfo\")}: ${Dates.getFormattedDate(this.summaryReportData.startDate)} - ${Dates.getFormattedDate(this.summaryReportData.endDate)}`;\r\n    }\r\n    return \"\";\r\n  }\r\n\r\n  /**\r\n   * Shows the period selection dialog and makes the search.\r\n   */\r\n  public showPeriodSelection() {\r\n    this.uiHelpers.openEditDialog(\r\n      \"salaxy-components/report/modals/SummaryReportPeriodSelection.html\",\r\n      this.queryOptions,\r\n      null).then((periodResult) => {\r\n        if (periodResult.action === \"ok\") {\r\n          this.queryOptions = periodResult.item;\r\n          this.query();\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Shows an edit dialog for the employment.\r\n   * @param row Row that contains field employmentId (Identifier for the employment).\r\n   * @param row.employmentId The row must contain the employment identifier.\r\n   */\r\n  public showEditEmploymentDialog(row: { employmentId: string } ): void {\r\n    if (!row.employmentId) {\r\n      console.error(\"EmploymentId is missing\", row);\r\n      return;\r\n    }\r\n    this.uiCrudHelpers.openEditEmploymentDialog(row.employmentId, \"default\").then((result) => {\r\n      if (result.action === \"ok\") {\r\n        this.query();\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Filters zero rows off\r\n   * @returns IrCodeIncomeReportRow[] containing not zero rows\r\n   */\r\n  public getIrReportRows(): IrCodeIncomeReportRow[] {\r\n    const results: IrCodeIncomeReportRow[] = [];\r\n    const irRows = this.resultRows.map(x => x.irCodeIncomeReportRow);\r\n    irRows.forEach( irRow => {\r\n      if(irRow) {\r\n        results.push(irRow);\r\n      }\r\n    });\r\n    return results;\r\n  }\r\n\r\n  /**\r\n   * Groups each result rows summary report entrepreneur results\r\n   * @returns array of grouped entrepreneur results\r\n   */\r\n  public getEntrepreneurSummaryReportResults(): SummaryReportRowResult[] {\r\n    const results = [];\r\n    this.resultRows.forEach(resultRow => {\r\n      if(resultRow?.summaryReportRow?.result?.entrepreneurResult) {\r\n        resultRow.summaryReportRow.result = resultRow.summaryReportRow.result || {};\r\n        resultRow.summaryReportRow.result.entrepreneurResult = resultRow.summaryReportRow.result.entrepreneurResult || this.getBlankSummaryReportRowResult();\r\n        resultRow.summaryReportRow.result.entrepreneurResult.avatar = resultRow.avatar;\r\n        resultRow.summaryReportRow.result.entrepreneurResult.workerId = resultRow.workerId;\r\n        resultRow.summaryReportRow.result.entrepreneurResult.employmentId = resultRow.employmentId;\r\n        results.push(resultRow.summaryReportRow.result.entrepreneurResult);\r\n      }\r\n    });\r\n    return results;\r\n  }\r\n\r\n  /**\r\n   * Groups each result rows summary report worker results\r\n   * @returns array of grouped worker results\r\n   */\r\n  public getWorkerSummaryReportResults(): SummaryReportRowResult[] {\r\n    const results = [];\r\n    this.resultRows.forEach(resultRow => {\r\n      if(resultRow.summaryReportRow.result.workerResult) {\r\n        resultRow.summaryReportRow.result.workerResult.avatar = resultRow.avatar;\r\n        resultRow.summaryReportRow.result.workerResult.workerId = resultRow.workerId;\r\n        resultRow.summaryReportRow.result.workerResult.employmentId = resultRow.employmentId;\r\n        results.push(resultRow.summaryReportRow.result.workerResult);\r\n      }\r\n    });\r\n    return results;\r\n  }\r\n\r\n  /**\r\n   * Export totalRows to excel\r\n   */\r\n   public exportToExcel() {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    let tableData = [];\r\n    let reportName = \"\";\r\n    if (this.currentTab == \"incomereport\") {\r\n      reportName = \"incomeReport\";\r\n      const irReportRows = this.irReportRows;\r\n      if (irReportRows.length > 0) {\r\n        tableData.push([Translations.get(\"SALAXY.NG1_Other.Roles.worker\"), ...irReportRows[0].rows.map(row => row.label)]);\r\n        const rowData = irReportRows.map(row => {\r\n          return [row.workerAvatar.displayName, ...row.rows.map(item => item.total)];\r\n        });\r\n        tableData.push(...rowData);\r\n      }\r\n    } else if (this.currentTab == \"salarypaymentreport\") {\r\n      reportName = \"salaryPaymentReport\";\r\n      const headers = [\r\n        Translations.get(\"SALAXY.NG1_Other.Roles.worker\"),\r\n        Translations.get(\"SALAXY.REPORTS.summary.table.totalGrossSalary\"),\r\n        Translations.get(\"SALAXY.REPORTS.summary.table.totalRowCategory\"),\r\n        Translations.get(\"SALAXY.REPORTS.summary.table.benefits\"),\r\n        Translations.get(\"SALAXY.REPORTS.summary.table.irCode\"),\r\n        Translations.get(\"SALAXY.REPORTS.summary.table.totalTaxable\"),\r\n        Translations.get(\"SALAXY.REPORTS.summary.table.tax\"),\r\n        Translations.get(\"SALAXY.REPORTS.summary.table.pension\"),\r\n        Translations.get(\"SALAXY.REPORTS.summary.table.unemploymentInsurance\"),\r\n        Translations.get(\"SALAXY.REPORTS.summary.table.unionPayment\"),\r\n        Translations.get(\"SALAXY.REPORTS.summary.table.foreclosure\"),\r\n        Translations.get(\"SALAXY.REPORTS.summary.table.otherDeductions\"),\r\n        Translations.get(\"SALAXY.REPORTS.summary.table.totalExpenses\"),\r\n        Translations.get(\"SALAXY.REPORTS.summary.table.totalWorkerPayment\"),\r\n        Translations.get(\"SALAXY.REPORTS.summary.table.totalPayment\"),\r\n        Translations.get(\"SALAXY.REPORTS.summary.table.palkkaus\"),\r\n        Translations.get(\"SALAXY.REPORTS.summary.table.service\"),\r\n        Translations.get(\"SALAXY.REPORTS.summary.table.socialSecurity\"),\r\n        Translations.get(\"SALAXY.REPORTS.summary.table.totalPensions\"),\r\n        Translations.get(\"SALAXY.REPORTS.summary.table.employerPension\"),\r\n        Translations.get(\"SALAXY.REPORTS.summary.table.unemployment\"),\r\n        Translations.get(\"SALAXY.REPORTS.summary.table.employerUnemployment\")\r\n      ];\r\n      tableData.push(headers);\r\n\r\n      if (this.entrepreneurSummaryReportResults.length > 0) {\r\n        const rowData = this.entrepreneurSummaryReportResults.map(row => {\r\n          return [\r\n            `${row.avatar.displayName} (YEL)`,\r\n            row.totalGrossSalary,\r\n            row.totalRowCategory,\r\n            row.benefits,\r\n            row.irCode,\r\n            row.totalTaxable,\r\n            row.tax,\r\n            row.pension,\r\n            row.unemploymentInsurance,\r\n            row.unionPayment,\r\n            row.foreclosure,\r\n            row.otherDeductions,\r\n            row.totalExpenses,\r\n            row.totalWorkerPayment,\r\n            row.totalPayment,\r\n            row.palkkaus,\r\n            row.service,\r\n            row.socialSecurity,\r\n            row.totalPensions,\r\n            row.employerPension,\r\n            row.unemployment,\r\n            row.employerUnemployment,\r\n          ];\r\n        });\r\n        tableData.push(...rowData);\r\n      }\r\n      if (this.workerSummaryReportResults.length > 0) {\r\n        const rowData = this.workerSummaryReportResults.map(row => {\r\n          return [\r\n            `${row.avatar.displayName} (TyEL)`,\r\n            row.totalGrossSalary,\r\n            row.totalRowCategory,\r\n            row.benefits,\r\n            row.irCode,\r\n            row.totalTaxable,\r\n            row.tax,\r\n            row.pension,\r\n            row.unemploymentInsurance,\r\n            row.unionPayment,\r\n            row.foreclosure,\r\n            row.otherDeductions,\r\n            row.totalExpenses,\r\n            row.totalWorkerPayment,\r\n            row.totalPayment,\r\n            row.palkkaus,\r\n            row.service,\r\n            row.socialSecurity,\r\n            row.totalPensions,\r\n            row.employerPension,\r\n            row.unemployment,\r\n            row.employerUnemployment,\r\n          ];\r\n        });\r\n        tableData.push(...rowData);\r\n      }\r\n      if (this.workerSummaryReportResults.length > 0 || this.entrepreneurSummaryReportResults.length > 0) {\r\n        const rowData = this.totalSummaryReportResults.map(row => {\r\n          return [\r\n            Translations.get(\"SALAXY.REPORTS.summary.table.total\"),\r\n            row.totalGrossSalary,\r\n            row.totalRowCategory,\r\n            row.benefits,\r\n            row.irCode,\r\n            row.totalTaxable,\r\n            row.tax,\r\n            row.pension,\r\n            row.unemploymentInsurance,\r\n            row.unionPayment,\r\n            row.foreclosure,\r\n            row.otherDeductions,\r\n            row.totalExpenses,\r\n            row.totalWorkerPayment,\r\n            row.totalPayment,\r\n            row.palkkaus,\r\n            row.service,\r\n            row.socialSecurity,\r\n            row.totalPensions,\r\n            row.employerPension,\r\n            row.unemployment,\r\n            row.employerUnemployment,\r\n          ];\r\n        });\r\n        tableData.push(...rowData);\r\n      }\r\n    } else if (this.currentTab == \"unionpaymentreport\") {\r\n      if (this.unionPaymentExcelRows.length > 0) {\r\n        reportName = \"unionPaymentReport\";\r\n        tableData = this.unionPaymentExcelRows;\r\n      }\r\n    } else if (this.currentTab == \"costcenterreport\") {\r\n      if (this.reportConfig.costCenterReportTableConfig.data) {\r\n        reportName =\"costCenterReport\";\r\n        tableData = CostCenterReportConfigGenerator.createCostCenterExcelRows(this.reportConfig.costCenterReportTableConfig);\r\n      }\r\n    }\r\n\r\n    reportName += \"-\" + Dates.getToday();\r\n    if (tableData.length > 0) {\r\n      ExcelHelpers.export(tableData, reportName).then(() => {\r\n        loading.dismiss();\r\n      });\r\n    } else {\r\n      loading.dismiss();\r\n    }\r\n  }\r\n\r\n  private query(): Promise<SummaryReportData> {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    return this.reports.getSummaryReportData(`${Dates.asDate(this.queryOptions.refDate)}`, this.queryOptions.periodType, `${Dates.asDate(this.queryOptions.endDate)}`, this.queryOptions.periodDateKind).then(data => {\r\n      this.summaryReportData = data;\r\n      this.resultRows = [];\r\n\r\n      const findAvatar = (employmentId: string) => {\r\n        const filteredAndSorted = this.summaryReportData.calculations\r\n          .filter(x => x.worker.employmentId === employmentId)\r\n          .sort((a, b) => a.updatedAt > b.updatedAt ? -1 : 1);\r\n        return filteredAndSorted[0]?.worker?.avatar;\r\n      };\r\n\r\n      this.summaryReportData?.calculations?.forEach(calc => {\r\n        let resultRow = this.resultRows.find(x => x.employmentId === calc.worker?.employmentId);\r\n        if(!resultRow) {\r\n          const newRow = this.getBlankResultRow();\r\n          const avatar = findAvatar(calc.worker.employmentId);\r\n          newRow.employmentId = calc.worker.employmentId;\r\n          newRow.avatar = avatar;\r\n          newRow.workerId = avatar?.id;\r\n          this.resultRows.push(newRow);\r\n          resultRow = newRow;\r\n        }\r\n        resultRow.calculations.push(calc);\r\n      });\r\n      this.generateResults();\r\n      loading.dismiss();\r\n      return data;\r\n    });\r\n  }\r\n\r\n  private generateResults(): void {\r\n    this.createIrReportRows();\r\n    this.createSummaryReportRows();\r\n    this.irReportRows = this.getIrReportRows();\r\n    this.entrepreneurSummaryReportResults = this.getEntrepreneurSummaryReportResults();\r\n    this.workerSummaryReportResults = this.getWorkerSummaryReportResults();\r\n    this.totalSummaryReportResults = this.resultRows[0]?.summaryReportRow?.result?.totalResult ? [this.resultRows[0].summaryReportRow.result.totalResult] : [];\r\n    this.createUnionPaymentReportData();\r\n\r\n    if (this.sessionService.isInRole(\"test\")) {\r\n      this.createCostCenterReportData();\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Creates Union payment report data - for browser and excel export.\r\n   */\r\n  private async createUnionPaymentReportData() {\r\n    this.unionPaymentExcelRows = [];\r\n    const tableData: any[] = [];\r\n\r\n    const headers = [\r\n      { field: \"worker\", title: Translations.get(\"SALAXY.REPORTS.unionPaymentReport.worker\") },\r\n      { field: \"salaryDate\", title: Translations.get(\"SALAXY.REPORTS.unionPaymentReport.salaryDate\") },\r\n      { field: \"salaryPeriodStart\", title: Translations.get(\"SALAXY.REPORTS.unionPaymentReport.salaryPeriodStart\") },\r\n      { field: \"salaryPeriodEnd\", title: Translations.get(\"SALAXY.REPORTS.unionPaymentReport.salaryPeriodEnd\") },\r\n      { field: \"union\", title: Translations.get(\"SALAXY.REPORTS.unionPaymentReport.union\") },\r\n      { field: \"membershipPayment\", title: Translations.get(\"SALAXY.REPORTS.unionPaymentReport.membershipPayment\") },\r\n      { field: \"referenceNumber\", title: Translations.get(\"SALAXY.REPORTS.unionPaymentReport.referenceNumber\") },\r\n      { field: \"bankAccount\", title: Translations.get(\"SALAXY.REPORTS.unionPaymentReport.bankAccount\") },\r\n    ];\r\n    this.unionPaymentExcelRows.push(headers.map(h => h.title));\r\n\r\n    let total = 0;\r\n    for (const calc of this.summaryReportData.calculations) {\r\n      const unionPaymentRows = calc.rows.filter(row => row.rowType === CalculationRowType.UnionPayment);\r\n\r\n      if (unionPaymentRows.length > 0) {\r\n        unionPaymentRows.forEach(row => {\r\n          total += row.price;\r\n\r\n          const workerName = calc.worker?.avatar?.displayName;\r\n          const salaryDate = calc.workflow.salaryDate;\r\n          const periodStart = calc.info.workStartDate;\r\n          const periodEnd = calc.info.workEndDate;\r\n          const unionName = row.data.recipientFullName;\r\n          const payment = row.price;\r\n          const refNumber = row.data.referenceNumber;\r\n          const iban = row.data.iban;\r\n\r\n          // Build table data row (for browser display).\r\n          tableData.push({\r\n            worker: workerName,\r\n            salaryDate: Dates.getFormattedDate(salaryDate),\r\n            salaryPeriodStart: Dates.getFormattedDate(periodStart),\r\n            salaryPeriodEnd: Dates.getFormattedDate(periodEnd),\r\n            union: unionName,\r\n            membershipPayment: calc.result.employerCalc.deductionUnionPayment,\r\n            referenceNumber: refNumber,\r\n            bankAccount: iban\r\n          });\r\n\r\n          // Build excel row.\r\n          this.unionPaymentExcelRows.push([\r\n            workerName,\r\n            Dates.asJSDate(salaryDate),\r\n            Dates.asJSDate(periodStart),\r\n            Dates.asJSDate(periodEnd),\r\n            unionName,\r\n            payment,\r\n            refNumber,\r\n            iban\r\n          ]);\r\n        });\r\n      }\r\n    }\r\n    // Add total rows to both table and excel.\r\n    tableData.push({\r\n      worker: Translations.get(\"SALAXY.REPORTS.unionPaymentReport.total\"),\r\n      membershipPayment: total\r\n    });\r\n    this.unionPaymentExcelRows.push([Translations.get(\"SALAXY.REPORTS.unionPaymentReport.total\"), \"\", \"\", \"\", \"\", total]);\r\n\r\n    this.reportConfig.unionPaymentTableConfig = UnionPaymentReportConfigGenerator.getConfig(tableData, headers);\r\n    await this.$timeout();\r\n    this.$sxyTable?.refresh();\r\n  }\r\n\r\n  /**\r\n   * Creates Cost center report data - for browser and excel export.\r\n   */\r\n  private async createCostCenterReportData() {\r\n    this.costCenterReportCalculations = [];\r\n    // Filter all eligible calcs for this report.\r\n    for (const calc of this.summaryReportData.calculations) {\r\n      const hasDimensions =\r\n        calc.accounting.dimensions.length > 0 ||\r\n        (calc.result.irRows?.some(irRow => irRow.accounting.dimensions.length > 0));\r\n\r\n      if (hasDimensions) {\r\n        this.costCenterReportCalculations.push(calc);\r\n      }\r\n    }\r\n    const systemDimensions = this.sessionService.session?.settings?.costAccounting?.dimensions;\r\n\r\n    this.reportConfig.costCenterReportTableConfig = CostCenterReportConfigGenerator.getConfig(this.costCenterReportCalculations, systemDimensions);\r\n    await this.$timeout();\r\n    this.$sxyTable?.refresh();\r\n  }\r\n\r\n  private createIrReportRows(): void {\r\n    this.resultRows.forEach(resultRow => {\r\n      //Create headers\r\n      const irRows = this.summaryReportData?.calculations?.map(x => x.result.irRows).flat().filter(x => x.irData.code !== 1 && x.irData.code !== 0) ?? [];\r\n      irRows.forEach(irRow => {\r\n        if(!resultRow.irCodeIncomeReportRow.rows.some(x => x.key === `${irRow.data.calculationRowType}-${irRow.irData.code}`)) {\r\n          resultRow.irCodeIncomeReportRow.rows.push({\r\n            key: `${irRow.data.calculationRowType}-${irRow.irData.code}`,\r\n            label: this.getLabel(irRow),\r\n            code: irRow.irData.code,\r\n            isCount: false,\r\n            total: 0\r\n          });\r\n        }\r\n        resultRow.irCodeIncomeReportRow.rows.sort((a, b) => a.code > b.code ? 1 : -1);\r\n      });\r\n      const hourlySalaryRowIndex = resultRow.irCodeIncomeReportRow.rows.findIndex(x => x.key === \"HourlySalary-201\");\r\n      if(hourlySalaryRowIndex >= 0) {\r\n        resultRow.irCodeIncomeReportRow.rows.splice(hourlySalaryRowIndex + 1, 0, {\r\n          key: \"salaryPaymentWorkingHours\",\r\n          label: Translations.get(\"SALAXY.NG1.HolidayReportComponent.salaryPaymentWorkingHours\"),\r\n          code: null,\r\n          isCount: true,\r\n          total: 0\r\n        });\r\n      }\r\n      // Insert salaryPaymentMonths after MonthlySalary-201 key\r\n      const monthlySalaryRowIndex = resultRow.irCodeIncomeReportRow.rows.findIndex(x => x.key === \"MonthlySalary-201\");\r\n      if(monthlySalaryRowIndex >= 0) {\r\n        resultRow.irCodeIncomeReportRow.rows.splice(monthlySalaryRowIndex + 1, 0, {\r\n          key: \"salaryPaymentMonths\",\r\n          label: Translations.get(\"SALAXY.NG1.HolidayReportComponent.salaryPaymentMonths\"),\r\n          code: null,\r\n          isCount: true,\r\n          total: 0\r\n        });\r\n      }\r\n\r\n      // Sum rows\r\n      const item: IrCodeIncomeReportRow = {\r\n        workerAvatar: resultRow.avatar,\r\n        workerId: resultRow.workerId,\r\n        employmentId: resultRow.employmentId,\r\n        rows: [...structuredClone(resultRow.irCodeIncomeReportRow.rows)]\r\n      };\r\n      resultRow.calculations.map(x => x.result.irRows).flat().filter(x => x.irData.code !== 1 && x.irData.code !== 0).forEach(irRow => {\r\n        const row = item.rows.find(x => x.key === `${irRow.data.calculationRowType}-${irRow.irData.code}`);\r\n        row.total += irRow.total;\r\n      });\r\n\r\n      const salaryPaymentHoursRow = item.rows.find(x => x.key === \"salaryPaymentWorkingHours\");\r\n      if(salaryPaymentHoursRow) {\r\n        const hourlySalariesRows = resultRow.calculations.map(x => x.result.irRows.filter(x => x.unit === Unit.Hours && x.irData.code === 201)).flat();\r\n        salaryPaymentHoursRow.total = Arrays.sum(hourlySalariesRows, x => x.count);\r\n      }\r\n      const salaryPaymentMonthsRow = item.rows.find(x => x.key === \"salaryPaymentMonths\");\r\n      if(salaryPaymentMonthsRow) {\r\n        const monthlySalariesCals = resultRow.calculations.filter(x => x.result.irRows.some(x => /*x.unit === Unit.Period &&*/ x.irData.code === 201));\r\n        salaryPaymentMonthsRow.total = [... new Set(monthlySalariesCals.map(x => Dates.getMonth(x.workflow.salaryDate)))].length;\r\n      }\r\n      if(item.rows.some(x => x.total > 0)) {\r\n        resultRow.irCodeIncomeReportRow = item;\r\n      } else {\r\n        resultRow.irCodeIncomeReportRow = null;\r\n      }\r\n    });\r\n  }\r\n\r\n  private createSummaryReportRows() {\r\n    if(!this.summaryReportData || Object.keys(this.summaryReportData).length === 0) {\r\n      return;\r\n    }\r\n    const summaryReportData = Objects.copy(this.summaryReportData);\r\n    this.resultRows.forEach(resultRow => {\r\n      summaryReportData.calculations = resultRow.calculations;\r\n      (SummaryMapper.getSummaryReport(summaryReportData)as any).result.workerResult.forEach(item => {\r\n        this.createSummaryReportRowResult(resultRow, item, \"workerResult\");\r\n      });\r\n      (SummaryMapper.getSummaryReport(summaryReportData)as any).result.entrepreneurResult.forEach(item => {\r\n        this.createSummaryReportRowResult(resultRow, item, \"entrepreneurResult\");\r\n      });\r\n      (SummaryMapper.getSummaryReport(summaryReportData)as any).totalResult.forEach(item => {\r\n        this.createSummaryReportRowResult(resultRow, item, \"totalResult\");\r\n      });\r\n    });\r\n  }\r\n\r\n  private createSummaryReportRowResult(resultRow: ResultRow, item: any, resultType: \"workerResult\" | \"entrepreneurResult\" | \"totalResult\"): void {\r\n    if(!resultRow.summaryReportRow.result[resultType]) {\r\n      resultRow.summaryReportRow.result[resultType] = this.getBlankSummaryReportRowResult();\r\n    }\r\n      delete item.worker;\r\n      delete item.workStartDate;\r\n      delete item.workStartEndDate;\r\n      for (const [key, value] of Object.entries(item)) {\r\n        resultRow.summaryReportRow.result[resultType][key] += Numeric.parseNumber(value as string);\r\n        Numeric.round(resultRow.summaryReportRow.result[resultType][key]);\r\n      }\r\n  }\r\n\r\n  private getLabel(irRow: IrRow): string {\r\n    let rowType = irRow.data.calculationRowType || CalculationRowType.Unknown;\r\n    rowType = (rowType.substr(0, 1).toLowerCase() + rowType.substr(1)) as CalculationRowType;\r\n    const code = irRow.irData?.code as number;\r\n    const kind = this.getKind(irRow);\r\n    let label = \"\";\r\n    if (rowType === CalculationRowType.IrIncomeType) {\r\n      label = IncomeTypesLogic.getAll(null).find( (x) => (kind && x.transactionCode === kind) || (code > 0 && x.code === code))?.label + `(${code})`;\r\n    } else if (rowType === CalculationRowType.MealBenefit && code !== 334) {\r\n      // Meal benefit deductions\r\n      label = IncomeTypesLogic.getAll(null).find( (x) => code > 0 && x.code === code)?.label + `(${code})`;\r\n    } else if([\r\n      CalculationRowType.Unknown,\r\n      CalculationRowType.CarBenefit,\r\n      CalculationRowType.BicycleBenefit,\r\n      CalculationRowType.SubsidisedCommute,\r\n      CalculationRowType.TaxAtSource,\r\n      CalculationRowType.HourlySalaryWithWorkingTimeCompensation\r\n    ].includes(rowType))\r\n    {\r\n      label = IncomeTypesLogic.getAll(null).find( (x) => code > 0 && x.code === code)?.label + `(${code})`;\r\n    }\r\n    else if([\r\n      CalculationRowType.DailyAllowance,\r\n      CalculationRowType.EmploymentTermination,\r\n      CalculationRowType.WorkingTimeCompensation,\r\n      CalculationRowType.Remuneration,\r\n      CalculationRowType.OtherCompensation,\r\n      CalculationRowType.NonProfitOrg,\r\n      CalculationRowType.MealBenefit, // main MealBenefit\r\n      CalculationRowType.Training,\r\n      CalculationRowType.PaidSickLeave,\r\n      CalculationRowType.TimeRatePay,\r\n    ].includes(rowType) && kind) {\r\n      label =  EnumerationsLogic.getEnumLabel(`${irRow.data.calculationRowType}Kind`, kind, null, null)  + `(${code})`;\r\n    }\r\n    return label || EnumerationsLogic.getEnumLabel(\"CalculationRowType\", rowType, null, null) + `(${code})`;\r\n  }\r\n\r\n  private getKind(irRow: IrRow): string {\r\n    if(irRow.data.kind) {\r\n      return irRow.data.kind;\r\n    }\r\n    // this forward, for backward compatibility\r\n    const rowType = (irRow.data.calculationRowType.substr(0, 1).toLowerCase() + irRow.data.calculationRowType.substr(1)) as CalculationRowType;\r\n    switch(rowType) {\r\n      case CalculationRowType.DailyAllowance: {\r\n        const code = irRow.irData.dailyAllowance[0];\r\n        const codeMapping = {\r\n          [AllowanceCode.InternationalDailyAllowance]: DailyAllowanceKind.InternationalDailyAllowance,\r\n          [AllowanceCode.PartialDailyAllowance]: DailyAllowanceKind.PartialDailyAllowance,\r\n          [AllowanceCode.MealAllowance]: DailyAllowanceKind.MealAllowance,\r\n          [AllowanceCode.FullDailyAllowance]: DailyAllowanceKind.FullDailyAllowance,\r\n        };\r\n        return codeMapping[code] ?? DailyAllowanceKind.Undefined;\r\n      }\r\n      case CalculationRowType.EmploymentTermination: {\r\n        switch(irRow.irData.code) {\r\n          case 208:\r\n            return EmploymentTerminationKind.NoticePeriodCompensation;\r\n          case 224:\r\n            return EmploymentTerminationKind.MonetaryWorkingTimeBankCompensation;\r\n          case 229:\r\n            return EmploymentTerminationKind.TerminationAndLayOffDamages;\r\n          case 231:\r\n            return EmploymentTerminationKind.VoluntaryTerminationCompensation;\r\n          case 338:\r\n            return EmploymentTerminationKind.PensionPaidByEmployer;\r\n        }\r\n        break;\r\n      }\r\n      case CalculationRowType.WorkingTimeCompensation: {\r\n        switch(irRow.irData.code) {\r\n          case 205:\r\n            return WorkingTimeCompensationKind.EmergencyWorkCompensation;\r\n          case 206:\r\n            return WorkingTimeCompensationKind.EveningWorkCompensation;\r\n          case 207:\r\n            return WorkingTimeCompensationKind.EveningShiftAllowance;\r\n          case 211:\r\n            return WorkingTimeCompensationKind.SaturdayPay;\r\n          case 212:\r\n            return WorkingTimeCompensationKind.ExtraWorkPremium;\r\n          case 216:\r\n            return WorkingTimeCompensationKind.OtherCompensation;\r\n          case 217:\r\n            return WorkingTimeCompensationKind.WaitingTimeCompensation;\r\n          case 221:\r\n            return WorkingTimeCompensationKind.SundayWorkCompensation;\r\n          case 230:\r\n            return WorkingTimeCompensationKind.StandByCompensation;\r\n          case 232:\r\n            return WorkingTimeCompensationKind.WeeklyRestCompensation;\r\n          case 235:\r\n            return WorkingTimeCompensationKind.OvertimeCompensation;\r\n          case 236:\r\n            return WorkingTimeCompensationKind.NightWorkAllowance;\r\n          case 237:\r\n            return WorkingTimeCompensationKind.NightShiftCompensation;\r\n        }\r\n        break;\r\n      }\r\n      case CalculationRowType.Remuneration: {\r\n        switch(irRow.irData.code) {\r\n          case 202:\r\n            return RemunerationKind.InitiativeFee;\r\n          case 203:\r\n            return RemunerationKind.BonusPay;\r\n          case 220:\r\n            return RemunerationKind.Commission;\r\n          case 223:\r\n            return RemunerationKind.PerformanceBonus;\r\n          case 226:\r\n            return RemunerationKind.ShareIssueForEmployees;\r\n          case 233:\r\n            return RemunerationKind.ProfitSharingBonus;\r\n        }\r\n        break;\r\n      }\r\n      case CalculationRowType.OtherCompensation: {\r\n        switch(irRow.irData.code) {\r\n          case 210:\r\n            return OtherCompensationKind.MeetingFee;\r\n          case 214:\r\n            return OtherCompensationKind.LectureFee;\r\n          case 215:\r\n            return OtherCompensationKind.PositionOfTrustCompensation;\r\n          case 225:\r\n            return OtherCompensationKind.AccruedTimeOffCompensation;\r\n          case 308:\r\n            return OtherCompensationKind.MembershipOfGoverningBodyCompensation;\r\n          case 310:\r\n            return OtherCompensationKind.MonetaryGiftForEmployees;\r\n          case 313:\r\n            return OtherCompensationKind.UseCompensationAsEarnedIncome;\r\n          case 314:\r\n            return OtherCompensationKind.UseCompensationAsCapitalIncome;\r\n          case 316:\r\n            return OtherCompensationKind.OtherTaxableIncomeAsEarnedIncome;\r\n          case 320:\r\n            return OtherCompensationKind.StockOptionsAndGrants;\r\n          case 326:\r\n            return OtherCompensationKind.EmployeeInventionCompensation;\r\n          case 332:\r\n            return OtherCompensationKind.CapitalIncomePayment;\r\n          case 339:\r\n            return OtherCompensationKind.WorkEffortBasedDividendsAsWage;\r\n          case 340:\r\n            return OtherCompensationKind.WorkEffortBasedDividendsAsNonWage;\r\n          case 343:\r\n            return OtherCompensationKind.EmployeeStockOption;\r\n          case 361:\r\n            return OtherCompensationKind.EmployeeStockOptionWithLowerPrice;\r\n          case 366:\r\n            return OtherCompensationKind.CopyrightRoyaltiesEarnedIncome;\r\n          case 367:\r\n            return OtherCompensationKind.StockGrantPaidInMoney;\r\n          case 368:\r\n            return OtherCompensationKind.EmployeeStockOptionPaidInMoney;\r\n        }\r\n        break;\r\n      }\r\n      case CalculationRowType.NonProfitOrg: {\r\n        switch(irRow.irData.code) {\r\n          case 358:\r\n          case 1358:\r\n            return NonProfitOrgKind.DailyAllowance;\r\n          case 357:\r\n            return NonProfitOrgKind.KilometreAllowance;\r\n        }\r\n        break;\r\n      }\r\n      case CalculationRowType.Training: {\r\n        switch(irRow.irData.code) {\r\n          case 227:\r\n            return TrainingKind.TrainingSalary;\r\n          case 201: {\r\n            if(irRow.unit === Unit.Hours) {\r\n              return TrainingKind.TrainingHourlySalary;\r\n            }\r\n            if(irRow.unit === Unit.Period) {\r\n              return TrainingKind.TrainingMonthlySalary;\r\n            }\r\n          }\r\n        }\r\n        break;\r\n      }\r\n      case CalculationRowType.PaidSickLeave: {\r\n        switch(irRow.irData.code) {\r\n          case 227:\r\n            return PaidSickLeaveKind.PaidSickLeaveSalary;\r\n          case 201: {\r\n            if(irRow.unit === Unit.Hours) {\r\n              return PaidSickLeaveKind.PaidSickLeaveHourlySalary;\r\n            }\r\n            if(irRow.unit === Unit.Period) {\r\n              return PaidSickLeaveKind.PaidSickLeaveMonthlySalary;\r\n            }\r\n          }\r\n        }\r\n        break;\r\n      }\r\n      default:\r\n        return null;\r\n    }\r\n  }\r\n\r\n  private getBlankResultRow(): ResultRow {\r\n    return {\r\n      employmentId: null,\r\n      avatar: null,\r\n      workerId: null,\r\n      calculations: [],\r\n      irCodeIncomeReportRow: this.getBlankIrCodeIncomeReportRow(),\r\n      summaryReportRow: this.getBlankSummaryReportRow()\r\n    };\r\n  }\r\n\r\n  private getBlankIrCodeIncomeReportRow(): IrCodeIncomeReportRow  {\r\n    return {\r\n      workerAvatar: null,\r\n      workerId: null,\r\n      employmentId: null,\r\n      rows: []\r\n    };\r\n  }\r\n\r\n  private getBlankSummaryReportRow(): SummaryReportRow {\r\n    return {\r\n      result: {\r\n        workerResult: null,\r\n        entrepreneurResult: null,\r\n        totalResult: null\r\n      }\r\n    };\r\n  }\r\n\r\n  private getBlankSummaryReportRowResult(): SummaryReportRowResult {\r\n    return  {\r\n      avatar: null,\r\n      workerId: null,\r\n      employmentId: null,\r\n      totalGrossSalary: 0,\r\n      totalRowCategory: 0,\r\n      benefits: 0,\r\n      irCode: 0,\r\n      totalTaxable: 0,\r\n      tax: 0,\r\n      pension: 0,\r\n      unemploymentInsurance: 0,\r\n      unionPayment: 0,\r\n      foreclosure: 0,\r\n      otherDeductions: 0,\r\n      totalExpenses: 0,\r\n      totalWorkerPayment: 0,\r\n      totalPayment: 0,\r\n      palkkaus: 0,\r\n      service: 0,\r\n      socialSecurity: 0,\r\n      totalPensions: 0,\r\n      employerPension: 0,\r\n      unemployment: 0,\r\n      employerUnemployment: 0,\r\n    };\r\n  }\r\n}\r\n\r\ninterface ResultRow {\r\n  employmentId: string;\r\n  avatar: Avatar;\r\n  workerId: string;\r\n  calculations: Calculation[];\r\n  irCodeIncomeReportRow: IrCodeIncomeReportRow;\r\n  summaryReportRow: SummaryReportRow;\r\n}\r\n\r\ninterface SummaryReportRow {\r\n  result: SummaryReportResult;\r\n}\r\n\r\ninterface SummaryReportResult {\r\n  workerResult?: SummaryReportRowResult;\r\n  entrepreneurResult?: SummaryReportRowResult;\r\n  totalResult?: SummaryReportRowResult;\r\n}\r\n\r\ninterface SummaryReportRowResult {\r\n  avatar: Avatar;\r\n  workerId: string;\r\n  employmentId: string;\r\n  totalGrossSalary: number;\r\n  totalRowCategory: number;\r\n  benefits: number;\r\n  irCode: number;\r\n  totalTaxable: number;\r\n  tax: number;\r\n  pension: number;\r\n  unemploymentInsurance: number;\r\n  unionPayment: number;\r\n  foreclosure: number;\r\n  otherDeductions: number;\r\n  totalExpenses: number;\r\n  totalWorkerPayment: number;\r\n  totalPayment: number;\r\n  palkkaus: number;\r\n  service: number;\r\n  socialSecurity: number;\r\n  totalPensions: number;\r\n  employerPension: number;\r\n  unemployment: number;\r\n  employerUnemployment: number;\r\n}\r\n\r\ninterface IrCodeIncomeReportRow {\r\n  workerAvatar: Avatar;\r\n  workerId: string;\r\n  employmentId: string;\r\n  rows: IrReportRow[];\r\n}\r\n\r\ninterface IrReportRow {\r\n  code: number;\r\n  key: string;\r\n  total: number;\r\n  label: string;\r\n  isCount: boolean;\r\n}","import angular from \"angular\";\r\n\r\nimport { Arrays, CalculationRowType, Dates, EnumerationsLogic, IncomeTypesLogic, IrRow, PayStatsCalculationReportDataResult, PayStatsTypeDefinition, Reports, Translations } from \"@salaxy/core\";\r\nimport { UiHelpers } from \"../../services\";\r\nimport { CellComponent, RowComponent } from \"tabulator-tables\";\r\n\r\n/**\r\n * Provides functionality for building ad hoc holiday pay reports.\r\n */\r\nexport class PayStatsReportQueryController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"Reports\",\r\n    \"UiHelpers\",\r\n    \"$routeParams\",\r\n    \"$compile\",\r\n    \"$scope\"\r\n  ];\r\n\r\n  /** Raw report from api */\r\n  public data: Array<{ type: PayStatsTypeDefinition, results: PayStatsCalculationReportDataResult[]}> = [];\r\n\r\n  /** Current employment id */\r\n  public employmentId: string;\r\n\r\n  /** Flag for indicating query in progress. */\r\n  public isQuerying: boolean = false;\r\n\r\n  /** Report configuration settings. */\r\n  public reportInclude: any;\r\n  public reportOptions: any;\r\n  public reportData: any;\r\n\r\n  constructor(\r\n    private reportsApi: Reports,\r\n    private uiHelpers: UiHelpers,\r\n    private $routeParams: angular.route.IRouteParamsService,\r\n    private $compile: angular.ICompileService,\r\n    private $scope: angular.IScope,\r\n  ) {}\r\n\r\n  /** Controller initialization */\r\n  public $onInit() {\r\n    const crudItemId = this.employmentId ?? (this.$routeParams.crudItemId ?? \"\").split(\"/\")[0];\r\n    this.employmentId = crudItemId;\r\n\r\n    /** Add a css class for all rows related to the parent row. */\r\n    function applyClassRecursive(row: RowComponent, className: string) {\r\n      const el = row.getElement();\r\n      el.classList.remove(\"nested-odd\", \"nested-even\");\r\n      el.classList.add(className);\r\n      row.getTreeChildren()?.forEach((childRow: RowComponent) => applyClassRecursive(childRow, className));\r\n    }\r\n\r\n    this.reportOptions = {\r\n      selectableRows: false,\r\n      layout: \"fitColumns\",\r\n      dataTree: true,\r\n      dataTreeChildIndent: 30,\r\n      dataTreeStartExpanded: [true, true, false],\r\n      rowFormatter: (row: any) => {\r\n        let depth = 0;\r\n        let parent = row.getTreeParent();\r\n        while (parent) {\r\n          depth++;\r\n          parent = parent.getTreeParent();\r\n        }\r\n\r\n        // Format the nested rows' odd/even classes starting from the second nested rows. (0th one is the main type, e.g. \"KTA\", so that will be ignored.)\r\n        if (depth == 1) {\r\n          const parent = row.getTreeParent()!;\r\n          const siblings = parent.getTreeChildren();\r\n          const idx = siblings.indexOf(row);\r\n          const className = idx % 2 === 0 ? \"nested-odd\" : \"nested-even\";\r\n          applyClassRecursive(row, className);\r\n        }\r\n      }\r\n    };\r\n  }\r\n\r\n  /** Queries the report data. */\r\n  public query() {\r\n    this.isQuerying = true;\r\n    this.data = [];\r\n    this.reportsApi.getPayStatsCalculationReportData(this.employmentId)\r\n      .then((result) => {\r\n        // get all distinct types\r\n        const types = Arrays.groupBy(result.results, x => x.type.id + \"-\" + x.type.kind);\r\n        for(const idx in types) {\r\n          this.data.push( {\r\n            type: types[idx][0].type,\r\n            results: types[idx],\r\n          });\r\n        }\r\n        this.reportInclude = this.generateHeaders();\r\n        this.reportData = this.generateReportData(this.data);\r\n        this.isQuerying = false;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Generates column headers for the table.\r\n   * @returns array of headers and their settings.\r\n   */\r\n  private generateHeaders() {\r\n    return [\r\n      { field: \"type\", title: Translations.get(\"SALAXY.REPORTS.payStatsReport.type\"), width: 200, formatter: cell => cell.getValue() ? `<strong>${cell.getValue()}</strong>` : \"\", headerSort: false },\r\n      { field: \"timeframe\", title: Translations.get(\"SALAXY.REPORTS.payStatsReport.timeframe\"), width: 200, headerSort: false },\r\n      { field: \"result\", title: Translations.get(\"SALAXY.REPORTS.payStatsReport.result\"), width: 80, hozAlign: \"right\", headerHozAlign: \"right\" },\r\n      { field: \"calculation\", title: Translations.get(\"SALAXY.REPORTS.payStatsReport.calculation\"), formatter: \"html\" },\r\n      { field: \"info\", title: Translations.get(\"SALAXY.REPORTS.payStatsReport.info\"), headerSort: false },\r\n      { field: \"amount\", title: Translations.get(\"SALAXY.REPORTS.payStatsReport.amount\"), width: 150, hozAlign: \"right\", headerHozAlign: \"right\", headerSort: false },\r\n      { field: \"price\", title: Translations.get(\"SALAXY.REPORTS.payStatsReport.price\"), width: 150, hozAlign: \"right\", headerHozAlign: \"right\", formatter: \"money\", formatterParams: { symbol: \"€\", symbolAfter: true, decimal: \",\", thousand: \" \", }, headerSort: false },\r\n      { field: \"workingTime\", title: Translations.get(\"SALAXY.REPORTS.payStatsReport.workingTime\"), width: 150, hozAlign: \"right\", headerHozAlign: \"right\" },\r\n      {\r\n        field: \"workingTimeType\",\r\n        title: Translations.get(\"SALAXY.REPORTS.payStatsReport.workingTimeType\"),\r\n        width: 200,\r\n        formatter: (cell: CellComponent) => {\r\n          return this.getBadgeFormatter(cell, \"workingTimeType\");\r\n        },\r\n        headerSort: false\r\n      },\r\n      { field: \"salary\", title: Translations.get(\"SALAXY.REPORTS.payStatsReport.salary\"), width: 150, hozAlign: \"right\", headerHozAlign: \"right\", formatter: \"money\", formatterParams: { symbol: \"€\", symbolAfter: true, decimal: \",\", thousand: \" \", }},\r\n      {\r\n        field: \"salaryType\",\r\n        title: Translations.get(\"SALAXY.REPORTS.payStatsReport.salaryType\"),\r\n        width: 200,\r\n        formatter: (cell: CellComponent) => {\r\n          return this.getBadgeFormatter(cell, \"salaryType\");\r\n        },\r\n        headerSort: false\r\n      }\r\n    ];\r\n  }\r\n\r\n\r\n  /**\r\n   * Formats value with a badge component (InputPayStatsRowType.ts).\r\n   * @param cell Cell data.\r\n   * @param rowVal Row value type name for AngularJS component.\r\n   * @returns DOM Node for Tabulator.\r\n   */\r\n  private getBadgeFormatter(cell: CellComponent, rowVal: string) {\r\n    const el = angular.element(`<salaxy-input-pay-stats-row-type name='${rowVal}' label-type='no-label' ng-model='row.${rowVal}' read-only='true'></salaxy-input-pay-stats-row-type>`);\r\n    const scope = (this.$scope.$new(true) as angular.IScope & { row: any });\r\n    scope.row = cell.getData();\r\n\r\n    this.$compile(el)(scope);\r\n    scope.$applyAsync();\r\n\r\n    return el[0];\r\n  }\r\n\r\n  /**\r\n   * Generates report data for multiple nested rows.\r\n   * @param data Report data.\r\n   * @returns Report data in nested rows for Tabulator.\r\n   */\r\n  private generateReportData(data) {\r\n    return data.map(payStatsCalc => ({\r\n      // The main report row (eg. \"KTA\").\r\n      type: this.getTypeLabel(payStatsCalc.type),\r\n      // Each child is a timeframe of calculations.\r\n      _children: payStatsCalc.results.map(result => ({\r\n        timeframe: `${Dates.getFormattedDate(result.start)} - ${Dates.getFormattedDate(result.end)}`,\r\n        result: result.result,\r\n        workingTime: result.workingTime,\r\n        salary: result.salary,\r\n        // Calculation rows.\r\n        _children: result.calculations.map(calc => ({\r\n          calculation: `<a href=\"#/calc/details/${calc.calculationId}\">${calc.calculationTitle} ${Dates.getFormattedDate(calc.salaryDate)}</a>`,\r\n          info: `${Dates.getFormattedDate(calc.workStartDate)} - ${Dates.getFormattedDate(calc.workEndDate)}`,\r\n          workingTime: calc.workingTime,\r\n          salary: calc.salary,\r\n          // Rows in each calculation.\r\n          _children: calc.rows.map(row => ({\r\n            info: this.getRowLabel(row.irRow),\r\n            amount: row.irRow.count,\r\n            price: row.irRow.price,\r\n            workingTime: row.workingTime,\r\n            workingTimeType: row.workingTimeType,\r\n            salary: row.salary,\r\n            salaryType: row.salaryType,\r\n          })),\r\n        })),\r\n      })),\r\n    }));\r\n  }\r\n\r\n  /** Returns label for the ir row. */\r\n  public getRowLabel(irRow: IrRow): string {\r\n\r\n    //TODO: add this logic to UiHelpers.\r\n\r\n    if (irRow.message) {\r\n      return irRow.message;\r\n    }\r\n    let rowType = irRow.data.calculationRowType || CalculationRowType.Unknown;\r\n    rowType = (rowType.substr(0, 1).toLowerCase() + rowType.substr(1)) as CalculationRowType;\r\n    const code = irRow.irData?.code as number;\r\n    const kind = irRow.data.kind as string;\r\n\r\n    let label = \"\";\r\n    if (rowType === CalculationRowType.IrIncomeType) {\r\n      label = IncomeTypesLogic.getAll(null).find( (x) => (kind && x.transactionCode === kind) || (code > 0 && x.code === code))?.label;\r\n    } else if (rowType === CalculationRowType.MealBenefit && code !== 334) {\r\n      // Meal benefit deductions\r\n      label = IncomeTypesLogic.getAll(null).find( (x) => code > 0 && x.code === code)?.label;\r\n    } else if([\r\n      CalculationRowType.Unknown,\r\n      CalculationRowType.CarBenefit,\r\n      CalculationRowType.BicycleBenefit,\r\n      CalculationRowType.SubsidisedCommute,\r\n      CalculationRowType.TaxAtSource,\r\n      CalculationRowType.HourlySalaryWithWorkingTimeCompensation\r\n    ].includes(rowType))\r\n    {\r\n      label = IncomeTypesLogic.getAll(null).find( (x) => code > 0 && x.code === code)?.label;\r\n    }\r\n    else if([\r\n      CalculationRowType.DailyAllowance,\r\n      CalculationRowType.EmploymentTermination,\r\n      CalculationRowType.WorkingTimeCompensation,\r\n      CalculationRowType.Remuneration,\r\n      CalculationRowType.OtherCompensation,\r\n      CalculationRowType.NonProfitOrg,\r\n      CalculationRowType.MealBenefit, // main MealBenefit\r\n      CalculationRowType.Training,\r\n      CalculationRowType.PaidSickLeave,\r\n      CalculationRowType.TimeRatePay,\r\n    ].includes(rowType) && kind) {\r\n      label =  EnumerationsLogic.getEnumLabel(`${irRow.data.calculationRowType}Kind`, kind, null, null);\r\n    }\r\n    return label || EnumerationsLogic.getEnumLabel(\"CalculationRowType\", rowType, null, null);\r\n\r\n  }\r\n\r\n  /** Returns label for type or result. */\r\n  public getTypeLabel(type: PayStatsTypeDefinition): string {\r\n    let label = type.description;\r\n    if (!label)\r\n    {\r\n        label = type.kind + \"/\" + type.periodLength;\r\n    }\r\n    return label;\r\n  }\r\n}","import angular from \"angular\";\r\n\r\nimport { AccountantType, AccountInIndex, Ajax, LegalEntityType, PrimaryPartnerSettings } from \"@salaxy/core\";\r\n\r\nimport { SettingsService, UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Controller for the accountant settings.\r\n */\r\nexport class AccountantController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"AjaxNg1\", \"SettingsService\", \"UiHelpers\"];\r\n\r\n\r\n   /** if true, removing accountant is disabled */\r\n   public removalDisabled: boolean;\r\n\r\n  constructor(private ajax: Ajax, private settingsService: SettingsService, private uiHelpers: UiHelpers) {\r\n  }\r\n\r\n  /**\r\n   * Returns current accountant.\r\n   */\r\n  public get accountant(): PrimaryPartnerSettings {\r\n    if (this.settingsService.current) {\r\n      return this.settingsService.current.partner;\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /** Returns accountant main type */\r\n  public get accountantMainType(): \"company\" | \"none\" {\r\n    return this.getAccountantMainType(this.accountant);\r\n  }\r\n\r\n  /** Shows the edit dialog */\r\n  public showEdit(removalDisabled = false) {\r\n    const accountant: PrimaryPartnerSettings = this.accountant || {\r\n      type: AccountantType.None,\r\n      info: {\r\n        avatar: {},\r\n      },\r\n    };\r\n    const logic = {\r\n      type: this.getAccountantMainType(accountant),\r\n      searchResult: [] as AccountInIndex[],\r\n      isLoading: false,\r\n      removalDisabled,\r\n      selected: this.getAccountantMainType(accountant) == \"company\" ? accountant.info : null,\r\n      select: (item: PrimaryPartnerSettings, row: AccountInIndex) => {\r\n        item.info = row;\r\n        item.type = AccountantType.PendingPrimaryPartner;\r\n        logic.selected = row;\r\n      },\r\n      reset: (item) => {\r\n        logic.selected = null;\r\n        Object.assign(item, accountant);\r\n      },\r\n      search: (search: string) => {\r\n        logic.isLoading = true;\r\n        return this.ajax.getJSON(`/v03/api/settings/partners?search=${encodeURIComponent(search)}`).then((result) => {\r\n          logic.searchResult = result;\r\n          logic.isLoading = false;\r\n          return logic.searchResult;\r\n        });\r\n      },\r\n    };\r\n\r\n    return this.uiHelpers.openEditDialog(\r\n      \"salaxy-components/modals/settings/AccountantSelection.html\",\r\n      accountant,\r\n      logic,\r\n      \"lg\").then((dialog) => {\r\n        if (dialog.result === \"ok\") {\r\n          const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.isSaving\");\r\n\r\n          if (logic.type === \"none\" && (dialog.item.info.avatar.firstName || dialog.item.info.avatar.lastName)) {\r\n            dialog.item.type = AccountantType.None;\r\n            dialog.item.info.avatar.displayName = (dialog.item.info.avatar.firstName + \" \" + dialog.item.info.avatar.lastName).trim();\r\n            dialog.item.info.avatar.color = \"gray\";\r\n            dialog.item.info.avatar.entityType = LegalEntityType.Person;\r\n            dialog.item.info.avatar.initials = (((dialog.item.info.avatar.firstName ?? \"\") + \" \")[0].toUpperCase() + ((dialog.item.info.avatar.lastName ?? \"\") + \" \")[0].toUpperCase()).trim();\r\n          }\r\n\r\n          this.settingsService.current.partner = dialog.item;\r\n          return this.settingsService.save().then(() => {\r\n            loading.dismiss();\r\n            return;\r\n          });\r\n        }\r\n        else if (dialog.result === \"remove\") {\r\n          this.settingsService.current.partner = {\r\n            info: {\r\n              avatar: {},\r\n            },\r\n            type: AccountantType.None,\r\n          };\r\n          const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.isSaving\");\r\n          return this.settingsService.save().then(() => {\r\n              loading.dismiss();\r\n          });\r\n        }\r\n        else if ( dialog.result === \"removePrimaryPartner\") {\r\n          this.showConfirmPartnerRemoval();\r\n          return;\r\n        }\r\n      });\r\n  }\r\n\r\n  /** Removes pricing partner using confirmation dialog. */\r\n  public showConfirmPartnerRemoval() {\r\n    this.uiHelpers.showConfirm(\"SALAXY.NG1.AccountantComponent.showConfirmPartnerRemovalTitle\", \"SALAXY.NG1.AccountantComponent.showConfirmPartnerRemovalDesciption\")\r\n      .then((result) => {\r\n        if (result) {\r\n          this.settingsService.current.partner = {\r\n            info: {\r\n              avatar: {},\r\n            },\r\n            type: AccountantType.None,\r\n          };\r\n          const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.isSaving\");\r\n          return this.settingsService.save().then(() => {\r\n              loading.dismiss();\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n  /** Save current accountant. This mainly for email address. */\r\n  public save(): Promise<void> {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.isSaving\");\r\n    return this.settingsService.save().then(() => {\r\n      loading.dismiss();\r\n      return;\r\n    });\r\n  }\r\n\r\n  private getAccountantMainType(accountant: PrimaryPartnerSettings): \"company\" | \"none\" {\r\n    if (!accountant ||\r\n        !accountant.type ||\r\n        accountant.type === AccountantType.Unknown ||\r\n        accountant.type === AccountantType.None) {\r\n      return \"none\";\r\n    }\r\n\r\n    return \"company\";\r\n\r\n  }\r\n}\r\n","import angular from \"angular\";\r\nimport { AccountingChannel, AccountingTargets, AccountingTargetSettings, Ajax, Configs, ExportMethod, ExternalDialogData } from \"@salaxy/core\";\r\nimport { ExternalDialogConfig, SessionService, SettingsService, UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Handles user interfaces for specifying settings for Payment Channels (and other payment related settings).\r\n */\r\nexport class AccountingChannelSettingsController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"SettingsService\", \"UiHelpers\", \"SessionService\", \"$http\", \"AjaxNg1\"];\r\n\r\n  // Function for closing the settings modal in case we need to close the window programmatically\r\n  // e.g. based on the return value fromt the external dialog.\r\n  private closeFn: (string) => any;\r\n\r\n  private static channelPaths = {\r\n    [AccountingChannel.Procountor]: {}, // Procountor accounting channel is under construction.\r\n    [AccountingChannel.VismaNetvisor]: {\r\n      settings: \"vismanetvisor/settings.html\",\r\n      coa: \"vismanetvisor/coa\",\r\n    },\r\n    [AccountingChannel.VismaFivaldi]: {\r\n      settings: \"vismafivaldi/settings.html\",\r\n      coa: \"vismafivaldi/coa\",\r\n    },\r\n  };\r\n\r\n  constructor(\r\n    private settingsService: SettingsService,\r\n    private uiHelpers: UiHelpers,\r\n    private sessionService: SessionService,\r\n    private $http: angular.IHttpService,\r\n    private ajax: Ajax\r\n  ) {\r\n  }\r\n\r\n  /**\r\n   * Controller initializations\r\n   */\r\n  public $onInit = () => {\r\n    // none\r\n  };\r\n\r\n  /**\r\n   * Returns true if the given accounting target item is an API integration type acccounting\r\n   * target.\r\n   * @param item The accounting target item\r\n   * @returns True or false.\r\n   */\r\n  public isApiIntegration(item: any): boolean {\r\n    return (item?.availableMethods ?? []).indexOf(ExportMethod.Api) > -1 && (\r\n        item?.channel === AccountingChannel.Procountor\r\n        || item?.channel === AccountingChannel.VismaNetvisor\r\n        || item?.channel === AccountingChannel.VismaFivaldi\r\n      );\r\n  }\r\n\r\n  /** Opens the channel setup dialog in a new window. */\r\n  // eslint-disable-next-line @typescript-eslint/no-unused-vars\r\n  public openChannelSetupDialog(target: AccountingTargetSettings, closeFn: (string) => any) {\r\n    if (!target?.channel) {\r\n      return;\r\n    }\r\n\r\n    this.closeFn = closeFn;\r\n\r\n    this.uiHelpers.showExternalDialog(\r\n      target.id,\r\n      this.getAccountingTargetSettingsUrl(target),\r\n      {},\r\n      this.getExternalDialogConfigByTarget(target)\r\n    )\r\n      .then(res => {\r\n        console.log(\"Accounting target settings saved, results = \", res);\r\n        // If handling of return data caused the settings to be saved\r\n        if (this.handleExternalDialogReturnData(target, res)) {\r\n          // Set the updated data also to the original target, otherwise the updates are not\r\n          // reflected on the caller e.g. on a settings page.\r\n          target.data = { ...target.data, ...(res.item as AccountingTargetSettings).data };\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Loads the chart of accounts from the channel.\r\n   * @param target Accounting target.\r\n   * @param closeFn $close function to call.\r\n   */\r\n  public async configureCoa(target: AccountingTargetSettings, closeFn: (string) => any) {\r\n    this.closeFn = closeFn;\r\n    const coa = await this.loadCoaFromChannel(target);\r\n\r\n    if (!coa) {\r\n      // TODO: Should throw/show some error?\r\n      return;\r\n    }\r\n\r\n    navigator.clipboard.writeText(coa);\r\n    // Navigate to accounting targets configuration view.\r\n    this.closeFn(\"close\");\r\n    const ownerId = ((await new AccountingTargets(this.ajax).getOData(null)) as any).items.find(v => v.id === target.id)?.owner;\r\n\r\n    if (this.isAdmin()) {\r\n      window.location.href = `/AccountingTargetDto/Client/${ownerId}/#/accounting-targets/details/${target.id}`;\r\n    } else {\r\n      window.location.href = `./#/accounting-targets/details/${target.id}@${ownerId}`;\r\n    }\r\n  }\r\n\r\n  private async loadCoaFromChannel(target: AccountingTargetSettings): Promise<string> {\r\n    const response = await this.$http.get(this.getCoaUrl(target), { responseType: \"json\" });\r\n    return Object.keys(response.data).reduce((pre, cur) => pre + cur + \";\" + response.data[cur] + \"\\n\", \"\");\r\n  }\r\n\r\n  private getAccountingTargetSettingsUrl(target: AccountingTargetSettings): string {\r\n    const accessToken = this.sessionService.getCurrentToken();\r\n    const url = Configs.current.integrationsServer + \"/\" + AccountingChannelSettingsController.channelPaths[target.channel].settings;\r\n\r\n    return `${url}?accessToken=${accessToken}&accountingTargetId=${target.id}`;\r\n  }\r\n\r\n  private getExternalDialogConfigByTarget(target: AccountingTargetSettings): ExternalDialogConfig {\r\n    switch(target.channel) {\r\n      case AccountingChannel.VismaFivaldi:\r\n        return { height: 810 };\r\n      default:\r\n        return {};\r\n    }\r\n  }\r\n\r\n  private getCoaUrl(target: AccountingTargetSettings): string {\r\n    const accessToken = this.sessionService.getCurrentToken();\r\n    const url = Configs.current.integrationsServer + \"/\" + AccountingChannelSettingsController.channelPaths[target.channel].coa;\r\n\r\n    return `${url}?accessToken=${accessToken}&accountingTargetId=${target.id}`;\r\n  }\r\n\r\n  private handleExternalDialogReturnData(target: AccountingTargetSettings, data: ExternalDialogData<any>): boolean {\r\n    switch(data.action) {\r\n      case \"cancel\":\r\n        break;\r\n      case \"save\":\r\n        if (!angular.equals(target.data, (data.item as AccountingTargetSettings).data)){\r\n          this.saveSettings(data.item);\r\n          return true;\r\n        }\r\n        break;\r\n      default:\r\n        return false;\r\n    }\r\n  }\r\n\r\n  private saveSettings(settings: AccountingTargetSettings) {\r\n    const targetToSave = this.findAccountingTargetFromCompanySettings(settings);\r\n    targetToSave.data = { ...targetToSave.data, ...settings.data };\r\n    this.settingsService.save();\r\n  }\r\n\r\n  private findAccountingTargetFromCompanySettings(target: AccountingTargetSettings): AccountingTargetSettings {\r\n    return this.settingsService.current.accounting?.targets\r\n      .find(v => v.id === target.id);\r\n  }\r\n\r\n  private isAdmin(): boolean {\r\n    const result = !!this.sessionService.clientRoles.find(v => v === \"admin\");\r\n    return result;\r\n  }\r\n\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { AccountingRuleSetAccount, AccountingRuleSetRow, AccountingTarget, AccountingTargetListItem, AccountingTargets, CalculationRowType, IncomeTypesLogic, FileLogic, Tables, FileDelimiter, ImportResult, DataRow, Translations, Language, PaidSickLeaveKind, TrainingKind, EnumerationsLogic, CalcRowsLogic } from \"@salaxy/core\";\r\nimport { EditDialogKnownActions, UiHelpers, SessionService } from \"../../services\";\r\nimport { ApiCrudObjectController } from \"../bases\";\r\n\r\n/**\r\n * UI logic for viewing and adding new (modifying) accounting targets.\r\n * Accounting targets define where the accounting data is sent and how it is mapped to a Chart of Accounts (CoA)\r\n */\r\nexport class AccountingTargetCrudController extends ApiCrudObjectController<AccountingTarget, AccountingTargetListItem> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"AccountingTargets\",\r\n    \"SessionService\",\r\n    \"UiHelpers\",\r\n    \"$location\",\r\n    \"$routeParams\",\r\n    \"$timeout\"\r\n  ];\r\n\r\n  /** If the current item is based on template, it should be here once loaded from server. */\r\n  public template: AccountingTarget;\r\n\r\n  /** import data */\r\n  public rawData: string | null;\r\n  public fileExtension: string | null;\r\n\r\n  public accountFilter = \"all\";\r\n\r\n  public showDistinct = false;\r\n\r\n  public optionTypes = [];\r\n\r\n  private entryCodeGroups = [\r\n    { value: \"incomeType\", text: \"Tulolaji\" },\r\n    { value: \"totalType\", text: \"Laskettu erä\" },\r\n  ];\r\n\r\n  private totalTypes = [\r\n    { value: \"totalPensionWorker\", text: \"Työntekijöiden TyEL-maksut\" },\r\n    { value: \"totalPensionEmployer\", text: \"Työnantajan TyEL-maksu\" },\r\n    { value: \"totalPension\", text: \"TyEL-maksut\" },\r\n    { value: \"totalUnemploymentWorker\", text: \"Työntekijöiden työttömyysvakuutusmaksut\" },\r\n    { value: \"totalUnemploymentEmployer\", text: \"Työnantajan työttömyysvakuutusmaksu\" },\r\n    { value: \"totalUnemployment\", text: \"Työttömyysvakuutusmaksut\" },\r\n    { value: \"totalSocialSecurityEmployer\", text: \"Työnantajan sairausvakuutusmaksu\" },\r\n    { value: \"totalSocialSecurityWorker\", text: \"Työntekijältä erikseen perittävä sairausvakuutusmaksu\" },\r\n    { value: \"totalTax\", text: \"Ennakonpidätykset\" },\r\n    { value: \"totalTaxAtSource\", text: \"Lähdeverot\" },\r\n    { value: \"totalPalkkaus\", text: \"Palkkaus.fi-palkkio\" },\r\n    { value: \"totalWorkerPayment\", text: \"Työntekijän nettopalkka ja kulukorvaukset\" },\r\n    { value: \"totalPayment\", text: \"Maksettu asiakasvaratilille\" },\r\n    { value: \"totalAccidentInsurance\", text: \"Työtapaturma- ja ammattitautivakuutusmaksut\" },\r\n    { value: \"totalGroupLifeInsurance\", text: \"Ryhmähenkivakuutusmaksut\" },\r\n    { value: \"totalAccruedHolidayPay\", text: \"Kertyneet lomapalkat\" },\r\n    { value: \"totalAccruedHolidayBonus\", text: \"Kertyneet lomarahat\" },\r\n    { value: \"totalAccruedHolidaySocialSecurity\", text: \"Kertyneet lomapalkkojen sairausvakuutusmaksut\" },\r\n    { value: \"totalAccruedHolidayPension\", text: \"Kertyneet lomapalkkojen TyEL-maksut\" },\r\n    { value: \"totalAccruedHolidayUnemployment\", text: \"Kertyneet lomapalkkojen työttömyysvakuutusmaksut (TVR)\" },\r\n    { value: \"totalAccruedGroupLifeInsurance\", text: \"Kertyneet lomapalkkojen ryhmähenkivakuutusmaksut\" },\r\n    { value: \"totalAccruedAccidentInsurance\", text: \"Kertyneet lomapalkkojen työtapaturma- ja ammattitautivakuutusmaksut\" },\r\n    { value: \"totalPaidHolidaySalary\", text: \"Maksetut loma-ajan palkat\" },\r\n    { value: \"totalPaidHolidayBonus\", text: \"Maksetut lomarahat\" },\r\n    { value: \"totalPaidHolidayCompensation\", text: \"Maksetut lomakorvaukset\" },\r\n    { value: \"totalPaidHolidaySocialSecurity\", text: \"Maksetut lomapalkkojen sairausvakuutusmaksut\" },\r\n    { value: \"totalPaidHolidayPension\", text: \"Maksetut lomapalkkojen TyEL-maksut\" },\r\n    { value: \"totalPaidHolidayUnemployment\", text: \"Maksetut lomapalkkojen työttömyysvakuutusmaksut (TVR)\" },\r\n  ];\r\n\r\n  private incomeTypes = IncomeTypesLogic.getAll(Translations.getLanguage() as any || Language.Fi).map((x) => ({ value: \"\" + x.code, text: x.code + \" - \" + x.label, title: x.description }));\r\n\r\n  constructor(\r\n    private fullApi: AccountingTargets,\r\n    private sessionService: SessionService,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    private $timeout: angular.ITimeoutService,\r\n  ) { // Dependency injection\r\n    super(fullApi, uiHelpers, $location, $routeParams);\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"/accounting-targets\",\r\n      detailsUrl: this.detailsUrl || \"/accounting-targets/details/\",\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/AccountingTargets.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Additional setup after the item has been loaded.\r\n   * @param item Item that has been loaded\r\n   */\r\n  public setCurrentRef(item: AccountingTarget) {\r\n    super.setCurrentRef(item);\r\n    if (this.current?.ruleSet?.templateId) {\r\n      if (this.current.ruleSet.templateId !== this.template?.ruleSet?.templateId) {\r\n        this.fullApi.getSingle(this.current.ruleSet.templateId).then((result) => {\r\n          this.template = result;\r\n        });\r\n      }\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Shows the detail view for the item.\r\n   * Supports viewing public items from other users as read-only.\r\n   * @param item Item may be either Container or list item.\r\n   */\r\n  public showDetails(item: AccountingTargetListItem | AccountingTarget): angular.ILocationService {\r\n    // TODO: Consider adding this support in super\r\n    if (this.parentController) {\r\n      return this.parentController.showDetails(item);\r\n    }\r\n    return this.$location.url(this.getDefaults().detailsUrl + this.getId(item) + \"@\" + item.owner);\r\n  }\r\n\r\n\r\n  /** Gets entry description */\r\n  public getEntryDescription(row: AccountingRuleSetRow) {\r\n    switch (row.entryCodeGroup) {\r\n      case \"incomeType\":\r\n        return this.entryCodeGroups.find((x) => x.value === row.entryCodeGroup).text + \": \" + this.incomeTypes.find((x) => x.value === row.entryCode).text;\r\n      case \"totalType\":\r\n        return this.entryCodeGroups.find((x) => x.value === row.entryCodeGroup).text + \": \" + this.totalTypes.find((x) => x.value === row.entryCode).text;\r\n    }\r\n    return \"\";\r\n  }\r\n\r\n  /** Selects entry */\r\n  public selectEntry(row: AccountingRuleSetRow) {\r\n    if (row.entryCodeGroup) {\r\n      if (row.entryCodeGroup === \"incomeType\") {\r\n        this.optionTypes = this.incomeTypes;\r\n      } else {\r\n        this.optionTypes = this.totalTypes;\r\n      }\r\n    }\r\n\r\n    const logic = {\r\n      entryCodeGroups: this.entryCodeGroups,\r\n      optionTypes: this.optionTypes,\r\n      currentItem: null as any,\r\n      onEntryCodeGroupChange: (value: string) => {\r\n        if (value === \"incomeType\") {\r\n          logic.optionTypes = this.incomeTypes;\r\n        } else {\r\n          logic.optionTypes = this.totalTypes;\r\n        }\r\n\r\n        // If the code group (ie. the parent typeahead value) changes, clear the entry code.\r\n        if (logic.currentItem) {\r\n          logic.currentItem.entryCode = null;\r\n        }\r\n      }\r\n    };\r\n\r\n    this.uiHelpers.openEditDialog(\r\n      \"salaxy-components/modals/settings/EntryCodes.html\",\r\n      row,\r\n      logic\r\n    ).then((result) => {\r\n      if (result.action == EditDialogKnownActions.Ok && result.item.entryCode && result.item.entryCodeGroup) {\r\n        row.entryCode = result.item.entryCode;\r\n        row.entryCodeGroup = result.item.entryCodeGroup;\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shows the detail view with a new item that is a copy of the given item.\r\n   * Please note that this method supports copying public items from other users. Override is required because the default cannoty copy from other users\r\n   * @param item Item may be either Container or list item.\r\n   */\r\n   public showCopyAsNew(item: AccountingTargetListItem | AccountingTarget): angular.ILocationService {\r\n    if (this.parentController) {\r\n      return this.parentController.showCopyAsNew(item);\r\n    }\r\n    return this.$location.url(this.getDefaults().detailsUrl + this.getId(item) + \"@\" + item.owner + \"/copy-as-new\");\r\n  }\r\n\r\n  /**\r\n   * Creates a copy of the current set\r\n   * Changes the settings so that the accounting target becomes a new item\r\n   * @param copySource Item (container item) to copy as new.\r\n   */\r\n  public copyItem(copySource: AccountingTarget): AccountingTarget {\r\n    const copy = super.copyItem(copySource);\r\n    copy.info.target.avatar.id = null;\r\n    copy.info.target.avatar.displayName = \"Kopio \" + copy.info.target.avatar.displayName;\r\n    copy.ruleSet.templateId = copySource.id + \"@\" + copySource.owner;\r\n    copy.isReadOnly = false;\r\n    copy.ruleSet.targetCoA = angular.copy(copy.ruleSet.accounts);\r\n    return copy;\r\n  }\r\n\r\n  /** Selects the account */\r\n  public selectAccount(row: AccountingRuleSetRow, isCredit: boolean) {\r\n    const accounts = angular.copy(this.current.ruleSet.accounts);\r\n    for (const account of accounts) {\r\n      if (isCredit) {\r\n        (account as any).isSelected = account.id === row.creditId;\r\n      } else {\r\n        (account as any).isSelected = account.id === row.debitId;\r\n      }\r\n    }\r\n\r\n    this.uiHelpers.showDialog(\r\n      \"salaxy-components/report/modals/AccountNumbers.html\",\r\n      null,\r\n      {\r\n        accounts,\r\n      },\r\n    ).then((account) => {\r\n      if (account) {\r\n        if (isCredit) {\r\n          row.creditId = account.id;\r\n        } else {\r\n          row.debitId = account.id;\r\n        }\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Sets selectedAccount\r\n   * @param selectedAccount selectedAccount\r\n   */\r\n  public selectTargetAccount(selectedAccount: AccountingRuleSetAccount) {\r\n    const accounts = angular.copy(this.current.ruleSet.targetCoA);\r\n    for (const account of accounts) {\r\n      (account as any).isSelected = account.account === selectedAccount.account;\r\n    }\r\n\r\n    this.uiHelpers.showDialog(\r\n      \"salaxy-components/report/modals/AccountNumbers.html\",\r\n      null,\r\n      {\r\n        accounts,\r\n      },\r\n    ).then((account) => {\r\n      if (account) {\r\n        selectedAccount.account = account.account;\r\n        selectedAccount.text = account.text;\r\n      }\r\n    });\r\n  }\r\n\r\n  /** Return targetCoA */\r\n  public get hasTargetCoA(): boolean {\r\n    return !!this.current.ruleSet.targetCoA.length;\r\n  }\r\n\r\n  private groupBy<T>(source: T[], getKey: (item: T) => string, sortKeys = false): { [key: string]: T[] } {\r\n    let result = source.reduce((previousValue, currentValue) => {\r\n      const key = getKey(currentValue);\r\n      previousValue[key] = previousValue[key] || [];\r\n      (previousValue[key]).push(currentValue);\r\n      return previousValue;\r\n    }, {});\r\n    if (sortKeys) {\r\n      result = Object.keys(result).sort().reduce((previousValue, key) => {\r\n        previousValue[key] = result[key];\r\n        return previousValue;\r\n      }, {});\r\n    }\r\n    return result;\r\n  }\r\n\r\n  /** Gets the ruleset rouws grouped by account and grouping */\r\n  public get groupedRows(): { [key: string]: AccountingRuleSetRow[] } {\r\n    return this.uiHelpers.cache(this, \"groupedRows\", () => {\r\n      if (!this.current) {\r\n        return null;\r\n      }\r\n      const getKey = (row: AccountingRuleSetRow): string => {\r\n        if (!row.isIncluded) {\r\n          return \"xxxx\";\r\n        }\r\n        const debit = (this.getAccount(row.debitId)?.account || \"9999\") + (row.debitGrouping || \"yyyy\");\r\n        const credit = (this.getAccount(row.creditId)?.account || \"9999\") + (row.creditGrouping || \"yyyy\");\r\n        return (debit + credit) || \"zzzz\";\r\n      };\r\n      return this.groupBy(this.current.ruleSet.rows, getKey, true);\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Get rows based on current ruleSet, account and isDebet\r\n   * @param account iterated account from current.ruleSet.accounts\r\n   * @param isDebet indicates if debet or credit account\r\n   */\r\n  public getRulesetByAccount(account: AccountingRuleSetAccount, isDebet: boolean): AccountingRuleSetRow[] {\r\n    return this.current.ruleSet.rows.filter((row) => isDebet ? row.debitId === account.id : row.creditId === account.id);\r\n  }\r\n\r\n  /** Returns account details */\r\n  public getAccount(id: string) {\r\n    return this.current.ruleSet.accounts.find((x) => x.id === id);\r\n  }\r\n\r\n  /** Adds new account */\r\n  public addAccount(addToEnd = false) {\r\n    const idx = addToEnd ? this.current.ruleSet.accounts.length : 0;\r\n    const copyRow = addToEnd ? this.current.ruleSet.accounts[this.current.ruleSet.accounts.length - 1] : this.current.ruleSet.accounts[0];\r\n    const newRow = {\r\n      isReadOnly: false,\r\n      id: this.newGuid(),\r\n      account: copyRow.account,\r\n      text: copyRow.text,\r\n    };\r\n    this.current.ruleSet.accounts.splice(idx, 0, newRow);\r\n  }\r\n\r\n  /**\r\n   * Add new account to TargetCoA\r\n   * @param addToEnd tells if adds to end of array or not\r\n   */\r\n  public addTargetCoaAccount(addToEnd = false) {\r\n    const idx = addToEnd ? this.current.ruleSet.targetCoA.length : 0;\r\n    const copyRow = addToEnd ? this.current.ruleSet.targetCoA[this.current.ruleSet.targetCoA.length - 1] : this.current.ruleSet.targetCoA[0];\r\n    const newRow = {\r\n      isReadOnly: false,\r\n      id: this.newGuid(),\r\n      account: copyRow.account,\r\n      text: copyRow.text,\r\n    };\r\n    this.current.ruleSet.targetCoA.splice(idx, 0, newRow);\r\n  }\r\n\r\n  /** Removes the account */\r\n  public removeAccount(row: AccountingRuleSetAccount, removeFromTargetCoa = false) {\r\n    if (!row.isReadOnly) {\r\n      if (removeFromTargetCoa) {\r\n        const idx = this.current.ruleSet.targetCoA.findIndex((x) => x === row);\r\n        this.current.ruleSet.targetCoA.splice(idx, 1);\r\n      } else {\r\n        // TODO: Consider adding a check if the account is in use in some of the derived rulesets. Perhaps in saving?\r\n        if (this.current.ruleSet.rows.some((r) => r.creditId === row.id || r.debitId === row.id)) {\r\n          this.uiHelpers.showAlert(\"Tiliä ei voi poistaa\", \"Tili on käytössä tiliöintimallissa.\");\r\n          return;\r\n        }\r\n        const idx = this.current.ruleSet.accounts.findIndex((x) => x.id === row.id);\r\n        this.current.ruleSet.accounts.splice(idx, 1);\r\n\r\n      }\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Validated row input\r\n   * @param row Row to be validated\r\n   */\r\n  public isValidAccount(row: AccountingRuleSetAccount): boolean {\r\n    if (!this.current.ruleSet.targetCoA.length) {\r\n      return true;\r\n    }\r\n    return !!this.current.ruleSet.targetCoA.find((x) => x.account.toString() === row.account.toString());\r\n  }\r\n\r\n  /** Adds a new row */\r\n  public addRow(row: AccountingRuleSetRow, addToStart = false) {\r\n    const idx = row ? this.current.ruleSet.rows.findIndex((x) => x.id === row.id) : this.current.ruleSet.rows.length;\r\n    const copyRow = row || (addToStart ? this.current.ruleSet.rows[0] : this.current.ruleSet.rows[this.current.ruleSet.rows.length - 1]);\r\n    const newRow = {\r\n      isReadOnly: false,\r\n      enabled: copyRow.enabled,\r\n      id: this.newGuid(),\r\n      entryCodeGroup: copyRow.entryCodeGroup,\r\n      entryCode: copyRow.entryCode,\r\n      isIncluded: copyRow.isIncluded,\r\n      debitId: copyRow.debitId,\r\n      debitGrouping: copyRow.debitGrouping,\r\n      creditId: copyRow.creditId,\r\n      creditGrouping: copyRow.creditGrouping,\r\n      flags: angular.copy(copyRow.flags),\r\n    };\r\n    this.current.ruleSet.rows.splice(addToStart ? 0 : idx, 0, newRow);\r\n  }\r\n\r\n  /** Removes the row */\r\n  public removeRow(row: AccountingRuleSetRow) {\r\n    const idx = this.current.ruleSet.rows.findIndex((x) => x.id === row.id);\r\n    if (!row.isReadOnly) {\r\n      this.current.ruleSet.rows.splice(idx, 1);\r\n    }\r\n  }\r\n\r\n  /** Selects flags */\r\n  public selectFlags(row: AccountingRuleSetRow) {\r\n    this.uiHelpers.openEditDialog(\r\n      \"salaxy-components/modals/settings/Flags.html\",\r\n      row,\r\n      {\r\n        getFlagText: (flag: string) => this.getFlagText(flag),\r\n        addFlag: (current: AccountingRuleSetRow) => {\r\n          const newFlag =  {\r\n            prefix: \"\",\r\n            value: \"\",\r\n            kind: \"\",\r\n            dimensionValue: \"\",\r\n          };\r\n          const logic =\r\n            {\r\n              _userDefinedRow:{\r\n                item: null,\r\n                row: {\r\n                  data: {\r\n                    get kind() {\r\n                      return logic._userDefinedRow.item.kind;\r\n                    },\r\n                    set kind(value) {\r\n                      logic._userDefinedRow.item.kind = value;\r\n                    },\r\n                  },\r\n                  get rowType() {\r\n                    if (logic._userDefinedRow.item.prefix == \"type\") {\r\n                      return logic._userDefinedRow.item._value;\r\n                    }\r\n                    else\r\n                    {\r\n                      return logic._userDefinedRow.item.value;\r\n                    }\r\n                  },\r\n                  set rowType(value) {\r\n                    if (logic._userDefinedRow.item.prefix == \"type\") {\r\n                      logic._userDefinedRow.item._value = value;\r\n                    }\r\n                    else\r\n                    {\r\n                      logic._userDefinedRow.item.value = value;\r\n                    }\r\n                  },\r\n                  get type() {\r\n                    if (logic._userDefinedRow.item.prefix == \"type\") {\r\n                      return logic._userDefinedRow.item.value;\r\n                    }\r\n                    else\r\n                    {\r\n                      return logic._userDefinedRow.item._value;\r\n                    }\r\n                  },\r\n                  set type(value) {\r\n                    if (logic._userDefinedRow.item.prefix == \"type\") {\r\n                      logic._userDefinedRow.item.value = value;\r\n                    }\r\n                    else\r\n                    {\r\n                      logic._userDefinedRow.item._value = value;\r\n                    }\r\n                  }\r\n                }\r\n              },\r\n              asUserDefinedRow: (item ) => {\r\n                logic._userDefinedRow.item = item;\r\n                return logic._userDefinedRow.row;\r\n              },\r\n              pensionCalculation: EnumerationsLogic.getEnumMetadata(\"PensionCalculation\").values.map( x => ({ text: x.label, value: x.name })).concat({ value: \"entrepreneurLike\", text: \"Sovellettava eläketurva: yrittäjä\" }),\r\n              selfPayment: [\r\n                { text: \"SALAXY.ENUM.InvoiceType.net.label\", value: \"net\"},\r\n                { text: \"SALAXY.ENUM.InvoiceType.tax.label\", value: \"tax\"},\r\n                { text: \"SALAXY.ENUM.InvoiceType.pension.label\", value: \"pension\"},\r\n                { text: \"SALAXY.ENUM.InvoiceType.unemployment.label\", value: \"unemployment\"}\r\n              ],\r\n              dimension: (this.sessionService.session?.settings?.costAccounting?.dimensions ?? []).map(x => ({ text: x.label, value: x.id })),\r\n              prefixOptions: [\r\n                { text: \"SALAXY.NG1.EmploymentRelation.employmentRelation\", value: \"employmentType\" },\r\n                { text: \"SALAXY.NG1.WorkerWizardComponent.employment.pension.title\", value: \"pensionCalculation\" },\r\n                { text: \"SALAXY.NG1.CalcRowTypeComponent.rowType\", value: \"rowType\" },\r\n                { text: \"SALAXY.NG1.CalcRowTypeComponent.wageType\", value: \"type\" },\r\n                { text: \"SALAXY.MODEL.CostAccountingSettings.title\", value: \"dimension\" },\r\n                { text: \"SelfPayment\", value: \"selfPayment\" },\r\n                { text: \"Behavior\", value: \"behavior\" },\r\n                { text: \"Regex\", value: \"regex\" },\r\n              ]\r\n             };\r\n          this.uiHelpers.openEditDialog(\r\n            \"salaxy-components/modals/settings/FlagSelection.html\",\r\n             newFlag,\r\n             logic,\r\n            ).then((addFlagResult) => {\r\n              if (addFlagResult.action == EditDialogKnownActions.Ok) {\r\n                if (addFlagResult.item.prefix == \"type\") {\r\n                  if (addFlagResult.item.kind) {\r\n                    current.flags.push(addFlagResult.item.prefix + \".\" + addFlagResult.item.value + \"/\" + addFlagResult.item.kind);\r\n                  }\r\n                  else {\r\n                    current.flags.push(addFlagResult.item.prefix + \".\" + addFlagResult.item.value);\r\n                  }\r\n                }\r\n                else if (addFlagResult.item.prefix == \"rowType\") {\r\n                  if (addFlagResult.item.kind) {\r\n                    current.flags.push(addFlagResult.item.prefix + \".\" + addFlagResult.item.value + \".\" + addFlagResult.item.kind);\r\n                  }\r\n                  else {\r\n                    current.flags.push(addFlagResult.item.prefix + \".\" + addFlagResult.item.value);\r\n                  }\r\n                }\r\n                else if (addFlagResult.item.prefix == \"dimension\") {\r\n                    current.flags.push(addFlagResult.item.prefix + \".\" + addFlagResult.item.value + \".\" + addFlagResult.item.dimensionValue);\r\n                }\r\n                else\r\n                {\r\n                  current.flags.push(addFlagResult.item.prefix + \".\" + addFlagResult.item.value);\r\n                }\r\n              }\r\n            });\r\n        },\r\n      }\r\n    ).then((result) => {\r\n      if (result.action == EditDialogKnownActions.Ok) {\r\n        row.flags = result.item.flags.filter(x => !!x);\r\n      }\r\n    });\r\n  }\r\n\r\n  /** Paste data from clipboard. */\r\n  public pasteFromClipboard(): Promise<string> {\r\n    this.rawData = null;\r\n    this.fileExtension = null;\r\n    return (navigator as any).clipboard.readText().then((text) => {\r\n      this.rawData = text;\r\n      this.import();\r\n      // Ensure refresh in UI\r\n      return this.$timeout(() => {\r\n        return this.rawData;\r\n      });\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Reads the file\r\n   * @param file Selected file\r\n   */\r\n  public readFile(file: File): Promise<string> {\r\n    this.rawData = null;\r\n    this.fileExtension = null;\r\n    if (!file) {\r\n      return Promise.resolve(null);\r\n    }\r\n    // TODO detect if excel file and read content using Excel reader.\r\n    if (file.name) {\r\n      this.fileExtension = FileLogic.getExtensionFromFileName(file.name);\r\n    }\r\n\r\n    const read = new Promise<string>((resolve, reject) => {\r\n      const reader = new FileReader();\r\n      reader.onloadend = () => {\r\n        resolve(reader.result as string);\r\n      };\r\n      reader.onerror = () => reject;\r\n      reader.readAsText(file);\r\n    });\r\n\r\n    return read.then((text) => {\r\n      this.rawData = text;\r\n      this.import();\r\n      // Ensure refresh in UI\r\n      return this.$timeout(() => {\r\n        return text;\r\n      });\r\n    });\r\n\r\n  }\r\n\r\n  /**\r\n   * Import data\r\n   */\r\n  public import(): void {\r\n    let tableData: ImportResult<DataRow> = null;\r\n    if (this.fileExtension && this.fileExtension === \"xlsx\") {\r\n      this.uiHelpers.showAlert(\"Tiedoston muotoa ei tueta\", \"Excel-tiedostot eivät ole vielä tuettuja. Tallenna Excel-taulukko csv-muodossa tai kopioi taulukko leikepöydän kautta.\");\r\n      return;\r\n    }\r\n    const fileDelimeter = FileLogic.getFileDelimiter(this.rawData);\r\n    if (fileDelimeter === FileDelimiter.Unknown) {\r\n      this.uiHelpers.showAlert(\"Tiedoston muotoa ei tueta\", \"Virheellinen\");\r\n      return;\r\n    }\r\n    const firstRow = Tables.getFirstRow(this.rawData, fileDelimeter);\r\n    if (!firstRow.length) {\r\n      this.uiHelpers.showAlert(\"Tiedoston rivejä ei voida lukea\", \"Virheellinen\");\r\n      return;\r\n    }\r\n\r\n    const keys = Object.keys(firstRow);\r\n    const headers = !/\\d/.test(firstRow[keys[0]]) && !/\\d/.test(firstRow[keys[1]]) ? null : [\"aaaa\", \"bbbb\"];\r\n    tableData = Tables.import(this.rawData, FileLogic.getTableFormatByDelimeter(fileDelimeter), FileLogic.getCsvLocale(fileDelimeter), headers);\r\n\r\n\r\n    const validation = this.validateTableData(tableData);\r\n    if (validation.validationSuccess) {\r\n      const mappingResult = tableData.data.map((item) => {\r\n        return { account: item[validation.account].toString(), text: item[validation.text] } as AccountingRuleSetAccount;\r\n      });\r\n\r\n      if (this.current.ruleSet.targetCoA.length) {\r\n        this.uiHelpers.showConfirm(\"Tilikartan päivitys\", \"Haluatko korvata aikaisemman tilikarttasi tuodulla\", \"Kyllä\", \"En\").then((result) => {\r\n          if (result) {\r\n            this.current.ruleSet.targetCoA = mappingResult;\r\n          }\r\n        });\r\n      } else {\r\n        this.current.ruleSet.targetCoA = mappingResult;\r\n      }\r\n\r\n    } else {\r\n      this.uiHelpers.showAlert(\"Tiedoston muotoa ei tueta\", \"Virheellinen\");\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Sort accounts\r\n   */\r\n  public sortRulesetAccounts(): void {\r\n    this.current.ruleSet.accounts.sort((a, b) => {\r\n      if (a.account > b.account) {\r\n        return 1;\r\n      }\r\n\r\n      if (a.account < b.account) {\r\n        return -1;\r\n      }\r\n\r\n      return 0;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Updates ruleSet account with provided targetCoA account\r\n   * @param targetCoaAccount targetCoA account\r\n   */\r\n  public updateRuleSetAccount(targetCoaAccount: AccountingRuleSetAccount) {\r\n    const item = this.current.ruleSet.accounts.find(x => x.account === targetCoaAccount.account);\r\n    if (item) {\r\n      item.text = targetCoaAccount.text;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Updates provided account text to match targetCoa account\r\n   * @param rulesetAccount ruleSet account\r\n   */\r\n  public updateAccountToMatchTargetCoa(rulesetAccount: AccountingRuleSetAccount) {\r\n    const item = this.current.ruleSet.targetCoA.find(x => x.account === rulesetAccount.account);\r\n    if (item) {\r\n      rulesetAccount.text = item.text;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Return account text to ui\r\n   */\r\n   public get accountFilterText() {\r\n    switch (this.accountFilter) {\r\n      case \"all\":\r\n        return \"SALAXY.NG1.AccountingTargetDetailsComponent.filters.all\";\r\n      case \"includedAndEnabled\":\r\n        return \"SALAXY.NG1.AccountingTargetDetailsComponent.filters.includedAndEnabled\";\r\n      case \"error\":\r\n        return \"SALAXY.NG1.AccountingTargetDetailsComponent.filters.error\";\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Filter accounts\r\n   */\r\n  public get filteredAccounts(): AccountingRuleSetAccount[] {\r\n    switch(this.accountFilter) {\r\n      case \"all\":\r\n        return this.current.ruleSet.accounts;\r\n      case \"includedAndEnabled\":\r\n        return this.current.ruleSet.accounts.filter(account => this.current.ruleSet.rows.find(x => x.enabled && x.isIncluded && (x.debitId === account.id || x.creditId === account.id)));\r\n      case \"error\":\r\n        return this.current.ruleSet.accounts.filter(x => !this.current.ruleSet.targetCoA.map(item => { return item.account; }).includes(x.account));\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Get accounting rules acount for distinct view\r\n   * @param account account id\r\n   * @returns rules count as number\r\n   */\r\n  public getRulesCount(account: string): number {\r\n    const ids = this.current.ruleSet.accounts.filter(x => x.account === account).map(x => x.id);\r\n    switch(this.accountFilter) {\r\n      case \"all\":\r\n      case \"error\":\r\n        return this.current.ruleSet.rows.filter(x => ids.indexOf(x.debitId) >= 0 || ids.indexOf(x.creditId) >= 0).length;\r\n      case \"includedAndEnabled\":\r\n          return this.current.ruleSet.rows.filter(x => x.enabled && x.isIncluded && (ids.indexOf(x.debitId) >= 0  || ids.indexOf(x.creditId) >= 0)).length;\r\n    }\r\n  }\r\n\r\n  /** Returns flag text */\r\n  public getFlagText(flag: string): {found: boolean, text: string} {\r\n    if (!flag) {\r\n      return { found: false, text: null };\r\n    }\r\n    const legacyFlagDescription = this.legacyFlags.find((x) => x.value === flag);\r\n    if (legacyFlagDescription) {\r\n      return { found: true, text: legacyFlagDescription.text };\r\n    }\r\n\r\n    const flagParts = flag.split(\".\");\r\n    let text = \"\";\r\n    switch (flagParts[0]) {\r\n      case \"employmentType\":\r\n        {\r\n          text = EnumerationsLogic.getEnumLabel(\"EmploymentRelationType\", flagParts[1]);\r\n        }\r\n        break;\r\n      case \"pensionCalculation\":\r\n        {\r\n          if (flagParts[1] == \"entrepereurLike\") {\r\n            text = \"Sovellettava eläketurva: yrittäjä\";\r\n          } else {\r\n            text = EnumerationsLogic.getEnumLabel(\"PensionCalculation\", flagParts[1]);\r\n          }\r\n        }\r\n        break;\r\n      case \"rowType\":\r\n        {\r\n          if (flagParts.length > 2) {\r\n            text = this.getCalculationRowTypeLabel(flagParts[1] as CalculationRowType, flagParts[2]);\r\n          }\r\n          else {\r\n            text = this.getCalculationRowTypeLabel(flagParts[1] as CalculationRowType, null);\r\n          }\r\n        }\r\n        break;\r\n      case \"type\":\r\n        {\r\n          text = flag.replace(\"type.\",\"\");\r\n        }\r\n        break;\r\n      case \"dimension\":\r\n        {\r\n          text = flag.replace(\"dimension.\",\"\");\r\n        }\r\n        break;\r\n      case \"selfPayment\":\r\n        {\r\n          text = EnumerationsLogic.getEnumLabel(\"InvoiceType\", flagParts[1]);\r\n          if (text) {\r\n            text = \"Self payment: \" + text;\r\n          }\r\n        }\r\n        break;\r\n      case \"behavior\":\r\n          {\r\n            text = EnumerationsLogic.getEnumLabel(\"CalculationFlag\", flagParts[1]);\r\n          }\r\n          break;\r\n      case \"regex\":\r\n        {\r\n          text = flag.replace(\"regex.\",\"\");\r\n        }\r\n        break;\r\n      default:\r\n        break;\r\n      }\r\n\r\n    if (text) {\r\n      return {found: true, text };\r\n    }\r\n\r\n    return {found: false, text: flag };\r\n  }\r\n\r\n  /**\r\n   * Created distinct object array with account key\r\n   */\r\n  public get distinctAccounts(): AccountingRuleSetAccount[] {\r\n    return [...new Map(this.filteredAccounts.map(item => [item[\"account\"], item])).values()];\r\n  }\r\n\r\n  /**\r\n   * Acount number of digits in account candidate\r\n   */\r\n  private countDigits(accountCandidate: string): number {\r\n    const digitsArr = accountCandidate.match(/\\d+/g);\r\n    if (digitsArr) {\r\n      return digitsArr.join(\"\").length;\r\n    }\r\n    return 0;\r\n  }\r\n\r\n  /**\r\n   * Validated generated Tables data\r\n   * @returns is TableData valid\r\n   */\r\n  private validateTableData(tableData: ImportResult<DataRow>): { validationSuccess: boolean, account: string, text: string } {\r\n    //Validate if data exists\r\n    if (!tableData.data) {\r\n      return { validationSuccess: false, account: null, text: null };\r\n    }\r\n\r\n    //Validate errors\r\n    if (tableData.errors.length !== 0) {\r\n      return { validationSuccess: false, account: null, text: null };\r\n    }\r\n\r\n    // Validate data array\r\n    if (tableData.data && tableData.data.length < 1) {\r\n      return { validationSuccess: false, account: null, text: null };\r\n    }\r\n\r\n    // Validate first data array entry key and value\r\n    for (const [key, value] of Object.entries(tableData.data[0])) {\r\n      if (key.length < 2 || value.length < 2) {\r\n        return { validationSuccess: false, account: null, text: null };\r\n      }\r\n    }\r\n\r\n    // Validate numeric field\r\n    for (const item of tableData.data) {\r\n      const keys = Object.keys(item);\r\n      // Check if item[keys[0]] or item[keys[0]] containt digits\r\n      // If no return validation false\r\n      // otherwise return validationSuccess true and figure out account and text\r\n      const firstKey = this.countDigits(item[keys[0]].toString());\r\n      const secondKey = this.countDigits(item[keys[1]].toString());\r\n      return !/\\d/.test(item[keys[0]]) && !/\\d/.test(item[keys[1]]) ? { validationSuccess: false, account: null, text: null } : { validationSuccess: true, account: firstKey > secondKey ? keys[0] : keys[1], text: firstKey > secondKey ? keys[1] : keys[0] };\r\n    }\r\n  }\r\n  private newGuid(): string {\r\n    let dt = new Date().getTime();\r\n    const uuid = \"xxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxx\".replace(/[xy]/g, (c) => {\r\n      /* eslint-disable-next-line no-bitwise */\r\n      const r = (dt + Math.random() * 16) % 16 | 0;\r\n      dt = Math.floor(dt / 16);\r\n      /* eslint-disable-next-line no-bitwise */\r\n      return (c === \"x\" ? r : (r & 0x3 | 0x8)).toString(16);\r\n    });\r\n    return uuid;\r\n  }\r\n\r\n  private legacyFlags = [\r\n    { value: \"customerSelfPayment\", text: \"Työnantaja hoitaa\" },\r\n    { value: \"cfDeductionAtSalaxy\", text: \"Palkkaus pidättää\" },\r\n\r\n    { value: \"incomeEarnerEntrepreneur\", text: \"Sovellettava eläketurva: yrittäjä\" },\r\n\r\n    { value: `${CalculationRowType.Expenses}`, text: \"Palkkalaji: Kulukorvaus\" },\r\n    { value: `${CalculationRowType.PrepaidExpenses}`, text: \"Palkkalaji: Kulukorvausennakko\" },\r\n    { value: `${CalculationRowType.Foreclosure}`, text: \"Palkkalaji: Ulosotto\"},\r\n    { value: `${CalculationRowType.UnionPayment}`, text: \"Palkkalaji: AY-jäsenmaksu\" },\r\n    { value: `${CalculationRowType.Advance}`, text: \"Palkkalaji: Palkkaennakko\" },\r\n    { value: `${CalculationRowType.Service}`, text: \"Palkkalaji: Palvelumaksu\" },\r\n    { value: `${CalculationRowType.HolidaySalary}`, text: \"Palkkalaji: Loma-ajan palkka\" },\r\n    { value: `${CalculationRowType.PaidSickLeave}.${PaidSickLeaveKind.PaidSickLeaveSalary}`, text: \"Palkkalaji: Palkallinen sairauspoissaolo, kertakorvaus\"},\r\n    { value: `${CalculationRowType.PaidSickLeave}.${PaidSickLeaveKind.PaidSickLeaveHourlySalary}`, text: \"Palkkalaji: Palkallinen sairauspoissaolo, tuntipalkka\" },\r\n    { value: `${CalculationRowType.PaidSickLeave}.${PaidSickLeaveKind.PaidSickLeaveMonthlySalary}`, text: \"Palkkalaji: Palkallinen sairauspoissaolo, kuukausipalkka\" },\r\n    { value: `${CalculationRowType.Training}.${TrainingKind.TrainingSalary}`, text: \"Palkkalaji: Koulutusaika, kertakorvaus\" },\r\n    { value: `${CalculationRowType.Training}.${TrainingKind.TrainingHourlySalary}`, text: \"Palkkalaji: Koulutusaika, tuntipalkka\"},\r\n    { value: `${CalculationRowType.Training}.${TrainingKind.TrainingMonthlySalary}`, text: \"Palkkalaji: Koulutusaika, kuukausipalkka\" },\r\n    { value: `${CalculationRowType.DeductibleOfExerciseAndCultureBenefit}`, text: \"Palkkalaji: Liikunta- ja kulttuuri-edun omavastuu\" },\r\n  ];\r\n\r\n  private getCalculationRowTypeLabel(rowType: CalculationRowType, kind: string): string {\r\n    let label = \"\";\r\n    if (rowType === CalculationRowType.IrIncomeType) {\r\n      label = IncomeTypesLogic.getAll(null).find( (x) => (kind && x.transactionCode === kind))?.label;\r\n    }\r\n    else if (kind) {\r\n      const rowConfig = CalcRowsLogic.getRowConfig(rowType);\r\n      label =  EnumerationsLogic.getEnumLabel(rowConfig.kind.name, kind, null, null);\r\n    }\r\n    return label || EnumerationsLogic.getEnumLabel(\"CalculationRowType\", rowType, null, null);\r\n\r\n  }\r\n}\r\n","import angular from \"angular\";\r\nimport { AccountingTargetListItem, AccountingTargetSettings, CompanyAccountSettings, Dates, InputEnumOption, InsuranceContract, PensionContract, SettingsLogic, SettingsStatus, Years, InvoicesLogic, Usecase, UsecaseListItem, ApiItemType, Arrays, ExportMethod, WorkerSalarySlipDeliveryMethod, Configs, Ajax, PaymentChannel } from \"@salaxy/core\";\r\nimport { SessionService, SettingsService, UiHelpers } from \"../../services\";\r\n\r\ntype SettingsSection = \"pensionContracts\" |\r\n  \"yelPensionContracts\" |\r\n  \"insuranceContracts\" |\r\n  \"incomesRegister\" |\r\n  \"eInvoice\" |\r\n  \"sepa\" |\r\n  \"taxAndSocialSecuritySelfHandling\" |\r\n  \"workerSelfHandling\" |\r\n  \"unemploymentSelfHandling\" |\r\n  \"payslip\" |\r\n  \"omapalkka\";\r\n/**\r\n * Controller for the accountant settings.\r\n */\r\nexport class CompanySettingsController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"SessionService\", \"SettingsService\", \"UiHelpers\", \"AjaxNg1\", \"$sce\"];\r\n\r\n  /** If true, current item is read only */\r\n  public isReadOnlyForced: boolean;\r\n\r\n  /** Possibility to restrict sections that are visible in settings. */\r\n  public sections: SettingsSection[];\r\n\r\n  /** Yearly sidecosts */\r\n  public sideCosts = Years.getYearlyChangingNumbers(new Date()).sideCosts;\r\n\r\n  /** The current editable settings */\r\n  private _current: CompanyAccountSettings;\r\n\r\n  private _irCertificate: any = null;\r\n\r\n  private _openAiKey: string = null;\r\n\r\n  private saves: { [key: string]: boolean } = {};\r\n\r\n  constructor(private sessionService: SessionService, private settingsService: SettingsService, private uiHelpers: UiHelpers, private ajax: Ajax, private $sce: angular.ISCEService) {\r\n  }\r\n\r\n  /**\r\n   * Initializes the controller\r\n   */\r\n  public $onInit() {\r\n    this.sections = this.sections || [\"pensionContracts\", \"yelPensionContracts\", \"insuranceContracts\", \"incomesRegister\", \"payslip\", \"omapalkka\"];\r\n    this._openAiKey = window.localStorage.getItem(\"openAiKey\") || \"\";\r\n  }\r\n\r\n  /** Copy current from SettingsService */\r\n  public get current(): CompanyAccountSettings {\r\n    if (!this._current && this.settingsService.current) {\r\n      this._current = angular.copy(this.settingsService.current);\r\n    }\r\n    return this._current;\r\n  }\r\n\r\n\r\n  /** Returns current pension contracts once loaded assuring there is at least one active item. */\r\n  public get pensionContracts(): PensionContract[] | null {\r\n    if (!this.current) {\r\n      return null;\r\n    }\r\n    if (!CompanySettingsController.getActive(this.current.calc.pensionContracts)) {\r\n      this.current.calc.pensionContracts.push({});\r\n    }\r\n    return this.current.calc.pensionContracts;\r\n  }\r\n\r\n  /** Returns current insurance contracts once loaded assuring there is at least one active item. */\r\n  public get insuranceContracts(): InsuranceContract[] | null {\r\n    if (!this.current) {\r\n      return null;\r\n    }\r\n    if (!CompanySettingsController.getActive(this.current.calc.insuranceContracts)) {\r\n      this.current.calc.insuranceContracts.push({});\r\n    }\r\n    return this.current.calc.insuranceContracts;\r\n  }\r\n\r\n  /**\r\n   * Returns current default accounting target.\r\n   */\r\n  public get defaultAccountingTarget(): AccountingTargetSettings {\r\n    if (!this.current?.accounting?.targets || !this.current?.accounting?.defaultTargetId) {\r\n      return null;\r\n    }\r\n    return this.current.accounting.targets.find((x) => x.id == this.current?.accounting.defaultTargetId);\r\n  }\r\n\r\n  /**\r\n   * Returns true, if the contract should be visible:\r\n   * Companies: All pending contracts and first active contract.\r\n   * Personal: The first active contract, no pending contracts.\r\n   * @param contract Contract to evaluate\r\n   * @param allContracts Collection of contracts that contain the contract to evaluate.\r\n   */\r\n  public isVisibleContract<ContractType extends PensionContract | InsuranceContract>(contract: ContractType, allContracts: ContractType[]): boolean {\r\n    if (contract.status === SettingsStatus.Pending) {\r\n      // Show all pending for companies. For households, this is an error / legacy.\r\n      return this.sessionService.isInRole(\"company\") ? true : false;\r\n    }\r\n    return contract === CompanySettingsController.getActive(allContracts);\r\n  }\r\n\r\n  /** Gets the relevant contracts that are shown in personal (household) userinterface. */\r\n  public get personal(): {\r\n    insurance: InsuranceContract,\r\n    pension: PensionContract,\r\n  } {\r\n    const result = {\r\n      insurance: null,\r\n      pension: null,\r\n    };\r\n    if (!this.current) {\r\n      return result;\r\n    }\r\n    result.insurance = CompanySettingsController.getActive(this.insuranceContracts);\r\n    result.pension = CompanySettingsController.getActive(this.pensionContracts);\r\n    return result;\r\n  }\r\n\r\n  /** Returns OPEN AI Key */\r\n  public get openAiKey(): string {\r\n    return this._openAiKey;\r\n  }\r\n\r\n  /** Sets OPEN AI Key */\r\n  public set openAiKey(value: string) {\r\n    this._openAiKey = value;\r\n  }\r\n\r\n  /** Saves open AI Key */\r\n  public saveOpenAiKey() {\r\n    window.localStorage.setItem(\"openAiKey\", this._openAiKey || \"\");\r\n  }\r\n\r\n  /**\r\n   * Saves changes for settings\r\n   * @param section Section to save: Copies only that section to settingsService.\r\n   * Null saves nothing.\r\n   */\r\n  public save(section: SettingsSection | \"all\" | null) {\r\n    switch (section) {\r\n      case \"pensionContracts\":\r\n        this.settingsService.current.calc.pensionContracts = angular.copy(this.current.calc.pensionContracts);\r\n        this.settingsService.current.payments.customerFunds.isPensionSelfHandling = this.current.payments.customerFunds.isPensionSelfHandling;\r\n        break;\r\n      case \"insuranceContracts\":\r\n        this.settingsService.current.calc.insuranceContracts = angular.copy(this.current.calc.insuranceContracts);\r\n        break;\r\n      case \"incomesRegister\":\r\n        this.settingsService.current.calc.incomesRegister = angular.copy(this.current.calc.incomesRegister);\r\n        break;\r\n      case \"eInvoice\":\r\n        this.settingsService.current.payments.invoice.eInvoiceReceiver = this.current.payments.invoice.eInvoiceReceiver;\r\n        this.settingsService.current.payments.invoice.eInvoiceIntermediator = this.current.payments.invoice.eInvoiceIntermediator;\r\n        break;\r\n      case \"sepa\":\r\n        this.settingsService.current.payments.invoice.sepaBankPartyId = this.current.payments.invoice.sepaBankPartyId;\r\n        this.settingsService.current.payments.invoice.ibanNumber = this.current.payments.invoice.ibanNumber;\r\n        break;\r\n      case \"taxAndSocialSecuritySelfHandling\":\r\n        this.settingsService.current.payments.customerFunds.isTaxAndSocialSecuritySelfHandling = this.current.payments.customerFunds.isTaxAndSocialSecuritySelfHandling;\r\n        break;\r\n      case \"workerSelfHandling\":\r\n        this.settingsService.current.payments.customerFunds.isWorkerSelfHandling = this.current.payments.customerFunds.isWorkerSelfHandling;\r\n        break;\r\n      case \"unemploymentSelfHandling\":\r\n        return;\r\n      case \"payslip\": {\r\n        const methods = this.settingsService.current.messaging.workerSalarySlipDeliveryMethods.filter(x => x !== WorkerSalarySlipDeliveryMethod.Payslip);\r\n        this.settingsService.current.messaging.workerSalarySlipDeliveryMethods.splice(0, this.settingsService.current.messaging.workerSalarySlipDeliveryMethods.length);\r\n        this.settingsService.current.messaging.workerSalarySlipDeliveryMethods.push(...methods);\r\n        if (this.current.messaging.workerSalarySlipDeliveryMethods.indexOf(WorkerSalarySlipDeliveryMethod.Payslip) > -1) {\r\n          this.settingsService.current.messaging.workerSalarySlipDeliveryMethods.push(WorkerSalarySlipDeliveryMethod.Payslip);\r\n        }\r\n        break;\r\n      }\r\n      case \"omapalkka\": {\r\n        const methods = this.settingsService.current.messaging.workerSalarySlipDeliveryMethods.filter(x => x !== WorkerSalarySlipDeliveryMethod.Omapalkka);\r\n        this.settingsService.current.messaging.workerSalarySlipDeliveryMethods.splice(0, this.settingsService.current.messaging.workerSalarySlipDeliveryMethods.length);\r\n        this.settingsService.current.messaging.workerSalarySlipDeliveryMethods.push(...methods);\r\n        if (this.current.messaging.workerSalarySlipDeliveryMethods.indexOf(WorkerSalarySlipDeliveryMethod.Omapalkka) > -1) {\r\n          this.settingsService.current.messaging.workerSalarySlipDeliveryMethods.push(WorkerSalarySlipDeliveryMethod.Omapalkka);\r\n        }\r\n        break;\r\n      }\r\n      case \"all\":\r\n        this.settingsService.current = angular.copy(this.current);\r\n        break;\r\n    }\r\n    if (section) {\r\n      this.saves[section] = true;\r\n      this.settingsService.save().then((data) => {\r\n        switch (section) {\r\n          case \"pensionContracts\":\r\n            this.current.calc.pensionContracts = angular.copy(data.calc.pensionContracts);\r\n            this.current.payments.customerFunds.isPensionSelfHandling = data.payments.customerFunds.isPensionSelfHandling;\r\n            break;\r\n          case \"insuranceContracts\":\r\n            this.current.calc.insuranceContracts = angular.copy(data.calc.insuranceContracts);\r\n            break;\r\n          case \"incomesRegister\":\r\n            this.current.calc.incomesRegister = angular.copy(data.calc.incomesRegister);\r\n            break;\r\n          case \"eInvoice\":\r\n            this.current.payments.invoice.eInvoiceReceiver = data.payments.invoice.eInvoiceReceiver;\r\n            this.current.payments.invoice.eInvoiceIntermediator = data.payments.invoice.eInvoiceIntermediator;\r\n            break;\r\n          case \"sepa\":\r\n            this.current.payments.invoice.sepaBankPartyId = data.payments.invoice.sepaBankPartyId;\r\n            this.current.payments.invoice.ibanNumber = data.payments.invoice.ibanNumber;\r\n            break;\r\n          case \"taxAndSocialSecuritySelfHandling\":\r\n            this.current.payments.customerFunds.isTaxAndSocialSecuritySelfHandling = data.payments.customerFunds.isTaxAndSocialSecuritySelfHandling;\r\n            break;\r\n          case \"workerSelfHandling\":\r\n            this.current.payments.customerFunds.isWorkerSelfHandling = data.payments.customerFunds.isWorkerSelfHandling;\r\n            break;\r\n          case \"payslip\":\r\n          case \"omapalkka\":\r\n            this.current.messaging.workerSalarySlipDeliveryMethods = data.messaging.workerSalarySlipDeliveryMethods;\r\n            break;\r\n          case \"all\":\r\n            this._current = angular.copy(data);\r\n            break;\r\n        }\r\n        this.saves[section] = false;\r\n      });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Creates a new IR certificate.\r\n   * @param transferId Transfer ID for the IR certificate.\r\n   * @param transferPassword One time transfer password for the IR certificate.\r\n   * @returns Information about the created IR certificate.\r\n   */\r\n  public async createIrCertificate(transferId: string, transferPassword: string): Promise<void> {\r\n    this.saves[\"irCertificate\"] = true;\r\n    try {\r\n      await this.settingsService.createIrCertificate(transferId, transferPassword);\r\n    } finally {\r\n      this.saves[\"irCertificate\"] = false;\r\n      this._irCertificate = null;\r\n    }\r\n    return Promise.resolve();\r\n  }\r\n\r\n  /**\r\n   * Renews an existing IR certificate.\r\n   * @returns Information about the created IR certificate.\r\n   */\r\n  public async renewIrCertificate(): Promise<void> {\r\n    this.saves[\"irCertificate\"] = true;\r\n    try {\r\n      await this.settingsService.renewIrCertificate();\r\n    } finally {\r\n      console.log(\"renewIrCertificate\");\r\n      this.saves[\"irCertificate\"] = false;\r\n      this._irCertificate = null;\r\n    }\r\n    return Promise.resolve();\r\n  }\r\n\r\n  /** Returns true if the account has chosen to use own certificate */\r\n  public hasOwnIrCertificate(): boolean {\r\n    return this.settingsService.current?.calc?.incomesRegister?.irDelivery?.senderOfficialId != null &&\r\n    this.settingsService.current?.calc?.incomesRegister?.irDelivery?.senderOfficialId == this.sessionService.session?.currentAccount?.identity?.officialId;\r\n  }\r\n\r\n  /** Current IR certificate */\r\n  public get irCertificate(): any {\r\n    if (this.hasOwnIrCertificate()) {\r\n      if (!this._irCertificate) {\r\n        this._irCertificate = {\r\n          id : null\r\n        };\r\n        this.settingsService.getIrCertificate().then((result) => {\r\n          if (result?.id) {\r\n            angular.copy(result, this._irCertificate);\r\n          }\r\n        });\r\n      }\r\n    }\r\n    return this._irCertificate;\r\n  }\r\n\r\n  /**\r\n   * Send all workers paid calculations to omapalkka\r\n   */\r\n  public sendPaidCalculationsToOmapalkka() {\r\n    const loading = this.uiHelpers.showLoading();\r\n    this.ajax.postJSON(`${Configs.current.getOmapalkkaApiServer()}/api/messages/create-for-salary/all`, {}).then(() => {\r\n      loading.dismiss();\r\n    }).catch(e => {\r\n      console.error(e);\r\n      loading.dismiss();\r\n    });\r\n  }\r\n\r\n  /** Checks if switch input should be disabled on salarySlipDeliveryMethodsForm*/\r\n  public disableSwitchInput(): boolean {\r\n    return this.isSaving(\"omapalkka\") || this.isSaving(\"payslip\") || !!this.isReadOnlyForced || (!this.current.messaging.denyServiceModel && this.current.partner.serviceModel.features.messaging);\r\n  }\r\n\r\n  /**\r\n   * Sets pension number for test account to the given contract\r\n   * @param item Pension contract\r\n   */\r\n  public setPensionNumberForTest(item: PensionContract) {\r\n    item.contractNumber = SettingsLogic.getPensionNumberForTest(item.company);\r\n  }\r\n\r\n  /**\r\n   * Shows the eInvoice selection dialog\r\n   */\r\n  public selectEInvoiceAddress() {\r\n    this.settingsService.selectEInvoiceAddress(this.current.payments.invoice);\r\n  }\r\n\r\n  /**\r\n   * Gets the progress of save operation.\r\n   * @param section Section to check for saving.\r\n   * Note that \"all\" will check only \"all\" operations, not underlying sub-sections saving (\"any\").\r\n   */\r\n  public isSaving(section: SettingsSection | \"all\"): boolean {\r\n    return !!(this.saves[section] || this.saves[\"all\"]);\r\n  }\r\n\r\n  /**\r\n   * Event handler for accounting target selection.\r\n   * @param current Settings object to edit/create.\r\n   * @param logic Logic object passed to the dialog controller.\r\n   * @param logic.isReadOnly Read-only flag in logic.\r\n   * @param value Boolean indicating if the item is selected or not.\r\n   * @param item  The selected item.\r\n   * @param allItems All selected items.\r\n   */\r\n  public onAccountingTargetSelect(current: AccountingTargetSettings, logic: { isReadOnly: boolean }, value: boolean, item: AccountingTargetListItem, allItems: AccountingTargetListItem[]) {\r\n    allItems.splice(0, allItems.length);\r\n    logic.isReadOnly = true;\r\n    if (value == true) {\r\n      current.id = item.id;\r\n      current.avatar = item.otherPartyInfo.avatar;\r\n      current.format = item.data.format;\r\n      current.channel = item.data.channel;\r\n      current.method = item.data.method;\r\n      current.availableMethods = Arrays.assureArray(item.data.availableMethods) as ExportMethod[];\r\n      logic.isReadOnly = false;\r\n      allItems.push(item);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Event handler for usecase selection.\r\n   * @param current Settings object to edit/create.\r\n   * @param logic Logic object passed to the dialog controller.\r\n   * @param logic.isReadOnly Read-only flag in logic.\r\n   * @param value Boolean indicating if the item is selected or not.\r\n   * @param item  The selected item.\r\n   * @param allItems All selected items.\r\n   */\r\n  public onUsecaseSelect(current: Usecase, logic: { isReadOnly: boolean }, value: boolean, item: UsecaseListItem, allItems: UsecaseListItem[]) {\r\n    allItems.splice(0, allItems.length);\r\n    logic.isReadOnly = true;\r\n    if (value == true) {\r\n      current.uri = item.reference;\r\n      current.label = item.shortText;\r\n      current.itemType = item.entityType as ApiItemType;\r\n      current.status = item.status;\r\n      current.order = item.data.order;\r\n      logic.isReadOnly = false;\r\n      allItems.push(item);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Return Avatar from current.payment.channels ENUM\r\n   * @returns Avatar\r\n   */\r\n  public getPaymentChannelAvatar(item) {\r\n    return InvoicesLogic.getChannelAvatar(item.channel);\r\n  }\r\n\r\n  /**\r\n   * Created InputEnumOption [] from current.accounting.targets\r\n   * @returns InputEnumOption [] for template\r\n   */\r\n  public getSelectableAccountingTargets(): InputEnumOption[] {\r\n    return this.uiHelpers.cache(this, \"selectableAccountingTargets\", () => {\r\n      return this.current.accounting.targets.map(item => ({\r\n        text: item.avatar.displayName,\r\n        value: item.id,\r\n        ui: item.avatar\r\n      }) as InputEnumOption);\r\n    }, () => this.current.accounting.targets.map(item => item.id)\r\n    );\r\n  }\r\n\r\n  /**\r\n   * Created InputEnumOption [] from current.payment.channels\r\n   * @returns InputEnumOption [] for template\r\n   */\r\n\r\n  public getSelectablePaymenMethods(): InputEnumOption[] {\r\n    return this.uiHelpers.cache(this, \"selectablePaymentMethods\", () => {\r\n      return this.current.payments.channels.map(item => {\r\n        const avatar = InvoicesLogic.getChannelAvatar(item.channel) ?? InvoicesLogic.getChannelAvatar(PaymentChannel.Undefined);\r\n        return {\r\n          text: avatar.displayName,\r\n          value: avatar.id,\r\n          ui: avatar\r\n        } as InputEnumOption;\r\n      });\r\n    }, () => this.current.payments.channels.map(item => InvoicesLogic.getChannelAvatar(item.channel)?.id)\r\n    );\r\n  }\r\n\r\n  /**\r\n   * Returns true if the payslip is included in worker's SalarySlipDeliveryMethods.\r\n   */\r\n  public get payslip(): boolean {\r\n    return this.current?.messaging?.workerSalarySlipDeliveryMethods?.indexOf(WorkerSalarySlipDeliveryMethod.Payslip) >= 0 || false;\r\n  }\r\n\r\n  /**\r\n   * Sets/unsets the payslip as one of worker's SalarySlipDeliveryMethods.\r\n   * @param value Boolean value if the payslip should be set.\r\n   */\r\n  public set payslip(value: boolean) {\r\n    if (!this.current) {\r\n      return;\r\n    }\r\n    if (!value) {\r\n      const methods = this.current.messaging.workerSalarySlipDeliveryMethods.filter(x => x !== WorkerSalarySlipDeliveryMethod.Payslip);\r\n      this.current.messaging.workerSalarySlipDeliveryMethods.splice(0, this.current.messaging.workerSalarySlipDeliveryMethods.length);\r\n      this.current.messaging.workerSalarySlipDeliveryMethods.push(...methods);\r\n    } else {\r\n      if (this.current.messaging.workerSalarySlipDeliveryMethods.indexOf(WorkerSalarySlipDeliveryMethod.Payslip) < 0) {\r\n        this.current.messaging.workerSalarySlipDeliveryMethods.push(WorkerSalarySlipDeliveryMethod.Payslip);\r\n      }\r\n    }\r\n    this.save(\"payslip\");\r\n  }\r\n\r\n  /**\r\n   * Returns true if the omapalkka is included in worker's SalarySlipDeliveryMethods.\r\n   */\r\n  public get omapalkka(): boolean {\r\n    return this.current?.messaging?.workerSalarySlipDeliveryMethods?.indexOf(WorkerSalarySlipDeliveryMethod.Omapalkka) >= 0 || false;\r\n  }\r\n\r\n  /**\r\n   * Sets/unsets the omapalkka as one of worker's SalarySlipDeliveryMethods.\r\n   * @param value Boolean value if the payslip should be set.\r\n   */\r\n  public set omapalkka(value: boolean) {\r\n    if (!this.current) {\r\n      return;\r\n    }\r\n    if (!value) {\r\n      const methods = this.current.messaging.workerSalarySlipDeliveryMethods.filter(x => x !== WorkerSalarySlipDeliveryMethod.Omapalkka);\r\n      this.current.messaging.workerSalarySlipDeliveryMethods.splice(0, this.current.messaging.workerSalarySlipDeliveryMethods.length);\r\n      this.current.messaging.workerSalarySlipDeliveryMethods.push(...methods);\r\n    } else {\r\n      if (this.current.messaging.workerSalarySlipDeliveryMethods.indexOf(WorkerSalarySlipDeliveryMethod.Omapalkka) < 0) {\r\n        this.current.messaging.workerSalarySlipDeliveryMethods.push(WorkerSalarySlipDeliveryMethod.Omapalkka);\r\n      }\r\n    }\r\n    this.save(\"omapalkka\");\r\n  }\r\n\r\n  /**\r\n   * Confirm service change\r\n   */\r\n  public confirmServiceModelChange() {\r\n    this.uiHelpers.showConfirm(\"Palvelumallin ohitus\", \"Olet muuttamassa palvelumallin käyttöä. Paina 'Ok' tallentaaksesi\").then((result) => {\r\n      if (result) {\r\n        this.save(\"all\");\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Creates datauri for given image\r\n   * @param logo Logo for dataurl\r\n   */\r\n  public createReportLogoDatauri(logo: any) {\r\n    const createDataUri = (logo): Promise<string> => {\r\n      return new Promise((resolve, reject) => {\r\n        const reader = new FileReader();\r\n        reader.onload = (event) => {\r\n          resolve(event.target?.result as string);\r\n        };\r\n        reader.onerror = (error) => {\r\n          reject(error);\r\n        };\r\n        reader.readAsDataURL(logo);\r\n      });\r\n    };\r\n    createDataUri(logo).then(dataUri => {\r\n      this.current.reporting.logo = `<img src=\"${dataUri}\">`;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Retrieves the report logo.\r\n   * @returns The report logo as a html string.\r\n   */\r\n  public getReportLogo(): string {\r\n    if (!this.current.reporting.logo) {\r\n      return \"\";\r\n    }\r\n\r\n    if (this.current.reporting.logo.startsWith(\"<img src=\")) {\r\n      return this.current.reporting.logo;\r\n    }\r\n\r\n    if (this.current.reporting.logo.startsWith(\"<svg\")) {\r\n      return this.$sce.trustAsHtml(this.current.reporting.logo);\r\n    }\r\n  }\r\n\r\n  private static getActive<ContractType extends PensionContract | InsuranceContract>(contracts: ContractType[]): ContractType {\r\n    const today = Dates.getToday();\r\n    return contracts?.find((x) => x.status !== SettingsStatus.Pending &&\r\n      Dates.isSameOrAfter(today, x.startDate ?? \"1900-01-01\") &&\r\n      Dates.isBefore(today, Dates.add(x.endDate ?? \"2100-01-01\", 1, \"day\")));\r\n  }\r\n}\r\n\r\n","import angular from \"angular\";\r\n\r\nimport { Dates, LocalTapiolaInsuranceOrder, LocalTapiolaInsuranceOrderType, PartnerServices, Translations } from \"@salaxy/core\";\r\n\r\nimport { UiHelpers, WizardService, WizardStep } from \"../../services\";\r\n\r\nimport { WizardController } from \"../bases/WizardController\";\r\n\r\n/**\r\n * Wizard for sending Local Tapiola Insurance Order\r\n */\r\nexport class InsuranceWizardController extends WizardController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   */\r\n  public static $inject = [\"$scope\", \"WizardService\", \"PartnerServices\", \"UiHelpers\"];\r\n\r\n\r\n  /** Insurance action */\r\n  public action: \"newInsurance\" | \"moveInsurance\" | \"newInsuranceForEntrepreneur\";\r\n\r\n  /** Form data validity */\r\n  public formDataValidity: boolean;\r\n\r\n  /** Indicates if the order has been sent. */\r\n  public isSent = false;\r\n\r\n  /** Indicates if order is just sending */\r\n  public isSending = false;\r\n\r\n  /** Current Local Tapiola insurance order data. */\r\n  public current: LocalTapiolaInsuranceOrder = null;\r\n\r\n  /** Today (for datepicker minDate) */\r\n  public today = Dates.getToday();\r\n\r\n  public countryCodes = [\r\n    { value: \"fi\", text: \"Suomi\" },\r\n    { value: \"sv\", text: \"Sverige\" },\r\n    { value: \"ee\", text: \"Eesti\" }\r\n  ];\r\n\r\n  /** Next possible dates for moving insurance to LocalTapiola */\r\n  public insuranceStartingPointDateOptions = {};\r\n\r\n  /** LocalTapiola Insurance wizard configuration */\r\n  private wizardSteps: WizardStep[] = [\r\n    { // 0\r\n      title: Translations.get(\"SALAXY.NG1.InsuranceComponent.start.wizard.title\"),\r\n      heading: Translations.get(\"SALAXY.NG1.InsuranceComponent.start.wizard.title\"),\r\n      intro: \"\",\r\n      active: true,\r\n      view: \"salaxy-components/modals/localTapiola/Start.html\",\r\n    },\r\n    { // 1\r\n      title: Translations.get(\"SALAXY.NG1.InsuranceComponent.contactInfo.wizard.title\"),\r\n      heading: Translations.get(\"SALAXY.NG1.InsuranceComponent.contactInfo.wizard.heading\"),\r\n      intro: \"\",\r\n      view: \"salaxy-components/modals/localTapiola/ContactInfo.html\",\r\n      buttonsView: \"salaxy-components/modals/localTapiola/buttons-default.html\",\r\n    },\r\n    { // 2\r\n      title: Translations.get(\"SALAXY.NG1.InsuranceComponent.ownerInfo.wizard.title\"),\r\n      heading: Translations.get(\"SALAXY.NG1.InsuranceComponent.ownerInfo.wizard.heading\"),\r\n      intro: Translations.get(\"SALAXY.NG1.InsuranceComponent.ownerInfo.wizard.intro\"),\r\n      view: \"salaxy-components/modals/localTapiola/Owner-info.html\",\r\n      buttonsView: \"salaxy-components/modals/localTapiola/buttons-default.html\",\r\n    },\r\n    { // 3\r\n      title: Translations.get(\"SALAXY.NG1.InsuranceComponent.beneficiaryInfo.wizard.title\"),\r\n      heading: Translations.get(\"SALAXY.NG1.InsuranceComponent.beneficiaryInfo.wizard.heading\"),\r\n      intro: Translations.get(\"SALAXY.NG1.InsuranceComponent.beneficiaryInfo.wizard.intro\"),\r\n      view: \"salaxy-components/modals/localTapiola/Beneficiary-info.html\",\r\n      buttonsView: \"salaxy-components/modals/localTapiola/buttons-default.html\",\r\n    },\r\n    {\r\n      // 4\r\n      title: Translations.get(\"SALAXY.NG1.InsuranceComponent.insuranceInfoNew.wizard.title\"),\r\n      heading: Translations.get(\"SALAXY.NG1.InsuranceComponent.insuranceInfoNew.wizard.heading\"),\r\n      intro: \"\",\r\n      view: \"salaxy-components/modals/localTapiola/InsuranceInfo-new.html\",\r\n      buttonsView: \"salaxy-components/modals/localTapiola/buttons-send.html\", //buttons send\r\n    },\r\n    {\r\n      // 5\r\n      title: Translations.get(\"SALAXY.NG1.InsuranceComponent.entrepreneur.wizard.title\"),\r\n      heading: Translations.get(\"SALAXY.NG1.InsuranceComponent.entrepreneur.wizard.heading\"),\r\n      intro: \"\",\r\n      view: \"salaxy-components/modals/localTapiola/Entrepreneur.html\",\r\n      buttonsView: \"salaxy-components/modals/localTapiola/buttons-default.html\",\r\n    },\r\n    { // 6\r\n      title: Translations.get(\"SALAXY.NG1.InsuranceComponent.contactInfoEntrepreneur.wizard.title\"),\r\n      heading: Translations.get(\"SALAXY.NG1.InsuranceComponent.contactInfoEntrepreneur.wizard.heading\"),\r\n      intro: \"\",\r\n      view: \"salaxy-components/modals/localTapiola/ContactInfo-entrepreneur.html\",\r\n      buttonsView: \"salaxy-components/modals/localTapiola/buttons-default.html\",\r\n    },\r\n    { // 7\r\n      title: Translations.get(\"SALAXY.NG1.InsuranceComponent.ownerInfo.wizard.titleAlt\"),\r\n      heading: Translations.get(\"SALAXY.NG1.InsuranceComponent.ownerInfo.wizard.heading\"),\r\n      intro: Translations.get(\"SALAXY.NG1.InsuranceComponent.ownerInfo.wizard.intro\"),\r\n      view: \"salaxy-components/modals/localTapiola/Owner-info.html\",\r\n      buttonsView: \"salaxy-components/modals/localTapiola/buttons-default.html\",\r\n    },\r\n    { // 8\r\n      title: Translations.get(\"SALAXY.NG1.InsuranceComponent.beneficiaryInfo.wizard.titleAlt\"),\r\n      heading: Translations.get(\"SALAXY.NG1.InsuranceComponent.beneficiaryInfo.wizard.heading\"),\r\n      intro: Translations.get(\"SALAXY.NG1.InsuranceComponent.beneficiaryInfo.wizard.intro\"),\r\n      view: \"salaxy-components/modals/localTapiola/Beneficiary-info.html\",\r\n      buttonsView: \"salaxy-components/modals/localTapiola/buttons-send.html\",\r\n    },\r\n    { // 9\r\n      title: Translations.get(\"SALAXY.NG1.InsuranceComponent.contactInfo.wizard.titleAlt\"),\r\n      heading: \"\",\r\n      intro: Translations.get(\"SALAXY.NG1.InsuranceComponent.contactInfo.wizard.intro\"),\r\n      view: \"salaxy-components/modals/localTapiola/ContactInfo.html\",\r\n      buttonsView: \"salaxy-components/modals/localTapiola/buttons-default.html\",\r\n    },\r\n    { // 10\r\n      title: Translations.get(\"SALAXY.NG1.InsuranceComponent.ownerInfo.wizard.titleMoveInsurance\"),\r\n      heading: Translations.get(\"SALAXY.NG1.InsuranceComponent.ownerInfo.wizard.heading\"),\r\n      intro: Translations.get(\"SALAXY.NG1.InsuranceComponent.ownerInfo.wizard.intro\"),\r\n      view: \"salaxy-components/modals/localTapiola/Owner-info.html\",\r\n      buttonsView: \"salaxy-components/modals/localTapiola/buttons-default.html\",\r\n    },\r\n    { // 11\r\n      title: Translations.get(\"SALAXY.NG1.InsuranceComponent.beneficiaryInfo.wizard.titleMoveInsurance\"),\r\n      heading: Translations.get(\"SALAXY.NG1.InsuranceComponent.beneficiaryInfo.wizard.heading\"),\r\n      intro: Translations.get(\"SALAXY.NG1.InsuranceComponent.beneficiaryInfo.wizard.intro\"),\r\n      view: \"salaxy-components/modals/localTapiola/Beneficiary-info.html\",\r\n      buttonsView: \"salaxy-components/modals/localTapiola/buttons-default.html\",\r\n    },\r\n    { // 12\r\n      title: Translations.get(\"SALAXY.NG1.InsuranceComponent.insuranceMove.wizard.title\"),\r\n      heading: \"\",\r\n      intro: \"\",\r\n      view: \"salaxy-components/modals/localTapiola/InsuranceInfo-move.html\",\r\n      buttonsView: \"salaxy-components/modals/localTapiola/buttons-send.html\",\r\n    },\r\n    { // 13\r\n      title: Translations.get(\"SALAXY.NG1.InsuranceComponent.thankYou.wizard.title\"),\r\n      heading: \"\",\r\n      intro: \"\",\r\n      view: \"salaxy-components/modals/localTapiola/ThankYou.html\",\r\n\r\n    },\r\n  ];\r\n\r\n  private newSteps = [\r\n    this.wizardSteps[0], // start\r\n    this.wizardSteps[1], // contact new\r\n    this.wizardSteps[2], // owner info\r\n    this.wizardSteps[3], // beneficiary info\r\n    this.wizardSteps[4], // additional info\r\n    this.wizardSteps[13], // thank you\r\n  ];\r\n\r\n  private newEntrepreneurSteps = [\r\n    this.wizardSteps[0], // start\r\n    this.wizardSteps[5], // additional info entrepreneur\r\n    this.wizardSteps[6], // contact info\r\n    this.wizardSteps[7], // owner info\r\n    this.wizardSteps[8], // beneficiary info\r\n    this.wizardSteps[13], // thank you\r\n  ];\r\n\r\n  private moveSteps = [\r\n    this.wizardSteps[0], // start\r\n    this.wizardSteps[9], // contact info (move)\r\n    this.wizardSteps[10], // owner info\r\n    this.wizardSteps[11], // beneficiary info\r\n    this.wizardSteps[12], // additional info (move)\r\n    this.wizardSteps[13], // thank you\r\n  ];\r\n\r\n  /**\r\n   * Creates a new WizardController\r\n   * @param $scope - The Angular scope\r\n   * @param wizardService - Maintains the state of the wizard\r\n   * @param partnerServices - Local Tapiola insurance orders API\r\n   * @param uiHelpers - Salaxy UI helpers\r\n   */\r\n  constructor(\r\n    $scope: angular.IScope,\r\n    wizardService: WizardService,\r\n    private partnerServices: PartnerServices,\r\n    private uiHelpers: UiHelpers,\r\n  ) {\r\n    super($scope, wizardService);\r\n  }\r\n\r\n  /**\r\n   * Sets the current wizard action and wizard steps\r\n   * @param insuranceAction - Action to performs: order new or move existing insurance.\r\n   */\r\n  public setInsuranceAction(insuranceAction: \"newInsurance\" | \"moveInsurance\" | \"newInsuranceForEntrepreneur\") {\r\n    this.isSending = false;\r\n    this.isSent = false;\r\n    this.formDataValidity = true;\r\n    this.action = insuranceAction;\r\n    this.getStartingPointDates();\r\n    this.current.id = null;\r\n    if (this.current.company.beneficiaries.length === 0) {\r\n      this.current.company.beneficiaries.push({});\r\n    }\r\n    if (this.current.company.owners.length === 0) {\r\n      this.current.company.owners.push({});\r\n    }\r\n\r\n\r\n    switch (insuranceAction) {\r\n      case \"newInsurance\":\r\n        this.current.items = [\r\n          {\r\n            orderType: LocalTapiolaInsuranceOrderType.NewWorkerInsurance,\r\n            occupations: [{}],\r\n          }\r\n        ];\r\n        this.wizardService.setSteps(this.newSteps);\r\n        break;\r\n      case \"moveInsurance\":\r\n        this.current.items = [\r\n          {\r\n            orderType: LocalTapiolaInsuranceOrderType.MoveWorkerInsurance,\r\n            occupations: [{}],\r\n          }\r\n        ];\r\n        this.wizardService.setSteps(this.moveSteps);\r\n        break;\r\n      case \"newInsuranceForEntrepreneur\":\r\n        this.current.items = [\r\n          {\r\n            orderType: LocalTapiolaInsuranceOrderType.NewEntrepreneurInsurance,\r\n            occupations: [{}],\r\n          }\r\n        ];\r\n        this.wizardService.setSteps(this.newEntrepreneurSteps);\r\n        break;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Controller initializations\r\n   */\r\n  public $onInit = () => {\r\n    this.partnerServices.getNewLocalTapiolaInsuranceOrder().then((data) => {\r\n      this.current = data;\r\n    });\r\n  };\r\n\r\n\r\n  /** Send the current order. */\r\n  public send() {\r\n\r\n    if (this.isSending) {\r\n      return;\r\n    }\r\n    if (this.isSent) {\r\n      this.goNext();\r\n      return;\r\n    }\r\n    this.isSending = true;\r\n\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n\r\n    this.partnerServices.sendLocalTapiolaInsuranceOrder(this.current).then(() => {\r\n      loading.dismiss();\r\n      this.goNext();\r\n      this.isSent = true;\r\n      this.isSending = false;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Get next possible dates for moving existing insurance contract to LocalTapiola\r\n   */\r\n  public getStartingPointDates() {\r\n    // Quarter starting dates as strings\r\n    const asap = \"Ensimmäinen mahdollinen ajankohta\";\r\n    const firstDate = Dates.add(Dates.startEnd(\"today\",\"start-quarter\"),1, \"quarter\");\r\n    const secondDate = Dates.add(Dates.startEnd(\"today\",\"start-quarter\"),2, \"quarter\");\r\n    const thirdDate = Dates.add(Dates.startEnd(\"today\",\"start-quarter\"),3, \"quarter\");\r\n    const fourthDate = Dates.add(Dates.startEnd(\"today\",\"start-quarter\"),4, \"quarter\");\r\n\r\n\r\n    this.insuranceStartingPointDateOptions = {\r\n      [asap]: \"Ensimmäinen mahdollinen ajankohta\",\r\n      [Dates.format(firstDate,\"YYYY-MM-DD\")]: Dates.format(firstDate,\"D.M.YYYY\"),\r\n      [Dates.format(secondDate,\"YYYY-MM-DD\")]: Dates.format(secondDate,\"D.M.YYYY\"),\r\n      [Dates.format(thirdDate,\"YYYY-MM-DD\")]: Dates.format(thirdDate,\"D.M.YYYY\"),\r\n      [Dates.format(fourthDate,\"YYYY-MM-DD\")]: Dates.format(fourthDate,\"D.M.YYYY\"),\r\n    };\r\n\r\n  }\r\n\r\n  /** Go to the next step */\r\n  public goNext() {\r\n    // TODO remove when ready and use super\r\n    this.step++;\r\n    //super.goNext();\r\n  }\r\n\r\n  /**\r\n   * Go to the last step (\"thank you\" step)\r\n   */\r\n  public goToLast() {\r\n    this.step = this.steps.length;\r\n  }\r\n  /**\r\n   * Navigates to the previous step if possible and saves the data.\r\n   */\r\n  public goPrevious() {\r\n    super.goPrevious();\r\n  }\r\n\r\n  /**\r\n   * Returns true, if the given order type exists in the current order items.\r\n   * @param orderTypes - Order type to check.\r\n   * @returns True, if the order type is found, otherwise default.\r\n   */\r\n  public hasOrderType(...orderTypes: LocalTapiolaInsuranceOrderType[]): boolean {\r\n    return (orderTypes ?? []).some((x) => !!(this.current.items ?? []).find((i) => i.orderType === x));\r\n  }\r\n\r\n  /** Returns true if user can go forward in wizard  */\r\n  public get canGoNext(): boolean {\r\n    if (this.steps.length > this.step) {\r\n      if (this.steps[this.step] && !this.steps[this.step].disabled) {\r\n        if (this.formDataValidity) {\r\n          return true;\r\n        }\r\n      }\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /** Opens the insurance dialog. */\r\n  public openModal() {\r\n    this.wizardService.setSteps([this.wizardSteps[0]]);\r\n    this.step = 1;\r\n    this.uiHelpers.showDialog(\r\n      \"salaxy-components/modals/account/Insurance.html\",\r\n      \"InsuranceWizardController\",\r\n      null,\r\n      null,\r\n      \"lg\");\r\n  }\r\n\r\n  /**\r\n   * Validates the order.\r\n   */\r\n  public validate(): Promise<LocalTapiolaInsuranceOrder> {\r\n    return this.partnerServices.validateLocalTapiolaInsuranceOrder(this.current).then((order) => {\r\n      this.current = order;\r\n      return this.current;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Resets the current order.\r\n   */\r\n  public reset() {\r\n    // this.current = null;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Arrays, BeneficialOwners, BeneficialOwnersApi } from \"@salaxy/core\";\r\n\r\n/**\r\n * Handles user interfaces for Owner and Beneficiary lists\r\n */\r\nexport class OwnerSettingsController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"BeneficialOwnersApi\", \"$timeout\"];\r\n\r\n  /** Mode */\r\n  public mode: \"byPercent\" | \"byAmount\" = \"byAmount\";\r\n\r\n  /** Current owners. */\r\n  public current: BeneficialOwners = null;\r\n\r\n  /** If true, current item is read only */\r\n  public isReadOnlyForced: \"<\";\r\n\r\n  private saves: { [key: string] : boolean } = {};\r\n\r\n  constructor(private beneficialOwnersApi: BeneficialOwnersApi, private $timoeut: angular.ITimeoutService\r\n  ) {\r\n  }\r\n\r\n  /**\r\n   * Controller initializations\r\n   */\r\n  public $onInit = () => {\r\n\r\n    this.beneficialOwnersApi.get().then((data) => {\r\n      this.current = data;\r\n    });\r\n  };\r\n\r\n  /**\r\n   * Total amount of user input shares\r\n   */\r\n  public getTotalAmount(): number {\r\n    if (!this.mode || !this.current) {\r\n      return 0;\r\n    }\r\n    return Arrays.sum(this.current.owners, (x) => x.numberOfShares ?? 0);\r\n  }\r\n\r\n  /**\r\n   * Total percentage of user input shares\r\n   */\r\n  public getTotalPercent(): number {\r\n    if (!this.mode || !this.current) {\r\n      return 0;\r\n    }\r\n    return Arrays.sum(this.current.owners, (x) => x.percentOfShares ?? 0);\r\n  }\r\n\r\n  /**\r\n   * Calculates percentage from the given share amount\r\n   */\r\n  public getPercentFromAmount(numberOfShares: number): number {\r\n    if (this.mode == \"byAmount\" && this.current && this.current.ownedCompanyDetails.totalNumberOfShares != null) {\r\n      return (numberOfShares / this.current.ownedCompanyDetails.totalNumberOfShares) * 100;\r\n    }\r\n    return 0;\r\n  }\r\n\r\n  /**\r\n   * Calculates share amount from the given share percentage\r\n   */\r\n  public getAmountFromPercent(percentOfShares: number): number {\r\n    if (this.mode == \"byPercent\" && this.current && this.current.ownedCompanyDetails.totalNumberOfShares != null) {\r\n      return this.current.ownedCompanyDetails.totalNumberOfShares * (percentOfShares / 100);\r\n    }\r\n    return 0;\r\n  }\r\n\r\n  /**\r\n   * update\r\n   */\r\n  public recalculateShares() {\r\n    if (!this.mode || !this.current) {\r\n      return;\r\n    }\r\n    if (this.mode == \"byPercent\") {\r\n      for (const singleOwner of this.current.owners) {\r\n        singleOwner.numberOfShares = this.current.ownedCompanyDetails.totalNumberOfShares * ( singleOwner.percentOfShares / 100 );\r\n      }\r\n    }\r\n    if (this.mode == \"byAmount\") {\r\n      for (const singleOwner of this.current.owners) {\r\n        singleOwner.percentOfShares = ( singleOwner.numberOfShares / this.current.ownedCompanyDetails.totalNumberOfShares ) * 100;\r\n      }\r\n    }\r\n  }\r\n\r\n  /** Saves the current owners and beneficiaries to backend. */\r\n  public save(target: \"owners\" | \"beneficiaries\") {\r\n    this.saves[target] = true;\r\n    this.beneficialOwnersApi.save(this.current).then( (data) => {\r\n      this.current = data;\r\n      this.saves[target] = false;\r\n    });\r\n  }\r\n\r\n  /** Indicates the progress of save operation. */\r\n  public isSaving(target: \"owners\" | \"beneficiaries\"): boolean {\r\n    return this.saves[target] || false;\r\n  }\r\n\r\n}","import { Avatar, Configs, InvoicesLogic, PaymentChannel, PaymentChannelSettings, PaymentChannelSettingsInfo, PensionCompany } from \"@salaxy/core\";\r\n\r\nimport { EditDialogKnownActions, SessionService, SettingsService, UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Handles user interfaces for specifying settings for Payment Channels (and other payment related settings).\r\n */\r\nexport class PaymentChannelSettingsController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"SettingsService\", \"UiHelpers\", \"SessionService\"];\r\n\r\n  private lastPaymentChannelWindow: PaymentChannel;\r\n\r\n  private _siteChannels: PaymentChannelSettings[] = null;\r\n\r\n  constructor(\r\n    private settingsService: SettingsService,\r\n    private uiHelpers: UiHelpers,\r\n    private sessionService: SessionService,\r\n  ) {\r\n  }\r\n\r\n  /**\r\n   * Controller initializations\r\n   */\r\n  public $onInit = () => {\r\n    // none\r\n  };\r\n\r\n  /**\r\n   * Gets the current settings object as soon as it is loaded.\r\n   * Note that this is null until the settings have been loaded from server.\r\n   */\r\n  public get current() {\r\n    return this.settingsService.current;\r\n  }\r\n\r\n  /**\r\n   * If the channels are set site specific (e.g. custom sites), the settings cannot be saved.\r\n   * Site specific changes are done to session, and exposed by InvoicesService\r\n   */\r\n  public get isReadOnly() {\r\n    // no settings\r\n    if (!this.current) {\r\n      return true;\r\n    }\r\n    // partner override\r\n    if (this.current.partner.serviceModel.features.payments && !this.current.payments.denyServiceModel) {\r\n      return true;\r\n    }\r\n    // site override\r\n    if (this.isSiteSpecific) {\r\n      return true;\r\n    }\r\n\r\n    return false;\r\n  }\r\n\r\n  /** Returns true, if the settings are site specific. */\r\n  public get isSiteSpecific() {\r\n    const enabled = this.current.payments.channels.filter( (x) => x.isAvailable && x.isEnabled);\r\n    const sameLength = enabled.length === this.sessionService.getSession()?.settings?.paymentChannels?.length;\r\n    if (sameLength && enabled.length > 0) {\r\n      const sameIds = this.sessionService.getSession().settings.paymentChannels.every((x) => enabled.some((c) => c.channel === x));\r\n      if (sameIds) {\r\n        return false;\r\n      }\r\n    }\r\n    return true;\r\n  }\r\n\r\n  /**\r\n   * Gets the payment channel.\r\n   * @param type Type of the channel to list:\r\n   *\r\n   * - enabled: Enabled channels\r\n   * - available: Available channels that can be enabled (have not yet been enabled).\r\n   * - unavailable: Unavailable channels (cannot be enabled)\r\n   * - all: Really all channels, even the technical ones that cannot be enabled.\r\n   */\r\n  public getPaymentChannels(type: \"all\" | \"available\" | \"enabled\" | \"unavailable\"): PaymentChannelSettings[] {\r\n    if (!this.current) {\r\n      return null;\r\n    }\r\n    let all: PaymentChannelSettings[] = [];\r\n    if (this.isSiteSpecific) {\r\n      if (this._siteChannels === null) {\r\n        this._siteChannels = this.sessionService.getSession().settings.paymentChannels.map<PaymentChannelSettings>((c) => ({ channel: c, isEnabled: true, isAvailable: true }));\r\n      }\r\n      all = all.concat(this._siteChannels);\r\n    } else {\r\n      all = all.concat(this.current.payments.channels);\r\n    }\r\n    all = all.filter((x) =>\r\n      x.channel !== PaymentChannel.PalkkausManual ||\r\n      (x.channel === PaymentChannel.PalkkausManual && this.sessionService.isInSomeRole(\"pro,sepaPartner\"))\r\n    );\r\n\r\n    switch (type) {\r\n      case \"all\":\r\n        return all;\r\n      case \"available\":\r\n        return all.filter((x) => x.isAvailable && !x.isEnabled);\r\n      case \"unavailable\":\r\n        return all.filter((x) => !x.isAvailable);\r\n      case \"enabled\":\r\n      default:\r\n        return all.filter((x) => x.isAvailable && x.isEnabled);\r\n    }\r\n  }\r\n\r\n  /** Gets the visual representation and language versioned UI texts of the payment channel */\r\n  public getAvatar(channel: PaymentChannel): Avatar {\r\n    return InvoicesLogic.getChannelAvatar(channel);\r\n  }\r\n\r\n  /** Gets the default channel. */\r\n  public get defaultChannel() {\r\n    return this.sessionService.getSession().settings.defaultPaymentChannel;\r\n  }\r\n\r\n  /** Opens the channel setup dialog in a new window. */\r\n  public openChannelSetupDialog(channel: PaymentChannel) {\r\n    let url = null;\r\n    let isExternal = false;\r\n    switch (channel) {\r\n      case PaymentChannel.Test:\r\n        isExternal = true;\r\n        url =\r\n          Configs.current.isTestData ?\r\n            \"https://test-integrations.salaxy.com/test#/dialogs/settings\" :\r\n            \"https://integrations.salaxy.com/test#/dialogs/settings\";\r\n        url += \"?token=\" + this.sessionService.getCurrentToken();\r\n        break;\r\n      case PaymentChannel.Procountor:\r\n        isExternal = true;\r\n        url =\r\n          Configs.current.isTestData ?\r\n            \"http://localhost:93/procountor/settings.html\" :\r\n            \"https://integrations.salaxy.com/procountor/settings.html\";\r\n        url += \"?token=\" + this.sessionService.getCurrentToken();\r\n        break;\r\n      case PaymentChannel.VismaNetvisor:\r\n        isExternal = true;\r\n        url =\r\n          Configs.current.isTestData ?\r\n            \"http://localhost:93/vismanetvisor/settings.html\" :\r\n            \"https://integrations.salaxy.com/vismanetvisor/settings.html\";\r\n        url += \"?token=\" + this.sessionService.getCurrentToken();\r\n        break;\r\n      default:\r\n        break;\r\n    }\r\n\r\n    const channelInEdit = this.getPaymentChannels(\"all\").find((x) => x.channel === channel);\r\n    if (!channelInEdit) {\r\n      this.uiHelpers.showAlert(\"Maksutapaa ei voi muokata\", \"Palkanlaskentasivuston asetukset estävät maksutavan muokkauksen.\");\r\n      return;\r\n    }\r\n\r\n    const p = this.current.payments;\r\n    const supportedCompanies = [PensionCompany.None, PensionCompany.Ilmarinen, PensionCompany.Elo, PensionCompany.Varma];\r\n    const isPensionIncludedSupported = this.current.calc.pensionContracts\r\n      .every((x) => supportedCompanies.indexOf(x.company) >= 0);\r\n\r\n    // TODO: Go through this data model and see what really is necessary?\r\n    const channelSettings: PaymentChannelSettingsInfo | any = {\r\n      id: channelInEdit.channel,\r\n      isDefault: channelInEdit.channel == this.defaultChannel,\r\n      settings: {\r\n        data: channelInEdit.data,\r\n        isAvailable: channelInEdit.isAvailable,\r\n        isEnabled: channelInEdit.isEnabled,\r\n      },\r\n      customerFundsSettings: {\r\n        isPensionIncludedSupported,\r\n        isPensionSelfHandling: p.customerFunds.isPensionSelfHandling,\r\n        isTaxAndSocialSecuritySelfHandling: p.customerFunds.isTaxAndSocialSecuritySelfHandling,\r\n        isWorkerSelfHandling: p.customerFunds.isWorkerSelfHandling,\r\n      },\r\n      invoiceSettings: {\r\n        eInvoiceIntermediator: p.invoice.eInvoiceIntermediator,\r\n        eInvoiceReceiver: p.invoice.eInvoiceReceiver,\r\n        ibanNumber: p.invoice.ibanNumber,\r\n        sepaBankPartyId: p.invoice.sepaBankPartyId,\r\n      },\r\n      isReadOnly: this.isReadOnly,\r\n    };\r\n\r\n    const saveSettings = (action: EditDialogKnownActions | \"set-default\", data: PaymentChannelSettingsInfo | any) => {\r\n\r\n      if (action === EditDialogKnownActions.Cancel) {\r\n        console.debug(\"Canceling: Remove this message\");\r\n        return;\r\n      }\r\n      if (data.id !== this.lastPaymentChannelWindow) {\r\n        throw new Error(`Invalid response from channel ${data.id || \"undefined\"}, expected ${this.lastPaymentChannelWindow}.`);\r\n      }\r\n\r\n      let channelToSave = p.channels.find((x) => x.channel === channel);\r\n      if (!channelToSave) {\r\n        channelToSave = channelInEdit;\r\n        p.channels.push(channelToSave);\r\n      }\r\n\r\n      if (action === EditDialogKnownActions.Ok || action === \"set-default\") {\r\n\r\n        channelToSave.data = data.settings.data;\r\n        channelToSave.isEnabled = channelToSave.isAvailable && true;\r\n        if (action === \"set-default\") {\r\n          p.defaultChannel = channel;\r\n        }\r\n\r\n        p.customerFunds.isPensionSelfHandling = data.customerFundsSettings.isPensionSelfHandling;\r\n        p.customerFunds.isTaxAndSocialSecuritySelfHandling = data.customerFundsSettings.isTaxAndSocialSecuritySelfHandling;\r\n        p.customerFunds.isWorkerSelfHandling = data.customerFundsSettings.isWorkerSelfHandling;\r\n\r\n        p.invoice.eInvoiceIntermediator = data.invoiceSettings.eInvoiceIntermediator;\r\n        p.invoice.eInvoiceReceiver = data.invoiceSettings.eInvoiceReceiver;\r\n        p.invoice.ibanNumber = data.invoiceSettings.ibanNumber;\r\n        p.invoice.sepaBankPartyId = data.invoiceSettings.sepaBankPartyId;\r\n\r\n        this.settingsService.save();\r\n      }\r\n      if (action === EditDialogKnownActions.Delete) {\r\n        channelInEdit.isEnabled = false;\r\n        // TODO: Make sure that server-side does not allow deleting last channel and that it sets the default channel if none is selected.\r\n        this.settingsService.save();\r\n      }\r\n    };\r\n\r\n    this.lastPaymentChannelWindow = channel;\r\n    if (isExternal) {\r\n      this.uiHelpers.showExternalDialog(channelSettings.id, url, channelSettings).then((dialogResult) => {\r\n          saveSettings(dialogResult.action as EditDialogKnownActions, dialogResult.item);\r\n      });\r\n    } else {\r\n      this.uiHelpers.openEditDialog(`salaxy-components/modals/settings/PaymentChannel.html`, channelSettings,\r\n        {\r\n          channelAvatar: InvoicesLogic.getChannelAvatar(channelSettings.id),\r\n          selectEInvoiceAddress: (itemRef) => {\r\n            this.settingsService.selectEInvoiceAddress(itemRef);\r\n          },\r\n        }\r\n      ).then((dialogResult) => {\r\n          saveSettings(dialogResult.action as EditDialogKnownActions, dialogResult.item);\r\n      });\r\n    }\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { EditDialogKnownActions, RowTypeService, UiHelpers } from \"../../services\";\r\nimport { CalcRowConfig, CalcRowsLogic, CalculationRowCategory, CalculationRowSource, CalculationRowType, CalculatorLogic, Employment, InputEnumOption, UserDefinedRowLogic, RowTypeDefinition, RowsUsecaseLogic, UserDefinedRow, EnumerationsLogic, IncomeTypesLogic, CalcRowConfigTypeGroup } from \"@salaxy/core\";\r\n\r\n/**\r\n * Controller for editing the row types in settings (Palkkalajit)\r\n */\r\nexport class RowTypesSettingsController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"RowTypeService\", \"UiHelpers\", \"$timeout\", \"$element\"];\r\n\r\n  /**\r\n   * Set this property if you want to explicitly set the model (currently only Employment).\r\n   * If undefinded, the component binds to company settings.\r\n   */\r\n  public model?: Employment;\r\n\r\n  /**\r\n   * Defines the type of rows editor: \"builtIn\" for built-in rows,\r\n   * \"custom\" for custom rows, \"prices\" company specific default prices per row type,\r\n   * \"copy\" for rows that should be copied to the calculation.\r\n   */\r\n  public mode: \"builtIn\" | \"custom\" | \"prices\" | \"copy\";\r\n\r\n  /** If set, filters the rows based on categories (plus rowTypes if set) */\r\n  public categories: CalculationRowCategory[];\r\n\r\n  /** Search text that is potentially input by the user. */\r\n  public searchText: string;\r\n\r\n  private listCache: {\r\n    /** Cache key */\r\n    key: string,\r\n    /** Cache value */\r\n    value: CalcRowConfig[],\r\n  } = null;\r\n\r\n  constructor(private rowTypeService: RowTypeService, private uiHelpers: UiHelpers, private $timeout: angular.ITimeoutService, private $element: JQLite) {\r\n  }\r\n\r\n  /** New empty row for databinding when creating a new row. */\r\n  public newRow: RowTypeDefinition;\r\n\r\n  /** Sets the default values in init. */\r\n  public $onInit() {\r\n    this.newRow = this.getBlank();\r\n  }\r\n\r\n  /** Saves the changes to row types. */\r\n  public save() {\r\n    this.rowTypeService.save();\r\n    this.listCache = null;\r\n  }\r\n\r\n  /**\r\n   * Gets the current object: Either the rows collection from settings as soon as it is loaded or an employment relation.\r\n   */\r\n  public get current(): RowTypeDefinition[] | Employment | undefined {\r\n    if (this.model) {\r\n      return this.model;\r\n    }\r\n    return this.rowTypeService.isReady ? this.rowTypeService.allCustomRows : undefined;\r\n  }\r\n\r\n  /**\r\n   * List of items to edit: In settings or Employment relation.\r\n   */\r\n  public get list(): RowTypeDefinition[] {\r\n    if ((this.current as Employment)?.work?.salaryDefaults) {\r\n      return (this.current as Employment).work.salaryDefaults as RowTypeDefinition[];\r\n    }\r\n    return this.rowTypeService.allCustomRows;\r\n  }\r\n\r\n  /**\r\n   * Gets the price rows in the current modeel.\r\n   */\r\n  public get pricesList(): RowTypeDefinition[] {\r\n    return this.list.filter(x => x.source === CalculationRowSource.PriceCompany || x.source == CalculationRowSource.PriceEmployment) as RowTypeDefinition[];\r\n  }\r\n\r\n  /**\r\n   * Gets the copy rows in the current model.\r\n   */\r\n  public get copyRowsList(): RowTypeDefinition[] {\r\n    return this.list.filter(x => x.source === CalculationRowSource.CopyCompany || x.source == CalculationRowSource.CopyEmployment) as RowTypeDefinition[];\r\n  }\r\n\r\n  /**\r\n   * Gets the default rows from the current model\r\n   */\r\n  public get defaultsList(): RowTypeDefinition[] {\r\n    return this.list.filter(x => !x.source || x.source === CalculationRowSource.Undefined || x.source == CalculationRowSource.ManualRow) as RowTypeDefinition[];\r\n  }\r\n\r\n  /**\r\n   * Gets the list of company specific rows, always in settings even if the bound model is employment.\r\n   */\r\n  public get settingsList(): RowTypeDefinition[] {\r\n    if (!this.rowTypeService.isReady) {\r\n      console.error(\"Settings not yet loaded, handle this edge case.\");\r\n      return undefined;\r\n    }\r\n    return this.rowTypeService.allCustomRows;\r\n  }\r\n\r\n  /**\r\n   * Gets the configuration object for a row definition.\r\n   * @param row Row for which the configuration is fetched.\r\n   * @returns The configuration for the row.\r\n   */\r\n  public getConfig(row: RowTypeDefinition): CalcRowConfig {\r\n    return this.rowTypeService.getConfig(row);\r\n  }\r\n\r\n  /** Creating of a new item. */\r\n    public getBlank(): RowTypeDefinition {\r\n      const nextId = Math.max(...this.list.map(x => x.rowIndex), 0) + 1;\r\n      const newRow = UserDefinedRowLogic.getBlank(nextId) as RowTypeDefinition;\r\n      newRow.config = {} as any;\r\n      return newRow;\r\n    }\r\n\r\n  /**\r\n   * Gets the search as cached item: Can be bound to ng-repeat.\r\n   * @param searchText The search text. If null or empty, returns the full list.\r\n   */\r\n  public getCachedSearch(searchText: string): InputEnumOption[] {\r\n    return this.uiHelpers.cache(this, \"search\",\r\n      () => {\r\n        return this.search(searchText, (this.mode == \"builtIn\" || this.mode == \"custom\") ? this.mode : undefined);\r\n      },\r\n      () => this.listCache?.key + this.rowTypeService.timestamp + searchText + this.categories?.toString() + this.mode);\r\n  }\r\n\r\n  /**\r\n   * Searches the row types.\r\n   * @param searchText The search text. If null or empty, returns the full list.\r\n   */\r\n  public search(searchText: string, group: \"builtIn\" | \"custom\" | undefined): InputEnumOption[] {\r\n    const toOption = (config: CalcRowConfig) => {\r\n      return {\r\n        text: config.label,\r\n        value: config.name,\r\n        title: config.descr,\r\n        ui: {\r\n          color: config.color,\r\n          iconText: config.iconText,\r\n          addedByChild: null,\r\n          // TODO: Requires refactoring\r\n          group: config.group,\r\n          type: config.type,\r\n          rowType: config.rowType,\r\n        },\r\n      };\r\n    };\r\n    const result: InputEnumOption[] = [];\r\n    searchText = (searchText || \"\").trim().toLowerCase();\r\n    this.getRowTypes(group).forEach((rowConfig) => {\r\n      let isParentAdded = false;\r\n      if (\r\n        !searchText\r\n        || (rowConfig.label + rowConfig.descr + rowConfig.name).toLowerCase().indexOf(searchText) >= 0\r\n      ) {\r\n        result.push(toOption(rowConfig));\r\n        isParentAdded = true;\r\n      }\r\n      if (rowConfig.kind?.values) {\r\n        rowConfig.kind.values.forEach((kind) => {\r\n          if (\r\n            !(kind.name == \"undefined\" || kind.name == \"unknown\") &&\r\n            (searchText && (kind.label + kind.descr + kind.name).toLowerCase().indexOf(searchText) >= 0)\r\n          ) {\r\n            if (!isParentAdded) {\r\n              const option = toOption(rowConfig);\r\n              option.ui.addedByChild = true;\r\n              result.push(option);\r\n              isParentAdded = true;\r\n            }\r\n            result.push({\r\n              text: kind.label,\r\n              value: rowConfig.name + \".\" + kind.name,\r\n              title: kind.descr,\r\n              // TODO: Requires refactoring\r\n              ui: {\r\n                group: rowConfig.group,\r\n                type: rowConfig.type,\r\n                rowType: rowConfig.rowType,\r\n              }\r\n            });\r\n          }\r\n        });\r\n      }\r\n    });\r\n    if (result.length === 2 && result[0].ui.addedByChild) {\r\n      // If only one parent with one child (child is exact match) => Merge to one row.\r\n      return [{\r\n        text: result[0].text + \": \" + result[1].text,\r\n        value: result[1].value,\r\n        title: result[1].title,\r\n        ui: result[0].ui,\r\n      }];\r\n    }\r\n    return result;\r\n  }\r\n\r\n  /**\r\n   * Opens an edit dialog for price or default row => Opening just a normal dialog.\r\n   * @param row Row to edit: This should be a price row or default row: Not a custom row.\r\n   */\r\n  public showEdit(row: RowTypeDefinition) {\r\n    if (!row) {\r\n      throw new Error(\"showEditDialog called without a parameter.\");\r\n    }\r\n    const isNew = false; // Add if necessary\r\n    const calc = CalculatorLogic.getBlank();\r\n    calc.usecase.data.standAloneRows = true;\r\n    calc.isReadOnly = false;\r\n\r\n    this.uiHelpers.openEditDialog(\"salaxy-components/calc/rows/CalcRows2019EditDialog.html\", row, {\r\n      calc,\r\n    }, \"\", \"CalcRows2019Controller\").then((result) => {\r\n      if (result.action === \"ok-no-save\") {\r\n        if (isNew) {\r\n          this.list.push(result.item);\r\n        }\r\n      } else if (result.action === \"delete-no-save\") {\r\n        if (!isNew) {\r\n          this.delete(row);\r\n        }\r\n      } else {\r\n        // No changes, cancel\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Deletes a row. This does not save changes.\r\n   * @param row Row to delete.\r\n   */\r\n  public delete(row: RowTypeDefinition) {\r\n    this.list.splice(this.list.indexOf(row), 1);\r\n  }\r\n\r\n  /** Copies the given text to clipboard. */\r\n  public copyToClipboard(text: string) {\r\n    navigator.clipboard.writeText(text);\r\n  }\r\n\r\n  /**\r\n   * Commits the new row in newRow property and adds it to the rows list.\r\n   * Updates usecase and sets the newRow as new blank row.\r\n   */\r\n  public commitNewRow(source: CalculationRowSource | \"price\" | \"copy\", showEdit = false): RowTypeDefinition {\r\n    if (!this.newRow?.type) {\r\n      return null;\r\n    }\r\n    const row = this.getBlank();\r\n    if (source == \"price\") {\r\n      row.source = this.model?.work ? CalculationRowSource.PriceEmployment : CalculationRowSource.PriceCompany;\r\n    } else if (source == \"copy\") {\r\n      row.source = this.model?.work ? CalculationRowSource.CopyEmployment : CalculationRowSource.CopyCompany;\r\n    } else {\r\n      row.source = source;\r\n    }\r\n    if (this.newRow.config?.group === \"custom\") {\r\n      // Custom row type\r\n      row.type = this.newRow.type;\r\n      // HACK: Not sure if we should store the config here => Should probably fetch it on-the-fly when presenting the row.\r\n      row.config = this.getRowTypes(undefined).find(x => x.type === row.type);\r\n      if (!row.config) {\r\n        throw new Error(\"Row type not found in config: \" + row.type);\r\n      }\r\n      row.rowType = row.config.rowType;\r\n      const settingsRow = this.settingsList.find(x => x.type === row.type);\r\n      if (!settingsRow) {\r\n        throw new Error(\"Row type not found in settings: \" + row.type);\r\n      }\r\n      row.data.kind = settingsRow.data.kind;\r\n      row.price = settingsRow.price;\r\n      this.rowTypeService.applyDefaultsToNewRow(row, undefined);\r\n    } else {\r\n      // Old logic\r\n      row.rowType = this.newRow.rowType;\r\n      row.data.kind = this.newRow.data.kind;\r\n      row.type = this.newRow.type;\r\n      row.config = {\r\n        group: \"builtIn\",\r\n      } as any;\r\n    }\r\n\r\n    RowsUsecaseLogic.getUsecaseLogicForCalc(row, CalculatorLogic.getBlank(), true);\r\n    this.list.push(row);\r\n    // TODO: Consider adding this => Does it make sense in prices / default rows?\r\n    // this.rowTypeChanged(row);\r\n    this.$timeout(() => {\r\n      // Reset new row type after timeout to avoid debounce\r\n      this.newRow = this.getBlank();\r\n    }, 300);\r\n    if (showEdit) {\r\n      this.showEdit(row); // TODO: What was the relevance of this: , \"auto\");\r\n    } else {\r\n      this.$timeout(() => {\r\n        let elem: HTMLElement = null;\r\n        elem = (this.$element[0] as HTMLElement).querySelector(\r\n          \"#iptPrice\" + row.rowIndex\r\n        );\r\n        if (elem) {\r\n          elem.focus();\r\n        }\r\n      }, 500);\r\n    }\r\n    return row;\r\n  }\r\n\r\n  /**\r\n   * Shows a dialog for editing the row-type or that shows information about the row-type if read-only.\r\n   * @param rowType The row type to show information about.\r\n   */\r\n  public showRowTypeDetails(rowType: InputEnumOption) {\r\n    let editableType: RowTypeDefinition = this.settingsList\r\n      .find(x => x.source == CalculationRowSource.CustomRowtype && (x as RowTypeDefinition).config.name == rowType.value) as RowTypeDefinition;\r\n    if (!editableType) {\r\n      // Not (an existing) custom row type => Show read-only dialog for a built-in type.\r\n      editableType = {\r\n        rowIndex: 0,\r\n        rowType: rowType.value as CalculationRowType,\r\n        source: CalculationRowSource.CustomRowtype,\r\n        data: {\r\n          dimensions: {},\r\n          accounting: {},\r\n        },\r\n        config: structuredClone(CalcRowsLogic.getRowConfig(rowType.value as CalculationRowType)),\r\n      };\r\n      editableType.config.group =  CalcRowConfigTypeGroup.BuiltIn;\r\n    }\r\n    if (!editableType) {\r\n      throw new Error(\"Row type not found: \" + rowType.value);\r\n    }\r\n    this.uiHelpers.openEditDialog(\"salaxy-components/calc/rows/RowTypeEditDialog.html\", editableType, {\r\n      calc: CalculatorLogic.getBlank(),\r\n      definitionEditor: this.getDialogLogic(editableType.config.group),\r\n    }, \"lg\", \"CalcRows2019Controller\",).then((_result) => {\r\n      if (_result.action == EditDialogKnownActions.Ok) {\r\n        this.rowTypeService.save();\r\n        this.listCache = null;\r\n      }\r\n    });\r\n  }\r\n\r\n  private getDialogLogic(mode: \"builtIn\" | \"custom\") {\r\n    return {\r\n      // Perhaps this is not really necessary => You could just get it from the config?\r\n      mode,\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Creates a new custom row type.\r\n   * @param rowType Base row type for the custom type.\r\n   */\r\n  public async createCustomRowType(rowType: InputEnumOption): Promise<void> {\r\n    const name = prompt(\"Syötä rivityypille ID (a-z, 0-9, _):\");\r\n    if (!name) {\r\n      return;\r\n    }\r\n    if (name.match(/[^a-zA-Z0-9_]/)) {\r\n      alert(\"Virheellinen ID\");\r\n      return;\r\n    }\r\n    if (this.getRowTypes(undefined).find((x) => x.name === name)) {\r\n      alert(`ID on '${name}' jo käytössä`);\r\n      return;\r\n    }\r\n    const config = structuredClone(CalcRowsLogic.getRowConfig(rowType.value as CalculationRowType));\r\n    config.group = CalcRowConfigTypeGroup.Custom;\r\n    config.name = name;\r\n    config.type = \"/custom/\" + name;\r\n    config.label = name + \" (uusi)\";\r\n\r\n    const editableType: RowTypeDefinition = {\r\n      type: \"/custom/\" + name,\r\n      rowType: rowType.value as CalculationRowType,\r\n      rowIndex: 0,\r\n      // HACK: Custom only if really custom\r\n      source: CalculationRowSource.CustomRowtype,\r\n      data: {\r\n        dimensions: {},\r\n        accounting: {},\r\n        scripting: {}\r\n      },\r\n      config,\r\n    };\r\n    const _result = await this.uiHelpers.openEditDialog(\"salaxy-components/calc/rows/RowTypeEditDialog.html\", editableType, {\r\n      calc: CalculatorLogic.getBlank(),\r\n      definitionEditor: this.getDialogLogic(\"custom\"),\r\n    }, \"lg\", \"CalcRows2019Controller\");\r\n    if (_result.action == EditDialogKnownActions.Ok) {\r\n      this.rowTypeService.allCustomRows.push(editableType);\r\n      this.rowTypeService.save().then(() => {\r\n        // TODO: Best UI would be if the tab would be changed from built-in to custom here.\r\n      });\r\n      this.listCache = null;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Deletes a custom row type.\r\n   * @param rowType The row type to delete.\r\n   */\r\n  public deleteCustomRowType(rowType: InputEnumOption) {\r\n    if (!confirm(\"Haluatko poistaa rivityypin '\" + rowType.text + \"'?\")) {\r\n      return;\r\n    }\r\n    this.rowTypeService.deleteRow(this.settingsList.find(x => x.source == CalculationRowSource.CustomRowtype && (x as RowTypeDefinition).config.name == rowType.value));\r\n    this.rowTypeService.save();\r\n  }\r\n\r\n  /**\r\n   * Returns placeholder text for row\r\n   * NOTE: Copied from CalcRows2019Controller - This will be refactored into a logic class!\r\n   * @param row used row\r\n   * @returns row message as string\r\n   */\r\n  public getMessagePlaceholderText(row: UserDefinedRow): string {\r\n    if (row.message) {\r\n      return row.message;\r\n    }\r\n    let label = \"\";\r\n    if (row.rowType === CalculationRowType.IrIncomeType) {\r\n      label = IncomeTypesLogic.getAll().find(\r\n        (x) =>\r\n          (row.data?.kind && x.transactionCode === row.data.kind) ||\r\n          (row.data?.irData?.code > 0 && x.code === row.data.irData.code)\r\n      )?.label;\r\n    } else if (row.rowType == CalculationRowType.AbsencePeriod) {\r\n      label = EnumerationsLogic.getEnumLabel(\r\n        \"AbsenceCauseCode\",\r\n        row.data?.kind\r\n      );\r\n    } else if (\r\n      [\r\n        CalculationRowType.DailyAllowance,\r\n        CalculationRowType.EmploymentTermination,\r\n        CalculationRowType.WorkingTimeCompensation,\r\n        CalculationRowType.Remuneration,\r\n        CalculationRowType.OtherCompensation,\r\n        CalculationRowType.NonProfitOrg,\r\n        CalculationRowType.MealBenefit,\r\n        CalculationRowType.Training,\r\n        CalculationRowType.PaidSickLeave,\r\n        CalculationRowType.TotalWorkerPayment,\r\n        CalculationRowType.TimeRatePay,\r\n      ].includes(row.rowType) &&\r\n      row.data?.kind\r\n    ) {\r\n      label = EnumerationsLogic.getEnumLabel(\r\n        `${row.rowType}Kind`,\r\n        row.data.kind\r\n      );\r\n    }\r\n\r\n    return (\r\n      label || EnumerationsLogic.getEnumLabel(\"CalculationRowType\", row.rowType)\r\n    );\r\n  }\r\n\r\n  /**\r\n   * Gets the list of row types. Method filters based on rowTypes and categories,\r\n   * the texts are language versioned.\r\n   */\r\n  private getRowTypes(group: \"builtIn\" | \"custom\" | undefined): CalcRowConfig[] {\r\n    if (!this.rowTypeService.isReady) {\r\n      console.error(\"Row types not yet loaded, handle this edge case.\");\r\n      return [];\r\n    }\r\n    const result = this.rowTypeService.getConfigs(group, this.categories);\r\n    return result;\r\n  }\r\n\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {\r\n  AccountingTargetSettings, AccountingTargetListItem, ApiItemType, Arrays, ExportMethod, InputEnumOption, InvoicesLogic,\r\n  OpenAPIV3, ServiceModel, ServiceModels, SitemapNode, Translations, TranslationsInstance, TranslationsDictionary,\r\n  Usecase, UsecaseListItem, ServiceModelListItem\r\n} from \"@salaxy/core\";\r\n\r\nimport { UiHelpers } from \"../../services\";\r\nimport { ApiCrudObjectController } from \"../bases\";\r\nimport { SitemapHelper } from \"../../helpers\";\r\n/**\r\n * UI logic for viewing and adding new (modifying) service models\r\n * Service models define service models\r\n */\r\nexport class ServiceModelCrudController extends ApiCrudObjectController<ServiceModel, ServiceModelListItem> {\r\n  isSaving: boolean;\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"ServiceModels\",\r\n    \"UiHelpers\",\r\n    \"$location\",\r\n    \"$routeParams\"\r\n  ];\r\n\r\n  constructor(\r\n    private fullApi: ServiceModels,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any\r\n  ) { // Dependency injection\r\n    super(fullApi, uiHelpers, $location, $routeParams);\r\n  }\r\n\r\n  $onInit() {\r\n    super.$onInit();\r\n    this.initLanguage();\r\n  }\r\n\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"/service-models\",\r\n      detailsUrl: this.detailsUrl || \"/service-models/details/\",\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/ServiceModels.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Event handler for accounting target selection.\r\n   * @param current Settings object to edit/create.\r\n   * @param logic Logic object passed to the dialog controller.\r\n   * @param logic.isReadOnly Read-only flag in logic.\r\n   * @param value Boolean indicating if the item is selected or not.\r\n   * @param item  The selected item.\r\n   * @param allItems All selected items.\r\n   */\r\n  public onAccountingTargetSelect(current: AccountingTargetSettings, logic: { isReadOnly: boolean }, value: boolean, item: AccountingTargetListItem, allItems: AccountingTargetListItem[]) {\r\n    allItems.splice(0, allItems.length);\r\n    logic.isReadOnly = true;\r\n    if (value == true) {\r\n      current.id = item.id;\r\n      current.avatar = item.otherPartyInfo.avatar;\r\n      current.format = item.data.format;\r\n      current.channel = item.data.channel;\r\n      current.method = item.data.method;\r\n      current.availableMethods = Arrays.assureArray(item.data.availableMethods) as ExportMethod[];\r\n      logic.isReadOnly = false;\r\n      allItems.push(item);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Event handler for usecase selection.\r\n   * @param current Settings object to edit/create.\r\n   * @param logic Logic object passed to the dialog controller.\r\n   * @param logic.isReadOnly Read-only flag in logic.\r\n   * @param value Boolean indicating if the item is selected or not.\r\n   * @param item  The selected item.\r\n   * @param allItems All selected items.\r\n   */\r\n  public onUsecaseSelect(current: Usecase, logic: { isReadOnly: boolean }, value: boolean, item: UsecaseListItem, allItems: UsecaseListItem[]) {\r\n    allItems.splice(0, allItems.length);\r\n    logic.isReadOnly = true;\r\n    if (value == true) {\r\n      current.uri = item.reference;\r\n      current.label = item.shortText;\r\n      current.itemType = item.entityType as ApiItemType;\r\n      current.status = item.status;\r\n      current.order = item.data.order;\r\n      logic.isReadOnly = false;\r\n      allItems.push(item);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Return Avatar from current.payment.channels ENUM\r\n   * @returns Avatar\r\n   */\r\n  /* public getPaymentChannelAvatar(item) {\r\n    return InvoicesLogic.getChannelAvatar(item.channel);\r\n  } */\r\n\r\n  /**\r\n   * Created InputEnumOption [] from current.accounting.targets\r\n   * @returns InputEnumOption [] for template\r\n   */\r\n  public getSelectableAccountingTargets(): InputEnumOption[] {\r\n    return this.uiHelpers.cache(this, \"selectableAccountingTargets\", () => {\r\n      return this.current.accounting.targets.map(item => ({\r\n        text: item.avatar.displayName,\r\n        value: item.id,\r\n        ui: { avatar: item.avatar }\r\n      }) as InputEnumOption);\r\n    }, () => this.current.accounting.targets.map(item => item.id)\r\n    );\r\n  }\r\n\r\n  /**\r\n   * Created InputEnumOption [] from all payment channels\r\n   * @returns InputEnumOption [] for template\r\n   */\r\n  public getSelectablePaymentChannels(): InputEnumOption[] {\r\n    if (this.current.payments.channels) {\r\n      return this.uiHelpers.cache(this, \"selectablePaymentChannels\", () => {\r\n        return this.current.payments.channels.map(item => {\r\n          const avatar = InvoicesLogic.getChannelAvatar(item.channel);\r\n          return {\r\n            text: avatar.displayName,\r\n            value: avatar.id,\r\n            ui: avatar\r\n          } as InputEnumOption;\r\n        });\r\n      }, () => this.current.payments.channels.map(item => InvoicesLogic.getChannelAvatar(item.channel).id)\r\n      );\r\n    }\r\n  }\r\n\r\n  /** Returns all payment channels. */\r\n  public getAllPaymentChannels(): InputEnumOption[] {\r\n    return this.uiHelpers.cache(this, \"allSelectablePaymentChannels\", () => {\r\n      return InvoicesLogic.getAllChannels().map(item => {\r\n        return {\r\n          text: item.displayName,\r\n          value: item.id,\r\n          ui: { avatar: item }\r\n        } as InputEnumOption;\r\n      });\r\n    }, () => InvoicesLogic.getAllChannels().map(item => item.id)\r\n    );\r\n  }\r\n\r\n  /**\r\n   * Save service model\r\n   */\r\n  public saveServiceModel() {\r\n    this.isSaving = true;\r\n    this.commitSitemapNode();\r\n    this.save().then(() => {\r\n      this.isSaving = false;\r\n    });\r\n  }\r\n\r\n  /**********************\r\n   * Sitemap functionality\r\n   **********************/\r\n\r\n  private _sitemap: SitemapNode[];\r\n\r\n  private _currentSitemapNode: SitemapNode;\r\n\r\n  /** Current instance of Translations. */\r\n  private translations: TranslationsInstance;\r\n\r\n  /** Clean dictionary for reloading the translations */\r\n  private cleanDictionary: TranslationsDictionary;\r\n\r\n  /** Gets the editable version of the sitemap */\r\n  public get sitemap(): SitemapNode[] {\r\n    if (!this._sitemap) {\r\n      this.translations.setTerms(this.current?.site?.texts);\r\n      this._sitemap = SitemapHelper.getEditableSitemap(this.current.site);\r\n      this.currentSitemapNode = this._sitemap[0];\r\n    }\r\n    return this._sitemap;\r\n  }\r\n\r\n  /** Resets all sitemap changes */\r\n  public resetSitemapChanges(): void {\r\n    this._sitemap = null;\r\n    this.current.site.texts = {};\r\n    this.current.site.sitemap = {};\r\n  }\r\n\r\n  /**\r\n   * Show / hide all nodes in the sitemap.\r\n   * @param open If true open / show all nodes. Default is close all nodes.\r\n   */\r\n  public showHideAll(open: boolean) {\r\n    this.sitemap.forEach((level1) => {\r\n      level1.$edit.$isOpen = open;\r\n      (level1.children || []).forEach((level2) => {\r\n        level2.$edit.$isOpen = open;\r\n      });\r\n    });\r\n  }\r\n\r\n  /** Currently edited sitemap node */\r\n  public get currentSitemapNode(): SitemapNode {\r\n    return this._currentSitemapNode;\r\n  }\r\n  public set currentSitemapNode(value) {\r\n    this.commitSitemapNode();\r\n    this._currentSitemapNode = value;\r\n  }\r\n\r\n  /** Commits the changes of the current sitemap node to current service model (no save to server.)  */\r\n  public commitSitemapNode() {\r\n    const node = this._currentSitemapNode;\r\n    if (node) {\r\n      this.current.site.sitemap = this.current.site.sitemap || {};\r\n      const entries = Object.entries(node.$edit).filter(([key, value]) => value != null && value != \"\" && !(Array.isArray(value) && value.length == 0) && key[0] != \"$\" && !(key == \"visible\" || value == \"default\"));\r\n      if (entries.length) {\r\n        const objToStore = Object.fromEntries(entries);\r\n        if (objToStore.roles) {\r\n          // TODO: Add proper Array editor and remove this (also in getEditableSitemap()).\r\n          objToStore.roles = Arrays.assureArray(objToStore.roles as string).map((x) => x.trim());\r\n        }\r\n        this.current.site.sitemap[node.$edit.$id] = objToStore;\r\n      } else if (this.current.site.sitemap[node.$edit.$id]) {\r\n        delete this.current.site.sitemap[node.$edit.$id];\r\n      }\r\n      this.translations = new TranslationsInstance(angular.copy(this.cleanDictionary));\r\n      this.translations.setTerms(this.current?.site?.texts);\r\n      this._sitemap = SitemapHelper.getEditableSitemap(this.current.site, this._sitemap);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Resets all changes for the current sitemap node.\r\n   * @param resetCommitted If true, also resets the values that are committed to the\r\n   * original values from in the library\r\n   */\r\n  public resetSitemapNode(resetCommitted: boolean) {\r\n    const node = this.currentSitemapNode;\r\n    if (resetCommitted) {\r\n      if (this.current.site.sitemap[node.$edit.$id]) {\r\n        delete this.current.site.sitemap[node.$edit.$id];\r\n      }\r\n    }\r\n    this.translations = new TranslationsInstance(angular.copy(this.cleanDictionary));\r\n    this.translations.setTerms(this.current?.site?.texts);\r\n    this._sitemap = SitemapHelper.getEditableSitemap(this.current.site, this._sitemap);\r\n  }\r\n\r\n  /**\r\n   * Returns true, if the node has test role set.\r\n   * @param node Node to evaluate.\r\n   */\r\n  public getIsTest(node: SitemapNode): boolean {\r\n    const roles = node.$edit.roles?.length ? node.$edit.roles : node.roles;\r\n    return roles ? Arrays.assureArray(roles).indexOf(\"test\") >= 0 : false;\r\n  }\r\n\r\n\r\n  /**\r\n   * Gets all roles except \"test\" (which is displayed by getIsTest) as comma separated string.\r\n   * @param node Node to evaluate.\r\n   */\r\n  public getRoles(node: SitemapNode): string {\r\n    const roles = node.$edit.roles?.length ? node.$edit.roles : node.roles;\r\n    return roles ? Arrays.assureArray(roles).filter((x) => x != \"test\").join(\", \") : null;\r\n  }\r\n\r\n  /** Gets the params schema from the sitemap (service model). */\r\n  public getSitemapParamsSchema(): OpenAPIV3.Document {\r\n    return this.uiHelpers.cache(this, \"sitemapNodeParams\", () => {\r\n      const node = this.currentSitemapNode;\r\n      const result: OpenAPIV3.Document = {\r\n        openapi: \"3.0.1\",\r\n        info: {\r\n          title: \"SitemapParams_\" + node.id,\r\n          version: \"1.0\",\r\n          description: `Sitemap parameters for node ${node.$edit.$id}`,\r\n        },\r\n        paths: {},\r\n        components: {\r\n          schemas: {},\r\n        }\r\n      };\r\n      this.addNodeParamSchemas(this.sitemap, result.components.schemas);\r\n      return result;\r\n    }, () => this.currentSitemapNode?.$edit.$id);\r\n  }\r\n\r\n  /** Field to export / import the current object (shown in code editor). */\r\n  public json: string;\r\n\r\n  /** Exports the current object as json to property this.json. */\r\n  public exportJson() {\r\n    this.json = JSON.stringify(this.current, null, 2);\r\n  }\r\n\r\n  /** Sets current object from the JSON (this.json shown in code editor). */\r\n  public importJson() {\r\n    this._sitemap = null;\r\n    this._currentSitemapNode = null;\r\n    this.translations = new TranslationsInstance(angular.copy(this.cleanDictionary));\r\n    this.translations.setTerms(this.current?.site?.texts);\r\n    this.setCurrentValue(JSON.parse(this.json));\r\n  }\r\n\r\n  private addNodeParamSchemas(nodes: SitemapNode[], schemas: { [key: string]: OpenAPIV3.SchemaObject | OpenAPIV3.ReferenceObject }): void {\r\n    if (!nodes?.length) {\r\n      return;\r\n    }\r\n    nodes.forEach((node) => {\r\n      if (Object.keys(node.params || {}).length) {\r\n        const schema = angular.copy(this.defaultParamsSchema);\r\n        schema.properties = {...schema.properties, ...this.currentSitemapNode.params};\r\n        schemas[node.$edit.$id] = schema;\r\n      } else {\r\n        schemas[node.$edit.$id] = this.defaultParamsSchema;\r\n      }\r\n      this.addNodeParamSchemas(node.children, schemas);\r\n    });\r\n  }\r\n\r\n  private defaultParamsSchema: OpenAPIV3.SchemaObject = {\r\n    title: \"Current sitemap node\",\r\n    type: \"object\",\r\n    properties: {}\r\n  };\r\n\r\n  /**\r\n   * Translates the given key to current language with the translations in the current service model\r\n   * @param key The translation key\r\n   */\r\n  public translate(key: string): string {\r\n    return this.translations.get(key);\r\n  }\r\n\r\n  /** Initializes the Translations instance (loads the language and sets the current language). */\r\n  private initLanguage() {\r\n    const lang = Translations.getLanguage();\r\n    if (!this.translations) {\r\n      this.translations = new TranslationsInstance();\r\n      this.translations.localesPath = Translations.instance.localesPath; // Get the locales path from the current site (global instance)\r\n    }\r\n    this.translations.loadLanguage(lang)\r\n      .then(() => {\r\n        this.cleanDictionary = angular.copy(this.translations.getCurrentDictionary());\r\n        this.translations.setLanguage(lang);\r\n        this.translations.setTerms(this.current?.site?.texts);\r\n      });\r\n  }\r\n\r\n}","import angular from \"angular\";\r\nimport { Configs } from \"@salaxy/core\";\r\n\r\n/**\r\n * Controller for code editing user interfaces: JSON Schema, JSON, JavaScript and HTML.\r\n */\r\nexport class SxyCodeEditorController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$transclude\", \"$element\", \"$sce\"];\r\n\r\n  /** Type of user interface to render: code-editor or basic HTML (textarea/pre) */\r\n  public mode: \"monaco\" | \"basic\";\r\n\r\n  /** If true, the component is read-only */\r\n  public readOnly: boolean;\r\n\r\n  /**\r\n   * Type of the main object that is called \"item\" in the code.\r\n   * Type should be one of @salaxy/core types (e.g. \"Calculation\") or supported\r\n   * native types (currently [\"any\", \"string\", \"[]\"]). Default is any.\r\n   */\r\n  public itemType: string;\r\n\r\n  /**\r\n   * Language of the code, e.g. \"javascript\" (default), \"html\", \"json\" or \"css\".\r\n   * Currently only affects the externalcodeeditor.\r\n   */\r\n  public lang: string;\r\n\r\n  /** The model that is bound to the input */\r\n  public model: angular.INgModelController;\r\n\r\n  /** The height of the editor as CSS, (e.g. \"calc(100vh - 600px)\"). Default is \"400px\" */\r\n  public height: string;\r\n\r\n  /** Type of the editor to use: \"monaco\" (default), \"sample\" or \"formula\". */\r\n  public editor: \"monaco\" | \"sample\" | \"formula\";\r\n\r\n  /**\r\n   * Raw value field, mainly used in direct AngularJS NgModel data binding and as internal storage.\r\n   * Typically, you should use get/set code for display and setting of the value.\r\n   */\r\n  public value: string;\r\n\r\n  /** salaxy code-editor URL */\r\n  public codeEditorUrl: string;\r\n\r\n  private targetOrigin: string;\r\n\r\n  /**\r\n   * IFrame element that hosts the external code editor.\r\n   * Only set after the window has loaded and sent the initialization message (external code editor is ready).\r\n   */\r\n  public codeEditorIFrame: HTMLIFrameElement;\r\n\r\n  constructor(\r\n\r\n    private $transclude: angular.ITranscludeFunction,\r\n\r\n    private $element: JQLite,\r\n    private $sce: angular.ISCEService\r\n  ) {\r\n\r\n  }\r\n\r\n  /** Initializes the controller */\r\n  public $onInit() {\r\n    if (!this.editor) {\r\n      this.editor = \"monaco\";\r\n    }\r\n    this.registerTransclude();\r\n    this.targetOrigin = Configs.current.codeEditor;\r\n    if (this.model) {\r\n      this.model.$render = () => {\r\n        this.value = this.model.$viewValue;\r\n        if (this.codeEditorIFrame) {\r\n          this.codeEditorIFrame.contentWindow.postMessage({ code: this.code }, this.codeEditorIFrame.contentWindow.origin);\r\n        }\r\n      };\r\n    }\r\n    this.registerCodeEditorWindow();\r\n  }\r\n\r\n  /** Clears the window event hooks */\r\n  public $onDestroy() {\r\n    window.removeEventListener(\"message\", this.onEditorMessage, false);\r\n  }\r\n\r\n  /** The code that is shown in editor. */\r\n  public get code(): string {\r\n    return this.value;\r\n  }\r\n  public set code(value: string) {\r\n    this.value = value;\r\n    if (this.model) {\r\n      this.model.$setViewValue(this.value);\r\n    }\r\n  }\r\n\r\n  /** On change of the value, do preventive operations and set value to model. */\r\n  protected onChange() {\r\n    if (this.model) {\r\n      this.model.$setViewValue(this.value);\r\n    }\r\n  }\r\n\r\n  private registerCodeEditorWindow() {\r\n    if (this.mode == \"basic\") {\r\n      return;\r\n    }\r\n    if(!this.targetOrigin) {\r\n      return;\r\n    }\r\n    this.codeEditorUrl = this.$sce.trustAsResourceUrl(`${this.targetOrigin}?editor=${this.editor}&readonly=${this.readOnly}&lang=${ this.lang || \"\"}`);\r\n    if (this.itemType) {\r\n      this.codeEditorUrl = this.$sce.trustAsResourceUrl(`${this.codeEditorUrl}&item=${this.itemType}`);\r\n    }\r\n    window.addEventListener(\"message\", this.onEditorMessage, false);\r\n  }\r\n\r\n  private onEditorMessage = (ev: MessageEvent<any>) => {\r\n    if (ev.origin !== this.targetOrigin) {\r\n      return;\r\n    }\r\n    if (this.codeEditorIFrame) {\r\n      if (this.codeEditorIFrame.contentWindow !== ev.source) {\r\n        return;\r\n      }\r\n      if (Object.prototype.hasOwnProperty.call(ev.data, \"code\")) {\r\n        this.code = ev.data.code;\r\n      }\r\n    }\r\n    else if (Object.prototype.hasOwnProperty.call(ev.data, \"loaded\")) {\r\n      // First message is for registration only.\r\n      const iFrame = this.codeEditorIFrame = (this.$element.find(\"iframe\")[0] as HTMLIFrameElement);\r\n      if (iFrame.contentWindow !== ev.source) {\r\n        return;\r\n      }\r\n      this.codeEditorIFrame = iFrame;\r\n      iFrame.contentWindow.postMessage({ code: this.code }, this.targetOrigin);\r\n      return;\r\n    }\r\n  };\r\n\r\n  private registerTransclude() {\r\n    // eslint-disable-next-line @typescript-eslint/no-unused-vars\r\n    this.$transclude((clonedElement, scope) => {\r\n      let content = \"\";\r\n      for (let i = 0; i < clonedElement.length; i++) {\r\n        if (clonedElement[i].nodeType === 3) {\r\n          content += (clonedElement[i] as unknown as Text).textContent;\r\n        } else {\r\n          content += (clonedElement[i].outerHTML || \"\").replace(\" ng-scope\", \"\").replace(\"ng-scope\", \"\").replace(\" class=\\\"\\\"\", \"\");\r\n        }\r\n      }\r\n      content = content.trim();\r\n      if (content) {\r\n        this.value = content;\r\n      }\r\n      return clonedElement;\r\n    });\r\n  }\r\n}","import angular from \"angular\";\r\n\r\nimport { OpenAPIV3 } from \"@salaxy/core\";\r\n\r\nimport { ApiValidation, ApiValidationError, ApiValidationErrorType, FormHelpers, InputMetadata, JsonInputType, JsonSchemaProperty, JsonSchemaUtils, Objects, Translations } from \"@salaxy/core\";\r\n\r\nimport { JsonSchemaService, UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Sxy form contains the definition for an editor used interface that\r\n * typically corresponds to an HTML form.\r\n */\r\nexport class SxyFormController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"JsonSchemaService\", \"$rootScope\", \"UiHelpers\", \"$timeout\"];\r\n\r\n  /** The model that is being edited. */\r\n  public model: any;\r\n\r\n  /** The schema model */\r\n  public schemaModel: OpenAPIV3.SchemaObject;\r\n\r\n  /**\r\n   * The translation code for the label / title.\r\n   * Default is \"SALAXY.MODEL.[type].title\"] or if not available, just the type text.\r\n   */\r\n  public label: string;\r\n\r\n  /**\r\n   * Sets the entire form as read-only. The value is true/1.\r\n   * Default value false/0, has no real effect: The behavior comes from either input or schema.\r\n   * Individual field may still be set read-only=false/1 to make it editable.\r\n   */\r\n  public readOnly: string;\r\n\r\n  /** If true, the schema loading is ready: The form can be rendered. */\r\n  public isReady: boolean;\r\n\r\n  /**\r\n   * URL for the Open API document that contains the definition for the type.\r\n   * The url can be an absolute url, relative url or an url with salaxy-secure/ -prefix.\r\n   * The salaxy-secure/ -prefix will be replaced in runtime with the salaxy api server url of the curren environment.\r\n   */\r\n  public openApi: string;\r\n\r\n  /** References a schema document directly: the schema document is not fetched from the UI */\r\n  public openApiDoc: any;\r\n\r\n  /** If true, shows the debugger view for the form. */\r\n  public debugger: boolean;\r\n\r\n  /** Unique id for the form. Init assures that this is unique in the AngularJs root scope. */\r\n  public id: string;\r\n\r\n  /** The angular form with validation etc. */\r\n  public ngForm: angular.IFormController;\r\n\r\n  /** If true, the inner for is auto-generated. */\r\n  public autoGen: boolean;\r\n\r\n  private lastUniqueId = 0;\r\n\r\n  private _info: OpenAPIV3.InfoObject;\r\n\r\n  public _type: string;\r\n\r\n  constructor(\r\n    private jsonSchemaService: JsonSchemaService,\r\n    private $rootScope: angular.IRootScopeService,\r\n    private uiHelpers: UiHelpers,\r\n    private $timeout: angular.ITimeoutService,\r\n  ) {\r\n    // Dependency injection\r\n  }\r\n\r\n  /** Initializes the controller */\r\n  public $onInit() {\r\n    this.init();\r\n  }\r\n\r\n  /**\r\n   * Type of the model: Bases for the user interface.\r\n   * This may be either a TypeScript typename or OpenApi schema component name.\r\n   */\r\n  public get type(): string {\r\n    return this._type;\r\n  }\r\n  public set type(value: string) {\r\n    this._type = value;\r\n    if (this.id) {\r\n      // Init has been done => redo and refresh\r\n      this.isReady = false;\r\n      this.$timeout().then(() => {\r\n        this.init();\r\n      });\r\n    }\r\n  }\r\n\r\n  /** Initializes or re-initializes the data model. */\r\n  public init() {\r\n    this.model = this.model || {};\r\n    this.id = (this.type || \"undefined\") + this.$rootScope.$id.toString();\r\n    if (this.openApi && this.type) {\r\n      if (this.openApiDoc) {\r\n        // TODO: Assure that the schema is cached in final implementation\r\n        this.jsonSchemaService.addSchemaDocument(this.openApi, this.openApiDoc);\r\n        this.schemaModel = this.jsonSchemaService.findSchema(this.openApi, this.type);\r\n        if (!this.model) {\r\n          this.model = {};\r\n        }\r\n        this._info = this.openApiDoc.info || {\r\n          title: \"unknown\",\r\n          version: \"0\",\r\n        };\r\n        this.label = this.label || Translations.getWithDefault(`${this.getModelNamespace()}.${this.type}.title`, this.schemaModel?.title || this.type);\r\n        this.isReady = true;\r\n      } else {\r\n        this.jsonSchemaService.assureSchemaDocument(this.openApi).then((openApiDoc) => {\r\n          this._info = openApiDoc.info || {\r\n            title: \"unknown\",\r\n            version: \"0\",\r\n          };\r\n          this.schemaModel = this.jsonSchemaService.findSchema(this.openApi, this.type);\r\n          if (!this.model) {\r\n            this.model = {};\r\n          }\r\n          this.label = this.label || Translations.getWithDefault(`${this.getModelNamespace()}.${this.type}.title`, this.schemaModel?.title || this.type);\r\n          this.isReady = true;\r\n        });\r\n      }\r\n    } else {\r\n      this.schemaModel = null;\r\n      this.isReady = true;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Registers an input (control) to a data point in the form.\r\n   * @param path Data path that the input registers to.\r\n   * This should be either \"form\" to register to the root of the form or\r\n   * more typically \"form.prop.perhapsSubProperty\" to register to a property.\r\n   */\r\n  public registerInput(path: string, type?: JsonInputType, format?: string): {\r\n    /** Description of the property or if path is \"form\" the data model of the form. */\r\n    prop: JsonSchemaProperty,\r\n    /** True, if the element is the form root. Otherwise this is a property.  */\r\n    isRoot: boolean,\r\n    /** Unique ID within the form */\r\n    id: string,\r\n    /** AngularJS template for rendering the input. */\r\n    templateUrl: string,\r\n    /** Metadata that can be used for rendering the input */\r\n    input: InputMetadata,\r\n  } {\r\n    if (!(path || \"\").trim()) {\r\n      throw Error(\"Path / model is required for each sxy-input element. Use e.g. 'form.temp'.\");\r\n    }\r\n    const result = {\r\n      prop: this.getProperty(path),\r\n      id: null,\r\n      isRoot: false,\r\n      templateUrl: null,\r\n      input: null,\r\n    };\r\n    if (!result.prop) {\r\n      // This is not a property\r\n      result.isRoot = path === \"form\";\r\n      if (result.isRoot) {\r\n        // \"form\": bound to root\r\n        result.id = `${this.id}_form${this.getUniqueId()}`;\r\n        result.input = this.schemaModel ? FormHelpers.getInputForSelf(this.schemaModel, null, path) : null;\r\n        if (result.input) {\r\n          result.input.format = format || result.input.format;\r\n        }\r\n        result.prop = {\r\n          isRequired: false,\r\n          parentName: this.type,\r\n          propertyName: null,\r\n          schema: this.schemaModel,\r\n        };\r\n        result.templateUrl = result.input ? this.jsonSchemaService.getTemplate(result.input) : null;\r\n      } else {\r\n        // Property path is there, but it is not found in the schema (perhaps a new or unofficial property)\r\n        const propertyName = path.substr(path.lastIndexOf(\".\") + 1);\r\n        result.id = `${this.id}_${propertyName}${this.getUniqueId()}`;\r\n        type = type || \"string\";\r\n        result.input = {\r\n          name: propertyName,\r\n          format,\r\n          isEnum: null,\r\n          path,\r\n          type,\r\n          content: `Property \"${path}\" does not exist in schema.`,\r\n        };\r\n        result.prop = {\r\n          isRequired: false,\r\n          parentName: null,\r\n          propertyName,\r\n          schema: null,\r\n        };\r\n        result.templateUrl = this.jsonSchemaService.getTemplate(result.input);\r\n      }\r\n    } else {\r\n      result.id = `${this.id}_${result.prop.propertyName}${this.getUniqueId()}`;\r\n      result.input = FormHelpers.getInputMetadata(result.prop.schema, result.prop.propertyName, path);\r\n      result.input.format = format || result.input.format;\r\n      result.templateUrl = this.jsonSchemaService.getTemplate(result.input);\r\n    }\r\n    this.registeredInputs[result.id] = result.prop;\r\n    return result;\r\n  }\r\n\r\n  /**\r\n   * Gets the model for a property that an invidual input within the form can bind to.\r\n   * @param path Property path, currently always starting with \"form.\",\r\n   * e.g. \"form.id\" or \"form.employer.accountId\"\r\n   */\r\n  public getProperty(path: string): JsonSchemaProperty {\r\n    const propPath = this.getFormPath(path);\r\n    if (!propPath) {\r\n      return null; // Path is \"form\" - this is not a property.\r\n    }\r\n    return JsonSchemaUtils.getProperty(this.schemaModel, propPath);\r\n  }\r\n\r\n  /**\r\n   * Sets a value in the model using property path.\r\n   * @param path Property path, currently always starting with \"form.\",\r\n   * e.g. \"form.id\" or \"form.owner.id\"\r\n   * @param value Value to set to model.\r\n   * @returns True if the property is set. Value is not set if there is no propertyPath/obj or\r\n   * if the value is already set to new value (currently strict equality check \"===\",\r\n   * but may be changed without it being a breaking change).\r\n   */\r\n  public setValue(path: string, value: any): boolean {\r\n    const propPath = this.getFormPath(path);\r\n    if (!propPath) {\r\n      throw new Error(\"Cannot set the objects own value. setValue only supports setting property values.\");\r\n    }\r\n    return Objects.setProperty(this.model, propPath, value);\r\n  }\r\n\r\n  /**\r\n   * Gets a value from the model using property path.\r\n   * @param path Property path, currently always starting with \"form.\",\r\n   * e.g. \"form.id\" or \"form.owner.id\"\r\n   */\r\n  public getValue(path: string): any {\r\n    const propPath = this.getFormPath(path);\r\n    if (!propPath) {\r\n      return this.model;\r\n    }\r\n    return Objects.getProperty(this.model, this.getFormPath(path));\r\n  }\r\n\r\n  /** Gets the validation based on the current form. */\r\n  public getValidation(): ApiValidation {\r\n    const rawErrors: string[][] = [];\r\n    if (this.ngForm.$invalid) {\r\n      for (const key of Object.keys(this.ngForm.$error)) {\r\n        for (let index = 0; index < this.ngForm.$error[key].length; index++) {\r\n          rawErrors.push([key, this.ngForm.$error[key][index].$name]);\r\n        }\r\n      }\r\n    }\r\n    return this.uiHelpers.cache(this, \"validation\", () => {\r\n      const errors = rawErrors.map((raw) => {\r\n        const key = raw[0];\r\n        const prop = this.registeredInputs[raw[1]];\r\n        const error: ApiValidationError = {\r\n          code: key,\r\n          key: raw[1],\r\n          type: raw[0] === \"required\" ? ApiValidationErrorType.Required : ApiValidationErrorType.Invalid,\r\n          msg: Translations.getWithDefault(\"SALAXY.VALIDATION.ValidationErrors.\" + key,\r\n            Translations.get(\"SALAXY.VALIDATION.ValidationErrors.unknown\", { error: key })),\r\n        };\r\n        if (prop?.propertyName) {\r\n          if (prop.parentName) {\r\n            // TODO: Better form path from a combination of prop/input\r\n            error.key = prop.parentName + \".\" + prop.propertyName;\r\n          } else {\r\n            error.key = prop.propertyName;\r\n          }\r\n          error.msg = Translations.getWithDefault(`${this.getModelNamespace()}.${error.key}.title`, prop.propertyName) + \": \" + error.msg;\r\n        }\r\n        return error;\r\n      });\r\n      return {\r\n        hasAllRequiredFields: !errors.find((x) => x.type === ApiValidationErrorType.Required),\r\n        isValid: errors.length === 0,\r\n        errors,\r\n      };\r\n    }, () => rawErrors);\r\n  }\r\n\r\n  /** Returns the namespace for the current openApi model, the default is SALAXY.MODEL */\r\n  public getModelNamespace(): string {\r\n    return this._info?.[\"x-salaxy-model-namespace\"] || \"SALAXY.MODEL\";\r\n  }\r\n\r\n  /** Returns the namespace for the current openApi enums, the default is SALAXY.ENUM */\r\n  public getEnumNamespace(): string {\r\n    return this._info?.[\"x-salaxy-enum-namespace\"] || \"SALAXY.ENUM\";\r\n  }\r\n\r\n  protected registeredInputs: {\r\n    [key: string]: JsonSchemaProperty;\r\n  } = {};\r\n\r\n  private getFormPath(path: string): string {\r\n    if (path === \"form\") {\r\n      return null;\r\n    }\r\n    if (!path.startsWith(\"form.\")) {\r\n      throw new Error(\"Currently, only 'form' and 'form.' supported in property paths.\");\r\n    }\r\n    return path.replace(\"form.\", \"\");\r\n  }\r\n\r\n  /** Gets a unique id to form components / inputs. This may later further track the inputs. */\r\n  private getUniqueId(): number {\r\n    return this.lastUniqueId++;\r\n  }\r\n}\r\n","\r\n/**\r\n * Controller for misc form elements that are not inputs:\r\n * These are not bound to models, but handle misc. form layout and grouping tasks.\r\n */\r\nexport class SxyFormElementController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [];\r\n\r\n  /**\r\n   * Typing depending on the component.\r\n   *\r\n   * - sxy-alert: \"default\" | \"primary\" | \"success\" | \"info\" | \"warning\" | \"danger\"\r\n   */\r\n  public type: \"default\" | \"primary\" | \"success\" | \"info\" | \"warning\" | \"danger\" | string;\r\n\r\n  /**\r\n   * For sxy-fieldset, defines the model that the fieldset should generate fields for.\r\n   * Should be \"form\" to refer to the current form or property path starting\r\n   * with \"form\", e.g. \"form.result.employerCalc\"\r\n   */\r\n  public model: string;\r\n\r\n  /**\r\n   * For alerts, possibility to speicfy a font-awesome icon.\r\n   * Setting \"none\", will show no icon.\r\n   * If not set, it is determined by type.\r\n   */\r\n  public icon: \"none\" | string;\r\n\r\n  constructor() {\r\n    // Dependency injection\r\n  }\r\n\r\n  /** Initializes the controller */\r\n  public $onInit() {\r\n    // init\r\n  }\r\n\r\n  /** For alert component, gets the classes that format the alert. */\r\n  public getAlertClasses() {\r\n    switch (this.type) {\r\n      case \"default\":\r\n      case \"primary\":\r\n      case \"success\":\r\n      case \"info\":\r\n      case \"warning\":\r\n      case \"danger\":\r\n        return `alert alert-${this.type}`;\r\n      case \"error\":\r\n        return `alert alert-danger`;\r\n      default:\r\n        return `alert alert-info`;\r\n    }\r\n  }\r\n\r\n  /** Returns the icon based on the type. */\r\n  public getAlertIcon() {\r\n    if (!this.icon) {\r\n      switch (this.type) {\r\n        case \"danger\":\r\n        case \"error\":\r\n          return \"fa-exclamation\";\r\n        case \"success\":\r\n          return \"fa-check\";\r\n        case \"warning\":\r\n          return \"fa-exclamation-triangle\";\r\n        default:\r\n          return \"fa-info\";\r\n      }\r\n    }\r\n    if (this.icon === \"none\") {\r\n      return null;\r\n    }\r\n    return this.icon;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {\r\n  ApiValidation, ApiValidationErrorType, Arrays, CellRenderingLogic, Configs, DataMapper, DataMappersLogic, EnumerationsLogic, Exportable, FileParser,\r\n  Importable, InputEnumOption, JsonSchemaUtils, OpenAPIV3\r\n} from \"@salaxy/core\";\r\n\r\nimport { UiHelpers, JsonSchemaService, FileService } from \"../../services\";\r\n\r\n/** Provides Grid UI for viewing and editing arrays. */\r\nexport class SxyGridController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"JsonSchemaService\", \"UiHelpers\", \"$element\", \"$timeout\", \"FileService\"];\r\n\r\n  /** Default bindings to the components */\r\n  public static bindings = {\r\n\r\n    /**\r\n     * The schema definition that defines the structure of the grid.\r\n     */\r\n    schemaDef: \"<\",\r\n\r\n    /**\r\n     * URL of the schema document that contains the schemaDef.\r\n     * If set with schema in init, loads the document.\r\n     */\r\n    doc: \"@\",\r\n\r\n    /**\r\n     * Key of schemaDef in doc.\r\n     * If set with doc in init, will load the schema document from server and set the schemaDef.\r\n     */\r\n    schema: \"@\",\r\n\r\n    /** Data that is rendered / edited in the grid. */\r\n    data: \"<\",\r\n\r\n    /**\r\n     * List of columns to include in the grid. Raw field names - may be a property tree.\r\n     */\r\n    include: \"<\",\r\n\r\n    /**\r\n     * List of columns to exclude from the grid.\r\n     * This property is currenlty used only if include property is undefined, i.e. in default\r\n     * rendering, which will render the first-level properties. As such, exclude does not really support property paths.\r\n     */\r\n    exclude: \"<\",\r\n\r\n  };\r\n\r\n  /**\r\n   * URL of the schema document that contains the schemaDef.\r\n   * If set with schema in init, loads the document.\r\n   */\r\n  public doc: string;\r\n\r\n  /**\r\n   * Key of schemaDef in doc.\r\n   * If set with doc in init (and schemaDef not set),\r\n   * will load the schema document from server and set the schemaDef.\r\n   */\r\n  public schema: string;\r\n\r\n  /** Data that is rendered / edited in the grid. */\r\n  public data: any[];\r\n\r\n  /**\r\n   * List of columns to include in the grid. Raw field names - may be a property tree.\r\n   */\r\n  public include: string | string[];\r\n\r\n  /**\r\n   * List of columns to exclude from the grid.\r\n   * This property is currenlty used only if include property is undefined, i.e. in default\r\n   * rendering, which will render the first-level properties. As such, exclude does not really support property paths.\r\n   */\r\n  public exclude: string | string[];\r\n\r\n  /** Array of items that is selected in the grid. These are grid nodes, not data items. */\r\n  public selection: any[] = [];\r\n\r\n  /**\r\n   * The grid options\r\n   * TODO: Consider adding at least some typing.\r\n   */\r\n  private gridOptions: any;\r\n\r\n  private isInitDone = false;\r\n\r\n  _schemaDef: OpenAPIV3.NonArraySchemaObject;\r\n\r\n  constructor(\r\n    private jsonSchemaService: JsonSchemaService,\r\n    private uiHelpers: UiHelpers,\r\n    private $element: JQLite,\r\n    private $timeout: angular.ITimeoutService,\r\n\r\n    private fileService: FileService,\r\n  ) {\r\n    // Dependency injection\r\n  }\r\n\r\n  /** Initializes the controller */\r\n  public $onInit() {\r\n    this.initModel();\r\n  }\r\n\r\n  /**\r\n   * The schema definition that defines the structure of each item in the grid.\r\n   */\r\n  public get schemaDef(): OpenAPIV3.NonArraySchemaObject {\r\n    return this._schemaDef;\r\n  }\r\n  public set schemaDef(value: OpenAPIV3.NonArraySchemaObject) {\r\n    this._schemaDef = value;\r\n    if (this.isInitDone) {\r\n      this.renderGrid();\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Adds an empty row to the grid.\r\n   * @param rowData Data to add to the grid. Array of of objects.\r\n   * @param index Index position. If null, will add to the end.\r\n   */\r\n  public addRow(rowData: any[] = [{}], index = null): void {\r\n    this.gridOptions.api.applyTransaction({\r\n      add: rowData,\r\n      addIndex: index,\r\n    });\r\n    this.commit();\r\n  }\r\n\r\n  /** Delete the selected rows from the grid. */\r\n  public deleteSelectedRows(): void {\r\n    const selectedRows = this.gridOptions.api.getSelectedRows();\r\n    this.gridOptions.api.applyTransaction({ remove: selectedRows });\r\n    this.commit();\r\n  }\r\n\r\n  /** Clears all rows in the grid. Sets the data to an empty array. */\r\n  public clear(): void {\r\n    this.gridOptions.api.setRowData([]);\r\n    this.commit();\r\n  }\r\n\r\n  /** Commits the changes in the grid to the source data. */\r\n  public commit(): void {\r\n    this.data.length = 0;\r\n    this.gridOptions.api.forEachNode((node) => {\r\n      this.data.push(node.data);\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Validates a single item based on the schema.\r\n   * @param item Item to validate\r\n   */\r\n  public validateItem(item: any): ApiValidation {\r\n    // TODO: Move to core JsonSchema helpers.\r\n    if (!item) {\r\n      return {\r\n        isValid: false,\r\n        hasAllRequiredFields: false,\r\n        errors: [{\r\n          msg: \"Row is empty / null, this is not allowed: Null rows must be filtered out before adding.\",\r\n          type: ApiValidationErrorType.General,\r\n        }],\r\n      };\r\n    }\r\n    const result: ApiValidation = {\r\n      errors: [],\r\n    };\r\n\r\n    Object.keys(item).forEach((key) => {\r\n      const val = item[key];\r\n      const prop = (this.schemaDef || {}).properties[key] as OpenAPIV3.SchemaObject;\r\n      if (prop) {\r\n        // Empty values are OK at least for now, required items may be added later to validation\r\n        if (val) {\r\n          switch (prop.type) {\r\n            case \"integer\":\r\n              if (!Number.isInteger(+val)) {\r\n                result.errors.push({\r\n                  msg: `Value '${val}' in ${key} is not an integer.`,\r\n                  type: ApiValidationErrorType.Invalid,\r\n                  key\r\n                });\r\n              }\r\n              break;\r\n            case \"number\":\r\n              if (isNaN(val)) {\r\n                result.errors.push({\r\n                  msg: `Value '${val}' in ${key} is not a number.`,\r\n                  type: ApiValidationErrorType.Invalid,\r\n                  key\r\n                });\r\n              }\r\n              break;\r\n            case \"boolean\":\r\n              // TODO: Perhaps add 0/1 and kyllä/ei\r\n              if ([\"true\", \"false\"].indexOf((val + \"\").toLowerCase()) < 0) {\r\n                result.errors.push({\r\n                  msg: `Value '${val}' in ${key} is not a valid boolean (true/false).`,\r\n                  type: ApiValidationErrorType.Invalid,\r\n                  key\r\n                });\r\n              }\r\n              break;\r\n            case \"array\":\r\n              if (!Array.isArray(val)) {\r\n                result.errors.push({\r\n                  msg: `Value '${val}' in ${key} is not a valid array.`,\r\n                  type: ApiValidationErrorType.Invalid,\r\n                  key\r\n                });\r\n              }\r\n              break;\r\n          }\r\n        }\r\n      } else {\r\n        result.errors.push({\r\n          msg: `Property ${key} is not defined in the schema.`,\r\n          type: ApiValidationErrorType.Warning,\r\n        });\r\n      }\r\n    });\r\n    (result as any).hasAllRequiredFields = !result.errors.find((x) => x.type == ApiValidationErrorType.Required);\r\n    (result as any).isValid = !result.errors.find((x) => x.type !== ApiValidationErrorType.Warning);\r\n    return result;\r\n  }\r\n\r\n  /**\r\n   * Takes an input object with string based data and maps to correct typing or empty objects.\r\n   * E.g. \"2\" => 2, \"True\" = true. Original data is not changed and only data in schema is returned.\r\n   * Keep the method in sync with validateItem.\r\n   * @param item Item to convert as typed item.\r\n   * @returns Typed item\r\n   */\r\n  public convertTypes(item: any): any {\r\n    // TODO: Move to core JsonSchema helpers.\r\n    if (!item) {\r\n      return null;\r\n    }\r\n    const result = {};\r\n    Object.keys(item).forEach((key) => {\r\n      const val = item[key];\r\n      const prop = (this.schemaDef || {}).properties[key] as OpenAPIV3.SchemaObject;\r\n      if (prop) {\r\n        // Empty values are OK at least for now, required items may be added later to validation\r\n        if (val) {\r\n          switch (prop.type) {\r\n            case \"integer\":\r\n              if (Number.isInteger(+val)) {\r\n                result[key] = Number(val);\r\n              }\r\n              break;\r\n            case \"number\":\r\n              if (!isNaN(val)) {\r\n                result[key] = Number(val);\r\n              }\r\n              break;\r\n            case \"boolean\":\r\n              if ([\"true\", \"false\"].indexOf((val + \"\").toLowerCase()) >= 0) {\r\n                // TODO: Perhaps add 0/1 and kyllä/ei\r\n                result[key] = (val + \"\").toLowerCase() == \"true\";\r\n              }\r\n              break;\r\n            case \"array\":\r\n              if (!Array.isArray(val)) {\r\n                // TODO: Consider adding validation to sub-items. This would probably need to be recursive.\r\n                result[key] = val;\r\n              }\r\n              break;\r\n            case \"string\":\r\n              result[key] = val;\r\n              break;\r\n          }\r\n        }\r\n      }\r\n    });\r\n    return result;\r\n  }\r\n\r\n  /** Gets the exportable for the current data model. */\r\n  public getExportable(): Exportable<any> {\r\n\r\n    const fullMapper = this.getMapper().reverse(this.schema + \"FullExport\", `Full object export for ${this.schema}`);\r\n\r\n    const exptMapper = new DataMapper<{ [key: string]: string }, any>(this.schema + \"GridExport\", `Table export for ${this.schema}`);\r\n    exptMapper.setSchema(this.schemaDef, this.schema, \"source\");\r\n    exptMapper.setPathsFromSourceSchema(this.getFields());\r\n\r\n    const mappers = [exptMapper, fullMapper];\r\n\r\n    const result: Exportable<any> = {\r\n      exporters: this.fileService.getDefaultExporters(),\r\n      getExportMappers: () => {\r\n        return mappers.map((x) => DataMappersLogic.getInfo(x));\r\n      },\r\n      getExportMapper: (id: string) => {\r\n        return Promise.resolve(mappers.find((x) => x.uri == id));\r\n      },\r\n      list: (maxCount) => {\r\n        const result = maxCount > 0 ? this.data.slice(0, maxCount) : this.data;\r\n        return Promise.resolve(result);\r\n      },\r\n      getSingle: (item) => {\r\n        return Promise.resolve(item);\r\n      },\r\n    };\r\n\r\n    return result;\r\n\r\n  }\r\n\r\n  /** Gets the importable for the current data model. */\r\n  public getImportable(): Importable<any> {\r\n    const mapper = this.getMapper();\r\n    return {\r\n      getImportMappers: () => {\r\n        const result: InputEnumOption = {\r\n          value: null,\r\n          text: mapper.title,\r\n        };\r\n        return [result];\r\n      },\r\n      getImportMapper() {\r\n        return Promise.resolve(mapper);\r\n      },\r\n      finalize: (items) => {\r\n        this.clear();\r\n        this.addRow(items.map((value) => this.convertTypes(value)));\r\n        this.commit();\r\n        return Promise.resolve();\r\n      },\r\n      validate: (itemToValidate: any): Promise<{ item: any, validation: ApiValidation }> => {\r\n        return Promise.resolve({ item: itemToValidate, validation: this.validateItem(itemToValidate) });\r\n      },\r\n      parsers: FileParser.getDefaultParsers(),\r\n    };\r\n  }\r\n\r\n  /** Available object mapper for import based on the current schema. */\r\n  private getMapper(): DataMapper<{ [key: string]: string }, any> {\r\n    const result = new DataMapper<{ [key: string]: string }, any>(this.schema + \"Import_sxyGrid\", `Table import for ${this.schema}`);\r\n    result.setStringToSchemaMapping(this.schemaDef, this.schema);\r\n    return result;\r\n  }\r\n\r\n  private initModel() {\r\n    this.doc = this.doc || \"salaxy-secure/schemas/v02.json\";\r\n    if (!this.schemaDef && this.doc && this.schema) {\r\n      this.jsonSchemaService.assureSchemaDocument(this.doc).then((schemaDoc) => {\r\n        this.isInitDone = true;\r\n        this.schemaDef = schemaDoc.components.schemas[this.schema] as OpenAPIV3.NonArraySchemaObject;\r\n      });\r\n    } else if (this.schemaDef) {\r\n      this.renderGrid();\r\n    }\r\n  }\r\n\r\n  /** Gets the fields based on include OR exclude and schema defs definitions. */\r\n  private getFields(): string[] {\r\n    let fields = Arrays.assureArray(this.include);\r\n    if (fields.length == 0) {\r\n      fields = Object.keys(this.schemaDef?.properties || {});\r\n      const excludeArr = Arrays.assureArray(this.exclude);\r\n      if (excludeArr.length > 0) {\r\n        fields = fields.filter((x) => excludeArr.indexOf(x) < 0);\r\n      }\r\n    }\r\n    return fields;\r\n  }\r\n\r\n  private renderGrid() {\r\n    this.gridOptions = {\r\n      defaultColDef: {\r\n        editable: true\r\n      },\r\n      rowSelection: \"multiple\",\r\n      undoRedoCellEditing: true,\r\n      undoRedoCellEditingLimit: 20,\r\n      onSelectionChanged: (event: {\r\n        /** Grid API */\r\n        api: any;\r\n        /** Column API */\r\n        columnApi: any;\r\n        /** Event identifier */\r\n        type: string;\r\n      }) => {\r\n        this.selection = event.api.getSelectedNodes();\r\n        this.$timeout(0);\r\n      },\r\n    };\r\n    const columnDefs = [];\r\n    this.getFields().forEach((key) => {\r\n      const schema = JsonSchemaUtils.getProperty(this.schemaDef, key)?.schema;\r\n      if (schema) {\r\n        let headerName = schema.title;\r\n        if (!headerName) {\r\n          headerName = key.indexOf(\".\") ? key.substring(key.lastIndexOf(\".\") + 1) : key;\r\n        }\r\n        const colDef = {\r\n          field: key,\r\n          headerName,\r\n        } as any;\r\n        switch (schema.type) {\r\n          case \"integer\":\r\n          case \"number\":\r\n            colDef.type = [\"numericColumn\"];\r\n            break;\r\n          case \"object\":\r\n            colDef.cellRenderer = CellRenderingLogic.getCellRenderer(schema);\r\n            break;\r\n        }\r\n        if (schema.description) {\r\n          colDef.headerTooltip = schema.description;\r\n        }\r\n        if (schema.enum?.length) {\r\n          const enumValues = EnumerationsLogic.getEnumMetadata(schema.format).values;\r\n          colDef.cellEditor = \"agSelectCellEditor\";\r\n          colDef.cellEditorParams = {\r\n            values: enumValues.map((x) => x.name),\r\n          };\r\n          colDef.refData = enumValues.reduce((a, v) => ({ ...a, [v.name]: v.label }), {});\r\n        }\r\n        columnDefs.push(colDef);\r\n      } else {\r\n        console.error(`Cannot find column ${key}`);\r\n      }\r\n    });\r\n    const getSalaxyGridModule = (): Promise<any> => {\r\n      // Support both esm and umd builds...\r\n      return Promise.resolve(Configs.global.salaxy.grid);\r\n    };\r\n\r\n    getSalaxyGridModule().then((salaxyGridModule) => {\r\n      const gridWrapper = salaxyGridModule.GridWrapper;\r\n      const agGrid = gridWrapper.agGrid;\r\n      agGrid.LicenseManager.setLicenseKey(gridWrapper.AG_GRID_LICENCE_KEY);\r\n      if (!agGrid.ModuleRegistry.getRegisteredModules().length) {\r\n        agGrid.ModuleRegistry.registerModules(agGrid.AllModules);\r\n      }\r\n\r\n      const eGridDiv = this.$element[0].querySelector(\"#dataGrid\");\r\n      new agGrid.Grid(eGridDiv, this.gridOptions);\r\n    });\r\n\r\n    // create the grid passing in the div to use together with the columns & data we want to use\r\n    this.$timeout(() => {\r\n      this.gridOptions.api.setRowData(this.data);\r\n      this.gridOptions.api.setColumnDefs(columnDefs);\r\n    });\r\n  }\r\n}","import angular from \"angular\";\r\n\r\nimport { Arrays, DataMapper, DataMappersLogic, EnumerationsLogic, Exportable, FormHelpers, InputEnumOption, InputMetadata, JsonInputType, JsonSchemaUtils, OpenAPIV3, Translations  } from \"@salaxy/core\";\r\n\r\nimport { EditDialogKnownActions, EditDialogResult, FileService, UiHelpers } from \"../../services\";\r\nimport { SxyFormController } from \"./SxyFormController\";\r\n\r\n/** Handles user interface logic for different form inputs components (including select etc.) */\r\nexport class SxyInputController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"UiHelpers\", \"$transclude\", \"$element\", \"FileService\"];\r\n\r\n  /** Default bindings to the components */\r\n  public static bindings = {\r\n    /**\r\n     * Model in the form. Currently always starts with \"form.\" to bind to main data object of the form.\r\n     * For fieldset, this may also be just \"form\" to bind to main model in form (not a property).\r\n     */\r\n    model: \"@\",\r\n\r\n    /** Possibility to override the label. */\r\n    label: \"@\",\r\n\r\n    /**\r\n     * Type of the input component as one of JSON schema types:\r\n     * 'boolean', 'object', 'number', 'string', 'integer' or 'array'.\r\n     * Typically, this will be inferred from the model, but you may set it explicitly if the property is not yet in the model.\r\n     */\r\n    type: \"@\",\r\n\r\n    /**\r\n     * Format of the input component as JSON schema format:\r\n     * Examples include \"multiline\", \"date\" (string) and \"radio\", \"checkbox\" (boolean).\r\n     */\r\n    format: \"@\",\r\n\r\n    /**\r\n     * True or false forces the read-only mode on the input regardless of the default value.\r\n     * This \"read-only\" attribute behaves differently than the HTML \"readonly\" attribute:\r\n     * The value is boolean (true/1 or false/0). Non existent attribute or empty/null uses\r\n     * the default value from metadata (API model) or from the form.\r\n     * Also, the input will become fully read-only view without any form control.\r\n     */\r\n    readOnly: \"@\",\r\n\r\n    /**\r\n     * True or false forces the disabled mode on the input.\r\n     * This \"disable\" attribute behaves differently than the HTML \"disabled\" attribute:\r\n     * The value is boolean (true/1 or false/0). Non existent attribute or empty/null\r\n     * uses the default value: Currently always false, but may later come from metadata.\r\n     */\r\n    disable: \"@\",\r\n\r\n    /**\r\n     * True or false forces the required mode on the input.\r\n     * This \"require\" attribute behaves differently than the HTML \"required\" attribute:\r\n     * The value is boolean (true/1 or false/0). Non existent attribute or empty/null\r\n     * uses the default value from metadata (API model).\r\n     */\r\n    require: \"@\",\r\n\r\n    /**\r\n     * Minimum value of the field\r\n     */\r\n    minimum: \"@\",\r\n\r\n    /**\r\n     * Maximum value of the field\r\n     */\r\n    maximum: \"@\",\r\n\r\n    /**\r\n     * Multiple of (step) of the value\r\n     */\r\n    multipleOf: \"@\",\r\n\r\n    /**\r\n     * For arrays, fieldsets and other components that enumerate children,\r\n     * defines which children are shown (taken to inputs collection).\r\n     * Comma separated list of property names.\r\n     */\r\n    include: \"@\",\r\n\r\n    /**\r\n     * For arrays, fieldsets and other components that enumerate children,\r\n     * defines which children are hidden (excluded from inputs collection).\r\n     * Comma separated list of property names.\r\n     */\r\n    exclude: \"@\",\r\n  };\r\n\r\n  /** Auto-generated unique id of the input */\r\n  public id: string;\r\n\r\n  /**\r\n   * Auto-generated name of the input.\r\n   * Currently, the same as ID, but this may change in the future.\r\n   * E.g. to make it more compatible with form POST (no id numbers etc.).\r\n   */\r\n  public name: string;\r\n\r\n  /** Model in the form. Currently always starts with \"form.\" to bind to main data object of the form. */\r\n  public model: string;\r\n\r\n  /**\r\n   * Possibility to override the label (default is \"SALAXY.MODEL.[TypeName].[propName].title\").\r\n   * Translated by default, if translation not found, shown as is.\r\n   * If starts with dot, will be interpreted as just the last part of the key,\r\n   * e.g. \".specialLabel\" will fetch key \"SALAXY.MODEL.[TypeName].[propName].specialLabel\".\r\n   */\r\n  public label: string;\r\n\r\n  /** Schema of the property */\r\n  public schemaModel: OpenAPIV3.SchemaObject | null;\r\n\r\n  /** Name of the parent schema (data model). Used in language keys. */\r\n  public parentSchemaName: string;\r\n\r\n  /** Name of the property to which this input is bound in the parentSchema. */\r\n  public propertyName: string;\r\n\r\n  /** SxyForm component that holds the data model and submit / reset logic etc. */\r\n  public form: SxyFormController;\r\n\r\n  /**\r\n   * Type of the input component as one of JSON schema types:\r\n   * 'boolean', 'object', 'number', 'string', 'integer' or 'array'.\r\n   * Typically, this will be inferred from the model, but you may set it explicitly if the property is not yet in the model.\r\n   */\r\n  public type: JsonInputType;\r\n\r\n  /**\r\n   * Format of the input component as JSON schema format:\r\n   * Examples include \"multiline\", \"date\" (string) and \"radio\", \"checkbox\" (boolean).\r\n   */\r\n  public format: string;\r\n\r\n  /**\r\n   * The read-only value as the user set it in the \"read-only\" attribute\r\n   * True or false forces the read-only mode on the input regardless of the default value or\r\n   * the read-only attribute set in the sxy-form level.\r\n   * This \"read-only\" attribute behaves differently than the HTML \"readonly\" attribute:\r\n   * The value is boolean (true/1 or false/0). Non existent attribute or empty/null uses\r\n   * the default value from metadata (API model) or from the form.\r\n   * Also, the input will become fully read-only view without any form control.\r\n   */\r\n  public readOnly: string;\r\n\r\n  /**\r\n   * True or false forces the disabled mode on the input.\r\n   * This \"disable\" attribute behaves differently than the HTML \"disabled\" attribute:\r\n   * The value is boolean (true/1 or false/0). Non existent attribute or empty/null\r\n   * uses the default value: Currently always false, but may later come from metadata.\r\n   */\r\n  public disable: string;\r\n\r\n  /**\r\n   * True or false forces the disabled mode on the input.\r\n   * This \"require\" attribute behaves differently than the HTML \"required\" attribute:\r\n   * The value is boolean (true/1 or false/0). Non existent attribute or empty/null\r\n   * uses the default value from metadata (API model).\r\n   */\r\n  public require: string;\r\n\r\n  /**\r\n   * Minimum value\r\n   */\r\n  public minimum: number | null;\r\n\r\n  /**\r\n   * Maximum value\r\n   */\r\n  public maximum: number | null;\r\n\r\n  /**\r\n   * Multiple of (step) of the value\r\n   */\r\n  public multipleOf: number | null;\r\n\r\n  /** Template URl that is used for rendering the input. */\r\n  public templateUrl: string;\r\n\r\n  /** Input metadata from the schema resolving process. */\r\n  public input: InputMetadata;\r\n\r\n  /**\r\n   * For arrays, fieldsets and other components that enumerate children,\r\n   * defines which children are shown (taken to inputs collection).\r\n   * Comma separated list of property names.\r\n   */\r\n  public include: string | string[];\r\n\r\n  /**\r\n   * For arrays, fieldsets and other components that enumerate children,\r\n   * defines which children are hidden (excluded from inputs collection).\r\n   * Comma separated list of property names.\r\n   */\r\n  public exclude: string | string[];\r\n\r\n  constructor(\r\n    private uiHelpers: UiHelpers,\r\n    private $transclude: angular.ITranscludeFunction,\r\n    private $element: JQLite,\r\n    private fileService: FileService,\r\n  ) {\r\n    // Dependency injection\r\n  }\r\n\r\n  /** Initializes the controller */\r\n  public $onInit() {\r\n    this.initModel();\r\n  }\r\n\r\n  /**\r\n   * Gets the formatted value for the input depending on the data type.\r\n   * @param childName For object arrays, gets the value for the specified child input.\r\n   * @param index For object the index of the item in the array.\r\n   * May later support other child scenarios.\r\n   */\r\n  public formatValue(childName?: string, index: number = null) {\r\n    if (childName && index != null) {\r\n      const arrayItemsType = ((this.schemaModel as OpenAPIV3.ArraySchemaObject)?.items as OpenAPIV3.SchemaObject);\r\n      if (arrayItemsType) {\r\n        const childType = arrayItemsType.properties[childName] as OpenAPIV3.SchemaObject;\r\n        const childvalue = this.value[index][childName];\r\n        if (childvalue && childType.format && childType.enum?.length) {\r\n          return EnumerationsLogic.getEnumLabel(`${this.form.getEnumNamespace()}.${childType.format}`, childvalue);\r\n        }\r\n        // TODO: Add number formatting etc. here as necessary.\r\n        return childvalue;\r\n      }\r\n      return `#ERR: formatValue not an array ${childName}, ${index}.`;\r\n    }\r\n    return \"#ERR: TODO Add other formatters here\";\r\n  }\r\n\r\n  /**\r\n   * Gets the label for the input.\r\n   * Default is \"SALAXY.MODEL.[TypeName].[propName].title\" in the dictionary.\r\n   * @param childName For object arrays, gets the label for the specified child input.\r\n   * May later support other child scenarios.\r\n   */\r\n  public getLabel(childName?: string) {\r\n    if (childName) {\r\n      const arrayItemsType = ((this.schemaModel as OpenAPIV3.ArraySchemaObject)?.items as OpenAPIV3.SchemaObject);\r\n      // TODO: We would need to move the type information away from format.\r\n      if (arrayItemsType?.type === \"object\" && arrayItemsType.format) {\r\n        const defaultLabel = (arrayItemsType.properties as OpenAPIV3.SchemaObject)?.[childName]?.title ?? (\"#\" + childName);\r\n        return Translations.getWithDefault(`${this.form.getModelNamespace()}.${arrayItemsType.format}.${childName}.title`, defaultLabel);\r\n      }\r\n      if (this.propertyName) {\r\n        return Translations.getWithDefault(`${this.form.getModelNamespace()}.${this.parentSchemaName}.${this.propertyName}.${childName}.title`, \"#\" + childName);\r\n      }\r\n      if (this.parentSchemaName) {\r\n        return Translations.getWithDefault(`${this.form.getModelNamespace()}.${this.parentSchemaName}.${childName}.title`, \"#\" + childName);\r\n      }\r\n      return \"#ERR: \" + childName;\r\n    }\r\n    if (this.label) {\r\n      if (this.label[0] === \".\" && this.label[1] !== \".\" && this.propertyName) {\r\n        this.label = `${this.form.getModelNamespace()}.${this.parentSchemaName}.${this.propertyName}${this.label}`;\r\n      }\r\n      return Translations.get(this.label);\r\n    }\r\n    if (this.propertyName) {\r\n      const defaultLabel = this.schemaModel?.title ?? (\"#\" + this.propertyName);\r\n      return Translations.getWithDefault(`${this.form.getModelNamespace()}.${this.parentSchemaName}.${this.propertyName}.title`, defaultLabel);\r\n    }\r\n    if (this.parentSchemaName) {\r\n      const defaultLabel = this.schemaModel?.title ?? (\"#\" + this.parentSchemaName);\r\n      return Translations.getWithDefault(`${this.form.getModelNamespace()}.${this.parentSchemaName}.title`, defaultLabel);\r\n    }\r\n    return \"#ERR: \" + this.model;\r\n  }\r\n\r\n  /** Gets the description for the input */\r\n  public getDescr(): string {\r\n    return Translations.getWithDefault(`${this.form.getModelNamespace()}.${this.parentSchemaName}.${this.propertyName}.descr`,\r\n      this.schemaModel?.description);\r\n  }\r\n\r\n  /** Gets the read-only value based on defaults and explicit values. */\r\n  public getReadOnly(): boolean {\r\n    const readOnlyValue = (this.readOnly || \"\").trim().toLowerCase();\r\n    if (readOnlyValue === \"true\" || readOnlyValue === \"1\") {\r\n      return true;\r\n    }\r\n    if (readOnlyValue === \"false\" || readOnlyValue === \"0\") {\r\n      return false;\r\n    }\r\n    const readOnlyFormValue = (this.form.readOnly || \"\").trim().toLowerCase();\r\n    if (readOnlyFormValue === \"true\" || readOnlyFormValue === \"1\") {\r\n      return true;\r\n    }\r\n    if (this.schemaModel?.readOnly != null) {\r\n      return this.schemaModel.readOnly;\r\n    }\r\n    // Default logic - this might later expand and/or some stuff may move to server.\r\n    const readOnlyFields = [\"id\", \"createdAt\", \"updatedAt\", \"isReadOnly\", \"owner\", \"partner\"];\r\n    if (readOnlyFields.indexOf(this.propertyName) >= 0) {\r\n      return true;\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /** Gets the minimum value */\r\n  public getMinimum(): number {\r\n    if (this.minimum != null) {\r\n      return this.minimum;\r\n    }\r\n    if (this.schemaModel?.minimum != null) {\r\n      return this.schemaModel.minimum;\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /** Gets the maximum value */\r\n  public getMaximum(): number {\r\n    if (this.maximum != null) {\r\n      return this.maximum;\r\n    }\r\n    if (this.schemaModel?.maximum != null) {\r\n      return this.schemaModel.maximum;\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /** Gets the multipleOf value */\r\n  public getMultipleOf(): number {\r\n    if (this.multipleOf != null) {\r\n      return this.multipleOf;\r\n    }\r\n    if (this.schemaModel?.multipleOf != null) {\r\n      return this.schemaModel.multipleOf;\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /** Gets the minimum length value for string input */\r\n  public getMinLength(): number {\r\n    if (this.schemaModel?.minLength != null) {\r\n      return this.schemaModel.minLength;\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /** Gets the maximum length value for string input */\r\n  public getMaxLength(): number {\r\n    if (this.schemaModel?.maxLength != null) {\r\n      return this.schemaModel.maxLength;\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /** Gets the minimum length value for string input */\r\n  public getPattern(): string {\r\n    if (this.schemaModel?.pattern != null) {\r\n      return this.schemaModel.pattern;\r\n    }\r\n    return null;\r\n  }\r\n  /** Gets the require value based on defaults and explicit values. */\r\n  public getRequire(): boolean {\r\n    const requireValue = (this.require || \"\").trim().toLowerCase();\r\n    if (requireValue === \"true\" || requireValue === \"1\") {\r\n      return true;\r\n    }\r\n    if (requireValue === \"false\" || requireValue === \"0\") {\r\n      return false;\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /** Gets the disable value based on defaults and explicit values. */\r\n  public getDisable(): boolean {\r\n    const disableValue = (this.disable || \"\").trim().toLowerCase();\r\n    if (disableValue === \"true\" || disableValue === \"1\") {\r\n      return true;\r\n    }\r\n    if (disableValue === \"false\" || disableValue === \"0\") {\r\n      return false;\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /** Gets or sets the value in the model */\r\n  public get value(): any {\r\n    return this.form?.getValue(this.model);\r\n  }\r\n  public set value(value: any) {\r\n    if (this.form) {\r\n      this.form.setValue(this.model, value);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * For datatype \"object\", gets the inputs for child properties.\r\n   * For datatype \"array\", gets the inputs for items.\r\n   * For other types, gets an array with single input for that type\r\n   * (TODO: Does this make sense? It is essentially the same as parent).\r\n   * @param defaultTop Returns top n children.\r\n   * If include is specified (fields are hand-picked), this proeprty is ignored.\r\n   */\r\n  public getChildInputs(defaultTop: number): InputMetadata[] {\r\n    return this.uiHelpers.cache(this, \"childInputs\", () => {\r\n      if (!this.schemaModel) {\r\n        return null;\r\n      }\r\n      let result: InputMetadata[];\r\n      if (this.schemaModel.type === \"object\") {\r\n        result = FormHelpers.getInputsForObject(this.schemaModel, this.model);\r\n      } else if (JsonSchemaUtils.isArraySchemaObject(this.schemaModel)) {\r\n        result = FormHelpers.getInputsForArray(this.schemaModel, this.model);\r\n      } else {\r\n        result = [FormHelpers.getInputForSelf(this.schemaModel, null, \"form\")];\r\n      }\r\n      const includeArr = Arrays.assureArray(this.include);\r\n      if (includeArr.length > 0) {\r\n        result = includeArr.map((x) => result.find((y) => y.name === x)).filter((x) => !!x);\r\n        defaultTop = includeArr.length;\r\n      }\r\n      const excludeArr = Arrays.assureArray(this.exclude);\r\n      if (excludeArr.length > 0) {\r\n        result = result.filter((x) => excludeArr.indexOf(x.name) < 0);\r\n      }\r\n      return result.slice(0, defaultTop);\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shows an edit dialog for item.\r\n   * @param item Item to edit\r\n   * @param index Index of the item in the current model array if available.\r\n   */\r\n  public edit(item: any, index: number): Promise<EditDialogResult<any>> {\r\n    // HACK: This now only works for array/object => Make more generic.\r\n    const logic = {\r\n      openApi: this.form.openApi,\r\n      type: ((this.schemaModel as OpenAPIV3.ArraySchemaObject)?.items as OpenAPIV3.SchemaObject)?.format,\r\n      title: index < 0 ? Translations.get(\"SALAXY.NG1.SxyInputComponent.addNewRow\") : Translations.get(\"SALAXY.NG1.SxyInputComponent.editRow\"),\r\n      showDelete: index > -1 && !this.getReadOnly(),\r\n      isReadOnly: this.getReadOnly(),\r\n      debugger: this.form.debugger,\r\n    };\r\n    if (this.$transclude?.isSlotFilled(\"form\")) {\r\n      let html = \"\";\r\n\r\n      // The cloning of the slot actually initializes all the components in the slot, be careful.\r\n      // the form has not been bound yet\r\n      this.$transclude((transEl, transScope) => { // eslint-disable-line @typescript-eslint/no-unused-vars\r\n        angular.forEach(transEl, (textOrElem) => {\r\n          if (textOrElem.tagName === \"FORM\") {\r\n            html += textOrElem.innerHTML;\r\n          }\r\n        });\r\n        html = html.trim();\r\n        return null as any;\r\n      }, this.$element, \"form\");\r\n      const template = `<div class=\"modal-header\">\r\n      <h2 class=\"modal-title\">{{ $ctrl.logic.title }}</h2>\r\n      <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n    </div>\r\n    <div class=\"modal-body\">\r\n      <sxy-form open-api=\"{{ $ctrl.logic.openApi }}\" type=\"{{ $ctrl.logic.type }}\" auto-gen=\"false\" debugger=\"$ctrl.logic.debugger\"\r\n        model=\"$ctrl.current\" read-only=\"{{$ctrl.logic.isReadOnly ? 'true' : ''}}\">\r\n        <div>${html || \"Form tag contains no data\"}</div>\r\n      </sxy-form>\r\n    </div>\r\n    <div class=\"modal-footer\">\r\n      <button type=\"button\" ng-if=\"$ctrl.logic.showDelete\" class=\"btn btn-danger\" ng-click=\"$close('delete-no-save')\" sxy-text=\"SALAXY.UI_Terms.delete\"></button>\r\n      <button type=\"reset\" ng-if=\"!$ctrl.logic.isReadOnly\" class=\"btn btn-default ms-auto\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n      <button type=\"button\" ng-if=\"!$ctrl.logic.isReadOnly\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.ok\"></button>\r\n      <button type=\"button\" ng-if=\"$ctrl.logic.isReadOnly\" class=\"btn btn-primary\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n    </div>`;\r\n      return this.uiHelpers.openEditDialog(null, item, logic, \"\", \"EditDialogController\", { template }).then((result) => {\r\n        if (result.action === EditDialogKnownActions.DeleteNoCommit) {\r\n          this.delete(item, index);\r\n        }\r\n        return result;\r\n      });\r\n    }\r\n    return this.uiHelpers.openEditDialog(\"salaxy-components/sxy-form/SxyInput-dialog-edit.html\", item, logic).then((result) => {\r\n      if (result.action === EditDialogKnownActions.DeleteNoCommit) {\r\n        this.delete(item, index);\r\n      }\r\n      return result;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Deletes an item (currently no \"Are you sure?\")\r\n   * @param item Item to delete\r\n   * @param index Index of the item in the current model array. This is currently required.\r\n   */\r\n  public delete(item: any, index: number): void {\r\n    (this.value as []).splice(index, 1);\r\n  }\r\n\r\n  /**\r\n   * Move an item in the array up one position.\r\n   * @param index Index of the item in the current model array.\r\n   */\r\n  public moveUp(index: number): void {\r\n    Arrays.moveItem(this.value as [], index, \"up\");\r\n  }\r\n\r\n  /**\r\n   * Move an item in the array down one position.\r\n   * @param index Index of the item in the current model array.\r\n   */\r\n  public moveDown(index: number): void {\r\n    Arrays.moveItem(this.value as [], index, \"down\");\r\n  }\r\n\r\n  /**\r\n   * Creates a new item to the current array.\r\n   * @param item Item to add. If not specified (default), shows an edit dialog for creating the item.\r\n   */\r\n  public createNew(item: any = null): Promise<EditDialogResult<any>> {\r\n    if (item) {\r\n      if (!this.value) {\r\n        this.value = [];\r\n      }\r\n      (this.value as any[]).push(item);\r\n      return;\r\n    }\r\n    // HACK: This now only works for array/object => Make more generic.\r\n    return this.edit({}, -1).then((result) => {\r\n      if (result.action === \"ok\") {\r\n        if (!this.value) {\r\n          this.value = [];\r\n        }\r\n        (this.value as any[]).push(result.item);\r\n      }\r\n      return result;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Gets an array total for view purposes\r\n   * @param field Name of the field for which the total is calculated\r\n   * @param type Type of calculation. Currently only sum is supported, but others may be added (e.g. \"avg\").\r\n   */\r\n  public getTotal(field: string, type: \"sum\" = \"sum\"): number {\r\n    if (!this.value) {\r\n      return;\r\n    }\r\n    switch (type) {\r\n      case \"sum\":\r\n      default:\r\n        return Arrays.sum(this.value as any[], (x) => x[field]);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Gets the options for enumerations based on schema.\r\n   * For an array, gets the options for item enumeration.\r\n   */\r\n  public getEnumOptions(): InputEnumOption[] {\r\n    // TODO: This is just quick partial implementation based on schema. Need to think through the different scenarios!\r\n    return this.uiHelpers.cache(this, \"getEnumOptions\", () => {\r\n      if (!this.schemaModel) {\r\n        return [];\r\n      }\r\n      let enumArr = this.schemaModel.enum;\r\n      let enumName = this.schemaModel.format;\r\n      if (!enumArr?.length) {\r\n        enumArr = ((this.schemaModel as OpenAPIV3.ArraySchemaObject).items as OpenAPIV3.SchemaObject)?.enum;\r\n        enumName = ((this.schemaModel as OpenAPIV3.ArraySchemaObject).items as OpenAPIV3.SchemaObject)?.format;\r\n      }\r\n      if (enumArr?.length > 0) {\r\n        return enumArr.map(x => ({\r\n          title: EnumerationsLogic.getEnumDescr(`${this.form.getEnumNamespace()}.${enumName}`, x),\r\n          text: EnumerationsLogic.getEnumLabel(`${this.form.getEnumNamespace()}.${enumName}`, x),\r\n          value: x,\r\n        }));\r\n      }\r\n    }, () => this.schemaModel.type + this.schemaModel.format + this.schemaModel.enum?.length);\r\n  }\r\n\r\n  /**\r\n   * Gets the format assuring that it is of supported type.\r\n   * Currently, there is only special logic for enums.\r\n   */\r\n  public getFormat(): string {\r\n    if (this.input.isEnum) {\r\n      const enumFormat = this.format || this.input.format;\r\n      const supportedFormats = [\"select\", \"radio\", \"multi-select\", \"typeahead\", \"list\"];\r\n      if (supportedFormats.indexOf(enumFormat) >= 0) {\r\n        return enumFormat;\r\n      }\r\n      // Especially \"enum\", \"default\" and null.\r\n      // TODO: Exact logic requires go-through.\r\n      return \"select\";\r\n    }\r\n    return this.format;\r\n  }\r\n\r\n    /** Gets the exportable for the current data model: For exporting an array. */\r\n    public getExportable(): Exportable<any> {\r\n      if (!(this.schemaModel as OpenAPIV3.ArraySchemaObject).items) {\r\n        return {\r\n          exporters: [],\r\n          getExportMappers: () => [],\r\n          getExportMapper: () => null,\r\n          list: () => Promise.resolve([]),\r\n          getSingle: (item) => Promise.resolve(item),\r\n        };\r\n      }\r\n\r\n      // TODO: Tarkista mikä ero näillä on käytännössä ja katso otetaanko mukaan molemmat vai toinen. Tarkista voisiko käyttää suoraan Gridiä vai onko se liian kompleksi?\r\n      // TODO: Harkitse tämän logiikan siirtämistä helperiin TAI ExportControlleriin (käytössä myös SxyGridController), samoin fileService tarpeen poistoa\r\n      // TODO: Lisää myös import.\r\n      // const fullMapper = this.getMapper().reverse(this.propertyName + \"FullExport\", `Full object export for ${this.propertyName}`);\r\n\r\n      const exptMapper = new DataMapper<{ [key: string]: string }, any>(this.propertyName + \"GridExport\", `Table export for ${this.propertyName}`);\r\n      exptMapper.setSchema((this.schemaModel as OpenAPIV3.ArraySchemaObject).items as OpenAPIV3.NonArraySchemaObject, this.propertyName, \"source\");\r\n      exptMapper.setPathsFromSourceSchema(this.getChildInputs(100).map((x) => x.name));\r\n\r\n      // const mappers = [exptMapper, fullMapper];\r\n      const mappers = [exptMapper];\r\n\r\n      const result: Exportable<any> = {\r\n        exporters: this.fileService.getDefaultExporters(),\r\n        getExportMappers: () => {\r\n          return mappers.map((x) => DataMappersLogic.getInfo(x));\r\n        },\r\n        getExportMapper: (id: string) => {\r\n          return Promise.resolve(mappers.find((x) => x.uri == id));\r\n        },\r\n        list: (maxCount) => {\r\n          const result = maxCount > 0 ? this.value.slice(0, maxCount) : this.value;\r\n          return Promise.resolve(result);\r\n        },\r\n        getSingle: (item) => {\r\n          return Promise.resolve(item);\r\n        },\r\n      };\r\n\r\n      return result;\r\n    }\r\n\r\n  private initModel() {\r\n    if (!this.model) {\r\n      throw new Error(`Input not bound to model.`);\r\n    }\r\n    if (!this.form) {\r\n      this.input = {\r\n        type: \"error\",\r\n        content: \"No sxy-form for input with model \" + this.model,\r\n        name: this.model,\r\n        path: this.model,\r\n        isEnum: false,\r\n        format: null,\r\n      };\r\n      this.name = this.id = this.input.name;\r\n      this.templateUrl = \"salaxy-components/sxy-form/error/default.html\";\r\n      this.schemaModel = null;\r\n      return;\r\n    }\r\n    const reg = this.form.registerInput(this.model, this.type, this.format);\r\n    this.schemaModel = reg.prop.schema || null;\r\n    this.parentSchemaName = reg.prop.parentName;\r\n    this.name = this.id = reg.id;\r\n    this.propertyName = reg.prop.propertyName;\r\n    if (reg.prop.isRequired && !(this.require || \"\").trim()) {\r\n      this.require = \"true\"; // Set from schema if not explicitly set.\r\n    }\r\n    this.input = reg.input;\r\n    if (this.type && this.type !== this.input.type) {\r\n      console.error(`Input type \"${this.type}\" not supported for property \"${this.input.name}\", defaulting to \"${this.input.type}\".`);\r\n    }\r\n    this.templateUrl = reg.templateUrl;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\nimport { InputEnumOption, OpenAPIV3 } from \"@salaxy/core\";\r\nimport { JsonSchemaService, UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Controller for schema editing user interfaces. Current implementation is OpenAPI V3 schema editing.\r\n */\r\nexport class SxySchemaEditorController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"JsonSchemaService\", \"UiHelpers\"];\r\n\r\n  /** Schema object that is being edited. */\r\n  public model: OpenAPIV3.SchemaObject;\r\n\r\n  public types: (InputEnumOption & {\r\n      formats: InputEnumOption[],\r\n    })[];\r\n\r\n  constructor(\r\n    private jsonSchemaService: JsonSchemaService,\r\n    private uiHelpers: UiHelpers,\r\n  ) {\r\n    // Dependency injection\r\n  }\r\n\r\n  /** Initializes the controller */\r\n  public $onInit() {\r\n    this.types = [];\r\n    const inputs = this.jsonSchemaService.getRegisteredInputs();\r\n    // TODO: Move to dictionary\r\n    const labels = { \"string\": \"Teksti\", \"number\": \"Numero\", \"array\": \"Lista\", \"boolean\": \"On/off (boolean)\", \"integer\": \"Kokonaisluku\", \"object\": \"Muu...\" };\r\n    Object.keys(inputs).forEach((key) => {\r\n      this.types.push({\r\n        text: labels[key],\r\n        value: key,\r\n        formats: Object.keys(inputs[key]).map((x) => ({\r\n          text: x == \"default\" ? \"Oletus\" : x, // TODO: Translate\r\n          value: x == \"default\" ? \"\" : x,\r\n        }))});\r\n    });\r\n  }\r\n\r\n  /** Adds a new property to the current schema */\r\n  public addProperty() {\r\n    // TODO: Add this to UI Helpers (as dialog) and search for prompt().\r\n    const name = window.prompt(\"Mikä on lisättävän tietueen tekninen nimi (a-z, 0-1, ei välejä eikä erikoismerkkejä)?\");\r\n    // TODO: Add property name validation / fix.\r\n    this.model[name] = {};\r\n  }\r\n\r\n  /** Deletes a property from the schema. */\r\n  public deleteProperty(key) {\r\n    delete this.model[key];\r\n  }\r\n\r\n  /** Gets the formats for given type */\r\n  public getFormats(type: string) {\r\n    return this.types.find((x) => x.value == type).formats;\r\n  }\r\n}","import angular from \"angular\";\r\n\r\nimport { OpenAPIV3 } from \"@salaxy/core\";\r\n\r\nimport { JsonSchemaUtils } from \"@salaxy/core\";\r\n\r\nimport { JsonSchemaService } from \"../../services\";\r\nimport { ColumnDefinition, Editor, EventCallBackMethods, Options, TabulatorFull as Tabulator } from \"tabulator-tables\";\r\n\r\n/**\r\n * Configuration object for SxyTable:\r\n * Extends Tabulator Options with events and potentially some SxyTables specific options in the future.\r\n */\r\nexport interface SxyTableOptions extends Options {\r\n  /** Event handlers that are added to Tabulator after it has been created. */\r\n  events?: Partial<EventCallBackMethods>,\r\n}\r\n\r\n/**\r\n * Sxy form contains the definition for an editor used interface that\r\n * typically corresponds to an HTML form.\r\n */\r\nexport class SxyTableController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"JsonSchemaService\", \"$element\", \"$timeout\"];\r\n\r\n  /**\r\n   * The schema definition that defines the structure of the grid.\r\n   */\r\n  public schemaDef?: OpenAPIV3.NonArraySchemaObject;\r\n\r\n  /**\r\n   * URL of the schema document that contains the schemaDef.\r\n   * If set with schema in init, loads the document.\r\n   */\r\n  public doc?: string;\r\n\r\n  /**\r\n   * Key of schemaDef in doc.\r\n   * If set with doc in init, will load the schema document from server and set the schemaDef.\r\n   */\r\n  public schema?: string;\r\n\r\n  /**\r\n   * Data that is rendered / edited in the grid.\r\n   * This is either an array or an object that implements getTabulatorConfig() method for ajax data.\r\n   */\r\n  public data?: any[] | { getTabulatorConfig: () => Options };\r\n\r\n  /**\r\n   * List of columns to include in the grid.\r\n   * This may be an array or comma separated string of field names (or a property tree, e.g. \"owner.avatar.displayName\").\r\n   * Alternatively, the entries in the array may be be full Tabulator column definitions, where `field` propererty defines the\r\n   * data item and fetches the default properties from the schema.\r\n   */\r\n  public include?: string | (string | ColumnDefinition)[];\r\n\r\n  /**\r\n   * List of columns to exclude from the grid.\r\n   * This property is currenlty used only if include property is undefined, i.e. in default\r\n   * rendering, which will render the first-level properties. As such, exclude does not really support property paths.\r\n   */\r\n  public exclude?: string | string[];\r\n\r\n  /** Additional configuration for the table in init. */\r\n  public options?: SxyTableOptions;\r\n\r\n  /** After init, exposes the Tabulator for calling methods. */\r\n  public tabulator?: Tabulator;\r\n\r\n  /**\r\n   * Gets the state of filters or sets the initial state of filters.\r\n   * By default, the filters are not shown before showFilters() function is called.\r\n   * If the property / attribute is set to true before initial render, the filters are shown.\r\n   * Use showFilters() function to show or hide the filters after initial render.\r\n   */\r\n  public filters = false;\r\n\r\n  /**\r\n   * By default, the header filters are not shown before showFilters() function is called.\r\n   * This is the place where the filter definitions are stored in the mean time.\r\n   */\r\n  public filterDefinitions: {\r\n    [key: string]: Editor,\r\n  } = {};\r\n\r\n  private tableConfigCache = {\r\n    data: null,\r\n    include: null,\r\n    exclude: null,\r\n    options: null\r\n  };\r\n\r\n  constructor(\r\n    private jsonSchemaService: JsonSchemaService,\r\n    private $element: JQLite,\r\n    protected $timeout: angular.ITimeoutService\r\n  ) {}\r\n\r\n  /** Initializes the controller */\r\n  public $onInit() {\r\n    this.init();\r\n  }\r\n\r\n  /** Intialises settings */\r\n  public async init(): Promise<void> {\r\n    this.doc = this.doc || \"salaxy-secure/schemas/v02.json\";\r\n    if (!this.schemaDef && this.doc && this.schema) {\r\n      const schemaDoc = await this.jsonSchemaService.assureSchemaDocument(this.doc);\r\n      this.schemaDef = schemaDoc?.components?.schemas?.[this.schema] as OpenAPIV3.NonArraySchemaObject | undefined;\r\n    }\r\n    this.renderTable();\r\n  }\r\n\r\n  /**\r\n   * Method used to refresh table if data, include, exclude or options changes\r\n   */\r\n  public refresh() {\r\n    this.renderTable();\r\n  }\r\n\r\n  private async renderTable() {\r\n    const columns: ColumnDefinition[] = [];\r\n    this.getFields().forEach((colDefOrKey: string | ColumnDefinition) => {\r\n      let key: string;\r\n      let colDef: ColumnDefinition;\r\n      if (typeof colDefOrKey === \"string\") {\r\n        key = colDefOrKey;\r\n        colDef = {\r\n          field: key,\r\n          title: \"#field\", // Will be replaced below\r\n        };\r\n      } else {\r\n        key = colDefOrKey.field || \"\";\r\n        colDef = colDefOrKey;\r\n      }\r\n      if (!key && !colDef.formatter) {\r\n        console.error(\"Invalid column definition (no field): \", colDefOrKey);\r\n        return;\r\n      }\r\n      const schema = JsonSchemaUtils.getProperty(this.schemaDef, key)?.schema;\r\n      if (schema) {\r\n        if (colDef == null || colDef.title == \"#field\") {\r\n          colDef.title = schema.title || \"#field\";\r\n        }\r\n        this.setDefaultFormatter(schema, colDef);\r\n        if (schema.description) {\r\n          colDef.headerTooltip = schema.description;\r\n        }\r\n        if (schema.enum?.length) {\r\n          // TODO: Add enum renderer.\r\n          // const enumValues = SxyForms.i18n.getEnumMetadata(schema.format).values;\r\n        }\r\n      }\r\n      if (colDef.title == null || colDef.title == \"#field\") {\r\n        colDef.title = key.indexOf(\".\") ? key.substring(key.lastIndexOf(\".\") + 1) : key;\r\n      }\r\n      if (colDef.headerFilter) {\r\n        if (colDef.field) {\r\n          this.filterDefinitions[colDef.field] = colDef.headerFilter;\r\n          if (!this.filters) {\r\n            colDef.headerFilter = undefined;\r\n          }\r\n        } else {\r\n          console.error(\"Cannot set filter for column without field: \", colDef);\r\n        }\r\n      }\r\n      columns.push(colDef);\r\n    });\r\n    const tableOptions: SxyTableOptions = {};\r\n    if (this.options) {\r\n      // TODO: Potentially remove the SxyTable-specific options (events etc.) for future backward compatibility.\r\n      Object.assign(tableOptions, this.options);\r\n    }\r\n    if ((this.data as any)?.getTabulatorConfig) {\r\n      Object.assign(tableOptions, (this.data as any).getTabulatorConfig());\r\n    } else {\r\n      tableOptions.data = this.data as any[] || [];\r\n    }\r\n    if (columns.length) {\r\n      tableOptions.columns = columns;\r\n    } else if (tableOptions.autoColumns == null) {\r\n      tableOptions.autoColumns = true;\r\n    }\r\n    const elem = this.$element.find(\"div\")[0] as HTMLElement;\r\n    if (!elem) {\r\n      throw new Error(\"Cannot find div element for table.\");\r\n    }\r\n    this.tabulator = new Tabulator(elem, tableOptions);\r\n    const events = tableOptions.events ?? {};\r\n    Object.keys(events).forEach((keyString: string) => {\r\n      const key = keyString as keyof EventCallBackMethods;\r\n      this.tabulator.on(key, events[key]);\r\n    });\r\n\r\n    await this.$timeout();\r\n  }\r\n\r\n  //TODO: Replaces @salaxy/core assureArray?\r\n  private assureArray<T>(arrayCandidate: string | (T | string)[] | undefined): (T | string)[] {\r\n    if (!arrayCandidate) {\r\n      return [];\r\n    }\r\n    if (Array.isArray(arrayCandidate)) {\r\n      return arrayCandidate;\r\n    }\r\n    return arrayCandidate.split(\",\");\r\n  }\r\n\r\n  private getFields(): (ColumnDefinition | string)[] {\r\n    let fields = this.assureArray(this.include);\r\n    if (fields.length == 0) {\r\n      let keys = Object.keys(this.schemaDef?.properties || {});\r\n      const excludeArr = this.assureArray(this.exclude);\r\n      if (excludeArr.length > 0) {\r\n        keys = keys.filter((x) => excludeArr.indexOf(x) < 0);\r\n      }\r\n      fields = keys;\r\n    }\r\n    return fields;\r\n  }\r\n\r\n  private setDefaultFormatter(schema: OpenAPIV3.SchemaObject, colDef: ColumnDefinition) {\r\n    if (colDef.formatter) {\r\n      return;\r\n    }\r\n    switch (schema.type) {\r\n      case \"integer\":\r\n      case \"number\":\r\n        // TODO: Add number formatter.\r\n        break;\r\n      case \"object\":\r\n        //TODO add avatar / other formatter\r\n        break;\r\n      case \"string\":\r\n        if (schema.format === \"date-time\") {\r\n          // HACK: Consider adding date time handling to utils\r\n          colDef.formatter = (cell, _formatterParams, _onRendered) => {\r\n            const value = cell.getValue();\r\n            if (!value) {\r\n              return \"\";\r\n            }\r\n            const date = new Date(value);\r\n            return date.toLocaleDateString(\"fi-FI\");\r\n          };\r\n          colDef.hozAlign = \"right\";\r\n        }\r\n    }\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Ajax, Test } from \"@salaxy/core\";\r\n\r\nimport { UiHelpers, SessionService } from \"../../services\";\r\n\r\n/**\r\n * Controller for resetting account data in the test environment.\r\n */\r\nexport class AccountResetController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"Test\",\r\n    \"UiHelpers\",\r\n    \"AjaxNg1\",\r\n    \"SessionService\"\r\n  ];\r\n\r\n  /**\r\n   * Creates a new AccountResetController.\r\n   * @param testApi - Api methods for resetting account data.\r\n   * @param uiHelpers - Salaxy UI Helpers.\r\n   * @param ajax - Salaxy ajax component.\r\n   */\r\n  constructor(\r\n    private testApi: Test,\r\n    private uiHelpers: UiHelpers,\r\n    private ajax: Ajax,\r\n    private sessionService: SessionService\r\n  ) { }\r\n\r\n  /**\r\n   * Delete the current account data and credentials (including Auth0 user).\r\n   * Can be called only in a test environment.\r\n   */\r\n  public deleteCurrent(): void {\r\n    this.uiHelpers.showConfirm(\"Haluatko varmasti poistaa tilin?\")\r\n      .then((result: boolean) => {\r\n        if (result) {\r\n          const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n          this.testApi.deleteCurrentAccount().then(() => {\r\n            loading.dismiss();\r\n            this.logout();\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Remove all calculations, workers etc. user objects except products and signature from the account.\r\n   * Can be called only in a test environment.\r\n   */\r\n  public deleteData(): void {\r\n    this.uiHelpers.showConfirm(\"Haluatko varmasti poistaa tiliin liittyvän datan?\")\r\n      .then((result: boolean) => {\r\n        if (result) {\r\n          const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n          this.testApi.deleteCurrentAccountData().then(() => {\r\n            loading.dismiss();\r\n            this.logout();\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Remove all calculations, payrolls and payments from the account.\r\n   * Can be called only in a test environment.\r\n   */\r\n  public deleteCalculations(): void {\r\n    this.uiHelpers.showConfirm(\"Haluatko varmasti poistaa tilin laskelmat?\")\r\n      .then((result: boolean) => {\r\n        if (result) {\r\n          const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n          this.testApi.deleteCurrentAccountCalculations().then(() => {\r\n            loading.dismiss();\r\n            this.logout();\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Remove workers including calculations, employment contracts and tax cards from the account.\r\n   * Can be called only in a test environment.\r\n   */\r\n  public deleteWorkers(): void {\r\n    this.uiHelpers.showConfirm(\"Haluatko varmasti poistaa tilin työntekijät?\")\r\n      .then((result: boolean) => {\r\n        if (result) {\r\n          const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n          this.testApi.deleteCurrentAccountWorkers().then(() => {\r\n            loading.dismiss();\r\n            this.logout();\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Remove all holiday year from all workers. Does not touch the default values of holidays in Worker Employment relation.\r\n   * Can be called only in a test environment.\r\n   */\r\n  public deleteHolidays(): void {\r\n    this.uiHelpers.showConfirm(\"Haluatko varmasti poistaa loma- ja poissaolotiedot?\")\r\n      .then((result: boolean) => {\r\n        if (result) {\r\n          const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n          this.testApi.deleteCurrentAccountHolidays().then(() => {\r\n            loading.dismiss();\r\n            this.logout();\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Delete all empty accounts (company or worker) created by this account.\r\n   * Can be called only in a test environment.\r\n   */\r\n  public deleteAuthorizingAccounts(): void {\r\n    this.uiHelpers.showConfirm(\"Haluatko varmasti poistaa tilin luomat muut tilit?\")\r\n      .then((result: boolean) => {\r\n        if (result) {\r\n          const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n          this.testApi.deleteCurrentAccountAuthorizingAccounts().then(() => {\r\n            loading.dismiss();\r\n            this.logout();\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Remove pension and insurance from the account.\r\n   * Can be called only in a test environment.\r\n   */\r\n  public deletePensionAndInsurance(): void {\r\n    this.uiHelpers.showConfirm(\"Haluatko varmasti poistaa tiliin liittyvän TyEL:n ja vakuutukset?\")\r\n      .then((result: boolean) => {\r\n        if (result) {\r\n          const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n          this.testApi.deleteCurrentAccountPensionAndInsurance().then(() => {\r\n            loading.dismiss();\r\n            this.logout();\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Remove the signature from the account.\r\n   * Can be called only in a test environment.\r\n   */\r\n  public deleteSignature(): void {\r\n    this.uiHelpers.showConfirm(\"Haluatko varmasti poistaa tilin valtuutuksen (allekirjoitus)?\")\r\n      .then((result: boolean) => {\r\n        if (result) {\r\n          const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n          this.testApi.deleteCurrentAccountSignature().then(() => {\r\n            loading.dismiss();\r\n            this.logout();\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Checks if the KYC (Know Your Customer) process is done for the current account.\r\n   * @returns A boolean value indicating whether the KYC process is done.\r\n   */\r\n  public isKycMissing(): boolean {\r\n    return !((this.sessionService.session?.currentAccount?.identity as any)?.kycUpdatedAt);\r\n  }\r\n\r\n  /**\r\n   * Handles the KYC (Know Your Customer) process.\r\n   * If KYC is missing, it activates the KYC.\r\n   * Otherwise, it deletes the KYC.\r\n   */\r\n  public handleKyc(): void {\r\n    if (this.isKycMissing()) {\r\n      this.activateKyc();\r\n    } else {\r\n      this.deleteKyc();\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Deletes the KYC (Know Your Customer) information for the current account.\r\n   * Shows a confirmation dialog before deleting the KYC.\r\n   * If the user confirms, it makes an API call to delete the KYC and logs out the user.\r\n   */\r\n  private deleteKyc(): void {\r\n    this.uiHelpers.showConfirm(\"Haluatko varmasti poistaa tilin KYCin?\")\r\n      .then((result: boolean) => {\r\n        if (result) {\r\n          const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n          this.testApi.deleteCurrentAccountKyc().then(() => {\r\n            loading.dismiss();\r\n            this.logout();\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Activates the KYC for the account.\r\n   * Displays a confirmation dialog and proceeds with the activation if confirmed.\r\n   * Deletes the current account signature and logs out after successful activation.\r\n   */\r\n  private activateKyc(): void {\r\n    this.uiHelpers.showConfirm(\"Haluatko varmasti aktivoidatilin KYCin?\")\r\n      .then((result: boolean) => {\r\n        if (result) {\r\n          const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n          this.testApi.activateCurrentAccountKyc().then(() => {\r\n            loading.dismiss();\r\n            this.logout();\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n  private logout() {\r\n    this.ajax.setCurrentToken(null);\r\n    window.location.assign(\"/\");\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { CalculatorLogic, Dates, Numeric, ReportType, TaxCard2019Logic, Token } from \"@salaxy/core\";\r\nimport { CalculationMapper, Templates } from \"@salaxy/reports\";\r\nimport { SessionService } from \"../../services\";\r\nimport jsonTest from \"./test.json\";\r\n\r\n/**\r\n * Helps in performing basic smoke test about salaxy libraries:\r\n * Are all the libraries and dependencies loaded and functional in the package.\r\n */\r\nexport class SmokeTestController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"SessionService\"];\r\n\r\n  /** Defines the view / set of tests: \"core\" or \"ng1\" */\r\n  public mode: \"core\" | \"ng1\";\r\n\r\n  public reportsTests = {\r\n    loaded: null as boolean,\r\n    mapper: null as boolean,\r\n    handlebars: null as boolean\r\n  };\r\n\r\n  constructor(public sessionSrv: SessionService) {\r\n  }\r\n\r\n  /**\r\n   * Controller initialization\r\n   */\r\n  public $onInit() {\r\n    try {\r\n      this.runReportTests();\r\n    }\r\n    catch(e)\r\n    {\r\n      console.error(\"Init tests run failed with exception.\");\r\n      console.log(e);\r\n    }\r\n  }\r\n\r\n  /** Gets number 1 from @salaxy/core library. */\r\n  public getNumber(): 1 | number {\r\n    return Numeric.parseNumber(\"1\") || null;\r\n  }\r\n\r\n  /** Gets a date formatted with Dates library: \"20.02.2020\" */\r\n  public getADate(): \"20.02.2020\" | string {\r\n    return Dates.format(Dates.asDate(\"2020-02-20\"));\r\n  }\r\n\r\n  /** Returns true if the code can read the token usin Base64 library. */\r\n  public readToken(): boolean {\r\n    const token = \"eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJpc3MiOiJPbmxpbmUgSldUIEJ1aWxkZXIiLCJpYXQiOjE2Mjg2OTE2OTMsImV4cCI6MTY2MDIyNzY5MywiYXVkIjoid3d3LmV4YW1wbGUuY29tIiwic3ViIjoianJvY2tldEBleGFtcGxlLmNvbSIsIkdpdmVuTmFtZSI6IkpvaG5ueSIsIlN1cm5hbWUiOiJSb2NrZXQiLCJFbWFpbCI6Impyb2NrZXRAZXhhbXBsZS5jb20iLCJSb2xlIjpbIk1hbmFnZXIiLCJQcm9qZWN0IEFkbWluaXN0cmF0b3IiXX0.WBuoHS5h8iZi0b5cE25onpvgYFv_X-QXbLdf0KjECEY\";\r\n    return Token.parseHeader(token).alg === \"HS256\";\r\n  }\r\n\r\n  /** Runs smoke tests related to Reports library. */\r\n  public runReportTests(): void {\r\n    this.reportsTests.loaded = !!new CalculationMapper();\r\n    this.reportsTests.mapper = this.isCalcMapperWorking();\r\n    this.reportsTests.handlebars = this.isHbsTemplatesWorking();\r\n  }\r\n\r\n  /** Shows a saveAs dialog for text file (\"Hello, world!\"). */\r\n  public saveAs() {\r\n    const blob = new Blob([\"Hello, world!\"], {type: \"text/plain;charset=utf-8\"});\r\n    // This only works in non-module mode (umd package). Implement module version if necessary.\r\n    (window as any).saveAs(blob, \"hello world.txt\");\r\n  }\r\n\r\n  /** Gets a text from json file. */\r\n  public getJson() {\r\n    return jsonTest.test;\r\n  }\r\n\r\n  /** Test chart with annotations */\r\n  public chartData: any = TaxCard2019Logic.getMainChart(\r\n    {\r\n      card: {\r\n        incomeLimit: 30000,\r\n        taxPercent: 10,\r\n        taxPercent2: 30,\r\n        forYear: Dates.getYear(Dates.getToday()),\r\n        personalId: \"111111-111*\",\r\n        validity: {\r\n          start: Dates.getToday(),\r\n        }\r\n     },\r\n     result: {\r\n       totalIncome: 21000,\r\n     },\r\n     incomeLog: [],\r\n    }\r\n  );\r\n  private isCalcMapperWorking(): boolean {\r\n    const calc = CalculatorLogic.getBlank();\r\n    calc.worker.avatar.firstName = \"James\";\r\n    calc.worker.avatar.sortableName = \"JamesB\";\r\n    calc.worker.tax.snapshot = { forYear: 2021, incomeLimit: 999.50 };\r\n    calc.result.totals = {};\r\n    calc.result.workerCalc = {};\r\n    calc.result.responsibilities = {};\r\n    calc.result.employerCalc = {};\r\n    const calcReport = CalculationMapper.getCalculationReport(calc, ReportType.SalarySlip, undefined);\r\n\r\n    return (\r\n      calcReport.header.taxcardIncomeLimit === 999.50\r\n      && calcReport.header.worker.avatar.firstName === \"James\"\r\n      && calcReport.header.worker.avatar.sortableName === \"JamesB\"\r\n    );\r\n  }\r\n\r\n  /**\r\n   * Tests that handlebars templates including nested partials and helpers are working correctly.\r\n   * @returns Returns true if templates are working and otherwise false.\r\n   */\r\n  private isHbsTemplatesWorking(): boolean {\r\n    const html = new Templates().getHtml(\r\n      \"salarySlipV2\",\r\n      {\r\n        report: {\r\n          header: {\r\n            taxcardIncomeLimit: 999.50,\r\n            worker: {\r\n              avatar: {\r\n                firstName: \"James\",\r\n                sortableName: \"JamesB\",\r\n              }\r\n            }\r\n          }\r\n        }\r\n      }\r\n    );\r\n\r\n    return (\r\n      // Produced by a deeply nested partial (salarySlipV2 -> workerReportHeadV2 ->\r\n      // contractPartiesContactDetailsV2)\r\n      html.indexOf(`<div class=\"uppercase\">JamesB</div>`) !== -1\r\n      // Produced by a helper function used in a deeply nested partial (salarySlipV2 ->\r\n      // workerReportHeadV2 -> workerContractDetailsV2 -> c\r\n      && html.indexOf(`<span>999,50€</span>`) !== -1\r\n    );\r\n  }\r\n\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {\r\n  ReferenceObject,ReferenceObjectListItem,ReferenceObjects,\r\n} from \"@salaxy/core\";\r\n\r\nimport { UiHelpers } from \"../../services\";\r\nimport { ApiCrudObjectController } from \"../bases\";\r\n\r\n/**\r\n * FOR TESTING OR DEVELOPMENT USE ONLY - NOT FOR PRODUCTION USE.\r\n * =============================================================\r\n * Provides UI logic for viewing and adding new (modifying) Reference Objects\r\n * The implementation is based on the current development conventions.\r\n * The reference objects have no meaning or use outside development or testing environments, and they\r\n * should not be used in production for any business purpose.\r\n */\r\nexport class ReferenceObjectCrudController extends ApiCrudObjectController<ReferenceObject, ReferenceObjectListItem> {\r\n  isSaving: boolean;\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"ReferenceObjects\",\r\n    \"UiHelpers\",\r\n    \"$location\",\r\n    \"$routeParams\"\r\n  ];\r\n\r\n  constructor(\r\n    api: ReferenceObjects,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any\r\n  ) { // Dependency injection\r\n    super(api, uiHelpers, $location, $routeParams);\r\n  }\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"/reference-objects\",\r\n      detailsUrl: this.detailsUrl || \"/reference-objects/details/\",\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/ReferenceObjects.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n}","import { AbsencePeriod, Arrays, Dates, EnumerationsLogic, HolidaysLogic, WorkerAbsences, CalendarSeries, CalendarUiEvent } from \"@salaxy/core\";\r\nimport { UiHelpers } from \"../../services\";\r\nimport { ListControllerBase, ListControllerBaseBindings } from \"../bases\";\r\n\r\nclass AbsencePeriodsControllerBindings extends ListControllerBaseBindings {\r\n   /** If true, will format the table with class table-condensed. Later may add some other condensed formatting. */\r\n   public condensed = \"<\";\r\n\r\n   /** Date filter start value. Will be compared to period end date. */\r\n   public filterStart = \"<\";\r\n\r\n   /** Date filter end value. Will be compared to period start date. */\r\n   public filterEnd = \"<\";\r\n}\r\n\r\n/**\r\n * Controls the absences list (poissaolokirjanpito) for a selected holiday year.\r\n */\r\nexport class AbsencePeriodsController extends ListControllerBase<WorkerAbsences, AbsencePeriod> {\r\n\r\n  /** Bindings for components that use this controller */\r\n  public static bindings = new AbsencePeriodsControllerBindings();\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"UiHelpers\"];\r\n\r\n  /** If true, will format the table with class table-condensed. Later may add some other condensed formatting. */\r\n  public condensed: boolean;\r\n\r\n  /** Date filter start value. Will be applied to period start dates. */\r\n  public filterStart: string;\r\n\r\n  /** Date filter end value. Will be applied to period end dates. */\r\n  public filterEnd: string;\r\n\r\n  constructor(uiHelpers: UiHelpers) {\r\n    super(uiHelpers);\r\n  }\r\n\r\n  /** List of items */\r\n  public get list(): AbsencePeriod[] {\r\n    if (!this.parent) {\r\n      return null;\r\n    }\r\n    return this.parent.periods;\r\n  }\r\n\r\n  /** Maps WorkerAbsences to calendar series. */\r\n  public mapToCalendar = (abs: WorkerAbsences): CalendarSeries[] => {\r\n    return [{\r\n      key: abs.id,\r\n      title: abs.workerSnapshot?.displayName,\r\n      avatar: abs.workerSnapshot,\r\n      events: abs.periods.map((period) => ({\r\n          start: period.period.start,\r\n          end: period.period.end,\r\n          summary: EnumerationsLogic.getEnumLabel(\"AbsenceCauseCode\", period.causeCode),\r\n          data: period,\r\n        })),\r\n    }];\r\n  };\r\n\r\n  /**\r\n   * Filter that is applied to the list\r\n   * @param value Item in the list\r\n   */\r\n  public filter = (value: AbsencePeriod) => {\r\n    if (this.filterEnd && value.period.start > this.filterEnd) {\r\n      return false;\r\n    }\r\n    if (this.filterStart && value.period.end < this.filterStart) {\r\n      return false;\r\n    }\r\n    return true;\r\n  };\r\n\r\n  /** Creating of a new item. */\r\n  public getBlank(): AbsencePeriod {\r\n    return {\r\n      period: {\r\n        start: Dates.getToday(),\r\n        end: Dates.getToday(),\r\n        daysCount: 1,\r\n      },\r\n    };\r\n  }\r\n\r\n  /** Template for edit UI that is shown in a modal dialog. */\r\n  public getEditDialogTemplateUrl() {\r\n    return \"salaxy-components/worker/AbsencePeriodsEditDialog.html\";\r\n  }\r\n\r\n  /** Calendar is clicked => Show edit dialog accorging to calendar data. */\r\n  public calendarClick(type: \"event\" | \"day\",  date: string, event: CalendarUiEvent) {\r\n    switch (type) {\r\n      case \"event\":\r\n        this.showEditDialog(event.data);\r\n        break;\r\n      case \"day\": {\r\n        const newItem = this.getBlank();\r\n        newItem.period.start = date;\r\n        newItem.period.end = date;\r\n        this.showEditDialog(newItem, true);\r\n        break;\r\n      }\r\n      default:\r\n        throw new Error(\"Not supported: \" + type);\r\n    }\r\n  }\r\n\r\n  /** Gets the needed logic for Edit dialog */\r\n  public getEditDialogLogic() {\r\n    return HolidaysLogic.getAbsencesEditDialogLogic();\r\n  }\r\n\r\n  /** Gets a total days calculation for different types. */\r\n  public getTotalDays(type: \"all\" | \"absencesPaid\" | \"absencesUnpaid\" | \"absencesHolidayAccrual\" | \"absencesNoHolidayAccrual\" = \"all\") {\r\n    const list = this.list.filter((x) => this.filter(x));\r\n    switch (type) {\r\n      case \"all\":\r\n        return Arrays.sum(list, (x) => x.period.daysCount);\r\n      case \"absencesPaid\":\r\n        return Arrays.sum(list.filter((x) => x.isPaid), (x) => x.period.daysCount);\r\n      case \"absencesUnpaid\":\r\n        return Arrays.sum(list.filter((x) => !x.isPaid), (x) => x.period.daysCount);\r\n      case \"absencesHolidayAccrual\":\r\n        return Arrays.sum(list.filter((x) => x.isHolidayAccrual), (x) => x.period.daysCount);\r\n      case \"absencesNoHolidayAccrual\":\r\n        return Arrays.sum(list.filter((x) => !x.isHolidayAccrual), (x) => x.period.daysCount);\r\n    }\r\n    return null;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { CalculationListItem, Calculations, DataMappersLogic, EmploymentLogic, EmploymentRelationSalaryPaymentMethod, EmploymentRelationTaxcard, EmploymentRelationType, Employments, EnumerationsLogic, Exportable, InsuranceCompany, Numeric, PensionCompany, TaxcardKind, Translations, UserSession } from \"@salaxy/core\";\r\nimport { AccountSettingsInSession, ContactAdvanced, ContactType, Country, Employment, EmploymentListItem, EmploymentSocialSecurityModel, WorkerAccount, Objects } from \"@salaxy/core\";\r\nimport { InternationalSocialSecurityException, PensionCalculation } from \"@salaxy/core\";\r\n\r\nimport { FileService, JsonSchemaService, SessionService, UiCrudHelpers, UiHelpers } from \"../../services\";\r\nimport type { EmploymentDetailsTabs } from \"../../services\";\r\nimport { ApiCrudObjectController } from \"../bases\";\r\nimport { EmploymentTaxcardsController } from \"./EmploymentTaxcardsController\";\r\n\r\n/**\r\n * CRUD functionality for Employment relation.\r\n */\r\nexport class EmploymentCrudController extends ApiCrudObjectController<Employment, EmploymentListItem> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Employments\", \"SessionService\", \"FileService\", \"JsonSchemaService\", \"UiCrudHelpers\", \"UiHelpers\", \"$location\", \"$routeParams\", \"$timeout\", \"Calculations\", \"$route\"];\r\n\r\n  /** If true, the save/delete etc. buttons are not shown (they will come from the container / modal) */\r\n  public isModal: boolean;\r\n\r\n  /**\r\n   * If set, the Worker details component can show infromation about the latest taxcard in the view.\r\n   * This is not present in the employment, but taxcards controller may be present in the same view.\r\n   * @example\r\n   * In the Details.html view we set:\r\n   * <salaxy-employment-taxcards employment-id=\"$ctrl.current.id\" ng-ref=\"$ctrl.taxcardsController\"></salaxy-employment-taxcards>\r\n   */\r\n  public taxcardsController: EmploymentTaxcardsController;\r\n\r\n  public employmentForm: angular.IFormController;\r\n\r\n  constructor(\r\n    private fullApi: Employments,\r\n    private sessionService: SessionService,\r\n    private fileService: FileService,\r\n    private jsonSchemaService: JsonSchemaService,\r\n    private uiCrudHelpers: UiCrudHelpers,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    private $timeout: angular.ITimeoutService,\r\n    private calculations: Calculations,\r\n    private $route: angular.route.IRouteService,\r\n  ) {\r\n    super(fullApi, uiHelpers, $location, $routeParams);\r\n  }\r\n\r\n  /**\r\n   * Initialization code.\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"/workers\",\r\n      detailsUrl: this.detailsUrl || \"/employments/details/\",\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/Employments.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Gets or sets the taxcard type in employment.\r\n   * In set, shows a confirm dialog before committing the change.\r\n   */\r\n  public get taxcardType(): EmploymentRelationTaxcard {\r\n    return this.current.info.taxcard;\r\n  }\r\n  public set taxcardType(value: EmploymentRelationTaxcard) {\r\n    if (!this.current?.info || this.current.info.taxcard == value) {\r\n      return;\r\n    }\r\n    if ((this.current.info?.taxcard || EmploymentRelationTaxcard.Undefined) == EmploymentRelationTaxcard.Undefined) {\r\n      this.current.info.taxcard = value;\r\n      this.save();\r\n      return;\r\n    }\r\n    this.uiHelpers.showConfirm(\"SALAXY.UI_Terms.areYouSure\", \"SALAXY.NG1.WorkerDetailsComponent.taxCard.typeAreYouSure\").then((result) => {\r\n      if (result) {\r\n        this.current.info.taxcard = value;\r\n        this.save();\r\n      }\r\n    });\r\n  }\r\n\r\n  /** Returns true if the employer is a household employer (person as opposed to company). */\r\n  public get isHousehold() {\r\n    return this.sessionService.isInRole(\"person\");\r\n  }\r\n\r\n  /**\r\n   * Gets a description text for an employment relation\r\n   * @param employment The employment relation to describe.\r\n   */\r\n  public getEmploymentDescription(employment: Employment | EmploymentListItem): string {\r\n    if (EmploymentLogic.isListItem(employment)) {\r\n      return EmploymentLogic.getDescription(employment.otherPartyInfo, employment.data.type, employment.data.pensionCalculation);\r\n    }\r\n    return EmploymentLogic.getDescription(employment.personalInfo, employment.info?.type, employment.info?.pensionCalculation);\r\n  }\r\n\r\n  /**\r\n   * Gets a descriptive text on whether the employment is active or not.\r\n   * @param employment Employment relation to get the text for.\r\n   * @returns A text that describes whether the employment is active or not with the dates (start and end).\r\n   */\r\n  public getActiveText(employment: Employment | EmploymentListItem): string {\r\n    return EmploymentLogic.getActiveText(employment);\r\n  }\r\n\r\n  /**\r\n   * Gets the tax card info text for active taxcard.\r\n   */\r\n  public getTaxCardInfo(): {\r\n    /** Text that is shown to the end user. */\r\n    text: string,\r\n    /** If true, the taxcard is missing => show as error. */\r\n    isMissing: boolean,\r\n  } | undefined {\r\n    const result = {\r\n      text: Translations.get(\"SALAXY.UI_Terms.loading\"),\r\n      isMissing: false,\r\n    };\r\n    if (!this.current) {\r\n      return result;\r\n    }\r\n    if (this.current.info.taxcard == EmploymentRelationTaxcard.NoTaxCard) {\r\n      result.text = EnumerationsLogic.getEnumLabel(\"TaxcardKind\", TaxcardKind.NoTaxCard);\r\n      return result;\r\n    }\r\n    if (this.current.info.taxcard == EmploymentRelationTaxcard.TaxAtSource) {\r\n      result.text = EnumerationsLogic.getEnumLabel(\"EmploymentRelationTaxcard\", EmploymentRelationTaxcard.TaxAtSource);\r\n      result.text = `${result.text} ${Numeric.formatPercent(this.current.international.taxAtSource.percent * 100, null)}`;\r\n      return result;\r\n    }\r\n    if (!this.taxcardsController?.current) {\r\n      return result;\r\n    }\r\n    const taxcardData = this.taxcardsController.current;\r\n    const taxCard = taxcardData.active;\r\n    if (!taxCard && taxcardData.employmentTaxcard == EmploymentRelationTaxcard.Auto) {\r\n      result.text = EnumerationsLogic.getEnumLabel(\"TaxcardKind\", TaxcardKind.Auto);\r\n    } else {\r\n      const kind = taxCard ? taxCard.card.kind : TaxcardKind.Undefined;\r\n      result.isMissing = kind == TaxcardKind.Undefined;\r\n      if (kind === TaxcardKind.Undefined || kind === TaxcardKind.NoTaxCard || kind === TaxcardKind.NoWithholdingHousehold) {\r\n        result.text = EnumerationsLogic.getEnumLabel(\"TaxcardKind\", kind);\r\n      } else {\r\n        const percent = taxCard?.card?.taxPercent === 0 ? 0 : (taxCard?.card?.taxPercent || 60);\r\n        result.text = EnumerationsLogic.getEnumLabel(\"TaxcardKind\", kind) + \": \" + Numeric.formatPercent(percent);\r\n      }\r\n    }\r\n    return result;\r\n  }\r\n\r\n  /**\r\n   * Gets a contact of specific type.\r\n   * @param type Type of contact to get. Use null to fetch any contact type (creates Default if requested).\r\n   * @param createIfNotExists If true creates the contact of given type if one does not exist.\r\n   * @returns Contact of given type or undefined if one is not found AND createIfNotExists is false.\r\n   */\r\n  public getContact(type: ContactType | null, createIfNotExists = true): ContactAdvanced | null {\r\n    return EmploymentLogic.getContact(this.current, type || ContactType.Default, createIfNotExists);\r\n  }\r\n\r\n  private _readOnlyDefaultContact = {};\r\n  /**\r\n   * Returns default contact as read only.\r\n   */\r\n  public get readOnlyDefaultContact() {\r\n    const contact = this.getContact(ContactType.Default) ?? {};\r\n    if (!Objects.equal(contact, this._readOnlyDefaultContact)) {\r\n        this._readOnlyDefaultContact = { ...contact };\r\n    }\r\n    return this._readOnlyDefaultContact;\r\n  }\r\n\r\n  /**\r\n   * Gets the text for a Taxcard type badge (short text in lists).\r\n   * Returns null if the badge should not be shown.\r\n   */\r\n  public getTaxcardBadge(cardType: EmploymentRelationTaxcard): string | null {\r\n    switch (cardType) {\r\n      case EmploymentRelationTaxcard.Auto:\r\n        return \"Auto\";\r\n      case EmploymentRelationTaxcard.Manual:\r\n        return \"Manual\";\r\n      case EmploymentRelationTaxcard.NoTaxCard:\r\n        return \"60%\";\r\n      case EmploymentRelationTaxcard.TaxAtSource:\r\n      default:\r\n        return EnumerationsLogic.getEnumLabel(\"EmploymentRelationTaxcard\", cardType);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Opens the new Employment relation wizard and if a new relation is created, moves the user to the list view.\r\n   */\r\n  public launchCreateEmploymentWizard() {\r\n    this.uiCrudHelpers.createNewEmployment().then((result) => {\r\n      if (result.action === \"ok\") {\r\n        const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n        return this.uiHelpers.wait(3000).then(() => {\r\n          loading.dismiss();\r\n          this.$route.reload();\r\n        });\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shows a dialog for editing an existing employment.\r\n   * If user clicks OK, the changes are saved.\r\n   * @param employmentId - Identifier of the Workers employment.\r\n   * @param buttonTypes \"default\" shows standard save button,\r\n   * \"updateCalc\" shows two buttons \"ok\" for full calc update and \"ok-no-rows\" update without touching default rows.\r\n   * @param initialTab - Tab to open.\r\n   * @returns Dialog result. Note that OK result may be either \"ok\" or \"ok-no-rows\".\r\n   * The latter means that for calculation only worker info should be updated, not the default rows.\r\n   */\r\n  public openEditEmploymentDialog(employmentId: string, buttonTypes: \"default\" | \"updateCalc\", initialTab: EmploymentDetailsTabs = null) {\r\n    return this.uiCrudHelpers.openEditEmploymentDialog(employmentId, buttonTypes, initialTab);\r\n  }\r\n\r\n  /**\r\n   * Returns Exportable api for the used crud.\r\n   * @returns Exportable api.\r\n   */\r\n  public getExportable(): Exportable<Employment> {\r\n    return {\r\n      getExportMappers: () => DataMappersLogic.getMappers([\"Employment\", \"EmploymentListItem\"]),\r\n      getExportMapper: (id) => DataMappersLogic.getBuiltInMapper(id, this.jsonSchemaService.getCache()),\r\n      exporters: this.fileService.getDefaultExporters(),\r\n      getSingle: (item) => this.getApi().getSingle(item.id),\r\n      list: (maxCount?, notify?) => this.odataController.exportItems(maxCount ?? 0, notify),\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Deletes the current employment if there are no associated calculations.\r\n   * This method checks for any calculations associated with the current employment.\r\n   * If no calculations are found, it proceeds to delete the employment.\r\n   * Otherwise, it shows an alert indicating that the employment cannot be deleted because there are associated calculations that need to be removed first.\r\n   */\r\n  public async deleteEmployment(): Promise<void> {\r\n      const result = await this.calculations.getOData({ $filter: `data/employmentId eq '${this.current.id}'` });\r\n      // If there are no calculations, delete the employment.\r\n      if (result.items.length === 0) {\r\n        await this.delete(this.current, Translations.get(\"SALAXY.NG1.WorkerListComponent.employmentDeletion.confirmText\"));\r\n        return;\r\n      }\r\n\r\n      this.uiHelpers.showAlert(\r\n        Translations.get(\"SALAXY.NG1.WorkerListComponent.employmentDeletion.existingtCalculationsHeading\"),\r\n        Translations.get(\"SALAXY.NG1.WorkerListComponent.employmentDeletion.existingtCalculationsText\")\r\n      );\r\n  }\r\n\r\n  /**\r\n   * Opens a list of employment relations in to a dialog window.\r\n   * Creates list of selected employments and updates taxcard to auto.\r\n   * @param items Optional array of currently loaded/visible items.\r\n   * The data.taxcard is updated so that the changes are refelected in the list.\r\n   */\r\n  public selectAutoTaxcardForEmployments(items?: EmploymentListItem[]) {\r\n    const employmentList: EmploymentListItem[] = [];\r\n    this.uiHelpers.openEditDialog(\r\n      \"salaxy-components/modals/calc/WorkerList.html\",\r\n      employmentList,\r\n      {\r\n        title: \"SALAXY.NG1.PayrollComponent.createNewCalcDialog\",\r\n        okButtonText: \"SALAXY.NG1.WorkerListComponent.okButtonText\",\r\n        infoHtml: \"SALAXY.NG1.WorkerListComponent.infoText.html\"\r\n      }).then((result) => {\r\n        if (result.action === \"ok\" && employmentList.length > 0) {\r\n          const loader = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.isSaving\");\r\n          let counter = 1;\r\n          employmentList.forEach(selectedItem => {\r\n            loader.setText(`${Translations.get(\"SALAXY.UI_Terms.isSaving\")} ${counter}/${employmentList.length}`);\r\n            this.fullApi.getSingle(selectedItem.id).then((fullEmployment) => {\r\n              fullEmployment.info.taxcard = EmploymentRelationTaxcard.Auto;\r\n              this.fullApi.save(fullEmployment).then((savedEmployment) => {\r\n                if (items) {\r\n                  const item = items.find(x => x.id === savedEmployment.id);\r\n                  if (item) {\r\n                    item.data.taxcard = savedEmployment.info.taxcard;\r\n                  }\r\n                }\r\n                counter++;\r\n                if (counter - 1 === employmentList.length) {\r\n                  loader.dismiss();\r\n                }\r\n              });\r\n            });\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Called when the type of pension calculation changes\r\n   * => Sets the PartialOwner and NoPensionRequired IncomeEarnerTypes accordingly.\r\n   */\r\n  public pensionCalculationChange() {\r\n    EmploymentLogic.resetModelFromPensionCalculation(this.current);\r\n  }\r\n\r\n  /** Gets the session - currently used for company type */\r\n  public get session(): UserSession {\r\n    return this.sessionService.session;\r\n  }\r\n\r\n  /** Called when the type of employment changes => Sets the income earner types accordingly. */\r\n  public employmentTypeChange(): void {\r\n    EmploymentLogic.resetModelFromType(this.current);\r\n  }\r\n\r\n  /** Gets the cached version of the social security selection. */\r\n  public get socSec() {\r\n    return this.uiHelpers.cache(this, \"socSec\",\r\n      () => this.getSocialSecurityModel(\r\n        this.sessionService.session?.settings, this.current.info.type, this.current.international.socialSecurity, this.current.info.pensionCalculation,\r\n        this.current.info.pensionCompany, this.current.info.insuranceCompany, this.current.international.socialSecurityExceptions),\r\n      () => this.current.info.type + this.current.international.socialSecurity + this.current.info.pensionCalculation\r\n        + this.current.info.pensionCompany + this.current?.info.insuranceCompany + this.current.international.socialSecurityExceptions\r\n    );\r\n  }\r\n\r\n  /** Gets or sets the current country. When setting, the \"foreign\" address is reset. When getting Finland (fi) is converted to null. */\r\n  public get country(): Country | null {\r\n    return this.current.international.country == Country.Fi ? null : this.current.international.country;\r\n  }\r\n  public set country(value: Country) {\r\n    this.current.international.country = value;\r\n    this.current.contacts = (this.current.contacts || []).filter(x => x.type != ContactType.Foreign);\r\n    const contact = this.getContact(ContactType.Foreign, true);\r\n    contact.country = value;\r\n  }\r\n\r\n  /**\r\n   * Gets the social security pensions model (available options) for the current selections.\r\n   * @param settings Account settings in the session\r\n   * @param type Type of employment relation selected\r\n   * @param socialSecurity Whether the person is in Finnish or foregion social security - or mixed\r\n   * @param pensionCalculation Type of Pension calculation: employee/TyEL or others (YEL, farmer etc.)\r\n   * @param pensionCompany Pension company (if several) that is selected.\r\n   * @param insuranceCompany Insurance company (if several) that is selected.\r\n   * @param socSecExceptions The selected social security exceptions (not subject to)\r\n   */\r\n  public getSocialSecurityModel(\r\n    settings: AccountSettingsInSession, type: EmploymentRelationType,\r\n    socialSecurity: \"default\" | \"foreign\" | \"mixed\", pensionCalculation: PensionCalculation,\r\n    pensionCompany: PensionCompany, insuranceCompany: InsuranceCompany,\r\n    socSecExceptions: InternationalSocialSecurityException[],\r\n  ): EmploymentSocialSecurityModel {\r\n    return EmploymentLogic.getSocialSecurityModel(settings, type, socialSecurity, pensionCalculation, pensionCompany, insuranceCompany, socSecExceptions);\r\n  }\r\n\r\n  /** Overrides the Save method so that it realoads the taxcards controller if present. */\r\n  public save(): Promise<WorkerAccount> {\r\n    return super.save().then((workerAccount) => {\r\n      if (this.taxcardsController) {\r\n        this.taxcardsController.reload();\r\n      }\r\n      return workerAccount;\r\n    });\r\n  }\r\n\r\n  /** Recalculate pay statistics for the current employment */\r\n  public recalculatePayStats(): Promise<Employment> {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    return this.fullApi.recalculateEmploymentPayStats(this.current.id).then( () => {\r\n      loading.dismiss();\r\n      return this.reload();\r\n    });\r\n  }\r\n\r\n  /** Recalculate pay statistics for all employments */\r\n  public recalculateAllPayStats() {\r\n      return this.uiHelpers.showConfirm(\"Ansioiden laskenta\",\r\n      `Haluatko varmasti laskea keskituntiansiot kaikille työntekijöille?`).then( (result) => {\r\n        if (result) {\r\n          const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n          return this.fullApi.recalculatePayStats().then( () => {\r\n            loading.dismiss();\r\n            return this.uiHelpers.showAlert(\"Ansioiden laskenta\", \"Keskituntiansioiden laskenta on käynnistetty. Laskenta tapahtuu taustalla, ja se voi kestää jonkin aikaa.\");\r\n          });\r\n        }\r\n        else {\r\n          return result;\r\n        }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Gets a tooltip that shows which fields are editied in the employment relation to be different\r\n   * from the worker account (what the registered Worker has input in their UI).\r\n   * @param inputName Name of the field in Contact or \"ibanNumber\".\r\n   * @returns Tooltip text if there is a diff and tooltip should be shown.\r\n   */\r\n  public getInputTooltip(inputName: \"email\" | \"telephone\" | \"street\" | \"postalCode\" | \"city\" | \"ibanNumber\"): string | undefined {\r\n    if (inputName == \"ibanNumber\") {\r\n      if (this.current.info.ibanNumber !== this.current.personalInfo.ibanNumber) {\r\n        return `Tilinumeroa on muokattu tähän työsuhteeseen. Rekisteröityneen työntekijän syöttämä arvo on \"${this.current.personalInfo.ibanNumber}\". Jos haluat käyttää työntekijän syöttämää arvoa, voit kopioida sen ja päivittää tiedon kenttään, tai tyhjentää kentän ja painaa Tallenna.`;\r\n      }\r\n      return undefined;\r\n    }\r\n    if (!EmploymentLogic.getContact(this.current, ContactType.EmployerOverride)) {\r\n      // If not originally overridden, we do not wish to show this (user is editing now).\r\n      return undefined;\r\n    }\r\n    const diff = EmploymentLogic.getContact(this.current, ContactType.EmployerOverride)?.[inputName];\r\n    const workerAccountValue = EmploymentLogic.getContact(this.current, ContactType.WorkerAccount)?.[inputName];\r\n    if (diff) {\r\n      return `Yhteystietoa on muokattu tähän työsuhteeseen. Rekisteröityneen työntekijän syöttämä arvo on \"${workerAccountValue}\"`;\r\n    }\r\n    return undefined;\r\n  }\r\n\r\n  /**\r\n   * Returns the true if the field is required for the more complex UI fields.\r\n   * @param inputName Name of the field in Contact address (currently email and telephone never required) or \"ibanNumber\".\r\n   * @returns True if required.\r\n   */\r\n  public isRequired(inputName: \"street\" | \"postalCode\" | \"city\" | \"ibanNumber\"): boolean {\r\n    if (inputName == \"ibanNumber\") {\r\n      if (this.current.info.salaryPaymentMethod != EmploymentRelationSalaryPaymentMethod.BankAccount) {\r\n        return false;\r\n      }\r\n      // Required if worker account is editable (this value is updated to Worker account) OR if worker account value is empty.\r\n      return !this.current.isRegistered || !this.current.personalInfo.ibanNumber;\r\n    }\r\n    // Address is required if Personal ID starts with 9 (keinohetu) AND the same as ibanNumber above (editable or worker account empty).\r\n    return this.isOtherIdentifier && (!this.current.isRegistered || !this.getContact(ContactType.WorkerAccount)[inputName]);\r\n  }\r\n\r\n  /**\r\n   * Returns true if the current personal ID is other identifier than Finnish Personal Identification Number (keinohetu).\r\n   */\r\n  public get isOtherIdentifier() {\r\n    return EmploymentLogic.isPersonalIdOther(this.current.identity.personalId);\r\n  }\r\n\r\n  private _otherEmployments: EmploymentListItem[] | \"loading\" | undefined;\r\n\r\n  /**\r\n   * Gets the list of other employments with this personal ID.\r\n   * First call starts the loading process and returns undefined.\r\n   * Once response is received, the getter returns an array of employments (list items).\r\n   */\r\n  public get otherEmployments(): EmploymentListItem[] | undefined {\r\n    if (!this.current) {\r\n      return undefined;\r\n    }\r\n    if (!this._otherEmployments) {\r\n      if (!this.current.personalInfo.officialId) {\r\n        this._otherEmployments = [];\r\n      } else {\r\n        this._otherEmployments = \"loading\";\r\n        this.fullApi.getOData({ $filter: `otherPartyInfo/officialId eq '${this.current.personalInfo.officialId}'` }).then((result) => {\r\n          this._otherEmployments = result.items.filter(x => x.id != this.current.id);\r\n        });\r\n      }\r\n    }\r\n    return this._otherEmployments == \"loading\" ? undefined : this._otherEmployments;\r\n  }\r\n\r\n  /** Provides the logic for worker calculations OData UI. */\r\n  public calcListLogic = {\r\n    /**\r\n     * Returns true if the calculation is for another employment relation than the current one.\r\n     * @param calc Calculation to evaluate.\r\n     * @returns True, if the calculation is for another employment relation.\r\n     */\r\n    isNotCurrentEmployment: (calc: CalculationListItem): boolean => {\r\n      return calc.data.employmentId !== this.currentId;\r\n    }\r\n  };\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Dates, TaxcardListItem, Taxcard, Taxcards, WorkerCurrentTaxcards } from \"@salaxy/core\";\r\nimport { EditDialogKnownActions, UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Helps listing current all tax cards for an employment relation (latest and previous ones).\r\n */\r\nexport class EmploymentTaxcardsController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Taxcards\", \"UiHelpers\"];\r\n\r\n  /** The data after it has been loaded. Null if nothing is loaded yet.  */\r\n  public current: WorkerCurrentTaxcards;\r\n\r\n  /**\r\n   * View mode:\r\n   *\r\n   * - \"active\" only shows the active taxcard.\r\n   * - \"list\" only shows the history list.\r\n   * - \"all\" (default) shows both active and history.\r\n   */\r\n  public mode: \"active\" | \"list\" | \"all\";\r\n\r\n  /**\r\n   * Today is explicitly defined, so that it can be changed in testing.\r\n   */\r\n  public today = Dates.getToday();\r\n\r\n  /** If true, does not show the save / current buttons - the parent must show them. */\r\n  public hideButtons: boolean;\r\n\r\n  /**\r\n   * Event that is called when a taxcard is saved and the parent UI probably needs to be refreshed.\r\n   * @example <salaxy-employment-taxcards employment-id=\"$ctrl.current.employmentId\" on-save=\"$ctrl.refresh()\"></salaxy-employment-taxcards>\r\n   */\r\n   public onSave: (eventData: {\r\n    /** The selected item. */\r\n    item: Taxcard,\r\n  }) => void;\r\n\r\n  private _employmentId: string;\r\n\r\n  /** Creates a new EmploymentTaxcardsController */\r\n  constructor(\r\n    private taxcards: Taxcards,\r\n    private uiHelpers: UiHelpers) { }\r\n\r\n  /** Initializes the controller. */\r\n  public $onInit = () => {\r\n    this.mode = this.mode || \"all\";\r\n  };\r\n\r\n  /**\r\n   * Defines to which employment relation the functionality is bound to.\r\n   * The setter also starts the loading process.\r\n   */\r\n  public get employmentId(): string {\r\n    return this._employmentId;\r\n  }\r\n  public set employmentId(value: string) {\r\n    this._employmentId = value;\r\n    this.reload();\r\n  }\r\n\r\n  /** List of taxcards after it has been loaded. Null if nothing is loaded yet. */\r\n  public get list(): TaxcardListItem[] {\r\n    if (this.current) {\r\n      return this.current.list;\r\n    }\r\n    return null;\r\n  }\r\n\r\n  /** Reloads the data from the server. */\r\n  public reload() {\r\n    this.current = null;\r\n    if (this.employmentId) {\r\n      this.taxcards.getEmploymentTaxcards(this.employmentId, this.today).then((result) => {\r\n        this.current = result;\r\n      });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Removes a taxcard from the list and does a refresh.\r\n   * @param id Taxcard id.\r\n   */\r\n  public deleteTaxCard(id: string) {\r\n    this.taxcards.delete(id).then(() => {\r\n      this.reload();\r\n    });\r\n  }\r\n\r\n  /** Edit income log. */\r\n  public editIncomeLog() {\r\n    this.uiHelpers.openEditDialog(\"salaxy-components/modals/worker/taxcard-income-log.html\", this.current.active,\r\n    { editable: true }, \"lg\").then((result) => {\r\n      if (result.action === EditDialogKnownActions.Ok) {\r\n        const loader = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.pleaseWait\");\r\n        this.taxcards.save(this.current.active).then((taxcard) => {\r\n          loader.dismiss();\r\n          this.reload();\r\n          if (this.onSave) {\r\n            this.onSave({ item: taxcard});\r\n          }\r\n        });\r\n      }\r\n    });\r\n  }\r\n\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { AccountSettingsInSession, ContactType, Country, Employment, EmploymentListItem, EmploymentLogic, EmploymentRelationTaxcard, EmploymentRelationType, EmploymentSocialSecurityModel, Employments, InsuranceCompany, InternationalSocialSecurityException, PensionCalculation, PensionCompany, TaxCard2019Logic, Taxcard, TaxcardKind, UserSession, Validation } from \"@salaxy/core\";\r\n\r\nimport { EditDialogParameters, SessionService, UiHelpers, WizardService, WizardStep } from \"../../services\";\r\nimport { WizardController } from \"../bases\";\r\n\r\n/**\r\n * Wizard for creating a new employment relation.\r\n */\r\nexport class EmploymentWizardController extends WizardController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"$scope\", \"EditDialogParameters\", \"WizardService\", \"SessionService\", \"UiHelpers\", \"Employments\"];\r\n\r\n  /** Form data validity: This is bound from the form tag in the view. */\r\n  public formDataValidity: boolean;\r\n\r\n  /** The employment relation that is being added. */\r\n  public current: Employment;\r\n\r\n  /** Taxcard that is optionally added. */\r\n  public taxcard: Taxcard;\r\n\r\n  /**\r\n   * Creates a new WizardController with dependency injection.\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    $scope: angular.IScope,\r\n    private editDialogParameters: EditDialogParameters<Employment>,\r\n    wizardService: WizardService,\r\n    private sessionService: SessionService,\r\n    private uiHelpers: UiHelpers,\r\n    private api: Employments,\r\n  ) {\r\n    super($scope, wizardService);\r\n  }\r\n\r\n  /**\r\n   * Initialization of the controller\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n    this.wizardService.setSteps(this.getWizardSteps());\r\n    this.wizardService.activeStepNumber = 1;\r\n    if (!this.editDialogParameters) {\r\n      throw new Error(\"No editDialogParameters coming in.\");\r\n    }\r\n    this.current = this.editDialogParameters.current;\r\n  }\r\n\r\n  /** Returns true if user can go forward in the wizard  */\r\n  public get canGoNext(): boolean {\r\n    if (this.steps.length > this.step) {\r\n      if (this.steps[this.step] && !this.steps[this.step].disabled) {\r\n        if (this.formDataValidity === true || this.formDataValidity === null) {\r\n          return true;\r\n        }\r\n      }\r\n    }\r\n    return false;\r\n  }\r\n\r\n  /** Gets the session - currently used for company type */\r\n  public get session(): UserSession {\r\n    return this.sessionService.session;\r\n  }\r\n\r\n  /** Called when the type of employment changes => Sets the income earner types accordingly. */\r\n  public employmentTypeChange(): void {\r\n    EmploymentLogic.resetModelFromType(this.current);\r\n    EmploymentLogic.setSalaryDefaultRows(this.current.info.type, this.current.work);\r\n  }\r\n\r\n  /** Gets the cached version of the social security selection. */\r\n  public get socSec() {\r\n    return this.uiHelpers.cache(this, \"socSec\",\r\n      () => this.getSocialSecurityModel(\r\n        this.sessionService.session?.settings, this.current.info.type, this.current.international.socialSecurity, this.current.info.pensionCalculation,\r\n        this.current.info.pensionCompany, this.current.info.insuranceCompany, this.current.international.socialSecurityExceptions),\r\n      () => this.current.info.type + this.current.international.socialSecurity + this.current.info.pensionCalculation\r\n        + this.current.info.pensionCompany + this.current?.info.insuranceCompany + this.current.international.socialSecurityExceptions\r\n    );\r\n  }\r\n\r\n  /** Gets or sets the current country. When setting, the \"foreign\" address is reset. When getting Finland (fi) is converted to null. */\r\n  public get country(): Country | null {\r\n    return this.current.international.country == Country.Fi ? null : this.current.international.country;\r\n  }\r\n  public set country(value: Country) {\r\n    this.current.international.country = value;\r\n    this.current.contacts = (this.current.contacts || []).filter(x => x.type != ContactType.Foreign);\r\n    const contact = this.getContact(ContactType.Foreign);\r\n    contact.country = value;\r\n  }\r\n\r\n  /**\r\n   * Gets the social security pensions model (available options) for the current selections.\r\n   * @param settings Account settings in the session\r\n   * @param type Type of employment relation selected\r\n   * @param socialSecurity Whether the person is in Finnish or foregion social security - or mixed\r\n   * @param pensionCalculation Type of Pension calculation: employee/TyEL or others (YEL, farmer etc.)\r\n   * @param pensionCompany Pension company (if several) that is selected.\r\n   * @param insuranceCompany Insurance company (if several) that is selected.\r\n   * @param socSecExceptions The selected social security exceptions (not subject to)\r\n   */\r\n  public getSocialSecurityModel(\r\n    settings: AccountSettingsInSession, type: EmploymentRelationType,\r\n    socialSecurity: \"default\" | \"foreign\" | \"mixed\", pensionCalculation: PensionCalculation,\r\n    pensionCompany: PensionCompany, insuranceCompany: InsuranceCompany,\r\n    socSecExceptions: InternationalSocialSecurityException[],\r\n  ): EmploymentSocialSecurityModel {\r\n    return EmploymentLogic.getSocialSecurityModel(settings, type, socialSecurity, pensionCalculation, pensionCompany, insuranceCompany, socSecExceptions);\r\n  }\r\n\r\n  /**\r\n   * Called when the type of pension calculation changes\r\n   * => Sets the PartialOwner and NoPensionRequired IncomeEarnerTypes accordingly.\r\n   */\r\n  public pensionCalculationChange() {\r\n    EmploymentLogic.resetModelFromPensionCalculation(this.current);\r\n  }\r\n\r\n  private _otherEmployments: EmploymentListItem[] | \"loading\" | undefined;\r\n\r\n  private _otherEmploymentsLastPersonalId: string | undefined;\r\n\r\n  /**\r\n   * Gets the list of other employments with this personal ID.\r\n   * First call starts the loading process and returns undefined.\r\n   * Once response is received, the getter returns an array of employments (list items).\r\n   * The method also initializes the taxcard (if personal ID is changed and valid).\r\n   */\r\n  public get otherEmployments(): EmploymentListItem[] | undefined {\r\n    if (!this.current) {\r\n      return undefined;\r\n    }\r\n    this.checkPersonalId();\r\n    return this._otherEmployments == \"loading\" ? undefined : this._otherEmployments;\r\n  }\r\n\r\n  /**\r\n   * Gets a description text for an employment relation\r\n   * @param employment The employment relation to describe.\r\n   */\r\n  public getEmploymentDescription(employment: Employment | EmploymentListItem): string {\r\n    if (EmploymentLogic.isListItem(employment)) {\r\n      return EmploymentLogic.getDescription(employment.otherPartyInfo, employment.data.type, employment.data.pensionCalculation);\r\n    }\r\n    return EmploymentLogic.getDescription(employment.personalInfo, employment.info?.type, employment.info?.pensionCalculation);\r\n  }\r\n\r\n  /**\r\n   * Gets a descriptive text on whether the employment is active or not.\r\n   * @param employment Employment relation to get the text for.\r\n   * @returns A text that describes whether the employment is active or not with the dates (start and end).\r\n   */\r\n  public getActiveText(employment: Employment | EmploymentListItem): string {\r\n    return EmploymentLogic.getActiveText(employment);\r\n  }\r\n\r\n  /**\r\n   * Populates worker with test data.\r\n   * @param useRealPersonaIdRange If true, uses the real personal id range instead of artificial ID range (\"keinohetu\": last 3 numbers start with 9).\r\n   */\r\n  public populateWithTestData(useRealPersonaIdRange = false) {\r\n    EmploymentLogic.populateWithTestData(this.current, useRealPersonaIdRange);\r\n  }\r\n\r\n  /**\r\n   * Deletes a calculation row.\r\n   * @param rowIndex - Zero based row index of the row that should be deleted.\r\n   */\r\n  public deleteSalaryDefaultsRow(rowIndex: number) {\r\n    this.current.work.salaryDefaults.splice(rowIndex);\r\n  }\r\n\r\n  /** Returns true if the employer is a household employer (person as opposed to company). */\r\n  public get isHousehold() {\r\n    return this.sessionService.isInRole(\"person\");\r\n  }\r\n\r\n  /** Worker wizard configuration */\r\n  public getWizardSteps(): WizardStep[] {\r\n    const commonSteps = [{\r\n      title: \"SALAXY.NG1.WorkerWizardComponent.step1.title\",\r\n      view: \"salaxy-components/worker/EmploymentWizard/identity.html\",\r\n    },\r\n    {\r\n      title: \"SALAXY.NG1.WorkerWizardComponent.step2.title\",\r\n      view: \"salaxy-components/worker/EmploymentWizard/person.html\",\r\n    },\r\n    {\r\n      title: \"SALAXY.NG1.WorkerWizardComponent.step3.title\",\r\n      view: \"salaxy-components/worker/EmploymentWizard/type.html\",\r\n    }];\r\n    if (this.isHousehold){\r\n      return commonSteps;\r\n    }\r\n    return [\r\n      ...commonSteps,\r\n      {\r\n        title: \"SALAXY.NG1.WorkerWizardComponent.step4.title\",\r\n        view: \"salaxy-components/worker/EmploymentWizard/work.html\",\r\n      },\r\n      {\r\n        title: \"SALAXY.NG1.WorkerWizardComponent.step5.title\",\r\n        view: \"salaxy-components/worker/EmploymentWizard/tax.html\",\r\n      }\r\n    ];\r\n  }\r\n\r\n  /** Saves the taxcard and closes the dialog. */\r\n  public saveAndClose(closeFunction: (result: any) => any) {\r\n    let card = this.taxcard;\r\n    if (this.current.info.taxcard != EmploymentRelationTaxcard.Manual\r\n      || !card.card.kind || card.card.kind === TaxcardKind.Undefined || card.card.kind === TaxcardKind.Auto) {\r\n      // For clarity, remove the taxcard if it is not manual or if there is no meaningful kind.\r\n      card = null;\r\n    }\r\n    closeFunction({\r\n      action: \"ok\",\r\n      employment: this.current,\r\n      taxcard: card,\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Gets the contact information of the worker. Contact of the specific type will be created if one does not exist.\r\n   * @param type Type of contact info.\r\n   * @returns Contact object for data binding.\r\n   */\r\n  public getContact(type = ContactType.Default) {\r\n    return EmploymentLogic.getContact(this.current, type, true);\r\n  }\r\n\r\n  /**\r\n   * Returns true if the current personal ID is other identifier than Finnish Personal Identification Number (keinohetu).\r\n   */\r\n  public get isOtherIdentifier(){\r\n    return EmploymentLogic.isPersonalIdOther(this.current.identity.personalId);\r\n  }\r\n\r\n  private checkPersonalId(): void {\r\n    const personalId = this.current.identity.personalId;\r\n    if (!personalId || !Validation.isPersonalIdFi(personalId)) {\r\n      if (this._otherEmployments || this._otherEmploymentsLastPersonalId) {\r\n        this._otherEmploymentsLastPersonalId = undefined;\r\n        this._otherEmployments = undefined;\r\n      }\r\n      return;\r\n    }\r\n    if (this.taxcard?.card?.personalId !== personalId) {\r\n      this.current.info.taxcard = EmploymentRelationTaxcard.Auto;\r\n      this.taxcard = TaxCard2019Logic.getBlank(personalId, TaxcardKind.Auto);\r\n    }\r\n    if (this._otherEmploymentsLastPersonalId != this.current.identity.personalId) {\r\n      this._otherEmploymentsLastPersonalId = this.current.identity.personalId;\r\n      this._otherEmployments = \"loading\";\r\n      this.api.getOData({ $filter: `otherPartyInfo/officialId eq '${ this.current.identity.personalId }'` }).then((result) => {\r\n        this._otherEmployments = result.items.filter(x => x.id != this.current.id);\r\n      });\r\n    }\r\n  }\r\n}\r\n","import { Arrays, Brand, Dates, HolidayAccrualEntry, HolidayAccrualSource, HolidayYear, HolidayYears, Translations } from \"@salaxy/core\";\r\n\r\nimport { UiHelpers } from \"../../services\";\r\n\r\nimport { ListControllerBase, ListControllerBaseBindings } from \"../bases\";\r\n\r\n/**\r\n * Controls holiday accrual (lomapäivien kertymä) of the annual leave for a selected holiday period.\r\n */\r\nexport class HolidayYearAccrualController extends ListControllerBase<HolidayYear, HolidayAccrualEntry> {\r\n\r\n  /** Bindings for components that use this controller */\r\n  public static bindings = new ListControllerBaseBindings();\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"HolidayYears\",\r\n    \"UiHelpers\",\r\n  ];\r\n\r\n  constructor(\r\n    private holidayYears: HolidayYears,\r\n    uiHelpers: UiHelpers,\r\n  ) {\r\n    super(uiHelpers);\r\n  }\r\n\r\n  /** List of items */\r\n  public get list(): HolidayAccrualEntry[] {\r\n    if (!this.parent || !this.parent.accrual || !this.parent.accrual.months) {\r\n      return [];\r\n    }\r\n    return this.parent.accrual.months;\r\n  }\r\n\r\n  /** Creating of a new item. */\r\n  public getBlank(): HolidayAccrualEntry {\r\n    return {};\r\n  }\r\n\r\n  /**\r\n   * Saves changes to the parent object using the CRUD API.\r\n   */\r\n  public saveParent(): void {\r\n    const loader = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.isSaving\");\r\n    this.holidayYears.save(this.parent)\r\n      .then((saved) => {\r\n        this.parent = saved;\r\n        loader.dismiss();\r\n      });\r\n  }\r\n\r\n  /** Template for edit UI that is shown in a modal dialog. */\r\n  public getEditDialogTemplateUrl() {\r\n    return \"salaxy-components/worker/holidays/HolidayYearAbsencesEditDialog.html\";\r\n  }\r\n\r\n  /** Chart config for accrual overview. */\r\n  public getChartConfig(list: HolidayAccrualEntry[]) {\r\n    return this.uiHelpers.cache(this, \"accrualChart\",() => this.createConfig(list));\r\n  }\r\n\r\n  private createConfig(list: HolidayAccrualEntry[]): {type: string, data: any, options: any} {\r\n    const data = [[], []];\r\n    const labels = [];\r\n    const startSaldo: number = (this.parent.accrual as any).startSaldo;\r\n    let cumulative = startSaldo;\r\n\r\n    for (const entry of list) {\r\n      cumulative += entry.daysAccrued;\r\n      const startOfMonth = Dates.startEnd(\"today\",\"start-month\");\r\n      data[0].push(entry.month <= startOfMonth ? cumulative : null);\r\n      data[1].push(entry.month >= startOfMonth ? cumulative : null);\r\n      labels.push(Translations.get(`SALAXY.ENUM.CalendarMonth.month${Dates.getMonth(entry.month)}.short`));\r\n    }\r\n    return {\r\n      type: \"line\",\r\n      data: {\r\n        labels,\r\n        datasets: [\r\n          {\r\n            label: Translations.get(\"SALAXY.NG1.HolidayYearAccrualComponent.accumulated\"),\r\n            data: [\r\n              ...data[0]\r\n            ],\r\n            borderColor: \"rgb(159,192,209)\",\r\n            fill: {\r\n              target: \"origin\",\r\n                above: \"rgb(234,241,245, 0.5)\"\r\n            },\r\n            elements: {\r\n              point: {\r\n                backgroundColor: \"rgb(234,241,245)\"\r\n              }\r\n            },\r\n          },\r\n          {\r\n            label: Translations.get(\"SALAXY.NG1.HolidayYearAccrualComponent.futureEstimate\"),\r\n            data: [\r\n              ...data[1]\r\n            ],\r\n            fill: {\r\n              target: \"origin\",\r\n                above: \"rgb(248,248,248, 0.5)\"\r\n            },\r\n            elements: {\r\n              point: {\r\n                backgroundColor: \"rgb(248,248,248)\"\r\n              }\r\n            },\r\n          }\r\n        ]\r\n      },\r\n      options: {\r\n        scales: {\r\n          y: {\r\n            ticks: {\r\n              beginAtZero: true,\r\n            },\r\n          },\r\n        },\r\n        plugins: {\r\n          legend: {\r\n            display: false\r\n          }\r\n        }\r\n      },\r\n    };\r\n  }\r\n  /** Gets the color for the row avatar */\r\n  public getRowColor(row: HolidayAccrualEntry | \"start\" | \"total\") {\r\n    if (row === \"start\" || row === \"total\") {\r\n      return Brand.getBrandColor(\"primary\");\r\n    }\r\n    if (row.month > this.getThisMonth()) {\r\n      return \"#ddd\";\r\n    }\r\n    if (row.month === this.getThisMonth()) {\r\n      return Brand.getBrandColor(\"danger\");\r\n    }\r\n    return Brand.getBrandColor(\"primary\");\r\n  }\r\n\r\n  /** Gets this month: The first date of this month */\r\n  public getThisMonth() {\r\n    return Dates.getToday().substr(0, 8) + \"01\";\r\n  }\r\n\r\n  /**\r\n   * Returns the notes if available or, if not, description text based on the source.\r\n   */\r\n  public getAccrualNotes(row: HolidayAccrualEntry) {\r\n    if (row.notes) {\r\n      return row.notes;\r\n    }\r\n    switch (row.source) {\r\n      case HolidayAccrualSource.Manual:\r\n        return Translations.get(\"SALAXY.NG1.HolidayYearAccrualComponent.holidayAccrualSource.manual\");\r\n      case HolidayAccrualSource.CalcDraft:\r\n        return Translations.get(\"SALAXY.NG1.HolidayYearAccrualComponent.holidayAccrualSource.calcDraft\");\r\n      case HolidayAccrualSource.CalcPaid:\r\n        return Translations.get(\"SALAXY.NG1.HolidayYearAccrualComponent.holidayAccrualSource.calcPaid\");\r\n      case HolidayAccrualSource.Initial:\r\n      default:\r\n        if (row.month === this.getThisMonth()) {\r\n          return Translations.get(\"SALAXY.NG1.HolidayYearAccrualComponent.holidayAccrualSource.defaultThisMonth\");\r\n        }\r\n        if (row.month > this.getThisMonth()) {\r\n          return Translations.get(\"SALAXY.NG1.HolidayYearAccrualComponent.holidayAccrualSource.defaultEstimate\");\r\n        }\r\n        return Translations.get(\"SALAXY.NG1.HolidayYearAccrualComponent.holidayAccrualSource.default\");\r\n    }\r\n  }\r\n\r\n  /** Gets calculations related to holiday accruals */\r\n  public getAccrualCalculations() {\r\n    const startSaldo: number = (this.parent.accrual as any).startSaldo;\r\n    const result = {\r\n      accrual: Arrays.sum(this.list, (x) => x.daysAccrued),\r\n      accrualToday: Arrays.sum(this.list.filter((x) => x.month < Dates.getToday()), (x) => x.daysAccrued),\r\n      total: 0,\r\n      totalToday: 0,\r\n    };\r\n    result.total = result.accrual + startSaldo;\r\n    result.totalToday = result.accrualToday + startSaldo;\r\n    return result;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {\r\n  Dates, HolidayCode, HolidaysLogic, HolidaySpecification, HolidaySpecificationForYear,\r\n  HolidayYear, HolidayYears, Translations, WageBasis, CalendarSeries,\r\n  InputEnumOption,\r\n  HolidayPayCalculation\r\n} from \"@salaxy/core\";\r\n\r\nimport { UiCrudHelpers, UiHelpers, SessionService } from \"../../services\";\r\nimport { ApiCrudObjectController } from \"../bases\";\r\n\r\n/**\r\n * Plain CRUD controller for HolidayYears.\r\n */\r\nexport class HolidayYearCrudController extends ApiCrudObjectController<HolidayYear, never> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"HolidayYears\",\r\n    \"UiHelpers\",\r\n    \"$location\",\r\n    \"$routeParams\",\r\n    \"UiCrudHelpers\",\r\n    \"SessionService\"\r\n  ];\r\n\r\n  /** View type currently shown in the UI */\r\n  public viewType: \"overview\" | \"parameters\" | \"accrual\" | \"holidays\" | \"absenses\" = \"overview\";\r\n\r\n  /**\r\n   * If employmentId is set, the controller fetches all the holiday years for this employment relation.\r\n   * The dafault of them will then be set to model and they can be switched easily e.g. using dropdown.\r\n   */\r\n  public employmentHolidayYears: HolidayYear[] = [];\r\n\r\n  /** If getHolidayYears() is called, the result will be here */\r\n  public allYears: HolidayYear[];\r\n\r\n  /**\r\n   * The date for which the UI is rendered. Default is today.\r\n   * For employment holiday years (WorkerHolidays or CalcWorktime), set this to salary period begin\r\n   * => Specifies the the holiday year to choose by default from all holiday years that Worker has:\r\n   * If the date is Jan-March will show the previous year, April-Dec will show the current year.\r\n   */\r\n  public forDate: string;\r\n\r\n  /** Parameters related to holiday report (lomalista). */\r\n  public reportParams: {\r\n    /** Today's date: Set this for testing how user interface is rendered (which view is presented) at different times of year. */\r\n    today: string;\r\n    /** Start date of the view: Can be get/set directly by the view */\r\n    start: string,\r\n    /** Start date of the view: Can be get/set directly by the view */\r\n    end: string,\r\n    /** Start date of the holiday year. Typically, just get: Set by the reportYear setter */\r\n    yearStart: string,\r\n    /** End date of the holiday year. Typically, just get: Set by the reportYear setter */\r\n    yearEnd: string,\r\n    /** Years that can be selected. */\r\n    years: number[];\r\n    /** Underlying field of reportView */\r\n    _view: \"summerPeriod\" | \"winterPeriod\" | \"otherPeriod\" | \"list\",\r\n    /** Underlying field of reportYear */\r\n    _year: number,\r\n  };\r\n\r\n  public isAccrualView = false;\r\n\r\n  private _employmentId: string;\r\n\r\n  private visualizationCache;\r\n  constructor(\r\n    private fullApi: HolidayYears,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    private uiCrudHelpers: UiCrudHelpers,\r\n    private sessionService: SessionService,\r\n\r\n  ) { // Dependency injection\r\n    super(fullApi, uiHelpers, $location, $routeParams);\r\n  }\r\n\r\n  /** Controller initialization */\r\n  public $onInit() {\r\n    this.forDate = this.forDate || Dates.getToday();\r\n    const thisYear = Dates.getYear(this.forDate);\r\n    this.reportParams = {\r\n      today: this.forDate,\r\n      years: Array.from({ length: 5 }, (v, ix) => thisYear + 1 - ix),\r\n    } as any;\r\n    // Fetching reportView initializes the rest of parameters with default values. Comment for lint if necessary.\r\n    // eslint-disable-next-line @typescript-eslint/no-unused-vars\r\n    const necessaryInitCall = this.reportView;\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"/workers\",\r\n      detailsUrl: this.detailsUrl || \"/workers/details/\",\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/Holidays.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Sets the employment ID and if it is different then starts the loading of the Absences object to that employment ID.\r\n   */\r\n  public set employmentId(value: string) {\r\n    if (this._employmentId === value) {\r\n      return;\r\n    }\r\n    this.employmentHolidayYears = [];\r\n    if (!value) {\r\n      if (this._employmentId) {\r\n        this._employmentId = null;\r\n        this.model = null;\r\n        this.reload();\r\n      }\r\n      return;\r\n    }\r\n    this._employmentId = value;\r\n    this.fullApi.getForEmployment(value).then((result) => {\r\n      this.employmentHolidayYears = result;\r\n      this.setYear();\r\n    });\r\n  }\r\n  /** Gets the employment ID */\r\n  public get employmentId() {\r\n    return this._employmentId;\r\n  }\r\n\r\n  /** Initializes the holidays for the current Worker */\r\n  public initHolidays(spec: HolidaySpecification,) {\r\n    const loader = this.uiHelpers.showLoading(Translations.get(\"SALAXY.NG1.HolidayYearComponent.dialog.creatingYearHolidays\"));\r\n    this.fullApi.initForEmployment(this.employmentId, spec)\r\n      .then((years) => {\r\n        this.employmentHolidayYears = years;\r\n        this.setYear();\r\n        loader.dismiss();\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Gets the holiday logic for the given specification.\r\n   * @param spec The specification for which the logic is calculated.\r\n   * @returns The logic object that can be used in the UI.\r\n   */\r\n  public getHolidayLogic(spec: HolidaySpecificationForYear) {\r\n    const logic =  {\r\n      /** If true, has holiday years => A warning for overwrite should be shown. */\r\n      hasData: !!this.current,\r\n      /** True if the accrual is based on law. Ui binds to this. */\r\n      accrualByLaw: !spec.accrualFixed,\r\n      /**\r\n       * Sets the accrualFixed value based on accrualByLaw value\r\n       * @param itemData The data that is being edited (current in view)\r\n       */\r\n      accrualByLawChanged: (itemData: HolidaySpecificationForYear) => {\r\n        itemData.accrualFixed = logic.accrualByLaw ? null : (itemData.code === HolidayCode.TemporaryTimeOff ? 2 : 2.5);\r\n      },\r\n      /**\r\n       * Sets the accrualByLaw value based on accrualFixed value\r\n       * @param itemData The data that is being edited (current in view)\r\n       */\r\n      accrualFixedChanged: (itemData: HolidaySpecificationForYear) => {\r\n        if (!itemData.accrualFixed) {\r\n          itemData.accrualFixed = null; // in case of empty string or 0.\r\n          logic.accrualByLaw = true;\r\n        }\r\n      },\r\n      /**\r\n       * Business logic for field visibility\r\n       * @param itemData The data that is being edited (current in view)\r\n       * @param field Name of the field for which the visibility is calculated.\r\n       */\r\n      getVisibility: (itemData: HolidaySpecificationForYear, field: \"accrualFixed\" | \"compensation\" | \"bonusMethod\" | \"bonusPercent\" | \"startSaldo\" | \"accruesHolidays\") => {\r\n        switch (field) {\r\n          case \"accruesHolidays\":\r\n          case \"startSaldo\":\r\n          case \"bonusMethod\":\r\n            return itemData.code === HolidayCode.Permanent14Days\r\n              || itemData.code === HolidayCode.Permanent35Hours\r\n              || itemData.code === HolidayCode.TemporaryTimeOff\r\n              || itemData.code === HolidayCode.Other\r\n              || itemData.code === HolidayCode.Script;\r\n          case \"accrualFixed\":\r\n            return itemData.code === HolidayCode.Permanent14Days\r\n            || itemData.code === HolidayCode.Permanent35Hours\r\n            || itemData.code === HolidayCode.TemporaryTimeOff;\r\n          case \"compensation\":\r\n            return itemData.code === HolidayCode.HolidayCompensation\r\n              || itemData.code === HolidayCode.HolidayCompensationIncluded\r\n              ;\r\n          case \"bonusPercent\":\r\n            return itemData.code === HolidayCode.Permanent14Days\r\n              || itemData.code === HolidayCode.Permanent35Hours\r\n              || itemData.code === HolidayCode.TemporaryTimeOff\r\n              || itemData.code === HolidayCode.Other\r\n              || itemData.code === HolidayCode.HolidayCompensation\r\n              || itemData.code === HolidayCode.HolidayCompensationIncluded\r\n              || itemData.code === HolidayCode.Script\r\n              ;\r\n          default:\r\n            return true;\r\n        }\r\n      },\r\n      getholidayPayCalculationOptions:(itemData: HolidaySpecificationForYear): InputEnumOption[] => {\r\n        return this.uiHelpers.cache(this, \"holidayPayCalculationOptions\", () => {\r\n          switch (itemData?.code) {\r\n            case HolidayCode.Permanent14Days:\r\n              if(itemData.wageBasis === WageBasis.Monthly) {\r\n                return [\r\n                  {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.normalMonthlyPay.label\"), value: HolidayPayCalculation.NormalMonthlyPay},\r\n                  {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.otherPay.label\"), value: HolidayPayCalculation.OtherPay},\r\n                  ...(this.sessionService.isInRole(\"bizConfigs\") ? [{text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.scriptPay.label\"), value: HolidayPayCalculation.ScriptPay}] : []),\r\n                ];\r\n              } else {\r\n                return [\r\n                  {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.averageHourlyPay.label\"), value: HolidayPayCalculation.AverageHourlyPay},\r\n                  {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.averageDailyPay.label\"), value: HolidayPayCalculation.AverageDailyPay},\r\n                  {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.otherPay.label\"), value: HolidayPayCalculation.OtherPay},\r\n                  ...(this.sessionService.isInRole(\"bizConfigs\") ? [{text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.scriptPay.label\"), value: HolidayPayCalculation.ScriptPay}] : []),\r\n                ];\r\n              }\r\n            case HolidayCode.Permanent35Hours:\r\n              if(itemData.wageBasis === WageBasis.Monthly) {\r\n                return [\r\n                  {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.normalMonthlyPay.label\"), value: HolidayPayCalculation.NormalMonthlyPay},\r\n                  {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.percentageBasedPay.label\"), value: HolidayPayCalculation.PercentageBasedPay},\r\n                  {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.otherPay.label\"), value: HolidayPayCalculation.OtherPay},\r\n                  ...(this.sessionService.isInRole(\"bizConfigs\") ? [{text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.scriptPay.label\"), value: HolidayPayCalculation.ScriptPay}] : []),\r\n                ];\r\n              } else {\r\n                return [\r\n                  {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.percentageBasedPay.label\"), value: HolidayPayCalculation.PercentageBasedPay},\r\n                  {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.otherPay.label\"), value: HolidayPayCalculation.OtherPay},\r\n                  ...(this.sessionService.isInRole(\"bizConfigs\") ? [{text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.scriptPay.label\"), value: HolidayPayCalculation.ScriptPay}] : []),\r\n                ];\r\n              }\r\n            case HolidayCode.TemporaryTimeOff:\r\n              return [\r\n                {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.holidayCompensation.label\"), value: HolidayPayCalculation.HolidayCompensation},\r\n                {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.otherPay.label\"), value: HolidayPayCalculation.OtherPay},\r\n                  ...(this.sessionService.isInRole(\"bizConfigs\") ? [{text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.scriptPay.label\"), value: HolidayPayCalculation.ScriptPay}] : []),\r\n              ];\r\n              break;\r\n            case HolidayCode.Other:\r\n            case HolidayCode.Script:\r\n                if(itemData.wageBasis === WageBasis.Monthly) {\r\n                  return [\r\n                    {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.normalMonthlyPay.label\"), value: HolidayPayCalculation.NormalMonthlyPay},\r\n                    {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.percentageBasedPay.label\"), value: HolidayPayCalculation.PercentageBasedPay},\r\n                    {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.holidayCompensation.label\"), value: HolidayPayCalculation.HolidayCompensation},\r\n                    {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.otherPay.label\"), value: HolidayPayCalculation.OtherPay},\r\n                  ...(this.sessionService.isInRole(\"bizConfigs\") ? [{text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.scriptPay.label\"), value: HolidayPayCalculation.ScriptPay}] : []),\r\n                  ];\r\n                } else {\r\n                  return [\r\n                    {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.averageHourlyPay.label\"), value: HolidayPayCalculation.AverageHourlyPay},\r\n                    {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.averageDailyPay.label\"), value: HolidayPayCalculation.AverageDailyPay},\r\n                    {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.percentageBasedPay.label\"), value: HolidayPayCalculation.PercentageBasedPay},\r\n                    {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.holidayCompensation.label\"), value: HolidayPayCalculation.HolidayCompensation},\r\n                    {text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.otherPay.label\"), value: HolidayPayCalculation.OtherPay},\r\n                  ...(this.sessionService.isInRole(\"bizConfigs\") ? [{text: Translations.get(\"SALAXY.ENUM.HolidayPayCalculation.scriptPay.label\"), value: HolidayPayCalculation.ScriptPay}] : []),\r\n                  ];\r\n                }\r\n            default:\r\n              return [];\r\n          }\r\n        });\r\n      }\r\n    };\r\n    return logic;\r\n  }\r\n\r\n  /** Shows the Init holidays dialog for initializing the holiday years for the given worker */\r\n  public showInitHolidays() {\r\n    if (!this.employmentId) {\r\n      throw Error(\"Employment ID not defined in showInitHolidays().\");\r\n    }\r\n    const loader = this.uiHelpers.showLoading(Translations.get(\"SALAXY.NG1.HolidayYearComponent.dialog.loadingDefaults\"));\r\n    this.fullApi.getDefaultSpecForEmployment(this.employmentId).then((defaults) => {\r\n\r\n      loader.dismiss();\r\n      const logic = this.getHolidayLogic(defaults);\r\n\r\n      this.uiHelpers.openEditDialog(\"salaxy-components/worker/holidays/WorkerHolidaysInitDialog.html\", defaults, logic, \"lg\")\r\n        .then((result) => {\r\n          if (result.action === \"ok\") {\r\n            this.initHolidays(result.item);\r\n          }\r\n        });\r\n    });\r\n  }\r\n\r\n  /** Gets the visualisation data for the selected holiday year. */\r\n  public getYearVisualisation() {\r\n    if (!this.current) {\r\n      return null;\r\n    }\r\n    if (!this.visualizationCache || this.visualizationCache.year !== this.current.year || this.visualizationCache.employmentId !== this.current.employmentId) {\r\n      this.visualizationCache = HolidaysLogic.getYearVisualisation(this.current);\r\n    }\r\n    return this.visualizationCache;\r\n  }\r\n\r\n  /** Gets a total days calculation for different types. */\r\n  public getTotalDays(type: \"all\" | \"summer\" | \"winter\" | \"holidaysSaldoEnd\" | \"holidaysSaldoStart\" = \"all\", year: HolidayYear = null) {\r\n    year = year || this.current;\r\n    return HolidaysLogic.getPlannedLeavesCount(year, type);\r\n  }\r\n\r\n  /**\r\n   * Gets items visibility based on properties of the selected holiday year.\r\n   * @param elements Logical name of group of items in teh view.\r\n   */\r\n  public getVisibility(elements: \"accrual\" | \"compensation\" | \"hourly\") {\r\n    const code = this.current.spec.code;\r\n    switch (elements) {\r\n      case \"accrual\":\r\n        return code === HolidayCode.Permanent14Days\r\n          || code === HolidayCode.Permanent35Hours\r\n          || code === HolidayCode.TemporaryTimeOff\r\n          || code === HolidayCode.Other\r\n          || code === HolidayCode.Script\r\n          ;\r\n      case \"hourly\":\r\n        return this.current.spec.wageBasis === WageBasis.Hourly\r\n          || this.current.spec.wageBasis === WageBasis.PerformanceBased\r\n          ;\r\n      case \"compensation\":\r\n        return code === HolidayCode.HolidayCompensation\r\n          || code === HolidayCode.HolidayCompensationIncluded\r\n          ;\r\n      default:\r\n        return true;\r\n    }\r\n  }\r\n\r\n  /** For the reporting purposes, gets or sets the holiday year as year number. */\r\n  public get reportYear(): number {\r\n    if (!this.reportParams._year) {\r\n      let year = Dates.getYear(this.reportParams.today || \"today\");\r\n      if (Dates.getMonth(this.reportParams.today || \"today\") < 3) {\r\n        year--;\r\n      }\r\n      this.reportYear = year; // Call the setter to init related values\r\n    }\r\n    return this.reportParams._year;\r\n  }\r\n  public set reportYear(value: number) {\r\n    value = Math.round(Number(value));\r\n    if (!value || value < 2018 || value > 2100) {\r\n      return;\r\n    }\r\n    this.reportParams._year = value;\r\n    if (this.reportView !== \"otherPeriod\") {\r\n      this.reportParams.yearStart = value + \"-01-01\";\r\n      this.reportParams.yearEnd = (value + 1) + \"-04-30\";\r\n    } else {\r\n      this.reportParams.yearStart = value + \"-05-01\";\r\n      this.reportParams.yearEnd = (value + 1) + \"-04-30\";\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Gets or sets the report view that is currently shown.\r\n   */\r\n  public get reportView(): \"summerPeriod\" | \"winterPeriod\" | \"otherPeriod\" | \"list\" {\r\n    if (!this.reportParams._view) {\r\n      // Use the setter for setting the defaault value so that dependent fields are also set\r\n      const month = Dates.getMonth(this.reportParams.today || \"today\");\r\n      const year = Dates.getYear(this.reportParams.today || \"today\");\r\n      if (year === this.reportYear) {\r\n        if (month < 10) { this.reportView = \"summerPeriod\"; }\r\n        else { this.reportView = \"winterPeriod\"; }\r\n      } else if (year - 1 === this.reportYear) {\r\n        if (month < 4) { this.reportView = \"winterPeriod\"; } // Current holidays\r\n        else { this.reportView = \"list\"; }\r\n      } else {\r\n        this.reportView = \"list\";\r\n      }\r\n    }\r\n    return this.reportParams._view;\r\n  }\r\n  public set reportView(value: \"summerPeriod\" | \"winterPeriod\" | \"otherPeriod\" | \"list\") {\r\n    this.reportParams._view = value;\r\n    switch (value) {\r\n      case \"summerPeriod\":\r\n        this.reportParams.start = this.reportYear + \"-05-01\";\r\n        this.reportParams.end = this.reportYear + \"-09-30\";\r\n        break;\r\n      case \"winterPeriod\":\r\n        this.reportParams.start = this.reportYear + \"-10-01\";\r\n        this.reportParams.end = this.reportYear + 1 + \"-04-30\";\r\n        break;\r\n      case \"otherPeriod\":\r\n        this.reportParams.start = this.reportYear + \"-01-01\";\r\n        this.reportParams.end = this.reportYear + 1 + \"-04-30\";\r\n        break;\r\n      default:\r\n        this.reportParams.start = this.reportParams.yearStart;\r\n        this.reportParams.end = this.reportParams.yearEnd;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Returns missing holiday year.\r\n   */\r\n  public get missingHolidayYear() {\r\n    if (!this.employmentHolidayYears || this.employmentHolidayYears.length == 0) {\r\n      // Not holiday years in use.\r\n      return null;\r\n    }\r\n    const today = Dates.getToday();\r\n    const missingYear = 1 + (Dates.getMonth(today) > 3 ? Dates.getYear(today) : Dates.getYear(today) - 1);\r\n    if (this.employmentHolidayYears.find((x) => x.year == missingYear)) {\r\n      return null;\r\n    }\r\n\r\n    return missingYear;\r\n  }\r\n\r\n  /**\r\n   * Saves a holiday year based on calendar input and updates the value in allYears property.\r\n   */\r\n  public saveYear(itemToSave: HolidayYear): Promise<void> {\r\n    const loader = this.uiHelpers.showLoading(`${Translations.get(\"SALAXY.NG1.HolidayYearComponent.dialog.saving\")}...`);\r\n    return this.api.save(itemToSave).then((savedValue) => {\r\n      angular.copy(savedValue, itemToSave);\r\n      loader.dismiss();\r\n      return;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Show an edit dialog for the holiday year.\r\n   * @param year The holiday year to update.\r\n   */\r\n  public showEditDialog(year: HolidayYear): void {\r\n    /* HACK: The edit dialog is not optimal, as it shows the entire edit worker dialog. Should be a separate edit holidays / holiday periods dialog. */\r\n    this.uiCrudHelpers.openEditEmploymentDialog(year.employmentId, \"default\", \"holidays\").then((result) => {\r\n      if (result.action === \"ok\") {\r\n        this.getHolidayYears(true);\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shows worker selection dialog and after that opens selected workers employment dialog.\r\n   */\r\n  public showAddWorker() {\r\n    const workerList = [];\r\n    this.uiHelpers.openEditDialog(\r\n      \"salaxy-components/modals/calc/WorkerSelect.html\",\r\n      workerList,\r\n      {\r\n        title: \"SALAXY.NG1.PayrollComponent.validate.addWorker\",\r\n      }).then((result) => {\r\n        if (result.action === \"ok\" && result.item.length == 1) {\r\n          this.uiCrudHelpers.openEditEmploymentDialog(result.item[0].id, \"default\", \"holidays\").then((result) => {\r\n            if (result.action === \"ok\") {\r\n              this.getHolidayYears(true);\r\n            }\r\n          });\r\n        }\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Gets the full holiday years for all Workers for reporting purposes\r\n   * @param keepView If true, does not reset the view based on the incoming data.\r\n   * If true, you should make sure the year does not change because then view will be invalid for the year\r\n   * I.e. should be true only for reload scenarios.\r\n   */\r\n  public getHolidayYears(keepView = false) {\r\n    this.fullApi.getForYear(this.reportYear).then((result: HolidayYear[]) => {\r\n      this.allYears = result;\r\n      if (!keepView) {\r\n        this.reportParams._view = null;\r\n        // eslint-disable-next-line @typescript-eslint/no-unused-vars\r\n        const getViewForInitAfterYearChange = this.reportView;\r\n      }\r\n    });\r\n  }\r\n\r\n  /** Maps an array of HolidayYear to calendar series. */\r\n  public mapToCalendar = (years: HolidayYear[]): CalendarSeries[] => {\r\n    return years.map((hy) => {\r\n      return {\r\n        key: hy.id,\r\n        title: hy.workerSnapshot.displayName,\r\n        description: `${Translations.get(\"SALAXY.NG1.HolidayYearComponent.planned\")} ${this.getTotalDays(\"all\", hy)}${Translations.get(\"SALAXY.NG1.HolidayYearComponent.date\")}, ${Translations.get(\"SALAXY.NG1.HolidayYearComponent.accumulation\")} ${hy.accrual.endSaldo}`,\r\n        avatar: hy.workerSnapshot,\r\n        data: hy,\r\n        events: hy.leaves.planned.map((leave) => ({\r\n          start: leave.period.start,\r\n          end: leave.period.end,\r\n          summary: leave.notes || `${Translations.get(\"SALAXY.NG1.HolidayYearComponent.holiday\")} ${leave.period.daysCount} ${Translations.get(\"SALAXY.NG1.HolidayYearComponent.days\")}`,\r\n          data: leave,\r\n        }\r\n        )),\r\n      };\r\n    });\r\n  };\r\n\r\n  /**\r\n   * Returns true, if two objects are different.\r\n   * @param obj1 First object to compare\r\n   * @param obj2 Second object to compare\r\n   */\r\n  public isChanged(obj1, obj2): boolean {\r\n    return !angular.equals(obj1, obj2);\r\n  }\r\n\r\n  /**\r\n   * Sets the view type for the holiday year.\r\n   * @param isAccrualView  If true, the view is set to this.currentYear +1, otherwise to this.currentYear.\r\n   */\r\n  public setAccrualView(isAccrualView: boolean): void {\r\n    this.isAccrualView = isAccrualView;\r\n  }\r\n\r\n  /**\r\n   * Sets the correct holiday year for the view based on the current date.\r\n   * This is for planning/consuming holidays.\r\n   */\r\n  public setYear(): void {\r\n    const date = this.forDate;\r\n    const holidayYear = date > Dates.getDate(Dates.getYear(date), 4, 30) ? Dates.getYear(date) : Dates.getYear(date) - 1;\r\n    this.model = this.employmentHolidayYears.find((x) => x.year === holidayYear) || this.employmentHolidayYears[0];\r\n  }\r\n\r\n  /** Recalculate holiday pay for the current holiday year */\r\n  public recalculateHolidayPay(): Promise<HolidayYear> {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    return this.fullApi.recalculateEmploymentHolidayPay(this.current.year, this.current.employmentId).then( () => {\r\n      loading.dismiss();\r\n      return this.reload();\r\n    });\r\n  }\r\n\r\n  /** Recalculate holiday pay for all employments in the holiday year */\r\n  public recalculateAllHolidayPay() {\r\n    return this.uiHelpers.showConfirm(\"Vuosiloma-ansion laskenta\",\r\n      `Haluatko varmasti laskea uudestaan vuosiloma-ansion kaikille työntekijöille lomavuodelle ${this.current.year}? Tämä voi kestää hetken.`).then( (result) => {\r\n        if (result) {\r\n          const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n          return this.fullApi.recalculateHolidayPay(this.current.year).then( () => {\r\n            loading.dismiss();\r\n            return this.uiHelpers.showAlert(\"Vuosiloma-ansion laskenta\", \"Vuosiloma-ansion laskenta on käynnistetty. Laskenta tapahtuu taustalla, ja se voi kestää jonkin aikaa.\");\r\n          });\r\n        }\r\n        else {\r\n          return result;\r\n        }\r\n      });\r\n  }\r\n}\r\n","import { AnnualLeave, Arrays, Dates, HolidaysLogic, HolidayYear } from \"@salaxy/core\";\r\n\r\nimport { EditDialogResult, UiHelpers } from \"../../services\";\r\n\r\nimport { ListControllerBase, ListControllerBaseBindings } from \"../bases\";\r\n\r\nclass HolidayYearHolidaysControllerBindings extends ListControllerBaseBindings {\r\n  /** If true, will format the table with class table-condensed. Later may add some other condensed formatting. */\r\n  public condensed = \"<\";\r\n\r\n  /** Date filter start value. Will be compared to period end date. */\r\n  public filterStart = \"<\";\r\n\r\n  /** Date filter end value. Will be compared to period start date. */\r\n  public filterEnd = \"<\";\r\n}\r\n\r\n/**\r\n * Controls the planned holidays list (lomakirjanpito / lomakalenteri) for a selected holiday year.\r\n */\r\nexport class HolidayYearHolidaysController  extends ListControllerBase<HolidayYear, AnnualLeave> {\r\n\r\n  /** Bindings for components that use this controller */\r\n  public static bindings = new HolidayYearHolidaysControllerBindings();\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"UiHelpers\"];\r\n\r\n  /** If true, will format the table with class table-condensed. Later may add some other condensed formatting. */\r\n  public condensed: boolean;\r\n\r\n  /** Date filter start value. Will be applied to period start dates. */\r\n  public filterStart: string;\r\n\r\n  /** Date filter end value. Will be applied to period end dates. */\r\n  public filterEnd: string;\r\n\r\n  constructor(uiHelpers: UiHelpers) {\r\n    super(uiHelpers);\r\n  }\r\n\r\n  /** List of items */\r\n  public get list(): AnnualLeave[] {\r\n    if (!this.parent || !this.parent.leaves || !this.parent.leaves.planned) {\r\n      return [];\r\n    }\r\n    return this.parent.leaves.planned;\r\n  }\r\n\r\n  /**\r\n   * Filter that is applied to the list when displayed.\r\n   * This is done in view: Does not apply to list property, but does affect getTotalDays().\r\n   * @param value Item in the list\r\n   */\r\n  public filter = (value: AnnualLeave) => {\r\n    if (this.filterEnd && value.period.start > this.filterEnd) {\r\n      return false;\r\n    }\r\n    if (this.filterStart && value.period.end < this.filterStart) {\r\n      return false;\r\n    }\r\n    return true;\r\n  };\r\n\r\n  /** Creating of a new item. */\r\n  public getBlank(): AnnualLeave {\r\n    return {\r\n      period: {\r\n        start: Dates.getToday(),\r\n        end: Dates.getToday(),\r\n        daysCount: 1,\r\n      },\r\n    };\r\n  }\r\n\r\n  /** Template for edit UI that is shown in a modal dialog. */\r\n  public getEditDialogTemplateUrl() {\r\n    return \"salaxy-components/worker/holidays/HolidayYearHolidaysEditDialog.html\";\r\n  }\r\n\r\n  /** Logic for edit dialog. */\r\n  public getEditDialogLogic() {\r\n    return {\r\n      /** Updates the workdays count */\r\n      updatePeriodDays: (current: AnnualLeave) => {\r\n        if (current.period.start > current.period.end) {\r\n          current.period.end = current.period.start;\r\n        }\r\n        if (current.period.start && current.period.end) {\r\n          if (current.period.days) {\r\n            current.period.days = Dates.getVacationDays(current.period.start, current.period.end);\r\n            current.period.daysCount = current.period.days.length;\r\n          } else {\r\n            current.period.daysCount = Dates.getVacationDays(current.period.start, current.period.end).length;\r\n          }\r\n        }\r\n      },\r\n\r\n      /** Sets the days array in period to enable days selection UI. */\r\n      setDaysSelection: (period: AnnualLeave) => {\r\n        period.period.days = Dates.getVacationDays(period.period.start, period.period.end);\r\n        period.period.daysCount = period.period.days.length;\r\n      },\r\n      /**\r\n       * For example, when parent year is 2024:\r\n       * - minDate is 2024-01-01\r\n       * - maxDate is 2025-04-30\r\n       */\r\n      minDate: Dates.getDate(this.parent.year, 1, 1),\r\n      maxDate: Dates.getDate(this.parent.year + 1, 4, 30)\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Shows the edit dialog.\r\n   * @param item Annual leave to edit or string \"new\" for creating a new one.\r\n   * @param isNew Optional way of specifying that the item is a new item (with default values, not yet added to the list).\r\n   * If item is string \"new\", this parameter will have no effect (will always be true).\r\n   */\r\n  public showEditDialog(item: AnnualLeave | \"new\", isNew = false) {\r\n    if (!item) {\r\n      throw new Error(\"showEditDialog called without a parameter.\");\r\n    }\r\n    if (item === \"new\") {\r\n      isNew = true;\r\n      item = this.getBlank();\r\n    }\r\n\r\n    const handleResult = (result: EditDialogResult<AnnualLeave>) => {\r\n      if (result.action === \"ok\" || result.action === \"ok-no-save\" ) {\r\n        if (isNew) {\r\n          this.list.push(result.item);\r\n        }\r\n        if (( isNew || result.hasChanges) && result.action !== \"ok-no-save\") {\r\n          this.commit();\r\n        }\r\n      } else if (result.action === \"delete\" || result.action === \"delete-no-save\") {\r\n        if (!isNew) {\r\n          this.delete(item as AnnualLeave);\r\n          if (result.action !== \"delete-no-save\" ) {\r\n            this.commit();\r\n          }\r\n        }\r\n      }\r\n    };\r\n\r\n    this.uiHelpers.openEditDialog(this.getEditDialogTemplateUrl(), item, this.getEditDialogLogic()).then((result) => {\r\n      /**\r\n       * parent is currently used holiday year\r\n       * Check if the holiday is outside the general holiday season (1.5.parent.year -30.4.parent.year + 1). Outside of general holiday season means 1.1.parent.year - 30.4.parent.year\r\n       */\r\n\r\n      if( (result.action === \"ok\" || result.action === \"ok-no-save\") && ( result.item.period.start >= Dates.getDate(this.parent.year,1,1) && result.item.period.end <= Dates.getDate(this.parent.year,4,30))) {\r\n        this.uiHelpers.showConfirm(\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidaysEditDialog.dialogHeading\", \"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidaysEditDialog.dialogText\")\r\n        .then((confirmResult: boolean) => {\r\n          if (confirmResult) {\r\n            handleResult(result);\r\n          }\r\n        });\r\n      } else {\r\n        handleResult(result);\r\n      }\r\n    });\r\n  }\r\n\r\n  /** Gets the description text for the planned holiday. */\r\n  public getDescription(row: AnnualLeave) {\r\n    if (row.notes) {\r\n      return row.notes;\r\n    }\r\n    return row.period.start < `${this.parent.year}-10-1` ? \"Kesäloma\" : \"Talviloma\";\r\n  }\r\n\r\n  /** Gets a total days calculation for different types. */\r\n  public getTotalDays(type: \"all\" | \"summer\" | \"winter\" | \"holidaysSaldoEnd\" | \"holidaysSaldoStart\" | \"filtered\" = \"all\") {\r\n    // HACK: jos periodi menee yli filterin tästä tulee väärä tulos (alku ennen filtterin alkua, loppu filtterin alun jälkeen).\r\n    if (type === \"filtered\") {\r\n      return Arrays.sum(this.list.filter((x) => this.filter(x)), (x) => x.period.daysCount);\r\n    }\r\n    if (this.parent) {\r\n      return HolidaysLogic.getPlannedLeavesCount(this.parent, type);\r\n    }\r\n    return null;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { AnnualLeavePayment, AnnualLeavePaymentKind, Dates, HolidaysLogic, HolidayYear, LegalEntityType, Avatar, HolidayCode, HolidayBonusPaymentMethod } from \"@salaxy/core\";\r\n\r\nimport { UiHelpers, ReportsService } from \"../../services\";\r\n\r\nimport { ListControllerBase, ListControllerBaseBindings } from \"../bases\";\r\n\r\ntype AnnualLeavePaymentWithAvatar = AnnualLeavePayment & { avatar: Avatar };\r\n/**\r\n * Controls the annual leave payments: HolidayCompensation, HolidayBonus and HolidaySalary.\r\n * These payments are typically fetched from paid calculations automatically,\r\n * but may also be marked paid manually. Also, in client-side logic, payments are fetched\r\n * optionally from Draft calculations.\r\n */\r\nexport class HolidayYearPaidController  extends ListControllerBase<HolidayYear, AnnualLeavePayment> {\r\n\r\n  /** Bindings for components that use this controller */\r\n  public static bindings = new ListControllerBaseBindings();\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"UiHelpers\",\r\n    \"ReportsService\"\r\n  ];\r\n\r\n  /** Total holiday pays */\r\n  public totals: {\r\n    /** Total calculation  */\r\n    total: AnnualLeavePayment,\r\n    /** Start saldo of the payments */\r\n    startSaldo: AnnualLeavePayment,\r\n\r\n    /** End saldo of the payments. */\r\n    endSaldo: AnnualLeavePayment,\r\n  };\r\n\r\n  /** Total bonus */\r\n  public bonusTotals: {\r\n    /** Total calculation  */\r\n    total: AnnualLeavePayment,\r\n    /** Start saldo of the payments */\r\n    startSaldo: AnnualLeavePayment,\r\n\r\n    /** End saldo of the payments. */\r\n    endSaldo: AnnualLeavePayment,\r\n  };\r\n\r\n  constructor(\r\n    uiHelpers: UiHelpers,\r\n    private reports: ReportsService,\r\n  ) {\r\n    super(uiHelpers);\r\n  }\r\n\r\n  /** Gets the worker ID for the current holiday year. */\r\n  public get workerId(): string {\r\n    if (!this.parent || !this.parent.workerSnapshot) {\r\n      return null;\r\n    }\r\n    return this.parent.workerSnapshot.id;\r\n  }\r\n\r\n  /** Gets the employment ID for the current holiday year. */\r\n  public get employmentId(): string {\r\n    if (!this.parent || !this.parent.workerSnapshot) {\r\n      return null;\r\n    }\r\n    return this.parent.employmentId;\r\n  }\r\n\r\n  /**\r\n   * List of items fetched from the holiday year,\r\n   * cached to the controller level, except when workerId changes.\r\n   */\r\n  public get list(): AnnualLeavePayment[] {\r\n    if (!this.parent || !this.parent.leaves || !this.parent.leaves.paid) {\r\n      return [];\r\n    }\r\n    return this.getLeavesPaid();\r\n  }\r\n\r\n  /**\r\n   * Returns true if the bonus should be paid for the employee.\r\n   */\r\n  public get shoudPayBonus(): boolean {\r\n    if (!this.parent?.spec) {\r\n      return false;\r\n    }\r\n\r\n    return ( this.parent.spec.code === HolidayCode.Permanent14Days\r\n          || this.parent.spec.code  === HolidayCode.Permanent35Hours\r\n          || this.parent.spec.code  === HolidayCode.TemporaryTimeOff\r\n          || this.parent.spec.code  === HolidayCode.Other\r\n          || this.parent.spec.code  === HolidayCode.Script\r\n    ) && this.parent.spec.bonusMethod !== HolidayBonusPaymentMethod.None;\r\n  }\r\n\r\n/**\r\n * List of paid holidays.\r\n */\r\n  private getLeavesPaid(): AnnualLeavePayment[] {\r\n      for (const paidLeave of this.parent.leaves.paid) {\r\n          (paidLeave as any).avatar ??= {};\r\n          if (paidLeave.holidayBonus > 0 && !(paidLeave.holidaySalary > 0 || paidLeave.holidayCompensation > 0)) {\r\n            angular.copy(HolidaysLogic.getPaidBonusAvatar(\"row\", paidLeave), (paidLeave as any).avatar);\r\n          }\r\n          else\r\n          {\r\n            angular.copy(HolidaysLogic.getPaidCalculationAvatar(\"row\", paidLeave), (paidLeave as any).avatar);\r\n          }\r\n      }\r\n\r\n      this.totals ??= {} as any;\r\n      this.totals.startSaldo = this.copyAnnualLeavePayment(HolidaysLogic.getPaidHolidaysCalculation(this.parent, \"startSaldo\"), this.totals.startSaldo);\r\n      this.totals.total = this.copyAnnualLeavePayment(HolidaysLogic.getPaidHolidaysCalculation(this.parent, \"total\"), this.totals.total);\r\n      this.totals.endSaldo = this.copyAnnualLeavePayment(HolidaysLogic.getPaidHolidaysCalculation(this.parent, \"endSaldo\"), this.totals.endSaldo);\r\n\r\n      this.bonusTotals ??= {} as any;\r\n      this.bonusTotals.startSaldo = this.copyAnnualLeavePayment(HolidaysLogic.getPaidBonusCalculation(this.parent, \"startSaldo\"), this.bonusTotals.startSaldo);\r\n      this.bonusTotals.total = this.copyAnnualLeavePayment(HolidaysLogic.getPaidBonusCalculation(this.parent, \"total\"), this.bonusTotals.total);\r\n      this.bonusTotals.endSaldo = this.copyAnnualLeavePayment(HolidaysLogic.getPaidBonusCalculation(this.parent, \"endSaldo\"), this.bonusTotals.endSaldo);\r\n      return this.parent.leaves.paid;\r\n  }\r\n\r\n  private copyAnnualLeavePayment(source: AnnualLeavePayment, target: AnnualLeavePayment):  AnnualLeavePayment{\r\n    target ??= {} as any;\r\n    (target as any).avatar ??= {} as any;\r\n\r\n    angular.copy((source as any).avatar, (target as any).avatar);\r\n    target.holidayBonus = source.holidayBonus;\r\n    target.holidayCompensation = source.holidayCompensation;\r\n    target.holidayDays = source.holidayDays;\r\n    target.holidaySalary = source.holidaySalary;\r\n\r\n    return target;\r\n  }\r\n\r\n  /** Creating of a new item. */\r\n  public getBlank(): AnnualLeavePaymentWithAvatar {\r\n    return {\r\n      kind: AnnualLeavePaymentKind.Undefined,\r\n      avatar: {\r\n        displayName: \"Käsin syötetty korjaus\",\r\n        description: null,\r\n        color: \"rgb(74, 146, 233)\",\r\n        initials: \"edit\",\r\n        entityType: LegalEntityType.Company,\r\n      },\r\n      date: Dates.getToday(),\r\n      period: Dates.getDateRange(Dates.getToday(), Dates.getToday()),\r\n      holidayBonus: null,\r\n      holidayCompensation: null,\r\n      holidayDays: null,\r\n      holidaySalary: null,\r\n    };\r\n  }\r\n\r\n  /** Gets calculations preview pdf url based on given id */\r\n  public getPdfUrl(calcId: string) {\r\n    return this.reports.getPdfUrlForCalc(\"salarySlip\", calcId, true);\r\n  }\r\n\r\n  /** Logic for edit dialog. */\r\n  public getEditDialogLogic() {\r\n    return {\r\n      /** Updates the workdays count */\r\n      updatePeriodDays: (current: AnnualLeavePayment) => {\r\n        if (current.period.start > current.period.end) {\r\n          current.period.end = current.period.start;\r\n        }\r\n        if (current.period.start && current.period.end) {\r\n          if (current.period.days) {\r\n            current.period.days = Dates.getVacationDays(current.period.start, current.period.end);\r\n            current.period.daysCount = current.period.days.length;\r\n          } else {\r\n            current.period.daysCount = Dates.getVacationDays(current.period.start, current.period.end).length;\r\n          }\r\n          current.holidayDays = current.period.daysCount;\r\n        }\r\n      },\r\n      updateDaysCount: (current: AnnualLeavePayment) => {\r\n        current.period.daysCount = current.holidayDays;\r\n      },\r\n      getPdfUrl: (calcId: string): string => this.getPdfUrl(calcId)\r\n    };\r\n  }\r\n\r\n  /** Template for edit UI that is shown in a modal dialog. */\r\n  public getEditDialogTemplateUrl() {\r\n    return \"salaxy-components/worker/holidays/HolidayYearPaidEditDialog.html\";\r\n  }\r\n}","import angular from \"angular\";\r\n\r\nimport { TaxCard2019Logic, Taxcard, TaxcardKind, Taxcards, WorkerCurrentTaxcards } from \"@salaxy/core\";\r\nimport { UiCrudHelpers, UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * Helps listing current account tax cards (latest and previous ones)\r\n * and also the employers that are using the latest taxcards.\r\n */\r\nexport class MyTaxcardsController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Taxcards\", \"UiCrudHelpers\", \"UiHelpers\"];\r\n\r\n  /** The data after it has been loaded. Null if nothing is loaded yet.  */\r\n  public current: WorkerCurrentTaxcards;\r\n\r\n  /** The current active tab. */\r\n  public currentTab: string;\r\n\r\n  /** Creates a new MyTaxcardsController */\r\n  constructor(\r\n    private taxcards: Taxcards,\r\n    private uiCrudHelpers: UiCrudHelpers,\r\n    private uiHelpers: UiHelpers,\r\n    ) {}\r\n\r\n  /** Initializes the controller. */\r\n  public $onInit = () => {\r\n    this.reload();\r\n  };\r\n\r\n  /** Reloads the data from the server. */\r\n  public reload() {\r\n    this.current = null;\r\n    this.taxcards.getMyTaxcards().then((result) => {\r\n      this.current = result;\r\n      if (this.current?.active) {\r\n        this.currentTab = \"calcs\";\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Removes a taxcard from the list and does a refresh.\r\n   * @param id Taxcard id.\r\n   */\r\n  public deleteTaxCard(id: string) {\r\n    this.taxcards.delete(id).then(() => {\r\n      this.reload();\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Sets the users automatic shared taxcard as ON or if already set refreshes the taxcard from tax authorities.\r\n   */\r\n  public setSharedAutoForSelf(): void {\r\n    if (this.current.active?.card.kind === TaxcardKind.Auto) {\r\n      this.uiCrudHelpers.refreshAutoTaxcard(this.current.active.id).then((_taxcards) => {\r\n        this.reload();\r\n      });\r\n    } else {\r\n      const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.WorkerDetailsComponent.taxCard.setSharedAutoForSelf.loadingTitle\", \"SALAXY.NG1.WorkerDetailsComponent.taxCard.setSharedAutoForSelf.loadingText\");\r\n      this.taxcards.setAuto(this.current.personalId).then((x) => {\r\n        if (x == null) {\r\n          loader.dismiss();\r\n          this.uiHelpers.showAlert(\"SALAXY.NG1.WorkerDetailsComponent.taxCard.setSharedAutoForSelf.alertTitle\", \"SALAXY.NG1.WorkerDetailsComponent.taxCard.setSharedAutoForSelf.alertTextAutoCard\");\r\n        } else {\r\n          this.reload();\r\n          loader.dismiss();\r\n        }\r\n      });\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Gets the chart type that should be shown.\r\n   */\r\n  public get chartType(): \"full\" | \"pie\" | \"none\" {\r\n    if (!this.current) {\r\n      return \"none\";\r\n    }\r\n    if (this.current.active.card.incomeLimit) {\r\n      return \"full\";\r\n    }\r\n    return \"pie\";\r\n  }\r\n\r\n  /**\r\n   * Gets main chart configuration for <salaxy-chart>\r\n   * @param taxcard current taxcard\r\n   */\r\n  public getMainChartConfig(taxcard: Taxcard) {\r\n    return this.uiHelpers.cache(this, \"mainChartConfig\",\r\n      () => TaxCard2019Logic.getMainChartV2(taxcard),\r\n      () => TaxCard2019Logic.getIncomeLimitInfo(taxcard));\r\n  }\r\n\r\n  /**\r\n   * Gets pie chart configuration for <salaxy-chart>\r\n   * @param taxcard current taxcard\r\n   */\r\n  public getPieChartConfig(taxcard: Taxcard) {\r\n    return this.uiHelpers.cache(this, \"pieChartConfig\",\r\n      () => TaxCard2019Logic.getPieChartDataV2(taxcard),\r\n      () => TaxCard2019Logic.getIncomeLimitInfo(taxcard));\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Dates, Taxcard, TaxCard2019Logic, TaxCardIncomeType, TaxcardKind, Translations } from \"@salaxy/core\";\r\n\r\nimport { SessionService } from \"../../services\";\r\n\r\n/**\r\n * UI logic for adding new manual taxcards.\r\n * Designed to be used in a modal dialog: You must pass personal ID for the Worker in EditDialogParameters.\r\n */\r\nexport class TaxcardManualEditController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"SessionService\"];\r\n\r\n  /** The current taxcard that is being edited. */\r\n  public current: Taxcard;\r\n\r\n  /** Edit taxcard form: Used for checking the validity. */\r\n  public editForm: angular.IFormController;\r\n\r\n  /**\r\n   * Today is explicitly defined, so that it can be changed in testing.\r\n   */\r\n  public today = Dates.getToday();\r\n\r\n  /** If true, shows the today edit box (in test only) */\r\n  public showToday = false;\r\n\r\n  /** Settings / instructions for the \"Create new\" UI (show/hide inputs, formatting etc). */\r\n  public addNewUi = {\r\n    /** If true, shown the 1st tax percent */\r\n    showTaxPercent: false,\r\n    /** If true, shown the income limit AND 2nd tax pecent. */\r\n    showIncomeLimit: false,\r\n    /** If true, the require the income limit AND 2nd tax percent (default yearly). */\r\n    requireIncomeLimit: false,\r\n    /** If true, shows input for previous salaries paid. */\r\n    showPreviousSalariesPaid: false,\r\n    /** If true, the tax percents etc. cannot be edited (no taxcard household or 60%).*/\r\n    readonly: false,\r\n    /** Options for the start date: currently min and max dates. */\r\n    startDateOptions: null as null | {\r\n      minDate: string,\r\n      maxDate: string,\r\n    },\r\n    /**\r\n     * Years that are allowed in the year selection:\r\n     * Current year + next year in December, previous year in January.\r\n     */\r\n    yearsAllowed: null as null | number[],\r\n  };\r\n\r\n  constructor(\r\n    private sessionService: SessionService,\r\n  ) {\r\n    // Dependency injection\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    if (this.sessionService.isInRole(\"company\")) {\r\n      delete this.taxcardKindOptions.noWithholdingHousehold;\r\n    }\r\n  }\r\n\r\n  /** Returns true if one of the edit forms is shown ad if it is valid. */\r\n  public get isFormValid() {\r\n    return this.editForm?.$valid && (this.current?.card?.kind || \"undefined\") != \"undefined\";\r\n  }\r\n\r\n  /**\r\n   * Gets a row for data binding of external salaries paid outside Salaxy system.\r\n   * Will create the row if it does not exist. The save method will remove any empty rows.\r\n   */\r\n  public get previousSalariesRow() {\r\n    if (!this.current) {\r\n      return null;\r\n    }\r\n    if (!this.current.incomeLog) {\r\n      this.current.incomeLog = [];\r\n    }\r\n    if (!this.current.incomeLog.find((x) => x.type === TaxCardIncomeType.ExternalSalaries)) {\r\n      this.current.incomeLog.push({\r\n        type: TaxCardIncomeType.ExternalSalaries,\r\n        id: null,\r\n        description: Translations.get(\"SALAXY.NG1.CurrentTaxCardComponent.previousSalariesRow\"),\r\n        startDate: this.today,\r\n        endDate: this.today,\r\n        income: null,\r\n        tax: null,\r\n      });\r\n    }\r\n    return this.current.incomeLog.find((x) => x.type === TaxCardIncomeType.ExternalSalaries);\r\n  }\r\n\r\n  /** Taxcard kinds that should be allowed for the new manual taxcard. */\r\n  public taxcardKindOptions = {\r\n    \"defaultYearly\": \"SALAXY.NG1.CurrentTaxCardComponent.taxcardKindOptions.defaultYearly\",\r\n    \"replacement\": \"SALAXY.NG1.CurrentTaxCardComponent.taxcardKindOptions.replacement\",\r\n    \"noTaxCard\": \"SALAXY.NG1.CurrentTaxCardComponent.taxcardKindOptions.noTaxCard\",\r\n    // This is removed from company role in init (only for household employers).\r\n    \"noWithholdingHousehold\": \"SALAXY.NG1.CurrentTaxCardComponent.taxcardKindOptions.noWithholdingHousehold\",\r\n  };\r\n\r\n  /**\r\n   * Resets the current taxcard as new (when the kind changes).\r\n   * @param kind If specified, reset the taxcard to the given type.\r\n   */\r\n  public resetAsNew(kind?: TaxcardKind) {\r\n    this.setCurrent(TaxCard2019Logic.getBlank(this.current.card.personalId, kind, null, this.today));\r\n    this.updateUISettings();\r\n  }\r\n\r\n  /** Handles change of the year in the years dropdown. */\r\n  public yearChanged() {\r\n    this.setCurrent(TaxCard2019Logic.getBlank(this.current.card.personalId, this.current.card.kind, this.current.card.forYear, this.today));\r\n    this.updateUISettings();\r\n  }\r\n\r\n  /** Sets the current item value keeping the original reference. */\r\n  private setCurrent(newItem: Taxcard) {\r\n    angular.copy(newItem, this.current);\r\n    this.updateUISettings();\r\n  }\r\n\r\n  /** Defines which fields to show/hide, require etc. in the view */\r\n  private updateUISettings() {\r\n    const settings = {\r\n      showTaxPercent: false,\r\n      showIncomeLimit: false,\r\n      requireIncomeLimit: false,\r\n      showPreviousSalariesPaid: false,\r\n      readonly: false,\r\n      startDateOptions: null,\r\n      yearsAllowed: null,\r\n    };\r\n    if (!this.current) {\r\n      this.addNewUi = settings;\r\n      return;\r\n    }\r\n    const todayYear = Dates.getYear(this.today);\r\n    const month = Dates.getMonth(this.today);\r\n    let yearsAllowed: number[];\r\n    if (month === 1) {\r\n      yearsAllowed = [todayYear, todayYear - 1];\r\n    } else if (month === 12) {\r\n      yearsAllowed = [todayYear, todayYear + 1];\r\n    } else {\r\n      yearsAllowed = [todayYear];\r\n    }\r\n    if (yearsAllowed.indexOf(this.current.card.forYear) < 0) {\r\n      if (!this.current.id) {\r\n        this.current.card.forYear = todayYear;\r\n      }\r\n    }\r\n    const forYear = this.current.card.forYear;\r\n    yearsAllowed = yearsAllowed.length < 2 ? null : yearsAllowed; // In the UI, the selection is not shown if there is only one item to select.\r\n    settings.showTaxPercent = true;\r\n\r\n    switch (this.current.card.kind) {\r\n      case TaxcardKind.Auto:\r\n        settings.showTaxPercent = false;\r\n        break;\r\n      case TaxcardKind.NoTaxCard:\r\n      case TaxcardKind.NoWithholdingHousehold:\r\n        settings.readonly = true;\r\n        break;\r\n      case TaxcardKind.Undefined:\r\n        settings.readonly = true;\r\n        settings.showTaxPercent = false;\r\n        break;\r\n      case TaxcardKind.DefaultYearly:\r\n        settings.showIncomeLimit = true;\r\n        settings.showPreviousSalariesPaid = true;\r\n        settings.requireIncomeLimit = true;\r\n        settings.yearsAllowed = yearsAllowed;\r\n        break;\r\n      case TaxcardKind.Replacement:\r\n        settings.showIncomeLimit = true;\r\n        settings.showPreviousSalariesPaid = true;\r\n        settings.yearsAllowed = yearsAllowed;\r\n        settings.startDateOptions = {\r\n            minDate: Dates.asJSDate(forYear + \"-01-01\"),\r\n            maxDate: Dates.asJSDate(forYear + \"-11-31\"),\r\n          };\r\n        break;\r\n    }\r\n    this.addNewUi = settings;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Dates, EmploymentRelationTaxcard, IUserObjectIndex, PersonAccount, Taxcard, TaxCard2019Logic, TaxCardIncomeType, TaxcardKind, TaxcardListItem, Taxcards, Translations } from \"@salaxy/core\";\r\n\r\nimport { EditDialogKnownActions, SessionService, UiCrudHelpers, UiHelpers, UploadService } from \"../../services\";\r\nimport { ApiCrudObjectController } from \"../bases\";\r\n\r\n/**\r\n * UI logic for viewing, adding new and editing taxcards.\r\n * You can edit a single taxcard (model to object, id or parent controller).\r\n * Note that creating a new taxcards requires setting Personal ID.\r\n * You can create a new one by setting the model as \"new\" (full add new UI) as well as null (quick buttons).\r\n */\r\nexport class TaxcardCrudController extends ApiCrudObjectController<Taxcard, TaxcardListItem> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"Taxcards\",\r\n    \"UiHelpers\",\r\n    \"UiCrudHelpers\",\r\n    \"$location\",\r\n    \"$routeParams\",\r\n    \"UploadService\",\r\n    \"SessionService\",\r\n    \"$timeout\",\r\n  ];\r\n\r\n  /** Mode is either \"pro\" (for admin / PRO-ui) or \"default\" */\r\n  public mode: \"pro\" | \"default\";\r\n\r\n  /**\r\n   * True if the taxcard is uploaded for the current Worker account (as opposed to Worker of an Employer) .\r\n   * This should typically not be set: It will be set by init (if current account is Worker) and personalId (if 'self' or personal id matches).\r\n   */\r\n  public isSelf: boolean;\r\n\r\n  /** The upload progress 0-100 */\r\n  public uploadProgress: number = null;\r\n\r\n  /** Edit taxcard form: Used for checking the validity. */\r\n  public editForm: angular.IFormController;\r\n\r\n  /**\r\n   * Today is explicitly defined, so that it can be changed in testing.\r\n   */\r\n  public today = Dates.getToday();\r\n\r\n  /** Settings / instructions for the \"Create new\" UI (show/hide inputs, formatting etc). */\r\n  public addNewUi: any;\r\n\r\n  /** If true, does not show the save / current buttons - the parent must show them. */\r\n  public hideButtons: boolean;\r\n\r\n  /** Type of employment taxcard */\r\n  public employmentRelationTaxcardType: EmploymentRelationTaxcard = EmploymentRelationTaxcard.Auto;\r\n\r\n  /** Possible taxcard kinds that should be available for current role to select. */\r\n  public kindSelection: string;\r\n\r\n  /**\r\n   * Event that is called when a taxcard is saved and the parent UI probably needs to be refreshed.\r\n   * @example <salaxy-taxcard-details model=\"$ctrl.current.active\" personal-id=\"$ctrl.current.personalId\" on-save=\"$ctrl.reload()\"></salaxy-taxcard-details>\r\n   */\r\n  public onSave: (eventData: {\r\n    /** The selected item. */\r\n    item: Taxcard,\r\n  }) => void;\r\n\r\n  /** Flags to indicate if the request is in progress */\r\n  public loaders:any = {};\r\n\r\n  private _personalId: string | \"self\";\r\n\r\n  private currentChartConfig: any = {};\r\n\r\n  constructor(\r\n    private fullApi: Taxcards,\r\n    uiHelpers: UiHelpers,\r\n    private uiCrudHelpers: UiCrudHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    private uploadService: UploadService,\r\n    private sessionService: SessionService,\r\n    private $timeout: angular.ITimeoutService,\r\n  ) { // Dependency injection\r\n    super(fullApi, uiHelpers, $location, $routeParams);\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    this.mode = this.mode || \"default\";\r\n    if (this.sessionService.isInRole(\"worker\")) {\r\n      // Just as a backup, this component should not be used for role worker any more.\r\n      this.isSelf = true;\r\n    }\r\n    if (this.sessionService.isInRole(\"company\")) {\r\n      delete this.taxcardKindOptions.noWithholdingHousehold;\r\n      delete this.taxcardKindOptionsV2.noWithholdingHousehold;\r\n    }\r\n    if (this.sessionService.isInRole(\"person\")) {\r\n      // Now, enabled for person\r\n      if (this.current?.card.kind === TaxcardKind.Undefined) {\r\n        this.current.card.kind = TaxcardKind.Auto;\r\n      }\r\n    } else {\r\n      if (this.current?.card.kind === TaxcardKind.Undefined) {\r\n        this.current.card.kind = TaxcardKind.Auto;\r\n      }\r\n    }\r\n    super.$onInit();\r\n  }\r\n\r\n  /**\r\n   * Either a valid Finnish Personal ID or \"self\" for the current Worker account.\r\n   * Required for creating a new taxcard: The personal ID is used for setting the connection to Worker account or self.\r\n   * The personal id is used when binding is null (buttons for create new) or \"new\" (actual new UI).\r\n   */\r\n  public get personalId(): string | \"self\" {\r\n    return this._personalId;\r\n  }\r\n  public set personalId(value: string | \"self\") {\r\n    if (!value) {\r\n      this._personalId = null;\r\n      return;\r\n    }\r\n    if (value === \"self\") {\r\n      if (!this.sessionService.isInRole(\"worker\")) {\r\n        throw new Error(\"Cannot bind taxcard to 'self' for Account that is not a Worker.\");\r\n      }\r\n      this._personalId = (this.sessionService.getCurrentAccount() as PersonAccount).identity.officialId;\r\n      this.isSelf = true;\r\n    } else {\r\n      this._personalId = value;\r\n      if ((this.sessionService.getCurrentAccount() as PersonAccount).identity.officialId === value) {\r\n        this.isSelf = true;\r\n      }\r\n    }\r\n    if (value && this.bindingMode === \"new\") {\r\n      this.reload();\r\n    }\r\n  }\r\n\r\n  /** Returns true if one of the edit forms is shown ad if it is valid. */\r\n  public get isFormValid() {\r\n    return this.editForm && this.editForm.$valid;\r\n  }\r\n\r\n  /**\r\n   * Gets the chart type that should be shown.\r\n   * Type \"preview\" means no chart: Only show the preview image of the card.\r\n   */\r\n  public get chartType(): \"preview\" | \"full\" | \"pie\" | \"none\" {\r\n    if (!this.current) {\r\n      return \"none\";\r\n    }\r\n    if (this.current.card.incomeLimit) {\r\n      return \"full\";\r\n    }\r\n    return \"pie\";\r\n  }\r\n\r\n  /**\r\n   * Gets a row for data binding of external salaries paid outside Salaxy system.\r\n   * Will create the row if it does not exist. The save method will remove any empty rows.\r\n   */\r\n  public get previousSalariesRow() {\r\n    if (!this.current) {\r\n      return null;\r\n    }\r\n    if (!this.current.incomeLog) {\r\n      this.current.incomeLog = [];\r\n    }\r\n    if (!this.current.incomeLog.find((x) => x.type === TaxCardIncomeType.ExternalSalaries)) {\r\n      this.current.incomeLog.push({\r\n        type: TaxCardIncomeType.ExternalSalaries,\r\n        id: null,\r\n        description: Translations.get(\"SALAXY.NG1.CurrentTaxCardComponent.previousSalariesRow\"),\r\n        startDate: this.today,\r\n        endDate: this.today,\r\n        income: null,\r\n        tax: null,\r\n      });\r\n    }\r\n    return this.current.incomeLog.find((x) => x.type === TaxCardIncomeType.ExternalSalaries);\r\n  }\r\n\r\n  /**\r\n   * Starts the reload process depending on the bindingMode:\r\n   */\r\n  public reload(): Promise<Taxcard> {\r\n    if (this.bindingMode === \"new\") {\r\n      this.setCurrentRef(TaxCard2019Logic.getBlank(this.personalId));\r\n      this._currentId = null;\r\n      this.setStatus(null);\r\n      this.updateUISettings();\r\n      return Promise.resolve(this.current);\r\n    }\r\n    return super.reload().then((result) => {\r\n      // TODO: Go through this at the source: Could we assure UI updating in parent controller.\r\n      this.$timeout(() => {\r\n        this.updateUISettings();\r\n      } );\r\n      return result;\r\n    });\r\n  }\r\n\r\n  /** Gets the user interface mode: The UI view that is shown by the component. */\r\n  public getMode(): \"pro\" | \"new\" | \"default\" | \"null\" | \"no-personal-id\" {\r\n    if (this.bindingMode === \"null\") {\r\n      return this.personalId ? \"null\" : \"no-personal-id\";\r\n    }\r\n    if (this.isNew()) {\r\n      return this.personalId ? \"new\" : \"no-personal-id\";\r\n    }\r\n    if (this.mode === \"pro\") {\r\n      return this.mode;\r\n    }\r\n    return \"default\";\r\n  }\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"/taxcards\",\r\n      detailsUrl: this.detailsUrl || null,\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/Taxcards.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Shows the detail view for the item.\r\n   * Typically, this takes the user to a new page with the ID.\r\n   * @param item Item may be either Container or list item.\r\n   */\r\n  public showDetails(item: Taxcard | IUserObjectIndex | TaxcardListItem): angular.ILocationService {\r\n    if (this.parentController) {\r\n      return this.parentController.showDetails(item);\r\n    }\r\n    if (!this.getDefaults().detailsUrl) {\r\n      if ((item as TaxcardListItem).data.employmentId) {\r\n        return this.$location.url(\"/employments/details/\" + (item as TaxcardListItem).data.employmentId + \"?tab=taxcards\");\r\n      } else if ((item as IUserObjectIndex).otherId) {\r\n        return this.$location.url(\"/employment/details/\" + (item as IUserObjectIndex).id + \"?tab=taxcards\");\r\n      } else if ((item as Taxcard).worker && (item as Taxcard).worker.id) {\r\n        return this.$location.url(\"/employment/details/\" + (item as Taxcard).employmentId + \"?tab=taxcards\");\r\n      } else {\r\n        return this.$location.url(\"/taxcards/details/\" + item.id);\r\n      }\r\n    }\r\n    return this.$location.url(this.getDefaults().detailsUrl + this.getId(item));\r\n  }\r\n\r\n  /** Save changes to the current item and then calls the on-save event. */\r\n  public save(): Promise<Taxcard> {\r\n    return super.save().then((savedCard) => {\r\n      if (!savedCard) {\r\n        throw new Error(\"Taxcard saving failed (api returns null): this should only occur with automatic taxcards, and only in adding (this controller is not designed for adding a new taxcard).\");\r\n      }\r\n      if (this.onSave) {\r\n        this.onSave({ item: savedCard });\r\n      }\r\n      return savedCard;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Saves the taxcard and checks the diff after save:\r\n   * If there are paid calculations that should be added to the taxcards, shows a dialog for that.\r\n   */\r\n  public saveCheckDiff(): Promise<Taxcard> {\r\n    return this.save().then((savedTaxcard) => {\r\n      if (savedTaxcard.incomeLog.find((x) => x.diff && x.diff !== \"default\")) {\r\n        return this.uiHelpers.openEditDialog(\"salaxy-components/modals/worker/taxcard-income-log.html\", savedTaxcard, { }, \"lg\")\r\n          .then((incomeLogResult) => {\r\n            if (incomeLogResult.action === \"ok\") {\r\n              const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.CurrentTaxCardComponent.saveCheckDiffSaving\");\r\n              this.fullApi.commitDiff(savedTaxcard).then((commitResult) => {\r\n                loader.dismiss();\r\n                return commitResult;\r\n              });\r\n            } else {\r\n              return savedTaxcard;\r\n            }\r\n          });\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Starts the \"Add new\" process for the tax card.\r\n   * By default we do not allow modifying taxcards to the end-user (only allowed for PRO-users).\r\n   * Instead, they will always add a new taxcard.\r\n   * Note: This method breaks the existing model binding of the controller and binds model=\"'new'\".\r\n   */\r\n  public showAddNew() {\r\n    if (!this.personalId) {\r\n      if (!this.current.card.personalId) {\r\n        throw new Error(\"No personal ID: Cannot add new card.\");\r\n      }\r\n      this.personalId = this.current.card.personalId;\r\n    }\r\n    this.loaders[\"showAddNew\"] = true;\r\n    this.uiCrudHelpers.createNewTaxcard(this.personalId).then((result) => {\r\n      if (result.action === \"ok\") {\r\n        if (this.bindingMode === \"url\") {\r\n          this.showDetails(result.item);\r\n        } else {\r\n          this.reload();\r\n          if (this.onSave) {\r\n            this.onSave({ item: result.item });\r\n          }\r\n        }\r\n      }\r\n      this.loaders[\"showAddNew\"] = false;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Sets auto taxcard and saves it\r\n   */\r\n  public async setAuto() {\r\n    if (!this.personalId) {\r\n      if (!this.current.card.personalId) {\r\n        throw new Error(\"No personal ID: Cannot add new card.\");\r\n      }\r\n      this.personalId = this.current.card.personalId;\r\n    }\r\n    this.loaders[\"showSetAuto\"] = true;\r\n    const loader = this.uiHelpers.showLoading(\"SALAXY.NG1.WorkerDetailsComponent.taxCard.setSharedAutoForSelf.loadingTitle\", \"SALAXY.NG1.WorkerDetailsComponent.taxCard.setSharedAutoForSelf.loadingText\");\r\n    const taxcard = await this.fullApi.setAuto(this.personalId);\r\n    if (taxcard == null) {\r\n      this.uiHelpers.showAlert(\"SALAXY.NG1.WorkerDetailsComponent.taxCard.setSharedAutoForSelf.alertTitle\", \"SALAXY.NG1.WorkerDetailsComponent.taxCard.setSharedAutoForSelf.alertTextAutoCard\");\r\n    } else {\r\n      if (this.onSave) {\r\n        this.onSave({ item: taxcard });\r\n      }\r\n    }\r\n    loader.dismiss();\r\n    this.loaders[\"showSetAuto\"] = false;\r\n  }\r\n\r\n  /** Shows the user interface for editing the minimum percent. */\r\n  public editTaxPercentMin() {\r\n    this.uiHelpers.openEditDialog(\"salaxy-components/modals/worker/taxcard-min-percent.html\", {\r\n      taxPercentMin: this.current.card.taxPercentMin,\r\n    }, {}).then((result) => {\r\n      if (result.action == EditDialogKnownActions.Ok) {\r\n        (this.current.card as any).taxPercentMinOwned = result.item.taxPercentMin || null;\r\n        this.current.card.taxPercentMin = result.item.taxPercentMin || null;\r\n        this.save();\r\n      }\r\n    });\r\n  }\r\n  public taxcardKindOptions = {\r\n    \"auto\": \"SALAXY.NG1.CurrentTaxCardComponent.taxcardKindOptions.auto\",\r\n    \"defaultYearly\": \"SALAXY.NG1.CurrentTaxCardComponent.taxcardKindOptions.defaultYearly\",\r\n    \"replacement\": \"SALAXY.NG1.CurrentTaxCardComponent.taxcardKindOptions.replacement\",\r\n    \"noTaxCard\": \"SALAXY.NG1.CurrentTaxCardComponent.taxcardKindOptions.noTaxCard\",\r\n    \"noWithholdingHousehold\": \"SALAXY.NG1.CurrentTaxCardComponent.taxcardKindOptions.noWithholdingHousehold\",\r\n  };\r\n\r\n  public taxcardKindOptionsV2 = {\r\n    \"defaultYearly\": \"SALAXY.NG1.CurrentTaxCardComponent.taxcardKindOptions.defaultYearly\",\r\n    \"replacement\": \"SALAXY.NG1.CurrentTaxCardComponent.taxcardKindOptions.replacement\",\r\n    \"noTaxCard\": \"SALAXY.NG1.CurrentTaxCardComponent.taxcardKindOptions.noTaxCard\",\r\n    \"noWithholdingHousehold\": \"SALAXY.NG1.CurrentTaxCardComponent.taxcardKindOptions.noWithholdingHousehold\",\r\n  };\r\n\r\n  /** Edit income log. */\r\n  public editIncomeLog() {\r\n    this.uiHelpers.openEditDialog(\"salaxy-components/modals/worker/taxcard-income-log.html\", this.current,\r\n    { editable: true }, \"lg\").then((result) => {\r\n      if (result.action === EditDialogKnownActions.Ok) {\r\n        this.save();\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Resets the current taxcard as new.\r\n   * @param kind If specified, reset the taxcard to the given type.\r\n   */\r\n  public resetAsNew(kind?: TaxcardKind) {\r\n    this.setCurrentValue(TaxCard2019Logic.getBlank(this.personalId, kind, null, this.today));\r\n    this.updateUISettings();\r\n  }\r\n\r\n  /** Handles change of the year in the years dropdown. */\r\n  public yearChanged() {\r\n    this.setCurrentValue(TaxCard2019Logic.getBlank(this.personalId, this.current.card.kind, this.current.card.forYear, this.today));\r\n    this.updateUISettings();\r\n  }\r\n\r\n  /**\r\n   * Returns the url where to download the tax card\r\n   * @param taxCard Taxcard or if null, the current is used.\r\n   */\r\n  public getTaxcardDownloadUrl(taxCard?: Taxcard): string {\r\n    taxCard = taxCard || this.current;\r\n    return this.fullApi.getDownloadUrl(taxCard);\r\n  }\r\n\r\n  /**\r\n   * Returns the url where to preview the tax card\r\n   * @param taxCard Taxcard or if null, the current is used.\r\n   */\r\n  public getTaxcardPreviewUrl(taxCard?: Taxcard): string {\r\n    taxCard = taxCard || this.current;\r\n    return this.fullApi.getPreviewUrl(taxCard);\r\n  }\r\n\r\n  /**\r\n   * Returns the url where to preview the tax card in upload scenario.\r\n   * When uploading (adding a new taxcard) the taxcard is not necessarily saved so the preview cannot be fetched based on taxcard id.\r\n   * On the other hand we are always in current user context (current user is the file owner), so we can use previewUri directly\r\n   * @param taxCard Taxcard or if null, the current is used.\r\n   */\r\n  public getUploadPreviewUrl(taxCard?: Taxcard): string {\r\n    taxCard = taxCard || this.current;\r\n    if (!taxCard || !taxCard.card.previewUri) {\r\n      return null;\r\n    }\r\n    return this.uploadService.getPreviewUrl(taxCard.card.previewUri);\r\n  }\r\n\r\n  /**\r\n   * Uploads tax card to the server.\r\n   * @param file - selected file\r\n   */\r\n  public uploadTaxCard(file: any) {\r\n    this.uploadProgress = null;\r\n    if (!file) {\r\n      return;\r\n    }\r\n    this.uploadService.upload<Taxcard>(this.fullApi.getUploadUrl(), { file }, (progress, error) => {\r\n      this.uploadProgress = progress;\r\n    }).then(\r\n      (resp) => {\r\n        this.uploadProgress = null;\r\n        this.current.card.fileUri = resp.card.fileUri;\r\n        this.current.card.previewUri = resp.card.previewUri;\r\n      }).catch((response) => {\r\n        this.uiHelpers.showAlert(\"SALAXY.UI_Terms.error\", \"SALAXY.NG1.CurrentTaxCardComponent.uploadTaxCardAlertDescr\");\r\n        throw new Error(response);\r\n      });\r\n  }\r\n\r\n  /**\r\n   * Gets main chart configuration for <salaxy-chart>\r\n   * @param taxcard current taxcard\r\n   */\r\n  public getMainChartConfig(taxcard: Taxcard) {\r\n    return this.uiHelpers.cache(this, \"mainChartConfig\",\r\n      () => TaxCard2019Logic.getMainChartV2(taxcard),\r\n      () => TaxCard2019Logic.getIncomeLimitInfo(taxcard));\r\n  }\r\n\r\n  /**\r\n   * Gets pie chart configuration for <salaxy-chart>\r\n   * @param taxcard current taxcard\r\n   */\r\n  public getPieChartConfig(taxcard: Taxcard) {\r\n    return this.uiHelpers.cache(this, \"pieChartConfig\",\r\n      () => TaxCard2019Logic.getPieChartDataV2(taxcard),\r\n      () => TaxCard2019Logic.getIncomeLimitInfo(taxcard));\r\n  }\r\n  /**\r\n   * Checks if the tax card is expired\r\n   * A tax card still valid in the next year's January\r\n   */\r\n  public isTaxCardExpired(taxCard: Taxcard): boolean {\r\n    return !TaxCard2019Logic.isTaxcardValid(taxCard, this.today);\r\n  }\r\n\r\n  /**\r\n   * Gets a language versioned error description ng-file-upload invalidFile errors (client-side before actual upload).\r\n   * @param invalidFile Invalid file of ng-file-upload component.\r\n   */\r\n  public getInvalidFileDescription(invalidFile) {\r\n    return this.uploadService.getInvalidFileDescription(invalidFile);\r\n  }\r\n\r\n  /**\r\n   * Adds a new taxcard for list item and after adding updates the current list without going to server.\r\n   * This is needed because refreshing of the list may not provide the correct results as search is asynchronous.\r\n   */\r\n  public showTaxCardAddDialogForTaxCardsList(listItem: TaxcardListItem) {\r\n    this.loaders[\"showTaxCardAddDialogForTaxCardsList\"] = true;\r\n    this.uiCrudHelpers.createNewTaxcard(listItem.otherPartyInfo.officialId).then((result) => {\r\n      if (result.action === \"ok\") {\r\n        const card = result.item.card;\r\n        listItem.data.employmentId = result.item.employmentId;\r\n        listItem.data.forYear = card.forYear;\r\n        listItem.data.incomeLimit = card.incomeLimit;\r\n        listItem.data.kind = card.kind as any;\r\n        listItem.data.taxPercent = card.taxPercent;\r\n        listItem.data.taxPercent2 = card.taxPercent2;\r\n        (listItem as any).payment = result.item.result.payment;\r\n        listItem.data.totalIncome = result.item.result.totalIncome;\r\n        listItem.startAt = card.validity.start;\r\n        listItem.endAt = card.validity.end;\r\n      }\r\n      this.loaders[\"showTaxCardAddDialogForTaxCardsList\"] = false;\r\n    });\r\n  }\r\n\r\n  /** Commits the DIFF's to storage: synchs the taxcard to actual paid calculations. */\r\n  public commitDiff() {\r\n    this.fullApi.commitDiff(this.current).then((result) => {\r\n      this.setCurrentValue(result, true);\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shows a dialog during the check of auto taxcard.\r\n   */\r\n  public showRefreshAutoTaxcardDialog() {\r\n    this.loaders[\"showRefreshAutoTaxcardDialog\"] = true;\r\n    this.uiCrudHelpers.refreshAutoTaxcard(this.current.id).then( (taxcards) => {\r\n        // reload\r\n        if (taxcards.length) {\r\n          this.setStatus(this.api.getSingle(taxcards[0].id)).then((taxcard) => {\r\n            this.setCurrent(taxcard);\r\n          });\r\n        }\r\n        this.loaders[\"showRefreshAutoTaxcardDialog\"] = false;\r\n    });\r\n  }\r\n\r\n  /** Defines which fields to show/hide, require etc. in the view */\r\n  private updateUISettings() {\r\n    const settings = {\r\n      /** If true, shown the 1st tax percent */\r\n      showTaxPercent: false,\r\n      /** If true, shown the income limit AND 2nd tax pecent. */\r\n      showIncomeLimit: false,\r\n      /** If true, the require the income limit AND 2nd tax percent. */\r\n      requireIncomeLimit: false,\r\n      /** If true, shows input for previous salaries paid. */\r\n      showPreviousSalariesPaid: false,\r\n      /** If true shows the image of an example tax card. */\r\n      showExampleTaxCard: true,\r\n      /** Upload is either hidden, shown as optional (at the end) or required (in the beginning). */\r\n      upload: \"hide\" as \"hide\" | \"show\" | \"required\",\r\n      /**\r\n       * If true, the tax percents etc. cannot be edited.\r\n       * In this case, also the helper numbers (1.-5.) that show where the number is in the PDF should not be shown.,\r\n       */\r\n      readonly: false,\r\n      /** Options for the start date: currently min and max dates. */\r\n      startDateOptions: null,\r\n      /**\r\n       * Years that are allowed in the year selection:\r\n       * Current year + next year in December, previous year in January.\r\n       */\r\n      yearsAllowed: null,\r\n    };\r\n    if (!this.current) {\r\n      this.addNewUi = settings;\r\n      return;\r\n    }\r\n    const todayYear = Dates.getYear(this.today);\r\n    const month = Dates.getMonth(this.today);\r\n    let yearsAllowed: number[];\r\n    if (month === 1) {\r\n      yearsAllowed = [todayYear, todayYear - 1];\r\n    } else if (month === 12) {\r\n      yearsAllowed = [todayYear, todayYear + 1];\r\n    } else {\r\n      yearsAllowed = [todayYear];\r\n    }\r\n    if (yearsAllowed.indexOf(this.current.card.forYear) < 0) {\r\n      if (!this.current.id) {\r\n        this.current.card.forYear = todayYear;\r\n      }\r\n    }\r\n    const forYear = this.current.card.forYear;\r\n    yearsAllowed = yearsAllowed.length < 2 ? null : yearsAllowed; // In the UI, the selection is not shown if there is only one item to select.\r\n    settings.showTaxPercent = true;\r\n    settings.showExampleTaxCard = true;\r\n\r\n    switch (this.current.card.kind) {\r\n      case TaxcardKind.Auto:\r\n        settings.showExampleTaxCard = false;\r\n        settings.showTaxPercent = false;\r\n        break;\r\n      case TaxcardKind.NoTaxCard:\r\n      case TaxcardKind.NoWithholdingHousehold:\r\n        settings.readonly = true;\r\n        settings.showExampleTaxCard = false;\r\n        break;\r\n      case TaxcardKind.Undefined:\r\n        settings.readonly = true;\r\n        settings.showTaxPercent = false;\r\n        break;\r\n      case TaxcardKind.DefaultYearly:\r\n        settings.showIncomeLimit = true;\r\n        settings.showPreviousSalariesPaid = true;\r\n        settings.requireIncomeLimit = true;\r\n        settings.showExampleTaxCard = true;\r\n        settings.upload = this.isSelf ? \"required\" : \"show\";\r\n        settings.yearsAllowed = yearsAllowed;\r\n        break;\r\n      case TaxcardKind.Replacement:\r\n        settings.showIncomeLimit = true;\r\n        settings.showPreviousSalariesPaid = true;\r\n        settings.showExampleTaxCard = true;\r\n        settings.upload = this.isSelf ? \"required\" : \"show\";\r\n        settings.yearsAllowed = yearsAllowed;\r\n        settings.startDateOptions = {\r\n            minDate: Dates.asJSDate(forYear + \"-01-01\"),\r\n            maxDate: Dates.asJSDate(forYear + \"-11-31\"),\r\n          };\r\n        break;\r\n    }\r\n    this.addNewUi = settings;\r\n  }\r\n}\r\n","import { Arrays, Dates, Taxcard, TaxCardIncome, TaxCardIncomeType } from \"@salaxy/core\";\r\n\r\nimport { UiHelpers } from \"../../services\";\r\nimport { ListControllerBase } from \"../bases\";\r\n\r\n/**\r\n * Handles user interface logic for viewing and editing the income log within a taxcard.\r\n */\r\nexport class TaxcardIncomeLogController extends ListControllerBase<Taxcard, TaxCardIncome> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"UiHelpers\"];\r\n\r\n  /** If true, the list can be edited, by default it is read-only. */\r\n  public editable: boolean;\r\n\r\n  /**\r\n   * Creates a new TaxcardIncomeLogController.\r\n   */\r\n  constructor(protected uiHelpers: UiHelpers) {\r\n    super(uiHelpers);\r\n  }\r\n\r\n  /** List that is edited */\r\n  public get list(): TaxCardIncome[] {\r\n    if (!this.parent) {\r\n      return null;\r\n    }\r\n    return this.parent.incomeLog;\r\n  }\r\n\r\n  /**\r\n   * Shows the edit dialog.\r\n   * @param item Item to edit or string \"new\" for creating a new one.\r\n   * @param isNew Optional way of specifying that the item is a new item (with default values, not yet added to the list).\r\n   * If item is string \"new\", this parameter will have no effect (will always be true).\r\n   */\r\n  public showEditDialog(item: TaxCardIncome | \"new\", isNew = false) {\r\n    if (!this.editable || (item !== \"new\" && this.isReadOnly(item))) {\r\n      return null;\r\n    }\r\n    super.showEditDialog(item, isNew);\r\n  }\r\n\r\n  /** Gets the URL for the log entry edit dialog. */\r\n  public getEditDialogTemplateUrl(): string {\r\n    return \"salaxy-components/worker/taxcard/TaxcardIncomeLogEditDialog.html\";\r\n  }\r\n\r\n  /** Gets a new blank entry with default values. */\r\n  public getBlank(): TaxCardIncome {\r\n    return {\r\n      type: TaxCardIncomeType.ExternalSalaries,\r\n      paidAt: Dates.getToday(),\r\n    };\r\n  }\r\n\r\n  /** Returns true, if the calculations paid are different than the calculations in the income log. */\r\n  public get hasDiff(): boolean {\r\n    return !!(this.list || []).find((x) => x.diff && x.diff !== \"default\");\r\n  }\r\n\r\n  /** Gets a sum from the list */\r\n  public getSum(field: \"tax\" | \"income\"): number {\r\n    if (!this.list) {\r\n      return null;\r\n    }\r\n    return Arrays.sum(this.list, (x) => x[field]);\r\n  }\r\n\r\n  /** Returns true if the row is read-only */\r\n  public isReadOnly(row: TaxCardIncome) {\r\n    return row.type !== TaxCardIncomeType.ExternalSalaries;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { AbsencePeriod, Absences, Arrays, DateRange, Dates, EnumerationsLogic, Translations, WorkerAbsences, CalendarSeries, ApiListItem } from \"@salaxy/core\";\r\nimport { UiCrudHelpers, UiHelpers } from \"../../services\";\r\nimport { ApiCrudObjectController } from \"../bases\";\r\n\r\n\r\n/**\r\n * Plain CRUD controller for WorkerAbsences.\r\n */\r\nexport class WorkerAbsencesCrudController extends ApiCrudObjectController<WorkerAbsences, ApiListItem> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"Absences\",\r\n    \"UiHelpers\",\r\n    \"$location\",\r\n    \"$routeParams\",\r\n    \"UiCrudHelpers\",\r\n  ];\r\n\r\n  /** UI view that is shown */\r\n  public viewType: \"overview\" | \"list\" = \"overview\";\r\n\r\n  /**\r\n   * Years that are available in the drop-down selection.\r\n   * Currently, only affects the calendar, but will probably also affect the lists etc.\r\n   * Currently, starting from 2019 until this year.\r\n   */\r\n  public years: number[];\r\n\r\n  /** Contains all the absences, once getAbsences() has been called. */\r\n  public allAbsences: WorkerAbsences[];\r\n\r\n  /** Current year: Currently, affects only the chart */\r\n  public currentYear: number;\r\n\r\n  /**\r\n   * The date for which the UI is rendered. Default is today.\r\n   * For employment holiday years (WorkerHolidays or CalcWorktime), set this to salary period begin\r\n   * => Specifies the the holiday year to choose by default from all holiday years that Worker has:\r\n   * If the date is Jan-April will show the previous year, May-Dec will show the current year.\r\n   */\r\n  public forDate: string;\r\n\r\n  /** Parameters related to holiday report (lomalista). */\r\n  public reportParams: {\r\n    /** Today's date: Set this for testing how user interface is rendered (which view is presented) at different times of year. */\r\n    today: string;\r\n    /** Start date of the view: Can be get/set directly by the view */\r\n    start: string,\r\n    /** Start date of the view: Can be get/set directly by the view */\r\n    end: string,\r\n    /** Underlying field of reportView */\r\n    _view: \"thisYear\" | \"lastYear\" | \"lastMonth\" | \"thisMonth\" | \"all\",\r\n  };\r\n\r\n  private _employmentId: string;\r\n\r\n  constructor(\r\n    private fullApi: Absences,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    private uiCrudHelpers: UiCrudHelpers,\r\n  ) { // Dependency injection\r\n    super(fullApi, uiHelpers, $location, $routeParams);\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    this.currentYear = Dates.getYear(\"today\");\r\n    this.years = Arrays.getRange(2019, this.currentYear);\r\n    this.reportParams = {\r\n      today: Dates.getToday(),\r\n    } as any;\r\n    this.reportView = \"thisYear\";\r\n    // Fetching reportView initializes the rest of parameters with default values. Comment for lint if necessary.\r\n    // eslint-disable-next-line @typescript-eslint/no-unused-vars\r\n    const necessaryInitCall = this.reportView;\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"/workers\",\r\n      detailsUrl: this.detailsUrl || \"/workers/details/\",\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/Absences.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Sets the employment ID and if it is different then starts the loading of the Absences object to that employment ID.\r\n   */\r\n  public set employmentId(value: string) {\r\n    if (this._employmentId === value) {\r\n      return;\r\n    }\r\n    if (!value) {\r\n      if (this._employmentId) {\r\n        this._employmentId = null;\r\n        this.model = null;\r\n        this.reload();\r\n      }\r\n      return;\r\n    }\r\n    this.fullApi.getForEmployment(value).then((model) => {\r\n      this.model = model;\r\n    });\r\n  }\r\n  /** Gets the employment ID */\r\n  public get employmentId() {\r\n    return this._employmentId;\r\n  }\r\n\r\n  /**\r\n   * Gets or sets the report view that is currently shown.\r\n   */\r\n  public get reportView(): \"thisYear\" | \"lastYear\" | \"lastMonth\" | \"thisMonth\" | \"all\" {\r\n    if (!this.reportParams._view) {\r\n      // Use the setter for setting the defaault value so that dependent fields are also set\r\n      this.reportView = \"thisMonth\";\r\n    }\r\n    return this.reportParams._view;\r\n  }\r\n  public set reportView(value: \"thisYear\" | \"lastYear\" | \"lastMonth\" | \"thisMonth\" | \"all\") {\r\n    this.reportParams._view = value;\r\n    const thisYear = Dates.getYear(this.reportParams.today);\r\n    const todayDay = Dates.asDate(this.reportParams.today);\r\n    const monthStart = Dates.startEnd(todayDay,\"start-month\");\r\n    const monthEnd = Dates.startEnd(todayDay,\"end-month\");\r\n    const previousMonthStart = Dates.add(Dates.startEnd(todayDay,\"start-month\"),-1, \"month\");\r\n    const previousMonthEnd = Dates.startEnd(previousMonthStart,\"end-month\");\r\n    switch (value) {\r\n      case \"thisYear\":\r\n        this.reportParams.start = thisYear + \"-01-01\";\r\n        this.reportParams.end = thisYear + \"-12-31\";\r\n        break;\r\n      case \"lastYear\":\r\n        this.reportParams.start = (thisYear - 1) + \"-01-01\";\r\n        this.reportParams.end = (thisYear - 1) + \"-12-31\";\r\n        break;\r\n      case \"thisMonth\":\r\n        this.reportParams.start = monthStart;\r\n        this.reportParams.end = monthEnd;\r\n        break;\r\n      case \"lastMonth\":\r\n        this.reportParams.start = previousMonthStart;\r\n        this.reportParams.end = previousMonthEnd;\r\n        break;\r\n      default:\r\n        this.reportParams.start = this.years[0] + \"-01-01\";\r\n        this.reportParams.end = this.years[this.years.length - 1] + \"-12-31\";\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Maps an array of Absences to array of calendar series\r\n   * @param source Absences to map.\r\n   */\r\n  public mapToCalendar = (source: WorkerAbsences[]): CalendarSeries[] => {\r\n    return source.map((abs) => {\r\n      return {\r\n        key: abs.id,\r\n        title: abs.workerSnapshot.displayName,\r\n        description: `${Translations.get(\"SALAXY.NG1.WorkerAbsencesCrudComponent.absencesPaid\")} ${this.getPeriodCalculation(abs, \"absencesPaid\")}, ${Translations.get(\"SALAXY.NG1.WorkerAbsencesCrudComponent.absencesUnpaid\")} ${this.getPeriodCalculation(abs, \"absencesUnpaid\")}`,\r\n        avatar: abs.workerSnapshot,\r\n        data: abs,\r\n        events: abs.periods.filter(this.filter).map((period) => ({\r\n          start: period.period.start,\r\n          end: period.period.end,\r\n          summary: EnumerationsLogic.getEnumLabel(\"AbsenceCauseCode\", period.causeCode) + ` ${Dates.getFormattedRange(period.period.start, period.period.end)}, ${period.period.days?.length || period.period.daysCount} ${Translations.get(\"SALAXY.NG1.WorkerAbsencesCrudComponent.days\")}.`,\r\n          data: period,\r\n        })),\r\n      };\r\n    });\r\n  };\r\n\r\n  /**\r\n   * Filter that is applied to the list\r\n   * @param value Item in the list\r\n   */\r\n  public filter = (value: AbsencePeriod) => {\r\n    if (this.reportParams.end && value.period.start > this.reportParams.end) {\r\n      return false;\r\n    }\r\n    if (this.reportParams.start && value.period.end < this.reportParams.start) {\r\n      return false;\r\n    }\r\n    return true;\r\n  };\r\n\r\n  /**\r\n   * Saves a the Worker absences based on calendar input and updates the value in allAbsences property.\r\n   * @param itemToSave A Worker absences object.\r\n   */\r\n  public saveAbsences(itemToSave: WorkerAbsences): Promise<void> {\r\n    const loader = this.uiHelpers.showLoading(`${Translations.get(\"SALAXY.NG1.WorkerAbsencesCrudComponent.saving\")}...`);\r\n    return this.api.save(itemToSave).then((savedValue) => {\r\n      angular.copy(savedValue, itemToSave);\r\n      loader.dismiss();\r\n      return;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Show an edit dialog for the absences.\r\n   * @param absences The Worker absences to update.\r\n   */\r\n   public showEditDialog(absences: WorkerAbsences): void {\r\n    /* TODO: The edit dialog is not optimal, as it shows the entire edit worker dialog. Should be a separate edit absence periods dialog. */\r\n    this.uiCrudHelpers.openEditEmploymentDialog(absences.employmentId, \"default\", \"absences\").then((result) => {\r\n      if (result.action === \"ok\") {\r\n        this.getAbsences();\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shows the add worker dialog: A\r\n   */\r\n  public showAddWorker() {\r\n    this.uiHelpers.openSelectEmployments().then((result) => {\r\n      if (result.action === \"ok\" && result.item.length) {\r\n        const newAbsences  = result.item.filter((x) => !this.allAbsences.find((absence) => absence.employmentId === x.id));\r\n        newAbsences.forEach((item) => {\r\n          const newItem = this.api.getBlank();\r\n          newItem.employmentId = item.id;\r\n          newItem.workerSnapshot = item.otherPartyInfo.avatar;\r\n          this.allAbsences.push(newItem);\r\n          this.saveAbsences(newItem);\r\n        });\r\n      }\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Gets the full absence objects for all Workers.\r\n   */\r\n  public getAbsences() {\r\n    this.fullApi.getLatest().then((result: WorkerAbsences[]) => {\r\n      this.allAbsences = result;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Returns true, if two objects are different.\r\n   * @param obj1 First object to compare\r\n   * @param obj2 Second object to compare\r\n   */\r\n  public isChanged(obj1, obj2): boolean {\r\n    return !angular.equals(obj1, obj2);\r\n  }\r\n\r\n  /**\r\n   * Gets a calculated value based on filtered absence periods.\r\n   * TODO: Consider moving to core (there is the same code in AbsencePeriodsController)\r\n   * @param absences Worker absences object.\r\n   * @param type Type of calculation\r\n   */\r\n  public getPeriodCalculation(absences: WorkerAbsences, type: \"all\" | \"length\" | \"firstPeriod\" | \"lastPeriod\" | \"absencesPaid\"\r\n    | \"absencesUnpaid\" | \"absencesHolidayAccrual\" | \"absencesNoHolidayAccrual\" = \"all\"): number | DateRange {\r\n    const list = absences.periods.filter(this.filter);\r\n    switch (type) {\r\n      case \"all\":\r\n        return Arrays.sum(list, (x) => x.period.daysCount);\r\n      case \"length\":\r\n        return list.length;\r\n      case \"firstPeriod\":\r\n        return list.length ? list[0].period : null;\r\n      case \"lastPeriod\":\r\n        return list.length ? list[list.length - 1].period : null;\r\n      case \"absencesPaid\":\r\n        return Arrays.sum(list.filter((x) => x.isPaid), (x) => x.period.daysCount);\r\n      case \"absencesUnpaid\":\r\n        return Arrays.sum(list.filter((x) => !x.isPaid), (x) => x.period.daysCount);\r\n      case \"absencesHolidayAccrual\":\r\n        return Arrays.sum(list.filter((x) => x.isHolidayAccrual), (x) => x.period.daysCount);\r\n      case \"absencesNoHolidayAccrual\":\r\n        return Arrays.sum(list.filter((x) => !x.isHolidayAccrual), (x) => x.period.daysCount);\r\n    }\r\n    return null;\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { WorkerAccount, WorkerListItem, Workers } from \"@salaxy/core\";\r\n\r\nimport { ApiCrudObjectController } from \"../bases\";\r\nimport { UiHelpers } from \"../../services\";\r\n\r\n/**\r\n * LEGACY: This used to be the controller for viewing and editing Worker AND Employment details, but now the EmploymentCrudController is used instead.\r\n * @deprecated Use EmploymentCrudController instead.\r\n */\r\nexport class WorkerAccountCrudController extends ApiCrudObjectController<WorkerAccount, WorkerListItem> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"Workers\", \"UiHelpers\", \"$location\", \"$routeParams\"];\r\n\r\n  constructor(\r\n    fullApi: Workers,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n  ) {\r\n    super(fullApi, uiHelpers, $location, $routeParams);\r\n  }\r\n\r\n  /**\r\n   * Initialization code.\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"/workers\",\r\n      detailsUrl: this.detailsUrl || \"/workers/details/\",\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/Employments.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Ajax, WorkerAccount } from \"@salaxy/core\";\r\n\r\nimport { ODataQueryController } from \"../../controllers/bases/ODataQueryController\";\r\n\r\nimport { UiHelpers } from \"../../services\";\r\nimport { EmploymentCrudController } from \"./EmploymentCrudController\";\r\n\r\n/**\r\n * Controller for creating stand-alone worker accounts.\r\n */\r\nexport class WorkerAssureController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\"UiHelpers\", \"AjaxNg1\"];\r\n\r\n  /** Data binding field for submitAssureWorkerAccount() method  */\r\n  public assureWorkerAccountReq = this.getEmptyAssureWorkerAccountReq();\r\n\r\n  /**\r\n   * Creates a new WorkerAssureController\r\n   * @param uiHelpers - Salaxy ui helpers service.\r\n   * @param ajax - Salaxy ajax service.\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    private uiHelpers: UiHelpers,\r\n    private ajax: Ajax,\r\n\r\n  ) {\r\n  }\r\n\r\n  /** Controller initialization */\r\n  public $onInit() {\r\n    // Empty\r\n  }\r\n\r\n  /**\r\n   * Calls the AssureWorkerAccount method in the API with the data defined in assureWorkerAccountReq\r\n   */\r\n  public submitAssureWorkerAccount(detailsCtrl: EmploymentCrudController, listCtrl: ODataQueryController): Promise<WorkerAccount> {\r\n    const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");\r\n    let method = \"/partner/assureworker\";\r\n    method += \"?officialId=\" + encodeURIComponent(this.assureWorkerAccountReq.officialId);\r\n    method += \"&firstName=\" + encodeURIComponent(this.assureWorkerAccountReq.firstName);\r\n    method += \"&lastName=\" + encodeURIComponent(this.assureWorkerAccountReq.lastName);\r\n    method += \"&email=\" + encodeURIComponent(this.assureWorkerAccountReq.email);\r\n    method += \"&telephone=\" + encodeURIComponent(this.assureWorkerAccountReq.telephone);\r\n    method += \"&bankAccountIban=\" + encodeURIComponent(this.assureWorkerAccountReq.bankAccountIban);\r\n    if (this.assureWorkerAccountReq.startDate) {\r\n      method += \"&startDate=\" + encodeURIComponent(this.assureWorkerAccountReq.startDate);\r\n    }\r\n    if (this.assureWorkerAccountReq.endDate) {\r\n      method += \"&endDate=\" + encodeURIComponent(this.assureWorkerAccountReq.endDate);\r\n    }\r\n    return this.ajax.postJSON(method, \"\")\r\n      .then((account: WorkerAccount) => {\r\n          const worker = listCtrl.items.find((x) => x.otherId === account.id);\r\n          if (worker == null) {\r\n            listCtrl.items.unshift({\r\n              createdAt: account.createdAt,\r\n              updatedAt: account.updatedAt,\r\n              otherId: account.id,\r\n              otherPartyInfo: {\r\n                avatar: account.avatar,\r\n                officialId: account.officialPersonId,\r\n                email: account.contact.email,\r\n                telephone: account.contact.telephone,\r\n                ibanNumber: account.ibanNumber,\r\n              },\r\n              data: {\r\n                type: account.employment.type,\r\n                pensionCalculation: account.employment.pensionCalculation,\r\n              },\r\n            });\r\n          }\r\n          detailsCtrl.model = account.employmentId;\r\n\r\n          this.resetAssureWorkerAccount();\r\n          loading.dismiss();\r\n          return account;\r\n        });\r\n  }\r\n\r\n  /**\r\n   * Resets assure worker account model.\r\n   */\r\n  public resetAssureWorkerAccount() {\r\n    this.assureWorkerAccountReq = this.getEmptyAssureWorkerAccountReq();\r\n  }\r\n\r\n  /** Gets an empty assureWorkerAccountReq - used for reset. */\r\n  private getEmptyAssureWorkerAccountReq() {\r\n    return {\r\n      officialId: null,\r\n      firstName: null,\r\n      lastName: null,\r\n      email: null,\r\n      telephone: null,\r\n      bankAccountIban: null,\r\n      startDate: null,\r\n      endDate: null,\r\n    };\r\n  }\r\n\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { CalendarActionType, CalendarEvent, CalendarEvents, Dates, DateTimes, Translations, CalendarEventListItem } from \"@salaxy/core\";\r\n\r\nimport { UiHelpers} from \"../../services\";\r\nimport { ApiCrudObjectController } from \"../bases\";\r\n\r\n/**\r\n * Controller for implementing Calendars that contain CalendarEvents (iCalendar).\r\n */\r\nexport class CalendarEventsCrudController extends ApiCrudObjectController<CalendarEvent, CalendarEventListItem> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"CalendarEvents\",\r\n    \"UiHelpers\",\r\n    \"$location\",\r\n    \"$routeParams\",\r\n  ];\r\n\r\n  public endMinDate: string;\r\n\r\n  public _tabOptions: any[] = [];\r\n\r\n\r\n  /**\r\n   * Creates a new WorkflowController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    private fullApi: CalendarEvents,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n  ) {\r\n    super(fullApi, uiHelpers, $location, $routeParams);\r\n  }\r\n\r\n  /**\r\n   * Controller initialization\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Dynamic tabs */\r\n  public get tabOptions(): any[] {\r\n    if (this._tabOptions.length == 0) {\r\n      this._tabOptions.push(...[\r\n        { value: \"basic\", text: \"Perustiedot\" },\r\n        { value: \"recurrence\" },\r\n        { value: \"actions\" },\r\n        { value: \"debug\", text: \"Debug\" }\r\n      ]);\r\n    }\r\n    if (this.current) {\r\n      this._tabOptions.find((x) => x.value == \"recurrence\").text = `Toistuvuus (${this.current?.event?.recurrenceRules?.length || \"ei toistu\"})`;\r\n      this._tabOptions.find((x) => x.value == \"actions\").text = `Tehtävät (${this.current?.event.actions?.length || 0})`;\r\n\r\n    }\r\n    return this._tabOptions;\r\n  }\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"/calendar\",\r\n      detailsUrl: this.detailsUrl || \"/calendar/details/\",\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/calendar/Events.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n\r\n  /** Adds a new recurrence rule to the event */\r\n  public addRecurrenceRule() {\r\n    this.current.event.recurrenceRules = this.current.event.recurrenceRules || [];\r\n    this.current.event.recurrenceRules.push(\"FREQ=MONTHLY;INTERVAL=1\");\r\n  }\r\n\r\n  /** Adds a new action to the event */\r\n  public addAction() {\r\n    this.current.event.actions = this.current.event.actions || [];\r\n    this.current.event.actions.push({ type: CalendarActionType.Script});\r\n  }\r\n\r\n  /**\r\n   * Deletes an item in the recurrence rules\r\n   * @param index The index number of the item to delete.\r\n   */\r\n  public deleteRecurrence(index: number): void {\r\n    this.current.event.recurrenceRules.splice(index, 1);\r\n  }\r\n\r\n  /**\r\n   * Deletes an item in the actions\r\n   * @param index The index number of the item to delete.\r\n   */\r\n  public deleteAction(index: number): void {\r\n    this.current.event.actions.splice(index, 1);\r\n  }\r\n\r\n  /**\r\n   * Saves the calendar item.\r\n   * Override done so that durations (timespans) are converted from number to string.\r\n   */\r\n  public save(): Promise<CalendarEvent> {\r\n    this.checkDurations();\r\n    return super.save();\r\n  }\r\n\r\n  /** Gets the event duration, even if it is null (start and end defined). */\r\n  public getEventDuration() {\r\n    if (!this.current) {\r\n      return null;\r\n    }\r\n    if (this.current.event.duration) {\r\n      return DateTimes.formatDuration(this.current.event.duration);\r\n    }\r\n    let end = this.current.event.end ?? this.current.event.start;\r\n    if (end < this.current.event.start) {\r\n      return Translations.get(\"SALAXY.NG1.ODataCalendarEventComponent.getEventDurationError\");\r\n    }\r\n    if (this.current.event.isAllDay) {\r\n      end = Dates.add(end, 1, \"day\");\r\n    }\r\n    return DateTimes.formatRangeToDuration(this.current.event.start, end);\r\n  }\r\n\r\n  /** Assures that the durations are strings, not numbers. The UI binding makes them numbers. */\r\n  public checkDurations() {\r\n    if (this.current?.event.duration) {\r\n      this.current.event.duration = this.current.event.duration.toString();\r\n    }\r\n    (this.current?.event.actions || []).forEach((action) => {\r\n      if (action.triggerDuration) {\r\n        action.triggerDuration = action.triggerDuration.toString();\r\n      }\r\n    });\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { ActionExecutor, ApiItemType, Dataset, DatasetListItem, Datasets, InputEnumOption, OpenAPIV3, UsecaseAction } from \"@salaxy/core\";\r\n\r\nimport { JsonSchemaService, SessionService, SessionUsecase, UiHelpers, UsecasesService } from \"../../services\";\r\nimport { ApiCrudObjectController } from \"../bases\";\r\nimport { AjaxNg1 } from \"../../ajax\";\r\n\r\n/**\r\n * Controller for listing, using and setting the data in Datasets:\r\n * Some arbitrary external data, typically Imports, Exports and Reports.\r\n */\r\nexport class DatasetsCrudController extends ApiCrudObjectController<Dataset, DatasetListItem> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"Datasets\",\r\n    \"UiHelpers\",\r\n    \"$location\",\r\n    \"$routeParams\",\r\n    \"UsecasesService\",\r\n    \"JsonSchemaService\",\r\n    \"SessionService\",\r\n    \"AjaxNg1\",\r\n    \"$timeout\"\r\n  ];\r\n\r\n  /**\r\n   * Type of component user interface.\r\n   * Default is usecase if one is specified, otherwise \"data-edit\".\r\n   * \"full-edit\" shows the full editor with data schema selections, adding new data objects etc.\r\n   */\r\n  public mode: \"full-edit\" | \"data-edit\" | \"usecase\" | \"default\";\r\n\r\n  /**\r\n   * The usecase definition if specified and loaded.\r\n   * If the usecase has been checked from server, but none is defined, the value is \"none\".\r\n   * For checking whether usecase really is available, check e.g. usecase.uri.\r\n   */\r\n  public usecase: null | \"none\" | SessionUsecase = null;\r\n\r\n  /** Defines the default usecase (uri) that is used for new objects. */\r\n  public defaultUsecase: string;\r\n\r\n  /** Available usecases if the user needs to make a selection of which usecase to take. */\r\n  public usecases: InputEnumOption[];\r\n\r\n  /**\r\n   * Creates a new DatasetsCrudController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    fullApi: Datasets,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    private usecasesService: UsecasesService,\r\n    private jsonSchemaService: JsonSchemaService,\r\n    private sessionService: SessionService,\r\n    private ajax: AjaxNg1,\r\n    private $timeout: angular.ITimeoutService,\r\n  ) {\r\n    super(fullApi, uiHelpers, $location, $routeParams);\r\n  }\r\n\r\n  /**\r\n   * Controller initialization\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"/datasets\",\r\n      detailsUrl: this.detailsUrl || \"/datasets/details/\",\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/Datasets.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n\r\n  /** Creates options for the tabs in the UI. */\r\n  public generateTabOptions = function() {\r\n    return this.uiHelpers.cache(this, \"generateTabOptions\", () => {\r\n      if (!this.current || !this.current.data) {\r\n        return [];\r\n      }\r\n\r\n      return this.current.data.map((table, index) => {\r\n        return {\r\n          value: table.name || `tab-${index}`,\r\n          text: table.label || table.name,\r\n        };\r\n      });\r\n    });\r\n  };\r\n\r\n  /** Overrides the reload to assure that usecase is also loaded. */\r\n  public reload(): Promise<Dataset> {\r\n    // TODO: Consider moving this functionality to base classes.\r\n    return super.reload().then((result) => {\r\n      if (!result) {\r\n        this.usecase = \"none\";\r\n        return result;\r\n      }\r\n      this.current.data.forEach((x: any) => {\r\n        if ((x.schemaDoc || \"any\") != \"any\" && x.schemaDoc != \"usecase\") {\r\n          // TODO: Assure that this loading does not happen several times for same URL.\r\n          this.jsonSchemaService.assureSchemaDocument(x.schemaDoc);\r\n        }\r\n      });\r\n      this.generateTabOptions();\r\n      const usecaseUri = this.$location?.search().usecase || this.defaultUsecase;\r\n      result.data.forEach((x) => x.content = x.content || []);\r\n      if (usecaseUri || result.usecase?.uri) {\r\n        return this.usecasesService.assureUsecase(ApiItemType.Dataset, result, usecaseUri).then((usecase) => {\r\n          if (usecase) {\r\n            this.usecase = usecase;\r\n          } else {\r\n            this.usecase = \"none\";\r\n            this.assureUsecasesLoaded();\r\n          }\r\n          return result;\r\n        });\r\n      } else {\r\n        this.assureUsecasesLoaded();\r\n        this.usecase = \"none\";\r\n        return result;\r\n      }\r\n    });\r\n  }\r\n\r\n  private assureUsecasesLoaded() {\r\n    this.usecasesService.getActiveUsecaseListItems(ApiItemType.Dataset).then((list) => {\r\n      this.usecases = list.sort((a, b) => (a.data.order || 100) - (b.data.order || 100))\r\n        .map((x) => ({ text: x.shortText, value: x.uri }));\r\n    });\r\n  }\r\n\r\n  /** Gets the user interface mode */\r\n  public getMode(): \"data-edit\" | \"full-edit\" | \"usecase\" | \"loading\" {\r\n    if (this.isLoading || (!(this.usecase as SessionUsecase)?.isLoaded && this.usecase != \"none\")) {\r\n      // TODO: Check the case when dataset has no usecase. Is it infinite loader now?\r\n      return \"loading\";\r\n    }\r\n    switch (this.mode) {\r\n      case \"data-edit\":\r\n      case \"full-edit\":\r\n      case \"usecase\":\r\n        return this.mode;\r\n      default:\r\n        if ((this.usecase as SessionUsecase)?.defaultView) {\r\n          return \"usecase\";\r\n        }\r\n        return \"data-edit\";\r\n    }\r\n  }\r\n\r\n  /** Adds a new \"table\" to the dataset */\r\n  public addDataObject() {\r\n    this.current.data.push({\r\n      label: \"Uusi tietue\"\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Removes a data object from the dataset\r\n   * @param index Index of the object to remove.\r\n   */\r\n  public deleteObject(index: number) {\r\n    // TODO: Add \"Are you sure?\"\r\n    this.current.data.splice(index, 1);\r\n  }\r\n\r\n  /** Executes the current action with the current item. */\r\n  public async executeAction(action: UsecaseAction): Promise<ActionExecutor> {\r\n    const executor = new ActionExecutor(action);\r\n    await executor.execute(this.current, this.sessionService.session, this.ajax);\r\n    if (executor.isAsync) {\r\n      this.$timeout();\r\n    }\r\n    return executor;\r\n  }\r\n\r\n  /**\r\n   * Adds an item to the default view (first view). Adds the view if it does not already exist.\r\n   * Method may later be extended to support multiple views and/or more elaborate column properties.\r\n   * @param dataObjectIndex Index of the data object to which the view item is added.\r\n   * @param type Add include or exclude rule.\r\n   * @param value Value to add to the array.\r\n   */\r\n  public addViewItem(dataObjectIndex: number, type: \"include\" | \"exclude\", value = \"\") {\r\n    const dataObj = this.current.data[dataObjectIndex];\r\n    dataObj.views = dataObj.views || [];\r\n    if (dataObj.views.length < 1) {\r\n      dataObj.views.push({});\r\n    }\r\n    const view = dataObj.views[0];\r\n    if (type == \"exclude\") {\r\n      view.exclude = view.exclude || [];\r\n      view.exclude.push(value);\r\n    } else if (type == \"include\") {\r\n      view.include = view.include || [];\r\n      view.include.push(value);\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Helper method to move an item in an array up or down.\r\n   * @param arr Array to operate on\r\n   * @param fromIndex Index of the item to move\r\n   * @param step How many items to move and to which direction: -1 is one up, 1 is one down.\r\n   */\r\n  public arraymove(arr: [], fromIndex: number, step: number) {\r\n    const element = arr[fromIndex];\r\n    arr.splice(fromIndex, 1);\r\n    let toIndex = fromIndex + step;\r\n    if (toIndex > arr.length) {\r\n      toIndex = arr.length;\r\n    }\r\n    if (toIndex < 0) {\r\n      toIndex = 0;\r\n    }\r\n    arr.splice(toIndex, 0, element);\r\n  }\r\n\r\n  /**\r\n   * Gets the available schema documents that can be used for modeling the data objects.\r\n   * @returns Cached collection of available schema documents.\r\n   */\r\n  public getSchemaDocs(): InputEnumOption[] {\r\n    return this.uiHelpers.cache(this, \"schemaList\", () => {\r\n      console.log(\"Refresh cache.\");\r\n      return [\r\n        {\r\n          value: \"any\",\r\n          text: \"Ei määritetty (any)\",\r\n          title: \"any\",\r\n        },\r\n        {\r\n          value: \"usecase\",\r\n          text: \"Räätälöinti\",\r\n          title: \"usecase\",\r\n        },\r\n        ...this.jsonSchemaService.getSchemas().map((x) => ({\r\n          value: x.url,\r\n          text: x.doc.info.title,\r\n          title: x.url,\r\n        }))\r\n      ];\r\n    }, () => this.jsonSchemaService.getSchemas().map((x) => x.url));\r\n  }\r\n\r\n  /**\r\n   * Gets the schemas defined in the specified schema document\r\n   * @param docUrl The URL (unique key in cache) for the schema document.\r\n   */\r\n  public getSchemas(docUrl): InputEnumOption[] {\r\n    if (!docUrl || docUrl == \"any\") {\r\n      docUrl = \"\";\r\n    }\r\n    if (!this.schemaCache[docUrl]) {\r\n      if (docUrl == \"usecase\") {\r\n        if (this.usecase == \"none\") {\r\n          this.schemaCache.usecase = [];\r\n        } else {\r\n          const schemas = this.usecase.schema.components.schemas;\r\n          this.schemaCache[docUrl] = Object.keys(schemas).map((key) => ({\r\n            value: key,\r\n            text: `${schemas[key].title} (${key})`,\r\n            title: schemas[key].description || key,\r\n          }));\r\n        }\r\n      } else {\r\n        const schemas = this.jsonSchemaService.findSchemaDoc(docUrl, true).doc.components.schemas;\r\n        this.schemaCache[docUrl] = Object.keys(schemas).map((key) => {\r\n          const text = (schemas[key] as OpenAPIV3.SchemaObject).title ? `${(schemas[key] as OpenAPIV3.SchemaObject).title} (${key})` : key;\r\n          return {\r\n            value: key,\r\n            text,\r\n            title: (schemas[key] as OpenAPIV3.SchemaObject).description || key,\r\n          };\r\n        });\r\n      }\r\n    }\r\n    return this.schemaCache[docUrl];\r\n  }\r\n\r\n  /**\r\n   * Gets the full schema definition for the specified table.\r\n   * @param index Index number of the data object in the data collection.\r\n   */\r\n  public getSchamaDef(index: number): OpenAPIV3.SchemaObject {\r\n    const docUrl = (this.current.data[index] as any).schemaDoc;\r\n    const schemaKey = this.current.data[index].schema;\r\n    if (!docUrl || docUrl == \"any\") {\r\n      return null;\r\n    }\r\n    if (docUrl == \"usecase\") {\r\n      if (this.usecase == \"none\") {\r\n        return null;\r\n      } else {\r\n        return this.usecase.schema.components.schemas[schemaKey];\r\n      }\r\n    } else {\r\n      const schemaDoc = this.jsonSchemaService.findSchemaDoc(docUrl, false);\r\n      return schemaDoc ? schemaDoc.doc.components.schemas[schemaKey] as OpenAPIV3.SchemaObject : null;\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Gets all the properties within a schema for property selection.\r\n   * @param index Index number of the data object in the data collection.\r\n   */\r\n  public getAllPropertiesOfSchema(index: number): InputEnumOption[] {\r\n    const docUrl = (this.current.data[index] as any).schemaDoc;\r\n    const schemaKey = this.current.data[index].schema;\r\n    if (this.propertyTreeCache[docUrl + schemaKey]) {\r\n      return this.propertyTreeCache[docUrl + schemaKey];\r\n    }\r\n    const result = this.getProperties(this.getSchamaDef(index));\r\n    this.propertyTreeCache[docUrl + schemaKey] = result;\r\n    return result;\r\n  }\r\n\r\n  private getProperties(schema: OpenAPIV3.SchemaObject, prefix = \"\"): InputEnumOption[] {\r\n    const result: InputEnumOption[] = [];\r\n    Object.keys(schema.properties || {}).forEach(key => {\r\n      const prop = schema.properties[key] as OpenAPIV3.SchemaObject;\r\n      result.push({\r\n        value: prefix + key,\r\n        text: prefix + key,\r\n        title: prop.title || prop.description,\r\n      });\r\n      if (prop.type == \"object\") {\r\n        result.push(...this.getProperties(prop as OpenAPIV3.SchemaObject, prefix + key + \".\"));\r\n      }\r\n    });\r\n    return result;\r\n  }\r\n\r\n  private schemaCache: { [key: string]: InputEnumOption[] } = {\r\n    \"\": [],\r\n  };\r\n\r\n  private propertyTreeCache: { [key: string]: InputEnumOption[] } = {\r\n    \"\": [],\r\n  };\r\n\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {\r\n  ActionExecutor, ApiItemType, BootstrapStyle, Calculations, Datasets,\r\n  JsonSchemaUtils, Payrolls, Usecase, UsecaseAction, UsecaseActionType, UsecaseStatus, UsecaseListItem,\r\n  Usecases, UsecaseView, Translations, ODataResult\r\n} from \"@salaxy/core\";\r\n\r\nimport { SessionService, UiHelpers, UsecaseApiCrudObject, UsecasesService } from \"../../services\";\r\nimport { ApiCrudObjectController } from \"../bases\";\r\nimport { AjaxNg1 } from \"../../ajax\";\r\n\r\n/**\r\n * Usecases controller.\r\n */\r\nexport class UsecasesCrudController extends ApiCrudObjectController<Usecase, UsecaseListItem> {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"Usecases\",\r\n    \"UiHelpers\",\r\n    \"$location\",\r\n    \"$routeParams\",\r\n    \"UsecasesService\",\r\n    \"SessionService\",\r\n    \"AjaxNg1\",\r\n    \"$timeout\",\r\n    \"Calculations\",\r\n    \"Payrolls\",\r\n    \"Datasets\",\r\n    \"$templateCache\",\r\n  ];\r\n\r\n  /** Action executor for the current action. */\r\n  public currentExecutor: ActionExecutor;\r\n\r\n  /** The current item that is being executed on. If not set, will be set to blank. */\r\n  public currentItem: UsecaseApiCrudObject;\r\n\r\n  /**\r\n   * Current view\r\n   */\r\n  private _currentView: UsecaseView;\r\n\r\n  /** Temporary collection of items: Will be replaced by OData query and/or settings. */\r\n  public localStorageItems: Usecase[];\r\n\r\n  private _currentAction: UsecaseAction;\r\n\r\n  private _currentSchema: {\r\n    key?: string,\r\n    schema?: any,\r\n  } = {};\r\n\r\n  private _list: UsecaseListItem[];\r\n\r\n  /**\r\n   * Creates a new UsecasesCrudController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    usecases: Usecases,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any,\r\n    private usecasesService: UsecasesService,\r\n    private sessionService: SessionService,\r\n    private ajax: AjaxNg1,\r\n    private $timeout: angular.ITimeoutService,\r\n    private calculations: Calculations,\r\n    private payrolls: Payrolls,\r\n\r\n    private datasets: Datasets,\r\n    private $templateCache: angular.ITemplateCacheService,\r\n  ) {\r\n    super(usecases, uiHelpers, $location, $routeParams);\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    super.$onInit();\r\n  }\r\n\r\n  /** Gets the type name of item type, i.e. \"Calculation\" for \"calculation\" enumeration. */\r\n  public get itemType() {\r\n    return \"CalculationListItem[]\";\r\n    // return ApiLogic.getType(this.current?.itemType);\r\n  }\r\n\r\n  /**\r\n   * Shows the detail view for the item.\r\n   * Supports viewing public items from other users as read-only.\r\n   * @param item Item may be either Container or list item.\r\n   */\r\n  public showDetails(item: UsecaseListItem | Usecase): angular.ILocationService {\r\n    // TODO: Consider adding this support in super\r\n    if (this.parentController) {\r\n      return this.parentController.showDetails(item);\r\n    }\r\n    return this.$location.url(this.getDefaults().detailsUrl + this.getId(item) + \"@\" + item.owner);\r\n  }\r\n\r\n  /**\r\n   * Gets the activity type of usecase from the settings.\r\n   * @param item List item to check.\r\n   * @returns Information on whether the usecase is active or not - or default usecase (also active).\r\n   */\r\n  public getActive(item: UsecaseListItem): UsecaseStatus {\r\n    return this.usecasesService.getActive(item.uri);\r\n  }\r\n\r\n  /**\r\n   * Gets the activity bg-color of usecase from the settings.\r\n   * @param status Status for color.\r\n   * @returns Bg color for the status.\r\n   */\r\n    public getStatusBgColor(status: UsecaseStatus): string {\r\n      switch( status ) {\r\n        case UsecaseStatus.Inactive:\r\n          return \"bg-warning\";\r\n        case UsecaseStatus.Active:\r\n          return \"bg-info\";\r\n        case UsecaseStatus.Default:\r\n          return \"bg-danger\";\r\n        case UsecaseStatus.Undefined:\r\n        default:\r\n          return \"bg-default\";\r\n      }\r\n    }\r\n\r\n  /**\r\n   * Gets the order  of usecase from the settings.\r\n   * @param item List item to get the order.\r\n   * @returns Order number for the usecase, 0 if not set.\r\n   */\r\n   public getOrder = (item: UsecaseListItem): number => {\r\n    return this.usecasesService.getOrder(item.uri);\r\n  };\r\n\r\n  private toLowerCamelCase(str) {\r\n    // TODO: Move to core\r\n    return str.toLowerCase().replace(/[^a-zA-Z0-9]+(.)/g, (m, chr) => chr.toUpperCase());\r\n  }\r\n\r\n  /**\r\n   * Shows the detail view with a new item that is a copy of the given item.\r\n   * Supports copying public items from other users.\r\n   * @param item Item may be either Container or list item.\r\n   */\r\n  public showCopyAsNew(item: UsecaseListItem | Usecase): angular.ILocationService {\r\n    // TODO: Consider adding this support in super\r\n    if (this.parentController) {\r\n      return this.parentController.showCopyAsNew(item);\r\n    }\r\n    return this.$location.url(this.getDefaults().detailsUrl + this.getId(item) + \"@\" + item.owner + \"/copy-as-new\");\r\n  }\r\n\r\n  /** The data container in the current business object */\r\n  public get usecase(): Usecase {\r\n    return this.currentItem?.usecase;\r\n  }\r\n\r\n  /** The data part of the usecase: Used in data binding. */\r\n  public get data(): any {\r\n    return this.currentItem?.usecase?.data;\r\n  }\r\n\r\n  /**\r\n   * Gets a list of usecases for the current account.\r\n   * First get will start the load process and then the list is cached to controller scope.\r\n   */\r\n  public get list(): UsecaseListItem[] {\r\n    if (!this._list) {\r\n      this._list = [];\r\n      this.getOData(null).then((result: ODataResult<UsecaseListItem>) => {\r\n        this._list = result.items.sort((a, b) => (a.data.order || 100) - (b.data.order || 100));\r\n      });\r\n    }\r\n    return this._list;\r\n  }\r\n\r\n  /**\r\n   * Checks if the given schema is defined in the current usecase: Exists and has any properties.\r\n   * @param schemaNames One or several names of the schema to check whether they are defined.\r\n   * If any schema is exists and has properties, returns true.\r\n   */\r\n  public isDefined(...schemaNames: string[]): boolean {\r\n    return JsonSchemaUtils.isDefined(this.current?.schema, ...schemaNames);\r\n  }\r\n\r\n  /** Returns the whole Open API schema document as editable string. */\r\n  public get editableSchema(): string {\r\n    return JSON.stringify(this.current.schema || \"{}\", null, \"\\t\");\r\n  }\r\n  /** Parses the schema from the given string. */\r\n  public set editableSchema(value: string) {\r\n    this.current.schema = JSON.parse(value);\r\n  }\r\n\r\n  /** Sets the current editable schema (one of the schemas within the Open API document). */\r\n  public setCurrentSchema(key: string): void {\r\n    this._currentSchema.key = key;\r\n    this._currentSchema.schema = this.current.schema.components.schemas[key];\r\n  }\r\n\r\n  /** Gets the current editable schema (one of the schemas within the Open API document). */\r\n  public get currentSchema(): any {\r\n    return this._currentSchema.schema;\r\n  }\r\n\r\n  /** Gets the property name / key of the current editable schema (one of the schemas within the Open API document). */\r\n  public get currentSchemaKey(): string {\r\n    return this._currentSchema.key;\r\n  }\r\n\r\n  /** Creates a new current editable schema (one of the schemas within the Open API document). */\r\n  public createSchema() {\r\n    // TODO: Add this to UI Helpers (as dialog) and search for prompt().\r\n    const name = window.prompt(Translations.get(\"SALAXY.NG1.UsecaseDetailsComponent.createSchemaName\"));\r\n    // TODO: Add property name validation / fix.\r\n    this._currentSchema.key = name;\r\n    this._currentSchema.schema = {\r\n      type: \"object\",\r\n      title: `${Translations.get(\"SALAXY.NG1.UsecaseDetailsComponent.createSchemaTitle\")} (${name})`,\r\n      properties: {},\r\n    };\r\n    this.current.schema.components.schemas[name] = this._currentSchema.schema;\r\n  }\r\n\r\n  /** Removes an schema from this usecase. */\r\n  public deleteSchema(key: string) {\r\n    delete this.current.schema.components.schemas[key];\r\n    if (this.currentSchemaKey == key) {\r\n      this._currentSchema.key = Object.keys(this.current.schema.components.schemas)[0];\r\n      this._currentSchema.schema = this._currentSchema.key ? this.current.schema.components.schemas[this._currentSchema.key] : null;\r\n    }\r\n  }\r\n\r\n  /** The currently selected editable action (script). */\r\n  public get currentAction(): UsecaseAction {\r\n    return this._currentAction;\r\n  }\r\n  public set currentAction(value: UsecaseAction) {\r\n    this._currentAction = value;\r\n    this.currentExecutor = new ActionExecutor(value);\r\n  }\r\n\r\n  /**\r\n   * Current editable view.\r\n   */\r\n  public get currentView() {\r\n    return this._currentView;\r\n  }\r\n  public set currentView(value: any) {\r\n    const key = \"salaxy-dynamic-templates/usecase-custom-view.html\";\r\n    this.$templateCache.remove(key);\r\n    if (value?.content?.trim()) {\r\n      this.$templateCache.put(key, value.content);\r\n    }\r\n    this._currentView = value;\r\n  }\r\n\r\n  /** Overrides the save for clear cache. */\r\n  public save(): Promise<Usecase> {\r\n    this.usecasesService.clearCache();\r\n    return super.save();\r\n  }\r\n\r\n  /** Create a new action / script to this usecase. */\r\n  public createAction() {\r\n    this.currentAction = {\r\n      actionType: UsecaseActionType.ClientScript,\r\n      uiColor: BootstrapStyle.Default,\r\n      uiText: Translations.get(\"SALAXY.NG1.UsecaseDetailsComponent.createAction\"),\r\n      content: \"// Add script here.\"\r\n    };\r\n    this.current.actions.push(this.currentAction);\r\n  }\r\n\r\n  /** Creates a new view and sets it as current. */\r\n  public createView() {\r\n    this.currentView = {\r\n      label: null,\r\n      description: null,\r\n      content: \"<p>Create your view here.</p>\",\r\n    };\r\n    (this.current as any).views.push(this.currentView);\r\n  }\r\n\r\n  /** Overrides the default reload for clearing the cache. */\r\n  public reload(): Promise<Usecase> {\r\n    return super.reload().then((value) => {\r\n      this.usecasesService.setToCache(value);\r\n      return value;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Refreshes the current usecase to cache: Used in preview.\r\n   */\r\n  public refreshCurrentInCache() {\r\n    this.usecasesService.setToCache(this.current);\r\n  }\r\n\r\n  /** Removes an action from this usecase. */\r\n  public deleteAction(action: UsecaseAction) {\r\n    if (!action) {\r\n      return;\r\n    }\r\n    this.current.actions.splice(this.current.actions.indexOf(action), 1);\r\n    if (this.currentAction == action) {\r\n      this.currentAction = this.current.actions[0];\r\n    }\r\n  }\r\n\r\n  /**\r\n   * Removes a view from this usecase.\r\n   */\r\n  public deleteView(view: UsecaseView) {\r\n    if (!view) {\r\n      return;\r\n    }\r\n    this.current.views.splice(this.current.views.indexOf(view), 1);\r\n    if (this.currentView == view) {\r\n      this.currentView = this.current.views[0];\r\n    }\r\n  }\r\n\r\n  /** Executes the current action with the current item. */\r\n  public async executeAction(action?: UsecaseAction): Promise<ActionExecutor> {\r\n    const executor = action ? new ActionExecutor(action) : this.currentExecutor;\r\n    await executor.execute(this.currentItem, this.sessionService.session, this.ajax);\r\n    if (executor.isAsync) {\r\n      this.$timeout();\r\n    }\r\n    return executor;\r\n  }\r\n\r\n  /**\r\n   * Opens a dialog for selecting the current item for which to execute a usecase.\r\n   * @param type Type of item to select: Select from dialog, new or null/empty.\r\n   */\r\n  public selectItem(type: \"select\" | \"new\" | null) {\r\n    if (!type) {\r\n      this.currentItem = null;\r\n      return;\r\n    }\r\n    switch (this.current.itemType) {\r\n      case ApiItemType.Calculation:\r\n      case ApiItemType.CalculationPaid:\r\n        if (type == \"new\") {\r\n          this.currentItem = this.calculations.getBlank();\r\n        } else {\r\n          const calcType = this.current.itemType == ApiItemType.CalculationPaid ? \"paid\" : \"draft\";\r\n          this.uiHelpers.openSelectCalcs(calcType, \"Select a calculation for demo\").then((result) => {\r\n            if (result.action == \"ok\" && result.item.length > 0) {\r\n              const loader = this.uiHelpers.showLoading();\r\n              this.calculations.getSingle(result.item[0].id).then((calc) => {\r\n                this.currentItem = calc;\r\n                calc.usecase.uri = this.current.uri;\r\n                loader.dismiss();\r\n              });\r\n            }\r\n          });\r\n        }\r\n        return;\r\n      case ApiItemType.PayrollDetails:\r\n        if (type == \"new\") {\r\n          this.currentItem = this.payrolls.getBlank();\r\n        } else {\r\n          alert(\"TODO: Payroll selection not yet supported.\");\r\n        }\r\n        return;\r\n      case ApiItemType.Dataset:\r\n        if (type == \"new\") {\r\n          this.currentItem = this.datasets.getBlank();\r\n        } else {\r\n          this.uiHelpers.openSelect(\"Select a dataset\").then((listItem) => {\r\n            if (listItem) {\r\n              const loader = this.uiHelpers.showLoading();\r\n              this.datasets.getSingle(listItem.id).then((payload) => {\r\n                this.currentItem = payload;\r\n                payload.usecase.uri = this.current.uri;\r\n                loader.dismiss();\r\n              });\r\n            }\r\n          });\r\n        }\r\n        return;\r\n      default:\r\n        alert(`Item type ${this.current.itemType} not supported for debug data.`);\r\n        return;\r\n    }\r\n  }\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"/usecases\",\r\n      detailsUrl: this.detailsUrl || \"/usecases/details/\",\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/Usecases.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {\r\n  BootstrapStyle,\r\n  SessionUserCredential,\r\n  Translations,\r\n  WorkflowData,\r\n  WorkflowEvent,\r\n} from \"@salaxy/core\";\r\n\r\nimport {\r\n  CredentialService,\r\n  SessionService,\r\n  UiHelpers,\r\n  WorkflowService,\r\n} from \"../../services\";\r\n\r\nimport { ApiCrudObjectController } from \"../bases/ApiCrudObjectController\";\r\n\r\nimport { WorkflowEditorConfig } from \"./WorkflowEditorConfig\";\r\n\r\n/**\r\n * Controller for implementing workflow logic.\r\n */\r\nexport class WorkflowController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"WorkflowService\",\r\n    \"UiHelpers\",\r\n    \"SessionService\",\r\n    \"CredentialService\",\r\n  ];\r\n\r\n  /**\r\n   * API CRUD controller for the object.\r\n   */\r\n  public apiCtrl: ApiCrudObjectController<any, any>;\r\n\r\n  public showWorkflowAssign: boolean;\r\n\r\n  /**\r\n   * Single wfType to show.\r\n   */\r\n  public wfType: string;\r\n\r\n  /** Returns true if the update is in progress */\r\n  public isUpdating = false;\r\n\r\n  /**\r\n   * Function that is called when a new workflow action has happened..\r\n   * Function has the following locals:  item: the parent item for workflow, isDelete: true/false if the workflow action was a removal of the event.\r\n   */\r\n  public onChange: (params: {\r\n    /** Item details after change */\r\n    item: any,\r\n    /** Delete/creation information */\r\n    isDelete: boolean,\r\n  }) => void;\r\n\r\n  /** Read only flag */\r\n  public readOnly: boolean;\r\n\r\n  private _events: WorkflowEvent[] = [];\r\n\r\n  /**\r\n   * Creates a new WorkflowController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    protected workflowService: WorkflowService,\r\n    protected uiHelpers: UiHelpers,\r\n    protected sessionService: SessionService,\r\n    protected credentialService: CredentialService\r\n  ) {\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    this.showWorkflowAssign = this.showWorkflowAssign !== false;\r\n    // no initializations\r\n  }\r\n\r\n  /** Returns the events of given type. */\r\n  public get events(): WorkflowEvent[] {\r\n    const eventsOfType = ((this.apiCtrl.current as any)?.workflowData?.events ?? []).filter((x) => x.type == this.wfType);\r\n    this.modifyArray(eventsOfType, this._events);\r\n    return this._events;\r\n  }\r\n\r\n  /**\r\n   * Returns the current workflow event of the given type.\r\n   * @param wfType Event type of the workflow event.\r\n   * @returns Returns the current workflow event of the given type.\r\n   */\r\n  public getWorkflowEvent(wfType: string): WorkflowEvent {\r\n    return this.getSingleWorkflowEvent(wfType);\r\n  }\r\n\r\n  /**\r\n   * Returns true if the workflow of the current item has an event of the given type.\r\n   * @param wfType Event type of the workflow event.\r\n   * @returns Returns true if the current item contains an event of the given type.\r\n   */\r\n  public hasWorkflowEvent(wfType: string): boolean {\r\n    return !!this.getWorkflowEvent(wfType);\r\n  }\r\n\r\n  /**\r\n   * Adds/updates the workflow event for the current item.\r\n   * @param wfEvent Workflow event to add/update.\r\n   * @returns Reloaded item.\r\n   */\r\n  public saveWorkflowEvent(wfEvent: WorkflowEvent): Promise<any> {\r\n    if (this.isUpdating) {\r\n      return;\r\n    }\r\n    this.isUpdating = true;\r\n    return this.workflowService.saveWorkflowEvent(this.apiCtrl, wfEvent).then((result) => {\r\n      this.isUpdating = false;\r\n      if (this.onChange) {\r\n      this.onChange({ item: result, isDelete: false });\r\n      }\r\n      return result;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Deletes the given event or all events with given type.\r\n   * @param wfIdOrType Id or type of the workflow event.\r\n   * @returns - Reloaded item.\r\n   */\r\n  public deleteWorkflowEvent(wfIdOrType: string): Promise<any> {\r\n    if (this.isUpdating) {\r\n      return;\r\n    }\r\n    this.isUpdating = true;\r\n    return this.workflowService.deleteWorkflowEvent(this.apiCtrl, wfIdOrType).then((result) => {\r\n      this.isUpdating = false;\r\n      if (this.onChange) {\r\n        this.onChange({ item: result, isDelete: true });\r\n      }\r\n      return result;\r\n    });\r\n  }\r\n\r\n  /**\r\n   * Shows a workflow editor for the given event.\r\n   * Saves the event and reloads the item.\r\n   * @param config Configuration for the worklow editor.\r\n   * @param wfEvent Workflow event for the editor.\r\n   * @returns - Reloaded item.\r\n   */\r\n  public showWorkflowEventEditor(config: WorkflowEditorConfig, wfEvent: WorkflowEvent): Promise<any> {\r\n    if (!this.apiCtrl.current) {\r\n      return Promise.resolve(this.apiCtrl.current);\r\n    }\r\n\r\n    config.title = config.title || \"SALAXY.NG1.WorkFlowIssueComponent.showWorkflowEventEditorTitle\";\r\n\r\n    return this.uiHelpers.openEditDialog(\r\n      \"salaxy-components/modals/workflow/WorkflowEventEdit.html\",\r\n      wfEvent,\r\n      {\r\n        ...config,\r\n        readOnly: this.readOnly,\r\n      }\r\n    ).then((dialogResult) => {\r\n      if (dialogResult.action === \"ok\") {\r\n        return this.saveWorkflowEvent(dialogResult.item);\r\n      } else {\r\n        return Promise.resolve(this.apiCtrl.current);\r\n      }\r\n    });\r\n  }\r\n\r\n  /** Returns avatar for the given credential. */\r\n  public getCredential(credentialId: string): SessionUserCredential {\r\n    return (this.credentials.find((x) => x.id === credentialId) || {});\r\n  }\r\n\r\n  /** Gets the credetial of the current assigned-to person or undefined if there is no assignment. */\r\n  public getAssignedTo(): SessionUserCredential | undefined {\r\n    const assignedTo = this.getWorkflowEvent(\"PartnerMessageAssignedTo\")?.assignedTo;\r\n    if (!assignedTo) {\r\n      return undefined;\r\n    }\r\n    return this.getCredential(assignedTo);\r\n  }\r\n\r\n  /** Returns credentials for the current account. */\r\n  public get credentials(): SessionUserCredential[] {\r\n    return this.workflowService.credentials;\r\n  }\r\n\r\n  /** Returns the credential for current session */\r\n  public get self(): SessionUserCredential {\r\n    return this.workflowService.self;\r\n  }\r\n\r\n  /**\r\n   * Responds to button click with appropriate UI logic.\r\n   * @param type The button that was clicked.\r\n   * @param credential The credential to assign to. Only for type \"assign\". Use undefined to remove assignment.\r\n   */\r\n  public buttonClick(type: \"close\" | \"assign\" | \"issue\", credential?: SessionUserCredential): void {\r\n    switch (type) {\r\n      case \"close\":\r\n        if (this.hasWorkflowEvent(\"PartnerMessageClosed\")) {\r\n          this.uiHelpers.showConfirm(\"SALAXY.NG1.WorkFlowIssueComponent.deleteConfirmations.close\").then((result: boolean) => {\r\n            if (result) {\r\n              this.deleteWorkflowEvent(\"PartnerMessageClosed\");\r\n            }\r\n          });\r\n        } else {\r\n          this.saveWorkflowEvent({\r\n            type: \"PartnerMessageClosed\",\r\n            ui: BootstrapStyle.Success,\r\n            message: Translations.get(\"SALAXY.UI_Terms.checked\")\r\n          });\r\n        }\r\n        return;\r\n      case \"issue\":\r\n        if (this.hasWorkflowEvent(\"PartnerMessageIssue\")) {\r\n          this.uiHelpers.showConfirm(\"SALAXY.NG1.WorkFlowIssueComponent.deleteConfirmations.issue\").then((result: boolean) => {\r\n            if (result) {\r\n              this.deleteWorkflowEvent(\"PartnerMessageIssue\");\r\n            }\r\n          });\r\n        } else {\r\n          this.showWorkflowEventEditor(\r\n            { title: undefined, showUi: false },\r\n            { type: \"PartnerMessageIssue\", ui: BootstrapStyle.Danger, message: \"\" }\r\n          );\r\n        }\r\n        return;\r\n      case \"assign\":\r\n        if (credential) {\r\n          this.saveWorkflowEvent({\r\n            type: \"PartnerMessageAssignedTo\",\r\n            ui: BootstrapStyle.Primary,\r\n            message: credential.email || credential.avatar.displayName,\r\n            assignedTo: credential.id,\r\n          });\r\n        } else {\r\n          this.deleteWorkflowEvent(\"PartnerMessageAssignedTo\");\r\n        }\r\n        return;\r\n      default:\r\n        throw new Error(\"Not implemented: \" + type);\r\n    }\r\n  }\r\n\r\n  private modifyArray(\r\n    source: any[],\r\n    target: any[]) {\r\n    if (angular.equals(source, target)) {\r\n      return;\r\n    }\r\n    target.splice(0, target.length);\r\n    target.push(...source);\r\n  }\r\n\r\n  private getSingleWorkflowEvent(wfType: string): WorkflowEvent {\r\n    if (!this.apiCtrl.current || !wfType) {\r\n      return null;\r\n    }\r\n\r\n    const workflowData: WorkflowData = (this.apiCtrl.current as any)?.workflowData;\r\n    if (!workflowData || !workflowData.events) {\r\n      return null;\r\n    }\r\n    return workflowData.events.find((x) => (x.type || \"\").toLowerCase() === wfType.toLowerCase());\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {\r\n  ApiCrudObject,\r\n  ApiListItem,\r\n  Attachment,\r\n  Record,\r\n  Records,\r\n  WorkflowData,\r\n  WorkflowEvent,\r\n} from \"@salaxy/core\";\r\n\r\nimport {\r\n  UiHelpers,\r\n  UploadService,\r\n} from \"../../services\";\r\n\r\nimport { ApiCrudObjectController } from \"../bases/ApiCrudObjectController\";\r\n\r\ntype WorkflowPayload = ApiCrudObject & { workflowData: WorkflowData };\r\n\r\nfunction isWorkflowPayload(model: WorkflowPayload | ApiListItem): model is WorkflowPayload {\r\n  return (model as WorkflowPayload).workflowData !== undefined;\r\n}\r\n\r\nfunction isMessagesListItem(model: WorkflowPayload | ApiListItem): model is ApiListItem {\r\n  return (model as ApiListItem).messages !== undefined;\r\n}\r\n\r\n/**\r\n * Controller for implementing workflow badge logic.\r\n */\r\nexport class WorkflowBadgeController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"UiHelpers\",\r\n    \"Records\",\r\n    \"UploadService\",\r\n  ];\r\n\r\n /**\r\n  * API CRUD controller for the object.\r\n  */\r\n  public apiCtrl: ApiCrudObjectController<any, any>;\r\n\r\n  /**\r\n   * wfTypes to show as badges.\r\n   */\r\n  public wfTypes: string[];\r\n\r\n  /** Bound model: ApiListItem or object with WorkflowData */\r\n  public model: ApiListItem | WorkflowPayload | null;\r\n\r\n  /** Visual mode of the component: horizontal or vertical (default). */\r\n  public mode: \"horizontal\" | \"vertical\";\r\n\r\n  private _events: WorkflowEvent[] = [];\r\n\r\n  /**\r\n   * Creates a new WorkflowBadgeController\r\n   * @ignore\r\n   */\r\n  constructor(\r\n    private uiHelpers: UiHelpers,\r\n    private records: Records,\r\n    private uploadService: UploadService,\r\n  ) {\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    // no initializations\r\n  }\r\n\r\n  /** Workflow events for ui. */\r\n  public get events() {\r\n    if (isWorkflowPayload(this.model)) {\r\n      const eventsOfTypes = (this.model.workflowData?.events ?? []).filter( (x) => !this.wfTypes || this.wfTypes.length == 0 || this.wfTypes.indexOf(x.type) >= 0);\r\n      this.modifyArray(eventsOfTypes, this._events);\r\n    }\r\n    else if (isMessagesListItem(this.model)){\r\n      const eventsOfTypes = [];\r\n      for(const msg of this.model.messages)  {\r\n        const eventOfType = this.toWorkflowEvent(msg);\r\n        if (!this.wfTypes || this.wfTypes.length == 0 || this.wfTypes.indexOf(eventOfType.type) >=0) {\r\n          eventsOfTypes.push(eventOfType);\r\n        }\r\n      }\r\n      this.modifyArray(eventsOfTypes, this._events);\r\n    }\r\n    else {\r\n      this.modifyArray([], this._events);\r\n    }\r\n\r\n    return this._events;\r\n  }\r\n\r\n  /** Opens a display for workflow event details */\r\n  public showEventDetails(original: WorkflowEvent) {\r\n    const ensureItem = (): Promise<any> => {\r\n      if (isMessagesListItem(this.model)) {\r\n        // Support old worker based lists\r\n        const id = this.apiCtrl.getApi().getBaseUrl() === \"/accounts/workers\" ?\r\n        this.model.otherId : this.model.id;\r\n        return this.apiCtrl.getApi().getSingle(id);\r\n      } else {\r\n        return Promise.resolve(this.model);\r\n      }\r\n    };\r\n\r\n    const getWorkflowEvent = () : Promise<{event: WorkflowEvent, record: Record }> => {\r\n      if (original?.id) {\r\n        return ensureItem().then( (item ) => {\r\n          return  Promise.resolve(item.workflowData.events.find(x => x.id == original.id)).then( result => {\r\n            if (!result) {\r\n              // Return original\r\n              return { event: original, record: null };\r\n            }\r\n            if (!result.record) {\r\n              return { event: result, record: null};\r\n            }\r\n            return this.records.getSingle(result.record).then( (record) =>{\r\n              return { event: result, record };\r\n            });\r\n          });\r\n        });\r\n        }\r\n      return Promise.resolve({event: original, record: null});\r\n    };\r\n\r\n    getWorkflowEvent().then( (result) => {\r\n      this.uiHelpers.openEditDialog(\r\n        \"salaxy-components/modals/workflow/WorkflowBadgeDetails.html\",\r\n        result,\r\n        {\r\n          getAttachmentDownloadUrl: (attachment) => this.getAttachmentDownloadUrl(attachment),\r\n          getAttachmentIcon: (attachment) => this.getAttachmentIcon(attachment),\r\n        }, \"lg\"\r\n      );\r\n    });\r\n\r\n  }\r\n\r\n    /** Returns file icon for the attachment. */\r\n    private getAttachmentIcon(attachment: Attachment): string {\r\n      return this.uploadService.getFileIcon(attachment?.fileName);\r\n    }\r\n\r\n    /** Returns download url for the attachment. */\r\n    private getAttachmentDownloadUrl(attachment: Attachment): string {\r\n      return this.uploadService.getFileUrl(attachment?.contentId);\r\n    }\r\n  private toWorkflowEvent(messageString: string): WorkflowEvent {\r\n    if (!messageString) {\r\n      return {};\r\n    }\r\n\r\n    // [type] (Ui[ui]):[message] ([User] at [yyyy-MM-dd HH:mm] to [assignedTo] id [id])\r\n\r\n    const uiStartX = messageString.indexOf(\"(Ui\");\r\n    const uiEndX = messageString.indexOf(\"):\", uiStartX + 3);\r\n    const type = (messageString.substring(0, uiStartX - 1) || \"\");\r\n    const ui = messageString.substring(uiStartX + 3, uiEndX).toLowerCase();\r\n    let rest = messageString.substring(uiEndX + 3);\r\n    const messageEndX = rest.lastIndexOf(\"(\");\r\n    const message = rest.substring(0, messageEndX).trim();\r\n    rest = rest.substring(messageEndX + 1); // Remove (\r\n    rest = rest.substring(0, rest.length - 1); // Remove )\r\n\r\n    let id = \"\";\r\n    const idx = rest.lastIndexOf(\" id \");\r\n    if (idx >= 0) {\r\n      id = rest.substring(idx + 4);\r\n      rest = rest.substring(0, idx);\r\n    }\r\n\r\n    let assignedTo = \"\";\r\n    const aIdx = rest.lastIndexOf(\" to \");\r\n    if (aIdx >= 0) {\r\n      assignedTo = rest.substring(aIdx + 4);\r\n      rest = rest.substring(0, aIdx);\r\n    }\r\n\r\n    let time = \"\";\r\n    const tIdx = rest.lastIndexOf(\" at \");\r\n    if (tIdx >= 0) {\r\n      time = rest.substring(tIdx + 4);\r\n      rest = rest.substring(0, tIdx);\r\n      // time\r\n      time = time.replace(\" \", \"T\")+\"Z\";\r\n    }\r\n    const user = rest;\r\n    return {\r\n      id,\r\n      type,\r\n      ui,\r\n      user,\r\n      assignedTo,\r\n      message,\r\n      time,\r\n    } as WorkflowEvent;\r\n  }\r\n\r\n  private modifyArray(\r\n    source: any[],\r\n    target: any[]) {\r\n    if (angular.equals(source, target)) {\r\n      return;\r\n    }\r\n    target.splice(0, target.length);\r\n    target.push(...source);\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport {\r\n  Template,TemplateListItem,BusinessTemplates,\r\n} from \"@salaxy/core\";\r\n\r\nimport { UiHelpers } from \"../../services\";\r\nimport { ApiCrudObjectController } from \"../bases\";\r\n\r\n/**\r\n * Controller for template management.\r\n */\r\nexport class TemplateCrudController extends ApiCrudObjectController<Template, TemplateListItem> {\r\n  isSaving: boolean;\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"BusinessTemplates\",\r\n    \"UiHelpers\",\r\n    \"$location\",\r\n    \"$routeParams\"\r\n  ];\r\n\r\n  constructor(\r\n    api: BusinessTemplates,\r\n    uiHelpers: UiHelpers,\r\n    $location: angular.ILocationService,\r\n    $routeParams: any\r\n  ) { // Dependency injection\r\n    super(api, uiHelpers, $location, $routeParams);\r\n  }\r\n\r\n  /** Implements the getDefaults of ApiCrudObjectController */\r\n  public getDefaults() {\r\n    return {\r\n      listUrl: this.listUrl || \"/templates\",\r\n      detailsUrl: this.detailsUrl || \"/templates/details/\",\r\n      oDataTemplateUrl: \"salaxy-components/odata/lists/Templates.html\",\r\n      oDataOptions: {},\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Select template.\r\n   */\r\n  public selectTemplate() {\r\n    return this.uiHelpers.openEditDialog(\r\n      \"salaxy-components/modals/templates/TemplateSelect.html\",     \r\n      [],\r\n      {\r\n        title: \"SALAXY.UI_Terms.select\",\r\n        options: null,\r\n        okButtonText: \"SALAXY.UI_Terms.ok\",\r\n        cancelButtonText: \"SALAXY.UI_Terms.cancel\",\r\n      },\"lg\").then((result) => {\r\n        if (result.action === \"ok\" && result.item.length > 0) {\r\n          this.uiHelpers.showConfirm(\"SALAXY.UI_Terms.confirm\",result.item[0].shortText + \"\\r\\n\" +result.item[0].data.description);\r\n          //const loading = this.uiHelpers.showLoading(\"SALAXY.UI_Terms.wait\");        \r\n          //loading.dismiss();\r\n        }\r\n      });\r\n  }\r\n\r\n}","import angular from \"angular\";\r\n\r\n/** Abstract Base class for salaxy components */\r\nexport abstract class ComponentBase implements angular.IComponentOptions {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public abstract bindings: any;\r\n\r\n    /**\r\n     * Controller has the actual implementation of the component.\r\n     * Same Controller may be reused between different components with different views and binding.\r\n     */\r\n    public abstract controller;\r\n\r\n    /** The default template for the component. */\r\n    public abstract defaultTemplate;\r\n\r\n    /**\r\n     * Set the template-url attribute to specify your custom template.\r\n     * @ignore\r\n     */\r\n    public templateUrl = [\"$element\", \"$attrs\" , ($element: JQLite, $attrs: angular.IAttributes) => {\r\n        if ($attrs.templateUrl) {\r\n            return $attrs.templateUrl;\r\n        }\r\n        return this.defaultTemplate;\r\n    }];\r\n}\r\n","import { SessionController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Simple presentation of Salaxy account info: employer and/or worker data\r\n * @example\r\n * ```html\r\n * <salaxy-account-info></salaxy-account-info>\r\n * ```\r\n */\r\nexport class AccountInfo extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to controller implementation\r\n     */\r\n    public bindings = {};\r\n\r\n    /** Uses the SessionController */\r\n    public controller = SessionController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/account/AccountInfo.html\";\r\n}\r\n","import { PartnerController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Component that assures that customer has specified a partner.\r\n * @example\r\n * ```html\r\n * <salaxy-assure-partner><main>This content is shown if partner selected!</main></salaxy-assure-partner>\r\n * ```\r\n */\r\nexport class AssurePartner extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {};\r\n\r\n    /**\r\n     * The \"main\" element contents is shown if the partner has been selected. Defaults to current partner info.\r\n     * The \"header\" element is shown before the \"main\" Defaults to \"Service provided by\" + an actions drop-down.\r\n     */\r\n    public transclude = {\r\n        main: \"?main\",\r\n        header: \"?header\",\r\n    };\r\n\r\n    /** Uses the AccountAuthorizationController */\r\n    public controller = PartnerController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/account/AssurePartner.html\";\r\n}\r\n","import { AccountAuthorizationController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a card for granting authorization\r\n * @example\r\n * ```html\r\n * <div ng-controller=\"AccountAuthorizationController as authCtrl\">\r\n *   <div class=\"row\">\r\n *     <div class=\"col-xs-12 col-sm-6 col-md-4 col-lg-3\" ng-repeat=\"site in authCtrl.partnerIntegrationSites\">\r\n *       <salaxy-auth-card auth-id=\"site.id\"></salaxy-auth-card>\r\n *     </div>\r\n *   </div>\r\n * </div>\r\n * ```\r\n */\r\nexport class AuthCard extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n        /** Id that specifies what auth card to be shown */\r\n        authId: \"<\",\r\n        /** If set to true, the switch is not shown on the card. */\r\n        hideSwitch: \"@\",\r\n    };\r\n\r\n    /** Uses the AccountAuthorizationController */\r\n    public controller = AccountAuthorizationController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/account/AuthCard.html\";\r\n}\r\n","import { AccountAuthorizationController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a list of all authorized accounts which can act on behalf of this account.\r\n * @example\r\n * ```html\r\n * <salaxy-authorized-accounts></salaxy-authorized-accounts>\r\n * ```\r\n */\r\nexport class AuthorizedAccounts extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = AccountAuthorizationController.crudBindings;\r\n\r\n    /**\r\n     * Header is mainly meant for buttons (Usually at least \"Add new\").\r\n     * These are positioned to the right side of the table header (thead).\r\n     */\r\n    public transclude = {\r\n        header: \"?header\",\r\n    };\r\n\r\n    /** Uses the AccountAuthorizationController */\r\n    public controller = AccountAuthorizationController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/account/AuthorizedAccounts.html\";\r\n}\r\n","import { AccountAuthorizationController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a list of all authorizing accounts on behalf of which this account can act.\r\n * @example\r\n * ```html\r\n * <salaxy-authorizing-accounts></salaxy-authorizing-accounts>\r\n * ```\r\n */\r\nexport class AuthorizingAccounts extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n    };\r\n\r\n    /**\r\n     * Header is mainly meant for buttons (Usually at least \"Add new\").\r\n     * These are positioned to the right side of the table header (thead).\r\n     */\r\n    public transclude = {\r\n        header: \"?header\",\r\n    };\r\n\r\n    /** Uses the AccountAuthorizationController */\r\n    public controller = AccountAuthorizationController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/account/AuthorizingAccounts.html\";\r\n}\r\n","import { CertificateController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a list of all certificates which has been generated for this account.\r\n * @example\r\n * ```html\r\n * <salaxy-certificates></salaxy-certificates>\r\n * ```\r\n */\r\nexport class Certificates extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = CertificateController.crudBindings;\r\n\r\n    /**\r\n     * Header is mainly meant for buttons (Usually at least \"Add new\").\r\n     * These are positioned to the right side of the table header (thead).\r\n     */\r\n    public transclude = {\r\n        header: \"?header\",\r\n    };\r\n\r\n    /** Uses the CertificateController */\r\n    public controller = CertificateController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/account/Certificates.html\";\r\n}\r\n","import { CredentialController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a list of all login credentials which can access this account.\r\n * @example\r\n * ```html\r\n * <salaxy-credentials></salaxy-credentials>\r\n * ```\r\n */\r\nexport class Credentials extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n      showEdit: \"<\",\r\n    };\r\n\r\n    /**\r\n     * Header is mainly meant for buttons (Usually at least \"Add new\").\r\n     * These are positioned to the right side of the table header (thead).\r\n     */\r\n    public transclude = {\r\n        header: \"?header\",\r\n    };\r\n\r\n    /** Uses the CredentialController */\r\n    public controller = CredentialController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/account/Credentials.html\";\r\n}\r\n","import { SessionController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a language selection control.\r\n * @example\r\n * ```html\r\n * <salaxy-language-selector></salaxy-language-selector>\r\n * ```\r\n */\r\nexport class LanguageSelector extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n\r\n    public bindings = {};\r\n\r\n    /** Uses the SessionController */\r\n    public controller = SessionController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/account/LanguageSelector.html\";\r\n\r\n}\r\n","import { SessionController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Renders a Login / Logout -button.\r\n * When anonymous, the button shows the login button.\r\n * When loggen in shows: Logout and links to Palkkaus Account and User Account pages.\r\n * @example\r\n * ```html\r\n * <salaxy-login-button redirect-url=\"'/my-page'\"></salaxy-login-button>\r\n * ```\r\n */\r\nexport class LoginButton extends ComponentBase {\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {\r\n        /** URL to which the user should be redirected. When you specify string, use quotes. */\r\n        redirectUrl: \"<\",\r\n\r\n        /** If specified, sets the login text. Default is \"SALAXY.UI_Terms.login\"  */\r\n        loginText: \"@\",\r\n\r\n        /** If specified, sets the button class. Default is \"btn-default\". */\r\n        btnClass: \"@\",\r\n    };\r\n\r\n    /** Uses the SessionController */\r\n    public controller = SessionController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/account/LoginButton.html\";\r\n\r\n}\r\n","import { SigningController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the signature for the current account for signing.\r\n * @example\r\n * ```html\r\n * <salaxy-signing ng-ref=\"$ctrl.$signing\"></salaxy-signing>\r\n * <div ng-if=\"$ctrl.$signing.isSigningOk\">\r\n *  Signature is OK => Show the rest of the page\r\n * </div>\r\n * ```\r\n */\r\nexport class Signing extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to controller implementation\r\n     */\r\n    public bindings = {\r\n      /** If true, shows the component even if the Signing is already OK. */\r\n      showAlways: \"<\",\r\n      /** If true, component shows success popup */\r\n      showInPopup: \"<\",\r\n    };\r\n\r\n    /** Uses the SessionController */\r\n    public controller = SigningController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/account/Signing.html\";\r\n}\r\n","import { SessionController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Simple presentation of Salaxy user info: employer and/or worker data\r\n * @example\r\n * ```html\r\n * <salaxy-user-info></salaxy-user-info>\r\n * ```\r\n */\r\nexport class UserInfo extends ComponentBase {\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {\r\n    };\r\n\r\n    /** Uses the SessionController */\r\n    public controller = SessionController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/account/UserInfo.html\";\r\n\r\n}\r\n","\r\nimport { SessionController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Edit the avatar information: Picture upload, Initials + color or Gravatar.\r\n * @example\r\n * ```html\r\n * <salaxy-account-avatar-edit></salaxy-account-avatar-edit>\r\n * ```\r\n */\r\nexport class AccountAvatarEdit extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {};\r\n\r\n    /** Uses the SessionController */\r\n    public controller = SessionController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/account/AccountAvatarEdit.html\";\r\n\r\n}\r\n","\r\nimport { SessionController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Editing UI of Contact information for account.\r\n * @example\r\n * ```html\r\n * <salaxy-account-contact-edit></salaxy-account-contact-edit>\r\n * ```\r\n */\r\nexport class AccountContactEdit extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {};\r\n\r\n    /** Uses the SessionController */\r\n    public controller = SessionController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate =  \"salaxy-components/account/AccountContactEdit.html\";\r\n\r\n}\r\n","import { CalcEmploymentController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * Shows / edits the relevant employment relation:\r\n * Employer, if the current user is worker\r\n * Worker, if the current user is employer or potentially both in some future admin / pro scenarios.\r\n * @example\r\n * ```html\r\n * <salaxy-calc-employment model=\"$ctrl.currentCalc\"></salaxy-calc-employment>\r\n * ```\r\n */\r\nexport class CalcEmployment extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n\r\n  public bindings = {\r\n    /** The calculation that is being edited  */\r\n    model: \"<\",\r\n\r\n    /**\r\n     * If true, will also update the calculation rows from employment relation when the employment\r\n     * relation is selected. By default, does not update the rows.\r\n     */\r\n    updateRows: \"<\",\r\n  };\r\n\r\n  /** Uses the CalcEmploymentController */\r\n  public controller = CalcEmploymentController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/calc/2022/CalcEmployment.html\";\r\n}\r\n","import { CalcRows2019Controller } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * Shows a mobile friendly rows editor for addding calculation rows: Salaries, expenses, benefits etc.\r\n * @example\r\n * ```html\r\n * <salaxy-calc-rows-editor parent=\"$ctrl.current\" title=\"Matkalaskun rivit\" on-commit=\"$ctrl.recalculate()\" show-edit-buttons=\"false\" show-gross-totals=\"true\"\r\n            template-url=\"\"\r\n            categories=\"['expenses']\"\r\n            is-in-edit=\"!$ctrl.current.isReadOnly\">\r\n * ```\r\n */\r\nexport class CalcRowsEditor extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = CalcRows2019Controller.bindings;\r\n\r\n  /**\r\n   * The \"footer\" is at the bottom of the rows list where \"Add new row\" buttons would typically be.\r\n   */\r\n  public transclude = {\r\n    footer: \"?footer\",\r\n  };\r\n\r\n  /** Uses the CalcRows2019Controller */\r\n  public controller = CalcRows2019Controller;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/calc/2022/CalcRowsEditor.html\";\r\n}\r\n","import { Calculator2022Controller } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * The **CalcUsecase** is the 2022 version of the calculator (Calc) that supports\n * usecases: customizations to user interfaces and logic using HTML and JavaScript.\n * It is expected to eventually replace the old Calc component.\n *\n * The component provides functionality for:\n *\n * 1. Selecting the Employment relation / Worker to the calculation (employer if the current user is Worker)\n * 2. Selecting the usecase if one is not provided in the URI.\n * 3. Defining the Worktime information: Period, Absences and holidays.\n * 4. Defining the calculation rows: salary, expences, benefits, deductions etc.\n * 5. Showing the results as charts and reports.\n * 6. Starting the payment process\n *\n * Controllers are defined in **salaxy.ng1.controllers**. Most of the functionality comes from Calculator2022Controller.\n * The view (html) can be modified using the usecase view mechanism.\n * @example\r\n * ```html\r\n * <salaxy-calc-usecase model=\"'new'\"></salaxy-calc-usecase>\r\n * ```\r\n */\r\nexport class CalcUsecase extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = Calculator2022Controller.crudBindings;\r\n\r\n    /** Uses the Calculator2022Controller */\r\n    public controller = Calculator2022Controller;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/calc/2022/CalcUsecase.html\";\r\n\r\n}\r\n","\r\nimport { ApiCrudObjectControllerBindings, Payroll4CrudController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * EXPERIMENTAL new version of the Payroll Details component.\r\n * Payroll (Palkkalista) is a list of employees who receive salary or wages from a particular organization.\r\n * Typical usecase is that a a company has e.g. a monthly salary list that is paid\r\n * at the end of month. For next month, a copy is then made from the latest list and\r\n * the copy is potentially modified with the changes of that particular month.\r\n * Payroll can also be started from scratch either by just writing salaries from\r\n * e.g. an e-mail or by uploading an Excel sheet.\r\n * @example\r\n * ```html\r\n * <salaxy-payroll-details></salaxy-payroll-details>\r\n * ```\r\n */\r\nexport class PayrollDetails extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = (new class extends ApiCrudObjectControllerBindings {\r\n    /** The action buttons shown by the component */\r\n    actions = \"<\";\r\n    /** Currently selected tab in the Payroll  */\r\n    payrollDetailsCurrentTab = \"@\";\r\n    /** Custom default tab. */\r\n    defaultTab = \"@\";\r\n  }());\r\n\r\n  /** Uses the PayrollCrudController */\r\n  public controller = Payroll4CrudController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/calc/payrollV4/PayrollDetails.html\";\r\n}\r\n","import { ApiCrudObjectControllerBindings, Payroll4CrudController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * EXPERIMENTAL new version of the Payroll Details component.\r\n * Payroll (Palkkalista) is a list of employees who receive salary or wages from a particular organization.\r\n * Typical usecase is that a a company has e.g. a monthly salary list that is paid\r\n * at the end of month. For next month, a copy is then made from the latest list and\r\n * the copy is potentially modified with the changes of that particular month.\r\n * Payroll can also be started from scratch either by just writing salaries from\r\n * e.g. an e-mail or by uploading an Excel sheet.\r\n * @example\r\n * ```html\r\n * <salaxy-payroll-details-list></salaxy-payroll-detais-list>\r\n * ```\r\n */\r\nexport class PayrollDetailsList extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n\r\n  public bindings = (new class extends ApiCrudObjectControllerBindings {\r\n   /**\r\n    * Option to hide New payroll button.\r\n    * Set this true if the site has action buttons configured elsewhere.\r\n    */\r\n    public hideButton = \"<\";\r\n\r\n   /**\r\n    * Mode of the payroll. Supports \"service\" or default.\r\n    * In \"service\" mode the payroll has less funtionality and payment is disabled.\r\n    */\r\n    public mode = \"<\";\r\n  }());\r\n\r\n\r\n  /**\r\n   * Header is mainly meant for buttons (Usually at least \"Add new\").\r\n   * These are positioned to the right side of the table header (thead).\r\n   */\r\n  public transclude = {\r\n    header: \"?header\",\r\n  };\r\n\r\n  /** Uses the PayrollCrudController */\r\n  public controller = Payroll4CrudController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/calc/payrollV4/PayrollDetailsList.html\";\r\n}\r\n","\r\nimport { ApiCrudObjectControllerBindings, PayrollCrudController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * Payroll (Palkkalista) is a list of employees who receive salary or wages from a particular organization.\r\n * Typical usecase is that a a company has e.g. a monthly salary list that is paid\r\n * at the end of month. For next month, a copy is then made from the latest list and\r\n * the copy is potentially modified with the changes of that particular month.\r\n * Payroll can also be started from scratch either by just writing salaries from\r\n * e.g. an e-mail or by uploading an Excel sheet.\r\n * @example\r\n * ```html\r\n * <salaxy-payroll-edit></salaxy-payroll-edit>\r\n * ```\r\n */\r\nexport class PayrollEdit extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = (new class extends ApiCrudObjectControllerBindings {\r\n    /** The action buttons shown by the component */\r\n    actions = \"<\";\r\n  }());\r\n\r\n  /** Uses the PayrollCrudController */\r\n  public controller = PayrollCrudController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/calc/payroll/PayrollEdit.html\";\r\n}\r\n","import { ApiCrudObjectControllerBindings, PayrollCrudController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * Payroll (Palkkalista) is a list of employees who receive salary or wages from a particular organization.\r\n * Typical usecase is that a a company has e.g. a monthly salary list that is paid\r\n * at the end of month. For next month, a copy is then made from the latest list and\r\n * the copy is potentially modified with the changes of that particular month.\r\n * Payroll can also be started from scratch either by just writing salaries from\r\n * e.g. an e-mail or by uploading an Excel sheet.\r\n * @example\r\n * ```html\r\n * <salaxy-payroll-list></salaxy-payroll-list>\r\n * ```\r\n */\r\nexport class PayrollList extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n\r\n  public bindings = (new class extends ApiCrudObjectControllerBindings {\r\n   /**\r\n    * Option to hide New payroll button.\r\n    * Set this true if the site has action buttons configured elsewhere.\r\n    */\r\n    public hideButton = \"<\";\r\n\r\n   /**\r\n    * Mode of the payroll. Supports \"service\" or default.\r\n    * In \"service\" mode the payroll has less funtionality and payment is disabled.\r\n    */\r\n    public mode = \"<\";\r\n  }());\r\n\r\n\r\n  /**\r\n   * Header is mainly meant for buttons (Usually at least \"Add new\").\r\n   * These are positioned to the right side of the table header (thead).\r\n   */\r\n  public transclude = {\r\n    header: \"?header\",\r\n  };\r\n\r\n  /** Uses the PayrollCrudController */\r\n  public controller = PayrollCrudController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/calc/payroll/PayrollList.html\";\r\n}\r\n","import { ODataQueryController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * Shows a list of calculations\r\n * @example\r\n * ```html\r\n * <salaxy-paryoll-select-list category=\"draft\" limit-to=\"5\"></salaxy-payroll-select-list>\r\n * ```\r\n */\r\nexport class PayrollSelectList extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n       /** Filters list by given field:value */\r\n      filter: \"@\",\r\n\r\n      /** Max count of calculations to show in the list. */\r\n      limitTo: \"<\",\r\n\r\n      /** Status category for the list. Possible categories: draft, paid. Default is paid */\r\n      category: \"@\",\r\n\r\n      /**\r\n       * List of statuses to include in the list.\r\n       * WARNING: This may be depricated in v03: Use category and/or $filter instead.\r\n       */\r\n      statusList: \"<\",\r\n\r\n      /**\r\n       * Function that is called when user selects an item in the list.\r\n       * Note that the event is called only in the selections (single and multi). Not when there is a link to details view in a link list.\r\n       * Function has the following locals: value: true/false, item: the last selected/unselected item, allItems: Array of all currently selected items.\r\n       * @example <salaxy-employment-list mode=\"select\" on-list-select=\"$ctrl.updateFromEmployment(item.id)\"></salaxy-employment-list>\r\n       */\r\n      onListSelect: \"&\",\r\n\r\n      /** Selected items for the case where the list is used as a select list (as opposed to link list). */\r\n      selectedItems: \"<\",\r\n\r\n      /** Type of the view. Currently supports \"default\", \"panel\" and \"select\" */\r\n      mode: \"@\",\r\n\r\n      /** OData query options */\r\n      options: \"<\",\r\n\r\n      /** URL to the OData service. */\r\n      url: \"@\",\r\n\r\n      /** Data passed from the parent to the component / view */\r\n      data: \"<\",\r\n\r\n       /** If readOnly is true, edit, copy etc. buttons from the new list view are hidden if readOnly property is supported */\r\n      readOnly: \"<\",\r\n\r\n      /**\r\n       * CRUD controller that implements Delete and potentially other methods about the object.\r\n       * If you wish to use this in the view use \"as $controllerName\" syntax\r\n       * @example\r\n       * <salaxy-odata-table crud-controller=\"CalculationCrudController as $crud\">\r\n       */\r\n      crudController: \"@\",\r\n\r\n    };\r\n\r\n    /** Uses the ODataQueryController */\r\n    public controller = ODataQueryController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/calc/payroll/PayrollSelectList.html\";\r\n\r\n}\r\n","import { ODataQueryController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * Shows a list of calculations\r\n * @example\r\n * ```html\r\n * <salaxy-payroll-details-select-list category=\"draft\" limit-to=\"5\"></salaxy-payroll-details-select-list>\r\n * ```\r\n */\r\nexport class PayrollDetailsSelectList extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n       /** Filters list by given field:value */\r\n      filter: \"@\",\r\n\r\n      /** Max count of calculations to show in the list. */\r\n      limitTo: \"<\",\r\n\r\n      /** Status category for the list. Possible categories: draft, paid. Default is paid */\r\n      category: \"@\",\r\n\r\n      /**\r\n       * List of statuses to include in the list.\r\n       * WARNING: This may be depricated in v03: Use category and/or $filter instead.\r\n       */\r\n      statusList: \"<\",\r\n\r\n      /**\r\n       * Function that is called when user selects an item in the list.\r\n       * Note that the event is called only in the selections (single and multi). Not when there is a link to details view in a link list.\r\n       * Function has the following locals: value: true/false, item: the last selected/unselected item, allItems: Array of all currently selected items.\r\n       * @example <salaxy-employment-list mode=\"select\" on-list-select=\"$ctrl.updateFromEmployment(item.id)\"></salaxy-employment-list>\r\n       */\r\n      onListSelect: \"&\",\r\n\r\n      /** Selected items for the case where the list is used as a select list (as opposed to link list). */\r\n      selectedItems: \"<\",\r\n\r\n      /** Type of the view. Currently supports \"default\", \"panel\" and \"select\" */\r\n      mode: \"@\",\r\n\r\n      /** OData query options */\r\n      options: \"<\",\r\n\r\n      /** URL to the OData service. */\r\n      url: \"@\",\r\n\r\n      /** Data passed from the parent to the component / view */\r\n      data: \"<\",\r\n\r\n       /** If readOnly is true, edit, copy etc. buttons from the new list view are hidden if readOnly property is supported */\r\n      readOnly: \"<\",\r\n\r\n      /**\r\n       * CRUD controller that implements Delete and potentially other methods about the object.\r\n       * If you wish to use this in the view use \"as $controllerName\" syntax\r\n       * @example\r\n       * <salaxy-odata-table crud-controller=\"CalculationCrudController as $crud\">\r\n       */\r\n      crudController: \"@\",\r\n\r\n    };\r\n\r\n    /** Uses the ODataQueryController */\r\n    public controller = ODataQueryController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/calc/payrollV4/PayrollDetailsSelectList.html\";\r\n\r\n}\r\n","\r\nimport { Payroll4AssistantController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * AI assitant for payroll.\r\n * @example\r\n * ```html\r\n * <salaxy-payroll-assistant model=\"$ctrl.current\"></salaxy-payroll-assistant>\r\n * ```\r\n */\r\nexport class PayrollAssistant extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n    /** Current payroll to assist */\r\n    current: \"<\",\r\n\r\n    /** Current page */\r\n    page: \"<\",\r\n  };\r\n\r\n  /** Uses the PayrollCrudController */\r\n  public controller = Payroll4AssistantController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/calc/payrollV4/PayrollAssistant.html\";\r\n}\r\n","import { CalcIrRowsController, Calculator2019Controller } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * Editor for Incomes Register (Tulorekisteri) rows from Calculation.\r\n * @example\r\n * ```html\r\n * <salaxy-calc-ir-rows model=\"'url'\"></salaxy-calc-ir-rows>\r\n * ```\r\n */\r\nexport class CalcIrRows extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = Calculator2019Controller.crudBindings;\r\n\r\n  /** Uses the CalcIrRowsController */\r\n  public controller = CalcIrRowsController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/calc/rows/CalcIrRows.html\";\r\n\r\n}\r\n","import { CalcRows2019Controller } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * Shows a grid-type rows editor for addding calculation rows: Salaries, expenses, benefits etc.\r\n * @example\r\n * ```html\r\n * <salaxy-calc-rows-2019-editor categories=\"['expenses']\" parent=\"$ctrl.currentCalc\" mode=\"edit\"\r\n *     title=\"Kulukorvaukset\"></salaxy-calc-rows-2019-editor>\r\n * ```\r\n */\r\nexport class CalcRows2019Editor extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = CalcRows2019Controller.bindings;\r\n\r\n    /** Uses the CalcRows2019Controller */\r\n    public controller = CalcRows2019Controller;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/calc/rows/CalcRows2019Editor.html\";\r\n\r\n}\r\n","import { CalcRowCostAccountingController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * Shows the cost accounting details for the calculation row.\r\n * @example\r\n * ```html\r\n * <salaxy-calc-row-cost-accounting parent=\"$ctrl.parent\" current=\"$ctrl.current\"></salaxy-calc-row-cost-accounting>\r\n * ```\r\n */\r\nexport class CalcRowCostAccounting extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {\r\n      /** Calculation for the row. */\r\n      calc: \"<\",\r\n      /** The calculation row. */\r\n      row: \"<\",\r\n      /** Forced read only state */\r\n      readOnly: \"<\",\r\n      /**\r\n       * Optional CostAccountingDimensionDefinitions\r\n       * If not set, cost accounting dimensions and their options are read from the settings.\r\n       */\r\n       dimensions: \"<\",\r\n    };\r\n\r\n    /** Uses the CalcRowCostAccountingController */\r\n    public controller = CalcRowCostAccountingController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/calc/rows/CalcRowCostAccounting.html\";\r\n}\r\n","import { CalcRowDimensionInputController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * Represents a component for handling dimension input in a calculation row.\r\n * @example\r\n * ```html\r\n * <salaxy-calc-row-dimension-input></salaxy-calc-row-dimension-input>\r\n * ```\r\n */\r\nexport class CalcRowDimensionInput extends ComponentBase {\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {\r\n      /** Currently edited row */\r\n      row: \"<\",\r\n      /** Dimension definition. */\r\n      definition: \"<\",\r\n      /** Possible inherited dimensions values from upper lever (e.g. calc level to rows) */\r\n      inherited: \"<\",\r\n      /** Forced read only state */\r\n      readOnly: \"<\",\r\n      /**\r\n       * Style of the inputs.\r\n       * Supports empty or 'openClose'. Only available when not readOnly\r\n       */\r\n      inputMode: \"@\",\r\n    };\r\n\r\n    /** Uses the CalcRowDimensionInputController */\r\n    public controller = CalcRowDimensionInputController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/calc/rows/CalcRowDimensionInput.html\";\r\n\r\n}\r\n","import { CalcsIrRowsController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * Component for showing tabulator based report of ir rows of given calculations\r\n * @example\r\n * ```html\r\n * <salaxy-calcs-ir-rows calcs=\"[calc1,calc2]\" lang=\"fi\"></salaxy-calcs-ir-rows calcs\r\n * ```\r\n */\r\nexport class CalcsIrRows extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n\r\n  public bindings = {\r\n    /** Calculations for report. */\r\n    calcs: \"<\",\r\n    /** The language of report. */\r\n    lang: \"<\"\r\n  };\r\n\r\n  /** Uses the CalcsIrRowsController */\r\n  public controller = CalcsIrRowsController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/calc/rows/CalcsIrRows.html\";\r\n\r\n}\r\n","import { CalcRowDocumentationController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * Generates documentation and examples for given row (UserDefinedRow)\r\n * @example\r\n * ```html\r\n * <salaxy-calc-row-documentation row=\"$ctrl.current\"></salaxy-calc-row-documentation>\r\n * ```\r\n */\r\nexport class CalcRowDocumentation extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {\r\n      /** The calculation row. */\r\n      row: \"<\"\r\n    };\r\n\r\n    /** Uses the CalcRowDocumentationController */\r\n    public controller = CalcRowDocumentationController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/calc/rows/CalcRowDocumentation.html\";\r\n}\r\n","import { CalcRowFormulaController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * Formula editor for a calculation row (UserDefinedRow).\r\n * @example\r\n * ```html\r\n * <salaxy-calc-row-formula row=\"$ctrl.current\"></salaxy-calc-row-formula>\r\n * ```\r\n */\r\nexport class CalcRowFormula extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {\r\n      /** The calculation row. */\r\n      row: \"<\"\r\n    };\r\n\r\n    /** Uses the CalcRowFormulaController */\r\n    public controller = CalcRowFormulaController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/calc/rows/CalcRowFormula.html\";\r\n}\r\n\r\n","import { Calculator2019Controller } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * The **salaxy.ng1.components.Calc** is the generic Angular-based salary calculator implementation.\r\n * It shows the basic features required for a salary calculator user interfaces:\r\n *\r\n * 1. Setting the Worker for the calculation\r\n * 2. Defining the Worktime information: Period, Absences and holidays.\r\n * 3. Defining the Salary and the benefits\r\n * 4. Defining Expenses, benefits, household subsidies etc.\r\n * 5. Showing the results as charts and reports.\r\n *\r\n * Controllers are defined in **salaxy.ng1.controllers**. Most of the functionality comes from Calculator2019Controller.\r\n * The views can be modified separately for each component using the templateUrl. See documentation for details.\r\n * @example\r\n * ```html\r\n * <salaxy-calc model=\"'new'\"></salaxy-calc>\r\n * ```\r\n */\r\nexport class Calc extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = Calculator2019Controller.crudBindings;\r\n\r\n    /** Uses the Calculator2019Controller */\r\n    public controller = Calculator2019Controller;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/calc/Calc.html\";\r\n\r\n}\r\n","import { CalcChartController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Chart.js based chart.\r\n * @example\r\n * ```html\r\n * <salaxy-calc-chart role=\"worker\" calc=\"$ctrl.currentCalc\"></salaxy-calc-chart>\r\n * ```\r\n */\r\nexport class CalcChart extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n\r\n  public bindings = {\r\n\r\n    /** Calculation for which the chart is rendered.  */\r\n    calc: \"<\",\r\n    /** Role for which the chart is rendered. Currently, 'worker' and 'employer' are supported. Employer is the default. */\r\n    role: \"@\",\r\n    /** If true, the Y axis of this chart is scaled so that if worker and employer charts are side to side, their Y axis are the same */\r\n    scaleYAxis: \"<\",\r\n    /** Type of the chart - \"pie\" and \"bar\" (default) are currently supported. */\r\n    chartType: \"<\",\r\n    /** - colors: Custom colors for the chart as a string containing hex values of the colors, separated by comma */\r\n    colors: \"@\",\r\n  };\r\n\r\n  /** Uses the CalcChartController */\r\n  public controller = CalcChartController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/calc/CalcChart.html\";\r\n}\r\n","import { ODataQueryController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows lists of calculations\r\n * @example\r\n * ```html\r\n * <salaxy-calc-dashboard></salaxy-calc-dashboard>\r\n * ```\r\n */\r\n\r\nexport class CalcDashboard extends ComponentBase {\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n\r\n  public bindings = {\r\n    /**\r\n     * Option to hide new calc button.\r\n     * Set this true if the site has action buttons configured elsewhere.\r\n     */\r\n    hideButton: \"<\",\r\n\r\n    /** If readOnly is true, edit, copy etc. buttons from the new list view are hidden if readOnly property is supported */\r\n    readOnly: \"<\",\r\n\r\n  };\r\n\r\n  /** Uses the ODataQueryController */\r\n  public controller = ODataQueryController;\r\n  // TODO: Consider should this be ODataQueryController or ApiCrudObjectController.\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/calc/CalcDashboard.html\";\r\n\r\n}\r\n","import { ODataQueryController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a list of calculations\r\n * @example\r\n * ```html\r\n * <salaxy-calc-list category=\"draft\" limit-to=\"5\"></salaxy-calc-list>\r\n * ```\r\n */\r\nexport class CalcList extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n       /** Filters list by given field:value */\r\n      filter: \"@\",\r\n\r\n      /** Max count of calculations to show in the list. */\r\n      limitTo: \"<\",\r\n\r\n      /** Status category for the list. Possible categories: draft, paid. Default is paid */\r\n      category: \"@\",\r\n\r\n      /**\r\n       * List of statuses to include in the list.\r\n       * WARNING: This may be depricated in v03: Use category and/or $filter instead.\r\n       */\r\n      statusList: \"<\",\r\n\r\n      /**\r\n       * Function that is called when user selects an item in the list.\r\n       * Note that the event is called only in the selections (single and multi). Not when there is a link to details view in a link list.\r\n       * Function has the following locals: value: true/false, item: the last selected/unselected item, allItems: Array of all currently selected items.\r\n       * @example <salaxy-employment-list mode=\"select\" on-list-select=\"$ctrl.updateFromEmployment(item.id)\"></salaxy-employment-list>\r\n       */\r\n      onListSelect: \"&\",\r\n\r\n      /** Selected items for the case where the list is used as a select list (as opposed to link list). */\r\n      selectedItems: \"<\",\r\n\r\n      /** Type of the view. Currently supports \"default\", \"panel\" and \"select\" */\r\n      mode: \"@\",\r\n\r\n      /** OData query options */\r\n      options: \"<\",\r\n\r\n      /** URL to the OData service. */\r\n      url: \"@\",\r\n\r\n      /** Data passed from the parent to the component / view */\r\n      data: \"<\",\r\n\r\n       /** If readOnly is true, edit, copy etc. buttons from the new list view are hidden if readOnly property is supported */\r\n      readOnly: \"<\",\r\n\r\n      /**\r\n       * CRUD controller that implements Delete and potentially other methods about the object.\r\n       * If you wish to use this in the view use \"as $controllerName\" syntax\r\n       * @example\r\n       * <salaxy-odata-table crud-controller=\"CalculationCrudController as $crud\">\r\n       */\r\n      crudController: \"@\",\r\n\r\n    };\r\n\r\n    /** Uses the ODataQueryController */\r\n    public controller = ODataQueryController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/calc/CalcList.html\";\r\n\r\n}\r\n","import { Calculator2019Controller } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows an introduction text (instructions) for the user when user starts a new calculation.\r\n * @example\r\n * ```html\r\n * <salaxy-calc-new-intro model=\"$ctrl.current\"></salaxy-calc-new-intro>\r\n * ```\r\n */\r\nexport class CalcNewIntro extends ComponentBase {\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = Calculator2019Controller.crudBindings;\r\n\r\n    /** Uses the Calculator2019Controller */\r\n    public controller = Calculator2019Controller;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/calc/CalcNewIntro.html\";\r\n\r\n}\r\n","import { CalcReportController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the report for the given calculation.\r\n * @example\r\n * ```html\r\n * <salaxy-calc-report calc=\"$ctrl.currentCalc\" report-type=\"'salarySlip'\" template-name=\"'salarySlipV2'\"></salaxy-calc-report>\r\n * ```\r\n */\r\nexport class CalcReport extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n    /** The calculation for the report. */\r\n    calc: \"<\",\r\n    /** Calculation report type (for example: salarySlip, employerReport or paymentReport) */\r\n    reportType: \"<\",\r\n    /** Template for the report (for example: salarySlipV2, employerReportV2, paymentReportV2 ) */\r\n    templateName: \"<\",\r\n    /** If true, uses the current style of the site. The default value is false. */\r\n    applySiteStyles: \"<\",\r\n    /** The language for report*/\r\n    lang: \"<\",\r\n    /** If true, adds the preview watermark to the report */\r\n    preview: \"<\",\r\n    /** Called when the report type has been changed. */\r\n    onReportTypeChange: \"&\",\r\n  };\r\n\r\n  /** Uses the CalcReportController */\r\n  public controller = CalcReportController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/calc/CalcReport.html\";\r\n\r\n}\r\n","import { CalcReportsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the salary reports for the given calculations.\r\n * @example\r\n * ```html\r\n * <salaxy-calc-reports calcs=\"$ctrl.calcs\" report-type=\"'salarySlip'></salaxy-calc-reports>\r\n * ```\r\n */\r\nexport class CalcReports extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n    /** The calculations for the report. */\r\n    calcs: \"<\",\r\n    /** Current report type. */\r\n    reportType: \"<\",\r\n    /**\r\n     * The default view shown in the UI: \"partial\" (default), \"page1\" or \"full\".\r\n     * Please note that not all reports support \"page1\" or \"full\".\r\n     */\r\n    view: \"@\",\r\n    /** If true, adds the preview watermark to the report */\r\n    preview: \"<\",\r\n    /** Called when the report type has been changed. */\r\n    onReportTypeChange: \"&\",\r\n  };\r\n\r\n  /** Uses the CalcReportsController */\r\n  public controller = CalcReportsController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/calc/CalcReports.html\";\r\n\r\n}\r\n","import { Calculator2019Controller } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the results view for the Calculator\r\n * @example\r\n * ```html\r\n * <salaxy-calc-results model=\"$ctrl.current\"></salaxy-calc-results>\r\n * ```\r\n */\r\nexport class CalcResults extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n    public bindings = Calculator2019Controller.crudBindings;\r\n\r\n    /** Uses the Calculator2019Controller */\r\n    public controller = Calculator2019Controller;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/calc/CalcResults.html\";\r\n\r\n}\r\n","import { CalcRowTypeController } from \"../../controllers\";\r\n\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Select component for Calculations row types.\r\n * @example\r\n * ```html\r\n * <salaxy-calc-row-type name=\"rowType\" model=\"row\" label=\"Basic datepicker\"></salaxy-calc-row-type>\r\n * ```\r\n */\r\nexport class CalcRowType extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n\r\n      /** Type of the input element. Options are typeahead and list (select, search-list and radio may be supported later). */\r\n      type: \"@\",\r\n\r\n      /** If set, filters the rows based on categories (plus rowTypes if set) */\r\n      categories: \"<\",\r\n\r\n      /** If set, shows only these types (plus categories if set) */\r\n      rowTypes: \"<\",\r\n\r\n      /** Name and identifier of the typeahead input */\r\n      name: \"@\",\r\n\r\n      /**\r\n       * Placeholder text in the typeahead input.\r\n       * Default is 'SALAXY.UI_Terms.select'.\r\n       */\r\n      placeholder: \"@\",\r\n\r\n      /** The calculation row that this component modifies. */\r\n      model: \"<\",\r\n\r\n      /**\r\n       * Function that is called after the row type and potentially kind and message have been changed.\r\n       * @example <salaxy-calc-row-type on-row-changed=\"$ctrl.commitNewRow()\"></salaxy-calc-row-type>\r\n       */\r\n      onRowChanged: \"&\",\r\n\r\n      /** If true, the list will show all the children under each parent that is shown */\r\n      showChildren: \"<\",\r\n\r\n      /** Normally (default true), the selected value is cleared and a row is created/added, but in some cases (false) the value is saved as-is (and not cleared - the typical typeahead element behaviour). */\r\n      clearOnSelect: \"<\"\r\n    };\r\n\r\n    /** Uses the InputCalcRowTypeController */\r\n    public controller = CalcRowTypeController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/calc/CalcRowType.html\";\r\n}\r\n","import { ApiCrudObjectControllerBindings, CalcSharingReceiptActionController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the sharing receipt action control for the given calculation id.\r\n * @example\r\n * ```html\r\n * <salaxy-calc-sharing-receipt-action model=\"$ctrl\" type=\"'approve'\"></salaxy-calc-sharing-receipt-action>\r\n * ```\r\n */\r\nexport class CalcSharingReceiptAction extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = (new class extends ApiCrudObjectControllerBindings {\r\n    /** Sharing action (approve or reject) */\r\n    public type = \"<\";\r\n    /** Disables the control. */\r\n    public disabled = \"<\";\r\n    /** Optional style class to use for button. Defaults to 'btn-block btn-sm' */\r\n    public buttonClass = \"@\";\r\n    /** Shows only icon in button. Used in compact views, i.e. panels */\r\n    public iconOnly = \"<\";\r\n  }());\r\n\r\n  /** Uses the CalcSharingReceiptActionController */\r\n  public controller = CalcSharingReceiptActionController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/calc/CalcSharingReceiptAction.html\";\r\n\r\n}\r\n","import { CalcLeavesController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Displays payments for current calculation period.\r\n * @example\r\n * ```html\r\n * <salaxy-calc-leaves ng-ref=\"$calcLeaves\" calc=\"$ctrl.current.calc\" worktime=\"$ctrl.current.worktime\"></salaxy-calc-leaves>\r\n * ```\r\n */\r\nexport class CalcLeaves extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {\r\n      /** The calculation*/\r\n      calc: \"<\",\r\n      /** The worktime*/\r\n      worktime: \"<\",\r\n    };\r\n\r\n    /** Uses the CalcLeavesController */\r\n    public controller = CalcLeavesController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/calc/CalcLeaves.html\";\r\n\r\n}\r\n","import { Calculator2019Controller } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows information about the Worker / employment relation within a calculation.\r\n * @example\r\n * ```html\r\n * <salaxy-calc-worker-info model=\"$ctrl.myWorkerOrCalc\"></salaxy-calc-worker-info>\r\n * ```\r\n */\r\nexport class CalcWorkerInfo extends ComponentBase {\r\n\r\n  // TODO: If the component is removed from payment pages, consider having it simply as an include within calculations\r\n  // (and not as a component) OR consider having a calc-component with several different layouts.\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = Calculator2019Controller.crudBindings;\r\n\r\n  /** Uses the Calculator2019Controller */\r\n  public controller = Calculator2019Controller;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/calc/CalcWorkerInfo.html\";\r\n\r\n}\r\n","import { CalcWorktimeController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * UI for setting the Worktime properties within the calculator\r\n * The process starts by selecting the period based on which relevatn worktime\r\n * data is fetched: Holidays, Absences and later Hours.\r\n * Calculation rows are then added based on this worktime.\r\n * @example\r\n * ```html\r\n * <salaxy-calc-worktime calc=\"$ctrl.currentCalc\"></salaxy-calc-worktime>\r\n * ```\r\n */\r\nexport class CalcWorktime extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {\r\n      /** The calculation that the component edits (shows in read-only mode). */\r\n      calc: \"<\",\r\n    };\r\n\r\n    /** Uses the CalcWorktimeController */\r\n    public controller = CalcWorktimeController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/calc/CalcWorktime.html\";\r\n\r\n}\r\n","import { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Renders a Payment -button or Payment Channel selection dropdown or both for the Calculation or Payroll\r\n * @example\r\n * ```html\r\n * <salaxy-pay-button model=\"$ctrl.current\"></salaxy-pay-button>\r\n * ```\r\n */\r\nexport class PayButton extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n\r\n      /**\r\n       * The current business item that is being paid: Either Calculation or PayrollDetails.\r\n       * Currently only supports direct reference. May later support 'url' etc. like CRUD controllers.\r\n       */\r\n      model: \"<\",\r\n\r\n      /** Expression for ng-disabled of the input. */\r\n      disabled: \"<\",\r\n\r\n      /**\r\n       * Additional class / classes for button. Can also be used to override default btn-primary class styles.\r\n       * (i.e. <salaxy-pay-button button-class=\"btn-lg uppercase btn-success\">)\r\n       */\r\n      buttonClass: \"@\",\r\n\r\n      /**\r\n       * Text for the payment button.\r\n       * This is typically customized in custom payment scenarios.\r\n       */\r\n      label: \"@\",\r\n\r\n      /** Mode is either \"pay-button\" (default), \"channel-select\", \"button-and-channel\" or \"button-and-channel-horizontal\" */\r\n      mode: \"@\",\r\n\r\n      /** Called when the payment channel has been changed. */\r\n      onPaymentChannelChange: \"&\",\r\n    };\r\n\r\n    /**\r\n     * Uses the PaymentController\r\n     * This is on purpose not typed. This is because we want the injection to be active for possible customer\r\n     * specific overrides.\r\n     */\r\n    public controller = \"PaymentController\";\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/calc/PayButton.html\";\r\n}\r\n","import { CalculationEditorController, ApiCrudObjectControllerBindings } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Editor for the given calculation.\r\n * @example\r\n * ```html\r\n * <salaxy-calc-editor model=\"'url'\"></salaxy-calc-editor>\r\n * ```\r\n */\r\nexport class CalcEditor extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = (new class extends ApiCrudObjectControllerBindings {\r\n\r\n\r\n\r\n    }());\r\n\r\n    /** Uses the CalcReportController */\r\n    public controller = CalculationEditorController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/calc/CalcEditor.html\";\r\n\r\n}\r\n","import { CalcCostAccountingController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the cost accounting details for the calculation.\r\n * @example\r\n * ```html\r\n * <salaxy-calc-cost-accounting current=\"$ctrl.current\"></salaxy-calc-cost-accounting>\r\n * ```\r\n */\r\nexport class CalcCostAccounting extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {\r\n      /** The calculation. */\r\n      calc: \"<\",\r\n      /** Forced read only state */\r\n      readOnly: \"<\",\r\n      /**\r\n       * Optional CostAccountingDimensionDefinitions\r\n       * If not set, cost accounting dimensions and their options are read from the settings.\r\n       */\r\n      dimensions: \"<\",\r\n\r\n      /**\r\n       * Style of the inputs.\r\n       * Supports empty or 'openClose'. Only available in not readOnly\r\n       */\r\n      inputMode: \"@\",\r\n    };\r\n\r\n    /** Uses the CalcCostAccountingController */\r\n    public controller = CalcCostAccountingController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/calc/CalcCostAccounting.html\";\r\n\r\n}\r\n","import { CostAccountingController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the cost accounting details for the calculation.\r\n * @example\r\n * ```html\r\n * <salaxy-cost-accounting current=\"calc.accounting.dimensions\" scope=\"calculation\"></salaxy-cost-accounting>\r\n * ```\r\n */\r\nexport class CostAccounting extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {\r\n      /** Dimension values for edit. */\r\n      current: \"<\",\r\n\r\n      /** Possible inherited dimensions values from upper lever (e.g. calc level to rows) */\r\n      inherited: \"<\",\r\n\r\n      /** Forced read only state */\r\n      readOnly: \"<\",\r\n      /**\r\n       * Optional CostAccountingDimensionDefinitions\r\n       * If not set, cost accounting dimensions and their options are read from the settings.\r\n       */\r\n      dimensions: \"<\",\r\n      /**\r\n       * Scope for the cost accounting: calculation or row.\r\n       */\r\n      scope: \"@\",\r\n\r\n      /**\r\n       * Style of the inputs.\r\n       * Supports empty or 'openClose'. Only available when not readOnly\r\n       */\r\n      inputMode: \"@\"\r\n    };\r\n\r\n    /** Uses the CostAccountingController */\r\n    public controller = CostAccountingController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/calc/CostAccounting.html\";\r\n\r\n}\r\n","import { ComponentBase } from \"../_ComponentBase\";\r\nimport { SalaryDateKindController } from \"../../controllers\";\r\n\r\n/**\r\n * Renders a Salary Date Kind selection -button for the Calculation or Payroll\r\n * @example\r\n * ```html\r\n * <salaxy-salary-date-kind-button disabled=\"$ctrl.isReadOnly\" model=\"$ctrl.current.workflow\"></salaxy-salary-date-kind-button>\r\n * ```\r\n */\r\nexport class SalaryDateKindButton extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n\r\n      /**\r\n       * The current object containing salaryDateKind -field: Either Calculation or PayrollDetails.\r\n       */\r\n      model: \"<\",\r\n\r\n      /** Expression for ng-disabled of the input. */\r\n      disabled: \"<\",\r\n\r\n      /**\r\n       * Additional class / classes for button. Can also be used to override default btn-primary class styles.\r\n       * (i.e. <salaxy-pay-button button-class=\"btn-lg uppercase btn-success\">)\r\n       */\r\n      buttonClass: \"@\",\r\n\r\n      /** Called when the salary date kind has been changed. */\r\n      onSalaryDateKindChange: \"&\",\r\n    };\r\n\r\n    /**\r\n     * Uses the SalaryDateKindController\r\n     */\r\n    public controller = SalaryDateKindController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/calc/SalaryDateKindButton.html\";\r\n}\r\n","import { CalcRepairController, ApiCrudObjectControllerBindings } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Editor for repairing the given calculation.\r\n * @example\r\n * ```html\r\n * <salaxy-calc-repair model=\"'url'\"></salaxy-calc-repair>\r\n * ```\r\n */\r\nexport class CalcRepair extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = (new class extends ApiCrudObjectControllerBindings {\r\n\r\n\r\n\r\n    }());\r\n\r\n    /** Uses the CalcReportController */\r\n    public controller = CalcRepairController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/calc/CalcRepair.html\";\r\n\r\n}\r\n","import { ApiCrudObjectControllerBindings, CalcRepairInfoController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the repair info for the current calculation.\r\n * @example\r\n * ```html\r\n * <salaxy-calc-repair-info model=\"$ctrl\"></salaxy-calc-repair-info>\r\n * ```\r\n */\r\nexport class CalcRepairInfo extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = (new class extends ApiCrudObjectControllerBindings {\r\n    }());\r\n\r\n\r\n  /** Uses the CalcRepairInfoController */\r\n  public controller = CalcRepairInfoController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/calc/CalcRepairInfo.html\";\r\n\r\n}\r\n","import { ContactInfoController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the customer service contact info and reference to zendesk's help-widget.\r\n * Options to show short content and hide contact info.\r\n * @example\r\n * ```html\r\n * <salaxy-contact-info></salaxy-contact-info>\r\n * ```\r\n */\r\nexport class ContactInfo extends ComponentBase {\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n\r\n    /** If true, short version of the content is shown */\r\n    showShortContent: \"=\",\r\n\r\n    /** If true, contact info is hidden */\r\n    hideContactInfo: \"<\",\r\n  };\r\n  /** Uses the AlertController */\r\n  public controller = ContactInfoController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/communications/ContactInfo.html\";\r\n}\r\n","import { ApiCrudObjectControllerBindings } from \"../../controllers/bases\";\r\nimport { MessageThreadCrudController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Edit and create new user interface for message thread.\r\n * @example\r\n * ```html\r\n * <salaxy-message-thread></salaxy-message-thread>\r\n * ```\r\n */\r\nexport class MessageThread extends ComponentBase {\r\n\r\n  /**\r\n   * Allows injecting HTML within the component.\r\n   */\r\n  public transclude = {\r\n    /** A \"header\" element can be used to add HTML on top of the message thread (where the header is now). */\r\n    header: \"?header\",\r\n    /** A \"header-new\" element overrides the default text for new message thread. */\r\n    headerNew: \"?headerNew\",\r\n  };\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = (new class extends ApiCrudObjectControllerBindings {\r\n\r\n    /** Role of the current user: typically \"owner\" (default) or \"otherParty\" */\r\n    public role = \"@\";\r\n\r\n    /** Salaxy ID (IBAN format) for the other party (besides the message thread owner) */\r\n    public otherParty = \"<\";\r\n\r\n    /**\r\n     * If set, shows a drop-down for these options using the enum component.\r\n     * Typically, use object with string key-value pairs.\r\n     */\r\n    public otherPartyOptions = \"<\";\r\n\r\n    /**\r\n     * If set, the controller will mark a message thread as open once it has been loaded.\r\n     * If the value is true, the message is marked as read immediately.\r\n     * If the value is number, the controller waits the given amount of seconds before marking the item as read.\r\n     */\r\n    public markAsRead = \"<\";\r\n\r\n    /**\r\n     * URL for the approval view.\r\n     */\r\n    public approvalUrl = \"@\";\r\n\r\n  }());\r\n\r\n  /** Uses the EmailMessageController */\r\n  public controller = MessageThreadCrudController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/communications/MessageThread.html\";\r\n\r\n}\r\n","import { VarmaBannerController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Varma banner component for displaying Varma popup\r\n * @example\r\n * ```html\r\n * <salaxy-varma-banner></salaxy-varma-banner>\r\n * ```\r\n */\r\nexport class VarmaBanner extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n      /** Current calculation */\r\n      calc: \"<\"\r\n\r\n    };\r\n\r\n    /** Uses the VarmaBannerController */\r\n    public controller = VarmaBannerController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/communications/VarmaBanner.html\";\r\n\r\n}\r\n","import { WelcomeController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a detail a Welcome message depending on the user profile.\r\n * Typically the first component on the front page.\r\n * @example\r\n * ```html\r\n * <salaxy-welcome></salaxy-welcome>\r\n * ```\r\n */\r\nexport class Welcome extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n        /**\r\n         * If set to true, the settings are handled by proxy:\r\n         * we do not ask the user to change the settings in\r\n         * the Welcome screen (mainly Pension or Insurance).\r\n         */\r\n        settingsByProxy: \"<\",\r\n    };\r\n\r\n    /** Uses the WelcomeController */\r\n    public controller = WelcomeController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/communications/Welcome.html\";\r\n\r\n}\r\n","import { WorkerHourlyReportController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * Component for HourlyReport usecase\r\n * @example\r\n * ```html\r\n * <salaxy-hourly-report></salaxy-hourly-report>\r\n * ```\r\n */\r\nexport class HourlyReport extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n     public bindings = WorkerHourlyReportController.bindings;\r\n\r\n    /** Uses the WorkerHourlyReportController */\r\n    public controller = WorkerHourlyReportController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/communications/messages/message-types/HourlyReport.html\";\r\n\r\n}\r\n","import {\r\n  ListControllerBaseBindings,\r\n  WorkerTimerController,\r\n} from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\nclass TimerBindings extends ListControllerBaseBindings {\r\n  /** The calculation that the component edits (shows in read-only mode). */\r\n  timerMode = \"@\";\r\n  /**\r\n   * CRUD controller that typically defines the values for url template and\r\n   */\r\n  public crudController = \"<\";\r\n}\r\n/**\r\n * Component for timer usecase\r\n * @example\r\n * ```html\r\n * <salaxy-timer></salaxy-timer>\r\n * ```\r\n */\r\nexport class Timer extends ComponentBase {\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = new TimerBindings();\r\n\r\n  /** Uses the WorkerTimerController */\r\n  public controller = WorkerTimerController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate =\r\n    \"salaxy-components/communications/messages/message-types/Timer.html\";\r\n}\r\n","import { WorkerExpenseReportController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * Component for ExpenseReport usecase\r\n * @example\r\n * ```html\r\n * <salaxy-expense-report ng-if=\"$ctrl.current\" parent=\"$ctrl.getMessage().contentData\" report-type=\"$ctrl.current.usecase.data.protoId\"></salaxy-expense-report>\r\n * ```\r\n */\r\nexport class ExpenseReport extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n     public bindings = WorkerExpenseReportController.bindings;\r\n\r\n    /** Uses the WorkerExpenseReportController */\r\n    public controller = WorkerExpenseReportController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/communications/messages/message-types/ExpenseReport.html\";\r\n\r\n}\r\n","import { ODataQueryController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n\r\n/**\r\n * Shows a list of messages.\r\n * @example\r\n * ```html\r\n * <salaxy-message-thread-list limit-to=\"5\" read-only=\"false\"></salaxy-message-thread-list>\r\n * ```\r\n */\r\nexport class MessageThreadList extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n\r\n    /** Max count of threads to show in the list. */\r\n    limitTo: \"<\",\r\n\r\n    /** If readOnly is true, create buttons from the list view are hidden if readOnly property is supported */\r\n    readOnly: \"<\",\r\n\r\n    /**\r\n     * URL for the approval view.\r\n     */\r\n    approvalUrl: \"@\",\r\n\r\n  };\r\n\r\n    /** Uses the ODataQueryController */\r\n    public controller = ODataQueryController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/communications/MessageThreadList.html\";\r\n\r\n}\r\n","import { DatepickerController, InputBase } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\nimport { Objects } from \"@salaxy/core\";\r\n\r\n/**\r\n * Modified ui.bootstrap.datepicker.\r\n * The component can be bound to a string typed variable.\r\n * @example\r\n * ```html\r\n * <salaxy-datepicker name=\"myDatepicker\" ng-model=\"temp\" label=\"Basic datepicker\"></salaxy-datepicker>\r\n * ```\r\n */\r\nexport class Datepicker extends ComponentBase {\r\n\r\n  /** ng-model is required, form tag is optionally used for validation and disabled/readonly */\r\n  public require = {\r\n    model: \"ngModel\",\r\n    form: \"?^^form\",\r\n  };\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = Objects.extend(InputBase.crudBindings, {\r\n    /**\r\n     * Preset algorithms for enabled/disabled dates.\r\n     * Currently, \"salary\" and \"next-weekday\" are implemented.\r\n     * If set as \"disable-function\", you should set the disable-function too.\r\n     */\r\n    dateDisabled: \"@\",\r\n\r\n    /** Disable function for date. If set, date-disabled is ignored. */\r\n    disableFunction: \"<\",\r\n\r\n    /** Payment channel. This affects which dates are disabled in the salary date selection. */\r\n    paymentChannel: \"<\",\r\n\r\n    /** Zero payment (no worker net salary payment). This affects which dates are disabled in the salary date selection. */\r\n    zeroPayment: \"<\",\r\n\r\n    /**\r\n     * Minimum available date.\r\n     * Bindable and ISO string version of the datepicker-options.minDate.\r\n     * Currently not supported together with dateDisabled filters.\r\n     */\r\n    minDate: \"<\",\r\n\r\n    /**\r\n     * Maximum available date.\r\n     * Bindable and ISO string version of the datepicker-options.maxDate.\r\n     * Currently not supported together with dateDisabled filters.\r\n     */\r\n    maxDate: \"<\",\r\n\r\n    /**\r\n     * If true, can pick multiple dates from the selector.\r\n     */\r\n    isMultiple: \"<\",\r\n\r\n    /**\r\n     * Whether to show timepicker alongside the calendar.\r\n     */\r\n    timepicker: \"<\",\r\n\r\n    /**\r\n     * Whether to show Today/Clear buttons below the calendar.\r\n     */\r\n    showButtons: \"<\",\r\n\r\n    /**\r\n     * External value that causes the disabled dates function to re-run.\r\n     */\r\n    updateDisabledDates: \"<\",\r\n\r\n    /** ng-change callback */\r\n    ngChange: \"&?\",\r\n  });\r\n\r\n  /** Uses the DatepickerController */\r\n  public controller = DatepickerController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/form-controls/Datepicker.html\";\r\n}\r\n","import { DatepickerPopupController, InputBase } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\nimport { Objects } from \"@salaxy/core\";\r\n\r\n/**\r\n * Modified ui.bootstrap.datepickerPopup.\r\n * The component can be bound to a string typed variable. The standard ui.bootstrap.datepickerPopup can be bound successfully only to a Date variable.\r\n * @example\r\n * ```html\r\n *\r\n * <salaxy-datepicker-popup name=\"myDatepickerPopup\" ng-model=\"temp\" label=\"Basic datepicker popup\"></salaxy-datepicker-popup>\r\n * ```\r\n */\r\nexport class DatepickerPopup extends ComponentBase {\r\n\r\n  /** ng-model is required, form tag is optionally used for validation and disabled/readonly */\r\n  public require = {\r\n    model: \"ngModel\",\r\n    form: \"?^^form\",\r\n  };\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = Objects.extend(InputBase.crudBindings, {\r\n    /** Format for the date, default is d.M.yyyy */\r\n    format: \"@\",\r\n\r\n    /**\r\n     * Preset algorithms for enabled/disabled dates.\r\n     * Currently, only \"salary\" is supported for salary dates, but more might be added later.\r\n     * If set as \"disable-function\", you should set the disable-function too.\r\n     */\r\n    dateDisabled: \"@\",\r\n\r\n    /** Disable function for date. If set, date-disabled is ignored. */\r\n    disableFunction: \"<\",\r\n\r\n    /** Payment channel. This affects which dates are disabled in the salary date selection. */\r\n    paymentChannel: \"<\",\r\n\r\n    /** Zero payment (no worker net salary payment). This affects which dates are disabled in the salary date selection. */\r\n    zeroPayment: \"<\",\r\n\r\n    /**\r\n     * Minimum available date.\r\n     * Bindable and ISO string version of the datepicker-options.minDate.\r\n     * Currently not supported together with dateDisabled filters.\r\n     */\r\n    minDate: \"<\",\r\n\r\n    /**\r\n     * Maximum available date.\r\n     * Bindable and ISO string version of the datepicker-options.maxDate.\r\n     * Currently not supported together with dateDisabled filters.\r\n     */\r\n    maxDate: \"<\",\r\n\r\n    /** ng-change callback */\r\n    ngChange: \"&?\",\r\n\r\n    /**\r\n     * External value that causes the disabled dates function to re-run.\r\n     */\r\n    updateDisabledDates: \"<\",\r\n  });\r\n\r\n  /** Uses the DatepickerController */\r\n  public controller = DatepickerPopupController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/form-controls/DatepickerPopup.html\";\r\n}","import { Objects } from \"@salaxy/core\";\r\n\r\nimport { DateRangeController, InputBase } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Provides a user interface for picking up a date range\r\n * and optionally specifying also the number of working days within that range.\r\n * @example\r\n * ```html\r\n * <salaxy-date-range name=\"myDateRange\" ng-model=\"temp\" label=\"Sample date range\"></salaxy-date-range>\r\n * ```\r\n */\r\nexport class DateRange extends ComponentBase {\r\n\r\n  /** ng-model is required, form tag is optionally used for validation and disabled/readonly */\r\n  public require = {\r\n    model: \"ngModel\",\r\n    form: \"?^^form\",\r\n  };\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = Objects.extend(InputBase.crudBindings, {\r\n    /**\r\n     * Label for the scondary input (Default: SALAXY.NG1.DateRange.labelDaysCount).\r\n     * Translation is attempted.\r\n     */\r\n    labelDaysCount: \"@\",\r\n\r\n    /**\r\n     * The selection mode is either:\r\n     *\r\n     * - \"range\" for (default) calendar control with start and end.\r\n     * - \"calc\" for period selection that is optimized for salary calculation (months, 2 weeks, 1/2 months etc.)\r\n     */\r\n    mode: \"@\",\r\n\r\n    /**\r\n     * Fires an event when the model is changing: Any of the values specific to the model are changing: start, end or daysCount.\r\n     * This should typically used instead of ng-change because ng-change will only fire if the object reference changes.\r\n     * On-change fires when dates or day count changes and this is typically what you are looking for.\r\n     * @example <salaxy-date-range ng-model=\"$ctrl.dateRange\" on-change=\"$ctrl.dateRangeChange()\"></salaxy-date-range>\r\n     */\r\n    onChange: \"&\",\r\n\r\n    /**\r\n     * The data range values: start, end, daysCount and formattedDate.\r\n     */\r\n    dateRangeValues: \"<\"\r\n  });\r\n\r\n  /** Uses the DateRangeController */\r\n  public controller = DateRangeController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/form-controls/DateRange.html\";\r\n}","import { FormGroupController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Helper for rendering the HTML for FormGroup:\r\n * This component renders only the label - input html.\r\n * It does not do any of the real form-control logic like ng-model, validations etc. (see salaxy-input for that).\r\n * The \"input\" part of the form group may be a non form control - e.g. just a text.\r\n * Also the label may be hidden.\r\n * @example\r\n * ```html\r\n * <salaxy-form-group label=\"Some label\" class=\"salaxy-read-only\" name=\"div1\"><div class=\"salaxy-read-only-value\">Some text here</div></salaxy-form-group>\r\n * ```\r\n */\r\nexport class FormGroup extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n    /** Name of the input - also used as id. */\r\n    name: \"@\",\r\n\r\n    /** Label for the control */\r\n    label: \"@\",\r\n\r\n    /**\r\n     * @deprecated Use \"require\" instead:\r\n     * This attribute overlaps with required/ng-required directive, which produces unexpected results.\r\n     */\r\n    required: \"@\",\r\n\r\n    /** If true the field is required (form validation) */\r\n    require: \"<\",\r\n\r\n    /**\r\n     * Positioning of the label of form-control.\r\n     * Supported values are \"horizontal\" (default), \"no-label\", \"plain\", \"basic\" and \"empty-label\".\r\n     * See FormGourpLabelType for details.\r\n     */\r\n    labelType: \"@\",\r\n\r\n    /**\r\n     * Label columns expressed as Bootstrap grid columns.\r\n     * Default is 'col-sm-4' for label-type: 'horizontal' and 'col-sm-12' for label-type: 'no-label'.\r\n     * Other label-types do not have column classes at the moment.\r\n     */\r\n    labelCols: \"@\",\r\n  };\r\n\r\n  /** Contents of the tag is the input element. */\r\n  public transclude = true;\r\n\r\n  /** Uses the InputController */\r\n  public controller = FormGroupController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/form-controls/FormGroup.html\";\r\n}\r\n","import { InputBase, InputController } from \"../../controllers\";\r\n\r\nimport { Objects } from \"@salaxy/core\";\r\n\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows an input control with label, validation error, info etc.\r\n *\r\n * Basic label-input control for forms.\r\n * @example\r\n * ```html\r\n * <salaxy-input name=\"myInput\" ng-model=\"temp\" label=\"Basic example\"></salaxy-input>\r\n * ```\r\n */\r\nexport class Input extends ComponentBase {\r\n\r\n    /** ng-model is required, form tag is optionally used for validation and disabled/readonly */\r\n    public require = {\r\n        model: \"ngModel\",\r\n\r\n        form: \"?^^form\",\r\n    };\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = Objects.extend(InputBase.crudBindings, {\r\n\r\n        /** Minimum length for the text value, default is 0 (form validation) */\r\n        minlength: \"@\",\r\n        /** Maximum length for the text value, default is 1024 (form validation) */\r\n        maxlength: \"@\",\r\n        /** Regular expression pattern for validation (form validation) */\r\n        pattern: \"@\",\r\n        /** Type for the input. Defaults to text. Supports currently text and password. */\r\n        type: \"@\",\r\n\r\n     });\r\n\r\n    /** Uses the InputController */\r\n    public controller = InputController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/form-controls/Input.html\";\r\n}\r\n","import { InputBase, InputAccountingTargetController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Select component for Accounting Targets.\r\n * @example\r\n * ```html\r\n * <salaxy-input-accounting-target></salaxy-input-accounting-target>\r\n * ```\r\n */\r\nexport class InputAccountingTarget extends ComponentBase {\r\n\r\n    /** ng-model is required, form tag is optionally used for validation and disabled/readonly */\r\n    public require = {\r\n      model: \"ngModel\",\r\n\r\n      form: \"?^^form\",\r\n  };\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = InputBase.crudBindings;\r\n\r\n    /** Uses the InputAccountingTargetController */\r\n    public controller = InputAccountingTargetController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/form-controls/InputAccountingTarget.html\";\r\n}\r\n","\r\nimport { InputBase, InputBooleanController } from \"../../controllers\";\r\n\r\nimport { Objects } from \"@salaxy/core\";\r\n\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a boolean input control with label, validation error, info etc.\r\n * @example\r\n * ```html\r\n * <salaxy-input-boolean name=\"myInput\" ng-model=\"temp\" label=\"Basic example\" type=\"radio\"></salaxy-input>\r\n * ```\r\n */\r\n\r\nexport class InputBoolean extends ComponentBase {\r\n\r\n  /** ng-model is required, form tag is optionally used for validation and disabled/readonly */\r\n  public require = {\r\n    model: \"ngModel\",\r\n\r\n    form: \"?^^form\",\r\n};\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = Objects.extend(InputBase.crudBindings, {\r\n\r\n     /** Type of the input element. Options are checkbox, radio, select and switch */\r\n     type: \"@\",\r\n\r\n     /**\r\n      * Text to show as a label for input with value FALSE\r\n      * Supported by types radio and select\r\n      */\r\n     labelFalse: \"@\",\r\n\r\n     /**\r\n      * Text to show as a label for input with value TRUE\r\n      * Supported by types radio, checkbox and select\r\n      */\r\n     labelTrue: \"@\",\r\n\r\n     /**\r\n      * TODO: Is this needed when there's support for 'empty-label' ?\r\n      * BS class for offsetting the input (no-label)\r\n      */\r\n     offsetCols: \"@\",\r\n\r\n     /** If true, the radio buttons are aligned horizontally side-by-side */\r\n     horizontal: \"<\",\r\n\r\n  });\r\n\r\n  /** Uses the InputEnumController */\r\n  public controller = InputBooleanController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/form-controls/InputBoolean.html\";\r\n}\r\n","import { InputBase, InputCollectiveBargainAgreementController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\nimport { Objects } from \"@salaxy/core\";\r\n\r\n/**\r\n * Visual selection for collective bargain agreement codes.\r\n * @example\r\n * ```html\r\n * <salaxy-input-collective-bargain-agreement ng-model=\"row.code\"></salaxy-input-collective-bargain-agreement>\r\n * ```\r\n */\r\nexport class InputCollectiveBargainAgreement extends ComponentBase {\r\n\r\n    /** ng-model is required, form tag is optionally used for validation and disabled/readonly */\r\n    public require = {\r\n      model: \"ngModel\",\r\n\r\n      form: \"?^^form\",\r\n  };\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = Objects.extend(InputBase.crudBindings, {\r\n        /** List of collective bargain agreement codes to exclude from the selection list. */\r\n        hiddenCodes: \"<\",\r\n    });\r\n\r\n    /** Uses the InputCollectiveBargainAgreementController */\r\n    public controller = InputCollectiveBargainAgreementController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/form-controls/InputCollectiveBargainAgreement.html\";\r\n}\r\n","import { InputBase, InputEnumController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\nimport { Objects } from \"@salaxy/core\";\r\n\r\n/**\r\n * Select component for enumerations.\r\n * @example\r\n * ```html\r\n * <salaxy-input-enum type=\"select\"  options=\"{FiOy:'Osakeyhtiö', FiTm:'Toiminimi'}\"  name=\"CompanyType\" enum=\"CompanyType\" label=\"Company\" invalid-enums=\"none,other\" required></salaxy-input-enum>\r\n * <salaxy-input-enum type=\"radio\"  name=\"CompanyType\" enum=\"CompanyType\" label=\"Company\" hidden-options=\"unknown\"></salaxy-input-enum>\r\n * ```\r\n */\r\nexport class InputEnum extends ComponentBase {\r\n\r\n  /** ng-model is required, form tag is optionally used for validation and disabled/readonly */\r\n  public require = {\r\n    model: \"ngModel\",\r\n\r\n    form: \"?^^form\",\r\n  };\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = Objects.extend(InputBase.crudBindings, {\r\n    /**\r\n     * Binds to an enumeration defined by the Salaxy API.\r\n     * Set the name of the enumeration.\r\n     */\r\n    enum: \"@\",\r\n\r\n    /**\r\n     * Options of the select control as a key-value object.\r\n     */\r\n    options: \"<\",\r\n\r\n    /** Type of the input element. Options are select, multi-select, radio and dropdown */\r\n    type: \"@\",\r\n\r\n    /**\r\n     * These values are visible only if they are selected in the data.\r\n     * I.e. after something else is selected, hidden value cannot be selected back.\r\n     * Use for not-selected values (\"Please choose...\") when you do not want selection reversed\r\n     * or legacy data that is not selectable, but may still exist on the server.\r\n     */\r\n    hiddenOptions: \"@\",\r\n\r\n    /**\r\n     * Array or comma separated string to filter the option values to just the given ones.\r\n     * Also sets the order to this order, so works for ordering a given set of values.\r\n     * Note that hiddenOptions is applied first, so if you want e.g. \"undefined\" to appear if selected,\r\n     * you may add it here and it behaves as expected (undefined is still hidden if a value is selevted).\r\n     */\r\n    filter: \"@\",\r\n\r\n    /**\r\n     * Comma serapated list of values that should not be considered as valid in the UI.\r\n     * Default is [\"unknown\"] and is only used when input is \"required\" and input type is \"select\".\r\n     * Use in situations where an unknown/other/none value is set in API but should not be available as an option.\r\n     */\r\n    invalidEnums: \"@\",\r\n\r\n    /** If true, the control is not caching values. */\r\n    disableCache: \"@\",\r\n\r\n    /**\r\n     * Label format for the option. The default format is to show only the text of the option.\r\n     * Options are:\r\n     * \"text\" or empty: only the text of the option is displayed.\r\n     * \"text-value\": in addition to the text, the value is also displayed in the label.\r\n     * \"value\": only the value is displayed.\r\n     */\r\n    labelFormat: \"@\",\r\n\r\n    /**\r\n     * If set, last selected option is stored in LocalStorage and set as default/selected value in element. Currently supported only in type 'select' and 'uib-dropbdown'.\r\n     */\r\n    remember: \"@\",\r\n  });\r\n\r\n  /** Uses the InputEnumController */\r\n  public controller = InputEnumController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/form-controls/InputEnum.html\";\r\n}\r\n","import { InputCredentialController } from \"../../controllers\";\r\n\r\nimport { InputEnum } from \"./InputEnum\";\r\n\r\n/**\r\n * Select credential.\r\n * @example\r\n * ```html\r\n * <salaxy-input-credential ng-model=\"credential\" type=\"select\"  name=\"Credential\"  label=\"Credential\"></salaxy-input-credential>\r\n * <salaxy-input-credential ng-model=\"credential\" type=\"radio\"  name=\"Credential\" label=\"Credential\" ></salaxy-input-credential>\r\n * <salaxy-input-credential ng-model=\"credential\" type=\"typeahead\"  name=\"Credential\" label=\"Credential\"></salaxy-input-credential>\r\n * ```\r\n */\r\nexport class InputCredential extends InputEnum {\r\n\r\n    constructor() {\r\n      super();\r\n      /** Uses the InputEnumController */\r\n      this.controller = InputCredentialController as any;\r\n    }\r\n}\r\n","\r\nimport { InputBase, InputDurationController } from \"../../controllers\";\r\n\r\nimport { Objects } from \"@salaxy/core\";\r\n\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a an editor / display component for a .Net Duration.\r\n * .Net Duration is a string in format \"ddd.hh:mm:ss.ttttttt\".\r\n * @example\r\n * ```html\r\n * <salaxy-input-duration name=\"myInput\" ng-model=\"temp\" label=\"Basic example\"></salaxy-input-duration>\r\n * ```\r\n */\r\n\r\nexport class InputDuration extends ComponentBase {\r\n\r\n  /** ng-model is required, form tag is optionally used for validation and disabled/readonly */\r\n  public require = {\r\n    model: \"ngModel\",\r\n\r\n    form: \"?^^form\",\r\n};\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = Objects.extend(InputBase.crudBindings, {});\r\n\r\n  /** Uses the InputDurationController */\r\n  public controller = InputDurationController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/form-controls/InputDuration.html\";\r\n}\r\n","import { InputBase, InputIncomeTypeController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\nimport { Objects } from \"@salaxy/core\";\r\n\r\n/**\r\n * Visual selection for income types (and deductibles) resulting to number code in Incomes register.\r\n * @example\r\n * ```html\r\n * <salaxy-input-income-type name=\"code\" ng-model=\"row.code\" label=\"income type\"></salaxy-input-income-type>\r\n * ```\r\n */\r\nexport class InputIncomeType extends ComponentBase {\r\n\r\n    /** ng-model is required, form tag is optionally used for validation and disabled/readonly */\r\n    public require = {\r\n      model: \"ngModel\",\r\n\r\n      form: \"?^^form\",\r\n  };\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = Objects.extend(InputBase.crudBindings, {\r\n\r\n        /** Type of the input element is either typehead or list. Default is typeahead. */\r\n        type: \"@\",\r\n        /** List of income type codes to exclude from the selection list. */\r\n        hiddenCodes: \"<\",\r\n    });\r\n\r\n    /** Uses the InputIncomeTypeController */\r\n    public controller = InputIncomeTypeController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/form-controls/InputIncomeType.html\";\r\n}\r\n","import { Objects } from \"@salaxy/core\";\r\n\r\nimport { InputBase, InputNumberController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Input control for numbers.\r\n * @example\r\n * ```html\r\n * <salaxy-input-number name=\"count\" ng-model=\"row.count\" label=\"Number of items\"></salaxy-input-number>\r\n * ```\r\n */\r\nexport class InputNumber extends ComponentBase {\r\n\r\n    /** ng-model is required, form tag is optionally used for validation and disabled/readonly */\r\n    public require = {\r\n      model: \"ngModel\",\r\n\r\n      form: \"?^^form\",\r\n  };\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = Objects.extend(InputBase.crudBindings, {\r\n\r\n      /**\r\n       * Unit for the number.\r\n       * If set, shows a visual clue of the unit.\r\n       * For 'percent' editor value is multiplied by 100.\r\n       */\r\n      unit: \"@\",\r\n\r\n      /**\r\n       * Expression for the allowed Units for the number.\r\n       * If set, shows a selection of control for the unit.\r\n       */\r\n      units: \"<\",\r\n\r\n      /** Minimum number*/\r\n      minimum: \"@\",\r\n\r\n      /** Maximum number*/\r\n      maximum: \"@\",\r\n\r\n      /** Multiple of (step) number*/\r\n      multipleOf: \"@\",\r\n\r\n      /**\r\n       * If true, the input edits negative value: The value is multiplied by -1.\r\n       * E.g. \"3\" days ago => -3.\r\n       */\r\n      negative: \"<\",\r\n\r\n      /** Type of the input element. Options: default or slider */\r\n      type: \"@\",\r\n\r\n      /** Step for slider */\r\n      sliderStep: \"@\",\r\n\r\n    /**\r\n     * Function that is called when the unit has been changed.\r\n     * Function has the following locals:  unit: the selected unit.\r\n     */\r\n      onUnitChange: \"&\",\r\n    });\r\n\r\n    /** Uses the InputNumberController */\r\n    public controller = InputNumberController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/form-controls/InputNumber.html\";\r\n}\r\n","import { InputBase, InputOccupationTypeController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\nimport { Objects } from \"@salaxy/core\";\r\n\r\n/**\r\n * Select component for Occupation types.\r\n * @example\r\n * ```html\r\n * <salaxy-input-occupation-type default-list=\"household\" name=\"occupationType\" ng-model=\"row.occupation\" label=\"occupationType\"></salaxy-input-occupation-type>\r\n * <salaxy-input-occupation-type default-list=\"21490,21510,21532\" name=\"occupationType\" ng-model=\"row.occupation\" label=\"occupationType\"></salaxy-input-occupation-type>\r\n * ```\r\n */\r\nexport class InputOccupationType extends ComponentBase {\r\n\r\n    /** ng-model is required, form tag is optionally used for validation and disabled/readonly */\r\n    public require = {\r\n      model: \"ngModel\",\r\n\r\n      form: \"?^^form\",\r\n  };\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = Objects.extend(InputBase.crudBindings, {\r\n\r\n      /**\r\n       * One or comma-separated list of occupation IDs, or a known keyword to define which occupations are shown\r\n       * Supported keywords: 'household' and 'company'\r\n       * If empty, shows all\r\n       */\r\n      defaultList: \"@\",\r\n    });\r\n\r\n    /** Uses the InputOccupationTypeController */\r\n    public controller = InputOccupationTypeController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/form-controls/InputOccupationType.html\";\r\n}\r\n","\r\nimport { InputBase, InputRruleController } from \"../../controllers\";\r\n\r\nimport { Objects } from \"@salaxy/core\";\r\n\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a an editor / display component for a Recurrence Rule (RRule).\r\n * Recurrence rules are a strings defined in iCalendar format, e.g. \"FREQ=MONTHLY;INTERVAL=1\".\r\n * For more information and examples, see http://jakubroztocil.github.io/rrule/ or https://icalendar.org/iCalendar-RFC-5545/3-8-5-3-recurrence-rule.html\r\n * @example\r\n * ```html\r\n * <salaxy-input-rrule name=\"myInput\" ng-model=\"temp\" label=\"Basic example\"></salaxy-input-rrule>\r\n * ```\r\n */\r\n\r\nexport class InputRrule extends ComponentBase {\r\n\r\n  /** ng-model is required, form tag is optionally used for validation and disabled/readonly */\r\n  public require = {\r\n    model: \"ngModel\",\r\n\r\n    form: \"?^^form\",\r\n};\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = Objects.extend(InputBase.crudBindings, {});\r\n\r\n  /** Uses the InputRruleController */\r\n  public controller = InputRruleController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/form-controls/InputRrule.html\";\r\n}\r\n","import { InputBase, InputTimeController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\nimport { Objects } from \"@salaxy/core\";\r\n\r\n/**\r\n * Input component for time\r\n * @example\r\n * ```html\r\n * <salaxy-input-time type=\"minutes\" name=\"workTime\" label=\"Worktime\" required></salaxy-input-enum>\r\n * <salaxy-input-time type=\"isoTime\" name=\"workTime\" label=\"Worktime\" required></salaxy-input-enum>\r\n * ```\r\n */\r\nexport class InputTime extends ComponentBase {\r\n\r\n  /** ng-model is required, form tag is optionally used for validation and disabled/readonly */\r\n  public require = {\r\n    model: \"ngModel\",\r\n\r\n    form: \"?^^form\",\r\n  };\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = Objects.extend(InputBase.crudBindings, {\r\n    /**\r\n     * Used type in input. Types are minutes and isoTime\r\n     */\r\n    type: \"@\",\r\n  });\r\n\r\n  /** Uses the InputTimeController */\r\n  public controller = InputTimeController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/form-controls/InputTime.html\";\r\n}\r\n","import { ToggleButtonsController, InputBase } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\nimport { Objects } from \"@salaxy/core\";\r\n\r\n/**\r\n * The ToggleButtons component provides a set of toggle buttons bound to a model.\r\n * For each given value string, a unique toggle button is created. Wraps them all inside a group element.\r\n * Type can be \"block\", \"row\" or \"inline\". Each is styled differently.\r\n * @example\r\n * ```html\r\n * <salaxy-toggle-buttons name=\"myToggleButtonsGroup\" ng-model=\"$ctrl.view\" options=\"[{ value: 'test1', label: 'Test1' }, { value: 'test2', label: 'Test2' }]\" type=\"block\"></salaxy-toggle-buttons>\r\n * ```\r\n */\r\nexport class ToggleButtons extends ComponentBase {\r\n  public require = {\r\n    model: \"ngModel\"\r\n  };\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = Objects.extend(InputBase.crudBindings, {\r\n    /** The options to be displayed in the toggle buttons. For each given value, a new button is created. */\r\n    options: \"<\",\r\n\r\n    /** Display type of toggle buttons: \"row\", \"inline\" or \"block\" */\r\n    type: \"@\",\r\n\r\n    /** Type \"row\" toggle button has an image on top of the the text. */\r\n    imgSrc: \"@\",\r\n  });\r\n\r\n  /** Uses the ToggleButtonsController */\r\n  public controller = ToggleButtonsController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/form-controls/ToggleButtons.html\";\r\n}","import { InputBase, InputController } from \"../../controllers\";\r\n\r\nimport { Objects } from \"@salaxy/core\";\r\n\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a textarea control with label, validation error, info etc.\r\n * @example\r\n * ```html\r\n * <salaxy-textarea name=\"myInput\" ng-model=\"temp\" rows=\"5\" label=\"Basic example\"></salaxy-textarea>\r\n * ```\r\n */\r\nexport class Textarea extends ComponentBase {\r\n\r\n    /** ng-model is required, form tag is optionally used for validation and disabled/readonly */\r\n    public require = {\r\n        model: \"ngModel\",\r\n\r\n        form: \"?^^form\",\r\n    };\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = Objects.extend(InputBase.crudBindings, {\r\n\r\n        /** Minimum length for the text value, default is 0 (form validation) */\r\n        minlength: \"@\",\r\n        /** Maximum length for the text value, default is 1024 (form validation) */\r\n        maxlength: \"@\",\r\n        /** Regular expression pattern for validation (form validation) */\r\n        pattern: \"@\",\r\n\r\n        /** The rows property of the textarea. Default is 3. */\r\n        rows: \"<\",\r\n\r\n     });\r\n\r\n    /** Uses the InputController */\r\n    public controller = InputController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/form-controls/Textarea.html\";\r\n}\r\n","import { ValidationSummaryController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a validation summary user interface.\r\n * Currently, this component is used for showing the status of server-side validation,\r\n * but the idea is that later implementation may enable it for using also with client-side validation.\r\n * @example\r\n * ```html\r\n * <salaxy-validation-summary api-validation=\"$ctrl.validationData\">\r\n *       <span>Everything is OK!</span>\r\n * </salaxy-validation-summary>\r\n * ```\r\n */\r\nexport class ValidationSummary extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n        /** The server-side API-validation object that is displayed by this component. */\r\n        apiValidation: \"<\",\r\n\r\n        /** HTML that should be shown when the bound validation data is null. */\r\n        loadingHtml: \"@\",\r\n\r\n        /** Layout of the validation html. Use \"minimal\" for easy customizing*/\r\n        layout: \"@\"\r\n    };\r\n\r\n    /** Inner HTML is shown in case object is valid. */\r\n    public transclude = true;\r\n\r\n    /** Uses the ValidationSummaryController */\r\n    public controller = ValidationSummaryController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/form-controls/ValidationSummary.html\";\r\n}\r\n","import { InputBase, InputTypeaheadController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\nimport { Objects } from \"@salaxy/core\";\r\n\r\n// TODO: commenting\r\n/**\r\n * Select component for typeahead.\r\n * @example\r\n * ```html\r\n * <salaxy-input-typeahead name=\"CompanyType\" label=\"Company\" hidden-options=\"unknown\"></salaxy-input-typeahead>\r\n * ```\r\n */\r\nexport class InputTypeahead extends ComponentBase {\r\n\r\n  /** ng-model is required, form tag is optionally used for validation and disabled/readonly */\r\n  public require = {\r\n    model: \"ngModel\",\r\n    form: \"?^^form\",\r\n  };\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = Objects.extend(InputBase.crudBindings, {\r\n    /**\r\n     * Binds to an enumeration defined by the Salaxy API.\r\n     * Set the name of the enumeration.\r\n     */\r\n    enum: \"@\",\r\n\r\n    /**\r\n     * Options of the select control as a key-value object.\r\n     */\r\n    options: \"<\",\r\n\r\n    /**\r\n     * Array or comma separated string to filter the option values to just the given ones.\r\n     * Also sets the order to this order, so works for ordering a given set of values.\r\n     * Note that hiddenOptions is applied first, so if you want e.g. \"undefined\" to appear if selected,\r\n     * you may add it here and it behaves as expected (undefined is still hidden if a value is selevted).\r\n     */\r\n    filter: \"@\",\r\n\r\n    /** If true, the control is not caching values. */\r\n    disableCache: \"@\",\r\n\r\n    /**\r\n     * Label format for the option. The default format is to show only the text of the option.\r\n     * Options are:\r\n     * \"text\" or empty: only the text of the option is displayed.\r\n     * \"text-value\": in addition to the text, the value is also displayed in the label.\r\n     * \"value\": only the value is displayed.\r\n     */\r\n    labelFormat: \"@\",\r\n\r\n    /** If true, upon selection the value is not set for the input field (it is used for other things thought). */\r\n    clearOnSelect: \"<\",\r\n\r\n    /** If true, save new values (ones typed but not found in the select list) to database. Used in ng1-aspa. */\r\n    allowCustomValues: \"<\",\r\n\r\n    /** True = return the typeahead selection object alongside the value. */\r\n    returnObject: \"<\",\r\n\r\n    /** The object data that's to be returned. */\r\n    objectData: \"=\",\r\n\r\n    /** True = The value is saved as a whole object, false = as a primitive (string/number/etc. from the item key \"value\") */\r\n    valueAsObject: \"<\",\r\n\r\n    /** Text if the input field must have a placeholder text. */\r\n    placeholder: \"@\"\r\n  });\r\n\r\n  /** Uses the InputTypeaheadController */\r\n  public controller = InputTypeaheadController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/form-controls/InputTypeahead.html\";\r\n}\r\n","import { InputBase, InputPayStatsRowTypeController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Form control for defining row type for pay statistics calculations.\r\n * @example\r\n * ```html\r\n * <salaxy-input-pay-stats-row-type name=\"salaryType\" ng-model=\"row.salaryType\" label=\"Row type or custom type\"></salaxy-input-pay-stats-row-type>\r\n * ```\r\n */\r\nexport class InputPayStatsRowType extends ComponentBase {\r\n\r\n    /** ng-model is required, form tag is optionally used for validation and disabled/readonly */\r\n    public require = {\r\n      model: \"ngModel\",\r\n\r\n      form: \"?^^form\",\r\n  };\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = InputBase.crudBindings;\r\n\r\n    /** Uses the InputPayStatsRowTypeController */\r\n    public controller = InputPayStatsRowTypeController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/form-controls/InputPayStatsRowType.html\";\r\n}\r\n","import { InputBase, InputHolidayMultipliersController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Form control for defining multipliers for holiday pay calculations.\r\n * @example\r\n * ```html\r\n * <salaxy-input-holiday-multipliers name=\"multipliers\" ng-model=\"settings.multipliers\" label=\"Multipliers for holiday pay calculation\"></salaxy-input-holiday-multipliers>\r\n * ```\r\n */\r\nexport class InputHolidayMultipliers extends ComponentBase {\r\n\r\n    /** ng-model is required, form tag is optionally used for validation and disabled/readonly */\r\n    public require = {\r\n      model: \"ngModel\",\r\n\r\n      form: \"?^^form\",\r\n  };\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = InputBase.crudBindings;\r\n\r\n    /** Uses the InputHolidayMultipliersController */\r\n    public controller = InputHolidayMultipliersController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/form-controls/InputHolidayMultipliers.html\";\r\n}\r\n","import { InputEmployeeGroupController } from \"../../controllers\";\r\n\r\nimport { InputEnum } from \"./InputEnum\";\r\n\r\n/**\r\n * Select an employee group.\r\n * @example\r\n * ```html\r\n * <salaxy-input-employee-group ng-model=\"employeeGroup\" type=\"select\"  name=\"EmployeeGroup\"  label=\"Employee Group\"></salaxy-input-employee-group>\r\n * ```\r\n */\r\nexport class InputEmployeeGroup extends InputEnum {\r\n\r\n    constructor() {\r\n      super();\r\n      /** Uses the InputEmployeeGroupController */\r\n      this.controller = InputEmployeeGroupController as any;\r\n    }\r\n}\r\n","import { InputBase, InputController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Form control for editing/viewing markdown content.\r\n * @example\r\n * ```html\r\n * <salaxy-input-markdown name=\"md\" ng-model=\"row.md\" label=\"Document\"></salaxy-input-markdown>\r\n * ```\r\n */\r\nexport class InputMarkdown extends ComponentBase {\r\n\r\n    /** ng-model is required, form tag is optionally used for validation and disabled/readonly */\r\n    public require = {\r\n      model: \"ngModel\",\r\n\r\n      form: \"?^^form\",\r\n  };\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = InputBase.crudBindings;\r\n\r\n    /** Uses the InputController */\r\n    public controller = InputController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/form-controls/InputMarkdown.html\";\r\n}\r\n","import { MarkdownEditorController, InputBase } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Markdown editor component\r\n * @example\r\n * ```html\r\n * <salaxy-markdown-editor ng-model=\"row.md\"></salaxy-markdown-editor>\r\n * ```\r\n */\r\nexport class MarkdownEditor extends ComponentBase {\r\n\r\n    /** ng-model containing markdown */\r\n    public require = {\r\n      model: \"ngModel\",\r\n  };\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = InputBase.crudBindings;\r\n\r\n    /** Uses the MarkdownEditorController */\r\n    public controller = MarkdownEditorController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/form-controls/MarkdownEditor.html\";\r\n}\r\n","import { MarkdownViewerController, InputBase } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Markdown viewer component\r\n * @example\r\n * ```html\r\n * <salaxy-markdown-viewer ng-model=\"row.md\"></salaxy-markdown-viewer>\r\n * ```\r\n */\r\nexport class MarkdownViewer extends ComponentBase {\r\n\r\n    /** ng-model containing markdown */\r\n    public require = {\r\n      model: \"ngModel\",\r\n  };\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = InputBase.crudBindings;\r\n\r\n    /** Uses the MarkdownViewerController */\r\n    public controller = MarkdownViewerController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/form-controls/MarkdownViewer.html\";\r\n}\r\n","import { ActionButtonController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Helper component to generate buttons with known actions such as creating a new worker, new calculation etc.\r\n * @example\r\n * ```html\r\n *  <salaxy-action-button label=\"SALAXY.NG1.WorkerDetailsComponent.newCalculation\" action=\"'newCalcForEmployment'\" options=\"{'id': $ctrl.currentId }\" button-class=\"btn-default pull-right-xs\"></salaxy-action-button>\r\n * ```\r\n */\r\n\r\nexport class ActionButton extends ComponentBase {\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n\r\n    /** Text for the button */\r\n    label: \"@\",\r\n\r\n    /** Additional Bootstrap or custom style classes. Bootstrap I.e. btn-danger, btn-sm, my-btn. Defaults to btn-primary */\r\n    buttonClass: \"@\",\r\n\r\n    /** Disabled but visible */\r\n    disabled: \"<\",\r\n\r\n    /** Options for button. */\r\n    options: \"<\",\r\n\r\n    /**\r\n     * Action to be executed.\r\n     * newCalc: starts a new blank calculation.\r\n     * newCalcForEmployment: starts a new calculation for the given employment id.\r\n     * newPayroll: starts a new blank payroll.\r\n     * newWorker: opens workerWizard for creating a new worker.\r\n     * newMessage: starts a new message thread with partner.\r\n     * payment: Not supported at the moment. opens the payment dialog for the current calculation.\r\n     * newTaxcard: Links to taxcards page. Currently supported only when role is Worker.\r\n     * newRepair: Starts a repair process for a calculation.\r\n     */\r\n    action: \"<\",\r\n\r\n    /**\r\n     * Function that is called after the function. This is typically used for navigation or a list reload.\r\n     */\r\n    onAfterAction: \"&\",\r\n\r\n  };\r\n\r\n  /** Uses the NaviController */\r\n  public controller = ActionButtonController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/helpers/ActionButton.html\";\r\n}\r\n","import { AlertController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows an alert box with styling.\r\n *\r\n * Based on Bootstrap alert, but has the following additional functionality:\r\n *\r\n * - primary style (in addition to success, info, warning and danger) for banner type of advertising\r\n * - Icon for better visuality\r\n * - Optional \"Read more\" area\r\n * @example\r\n * ```html\r\n * <salaxy-alert type=\"warning\" text=\"This is a Warning\"></salaxy-alert>\r\n * ```\r\n */\r\nexport class Alert extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n\r\n        /**\r\n         * Possibility to speicfy a font-awesome icon.\r\n         * Setting \"none\", will show no icon.\r\n         * If not set, it is determined by type.\r\n         */\r\n        icon: \"@\",\r\n\r\n        /** Type of the alert is the Bootstrap style: Note that also \"primary\" and \"default\" are supported. */\r\n        type: \"@\",\r\n\r\n        /**\r\n         * Alert main content as simple text.\r\n         * You can alternatively provide html as main element.\r\n         */\r\n        text: \"@\",\r\n\r\n        /** If true, the aside part is shown immidiately. Also hides \"read more\"- button. */\r\n        forceMoreInfo: \"<\",\r\n    };\r\n\r\n    /**\r\n     * Transclusion slots\r\n     */\r\n    public transclude = {\r\n        /**\r\n         * The main content of the alert.\r\n         * You can alternatively provide a simple text in \"text\" property.\r\n         */\r\n        main: \"?main\",\r\n\r\n        /**\r\n         * Optional Details part of the alert.\r\n         * Will automatically show \"Read more\" button.\r\n         */\r\n        aside: \"?aside\",\r\n    };\r\n\r\n    /** Uses the AlertController */\r\n    public controller = AlertController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/helpers/Alert.html\";\r\n}\r\n","import { AvatarController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the Palkkaus Avatar image: This is either an image or a font-icon with a user specific color/initilas combination.\r\n * @example\r\n * ```html\r\n * <salaxy-avatar avatar=\"$ctrl.myAvatar\"></salaxy-avatar>\r\n * ```\r\n */\r\nexport class Avatar extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n        /** The Avatar object that should be rendered */\r\n        avatar: \"=\",\r\n    };\r\n\r\n    /** Uses the AvatarController */\r\n    public controller = AvatarController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/helpers/Avatar.html\";\r\n\r\n    /** Rendered HTML replaces the original element */\r\n    public replace: true;\r\n}\r\n","import { CalendarController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Renders a monthly calendar where one month is one row and you can show ranges and special days (only partial support).\r\n * Future implementations will support categories / swimlanes of periods (e.g. holidays from several persons)\r\n * and have better support for special days: different types of markers, pop-up etc.\r\n * @example\r\n * ```html\r\n * <salaxy-calendar start=\"'2019-01-5'\" end=\"$ctrl.getToday()\" periods=\"$ctrl.getPeriods()\"></salaxy-chart>\r\n * ```\r\n */\r\nexport class Calendar extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n\r\n        /**\r\n         * Start date for the calendar as ISO date yyyy-MM-dd. Renders from the beginning of this month.\r\n         */\r\n        start: \"<\",\r\n\r\n        /**\r\n         * End date of the calendar as ISO date yyyy-MM-dd. Renders until the end of this month.\r\n         */\r\n        end: \"<\",\r\n\r\n        /**\r\n         * Today date for the calendar as ISO date yyyy-MM-dd.\r\n         * Can be set as dately object (e.g. ISO string, JS Date or key string \"today\")\r\n         */\r\n        today: \"<\",\r\n\r\n        /** The data that is plotted on the calendar chart. */\r\n        data: \"<\",\r\n\r\n        /** Optional data mapper function that is used in mapping the data to CalendarSeries array. */\r\n        mapper: \"<\",\r\n\r\n        /** TODO: Remove */\r\n        periods: \"<\",\r\n\r\n        /** TODO: Remove */\r\n        days: \"<\",\r\n\r\n        /** Type of chart: \"align-weekdays\", \"align-left\" or horizontal. */\r\n        mode: \"@\",\r\n\r\n        /**\r\n         * Function that is called when user selects an item in the calendar.\r\n         * Function can have the following locals: type: \"event\" | \"day\", date: string, day: Full calendar day with all the day info,\r\n         * calEvent: The calendar event if type is \"event\", series: Series that the event belongs to or the series that is clicked (not always available).\r\n         * @example <salaxy-calendar on-list-select=\"$ctrl.myCustomSelectFunc(type, date, calEvent)\"></salaxy-calendar>\r\n         */\r\n        onListSelect: \"&\",\r\n\r\n        /** Possibility of specifying a list controller that can be used for item editing. */\r\n        listController: \"<\",\r\n\r\n        /** If set to true, the export buttons are visible. */\r\n        showExport: \"<\",\r\n    };\r\n\r\n    /** Uses the CalendarController */\r\n    public controller = CalendarController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/helpers/Calendar.html\";\r\n}\r\n","import { ChartController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Controller rendering chart by provided config\r\n * Config type example: config: ChartConfiguration<\"pie\" | \"bar\", { labels: string[]; datasets: any[] }, any>\r\n * Config follows official chart.js ChartConfiguration interface\r\n * @example\r\n * ```html\r\n *  <salaxy-chart config=\"config\"></salaxy-chart>\r\n * ```\r\n */\r\nexport class Chart extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n      /** Config of chart */\r\n      config: \"<\",\r\n      /** Custom height of chart */\r\n      customHeight: \"@\",\r\n      /** Custom height of chart */\r\n      customWidth: \"@\",\r\n      /** Custom height of chart */\r\n      customClass: \"@\",\r\n    };\r\n\r\n    /** Uses the ChartController */\r\n    public controller = ChartController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/helpers/Chart.html\";\r\n}\r\n","import { ModalGenericDialogController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * User interface for debugging definition and values.\r\n * @example\r\n * ```html\r\n * <salaxy-data-mapper model=\"$ctrl.mapper\"></salaxy-data-mapper>\r\n * ```\r\n */\r\nexport class DataMapper extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n      /** The DataMapper that is shown.  */\r\n      model: \"<\",\r\n\r\n      /**\r\n       * Type of the user interface:\r\n       *\r\n       * - \"value-map\" (default) Shows the source values in the table, target mapping is editable.\r\n       * - \"debug\" Full data mapper debugger / editor UI.\r\n       * - \"source-value\" Shows the source values in a table, also the validation column\r\n       * - \"target-value\" Shows the target values in a table, also the validation column\r\n       */\r\n      type: \"@\",\r\n    };\r\n\r\n    /** Uses the ModalGenericDialogController */\r\n    public controller = ModalGenericDialogController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/helpers/DataMapper.html\";\r\n}\r\n","import { JsonFormatterController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a JavaScript object JSON as formatted HTML.\r\n * Open attribute accepts a number that indicated how many levels JSON should be open.\r\n * Based on http://azimi.me/json-formatter/demo/demo.html\r\n * @example\r\n * ```html\r\n * <salaxy-json-formatter open=\"1\" json=\"$ctrl.current\"></salaxy-json-formatter>\r\n * <salaxy-json-formatter key=\"'Debugger'\" json=\"$ctrl.sitemap\" open=\"1\" type=\"dialog\"></salaxy-json-formatter>\r\n * ```\r\n */\r\nexport class JsonFormatter extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n      /** The JavaScript object that should be displayed. */\r\n      json: \"<\",\r\n      /** If true json is compared to compare-to value. */\r\n      compare: \"<\",\r\n      /** The original JavaScript to which to show DIFF (show changes in data). */\r\n      compareTo: \"<\",\r\n      /** When displaying children, sets the property / key name for json */\r\n      key: \"<\",\r\n      /** Number that indicated how many levels JSON should be open */\r\n      open: \"<\",\r\n      /**\r\n       * Set to \"dialog\" if you want to show a button that opens the JSON in dialog.\r\n       * Otherwise, an inline tree view is shown.\r\n       */\r\n      type: \"@\",\r\n\r\n      /** Optional button class for the dialog button. Default is \"btn btn-default btn-xs\" */\r\n      btnClass: \"@\",\r\n    };\r\n\r\n    /** Uses the JsonFormatterController */\r\n    public controller = JsonFormatterController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/helpers/JsonFormatter.html\";\r\n\r\n    /** Rendered HTML replaces the original element */\r\n    public replace: true;\r\n}\r\n","import { NaviController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Helper component to generate navigation components and views:\r\n * Top- and side-menus, paths and controls that show the current title.\r\n * These controls take the navigation logic from an object (sitemap) and are aware of current node / open page on that sitemap.\r\n *\r\n *\r\n * NOTE: This is just an optional helper to make creating simple demo sites easier.\r\n * There is no need to use NaviService, NaviController or components in your custom site!\r\n * You can use something completely different.\r\n * @example\r\n * ```html\r\n * <salaxy-navi-sitemap></salaxy-navi-sitemap>\r\n * ```\r\n */\r\n\r\nexport class NaviSitemap extends ComponentBase {\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {\r\n        /**\r\n         * - mode: \"default\", \"accordion\" or \"horizontal\"\r\n         * - default: shows full two levels of the tree. Typically used as sitemap in the content area.\r\n         * - accordion: shows first level of the navi tree and second level only if is in the current path.\r\n         * Typically used in left menu navigation.\r\n         * - horizontal: Full navi on top bar. Second tier in dropdowns.\r\n         * - 3-levels: Accordion with 3 levels.\r\n         */\r\n        mode: \"@\",\r\n    };\r\n\r\n    /** Uses the NaviController */\r\n    public controller = NaviController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/helpers/NaviSitemap.html\";\r\n}\r\n","import { NaviController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Helper component to easily create a web site that is responsive and usable.\r\n * The starter contains:\r\n *\r\n * - Customizable Header with title\r\n * - Left menu with logo, authentication info / login button and sitemap\r\n * - Mobile version with simple header: Title + Hamburger button that shows the menu, which is hidden by default.\r\n * - Loader message / animation\r\n * - Content area as ng-view\r\n * - Alert container\r\n *\r\n *\r\n * NOTE: This is just an optional helper to make creating simple (demo) sites easier.\r\n * There is no need to use NaviStarterLayout, NaviService, NaviController or components in your custom site!\r\n * You can use something completely different.\r\n * @example\r\n * ```html\r\n * <salaxy-navi-starter-layout>\r\n *   <header ng-controller=\"NaviController as navi\">\r\n *     Your html here: {{ navi.title }}\r\n *   </header>\r\n *   <main ng-controller=\"NaviController as navi\">\r\n *   \t<div ng-class=\"navi.current.isFullWidth ? 'container-fluid' : 'container'\" ng-view autoscroll=\"true\"></div>\r\n *   </main>\r\n * </salaxy-navi-starter-layout>\r\n * ```\r\n */\r\nexport class NaviStarterLayout extends ComponentBase {\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n    /**\r\n     * - mode: \"default\", \"accordion\" or \"horizontal\"\r\n     * - default: shows full two levels of the tree. Typically used as sitemap in the content area.\r\n     * - accordion: shows first level of the navi tree and second level only if is in the current path.\r\n     * - horizontal: Full navi on top bar. Second tier in dropdowns.\r\n     * Typically used in left menu navigation.\r\n     */\r\n    mode: \"@\",\r\n\r\n    /**\r\n     * - layout: \"default\" or \"iframe\"\r\n     * - default: Basic layout with full navigation (left sidebar or horizontal).\r\n     * - iframe: Layout without first tier navigation on left sidebar. Second tier navigation items are under dropdown in top bar / header if mode is default. On horizontal mode full navigation is on top bar.\r\n     */\r\n     layout: \"@\",\r\n  };\r\n\r\n  /**\r\n   * Component may contain header and main tags to\r\n   * override the default rendering of the header (non-mobile) and main content area respectively.\r\n   */\r\n  public transclude = {\r\n    /** Header part of the page. Note that mobile header is defined separately. */\r\n    header: \"?header\",\r\n    /** Main content part of the page */\r\n    main: \"?main\",\r\n    /** The main navigation: By default: left sidebar. */\r\n    nav: \"?nav\",\r\n  };\r\n\r\n  /** Uses the NaviController */\r\n  public controller = NaviController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/helpers/NaviStarterLayout.html\";\r\n\r\n}\r\n","import { SpinnerController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Spinner as a UI component\r\n * @example\r\n * ```html\r\n * <salaxy-spinner salaxy-if-role=\"init\" full-screen=\"true\" heading=\"Loading...\" text=\"Please wait.\"></salaxy-spinner>\r\n * ```\r\n */\r\nexport class Spinner extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n        /** If true, the spinner is shown full screen. */\r\n        fullScreen: \"=\",\r\n\r\n        /**\r\n         * Heading is the larger text under the spinner.\r\n         * The text is translated.\r\n         */\r\n        heading: \"@\",\r\n\r\n        /**\r\n         * Small text - use pre for line breaks.\r\n         * The text is translated.\r\n         */\r\n        text: \"@\",\r\n    };\r\n\r\n    /** Uses the SpinnerController */\r\n    public controller = SpinnerController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/helpers/Spinner.html\";\r\n}\r\n","import { TabController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Component for a single tab pane in the tabs control.\r\n * Shows a navigation header and a tab pane.\r\n * Contains salaxy-tab-heading element for the tab header.\r\n * Contains salaxy-tab-content element for the tab pane content.\r\n * The disable attribute can be used to disable the tab.\r\n * The index attribute can be used to name the tab. The index\r\n * is used in setting the active tab in the salaxy-tabs element using the active attribute.\r\n * @example\r\n * ```html\r\n * <salaxy-tabs active=\"active\">\r\n *   <salaxy-tab>\r\n *      <salaxy-tab-heading>Tab number one</salaxy-tab-heading>\r\n *      <salaxy-tab-content>\r\n *          <p>Tab one content</p>\r\n *      </salaxy-tab-content>\r\n *  </salaxy-tab>\r\n *  <salaxy-tab index=\"'kolme'\">\r\n *      <salaxy-tab-heading><i>Tab number two</i></salaxy-tab-heading>\r\n *      <salaxy-tab-content>\r\n *          <p>Tab two content</p>\r\n *      </salaxy-tab-content>\r\n *  </salaxy-tab>\r\n *  <salaxy-tab disable=\"true\" heading=\"Tab text number three\">\r\n *      <salaxy-tab-content>\r\n *          <p>Tab three content</p>\r\n *      </salaxy-tab-content>\r\n *  </salaxy-tab>\r\n * </salaxy-tabs>\r\n * ```\r\n */\r\nexport class Tab extends ComponentBase   {\r\n\r\n    /** Require salaxy-tabs */\r\n    public require = {\r\n        tabsCtrl: \"^salaxyTabs\",\r\n    };\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n     public bindings = {\r\n        /** Index/name for the tab. */\r\n         index: \"<\",\r\n        /** Disable tab attribute. */\r\n         disable: \"<\",\r\n        /** Text heading. */\r\n        heading: \"@\",\r\n        /** Selection event handler */\r\n        onSelect: \"&select\",\r\n     };\r\n\r\n     /** Uses the TabController */\r\n     public controller = TabController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/helpers/Tab.html\";\r\n\r\n    /** Transclusion */\r\n    public transclude = {\r\n        content: \"?salaxyTabContent\",\r\n        heading: \"?salaxyTabHeading\",\r\n    };\r\n}\r\n","import { TabsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Component for a tabs control.\r\n * Shows navigation headers and tab panes.\r\n * Contains one or more salaxy-tab elements, each for one tab.\r\n * The active-attribute shows/sets the current active tab.\r\n * @example\r\n * ```html\r\n * <salaxy-tabs active=\"active\">\r\n *   <salaxy-tab>\r\n *      <salaxy-tab-heading>Tab number one</salaxy-tab-heading>\r\n *      <salaxy-tab-content>\r\n *          <p>Tab one content</p>\r\n *      </salaxy-tab-content>\r\n *  </salaxy-tab>\r\n *  <salaxy-tab index=\"'kolme'\">\r\n *      <salaxy-tab-heading><i>Tab number two</i></salaxy-tab-heading>\r\n *      <salaxy-tab-content>\r\n *          <p>Tab two content</p>\r\n *      </salaxy-tab-content>\r\n *  </salaxy-tab>\r\n *  <salaxy-tab disable=\"true\" heading=\"Tab text number three\">\r\n *      <salaxy-tab-content>\r\n *          <p>Tab three content</p>\r\n *      </salaxy-tab-content>\r\n *  </salaxy-tab>\r\n * </salaxy-tabs>\r\n * ```\r\n */\r\nexport class Tabs extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n     public bindings = {\r\n        /** Expression for active tab in the tabset */\r\n        active: \"=?\",\r\n     };\r\n\r\n    /** Uses the TabsController */\r\n    public controller = TabsController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/helpers/Tabs.html\";\r\n\r\n    /** Transclusion */\r\n    public transclude = true;\r\n\r\n}\r\n","import { TabButtonsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Component for tab buttons selectors.\r\n * Shows a navigation header.\r\n * The disable attribute can be used to disable the tab.\r\n * @example\r\n * ```html\r\n * <salaxy-tab-buttons active=\"active\">\r\n * </salaxy-tab-buttons>\r\n * ```\r\n */\r\nexport class TabButtons extends ComponentBase   {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n      currentTab: \"=\",\r\n      options: \"<\",\r\n      tabsId: \"@\",\r\n      defaultTab: \"<\",\r\n      // Updates the ?tab= parameter on tab change, causing a browser reload.\r\n      updateTabParam: \"<\"\r\n    };\r\n\r\n    /** Uses the TabButtonsController */\r\n    public controller = TabButtonsController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/helpers/TabButtons.html\";\r\n}","import { UiTranslatorController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * User interface for translating user interfaces\r\n * @example\r\n * ```html\r\n * <salaxy-ui-translator></salaxy-ui-translator>\r\n * ```\r\n */\r\nexport class UiTranslator extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n\r\n      /** User interface mode for the component: \"table\" (default) or \"fieldset\" */\r\n      mode: \"@\",\r\n\r\n      /**\r\n       * Beginning of the full key that is used to filtering the dictionary items (allKeyValues filter).\r\n       * The value may be a string, array or comma separated string of values.\r\n       */\r\n      filter: \"<\",\r\n\r\n      /** Texts from serviceModel that are being edited */\r\n      texts: \"<\",\r\n    };\r\n\r\n    /** Uses the UiTranslatorController */\r\n    public controller = UiTranslatorController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/helpers/UiTranslator.html\";\r\n}\r\n","import { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * Base component for mass data loading.\r\n */\r\nexport abstract class DataImportComponentBase extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = { };\r\n\r\n    /** No controller */\r\n    public controller = null;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/helpers/import/DataImport.html\";\r\n}\r\n","import { CalcImportController } from \"../../../controllers\";\r\nimport { DataImportComponentBase } from \"./DataImportComponentBase\";\r\n\r\n/**\r\n * User interface for calculation mass loading.\r\n * @example\r\n * ```html\r\n * <salaxy-calc-import></salaxy-calc-import>\r\n * ```\r\n */\r\nexport class CalcImport extends DataImportComponentBase {\r\n\r\n    /** Uses the CalcImportController */\r\n    public controller = CalcImportController;\r\n\r\n}","import { CompanyImportController } from \"../../../controllers\";\r\nimport { DataImportComponentBase } from \"./DataImportComponentBase\";\r\n\r\n/**\r\n * User interface for worker mass loading.\r\n * @example\r\n * ```html\r\n * <salaxy-company-import></salaxy-company-import>\r\n * ```\r\n */\r\nexport class CompanyImport extends DataImportComponentBase {\r\n\r\n    /** Uses the CompanyImportController */\r\n    public controller = CompanyImportController;\r\n\r\n}","import { ImportStagingController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * Provides an UI to the import staging area if one is available for the current company..\r\n */\r\nexport class ImportStaging extends ComponentBase {\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n    /** Binds the current payroll (the full object) typically from the Payroll details view. */\r\n    payroll: \"<\",\r\n\r\n    /** If the list off calculations committed into the Payroll typically from the Payroll details view. */\r\n    payrollCalcs: \"<\",\r\n  };\r\n\r\n  /** Uses the ImportStagingController */\r\n  public controller = ImportStagingController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/helpers/import/staging/ImportStaging.html\";\r\n}\r\n","import { WorkerImportController } from \"../../../controllers\";\r\nimport { DataImportComponentBase } from \"./DataImportComponentBase\";\r\n\r\n/**\r\n * User interface for worker mass loading.\r\n * @example\r\n * ```html\r\n * <salaxy-worker-import></salaxy-worker-import>\r\n * ```\r\n */\r\nexport class WorkerImport extends DataImportComponentBase {\r\n\r\n    /** Uses the WorkerImportController */\r\n    public controller = WorkerImportController;\r\n\r\n}\r\n","import { JsonDiffController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * JSON Diff component that compares two JSON objects and displays differences in a table format.\r\n * Uses json-diff-ts package for comparison.\r\n * <salaxy-json-diff json=\"json\" compareTo=\"compareTo\" excludePaths=\"excludePaths\" openApi=\"openApi\" itemType=\"itemType\"></salaxy-json-diff>\r\n */\r\nexport class JsonDiff extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n        /** JSON object to compare */\r\n        json: \"<\",\r\n        /** JSON object to compare to */\r\n        compareTo: \"<\",\r\n        /** exclude paths from the diff */\r\n        excludePaths: \"<\",\r\n        /** URL for the Open API document that contains the definition for the type. */\r\n        openApi: \"<\",\r\n        /** The type of the item to diff */\r\n        itemType: \"<\"\r\n    };\r\n\r\n    /** Uses the JsonDiffController */\r\n    public controller = JsonDiffController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/helpers/JsonDiff.html\";\r\n}\r\n","import { CreditTransferController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Credit Transfer Form for Invoice visualization.\r\n * @example\r\n * ```html\r\n * <salaxy-credit-transfer invoice=\"$ctrl.current\">\r\n *   <message>My <strong>custom HTML</strong> message</message>\r\n * </salaxy-credit-transfer>\r\n * ```\r\n */\r\nexport class CreditTransfer extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n\r\n    /** Invoice to display in the credit transfer. */\r\n    invoice: \"<\",\r\n\r\n    /** Invoice preview to display in the credit transfer. */\r\n    invoicePreview: \"<\",\r\n\r\n    /**\r\n     * Display mode is either\r\n     *\r\n     * - \"official\": The official printable credit transfer (Finanssialan keskusliitto)\r\n     * - \"barcode-copy\": The copy-paste input + button (in a div) for copy pasting the the barcode into a web bank\r\n     * - \"default\": Both of the above separted by an explaining text.\r\n     */\r\n    mode: \"@\",\r\n  };\r\n\r\n  /**\r\n   * Transclusion slots\r\n   */\r\n  public transclude = {\r\n    /**\r\n     * HTML to include in the message section\r\n     */\r\n    message: \"?message\",\r\n  };\r\n\r\n  /** Uses the CreateCompanyAccountWizardController */\r\n  public controller = CreditTransferController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/invoices/CreditTransfer.html\";\r\n\r\n}\r\n","import { ApiCrudObjectControllerBindings, InvoiceCrudController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Edit / actions user interface for a single invoice.\r\n * @example\r\n * ```html\r\n * <salaxy-invoice-edit model=\"'url'\"></salaxy-invoice-edit>\r\n * ```\r\n */\r\nexport class InvoiceEdit extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = new ApiCrudObjectControllerBindings();\r\n\r\n    /** Uses the InvoiceCrudController */\r\n    public controller = InvoiceCrudController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/invoices/InvoiceEdit.html\";\r\n\r\n}\r\n","import { InvoiceCrudController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a list of salary reports.\r\n * @example\r\n * ```html\r\n * <salaxy-invoice-list mode=\"panel\"></salaxy-salary-report-list>\r\n * ```\r\n */\r\nexport class InvoiceList extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n      /**\r\n       * list view 'mode'.\r\n       * If undefined, defaults to full list.\r\n       * Use panel for dashboards etc.\r\n       */\r\n      mode: \"@\"\r\n     };\r\n\r\n    /** Uses the InvoiceCrudController */\r\n    public controller = InvoiceCrudController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/invoices/InvoiceList.html\";\r\n\r\n}\r\n","import { InvoicePaymentListController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the report for the given invoice.\r\n * @example\r\n * ```html\r\n * <salaxy-invoice-payment-list payment-channel=\"$ctrl.paymentChannel\"></salaxy-invoice-payment-list>\r\n * ```\r\n */\r\nexport class InvoicePaymentList extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {};\r\n\r\n    /** Uses the InvoicePaymentListController */\r\n    public controller = InvoicePaymentListController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/invoices/InvoicePaymentList.html\";\r\n\r\n}\r\n","import { ApiCrudObjectControllerBindings, InvoiceCrudController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a print-like preview for an invoice.\r\n * @example\r\n * ```html\r\n * <salaxy-invoice-preview model=\"$ctrl.current\"></salaxy-invoice-preview>\r\n * ```\r\n */\r\nexport class InvoicePreview extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = new ApiCrudObjectControllerBindings();\r\n\r\n    /** Uses the InvoiceCrudController */\r\n    public controller = InvoiceCrudController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/invoices/InvoicePreview.html\";\r\n\r\n}\r\n","import { ApiCrudObjectControllerBindings, InvoicesCreateController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a view for creating invoices: PaymentChannel selection, validation errors if necessary,\r\n * Payment channel selection and button for creating invoices for Payroll or Calculation.\r\n * If pointed to a paid calculation, shows the invoices that were already created or legacy payment method.\r\n * @example\r\n * ```html\r\n * <salaxy-invoices-create model=\"$ctrl.current\"></salaxy-invoices-create>\r\n * ```\r\n */\r\nexport class InvoicesCreate extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = new ApiCrudObjectControllerBindings();\r\n\r\n    /** Uses the InvoicesCreateController */\r\n    public controller = InvoicesCreateController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/invoices/InvoicesCreate.html\";\r\n\r\n}\r\n","import { ApiCrudObjectControllerBindings, PaymentChannelController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a print-like preview for an invoice.\r\n * @example\r\n * ```html\r\n * <salaxy-payment-channel-invoice-preview model=\"$ctrl.current\"></salaxy-payment-channel-invoice-preview>\r\n * ```\r\n */\r\nexport class PaymentChannelInvoicePreview extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = new ApiCrudObjectControllerBindings();\r\n\r\n    /** Uses the PaymentChannelController */\r\n    public controller = PaymentChannelController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/invoices/InvoicePreview.html\";\r\n\r\n}\r\n","import { InvoiceToolsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the export tools for the invoices.\r\n * @example\r\n * ```html\r\n * <salaxy-invoice-tools reader=\"$ctrl.dataReader\"></salaxy-invoice-tools>\r\n * ```\r\n */\r\nexport class InvoiceTools extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {\r\n      /** Reference to the data reader object. */\r\n      reader: \"<\",\r\n    };\r\n\r\n    /** Uses the InvoiceToolsController */\r\n    public controller = InvoiceToolsController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/invoices/InvoiceTools.html\";\r\n\r\n}\r\n","import { InvoiceReportController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the report for the given invoice.\r\n * @example\r\n * ```html\r\n * <salaxy-invoice-report invoice=\"$ctrl.currentInvoice\"\"></salaxy-invoice-report>\r\n * ```\r\n */\r\nexport class InvoiceReport extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {\r\n      /** The invoice for the report. */\r\n      invoice: \"<\",\r\n      /** If true, uses the current style of the site. The default value is false. */\r\n      applySiteStyles: \"<\",\r\n      /** The language for report*/\r\n      lang: \"<\"\r\n    };\r\n\r\n    /** Uses the InvoiceReportController */\r\n    public controller = InvoiceReportController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/invoices/InvoiceReport.html\";\r\n\r\n}\r\n","import { CompanyInvoicesController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the invoice processing ui for companies.\r\n * @example\r\n * ```html\r\n * <salaxy-company-invoices></salaxy-company-invoices>\r\n * ```\r\n */\r\nexport class CompanyInvoices extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n      /**\r\n       * channel for the invocie processing. Default is PalkkausInvoices.\r\n       */\r\n         channel: \"<\",\r\n    };\r\n\r\n    /** Uses the InvoiceCrudController */\r\n    public controller = CompanyInvoicesController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/invoices/CompanyInvoices.html\";\r\n\r\n}\r\n","import { InvoiceAlertsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n\r\n/**\r\n * Component that displays alerts for invoices that are in \"Payment Started\" status.\r\n * This component shows warnings for each payment channel that has pending payments.\r\n * @example\r\n * ```html\r\n * <salaxy-invoice-alerts\r\n *   payment-channels=\"['palkkausManual', 'holvi', 'talenomOnline']\"\r\n *   is-pro=\"true\">\r\n * </salaxy-invoice-alerts>\r\n * ```\r\n */\r\nexport class InvoiceAlerts extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {\r\n      /** Payment channels for OData query. */\r\n      paymentChannels: \"<\",\r\n      /** Indicates if used in pro. */\r\n      isPro: \"<\"\r\n    };\r\n\r\n    /** Uses the InvoiceAlertsController */\r\n    public controller = InvoiceAlertsController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/invoices/InvoiceAlerts.html\";\r\n\r\n}\r\n","import { WorkerAssureController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * DEPRECATED: Being used by an isolated partner(s) that have special access.\r\n * => Remove in a next major release.\r\n * Alternative component for adding Worker accounts.\r\n * Uses the AssureWorkerAccount API service that is currently reserved for partner access.\r\n * @deprecated Being used by an isolated partner(s) that have special access. => Remove in a next major release.\r\n * @example\r\n * ```html\r\n * <salaxy-worker-assure></salaxy-worker-assure>\r\n * ```\r\n */\r\nexport class WorkerAssure extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {};\r\n\r\n    /** Uses the WorkerAssureController */\r\n    public controller = WorkerAssureController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/worker/WorkerAssure.html\";\r\n\r\n}\r\n","import { ODataHelperController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Renders the footer within OdataTable.\r\n * Requires salaxy-odata-table component as parent.\r\n * TODO: Example\r\n */\r\nexport class OdataFooter extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n        /** Type of paging */\r\n        paging: \"@\",\r\n\r\n        /**\r\n         * Manually defined URL for the nextPageLink.\r\n         * Browser is directed to this URL instead of loading more data from nextPageLink.\r\n         */\r\n        nextPageUrl: \"@\",\r\n    };\r\n\r\n    /** Attribute must be used within salaxy-odata-table component to access the common ODataQueryController  */\r\n    public require = {\r\n      $odata: \"^^salaxyOdataTable\",\r\n    };\r\n\r\n    /** Uses the ODataHelperController */\r\n    public controller = ODataHelperController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/odata/OdataFooter.html\";\r\n}\r\n","import { ODataQueryController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Helper for rendering an OData service based table / grid.\r\n */\r\nexport class OdataTable extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n        /** OData query options */\r\n        options: \"<\",\r\n\r\n        /** URL to the OData service. */\r\n        url: \"@\",\r\n\r\n        /** Data passed from the parent to the component / view */\r\n        data: \"<\",\r\n\r\n        /** Selected items for the case where the list is used as a select list (as opposed to link list). */\r\n        selectedItems: \"<\",\r\n\r\n        /** Current list of items. */\r\n        items: \"<\",\r\n\r\n        /**\r\n         * Function that is called when user selects an item in the list.\r\n         * Note that the event is called only in the selections (single and multi). Not when there is a link to details view in a link list.\r\n         * Function has the following locals: value: true/false, item: the last selected/unselected item, allItems: Array of all currently selected items.\r\n         * @example <salaxy-employment-list mode=\"select\" on-list-select=\"$ctrl.updateFromEmployment(item.id)\"></salaxy-employment-list>\r\n         */\r\n        onListSelect: \"&\",\r\n\r\n        /** Function that is called when the data has been loaded and set as values of the items. */\r\n        onDataLoaded: \"&\",\r\n\r\n        /**\r\n         * CRUD controller that typically defines the values for url template and\r\n         * @example\r\n         * <salaxy-odata-table crud-controller=\"PayrollCrudController as $crud\">\r\n         */\r\n        crudController: \"@\",\r\n\r\n        /**\r\n         * Optional bindings for the CRUD controller. All properties are set to crudController before calling init.\r\n         * @example\r\n         * <salaxy-odata-table crud-controller=\"PayrollCrudController as $crud\" crud-bindings=\"{ myProp: 'foobar' }\">\r\n         */\r\n        crudBindings: \"<\",\r\n\r\n        /** Defines the cache key. A non-null value also means that the caqche is enabled. */\r\n        cacheKey: \"@\",\r\n\r\n        /** Optional reader component for OData. Uses the given url and reads data from the OData source. */\r\n        reader: \"<\",\r\n\r\n        /** If readOnly is true, edit, copy etc. buttons from the new list view are hidden if readOnly property is supported */\r\n        readOnly: \"<\",\r\n\r\n        /** Logic object for component */\r\n        logic: \"<\",\r\n        /**Select mode for component */\r\n        selectMode: \"<\"\r\n    };\r\n\r\n    /** Uses the ODataQueryController */\r\n    public controller = ODataQueryController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/odata/lists/_default.html\";\r\n\r\n    /** Rendered HTML replaces the original element */\r\n    public replace: true;\r\n}\r\n","import { ODataActionsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Renders the search box and export/import functions within OdataTable.\r\n * Requires salaxy-odata-table component as parent.\r\n */\r\nexport class OdataActions extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n        /** Default locale for data exports/imports. */\r\n        localeId: \"<\",\r\n        /** Flag indicating if the export options are visible. */\r\n        showExport: \"@\",\r\n    };\r\n\r\n    /** Attribute must be used within salaxy-odata-table component to access the common ODataQueryController  */\r\n    public require = {\r\n      $odata: \"^^salaxyOdataTable\",\r\n    };\r\n\r\n    /** Actions */\r\n    public transclude = true;\r\n\r\n    /** Uses the ODataActionsController */\r\n    public controller = ODataActionsController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/odata/OdataActions.html\";\r\n}\r\n","import { SessionController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows account authorization and Credentials information including\r\n * a link to Authorization document (digitally signed pdf) and\r\n * type and UID (typically e-mail) of the current credentials.\r\n * @example\r\n * ```html\r\n * <salaxy-account-authorization-person></salaxy-account-authorization-person>\r\n * ```\r\n */\r\nexport class AccountAuthorizationPerson extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to controller implementation\r\n     */\r\n    public bindings = {};\r\n\r\n    /** Uses the SessionController */\r\n    public controller = SessionController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/personal/AccountAuthorizationPerson.html\";\r\n}\r\n","\r\nimport { PersonAccountController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Edit the avatar information: Picture upload, Initials + color or Gravatar.\r\n * Currently used only in Personal accounts, but this could potentially be also\r\n * used in Company side to edit Avatar?\r\n * @example\r\n * ```html\r\n * <salaxy-account-avatar-edit-person></salaxy-account-avatar-edit-person>\r\n * ```\r\n */\r\nexport class AccountAvatarEditPerson extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n      /** Current person account. Optional */\r\n      current: \"<\",\r\n    };\r\n\r\n    /** Uses the PersonAccountController */\r\n    public controller = PersonAccountController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/personal/AccountAvatarEditPerson.html\";\r\n\r\n}\r\n","\r\nimport { PersonAccountController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Editing UI of Contact information for Personal account.\r\n * @example\r\n * ```html\r\n * <salaxy-account-contact-edit-person></salaxy-account-contact-edit-person>\r\n * ```\r\n */\r\nexport class AccountContactEditPerson extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n      /** Current person account. Optional */\r\n      current: \"<\",\r\n    };\r\n\r\n    /** Uses the PersonAccountController */\r\n    public controller = PersonAccountController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/personal/AccountContactEditPerson.html\";\r\n\r\n}\r\n","\r\nimport { PersonAccountController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Editor view for Person's contact and payment information,\r\n * for example avatar, phone number and bank account number.\r\n * @example\r\n * ```html\r\n * <salaxy-account-details-person></salaxy-account-details-person>\r\n * ```\r\n */\r\nexport class AccountDetailsPerson extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n      /** Current tab in initialization. If not set, will be fetched from url hash. */\r\n      currentTab: \"@\",\r\n    };\r\n\r\n    /** Uses the PersonAccountController */\r\n    public controller = PersonAccountController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/personal/AccountDetailsPerson.html\";\r\n\r\n}\r\n","import { PersonAccountController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Editor for main identity data of Personal account: Names (currently opens a wizard),\r\n * Personal ID (read-only) or IBAN (should require strong authentication).\r\n * @example\r\n * ```html\r\n * <salaxy-account-details-edit-person></salaxy-account-details-edit-person>\r\n * ```\r\n */\r\nexport class AccountDetailsEditPerson extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n      /** Current person account. Optional */\r\n      current: \"<\",\r\n    };\r\n\r\n    /** Uses the PersonAccountController */\r\n    public controller = PersonAccountController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/personal/AccountDetailsEditPerson.html\";\r\n\r\n}\r\n","import { SessionController} from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Quick basic information about the Person account: Avatar, name, phone and e-mail.\r\n * The component may be bound with ng-model or if omitted binds to session current account.\r\n * The component is currently for Personal acocunt only, but it could be generalized\r\n * for companies as well.\r\n * @example\r\n * ```html\r\n * <salaxy-account-info-person view-type=\"details\" ng-model=\"\"></salaxy-account-info-person>\r\n * ```\r\n */\r\nexport class AccountInfoPerson extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n\r\n    };\r\n\r\n    /** ngModel may be used */\r\n    public require = {\r\n      model: \"?ngModel\",\r\n    };\r\n\r\n    /** Uses the SessionController */\r\n    public controller = SessionController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/personal/AccountInfoPerson.html\";\r\n\r\n}\r\n","\r\nimport { CompanySettingsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Edit UI for Household's own insurance information including Pension and Unemployment insurance.\r\n * Designed for Person Employer only, should not be shown in Worker scenarios as it may be confusing.\r\n * @example\r\n * ```html\r\n * <salaxy-account-insurance-edit-person></salaxy-account-insurance-edit-person>\r\n * ```\r\n */\r\nexport class AccountInsuranceEditPerson extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n    };\r\n\r\n    /** Uses the CompanySettingsController */\r\n    public controller = CompanySettingsController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/personal/AccountInsuranceEditPerson.html\";\r\n\r\n}\r\n","import { EmployerListController } from \"../../controllers\";\r\nimport { ApiCrudObjectControllerBindings } from \"../../controllers/bases\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows employer list\r\n * @example\r\n * ```html\r\n * <salaxy-employer-list></salaxy-employer-list>\r\n * ```\r\n */\r\nexport class EmployerList extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n   public bindings = (new class extends ApiCrudObjectControllerBindings {\r\n\r\n     /** Selected items for the case where the list is used as a select list (as opposed to link list). */\r\n     selectedItems = \"<\";\r\n\r\n     /** Current list of items. */\r\n     items = \"<\";\r\n    /**\r\n     * Function that is called when user selects an item in the list.\r\n     * Note that the event is called only in the selection. Not when there is a link to details view in a link list.\r\n     * Function has the following locals: value: true/false, item: the last selected/unselected item.\r\n     * @example <salaxy-employer-select on-employer-select=\"$ctrl.updateFromEmployment(item.id)\"></salaxy-employer-select>\r\n     */\r\n      onEmployerSelect = \"&\";\r\n\r\n    }());\r\n\r\n    /** Uses the CalcSharingController */\r\n    public controller = EmployerListController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/personal/EmployerList.html\";\r\n\r\n}\r\n","import { EmployerReportController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the employer report.\r\n * @example\r\n * ```html\r\n * <salaxy-employer-report></salaxy-employer-report>\r\n * ```\r\n */\r\nexport class EmployerReport extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n  };\r\n\r\n  /** Uses the EmployerReportController */\r\n  public controller = EmployerReportController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/personal/EmployerReport.html\";\r\n\r\n}\r\n","import { EmployerSelectController } from \"../../controllers\";\r\nimport { ApiCrudObjectControllerBindings } from \"../../controllers/bases\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows employer selection\r\n * @example\r\n * ```html\r\n * <salaxy-employer-select model=\"\" on-employer-select=\"\"></salaxy-employer-select>\r\n * ```\r\n */\r\nexport class EmployerSelect extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n   public bindings = (new class extends ApiCrudObjectControllerBindings {\r\n\r\n     /** Selected items for the case where the list is used as a select list (as opposed to link list). */\r\n     selectedItems = \"<\";\r\n\r\n     /** Current list of items. */\r\n     items = \"<\";\r\n    /**\r\n     * Function that is called when user selects an item in the list.\r\n     * Note that the event is called only in the selection. Not when there is a link to details view in a link list.\r\n     * Function has the following locals: value: true/false, item: the last selected/unselected item.\r\n     * @example <salaxy-employer-select on-employer-select=\"$ctrl.updateFromEmployment(item.id)\"></salaxy-employer-select>\r\n     */\r\n      onEmployerSelect = \"&\";\r\n\r\n    }());\r\n\r\n    /** Uses the CalcSharingController */\r\n    public controller = EmployerSelectController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/personal/EmployerSelect.html\";\r\n\r\n}\r\n","import { CalcHouseholdUsecaseController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * UI for setting the Household Usecases within the calculator\r\n * @example\r\n * ```html\r\n * <salaxy-calc-household-usecase calc=\"$ctrl.currentCalc\"></salaxy-calc-household-usecase>\r\n * ```\r\n */\r\nexport class CalcHouseholdUsecase extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n    /** The calculation that the component edits */\r\n    calc: \"<\",\r\n\r\n    /** Alternative data binding: creates a calculation based on Worker defaults. */\r\n    worker: \"<\",\r\n\r\n    /**\r\n     * Shows the Save and Reset buttons.\r\n     * Currently, this is only enabled for WorkerAccount data binding, but may later be enabled for calc.\r\n     */\r\n    showSave: \"<\",\r\n\r\n    /** isReadOnly*/\r\n    isReadOnly: \"<\"\r\n  };\r\n\r\n  /** Uses the CalcHouseholdUsecaseController */\r\n  public controller = CalcHouseholdUsecaseController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/personal/CalcHouseholdUsecase.html\";\r\n\r\n}\r\n","import { CalcSharingController } from \"../../controllers\";\r\nimport { ApiCrudObjectControllerBindings } from \"../../controllers/bases\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the sharing control for the current calculation\r\n * @example\r\n * ```html\r\n * <salaxy-calc-sharing model='url'></salaxy-calc-sharing>\r\n * ```\r\n */\r\nexport class CalcSharing extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n   public bindings = (new class extends ApiCrudObjectControllerBindings {\r\n\r\n       /** If true, template shows option to share direct link to the calculation. Currently used only in Rakennusliitto site. */\r\n      public showLinkSharing = \"<\";\r\n    }());\r\n\r\n    /** Uses the CalcSharingController */\r\n    public controller = CalcSharingController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/personal/CalcSharing.html\";\r\n\r\n}\r\n","import { CalcSharingController } from \"../../controllers\";\r\nimport { ApiCrudObjectControllerBindings } from \"../../controllers/bases\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the current status of sharing for the calculation\r\n * @example\r\n * ```html\r\n * <salaxy-calc-sharing-info model='url'></salaxy-calc-sharing-info>\r\n * ```\r\n */\r\nexport class CalcSharingInfo extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = new ApiCrudObjectControllerBindings();\r\n\r\n    /** Uses the CalcSharingController */\r\n    public controller = CalcSharingController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/personal/CalcSharingInfo.html\";\r\n\r\n}\r\n","import { HouseholdDeductionReportController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the household deduction report.\r\n * @example\r\n * ```html\r\n * <salaxy-household-deduction-report></salaxy-household-deduction-report>\r\n * ```\r\n */\r\nexport class HouseholdDeductionReport extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n  };\r\n\r\n  /** Uses the HouseholdDeductionReportController */\r\n  public controller = HouseholdDeductionReportController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/personal/HouseholdDeductionReport.html\";\r\n\r\n}\r\n","import { WorkerReportController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the worker report.\r\n * @example\r\n * ```html\r\n * <salaxy-worker-report></salaxy-worker-report>\r\n * ```\r\n */\r\nexport class WorkerReport extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n  };\r\n\r\n  /** Uses the WorkerReportController */\r\n  public controller = WorkerReportController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/personal/WorkerReport.html\";\r\n\r\n}\r\n","import { HouseholdYearCrudController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a list of household yearly deductions.\r\n * @example\r\n * ```html\r\n * <salaxy-household-year-list></salaxy-household-year-list>\r\n * ```\r\n */\r\nexport class HouseholdYearList extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = { };\r\n\r\n    /** Uses the HouseholdYearCrudController */\r\n    public controller = HouseholdYearCrudController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/personal/HouseholdYearList.html\";\r\n\r\n}\r\n","import { ApiCrudObjectControllerBindings, HouseholdYearCrudController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Edit / actions user interface for a year specific household deductions.\r\n * @example\r\n * ```html\r\n * <salaxy-household-year-details model=\"'url'\"></salaxy-household-year-details>\r\n * ```\r\n */\r\nexport class HouseholdYearDetails extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = new ApiCrudObjectControllerBindings();\r\n\r\n    /** Uses the HouseholdYearCrudController */\r\n    public controller = HouseholdYearCrudController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/personal/HouseholdYearDetails.html\";\r\n\r\n}\r\n","import { AccountingReportCrudController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a list of accounting reports.\r\n * @example\r\n * ```html\r\n * <salaxy-accounting-report-list></salaxy-accounting-report-list>\r\n * ```\r\n */\r\nexport class AccountingReportList extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n      /**\r\n       * list view 'mode'.\r\n       * If undefined, defaults to full list.\r\n       * Use panel for dashboards etc.\r\n       */\r\n      mode: \"@\",\r\n\r\n     };\r\n\r\n    /** Uses the AccountingReportCrudController */\r\n    public controller = AccountingReportCrudController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/report/AccountingReportList.html\";\r\n\r\n}\r\n","import { AccountingReportQueryController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the accounting report builder for ad hoc reporting queries.\r\n * @example\r\n * ```html\r\n * <salaxy-accounting-report-query></salaxy-accounting-report-query>\r\n * ```\r\n */\r\nexport class AccountingReportQuery extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {\r\n      /**\r\n       * Specify the calculations that should be reported.\r\n       * If null, will show a user interface to select calculations or period.\r\n       */\r\n      calcs: \"<\",\r\n\r\n      /**\r\n       * Report view table only (partial) or pdf preview (full)\r\n       * Defaults to 'partial'\r\n       */\r\n      view: \"<\",\r\n      /** The language for report*/\r\n      lang: \"<\"\r\n    };\r\n\r\n    /** Uses the AccountingReportQueryController */\r\n    public controller = AccountingReportQueryController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/report/AccountingReportQuery.html\";\r\n\r\n}\r\n","import { AccountingReportRowsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the rows of the accounting report.\r\n * @example\r\n * ```html\r\n * <salaxy-accounting-report-rows data=\"$ctrl.data\"></salaxy-accouting-report-rows>\r\n * ```\r\n */\r\nexport class AccountingReportRows extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n    /** Accounting data */\r\n    data: \"<\",\r\n    /**\r\n     * Report view table only (partial) or pdf preview (full)\r\n     * Defaults to 'partial'\r\n     */\r\n    view: \"<\",\r\n    /** The language for report*/\r\n    lang: \"<\"\r\n  };\r\n\r\n  /** Uses the AccountingReportRowsController */\r\n  public controller = AccountingReportRowsController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/report/AccountingReportRows.html\";\r\n\r\n}\r\n","import { AccountingReportToolsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the export tools for the accounting report.\r\n * @example\r\n * ```html\r\n * <salaxy-accounting-report-tools reader=\"$ctrl.dataReader\"></salaxy-accouting-report-tools>\r\n * ```\r\n */\r\nexport class AccountingReportTools extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n    /** Reference to the data reader object. */\r\n    reader: \"<\",\r\n    /** Called when the target has been changed. */\r\n    onTargetChange: \"&\",\r\n    /** Called when the expand button state changed */\r\n    onExpandChange: \"&\",\r\n    /** Binded expand state*/\r\n    anyExpanded: \"<\",\r\n\r\n    /**\r\n     * Report view table only (partial) or pdf preview (full)\r\n     * Defaults to 'partial'\r\n     */\r\n    view: \"<\"\r\n  };\r\n\r\n  /** Uses the AccountingReportToolsController */\r\n  public controller = AccountingReportToolsController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/report/AccountingReportTools.html\";\r\n\r\n}\r\n","import { AccountingReportCrudController } from \"../../controllers\";\r\nimport { ApiCrudObjectControllerBindings } from \"../../controllers/bases\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the accounting report viewer for the pre-built reports.\r\n * @example\r\n * ```html\r\n * <salaxy-accounting-report-viewer model='url'></salaxy-accounting-report-viewer>\r\n * ```\r\n */\r\nexport class AccountingReportViewer extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = new ApiCrudObjectControllerBindings();\r\n\r\n    /** Uses the AccountingReportCrudController */\r\n    public controller = AccountingReportCrudController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/report/AccountingReportViewer.html\";\r\n}\r\n","import { CalculationReportController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the calculation report builder for ad hoc calculation reports.\r\n * @example\r\n * ```html\r\n * <salaxy-calculation-report template-id=\"plain\"></salaxy-calculation-report>\r\n * ```\r\n */\r\nexport class CalculationReport extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {\r\n      /** Template for the report */\r\n      templateId: \"<\",\r\n    };\r\n\r\n    /** Uses the CalculationReportController */\r\n    public controller = CalculationReportController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/report/CalculationReport.html\";\r\n\r\n}\r\n","import { HolidayReportController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows holiday report of selected holiday year\r\n * @example\r\n * ```html\r\n * <salaxy-holiday-report></salaxy-holiday-report>\r\n * ```\r\n */\r\nexport class HolidayReport extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {};\r\n\r\n    /** Uses the HolidayReportController */\r\n    public controller = HolidayReportController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/report/HolidayReport.html\";\r\n\r\n}\r\n","import { ApiCrudObjectControllerBindings, IrEarningsPaymentCrudController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a user interface for Earnings Payment Report (\"Tulorekisteri-ilmoitus\").\r\n * Currently, the UI is read-only, but it may later be extended to be editable\r\n * for purposes of corrections.\r\n * @example\r\n * ```html\r\n * <salaxy-ir-earnings-payment model=\"$ctrl.current\"></salaxy-ir-earnings-payment>\r\n * ```\r\n */\r\nexport class IrEarningsPayment extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = (new class extends ApiCrudObjectControllerBindings {\r\n    /**\r\n     * Alternative model binding.\r\n     * Instead of model=\"EarningsPaymentId\", you may specify calculation-id=\"calculationId\"\r\n     */\r\n    public calculationId = \"<\";\r\n\r\n    /**\r\n     * Alternative model binding.\r\n     * Instead of model=\"EarningsPaymentId\", you may specify calculation=\"calculation\"\r\n     */\r\n    public calculation = \"<\";\r\n\r\n    /**\r\n     * Alternative model binding.\r\n     * In this case, you should set both the model (using model) and the calculation (using calculationFor)\r\n     */\r\n    public calculationFor = \"<\";\r\n  }());\r\n\r\n  /** Uses the EarningsPaymentReportController */\r\n  public controller = IrEarningsPaymentCrudController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/report/IrEarningsPayment.html\";\r\n\r\n}\r\n","import { IrEarningsPaymentCrudController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a list of earnings payments.\r\n * @example\r\n * ```html\r\n * <salaxy-ir-earnings-payment-list></salaxy-ir-earnings-payment-list>\r\n * ```\r\n */\r\nexport class IrEarningsPaymentList extends ComponentBase {\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n  };\r\n\r\n  /** Uses the AccountingReportCrudController */\r\n  public controller = IrEarningsPaymentCrudController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/report/IrEarningsPaymentList.html\";\r\n\r\n}\r\n","import { ApiCrudObjectControllerBindings, IrPayerSummaryCrudController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a user interface for Payer Summary Report (\"Erillisilmoitus\").\r\n * Currently, the UI is read-only, but it may later be extended to be editable\r\n * for purposes of corrections.\r\n * @example\r\n * ```html\r\n * <salaxy-ir-payer-summary model=\"$ctrl.current\"></salaxy-ir-payer-summary>\r\n * ```\r\n */\r\nexport class IrPayerSummary extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = (new class extends ApiCrudObjectControllerBindings {\r\n  }());\r\n\r\n  /** Uses the IrPayerSummaryCrudController */\r\n  public controller = IrPayerSummaryCrudController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/report/IrPayerSummary.html\";\r\n\r\n}\r\n","import { IrPayerSummaryCrudController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a list of payer summaries.\r\n * @example\r\n * ```html\r\n * <salaxy-ir-payer-summary-list></salaxy-ir-payer-summary-list>\r\n * ```\r\n */\r\nexport class IrPayerSummaryList extends ComponentBase {\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n  };\r\n\r\n  /** Uses the AccountingReportCrudController */\r\n  public controller = IrPayerSummaryCrudController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/report/IrPayerSummaryList.html\";\r\n\r\n}\r\n","import { PayCertificateController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a wizard for creating a pay certificate for a worker.\r\n * @example\r\n * ```html\r\n * <salaxy-pay-certificate></salaxy-pay-certificate>\r\n * ```\r\n */\r\nexport class PayCertificate extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = { };\r\n\r\n    /** Uses the PayCertificateController */\r\n    public controller = PayCertificateController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/report/PayCertificate.html\";\r\n\r\n}\r\n","import { ReportsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a list of reports\r\n * @example\r\n * ```html\r\n * <salaxy-report-list report-type=\"unemployment\"></salaxy-report-list>\r\n * ```\r\n */\r\nexport class ReportList extends ComponentBase {\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {\r\n        /**\r\n         * - report-type: Type of the report (string, see reportType enumeration) that is shown in the list.\r\n         * Also supports value null/\"current\" for showing reports defined by reportsService.currentReportType.\r\n         */\r\n        reportType: \"<\",\r\n\r\n        /**\r\n         * -title\r\n         * Heading of the list. Supports translation keys.\r\n         * Default is reportType based enumeration translation.\r\n         */\r\n        heading: \"@\",\r\n    };\r\n\r\n    /** Uses the ReportsController */\r\n    public controller = ReportsController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/report/ReportList.html\";\r\n\r\n}\r\n","import { SalaryReportCrudController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a list of salary reports.\r\n * @example\r\n * ```html\r\n * <salaxy-salary-report-list mode=\"panel\"></salaxy-salary-report-list>\r\n * ```\r\n */\r\nexport class SalaryReportList extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n      /**\r\n       * list view 'mode'.\r\n       * If undefined, defaults to full list.\r\n       * Use panel for dashboards etc.\r\n       */\r\n      mode: \"@\",\r\n\r\n     };\r\n\r\n    /** Uses the AccountingReportCrudController */\r\n    public controller = SalaryReportCrudController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/report/SalaryReportList.html\";\r\n\r\n}\r\n","import { AccountingRowReportController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the rows report builder for ad hoc accounting row based reports.\r\n * @example\r\n * ```html\r\n * <salaxy-accounting-row-report template-id=\"plain\"></salaxy-accounting-row-report>\r\n * ```\r\n */\r\nexport class AccountingRowReport extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {\r\n      /** Template for the report */\r\n      templateId: \"<\",\r\n    };\r\n\r\n    /** Uses the AccountngRowReportController */\r\n    public controller = AccountingRowReportController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/report/AccountingRowReport.html\";\r\n\r\n}\r\n","import { SummaryReportController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the summary reports for the given data.\r\n * @example\r\n * ```html\r\n * <salaxy-summary-report data=\"$ctrl.data\"></salaxy-summary-report>\r\n * ```\r\n */\r\nexport class SummaryReport extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {\r\n      /** The data for the report. */\r\n      data: \"<\"\r\n    };\r\n\r\n    /** Uses the SummaryReportController */\r\n    public controller = SummaryReportController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/report/SummaryReport.html\";\r\n\r\n}\r\n","import { WorkerSummaryReportController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the summary reports for the given data.\r\n * @example\r\n * ```html\r\n * <salaxy-worker-summary-report data=\"$ctrl.data\"></salaxy-worker-summary-report>\r\n * ```\r\n */\r\nexport class WorkerSummaryReport extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {\r\n      /** The data for the report. */\r\n      data: \"<\"\r\n    };\r\n\r\n    /** Uses the WorkerSummaryReportController */\r\n    public controller = WorkerSummaryReportController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/report/WorkerSummaryReport.html\";\r\n\r\n}\r\n","import { AccountingHolidayPayDebtReportQueryController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the accounting holiday debt report builder for ad hoc reporting queries.\r\n * @example\r\n * ```html\r\n * <salaxy-accounting-holiday-debt-report-query></salaxy-accounting-holiday-debt-report-query>\r\n * ```\r\n */\r\nexport class AccountingHolidayPayDebtReportQuery extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {\r\n      /**\r\n       * Report view table only (partial) or pdf preview (full)\r\n       * Defaults to 'partial'\r\n       */\r\n      view: \"<\",\r\n      /** The language for report*/\r\n      lang: \"<\"\r\n    };\r\n\r\n    /** Uses the AccountingReportQueryController */\r\n    public controller = AccountingHolidayPayDebtReportQueryController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/report/AccountingHolidayPayDebtReportQuery.html\";\r\n\r\n}\r\n","import { HolidayPayReportQueryController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows holiday pay report of selected holiday year\r\n * @example\r\n * ```html\r\n * <salaxy-holiday-pay-report-query></salaxy-holiday-pay-report-query>\r\n * ```\r\n */\r\nexport class HolidayPayReportQuery extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {};\r\n\r\n    /** Uses the HolidayPayReportQueryController */\r\n    public controller = HolidayPayReportQueryController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/report/HolidayPayReportQuery.html\";\r\n\r\n}\r\n","import { SummaryReportQueryController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows summary report of selected period.\r\n * @example\r\n * ```html\r\n * <salaxy-summary-report-query></salaxy-summary-report-query>\r\n * ```\r\n */\r\nexport class SummaryReportQuery extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {};\r\n\r\n    /** Uses the SummaryReportQueryController */\r\n    public controller = SummaryReportQueryController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/report/SummaryReportQuery.html\";\r\n\r\n}\r\n","import { PayStatsReportQueryController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows pay statistics report for the employment.\r\n * @example\r\n * ```html\r\n * <salaxy-pay-stats-report-query></salaxy-pay-stats-report-query>\r\n * ```\r\n */\r\nexport class PayStatsReportQuery extends ComponentBase {\r\n\r\n   /**\r\n    * The following component properties (attributes in HTML) are bound to the Controller.\r\n    * For detailed functionality, refer to [controller](#controller) implementation.\r\n    */\r\n    public bindings = {\r\n      /** Optional employment id if not given in url */\r\n      employmentId : \"<\",\r\n    };\r\n\r\n    /** Uses the PayStatsReportQueryController */\r\n    public controller = PayStatsReportQueryController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/report/PayStatsReportQuery.html\";\r\n\r\n}\r\n","import { AccountantController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Payment Settings\r\n * @example\r\n * ```html\r\n * <salaxy-accountant></salaxy-accountant>\r\n * ```\r\n */\r\n\r\nexport class Accountant extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n\r\n    /** If true, removing accountant is disabled */\r\n    removalDisabled: \"<\"\r\n  };\r\n\r\n  /** Uses the AccountController */\r\n  public controller = AccountantController;\r\n\r\n  /** Default template is the view  */\r\n  public defaultTemplate = \"salaxy-components/settings/Accountant.html\";\r\n\r\n}\r\n","import { CompanySettingsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Accounting settings.\r\n * @example\r\n * ```html\r\n * <salaxy-accounting-settings></salaxy-accounting-settings>\r\n * ```\r\n */\r\n\r\nexport class AccountingSettings extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {};\r\n\r\n  /** Uses the CompanySettingsController */\r\n  public controller = CompanySettingsController;\r\n\r\n  /** Default template is the view  */\r\n  public defaultTemplate = \"salaxy-components/settings/AccountingSettings.html\";\r\n\r\n}\r\n","import { AccountingTargetCrudController, ApiCrudObjectControllerBindings } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Provides UI for viewing and adding new (modifying) accounting targets.\r\n * Accounting targets define where the accounting data is sent and how it is mapped to a Chart of Accounts (CoA)\r\n * @example\r\n * ```html\r\n * <salaxy-accounting-target-details></salaxy-accounting-target-details>\r\n * ```\r\n */\r\n\r\nexport class AccountingTargetDetails extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = new ApiCrudObjectControllerBindings();\r\n\r\n  /** Uses the AccountController */\r\n  public controller = AccountingTargetCrudController;\r\n\r\n  /** Default template is the view  */\r\n  public defaultTemplate = \"salaxy-components/settings/AccountingTargetDetails.html\";\r\n\r\n}\r\n","import { CompanySettingsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Accounting target settings.\r\n * @example\r\n * ```html\r\n * <salaxy-accounting-target-settings></salaxy-accounting-target-settings>\r\n * ```\r\n */\r\n\r\nexport class AccountingTargetSettings extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n    /** Forced read only state */\r\n    isReadOnlyForced: \"<\"\r\n  };\r\n\r\n  /** Uses the CompanySettingsController */\r\n  public controller = CompanySettingsController;\r\n\r\n  /** Default template is the view  */\r\n  public defaultTemplate = \"salaxy-components/settings/AccountingTargetSettings.html\";\r\n\r\n}\r\n","import { CompanySettingsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Cost accounting settings.\r\n * @example\r\n * ```html\r\n * <salaxy-cost-accounting-settings></salaxy-cost-accounting-settings>\r\n * ```\r\n */\r\n\r\nexport class CostAccountingSettings extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n     /** Forced read only state */\r\n     isReadOnlyForced: \"<\"\r\n  };\r\n\r\n  /** Uses the CompanySettingsController */\r\n  public controller = CompanySettingsController;\r\n\r\n  /** Default template is the view  */\r\n  public defaultTemplate = \"salaxy-components/settings/CostAccountingSettings.html\";\r\n\r\n}\r\n","import { CompanySettingsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Holiday settings.\r\n * @example\r\n * ```html\r\n * <salaxy-holiday-settings></salaxy-holiday-settings>\r\n * ```\r\n */\r\n\r\nexport class HolidaySettings extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {};\r\n\r\n  /** Uses the CompanySettingsController */\r\n  public controller = CompanySettingsController;\r\n\r\n  /** Default template is the view  */\r\n  public defaultTemplate = \"salaxy-components/settings/HolidaySettings.html\";\r\n\r\n}\r\n","import { InsuranceWizardController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shop in shop modal for getting Lähitapiola insurance.\r\n * @example\r\n * ```html\r\n * <salaxy-insurance></salaxy-insurance>\r\n * ```\r\n */\r\nexport class Insurance extends ComponentBase {\r\n\r\n/**\r\n * The following component properties (attributes in HTML) are bound to the Controller.\r\n * For detailed functionality, refer to [controller](#controller) implementation.\r\n */\r\n    public bindings = {};\r\n\r\n    /** Uses the InsuranceWizardController */\r\n    public controller = InsuranceWizardController;\r\n\r\n    /** Uses the controller as aliasing */\r\n    public controllerAs = \"$ctrl\";\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/modals/account/Insurance.html\";\r\n\r\n}","import { CompanySettingsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Settings needed for insurance contracts and pension contracts.\r\n * @example\r\n * ```html\r\n * <salaxy-insurance-settings></salaxy-insurance-settings>\r\n * ```\r\n */\r\n\r\nexport class InsuranceSettings extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n    /**\r\n     * Array of section ids to show\r\n     * By default: ['pensionContracts','insuranceContracts']\r\n     * All options:\r\n     * 'pensionContracts': Pension related settings\r\n     * 'yelPensionContracts': Pension related settings\r\n     * 'insuranceContracts' : Insureance contract related settings\r\n     */\r\n    sections: \"<\",\r\n\r\n    /** Sets the isReadOnlyForced status. */\r\n    isReadOnlyForced:\"<\"\r\n  };\r\n\r\n  /** Uses the CompanySettingsController */\r\n  public controller = CompanySettingsController;\r\n\r\n  /** Default template is the view  */\r\n  public defaultTemplate = \"salaxy-components/settings/Insurances.html\";\r\n\r\n}\r\n","import { OwnerSettingsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * User interfaces for Owner and Beneficiary lists.\r\n * @example\r\n * ```html\r\n * <salaxy-owner-settings></salaxy-owner-settings>\r\n * ```\r\n */\r\n\r\nexport class OwnerSettings extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n    /** Sets the isReadOnlyForced status. */\r\n    isReadOnlyForced:\"<\"\r\n  };\r\n\r\n  /** Uses the OwnerSettingsController */\r\n  public controller = OwnerSettingsController;\r\n\r\n  /** Default template is the view  */\r\n  public defaultTemplate = \"salaxy-components/settings/OwnerSettings.html\";\r\n\r\n}\r\n","import { PaymentChannelSettingsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows and modifies Payment Settings related to Payment Channels\r\n * @example\r\n * ```html\r\n * <salaxy-payment-channel-settings></salaxy-payment-settings>\r\n * ```\r\n */\r\n\r\nexport class PaymentChannelSettings extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {};\r\n\r\n  /** Uses the AccountController */\r\n  public controller = PaymentChannelSettingsController;\r\n\r\n  /** Default template is the view  */\r\n  public defaultTemplate = \"salaxy-components/settings/PaymentChannelSettings.html\";\r\n\r\n}\r\n","import { CompanySettingsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Overall settings needed for starting salary payment.\r\n * @example\r\n * ```html\r\n * <salaxy-payment-settings></salaxy-payment-settings>\r\n * ```\r\n */\r\n\r\nexport class PaymentSettings extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n    /**\r\n     * Array of section ids to show\r\n     * By default: ['pensionContracts','insuranceContracts','incomesRegister']\r\n     * All options:\r\n     * 'pensionContracts': Pension related settings\r\n     * 'insuranceContracts' : Insureance contract related settings\r\n     * 'incomesRegister': Tax reporting related settings\r\n     * 'eInvoice': EInvoice related settings\r\n     * 'sepa' : Sepa payments related settings\r\n     * 'taxAndSocialSecuritySelfHandling': Settings for tax payments\r\n     * 'pensionSelfHandling': Settings for pension payments\r\n     * 'workerSelfHandling': Settings for net salary payments\r\n     * 'unemploymentSelfHandling' Settings for unemployment payments\r\n     */\r\n    sections: \"<\",\r\n\r\n    /** Sets the isReadOnlyForced status. */\r\n    isReadOnlyForced:\"<\"\r\n  };\r\n\r\n  /** Uses the CompanySettingsController */\r\n  public controller = CompanySettingsController;\r\n\r\n  /** Default template is the view  */\r\n  public defaultTemplate = \"salaxy-components/settings/PaymentSettings.html\";\r\n\r\n}\r\n","import { CompanySettingsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * All settings\r\n * @example\r\n * ```html\r\n * <salaxy-pro-settings></salaxy-pro-settings>\r\n * ```\r\n */\r\n\r\nexport class ProSettings extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {};\r\n\r\n  /** Uses the CompanySettingsController */\r\n  public controller = CompanySettingsController;\r\n\r\n  /** Default template is the view  */\r\n  public defaultTemplate = \"salaxy-components/settings/ProSettings.html\";\r\n\r\n}\r\n","import { RowTypesSettingsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Settings editor for Row types (Palkkalajit)\r\n * @example\r\n * ```html\r\n * <salaxy-row-types-sessings></salaxy-row-types-sessings>\r\n * ```\r\n */\r\nexport class RowTypesSettings extends ComponentBase {\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n    /**\r\n     * Defines the type of rows editor: \"builtIn\" for built-in rows,\r\n     * \"custom\" for custom rows, \"prices\" company specific default prices per row type.\r\n     */\r\n    mode: \"@\",\r\n\r\n    /**\r\n     * Set this property if you want to explicitly set the model.\r\n     * If undefinded, the component binds to company settings.\r\n     */\r\n    model: \"<\",\r\n  };\r\n\r\n  /** Uses the AccountController */\r\n  public controller = RowTypesSettingsController;\r\n\r\n  /** Default template is the view  */\r\n  public defaultTemplate = \"salaxy-components/settings/RowTypesSettings.html\";\r\n\r\n}\r\n","import { ServiceModelCrudController, ApiCrudObjectControllerBindings } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Provides UI for modifying service model.\r\n * @example\r\n * ```html\r\n * <salaxy-service-model-details></salaxy-service-model-details>\r\n * ```\r\n */\r\n\r\nexport class ServiceModelDetails extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = new ApiCrudObjectControllerBindings();\r\n\r\n  /** Uses the AccountController */\r\n  public controller = ServiceModelCrudController;\r\n\r\n  /** Default template is the view  */\r\n  public defaultTemplate = \"salaxy-components/settings/ServiceModelDetails.html\";\r\n\r\n}\r\n","import { CompanySettingsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * IR delivery settings.\r\n * @example\r\n * ```html\r\n * <salaxy-ir-delivery-settings></salaxy-ir-delivery-settings>\r\n * ```\r\n */\r\n\r\nexport class IrDeliverySettings extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {};\r\n\r\n  /** Uses the CompanySettingsController */\r\n  public controller = CompanySettingsController;\r\n\r\n  /** Default template is the view  */\r\n  public defaultTemplate = \"salaxy-components/settings/IrDeliverySettings.html\";\r\n\r\n}\r\n","import { CompanySettingsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Settings for pay statistics calculations.\r\n * @example\r\n * ```html\r\n * <salaxy-pay-stats-settings></salaxy-pay-stats-settings>\r\n * ```\r\n */\r\n\r\nexport class PayStatsSettings extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {};\r\n\r\n  /** Uses the CompanySettingsController */\r\n  public controller = CompanySettingsController;\r\n\r\n  /** Default template is the view  */\r\n  public defaultTemplate = \"salaxy-components/settings/PayStatsSettings.html\";\r\n\r\n}\r\n","import { SxyFormElementController } from \"../../controllers\";\r\n\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows an alert with type \"error\" or one of the bootstrap styles: \"danger\", \"info\", \"warning\", \"success\".\r\n * @example\r\n * ```html\r\n * <sxy-alert type=\"primary\"><strong>NOTE:</strong> Here is a primary message to user.</sxy-alert>\r\n * <sxy-alert type=\"error\" icon=\"fa-sign-in\" msg=\"SALAXY.NG1.WelcomeComponent.showAnon.main.html\"></sxy-alert>\r\n * ```\r\n */\r\nexport class SxyAlert extends ComponentBase {\r\n\r\n  /** Inner content is the message. */\r\n  public transclude = true;\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n\r\n    /**\r\n     * Possibility to speicfy a font-awesome icon.\r\n     * Setting \"none\", will show no icon.\r\n     * If not set, it is determined by type.\r\n     */\r\n    icon: \"@\",\r\n\r\n    /** Type of the alert is the Bootstrap style: Note that also \"primary\" and \"default\" are supported. */\r\n    type: \"@\",\r\n\r\n    /**\r\n     * Translation key to HTML that should be the main message of the alert.\r\n     * You can alternatively provide html as main element (transclude).\r\n     */\r\n    msg: \"@\",\r\n\r\n    /**\r\n     * Alert main content as simple text.\r\n     * You can alternatively provide html as main element.\r\n     */\r\n    text: \"@\",\r\n\r\n    /**\r\n     * Optional Details part of the alert.\r\n     * Will automatically show \"Read more\" button.\r\n     */\r\n    aside: \"@\",\r\n  };\r\n\r\n  /** Uses the SxyFormElementController */\r\n  public controller = SxyFormElementController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/sxy-form/SxyAlert.html\";\r\n}\r\n","import { SxyCodeEditorController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Code editor can be used in editing JSON, Schema and even JavaScript and HTML.\r\n * The system uses external code editor (https://code-editor.salaxy.com / https://test-code-editor.salaxy.com) if available or falls back to textarea when not available.\r\n * @example\r\n * ```html\r\n * <sxy-code-editor ng-model=\"$ctrl.currentSchema\" lang=\"json\"></sxy-code-editor>\r\n * ```\r\n */\r\nexport class SxyCodeEditor extends ComponentBase {\r\n\r\n  /** Components contents can be used to set the initial code. */\r\n  public transclude = true;\r\n\r\n  /** ng-model may be used to binding the code to a string in an object. */\r\n  public require = {\r\n    model: \"?ngModel\",\r\n  };\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n    /** Type of user interface to render: \"monaco\" (default) or \"basic\" HTML (textarea/pre) */\r\n    mode: \"@\",\r\n    /** If true, the component is read-only */\r\n    readOnly: \"<\",\r\n    /**\r\n     * Language of the code, e.g. \"javascript\" (default), \"html\", \"json\" or \"css\".\r\n     * Currently only affects the Monaco editor.\r\n     */\r\n    lang: \"@\",\r\n\r\n    /**\r\n     * Type of the main object that is called \"item\" in the code.\r\n     * Type should be one of @salaxy/core types (e.g. \"Calculation\") or supported\r\n     * native types (currently [\"any\", \"string\", \"[]\"]). Default is any.\r\n     */\r\n    itemType: \"<\",\r\n\r\n    /** The height of the editor as CSS, (e.g. \"calc(100vh - 600px)\"). Default is \"400px\" */\r\n    height: \"@\",\r\n    /**\r\n     * Type of the editor to use: \"monaco\" (default), \"sample\" or \"formula\".\r\n     */\r\n    editor: \"@\"\r\n  };\r\n\r\n  /** Uses the SxyInputController */\r\n  public controller = SxyCodeEditorController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/sxy-form/SxyCodeEditor.html\";\r\n}\r\n","import { Objects } from \"@salaxy/core\";\r\n\r\nimport { SxyInputController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a fieldset based on a given object in form\r\n * @example\r\n * ```html\r\n * <sxy-fieldset model=\"form.identity\"></sxy-fieldset>\r\n * ```\r\n */\r\nexport class SxyFieldset extends ComponentBase {\r\n\r\n    /** sxy-form is required */\r\n    public require = {\r\n        form: \"^^sxyForm\",\r\n    };\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = Objects.extend(SxyInputController.bindings , {});\r\n\r\n    /** Uses the SxyInputController */\r\n    public controller = SxyInputController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/sxy-form/SxyFieldset.html\";\r\n}\r\n","import { SxyFormController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * The sxy-form component encapsulates the data binding and auto-generation logic for editable models using JSON schema.\r\n * @example\r\n * ```html\r\n * <sxy-form type=\"Calculation\" model=\"{}\"></sxy-form>\r\n * ```\r\n */\r\nexport class SxyForm extends ComponentBase {\r\n\r\n  /**\r\n   * Inner DIV element may be transclude.\r\n   * Future implementations will probably contain header, footer etc.\r\n   */\r\n  public transclude = {\r\n    div: \"?div\",\r\n  };\r\n\r\n  /** Component bindings. */\r\n  public bindings = {\r\n\r\n    /** Data object that is being edited by the fieldset. */\r\n    model: \"<\",\r\n\r\n    /** The data type that describes the object and creates the user interface. */\r\n    type: \"@\",\r\n\r\n    /**\r\n     * URL for the Open API document that contains the definition for the type.\r\n     * The url can be an absolute url, relative url or an url with salaxy-secure/ -prefix.\r\n     * The salaxy-secure/ -prefix will be replaced in runtime with the salaxy api server url of the curren environment.\r\n     */\r\n    openApi: \"@\",\r\n\r\n    /** Direct reference to internal document object. */\r\n    openApiDoc: \"<\",\r\n\r\n    /**\r\n     * The translation code for the label/legend/title.\r\n     * Default is \"SALAXY.MODEL.[type].title\"] or if not available, just the type text.\r\n     */\r\n    label: \"@\",\r\n\r\n    /**\r\n     * If true, the form is auto-generated from the type and inner HTML is ignored.\r\n     * If false (default), the inner HTML is used to show the form.\r\n     */\r\n    autoGen: \"<\",\r\n\r\n    /** If true, shows the form debugger */\r\n    debugger: \"<\",\r\n\r\n    /** Sets the entire form as read-only. Individual field may still be set read-only=false to make it editable. */\r\n    readOnly: \"@\",\r\n\r\n  };\r\n\r\n  /** Uses the SxyFormController */\r\n  public controller = SxyFormController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/sxy-form/SxyForm.html\";\r\n}\r\n","import { SxyGridController } from \"../../controllers\";\r\n\r\nimport { Objects } from \"@salaxy/core\";\r\n\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows a grid component for view / edit of arrays.\r\n * @example\r\n * ```html\r\n * <sxy-grid schema=\"UserDefinedRow\" data=\"$ctrl.temp\"></sxy-grid>\r\n * ```\r\n */\r\nexport class SxyGrid extends ComponentBase {\r\n\r\n    /** sxy-form is optional */\r\n    public require = {\r\n        form: \"?^^sxyForm\",\r\n    };\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = Objects.extend(SxyGridController.bindings , {});\r\n\r\n    /** Uses the SxyGridController */\r\n    public controller = SxyGridController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/sxy-form/SxyGrid.html\";\r\n}\r\n","import { SxyInputController } from \"../../controllers\";\r\n\r\nimport { Objects } from \"@salaxy/core\";\r\n\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows an input control with label, validation error, info etc.\r\n * @example\r\n * ```html\r\n * <sxy-ipt-text data-sxy=\"form.owner\" model=\"Calculation.owner\"></sxy-ipt-text>\r\n * ```\r\n */\r\nexport class SxyInput extends ComponentBase {\r\n\r\n    /** sxy-form is required */\r\n    public require = {\r\n        form: \"?^^sxyForm\",\r\n    };\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = Objects.extend(SxyInputController.bindings , {});\r\n\r\n    /**\r\n     * Transclude optional templates for input parts.\r\n     * Currently supports form, but may later support header, footer etc.\r\n     */\r\n    public transclude = {\r\n\r\n      /** Defines the inner form of Array dialogs and later potentially other dialogs and sub-forms */\r\n      form: \"?form\"\r\n    };\r\n\r\n    /** Uses the SxyIptController */\r\n    public controller = SxyInputController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/sxy-form/SxyInput.html\";\r\n}\r\n","import { SxySchemaEditorController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Open API schema editor: Used for editing schemas is usecases.\n * @example\r\n * ```html\r\n * <sxy-schema-editor model=\"$ctrl.currentSchema\"></sxy-schema-editor>\r\n * ```\r\n */\r\nexport class SxySchemaEditor extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n      model: \"<\",\r\n    };\r\n\r\n    /** Uses the SxyInputController */\r\n    public controller = SxySchemaEditorController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/sxy-form/SxySchemaEditor.html\";\r\n}\r\n","import { SxyTableController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Renders a read-only table based on a schema and ata.\r\n * @example <sxy-table></sxy-table>\r\n */\r\nexport class SxyTable extends ComponentBase {\r\n  /** Component bindings. */\r\n  public bindings = {\r\n    /** The schema definition that defines the structure of the grid. */\r\n    schemaDef: \"<\",\r\n\r\n    /** URL of the schema document that contains the schemaDef. If set with schema in init, loads the document.*/\r\n    doc: \"@\",\r\n\r\n    /** Key of schemaDef in doc. If set with doc in init, will load the schema document from server and set the schemaDef.*/\r\n    schema: \"@\",\r\n\r\n    /** Data that is rendered / edited in the grid. This is either an array or an object that implements getTabulatorConfig() method for ajax data.*/\r\n    data: \"<\",\r\n\r\n    /**\r\n     * List of columns to include in the grid.\r\n     * This may be an array or comma separated string of field names (or a property tree, e.g. \"owner.avatar.displayName\").\r\n     * Alternatively, the entries in the array may be be full Tabulator column definitions, where `field` propererty defines the\r\n     * data item and fetches the default properties from the schema.\r\n     */\r\n    include: \"<\",\r\n\r\n    /**\r\n     * List of columns to exclude from the grid.\r\n     * This property is currenlty used only if include property is undefined, i.e. in default\r\n     * rendering, which will render the first-level properties. As such, exclude does not really support property paths.\r\n     */\r\n    exclude: \"<\",\r\n\r\n    /** Additional configuration for the table in init. */\r\n    options: \"<\",\r\n\r\n    /** After init, exposes the Tabulator for calling methods. */\r\n    tabulator: \"<\",\r\n\r\n    /**\r\n     * Gets the state of filters or sets the initial state of filters.\r\n     * By default, the filters are not shown before showFilters() function is called.\r\n     * If the property / attribute is set to true before initial render, the filters are shown.\r\n     * Use showFilters() function to show or hide the filters after initial render.\r\n     */\r\n    filters: \"<\"\r\n  };\r\n\r\n  /** Uses the SxyTableController */\r\n  public controller = SxyTableController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/sxy-table/SxyTable.html\";\r\n}\r\n","import { AccountResetController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Methods for editing test account\r\n * @example\r\n * ```html\r\n * <salaxy-account-reset></salaxy-account-reset>\r\n * ```\r\n */\r\nexport class AccountReset extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to controller implementation\r\n     */\r\n    public bindings = {};\r\n\r\n    /** Uses the SessionController */\r\n    public controller = AccountResetController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/test/AccountReset.html\";\r\n}\r\n","import * as angular from \"angular\";\r\n\r\nimport { SmokeTestController } from \"../../controllers\";\r\n\r\n/**\r\n * Component for performing basic smoke test about salaxy libraries:\r\n * Are all the libraries and dependencies loaded and functional in the package.\r\n */\r\nexport class SmokeTest implements angular.IComponentOptions {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to controller implementation\r\n   */\r\n  bindings = {\r\n    /** Defines the view / set of tests: \"core\" or \"ng1\" */\r\n    mode: \"@\",\r\n  };\r\n\r\n  /** Uses the SalaxySmokeTestController */\r\n  public controller = SmokeTestController;\r\n\r\n  /** Teh template URL */\r\n  public templateUrl = \"salaxy-components/test/SmokeTest.html\";\r\n}\r\n","import { HolidayYearAccrualController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * UI for holiday accrual (lomapäivien kertymä) of the annual leave for a selected holiday period.\r\n * @example\r\n * ```html\r\n * <salaxy-holiday-year-accrual parent=\"$ctrl.current\"></salaxy-holiday-year-accrual>\r\n * ```\r\n */\r\nexport class HolidayYearAccrual extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = HolidayYearAccrualController.bindings;\r\n\r\n    /** Uses the HolidayYearAccrualController */\r\n    public controller = HolidayYearAccrualController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/worker/holidays/HolidayYearAccrual.html\";\r\n\r\n}\r\n","import { HolidayYearHolidaysController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * UI for the planned holidays list (lomakirjanpito / lomakalenteri) for a selected holiday year.\r\n * @example\r\n * ```html\r\n * <salaxy-holiday-year-holidays></salaxy-holiday-year-holidays>\r\n * ```\r\n */\r\nexport class HolidayYearHolidays extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = HolidayYearHolidaysController.bindings;\r\n\r\n    /** Uses the HolidayYearHolidaysController */\r\n    public controller = HolidayYearHolidaysController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/worker/holidays/HolidayYearHolidays.html\";\r\n\r\n}\r\n","import { HolidayYearPaidController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * User interface for the annual leave payments: HolidayCompensation, HolidayBonus and HolidaySalary.\r\n * These payments are typically fetched from paid calculations automatically,\r\n * but may also be marked paid manually. Also, in client-side logic, payments are fetched\r\n * optionally from Draft calculations.\r\n * @example\r\n * ```html\r\n * <salaxy-holiday-year-paid parent=\"$ctrl.current\"></salaxy-holiday-year-paid>\r\n * ```\r\n */\r\nexport class HolidayYearPaid extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = HolidayYearPaidController.bindings;\r\n\r\n    /** Uses the HolidayYearPaidController */\r\n    public controller = HolidayYearPaidController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/worker/holidays/HolidayYearPaid.html\";\r\n\r\n}\r\n","import { ApiCrudObjectControllerBindings, HolidayYearCrudController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * Viewing and modifying of Worker holidays (holiday years and related settings).\r\n * @example\r\n * ```html\r\n * <salaxy-worker-holidays></salaxy-worker-holidays>\r\n * ```\r\n */\r\nexport class WorkerHolidays extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = (new class extends ApiCrudObjectControllerBindings {\r\n\r\n      /**\r\n       * Alternative model binding.\r\n       * Instead of model=\"holidayYearId\", you may specify employment-id=\"employmentId\".\r\n       * This loads all the holiday years to HolidayYearCrudController.employmentHolidayYears\r\n       */\r\n      public employmentId = \"<\";\r\n\r\n      /**\r\n       * Setting this value (iso date) will specify the the holiday year:\r\n       * If the date is Jan-April will show the previous year, May-Dec will show the current year.\r\n       * Default is today.\r\n       */\r\n      public forDate = \"<\";\r\n\r\n      /**\r\n       * If true, the view is for accruals (not for paid holidays or holiday planning).\r\n       */\r\n      public isAccrualView: \"<\";\r\n\r\n    }());\r\n\r\n    /** Uses the HolidayYearCrudController */\r\n    public controller = HolidayYearCrudController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/worker/holidays/WorkerHolidays.html\";\r\n\r\n}\r\n","import { EmploymentTaxcardsController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * Helps listing current all tax cards for an employment relation (latest and previous ones).\r\n * @example\r\n * ```html\r\n * <salaxy-employment-taxcards employment-id=\"$ctrl.current.employmentId\"></salaxy-employment-taxcards>\r\n * ```\r\n */\r\nexport class EmploymentTaxcards extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n    /** Employment ID of the Worker whose taxcards are shown in the component. */\r\n    employmentId: \"<\",\r\n\r\n    /**\r\n     * View mode:\r\n     *\r\n     * - \"active\" only shows the active taxcard.\r\n     * - \"list\" only shows the history list.\r\n     * - \"all\" (default) shows both active and history.\r\n     */\r\n    mode: \"@\",\r\n\r\n    /**\r\n     * Event that is called when a taxcard is saved and the parent UI probably needs to be refreshed.\r\n     * @example <salaxy-employment-taxcards employment-id=\"$ctrl.current.employmentId\" on-save=\"$ctrl.refresh()\"></salaxy-employment-taxcards>\r\n     */\r\n     onSave: \"&\",\r\n\r\n\r\n     /** If true, does not show the save / current buttons - the parent must show them. */\r\n    hideButtons: \"<\",\r\n  };\r\n\r\n  /** Uses the EmploymentTaxcardsController */\r\n  public controller = EmploymentTaxcardsController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/worker/taxcard/EmploymentTaxcards.html\";\r\n}\r\n","import { ApiCrudObjectControllerBindings, TaxcardCrudController } from \"../../../controllers\";\r\n\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * Shows the editor for a taxcard.\r\n * @example\r\n * ```html\r\n * <salaxy-taxcard-details model=\"$ctrl\" mode=\"pro\"></salaxy-taxcard-details>\r\n * ```\r\n */\r\n\r\nexport class TaxcardDetails extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = (new class extends ApiCrudObjectControllerBindings {\r\n    /** Mode is either \"pro\" (for admin / PRO-ui) or \"default\" */\r\n    public mode = \"@\";\r\n    /**\r\n     * Either a valid Finnish Personal ID or \"self\" for the current Worker account.\r\n     * Required for creating a new taxcard: The personal ID is used for setting the connection to Worker account or self.\r\n     */\r\n    public personalId = \"<\";\r\n\r\n    /**\r\n     * Event that is called when a taxcard is saved and the parent UI probably needs to be refreshed.\r\n     * @example <salaxy-taxcard-details model=\"$ctrl.current.active\" personal-id=\"$ctrl.current.personalId\" on-save=\"$ctrl.reload()\"></salaxy-taxcard-details>\r\n     */\r\n    public onSave = \"&\";\r\n\r\n    /** If true, does not show the save / current buttons - the parent must show them. */\r\n    public hideButtons = \"<\";\r\n    /** Type of employment taxcard */\r\n    public employmentRelationTaxcardType = \"<\";\r\n  }());\r\n\r\n  /** Uses the TaxcardCrudController */\r\n  public controller = TaxcardCrudController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/worker/taxcard/TaxcardDetails.html\";\r\n\r\n}\r\n","import { ListControllerBaseBindings, TaxcardIncomeLogController } from \"../../../controllers\";\r\n\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\nclass TaxcardIncomeLogBindings extends ListControllerBaseBindings {\r\n /** If true, the list can be edited, by default it is read-only. */\r\n public editable = \"<\";\r\n}\r\n\r\n/**\r\n * Shows view / editor table for the income log of taxcard.\r\n * @example\r\n * ```html\r\n * <salaxy-taxcard-income-log parent=\"$ctrl.current\"></salaxy-taxcard-income-log>\r\n * ```\r\n */\r\n\r\nexport class TaxcardIncomeLog extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = new TaxcardIncomeLogBindings();\r\n\r\n  /** Uses the TaxcardIncomeLogController */\r\n  public controller = TaxcardIncomeLogController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/worker/taxcard/TaxcardIncomeLog.html\";\r\n\r\n}\r\n","import { TaxcardManualEditController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * Shows a UI for editing a manual taxcard.\n * Typically, this is only used for adding a new tacard: You should not edit existing taxcards except in very limited scenarios (admin/pro).\n * @example\r\n * ```html\r\n * <salaxy-taxcard-manual-edit ng-ref=\"$edit\" current=\"$ctrl.item\"></salaxy-taxcard-manual-edit>\r\n * <button type=\"submit\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" ng-disabled=\"!$edit.isFormValid\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n * ```\r\n */\r\nexport class TaxcardManualEdit extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n    /** The taxcard that is being edited */\r\n    current: \"<\",\r\n  };\r\n\r\n  /** Uses the ODataQueryController */\r\n  public controller = TaxcardManualEditController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/worker/taxcard/TaxcardManualEdit.html\";\r\n\r\n}\r\n","import { ODataQueryController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * Shows a list of workers and their taxcards\r\n * @example\r\n * ```html\r\n * <salaxy-tax-cards-list></salaxy-tax-cards-list>\r\n * ```\r\n */\r\nexport class TaxCardsList extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n\r\n  };\r\n\r\n  /** Uses the ODataQueryController */\r\n  public controller = ODataQueryController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/worker/taxcard/TaxCardsList.html\";\r\n\r\n}\r\n","import { ODataQueryController } from \"../../../controllers\";\r\nimport { ComponentBase } from \"../../_ComponentBase\";\r\n\r\n/**\r\n * Shows a list of taxcards\r\n * @example\r\n * ```html\r\n * <salaxy-taxcard-list ></salaxy-taxcard-list>\r\n * ```\r\n */\r\nexport class TaxcardList extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n      /**\r\n       * Function that is called when user selects an item in the list.\r\n       * Note that the event is called only in the selections (single and multi).\r\n       * Function has the following locals: value: true/false, item: the last selected/unselected item, allItems: Array of all currently selected items.\r\n       * @example <salaxy-taxcard-list mode=\"select\" options=\"$ctrl.logic.options\" on-list-select=\"$ctrl.logic.doSomething(item.id)\"></salaxy-taxcard-list>\r\n       */\r\n      onListSelect: \"&\",\r\n\r\n      /** Selected items for the case where the list is used as a select list (as opposed to link list). */\r\n      selectedItems: \"<\",\r\n\r\n      /** Type of the view. Currently supports \"default\", \"panel\" and \"select\" */\r\n      mode: \"@\",\r\n\r\n      /** OData query options */\r\n      options: \"<\",\r\n    };\r\n\r\n    /** Uses the ODataQueryController */\r\n    public controller = ODataQueryController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/worker/taxcard/TaxcardList.html\";\r\n\r\n}\r\n","import { AbsencePeriodsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * UI for the absences list (poissaolokirjanpito).\r\n * @example\r\n * ```html\r\n * <salaxy-absence-periods></salaxy-absence-periods>\r\n * ```\r\n */\r\nexport class AbsencePeriods extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = AbsencePeriodsController.bindings;\r\n\r\n    /** Uses the AbsencePeriodsController */\r\n    public controller = AbsencePeriodsController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/worker/AbsencePeriods.html\";\r\n\r\n}\r\n","import { ApiCrudObjectControllerBindings, EmploymentCrudController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Renders an edit view for single Employment relation (Worker for one Employer).\r\n * @example\r\n * ```html\r\n * <salaxy-employment-details-edit></salaxy-employment-details-edit>\r\n * ```\r\n */\r\nexport class EmploymentDetails extends ComponentBase {\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = (new class extends ApiCrudObjectControllerBindings {\r\n\r\n      /** Current tab in initialization. */\r\n      public currentTab = \"@\";\r\n\r\n      /** If true, the component is shown in modal: Hide buttons and switch employment works in a different way. */\r\n      public isModal = \"<\";\r\n    }());\r\n\r\n    /** Uses the EmploymentCrudController */\r\n    public controller = EmploymentCrudController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/worker/employment/Details.html\";\r\n\r\n}\r\n","import { ApiCrudObjectControllerBindings, WorkerAbsencesCrudController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * UI for absences of a single worker / employment relation.\r\n * @example\r\n * ```html\r\n * <salaxy-worker-absences employment-id=\"$ctrl.current.employmentId\"></salaxy-worker-absences>\r\n * ```\r\n */\r\nexport class WorkerAbsences extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = (new class extends ApiCrudObjectControllerBindings {\r\n\r\n      /**\r\n       * Alternative model binding.\r\n       * Instead of model=\"absenceObjectId\", you may specify employment-id=\"employmentId\"\r\n       */\r\n      public employmentId = \"<\";\r\n\r\n    }());\r\n\r\n    /** Uses the WorkerAbsencesCrudController */\r\n    public controller = WorkerAbsencesCrudController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/worker/WorkerAbsences.html\";\r\n\r\n}\r\n","import { ApiCrudObjectControllerBindings, WorkerAccountCrudController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * LEGACY: Shows a view of a single worker account, which may have one or several Employments Relations.\r\n * This used to be the main way of viewing and editing Worker AND Employment details, but now the Employment view is used instead.\r\n * @deprecated Use EmploymentDetails instead.\r\n */\r\nexport class WorkerDetails extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = new ApiCrudObjectControllerBindings();\r\n\r\n    /** Uses the WorkerAccountCrudController */\r\n    public controller = WorkerAccountCrudController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/worker/WorkerDetails.html\";\r\n\r\n}\r\n","import { ODataQueryController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n\r\n/**\r\n * Shows a list of employment relations for an employer.\r\n * Note that for backward compatibility, this list is also available as\r\n * salaxy-worker-list component (to be removed).\r\n * @example\r\n * ```html\r\n * <salaxy-employment-list limit-to=\"5\" mode=\"select\"></salaxy-employment-list>\r\n * <!--\r\n * Legacy:\r\n * <salaxy-worker-list limit-to=\"5\" mode=\"select\"></salaxy-worker-list>\r\n * -->\r\n * ```\r\n */\r\nexport class EmploymentList extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = {\r\n\r\n    /**\r\n     * Function that is called when user selects an item in the list.\r\n     * Note that the event is called only in the selections (single and multi). Not when there is a link to details view in a link list.\r\n     * Function has the following locals: value: true/false, item: the last selected/unselected item, allItems: Array of all currently selected items.\r\n     * @example <salaxy-employment-list mode=\"select\" on-list-select=\"$ctrl.updateFromEmployment(item.id)\"></salaxy-employment-list>\r\n     */\r\n    onListSelect: \"&\",\r\n\r\n    /** Selected items for the case where the list is used as a select list (as opposed to link list). */\r\n    selectedItems: \"<\",\r\n\r\n    /** Type of the view. Currently supports \"default\" and \"select\" */\r\n    mode: \"@\",\r\n\r\n    /** Max count of workers to show in the list. */\r\n    limitTo: \"<\",\r\n\r\n    /** If readOnly is true, edit, copy etc. buttons from the new list view are hidden if readOnly property is supported */\r\n    readOnly: \"<\",\r\n\r\n    /** boolean indicating if toolbar should be shown*/\r\n    showToolbar: \"<\"\r\n\r\n  };\r\n\r\n    /** Uses the ODataQueryController */\r\n    public controller = ODataQueryController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/worker/EmploymentList.html\";\r\n\r\n}\r\n","import { ApiCrudObjectControllerBindings, CalendarEventsCrudController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Renders an editor / details component for a Calendar Event.\r\n * @example\r\n * ```html\r\n * <salaxy-calendar-event-details model=\"'url\"></salaxy-calendar-event-details>\r\n * ```\r\n */\r\nexport class CalendarEventDetails extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = (new class extends ApiCrudObjectControllerBindings {}());\r\n\r\n  /** Uses the CalendarEventsCrudController */\r\n  public controller = CalendarEventsCrudController;\r\n\r\n  /** The default template for the component. */\r\n  public defaultTemplate = \"salaxy-components/workflow/CalendarEventDetails.html\";\r\n}\r\n","import { DatasetsCrudController, ApiCrudObjectControllerBindings } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Provides UI for viewing and editing datasets.\r\n * @example\r\n * ```html\r\n * <salaxy-dataset-details></salaxy-dataset-details>\r\n * ```\r\n */\r\n\r\nexport class DatasetDetails extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n   public bindings = (new class extends ApiCrudObjectControllerBindings {\r\n    /** Type of user interface to show. */\r\n    public mode = \"@\";\r\n\r\n    /** Defines the default usecase (uri) that is used for new calculations. */\r\n    public defaultUsecase = \"@\";\r\n  }());\r\n\r\n  /** Uses the DatasetsCrudController */\r\n  public controller = DatasetsCrudController;\r\n\r\n  /** Default template is the view  */\r\n  public defaultTemplate = \"salaxy-components/workflow/dataset/DatasetDetails.html\";\r\n\r\n}\r\n","import { UsecasesCrudController, ApiCrudObjectControllerBindings } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Provides UI for viewing and editing usecase.\r\n * @example\r\n * ```html\r\n * <salaxy-usecase-details></salaxy-usecase-details>\r\n * ```\r\n */\r\n\r\nexport class UsecaseDetails extends ComponentBase {\r\n\r\n  /**\r\n   * The following component properties (attributes in HTML) are bound to the Controller.\r\n   * For detailed functionality, refer to [controller](#controller) implementation.\r\n   */\r\n  public bindings = new ApiCrudObjectControllerBindings();\r\n\r\n  /** Uses the UsecasesCrudController */\r\n  public controller = UsecasesCrudController;\r\n\r\n  /** Default template is the view  */\r\n  public defaultTemplate = \"salaxy-components/workflow/usecases/UsecaseDetails.html\";\r\n\r\n}\r\n","import { RecordsController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * UI for records of the entity .\r\n * @example\r\n * ```html\r\n * <salaxy-records entity-type=\"'employment'\" api-ctrl=\"$worker\"></salaxy-records>\r\n * ```\r\n */\r\nexport class Records extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n     /**\r\n      * Binding to entity type\r\n      */\r\n      entityType: \"<\",\r\n\r\n      /** Expression for the api controller . */\r\n      apiCtrl: \"<\",\r\n\r\n      /** Binding to read only state */\r\n      readOnly: \"<\"\r\n\r\n    };\r\n\r\n    /** Uses the WorkerRecordsController */\r\n    public controller = RecordsController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/records/Records.html\";\r\n\r\n}\r\n","import { WorkflowController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Renders a workflow buttons in the toolbar for assign, issue, close.\r\n * @example\r\n * ```html\r\n * <salaxy-workflow-buttons api-ctrl=\"$ctrl\" disabled=\"!ok\"></salaxy-workflow-buttons>\r\n * ```\r\n */\r\nexport class WorkflowButtons extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n      /** Expression for the api controller . */\r\n      apiCtrl: \"<\",\r\n      /** Optional binding for enabling/disabling the controls */\r\n      disabled: \"<\",\r\n      /** on-change event */\r\n      onChange: \"&\",\r\n      /** Option to show/hide workflow assign control. Default is true */\r\n      showWorkflowAssign: \"<\"\r\n    };\r\n\r\n    /** Uses the WorkflowController */\r\n    public controller = WorkflowController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/workflow/WorkflowButtons.html\";\r\n}\r\n","import { WorkflowController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Renders a workflow re-open control.\r\n * @example\r\n * ```html\r\n * <salaxy-workflow-reopen api-ctrl=\"$ctrl\"  disabled=\"!ok\" ></salaxy-workflow-reopen>\r\n * ```\r\n */\r\nexport class WorkflowReopen extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n      /** Expression for the api controller . */\r\n      apiCtrl: \"<\",\r\n      /** Optional binding for enabling/disabling the control */\r\n      disabled: \"<\",\r\n      /** Called when workflow action has been taken */\r\n      onChange: \"&\",\r\n    };\r\n\r\n    /** Uses the WorkflowController */\r\n    public controller = WorkflowController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/workflow/WorkflowReopen.html\";\r\n}\r\n","import { WorkflowBadgeController } from \"../../controllers\";\r\nimport { ComponentBase } from \"../_ComponentBase\";\r\n\r\n/**\r\n * Shows the workflow badge for object or list item.\r\n * @example\r\n * ```html\r\n * <salaxy-workflow-badge api-ctrl=\"$ctrl\" model=\"$ctrl.current\" wf-types=\"'EmployerMessageRecord'\"></salaxy-workflow-badge>\r\n * ```\r\n */\r\nexport class WorkflowBadge extends ComponentBase {\r\n\r\n    /**\r\n     * The following component properties (attributes in HTML) are bound to the Controller.\r\n     * For detailed functionality, refer to [controller](#controller) implementation.\r\n     */\r\n    public bindings = {\r\n      /** Expression for the api controller . */\r\n      apiCtrl: \"<\",\r\n      /** Object or list item which contains workflow message data. */\r\n      model: \"<\",\r\n      /** Comma separated list of types to show the badge for. */\r\n      wfTypes: \"<\",\r\n      /** Visual mode of the component: horizontal or vertical (default). */\r\n      mode: \"@\"\r\n    };\r\n\r\n    /** Uses the WorkflowBadgeController */\r\n    public controller = WorkflowBadgeController;\r\n\r\n    /** The default template for the component. */\r\n    public defaultTemplate = \"salaxy-components/workflow/WorkflowBadge.html\";\r\n}\r\n","// Components\r\nimport {\r\n  AbsencePeriods,\r\n  Accountant,\r\n  AccountAuthorizationPerson,\r\n  AccountAvatarEdit,\r\n  AccountAvatarEditPerson,\r\n  AccountContactEdit,\r\n  AccountContactEditPerson,\r\n  AccountDetailsEditPerson,\r\n  AccountDetailsPerson,\r\n  AccountInfo,\r\n  AccountInfoPerson,\r\n  AccountingReportList,\r\n  AccountingReportQuery,\r\n  AccountingHolidayPayDebtReportQuery,\r\n  AccountingReportRows,\r\n  AccountingReportTools,\r\n  AccountingReportViewer,\r\n  AccountingRowReport,\r\n  AccountingSettings,\r\n  AccountingTargetDetails,\r\n  AccountingTargetSettings,\r\n  AccountInsuranceEditPerson,\r\n  AccountReset,\r\n  ActionButton,\r\n  Alert,\r\n  AssurePartner,\r\n  AuthCard,\r\n  AuthorizedAccounts,\r\n  AuthorizingAccounts,\r\n  Avatar,\r\n  Calc,\r\n  CalcChart,\r\n  CalcCostAccounting,\r\n  CalcDashboard,\r\n  CalendarEventDetails,\r\n  CalcEmployment,\r\n  CalcEditor,\r\n  CalcHouseholdUsecase,\r\n  CalcImport,\r\n  CalcIrRows,\r\n  CalcsIrRows,\r\n  CalcList,\r\n  CalcNewIntro,\r\n  CalcRepair,\r\n  CalcRepairInfo,\r\n  CalcReport,\r\n  CalcReports,\r\n  CalcResults,\r\n  CalcRowCostAccounting,\r\n  CalcRowDimensionInput,\r\n  CalcRowDocumentation,\r\n  CalcRowFormula,\r\n  CalcRowsEditor,\r\n  CalcRows2019Editor,\r\n  CalcRowType,\r\n  CalcSharing,\r\n  CalcSharingInfo,\r\n  CalcSharingReceiptAction,\r\n  CalcLeaves,\r\n  CalculationReport,\r\n  CalcUsecase,\r\n  CalcWorkerInfo,\r\n  CalcWorktime,\r\n  Calendar,\r\n  Certificates,\r\n  Chart,\r\n  CompanyImport,\r\n  CompanyInvoices,\r\n  ContactInfo,\r\n  CostAccounting,\r\n  CostAccountingSettings,\r\n  HolidaySettings,\r\n  Credentials,\r\n  CreditTransfer,\r\n  DataMapper,\r\n  DatasetDetails,\r\n  Datepicker,\r\n  DatepickerPopup,\r\n  DateRange,\r\n  EmployerList,\r\n  EmployerReport,\r\n  EmployerSelect,\r\n  EmploymentDetails,\r\n  EmploymentTaxcards,\r\n  ExpenseReport,\r\n  FormGroup,\r\n  HolidayPayReportQuery,\r\n  HolidayReport,\r\n  HolidayYearAccrual,\r\n  HolidayYearHolidays,\r\n  HolidayYearPaid,\r\n  HourlyReport,\r\n  HouseholdDeductionReport,\r\n  HouseholdYearDetails,\r\n  HouseholdYearList,\r\n  ImportStaging,\r\n  InputAccountingTarget,\r\n  Input,\r\n  InputBoolean,\r\n  InputCollectiveBargainAgreement,\r\n  InputCredential,\r\n  InputDuration,\r\n  InputEmployeeGroup,\r\n  InputEnum,\r\n  InputHolidayMultipliers,\r\n  InputPayStatsRowType,\r\n  InputIncomeType,\r\n  InputMarkdown,\r\n  InputNumber,\r\n  InputOccupationType,\r\n  InputRrule,\r\n  InputTime,\r\n  InputTypeahead,\r\n  Insurance,\r\n  InsuranceSettings,\r\n  InvoiceAlerts,\r\n  InvoiceEdit,\r\n  InvoiceList,\r\n  InvoicePreview,\r\n  InvoicesCreate,\r\n  InvoiceTools,\r\n  InvoiceReport,\r\n  InvoicePaymentList,\r\n  IrDeliverySettings,\r\n  IrEarningsPayment,\r\n  IrPayerSummary,\r\n  JsonFormatter,\r\n  JsonDiff,\r\n  LanguageSelector,\r\n  LoginButton,\r\n  MarkdownEditor,\r\n  MarkdownViewer,\r\n  MessageThread,\r\n  MessageThreadList,\r\n  NaviSitemap,\r\n  NaviStarterLayout,\r\n  OdataActions,\r\n  OdataFooter,\r\n  OdataTable,\r\n  OwnerSettings,\r\n  PayButton,\r\n  PayCertificate,\r\n  PaymentChannelInvoicePreview,\r\n  PaymentChannelSettings,\r\n  PaymentSettings,\r\n  PayrollAssistant,\r\n  PayrollDetails,\r\n  PayrollDetailsList,\r\n  PayrollDetailsSelectList,\r\n  PayrollEdit,\r\n  PayrollList,\r\n  PayrollSelectList,\r\n  PayStatsReportQuery,\r\n  PayStatsSettings,\r\n  ProSettings,\r\n  Records,\r\n  ReportList,\r\n  RowTypesSettings,\r\n  SalaryDateKindButton,\r\n  SalaryReportList,\r\n  ServiceModelDetails,\r\n  Signing,\r\n  SmokeTest,\r\n  Spinner,\r\n  SummaryReport,\r\n  SummaryReportQuery,\r\n  SxyAlert,\r\n  SxyCodeEditor,\r\n  SxyFieldset,\r\n  SxyForm,\r\n  SxyTable,\r\n  SxyGrid,\r\n  SxyInput,\r\n  SxySchemaEditor,\r\n  Tab,\r\n  Tabs,\r\n  TabButtons,\r\n  TaxcardDetails,\r\n  TaxcardIncomeLog,\r\n  TaxcardManualEdit,\r\n  TaxcardList,\r\n  TaxCardsList,\r\n  Textarea,\r\n  ToggleButtons,\r\n  Timer,\r\n  UiTranslator,\r\n  UsecaseDetails,\r\n  UserInfo,\r\n  ValidationSummary,\r\n  VarmaBanner,\r\n  Welcome,\r\n  WorkerAbsences,\r\n  WorkerAssure,\r\n  WorkerDetails,\r\n  WorkerHolidays,\r\n  WorkerImport,\r\n  EmploymentList,\r\n  WorkerReport,\r\n  WorkerSummaryReport,\r\n  WorkflowButtons,\r\n  WorkflowBadge,\r\n  WorkflowReopen,\r\n} from \"./index_components\";\r\nimport {\r\n  IrEarningsPaymentList,\r\n  IrPayerSummaryList\r\n} from \"./report\";\r\n\r\n/**\r\n * Provides the method for registering components to the module.\r\n */\r\nexport class ComponentsRegistration {\r\n\r\n  /** Gets the components for Module registration. */\r\n  public static getComponents() {\r\n    return {\r\n      // - account\r\n      salaxyAccountInfo: new AccountInfo() as any,\r\n      salaxyAssurePartner: new AssurePartner() as any,\r\n      salaxyAuthCard: new AuthCard() as any,\r\n      salaxyAuthorizedAccounts: new AuthorizedAccounts() as any,\r\n      salaxyAuthorizingAccounts: new AuthorizingAccounts() as any,\r\n      salaxyCertificates: new Certificates() as any,\r\n      salaxyCredentials: new Credentials() as any,\r\n      salaxyLanguageSelector: new LanguageSelector() as any,\r\n      salaxyLoginButton: new LoginButton() as any,\r\n      salaxySigning: new Signing() as any,\r\n      salaxyUserInfo: new UserInfo() as any,\r\n      salaxyAccountAvatarEdit: new AccountAvatarEdit() as any,\r\n      salaxyAccountContactEdit: new AccountContactEdit() as any,\r\n\r\n      // - personal\r\n      salaxyAccountAuthorizationPerson: new AccountAuthorizationPerson() as any,\r\n      salaxyAccountAvatarEditPerson: new AccountAvatarEditPerson() as any,\r\n      salaxyAccountContactEditPerson: new AccountContactEditPerson() as any,\r\n      salaxyAccountDetailsEditPerson: new AccountDetailsEditPerson() as any,\r\n      salaxyAccountDetailsPerson: new AccountDetailsPerson() as any,\r\n      salaxyAccountInfoPerson: new AccountInfoPerson() as any,\r\n      salaxyAccountInsuranceEditPerson: new AccountInsuranceEditPerson() as any,\r\n      salaxyEmployerList: new EmployerList() as any,\r\n      salaxyEmployerSelect: new EmployerSelect() as any,\r\n\r\n      // - calc\r\n      salaxyCalcEmployment: new CalcEmployment() as any,\r\n      salaxyCalcHouseholdUsecase: new CalcHouseholdUsecase() as any,\r\n      salaxyCalcIrRows: new CalcIrRows() as any,\r\n      salaxyCalcsIrRows: new CalcsIrRows() as any,\r\n      salaxyCalcList: new CalcList() as any,\r\n      salaxyCalcWorktime: new CalcWorktime() as any,\r\n      salaxyCalc: new Calc() as any,\r\n      salaxyCalcChart: new CalcChart() as any,\r\n      salaxyCalcDashboard: new CalcDashboard() as any,\r\n      salaxyCalcEditor: new CalcEditor() as any,\r\n      salaxyCalcNewIntro: new CalcNewIntro() as any,\r\n      salaxyCalcRepair: new CalcRepair() as any,\r\n      salaxyCalcRepairInfo: new CalcRepairInfo() as any,\r\n      salaxyCalcReport: new CalcReport() as any,\r\n      salaxyCalcReports: new CalcReports() as any,\r\n      salaxyCalcResults: new CalcResults() as any,\r\n      salaxyCalcRowType: new CalcRowType() as any,\r\n      salaxyCalcRowsEditor: new CalcRowsEditor() as any,\r\n      salaxyCalcRows2019Editor: new CalcRows2019Editor() as any,\r\n      salaxyCalcRowFormula: new CalcRowFormula() as any,\r\n      salaxyCalcUsecase: new CalcUsecase() as any,\r\n      salaxyPayrollDetails: new PayrollDetails() as any,\r\n      salaxyPayrollDetailsList: new PayrollDetailsList() as any,\r\n      salaxyPayrollDetailsSelectList: new PayrollDetailsSelectList() as any,\r\n      salaxyPayrollEdit: new PayrollEdit() as any,\r\n      salaxyPayrollList: new PayrollList() as any,\r\n      salaxyPayrollAssistant: new PayrollAssistant() as any,\r\n      salaxyPayButton: new PayButton() as any,\r\n      salaxySalaryDateKindButton: new SalaryDateKindButton() as any,\r\n      salaxyCalcSharing: new CalcSharing() as any,\r\n      salaxyCalcSharingInfo: new CalcSharingInfo() as any,\r\n      salaxyCalcSharingReceiptAction: new CalcSharingReceiptAction() as any,\r\n      salaxyCalcLeaves: new CalcLeaves() as any,\r\n      salaxyCalcWorkerInfo: new CalcWorkerInfo() as any,\r\n      salaxyPayrollSelectList: new PayrollSelectList as any,\r\n      salaxyCalcCostAccounting: new CalcCostAccounting as any,\r\n      salaxyCalcRowCostAccounting: new CalcRowCostAccounting as any,\r\n      salaxyCalcRowDimensionInput: new CalcRowDimensionInput as any,\r\n      salaxyCalcRowDocumentation: new CalcRowDocumentation as any,\r\n      salaxyCostAccounting: new CostAccounting as any,\r\n\r\n      // - communications\r\n      salaxyContactInfo: new ContactInfo() as any,\r\n      salaxyHourlyReport: new HourlyReport() as any,\r\n      salaxyMessageThread: new MessageThread() as any,\r\n      salaxyMessageThreadList: new MessageThreadList() as any,\r\n      salaxyTimer: new Timer() as any,\r\n      salaxyVarmaBanner: new VarmaBanner() as any,\r\n      salaxyWelcome: new Welcome() as any,\r\n      salaxyExpenseReport: new ExpenseReport() as any,\r\n\r\n      // - sxy-form framework\r\n      sxyAlert: new SxyAlert() as any,\r\n      sxyCodeEditor: new SxyCodeEditor() as any,\r\n      sxyFieldset: new SxyFieldset() as any,\r\n      sxyForm: new SxyForm() as any,\r\n      sxyGrid: new SxyGrid() as any,\r\n      sxyInput: new SxyInput() as any,\r\n      sxySchemaEditor: new SxySchemaEditor() as any,\r\n\r\n      // - sxy-table framework\r\n      sxyTable: new SxyTable() as any,\r\n\r\n      // - test: Test data and system testing.\r\n      salaxyAccountReset: new AccountReset() as any,\r\n      salaxySmokeTest: new SmokeTest() as any,\r\n\r\n      // - form-controls\r\n      salaxyDatepicker: new Datepicker() as any,\r\n      salaxyDatepickerPopup: new DatepickerPopup() as any,\r\n      salaxyDateRange: new DateRange() as any,\r\n      salaxyFormGroup: new FormGroup() as any,\r\n      salaxyInput: new Input() as any,\r\n      salaxyInputAccountingTarget: new InputAccountingTarget() as any,\r\n      salaxyInputBoolean: new InputBoolean() as any,\r\n      salaxyInputCollectiveBargainAgreement: new InputCollectiveBargainAgreement() as any,\r\n      salaxyInputCredential: new InputCredential() as any,\r\n      salaxyInputDuration: new InputDuration() as any,\r\n      salaxyInputEmployeeGroup: new InputEmployeeGroup() as any,\r\n      salaxyInputEnum: new InputEnum() as any,\r\n      salaxyInputIncomeType: new InputIncomeType() as any,\r\n      salaxyInputMarkdown: new InputMarkdown() as any,\r\n      salaxyMarkdownEditor: new MarkdownEditor() as any,\r\n      salaxyMarkdownViewer: new MarkdownViewer() as any,\r\n      salaxyInputNumber: new InputNumber() as any,\r\n      salaxyInputOccupationType: new InputOccupationType() as any,\r\n      salaxyInputRrule: new InputRrule() as any,\r\n      salaxyInputTime: new InputTime() as any,\r\n      salaxyInputTypeahead: new InputTypeahead() as any,\r\n      salaxyToggleButtons: new ToggleButtons() as any,\r\n      salaxyTextarea: new Textarea() as any,\r\n      salaxyValidationSummary: new ValidationSummary() as any,\r\n      salaxyInputHolidayMultipliers: new InputHolidayMultipliers() as any,\r\n      salaxyInputPayStatsRowType: new InputPayStatsRowType() as any,\r\n\r\n      // - helpers\r\n      salaxyActionButton: new ActionButton() as any,\r\n      salaxyAlert: new Alert() as any,\r\n      salaxyAvatar: new Avatar() as any,\r\n      salaxyChart: new Chart() as any,\r\n      salaxyCalendar: new Calendar() as any,\r\n      salaxyDataMapper: new DataMapper() as any,\r\n      salaxyJsonFormatter: new JsonFormatter() as any,\r\n      salaxyJsonDiff: new JsonDiff() as any,\r\n      salaxyNaviSitemap: new NaviSitemap() as any,\r\n      salaxyNaviStarterLayout: new NaviStarterLayout() as any,\r\n      salaxyOdataActions: new OdataActions() as any,\r\n      salaxyOdataFooter: new OdataFooter() as any,\r\n      salaxyOdataTable: new OdataTable() as any,\r\n      salaxySpinner: new Spinner() as any,\r\n      salaxyTabs: new Tabs() as any,\r\n      salaxyTab: new Tab() as any,\r\n      salaxyTabButtons: new TabButtons() as any,\r\n      salaxyUiTranslator: new UiTranslator() as any,\r\n\r\n      // - import\r\n      salaxyCalcImport: new CalcImport() as any,\r\n      salaxyCompanyImport: new CompanyImport() as any,\r\n      salaxyImportStaging: new ImportStaging() as any,\r\n      salaxyWorkerImport: new WorkerImport as any,\r\n\r\n      // - invoices\r\n      salaxyCreditTransfer: new CreditTransfer() as any,\r\n      salaxyInvoiceAlerts: new InvoiceAlerts() as any,\r\n      salaxyInvoiceEdit: new InvoiceEdit() as any,\r\n      salaxyInvoiceList: new InvoiceList() as any,\r\n      salaxyInvoicePreview: new InvoicePreview() as any,\r\n      salaxyInvoicesCreate: new InvoicesCreate() as any,\r\n      salaxyPaymentChannelInvoicePreview: new PaymentChannelInvoicePreview() as any,\r\n      salaxyInvoiceTools: new InvoiceTools() as any,\r\n      salaxyInvoiceReport: new InvoiceReport() as any,\r\n      salaxyInvoicePaymentList: new InvoicePaymentList() as any,\r\n      salaxyCompanyInvoices: new CompanyInvoices,\r\n\r\n      // - report\r\n      salaxyHolidayReport: new HolidayReport() as any,\r\n      salaxyHolidayPayReportQuery: new HolidayPayReportQuery() as any,\r\n      salaxyIrEarningsPayment: new IrEarningsPayment() as any,\r\n      salaxyIrEarningsPaymentList: new IrEarningsPaymentList() as any,\r\n      salaxyIrPayerSummary: new IrPayerSummary() as any,\r\n      salaxyIrPayerSummaryList: new IrPayerSummaryList() as any,\r\n      salaxyReportList: new ReportList() as any,\r\n      salaxySalaryReportList: new SalaryReportList() as any,\r\n      salaxyAccountingReportQuery: new AccountingReportQuery() as any,\r\n      salaxyAccountingHolidayPayDebtReportQuery: new AccountingHolidayPayDebtReportQuery() as any,\r\n      salaxyAccountingReportList: new AccountingReportList() as any,\r\n      salaxyAccountingReportRows: new AccountingReportRows() as any,\r\n      salaxyAccountingReportTools: new AccountingReportTools() as any,\r\n      salaxyAccountingReportViewer: new AccountingReportViewer() as any,\r\n      salaxyPayCertificate: new PayCertificate() as any,\r\n      salaxyCalculationReport: new CalculationReport() as any,\r\n      salaxyAccountingRowReport: new AccountingRowReport() as any,\r\n      salaxyEmployerReport: new EmployerReport() as any,\r\n      salaxyWorkerReport: new WorkerReport() as any,\r\n      salaxyHouseholdDeductionReport: new HouseholdDeductionReport() as any,\r\n      salaxyHouseholdYearDetails: new HouseholdYearDetails() as any,\r\n      salaxyHouseholdYearList: new HouseholdYearList() as any,\r\n      salaxySummaryReport: new SummaryReport() as any,\r\n      salaxySummaryReportQuery: new SummaryReportQuery() as any,\r\n      salaxyWorkerSummaryReport: new WorkerSummaryReport() as any,\r\n      salaxyPayStatsReportQuery: new PayStatsReportQuery() as any,\r\n\r\n      // - worker\r\n      salaxyAbsencePeriods: new AbsencePeriods() as any,\r\n      salaxyEmploymentDetails: new EmploymentDetails(),\r\n      salaxyEmploymentTaxcards: new EmploymentTaxcards() as any,\r\n      salaxyHolidayYearAccrual: new HolidayYearAccrual() as any,\r\n      salaxyHolidayYearHolidays: new HolidayYearHolidays() as any,\r\n      salaxyHolidayYearPaid: new HolidayYearPaid() as any,\r\n      salaxyTaxcardDetails: new TaxcardDetails() as any,\r\n      salaxyTaxcardIncomeLog: new TaxcardIncomeLog() as any,\r\n      salaxyTaxcardManualEdit: new TaxcardManualEdit() as any,\r\n      salaxyTaxcardList: new TaxcardList() as any,\r\n      salaxyTaxCardsList: new TaxCardsList() as any,\r\n      salaxyWorkerAbsences: new WorkerAbsences() as any,\r\n      salaxyWorkerDetails: new WorkerDetails() as any,\r\n      salaxyWorkerHolidays: new WorkerHolidays() as any,\r\n      salaxyEmploymentList: new EmploymentList() as any,\r\n      salaxyWorkerList: new EmploymentList() as any, // For backward compatibility only\r\n\r\n      // - obsolete\r\n      salaxyWorkerAssure: new WorkerAssure() as any,\r\n\r\n      // - workflow\r\n      salaxyCalendarEventDetails: new CalendarEventDetails() as any,\r\n      salaxyDatasetDetails: new DatasetDetails() as any,\r\n      salaxyWorkflowButtons: new WorkflowButtons() as any,\r\n      salaxyWorkflowReopen: new WorkflowReopen() as any,\r\n      salaxyWorkflowBadge: new WorkflowBadge() as any,\r\n\r\n      // - records\r\n      salaxyRecords: new Records() as any,\r\n\r\n      // - settings\r\n      salaxyAccountant: new Accountant() as any,\r\n      salaxyRowTypesSettings: new RowTypesSettings() as any,\r\n      salaxyAccountingTargetDetails: new AccountingTargetDetails() as any,\r\n      salaxyInsurance: new Insurance() as any,\r\n      salaxyInsuranceSettings: new InsuranceSettings() as any,\r\n      salaxyOwnerSettings: new OwnerSettings() as any,\r\n      salaxyPaymentChannelSettings: new PaymentChannelSettings() as any,\r\n      salaxyPaymentSettings: new PaymentSettings() as any,\r\n      salaxyProSettings: new ProSettings() as any,\r\n      salaxyAccountingTargetSettings: new   AccountingTargetSettings() as any,\r\n      salaxyServiceModelDetails: new ServiceModelDetails() as any,\r\n      salaxyUsecaseDetails: new UsecaseDetails() as any,\r\n      salaxyCostAccountingSettings: new CostAccountingSettings() as any,\r\n      salaxyAccountingSettings: new AccountingSettings() as any,\r\n      salaxyHolidaySettings: new HolidaySettings() as any,\r\n      salaxyPayStatsSettings: new PayStatsSettings() as any,\r\n      salaxyIrDeliverySettings: new IrDeliverySettings() as any,\r\n    };\r\n  }\r\n}\r\n","/**\n * @license AngularJS v1.8.3\n * (c) 2010-2020 Google LLC. http://angularjs.org\n * License: MIT\n */\n(function(window, angular) {'use strict';\n\n/* global shallowCopy: true */\n\n/**\n * Creates a shallow copy of an object, an array or a primitive.\n *\n * Assumes that there are no proto properties for objects.\n */\nfunction shallowCopy(src, dst) {\n  if (isArray(src)) {\n    dst = dst || [];\n\n    for (var i = 0, ii = src.length; i < ii; i++) {\n      dst[i] = src[i];\n    }\n  } else if (isObject(src)) {\n    dst = dst || {};\n\n    for (var key in src) {\n      if (!(key.charAt(0) === '$' && key.charAt(1) === '$')) {\n        dst[key] = src[key];\n      }\n    }\n  }\n\n  return dst || src;\n}\n\n/* global routeToRegExp: true */\n\n/**\n * @param {string} path - The path to parse. (It is assumed to have query and hash stripped off.)\n * @param {Object} opts - Options.\n * @return {Object} - An object containing an array of path parameter names (`keys`) and a regular\n *     expression (`regexp`) that can be used to identify a matching URL and extract the path\n *     parameter values.\n *\n * @description\n * Parses the given path, extracting path parameter names and a regular expression to match URLs.\n *\n * Originally inspired by `pathRexp` in `visionmedia/express/lib/utils.js`.\n */\nfunction routeToRegExp(path, opts) {\n  var keys = [];\n\n  var pattern = path\n    .replace(/([().])/g, '\\\\$1')\n    .replace(/(\\/)?:(\\w+)(\\*\\?|[?*])?/g, function(_, slash, key, option) {\n      var optional = option === '?' || option === '*?';\n      var star = option === '*' || option === '*?';\n      keys.push({name: key, optional: optional});\n      slash = slash || '';\n      return (\n        (optional ? '(?:' + slash : slash + '(?:') +\n        (star ? '(.+?)' : '([^/]+)') +\n        (optional ? '?)?' : ')')\n      );\n    })\n    .replace(/([/$*])/g, '\\\\$1');\n\n  if (opts.ignoreTrailingSlashes) {\n    pattern = pattern.replace(/\\/+$/, '') + '/*';\n  }\n\n  return {\n    keys: keys,\n    regexp: new RegExp(\n      '^' + pattern + '(?:[?#]|$)',\n      opts.caseInsensitiveMatch ? 'i' : ''\n    )\n  };\n}\n\n/* global routeToRegExp: false */\n/* global shallowCopy: false */\n\n// `isArray` and `isObject` are necessary for `shallowCopy()` (included via `src/shallowCopy.js`).\n// They are initialized inside the `$RouteProvider`, to ensure `window.angular` is available.\nvar isArray;\nvar isObject;\nvar isDefined;\nvar noop;\n\n/**\n * @ngdoc module\n * @name ngRoute\n * @description\n *\n * The `ngRoute` module provides routing and deeplinking services and directives for AngularJS apps.\n *\n * ## Example\n * See {@link ngRoute.$route#examples $route} for an example of configuring and using `ngRoute`.\n *\n */\n/* global -ngRouteModule */\nvar ngRouteModule = angular.\n  module('ngRoute', []).\n  info({ angularVersion: '1.8.3' }).\n  provider('$route', $RouteProvider).\n  // Ensure `$route` will be instantiated in time to capture the initial `$locationChangeSuccess`\n  // event (unless explicitly disabled). This is necessary in case `ngView` is included in an\n  // asynchronously loaded template.\n  run(instantiateRoute);\nvar $routeMinErr = angular.$$minErr('ngRoute');\nvar isEagerInstantiationEnabled;\n\n\n/**\n * @ngdoc provider\n * @name $routeProvider\n * @this\n *\n * @description\n *\n * Used for configuring routes.\n *\n * ## Example\n * See {@link ngRoute.$route#examples $route} for an example of configuring and using `ngRoute`.\n *\n * ## Dependencies\n * Requires the {@link ngRoute `ngRoute`} module to be installed.\n */\nfunction $RouteProvider() {\n  isArray = angular.isArray;\n  isObject = angular.isObject;\n  isDefined = angular.isDefined;\n  noop = angular.noop;\n\n  function inherit(parent, extra) {\n    return angular.extend(Object.create(parent), extra);\n  }\n\n  var routes = {};\n\n  /**\n   * @ngdoc method\n   * @name $routeProvider#when\n   *\n   * @param {string} path Route path (matched against `$location.path`). If `$location.path`\n   *    contains redundant trailing slash or is missing one, the route will still match and the\n   *    `$location.path` will be updated to add or drop the trailing slash to exactly match the\n   *    route definition.\n   *\n   *    * `path` can contain named groups starting with a colon: e.g. `:name`. All characters up\n   *        to the next slash are matched and stored in `$routeParams` under the given `name`\n   *        when the route matches.\n   *    * `path` can contain named groups starting with a colon and ending with a star:\n   *        e.g.`:name*`. All characters are eagerly stored in `$routeParams` under the given `name`\n   *        when the route matches.\n   *    * `path` can contain optional named groups with a question mark: e.g.`:name?`.\n   *\n   *    For example, routes like `/color/:color/largecode/:largecode*\\/edit` will match\n   *    `/color/brown/largecode/code/with/slashes/edit` and extract:\n   *\n   *    * `color: brown`\n   *    * `largecode: code/with/slashes`.\n   *\n   *\n   * @param {Object} route Mapping information to be assigned to `$route.current` on route\n   *    match.\n   *\n   *    Object properties:\n   *\n   *    - `controller` – `{(string|Function)=}` – Controller fn that should be associated with\n   *      newly created scope or the name of a {@link angular.Module#controller registered\n   *      controller} if passed as a string.\n   *    - `controllerAs` – `{string=}` – An identifier name for a reference to the controller.\n   *      If present, the controller will be published to scope under the `controllerAs` name.\n   *    - `template` – `{(string|Function)=}` – html template as a string or a function that\n   *      returns an html template as a string which should be used by {@link\n   *      ngRoute.directive:ngView ngView} or {@link ng.directive:ngInclude ngInclude} directives.\n   *      This property takes precedence over `templateUrl`.\n   *\n   *      If `template` is a function, it will be called with the following parameters:\n   *\n   *      - `{Array.<Object>}` - route parameters extracted from the current\n   *        `$location.path()` by applying the current route\n   *\n   *      One of `template` or `templateUrl` is required.\n   *\n   *    - `templateUrl` – `{(string|Function)=}` – path or function that returns a path to an html\n   *      template that should be used by {@link ngRoute.directive:ngView ngView}.\n   *\n   *      If `templateUrl` is a function, it will be called with the following parameters:\n   *\n   *      - `{Array.<Object>}` - route parameters extracted from the current\n   *        `$location.path()` by applying the current route\n   *\n   *      One of `templateUrl` or `template` is required.\n   *\n   *    - `resolve` - `{Object.<string, Function>=}` - An optional map of dependencies which should\n   *      be injected into the controller. If any of these dependencies are promises, the router\n   *      will wait for them all to be resolved or one to be rejected before the controller is\n   *      instantiated.\n   *      If all the promises are resolved successfully, the values of the resolved promises are\n   *      injected and {@link ngRoute.$route#$routeChangeSuccess $routeChangeSuccess} event is\n   *      fired. If any of the promises are rejected the\n   *      {@link ngRoute.$route#$routeChangeError $routeChangeError} event is fired.\n   *      For easier access to the resolved dependencies from the template, the `resolve` map will\n   *      be available on the scope of the route, under `$resolve` (by default) or a custom name\n   *      specified by the `resolveAs` property (see below). This can be particularly useful, when\n   *      working with {@link angular.Module#component components} as route templates.<br />\n   *      <div class=\"alert alert-warning\">\n   *        **Note:** If your scope already contains a property with this name, it will be hidden\n   *        or overwritten. Make sure, you specify an appropriate name for this property, that\n   *        does not collide with other properties on the scope.\n   *      </div>\n   *      The map object is:\n   *\n   *      - `key` – `{string}`: a name of a dependency to be injected into the controller.\n   *      - `factory` - `{string|Function}`: If `string` then it is an alias for a service.\n   *        Otherwise if function, then it is {@link auto.$injector#invoke injected}\n   *        and the return value is treated as the dependency. If the result is a promise, it is\n   *        resolved before its value is injected into the controller. Be aware that\n   *        `ngRoute.$routeParams` will still refer to the previous route within these resolve\n   *        functions.  Use `$route.current.params` to access the new route parameters, instead.\n   *\n   *    - `resolveAs` - `{string=}` - The name under which the `resolve` map will be available on\n   *      the scope of the route. If omitted, defaults to `$resolve`.\n   *\n   *    - `redirectTo` – `{(string|Function)=}` – value to update\n   *      {@link ng.$location $location} path with and trigger route redirection.\n   *\n   *      If `redirectTo` is a function, it will be called with the following parameters:\n   *\n   *      - `{Object.<string>}` - route parameters extracted from the current\n   *        `$location.path()` by applying the current route templateUrl.\n   *      - `{string}` - current `$location.path()`\n   *      - `{Object}` - current `$location.search()`\n   *\n   *      The custom `redirectTo` function is expected to return a string which will be used\n   *      to update `$location.url()`. If the function throws an error, no further processing will\n   *      take place and the {@link ngRoute.$route#$routeChangeError $routeChangeError} event will\n   *      be fired.\n   *\n   *      Routes that specify `redirectTo` will not have their controllers, template functions\n   *      or resolves called, the `$location` will be changed to the redirect url and route\n   *      processing will stop. The exception to this is if the `redirectTo` is a function that\n   *      returns `undefined`. In this case the route transition occurs as though there was no\n   *      redirection.\n   *\n   *    - `resolveRedirectTo` – `{Function=}` – a function that will (eventually) return the value\n   *      to update {@link ng.$location $location} URL with and trigger route redirection. In\n   *      contrast to `redirectTo`, dependencies can be injected into `resolveRedirectTo` and the\n   *      return value can be either a string or a promise that will be resolved to a string.\n   *\n   *      Similar to `redirectTo`, if the return value is `undefined` (or a promise that gets\n   *      resolved to `undefined`), no redirection takes place and the route transition occurs as\n   *      though there was no redirection.\n   *\n   *      If the function throws an error or the returned promise gets rejected, no further\n   *      processing will take place and the\n   *      {@link ngRoute.$route#$routeChangeError $routeChangeError} event will be fired.\n   *\n   *      `redirectTo` takes precedence over `resolveRedirectTo`, so specifying both on the same\n   *      route definition, will cause the latter to be ignored.\n   *\n   *    - `[reloadOnUrl=true]` - `{boolean=}` - reload route when any part of the URL changes\n   *      (including the path) even if the new URL maps to the same route.\n   *\n   *      If the option is set to `false` and the URL in the browser changes, but the new URL maps\n   *      to the same route, then a `$routeUpdate` event is broadcasted on the root scope (without\n   *      reloading the route).\n   *\n   *    - `[reloadOnSearch=true]` - `{boolean=}` - reload route when only `$location.search()`\n   *      or `$location.hash()` changes.\n   *\n   *      If the option is set to `false` and the URL in the browser changes, then a `$routeUpdate`\n   *      event is broadcasted on the root scope (without reloading the route).\n   *\n   *      <div class=\"alert alert-warning\">\n   *        **Note:** This option has no effect if `reloadOnUrl` is set to `false`.\n   *      </div>\n   *\n   *    - `[caseInsensitiveMatch=false]` - `{boolean=}` - match routes without being case sensitive\n   *\n   *      If the option is set to `true`, then the particular route can be matched without being\n   *      case sensitive\n   *\n   * @returns {Object} self\n   *\n   * @description\n   * Adds a new route definition to the `$route` service.\n   */\n  this.when = function(path, route) {\n    //copy original route object to preserve params inherited from proto chain\n    var routeCopy = shallowCopy(route);\n    if (angular.isUndefined(routeCopy.reloadOnUrl)) {\n      routeCopy.reloadOnUrl = true;\n    }\n    if (angular.isUndefined(routeCopy.reloadOnSearch)) {\n      routeCopy.reloadOnSearch = true;\n    }\n    if (angular.isUndefined(routeCopy.caseInsensitiveMatch)) {\n      routeCopy.caseInsensitiveMatch = this.caseInsensitiveMatch;\n    }\n    routes[path] = angular.extend(\n      routeCopy,\n      {originalPath: path},\n      path && routeToRegExp(path, routeCopy)\n    );\n\n    // create redirection for trailing slashes\n    if (path) {\n      var redirectPath = (path[path.length - 1] === '/')\n            ? path.substr(0, path.length - 1)\n            : path + '/';\n\n      routes[redirectPath] = angular.extend(\n        {originalPath: path, redirectTo: path},\n        routeToRegExp(redirectPath, routeCopy)\n      );\n    }\n\n    return this;\n  };\n\n  /**\n   * @ngdoc property\n   * @name $routeProvider#caseInsensitiveMatch\n   * @description\n   *\n   * A boolean property indicating if routes defined\n   * using this provider should be matched using a case insensitive\n   * algorithm. Defaults to `false`.\n   */\n  this.caseInsensitiveMatch = false;\n\n  /**\n   * @ngdoc method\n   * @name $routeProvider#otherwise\n   *\n   * @description\n   * Sets route definition that will be used on route change when no other route definition\n   * is matched.\n   *\n   * @param {Object|string} params Mapping information to be assigned to `$route.current`.\n   * If called with a string, the value maps to `redirectTo`.\n   * @returns {Object} self\n   */\n  this.otherwise = function(params) {\n    if (typeof params === 'string') {\n      params = {redirectTo: params};\n    }\n    this.when(null, params);\n    return this;\n  };\n\n  /**\n   * @ngdoc method\n   * @name $routeProvider#eagerInstantiationEnabled\n   * @kind function\n   *\n   * @description\n   * Call this method as a setter to enable/disable eager instantiation of the\n   * {@link ngRoute.$route $route} service upon application bootstrap. You can also call it as a\n   * getter (i.e. without any arguments) to get the current value of the\n   * `eagerInstantiationEnabled` flag.\n   *\n   * Instantiating `$route` early is necessary for capturing the initial\n   * {@link ng.$location#$locationChangeStart $locationChangeStart} event and navigating to the\n   * appropriate route. Usually, `$route` is instantiated in time by the\n   * {@link ngRoute.ngView ngView} directive. Yet, in cases where `ngView` is included in an\n   * asynchronously loaded template (e.g. in another directive's template), the directive factory\n   * might not be called soon enough for `$route` to be instantiated _before_ the initial\n   * `$locationChangeSuccess` event is fired. Eager instantiation ensures that `$route` is always\n   * instantiated in time, regardless of when `ngView` will be loaded.\n   *\n   * The default value is true.\n   *\n   * **Note**:<br />\n   * You may want to disable the default behavior when unit-testing modules that depend on\n   * `ngRoute`, in order to avoid an unexpected request for the default route's template.\n   *\n   * @param {boolean=} enabled - If provided, update the internal `eagerInstantiationEnabled` flag.\n   *\n   * @returns {*} The current value of the `eagerInstantiationEnabled` flag if used as a getter or\n   *     itself (for chaining) if used as a setter.\n   */\n  isEagerInstantiationEnabled = true;\n  this.eagerInstantiationEnabled = function eagerInstantiationEnabled(enabled) {\n    if (isDefined(enabled)) {\n      isEagerInstantiationEnabled = enabled;\n      return this;\n    }\n\n    return isEagerInstantiationEnabled;\n  };\n\n\n  this.$get = ['$rootScope',\n               '$location',\n               '$routeParams',\n               '$q',\n               '$injector',\n               '$templateRequest',\n               '$sce',\n               '$browser',\n      function($rootScope, $location, $routeParams, $q, $injector, $templateRequest, $sce, $browser) {\n\n    /**\n     * @ngdoc service\n     * @name $route\n     * @requires $location\n     * @requires $routeParams\n     *\n     * @property {Object} current Reference to the current route definition.\n     * The route definition contains:\n     *\n     *   - `controller`: The controller constructor as defined in the route definition.\n     *   - `locals`: A map of locals which is used by {@link ng.$controller $controller} service for\n     *     controller instantiation. The `locals` contain\n     *     the resolved values of the `resolve` map. Additionally the `locals` also contain:\n     *\n     *     - `$scope` - The current route scope.\n     *     - `$template` - The current route template HTML.\n     *\n     *     The `locals` will be assigned to the route scope's `$resolve` property. You can override\n     *     the property name, using `resolveAs` in the route definition. See\n     *     {@link ngRoute.$routeProvider $routeProvider} for more info.\n     *\n     * @property {Object} routes Object with all route configuration Objects as its properties.\n     *\n     * @description\n     * `$route` is used for deep-linking URLs to controllers and views (HTML partials).\n     * It watches `$location.url()` and tries to map the path to an existing route definition.\n     *\n     * Requires the {@link ngRoute `ngRoute`} module to be installed.\n     *\n     * You can define routes through {@link ngRoute.$routeProvider $routeProvider}'s API.\n     *\n     * The `$route` service is typically used in conjunction with the\n     * {@link ngRoute.directive:ngView `ngView`} directive and the\n     * {@link ngRoute.$routeParams `$routeParams`} service.\n     *\n     * @example\n     * This example shows how changing the URL hash causes the `$route` to match a route against the\n     * URL, and the `ngView` pulls in the partial.\n     *\n     * <example name=\"$route-service\" module=\"ngRouteExample\"\n     *          deps=\"angular-route.js\" fixBase=\"true\">\n     *   <file name=\"index.html\">\n     *     <div ng-controller=\"MainController\">\n     *       Choose:\n     *       <a href=\"Book/Moby\">Moby</a> |\n     *       <a href=\"Book/Moby/ch/1\">Moby: Ch1</a> |\n     *       <a href=\"Book/Gatsby\">Gatsby</a> |\n     *       <a href=\"Book/Gatsby/ch/4?key=value\">Gatsby: Ch4</a> |\n     *       <a href=\"Book/Scarlet\">Scarlet Letter</a><br/>\n     *\n     *       <div ng-view></div>\n     *\n     *       <hr />\n     *\n     *       <pre>$location.path() = {{$location.path()}}</pre>\n     *       <pre>$route.current.templateUrl = {{$route.current.templateUrl}}</pre>\n     *       <pre>$route.current.params = {{$route.current.params}}</pre>\n     *       <pre>$route.current.scope.name = {{$route.current.scope.name}}</pre>\n     *       <pre>$routeParams = {{$routeParams}}</pre>\n     *     </div>\n     *   </file>\n     *\n     *   <file name=\"book.html\">\n     *     controller: {{name}}<br />\n     *     Book Id: {{params.bookId}}<br />\n     *   </file>\n     *\n     *   <file name=\"chapter.html\">\n     *     controller: {{name}}<br />\n     *     Book Id: {{params.bookId}}<br />\n     *     Chapter Id: {{params.chapterId}}\n     *   </file>\n     *\n     *   <file name=\"script.js\">\n     *     angular.module('ngRouteExample', ['ngRoute'])\n     *\n     *      .controller('MainController', function($scope, $route, $routeParams, $location) {\n     *          $scope.$route = $route;\n     *          $scope.$location = $location;\n     *          $scope.$routeParams = $routeParams;\n     *      })\n     *\n     *      .controller('BookController', function($scope, $routeParams) {\n     *          $scope.name = 'BookController';\n     *          $scope.params = $routeParams;\n     *      })\n     *\n     *      .controller('ChapterController', function($scope, $routeParams) {\n     *          $scope.name = 'ChapterController';\n     *          $scope.params = $routeParams;\n     *      })\n     *\n     *     .config(function($routeProvider, $locationProvider) {\n     *       $routeProvider\n     *        .when('/Book/:bookId', {\n     *         templateUrl: 'book.html',\n     *         controller: 'BookController',\n     *         resolve: {\n     *           // I will cause a 1 second delay\n     *           delay: function($q, $timeout) {\n     *             var delay = $q.defer();\n     *             $timeout(delay.resolve, 1000);\n     *             return delay.promise;\n     *           }\n     *         }\n     *       })\n     *       .when('/Book/:bookId/ch/:chapterId', {\n     *         templateUrl: 'chapter.html',\n     *         controller: 'ChapterController'\n     *       });\n     *\n     *       // configure html5 to get links working on jsfiddle\n     *       $locationProvider.html5Mode(true);\n     *     });\n     *\n     *   </file>\n     *\n     *   <file name=\"protractor.js\" type=\"protractor\">\n     *     it('should load and compile correct template', function() {\n     *       element(by.linkText('Moby: Ch1')).click();\n     *       var content = element(by.css('[ng-view]')).getText();\n     *       expect(content).toMatch(/controller: ChapterController/);\n     *       expect(content).toMatch(/Book Id: Moby/);\n     *       expect(content).toMatch(/Chapter Id: 1/);\n     *\n     *       element(by.partialLinkText('Scarlet')).click();\n     *\n     *       content = element(by.css('[ng-view]')).getText();\n     *       expect(content).toMatch(/controller: BookController/);\n     *       expect(content).toMatch(/Book Id: Scarlet/);\n     *     });\n     *   </file>\n     * </example>\n     */\n\n    /**\n     * @ngdoc event\n     * @name $route#$routeChangeStart\n     * @eventType broadcast on root scope\n     * @description\n     * Broadcasted before a route change. At this  point the route services starts\n     * resolving all of the dependencies needed for the route change to occur.\n     * Typically this involves fetching the view template as well as any dependencies\n     * defined in `resolve` route property. Once  all of the dependencies are resolved\n     * `$routeChangeSuccess` is fired.\n     *\n     * The route change (and the `$location` change that triggered it) can be prevented\n     * by calling `preventDefault` method of the event. See {@link ng.$rootScope.Scope#$on}\n     * for more details about event object.\n     *\n     * @param {Object} angularEvent Synthetic event object.\n     * @param {Route} next Future route information.\n     * @param {Route} current Current route information.\n     */\n\n    /**\n     * @ngdoc event\n     * @name $route#$routeChangeSuccess\n     * @eventType broadcast on root scope\n     * @description\n     * Broadcasted after a route change has happened successfully.\n     * The `resolve` dependencies are now available in the `current.locals` property.\n     *\n     * {@link ngRoute.directive:ngView ngView} listens for the directive\n     * to instantiate the controller and render the view.\n     *\n     * @param {Object} angularEvent Synthetic event object.\n     * @param {Route} current Current route information.\n     * @param {Route|Undefined} previous Previous route information, or undefined if current is\n     * first route entered.\n     */\n\n    /**\n     * @ngdoc event\n     * @name $route#$routeChangeError\n     * @eventType broadcast on root scope\n     * @description\n     * Broadcasted if a redirection function fails or any redirection or resolve promises are\n     * rejected.\n     *\n     * @param {Object} angularEvent Synthetic event object\n     * @param {Route} current Current route information.\n     * @param {Route} previous Previous route information.\n     * @param {Route} rejection The thrown error or the rejection reason of the promise. Usually\n     * the rejection reason is the error that caused the promise to get rejected.\n     */\n\n    /**\n     * @ngdoc event\n     * @name $route#$routeUpdate\n     * @eventType broadcast on root scope\n     * @description\n     * Broadcasted if the same instance of a route (including template, controller instance,\n     * resolved dependencies, etc.) is being reused. This can happen if either `reloadOnSearch` or\n     * `reloadOnUrl` has been set to `false`.\n     *\n     * @param {Object} angularEvent Synthetic event object\n     * @param {Route} current Current/previous route information.\n     */\n\n    var forceReload = false,\n        preparedRoute,\n        preparedRouteIsUpdateOnly,\n        $route = {\n          routes: routes,\n\n          /**\n           * @ngdoc method\n           * @name $route#reload\n           *\n           * @description\n           * Causes `$route` service to reload the current route even if\n           * {@link ng.$location $location} hasn't changed.\n           *\n           * As a result of that, {@link ngRoute.directive:ngView ngView}\n           * creates new scope and reinstantiates the controller.\n           */\n          reload: function() {\n            forceReload = true;\n\n            var fakeLocationEvent = {\n              defaultPrevented: false,\n              preventDefault: function fakePreventDefault() {\n                this.defaultPrevented = true;\n                forceReload = false;\n              }\n            };\n\n            $rootScope.$evalAsync(function() {\n              prepareRoute(fakeLocationEvent);\n              if (!fakeLocationEvent.defaultPrevented) commitRoute();\n            });\n          },\n\n          /**\n           * @ngdoc method\n           * @name $route#updateParams\n           *\n           * @description\n           * Causes `$route` service to update the current URL, replacing\n           * current route parameters with those specified in `newParams`.\n           * Provided property names that match the route's path segment\n           * definitions will be interpolated into the location's path, while\n           * remaining properties will be treated as query params.\n           *\n           * @param {!Object<string, string>} newParams mapping of URL parameter names to values\n           */\n          updateParams: function(newParams) {\n            if (this.current && this.current.$$route) {\n              newParams = angular.extend({}, this.current.params, newParams);\n              $location.path(interpolate(this.current.$$route.originalPath, newParams));\n              // interpolate modifies newParams, only query params are left\n              $location.search(newParams);\n            } else {\n              throw $routeMinErr('norout', 'Tried updating route with no current route');\n            }\n          }\n        };\n\n    $rootScope.$on('$locationChangeStart', prepareRoute);\n    $rootScope.$on('$locationChangeSuccess', commitRoute);\n\n    return $route;\n\n    /////////////////////////////////////////////////////\n\n    /**\n     * @param on {string} current url\n     * @param route {Object} route regexp to match the url against\n     * @return {?Object}\n     *\n     * @description\n     * Check if the route matches the current url.\n     *\n     * Inspired by match in\n     * visionmedia/express/lib/router/router.js.\n     */\n    function switchRouteMatcher(on, route) {\n      var keys = route.keys,\n          params = {};\n\n      if (!route.regexp) return null;\n\n      var m = route.regexp.exec(on);\n      if (!m) return null;\n\n      for (var i = 1, len = m.length; i < len; ++i) {\n        var key = keys[i - 1];\n\n        var val = m[i];\n\n        if (key && val) {\n          params[key.name] = val;\n        }\n      }\n      return params;\n    }\n\n    function prepareRoute($locationEvent) {\n      var lastRoute = $route.current;\n\n      preparedRoute = parseRoute();\n      preparedRouteIsUpdateOnly = isNavigationUpdateOnly(preparedRoute, lastRoute);\n\n      if (!preparedRouteIsUpdateOnly && (lastRoute || preparedRoute)) {\n        if ($rootScope.$broadcast('$routeChangeStart', preparedRoute, lastRoute).defaultPrevented) {\n          if ($locationEvent) {\n            $locationEvent.preventDefault();\n          }\n        }\n      }\n    }\n\n    function commitRoute() {\n      var lastRoute = $route.current;\n      var nextRoute = preparedRoute;\n\n      if (preparedRouteIsUpdateOnly) {\n        lastRoute.params = nextRoute.params;\n        angular.copy(lastRoute.params, $routeParams);\n        $rootScope.$broadcast('$routeUpdate', lastRoute);\n      } else if (nextRoute || lastRoute) {\n        forceReload = false;\n        $route.current = nextRoute;\n\n        var nextRoutePromise = $q.resolve(nextRoute);\n\n        $browser.$$incOutstandingRequestCount('$route');\n\n        nextRoutePromise.\n          then(getRedirectionData).\n          then(handlePossibleRedirection).\n          then(function(keepProcessingRoute) {\n            return keepProcessingRoute && nextRoutePromise.\n              then(resolveLocals).\n              then(function(locals) {\n                // after route change\n                if (nextRoute === $route.current) {\n                  if (nextRoute) {\n                    nextRoute.locals = locals;\n                    angular.copy(nextRoute.params, $routeParams);\n                  }\n                  $rootScope.$broadcast('$routeChangeSuccess', nextRoute, lastRoute);\n                }\n              });\n          }).catch(function(error) {\n            if (nextRoute === $route.current) {\n              $rootScope.$broadcast('$routeChangeError', nextRoute, lastRoute, error);\n            }\n          }).finally(function() {\n            // Because `commitRoute()` is called from a `$rootScope.$evalAsync` block (see\n            // `$locationWatch`), this `$$completeOutstandingRequest()` call will not cause\n            // `outstandingRequestCount` to hit zero.  This is important in case we are redirecting\n            // to a new route which also requires some asynchronous work.\n\n            $browser.$$completeOutstandingRequest(noop, '$route');\n          });\n      }\n    }\n\n    function getRedirectionData(route) {\n      var data = {\n        route: route,\n        hasRedirection: false\n      };\n\n      if (route) {\n        if (route.redirectTo) {\n          if (angular.isString(route.redirectTo)) {\n            data.path = interpolate(route.redirectTo, route.params);\n            data.search = route.params;\n            data.hasRedirection = true;\n          } else {\n            var oldPath = $location.path();\n            var oldSearch = $location.search();\n            var newUrl = route.redirectTo(route.pathParams, oldPath, oldSearch);\n\n            if (angular.isDefined(newUrl)) {\n              data.url = newUrl;\n              data.hasRedirection = true;\n            }\n          }\n        } else if (route.resolveRedirectTo) {\n          return $q.\n            resolve($injector.invoke(route.resolveRedirectTo)).\n            then(function(newUrl) {\n              if (angular.isDefined(newUrl)) {\n                data.url = newUrl;\n                data.hasRedirection = true;\n              }\n\n              return data;\n            });\n        }\n      }\n\n      return data;\n    }\n\n    function handlePossibleRedirection(data) {\n      var keepProcessingRoute = true;\n\n      if (data.route !== $route.current) {\n        keepProcessingRoute = false;\n      } else if (data.hasRedirection) {\n        var oldUrl = $location.url();\n        var newUrl = data.url;\n\n        if (newUrl) {\n          $location.\n            url(newUrl).\n            replace();\n        } else {\n          newUrl = $location.\n            path(data.path).\n            search(data.search).\n            replace().\n            url();\n        }\n\n        if (newUrl !== oldUrl) {\n          // Exit out and don't process current next value,\n          // wait for next location change from redirect\n          keepProcessingRoute = false;\n        }\n      }\n\n      return keepProcessingRoute;\n    }\n\n    function resolveLocals(route) {\n      if (route) {\n        var locals = angular.extend({}, route.resolve);\n        angular.forEach(locals, function(value, key) {\n          locals[key] = angular.isString(value) ?\n              $injector.get(value) :\n              $injector.invoke(value, null, null, key);\n        });\n        var template = getTemplateFor(route);\n        if (angular.isDefined(template)) {\n          locals['$template'] = template;\n        }\n        return $q.all(locals);\n      }\n    }\n\n    function getTemplateFor(route) {\n      var template, templateUrl;\n      if (angular.isDefined(template = route.template)) {\n        if (angular.isFunction(template)) {\n          template = template(route.params);\n        }\n      } else if (angular.isDefined(templateUrl = route.templateUrl)) {\n        if (angular.isFunction(templateUrl)) {\n          templateUrl = templateUrl(route.params);\n        }\n        if (angular.isDefined(templateUrl)) {\n          route.loadedTemplateUrl = $sce.valueOf(templateUrl);\n          template = $templateRequest(templateUrl);\n        }\n      }\n      return template;\n    }\n\n    /**\n     * @returns {Object} the current active route, by matching it against the URL\n     */\n    function parseRoute() {\n      // Match a route\n      var params, match;\n      angular.forEach(routes, function(route, path) {\n        if (!match && (params = switchRouteMatcher($location.path(), route))) {\n          match = inherit(route, {\n            params: angular.extend({}, $location.search(), params),\n            pathParams: params});\n          match.$$route = route;\n        }\n      });\n      // No route matched; fallback to \"otherwise\" route\n      return match || routes[null] && inherit(routes[null], {params: {}, pathParams:{}});\n    }\n\n    /**\n     * @param {Object} newRoute - The new route configuration (as returned by `parseRoute()`).\n     * @param {Object} oldRoute - The previous route configuration (as returned by `parseRoute()`).\n     * @returns {boolean} Whether this is an \"update-only\" navigation, i.e. the URL maps to the same\n     *                    route and it can be reused (based on the config and the type of change).\n     */\n    function isNavigationUpdateOnly(newRoute, oldRoute) {\n      // IF this is not a forced reload\n      return !forceReload\n          // AND both `newRoute`/`oldRoute` are defined\n          && newRoute && oldRoute\n          // AND they map to the same Route Definition Object\n          && (newRoute.$$route === oldRoute.$$route)\n          // AND `reloadOnUrl` is disabled\n          && (!newRoute.reloadOnUrl\n              // OR `reloadOnSearch` is disabled\n              || (!newRoute.reloadOnSearch\n                  // AND both routes have the same path params\n                  && angular.equals(newRoute.pathParams, oldRoute.pathParams)\n              )\n          );\n    }\n\n    /**\n     * @returns {string} interpolation of the redirect path with the parameters\n     */\n    function interpolate(string, params) {\n      var result = [];\n      angular.forEach((string || '').split(':'), function(segment, i) {\n        if (i === 0) {\n          result.push(segment);\n        } else {\n          var segmentMatch = segment.match(/(\\w+)(?:[?*])?(.*)/);\n          var key = segmentMatch[1];\n          result.push(params[key]);\n          result.push(segmentMatch[2] || '');\n          delete params[key];\n        }\n      });\n      return result.join('');\n    }\n  }];\n}\n\ninstantiateRoute.$inject = ['$injector'];\nfunction instantiateRoute($injector) {\n  if (isEagerInstantiationEnabled) {\n    // Instantiate `$route`\n    $injector.get('$route');\n  }\n}\n\nngRouteModule.provider('$routeParams', $RouteParamsProvider);\n\n\n/**\n * @ngdoc service\n * @name $routeParams\n * @requires $route\n * @this\n *\n * @description\n * The `$routeParams` service allows you to retrieve the current set of route parameters.\n *\n * Requires the {@link ngRoute `ngRoute`} module to be installed.\n *\n * The route parameters are a combination of {@link ng.$location `$location`}'s\n * {@link ng.$location#search `search()`} and {@link ng.$location#path `path()`}.\n * The `path` parameters are extracted when the {@link ngRoute.$route `$route`} path is matched.\n *\n * In case of parameter name collision, `path` params take precedence over `search` params.\n *\n * The service guarantees that the identity of the `$routeParams` object will remain unchanged\n * (but its properties will likely change) even when a route change occurs.\n *\n * Note that the `$routeParams` are only updated *after* a route change completes successfully.\n * This means that you cannot rely on `$routeParams` being correct in route resolve functions.\n * Instead you can use `$route.current.params` to access the new route's parameters.\n *\n * @example\n * ```js\n *  // Given:\n *  // URL: http://server.com/index.html#/Chapter/1/Section/2?search=moby\n *  // Route: /Chapter/:chapterId/Section/:sectionId\n *  //\n *  // Then\n *  $routeParams ==> {chapterId:'1', sectionId:'2', search:'moby'}\n * ```\n */\nfunction $RouteParamsProvider() {\n  this.$get = function() { return {}; };\n}\n\nngRouteModule.directive('ngView', ngViewFactory);\nngRouteModule.directive('ngView', ngViewFillContentFactory);\n\n\n/**\n * @ngdoc directive\n * @name ngView\n * @restrict ECA\n *\n * @description\n * `ngView` is a directive that complements the {@link ngRoute.$route $route} service by\n * including the rendered template of the current route into the main layout (`index.html`) file.\n * Every time the current route changes, the included view changes with it according to the\n * configuration of the `$route` service.\n *\n * Requires the {@link ngRoute `ngRoute`} module to be installed.\n *\n * @animations\n * | Animation                        | Occurs                              |\n * |----------------------------------|-------------------------------------|\n * | {@link ng.$animate#enter enter}  | when the new element is inserted to the DOM |\n * | {@link ng.$animate#leave leave}  | when the old element is removed from to the DOM  |\n *\n * The enter and leave animation occur concurrently.\n *\n * @scope\n * @priority 400\n * @param {string=} onload Expression to evaluate whenever the view updates.\n *\n * @param {string=} autoscroll Whether `ngView` should call {@link ng.$anchorScroll\n *                  $anchorScroll} to scroll the viewport after the view is updated.\n *\n *                  - If the attribute is not set, disable scrolling.\n *                  - If the attribute is set without value, enable scrolling.\n *                  - Otherwise enable scrolling only if the `autoscroll` attribute value evaluated\n *                    as an expression yields a truthy value.\n * @example\n    <example name=\"ngView-directive\" module=\"ngViewExample\"\n             deps=\"angular-route.js;angular-animate.js\"\n             animations=\"true\" fixBase=\"true\">\n      <file name=\"index.html\">\n        <div ng-controller=\"MainCtrl as main\">\n          Choose:\n          <a href=\"Book/Moby\">Moby</a> |\n          <a href=\"Book/Moby/ch/1\">Moby: Ch1</a> |\n          <a href=\"Book/Gatsby\">Gatsby</a> |\n          <a href=\"Book/Gatsby/ch/4?key=value\">Gatsby: Ch4</a> |\n          <a href=\"Book/Scarlet\">Scarlet Letter</a><br/>\n\n          <div class=\"view-animate-container\">\n            <div ng-view class=\"view-animate\"></div>\n          </div>\n          <hr />\n\n          <pre>$location.path() = {{main.$location.path()}}</pre>\n          <pre>$route.current.templateUrl = {{main.$route.current.templateUrl}}</pre>\n          <pre>$route.current.params = {{main.$route.current.params}}</pre>\n          <pre>$routeParams = {{main.$routeParams}}</pre>\n        </div>\n      </file>\n\n      <file name=\"book.html\">\n        <div>\n          controller: {{book.name}}<br />\n          Book Id: {{book.params.bookId}}<br />\n        </div>\n      </file>\n\n      <file name=\"chapter.html\">\n        <div>\n          controller: {{chapter.name}}<br />\n          Book Id: {{chapter.params.bookId}}<br />\n          Chapter Id: {{chapter.params.chapterId}}\n        </div>\n      </file>\n\n      <file name=\"animations.css\">\n        .view-animate-container {\n          position:relative;\n          height:100px!important;\n          background:white;\n          border:1px solid black;\n          height:40px;\n          overflow:hidden;\n        }\n\n        .view-animate {\n          padding:10px;\n        }\n\n        .view-animate.ng-enter, .view-animate.ng-leave {\n          transition:all cubic-bezier(0.250, 0.460, 0.450, 0.940) 1.5s;\n\n          display:block;\n          width:100%;\n          border-left:1px solid black;\n\n          position:absolute;\n          top:0;\n          left:0;\n          right:0;\n          bottom:0;\n          padding:10px;\n        }\n\n        .view-animate.ng-enter {\n          left:100%;\n        }\n        .view-animate.ng-enter.ng-enter-active {\n          left:0;\n        }\n        .view-animate.ng-leave.ng-leave-active {\n          left:-100%;\n        }\n      </file>\n\n      <file name=\"script.js\">\n        angular.module('ngViewExample', ['ngRoute', 'ngAnimate'])\n          .config(['$routeProvider', '$locationProvider',\n            function($routeProvider, $locationProvider) {\n              $routeProvider\n                .when('/Book/:bookId', {\n                  templateUrl: 'book.html',\n                  controller: 'BookCtrl',\n                  controllerAs: 'book'\n                })\n                .when('/Book/:bookId/ch/:chapterId', {\n                  templateUrl: 'chapter.html',\n                  controller: 'ChapterCtrl',\n                  controllerAs: 'chapter'\n                });\n\n              $locationProvider.html5Mode(true);\n          }])\n          .controller('MainCtrl', ['$route', '$routeParams', '$location',\n            function MainCtrl($route, $routeParams, $location) {\n              this.$route = $route;\n              this.$location = $location;\n              this.$routeParams = $routeParams;\n          }])\n          .controller('BookCtrl', ['$routeParams', function BookCtrl($routeParams) {\n            this.name = 'BookCtrl';\n            this.params = $routeParams;\n          }])\n          .controller('ChapterCtrl', ['$routeParams', function ChapterCtrl($routeParams) {\n            this.name = 'ChapterCtrl';\n            this.params = $routeParams;\n          }]);\n\n      </file>\n\n      <file name=\"protractor.js\" type=\"protractor\">\n        it('should load and compile correct template', function() {\n          element(by.linkText('Moby: Ch1')).click();\n          var content = element(by.css('[ng-view]')).getText();\n          expect(content).toMatch(/controller: ChapterCtrl/);\n          expect(content).toMatch(/Book Id: Moby/);\n          expect(content).toMatch(/Chapter Id: 1/);\n\n          element(by.partialLinkText('Scarlet')).click();\n\n          content = element(by.css('[ng-view]')).getText();\n          expect(content).toMatch(/controller: BookCtrl/);\n          expect(content).toMatch(/Book Id: Scarlet/);\n        });\n      </file>\n    </example>\n */\n\n\n/**\n * @ngdoc event\n * @name ngView#$viewContentLoaded\n * @eventType emit on the current ngView scope\n * @description\n * Emitted every time the ngView content is reloaded.\n */\nngViewFactory.$inject = ['$route', '$anchorScroll', '$animate'];\nfunction ngViewFactory($route, $anchorScroll, $animate) {\n  return {\n    restrict: 'ECA',\n    terminal: true,\n    priority: 400,\n    transclude: 'element',\n    link: function(scope, $element, attr, ctrl, $transclude) {\n        var currentScope,\n            currentElement,\n            previousLeaveAnimation,\n            autoScrollExp = attr.autoscroll,\n            onloadExp = attr.onload || '';\n\n        scope.$on('$routeChangeSuccess', update);\n        update();\n\n        function cleanupLastView() {\n          if (previousLeaveAnimation) {\n            $animate.cancel(previousLeaveAnimation);\n            previousLeaveAnimation = null;\n          }\n\n          if (currentScope) {\n            currentScope.$destroy();\n            currentScope = null;\n          }\n          if (currentElement) {\n            previousLeaveAnimation = $animate.leave(currentElement);\n            previousLeaveAnimation.done(function(response) {\n              if (response !== false) previousLeaveAnimation = null;\n            });\n            currentElement = null;\n          }\n        }\n\n        function update() {\n          var locals = $route.current && $route.current.locals,\n              template = locals && locals.$template;\n\n          if (angular.isDefined(template)) {\n            var newScope = scope.$new();\n            var current = $route.current;\n\n            // Note: This will also link all children of ng-view that were contained in the original\n            // html. If that content contains controllers, ... they could pollute/change the scope.\n            // However, using ng-view on an element with additional content does not make sense...\n            // Note: We can't remove them in the cloneAttchFn of $transclude as that\n            // function is called before linking the content, which would apply child\n            // directives to non existing elements.\n            var clone = $transclude(newScope, function(clone) {\n              $animate.enter(clone, null, currentElement || $element).done(function onNgViewEnter(response) {\n                if (response !== false && angular.isDefined(autoScrollExp)\n                  && (!autoScrollExp || scope.$eval(autoScrollExp))) {\n                  $anchorScroll();\n                }\n              });\n              cleanupLastView();\n            });\n\n            currentElement = clone;\n            currentScope = current.scope = newScope;\n            currentScope.$emit('$viewContentLoaded');\n            currentScope.$eval(onloadExp);\n          } else {\n            cleanupLastView();\n          }\n        }\n    }\n  };\n}\n\n// This directive is called during the $transclude call of the first `ngView` directive.\n// It will replace and compile the content of the element with the loaded template.\n// We need this directive so that the element content is already filled when\n// the link function of another directive on the same element as ngView\n// is called.\nngViewFillContentFactory.$inject = ['$compile', '$controller', '$route'];\nfunction ngViewFillContentFactory($compile, $controller, $route) {\n  return {\n    restrict: 'ECA',\n    priority: -400,\n    link: function(scope, $element) {\n      var current = $route.current,\n          locals = current.locals;\n\n      $element.html(locals.$template);\n\n      var link = $compile($element.contents());\n\n      if (current.controller) {\n        locals.$scope = scope;\n        var controller = $controller(current.controller, locals);\n        if (current.controllerAs) {\n          scope[current.controllerAs] = controller;\n        }\n        $element.data('$ngControllerController', controller);\n        $element.children().data('$ngControllerController', controller);\n      }\n      scope[current.resolveAs || '$resolve'] = locals;\n\n      link(scope);\n    }\n  };\n}\n\n\n})(window, window.angular);\n","require('./angular-route');\nmodule.exports = 'ngRoute';\n","'use strict';\nangular.module(\"ngLocale\", [], [\"$provide\", function($provide) {\nvar PLURAL_CATEGORY = {ZERO: \"zero\", ONE: \"one\", TWO: \"two\", FEW: \"few\", MANY: \"many\", OTHER: \"other\"};\nfunction getDecimals(n) {\n  n = n + '';\n  var i = n.indexOf('.');\n  return (i == -1) ? 0 : n.length - i - 1;\n}\n\nfunction getVF(n, opt_precision) {\n  var v = opt_precision;\n\n  if (undefined === v) {\n    v = Math.min(getDecimals(n), 3);\n  }\n\n  var base = Math.pow(10, v);\n  var f = ((n * base) | 0) % base;\n  return {v: v, f: f};\n}\n\n$provide.value(\"$locale\", {\n  \"DATETIME_FORMATS\": {\n    \"AMPMS\": [\n      \"ap.\",\n      \"ip.\"\n    ],\n    \"DAY\": [\n      \"sunnuntaina\",\n      \"maanantaina\",\n      \"tiistaina\",\n      \"keskiviikkona\",\n      \"torstaina\",\n      \"perjantaina\",\n      \"lauantaina\"\n    ],\n    \"ERANAMES\": [\n      \"ennen Kristuksen syntym\\u00e4\\u00e4\",\n      \"j\\u00e4lkeen Kristuksen syntym\\u00e4n\"\n    ],\n    \"ERAS\": [\n      \"eKr.\",\n      \"jKr.\"\n    ],\n    \"FIRSTDAYOFWEEK\": 0,\n    \"MONTH\": [\n      \"tammikuuta\",\n      \"helmikuuta\",\n      \"maaliskuuta\",\n      \"huhtikuuta\",\n      \"toukokuuta\",\n      \"kes\\u00e4kuuta\",\n      \"hein\\u00e4kuuta\",\n      \"elokuuta\",\n      \"syyskuuta\",\n      \"lokakuuta\",\n      \"marraskuuta\",\n      \"joulukuuta\"\n    ],\n    \"SHORTDAY\": [\n      \"su\",\n      \"ma\",\n      \"ti\",\n      \"ke\",\n      \"to\",\n      \"pe\",\n      \"la\"\n    ],\n    \"SHORTMONTH\": [\n      \"tammik.\",\n      \"helmik.\",\n      \"maalisk.\",\n      \"huhtik.\",\n      \"toukok.\",\n      \"kes\\u00e4k.\",\n      \"hein\\u00e4k.\",\n      \"elok.\",\n      \"syysk.\",\n      \"lokak.\",\n      \"marrask.\",\n      \"jouluk.\"\n    ],\n    \"STANDALONEMONTH\": [\n      \"tammikuu\",\n      \"helmikuu\",\n      \"maaliskuu\",\n      \"huhtikuu\",\n      \"toukokuu\",\n      \"kes\\u00e4kuu\",\n      \"hein\\u00e4kuu\",\n      \"elokuu\",\n      \"syyskuu\",\n      \"lokakuu\",\n      \"marraskuu\",\n      \"joulukuu\"\n    ],\n    \"WEEKENDRANGE\": [\n      5,\n      6\n    ],\n    \"fullDate\": \"cccc d. MMMM y\",\n    \"longDate\": \"d. MMMM y\",\n    \"medium\": \"d.M.y H.mm.ss\",\n    \"mediumDate\": \"d.M.y\",\n    \"mediumTime\": \"H.mm.ss\",\n    \"short\": \"d.M.y H.mm\",\n    \"shortDate\": \"d.M.y\",\n    \"shortTime\": \"H.mm\"\n  },\n  \"NUMBER_FORMATS\": {\n    \"CURRENCY_SYM\": \"\\u20ac\",\n    \"DECIMAL_SEP\": \",\",\n    \"GROUP_SEP\": \"\\u00a0\",\n    \"PATTERNS\": [\n      {\n        \"gSize\": 3,\n        \"lgSize\": 3,\n        \"maxFrac\": 3,\n        \"minFrac\": 0,\n        \"minInt\": 1,\n        \"negPre\": \"-\",\n        \"negSuf\": \"\",\n        \"posPre\": \"\",\n        \"posSuf\": \"\"\n      },\n      {\n        \"gSize\": 3,\n        \"lgSize\": 3,\n        \"maxFrac\": 2,\n        \"minFrac\": 2,\n        \"minInt\": 1,\n        \"negPre\": \"-\",\n        \"negSuf\": \"\\u00a0\\u00a4\",\n        \"posPre\": \"\",\n        \"posSuf\": \"\\u00a0\\u00a4\"\n      }\n    ]\n  },\n  \"id\": \"fi\",\n  \"localeID\": \"fi\",\n  \"pluralCat\": function(n, opt_precision) {  var i = n | 0;  var vf = getVF(n, opt_precision);  if (i == 1 && vf.v == 0) {    return PLURAL_CATEGORY.ONE;  }  return PLURAL_CATEGORY.OTHER;}\n});\n}]);\n","/*\n * angular-ui-bootstrap\n * http://angular-ui.github.io/bootstrap/\n\n * Version: 2.5.6 - 2017-10-14\n * License: MIT\n */angular.module(\"ui.bootstrap\", [\"ui.bootstrap.tpls\", \"ui.bootstrap.collapse\",\"ui.bootstrap.tabindex\",\"ui.bootstrap.accordion\",\"ui.bootstrap.alert\",\"ui.bootstrap.buttons\",\"ui.bootstrap.carousel\",\"ui.bootstrap.dateparser\",\"ui.bootstrap.isClass\",\"ui.bootstrap.datepicker\",\"ui.bootstrap.position\",\"ui.bootstrap.datepickerPopup\",\"ui.bootstrap.debounce\",\"ui.bootstrap.multiMap\",\"ui.bootstrap.dropdown\",\"ui.bootstrap.stackedMap\",\"ui.bootstrap.modal\",\"ui.bootstrap.paging\",\"ui.bootstrap.pager\",\"ui.bootstrap.pagination\",\"ui.bootstrap.tooltip\",\"ui.bootstrap.popover\",\"ui.bootstrap.progressbar\",\"ui.bootstrap.rating\",\"ui.bootstrap.tabs\",\"ui.bootstrap.timepicker\",\"ui.bootstrap.typeahead\"]);\nangular.module(\"ui.bootstrap.tpls\", [\"uib/template/accordion/accordion-group.html\",\"uib/template/accordion/accordion.html\",\"uib/template/alert/alert.html\",\"uib/template/carousel/carousel.html\",\"uib/template/carousel/slide.html\",\"uib/template/datepicker/datepicker.html\",\"uib/template/datepicker/day.html\",\"uib/template/datepicker/month.html\",\"uib/template/datepicker/year.html\",\"uib/template/datepickerPopup/popup.html\",\"uib/template/modal/window.html\",\"uib/template/pager/pager.html\",\"uib/template/pagination/pagination.html\",\"uib/template/tooltip/tooltip-html-popup.html\",\"uib/template/tooltip/tooltip-popup.html\",\"uib/template/tooltip/tooltip-template-popup.html\",\"uib/template/popover/popover-html.html\",\"uib/template/popover/popover-template.html\",\"uib/template/popover/popover.html\",\"uib/template/progressbar/bar.html\",\"uib/template/progressbar/progress.html\",\"uib/template/progressbar/progressbar.html\",\"uib/template/rating/rating.html\",\"uib/template/tabs/tab.html\",\"uib/template/tabs/tabset.html\",\"uib/template/timepicker/timepicker.html\",\"uib/template/typeahead/typeahead-match.html\",\"uib/template/typeahead/typeahead-popup.html\"]);\nangular.module('ui.bootstrap.collapse', [])\n\n  .directive('uibCollapse', ['$animate', '$q', '$parse', '$injector', function($animate, $q, $parse, $injector) {\n    var $animateCss = $injector.has('$animateCss') ? $injector.get('$animateCss') : null;\n    return {\n      link: function(scope, element, attrs) {\n        var expandingExpr = $parse(attrs.expanding),\n          expandedExpr = $parse(attrs.expanded),\n          collapsingExpr = $parse(attrs.collapsing),\n          collapsedExpr = $parse(attrs.collapsed),\n          horizontal = false,\n          css = {},\n          cssTo = {};\n\n        init();\n\n        function init() {\n          horizontal = !!('horizontal' in attrs);\n          if (horizontal) {\n            css = {\n              width: ''\n            };\n            cssTo = {width: '0'};\n          } else {\n            css = {\n              height: ''\n            };\n            cssTo = {height: '0'};\n          }\n          if (!scope.$eval(attrs.uibCollapse)) {\n            element.addClass('in')\n              .addClass('collapse')\n              .attr('aria-expanded', true)\n              .attr('aria-hidden', false)\n              .css(css);\n          }\n        }\n\n        function getScrollFromElement(element) {\n          if (horizontal) {\n            return {width: element.scrollWidth + 'px'};\n          }\n          return {height: element.scrollHeight + 'px'};\n        }\n\n        function expand() {\n          if (element.hasClass('collapse') && element.hasClass('in')) {\n            return;\n          }\n\n          $q.resolve(expandingExpr(scope))\n            .then(function() {\n              element.removeClass('collapse')\n                .addClass('collapsing')\n                .attr('aria-expanded', true)\n                .attr('aria-hidden', false);\n\n              if ($animateCss) {\n                $animateCss(element, {\n                  addClass: 'in',\n                  easing: 'ease',\n                  css: {\n                    overflow: 'hidden'\n                  },\n                  to: getScrollFromElement(element[0])\n                }).start()['finally'](expandDone);\n              } else {\n                $animate.addClass(element, 'in', {\n                  css: {\n                    overflow: 'hidden'\n                  },\n                  to: getScrollFromElement(element[0])\n                }).then(expandDone);\n              }\n            }, angular.noop);\n        }\n\n        function expandDone() {\n          element.removeClass('collapsing')\n            .addClass('collapse')\n            .css(css);\n          expandedExpr(scope);\n        }\n\n        function collapse() {\n          if (!element.hasClass('collapse') && !element.hasClass('in')) {\n            return collapseDone();\n          }\n\n          $q.resolve(collapsingExpr(scope))\n            .then(function() {\n              element\n              // IMPORTANT: The width must be set before adding \"collapsing\" class.\n              // Otherwise, the browser attempts to animate from width 0 (in\n              // collapsing class) to the given width here.\n                .css(getScrollFromElement(element[0]))\n                // initially all panel collapse have the collapse class, this removal\n                // prevents the animation from jumping to collapsed state\n                .removeClass('collapse')\n                .addClass('collapsing')\n                .attr('aria-expanded', false)\n                .attr('aria-hidden', true);\n\n              if ($animateCss) {\n                $animateCss(element, {\n                  removeClass: 'in',\n                  to: cssTo\n                }).start()['finally'](collapseDone);\n              } else {\n                $animate.removeClass(element, 'in', {\n                  to: cssTo\n                }).then(collapseDone);\n              }\n            }, angular.noop);\n        }\n\n        function collapseDone() {\n          element.css(cssTo); // Required so that collapse works when animation is disabled\n          element.removeClass('collapsing')\n            .addClass('collapse');\n          collapsedExpr(scope);\n        }\n\n        scope.$watch(attrs.uibCollapse, function(shouldCollapse) {\n          if (shouldCollapse) {\n            collapse();\n          } else {\n            expand();\n          }\n        });\n      }\n    };\n  }]);\n\nangular.module('ui.bootstrap.tabindex', [])\n\n.directive('uibTabindexToggle', function() {\n  return {\n    restrict: 'A',\n    link: function(scope, elem, attrs) {\n      attrs.$observe('disabled', function(disabled) {\n        attrs.$set('tabindex', disabled ? -1 : null);\n      });\n    }\n  };\n});\n\nangular.module('ui.bootstrap.accordion', ['ui.bootstrap.collapse', 'ui.bootstrap.tabindex'])\n\n.constant('uibAccordionConfig', {\n  closeOthers: true\n})\n\n.controller('UibAccordionController', ['$scope', '$attrs', 'uibAccordionConfig', function($scope, $attrs, accordionConfig) {\n  // This array keeps track of the accordion groups\n  this.groups = [];\n\n  // Ensure that all the groups in this accordion are closed, unless close-others explicitly says not to\n  this.closeOthers = function(openGroup) {\n    var closeOthers = angular.isDefined($attrs.closeOthers) ?\n      $scope.$eval($attrs.closeOthers) : accordionConfig.closeOthers;\n    if (closeOthers) {\n      angular.forEach(this.groups, function(group) {\n        if (group !== openGroup) {\n          group.isOpen = false;\n        }\n      });\n    }\n  };\n\n  // This is called from the accordion-group directive to add itself to the accordion\n  this.addGroup = function(groupScope) {\n    var that = this;\n    this.groups.push(groupScope);\n\n    groupScope.$on('$destroy', function(event) {\n      that.removeGroup(groupScope);\n    });\n  };\n\n  // This is called from the accordion-group directive when to remove itself\n  this.removeGroup = function(group) {\n    var index = this.groups.indexOf(group);\n    if (index !== -1) {\n      this.groups.splice(index, 1);\n    }\n  };\n}])\n\n// The accordion directive simply sets up the directive controller\n// and adds an accordion CSS class to itself element.\n.directive('uibAccordion', function() {\n  return {\n    controller: 'UibAccordionController',\n    controllerAs: 'accordion',\n    transclude: true,\n    templateUrl: function(element, attrs) {\n      return attrs.templateUrl || 'uib/template/accordion/accordion.html';\n    }\n  };\n})\n\n// The accordion-group directive indicates a block of html that will expand and collapse in an accordion\n.directive('uibAccordionGroup', function() {\n  return {\n    require: '^uibAccordion',         // We need this directive to be inside an accordion\n    transclude: true,              // It transcludes the contents of the directive into the template\n    restrict: 'A',\n    templateUrl: function(element, attrs) {\n      return attrs.templateUrl || 'uib/template/accordion/accordion-group.html';\n    },\n    scope: {\n      heading: '@',               // Interpolate the heading attribute onto this scope\n      panelClass: '@?',           // Ditto with panelClass\n      isOpen: '=?',\n      isDisabled: '=?'\n    },\n    controller: function() {\n      this.setHeading = function(element) {\n        this.heading = element;\n      };\n    },\n    link: function(scope, element, attrs, accordionCtrl) {\n      element.addClass('panel');\n      accordionCtrl.addGroup(scope);\n\n      scope.openClass = attrs.openClass || 'panel-open';\n      scope.panelClass = attrs.panelClass || 'panel-default';\n      scope.$watch('isOpen', function(value) {\n        element.toggleClass(scope.openClass, !!value);\n        if (value) {\n          accordionCtrl.closeOthers(scope);\n        }\n      });\n\n      scope.toggleOpen = function($event) {\n        if (!scope.isDisabled) {\n          if (!$event || $event.which === 32) {\n            scope.isOpen = !scope.isOpen;\n          }\n        }\n      };\n\n      var id = 'accordiongroup-' + scope.$id + '-' + Math.floor(Math.random() * 10000);\n      scope.headingId = id + '-tab';\n      scope.panelId = id + '-panel';\n    }\n  };\n})\n\n// Use accordion-heading below an accordion-group to provide a heading containing HTML\n.directive('uibAccordionHeading', function() {\n  return {\n    transclude: true,   // Grab the contents to be used as the heading\n    template: '',       // In effect remove this element!\n    replace: true,\n    require: '^uibAccordionGroup',\n    link: function(scope, element, attrs, accordionGroupCtrl, transclude) {\n      // Pass the heading to the accordion-group controller\n      // so that it can be transcluded into the right place in the template\n      // [The second parameter to transclude causes the elements to be cloned so that they work in ng-repeat]\n      accordionGroupCtrl.setHeading(transclude(scope, angular.noop));\n    }\n  };\n})\n\n// Use in the accordion-group template to indicate where you want the heading to be transcluded\n// You must provide the property on the accordion-group controller that will hold the transcluded element\n.directive('uibAccordionTransclude', function() {\n  return {\n    require: '^uibAccordionGroup',\n    link: function(scope, element, attrs, controller) {\n      scope.$watch(function() { return controller[attrs.uibAccordionTransclude]; }, function(heading) {\n        if (heading) {\n          var elem = angular.element(element[0].querySelector(getHeaderSelectors()));\n          elem.html('');\n          elem.append(heading);\n        }\n      });\n    }\n  };\n\n  function getHeaderSelectors() {\n      return 'uib-accordion-header,' +\n          'data-uib-accordion-header,' +\n          'x-uib-accordion-header,' +\n          'uib\\\\:accordion-header,' +\n          '[uib-accordion-header],' +\n          '[data-uib-accordion-header],' +\n          '[x-uib-accordion-header]';\n  }\n});\n\nangular.module('ui.bootstrap.alert', [])\n\n.controller('UibAlertController', ['$scope', '$element', '$attrs', '$interpolate', '$timeout', function($scope, $element, $attrs, $interpolate, $timeout) {\n  $scope.closeable = !!$attrs.close;\n  $element.addClass('alert');\n  $attrs.$set('role', 'alert');\n  if ($scope.closeable) {\n    $element.addClass('alert-dismissible');\n  }\n\n  var dismissOnTimeout = angular.isDefined($attrs.dismissOnTimeout) ?\n    $interpolate($attrs.dismissOnTimeout)($scope.$parent) : null;\n\n  if (dismissOnTimeout) {\n    $timeout(function() {\n      $scope.close();\n    }, parseInt(dismissOnTimeout, 10));\n  }\n}])\n\n.directive('uibAlert', function() {\n  return {\n    controller: 'UibAlertController',\n    controllerAs: 'alert',\n    restrict: 'A',\n    templateUrl: function(element, attrs) {\n      return attrs.templateUrl || 'uib/template/alert/alert.html';\n    },\n    transclude: true,\n    scope: {\n      close: '&'\n    }\n  };\n});\n\nangular.module('ui.bootstrap.buttons', [])\n\n.constant('uibButtonConfig', {\n  activeClass: 'active',\n  toggleEvent: 'click'\n})\n\n.controller('UibButtonsController', ['uibButtonConfig', function(buttonConfig) {\n  this.activeClass = buttonConfig.activeClass || 'active';\n  this.toggleEvent = buttonConfig.toggleEvent || 'click';\n}])\n\n.directive('uibBtnRadio', ['$parse', function($parse) {\n  return {\n    require: ['uibBtnRadio', 'ngModel'],\n    controller: 'UibButtonsController',\n    controllerAs: 'buttons',\n    link: function(scope, element, attrs, ctrls) {\n      var buttonsCtrl = ctrls[0], ngModelCtrl = ctrls[1];\n      var uncheckableExpr = $parse(attrs.uibUncheckable);\n\n      element.find('input').css({display: 'none'});\n\n      //model -> UI\n      ngModelCtrl.$render = function() {\n        element.toggleClass(buttonsCtrl.activeClass, angular.equals(ngModelCtrl.$modelValue, scope.$eval(attrs.uibBtnRadio)));\n      };\n\n      //ui->model\n      element.on(buttonsCtrl.toggleEvent, function() {\n        if (attrs.disabled) {\n          return;\n        }\n\n        var isActive = element.hasClass(buttonsCtrl.activeClass);\n\n        if (!isActive || angular.isDefined(attrs.uncheckable)) {\n          scope.$apply(function() {\n            ngModelCtrl.$setViewValue(isActive ? null : scope.$eval(attrs.uibBtnRadio));\n            ngModelCtrl.$render();\n          });\n        }\n      });\n\n      if (attrs.uibUncheckable) {\n        scope.$watch(uncheckableExpr, function(uncheckable) {\n          attrs.$set('uncheckable', uncheckable ? '' : undefined);\n        });\n      }\n    }\n  };\n}])\n\n.directive('uibBtnCheckbox', function() {\n  return {\n    require: ['uibBtnCheckbox', 'ngModel'],\n    controller: 'UibButtonsController',\n    controllerAs: 'button',\n    link: function(scope, element, attrs, ctrls) {\n      var buttonsCtrl = ctrls[0], ngModelCtrl = ctrls[1];\n\n      element.find('input').css({display: 'none'});\n\n      function getTrueValue() {\n        return getCheckboxValue(attrs.btnCheckboxTrue, true);\n      }\n\n      function getFalseValue() {\n        return getCheckboxValue(attrs.btnCheckboxFalse, false);\n      }\n\n      function getCheckboxValue(attribute, defaultValue) {\n        return angular.isDefined(attribute) ? scope.$eval(attribute) : defaultValue;\n      }\n\n      //model -> UI\n      ngModelCtrl.$render = function() {\n        element.toggleClass(buttonsCtrl.activeClass, angular.equals(ngModelCtrl.$modelValue, getTrueValue()));\n      };\n\n      //ui->model\n      element.on(buttonsCtrl.toggleEvent, function() {\n        if (attrs.disabled) {\n          return;\n        }\n\n        scope.$apply(function() {\n          ngModelCtrl.$setViewValue(element.hasClass(buttonsCtrl.activeClass) ? getFalseValue() : getTrueValue());\n          ngModelCtrl.$render();\n        });\n      });\n    }\n  };\n});\n\nangular.module('ui.bootstrap.carousel', [])\n\n.controller('UibCarouselController', ['$scope', '$element', '$interval', '$timeout', '$animate', function($scope, $element, $interval, $timeout, $animate) {\n  var self = this,\n    slides = self.slides = $scope.slides = [],\n    SLIDE_DIRECTION = 'uib-slideDirection',\n    currentIndex = $scope.active,\n    currentInterval, isPlaying;\n\n  var destroyed = false;\n  $element.addClass('carousel');\n\n  self.addSlide = function(slide, element) {\n    slides.push({\n      slide: slide,\n      element: element\n    });\n    slides.sort(function(a, b) {\n      return +a.slide.index - +b.slide.index;\n    });\n    //if this is the first slide or the slide is set to active, select it\n    if (slide.index === $scope.active || slides.length === 1 && !angular.isNumber($scope.active)) {\n      if ($scope.$currentTransition) {\n        $scope.$currentTransition = null;\n      }\n\n      currentIndex = slide.index;\n      $scope.active = slide.index;\n      setActive(currentIndex);\n      self.select(slides[findSlideIndex(slide)]);\n      if (slides.length === 1) {\n        $scope.play();\n      }\n    }\n  };\n\n  self.getCurrentIndex = function() {\n    for (var i = 0; i < slides.length; i++) {\n      if (slides[i].slide.index === currentIndex) {\n        return i;\n      }\n    }\n  };\n\n  self.next = $scope.next = function() {\n    var newIndex = (self.getCurrentIndex() + 1) % slides.length;\n\n    if (newIndex === 0 && $scope.noWrap()) {\n      $scope.pause();\n      return;\n    }\n\n    return self.select(slides[newIndex], 'next');\n  };\n\n  self.prev = $scope.prev = function() {\n    var newIndex = self.getCurrentIndex() - 1 < 0 ? slides.length - 1 : self.getCurrentIndex() - 1;\n\n    if ($scope.noWrap() && newIndex === slides.length - 1) {\n      $scope.pause();\n      return;\n    }\n\n    return self.select(slides[newIndex], 'prev');\n  };\n\n  self.removeSlide = function(slide) {\n    var index = findSlideIndex(slide);\n\n    //get the index of the slide inside the carousel\n    slides.splice(index, 1);\n    if (slides.length > 0 && currentIndex === index) {\n      if (index >= slides.length) {\n        currentIndex = slides.length - 1;\n        $scope.active = currentIndex;\n        setActive(currentIndex);\n        self.select(slides[slides.length - 1]);\n      } else {\n        currentIndex = index;\n        $scope.active = currentIndex;\n        setActive(currentIndex);\n        self.select(slides[index]);\n      }\n    } else if (currentIndex > index) {\n      currentIndex--;\n      $scope.active = currentIndex;\n    }\n\n    //clean the active value when no more slide\n    if (slides.length === 0) {\n      currentIndex = null;\n      $scope.active = null;\n    }\n  };\n\n  /* direction: \"prev\" or \"next\" */\n  self.select = $scope.select = function(nextSlide, direction) {\n    var nextIndex = findSlideIndex(nextSlide.slide);\n    //Decide direction if it's not given\n    if (direction === undefined) {\n      direction = nextIndex > self.getCurrentIndex() ? 'next' : 'prev';\n    }\n    //Prevent this user-triggered transition from occurring if there is already one in progress\n    if (nextSlide.slide.index !== currentIndex &&\n      !$scope.$currentTransition) {\n      goNext(nextSlide.slide, nextIndex, direction);\n    }\n  };\n\n  /* Allow outside people to call indexOf on slides array */\n  $scope.indexOfSlide = function(slide) {\n    return +slide.slide.index;\n  };\n\n  $scope.isActive = function(slide) {\n    return $scope.active === slide.slide.index;\n  };\n\n  $scope.isPrevDisabled = function() {\n    return $scope.active === 0 && $scope.noWrap();\n  };\n\n  $scope.isNextDisabled = function() {\n    return $scope.active === slides.length - 1 && $scope.noWrap();\n  };\n\n  $scope.pause = function() {\n    if (!$scope.noPause) {\n      isPlaying = false;\n      resetTimer();\n    }\n  };\n\n  $scope.play = function() {\n    if (!isPlaying) {\n      isPlaying = true;\n      restartTimer();\n    }\n  };\n\n  $element.on('mouseenter', $scope.pause);\n  $element.on('mouseleave', $scope.play);\n\n  $scope.$on('$destroy', function() {\n    destroyed = true;\n    resetTimer();\n  });\n\n  $scope.$watch('noTransition', function(noTransition) {\n    $animate.enabled($element, !noTransition);\n  });\n\n  $scope.$watch('interval', restartTimer);\n\n  $scope.$watchCollection('slides', resetTransition);\n\n  $scope.$watch('active', function(index) {\n    if (angular.isNumber(index) && currentIndex !== index) {\n      for (var i = 0; i < slides.length; i++) {\n        if (slides[i].slide.index === index) {\n          index = i;\n          break;\n        }\n      }\n\n      var slide = slides[index];\n      if (slide) {\n        setActive(index);\n        self.select(slides[index]);\n        currentIndex = index;\n      }\n    }\n  });\n\n  function getSlideByIndex(index) {\n    for (var i = 0, l = slides.length; i < l; ++i) {\n      if (slides[i].index === index) {\n        return slides[i];\n      }\n    }\n  }\n\n  function setActive(index) {\n    for (var i = 0; i < slides.length; i++) {\n      slides[i].slide.active = i === index;\n    }\n  }\n\n  function goNext(slide, index, direction) {\n    if (destroyed) {\n      return;\n    }\n\n    angular.extend(slide, {direction: direction});\n    angular.extend(slides[currentIndex].slide || {}, {direction: direction});\n    if ($animate.enabled($element) && !$scope.$currentTransition &&\n      slides[index].element && self.slides.length > 1) {\n      slides[index].element.data(SLIDE_DIRECTION, slide.direction);\n      var currentIdx = self.getCurrentIndex();\n\n      if (angular.isNumber(currentIdx) && slides[currentIdx].element) {\n        slides[currentIdx].element.data(SLIDE_DIRECTION, slide.direction);\n      }\n\n      $scope.$currentTransition = true;\n      $animate.on('addClass', slides[index].element, function(element, phase) {\n        if (phase === 'close') {\n          $scope.$currentTransition = null;\n          $animate.off('addClass', element);\n        }\n      });\n    }\n\n    $scope.active = slide.index;\n    currentIndex = slide.index;\n    setActive(index);\n\n    //every time you change slides, reset the timer\n    restartTimer();\n  }\n\n  function findSlideIndex(slide) {\n    for (var i = 0; i < slides.length; i++) {\n      if (slides[i].slide === slide) {\n        return i;\n      }\n    }\n  }\n\n  function resetTimer() {\n    if (currentInterval) {\n      $interval.cancel(currentInterval);\n      currentInterval = null;\n    }\n  }\n\n  function resetTransition(slides) {\n    if (!slides.length) {\n      $scope.$currentTransition = null;\n    }\n  }\n\n  function restartTimer() {\n    resetTimer();\n    var interval = +$scope.interval;\n    if (!isNaN(interval) && interval > 0) {\n      currentInterval = $interval(timerFn, interval);\n    }\n  }\n\n  function timerFn() {\n    var interval = +$scope.interval;\n    if (isPlaying && !isNaN(interval) && interval > 0 && slides.length) {\n      $scope.next();\n    } else {\n      $scope.pause();\n    }\n  }\n}])\n\n.directive('uibCarousel', function() {\n  return {\n    transclude: true,\n    controller: 'UibCarouselController',\n    controllerAs: 'carousel',\n    restrict: 'A',\n    templateUrl: function(element, attrs) {\n      return attrs.templateUrl || 'uib/template/carousel/carousel.html';\n    },\n    scope: {\n      active: '=',\n      interval: '=',\n      noTransition: '=',\n      noPause: '=',\n      noWrap: '&'\n    }\n  };\n})\n\n.directive('uibSlide', ['$animate', function($animate) {\n  return {\n    require: '^uibCarousel',\n    restrict: 'A',\n    transclude: true,\n    templateUrl: function(element, attrs) {\n      return attrs.templateUrl || 'uib/template/carousel/slide.html';\n    },\n    scope: {\n      actual: '=?',\n      index: '=?'\n    },\n    link: function (scope, element, attrs, carouselCtrl) {\n      element.addClass('item');\n      carouselCtrl.addSlide(scope, element);\n      //when the scope is destroyed then remove the slide from the current slides array\n      scope.$on('$destroy', function() {\n        carouselCtrl.removeSlide(scope);\n      });\n\n      scope.$watch('active', function(active) {\n        $animate[active ? 'addClass' : 'removeClass'](element, 'active');\n      });\n    }\n  };\n}])\n\n.animation('.item', ['$animateCss',\nfunction($animateCss) {\n  var SLIDE_DIRECTION = 'uib-slideDirection';\n\n  function removeClass(element, className, callback) {\n    element.removeClass(className);\n    if (callback) {\n      callback();\n    }\n  }\n\n  return {\n    beforeAddClass: function(element, className, done) {\n      if (className === 'active') {\n        var stopped = false;\n        var direction = element.data(SLIDE_DIRECTION);\n        var directionClass = direction === 'next' ? 'left' : 'right';\n        var removeClassFn = removeClass.bind(this, element,\n          directionClass + ' ' + direction, done);\n        element.addClass(direction);\n\n        $animateCss(element, {addClass: directionClass})\n          .start()\n          .done(removeClassFn);\n\n        return function() {\n          stopped = true;\n        };\n      }\n      done();\n    },\n    beforeRemoveClass: function (element, className, done) {\n      if (className === 'active') {\n        var stopped = false;\n        var direction = element.data(SLIDE_DIRECTION);\n        var directionClass = direction === 'next' ? 'left' : 'right';\n        var removeClassFn = removeClass.bind(this, element, directionClass, done);\n\n        $animateCss(element, {addClass: directionClass})\n          .start()\n          .done(removeClassFn);\n\n        return function() {\n          stopped = true;\n        };\n      }\n      done();\n    }\n  };\n}]);\n\nangular.module('ui.bootstrap.dateparser', [])\n\n.service('uibDateParser', ['$log', '$locale', 'dateFilter', 'orderByFilter', 'filterFilter', function($log, $locale, dateFilter, orderByFilter, filterFilter) {\n  // Pulled from https://github.com/mbostock/d3/blob/master/src/format/requote.js\n  var SPECIAL_CHARACTERS_REGEXP = /[\\\\\\^\\$\\*\\+\\?\\|\\[\\]\\(\\)\\.\\{\\}]/g;\n\n  var localeId;\n  var formatCodeToRegex;\n\n  this.init = function() {\n    localeId = $locale.id;\n\n    this.parsers = {};\n    this.formatters = {};\n\n    formatCodeToRegex = [\n      {\n        key: 'yyyy',\n        regex: '\\\\d{4}',\n        apply: function(value) { this.year = +value; },\n        formatter: function(date) {\n          var _date = new Date();\n          _date.setFullYear(Math.abs(date.getFullYear()));\n          return dateFilter(_date, 'yyyy');\n        }\n      },\n      {\n        key: 'yy',\n        regex: '\\\\d{2}',\n        apply: function(value) { value = +value; this.year = value < 69 ? value + 2000 : value + 1900; },\n        formatter: function(date) {\n          var _date = new Date();\n          _date.setFullYear(Math.abs(date.getFullYear()));\n          return dateFilter(_date, 'yy');\n        }\n      },\n      {\n        key: 'y',\n        regex: '\\\\d{1,4}',\n        apply: function(value) { this.year = +value; },\n        formatter: function(date) {\n          var _date = new Date();\n          _date.setFullYear(Math.abs(date.getFullYear()));\n          return dateFilter(_date, 'y');\n        }\n      },\n      {\n        key: 'M!',\n        regex: '0?[1-9]|1[0-2]',\n        apply: function(value) { this.month = value - 1; },\n        formatter: function(date) {\n          var value = date.getMonth();\n          if (/^[0-9]$/.test(value)) {\n            return dateFilter(date, 'MM');\n          }\n\n          return dateFilter(date, 'M');\n        }\n      },\n      {\n        key: 'MMMM',\n        regex: $locale.DATETIME_FORMATS.MONTH.join('|'),\n        apply: function(value) { this.month = $locale.DATETIME_FORMATS.MONTH.indexOf(value); },\n        formatter: function(date) { return dateFilter(date, 'MMMM'); }\n      },\n      {\n        key: 'MMM',\n        regex: $locale.DATETIME_FORMATS.SHORTMONTH.join('|'),\n        apply: function(value) { this.month = $locale.DATETIME_FORMATS.SHORTMONTH.indexOf(value); },\n        formatter: function(date) { return dateFilter(date, 'MMM'); }\n      },\n      {\n        key: 'MM',\n        regex: '0[1-9]|1[0-2]',\n        apply: function(value) { this.month = value - 1; },\n        formatter: function(date) { return dateFilter(date, 'MM'); }\n      },\n      {\n        key: 'M',\n        regex: '[1-9]|1[0-2]',\n        apply: function(value) { this.month = value - 1; },\n        formatter: function(date) { return dateFilter(date, 'M'); }\n      },\n      {\n        key: 'd!',\n        regex: '[0-2]?[0-9]{1}|3[0-1]{1}',\n        apply: function(value) { this.date = +value; },\n        formatter: function(date) {\n          var value = date.getDate();\n          if (/^[1-9]$/.test(value)) {\n            return dateFilter(date, 'dd');\n          }\n\n          return dateFilter(date, 'd');\n        }\n      },\n      {\n        key: 'dd',\n        regex: '[0-2][0-9]{1}|3[0-1]{1}',\n        apply: function(value) { this.date = +value; },\n        formatter: function(date) { return dateFilter(date, 'dd'); }\n      },\n      {\n        key: 'd',\n        regex: '[1-2]?[0-9]{1}|3[0-1]{1}',\n        apply: function(value) { this.date = +value; },\n        formatter: function(date) { return dateFilter(date, 'd'); }\n      },\n      {\n        key: 'EEEE',\n        regex: $locale.DATETIME_FORMATS.DAY.join('|'),\n        formatter: function(date) { return dateFilter(date, 'EEEE'); }\n      },\n      {\n        key: 'EEE',\n        regex: $locale.DATETIME_FORMATS.SHORTDAY.join('|'),\n        formatter: function(date) { return dateFilter(date, 'EEE'); }\n      },\n      {\n        key: 'HH',\n        regex: '(?:0|1)[0-9]|2[0-3]',\n        apply: function(value) { this.hours = +value; },\n        formatter: function(date) { return dateFilter(date, 'HH'); }\n      },\n      {\n        key: 'hh',\n        regex: '0[0-9]|1[0-2]',\n        apply: function(value) { this.hours = +value; },\n        formatter: function(date) { return dateFilter(date, 'hh'); }\n      },\n      {\n        key: 'H',\n        regex: '1?[0-9]|2[0-3]',\n        apply: function(value) { this.hours = +value; },\n        formatter: function(date) { return dateFilter(date, 'H'); }\n      },\n      {\n        key: 'h',\n        regex: '[0-9]|1[0-2]',\n        apply: function(value) { this.hours = +value; },\n        formatter: function(date) { return dateFilter(date, 'h'); }\n      },\n      {\n        key: 'mm',\n        regex: '[0-5][0-9]',\n        apply: function(value) { this.minutes = +value; },\n        formatter: function(date) { return dateFilter(date, 'mm'); }\n      },\n      {\n        key: 'm',\n        regex: '[0-9]|[1-5][0-9]',\n        apply: function(value) { this.minutes = +value; },\n        formatter: function(date) { return dateFilter(date, 'm'); }\n      },\n      {\n        key: 'sss',\n        regex: '[0-9][0-9][0-9]',\n        apply: function(value) { this.milliseconds = +value; },\n        formatter: function(date) { return dateFilter(date, 'sss'); }\n      },\n      {\n        key: 'ss',\n        regex: '[0-5][0-9]',\n        apply: function(value) { this.seconds = +value; },\n        formatter: function(date) { return dateFilter(date, 'ss'); }\n      },\n      {\n        key: 's',\n        regex: '[0-9]|[1-5][0-9]',\n        apply: function(value) { this.seconds = +value; },\n        formatter: function(date) { return dateFilter(date, 's'); }\n      },\n      {\n        key: 'a',\n        regex: $locale.DATETIME_FORMATS.AMPMS.join('|'),\n        apply: function(value) {\n          if (this.hours === 12) {\n            this.hours = 0;\n          }\n\n          if (value === 'PM') {\n            this.hours += 12;\n          }\n        },\n        formatter: function(date) { return dateFilter(date, 'a'); }\n      },\n      {\n        key: 'Z',\n        regex: '[+-]\\\\d{4}',\n        apply: function(value) {\n          var matches = value.match(/([+-])(\\d{2})(\\d{2})/),\n            sign = matches[1],\n            hours = matches[2],\n            minutes = matches[3];\n          this.hours += toInt(sign + hours);\n          this.minutes += toInt(sign + minutes);\n        },\n        formatter: function(date) {\n          return dateFilter(date, 'Z');\n        }\n      },\n      {\n        key: 'ww',\n        regex: '[0-4][0-9]|5[0-3]',\n        formatter: function(date) { return dateFilter(date, 'ww'); }\n      },\n      {\n        key: 'w',\n        regex: '[0-9]|[1-4][0-9]|5[0-3]',\n        formatter: function(date) { return dateFilter(date, 'w'); }\n      },\n      {\n        key: 'GGGG',\n        regex: $locale.DATETIME_FORMATS.ERANAMES.join('|').replace(/\\s/g, '\\\\s'),\n        formatter: function(date) { return dateFilter(date, 'GGGG'); }\n      },\n      {\n        key: 'GGG',\n        regex: $locale.DATETIME_FORMATS.ERAS.join('|'),\n        formatter: function(date) { return dateFilter(date, 'GGG'); }\n      },\n      {\n        key: 'GG',\n        regex: $locale.DATETIME_FORMATS.ERAS.join('|'),\n        formatter: function(date) { return dateFilter(date, 'GG'); }\n      },\n      {\n        key: 'G',\n        regex: $locale.DATETIME_FORMATS.ERAS.join('|'),\n        formatter: function(date) { return dateFilter(date, 'G'); }\n      }\n    ];\n\n    if (angular.version.major >= 1 && angular.version.minor > 4) {\n      formatCodeToRegex.push({\n        key: 'LLLL',\n        regex: $locale.DATETIME_FORMATS.STANDALONEMONTH.join('|'),\n        apply: function(value) { this.month = $locale.DATETIME_FORMATS.STANDALONEMONTH.indexOf(value); },\n        formatter: function(date) { return dateFilter(date, 'LLLL'); }\n      });\n    }\n  };\n\n  this.init();\n\n  function getFormatCodeToRegex(key) {\n    return filterFilter(formatCodeToRegex, {key: key}, true)[0];\n  }\n\n  this.getParser = function (key) {\n    var f = getFormatCodeToRegex(key);\n    return f && f.apply || null;\n  };\n\n  this.overrideParser = function (key, parser) {\n    var f = getFormatCodeToRegex(key);\n    if (f && angular.isFunction(parser)) {\n      this.parsers = {};\n      f.apply = parser;\n    }\n  }.bind(this);\n\n  function createParser(format) {\n    var map = [], regex = format.split('');\n\n    // check for literal values\n    var quoteIndex = format.indexOf('\\'');\n    if (quoteIndex > -1) {\n      var inLiteral = false;\n      format = format.split('');\n      for (var i = quoteIndex; i < format.length; i++) {\n        if (inLiteral) {\n          if (format[i] === '\\'') {\n            if (i + 1 < format.length && format[i+1] === '\\'') { // escaped single quote\n              format[i+1] = '$';\n              regex[i+1] = '';\n            } else { // end of literal\n              regex[i] = '';\n              inLiteral = false;\n            }\n          }\n          format[i] = '$';\n        } else {\n          if (format[i] === '\\'') { // start of literal\n            format[i] = '$';\n            regex[i] = '';\n            inLiteral = true;\n          }\n        }\n      }\n\n      format = format.join('');\n    }\n\n    angular.forEach(formatCodeToRegex, function(data) {\n      var index = format.indexOf(data.key);\n\n      if (index > -1) {\n        format = format.split('');\n\n        regex[index] = '(' + data.regex + ')';\n        format[index] = '$'; // Custom symbol to define consumed part of format\n        for (var i = index + 1, n = index + data.key.length; i < n; i++) {\n          regex[i] = '';\n          format[i] = '$';\n        }\n        format = format.join('');\n\n        map.push({\n          index: index,\n          key: data.key,\n          apply: data.apply,\n          matcher: data.regex\n        });\n      }\n    });\n\n    return {\n      regex: new RegExp('^' + regex.join('') + '$'),\n      map: orderByFilter(map, 'index')\n    };\n  }\n\n  function createFormatter(format) {\n    var formatters = [];\n    var i = 0;\n    var formatter, literalIdx;\n    while (i < format.length) {\n      if (angular.isNumber(literalIdx)) {\n        if (format.charAt(i) === '\\'') {\n          if (i + 1 >= format.length || format.charAt(i + 1) !== '\\'') {\n            formatters.push(constructLiteralFormatter(format, literalIdx, i));\n            literalIdx = null;\n          }\n        } else if (i === format.length) {\n          while (literalIdx < format.length) {\n            formatter = constructFormatterFromIdx(format, literalIdx);\n            formatters.push(formatter);\n            literalIdx = formatter.endIdx;\n          }\n        }\n\n        i++;\n        continue;\n      }\n\n      if (format.charAt(i) === '\\'') {\n        literalIdx = i;\n        i++;\n        continue;\n      }\n\n      formatter = constructFormatterFromIdx(format, i);\n\n      formatters.push(formatter.parser);\n      i = formatter.endIdx;\n    }\n\n    return formatters;\n  }\n\n  function constructLiteralFormatter(format, literalIdx, endIdx) {\n    return function() {\n      return format.substr(literalIdx + 1, endIdx - literalIdx - 1);\n    };\n  }\n\n  function constructFormatterFromIdx(format, i) {\n    var currentPosStr = format.substr(i);\n    for (var j = 0; j < formatCodeToRegex.length; j++) {\n      if (new RegExp('^' + formatCodeToRegex[j].key).test(currentPosStr)) {\n        var data = formatCodeToRegex[j];\n        return {\n          endIdx: i + data.key.length,\n          parser: data.formatter\n        };\n      }\n    }\n\n    return {\n      endIdx: i + 1,\n      parser: function() {\n        return currentPosStr.charAt(0);\n      }\n    };\n  }\n\n  this.filter = function(date, format) {\n    if (!angular.isDate(date) || isNaN(date) || !format) {\n      return '';\n    }\n\n    format = $locale.DATETIME_FORMATS[format] || format;\n\n    if ($locale.id !== localeId) {\n      this.init();\n    }\n\n    if (!this.formatters[format]) {\n      this.formatters[format] = createFormatter(format);\n    }\n\n    var formatters = this.formatters[format];\n\n    return formatters.reduce(function(str, formatter) {\n      return str + formatter(date);\n    }, '');\n  };\n\n  this.parse = function(input, format, baseDate) {\n    if (!angular.isString(input) || !format) {\n      return input;\n    }\n\n    format = $locale.DATETIME_FORMATS[format] || format;\n    format = format.replace(SPECIAL_CHARACTERS_REGEXP, '\\\\$&');\n\n    if ($locale.id !== localeId) {\n      this.init();\n    }\n\n    if (!this.parsers[format]) {\n      this.parsers[format] = createParser(format, 'apply');\n    }\n\n    var parser = this.parsers[format],\n        regex = parser.regex,\n        map = parser.map,\n        results = input.match(regex),\n        tzOffset = false;\n    if (results && results.length) {\n      var fields, dt;\n      if (angular.isDate(baseDate) && !isNaN(baseDate.getTime())) {\n        fields = {\n          year: baseDate.getFullYear(),\n          month: baseDate.getMonth(),\n          date: baseDate.getDate(),\n          hours: baseDate.getHours(),\n          minutes: baseDate.getMinutes(),\n          seconds: baseDate.getSeconds(),\n          milliseconds: baseDate.getMilliseconds()\n        };\n      } else {\n        if (baseDate) {\n          $log.warn('dateparser:', 'baseDate is not a valid date');\n        }\n        fields = { year: 1900, month: 0, date: 1, hours: 0, minutes: 0, seconds: 0, milliseconds: 0 };\n      }\n\n      for (var i = 1, n = results.length; i < n; i++) {\n        var mapper = map[i - 1];\n        if (mapper.matcher === 'Z') {\n          tzOffset = true;\n        }\n\n        if (mapper.apply) {\n          mapper.apply.call(fields, results[i]);\n        }\n      }\n\n      var datesetter = tzOffset ? Date.prototype.setUTCFullYear :\n        Date.prototype.setFullYear;\n      var timesetter = tzOffset ? Date.prototype.setUTCHours :\n        Date.prototype.setHours;\n\n      if (isValid(fields.year, fields.month, fields.date)) {\n        if (angular.isDate(baseDate) && !isNaN(baseDate.getTime()) && !tzOffset) {\n          dt = new Date(baseDate);\n          datesetter.call(dt, fields.year, fields.month, fields.date);\n          timesetter.call(dt, fields.hours, fields.minutes,\n            fields.seconds, fields.milliseconds);\n        } else {\n          dt = new Date(0);\n          datesetter.call(dt, fields.year, fields.month, fields.date);\n          timesetter.call(dt, fields.hours || 0, fields.minutes || 0,\n            fields.seconds || 0, fields.milliseconds || 0);\n        }\n      }\n\n      return dt;\n    }\n  };\n\n  // Check if date is valid for specific month (and year for February).\n  // Month: 0 = Jan, 1 = Feb, etc\n  function isValid(year, month, date) {\n    if (date < 1) {\n      return false;\n    }\n\n    if (month === 1 && date > 28) {\n      return date === 29 && (year % 4 === 0 && year % 100 !== 0 || year % 400 === 0);\n    }\n\n    if (month === 3 || month === 5 || month === 8 || month === 10) {\n      return date < 31;\n    }\n\n    return true;\n  }\n\n  function toInt(str) {\n    return parseInt(str, 10);\n  }\n\n  this.toTimezone = toTimezone;\n  this.fromTimezone = fromTimezone;\n  this.timezoneToOffset = timezoneToOffset;\n  this.addDateMinutes = addDateMinutes;\n  this.convertTimezoneToLocal = convertTimezoneToLocal;\n\n  function toTimezone(date, timezone) {\n    return date && timezone ? convertTimezoneToLocal(date, timezone) : date;\n  }\n\n  function fromTimezone(date, timezone) {\n    return date && timezone ? convertTimezoneToLocal(date, timezone, true) : date;\n  }\n\n  //https://github.com/angular/angular.js/blob/622c42169699ec07fc6daaa19fe6d224e5d2f70e/src/Angular.js#L1207\n  function timezoneToOffset(timezone, fallback) {\n    timezone = timezone.replace(/:/g, '');\n    var requestedTimezoneOffset = Date.parse('Jan 01, 1970 00:00:00 ' + timezone) / 60000;\n    return isNaN(requestedTimezoneOffset) ? fallback : requestedTimezoneOffset;\n  }\n\n  function addDateMinutes(date, minutes) {\n    date = new Date(date.getTime());\n    date.setMinutes(date.getMinutes() + minutes);\n    return date;\n  }\n\n  function convertTimezoneToLocal(date, timezone, reverse) {\n    reverse = reverse ? -1 : 1;\n    var dateTimezoneOffset = date.getTimezoneOffset();\n    var timezoneOffset = timezoneToOffset(timezone, dateTimezoneOffset);\n    return addDateMinutes(date, reverse * (timezoneOffset - dateTimezoneOffset));\n  }\n}]);\n\n// Avoiding use of ng-class as it creates a lot of watchers when a class is to be applied to\n// at most one element.\nangular.module('ui.bootstrap.isClass', [])\n.directive('uibIsClass', [\n         '$animate',\nfunction ($animate) {\n  //                    11111111          22222222\n  var ON_REGEXP = /^\\s*([\\s\\S]+?)\\s+on\\s+([\\s\\S]+?)\\s*$/;\n  //                    11111111           22222222\n  var IS_REGEXP = /^\\s*([\\s\\S]+?)\\s+for\\s+([\\s\\S]+?)\\s*$/;\n\n  var dataPerTracked = {};\n\n  return {\n    restrict: 'A',\n    compile: function(tElement, tAttrs) {\n      var linkedScopes = [];\n      var instances = [];\n      var expToData = {};\n      var lastActivated = null;\n      var onExpMatches = tAttrs.uibIsClass.match(ON_REGEXP);\n      var onExp = onExpMatches[2];\n      var expsStr = onExpMatches[1];\n      var exps = expsStr.split(',');\n\n      return linkFn;\n\n      function linkFn(scope, element, attrs) {\n        linkedScopes.push(scope);\n        instances.push({\n          scope: scope,\n          element: element\n        });\n\n        exps.forEach(function(exp, k) {\n          addForExp(exp, scope);\n        });\n\n        scope.$on('$destroy', removeScope);\n      }\n\n      function addForExp(exp, scope) {\n        var matches = exp.match(IS_REGEXP);\n        var clazz = scope.$eval(matches[1]);\n        var compareWithExp = matches[2];\n        var data = expToData[exp];\n        if (!data) {\n          var watchFn = function(compareWithVal) {\n            var newActivated = null;\n            instances.some(function(instance) {\n              var thisVal = instance.scope.$eval(onExp);\n              if (thisVal === compareWithVal) {\n                newActivated = instance;\n                return true;\n              }\n            });\n            if (data.lastActivated !== newActivated) {\n              if (data.lastActivated) {\n                $animate.removeClass(data.lastActivated.element, clazz);\n              }\n              if (newActivated) {\n                $animate.addClass(newActivated.element, clazz);\n              }\n              data.lastActivated = newActivated;\n            }\n          };\n          expToData[exp] = data = {\n            lastActivated: null,\n            scope: scope,\n            watchFn: watchFn,\n            compareWithExp: compareWithExp,\n            watcher: scope.$watch(compareWithExp, watchFn)\n          };\n        }\n        data.watchFn(scope.$eval(compareWithExp));\n      }\n\n      function removeScope(e) {\n        var removedScope = e.targetScope;\n        var index = linkedScopes.indexOf(removedScope);\n        linkedScopes.splice(index, 1);\n        instances.splice(index, 1);\n        if (linkedScopes.length) {\n          var newWatchScope = linkedScopes[0];\n          angular.forEach(expToData, function(data) {\n            if (data.scope === removedScope) {\n              data.watcher = newWatchScope.$watch(data.compareWithExp, data.watchFn);\n              data.scope = newWatchScope;\n            }\n          });\n        } else {\n          expToData = {};\n        }\n      }\n    }\n  };\n}]);\nangular.module('ui.bootstrap.datepicker', ['ui.bootstrap.dateparser', 'ui.bootstrap.isClass'])\n\n.value('$datepickerSuppressError', false)\n\n.value('$datepickerLiteralWarning', true)\n\n.constant('uibDatepickerConfig', {\n  datepickerMode: 'day',\n  formatDay: 'dd',\n  formatMonth: 'MMMM',\n  formatYear: 'yyyy',\n  formatDayHeader: 'EEE',\n  formatDayTitle: 'MMMM yyyy',\n  formatMonthTitle: 'yyyy',\n  maxDate: null,\n  maxMode: 'year',\n  minDate: null,\n  minMode: 'day',\n  monthColumns: 3,\n  ngModelOptions: {},\n  shortcutPropagation: false,\n  showWeeks: true,\n  yearColumns: 5,\n  yearRows: 4\n})\n\n.controller('UibDatepickerController', ['$scope', '$element', '$attrs', '$parse', '$interpolate', '$locale', '$log', 'dateFilter', 'uibDatepickerConfig', '$datepickerLiteralWarning', '$datepickerSuppressError', 'uibDateParser',\n  function($scope, $element, $attrs, $parse, $interpolate, $locale, $log, dateFilter, datepickerConfig, $datepickerLiteralWarning, $datepickerSuppressError, dateParser) {\n  var self = this,\n      ngModelCtrl = { $setViewValue: angular.noop }, // nullModelCtrl;\n      ngModelOptions = {},\n      watchListeners = [];\n\n  $element.addClass('uib-datepicker');\n  $attrs.$set('role', 'application');\n\n  if (!$scope.datepickerOptions) {\n    $scope.datepickerOptions = {};\n  }\n\n  // Modes chain\n  this.modes = ['day', 'month', 'year'];\n\n  [\n    'customClass',\n    'dateDisabled',\n    'datepickerMode',\n    'formatDay',\n    'formatDayHeader',\n    'formatDayTitle',\n    'formatMonth',\n    'formatMonthTitle',\n    'formatYear',\n    'maxDate',\n    'maxMode',\n    'minDate',\n    'minMode',\n    'monthColumns',\n    'showWeeks',\n    'shortcutPropagation',\n    'startingDay',\n    'yearColumns',\n    'yearRows'\n  ].forEach(function(key) {\n    switch (key) {\n      case 'customClass':\n      case 'dateDisabled':\n        $scope[key] = $scope.datepickerOptions[key] || angular.noop;\n        break;\n      case 'datepickerMode':\n        $scope.datepickerMode = angular.isDefined($scope.datepickerOptions.datepickerMode) ?\n          $scope.datepickerOptions.datepickerMode : datepickerConfig.datepickerMode;\n        break;\n      case 'formatDay':\n      case 'formatDayHeader':\n      case 'formatDayTitle':\n      case 'formatMonth':\n      case 'formatMonthTitle':\n      case 'formatYear':\n        self[key] = angular.isDefined($scope.datepickerOptions[key]) ?\n          $interpolate($scope.datepickerOptions[key])($scope.$parent) :\n          datepickerConfig[key];\n        break;\n      case 'monthColumns':\n      case 'showWeeks':\n      case 'shortcutPropagation':\n      case 'yearColumns':\n      case 'yearRows':\n        self[key] = angular.isDefined($scope.datepickerOptions[key]) ?\n          $scope.datepickerOptions[key] : datepickerConfig[key];\n        break;\n      case 'startingDay':\n        if (angular.isDefined($scope.datepickerOptions.startingDay)) {\n          self.startingDay = $scope.datepickerOptions.startingDay;\n        } else if (angular.isNumber(datepickerConfig.startingDay)) {\n          self.startingDay = datepickerConfig.startingDay;\n        } else {\n          self.startingDay = ($locale.DATETIME_FORMATS.FIRSTDAYOFWEEK + 8) % 7;\n        }\n\n        break;\n      case 'maxDate':\n      case 'minDate':\n        $scope.$watch('datepickerOptions.' + key, function(value) {\n          if (value) {\n            if (angular.isDate(value)) {\n              self[key] = dateParser.fromTimezone(new Date(value), ngModelOptions.getOption('timezone'));\n            } else {\n              if ($datepickerLiteralWarning) {\n                $log.warn('Literal date support has been deprecated, please switch to date object usage');\n              }\n\n              self[key] = new Date(dateFilter(value, 'medium'));\n            }\n          } else {\n            self[key] = datepickerConfig[key] ?\n              dateParser.fromTimezone(new Date(datepickerConfig[key]), ngModelOptions.getOption('timezone')) :\n              null;\n          }\n\n          self.refreshView();\n        });\n\n        break;\n      case 'maxMode':\n      case 'minMode':\n        if ($scope.datepickerOptions[key]) {\n          $scope.$watch(function() { return $scope.datepickerOptions[key]; }, function(value) {\n            self[key] = $scope[key] = angular.isDefined(value) ? value : $scope.datepickerOptions[key];\n            if (key === 'minMode' && self.modes.indexOf($scope.datepickerOptions.datepickerMode) < self.modes.indexOf(self[key]) ||\n              key === 'maxMode' && self.modes.indexOf($scope.datepickerOptions.datepickerMode) > self.modes.indexOf(self[key])) {\n              $scope.datepickerMode = self[key];\n              $scope.datepickerOptions.datepickerMode = self[key];\n            }\n          });\n        } else {\n          self[key] = $scope[key] = datepickerConfig[key] || null;\n        }\n\n        break;\n    }\n  });\n\n  $scope.uniqueId = 'datepicker-' + $scope.$id + '-' + Math.floor(Math.random() * 10000);\n\n  $scope.disabled = angular.isDefined($attrs.disabled) || false;\n  if (angular.isDefined($attrs.ngDisabled)) {\n    watchListeners.push($scope.$parent.$watch($attrs.ngDisabled, function(disabled) {\n      $scope.disabled = disabled;\n      self.refreshView();\n    }));\n  }\n\n  $scope.isActive = function(dateObject) {\n    if (self.compare(dateObject.date, self.activeDate) === 0) {\n      $scope.activeDateId = dateObject.uid;\n      return true;\n    }\n    return false;\n  };\n\n  this.init = function(ngModelCtrl_) {\n    ngModelCtrl = ngModelCtrl_;\n    ngModelOptions = extractOptions(ngModelCtrl);\n\n    if ($scope.datepickerOptions.initDate) {\n      self.activeDate = dateParser.fromTimezone($scope.datepickerOptions.initDate, ngModelOptions.getOption('timezone')) || new Date();\n      $scope.$watch('datepickerOptions.initDate', function(initDate) {\n        if (initDate && (ngModelCtrl.$isEmpty(ngModelCtrl.$modelValue) || ngModelCtrl.$invalid)) {\n          self.activeDate = dateParser.fromTimezone(initDate, ngModelOptions.getOption('timezone'));\n          self.refreshView();\n        }\n      });\n    } else {\n      self.activeDate = new Date();\n    }\n\n    var date = ngModelCtrl.$modelValue ? new Date(ngModelCtrl.$modelValue) : new Date();\n    this.activeDate = !isNaN(date) ?\n      dateParser.fromTimezone(date, ngModelOptions.getOption('timezone')) :\n      dateParser.fromTimezone(new Date(), ngModelOptions.getOption('timezone'));\n\n    ngModelCtrl.$render = function() {\n      self.render();\n    };\n  };\n\n  this.render = function() {\n    if (ngModelCtrl.$viewValue) {\n      var date = new Date(ngModelCtrl.$viewValue),\n          isValid = !isNaN(date);\n\n      if (isValid) {\n        this.activeDate = dateParser.fromTimezone(date, ngModelOptions.getOption('timezone'));\n      } else if (!$datepickerSuppressError) {\n        $log.error('Datepicker directive: \"ng-model\" value must be a Date object');\n      }\n    }\n    this.refreshView();\n  };\n\n  this.refreshView = function() {\n    if (this.element) {\n      $scope.selectedDt = null;\n      this._refreshView();\n      if ($scope.activeDt) {\n        $scope.activeDateId = $scope.activeDt.uid;\n      }\n\n      var date = ngModelCtrl.$viewValue ? new Date(ngModelCtrl.$viewValue) : null;\n      date = dateParser.fromTimezone(date, ngModelOptions.getOption('timezone'));\n      ngModelCtrl.$setValidity('dateDisabled', !date ||\n        this.element && !this.isDisabled(date));\n    }\n  };\n\n  this.createDateObject = function(date, format) {\n    var model = ngModelCtrl.$viewValue ? new Date(ngModelCtrl.$viewValue) : null;\n    model = dateParser.fromTimezone(model, ngModelOptions.getOption('timezone'));\n    var today = new Date();\n    today = dateParser.fromTimezone(today, ngModelOptions.getOption('timezone'));\n    var time = this.compare(date, today);\n    var dt = {\n      date: date,\n      label: dateParser.filter(date, format),\n      selected: model && this.compare(date, model) === 0,\n      disabled: this.isDisabled(date),\n      past: time < 0,\n      current: time === 0,\n      future: time > 0,\n      customClass: this.customClass(date) || null\n    };\n\n    if (model && this.compare(date, model) === 0) {\n      $scope.selectedDt = dt;\n    }\n\n    if (self.activeDate && this.compare(dt.date, self.activeDate) === 0) {\n      $scope.activeDt = dt;\n    }\n\n    return dt;\n  };\n\n  this.isDisabled = function(date) {\n    return $scope.disabled ||\n      this.minDate && this.compare(date, this.minDate) < 0 ||\n      this.maxDate && this.compare(date, this.maxDate) > 0 ||\n      $scope.dateDisabled && $scope.dateDisabled({date: date, mode: $scope.datepickerMode});\n  };\n\n  this.customClass = function(date) {\n    return $scope.customClass({date: date, mode: $scope.datepickerMode});\n  };\n\n  // Split array into smaller arrays\n  this.split = function(arr, size) {\n    var arrays = [];\n    while (arr.length > 0) {\n      arrays.push(arr.splice(0, size));\n    }\n    return arrays;\n  };\n\n  $scope.select = function(date) {\n    if ($scope.datepickerMode === self.minMode) {\n      var dt = ngModelCtrl.$viewValue ? dateParser.fromTimezone(new Date(ngModelCtrl.$viewValue), ngModelOptions.getOption('timezone')) : new Date(0, 0, 0, 0, 0, 0, 0);\n      dt.setFullYear(date.getFullYear(), date.getMonth(), date.getDate());\n      dt = dateParser.toTimezone(dt, ngModelOptions.getOption('timezone'));\n      ngModelCtrl.$setViewValue(dt);\n      ngModelCtrl.$render();\n    } else {\n      self.activeDate = date;\n      setMode(self.modes[self.modes.indexOf($scope.datepickerMode) - 1]);\n\n      $scope.$emit('uib:datepicker.mode');\n    }\n\n    $scope.$broadcast('uib:datepicker.focus');\n  };\n\n  $scope.move = function(direction) {\n    var year = self.activeDate.getFullYear() + direction * (self.step.years || 0),\n        month = self.activeDate.getMonth() + direction * (self.step.months || 0);\n    self.activeDate.setFullYear(year, month, 1);\n    self.refreshView();\n  };\n\n  $scope.toggleMode = function(direction) {\n    direction = direction || 1;\n\n    if ($scope.datepickerMode === self.maxMode && direction === 1 ||\n      $scope.datepickerMode === self.minMode && direction === -1) {\n      return;\n    }\n\n    setMode(self.modes[self.modes.indexOf($scope.datepickerMode) + direction]);\n\n    $scope.$emit('uib:datepicker.mode');\n  };\n\n  // Key event mapper\n  $scope.keys = { 13: 'enter', 32: 'space', 33: 'pageup', 34: 'pagedown', 35: 'end', 36: 'home', 37: 'left', 38: 'up', 39: 'right', 40: 'down' };\n\n  var focusElement = function() {\n    self.element[0].focus();\n  };\n\n  // Listen for focus requests from popup directive\n  $scope.$on('uib:datepicker.focus', focusElement);\n\n  $scope.keydown = function(evt) {\n    var key = $scope.keys[evt.which];\n\n    if (!key || evt.shiftKey || evt.altKey || $scope.disabled) {\n      return;\n    }\n\n    evt.preventDefault();\n    if (!self.shortcutPropagation) {\n      evt.stopPropagation();\n    }\n\n    if (key === 'enter' || key === 'space') {\n      if (self.isDisabled(self.activeDate)) {\n        return; // do nothing\n      }\n      $scope.select(self.activeDate);\n    } else if (evt.ctrlKey && (key === 'up' || key === 'down')) {\n      $scope.toggleMode(key === 'up' ? 1 : -1);\n    } else {\n      self.handleKeyDown(key, evt);\n      self.refreshView();\n    }\n  };\n\n  $element.on('keydown', function(evt) {\n    $scope.$apply(function() {\n      $scope.keydown(evt);\n    });\n  });\n\n  $scope.$on('$destroy', function() {\n    //Clear all watch listeners on destroy\n    while (watchListeners.length) {\n      watchListeners.shift()();\n    }\n  });\n\n  function setMode(mode) {\n    $scope.datepickerMode = mode;\n    $scope.datepickerOptions.datepickerMode = mode;\n  }\n\n  function extractOptions(ngModelCtrl) {\n    var ngModelOptions;\n\n    if (angular.version.minor < 6) { // in angular < 1.6 $options could be missing\n      // guarantee a value\n      ngModelOptions = ngModelCtrl.$options ||\n        $scope.datepickerOptions.ngModelOptions ||\n        datepickerConfig.ngModelOptions ||\n        {};\n\n      // mimic 1.6+ api\n      ngModelOptions.getOption = function (key) {\n        return ngModelOptions[key];\n      };\n    } else { // in angular >=1.6 $options is always present\n      // ng-model-options defaults timezone to null; don't let its precedence squash a non-null value\n      var timezone = ngModelCtrl.$options.getOption('timezone') ||\n        ($scope.datepickerOptions.ngModelOptions ? $scope.datepickerOptions.ngModelOptions.timezone : null) ||\n        (datepickerConfig.ngModelOptions ? datepickerConfig.ngModelOptions.timezone : null);\n\n      // values passed to createChild override existing values\n      ngModelOptions = ngModelCtrl.$options // start with a ModelOptions instance\n        .createChild(datepickerConfig.ngModelOptions) // lowest precedence\n        .createChild($scope.datepickerOptions.ngModelOptions)\n        .createChild(ngModelCtrl.$options) // highest precedence\n        .createChild({timezone: timezone}); // to keep from squashing a non-null value\n    }\n\n    return ngModelOptions;\n  }\n}])\n\n.controller('UibDaypickerController', ['$scope', '$element', 'dateFilter', function(scope, $element, dateFilter) {\n  var DAYS_IN_MONTH = [31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31];\n\n  this.step = { months: 1 };\n  this.element = $element;\n  function getDaysInMonth(year, month) {\n    return month === 1 && year % 4 === 0 &&\n      (year % 100 !== 0 || year % 400 === 0) ? 29 : DAYS_IN_MONTH[month];\n  }\n\n  this.init = function(ctrl) {\n    angular.extend(ctrl, this);\n    scope.showWeeks = ctrl.showWeeks;\n    ctrl.refreshView();\n  };\n\n  this.getDates = function(startDate, n) {\n    var dates = new Array(n), current = new Date(startDate), i = 0, date;\n    while (i < n) {\n      date = new Date(current);\n      dates[i++] = date;\n      current.setDate(current.getDate() + 1);\n    }\n    return dates;\n  };\n\n  this._refreshView = function() {\n    var year = this.activeDate.getFullYear(),\n      month = this.activeDate.getMonth(),\n      firstDayOfMonth = new Date(this.activeDate);\n\n    firstDayOfMonth.setFullYear(year, month, 1);\n\n    var difference = this.startingDay - firstDayOfMonth.getDay(),\n      numDisplayedFromPreviousMonth = difference > 0 ?\n        7 - difference : - difference,\n      firstDate = new Date(firstDayOfMonth);\n\n    if (numDisplayedFromPreviousMonth > 0) {\n      firstDate.setDate(-numDisplayedFromPreviousMonth + 1);\n    }\n\n    // 42 is the number of days on a six-week calendar\n    var days = this.getDates(firstDate, 42);\n    for (var i = 0; i < 42; i ++) {\n      days[i] = angular.extend(this.createDateObject(days[i], this.formatDay), {\n        secondary: days[i].getMonth() !== month,\n        uid: scope.uniqueId + '-' + i\n      });\n    }\n\n    scope.labels = new Array(7);\n    for (var j = 0; j < 7; j++) {\n      scope.labels[j] = {\n        abbr: dateFilter(days[j].date, this.formatDayHeader),\n        full: dateFilter(days[j].date, 'EEEE')\n      };\n    }\n\n    scope.title = dateFilter(this.activeDate, this.formatDayTitle);\n    scope.rows = this.split(days, 7);\n\n    if (scope.showWeeks) {\n      scope.weekNumbers = [];\n      var thursdayIndex = (4 + 7 - this.startingDay) % 7,\n          numWeeks = scope.rows.length;\n      for (var curWeek = 0; curWeek < numWeeks; curWeek++) {\n        scope.weekNumbers.push(\n          getISO8601WeekNumber(scope.rows[curWeek][thursdayIndex].date));\n      }\n    }\n  };\n\n  this.compare = function(date1, date2) {\n    var _date1 = new Date(date1.getFullYear(), date1.getMonth(), date1.getDate());\n    var _date2 = new Date(date2.getFullYear(), date2.getMonth(), date2.getDate());\n    _date1.setFullYear(date1.getFullYear());\n    _date2.setFullYear(date2.getFullYear());\n    return _date1 - _date2;\n  };\n\n  function getISO8601WeekNumber(date) {\n    var checkDate = new Date(date);\n    checkDate.setDate(checkDate.getDate() + 4 - (checkDate.getDay() || 7)); // Thursday\n    var time = checkDate.getTime();\n    checkDate.setMonth(0); // Compare with Jan 1\n    checkDate.setDate(1);\n    return Math.floor(Math.round((time - checkDate) / 86400000) / 7) + 1;\n  }\n\n  this.handleKeyDown = function(key, evt) {\n    var date = this.activeDate.getDate();\n\n    if (key === 'left') {\n      date = date - 1;\n    } else if (key === 'up') {\n      date = date - 7;\n    } else if (key === 'right') {\n      date = date + 1;\n    } else if (key === 'down') {\n      date = date + 7;\n    } else if (key === 'pageup' || key === 'pagedown') {\n      var month = this.activeDate.getMonth() + (key === 'pageup' ? - 1 : 1);\n      this.activeDate.setMonth(month, 1);\n      date = Math.min(getDaysInMonth(this.activeDate.getFullYear(), this.activeDate.getMonth()), date);\n    } else if (key === 'home') {\n      date = 1;\n    } else if (key === 'end') {\n      date = getDaysInMonth(this.activeDate.getFullYear(), this.activeDate.getMonth());\n    }\n    this.activeDate.setDate(date);\n  };\n}])\n\n.controller('UibMonthpickerController', ['$scope', '$element', 'dateFilter', function(scope, $element, dateFilter) {\n  this.step = { years: 1 };\n  this.element = $element;\n\n  this.init = function(ctrl) {\n    angular.extend(ctrl, this);\n    ctrl.refreshView();\n  };\n\n  this._refreshView = function() {\n    var months = new Array(12),\n        year = this.activeDate.getFullYear(),\n        date;\n\n    for (var i = 0; i < 12; i++) {\n      date = new Date(this.activeDate);\n      date.setFullYear(year, i, 1);\n      months[i] = angular.extend(this.createDateObject(date, this.formatMonth), {\n        uid: scope.uniqueId + '-' + i\n      });\n    }\n\n    scope.title = dateFilter(this.activeDate, this.formatMonthTitle);\n    scope.rows = this.split(months, this.monthColumns);\n    scope.yearHeaderColspan = this.monthColumns > 3 ? this.monthColumns - 2 : 1;\n  };\n\n  this.compare = function(date1, date2) {\n    var _date1 = new Date(date1.getFullYear(), date1.getMonth());\n    var _date2 = new Date(date2.getFullYear(), date2.getMonth());\n    _date1.setFullYear(date1.getFullYear());\n    _date2.setFullYear(date2.getFullYear());\n    return _date1 - _date2;\n  };\n\n  this.handleKeyDown = function(key, evt) {\n    var date = this.activeDate.getMonth();\n\n    if (key === 'left') {\n      date = date - 1;\n    } else if (key === 'up') {\n      date = date - this.monthColumns;\n    } else if (key === 'right') {\n      date = date + 1;\n    } else if (key === 'down') {\n      date = date + this.monthColumns;\n    } else if (key === 'pageup' || key === 'pagedown') {\n      var year = this.activeDate.getFullYear() + (key === 'pageup' ? - 1 : 1);\n      this.activeDate.setFullYear(year);\n    } else if (key === 'home') {\n      date = 0;\n    } else if (key === 'end') {\n      date = 11;\n    }\n    this.activeDate.setMonth(date);\n  };\n}])\n\n.controller('UibYearpickerController', ['$scope', '$element', 'dateFilter', function(scope, $element, dateFilter) {\n  var columns, range;\n  this.element = $element;\n\n  function getStartingYear(year) {\n    return parseInt((year - 1) / range, 10) * range + 1;\n  }\n\n  this.yearpickerInit = function() {\n    columns = this.yearColumns;\n    range = this.yearRows * columns;\n    this.step = { years: range };\n  };\n\n  this._refreshView = function() {\n    var years = new Array(range), date;\n\n    for (var i = 0, start = getStartingYear(this.activeDate.getFullYear()); i < range; i++) {\n      date = new Date(this.activeDate);\n      date.setFullYear(start + i, 0, 1);\n      years[i] = angular.extend(this.createDateObject(date, this.formatYear), {\n        uid: scope.uniqueId + '-' + i\n      });\n    }\n\n    scope.title = [years[0].label, years[range - 1].label].join(' - ');\n    scope.rows = this.split(years, columns);\n    scope.columns = columns;\n  };\n\n  this.compare = function(date1, date2) {\n    return date1.getFullYear() - date2.getFullYear();\n  };\n\n  this.handleKeyDown = function(key, evt) {\n    var date = this.activeDate.getFullYear();\n\n    if (key === 'left') {\n      date = date - 1;\n    } else if (key === 'up') {\n      date = date - columns;\n    } else if (key === 'right') {\n      date = date + 1;\n    } else if (key === 'down') {\n      date = date + columns;\n    } else if (key === 'pageup' || key === 'pagedown') {\n      date += (key === 'pageup' ? - 1 : 1) * range;\n    } else if (key === 'home') {\n      date = getStartingYear(this.activeDate.getFullYear());\n    } else if (key === 'end') {\n      date = getStartingYear(this.activeDate.getFullYear()) + range - 1;\n    }\n    this.activeDate.setFullYear(date);\n  };\n}])\n\n.directive('uibDatepicker', function() {\n  return {\n    templateUrl: function(element, attrs) {\n      return attrs.templateUrl || 'uib/template/datepicker/datepicker.html';\n    },\n    scope: {\n      datepickerOptions: '=?'\n    },\n    require: ['uibDatepicker', '^ngModel'],\n    restrict: 'A',\n    controller: 'UibDatepickerController',\n    controllerAs: 'datepicker',\n    link: function(scope, element, attrs, ctrls) {\n      var datepickerCtrl = ctrls[0], ngModelCtrl = ctrls[1];\n\n      datepickerCtrl.init(ngModelCtrl);\n    }\n  };\n})\n\n.directive('uibDaypicker', function() {\n  return {\n    templateUrl: function(element, attrs) {\n      return attrs.templateUrl || 'uib/template/datepicker/day.html';\n    },\n    require: ['^uibDatepicker', 'uibDaypicker'],\n    restrict: 'A',\n    controller: 'UibDaypickerController',\n    link: function(scope, element, attrs, ctrls) {\n      var datepickerCtrl = ctrls[0],\n        daypickerCtrl = ctrls[1];\n\n      daypickerCtrl.init(datepickerCtrl);\n    }\n  };\n})\n\n.directive('uibMonthpicker', function() {\n  return {\n    templateUrl: function(element, attrs) {\n      return attrs.templateUrl || 'uib/template/datepicker/month.html';\n    },\n    require: ['^uibDatepicker', 'uibMonthpicker'],\n    restrict: 'A',\n    controller: 'UibMonthpickerController',\n    link: function(scope, element, attrs, ctrls) {\n      var datepickerCtrl = ctrls[0],\n        monthpickerCtrl = ctrls[1];\n\n      monthpickerCtrl.init(datepickerCtrl);\n    }\n  };\n})\n\n.directive('uibYearpicker', function() {\n  return {\n    templateUrl: function(element, attrs) {\n      return attrs.templateUrl || 'uib/template/datepicker/year.html';\n    },\n    require: ['^uibDatepicker', 'uibYearpicker'],\n    restrict: 'A',\n    controller: 'UibYearpickerController',\n    link: function(scope, element, attrs, ctrls) {\n      var ctrl = ctrls[0];\n      angular.extend(ctrl, ctrls[1]);\n      ctrl.yearpickerInit();\n\n      ctrl.refreshView();\n    }\n  };\n});\n\nangular.module('ui.bootstrap.position', [])\n\n/**\n * A set of utility methods for working with the DOM.\n * It is meant to be used where we need to absolute-position elements in\n * relation to another element (this is the case for tooltips, popovers,\n * typeahead suggestions etc.).\n */\n  .factory('$uibPosition', ['$document', '$window', function($document, $window) {\n    /**\n     * Used by scrollbarWidth() function to cache scrollbar's width.\n     * Do not access this variable directly, use scrollbarWidth() instead.\n     */\n    var SCROLLBAR_WIDTH;\n    /**\n     * scrollbar on body and html element in IE and Edge overlay\n     * content and should be considered 0 width.\n     */\n    var BODY_SCROLLBAR_WIDTH;\n    var OVERFLOW_REGEX = {\n      normal: /(auto|scroll)/,\n      hidden: /(auto|scroll|hidden)/\n    };\n    var PLACEMENT_REGEX = {\n      auto: /\\s?auto?\\s?/i,\n      primary: /^(top|bottom|left|right)$/,\n      secondary: /^(top|bottom|left|right|center)$/,\n      vertical: /^(top|bottom)$/\n    };\n    var BODY_REGEX = /(HTML|BODY)/;\n\n    return {\n\n      /**\n       * Provides a raw DOM element from a jQuery/jQLite element.\n       *\n       * @param {element} elem - The element to convert.\n       *\n       * @returns {element} A HTML element.\n       */\n      getRawNode: function(elem) {\n        return elem.nodeName ? elem : elem[0] || elem;\n      },\n\n      /**\n       * Provides a parsed number for a style property.  Strips\n       * units and casts invalid numbers to 0.\n       *\n       * @param {string} value - The style value to parse.\n       *\n       * @returns {number} A valid number.\n       */\n      parseStyle: function(value) {\n        value = parseFloat(value);\n        return isFinite(value) ? value : 0;\n      },\n\n      /**\n       * Provides the closest positioned ancestor.\n       *\n       * @param {element} element - The element to get the offest parent for.\n       *\n       * @returns {element} The closest positioned ancestor.\n       */\n      offsetParent: function(elem) {\n        elem = this.getRawNode(elem);\n\n        var offsetParent = elem.offsetParent || $document[0].documentElement;\n\n        function isStaticPositioned(el) {\n          return ($window.getComputedStyle(el).position || 'static') === 'static';\n        }\n\n        while (offsetParent && offsetParent !== $document[0].documentElement && isStaticPositioned(offsetParent)) {\n          offsetParent = offsetParent.offsetParent;\n        }\n\n        return offsetParent || $document[0].documentElement;\n      },\n\n      /**\n       * Provides the scrollbar width, concept from TWBS measureScrollbar()\n       * function in https://github.com/twbs/bootstrap/blob/master/js/modal.js\n       * In IE and Edge, scollbar on body and html element overlay and should\n       * return a width of 0.\n       *\n       * @returns {number} The width of the browser scollbar.\n       */\n      scrollbarWidth: function(isBody) {\n        if (isBody) {\n          if (angular.isUndefined(BODY_SCROLLBAR_WIDTH)) {\n            var bodyElem = $document.find('body');\n            bodyElem.addClass('uib-position-body-scrollbar-measure');\n            BODY_SCROLLBAR_WIDTH = $window.innerWidth - bodyElem[0].clientWidth;\n            BODY_SCROLLBAR_WIDTH = isFinite(BODY_SCROLLBAR_WIDTH) ? BODY_SCROLLBAR_WIDTH : 0;\n            bodyElem.removeClass('uib-position-body-scrollbar-measure');\n          }\n          return BODY_SCROLLBAR_WIDTH;\n        }\n\n        if (angular.isUndefined(SCROLLBAR_WIDTH)) {\n          var scrollElem = angular.element('<div class=\"uib-position-scrollbar-measure\"></div>');\n          $document.find('body').append(scrollElem);\n          SCROLLBAR_WIDTH = scrollElem[0].offsetWidth - scrollElem[0].clientWidth;\n          SCROLLBAR_WIDTH = isFinite(SCROLLBAR_WIDTH) ? SCROLLBAR_WIDTH : 0;\n          scrollElem.remove();\n        }\n\n        return SCROLLBAR_WIDTH;\n      },\n\n      /**\n       * Provides the padding required on an element to replace the scrollbar.\n       *\n       * @returns {object} An object with the following properties:\n       *   <ul>\n       *     <li>**scrollbarWidth**: the width of the scrollbar</li>\n       *     <li>**widthOverflow**: whether the the width is overflowing</li>\n       *     <li>**right**: the amount of right padding on the element needed to replace the scrollbar</li>\n       *     <li>**rightOriginal**: the amount of right padding currently on the element</li>\n       *     <li>**heightOverflow**: whether the the height is overflowing</li>\n       *     <li>**bottom**: the amount of bottom padding on the element needed to replace the scrollbar</li>\n       *     <li>**bottomOriginal**: the amount of bottom padding currently on the element</li>\n       *   </ul>\n       */\n      scrollbarPadding: function(elem) {\n        elem = this.getRawNode(elem);\n\n        var elemStyle = $window.getComputedStyle(elem);\n        var paddingRight = this.parseStyle(elemStyle.paddingRight);\n        var paddingBottom = this.parseStyle(elemStyle.paddingBottom);\n        var scrollParent = this.scrollParent(elem, false, true);\n        var scrollbarWidth = this.scrollbarWidth(BODY_REGEX.test(scrollParent.tagName));\n\n        return {\n          scrollbarWidth: scrollbarWidth,\n          widthOverflow: scrollParent.scrollWidth > scrollParent.clientWidth,\n          right: paddingRight + scrollbarWidth,\n          originalRight: paddingRight,\n          heightOverflow: scrollParent.scrollHeight > scrollParent.clientHeight,\n          bottom: paddingBottom + scrollbarWidth,\n          originalBottom: paddingBottom\n         };\n      },\n\n      /**\n       * Checks to see if the element is scrollable.\n       *\n       * @param {element} elem - The element to check.\n       * @param {boolean=} [includeHidden=false] - Should scroll style of 'hidden' be considered,\n       *   default is false.\n       *\n       * @returns {boolean} Whether the element is scrollable.\n       */\n      isScrollable: function(elem, includeHidden) {\n        elem = this.getRawNode(elem);\n\n        var overflowRegex = includeHidden ? OVERFLOW_REGEX.hidden : OVERFLOW_REGEX.normal;\n        var elemStyle = $window.getComputedStyle(elem);\n        return overflowRegex.test(elemStyle.overflow + elemStyle.overflowY + elemStyle.overflowX);\n      },\n\n      /**\n       * Provides the closest scrollable ancestor.\n       * A port of the jQuery UI scrollParent method:\n       * https://github.com/jquery/jquery-ui/blob/master/ui/scroll-parent.js\n       *\n       * @param {element} elem - The element to find the scroll parent of.\n       * @param {boolean=} [includeHidden=false] - Should scroll style of 'hidden' be considered,\n       *   default is false.\n       * @param {boolean=} [includeSelf=false] - Should the element being passed be\n       * included in the scrollable llokup.\n       *\n       * @returns {element} A HTML element.\n       */\n      scrollParent: function(elem, includeHidden, includeSelf) {\n        elem = this.getRawNode(elem);\n\n        var overflowRegex = includeHidden ? OVERFLOW_REGEX.hidden : OVERFLOW_REGEX.normal;\n        var documentEl = $document[0].documentElement;\n        var elemStyle = $window.getComputedStyle(elem);\n        if (includeSelf && overflowRegex.test(elemStyle.overflow + elemStyle.overflowY + elemStyle.overflowX)) {\n          return elem;\n        }\n        var excludeStatic = elemStyle.position === 'absolute';\n        var scrollParent = elem.parentElement || documentEl;\n\n        if (scrollParent === documentEl || elemStyle.position === 'fixed') {\n          return documentEl;\n        }\n\n        while (scrollParent.parentElement && scrollParent !== documentEl) {\n          var spStyle = $window.getComputedStyle(scrollParent);\n          if (excludeStatic && spStyle.position !== 'static') {\n            excludeStatic = false;\n          }\n\n          if (!excludeStatic && overflowRegex.test(spStyle.overflow + spStyle.overflowY + spStyle.overflowX)) {\n            break;\n          }\n          scrollParent = scrollParent.parentElement;\n        }\n\n        return scrollParent;\n      },\n\n      /**\n       * Provides read-only equivalent of jQuery's position function:\n       * http://api.jquery.com/position/ - distance to closest positioned\n       * ancestor.  Does not account for margins by default like jQuery position.\n       *\n       * @param {element} elem - The element to caclulate the position on.\n       * @param {boolean=} [includeMargins=false] - Should margins be accounted\n       * for, default is false.\n       *\n       * @returns {object} An object with the following properties:\n       *   <ul>\n       *     <li>**width**: the width of the element</li>\n       *     <li>**height**: the height of the element</li>\n       *     <li>**top**: distance to top edge of offset parent</li>\n       *     <li>**left**: distance to left edge of offset parent</li>\n       *   </ul>\n       */\n      position: function(elem, includeMagins) {\n        elem = this.getRawNode(elem);\n\n        var elemOffset = this.offset(elem);\n        if (includeMagins) {\n          var elemStyle = $window.getComputedStyle(elem);\n          elemOffset.top -= this.parseStyle(elemStyle.marginTop);\n          elemOffset.left -= this.parseStyle(elemStyle.marginLeft);\n        }\n        var parent = this.offsetParent(elem);\n        var parentOffset = {top: 0, left: 0};\n\n        if (parent !== $document[0].documentElement) {\n          parentOffset = this.offset(parent);\n          parentOffset.top += parent.clientTop - parent.scrollTop;\n          parentOffset.left += parent.clientLeft - parent.scrollLeft;\n        }\n\n        return {\n          width: Math.round(angular.isNumber(elemOffset.width) ? elemOffset.width : elem.offsetWidth),\n          height: Math.round(angular.isNumber(elemOffset.height) ? elemOffset.height : elem.offsetHeight),\n          top: Math.round(elemOffset.top - parentOffset.top),\n          left: Math.round(elemOffset.left - parentOffset.left)\n        };\n      },\n\n      /**\n       * Provides read-only equivalent of jQuery's offset function:\n       * http://api.jquery.com/offset/ - distance to viewport.  Does\n       * not account for borders, margins, or padding on the body\n       * element.\n       *\n       * @param {element} elem - The element to calculate the offset on.\n       *\n       * @returns {object} An object with the following properties:\n       *   <ul>\n       *     <li>**width**: the width of the element</li>\n       *     <li>**height**: the height of the element</li>\n       *     <li>**top**: distance to top edge of viewport</li>\n       *     <li>**right**: distance to bottom edge of viewport</li>\n       *   </ul>\n       */\n      offset: function(elem) {\n        elem = this.getRawNode(elem);\n\n        var elemBCR = elem.getBoundingClientRect();\n        return {\n          width: Math.round(angular.isNumber(elemBCR.width) ? elemBCR.width : elem.offsetWidth),\n          height: Math.round(angular.isNumber(elemBCR.height) ? elemBCR.height : elem.offsetHeight),\n          top: Math.round(elemBCR.top + ($window.pageYOffset || $document[0].documentElement.scrollTop)),\n          left: Math.round(elemBCR.left + ($window.pageXOffset || $document[0].documentElement.scrollLeft))\n        };\n      },\n\n      /**\n       * Provides offset distance to the closest scrollable ancestor\n       * or viewport.  Accounts for border and scrollbar width.\n       *\n       * Right and bottom dimensions represent the distance to the\n       * respective edge of the viewport element.  If the element\n       * edge extends beyond the viewport, a negative value will be\n       * reported.\n       *\n       * @param {element} elem - The element to get the viewport offset for.\n       * @param {boolean=} [useDocument=false] - Should the viewport be the document element instead\n       * of the first scrollable element, default is false.\n       * @param {boolean=} [includePadding=true] - Should the padding on the offset parent element\n       * be accounted for, default is true.\n       *\n       * @returns {object} An object with the following properties:\n       *   <ul>\n       *     <li>**top**: distance to the top content edge of viewport element</li>\n       *     <li>**bottom**: distance to the bottom content edge of viewport element</li>\n       *     <li>**left**: distance to the left content edge of viewport element</li>\n       *     <li>**right**: distance to the right content edge of viewport element</li>\n       *   </ul>\n       */\n      viewportOffset: function(elem, useDocument, includePadding) {\n        elem = this.getRawNode(elem);\n        includePadding = includePadding !== false ? true : false;\n\n        var elemBCR = elem.getBoundingClientRect();\n        var offsetBCR = {top: 0, left: 0, bottom: 0, right: 0};\n\n        var offsetParent = useDocument ? $document[0].documentElement : this.scrollParent(elem);\n        var offsetParentBCR = offsetParent.getBoundingClientRect();\n\n        offsetBCR.top = offsetParentBCR.top + offsetParent.clientTop;\n        offsetBCR.left = offsetParentBCR.left + offsetParent.clientLeft;\n        if (offsetParent === $document[0].documentElement) {\n          offsetBCR.top += $window.pageYOffset;\n          offsetBCR.left += $window.pageXOffset;\n        }\n        offsetBCR.bottom = offsetBCR.top + offsetParent.clientHeight;\n        offsetBCR.right = offsetBCR.left + offsetParent.clientWidth;\n\n        if (includePadding) {\n          var offsetParentStyle = $window.getComputedStyle(offsetParent);\n          offsetBCR.top += this.parseStyle(offsetParentStyle.paddingTop);\n          offsetBCR.bottom -= this.parseStyle(offsetParentStyle.paddingBottom);\n          offsetBCR.left += this.parseStyle(offsetParentStyle.paddingLeft);\n          offsetBCR.right -= this.parseStyle(offsetParentStyle.paddingRight);\n        }\n\n        return {\n          top: Math.round(elemBCR.top - offsetBCR.top),\n          bottom: Math.round(offsetBCR.bottom - elemBCR.bottom),\n          left: Math.round(elemBCR.left - offsetBCR.left),\n          right: Math.round(offsetBCR.right - elemBCR.right)\n        };\n      },\n\n      /**\n       * Provides an array of placement values parsed from a placement string.\n       * Along with the 'auto' indicator, supported placement strings are:\n       *   <ul>\n       *     <li>top: element on top, horizontally centered on host element.</li>\n       *     <li>top-left: element on top, left edge aligned with host element left edge.</li>\n       *     <li>top-right: element on top, lerightft edge aligned with host element right edge.</li>\n       *     <li>bottom: element on bottom, horizontally centered on host element.</li>\n       *     <li>bottom-left: element on bottom, left edge aligned with host element left edge.</li>\n       *     <li>bottom-right: element on bottom, right edge aligned with host element right edge.</li>\n       *     <li>left: element on left, vertically centered on host element.</li>\n       *     <li>left-top: element on left, top edge aligned with host element top edge.</li>\n       *     <li>left-bottom: element on left, bottom edge aligned with host element bottom edge.</li>\n       *     <li>right: element on right, vertically centered on host element.</li>\n       *     <li>right-top: element on right, top edge aligned with host element top edge.</li>\n       *     <li>right-bottom: element on right, bottom edge aligned with host element bottom edge.</li>\n       *   </ul>\n       * A placement string with an 'auto' indicator is expected to be\n       * space separated from the placement, i.e: 'auto bottom-left'  If\n       * the primary and secondary placement values do not match 'top,\n       * bottom, left, right' then 'top' will be the primary placement and\n       * 'center' will be the secondary placement.  If 'auto' is passed, true\n       * will be returned as the 3rd value of the array.\n       *\n       * @param {string} placement - The placement string to parse.\n       *\n       * @returns {array} An array with the following values\n       * <ul>\n       *   <li>**[0]**: The primary placement.</li>\n       *   <li>**[1]**: The secondary placement.</li>\n       *   <li>**[2]**: If auto is passed: true, else undefined.</li>\n       * </ul>\n       */\n      parsePlacement: function(placement) {\n        var autoPlace = PLACEMENT_REGEX.auto.test(placement);\n        if (autoPlace) {\n          placement = placement.replace(PLACEMENT_REGEX.auto, '');\n        }\n\n        placement = placement.split('-');\n\n        placement[0] = placement[0] || 'top';\n        if (!PLACEMENT_REGEX.primary.test(placement[0])) {\n          placement[0] = 'top';\n        }\n\n        placement[1] = placement[1] || 'center';\n        if (!PLACEMENT_REGEX.secondary.test(placement[1])) {\n          placement[1] = 'center';\n        }\n\n        if (autoPlace) {\n          placement[2] = true;\n        } else {\n          placement[2] = false;\n        }\n\n        return placement;\n      },\n\n      /**\n       * Provides coordinates for an element to be positioned relative to\n       * another element.  Passing 'auto' as part of the placement parameter\n       * will enable smart placement - where the element fits. i.e:\n       * 'auto left-top' will check to see if there is enough space to the left\n       * of the hostElem to fit the targetElem, if not place right (same for secondary\n       * top placement).  Available space is calculated using the viewportOffset\n       * function.\n       *\n       * @param {element} hostElem - The element to position against.\n       * @param {element} targetElem - The element to position.\n       * @param {string=} [placement=top] - The placement for the targetElem,\n       *   default is 'top'. 'center' is assumed as secondary placement for\n       *   'top', 'left', 'right', and 'bottom' placements.  Available placements are:\n       *   <ul>\n       *     <li>top</li>\n       *     <li>top-right</li>\n       *     <li>top-left</li>\n       *     <li>bottom</li>\n       *     <li>bottom-left</li>\n       *     <li>bottom-right</li>\n       *     <li>left</li>\n       *     <li>left-top</li>\n       *     <li>left-bottom</li>\n       *     <li>right</li>\n       *     <li>right-top</li>\n       *     <li>right-bottom</li>\n       *   </ul>\n       * @param {boolean=} [appendToBody=false] - Should the top and left values returned\n       *   be calculated from the body element, default is false.\n       *\n       * @returns {object} An object with the following properties:\n       *   <ul>\n       *     <li>**top**: Value for targetElem top.</li>\n       *     <li>**left**: Value for targetElem left.</li>\n       *     <li>**placement**: The resolved placement.</li>\n       *   </ul>\n       */\n      positionElements: function(hostElem, targetElem, placement, appendToBody) {\n        hostElem = this.getRawNode(hostElem);\n        targetElem = this.getRawNode(targetElem);\n\n        // need to read from prop to support tests.\n        var targetWidth = angular.isDefined(targetElem.offsetWidth) ? targetElem.offsetWidth : targetElem.prop('offsetWidth');\n        var targetHeight = angular.isDefined(targetElem.offsetHeight) ? targetElem.offsetHeight : targetElem.prop('offsetHeight');\n\n        placement = this.parsePlacement(placement);\n\n        var hostElemPos = appendToBody ? this.offset(hostElem) : this.position(hostElem);\n        var targetElemPos = {top: 0, left: 0, placement: ''};\n\n        if (placement[2]) {\n          var viewportOffset = this.viewportOffset(hostElem, appendToBody);\n\n          var targetElemStyle = $window.getComputedStyle(targetElem);\n          var adjustedSize = {\n            width: targetWidth + Math.round(Math.abs(this.parseStyle(targetElemStyle.marginLeft) + this.parseStyle(targetElemStyle.marginRight))),\n            height: targetHeight + Math.round(Math.abs(this.parseStyle(targetElemStyle.marginTop) + this.parseStyle(targetElemStyle.marginBottom)))\n          };\n\n          placement[0] = placement[0] === 'top' && adjustedSize.height > viewportOffset.top && adjustedSize.height <= viewportOffset.bottom ? 'bottom' :\n                         placement[0] === 'bottom' && adjustedSize.height > viewportOffset.bottom && adjustedSize.height <= viewportOffset.top ? 'top' :\n                         placement[0] === 'left' && adjustedSize.width > viewportOffset.left && adjustedSize.width <= viewportOffset.right ? 'right' :\n                         placement[0] === 'right' && adjustedSize.width > viewportOffset.right && adjustedSize.width <= viewportOffset.left ? 'left' :\n                         placement[0];\n\n          placement[1] = placement[1] === 'top' && adjustedSize.height - hostElemPos.height > viewportOffset.bottom && adjustedSize.height - hostElemPos.height <= viewportOffset.top ? 'bottom' :\n                         placement[1] === 'bottom' && adjustedSize.height - hostElemPos.height > viewportOffset.top && adjustedSize.height - hostElemPos.height <= viewportOffset.bottom ? 'top' :\n                         placement[1] === 'left' && adjustedSize.width - hostElemPos.width > viewportOffset.right && adjustedSize.width - hostElemPos.width <= viewportOffset.left ? 'right' :\n                         placement[1] === 'right' && adjustedSize.width - hostElemPos.width > viewportOffset.left && adjustedSize.width - hostElemPos.width <= viewportOffset.right ? 'left' :\n                         placement[1];\n\n          if (placement[1] === 'center') {\n            if (PLACEMENT_REGEX.vertical.test(placement[0])) {\n              var xOverflow = hostElemPos.width / 2 - targetWidth / 2;\n              if (viewportOffset.left + xOverflow < 0 && adjustedSize.width - hostElemPos.width <= viewportOffset.right) {\n                placement[1] = 'left';\n              } else if (viewportOffset.right + xOverflow < 0 && adjustedSize.width - hostElemPos.width <= viewportOffset.left) {\n                placement[1] = 'right';\n              }\n            } else {\n              var yOverflow = hostElemPos.height / 2 - adjustedSize.height / 2;\n              if (viewportOffset.top + yOverflow < 0 && adjustedSize.height - hostElemPos.height <= viewportOffset.bottom) {\n                placement[1] = 'top';\n              } else if (viewportOffset.bottom + yOverflow < 0 && adjustedSize.height - hostElemPos.height <= viewportOffset.top) {\n                placement[1] = 'bottom';\n              }\n            }\n          }\n        }\n\n        switch (placement[0]) {\n          case 'top':\n            targetElemPos.top = hostElemPos.top - targetHeight;\n            break;\n          case 'bottom':\n            targetElemPos.top = hostElemPos.top + hostElemPos.height;\n            break;\n          case 'left':\n            targetElemPos.left = hostElemPos.left - targetWidth;\n            break;\n          case 'right':\n            targetElemPos.left = hostElemPos.left + hostElemPos.width;\n            break;\n        }\n\n        switch (placement[1]) {\n          case 'top':\n            targetElemPos.top = hostElemPos.top;\n            break;\n          case 'bottom':\n            targetElemPos.top = hostElemPos.top + hostElemPos.height - targetHeight;\n            break;\n          case 'left':\n            targetElemPos.left = hostElemPos.left;\n            break;\n          case 'right':\n            targetElemPos.left = hostElemPos.left + hostElemPos.width - targetWidth;\n            break;\n          case 'center':\n            if (PLACEMENT_REGEX.vertical.test(placement[0])) {\n              targetElemPos.left = hostElemPos.left + hostElemPos.width / 2 - targetWidth / 2;\n            } else {\n              targetElemPos.top = hostElemPos.top + hostElemPos.height / 2 - targetHeight / 2;\n            }\n            break;\n        }\n\n        targetElemPos.top = Math.round(targetElemPos.top);\n        targetElemPos.left = Math.round(targetElemPos.left);\n        targetElemPos.placement = placement[1] === 'center' ? placement[0] : placement[0] + '-' + placement[1];\n\n        return targetElemPos;\n      },\n\n      /**\n       * Provides a way to adjust the top positioning after first\n       * render to correctly align element to top after content\n       * rendering causes resized element height\n       *\n       * @param {array} placementClasses - The array of strings of classes\n       * element should have.\n       * @param {object} containerPosition - The object with container\n       * position information\n       * @param {number} initialHeight - The initial height for the elem.\n       * @param {number} currentHeight - The current height for the elem.\n       */\n      adjustTop: function(placementClasses, containerPosition, initialHeight, currentHeight) {\n        if (placementClasses.indexOf('top') !== -1 && initialHeight !== currentHeight) {\n          return {\n            top: containerPosition.top - currentHeight + 'px'\n          };\n        }\n      },\n\n      /**\n       * Provides a way for positioning tooltip & dropdown\n       * arrows when using placement options beyond the standard\n       * left, right, top, or bottom.\n       *\n       * @param {element} elem - The tooltip/dropdown element.\n       * @param {string} placement - The placement for the elem.\n       */\n      positionArrow: function(elem, placement) {\n        elem = this.getRawNode(elem);\n\n        var innerElem = elem.querySelector('.tooltip-inner, .popover-inner');\n        if (!innerElem) {\n          return;\n        }\n\n        var isTooltip = angular.element(innerElem).hasClass('tooltip-inner');\n\n        var arrowElem = isTooltip ? elem.querySelector('.tooltip-arrow') : elem.querySelector('.arrow');\n        if (!arrowElem) {\n          return;\n        }\n\n        var arrowCss = {\n          top: '',\n          bottom: '',\n          left: '',\n          right: ''\n        };\n\n        placement = this.parsePlacement(placement);\n        if (placement[1] === 'center') {\n          // no adjustment necessary - just reset styles\n          angular.element(arrowElem).css(arrowCss);\n          return;\n        }\n\n        var borderProp = 'border-' + placement[0] + '-width';\n        var borderWidth = $window.getComputedStyle(arrowElem)[borderProp];\n\n        var borderRadiusProp = 'border-';\n        if (PLACEMENT_REGEX.vertical.test(placement[0])) {\n          borderRadiusProp += placement[0] + '-' + placement[1];\n        } else {\n          borderRadiusProp += placement[1] + '-' + placement[0];\n        }\n        borderRadiusProp += '-radius';\n        var borderRadius = $window.getComputedStyle(isTooltip ? innerElem : elem)[borderRadiusProp];\n\n        switch (placement[0]) {\n          case 'top':\n            arrowCss.bottom = isTooltip ? '0' : '-' + borderWidth;\n            break;\n          case 'bottom':\n            arrowCss.top = isTooltip ? '0' : '-' + borderWidth;\n            break;\n          case 'left':\n            arrowCss.right = isTooltip ? '0' : '-' + borderWidth;\n            break;\n          case 'right':\n            arrowCss.left = isTooltip ? '0' : '-' + borderWidth;\n            break;\n        }\n\n        arrowCss[placement[1]] = borderRadius;\n\n        angular.element(arrowElem).css(arrowCss);\n      }\n    };\n  }]);\n\nangular.module('ui.bootstrap.datepickerPopup', ['ui.bootstrap.datepicker', 'ui.bootstrap.position'])\n\n.value('$datepickerPopupLiteralWarning', true)\n\n.constant('uibDatepickerPopupConfig', {\n  altInputFormats: [],\n  appendToBody: false,\n  clearText: 'Clear',\n  closeOnDateSelection: true,\n  closeText: 'Done',\n  currentText: 'Today',\n  datepickerPopup: 'yyyy-MM-dd',\n  datepickerPopupTemplateUrl: 'uib/template/datepickerPopup/popup.html',\n  datepickerTemplateUrl: 'uib/template/datepicker/datepicker.html',\n  html5Types: {\n    date: 'yyyy-MM-dd',\n    'datetime-local': 'yyyy-MM-ddTHH:mm:ss.sss',\n    'month': 'yyyy-MM'\n  },\n  onOpenFocus: true,\n  showButtonBar: true,\n  placement: 'auto bottom-left'\n})\n\n.controller('UibDatepickerPopupController', ['$scope', '$element', '$attrs', '$compile', '$log', '$parse', '$window', '$document', '$rootScope', '$uibPosition', 'dateFilter', 'uibDateParser', 'uibDatepickerPopupConfig', '$timeout', 'uibDatepickerConfig', '$datepickerPopupLiteralWarning',\nfunction($scope, $element, $attrs, $compile, $log, $parse, $window, $document, $rootScope, $position, dateFilter, dateParser, datepickerPopupConfig, $timeout, datepickerConfig, $datepickerPopupLiteralWarning) {\n  var cache = {},\n    isHtml5DateInput = false;\n  var dateFormat, closeOnDateSelection, appendToBody, onOpenFocus,\n    datepickerPopupTemplateUrl, datepickerTemplateUrl, popupEl, datepickerEl, scrollParentEl,\n    ngModel, ngModelOptions, $popup, altInputFormats, watchListeners = [];\n\n  this.init = function(_ngModel_) {\n    ngModel = _ngModel_;\n    ngModelOptions = extractOptions(ngModel);\n    closeOnDateSelection = angular.isDefined($attrs.closeOnDateSelection) ?\n      $scope.$parent.$eval($attrs.closeOnDateSelection) :\n      datepickerPopupConfig.closeOnDateSelection;\n    appendToBody = angular.isDefined($attrs.datepickerAppendToBody) ?\n      $scope.$parent.$eval($attrs.datepickerAppendToBody) :\n      datepickerPopupConfig.appendToBody;\n    onOpenFocus = angular.isDefined($attrs.onOpenFocus) ?\n      $scope.$parent.$eval($attrs.onOpenFocus) : datepickerPopupConfig.onOpenFocus;\n    datepickerPopupTemplateUrl = angular.isDefined($attrs.datepickerPopupTemplateUrl) ?\n      $attrs.datepickerPopupTemplateUrl :\n      datepickerPopupConfig.datepickerPopupTemplateUrl;\n    datepickerTemplateUrl = angular.isDefined($attrs.datepickerTemplateUrl) ?\n      $attrs.datepickerTemplateUrl : datepickerPopupConfig.datepickerTemplateUrl;\n    altInputFormats = angular.isDefined($attrs.altInputFormats) ?\n      $scope.$parent.$eval($attrs.altInputFormats) :\n      datepickerPopupConfig.altInputFormats;\n\n    $scope.showButtonBar = angular.isDefined($attrs.showButtonBar) ?\n      $scope.$parent.$eval($attrs.showButtonBar) :\n      datepickerPopupConfig.showButtonBar;\n\n    if (datepickerPopupConfig.html5Types[$attrs.type]) {\n      dateFormat = datepickerPopupConfig.html5Types[$attrs.type];\n      isHtml5DateInput = true;\n    } else {\n      dateFormat = $attrs.uibDatepickerPopup || datepickerPopupConfig.datepickerPopup;\n      $attrs.$observe('uibDatepickerPopup', function(value, oldValue) {\n        var newDateFormat = value || datepickerPopupConfig.datepickerPopup;\n        // Invalidate the $modelValue to ensure that formatters re-run\n        // FIXME: Refactor when PR is merged: https://github.com/angular/angular.js/pull/10764\n        if (newDateFormat !== dateFormat) {\n          dateFormat = newDateFormat;\n          ngModel.$modelValue = null;\n\n          if (!dateFormat) {\n            throw new Error('uibDatepickerPopup must have a date format specified.');\n          }\n        }\n      });\n    }\n\n    if (!dateFormat) {\n      throw new Error('uibDatepickerPopup must have a date format specified.');\n    }\n\n    if (isHtml5DateInput && $attrs.uibDatepickerPopup) {\n      throw new Error('HTML5 date input types do not support custom formats.');\n    }\n\n    // popup element used to display calendar\n    popupEl = angular.element('<div uib-datepicker-popup-wrap><div uib-datepicker></div></div>');\n\n    popupEl.attr({\n      'ng-model': 'date',\n      'ng-change': 'dateSelection(date)',\n      'template-url': datepickerPopupTemplateUrl\n    });\n\n    // datepicker element\n    datepickerEl = angular.element(popupEl.children()[0]);\n    datepickerEl.attr('template-url', datepickerTemplateUrl);\n\n    if (!$scope.datepickerOptions) {\n      $scope.datepickerOptions = {};\n    }\n\n    if (isHtml5DateInput) {\n      if ($attrs.type === 'month') {\n        $scope.datepickerOptions.datepickerMode = 'month';\n        $scope.datepickerOptions.minMode = 'month';\n      }\n    }\n\n    datepickerEl.attr('datepicker-options', 'datepickerOptions');\n\n    if (!isHtml5DateInput) {\n      // Internal API to maintain the correct ng-invalid-[key] class\n      ngModel.$$parserName = 'date';\n      ngModel.$validators.date = validator;\n      ngModel.$parsers.unshift(parseDate);\n      ngModel.$formatters.push(function(value) {\n        if (ngModel.$isEmpty(value)) {\n          $scope.date = value;\n          return value;\n        }\n\n        if (angular.isNumber(value)) {\n          value = new Date(value);\n        }\n\n        $scope.date = dateParser.fromTimezone(value, ngModelOptions.getOption('timezone'));\n\n        return dateParser.filter($scope.date, dateFormat);\n      });\n    } else {\n      ngModel.$formatters.push(function(value) {\n        $scope.date = dateParser.fromTimezone(value, ngModelOptions.getOption('timezone'));\n        return value;\n      });\n    }\n\n    // Detect changes in the view from the text box\n    ngModel.$viewChangeListeners.push(function() {\n      $scope.date = parseDateString(ngModel.$viewValue);\n    });\n\n    $element.on('keydown', inputKeydownBind);\n\n    $popup = $compile(popupEl)($scope);\n    // Prevent jQuery cache memory leak (template is now redundant after linking)\n    popupEl.remove();\n\n    if (appendToBody) {\n      $document.find('body').append($popup);\n    } else {\n      $element.after($popup);\n    }\n\n    $scope.$on('$destroy', function() {\n      if ($scope.isOpen === true) {\n        if (!$rootScope.$$phase) {\n          $scope.$apply(function() {\n            $scope.isOpen = false;\n          });\n        }\n      }\n\n      $popup.remove();\n      $element.off('keydown', inputKeydownBind);\n      $document.off('click', documentClickBind);\n      if (scrollParentEl) {\n        scrollParentEl.off('scroll', positionPopup);\n      }\n      angular.element($window).off('resize', positionPopup);\n\n      //Clear all watch listeners on destroy\n      while (watchListeners.length) {\n        watchListeners.shift()();\n      }\n    });\n  };\n\n  $scope.getText = function(key) {\n    return $scope[key + 'Text'] || datepickerPopupConfig[key + 'Text'];\n  };\n\n  $scope.isDisabled = function(date) {\n    if (date === 'today') {\n      date = dateParser.fromTimezone(new Date(), ngModelOptions.getOption('timezone'));\n    }\n\n    var dates = {};\n    angular.forEach(['minDate', 'maxDate'], function(key) {\n      if (!$scope.datepickerOptions[key]) {\n        dates[key] = null;\n      } else if (angular.isDate($scope.datepickerOptions[key])) {\n        dates[key] = new Date($scope.datepickerOptions[key]);\n      } else {\n        if ($datepickerPopupLiteralWarning) {\n          $log.warn('Literal date support has been deprecated, please switch to date object usage');\n        }\n\n        dates[key] = new Date(dateFilter($scope.datepickerOptions[key], 'medium'));\n      }\n    });\n\n    return $scope.datepickerOptions &&\n      dates.minDate && $scope.compare(date, dates.minDate) < 0 ||\n      dates.maxDate && $scope.compare(date, dates.maxDate) > 0;\n  };\n\n  $scope.compare = function(date1, date2) {\n    return new Date(date1.getFullYear(), date1.getMonth(), date1.getDate()) - new Date(date2.getFullYear(), date2.getMonth(), date2.getDate());\n  };\n\n  // Inner change\n  $scope.dateSelection = function(dt) {\n    $scope.date = dt;\n    var date = $scope.date ? dateParser.filter($scope.date, dateFormat) : null; // Setting to NULL is necessary for form validators to function\n    $element.val(date);\n    ngModel.$setViewValue(date);\n\n    if (closeOnDateSelection) {\n      $scope.isOpen = false;\n      $element[0].focus();\n    }\n  };\n\n  $scope.keydown = function(evt) {\n    if (evt.which === 27) {\n      evt.stopPropagation();\n      $scope.isOpen = false;\n      $element[0].focus();\n    }\n  };\n\n  $scope.select = function(date, evt) {\n    evt.stopPropagation();\n\n    if (date === 'today') {\n      var today = new Date();\n      if (angular.isDate($scope.date)) {\n        date = new Date($scope.date);\n        date.setFullYear(today.getFullYear(), today.getMonth(), today.getDate());\n      } else {\n        date = dateParser.fromTimezone(today, ngModelOptions.getOption('timezone'));\n        date.setHours(0, 0, 0, 0);\n      }\n    }\n    $scope.dateSelection(date);\n  };\n\n  $scope.close = function(evt) {\n    evt.stopPropagation();\n\n    $scope.isOpen = false;\n    $element[0].focus();\n  };\n\n  $scope.disabled = angular.isDefined($attrs.disabled) || false;\n  if ($attrs.ngDisabled) {\n    watchListeners.push($scope.$parent.$watch($parse($attrs.ngDisabled), function(disabled) {\n      $scope.disabled = disabled;\n    }));\n  }\n\n  $scope.$watch('isOpen', function(value) {\n    if (value) {\n      if (!$scope.disabled) {\n        $timeout(function() {\n          positionPopup();\n\n          if (onOpenFocus) {\n            $scope.$broadcast('uib:datepicker.focus');\n          }\n\n          $document.on('click', documentClickBind);\n\n          var placement = $attrs.popupPlacement ? $attrs.popupPlacement : datepickerPopupConfig.placement;\n          if (appendToBody || $position.parsePlacement(placement)[2]) {\n            scrollParentEl = scrollParentEl || angular.element($position.scrollParent($element));\n            if (scrollParentEl) {\n              scrollParentEl.on('scroll', positionPopup);\n            }\n          } else {\n            scrollParentEl = null;\n          }\n\n          angular.element($window).on('resize', positionPopup);\n        }, 0, false);\n      } else {\n        $scope.isOpen = false;\n      }\n    } else {\n      $document.off('click', documentClickBind);\n      if (scrollParentEl) {\n        scrollParentEl.off('scroll', positionPopup);\n      }\n      angular.element($window).off('resize', positionPopup);\n    }\n  });\n\n  function cameltoDash(string) {\n    return string.replace(/([A-Z])/g, function($1) { return '-' + $1.toLowerCase(); });\n  }\n\n  function parseDateString(viewValue) {\n    var date = dateParser.parse(viewValue, dateFormat, $scope.date);\n    if (isNaN(date)) {\n      for (var i = 0; i < altInputFormats.length; i++) {\n        date = dateParser.parse(viewValue, altInputFormats[i], $scope.date);\n        if (!isNaN(date)) {\n          return date;\n        }\n      }\n    }\n    return date;\n  }\n\n  function parseDate(viewValue) {\n    if (angular.isNumber(viewValue)) {\n      // presumably timestamp to date object\n      viewValue = new Date(viewValue);\n    }\n\n    if (!viewValue) {\n      return null;\n    }\n\n    if (angular.isDate(viewValue) && !isNaN(viewValue)) {\n      return viewValue;\n    }\n\n    if (angular.isString(viewValue)) {\n      var date = parseDateString(viewValue);\n      if (!isNaN(date)) {\n        return dateParser.toTimezone(date, ngModelOptions.getOption('timezone'));\n      }\n    }\n\n    return ngModelOptions.getOption('allowInvalid') ? viewValue : undefined;\n  }\n\n  function validator(modelValue, viewValue) {\n    var value = modelValue || viewValue;\n\n    if (!$attrs.ngRequired && !value) {\n      return true;\n    }\n\n    if (angular.isNumber(value)) {\n      value = new Date(value);\n    }\n\n    if (!value) {\n      return true;\n    }\n\n    if (angular.isDate(value) && !isNaN(value)) {\n      return true;\n    }\n\n    if (angular.isString(value)) {\n      return !isNaN(parseDateString(value));\n    }\n\n    return false;\n  }\n\n  function documentClickBind(event) {\n    if (!$scope.isOpen && $scope.disabled) {\n      return;\n    }\n\n    var popup = $popup[0];\n    var dpContainsTarget = $element[0].contains(event.target);\n    // The popup node may not be an element node\n    // In some browsers (IE) only element nodes have the 'contains' function\n    var popupContainsTarget = popup.contains !== undefined && popup.contains(event.target);\n    if ($scope.isOpen && !(dpContainsTarget || popupContainsTarget)) {\n      $scope.$apply(function() {\n        $scope.isOpen = false;\n      });\n    }\n  }\n\n  function inputKeydownBind(evt) {\n    if (evt.which === 27 && $scope.isOpen) {\n      evt.preventDefault();\n      evt.stopPropagation();\n      $scope.$apply(function() {\n        $scope.isOpen = false;\n      });\n      $element[0].focus();\n    } else if (evt.which === 40 && !$scope.isOpen) {\n      evt.preventDefault();\n      evt.stopPropagation();\n      $scope.$apply(function() {\n        $scope.isOpen = true;\n      });\n    }\n  }\n\n  function positionPopup() {\n    if ($scope.isOpen) {\n      var dpElement = angular.element($popup[0].querySelector('.uib-datepicker-popup'));\n      var placement = $attrs.popupPlacement ? $attrs.popupPlacement : datepickerPopupConfig.placement;\n      var position = $position.positionElements($element, dpElement, placement, appendToBody);\n      dpElement.css({top: position.top + 'px', left: position.left + 'px'});\n      if (dpElement.hasClass('uib-position-measure')) {\n        dpElement.removeClass('uib-position-measure');\n      }\n    }\n  }\n\n  function extractOptions(ngModelCtrl) {\n    var ngModelOptions;\n\n    if (angular.version.minor < 6) { // in angular < 1.6 $options could be missing\n      // guarantee a value\n      ngModelOptions = angular.isObject(ngModelCtrl.$options) ?\n        ngModelCtrl.$options :\n        {\n          timezone: null\n        };\n\n      // mimic 1.6+ api\n      ngModelOptions.getOption = function (key) {\n        return ngModelOptions[key];\n      };\n    } else { // in angular >=1.6 $options is always present\n      ngModelOptions = ngModelCtrl.$options;\n    }\n\n    return ngModelOptions;\n  }\n\n  $scope.$on('uib:datepicker.mode', function() {\n    $timeout(positionPopup, 0, false);\n  });\n}])\n\n.directive('uibDatepickerPopup', function() {\n  return {\n    require: ['ngModel', 'uibDatepickerPopup'],\n    controller: 'UibDatepickerPopupController',\n    scope: {\n      datepickerOptions: '=?',\n      isOpen: '=?',\n      currentText: '@',\n      clearText: '@',\n      closeText: '@'\n    },\n    link: function(scope, element, attrs, ctrls) {\n      var ngModel = ctrls[0],\n        ctrl = ctrls[1];\n\n      ctrl.init(ngModel);\n    }\n  };\n})\n\n.directive('uibDatepickerPopupWrap', function() {\n  return {\n    restrict: 'A',\n    transclude: true,\n    templateUrl: function(element, attrs) {\n      return attrs.templateUrl || 'uib/template/datepickerPopup/popup.html';\n    }\n  };\n});\n\nangular.module('ui.bootstrap.debounce', [])\n/**\n * A helper, internal service that debounces a function\n */\n  .factory('$$debounce', ['$timeout', function($timeout) {\n    return function(callback, debounceTime) {\n      var timeoutPromise;\n\n      return function() {\n        var self = this;\n        var args = Array.prototype.slice.call(arguments);\n        if (timeoutPromise) {\n          $timeout.cancel(timeoutPromise);\n        }\n\n        timeoutPromise = $timeout(function() {\n          callback.apply(self, args);\n        }, debounceTime);\n      };\n    };\n  }]);\n\nangular.module('ui.bootstrap.multiMap', [])\n/**\n * A helper, internal data structure that stores all references attached to key\n */\n  .factory('$$multiMap', function() {\n    return {\n      createNew: function() {\n        var map = {};\n\n        return {\n          entries: function() {\n            return Object.keys(map).map(function(key) {\n              return {\n                key: key,\n                value: map[key]\n              };\n            });\n          },\n          get: function(key) {\n            return map[key];\n          },\n          hasKey: function(key) {\n            return !!map[key];\n          },\n          keys: function() {\n            return Object.keys(map);\n          },\n          put: function(key, value) {\n            if (!map[key]) {\n              map[key] = [];\n            }\n\n            map[key].push(value);\n          },\n          remove: function(key, value) {\n            var values = map[key];\n\n            if (!values) {\n              return;\n            }\n\n            var idx = values.indexOf(value);\n\n            if (idx !== -1) {\n              values.splice(idx, 1);\n            }\n\n            if (!values.length) {\n              delete map[key];\n            }\n          }\n        };\n      }\n    };\n  });\n\nangular.module('ui.bootstrap.dropdown', ['ui.bootstrap.multiMap', 'ui.bootstrap.position'])\n\n.constant('uibDropdownConfig', {\n  appendToOpenClass: 'uib-dropdown-open',\n  openClass: 'open'\n})\n\n.service('uibDropdownService', ['$document', '$rootScope', '$$multiMap', function($document, $rootScope, $$multiMap) {\n  var openScope = null;\n  var openedContainers = $$multiMap.createNew();\n\n  this.isOnlyOpen = function(dropdownScope, appendTo) {\n    var openedDropdowns = openedContainers.get(appendTo);\n    if (openedDropdowns) {\n      var openDropdown = openedDropdowns.reduce(function(toClose, dropdown) {\n        if (dropdown.scope === dropdownScope) {\n          return dropdown;\n        }\n\n        return toClose;\n      }, {});\n      if (openDropdown) {\n        return openedDropdowns.length === 1;\n      }\n    }\n\n    return false;\n  };\n\n  this.open = function(dropdownScope, element, appendTo) {\n    if (!openScope) {\n      $document.on('click', closeDropdown);\n    }\n\n    if (openScope && openScope !== dropdownScope) {\n      openScope.isOpen = false;\n    }\n\n    openScope = dropdownScope;\n\n    if (!appendTo) {\n      return;\n    }\n\n    var openedDropdowns = openedContainers.get(appendTo);\n    if (openedDropdowns) {\n      var openedScopes = openedDropdowns.map(function(dropdown) {\n        return dropdown.scope;\n      });\n      if (openedScopes.indexOf(dropdownScope) === -1) {\n        openedContainers.put(appendTo, {\n          scope: dropdownScope\n        });\n      }\n    } else {\n      openedContainers.put(appendTo, {\n        scope: dropdownScope\n      });\n    }\n  };\n\n  this.close = function(dropdownScope, element, appendTo) {\n    if (openScope === dropdownScope) {\n      $document.off('click', closeDropdown);\n      $document.off('keydown', this.keybindFilter);\n      openScope = null;\n    }\n\n    if (!appendTo) {\n      return;\n    }\n\n    var openedDropdowns = openedContainers.get(appendTo);\n    if (openedDropdowns) {\n      var dropdownToClose = openedDropdowns.reduce(function(toClose, dropdown) {\n        if (dropdown.scope === dropdownScope) {\n          return dropdown;\n        }\n\n        return toClose;\n      }, {});\n      if (dropdownToClose) {\n        openedContainers.remove(appendTo, dropdownToClose);\n      }\n    }\n  };\n\n  var closeDropdown = function(evt) {\n    // This method may still be called during the same mouse event that\n    // unbound this event handler. So check openScope before proceeding.\n    if (!openScope || !openScope.isOpen) { return; }\n\n    if (evt && openScope.getAutoClose() === 'disabled') { return; }\n\n    if (evt && evt.which === 3) { return; }\n\n    var toggleElement = openScope.getToggleElement();\n    if (evt && toggleElement && toggleElement[0].contains(evt.target)) {\n      return;\n    }\n\n    var dropdownElement = openScope.getDropdownElement();\n    if (evt && openScope.getAutoClose() === 'outsideClick' &&\n      dropdownElement && dropdownElement[0].contains(evt.target)) {\n      return;\n    }\n\n    openScope.focusToggleElement();\n    openScope.isOpen = false;\n\n    if (!$rootScope.$$phase) {\n      openScope.$apply();\n    }\n  };\n\n  this.keybindFilter = function(evt) {\n    if (!openScope) {\n      // see this.close as ESC could have been pressed which kills the scope so we can not proceed\n      return;\n    }\n\n    var dropdownElement = openScope.getDropdownElement();\n    var toggleElement = openScope.getToggleElement();\n    var dropdownElementTargeted = dropdownElement && dropdownElement[0].contains(evt.target);\n    var toggleElementTargeted = toggleElement && toggleElement[0].contains(evt.target);\n    if (evt.which === 27) {\n      evt.stopPropagation();\n      openScope.focusToggleElement();\n      closeDropdown();\n    } else if (openScope.isKeynavEnabled() && [38, 40].indexOf(evt.which) !== -1 && openScope.isOpen && (dropdownElementTargeted || toggleElementTargeted)) {\n      evt.preventDefault();\n      evt.stopPropagation();\n      openScope.focusDropdownEntry(evt.which);\n    }\n  };\n}])\n\n.controller('UibDropdownController', ['$scope', '$element', '$attrs', '$parse', 'uibDropdownConfig', 'uibDropdownService', '$animate', '$uibPosition', '$document', '$compile', '$templateRequest', function($scope, $element, $attrs, $parse, dropdownConfig, uibDropdownService, $animate, $position, $document, $compile, $templateRequest) {\n  var self = this,\n    scope = $scope.$new(), // create a child scope so we are not polluting original one\n    templateScope,\n    appendToOpenClass = dropdownConfig.appendToOpenClass,\n    openClass = dropdownConfig.openClass,\n    getIsOpen,\n    setIsOpen = angular.noop,\n    toggleInvoker = $attrs.onToggle ? $parse($attrs.onToggle) : angular.noop,\n    keynavEnabled = false,\n    selectedOption = null,\n    body = $document.find('body');\n\n  $element.addClass('dropdown');\n\n  this.init = function() {\n    if ($attrs.isOpen) {\n      getIsOpen = $parse($attrs.isOpen);\n      setIsOpen = getIsOpen.assign;\n\n      $scope.$watch(getIsOpen, function(value) {\n        scope.isOpen = !!value;\n      });\n    }\n\n    keynavEnabled = angular.isDefined($attrs.keyboardNav);\n  };\n\n  this.toggle = function(open) {\n    scope.isOpen = arguments.length ? !!open : !scope.isOpen;\n    if (angular.isFunction(setIsOpen)) {\n      setIsOpen(scope, scope.isOpen);\n    }\n\n    return scope.isOpen;\n  };\n\n  // Allow other directives to watch status\n  this.isOpen = function() {\n    return scope.isOpen;\n  };\n\n  scope.getToggleElement = function() {\n    return self.toggleElement;\n  };\n\n  scope.getAutoClose = function() {\n    return $attrs.autoClose || 'always'; //or 'outsideClick' or 'disabled'\n  };\n\n  scope.getElement = function() {\n    return $element;\n  };\n\n  scope.isKeynavEnabled = function() {\n    return keynavEnabled;\n  };\n\n  scope.focusDropdownEntry = function(keyCode) {\n    var elems = self.dropdownMenu ? //If append to body is used.\n      angular.element(self.dropdownMenu).find('a') :\n      $element.find('ul').eq(0).find('a');\n\n    switch (keyCode) {\n      case 40: {\n        if (!angular.isNumber(self.selectedOption)) {\n          self.selectedOption = 0;\n        } else {\n          self.selectedOption = self.selectedOption === elems.length - 1 ?\n            self.selectedOption :\n            self.selectedOption + 1;\n        }\n        break;\n      }\n      case 38: {\n        if (!angular.isNumber(self.selectedOption)) {\n          self.selectedOption = elems.length - 1;\n        } else {\n          self.selectedOption = self.selectedOption === 0 ?\n            0 : self.selectedOption - 1;\n        }\n        break;\n      }\n    }\n    elems[self.selectedOption].focus();\n  };\n\n  scope.getDropdownElement = function() {\n    return self.dropdownMenu;\n  };\n\n  scope.focusToggleElement = function() {\n    if (self.toggleElement) {\n      self.toggleElement[0].focus();\n    }\n  };\n\n  function removeDropdownMenu() {\n    $element.append(self.dropdownMenu);\n  }\n\n  scope.$watch('isOpen', function(isOpen, wasOpen) {\n    var appendTo = null,\n      appendToBody = false;\n\n    if (angular.isDefined($attrs.dropdownAppendTo)) {\n      var appendToEl = $parse($attrs.dropdownAppendTo)(scope);\n      if (appendToEl) {\n        appendTo = angular.element(appendToEl);\n      }\n    }\n\n    if (angular.isDefined($attrs.dropdownAppendToBody)) {\n      var appendToBodyValue = $parse($attrs.dropdownAppendToBody)(scope);\n      if (appendToBodyValue !== false) {\n        appendToBody = true;\n      }\n    }\n\n    if (appendToBody && !appendTo) {\n      appendTo = body;\n    }\n\n    if (appendTo && self.dropdownMenu) {\n      if (isOpen) {\n        appendTo.append(self.dropdownMenu);\n        $element.on('$destroy', removeDropdownMenu);\n      } else {\n        $element.off('$destroy', removeDropdownMenu);\n        removeDropdownMenu();\n      }\n    }\n\n    if (appendTo && self.dropdownMenu) {\n      var pos = $position.positionElements($element, self.dropdownMenu, 'bottom-left', true),\n        css,\n        rightalign,\n        scrollbarPadding,\n        scrollbarWidth = 0;\n\n      css = {\n        top: pos.top + 'px',\n        display: isOpen ? 'block' : 'none'\n      };\n\n      rightalign = self.dropdownMenu.hasClass('dropdown-menu-right');\n      if (!rightalign) {\n        css.left = pos.left + 'px';\n        css.right = 'auto';\n      } else {\n        css.left = 'auto';\n        scrollbarPadding = $position.scrollbarPadding(appendTo);\n\n        if (scrollbarPadding.heightOverflow && scrollbarPadding.scrollbarWidth) {\n          scrollbarWidth = scrollbarPadding.scrollbarWidth;\n        }\n\n        css.right = window.innerWidth - scrollbarWidth -\n          (pos.left + $element.prop('offsetWidth')) + 'px';\n      }\n\n      // Need to adjust our positioning to be relative to the appendTo container\n      // if it's not the body element\n      if (!appendToBody) {\n        var appendOffset = $position.offset(appendTo);\n\n        css.top = pos.top - appendOffset.top + 'px';\n\n        if (!rightalign) {\n          css.left = pos.left - appendOffset.left + 'px';\n        } else {\n          css.right = window.innerWidth -\n            (pos.left - appendOffset.left + $element.prop('offsetWidth')) + 'px';\n        }\n      }\n\n      self.dropdownMenu.css(css);\n    }\n\n    var openContainer = appendTo ? appendTo : $element;\n    var dropdownOpenClass = appendTo ? appendToOpenClass : openClass;\n    var hasOpenClass = openContainer.hasClass(dropdownOpenClass);\n    var isOnlyOpen = uibDropdownService.isOnlyOpen($scope, appendTo);\n\n    if (hasOpenClass === !isOpen) {\n      var toggleClass;\n      if (appendTo) {\n        toggleClass = !isOnlyOpen ? 'addClass' : 'removeClass';\n      } else {\n        toggleClass = isOpen ? 'addClass' : 'removeClass';\n      }\n      $animate[toggleClass](openContainer, dropdownOpenClass).then(function() {\n        if (angular.isDefined(isOpen) && isOpen !== wasOpen) {\n          toggleInvoker($scope, { open: !!isOpen });\n        }\n      });\n    }\n\n    if (isOpen) {\n      if (self.dropdownMenuTemplateUrl) {\n        $templateRequest(self.dropdownMenuTemplateUrl).then(function(tplContent) {\n          templateScope = scope.$new();\n          $compile(tplContent.trim())(templateScope, function(dropdownElement) {\n            var newEl = dropdownElement;\n            self.dropdownMenu.replaceWith(newEl);\n            self.dropdownMenu = newEl;\n            $document.on('keydown', uibDropdownService.keybindFilter);\n          });\n        });\n      } else {\n        $document.on('keydown', uibDropdownService.keybindFilter);\n      }\n\n      scope.focusToggleElement();\n      uibDropdownService.open(scope, $element, appendTo);\n    } else {\n      uibDropdownService.close(scope, $element, appendTo);\n      if (self.dropdownMenuTemplateUrl) {\n        if (templateScope) {\n          templateScope.$destroy();\n        }\n        var newEl = angular.element('<ul class=\"dropdown-menu\"></ul>');\n        self.dropdownMenu.replaceWith(newEl);\n        self.dropdownMenu = newEl;\n      }\n\n      self.selectedOption = null;\n    }\n\n    if (angular.isFunction(setIsOpen)) {\n      setIsOpen($scope, isOpen);\n    }\n  });\n}])\n\n.directive('uibDropdown', function() {\n  return {\n    controller: 'UibDropdownController',\n    link: function(scope, element, attrs, dropdownCtrl) {\n      dropdownCtrl.init();\n    }\n  };\n})\n\n.directive('uibDropdownMenu', function() {\n  return {\n    restrict: 'A',\n    require: '?^uibDropdown',\n    link: function(scope, element, attrs, dropdownCtrl) {\n      if (!dropdownCtrl || angular.isDefined(attrs.dropdownNested)) {\n        return;\n      }\n\n      element.addClass('dropdown-menu');\n\n      var tplUrl = attrs.templateUrl;\n      if (tplUrl) {\n        dropdownCtrl.dropdownMenuTemplateUrl = tplUrl;\n      }\n\n      if (!dropdownCtrl.dropdownMenu) {\n        dropdownCtrl.dropdownMenu = element;\n      }\n    }\n  };\n})\n\n.directive('uibDropdownToggle', function() {\n  return {\n    require: '?^uibDropdown',\n    link: function(scope, element, attrs, dropdownCtrl) {\n      if (!dropdownCtrl) {\n        return;\n      }\n\n      element.addClass('dropdown-toggle');\n\n      dropdownCtrl.toggleElement = element;\n\n      var toggleDropdown = function(event) {\n        event.preventDefault();\n\n        if (!element.hasClass('disabled') && !attrs.disabled) {\n          scope.$apply(function() {\n            dropdownCtrl.toggle();\n          });\n        }\n      };\n\n      element.on('click', toggleDropdown);\n\n      // WAI-ARIA\n      element.attr({ 'aria-haspopup': true, 'aria-expanded': false });\n      scope.$watch(dropdownCtrl.isOpen, function(isOpen) {\n        element.attr('aria-expanded', !!isOpen);\n      });\n\n      scope.$on('$destroy', function() {\n        element.off('click', toggleDropdown);\n      });\n    }\n  };\n});\n\nangular.module('ui.bootstrap.stackedMap', [])\n/**\n * A helper, internal data structure that acts as a map but also allows getting / removing\n * elements in the LIFO order\n */\n  .factory('$$stackedMap', function() {\n    return {\n      createNew: function() {\n        var stack = [];\n\n        return {\n          add: function(key, value) {\n            stack.push({\n              key: key,\n              value: value\n            });\n          },\n          get: function(key) {\n            for (var i = 0; i < stack.length; i++) {\n              if (key === stack[i].key) {\n                return stack[i];\n              }\n            }\n          },\n          keys: function() {\n            var keys = [];\n            for (var i = 0; i < stack.length; i++) {\n              keys.push(stack[i].key);\n            }\n            return keys;\n          },\n          top: function() {\n            return stack[stack.length - 1];\n          },\n          remove: function(key) {\n            var idx = -1;\n            for (var i = 0; i < stack.length; i++) {\n              if (key === stack[i].key) {\n                idx = i;\n                break;\n              }\n            }\n            return stack.splice(idx, 1)[0];\n          },\n          removeTop: function() {\n            return stack.pop();\n          },\n          length: function() {\n            return stack.length;\n          }\n        };\n      }\n    };\n  });\nangular.module('ui.bootstrap.modal', ['ui.bootstrap.multiMap', 'ui.bootstrap.stackedMap', 'ui.bootstrap.position'])\n/**\n * Pluggable resolve mechanism for the modal resolve resolution\n * Supports UI Router's $resolve service\n */\n  .provider('$uibResolve', function() {\n    var resolve = this;\n    this.resolver = null;\n\n    this.setResolver = function(resolver) {\n      this.resolver = resolver;\n    };\n\n    this.$get = ['$injector', '$q', function($injector, $q) {\n      var resolver = resolve.resolver ? $injector.get(resolve.resolver) : null;\n      return {\n        resolve: function(invocables, locals, parent, self) {\n          if (resolver) {\n            return resolver.resolve(invocables, locals, parent, self);\n          }\n\n          var promises = [];\n\n          angular.forEach(invocables, function(value) {\n            if (angular.isFunction(value) || angular.isArray(value)) {\n              promises.push($q.resolve($injector.invoke(value)));\n            } else if (angular.isString(value)) {\n              promises.push($q.resolve($injector.get(value)));\n            } else {\n              promises.push($q.resolve(value));\n            }\n          });\n\n          return $q.all(promises).then(function(resolves) {\n            var resolveObj = {};\n            var resolveIter = 0;\n            angular.forEach(invocables, function(value, key) {\n              resolveObj[key] = resolves[resolveIter++];\n            });\n\n            return resolveObj;\n          });\n        }\n      };\n    }];\n  })\n\n/**\n * A helper directive for the $modal service. It creates a backdrop element.\n */\n  .directive('uibModalBackdrop', ['$animate', '$injector', '$uibModalStack',\n  function($animate, $injector, $modalStack) {\n    return {\n      restrict: 'A',\n      compile: function(tElement, tAttrs) {\n        tElement.addClass(tAttrs.backdropClass);\n        return linkFn;\n      }\n    };\n\n    function linkFn(scope, element, attrs) {\n      if (attrs.modalInClass) {\n        $animate.addClass(element, attrs.modalInClass);\n\n        scope.$on($modalStack.NOW_CLOSING_EVENT, function(e, setIsAsync) {\n          var done = setIsAsync();\n          if (scope.modalOptions.animation) {\n            $animate.removeClass(element, attrs.modalInClass).then(done);\n          } else {\n            done();\n          }\n        });\n      }\n    }\n  }])\n\n  .directive('uibModalWindow', ['$uibModalStack', '$q', '$animateCss', '$document',\n  function($modalStack, $q, $animateCss, $document) {\n    return {\n      scope: {\n        index: '@'\n      },\n      restrict: 'A',\n      transclude: true,\n      templateUrl: function(tElement, tAttrs) {\n        return tAttrs.templateUrl || 'uib/template/modal/window.html';\n      },\n      link: function(scope, element, attrs) {\n        element.addClass(attrs.windowTopClass || '');\n        scope.size = attrs.size;\n\n        scope.close = function(evt) {\n          var modal = $modalStack.getTop();\n          if (modal && modal.value.backdrop &&\n            modal.value.backdrop !== 'static' &&\n            evt.target === evt.currentTarget) {\n            evt.preventDefault();\n            evt.stopPropagation();\n            $modalStack.dismiss(modal.key, 'backdrop click');\n          }\n        };\n\n        // moved from template to fix issue #2280\n        element.on('click', scope.close);\n\n        // This property is only added to the scope for the purpose of detecting when this directive is rendered.\n        // We can detect that by using this property in the template associated with this directive and then use\n        // {@link Attribute#$observe} on it. For more details please see {@link TableColumnResize}.\n        scope.$isRendered = true;\n\n        // Deferred object that will be resolved when this modal is rendered.\n        var modalRenderDeferObj = $q.defer();\n        // Resolve render promise post-digest\n        scope.$$postDigest(function() {\n          modalRenderDeferObj.resolve();\n        });\n\n        modalRenderDeferObj.promise.then(function() {\n          var animationPromise = null;\n\n          if (attrs.modalInClass) {\n            animationPromise = $animateCss(element, {\n              addClass: attrs.modalInClass\n            }).start();\n\n            scope.$on($modalStack.NOW_CLOSING_EVENT, function(e, setIsAsync) {\n              var done = setIsAsync();\n              $animateCss(element, {\n                removeClass: attrs.modalInClass\n              }).start().then(done);\n            });\n          }\n\n\n          $q.when(animationPromise).then(function() {\n            // Notify {@link $modalStack} that modal is rendered.\n            var modal = $modalStack.getTop();\n            if (modal) {\n              $modalStack.modalRendered(modal.key);\n            }\n\n            /**\n             * If something within the freshly-opened modal already has focus (perhaps via a\n             * directive that causes focus) then there's no need to try to focus anything.\n             */\n            if (!($document[0].activeElement && element[0].contains($document[0].activeElement))) {\n              var inputWithAutofocus = element[0].querySelector('[autofocus]');\n              /**\n               * Auto-focusing of a freshly-opened modal element causes any child elements\n               * with the autofocus attribute to lose focus. This is an issue on touch\n               * based devices which will show and then hide the onscreen keyboard.\n               * Attempts to refocus the autofocus element via JavaScript will not reopen\n               * the onscreen keyboard. Fixed by updated the focusing logic to only autofocus\n               * the modal element if the modal does not contain an autofocus element.\n               */\n              if (inputWithAutofocus) {\n                inputWithAutofocus.focus();\n              } else {\n                element[0].focus();\n              }\n            }\n          });\n        });\n      }\n    };\n  }])\n\n  .directive('uibModalAnimationClass', function() {\n    return {\n      compile: function(tElement, tAttrs) {\n        if (tAttrs.modalAnimation) {\n          tElement.addClass(tAttrs.uibModalAnimationClass);\n        }\n      }\n    };\n  })\n\n  .directive('uibModalTransclude', ['$animate', function($animate) {\n    return {\n      link: function(scope, element, attrs, controller, transclude) {\n        transclude(scope.$parent, function(clone) {\n          element.empty();\n          $animate.enter(clone, element);\n        });\n      }\n    };\n  }])\n\n  .factory('$uibModalStack', ['$animate', '$animateCss', '$document',\n    '$compile', '$rootScope', '$q', '$$multiMap', '$$stackedMap', '$uibPosition',\n    function($animate, $animateCss, $document, $compile, $rootScope, $q, $$multiMap, $$stackedMap, $uibPosition) {\n      var OPENED_MODAL_CLASS = 'modal-open';\n\n      var backdropDomEl, backdropScope;\n      var openedWindows = $$stackedMap.createNew();\n      var openedClasses = $$multiMap.createNew();\n      var $modalStack = {\n        NOW_CLOSING_EVENT: 'modal.stack.now-closing'\n      };\n      var topModalIndex = 0;\n      var previousTopOpenedModal = null;\n      var ARIA_HIDDEN_ATTRIBUTE_NAME = 'data-bootstrap-modal-aria-hidden-count';\n\n      //Modal focus behavior\n      var tabbableSelector = 'a[href], area[href], input:not([disabled]):not([tabindex=\\'-1\\']), ' +\n        'button:not([disabled]):not([tabindex=\\'-1\\']),select:not([disabled]):not([tabindex=\\'-1\\']), textarea:not([disabled]):not([tabindex=\\'-1\\']), ' +\n        'iframe, object, embed, *[tabindex]:not([tabindex=\\'-1\\']), *[contenteditable=true]';\n      var scrollbarPadding;\n      var SNAKE_CASE_REGEXP = /[A-Z]/g;\n\n      // TODO: extract into common dependency with tooltip\n      function snake_case(name) {\n        var separator = '-';\n        return name.replace(SNAKE_CASE_REGEXP, function(letter, pos) {\n          return (pos ? separator : '') + letter.toLowerCase();\n        });\n      }\n\n      function isVisible(element) {\n        return !!(element.offsetWidth ||\n          element.offsetHeight ||\n          element.getClientRects().length);\n      }\n\n      function backdropIndex() {\n        var topBackdropIndex = -1;\n        var opened = openedWindows.keys();\n        for (var i = 0; i < opened.length; i++) {\n          if (openedWindows.get(opened[i]).value.backdrop) {\n            topBackdropIndex = i;\n          }\n        }\n\n        // If any backdrop exist, ensure that it's index is always\n        // right below the top modal\n        if (topBackdropIndex > -1 && topBackdropIndex < topModalIndex) {\n          topBackdropIndex = topModalIndex;\n        }\n        return topBackdropIndex;\n      }\n\n      $rootScope.$watch(backdropIndex, function(newBackdropIndex) {\n        if (backdropScope) {\n          backdropScope.index = newBackdropIndex;\n        }\n      });\n\n      function removeModalWindow(modalInstance, elementToReceiveFocus) {\n        var modalWindow = openedWindows.get(modalInstance).value;\n        var appendToElement = modalWindow.appendTo;\n\n        //clean up the stack\n        openedWindows.remove(modalInstance);\n        previousTopOpenedModal = openedWindows.top();\n        if (previousTopOpenedModal) {\n          topModalIndex = parseInt(previousTopOpenedModal.value.modalDomEl.attr('index'), 10);\n        }\n\n        removeAfterAnimate(modalWindow.modalDomEl, modalWindow.modalScope, function() {\n          var modalBodyClass = modalWindow.openedClass || OPENED_MODAL_CLASS;\n          openedClasses.remove(modalBodyClass, modalInstance);\n          var areAnyOpen = openedClasses.hasKey(modalBodyClass);\n          appendToElement.toggleClass(modalBodyClass, areAnyOpen);\n          if (!areAnyOpen && scrollbarPadding && scrollbarPadding.heightOverflow && scrollbarPadding.scrollbarWidth) {\n            if (scrollbarPadding.originalRight) {\n              appendToElement.css({paddingRight: scrollbarPadding.originalRight + 'px'});\n            } else {\n              appendToElement.css({paddingRight: ''});\n            }\n            scrollbarPadding = null;\n          }\n          toggleTopWindowClass(true);\n        }, modalWindow.closedDeferred);\n        checkRemoveBackdrop();\n\n        //move focus to specified element if available, or else to body\n        if (elementToReceiveFocus && elementToReceiveFocus.focus) {\n          elementToReceiveFocus.focus();\n        } else if (appendToElement.focus) {\n          appendToElement.focus();\n        }\n      }\n\n      // Add or remove \"windowTopClass\" from the top window in the stack\n      function toggleTopWindowClass(toggleSwitch) {\n        var modalWindow;\n\n        if (openedWindows.length() > 0) {\n          modalWindow = openedWindows.top().value;\n          modalWindow.modalDomEl.toggleClass(modalWindow.windowTopClass || '', toggleSwitch);\n        }\n      }\n\n      function checkRemoveBackdrop() {\n        //remove backdrop if no longer needed\n        if (backdropDomEl && backdropIndex() === -1) {\n          var backdropScopeRef = backdropScope;\n          removeAfterAnimate(backdropDomEl, backdropScope, function() {\n            backdropScopeRef = null;\n          });\n          backdropDomEl = undefined;\n          backdropScope = undefined;\n        }\n      }\n\n      function removeAfterAnimate(domEl, scope, done, closedDeferred) {\n        var asyncDeferred;\n        var asyncPromise = null;\n        var setIsAsync = function() {\n          if (!asyncDeferred) {\n            asyncDeferred = $q.defer();\n            asyncPromise = asyncDeferred.promise;\n          }\n\n          return function asyncDone() {\n            asyncDeferred.resolve();\n          };\n        };\n        scope.$broadcast($modalStack.NOW_CLOSING_EVENT, setIsAsync);\n\n        // Note that it's intentional that asyncPromise might be null.\n        // That's when setIsAsync has not been called during the\n        // NOW_CLOSING_EVENT broadcast.\n        return $q.when(asyncPromise).then(afterAnimating);\n\n        function afterAnimating() {\n          if (afterAnimating.done) {\n            return;\n          }\n          afterAnimating.done = true;\n\n          $animate.leave(domEl).then(function() {\n            if (done) {\n              done();\n            }\n\n            domEl.remove();\n            if (closedDeferred) {\n              closedDeferred.resolve();\n            }\n          });\n\n          scope.$destroy();\n        }\n      }\n\n      $document.on('keydown', keydownListener);\n\n      $rootScope.$on('$destroy', function() {\n        $document.off('keydown', keydownListener);\n      });\n\n      function keydownListener(evt) {\n        if (evt.isDefaultPrevented()) {\n          return evt;\n        }\n\n        var modal = openedWindows.top();\n        if (modal) {\n          switch (evt.which) {\n            case 27: {\n              if (modal.value.keyboard) {\n                evt.preventDefault();\n                $rootScope.$apply(function() {\n                  $modalStack.dismiss(modal.key, 'escape key press');\n                });\n              }\n              break;\n            }\n            case 9: {\n              var list = $modalStack.loadFocusElementList(modal);\n              var focusChanged = false;\n              if (evt.shiftKey) {\n                if ($modalStack.isFocusInFirstItem(evt, list) || $modalStack.isModalFocused(evt, modal)) {\n                  focusChanged = $modalStack.focusLastFocusableElement(list);\n                }\n              } else {\n                if ($modalStack.isFocusInLastItem(evt, list)) {\n                  focusChanged = $modalStack.focusFirstFocusableElement(list);\n                }\n              }\n\n              if (focusChanged) {\n                evt.preventDefault();\n                evt.stopPropagation();\n              }\n\n              break;\n            }\n          }\n        }\n      }\n\n      $modalStack.open = function(modalInstance, modal) {\n        var modalOpener = $document[0].activeElement,\n          modalBodyClass = modal.openedClass || OPENED_MODAL_CLASS;\n\n        toggleTopWindowClass(false);\n\n        // Store the current top first, to determine what index we ought to use\n        // for the current top modal\n        previousTopOpenedModal = openedWindows.top();\n\n        openedWindows.add(modalInstance, {\n          deferred: modal.deferred,\n          renderDeferred: modal.renderDeferred,\n          closedDeferred: modal.closedDeferred,\n          modalScope: modal.scope,\n          backdrop: modal.backdrop,\n          keyboard: modal.keyboard,\n          openedClass: modal.openedClass,\n          windowTopClass: modal.windowTopClass,\n          animation: modal.animation,\n          appendTo: modal.appendTo\n        });\n\n        openedClasses.put(modalBodyClass, modalInstance);\n\n        var appendToElement = modal.appendTo,\n            currBackdropIndex = backdropIndex();\n\n        if (currBackdropIndex >= 0 && !backdropDomEl) {\n          backdropScope = $rootScope.$new(true);\n          backdropScope.modalOptions = modal;\n          backdropScope.index = currBackdropIndex;\n          backdropDomEl = angular.element('<div uib-modal-backdrop=\"modal-backdrop\"></div>');\n          backdropDomEl.attr({\n            'class': 'modal-backdrop',\n            'ng-style': '{\\'z-index\\': 1040 + (index && 1 || 0) + index*10}',\n            'uib-modal-animation-class': 'fade',\n            'modal-in-class': 'in'\n          });\n          if (modal.backdropClass) {\n            backdropDomEl.addClass(modal.backdropClass);\n          }\n\n          if (modal.animation) {\n            backdropDomEl.attr('modal-animation', 'true');\n          }\n          $compile(backdropDomEl)(backdropScope);\n          $animate.enter(backdropDomEl, appendToElement);\n          if ($uibPosition.isScrollable(appendToElement)) {\n            scrollbarPadding = $uibPosition.scrollbarPadding(appendToElement);\n            if (scrollbarPadding.heightOverflow && scrollbarPadding.scrollbarWidth) {\n              appendToElement.css({paddingRight: scrollbarPadding.right + 'px'});\n            }\n          }\n        }\n\n        var content;\n        if (modal.component) {\n          content = document.createElement(snake_case(modal.component.name));\n          content = angular.element(content);\n          content.attr({\n            resolve: '$resolve',\n            'modal-instance': '$uibModalInstance',\n            close: '$close($value)',\n            dismiss: '$dismiss($value)'\n          });\n        } else {\n          content = modal.content;\n        }\n\n        // Set the top modal index based on the index of the previous top modal\n        topModalIndex = previousTopOpenedModal ? parseInt(previousTopOpenedModal.value.modalDomEl.attr('index'), 10) + 1 : 0;\n        var angularDomEl = angular.element('<div uib-modal-window=\"modal-window\"></div>');\n        angularDomEl.attr({\n          'class': 'modal',\n          'template-url': modal.windowTemplateUrl,\n          'window-top-class': modal.windowTopClass,\n          'role': 'dialog',\n          'aria-labelledby': modal.ariaLabelledBy,\n          'aria-describedby': modal.ariaDescribedBy,\n          'size': modal.size,\n          'index': topModalIndex,\n          'animate': 'animate',\n          'ng-style': '{\\'z-index\\': 1050 + $$topModalIndex*10, display: \\'block\\'}',\n          'tabindex': -1,\n          'uib-modal-animation-class': 'fade',\n          'modal-in-class': 'in'\n        }).append(content);\n        if (modal.windowClass) {\n          angularDomEl.addClass(modal.windowClass);\n        }\n\n        if (modal.animation) {\n          angularDomEl.attr('modal-animation', 'true');\n        }\n\n        appendToElement.addClass(modalBodyClass);\n        if (modal.scope) {\n          // we need to explicitly add the modal index to the modal scope\n          // because it is needed by ngStyle to compute the zIndex property.\n          modal.scope.$$topModalIndex = topModalIndex;\n        }\n        $animate.enter($compile(angularDomEl)(modal.scope), appendToElement);\n\n        openedWindows.top().value.modalDomEl = angularDomEl;\n        openedWindows.top().value.modalOpener = modalOpener;\n\n        applyAriaHidden(angularDomEl);\n\n        function applyAriaHidden(el) {\n          if (!el || el[0].tagName === 'BODY') {\n            return;\n          }\n\n          getSiblings(el).forEach(function(sibling) {\n            var elemIsAlreadyHidden = sibling.getAttribute('aria-hidden') === 'true',\n              ariaHiddenCount = parseInt(sibling.getAttribute(ARIA_HIDDEN_ATTRIBUTE_NAME), 10);\n\n            if (!ariaHiddenCount) {\n              ariaHiddenCount = elemIsAlreadyHidden ? 1 : 0;\n            }\n\n            sibling.setAttribute(ARIA_HIDDEN_ATTRIBUTE_NAME, ariaHiddenCount + 1);\n            sibling.setAttribute('aria-hidden', 'true');\n          });\n\n          return applyAriaHidden(el.parent());\n\n          function getSiblings(el) {\n            var children = el.parent() ? el.parent().children() : [];\n\n            return Array.prototype.filter.call(children, function(child) {\n              return child !== el[0];\n            });\n          }\n        }\n      };\n\n      function broadcastClosing(modalWindow, resultOrReason, closing) {\n        return !modalWindow.value.modalScope.$broadcast('modal.closing', resultOrReason, closing).defaultPrevented;\n      }\n\n      function unhideBackgroundElements() {\n        Array.prototype.forEach.call(\n          document.querySelectorAll('[' + ARIA_HIDDEN_ATTRIBUTE_NAME + ']'),\n          function(hiddenEl) {\n            var ariaHiddenCount = parseInt(hiddenEl.getAttribute(ARIA_HIDDEN_ATTRIBUTE_NAME), 10),\n              newHiddenCount = ariaHiddenCount - 1;\n            hiddenEl.setAttribute(ARIA_HIDDEN_ATTRIBUTE_NAME, newHiddenCount);\n\n            if (!newHiddenCount) {\n              hiddenEl.removeAttribute(ARIA_HIDDEN_ATTRIBUTE_NAME);\n              hiddenEl.removeAttribute('aria-hidden');\n            }\n          }\n        );\n      }\n\n      $modalStack.close = function(modalInstance, result) {\n        var modalWindow = openedWindows.get(modalInstance);\n        unhideBackgroundElements();\n        if (modalWindow && broadcastClosing(modalWindow, result, true)) {\n          modalWindow.value.modalScope.$$uibDestructionScheduled = true;\n          modalWindow.value.deferred.resolve(result);\n          removeModalWindow(modalInstance, modalWindow.value.modalOpener);\n          return true;\n        }\n\n        return !modalWindow;\n      };\n\n      $modalStack.dismiss = function(modalInstance, reason) {\n        var modalWindow = openedWindows.get(modalInstance);\n        unhideBackgroundElements();\n        if (modalWindow && broadcastClosing(modalWindow, reason, false)) {\n          modalWindow.value.modalScope.$$uibDestructionScheduled = true;\n          modalWindow.value.deferred.reject(reason);\n          removeModalWindow(modalInstance, modalWindow.value.modalOpener);\n          return true;\n        }\n        return !modalWindow;\n      };\n\n      $modalStack.dismissAll = function(reason) {\n        var topModal = this.getTop();\n        while (topModal && this.dismiss(topModal.key, reason)) {\n          topModal = this.getTop();\n        }\n      };\n\n      $modalStack.getTop = function() {\n        return openedWindows.top();\n      };\n\n      $modalStack.modalRendered = function(modalInstance) {\n        var modalWindow = openedWindows.get(modalInstance);\n        if (modalWindow) {\n          modalWindow.value.renderDeferred.resolve();\n        }\n      };\n\n      $modalStack.focusFirstFocusableElement = function(list) {\n        if (list.length > 0) {\n          list[0].focus();\n          return true;\n        }\n        return false;\n      };\n\n      $modalStack.focusLastFocusableElement = function(list) {\n        if (list.length > 0) {\n          list[list.length - 1].focus();\n          return true;\n        }\n        return false;\n      };\n\n      $modalStack.isModalFocused = function(evt, modalWindow) {\n        if (evt && modalWindow) {\n          var modalDomEl = modalWindow.value.modalDomEl;\n          if (modalDomEl && modalDomEl.length) {\n            return (evt.target || evt.srcElement) === modalDomEl[0];\n          }\n        }\n        return false;\n      };\n\n      $modalStack.isFocusInFirstItem = function(evt, list) {\n        if (list.length > 0) {\n          return (evt.target || evt.srcElement) === list[0];\n        }\n        return false;\n      };\n\n      $modalStack.isFocusInLastItem = function(evt, list) {\n        if (list.length > 0) {\n          return (evt.target || evt.srcElement) === list[list.length - 1];\n        }\n        return false;\n      };\n\n      $modalStack.loadFocusElementList = function(modalWindow) {\n        if (modalWindow) {\n          var modalDomE1 = modalWindow.value.modalDomEl;\n          if (modalDomE1 && modalDomE1.length) {\n            var elements = modalDomE1[0].querySelectorAll(tabbableSelector);\n            return elements ?\n              Array.prototype.filter.call(elements, function(element) {\n                return isVisible(element);\n              }) : elements;\n          }\n        }\n      };\n\n      return $modalStack;\n    }])\n\n  .provider('$uibModal', function() {\n    var $modalProvider = {\n      options: {\n        animation: true,\n        backdrop: true, //can also be false or 'static'\n        keyboard: true\n      },\n      $get: ['$rootScope', '$q', '$document', '$templateRequest', '$controller', '$uibResolve', '$uibModalStack',\n        function ($rootScope, $q, $document, $templateRequest, $controller, $uibResolve, $modalStack) {\n          var $modal = {};\n\n          function getTemplatePromise(options) {\n            return options.template ? $q.when(options.template) :\n              $templateRequest(angular.isFunction(options.templateUrl) ?\n                options.templateUrl() : options.templateUrl);\n          }\n\n          var promiseChain = null;\n          $modal.getPromiseChain = function() {\n            return promiseChain;\n          };\n\n          $modal.open = function(modalOptions) {\n            var modalResultDeferred = $q.defer();\n            var modalOpenedDeferred = $q.defer();\n            var modalClosedDeferred = $q.defer();\n            var modalRenderDeferred = $q.defer();\n\n            //prepare an instance of a modal to be injected into controllers and returned to a caller\n            var modalInstance = {\n              result: modalResultDeferred.promise,\n              opened: modalOpenedDeferred.promise,\n              closed: modalClosedDeferred.promise,\n              rendered: modalRenderDeferred.promise,\n              close: function (result) {\n                return $modalStack.close(modalInstance, result);\n              },\n              dismiss: function (reason) {\n                return $modalStack.dismiss(modalInstance, reason);\n              }\n            };\n\n            //merge and clean up options\n            modalOptions = angular.extend({}, $modalProvider.options, modalOptions);\n            modalOptions.resolve = modalOptions.resolve || {};\n            modalOptions.appendTo = modalOptions.appendTo || $document.find('body').eq(0);\n\n            if (!modalOptions.appendTo.length) {\n              throw new Error('appendTo element not found. Make sure that the element passed is in DOM.');\n            }\n\n            //verify options\n            if (!modalOptions.component && !modalOptions.template && !modalOptions.templateUrl) {\n              throw new Error('One of component or template or templateUrl options is required.');\n            }\n\n            var templateAndResolvePromise;\n            if (modalOptions.component) {\n              templateAndResolvePromise = $q.when($uibResolve.resolve(modalOptions.resolve, {}, null, null));\n            } else {\n              templateAndResolvePromise =\n                $q.all([getTemplatePromise(modalOptions), $uibResolve.resolve(modalOptions.resolve, {}, null, null)]);\n            }\n\n            function resolveWithTemplate() {\n              return templateAndResolvePromise;\n            }\n\n            // Wait for the resolution of the existing promise chain.\n            // Then switch to our own combined promise dependency (regardless of how the previous modal fared).\n            // Then add to $modalStack and resolve opened.\n            // Finally clean up the chain variable if no subsequent modal has overwritten it.\n            var samePromise;\n            samePromise = promiseChain = $q.all([promiseChain])\n              .then(resolveWithTemplate, resolveWithTemplate)\n              .then(function resolveSuccess(tplAndVars) {\n                var providedScope = modalOptions.scope || $rootScope;\n\n                var modalScope = providedScope.$new();\n                modalScope.$close = modalInstance.close;\n                modalScope.$dismiss = modalInstance.dismiss;\n\n                modalScope.$on('$destroy', function() {\n                  if (!modalScope.$$uibDestructionScheduled) {\n                    modalScope.$dismiss('$uibUnscheduledDestruction');\n                  }\n                });\n\n                var modal = {\n                  scope: modalScope,\n                  deferred: modalResultDeferred,\n                  renderDeferred: modalRenderDeferred,\n                  closedDeferred: modalClosedDeferred,\n                  animation: modalOptions.animation,\n                  backdrop: modalOptions.backdrop,\n                  keyboard: modalOptions.keyboard,\n                  backdropClass: modalOptions.backdropClass,\n                  windowTopClass: modalOptions.windowTopClass,\n                  windowClass: modalOptions.windowClass,\n                  windowTemplateUrl: modalOptions.windowTemplateUrl,\n                  ariaLabelledBy: modalOptions.ariaLabelledBy,\n                  ariaDescribedBy: modalOptions.ariaDescribedBy,\n                  size: modalOptions.size,\n                  openedClass: modalOptions.openedClass,\n                  appendTo: modalOptions.appendTo\n                };\n\n                var component = {};\n                var ctrlInstance, ctrlInstantiate, ctrlLocals = {};\n\n                if (modalOptions.component) {\n                  constructLocals(component, false, true, false);\n                  component.name = modalOptions.component;\n                  modal.component = component;\n                } else if (modalOptions.controller) {\n                  constructLocals(ctrlLocals, true, false, true);\n\n                  // the third param will make the controller instantiate later,private api\n                  // @see https://github.com/angular/angular.js/blob/master/src/ng/controller.js#L126\n                  ctrlInstantiate = $controller(modalOptions.controller, ctrlLocals, true, modalOptions.controllerAs);\n                  if (modalOptions.controllerAs && modalOptions.bindToController) {\n                    ctrlInstance = ctrlInstantiate.instance;\n                    ctrlInstance.$close = modalScope.$close;\n                    ctrlInstance.$dismiss = modalScope.$dismiss;\n                    angular.extend(ctrlInstance, {\n                      $resolve: ctrlLocals.$scope.$resolve\n                    }, providedScope);\n                  }\n\n                  ctrlInstance = ctrlInstantiate();\n\n                  if (angular.isFunction(ctrlInstance.$onInit)) {\n                    ctrlInstance.$onInit();\n                  }\n                }\n\n                if (!modalOptions.component) {\n                  modal.content = tplAndVars[0];\n                }\n\n                $modalStack.open(modalInstance, modal);\n                modalOpenedDeferred.resolve(true);\n\n                function constructLocals(obj, template, instanceOnScope, injectable) {\n                  obj.$scope = modalScope;\n                  obj.$scope.$resolve = {};\n                  if (instanceOnScope) {\n                    obj.$scope.$uibModalInstance = modalInstance;\n                  } else {\n                    obj.$uibModalInstance = modalInstance;\n                  }\n\n                  var resolves = template ? tplAndVars[1] : tplAndVars;\n                  angular.forEach(resolves, function(value, key) {\n                    if (injectable) {\n                      obj[key] = value;\n                    }\n\n                    obj.$scope.$resolve[key] = value;\n                  });\n                }\n            }, function resolveError(reason) {\n              modalOpenedDeferred.reject(reason);\n              modalResultDeferred.reject(reason);\n            })['finally'](function() {\n              if (promiseChain === samePromise) {\n                promiseChain = null;\n              }\n            });\n\n            return modalInstance;\n          };\n\n          return $modal;\n        }\n      ]\n    };\n\n    return $modalProvider;\n  });\n\nangular.module('ui.bootstrap.paging', [])\n/**\n * Helper internal service for generating common controller code between the\n * pager and pagination components\n */\n.factory('uibPaging', ['$parse', function($parse) {\n  return {\n    create: function(ctrl, $scope, $attrs) {\n      ctrl.setNumPages = $attrs.numPages ? $parse($attrs.numPages).assign : angular.noop;\n      ctrl.ngModelCtrl = { $setViewValue: angular.noop }; // nullModelCtrl\n      ctrl._watchers = [];\n\n      ctrl.init = function(ngModelCtrl, config) {\n        ctrl.ngModelCtrl = ngModelCtrl;\n        ctrl.config = config;\n\n        ngModelCtrl.$render = function() {\n          ctrl.render();\n        };\n\n        if ($attrs.itemsPerPage) {\n          ctrl._watchers.push($scope.$parent.$watch($attrs.itemsPerPage, function(value) {\n            ctrl.itemsPerPage = parseInt(value, 10);\n            $scope.totalPages = ctrl.calculateTotalPages();\n            ctrl.updatePage();\n          }));\n        } else {\n          ctrl.itemsPerPage = config.itemsPerPage;\n        }\n\n        $scope.$watch('totalItems', function(newTotal, oldTotal) {\n          if (angular.isDefined(newTotal) || newTotal !== oldTotal) {\n            $scope.totalPages = ctrl.calculateTotalPages();\n            ctrl.updatePage();\n          }\n        });\n      };\n\n      ctrl.calculateTotalPages = function() {\n        var totalPages = ctrl.itemsPerPage < 1 ? 1 : Math.ceil($scope.totalItems / ctrl.itemsPerPage);\n        return Math.max(totalPages || 0, 1);\n      };\n\n      ctrl.render = function() {\n        $scope.page = parseInt(ctrl.ngModelCtrl.$viewValue, 10) || 1;\n      };\n\n      $scope.selectPage = function(page, evt) {\n        if (evt) {\n          evt.preventDefault();\n        }\n\n        var clickAllowed = !$scope.ngDisabled || !evt;\n        if (clickAllowed && $scope.page !== page && page > 0 && page <= $scope.totalPages) {\n          if (evt && evt.target) {\n            evt.target.blur();\n          }\n          ctrl.ngModelCtrl.$setViewValue(page);\n          ctrl.ngModelCtrl.$render();\n        }\n      };\n\n      $scope.getText = function(key) {\n        return $scope[key + 'Text'] || ctrl.config[key + 'Text'];\n      };\n\n      $scope.noPrevious = function() {\n        return $scope.page === 1;\n      };\n\n      $scope.noNext = function() {\n        return $scope.page === $scope.totalPages;\n      };\n\n      ctrl.updatePage = function() {\n        ctrl.setNumPages($scope.$parent, $scope.totalPages); // Readonly variable\n\n        if ($scope.page > $scope.totalPages) {\n          $scope.selectPage($scope.totalPages);\n        } else {\n          ctrl.ngModelCtrl.$render();\n        }\n      };\n\n      $scope.$on('$destroy', function() {\n        while (ctrl._watchers.length) {\n          ctrl._watchers.shift()();\n        }\n      });\n    }\n  };\n}]);\n\nangular.module('ui.bootstrap.pager', ['ui.bootstrap.paging', 'ui.bootstrap.tabindex'])\n\n.controller('UibPagerController', ['$scope', '$attrs', 'uibPaging', 'uibPagerConfig', function($scope, $attrs, uibPaging, uibPagerConfig) {\n  $scope.align = angular.isDefined($attrs.align) ? $scope.$parent.$eval($attrs.align) : uibPagerConfig.align;\n\n  uibPaging.create(this, $scope, $attrs);\n}])\n\n.constant('uibPagerConfig', {\n  itemsPerPage: 10,\n  previousText: '« Previous',\n  nextText: 'Next »',\n  align: true\n})\n\n.directive('uibPager', ['uibPagerConfig', function(uibPagerConfig) {\n  return {\n    scope: {\n      totalItems: '=',\n      previousText: '@',\n      nextText: '@',\n      ngDisabled: '='\n    },\n    require: ['uibPager', '?ngModel'],\n    restrict: 'A',\n    controller: 'UibPagerController',\n    controllerAs: 'pager',\n    templateUrl: function(element, attrs) {\n      return attrs.templateUrl || 'uib/template/pager/pager.html';\n    },\n    link: function(scope, element, attrs, ctrls) {\n      element.addClass('pager');\n      var paginationCtrl = ctrls[0], ngModelCtrl = ctrls[1];\n\n      if (!ngModelCtrl) {\n        return; // do nothing if no ng-model\n      }\n\n      paginationCtrl.init(ngModelCtrl, uibPagerConfig);\n    }\n  };\n}]);\n\nangular.module('ui.bootstrap.pagination', ['ui.bootstrap.paging', 'ui.bootstrap.tabindex'])\n.controller('UibPaginationController', ['$scope', '$attrs', '$parse', 'uibPaging', 'uibPaginationConfig', function($scope, $attrs, $parse, uibPaging, uibPaginationConfig) {\n  var ctrl = this;\n  // Setup configuration parameters\n  var maxSize = angular.isDefined($attrs.maxSize) ? $scope.$parent.$eval($attrs.maxSize) : uibPaginationConfig.maxSize,\n    rotate = angular.isDefined($attrs.rotate) ? $scope.$parent.$eval($attrs.rotate) : uibPaginationConfig.rotate,\n    forceEllipses = angular.isDefined($attrs.forceEllipses) ? $scope.$parent.$eval($attrs.forceEllipses) : uibPaginationConfig.forceEllipses,\n    boundaryLinkNumbers = angular.isDefined($attrs.boundaryLinkNumbers) ? $scope.$parent.$eval($attrs.boundaryLinkNumbers) : uibPaginationConfig.boundaryLinkNumbers,\n    pageLabel = angular.isDefined($attrs.pageLabel) ? function(idx) { return $scope.$parent.$eval($attrs.pageLabel, {$page: idx}); } : angular.identity;\n  $scope.boundaryLinks = angular.isDefined($attrs.boundaryLinks) ? $scope.$parent.$eval($attrs.boundaryLinks) : uibPaginationConfig.boundaryLinks;\n  $scope.directionLinks = angular.isDefined($attrs.directionLinks) ? $scope.$parent.$eval($attrs.directionLinks) : uibPaginationConfig.directionLinks;\n  $attrs.$set('role', 'menu');\n\n  uibPaging.create(this, $scope, $attrs);\n\n  if ($attrs.maxSize) {\n    ctrl._watchers.push($scope.$parent.$watch($parse($attrs.maxSize), function(value) {\n      maxSize = parseInt(value, 10);\n      ctrl.render();\n    }));\n  }\n\n  // Create page object used in template\n  function makePage(number, text, isActive) {\n    return {\n      number: number,\n      text: text,\n      active: isActive\n    };\n  }\n\n  function getPages(currentPage, totalPages) {\n    var pages = [];\n\n    // Default page limits\n    var startPage = 1, endPage = totalPages;\n    var isMaxSized = angular.isDefined(maxSize) && maxSize < totalPages;\n\n    // recompute if maxSize\n    if (isMaxSized) {\n      if (rotate) {\n        // Current page is displayed in the middle of the visible ones\n        startPage = Math.max(currentPage - Math.floor(maxSize / 2), 1);\n        endPage = startPage + maxSize - 1;\n\n        // Adjust if limit is exceeded\n        if (endPage > totalPages) {\n          endPage = totalPages;\n          startPage = endPage - maxSize + 1;\n        }\n      } else {\n        // Visible pages are paginated with maxSize\n        startPage = (Math.ceil(currentPage / maxSize) - 1) * maxSize + 1;\n\n        // Adjust last page if limit is exceeded\n        endPage = Math.min(startPage + maxSize - 1, totalPages);\n      }\n    }\n\n    // Add page number links\n    for (var number = startPage; number <= endPage; number++) {\n      var page = makePage(number, pageLabel(number), number === currentPage);\n      pages.push(page);\n    }\n\n    // Add links to move between page sets\n    if (isMaxSized && maxSize > 0 && (!rotate || forceEllipses || boundaryLinkNumbers)) {\n      if (startPage > 1) {\n        if (!boundaryLinkNumbers || startPage > 3) { //need ellipsis for all options unless range is too close to beginning\n        var previousPageSet = makePage(startPage - 1, '...', false);\n        pages.unshift(previousPageSet);\n      }\n        if (boundaryLinkNumbers) {\n          if (startPage === 3) { //need to replace ellipsis when the buttons would be sequential\n            var secondPageLink = makePage(2, '2', false);\n            pages.unshift(secondPageLink);\n          }\n          //add the first page\n          var firstPageLink = makePage(1, '1', false);\n          pages.unshift(firstPageLink);\n        }\n      }\n\n      if (endPage < totalPages) {\n        if (!boundaryLinkNumbers || endPage < totalPages - 2) { //need ellipsis for all options unless range is too close to end\n        var nextPageSet = makePage(endPage + 1, '...', false);\n        pages.push(nextPageSet);\n      }\n        if (boundaryLinkNumbers) {\n          if (endPage === totalPages - 2) { //need to replace ellipsis when the buttons would be sequential\n            var secondToLastPageLink = makePage(totalPages - 1, totalPages - 1, false);\n            pages.push(secondToLastPageLink);\n          }\n          //add the last page\n          var lastPageLink = makePage(totalPages, totalPages, false);\n          pages.push(lastPageLink);\n        }\n      }\n    }\n    return pages;\n  }\n\n  var originalRender = this.render;\n  this.render = function() {\n    originalRender();\n    if ($scope.page > 0 && $scope.page <= $scope.totalPages) {\n      $scope.pages = getPages($scope.page, $scope.totalPages);\n    }\n  };\n}])\n\n.constant('uibPaginationConfig', {\n  itemsPerPage: 10,\n  boundaryLinks: false,\n  boundaryLinkNumbers: false,\n  directionLinks: true,\n  firstText: 'First',\n  previousText: 'Previous',\n  nextText: 'Next',\n  lastText: 'Last',\n  rotate: true,\n  forceEllipses: false\n})\n\n.directive('uibPagination', ['$parse', 'uibPaginationConfig', function($parse, uibPaginationConfig) {\n  return {\n    scope: {\n      totalItems: '=',\n      firstText: '@',\n      previousText: '@',\n      nextText: '@',\n      lastText: '@',\n      ngDisabled:'='\n    },\n    require: ['uibPagination', '?ngModel'],\n    restrict: 'A',\n    controller: 'UibPaginationController',\n    controllerAs: 'pagination',\n    templateUrl: function(element, attrs) {\n      return attrs.templateUrl || 'uib/template/pagination/pagination.html';\n    },\n    link: function(scope, element, attrs, ctrls) {\n      element.addClass('pagination');\n      var paginationCtrl = ctrls[0], ngModelCtrl = ctrls[1];\n\n      if (!ngModelCtrl) {\n         return; // do nothing if no ng-model\n      }\n\n      paginationCtrl.init(ngModelCtrl, uibPaginationConfig);\n    }\n  };\n}]);\n\n/**\n * The following features are still outstanding: animation as a\n * function, placement as a function, inside, support for more triggers than\n * just mouse enter/leave, html tooltips, and selector delegation.\n */\nangular.module('ui.bootstrap.tooltip', ['ui.bootstrap.position', 'ui.bootstrap.stackedMap'])\n\n/**\n * The $tooltip service creates tooltip- and popover-like directives as well as\n * houses global options for them.\n */\n.provider('$uibTooltip', function() {\n  // The default options tooltip and popover.\n  var defaultOptions = {\n    placement: 'top',\n    placementClassPrefix: '',\n    animation: true,\n    popupDelay: 0,\n    popupCloseDelay: 0,\n    useContentExp: false\n  };\n\n  // Default hide triggers for each show trigger\n  var triggerMap = {\n    'mouseenter': 'mouseleave',\n    'click': 'click',\n    'outsideClick': 'outsideClick',\n    'focus': 'blur',\n    'none': ''\n  };\n\n  // The options specified to the provider globally.\n  var globalOptions = {};\n\n  /**\n   * `options({})` allows global configuration of all tooltips in the\n   * application.\n   *\n   *   var app = angular.module( 'App', ['ui.bootstrap.tooltip'], function( $tooltipProvider ) {\n   *     // place tooltips left instead of top by default\n   *     $tooltipProvider.options( { placement: 'left' } );\n   *   });\n   */\n\tthis.options = function(value) {\n\t\tangular.extend(globalOptions, value);\n\t};\n\n  /**\n   * This allows you to extend the set of trigger mappings available. E.g.:\n   *\n   *   $tooltipProvider.setTriggers( { 'openTrigger': 'closeTrigger' } );\n   */\n  this.setTriggers = function setTriggers(triggers) {\n    angular.extend(triggerMap, triggers);\n  };\n\n  /**\n   * This is a helper function for translating camel-case to snake_case.\n   */\n  function snake_case(name) {\n    var regexp = /[A-Z]/g;\n    var separator = '-';\n    return name.replace(regexp, function(letter, pos) {\n      return (pos ? separator : '') + letter.toLowerCase();\n    });\n  }\n\n  /**\n   * Returns the actual instance of the $tooltip service.\n   * TODO support multiple triggers\n   */\n  this.$get = ['$window', '$compile', '$timeout', '$document', '$uibPosition', '$interpolate', '$rootScope', '$parse', '$$stackedMap', function($window, $compile, $timeout, $document, $position, $interpolate, $rootScope, $parse, $$stackedMap) {\n    var openedTooltips = $$stackedMap.createNew();\n    $document.on('keyup', keypressListener);\n\n    $rootScope.$on('$destroy', function() {\n      $document.off('keyup', keypressListener);\n    });\n\n    function keypressListener(e) {\n      if (e.which === 27) {\n        var last = openedTooltips.top();\n        if (last) {\n          last.value.close();\n          last = null;\n        }\n      }\n    }\n\n    return function $tooltip(ttType, prefix, defaultTriggerShow, options) {\n      options = angular.extend({}, defaultOptions, globalOptions, options);\n\n      /**\n       * Returns an object of show and hide triggers.\n       *\n       * If a trigger is supplied,\n       * it is used to show the tooltip; otherwise, it will use the `trigger`\n       * option passed to the `$tooltipProvider.options` method; else it will\n       * default to the trigger supplied to this directive factory.\n       *\n       * The hide trigger is based on the show trigger. If the `trigger` option\n       * was passed to the `$tooltipProvider.options` method, it will use the\n       * mapped trigger from `triggerMap` or the passed trigger if the map is\n       * undefined; otherwise, it uses the `triggerMap` value of the show\n       * trigger; else it will just use the show trigger.\n       */\n      function getTriggers(trigger) {\n        var show = (trigger || options.trigger || defaultTriggerShow).split(' ');\n        var hide = show.map(function(trigger) {\n          return triggerMap[trigger] || trigger;\n        });\n        return {\n          show: show,\n          hide: hide\n        };\n      }\n\n      var directiveName = snake_case(ttType);\n\n      var startSym = $interpolate.startSymbol();\n      var endSym = $interpolate.endSymbol();\n      var template =\n        '<div '+ directiveName + '-popup ' +\n          'uib-title=\"' + startSym + 'title' + endSym + '\" ' +\n          (options.useContentExp ?\n            'content-exp=\"contentExp()\" ' :\n            'content=\"' + startSym + 'content' + endSym + '\" ') +\n          'origin-scope=\"origScope\" ' +\n          'class=\"uib-position-measure ' + prefix + '\" ' +\n          'tooltip-animation-class=\"fade\"' +\n          'uib-tooltip-classes ' +\n          'ng-class=\"{ in: isOpen }\" ' +\n          '>' +\n        '</div>';\n\n      return {\n        compile: function(tElem, tAttrs) {\n          var tooltipLinker = $compile(template);\n\n          return function link(scope, element, attrs, tooltipCtrl) {\n            var tooltip;\n            var tooltipLinkedScope;\n            var transitionTimeout;\n            var showTimeout;\n            var hideTimeout;\n            var positionTimeout;\n            var adjustmentTimeout;\n            var appendToBody = angular.isDefined(options.appendToBody) ? options.appendToBody : false;\n            var triggers = getTriggers(undefined);\n            var hasEnableExp = angular.isDefined(attrs[prefix + 'Enable']);\n            var ttScope = scope.$new(true);\n            var repositionScheduled = false;\n            var isOpenParse = angular.isDefined(attrs[prefix + 'IsOpen']) ? $parse(attrs[prefix + 'IsOpen']) : false;\n            var contentParse = options.useContentExp ? $parse(attrs[ttType]) : false;\n            var observers = [];\n            var lastPlacement;\n\n            var positionTooltip = function() {\n              // check if tooltip exists and is not empty\n              if (!tooltip || !tooltip.html()) { return; }\n\n              if (!positionTimeout) {\n                positionTimeout = $timeout(function() {\n                  var ttPosition = $position.positionElements(element, tooltip, ttScope.placement, appendToBody);\n                  var initialHeight = angular.isDefined(tooltip.offsetHeight) ? tooltip.offsetHeight : tooltip.prop('offsetHeight');\n                  var elementPos = appendToBody ? $position.offset(element) : $position.position(element);\n                  tooltip.css({ top: ttPosition.top + 'px', left: ttPosition.left + 'px' });\n                  var placementClasses = ttPosition.placement.split('-');\n\n                  if (!tooltip.hasClass(placementClasses[0])) {\n                    tooltip.removeClass(lastPlacement.split('-')[0]);\n                    tooltip.addClass(placementClasses[0]);\n                  }\n\n                  if (!tooltip.hasClass(options.placementClassPrefix + ttPosition.placement)) {\n                    tooltip.removeClass(options.placementClassPrefix + lastPlacement);\n                    tooltip.addClass(options.placementClassPrefix + ttPosition.placement);\n                  }\n\n                  adjustmentTimeout = $timeout(function() {\n                    var currentHeight = angular.isDefined(tooltip.offsetHeight) ? tooltip.offsetHeight : tooltip.prop('offsetHeight');\n                    var adjustment = $position.adjustTop(placementClasses, elementPos, initialHeight, currentHeight);\n                    if (adjustment) {\n                      tooltip.css(adjustment);\n                    }\n                    adjustmentTimeout = null;\n                  }, 0, false);\n\n                  // first time through tt element will have the\n                  // uib-position-measure class or if the placement\n                  // has changed we need to position the arrow.\n                  if (tooltip.hasClass('uib-position-measure')) {\n                    $position.positionArrow(tooltip, ttPosition.placement);\n                    tooltip.removeClass('uib-position-measure');\n                  } else if (lastPlacement !== ttPosition.placement) {\n                    $position.positionArrow(tooltip, ttPosition.placement);\n                  }\n                  lastPlacement = ttPosition.placement;\n\n                  positionTimeout = null;\n                }, 0, false);\n              }\n            };\n\n            // Set up the correct scope to allow transclusion later\n            ttScope.origScope = scope;\n\n            // By default, the tooltip is not open.\n            // TODO add ability to start tooltip opened\n            ttScope.isOpen = false;\n\n            function toggleTooltipBind() {\n              if (!ttScope.isOpen) {\n                showTooltipBind();\n              } else {\n                hideTooltipBind();\n              }\n            }\n\n            // Show the tooltip with delay if specified, otherwise show it immediately\n            function showTooltipBind() {\n              if (hasEnableExp && !scope.$eval(attrs[prefix + 'Enable'])) {\n                return;\n              }\n\n              cancelHide();\n              prepareTooltip();\n\n              if (ttScope.popupDelay) {\n                // Do nothing if the tooltip was already scheduled to pop-up.\n                // This happens if show is triggered multiple times before any hide is triggered.\n                if (!showTimeout) {\n                  showTimeout = $timeout(show, ttScope.popupDelay, false);\n                }\n              } else {\n                show();\n              }\n            }\n\n            function hideTooltipBind() {\n              cancelShow();\n\n              if (ttScope.popupCloseDelay) {\n                if (!hideTimeout) {\n                  hideTimeout = $timeout(hide, ttScope.popupCloseDelay, false);\n                }\n              } else {\n                hide();\n              }\n            }\n\n            // Show the tooltip popup element.\n            function show() {\n              cancelShow();\n              cancelHide();\n\n              // Don't show empty tooltips.\n              if (!ttScope.content) {\n                return angular.noop;\n              }\n\n              createTooltip();\n\n              // And show the tooltip.\n              ttScope.$evalAsync(function() {\n                ttScope.isOpen = true;\n                assignIsOpen(true);\n                positionTooltip();\n              });\n            }\n\n            function cancelShow() {\n              if (showTimeout) {\n                $timeout.cancel(showTimeout);\n                showTimeout = null;\n              }\n\n              if (positionTimeout) {\n                $timeout.cancel(positionTimeout);\n                positionTimeout = null;\n              }\n            }\n\n            // Hide the tooltip popup element.\n            function hide() {\n              if (!ttScope) {\n                return;\n              }\n\n              // First things first: we don't show it anymore.\n              ttScope.$evalAsync(function() {\n                if (ttScope) {\n                  ttScope.isOpen = false;\n                  assignIsOpen(false);\n                  // And now we remove it from the DOM. However, if we have animation, we\n                  // need to wait for it to expire beforehand.\n                  // FIXME: this is a placeholder for a port of the transitions library.\n                  // The fade transition in TWBS is 150ms.\n                  if (ttScope.animation) {\n                    if (!transitionTimeout) {\n                      transitionTimeout = $timeout(removeTooltip, 150, false);\n                    }\n                  } else {\n                    removeTooltip();\n                  }\n                }\n              });\n            }\n\n            function cancelHide() {\n              if (hideTimeout) {\n                $timeout.cancel(hideTimeout);\n                hideTimeout = null;\n              }\n\n              if (transitionTimeout) {\n                $timeout.cancel(transitionTimeout);\n                transitionTimeout = null;\n              }\n            }\n\n            function createTooltip() {\n              // There can only be one tooltip element per directive shown at once.\n              if (tooltip) {\n                return;\n              }\n\n              tooltipLinkedScope = ttScope.$new();\n              tooltip = tooltipLinker(tooltipLinkedScope, function(tooltip) {\n                if (appendToBody) {\n                  $document.find('body').append(tooltip);\n                } else {\n                  element.after(tooltip);\n                }\n              });\n\n              openedTooltips.add(ttScope, {\n                close: hide\n              });\n\n              prepObservers();\n            }\n\n            function removeTooltip() {\n              cancelShow();\n              cancelHide();\n              unregisterObservers();\n\n              if (tooltip) {\n                tooltip.remove();\n                \n                tooltip = null;\n                if (adjustmentTimeout) {\n                  $timeout.cancel(adjustmentTimeout);\n                }\n              }\n\n              openedTooltips.remove(ttScope);\n              \n              if (tooltipLinkedScope) {\n                tooltipLinkedScope.$destroy();\n                tooltipLinkedScope = null;\n              }\n            }\n\n            /**\n             * Set the initial scope values. Once\n             * the tooltip is created, the observers\n             * will be added to keep things in sync.\n             */\n            function prepareTooltip() {\n              ttScope.title = attrs[prefix + 'Title'];\n              if (contentParse) {\n                ttScope.content = contentParse(scope);\n              } else {\n                ttScope.content = attrs[ttType];\n              }\n\n              ttScope.popupClass = attrs[prefix + 'Class'];\n              ttScope.placement = angular.isDefined(attrs[prefix + 'Placement']) ? attrs[prefix + 'Placement'] : options.placement;\n              var placement = $position.parsePlacement(ttScope.placement);\n              lastPlacement = placement[1] ? placement[0] + '-' + placement[1] : placement[0];\n\n              var delay = parseInt(attrs[prefix + 'PopupDelay'], 10);\n              var closeDelay = parseInt(attrs[prefix + 'PopupCloseDelay'], 10);\n              ttScope.popupDelay = !isNaN(delay) ? delay : options.popupDelay;\n              ttScope.popupCloseDelay = !isNaN(closeDelay) ? closeDelay : options.popupCloseDelay;\n            }\n\n            function assignIsOpen(isOpen) {\n              if (isOpenParse && angular.isFunction(isOpenParse.assign)) {\n                isOpenParse.assign(scope, isOpen);\n              }\n            }\n\n            ttScope.contentExp = function() {\n              return ttScope.content;\n            };\n\n            /**\n             * Observe the relevant attributes.\n             */\n            attrs.$observe('disabled', function(val) {\n              if (val) {\n                cancelShow();\n              }\n\n              if (val && ttScope.isOpen) {\n                hide();\n              }\n            });\n\n            if (isOpenParse) {\n              scope.$watch(isOpenParse, function(val) {\n                if (ttScope && !val === ttScope.isOpen) {\n                  toggleTooltipBind();\n                }\n              });\n            }\n\n            function prepObservers() {\n              observers.length = 0;\n\n              if (contentParse) {\n                observers.push(\n                  scope.$watch(contentParse, function(val) {\n                    ttScope.content = val;\n                    if (!val && ttScope.isOpen) {\n                      hide();\n                    }\n                  })\n                );\n\n                observers.push(\n                  tooltipLinkedScope.$watch(function() {\n                    if (!repositionScheduled) {\n                      repositionScheduled = true;\n                      tooltipLinkedScope.$$postDigest(function() {\n                        repositionScheduled = false;\n                        if (ttScope && ttScope.isOpen) {\n                          positionTooltip();\n                        }\n                      });\n                    }\n                  })\n                );\n              } else {\n                observers.push(\n                  attrs.$observe(ttType, function(val) {\n                    ttScope.content = val;\n                    if (!val && ttScope.isOpen) {\n                      hide();\n                    } else {\n                      positionTooltip();\n                    }\n                  })\n                );\n              }\n\n              observers.push(\n                attrs.$observe(prefix + 'Title', function(val) {\n                  ttScope.title = val;\n                  if (ttScope.isOpen) {\n                    positionTooltip();\n                  }\n                })\n              );\n\n              observers.push(\n                attrs.$observe(prefix + 'Placement', function(val) {\n                  ttScope.placement = val ? val : options.placement;\n                  if (ttScope.isOpen) {\n                    positionTooltip();\n                  }\n                })\n              );\n            }\n\n            function unregisterObservers() {\n              if (observers.length) {\n                angular.forEach(observers, function(observer) {\n                  observer();\n                });\n                observers.length = 0;\n              }\n            }\n\n            // hide tooltips/popovers for outsideClick trigger\n            function bodyHideTooltipBind(e) {\n              if (!ttScope || !ttScope.isOpen || !tooltip) {\n                return;\n              }\n              // make sure the tooltip/popover link or tool tooltip/popover itself were not clicked\n              if (!element[0].contains(e.target) && !tooltip[0].contains(e.target)) {\n                hideTooltipBind();\n              }\n            }\n\n            // KeyboardEvent handler to hide the tooltip on Escape key press\n            function hideOnEscapeKey(e) {\n              if (e.which === 27) {\n                hideTooltipBind();\n              }\n            }\n\n            var unregisterTriggers = function() {\n              triggers.show.forEach(function(trigger) {\n                if (trigger === 'outsideClick') {\n                  element.off('click', toggleTooltipBind);\n                } else {\n                  element.off(trigger, showTooltipBind);\n                  element.off(trigger, toggleTooltipBind);\n                }\n                element.off('keypress', hideOnEscapeKey);\n              });\n              triggers.hide.forEach(function(trigger) {\n                if (trigger === 'outsideClick') {\n                  $document.off('click', bodyHideTooltipBind);\n                } else {\n                  element.off(trigger, hideTooltipBind);\n                }\n              });\n            };\n\n            function prepTriggers() {\n              var showTriggers = [], hideTriggers = [];\n              var val = scope.$eval(attrs[prefix + 'Trigger']);\n              unregisterTriggers();\n\n              if (angular.isObject(val)) {\n                Object.keys(val).forEach(function(key) {\n                  showTriggers.push(key);\n                  hideTriggers.push(val[key]);\n                });\n                triggers = {\n                  show: showTriggers,\n                  hide: hideTriggers\n                };\n              } else {\n                triggers = getTriggers(val);\n              }\n\n              if (triggers.show !== 'none') {\n                triggers.show.forEach(function(trigger, idx) {\n                  if (trigger === 'outsideClick') {\n                    element.on('click', toggleTooltipBind);\n                    $document.on('click', bodyHideTooltipBind);\n                  } else if (trigger === triggers.hide[idx]) {\n                    element.on(trigger, toggleTooltipBind);\n                  } else if (trigger) {\n                    element.on(trigger, showTooltipBind);\n                    element.on(triggers.hide[idx], hideTooltipBind);\n                  }\n                  element.on('keypress', hideOnEscapeKey);\n                });\n              }\n            }\n\n            prepTriggers();\n\n            var animation = scope.$eval(attrs[prefix + 'Animation']);\n            ttScope.animation = angular.isDefined(animation) ? !!animation : options.animation;\n\n            var appendToBodyVal;\n            var appendKey = prefix + 'AppendToBody';\n            if (appendKey in attrs && attrs[appendKey] === undefined) {\n              appendToBodyVal = true;\n            } else {\n              appendToBodyVal = scope.$eval(attrs[appendKey]);\n            }\n\n            appendToBody = angular.isDefined(appendToBodyVal) ? appendToBodyVal : appendToBody;\n\n            // Make sure tooltip is destroyed and removed.\n            scope.$on('$destroy', function onDestroyTooltip() {\n              unregisterTriggers();\n              removeTooltip();\n              ttScope = null;\n            });\n          };\n        }\n      };\n    };\n  }];\n})\n\n// This is mostly ngInclude code but with a custom scope\n.directive('uibTooltipTemplateTransclude', [\n         '$animate', '$sce', '$compile', '$templateRequest',\nfunction ($animate, $sce, $compile, $templateRequest) {\n  return {\n    link: function(scope, elem, attrs) {\n      var origScope = scope.$eval(attrs.tooltipTemplateTranscludeScope);\n\n      var changeCounter = 0,\n        currentScope,\n        previousElement,\n        currentElement;\n\n      var cleanupLastIncludeContent = function() {\n        if (previousElement) {\n          previousElement.remove();\n          previousElement = null;\n        }\n\n        if (currentScope) {\n          currentScope.$destroy();\n          currentScope = null;\n        }\n\n        if (currentElement) {\n          $animate.leave(currentElement).then(function() {\n            previousElement = null;\n          });\n          previousElement = currentElement;\n          currentElement = null;\n        }\n      };\n\n      scope.$watch($sce.parseAsResourceUrl(attrs.uibTooltipTemplateTransclude), function(src) {\n        var thisChangeId = ++changeCounter;\n\n        if (src) {\n          //set the 2nd param to true to ignore the template request error so that the inner\n          //contents and scope can be cleaned up.\n          $templateRequest(src, true).then(function(response) {\n            if (thisChangeId !== changeCounter) { return; }\n            var newScope = origScope.$new();\n            var template = response;\n\n            var clone = $compile(template)(newScope, function(clone) {\n              cleanupLastIncludeContent();\n              $animate.enter(clone, elem);\n            });\n\n            currentScope = newScope;\n            currentElement = clone;\n\n            currentScope.$emit('$includeContentLoaded', src);\n          }, function() {\n            if (thisChangeId === changeCounter) {\n              cleanupLastIncludeContent();\n              scope.$emit('$includeContentError', src);\n            }\n          });\n          scope.$emit('$includeContentRequested', src);\n        } else {\n          cleanupLastIncludeContent();\n        }\n      });\n\n      scope.$on('$destroy', cleanupLastIncludeContent);\n    }\n  };\n}])\n\n/**\n * Note that it's intentional that these classes are *not* applied through $animate.\n * They must not be animated as they're expected to be present on the tooltip on\n * initialization.\n */\n.directive('uibTooltipClasses', ['$uibPosition', function($uibPosition) {\n  return {\n    restrict: 'A',\n    link: function(scope, element, attrs) {\n      // need to set the primary position so the\n      // arrow has space during position measure.\n      // tooltip.positionTooltip()\n      if (scope.placement) {\n        // // There are no top-left etc... classes\n        // // in TWBS, so we need the primary position.\n        var position = $uibPosition.parsePlacement(scope.placement);\n        element.addClass(position[0]);\n      }\n\n      if (scope.popupClass) {\n        element.addClass(scope.popupClass);\n      }\n\n      if (scope.animation) {\n        element.addClass(attrs.tooltipAnimationClass);\n      }\n    }\n  };\n}])\n\n.directive('uibTooltipPopup', function() {\n  return {\n    restrict: 'A',\n    scope: { content: '@' },\n    templateUrl: 'uib/template/tooltip/tooltip-popup.html'\n  };\n})\n\n.directive('uibTooltip', [ '$uibTooltip', function($uibTooltip) {\n  return $uibTooltip('uibTooltip', 'tooltip', 'mouseenter');\n}])\n\n.directive('uibTooltipTemplatePopup', function() {\n  return {\n    restrict: 'A',\n    scope: { contentExp: '&', originScope: '&' },\n    templateUrl: 'uib/template/tooltip/tooltip-template-popup.html'\n  };\n})\n\n.directive('uibTooltipTemplate', ['$uibTooltip', function($uibTooltip) {\n  return $uibTooltip('uibTooltipTemplate', 'tooltip', 'mouseenter', {\n    useContentExp: true\n  });\n}])\n\n.directive('uibTooltipHtmlPopup', function() {\n  return {\n    restrict: 'A',\n    scope: { contentExp: '&' },\n    templateUrl: 'uib/template/tooltip/tooltip-html-popup.html'\n  };\n})\n\n.directive('uibTooltipHtml', ['$uibTooltip', function($uibTooltip) {\n  return $uibTooltip('uibTooltipHtml', 'tooltip', 'mouseenter', {\n    useContentExp: true\n  });\n}]);\n\n/**\n * The following features are still outstanding: popup delay, animation as a\n * function, placement as a function, inside, support for more triggers than\n * just mouse enter/leave, and selector delegatation.\n */\nangular.module('ui.bootstrap.popover', ['ui.bootstrap.tooltip'])\n\n.directive('uibPopoverTemplatePopup', function() {\n  return {\n    restrict: 'A',\n    scope: { uibTitle: '@', contentExp: '&', originScope: '&' },\n    templateUrl: 'uib/template/popover/popover-template.html'\n  };\n})\n\n.directive('uibPopoverTemplate', ['$uibTooltip', function($uibTooltip) {\n  return $uibTooltip('uibPopoverTemplate', 'popover', 'click', {\n    useContentExp: true\n  });\n}])\n\n.directive('uibPopoverHtmlPopup', function() {\n  return {\n    restrict: 'A',\n    scope: { contentExp: '&', uibTitle: '@' },\n    templateUrl: 'uib/template/popover/popover-html.html'\n  };\n})\n\n.directive('uibPopoverHtml', ['$uibTooltip', function($uibTooltip) {\n  return $uibTooltip('uibPopoverHtml', 'popover', 'click', {\n    useContentExp: true\n  });\n}])\n\n.directive('uibPopoverPopup', function() {\n  return {\n    restrict: 'A',\n    scope: { uibTitle: '@', content: '@' },\n    templateUrl: 'uib/template/popover/popover.html'\n  };\n})\n\n.directive('uibPopover', ['$uibTooltip', function($uibTooltip) {\n  return $uibTooltip('uibPopover', 'popover', 'click');\n}]);\n\nangular.module('ui.bootstrap.progressbar', [])\n\n.constant('uibProgressConfig', {\n  animate: true,\n  max: 100\n})\n\n.controller('UibProgressController', ['$scope', '$attrs', 'uibProgressConfig', function($scope, $attrs, progressConfig) {\n  var self = this,\n      animate = angular.isDefined($attrs.animate) ? $scope.$parent.$eval($attrs.animate) : progressConfig.animate;\n\n  this.bars = [];\n  $scope.max = getMaxOrDefault();\n\n  this.addBar = function(bar, element, attrs) {\n    if (!animate) {\n      element.css({'transition': 'none'});\n    }\n\n    this.bars.push(bar);\n\n    bar.max = getMaxOrDefault();\n    bar.title = attrs && angular.isDefined(attrs.title) ? attrs.title : 'progressbar';\n\n    bar.$watch('value', function(value) {\n      bar.recalculatePercentage();\n    });\n\n    bar.recalculatePercentage = function() {\n      var totalPercentage = self.bars.reduce(function(total, bar) {\n        bar.percent = +(100 * bar.value / bar.max).toFixed(2);\n        return total + bar.percent;\n      }, 0);\n\n      if (totalPercentage > 100) {\n        bar.percent -= totalPercentage - 100;\n      }\n    };\n\n    bar.$on('$destroy', function() {\n      element = null;\n      self.removeBar(bar);\n    });\n  };\n\n  this.removeBar = function(bar) {\n    this.bars.splice(this.bars.indexOf(bar), 1);\n    this.bars.forEach(function (bar) {\n      bar.recalculatePercentage();\n    });\n  };\n\n  //$attrs.$observe('maxParam', function(maxParam) {\n  $scope.$watch('maxParam', function(maxParam) {\n    self.bars.forEach(function(bar) {\n      bar.max = getMaxOrDefault();\n      bar.recalculatePercentage();\n    });\n  });\n\n  function getMaxOrDefault () {\n    return angular.isDefined($scope.maxParam) ? $scope.maxParam : progressConfig.max;\n  }\n}])\n\n.directive('uibProgress', function() {\n  return {\n    replace: true,\n    transclude: true,\n    controller: 'UibProgressController',\n    require: 'uibProgress',\n    scope: {\n      maxParam: '=?max'\n    },\n    templateUrl: 'uib/template/progressbar/progress.html'\n  };\n})\n\n.directive('uibBar', function() {\n  return {\n    replace: true,\n    transclude: true,\n    require: '^uibProgress',\n    scope: {\n      value: '=',\n      type: '@'\n    },\n    templateUrl: 'uib/template/progressbar/bar.html',\n    link: function(scope, element, attrs, progressCtrl) {\n      progressCtrl.addBar(scope, element, attrs);\n    }\n  };\n})\n\n.directive('uibProgressbar', function() {\n  return {\n    replace: true,\n    transclude: true,\n    controller: 'UibProgressController',\n    scope: {\n      value: '=',\n      maxParam: '=?max',\n      type: '@'\n    },\n    templateUrl: 'uib/template/progressbar/progressbar.html',\n    link: function(scope, element, attrs, progressCtrl) {\n      progressCtrl.addBar(scope, angular.element(element.children()[0]), {title: attrs.title});\n    }\n  };\n});\n\nangular.module('ui.bootstrap.rating', [])\n\n.constant('uibRatingConfig', {\n  max: 5,\n  stateOn: null,\n  stateOff: null,\n  enableReset: true,\n  titles: ['one', 'two', 'three', 'four', 'five']\n})\n\n.controller('UibRatingController', ['$scope', '$attrs', 'uibRatingConfig', function($scope, $attrs, ratingConfig) {\n  var ngModelCtrl = { $setViewValue: angular.noop },\n    self = this;\n\n  this.init = function(ngModelCtrl_) {\n    ngModelCtrl = ngModelCtrl_;\n    ngModelCtrl.$render = this.render;\n\n    ngModelCtrl.$formatters.push(function(value) {\n      if (angular.isNumber(value) && value << 0 !== value) {\n        value = Math.round(value);\n      }\n\n      return value;\n    });\n\n    this.stateOn = angular.isDefined($attrs.stateOn) ? $scope.$parent.$eval($attrs.stateOn) : ratingConfig.stateOn;\n    this.stateOff = angular.isDefined($attrs.stateOff) ? $scope.$parent.$eval($attrs.stateOff) : ratingConfig.stateOff;\n    this.enableReset = angular.isDefined($attrs.enableReset) ?\n      $scope.$parent.$eval($attrs.enableReset) : ratingConfig.enableReset;\n    var tmpTitles = angular.isDefined($attrs.titles) ? $scope.$parent.$eval($attrs.titles) : ratingConfig.titles;\n    this.titles = angular.isArray(tmpTitles) && tmpTitles.length > 0 ?\n      tmpTitles : ratingConfig.titles;\n\n    var ratingStates = angular.isDefined($attrs.ratingStates) ?\n      $scope.$parent.$eval($attrs.ratingStates) :\n      new Array(angular.isDefined($attrs.max) ? $scope.$parent.$eval($attrs.max) : ratingConfig.max);\n    $scope.range = this.buildTemplateObjects(ratingStates);\n  };\n\n  this.buildTemplateObjects = function(states) {\n    for (var i = 0, n = states.length; i < n; i++) {\n      states[i] = angular.extend({ index: i }, { stateOn: this.stateOn, stateOff: this.stateOff, title: this.getTitle(i) }, states[i]);\n    }\n    return states;\n  };\n\n  this.getTitle = function(index) {\n    if (index >= this.titles.length) {\n      return index + 1;\n    }\n\n    return this.titles[index];\n  };\n\n  $scope.rate = function(value) {\n    if (!$scope.readonly && value >= 0 && value <= $scope.range.length) {\n      var newViewValue = self.enableReset && ngModelCtrl.$viewValue === value ? 0 : value;\n      ngModelCtrl.$setViewValue(newViewValue);\n      ngModelCtrl.$render();\n    }\n  };\n\n  $scope.enter = function(value) {\n    if (!$scope.readonly) {\n      $scope.value = value;\n    }\n    $scope.onHover({value: value});\n  };\n\n  $scope.reset = function() {\n    $scope.value = ngModelCtrl.$viewValue;\n    $scope.onLeave();\n  };\n\n  $scope.onKeydown = function(evt) {\n    if (/(37|38|39|40)/.test(evt.which)) {\n      evt.preventDefault();\n      evt.stopPropagation();\n      $scope.rate($scope.value + (evt.which === 38 || evt.which === 39 ? 1 : -1));\n    }\n  };\n\n  this.render = function() {\n    $scope.value = ngModelCtrl.$viewValue;\n    $scope.title = self.getTitle($scope.value - 1);\n  };\n}])\n\n.directive('uibRating', function() {\n  return {\n    require: ['uibRating', 'ngModel'],\n    restrict: 'A',\n    scope: {\n      readonly: '=?readOnly',\n      onHover: '&',\n      onLeave: '&'\n    },\n    controller: 'UibRatingController',\n    templateUrl: 'uib/template/rating/rating.html',\n    link: function(scope, element, attrs, ctrls) {\n      var ratingCtrl = ctrls[0], ngModelCtrl = ctrls[1];\n      ratingCtrl.init(ngModelCtrl);\n    }\n  };\n});\n\nangular.module('ui.bootstrap.tabs', [])\n\n.controller('UibTabsetController', ['$scope', function ($scope) {\n  var ctrl = this,\n    oldIndex;\n  ctrl.tabs = [];\n\n  ctrl.select = function(index, evt) {\n    if (!destroyed) {\n      var previousIndex = findTabIndex(oldIndex);\n      var previousSelected = ctrl.tabs[previousIndex];\n      if (previousSelected) {\n        previousSelected.tab.onDeselect({\n          $event: evt,\n          $selectedIndex: index\n        });\n        if (evt && evt.isDefaultPrevented()) {\n          return;\n        }\n        previousSelected.tab.active = false;\n      }\n\n      var selected = ctrl.tabs[index];\n      if (selected) {\n        selected.tab.onSelect({\n          $event: evt\n        });\n        selected.tab.active = true;\n        ctrl.active = selected.index;\n        oldIndex = selected.index;\n      } else if (!selected && angular.isDefined(oldIndex)) {\n        ctrl.active = null;\n        oldIndex = null;\n      }\n    }\n  };\n\n  ctrl.addTab = function addTab(tab) {\n    ctrl.tabs.push({\n      tab: tab,\n      index: tab.index\n    });\n    ctrl.tabs.sort(function(t1, t2) {\n      if (t1.index > t2.index) {\n        return 1;\n      }\n\n      if (t1.index < t2.index) {\n        return -1;\n      }\n\n      return 0;\n    });\n\n    if (tab.index === ctrl.active || !angular.isDefined(ctrl.active) && ctrl.tabs.length === 1) {\n      var newActiveIndex = findTabIndex(tab.index);\n      ctrl.select(newActiveIndex);\n    }\n  };\n\n  ctrl.removeTab = function removeTab(tab) {\n    var index;\n    for (var i = 0; i < ctrl.tabs.length; i++) {\n      if (ctrl.tabs[i].tab === tab) {\n        index = i;\n        break;\n      }\n    }\n\n    if (ctrl.tabs[index].index === ctrl.active) {\n      var newActiveTabIndex = index === ctrl.tabs.length - 1 ?\n        index - 1 : index + 1 % ctrl.tabs.length;\n      ctrl.select(newActiveTabIndex);\n    }\n\n    ctrl.tabs.splice(index, 1);\n  };\n\n  $scope.$watch('tabset.active', function(val) {\n    if (angular.isDefined(val) && val !== oldIndex) {\n      ctrl.select(findTabIndex(val));\n    }\n  });\n\n  var destroyed;\n  $scope.$on('$destroy', function() {\n    destroyed = true;\n  });\n\n  function findTabIndex(index) {\n    for (var i = 0; i < ctrl.tabs.length; i++) {\n      if (ctrl.tabs[i].index === index) {\n        return i;\n      }\n    }\n  }\n}])\n\n.directive('uibTabset', function() {\n  return {\n    transclude: true,\n    replace: true,\n    scope: {},\n    bindToController: {\n      active: '=?',\n      type: '@'\n    },\n    controller: 'UibTabsetController',\n    controllerAs: 'tabset',\n    templateUrl: function(element, attrs) {\n      return attrs.templateUrl || 'uib/template/tabs/tabset.html';\n    },\n    link: function(scope, element, attrs) {\n      scope.vertical = angular.isDefined(attrs.vertical) ?\n        scope.$parent.$eval(attrs.vertical) : false;\n      scope.justified = angular.isDefined(attrs.justified) ?\n        scope.$parent.$eval(attrs.justified) : false;\n    }\n  };\n})\n\n.directive('uibTab', ['$parse', function($parse) {\n  return {\n    require: '^uibTabset',\n    replace: true,\n    templateUrl: function(element, attrs) {\n      return attrs.templateUrl || 'uib/template/tabs/tab.html';\n    },\n    transclude: true,\n    scope: {\n      heading: '@',\n      index: '=?',\n      classes: '@?',\n      onSelect: '&select', //This callback is called in contentHeadingTransclude\n                          //once it inserts the tab's content into the dom\n      onDeselect: '&deselect'\n    },\n    controller: function() {\n      //Empty controller so other directives can require being 'under' a tab\n    },\n    controllerAs: 'tab',\n    link: function(scope, elm, attrs, tabsetCtrl, transclude) {\n      scope.disabled = false;\n      if (attrs.disable) {\n        scope.$parent.$watch($parse(attrs.disable), function(value) {\n          scope.disabled = !! value;\n        });\n      }\n\n      if (angular.isUndefined(attrs.index)) {\n        if (tabsetCtrl.tabs && tabsetCtrl.tabs.length) {\n          scope.index = Math.max.apply(null, tabsetCtrl.tabs.map(function(t) { return t.index; })) + 1;\n        } else {\n          scope.index = 0;\n        }\n      }\n\n      if (angular.isUndefined(attrs.classes)) {\n        scope.classes = '';\n      }\n\n      scope.select = function(evt) {\n        if (!scope.disabled) {\n          var index;\n          for (var i = 0; i < tabsetCtrl.tabs.length; i++) {\n            if (tabsetCtrl.tabs[i].tab === scope) {\n              index = i;\n              break;\n            }\n          }\n\n          tabsetCtrl.select(index, evt);\n        }\n      };\n\n      tabsetCtrl.addTab(scope);\n      scope.$on('$destroy', function() {\n        tabsetCtrl.removeTab(scope);\n      });\n\n      //We need to transclude later, once the content container is ready.\n      //when this link happens, we're inside a tab heading.\n      scope.$transcludeFn = transclude;\n    }\n  };\n}])\n\n.directive('uibTabHeadingTransclude', function() {\n  return {\n    restrict: 'A',\n    require: '^uibTab',\n    link: function(scope, elm) {\n      scope.$watch('headingElement', function updateHeadingElement(heading) {\n        if (heading) {\n          elm.html('');\n          elm.append(heading);\n        }\n      });\n    }\n  };\n})\n\n.directive('uibTabContentTransclude', function() {\n  return {\n    restrict: 'A',\n    require: '^uibTabset',\n    link: function(scope, elm, attrs) {\n      var tab = scope.$eval(attrs.uibTabContentTransclude).tab;\n\n      //Now our tab is ready to be transcluded: both the tab heading area\n      //and the tab content area are loaded.  Transclude 'em both.\n      tab.$transcludeFn(tab.$parent, function(contents) {\n        angular.forEach(contents, function(node) {\n          if (isTabHeading(node)) {\n            //Let tabHeadingTransclude know.\n            tab.headingElement = node;\n          } else {\n            elm.append(node);\n          }\n        });\n      });\n    }\n  };\n\n  function isTabHeading(node) {\n    return node.tagName && (\n      node.hasAttribute('uib-tab-heading') ||\n      node.hasAttribute('data-uib-tab-heading') ||\n      node.hasAttribute('x-uib-tab-heading') ||\n      node.tagName.toLowerCase() === 'uib-tab-heading' ||\n      node.tagName.toLowerCase() === 'data-uib-tab-heading' ||\n      node.tagName.toLowerCase() === 'x-uib-tab-heading' ||\n      node.tagName.toLowerCase() === 'uib:tab-heading'\n    );\n  }\n});\n\nangular.module('ui.bootstrap.timepicker', [])\n\n.constant('uibTimepickerConfig', {\n  hourStep: 1,\n  minuteStep: 1,\n  secondStep: 1,\n  showMeridian: true,\n  showSeconds: false,\n  meridians: null,\n  readonlyInput: false,\n  mousewheel: true,\n  arrowkeys: true,\n  showSpinners: true,\n  templateUrl: 'uib/template/timepicker/timepicker.html'\n})\n\n.controller('UibTimepickerController', ['$scope', '$element', '$attrs', '$parse', '$log', '$locale', 'uibTimepickerConfig', function($scope, $element, $attrs, $parse, $log, $locale, timepickerConfig) {\n  var hoursModelCtrl, minutesModelCtrl, secondsModelCtrl;\n  var selected = new Date(),\n    watchers = [],\n    ngModelCtrl = { $setViewValue: angular.noop }, // nullModelCtrl\n    meridians = angular.isDefined($attrs.meridians) ? $scope.$parent.$eval($attrs.meridians) : timepickerConfig.meridians || $locale.DATETIME_FORMATS.AMPMS,\n    padHours = angular.isDefined($attrs.padHours) ? $scope.$parent.$eval($attrs.padHours) : true;\n\n  $scope.tabindex = angular.isDefined($attrs.tabindex) ? $attrs.tabindex : 0;\n  $element.removeAttr('tabindex');\n\n  this.init = function(ngModelCtrl_, inputs) {\n    ngModelCtrl = ngModelCtrl_;\n    ngModelCtrl.$render = this.render;\n\n    ngModelCtrl.$formatters.unshift(function(modelValue) {\n      return modelValue ? new Date(modelValue) : null;\n    });\n\n    var hoursInputEl = inputs.eq(0),\n        minutesInputEl = inputs.eq(1),\n        secondsInputEl = inputs.eq(2);\n\n    hoursModelCtrl = hoursInputEl.controller('ngModel');\n    minutesModelCtrl = minutesInputEl.controller('ngModel');\n    secondsModelCtrl = secondsInputEl.controller('ngModel');\n\n    var mousewheel = angular.isDefined($attrs.mousewheel) ? $scope.$parent.$eval($attrs.mousewheel) : timepickerConfig.mousewheel;\n\n    if (mousewheel) {\n      this.setupMousewheelEvents(hoursInputEl, minutesInputEl, secondsInputEl);\n    }\n\n    var arrowkeys = angular.isDefined($attrs.arrowkeys) ? $scope.$parent.$eval($attrs.arrowkeys) : timepickerConfig.arrowkeys;\n    if (arrowkeys) {\n      this.setupArrowkeyEvents(hoursInputEl, minutesInputEl, secondsInputEl);\n    }\n\n    $scope.readonlyInput = angular.isDefined($attrs.readonlyInput) ? $scope.$parent.$eval($attrs.readonlyInput) : timepickerConfig.readonlyInput;\n    this.setupInputEvents(hoursInputEl, minutesInputEl, secondsInputEl);\n  };\n\n  var hourStep = timepickerConfig.hourStep;\n  if ($attrs.hourStep) {\n    watchers.push($scope.$parent.$watch($parse($attrs.hourStep), function(value) {\n      hourStep = +value;\n    }));\n  }\n\n  var minuteStep = timepickerConfig.minuteStep;\n  if ($attrs.minuteStep) {\n    watchers.push($scope.$parent.$watch($parse($attrs.minuteStep), function(value) {\n      minuteStep = +value;\n    }));\n  }\n\n  var min;\n  watchers.push($scope.$parent.$watch($parse($attrs.min), function(value) {\n    var dt = new Date(value);\n    min = isNaN(dt) ? undefined : dt;\n  }));\n\n  var max;\n  watchers.push($scope.$parent.$watch($parse($attrs.max), function(value) {\n    var dt = new Date(value);\n    max = isNaN(dt) ? undefined : dt;\n  }));\n\n  var disabled = false;\n  if ($attrs.ngDisabled) {\n    watchers.push($scope.$parent.$watch($parse($attrs.ngDisabled), function(value) {\n      disabled = value;\n    }));\n  }\n\n  $scope.noIncrementHours = function() {\n    var incrementedSelected = addMinutes(selected, hourStep * 60);\n    return disabled || incrementedSelected > max ||\n      incrementedSelected < selected && incrementedSelected < min;\n  };\n\n  $scope.noDecrementHours = function() {\n    var decrementedSelected = addMinutes(selected, -hourStep * 60);\n    return disabled || decrementedSelected < min ||\n      decrementedSelected > selected && decrementedSelected > max;\n  };\n\n  $scope.noIncrementMinutes = function() {\n    var incrementedSelected = addMinutes(selected, minuteStep);\n    return disabled || incrementedSelected > max ||\n      incrementedSelected < selected && incrementedSelected < min;\n  };\n\n  $scope.noDecrementMinutes = function() {\n    var decrementedSelected = addMinutes(selected, -minuteStep);\n    return disabled || decrementedSelected < min ||\n      decrementedSelected > selected && decrementedSelected > max;\n  };\n\n  $scope.noIncrementSeconds = function() {\n    var incrementedSelected = addSeconds(selected, secondStep);\n    return disabled || incrementedSelected > max ||\n      incrementedSelected < selected && incrementedSelected < min;\n  };\n\n  $scope.noDecrementSeconds = function() {\n    var decrementedSelected = addSeconds(selected, -secondStep);\n    return disabled || decrementedSelected < min ||\n      decrementedSelected > selected && decrementedSelected > max;\n  };\n\n  $scope.noToggleMeridian = function() {\n    if (selected.getHours() < 12) {\n      return disabled || addMinutes(selected, 12 * 60) > max;\n    }\n\n    return disabled || addMinutes(selected, -12 * 60) < min;\n  };\n\n  var secondStep = timepickerConfig.secondStep;\n  if ($attrs.secondStep) {\n    watchers.push($scope.$parent.$watch($parse($attrs.secondStep), function(value) {\n      secondStep = +value;\n    }));\n  }\n\n  $scope.showSeconds = timepickerConfig.showSeconds;\n  if ($attrs.showSeconds) {\n    watchers.push($scope.$parent.$watch($parse($attrs.showSeconds), function(value) {\n      $scope.showSeconds = !!value;\n    }));\n  }\n\n  // 12H / 24H mode\n  $scope.showMeridian = timepickerConfig.showMeridian;\n  if ($attrs.showMeridian) {\n    watchers.push($scope.$parent.$watch($parse($attrs.showMeridian), function(value) {\n      $scope.showMeridian = !!value;\n\n      if (ngModelCtrl.$error.time) {\n        // Evaluate from template\n        var hours = getHoursFromTemplate(), minutes = getMinutesFromTemplate();\n        if (angular.isDefined(hours) && angular.isDefined(minutes)) {\n          selected.setHours(hours);\n          refresh();\n        }\n      } else {\n        updateTemplate();\n      }\n    }));\n  }\n\n  // Get $scope.hours in 24H mode if valid\n  function getHoursFromTemplate() {\n    var hours = +$scope.hours;\n    var valid = $scope.showMeridian ? hours > 0 && hours < 13 :\n      hours >= 0 && hours < 24;\n    if (!valid || $scope.hours === '') {\n      return undefined;\n    }\n\n    if ($scope.showMeridian) {\n      if (hours === 12) {\n        hours = 0;\n      }\n      if ($scope.meridian === meridians[1]) {\n        hours = hours + 12;\n      }\n    }\n    return hours;\n  }\n\n  function getMinutesFromTemplate() {\n    var minutes = +$scope.minutes;\n    var valid = minutes >= 0 && minutes < 60;\n    if (!valid || $scope.minutes === '') {\n      return undefined;\n    }\n    return minutes;\n  }\n\n  function getSecondsFromTemplate() {\n    var seconds = +$scope.seconds;\n    return seconds >= 0 && seconds < 60 ? seconds : undefined;\n  }\n\n  function pad(value, noPad) {\n    if (value === null) {\n      return '';\n    }\n\n    return angular.isDefined(value) && value.toString().length < 2 && !noPad ?\n      '0' + value : value.toString();\n  }\n\n  // Respond on mousewheel spin\n  this.setupMousewheelEvents = function(hoursInputEl, minutesInputEl, secondsInputEl) {\n    var isScrollingUp = function(e) {\n      if (e.originalEvent) {\n        e = e.originalEvent;\n      }\n      //pick correct delta variable depending on event\n      var delta = e.wheelDelta ? e.wheelDelta : -e.deltaY;\n      return e.detail || delta > 0;\n    };\n\n    hoursInputEl.on('mousewheel wheel', function(e) {\n      if (!disabled) {\n        $scope.$apply(isScrollingUp(e) ? $scope.incrementHours() : $scope.decrementHours());\n      }\n      e.preventDefault();\n    });\n\n    minutesInputEl.on('mousewheel wheel', function(e) {\n      if (!disabled) {\n        $scope.$apply(isScrollingUp(e) ? $scope.incrementMinutes() : $scope.decrementMinutes());\n      }\n      e.preventDefault();\n    });\n\n     secondsInputEl.on('mousewheel wheel', function(e) {\n      if (!disabled) {\n        $scope.$apply(isScrollingUp(e) ? $scope.incrementSeconds() : $scope.decrementSeconds());\n      }\n      e.preventDefault();\n    });\n  };\n\n  // Respond on up/down arrowkeys\n  this.setupArrowkeyEvents = function(hoursInputEl, minutesInputEl, secondsInputEl) {\n    hoursInputEl.on('keydown', function(e) {\n      if (!disabled) {\n        if (e.which === 38) { // up\n          e.preventDefault();\n          $scope.incrementHours();\n          $scope.$apply();\n        } else if (e.which === 40) { // down\n          e.preventDefault();\n          $scope.decrementHours();\n          $scope.$apply();\n        }\n      }\n    });\n\n    minutesInputEl.on('keydown', function(e) {\n      if (!disabled) {\n        if (e.which === 38) { // up\n          e.preventDefault();\n          $scope.incrementMinutes();\n          $scope.$apply();\n        } else if (e.which === 40) { // down\n          e.preventDefault();\n          $scope.decrementMinutes();\n          $scope.$apply();\n        }\n      }\n    });\n\n    secondsInputEl.on('keydown', function(e) {\n      if (!disabled) {\n        if (e.which === 38) { // up\n          e.preventDefault();\n          $scope.incrementSeconds();\n          $scope.$apply();\n        } else if (e.which === 40) { // down\n          e.preventDefault();\n          $scope.decrementSeconds();\n          $scope.$apply();\n        }\n      }\n    });\n  };\n\n  this.setupInputEvents = function(hoursInputEl, minutesInputEl, secondsInputEl) {\n    if ($scope.readonlyInput) {\n      $scope.updateHours = angular.noop;\n      $scope.updateMinutes = angular.noop;\n      $scope.updateSeconds = angular.noop;\n      return;\n    }\n\n    var invalidate = function(invalidHours, invalidMinutes, invalidSeconds) {\n      ngModelCtrl.$setViewValue(null);\n      ngModelCtrl.$setValidity('time', false);\n      if (angular.isDefined(invalidHours)) {\n        $scope.invalidHours = invalidHours;\n        if (hoursModelCtrl) {\n          hoursModelCtrl.$setValidity('hours', false);\n        }\n      }\n\n      if (angular.isDefined(invalidMinutes)) {\n        $scope.invalidMinutes = invalidMinutes;\n        if (minutesModelCtrl) {\n          minutesModelCtrl.$setValidity('minutes', false);\n        }\n      }\n\n      if (angular.isDefined(invalidSeconds)) {\n        $scope.invalidSeconds = invalidSeconds;\n        if (secondsModelCtrl) {\n          secondsModelCtrl.$setValidity('seconds', false);\n        }\n      }\n    };\n\n    $scope.updateHours = function() {\n      var hours = getHoursFromTemplate(),\n        minutes = getMinutesFromTemplate();\n\n      ngModelCtrl.$setDirty();\n\n      if (angular.isDefined(hours) && angular.isDefined(minutes)) {\n        selected.setHours(hours);\n        selected.setMinutes(minutes);\n        if (selected < min || selected > max) {\n          invalidate(true);\n        } else {\n          refresh('h');\n        }\n      } else {\n        invalidate(true);\n      }\n    };\n\n    hoursInputEl.on('blur', function(e) {\n      ngModelCtrl.$setTouched();\n      if (modelIsEmpty()) {\n        makeValid();\n      } else if ($scope.hours === null || $scope.hours === '') {\n        invalidate(true);\n      } else if (!$scope.invalidHours && $scope.hours < 10) {\n        $scope.$apply(function() {\n          $scope.hours = pad($scope.hours, !padHours);\n        });\n      }\n    });\n\n    $scope.updateMinutes = function() {\n      var minutes = getMinutesFromTemplate(),\n        hours = getHoursFromTemplate();\n\n      ngModelCtrl.$setDirty();\n\n      if (angular.isDefined(minutes) && angular.isDefined(hours)) {\n        selected.setHours(hours);\n        selected.setMinutes(minutes);\n        if (selected < min || selected > max) {\n          invalidate(undefined, true);\n        } else {\n          refresh('m');\n        }\n      } else {\n        invalidate(undefined, true);\n      }\n    };\n\n    minutesInputEl.on('blur', function(e) {\n      ngModelCtrl.$setTouched();\n      if (modelIsEmpty()) {\n        makeValid();\n      } else if ($scope.minutes === null) {\n        invalidate(undefined, true);\n      } else if (!$scope.invalidMinutes && $scope.minutes < 10) {\n        $scope.$apply(function() {\n          $scope.minutes = pad($scope.minutes);\n        });\n      }\n    });\n\n    $scope.updateSeconds = function() {\n      var seconds = getSecondsFromTemplate();\n\n      ngModelCtrl.$setDirty();\n\n      if (angular.isDefined(seconds)) {\n        selected.setSeconds(seconds);\n        refresh('s');\n      } else {\n        invalidate(undefined, undefined, true);\n      }\n    };\n\n    secondsInputEl.on('blur', function(e) {\n      if (modelIsEmpty()) {\n        makeValid();\n      } else if (!$scope.invalidSeconds && $scope.seconds < 10) {\n        $scope.$apply( function() {\n          $scope.seconds = pad($scope.seconds);\n        });\n      }\n    });\n\n  };\n\n  this.render = function() {\n    var date = ngModelCtrl.$viewValue;\n\n    if (isNaN(date)) {\n      ngModelCtrl.$setValidity('time', false);\n      $log.error('Timepicker directive: \"ng-model\" value must be a Date object, a number of milliseconds since 01.01.1970 or a string representing an RFC2822 or ISO 8601 date.');\n    } else {\n      if (date) {\n        selected = date;\n      }\n\n      if (selected < min || selected > max) {\n        ngModelCtrl.$setValidity('time', false);\n        $scope.invalidHours = true;\n        $scope.invalidMinutes = true;\n      } else {\n        makeValid();\n      }\n      updateTemplate();\n    }\n  };\n\n  // Call internally when we know that model is valid.\n  function refresh(keyboardChange) {\n    makeValid();\n    ngModelCtrl.$setViewValue(new Date(selected));\n    updateTemplate(keyboardChange);\n  }\n\n  function makeValid() {\n    if (hoursModelCtrl) {\n      hoursModelCtrl.$setValidity('hours', true);\n    }\n\n    if (minutesModelCtrl) {\n      minutesModelCtrl.$setValidity('minutes', true);\n    }\n\n    if (secondsModelCtrl) {\n      secondsModelCtrl.$setValidity('seconds', true);\n    }\n\n    ngModelCtrl.$setValidity('time', true);\n    $scope.invalidHours = false;\n    $scope.invalidMinutes = false;\n    $scope.invalidSeconds = false;\n  }\n\n  function updateTemplate(keyboardChange) {\n    if (!ngModelCtrl.$modelValue) {\n      $scope.hours = null;\n      $scope.minutes = null;\n      $scope.seconds = null;\n      $scope.meridian = meridians[0];\n    } else {\n      var hours = selected.getHours(),\n        minutes = selected.getMinutes(),\n        seconds = selected.getSeconds();\n\n      if ($scope.showMeridian) {\n        hours = hours === 0 || hours === 12 ? 12 : hours % 12; // Convert 24 to 12 hour system\n      }\n\n      $scope.hours = keyboardChange === 'h' ? hours : pad(hours, !padHours);\n      if (keyboardChange !== 'm') {\n        $scope.minutes = pad(minutes);\n      }\n      $scope.meridian = selected.getHours() < 12 ? meridians[0] : meridians[1];\n\n      if (keyboardChange !== 's') {\n        $scope.seconds = pad(seconds);\n      }\n      $scope.meridian = selected.getHours() < 12 ? meridians[0] : meridians[1];\n    }\n  }\n\n  function addSecondsToSelected(seconds) {\n    selected = addSeconds(selected, seconds);\n    refresh();\n  }\n\n  function addMinutes(selected, minutes) {\n    return addSeconds(selected, minutes*60);\n  }\n\n  function addSeconds(date, seconds) {\n    var dt = new Date(date.getTime() + seconds * 1000);\n    var newDate = new Date(date);\n    newDate.setHours(dt.getHours(), dt.getMinutes(), dt.getSeconds());\n    return newDate;\n  }\n\n  function modelIsEmpty() {\n    return ($scope.hours === null || $scope.hours === '') &&\n      ($scope.minutes === null || $scope.minutes === '') &&\n      (!$scope.showSeconds || $scope.showSeconds && ($scope.seconds === null || $scope.seconds === ''));\n  }\n\n  $scope.showSpinners = angular.isDefined($attrs.showSpinners) ?\n    $scope.$parent.$eval($attrs.showSpinners) : timepickerConfig.showSpinners;\n\n  $scope.incrementHours = function() {\n    if (!$scope.noIncrementHours()) {\n      addSecondsToSelected(hourStep * 60 * 60);\n    }\n  };\n\n  $scope.decrementHours = function() {\n    if (!$scope.noDecrementHours()) {\n      addSecondsToSelected(-hourStep * 60 * 60);\n    }\n  };\n\n  $scope.incrementMinutes = function() {\n    if (!$scope.noIncrementMinutes()) {\n      addSecondsToSelected(minuteStep * 60);\n    }\n  };\n\n  $scope.decrementMinutes = function() {\n    if (!$scope.noDecrementMinutes()) {\n      addSecondsToSelected(-minuteStep * 60);\n    }\n  };\n\n  $scope.incrementSeconds = function() {\n    if (!$scope.noIncrementSeconds()) {\n      addSecondsToSelected(secondStep);\n    }\n  };\n\n  $scope.decrementSeconds = function() {\n    if (!$scope.noDecrementSeconds()) {\n      addSecondsToSelected(-secondStep);\n    }\n  };\n\n  $scope.toggleMeridian = function() {\n    var minutes = getMinutesFromTemplate(),\n        hours = getHoursFromTemplate();\n\n    if (!$scope.noToggleMeridian()) {\n      if (angular.isDefined(minutes) && angular.isDefined(hours)) {\n        addSecondsToSelected(12 * 60 * (selected.getHours() < 12 ? 60 : -60));\n      } else {\n        $scope.meridian = $scope.meridian === meridians[0] ? meridians[1] : meridians[0];\n      }\n    }\n  };\n\n  $scope.blur = function() {\n    ngModelCtrl.$setTouched();\n  };\n\n  $scope.$on('$destroy', function() {\n    while (watchers.length) {\n      watchers.shift()();\n    }\n  });\n}])\n\n.directive('uibTimepicker', ['uibTimepickerConfig', function(uibTimepickerConfig) {\n  return {\n    require: ['uibTimepicker', '?^ngModel'],\n    restrict: 'A',\n    controller: 'UibTimepickerController',\n    controllerAs: 'timepicker',\n    scope: {},\n    templateUrl: function(element, attrs) {\n      return attrs.templateUrl || uibTimepickerConfig.templateUrl;\n    },\n    link: function(scope, element, attrs, ctrls) {\n      var timepickerCtrl = ctrls[0], ngModelCtrl = ctrls[1];\n\n      if (ngModelCtrl) {\n        timepickerCtrl.init(ngModelCtrl, element.find('input'));\n      }\n    }\n  };\n}]);\n\nangular.module('ui.bootstrap.typeahead', ['ui.bootstrap.debounce', 'ui.bootstrap.position'])\n\n/**\n * A helper service that can parse typeahead's syntax (string provided by users)\n * Extracted to a separate service for ease of unit testing\n */\n  .factory('uibTypeaheadParser', ['$parse', function($parse) {\n    //                      000001111111100000000000002222222200000000000000003333333333333330000000000044444444000\n    var TYPEAHEAD_REGEXP = /^\\s*([\\s\\S]+?)(?:\\s+as\\s+([\\s\\S]+?))?\\s+for\\s+(?:([\\$\\w][\\$\\w\\d]*))\\s+in\\s+([\\s\\S]+?)$/;\n    return {\n      parse: function(input) {\n        var match = input.match(TYPEAHEAD_REGEXP);\n        if (!match) {\n          throw new Error(\n            'Expected typeahead specification in form of \"_modelValue_ (as _label_)? for _item_ in _collection_\"' +\n              ' but got \"' + input + '\".');\n        }\n\n        return {\n          itemName: match[3],\n          source: $parse(match[4]),\n          viewMapper: $parse(match[2] || match[1]),\n          modelMapper: $parse(match[1])\n        };\n      }\n    };\n  }])\n\n  .controller('UibTypeaheadController', ['$scope', '$element', '$attrs', '$compile', '$parse', '$q', '$timeout', '$document', '$window', '$rootScope', '$$debounce', '$uibPosition', 'uibTypeaheadParser',\n    function(originalScope, element, attrs, $compile, $parse, $q, $timeout, $document, $window, $rootScope, $$debounce, $position, typeaheadParser) {\n    var HOT_KEYS = [9, 13, 27, 38, 40];\n    var eventDebounceTime = 200;\n    var modelCtrl, ngModelOptions;\n    //SUPPORTED ATTRIBUTES (OPTIONS)\n\n    //minimal no of characters that needs to be entered before typeahead kicks-in\n    var minLength = originalScope.$eval(attrs.typeaheadMinLength);\n    if (!minLength && minLength !== 0) {\n      minLength = 1;\n    }\n\n    originalScope.$watch(attrs.typeaheadMinLength, function (newVal) {\n        minLength = !newVal && newVal !== 0 ? 1 : newVal;\n    });\n\n    //minimal wait time after last character typed before typeahead kicks-in\n    var waitTime = originalScope.$eval(attrs.typeaheadWaitMs) || 0;\n\n    //should it restrict model values to the ones selected from the popup only?\n    var isEditable = originalScope.$eval(attrs.typeaheadEditable) !== false;\n    originalScope.$watch(attrs.typeaheadEditable, function (newVal) {\n      isEditable = newVal !== false;\n    });\n\n    //binding to a variable that indicates if matches are being retrieved asynchronously\n    var isLoadingSetter = $parse(attrs.typeaheadLoading).assign || angular.noop;\n\n    //a function to determine if an event should cause selection\n    var isSelectEvent = attrs.typeaheadShouldSelect ? $parse(attrs.typeaheadShouldSelect) : function(scope, vals) {\n      var evt = vals.$event;\n      return evt.which === 13 || evt.which === 9;\n    };\n\n    //a callback executed when a match is selected\n    var onSelectCallback = $parse(attrs.typeaheadOnSelect);\n\n    //should it select highlighted popup value when losing focus?\n    var isSelectOnBlur = angular.isDefined(attrs.typeaheadSelectOnBlur) ? originalScope.$eval(attrs.typeaheadSelectOnBlur) : false;\n\n    //binding to a variable that indicates if there were no results after the query is completed\n    var isNoResultsSetter = $parse(attrs.typeaheadNoResults).assign || angular.noop;\n\n    var inputFormatter = attrs.typeaheadInputFormatter ? $parse(attrs.typeaheadInputFormatter) : undefined;\n\n    var appendToBody = attrs.typeaheadAppendToBody ? originalScope.$eval(attrs.typeaheadAppendToBody) : false;\n\n    var appendTo = attrs.typeaheadAppendTo ?\n      originalScope.$eval(attrs.typeaheadAppendTo) : null;\n\n    var focusFirst = originalScope.$eval(attrs.typeaheadFocusFirst) !== false;\n\n    //If input matches an item of the list exactly, select it automatically\n    var selectOnExact = attrs.typeaheadSelectOnExact ? originalScope.$eval(attrs.typeaheadSelectOnExact) : false;\n\n    //binding to a variable that indicates if dropdown is open\n    var isOpenSetter = $parse(attrs.typeaheadIsOpen).assign || angular.noop;\n\n    var showHint = originalScope.$eval(attrs.typeaheadShowHint) || false;\n\n    //INTERNAL VARIABLES\n\n    //model setter executed upon match selection\n    var parsedModel = $parse(attrs.ngModel);\n    var invokeModelSetter = $parse(attrs.ngModel + '($$$p)');\n    var $setModelValue = function(scope, newValue) {\n      if (angular.isFunction(parsedModel(originalScope)) &&\n        ngModelOptions.getOption('getterSetter')) {\n        return invokeModelSetter(scope, {$$$p: newValue});\n      }\n\n      return parsedModel.assign(scope, newValue);\n    };\n\n    //expressions used by typeahead\n    var parserResult = typeaheadParser.parse(attrs.uibTypeahead);\n\n    var hasFocus;\n\n    //Used to avoid bug in iOS webview where iOS keyboard does not fire\n    //mousedown & mouseup events\n    //Issue #3699\n    var selected;\n\n    //create a child scope for the typeahead directive so we are not polluting original scope\n    //with typeahead-specific data (matches, query etc.)\n    var scope = originalScope.$new();\n    var offDestroy = originalScope.$on('$destroy', function() {\n      scope.$destroy();\n    });\n    scope.$on('$destroy', offDestroy);\n\n    // WAI-ARIA\n    var popupId = 'typeahead-' + scope.$id + '-' + Math.floor(Math.random() * 10000);\n    element.attr({\n      'aria-autocomplete': 'list',\n      'aria-expanded': false,\n      'aria-owns': popupId\n    });\n\n    var inputsContainer, hintInputElem;\n    //add read-only input to show hint\n    if (showHint) {\n      inputsContainer = angular.element('<div></div>');\n      inputsContainer.css('position', 'relative');\n      element.after(inputsContainer);\n      hintInputElem = element.clone();\n      hintInputElem.attr('placeholder', '');\n      hintInputElem.attr('tabindex', '-1');\n      hintInputElem.val('');\n      hintInputElem.css({\n        'position': 'absolute',\n        'top': '0px',\n        'left': '0px',\n        'border-color': 'transparent',\n        'box-shadow': 'none',\n        'opacity': 1,\n        'background': 'none 0% 0% / auto repeat scroll padding-box border-box rgb(255, 255, 255)',\n        'color': '#999'\n      });\n      element.css({\n        'position': 'relative',\n        'vertical-align': 'top',\n        'background-color': 'transparent'\n      });\n\n      if (hintInputElem.attr('id')) {\n        hintInputElem.removeAttr('id'); // remove duplicate id if present.\n      }\n      inputsContainer.append(hintInputElem);\n      hintInputElem.after(element);\n    }\n\n    //pop-up element used to display matches\n    var popUpEl = angular.element('<div uib-typeahead-popup></div>');\n    popUpEl.attr({\n      id: popupId,\n      matches: 'matches',\n      active: 'activeIdx',\n      select: 'select(activeIdx, evt)',\n      'move-in-progress': 'moveInProgress',\n      query: 'query',\n      position: 'position',\n      'assign-is-open': 'assignIsOpen(isOpen)',\n      debounce: 'debounceUpdate'\n    });\n    //custom item template\n    if (angular.isDefined(attrs.typeaheadTemplateUrl)) {\n      popUpEl.attr('template-url', attrs.typeaheadTemplateUrl);\n    }\n\n    if (angular.isDefined(attrs.typeaheadPopupTemplateUrl)) {\n      popUpEl.attr('popup-template-url', attrs.typeaheadPopupTemplateUrl);\n    }\n\n    var resetHint = function() {\n      if (showHint) {\n        hintInputElem.val('');\n      }\n    };\n\n    var resetMatches = function() {\n      scope.matches = [];\n      scope.activeIdx = -1;\n      element.attr('aria-expanded', false);\n      resetHint();\n    };\n\n    var getMatchId = function(index) {\n      return popupId + '-option-' + index;\n    };\n\n    // Indicate that the specified match is the active (pre-selected) item in the list owned by this typeahead.\n    // This attribute is added or removed automatically when the `activeIdx` changes.\n    scope.$watch('activeIdx', function(index) {\n      if (index < 0) {\n        element.removeAttr('aria-activedescendant');\n      } else {\n        element.attr('aria-activedescendant', getMatchId(index));\n      }\n    });\n\n    var inputIsExactMatch = function(inputValue, index) {\n      if (scope.matches.length > index && inputValue) {\n        return inputValue.toUpperCase() === scope.matches[index].label.toUpperCase();\n      }\n\n      return false;\n    };\n\n    var getMatchesAsync = function(inputValue, evt) {\n      var locals = {$viewValue: inputValue};\n      isLoadingSetter(originalScope, true);\n      isNoResultsSetter(originalScope, false);\n      $q.when(parserResult.source(originalScope, locals)).then(function(matches) {\n        //it might happen that several async queries were in progress if a user were typing fast\n        //but we are interested only in responses that correspond to the current view value\n        var onCurrentRequest = inputValue === modelCtrl.$viewValue;\n        if (onCurrentRequest && hasFocus) {\n          if (matches && matches.length > 0) {\n            scope.activeIdx = focusFirst ? 0 : -1;\n            isNoResultsSetter(originalScope, false);\n            scope.matches.length = 0;\n\n            //transform labels\n            for (var i = 0; i < matches.length; i++) {\n              locals[parserResult.itemName] = matches[i];\n              scope.matches.push({\n                id: getMatchId(i),\n                label: parserResult.viewMapper(scope, locals),\n                model: matches[i]\n              });\n            }\n\n            scope.query = inputValue;\n            //position pop-up with matches - we need to re-calculate its position each time we are opening a window\n            //with matches as a pop-up might be absolute-positioned and position of an input might have changed on a page\n            //due to other elements being rendered\n            recalculatePosition();\n\n            element.attr('aria-expanded', true);\n\n            //Select the single remaining option if user input matches\n            if (selectOnExact && scope.matches.length === 1 && inputIsExactMatch(inputValue, 0)) {\n              if (angular.isNumber(scope.debounceUpdate) || angular.isObject(scope.debounceUpdate)) {\n                $$debounce(function() {\n                  scope.select(0, evt);\n                }, angular.isNumber(scope.debounceUpdate) ? scope.debounceUpdate : scope.debounceUpdate['default']);\n              } else {\n                scope.select(0, evt);\n              }\n            }\n\n            if (showHint) {\n              var firstLabel = scope.matches[0].label;\n              if (angular.isString(inputValue) &&\n                inputValue.length > 0 &&\n                firstLabel.slice(0, inputValue.length).toUpperCase() === inputValue.toUpperCase()) {\n                hintInputElem.val(inputValue + firstLabel.slice(inputValue.length));\n              } else {\n                hintInputElem.val('');\n              }\n            }\n          } else {\n            resetMatches();\n            isNoResultsSetter(originalScope, true);\n          }\n        }\n        if (onCurrentRequest) {\n          isLoadingSetter(originalScope, false);\n        }\n      }, function() {\n        resetMatches();\n        isLoadingSetter(originalScope, false);\n        isNoResultsSetter(originalScope, true);\n      });\n    };\n\n    // bind events only if appendToBody params exist - performance feature\n    if (appendToBody) {\n      angular.element($window).on('resize', fireRecalculating);\n      $document.find('body').on('scroll', fireRecalculating);\n    }\n\n    // Declare the debounced function outside recalculating for\n    // proper debouncing\n    var debouncedRecalculate = $$debounce(function() {\n      // if popup is visible\n      if (scope.matches.length) {\n        recalculatePosition();\n      }\n\n      scope.moveInProgress = false;\n    }, eventDebounceTime);\n\n    // Default progress type\n    scope.moveInProgress = false;\n\n    function fireRecalculating() {\n      if (!scope.moveInProgress) {\n        scope.moveInProgress = true;\n        scope.$digest();\n      }\n\n      debouncedRecalculate();\n    }\n\n    // recalculate actual position and set new values to scope\n    // after digest loop is popup in right position\n    function recalculatePosition() {\n      scope.position = appendToBody ? $position.offset(element) : $position.position(element);\n      scope.position.top += element.prop('offsetHeight');\n    }\n\n    //we need to propagate user's query so we can higlight matches\n    scope.query = undefined;\n\n    //Declare the timeout promise var outside the function scope so that stacked calls can be cancelled later\n    var timeoutPromise;\n\n    var scheduleSearchWithTimeout = function(inputValue) {\n      timeoutPromise = $timeout(function() {\n        getMatchesAsync(inputValue);\n      }, waitTime);\n    };\n\n    var cancelPreviousTimeout = function() {\n      if (timeoutPromise) {\n        $timeout.cancel(timeoutPromise);\n      }\n    };\n\n    resetMatches();\n\n    scope.assignIsOpen = function (isOpen) {\n      isOpenSetter(originalScope, isOpen);\n    };\n\n    scope.select = function(activeIdx, evt) {\n      //called from within the $digest() cycle\n      var locals = {};\n      var model, item;\n\n      selected = true;\n      locals[parserResult.itemName] = item = scope.matches[activeIdx].model;\n      model = parserResult.modelMapper(originalScope, locals);\n      $setModelValue(originalScope, model);\n      modelCtrl.$setValidity('editable', true);\n      modelCtrl.$setValidity('parse', true);\n\n      onSelectCallback(originalScope, {\n        $item: item,\n        $model: model,\n        $label: parserResult.viewMapper(originalScope, locals),\n        $event: evt\n      });\n\n      resetMatches();\n\n      //return focus to the input element if a match was selected via a mouse click event\n      // use timeout to avoid $rootScope:inprog error\n      if (scope.$eval(attrs.typeaheadFocusOnSelect) !== false) {\n        $timeout(function() { element[0].focus(); }, 0, false);\n      }\n    };\n\n    //bind keyboard events: arrows up(38) / down(40), enter(13) and tab(9), esc(27)\n    element.on('keydown', function(evt) {\n      //typeahead is open and an \"interesting\" key was pressed\n      if (scope.matches.length === 0 || HOT_KEYS.indexOf(evt.which) === -1) {\n        return;\n      }\n\n      var shouldSelect = isSelectEvent(originalScope, {$event: evt});\n\n      /**\n       * if there's nothing selected (i.e. focusFirst) and enter or tab is hit\n       * or\n       * shift + tab is pressed to bring focus to the previous element\n       * then clear the results\n       */\n      if (scope.activeIdx === -1 && shouldSelect || evt.which === 9 && !!evt.shiftKey) {\n        resetMatches();\n        scope.$digest();\n        return;\n      }\n\n      evt.preventDefault();\n      var target;\n      switch (evt.which) {\n        case 27: // escape\n          evt.stopPropagation();\n\n          resetMatches();\n          originalScope.$digest();\n          break;\n        case 38: // up arrow\n          scope.activeIdx = (scope.activeIdx > 0 ? scope.activeIdx : scope.matches.length) - 1;\n          scope.$digest();\n          target = popUpEl[0].querySelectorAll('.uib-typeahead-match')[scope.activeIdx];\n          target.parentNode.scrollTop = target.offsetTop;\n          break;\n        case 40: // down arrow\n          scope.activeIdx = (scope.activeIdx + 1) % scope.matches.length;\n          scope.$digest();\n          target = popUpEl[0].querySelectorAll('.uib-typeahead-match')[scope.activeIdx];\n          target.parentNode.scrollTop = target.offsetTop;\n          break;\n        default:\n          if (shouldSelect) {\n            scope.$apply(function() {\n              if (angular.isNumber(scope.debounceUpdate) || angular.isObject(scope.debounceUpdate)) {\n                $$debounce(function() {\n                  scope.select(scope.activeIdx, evt);\n                }, angular.isNumber(scope.debounceUpdate) ? scope.debounceUpdate : scope.debounceUpdate['default']);\n              } else {\n                scope.select(scope.activeIdx, evt);\n              }\n            });\n          }\n      }\n    });\n\n    element.on('focus', function (evt) {\n      hasFocus = true;\n      if (minLength === 0 && !modelCtrl.$viewValue) {\n        $timeout(function() {\n          getMatchesAsync(modelCtrl.$viewValue, evt);\n        }, 0);\n      }\n    });\n\n    element.on('blur', function(evt) {\n      if (isSelectOnBlur && scope.matches.length && scope.activeIdx !== -1 && !selected) {\n        selected = true;\n        scope.$apply(function() {\n          if (angular.isObject(scope.debounceUpdate) && angular.isNumber(scope.debounceUpdate.blur)) {\n            $$debounce(function() {\n              scope.select(scope.activeIdx, evt);\n            }, scope.debounceUpdate.blur);\n          } else {\n            scope.select(scope.activeIdx, evt);\n          }\n        });\n      }\n      if (!isEditable && modelCtrl.$error.editable) {\n        modelCtrl.$setViewValue();\n        scope.$apply(function() {\n          // Reset validity as we are clearing\n          modelCtrl.$setValidity('editable', true);\n          modelCtrl.$setValidity('parse', true);\n        });\n        element.val('');\n      }\n      hasFocus = false;\n      selected = false;\n    });\n\n    // Keep reference to click handler to unbind it.\n    var dismissClickHandler = function(evt) {\n      // Issue #3973\n      // Firefox treats right click as a click on document\n      if (element[0] !== evt.target && evt.which !== 3 && scope.matches.length !== 0) {\n        resetMatches();\n        if (!$rootScope.$$phase) {\n          originalScope.$digest();\n        }\n      }\n    };\n\n    $document.on('click', dismissClickHandler);\n\n    originalScope.$on('$destroy', function() {\n      $document.off('click', dismissClickHandler);\n      if (appendToBody || appendTo) {\n        $popup.remove();\n      }\n\n      if (appendToBody) {\n        angular.element($window).off('resize', fireRecalculating);\n        $document.find('body').off('scroll', fireRecalculating);\n      }\n      // Prevent jQuery cache memory leak\n      popUpEl.remove();\n\n      if (showHint) {\n          inputsContainer.remove();\n      }\n    });\n\n    var $popup = $compile(popUpEl)(scope);\n\n    if (appendToBody) {\n      $document.find('body').append($popup);\n    } else if (appendTo) {\n      angular.element(appendTo).eq(0).append($popup);\n    } else {\n      element.after($popup);\n    }\n\n    this.init = function(_modelCtrl) {\n      modelCtrl = _modelCtrl;\n      ngModelOptions = extractOptions(modelCtrl);\n\n      scope.debounceUpdate = $parse(ngModelOptions.getOption('debounce'))(originalScope);\n\n      //plug into $parsers pipeline to open a typeahead on view changes initiated from DOM\n      //$parsers kick-in on all the changes coming from the view as well as manually triggered by $setViewValue\n      modelCtrl.$parsers.unshift(function(inputValue) {\n        hasFocus = true;\n\n        if (minLength === 0 || inputValue && inputValue.length >= minLength) {\n          if (waitTime > 0) {\n            cancelPreviousTimeout();\n            scheduleSearchWithTimeout(inputValue);\n          } else {\n            getMatchesAsync(inputValue);\n          }\n        } else {\n          isLoadingSetter(originalScope, false);\n          cancelPreviousTimeout();\n          resetMatches();\n        }\n\n        if (isEditable) {\n          return inputValue;\n        }\n\n        if (!inputValue) {\n          // Reset in case user had typed something previously.\n          modelCtrl.$setValidity('editable', true);\n          return null;\n        }\n\n        modelCtrl.$setValidity('editable', false);\n        return undefined;\n      });\n\n      modelCtrl.$formatters.push(function(modelValue) {\n        var candidateViewValue, emptyViewValue;\n        var locals = {};\n\n        // The validity may be set to false via $parsers (see above) if\n        // the model is restricted to selected values. If the model\n        // is set manually it is considered to be valid.\n        if (!isEditable) {\n          modelCtrl.$setValidity('editable', true);\n        }\n\n        if (inputFormatter) {\n          locals.$model = modelValue;\n          return inputFormatter(originalScope, locals);\n        }\n\n        //it might happen that we don't have enough info to properly render input value\n        //we need to check for this situation and simply return model value if we can't apply custom formatting\n        locals[parserResult.itemName] = modelValue;\n        candidateViewValue = parserResult.viewMapper(originalScope, locals);\n        locals[parserResult.itemName] = undefined;\n        emptyViewValue = parserResult.viewMapper(originalScope, locals);\n\n        return candidateViewValue !== emptyViewValue ? candidateViewValue : modelValue;\n      });\n    };\n\n    function extractOptions(ngModelCtrl) {\n      var ngModelOptions;\n\n      if (angular.version.minor < 6) { // in angular < 1.6 $options could be missing\n        // guarantee a value\n        ngModelOptions = ngModelCtrl.$options || {};\n\n        // mimic 1.6+ api\n        ngModelOptions.getOption = function (key) {\n          return ngModelOptions[key];\n        };\n      } else { // in angular >=1.6 $options is always present\n        ngModelOptions = ngModelCtrl.$options;\n      }\n\n      return ngModelOptions;\n    }\n  }])\n\n  .directive('uibTypeahead', function() {\n    return {\n      controller: 'UibTypeaheadController',\n      require: ['ngModel', 'uibTypeahead'],\n      link: function(originalScope, element, attrs, ctrls) {\n        ctrls[1].init(ctrls[0]);\n      }\n    };\n  })\n\n  .directive('uibTypeaheadPopup', ['$$debounce', function($$debounce) {\n    return {\n      scope: {\n        matches: '=',\n        query: '=',\n        active: '=',\n        position: '&',\n        moveInProgress: '=',\n        select: '&',\n        assignIsOpen: '&',\n        debounce: '&'\n      },\n      replace: true,\n      templateUrl: function(element, attrs) {\n        return attrs.popupTemplateUrl || 'uib/template/typeahead/typeahead-popup.html';\n      },\n      link: function(scope, element, attrs) {\n        scope.templateUrl = attrs.templateUrl;\n\n        scope.isOpen = function() {\n          var isDropdownOpen = scope.matches.length > 0;\n          scope.assignIsOpen({ isOpen: isDropdownOpen });\n          return isDropdownOpen;\n        };\n\n        scope.isActive = function(matchIdx) {\n          return scope.active === matchIdx;\n        };\n\n        scope.selectActive = function(matchIdx) {\n          scope.active = matchIdx;\n        };\n\n        scope.selectMatch = function(activeIdx, evt) {\n          var debounce = scope.debounce();\n          if (angular.isNumber(debounce) || angular.isObject(debounce)) {\n            $$debounce(function() {\n              scope.select({activeIdx: activeIdx, evt: evt});\n            }, angular.isNumber(debounce) ? debounce : debounce['default']);\n          } else {\n            scope.select({activeIdx: activeIdx, evt: evt});\n          }\n        };\n      }\n    };\n  }])\n\n  .directive('uibTypeaheadMatch', ['$templateRequest', '$compile', '$parse', function($templateRequest, $compile, $parse) {\n    return {\n      scope: {\n        index: '=',\n        match: '=',\n        query: '='\n      },\n      link: function(scope, element, attrs) {\n        var tplUrl = $parse(attrs.templateUrl)(scope.$parent) || 'uib/template/typeahead/typeahead-match.html';\n        $templateRequest(tplUrl).then(function(tplContent) {\n          var tplEl = angular.element(tplContent.trim());\n          element.replaceWith(tplEl);\n          $compile(tplEl)(scope);\n        });\n      }\n    };\n  }])\n\n  .filter('uibTypeaheadHighlight', ['$sce', '$injector', '$log', function($sce, $injector, $log) {\n    var isSanitizePresent;\n    isSanitizePresent = $injector.has('$sanitize');\n\n    function escapeRegexp(queryToEscape) {\n      // Regex: capture the whole query string and replace it with the string that will be used to match\n      // the results, for example if the capture is \"a\" the result will be \\a\n      return queryToEscape.replace(/([.?*+^$[\\]\\\\(){}|-])/g, '\\\\$1');\n    }\n\n    function containsHtml(matchItem) {\n      return /<.*>/g.test(matchItem);\n    }\n\n    return function(matchItem, query) {\n      if (!isSanitizePresent && containsHtml(matchItem)) {\n        $log.warn('Unsafe use of typeahead please use ngSanitize'); // Warn the user about the danger\n      }\n      matchItem = query ? ('' + matchItem).replace(new RegExp(escapeRegexp(query), 'gi'), '<strong>$&</strong>') : matchItem; // Replaces the capture string with a the same string inside of a \"strong\" tag\n      if (!isSanitizePresent) {\n        matchItem = $sce.trustAsHtml(matchItem); // If $sanitize is not present we pack the string in a $sce object for the ng-bind-html directive\n      }\n      return matchItem;\n    };\n  }]);\n\nangular.module(\"uib/template/accordion/accordion-group.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/accordion/accordion-group.html\",\n    \"<div role=\\\"tab\\\" id=\\\"{{::headingId}}\\\" aria-selected=\\\"{{isOpen}}\\\" class=\\\"panel-heading\\\" ng-keypress=\\\"toggleOpen($event)\\\">\\n\" +\n    \"  <h4 class=\\\"panel-title\\\">\\n\" +\n    \"    <a role=\\\"button\\\" data-toggle=\\\"collapse\\\" href aria-expanded=\\\"{{isOpen}}\\\" aria-controls=\\\"{{::panelId}}\\\" tabindex=\\\"0\\\" class=\\\"accordion-toggle\\\" ng-click=\\\"toggleOpen()\\\" uib-accordion-transclude=\\\"heading\\\" ng-disabled=\\\"isDisabled\\\" uib-tabindex-toggle><span uib-accordion-header ng-class=\\\"{'text-muted': isDisabled}\\\">{{heading}}</span></a>\\n\" +\n    \"  </h4>\\n\" +\n    \"</div>\\n\" +\n    \"<div id=\\\"{{::panelId}}\\\" aria-labelledby=\\\"{{::headingId}}\\\" aria-hidden=\\\"{{!isOpen}}\\\" role=\\\"tabpanel\\\" class=\\\"panel-collapse collapse\\\" uib-collapse=\\\"!isOpen\\\">\\n\" +\n    \"  <div class=\\\"panel-body\\\" ng-transclude></div>\\n\" +\n    \"</div>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/accordion/accordion.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/accordion/accordion.html\",\n    \"<div role=\\\"tablist\\\" class=\\\"panel-group\\\" ng-transclude></div>\");\n}]);\n\nangular.module(\"uib/template/alert/alert.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/alert/alert.html\",\n    \"<button ng-show=\\\"closeable\\\" type=\\\"button\\\" class=\\\"close\\\" ng-click=\\\"close({$event: $event})\\\">\\n\" +\n    \"  <span aria-hidden=\\\"true\\\">&times;</span>\\n\" +\n    \"  <span class=\\\"sr-only\\\">Close</span>\\n\" +\n    \"</button>\\n\" +\n    \"<div ng-transclude></div>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/carousel/carousel.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/carousel/carousel.html\",\n    \"<div class=\\\"carousel-inner\\\" ng-transclude></div>\\n\" +\n    \"<a role=\\\"button\\\" href class=\\\"left carousel-control\\\" ng-click=\\\"prev()\\\" ng-class=\\\"{ disabled: isPrevDisabled() }\\\" ng-show=\\\"slides.length > 1\\\">\\n\" +\n    \"  <span aria-hidden=\\\"true\\\" class=\\\"glyphicon glyphicon-chevron-left\\\"></span>\\n\" +\n    \"  <span class=\\\"sr-only\\\">previous</span>\\n\" +\n    \"</a>\\n\" +\n    \"<a role=\\\"button\\\" href class=\\\"right carousel-control\\\" ng-click=\\\"next()\\\" ng-class=\\\"{ disabled: isNextDisabled() }\\\" ng-show=\\\"slides.length > 1\\\">\\n\" +\n    \"  <span aria-hidden=\\\"true\\\" class=\\\"glyphicon glyphicon-chevron-right\\\"></span>\\n\" +\n    \"  <span class=\\\"sr-only\\\">next</span>\\n\" +\n    \"</a>\\n\" +\n    \"<ol class=\\\"carousel-indicators\\\" ng-show=\\\"slides.length > 1\\\">\\n\" +\n    \"  <li ng-repeat=\\\"slide in slides | orderBy:indexOfSlide track by $index\\\" ng-class=\\\"{ active: isActive(slide) }\\\" ng-click=\\\"select(slide)\\\">\\n\" +\n    \"    <span class=\\\"sr-only\\\">slide {{ $index + 1 }} of {{ slides.length }}<span ng-if=\\\"isActive(slide)\\\">, currently active</span></span>\\n\" +\n    \"  </li>\\n\" +\n    \"</ol>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/carousel/slide.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/carousel/slide.html\",\n    \"<div class=\\\"text-center\\\" ng-transclude></div>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/datepicker/datepicker.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/datepicker/datepicker.html\",\n    \"<div ng-switch=\\\"datepickerMode\\\">\\n\" +\n    \"  <div uib-daypicker ng-switch-when=\\\"day\\\" tabindex=\\\"0\\\" class=\\\"uib-daypicker\\\"></div>\\n\" +\n    \"  <div uib-monthpicker ng-switch-when=\\\"month\\\" tabindex=\\\"0\\\" class=\\\"uib-monthpicker\\\"></div>\\n\" +\n    \"  <div uib-yearpicker ng-switch-when=\\\"year\\\" tabindex=\\\"0\\\" class=\\\"uib-yearpicker\\\"></div>\\n\" +\n    \"</div>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/datepicker/day.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/datepicker/day.html\",\n    \"<table role=\\\"grid\\\" aria-labelledby=\\\"{{::uniqueId}}-title\\\" aria-activedescendant=\\\"{{activeDateId}}\\\">\\n\" +\n    \"  <thead>\\n\" +\n    \"    <tr>\\n\" +\n    \"      <th><button type=\\\"button\\\" class=\\\"btn btn-default btn-sm pull-left uib-left\\\" ng-click=\\\"move(-1)\\\" tabindex=\\\"-1\\\"><i aria-hidden=\\\"true\\\" class=\\\"glyphicon glyphicon-chevron-left\\\"></i><span class=\\\"sr-only\\\">previous</span></button></th>\\n\" +\n    \"      <th colspan=\\\"{{::5 + showWeeks}}\\\"><button id=\\\"{{::uniqueId}}-title\\\" role=\\\"heading\\\" aria-live=\\\"assertive\\\" aria-atomic=\\\"true\\\" type=\\\"button\\\" class=\\\"btn btn-default btn-sm uib-title\\\" ng-click=\\\"toggleMode()\\\" ng-disabled=\\\"datepickerMode === maxMode\\\" tabindex=\\\"-1\\\"><strong>{{title}}</strong></button></th>\\n\" +\n    \"      <th><button type=\\\"button\\\" class=\\\"btn btn-default btn-sm pull-right uib-right\\\" ng-click=\\\"move(1)\\\" tabindex=\\\"-1\\\"><i aria-hidden=\\\"true\\\" class=\\\"glyphicon glyphicon-chevron-right\\\"></i><span class=\\\"sr-only\\\">next</span></button></th>\\n\" +\n    \"    </tr>\\n\" +\n    \"    <tr>\\n\" +\n    \"      <th ng-if=\\\"showWeeks\\\" class=\\\"text-center\\\"></th>\\n\" +\n    \"      <th ng-repeat=\\\"label in ::labels track by $index\\\" class=\\\"text-center\\\"><small aria-label=\\\"{{::label.full}}\\\">{{::label.abbr}}</small></th>\\n\" +\n    \"    </tr>\\n\" +\n    \"  </thead>\\n\" +\n    \"  <tbody>\\n\" +\n    \"    <tr class=\\\"uib-weeks\\\" ng-repeat=\\\"row in rows track by $index\\\" role=\\\"row\\\">\\n\" +\n    \"      <td ng-if=\\\"showWeeks\\\" class=\\\"text-center h6\\\"><em>{{ weekNumbers[$index] }}</em></td>\\n\" +\n    \"      <td ng-repeat=\\\"dt in row\\\" class=\\\"uib-day text-center\\\" role=\\\"gridcell\\\"\\n\" +\n    \"        id=\\\"{{::dt.uid}}\\\"\\n\" +\n    \"        ng-class=\\\"::dt.customClass\\\">\\n\" +\n    \"        <button type=\\\"button\\\" class=\\\"btn btn-default btn-sm\\\"\\n\" +\n    \"          uib-is-class=\\\"\\n\" +\n    \"            'btn-info' for selectedDt,\\n\" +\n    \"            'active' for activeDt\\n\" +\n    \"            on dt\\\"\\n\" +\n    \"          ng-click=\\\"select(dt.date)\\\"\\n\" +\n    \"          ng-disabled=\\\"::dt.disabled\\\"\\n\" +\n    \"          tabindex=\\\"-1\\\"><span ng-class=\\\"::{'text-muted': dt.secondary, 'text-info': dt.current}\\\">{{::dt.label}}</span></button>\\n\" +\n    \"      </td>\\n\" +\n    \"    </tr>\\n\" +\n    \"  </tbody>\\n\" +\n    \"</table>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/datepicker/month.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/datepicker/month.html\",\n    \"<table role=\\\"grid\\\" aria-labelledby=\\\"{{::uniqueId}}-title\\\" aria-activedescendant=\\\"{{activeDateId}}\\\">\\n\" +\n    \"  <thead>\\n\" +\n    \"    <tr>\\n\" +\n    \"      <th><button type=\\\"button\\\" class=\\\"btn btn-default btn-sm pull-left uib-left\\\" ng-click=\\\"move(-1)\\\" tabindex=\\\"-1\\\"><i aria-hidden=\\\"true\\\" class=\\\"glyphicon glyphicon-chevron-left\\\"></i><span class=\\\"sr-only\\\">previous</span></button></th>\\n\" +\n    \"      <th colspan=\\\"{{::yearHeaderColspan}}\\\"><button id=\\\"{{::uniqueId}}-title\\\" role=\\\"heading\\\" aria-live=\\\"assertive\\\" aria-atomic=\\\"true\\\" type=\\\"button\\\" class=\\\"btn btn-default btn-sm uib-title\\\" ng-click=\\\"toggleMode()\\\" ng-disabled=\\\"datepickerMode === maxMode\\\" tabindex=\\\"-1\\\"><strong>{{title}}</strong></button></th>\\n\" +\n    \"      <th><button type=\\\"button\\\" class=\\\"btn btn-default btn-sm pull-right uib-right\\\" ng-click=\\\"move(1)\\\" tabindex=\\\"-1\\\"><i aria-hidden=\\\"true\\\" class=\\\"glyphicon glyphicon-chevron-right\\\"></i><span class=\\\"sr-only\\\">next</span></i></button></th>\\n\" +\n    \"    </tr>\\n\" +\n    \"  </thead>\\n\" +\n    \"  <tbody>\\n\" +\n    \"    <tr class=\\\"uib-months\\\" ng-repeat=\\\"row in rows track by $index\\\" role=\\\"row\\\">\\n\" +\n    \"      <td ng-repeat=\\\"dt in row\\\" class=\\\"uib-month text-center\\\" role=\\\"gridcell\\\"\\n\" +\n    \"        id=\\\"{{::dt.uid}}\\\"\\n\" +\n    \"        ng-class=\\\"::dt.customClass\\\">\\n\" +\n    \"        <button type=\\\"button\\\" class=\\\"btn btn-default\\\"\\n\" +\n    \"          uib-is-class=\\\"\\n\" +\n    \"            'btn-info' for selectedDt,\\n\" +\n    \"            'active' for activeDt\\n\" +\n    \"            on dt\\\"\\n\" +\n    \"          ng-click=\\\"select(dt.date)\\\"\\n\" +\n    \"          ng-disabled=\\\"::dt.disabled\\\"\\n\" +\n    \"          tabindex=\\\"-1\\\"><span ng-class=\\\"::{'text-info': dt.current}\\\">{{::dt.label}}</span></button>\\n\" +\n    \"      </td>\\n\" +\n    \"    </tr>\\n\" +\n    \"  </tbody>\\n\" +\n    \"</table>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/datepicker/popup.html\", []).run([\"$templateCache\", function($templateCache) {\n  $templateCache.put(\"uib/template/datepicker/popup.html\",\n    \"<div>\\n\" +\n    \"  <ul class=\\\"uib-datepicker-popup dropdown-menu uib-position-measure\\\" dropdown-nested ng-if=\\\"isOpen\\\" ng-keydown=\\\"keydown($event)\\\" ng-click=\\\"$event.stopPropagation()\\\">\\n\" +\n    \"    <li ng-transclude></li>\\n\" +\n    \"    <li ng-if=\\\"showButtonBar\\\" class=\\\"uib-button-bar\\\">\\n\" +\n    \"      <span class=\\\"btn-group pull-left\\\">\\n\" +\n    \"        <button type=\\\"button\\\" class=\\\"btn btn-sm btn-info uib-datepicker-current\\\" ng-click=\\\"select('today', $event)\\\" ng-disabled=\\\"isDisabled('today')\\\">{{ getText('current') }}</button>\\n\" +\n    \"        <button type=\\\"button\\\" class=\\\"btn btn-sm btn-danger uib-clear\\\" ng-click=\\\"select(null, $event)\\\">{{ getText('clear') }}</button>\\n\" +\n    \"      </span>\\n\" +\n    \"      <button type=\\\"button\\\" class=\\\"btn btn-sm btn-success pull-right uib-close\\\" ng-click=\\\"close($event)\\\">{{ getText('close') }}</button>\\n\" +\n    \"    </li>\\n\" +\n    \"  </ul>\\n\" +\n    \"</div>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/datepicker/year.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/datepicker/year.html\",\n    \"<table role=\\\"grid\\\" aria-labelledby=\\\"{{::uniqueId}}-title\\\" aria-activedescendant=\\\"{{activeDateId}}\\\">\\n\" +\n    \"  <thead>\\n\" +\n    \"    <tr>\\n\" +\n    \"      <th><button type=\\\"button\\\" class=\\\"btn btn-default btn-sm pull-left uib-left\\\" ng-click=\\\"move(-1)\\\" tabindex=\\\"-1\\\"><i aria-hidden=\\\"true\\\" class=\\\"glyphicon glyphicon-chevron-left\\\"></i><span class=\\\"sr-only\\\">previous</span></button></th>\\n\" +\n    \"      <th colspan=\\\"{{::columns - 2}}\\\"><button id=\\\"{{::uniqueId}}-title\\\" role=\\\"heading\\\" aria-live=\\\"assertive\\\" aria-atomic=\\\"true\\\" type=\\\"button\\\" class=\\\"btn btn-default btn-sm uib-title\\\" ng-click=\\\"toggleMode()\\\" ng-disabled=\\\"datepickerMode === maxMode\\\" tabindex=\\\"-1\\\"><strong>{{title}}</strong></button></th>\\n\" +\n    \"      <th><button type=\\\"button\\\" class=\\\"btn btn-default btn-sm pull-right uib-right\\\" ng-click=\\\"move(1)\\\" tabindex=\\\"-1\\\"><i aria-hidden=\\\"true\\\" class=\\\"glyphicon glyphicon-chevron-right\\\"></i><span class=\\\"sr-only\\\">next</span></button></th>\\n\" +\n    \"    </tr>\\n\" +\n    \"  </thead>\\n\" +\n    \"  <tbody>\\n\" +\n    \"    <tr class=\\\"uib-years\\\" ng-repeat=\\\"row in rows track by $index\\\" role=\\\"row\\\">\\n\" +\n    \"      <td ng-repeat=\\\"dt in row\\\" class=\\\"uib-year text-center\\\" role=\\\"gridcell\\\"\\n\" +\n    \"        id=\\\"{{::dt.uid}}\\\"\\n\" +\n    \"        ng-class=\\\"::dt.customClass\\\">\\n\" +\n    \"        <button type=\\\"button\\\" class=\\\"btn btn-default\\\"\\n\" +\n    \"          uib-is-class=\\\"\\n\" +\n    \"            'btn-info' for selectedDt,\\n\" +\n    \"            'active' for activeDt\\n\" +\n    \"            on dt\\\"\\n\" +\n    \"          ng-click=\\\"select(dt.date)\\\"\\n\" +\n    \"          ng-disabled=\\\"::dt.disabled\\\"\\n\" +\n    \"          tabindex=\\\"-1\\\"><span ng-class=\\\"::{'text-info': dt.current}\\\">{{::dt.label}}</span></button>\\n\" +\n    \"      </td>\\n\" +\n    \"    </tr>\\n\" +\n    \"  </tbody>\\n\" +\n    \"</table>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/datepickerPopup/popup.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/datepickerPopup/popup.html\",\n    \"<ul role=\\\"presentation\\\" class=\\\"uib-datepicker-popup dropdown-menu uib-position-measure\\\" dropdown-nested ng-if=\\\"isOpen\\\" ng-keydown=\\\"keydown($event)\\\" ng-click=\\\"$event.stopPropagation()\\\">\\n\" +\n    \"  <li ng-transclude></li>\\n\" +\n    \"  <li ng-if=\\\"showButtonBar\\\" class=\\\"uib-button-bar\\\">\\n\" +\n    \"    <span class=\\\"btn-group pull-left\\\">\\n\" +\n    \"      <button type=\\\"button\\\" class=\\\"btn btn-sm btn-info uib-datepicker-current\\\" ng-click=\\\"select('today', $event)\\\" ng-disabled=\\\"isDisabled('today')\\\">{{ getText('current') }}</button>\\n\" +\n    \"      <button type=\\\"button\\\" class=\\\"btn btn-sm btn-danger uib-clear\\\" ng-click=\\\"select(null, $event)\\\">{{ getText('clear') }}</button>\\n\" +\n    \"    </span>\\n\" +\n    \"    <button type=\\\"button\\\" class=\\\"btn btn-sm btn-success pull-right uib-close\\\" ng-click=\\\"close($event)\\\">{{ getText('close') }}</button>\\n\" +\n    \"  </li>\\n\" +\n    \"</ul>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/modal/backdrop.html\", []).run([\"$templateCache\", function($templateCache) {\n  $templateCache.put(\"uib/template/modal/backdrop.html\",\n    \"<div class=\\\"modal-backdrop\\\"\\n\" +\n    \"     uib-modal-animation-class=\\\"fade\\\"\\n\" +\n    \"     modal-in-class=\\\"in\\\"\\n\" +\n    \"     ng-style=\\\"{'z-index': 1040 + (index && 1 || 0) + index*10}\\\"\\n\" +\n    \"></div>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/modal/window.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/modal/window.html\",\n    \"<div class=\\\"modal-dialog {{size ? 'modal-' + size : ''}}\\\"><div class=\\\"modal-content\\\" uib-modal-transclude></div></div>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/pager/pager.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/pager/pager.html\",\n    \"<li ng-class=\\\"{disabled: noPrevious()||ngDisabled, previous: align}\\\"><a href ng-click=\\\"selectPage(page - 1, $event)\\\" ng-disabled=\\\"noPrevious()||ngDisabled\\\" uib-tabindex-toggle>{{::getText('previous')}}</a></li>\\n\" +\n    \"<li ng-class=\\\"{disabled: noNext()||ngDisabled, next: align}\\\"><a href ng-click=\\\"selectPage(page + 1, $event)\\\" ng-disabled=\\\"noNext()||ngDisabled\\\" uib-tabindex-toggle>{{::getText('next')}}</a></li>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/pagination/pagination.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/pagination/pagination.html\",\n    \"<li role=\\\"menuitem\\\" ng-if=\\\"::boundaryLinks\\\" ng-class=\\\"{disabled: noPrevious()||ngDisabled}\\\" class=\\\"pagination-first\\\"><a href ng-click=\\\"selectPage(1, $event)\\\" ng-disabled=\\\"noPrevious()||ngDisabled\\\" uib-tabindex-toggle>{{::getText('first')}}</a></li>\\n\" +\n    \"<li role=\\\"menuitem\\\" ng-if=\\\"::directionLinks\\\" ng-class=\\\"{disabled: noPrevious()||ngDisabled}\\\" class=\\\"pagination-prev\\\"><a href ng-click=\\\"selectPage(page - 1, $event)\\\" ng-disabled=\\\"noPrevious()||ngDisabled\\\" uib-tabindex-toggle>{{::getText('previous')}}</a></li>\\n\" +\n    \"<li role=\\\"menuitem\\\" ng-repeat=\\\"page in pages track by $index\\\" ng-class=\\\"{active: page.active,disabled: ngDisabled&&!page.active}\\\" class=\\\"pagination-page\\\"><a href ng-click=\\\"selectPage(page.number, $event)\\\" ng-disabled=\\\"ngDisabled&&!page.active\\\" uib-tabindex-toggle>{{page.text}}</a></li>\\n\" +\n    \"<li role=\\\"menuitem\\\" ng-if=\\\"::directionLinks\\\" ng-class=\\\"{disabled: noNext()||ngDisabled}\\\" class=\\\"pagination-next\\\"><a href ng-click=\\\"selectPage(page + 1, $event)\\\" ng-disabled=\\\"noNext()||ngDisabled\\\" uib-tabindex-toggle>{{::getText('next')}}</a></li>\\n\" +\n    \"<li role=\\\"menuitem\\\" ng-if=\\\"::boundaryLinks\\\" ng-class=\\\"{disabled: noNext()||ngDisabled}\\\" class=\\\"pagination-last\\\"><a href ng-click=\\\"selectPage(totalPages, $event)\\\" ng-disabled=\\\"noNext()||ngDisabled\\\" uib-tabindex-toggle>{{::getText('last')}}</a></li>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/tooltip/tooltip-html-popup.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/tooltip/tooltip-html-popup.html\",\n    \"<div class=\\\"tooltip-arrow\\\"></div>\\n\" +\n    \"<div class=\\\"tooltip-inner\\\" ng-bind-html=\\\"contentExp()\\\"></div>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/tooltip/tooltip-popup.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/tooltip/tooltip-popup.html\",\n    \"<div class=\\\"tooltip-arrow\\\"></div>\\n\" +\n    \"<div class=\\\"tooltip-inner\\\" ng-bind=\\\"content\\\"></div>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/tooltip/tooltip-template-popup.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/tooltip/tooltip-template-popup.html\",\n    \"<div class=\\\"tooltip-arrow\\\"></div>\\n\" +\n    \"<div class=\\\"tooltip-inner\\\"\\n\" +\n    \"  uib-tooltip-template-transclude=\\\"contentExp()\\\"\\n\" +\n    \"  tooltip-template-transclude-scope=\\\"originScope()\\\"></div>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/popover/popover-html.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/popover/popover-html.html\",\n    \"<div class=\\\"arrow\\\"></div>\\n\" +\n    \"\\n\" +\n    \"<div class=\\\"popover-inner\\\">\\n\" +\n    \"    <h3 class=\\\"popover-title\\\" ng-bind=\\\"uibTitle\\\" ng-if=\\\"uibTitle\\\"></h3>\\n\" +\n    \"    <div class=\\\"popover-content\\\" ng-bind-html=\\\"contentExp()\\\"></div>\\n\" +\n    \"</div>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/popover/popover-template.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/popover/popover-template.html\",\n    \"<div class=\\\"arrow\\\"></div>\\n\" +\n    \"\\n\" +\n    \"<div class=\\\"popover-inner\\\">\\n\" +\n    \"    <h3 class=\\\"popover-title\\\" ng-bind=\\\"uibTitle\\\" ng-if=\\\"uibTitle\\\"></h3>\\n\" +\n    \"    <div class=\\\"popover-content\\\"\\n\" +\n    \"      uib-tooltip-template-transclude=\\\"contentExp()\\\"\\n\" +\n    \"      tooltip-template-transclude-scope=\\\"originScope()\\\"></div>\\n\" +\n    \"</div>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/popover/popover.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/popover/popover.html\",\n    \"<div class=\\\"arrow\\\"></div>\\n\" +\n    \"\\n\" +\n    \"<div class=\\\"popover-inner\\\">\\n\" +\n    \"    <h3 class=\\\"popover-title\\\" ng-bind=\\\"uibTitle\\\" ng-if=\\\"uibTitle\\\"></h3>\\n\" +\n    \"    <div class=\\\"popover-content\\\" ng-bind=\\\"content\\\"></div>\\n\" +\n    \"</div>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/progressbar/bar.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/progressbar/bar.html\",\n    \"<div class=\\\"progress-bar\\\" ng-class=\\\"type && 'progress-bar-' + type\\\" role=\\\"progressbar\\\" aria-valuenow=\\\"{{value}}\\\" aria-valuemin=\\\"0\\\" aria-valuemax=\\\"{{max}}\\\" ng-style=\\\"{width: (percent < 100 ? percent : 100) + '%'}\\\" aria-valuetext=\\\"{{percent | number:0}}%\\\" aria-labelledby=\\\"{{::title}}\\\" ng-transclude></div>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/progressbar/progress.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/progressbar/progress.html\",\n    \"<div class=\\\"progress\\\" ng-transclude aria-labelledby=\\\"{{::title}}\\\"></div>\");\n}]);\n\nangular.module(\"uib/template/progressbar/progressbar.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/progressbar/progressbar.html\",\n    \"<div class=\\\"progress\\\">\\n\" +\n    \"  <div class=\\\"progress-bar\\\" ng-class=\\\"type && 'progress-bar-' + type\\\" role=\\\"progressbar\\\" aria-valuenow=\\\"{{value}}\\\" aria-valuemin=\\\"0\\\" aria-valuemax=\\\"{{max}}\\\" ng-style=\\\"{width: (percent < 100 ? percent : 100) + '%'}\\\" aria-valuetext=\\\"{{percent | number:0}}%\\\" aria-labelledby=\\\"{{::title}}\\\" ng-transclude></div>\\n\" +\n    \"</div>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/rating/rating.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/rating/rating.html\",\n    \"<span ng-mouseleave=\\\"reset()\\\" ng-keydown=\\\"onKeydown($event)\\\" tabindex=\\\"0\\\" role=\\\"slider\\\" aria-valuemin=\\\"0\\\" aria-valuemax=\\\"{{range.length}}\\\" aria-valuenow=\\\"{{value}}\\\" aria-valuetext=\\\"{{title}}\\\">\\n\" +\n    \"    <span ng-repeat-start=\\\"r in range track by $index\\\" class=\\\"sr-only\\\">({{ $index < value ? '*' : ' ' }})</span>\\n\" +\n    \"    <i ng-repeat-end ng-mouseenter=\\\"enter($index + 1)\\\" ng-click=\\\"rate($index + 1)\\\" class=\\\"glyphicon\\\" ng-class=\\\"$index < value && (r.stateOn || 'glyphicon-star') || (r.stateOff || 'glyphicon-star-empty')\\\" ng-attr-title=\\\"{{r.title}}\\\"></i>\\n\" +\n    \"</span>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/tabs/tab.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/tabs/tab.html\",\n    \"<li ng-class=\\\"[{active: active, disabled: disabled}, classes]\\\" class=\\\"uib-tab nav-item\\\">\\n\" +\n    \"  <a href ng-click=\\\"select($event)\\\" class=\\\"nav-link\\\" uib-tab-heading-transclude>{{heading}}</a>\\n\" +\n    \"</li>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/tabs/tabset.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/tabs/tabset.html\",\n    \"<div>\\n\" +\n    \"  <ul class=\\\"nav nav-{{tabset.type || 'tabs'}}\\\" ng-class=\\\"{'nav-stacked': vertical, 'nav-justified': justified}\\\" ng-transclude></ul>\\n\" +\n    \"  <div class=\\\"tab-content\\\">\\n\" +\n    \"    <div class=\\\"tab-pane\\\"\\n\" +\n    \"         ng-repeat=\\\"tab in tabset.tabs\\\"\\n\" +\n    \"         ng-class=\\\"{active: tabset.active === tab.index}\\\"\\n\" +\n    \"         uib-tab-content-transclude=\\\"tab\\\">\\n\" +\n    \"    </div>\\n\" +\n    \"  </div>\\n\" +\n    \"</div>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/timepicker/timepicker.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/timepicker/timepicker.html\",\n    \"<table class=\\\"uib-timepicker\\\">\\n\" +\n    \"  <tbody>\\n\" +\n    \"    <tr class=\\\"text-center\\\" ng-show=\\\"::showSpinners\\\">\\n\" +\n    \"      <td class=\\\"uib-increment hours\\\"><a ng-click=\\\"incrementHours()\\\" ng-class=\\\"{disabled: noIncrementHours()}\\\" class=\\\"btn btn-link\\\" ng-disabled=\\\"noIncrementHours()\\\" tabindex=\\\"-1\\\"><span class=\\\"glyphicon glyphicon-chevron-up\\\"></span></a></td>\\n\" +\n    \"      <td>&nbsp;</td>\\n\" +\n    \"      <td class=\\\"uib-increment minutes\\\"><a ng-click=\\\"incrementMinutes()\\\" ng-class=\\\"{disabled: noIncrementMinutes()}\\\" class=\\\"btn btn-link\\\" ng-disabled=\\\"noIncrementMinutes()\\\" tabindex=\\\"-1\\\"><span class=\\\"glyphicon glyphicon-chevron-up\\\"></span></a></td>\\n\" +\n    \"      <td ng-show=\\\"showSeconds\\\">&nbsp;</td>\\n\" +\n    \"      <td ng-show=\\\"showSeconds\\\" class=\\\"uib-increment seconds\\\"><a ng-click=\\\"incrementSeconds()\\\" ng-class=\\\"{disabled: noIncrementSeconds()}\\\" class=\\\"btn btn-link\\\" ng-disabled=\\\"noIncrementSeconds()\\\" tabindex=\\\"-1\\\"><span class=\\\"glyphicon glyphicon-chevron-up\\\"></span></a></td>\\n\" +\n    \"      <td ng-show=\\\"showMeridian\\\"></td>\\n\" +\n    \"    </tr>\\n\" +\n    \"    <tr>\\n\" +\n    \"      <td class=\\\"form-group uib-time hours\\\" ng-class=\\\"{'has-error': invalidHours}\\\">\\n\" +\n    \"        <input type=\\\"text\\\" placeholder=\\\"HH\\\" ng-model=\\\"hours\\\" ng-change=\\\"updateHours()\\\" class=\\\"form-control text-center\\\" ng-readonly=\\\"::readonlyInput\\\" maxlength=\\\"2\\\" tabindex=\\\"{{::tabindex}}\\\" ng-disabled=\\\"noIncrementHours()\\\" ng-blur=\\\"blur()\\\">\\n\" +\n    \"      </td>\\n\" +\n    \"      <td class=\\\"uib-separator\\\">:</td>\\n\" +\n    \"      <td class=\\\"form-group uib-time minutes\\\" ng-class=\\\"{'has-error': invalidMinutes}\\\">\\n\" +\n    \"        <input type=\\\"text\\\" placeholder=\\\"MM\\\" ng-model=\\\"minutes\\\" ng-change=\\\"updateMinutes()\\\" class=\\\"form-control text-center\\\" ng-readonly=\\\"::readonlyInput\\\" maxlength=\\\"2\\\" tabindex=\\\"{{::tabindex}}\\\" ng-disabled=\\\"noIncrementMinutes()\\\" ng-blur=\\\"blur()\\\">\\n\" +\n    \"      </td>\\n\" +\n    \"      <td ng-show=\\\"showSeconds\\\" class=\\\"uib-separator\\\">:</td>\\n\" +\n    \"      <td class=\\\"form-group uib-time seconds\\\" ng-class=\\\"{'has-error': invalidSeconds}\\\" ng-show=\\\"showSeconds\\\">\\n\" +\n    \"        <input type=\\\"text\\\" placeholder=\\\"SS\\\" ng-model=\\\"seconds\\\" ng-change=\\\"updateSeconds()\\\" class=\\\"form-control text-center\\\" ng-readonly=\\\"readonlyInput\\\" maxlength=\\\"2\\\" tabindex=\\\"{{::tabindex}}\\\" ng-disabled=\\\"noIncrementSeconds()\\\" ng-blur=\\\"blur()\\\">\\n\" +\n    \"      </td>\\n\" +\n    \"      <td ng-show=\\\"showMeridian\\\" class=\\\"uib-time am-pm\\\"><button type=\\\"button\\\" ng-class=\\\"{disabled: noToggleMeridian()}\\\" class=\\\"btn btn-default text-center\\\" ng-click=\\\"toggleMeridian()\\\" ng-disabled=\\\"noToggleMeridian()\\\" tabindex=\\\"{{::tabindex}}\\\">{{meridian}}</button></td>\\n\" +\n    \"    </tr>\\n\" +\n    \"    <tr class=\\\"text-center\\\" ng-show=\\\"::showSpinners\\\">\\n\" +\n    \"      <td class=\\\"uib-decrement hours\\\"><a ng-click=\\\"decrementHours()\\\" ng-class=\\\"{disabled: noDecrementHours()}\\\" class=\\\"btn btn-link\\\" ng-disabled=\\\"noDecrementHours()\\\" tabindex=\\\"-1\\\"><span class=\\\"glyphicon glyphicon-chevron-down\\\"></span></a></td>\\n\" +\n    \"      <td>&nbsp;</td>\\n\" +\n    \"      <td class=\\\"uib-decrement minutes\\\"><a ng-click=\\\"decrementMinutes()\\\" ng-class=\\\"{disabled: noDecrementMinutes()}\\\" class=\\\"btn btn-link\\\" ng-disabled=\\\"noDecrementMinutes()\\\" tabindex=\\\"-1\\\"><span class=\\\"glyphicon glyphicon-chevron-down\\\"></span></a></td>\\n\" +\n    \"      <td ng-show=\\\"showSeconds\\\">&nbsp;</td>\\n\" +\n    \"      <td ng-show=\\\"showSeconds\\\" class=\\\"uib-decrement seconds\\\"><a ng-click=\\\"decrementSeconds()\\\" ng-class=\\\"{disabled: noDecrementSeconds()}\\\" class=\\\"btn btn-link\\\" ng-disabled=\\\"noDecrementSeconds()\\\" tabindex=\\\"-1\\\"><span class=\\\"glyphicon glyphicon-chevron-down\\\"></span></a></td>\\n\" +\n    \"      <td ng-show=\\\"showMeridian\\\"></td>\\n\" +\n    \"    </tr>\\n\" +\n    \"  </tbody>\\n\" +\n    \"</table>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/typeahead/typeahead-match.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/typeahead/typeahead-match.html\",\n    \"<a href\\n\" +\n    \"   tabindex=\\\"-1\\\"\\n\" +\n    \"   ng-bind-html=\\\"match.label | uibTypeaheadHighlight:query\\\"\\n\" +\n    \"   ng-attr-title=\\\"{{match.label}}\\\"></a>\\n\" +\n    \"\");\n}]);\n\nangular.module(\"uib/template/typeahead/typeahead-popup.html\", []).run([\"$templateCache\", function ($templateCache) {\n  $templateCache.put(\"uib/template/typeahead/typeahead-popup.html\",\n    \"<ul class=\\\"dropdown-menu\\\" ng-show=\\\"isOpen() && !moveInProgress\\\" ng-style=\\\"{top: position().top+'px', left: position().left+'px'}\\\" role=\\\"listbox\\\" aria-hidden=\\\"{{!isOpen()}}\\\">\\n\" +\n    \"    <li class=\\\"uib-typeahead-match\\\" ng-repeat=\\\"match in matches track by $index\\\" ng-class=\\\"{active: isActive($index) }\\\" ng-mouseenter=\\\"selectActive($index)\\\" ng-click=\\\"selectMatch($index, $event)\\\" role=\\\"option\\\" id=\\\"{{::match.id}}\\\">\\n\" +\n    \"        <div uib-typeahead-match index=\\\"$index\\\" match=\\\"match\\\" query=\\\"query\\\" template-url=\\\"templateUrl\\\"></div>\\n\" +\n    \"    </li>\\n\" +\n    \"</ul>\\n\" +\n    \"\");\n}]);\nangular.module('ui.bootstrap.carousel').run(function() {!angular.$$csp().noInlineStyle && !angular.$$uibCarouselCss && angular.element(document).find('head').prepend('<style type=\"text/css\">.ng-animate.item:not(.left):not(.right){-webkit-transition:0s ease-in-out left;transition:0s ease-in-out left}</style>'); angular.$$uibCarouselCss = true; });\nangular.module('ui.bootstrap.datepicker').run(function() {!angular.$$csp().noInlineStyle && !angular.$$uibDatepickerCss && angular.element(document).find('head').prepend('<style type=\"text/css\">.uib-datepicker .uib-title{width:100%;}.uib-day button,.uib-month button,.uib-year button{min-width:100%;}.uib-left,.uib-right{width:100%}</style>'); angular.$$uibDatepickerCss = true; });\nangular.module('ui.bootstrap.position').run(function() {!angular.$$csp().noInlineStyle && !angular.$$uibPositionCss && angular.element(document).find('head').prepend('<style type=\"text/css\">.uib-position-measure{display:block !important;visibility:hidden !important;position:absolute !important;top:-9999px !important;left:-9999px !important;}.uib-position-scrollbar-measure{position:absolute !important;top:-9999px !important;width:50px !important;height:50px !important;overflow:scroll !important;}.uib-position-body-scrollbar-measure{overflow:scroll !important;}</style>'); angular.$$uibPositionCss = true; });\nangular.module('ui.bootstrap.datepickerPopup').run(function() {!angular.$$csp().noInlineStyle && !angular.$$uibDatepickerpopupCss && angular.element(document).find('head').prepend('<style type=\"text/css\">.uib-datepicker-popup.dropdown-menu{display:block;float:none;margin:0;}.uib-button-bar{padding:10px 9px 2px;}</style>'); angular.$$uibDatepickerpopupCss = true; });\nangular.module('ui.bootstrap.tooltip').run(function() {!angular.$$csp().noInlineStyle && !angular.$$uibTooltipCss && angular.element(document).find('head').prepend('<style type=\"text/css\">[uib-tooltip-popup].tooltip.top-left > .tooltip-arrow,[uib-tooltip-popup].tooltip.top-right > .tooltip-arrow,[uib-tooltip-popup].tooltip.bottom-left > .tooltip-arrow,[uib-tooltip-popup].tooltip.bottom-right > .tooltip-arrow,[uib-tooltip-popup].tooltip.left-top > .tooltip-arrow,[uib-tooltip-popup].tooltip.left-bottom > .tooltip-arrow,[uib-tooltip-popup].tooltip.right-top > .tooltip-arrow,[uib-tooltip-popup].tooltip.right-bottom > .tooltip-arrow,[uib-tooltip-html-popup].tooltip.top-left > .tooltip-arrow,[uib-tooltip-html-popup].tooltip.top-right > .tooltip-arrow,[uib-tooltip-html-popup].tooltip.bottom-left > .tooltip-arrow,[uib-tooltip-html-popup].tooltip.bottom-right > .tooltip-arrow,[uib-tooltip-html-popup].tooltip.left-top > .tooltip-arrow,[uib-tooltip-html-popup].tooltip.left-bottom > .tooltip-arrow,[uib-tooltip-html-popup].tooltip.right-top > .tooltip-arrow,[uib-tooltip-html-popup].tooltip.right-bottom > .tooltip-arrow,[uib-tooltip-template-popup].tooltip.top-left > .tooltip-arrow,[uib-tooltip-template-popup].tooltip.top-right > .tooltip-arrow,[uib-tooltip-template-popup].tooltip.bottom-left > .tooltip-arrow,[uib-tooltip-template-popup].tooltip.bottom-right > .tooltip-arrow,[uib-tooltip-template-popup].tooltip.left-top > .tooltip-arrow,[uib-tooltip-template-popup].tooltip.left-bottom > .tooltip-arrow,[uib-tooltip-template-popup].tooltip.right-top > .tooltip-arrow,[uib-tooltip-template-popup].tooltip.right-bottom > .tooltip-arrow,[uib-popover-popup].popover.top-left > .arrow,[uib-popover-popup].popover.top-right > .arrow,[uib-popover-popup].popover.bottom-left > .arrow,[uib-popover-popup].popover.bottom-right > .arrow,[uib-popover-popup].popover.left-top > .arrow,[uib-popover-popup].popover.left-bottom > .arrow,[uib-popover-popup].popover.right-top > .arrow,[uib-popover-popup].popover.right-bottom > .arrow,[uib-popover-html-popup].popover.top-left > .arrow,[uib-popover-html-popup].popover.top-right > .arrow,[uib-popover-html-popup].popover.bottom-left > .arrow,[uib-popover-html-popup].popover.bottom-right > .arrow,[uib-popover-html-popup].popover.left-top > .arrow,[uib-popover-html-popup].popover.left-bottom > .arrow,[uib-popover-html-popup].popover.right-top > .arrow,[uib-popover-html-popup].popover.right-bottom > .arrow,[uib-popover-template-popup].popover.top-left > .arrow,[uib-popover-template-popup].popover.top-right > .arrow,[uib-popover-template-popup].popover.bottom-left > .arrow,[uib-popover-template-popup].popover.bottom-right > .arrow,[uib-popover-template-popup].popover.left-top > .arrow,[uib-popover-template-popup].popover.left-bottom > .arrow,[uib-popover-template-popup].popover.right-top > .arrow,[uib-popover-template-popup].popover.right-bottom > .arrow{top:auto;bottom:auto;left:auto;right:auto;margin:0;}[uib-popover-popup].popover,[uib-popover-html-popup].popover,[uib-popover-template-popup].popover{display:block !important;}</style>'); angular.$$uibTooltipCss = true; });\nangular.module('ui.bootstrap.timepicker').run(function() {!angular.$$csp().noInlineStyle && !angular.$$uibTimepickerCss && angular.element(document).find('head').prepend('<style type=\"text/css\">.uib-time input{width:50px;}</style>'); angular.$$uibTimepickerCss = true; });\nangular.module('ui.bootstrap.typeahead').run(function() {!angular.$$csp().noInlineStyle && !angular.$$uibTypeaheadCss && angular.element(document).find('head').prepend('<style type=\"text/css\">[uib-typeahead-popup].dropdown-menu{display:block;}</style>'); angular.$$uibTypeaheadCss = true; });","require('./dist/ui-bootstrap-tpls');\n\nmodule.exports = 'ui.bootstrap';\n","/**\n * @license AngularJS v1.8.3\n * (c) 2010-2020 Google LLC. http://angularjs.org\n * License: MIT\n */\n(function(window, angular) {'use strict';\n\n/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *\n *     Any commits to this file should be reviewed with security in mind.  *\n *   Changes to this file can potentially create security vulnerabilities. *\n *          An approval from 2 Core members with history of modifying      *\n *                         this file is required.                          *\n *                                                                         *\n *  Does the change somehow allow for arbitrary javascript to be executed? *\n *    Or allows for someone to change the prototype of built-in objects?   *\n *     Or gives undesired access to variables likes document or window?    *\n * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */\n\nvar $sanitizeMinErr = angular.$$minErr('$sanitize');\nvar bind;\nvar extend;\nvar forEach;\nvar isArray;\nvar isDefined;\nvar lowercase;\nvar noop;\nvar nodeContains;\nvar htmlParser;\nvar htmlSanitizeWriter;\n\n/**\n * @ngdoc module\n * @name ngSanitize\n * @description\n *\n * The `ngSanitize` module provides functionality to sanitize HTML.\n *\n * See {@link ngSanitize.$sanitize `$sanitize`} for usage.\n */\n\n/**\n * @ngdoc service\n * @name $sanitize\n * @kind function\n *\n * @description\n *   Sanitizes an html string by stripping all potentially dangerous tokens.\n *\n *   The input is sanitized by parsing the HTML into tokens. All safe tokens (from a trusted URI list) are\n *   then serialized back to a properly escaped HTML string. This means that no unsafe input can make\n *   it into the returned string.\n *\n *   The trusted URIs for URL sanitization of attribute values is configured using the functions\n *   `aHrefSanitizationTrustedUrlList` and `imgSrcSanitizationTrustedUrlList` of {@link $compileProvider}.\n *\n *   The input may also contain SVG markup if this is enabled via {@link $sanitizeProvider}.\n *\n * @param {string} html HTML input.\n * @returns {string} Sanitized HTML.\n *\n * @example\n   <example module=\"sanitizeExample\" deps=\"angular-sanitize.js\" name=\"sanitize-service\">\n   <file name=\"index.html\">\n     <script>\n         angular.module('sanitizeExample', ['ngSanitize'])\n           .controller('ExampleController', ['$scope', '$sce', function($scope, $sce) {\n             $scope.snippet =\n               '<p style=\"color:blue\">an html\\n' +\n               '<em onmouseover=\"this.textContent=\\'PWN3D!\\'\">click here</em>\\n' +\n               'snippet</p>';\n             $scope.deliberatelyTrustDangerousSnippet = function() {\n               return $sce.trustAsHtml($scope.snippet);\n             };\n           }]);\n     </script>\n     <div ng-controller=\"ExampleController\">\n        Snippet: <textarea ng-model=\"snippet\" cols=\"60\" rows=\"3\"></textarea>\n       <table>\n         <tr>\n           <td>Directive</td>\n           <td>How</td>\n           <td>Source</td>\n           <td>Rendered</td>\n         </tr>\n         <tr id=\"bind-html-with-sanitize\">\n           <td>ng-bind-html</td>\n           <td>Automatically uses $sanitize</td>\n           <td><pre>&lt;div ng-bind-html=\"snippet\"&gt;<br/>&lt;/div&gt;</pre></td>\n           <td><div ng-bind-html=\"snippet\"></div></td>\n         </tr>\n         <tr id=\"bind-html-with-trust\">\n           <td>ng-bind-html</td>\n           <td>Bypass $sanitize by explicitly trusting the dangerous value</td>\n           <td>\n           <pre>&lt;div ng-bind-html=\"deliberatelyTrustDangerousSnippet()\"&gt;\n&lt;/div&gt;</pre>\n           </td>\n           <td><div ng-bind-html=\"deliberatelyTrustDangerousSnippet()\"></div></td>\n         </tr>\n         <tr id=\"bind-default\">\n           <td>ng-bind</td>\n           <td>Automatically escapes</td>\n           <td><pre>&lt;div ng-bind=\"snippet\"&gt;<br/>&lt;/div&gt;</pre></td>\n           <td><div ng-bind=\"snippet\"></div></td>\n         </tr>\n       </table>\n       </div>\n   </file>\n   <file name=\"protractor.js\" type=\"protractor\">\n     it('should sanitize the html snippet by default', function() {\n       expect(element(by.css('#bind-html-with-sanitize div')).getAttribute('innerHTML')).\n         toBe('<p>an html\\n<em>click here</em>\\nsnippet</p>');\n     });\n\n     it('should inline raw snippet if bound to a trusted value', function() {\n       expect(element(by.css('#bind-html-with-trust div')).getAttribute('innerHTML')).\n         toBe(\"<p style=\\\"color:blue\\\">an html\\n\" +\n              \"<em onmouseover=\\\"this.textContent='PWN3D!'\\\">click here</em>\\n\" +\n              \"snippet</p>\");\n     });\n\n     it('should escape snippet without any filter', function() {\n       expect(element(by.css('#bind-default div')).getAttribute('innerHTML')).\n         toBe(\"&lt;p style=\\\"color:blue\\\"&gt;an html\\n\" +\n              \"&lt;em onmouseover=\\\"this.textContent='PWN3D!'\\\"&gt;click here&lt;/em&gt;\\n\" +\n              \"snippet&lt;/p&gt;\");\n     });\n\n     it('should update', function() {\n       element(by.model('snippet')).clear();\n       element(by.model('snippet')).sendKeys('new <b onclick=\"alert(1)\">text</b>');\n       expect(element(by.css('#bind-html-with-sanitize div')).getAttribute('innerHTML')).\n         toBe('new <b>text</b>');\n       expect(element(by.css('#bind-html-with-trust div')).getAttribute('innerHTML')).toBe(\n         'new <b onclick=\"alert(1)\">text</b>');\n       expect(element(by.css('#bind-default div')).getAttribute('innerHTML')).toBe(\n         \"new &lt;b onclick=\\\"alert(1)\\\"&gt;text&lt;/b&gt;\");\n     });\n   </file>\n   </example>\n */\n\n\n/**\n * @ngdoc provider\n * @name $sanitizeProvider\n * @this\n *\n * @description\n * Creates and configures {@link $sanitize} instance.\n */\nfunction $SanitizeProvider() {\n  var hasBeenInstantiated = false;\n  var svgEnabled = false;\n\n  this.$get = ['$$sanitizeUri', function($$sanitizeUri) {\n    hasBeenInstantiated = true;\n    if (svgEnabled) {\n      extend(validElements, svgElements);\n    }\n    return function(html) {\n      var buf = [];\n      htmlParser(html, htmlSanitizeWriter(buf, function(uri, isImage) {\n        return !/^unsafe:/.test($$sanitizeUri(uri, isImage));\n      }));\n      return buf.join('');\n    };\n  }];\n\n\n  /**\n   * @ngdoc method\n   * @name $sanitizeProvider#enableSvg\n   * @kind function\n   *\n   * @description\n   * Enables a subset of svg to be supported by the sanitizer.\n   *\n   * <div class=\"alert alert-warning\">\n   *   <p>By enabling this setting without taking other precautions, you might expose your\n   *   application to click-hijacking attacks. In these attacks, sanitized svg elements could be positioned\n   *   outside of the containing element and be rendered over other elements on the page (e.g. a login\n   *   link). Such behavior can then result in phishing incidents.</p>\n   *\n   *   <p>To protect against these, explicitly setup `overflow: hidden` css rule for all potential svg\n   *   tags within the sanitized content:</p>\n   *\n   *   <br>\n   *\n   *   <pre><code>\n   *   .rootOfTheIncludedContent svg {\n   *     overflow: hidden !important;\n   *   }\n   *   </code></pre>\n   * </div>\n   *\n   * @param {boolean=} flag Enable or disable SVG support in the sanitizer.\n   * @returns {boolean|$sanitizeProvider} Returns the currently configured value if called\n   *    without an argument or self for chaining otherwise.\n   */\n  this.enableSvg = function(enableSvg) {\n    if (isDefined(enableSvg)) {\n      svgEnabled = enableSvg;\n      return this;\n    } else {\n      return svgEnabled;\n    }\n  };\n\n\n  /**\n   * @ngdoc method\n   * @name $sanitizeProvider#addValidElements\n   * @kind function\n   *\n   * @description\n   * Extends the built-in lists of valid HTML/SVG elements, i.e. elements that are considered safe\n   * and are not stripped off during sanitization. You can extend the following lists of elements:\n   *\n   * - `htmlElements`: A list of elements (tag names) to extend the current list of safe HTML\n   *   elements. HTML elements considered safe will not be removed during sanitization. All other\n   *   elements will be stripped off.\n   *\n   * - `htmlVoidElements`: This is similar to `htmlElements`, but marks the elements as\n   *   \"void elements\" (similar to HTML\n   *   [void elements](https://rawgit.com/w3c/html/html5.1-2/single-page.html#void-elements)). These\n   *   elements have no end tag and cannot have content.\n   *\n   * - `svgElements`: This is similar to `htmlElements`, but for SVG elements. This list is only\n   *   taken into account if SVG is {@link ngSanitize.$sanitizeProvider#enableSvg enabled} for\n   *   `$sanitize`.\n   *\n   * <div class=\"alert alert-info\">\n   *   This method must be called during the {@link angular.Module#config config} phase. Once the\n   *   `$sanitize` service has been instantiated, this method has no effect.\n   * </div>\n   *\n   * <div class=\"alert alert-warning\">\n   *   Keep in mind that extending the built-in lists of elements may expose your app to XSS or\n   *   other vulnerabilities. Be very mindful of the elements you add.\n   * </div>\n   *\n   * @param {Array<String>|Object} elements - A list of valid HTML elements or an object with one or\n   *   more of the following properties:\n   *   - **htmlElements** - `{Array<String>}` - A list of elements to extend the current list of\n   *     HTML elements.\n   *   - **htmlVoidElements** - `{Array<String>}` - A list of elements to extend the current list of\n   *     void HTML elements; i.e. elements that do not have an end tag.\n   *   - **svgElements** - `{Array<String>}` - A list of elements to extend the current list of SVG\n   *     elements. The list of SVG elements is only taken into account if SVG is\n   *     {@link ngSanitize.$sanitizeProvider#enableSvg enabled} for `$sanitize`.\n   *\n   * Passing an array (`[...]`) is equivalent to passing `{htmlElements: [...]}`.\n   *\n   * @return {$sanitizeProvider} Returns self for chaining.\n   */\n  this.addValidElements = function(elements) {\n    if (!hasBeenInstantiated) {\n      if (isArray(elements)) {\n        elements = {htmlElements: elements};\n      }\n\n      addElementsTo(svgElements, elements.svgElements);\n      addElementsTo(voidElements, elements.htmlVoidElements);\n      addElementsTo(validElements, elements.htmlVoidElements);\n      addElementsTo(validElements, elements.htmlElements);\n    }\n\n    return this;\n  };\n\n\n  /**\n   * @ngdoc method\n   * @name $sanitizeProvider#addValidAttrs\n   * @kind function\n   *\n   * @description\n   * Extends the built-in list of valid attributes, i.e. attributes that are considered safe and are\n   * not stripped off during sanitization.\n   *\n   * **Note**:\n   * The new attributes will not be treated as URI attributes, which means their values will not be\n   * sanitized as URIs using `$compileProvider`'s\n   * {@link ng.$compileProvider#aHrefSanitizationTrustedUrlList aHrefSanitizationTrustedUrlList} and\n   * {@link ng.$compileProvider#imgSrcSanitizationTrustedUrlList imgSrcSanitizationTrustedUrlList}.\n   *\n   * <div class=\"alert alert-info\">\n   *   This method must be called during the {@link angular.Module#config config} phase. Once the\n   *   `$sanitize` service has been instantiated, this method has no effect.\n   * </div>\n   *\n   * <div class=\"alert alert-warning\">\n   *   Keep in mind that extending the built-in list of attributes may expose your app to XSS or\n   *   other vulnerabilities. Be very mindful of the attributes you add.\n   * </div>\n   *\n   * @param {Array<String>} attrs - A list of valid attributes.\n   *\n   * @returns {$sanitizeProvider} Returns self for chaining.\n   */\n  this.addValidAttrs = function(attrs) {\n    if (!hasBeenInstantiated) {\n      extend(validAttrs, arrayToMap(attrs, true));\n    }\n    return this;\n  };\n\n  //////////////////////////////////////////////////////////////////////////////////////////////////\n  // Private stuff\n  //////////////////////////////////////////////////////////////////////////////////////////////////\n\n  bind = angular.bind;\n  extend = angular.extend;\n  forEach = angular.forEach;\n  isArray = angular.isArray;\n  isDefined = angular.isDefined;\n  lowercase = angular.$$lowercase;\n  noop = angular.noop;\n\n  htmlParser = htmlParserImpl;\n  htmlSanitizeWriter = htmlSanitizeWriterImpl;\n\n  nodeContains = window.Node.prototype.contains || /** @this */ function(arg) {\n    // eslint-disable-next-line no-bitwise\n    return !!(this.compareDocumentPosition(arg) & 16);\n  };\n\n  // Regular Expressions for parsing tags and attributes\n  var SURROGATE_PAIR_REGEXP = /[\\uD800-\\uDBFF][\\uDC00-\\uDFFF]/g,\n    // Match everything outside of normal chars and \" (quote character)\n    NON_ALPHANUMERIC_REGEXP = /([^#-~ |!])/g;\n\n\n  // Good source of info about elements and attributes\n  // http://dev.w3.org/html5/spec/Overview.html#semantics\n  // http://simon.html5.org/html-elements\n\n  // Safe Void Elements - HTML5\n  // http://dev.w3.org/html5/spec/Overview.html#void-elements\n  var voidElements = stringToMap('area,br,col,hr,img,wbr');\n\n  // Elements that you can, intentionally, leave open (and which close themselves)\n  // http://dev.w3.org/html5/spec/Overview.html#optional-tags\n  var optionalEndTagBlockElements = stringToMap('colgroup,dd,dt,li,p,tbody,td,tfoot,th,thead,tr'),\n      optionalEndTagInlineElements = stringToMap('rp,rt'),\n      optionalEndTagElements = extend({},\n                                              optionalEndTagInlineElements,\n                                              optionalEndTagBlockElements);\n\n  // Safe Block Elements - HTML5\n  var blockElements = extend({}, optionalEndTagBlockElements, stringToMap('address,article,' +\n          'aside,blockquote,caption,center,del,dir,div,dl,figure,figcaption,footer,h1,h2,h3,h4,h5,' +\n          'h6,header,hgroup,hr,ins,map,menu,nav,ol,pre,section,table,ul'));\n\n  // Inline Elements - HTML5\n  var inlineElements = extend({}, optionalEndTagInlineElements, stringToMap('a,abbr,acronym,b,' +\n          'bdi,bdo,big,br,cite,code,del,dfn,em,font,i,img,ins,kbd,label,map,mark,q,ruby,rp,rt,s,' +\n          'samp,small,span,strike,strong,sub,sup,time,tt,u,var'));\n\n  // SVG Elements\n  // https://wiki.whatwg.org/wiki/Sanitization_rules#svg_Elements\n  // Note: the elements animate,animateColor,animateMotion,animateTransform,set are intentionally omitted.\n  // They can potentially allow for arbitrary javascript to be executed. See #11290\n  var svgElements = stringToMap('circle,defs,desc,ellipse,font-face,font-face-name,font-face-src,g,glyph,' +\n          'hkern,image,linearGradient,line,marker,metadata,missing-glyph,mpath,path,polygon,polyline,' +\n          'radialGradient,rect,stop,svg,switch,text,title,tspan');\n\n  // Blocked Elements (will be stripped)\n  var blockedElements = stringToMap('script,style');\n\n  var validElements = extend({},\n                                     voidElements,\n                                     blockElements,\n                                     inlineElements,\n                                     optionalEndTagElements);\n\n  //Attributes that have href and hence need to be sanitized\n  var uriAttrs = stringToMap('background,cite,href,longdesc,src,xlink:href,xml:base');\n\n  var htmlAttrs = stringToMap('abbr,align,alt,axis,bgcolor,border,cellpadding,cellspacing,class,clear,' +\n      'color,cols,colspan,compact,coords,dir,face,headers,height,hreflang,hspace,' +\n      'ismap,lang,language,nohref,nowrap,rel,rev,rows,rowspan,rules,' +\n      'scope,scrolling,shape,size,span,start,summary,tabindex,target,title,type,' +\n      'valign,value,vspace,width');\n\n  // SVG attributes (without \"id\" and \"name\" attributes)\n  // https://wiki.whatwg.org/wiki/Sanitization_rules#svg_Attributes\n  var svgAttrs = stringToMap('accent-height,accumulate,additive,alphabetic,arabic-form,ascent,' +\n      'baseProfile,bbox,begin,by,calcMode,cap-height,class,color,color-rendering,content,' +\n      'cx,cy,d,dx,dy,descent,display,dur,end,fill,fill-rule,font-family,font-size,font-stretch,' +\n      'font-style,font-variant,font-weight,from,fx,fy,g1,g2,glyph-name,gradientUnits,hanging,' +\n      'height,horiz-adv-x,horiz-origin-x,ideographic,k,keyPoints,keySplines,keyTimes,lang,' +\n      'marker-end,marker-mid,marker-start,markerHeight,markerUnits,markerWidth,mathematical,' +\n      'max,min,offset,opacity,orient,origin,overline-position,overline-thickness,panose-1,' +\n      'path,pathLength,points,preserveAspectRatio,r,refX,refY,repeatCount,repeatDur,' +\n      'requiredExtensions,requiredFeatures,restart,rotate,rx,ry,slope,stemh,stemv,stop-color,' +\n      'stop-opacity,strikethrough-position,strikethrough-thickness,stroke,stroke-dasharray,' +\n      'stroke-dashoffset,stroke-linecap,stroke-linejoin,stroke-miterlimit,stroke-opacity,' +\n      'stroke-width,systemLanguage,target,text-anchor,to,transform,type,u1,u2,underline-position,' +\n      'underline-thickness,unicode,unicode-range,units-per-em,values,version,viewBox,visibility,' +\n      'width,widths,x,x-height,x1,x2,xlink:actuate,xlink:arcrole,xlink:role,xlink:show,xlink:title,' +\n      'xlink:type,xml:base,xml:lang,xml:space,xmlns,xmlns:xlink,y,y1,y2,zoomAndPan', true);\n\n  var validAttrs = extend({},\n                                  uriAttrs,\n                                  svgAttrs,\n                                  htmlAttrs);\n\n  function stringToMap(str, lowercaseKeys) {\n    return arrayToMap(str.split(','), lowercaseKeys);\n  }\n\n  function arrayToMap(items, lowercaseKeys) {\n    var obj = {}, i;\n    for (i = 0; i < items.length; i++) {\n      obj[lowercaseKeys ? lowercase(items[i]) : items[i]] = true;\n    }\n    return obj;\n  }\n\n  function addElementsTo(elementsMap, newElements) {\n    if (newElements && newElements.length) {\n      extend(elementsMap, arrayToMap(newElements));\n    }\n  }\n\n  /**\n   * Create an inert document that contains the dirty HTML that needs sanitizing.\n   * We use the DOMParser API by default and fall back to createHTMLDocument if DOMParser is not\n   * available.\n   */\n  var getInertBodyElement /* function(html: string): HTMLBodyElement */ = (function(window, document) {\n    if (isDOMParserAvailable()) {\n      return getInertBodyElement_DOMParser;\n    }\n\n    if (!document || !document.implementation) {\n      throw $sanitizeMinErr('noinert', 'Can\\'t create an inert html document');\n    }\n    var inertDocument = document.implementation.createHTMLDocument('inert');\n    var inertBodyElement = (inertDocument.documentElement || inertDocument.getDocumentElement()).querySelector('body');\n    return getInertBodyElement_InertDocument;\n\n    function isDOMParserAvailable() {\n      try {\n        return !!getInertBodyElement_DOMParser('');\n      } catch (e) {\n        return false;\n      }\n    }\n\n    function getInertBodyElement_DOMParser(html) {\n      // We add this dummy element to ensure that the rest of the content is parsed as expected\n      // e.g. leading whitespace is maintained and tags like `<meta>` do not get hoisted to the `<head>` tag.\n      html = '<remove></remove>' + html;\n      try {\n        var body = new window.DOMParser().parseFromString(html, 'text/html').body;\n        body.firstChild.remove();\n        return body;\n      } catch (e) {\n        return undefined;\n      }\n    }\n\n    function getInertBodyElement_InertDocument(html) {\n      inertBodyElement.innerHTML = html;\n\n      // Support: IE 9-11 only\n      // strip custom-namespaced attributes on IE<=11\n      if (document.documentMode) {\n        stripCustomNsAttrs(inertBodyElement);\n      }\n\n      return inertBodyElement;\n    }\n  })(window, window.document);\n\n  /**\n   * @example\n   * htmlParser(htmlString, {\n   *     start: function(tag, attrs) {},\n   *     end: function(tag) {},\n   *     chars: function(text) {},\n   *     comment: function(text) {}\n   * });\n   *\n   * @param {string} html string\n   * @param {object} handler\n   */\n  function htmlParserImpl(html, handler) {\n    if (html === null || html === undefined) {\n      html = '';\n    } else if (typeof html !== 'string') {\n      html = '' + html;\n    }\n\n    var inertBodyElement = getInertBodyElement(html);\n    if (!inertBodyElement) return '';\n\n    //mXSS protection\n    var mXSSAttempts = 5;\n    do {\n      if (mXSSAttempts === 0) {\n        throw $sanitizeMinErr('uinput', 'Failed to sanitize html because the input is unstable');\n      }\n      mXSSAttempts--;\n\n      // trigger mXSS if it is going to happen by reading and writing the innerHTML\n      html = inertBodyElement.innerHTML;\n      inertBodyElement = getInertBodyElement(html);\n    } while (html !== inertBodyElement.innerHTML);\n\n    var node = inertBodyElement.firstChild;\n    while (node) {\n      switch (node.nodeType) {\n        case 1: // ELEMENT_NODE\n          handler.start(node.nodeName.toLowerCase(), attrToMap(node.attributes));\n          break;\n        case 3: // TEXT NODE\n          handler.chars(node.textContent);\n          break;\n      }\n\n      var nextNode;\n      if (!(nextNode = node.firstChild)) {\n        if (node.nodeType === 1) {\n          handler.end(node.nodeName.toLowerCase());\n        }\n        nextNode = getNonDescendant('nextSibling', node);\n        if (!nextNode) {\n          while (nextNode == null) {\n            node = getNonDescendant('parentNode', node);\n            if (node === inertBodyElement) break;\n            nextNode = getNonDescendant('nextSibling', node);\n            if (node.nodeType === 1) {\n              handler.end(node.nodeName.toLowerCase());\n            }\n          }\n        }\n      }\n      node = nextNode;\n    }\n\n    while ((node = inertBodyElement.firstChild)) {\n      inertBodyElement.removeChild(node);\n    }\n  }\n\n  function attrToMap(attrs) {\n    var map = {};\n    for (var i = 0, ii = attrs.length; i < ii; i++) {\n      var attr = attrs[i];\n      map[attr.name] = attr.value;\n    }\n    return map;\n  }\n\n\n  /**\n   * Escapes all potentially dangerous characters, so that the\n   * resulting string can be safely inserted into attribute or\n   * element text.\n   * @param value\n   * @returns {string} escaped text\n   */\n  function encodeEntities(value) {\n    return value.\n      replace(/&/g, '&amp;').\n      replace(SURROGATE_PAIR_REGEXP, function(value) {\n        var hi = value.charCodeAt(0);\n        var low = value.charCodeAt(1);\n        return '&#' + (((hi - 0xD800) * 0x400) + (low - 0xDC00) + 0x10000) + ';';\n      }).\n      replace(NON_ALPHANUMERIC_REGEXP, function(value) {\n        return '&#' + value.charCodeAt(0) + ';';\n      }).\n      replace(/</g, '&lt;').\n      replace(/>/g, '&gt;');\n  }\n\n  /**\n   * create an HTML/XML writer which writes to buffer\n   * @param {Array} buf use buf.join('') to get out sanitized html string\n   * @returns {object} in the form of {\n   *     start: function(tag, attrs) {},\n   *     end: function(tag) {},\n   *     chars: function(text) {},\n   *     comment: function(text) {}\n   * }\n   */\n  function htmlSanitizeWriterImpl(buf, uriValidator) {\n    var ignoreCurrentElement = false;\n    var out = bind(buf, buf.push);\n    return {\n      start: function(tag, attrs) {\n        tag = lowercase(tag);\n        if (!ignoreCurrentElement && blockedElements[tag]) {\n          ignoreCurrentElement = tag;\n        }\n        if (!ignoreCurrentElement && validElements[tag] === true) {\n          out('<');\n          out(tag);\n          forEach(attrs, function(value, key) {\n            var lkey = lowercase(key);\n            var isImage = (tag === 'img' && lkey === 'src') || (lkey === 'background');\n            if (validAttrs[lkey] === true &&\n              (uriAttrs[lkey] !== true || uriValidator(value, isImage))) {\n              out(' ');\n              out(key);\n              out('=\"');\n              out(encodeEntities(value));\n              out('\"');\n            }\n          });\n          out('>');\n        }\n      },\n      end: function(tag) {\n        tag = lowercase(tag);\n        if (!ignoreCurrentElement && validElements[tag] === true && voidElements[tag] !== true) {\n          out('</');\n          out(tag);\n          out('>');\n        }\n        // eslint-disable-next-line eqeqeq\n        if (tag == ignoreCurrentElement) {\n          ignoreCurrentElement = false;\n        }\n      },\n      chars: function(chars) {\n        if (!ignoreCurrentElement) {\n          out(encodeEntities(chars));\n        }\n      }\n    };\n  }\n\n\n  /**\n   * When IE9-11 comes across an unknown namespaced attribute e.g. 'xlink:foo' it adds 'xmlns:ns1' attribute to declare\n   * ns1 namespace and prefixes the attribute with 'ns1' (e.g. 'ns1:xlink:foo'). This is undesirable since we don't want\n   * to allow any of these custom attributes. This method strips them all.\n   *\n   * @param node Root element to process\n   */\n  function stripCustomNsAttrs(node) {\n    while (node) {\n      if (node.nodeType === window.Node.ELEMENT_NODE) {\n        var attrs = node.attributes;\n        for (var i = 0, l = attrs.length; i < l; i++) {\n          var attrNode = attrs[i];\n          var attrName = attrNode.name.toLowerCase();\n          if (attrName === 'xmlns:ns1' || attrName.lastIndexOf('ns1:', 0) === 0) {\n            node.removeAttributeNode(attrNode);\n            i--;\n            l--;\n          }\n        }\n      }\n\n      var nextNode = node.firstChild;\n      if (nextNode) {\n        stripCustomNsAttrs(nextNode);\n      }\n\n      node = getNonDescendant('nextSibling', node);\n    }\n  }\n\n  function getNonDescendant(propName, node) {\n    // An element is clobbered if its `propName` property points to one of its descendants\n    var nextNode = node[propName];\n    if (nextNode && nodeContains.call(node, nextNode)) {\n      throw $sanitizeMinErr('elclob', 'Failed to sanitize html because the element is clobbered: {0}', node.outerHTML || node.outerText);\n    }\n    return nextNode;\n  }\n}\n\nfunction sanitizeText(chars) {\n  var buf = [];\n  var writer = htmlSanitizeWriter(buf, noop);\n  writer.chars(chars);\n  return buf.join('');\n}\n\n\n// define ngSanitize module and register $sanitize service\nangular.module('ngSanitize', [])\n  .provider('$sanitize', $SanitizeProvider)\n  .info({ angularVersion: '1.8.3' });\n\n/**\n * @ngdoc filter\n * @name linky\n * @kind function\n *\n * @description\n * Finds links in text input and turns them into html links. Supports `http/https/ftp/sftp/mailto` and\n * plain email address links.\n *\n * Requires the {@link ngSanitize `ngSanitize`} module to be installed.\n *\n * @param {string} text Input text.\n * @param {string} [target] Window (`_blank|_self|_parent|_top`) or named frame to open links in.\n * @param {object|function(url)} [attributes] Add custom attributes to the link element.\n *\n *    Can be one of:\n *\n *    - `object`: A map of attributes\n *    - `function`: Takes the url as a parameter and returns a map of attributes\n *\n *    If the map of attributes contains a value for `target`, it overrides the value of\n *    the target parameter.\n *\n *\n * @returns {string} Html-linkified and {@link $sanitize sanitized} text.\n *\n * @usage\n   <span ng-bind-html=\"linky_expression | linky\"></span>\n *\n * @example\n   <example module=\"linkyExample\" deps=\"angular-sanitize.js\" name=\"linky-filter\">\n     <file name=\"index.html\">\n       <div ng-controller=\"ExampleController\">\n       Snippet: <textarea ng-model=\"snippet\" cols=\"60\" rows=\"3\"></textarea>\n       <table>\n         <tr>\n           <th>Filter</th>\n           <th>Source</th>\n           <th>Rendered</th>\n         </tr>\n         <tr id=\"linky-filter\">\n           <td>linky filter</td>\n           <td>\n             <pre>&lt;div ng-bind-html=\"snippet | linky\"&gt;<br>&lt;/div&gt;</pre>\n           </td>\n           <td>\n             <div ng-bind-html=\"snippet | linky\"></div>\n           </td>\n         </tr>\n         <tr id=\"linky-target\">\n          <td>linky target</td>\n          <td>\n            <pre>&lt;div ng-bind-html=\"snippetWithSingleURL | linky:'_blank'\"&gt;<br>&lt;/div&gt;</pre>\n          </td>\n          <td>\n            <div ng-bind-html=\"snippetWithSingleURL | linky:'_blank'\"></div>\n          </td>\n         </tr>\n         <tr id=\"linky-custom-attributes\">\n          <td>linky custom attributes</td>\n          <td>\n            <pre>&lt;div ng-bind-html=\"snippetWithSingleURL | linky:'_self':{rel: 'nofollow'}\"&gt;<br>&lt;/div&gt;</pre>\n          </td>\n          <td>\n            <div ng-bind-html=\"snippetWithSingleURL | linky:'_self':{rel: 'nofollow'}\"></div>\n          </td>\n         </tr>\n         <tr id=\"escaped-html\">\n           <td>no filter</td>\n           <td><pre>&lt;div ng-bind=\"snippet\"&gt;<br>&lt;/div&gt;</pre></td>\n           <td><div ng-bind=\"snippet\"></div></td>\n         </tr>\n       </table>\n     </file>\n     <file name=\"script.js\">\n       angular.module('linkyExample', ['ngSanitize'])\n         .controller('ExampleController', ['$scope', function($scope) {\n           $scope.snippet =\n             'Pretty text with some links:\\n' +\n             'http://angularjs.org/,\\n' +\n             'mailto:us@somewhere.org,\\n' +\n             'another@somewhere.org,\\n' +\n             'and one more: ftp://127.0.0.1/.';\n           $scope.snippetWithSingleURL = 'http://angularjs.org/';\n         }]);\n     </file>\n     <file name=\"protractor.js\" type=\"protractor\">\n       it('should linkify the snippet with urls', function() {\n         expect(element(by.id('linky-filter')).element(by.binding('snippet | linky')).getText()).\n             toBe('Pretty text with some links: http://angularjs.org/, us@somewhere.org, ' +\n                  'another@somewhere.org, and one more: ftp://127.0.0.1/.');\n         expect(element.all(by.css('#linky-filter a')).count()).toEqual(4);\n       });\n\n       it('should not linkify snippet without the linky filter', function() {\n         expect(element(by.id('escaped-html')).element(by.binding('snippet')).getText()).\n             toBe('Pretty text with some links: http://angularjs.org/, mailto:us@somewhere.org, ' +\n                  'another@somewhere.org, and one more: ftp://127.0.0.1/.');\n         expect(element.all(by.css('#escaped-html a')).count()).toEqual(0);\n       });\n\n       it('should update', function() {\n         element(by.model('snippet')).clear();\n         element(by.model('snippet')).sendKeys('new http://link.');\n         expect(element(by.id('linky-filter')).element(by.binding('snippet | linky')).getText()).\n             toBe('new http://link.');\n         expect(element.all(by.css('#linky-filter a')).count()).toEqual(1);\n         expect(element(by.id('escaped-html')).element(by.binding('snippet')).getText())\n             .toBe('new http://link.');\n       });\n\n       it('should work with the target property', function() {\n        expect(element(by.id('linky-target')).\n            element(by.binding(\"snippetWithSingleURL | linky:'_blank'\")).getText()).\n            toBe('http://angularjs.org/');\n        expect(element(by.css('#linky-target a')).getAttribute('target')).toEqual('_blank');\n       });\n\n       it('should optionally add custom attributes', function() {\n        expect(element(by.id('linky-custom-attributes')).\n            element(by.binding(\"snippetWithSingleURL | linky:'_self':{rel: 'nofollow'}\")).getText()).\n            toBe('http://angularjs.org/');\n        expect(element(by.css('#linky-custom-attributes a')).getAttribute('rel')).toEqual('nofollow');\n       });\n     </file>\n   </example>\n */\nangular.module('ngSanitize').filter('linky', ['$sanitize', function($sanitize) {\n  var LINKY_URL_REGEXP =\n        /((s?ftp|https?):\\/\\/|(www\\.)|(mailto:)?[A-Za-z0-9._%+-]+@)\\S*[^\\s.;,(){}<>\"\\u201d\\u2019]/i,\n      MAILTO_REGEXP = /^mailto:/i;\n\n  var linkyMinErr = angular.$$minErr('linky');\n  var isDefined = angular.isDefined;\n  var isFunction = angular.isFunction;\n  var isObject = angular.isObject;\n  var isString = angular.isString;\n\n  return function(text, target, attributes) {\n    if (text == null || text === '') return text;\n    if (!isString(text)) throw linkyMinErr('notstring', 'Expected string but received: {0}', text);\n\n    var attributesFn =\n      isFunction(attributes) ? attributes :\n      isObject(attributes) ? function getAttributesObject() {return attributes;} :\n      function getEmptyAttributesObject() {return {};};\n\n    var match;\n    var raw = text;\n    var html = [];\n    var url;\n    var i;\n    while ((match = raw.match(LINKY_URL_REGEXP))) {\n      // We can not end in these as they are sometimes found at the end of the sentence\n      url = match[0];\n      // if we did not match ftp/http/www/mailto then assume mailto\n      if (!match[2] && !match[4]) {\n        url = (match[3] ? 'http://' : 'mailto:') + url;\n      }\n      i = match.index;\n      addText(raw.substr(0, i));\n      addLink(url, match[0].replace(MAILTO_REGEXP, ''));\n      raw = raw.substring(i + match[0].length);\n    }\n    addText(raw);\n    return $sanitize(html.join(''));\n\n    function addText(text) {\n      if (!text) {\n        return;\n      }\n      html.push(sanitizeText(text));\n    }\n\n    function addLink(url, text) {\n      var key, linkAttributes = attributesFn(url);\n      html.push('<a ');\n\n      for (key in linkAttributes) {\n        html.push(key + '=\"' + linkAttributes[key] + '\" ');\n      }\n\n      if (isDefined(target) && !('target' in linkAttributes)) {\n        html.push('target=\"',\n                  target,\n                  '\" ');\n      }\n      html.push('href=\"',\n                url.replace(/\"/g, '&quot;'),\n                '\">');\n      addText(text);\n      html.push('</a>');\n    }\n  };\n}]);\n\n\n})(window, window.angular);\n","require('./angular-sanitize');\nmodule.exports = 'ngSanitize';\n","/**!\n * AngularJS file upload directives and services. Supports: file upload/drop/paste, resume, cancel/abort,\n * progress, resize, thumbnail, preview, validation and CORS\n * FileAPI Flash shim for old browsers not supporting FormData\n * @author  Danial  <danial.farid@gmail.com>\n * @version 12.2.13\n */\n\n(function () {\n  /** @namespace FileAPI.noContentTimeout */\n\n  function patchXHR(fnName, newFn) {\n    window.XMLHttpRequest.prototype[fnName] = newFn(window.XMLHttpRequest.prototype[fnName]);\n  }\n\n  function redefineProp(xhr, prop, fn) {\n    try {\n      Object.defineProperty(xhr, prop, {get: fn});\n    } catch (e) {/*ignore*/\n    }\n  }\n\n  if (!window.FileAPI) {\n    window.FileAPI = {};\n  }\n\n  if (!window.XMLHttpRequest) {\n    throw 'AJAX is not supported. XMLHttpRequest is not defined.';\n  }\n\n  FileAPI.shouldLoad = !window.FormData || FileAPI.forceLoad;\n  if (FileAPI.shouldLoad) {\n    var initializeUploadListener = function (xhr) {\n      if (!xhr.__listeners) {\n        if (!xhr.upload) xhr.upload = {};\n        xhr.__listeners = [];\n        var origAddEventListener = xhr.upload.addEventListener;\n        xhr.upload.addEventListener = function (t, fn) {\n          xhr.__listeners[t] = fn;\n          if (origAddEventListener) origAddEventListener.apply(this, arguments);\n        };\n      }\n    };\n\n    patchXHR('open', function (orig) {\n      return function (m, url, b) {\n        initializeUploadListener(this);\n        this.__url = url;\n        try {\n          orig.apply(this, [m, url, b]);\n        } catch (e) {\n          if (e.message.indexOf('Access is denied') > -1) {\n            this.__origError = e;\n            orig.apply(this, [m, '_fix_for_ie_crossdomain__', b]);\n          }\n        }\n      };\n    });\n\n    patchXHR('getResponseHeader', function (orig) {\n      return function (h) {\n        return this.__fileApiXHR && this.__fileApiXHR.getResponseHeader ? this.__fileApiXHR.getResponseHeader(h) : (orig == null ? null : orig.apply(this, [h]));\n      };\n    });\n\n    patchXHR('getAllResponseHeaders', function (orig) {\n      return function () {\n        return this.__fileApiXHR && this.__fileApiXHR.getAllResponseHeaders ? this.__fileApiXHR.getAllResponseHeaders() : (orig == null ? null : orig.apply(this));\n      };\n    });\n\n    patchXHR('abort', function (orig) {\n      return function () {\n        return this.__fileApiXHR && this.__fileApiXHR.abort ? this.__fileApiXHR.abort() : (orig == null ? null : orig.apply(this));\n      };\n    });\n\n    patchXHR('setRequestHeader', function (orig) {\n      return function (header, value) {\n        if (header === '__setXHR_') {\n          initializeUploadListener(this);\n          var val = value(this);\n          // fix for angular < 1.2.0\n          if (val instanceof Function) {\n            val(this);\n          }\n        } else {\n          this.__requestHeaders = this.__requestHeaders || {};\n          this.__requestHeaders[header] = value;\n          orig.apply(this, arguments);\n        }\n      };\n    });\n\n    patchXHR('send', function (orig) {\n      return function () {\n        var xhr = this;\n        if (arguments[0] && arguments[0].__isFileAPIShim) {\n          var formData = arguments[0];\n          var config = {\n            url: xhr.__url,\n            jsonp: false, //removes the callback form param\n            cache: true, //removes the ?fileapiXXX in the url\n            complete: function (err, fileApiXHR) {\n              if (err && angular.isString(err) && err.indexOf('#2174') !== -1) {\n                // this error seems to be fine the file is being uploaded properly.\n                err = null;\n              }\n              xhr.__completed = true;\n              if (!err && xhr.__listeners.load)\n                xhr.__listeners.load({\n                  type: 'load',\n                  loaded: xhr.__loaded,\n                  total: xhr.__total,\n                  target: xhr,\n                  lengthComputable: true\n                });\n              if (!err && xhr.__listeners.loadend)\n                xhr.__listeners.loadend({\n                  type: 'loadend',\n                  loaded: xhr.__loaded,\n                  total: xhr.__total,\n                  target: xhr,\n                  lengthComputable: true\n                });\n              if (err === 'abort' && xhr.__listeners.abort)\n                xhr.__listeners.abort({\n                  type: 'abort',\n                  loaded: xhr.__loaded,\n                  total: xhr.__total,\n                  target: xhr,\n                  lengthComputable: true\n                });\n              if (fileApiXHR.status !== undefined) redefineProp(xhr, 'status', function () {\n                return (fileApiXHR.status === 0 && err && err !== 'abort') ? 500 : fileApiXHR.status;\n              });\n              if (fileApiXHR.statusText !== undefined) redefineProp(xhr, 'statusText', function () {\n                return fileApiXHR.statusText;\n              });\n              redefineProp(xhr, 'readyState', function () {\n                return 4;\n              });\n              if (fileApiXHR.response !== undefined) redefineProp(xhr, 'response', function () {\n                return fileApiXHR.response;\n              });\n              var resp = fileApiXHR.responseText || (err && fileApiXHR.status === 0 && err !== 'abort' ? err : undefined);\n              redefineProp(xhr, 'responseText', function () {\n                return resp;\n              });\n              redefineProp(xhr, 'response', function () {\n                return resp;\n              });\n              if (err) redefineProp(xhr, 'err', function () {\n                return err;\n              });\n              xhr.__fileApiXHR = fileApiXHR;\n              if (xhr.onreadystatechange) xhr.onreadystatechange();\n              if (xhr.onload) xhr.onload();\n            },\n            progress: function (e) {\n              e.target = xhr;\n              if (xhr.__listeners.progress) xhr.__listeners.progress(e);\n              xhr.__total = e.total;\n              xhr.__loaded = e.loaded;\n              if (e.total === e.loaded) {\n                // fix flash issue that doesn't call complete if there is no response text from the server\n                var _this = this;\n                setTimeout(function () {\n                  if (!xhr.__completed) {\n                    xhr.getAllResponseHeaders = function () {\n                    };\n                    _this.complete(null, {status: 204, statusText: 'No Content'});\n                  }\n                }, FileAPI.noContentTimeout || 10000);\n              }\n            },\n            headers: xhr.__requestHeaders\n          };\n          config.data = {};\n          config.files = {};\n          for (var i = 0; i < formData.data.length; i++) {\n            var item = formData.data[i];\n            if (item.val != null && item.val.name != null && item.val.size != null && item.val.type != null) {\n              config.files[item.key] = item.val;\n            } else {\n              config.data[item.key] = item.val;\n            }\n          }\n\n          setTimeout(function () {\n            if (!FileAPI.hasFlash) {\n              throw 'Adode Flash Player need to be installed. To check ahead use \"FileAPI.hasFlash\"';\n            }\n            xhr.__fileApiXHR = FileAPI.upload(config);\n          }, 1);\n        } else {\n          if (this.__origError) {\n            throw this.__origError;\n          }\n          orig.apply(xhr, arguments);\n        }\n      };\n    });\n    window.XMLHttpRequest.__isFileAPIShim = true;\n    window.FormData = FormData = function () {\n      return {\n        append: function (key, val, name) {\n          if (val.__isFileAPIBlobShim) {\n            val = val.data[0];\n          }\n          this.data.push({\n            key: key,\n            val: val,\n            name: name\n          });\n        },\n        data: [],\n        __isFileAPIShim: true\n      };\n    };\n\n    window.Blob = Blob = function (b) {\n      return {\n        data: b,\n        __isFileAPIBlobShim: true\n      };\n    };\n  }\n\n})();\n\n(function () {\n  /** @namespace FileAPI.forceLoad */\n  /** @namespace window.FileAPI.jsUrl */\n  /** @namespace window.FileAPI.jsPath */\n\n  function isInputTypeFile(elem) {\n    return elem[0].tagName.toLowerCase() === 'input' && elem.attr('type') && elem.attr('type').toLowerCase() === 'file';\n  }\n\n  function hasFlash() {\n    try {\n      var fo = new ActiveXObject('ShockwaveFlash.ShockwaveFlash');\n      if (fo) return true;\n    } catch (e) {\n      if (navigator.mimeTypes['application/x-shockwave-flash'] !== undefined) return true;\n    }\n    return false;\n  }\n\n  function getOffset(obj) {\n    var left = 0, top = 0;\n\n    if (window.jQuery) {\n      return jQuery(obj).offset();\n    }\n\n    if (obj.offsetParent) {\n      do {\n        left += (obj.offsetLeft - obj.scrollLeft);\n        top += (obj.offsetTop - obj.scrollTop);\n        obj = obj.offsetParent;\n      } while (obj);\n    }\n    return {\n      left: left,\n      top: top\n    };\n  }\n\n  if (FileAPI.shouldLoad) {\n    FileAPI.hasFlash = hasFlash();\n\n    //load FileAPI\n    if (FileAPI.forceLoad) {\n      FileAPI.html5 = false;\n    }\n\n    if (!FileAPI.upload) {\n      var jsUrl, basePath, script = document.createElement('script'), allScripts = document.getElementsByTagName('script'), i, index, src;\n      if (window.FileAPI.jsUrl) {\n        jsUrl = window.FileAPI.jsUrl;\n      } else if (window.FileAPI.jsPath) {\n        basePath = window.FileAPI.jsPath;\n      } else {\n        for (i = 0; i < allScripts.length; i++) {\n          src = allScripts[i].src;\n          index = src.search(/\\/ng\\-file\\-upload[\\-a-zA-z0-9\\.]*\\.js/);\n          if (index > -1) {\n            basePath = src.substring(0, index + 1);\n            break;\n          }\n        }\n      }\n\n      if (FileAPI.staticPath == null) FileAPI.staticPath = basePath;\n      script.setAttribute('src', jsUrl || basePath + 'FileAPI.min.js');\n      document.getElementsByTagName('head')[0].appendChild(script);\n    }\n\n    FileAPI.ngfFixIE = function (elem, fileElem, changeFn) {\n      if (!hasFlash()) {\n        throw 'Adode Flash Player need to be installed. To check ahead use \"FileAPI.hasFlash\"';\n      }\n      var fixInputStyle = function () {\n        var label = fileElem.parent();\n        if (elem.attr('disabled')) {\n          if (label) label.removeClass('js-fileapi-wrapper');\n        } else {\n          if (!fileElem.attr('__ngf_flash_')) {\n            fileElem.unbind('change');\n            fileElem.unbind('click');\n            fileElem.bind('change', function (evt) {\n              fileApiChangeFn.apply(this, [evt]);\n              changeFn.apply(this, [evt]);\n            });\n            fileElem.attr('__ngf_flash_', 'true');\n          }\n          label.addClass('js-fileapi-wrapper');\n          if (!isInputTypeFile(elem)) {\n            label.css('position', 'absolute')\n              .css('top', getOffset(elem[0]).top + 'px').css('left', getOffset(elem[0]).left + 'px')\n              .css('width', elem[0].offsetWidth + 'px').css('height', elem[0].offsetHeight + 'px')\n              .css('filter', 'alpha(opacity=0)').css('display', elem.css('display'))\n              .css('overflow', 'hidden').css('z-index', '900000')\n              .css('visibility', 'visible');\n            fileElem.css('width', elem[0].offsetWidth + 'px').css('height', elem[0].offsetHeight + 'px')\n              .css('position', 'absolute').css('top', '0px').css('left', '0px');\n          }\n        }\n      };\n\n      elem.bind('mouseenter', fixInputStyle);\n\n      var fileApiChangeFn = function (evt) {\n        var files = FileAPI.getFiles(evt);\n        //just a double check for #233\n        for (var i = 0; i < files.length; i++) {\n          if (files[i].size === undefined) files[i].size = 0;\n          if (files[i].name === undefined) files[i].name = 'file';\n          if (files[i].type === undefined) files[i].type = 'undefined';\n        }\n        if (!evt.target) {\n          evt.target = {};\n        }\n        evt.target.files = files;\n        // if evt.target.files is not writable use helper field\n        if (evt.target.files !== files) {\n          evt.__files_ = files;\n        }\n        (evt.__files_ || evt.target.files).item = function (i) {\n          return (evt.__files_ || evt.target.files)[i] || null;\n        };\n      };\n    };\n\n    FileAPI.disableFileInput = function (elem, disable) {\n      if (disable) {\n        elem.removeClass('js-fileapi-wrapper');\n      } else {\n        elem.addClass('js-fileapi-wrapper');\n      }\n    };\n  }\n})();\n\nif (!window.FileReader) {\n  window.FileReader = function () {\n    var _this = this, loadStarted = false;\n    this.listeners = {};\n    this.addEventListener = function (type, fn) {\n      _this.listeners[type] = _this.listeners[type] || [];\n      _this.listeners[type].push(fn);\n    };\n    this.removeEventListener = function (type, fn) {\n      if (_this.listeners[type]) _this.listeners[type].splice(_this.listeners[type].indexOf(fn), 1);\n    };\n    this.dispatchEvent = function (evt) {\n      var list = _this.listeners[evt.type];\n      if (list) {\n        for (var i = 0; i < list.length; i++) {\n          list[i].call(_this, evt);\n        }\n      }\n    };\n    this.onabort = this.onerror = this.onload = this.onloadstart = this.onloadend = this.onprogress = null;\n\n    var constructEvent = function (type, evt) {\n      var e = {type: type, target: _this, loaded: evt.loaded, total: evt.total, error: evt.error};\n      if (evt.result != null) e.target.result = evt.result;\n      return e;\n    };\n    var listener = function (evt) {\n      if (!loadStarted) {\n        loadStarted = true;\n        if (_this.onloadstart) _this.onloadstart(constructEvent('loadstart', evt));\n      }\n      var e;\n      if (evt.type === 'load') {\n        if (_this.onloadend) _this.onloadend(constructEvent('loadend', evt));\n        e = constructEvent('load', evt);\n        if (_this.onload) _this.onload(e);\n        _this.dispatchEvent(e);\n      } else if (evt.type === 'progress') {\n        e = constructEvent('progress', evt);\n        if (_this.onprogress) _this.onprogress(e);\n        _this.dispatchEvent(e);\n      } else {\n        e = constructEvent('error', evt);\n        if (_this.onerror) _this.onerror(e);\n        _this.dispatchEvent(e);\n      }\n    };\n    this.readAsDataURL = function (file) {\n      FileAPI.readAsDataURL(file, listener);\n    };\n    this.readAsText = function (file) {\n      FileAPI.readAsText(file, listener);\n    };\n  };\n}\n\n/**!\n * AngularJS file upload directives and services. Supoorts: file upload/drop/paste, resume, cancel/abort,\n * progress, resize, thumbnail, preview, validation and CORS\n * @author  Danial  <danial.farid@gmail.com>\n * @version 12.2.13\n */\n\nif (window.XMLHttpRequest && !(window.FileAPI && FileAPI.shouldLoad)) {\n  window.XMLHttpRequest.prototype.setRequestHeader = (function (orig) {\n    return function (header, value) {\n      if (header === '__setXHR_') {\n        var val = value(this);\n        // fix for angular < 1.2.0\n        if (val instanceof Function) {\n          val(this);\n        }\n      } else {\n        orig.apply(this, arguments);\n      }\n    };\n  })(window.XMLHttpRequest.prototype.setRequestHeader);\n}\n\nvar ngFileUpload = angular.module('ngFileUpload', []);\n\nngFileUpload.version = '12.2.13';\n\nngFileUpload.service('UploadBase', ['$http', '$q', '$timeout', function ($http, $q, $timeout) {\n  var upload = this;\n  upload.promisesCount = 0;\n\n  this.isResumeSupported = function () {\n    return window.Blob && window.Blob.prototype.slice;\n  };\n\n  var resumeSupported = this.isResumeSupported();\n\n  function sendHttp(config) {\n    config.method = config.method || 'POST';\n    config.headers = config.headers || {};\n\n    var deferred = config._deferred = config._deferred || $q.defer();\n    var promise = deferred.promise;\n\n    function notifyProgress(e) {\n      if (deferred.notify) {\n        deferred.notify(e);\n      }\n      if (promise.progressFunc) {\n        $timeout(function () {\n          promise.progressFunc(e);\n        });\n      }\n    }\n\n    function getNotifyEvent(n) {\n      if (config._start != null && resumeSupported) {\n        return {\n          loaded: n.loaded + config._start,\n          total: (config._file && config._file.size) || n.total,\n          type: n.type, config: config,\n          lengthComputable: true, target: n.target\n        };\n      } else {\n        return n;\n      }\n    }\n\n    if (!config.disableProgress) {\n      config.headers.__setXHR_ = function () {\n        return function (xhr) {\n          if (!xhr || !xhr.upload || !xhr.upload.addEventListener) return;\n          config.__XHR = xhr;\n          if (config.xhrFn) config.xhrFn(xhr);\n          xhr.upload.addEventListener('progress', function (e) {\n            e.config = config;\n            notifyProgress(getNotifyEvent(e));\n          }, false);\n          //fix for firefox not firing upload progress end, also IE8-9\n          xhr.upload.addEventListener('load', function (e) {\n            if (e.lengthComputable) {\n              e.config = config;\n              notifyProgress(getNotifyEvent(e));\n            }\n          }, false);\n        };\n      };\n    }\n\n    function uploadWithAngular() {\n      $http(config).then(function (r) {\n          if (resumeSupported && config._chunkSize && !config._finished && config._file) {\n            var fileSize = config._file && config._file.size || 0;\n            notifyProgress({\n                loaded: Math.min(config._end, fileSize),\n                total: fileSize,\n                config: config,\n                type: 'progress'\n              }\n            );\n            upload.upload(config, true);\n          } else {\n            if (config._finished) delete config._finished;\n            deferred.resolve(r);\n          }\n        }, function (e) {\n          deferred.reject(e);\n        }, function (n) {\n          deferred.notify(n);\n        }\n      );\n    }\n\n    if (!resumeSupported) {\n      uploadWithAngular();\n    } else if (config._chunkSize && config._end && !config._finished) {\n      config._start = config._end;\n      config._end += config._chunkSize;\n      uploadWithAngular();\n    } else if (config.resumeSizeUrl) {\n      $http.get(config.resumeSizeUrl).then(function (resp) {\n        if (config.resumeSizeResponseReader) {\n          config._start = config.resumeSizeResponseReader(resp.data);\n        } else {\n          config._start = parseInt((resp.data.size == null ? resp.data : resp.data.size).toString());\n        }\n        if (config._chunkSize) {\n          config._end = config._start + config._chunkSize;\n        }\n        uploadWithAngular();\n      }, function (e) {\n        throw e;\n      });\n    } else if (config.resumeSize) {\n      config.resumeSize().then(function (size) {\n        config._start = size;\n        if (config._chunkSize) {\n          config._end = config._start + config._chunkSize;\n        }\n        uploadWithAngular();\n      }, function (e) {\n        throw e;\n      });\n    } else {\n      if (config._chunkSize) {\n        config._start = 0;\n        config._end = config._start + config._chunkSize;\n      }\n      uploadWithAngular();\n    }\n\n\n    promise.success = function (fn) {\n      promise.then(function (response) {\n        fn(response.data, response.status, response.headers, config);\n      });\n      return promise;\n    };\n\n    promise.error = function (fn) {\n      promise.then(null, function (response) {\n        fn(response.data, response.status, response.headers, config);\n      });\n      return promise;\n    };\n\n    promise.progress = function (fn) {\n      promise.progressFunc = fn;\n      promise.then(null, null, function (n) {\n        fn(n);\n      });\n      return promise;\n    };\n    promise.abort = promise.pause = function () {\n      if (config.__XHR) {\n        $timeout(function () {\n          config.__XHR.abort();\n        });\n      }\n      return promise;\n    };\n    promise.xhr = function (fn) {\n      config.xhrFn = (function (origXhrFn) {\n        return function () {\n          if (origXhrFn) origXhrFn.apply(promise, arguments);\n          fn.apply(promise, arguments);\n        };\n      })(config.xhrFn);\n      return promise;\n    };\n\n    upload.promisesCount++;\n    if (promise['finally'] && promise['finally'] instanceof Function) {\n      promise['finally'](function () {\n        upload.promisesCount--;\n      });\n    }\n    return promise;\n  }\n\n  this.isUploadInProgress = function () {\n    return upload.promisesCount > 0;\n  };\n\n  this.rename = function (file, name) {\n    file.ngfName = name;\n    return file;\n  };\n\n  this.jsonBlob = function (val) {\n    if (val != null && !angular.isString(val)) {\n      val = JSON.stringify(val);\n    }\n    var blob = new window.Blob([val], {type: 'application/json'});\n    blob._ngfBlob = true;\n    return blob;\n  };\n\n  this.json = function (val) {\n    return angular.toJson(val);\n  };\n\n  function copy(obj) {\n    var clone = {};\n    for (var key in obj) {\n      if (obj.hasOwnProperty(key)) {\n        clone[key] = obj[key];\n      }\n    }\n    return clone;\n  }\n\n  this.isFile = function (file) {\n    return file != null && (file instanceof window.Blob || (file.flashId && file.name && file.size));\n  };\n\n  this.upload = function (config, internal) {\n    function toResumeFile(file, formData) {\n      if (file._ngfBlob) return file;\n      config._file = config._file || file;\n      if (config._start != null && resumeSupported) {\n        if (config._end && config._end >= file.size) {\n          config._finished = true;\n          config._end = file.size;\n        }\n        var slice = file.slice(config._start, config._end || file.size);\n        slice.name = file.name;\n        slice.ngfName = file.ngfName;\n        if (config._chunkSize) {\n          formData.append('_chunkSize', config._chunkSize);\n          formData.append('_currentChunkSize', config._end - config._start);\n          formData.append('_chunkNumber', Math.floor(config._start / config._chunkSize));\n          formData.append('_totalSize', config._file.size);\n        }\n        return slice;\n      }\n      return file;\n    }\n\n    function addFieldToFormData(formData, val, key) {\n      if (val !== undefined) {\n        if (angular.isDate(val)) {\n          val = val.toISOString();\n        }\n        if (angular.isString(val)) {\n          formData.append(key, val);\n        } else if (upload.isFile(val)) {\n          var file = toResumeFile(val, formData);\n          var split = key.split(',');\n          if (split[1]) {\n            file.ngfName = split[1].replace(/^\\s+|\\s+$/g, '');\n            key = split[0];\n          }\n          config._fileKey = config._fileKey || key;\n          formData.append(key, file, file.ngfName || file.name);\n        } else {\n          if (angular.isObject(val)) {\n            if (val.$$ngfCircularDetection) throw 'ngFileUpload: Circular reference in config.data. Make sure specified data for Upload.upload() has no circular reference: ' + key;\n\n            val.$$ngfCircularDetection = true;\n            try {\n              for (var k in val) {\n                if (val.hasOwnProperty(k) && k !== '$$ngfCircularDetection') {\n                  var objectKey = config.objectKey == null ? '[i]' : config.objectKey;\n                  if (val.length && parseInt(k) > -1) {\n                    objectKey = config.arrayKey == null ? objectKey : config.arrayKey;\n                  }\n                  addFieldToFormData(formData, val[k], key + objectKey.replace(/[ik]/g, k));\n                }\n              }\n            } finally {\n              delete val.$$ngfCircularDetection;\n            }\n          } else {\n            formData.append(key, val);\n          }\n        }\n      }\n    }\n\n    function digestConfig() {\n      config._chunkSize = upload.translateScalars(config.resumeChunkSize);\n      config._chunkSize = config._chunkSize ? parseInt(config._chunkSize.toString()) : null;\n\n      config.headers = config.headers || {};\n      config.headers['Content-Type'] = undefined;\n      config.transformRequest = config.transformRequest ?\n        (angular.isArray(config.transformRequest) ?\n          config.transformRequest : [config.transformRequest]) : [];\n      config.transformRequest.push(function (data) {\n        var formData = new window.FormData(), key;\n        data = data || config.fields || {};\n        if (config.file) {\n          data.file = config.file;\n        }\n        for (key in data) {\n          if (data.hasOwnProperty(key)) {\n            var val = data[key];\n            if (config.formDataAppender) {\n              config.formDataAppender(formData, key, val);\n            } else {\n              addFieldToFormData(formData, val, key);\n            }\n          }\n        }\n\n        return formData;\n      });\n    }\n\n    if (!internal) config = copy(config);\n    if (!config._isDigested) {\n      config._isDigested = true;\n      digestConfig();\n    }\n\n    return sendHttp(config);\n  };\n\n  this.http = function (config) {\n    config = copy(config);\n    config.transformRequest = config.transformRequest || function (data) {\n        if ((window.ArrayBuffer && data instanceof window.ArrayBuffer) || data instanceof window.Blob) {\n          return data;\n        }\n        return $http.defaults.transformRequest[0].apply(this, arguments);\n      };\n    config._chunkSize = upload.translateScalars(config.resumeChunkSize);\n    config._chunkSize = config._chunkSize ? parseInt(config._chunkSize.toString()) : null;\n\n    return sendHttp(config);\n  };\n\n  this.translateScalars = function (str) {\n    if (angular.isString(str)) {\n      if (str.search(/kb/i) === str.length - 2) {\n        return parseFloat(str.substring(0, str.length - 2) * 1024);\n      } else if (str.search(/mb/i) === str.length - 2) {\n        return parseFloat(str.substring(0, str.length - 2) * 1048576);\n      } else if (str.search(/gb/i) === str.length - 2) {\n        return parseFloat(str.substring(0, str.length - 2) * 1073741824);\n      } else if (str.search(/b/i) === str.length - 1) {\n        return parseFloat(str.substring(0, str.length - 1));\n      } else if (str.search(/s/i) === str.length - 1) {\n        return parseFloat(str.substring(0, str.length - 1));\n      } else if (str.search(/m/i) === str.length - 1) {\n        return parseFloat(str.substring(0, str.length - 1) * 60);\n      } else if (str.search(/h/i) === str.length - 1) {\n        return parseFloat(str.substring(0, str.length - 1) * 3600);\n      }\n    }\n    return str;\n  };\n\n  this.urlToBlob = function(url) {\n    var defer = $q.defer();\n    $http({url: url, method: 'get', responseType: 'arraybuffer'}).then(function (resp) {\n      var arrayBufferView = new Uint8Array(resp.data);\n      var type = resp.headers('content-type') || 'image/WebP';\n      var blob = new window.Blob([arrayBufferView], {type: type});\n      var matches = url.match(/.*\\/(.+?)(\\?.*)?$/);\n      if (matches.length > 1) {\n        blob.name = matches[1];\n      }\n      defer.resolve(blob);\n    }, function (e) {\n      defer.reject(e);\n    });\n    return defer.promise;\n  };\n\n  this.setDefaults = function (defaults) {\n    this.defaults = defaults || {};\n  };\n\n  this.defaults = {};\n  this.version = ngFileUpload.version;\n}\n\n]);\n\nngFileUpload.service('Upload', ['$parse', '$timeout', '$compile', '$q', 'UploadExif', function ($parse, $timeout, $compile, $q, UploadExif) {\n  var upload = UploadExif;\n  upload.getAttrWithDefaults = function (attr, name) {\n    if (attr[name] != null) return attr[name];\n    var def = upload.defaults[name];\n    return (def == null ? def : (angular.isString(def) ? def : JSON.stringify(def)));\n  };\n\n  upload.attrGetter = function (name, attr, scope, params) {\n    var attrVal = this.getAttrWithDefaults(attr, name);\n    if (scope) {\n      try {\n        if (params) {\n          return $parse(attrVal)(scope, params);\n        } else {\n          return $parse(attrVal)(scope);\n        }\n      } catch (e) {\n        // hangle string value without single qoute\n        if (name.search(/min|max|pattern/i)) {\n          return attrVal;\n        } else {\n          throw e;\n        }\n      }\n    } else {\n      return attrVal;\n    }\n  };\n\n  upload.shouldUpdateOn = function (type, attr, scope) {\n    var modelOptions = upload.attrGetter('ngfModelOptions', attr, scope);\n    if (modelOptions && modelOptions.updateOn) {\n      return modelOptions.updateOn.split(' ').indexOf(type) > -1;\n    }\n    return true;\n  };\n\n  upload.emptyPromise = function () {\n    var d = $q.defer();\n    var args = arguments;\n    $timeout(function () {\n      d.resolve.apply(d, args);\n    });\n    return d.promise;\n  };\n\n  upload.rejectPromise = function () {\n    var d = $q.defer();\n    var args = arguments;\n    $timeout(function () {\n      d.reject.apply(d, args);\n    });\n    return d.promise;\n  };\n\n  upload.happyPromise = function (promise, data) {\n    var d = $q.defer();\n    promise.then(function (result) {\n      d.resolve(result);\n    }, function (error) {\n      $timeout(function () {\n        throw error;\n      });\n      d.resolve(data);\n    });\n    return d.promise;\n  };\n\n  function applyExifRotations(files, attr, scope) {\n    var promises = [upload.emptyPromise()];\n    angular.forEach(files, function (f, i) {\n      if (f.type.indexOf('image/jpeg') === 0 && upload.attrGetter('ngfFixOrientation', attr, scope, {$file: f})) {\n        promises.push(upload.happyPromise(upload.applyExifRotation(f), f).then(function (fixedFile) {\n          files.splice(i, 1, fixedFile);\n        }));\n      }\n    });\n    return $q.all(promises);\n  }\n\n  function resizeFile(files, attr, scope, ngModel) {\n    var resizeVal = upload.attrGetter('ngfResize', attr, scope);\n    if (!resizeVal || !upload.isResizeSupported() || !files.length) return upload.emptyPromise();\n    if (resizeVal instanceof Function) {\n      var defer = $q.defer();\n      return resizeVal(files).then(function (p) {\n        resizeWithParams(p, files, attr, scope, ngModel).then(function (r) {\n          defer.resolve(r);\n        }, function (e) {\n          defer.reject(e);\n        });\n      }, function (e) {\n        defer.reject(e);\n      });\n    } else {\n      return resizeWithParams(resizeVal, files, attr, scope, ngModel);\n    }\n  }\n\n  function resizeWithParams(params, files, attr, scope, ngModel) {\n    var promises = [upload.emptyPromise()];\n\n    function handleFile(f, i) {\n      if (f.type.indexOf('image') === 0) {\n        if (params.pattern && !upload.validatePattern(f, params.pattern)) return;\n        params.resizeIf = function (width, height) {\n          return upload.attrGetter('ngfResizeIf', attr, scope,\n            {$width: width, $height: height, $file: f});\n        };\n        var promise = upload.resize(f, params);\n        promises.push(promise);\n        promise.then(function (resizedFile) {\n          files.splice(i, 1, resizedFile);\n        }, function (e) {\n          f.$error = 'resize';\n          (f.$errorMessages = (f.$errorMessages || {})).resize = true;\n          f.$errorParam = (e ? (e.message ? e.message : e) + ': ' : '') + (f && f.name);\n          ngModel.$ngfValidations.push({name: 'resize', valid: false});\n          upload.applyModelValidation(ngModel, files);\n        });\n      }\n    }\n\n    for (var i = 0; i < files.length; i++) {\n      handleFile(files[i], i);\n    }\n    return $q.all(promises);\n  }\n\n  upload.updateModel = function (ngModel, attr, scope, fileChange, files, evt, noDelay) {\n    function update(files, invalidFiles, newFiles, dupFiles, isSingleModel) {\n      attr.$$ngfPrevValidFiles = files;\n      attr.$$ngfPrevInvalidFiles = invalidFiles;\n      var file = files && files.length ? files[0] : null;\n      var invalidFile = invalidFiles && invalidFiles.length ? invalidFiles[0] : null;\n\n      if (ngModel) {\n        upload.applyModelValidation(ngModel, files);\n        ngModel.$setViewValue(isSingleModel ? file : files);\n      }\n\n      if (fileChange) {\n        $parse(fileChange)(scope, {\n          $files: files,\n          $file: file,\n          $newFiles: newFiles,\n          $duplicateFiles: dupFiles,\n          $invalidFiles: invalidFiles,\n          $invalidFile: invalidFile,\n          $event: evt\n        });\n      }\n\n      var invalidModel = upload.attrGetter('ngfModelInvalid', attr);\n      if (invalidModel) {\n        $timeout(function () {\n          $parse(invalidModel).assign(scope, isSingleModel ? invalidFile : invalidFiles);\n        });\n      }\n      $timeout(function () {\n        // scope apply changes\n      });\n    }\n\n    var allNewFiles, dupFiles = [], prevValidFiles, prevInvalidFiles,\n      invalids = [], valids = [];\n\n    function removeDuplicates() {\n      function equals(f1, f2) {\n        return f1.name === f2.name && (f1.$ngfOrigSize || f1.size) === (f2.$ngfOrigSize || f2.size) &&\n          f1.type === f2.type;\n      }\n\n      function isInPrevFiles(f) {\n        var j;\n        for (j = 0; j < prevValidFiles.length; j++) {\n          if (equals(f, prevValidFiles[j])) {\n            return true;\n          }\n        }\n        for (j = 0; j < prevInvalidFiles.length; j++) {\n          if (equals(f, prevInvalidFiles[j])) {\n            return true;\n          }\n        }\n        return false;\n      }\n\n      if (files) {\n        allNewFiles = [];\n        dupFiles = [];\n        for (var i = 0; i < files.length; i++) {\n          if (isInPrevFiles(files[i])) {\n            dupFiles.push(files[i]);\n          } else {\n            allNewFiles.push(files[i]);\n          }\n        }\n      }\n    }\n\n    function toArray(v) {\n      return angular.isArray(v) ? v : [v];\n    }\n\n    function resizeAndUpdate() {\n      function updateModel() {\n        $timeout(function () {\n          update(keep ? prevValidFiles.concat(valids) : valids,\n            keep ? prevInvalidFiles.concat(invalids) : invalids,\n            files, dupFiles, isSingleModel);\n        }, options && options.debounce ? options.debounce.change || options.debounce : 0);\n      }\n\n      var resizingFiles = validateAfterResize ? allNewFiles : valids;\n      resizeFile(resizingFiles, attr, scope, ngModel).then(function () {\n        if (validateAfterResize) {\n          upload.validate(allNewFiles, keep ? prevValidFiles.length : 0, ngModel, attr, scope)\n            .then(function (validationResult) {\n              valids = validationResult.validsFiles;\n              invalids = validationResult.invalidsFiles;\n              updateModel();\n            });\n        } else {\n          updateModel();\n        }\n      }, function () {\n        for (var i = 0; i < resizingFiles.length; i++) {\n          var f = resizingFiles[i];\n          if (f.$error === 'resize') {\n            var index = valids.indexOf(f);\n            if (index > -1) {\n              valids.splice(index, 1);\n              invalids.push(f);\n            }\n            updateModel();\n          }\n        }\n      });\n    }\n\n    prevValidFiles = attr.$$ngfPrevValidFiles || [];\n    prevInvalidFiles = attr.$$ngfPrevInvalidFiles || [];\n    if (ngModel && ngModel.$modelValue) {\n      prevValidFiles = toArray(ngModel.$modelValue);\n    }\n\n    var keep = upload.attrGetter('ngfKeep', attr, scope);\n    allNewFiles = (files || []).slice(0);\n    if (keep === 'distinct' || upload.attrGetter('ngfKeepDistinct', attr, scope) === true) {\n      removeDuplicates(attr, scope);\n    }\n\n    var isSingleModel = !keep && !upload.attrGetter('ngfMultiple', attr, scope) && !upload.attrGetter('multiple', attr);\n\n    if (keep && !allNewFiles.length) return;\n\n    upload.attrGetter('ngfBeforeModelChange', attr, scope, {\n      $files: files,\n      $file: files && files.length ? files[0] : null,\n      $newFiles: allNewFiles,\n      $duplicateFiles: dupFiles,\n      $event: evt\n    });\n\n    var validateAfterResize = upload.attrGetter('ngfValidateAfterResize', attr, scope);\n\n    var options = upload.attrGetter('ngfModelOptions', attr, scope);\n    upload.validate(allNewFiles, keep ? prevValidFiles.length : 0, ngModel, attr, scope)\n      .then(function (validationResult) {\n      if (noDelay) {\n        update(allNewFiles, [], files, dupFiles, isSingleModel);\n      } else {\n        if ((!options || !options.allowInvalid) && !validateAfterResize) {\n          valids = validationResult.validFiles;\n          invalids = validationResult.invalidFiles;\n        } else {\n          valids = allNewFiles;\n        }\n        if (upload.attrGetter('ngfFixOrientation', attr, scope) && upload.isExifSupported()) {\n          applyExifRotations(valids, attr, scope).then(function () {\n            resizeAndUpdate();\n          });\n        } else {\n          resizeAndUpdate();\n        }\n      }\n    });\n  };\n\n  return upload;\n}]);\n\nngFileUpload.directive('ngfSelect', ['$parse', '$timeout', '$compile', 'Upload', function ($parse, $timeout, $compile, Upload) {\n  var generatedElems = [];\n\n  function isDelayedClickSupported(ua) {\n    // fix for android native browser < 4.4 and safari windows\n    var m = ua.match(/Android[^\\d]*(\\d+)\\.(\\d+)/);\n    if (m && m.length > 2) {\n      var v = Upload.defaults.androidFixMinorVersion || 4;\n      return parseInt(m[1]) < 4 || (parseInt(m[1]) === v && parseInt(m[2]) < v);\n    }\n\n    // safari on windows\n    return ua.indexOf('Chrome') === -1 && /.*Windows.*Safari.*/.test(ua);\n  }\n\n  function linkFileSelect(scope, elem, attr, ngModel, $parse, $timeout, $compile, upload) {\n    /** @namespace attr.ngfSelect */\n    /** @namespace attr.ngfChange */\n    /** @namespace attr.ngModel */\n    /** @namespace attr.ngfModelOptions */\n    /** @namespace attr.ngfMultiple */\n    /** @namespace attr.ngfCapture */\n    /** @namespace attr.ngfValidate */\n    /** @namespace attr.ngfKeep */\n    var attrGetter = function (name, scope) {\n      return upload.attrGetter(name, attr, scope);\n    };\n\n    function isInputTypeFile() {\n      return elem[0].tagName.toLowerCase() === 'input' && attr.type && attr.type.toLowerCase() === 'file';\n    }\n\n    function fileChangeAttr() {\n      return attrGetter('ngfChange') || attrGetter('ngfSelect');\n    }\n\n    function changeFn(evt) {\n      if (upload.shouldUpdateOn('change', attr, scope)) {\n        var fileList = evt.__files_ || (evt.target && evt.target.files), files = [];\n        /* Handle duplicate call in  IE11 */\n        if (!fileList) return;\n        for (var i = 0; i < fileList.length; i++) {\n          files.push(fileList[i]);\n        }\n        upload.updateModel(ngModel, attr, scope, fileChangeAttr(),\n          files.length ? files : null, evt);\n      }\n    }\n\n    upload.registerModelChangeValidator(ngModel, attr, scope);\n\n    var unwatches = [];\n    if (attrGetter('ngfMultiple')) {\n      unwatches.push(scope.$watch(attrGetter('ngfMultiple'), function () {\n        fileElem.attr('multiple', attrGetter('ngfMultiple', scope));\n      }));\n    }\n    if (attrGetter('ngfCapture')) {\n      unwatches.push(scope.$watch(attrGetter('ngfCapture'), function () {\n        fileElem.attr('capture', attrGetter('ngfCapture', scope));\n      }));\n    }\n    if (attrGetter('ngfAccept')) {\n      unwatches.push(scope.$watch(attrGetter('ngfAccept'), function () {\n        fileElem.attr('accept', attrGetter('ngfAccept', scope));\n      }));\n    }\n    unwatches.push(attr.$observe('accept', function () {\n      fileElem.attr('accept', attrGetter('accept'));\n    }));\n    function bindAttrToFileInput(fileElem, label) {\n      function updateId(val) {\n        fileElem.attr('id', 'ngf-' + val);\n        label.attr('id', 'ngf-label-' + val);\n      }\n\n      for (var i = 0; i < elem[0].attributes.length; i++) {\n        var attribute = elem[0].attributes[i];\n        if (attribute.name !== 'type' && attribute.name !== 'class' && attribute.name !== 'style') {\n          if (attribute.name === 'id') {\n            updateId(attribute.value);\n            unwatches.push(attr.$observe('id', updateId));\n          } else {\n            fileElem.attr(attribute.name, (!attribute.value && (attribute.name === 'required' ||\n            attribute.name === 'multiple')) ? attribute.name : attribute.value);\n          }\n        }\n      }\n    }\n\n    function createFileInput() {\n      if (isInputTypeFile()) {\n        return elem;\n      }\n\n      var fileElem = angular.element('<input type=\"file\">');\n\n      var label = angular.element('<label>upload</label>');\n      label.css('visibility', 'hidden').css('position', 'absolute').css('overflow', 'hidden')\n        .css('width', '0px').css('height', '0px').css('border', 'none')\n        .css('margin', '0px').css('padding', '0px').attr('tabindex', '-1');\n      bindAttrToFileInput(fileElem, label);\n\n      generatedElems.push({el: elem, ref: label});\n\n      document.body.appendChild(label.append(fileElem)[0]);\n\n      return fileElem;\n    }\n\n    function clickHandler(evt) {\n      if (elem.attr('disabled')) return false;\n      if (attrGetter('ngfSelectDisabled', scope)) return;\n\n      var r = detectSwipe(evt);\n      // prevent the click if it is a swipe\n      if (r != null) return r;\n\n      resetModel(evt);\n\n      // fix for md when the element is removed from the DOM and added back #460\n      try {\n        if (!isInputTypeFile() && !document.body.contains(fileElem[0])) {\n          generatedElems.push({el: elem, ref: fileElem.parent()});\n          document.body.appendChild(fileElem.parent()[0]);\n          fileElem.bind('change', changeFn);\n        }\n      } catch (e) {/*ignore*/\n      }\n\n      if (isDelayedClickSupported(navigator.userAgent)) {\n        setTimeout(function () {\n          fileElem[0].click();\n        }, 0);\n      } else {\n        fileElem[0].click();\n      }\n\n      return false;\n    }\n\n\n    var initialTouchStartY = 0;\n    var initialTouchStartX = 0;\n\n    function detectSwipe(evt) {\n      var touches = evt.changedTouches || (evt.originalEvent && evt.originalEvent.changedTouches);\n      if (touches) {\n        if (evt.type === 'touchstart') {\n          initialTouchStartX = touches[0].clientX;\n          initialTouchStartY = touches[0].clientY;\n          return true; // don't block event default\n        } else {\n          // prevent scroll from triggering event\n          if (evt.type === 'touchend') {\n            var currentX = touches[0].clientX;\n            var currentY = touches[0].clientY;\n            if ((Math.abs(currentX - initialTouchStartX) > 20) ||\n              (Math.abs(currentY - initialTouchStartY) > 20)) {\n              evt.stopPropagation();\n              evt.preventDefault();\n              return false;\n            }\n          }\n          return true;\n        }\n      }\n    }\n\n    var fileElem = elem;\n\n    function resetModel(evt) {\n      if (upload.shouldUpdateOn('click', attr, scope) && fileElem.val()) {\n        fileElem.val(null);\n        upload.updateModel(ngModel, attr, scope, fileChangeAttr(), null, evt, true);\n      }\n    }\n\n    if (!isInputTypeFile()) {\n      fileElem = createFileInput();\n    }\n    fileElem.bind('change', changeFn);\n\n    if (!isInputTypeFile()) {\n      elem.bind('click touchstart touchend', clickHandler);\n    } else {\n      elem.bind('click', resetModel);\n    }\n\n    function ie10SameFileSelectFix(evt) {\n      if (fileElem && !fileElem.attr('__ngf_ie10_Fix_')) {\n        if (!fileElem[0].parentNode) {\n          fileElem = null;\n          return;\n        }\n        evt.preventDefault();\n        evt.stopPropagation();\n        fileElem.unbind('click');\n        var clone = fileElem.clone();\n        fileElem.replaceWith(clone);\n        fileElem = clone;\n        fileElem.attr('__ngf_ie10_Fix_', 'true');\n        fileElem.bind('change', changeFn);\n        fileElem.bind('click', ie10SameFileSelectFix);\n        fileElem[0].click();\n        return false;\n      } else {\n        fileElem.removeAttr('__ngf_ie10_Fix_');\n      }\n    }\n\n    if (navigator.appVersion.indexOf('MSIE 10') !== -1) {\n      fileElem.bind('click', ie10SameFileSelectFix);\n    }\n\n    if (ngModel) ngModel.$formatters.push(function (val) {\n      if (val == null || val.length === 0) {\n        if (fileElem.val()) {\n          fileElem.val(null);\n        }\n      }\n      return val;\n    });\n\n    scope.$on('$destroy', function () {\n      if (!isInputTypeFile()) fileElem.parent().remove();\n      angular.forEach(unwatches, function (unwatch) {\n        unwatch();\n      });\n    });\n\n    $timeout(function () {\n      for (var i = 0; i < generatedElems.length; i++) {\n        var g = generatedElems[i];\n        if (!document.body.contains(g.el[0])) {\n          generatedElems.splice(i, 1);\n          g.ref.remove();\n        }\n      }\n    });\n\n    if (window.FileAPI && window.FileAPI.ngfFixIE) {\n      window.FileAPI.ngfFixIE(elem, fileElem, changeFn);\n    }\n  }\n\n  return {\n    restrict: 'AEC',\n    require: '?ngModel',\n    link: function (scope, elem, attr, ngModel) {\n      linkFileSelect(scope, elem, attr, ngModel, $parse, $timeout, $compile, Upload);\n    }\n  };\n}]);\n\n(function () {\n\n  ngFileUpload.service('UploadDataUrl', ['UploadBase', '$timeout', '$q', function (UploadBase, $timeout, $q) {\n    var upload = UploadBase;\n    upload.base64DataUrl = function (file) {\n      if (angular.isArray(file)) {\n        var d = $q.defer(), count = 0;\n        angular.forEach(file, function (f) {\n          upload.dataUrl(f, true)['finally'](function () {\n            count++;\n            if (count === file.length) {\n              var urls = [];\n              angular.forEach(file, function (ff) {\n                urls.push(ff.$ngfDataUrl);\n              });\n              d.resolve(urls, file);\n            }\n          });\n        });\n        return d.promise;\n      } else {\n        return upload.dataUrl(file, true);\n      }\n    };\n    upload.dataUrl = function (file, disallowObjectUrl) {\n      if (!file) return upload.emptyPromise(file, file);\n      if ((disallowObjectUrl && file.$ngfDataUrl != null) || (!disallowObjectUrl && file.$ngfBlobUrl != null)) {\n        return upload.emptyPromise(disallowObjectUrl ? file.$ngfDataUrl : file.$ngfBlobUrl, file);\n      }\n      var p = disallowObjectUrl ? file.$$ngfDataUrlPromise : file.$$ngfBlobUrlPromise;\n      if (p) return p;\n\n      var deferred = $q.defer();\n      $timeout(function () {\n        if (window.FileReader && file &&\n          (!window.FileAPI || navigator.userAgent.indexOf('MSIE 8') === -1 || file.size < 20000) &&\n          (!window.FileAPI || navigator.userAgent.indexOf('MSIE 9') === -1 || file.size < 4000000)) {\n          //prefer URL.createObjectURL for handling refrences to files of all sizes\n          //since it doesn´t build a large string in memory\n          var URL = window.URL || window.webkitURL;\n          if (URL && URL.createObjectURL && !disallowObjectUrl) {\n            var url;\n            try {\n              url = URL.createObjectURL(file);\n            } catch (e) {\n              $timeout(function () {\n                file.$ngfBlobUrl = '';\n                deferred.reject();\n              });\n              return;\n            }\n            $timeout(function () {\n              file.$ngfBlobUrl = url;\n              if (url) {\n                deferred.resolve(url, file);\n                upload.blobUrls = upload.blobUrls || [];\n                upload.blobUrlsTotalSize = upload.blobUrlsTotalSize || 0;\n                upload.blobUrls.push({url: url, size: file.size});\n                upload.blobUrlsTotalSize += file.size || 0;\n                var maxMemory = upload.defaults.blobUrlsMaxMemory || 268435456;\n                var maxLength = upload.defaults.blobUrlsMaxQueueSize || 200;\n                while ((upload.blobUrlsTotalSize > maxMemory || upload.blobUrls.length > maxLength) && upload.blobUrls.length > 1) {\n                  var obj = upload.blobUrls.splice(0, 1)[0];\n                  URL.revokeObjectURL(obj.url);\n                  upload.blobUrlsTotalSize -= obj.size;\n                }\n              }\n            });\n          } else {\n            var fileReader = new FileReader();\n            fileReader.onload = function (e) {\n              $timeout(function () {\n                file.$ngfDataUrl = e.target.result;\n                deferred.resolve(e.target.result, file);\n                $timeout(function () {\n                  delete file.$ngfDataUrl;\n                }, 1000);\n              });\n            };\n            fileReader.onerror = function () {\n              $timeout(function () {\n                file.$ngfDataUrl = '';\n                deferred.reject();\n              });\n            };\n            fileReader.readAsDataURL(file);\n          }\n        } else {\n          $timeout(function () {\n            file[disallowObjectUrl ? '$ngfDataUrl' : '$ngfBlobUrl'] = '';\n            deferred.reject();\n          });\n        }\n      });\n\n      if (disallowObjectUrl) {\n        p = file.$$ngfDataUrlPromise = deferred.promise;\n      } else {\n        p = file.$$ngfBlobUrlPromise = deferred.promise;\n      }\n      p['finally'](function () {\n        delete file[disallowObjectUrl ? '$$ngfDataUrlPromise' : '$$ngfBlobUrlPromise'];\n      });\n      return p;\n    };\n    return upload;\n  }]);\n\n  function getTagType(el) {\n    if (el.tagName.toLowerCase() === 'img') return 'image';\n    if (el.tagName.toLowerCase() === 'audio') return 'audio';\n    if (el.tagName.toLowerCase() === 'video') return 'video';\n    return /./;\n  }\n\n  function linkFileDirective(Upload, $timeout, scope, elem, attr, directiveName, resizeParams, isBackground) {\n    function constructDataUrl(file) {\n      var disallowObjectUrl = Upload.attrGetter('ngfNoObjectUrl', attr, scope);\n      Upload.dataUrl(file, disallowObjectUrl)['finally'](function () {\n        $timeout(function () {\n          var src = (disallowObjectUrl ? file.$ngfDataUrl : file.$ngfBlobUrl) || file.$ngfDataUrl;\n          if (isBackground) {\n            elem.css('background-image', 'url(\\'' + (src || '') + '\\')');\n          } else {\n            elem.attr('src', src);\n          }\n          if (src) {\n            elem.removeClass('ng-hide');\n          } else {\n            elem.addClass('ng-hide');\n          }\n        });\n      });\n    }\n\n    $timeout(function () {\n      var unwatch = scope.$watch(attr[directiveName], function (file) {\n        var size = resizeParams;\n        if (directiveName === 'ngfThumbnail') {\n          if (!size) {\n            size = {\n              width: elem[0].naturalWidth || elem[0].clientWidth,\n              height: elem[0].naturalHeight || elem[0].clientHeight\n            };\n          }\n          if (size.width === 0 && window.getComputedStyle) {\n            var style = getComputedStyle(elem[0]);\n            if (style.width && style.width.indexOf('px') > -1 && style.height && style.height.indexOf('px') > -1) {\n              size = {\n                width: parseInt(style.width.slice(0, -2)),\n                height: parseInt(style.height.slice(0, -2))\n              };\n            }\n          }\n        }\n\n        if (angular.isString(file)) {\n          elem.removeClass('ng-hide');\n          if (isBackground) {\n            return elem.css('background-image', 'url(\\'' + file + '\\')');\n          } else {\n            return elem.attr('src', file);\n          }\n        }\n        if (file && file.type && file.type.search(getTagType(elem[0])) === 0 &&\n          (!isBackground || file.type.indexOf('image') === 0)) {\n          if (size && Upload.isResizeSupported()) {\n            size.resizeIf = function (width, height) {\n              return Upload.attrGetter('ngfResizeIf', attr, scope,\n                {$width: width, $height: height, $file: file});\n            };\n            Upload.resize(file, size).then(\n              function (f) {\n                constructDataUrl(f);\n              }, function (e) {\n                throw e;\n              }\n            );\n          } else {\n            constructDataUrl(file);\n          }\n        } else {\n          elem.addClass('ng-hide');\n        }\n      });\n\n      scope.$on('$destroy', function () {\n        unwatch();\n      });\n    });\n  }\n\n\n  /** @namespace attr.ngfSrc */\n  /** @namespace attr.ngfNoObjectUrl */\n  ngFileUpload.directive('ngfSrc', ['Upload', '$timeout', function (Upload, $timeout) {\n    return {\n      restrict: 'AE',\n      link: function (scope, elem, attr) {\n        linkFileDirective(Upload, $timeout, scope, elem, attr, 'ngfSrc',\n          Upload.attrGetter('ngfResize', attr, scope), false);\n      }\n    };\n  }]);\n\n  /** @namespace attr.ngfBackground */\n  /** @namespace attr.ngfNoObjectUrl */\n  ngFileUpload.directive('ngfBackground', ['Upload', '$timeout', function (Upload, $timeout) {\n    return {\n      restrict: 'AE',\n      link: function (scope, elem, attr) {\n        linkFileDirective(Upload, $timeout, scope, elem, attr, 'ngfBackground',\n          Upload.attrGetter('ngfResize', attr, scope), true);\n      }\n    };\n  }]);\n\n  /** @namespace attr.ngfThumbnail */\n  /** @namespace attr.ngfAsBackground */\n  /** @namespace attr.ngfSize */\n  /** @namespace attr.ngfNoObjectUrl */\n  ngFileUpload.directive('ngfThumbnail', ['Upload', '$timeout', function (Upload, $timeout) {\n    return {\n      restrict: 'AE',\n      link: function (scope, elem, attr) {\n        var size = Upload.attrGetter('ngfSize', attr, scope);\n        linkFileDirective(Upload, $timeout, scope, elem, attr, 'ngfThumbnail', size,\n          Upload.attrGetter('ngfAsBackground', attr, scope));\n      }\n    };\n  }]);\n\n  ngFileUpload.config(['$compileProvider', function ($compileProvider) {\n    if ($compileProvider.imgSrcSanitizationWhitelist) $compileProvider.imgSrcSanitizationWhitelist(/^\\s*(https?|ftp|mailto|tel|webcal|local|file|data|blob):/);\n    if ($compileProvider.aHrefSanitizationWhitelist) $compileProvider.aHrefSanitizationWhitelist(/^\\s*(https?|ftp|mailto|tel|webcal|local|file|data|blob):/);\n  }]);\n\n  ngFileUpload.filter('ngfDataUrl', ['UploadDataUrl', '$sce', function (UploadDataUrl, $sce) {\n    return function (file, disallowObjectUrl, trustedUrl) {\n      if (angular.isString(file)) {\n        return $sce.trustAsResourceUrl(file);\n      }\n      var src = file && ((disallowObjectUrl ? file.$ngfDataUrl : file.$ngfBlobUrl) || file.$ngfDataUrl);\n      if (file && !src) {\n        if (!file.$ngfDataUrlFilterInProgress && angular.isObject(file)) {\n          file.$ngfDataUrlFilterInProgress = true;\n          UploadDataUrl.dataUrl(file, disallowObjectUrl);\n        }\n        return '';\n      }\n      if (file) delete file.$ngfDataUrlFilterInProgress;\n      return (file && src ? (trustedUrl ? $sce.trustAsResourceUrl(src) : src) : file) || '';\n    };\n  }]);\n\n})();\n\nngFileUpload.service('UploadValidate', ['UploadDataUrl', '$q', '$timeout', function (UploadDataUrl, $q, $timeout) {\n  var upload = UploadDataUrl;\n\n  function globStringToRegex(str) {\n    var regexp = '', excludes = [];\n    if (str.length > 2 && str[0] === '/' && str[str.length - 1] === '/') {\n      regexp = str.substring(1, str.length - 1);\n    } else {\n      var split = str.split(',');\n      if (split.length > 1) {\n        for (var i = 0; i < split.length; i++) {\n          var r = globStringToRegex(split[i]);\n          if (r.regexp) {\n            regexp += '(' + r.regexp + ')';\n            if (i < split.length - 1) {\n              regexp += '|';\n            }\n          } else {\n            excludes = excludes.concat(r.excludes);\n          }\n        }\n      } else {\n        if (str.indexOf('!') === 0) {\n          excludes.push('^((?!' + globStringToRegex(str.substring(1)).regexp + ').)*$');\n        } else {\n          if (str.indexOf('.') === 0) {\n            str = '*' + str;\n          }\n          regexp = '^' + str.replace(new RegExp('[.\\\\\\\\+*?\\\\[\\\\^\\\\]$(){}=!<>|:\\\\-]', 'g'), '\\\\$&') + '$';\n          regexp = regexp.replace(/\\\\\\*/g, '.*').replace(/\\\\\\?/g, '.');\n        }\n      }\n    }\n    return {regexp: regexp, excludes: excludes};\n  }\n\n  upload.validatePattern = function (file, val) {\n    if (!val) {\n      return true;\n    }\n    var pattern = globStringToRegex(val), valid = true;\n    if (pattern.regexp && pattern.regexp.length) {\n      var regexp = new RegExp(pattern.regexp, 'i');\n      valid = (file.type != null && regexp.test(file.type)) ||\n        (file.name != null && regexp.test(file.name));\n    }\n    var len = pattern.excludes.length;\n    while (len--) {\n      var exclude = new RegExp(pattern.excludes[len], 'i');\n      valid = valid && (file.type == null || exclude.test(file.type)) &&\n        (file.name == null || exclude.test(file.name));\n    }\n    return valid;\n  };\n\n  upload.ratioToFloat = function (val) {\n    var r = val.toString(), xIndex = r.search(/[x:]/i);\n    if (xIndex > -1) {\n      r = parseFloat(r.substring(0, xIndex)) / parseFloat(r.substring(xIndex + 1));\n    } else {\n      r = parseFloat(r);\n    }\n    return r;\n  };\n\n  upload.registerModelChangeValidator = function (ngModel, attr, scope) {\n    if (ngModel) {\n      ngModel.$formatters.push(function (files) {\n        if (ngModel.$dirty) {\n          var filesArray = files;\n          if (files && !angular.isArray(files)) {\n            filesArray = [files];\n          }\n          upload.validate(filesArray, 0, ngModel, attr, scope).then(function () {\n            upload.applyModelValidation(ngModel, filesArray);\n          });\n        }\n        return files;\n      });\n    }\n  };\n\n  function markModelAsDirty(ngModel, files) {\n    if (files != null && !ngModel.$dirty) {\n      if (ngModel.$setDirty) {\n        ngModel.$setDirty();\n      } else {\n        ngModel.$dirty = true;\n      }\n    }\n  }\n\n  upload.applyModelValidation = function (ngModel, files) {\n    markModelAsDirty(ngModel, files);\n    angular.forEach(ngModel.$ngfValidations, function (validation) {\n      ngModel.$setValidity(validation.name, validation.valid);\n    });\n  };\n\n  upload.getValidationAttr = function (attr, scope, name, validationName, file) {\n    var dName = 'ngf' + name[0].toUpperCase() + name.substr(1);\n    var val = upload.attrGetter(dName, attr, scope, {$file: file});\n    if (val == null) {\n      val = upload.attrGetter('ngfValidate', attr, scope, {$file: file});\n      if (val) {\n        var split = (validationName || name).split('.');\n        val = val[split[0]];\n        if (split.length > 1) {\n          val = val && val[split[1]];\n        }\n      }\n    }\n    return val;\n  };\n\n  upload.validate = function (files, prevLength, ngModel, attr, scope) {\n    ngModel = ngModel || {};\n    ngModel.$ngfValidations = ngModel.$ngfValidations || [];\n\n    angular.forEach(ngModel.$ngfValidations, function (v) {\n      v.valid = true;\n    });\n\n    var attrGetter = function (name, params) {\n      return upload.attrGetter(name, attr, scope, params);\n    };\n\n    var ignoredErrors = (upload.attrGetter('ngfIgnoreInvalid', attr, scope) || '').split(' ');\n    var runAllValidation = upload.attrGetter('ngfRunAllValidations', attr, scope);\n\n    if (files == null || files.length === 0) {\n      return upload.emptyPromise({'validFiles': files, 'invalidFiles': []});\n    }\n\n    files = files.length === undefined ? [files] : files.slice(0);\n    var invalidFiles = [];\n\n    function validateSync(name, validationName, fn) {\n      if (files) {\n        var i = files.length, valid = null;\n        while (i--) {\n          var file = files[i];\n          if (file) {\n            var val = upload.getValidationAttr(attr, scope, name, validationName, file);\n            if (val != null) {\n              if (!fn(file, val, i)) {\n                if (ignoredErrors.indexOf(name) === -1) {\n                  file.$error = name;\n                  (file.$errorMessages = (file.$errorMessages || {}))[name] = true;\n                  file.$errorParam = val;\n                  if (invalidFiles.indexOf(file) === -1) {\n                    invalidFiles.push(file);\n                  }\n                  if (!runAllValidation) {\n                    files.splice(i, 1);\n                  }\n                  valid = false;\n                } else {\n                  files.splice(i, 1);\n                }\n              }\n            }\n          }\n        }\n        if (valid !== null) {\n          ngModel.$ngfValidations.push({name: name, valid: valid});\n        }\n      }\n    }\n\n    validateSync('pattern', null, upload.validatePattern);\n    validateSync('minSize', 'size.min', function (file, val) {\n      return file.size + 0.1 >= upload.translateScalars(val);\n    });\n    validateSync('maxSize', 'size.max', function (file, val) {\n      return file.size - 0.1 <= upload.translateScalars(val);\n    });\n    var totalSize = 0;\n    validateSync('maxTotalSize', null, function (file, val) {\n      totalSize += file.size;\n      if (totalSize > upload.translateScalars(val)) {\n        files.splice(0, files.length);\n        return false;\n      }\n      return true;\n    });\n\n    validateSync('validateFn', null, function (file, r) {\n      return r === true || r === null || r === '';\n    });\n\n    if (!files.length) {\n      return upload.emptyPromise({'validFiles': [], 'invalidFiles': invalidFiles});\n    }\n\n    function validateAsync(name, validationName, type, asyncFn, fn) {\n      function resolveResult(defer, file, val) {\n        function resolveInternal(fn) {\n          if (fn()) {\n            if (ignoredErrors.indexOf(name) === -1) {\n              file.$error = name;\n              (file.$errorMessages = (file.$errorMessages || {}))[name] = true;\n              file.$errorParam = val;\n              if (invalidFiles.indexOf(file) === -1) {\n                invalidFiles.push(file);\n              }\n              if (!runAllValidation) {\n                var i = files.indexOf(file);\n                if (i > -1) files.splice(i, 1);\n              }\n              defer.resolve(false);\n            } else {\n              var j = files.indexOf(file);\n              if (j > -1) files.splice(j, 1);\n              defer.resolve(true);\n            }\n          } else {\n            defer.resolve(true);\n          }\n        }\n\n        if (val != null) {\n          asyncFn(file, val).then(function (d) {\n            resolveInternal(function () {\n              return !fn(d, val);\n            });\n          }, function () {\n            resolveInternal(function () {\n              return attrGetter('ngfValidateForce', {$file: file});\n            });\n          });\n        } else {\n          defer.resolve(true);\n        }\n      }\n\n      var promises = [upload.emptyPromise(true)];\n      if (files) {\n        files = files.length === undefined ? [files] : files;\n        angular.forEach(files, function (file) {\n          var defer = $q.defer();\n          promises.push(defer.promise);\n          if (type && (file.type == null || file.type.search(type) !== 0)) {\n            defer.resolve(true);\n            return;\n          }\n          if (name === 'dimensions' && upload.attrGetter('ngfDimensions', attr) != null) {\n            upload.imageDimensions(file).then(function (d) {\n              resolveResult(defer, file,\n                attrGetter('ngfDimensions', {$file: file, $width: d.width, $height: d.height}));\n            }, function () {\n              defer.resolve(false);\n            });\n          } else if (name === 'duration' && upload.attrGetter('ngfDuration', attr) != null) {\n            upload.mediaDuration(file).then(function (d) {\n              resolveResult(defer, file,\n                attrGetter('ngfDuration', {$file: file, $duration: d}));\n            }, function () {\n              defer.resolve(false);\n            });\n          } else {\n            resolveResult(defer, file,\n              upload.getValidationAttr(attr, scope, name, validationName, file));\n          }\n        });\n      }\n      var deffer = $q.defer();\n      $q.all(promises).then(function (values) {\n        var isValid = true;\n        for (var i = 0; i < values.length; i++) {\n          if (!values[i]) {\n            isValid = false;\n            break;\n          }\n        }\n        ngModel.$ngfValidations.push({name: name, valid: isValid});\n        deffer.resolve(isValid);\n      });\n      return deffer.promise;\n    }\n\n    var deffer = $q.defer();\n    var promises = [];\n\n    promises.push(validateAsync('maxHeight', 'height.max', /image/,\n      this.imageDimensions, function (d, val) {\n        return d.height <= val;\n      }));\n    promises.push(validateAsync('minHeight', 'height.min', /image/,\n      this.imageDimensions, function (d, val) {\n        return d.height >= val;\n      }));\n    promises.push(validateAsync('maxWidth', 'width.max', /image/,\n      this.imageDimensions, function (d, val) {\n        return d.width <= val;\n      }));\n    promises.push(validateAsync('minWidth', 'width.min', /image/,\n      this.imageDimensions, function (d, val) {\n        return d.width >= val;\n      }));\n    promises.push(validateAsync('dimensions', null, /image/,\n      function (file, val) {\n        return upload.emptyPromise(val);\n      }, function (r) {\n        return r;\n      }));\n    promises.push(validateAsync('ratio', null, /image/,\n      this.imageDimensions, function (d, val) {\n        var split = val.toString().split(','), valid = false;\n        for (var i = 0; i < split.length; i++) {\n          if (Math.abs((d.width / d.height) - upload.ratioToFloat(split[i])) < 0.01) {\n            valid = true;\n          }\n        }\n        return valid;\n      }));\n    promises.push(validateAsync('maxRatio', 'ratio.max', /image/,\n      this.imageDimensions, function (d, val) {\n        return (d.width / d.height) - upload.ratioToFloat(val) < 0.0001;\n      }));\n    promises.push(validateAsync('minRatio', 'ratio.min', /image/,\n      this.imageDimensions, function (d, val) {\n        return (d.width / d.height) - upload.ratioToFloat(val) > -0.0001;\n      }));\n    promises.push(validateAsync('maxDuration', 'duration.max', /audio|video/,\n      this.mediaDuration, function (d, val) {\n        return d <= upload.translateScalars(val);\n      }));\n    promises.push(validateAsync('minDuration', 'duration.min', /audio|video/,\n      this.mediaDuration, function (d, val) {\n        return d >= upload.translateScalars(val);\n      }));\n    promises.push(validateAsync('duration', null, /audio|video/,\n      function (file, val) {\n        return upload.emptyPromise(val);\n      }, function (r) {\n        return r;\n      }));\n\n    promises.push(validateAsync('validateAsyncFn', null, null,\n      function (file, val) {\n        return val;\n      }, function (r) {\n        return r === true || r === null || r === '';\n      }));\n\n    $q.all(promises).then(function () {\n\n      if (runAllValidation) {\n        for (var i = 0; i < files.length; i++) {\n          var file = files[i];\n          if (file.$error) {\n            files.splice(i--, 1);\n          }\n        }\n      }\n\n      runAllValidation = false;\n      validateSync('maxFiles', null, function (file, val, i) {\n        return prevLength + i < val;\n      });\n\n      deffer.resolve({'validFiles': files, 'invalidFiles': invalidFiles});\n    });\n    return deffer.promise;\n  };\n\n  upload.imageDimensions = function (file) {\n    if (file.$ngfWidth && file.$ngfHeight) {\n      var d = $q.defer();\n      $timeout(function () {\n        d.resolve({width: file.$ngfWidth, height: file.$ngfHeight});\n      });\n      return d.promise;\n    }\n    if (file.$ngfDimensionPromise) return file.$ngfDimensionPromise;\n\n    var deferred = $q.defer();\n    $timeout(function () {\n      if (file.type.indexOf('image') !== 0) {\n        deferred.reject('not image');\n        return;\n      }\n      upload.dataUrl(file).then(function (dataUrl) {\n        var img = angular.element('<img>').attr('src', dataUrl)\n          .css('visibility', 'hidden').css('position', 'fixed')\n          .css('max-width', 'none !important').css('max-height', 'none !important');\n\n        function success() {\n          var width = img[0].naturalWidth || img[0].clientWidth;\n          var height = img[0].naturalHeight || img[0].clientHeight;\n          img.remove();\n          file.$ngfWidth = width;\n          file.$ngfHeight = height;\n          deferred.resolve({width: width, height: height});\n        }\n\n        function error() {\n          img.remove();\n          deferred.reject('load error');\n        }\n\n        img.on('load', success);\n        img.on('error', error);\n\n        var secondsCounter = 0;\n        function checkLoadErrorInCaseOfNoCallback() {\n          $timeout(function () {\n            if (img[0].parentNode) {\n              if (img[0].clientWidth) {\n                success();\n              } else if (secondsCounter++ > 10) {\n                error();\n              } else {\n                checkLoadErrorInCaseOfNoCallback();\n              }\n            }\n          }, 1000);\n        }\n\n        checkLoadErrorInCaseOfNoCallback();\n\n        angular.element(document.getElementsByTagName('body')[0]).append(img);\n      }, function () {\n        deferred.reject('load error');\n      });\n    });\n\n    file.$ngfDimensionPromise = deferred.promise;\n    file.$ngfDimensionPromise['finally'](function () {\n      delete file.$ngfDimensionPromise;\n    });\n    return file.$ngfDimensionPromise;\n  };\n\n  upload.mediaDuration = function (file) {\n    if (file.$ngfDuration) {\n      var d = $q.defer();\n      $timeout(function () {\n        d.resolve(file.$ngfDuration);\n      });\n      return d.promise;\n    }\n    if (file.$ngfDurationPromise) return file.$ngfDurationPromise;\n\n    var deferred = $q.defer();\n    $timeout(function () {\n      if (file.type.indexOf('audio') !== 0 && file.type.indexOf('video') !== 0) {\n        deferred.reject('not media');\n        return;\n      }\n      upload.dataUrl(file).then(function (dataUrl) {\n        var el = angular.element(file.type.indexOf('audio') === 0 ? '<audio>' : '<video>')\n          .attr('src', dataUrl).css('visibility', 'none').css('position', 'fixed');\n\n        function success() {\n          var duration = el[0].duration;\n          file.$ngfDuration = duration;\n          el.remove();\n          deferred.resolve(duration);\n        }\n\n        function error() {\n          el.remove();\n          deferred.reject('load error');\n        }\n\n        el.on('loadedmetadata', success);\n        el.on('error', error);\n        var count = 0;\n\n        function checkLoadError() {\n          $timeout(function () {\n            if (el[0].parentNode) {\n              if (el[0].duration) {\n                success();\n              } else if (count > 10) {\n                error();\n              } else {\n                checkLoadError();\n              }\n            }\n          }, 1000);\n        }\n\n        checkLoadError();\n\n        angular.element(document.body).append(el);\n      }, function () {\n        deferred.reject('load error');\n      });\n    });\n\n    file.$ngfDurationPromise = deferred.promise;\n    file.$ngfDurationPromise['finally'](function () {\n      delete file.$ngfDurationPromise;\n    });\n    return file.$ngfDurationPromise;\n  };\n  return upload;\n}\n]);\n\nngFileUpload.service('UploadResize', ['UploadValidate', '$q', function (UploadValidate, $q) {\n  var upload = UploadValidate;\n\n  /**\n   * Conserve aspect ratio of the original region. Useful when shrinking/enlarging\n   * images to fit into a certain area.\n   * Source:  http://stackoverflow.com/a/14731922\n   *\n   * @param {Number} srcWidth Source area width\n   * @param {Number} srcHeight Source area height\n   * @param {Number} maxWidth Nestable area maximum available width\n   * @param {Number} maxHeight Nestable area maximum available height\n   * @return {Object} { width, height }\n   */\n  var calculateAspectRatioFit = function (srcWidth, srcHeight, maxWidth, maxHeight, centerCrop) {\n    var ratio = centerCrop ? Math.max(maxWidth / srcWidth, maxHeight / srcHeight) :\n      Math.min(maxWidth / srcWidth, maxHeight / srcHeight);\n    return {\n      width: srcWidth * ratio, height: srcHeight * ratio,\n      marginX: srcWidth * ratio - maxWidth, marginY: srcHeight * ratio - maxHeight\n    };\n  };\n\n  // Extracted from https://github.com/romelgomez/angular-firebase-image-upload/blob/master/app/scripts/fileUpload.js#L89\n  var resize = function (imagen, width, height, quality, type, ratio, centerCrop, resizeIf) {\n    var deferred = $q.defer();\n    var canvasElement = document.createElement('canvas');\n    var imageElement = document.createElement('img');\n    imageElement.setAttribute('style', 'visibility:hidden;position:fixed;z-index:-100000');\n    document.body.appendChild(imageElement);\n\n    imageElement.onload = function () {\n      var imgWidth = imageElement.width, imgHeight = imageElement.height;\n      imageElement.parentNode.removeChild(imageElement);\n      if (resizeIf != null && resizeIf(imgWidth, imgHeight) === false) {\n        deferred.reject('resizeIf');\n        return;\n      }\n      try {\n        if (ratio) {\n          var ratioFloat = upload.ratioToFloat(ratio);\n          var imgRatio = imgWidth / imgHeight;\n          if (imgRatio < ratioFloat) {\n            width = imgWidth;\n            height = width / ratioFloat;\n          } else {\n            height = imgHeight;\n            width = height * ratioFloat;\n          }\n        }\n        if (!width) {\n          width = imgWidth;\n        }\n        if (!height) {\n          height = imgHeight;\n        }\n        var dimensions = calculateAspectRatioFit(imgWidth, imgHeight, width, height, centerCrop);\n        canvasElement.width = Math.min(dimensions.width, width);\n        canvasElement.height = Math.min(dimensions.height, height);\n        var context = canvasElement.getContext('2d');\n        context.drawImage(imageElement,\n          Math.min(0, -dimensions.marginX / 2), Math.min(0, -dimensions.marginY / 2),\n          dimensions.width, dimensions.height);\n        deferred.resolve(canvasElement.toDataURL(type || 'image/WebP', quality || 0.934));\n      } catch (e) {\n        deferred.reject(e);\n      }\n    };\n    imageElement.onerror = function () {\n      imageElement.parentNode.removeChild(imageElement);\n      deferred.reject();\n    };\n    imageElement.src = imagen;\n    return deferred.promise;\n  };\n\n  upload.dataUrltoBlob = function (dataurl, name, origSize) {\n    var arr = dataurl.split(','), mime = arr[0].match(/:(.*?);/)[1],\n      bstr = atob(arr[1]), n = bstr.length, u8arr = new Uint8Array(n);\n    while (n--) {\n      u8arr[n] = bstr.charCodeAt(n);\n    }\n    var blob = new window.Blob([u8arr], {type: mime});\n    blob.name = name;\n    blob.$ngfOrigSize = origSize;\n    return blob;\n  };\n\n  upload.isResizeSupported = function () {\n    var elem = document.createElement('canvas');\n    return window.atob && elem.getContext && elem.getContext('2d') && window.Blob;\n  };\n\n  if (upload.isResizeSupported()) {\n    // add name getter to the blob constructor prototype\n    Object.defineProperty(window.Blob.prototype, 'name', {\n      get: function () {\n        return this.$ngfName;\n      },\n      set: function (v) {\n        this.$ngfName = v;\n      },\n      configurable: true\n    });\n  }\n\n  upload.resize = function (file, options) {\n    if (file.type.indexOf('image') !== 0) return upload.emptyPromise(file);\n\n    var deferred = $q.defer();\n    upload.dataUrl(file, true).then(function (url) {\n      resize(url, options.width, options.height, options.quality, options.type || file.type,\n        options.ratio, options.centerCrop, options.resizeIf)\n        .then(function (dataUrl) {\n          if (file.type === 'image/jpeg' && options.restoreExif !== false) {\n            try {\n              dataUrl = upload.restoreExif(url, dataUrl);\n            } catch (e) {\n              setTimeout(function () {throw e;}, 1);\n            }\n          }\n          try {\n            var blob = upload.dataUrltoBlob(dataUrl, file.name, file.size);\n            deferred.resolve(blob);\n          } catch (e) {\n            deferred.reject(e);\n          }\n        }, function (r) {\n          if (r === 'resizeIf') {\n            deferred.resolve(file);\n          }\n          deferred.reject(r);\n        });\n    }, function (e) {\n      deferred.reject(e);\n    });\n    return deferred.promise;\n  };\n\n  return upload;\n}]);\n\n(function () {\n  ngFileUpload.directive('ngfDrop', ['$parse', '$timeout', '$window', 'Upload', '$http', '$q',\n    function ($parse, $timeout, $window, Upload, $http, $q) {\n      return {\n        restrict: 'AEC',\n        require: '?ngModel',\n        link: function (scope, elem, attr, ngModel) {\n          linkDrop(scope, elem, attr, ngModel, $parse, $timeout, $window, Upload, $http, $q);\n        }\n      };\n    }]);\n\n  ngFileUpload.directive('ngfNoFileDrop', function () {\n    return function (scope, elem) {\n      if (dropAvailable()) elem.css('display', 'none');\n    };\n  });\n\n  ngFileUpload.directive('ngfDropAvailable', ['$parse', '$timeout', 'Upload', function ($parse, $timeout, Upload) {\n    return function (scope, elem, attr) {\n      if (dropAvailable()) {\n        var model = $parse(Upload.attrGetter('ngfDropAvailable', attr));\n        $timeout(function () {\n          model(scope);\n          if (model.assign) {\n            model.assign(scope, true);\n          }\n        });\n      }\n    };\n  }]);\n\n  function linkDrop(scope, elem, attr, ngModel, $parse, $timeout, $window, upload, $http, $q) {\n    var available = dropAvailable();\n\n    var attrGetter = function (name, scope, params) {\n      return upload.attrGetter(name, attr, scope, params);\n    };\n\n    if (attrGetter('dropAvailable')) {\n      $timeout(function () {\n        if (scope[attrGetter('dropAvailable')]) {\n          scope[attrGetter('dropAvailable')].value = available;\n        } else {\n          scope[attrGetter('dropAvailable')] = available;\n        }\n      });\n    }\n    if (!available) {\n      if (attrGetter('ngfHideOnDropNotAvailable', scope) === true) {\n        elem.css('display', 'none');\n      }\n      return;\n    }\n\n    function isDisabled() {\n      return elem.attr('disabled') || attrGetter('ngfDropDisabled', scope);\n    }\n\n    if (attrGetter('ngfSelect') == null) {\n      upload.registerModelChangeValidator(ngModel, attr, scope);\n    }\n\n    var leaveTimeout = null;\n    var stopPropagation = $parse(attrGetter('ngfStopPropagation'));\n    var dragOverDelay = 1;\n    var actualDragOverClass;\n\n    elem[0].addEventListener('dragover', function (evt) {\n      if (isDisabled() || !upload.shouldUpdateOn('drop', attr, scope)) return;\n      evt.preventDefault();\n      if (stopPropagation(scope)) evt.stopPropagation();\n      // handling dragover events from the Chrome download bar\n      if (navigator.userAgent.indexOf('Chrome') > -1) {\n        var b = evt.dataTransfer.effectAllowed;\n        evt.dataTransfer.dropEffect = ('move' === b || 'linkMove' === b) ? 'move' : 'copy';\n      }\n      $timeout.cancel(leaveTimeout);\n      if (!actualDragOverClass) {\n        actualDragOverClass = 'C';\n        calculateDragOverClass(scope, attr, evt, function (clazz) {\n          actualDragOverClass = clazz;\n          elem.addClass(actualDragOverClass);\n          attrGetter('ngfDrag', scope, {$isDragging: true, $class: actualDragOverClass, $event: evt});\n        });\n      }\n    }, false);\n    elem[0].addEventListener('dragenter', function (evt) {\n      if (isDisabled() || !upload.shouldUpdateOn('drop', attr, scope)) return;\n      evt.preventDefault();\n      if (stopPropagation(scope)) evt.stopPropagation();\n    }, false);\n    elem[0].addEventListener('dragleave', function (evt) {\n      if (isDisabled() || !upload.shouldUpdateOn('drop', attr, scope)) return;\n      evt.preventDefault();\n      if (stopPropagation(scope)) evt.stopPropagation();\n      leaveTimeout = $timeout(function () {\n        if (actualDragOverClass) elem.removeClass(actualDragOverClass);\n        actualDragOverClass = null;\n        attrGetter('ngfDrag', scope, {$isDragging: false, $event: evt});\n      }, dragOverDelay || 100);\n    }, false);\n    elem[0].addEventListener('drop', function (evt) {\n      if (isDisabled() || !upload.shouldUpdateOn('drop', attr, scope)) return;\n      evt.preventDefault();\n      if (stopPropagation(scope)) evt.stopPropagation();\n      if (actualDragOverClass) elem.removeClass(actualDragOverClass);\n      actualDragOverClass = null;\n      extractFilesAndUpdateModel(evt.dataTransfer, evt, 'dropUrl');\n    }, false);\n    elem[0].addEventListener('paste', function (evt) {\n      if (navigator.userAgent.toLowerCase().indexOf('firefox') > -1 &&\n        attrGetter('ngfEnableFirefoxPaste', scope)) {\n        evt.preventDefault();\n      }\n      if (isDisabled() || !upload.shouldUpdateOn('paste', attr, scope)) return;\n      extractFilesAndUpdateModel(evt.clipboardData || evt.originalEvent.clipboardData, evt, 'pasteUrl');\n    }, false);\n\n    if (navigator.userAgent.toLowerCase().indexOf('firefox') > -1 &&\n      attrGetter('ngfEnableFirefoxPaste', scope)) {\n      elem.attr('contenteditable', true);\n      elem.on('keypress', function (e) {\n        if (!e.metaKey && !e.ctrlKey) {\n          e.preventDefault();\n        }\n      });\n    }\n\n    function extractFilesAndUpdateModel(source, evt, updateOnType) {\n      if (!source) return;\n      // html needs to be calculated on the same process otherwise the data will be wiped\n      // after promise resolve or setTimeout.\n      var html;\n      try {\n        html = source && source.getData && source.getData('text/html');\n      } catch (e) {/* Fix IE11 that throw error calling getData */\n      }\n      extractFiles(source.items, source.files, attrGetter('ngfAllowDir', scope) !== false,\n        attrGetter('multiple') || attrGetter('ngfMultiple', scope)).then(function (files) {\n        if (files.length) {\n          updateModel(files, evt);\n        } else {\n          extractFilesFromHtml(updateOnType, html).then(function (files) {\n            updateModel(files, evt);\n          });\n        }\n      });\n    }\n\n    function updateModel(files, evt) {\n      upload.updateModel(ngModel, attr, scope, attrGetter('ngfChange') || attrGetter('ngfDrop'), files, evt);\n    }\n\n    function extractFilesFromHtml(updateOn, html) {\n      if (!upload.shouldUpdateOn(updateOn, attr, scope) || typeof html !== 'string') return upload.rejectPromise([]);\n      var urls = [];\n      html.replace(/<(img src|img [^>]* src) *=\\\"([^\\\"]*)\\\"/gi, function (m, n, src) {\n        urls.push(src);\n      });\n      var promises = [], files = [];\n      if (urls.length) {\n        angular.forEach(urls, function (url) {\n          promises.push(upload.urlToBlob(url).then(function (blob) {\n            files.push(blob);\n          }));\n        });\n        var defer = $q.defer();\n        $q.all(promises).then(function () {\n          defer.resolve(files);\n        }, function (e) {\n          defer.reject(e);\n        });\n        return defer.promise;\n      }\n      return upload.emptyPromise();\n    }\n\n    function calculateDragOverClass(scope, attr, evt, callback) {\n      var obj = attrGetter('ngfDragOverClass', scope, {$event: evt}), dClass = 'dragover';\n      if (angular.isString(obj)) {\n        dClass = obj;\n      } else if (obj) {\n        if (obj.delay) dragOverDelay = obj.delay;\n        if (obj.accept || obj.reject) {\n          var items = evt.dataTransfer.items;\n          if (items == null || !items.length) {\n            dClass = obj.accept;\n          } else {\n            var pattern = obj.pattern || attrGetter('ngfPattern', scope, {$event: evt});\n            var len = items.length;\n            while (len--) {\n              if (!upload.validatePattern(items[len], pattern)) {\n                dClass = obj.reject;\n                break;\n              } else {\n                dClass = obj.accept;\n              }\n            }\n          }\n        }\n      }\n      callback(dClass);\n    }\n\n    function extractFiles(items, fileList, allowDir, multiple) {\n      var maxFiles = upload.getValidationAttr(attr, scope, 'maxFiles');\n      if (maxFiles == null) {\n        maxFiles = Number.MAX_VALUE;\n      }\n      var maxTotalSize = upload.getValidationAttr(attr, scope, 'maxTotalSize');\n      if (maxTotalSize == null) {\n        maxTotalSize = Number.MAX_VALUE;\n      }\n      var includeDir = attrGetter('ngfIncludeDir', scope);\n      var files = [], totalSize = 0;\n\n      function traverseFileTree(entry, path) {\n        var defer = $q.defer();\n        if (entry != null) {\n          if (entry.isDirectory) {\n            var promises = [upload.emptyPromise()];\n            if (includeDir) {\n              var file = {type: 'directory'};\n              file.name = file.path = (path || '') + entry.name;\n              files.push(file);\n            }\n            var dirReader = entry.createReader();\n            var entries = [];\n            var readEntries = function () {\n              dirReader.readEntries(function (results) {\n                try {\n                  if (!results.length) {\n                    angular.forEach(entries.slice(0), function (e) {\n                      if (files.length <= maxFiles && totalSize <= maxTotalSize) {\n                        promises.push(traverseFileTree(e, (path ? path : '') + entry.name + '/'));\n                      }\n                    });\n                    $q.all(promises).then(function () {\n                      defer.resolve();\n                    }, function (e) {\n                      defer.reject(e);\n                    });\n                  } else {\n                    entries = entries.concat(Array.prototype.slice.call(results || [], 0));\n                    readEntries();\n                  }\n                } catch (e) {\n                  defer.reject(e);\n                }\n              }, function (e) {\n                defer.reject(e);\n              });\n            };\n            readEntries();\n          } else {\n            entry.file(function (file) {\n              try {\n                file.path = (path ? path : '') + file.name;\n                if (includeDir) {\n                  file = upload.rename(file, file.path);\n                }\n                files.push(file);\n                totalSize += file.size;\n                defer.resolve();\n              } catch (e) {\n                defer.reject(e);\n              }\n            }, function (e) {\n              defer.reject(e);\n            });\n          }\n        }\n        return defer.promise;\n      }\n\n      var promises = [upload.emptyPromise()];\n\n      if (items && items.length > 0 && $window.location.protocol !== 'file:') {\n        for (var i = 0; i < items.length; i++) {\n          if (items[i].webkitGetAsEntry && items[i].webkitGetAsEntry() && items[i].webkitGetAsEntry().isDirectory) {\n            var entry = items[i].webkitGetAsEntry();\n            if (entry.isDirectory && !allowDir) {\n              continue;\n            }\n            if (entry != null) {\n              promises.push(traverseFileTree(entry));\n            }\n          } else {\n            var f = items[i].getAsFile();\n            if (f != null) {\n              files.push(f);\n              totalSize += f.size;\n            }\n          }\n          if (files.length > maxFiles || totalSize > maxTotalSize ||\n            (!multiple && files.length > 0)) break;\n        }\n      } else {\n        if (fileList != null) {\n          for (var j = 0; j < fileList.length; j++) {\n            var file = fileList.item(j);\n            if (file.type || file.size > 0) {\n              files.push(file);\n              totalSize += file.size;\n            }\n            if (files.length > maxFiles || totalSize > maxTotalSize ||\n              (!multiple && files.length > 0)) break;\n          }\n        }\n      }\n\n      var defer = $q.defer();\n      $q.all(promises).then(function () {\n        if (!multiple && !includeDir && files.length) {\n          var i = 0;\n          while (files[i] && files[i].type === 'directory') i++;\n          defer.resolve([files[i]]);\n        } else {\n          defer.resolve(files);\n        }\n      }, function (e) {\n        defer.reject(e);\n      });\n\n      return defer.promise;\n    }\n  }\n\n  function dropAvailable() {\n    var div = document.createElement('div');\n    return ('draggable' in div) && ('ondrop' in div) && !/Edge\\/12./i.test(navigator.userAgent);\n  }\n\n})();\n\n// customized version of https://github.com/exif-js/exif-js\nngFileUpload.service('UploadExif', ['UploadResize', '$q', function (UploadResize, $q) {\n  var upload = UploadResize;\n\n  upload.isExifSupported = function () {\n    return window.FileReader && new FileReader().readAsArrayBuffer && upload.isResizeSupported();\n  };\n\n  function applyTransform(ctx, orientation, width, height) {\n    switch (orientation) {\n      case 2:\n        return ctx.transform(-1, 0, 0, 1, width, 0);\n      case 3:\n        return ctx.transform(-1, 0, 0, -1, width, height);\n      case 4:\n        return ctx.transform(1, 0, 0, -1, 0, height);\n      case 5:\n        return ctx.transform(0, 1, 1, 0, 0, 0);\n      case 6:\n        return ctx.transform(0, 1, -1, 0, height, 0);\n      case 7:\n        return ctx.transform(0, -1, -1, 0, height, width);\n      case 8:\n        return ctx.transform(0, -1, 1, 0, 0, width);\n    }\n  }\n\n  upload.readOrientation = function (file) {\n    var defer = $q.defer();\n    var reader = new FileReader();\n    var slicedFile = file.slice ? file.slice(0, 64 * 1024) : file;\n    reader.readAsArrayBuffer(slicedFile);\n    reader.onerror = function (e) {\n      return defer.reject(e);\n    };\n    reader.onload = function (e) {\n      var result = {orientation: 1};\n      var view = new DataView(this.result);\n      if (view.getUint16(0, false) !== 0xFFD8) return defer.resolve(result);\n\n      var length = view.byteLength,\n        offset = 2;\n      while (offset < length) {\n        var marker = view.getUint16(offset, false);\n        offset += 2;\n        if (marker === 0xFFE1) {\n          if (view.getUint32(offset += 2, false) !== 0x45786966) return defer.resolve(result);\n\n          var little = view.getUint16(offset += 6, false) === 0x4949;\n          offset += view.getUint32(offset + 4, little);\n          var tags = view.getUint16(offset, little);\n          offset += 2;\n          for (var i = 0; i < tags; i++)\n            if (view.getUint16(offset + (i * 12), little) === 0x0112) {\n              var orientation = view.getUint16(offset + (i * 12) + 8, little);\n              if (orientation >= 2 && orientation <= 8) {\n                view.setUint16(offset + (i * 12) + 8, 1, little);\n                result.fixedArrayBuffer = e.target.result;\n              }\n              result.orientation = orientation;\n              return defer.resolve(result);\n            }\n        } else if ((marker & 0xFF00) !== 0xFF00) break;\n        else offset += view.getUint16(offset, false);\n      }\n      return defer.resolve(result);\n    };\n    return defer.promise;\n  };\n\n  function arrayBufferToBase64(buffer) {\n    var binary = '';\n    var bytes = new Uint8Array(buffer);\n    var len = bytes.byteLength;\n    for (var i = 0; i < len; i++) {\n      binary += String.fromCharCode(bytes[i]);\n    }\n    return window.btoa(binary);\n  }\n\n  upload.applyExifRotation = function (file) {\n    if (file.type.indexOf('image/jpeg') !== 0) {\n      return upload.emptyPromise(file);\n    }\n\n    var deferred = $q.defer();\n    upload.readOrientation(file).then(function (result) {\n      if (result.orientation < 2 || result.orientation > 8) {\n        return deferred.resolve(file);\n      }\n      upload.dataUrl(file, true).then(function (url) {\n        var canvas = document.createElement('canvas');\n        var img = document.createElement('img');\n\n        img.onload = function () {\n          try {\n            canvas.width = result.orientation > 4 ? img.height : img.width;\n            canvas.height = result.orientation > 4 ? img.width : img.height;\n            var ctx = canvas.getContext('2d');\n            applyTransform(ctx, result.orientation, img.width, img.height);\n            ctx.drawImage(img, 0, 0);\n            var dataUrl = canvas.toDataURL(file.type || 'image/WebP', 0.934);\n            dataUrl = upload.restoreExif(arrayBufferToBase64(result.fixedArrayBuffer), dataUrl);\n            var blob = upload.dataUrltoBlob(dataUrl, file.name);\n            deferred.resolve(blob);\n          } catch (e) {\n            return deferred.reject(e);\n          }\n        };\n        img.onerror = function () {\n          deferred.reject();\n        };\n        img.src = url;\n      }, function (e) {\n        deferred.reject(e);\n      });\n    }, function (e) {\n      deferred.reject(e);\n    });\n    return deferred.promise;\n  };\n\n  upload.restoreExif = function (orig, resized) {\n    var ExifRestorer = {};\n\n    ExifRestorer.KEY_STR = 'ABCDEFGHIJKLMNOP' +\n      'QRSTUVWXYZabcdef' +\n      'ghijklmnopqrstuv' +\n      'wxyz0123456789+/' +\n      '=';\n\n    ExifRestorer.encode64 = function (input) {\n      var output = '',\n        chr1, chr2, chr3 = '',\n        enc1, enc2, enc3, enc4 = '',\n        i = 0;\n\n      do {\n        chr1 = input[i++];\n        chr2 = input[i++];\n        chr3 = input[i++];\n\n        enc1 = chr1 >> 2;\n        enc2 = ((chr1 & 3) << 4) | (chr2 >> 4);\n        enc3 = ((chr2 & 15) << 2) | (chr3 >> 6);\n        enc4 = chr3 & 63;\n\n        if (isNaN(chr2)) {\n          enc3 = enc4 = 64;\n        } else if (isNaN(chr3)) {\n          enc4 = 64;\n        }\n\n        output = output +\n          this.KEY_STR.charAt(enc1) +\n          this.KEY_STR.charAt(enc2) +\n          this.KEY_STR.charAt(enc3) +\n          this.KEY_STR.charAt(enc4);\n        chr1 = chr2 = chr3 = '';\n        enc1 = enc2 = enc3 = enc4 = '';\n      } while (i < input.length);\n\n      return output;\n    };\n\n    ExifRestorer.restore = function (origFileBase64, resizedFileBase64) {\n      if (origFileBase64.match('data:image/jpeg;base64,')) {\n        origFileBase64 = origFileBase64.replace('data:image/jpeg;base64,', '');\n      }\n\n      var rawImage = this.decode64(origFileBase64);\n      var segments = this.slice2Segments(rawImage);\n\n      var image = this.exifManipulation(resizedFileBase64, segments);\n\n      return 'data:image/jpeg;base64,' + this.encode64(image);\n    };\n\n\n    ExifRestorer.exifManipulation = function (resizedFileBase64, segments) {\n      var exifArray = this.getExifArray(segments),\n        newImageArray = this.insertExif(resizedFileBase64, exifArray);\n      return new Uint8Array(newImageArray);\n    };\n\n\n    ExifRestorer.getExifArray = function (segments) {\n      var seg;\n      for (var x = 0; x < segments.length; x++) {\n        seg = segments[x];\n        if (seg[0] === 255 & seg[1] === 225) //(ff e1)\n        {\n          return seg;\n        }\n      }\n      return [];\n    };\n\n\n    ExifRestorer.insertExif = function (resizedFileBase64, exifArray) {\n      var imageData = resizedFileBase64.replace('data:image/jpeg;base64,', ''),\n        buf = this.decode64(imageData),\n        separatePoint = buf.indexOf(255, 3),\n        mae = buf.slice(0, separatePoint),\n        ato = buf.slice(separatePoint),\n        array = mae;\n\n      array = array.concat(exifArray);\n      array = array.concat(ato);\n      return array;\n    };\n\n\n    ExifRestorer.slice2Segments = function (rawImageArray) {\n      var head = 0,\n        segments = [];\n\n      while (1) {\n        if (rawImageArray[head] === 255 & rawImageArray[head + 1] === 218) {\n          break;\n        }\n        if (rawImageArray[head] === 255 & rawImageArray[head + 1] === 216) {\n          head += 2;\n        }\n        else {\n          var length = rawImageArray[head + 2] * 256 + rawImageArray[head + 3],\n            endPoint = head + length + 2,\n            seg = rawImageArray.slice(head, endPoint);\n          segments.push(seg);\n          head = endPoint;\n        }\n        if (head > rawImageArray.length) {\n          break;\n        }\n      }\n\n      return segments;\n    };\n\n\n    ExifRestorer.decode64 = function (input) {\n      var chr1, chr2, chr3 = '',\n        enc1, enc2, enc3, enc4 = '',\n        i = 0,\n        buf = [];\n\n      // remove all characters that are not A-Z, a-z, 0-9, +, /, or =\n      var base64test = /[^A-Za-z0-9\\+\\/\\=]/g;\n      if (base64test.exec(input)) {\n        console.log('There were invalid base64 characters in the input text.\\n' +\n          'Valid base64 characters are A-Z, a-z, 0-9, ' + ', ' / ',and \"=\"\\n' +\n          'Expect errors in decoding.');\n      }\n      input = input.replace(/[^A-Za-z0-9\\+\\/\\=]/g, '');\n\n      do {\n        enc1 = this.KEY_STR.indexOf(input.charAt(i++));\n        enc2 = this.KEY_STR.indexOf(input.charAt(i++));\n        enc3 = this.KEY_STR.indexOf(input.charAt(i++));\n        enc4 = this.KEY_STR.indexOf(input.charAt(i++));\n\n        chr1 = (enc1 << 2) | (enc2 >> 4);\n        chr2 = ((enc2 & 15) << 4) | (enc3 >> 2);\n        chr3 = ((enc3 & 3) << 6) | enc4;\n\n        buf.push(chr1);\n\n        if (enc3 !== 64) {\n          buf.push(chr2);\n        }\n        if (enc4 !== 64) {\n          buf.push(chr3);\n        }\n\n        chr1 = chr2 = chr3 = '';\n        enc1 = enc2 = enc3 = enc4 = '';\n\n      } while (i < input.length);\n\n      return buf;\n    };\n\n    return ExifRestorer.restore(orig, resized);  //<= EXIF\n  };\n\n  return upload;\n}]);\n\n","require('./dist/ng-file-upload-all');\nmodule.exports = 'ngFileUpload';","/*!\n * angular-translate - v2.19.1 - 2024-01-21\n * \n * Copyright (c) 2024 The angular-translate team, Pascal Precht; Licensed MIT\n */\n(function (root, factory) {\n  if (typeof define === 'function' && define.amd) {\n    // AMD. Register as an anonymous module unless amdModuleId is set\n    define([], function () {\n      return (factory());\n    });\n  } else if (typeof module === 'object' && module.exports) {\n    // Node. Does not work with strict CommonJS, but\n    // only CommonJS-like environments that support module.exports,\n    // like Node.\n    module.exports = factory();\n  } else {\n    factory();\n  }\n}(this, function () {\n\n/**\n * @ngdoc overview\n * @name pascalprecht.translate\n *\n * @description\n * The main module which holds everything together.\n */\nrunTranslate.$inject = ['$translate'];\n$translate.$inject = ['$STORAGE_KEY', '$windowProvider', '$translateSanitizationProvider', 'pascalprechtTranslateOverrider'];\n$translateDefaultInterpolation.$inject = ['$interpolate', '$translateSanitization'];\ntranslateDirective.$inject = ['$translate', '$interpolate', '$compile', '$parse', '$rootScope'];\ntranslateAttrDirective.$inject = ['$translate', '$rootScope'];\ntranslateCloakDirective.$inject = ['$translate', '$rootScope'];\ntranslateFilterFactory.$inject = ['$parse', '$translate'];\n$translationCache.$inject = ['$cacheFactory'];\nangular.module('pascalprecht.translate', ['ng'])\n  .run(runTranslate);\n\nfunction runTranslate($translate) {\n\n  'use strict';\n\n  var key = $translate.storageKey(),\n    storage = $translate.storage();\n\n  var fallbackFromIncorrectStorageValue = function () {\n    var preferred = $translate.preferredLanguage();\n    if (angular.isString(preferred)) {\n      $translate.use(preferred);\n      // $translate.use() will also remember the language.\n      // So, we don't need to call storage.put() here.\n    } else {\n      storage.put(key, $translate.use());\n    }\n  };\n\n  fallbackFromIncorrectStorageValue.displayName = 'fallbackFromIncorrectStorageValue';\n\n  if (storage) {\n    if (!storage.get(key)) {\n      fallbackFromIncorrectStorageValue();\n    } else {\n      $translate.use(storage.get(key))['catch'](fallbackFromIncorrectStorageValue);\n    }\n  } else if (angular.isString($translate.preferredLanguage())) {\n    $translate.use($translate.preferredLanguage());\n  }\n}\n\nrunTranslate.displayName = 'runTranslate';\n\n/**\n * @ngdoc object\n * @name pascalprecht.translate.$translateSanitizationProvider\n *\n * @description\n *\n * Configurations for $translateSanitization\n */\nangular.module('pascalprecht.translate').provider('$translateSanitization', $translateSanitizationProvider);\n\nfunction $translateSanitizationProvider () {\n\n  'use strict';\n\n  var $sanitize,\n      $sce,\n      currentStrategy = null, // TODO change to either 'sanitize', 'escape' or ['sanitize', 'escapeParameters'] in 3.0.\n      hasConfiguredStrategy = false,\n      hasShownNoStrategyConfiguredWarning = false,\n      strategies;\n\n  /**\n   * Definition of a sanitization strategy function\n   * @callback StrategyFunction\n   * @param {string|object} value - value to be sanitized (either a string or an interpolated value map)\n   * @param {string} mode - either 'text' for a string (translation) or 'params' for the interpolated params\n   * @return {string|object}\n   */\n\n  /**\n   * @ngdoc property\n   * @name strategies\n   * @propertyOf pascalprecht.translate.$translateSanitizationProvider\n   *\n   * @description\n   * Following strategies are built-in:\n   * <dl>\n   *   <dt>sanitize</dt>\n   *   <dd>Sanitizes HTML in the translation text using $sanitize</dd>\n   *   <dt>escape</dt>\n   *   <dd>Escapes HTML in the translation</dd>\n   *   <dt>sanitizeParameters</dt>\n   *   <dd>Sanitizes HTML in the values of the interpolation parameters using $sanitize</dd>\n   *   <dt>escapeParameters</dt>\n   *   <dd>Escapes HTML in the values of the interpolation parameters</dd>\n   *   <dt>escaped</dt>\n   *   <dd>Support legacy strategy name 'escaped' for backwards compatibility (will be removed in 3.0)</dd>\n   * </dl>\n   *\n   */\n\n  strategies = {\n    sanitize: function (value, mode/*, context*/) {\n      if (mode === 'text') {\n        value = htmlSanitizeValue(value);\n      }\n      return value;\n    },\n    escape: function (value, mode/*, context*/) {\n      if (mode === 'text') {\n        value = htmlEscapeValue(value);\n      }\n      return value;\n    },\n    sanitizeParameters: function (value, mode/*, context*/) {\n      if (mode === 'params') {\n        value = mapInterpolationParameters(value, htmlSanitizeValue);\n      }\n      return value;\n    },\n    escapeParameters: function (value, mode/*, context*/) {\n      if (mode === 'params') {\n        value = mapInterpolationParameters(value, htmlEscapeValue);\n      }\n      return value;\n    },\n    sce: function (value, mode, context) {\n      if (mode === 'text') {\n        value = htmlTrustValue(value);\n      } else if (mode === 'params') {\n        if (context !== 'filter') {\n          // do html escape in filter context #1101\n          value = mapInterpolationParameters(value, htmlEscapeValue);\n        }\n      }\n      return value;\n    },\n    sceParameters: function (value, mode/*, context*/) {\n      if (mode === 'params') {\n        value = mapInterpolationParameters(value, htmlTrustValue);\n      }\n      return value;\n    }\n  };\n  // Support legacy strategy name 'escaped' for backwards compatibility.\n  // TODO should be removed in 3.0\n  strategies.escaped = strategies.escapeParameters;\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateSanitizationProvider#addStrategy\n   * @methodOf pascalprecht.translate.$translateSanitizationProvider\n   *\n   * @description\n   * Adds a sanitization strategy to the list of known strategies.\n   *\n   * @param {string} strategyName - unique key for a strategy\n   * @param {StrategyFunction} strategyFunction - strategy function\n   * @returns {object} this\n   */\n  this.addStrategy = function (strategyName, strategyFunction) {\n    strategies[strategyName] = strategyFunction;\n    return this;\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateSanitizationProvider#removeStrategy\n   * @methodOf pascalprecht.translate.$translateSanitizationProvider\n   *\n   * @description\n   * Removes a sanitization strategy from the list of known strategies.\n   *\n   * @param {string} strategyName - unique key for a strategy\n   * @returns {object} this\n   */\n  this.removeStrategy = function (strategyName) {\n    delete strategies[strategyName];\n    return this;\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateSanitizationProvider#useStrategy\n   * @methodOf pascalprecht.translate.$translateSanitizationProvider\n   *\n   * @description\n   * Selects a sanitization strategy. When an array is provided the strategies will be executed in order.\n   *\n   * @param {string|StrategyFunction|array} strategy The sanitization strategy / strategies which should be used. Either a name of an existing strategy, a custom strategy function, or an array consisting of multiple names and / or custom functions.\n   * @returns {object} this\n   */\n  this.useStrategy = function (strategy) {\n    hasConfiguredStrategy = true;\n    currentStrategy = strategy;\n    return this;\n  };\n\n  /**\n   * @ngdoc object\n   * @name pascalprecht.translate.$translateSanitization\n   * @requires $injector\n   * @requires $log\n   *\n   * @description\n   * Sanitizes interpolation parameters and translated texts.\n   *\n   */\n  this.$get = ['$injector', '$log', function ($injector, $log) {\n\n    var cachedStrategyMap = {};\n\n    var applyStrategies = function (value, mode, context, selectedStrategies) {\n      angular.forEach(selectedStrategies, function (selectedStrategy) {\n        if (angular.isFunction(selectedStrategy)) {\n          value = selectedStrategy(value, mode, context);\n        } else if (angular.isFunction(strategies[selectedStrategy])) {\n          value = strategies[selectedStrategy](value, mode, context);\n        } else if (angular.isString(strategies[selectedStrategy])) {\n          if (!cachedStrategyMap[strategies[selectedStrategy]]) {\n            try {\n              cachedStrategyMap[strategies[selectedStrategy]] = $injector.get(strategies[selectedStrategy]);\n            } catch (e) {\n              cachedStrategyMap[strategies[selectedStrategy]] = function() {};\n              throw new Error('pascalprecht.translate.$translateSanitization: Unknown sanitization strategy: \\'' + selectedStrategy + '\\'');\n            }\n          }\n          value = cachedStrategyMap[strategies[selectedStrategy]](value, mode, context);\n        } else {\n          throw new Error('pascalprecht.translate.$translateSanitization: Unknown sanitization strategy: \\'' + selectedStrategy + '\\'');\n        }\n      });\n      return value;\n    };\n\n    // TODO: should be removed in 3.0\n    var showNoStrategyConfiguredWarning = function () {\n      if (!hasConfiguredStrategy && !hasShownNoStrategyConfiguredWarning) {\n        $log.warn('pascalprecht.translate.$translateSanitization: No sanitization strategy has been configured. This can have serious security implications. See http://angular-translate.github.io/docs/#/guide/19_security for details.');\n        hasShownNoStrategyConfiguredWarning = true;\n      }\n    };\n\n    if ($injector.has('$sanitize')) {\n      $sanitize = $injector.get('$sanitize');\n    }\n    if ($injector.has('$sce')) {\n      $sce = $injector.get('$sce');\n    }\n\n    return {\n      /**\n       * @ngdoc function\n       * @name pascalprecht.translate.$translateSanitization#useStrategy\n       * @methodOf pascalprecht.translate.$translateSanitization\n       *\n       * @description\n       * Selects a sanitization strategy. When an array is provided the strategies will be executed in order.\n       *\n       * @param {string|StrategyFunction|array} strategy The sanitization strategy / strategies which should be used. Either a name of an existing strategy, a custom strategy function, or an array consisting of multiple names and / or custom functions.\n       */\n      useStrategy: (function (self) {\n        return function (strategy) {\n          self.useStrategy(strategy);\n        };\n      })(this),\n\n      /**\n       * @ngdoc function\n       * @name pascalprecht.translate.$translateSanitization#sanitize\n       * @methodOf pascalprecht.translate.$translateSanitization\n       *\n       * @description\n       * Sanitizes a value.\n       *\n       * @param {string|object} value The value which should be sanitized.\n       * @param {string} mode The current sanitization mode, either 'params' or 'text'.\n       * @param {string|StrategyFunction|array} [strategy] Optional custom strategy which should be used instead of the currently selected strategy.\n       * @param {string} [context] The context of this call: filter, service. Default is service\n       * @returns {string|object} sanitized value\n       */\n      sanitize: function (value, mode, strategy, context) {\n        if (!currentStrategy) {\n          showNoStrategyConfiguredWarning();\n        }\n\n        if (!strategy && strategy !== null) {\n          strategy = currentStrategy;\n        }\n\n        if (!strategy) {\n          return value;\n        }\n\n        if (!context) {\n          context = 'service';\n        }\n\n        var selectedStrategies = angular.isArray(strategy) ? strategy : [strategy];\n        return applyStrategies(value, mode, context, selectedStrategies);\n      }\n    };\n  }];\n\n  var htmlEscapeValue = function (value) {\n    var element = angular.element('<div></div>');\n    element.text(value); // not chainable, see #1044\n    return element.html();\n  };\n\n  var htmlSanitizeValue = function (value) {\n    if (!$sanitize) {\n      throw new Error('pascalprecht.translate.$translateSanitization: Error cannot find $sanitize service. Either include the ngSanitize module (https://docs.angularjs.org/api/ngSanitize) or use a sanitization strategy which does not depend on $sanitize, such as \\'escape\\'.');\n    }\n    return $sanitize(value);\n  };\n\n  var htmlTrustValue = function (value) {\n    if (!$sce) {\n      throw new Error('pascalprecht.translate.$translateSanitization: Error cannot find $sce service.');\n    }\n    return $sce.trustAsHtml(value);\n  };\n\n  var mapInterpolationParameters = function (value, iteratee, stack) {\n    if (angular.isDate(value)) {\n      return value;\n    } else if (angular.isObject(value)) {\n      var result = angular.isArray(value) ? [] : {};\n\n      if (!stack) {\n        stack = [];\n      } else {\n        if (stack.indexOf(value) > -1) {\n          throw new Error('pascalprecht.translate.$translateSanitization: Error cannot interpolate parameter due recursive object');\n        }\n      }\n\n      stack.push(value);\n      angular.forEach(value, function (propertyValue, propertyKey) {\n\n        /* Skipping function properties. */\n        if (angular.isFunction(propertyValue)) {\n          return;\n        }\n\n        result[propertyKey] = mapInterpolationParameters(propertyValue, iteratee, stack);\n      });\n      stack.splice(-1, 1); // remove last\n\n      return result;\n    } else if (angular.isNumber(value)) {\n      return value;\n    } else if (value === true || value === false) {\n      return value;\n    } else if (!angular.isUndefined(value) && value !== null) {\n      return iteratee(value);\n    } else {\n      return value;\n    }\n  };\n}\n\n/**\n * @ngdoc object\n * @name pascalprecht.translate.$translateProvider\n * @description\n *\n * $translateProvider allows developers to register translation-tables, asynchronous loaders\n * and similar to configure translation behavior directly inside of a module.\n *\n */\nangular.module('pascalprecht.translate')\n  .constant('pascalprechtTranslateOverrider', {})\n  .provider('$translate', $translate);\n\nfunction $translate($STORAGE_KEY, $windowProvider, $translateSanitizationProvider, pascalprechtTranslateOverrider) {\n\n  'use strict';\n\n  var $translationTable = {},\n    $preferredLanguage,\n    $availableLanguageKeys = [],\n    $languageKeyAliases,\n    $fallbackLanguage,\n    $fallbackWasString,\n    $uses,\n    $nextLang,\n    $storageFactory,\n    $storageKey = $STORAGE_KEY,\n    $storagePrefix,\n    $missingTranslationHandlerFactory,\n    $interpolationFactory,\n    $interpolatorFactories = [],\n    $loaderFactory,\n    $cloakClassName = 'translate-cloak',\n    $loaderOptions,\n    $notFoundIndicatorLeft,\n    $notFoundIndicatorRight,\n    $postCompilingEnabled = false,\n    $forceAsyncReloadEnabled = false,\n    $allowNamespaces = true,\n    $nestedObjectDelimeter = '.',\n    $isReady = false,\n    $keepContent = false,\n    loaderCache,\n    directivePriority = 0,\n    statefulFilter = true,\n    postProcessFn,\n    uniformLanguageTagResolver = 'default',\n    languageTagResolver = {\n      'default' : function (tag) {\n        return (tag || '').split('-').join('_');\n      },\n      java : function (tag) {\n        var temp = (tag || '').split('-').join('_');\n        var parts = temp.split('_');\n        return parts.length > 1 ? (parts[0].toLowerCase() + '_' + parts[1].toUpperCase()) : temp;\n      },\n      bcp47 : function (tag) {\n        var temp = (tag || '').split('_').join('-');\n        var parts = temp.split('-');\n\n        switch (parts.length) {\n          case 1: // language only\n            parts[0] = parts[0].toLowerCase();\n            break;\n          case 2: // language-script or language-region\n            parts[0] = parts[0].toLowerCase();\n            if (parts[1].length === 4) { // parts[1] is script\n              parts[1] = parts[1].charAt(0).toUpperCase() + parts[1].slice(1).toLowerCase();\n            } else { // parts[1] is region\n              parts[1] = parts[1].toUpperCase();\n            }\n            break;\n          case 3: // language-script-region\n            parts[0] = parts[0].toLowerCase();\n            parts[1] = parts[1].charAt(0).toUpperCase() + parts[1].slice(1).toLowerCase();\n            parts[2] = parts[2].toUpperCase();\n            break;\n          default:\n            return temp;\n        }\n\n        return parts.join('-');\n      },\n      'iso639-1' : function (tag) {\n        var temp = (tag || '').split('_').join('-');\n        var parts = temp.split('-');\n        return parts[0].toLowerCase();\n      }\n    };\n\n  var version = '2.19.1';\n\n  // tries to determine the browsers language\n  var getFirstBrowserLanguage = function () {\n\n    // internal purpose only\n    if (angular.isFunction(pascalprechtTranslateOverrider.getLocale)) {\n      return pascalprechtTranslateOverrider.getLocale();\n    }\n\n    var nav = $windowProvider.$get().navigator,\n      browserLanguagePropertyKeys = ['language', 'browserLanguage', 'systemLanguage', 'userLanguage'],\n      i,\n      language;\n\n    // support for HTML 5.1 \"navigator.languages\"\n    if (angular.isArray(nav.languages)) {\n      for (i = 0; i < nav.languages.length; i++) {\n        language = nav.languages[i];\n        if (language && language.length) {\n          return language;\n        }\n      }\n    }\n\n    // support for other well known properties in browsers\n    for (i = 0; i < browserLanguagePropertyKeys.length; i++) {\n      language = nav[browserLanguagePropertyKeys[i]];\n      if (language && language.length) {\n        return language;\n      }\n    }\n\n    return null;\n  };\n  getFirstBrowserLanguage.displayName = 'angular-translate/service: getFirstBrowserLanguage';\n\n  // tries to determine the browsers locale\n  var getLocale = function () {\n    var locale = getFirstBrowserLanguage() || '';\n    if (languageTagResolver[uniformLanguageTagResolver]) {\n      locale = languageTagResolver[uniformLanguageTagResolver](locale);\n    }\n    return locale;\n  };\n  getLocale.displayName = 'angular-translate/service: getLocale';\n\n  /**\n   * @name indexOf\n   * @private\n   *\n   * @description\n   * indexOf polyfill. Kinda sorta.\n   *\n   * @param {array} array Array to search in.\n   * @param {string} searchElement Element to search for.\n   *\n   * @returns {int} Index of search element.\n   */\n  var indexOf = function (array, searchElement) {\n    for (var i = 0, len = array.length; i < len; i++) {\n      if (array[i] === searchElement) {\n        return i;\n      }\n    }\n    return -1;\n  };\n\n  /**\n   * @name trim\n   * @private\n   *\n   * @description\n   * trim polyfill\n   *\n   * @returns {string} The string stripped of whitespace from both ends\n   */\n  var trim = function () {\n    return this.toString().replace(/^\\s+|\\s+$/g, '');\n  };\n\n  /**\n   * @name lowercase\n   * @private\n   *\n   * @description\n   * Return the lowercase string only if the type is string\n   *\n   * @returns {string} The string all in lowercase\n   */\n  var lowercase = function (string) {\n    return angular.isString(string) ? string.toLowerCase() : string;\n  };\n\n  var negotiateLocale = function (preferred) {\n    if (!preferred) {\n      return;\n    }\n\n    var avail = [],\n      locale = lowercase(preferred),\n      i = 0,\n      n = $availableLanguageKeys.length;\n\n    for (; i < n; i++) {\n      avail.push(lowercase($availableLanguageKeys[i]));\n    }\n\n    // Check for an exact match in our list of available keys\n    i = indexOf(avail, locale);\n    if (i > -1) {\n      return $availableLanguageKeys[i];\n    }\n\n    if ($languageKeyAliases) {\n      var alias;\n      for (var langKeyAlias in $languageKeyAliases) {\n        if ($languageKeyAliases.hasOwnProperty(langKeyAlias)) {\n          var hasWildcardKey = false;\n          var hasExactKey = Object.prototype.hasOwnProperty.call($languageKeyAliases, langKeyAlias) &&\n            lowercase(langKeyAlias) === lowercase(preferred);\n\n          if (langKeyAlias.slice(-1) === '*') {\n            hasWildcardKey = lowercase(langKeyAlias.slice(0, -1)) === lowercase(preferred.slice(0, langKeyAlias.length - 1));\n          }\n          if (hasExactKey || hasWildcardKey) {\n            alias = $languageKeyAliases[langKeyAlias];\n            if (indexOf(avail, lowercase(alias)) > -1) {\n              return alias;\n            }\n          }\n        }\n      }\n    }\n\n    // Check for a language code without region\n    var parts = preferred.split('_');\n\n    if (parts.length > 1 && indexOf(avail, lowercase(parts[0])) > -1) {\n      return parts[0];\n    }\n\n    // If everything fails, return undefined.\n    return;\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#translations\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Registers a new translation table for specific language key.\n   *\n   * To register a translation table for specific language, pass a defined language\n   * key as first parameter.\n   *\n   * <pre>\n   *  // register translation table for language: 'de_DE'\n   *  $translateProvider.translations('de_DE', {\n   *    'GREETING': 'Hallo Welt!'\n   *  });\n   *\n   *  // register another one\n   *  $translateProvider.translations('en_US', {\n   *    'GREETING': 'Hello world!'\n   *  });\n   * </pre>\n   *\n   * When registering multiple translation tables for for the same language key,\n   * the actual translation table gets extended. This allows you to define module\n   * specific translation which only get added, once a specific module is loaded in\n   * your app.\n   *\n   * Invoking this method with no arguments returns the translation table which was\n   * registered with no language key. Invoking it with a language key returns the\n   * related translation table.\n   *\n   * @param {string} langKey A language key.\n   * @param {object} translationTable A plain old JavaScript object that represents a translation table.\n   *\n   */\n  var translations = function (langKey, translationTable) {\n\n    if (!langKey && !translationTable) {\n      return $translationTable;\n    }\n\n    if (langKey && !translationTable) {\n      if (angular.isString(langKey)) {\n        return $translationTable[langKey];\n      }\n    } else {\n      if (!angular.isObject($translationTable[langKey])) {\n        $translationTable[langKey] = {};\n      }\n      angular.extend($translationTable[langKey], flatObject(translationTable));\n    }\n    return this;\n  };\n\n  this.translations = translations;\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#cloakClassName\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   *\n   * Let's you change the class name for `translate-cloak` directive.\n   * Default class name is `translate-cloak`.\n   *\n   * @param {string} name translate-cloak class name\n   */\n  this.cloakClassName = function (name) {\n    if (!name) {\n      return $cloakClassName;\n    }\n    $cloakClassName = name;\n    return this;\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#allowNamespaces\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Let's you disable namespaces, if you don't need nested translation\n   * object files. Disabling namespaces can improve performance.\n   *\n   * Default value is `true`. Namespaces are enabled by default.\n   *\n   * @param {boolean} namespacesEnabled - namespaces are enabled or not\n   */\n  this.allowNamespaces = function (namespacesEnabled) {\n    if (namespacesEnabled === undefined) {\n      return $allowNamespaces;\n    }\n    $allowNamespaces = namespacesEnabled;\n    return this;\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#nestedObjectDelimeter\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   *\n   * Let's you change the delimiter for namespaced translations.\n   * Default delimiter is `.`.\n   *\n   * @param {string} delimiter namespace separator\n   */\n  this.nestedObjectDelimeter = function (delimiter) {\n    if (!delimiter) {\n      return $nestedObjectDelimeter;\n    }\n    $nestedObjectDelimeter = delimiter;\n    return this;\n  };\n\n  /**\n   * @name flatObject\n   * @private\n   *\n   * @description\n   * Flats an object. This function is used to flatten given translation data with\n   * namespaces, so they are later accessible via dot notation.\n   */\n  var flatObject = function (data, path, result, prevKey) {\n    var key, keyWithPath, keyWithShortPath, val;\n\n    if (!path) {\n      path = [];\n    }\n    if (!result) {\n      result = {};\n    }\n    if (!$allowNamespaces) {\n      return data;\n    }\n    for (key in data) {\n      if (!Object.prototype.hasOwnProperty.call(data, key)) {\n        continue;\n      }\n      val = data[key];\n      if (angular.isObject(val)) {\n        flatObject(val, path.concat(key), result, key);\n      } else {\n        keyWithPath = path.length ? ('' + path.join($nestedObjectDelimeter) + $nestedObjectDelimeter + key) : key;\n        if (path.length && key === prevKey) {\n          // Create shortcut path (foo.bar == foo.bar.bar)\n          keyWithShortPath = '' + path.join($nestedObjectDelimeter);\n          // Link it to original path\n          result[keyWithShortPath] = '@:' + keyWithPath;\n        }\n        result[keyWithPath] = val;\n      }\n    }\n    return result;\n  };\n  flatObject.displayName = 'flatObject';\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#addInterpolation\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Adds interpolation services to angular-translate, so it can manage them.\n   *\n   * @param {object} factory Interpolation service factory\n   */\n  this.addInterpolation = function (factory) {\n    $interpolatorFactories.push(factory);\n    return this;\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#useMessageFormatInterpolation\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Tells angular-translate to use interpolation functionality of messageformat.js.\n   * This is useful when having high level pluralization and gender selection.\n   */\n  this.useMessageFormatInterpolation = function () {\n    return this.useInterpolation('$translateMessageFormatInterpolation');\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#useInterpolation\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Tells angular-translate which interpolation style to use as default, application-wide.\n   * Simply pass a factory/service name. The interpolation service has to implement\n   * the correct interface.\n   *\n   * @param {string} factory Interpolation service name.\n   */\n  this.useInterpolation = function (factory) {\n    $interpolationFactory = factory;\n    return this;\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#useSanitizeStrategy\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Simply sets a sanitation strategy type.\n   *\n   * @param {string} value Strategy type.\n   */\n  this.useSanitizeValueStrategy = function (value) {\n    $translateSanitizationProvider.useStrategy(value);\n    return this;\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#preferredLanguage\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Tells the module which of the registered translation tables to use for translation\n   * at initial startup by passing a language key. Similar to `$translateProvider#use`\n   * only that it says which language to **prefer**.\n   * It is recommended to call this after {@link pascalprecht.translate.$translate#fallbackLanguage fallbackLanguage()}.\n   *\n   * @param {string} langKey A language key.\n   */\n  this.preferredLanguage = function (langKey) {\n    if (langKey) {\n      setupPreferredLanguage(langKey);\n      return this;\n    }\n    return $preferredLanguage;\n  };\n  var setupPreferredLanguage = function (langKey) {\n    if (langKey) {\n      $preferredLanguage = langKey;\n    }\n    return $preferredLanguage;\n  };\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#translationNotFoundIndicator\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Sets an indicator which is used when a translation isn't found. E.g. when\n   * setting the indicator as 'X' and one tries to translate a translation id\n   * called `NOT_FOUND`, this will result in `X NOT_FOUND X`.\n   *\n   * Internally this methods sets a left indicator and a right indicator using\n   * `$translateProvider.translationNotFoundIndicatorLeft()` and\n   * `$translateProvider.translationNotFoundIndicatorRight()`.\n   *\n   * **Note**: These methods automatically add a whitespace between the indicators\n   * and the translation id.\n   *\n   * @param {string} indicator An indicator, could be any string.\n   */\n  this.translationNotFoundIndicator = function (indicator) {\n    this.translationNotFoundIndicatorLeft(indicator);\n    this.translationNotFoundIndicatorRight(indicator);\n    return this;\n  };\n\n  /**\n   * ngdoc function\n   * @name pascalprecht.translate.$translateProvider#translationNotFoundIndicatorLeft\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Sets an indicator which is used when a translation isn't found left to the\n   * translation id.\n   *\n   * @param {string} indicator An indicator.\n   */\n  this.translationNotFoundIndicatorLeft = function (indicator) {\n    if (!indicator) {\n      return $notFoundIndicatorLeft;\n    }\n    $notFoundIndicatorLeft = indicator;\n    return this;\n  };\n\n  /**\n   * ngdoc function\n   * @name pascalprecht.translate.$translateProvider#translationNotFoundIndicatorLeft\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Sets an indicator which is used when a translation isn't found right to the\n   * translation id.\n   *\n   * @param {string} indicator An indicator.\n   */\n  this.translationNotFoundIndicatorRight = function (indicator) {\n    if (!indicator) {\n      return $notFoundIndicatorRight;\n    }\n    $notFoundIndicatorRight = indicator;\n    return this;\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#fallbackLanguage\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Tells the module which of the registered translation tables to use when missing translations\n   * at initial startup by passing a language key. Similar to `$translateProvider#use`\n   * only that it says which language to **fallback**.\n   *\n   * @param {string||array} langKey A language key.\n   *\n   */\n  this.fallbackLanguage = function (langKey) {\n    fallbackStack(langKey);\n    return this;\n  };\n\n  var fallbackStack = function (langKey) {\n    if (langKey) {\n      if (angular.isString(langKey)) {\n        $fallbackWasString = true;\n        $fallbackLanguage = [langKey];\n      } else if (angular.isArray(langKey)) {\n        $fallbackWasString = false;\n        $fallbackLanguage = langKey;\n      }\n      if (angular.isString($preferredLanguage) && indexOf($fallbackLanguage, $preferredLanguage) < 0) {\n        $fallbackLanguage.push($preferredLanguage);\n      }\n\n      return this;\n    } else {\n      if ($fallbackWasString) {\n        return $fallbackLanguage[0];\n      } else {\n        return $fallbackLanguage;\n      }\n    }\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#use\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Set which translation table to use for translation by given language key. When\n   * trying to 'use' a language which isn't provided, it'll throw an error.\n   *\n   * You actually don't have to use this method since `$translateProvider#preferredLanguage`\n   * does the job too.\n   *\n   * @param {string} langKey A language key.\n   */\n  this.use = function (langKey) {\n    if (langKey) {\n      if (!$translationTable[langKey] && (!$loaderFactory)) {\n        // only throw an error, when not loading translation data asynchronously\n        throw new Error('$translateProvider couldn\\'t find translationTable for langKey: \\'' + langKey + '\\'');\n      }\n      $uses = langKey;\n      return this;\n    }\n    return $uses;\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#resolveClientLocale\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * This returns the current browser/client's language key. The result is processed with the configured uniform tag resolver.\n   *\n   * @returns {string} the current client/browser language key\n   */\n  this.resolveClientLocale = function () {\n    return getLocale();\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#storageKey\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Tells the module which key must represent the choosed language by a user in the storage.\n   *\n   * @param {string} key A key for the storage.\n   */\n  var storageKey = function (key) {\n    if (!key) {\n      if ($storagePrefix) {\n        return $storagePrefix + $storageKey;\n      }\n      return $storageKey;\n    }\n    $storageKey = key;\n    return this;\n  };\n\n  this.storageKey = storageKey;\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#useUrlLoader\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Tells angular-translate to use `$translateUrlLoader` extension service as loader.\n   *\n   * @param {string} url Url\n   * @param {Object=} options Optional configuration object\n   */\n  this.useUrlLoader = function (url, options) {\n    return this.useLoader('$translateUrlLoader', angular.extend({url : url}, options));\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#useStaticFilesLoader\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Tells angular-translate to use `$translateStaticFilesLoader` extension service as loader.\n   *\n   * @param {Object=} options Optional configuration object\n   */\n  this.useStaticFilesLoader = function (options) {\n    return this.useLoader('$translateStaticFilesLoader', options);\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#useLoader\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Tells angular-translate to use any other service as loader.\n   *\n   * @param {string} loaderFactory Factory name to use\n   * @param {Object=} options Optional configuration object\n   */\n  this.useLoader = function (loaderFactory, options) {\n    $loaderFactory = loaderFactory;\n    $loaderOptions = options || {};\n    return this;\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#useLocalStorage\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Tells angular-translate to use `$translateLocalStorage` service as storage layer.\n   *\n   */\n  this.useLocalStorage = function () {\n    return this.useStorage('$translateLocalStorage');\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#useCookieStorage\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Tells angular-translate to use `$translateCookieStorage` service as storage layer.\n   */\n  this.useCookieStorage = function () {\n    return this.useStorage('$translateCookieStorage');\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#useStorage\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Tells angular-translate to use custom service as storage layer.\n   */\n  this.useStorage = function (storageFactory) {\n    $storageFactory = storageFactory;\n    return this;\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#storagePrefix\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Sets prefix for storage key.\n   *\n   * @param {string} prefix Storage key prefix\n   */\n  this.storagePrefix = function (prefix) {\n    if (!prefix) {\n      return prefix;\n    }\n    $storagePrefix = prefix;\n    return this;\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#useMissingTranslationHandlerLog\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Tells angular-translate to use built-in log handler when trying to translate\n   * a translation Id which doesn't exist.\n   *\n   * This is actually a shortcut method for `useMissingTranslationHandler()`.\n   *\n   */\n  this.useMissingTranslationHandlerLog = function () {\n    return this.useMissingTranslationHandler('$translateMissingTranslationHandlerLog');\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#useMissingTranslationHandler\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Expects a factory name which later gets instantiated with `$injector`.\n   * This method can be used to tell angular-translate to use a custom\n   * missingTranslationHandler. Just build a factory which returns a function\n   * and expects a translation id as argument.\n   *\n   * Example:\n   * <pre>\n   *  app.config(function ($translateProvider) {\n   *    $translateProvider.useMissingTranslationHandler('customHandler');\n   *  });\n   *\n   *  app.factory('customHandler', function (dep1, dep2) {\n   *    return function (translationId) {\n   *      // something with translationId and dep1 and dep2\n   *    };\n   *  });\n   * </pre>\n   *\n   * @param {string} factory Factory name\n   */\n  this.useMissingTranslationHandler = function (factory) {\n    $missingTranslationHandlerFactory = factory;\n    return this;\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#usePostCompiling\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * If post compiling is enabled, all translated values will be processed\n   * again with AngularJS' $compile.\n   *\n   * Example:\n   * <pre>\n   *  app.config(function ($translateProvider) {\n   *    $translateProvider.usePostCompiling(true);\n   *  });\n   * </pre>\n   *\n   * @param {string} factory Factory name\n   */\n  this.usePostCompiling = function (value) {\n    $postCompilingEnabled = !(!value);\n    return this;\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#forceAsyncReload\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * If force async reload is enabled, async loader will always be called\n   * even if $translationTable already contains the language key, adding\n   * possible new entries to the $translationTable.\n   *\n   * Example:\n   * <pre>\n   *  app.config(function ($translateProvider) {\n   *    $translateProvider.forceAsyncReload(true);\n   *  });\n   * </pre>\n   *\n   * @param {boolean} value - valid values are true or false\n   */\n  this.forceAsyncReload = function (value) {\n    $forceAsyncReloadEnabled = !(!value);\n    return this;\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#uniformLanguageTag\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Tells angular-translate which language tag should be used as a result when determining\n   * the current browser language.\n   *\n   * This setting must be set before invoking {@link pascalprecht.translate.$translateProvider#methods_determinePreferredLanguage determinePreferredLanguage()}.\n   *\n   * <pre>\n   * $translateProvider\n   *   .uniformLanguageTag('bcp47')\n   *   .determinePreferredLanguage()\n   * </pre>\n   *\n   * The resolver currently supports:\n   * * default\n   *     (traditionally: hyphens will be converted into underscores, i.e. en-US => en_US)\n   *     en-US => en_US\n   *     en_US => en_US\n   *     en-us => en_us\n   * * java\n   *     like default, but the second part will be always in uppercase\n   *     en-US => en_US\n   *     en_US => en_US\n   *     en-us => en_US\n   * * BCP 47 (RFC 4646 & 4647)\n   *     EN => en\n   *     en-US => en-US\n   *     en_US => en-US\n   *     en-us => en-US\n   *     sr-latn => sr-Latn\n   *     sr-latn-rs => sr-Latn-RS\n   *\n   * See also:\n   * * http://en.wikipedia.org/wiki/IETF_language_tag\n   * * http://www.w3.org/International/core/langtags/\n   * * http://tools.ietf.org/html/bcp47\n   *\n   * @param {string|object} options - options (or standard)\n   * @param {string} options.standard - valid values are 'default', 'bcp47', 'java'\n   */\n  this.uniformLanguageTag = function (options) {\n\n    if (!options) {\n      options = {};\n    } else if (angular.isString(options)) {\n      options = {\n        standard : options\n      };\n    }\n\n    uniformLanguageTagResolver = options.standard;\n\n    return this;\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#determinePreferredLanguage\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Tells angular-translate to try to determine on its own which language key\n   * to set as preferred language. When `fn` is given, angular-translate uses it\n   * to determine a language key, otherwise it uses the built-in `getLocale()`\n   * method.\n   *\n   * The `getLocale()` returns a language key in the format `[lang]_[country]` or\n   * `[lang]` depending on what the browser provides.\n   *\n   * Use this method at your own risk, since not all browsers return a valid\n   * locale (see {@link pascalprecht.translate.$translateProvider#methods_uniformLanguageTag uniformLanguageTag()}).\n   *\n   * @param {Function=} fn Function to determine a browser's locale\n   */\n  this.determinePreferredLanguage = function (fn) {\n\n    var locale = (fn && angular.isFunction(fn)) ? fn() : getLocale();\n\n    if (!$availableLanguageKeys.length) {\n      $preferredLanguage = locale;\n    } else {\n      $preferredLanguage = negotiateLocale(locale) || locale;\n    }\n\n    return this;\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#registerAvailableLanguageKeys\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Registers a set of language keys the app will work with. Use this method in\n   * combination with\n   * {@link pascalprecht.translate.$translateProvider#determinePreferredLanguage determinePreferredLanguage}.\n   * When available languages keys are registered, angular-translate\n   * tries to find the best fitting language key depending on the browsers locale,\n   * considering your language key convention.\n   *\n   * @param {object} languageKeys Array of language keys the your app will use\n   * @param {object=} aliases Alias map.\n   */\n  this.registerAvailableLanguageKeys = function (languageKeys, aliases) {\n    if (languageKeys) {\n      $availableLanguageKeys = languageKeys;\n      if (aliases) {\n        $languageKeyAliases = aliases;\n      }\n      return this;\n    }\n    return $availableLanguageKeys;\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#useLoaderCache\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Registers a cache for internal $http based loaders.\n   * {@link pascalprecht.translate.$translationCache $translationCache}.\n   * When false the cache will be disabled (default). When true or undefined\n   * the cache will be a default (see $cacheFactory). When an object it will\n   * be treat as a cache object itself: the usage is $http({cache: cache})\n   *\n   * @param {object} cache boolean, string or cache-object\n   */\n  this.useLoaderCache = function (cache) {\n    if (cache === false) {\n      // disable cache\n      loaderCache = undefined;\n    } else if (cache === true) {\n      // enable cache using AJS defaults\n      loaderCache = true;\n    } else if (typeof(cache) === 'undefined') {\n      // enable cache using default\n      loaderCache = '$translationCache';\n    } else if (cache) {\n      // enable cache using given one (see $cacheFactory)\n      loaderCache = cache;\n    }\n    return this;\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#directivePriority\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Sets the default priority of the translate directive. The standard value is `0`.\n   * Calling this function without an argument will return the current value.\n   *\n   * @param {number} priority for the translate-directive\n   */\n  this.directivePriority = function (priority) {\n    if (priority === undefined) {\n      // getter\n      return directivePriority;\n    } else {\n      // setter with chaining\n      directivePriority = priority;\n      return this;\n    }\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#statefulFilter\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * Since AngularJS 1.3, filters which are not stateless (depending at the scope)\n   * have to explicit define this behavior.\n   * Sets whether the translate filter should be stateful or stateless. The standard value is `true`\n   * meaning being stateful.\n   * Calling this function without an argument will return the current value.\n   *\n   * @param {boolean} state - defines the state of the filter\n   */\n  this.statefulFilter = function (state) {\n    if (state === undefined) {\n      // getter\n      return statefulFilter;\n    } else {\n      // setter with chaining\n      statefulFilter = state;\n      return this;\n    }\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#postProcess\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * The post processor will be intercept right after the translation result. It can modify the result.\n   *\n   * @param {object} fn Function or service name (string) to be called after the translation value has been set / resolved. The function itself will enrich every value being processed and then continue the normal resolver process\n   */\n  this.postProcess = function (fn) {\n    if (fn) {\n      postProcessFn = fn;\n    } else {\n      postProcessFn = undefined;\n    }\n    return this;\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateProvider#keepContent\n   * @methodOf pascalprecht.translate.$translateProvider\n   *\n   * @description\n   * If keepContent is set to true than translate directive will always use innerHTML\n   * as a default translation\n   *\n   * Example:\n   * <pre>\n   *  app.config(function ($translateProvider) {\n   *    $translateProvider.keepContent(true);\n   *  });\n   * </pre>\n   *\n   * @param {boolean} value - valid values are true or false\n   */\n  this.keepContent = function (value) {\n    $keepContent = !(!value);\n    return this;\n  };\n\n  /**\n   * @ngdoc object\n   * @name pascalprecht.translate.$translate\n   * @requires $interpolate\n   * @requires $log\n   * @requires $rootScope\n   * @requires $q\n   *\n   * @description\n   * The `$translate` service is the actual core of angular-translate. It expects a translation id\n   * and optional interpolate parameters to translate contents.\n   *\n   * <pre>\n   *  $translate('HEADLINE_TEXT').then(function (translation) {\n   *    $scope.translatedText = translation;\n   *  });\n   * </pre>\n   *\n   * @param {string|array} translationId A token which represents a translation id\n   *                                     This can be optionally an array of translation ids which\n   *                                     results that the function returns an object where each key\n   *                                     is the translation id and the value the translation.\n   * @param {object=} [interpolateParams={}] An object hash for dynamic values\n   * @param {string=} [interpolationId=undefined] The id of the interpolation to use (use default unless set via useInterpolation())\n   * @param {string=} [defaultTranslationText=undefined] the optional default translation text that is written as\n   *                                        as default text in case it is not found in any configured language\n   * @param {string=} [forceLanguage=false] A language to be used instead of the current language\n   * @param {string=} [sanitizeStrategy=undefined] force sanitize strategy for this call instead of using the configured one (use default unless set)\n   * @returns {object} promise\n   */\n  this.$get = ['$log', '$injector', '$rootScope', '$q', function ($log, $injector, $rootScope, $q) {\n\n    var Storage,\n      defaultInterpolator = $injector.get($interpolationFactory || '$translateDefaultInterpolation'),\n      pendingLoader = false,\n      interpolatorHashMap = {},\n      langPromises = {},\n      fallbackIndex,\n      startFallbackIteration;\n\n    var $translate = function (translationId, interpolateParams, interpolationId, defaultTranslationText, forceLanguage, sanitizeStrategy) {\n      if (!$uses && $preferredLanguage) {\n        $uses = $preferredLanguage;\n      }\n      var uses = (forceLanguage && forceLanguage !== $uses) ? // we don't want to re-negotiate $uses\n        (negotiateLocale(forceLanguage) || forceLanguage) : $uses;\n\n      // Check forceLanguage is present\n      if (forceLanguage) {\n        loadTranslationsIfMissing(forceLanguage);\n      }\n\n      // Duck detection: If the first argument is an array, a bunch of translations was requested.\n      // The result is an object.\n      if (angular.isArray(translationId)) {\n        // Inspired by Q.allSettled by Kris Kowal\n        // https://github.com/kriskowal/q/blob/b0fa72980717dc202ffc3cbf03b936e10ebbb9d7/q.js#L1553-1563\n        // This transforms all promises regardless resolved or rejected\n        var translateAll = function (translationIds) {\n          var results = {}; // storing the actual results\n          var promises = []; // promises to wait for\n          // Wraps the promise a) being always resolved and b) storing the link id->value\n          var translate = function (translationId) {\n            var deferred = $q.defer();\n            var regardless = function (value) {\n              results[translationId] = value;\n              deferred.resolve([translationId, value]);\n            };\n            // we don't care whether the promise was resolved or rejected; just store the values\n            $translate(translationId, interpolateParams, interpolationId, defaultTranslationText, forceLanguage, sanitizeStrategy).then(regardless, regardless);\n            return deferred.promise;\n          };\n          for (var i = 0, c = translationIds.length; i < c; i++) {\n            promises.push(translate(translationIds[i]));\n          }\n          // wait for all (including storing to results)\n          return $q.all(promises).then(function () {\n            // return the results\n            return results;\n          });\n        };\n        return translateAll(translationId);\n      }\n\n      var deferred = $q.defer();\n\n      // trim off any whitespace\n      if (translationId) {\n        translationId = trim.apply(translationId);\n      } else {\n        throw new TypeError('translationId must be a not empty string');\n      }\n\n      var promiseToWaitFor = (function () {\n        var promise = langPromises[uses] || langPromises[$preferredLanguage];\n\n        fallbackIndex = 0;\n\n        if ($storageFactory && !promise) {\n          // looks like there's no pending promise for $preferredLanguage or\n          // $uses. Maybe there's one pending for a language that comes from\n          // storage.\n          var langKey = Storage.get($storageKey);\n          promise = langPromises[langKey];\n\n          if ($fallbackLanguage && $fallbackLanguage.length) {\n            var index = indexOf($fallbackLanguage, langKey);\n            // maybe the language from storage is also defined as fallback language\n            // we increase the fallback language index to not search in that language\n            // as fallback, since it's probably the first used language\n            // in that case the index starts after the first element\n            fallbackIndex = (index === 0) ? 1 : 0;\n\n            // but we can make sure to ALWAYS fallback to preferred language at least\n            if (indexOf($fallbackLanguage, $preferredLanguage) < 0) {\n              $fallbackLanguage.push($preferredLanguage);\n            }\n          }\n        }\n        return promise;\n      }());\n\n      if (!promiseToWaitFor) {\n        // no promise to wait for? okay. Then there's no loader registered\n        // nor is a one pending for language that comes from storage.\n        // We can just translate.\n        determineTranslation(translationId, interpolateParams, interpolationId, defaultTranslationText, uses, sanitizeStrategy).then(deferred.resolve, deferred.reject);\n      } else {\n        var promiseResolved = function () {\n          // $uses may have changed while waiting\n          if (!forceLanguage) {\n            uses = $uses;\n          }\n          determineTranslation(translationId, interpolateParams, interpolationId, defaultTranslationText, uses, sanitizeStrategy).then(deferred.resolve, deferred.reject);\n        };\n        promiseResolved.displayName = 'promiseResolved';\n\n        promiseToWaitFor['finally'](promiseResolved)['catch'](angular.noop); // we don't care about errors here, already handled\n      }\n      return deferred.promise;\n    };\n\n    /**\n     * @name applyNotFoundIndicators\n     * @private\n     *\n     * @description\n     * Applies not fount indicators to given translation id, if needed.\n     * This function gets only executed, if a translation id doesn't exist,\n     * which is why a translation id is expected as argument.\n     *\n     * @param {string} translationId Translation id.\n     * @returns {string} Same as given translation id but applied with not found\n     * indicators.\n     */\n    var applyNotFoundIndicators = function (translationId) {\n      // applying notFoundIndicators\n      if ($notFoundIndicatorLeft) {\n        translationId = [$notFoundIndicatorLeft, translationId].join(' ');\n      }\n      if ($notFoundIndicatorRight) {\n        translationId = [translationId, $notFoundIndicatorRight].join(' ');\n      }\n      return translationId;\n    };\n\n    /**\n     * @name useLanguage\n     * @private\n     *\n     * @description\n     * Makes actual use of a language by setting a given language key as used\n     * language and informs registered interpolators to also use the given\n     * key as locale.\n     *\n     * @param {string} key Locale key.\n     */\n    var useLanguage = function (key) {\n      $uses = key;\n\n      // make sure to store new language key before triggering success event\n      if ($storageFactory) {\n        Storage.put($translate.storageKey(), $uses);\n      }\n\n      $rootScope.$emit('$translateChangeSuccess', {language : key});\n\n      // inform default interpolator\n      defaultInterpolator.setLocale($uses);\n\n      var eachInterpolator = function (interpolator, id) {\n        interpolatorHashMap[id].setLocale($uses);\n      };\n      eachInterpolator.displayName = 'eachInterpolatorLocaleSetter';\n\n      // inform all others too!\n      angular.forEach(interpolatorHashMap, eachInterpolator);\n      $rootScope.$emit('$translateChangeEnd', {language : key});\n    };\n\n    /**\n     * @name loadAsync\n     * @private\n     *\n     * @description\n     * Kicks off registered async loader using `$injector` and applies existing\n     * loader options. When resolved, it updates translation tables accordingly\n     * or rejects with given language key.\n     *\n     * @param {string} key Language key.\n     * @return {Promise} A promise.\n     */\n    var loadAsync = function (key) {\n      if (!key) {\n        throw 'No language key specified for loading.';\n      }\n\n      var deferred = $q.defer();\n\n      $rootScope.$emit('$translateLoadingStart', {language : key});\n      pendingLoader = true;\n\n      var cache = loaderCache;\n      if (typeof(cache) === 'string') {\n        // getting on-demand instance of loader\n        cache = $injector.get(cache);\n      }\n\n      var loaderOptions = angular.extend({}, $loaderOptions, {\n        key : key,\n        $http : angular.extend({}, {\n          cache : cache\n        }, $loaderOptions.$http)\n      });\n\n      var onLoaderSuccess = function (data) {\n        var translationTable = {};\n        $rootScope.$emit('$translateLoadingSuccess', {language : key});\n\n        if (angular.isArray(data)) {\n          angular.forEach(data, function (table) {\n            angular.extend(translationTable, flatObject(table));\n          });\n        } else {\n          angular.extend(translationTable, flatObject(data));\n        }\n        pendingLoader = false;\n        deferred.resolve({\n          key : key,\n          table : translationTable\n        });\n        $rootScope.$emit('$translateLoadingEnd', {language : key});\n      };\n      onLoaderSuccess.displayName = 'onLoaderSuccess';\n\n      var onLoaderError = function (key) {\n        $rootScope.$emit('$translateLoadingError', {language : key});\n        deferred.reject(key);\n        $rootScope.$emit('$translateLoadingEnd', {language : key});\n      };\n      onLoaderError.displayName = 'onLoaderError';\n\n      $injector.get($loaderFactory)(loaderOptions)\n        .then(onLoaderSuccess, onLoaderError);\n\n      return deferred.promise;\n    };\n\n    if ($storageFactory) {\n      Storage = $injector.get($storageFactory);\n\n      if (!Storage.get || !Storage.put) {\n        throw new Error('Couldn\\'t use storage \\'' + $storageFactory + '\\', missing get() or put() method!');\n      }\n    }\n\n    // if we have additional interpolations that were added via\n    // $translateProvider.addInterpolation(), we have to map'em\n    if ($interpolatorFactories.length) {\n      var eachInterpolationFactory = function (interpolatorFactory) {\n        var interpolator = $injector.get(interpolatorFactory);\n        // setting initial locale for each interpolation service\n        interpolator.setLocale($preferredLanguage || $uses);\n        // make'em recognizable through id\n        interpolatorHashMap[interpolator.getInterpolationIdentifier()] = interpolator;\n      };\n      eachInterpolationFactory.displayName = 'interpolationFactoryAdder';\n\n      angular.forEach($interpolatorFactories, eachInterpolationFactory);\n    }\n\n    /**\n     * @name getTranslationTable\n     * @private\n     *\n     * @description\n     * Returns a promise that resolves to the translation table\n     * or is rejected if an error occurred.\n     *\n     * @param langKey\n     * @returns {Q.promise}\n     */\n    var getTranslationTable = function (langKey) {\n      var deferred = $q.defer();\n      if (Object.prototype.hasOwnProperty.call($translationTable, langKey)) {\n        deferred.resolve($translationTable[langKey]);\n      } else if (langPromises[langKey]) {\n        var onResolve = function (data) {\n          translations(data.key, data.table);\n          deferred.resolve(data.table);\n        };\n        onResolve.displayName = 'translationTableResolver';\n        langPromises[langKey].then(onResolve, deferred.reject);\n      } else {\n        deferred.reject();\n      }\n      return deferred.promise;\n    };\n\n    /**\n     * @name getFallbackTranslation\n     * @private\n     *\n     * @description\n     * Returns a promise that will resolve to the translation\n     * or be rejected if no translation was found for the language.\n     * This function is currently only used for fallback language translation.\n     *\n     * @param langKey The language to translate to.\n     * @param translationId\n     * @param interpolateParams\n     * @param Interpolator\n     * @param sanitizeStrategy\n     * @returns {Q.promise}\n     */\n    var getFallbackTranslation = function (langKey, translationId, interpolateParams, Interpolator, sanitizeStrategy) {\n      var deferred = $q.defer();\n\n      var onResolve = function (translationTable) {\n        if (Object.prototype.hasOwnProperty.call(translationTable, translationId) && translationTable[translationId] !== null) {\n          Interpolator.setLocale(langKey);\n          var translation = translationTable[translationId];\n          if (translation.substr(0, 2) === '@:') {\n            getFallbackTranslation(langKey, translation.substr(2), interpolateParams, Interpolator, sanitizeStrategy)\n              .then(deferred.resolve, deferred.reject);\n          } else {\n            var interpolatedValue = Interpolator.interpolate(translationTable[translationId], interpolateParams, 'service', sanitizeStrategy, translationId);\n            interpolatedValue = applyPostProcessing(translationId, translationTable[translationId], interpolatedValue, interpolateParams, langKey);\n\n            deferred.resolve(interpolatedValue);\n\n          }\n          Interpolator.setLocale($uses);\n        } else {\n          deferred.reject();\n        }\n      };\n      onResolve.displayName = 'fallbackTranslationResolver';\n\n      getTranslationTable(langKey).then(onResolve, deferred.reject);\n\n      return deferred.promise;\n    };\n\n    /**\n     * @name getFallbackTranslationInstant\n     * @private\n     *\n     * @description\n     * Returns a translation\n     * This function is currently only used for fallback language translation.\n     *\n     * @param langKey The language to translate to.\n     * @param translationId\n     * @param interpolateParams\n     * @param Interpolator\n     * @param sanitizeStrategy sanitize strategy override\n     *\n     * @returns {string} translation\n     */\n    var getFallbackTranslationInstant = function (langKey, translationId, interpolateParams, Interpolator, sanitizeStrategy) {\n      var result, translationTable = $translationTable[langKey];\n\n      if (translationTable && Object.prototype.hasOwnProperty.call(translationTable, translationId) && translationTable[translationId] !== null) {\n        Interpolator.setLocale(langKey);\n        result = Interpolator.interpolate(translationTable[translationId], interpolateParams, 'filter', sanitizeStrategy, translationId);\n        result = applyPostProcessing(translationId, translationTable[translationId], result, interpolateParams, langKey, sanitizeStrategy);\n        // workaround for TrustedValueHolderType\n        if (!angular.isString(result) && angular.isFunction(result.$$unwrapTrustedValue)) {\n          var result2 = result.$$unwrapTrustedValue();\n          if (result2.substr(0, 2) === '@:') {\n            return getFallbackTranslationInstant(langKey, result2.substr(2), interpolateParams, Interpolator, sanitizeStrategy);\n          }\n        } else if (result.substr(0, 2) === '@:') {\n          return getFallbackTranslationInstant(langKey, result.substr(2), interpolateParams, Interpolator, sanitizeStrategy);\n        }\n        Interpolator.setLocale($uses);\n      }\n\n      return result;\n    };\n\n\n    /**\n     * @name translateByHandler\n     * @private\n     *\n     * Translate by missing translation handler.\n     *\n     * @param translationId\n     * @param interpolateParams\n     * @param defaultTranslationText\n     * @param sanitizeStrategy sanitize strategy override\n     *\n     * @returns translation created by $missingTranslationHandler or translationId is $missingTranslationHandler is\n     * absent\n     */\n    var translateByHandler = function (translationId, interpolateParams, defaultTranslationText, sanitizeStrategy) {\n      // If we have a handler factory - we might also call it here to determine if it provides\n      // a default text for a translationid that can't be found anywhere in our tables\n      if ($missingTranslationHandlerFactory) {\n        return $injector.get($missingTranslationHandlerFactory)(translationId, $uses, interpolateParams, defaultTranslationText, sanitizeStrategy);\n      } else {\n        return translationId;\n      }\n    };\n\n    /**\n     * @name resolveForFallbackLanguage\n     * @private\n     *\n     * Recursive helper function for fallbackTranslation that will sequentially look\n     * for a translation in the fallbackLanguages starting with fallbackLanguageIndex.\n     *\n     * @param fallbackLanguageIndex\n     * @param translationId\n     * @param interpolateParams\n     * @param Interpolator\n     * @param defaultTranslationText\n     * @param sanitizeStrategy\n     * @returns {Q.promise} Promise that will resolve to the translation.\n     */\n    var resolveForFallbackLanguage = function (fallbackLanguageIndex, translationId, interpolateParams, Interpolator, defaultTranslationText, sanitizeStrategy) {\n      var deferred = $q.defer();\n\n      if (fallbackLanguageIndex < $fallbackLanguage.length) {\n        var langKey = $fallbackLanguage[fallbackLanguageIndex];\n        getFallbackTranslation(langKey, translationId, interpolateParams, Interpolator, sanitizeStrategy).then(\n          function (data) {\n            deferred.resolve(data);\n          },\n          function () {\n            // Look in the next fallback language for a translation.\n            // It delays the resolving by passing another promise to resolve.\n            return resolveForFallbackLanguage(fallbackLanguageIndex + 1, translationId, interpolateParams, Interpolator, defaultTranslationText, sanitizeStrategy).then(deferred.resolve, deferred.reject);\n          }\n        );\n      } else {\n        // No translation found in any fallback language\n        // if a default translation text is set in the directive, then return this as a result\n        if (defaultTranslationText) {\n          deferred.resolve(defaultTranslationText);\n        } else {\n          var missingTranslationHandlerTranslation = translateByHandler(translationId, interpolateParams, defaultTranslationText);\n\n          // if no default translation is set and an error handler is defined, send it to the handler\n          // and then return the result if it isn't undefined\n          if ($missingTranslationHandlerFactory && missingTranslationHandlerTranslation) {\n            deferred.resolve(missingTranslationHandlerTranslation);\n          } else {\n            deferred.reject(applyNotFoundIndicators(translationId));\n          }\n        }\n      }\n      return deferred.promise;\n    };\n\n    /**\n     * @name resolveForFallbackLanguageInstant\n     * @private\n     *\n     * Recursive helper function for fallbackTranslation that will sequentially look\n     * for a translation in the fallbackLanguages starting with fallbackLanguageIndex.\n     *\n     * @param fallbackLanguageIndex\n     * @param translationId\n     * @param interpolateParams\n     * @param Interpolator\n     * @param sanitizeStrategy\n     * @returns {string} translation\n     */\n    var resolveForFallbackLanguageInstant = function (fallbackLanguageIndex, translationId, interpolateParams, Interpolator, sanitizeStrategy) {\n      var result;\n\n      if (fallbackLanguageIndex < $fallbackLanguage.length) {\n        var langKey = $fallbackLanguage[fallbackLanguageIndex];\n        result = getFallbackTranslationInstant(langKey, translationId, interpolateParams, Interpolator, sanitizeStrategy);\n        if (!result && result !== '') {\n          result = resolveForFallbackLanguageInstant(fallbackLanguageIndex + 1, translationId, interpolateParams, Interpolator);\n        }\n      }\n      return result;\n    };\n\n    /**\n     * Translates with the usage of the fallback languages.\n     *\n     * @param translationId\n     * @param interpolateParams\n     * @param Interpolator\n     * @param defaultTranslationText\n     * @param sanitizeStrategy\n     * @returns {Q.promise} Promise, that resolves to the translation.\n     */\n    var fallbackTranslation = function (translationId, interpolateParams, Interpolator, defaultTranslationText, sanitizeStrategy) {\n      // Start with the fallbackLanguage with index 0\n      return resolveForFallbackLanguage((startFallbackIteration > 0 ? startFallbackIteration : fallbackIndex), translationId, interpolateParams, Interpolator, defaultTranslationText, sanitizeStrategy);\n    };\n\n    /**\n     * Translates with the usage of the fallback languages.\n     *\n     * @param translationId\n     * @param interpolateParams\n     * @param Interpolator\n     * @param sanitizeStrategy\n     * @returns {String} translation\n     */\n    var fallbackTranslationInstant = function (translationId, interpolateParams, Interpolator, sanitizeStrategy) {\n      // Start with the fallbackLanguage with index 0\n      return resolveForFallbackLanguageInstant((startFallbackIteration > 0 ? startFallbackIteration : fallbackIndex), translationId, interpolateParams, Interpolator, sanitizeStrategy);\n    };\n\n    var determineTranslation = function (translationId, interpolateParams, interpolationId, defaultTranslationText, uses, sanitizeStrategy) {\n\n      var deferred = $q.defer();\n\n      var table = uses ? $translationTable[uses] : $translationTable,\n        Interpolator = (interpolationId) ? interpolatorHashMap[interpolationId] : defaultInterpolator;\n\n      // if the translation id exists, we can just interpolate it\n      if (table && Object.prototype.hasOwnProperty.call(table, translationId) && table[translationId] !== null) {\n        var translation = table[translationId];\n\n        // If using link, rerun $translate with linked translationId and return it\n        if (translation.substr(0, 2) === '@:') {\n\n          $translate(translation.substr(2), interpolateParams, interpolationId, defaultTranslationText, uses, sanitizeStrategy)\n            .then(deferred.resolve, deferred.reject);\n        } else {\n          //\n          var resolvedTranslation = Interpolator.interpolate(translation, interpolateParams, 'service', sanitizeStrategy, translationId);\n          resolvedTranslation = applyPostProcessing(translationId, translation, resolvedTranslation, interpolateParams, uses);\n          deferred.resolve(resolvedTranslation);\n        }\n      } else {\n        var missingTranslationHandlerTranslation;\n        // for logging purposes only (as in $translateMissingTranslationHandlerLog), value is not returned to promise\n        if ($missingTranslationHandlerFactory && !pendingLoader) {\n          missingTranslationHandlerTranslation = translateByHandler(translationId, interpolateParams, defaultTranslationText);\n        }\n\n        // since we couldn't translate the inital requested translation id,\n        // we try it now with one or more fallback languages, if fallback language(s) is\n        // configured.\n        if (uses && $fallbackLanguage && $fallbackLanguage.length) {\n          fallbackTranslation(translationId, interpolateParams, Interpolator, defaultTranslationText, sanitizeStrategy)\n            .then(function (translation) {\n              deferred.resolve(translation);\n            }, function (_translationId) {\n              deferred.reject(applyNotFoundIndicators(_translationId));\n            });\n        } else if ($missingTranslationHandlerFactory && !pendingLoader && missingTranslationHandlerTranslation) {\n          // looks like the requested translation id doesn't exists.\n          // Now, if there is a registered handler for missing translations and no\n          // asyncLoader is pending, we execute the handler\n          if (defaultTranslationText) {\n            deferred.resolve(defaultTranslationText);\n          } else {\n            deferred.resolve(missingTranslationHandlerTranslation);\n          }\n        } else {\n          if (defaultTranslationText) {\n            deferred.resolve(defaultTranslationText);\n          } else {\n            deferred.reject(applyNotFoundIndicators(translationId));\n          }\n        }\n      }\n      return deferred.promise;\n    };\n\n    var determineTranslationInstant = function (translationId, interpolateParams, interpolationId, uses, sanitizeStrategy) {\n\n      var result, table = uses ? $translationTable[uses] : $translationTable,\n        Interpolator = defaultInterpolator;\n\n      // if the interpolation id exists use custom interpolator\n      if (interpolatorHashMap && Object.prototype.hasOwnProperty.call(interpolatorHashMap, interpolationId)) {\n        Interpolator = interpolatorHashMap[interpolationId];\n      }\n\n      // if the translation id exists, we can just interpolate it\n      if (table && Object.prototype.hasOwnProperty.call(table, translationId) && table[translationId] !== null) {\n        var translation = table[translationId];\n\n        // If using link, rerun $translate with linked translationId and return it\n        if (translation.substr(0, 2) === '@:') {\n          result = determineTranslationInstant(translation.substr(2), interpolateParams, interpolationId, uses, sanitizeStrategy);\n        } else {\n          result = Interpolator.interpolate(translation, interpolateParams, 'filter', sanitizeStrategy, translationId);\n          result = applyPostProcessing(translationId, translation, result, interpolateParams, uses, sanitizeStrategy);\n        }\n      } else {\n        var missingTranslationHandlerTranslation;\n        // for logging purposes only (as in $translateMissingTranslationHandlerLog), value is not returned to promise\n        if ($missingTranslationHandlerFactory && !pendingLoader) {\n          missingTranslationHandlerTranslation = translateByHandler(translationId, interpolateParams, sanitizeStrategy);\n        }\n\n        // since we couldn't translate the inital requested translation id,\n        // we try it now with one or more fallback languages, if fallback language(s) is\n        // configured.\n        if (uses && $fallbackLanguage && $fallbackLanguage.length) {\n          fallbackIndex = 0;\n          result = fallbackTranslationInstant(translationId, interpolateParams, Interpolator, sanitizeStrategy);\n        } else if ($missingTranslationHandlerFactory && !pendingLoader && missingTranslationHandlerTranslation) {\n          // looks like the requested translation id doesn't exists.\n          // Now, if there is a registered handler for missing translations and no\n          // asyncLoader is pending, we execute the handler\n          result = missingTranslationHandlerTranslation;\n        } else {\n          result = applyNotFoundIndicators(translationId);\n        }\n      }\n\n      return result;\n    };\n\n    var clearNextLangAndPromise = function (key) {\n      if ($nextLang === key) {\n        $nextLang = undefined;\n      }\n      langPromises[key] = undefined;\n    };\n\n    var applyPostProcessing = function (translationId, translation, resolvedTranslation, interpolateParams, uses, sanitizeStrategy) {\n      var fn = postProcessFn;\n\n      if (fn) {\n\n        if (typeof(fn) === 'string') {\n          // getting on-demand instance\n          fn = $injector.get(fn);\n        }\n        if (fn) {\n          return fn(translationId, translation, resolvedTranslation, interpolateParams, uses, sanitizeStrategy);\n        }\n      }\n\n      return resolvedTranslation;\n    };\n\n    var loadTranslationsIfMissing = function (key) {\n      if (!$translationTable[key] && $loaderFactory && !langPromises[key]) {\n        langPromises[key] = loadAsync(key).then(function (translation) {\n          translations(translation.key, translation.table);\n          return translation;\n        });\n      }\n    };\n\n    /**\n     * @ngdoc function\n     * @name pascalprecht.translate.$translate#preferredLanguage\n     * @methodOf pascalprecht.translate.$translate\n     *\n     * @description\n     * Returns the language key for the preferred language.\n     *\n     * @param {string} langKey language String or Array to be used as preferredLanguage (changing at runtime)\n     *\n     * @return {string} preferred language key\n     */\n    $translate.preferredLanguage = function (langKey) {\n      if (langKey) {\n        setupPreferredLanguage(langKey);\n      }\n      return $preferredLanguage;\n    };\n\n    /**\n     * @ngdoc function\n     * @name pascalprecht.translate.$translate#cloakClassName\n     * @methodOf pascalprecht.translate.$translate\n     *\n     * @description\n     * Returns the configured class name for `translate-cloak` directive.\n     *\n     * @return {string} cloakClassName\n     */\n    $translate.cloakClassName = function () {\n      return $cloakClassName;\n    };\n\n    /**\n     * @ngdoc function\n     * @name pascalprecht.translate.$translate#allowNamespaces\n     * @methodOf pascalprecht.translate.$translate\n     *\n     * @description\n     * Returns if namespaces are enabled\n     *\n     * @return {boolean} allowNamespaces value\n     */\n    $translate.allowNamespaces = function () {\n      return $allowNamespaces;\n    };\n\n    /**\n     * @ngdoc function\n     * @name pascalprecht.translate.$translate#nestedObjectDelimeter\n     * @methodOf pascalprecht.translate.$translate\n     *\n     * @description\n     * Returns the configured delimiter for nested namespaces.\n     *\n     * @return {string} nestedObjectDelimeter\n     */\n    $translate.nestedObjectDelimeter = function () {\n      return $nestedObjectDelimeter;\n    };\n\n    /**\n     * @ngdoc function\n     * @name pascalprecht.translate.$translate#fallbackLanguage\n     * @methodOf pascalprecht.translate.$translate\n     *\n     * @description\n     * Returns the language key for the fallback languages or sets a new fallback stack.\n     * It is recommended to call this before {@link pascalprecht.translate.$translateProvider#preferredLanguage preferredLanguage()}.\n     *\n     * @param {string=} langKey language String or Array of fallback languages to be used (to change stack at runtime)\n     *\n     * @return {string||array} fallback language key\n     */\n    $translate.fallbackLanguage = function (langKey) {\n      if (langKey !== undefined && langKey !== null) {\n        fallbackStack(langKey);\n\n        // as we might have an async loader initiated and a new translation language might have been defined\n        // we need to add the promise to the stack also. So - iterate.\n        if ($loaderFactory) {\n          if ($fallbackLanguage && $fallbackLanguage.length) {\n            for (var i = 0, len = $fallbackLanguage.length; i < len; i++) {\n              if (!langPromises[$fallbackLanguage[i]]) {\n                langPromises[$fallbackLanguage[i]] = loadAsync($fallbackLanguage[i]);\n              }\n            }\n          }\n        }\n        $translate.use($translate.use());\n      }\n      if ($fallbackWasString) {\n        return $fallbackLanguage[0];\n      } else {\n        return $fallbackLanguage;\n      }\n\n    };\n\n    /**\n     * @ngdoc function\n     * @name pascalprecht.translate.$translate#useFallbackLanguage\n     * @methodOf pascalprecht.translate.$translate\n     *\n     * @description\n     * Sets the first key of the fallback language stack to be used for translation.\n     * Therefore all languages in the fallback array BEFORE this key will be skipped!\n     *\n     * @param {string=} langKey Contains the langKey the iteration shall start with. Set to false if you want to\n     * get back to the whole stack\n     */\n    $translate.useFallbackLanguage = function (langKey) {\n      if (langKey !== undefined && langKey !== null) {\n        if (!langKey) {\n          startFallbackIteration = 0;\n        } else {\n          var langKeyPosition = indexOf($fallbackLanguage, langKey);\n          if (langKeyPosition > -1) {\n            startFallbackIteration = langKeyPosition;\n          }\n        }\n\n      }\n\n    };\n\n    /**\n     * @ngdoc function\n     * @name pascalprecht.translate.$translate#proposedLanguage\n     * @methodOf pascalprecht.translate.$translate\n     *\n     * @description\n     * Returns the language key of language that is currently loaded asynchronously.\n     *\n     * @return {string} language key\n     */\n    $translate.proposedLanguage = function () {\n      return $nextLang;\n    };\n\n    /**\n     * @ngdoc function\n     * @name pascalprecht.translate.$translate#storage\n     * @methodOf pascalprecht.translate.$translate\n     *\n     * @description\n     * Returns registered storage.\n     *\n     * @return {object} Storage\n     */\n    $translate.storage = function () {\n      return Storage;\n    };\n\n    /**\n     * @ngdoc function\n     * @name pascalprecht.translate.$translate#negotiateLocale\n     * @methodOf pascalprecht.translate.$translate\n     *\n     * @description\n     * Returns a language key based on available languages and language aliases. If a\n     * language key cannot be resolved, returns undefined.\n     *\n     * If no or a falsy key is given, returns undefined.\n     *\n     * @param {string} [key] Language key\n     * @return {string|undefined} Language key or undefined if no language key is found.\n     */\n    $translate.negotiateLocale = negotiateLocale;\n\n    /**\n     * @ngdoc function\n     * @name pascalprecht.translate.$translate#use\n     * @methodOf pascalprecht.translate.$translate\n     *\n     * @description\n     * Tells angular-translate which language to use by given language key. This method is\n     * used to change language at runtime. It also takes care of storing the language\n     * key in a configured store to let your app remember the choosed language.\n     *\n     * When trying to 'use' a language which isn't available it tries to load it\n     * asynchronously with registered loaders.\n     *\n     * Returns promise object with loaded language file data or string of the currently used language.\n     *\n     * If no or a falsy key is given it returns the currently used language key.\n     * The returned string will be ```undefined``` if setting up $translate hasn't finished.\n     * @example\n     * $translate.use(\"en_US\").then(function(data){\n       *   $scope.text = $translate(\"HELLO\");\n       * });\n     *\n     * @param {string=} key Language key\n     * @return {object|string} Promise with loaded language data or the language key if a falsy param was given.\n     */\n    $translate.use = function (key) {\n      if (!key) {\n        return $uses;\n      }\n\n      var deferred = $q.defer();\n      deferred.promise.then(null, angular.noop); // AJS \"Possibly unhandled rejection\"\n\n      $rootScope.$emit('$translateChangeStart', {language : key});\n\n      // Try to get the aliased language key\n      var aliasedKey = negotiateLocale(key);\n      // Ensure only registered language keys will be loaded\n      if ($availableLanguageKeys.length > 0 && !aliasedKey) {\n        return $q.reject(key);\n      }\n\n      if (aliasedKey) {\n        key = aliasedKey;\n      }\n\n      // if there isn't a translation table for the language we've requested,\n      // we load it asynchronously\n      $nextLang = key;\n      if (($forceAsyncReloadEnabled || !$translationTable[key]) && $loaderFactory && !langPromises[key]) {\n        langPromises[key] = loadAsync(key).then(function (translation) {\n          translations(translation.key, translation.table);\n          deferred.resolve(translation.key);\n          if ($nextLang === key) {\n            useLanguage(translation.key);\n          }\n          return translation;\n        }, function (key) {\n          $rootScope.$emit('$translateChangeError', {language : key});\n          deferred.reject(key);\n          $rootScope.$emit('$translateChangeEnd', {language : key});\n          return $q.reject(key);\n        });\n        langPromises[key]['finally'](function () {\n          clearNextLangAndPromise(key);\n        })['catch'](angular.noop); // we don't care about errors (clearing)\n      } else if (langPromises[key]) {\n        // we are already loading this asynchronously\n        // resolve our new deferred when the old langPromise is resolved\n        langPromises[key].then(function (translation) {\n          if ($nextLang === translation.key) {\n            useLanguage(translation.key);\n          }\n          deferred.resolve(translation.key);\n          return translation;\n        }, function (key) {\n          // find first available fallback language if that request has failed\n          if (!$uses && $fallbackLanguage && $fallbackLanguage.length > 0 && $fallbackLanguage[0] !== key) {\n            return $translate.use($fallbackLanguage[0]).then(deferred.resolve, deferred.reject);\n          } else {\n            return deferred.reject(key);\n          }\n        });\n      } else {\n        deferred.resolve(key);\n        useLanguage(key);\n      }\n\n      return deferred.promise;\n    };\n\n    /**\n     * @ngdoc function\n     * @name pascalprecht.translate.$translate#resolveClientLocale\n     * @methodOf pascalprecht.translate.$translate\n     *\n     * @description\n     * This returns the current browser/client's language key. The result is processed with the configured uniform tag resolver.\n     *\n     * @returns {string} the current client/browser language key\n     */\n    $translate.resolveClientLocale = function () {\n      return getLocale();\n    };\n\n    /**\n     * @ngdoc function\n     * @name pascalprecht.translate.$translate#storageKey\n     * @methodOf pascalprecht.translate.$translate\n     *\n     * @description\n     * Returns the key for the storage.\n     *\n     * @return {string} storage key\n     */\n    $translate.storageKey = function () {\n      return storageKey();\n    };\n\n    /**\n     * @ngdoc function\n     * @name pascalprecht.translate.$translate#isPostCompilingEnabled\n     * @methodOf pascalprecht.translate.$translate\n     *\n     * @description\n     * Returns whether post compiling is enabled or not\n     *\n     * @return {bool} storage key\n     */\n    $translate.isPostCompilingEnabled = function () {\n      return $postCompilingEnabled;\n    };\n\n    /**\n     * @ngdoc function\n     * @name pascalprecht.translate.$translate#isForceAsyncReloadEnabled\n     * @methodOf pascalprecht.translate.$translate\n     *\n     * @description\n     * Returns whether force async reload is enabled or not\n     *\n     * @return {boolean} forceAsyncReload value\n     */\n    $translate.isForceAsyncReloadEnabled = function () {\n      return $forceAsyncReloadEnabled;\n    };\n\n    /**\n     * @ngdoc function\n     * @name pascalprecht.translate.$translate#isKeepContent\n     * @methodOf pascalprecht.translate.$translate\n     *\n     * @description\n     * Returns whether keepContent or not\n     *\n     * @return {boolean} keepContent value\n     */\n    $translate.isKeepContent = function () {\n      return $keepContent;\n    };\n\n    /**\n     * @ngdoc function\n     * @name pascalprecht.translate.$translate#refresh\n     * @methodOf pascalprecht.translate.$translate\n     *\n     * @description\n     * Refreshes a translation table pointed by the given langKey. If langKey is not specified,\n     * the module will drop all existent translation tables and load new version of those which\n     * are currently in use.\n     *\n     * Refresh means that the module will drop target translation table and try to load it again.\n     *\n     * In case there are no loaders registered the refresh() method will throw an Error.\n     *\n     * If the module is able to refresh translation tables refresh() method will broadcast\n     * $translateRefreshStart and $translateRefreshEnd events.\n     *\n     * @example\n     * // this will drop all currently existent translation tables and reload those which are\n     * // currently in use\n     * $translate.refresh();\n     * // this will refresh a translation table for the en_US language\n     * $translate.refresh('en_US');\n     *\n     * @param {string} langKey A language key of the table, which has to be refreshed\n     *\n     * @return {promise} Promise, which will be resolved in case a translation tables refreshing\n     * process is finished successfully, and reject if not.\n     */\n    $translate.refresh = function (langKey) {\n      if (!$loaderFactory) {\n        throw new Error('Couldn\\'t refresh translation table, no loader registered!');\n      }\n\n      $rootScope.$emit('$translateRefreshStart', {language : langKey});\n\n      var deferred = $q.defer(), updatedLanguages = {};\n\n      //private helper\n      function loadNewData(languageKey) {\n        var promise = loadAsync(languageKey);\n        //update the load promise cache for this language\n        langPromises[languageKey] = promise;\n        //register a data handler for the promise\n        promise.then(function (data) {\n            //clear the cache for this language\n            $translationTable[languageKey] = {};\n            //add the new data for this language\n            translations(languageKey, data.table);\n            //track that we updated this language\n            updatedLanguages[languageKey] = true;\n          },\n          //handle rejection to appease the $q validation\n          angular.noop);\n        return promise;\n      }\n\n      //set up post-processing\n      deferred.promise.then(\n        function () {\n          for (var key in $translationTable) {\n            if ($translationTable.hasOwnProperty(key)) {\n              //delete cache entries that were not updated\n              if (!(key in updatedLanguages)) {\n                delete $translationTable[key];\n              }\n            }\n          }\n          if ($uses) {\n            useLanguage($uses);\n          }\n        },\n        //handle rejection to appease the $q validation\n        angular.noop\n      )['finally'](\n        function () {\n          $rootScope.$emit('$translateRefreshEnd', {language : langKey});\n        }\n      );\n\n      if (!langKey) {\n        // if there's no language key specified we refresh ALL THE THINGS!\n        var languagesToReload = $fallbackLanguage && $fallbackLanguage.slice() || [];\n        if ($uses && languagesToReload.indexOf($uses) === -1) {\n          languagesToReload.push($uses);\n        }\n        $q.all(languagesToReload.map(loadNewData)).then(deferred.resolve, deferred.reject);\n\n      } else if ($translationTable[langKey]) {\n        //just refresh the specified language cache\n        loadNewData(langKey).then(deferred.resolve, deferred.reject);\n\n      } else {\n        deferred.reject();\n      }\n\n      return deferred.promise;\n    };\n\n    /**\n     * @ngdoc function\n     * @name pascalprecht.translate.$translate#instant\n     * @methodOf pascalprecht.translate.$translate\n     *\n     * @description\n     * Returns a translation instantly from the internal state of loaded translation. All rules\n     * regarding the current language, the preferred language of even fallback languages will be\n     * used except any promise handling. If a language was not found, an asynchronous loading\n     * will be invoked in the background.\n     *\n     * @param {string|array} translationId A token which represents a translation id\n     *                                     This can be optionally an array of translation ids which\n     *                                     results that the function's promise returns an object where\n     *                                     each key is the translation id and the value the translation.\n     * @param {object=} [interpolateParams={}] Params\n     * @param {string=} [interpolationId=undefined] The id of the interpolation to use (use default unless set via useInterpolation())\n     * @param {string=} [forceLanguage=false] A language to be used instead of the current language\n     * @param {string=} [sanitizeStrategy=undefined] force sanitize strategy for this call instead of using the configured one (use default unless set)\n     *\n     * @return {string|object} translation\n     */\n    $translate.instant = function (translationId, interpolateParams, interpolationId, forceLanguage, sanitizeStrategy) {\n\n      // we don't want to re-negotiate $uses\n      var uses = (forceLanguage && forceLanguage !== $uses) ? // we don't want to re-negotiate $uses\n        (negotiateLocale(forceLanguage) || forceLanguage) : $uses;\n\n      // Detect undefined and null values to shorten the execution and prevent exceptions\n      if (translationId === null || angular.isUndefined(translationId)) {\n        return translationId;\n      }\n\n      // Check forceLanguage is present\n      if (forceLanguage) {\n        loadTranslationsIfMissing(forceLanguage);\n      }\n\n      // Duck detection: If the first argument is an array, a bunch of translations was requested.\n      // The result is an object.\n      if (angular.isArray(translationId)) {\n        var results = {};\n        for (var i = 0, c = translationId.length; i < c; i++) {\n          results[translationId[i]] = $translate.instant(translationId[i], interpolateParams, interpolationId, forceLanguage, sanitizeStrategy);\n        }\n        return results;\n      }\n\n      // We discarded unacceptable values. So we just need to verify if translationId is empty String\n      if (angular.isString(translationId) && translationId.length < 1) {\n        return translationId;\n      }\n\n      // trim off any whitespace\n      if (translationId) {\n        translationId = trim.apply(translationId);\n      }\n\n      var result, possibleLangKeys = [];\n      if ($preferredLanguage) {\n        possibleLangKeys.push($preferredLanguage);\n      }\n      if (uses) {\n        possibleLangKeys.push(uses);\n      }\n      if ($fallbackLanguage && $fallbackLanguage.length) {\n        possibleLangKeys = possibleLangKeys.concat($fallbackLanguage);\n      }\n      for (var j = 0, d = possibleLangKeys.length; j < d; j++) {\n        var possibleLangKey = possibleLangKeys[j];\n        if ($translationTable[possibleLangKey]) {\n          if (typeof $translationTable[possibleLangKey][translationId] !== 'undefined') {\n            result = determineTranslationInstant(translationId, interpolateParams, interpolationId, uses, sanitizeStrategy);\n          }\n        }\n        if (typeof result !== 'undefined') {\n          break;\n        }\n      }\n\n      if (!result && result !== '') {\n        if ($notFoundIndicatorLeft || $notFoundIndicatorRight) {\n          result = applyNotFoundIndicators(translationId);\n        } else {\n          // Return translation of default interpolator if not found anything.\n          result = defaultInterpolator.interpolate(translationId, interpolateParams, 'filter', sanitizeStrategy);\n\n          // looks like the requested translation id doesn't exists.\n          // Now, if there is a registered handler for missing translations and no\n          // asyncLoader is pending, we execute the handler\n          var missingTranslationHandlerTranslation;\n          if ($missingTranslationHandlerFactory && !pendingLoader) {\n            missingTranslationHandlerTranslation = translateByHandler(translationId, interpolateParams, sanitizeStrategy);\n          }\n\n          if ($missingTranslationHandlerFactory && !pendingLoader && missingTranslationHandlerTranslation) {\n            result = missingTranslationHandlerTranslation;\n          }\n        }\n      }\n\n      return result;\n    };\n\n    /**\n     * @ngdoc function\n     * @name pascalprecht.translate.$translate#versionInfo\n     * @methodOf pascalprecht.translate.$translate\n     *\n     * @description\n     * Returns the current version information for the angular-translate library\n     *\n     * @return {string} angular-translate version\n     */\n    $translate.versionInfo = function () {\n      return version;\n    };\n\n    /**\n     * @ngdoc function\n     * @name pascalprecht.translate.$translate#loaderCache\n     * @methodOf pascalprecht.translate.$translate\n     *\n     * @description\n     * Returns the defined loaderCache.\n     *\n     * @return {boolean|string|object} current value of loaderCache\n     */\n    $translate.loaderCache = function () {\n      return loaderCache;\n    };\n\n    // internal purpose only\n    $translate.directivePriority = function () {\n      return directivePriority;\n    };\n\n    // internal purpose only\n    $translate.statefulFilter = function () {\n      return statefulFilter;\n    };\n\n    /**\n     * @ngdoc function\n     * @name pascalprecht.translate.$translate#isReady\n     * @methodOf pascalprecht.translate.$translate\n     *\n     * @description\n     * Returns whether the service is \"ready\" to translate (i.e. loading 1st language).\n     *\n     * See also {@link pascalprecht.translate.$translate#methods_onReady onReady()}.\n     *\n     * @return {boolean} current value of ready\n     */\n    $translate.isReady = function () {\n      return $isReady;\n    };\n\n    var $onReadyDeferred = $q.defer();\n    $onReadyDeferred.promise.then(function () {\n      $isReady = true;\n    });\n\n    /**\n     * @ngdoc function\n     * @name pascalprecht.translate.$translate#onReady\n     * @methodOf pascalprecht.translate.$translate\n     *\n     * @description\n     * Calls the function provided or resolved the returned promise after the service is \"ready\" to translate (i.e. loading 1st language).\n     *\n     * See also {@link pascalprecht.translate.$translate#methods_isReady isReady()}.\n     *\n     * @param {Function=} fn Function to invoke when service is ready\n     * @return {object} Promise resolved when service is ready\n     */\n    $translate.onReady = function (fn) {\n      var deferred = $q.defer();\n      if (angular.isFunction(fn)) {\n        deferred.promise.then(fn);\n      }\n      if ($isReady) {\n        deferred.resolve();\n      } else {\n        $onReadyDeferred.promise.then(deferred.resolve);\n      }\n      return deferred.promise;\n    };\n\n    /**\n     * @ngdoc function\n     * @name pascalprecht.translate.$translate#getAvailableLanguageKeys\n     * @methodOf pascalprecht.translate.$translate\n     *\n     * @description\n     * This function simply returns the registered language keys being defined before in the config phase\n     * With this, an application can use the array to provide a language selection dropdown or similar\n     * without any additional effort\n     *\n     * @returns {object} returns the list of possibly registered language keys and mapping or null if not defined\n     */\n    $translate.getAvailableLanguageKeys = function () {\n      if ($availableLanguageKeys.length > 0) {\n        return $availableLanguageKeys;\n      }\n      return null;\n    };\n\n    /**\n     * @ngdoc function\n     * @name pascalprecht.translate.$translate#getTranslationTable\n     * @methodOf pascalprecht.translate.$translate\n     *\n     * @description\n     * Returns translation table by the given language key.\n     *\n     * Unless a language is provided it returns a translation table of the current one.\n     * Note: If translation dictionary is currently downloading or in progress\n     * it will return null.\n     *\n     * @param {string} langKey A token which represents a translation id\n     *\n     * @return {object} a copy of angular-translate $translationTable\n     */\n    $translate.getTranslationTable = function (langKey) {\n      langKey = langKey || $translate.use();\n      if (langKey && $translationTable[langKey]) {\n        return angular.copy($translationTable[langKey]);\n      }\n      return null;\n    };\n\n    // Whenever $translateReady is being fired, this will ensure the state of $isReady\n    var globalOnReadyListener = $rootScope.$on('$translateReady', function () {\n      $onReadyDeferred.resolve();\n      globalOnReadyListener(); // one time only\n      globalOnReadyListener = null;\n    });\n    var globalOnChangeListener = $rootScope.$on('$translateChangeEnd', function () {\n      $onReadyDeferred.resolve();\n      globalOnChangeListener(); // one time only\n      globalOnChangeListener = null;\n    });\n\n    if ($loaderFactory) {\n\n      // If at least one async loader is defined and there are no\n      // (default) translations available we should try to load them.\n      if (angular.equals($translationTable, {})) {\n        if ($translate.use()) {\n          $translate.use($translate.use());\n        }\n      }\n\n      // Also, if there are any fallback language registered, we start\n      // loading them asynchronously as soon as we can.\n      if ($fallbackLanguage && $fallbackLanguage.length) {\n        var processAsyncResult = function (translation) {\n          translations(translation.key, translation.table);\n          $rootScope.$emit('$translateChangeEnd', {language : translation.key});\n          return translation;\n        };\n        for (var i = 0, len = $fallbackLanguage.length; i < len; i++) {\n          var fallbackLanguageId = $fallbackLanguage[i];\n          if ($forceAsyncReloadEnabled || !$translationTable[fallbackLanguageId]) {\n            langPromises[fallbackLanguageId] = loadAsync(fallbackLanguageId).then(processAsyncResult);\n          }\n        }\n      }\n    } else {\n      $rootScope.$emit('$translateReady', {language : $translate.use()});\n    }\n\n    return $translate;\n  }];\n}\n\n$translate.displayName = 'displayName';\n\n/**\n * @ngdoc object\n * @name pascalprecht.translate.$translateDefaultInterpolation\n * @requires $interpolate\n *\n * @description\n * Uses angular's `$interpolate` services to interpolate strings against some values.\n *\n * Be aware to configure a proper sanitization strategy.\n *\n * See also:\n * * {@link pascalprecht.translate.$translateSanitization}\n *\n * @return {object} $translateDefaultInterpolation Interpolator service\n */\nangular.module('pascalprecht.translate').factory('$translateDefaultInterpolation', $translateDefaultInterpolation);\n\nfunction $translateDefaultInterpolation ($interpolate, $translateSanitization) {\n\n  'use strict';\n\n  var $translateInterpolator = {},\n      $locale,\n      $identifier = 'default';\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateDefaultInterpolation#setLocale\n   * @methodOf pascalprecht.translate.$translateDefaultInterpolation\n   *\n   * @description\n   * Sets current locale (this is currently not use in this interpolation).\n   *\n   * @param {string} locale Language key or locale.\n   */\n  $translateInterpolator.setLocale = function (locale) {\n    $locale = locale;\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateDefaultInterpolation#getInterpolationIdentifier\n   * @methodOf pascalprecht.translate.$translateDefaultInterpolation\n   *\n   * @description\n   * Returns an identifier for this interpolation service.\n   *\n   * @returns {string} $identifier\n   */\n  $translateInterpolator.getInterpolationIdentifier = function () {\n    return $identifier;\n  };\n\n  /**\n   * @deprecated will be removed in 3.0\n   * @see {@link pascalprecht.translate.$translateSanitization}\n   */\n  $translateInterpolator.useSanitizeValueStrategy = function (value) {\n    $translateSanitization.useStrategy(value);\n    return this;\n  };\n\n  /**\n   * @ngdoc function\n   * @name pascalprecht.translate.$translateDefaultInterpolation#interpolate\n   * @methodOf pascalprecht.translate.$translateDefaultInterpolation\n   *\n   * @description\n   * Interpolates given value agains given interpolate params using angulars\n   * `$interpolate` service.\n   *\n   * Since AngularJS 1.5, `value` must not be a string but can be anything input.\n   *\n   * @param {string} value translation\n   * @param {object} [interpolationParams={}] interpolation params\n   * @param {string} [context=undefined] current context (filter, directive, service)\n   * @param {string} [sanitizeStrategy=undefined] sanitize strategy (use default unless set)\n   * @param {string} translationId current translationId\n   *\n   * @returns {string} interpolated string\n   */\n  $translateInterpolator.interpolate = function (value, interpolationParams, context, sanitizeStrategy, translationId) { // jshint ignore:line\n    interpolationParams = interpolationParams || {};\n    interpolationParams = $translateSanitization.sanitize(interpolationParams, 'params', sanitizeStrategy, context);\n\n    var interpolatedText;\n    if (angular.isNumber(value)) {\n      // numbers are safe\n      interpolatedText = '' + value;\n    } else if (angular.isString(value)) {\n      // strings must be interpolated (that's the job here)\n      interpolatedText = $interpolate(value)(interpolationParams);\n      interpolatedText = $translateSanitization.sanitize(interpolatedText, 'text', sanitizeStrategy, context);\n    } else {\n      // neither a number or a string, cant interpolate => empty string\n      interpolatedText = '';\n    }\n\n    return interpolatedText;\n  };\n\n  return $translateInterpolator;\n}\n\n$translateDefaultInterpolation.displayName = '$translateDefaultInterpolation';\n\nangular.module('pascalprecht.translate').constant('$STORAGE_KEY', 'NG_TRANSLATE_LANG_KEY');\n\nangular.module('pascalprecht.translate')\n/**\n * @ngdoc directive\n * @name pascalprecht.translate.directive:translate\n * @requires $interpolate,\n * @requires $compile,\n * @requires $parse,\n * @requires $rootScope\n * @restrict AE\n *\n * @description\n * Translates given translation id either through attribute or DOM content.\n * Internally it uses $translate service to translate the translation id. It possible to\n * pass an optional `translate-values` object literal as string into translation id.\n *\n * @param {string=} translate Translation id which could be either string or interpolated string.\n * @param {string=} translate-values Values to pass into translation id. Can be passed as object literal string or interpolated object.\n * @param {string=} translate-attr-ATTR translate Translation id and put it into ATTR attribute.\n * @param {string=} translate-default will be used unless translation was successful\n * @param {string=} translate-sanitize-strategy defines locally sanitize strategy\n * @param {boolean=} translate-compile (default true if present) defines locally activation of {@link pascalprecht.translate.$translateProvider#methods_usePostCompiling}\n * @param {boolean=} translate-keep-content (default true if present) defines that in case a KEY could not be translated, that the existing content is left in the innerHTML}\n *\n * @example\n   <example module=\"ngView\">\n    <file name=\"index.html\">\n      <div ng-controller=\"TranslateCtrl\">\n\n        <pre translate=\"TRANSLATION_ID\"></pre>\n        <pre translate>TRANSLATION_ID</pre>\n        <pre translate translate-attr-title=\"TRANSLATION_ID\"></pre>\n        <pre translate=\"{{translationId}}\"></pre>\n        <pre translate>{{translationId}}</pre>\n        <pre translate=\"WITH_VALUES\" translate-values=\"{value: 5}\"></pre>\n        <pre translate translate-values=\"{value: 5}\">WITH_VALUES</pre>\n        <pre translate=\"WITH_VALUES\" translate-values=\"{{values}}\"></pre>\n        <pre translate translate-values=\"{{values}}\">WITH_VALUES</pre>\n        <pre translate translate-attr-title=\"WITH_VALUES\" translate-values=\"{{values}}\"></pre>\n        <pre translate=\"WITH_CAMEL_CASE_KEY\" translate-value-camel-case-key=\"Hi\"></pre>\n\n      </div>\n    </file>\n    <file name=\"script.js\">\n      angular.module('ngView', ['pascalprecht.translate'])\n\n      .config(function ($translateProvider) {\n\n        $translateProvider.translations('en',{\n          'TRANSLATION_ID': 'Hello there!',\n          'WITH_VALUES': 'The following value is dynamic: {{value}}',\n          'WITH_CAMEL_CASE_KEY': 'The interpolation key is camel cased: {{camelCaseKey}}'\n        }).preferredLanguage('en');\n\n      });\n\n      angular.module('ngView').controller('TranslateCtrl', function ($scope) {\n        $scope.translationId = 'TRANSLATION_ID';\n\n        $scope.values = {\n          value: 78\n        };\n      });\n    </file>\n    <file name=\"scenario.js\">\n      it('should translate', function () {\n        inject(function ($rootScope, $compile) {\n          $rootScope.translationId = 'TRANSLATION_ID';\n\n          element = $compile('<p translate=\"TRANSLATION_ID\"></p>')($rootScope);\n          $rootScope.$digest();\n          expect(element.text()).toBe('Hello there!');\n\n          element = $compile('<p translate=\"{{translationId}}\"></p>')($rootScope);\n          $rootScope.$digest();\n          expect(element.text()).toBe('Hello there!');\n\n          element = $compile('<p translate>TRANSLATION_ID</p>')($rootScope);\n          $rootScope.$digest();\n          expect(element.text()).toBe('Hello there!');\n\n          element = $compile('<p translate>{{translationId}}</p>')($rootScope);\n          $rootScope.$digest();\n          expect(element.text()).toBe('Hello there!');\n\n          element = $compile('<p translate translate-attr-title=\"TRANSLATION_ID\"></p>')($rootScope);\n          $rootScope.$digest();\n          expect(element.attr('title')).toBe('Hello there!');\n\n          element = $compile('<p translate=\"WITH_CAMEL_CASE_KEY\" translate-value-camel-case-key=\"Hello\"></p>')($rootScope);\n          $rootScope.$digest();\n          expect(element.text()).toBe('The interpolation key is camel cased: Hello');\n        });\n      });\n    </file>\n   </example>\n */\n.directive('translate', translateDirective);\nfunction translateDirective($translate, $interpolate, $compile, $parse, $rootScope) {\n\n  'use strict';\n\n  /**\n   * @name trim\n   * @private\n   *\n   * @description\n   * trim polyfill\n   *\n   * @returns {string} The string stripped of whitespace from both ends\n   */\n  var trim = function() {\n    return this.toString().replace(/^\\s+|\\s+$/g, '');\n  };\n\n  /**\n   * @name lowercase\n   * @private\n   *\n   * @description\n   * Return the lowercase string only if the type is string\n   *\n   * @returns {string} The string all in lowercase\n   */\n  var lowercase = function (string) {\n    return angular.isString(string) ? string.toLowerCase() : string;\n  };\n\n  return {\n    restrict: 'AE',\n    scope: true,\n    priority: $translate.directivePriority(),\n    compile: function (tElement, tAttr) {\n\n      var translateValuesExist = (tAttr.translateValues) ?\n        tAttr.translateValues : undefined;\n\n      var translateInterpolation = (tAttr.translateInterpolation) ?\n        tAttr.translateInterpolation : undefined;\n\n      var translateSanitizeStrategyExist = (tAttr.translateSanitizeStrategy) ?\n        tAttr.translateSanitizeStrategy : undefined;\n\n      var translateValueExist = tElement[0].outerHTML.match(/translate-value-+/i);\n\n      var interpolateRegExp = '^(.*)(' + $interpolate.startSymbol() + '.*' + $interpolate.endSymbol() + ')(.*)',\n          watcherRegExp = '^(.*)' + $interpolate.startSymbol() + '(.*)' + $interpolate.endSymbol() + '(.*)';\n\n      return function linkFn(scope, iElement, iAttr) {\n\n        scope.interpolateParams = {};\n        scope.preText = '';\n        scope.postText = '';\n        scope.translateNamespace = getTranslateNamespace(scope);\n        var translationIds = {};\n\n        var initInterpolationParams = function (interpolateParams, iAttr, tAttr) {\n          // initial setup\n          if (iAttr.translateValues) {\n            angular.extend(interpolateParams, $parse(iAttr.translateValues)(scope.$parent));\n          }\n          // initially fetch all attributes if existing and fill the params\n          if (translateValueExist) {\n            for (var attr in tAttr) {\n              if (Object.prototype.hasOwnProperty.call(iAttr, attr) && attr.substr(0, 14) === 'translateValue' && attr !== 'translateValues') {\n                var attributeName = lowercase(attr.substr(14, 1)) + attr.substr(15);\n                interpolateParams[attributeName] = tAttr[attr];\n              }\n            }\n          }\n        };\n\n        // Ensures any change of the attribute \"translate\" containing the id will\n        // be re-stored to the scope's \"translationId\".\n        // If the attribute has no content, the element's text value (white spaces trimmed off) will be used.\n        var observeElementTranslation = function (translationId) {\n\n          // Remove any old watcher\n          if (angular.isFunction(observeElementTranslation._unwatchOld)) {\n            observeElementTranslation._unwatchOld();\n            observeElementTranslation._unwatchOld = undefined;\n          }\n\n          if (angular.equals(translationId , '') || !angular.isDefined(translationId)) {\n            var iElementText = trim.apply(iElement.text()).replace(/\\n/g, ' ');\n\n            // Resolve translation id by inner html if required\n            var interpolateMatches = iElementText.match(interpolateRegExp);\n            // Interpolate translation id if required\n            if (angular.isArray(interpolateMatches)) {\n              scope.preText = interpolateMatches[1];\n              scope.postText = interpolateMatches[3];\n              translationIds.translate = $interpolate(interpolateMatches[2])(scope.$parent);\n              var watcherMatches = iElementText.match(watcherRegExp);\n              if (angular.isArray(watcherMatches) && watcherMatches[2] && watcherMatches[2].length) {\n                observeElementTranslation._unwatchOld = scope.$watch(watcherMatches[2], function (newValue) {\n                  translationIds.translate = newValue;\n                  updateTranslations();\n                });\n              }\n            } else {\n              // do not assigne the translation id if it is empty.\n              translationIds.translate = !iElementText ? undefined : iElementText;\n            }\n          } else {\n            translationIds.translate = translationId;\n          }\n          updateTranslations();\n        };\n\n        var observeAttributeTranslation = function (translateAttr) {\n          iAttr.$observe(translateAttr, function (translationId) {\n            translationIds[translateAttr] = translationId;\n            updateTranslations();\n          });\n        };\n\n        // initial setup with values\n        initInterpolationParams(scope.interpolateParams, iAttr, tAttr);\n\n        var firstAttributeChangedEvent = true;\n        iAttr.$observe('translate', function (translationId) {\n          if (typeof translationId === 'undefined') {\n            // case of element \"<translate>xyz</translate>\"\n            observeElementTranslation('');\n          } else {\n            // case of regular attribute\n            if (translationId !== '' || !firstAttributeChangedEvent) {\n              translationIds.translate = translationId;\n              updateTranslations();\n            }\n          }\n          firstAttributeChangedEvent = false;\n        });\n\n        for (var translateAttr in iAttr) {\n          if (iAttr.hasOwnProperty(translateAttr) && translateAttr.substr(0, 13) === 'translateAttr' && translateAttr.length > 13) {\n            observeAttributeTranslation(translateAttr);\n          }\n        }\n\n        iAttr.$observe('translateDefault', function (value) {\n          scope.defaultText = value;\n          updateTranslations();\n        });\n\n        if (translateSanitizeStrategyExist) {\n          iAttr.$observe('translateSanitizeStrategy', function (value) {\n            scope.sanitizeStrategy = $parse(value)(scope.$parent);\n            updateTranslations();\n          });\n        }\n\n        if (translateValuesExist) {\n          iAttr.$observe('translateValues', function (interpolateParams) {\n            if (interpolateParams) {\n              scope.$parent.$watch(function () {\n                angular.extend(scope.interpolateParams, $parse(interpolateParams)(scope.$parent));\n              });\n            }\n          });\n        }\n\n        if (translateValueExist) {\n          var observeValueAttribute = function (attrName) {\n            iAttr.$observe(attrName, function (value) {\n              var attributeName = lowercase(attrName.substr(14, 1)) + attrName.substr(15);\n              scope.interpolateParams[attributeName] = value;\n            });\n          };\n          for (var attr in iAttr) {\n            if (Object.prototype.hasOwnProperty.call(iAttr, attr) && attr.substr(0, 14) === 'translateValue' && attr !== 'translateValues') {\n              observeValueAttribute(attr);\n            }\n          }\n        }\n\n        // Master update function\n        var updateTranslations = function () {\n          for (var key in translationIds) {\n            if (translationIds.hasOwnProperty(key) && translationIds[key] !== undefined) {\n              updateTranslation(key, translationIds[key], scope, scope.interpolateParams, scope.defaultText, scope.translateNamespace);\n            }\n          }\n        };\n\n        // Put translation processing function outside loop\n        var updateTranslation = function(translateAttr, translationId, scope, interpolateParams, defaultTranslationText, translateNamespace) {\n          if (translationId) {\n            // if translation id starts with '.' and translateNamespace given, prepend namespace\n            if (translateNamespace && translationId.charAt(0) === '.') {\n              translationId = translateNamespace + translationId;\n            }\n\n            $translate(translationId, interpolateParams, translateInterpolation, defaultTranslationText, scope.translateLanguage, scope.sanitizeStrategy)\n              .then(function (translation) {\n                applyTranslation(translation, scope, true, translateAttr);\n              }, function (translationId) {\n                applyTranslation(translationId, scope, false, translateAttr);\n              });\n          } else {\n            // as an empty string cannot be translated, we can solve this using successful=false\n            applyTranslation(translationId, scope, false, translateAttr);\n          }\n        };\n\n        var applyTranslation = function (value, scope, successful, translateAttr) {\n          if (!successful) {\n            if (typeof scope.defaultText !== 'undefined') {\n              value = scope.defaultText;\n            }\n          }\n          if (translateAttr === 'translate') {\n            // default translate into innerHTML\n            if (successful || (!successful && !$translate.isKeepContent() && typeof iAttr.translateKeepContent === 'undefined')) {\n              iElement.empty().append(scope.preText + value + scope.postText);\n            }\n            var globallyEnabled = $translate.isPostCompilingEnabled();\n            var locallyDefined = typeof tAttr.translateCompile !== 'undefined';\n            var locallyEnabled = locallyDefined && tAttr.translateCompile !== 'false';\n            if ((globallyEnabled && !locallyDefined) || locallyEnabled) {\n              $compile(iElement.contents())(scope);\n            }\n          } else {\n            // translate attribute\n            var attributeName = iAttr.$attr[translateAttr];\n            if (attributeName.substr(0, 5) === 'data-') {\n              // ensure html5 data prefix is stripped\n              attributeName = attributeName.substr(5);\n            }\n            attributeName = attributeName.substr(15);\n            iElement.attr(attributeName, value);\n          }\n        };\n\n        if (translateValuesExist || translateValueExist || iAttr.translateDefault) {\n          scope.$watch('interpolateParams', updateTranslations, true);\n        }\n\n        // Replaced watcher on translateLanguage with event listener\n        scope.$on('translateLanguageChanged', updateTranslations);\n\n        // Ensures the text will be refreshed after the current language was changed\n        // w/ $translate.use(...)\n        var unbind = $rootScope.$on('$translateChangeSuccess', updateTranslations);\n\n        // ensure translation will be looked up at least one\n        if (iElement.text().length) {\n          if (iAttr.translate) {\n            observeElementTranslation(iAttr.translate);\n          } else {\n            observeElementTranslation('');\n          }\n        } else if (iAttr.translate) {\n          // ensure attribute will be not skipped\n          observeElementTranslation(iAttr.translate);\n        }\n        updateTranslations();\n        scope.$on('$destroy', unbind);\n      };\n    }\n  };\n}\n\n/**\n * Returns the scope's namespace.\n * @private\n * @param scope\n * @returns {string}\n */\nfunction getTranslateNamespace(scope) {\n  'use strict';\n  if (scope.translateNamespace) {\n    return scope.translateNamespace;\n  }\n  if (scope.$parent) {\n    return getTranslateNamespace(scope.$parent);\n  }\n}\n\ntranslateDirective.displayName = 'translateDirective';\n\nangular.module('pascalprecht.translate')\n/**\n * @ngdoc directive\n * @name pascalprecht.translate.directive:translate-attr\n * @restrict A\n *\n * @description\n * Translates attributes like translate-attr-ATTR, but with an object like ng-class.\n * Internally it uses `translate` service to translate translation id. It possible to\n * pass an optional `translate-values` object literal as string into translation id.\n *\n * @param {string=} translate-attr Object literal mapping attributes to translation ids.\n * @param {string=} translate-values Values to pass into the translation ids. Can be passed as object literal string.\n * @param {string=} translate-sanitize-strategy defines locally sanitize strategy\n *\n * @example\n   <example module=\"ngView\">\n    <file name=\"index.html\">\n      <div ng-controller=\"TranslateCtrl\">\n\n        <input translate-attr=\"{ placeholder: translationId, title: 'WITH_VALUES' }\" translate-values=\"{value: 5}\" />\n\n      </div>\n    </file>\n    <file name=\"script.js\">\n      angular.module('ngView', ['pascalprecht.translate'])\n\n      .config(function ($translateProvider) {\n\n        $translateProvider.translations('en',{\n          'TRANSLATION_ID': 'Hello there!',\n          'WITH_VALUES': 'The following value is dynamic: {{value}}',\n        }).preferredLanguage('en');\n\n      });\n\n      angular.module('ngView').controller('TranslateCtrl', function ($scope) {\n        $scope.translationId = 'TRANSLATION_ID';\n\n        $scope.values = {\n          value: 78\n        };\n      });\n    </file>\n    <file name=\"scenario.js\">\n      it('should translate', function () {\n        inject(function ($rootScope, $compile) {\n          $rootScope.translationId = 'TRANSLATION_ID';\n\n          element = $compile('<input translate-attr=\"{ placeholder: translationId, title: 'WITH_VALUES' }\" translate-values=\"{ value: 5 }\" />')($rootScope);\n          $rootScope.$digest();\n          expect(element.attr('placeholder)).toBe('Hello there!');\n          expect(element.attr('title)).toBe('The following value is dynamic: 5');\n        });\n      });\n    </file>\n   </example>\n */\n.directive('translateAttr', translateAttrDirective);\nfunction translateAttrDirective($translate, $rootScope) {\n\n  'use strict';\n\n  return {\n    restrict: 'A',\n    priority: $translate.directivePriority(),\n    link: function linkFn(scope, element, attr) {\n\n      var translateAttr,\n          translateValues,\n          translateSanitizeStrategy,\n          previousAttributes = {};\n\n      // Main update translations function\n      var updateTranslations = function () {\n        angular.forEach(translateAttr, function (translationId, attributeName) {\n          if (!translationId) {\n            return;\n          }\n          previousAttributes[attributeName] = true;\n\n          // if translation id starts with '.' and translateNamespace given, prepend namespace\n          if (scope.translateNamespace && translationId.charAt(0) === '.') {\n            translationId = scope.translateNamespace + translationId;\n          }\n          $translate(translationId, translateValues, attr.translateInterpolation, undefined, scope.translateLanguage, translateSanitizeStrategy)\n            .then(function (translation) {\n              element.attr(attributeName, translation);\n            }, function (translationId) {\n              element.attr(attributeName, translationId);\n            });\n        });\n\n        // Removing unused attributes that were previously used\n        angular.forEach(previousAttributes, function (flag, attributeName) {\n          if (!translateAttr[attributeName]) {\n            element.removeAttr(attributeName);\n            delete previousAttributes[attributeName];\n          }\n        });\n      };\n\n      // Watch for attribute changes\n      watchAttribute(\n        scope,\n        attr.translateAttr,\n        function (newValue) { translateAttr = newValue; },\n        updateTranslations\n      );\n      // Watch for value changes\n      watchAttribute(\n        scope,\n        attr.translateValues,\n        function (newValue) { translateValues = newValue; },\n        updateTranslations\n      );\n      // Watch for sanitize strategy changes\n      watchAttribute(\n        scope,\n        attr.translateSanitizeStrategy,\n        function (newValue) { translateSanitizeStrategy = newValue; },\n        updateTranslations\n      );\n\n      if (attr.translateValues) {\n        scope.$watch(attr.translateValues, updateTranslations, true);\n      }\n\n      // Replaced watcher on translateLanguage with event listener\n      scope.$on('translateLanguageChanged', updateTranslations);\n\n      // Ensures the text will be refreshed after the current language was changed\n      // w/ $translate.use(...)\n      var unbind = $rootScope.$on('$translateChangeSuccess', updateTranslations);\n\n      updateTranslations();\n      scope.$on('$destroy', unbind);\n    }\n  };\n}\n\nfunction watchAttribute(scope, attribute, valueCallback, changeCallback) {\n  'use strict';\n  if (!attribute) {\n    return;\n  }\n  if (attribute.substr(0, 2) === '::') {\n    attribute = attribute.substr(2);\n  } else {\n    scope.$watch(attribute, function(newValue) {\n      valueCallback(newValue);\n      changeCallback();\n    }, true);\n  }\n  valueCallback(scope.$eval(attribute));\n}\n\ntranslateAttrDirective.displayName = 'translateAttrDirective';\n\nangular.module('pascalprecht.translate')\n/**\n * @ngdoc directive\n * @name pascalprecht.translate.directive:translateCloak\n * @requires $translate\n * @restrict A\n *\n * $description\n * Adds a `translate-cloak` class name to the given element where this directive\n * is applied initially and removes it, once a loader has finished loading.\n *\n * This directive can be used to prevent initial flickering when loading translation\n * data asynchronously.\n *\n * The class name is defined in\n * {@link pascalprecht.translate.$translateProvider#cloakClassName $translate.cloakClassName()}.\n *\n * @param {string=} translate-cloak If a translationId is provided, it will be used for showing\n *                                  or hiding the cloak. Basically it relies on the translation\n *                                  resolve.\n */\n.directive('translateCloak', translateCloakDirective);\n\nfunction translateCloakDirective($translate, $rootScope) {\n\n  'use strict';\n\n  return {\n    compile : function (tElement) {\n      var applyCloak = function (element) {\n          element.addClass($translate.cloakClassName());\n        },\n        removeCloak = function (element) {\n          element.removeClass($translate.cloakClassName());\n        };\n      applyCloak(tElement);\n\n      return function linkFn(scope, iElement, iAttr) {\n        //Create bound functions that incorporate the active DOM element.\n        var iRemoveCloak = removeCloak.bind(this, iElement), iApplyCloak = applyCloak.bind(this, iElement);\n        if (iAttr.translateCloak && iAttr.translateCloak.length) {\n          // Register a watcher for the defined translation allowing a fine tuned cloak\n          iAttr.$observe('translateCloak', function (translationId) {\n            $translate(translationId).then(iRemoveCloak, iApplyCloak);\n          });\n          $rootScope.$on('$translateChangeSuccess', function () {\n            $translate(iAttr.translateCloak).then(iRemoveCloak, iApplyCloak);\n          });\n        } else {\n          $translate.onReady(iRemoveCloak);\n        }\n      };\n    }\n  };\n}\n\ntranslateCloakDirective.displayName = 'translateCloakDirective';\n\nangular.module('pascalprecht.translate')\n/**\n * @ngdoc directive\n * @name pascalprecht.translate.directive:translateNamespace\n * @restrict A\n *\n * @description\n * Translates given translation id either through attribute or DOM content.\n * Internally it uses `translate` filter to translate translation id. It is possible to\n * pass an optional `translate-values` object literal as string into translation id.\n *\n * @param {string=} translate namespace name which could be either string or interpolated string.\n *\n * @example\n   <example module=\"ngView\">\n    <file name=\"index.html\">\n      <div translate-namespace=\"CONTENT\">\n\n        <div>\n            <h1 translate>.HEADERS.TITLE</h1>\n            <h1 translate>.HEADERS.WELCOME</h1>\n        </div>\n\n        <div translate-namespace=\".HEADERS\">\n            <h1 translate>.TITLE</h1>\n            <h1 translate>.WELCOME</h1>\n        </div>\n\n      </div>\n    </file>\n    <file name=\"script.js\">\n      angular.module('ngView', ['pascalprecht.translate'])\n\n      .config(function ($translateProvider) {\n\n        $translateProvider.translations('en',{\n          'TRANSLATION_ID': 'Hello there!',\n          'CONTENT': {\n            'HEADERS': {\n                TITLE: 'Title'\n            }\n          },\n          'CONTENT.HEADERS.WELCOME': 'Welcome'\n        }).preferredLanguage('en');\n\n      });\n\n    </file>\n   </example>\n */\n.directive('translateNamespace', translateNamespaceDirective);\n\nfunction translateNamespaceDirective() {\n\n  'use strict';\n\n  return {\n    restrict: 'A',\n    scope: true,\n    compile: function () {\n      return {\n        pre: function (scope, iElement, iAttrs) {\n          scope.translateNamespace = _getTranslateNamespace(scope);\n\n          if (scope.translateNamespace && iAttrs.translateNamespace.charAt(0) === '.') {\n            scope.translateNamespace += iAttrs.translateNamespace;\n          } else {\n            scope.translateNamespace = iAttrs.translateNamespace;\n          }\n        }\n      };\n    }\n  };\n}\n\n/**\n * Returns the scope's namespace.\n * @private\n * @param scope\n * @returns {string}\n */\nfunction _getTranslateNamespace(scope) {\n  'use strict';\n  if (scope.translateNamespace) {\n    return scope.translateNamespace;\n  }\n  if (scope.$parent) {\n    return _getTranslateNamespace(scope.$parent);\n  }\n}\n\ntranslateNamespaceDirective.displayName = 'translateNamespaceDirective';\n\nangular.module('pascalprecht.translate')\n/**\n * @ngdoc directive\n * @name pascalprecht.translate.directive:translateLanguage\n * @restrict A\n *\n * @description\n * Forces the language to the directives in the underlying scope.\n *\n * @param {string=} translate language that will be negotiated.\n *\n * @example\n   <example module=\"ngView\">\n    <file name=\"index.html\">\n      <div>\n\n        <div>\n            <h1 translate>HELLO</h1>\n        </div>\n\n        <div translate-language=\"de\">\n            <h1 translate>HELLO</h1>\n        </div>\n\n      </div>\n    </file>\n    <file name=\"script.js\">\n      angular.module('ngView', ['pascalprecht.translate'])\n\n      .config(function ($translateProvider) {\n\n        $translateProvider\n          .translations('en',{\n            'HELLO': 'Hello world!'\n          })\n          .translations('de',{\n            'HELLO': 'Hallo Welt!'\n          })\n          .preferredLanguage('en');\n\n      });\n\n    </file>\n   </example>\n */\n.directive('translateLanguage', translateLanguageDirective);\n\nfunction translateLanguageDirective() {\n\n  'use strict';\n\n  return {\n    restrict: 'A',\n    scope: true,\n    compile: function () {\n      return function linkFn(scope, iElement, iAttrs) {\n\n        iAttrs.$observe('translateLanguage', function (newTranslateLanguage) {\n          scope.translateLanguage = newTranslateLanguage;\n        });\n\n        scope.$watch('translateLanguage', function(){\n          scope.$broadcast('translateLanguageChanged');\n        });\n      };\n    }\n  };\n}\n\ntranslateLanguageDirective.displayName = 'translateLanguageDirective';\n\nangular.module('pascalprecht.translate')\n/**\n * @ngdoc filter\n * @name pascalprecht.translate.filter:translate\n * @requires $parse\n * @requires pascalprecht.translate.$translate\n * @function\n *\n * @description\n * Uses `$translate` service to translate contents. Accepts interpolate parameters\n * to pass dynamized values though translation.\n *\n * @param {string} translationId A translation id to be translated.\n * @param {*=} interpolateParams Optional object literal (as hash or string) to pass values into translation.\n *\n * @returns {string} Translated text.\n *\n * @example\n   <example module=\"ngView\">\n    <file name=\"index.html\">\n      <div ng-controller=\"TranslateCtrl\">\n\n        <pre>{{ 'TRANSLATION_ID' | translate }}</pre>\n        <pre>{{ translationId | translate }}</pre>\n        <pre>{{ 'WITH_VALUES' | translate:'{value: 5}' }}</pre>\n        <pre>{{ 'WITH_VALUES' | translate:values }}</pre>\n\n      </div>\n    </file>\n    <file name=\"script.js\">\n      angular.module('ngView', ['pascalprecht.translate'])\n\n      .config(function ($translateProvider) {\n\n        $translateProvider.translations('en', {\n          'TRANSLATION_ID': 'Hello there!',\n          'WITH_VALUES': 'The following value is dynamic: {{value}}'\n        });\n        $translateProvider.preferredLanguage('en');\n\n      });\n\n      angular.module('ngView').controller('TranslateCtrl', function ($scope) {\n        $scope.translationId = 'TRANSLATION_ID';\n\n        $scope.values = {\n          value: 78\n        };\n      });\n    </file>\n   </example>\n */\n.filter('translate', translateFilterFactory);\n\nfunction translateFilterFactory($parse, $translate) {\n\n  'use strict';\n\n  var translateFilter = function (translationId, interpolateParams, interpolation, forceLanguage) {\n    if (!angular.isObject(interpolateParams)) {\n      var ctx = this || {\n        '__SCOPE_IS_NOT_AVAILABLE': 'More info at https://github.com/angular/angular.js/commit/8863b9d04c722b278fa93c5d66ad1e578ad6eb1f'\n        };\n      interpolateParams = $parse(interpolateParams)(ctx);\n    }\n\n    return $translate.instant(translationId, interpolateParams, interpolation, forceLanguage);\n  };\n\n  if ($translate.statefulFilter()) {\n    translateFilter.$stateful = true;\n  }\n\n  return translateFilter;\n}\n\ntranslateFilterFactory.displayName = 'translateFilterFactory';\n\nangular.module('pascalprecht.translate')\n\n/**\n * @ngdoc object\n * @name pascalprecht.translate.$translationCache\n * @requires $cacheFactory\n *\n * @description\n * The first time a translation table is used, it is loaded in the translation cache for quick retrieval. You\n * can load translation tables directly into the cache by consuming the\n * `$translationCache` service directly.\n *\n * @return {object} $cacheFactory object.\n */\n  .factory('$translationCache', $translationCache);\n\nfunction $translationCache($cacheFactory) {\n\n  'use strict';\n\n  return $cacheFactory('translations');\n}\n\n$translationCache.displayName = '$translationCache';\nreturn 'pascalprecht.translate';\n\n}));\n","import {\r\n  AbsencePeriodsController,\r\n  AccountantController,\r\n  AccountantWizardController,\r\n  AccountingChannelSettingsController,\r\n  AccountAuthorizationController,\r\n  AccountingHolidayPayDebtReportQueryController,\r\n  AccountingReportCrudController,\r\n  AccountingReportDisplayController,\r\n  AccountingReportQueryController,\r\n  AccountingReportRowsController,\r\n  AccountingReportToolsController,\r\n  AccountingRowReportController,\r\n  AccountingTargetCrudController,\r\n  AccountResetController,\r\n  ActionButtonController,\r\n  AlertController,\r\n  AvatarController,\r\n  BatchProcessController,\r\n  CalcChartController,\r\n  CalcCostAccountingController,\r\n  CalcEmploymentController,\r\n  CalcHouseholdUsecaseController,\r\n  CalcImportController,\r\n  CalcIrRowsController,\r\n  CalcsIrRowsController,\r\n  CalcRepairController,\r\n  CalcRepairInfoController,\r\n  CalcReportController,\r\n  CalcReportsController,\r\n  CalcReportsDisplayController,\r\n  CalcRowCostAccountingController,\r\n  CalcRowDimensionInputController,\r\n  CalcRowDocumentationController,\r\n  CalcRowFormulaController,\r\n  CalcRowTypeController,\r\n  CalcRows2019Controller,\r\n  CalcSharingController,\r\n  CalcSharingReceiptActionController,\r\n  CalculationCrudController,\r\n  CalculationEditorController,\r\n  CalculationReportController,\r\n  Calculator2019Controller,\r\n  Calculator2022Controller,\r\n  CalcWorktimeController,\r\n  CalendarController,\r\n  CalendarEventsCrudController,\r\n  CertificateController,\r\n  ChartController,\r\n  CompanyAccountController,\r\n  CompanyInvoicesController,\r\n  CompanyImportController,\r\n  CompanyOnboardingController,\r\n  CompanySettingsController,\r\n  ContactInfoController,\r\n  CostAccountingController,\r\n  CredentialController,\r\n  CreditTransferController,\r\n  CustomerInvoiceCrudController,\r\n  CustomerOnboardingController,\r\n  DatasetsCrudController,\r\n  DatepickerController,\r\n  DatepickerPopupController,\r\n  DateRangeController,\r\n  EditDialogController,\r\n  EmbeddedUiController,\r\n  EmployerListController,\r\n  EmployerReportController,\r\n  EmployerSelectController,\r\n  EmploymentCrudController,\r\n  EmploymentTaxcardsController,\r\n  EmploymentWizardController,\r\n  ExportController,\r\n  HolidayPayReportQueryController,\r\n  HolidayReportController,\r\n  HolidayYearAccrualController,\r\n  HolidayYearCrudController,\r\n  HolidayYearHolidaysController,\r\n  HolidayYearPaidController,\r\n  HouseholdDeductionReportController,\r\n  HouseholdOnboardingController,\r\n  HouseholdYearCrudController,\r\n  ImportController,\r\n  ImportStagingController,\r\n  InputBooleanController,\r\n  InputCollectiveBargainAgreementController,\r\n  InputCredentialController,\r\n  InputDurationController,\r\n  InputEmployeeGroupController,\r\n  InputEnumController,\r\n  InputHolidayMultipliersController,\r\n  InputPayStatsRowTypeController,\r\n  InputIncomeTypeController,\r\n  InputNumberController,\r\n  InputRruleController,\r\n  InputTimeController,\r\n  InputTypeaheadController,\r\n  InsuranceWizardController,\r\n  InvoiceCrudController,\r\n  InvoicesCreateController,\r\n  InvoiceReportController,\r\n  InvoiceSepaController,\r\n  InvoiceToolsController,\r\n  InvoiceAlertsController,\r\n  InvoicePaymentListController,\r\n  IrEarningsPaymentCrudController,\r\n  IrPayerSummaryCrudController,\r\n  JsonFormatterController,\r\n  JsonDiffController,\r\n  MarkdownEditorController,\r\n  MarkdownViewerController,\r\n  MessageThreadCrudController,\r\n  ModalGenericDialogController,\r\n  MyTaxcardsController,\r\n  NaviController,\r\n  NewPaymentController,\r\n  ODataActionsController,\r\n  ODataHelperController,\r\n  ODataQueryController,\r\n  OmapalkkaController,\r\n  OwnerSettingsController,\r\n  PartnerController,\r\n  PayCertificateController,\r\n  PaymentChannelController,\r\n  PaymentController,\r\n  PaymentChannelSettingsController,\r\n  PayrollCrudController,\r\n  Payroll4AssistantController,\r\n  Payroll4CrudController,\r\n  PayStatsReportQueryController,\r\n  PalkkausPersonalPaymentOverviewController,\r\n  PersonAccountController,\r\n  RecordsController,\r\n  ReferenceObjectCrudController,\r\n  ReportsController,\r\n  RowTypesSettingsController,\r\n  SalaryBasesController,\r\n  SalaryDateKindController,\r\n  SalarySlipDownloadController,\r\n  SalaryReportCrudController,\r\n  SessionController,\r\n  SignatureController,\r\n  ServiceModelCrudController,\r\n  SigningController,\r\n  SmokeTestController,\r\n  SpinnerController,\r\n  SxyCodeEditorController,\r\n  SxyFormController,\r\n  SxyFormElementController,\r\n  SxyTableController,\r\n  SxyGridController,\r\n  SxyInputController,\r\n  SxySchemaEditorController,\r\n  TabController,\r\n  TabsController,\r\n  TabButtonsController,\r\n  TaxcardManualEditController,\r\n  TaxcardCrudController,\r\n  TaxcardIncomeLogController,\r\n  TemplateCrudController,\r\n  ToggleButtonsController,\r\n  UiTranslatorController,\r\n  UsecasesCrudController,\r\n  VarmaBannerController,\r\n  WelcomeController,\r\n  WizardController,\r\n  WorkerAbsencesCrudController,\r\n  WorkerAccountCrudController,\r\n  WorkerAssureController,\r\n  WorkerExpenseReportController,\r\n  WorkerHourlyReportController,\r\n  WorkerImportController,\r\n  WorkerOnboardingController,\r\n  WorkerReportController,\r\n  WorkerSummaryReportController,\r\n  WorkerSummaryReportDisplayController,\r\n  WorkerTimerController,\r\n  WorkflowController,\r\n  WorkflowBadgeController,\r\n  SummaryReportDisplayController,\r\n  SummaryReportController,\r\n  SummaryReportQueryController,\r\n  TimesheetWorkerDemoController,\r\n  ValidationSummaryController\r\n} from \".\";\r\nimport { CalcLeavesController } from \"./calc/CalcLeavesController\";\r\n\r\n/**\r\n * Provides methods for registering the Controllers to module\r\n * (and other related metadata in the future).\r\n */\r\nexport class ControllersRegistration {\r\n\r\n  /** Gets the controllers for Module registration. */\r\n  public static getControllers () {\r\n    return {\r\n      AbsencePeriodsController,\r\n      AccountantController,\r\n      AccountantWizardController,\r\n      AccountingChannelSettingsController,\r\n      AccountAuthorizationController,\r\n      AccountingHolidayPayDebtReportQueryController,\r\n      AccountingReportCrudController,\r\n      AccountingReportDisplayController,\r\n      AccountingReportQueryController,\r\n      AccountingReportRowsController,\r\n      AccountingReportToolsController,\r\n      AccountingRowReportController,\r\n      AccountingTargetCrudController,\r\n      AccountResetController,\r\n      ActionButtonController,\r\n      AlertController,\r\n      AvatarController,\r\n      BatchProcessController,\r\n      CalcChartController,\r\n      CalcCostAccountingController,\r\n      CalcEmploymentController,\r\n      CalcHouseholdUsecaseController,\r\n      CalcImportController,\r\n      CalcIrRowsController,\r\n      CalcsIrRowsController,\r\n      CalcWorktimeController,\r\n      CalcRepairController,\r\n      CalcRepairInfoController,\r\n      CalcReportController,\r\n      CalcReportsController,\r\n      CalcReportsDisplayController,\r\n      CalcRowCostAccountingController,\r\n      CalcRowDimensionInputController,\r\n      CalcRowDocumentationController,\r\n      CalcRowFormulaController,\r\n      CalcRowTypeController,\r\n      CalcRows2019Controller,\r\n      CalcSharingController,\r\n      CalcSharingReceiptActionController,\r\n      CalculationCrudController,\r\n      CalculationEditorController,\r\n      CalculationReportController,\r\n      Calculator2019Controller,\r\n      Calculator2022Controller,\r\n      CalcLeavesController,\r\n      CalendarController,\r\n      CalendarEventsCrudController,\r\n      CertificateController,\r\n      ChartController,\r\n      CompanyAccountController,\r\n      CompanyInvoicesController,\r\n      CompanyImportController,\r\n      CompanyOnboardingController,\r\n      CompanySettingsController,\r\n      ContactInfoController,\r\n      CostAccountingController,\r\n      CredentialController,\r\n      CreditTransferController,\r\n      CustomerInvoiceCrudController,\r\n      CustomerOnboardingController,\r\n      DatasetsCrudController,\r\n      DatepickerController,\r\n      DatepickerPopupController,\r\n      DateRangeController,\r\n      EditDialogController,\r\n      EmbeddedUiController,\r\n      EmployerListController,\r\n      EmployerReportController,\r\n      EmployerSelectController,\r\n      EmploymentCrudController,\r\n      EmploymentTaxcardsController,\r\n      EmploymentWizardController,\r\n      ExportController,\r\n      HolidayPayReportQueryController,\r\n      HolidayReportController,\r\n      HolidayYearAccrualController,\r\n      HolidayYearCrudController,\r\n      HolidayYearHolidaysController,\r\n      HolidayYearPaidController,\r\n      HouseholdDeductionReportController,\r\n      HouseholdOnboardingController,\r\n      HouseholdYearCrudController,\r\n      ImportController,\r\n      ImportStagingController,\r\n      InputBooleanController,\r\n      InputCollectiveBargainAgreementController,\r\n      InputCredentialController,\r\n      InputDurationController,\r\n      InputEmployeeGroupController,\r\n      InputEnumController,\r\n      InputHolidayMultipliersController,\r\n      InputPayStatsRowTypeController,\r\n      InputIncomeTypeController,\r\n      InputNumberController,\r\n      InputRruleController,\r\n      InputTimeController,\r\n      InputTypeaheadController,\r\n      InsuranceWizardController,\r\n      InvoiceCrudController,\r\n      InvoicesCreateController,\r\n      InvoiceReportController,\r\n      InvoiceSepaController,\r\n      InvoiceToolsController,\r\n      InvoiceAlertsController,\r\n      InvoicePaymentListController,\r\n      IrEarningsPaymentCrudController,\r\n      IrPayerSummaryCrudController,\r\n      JsonFormatterController,\r\n      JsonDiffController,\r\n      MarkdownEditorController,\r\n      MarkdownViewerController,\r\n      MessageThreadCrudController,\r\n      ModalGenericDialogController,\r\n      MyTaxcardsController,\r\n      NaviController,\r\n      NewPaymentController,\r\n      ODataActionsController,\r\n      ODataHelperController,\r\n      ODataQueryController,\r\n      OmapalkkaController,\r\n      OwnerSettingsController,\r\n      PartnerController,\r\n      PayCertificateController,\r\n      PaymentController,\r\n      PaymentChannelController,\r\n      PaymentChannelSettingsController,\r\n      PayrollCrudController,\r\n      Payroll4AssistantController,\r\n      Payroll4CrudController,\r\n      PayStatsReportQueryController,\r\n      PalkkausPersonalPaymentOverviewController,\r\n      PersonAccountController,\r\n      RecordsController,\r\n      ReferenceObjectCrudController,\r\n      ReportsController,\r\n      RowTypesSettingsController,\r\n      SalaryBasesController,\r\n      SalaryDateKindController,\r\n      SalarySlipDownloadController,\r\n      SalaryReportCrudController,\r\n      SessionController,\r\n      ServiceModelCrudController,\r\n      SignatureController,\r\n      SigningController,\r\n      SmokeTestController,\r\n      SpinnerController,\r\n      SummaryReportController,\r\n      SummaryReportDisplayController,\r\n      SummaryReportQueryController,\r\n      SxyCodeEditorController,\r\n      SxyFormController,\r\n      SxyFormElementController,\r\n      SxyTableController,\r\n      SxyGridController,\r\n      SxyInputController,\r\n      SxySchemaEditorController,\r\n      TabController,\r\n      TabsController,\r\n      TabButtonsController,\r\n      TaxcardManualEditController,\r\n      TaxcardCrudController,\r\n      TaxcardIncomeLogController,\r\n      TemplateCrudController,\r\n      ToggleButtonsController,\r\n      UiTranslatorController,\r\n      UsecasesCrudController,\r\n      VarmaBannerController,\r\n      WelcomeController,\r\n      WizardController,\r\n      WorkerAbsencesCrudController,\r\n      WorkerAccountCrudController,\r\n      WorkerAssureController,\r\n      WorkerExpenseReportController,\r\n      WorkerHourlyReportController,\r\n      WorkerImportController,\r\n      WorkerOnboardingController,\r\n      WorkerReportController,\r\n      WorkerSummaryReportController,\r\n      WorkerSummaryReportDisplayController,\r\n      WorkerTimerController,\r\n      WorkflowController,\r\n      WorkflowBadgeController,\r\n      TimesheetWorkerDemoController,\r\n      ValidationSummaryController\r\n    };\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\n/**\r\n * Appends the given element to the current element.\r\n * The existing element will be removed from the source parent element.\r\n * The attribute value should resolve to an existing DOM node or string.\r\n * @example\r\n * ```html\r\n * <div salaxy-append-node=\"tab.headingElement\"></div>\r\n * ```\r\n */\r\nexport class AppendNodeDirective implements angular.IDirective {\r\n\r\n    /**\r\n     * Factory for directive registration.\r\n     * @ignore\r\n     */\r\n    public static salaxyAppendNode() {\r\n        const factory = () => new AppendNodeDirective();\r\n        factory.$inject = [];\r\n        return factory;\r\n    }\r\n\r\n    /**\r\n     * Applies to attributes only.\r\n     * @ignore\r\n     */\r\n    public restrict = \"A\";\r\n\r\n   /**\r\n    * Creates a new instance of the directive.\r\n    */\r\n    constructor() {\r\n        // initialization\r\n     }\r\n\r\n   /**\r\n    * Evaluates the attribute value (DOM node or default string), and appends it to the current element.\r\n    * @ignore\r\n    */\r\n    public link(scope: any, element: any, attrs: any) {\r\n      const node = scope.$eval(attrs.salaxyAppendNode);\r\n      element.append(node);\r\n    }\r\n}\r\n","/*!\n  * Bootstrap v5.3.3 (https://getbootstrap.com/)\n  * Copyright 2011-2024 The Bootstrap Authors (https://github.com/twbs/bootstrap/graphs/contributors)\n  * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n  */\nimport * as Popper from '@popperjs/core';\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap dom/data.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\n/**\n * Constants\n */\n\nconst elementMap = new Map();\nconst Data = {\n  set(element, key, instance) {\n    if (!elementMap.has(element)) {\n      elementMap.set(element, new Map());\n    }\n    const instanceMap = elementMap.get(element);\n\n    // make it clear we only want one instance per element\n    // can be removed later when multiple key/instances are fine to be used\n    if (!instanceMap.has(key) && instanceMap.size !== 0) {\n      // eslint-disable-next-line no-console\n      console.error(`Bootstrap doesn't allow more than one instance per element. Bound instance: ${Array.from(instanceMap.keys())[0]}.`);\n      return;\n    }\n    instanceMap.set(key, instance);\n  },\n  get(element, key) {\n    if (elementMap.has(element)) {\n      return elementMap.get(element).get(key) || null;\n    }\n    return null;\n  },\n  remove(element, key) {\n    if (!elementMap.has(element)) {\n      return;\n    }\n    const instanceMap = elementMap.get(element);\n    instanceMap.delete(key);\n\n    // free up element references if there are no instances left for an element\n    if (instanceMap.size === 0) {\n      elementMap.delete(element);\n    }\n  }\n};\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap util/index.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\nconst MAX_UID = 1000000;\nconst MILLISECONDS_MULTIPLIER = 1000;\nconst TRANSITION_END = 'transitionend';\n\n/**\n * Properly escape IDs selectors to handle weird IDs\n * @param {string} selector\n * @returns {string}\n */\nconst parseSelector = selector => {\n  if (selector && window.CSS && window.CSS.escape) {\n    // document.querySelector needs escaping to handle IDs (html5+) containing for instance /\n    selector = selector.replace(/#([^\\s\"#']+)/g, (match, id) => `#${CSS.escape(id)}`);\n  }\n  return selector;\n};\n\n// Shout-out Angus Croll (https://goo.gl/pxwQGp)\nconst toType = object => {\n  if (object === null || object === undefined) {\n    return `${object}`;\n  }\n  return Object.prototype.toString.call(object).match(/\\s([a-z]+)/i)[1].toLowerCase();\n};\n\n/**\n * Public Util API\n */\n\nconst getUID = prefix => {\n  do {\n    prefix += Math.floor(Math.random() * MAX_UID);\n  } while (document.getElementById(prefix));\n  return prefix;\n};\nconst getTransitionDurationFromElement = element => {\n  if (!element) {\n    return 0;\n  }\n\n  // Get transition-duration of the element\n  let {\n    transitionDuration,\n    transitionDelay\n  } = window.getComputedStyle(element);\n  const floatTransitionDuration = Number.parseFloat(transitionDuration);\n  const floatTransitionDelay = Number.parseFloat(transitionDelay);\n\n  // Return 0 if element or transition duration is not found\n  if (!floatTransitionDuration && !floatTransitionDelay) {\n    return 0;\n  }\n\n  // If multiple durations are defined, take the first\n  transitionDuration = transitionDuration.split(',')[0];\n  transitionDelay = transitionDelay.split(',')[0];\n  return (Number.parseFloat(transitionDuration) + Number.parseFloat(transitionDelay)) * MILLISECONDS_MULTIPLIER;\n};\nconst triggerTransitionEnd = element => {\n  element.dispatchEvent(new Event(TRANSITION_END));\n};\nconst isElement = object => {\n  if (!object || typeof object !== 'object') {\n    return false;\n  }\n  if (typeof object.jquery !== 'undefined') {\n    object = object[0];\n  }\n  return typeof object.nodeType !== 'undefined';\n};\nconst getElement = object => {\n  // it's a jQuery object or a node element\n  if (isElement(object)) {\n    return object.jquery ? object[0] : object;\n  }\n  if (typeof object === 'string' && object.length > 0) {\n    return document.querySelector(parseSelector(object));\n  }\n  return null;\n};\nconst isVisible = element => {\n  if (!isElement(element) || element.getClientRects().length === 0) {\n    return false;\n  }\n  const elementIsVisible = getComputedStyle(element).getPropertyValue('visibility') === 'visible';\n  // Handle `details` element as its content may falsie appear visible when it is closed\n  const closedDetails = element.closest('details:not([open])');\n  if (!closedDetails) {\n    return elementIsVisible;\n  }\n  if (closedDetails !== element) {\n    const summary = element.closest('summary');\n    if (summary && summary.parentNode !== closedDetails) {\n      return false;\n    }\n    if (summary === null) {\n      return false;\n    }\n  }\n  return elementIsVisible;\n};\nconst isDisabled = element => {\n  if (!element || element.nodeType !== Node.ELEMENT_NODE) {\n    return true;\n  }\n  if (element.classList.contains('disabled')) {\n    return true;\n  }\n  if (typeof element.disabled !== 'undefined') {\n    return element.disabled;\n  }\n  return element.hasAttribute('disabled') && element.getAttribute('disabled') !== 'false';\n};\nconst findShadowRoot = element => {\n  if (!document.documentElement.attachShadow) {\n    return null;\n  }\n\n  // Can find the shadow root otherwise it'll return the document\n  if (typeof element.getRootNode === 'function') {\n    const root = element.getRootNode();\n    return root instanceof ShadowRoot ? root : null;\n  }\n  if (element instanceof ShadowRoot) {\n    return element;\n  }\n\n  // when we don't find a shadow root\n  if (!element.parentNode) {\n    return null;\n  }\n  return findShadowRoot(element.parentNode);\n};\nconst noop = () => {};\n\n/**\n * Trick to restart an element's animation\n *\n * @param {HTMLElement} element\n * @return void\n *\n * @see https://www.charistheo.io/blog/2021/02/restart-a-css-animation-with-javascript/#restarting-a-css-animation\n */\nconst reflow = element => {\n  element.offsetHeight; // eslint-disable-line no-unused-expressions\n};\nconst getjQuery = () => {\n  if (window.jQuery && !document.body.hasAttribute('data-bs-no-jquery')) {\n    return window.jQuery;\n  }\n  return null;\n};\nconst DOMContentLoadedCallbacks = [];\nconst onDOMContentLoaded = callback => {\n  if (document.readyState === 'loading') {\n    // add listener on the first call when the document is in loading state\n    if (!DOMContentLoadedCallbacks.length) {\n      document.addEventListener('DOMContentLoaded', () => {\n        for (const callback of DOMContentLoadedCallbacks) {\n          callback();\n        }\n      });\n    }\n    DOMContentLoadedCallbacks.push(callback);\n  } else {\n    callback();\n  }\n};\nconst isRTL = () => document.documentElement.dir === 'rtl';\nconst defineJQueryPlugin = plugin => {\n  onDOMContentLoaded(() => {\n    const $ = getjQuery();\n    /* istanbul ignore if */\n    if ($) {\n      const name = plugin.NAME;\n      const JQUERY_NO_CONFLICT = $.fn[name];\n      $.fn[name] = plugin.jQueryInterface;\n      $.fn[name].Constructor = plugin;\n      $.fn[name].noConflict = () => {\n        $.fn[name] = JQUERY_NO_CONFLICT;\n        return plugin.jQueryInterface;\n      };\n    }\n  });\n};\nconst execute = (possibleCallback, args = [], defaultValue = possibleCallback) => {\n  return typeof possibleCallback === 'function' ? possibleCallback(...args) : defaultValue;\n};\nconst executeAfterTransition = (callback, transitionElement, waitForTransition = true) => {\n  if (!waitForTransition) {\n    execute(callback);\n    return;\n  }\n  const durationPadding = 5;\n  const emulatedDuration = getTransitionDurationFromElement(transitionElement) + durationPadding;\n  let called = false;\n  const handler = ({\n    target\n  }) => {\n    if (target !== transitionElement) {\n      return;\n    }\n    called = true;\n    transitionElement.removeEventListener(TRANSITION_END, handler);\n    execute(callback);\n  };\n  transitionElement.addEventListener(TRANSITION_END, handler);\n  setTimeout(() => {\n    if (!called) {\n      triggerTransitionEnd(transitionElement);\n    }\n  }, emulatedDuration);\n};\n\n/**\n * Return the previous/next element of a list.\n *\n * @param {array} list    The list of elements\n * @param activeElement   The active element\n * @param shouldGetNext   Choose to get next or previous element\n * @param isCycleAllowed\n * @return {Element|elem} The proper element\n */\nconst getNextActiveElement = (list, activeElement, shouldGetNext, isCycleAllowed) => {\n  const listLength = list.length;\n  let index = list.indexOf(activeElement);\n\n  // if the element does not exist in the list return an element\n  // depending on the direction and if cycle is allowed\n  if (index === -1) {\n    return !shouldGetNext && isCycleAllowed ? list[listLength - 1] : list[0];\n  }\n  index += shouldGetNext ? 1 : -1;\n  if (isCycleAllowed) {\n    index = (index + listLength) % listLength;\n  }\n  return list[Math.max(0, Math.min(index, listLength - 1))];\n};\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap dom/event-handler.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\n\n/**\n * Constants\n */\n\nconst namespaceRegex = /[^.]*(?=\\..*)\\.|.*/;\nconst stripNameRegex = /\\..*/;\nconst stripUidRegex = /::\\d+$/;\nconst eventRegistry = {}; // Events storage\nlet uidEvent = 1;\nconst customEvents = {\n  mouseenter: 'mouseover',\n  mouseleave: 'mouseout'\n};\nconst nativeEvents = new Set(['click', 'dblclick', 'mouseup', 'mousedown', 'contextmenu', 'mousewheel', 'DOMMouseScroll', 'mouseover', 'mouseout', 'mousemove', 'selectstart', 'selectend', 'keydown', 'keypress', 'keyup', 'orientationchange', 'touchstart', 'touchmove', 'touchend', 'touchcancel', 'pointerdown', 'pointermove', 'pointerup', 'pointerleave', 'pointercancel', 'gesturestart', 'gesturechange', 'gestureend', 'focus', 'blur', 'change', 'reset', 'select', 'submit', 'focusin', 'focusout', 'load', 'unload', 'beforeunload', 'resize', 'move', 'DOMContentLoaded', 'readystatechange', 'error', 'abort', 'scroll']);\n\n/**\n * Private methods\n */\n\nfunction makeEventUid(element, uid) {\n  return uid && `${uid}::${uidEvent++}` || element.uidEvent || uidEvent++;\n}\nfunction getElementEvents(element) {\n  const uid = makeEventUid(element);\n  element.uidEvent = uid;\n  eventRegistry[uid] = eventRegistry[uid] || {};\n  return eventRegistry[uid];\n}\nfunction bootstrapHandler(element, fn) {\n  return function handler(event) {\n    hydrateObj(event, {\n      delegateTarget: element\n    });\n    if (handler.oneOff) {\n      EventHandler.off(element, event.type, fn);\n    }\n    return fn.apply(element, [event]);\n  };\n}\nfunction bootstrapDelegationHandler(element, selector, fn) {\n  return function handler(event) {\n    const domElements = element.querySelectorAll(selector);\n    for (let {\n      target\n    } = event; target && target !== this; target = target.parentNode) {\n      for (const domElement of domElements) {\n        if (domElement !== target) {\n          continue;\n        }\n        hydrateObj(event, {\n          delegateTarget: target\n        });\n        if (handler.oneOff) {\n          EventHandler.off(element, event.type, selector, fn);\n        }\n        return fn.apply(target, [event]);\n      }\n    }\n  };\n}\nfunction findHandler(events, callable, delegationSelector = null) {\n  return Object.values(events).find(event => event.callable === callable && event.delegationSelector === delegationSelector);\n}\nfunction normalizeParameters(originalTypeEvent, handler, delegationFunction) {\n  const isDelegated = typeof handler === 'string';\n  // TODO: tooltip passes `false` instead of selector, so we need to check\n  const callable = isDelegated ? delegationFunction : handler || delegationFunction;\n  let typeEvent = getTypeEvent(originalTypeEvent);\n  if (!nativeEvents.has(typeEvent)) {\n    typeEvent = originalTypeEvent;\n  }\n  return [isDelegated, callable, typeEvent];\n}\nfunction addHandler(element, originalTypeEvent, handler, delegationFunction, oneOff) {\n  if (typeof originalTypeEvent !== 'string' || !element) {\n    return;\n  }\n  let [isDelegated, callable, typeEvent] = normalizeParameters(originalTypeEvent, handler, delegationFunction);\n\n  // in case of mouseenter or mouseleave wrap the handler within a function that checks for its DOM position\n  // this prevents the handler from being dispatched the same way as mouseover or mouseout does\n  if (originalTypeEvent in customEvents) {\n    const wrapFunction = fn => {\n      return function (event) {\n        if (!event.relatedTarget || event.relatedTarget !== event.delegateTarget && !event.delegateTarget.contains(event.relatedTarget)) {\n          return fn.call(this, event);\n        }\n      };\n    };\n    callable = wrapFunction(callable);\n  }\n  const events = getElementEvents(element);\n  const handlers = events[typeEvent] || (events[typeEvent] = {});\n  const previousFunction = findHandler(handlers, callable, isDelegated ? handler : null);\n  if (previousFunction) {\n    previousFunction.oneOff = previousFunction.oneOff && oneOff;\n    return;\n  }\n  const uid = makeEventUid(callable, originalTypeEvent.replace(namespaceRegex, ''));\n  const fn = isDelegated ? bootstrapDelegationHandler(element, handler, callable) : bootstrapHandler(element, callable);\n  fn.delegationSelector = isDelegated ? handler : null;\n  fn.callable = callable;\n  fn.oneOff = oneOff;\n  fn.uidEvent = uid;\n  handlers[uid] = fn;\n  element.addEventListener(typeEvent, fn, isDelegated);\n}\nfunction removeHandler(element, events, typeEvent, handler, delegationSelector) {\n  const fn = findHandler(events[typeEvent], handler, delegationSelector);\n  if (!fn) {\n    return;\n  }\n  element.removeEventListener(typeEvent, fn, Boolean(delegationSelector));\n  delete events[typeEvent][fn.uidEvent];\n}\nfunction removeNamespacedHandlers(element, events, typeEvent, namespace) {\n  const storeElementEvent = events[typeEvent] || {};\n  for (const [handlerKey, event] of Object.entries(storeElementEvent)) {\n    if (handlerKey.includes(namespace)) {\n      removeHandler(element, events, typeEvent, event.callable, event.delegationSelector);\n    }\n  }\n}\nfunction getTypeEvent(event) {\n  // allow to get the native events from namespaced events ('click.bs.button' --> 'click')\n  event = event.replace(stripNameRegex, '');\n  return customEvents[event] || event;\n}\nconst EventHandler = {\n  on(element, event, handler, delegationFunction) {\n    addHandler(element, event, handler, delegationFunction, false);\n  },\n  one(element, event, handler, delegationFunction) {\n    addHandler(element, event, handler, delegationFunction, true);\n  },\n  off(element, originalTypeEvent, handler, delegationFunction) {\n    if (typeof originalTypeEvent !== 'string' || !element) {\n      return;\n    }\n    const [isDelegated, callable, typeEvent] = normalizeParameters(originalTypeEvent, handler, delegationFunction);\n    const inNamespace = typeEvent !== originalTypeEvent;\n    const events = getElementEvents(element);\n    const storeElementEvent = events[typeEvent] || {};\n    const isNamespace = originalTypeEvent.startsWith('.');\n    if (typeof callable !== 'undefined') {\n      // Simplest case: handler is passed, remove that listener ONLY.\n      if (!Object.keys(storeElementEvent).length) {\n        return;\n      }\n      removeHandler(element, events, typeEvent, callable, isDelegated ? handler : null);\n      return;\n    }\n    if (isNamespace) {\n      for (const elementEvent of Object.keys(events)) {\n        removeNamespacedHandlers(element, events, elementEvent, originalTypeEvent.slice(1));\n      }\n    }\n    for (const [keyHandlers, event] of Object.entries(storeElementEvent)) {\n      const handlerKey = keyHandlers.replace(stripUidRegex, '');\n      if (!inNamespace || originalTypeEvent.includes(handlerKey)) {\n        removeHandler(element, events, typeEvent, event.callable, event.delegationSelector);\n      }\n    }\n  },\n  trigger(element, event, args) {\n    if (typeof event !== 'string' || !element) {\n      return null;\n    }\n    const $ = getjQuery();\n    const typeEvent = getTypeEvent(event);\n    const inNamespace = event !== typeEvent;\n    let jQueryEvent = null;\n    let bubbles = true;\n    let nativeDispatch = true;\n    let defaultPrevented = false;\n    if (inNamespace && $) {\n      jQueryEvent = $.Event(event, args);\n      $(element).trigger(jQueryEvent);\n      bubbles = !jQueryEvent.isPropagationStopped();\n      nativeDispatch = !jQueryEvent.isImmediatePropagationStopped();\n      defaultPrevented = jQueryEvent.isDefaultPrevented();\n    }\n    const evt = hydrateObj(new Event(event, {\n      bubbles,\n      cancelable: true\n    }), args);\n    if (defaultPrevented) {\n      evt.preventDefault();\n    }\n    if (nativeDispatch) {\n      element.dispatchEvent(evt);\n    }\n    if (evt.defaultPrevented && jQueryEvent) {\n      jQueryEvent.preventDefault();\n    }\n    return evt;\n  }\n};\nfunction hydrateObj(obj, meta = {}) {\n  for (const [key, value] of Object.entries(meta)) {\n    try {\n      obj[key] = value;\n    } catch (_unused) {\n      Object.defineProperty(obj, key, {\n        configurable: true,\n        get() {\n          return value;\n        }\n      });\n    }\n  }\n  return obj;\n}\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap dom/manipulator.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\nfunction normalizeData(value) {\n  if (value === 'true') {\n    return true;\n  }\n  if (value === 'false') {\n    return false;\n  }\n  if (value === Number(value).toString()) {\n    return Number(value);\n  }\n  if (value === '' || value === 'null') {\n    return null;\n  }\n  if (typeof value !== 'string') {\n    return value;\n  }\n  try {\n    return JSON.parse(decodeURIComponent(value));\n  } catch (_unused) {\n    return value;\n  }\n}\nfunction normalizeDataKey(key) {\n  return key.replace(/[A-Z]/g, chr => `-${chr.toLowerCase()}`);\n}\nconst Manipulator = {\n  setDataAttribute(element, key, value) {\n    element.setAttribute(`data-bs-${normalizeDataKey(key)}`, value);\n  },\n  removeDataAttribute(element, key) {\n    element.removeAttribute(`data-bs-${normalizeDataKey(key)}`);\n  },\n  getDataAttributes(element) {\n    if (!element) {\n      return {};\n    }\n    const attributes = {};\n    const bsKeys = Object.keys(element.dataset).filter(key => key.startsWith('bs') && !key.startsWith('bsConfig'));\n    for (const key of bsKeys) {\n      let pureKey = key.replace(/^bs/, '');\n      pureKey = pureKey.charAt(0).toLowerCase() + pureKey.slice(1, pureKey.length);\n      attributes[pureKey] = normalizeData(element.dataset[key]);\n    }\n    return attributes;\n  },\n  getDataAttribute(element, key) {\n    return normalizeData(element.getAttribute(`data-bs-${normalizeDataKey(key)}`));\n  }\n};\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap util/config.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\n\n/**\n * Class definition\n */\n\nclass Config {\n  // Getters\n  static get Default() {\n    return {};\n  }\n  static get DefaultType() {\n    return {};\n  }\n  static get NAME() {\n    throw new Error('You have to implement the static method \"NAME\", for each component!');\n  }\n  _getConfig(config) {\n    config = this._mergeConfigObj(config);\n    config = this._configAfterMerge(config);\n    this._typeCheckConfig(config);\n    return config;\n  }\n  _configAfterMerge(config) {\n    return config;\n  }\n  _mergeConfigObj(config, element) {\n    const jsonConfig = isElement(element) ? Manipulator.getDataAttribute(element, 'config') : {}; // try to parse\n\n    return {\n      ...this.constructor.Default,\n      ...(typeof jsonConfig === 'object' ? jsonConfig : {}),\n      ...(isElement(element) ? Manipulator.getDataAttributes(element) : {}),\n      ...(typeof config === 'object' ? config : {})\n    };\n  }\n  _typeCheckConfig(config, configTypes = this.constructor.DefaultType) {\n    for (const [property, expectedTypes] of Object.entries(configTypes)) {\n      const value = config[property];\n      const valueType = isElement(value) ? 'element' : toType(value);\n      if (!new RegExp(expectedTypes).test(valueType)) {\n        throw new TypeError(`${this.constructor.NAME.toUpperCase()}: Option \"${property}\" provided type \"${valueType}\" but expected type \"${expectedTypes}\".`);\n      }\n    }\n  }\n}\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap base-component.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\n\n/**\n * Constants\n */\n\nconst VERSION = '5.3.3';\n\n/**\n * Class definition\n */\n\nclass BaseComponent extends Config {\n  constructor(element, config) {\n    super();\n    element = getElement(element);\n    if (!element) {\n      return;\n    }\n    this._element = element;\n    this._config = this._getConfig(config);\n    Data.set(this._element, this.constructor.DATA_KEY, this);\n  }\n\n  // Public\n  dispose() {\n    Data.remove(this._element, this.constructor.DATA_KEY);\n    EventHandler.off(this._element, this.constructor.EVENT_KEY);\n    for (const propertyName of Object.getOwnPropertyNames(this)) {\n      this[propertyName] = null;\n    }\n  }\n  _queueCallback(callback, element, isAnimated = true) {\n    executeAfterTransition(callback, element, isAnimated);\n  }\n  _getConfig(config) {\n    config = this._mergeConfigObj(config, this._element);\n    config = this._configAfterMerge(config);\n    this._typeCheckConfig(config);\n    return config;\n  }\n\n  // Static\n  static getInstance(element) {\n    return Data.get(getElement(element), this.DATA_KEY);\n  }\n  static getOrCreateInstance(element, config = {}) {\n    return this.getInstance(element) || new this(element, typeof config === 'object' ? config : null);\n  }\n  static get VERSION() {\n    return VERSION;\n  }\n  static get DATA_KEY() {\n    return `bs.${this.NAME}`;\n  }\n  static get EVENT_KEY() {\n    return `.${this.DATA_KEY}`;\n  }\n  static eventName(name) {\n    return `${name}${this.EVENT_KEY}`;\n  }\n}\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap dom/selector-engine.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\nconst getSelector = element => {\n  let selector = element.getAttribute('data-bs-target');\n  if (!selector || selector === '#') {\n    let hrefAttribute = element.getAttribute('href');\n\n    // The only valid content that could double as a selector are IDs or classes,\n    // so everything starting with `#` or `.`. If a \"real\" URL is used as the selector,\n    // `document.querySelector` will rightfully complain it is invalid.\n    // See https://github.com/twbs/bootstrap/issues/32273\n    if (!hrefAttribute || !hrefAttribute.includes('#') && !hrefAttribute.startsWith('.')) {\n      return null;\n    }\n\n    // Just in case some CMS puts out a full URL with the anchor appended\n    if (hrefAttribute.includes('#') && !hrefAttribute.startsWith('#')) {\n      hrefAttribute = `#${hrefAttribute.split('#')[1]}`;\n    }\n    selector = hrefAttribute && hrefAttribute !== '#' ? hrefAttribute.trim() : null;\n  }\n  return selector ? selector.split(',').map(sel => parseSelector(sel)).join(',') : null;\n};\nconst SelectorEngine = {\n  find(selector, element = document.documentElement) {\n    return [].concat(...Element.prototype.querySelectorAll.call(element, selector));\n  },\n  findOne(selector, element = document.documentElement) {\n    return Element.prototype.querySelector.call(element, selector);\n  },\n  children(element, selector) {\n    return [].concat(...element.children).filter(child => child.matches(selector));\n  },\n  parents(element, selector) {\n    const parents = [];\n    let ancestor = element.parentNode.closest(selector);\n    while (ancestor) {\n      parents.push(ancestor);\n      ancestor = ancestor.parentNode.closest(selector);\n    }\n    return parents;\n  },\n  prev(element, selector) {\n    let previous = element.previousElementSibling;\n    while (previous) {\n      if (previous.matches(selector)) {\n        return [previous];\n      }\n      previous = previous.previousElementSibling;\n    }\n    return [];\n  },\n  // TODO: this is now unused; remove later along with prev()\n  next(element, selector) {\n    let next = element.nextElementSibling;\n    while (next) {\n      if (next.matches(selector)) {\n        return [next];\n      }\n      next = next.nextElementSibling;\n    }\n    return [];\n  },\n  focusableChildren(element) {\n    const focusables = ['a', 'button', 'input', 'textarea', 'select', 'details', '[tabindex]', '[contenteditable=\"true\"]'].map(selector => `${selector}:not([tabindex^=\"-\"])`).join(',');\n    return this.find(focusables, element).filter(el => !isDisabled(el) && isVisible(el));\n  },\n  getSelectorFromElement(element) {\n    const selector = getSelector(element);\n    if (selector) {\n      return SelectorEngine.findOne(selector) ? selector : null;\n    }\n    return null;\n  },\n  getElementFromSelector(element) {\n    const selector = getSelector(element);\n    return selector ? SelectorEngine.findOne(selector) : null;\n  },\n  getMultipleElementsFromSelector(element) {\n    const selector = getSelector(element);\n    return selector ? SelectorEngine.find(selector) : [];\n  }\n};\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap util/component-functions.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\nconst enableDismissTrigger = (component, method = 'hide') => {\n  const clickEvent = `click.dismiss${component.EVENT_KEY}`;\n  const name = component.NAME;\n  EventHandler.on(document, clickEvent, `[data-bs-dismiss=\"${name}\"]`, function (event) {\n    if (['A', 'AREA'].includes(this.tagName)) {\n      event.preventDefault();\n    }\n    if (isDisabled(this)) {\n      return;\n    }\n    const target = SelectorEngine.getElementFromSelector(this) || this.closest(`.${name}`);\n    const instance = component.getOrCreateInstance(target);\n\n    // Method argument is left, for Alert and only, as it doesn't implement the 'hide' method\n    instance[method]();\n  });\n};\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap alert.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\n\n/**\n * Constants\n */\n\nconst NAME$f = 'alert';\nconst DATA_KEY$a = 'bs.alert';\nconst EVENT_KEY$b = `.${DATA_KEY$a}`;\nconst EVENT_CLOSE = `close${EVENT_KEY$b}`;\nconst EVENT_CLOSED = `closed${EVENT_KEY$b}`;\nconst CLASS_NAME_FADE$5 = 'fade';\nconst CLASS_NAME_SHOW$8 = 'show';\n\n/**\n * Class definition\n */\n\nclass Alert extends BaseComponent {\n  // Getters\n  static get NAME() {\n    return NAME$f;\n  }\n\n  // Public\n  close() {\n    const closeEvent = EventHandler.trigger(this._element, EVENT_CLOSE);\n    if (closeEvent.defaultPrevented) {\n      return;\n    }\n    this._element.classList.remove(CLASS_NAME_SHOW$8);\n    const isAnimated = this._element.classList.contains(CLASS_NAME_FADE$5);\n    this._queueCallback(() => this._destroyElement(), this._element, isAnimated);\n  }\n\n  // Private\n  _destroyElement() {\n    this._element.remove();\n    EventHandler.trigger(this._element, EVENT_CLOSED);\n    this.dispose();\n  }\n\n  // Static\n  static jQueryInterface(config) {\n    return this.each(function () {\n      const data = Alert.getOrCreateInstance(this);\n      if (typeof config !== 'string') {\n        return;\n      }\n      if (data[config] === undefined || config.startsWith('_') || config === 'constructor') {\n        throw new TypeError(`No method named \"${config}\"`);\n      }\n      data[config](this);\n    });\n  }\n}\n\n/**\n * Data API implementation\n */\n\nenableDismissTrigger(Alert, 'close');\n\n/**\n * jQuery\n */\n\ndefineJQueryPlugin(Alert);\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap button.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\n\n/**\n * Constants\n */\n\nconst NAME$e = 'button';\nconst DATA_KEY$9 = 'bs.button';\nconst EVENT_KEY$a = `.${DATA_KEY$9}`;\nconst DATA_API_KEY$6 = '.data-api';\nconst CLASS_NAME_ACTIVE$3 = 'active';\nconst SELECTOR_DATA_TOGGLE$5 = '[data-bs-toggle=\"button\"]';\nconst EVENT_CLICK_DATA_API$6 = `click${EVENT_KEY$a}${DATA_API_KEY$6}`;\n\n/**\n * Class definition\n */\n\nclass Button extends BaseComponent {\n  // Getters\n  static get NAME() {\n    return NAME$e;\n  }\n\n  // Public\n  toggle() {\n    // Toggle class and sync the `aria-pressed` attribute with the return value of the `.toggle()` method\n    this._element.setAttribute('aria-pressed', this._element.classList.toggle(CLASS_NAME_ACTIVE$3));\n  }\n\n  // Static\n  static jQueryInterface(config) {\n    return this.each(function () {\n      const data = Button.getOrCreateInstance(this);\n      if (config === 'toggle') {\n        data[config]();\n      }\n    });\n  }\n}\n\n/**\n * Data API implementation\n */\n\nEventHandler.on(document, EVENT_CLICK_DATA_API$6, SELECTOR_DATA_TOGGLE$5, event => {\n  event.preventDefault();\n  const button = event.target.closest(SELECTOR_DATA_TOGGLE$5);\n  const data = Button.getOrCreateInstance(button);\n  data.toggle();\n});\n\n/**\n * jQuery\n */\n\ndefineJQueryPlugin(Button);\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap util/swipe.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\n\n/**\n * Constants\n */\n\nconst NAME$d = 'swipe';\nconst EVENT_KEY$9 = '.bs.swipe';\nconst EVENT_TOUCHSTART = `touchstart${EVENT_KEY$9}`;\nconst EVENT_TOUCHMOVE = `touchmove${EVENT_KEY$9}`;\nconst EVENT_TOUCHEND = `touchend${EVENT_KEY$9}`;\nconst EVENT_POINTERDOWN = `pointerdown${EVENT_KEY$9}`;\nconst EVENT_POINTERUP = `pointerup${EVENT_KEY$9}`;\nconst POINTER_TYPE_TOUCH = 'touch';\nconst POINTER_TYPE_PEN = 'pen';\nconst CLASS_NAME_POINTER_EVENT = 'pointer-event';\nconst SWIPE_THRESHOLD = 40;\nconst Default$c = {\n  endCallback: null,\n  leftCallback: null,\n  rightCallback: null\n};\nconst DefaultType$c = {\n  endCallback: '(function|null)',\n  leftCallback: '(function|null)',\n  rightCallback: '(function|null)'\n};\n\n/**\n * Class definition\n */\n\nclass Swipe extends Config {\n  constructor(element, config) {\n    super();\n    this._element = element;\n    if (!element || !Swipe.isSupported()) {\n      return;\n    }\n    this._config = this._getConfig(config);\n    this._deltaX = 0;\n    this._supportPointerEvents = Boolean(window.PointerEvent);\n    this._initEvents();\n  }\n\n  // Getters\n  static get Default() {\n    return Default$c;\n  }\n  static get DefaultType() {\n    return DefaultType$c;\n  }\n  static get NAME() {\n    return NAME$d;\n  }\n\n  // Public\n  dispose() {\n    EventHandler.off(this._element, EVENT_KEY$9);\n  }\n\n  // Private\n  _start(event) {\n    if (!this._supportPointerEvents) {\n      this._deltaX = event.touches[0].clientX;\n      return;\n    }\n    if (this._eventIsPointerPenTouch(event)) {\n      this._deltaX = event.clientX;\n    }\n  }\n  _end(event) {\n    if (this._eventIsPointerPenTouch(event)) {\n      this._deltaX = event.clientX - this._deltaX;\n    }\n    this._handleSwipe();\n    execute(this._config.endCallback);\n  }\n  _move(event) {\n    this._deltaX = event.touches && event.touches.length > 1 ? 0 : event.touches[0].clientX - this._deltaX;\n  }\n  _handleSwipe() {\n    const absDeltaX = Math.abs(this._deltaX);\n    if (absDeltaX <= SWIPE_THRESHOLD) {\n      return;\n    }\n    const direction = absDeltaX / this._deltaX;\n    this._deltaX = 0;\n    if (!direction) {\n      return;\n    }\n    execute(direction > 0 ? this._config.rightCallback : this._config.leftCallback);\n  }\n  _initEvents() {\n    if (this._supportPointerEvents) {\n      EventHandler.on(this._element, EVENT_POINTERDOWN, event => this._start(event));\n      EventHandler.on(this._element, EVENT_POINTERUP, event => this._end(event));\n      this._element.classList.add(CLASS_NAME_POINTER_EVENT);\n    } else {\n      EventHandler.on(this._element, EVENT_TOUCHSTART, event => this._start(event));\n      EventHandler.on(this._element, EVENT_TOUCHMOVE, event => this._move(event));\n      EventHandler.on(this._element, EVENT_TOUCHEND, event => this._end(event));\n    }\n  }\n  _eventIsPointerPenTouch(event) {\n    return this._supportPointerEvents && (event.pointerType === POINTER_TYPE_PEN || event.pointerType === POINTER_TYPE_TOUCH);\n  }\n\n  // Static\n  static isSupported() {\n    return 'ontouchstart' in document.documentElement || navigator.maxTouchPoints > 0;\n  }\n}\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap carousel.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\n\n/**\n * Constants\n */\n\nconst NAME$c = 'carousel';\nconst DATA_KEY$8 = 'bs.carousel';\nconst EVENT_KEY$8 = `.${DATA_KEY$8}`;\nconst DATA_API_KEY$5 = '.data-api';\nconst ARROW_LEFT_KEY$1 = 'ArrowLeft';\nconst ARROW_RIGHT_KEY$1 = 'ArrowRight';\nconst TOUCHEVENT_COMPAT_WAIT = 500; // Time for mouse compat events to fire after touch\n\nconst ORDER_NEXT = 'next';\nconst ORDER_PREV = 'prev';\nconst DIRECTION_LEFT = 'left';\nconst DIRECTION_RIGHT = 'right';\nconst EVENT_SLIDE = `slide${EVENT_KEY$8}`;\nconst EVENT_SLID = `slid${EVENT_KEY$8}`;\nconst EVENT_KEYDOWN$1 = `keydown${EVENT_KEY$8}`;\nconst EVENT_MOUSEENTER$1 = `mouseenter${EVENT_KEY$8}`;\nconst EVENT_MOUSELEAVE$1 = `mouseleave${EVENT_KEY$8}`;\nconst EVENT_DRAG_START = `dragstart${EVENT_KEY$8}`;\nconst EVENT_LOAD_DATA_API$3 = `load${EVENT_KEY$8}${DATA_API_KEY$5}`;\nconst EVENT_CLICK_DATA_API$5 = `click${EVENT_KEY$8}${DATA_API_KEY$5}`;\nconst CLASS_NAME_CAROUSEL = 'carousel';\nconst CLASS_NAME_ACTIVE$2 = 'active';\nconst CLASS_NAME_SLIDE = 'slide';\nconst CLASS_NAME_END = 'carousel-item-end';\nconst CLASS_NAME_START = 'carousel-item-start';\nconst CLASS_NAME_NEXT = 'carousel-item-next';\nconst CLASS_NAME_PREV = 'carousel-item-prev';\nconst SELECTOR_ACTIVE = '.active';\nconst SELECTOR_ITEM = '.carousel-item';\nconst SELECTOR_ACTIVE_ITEM = SELECTOR_ACTIVE + SELECTOR_ITEM;\nconst SELECTOR_ITEM_IMG = '.carousel-item img';\nconst SELECTOR_INDICATORS = '.carousel-indicators';\nconst SELECTOR_DATA_SLIDE = '[data-bs-slide], [data-bs-slide-to]';\nconst SELECTOR_DATA_RIDE = '[data-bs-ride=\"carousel\"]';\nconst KEY_TO_DIRECTION = {\n  [ARROW_LEFT_KEY$1]: DIRECTION_RIGHT,\n  [ARROW_RIGHT_KEY$1]: DIRECTION_LEFT\n};\nconst Default$b = {\n  interval: 5000,\n  keyboard: true,\n  pause: 'hover',\n  ride: false,\n  touch: true,\n  wrap: true\n};\nconst DefaultType$b = {\n  interval: '(number|boolean)',\n  // TODO:v6 remove boolean support\n  keyboard: 'boolean',\n  pause: '(string|boolean)',\n  ride: '(boolean|string)',\n  touch: 'boolean',\n  wrap: 'boolean'\n};\n\n/**\n * Class definition\n */\n\nclass Carousel extends BaseComponent {\n  constructor(element, config) {\n    super(element, config);\n    this._interval = null;\n    this._activeElement = null;\n    this._isSliding = false;\n    this.touchTimeout = null;\n    this._swipeHelper = null;\n    this._indicatorsElement = SelectorEngine.findOne(SELECTOR_INDICATORS, this._element);\n    this._addEventListeners();\n    if (this._config.ride === CLASS_NAME_CAROUSEL) {\n      this.cycle();\n    }\n  }\n\n  // Getters\n  static get Default() {\n    return Default$b;\n  }\n  static get DefaultType() {\n    return DefaultType$b;\n  }\n  static get NAME() {\n    return NAME$c;\n  }\n\n  // Public\n  next() {\n    this._slide(ORDER_NEXT);\n  }\n  nextWhenVisible() {\n    // FIXME TODO use `document.visibilityState`\n    // Don't call next when the page isn't visible\n    // or the carousel or its parent isn't visible\n    if (!document.hidden && isVisible(this._element)) {\n      this.next();\n    }\n  }\n  prev() {\n    this._slide(ORDER_PREV);\n  }\n  pause() {\n    if (this._isSliding) {\n      triggerTransitionEnd(this._element);\n    }\n    this._clearInterval();\n  }\n  cycle() {\n    this._clearInterval();\n    this._updateInterval();\n    this._interval = setInterval(() => this.nextWhenVisible(), this._config.interval);\n  }\n  _maybeEnableCycle() {\n    if (!this._config.ride) {\n      return;\n    }\n    if (this._isSliding) {\n      EventHandler.one(this._element, EVENT_SLID, () => this.cycle());\n      return;\n    }\n    this.cycle();\n  }\n  to(index) {\n    const items = this._getItems();\n    if (index > items.length - 1 || index < 0) {\n      return;\n    }\n    if (this._isSliding) {\n      EventHandler.one(this._element, EVENT_SLID, () => this.to(index));\n      return;\n    }\n    const activeIndex = this._getItemIndex(this._getActive());\n    if (activeIndex === index) {\n      return;\n    }\n    const order = index > activeIndex ? ORDER_NEXT : ORDER_PREV;\n    this._slide(order, items[index]);\n  }\n  dispose() {\n    if (this._swipeHelper) {\n      this._swipeHelper.dispose();\n    }\n    super.dispose();\n  }\n\n  // Private\n  _configAfterMerge(config) {\n    config.defaultInterval = config.interval;\n    return config;\n  }\n  _addEventListeners() {\n    if (this._config.keyboard) {\n      EventHandler.on(this._element, EVENT_KEYDOWN$1, event => this._keydown(event));\n    }\n    if (this._config.pause === 'hover') {\n      EventHandler.on(this._element, EVENT_MOUSEENTER$1, () => this.pause());\n      EventHandler.on(this._element, EVENT_MOUSELEAVE$1, () => this._maybeEnableCycle());\n    }\n    if (this._config.touch && Swipe.isSupported()) {\n      this._addTouchEventListeners();\n    }\n  }\n  _addTouchEventListeners() {\n    for (const img of SelectorEngine.find(SELECTOR_ITEM_IMG, this._element)) {\n      EventHandler.on(img, EVENT_DRAG_START, event => event.preventDefault());\n    }\n    const endCallBack = () => {\n      if (this._config.pause !== 'hover') {\n        return;\n      }\n\n      // If it's a touch-enabled device, mouseenter/leave are fired as\n      // part of the mouse compatibility events on first tap - the carousel\n      // would stop cycling until user tapped out of it;\n      // here, we listen for touchend, explicitly pause the carousel\n      // (as if it's the second time we tap on it, mouseenter compat event\n      // is NOT fired) and after a timeout (to allow for mouse compatibility\n      // events to fire) we explicitly restart cycling\n\n      this.pause();\n      if (this.touchTimeout) {\n        clearTimeout(this.touchTimeout);\n      }\n      this.touchTimeout = setTimeout(() => this._maybeEnableCycle(), TOUCHEVENT_COMPAT_WAIT + this._config.interval);\n    };\n    const swipeConfig = {\n      leftCallback: () => this._slide(this._directionToOrder(DIRECTION_LEFT)),\n      rightCallback: () => this._slide(this._directionToOrder(DIRECTION_RIGHT)),\n      endCallback: endCallBack\n    };\n    this._swipeHelper = new Swipe(this._element, swipeConfig);\n  }\n  _keydown(event) {\n    if (/input|textarea/i.test(event.target.tagName)) {\n      return;\n    }\n    const direction = KEY_TO_DIRECTION[event.key];\n    if (direction) {\n      event.preventDefault();\n      this._slide(this._directionToOrder(direction));\n    }\n  }\n  _getItemIndex(element) {\n    return this._getItems().indexOf(element);\n  }\n  _setActiveIndicatorElement(index) {\n    if (!this._indicatorsElement) {\n      return;\n    }\n    const activeIndicator = SelectorEngine.findOne(SELECTOR_ACTIVE, this._indicatorsElement);\n    activeIndicator.classList.remove(CLASS_NAME_ACTIVE$2);\n    activeIndicator.removeAttribute('aria-current');\n    const newActiveIndicator = SelectorEngine.findOne(`[data-bs-slide-to=\"${index}\"]`, this._indicatorsElement);\n    if (newActiveIndicator) {\n      newActiveIndicator.classList.add(CLASS_NAME_ACTIVE$2);\n      newActiveIndicator.setAttribute('aria-current', 'true');\n    }\n  }\n  _updateInterval() {\n    const element = this._activeElement || this._getActive();\n    if (!element) {\n      return;\n    }\n    const elementInterval = Number.parseInt(element.getAttribute('data-bs-interval'), 10);\n    this._config.interval = elementInterval || this._config.defaultInterval;\n  }\n  _slide(order, element = null) {\n    if (this._isSliding) {\n      return;\n    }\n    const activeElement = this._getActive();\n    const isNext = order === ORDER_NEXT;\n    const nextElement = element || getNextActiveElement(this._getItems(), activeElement, isNext, this._config.wrap);\n    if (nextElement === activeElement) {\n      return;\n    }\n    const nextElementIndex = this._getItemIndex(nextElement);\n    const triggerEvent = eventName => {\n      return EventHandler.trigger(this._element, eventName, {\n        relatedTarget: nextElement,\n        direction: this._orderToDirection(order),\n        from: this._getItemIndex(activeElement),\n        to: nextElementIndex\n      });\n    };\n    const slideEvent = triggerEvent(EVENT_SLIDE);\n    if (slideEvent.defaultPrevented) {\n      return;\n    }\n    if (!activeElement || !nextElement) {\n      // Some weirdness is happening, so we bail\n      // TODO: change tests that use empty divs to avoid this check\n      return;\n    }\n    const isCycling = Boolean(this._interval);\n    this.pause();\n    this._isSliding = true;\n    this._setActiveIndicatorElement(nextElementIndex);\n    this._activeElement = nextElement;\n    const directionalClassName = isNext ? CLASS_NAME_START : CLASS_NAME_END;\n    const orderClassName = isNext ? CLASS_NAME_NEXT : CLASS_NAME_PREV;\n    nextElement.classList.add(orderClassName);\n    reflow(nextElement);\n    activeElement.classList.add(directionalClassName);\n    nextElement.classList.add(directionalClassName);\n    const completeCallBack = () => {\n      nextElement.classList.remove(directionalClassName, orderClassName);\n      nextElement.classList.add(CLASS_NAME_ACTIVE$2);\n      activeElement.classList.remove(CLASS_NAME_ACTIVE$2, orderClassName, directionalClassName);\n      this._isSliding = false;\n      triggerEvent(EVENT_SLID);\n    };\n    this._queueCallback(completeCallBack, activeElement, this._isAnimated());\n    if (isCycling) {\n      this.cycle();\n    }\n  }\n  _isAnimated() {\n    return this._element.classList.contains(CLASS_NAME_SLIDE);\n  }\n  _getActive() {\n    return SelectorEngine.findOne(SELECTOR_ACTIVE_ITEM, this._element);\n  }\n  _getItems() {\n    return SelectorEngine.find(SELECTOR_ITEM, this._element);\n  }\n  _clearInterval() {\n    if (this._interval) {\n      clearInterval(this._interval);\n      this._interval = null;\n    }\n  }\n  _directionToOrder(direction) {\n    if (isRTL()) {\n      return direction === DIRECTION_LEFT ? ORDER_PREV : ORDER_NEXT;\n    }\n    return direction === DIRECTION_LEFT ? ORDER_NEXT : ORDER_PREV;\n  }\n  _orderToDirection(order) {\n    if (isRTL()) {\n      return order === ORDER_PREV ? DIRECTION_LEFT : DIRECTION_RIGHT;\n    }\n    return order === ORDER_PREV ? DIRECTION_RIGHT : DIRECTION_LEFT;\n  }\n\n  // Static\n  static jQueryInterface(config) {\n    return this.each(function () {\n      const data = Carousel.getOrCreateInstance(this, config);\n      if (typeof config === 'number') {\n        data.to(config);\n        return;\n      }\n      if (typeof config === 'string') {\n        if (data[config] === undefined || config.startsWith('_') || config === 'constructor') {\n          throw new TypeError(`No method named \"${config}\"`);\n        }\n        data[config]();\n      }\n    });\n  }\n}\n\n/**\n * Data API implementation\n */\n\nEventHandler.on(document, EVENT_CLICK_DATA_API$5, SELECTOR_DATA_SLIDE, function (event) {\n  const target = SelectorEngine.getElementFromSelector(this);\n  if (!target || !target.classList.contains(CLASS_NAME_CAROUSEL)) {\n    return;\n  }\n  event.preventDefault();\n  const carousel = Carousel.getOrCreateInstance(target);\n  const slideIndex = this.getAttribute('data-bs-slide-to');\n  if (slideIndex) {\n    carousel.to(slideIndex);\n    carousel._maybeEnableCycle();\n    return;\n  }\n  if (Manipulator.getDataAttribute(this, 'slide') === 'next') {\n    carousel.next();\n    carousel._maybeEnableCycle();\n    return;\n  }\n  carousel.prev();\n  carousel._maybeEnableCycle();\n});\nEventHandler.on(window, EVENT_LOAD_DATA_API$3, () => {\n  const carousels = SelectorEngine.find(SELECTOR_DATA_RIDE);\n  for (const carousel of carousels) {\n    Carousel.getOrCreateInstance(carousel);\n  }\n});\n\n/**\n * jQuery\n */\n\ndefineJQueryPlugin(Carousel);\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap collapse.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\n\n/**\n * Constants\n */\n\nconst NAME$b = 'collapse';\nconst DATA_KEY$7 = 'bs.collapse';\nconst EVENT_KEY$7 = `.${DATA_KEY$7}`;\nconst DATA_API_KEY$4 = '.data-api';\nconst EVENT_SHOW$6 = `show${EVENT_KEY$7}`;\nconst EVENT_SHOWN$6 = `shown${EVENT_KEY$7}`;\nconst EVENT_HIDE$6 = `hide${EVENT_KEY$7}`;\nconst EVENT_HIDDEN$6 = `hidden${EVENT_KEY$7}`;\nconst EVENT_CLICK_DATA_API$4 = `click${EVENT_KEY$7}${DATA_API_KEY$4}`;\nconst CLASS_NAME_SHOW$7 = 'show';\nconst CLASS_NAME_COLLAPSE = 'collapse';\nconst CLASS_NAME_COLLAPSING = 'collapsing';\nconst CLASS_NAME_COLLAPSED = 'collapsed';\nconst CLASS_NAME_DEEPER_CHILDREN = `:scope .${CLASS_NAME_COLLAPSE} .${CLASS_NAME_COLLAPSE}`;\nconst CLASS_NAME_HORIZONTAL = 'collapse-horizontal';\nconst WIDTH = 'width';\nconst HEIGHT = 'height';\nconst SELECTOR_ACTIVES = '.collapse.show, .collapse.collapsing';\nconst SELECTOR_DATA_TOGGLE$4 = '[data-bs-toggle=\"collapse\"]';\nconst Default$a = {\n  parent: null,\n  toggle: true\n};\nconst DefaultType$a = {\n  parent: '(null|element)',\n  toggle: 'boolean'\n};\n\n/**\n * Class definition\n */\n\nclass Collapse extends BaseComponent {\n  constructor(element, config) {\n    super(element, config);\n    this._isTransitioning = false;\n    this._triggerArray = [];\n    const toggleList = SelectorEngine.find(SELECTOR_DATA_TOGGLE$4);\n    for (const elem of toggleList) {\n      const selector = SelectorEngine.getSelectorFromElement(elem);\n      const filterElement = SelectorEngine.find(selector).filter(foundElement => foundElement === this._element);\n      if (selector !== null && filterElement.length) {\n        this._triggerArray.push(elem);\n      }\n    }\n    this._initializeChildren();\n    if (!this._config.parent) {\n      this._addAriaAndCollapsedClass(this._triggerArray, this._isShown());\n    }\n    if (this._config.toggle) {\n      this.toggle();\n    }\n  }\n\n  // Getters\n  static get Default() {\n    return Default$a;\n  }\n  static get DefaultType() {\n    return DefaultType$a;\n  }\n  static get NAME() {\n    return NAME$b;\n  }\n\n  // Public\n  toggle() {\n    if (this._isShown()) {\n      this.hide();\n    } else {\n      this.show();\n    }\n  }\n  show() {\n    if (this._isTransitioning || this._isShown()) {\n      return;\n    }\n    let activeChildren = [];\n\n    // find active children\n    if (this._config.parent) {\n      activeChildren = this._getFirstLevelChildren(SELECTOR_ACTIVES).filter(element => element !== this._element).map(element => Collapse.getOrCreateInstance(element, {\n        toggle: false\n      }));\n    }\n    if (activeChildren.length && activeChildren[0]._isTransitioning) {\n      return;\n    }\n    const startEvent = EventHandler.trigger(this._element, EVENT_SHOW$6);\n    if (startEvent.defaultPrevented) {\n      return;\n    }\n    for (const activeInstance of activeChildren) {\n      activeInstance.hide();\n    }\n    const dimension = this._getDimension();\n    this._element.classList.remove(CLASS_NAME_COLLAPSE);\n    this._element.classList.add(CLASS_NAME_COLLAPSING);\n    this._element.style[dimension] = 0;\n    this._addAriaAndCollapsedClass(this._triggerArray, true);\n    this._isTransitioning = true;\n    const complete = () => {\n      this._isTransitioning = false;\n      this._element.classList.remove(CLASS_NAME_COLLAPSING);\n      this._element.classList.add(CLASS_NAME_COLLAPSE, CLASS_NAME_SHOW$7);\n      this._element.style[dimension] = '';\n      EventHandler.trigger(this._element, EVENT_SHOWN$6);\n    };\n    const capitalizedDimension = dimension[0].toUpperCase() + dimension.slice(1);\n    const scrollSize = `scroll${capitalizedDimension}`;\n    this._queueCallback(complete, this._element, true);\n    this._element.style[dimension] = `${this._element[scrollSize]}px`;\n  }\n  hide() {\n    if (this._isTransitioning || !this._isShown()) {\n      return;\n    }\n    const startEvent = EventHandler.trigger(this._element, EVENT_HIDE$6);\n    if (startEvent.defaultPrevented) {\n      return;\n    }\n    const dimension = this._getDimension();\n    this._element.style[dimension] = `${this._element.getBoundingClientRect()[dimension]}px`;\n    reflow(this._element);\n    this._element.classList.add(CLASS_NAME_COLLAPSING);\n    this._element.classList.remove(CLASS_NAME_COLLAPSE, CLASS_NAME_SHOW$7);\n    for (const trigger of this._triggerArray) {\n      const element = SelectorEngine.getElementFromSelector(trigger);\n      if (element && !this._isShown(element)) {\n        this._addAriaAndCollapsedClass([trigger], false);\n      }\n    }\n    this._isTransitioning = true;\n    const complete = () => {\n      this._isTransitioning = false;\n      this._element.classList.remove(CLASS_NAME_COLLAPSING);\n      this._element.classList.add(CLASS_NAME_COLLAPSE);\n      EventHandler.trigger(this._element, EVENT_HIDDEN$6);\n    };\n    this._element.style[dimension] = '';\n    this._queueCallback(complete, this._element, true);\n  }\n  _isShown(element = this._element) {\n    return element.classList.contains(CLASS_NAME_SHOW$7);\n  }\n\n  // Private\n  _configAfterMerge(config) {\n    config.toggle = Boolean(config.toggle); // Coerce string values\n    config.parent = getElement(config.parent);\n    return config;\n  }\n  _getDimension() {\n    return this._element.classList.contains(CLASS_NAME_HORIZONTAL) ? WIDTH : HEIGHT;\n  }\n  _initializeChildren() {\n    if (!this._config.parent) {\n      return;\n    }\n    const children = this._getFirstLevelChildren(SELECTOR_DATA_TOGGLE$4);\n    for (const element of children) {\n      const selected = SelectorEngine.getElementFromSelector(element);\n      if (selected) {\n        this._addAriaAndCollapsedClass([element], this._isShown(selected));\n      }\n    }\n  }\n  _getFirstLevelChildren(selector) {\n    const children = SelectorEngine.find(CLASS_NAME_DEEPER_CHILDREN, this._config.parent);\n    // remove children if greater depth\n    return SelectorEngine.find(selector, this._config.parent).filter(element => !children.includes(element));\n  }\n  _addAriaAndCollapsedClass(triggerArray, isOpen) {\n    if (!triggerArray.length) {\n      return;\n    }\n    for (const element of triggerArray) {\n      element.classList.toggle(CLASS_NAME_COLLAPSED, !isOpen);\n      element.setAttribute('aria-expanded', isOpen);\n    }\n  }\n\n  // Static\n  static jQueryInterface(config) {\n    const _config = {};\n    if (typeof config === 'string' && /show|hide/.test(config)) {\n      _config.toggle = false;\n    }\n    return this.each(function () {\n      const data = Collapse.getOrCreateInstance(this, _config);\n      if (typeof config === 'string') {\n        if (typeof data[config] === 'undefined') {\n          throw new TypeError(`No method named \"${config}\"`);\n        }\n        data[config]();\n      }\n    });\n  }\n}\n\n/**\n * Data API implementation\n */\n\nEventHandler.on(document, EVENT_CLICK_DATA_API$4, SELECTOR_DATA_TOGGLE$4, function (event) {\n  // preventDefault only for <a> elements (which change the URL) not inside the collapsible element\n  if (event.target.tagName === 'A' || event.delegateTarget && event.delegateTarget.tagName === 'A') {\n    event.preventDefault();\n  }\n  for (const element of SelectorEngine.getMultipleElementsFromSelector(this)) {\n    Collapse.getOrCreateInstance(element, {\n      toggle: false\n    }).toggle();\n  }\n});\n\n/**\n * jQuery\n */\n\ndefineJQueryPlugin(Collapse);\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap dropdown.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\n\n/**\n * Constants\n */\n\nconst NAME$a = 'dropdown';\nconst DATA_KEY$6 = 'bs.dropdown';\nconst EVENT_KEY$6 = `.${DATA_KEY$6}`;\nconst DATA_API_KEY$3 = '.data-api';\nconst ESCAPE_KEY$2 = 'Escape';\nconst TAB_KEY$1 = 'Tab';\nconst ARROW_UP_KEY$1 = 'ArrowUp';\nconst ARROW_DOWN_KEY$1 = 'ArrowDown';\nconst RIGHT_MOUSE_BUTTON = 2; // MouseEvent.button value for the secondary button, usually the right button\n\nconst EVENT_HIDE$5 = `hide${EVENT_KEY$6}`;\nconst EVENT_HIDDEN$5 = `hidden${EVENT_KEY$6}`;\nconst EVENT_SHOW$5 = `show${EVENT_KEY$6}`;\nconst EVENT_SHOWN$5 = `shown${EVENT_KEY$6}`;\nconst EVENT_CLICK_DATA_API$3 = `click${EVENT_KEY$6}${DATA_API_KEY$3}`;\nconst EVENT_KEYDOWN_DATA_API = `keydown${EVENT_KEY$6}${DATA_API_KEY$3}`;\nconst EVENT_KEYUP_DATA_API = `keyup${EVENT_KEY$6}${DATA_API_KEY$3}`;\nconst CLASS_NAME_SHOW$6 = 'show';\nconst CLASS_NAME_DROPUP = 'dropup';\nconst CLASS_NAME_DROPEND = 'dropend';\nconst CLASS_NAME_DROPSTART = 'dropstart';\nconst CLASS_NAME_DROPUP_CENTER = 'dropup-center';\nconst CLASS_NAME_DROPDOWN_CENTER = 'dropdown-center';\nconst SELECTOR_DATA_TOGGLE$3 = '[data-bs-toggle=\"dropdown\"]:not(.disabled):not(:disabled)';\nconst SELECTOR_DATA_TOGGLE_SHOWN = `${SELECTOR_DATA_TOGGLE$3}.${CLASS_NAME_SHOW$6}`;\nconst SELECTOR_MENU = '.dropdown-menu';\nconst SELECTOR_NAVBAR = '.navbar';\nconst SELECTOR_NAVBAR_NAV = '.navbar-nav';\nconst SELECTOR_VISIBLE_ITEMS = '.dropdown-menu .dropdown-item:not(.disabled):not(:disabled)';\nconst PLACEMENT_TOP = isRTL() ? 'top-end' : 'top-start';\nconst PLACEMENT_TOPEND = isRTL() ? 'top-start' : 'top-end';\nconst PLACEMENT_BOTTOM = isRTL() ? 'bottom-end' : 'bottom-start';\nconst PLACEMENT_BOTTOMEND = isRTL() ? 'bottom-start' : 'bottom-end';\nconst PLACEMENT_RIGHT = isRTL() ? 'left-start' : 'right-start';\nconst PLACEMENT_LEFT = isRTL() ? 'right-start' : 'left-start';\nconst PLACEMENT_TOPCENTER = 'top';\nconst PLACEMENT_BOTTOMCENTER = 'bottom';\nconst Default$9 = {\n  autoClose: true,\n  boundary: 'clippingParents',\n  display: 'dynamic',\n  offset: [0, 2],\n  popperConfig: null,\n  reference: 'toggle'\n};\nconst DefaultType$9 = {\n  autoClose: '(boolean|string)',\n  boundary: '(string|element)',\n  display: 'string',\n  offset: '(array|string|function)',\n  popperConfig: '(null|object|function)',\n  reference: '(string|element|object)'\n};\n\n/**\n * Class definition\n */\n\nclass Dropdown extends BaseComponent {\n  constructor(element, config) {\n    super(element, config);\n    this._popper = null;\n    this._parent = this._element.parentNode; // dropdown wrapper\n    // TODO: v6 revert #37011 & change markup https://getbootstrap.com/docs/5.3/forms/input-group/\n    this._menu = SelectorEngine.next(this._element, SELECTOR_MENU)[0] || SelectorEngine.prev(this._element, SELECTOR_MENU)[0] || SelectorEngine.findOne(SELECTOR_MENU, this._parent);\n    this._inNavbar = this._detectNavbar();\n  }\n\n  // Getters\n  static get Default() {\n    return Default$9;\n  }\n  static get DefaultType() {\n    return DefaultType$9;\n  }\n  static get NAME() {\n    return NAME$a;\n  }\n\n  // Public\n  toggle() {\n    return this._isShown() ? this.hide() : this.show();\n  }\n  show() {\n    if (isDisabled(this._element) || this._isShown()) {\n      return;\n    }\n    const relatedTarget = {\n      relatedTarget: this._element\n    };\n    const showEvent = EventHandler.trigger(this._element, EVENT_SHOW$5, relatedTarget);\n    if (showEvent.defaultPrevented) {\n      return;\n    }\n    this._createPopper();\n\n    // If this is a touch-enabled device we add extra\n    // empty mouseover listeners to the body's immediate children;\n    // only needed because of broken event delegation on iOS\n    // https://www.quirksmode.org/blog/archives/2014/02/mouse_event_bub.html\n    if ('ontouchstart' in document.documentElement && !this._parent.closest(SELECTOR_NAVBAR_NAV)) {\n      for (const element of [].concat(...document.body.children)) {\n        EventHandler.on(element, 'mouseover', noop);\n      }\n    }\n    this._element.focus();\n    this._element.setAttribute('aria-expanded', true);\n    this._menu.classList.add(CLASS_NAME_SHOW$6);\n    this._element.classList.add(CLASS_NAME_SHOW$6);\n    EventHandler.trigger(this._element, EVENT_SHOWN$5, relatedTarget);\n  }\n  hide() {\n    if (isDisabled(this._element) || !this._isShown()) {\n      return;\n    }\n    const relatedTarget = {\n      relatedTarget: this._element\n    };\n    this._completeHide(relatedTarget);\n  }\n  dispose() {\n    if (this._popper) {\n      this._popper.destroy();\n    }\n    super.dispose();\n  }\n  update() {\n    this._inNavbar = this._detectNavbar();\n    if (this._popper) {\n      this._popper.update();\n    }\n  }\n\n  // Private\n  _completeHide(relatedTarget) {\n    const hideEvent = EventHandler.trigger(this._element, EVENT_HIDE$5, relatedTarget);\n    if (hideEvent.defaultPrevented) {\n      return;\n    }\n\n    // If this is a touch-enabled device we remove the extra\n    // empty mouseover listeners we added for iOS support\n    if ('ontouchstart' in document.documentElement) {\n      for (const element of [].concat(...document.body.children)) {\n        EventHandler.off(element, 'mouseover', noop);\n      }\n    }\n    if (this._popper) {\n      this._popper.destroy();\n    }\n    this._menu.classList.remove(CLASS_NAME_SHOW$6);\n    this._element.classList.remove(CLASS_NAME_SHOW$6);\n    this._element.setAttribute('aria-expanded', 'false');\n    Manipulator.removeDataAttribute(this._menu, 'popper');\n    EventHandler.trigger(this._element, EVENT_HIDDEN$5, relatedTarget);\n  }\n  _getConfig(config) {\n    config = super._getConfig(config);\n    if (typeof config.reference === 'object' && !isElement(config.reference) && typeof config.reference.getBoundingClientRect !== 'function') {\n      // Popper virtual elements require a getBoundingClientRect method\n      throw new TypeError(`${NAME$a.toUpperCase()}: Option \"reference\" provided type \"object\" without a required \"getBoundingClientRect\" method.`);\n    }\n    return config;\n  }\n  _createPopper() {\n    if (typeof Popper === 'undefined') {\n      throw new TypeError('Bootstrap\\'s dropdowns require Popper (https://popper.js.org)');\n    }\n    let referenceElement = this._element;\n    if (this._config.reference === 'parent') {\n      referenceElement = this._parent;\n    } else if (isElement(this._config.reference)) {\n      referenceElement = getElement(this._config.reference);\n    } else if (typeof this._config.reference === 'object') {\n      referenceElement = this._config.reference;\n    }\n    const popperConfig = this._getPopperConfig();\n    this._popper = Popper.createPopper(referenceElement, this._menu, popperConfig);\n  }\n  _isShown() {\n    return this._menu.classList.contains(CLASS_NAME_SHOW$6);\n  }\n  _getPlacement() {\n    const parentDropdown = this._parent;\n    if (parentDropdown.classList.contains(CLASS_NAME_DROPEND)) {\n      return PLACEMENT_RIGHT;\n    }\n    if (parentDropdown.classList.contains(CLASS_NAME_DROPSTART)) {\n      return PLACEMENT_LEFT;\n    }\n    if (parentDropdown.classList.contains(CLASS_NAME_DROPUP_CENTER)) {\n      return PLACEMENT_TOPCENTER;\n    }\n    if (parentDropdown.classList.contains(CLASS_NAME_DROPDOWN_CENTER)) {\n      return PLACEMENT_BOTTOMCENTER;\n    }\n\n    // We need to trim the value because custom properties can also include spaces\n    const isEnd = getComputedStyle(this._menu).getPropertyValue('--bs-position').trim() === 'end';\n    if (parentDropdown.classList.contains(CLASS_NAME_DROPUP)) {\n      return isEnd ? PLACEMENT_TOPEND : PLACEMENT_TOP;\n    }\n    return isEnd ? PLACEMENT_BOTTOMEND : PLACEMENT_BOTTOM;\n  }\n  _detectNavbar() {\n    return this._element.closest(SELECTOR_NAVBAR) !== null;\n  }\n  _getOffset() {\n    const {\n      offset\n    } = this._config;\n    if (typeof offset === 'string') {\n      return offset.split(',').map(value => Number.parseInt(value, 10));\n    }\n    if (typeof offset === 'function') {\n      return popperData => offset(popperData, this._element);\n    }\n    return offset;\n  }\n  _getPopperConfig() {\n    const defaultBsPopperConfig = {\n      placement: this._getPlacement(),\n      modifiers: [{\n        name: 'preventOverflow',\n        options: {\n          boundary: this._config.boundary\n        }\n      }, {\n        name: 'offset',\n        options: {\n          offset: this._getOffset()\n        }\n      }]\n    };\n\n    // Disable Popper if we have a static display or Dropdown is in Navbar\n    if (this._inNavbar || this._config.display === 'static') {\n      Manipulator.setDataAttribute(this._menu, 'popper', 'static'); // TODO: v6 remove\n      defaultBsPopperConfig.modifiers = [{\n        name: 'applyStyles',\n        enabled: false\n      }];\n    }\n    return {\n      ...defaultBsPopperConfig,\n      ...execute(this._config.popperConfig, [defaultBsPopperConfig])\n    };\n  }\n  _selectMenuItem({\n    key,\n    target\n  }) {\n    const items = SelectorEngine.find(SELECTOR_VISIBLE_ITEMS, this._menu).filter(element => isVisible(element));\n    if (!items.length) {\n      return;\n    }\n\n    // if target isn't included in items (e.g. when expanding the dropdown)\n    // allow cycling to get the last item in case key equals ARROW_UP_KEY\n    getNextActiveElement(items, target, key === ARROW_DOWN_KEY$1, !items.includes(target)).focus();\n  }\n\n  // Static\n  static jQueryInterface(config) {\n    return this.each(function () {\n      const data = Dropdown.getOrCreateInstance(this, config);\n      if (typeof config !== 'string') {\n        return;\n      }\n      if (typeof data[config] === 'undefined') {\n        throw new TypeError(`No method named \"${config}\"`);\n      }\n      data[config]();\n    });\n  }\n  static clearMenus(event) {\n    if (event.button === RIGHT_MOUSE_BUTTON || event.type === 'keyup' && event.key !== TAB_KEY$1) {\n      return;\n    }\n    const openToggles = SelectorEngine.find(SELECTOR_DATA_TOGGLE_SHOWN);\n    for (const toggle of openToggles) {\n      const context = Dropdown.getInstance(toggle);\n      if (!context || context._config.autoClose === false) {\n        continue;\n      }\n      const composedPath = event.composedPath();\n      const isMenuTarget = composedPath.includes(context._menu);\n      if (composedPath.includes(context._element) || context._config.autoClose === 'inside' && !isMenuTarget || context._config.autoClose === 'outside' && isMenuTarget) {\n        continue;\n      }\n\n      // Tab navigation through the dropdown menu or events from contained inputs shouldn't close the menu\n      if (context._menu.contains(event.target) && (event.type === 'keyup' && event.key === TAB_KEY$1 || /input|select|option|textarea|form/i.test(event.target.tagName))) {\n        continue;\n      }\n      const relatedTarget = {\n        relatedTarget: context._element\n      };\n      if (event.type === 'click') {\n        relatedTarget.clickEvent = event;\n      }\n      context._completeHide(relatedTarget);\n    }\n  }\n  static dataApiKeydownHandler(event) {\n    // If not an UP | DOWN | ESCAPE key => not a dropdown command\n    // If input/textarea && if key is other than ESCAPE => not a dropdown command\n\n    const isInput = /input|textarea/i.test(event.target.tagName);\n    const isEscapeEvent = event.key === ESCAPE_KEY$2;\n    const isUpOrDownEvent = [ARROW_UP_KEY$1, ARROW_DOWN_KEY$1].includes(event.key);\n    if (!isUpOrDownEvent && !isEscapeEvent) {\n      return;\n    }\n    if (isInput && !isEscapeEvent) {\n      return;\n    }\n    event.preventDefault();\n\n    // TODO: v6 revert #37011 & change markup https://getbootstrap.com/docs/5.3/forms/input-group/\n    const getToggleButton = this.matches(SELECTOR_DATA_TOGGLE$3) ? this : SelectorEngine.prev(this, SELECTOR_DATA_TOGGLE$3)[0] || SelectorEngine.next(this, SELECTOR_DATA_TOGGLE$3)[0] || SelectorEngine.findOne(SELECTOR_DATA_TOGGLE$3, event.delegateTarget.parentNode);\n    const instance = Dropdown.getOrCreateInstance(getToggleButton);\n    if (isUpOrDownEvent) {\n      event.stopPropagation();\n      instance.show();\n      instance._selectMenuItem(event);\n      return;\n    }\n    if (instance._isShown()) {\n      // else is escape and we check if it is shown\n      event.stopPropagation();\n      instance.hide();\n      getToggleButton.focus();\n    }\n  }\n}\n\n/**\n * Data API implementation\n */\n\nEventHandler.on(document, EVENT_KEYDOWN_DATA_API, SELECTOR_DATA_TOGGLE$3, Dropdown.dataApiKeydownHandler);\nEventHandler.on(document, EVENT_KEYDOWN_DATA_API, SELECTOR_MENU, Dropdown.dataApiKeydownHandler);\nEventHandler.on(document, EVENT_CLICK_DATA_API$3, Dropdown.clearMenus);\nEventHandler.on(document, EVENT_KEYUP_DATA_API, Dropdown.clearMenus);\nEventHandler.on(document, EVENT_CLICK_DATA_API$3, SELECTOR_DATA_TOGGLE$3, function (event) {\n  event.preventDefault();\n  Dropdown.getOrCreateInstance(this).toggle();\n});\n\n/**\n * jQuery\n */\n\ndefineJQueryPlugin(Dropdown);\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap util/backdrop.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\n\n/**\n * Constants\n */\n\nconst NAME$9 = 'backdrop';\nconst CLASS_NAME_FADE$4 = 'fade';\nconst CLASS_NAME_SHOW$5 = 'show';\nconst EVENT_MOUSEDOWN = `mousedown.bs.${NAME$9}`;\nconst Default$8 = {\n  className: 'modal-backdrop',\n  clickCallback: null,\n  isAnimated: false,\n  isVisible: true,\n  // if false, we use the backdrop helper without adding any element to the dom\n  rootElement: 'body' // give the choice to place backdrop under different elements\n};\nconst DefaultType$8 = {\n  className: 'string',\n  clickCallback: '(function|null)',\n  isAnimated: 'boolean',\n  isVisible: 'boolean',\n  rootElement: '(element|string)'\n};\n\n/**\n * Class definition\n */\n\nclass Backdrop extends Config {\n  constructor(config) {\n    super();\n    this._config = this._getConfig(config);\n    this._isAppended = false;\n    this._element = null;\n  }\n\n  // Getters\n  static get Default() {\n    return Default$8;\n  }\n  static get DefaultType() {\n    return DefaultType$8;\n  }\n  static get NAME() {\n    return NAME$9;\n  }\n\n  // Public\n  show(callback) {\n    if (!this._config.isVisible) {\n      execute(callback);\n      return;\n    }\n    this._append();\n    const element = this._getElement();\n    if (this._config.isAnimated) {\n      reflow(element);\n    }\n    element.classList.add(CLASS_NAME_SHOW$5);\n    this._emulateAnimation(() => {\n      execute(callback);\n    });\n  }\n  hide(callback) {\n    if (!this._config.isVisible) {\n      execute(callback);\n      return;\n    }\n    this._getElement().classList.remove(CLASS_NAME_SHOW$5);\n    this._emulateAnimation(() => {\n      this.dispose();\n      execute(callback);\n    });\n  }\n  dispose() {\n    if (!this._isAppended) {\n      return;\n    }\n    EventHandler.off(this._element, EVENT_MOUSEDOWN);\n    this._element.remove();\n    this._isAppended = false;\n  }\n\n  // Private\n  _getElement() {\n    if (!this._element) {\n      const backdrop = document.createElement('div');\n      backdrop.className = this._config.className;\n      if (this._config.isAnimated) {\n        backdrop.classList.add(CLASS_NAME_FADE$4);\n      }\n      this._element = backdrop;\n    }\n    return this._element;\n  }\n  _configAfterMerge(config) {\n    // use getElement() with the default \"body\" to get a fresh Element on each instantiation\n    config.rootElement = getElement(config.rootElement);\n    return config;\n  }\n  _append() {\n    if (this._isAppended) {\n      return;\n    }\n    const element = this._getElement();\n    this._config.rootElement.append(element);\n    EventHandler.on(element, EVENT_MOUSEDOWN, () => {\n      execute(this._config.clickCallback);\n    });\n    this._isAppended = true;\n  }\n  _emulateAnimation(callback) {\n    executeAfterTransition(callback, this._getElement(), this._config.isAnimated);\n  }\n}\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap util/focustrap.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\n\n/**\n * Constants\n */\n\nconst NAME$8 = 'focustrap';\nconst DATA_KEY$5 = 'bs.focustrap';\nconst EVENT_KEY$5 = `.${DATA_KEY$5}`;\nconst EVENT_FOCUSIN$2 = `focusin${EVENT_KEY$5}`;\nconst EVENT_KEYDOWN_TAB = `keydown.tab${EVENT_KEY$5}`;\nconst TAB_KEY = 'Tab';\nconst TAB_NAV_FORWARD = 'forward';\nconst TAB_NAV_BACKWARD = 'backward';\nconst Default$7 = {\n  autofocus: true,\n  trapElement: null // The element to trap focus inside of\n};\nconst DefaultType$7 = {\n  autofocus: 'boolean',\n  trapElement: 'element'\n};\n\n/**\n * Class definition\n */\n\nclass FocusTrap extends Config {\n  constructor(config) {\n    super();\n    this._config = this._getConfig(config);\n    this._isActive = false;\n    this._lastTabNavDirection = null;\n  }\n\n  // Getters\n  static get Default() {\n    return Default$7;\n  }\n  static get DefaultType() {\n    return DefaultType$7;\n  }\n  static get NAME() {\n    return NAME$8;\n  }\n\n  // Public\n  activate() {\n    if (this._isActive) {\n      return;\n    }\n    if (this._config.autofocus) {\n      this._config.trapElement.focus();\n    }\n    EventHandler.off(document, EVENT_KEY$5); // guard against infinite focus loop\n    EventHandler.on(document, EVENT_FOCUSIN$2, event => this._handleFocusin(event));\n    EventHandler.on(document, EVENT_KEYDOWN_TAB, event => this._handleKeydown(event));\n    this._isActive = true;\n  }\n  deactivate() {\n    if (!this._isActive) {\n      return;\n    }\n    this._isActive = false;\n    EventHandler.off(document, EVENT_KEY$5);\n  }\n\n  // Private\n  _handleFocusin(event) {\n    const {\n      trapElement\n    } = this._config;\n    if (event.target === document || event.target === trapElement || trapElement.contains(event.target)) {\n      return;\n    }\n    const elements = SelectorEngine.focusableChildren(trapElement);\n    if (elements.length === 0) {\n      trapElement.focus();\n    } else if (this._lastTabNavDirection === TAB_NAV_BACKWARD) {\n      elements[elements.length - 1].focus();\n    } else {\n      elements[0].focus();\n    }\n  }\n  _handleKeydown(event) {\n    if (event.key !== TAB_KEY) {\n      return;\n    }\n    this._lastTabNavDirection = event.shiftKey ? TAB_NAV_BACKWARD : TAB_NAV_FORWARD;\n  }\n}\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap util/scrollBar.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\n\n/**\n * Constants\n */\n\nconst SELECTOR_FIXED_CONTENT = '.fixed-top, .fixed-bottom, .is-fixed, .sticky-top';\nconst SELECTOR_STICKY_CONTENT = '.sticky-top';\nconst PROPERTY_PADDING = 'padding-right';\nconst PROPERTY_MARGIN = 'margin-right';\n\n/**\n * Class definition\n */\n\nclass ScrollBarHelper {\n  constructor() {\n    this._element = document.body;\n  }\n\n  // Public\n  getWidth() {\n    // https://developer.mozilla.org/en-US/docs/Web/API/Window/innerWidth#usage_notes\n    const documentWidth = document.documentElement.clientWidth;\n    return Math.abs(window.innerWidth - documentWidth);\n  }\n  hide() {\n    const width = this.getWidth();\n    this._disableOverFlow();\n    // give padding to element to balance the hidden scrollbar width\n    this._setElementAttributes(this._element, PROPERTY_PADDING, calculatedValue => calculatedValue + width);\n    // trick: We adjust positive paddingRight and negative marginRight to sticky-top elements to keep showing fullwidth\n    this._setElementAttributes(SELECTOR_FIXED_CONTENT, PROPERTY_PADDING, calculatedValue => calculatedValue + width);\n    this._setElementAttributes(SELECTOR_STICKY_CONTENT, PROPERTY_MARGIN, calculatedValue => calculatedValue - width);\n  }\n  reset() {\n    this._resetElementAttributes(this._element, 'overflow');\n    this._resetElementAttributes(this._element, PROPERTY_PADDING);\n    this._resetElementAttributes(SELECTOR_FIXED_CONTENT, PROPERTY_PADDING);\n    this._resetElementAttributes(SELECTOR_STICKY_CONTENT, PROPERTY_MARGIN);\n  }\n  isOverflowing() {\n    return this.getWidth() > 0;\n  }\n\n  // Private\n  _disableOverFlow() {\n    this._saveInitialAttribute(this._element, 'overflow');\n    this._element.style.overflow = 'hidden';\n  }\n  _setElementAttributes(selector, styleProperty, callback) {\n    const scrollbarWidth = this.getWidth();\n    const manipulationCallBack = element => {\n      if (element !== this._element && window.innerWidth > element.clientWidth + scrollbarWidth) {\n        return;\n      }\n      this._saveInitialAttribute(element, styleProperty);\n      const calculatedValue = window.getComputedStyle(element).getPropertyValue(styleProperty);\n      element.style.setProperty(styleProperty, `${callback(Number.parseFloat(calculatedValue))}px`);\n    };\n    this._applyManipulationCallback(selector, manipulationCallBack);\n  }\n  _saveInitialAttribute(element, styleProperty) {\n    const actualValue = element.style.getPropertyValue(styleProperty);\n    if (actualValue) {\n      Manipulator.setDataAttribute(element, styleProperty, actualValue);\n    }\n  }\n  _resetElementAttributes(selector, styleProperty) {\n    const manipulationCallBack = element => {\n      const value = Manipulator.getDataAttribute(element, styleProperty);\n      // We only want to remove the property if the value is `null`; the value can also be zero\n      if (value === null) {\n        element.style.removeProperty(styleProperty);\n        return;\n      }\n      Manipulator.removeDataAttribute(element, styleProperty);\n      element.style.setProperty(styleProperty, value);\n    };\n    this._applyManipulationCallback(selector, manipulationCallBack);\n  }\n  _applyManipulationCallback(selector, callBack) {\n    if (isElement(selector)) {\n      callBack(selector);\n      return;\n    }\n    for (const sel of SelectorEngine.find(selector, this._element)) {\n      callBack(sel);\n    }\n  }\n}\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap modal.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\n\n/**\n * Constants\n */\n\nconst NAME$7 = 'modal';\nconst DATA_KEY$4 = 'bs.modal';\nconst EVENT_KEY$4 = `.${DATA_KEY$4}`;\nconst DATA_API_KEY$2 = '.data-api';\nconst ESCAPE_KEY$1 = 'Escape';\nconst EVENT_HIDE$4 = `hide${EVENT_KEY$4}`;\nconst EVENT_HIDE_PREVENTED$1 = `hidePrevented${EVENT_KEY$4}`;\nconst EVENT_HIDDEN$4 = `hidden${EVENT_KEY$4}`;\nconst EVENT_SHOW$4 = `show${EVENT_KEY$4}`;\nconst EVENT_SHOWN$4 = `shown${EVENT_KEY$4}`;\nconst EVENT_RESIZE$1 = `resize${EVENT_KEY$4}`;\nconst EVENT_CLICK_DISMISS = `click.dismiss${EVENT_KEY$4}`;\nconst EVENT_MOUSEDOWN_DISMISS = `mousedown.dismiss${EVENT_KEY$4}`;\nconst EVENT_KEYDOWN_DISMISS$1 = `keydown.dismiss${EVENT_KEY$4}`;\nconst EVENT_CLICK_DATA_API$2 = `click${EVENT_KEY$4}${DATA_API_KEY$2}`;\nconst CLASS_NAME_OPEN = 'modal-open';\nconst CLASS_NAME_FADE$3 = 'fade';\nconst CLASS_NAME_SHOW$4 = 'show';\nconst CLASS_NAME_STATIC = 'modal-static';\nconst OPEN_SELECTOR$1 = '.modal.show';\nconst SELECTOR_DIALOG = '.modal-dialog';\nconst SELECTOR_MODAL_BODY = '.modal-body';\nconst SELECTOR_DATA_TOGGLE$2 = '[data-bs-toggle=\"modal\"]';\nconst Default$6 = {\n  backdrop: true,\n  focus: true,\n  keyboard: true\n};\nconst DefaultType$6 = {\n  backdrop: '(boolean|string)',\n  focus: 'boolean',\n  keyboard: 'boolean'\n};\n\n/**\n * Class definition\n */\n\nclass Modal extends BaseComponent {\n  constructor(element, config) {\n    super(element, config);\n    this._dialog = SelectorEngine.findOne(SELECTOR_DIALOG, this._element);\n    this._backdrop = this._initializeBackDrop();\n    this._focustrap = this._initializeFocusTrap();\n    this._isShown = false;\n    this._isTransitioning = false;\n    this._scrollBar = new ScrollBarHelper();\n    this._addEventListeners();\n  }\n\n  // Getters\n  static get Default() {\n    return Default$6;\n  }\n  static get DefaultType() {\n    return DefaultType$6;\n  }\n  static get NAME() {\n    return NAME$7;\n  }\n\n  // Public\n  toggle(relatedTarget) {\n    return this._isShown ? this.hide() : this.show(relatedTarget);\n  }\n  show(relatedTarget) {\n    if (this._isShown || this._isTransitioning) {\n      return;\n    }\n    const showEvent = EventHandler.trigger(this._element, EVENT_SHOW$4, {\n      relatedTarget\n    });\n    if (showEvent.defaultPrevented) {\n      return;\n    }\n    this._isShown = true;\n    this._isTransitioning = true;\n    this._scrollBar.hide();\n    document.body.classList.add(CLASS_NAME_OPEN);\n    this._adjustDialog();\n    this._backdrop.show(() => this._showElement(relatedTarget));\n  }\n  hide() {\n    if (!this._isShown || this._isTransitioning) {\n      return;\n    }\n    const hideEvent = EventHandler.trigger(this._element, EVENT_HIDE$4);\n    if (hideEvent.defaultPrevented) {\n      return;\n    }\n    this._isShown = false;\n    this._isTransitioning = true;\n    this._focustrap.deactivate();\n    this._element.classList.remove(CLASS_NAME_SHOW$4);\n    this._queueCallback(() => this._hideModal(), this._element, this._isAnimated());\n  }\n  dispose() {\n    EventHandler.off(window, EVENT_KEY$4);\n    EventHandler.off(this._dialog, EVENT_KEY$4);\n    this._backdrop.dispose();\n    this._focustrap.deactivate();\n    super.dispose();\n  }\n  handleUpdate() {\n    this._adjustDialog();\n  }\n\n  // Private\n  _initializeBackDrop() {\n    return new Backdrop({\n      isVisible: Boolean(this._config.backdrop),\n      // 'static' option will be translated to true, and booleans will keep their value,\n      isAnimated: this._isAnimated()\n    });\n  }\n  _initializeFocusTrap() {\n    return new FocusTrap({\n      trapElement: this._element\n    });\n  }\n  _showElement(relatedTarget) {\n    // try to append dynamic modal\n    if (!document.body.contains(this._element)) {\n      document.body.append(this._element);\n    }\n    this._element.style.display = 'block';\n    this._element.removeAttribute('aria-hidden');\n    this._element.setAttribute('aria-modal', true);\n    this._element.setAttribute('role', 'dialog');\n    this._element.scrollTop = 0;\n    const modalBody = SelectorEngine.findOne(SELECTOR_MODAL_BODY, this._dialog);\n    if (modalBody) {\n      modalBody.scrollTop = 0;\n    }\n    reflow(this._element);\n    this._element.classList.add(CLASS_NAME_SHOW$4);\n    const transitionComplete = () => {\n      if (this._config.focus) {\n        this._focustrap.activate();\n      }\n      this._isTransitioning = false;\n      EventHandler.trigger(this._element, EVENT_SHOWN$4, {\n        relatedTarget\n      });\n    };\n    this._queueCallback(transitionComplete, this._dialog, this._isAnimated());\n  }\n  _addEventListeners() {\n    EventHandler.on(this._element, EVENT_KEYDOWN_DISMISS$1, event => {\n      if (event.key !== ESCAPE_KEY$1) {\n        return;\n      }\n      if (this._config.keyboard) {\n        this.hide();\n        return;\n      }\n      this._triggerBackdropTransition();\n    });\n    EventHandler.on(window, EVENT_RESIZE$1, () => {\n      if (this._isShown && !this._isTransitioning) {\n        this._adjustDialog();\n      }\n    });\n    EventHandler.on(this._element, EVENT_MOUSEDOWN_DISMISS, event => {\n      // a bad trick to segregate clicks that may start inside dialog but end outside, and avoid listen to scrollbar clicks\n      EventHandler.one(this._element, EVENT_CLICK_DISMISS, event2 => {\n        if (this._element !== event.target || this._element !== event2.target) {\n          return;\n        }\n        if (this._config.backdrop === 'static') {\n          this._triggerBackdropTransition();\n          return;\n        }\n        if (this._config.backdrop) {\n          this.hide();\n        }\n      });\n    });\n  }\n  _hideModal() {\n    this._element.style.display = 'none';\n    this._element.setAttribute('aria-hidden', true);\n    this._element.removeAttribute('aria-modal');\n    this._element.removeAttribute('role');\n    this._isTransitioning = false;\n    this._backdrop.hide(() => {\n      document.body.classList.remove(CLASS_NAME_OPEN);\n      this._resetAdjustments();\n      this._scrollBar.reset();\n      EventHandler.trigger(this._element, EVENT_HIDDEN$4);\n    });\n  }\n  _isAnimated() {\n    return this._element.classList.contains(CLASS_NAME_FADE$3);\n  }\n  _triggerBackdropTransition() {\n    const hideEvent = EventHandler.trigger(this._element, EVENT_HIDE_PREVENTED$1);\n    if (hideEvent.defaultPrevented) {\n      return;\n    }\n    const isModalOverflowing = this._element.scrollHeight > document.documentElement.clientHeight;\n    const initialOverflowY = this._element.style.overflowY;\n    // return if the following background transition hasn't yet completed\n    if (initialOverflowY === 'hidden' || this._element.classList.contains(CLASS_NAME_STATIC)) {\n      return;\n    }\n    if (!isModalOverflowing) {\n      this._element.style.overflowY = 'hidden';\n    }\n    this._element.classList.add(CLASS_NAME_STATIC);\n    this._queueCallback(() => {\n      this._element.classList.remove(CLASS_NAME_STATIC);\n      this._queueCallback(() => {\n        this._element.style.overflowY = initialOverflowY;\n      }, this._dialog);\n    }, this._dialog);\n    this._element.focus();\n  }\n\n  /**\n   * The following methods are used to handle overflowing modals\n   */\n\n  _adjustDialog() {\n    const isModalOverflowing = this._element.scrollHeight > document.documentElement.clientHeight;\n    const scrollbarWidth = this._scrollBar.getWidth();\n    const isBodyOverflowing = scrollbarWidth > 0;\n    if (isBodyOverflowing && !isModalOverflowing) {\n      const property = isRTL() ? 'paddingLeft' : 'paddingRight';\n      this._element.style[property] = `${scrollbarWidth}px`;\n    }\n    if (!isBodyOverflowing && isModalOverflowing) {\n      const property = isRTL() ? 'paddingRight' : 'paddingLeft';\n      this._element.style[property] = `${scrollbarWidth}px`;\n    }\n  }\n  _resetAdjustments() {\n    this._element.style.paddingLeft = '';\n    this._element.style.paddingRight = '';\n  }\n\n  // Static\n  static jQueryInterface(config, relatedTarget) {\n    return this.each(function () {\n      const data = Modal.getOrCreateInstance(this, config);\n      if (typeof config !== 'string') {\n        return;\n      }\n      if (typeof data[config] === 'undefined') {\n        throw new TypeError(`No method named \"${config}\"`);\n      }\n      data[config](relatedTarget);\n    });\n  }\n}\n\n/**\n * Data API implementation\n */\n\nEventHandler.on(document, EVENT_CLICK_DATA_API$2, SELECTOR_DATA_TOGGLE$2, function (event) {\n  const target = SelectorEngine.getElementFromSelector(this);\n  if (['A', 'AREA'].includes(this.tagName)) {\n    event.preventDefault();\n  }\n  EventHandler.one(target, EVENT_SHOW$4, showEvent => {\n    if (showEvent.defaultPrevented) {\n      // only register focus restorer if modal will actually get shown\n      return;\n    }\n    EventHandler.one(target, EVENT_HIDDEN$4, () => {\n      if (isVisible(this)) {\n        this.focus();\n      }\n    });\n  });\n\n  // avoid conflict when clicking modal toggler while another one is open\n  const alreadyOpen = SelectorEngine.findOne(OPEN_SELECTOR$1);\n  if (alreadyOpen) {\n    Modal.getInstance(alreadyOpen).hide();\n  }\n  const data = Modal.getOrCreateInstance(target);\n  data.toggle(this);\n});\nenableDismissTrigger(Modal);\n\n/**\n * jQuery\n */\n\ndefineJQueryPlugin(Modal);\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap offcanvas.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\n\n/**\n * Constants\n */\n\nconst NAME$6 = 'offcanvas';\nconst DATA_KEY$3 = 'bs.offcanvas';\nconst EVENT_KEY$3 = `.${DATA_KEY$3}`;\nconst DATA_API_KEY$1 = '.data-api';\nconst EVENT_LOAD_DATA_API$2 = `load${EVENT_KEY$3}${DATA_API_KEY$1}`;\nconst ESCAPE_KEY = 'Escape';\nconst CLASS_NAME_SHOW$3 = 'show';\nconst CLASS_NAME_SHOWING$1 = 'showing';\nconst CLASS_NAME_HIDING = 'hiding';\nconst CLASS_NAME_BACKDROP = 'offcanvas-backdrop';\nconst OPEN_SELECTOR = '.offcanvas.show';\nconst EVENT_SHOW$3 = `show${EVENT_KEY$3}`;\nconst EVENT_SHOWN$3 = `shown${EVENT_KEY$3}`;\nconst EVENT_HIDE$3 = `hide${EVENT_KEY$3}`;\nconst EVENT_HIDE_PREVENTED = `hidePrevented${EVENT_KEY$3}`;\nconst EVENT_HIDDEN$3 = `hidden${EVENT_KEY$3}`;\nconst EVENT_RESIZE = `resize${EVENT_KEY$3}`;\nconst EVENT_CLICK_DATA_API$1 = `click${EVENT_KEY$3}${DATA_API_KEY$1}`;\nconst EVENT_KEYDOWN_DISMISS = `keydown.dismiss${EVENT_KEY$3}`;\nconst SELECTOR_DATA_TOGGLE$1 = '[data-bs-toggle=\"offcanvas\"]';\nconst Default$5 = {\n  backdrop: true,\n  keyboard: true,\n  scroll: false\n};\nconst DefaultType$5 = {\n  backdrop: '(boolean|string)',\n  keyboard: 'boolean',\n  scroll: 'boolean'\n};\n\n/**\n * Class definition\n */\n\nclass Offcanvas extends BaseComponent {\n  constructor(element, config) {\n    super(element, config);\n    this._isShown = false;\n    this._backdrop = this._initializeBackDrop();\n    this._focustrap = this._initializeFocusTrap();\n    this._addEventListeners();\n  }\n\n  // Getters\n  static get Default() {\n    return Default$5;\n  }\n  static get DefaultType() {\n    return DefaultType$5;\n  }\n  static get NAME() {\n    return NAME$6;\n  }\n\n  // Public\n  toggle(relatedTarget) {\n    return this._isShown ? this.hide() : this.show(relatedTarget);\n  }\n  show(relatedTarget) {\n    if (this._isShown) {\n      return;\n    }\n    const showEvent = EventHandler.trigger(this._element, EVENT_SHOW$3, {\n      relatedTarget\n    });\n    if (showEvent.defaultPrevented) {\n      return;\n    }\n    this._isShown = true;\n    this._backdrop.show();\n    if (!this._config.scroll) {\n      new ScrollBarHelper().hide();\n    }\n    this._element.setAttribute('aria-modal', true);\n    this._element.setAttribute('role', 'dialog');\n    this._element.classList.add(CLASS_NAME_SHOWING$1);\n    const completeCallBack = () => {\n      if (!this._config.scroll || this._config.backdrop) {\n        this._focustrap.activate();\n      }\n      this._element.classList.add(CLASS_NAME_SHOW$3);\n      this._element.classList.remove(CLASS_NAME_SHOWING$1);\n      EventHandler.trigger(this._element, EVENT_SHOWN$3, {\n        relatedTarget\n      });\n    };\n    this._queueCallback(completeCallBack, this._element, true);\n  }\n  hide() {\n    if (!this._isShown) {\n      return;\n    }\n    const hideEvent = EventHandler.trigger(this._element, EVENT_HIDE$3);\n    if (hideEvent.defaultPrevented) {\n      return;\n    }\n    this._focustrap.deactivate();\n    this._element.blur();\n    this._isShown = false;\n    this._element.classList.add(CLASS_NAME_HIDING);\n    this._backdrop.hide();\n    const completeCallback = () => {\n      this._element.classList.remove(CLASS_NAME_SHOW$3, CLASS_NAME_HIDING);\n      this._element.removeAttribute('aria-modal');\n      this._element.removeAttribute('role');\n      if (!this._config.scroll) {\n        new ScrollBarHelper().reset();\n      }\n      EventHandler.trigger(this._element, EVENT_HIDDEN$3);\n    };\n    this._queueCallback(completeCallback, this._element, true);\n  }\n  dispose() {\n    this._backdrop.dispose();\n    this._focustrap.deactivate();\n    super.dispose();\n  }\n\n  // Private\n  _initializeBackDrop() {\n    const clickCallback = () => {\n      if (this._config.backdrop === 'static') {\n        EventHandler.trigger(this._element, EVENT_HIDE_PREVENTED);\n        return;\n      }\n      this.hide();\n    };\n\n    // 'static' option will be translated to true, and booleans will keep their value\n    const isVisible = Boolean(this._config.backdrop);\n    return new Backdrop({\n      className: CLASS_NAME_BACKDROP,\n      isVisible,\n      isAnimated: true,\n      rootElement: this._element.parentNode,\n      clickCallback: isVisible ? clickCallback : null\n    });\n  }\n  _initializeFocusTrap() {\n    return new FocusTrap({\n      trapElement: this._element\n    });\n  }\n  _addEventListeners() {\n    EventHandler.on(this._element, EVENT_KEYDOWN_DISMISS, event => {\n      if (event.key !== ESCAPE_KEY) {\n        return;\n      }\n      if (this._config.keyboard) {\n        this.hide();\n        return;\n      }\n      EventHandler.trigger(this._element, EVENT_HIDE_PREVENTED);\n    });\n  }\n\n  // Static\n  static jQueryInterface(config) {\n    return this.each(function () {\n      const data = Offcanvas.getOrCreateInstance(this, config);\n      if (typeof config !== 'string') {\n        return;\n      }\n      if (data[config] === undefined || config.startsWith('_') || config === 'constructor') {\n        throw new TypeError(`No method named \"${config}\"`);\n      }\n      data[config](this);\n    });\n  }\n}\n\n/**\n * Data API implementation\n */\n\nEventHandler.on(document, EVENT_CLICK_DATA_API$1, SELECTOR_DATA_TOGGLE$1, function (event) {\n  const target = SelectorEngine.getElementFromSelector(this);\n  if (['A', 'AREA'].includes(this.tagName)) {\n    event.preventDefault();\n  }\n  if (isDisabled(this)) {\n    return;\n  }\n  EventHandler.one(target, EVENT_HIDDEN$3, () => {\n    // focus on trigger when it is closed\n    if (isVisible(this)) {\n      this.focus();\n    }\n  });\n\n  // avoid conflict when clicking a toggler of an offcanvas, while another is open\n  const alreadyOpen = SelectorEngine.findOne(OPEN_SELECTOR);\n  if (alreadyOpen && alreadyOpen !== target) {\n    Offcanvas.getInstance(alreadyOpen).hide();\n  }\n  const data = Offcanvas.getOrCreateInstance(target);\n  data.toggle(this);\n});\nEventHandler.on(window, EVENT_LOAD_DATA_API$2, () => {\n  for (const selector of SelectorEngine.find(OPEN_SELECTOR)) {\n    Offcanvas.getOrCreateInstance(selector).show();\n  }\n});\nEventHandler.on(window, EVENT_RESIZE, () => {\n  for (const element of SelectorEngine.find('[aria-modal][class*=show][class*=offcanvas-]')) {\n    if (getComputedStyle(element).position !== 'fixed') {\n      Offcanvas.getOrCreateInstance(element).hide();\n    }\n  }\n});\nenableDismissTrigger(Offcanvas);\n\n/**\n * jQuery\n */\n\ndefineJQueryPlugin(Offcanvas);\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap util/sanitizer.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\n// js-docs-start allow-list\nconst ARIA_ATTRIBUTE_PATTERN = /^aria-[\\w-]*$/i;\nconst DefaultAllowlist = {\n  // Global attributes allowed on any supplied element below.\n  '*': ['class', 'dir', 'id', 'lang', 'role', ARIA_ATTRIBUTE_PATTERN],\n  a: ['target', 'href', 'title', 'rel'],\n  area: [],\n  b: [],\n  br: [],\n  col: [],\n  code: [],\n  dd: [],\n  div: [],\n  dl: [],\n  dt: [],\n  em: [],\n  hr: [],\n  h1: [],\n  h2: [],\n  h3: [],\n  h4: [],\n  h5: [],\n  h6: [],\n  i: [],\n  img: ['src', 'srcset', 'alt', 'title', 'width', 'height'],\n  li: [],\n  ol: [],\n  p: [],\n  pre: [],\n  s: [],\n  small: [],\n  span: [],\n  sub: [],\n  sup: [],\n  strong: [],\n  u: [],\n  ul: []\n};\n// js-docs-end allow-list\n\nconst uriAttributes = new Set(['background', 'cite', 'href', 'itemtype', 'longdesc', 'poster', 'src', 'xlink:href']);\n\n/**\n * A pattern that recognizes URLs that are safe wrt. XSS in URL navigation\n * contexts.\n *\n * Shout-out to Angular https://github.com/angular/angular/blob/15.2.8/packages/core/src/sanitization/url_sanitizer.ts#L38\n */\n// eslint-disable-next-line unicorn/better-regex\nconst SAFE_URL_PATTERN = /^(?!javascript:)(?:[a-z0-9+.-]+:|[^&:/?#]*(?:[/?#]|$))/i;\nconst allowedAttribute = (attribute, allowedAttributeList) => {\n  const attributeName = attribute.nodeName.toLowerCase();\n  if (allowedAttributeList.includes(attributeName)) {\n    if (uriAttributes.has(attributeName)) {\n      return Boolean(SAFE_URL_PATTERN.test(attribute.nodeValue));\n    }\n    return true;\n  }\n\n  // Check if a regular expression validates the attribute.\n  return allowedAttributeList.filter(attributeRegex => attributeRegex instanceof RegExp).some(regex => regex.test(attributeName));\n};\nfunction sanitizeHtml(unsafeHtml, allowList, sanitizeFunction) {\n  if (!unsafeHtml.length) {\n    return unsafeHtml;\n  }\n  if (sanitizeFunction && typeof sanitizeFunction === 'function') {\n    return sanitizeFunction(unsafeHtml);\n  }\n  const domParser = new window.DOMParser();\n  const createdDocument = domParser.parseFromString(unsafeHtml, 'text/html');\n  const elements = [].concat(...createdDocument.body.querySelectorAll('*'));\n  for (const element of elements) {\n    const elementName = element.nodeName.toLowerCase();\n    if (!Object.keys(allowList).includes(elementName)) {\n      element.remove();\n      continue;\n    }\n    const attributeList = [].concat(...element.attributes);\n    const allowedAttributes = [].concat(allowList['*'] || [], allowList[elementName] || []);\n    for (const attribute of attributeList) {\n      if (!allowedAttribute(attribute, allowedAttributes)) {\n        element.removeAttribute(attribute.nodeName);\n      }\n    }\n  }\n  return createdDocument.body.innerHTML;\n}\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap util/template-factory.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\n\n/**\n * Constants\n */\n\nconst NAME$5 = 'TemplateFactory';\nconst Default$4 = {\n  allowList: DefaultAllowlist,\n  content: {},\n  // { selector : text ,  selector2 : text2 , }\n  extraClass: '',\n  html: false,\n  sanitize: true,\n  sanitizeFn: null,\n  template: '<div></div>'\n};\nconst DefaultType$4 = {\n  allowList: 'object',\n  content: 'object',\n  extraClass: '(string|function)',\n  html: 'boolean',\n  sanitize: 'boolean',\n  sanitizeFn: '(null|function)',\n  template: 'string'\n};\nconst DefaultContentType = {\n  entry: '(string|element|function|null)',\n  selector: '(string|element)'\n};\n\n/**\n * Class definition\n */\n\nclass TemplateFactory extends Config {\n  constructor(config) {\n    super();\n    this._config = this._getConfig(config);\n  }\n\n  // Getters\n  static get Default() {\n    return Default$4;\n  }\n  static get DefaultType() {\n    return DefaultType$4;\n  }\n  static get NAME() {\n    return NAME$5;\n  }\n\n  // Public\n  getContent() {\n    return Object.values(this._config.content).map(config => this._resolvePossibleFunction(config)).filter(Boolean);\n  }\n  hasContent() {\n    return this.getContent().length > 0;\n  }\n  changeContent(content) {\n    this._checkContent(content);\n    this._config.content = {\n      ...this._config.content,\n      ...content\n    };\n    return this;\n  }\n  toHtml() {\n    const templateWrapper = document.createElement('div');\n    templateWrapper.innerHTML = this._maybeSanitize(this._config.template);\n    for (const [selector, text] of Object.entries(this._config.content)) {\n      this._setContent(templateWrapper, text, selector);\n    }\n    const template = templateWrapper.children[0];\n    const extraClass = this._resolvePossibleFunction(this._config.extraClass);\n    if (extraClass) {\n      template.classList.add(...extraClass.split(' '));\n    }\n    return template;\n  }\n\n  // Private\n  _typeCheckConfig(config) {\n    super._typeCheckConfig(config);\n    this._checkContent(config.content);\n  }\n  _checkContent(arg) {\n    for (const [selector, content] of Object.entries(arg)) {\n      super._typeCheckConfig({\n        selector,\n        entry: content\n      }, DefaultContentType);\n    }\n  }\n  _setContent(template, content, selector) {\n    const templateElement = SelectorEngine.findOne(selector, template);\n    if (!templateElement) {\n      return;\n    }\n    content = this._resolvePossibleFunction(content);\n    if (!content) {\n      templateElement.remove();\n      return;\n    }\n    if (isElement(content)) {\n      this._putElementInTemplate(getElement(content), templateElement);\n      return;\n    }\n    if (this._config.html) {\n      templateElement.innerHTML = this._maybeSanitize(content);\n      return;\n    }\n    templateElement.textContent = content;\n  }\n  _maybeSanitize(arg) {\n    return this._config.sanitize ? sanitizeHtml(arg, this._config.allowList, this._config.sanitizeFn) : arg;\n  }\n  _resolvePossibleFunction(arg) {\n    return execute(arg, [this]);\n  }\n  _putElementInTemplate(element, templateElement) {\n    if (this._config.html) {\n      templateElement.innerHTML = '';\n      templateElement.append(element);\n      return;\n    }\n    templateElement.textContent = element.textContent;\n  }\n}\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap tooltip.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\n\n/**\n * Constants\n */\n\nconst NAME$4 = 'tooltip';\nconst DISALLOWED_ATTRIBUTES = new Set(['sanitize', 'allowList', 'sanitizeFn']);\nconst CLASS_NAME_FADE$2 = 'fade';\nconst CLASS_NAME_MODAL = 'modal';\nconst CLASS_NAME_SHOW$2 = 'show';\nconst SELECTOR_TOOLTIP_INNER = '.tooltip-inner';\nconst SELECTOR_MODAL = `.${CLASS_NAME_MODAL}`;\nconst EVENT_MODAL_HIDE = 'hide.bs.modal';\nconst TRIGGER_HOVER = 'hover';\nconst TRIGGER_FOCUS = 'focus';\nconst TRIGGER_CLICK = 'click';\nconst TRIGGER_MANUAL = 'manual';\nconst EVENT_HIDE$2 = 'hide';\nconst EVENT_HIDDEN$2 = 'hidden';\nconst EVENT_SHOW$2 = 'show';\nconst EVENT_SHOWN$2 = 'shown';\nconst EVENT_INSERTED = 'inserted';\nconst EVENT_CLICK$1 = 'click';\nconst EVENT_FOCUSIN$1 = 'focusin';\nconst EVENT_FOCUSOUT$1 = 'focusout';\nconst EVENT_MOUSEENTER = 'mouseenter';\nconst EVENT_MOUSELEAVE = 'mouseleave';\nconst AttachmentMap = {\n  AUTO: 'auto',\n  TOP: 'top',\n  RIGHT: isRTL() ? 'left' : 'right',\n  BOTTOM: 'bottom',\n  LEFT: isRTL() ? 'right' : 'left'\n};\nconst Default$3 = {\n  allowList: DefaultAllowlist,\n  animation: true,\n  boundary: 'clippingParents',\n  container: false,\n  customClass: '',\n  delay: 0,\n  fallbackPlacements: ['top', 'right', 'bottom', 'left'],\n  html: false,\n  offset: [0, 6],\n  placement: 'top',\n  popperConfig: null,\n  sanitize: true,\n  sanitizeFn: null,\n  selector: false,\n  template: '<div class=\"tooltip\" role=\"tooltip\">' + '<div class=\"tooltip-arrow\"></div>' + '<div class=\"tooltip-inner\"></div>' + '</div>',\n  title: '',\n  trigger: 'hover focus'\n};\nconst DefaultType$3 = {\n  allowList: 'object',\n  animation: 'boolean',\n  boundary: '(string|element)',\n  container: '(string|element|boolean)',\n  customClass: '(string|function)',\n  delay: '(number|object)',\n  fallbackPlacements: 'array',\n  html: 'boolean',\n  offset: '(array|string|function)',\n  placement: '(string|function)',\n  popperConfig: '(null|object|function)',\n  sanitize: 'boolean',\n  sanitizeFn: '(null|function)',\n  selector: '(string|boolean)',\n  template: 'string',\n  title: '(string|element|function)',\n  trigger: 'string'\n};\n\n/**\n * Class definition\n */\n\nclass Tooltip extends BaseComponent {\n  constructor(element, config) {\n    if (typeof Popper === 'undefined') {\n      throw new TypeError('Bootstrap\\'s tooltips require Popper (https://popper.js.org)');\n    }\n    super(element, config);\n\n    // Private\n    this._isEnabled = true;\n    this._timeout = 0;\n    this._isHovered = null;\n    this._activeTrigger = {};\n    this._popper = null;\n    this._templateFactory = null;\n    this._newContent = null;\n\n    // Protected\n    this.tip = null;\n    this._setListeners();\n    if (!this._config.selector) {\n      this._fixTitle();\n    }\n  }\n\n  // Getters\n  static get Default() {\n    return Default$3;\n  }\n  static get DefaultType() {\n    return DefaultType$3;\n  }\n  static get NAME() {\n    return NAME$4;\n  }\n\n  // Public\n  enable() {\n    this._isEnabled = true;\n  }\n  disable() {\n    this._isEnabled = false;\n  }\n  toggleEnabled() {\n    this._isEnabled = !this._isEnabled;\n  }\n  toggle() {\n    if (!this._isEnabled) {\n      return;\n    }\n    this._activeTrigger.click = !this._activeTrigger.click;\n    if (this._isShown()) {\n      this._leave();\n      return;\n    }\n    this._enter();\n  }\n  dispose() {\n    clearTimeout(this._timeout);\n    EventHandler.off(this._element.closest(SELECTOR_MODAL), EVENT_MODAL_HIDE, this._hideModalHandler);\n    if (this._element.getAttribute('data-bs-original-title')) {\n      this._element.setAttribute('title', this._element.getAttribute('data-bs-original-title'));\n    }\n    this._disposePopper();\n    super.dispose();\n  }\n  show() {\n    if (this._element.style.display === 'none') {\n      throw new Error('Please use show on visible elements');\n    }\n    if (!(this._isWithContent() && this._isEnabled)) {\n      return;\n    }\n    const showEvent = EventHandler.trigger(this._element, this.constructor.eventName(EVENT_SHOW$2));\n    const shadowRoot = findShadowRoot(this._element);\n    const isInTheDom = (shadowRoot || this._element.ownerDocument.documentElement).contains(this._element);\n    if (showEvent.defaultPrevented || !isInTheDom) {\n      return;\n    }\n\n    // TODO: v6 remove this or make it optional\n    this._disposePopper();\n    const tip = this._getTipElement();\n    this._element.setAttribute('aria-describedby', tip.getAttribute('id'));\n    const {\n      container\n    } = this._config;\n    if (!this._element.ownerDocument.documentElement.contains(this.tip)) {\n      container.append(tip);\n      EventHandler.trigger(this._element, this.constructor.eventName(EVENT_INSERTED));\n    }\n    this._popper = this._createPopper(tip);\n    tip.classList.add(CLASS_NAME_SHOW$2);\n\n    // If this is a touch-enabled device we add extra\n    // empty mouseover listeners to the body's immediate children;\n    // only needed because of broken event delegation on iOS\n    // https://www.quirksmode.org/blog/archives/2014/02/mouse_event_bub.html\n    if ('ontouchstart' in document.documentElement) {\n      for (const element of [].concat(...document.body.children)) {\n        EventHandler.on(element, 'mouseover', noop);\n      }\n    }\n    const complete = () => {\n      EventHandler.trigger(this._element, this.constructor.eventName(EVENT_SHOWN$2));\n      if (this._isHovered === false) {\n        this._leave();\n      }\n      this._isHovered = false;\n    };\n    this._queueCallback(complete, this.tip, this._isAnimated());\n  }\n  hide() {\n    if (!this._isShown()) {\n      return;\n    }\n    const hideEvent = EventHandler.trigger(this._element, this.constructor.eventName(EVENT_HIDE$2));\n    if (hideEvent.defaultPrevented) {\n      return;\n    }\n    const tip = this._getTipElement();\n    tip.classList.remove(CLASS_NAME_SHOW$2);\n\n    // If this is a touch-enabled device we remove the extra\n    // empty mouseover listeners we added for iOS support\n    if ('ontouchstart' in document.documentElement) {\n      for (const element of [].concat(...document.body.children)) {\n        EventHandler.off(element, 'mouseover', noop);\n      }\n    }\n    this._activeTrigger[TRIGGER_CLICK] = false;\n    this._activeTrigger[TRIGGER_FOCUS] = false;\n    this._activeTrigger[TRIGGER_HOVER] = false;\n    this._isHovered = null; // it is a trick to support manual triggering\n\n    const complete = () => {\n      if (this._isWithActiveTrigger()) {\n        return;\n      }\n      if (!this._isHovered) {\n        this._disposePopper();\n      }\n      this._element.removeAttribute('aria-describedby');\n      EventHandler.trigger(this._element, this.constructor.eventName(EVENT_HIDDEN$2));\n    };\n    this._queueCallback(complete, this.tip, this._isAnimated());\n  }\n  update() {\n    if (this._popper) {\n      this._popper.update();\n    }\n  }\n\n  // Protected\n  _isWithContent() {\n    return Boolean(this._getTitle());\n  }\n  _getTipElement() {\n    if (!this.tip) {\n      this.tip = this._createTipElement(this._newContent || this._getContentForTemplate());\n    }\n    return this.tip;\n  }\n  _createTipElement(content) {\n    const tip = this._getTemplateFactory(content).toHtml();\n\n    // TODO: remove this check in v6\n    if (!tip) {\n      return null;\n    }\n    tip.classList.remove(CLASS_NAME_FADE$2, CLASS_NAME_SHOW$2);\n    // TODO: v6 the following can be achieved with CSS only\n    tip.classList.add(`bs-${this.constructor.NAME}-auto`);\n    const tipId = getUID(this.constructor.NAME).toString();\n    tip.setAttribute('id', tipId);\n    if (this._isAnimated()) {\n      tip.classList.add(CLASS_NAME_FADE$2);\n    }\n    return tip;\n  }\n  setContent(content) {\n    this._newContent = content;\n    if (this._isShown()) {\n      this._disposePopper();\n      this.show();\n    }\n  }\n  _getTemplateFactory(content) {\n    if (this._templateFactory) {\n      this._templateFactory.changeContent(content);\n    } else {\n      this._templateFactory = new TemplateFactory({\n        ...this._config,\n        // the `content` var has to be after `this._config`\n        // to override config.content in case of popover\n        content,\n        extraClass: this._resolvePossibleFunction(this._config.customClass)\n      });\n    }\n    return this._templateFactory;\n  }\n  _getContentForTemplate() {\n    return {\n      [SELECTOR_TOOLTIP_INNER]: this._getTitle()\n    };\n  }\n  _getTitle() {\n    return this._resolvePossibleFunction(this._config.title) || this._element.getAttribute('data-bs-original-title');\n  }\n\n  // Private\n  _initializeOnDelegatedTarget(event) {\n    return this.constructor.getOrCreateInstance(event.delegateTarget, this._getDelegateConfig());\n  }\n  _isAnimated() {\n    return this._config.animation || this.tip && this.tip.classList.contains(CLASS_NAME_FADE$2);\n  }\n  _isShown() {\n    return this.tip && this.tip.classList.contains(CLASS_NAME_SHOW$2);\n  }\n  _createPopper(tip) {\n    const placement = execute(this._config.placement, [this, tip, this._element]);\n    const attachment = AttachmentMap[placement.toUpperCase()];\n    return Popper.createPopper(this._element, tip, this._getPopperConfig(attachment));\n  }\n  _getOffset() {\n    const {\n      offset\n    } = this._config;\n    if (typeof offset === 'string') {\n      return offset.split(',').map(value => Number.parseInt(value, 10));\n    }\n    if (typeof offset === 'function') {\n      return popperData => offset(popperData, this._element);\n    }\n    return offset;\n  }\n  _resolvePossibleFunction(arg) {\n    return execute(arg, [this._element]);\n  }\n  _getPopperConfig(attachment) {\n    const defaultBsPopperConfig = {\n      placement: attachment,\n      modifiers: [{\n        name: 'flip',\n        options: {\n          fallbackPlacements: this._config.fallbackPlacements\n        }\n      }, {\n        name: 'offset',\n        options: {\n          offset: this._getOffset()\n        }\n      }, {\n        name: 'preventOverflow',\n        options: {\n          boundary: this._config.boundary\n        }\n      }, {\n        name: 'arrow',\n        options: {\n          element: `.${this.constructor.NAME}-arrow`\n        }\n      }, {\n        name: 'preSetPlacement',\n        enabled: true,\n        phase: 'beforeMain',\n        fn: data => {\n          // Pre-set Popper's placement attribute in order to read the arrow sizes properly.\n          // Otherwise, Popper mixes up the width and height dimensions since the initial arrow style is for top placement\n          this._getTipElement().setAttribute('data-popper-placement', data.state.placement);\n        }\n      }]\n    };\n    return {\n      ...defaultBsPopperConfig,\n      ...execute(this._config.popperConfig, [defaultBsPopperConfig])\n    };\n  }\n  _setListeners() {\n    const triggers = this._config.trigger.split(' ');\n    for (const trigger of triggers) {\n      if (trigger === 'click') {\n        EventHandler.on(this._element, this.constructor.eventName(EVENT_CLICK$1), this._config.selector, event => {\n          const context = this._initializeOnDelegatedTarget(event);\n          context.toggle();\n        });\n      } else if (trigger !== TRIGGER_MANUAL) {\n        const eventIn = trigger === TRIGGER_HOVER ? this.constructor.eventName(EVENT_MOUSEENTER) : this.constructor.eventName(EVENT_FOCUSIN$1);\n        const eventOut = trigger === TRIGGER_HOVER ? this.constructor.eventName(EVENT_MOUSELEAVE) : this.constructor.eventName(EVENT_FOCUSOUT$1);\n        EventHandler.on(this._element, eventIn, this._config.selector, event => {\n          const context = this._initializeOnDelegatedTarget(event);\n          context._activeTrigger[event.type === 'focusin' ? TRIGGER_FOCUS : TRIGGER_HOVER] = true;\n          context._enter();\n        });\n        EventHandler.on(this._element, eventOut, this._config.selector, event => {\n          const context = this._initializeOnDelegatedTarget(event);\n          context._activeTrigger[event.type === 'focusout' ? TRIGGER_FOCUS : TRIGGER_HOVER] = context._element.contains(event.relatedTarget);\n          context._leave();\n        });\n      }\n    }\n    this._hideModalHandler = () => {\n      if (this._element) {\n        this.hide();\n      }\n    };\n    EventHandler.on(this._element.closest(SELECTOR_MODAL), EVENT_MODAL_HIDE, this._hideModalHandler);\n  }\n  _fixTitle() {\n    const title = this._element.getAttribute('title');\n    if (!title) {\n      return;\n    }\n    if (!this._element.getAttribute('aria-label') && !this._element.textContent.trim()) {\n      this._element.setAttribute('aria-label', title);\n    }\n    this._element.setAttribute('data-bs-original-title', title); // DO NOT USE IT. Is only for backwards compatibility\n    this._element.removeAttribute('title');\n  }\n  _enter() {\n    if (this._isShown() || this._isHovered) {\n      this._isHovered = true;\n      return;\n    }\n    this._isHovered = true;\n    this._setTimeout(() => {\n      if (this._isHovered) {\n        this.show();\n      }\n    }, this._config.delay.show);\n  }\n  _leave() {\n    if (this._isWithActiveTrigger()) {\n      return;\n    }\n    this._isHovered = false;\n    this._setTimeout(() => {\n      if (!this._isHovered) {\n        this.hide();\n      }\n    }, this._config.delay.hide);\n  }\n  _setTimeout(handler, timeout) {\n    clearTimeout(this._timeout);\n    this._timeout = setTimeout(handler, timeout);\n  }\n  _isWithActiveTrigger() {\n    return Object.values(this._activeTrigger).includes(true);\n  }\n  _getConfig(config) {\n    const dataAttributes = Manipulator.getDataAttributes(this._element);\n    for (const dataAttribute of Object.keys(dataAttributes)) {\n      if (DISALLOWED_ATTRIBUTES.has(dataAttribute)) {\n        delete dataAttributes[dataAttribute];\n      }\n    }\n    config = {\n      ...dataAttributes,\n      ...(typeof config === 'object' && config ? config : {})\n    };\n    config = this._mergeConfigObj(config);\n    config = this._configAfterMerge(config);\n    this._typeCheckConfig(config);\n    return config;\n  }\n  _configAfterMerge(config) {\n    config.container = config.container === false ? document.body : getElement(config.container);\n    if (typeof config.delay === 'number') {\n      config.delay = {\n        show: config.delay,\n        hide: config.delay\n      };\n    }\n    if (typeof config.title === 'number') {\n      config.title = config.title.toString();\n    }\n    if (typeof config.content === 'number') {\n      config.content = config.content.toString();\n    }\n    return config;\n  }\n  _getDelegateConfig() {\n    const config = {};\n    for (const [key, value] of Object.entries(this._config)) {\n      if (this.constructor.Default[key] !== value) {\n        config[key] = value;\n      }\n    }\n    config.selector = false;\n    config.trigger = 'manual';\n\n    // In the future can be replaced with:\n    // const keysWithDifferentValues = Object.entries(this._config).filter(entry => this.constructor.Default[entry[0]] !== this._config[entry[0]])\n    // `Object.fromEntries(keysWithDifferentValues)`\n    return config;\n  }\n  _disposePopper() {\n    if (this._popper) {\n      this._popper.destroy();\n      this._popper = null;\n    }\n    if (this.tip) {\n      this.tip.remove();\n      this.tip = null;\n    }\n  }\n\n  // Static\n  static jQueryInterface(config) {\n    return this.each(function () {\n      const data = Tooltip.getOrCreateInstance(this, config);\n      if (typeof config !== 'string') {\n        return;\n      }\n      if (typeof data[config] === 'undefined') {\n        throw new TypeError(`No method named \"${config}\"`);\n      }\n      data[config]();\n    });\n  }\n}\n\n/**\n * jQuery\n */\n\ndefineJQueryPlugin(Tooltip);\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap popover.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\n\n/**\n * Constants\n */\n\nconst NAME$3 = 'popover';\nconst SELECTOR_TITLE = '.popover-header';\nconst SELECTOR_CONTENT = '.popover-body';\nconst Default$2 = {\n  ...Tooltip.Default,\n  content: '',\n  offset: [0, 8],\n  placement: 'right',\n  template: '<div class=\"popover\" role=\"tooltip\">' + '<div class=\"popover-arrow\"></div>' + '<h3 class=\"popover-header\"></h3>' + '<div class=\"popover-body\"></div>' + '</div>',\n  trigger: 'click'\n};\nconst DefaultType$2 = {\n  ...Tooltip.DefaultType,\n  content: '(null|string|element|function)'\n};\n\n/**\n * Class definition\n */\n\nclass Popover extends Tooltip {\n  // Getters\n  static get Default() {\n    return Default$2;\n  }\n  static get DefaultType() {\n    return DefaultType$2;\n  }\n  static get NAME() {\n    return NAME$3;\n  }\n\n  // Overrides\n  _isWithContent() {\n    return this._getTitle() || this._getContent();\n  }\n\n  // Private\n  _getContentForTemplate() {\n    return {\n      [SELECTOR_TITLE]: this._getTitle(),\n      [SELECTOR_CONTENT]: this._getContent()\n    };\n  }\n  _getContent() {\n    return this._resolvePossibleFunction(this._config.content);\n  }\n\n  // Static\n  static jQueryInterface(config) {\n    return this.each(function () {\n      const data = Popover.getOrCreateInstance(this, config);\n      if (typeof config !== 'string') {\n        return;\n      }\n      if (typeof data[config] === 'undefined') {\n        throw new TypeError(`No method named \"${config}\"`);\n      }\n      data[config]();\n    });\n  }\n}\n\n/**\n * jQuery\n */\n\ndefineJQueryPlugin(Popover);\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap scrollspy.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\n\n/**\n * Constants\n */\n\nconst NAME$2 = 'scrollspy';\nconst DATA_KEY$2 = 'bs.scrollspy';\nconst EVENT_KEY$2 = `.${DATA_KEY$2}`;\nconst DATA_API_KEY = '.data-api';\nconst EVENT_ACTIVATE = `activate${EVENT_KEY$2}`;\nconst EVENT_CLICK = `click${EVENT_KEY$2}`;\nconst EVENT_LOAD_DATA_API$1 = `load${EVENT_KEY$2}${DATA_API_KEY}`;\nconst CLASS_NAME_DROPDOWN_ITEM = 'dropdown-item';\nconst CLASS_NAME_ACTIVE$1 = 'active';\nconst SELECTOR_DATA_SPY = '[data-bs-spy=\"scroll\"]';\nconst SELECTOR_TARGET_LINKS = '[href]';\nconst SELECTOR_NAV_LIST_GROUP = '.nav, .list-group';\nconst SELECTOR_NAV_LINKS = '.nav-link';\nconst SELECTOR_NAV_ITEMS = '.nav-item';\nconst SELECTOR_LIST_ITEMS = '.list-group-item';\nconst SELECTOR_LINK_ITEMS = `${SELECTOR_NAV_LINKS}, ${SELECTOR_NAV_ITEMS} > ${SELECTOR_NAV_LINKS}, ${SELECTOR_LIST_ITEMS}`;\nconst SELECTOR_DROPDOWN = '.dropdown';\nconst SELECTOR_DROPDOWN_TOGGLE$1 = '.dropdown-toggle';\nconst Default$1 = {\n  offset: null,\n  // TODO: v6 @deprecated, keep it for backwards compatibility reasons\n  rootMargin: '0px 0px -25%',\n  smoothScroll: false,\n  target: null,\n  threshold: [0.1, 0.5, 1]\n};\nconst DefaultType$1 = {\n  offset: '(number|null)',\n  // TODO v6 @deprecated, keep it for backwards compatibility reasons\n  rootMargin: 'string',\n  smoothScroll: 'boolean',\n  target: 'element',\n  threshold: 'array'\n};\n\n/**\n * Class definition\n */\n\nclass ScrollSpy extends BaseComponent {\n  constructor(element, config) {\n    super(element, config);\n\n    // this._element is the observablesContainer and config.target the menu links wrapper\n    this._targetLinks = new Map();\n    this._observableSections = new Map();\n    this._rootElement = getComputedStyle(this._element).overflowY === 'visible' ? null : this._element;\n    this._activeTarget = null;\n    this._observer = null;\n    this._previousScrollData = {\n      visibleEntryTop: 0,\n      parentScrollTop: 0\n    };\n    this.refresh(); // initialize\n  }\n\n  // Getters\n  static get Default() {\n    return Default$1;\n  }\n  static get DefaultType() {\n    return DefaultType$1;\n  }\n  static get NAME() {\n    return NAME$2;\n  }\n\n  // Public\n  refresh() {\n    this._initializeTargetsAndObservables();\n    this._maybeEnableSmoothScroll();\n    if (this._observer) {\n      this._observer.disconnect();\n    } else {\n      this._observer = this._getNewObserver();\n    }\n    for (const section of this._observableSections.values()) {\n      this._observer.observe(section);\n    }\n  }\n  dispose() {\n    this._observer.disconnect();\n    super.dispose();\n  }\n\n  // Private\n  _configAfterMerge(config) {\n    // TODO: on v6 target should be given explicitly & remove the {target: 'ss-target'} case\n    config.target = getElement(config.target) || document.body;\n\n    // TODO: v6 Only for backwards compatibility reasons. Use rootMargin only\n    config.rootMargin = config.offset ? `${config.offset}px 0px -30%` : config.rootMargin;\n    if (typeof config.threshold === 'string') {\n      config.threshold = config.threshold.split(',').map(value => Number.parseFloat(value));\n    }\n    return config;\n  }\n  _maybeEnableSmoothScroll() {\n    if (!this._config.smoothScroll) {\n      return;\n    }\n\n    // unregister any previous listeners\n    EventHandler.off(this._config.target, EVENT_CLICK);\n    EventHandler.on(this._config.target, EVENT_CLICK, SELECTOR_TARGET_LINKS, event => {\n      const observableSection = this._observableSections.get(event.target.hash);\n      if (observableSection) {\n        event.preventDefault();\n        const root = this._rootElement || window;\n        const height = observableSection.offsetTop - this._element.offsetTop;\n        if (root.scrollTo) {\n          root.scrollTo({\n            top: height,\n            behavior: 'smooth'\n          });\n          return;\n        }\n\n        // Chrome 60 doesn't support `scrollTo`\n        root.scrollTop = height;\n      }\n    });\n  }\n  _getNewObserver() {\n    const options = {\n      root: this._rootElement,\n      threshold: this._config.threshold,\n      rootMargin: this._config.rootMargin\n    };\n    return new IntersectionObserver(entries => this._observerCallback(entries), options);\n  }\n\n  // The logic of selection\n  _observerCallback(entries) {\n    const targetElement = entry => this._targetLinks.get(`#${entry.target.id}`);\n    const activate = entry => {\n      this._previousScrollData.visibleEntryTop = entry.target.offsetTop;\n      this._process(targetElement(entry));\n    };\n    const parentScrollTop = (this._rootElement || document.documentElement).scrollTop;\n    const userScrollsDown = parentScrollTop >= this._previousScrollData.parentScrollTop;\n    this._previousScrollData.parentScrollTop = parentScrollTop;\n    for (const entry of entries) {\n      if (!entry.isIntersecting) {\n        this._activeTarget = null;\n        this._clearActiveClass(targetElement(entry));\n        continue;\n      }\n      const entryIsLowerThanPrevious = entry.target.offsetTop >= this._previousScrollData.visibleEntryTop;\n      // if we are scrolling down, pick the bigger offsetTop\n      if (userScrollsDown && entryIsLowerThanPrevious) {\n        activate(entry);\n        // if parent isn't scrolled, let's keep the first visible item, breaking the iteration\n        if (!parentScrollTop) {\n          return;\n        }\n        continue;\n      }\n\n      // if we are scrolling up, pick the smallest offsetTop\n      if (!userScrollsDown && !entryIsLowerThanPrevious) {\n        activate(entry);\n      }\n    }\n  }\n  _initializeTargetsAndObservables() {\n    this._targetLinks = new Map();\n    this._observableSections = new Map();\n    const targetLinks = SelectorEngine.find(SELECTOR_TARGET_LINKS, this._config.target);\n    for (const anchor of targetLinks) {\n      // ensure that the anchor has an id and is not disabled\n      if (!anchor.hash || isDisabled(anchor)) {\n        continue;\n      }\n      const observableSection = SelectorEngine.findOne(decodeURI(anchor.hash), this._element);\n\n      // ensure that the observableSection exists & is visible\n      if (isVisible(observableSection)) {\n        this._targetLinks.set(decodeURI(anchor.hash), anchor);\n        this._observableSections.set(anchor.hash, observableSection);\n      }\n    }\n  }\n  _process(target) {\n    if (this._activeTarget === target) {\n      return;\n    }\n    this._clearActiveClass(this._config.target);\n    this._activeTarget = target;\n    target.classList.add(CLASS_NAME_ACTIVE$1);\n    this._activateParents(target);\n    EventHandler.trigger(this._element, EVENT_ACTIVATE, {\n      relatedTarget: target\n    });\n  }\n  _activateParents(target) {\n    // Activate dropdown parents\n    if (target.classList.contains(CLASS_NAME_DROPDOWN_ITEM)) {\n      SelectorEngine.findOne(SELECTOR_DROPDOWN_TOGGLE$1, target.closest(SELECTOR_DROPDOWN)).classList.add(CLASS_NAME_ACTIVE$1);\n      return;\n    }\n    for (const listGroup of SelectorEngine.parents(target, SELECTOR_NAV_LIST_GROUP)) {\n      // Set triggered links parents as active\n      // With both <ul> and <nav> markup a parent is the previous sibling of any nav ancestor\n      for (const item of SelectorEngine.prev(listGroup, SELECTOR_LINK_ITEMS)) {\n        item.classList.add(CLASS_NAME_ACTIVE$1);\n      }\n    }\n  }\n  _clearActiveClass(parent) {\n    parent.classList.remove(CLASS_NAME_ACTIVE$1);\n    const activeNodes = SelectorEngine.find(`${SELECTOR_TARGET_LINKS}.${CLASS_NAME_ACTIVE$1}`, parent);\n    for (const node of activeNodes) {\n      node.classList.remove(CLASS_NAME_ACTIVE$1);\n    }\n  }\n\n  // Static\n  static jQueryInterface(config) {\n    return this.each(function () {\n      const data = ScrollSpy.getOrCreateInstance(this, config);\n      if (typeof config !== 'string') {\n        return;\n      }\n      if (data[config] === undefined || config.startsWith('_') || config === 'constructor') {\n        throw new TypeError(`No method named \"${config}\"`);\n      }\n      data[config]();\n    });\n  }\n}\n\n/**\n * Data API implementation\n */\n\nEventHandler.on(window, EVENT_LOAD_DATA_API$1, () => {\n  for (const spy of SelectorEngine.find(SELECTOR_DATA_SPY)) {\n    ScrollSpy.getOrCreateInstance(spy);\n  }\n});\n\n/**\n * jQuery\n */\n\ndefineJQueryPlugin(ScrollSpy);\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap tab.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\n\n/**\n * Constants\n */\n\nconst NAME$1 = 'tab';\nconst DATA_KEY$1 = 'bs.tab';\nconst EVENT_KEY$1 = `.${DATA_KEY$1}`;\nconst EVENT_HIDE$1 = `hide${EVENT_KEY$1}`;\nconst EVENT_HIDDEN$1 = `hidden${EVENT_KEY$1}`;\nconst EVENT_SHOW$1 = `show${EVENT_KEY$1}`;\nconst EVENT_SHOWN$1 = `shown${EVENT_KEY$1}`;\nconst EVENT_CLICK_DATA_API = `click${EVENT_KEY$1}`;\nconst EVENT_KEYDOWN = `keydown${EVENT_KEY$1}`;\nconst EVENT_LOAD_DATA_API = `load${EVENT_KEY$1}`;\nconst ARROW_LEFT_KEY = 'ArrowLeft';\nconst ARROW_RIGHT_KEY = 'ArrowRight';\nconst ARROW_UP_KEY = 'ArrowUp';\nconst ARROW_DOWN_KEY = 'ArrowDown';\nconst HOME_KEY = 'Home';\nconst END_KEY = 'End';\nconst CLASS_NAME_ACTIVE = 'active';\nconst CLASS_NAME_FADE$1 = 'fade';\nconst CLASS_NAME_SHOW$1 = 'show';\nconst CLASS_DROPDOWN = 'dropdown';\nconst SELECTOR_DROPDOWN_TOGGLE = '.dropdown-toggle';\nconst SELECTOR_DROPDOWN_MENU = '.dropdown-menu';\nconst NOT_SELECTOR_DROPDOWN_TOGGLE = `:not(${SELECTOR_DROPDOWN_TOGGLE})`;\nconst SELECTOR_TAB_PANEL = '.list-group, .nav, [role=\"tablist\"]';\nconst SELECTOR_OUTER = '.nav-item, .list-group-item';\nconst SELECTOR_INNER = `.nav-link${NOT_SELECTOR_DROPDOWN_TOGGLE}, .list-group-item${NOT_SELECTOR_DROPDOWN_TOGGLE}, [role=\"tab\"]${NOT_SELECTOR_DROPDOWN_TOGGLE}`;\nconst SELECTOR_DATA_TOGGLE = '[data-bs-toggle=\"tab\"], [data-bs-toggle=\"pill\"], [data-bs-toggle=\"list\"]'; // TODO: could only be `tab` in v6\nconst SELECTOR_INNER_ELEM = `${SELECTOR_INNER}, ${SELECTOR_DATA_TOGGLE}`;\nconst SELECTOR_DATA_TOGGLE_ACTIVE = `.${CLASS_NAME_ACTIVE}[data-bs-toggle=\"tab\"], .${CLASS_NAME_ACTIVE}[data-bs-toggle=\"pill\"], .${CLASS_NAME_ACTIVE}[data-bs-toggle=\"list\"]`;\n\n/**\n * Class definition\n */\n\nclass Tab extends BaseComponent {\n  constructor(element) {\n    super(element);\n    this._parent = this._element.closest(SELECTOR_TAB_PANEL);\n    if (!this._parent) {\n      return;\n      // TODO: should throw exception in v6\n      // throw new TypeError(`${element.outerHTML} has not a valid parent ${SELECTOR_INNER_ELEM}`)\n    }\n\n    // Set up initial aria attributes\n    this._setInitialAttributes(this._parent, this._getChildren());\n    EventHandler.on(this._element, EVENT_KEYDOWN, event => this._keydown(event));\n  }\n\n  // Getters\n  static get NAME() {\n    return NAME$1;\n  }\n\n  // Public\n  show() {\n    // Shows this elem and deactivate the active sibling if exists\n    const innerElem = this._element;\n    if (this._elemIsActive(innerElem)) {\n      return;\n    }\n\n    // Search for active tab on same parent to deactivate it\n    const active = this._getActiveElem();\n    const hideEvent = active ? EventHandler.trigger(active, EVENT_HIDE$1, {\n      relatedTarget: innerElem\n    }) : null;\n    const showEvent = EventHandler.trigger(innerElem, EVENT_SHOW$1, {\n      relatedTarget: active\n    });\n    if (showEvent.defaultPrevented || hideEvent && hideEvent.defaultPrevented) {\n      return;\n    }\n    this._deactivate(active, innerElem);\n    this._activate(innerElem, active);\n  }\n\n  // Private\n  _activate(element, relatedElem) {\n    if (!element) {\n      return;\n    }\n    element.classList.add(CLASS_NAME_ACTIVE);\n    this._activate(SelectorEngine.getElementFromSelector(element)); // Search and activate/show the proper section\n\n    const complete = () => {\n      if (element.getAttribute('role') !== 'tab') {\n        element.classList.add(CLASS_NAME_SHOW$1);\n        return;\n      }\n      element.removeAttribute('tabindex');\n      element.setAttribute('aria-selected', true);\n      this._toggleDropDown(element, true);\n      EventHandler.trigger(element, EVENT_SHOWN$1, {\n        relatedTarget: relatedElem\n      });\n    };\n    this._queueCallback(complete, element, element.classList.contains(CLASS_NAME_FADE$1));\n  }\n  _deactivate(element, relatedElem) {\n    if (!element) {\n      return;\n    }\n    element.classList.remove(CLASS_NAME_ACTIVE);\n    element.blur();\n    this._deactivate(SelectorEngine.getElementFromSelector(element)); // Search and deactivate the shown section too\n\n    const complete = () => {\n      if (element.getAttribute('role') !== 'tab') {\n        element.classList.remove(CLASS_NAME_SHOW$1);\n        return;\n      }\n      element.setAttribute('aria-selected', false);\n      element.setAttribute('tabindex', '-1');\n      this._toggleDropDown(element, false);\n      EventHandler.trigger(element, EVENT_HIDDEN$1, {\n        relatedTarget: relatedElem\n      });\n    };\n    this._queueCallback(complete, element, element.classList.contains(CLASS_NAME_FADE$1));\n  }\n  _keydown(event) {\n    if (![ARROW_LEFT_KEY, ARROW_RIGHT_KEY, ARROW_UP_KEY, ARROW_DOWN_KEY, HOME_KEY, END_KEY].includes(event.key)) {\n      return;\n    }\n    event.stopPropagation(); // stopPropagation/preventDefault both added to support up/down keys without scrolling the page\n    event.preventDefault();\n    const children = this._getChildren().filter(element => !isDisabled(element));\n    let nextActiveElement;\n    if ([HOME_KEY, END_KEY].includes(event.key)) {\n      nextActiveElement = children[event.key === HOME_KEY ? 0 : children.length - 1];\n    } else {\n      const isNext = [ARROW_RIGHT_KEY, ARROW_DOWN_KEY].includes(event.key);\n      nextActiveElement = getNextActiveElement(children, event.target, isNext, true);\n    }\n    if (nextActiveElement) {\n      nextActiveElement.focus({\n        preventScroll: true\n      });\n      Tab.getOrCreateInstance(nextActiveElement).show();\n    }\n  }\n  _getChildren() {\n    // collection of inner elements\n    return SelectorEngine.find(SELECTOR_INNER_ELEM, this._parent);\n  }\n  _getActiveElem() {\n    return this._getChildren().find(child => this._elemIsActive(child)) || null;\n  }\n  _setInitialAttributes(parent, children) {\n    this._setAttributeIfNotExists(parent, 'role', 'tablist');\n    for (const child of children) {\n      this._setInitialAttributesOnChild(child);\n    }\n  }\n  _setInitialAttributesOnChild(child) {\n    child = this._getInnerElement(child);\n    const isActive = this._elemIsActive(child);\n    const outerElem = this._getOuterElement(child);\n    child.setAttribute('aria-selected', isActive);\n    if (outerElem !== child) {\n      this._setAttributeIfNotExists(outerElem, 'role', 'presentation');\n    }\n    if (!isActive) {\n      child.setAttribute('tabindex', '-1');\n    }\n    this._setAttributeIfNotExists(child, 'role', 'tab');\n\n    // set attributes to the related panel too\n    this._setInitialAttributesOnTargetPanel(child);\n  }\n  _setInitialAttributesOnTargetPanel(child) {\n    const target = SelectorEngine.getElementFromSelector(child);\n    if (!target) {\n      return;\n    }\n    this._setAttributeIfNotExists(target, 'role', 'tabpanel');\n    if (child.id) {\n      this._setAttributeIfNotExists(target, 'aria-labelledby', `${child.id}`);\n    }\n  }\n  _toggleDropDown(element, open) {\n    const outerElem = this._getOuterElement(element);\n    if (!outerElem.classList.contains(CLASS_DROPDOWN)) {\n      return;\n    }\n    const toggle = (selector, className) => {\n      const element = SelectorEngine.findOne(selector, outerElem);\n      if (element) {\n        element.classList.toggle(className, open);\n      }\n    };\n    toggle(SELECTOR_DROPDOWN_TOGGLE, CLASS_NAME_ACTIVE);\n    toggle(SELECTOR_DROPDOWN_MENU, CLASS_NAME_SHOW$1);\n    outerElem.setAttribute('aria-expanded', open);\n  }\n  _setAttributeIfNotExists(element, attribute, value) {\n    if (!element.hasAttribute(attribute)) {\n      element.setAttribute(attribute, value);\n    }\n  }\n  _elemIsActive(elem) {\n    return elem.classList.contains(CLASS_NAME_ACTIVE);\n  }\n\n  // Try to get the inner element (usually the .nav-link)\n  _getInnerElement(elem) {\n    return elem.matches(SELECTOR_INNER_ELEM) ? elem : SelectorEngine.findOne(SELECTOR_INNER_ELEM, elem);\n  }\n\n  // Try to get the outer element (usually the .nav-item)\n  _getOuterElement(elem) {\n    return elem.closest(SELECTOR_OUTER) || elem;\n  }\n\n  // Static\n  static jQueryInterface(config) {\n    return this.each(function () {\n      const data = Tab.getOrCreateInstance(this);\n      if (typeof config !== 'string') {\n        return;\n      }\n      if (data[config] === undefined || config.startsWith('_') || config === 'constructor') {\n        throw new TypeError(`No method named \"${config}\"`);\n      }\n      data[config]();\n    });\n  }\n}\n\n/**\n * Data API implementation\n */\n\nEventHandler.on(document, EVENT_CLICK_DATA_API, SELECTOR_DATA_TOGGLE, function (event) {\n  if (['A', 'AREA'].includes(this.tagName)) {\n    event.preventDefault();\n  }\n  if (isDisabled(this)) {\n    return;\n  }\n  Tab.getOrCreateInstance(this).show();\n});\n\n/**\n * Initialize on focus\n */\nEventHandler.on(window, EVENT_LOAD_DATA_API, () => {\n  for (const element of SelectorEngine.find(SELECTOR_DATA_TOGGLE_ACTIVE)) {\n    Tab.getOrCreateInstance(element);\n  }\n});\n/**\n * jQuery\n */\n\ndefineJQueryPlugin(Tab);\n\n/**\n * --------------------------------------------------------------------------\n * Bootstrap toast.js\n * Licensed under MIT (https://github.com/twbs/bootstrap/blob/main/LICENSE)\n * --------------------------------------------------------------------------\n */\n\n\n/**\n * Constants\n */\n\nconst NAME = 'toast';\nconst DATA_KEY = 'bs.toast';\nconst EVENT_KEY = `.${DATA_KEY}`;\nconst EVENT_MOUSEOVER = `mouseover${EVENT_KEY}`;\nconst EVENT_MOUSEOUT = `mouseout${EVENT_KEY}`;\nconst EVENT_FOCUSIN = `focusin${EVENT_KEY}`;\nconst EVENT_FOCUSOUT = `focusout${EVENT_KEY}`;\nconst EVENT_HIDE = `hide${EVENT_KEY}`;\nconst EVENT_HIDDEN = `hidden${EVENT_KEY}`;\nconst EVENT_SHOW = `show${EVENT_KEY}`;\nconst EVENT_SHOWN = `shown${EVENT_KEY}`;\nconst CLASS_NAME_FADE = 'fade';\nconst CLASS_NAME_HIDE = 'hide'; // @deprecated - kept here only for backwards compatibility\nconst CLASS_NAME_SHOW = 'show';\nconst CLASS_NAME_SHOWING = 'showing';\nconst DefaultType = {\n  animation: 'boolean',\n  autohide: 'boolean',\n  delay: 'number'\n};\nconst Default = {\n  animation: true,\n  autohide: true,\n  delay: 5000\n};\n\n/**\n * Class definition\n */\n\nclass Toast extends BaseComponent {\n  constructor(element, config) {\n    super(element, config);\n    this._timeout = null;\n    this._hasMouseInteraction = false;\n    this._hasKeyboardInteraction = false;\n    this._setListeners();\n  }\n\n  // Getters\n  static get Default() {\n    return Default;\n  }\n  static get DefaultType() {\n    return DefaultType;\n  }\n  static get NAME() {\n    return NAME;\n  }\n\n  // Public\n  show() {\n    const showEvent = EventHandler.trigger(this._element, EVENT_SHOW);\n    if (showEvent.defaultPrevented) {\n      return;\n    }\n    this._clearTimeout();\n    if (this._config.animation) {\n      this._element.classList.add(CLASS_NAME_FADE);\n    }\n    const complete = () => {\n      this._element.classList.remove(CLASS_NAME_SHOWING);\n      EventHandler.trigger(this._element, EVENT_SHOWN);\n      this._maybeScheduleHide();\n    };\n    this._element.classList.remove(CLASS_NAME_HIDE); // @deprecated\n    reflow(this._element);\n    this._element.classList.add(CLASS_NAME_SHOW, CLASS_NAME_SHOWING);\n    this._queueCallback(complete, this._element, this._config.animation);\n  }\n  hide() {\n    if (!this.isShown()) {\n      return;\n    }\n    const hideEvent = EventHandler.trigger(this._element, EVENT_HIDE);\n    if (hideEvent.defaultPrevented) {\n      return;\n    }\n    const complete = () => {\n      this._element.classList.add(CLASS_NAME_HIDE); // @deprecated\n      this._element.classList.remove(CLASS_NAME_SHOWING, CLASS_NAME_SHOW);\n      EventHandler.trigger(this._element, EVENT_HIDDEN);\n    };\n    this._element.classList.add(CLASS_NAME_SHOWING);\n    this._queueCallback(complete, this._element, this._config.animation);\n  }\n  dispose() {\n    this._clearTimeout();\n    if (this.isShown()) {\n      this._element.classList.remove(CLASS_NAME_SHOW);\n    }\n    super.dispose();\n  }\n  isShown() {\n    return this._element.classList.contains(CLASS_NAME_SHOW);\n  }\n\n  // Private\n\n  _maybeScheduleHide() {\n    if (!this._config.autohide) {\n      return;\n    }\n    if (this._hasMouseInteraction || this._hasKeyboardInteraction) {\n      return;\n    }\n    this._timeout = setTimeout(() => {\n      this.hide();\n    }, this._config.delay);\n  }\n  _onInteraction(event, isInteracting) {\n    switch (event.type) {\n      case 'mouseover':\n      case 'mouseout':\n        {\n          this._hasMouseInteraction = isInteracting;\n          break;\n        }\n      case 'focusin':\n      case 'focusout':\n        {\n          this._hasKeyboardInteraction = isInteracting;\n          break;\n        }\n    }\n    if (isInteracting) {\n      this._clearTimeout();\n      return;\n    }\n    const nextElement = event.relatedTarget;\n    if (this._element === nextElement || this._element.contains(nextElement)) {\n      return;\n    }\n    this._maybeScheduleHide();\n  }\n  _setListeners() {\n    EventHandler.on(this._element, EVENT_MOUSEOVER, event => this._onInteraction(event, true));\n    EventHandler.on(this._element, EVENT_MOUSEOUT, event => this._onInteraction(event, false));\n    EventHandler.on(this._element, EVENT_FOCUSIN, event => this._onInteraction(event, true));\n    EventHandler.on(this._element, EVENT_FOCUSOUT, event => this._onInteraction(event, false));\n  }\n  _clearTimeout() {\n    clearTimeout(this._timeout);\n    this._timeout = null;\n  }\n\n  // Static\n  static jQueryInterface(config) {\n    return this.each(function () {\n      const data = Toast.getOrCreateInstance(this, config);\n      if (typeof config === 'string') {\n        if (typeof data[config] === 'undefined') {\n          throw new TypeError(`No method named \"${config}\"`);\n        }\n        data[config](this);\n      }\n    });\n  }\n}\n\n/**\n * Data API implementation\n */\n\nenableDismissTrigger(Toast);\n\n/**\n * jQuery\n */\n\ndefineJQueryPlugin(Toast);\n\nexport { Alert, Button, Carousel, Collapse, Dropdown, Modal, Offcanvas, Popover, ScrollSpy, Tab, Toast, Tooltip };\n//# sourceMappingURL=bootstrap.esm.js.map\n","import angular from \"angular\";\r\nimport { Tooltip } from \"bootstrap\";\r\n\r\n/**\r\n * Fires the necessary Bootstrap 5 initialization for the given element.\r\n * @example\r\n * ```html\r\n * <a href=\"#\" sxy-bs5-tooltip data-bs-toggle=\"tooltip\" data-bs-title=\"Default tooltip\">inline links</a>\r\n * ```\r\n */\r\nexport class Bs5Tooltip implements angular.IDirective {\r\n\r\n  /**\r\n   * Factory for directive registration.\r\n   * @ignore\r\n   */\r\n  public static salaxyBs5Tooltip() {\r\n    const factory = () => new Bs5Tooltip();\r\n    factory.$inject = [];\r\n    return factory;\r\n  }\r\n\r\n  /**\r\n   * Applies to attributes only.\r\n   * @ignore\r\n   */\r\n  public restrict = \"A\";\r\n\r\n  /**\r\n   * Creates a new instance of the directive.\r\n   */\r\n  constructor() {}\r\n\r\n  /**\r\n   * Attaches the appropriate Bootstrap scripts to the element.\r\n   * @ignore\r\n   */\r\n  public link(scope: any, element: JQLite, attrs: any) {\r\n    new Tooltip(element[0], {\r\n      title: \"<div>\" + attrs.title + \"</div>\",\r\n      html: true\r\n    });\r\n  }\r\n}","import angular from \"angular\";\r\nimport { Popover } from \"bootstrap\";\r\n\r\n/**\r\n * Fires the necessary Bootstrap 5 initialization for the given element.\r\n * @example\r\n * ```html\r\n * <a href=\"#\" sxy-bs5-popover data-bs-toggle=\"popover\" data-bs-title=\"Default popover\">inline links</a>\r\n * ```\r\n */\r\nexport class Bs5Popover implements angular.IDirective {\r\n\r\n    /**\r\n     * Factory for directive registration.\r\n     * @ignore\r\n     */\r\n    public static salaxyBs5Popover() {\r\n      const factory = () => new Bs5Popover();\r\n      factory.$inject = [];\r\n      return factory;\r\n    }\r\n\r\n    /**\r\n     * Applies to attributes only.\r\n     * @ignore\r\n     */\r\n    public restrict = \"A\";\r\n\r\n   /**\r\n    * Creates a new instance of the directive.\r\n    */\r\n    constructor() {}\r\n\r\n   /**\r\n    * Attaches the appropriate Bootstrap scripts to the element.\r\n    * @ignore\r\n    */\r\n    public link(scope: any, element: JQLite, attrs: any) {\r\n      const title = scope.$eval(attrs.bsTitle);\r\n      const content = \"<div>\" + scope.$eval(attrs.bsContent) + \"</div>\";\r\n      const placement = scope.$eval(attrs.bsPlacement) || \"right\";\r\n      new Popover(element[0], {\r\n        title: title,\r\n        content: content,\r\n        placement: placement,\r\n        trigger: \"focus\"\r\n      });\r\n    }\r\n}\r\n","/**\r\n * Parser and formatter functions for different enum inputs.\r\n * This is required for AngularJS versions less than 1.6\r\n */\r\nexport class EnumParserFunctions {\r\n\r\n  /**\r\n   * Boolean conversion.\r\n   * @example\r\n   * ```html\r\n   * <select ng-model=\"model.value\" sxy-enum-as-boolean>\r\n   *  <option value=\"null\">Null</option>\r\n   *  <option value=\"true\">True</option>\r\n   *  <option value=\"false\">False</option>\r\n   * </select>\r\n   * ```\r\n   */\r\n  public static sxyEnumAsBoolean() {\r\n    // eslint-disable-next-line @typescript-eslint/unbound-method\r\n    return () => EnumParserFunctions.directive(\"sxyEnumAsBoolean\", EnumParserFunctions.booleanParser);\r\n  }\r\n\r\n  private static directive(name: string, parser: (input: any) => any, formatter: (input: any) => string = null): any {\r\n    return {\r\n      restrict: \"A\",\r\n      require: \"ngModel\",\r\n      link: EnumParserFunctions.getLink(name, parser, formatter),\r\n    };\r\n  }\r\n\r\n  private static getLink(name: string, parser: (input: any) => any, formatter: (input: any) => string): any {\r\n    return (scope: any, element: any, attrs: any, ngModel: any) => {\r\n      ngModel.$parsers.push(parser);\r\n      // eslint-disable-next-line @typescript-eslint/unbound-method\r\n      ngModel.$formatters.push(formatter || EnumParserFunctions.defaultFormatter);\r\n    };\r\n  }\r\n\r\n  private static booleanParser(val: any): any {\r\n    switch (val) {\r\n      case \"null\":\r\n        return null;\r\n      case \"false\":\r\n        return false;\r\n      case \"true\":\r\n        return true;\r\n    }\r\n    return val;\r\n  }\r\n\r\n  private static defaultFormatter(val: any): string {\r\n    return \"\" + val;\r\n  }\r\n\r\n}\r\n","import angular from \"angular\";\r\nimport { SessionService } from \"../services\";\r\n\r\n/**\r\n * Shows the element if the user is in the given role / in one of the given roles.\r\n * The attribute value should resolve to either role string or array of role strings.\r\n * @example\r\n * ```html\r\n * <div *sxy-if-role=\"anon\">You are not logged in.</div>\r\n * <div *sxy-if-role=\"household,worker\">This text is shown to Household or Worker roles.</div>\r\n * ```\r\n */\r\nexport class IfRoleDirective implements angular.IDirective {\r\n\r\n    /**\r\n     * Factory method for the directive creation.\r\n     * @ignore\r\n     */\r\n    public static sxyIfRole() {\r\n        const factory = (sessionService: SessionService, ngIfDirective: any) => new IfRoleDirective(sessionService, ngIfDirective);\r\n        factory.$inject = [\"SessionService\", \"ngIfDirective\"];\r\n        return factory;\r\n    }\r\n\r\n    /**\r\n     * Directive restrictions.\r\n     * @ignore\r\n     */\r\n    public restrict;\r\n\r\n    /**\r\n     * Transclusion.\r\n     * @ignore\r\n     */\r\n    public transclude;\r\n\r\n    /**\r\n     * Priority parameter.\r\n     * @ignore\r\n     */\r\n    public priority;\r\n\r\n    /**\r\n     * Terminal parameter.\r\n     * @ignore\r\n     */\r\n    public terminal;\r\n\r\n    /** Uses the original ngIf class as bases for the functionality. */\r\n    private ngIf: any;\r\n\r\n   /**\r\n    * Creates a new instance of the directive.\r\n    */\r\n    constructor(private sessionService: SessionService, ngIfDirective: any) {\r\n        this.ngIf = ngIfDirective[0];\r\n        this.restrict = this.ngIf.restrict;\r\n        this.transclude = this.ngIf.transclude;\r\n        this.priority = this.ngIf.priority;\r\n        this.terminal = this.ngIf.terminal;\r\n     }\r\n\r\n   /**\r\n    * Link function for the directive.\r\n    * @ignore\r\n    */\r\n    public link(scope: any, element: any, attrs: any) {\r\n        const value = attrs.sxyIfRole || attrs.salaxyIfRole;\r\n        attrs.ngIf = () => {\r\n            return this.sessionService.isInSomeRole(value);\r\n        };\r\n        // eslint-disable-next-line prefer-spread, prefer-rest-params\r\n        this.ngIf.link.apply(this.ngIf, arguments);\r\n    }\r\n}\r\n","import angular from \"angular\";\r\nimport { NaviService } from \"../services\";\r\n\r\n/**\r\n * Shows the element based on Sitemap parameters:\r\n * Currently supported are Visibility and isFullWidth as interpreted by SitemapHelper.getVisibility() method,\r\n * e.g. \"hidden\" includes HiddenReadOnly, Disabled and current node not resolved situations besides Hidden.\r\n * See description of SitemapHelper.getVisibility() for exact details.\r\n * @example\r\n * ```html\r\n * <div *sxy-if-sitemap=\"hidden\">Shown if the current page is hidden (including HiddenReadOnly, Disabled and current node not resolved)</div>\r\n * <div *sxy-if-sitemap=\"visible\">Shown if the current page is visible (visibility null or Visible).</div>\r\n * ```\r\n */\r\nexport class IfSitemapDirective implements angular.IDirective {\r\n\r\n  /**\r\n   * Factory method for the directive creation.\r\n   * @ignore\r\n   */\r\n  public static sxyIfSitemap() {\r\n    const factory = (naviService: NaviService, ngIfDirective: any) => new IfSitemapDirective(naviService, ngIfDirective);\r\n    factory.$inject = [\"NaviService\", \"ngIfDirective\"];\r\n    return factory;\r\n  }\r\n\r\n  /**\r\n   * Directive restrictions.\r\n   * @ignore\r\n   */\r\n  public restrict;\r\n\r\n  /**\r\n   * Transclusion.\r\n   * @ignore\r\n   */\r\n  public transclude;\r\n\r\n  /**\r\n   * Priority parameter.\r\n   * @ignore\r\n   */\r\n  public priority;\r\n\r\n  /**\r\n   * Terminal parameter.\r\n   * @ignore\r\n   */\r\n  public terminal;\r\n\r\n  /** Uses the original ngIf class as bases for the functionality. */\r\n  private ngIf: any;\r\n\r\n  /**\r\n   * Creates a new instance of the directive.\r\n   */\r\n  constructor(private naviService: NaviService, ngIfDirective: any) {\r\n    this.ngIf = ngIfDirective[0];\r\n    this.restrict = this.ngIf.restrict;\r\n    this.transclude = this.ngIf.transclude;\r\n    this.priority = this.ngIf.priority;\r\n    this.terminal = this.ngIf.terminal;\r\n  }\r\n\r\n  /**\r\n   * Link function for the directive.\r\n   * @ignore\r\n   */\r\n  public link(scope: any, element: any, attrs: any) {\r\n    const value = attrs.sxyIfSitemap;\r\n    const prop = attrs.prop;\r\n    attrs.ngIf = () => {\r\n      if (prop && prop != \"visibility\") {\r\n        const compareTo = this.naviService.current.node?.[prop]?.toString();\r\n        if (compareTo?.trim() && value?.trim()) {\r\n          return compareTo.trim().toLowerCase() == value.trim().toLowerCase();\r\n        }\r\n        return false;\r\n      } else {\r\n        return this.naviService.current.getVisibility(value);\r\n      }\r\n    };\r\n    // eslint-disable-next-line prefer-spread, prefer-rest-params\r\n    this.ngIf.link.apply(this.ngIf, arguments);\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\n/**\r\n * Loading indicator directive.\r\n * Toggles class \"salaxy-loading\" on an element. Toggling is based on  \"salaxy-loader-show\" and \"salaxy-loader-hide\" events from the\r\n * LoaderInterceptor which intercepts http calls.\r\n * @example\r\n * ```html\r\n * <div salaxy-loader class=\"spinner\">\r\n *   <div class=\"bounce1\"></div>\r\n *   <div class=\"bounce2\"></div>\r\n *   <div class=\"bounce3\"></div>\r\n * </div>\r\n * ```\r\n */\r\nexport class LoaderDirective implements angular.IDirective {\r\n\r\n  /**\r\n   * Factory for the directive creation.\r\n   * @ignore\r\n   */\r\n  public static salaxyLoader() {\r\n    const factory = () => new LoaderDirective();\r\n    factory.$inject = [];\r\n    return factory;\r\n  }\r\n\r\n  /**\r\n   * Directive restrictions.\r\n   * @ignore\r\n   */\r\n  public restrict = \"A\";\r\n\r\n  /**\r\n   * Creates a new instance of the directive.\r\n   */\r\n  constructor() {\r\n    // empty\r\n  }\r\n\r\n  /**\r\n   * Link function for the directive.\r\n   * @ignore\r\n   */\r\n  public link(scope: any, element: any, attrs: any) { // eslint-disable-line @typescript-eslint/no-unused-vars\r\n    scope.$on(\"salaxy-loader-show\", () => {\r\n      if (!element.hasClass(\"salaxy-loading\")) {\r\n        element.addClass(\"salaxy-loading\");\r\n      }\r\n    });\r\n    scope.$on(\"salaxy-loader-hide\", () => {\r\n      if (element.hasClass(\"salaxy-loading\")) {\r\n        element.removeClass(\"salaxy-loading\");\r\n      }\r\n    });\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\n/**\r\n * Adds the OData $orderby functionality to table column header.\r\n * Primary design is for thead > tr > th element or for span / div within that tag.\r\n * Requires salaxy-odata-table component as parent.\r\n * @example\r\n * ```html\r\n * <thead>\r\n *   <th>\r\n *     <span sxy-orderby=\"title\">Title</span>\r\n *     <br /> other text\r\n *   </th>\r\n *   <th sxy-orderby=\"section\" class=\"right\"><small>Section</small></th>\r\n * ```\r\n */\r\nexport class OrderbyDirective implements angular.IDirective {\r\n\r\n    /**\r\n     * Factory for directive registration.\r\n     * @ignore\r\n     */\r\n    public static sxyOrderby() {\r\n      const factory = () => new OrderbyDirective();\r\n      factory.$inject = [];\r\n      return factory;\r\n    }\r\n\r\n    /**\r\n     * Applies to attributes only.\r\n     * @ignore\r\n     */\r\n    public restrict = \"A\";\r\n\r\n    /** The view replaces the original element */\r\n    public replace = true;\r\n\r\n    /** Contents of the tag is transcluded: HTML can be used as input. */\r\n    public transclude = true;\r\n\r\n    /** Set isolate scope */\r\n    public scope = true;\r\n\r\n    /** Attribute must be used within salaxy-odata-table component to access the common ODataQueryController  */\r\n    public require = {\r\n      $odata: \"^^salaxyOdataTable\",\r\n    };\r\n\r\n   /**\r\n    * Creates a new instance of the directive.\r\n    */\r\n    constructor() {\r\n        // initialization\r\n     }\r\n\r\n     /**\r\n      * Template is based on the original tag.\r\n      */\r\n    public template(element, attrs: any ) { // eslint-disable-line @typescript-eslint/no-unused-vars\r\n      const tag = element[0].nodeName;\r\n      return `<${tag} ng-click=\"$odata.orderBy(orderby)\" class=\"clickable\">\r\n            <ng-transclude></ng-transclude><i ng-if=\"$odata.getColumnOrder(orderby)\" class=\"bi salaxy-odata-table-sort bi-sort-{{ $odata.getColumnOrder(orderby) == 'asc' ? 'up' : 'down' }}\" aria-hidden=\"true\"></i></${tag}>`;\r\n    }\r\n\r\n     /**\r\n      * Links the directive: Access to scope, element and attrs.\r\n      * @ignore\r\n      */\r\n    public link = (scope: any, element: any, attrs: any, controllers: any) => {\r\n        scope.$odata = controllers.$odata;\r\n        scope.orderby = attrs.sxyOrderby;\r\n    };\r\n}\r\n","import { Arrays, Validation, Numeric } from \"@salaxy/core\";\r\n\r\n/* eslint-disable @typescript-eslint/unbound-method */\r\n\r\n/**\r\n * Validator directives for different form inputs.\r\n * See mthods for examples of use.\r\n */\r\nexport class ValidatorFunctions {\r\n\r\n    /**\r\n     * Tax percent validator.\r\n     * @example\r\n     * ```html\r\n     * <input name=\"taxPercent\" type=\"text\" ng-model=\"taxPercent\" sxy-tax-percent>\r\n     * ```\r\n     */\r\n    public static sxyTaxPercent() {\r\n        return () => ValidatorFunctions.directive(\"sxyTaxPercent\", Validation.isTaxPercent);\r\n    }\r\n\r\n    /**\r\n     * Currency value validator.\r\n     * @example\r\n     * ```html\r\n     * <input name=\"currency\" type=\"text\" ng-model=\"currency\" sxy-currency>\r\n     * ```\r\n     */\r\n    public static sxyCurrency() {\r\n        return () => ValidatorFunctions.directive(\"sxyCurrency\", Validation.isCurrency);\r\n    }\r\n\r\n    /**\r\n     * Iban validator.\r\n     * @example\r\n     * ```html\r\n     * <input name=\"iban\" type=\"text\" ng-model=\"iban\" sxy-iban>\r\n     * ```\r\n     */\r\n    public static sxyIban() {\r\n        return () => ValidatorFunctions.directive(\"sxyIban\", Validation.isIban);\r\n    }\r\n\r\n    /**\r\n     * Email validator.\r\n     * @example\r\n     * ```html\r\n     * <input name=\"email\" type=\"text\" ng-model=\"email\" sxy-email>\r\n     * ```\r\n     */\r\n    public static sxyEmail() {\r\n        return () => ValidatorFunctions.directive(\"sxyEmail\", Validation.isEmail);\r\n    }\r\n\r\n    /**\r\n     * Mobile phone validator.\r\n     * @example\r\n     * ```html\r\n     * <input name=\"mobilePhone\" type=\"text\" ng-model=\"mobilePhone\" sxy-mobile-phone>\r\n     * ```\r\n     */\r\n    public static sxyMobilePhone() {\r\n        return () => ValidatorFunctions.directive(\"sxyMobilePhone\", Validation.isMobilePhone);\r\n    }\r\n\r\n    /**\r\n     * Finnish personal id validator.\r\n     * @example\r\n     * ```html\r\n     * <input name=\"personalIdFi\" type=\"text\" ng-model=\"personalIdFi\" sxy-personal-id-fi>\r\n     * ```\r\n     */\r\n    public static sxyPersonalIdFi() {\r\n        return () => ValidatorFunctions.directive(\"sxyPersonalIdFi\", Validation.isPersonalIdFi);\r\n    }\r\n\r\n    /**\r\n     * Finnish company id validator.\r\n     * @example\r\n     * ```html\r\n     * <input name=\"companyIdFi\" type=\"text\" ng-model=\"companyIdFi\" sxy-company-id-fi>\r\n     * ```\r\n     */\r\n    public static sxyCompanyIdFi() {\r\n        return () => ValidatorFunctions.directive(\"sxyCompanyIdFi\", Validation.formatCompanyIdFi);\r\n    }\r\n\r\n    /**\r\n     * Finnish official id validator. Official ID may be either company id orr personal id.\r\n     * @example\r\n     * ```html\r\n     * <input name=\"officialIdFi\" type=\"text\" ng-model=\"officialIdFi\" sxy-official-id-fi>\r\n     * ```\r\n     */\r\n     public static sxyOfficialIdFi() {\r\n      return () => ValidatorFunctions.directive(\"sxyOfficialIdFi\", (input) => {\r\n        return Validation.formatCompanyIdFi(input, true) || Validation.isPersonalIdFi(input);\r\n      });\r\n    }\r\n\r\n    /**\r\n     * Finnish postal code validator.\r\n     * @example\r\n     * ```html\r\n     * <input name=\"postalCodeFi\" type=\"text\" ng-model=\"postalCodeFi\" sxy-postal-code-fi>\r\n     * ```\r\n     */\r\n    public static sxyPostalCodeFi() {\r\n        return () => ValidatorFunctions.directive(\"sxyPostalCodeFi\", Validation.isPostalCodeFi);\r\n    }\r\n\r\n    /**\r\n     * Number validator.\r\n     * @example\r\n     * ```html\r\n     * <input name=\"number\" type=\"text\" ng-model=\"number\" sxy-number>\r\n     * ```\r\n     */\r\n    public static sxyNumber() {\r\n        return () => ValidatorFunctions.directive(\"sxyNumber\", Validation.isNumber);\r\n    }\r\n\r\n    /**\r\n     * Pension contract number validator.\r\n     * @example\r\n     * ```html\r\n     * <input name=\"pensionContractNumber\" type=\"text\" ng-model=\"pensionContractNumber\" sxy-pension-contract-number=\"'varma'\">\r\n     * ```\r\n     */\r\n     public static sxyPensionContractNumber() {\r\n        /** return () => ValidatorFunctions.parserAndFormatterDirective([\"sxyPensionContractNumber\"], [(val) => !!Validation.isPensionContractNumber(val)]);*/\r\n\r\n        return () => ValidatorFunctions.directive(\"sxyPensionContractNumber\", (value: string, attrValue: any) => {\r\n          let result = false;\r\n          if(!attrValue) {\r\n            result = !!Validation.isPensionContractNumber(value);\r\n          } else {\r\n            result = attrValue == Validation.isPensionContractNumber(value);\r\n          }\r\n          setTimeout(() => {\r\n            //\r\n          });\r\n          return result;\r\n        } );\r\n     }\r\n\r\n    /**\r\n     * Integer validator.\r\n     * @example\r\n     * ```html\r\n     * <input name=\"intger\" type=\"text\" ng-model=\"integer\" sxy-integer>\r\n     * ```\r\n     */\r\n    public static sxyInteger() {\r\n        return () => ValidatorFunctions.directive(\"sxyInteger\", Validation.isInteger);\r\n    }\r\n\r\n    /**\r\n     * Maximum value validator\r\n     * <input name=\"number\" type=\"text\" ng-model=\"number\" sxy-min=\"$ctrl.maximum\">\r\n     */\r\n    public static sxyMin() {\r\n      return () => ValidatorFunctions.directive(\"sxyMin\", (value: string, attrValue: any) => {\r\n        if(!Validation.isNumber(value) || !Validation.isNumber(attrValue)){\r\n          return true;\r\n        }\r\n        return Numeric.parseNumber(value) >= Numeric.parseNumber(attrValue);\r\n      } );\r\n    }\r\n\r\n    /**\r\n     * Maximum value validator\r\n     * <input name=\"number\" type=\"text\" ng-model=\"number\" sxy-max=\"$ctrl.maximum\">\r\n     */\r\n    public static sxyMax() {\r\n      return () => ValidatorFunctions.directive(\"sxyMax\", (value: string, attrValue: any) => {\r\n        if(!Validation.isNumber(value) || !Validation.isNumber(attrValue) ){\r\n          return true;\r\n        }\r\n        return Numeric.parseNumber(value) <= Numeric.parseNumber(attrValue);\r\n      } );\r\n    }\r\n\r\n    /**\r\n     * Multiple of value validator\r\n     * <input name=\"number\" type=\"text\" ng-model=\"number\" sxy-multiple-of=\"$ctrl.multipleOf\">\r\n     */\r\n    public static sxyMultipleOf() {\r\n      return () => ValidatorFunctions.directive(\"sxyMultipleOf\", (value: string, attrValue: any) => {\r\n        if(!Validation.isNumber(value) || !Validation.isNumber(attrValue)){\r\n          return true;\r\n        }\r\n        if(Numeric.parseNumber(attrValue) <= 0){\r\n          return false;\r\n        }\r\n        return Numeric.parseNumber(value) % Numeric.parseNumber(attrValue) === 0;\r\n      } );\r\n    }\r\n\r\n    /**\r\n     * Finnish bank reference number validator.\r\n     * @example\r\n     * ```html\r\n     * <input name=\"bankRefNumber\" type=\"text\" ng-model=\"bankRefNumber\" sxy-bank-reference-fi>\r\n     * ```\r\n     */\r\n     public static sxyBankReferenceFi() {\r\n      return () => ValidatorFunctions.directive(\"sxyBankReferenceFi\", Validation.isFinnishBankReferenceNumber);\r\n    }\r\n    /**\r\n     * Validator for values which should not be considered as valid in the UI (i.e. unknown, none)\r\n     */\r\n    public static sxyExcludeUnknowns() {\r\n      return () => ValidatorFunctions.directive(\"sxyExcludeUnknowns\", (value: string, attrValue: any) => {\r\n        const invalidValues = Arrays.assureArray(attrValue);\r\n        return !(invalidValues.indexOf(value) >= 0);\r\n      } );\r\n    }\r\n    private static directive(name: string, validationFunction: (input: string, attrValue: any) => boolean): any {\r\n        return {\r\n            restrict: \"A\",\r\n            require: \"ngModel\",\r\n            link: ValidatorFunctions.setValidator(name, validationFunction),\r\n        };\r\n    }\r\n\r\n    private static parserAndFormatterDirective(names: string[], validationFunctions: ((input: string) => boolean)[]): any {\r\n        return {\r\n            restrict: \"A\",\r\n            require: \"ngModel\",\r\n            link: ValidatorFunctions.setParserAndFormatter(names, validationFunctions),\r\n        };\r\n    }\r\n    private static setValidator(name: string, validationFunction: (input: string, attrValue: any) => boolean): any {\r\n        return (scope: any, element: any, attrs: any, ctrl: any) => {\r\n            ctrl.$validators[name] = (modelValue, viewValue) => {\r\n                if (ctrl.$isEmpty(modelValue)) {\r\n                    // consider empty models to be valid\r\n                    return true;\r\n                }\r\n                return validationFunction(viewValue,  scope.$eval(attrs[name]));\r\n            };\r\n        };\r\n    }\r\n\r\n    private static setParserAndFormatter(names: string[], validationFunctions: ((input: string) => boolean)[]): any {\r\n        return (scope: any, element: any, attrs: any, ctrl: any) => {\r\n\r\n                ctrl.$parsers.unshift( (value) => {\r\n                    let allValid = true;\r\n                    for ( let i = 0; i < names.length; i++) {\r\n                    // test and set the validity after update.\r\n                        const valid = validationFunctions[i](value);\r\n                        ctrl.$setValidity(names[i], valid);\r\n                        if (!valid) {\r\n                            allValid = false;\r\n                        }\r\n                    }\r\n\r\n                    // if it's valid, return the value to the model,\r\n                    // otherwise return undefined.\r\n                    return allValid ? value : undefined;\r\n                });\r\n            };\r\n        }\r\n    }\r\n","import angular from \"angular\";\r\n\r\nimport { Dates } from \"@salaxy/core\";\r\n\r\n/**\r\n * Validates the datepicker manual input using the same rules\r\n * as the actual calendar selection control.\r\n * Currently this directive is used internally in salaxy-datepicker-popup only.\r\n *\r\n */\r\nexport class DatepickerInputValidationDirective implements angular.IDirective {\r\n\r\n  /**\r\n   * Factory for directive registration.\r\n   * @ignore\r\n   */\r\n  public static salaxyDatepickerInputValidation() {\r\n    const factory = () => new DatepickerInputValidationDirective();\r\n    factory.$inject = [];\r\n    return factory;\r\n  }\r\n\r\n  /**\r\n   * Applies to attributes only.\r\n   * @ignore\r\n   */\r\n  public restrict = \"A\";\r\n\r\n  /**\r\n   * Requires model.\r\n   * @ignore\r\n   */\r\n  public require = \"ngModel\";\r\n\r\n  /**\r\n   * Creates a new instance of the directive.\r\n   */\r\n  constructor() {\r\n    // initialization\r\n  }\r\n\r\n  /**\r\n   * Validates the datepicker manual input using the same rules\r\n   * as the actual calendar selection control.\r\n   * @ignore\r\n   */\r\n  public link(scope: any, element: any, attrs: any, ngModel: any) {\r\n\r\n    // Validates date if it has a value:\r\n    // - within minDate and maxDate of datepicker options\r\n    // - not disabled according to datepicker options' dateDisabled function\r\n    // eslint-disable-next-line @typescript-eslint/no-unused-vars\r\n    ngModel.$validators.invalidDate = (modelValue, viewValue) => {\r\n      if (!modelValue) {\r\n        return true;\r\n      }\r\n\r\n      const datepickerOptions = scope.$eval(attrs.datepickerOptions);\r\n      if (!datepickerOptions) {\r\n        return true;\r\n      }\r\n\r\n      if (datepickerOptions.minDate || datepickerOptions.maxDate) {\r\n        const modelValueDay = Dates.asDate(modelValue);\r\n\r\n        if (datepickerOptions.minDate) {\r\n          const minDateDay = Dates.asDate(datepickerOptions.minDate);\r\n          if (modelValueDay < minDateDay) {\r\n            return false;\r\n          }\r\n        }\r\n\r\n        if (datepickerOptions.maxDate) {\r\n          const maxDateDay = Dates.asDate(datepickerOptions.maxDate);\r\n          if (modelValueDay > maxDateDay) {\r\n            return false;\r\n          }\r\n        }\r\n      }\r\n\r\n      if (datepickerOptions.dateDisabled && datepickerOptions.dateDisabled({ date: Dates.asJSDate(modelValue) })) {\r\n        return false;\r\n      }\r\n\r\n      return true;\r\n    };\r\n  }\r\n}\r\n","/**\n * marked v12.0.2 - a markdown parser\n * Copyright (c) 2011-2024, Christopher Jeffrey. (MIT Licensed)\n * https://github.com/markedjs/marked\n */\n\n/**\n * DO NOT EDIT THIS FILE\n * The code in this file is generated from files in ./src/\n */\n\n/**\n * Gets the original marked default options.\n */\nfunction _getDefaults() {\n    return {\n        async: false,\n        breaks: false,\n        extensions: null,\n        gfm: true,\n        hooks: null,\n        pedantic: false,\n        renderer: null,\n        silent: false,\n        tokenizer: null,\n        walkTokens: null\n    };\n}\nlet _defaults = _getDefaults();\nfunction changeDefaults(newDefaults) {\n    _defaults = newDefaults;\n}\n\n/**\n * Helpers\n */\nconst escapeTest = /[&<>\"']/;\nconst escapeReplace = new RegExp(escapeTest.source, 'g');\nconst escapeTestNoEncode = /[<>\"']|&(?!(#\\d{1,7}|#[Xx][a-fA-F0-9]{1,6}|\\w+);)/;\nconst escapeReplaceNoEncode = new RegExp(escapeTestNoEncode.source, 'g');\nconst escapeReplacements = {\n    '&': '&amp;',\n    '<': '&lt;',\n    '>': '&gt;',\n    '\"': '&quot;',\n    \"'\": '&#39;'\n};\nconst getEscapeReplacement = (ch) => escapeReplacements[ch];\nfunction escape$1(html, encode) {\n    if (encode) {\n        if (escapeTest.test(html)) {\n            return html.replace(escapeReplace, getEscapeReplacement);\n        }\n    }\n    else {\n        if (escapeTestNoEncode.test(html)) {\n            return html.replace(escapeReplaceNoEncode, getEscapeReplacement);\n        }\n    }\n    return html;\n}\nconst unescapeTest = /&(#(?:\\d+)|(?:#x[0-9A-Fa-f]+)|(?:\\w+));?/ig;\nfunction unescape(html) {\n    // explicitly match decimal, hex, and named HTML entities\n    return html.replace(unescapeTest, (_, n) => {\n        n = n.toLowerCase();\n        if (n === 'colon')\n            return ':';\n        if (n.charAt(0) === '#') {\n            return n.charAt(1) === 'x'\n                ? String.fromCharCode(parseInt(n.substring(2), 16))\n                : String.fromCharCode(+n.substring(1));\n        }\n        return '';\n    });\n}\nconst caret = /(^|[^\\[])\\^/g;\nfunction edit(regex, opt) {\n    let source = typeof regex === 'string' ? regex : regex.source;\n    opt = opt || '';\n    const obj = {\n        replace: (name, val) => {\n            let valSource = typeof val === 'string' ? val : val.source;\n            valSource = valSource.replace(caret, '$1');\n            source = source.replace(name, valSource);\n            return obj;\n        },\n        getRegex: () => {\n            return new RegExp(source, opt);\n        }\n    };\n    return obj;\n}\nfunction cleanUrl(href) {\n    try {\n        href = encodeURI(href).replace(/%25/g, '%');\n    }\n    catch (e) {\n        return null;\n    }\n    return href;\n}\nconst noopTest = { exec: () => null };\nfunction splitCells(tableRow, count) {\n    // ensure that every cell-delimiting pipe has a space\n    // before it to distinguish it from an escaped pipe\n    const row = tableRow.replace(/\\|/g, (match, offset, str) => {\n        let escaped = false;\n        let curr = offset;\n        while (--curr >= 0 && str[curr] === '\\\\')\n            escaped = !escaped;\n        if (escaped) {\n            // odd number of slashes means | is escaped\n            // so we leave it alone\n            return '|';\n        }\n        else {\n            // add space before unescaped |\n            return ' |';\n        }\n    }), cells = row.split(/ \\|/);\n    let i = 0;\n    // First/last cell in a row cannot be empty if it has no leading/trailing pipe\n    if (!cells[0].trim()) {\n        cells.shift();\n    }\n    if (cells.length > 0 && !cells[cells.length - 1].trim()) {\n        cells.pop();\n    }\n    if (count) {\n        if (cells.length > count) {\n            cells.splice(count);\n        }\n        else {\n            while (cells.length < count)\n                cells.push('');\n        }\n    }\n    for (; i < cells.length; i++) {\n        // leading or trailing whitespace is ignored per the gfm spec\n        cells[i] = cells[i].trim().replace(/\\\\\\|/g, '|');\n    }\n    return cells;\n}\n/**\n * Remove trailing 'c's. Equivalent to str.replace(/c*$/, '').\n * /c*$/ is vulnerable to REDOS.\n *\n * @param str\n * @param c\n * @param invert Remove suffix of non-c chars instead. Default falsey.\n */\nfunction rtrim(str, c, invert) {\n    const l = str.length;\n    if (l === 0) {\n        return '';\n    }\n    // Length of suffix matching the invert condition.\n    let suffLen = 0;\n    // Step left until we fail to match the invert condition.\n    while (suffLen < l) {\n        const currChar = str.charAt(l - suffLen - 1);\n        if (currChar === c && !invert) {\n            suffLen++;\n        }\n        else if (currChar !== c && invert) {\n            suffLen++;\n        }\n        else {\n            break;\n        }\n    }\n    return str.slice(0, l - suffLen);\n}\nfunction findClosingBracket(str, b) {\n    if (str.indexOf(b[1]) === -1) {\n        return -1;\n    }\n    let level = 0;\n    for (let i = 0; i < str.length; i++) {\n        if (str[i] === '\\\\') {\n            i++;\n        }\n        else if (str[i] === b[0]) {\n            level++;\n        }\n        else if (str[i] === b[1]) {\n            level--;\n            if (level < 0) {\n                return i;\n            }\n        }\n    }\n    return -1;\n}\n\nfunction outputLink(cap, link, raw, lexer) {\n    const href = link.href;\n    const title = link.title ? escape$1(link.title) : null;\n    const text = cap[1].replace(/\\\\([\\[\\]])/g, '$1');\n    if (cap[0].charAt(0) !== '!') {\n        lexer.state.inLink = true;\n        const token = {\n            type: 'link',\n            raw,\n            href,\n            title,\n            text,\n            tokens: lexer.inlineTokens(text)\n        };\n        lexer.state.inLink = false;\n        return token;\n    }\n    return {\n        type: 'image',\n        raw,\n        href,\n        title,\n        text: escape$1(text)\n    };\n}\nfunction indentCodeCompensation(raw, text) {\n    const matchIndentToCode = raw.match(/^(\\s+)(?:```)/);\n    if (matchIndentToCode === null) {\n        return text;\n    }\n    const indentToCode = matchIndentToCode[1];\n    return text\n        .split('\\n')\n        .map(node => {\n        const matchIndentInNode = node.match(/^\\s+/);\n        if (matchIndentInNode === null) {\n            return node;\n        }\n        const [indentInNode] = matchIndentInNode;\n        if (indentInNode.length >= indentToCode.length) {\n            return node.slice(indentToCode.length);\n        }\n        return node;\n    })\n        .join('\\n');\n}\n/**\n * Tokenizer\n */\nclass _Tokenizer {\n    options;\n    rules; // set by the lexer\n    lexer; // set by the lexer\n    constructor(options) {\n        this.options = options || _defaults;\n    }\n    space(src) {\n        const cap = this.rules.block.newline.exec(src);\n        if (cap && cap[0].length > 0) {\n            return {\n                type: 'space',\n                raw: cap[0]\n            };\n        }\n    }\n    code(src) {\n        const cap = this.rules.block.code.exec(src);\n        if (cap) {\n            const text = cap[0].replace(/^ {1,4}/gm, '');\n            return {\n                type: 'code',\n                raw: cap[0],\n                codeBlockStyle: 'indented',\n                text: !this.options.pedantic\n                    ? rtrim(text, '\\n')\n                    : text\n            };\n        }\n    }\n    fences(src) {\n        const cap = this.rules.block.fences.exec(src);\n        if (cap) {\n            const raw = cap[0];\n            const text = indentCodeCompensation(raw, cap[3] || '');\n            return {\n                type: 'code',\n                raw,\n                lang: cap[2] ? cap[2].trim().replace(this.rules.inline.anyPunctuation, '$1') : cap[2],\n                text\n            };\n        }\n    }\n    heading(src) {\n        const cap = this.rules.block.heading.exec(src);\n        if (cap) {\n            let text = cap[2].trim();\n            // remove trailing #s\n            if (/#$/.test(text)) {\n                const trimmed = rtrim(text, '#');\n                if (this.options.pedantic) {\n                    text = trimmed.trim();\n                }\n                else if (!trimmed || / $/.test(trimmed)) {\n                    // CommonMark requires space before trailing #s\n                    text = trimmed.trim();\n                }\n            }\n            return {\n                type: 'heading',\n                raw: cap[0],\n                depth: cap[1].length,\n                text,\n                tokens: this.lexer.inline(text)\n            };\n        }\n    }\n    hr(src) {\n        const cap = this.rules.block.hr.exec(src);\n        if (cap) {\n            return {\n                type: 'hr',\n                raw: cap[0]\n            };\n        }\n    }\n    blockquote(src) {\n        const cap = this.rules.block.blockquote.exec(src);\n        if (cap) {\n            // precede setext continuation with 4 spaces so it isn't a setext\n            let text = cap[0].replace(/\\n {0,3}((?:=+|-+) *)(?=\\n|$)/g, '\\n    $1');\n            text = rtrim(text.replace(/^ *>[ \\t]?/gm, ''), '\\n');\n            const top = this.lexer.state.top;\n            this.lexer.state.top = true;\n            const tokens = this.lexer.blockTokens(text);\n            this.lexer.state.top = top;\n            return {\n                type: 'blockquote',\n                raw: cap[0],\n                tokens,\n                text\n            };\n        }\n    }\n    list(src) {\n        let cap = this.rules.block.list.exec(src);\n        if (cap) {\n            let bull = cap[1].trim();\n            const isordered = bull.length > 1;\n            const list = {\n                type: 'list',\n                raw: '',\n                ordered: isordered,\n                start: isordered ? +bull.slice(0, -1) : '',\n                loose: false,\n                items: []\n            };\n            bull = isordered ? `\\\\d{1,9}\\\\${bull.slice(-1)}` : `\\\\${bull}`;\n            if (this.options.pedantic) {\n                bull = isordered ? bull : '[*+-]';\n            }\n            // Get next list item\n            const itemRegex = new RegExp(`^( {0,3}${bull})((?:[\\t ][^\\\\n]*)?(?:\\\\n|$))`);\n            let raw = '';\n            let itemContents = '';\n            let endsWithBlankLine = false;\n            // Check if current bullet point can start a new List Item\n            while (src) {\n                let endEarly = false;\n                if (!(cap = itemRegex.exec(src))) {\n                    break;\n                }\n                if (this.rules.block.hr.test(src)) { // End list if bullet was actually HR (possibly move into itemRegex?)\n                    break;\n                }\n                raw = cap[0];\n                src = src.substring(raw.length);\n                let line = cap[2].split('\\n', 1)[0].replace(/^\\t+/, (t) => ' '.repeat(3 * t.length));\n                let nextLine = src.split('\\n', 1)[0];\n                let indent = 0;\n                if (this.options.pedantic) {\n                    indent = 2;\n                    itemContents = line.trimStart();\n                }\n                else {\n                    indent = cap[2].search(/[^ ]/); // Find first non-space char\n                    indent = indent > 4 ? 1 : indent; // Treat indented code blocks (> 4 spaces) as having only 1 indent\n                    itemContents = line.slice(indent);\n                    indent += cap[1].length;\n                }\n                let blankLine = false;\n                if (!line && /^ *$/.test(nextLine)) { // Items begin with at most one blank line\n                    raw += nextLine + '\\n';\n                    src = src.substring(nextLine.length + 1);\n                    endEarly = true;\n                }\n                if (!endEarly) {\n                    const nextBulletRegex = new RegExp(`^ {0,${Math.min(3, indent - 1)}}(?:[*+-]|\\\\d{1,9}[.)])((?:[ \\t][^\\\\n]*)?(?:\\\\n|$))`);\n                    const hrRegex = new RegExp(`^ {0,${Math.min(3, indent - 1)}}((?:- *){3,}|(?:_ *){3,}|(?:\\\\* *){3,})(?:\\\\n+|$)`);\n                    const fencesBeginRegex = new RegExp(`^ {0,${Math.min(3, indent - 1)}}(?:\\`\\`\\`|~~~)`);\n                    const headingBeginRegex = new RegExp(`^ {0,${Math.min(3, indent - 1)}}#`);\n                    // Check if following lines should be included in List Item\n                    while (src) {\n                        const rawLine = src.split('\\n', 1)[0];\n                        nextLine = rawLine;\n                        // Re-align to follow commonmark nesting rules\n                        if (this.options.pedantic) {\n                            nextLine = nextLine.replace(/^ {1,4}(?=( {4})*[^ ])/g, '  ');\n                        }\n                        // End list item if found code fences\n                        if (fencesBeginRegex.test(nextLine)) {\n                            break;\n                        }\n                        // End list item if found start of new heading\n                        if (headingBeginRegex.test(nextLine)) {\n                            break;\n                        }\n                        // End list item if found start of new bullet\n                        if (nextBulletRegex.test(nextLine)) {\n                            break;\n                        }\n                        // Horizontal rule found\n                        if (hrRegex.test(src)) {\n                            break;\n                        }\n                        if (nextLine.search(/[^ ]/) >= indent || !nextLine.trim()) { // Dedent if possible\n                            itemContents += '\\n' + nextLine.slice(indent);\n                        }\n                        else {\n                            // not enough indentation\n                            if (blankLine) {\n                                break;\n                            }\n                            // paragraph continuation unless last line was a different block level element\n                            if (line.search(/[^ ]/) >= 4) { // indented code block\n                                break;\n                            }\n                            if (fencesBeginRegex.test(line)) {\n                                break;\n                            }\n                            if (headingBeginRegex.test(line)) {\n                                break;\n                            }\n                            if (hrRegex.test(line)) {\n                                break;\n                            }\n                            itemContents += '\\n' + nextLine;\n                        }\n                        if (!blankLine && !nextLine.trim()) { // Check if current line is blank\n                            blankLine = true;\n                        }\n                        raw += rawLine + '\\n';\n                        src = src.substring(rawLine.length + 1);\n                        line = nextLine.slice(indent);\n                    }\n                }\n                if (!list.loose) {\n                    // If the previous item ended with a blank line, the list is loose\n                    if (endsWithBlankLine) {\n                        list.loose = true;\n                    }\n                    else if (/\\n *\\n *$/.test(raw)) {\n                        endsWithBlankLine = true;\n                    }\n                }\n                let istask = null;\n                let ischecked;\n                // Check for task list items\n                if (this.options.gfm) {\n                    istask = /^\\[[ xX]\\] /.exec(itemContents);\n                    if (istask) {\n                        ischecked = istask[0] !== '[ ] ';\n                        itemContents = itemContents.replace(/^\\[[ xX]\\] +/, '');\n                    }\n                }\n                list.items.push({\n                    type: 'list_item',\n                    raw,\n                    task: !!istask,\n                    checked: ischecked,\n                    loose: false,\n                    text: itemContents,\n                    tokens: []\n                });\n                list.raw += raw;\n            }\n            // Do not consume newlines at end of final item. Alternatively, make itemRegex *start* with any newlines to simplify/speed up endsWithBlankLine logic\n            list.items[list.items.length - 1].raw = raw.trimEnd();\n            (list.items[list.items.length - 1]).text = itemContents.trimEnd();\n            list.raw = list.raw.trimEnd();\n            // Item child tokens handled here at end because we needed to have the final item to trim it first\n            for (let i = 0; i < list.items.length; i++) {\n                this.lexer.state.top = false;\n                list.items[i].tokens = this.lexer.blockTokens(list.items[i].text, []);\n                if (!list.loose) {\n                    // Check if list should be loose\n                    const spacers = list.items[i].tokens.filter(t => t.type === 'space');\n                    const hasMultipleLineBreaks = spacers.length > 0 && spacers.some(t => /\\n.*\\n/.test(t.raw));\n                    list.loose = hasMultipleLineBreaks;\n                }\n            }\n            // Set all items to loose if list is loose\n            if (list.loose) {\n                for (let i = 0; i < list.items.length; i++) {\n                    list.items[i].loose = true;\n                }\n            }\n            return list;\n        }\n    }\n    html(src) {\n        const cap = this.rules.block.html.exec(src);\n        if (cap) {\n            const token = {\n                type: 'html',\n                block: true,\n                raw: cap[0],\n                pre: cap[1] === 'pre' || cap[1] === 'script' || cap[1] === 'style',\n                text: cap[0]\n            };\n            return token;\n        }\n    }\n    def(src) {\n        const cap = this.rules.block.def.exec(src);\n        if (cap) {\n            const tag = cap[1].toLowerCase().replace(/\\s+/g, ' ');\n            const href = cap[2] ? cap[2].replace(/^<(.*)>$/, '$1').replace(this.rules.inline.anyPunctuation, '$1') : '';\n            const title = cap[3] ? cap[3].substring(1, cap[3].length - 1).replace(this.rules.inline.anyPunctuation, '$1') : cap[3];\n            return {\n                type: 'def',\n                tag,\n                raw: cap[0],\n                href,\n                title\n            };\n        }\n    }\n    table(src) {\n        const cap = this.rules.block.table.exec(src);\n        if (!cap) {\n            return;\n        }\n        if (!/[:|]/.test(cap[2])) {\n            // delimiter row must have a pipe (|) or colon (:) otherwise it is a setext heading\n            return;\n        }\n        const headers = splitCells(cap[1]);\n        const aligns = cap[2].replace(/^\\||\\| *$/g, '').split('|');\n        const rows = cap[3] && cap[3].trim() ? cap[3].replace(/\\n[ \\t]*$/, '').split('\\n') : [];\n        const item = {\n            type: 'table',\n            raw: cap[0],\n            header: [],\n            align: [],\n            rows: []\n        };\n        if (headers.length !== aligns.length) {\n            // header and align columns must be equal, rows can be different.\n            return;\n        }\n        for (const align of aligns) {\n            if (/^ *-+: *$/.test(align)) {\n                item.align.push('right');\n            }\n            else if (/^ *:-+: *$/.test(align)) {\n                item.align.push('center');\n            }\n            else if (/^ *:-+ *$/.test(align)) {\n                item.align.push('left');\n            }\n            else {\n                item.align.push(null);\n            }\n        }\n        for (const header of headers) {\n            item.header.push({\n                text: header,\n                tokens: this.lexer.inline(header)\n            });\n        }\n        for (const row of rows) {\n            item.rows.push(splitCells(row, item.header.length).map(cell => {\n                return {\n                    text: cell,\n                    tokens: this.lexer.inline(cell)\n                };\n            }));\n        }\n        return item;\n    }\n    lheading(src) {\n        const cap = this.rules.block.lheading.exec(src);\n        if (cap) {\n            return {\n                type: 'heading',\n                raw: cap[0],\n                depth: cap[2].charAt(0) === '=' ? 1 : 2,\n                text: cap[1],\n                tokens: this.lexer.inline(cap[1])\n            };\n        }\n    }\n    paragraph(src) {\n        const cap = this.rules.block.paragraph.exec(src);\n        if (cap) {\n            const text = cap[1].charAt(cap[1].length - 1) === '\\n'\n                ? cap[1].slice(0, -1)\n                : cap[1];\n            return {\n                type: 'paragraph',\n                raw: cap[0],\n                text,\n                tokens: this.lexer.inline(text)\n            };\n        }\n    }\n    text(src) {\n        const cap = this.rules.block.text.exec(src);\n        if (cap) {\n            return {\n                type: 'text',\n                raw: cap[0],\n                text: cap[0],\n                tokens: this.lexer.inline(cap[0])\n            };\n        }\n    }\n    escape(src) {\n        const cap = this.rules.inline.escape.exec(src);\n        if (cap) {\n            return {\n                type: 'escape',\n                raw: cap[0],\n                text: escape$1(cap[1])\n            };\n        }\n    }\n    tag(src) {\n        const cap = this.rules.inline.tag.exec(src);\n        if (cap) {\n            if (!this.lexer.state.inLink && /^<a /i.test(cap[0])) {\n                this.lexer.state.inLink = true;\n            }\n            else if (this.lexer.state.inLink && /^<\\/a>/i.test(cap[0])) {\n                this.lexer.state.inLink = false;\n            }\n            if (!this.lexer.state.inRawBlock && /^<(pre|code|kbd|script)(\\s|>)/i.test(cap[0])) {\n                this.lexer.state.inRawBlock = true;\n            }\n            else if (this.lexer.state.inRawBlock && /^<\\/(pre|code|kbd|script)(\\s|>)/i.test(cap[0])) {\n                this.lexer.state.inRawBlock = false;\n            }\n            return {\n                type: 'html',\n                raw: cap[0],\n                inLink: this.lexer.state.inLink,\n                inRawBlock: this.lexer.state.inRawBlock,\n                block: false,\n                text: cap[0]\n            };\n        }\n    }\n    link(src) {\n        const cap = this.rules.inline.link.exec(src);\n        if (cap) {\n            const trimmedUrl = cap[2].trim();\n            if (!this.options.pedantic && /^</.test(trimmedUrl)) {\n                // commonmark requires matching angle brackets\n                if (!(/>$/.test(trimmedUrl))) {\n                    return;\n                }\n                // ending angle bracket cannot be escaped\n                const rtrimSlash = rtrim(trimmedUrl.slice(0, -1), '\\\\');\n                if ((trimmedUrl.length - rtrimSlash.length) % 2 === 0) {\n                    return;\n                }\n            }\n            else {\n                // find closing parenthesis\n                const lastParenIndex = findClosingBracket(cap[2], '()');\n                if (lastParenIndex > -1) {\n                    const start = cap[0].indexOf('!') === 0 ? 5 : 4;\n                    const linkLen = start + cap[1].length + lastParenIndex;\n                    cap[2] = cap[2].substring(0, lastParenIndex);\n                    cap[0] = cap[0].substring(0, linkLen).trim();\n                    cap[3] = '';\n                }\n            }\n            let href = cap[2];\n            let title = '';\n            if (this.options.pedantic) {\n                // split pedantic href and title\n                const link = /^([^'\"]*[^\\s])\\s+(['\"])(.*)\\2/.exec(href);\n                if (link) {\n                    href = link[1];\n                    title = link[3];\n                }\n            }\n            else {\n                title = cap[3] ? cap[3].slice(1, -1) : '';\n            }\n            href = href.trim();\n            if (/^</.test(href)) {\n                if (this.options.pedantic && !(/>$/.test(trimmedUrl))) {\n                    // pedantic allows starting angle bracket without ending angle bracket\n                    href = href.slice(1);\n                }\n                else {\n                    href = href.slice(1, -1);\n                }\n            }\n            return outputLink(cap, {\n                href: href ? href.replace(this.rules.inline.anyPunctuation, '$1') : href,\n                title: title ? title.replace(this.rules.inline.anyPunctuation, '$1') : title\n            }, cap[0], this.lexer);\n        }\n    }\n    reflink(src, links) {\n        let cap;\n        if ((cap = this.rules.inline.reflink.exec(src))\n            || (cap = this.rules.inline.nolink.exec(src))) {\n            const linkString = (cap[2] || cap[1]).replace(/\\s+/g, ' ');\n            const link = links[linkString.toLowerCase()];\n            if (!link) {\n                const text = cap[0].charAt(0);\n                return {\n                    type: 'text',\n                    raw: text,\n                    text\n                };\n            }\n            return outputLink(cap, link, cap[0], this.lexer);\n        }\n    }\n    emStrong(src, maskedSrc, prevChar = '') {\n        let match = this.rules.inline.emStrongLDelim.exec(src);\n        if (!match)\n            return;\n        // _ can't be between two alphanumerics. \\p{L}\\p{N} includes non-english alphabet/numbers as well\n        if (match[3] && prevChar.match(/[\\p{L}\\p{N}]/u))\n            return;\n        const nextChar = match[1] || match[2] || '';\n        if (!nextChar || !prevChar || this.rules.inline.punctuation.exec(prevChar)) {\n            // unicode Regex counts emoji as 1 char; spread into array for proper count (used multiple times below)\n            const lLength = [...match[0]].length - 1;\n            let rDelim, rLength, delimTotal = lLength, midDelimTotal = 0;\n            const endReg = match[0][0] === '*' ? this.rules.inline.emStrongRDelimAst : this.rules.inline.emStrongRDelimUnd;\n            endReg.lastIndex = 0;\n            // Clip maskedSrc to same section of string as src (move to lexer?)\n            maskedSrc = maskedSrc.slice(-1 * src.length + lLength);\n            while ((match = endReg.exec(maskedSrc)) != null) {\n                rDelim = match[1] || match[2] || match[3] || match[4] || match[5] || match[6];\n                if (!rDelim)\n                    continue; // skip single * in __abc*abc__\n                rLength = [...rDelim].length;\n                if (match[3] || match[4]) { // found another Left Delim\n                    delimTotal += rLength;\n                    continue;\n                }\n                else if (match[5] || match[6]) { // either Left or Right Delim\n                    if (lLength % 3 && !((lLength + rLength) % 3)) {\n                        midDelimTotal += rLength;\n                        continue; // CommonMark Emphasis Rules 9-10\n                    }\n                }\n                delimTotal -= rLength;\n                if (delimTotal > 0)\n                    continue; // Haven't found enough closing delimiters\n                // Remove extra characters. *a*** -> *a*\n                rLength = Math.min(rLength, rLength + delimTotal + midDelimTotal);\n                // char length can be >1 for unicode characters;\n                const lastCharLength = [...match[0]][0].length;\n                const raw = src.slice(0, lLength + match.index + lastCharLength + rLength);\n                // Create `em` if smallest delimiter has odd char count. *a***\n                if (Math.min(lLength, rLength) % 2) {\n                    const text = raw.slice(1, -1);\n                    return {\n                        type: 'em',\n                        raw,\n                        text,\n                        tokens: this.lexer.inlineTokens(text)\n                    };\n                }\n                // Create 'strong' if smallest delimiter has even char count. **a***\n                const text = raw.slice(2, -2);\n                return {\n                    type: 'strong',\n                    raw,\n                    text,\n                    tokens: this.lexer.inlineTokens(text)\n                };\n            }\n        }\n    }\n    codespan(src) {\n        const cap = this.rules.inline.code.exec(src);\n        if (cap) {\n            let text = cap[2].replace(/\\n/g, ' ');\n            const hasNonSpaceChars = /[^ ]/.test(text);\n            const hasSpaceCharsOnBothEnds = /^ /.test(text) && / $/.test(text);\n            if (hasNonSpaceChars && hasSpaceCharsOnBothEnds) {\n                text = text.substring(1, text.length - 1);\n            }\n            text = escape$1(text, true);\n            return {\n                type: 'codespan',\n                raw: cap[0],\n                text\n            };\n        }\n    }\n    br(src) {\n        const cap = this.rules.inline.br.exec(src);\n        if (cap) {\n            return {\n                type: 'br',\n                raw: cap[0]\n            };\n        }\n    }\n    del(src) {\n        const cap = this.rules.inline.del.exec(src);\n        if (cap) {\n            return {\n                type: 'del',\n                raw: cap[0],\n                text: cap[2],\n                tokens: this.lexer.inlineTokens(cap[2])\n            };\n        }\n    }\n    autolink(src) {\n        const cap = this.rules.inline.autolink.exec(src);\n        if (cap) {\n            let text, href;\n            if (cap[2] === '@') {\n                text = escape$1(cap[1]);\n                href = 'mailto:' + text;\n            }\n            else {\n                text = escape$1(cap[1]);\n                href = text;\n            }\n            return {\n                type: 'link',\n                raw: cap[0],\n                text,\n                href,\n                tokens: [\n                    {\n                        type: 'text',\n                        raw: text,\n                        text\n                    }\n                ]\n            };\n        }\n    }\n    url(src) {\n        let cap;\n        if (cap = this.rules.inline.url.exec(src)) {\n            let text, href;\n            if (cap[2] === '@') {\n                text = escape$1(cap[0]);\n                href = 'mailto:' + text;\n            }\n            else {\n                // do extended autolink path validation\n                let prevCapZero;\n                do {\n                    prevCapZero = cap[0];\n                    cap[0] = this.rules.inline._backpedal.exec(cap[0])?.[0] ?? '';\n                } while (prevCapZero !== cap[0]);\n                text = escape$1(cap[0]);\n                if (cap[1] === 'www.') {\n                    href = 'http://' + cap[0];\n                }\n                else {\n                    href = cap[0];\n                }\n            }\n            return {\n                type: 'link',\n                raw: cap[0],\n                text,\n                href,\n                tokens: [\n                    {\n                        type: 'text',\n                        raw: text,\n                        text\n                    }\n                ]\n            };\n        }\n    }\n    inlineText(src) {\n        const cap = this.rules.inline.text.exec(src);\n        if (cap) {\n            let text;\n            if (this.lexer.state.inRawBlock) {\n                text = cap[0];\n            }\n            else {\n                text = escape$1(cap[0]);\n            }\n            return {\n                type: 'text',\n                raw: cap[0],\n                text\n            };\n        }\n    }\n}\n\n/**\n * Block-Level Grammar\n */\nconst newline = /^(?: *(?:\\n|$))+/;\nconst blockCode = /^( {4}[^\\n]+(?:\\n(?: *(?:\\n|$))*)?)+/;\nconst fences = /^ {0,3}(`{3,}(?=[^`\\n]*(?:\\n|$))|~{3,})([^\\n]*)(?:\\n|$)(?:|([\\s\\S]*?)(?:\\n|$))(?: {0,3}\\1[~`]* *(?=\\n|$)|$)/;\nconst hr = /^ {0,3}((?:-[\\t ]*){3,}|(?:_[ \\t]*){3,}|(?:\\*[ \\t]*){3,})(?:\\n+|$)/;\nconst heading = /^ {0,3}(#{1,6})(?=\\s|$)(.*)(?:\\n+|$)/;\nconst bullet = /(?:[*+-]|\\d{1,9}[.)])/;\nconst lheading = edit(/^(?!bull |blockCode|fences|blockquote|heading|html)((?:.|\\n(?!\\s*?\\n|bull |blockCode|fences|blockquote|heading|html))+?)\\n {0,3}(=+|-+) *(?:\\n+|$)/)\n    .replace(/bull/g, bullet) // lists can interrupt\n    .replace(/blockCode/g, / {4}/) // indented code blocks can interrupt\n    .replace(/fences/g, / {0,3}(?:`{3,}|~{3,})/) // fenced code blocks can interrupt\n    .replace(/blockquote/g, / {0,3}>/) // blockquote can interrupt\n    .replace(/heading/g, / {0,3}#{1,6}/) // ATX heading can interrupt\n    .replace(/html/g, / {0,3}<[^\\n>]+>\\n/) // block html can interrupt\n    .getRegex();\nconst _paragraph = /^([^\\n]+(?:\\n(?!hr|heading|lheading|blockquote|fences|list|html|table| +\\n)[^\\n]+)*)/;\nconst blockText = /^[^\\n]+/;\nconst _blockLabel = /(?!\\s*\\])(?:\\\\.|[^\\[\\]\\\\])+/;\nconst def = edit(/^ {0,3}\\[(label)\\]: *(?:\\n *)?([^<\\s][^\\s]*|<.*?>)(?:(?: +(?:\\n *)?| *\\n *)(title))? *(?:\\n+|$)/)\n    .replace('label', _blockLabel)\n    .replace('title', /(?:\"(?:\\\\\"?|[^\"\\\\])*\"|'[^'\\n]*(?:\\n[^'\\n]+)*\\n?'|\\([^()]*\\))/)\n    .getRegex();\nconst list = edit(/^( {0,3}bull)([ \\t][^\\n]+?)?(?:\\n|$)/)\n    .replace(/bull/g, bullet)\n    .getRegex();\nconst _tag = 'address|article|aside|base|basefont|blockquote|body|caption'\n    + '|center|col|colgroup|dd|details|dialog|dir|div|dl|dt|fieldset|figcaption'\n    + '|figure|footer|form|frame|frameset|h[1-6]|head|header|hr|html|iframe'\n    + '|legend|li|link|main|menu|menuitem|meta|nav|noframes|ol|optgroup|option'\n    + '|p|param|search|section|summary|table|tbody|td|tfoot|th|thead|title'\n    + '|tr|track|ul';\nconst _comment = /<!--(?:-?>|[\\s\\S]*?(?:-->|$))/;\nconst html = edit('^ {0,3}(?:' // optional indentation\n    + '<(script|pre|style|textarea)[\\\\s>][\\\\s\\\\S]*?(?:</\\\\1>[^\\\\n]*\\\\n+|$)' // (1)\n    + '|comment[^\\\\n]*(\\\\n+|$)' // (2)\n    + '|<\\\\?[\\\\s\\\\S]*?(?:\\\\?>\\\\n*|$)' // (3)\n    + '|<![A-Z][\\\\s\\\\S]*?(?:>\\\\n*|$)' // (4)\n    + '|<!\\\\[CDATA\\\\[[\\\\s\\\\S]*?(?:\\\\]\\\\]>\\\\n*|$)' // (5)\n    + '|</?(tag)(?: +|\\\\n|/?>)[\\\\s\\\\S]*?(?:(?:\\\\n *)+\\\\n|$)' // (6)\n    + '|<(?!script|pre|style|textarea)([a-z][\\\\w-]*)(?:attribute)*? */?>(?=[ \\\\t]*(?:\\\\n|$))[\\\\s\\\\S]*?(?:(?:\\\\n *)+\\\\n|$)' // (7) open tag\n    + '|</(?!script|pre|style|textarea)[a-z][\\\\w-]*\\\\s*>(?=[ \\\\t]*(?:\\\\n|$))[\\\\s\\\\S]*?(?:(?:\\\\n *)+\\\\n|$)' // (7) closing tag\n    + ')', 'i')\n    .replace('comment', _comment)\n    .replace('tag', _tag)\n    .replace('attribute', / +[a-zA-Z:_][\\w.:-]*(?: *= *\"[^\"\\n]*\"| *= *'[^'\\n]*'| *= *[^\\s\"'=<>`]+)?/)\n    .getRegex();\nconst paragraph = edit(_paragraph)\n    .replace('hr', hr)\n    .replace('heading', ' {0,3}#{1,6}(?:\\\\s|$)')\n    .replace('|lheading', '') // setext headings don't interrupt commonmark paragraphs\n    .replace('|table', '')\n    .replace('blockquote', ' {0,3}>')\n    .replace('fences', ' {0,3}(?:`{3,}(?=[^`\\\\n]*\\\\n)|~{3,})[^\\\\n]*\\\\n')\n    .replace('list', ' {0,3}(?:[*+-]|1[.)]) ') // only lists starting from 1 can interrupt\n    .replace('html', '</?(?:tag)(?: +|\\\\n|/?>)|<(?:script|pre|style|textarea|!--)')\n    .replace('tag', _tag) // pars can be interrupted by type (6) html blocks\n    .getRegex();\nconst blockquote = edit(/^( {0,3}> ?(paragraph|[^\\n]*)(?:\\n|$))+/)\n    .replace('paragraph', paragraph)\n    .getRegex();\n/**\n * Normal Block Grammar\n */\nconst blockNormal = {\n    blockquote,\n    code: blockCode,\n    def,\n    fences,\n    heading,\n    hr,\n    html,\n    lheading,\n    list,\n    newline,\n    paragraph,\n    table: noopTest,\n    text: blockText\n};\n/**\n * GFM Block Grammar\n */\nconst gfmTable = edit('^ *([^\\\\n ].*)\\\\n' // Header\n    + ' {0,3}((?:\\\\| *)?:?-+:? *(?:\\\\| *:?-+:? *)*(?:\\\\| *)?)' // Align\n    + '(?:\\\\n((?:(?! *\\\\n|hr|heading|blockquote|code|fences|list|html).*(?:\\\\n|$))*)\\\\n*|$)') // Cells\n    .replace('hr', hr)\n    .replace('heading', ' {0,3}#{1,6}(?:\\\\s|$)')\n    .replace('blockquote', ' {0,3}>')\n    .replace('code', ' {4}[^\\\\n]')\n    .replace('fences', ' {0,3}(?:`{3,}(?=[^`\\\\n]*\\\\n)|~{3,})[^\\\\n]*\\\\n')\n    .replace('list', ' {0,3}(?:[*+-]|1[.)]) ') // only lists starting from 1 can interrupt\n    .replace('html', '</?(?:tag)(?: +|\\\\n|/?>)|<(?:script|pre|style|textarea|!--)')\n    .replace('tag', _tag) // tables can be interrupted by type (6) html blocks\n    .getRegex();\nconst blockGfm = {\n    ...blockNormal,\n    table: gfmTable,\n    paragraph: edit(_paragraph)\n        .replace('hr', hr)\n        .replace('heading', ' {0,3}#{1,6}(?:\\\\s|$)')\n        .replace('|lheading', '') // setext headings don't interrupt commonmark paragraphs\n        .replace('table', gfmTable) // interrupt paragraphs with table\n        .replace('blockquote', ' {0,3}>')\n        .replace('fences', ' {0,3}(?:`{3,}(?=[^`\\\\n]*\\\\n)|~{3,})[^\\\\n]*\\\\n')\n        .replace('list', ' {0,3}(?:[*+-]|1[.)]) ') // only lists starting from 1 can interrupt\n        .replace('html', '</?(?:tag)(?: +|\\\\n|/?>)|<(?:script|pre|style|textarea|!--)')\n        .replace('tag', _tag) // pars can be interrupted by type (6) html blocks\n        .getRegex()\n};\n/**\n * Pedantic grammar (original John Gruber's loose markdown specification)\n */\nconst blockPedantic = {\n    ...blockNormal,\n    html: edit('^ *(?:comment *(?:\\\\n|\\\\s*$)'\n        + '|<(tag)[\\\\s\\\\S]+?</\\\\1> *(?:\\\\n{2,}|\\\\s*$)' // closed tag\n        + '|<tag(?:\"[^\"]*\"|\\'[^\\']*\\'|\\\\s[^\\'\"/>\\\\s]*)*?/?> *(?:\\\\n{2,}|\\\\s*$))')\n        .replace('comment', _comment)\n        .replace(/tag/g, '(?!(?:'\n        + 'a|em|strong|small|s|cite|q|dfn|abbr|data|time|code|var|samp|kbd|sub'\n        + '|sup|i|b|u|mark|ruby|rt|rp|bdi|bdo|span|br|wbr|ins|del|img)'\n        + '\\\\b)\\\\w+(?!:|[^\\\\w\\\\s@]*@)\\\\b')\n        .getRegex(),\n    def: /^ *\\[([^\\]]+)\\]: *<?([^\\s>]+)>?(?: +([\"(][^\\n]+[\")]))? *(?:\\n+|$)/,\n    heading: /^(#{1,6})(.*)(?:\\n+|$)/,\n    fences: noopTest, // fences not supported\n    lheading: /^(.+?)\\n {0,3}(=+|-+) *(?:\\n+|$)/,\n    paragraph: edit(_paragraph)\n        .replace('hr', hr)\n        .replace('heading', ' *#{1,6} *[^\\n]')\n        .replace('lheading', lheading)\n        .replace('|table', '')\n        .replace('blockquote', ' {0,3}>')\n        .replace('|fences', '')\n        .replace('|list', '')\n        .replace('|html', '')\n        .replace('|tag', '')\n        .getRegex()\n};\n/**\n * Inline-Level Grammar\n */\nconst escape = /^\\\\([!\"#$%&'()*+,\\-./:;<=>?@\\[\\]\\\\^_`{|}~])/;\nconst inlineCode = /^(`+)([^`]|[^`][\\s\\S]*?[^`])\\1(?!`)/;\nconst br = /^( {2,}|\\\\)\\n(?!\\s*$)/;\nconst inlineText = /^(`+|[^`])(?:(?= {2,}\\n)|[\\s\\S]*?(?:(?=[\\\\<!\\[`*_]|\\b_|$)|[^ ](?= {2,}\\n)))/;\n// list of unicode punctuation marks, plus any missing characters from CommonMark spec\nconst _punctuation = '\\\\p{P}\\\\p{S}';\nconst punctuation = edit(/^((?![*_])[\\spunctuation])/, 'u')\n    .replace(/punctuation/g, _punctuation).getRegex();\n// sequences em should skip over [title](link), `code`, <html>\nconst blockSkip = /\\[[^[\\]]*?\\]\\([^\\(\\)]*?\\)|`[^`]*?`|<[^<>]*?>/g;\nconst emStrongLDelim = edit(/^(?:\\*+(?:((?!\\*)[punct])|[^\\s*]))|^_+(?:((?!_)[punct])|([^\\s_]))/, 'u')\n    .replace(/punct/g, _punctuation)\n    .getRegex();\nconst emStrongRDelimAst = edit('^[^_*]*?__[^_*]*?\\\\*[^_*]*?(?=__)' // Skip orphan inside strong\n    + '|[^*]+(?=[^*])' // Consume to delim\n    + '|(?!\\\\*)[punct](\\\\*+)(?=[\\\\s]|$)' // (1) #*** can only be a Right Delimiter\n    + '|[^punct\\\\s](\\\\*+)(?!\\\\*)(?=[punct\\\\s]|$)' // (2) a***#, a*** can only be a Right Delimiter\n    + '|(?!\\\\*)[punct\\\\s](\\\\*+)(?=[^punct\\\\s])' // (3) #***a, ***a can only be Left Delimiter\n    + '|[\\\\s](\\\\*+)(?!\\\\*)(?=[punct])' // (4) ***# can only be Left Delimiter\n    + '|(?!\\\\*)[punct](\\\\*+)(?!\\\\*)(?=[punct])' // (5) #***# can be either Left or Right Delimiter\n    + '|[^punct\\\\s](\\\\*+)(?=[^punct\\\\s])', 'gu') // (6) a***a can be either Left or Right Delimiter\n    .replace(/punct/g, _punctuation)\n    .getRegex();\n// (6) Not allowed for _\nconst emStrongRDelimUnd = edit('^[^_*]*?\\\\*\\\\*[^_*]*?_[^_*]*?(?=\\\\*\\\\*)' // Skip orphan inside strong\n    + '|[^_]+(?=[^_])' // Consume to delim\n    + '|(?!_)[punct](_+)(?=[\\\\s]|$)' // (1) #___ can only be a Right Delimiter\n    + '|[^punct\\\\s](_+)(?!_)(?=[punct\\\\s]|$)' // (2) a___#, a___ can only be a Right Delimiter\n    + '|(?!_)[punct\\\\s](_+)(?=[^punct\\\\s])' // (3) #___a, ___a can only be Left Delimiter\n    + '|[\\\\s](_+)(?!_)(?=[punct])' // (4) ___# can only be Left Delimiter\n    + '|(?!_)[punct](_+)(?!_)(?=[punct])', 'gu') // (5) #___# can be either Left or Right Delimiter\n    .replace(/punct/g, _punctuation)\n    .getRegex();\nconst anyPunctuation = edit(/\\\\([punct])/, 'gu')\n    .replace(/punct/g, _punctuation)\n    .getRegex();\nconst autolink = edit(/^<(scheme:[^\\s\\x00-\\x1f<>]*|email)>/)\n    .replace('scheme', /[a-zA-Z][a-zA-Z0-9+.-]{1,31}/)\n    .replace('email', /[a-zA-Z0-9.!#$%&'*+/=?^_`{|}~-]+(@)[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(?:\\.[a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)+(?![-_])/)\n    .getRegex();\nconst _inlineComment = edit(_comment).replace('(?:-->|$)', '-->').getRegex();\nconst tag = edit('^comment'\n    + '|^</[a-zA-Z][\\\\w:-]*\\\\s*>' // self-closing tag\n    + '|^<[a-zA-Z][\\\\w-]*(?:attribute)*?\\\\s*/?>' // open tag\n    + '|^<\\\\?[\\\\s\\\\S]*?\\\\?>' // processing instruction, e.g. <?php ?>\n    + '|^<![a-zA-Z]+\\\\s[\\\\s\\\\S]*?>' // declaration, e.g. <!DOCTYPE html>\n    + '|^<!\\\\[CDATA\\\\[[\\\\s\\\\S]*?\\\\]\\\\]>') // CDATA section\n    .replace('comment', _inlineComment)\n    .replace('attribute', /\\s+[a-zA-Z:_][\\w.:-]*(?:\\s*=\\s*\"[^\"]*\"|\\s*=\\s*'[^']*'|\\s*=\\s*[^\\s\"'=<>`]+)?/)\n    .getRegex();\nconst _inlineLabel = /(?:\\[(?:\\\\.|[^\\[\\]\\\\])*\\]|\\\\.|`[^`]*`|[^\\[\\]\\\\`])*?/;\nconst link = edit(/^!?\\[(label)\\]\\(\\s*(href)(?:\\s+(title))?\\s*\\)/)\n    .replace('label', _inlineLabel)\n    .replace('href', /<(?:\\\\.|[^\\n<>\\\\])+>|[^\\s\\x00-\\x1f]*/)\n    .replace('title', /\"(?:\\\\\"?|[^\"\\\\])*\"|'(?:\\\\'?|[^'\\\\])*'|\\((?:\\\\\\)?|[^)\\\\])*\\)/)\n    .getRegex();\nconst reflink = edit(/^!?\\[(label)\\]\\[(ref)\\]/)\n    .replace('label', _inlineLabel)\n    .replace('ref', _blockLabel)\n    .getRegex();\nconst nolink = edit(/^!?\\[(ref)\\](?:\\[\\])?/)\n    .replace('ref', _blockLabel)\n    .getRegex();\nconst reflinkSearch = edit('reflink|nolink(?!\\\\()', 'g')\n    .replace('reflink', reflink)\n    .replace('nolink', nolink)\n    .getRegex();\n/**\n * Normal Inline Grammar\n */\nconst inlineNormal = {\n    _backpedal: noopTest, // only used for GFM url\n    anyPunctuation,\n    autolink,\n    blockSkip,\n    br,\n    code: inlineCode,\n    del: noopTest,\n    emStrongLDelim,\n    emStrongRDelimAst,\n    emStrongRDelimUnd,\n    escape,\n    link,\n    nolink,\n    punctuation,\n    reflink,\n    reflinkSearch,\n    tag,\n    text: inlineText,\n    url: noopTest\n};\n/**\n * Pedantic Inline Grammar\n */\nconst inlinePedantic = {\n    ...inlineNormal,\n    link: edit(/^!?\\[(label)\\]\\((.*?)\\)/)\n        .replace('label', _inlineLabel)\n        .getRegex(),\n    reflink: edit(/^!?\\[(label)\\]\\s*\\[([^\\]]*)\\]/)\n        .replace('label', _inlineLabel)\n        .getRegex()\n};\n/**\n * GFM Inline Grammar\n */\nconst inlineGfm = {\n    ...inlineNormal,\n    escape: edit(escape).replace('])', '~|])').getRegex(),\n    url: edit(/^((?:ftp|https?):\\/\\/|www\\.)(?:[a-zA-Z0-9\\-]+\\.?)+[^\\s<]*|^email/, 'i')\n        .replace('email', /[A-Za-z0-9._+-]+(@)[a-zA-Z0-9-_]+(?:\\.[a-zA-Z0-9-_]*[a-zA-Z0-9])+(?![-_])/)\n        .getRegex(),\n    _backpedal: /(?:[^?!.,:;*_'\"~()&]+|\\([^)]*\\)|&(?![a-zA-Z0-9]+;$)|[?!.,:;*_'\"~)]+(?!$))+/,\n    del: /^(~~?)(?=[^\\s~])([\\s\\S]*?[^\\s~])\\1(?=[^~]|$)/,\n    text: /^([`~]+|[^`~])(?:(?= {2,}\\n)|(?=[a-zA-Z0-9.!#$%&'*+\\/=?_`{\\|}~-]+@)|[\\s\\S]*?(?:(?=[\\\\<!\\[`*~_]|\\b_|https?:\\/\\/|ftp:\\/\\/|www\\.|$)|[^ ](?= {2,}\\n)|[^a-zA-Z0-9.!#$%&'*+\\/=?_`{\\|}~-](?=[a-zA-Z0-9.!#$%&'*+\\/=?_`{\\|}~-]+@)))/\n};\n/**\n * GFM + Line Breaks Inline Grammar\n */\nconst inlineBreaks = {\n    ...inlineGfm,\n    br: edit(br).replace('{2,}', '*').getRegex(),\n    text: edit(inlineGfm.text)\n        .replace('\\\\b_', '\\\\b_| {2,}\\\\n')\n        .replace(/\\{2,\\}/g, '*')\n        .getRegex()\n};\n/**\n * exports\n */\nconst block = {\n    normal: blockNormal,\n    gfm: blockGfm,\n    pedantic: blockPedantic\n};\nconst inline = {\n    normal: inlineNormal,\n    gfm: inlineGfm,\n    breaks: inlineBreaks,\n    pedantic: inlinePedantic\n};\n\n/**\n * Block Lexer\n */\nclass _Lexer {\n    tokens;\n    options;\n    state;\n    tokenizer;\n    inlineQueue;\n    constructor(options) {\n        // TokenList cannot be created in one go\n        this.tokens = [];\n        this.tokens.links = Object.create(null);\n        this.options = options || _defaults;\n        this.options.tokenizer = this.options.tokenizer || new _Tokenizer();\n        this.tokenizer = this.options.tokenizer;\n        this.tokenizer.options = this.options;\n        this.tokenizer.lexer = this;\n        this.inlineQueue = [];\n        this.state = {\n            inLink: false,\n            inRawBlock: false,\n            top: true\n        };\n        const rules = {\n            block: block.normal,\n            inline: inline.normal\n        };\n        if (this.options.pedantic) {\n            rules.block = block.pedantic;\n            rules.inline = inline.pedantic;\n        }\n        else if (this.options.gfm) {\n            rules.block = block.gfm;\n            if (this.options.breaks) {\n                rules.inline = inline.breaks;\n            }\n            else {\n                rules.inline = inline.gfm;\n            }\n        }\n        this.tokenizer.rules = rules;\n    }\n    /**\n     * Expose Rules\n     */\n    static get rules() {\n        return {\n            block,\n            inline\n        };\n    }\n    /**\n     * Static Lex Method\n     */\n    static lex(src, options) {\n        const lexer = new _Lexer(options);\n        return lexer.lex(src);\n    }\n    /**\n     * Static Lex Inline Method\n     */\n    static lexInline(src, options) {\n        const lexer = new _Lexer(options);\n        return lexer.inlineTokens(src);\n    }\n    /**\n     * Preprocessing\n     */\n    lex(src) {\n        src = src\n            .replace(/\\r\\n|\\r/g, '\\n');\n        this.blockTokens(src, this.tokens);\n        for (let i = 0; i < this.inlineQueue.length; i++) {\n            const next = this.inlineQueue[i];\n            this.inlineTokens(next.src, next.tokens);\n        }\n        this.inlineQueue = [];\n        return this.tokens;\n    }\n    blockTokens(src, tokens = []) {\n        if (this.options.pedantic) {\n            src = src.replace(/\\t/g, '    ').replace(/^ +$/gm, '');\n        }\n        else {\n            src = src.replace(/^( *)(\\t+)/gm, (_, leading, tabs) => {\n                return leading + '    '.repeat(tabs.length);\n            });\n        }\n        let token;\n        let lastToken;\n        let cutSrc;\n        let lastParagraphClipped;\n        while (src) {\n            if (this.options.extensions\n                && this.options.extensions.block\n                && this.options.extensions.block.some((extTokenizer) => {\n                    if (token = extTokenizer.call({ lexer: this }, src, tokens)) {\n                        src = src.substring(token.raw.length);\n                        tokens.push(token);\n                        return true;\n                    }\n                    return false;\n                })) {\n                continue;\n            }\n            // newline\n            if (token = this.tokenizer.space(src)) {\n                src = src.substring(token.raw.length);\n                if (token.raw.length === 1 && tokens.length > 0) {\n                    // if there's a single \\n as a spacer, it's terminating the last line,\n                    // so move it there so that we don't get unnecessary paragraph tags\n                    tokens[tokens.length - 1].raw += '\\n';\n                }\n                else {\n                    tokens.push(token);\n                }\n                continue;\n            }\n            // code\n            if (token = this.tokenizer.code(src)) {\n                src = src.substring(token.raw.length);\n                lastToken = tokens[tokens.length - 1];\n                // An indented code block cannot interrupt a paragraph.\n                if (lastToken && (lastToken.type === 'paragraph' || lastToken.type === 'text')) {\n                    lastToken.raw += '\\n' + token.raw;\n                    lastToken.text += '\\n' + token.text;\n                    this.inlineQueue[this.inlineQueue.length - 1].src = lastToken.text;\n                }\n                else {\n                    tokens.push(token);\n                }\n                continue;\n            }\n            // fences\n            if (token = this.tokenizer.fences(src)) {\n                src = src.substring(token.raw.length);\n                tokens.push(token);\n                continue;\n            }\n            // heading\n            if (token = this.tokenizer.heading(src)) {\n                src = src.substring(token.raw.length);\n                tokens.push(token);\n                continue;\n            }\n            // hr\n            if (token = this.tokenizer.hr(src)) {\n                src = src.substring(token.raw.length);\n                tokens.push(token);\n                continue;\n            }\n            // blockquote\n            if (token = this.tokenizer.blockquote(src)) {\n                src = src.substring(token.raw.length);\n                tokens.push(token);\n                continue;\n            }\n            // list\n            if (token = this.tokenizer.list(src)) {\n                src = src.substring(token.raw.length);\n                tokens.push(token);\n                continue;\n            }\n            // html\n            if (token = this.tokenizer.html(src)) {\n                src = src.substring(token.raw.length);\n                tokens.push(token);\n                continue;\n            }\n            // def\n            if (token = this.tokenizer.def(src)) {\n                src = src.substring(token.raw.length);\n                lastToken = tokens[tokens.length - 1];\n                if (lastToken && (lastToken.type === 'paragraph' || lastToken.type === 'text')) {\n                    lastToken.raw += '\\n' + token.raw;\n                    lastToken.text += '\\n' + token.raw;\n                    this.inlineQueue[this.inlineQueue.length - 1].src = lastToken.text;\n                }\n                else if (!this.tokens.links[token.tag]) {\n                    this.tokens.links[token.tag] = {\n                        href: token.href,\n                        title: token.title\n                    };\n                }\n                continue;\n            }\n            // table (gfm)\n            if (token = this.tokenizer.table(src)) {\n                src = src.substring(token.raw.length);\n                tokens.push(token);\n                continue;\n            }\n            // lheading\n            if (token = this.tokenizer.lheading(src)) {\n                src = src.substring(token.raw.length);\n                tokens.push(token);\n                continue;\n            }\n            // top-level paragraph\n            // prevent paragraph consuming extensions by clipping 'src' to extension start\n            cutSrc = src;\n            if (this.options.extensions && this.options.extensions.startBlock) {\n                let startIndex = Infinity;\n                const tempSrc = src.slice(1);\n                let tempStart;\n                this.options.extensions.startBlock.forEach((getStartIndex) => {\n                    tempStart = getStartIndex.call({ lexer: this }, tempSrc);\n                    if (typeof tempStart === 'number' && tempStart >= 0) {\n                        startIndex = Math.min(startIndex, tempStart);\n                    }\n                });\n                if (startIndex < Infinity && startIndex >= 0) {\n                    cutSrc = src.substring(0, startIndex + 1);\n                }\n            }\n            if (this.state.top && (token = this.tokenizer.paragraph(cutSrc))) {\n                lastToken = tokens[tokens.length - 1];\n                if (lastParagraphClipped && lastToken.type === 'paragraph') {\n                    lastToken.raw += '\\n' + token.raw;\n                    lastToken.text += '\\n' + token.text;\n                    this.inlineQueue.pop();\n                    this.inlineQueue[this.inlineQueue.length - 1].src = lastToken.text;\n                }\n                else {\n                    tokens.push(token);\n                }\n                lastParagraphClipped = (cutSrc.length !== src.length);\n                src = src.substring(token.raw.length);\n                continue;\n            }\n            // text\n            if (token = this.tokenizer.text(src)) {\n                src = src.substring(token.raw.length);\n                lastToken = tokens[tokens.length - 1];\n                if (lastToken && lastToken.type === 'text') {\n                    lastToken.raw += '\\n' + token.raw;\n                    lastToken.text += '\\n' + token.text;\n                    this.inlineQueue.pop();\n                    this.inlineQueue[this.inlineQueue.length - 1].src = lastToken.text;\n                }\n                else {\n                    tokens.push(token);\n                }\n                continue;\n            }\n            if (src) {\n                const errMsg = 'Infinite loop on byte: ' + src.charCodeAt(0);\n                if (this.options.silent) {\n                    console.error(errMsg);\n                    break;\n                }\n                else {\n                    throw new Error(errMsg);\n                }\n            }\n        }\n        this.state.top = true;\n        return tokens;\n    }\n    inline(src, tokens = []) {\n        this.inlineQueue.push({ src, tokens });\n        return tokens;\n    }\n    /**\n     * Lexing/Compiling\n     */\n    inlineTokens(src, tokens = []) {\n        let token, lastToken, cutSrc;\n        // String with links masked to avoid interference with em and strong\n        let maskedSrc = src;\n        let match;\n        let keepPrevChar, prevChar;\n        // Mask out reflinks\n        if (this.tokens.links) {\n            const links = Object.keys(this.tokens.links);\n            if (links.length > 0) {\n                while ((match = this.tokenizer.rules.inline.reflinkSearch.exec(maskedSrc)) != null) {\n                    if (links.includes(match[0].slice(match[0].lastIndexOf('[') + 1, -1))) {\n                        maskedSrc = maskedSrc.slice(0, match.index) + '[' + 'a'.repeat(match[0].length - 2) + ']' + maskedSrc.slice(this.tokenizer.rules.inline.reflinkSearch.lastIndex);\n                    }\n                }\n            }\n        }\n        // Mask out other blocks\n        while ((match = this.tokenizer.rules.inline.blockSkip.exec(maskedSrc)) != null) {\n            maskedSrc = maskedSrc.slice(0, match.index) + '[' + 'a'.repeat(match[0].length - 2) + ']' + maskedSrc.slice(this.tokenizer.rules.inline.blockSkip.lastIndex);\n        }\n        // Mask out escaped characters\n        while ((match = this.tokenizer.rules.inline.anyPunctuation.exec(maskedSrc)) != null) {\n            maskedSrc = maskedSrc.slice(0, match.index) + '++' + maskedSrc.slice(this.tokenizer.rules.inline.anyPunctuation.lastIndex);\n        }\n        while (src) {\n            if (!keepPrevChar) {\n                prevChar = '';\n            }\n            keepPrevChar = false;\n            // extensions\n            if (this.options.extensions\n                && this.options.extensions.inline\n                && this.options.extensions.inline.some((extTokenizer) => {\n                    if (token = extTokenizer.call({ lexer: this }, src, tokens)) {\n                        src = src.substring(token.raw.length);\n                        tokens.push(token);\n                        return true;\n                    }\n                    return false;\n                })) {\n                continue;\n            }\n            // escape\n            if (token = this.tokenizer.escape(src)) {\n                src = src.substring(token.raw.length);\n                tokens.push(token);\n                continue;\n            }\n            // tag\n            if (token = this.tokenizer.tag(src)) {\n                src = src.substring(token.raw.length);\n                lastToken = tokens[tokens.length - 1];\n                if (lastToken && token.type === 'text' && lastToken.type === 'text') {\n                    lastToken.raw += token.raw;\n                    lastToken.text += token.text;\n                }\n                else {\n                    tokens.push(token);\n                }\n                continue;\n            }\n            // link\n            if (token = this.tokenizer.link(src)) {\n                src = src.substring(token.raw.length);\n                tokens.push(token);\n                continue;\n            }\n            // reflink, nolink\n            if (token = this.tokenizer.reflink(src, this.tokens.links)) {\n                src = src.substring(token.raw.length);\n                lastToken = tokens[tokens.length - 1];\n                if (lastToken && token.type === 'text' && lastToken.type === 'text') {\n                    lastToken.raw += token.raw;\n                    lastToken.text += token.text;\n                }\n                else {\n                    tokens.push(token);\n                }\n                continue;\n            }\n            // em & strong\n            if (token = this.tokenizer.emStrong(src, maskedSrc, prevChar)) {\n                src = src.substring(token.raw.length);\n                tokens.push(token);\n                continue;\n            }\n            // code\n            if (token = this.tokenizer.codespan(src)) {\n                src = src.substring(token.raw.length);\n                tokens.push(token);\n                continue;\n            }\n            // br\n            if (token = this.tokenizer.br(src)) {\n                src = src.substring(token.raw.length);\n                tokens.push(token);\n                continue;\n            }\n            // del (gfm)\n            if (token = this.tokenizer.del(src)) {\n                src = src.substring(token.raw.length);\n                tokens.push(token);\n                continue;\n            }\n            // autolink\n            if (token = this.tokenizer.autolink(src)) {\n                src = src.substring(token.raw.length);\n                tokens.push(token);\n                continue;\n            }\n            // url (gfm)\n            if (!this.state.inLink && (token = this.tokenizer.url(src))) {\n                src = src.substring(token.raw.length);\n                tokens.push(token);\n                continue;\n            }\n            // text\n            // prevent inlineText consuming extensions by clipping 'src' to extension start\n            cutSrc = src;\n            if (this.options.extensions && this.options.extensions.startInline) {\n                let startIndex = Infinity;\n                const tempSrc = src.slice(1);\n                let tempStart;\n                this.options.extensions.startInline.forEach((getStartIndex) => {\n                    tempStart = getStartIndex.call({ lexer: this }, tempSrc);\n                    if (typeof tempStart === 'number' && tempStart >= 0) {\n                        startIndex = Math.min(startIndex, tempStart);\n                    }\n                });\n                if (startIndex < Infinity && startIndex >= 0) {\n                    cutSrc = src.substring(0, startIndex + 1);\n                }\n            }\n            if (token = this.tokenizer.inlineText(cutSrc)) {\n                src = src.substring(token.raw.length);\n                if (token.raw.slice(-1) !== '_') { // Track prevChar before string of ____ started\n                    prevChar = token.raw.slice(-1);\n                }\n                keepPrevChar = true;\n                lastToken = tokens[tokens.length - 1];\n                if (lastToken && lastToken.type === 'text') {\n                    lastToken.raw += token.raw;\n                    lastToken.text += token.text;\n                }\n                else {\n                    tokens.push(token);\n                }\n                continue;\n            }\n            if (src) {\n                const errMsg = 'Infinite loop on byte: ' + src.charCodeAt(0);\n                if (this.options.silent) {\n                    console.error(errMsg);\n                    break;\n                }\n                else {\n                    throw new Error(errMsg);\n                }\n            }\n        }\n        return tokens;\n    }\n}\n\n/**\n * Renderer\n */\nclass _Renderer {\n    options;\n    constructor(options) {\n        this.options = options || _defaults;\n    }\n    code(code, infostring, escaped) {\n        const lang = (infostring || '').match(/^\\S*/)?.[0];\n        code = code.replace(/\\n$/, '') + '\\n';\n        if (!lang) {\n            return '<pre><code>'\n                + (escaped ? code : escape$1(code, true))\n                + '</code></pre>\\n';\n        }\n        return '<pre><code class=\"language-'\n            + escape$1(lang)\n            + '\">'\n            + (escaped ? code : escape$1(code, true))\n            + '</code></pre>\\n';\n    }\n    blockquote(quote) {\n        return `<blockquote>\\n${quote}</blockquote>\\n`;\n    }\n    html(html, block) {\n        return html;\n    }\n    heading(text, level, raw) {\n        // ignore IDs\n        return `<h${level}>${text}</h${level}>\\n`;\n    }\n    hr() {\n        return '<hr>\\n';\n    }\n    list(body, ordered, start) {\n        const type = ordered ? 'ol' : 'ul';\n        const startatt = (ordered && start !== 1) ? (' start=\"' + start + '\"') : '';\n        return '<' + type + startatt + '>\\n' + body + '</' + type + '>\\n';\n    }\n    listitem(text, task, checked) {\n        return `<li>${text}</li>\\n`;\n    }\n    checkbox(checked) {\n        return '<input '\n            + (checked ? 'checked=\"\" ' : '')\n            + 'disabled=\"\" type=\"checkbox\">';\n    }\n    paragraph(text) {\n        return `<p>${text}</p>\\n`;\n    }\n    table(header, body) {\n        if (body)\n            body = `<tbody>${body}</tbody>`;\n        return '<table>\\n'\n            + '<thead>\\n'\n            + header\n            + '</thead>\\n'\n            + body\n            + '</table>\\n';\n    }\n    tablerow(content) {\n        return `<tr>\\n${content}</tr>\\n`;\n    }\n    tablecell(content, flags) {\n        const type = flags.header ? 'th' : 'td';\n        const tag = flags.align\n            ? `<${type} align=\"${flags.align}\">`\n            : `<${type}>`;\n        return tag + content + `</${type}>\\n`;\n    }\n    /**\n     * span level renderer\n     */\n    strong(text) {\n        return `<strong>${text}</strong>`;\n    }\n    em(text) {\n        return `<em>${text}</em>`;\n    }\n    codespan(text) {\n        return `<code>${text}</code>`;\n    }\n    br() {\n        return '<br>';\n    }\n    del(text) {\n        return `<del>${text}</del>`;\n    }\n    link(href, title, text) {\n        const cleanHref = cleanUrl(href);\n        if (cleanHref === null) {\n            return text;\n        }\n        href = cleanHref;\n        let out = '<a href=\"' + href + '\"';\n        if (title) {\n            out += ' title=\"' + title + '\"';\n        }\n        out += '>' + text + '</a>';\n        return out;\n    }\n    image(href, title, text) {\n        const cleanHref = cleanUrl(href);\n        if (cleanHref === null) {\n            return text;\n        }\n        href = cleanHref;\n        let out = `<img src=\"${href}\" alt=\"${text}\"`;\n        if (title) {\n            out += ` title=\"${title}\"`;\n        }\n        out += '>';\n        return out;\n    }\n    text(text) {\n        return text;\n    }\n}\n\n/**\n * TextRenderer\n * returns only the textual part of the token\n */\nclass _TextRenderer {\n    // no need for block level renderers\n    strong(text) {\n        return text;\n    }\n    em(text) {\n        return text;\n    }\n    codespan(text) {\n        return text;\n    }\n    del(text) {\n        return text;\n    }\n    html(text) {\n        return text;\n    }\n    text(text) {\n        return text;\n    }\n    link(href, title, text) {\n        return '' + text;\n    }\n    image(href, title, text) {\n        return '' + text;\n    }\n    br() {\n        return '';\n    }\n}\n\n/**\n * Parsing & Compiling\n */\nclass _Parser {\n    options;\n    renderer;\n    textRenderer;\n    constructor(options) {\n        this.options = options || _defaults;\n        this.options.renderer = this.options.renderer || new _Renderer();\n        this.renderer = this.options.renderer;\n        this.renderer.options = this.options;\n        this.textRenderer = new _TextRenderer();\n    }\n    /**\n     * Static Parse Method\n     */\n    static parse(tokens, options) {\n        const parser = new _Parser(options);\n        return parser.parse(tokens);\n    }\n    /**\n     * Static Parse Inline Method\n     */\n    static parseInline(tokens, options) {\n        const parser = new _Parser(options);\n        return parser.parseInline(tokens);\n    }\n    /**\n     * Parse Loop\n     */\n    parse(tokens, top = true) {\n        let out = '';\n        for (let i = 0; i < tokens.length; i++) {\n            const token = tokens[i];\n            // Run any renderer extensions\n            if (this.options.extensions && this.options.extensions.renderers && this.options.extensions.renderers[token.type]) {\n                const genericToken = token;\n                const ret = this.options.extensions.renderers[genericToken.type].call({ parser: this }, genericToken);\n                if (ret !== false || !['space', 'hr', 'heading', 'code', 'table', 'blockquote', 'list', 'html', 'paragraph', 'text'].includes(genericToken.type)) {\n                    out += ret || '';\n                    continue;\n                }\n            }\n            switch (token.type) {\n                case 'space': {\n                    continue;\n                }\n                case 'hr': {\n                    out += this.renderer.hr();\n                    continue;\n                }\n                case 'heading': {\n                    const headingToken = token;\n                    out += this.renderer.heading(this.parseInline(headingToken.tokens), headingToken.depth, unescape(this.parseInline(headingToken.tokens, this.textRenderer)));\n                    continue;\n                }\n                case 'code': {\n                    const codeToken = token;\n                    out += this.renderer.code(codeToken.text, codeToken.lang, !!codeToken.escaped);\n                    continue;\n                }\n                case 'table': {\n                    const tableToken = token;\n                    let header = '';\n                    // header\n                    let cell = '';\n                    for (let j = 0; j < tableToken.header.length; j++) {\n                        cell += this.renderer.tablecell(this.parseInline(tableToken.header[j].tokens), { header: true, align: tableToken.align[j] });\n                    }\n                    header += this.renderer.tablerow(cell);\n                    let body = '';\n                    for (let j = 0; j < tableToken.rows.length; j++) {\n                        const row = tableToken.rows[j];\n                        cell = '';\n                        for (let k = 0; k < row.length; k++) {\n                            cell += this.renderer.tablecell(this.parseInline(row[k].tokens), { header: false, align: tableToken.align[k] });\n                        }\n                        body += this.renderer.tablerow(cell);\n                    }\n                    out += this.renderer.table(header, body);\n                    continue;\n                }\n                case 'blockquote': {\n                    const blockquoteToken = token;\n                    const body = this.parse(blockquoteToken.tokens);\n                    out += this.renderer.blockquote(body);\n                    continue;\n                }\n                case 'list': {\n                    const listToken = token;\n                    const ordered = listToken.ordered;\n                    const start = listToken.start;\n                    const loose = listToken.loose;\n                    let body = '';\n                    for (let j = 0; j < listToken.items.length; j++) {\n                        const item = listToken.items[j];\n                        const checked = item.checked;\n                        const task = item.task;\n                        let itemBody = '';\n                        if (item.task) {\n                            const checkbox = this.renderer.checkbox(!!checked);\n                            if (loose) {\n                                if (item.tokens.length > 0 && item.tokens[0].type === 'paragraph') {\n                                    item.tokens[0].text = checkbox + ' ' + item.tokens[0].text;\n                                    if (item.tokens[0].tokens && item.tokens[0].tokens.length > 0 && item.tokens[0].tokens[0].type === 'text') {\n                                        item.tokens[0].tokens[0].text = checkbox + ' ' + item.tokens[0].tokens[0].text;\n                                    }\n                                }\n                                else {\n                                    item.tokens.unshift({\n                                        type: 'text',\n                                        text: checkbox + ' '\n                                    });\n                                }\n                            }\n                            else {\n                                itemBody += checkbox + ' ';\n                            }\n                        }\n                        itemBody += this.parse(item.tokens, loose);\n                        body += this.renderer.listitem(itemBody, task, !!checked);\n                    }\n                    out += this.renderer.list(body, ordered, start);\n                    continue;\n                }\n                case 'html': {\n                    const htmlToken = token;\n                    out += this.renderer.html(htmlToken.text, htmlToken.block);\n                    continue;\n                }\n                case 'paragraph': {\n                    const paragraphToken = token;\n                    out += this.renderer.paragraph(this.parseInline(paragraphToken.tokens));\n                    continue;\n                }\n                case 'text': {\n                    let textToken = token;\n                    let body = textToken.tokens ? this.parseInline(textToken.tokens) : textToken.text;\n                    while (i + 1 < tokens.length && tokens[i + 1].type === 'text') {\n                        textToken = tokens[++i];\n                        body += '\\n' + (textToken.tokens ? this.parseInline(textToken.tokens) : textToken.text);\n                    }\n                    out += top ? this.renderer.paragraph(body) : body;\n                    continue;\n                }\n                default: {\n                    const errMsg = 'Token with \"' + token.type + '\" type was not found.';\n                    if (this.options.silent) {\n                        console.error(errMsg);\n                        return '';\n                    }\n                    else {\n                        throw new Error(errMsg);\n                    }\n                }\n            }\n        }\n        return out;\n    }\n    /**\n     * Parse Inline Tokens\n     */\n    parseInline(tokens, renderer) {\n        renderer = renderer || this.renderer;\n        let out = '';\n        for (let i = 0; i < tokens.length; i++) {\n            const token = tokens[i];\n            // Run any renderer extensions\n            if (this.options.extensions && this.options.extensions.renderers && this.options.extensions.renderers[token.type]) {\n                const ret = this.options.extensions.renderers[token.type].call({ parser: this }, token);\n                if (ret !== false || !['escape', 'html', 'link', 'image', 'strong', 'em', 'codespan', 'br', 'del', 'text'].includes(token.type)) {\n                    out += ret || '';\n                    continue;\n                }\n            }\n            switch (token.type) {\n                case 'escape': {\n                    const escapeToken = token;\n                    out += renderer.text(escapeToken.text);\n                    break;\n                }\n                case 'html': {\n                    const tagToken = token;\n                    out += renderer.html(tagToken.text);\n                    break;\n                }\n                case 'link': {\n                    const linkToken = token;\n                    out += renderer.link(linkToken.href, linkToken.title, this.parseInline(linkToken.tokens, renderer));\n                    break;\n                }\n                case 'image': {\n                    const imageToken = token;\n                    out += renderer.image(imageToken.href, imageToken.title, imageToken.text);\n                    break;\n                }\n                case 'strong': {\n                    const strongToken = token;\n                    out += renderer.strong(this.parseInline(strongToken.tokens, renderer));\n                    break;\n                }\n                case 'em': {\n                    const emToken = token;\n                    out += renderer.em(this.parseInline(emToken.tokens, renderer));\n                    break;\n                }\n                case 'codespan': {\n                    const codespanToken = token;\n                    out += renderer.codespan(codespanToken.text);\n                    break;\n                }\n                case 'br': {\n                    out += renderer.br();\n                    break;\n                }\n                case 'del': {\n                    const delToken = token;\n                    out += renderer.del(this.parseInline(delToken.tokens, renderer));\n                    break;\n                }\n                case 'text': {\n                    const textToken = token;\n                    out += renderer.text(textToken.text);\n                    break;\n                }\n                default: {\n                    const errMsg = 'Token with \"' + token.type + '\" type was not found.';\n                    if (this.options.silent) {\n                        console.error(errMsg);\n                        return '';\n                    }\n                    else {\n                        throw new Error(errMsg);\n                    }\n                }\n            }\n        }\n        return out;\n    }\n}\n\nclass _Hooks {\n    options;\n    constructor(options) {\n        this.options = options || _defaults;\n    }\n    static passThroughHooks = new Set([\n        'preprocess',\n        'postprocess',\n        'processAllTokens'\n    ]);\n    /**\n     * Process markdown before marked\n     */\n    preprocess(markdown) {\n        return markdown;\n    }\n    /**\n     * Process HTML after marked is finished\n     */\n    postprocess(html) {\n        return html;\n    }\n    /**\n     * Process all tokens before walk tokens\n     */\n    processAllTokens(tokens) {\n        return tokens;\n    }\n}\n\nclass Marked {\n    defaults = _getDefaults();\n    options = this.setOptions;\n    parse = this.#parseMarkdown(_Lexer.lex, _Parser.parse);\n    parseInline = this.#parseMarkdown(_Lexer.lexInline, _Parser.parseInline);\n    Parser = _Parser;\n    Renderer = _Renderer;\n    TextRenderer = _TextRenderer;\n    Lexer = _Lexer;\n    Tokenizer = _Tokenizer;\n    Hooks = _Hooks;\n    constructor(...args) {\n        this.use(...args);\n    }\n    /**\n     * Run callback for every token\n     */\n    walkTokens(tokens, callback) {\n        let values = [];\n        for (const token of tokens) {\n            values = values.concat(callback.call(this, token));\n            switch (token.type) {\n                case 'table': {\n                    const tableToken = token;\n                    for (const cell of tableToken.header) {\n                        values = values.concat(this.walkTokens(cell.tokens, callback));\n                    }\n                    for (const row of tableToken.rows) {\n                        for (const cell of row) {\n                            values = values.concat(this.walkTokens(cell.tokens, callback));\n                        }\n                    }\n                    break;\n                }\n                case 'list': {\n                    const listToken = token;\n                    values = values.concat(this.walkTokens(listToken.items, callback));\n                    break;\n                }\n                default: {\n                    const genericToken = token;\n                    if (this.defaults.extensions?.childTokens?.[genericToken.type]) {\n                        this.defaults.extensions.childTokens[genericToken.type].forEach((childTokens) => {\n                            const tokens = genericToken[childTokens].flat(Infinity);\n                            values = values.concat(this.walkTokens(tokens, callback));\n                        });\n                    }\n                    else if (genericToken.tokens) {\n                        values = values.concat(this.walkTokens(genericToken.tokens, callback));\n                    }\n                }\n            }\n        }\n        return values;\n    }\n    use(...args) {\n        const extensions = this.defaults.extensions || { renderers: {}, childTokens: {} };\n        args.forEach((pack) => {\n            // copy options to new object\n            const opts = { ...pack };\n            // set async to true if it was set to true before\n            opts.async = this.defaults.async || opts.async || false;\n            // ==-- Parse \"addon\" extensions --== //\n            if (pack.extensions) {\n                pack.extensions.forEach((ext) => {\n                    if (!ext.name) {\n                        throw new Error('extension name required');\n                    }\n                    if ('renderer' in ext) { // Renderer extensions\n                        const prevRenderer = extensions.renderers[ext.name];\n                        if (prevRenderer) {\n                            // Replace extension with func to run new extension but fall back if false\n                            extensions.renderers[ext.name] = function (...args) {\n                                let ret = ext.renderer.apply(this, args);\n                                if (ret === false) {\n                                    ret = prevRenderer.apply(this, args);\n                                }\n                                return ret;\n                            };\n                        }\n                        else {\n                            extensions.renderers[ext.name] = ext.renderer;\n                        }\n                    }\n                    if ('tokenizer' in ext) { // Tokenizer Extensions\n                        if (!ext.level || (ext.level !== 'block' && ext.level !== 'inline')) {\n                            throw new Error(\"extension level must be 'block' or 'inline'\");\n                        }\n                        const extLevel = extensions[ext.level];\n                        if (extLevel) {\n                            extLevel.unshift(ext.tokenizer);\n                        }\n                        else {\n                            extensions[ext.level] = [ext.tokenizer];\n                        }\n                        if (ext.start) { // Function to check for start of token\n                            if (ext.level === 'block') {\n                                if (extensions.startBlock) {\n                                    extensions.startBlock.push(ext.start);\n                                }\n                                else {\n                                    extensions.startBlock = [ext.start];\n                                }\n                            }\n                            else if (ext.level === 'inline') {\n                                if (extensions.startInline) {\n                                    extensions.startInline.push(ext.start);\n                                }\n                                else {\n                                    extensions.startInline = [ext.start];\n                                }\n                            }\n                        }\n                    }\n                    if ('childTokens' in ext && ext.childTokens) { // Child tokens to be visited by walkTokens\n                        extensions.childTokens[ext.name] = ext.childTokens;\n                    }\n                });\n                opts.extensions = extensions;\n            }\n            // ==-- Parse \"overwrite\" extensions --== //\n            if (pack.renderer) {\n                const renderer = this.defaults.renderer || new _Renderer(this.defaults);\n                for (const prop in pack.renderer) {\n                    if (!(prop in renderer)) {\n                        throw new Error(`renderer '${prop}' does not exist`);\n                    }\n                    if (prop === 'options') {\n                        // ignore options property\n                        continue;\n                    }\n                    const rendererProp = prop;\n                    const rendererFunc = pack.renderer[rendererProp];\n                    const prevRenderer = renderer[rendererProp];\n                    // Replace renderer with func to run extension, but fall back if false\n                    renderer[rendererProp] = (...args) => {\n                        let ret = rendererFunc.apply(renderer, args);\n                        if (ret === false) {\n                            ret = prevRenderer.apply(renderer, args);\n                        }\n                        return ret || '';\n                    };\n                }\n                opts.renderer = renderer;\n            }\n            if (pack.tokenizer) {\n                const tokenizer = this.defaults.tokenizer || new _Tokenizer(this.defaults);\n                for (const prop in pack.tokenizer) {\n                    if (!(prop in tokenizer)) {\n                        throw new Error(`tokenizer '${prop}' does not exist`);\n                    }\n                    if (['options', 'rules', 'lexer'].includes(prop)) {\n                        // ignore options, rules, and lexer properties\n                        continue;\n                    }\n                    const tokenizerProp = prop;\n                    const tokenizerFunc = pack.tokenizer[tokenizerProp];\n                    const prevTokenizer = tokenizer[tokenizerProp];\n                    // Replace tokenizer with func to run extension, but fall back if false\n                    // @ts-expect-error cannot type tokenizer function dynamically\n                    tokenizer[tokenizerProp] = (...args) => {\n                        let ret = tokenizerFunc.apply(tokenizer, args);\n                        if (ret === false) {\n                            ret = prevTokenizer.apply(tokenizer, args);\n                        }\n                        return ret;\n                    };\n                }\n                opts.tokenizer = tokenizer;\n            }\n            // ==-- Parse Hooks extensions --== //\n            if (pack.hooks) {\n                const hooks = this.defaults.hooks || new _Hooks();\n                for (const prop in pack.hooks) {\n                    if (!(prop in hooks)) {\n                        throw new Error(`hook '${prop}' does not exist`);\n                    }\n                    if (prop === 'options') {\n                        // ignore options property\n                        continue;\n                    }\n                    const hooksProp = prop;\n                    const hooksFunc = pack.hooks[hooksProp];\n                    const prevHook = hooks[hooksProp];\n                    if (_Hooks.passThroughHooks.has(prop)) {\n                        // @ts-expect-error cannot type hook function dynamically\n                        hooks[hooksProp] = (arg) => {\n                            if (this.defaults.async) {\n                                return Promise.resolve(hooksFunc.call(hooks, arg)).then(ret => {\n                                    return prevHook.call(hooks, ret);\n                                });\n                            }\n                            const ret = hooksFunc.call(hooks, arg);\n                            return prevHook.call(hooks, ret);\n                        };\n                    }\n                    else {\n                        // @ts-expect-error cannot type hook function dynamically\n                        hooks[hooksProp] = (...args) => {\n                            let ret = hooksFunc.apply(hooks, args);\n                            if (ret === false) {\n                                ret = prevHook.apply(hooks, args);\n                            }\n                            return ret;\n                        };\n                    }\n                }\n                opts.hooks = hooks;\n            }\n            // ==-- Parse WalkTokens extensions --== //\n            if (pack.walkTokens) {\n                const walkTokens = this.defaults.walkTokens;\n                const packWalktokens = pack.walkTokens;\n                opts.walkTokens = function (token) {\n                    let values = [];\n                    values.push(packWalktokens.call(this, token));\n                    if (walkTokens) {\n                        values = values.concat(walkTokens.call(this, token));\n                    }\n                    return values;\n                };\n            }\n            this.defaults = { ...this.defaults, ...opts };\n        });\n        return this;\n    }\n    setOptions(opt) {\n        this.defaults = { ...this.defaults, ...opt };\n        return this;\n    }\n    lexer(src, options) {\n        return _Lexer.lex(src, options ?? this.defaults);\n    }\n    parser(tokens, options) {\n        return _Parser.parse(tokens, options ?? this.defaults);\n    }\n    #parseMarkdown(lexer, parser) {\n        return (src, options) => {\n            const origOpt = { ...options };\n            const opt = { ...this.defaults, ...origOpt };\n            // Show warning if an extension set async to true but the parse was called with async: false\n            if (this.defaults.async === true && origOpt.async === false) {\n                if (!opt.silent) {\n                    console.warn('marked(): The async option was set to true by an extension. The async: false option sent to parse will be ignored.');\n                }\n                opt.async = true;\n            }\n            const throwError = this.#onError(!!opt.silent, !!opt.async);\n            // throw error in case of non string input\n            if (typeof src === 'undefined' || src === null) {\n                return throwError(new Error('marked(): input parameter is undefined or null'));\n            }\n            if (typeof src !== 'string') {\n                return throwError(new Error('marked(): input parameter is of type '\n                    + Object.prototype.toString.call(src) + ', string expected'));\n            }\n            if (opt.hooks) {\n                opt.hooks.options = opt;\n            }\n            if (opt.async) {\n                return Promise.resolve(opt.hooks ? opt.hooks.preprocess(src) : src)\n                    .then(src => lexer(src, opt))\n                    .then(tokens => opt.hooks ? opt.hooks.processAllTokens(tokens) : tokens)\n                    .then(tokens => opt.walkTokens ? Promise.all(this.walkTokens(tokens, opt.walkTokens)).then(() => tokens) : tokens)\n                    .then(tokens => parser(tokens, opt))\n                    .then(html => opt.hooks ? opt.hooks.postprocess(html) : html)\n                    .catch(throwError);\n            }\n            try {\n                if (opt.hooks) {\n                    src = opt.hooks.preprocess(src);\n                }\n                let tokens = lexer(src, opt);\n                if (opt.hooks) {\n                    tokens = opt.hooks.processAllTokens(tokens);\n                }\n                if (opt.walkTokens) {\n                    this.walkTokens(tokens, opt.walkTokens);\n                }\n                let html = parser(tokens, opt);\n                if (opt.hooks) {\n                    html = opt.hooks.postprocess(html);\n                }\n                return html;\n            }\n            catch (e) {\n                return throwError(e);\n            }\n        };\n    }\n    #onError(silent, async) {\n        return (e) => {\n            e.message += '\\nPlease report this to https://github.com/markedjs/marked.';\n            if (silent) {\n                const msg = '<p>An error occurred:</p><pre>'\n                    + escape$1(e.message + '', true)\n                    + '</pre>';\n                if (async) {\n                    return Promise.resolve(msg);\n                }\n                return msg;\n            }\n            if (async) {\n                return Promise.reject(e);\n            }\n            throw e;\n        };\n    }\n}\n\nconst markedInstance = new Marked();\nfunction marked(src, opt) {\n    return markedInstance.parse(src, opt);\n}\n/**\n * Sets the default options.\n *\n * @param options Hash of options\n */\nmarked.options =\n    marked.setOptions = function (options) {\n        markedInstance.setOptions(options);\n        marked.defaults = markedInstance.defaults;\n        changeDefaults(marked.defaults);\n        return marked;\n    };\n/**\n * Gets the original marked default options.\n */\nmarked.getDefaults = _getDefaults;\nmarked.defaults = _defaults;\n/**\n * Use Extension\n */\nmarked.use = function (...args) {\n    markedInstance.use(...args);\n    marked.defaults = markedInstance.defaults;\n    changeDefaults(marked.defaults);\n    return marked;\n};\n/**\n * Run callback for every token\n */\nmarked.walkTokens = function (tokens, callback) {\n    return markedInstance.walkTokens(tokens, callback);\n};\n/**\n * Compiles markdown to HTML without enclosing `p` tag.\n *\n * @param src String of markdown source to be compiled\n * @param options Hash of options\n * @return String of compiled HTML\n */\nmarked.parseInline = markedInstance.parseInline;\n/**\n * Expose\n */\nmarked.Parser = _Parser;\nmarked.parser = _Parser.parse;\nmarked.Renderer = _Renderer;\nmarked.TextRenderer = _TextRenderer;\nmarked.Lexer = _Lexer;\nmarked.lexer = _Lexer.lex;\nmarked.Tokenizer = _Tokenizer;\nmarked.Hooks = _Hooks;\nmarked.parse = marked;\nconst options = marked.options;\nconst setOptions = marked.setOptions;\nconst use = marked.use;\nconst walkTokens = marked.walkTokens;\nconst parseInline = marked.parseInline;\nconst parse = marked;\nconst parser = _Parser.parse;\nconst lexer = _Lexer.lex;\n\nexport { _Hooks as Hooks, _Lexer as Lexer, Marked, _Parser as Parser, _Renderer as Renderer, _TextRenderer as TextRenderer, _Tokenizer as Tokenizer, _defaults as defaults, _getDefaults as getDefaults, lexer, marked, options, parse, parseInline, parser, setOptions, use, walkTokens };\n//# sourceMappingURL=marked.esm.js.map\n","import angular from \"angular\";\r\nimport { marked } from \"marked\";\r\nimport { Translations } from \"@salaxy/core\";\r\n\r\n/**\r\n * Directive for binding html for the element.\r\n * The attribute sxy-html should contain the translation key for the html content.\r\n * This directive should be used instead of the AngularJs ng-bind-html element.\r\n * Interpolation parameters for translation can be given using params -attribute.\r\n * @example\r\n * ```html\r\n * <p class=\"lead\" sxy-html=\"SALAXY.NG1.UserInfoComponent.description.html\" ></p>\r\n * ```\r\n */\r\nexport class HtmlDirective implements angular.IDirective {\r\n\r\n    /**\r\n     * Factory method for the directive creation.\r\n     * @ignore\r\n     */\r\n    public static sxyHtml(): any {\r\n        const factory = ($sce: angular.ISCEService) => new HtmlDirective($sce);\r\n        factory.$inject = [\"$sce\"];\r\n        return factory;\r\n    }\r\n\r\n    /**\r\n     * Directive restrictions.\r\n     * @ignore\r\n     */\r\n    public restrict = \"A\";\r\n\r\n   /**\r\n    * Creates a new instance of the directive.\r\n    */\r\n    constructor(private $sce: angular.ISCEService) {\r\n    }\r\n\r\n   /**\r\n    * Compile function for the directive.\r\n    * @ignore\r\n    */\r\n    public compile(cElement: any, cAttr: any): any { // eslint-disable-line @typescript-eslint/no-unused-vars\r\n      return  (scope: any, element: any, attr: any) => {\r\n\r\n        const endsWith = (str1: string, str2: string) => {\r\n          return str1.substring(str1.length - str2.length, str1.length) === str2;\r\n        };\r\n\r\n        const params = () => scope.$eval(attr.params);\r\n        const sxyHtml = () => attr.sxyHtml;\r\n\r\n        scope.$watch( () => sxyHtml() + JSON.stringify(params()), () => {\r\n          let html = Translations.get(sxyHtml(), params());\r\n          if (endsWith(sxyHtml(), \".md\")) {\r\n            html = marked(html) as string;\r\n          }\r\n          element.html(this.$sce.getTrustedHtml(html));\r\n        });\r\n      };\r\n    }\r\n}\r\n","import angular from \"angular\";\r\nimport { Translations } from \"@salaxy/core\";\r\n\r\n/**\r\n * Directive for binding text for the element.\r\n * The attribute sxy-text should contain the translation key for the text content.\r\n * This directive should be used to replace AngularJS expression and translation pipe filter.\r\n * Small additions to the beginning and end can be added with pre and ps attributes.\r\n * Interpolation parameters for translation can be given using params -attribute.\r\n * @example\r\n * ```html\r\n * <div sxy-text=\"SALAXY.NG1.UserInfoComponent.authType\" ps=\":\" pre=\"HUOM: \"></div>\r\n * ```\r\n */\r\nexport class TextDirective implements angular.IDirective {\r\n\r\n  /**\r\n   * Factory method for the directive creation.\r\n   * @ignore\r\n   */\r\n  public static sxyText(): any {\r\n    const factory = () => new TextDirective();\r\n    return factory;\r\n  }\r\n\r\n  /**\r\n   * Directive restrictions.\r\n   * @ignore\r\n   */\r\n  public restrict = \"A\";\r\n\r\n\r\n  /**\r\n   * Compile function for the directive.\r\n   * @ignore\r\n   */\r\n  public compile(cElement: any, cAttr: any): any { // eslint-disable-line @typescript-eslint/no-unused-vars\r\n    return (scope: any, element: any, attr: any) => {\r\n      // Translation which preserver whitespace\r\n      const wsTranslate = (key: string, interpolateParams?: any) => {\r\n        const text = Translations.get(key, interpolateParams);\r\n        if (key.trim() ===  text) {\r\n          return key;\r\n        }\r\n        return text;\r\n      };\r\n\r\n      // Returns the untrimmed attribute value (as opposite to attr)\r\n      const getUntrimmedAttributeValue = (name: string) => {\r\n        return (element[0].attributes[name] || {value: \"\"} ).value;\r\n      };\r\n\r\n      const params = () => scope.$eval(attr.params);\r\n\r\n      scope.$watch(() => getUntrimmedAttributeValue(\"pre\") + getUntrimmedAttributeValue(\"sxy-text\") + JSON.stringify(params()) + getUntrimmedAttributeValue(\"ps\"), () => {\r\n        element.text(wsTranslate(getUntrimmedAttributeValue(\"pre\")) + wsTranslate( getUntrimmedAttributeValue(\"sxy-text\"), params()) + wsTranslate(getUntrimmedAttributeValue(\"ps\")));\r\n      });\r\n    };\r\n  }\r\n}\r\n","import {\r\n  AppendNodeDirective,\r\n  Bs5Tooltip,\r\n  Bs5Popover,\r\n  DatepickerInputValidationDirective,\r\n  EnumParserFunctions,\r\n  HtmlDirective,\r\n  IfRoleDirective,\r\n  IfSitemapDirective,\r\n  LoaderDirective,\r\n  OrderbyDirective,\r\n  TextDirective,\r\n  ValidatorFunctions,\r\n} from \".\";\r\n\r\n/**\r\n * Provides methods for registering the Directives to module\r\n * (and other related metadata in the future).\r\n */\r\nexport class DirectivesRegistration {\r\n\r\n  /** Gets the directives for Module registration. */\r\n  public static getDirectives() {\r\n    return {\r\n      // TODO: Remove depency to directives starting with \"salaxy-\" => \"sxy-\".\r\n      salaxyIfRole: IfRoleDirective.sxyIfRole(),\r\n      // TODO: Go through: are these needed? If so => \"sxy-\"\r\n      salaxyAppendNode: AppendNodeDirective.salaxyAppendNode(), // Useful? Used in tabs, are tabs really used?\r\n      salaxyDatepickerInputValidation: DatepickerInputValidationDirective.salaxyDatepickerInputValidation(), // Could this be in ValidatorFunctions or is there special functionality? This is used only in date picker.\r\n      // TODO: Move as <salaxy-loader> component instead of directive (removes unnecessary HTML from the views).\r\n      //       Also evaluate relation to salaxy-spinner: There should be only one if possible with different layout options.\r\n      salaxyLoader: LoaderDirective.salaxyLoader(),\r\n\r\n      // All new directives should start with \"sxy-\"\r\n      sxyBs5Tooltip: Bs5Tooltip.salaxyBs5Tooltip(),\r\n      sxyBs5Popover: Bs5Popover.salaxyBs5Popover(),\r\n      sxyIfRole: IfRoleDirective.sxyIfRole(),\r\n      sxyIfSitemap: IfSitemapDirective.sxyIfSitemap(),\r\n      sxyOrderby: OrderbyDirective.sxyOrderby(),\r\n      // Validator functions\r\n      sxyTaxPercent: ValidatorFunctions.sxyTaxPercent(),\r\n      sxyCurrency: ValidatorFunctions.sxyCurrency(),\r\n      sxyIban: ValidatorFunctions.sxyIban(),\r\n      sxyEmail: ValidatorFunctions.sxyEmail(),\r\n      sxyEnumAsBoolean: EnumParserFunctions.sxyEnumAsBoolean(),\r\n      sxyMobilePhone: ValidatorFunctions.sxyMobilePhone(),\r\n      sxyExcludeUnknowns: ValidatorFunctions.sxyExcludeUnknowns(),\r\n      sxyBankReferenceFi: ValidatorFunctions.sxyBankReferenceFi(),\r\n      sxyPersonalIdFi: ValidatorFunctions.sxyPersonalIdFi(),\r\n      sxyCompanyIdFi: ValidatorFunctions.sxyCompanyIdFi(),\r\n      sxyOfficialIdFi: ValidatorFunctions.sxyOfficialIdFi(),\r\n      sxyPostalCodeFi: ValidatorFunctions.sxyPostalCodeFi(),\r\n      sxyNumber: ValidatorFunctions.sxyNumber(),\r\n      sxyInteger: ValidatorFunctions.sxyInteger(),\r\n      sxyMax: ValidatorFunctions.sxyMax(),\r\n      sxyMin: ValidatorFunctions.sxyMin(),\r\n      sxyMultipleOf: ValidatorFunctions.sxyMultipleOf(),\r\n      sxyPensionContractNumber: ValidatorFunctions.sxyPensionContractNumber(),\r\n      sxyHtml: HtmlDirective.sxyHtml(),\r\n      sxyText: TextDirective.sxyText(),\r\n    };\r\n  }\r\n}\r\n","\r\nimport { marked } from \"marked\";\r\n\r\nimport {\r\n  ApiListItem,\r\n  CalcInfo,\r\n  CalcRowsLogic,\r\n  DatelyObject,\r\n  DateRange,\r\n  Dates,\r\n  DateTimes,\r\n  EmploymentData,\r\n  EnumerationsLogic,\r\n  Iban,\r\n  Numeric,\r\n  Occupations,\r\n  Role,\r\n  SitemapNode,\r\n  SystemRole,\r\n  Translations,\r\n  Unit,\r\n  WorkflowEvent\r\n} from \"@salaxy/core\";\r\n\r\nimport { NaviService, SessionService } from \"../services\";\r\nimport { SitemapHelper } from \"../helpers\";\r\n\r\n/**\r\n * Contains the simple filter functions where implementation\r\n * is in some other class (typically @salaxy/core) and thus the filter implementation is very small.\r\n * This should typically the case, but some filters may contain a lot of NG1 specific\r\n * implementation (e.g. SalaxyTranslateFilter) and/or dependency injection and thus deserve their own class.\r\n */\r\nexport class FilterFunctions {\r\n\r\n  /**\r\n   * Formats a Workflow message string from index.\r\n   * List of allowed message types can be given as a comma seprated list.\r\n   *\r\n   * Parameters of the filter are:\r\n   *\r\n   * - messageString: Workflow message\r\n   * - types: Allowed message types.\r\n   */\r\n  public static sxyWorkflowMessage = [\"$sce\", ($sce: angular.ISCEService) => {\r\n    return (messageString: string, types: string) => {\r\n      if (!messageString) {\r\n        return $sce.getTrustedHtml(\"<span></span>\");\r\n      }\r\n      const messageTypes = (types || \"\").split(\",\");\r\n      const uiClassMarker = messageString.indexOf(\"(Ui\");\r\n      const uiClassEndMarker = messageString.indexOf(\"):\", uiClassMarker + 3);\r\n      const type = (messageString.substring(0, uiClassMarker - 1) || \"UnknownEvent\");\r\n\r\n      if (messageTypes.length > 0) {\r\n        if (!messageTypes.some((x) => x.trim() === type)) {\r\n          return $sce.getTrustedHtml(\"<span></span>\");\r\n        }\r\n      }\r\n\r\n      if (type.startsWith(\"SystemMessage\")) {\r\n        const wfEvent = FilterFunctions.toWorkflowEvent(messageString);\r\n        const time = wfEvent.time ? Dates.format(wfEvent.time, \"D.M.YYYY HH:mm\") : \"\";\r\n        let shortMessage = type.substring(13);\r\n        shortMessage = shortMessage.substring(0, 1).toLowerCase() + shortMessage.substring(1);\r\n        shortMessage = Translations.get(\"SALAXY.ENUM.SystemMessage.\" + shortMessage + \".label\" ) as string;\r\n        const fullMessage = (wfEvent.message + \" \" + time).trim();\r\n        return $sce.getTrustedHtml(`<span class=\"badge bg-${wfEvent.ui}\" title=\"${fullMessage}\">${shortMessage}</span>`);\r\n      }\r\n      else {\r\n\r\n        const uiClass = messageString.substring(uiClassMarker + 3, uiClassEndMarker).toLowerCase();\r\n        let fullMessage = messageString.substring(uiClassEndMarker + 3);\r\n        const dtReg = /([0-9]{4})-(0[1-9]|1[0-2])-(0[1-9]|[1-2][0-9]|3[0-1]) (2[0-3]|[01][0-9]):([0-5][0-9])/g;\r\n        fullMessage = fullMessage.replace(dtReg, (match: string, year, month, day, hours, minutes) => {\r\n          const d = Date.UTC(parseInt(year, 10), parseInt(month, 10) - 1, parseInt(day, 10), parseInt(hours, 10), parseInt(minutes, 10));\r\n          return Dates.format(d, \"D.M.YYYY HH:mm\");\r\n        });\r\n        const shortMessage = fullMessage.substring(0, fullMessage.lastIndexOf(\"(\"));\r\n        return $sce.getTrustedHtml(`<span class=\"badge bg-${uiClass}\" title=\"${fullMessage}\">${shortMessage}</span>`);\r\n      }\r\n    };\r\n  }];\r\n\r\n  private static toWorkflowEvent(messageString: string): WorkflowEvent {\r\n    if (!messageString) {\r\n      return {};\r\n    }\r\n    // [type] (Ui[ui]):[message] ([User] at [yyyy-MM-dd HH:mm] to [assignedTo] id [id])\r\n    const uiStartX = messageString.indexOf(\"(Ui\");\r\n    const uiEndX = messageString.indexOf(\"):\", uiStartX + 3);\r\n    const type = (messageString.substring(0, uiStartX - 1) || \"\");\r\n    const ui = messageString.substring(uiStartX + 3, uiEndX).toLowerCase();\r\n    let rest = messageString.substring(uiEndX + 3);\r\n    const messageEndX = rest.lastIndexOf(\"(\");\r\n    const message = rest.substring(0, messageEndX).trim();\r\n    rest = rest.substring(messageEndX + 1); // Remove (\r\n    rest = rest.substring(0, rest.length - 1); // Remove )\r\n    let id = \"\";\r\n    const idx = rest.lastIndexOf(\" id \");\r\n    if (idx >= 0) {\r\n      id = rest.substring(idx + 4);\r\n      rest = rest.substring(0, idx);\r\n    }\r\n    let assignedTo = \"\";\r\n    const aIdx = rest.lastIndexOf(\" to \");\r\n    if (aIdx >= 0) {\r\n      assignedTo = rest.substring(aIdx + 4);\r\n      rest = rest.substring(0, aIdx);\r\n    }\r\n    let time = \"\";\r\n    const tIdx = rest.lastIndexOf(\" at \");\r\n    if (tIdx >= 0) {\r\n      time = rest.substring(tIdx + 4);\r\n      rest = rest.substring(0, tIdx);\r\n      // time\r\n      time = time.replace(\" \", \"T\") + \"Z\";\r\n    }\r\n    const user = rest;\r\n    return {\r\n      id,\r\n      type,\r\n      ui,\r\n      user,\r\n      assignedTo,\r\n      message,\r\n      time,\r\n    } as WorkflowEvent;\r\n  }\r\n\r\n  public static sxyShow = [\"NaviService\", (naviService: NaviService) => {\r\n    return (sectionToCheck: string, sitemapPath: string): boolean => {\r\n      if (!sectionToCheck || !sitemapPath) {\r\n        return true;\r\n      }\r\n      const splitPaths = sitemapPath.split(\".\");\r\n      let sitemap: SitemapNode[] = naviService.getSitemap();\r\n      const companySite = sitemap.find(node => node.id === \"company-site\");\r\n      if (companySite) {\r\n        sitemap = [companySite];\r\n      }\r\n      let resultSitemapNode: SitemapNode;\r\n      if (splitPaths.length >= 3) {\r\n        let currentSection: SitemapNode[] = sitemap;\r\n        for (const path of splitPaths) {\r\n          const section = SitemapHelper.getSection(currentSection, path);\r\n          if (path === splitPaths[splitPaths.length - 1]) {\r\n            resultSitemapNode = section;\r\n          } else {\r\n            currentSection = section.children;\r\n          }\r\n        }\r\n      } else if (splitPaths.length === 2) {\r\n        resultSitemapNode = SitemapHelper.getNode(sitemap, splitPaths[0], splitPaths[1]);\r\n      } else {\r\n        resultSitemapNode = SitemapHelper.getSection(sitemap, splitPaths[0]);\r\n      }\r\n      if (resultSitemapNode) {\r\n        return !(resultSitemapNode?.hidden ?? []).includes(sectionToCheck);\r\n      }\r\n      return true;\r\n    };\r\n  }];\r\n\r\n  /**\r\n   * Translate filter with key and interpolation parameter.\r\n   * Converts content with translationId ending with '.html', to safe html.\r\n   * Converts content with translationId ending with '.md', first to html and then to safe html.\r\n   * If the text contains a variable placeholder like: 'Hello {{name}}!', it will be replaced by given parameter.\r\n   *\r\n   * Parameters of the filter are:\r\n   *\r\n   * - translationId: Translation key\r\n   * - interpolateParams: Interpolation parameters applied if text had interpolation.\r\n   * @example\r\n   * ```html\r\n   * <p sxy-text=\"SALAXY.NG1.test1\"></p>\r\n   * <p>{{ 'SALAXY.NG1.hello' | sxyTranslate: { name: 'John'} }}</p>\r\n   * ```\r\n   */\r\n  public static sxyTranslate = [\"$sce\", ($sce: angular.ISCEService) => {\r\n    return (translationId: string, interpolateParams: any): string => {\r\n      const endsWith = (str1: string, str2: string) => {\r\n        return str1.substring(str1.length - str2.length, str1.length) === str2;\r\n      };\r\n      const str = Translations.get(translationId, interpolateParams) as string;\r\n      if (translationId) {\r\n        if (endsWith(translationId, \".html\")) {\r\n          return $sce.getTrustedHtml(str);\r\n        } else if (endsWith(translationId, \".md\")) {\r\n          return $sce.getTrustedHtml(marked(str));\r\n        }\r\n      }\r\n      return str;\r\n    };\r\n  }];\r\n\r\n  /**\r\n   * Formats a string using markdown and returns trusted HTML.\r\n   * Parameters of the filter are:\r\n   * - markdown: Markdown input to format as HTML.\r\n   * @example\r\n   * ```html\r\n   * <div ng-bind-html=\"$ctrl.current.example | sxyMarkdown\"></div>\r\n   * ```\r\n   */\r\n  public static sxyMarkdown = [\"$sce\", ($sce: angular.ISCEService) => {\r\n    return (markdown: string): string => {\r\n      if (markdown == null) {\r\n        return null;\r\n      }\r\n      return $sce.getTrustedHtml(marked(markdown));\r\n    };\r\n  }];\r\n\r\n  /**\r\n   * IsInRole filter returns true if the user is in any of the given roles.\r\n   * The input may be Array of roles or comma separated string containing role names.\r\n   * This can be used instead of sxy-if-role directive when the component requires transcusion\r\n   * and also in constructing other logic in expressions.\r\n   *\r\n   * Parameters of the filter are:\r\n   *\r\n   * - commaSeparatedRolesList: Comma separated list of roles\r\n   *\r\n   * NOTE: Because the actual value is constant, the filter is not rerun after session check).\r\n   * Because of this, the method should only be used after the session has been checked.\r\n   * Typically, by making sure, the filters are inside `sxy-if-role=\"$ctrl.current\"`, `sxy-if-role=\"auth\"` or `sxy-if-role=\"!unknown\"`.\r\n   * @example\r\n   * ```html\r\n   * <div sxy-if-role=\"auth\">\r\n   *   <uib-tab index=\"'holidays'\" heading=\"Lomat\" ng-if=\"'company' | sxyIsInRole\">\r\n   *   <p>{{ 'company' | sxyIsInRole ? 'Company text' : 'Default text' }}</p>\r\n   * </div>\r\n   * ```\r\n   */\r\n  public static sxyIsInRole = [\"SessionService\", (sessionService: SessionService) => {\r\n    return (commaSeparatedRolesList: (SystemRole | Role | string)[] | string): boolean => {\r\n      return sessionService.isInSomeRole(commaSeparatedRolesList);\r\n    };\r\n  }];\r\n\r\n  /**\r\n   * IsVisibility filter returns true/false when evaluating the logical visibility of a sitemap,\r\n   * as used in the views an UI logic, i.e.:\r\n   *\r\n   * - hidden: Node is null or visibility is Hidden, HiddenReadOnly or Disabled.\r\n   * - readOnly: Node is null or visibility is ReadOnly, HiddenReadOnly or Disabled.\r\n   * - disabled: Visibility is Disabled.\r\n   * - Visible: Visibility is Visible or null, node is not null.\r\n   * - isFullWidth: The node has an isFullWidth boolean flag set to true.\r\n   *\r\n   * This can be used instead of sxy-if-sitemap directive when the component requires transcusion\r\n   * and also in constructing other logic in expressions.\r\n   *\r\n   * Parameters of the filter are:\r\n   *\r\n   * - visibilityToEvaluate: The visibility value to evaluate for.\r\n   *\r\n   * NOTE: Because the actual value is constant, the filter is not rerun after session check).\r\n   * Because of this, the method should only be used after the session has been checked.\r\n   * Typically, by making sure, the filters are inside `sxy-if-role=\"$ctrl.current\"`, `sxy-if-role=\"auth\"` or `sxy-if-role=\"!unknown\"`.\r\n   * @example\r\n   * ```html\r\n   * <div sxy-if-role=\"auth\">\r\n   *   <uib-tab index=\"'holidaysReadOnly'\" heading=\"Lomat (Read-only)\" ng-if=\"'readOnly' | sxyIsVisibility\">\r\n   *   <p>{{ 'readOnly' | sxyIsVisibility ? 'Read-only text' : 'Default text' }}</p>\r\n   * </div>\r\n   * ```\r\n   */\r\n  public static sxyIsVisibility = [\"NaviService\", (naviService: NaviService) => {\r\n    return (visibilityToEvaluate: string): boolean => {\r\n      // TODO: For some reason Rollup fails in build if type is set to SitemapVisibility (from core).\r\n      return naviService.current.getVisibility(visibilityToEvaluate as any);\r\n    };\r\n  }];\r\n\r\n  /**\r\n   * Returns the label for an enumeration.\r\n   *\r\n   * Parameters of the filter are:\r\n   *\r\n   * - input: Enumeration in format \"[EnumType].[EnumName]\". First letter is case-insensitive so you can use lowerCamelCase or UpperCamelCase.\r\n   * - defaultValue: Optional default value when language version is not available.\r\n   * Special values \"name\" and \"#name\", may be used to return the enum member name either with hash or without it.\r\n   * Default is \"#name\", which returns \"#[MemberName]\" if the translation is not found.\r\n   * @example\r\n   * ```html\r\n   * <p>{{ 'CalculationStatus.Draft' | sxyEnum }} - The enum full name</p>\r\n   * <p>{{ 'CalculationStatus.paymentSucceeded' | sxyEnum }} - you may also use JSON value where first letter is lower-case.</p>\r\n   * <p>{{ 'CalculationStatus.' + calc.status | sxyEnum }} - ...which makes it easy to use with data.</p>\r\n   * ```\r\n   */\r\n  public static sxyEnum() {\r\n    return (input: string, defaultValue: null | string | \"name\" | \"#name\" = \"#name\") => {\r\n      const splitValues = (input || \"\").split(\".\");\r\n      if (splitValues.length !== 2) {\r\n        return \"#ERR: sxyEnum\";\r\n      }\r\n      if (!splitValues[1]) {\r\n        return null;\r\n      }\r\n      return EnumerationsLogic.getEnumLabel(splitValues[0], splitValues[1], defaultValue);\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Returns the description for an enumeration value in current language.\r\n   *\r\n   * Parameters of the filter are:\r\n   *\r\n   * - input: Enumeration in format \"[EnumType].[EnumName]\". First letter is case-insensitive so you can use lowerCamelCase or UpperCamelCase.\r\n   * - defaultValue: Optional default value when language version is not available. Default is null\r\n   * Special values \"name\" and \"#name\", may be used to return the enum member name either with hash or without it.\r\n   * @example\r\n   * ```html\r\n   * <p>{{ 'CalculationStatus.Draft' | sxyEnumDescr }} - The enum full name</p>\r\n   * <p>{{ 'CalculationStatus.paymentSucceeded' | sxyEnumDescr }} - you may also use JSON value where first letter is lower-case.</p>\r\n   * <p>{{ 'CalculationStatus.' + calc.status | sxyEnumDescr }} - ...which makes it easy to use with data.</p>\r\n   * ```\r\n   */\r\n  public static sxyEnumDescr() {\r\n    return (input: string, defaultValue?: null | string | \"name\" | \"#name\") => {\r\n      const splitValues = (input || \"\").split(\".\");\r\n      if (splitValues.length !== 2) {\r\n        return \"#ERR: sxyEnumDescr\";\r\n      }\r\n      if (!splitValues[1]) {\r\n        return null;\r\n      }\r\n      return EnumerationsLogic.getEnumDescr(splitValues[0], splitValues[1], defaultValue);\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Formats the date with Dates.getFormattedDate in core project.\r\n   * If the input is not recognized as date or if it is empty or less than year 1900, shows a dash.\r\n   *\r\n   * Parameters of the filter are:\r\n   *\r\n   * - input: Input to format\r\n   * @example\r\n   * ```html\r\n   * <p>{{ calc.workflow.paidAt | sxyDate }}</p>\r\n   * ```\r\n   */\r\n  public static sxyDate() {\r\n    return (input: string) => {\r\n      const year = Dates.getYear(input);\r\n      if (!year || year < 1900) {\r\n        return \"-\";\r\n      }\r\n      return Dates.getFormattedDate(input);\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Formats a DateRange with Dates.getFormattedRange() in core project.\r\n   * If input is null, shows a dash.\r\n   * Also supports the ApiListItem (startAt, endAt), CalcInfo type in Calculation.info property (workStartDate and workEndDate) and EmploymentData (startDate and endDate)\r\n   *\r\n   * Parameters of the filter are:\r\n   *\r\n   * - input: Input to format\r\n   *\r\n   */\r\n  public static sxyDateRange() {\r\n    return (input: DateRange) => {\r\n      if (!input) {\r\n        return \"-\";\r\n      }\r\n      const info = input as CalcInfo;\r\n      if (info.workStartDate || info.workEndDate) {\r\n        return Dates.getFormattedRange(info.workStartDate, info.workEndDate);\r\n      }\r\n      const listItem = input as ApiListItem;\r\n      if (listItem.startAt || listItem.endAt) {\r\n        return Dates.getFormattedRange(listItem.startAt, listItem.endAt);\r\n      }\r\n      const employmentData = input as EmploymentData;\r\n      if (employmentData.startDate || employmentData.endDate) {\r\n        return Dates.getFormattedRange(employmentData.startDate, employmentData.endDate);\r\n      }\r\n      return Dates.getFormattedRange(input.start, input.end);\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Iban formatting filter.\r\n   *\r\n   * Parameters of the filter are:\r\n   *\r\n   * - input: Input text to format as IBAN.\r\n   *\r\n   */\r\n  public static sxyIban() {\r\n    return (input: string) => {\r\n      if (!input) {\r\n        return null;\r\n      }\r\n      return Iban.formatIban(input);\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Formats a number as count optionally taking into account the related unit\r\n   *\r\n   * Parameters of the filter are:\r\n   *\r\n   * - input: Input to format\r\n   * - unit: Unit that is used in formatting.\r\n   * - decimals: Number of decimals to show.\r\n   * - nullText: Text to show if the value is null / undefined. By default returns null, which can then be cought by another filter or logical or (\"||\").\r\n   * - zeroText: If specified, will use this text without the Unit formatting if the value is zero. By default zero is formatted as \"0 [unitText]\".\r\n   */\r\n  public static sxyCount() {\r\n    return (\r\n      input: number,\r\n      unit: Unit = null,\r\n      decimals: number = null,\r\n      nullText: string = null,\r\n      zeroText: string = null) => {\r\n      if (input == null) {\r\n        return nullText;\r\n      }\r\n      if (zeroText != null && input === 0) {\r\n        return zeroText;\r\n      }\r\n      const rounded = Numeric.round(input, decimals || 2);\r\n      switch (unit) {\r\n        case Unit.One:\r\n          return \"\";\r\n        case Unit.Period:\r\n          return rounded + Translations.get(\"SALAXY.NG1.FilterFunctions.sxyCount.period\" + (rounded === 1 ? \"\" : \"s\"));\r\n        case Unit.Percent:\r\n          return Numeric.round(input * 100, decimals || 2) + \"%\";\r\n        case Unit.Hours:\r\n        case Unit.Days:\r\n        case Unit.Weeks:\r\n        case Unit.Count:\r\n        case Unit.Kilometers:\r\n        case Unit.Undefined:\r\n        default:\r\n          return rounded + \" \" + (CalcRowsLogic.getUnitIndicator(unit) || \"\");\r\n      }\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Formats a datetime ISO string (or other DayJS-object compatible time)\r\n   * As time with texts \"Today\", \"Yesterday\", \"D.M. HH:mm\" for this year\r\n   * and \"D.M.YYYY\" for other years (if necessary, add option for adding time to previous years).\r\n   *\r\n   * Parameters of the filter are:\r\n   *\r\n   * - time: Input to format\r\n   *\r\n   */\r\n  public static sxyTime() {\r\n    // TODO: This is being rewritten in CalendarEventsCrudController. When ready, move to core and use the same function here.\r\n    return (time: string) => {\r\n      return DateTimes.format(time);\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Calls the Salaxy standard Dates.asDate to convert a DatelyObject to ISO date string (without time).\r\n   * ISO dates can then be used in comparison and equality.\r\n   * Also note that, DatelyObject can be constants like \"today\" | \"yesterday\" | \"tomorrow\". See documentation for details.\r\n   *\r\n   * Parameters of the filter are:\r\n   *\r\n   * - input: Input to format as DatelyObject\r\n   * - addWorkDays: If set, adds the number of workdays to the input.\r\n   * May also be zero (0) to return input if it is a workday or next workday if input is not a workday.\r\n   *\r\n   */\r\n  public static sxyAsDate() {\r\n    return (input: DatelyObject, addWorkDays: number) => {\r\n      if (addWorkDays != null) {\r\n        return Dates.addWorkdays(input, addWorkDays);\r\n      }\r\n      return Dates.asDate(input);\r\n    };\r\n  }\r\n  /**\r\n   * Formats a date/time range to an end-user friendly duration text.\r\n   * Input may be Duration as ISO duration string (e.g. P3Y6M4DT12H30M5S) or .Net timespan (e.g. '7.23:59:59.999').\r\n   */\r\n  public static sxyDuration() {\r\n    return (input: string) => {\r\n      return DateTimes.formatDuration(input);\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Converts the occupation to a language versioned string.\r\n   *\r\n   * Parameters of the filter are:\r\n   *\r\n   * - input: The occupation code as stored / returned from the API.\r\n   * - format: Default is just the label for the occupation. \"code-label\" is in format \"[code]: [label]`\r\n   *\r\n   */\r\n  public static sxyOccupation() {\r\n    return (input: string, format: \"default\" | \"code-label\") => {\r\n      const occupation = Occupations.getById(input);\r\n      if (!occupation) {\r\n        return Translations.get(\"SALAXY.NG1.FilterFunctions.sxyOccupation.occupationMissing\");\r\n      }\r\n      if (format === \"code-label\") {\r\n        return `${occupation.code}: ${occupation.label}`;\r\n      }\r\n      return occupation.label;\r\n    };\r\n  }\r\n\r\n  /**\r\n   * Formats a time (input) to an end-user friendly totaltime (12:34 or 12:34:56) text.\r\n   * Input may be Duration as ISO duration string (e.g. P3Y6M4DT12H30M5S) or .Net timespan (e.g. '7.23:59:59.999').\r\n   */\r\n  public static sxyTotalTime() {\r\n    return (input: number, format: \"minutes\" | \"seconds\") => {\r\n      const padTo2Digits = (num) => {\r\n        return num.toString().padStart(2, \"0\");\r\n      };\r\n      input = Numeric.isNumber(input) ? input : 0;\r\n      switch (format) {\r\n        case \"minutes\": {\r\n          const hours = Math.floor(input / 60);\r\n          const minutes = input % 60;\r\n          return `${padTo2Digits(hours)}:${padTo2Digits(minutes)}`;\r\n        }\r\n        case \"seconds\": {\r\n          const hours = Math.floor(input / 3600);\r\n          const minutes = Math.floor((input % 3600) / 60);\r\n          const seconds = input % 60;\r\n          return `${padTo2Digits(hours)}:${padTo2Digits(minutes)}:${padTo2Digits(seconds)}`;\r\n        }\r\n      }\r\n    };\r\n  }\r\n\r\n}\r\n","import { FilterFunctions } from \"./FilterFunctions\";\r\n\r\n/**\r\n * Provides the method for registering filters to the module.\r\n */\r\nexport class FiltersRegistration {\r\n\r\n  /** Gets the filters for Module registration. */\r\n  public static getFilters() {\r\n    /* eslint-disable @typescript-eslint/unbound-method */\r\n    return {\r\n      sxyAsDate: FilterFunctions.sxyAsDate,\r\n      sxyCount: FilterFunctions.sxyCount,\r\n      sxyDate: FilterFunctions.sxyDate,\r\n      sxyDateRange: FilterFunctions.sxyDateRange,\r\n      sxyDuration: FilterFunctions.sxyDuration,\r\n      sxyEnum: FilterFunctions.sxyEnum,\r\n      sxyEnumDescr: FilterFunctions.sxyEnumDescr,\r\n      sxyIban: FilterFunctions.sxyIban,\r\n      sxyMarkdown: FilterFunctions.sxyMarkdown,\r\n      sxyOccupation: FilterFunctions.sxyOccupation,\r\n      sxyTime: FilterFunctions.sxyTime,\r\n      sxyTranslate: FilterFunctions.sxyTranslate,\r\n      sxyIsInRole: FilterFunctions.sxyIsInRole,\r\n      sxyIsVisibility: FilterFunctions.sxyIsVisibility,\r\n      sxyWorkflowMessage: FilterFunctions.sxyWorkflowMessage,\r\n      sxyTotalTime: FilterFunctions.sxyTotalTime,\r\n      sxyShow: FilterFunctions.sxyShow,\r\n    };\r\n    /* eslint-enable @typescript-eslint/unbound-method */\r\n  }\r\n}\r\n","import angular from \"angular\";\r\n\r\n/**\r\n * Interceptor for monitoring $http-service calls.\r\n */\r\nexport class LoaderInterceptor {\r\n\r\n    /**\r\n     * Factory method for creating the interceptor.\r\n     */\r\n    public static factory() {\r\n      const factory = ($q: angular.IQService, $rootScope: angular.IRootScopeService) => {\r\n        if (LoaderInterceptor.instance == null) {\r\n          LoaderInterceptor.instance = new LoaderInterceptor($q, $rootScope);\r\n        }\r\n        return LoaderInterceptor.instance;\r\n      };\r\n      factory.$inject = [\"$q\", \"$rootScope\"];\r\n      return factory;\r\n  }\r\n\r\n    /**\r\n     * Singleton\r\n     */\r\n    private static instance: LoaderInterceptor;\r\n\r\n    private loadingCount = 0;\r\n\r\n    /**\r\n     * Constructor creating a new interceptor.\r\n     * @param  $q - $q service.\r\n     * @param  $rootScope - Angular root scope.\r\n     */\r\n    private constructor(private $q: angular.IQService, private $rootScope: angular.IRootScopeService) {\r\n    }\r\n\r\n    /**\r\n     * Intercepting method for request.\r\n     * @param config - $http request.\r\n     */\r\n    public request = (config: angular.IRequestConfig) => {\r\n        this.loadingCount++;\r\n        this.$rootScope.$broadcast(\"salaxy-loader-show\");\r\n        return config || this.$q.when(config);\r\n    };\r\n\r\n    /**\r\n     * Intercepting method for response.\r\n     * @param response - $http response.\r\n     */\r\n    public response = (response: angular.IHttpPromiseCallbackArg<any>) => {\r\n        if ((--this.loadingCount) === 0) {\r\n            this.$rootScope.$broadcast(\"salaxy-loader-hide\");\r\n        }\r\n        return response || this.$q.when(response);\r\n    };\r\n\r\n    /**\r\n     * Intercepting method for response error.\r\n     * @param rejection - $http error.\r\n     */\r\n    public responseError = (rejection: any) => {\r\n        if ((--this.loadingCount) === 0) {\r\n            this.$rootScope.$broadcast(\"salaxy-loader-hide\");\r\n        }\r\n        return this.$q.reject(rejection);\r\n    };\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Dates } from \"@salaxy/core\";\r\n\r\n/**\r\n * Interceptor for enabling non-cached views.\r\n * The interceptor adds a 'v'-query parameter to the template path.\r\n * The value of the v-parameter is a timestamp formatted by the given format.\r\n */\r\nexport class TemplateInterceptor {\r\n\r\n    /**\r\n     * Factory method for creating the interceptor.\r\n     * Interceptor for enabling non-cached views.\r\n     * The interceptor adds a 'v'-query parameter to the template path.\r\n     * The value of the v-parameter is a timestamp formatted by the given format.\r\n     * @param views - Regex for views folders (template paths), default is /views\\//\r\n     * @param format - DayJs format for the current time based timestamp. default is \"YYYYMMDDHH\"\r\n     */\r\n    public static factory(views = /views\\//, format = \"YYYYMMDDHH\") {\r\n      const factory = () => {\r\n        return new TemplateInterceptor(views, format);\r\n      };\r\n      factory.$inject = [];\r\n      return factory;\r\n  }\r\n\r\n    /**\r\n     * Constructor for creating a new interceptor.\r\n     */\r\n    private constructor(private views: RegExp, private format: string) {\r\n    }\r\n\r\n    /**\r\n     * Intercepting method for request.\r\n     * @param config - $http request.\r\n     */\r\n    public request = (config: angular.IRequestConfig) => {\r\n      if (config && config.url) {\r\n        if (this.views.test(config.url)) {\r\n          config.url = `${config.url}${config.url.indexOf(\"?\") < 0 ? \"?\" : \"&\" }v=${Dates.format(new Date(),this.format)}`;\r\n        }\r\n      }\r\n      return config;\r\n    };\r\n}\r\n","// Services from this project.\r\nimport {\r\n  AlertService,\r\n  AuthorizedAccountService,\r\n  CacheService,\r\n  CertificateService,\r\n  CredentialService,\r\n  FileService,\r\n  InvoicesService,\r\n  JsonSchemaService,\r\n  NaviService,\r\n  OnboardingService,\r\n  PartnerService,\r\n  ReportsService,\r\n  RowTypeService,\r\n  SessionService,\r\n  SettingsService,\r\n  SignatureService,\r\n  UiCrudHelpers,\r\n  UiHelpers,\r\n  UiTranslatorService,\r\n  UploadService,\r\n  UsecasesService,\r\n  UserSettingsService,\r\n  VarmaPensionService,\r\n  WizardService,\r\n  WorkflowService,\r\n} from \".\";\r\n\r\nimport { AjaxNg1 } from \"../ajax/AjaxNg1\";\r\n\r\n// @salaxy/core services and interfaces\r\nimport {\r\n  Absences,\r\n  AccountingTargets,\r\n  Accounts,\r\n  AccountSettings,\r\n  AuthorizedAccounts,\r\n  BeneficialOwnersApi,\r\n  BusinessTemplates,\r\n  Calculations,\r\n  Calculator,\r\n  CalendarEvents,\r\n  Certificates,\r\n  Client,\r\n  Credentials,\r\n  CustomerInvoices,\r\n  Datasets,\r\n  Employments,\r\n  Files,\r\n  HolidayYears,\r\n  Imports,\r\n  Invoices,\r\n  IrEarningsPayments,\r\n  IrPayerSummaries,\r\n  MessageThreads,\r\n  OAuth2,\r\n  Onboardings,\r\n  Overview,\r\n  PartnerServices,\r\n  PaymentChannelApi,\r\n  Payrolls,\r\n  Payrolls4,\r\n  ProApi,\r\n  Records,\r\n  ReferenceObjects,\r\n  Reports,\r\n  Session,\r\n  Taxcards,\r\n  Test,\r\n  Usecases,\r\n  Workers,\r\n  ServiceModels,\r\n  HouseholdYears,\r\n} from \"@salaxy/core\";\r\n\r\n// @salaxy/report services\r\nimport {\r\n  Templates,\r\n} from \"@salaxy/reports\";\r\n\r\n/**\r\n * Provides methods for registering the Services to module\r\n * (and other related metadata in the future).\r\n */\r\nexport class ServicesRegistration {\r\n\r\n  /** Gets the services for Module registration. */\r\n  public static getServices () {\r\n    return {\r\n      AjaxNg1,\r\n      AlertService,\r\n      AuthorizedAccountService,\r\n      CacheService,\r\n      CertificateService,\r\n      CredentialService,\r\n      CustomerInvoices,\r\n      FileService,\r\n      InvoicesService,\r\n      JsonSchemaService,\r\n      NaviService,\r\n      OnboardingService,\r\n      PartnerService,\r\n      ReportsService,\r\n      RowTypeService,\r\n      SessionService,\r\n      SettingsService,\r\n      SignatureService,\r\n      UiCrudHelpers,\r\n      UiHelpers,\r\n      UiTranslatorService,\r\n      UploadService,\r\n      UsecasesService,\r\n      UserSettingsService,\r\n      VarmaPensionService,\r\n      WizardService,\r\n      WorkflowService,\r\n    };\r\n  }\r\n\r\n  /** Gets the services from the @salaxy/core project that need to be registered for NG1 dependency injection. */\r\n  public static getCoreServices () {\r\n    return {\r\n      Absences,\r\n      AccountingTargets,\r\n      Accounts,\r\n      AccountSettings,\r\n      AuthorizedAccounts,\r\n      BeneficialOwnersApi,\r\n      BusinessTemplates,\r\n      Calculations,\r\n      Calculator,\r\n      CalendarEvents,\r\n      Certificates,\r\n      Client,\r\n      Credentials,\r\n      Datasets,\r\n      Employments,\r\n      Files,\r\n      HolidayYears,\r\n      Imports,\r\n      Invoices,\r\n      IrEarningsPayments,\r\n      IrPayerSummaries,\r\n      MessageThreads,\r\n      OAuth2,\r\n      Onboardings,\r\n      Overview,\r\n      PartnerServices,\r\n      PaymentChannelApi,\r\n      Payrolls,\r\n      Payrolls4,\r\n      ProApi,\r\n      Records,\r\n      ReferenceObjects,\r\n      Reports,\r\n      Session,\r\n      Taxcards,\r\n      Templates,\r\n      Test,\r\n      Usecases,\r\n      Workers,\r\n      ServiceModels,\r\n      HouseholdYears,\r\n    };\r\n  }\r\n}\r\n","import angular from \"angular\";\r\nimport routes from \"angular-route\";\r\nimport \"angular-i18n/angular-locale_fi.js\";\r\nimport ngBs from \"angular-ui-bootstrap\";\r\n\r\nimport sco from \"angular-sanitize\";\r\nimport upload from \"ng-file-upload\";\r\nimport tx from \"angular-translate\";\r\n\r\nimport { ComponentsRegistration } from \"../components/_ComponentsRegistration\";\r\nimport { ControllersRegistration } from \"../controllers/_ControllersRegistration\";\r\nimport { DirectivesRegistration } from \"../directives/_DirectivesRegistration\";\r\nimport { FiltersRegistration } from \"../filters/_FiltersRegistration\";\r\nimport { PromisePolyfill, RouteHelperProvider } from \"../helpers\";\r\nimport { LoaderInterceptor } from \"../interceptors\";\r\nimport { ServicesRegistration } from \"../services/_ServicesRegistration\";\r\n\r\n/**\r\n * Components contain the user interface element (the view) on top of the controller logic.\r\n * This is the Angular2 compatible alternative to Directives introduced in Angular 1.5.\r\n *\r\n * Registers the salaxy.ng1.components.all module that contains the entire\r\n * Palkkaus.fi Angular stack\r\n * @example\r\n * angular.module(\"myAngularApplication\", [\"salaxy.ng1.components.all\"])\r\n * @ignore\r\n */\r\nexport const SalaxyNg1ComponentsModule = angular.module(\"salaxy.ng1.components.all\", [\r\n    \"salaxy.ng1.templates.bootstrap\",\r\n    \"ui.bootstrap\",\r\n    \"ngRoute\",\r\n    \"ngSanitize\",\r\n    \"ngFileUpload\",\r\n    \"pascalprecht.translate\",\r\n])\r\n    .config([() => {\r\n      const assureReg = [routes, ngBs, sco, upload, tx];\r\n      console.debug(`@salaxy/ng1 init with ${assureReg.length} modules.`);\r\n    }])\r\n    // Registrations\r\n    .provider(\"RouteHelper\", RouteHelperProvider)\r\n    .service(ServicesRegistration.getCoreServices())\r\n    .service(ServicesRegistration.getServices())\r\n    .controller(ControllersRegistration.getControllers())\r\n    .directive(DirectivesRegistration.getDirectives())\r\n    .component(ComponentsRegistration.getComponents())\r\n    .filter(FiltersRegistration.getFilters())\r\n    .constant(\"data\", { isNotDefined: true })\r\n    .constant(\"EditDialogParameters\", { isNotDefined: true })\r\n    // Interceptors\r\n    .config([\"$httpProvider\", ($httpProvider: ng.IHttpProvider) => {\r\n       $httpProvider.interceptors.push(LoaderInterceptor.factory());\r\n     }])\r\n\r\n    // Misc configurations\r\n    .config([\"$provide\", \"$translateProvider\", ($provide: any, $translateProvider: angular.translate.ITranslateProvider) => {\r\n        // Currently there is an issue with the sanitize mode, it will double encode UTF-8 characters or special characters.\r\n        // use the null strategy, until this is resolved.\r\n        $translateProvider.useSanitizeValueStrategy(null);\r\n        $provide.value(\"$translateProvider\", $translateProvider);\r\n    }])\r\n    // supporting the default empty hash-prefix after upgrade from 1.5 -> 1.6\r\n    .config([\"$locationProvider\", ($locationProvider) => {\r\n      $locationProvider.hashPrefix(\"\");\r\n    }])\r\n    .run(PromisePolyfill)\r\n\r\n    ;\r\n","/* eslint-disable */\n  import angular from \"angular\";\n  import { Configs } from \"@salaxy/core\";\n  /**\n   * Bootstrap templates compiled to JavaScript\n   * @ignore\n   */\n  export const SalaxyNg1BootstrapTemplatesModule = angular.module(\"salaxy.ng1.templates.bootstrap\", [])\n    .run([\"$templateCache\", function ($templateCache) {\n      const useCache = !((Configs.current as any)?.noCache);\n      if (useCache) {\n        \n $templateCache.put(\"salaxy-components/account/AccountAvatarEdit.html\",`<div class=\"salaxy-component salaxy-account-contact-edit\" ng-if=\"$ctrl.isAuthenticated\">\r\n  <div ng-if=\"$ctrl.session.currentAccount.entityType == 'company'\" ng-controller=\"CompanyAccountController as $accountCtrl\">\r\n    <ng-include src=\"'AvatarEditor.html'\"></ng-include>\r\n  </div>\r\n  <div ng-if=\"$ctrl.session.currentAccount.entityType != 'company'\" ng-controller=\"PersonAccountController as $accountCtrl\">\r\n    <ng-include src=\"'AvatarEditor.html'\"></ng-include>\r\n  </div>\r\n  <script type=\"text/ng-template\" id=\"AvatarEditor.html\">\r\n    <form name=\"avatarForm\" class=\"form-horizontal\" ng-if=\"$accountCtrl.current\">\r\n      <div class=\"form-group\">\r\n        <div class=\"col-12 col-sm-4\">\r\n          <label for=\"avatarPreview\" class=\"control-label\" style=\"text-align:left\" sxy-text=\"SALAXY.NG1.AccountAvatarEditPersonComponent.avatarLabel\"></label>\r\n        </div>\r\n        <div class=\"col-12 col-sm-8\">\r\n          <div class=\"worker-avatar-col\">\r\n            <salaxy-avatar style=\"font-size: 130px\" avatar=\"$accountCtrl.current.avatar\"></salaxy-avatar>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div class=\"form-group\">\r\n        <div class=\"col-12 col-sm-4\">\r\n          <label for=\"avatarPictureType\" class=\"control-label\" style=\"text-align:left\" sxy-text=\"SALAXY.NG1.AccountAvatarEditPersonComponent.avatarTypeLabel\"></label>\r\n        </div>\r\n        <div class=\"col-12 col-sm-8\">\r\n          <select class=\"form-select\" id=\"avatarPictureType\" ng-model=\"$accountCtrl.current.avatar.pictureType\" ng-change=\"$accountCtrl.typeForAvatarChanged()\">\r\n            <option value=\"\" disabled sxy-text=\"SALAXY.NG1.AccountAvatarEditPersonComponent.optionChoose\"></option>\r\n            <option value=\"icon\" sxy-text=\"SALAXY.NG1.AccountAvatarEditPersonComponent.optionIcon\"></option>\r\n            <option value=\"uploaded\" sxy-text=\"SALAXY.NG1.AccountAvatarEditPersonComponent.optionUploaded\"></option>\r\n            <option value=\"gravatar\" sxy-text=\"SALAXY.NG1.AccountAvatarEditPersonComponent.optionGravatar\"></option>\r\n          </select>\r\n        </div>\r\n      </div>\r\n      <div ng-if=\"$accountCtrl.current.avatar.pictureType == 'gravatar'\" class=\"row\">\r\n        <div class=\"input-info col-sm-8 offset-sm-4\">\r\n          <div class=\"input-info-icon\"><i class=\"bi bi-info-circle-fill text-default\"></i></div>\r\n          <p class=\"small input-info-text with-icon \" sxy-html=\"SALAXY.NG1.AccountAvatarEditPersonComponent.gravatarInfo.html\"></p>\r\n        </div>\r\n      </div>\r\n      <div ng-if=\"$accountCtrl.current.avatar.pictureType == 'icon'\">\r\n        <salaxy-input name=\"avatarInitials\" label=\"SALAXY.NG1.AccountAvatarEditPersonComponent.initialsLabel\" ng-model=\"$accountCtrl.current.avatar.initials\" max-length=\"2\"></salaxy-input>\r\n        <salaxy-input-enum ng-model=\"$accountCtrl.current.avatar.color\" name=\"avatarColor\" label=\"SALAXY.NG1.AccountAvatarEditPersonComponent.colorLabel\" options=\"{\r\n          '#009FD8': '#009FD8',\r\n          '#91D214': '#91D214',\r\n          '#D10074': '#D10074',\r\n          '#3C3C3C': '#3C3C3C',\r\n          '#61703B': '#61703B',\r\n          '#7F2C2A': '#7F2C2A',\r\n          '#FF911E': '#FF911E',\r\n          '#289548': '#289548',\r\n          'blue': 'blue',\r\n          'lime': 'lime',\r\n          'pink': 'pink',\r\n          'gray': 'gray',\r\n          'darkgreen': 'darkgreen',\r\n          'brown': 'brown',\r\n          'yellow': 'yellow',\r\n          'orange': 'orange',\r\n          'green': 'green',\r\n          'black': 'black'         \r\n          }\">\r\n        </salaxy-input-enum>\r\n      </div>\r\n      <div class=\"form-group\">\r\n        <div ng-if=\"$accountCtrl.current.avatar.pictureType == 'uploaded'\">\r\n          <div class=\"col-12 col-sm-4\">\r\n            <label for=\"avatarImageUpload\" sxy-text=\"SALAXY.NG1.AccountAvatarEditPersonComponent.uploadImageLabel\"></label>\r\n          </div>\r\n          <div class=\"col-12 col-sm-8\">\r\n            <div name=\"avatarImageUpload\" ng-model=\"avatarImage\" ngf-drop=\"$accountCtrl.uploadAvatarImage($file)\" ngf-select=\"$accountCtrl.uploadAvatarImage($file)\" class=\"salaxy-drop-box\" ngf-drag-over-class=\"'salaxy-drag-over'\" ngf-multiple=\"false\" ngf-min-size=\"5KB\" ngf-max-size=\"10MB\"\r\n              ngf-pattern=\"'image/*'\" ngf-model-invalid=\"invalidFile\" ng-class=\"invalidFile.$error != null ? 'error' : ''\">\r\n              <span sxy-html=\"SALAXY.NG1.AccountAvatarEditPersonComponent.uploadImage.html\"></span>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div class=\"text-end\">\r\n        <button ng-click=\"$accountCtrl.saveCurrent()\" ng-disabled=\"avatarForm.$invalid\" class=\"btn btn-primary\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n      </div>\r\n    </form>\r\n  </script>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/account/AccountContactEdit.html\",`<div class=\"salaxy-component salaxy-account-contact-edit\" ng-if=\"$ctrl.isAuthenticated\">\r\n  <div ng-if=\"$ctrl.session.currentAccount.entityType == 'company'\" ng-controller=\"CompanyAccountController as $accountCtrl\">\r\n    <ng-include src=\"'ContactEditor.html'\"></ng-include>\r\n  </div>\r\n  <div ng-if=\"$ctrl.session.currentAccount.entityType != 'company'\" ng-controller=\"PersonAccountController as $accountCtrl\">\r\n    <ng-include src=\"'ContactEditor.html'\"></ng-include>\r\n  </div>\r\n  <script type=\"text/ng-template\" id=\"ContactEditor.html\">\r\n    <form name=\"contactForm\" class=\"form-horizontal\" ng-if=\"$accountCtrl.current\">\r\n      <div class=\"row\">\r\n        <div class=\"col-12\">\r\n          <salaxy-input name=\"email\" label=\"SALAXY.MODEL.PersonAccount.contact.email.title\" sxy-email ng-model=\"$accountCtrl.current.contact.email\" ng-change=\"$accountCtrl.emailForAvatarChanged()\">\r\n          </salaxy-input>\r\n          <salaxy-input name=\"telephone\" label=\"SALAXY.MODEL.PersonAccount.contact.telephone.title\" sxy-mobile-phone ng-model=\"$accountCtrl.current.contact.telephone\"></salaxy-input>\r\n          <salaxy-input name=\"street\" label=\"SALAXY.MODEL.PersonAccount.contact.street.title\" ng-model=\"$accountCtrl.current.contact.street\" ng-required=\"('household' | sxyIsInRole) || ('company' | sxyIsInRole)\"></salaxy-input>\r\n          <salaxy-input name=\"postalCode\" label=\"SALAXY.MODEL.PersonAccount.contact.postalCode.title\" sxy-postal-code-fi ng-model=\"$accountCtrl.current.contact.postalCode\" ng-required=\"('household' | sxyIsInRole) || ('company' | sxyIsInRole)\"></salaxy-input>\r\n          <salaxy-input name=\"city\" label=\"SALAXY.MODEL.PersonAccount.contact.city.title\" ng-model=\"$accountCtrl.current.contact.city\" ng-required=\"('household' | sxyIsInRole) || ('company' | sxyIsInRole)\"></salaxy-input>\r\n          <salaxy-input-enum type=\"select\" label=\"SALAXY.MODEL.PersonAccount.contact.countryCode.title\" ng-model=\"$accountCtrl.current.contact.countryCode\"\r\n          name=\"country\" read-only=\"true\" enum=\"Country\"></salaxy-input-enum>\r\n        </div>\r\n      </div>\r\n      <div class=\"text-end\">\r\n        <button ng-click=\"$accountCtrl.saveCurrent()\" ng-disabled=\"contactForm.$invalid\" class=\"btn btn-primary\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n      </div>\r\n    </form>\r\n  </script>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/account/AccountInfo.html\",`﻿<div class=\"container-fixed salaxy-component salaxy-account-info\" ng-controller=\"CompanyAccountController as $companyCtrl\">\r\n  <div class=\"d-flex flex-column flex-md-row\">\r\n    <div>\r\n      <salaxy-avatar avatar=\"$ctrl.company.avatar\" class=\"avatar-xl mb-4 me-4\"></salaxy-avatar>\r\n      <button type=\"button\" style=\"margin-bottom: 5px;\" class=\"btn btn-sm btn-default mb-2\" ng-click=\"$companyCtrl.openEditDialog('avatar')\" sxy-text=\"SALAXY.NG1.AccountInfoComponent.changeAvatar\"></button>\r\n    </div>   \r\n    <p class=\"lead\" ng-controller=\"CompanyOnboardingController as $onBoarding\">\r\n      {{'SALAXY.NG1.AccountInfoComponent.lead.infoText' | sxyTranslate}} <a ng-click=\"$onBoarding.openSigningWizardDialog()\">{{'SALAXY.NG1.AccountInfoComponent.lead.buttonText' | sxyTranslate}}</a> {{'SALAXY.NG1.AccountInfoComponent.lead.infoTextAlt' | sxyTranslate}}\r\n    </p>\r\n  </div>\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table\">\r\n      <tr>\r\n        <th sxy-text=\"SALAXY.NG1.AccountInfoComponent.palkkausAccount\" ps=\":\"></th>\r\n        <td>{{ $ctrl.company.id | sxyIban }}</td>\r\n        <th sxy-text=\"SALAXY.NG1.AccountInfoComponent.email\" ps=\":\"></th>\r\n        <td>{{ $ctrl.company.contact.email }}</td>\r\n      </tr>\r\n      <tr>\r\n        <th sxy-text=\"SALAXY.NG1.AccountInfoComponent.companyName\" ps=\":\"></th>\r\n        <td>{{ $ctrl.company.avatar.displayName }}</td>\r\n        <th sxy-text=\"SALAXY.NG1.AccountInfoComponent.phone\" ps=\":\"></th>\r\n        <td>{{ $ctrl.company.contact.telephone }}</td>\r\n      </tr>\r\n      <tr>\r\n        <th sxy-text=\"SALAXY.NG1.AccountInfoComponent.officialId\" ps=\":\"></th>\r\n        <td>{{ $ctrl.company.identity.officialId }}</td>\r\n        <th sxy-text=\"SALAXY.NG1.AccountInfoComponent.address\" ps=\":\"></th>\r\n        <td>\r\n          {{ $ctrl.company.contact.street }}<br /> {{ $ctrl.company.contact.postalCode }} {{ $ctrl.company.contact.city }}\r\n        </td>\r\n      </tr>\r\n      <tr>\r\n        <th sxy-text=\"SALAXY.NG1.AccountInfoComponent.companyType\" ps=\":\"></th>\r\n        <td>{{ 'CompanyType.' + $ctrl.company.companyType | sxyEnum }}</td>\r\n        <th sxy-text=\"SALAXY.NG1.AccountInfoComponent.ibanNumber\" ps=\":\"></th>\r\n        <td>{{ $ctrl.company.identity.ibanNumber | sxyIban }}</td>\r\n      </tr>\r\n      <tr>\r\n        <th sxy-text=\"SALAXY.NG1.AccountInfoComponent.authorizationType\" ps=\":\"></th>\r\n        <td>\r\n          {{ 'AuthorizationType.' + $ctrl.company.identity.contract.authorizationType | sxyEnum }}\r\n          <span ng-if=\"$ctrl.company.identity.contract.authorizationType == 'companyContract' || $ctrl.company.identity.contract.authorizationType == 'employerAuthorization'\">\r\n            (<a class=\"\" ng-href=\"{{$ctrl.authorizationPdfUrl}}\" target=\"_blank\" sxy-text=\"SALAXY.UI_Terms.seePreview\"></a>)\r\n          </span>\r\n        </td>\r\n        <th><button type=\"button\" class=\"btn btn-sm btn-default mb-1\" ng-click=\"$companyCtrl.openEditDialog('contactInfo')\" sxy-text=\"SALAXY.NG1.AccountInfoComponent.editContactInfo\"></button></th>\r\n        <td></td>\r\n      </tr>\r\n      <tr>\r\n        <th sxy-text=\"Asiakkaan tunnistaminen tehty\" ps=\":\"></th>\r\n        <td>\r\n          <span ng-if=\"$ctrl.kycState == 'ignored'\"></span>\r\n          <span ng-if=\"$ctrl.kycState == 'valid'\" class=\"text-success\">KYC OK {{ $ctrl.kycUpdatedAt | sxyDate }}</span>\r\n          <span ng-if=\"$ctrl.kycState == 'missing'\" class=\"text-danger\">Päivitä KYC</span>\r\n          <span ng-if=\"$ctrl.kycState == 'expired'\" class=\"text-warning\">KYC vanhenee {{ $ctrl.kycExpiresAt | sxyDate }}</span>\r\n        </td>\r\n        <th>\r\n          <a ng-href=\"{{('test' | sxyIsInRole) ? 'https://rc-iam.palkkaus.fi/wizard/index.html' : 'https://iam.palkkaus.fi/wizard/index.html'}}\" target=\"_blank\" class=\"btn btn-sm btn-default\" role=\"button\">Päivitä asiakkaan tunnistaminen</a>\r\n        </th>\r\n        <td></td>\r\n      </tr>\r\n    </table>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/account/AssurePartner.html\",`<div class=\"salaxy-assure-partner salaxy-component\" ng-controller=\"SessionController as $sessionCtrl\">\r\n  <div ng-if=\"$sessionCtrl.session.settings.partner.accountId\">\r\n    <ng-transclude ng-transclude-slot=\"header\">\r\n      <!-- Further information of the partner etc. -->\r\n    </ng-transclude>\r\n    <ng-transclude ng-transclude-slot=\"main\">\r\n      <!-- Content to assure -->\r\n    </ng-transclude>\r\n  </div>\r\n  <div ng-if=\"!$sessionCtrl.session.settings.partner.accountId\">\r\n    <div class=\"row\">\r\n      <div class=\"col-12\">\r\n        <div class=\"content settings\">\r\n          <salaxy-accountant></salaxy-accountant>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/account/AuthCard.html\",`<div class=\"salaxy-component salaxy-product-card p-3 d-flex flex-column\" ng-click=\"$ctrl.showPartnerSiteDialog($ctrl.authId)\">\r\n  <div class=\"d-flex row flex-grow-1\">\r\n    <div class=\"col-4\">\r\n      <i class=\"salaxy-avatar avatar-lg\"><img ng-src=\"{{$ctrl.getPartnerSite($ctrl.authId).img}}\" /></i>\r\n    </div>\r\n    <div class=\"col-8 ps-4\">\r\n      <div class=\"salaxy-product-title text-break\">{{ $ctrl.getPartnerSite($ctrl.authId).title }}</div>\r\n      <div class=\"salaxy-product-descr text-break\">{{ $ctrl.getPartnerSite($ctrl.authId).status }}</div>\r\n    </div>\r\n  </div>\r\n  <div class=\"d-flex justify-content-end\">\r\n    <salaxy-input-boolean type=\"switch\" ng-if=\"$ctrl.isInRole('auth') && !$ctrl.hideSwitch\" id=\"salaxyService\" name=\"salaxyService\" ng-model=\"$ctrl.getPartnerSite($ctrl.authId).enabled\" label-type=\"no-label\" label-true=\"Aktivoitu\" label-false=\"Aktivoi\"></salaxy-input-boolean>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/account/AuthorizedAccounts.html\",`<div class=\"card card-default\" ng-controller=\"AccountAuthorizationController as $ctrl\">\r\n  <div class=\"card-header\">\r\n    <h2 sxy-text=\"SALAXY.NG1.AuthoringAccountComponent.authorizeIntro\"></h2>\r\n    <p><small sxy-text=\"SALAXY.NG1.AuthoringAccountComponent.authorizeDescription\"></small></p>\r\n  </div>\r\n  <div class=\"card-body\">\r\n    <div class=\"salaxy-component salaxy-authorized-accounts\">\r\n      <div class=\"table-responsive\">\r\n        <table class=\"table table-striped\">\r\n          <thead>\r\n            <tr>\r\n              <th colspan=\"2\" sxy-text=\"SALAXY.NG1.AuthoringAccountComponent.palkkausAccount\"></th>\r\n              <th ng-if=\"('admin' | sxyIsInRole)\">Partnerin antama ID</th>\r\n              <th class=\"right\" sxy-text=\"SALAXY.NG1.AuthoringAccountComponent.date\"></th>\r\n              <th class=\"right\">\r\n                <ng-transclude ng-transclude-slot=\"header\">\r\n                  <button class=\"btn btn-sm btn-default\" ng-click=\"$ctrl.showAuthorizedAccountAddDialog()\" sxy-text=\"SALAXY.UI_Terms.createNew\"></button>\r\n                </ng-transclude>\r\n              </th>\r\n            </tr>\r\n          </thead>\r\n          <tbody>\r\n            <tr ng-repeat=\"avatar in $ctrl.list\">\r\n              <td>\r\n                <salaxy-avatar class=\"avatar-sm\" avatar=\"avatar\"></salaxy-avatar>\r\n              </td>\r\n              <td>\r\n                <strong>{{avatar.displayName}}</strong><br/>\r\n                <small>{{avatar.id | sxyIban}}</small>\r\n              </td>\r\n              <td  ng-if=\"('admin' | sxyIsInRole)\">{{avatar.partnerKey}}</td>\r\n              <td class=\"right\">{{avatar.createdAt | date}}</td>\r\n              <td class=\"right\">\r\n                <button ng-click=\"$ctrl.delete(avatar.id)\" class=\"btn btn-danger btn-sm\" sxy-text=\"SALAXY.UI_Terms.delete\"></button>\r\n              </td>\r\n            </tr>\r\n          </tbody>\r\n        </table>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/account/AuthorizingAccounts.html\",`<div class=\"salaxy-component salaxy-authorizing-accounts\">\r\n  <div class=\"table-responsive\" ng-controller=\"CustomerOnboardingController as wizard\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\" sxy-text=\"SALAXY.NG1.AuthoringAccountComponent.palkkausAccount\"></th>\r\n          <th sxy-text=\"SALAXY.NG1.AuthoringAccountComponent.status\"></th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.AuthoringAccountComponent.date\"></th>\r\n          <th class=\"right\" colspan=\"3\">\r\n            <ng-transclude ng-transclude-slot=\"header\">\r\n              <button class=\"btn btn-sm btn-default\" ng-click=\"wizard.launch()\" sxy-text=\"SALAXY.UI_Terms.createNew\"></button>\r\n            </ng-transclude>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"account in $ctrl.authorizingAccounts\">\r\n          <td>\r\n            <salaxy-avatar class=\"avatar-sm\" avatar=\"account.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td>\r\n            <strong>{{account.avatar.displayName}}</strong><br/>\r\n            <small>{{account.id | sxyIban }}</small>\r\n          </td>\r\n          <td>\r\n            <small class=\"text-success\" ng-if=\"account.identity.contract.isSigned\" sxy-text=\"SALAXY.NG1.AuthoringAccountComponent.signeratureOk\"></small>\r\n            <small class=\"text-danger\" ng-if=\"!account.identity.contract.isSigned\" sxy-text=\"SALAXY.NG1.AuthoringAccountComponent.signeratureNo\"></small>\r\n          </td>\r\n          <td class=\"right\">{{account.createdAt | date }}</td>\r\n          <td>\r\n            <button ng-if=\"!account.identity.contract.isSigned && account.entityType == 'company'\" ng-click=\"wizard.launch(account.id)\" class=\"btn btn-default btn-block\" sxy-text=\"SALAXY.NG1.AuthoringAccountComponent.invite\"></button>\r\n          </td>\r\n          <td>\r\n            <a ng-href=\"{{$ctrl.getLoginAsUrl(account.id)}}\" target=\"_blank\" class=\"btn btn-primary btn-block\" sxy-text=\"SALAXY.NG1.AuthoringAccountComponent.signIn\"></a>\r\n          </td>\r\n          <td>\r\n            <button salaxy-if-role=\"test\" ng-click=\"$ctrl.deleteAccount(account.id)\" class=\"btn btn-danger btn-block\" sxy-text=\"SALAXY.UI_Terms.delete\"></button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/account/Certificates.html\",`<div class=\"card card-default\">\r\n  <div class=\"card-header\">\r\n    <h2 sxy-text=\"SALAXY.NG1.CertificatesComponent.title\"></h2>    \r\n  </div>\r\n  <div class=\"card-body\">\r\n    <div class=\"salaxy-component salaxy-certificates\">\r\n      <div class=\"table-responsive\">\r\n        <table class=\"table table-striped\">\r\n          <thead>\r\n            <tr>\r\n              <th sxy-text=\"SALAXY.NG1.CertificatesComponent.name\"></th>\r\n              <th sxy-text=\"SALAXY.NG1.CertificatesComponent.id\"></th>\r\n              <th class=\"right\" sxy-text=\"SALAXY.NG1.AuthoringAccountComponent.date\"></th>\r\n              <th class=\"right\">\r\n                <ng-transclude ng-transclude-slot=\"header\">\r\n                  <button class=\"btn btn-default btn-sm\" ng-click=\"$ctrl.showCertificateAddDialog()\" sxy-text=\"SALAXY.UI_Terms.createNew\"></button>\r\n                </ng-transclude>\r\n              </th>\r\n            </tr>\r\n          </thead>\r\n          <tbody>\r\n            <tr ng-repeat=\"certificate in $ctrl.list\">\r\n              <td>{{certificate.title || '-'}}</td>\r\n              <td>{{certificate.thumbprint}}</td>\r\n              <td class=\"right\">{{certificate.createdAt | date}}</td>\r\n              <td class=\"right\">\r\n                <button ng-click=\"$ctrl.delete(certificate.thumbprint)\" class=\"btn btn-danger btn-sm\" sxy-text=\"SALAXY.UI_Terms.delete\"></button>\r\n              </td>\r\n            </tr>\r\n          </tbody>\r\n        </table>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/account/Credentials.html\",`<div class=\"card card-secondary\">\r\n\r\n  <div class=\"card-header\">\r\n    <h2 sxy-text=\"SALAXY.NG1.CredentialsComponent.title\"></h2>\r\n    <p>\r\n      <!--<small sxy-text=\"SALAXY.NG1.CredentialsComponent.intro\"></small>--></p>\r\n  </div>\r\n  <div class=\"card-body\">\r\n    <div class=\"salaxy-component salaxy-credentials\">\r\n      <div class=\"table-responsive\">\r\n        <table class=\"table table-striped\">\r\n          <thead>\r\n            <tr>\r\n              <th sxy-text=\"SALAXY.NG1.CredentialsComponent.userId\"></th>\r\n              <th sxy-text=\"SALAXY.NG1.CredentialsComponent.authenticationMethod\"></th>\r\n              <th class=\"right\" sxy-text=\"SALAXY.NG1.AuthoringAccountComponent.date\"></th>\r\n              <th class=\"right\">\r\n                <ng-transclude ng-transclude-slot=\"header\"></ng-transclude>\r\n              </th>\r\n            </tr>\r\n          </thead>\r\n          <tbody>\r\n            <tr ng-repeat=\"credential in $ctrl.list\">\r\n              <td>{{credential.email}}</td>\r\n              <td>{{ 'AuthenticationMethod.' + credential.authenticationMethod | sxyEnum}}</td>\r\n              <td class=\"right\">{{credential.createdAt | date}}</td>\r\n              <td class=\"right\">\r\n\r\n                <button ng-if=\"$ctrl.showEdit\" ng-click=\"$ctrl.setCurrent(credential)\" class=\"btn btn-primary btn-sm\" sxy-text=\"SALAXY.UI_Terms.select\"></button>\r\n                <button ng-if=\"$ctrl.showEdit && !('admin' | sxyIsInRole)\" ng-disabled=\"$ctrl.list.length &lt;= 1\" ng-click=\"$ctrl.delete(credential.id)\" class=\"btn btn-danger btn-sm\" sxy-text=\"SALAXY.UI_Terms.delete\"></button>\r\n                <button ng-if=\"$ctrl.showEdit && ('admin' | sxyIsInRole)\" ng-click=\"$ctrl.delete(credential.id)\" class=\"btn btn-danger btn-sm\" sxy-text=\"SALAXY.UI_Terms.delete\"></button>\r\n              </td>\r\n            </tr>\r\n          </tbody>\r\n        </table>\r\n      </div>\r\n      <form name=\"credentialsForm\" class=\"form-horizontal\" ng-if=\"$ctrl.current && $ctrl.showEdit\">\r\n        <div class=\"row\">\r\n          <div class=\"col-12\">\r\n            <salaxy-input name=\"firstName\" label=\"SALAXY.NG1.CredentialsComponent.firstName\" ng-model=\"$ctrl.current.avatar.firstName\"></salaxy-input>\r\n            <salaxy-input name=\"lastName\" label=\"SALAXY.NG1.CredentialsComponent.lastName\" ng-model=\"$ctrl.current.avatar.lastName\"></salaxy-input>\r\n            <salaxy-input name=\"email\" label=\"SALAXY.NG1.CredentialsComponent.email\" ng-model=\"$ctrl.current.email\" ng-change=\"$ctrl.emailForAvatarChanged()\"></salaxy-input>\r\n            <!-- <salaxy-input name=\"telephone\" label=\"SALAXY.NG1.CredentialsComponent.telephone\" ng-model=\"$ctrl.current.telephone\"></salaxy-input>-->\r\n            <div class=\"form-group\">\r\n              <div class=\"col-12 col-sm-4\">\r\n                <strong sxy-text=\"SALAXY.NG1.CredentialsComponent.authenticationMethod\"></strong>\r\n              </div>\r\n              <div class=\"col-12 col-sm-8\">\r\n                {{ 'AuthenticationMethod.' + $ctrl.current.authenticationMethod | sxyEnum}}\r\n              </div>\r\n            </div>\r\n\r\n          </div>\r\n        </div>\r\n\r\n        <div class=\"form-group\">\r\n\r\n          <div class=\"col-12 col-sm-4\">\r\n            <label for=\"avatarPictureType\" class=\"control-label\" style=\"text-align:left\" sxy-text=\"SALAXY.NG1.CredentialsComponent.avatar.label\"></label>\r\n          </div>\r\n          <div class=\"col-12 col-sm-6\">\r\n            <select class=\"form-select\" style=\"margin-bottom:15px;\" id=\"avatarPictureType\" ng-model=\"$ctrl.current.avatar.pictureType\" ng-change=\"$ctrl.typeForAvatarChanged()\">\r\n              <option value=\"\" disabled sxy-text=\"SALAXY.NG1.CredentialsComponent.avatar.optionChoose\"></option>\r\n              <option value=\"icon\" sxy-text=\"SALAXY.NG1.CredentialsComponent.avatar.optionIcon\"></option>\r\n              <option value=\"uploaded\" sxy-text=\"SALAXY.NG1.CredentialsComponent.avatar.optionUploaded\"></option>\r\n              <option value=\"gravatar\" sxy-text=\"SALAXY.NG1.CredentialsComponent.avatar.optionGravatar\"></option>\r\n            </select>\r\n            <div ng-if=\"$ctrl.current.avatar.pictureType == 'gravatar'\" class=\"input-info\">\r\n              <div class=\"input-info-icon\"><i class=\"bi bi-info-circle-fill text-default\"></i></div>\r\n              <p class=\"small input-info-text with-icon \" sxy-html=\"SALAXY.NG1.CredentialsComponent.avatar.gravatarInfo.html\"></p>\r\n            </div>\r\n            <div ng-if=\"$ctrl.current.avatar.pictureType == 'icon'\">\r\n              <salaxy-input name=\"avatarInitials\" label=\"SALAXY.NG1.CredentialsComponent.avatar.labelInitials\" ng-model=\"$ctrl.current.avatar.initials\" max-length=\"2\"></salaxy-input>\r\n              <salaxy-input-enum name=\"avatarColor\" label=\"SALAXY.NG1.CredentialsComponent.avatar.labelColor\" ng-model=\"$ctrl.current.avatar.color\" options=\"$ctrl.colorOptions\">\r\n              </salaxy-input-enum>\r\n            </div>\r\n            <div ng-if=\"$ctrl.current.avatar.pictureType == 'uploaded'\" class=\"form-group\">\r\n              <div class=\"col-12 col-sm-4\">\r\n                <label for=\"avatarImageUpload\" sxy-text=\"SALAXY.NG1.CredentialsComponent.avatar.labelUploadImage\"></label>\r\n              </div>\r\n              <div class=\"col-12 col-sm-8\">\r\n                <div name=\"avatarImageUpload\" ng-model=\"avatarImage\" ngf-drop=\"$ctrl.uploadAvatarImage($file)\" ngf-select=\"$ctrl.uploadAvatarImage($file)\" class=\"salaxy-drop-box\" ngf-drag-over-class=\"'salaxy-drag-over'\" ngf-multiple=\"false\" ngf-min-size=\"5KB\" ngf-max-size=\"10MB\"\r\n                  ngf-pattern=\"'image/*'\" ngf-model-invalid=\"invalidFile\" ng-class=\"invalidFile.$error != null ? 'error' : ''\">\r\n                  <span sxy-html=\"SALAXY.NG1.CredentialsComponent.avatar.uploadImage.html\"></span>\r\n                </div>\r\n              </div>\r\n            </div>\r\n          </div>\r\n          <div class=\"col-sm-2 col-12 text-center\">\r\n            <salaxy-avatar avatar=\"$ctrl.current.avatar\" style=\"font-size:70px;\"></salaxy-avatar>\r\n          </div>\r\n        </div>\r\n\r\n        <div class=\"row\">\r\n          <div class=\"col-12 text-end\">\r\n            <button ng-click=\"$ctrl.saveCurrent()\" ng-disabled=\"credentialsForm.$invalid\" class=\"btn btn-primary\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n          </div>\r\n        </div>\r\n      </form>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/account/LanguageSelector.html\",`<div class=\"salaxy-component salaxy-language-selector\" ng-controller=\"CompanyAccountController as $accountCtrl\">\r\n  <div class=\"card language-selection card-secondary\">\r\n    <div class=\"card-header\">\r\n      <h2>{{'SALAXY.NG1.LanguageSelectionComponent.panelTitle' | sxyTranslate}}</h2>\r\n    </div>\r\n    <div class=\"card-body\">\r\n      <div class=\"row\">\r\n        <div class=\"col-sm-6\">\r\n          <fieldset>\r\n            <legend sxy-text=\"SALAXY.NG1.LanguageSelectionComponent.changeLanguage\"></legend>\r\n            <p sxy-text=\"SALAXY.NG1.LanguageSelectionComponent.changeLanguageInfo\"></p>\r\n            <div class=\"btn-group\">\r\n              <button type=\"button\" class=\"btn\" ng-class=\"$ctrl.getLanguage() == 'fi' ? 'btn-primary disabled' : 'btn-default'\" ng-click=\"$ctrl.setLanguage('fi')\" sxy-text=\"SALAXY.ENUM.Language.fi.label\"></button>\r\n              <button type=\"button\" class=\"btn\" ng-class=\"$ctrl.getLanguage() == 'en' ? 'btn-primary disabled' : 'btn-default'\" ng-click=\"$ctrl.setLanguage('en')\" sxy-text=\"SALAXY.ENUM.Language.en.label\"></button>\r\n              <button type=\"button\" class=\"btn\" ng-class=\"$ctrl.getLanguage() == 'sv' ? 'btn-primary disabled' : 'btn-default'\" ng-click=\"$ctrl.setLanguage('sv')\" sxy-text=\"SALAXY.ENUM.Language.sv.label\"></button>\r\n            </div>\r\n          </fieldset>\r\n        </div>\r\n        <div class=\"col-sm-6\">\r\n          <fieldset>\r\n            <legend sxy-text=\"SALAXY.NG1.LanguageSelectionComponent.changeCompanyDefaultLanguage\"></legend>\r\n            <p sxy-text=\"SALAXY.NG1.LanguageSelectionComponent.changeCompanyDefaultLanguageInfo\"></p>\r\n            <div class=\"btn-group\">\r\n              <button type=\"button\" class=\"btn\" ng-class=\"$accountCtrl.getAccountLanguage() == 'fi' ? 'btn-primary active disabled' : 'btn-default'\" ng-click=\"$accountCtrl.current.language = 'fi'\" sxy-text=\"SALAXY.ENUM.Language.fi.label\"></button>\r\n              <button type=\"button\" class=\"btn\" ng-class=\"$accountCtrl.getAccountLanguage() == 'en' ? 'btn-primary active disabled' : 'btn-default'\" ng-click=\"$accountCtrl.current.language = 'en'\" sxy-text=\"SALAXY.ENUM.Language.en.label\"></button>\r\n              <button type=\"button\" class=\"btn\" ng-class=\"$accountCtrl.getAccountLanguage() == 'sv' ? 'btn-primary active disabled' : 'btn-default'\" ng-click=\"$accountCtrl.current.language = 'sv'\" sxy-text=\"SALAXY.ENUM.Language.sv.label\"></button>\r\n            </div>\r\n            <div>&nbsp;</div>\r\n            <div class=\"alert alert-warning\" sxy-html=\"SALAXY.NG1.LanguageSelectionComponent.warning.html\"></div>\r\n          </fieldset>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"card-footer\">\r\n      <div class=\"row\">\r\n        <div class=\"col text-end\">\r\n          <button class=\"btn btn-primary\" ng-click=\"$accountCtrl.saveCurrent()\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/account/LoginButton.html\",`<div class=\"salaxy-login-button salaxy-component d-flex\" sxy-if-role=\"!worker\">\r\n  <button ng-hide=\"$ctrl.isAuthenticated\" ng-click=\"$ctrl.signIn()\" class=\"btn salaxy-login-button-login\" ng-class=\"$ctrl.btnClass || 'btn-default'\">\r\n    <span class=\"bi bi-lock-fill me-2\"></span>\r\n    <span class=\"salaxy-login-button-text\">{{ $ctrl.isSessionChecking ?  ('SALAXY.NG1.LoginButtonComponent.searching' | sxyTranslate) : ($ctrl.loginText || 'SALAXY.UI_Terms.login' | sxyTranslate) }}</span>\r\n  </button>\r\n  <div ng-show=\"$ctrl.isAuthenticated\" class=\"btn-group dropdown salaxy-login-button-logout\">\r\n    <button type=\"button\" id=\"loginBtn\" class=\"btn dropdown-toggle\" ng-class=\"$ctrl.btnClass || 'btn-default'\" data-bs-toggle=\"dropdown\" aria-expanded=\"false\">\r\n      <salaxy-avatar class=\"me-2\" avatar=\"$ctrl.avatar\"></salaxy-avatar>\r\n      <span class=\"salaxy-login-button-text\">{{ $ctrl.isAuthenticated ? $ctrl.avatar.displayName : ('SALAXY.NG1.LoginButtonComponent.authenticating' | sxyTranslate) }}</span>\r\n    </button>\r\n    <ul class=\"dropdown-menu\" aria-labelledby=\"loginBtn\" ng-controller=\"NaviController as $navi\">\r\n      <li>\r\n        <a href=\"#\" class=\"dropdown-item\" ng-click=\"$ctrl.signOut()\" sxy-text=\"SALAXY.UI_Terms.logout\"></a>\r\n      </li>\r\n      <li role=\"separator\" class=\"divider\"></li>\r\n      <li>\r\n        <a href=\"#/settings/service-settings\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.LoginButtonComponent.accountSettings\" ng-click=\"$navi.toggleNavi()\"></a>\r\n      </li>\r\n      <li>\r\n        <a href=\"#/settings/authorizations\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.LoginButtonComponent.authAndCerti\" ng-click=\"$navi.toggleNavi()\"></a>\r\n      </li>\r\n      <li ng-if=\"$ctrl.ownedPaymentChannel\">\r\n        <a href=\"#/payment-channel\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.LoginButtonComponent.paymentChannel\" ng-click=\"$navi.toggleNavi()\"></a>\r\n      </li>\r\n    </ul>\r\n  </div>\r\n</div>\r\n<div class=\"salaxy-login-button\" sxy-if-role=\"worker\" ng-controller=\"NaviController as $navi\">\r\n  <div ng-show=\"$ctrl.isAuthenticated\" class=\"dropdown salaxy-login-button-logout\">\r\n    <button type=\"button\" class=\"btn dropdown-toggle btn-transparent\" data-bs-toggle=\"dropdown\">\r\n      <salaxy-avatar avatar=\"$ctrl.avatar\" class=\"me-2\"></salaxy-avatar>\r\n      <span class=\"salaxy-login-button-text\">{{ $ctrl.isAuthenticated ? $ctrl.avatar.displayName : ('SALAXY.NG1.LoginButtonComponent.authenticating' | sxyTranslate) }}\r\n      </span>\r\n    </button>\r\n    <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"account-menu\">\r\n      <li>\r\n        <a href=\"#\" ng-click=\"$ctrl.signOut()\" class=\"dropdown-item\" sxy-text=\"SALAXY.UI_Terms.logout\"></a>\r\n      </li>\r\n      <li role=\"separator\" class=\"dropdown-divider\"></li>\r\n      <li>\r\n        <a href=\"#/account/account-info\" sxy-text=\"SALAXY.NG1.LoginButtonComponent.accountSettings\" ng-click=\"$navi.toggleNavi()\" class=\"dropdown-item\"></a>\r\n      </li>\r\n      <li>\r\n        <a href=\"#/settings/authorizations\" sxy-text=\"SALAXY.NG1.LoginButtonComponent.authAndCerti\" ng-click=\"$navi.toggleNavi()\" class=\"dropdown-item\"></a>\r\n      </li>\r\n    </ul>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/account/Signing.html\",`<div class=\"salaxy-component salaxy-signing\">\r\n  <div salaxy-if-role=\"init\">\r\n    <salaxy-spinner heading=\"SALAXY.UI_Terms.loading\"></salaxy-spinner>\r\n    <p>&nbsp;</p>\r\n  </div>\r\n  <div ng-if=\"$ctrl.isSigningRequired || $ctrl.showAlways\">\r\n    <form name=\"signingForm\" class=\"form-horizontal\">\r\n      <h2 sxy-text=\"SALAXY.NG1.SigningComponent.heading\"></h2>\r\n      <div class=\"row\">\r\n        <div class=\"col-md-6\">\r\n          <fieldset>\r\n            <legend sxy-text=\"SALAXY.NG1.SigningComponent.signerInformation\"></legend>\r\n            <salaxy-input name=\"sign_personName\" label=\"SALAXY.NG1.SigningComponent.name\" ng-model=\"$ctrl.model.signature.personName\" ng-required=\"true\"></salaxy-input>\r\n            <salaxy-input name=\"sign_email\" label=\"SALAXY.NG1.SigningComponent.email\" sxy-email ng-model=\"$ctrl.model.signature.email\" ng-required=\"true\"></salaxy-input>\r\n            <salaxy-input name=\"sign_telephone\" label=\"SALAXY.NG1.SigningComponent.tel\" sxy-mobile-phone ng-model=\"$ctrl.model.signature.telephone\" ng-required=\"true\">\r\n            </salaxy-input>\r\n            <salaxy-input name=\"sign_personalId\" label=\"SALAXY.NG1.SigningComponent.ssNumber\" sxy-personal-id-fi ng-model=\"$ctrl.model.signature.personalId\" ng-required=\"true\">\r\n            </salaxy-input>\r\n            <div class=\"text-right text-danger\" style=\"margin-top: -14px; font-weight: bold;\" sxy-if-role=\"test\"> TEST ONLY: Ota hetu täältä ==></div>\r\n            <salaxy-input-boolean type=\"checkbox\" name=\"isProcura\" required ng-model=\"$ctrl.model.signature.isProcura\" label=\"SALAXY.NG1.SigningComponent.isProcuraLabel\"\r\n              label-true=\"SALAXY.NG1.SigningComponent.isProcuraLabelTrue\"></salaxy-input-boolean>\r\n          </fieldset>\r\n        </div>\r\n        <div class=\"col-md-6\">\r\n          <legend sxy-text=\"SALAXY.NG1.SigningComponent.attorney.info\"></legend>\r\n          <p>\r\n            <span sxy-text=\"SALAXY.NG1.SigningComponent.attorney.infoText\"></span>\r\n\r\n            <a ng-href=\"{{ $ctrl.getPdfPreviewAddress() }}\" target=\"_blank\">{{'SALAXY.NG1.SigningComponent.attorney.linkText' | sxyTranslate}}</a>.\r\n            {{'SALAXY.NG1.SigningComponent.attorney.linkTextInfo' | sxyTranslate}}\r\n          </p>\r\n          <p sxy-text=\"SALAXY.NG1.SigningComponent.attorney.signingConfirmationInfo\"></p>\r\n          <div sxy-if-role=\"test\" class=\"alert alert-danger\">\r\n            <p>\r\n              Allekirjoitus ohjaa nyt testiympäristöön, jossa\r\n              <strong>HETU tarkistetaan</strong>.\r\n              Katso testiympäristön\r\n              <a href=\"https://gist.github.com/ykarikos/e43e567eb7b9e05432d4bd9d0b51ef35\" target=\"_blank\">HETU:t täältä</a>\r\n              (valitse validi hetu).\r\n            </p>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div class=\"row\">\r\n        <div class=\"col-md-6\">\r\n          <fieldset>\r\n            <legend sxy-text=\"SALAXY.NG1.SigningComponent.salaryPaymentContactInformation\"></legend>\r\n            <p sxy-text=\"SALAXY.NG1.SigningComponent.salaryPaymentContanctInformationToAuthoritiesInfo\"></p>\r\n            <salaxy-input-boolean type=\"checkbox\" name=\"isContactPersonSigner\" ng-model=\"$ctrl.isContactPersonSigner\" label=\"SALAXY.NG1.SigningComponent.contactPersonLabel\"\r\n              label-true=\"SALAXY.NG1.SigningComponent.contactPersonLabelTrue\"></salaxy-input-boolean>\r\n            <div ng-if=\"!$ctrl.isContactPersonSigner\">\r\n              <salaxy-input name=\"contact_email\" label=\"SALAXY.NG1.SigningComponent.email\" sxy-email ng-model=\"$ctrl.model.company.contact.email\" ng-required=\"true\">\r\n              </salaxy-input>\r\n              <salaxy-input name=\"contact_telephone\" label=\"SALAXY.NG1.SigningComponent.tel\" sxy-mobile-phone ng-model=\"$ctrl.model.company.contact.telephone\" ng-required=\"true\">\r\n              </salaxy-input>\r\n            </div>\r\n          </fieldset>\r\n        </div>\r\n        <div class=\"col-md-6\">\r\n          <fieldset>\r\n            <legend sxy-text=\"SALAXY.NG1.SigningComponent.postalAddress\"></legend>\r\n            <salaxy-input label=\"SALAXY.NG1.SigningComponent.streetAddress\" name=\"Katuosoite\" ng-model=\"$ctrl.model.company.contact.street\" ng-required=\"true\"></salaxy-input>\r\n            <salaxy-input label=\"SALAXY.NG1.SigningComponent.postalNumber\" name=\"Postinumero\" sxy-postal-code-fi ng-model=\"$ctrl.model.company.contact.postalCode\"\r\n              ng-required=\"true\"></salaxy-input>\r\n            <salaxy-input label=\"SALAXY.NG1.SigningComponent.postOffice\" name=\"Postitoimipaikka\" ng-model=\"$ctrl.model.company.contact.city\" ng-required=\"true\"></salaxy-input>\r\n          </fieldset>\r\n        </div>\r\n      </div>\r\n      <p sxy-html=\"SALAXY.NG1.SigningComponent.authoritativeQuestions.bySigningAcceptTermsOfUse.html\"></p>\r\n      <div class=\"mb-2\">\r\n        <div>\r\n          <button class=\"btn btn-primary\" ng-disabled=\"!signingForm.$valid || $ctrl.isSigninStarted\" ng-click=\"signingForm.$valid ? $ctrl.startDigitalSignature() : null\"\r\n            sxy-text=\"SALAXY.NG1.SigningComponent.signBtn\"></button> &nbsp; &nbsp;\r\n          <span ng-if=\"!signingForm.$valid\" class=\"text-danger\" sxy-text=\"SALAXY.NG1.SigningComponent.authoritativeQuestions.error\"></span>\r\n        </div>\r\n      </div>\r\n      <p sxy-text=\"SALAXY.NG1.SigningComponent.authoritativeQuestions.usePersonalMobileBanking\"></p>\r\n      <hr />\r\n      <div>\r\n        <div class=\"d-flex justify-content-between\">\r\n          <h3 sxy-text=\"SALAXY.NG1.SigningComponent.authoritativeQuestions.previewAttorney\"></h3>\r\n          <div>\r\n            <small><a ng-href=\"{{ $ctrl.getPdfPreviewAddress() }}\" target=\"_blank\" sxy-text=\"SALAXY.NG1.SigningComponent.authoritativeQuestions.downloadPDF\"></a>&nbsp;&nbsp;</small>\r\n            <button ng-click=\"$ctrl.save()\" ng-disabled=\"!signingForm.$valid\" class=\"btn btn-primary\"\r\n              sxy-text=\"SALAXY.NG1.SigningComponent.authoritativeQuestions.updateForPreview\"></button>\r\n          </div>\r\n        </div>\r\n        <iframe id=\"preview-power-of-attorney-pdf\" ng-src=\"{{ $ctrl.getPdfPreviewAddress() }}\" class=\"w-100\"></iframe>\r\n      </div>\r\n    </form>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/account/UserInfo.html\",`﻿<div class=\"salaxy-component salaxy-user-info\">\r\n  <div class=\"d-flex flex-column flex-md-row\">\r\n    <salaxy-avatar class=\"avatar-xl mb-1 me-4\" avatar=\"$ctrl.session.currentCredential.avatar\"></salaxy-avatar>\r\n    <p class=\"lead\" sxy-html=\"SALAXY.NG1.UserInfoComponent.description.html\"></p>\r\n  </div>\r\n   \r\n  <div class=\"table-responsive\">\r\n    <table class=\"table\">\r\n      <tr>\r\n        <th colspan=\"2\">\r\n          <h3 sxy-text=\"SALAXY.NG1.UserInfoComponent.userNameTitle\"></h3>\r\n        </th>\r\n      </tr>\r\n      <tr>\r\n        <th sxy-text=\"SALAXY.NG1.UserInfoComponent.authType\" ps=\":\"></th>\r\n        <td>{{ 'AuthenticationMethod.' + $ctrl.session.currentCredential.authenticationMethod | sxyEnum }}</td>\r\n      </tr>\r\n      <tr>\r\n        <th sxy-text=\"SALAXY.NG1.UserInfoComponent.userName\" ps=\":\"></th>\r\n        <td>{{ $ctrl.session.currentCredential.id }}</td>\r\n      </tr>\r\n      <tr ng-if=\"$ctrl.session.currentCredential.authenticationMethod != 'salaxy' && $ctrl.session.currentCredential.authenticationMethod != 'x509'\">\r\n        <th sxy-text=\"SALAXY.NG1.UserInfoComponent.email\" ps=\":\"></th>\r\n        <td>{{ $ctrl.session.currentCredential.email }}</td>\r\n      </tr>\r\n      <tr>\r\n        <th sxy-text=\"SALAXY.NG1.UserInfoComponent.name\" ps=\":\"></th>\r\n        <td>{{ $ctrl.session.currentCredential.avatar.displayName }}</td>\r\n      </tr>\r\n    </table>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/2022/CalcEmployment.html\",`<div class=\"salaxy-component salaxy-calc-employment\">\r\n  <div ng-if=\"!$ctrl.current.worker.employmentId\" class=\"alert alert-danger\">\r\n    <strong>Error: Not supported</strong>\r\n    <p>Tämä komponentti ei tue uuden Työntekijän valintaa (implement EmploymentSelect)</p>\r\n  </div>\r\n  <div ng-if=\"$ctrl.current.worker.employmentId\">\r\n    <salaxy-form-group class=\"select-worker\" name=\"worker\" label=\"SALAXY.NG1_Pages.Calc.History.workerLabel\">\r\n      <!--\r\n        TODO: Need to create Employment relation selection component!\r\n        <button class=\"btn btn-default float-end\" ng-click=\"$ctrl.current.worker=null;todo()\">Vaihda...</button>\r\n      -->\r\n      <div class=\"salaxy-worker-item\">\r\n        <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" avatar=\"$ctrl.current.worker.avatar\"></salaxy-avatar>\r\n        <b>{{ $ctrl.current.worker.avatar.displayName }} ({{$ctrl.current.worker.paymentData.socialSecurityNumberValid}}) </b> <br />\r\n        <small>\r\n          <div>IBAN: {{ $ctrl.current.worker.paymentData.ibanNumber | sxyIban }}</div>\r\n        </small>\r\n      </div>\r\n    </salaxy-form-group>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/2022/CalcRowsEditor.html\",`<div class=\"salaxy-component salaxy-calc-rows-editor salaxy-calc-rows-2022-editor\" ng-switch=\"$ctrl.type\">\r\n  <div ng-switch-when=\"salary-defaults\" class=\"salaxy-calc-rows-editor-worktime-import\">\r\n    <!-- TODO: Will be replaced by new row type editors -->\r\n    <table class=\"table table-sm align-middle\">\r\n      <thead>\r\n        <tr>\r\n          <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.action\"></th>\r\n          <th colspan=\"2\">{{ $ctrl.title | sxyTranslate }}</th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.DateRange.labelStartAndEndDate\"></th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.totals.total\"></th>\r\n          <th></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.filteredList track by $index\">\r\n          <td style=\"width: 25%;\">\r\n            <salaxy-input-enum type=\"select\" label-type=\"plain\" ng-model=\"row.source\"\r\n              filter=\"{{$ctrl.rowSources}}\" hidden-options=\"''\"\r\n              name=\"{{ 'source' + $index }}\" enum=\"CalculationRowSource\"></salaxy-input-enum>\r\n          </td>\r\n          <td style=\"width: 32px;\">\r\n            <salaxy-avatar ng-if=\"row.rowType\" class=\"salaxy-calc-row-type-avatar\"\r\n              avatar=\"{ color: $ctrl.getConfig(row).color, initials: $ctrl.getConfig(row).iconText, entityType: 'company' }\"></salaxy-avatar>\r\n          </td>\r\n          <td style=\"width: 40%;\">\r\n            <div>{{row.message || ( \"CalculationRowType.\" + row.rowType | sxyEnum) }}</div>\r\n            <div ng-if=\"row.count && row.count != 1\"><small class=\"text-muted\">{{row.count | sxyCount : row.unit }} * {{ row.price | currency }}</small></div>\r\n            <small class=\"\" ng-if=\"$ctrl.getValidation(row).type == 'default'\">\r\n              {{ $ctrl.getValidation(row).msg | sxyTranslate }}\r\n            </small>\r\n            <span ng-if=\"$ctrl.getValidation(row).type == 'error'\">\r\n              <span class=\"label label-danger\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.validation.note\"></span>\r\n              <small class=\"alert-danger\">{{ $ctrl.getValidation(row).msg | sxyTranslate }}\r\n                <a href=\"\" ng-click=\"$ctrl.showEdit(row, 'auto')\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.validation.edit\" ps=\"...\"></a>\r\n              </small>\r\n            </span>\r\n          </td>\r\n          <td class=\"right\">\r\n            <div>{{ row.period | sxyDateRange }}&nbsp;&nbsp;</div>\r\n          </td>\r\n          <td style=\"width: 32px;\">\r\n            <div class=\"float-end\">{{ $ctrl.getRowTotal(row) | currency }}</div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <button type=\"button\" class=\"edit btn btn-info\" ng-click=\"$ctrl.showEdit(row, 'auto')\"\r\n              title=\"{{'SALAXY.NG1.CalcRowsComponent.editor.buttons.infoIcon' | sxyTranslate}}\">\r\n              <i class=\"bi bi-info-circle-fill\" ng-class=\"$ctrl.current == row ? 'bi-arrow-right-circle-fill' : 'bi-info-circle'\"></i></button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n    <ng-transclude ng-transclude-slot=\"footer\">\r\n      <footer>\r\n        <p><b>{{'SALAXY.NG1.CalcRowsComponent.editor.addNewRow' | sxyTranslate}}:</b></p>\r\n        <table>\r\n          <tbody>\r\n            <tr>\r\n              <td style=\"width: 40%;\">\r\n                <salaxy-input-enum type=\"select\" label-type=\"plain\" ng-model=\"$ctrl.newRow.source\"\r\n                  filter=\"{{$ctrl.rowSources}}\" hidden-options=\"''\"\r\n                  name=\"newRowSource\" enum=\"CalculationRowSource\"></salaxy-input-enum>\r\n              </td>\r\n              <td style=\"width: 40%;\">\r\n                <salaxy-calc-row-type name=\"newRowType\" model=\"$ctrl.newRow\" placeholder=\"SALAXY.NG1.CalcRowsComponent.editor.calcRowTypePlaceholder\"\r\n                  on-row-changed=\"$ctrl.commitNewRow(true)\" row-types=\"$ctrl.rowTypes\" categories=\"$ctrl.categories\"></salaxy-calc-row-type>\r\n              </td>\r\n              <td>\r\n                <button type=\"button\" class=\"btn btn-default w-100\" ng-click=\"$ctrl.showRowTypeSelectionDialog()\"><i class=\"bi bi-info-circle-fill text-primary me-2\"></i> <span\r\n                    sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.buttons.readMore\" ps=\"...\"></span></button>\r\n              </td>\r\n            </tr>\r\n          </tbody>\r\n        </table>\r\n      </footer>\r\n    </ng-transclude>\r\n  </div>\r\n  <div ng-switch-when=\"salary-defaults-temp2\" class=\"salaxy-calc-rows-editor-worktime-import\">\r\n    <!-- TODO: Will be replaced by new row type editors -->\r\n    <table class=\"table table-condensed\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\">{{ $ctrl.title | sxyTranslate }}</th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.DateRange.labelStartAndEndDate\"></th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.totals.total\"></th>\r\n          <th></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.filteredList track by $index\">\r\n          <td style=\"width: 32px;\">\r\n            <salaxy-avatar ng-if=\"row.rowType\" class=\"salaxy-calc-row-type-avatar\"\r\n              avatar=\"{ color: $ctrl.getConfig(row).color, initials: $ctrl.getConfig(row).iconText, entityType: 'company' }\"></salaxy-avatar>\r\n          </td>\r\n          <td style=\"width: 40%;\">\r\n            <div>{{row.message || ( \"CalculationRowType.\" + row.rowType | sxyEnum) }}</div>\r\n            <div ng-if=\"row.count && row.count != 1\"><small class=\"text-muted\">{{row.count | sxyCount : row.unit }} * {{ row.price | currency }}</small></div>\r\n            <small class=\"\" ng-if=\"$ctrl.getValidation(row).type == 'default'\">\r\n              {{ $ctrl.getValidation(row).msg | sxyTranslate }}\r\n            </small>\r\n            <span ng-if=\"$ctrl.getValidation(row).type == 'error'\">\r\n              <span class=\"label label-danger\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.validation.note\"></span>\r\n              <small class=\"alert-danger\">{{ $ctrl.getValidation(row).msg | sxyTranslate }}\r\n                <a href=\"\" ng-click=\"$ctrl.showEdit(row, 'auto')\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.validation.edit\" ps=\"...\"></a>\r\n              </small>\r\n            </span>\r\n          </td>\r\n          <td class=\"right\">\r\n            <div>{{ row.period | sxyDateRange }}&nbsp;&nbsp;</div>\r\n          </td>\r\n          <td style=\"width: 32px;\">\r\n            <div class=\"float-end\">{{ $ctrl.getRowTotal(row) | currency }}</div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <button type=\"button\" class=\"edit btn btn-info\" ng-click=\"$ctrl.showEdit(row, 'auto')\"\r\n              title=\"{{'SALAXY.NG1.CalcRowsComponent.editor.buttons.infoIcon' | sxyTranslate}}\">\r\n              <i class=\"bi bi-info-circle-fill\" ng-class=\"$ctrl.current == row ? 'bi-arrow-right-circle-fill' : 'bi-info-circle'\"></i></button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n    <ng-transclude ng-transclude-slot=\"footer\">\r\n      <footer>\r\n        <table>\r\n          <tbody>\r\n            <tr>\r\n              <td><b>{{'SALAXY.NG1.CalcRowsComponent.editor.addNewRow' | sxyTranslate}}:</b></td>\r\n              <td>\r\n                <salaxy-calc-row-type name=\"newRowType\" model=\"$ctrl.newRow\" placeholder=\"SALAXY.NG1.CalcRowsComponent.editor.calcRowTypePlaceholder\"\r\n                  on-row-changed=\"$ctrl.commitNewRow(true)\" row-types=\"$ctrl.rowTypes\" categories=\"$ctrl.categories\" clear-on-select=\"true\"></salaxy-calc-row-type>\r\n              </td>\r\n              <td>\r\n                <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showRowTypeSelectionDialog()\"><i class=\"bi bi-info-circle-fill text-primary me-2\"></i> <span\r\n                    sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.buttons.readMore\" ps=\"...\"></span></button>\r\n              </td>\r\n            </tr>\r\n          </tbody>\r\n        </table>\r\n      </footer>\r\n    </ng-transclude>\r\n  </div>\r\n  <div ng-switch-when=\"worktime-import\" class=\"salaxy-calc-rows-editor-worktime-import\">\r\n    <table class=\"table table-condensed\">\r\n      <thead>\r\n        <tr>\r\n          <th sxy-text=\"SALAXY.NG1.ImportStagingCalcRowsEditorComponent.validation\"></th>\r\n          <th colspan=\"2\">\r\n            <div sxy-text=\"SALAXY.NG1.ImportStagingCalcRowsEditorComponent.employmentId\"></div>\r\n            <div sxy-text=\"SALAXY.NG1.ImportStagingCalcRowsEditorComponent.personalId\"></div>\r\n          </th>\r\n          <th colspan=\"2\">{{ $ctrl.title | sxyTranslate }}</th>\r\n          <th>\r\n            <div sxy-text=\"SALAXY.NG1.ImportStagingCalcRowsEditorComponent.rowType\"></div>\r\n            <div sxy-text=\"SALAXY.NG1.ImportStagingCalcRowsEditorComponent.kind\"></div>\r\n          </th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.totals.total\"></th>\r\n          <th></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.filteredList track by $index\">\r\n          <td ng-if=\"row.validation.isValid\">\r\n            <div class=\"text-success\"><b>{{\"SALAXY.UI_Terms.ok\" | sxyTranslate}}</b></div>\r\n          </td>\r\n          <td ng-if=\"row.validation.isValid == null\">\r\n            <div class=\"text-muted\" sxy-text=\"SALAXY.NG1.ImportStagingCalcRowsEditorComponent.noValidation\"></div>\r\n          </td>\r\n          <td ng-if=\"row.validation.isValid === false\">\r\n            <div class=\"text-danger\"><salaxy-validation-summary api-validation=\"row.validation\" layout=\"minimal\"></salaxy-validation-summary></div>\r\n          </td>\r\n          <td style=\"width: 32px;\">\r\n            <salaxy-avatar class=\"salaxy-calc-row-type-avatar\"\r\n              avatar=\"row.$avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td ng-if=\"row.$avatar\">\r\n            <div>{{ row.$avatar.sortableName }}</div>\r\n            <div>{{ row.personalId || \"-\" }} ({{ row.employmentType || \"-\" }})</div>\r\n          </td>\r\n          <td ng-if=\"!row.$avatar\">\r\n            <div>{{ row.employmentId || \"-\" }}</div>\r\n            <div>{{ row.personalId || \"-\" }} ({{ row.employmentType || \"-\" }})</div>\r\n          </td>\r\n          <td style=\"width: 32px;\">\r\n            <salaxy-avatar ng-if=\"row.rowType\" class=\"salaxy-calc-row-type-avatar\"\r\n              avatar=\"{ color: $ctrl.getConfig(row).color, initials: $ctrl.getConfig(row).iconText, entityType: 'company' }\"></salaxy-avatar>\r\n          </td>\r\n          <td>\r\n            <div>{{row.message || ( \"CalculationRowType.\" + row.rowType | sxyEnum) }}</div>\r\n            <div ng-if=\"row.count && row.count != 1\"><small class=\"text-muted\">{{row.count | sxyCount : row.unit }} * {{ row.price | currency }}</small></div>\r\n            <small class=\"\" ng-if=\"$ctrl.getValidation(row).type == 'default'\">\r\n              {{ $ctrl.getValidation(row).msg | sxyTranslate }}\r\n            </small>\r\n            <span ng-if=\"$ctrl.getValidation(row).type == 'error'\">\r\n              <span class=\"label label-danger\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.validation.note\"></span>\r\n              <small class=\"alert-danger\">{{ $ctrl.getValidation(row).msg | sxyTranslate }}\r\n                <a href=\"\" ng-click=\"$ctrl.showEdit(row, 'auto')\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.validation.edit\" ps=\"...\"></a>\r\n              </small>\r\n            </span>\r\n          </td>\r\n          <td>\r\n            <div>{{ (\"CalculationRowType.\" + row.rowType | sxyEnum ) || \"-\" }}</div>\r\n            <div>{{ row.data.kind || \"-\" }}</div>\r\n          </td>\r\n          <td>\r\n            <div class=\"float-end\">{{ $ctrl.getRowTotal(row) | currency }}</div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <button type=\"button\" class=\"edit btn btn-info\" ng-click=\"$ctrl.showEdit(row, 'auto')\"\r\n              title=\"{{'SALAXY.NG1.CalcRowsComponent.editor.buttons.infoIcon' | sxyTranslate}}\">\r\n              <i class=\"bi bi-info-circle-fill\" ng-class=\"$ctrl.current == row ? 'bi-arrow-right-circle-fill' : 'bi-info-circle'\"></i></button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <div ng-switch-when=\"worktime-import-employment\" class=\"salaxy-calc-rows-editor-worktime-import\">\r\n    <table class=\"table table-condensed\">\r\n      <thead>\r\n        <tr>\r\n          <th sxy-text=\"SALAXY.NG1.ImportStagingCalcRowsEditorComponent.validation\"></th>\r\n          <th class=\"right\">\r\n            <div sxy-text=\"SALAXY.NG1.ImportStagingCalcRowsEditorComponent.period\"></div>\r\n            <div sxy-text=\"SALAXY.NG1.ImportStagingCalcRowsEditorComponent.status\"></div>\r\n          </th>\r\n          <th colspan=\"2\">{{ $ctrl.title | sxyTranslate }}</th>\r\n          <th>\r\n            <div sxy-text=\"SALAXY.NG1.ImportStagingCalcRowsEditorComponent.rowType\"></div>\r\n            <div sxy-text=\"SALAXY.NG1.ImportStagingCalcRowsEditorComponent.kind\"></div>\r\n          </th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.totals.total\"></th>\r\n          <th></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.filteredList track by $index\">\r\n          <td ng-if=\"row.validation.isValid\">\r\n            <div class=\"text-success\">\r\n              <b>OK</b>\r\n              <a ng-href=\"{{ '#/payroll/details/' + row.data.payrollId }}\" ng-if=\"row.data.payrollId\">{{'SALAXY.NG1.ImportStagingCalcRowsEditorComponent.payroll' | sxyTranslate}}</a>\r\n            </div>\r\n            <div ng-if=\"row.data.originalPayrollId\" style=\"padding-left: 22px;\">\r\n              <a ng-href=\"{{ '#/payroll/details/' + row.data.originalPayrollId }}\" ng-if=\"row.data.originalPayrollId\">{{'SALAXY.NG1.ImportStagingCalcRowsEditorComponent.originalPayroll' | sxyTranslate}}</a>\r\n            </div>\r\n          </td>\r\n          <td ng-if=\"row.validation.isValid == null\">\r\n            <div class=\"text-muted\" sxy-text=\"SALAXY.NG1.ImportStagingCalcRowsEditorComponent.noValidation\"></div>\r\n          </td>\r\n          <td ng-if=\"row.validation.isValid === false\">\r\n            <div class=\"text-danger\"><salaxy-validation-summary api-validation=\"row.validation\" layout=\"minimal\"></salaxy-validation-summary></div>\r\n          </td>\r\n          <td class=\"right\" ng-switch=\"row.status\">\r\n            <div>{{ row.period | sxyDateRange }}</div>\r\n            <div ng-switch-when=\"preview\" class=\"text-warning\"><b>{{\"SALAXY.NG1.ImportStagingCalcRowsEditorComponent.rowStatuses.preview\" | sxyTranslate}}</b></div>\r\n            <div ng-switch-when=\"new\" class=\"text-primary\"><b>{{\"SALAXY.NG1.ImportStagingCalcRowsEditorComponent.rowStatuses.new\" | sxyTranslate}}</b></div>\r\n            <div ng-switch-when=\"deleted\" class=\"text-danger\"><s>{{\"SALAXY.NG1.ImportStagingCalcRowsEditorComponent.rowStatuses.deleted\" | sxyTranslate}}</s></div>\r\n            <div ng-switch-when=\"error\" class=\"text-danger\"><b>{{\"SALAXY.NG1.ImportStagingCalcRowsEditorComponent.rowStatuses.error\" | sxyTranslate}}</b></div>\r\n            <div ng-switch-when=\"committed\" class=\"text-success\"><b>{{\"SALAXY.NG1.ImportStagingCalcRowsEditorComponent.rowStatuses.committed\" | sxyTranslate}}</b></div>\r\n            <div ng-switch-when=\"ignored\" class=\"text-muted\"><s>{{\"SALAXY.NG1.ImportStagingCalcRowsEditorComponent.rowStatuses.ignored\" | sxyTranslate}}</s></div>\r\n            <div ng-switch-when=\"edited\" class=\"text-primary\">{{\"SALAXY.NG1.ImportStagingCalcRowsEditorComponent.rowStatuses.edited\" | sxyTranslate}}</div>\r\n            <div ng-switch-default>{{ row.status }}</div>\r\n          </td>\r\n          <td style=\"width: 32px;\">\r\n            <salaxy-avatar ng-if=\"row.rowType\" class=\"salaxy-calc-row-type-avatar\"\r\n              avatar=\"{ color: $ctrl.getConfig(row).color, initials: $ctrl.getConfig(row).iconText, entityType: 'company' }\"></salaxy-avatar>\r\n          </td>\r\n          <td>\r\n            <div>{{row.message || ( \"CalculationRowType.\" + row.rowType | sxyEnum) }}</div>\r\n            <div ng-if=\"row.count && row.count != 1\"><small class=\"text-muted\">{{row.count | sxyCount : row.unit }} * {{ row.price | currency }}</small></div>\r\n            <small class=\"\" ng-if=\"$ctrl.getValidation(row).type == 'default'\">\r\n              {{ $ctrl.getValidation(row).msg | sxyTranslate }}\r\n            </small>\r\n            <span ng-if=\"$ctrl.getValidation(row).type == 'error'\">\r\n              <span class=\"label label-danger\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.validation.note\"></span>\r\n              <small class=\"alert-danger\">{{ $ctrl.getValidation(row).msg | sxyTranslate }}\r\n                <a href=\"\" ng-click=\"$ctrl.showEdit(row, 'auto')\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.validation.edit\" ps=\"...\"></a>\r\n              </small>\r\n            </span>\r\n          </td>\r\n          <td>\r\n            <div>{{ (row.rowType || 'unknown') == \"unknown\" ? \"-\" : (\"CalculationRowType.\" + row.rowType | sxyEnum) }}</div>\r\n            <div>{{ row.data.kind || \"-\" }}</div>\r\n          </td>\r\n          <td>\r\n            <div class=\"float-end\">{{ $ctrl.getRowTotal(row) ? ($ctrl.getRowTotal(row) | currency) : \"-\" }}</div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <input type=\"checkbox\" ng-model=\"row.data.isSelected\" ng-if=\"$ctrl.showRowSelection\" style=\"margin-right: 8px;margin-top: 10px;\" />\r\n            <button type=\"button\" class=\"edit btn btn-info\" ng-click=\"$ctrl.showEdit(row, 'auto')\"\r\n              title=\"{{'SALAXY.NG1.CalcRowsComponent.editor.buttons.infoIcon' | sxyTranslate}}\">\r\n              <i class=\"bi bi-info-circle-fill\" ng-class=\"$ctrl.current == row ? 'bi-arrow-right-circle-fill' : 'bi-info-circle'\"></i></button>\r\n            <salaxy-json-formatter key=\"'js'\" json=\"row\" open=\"2\" type=\"dialog\" btn-class=\"btn btn-default\" ></salaxy-json-formatter>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <div ng-switch-default class=\"row\">\r\n    <div class=\"col-sm-6\">\r\n      <table class=\"table table-sm\">\r\n        <thead>\r\n          <tr>\r\n            <th colspan=\"2\" class=\"uppercase\">{{ $ctrl.title || ('SALAXY.NG1.CalcRowsComponent.editor.calcRow' | sxyTranslate) }}</th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.totals.total\"></th>\r\n            <th></th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr ng-repeat=\"row in $ctrl.filteredList track by $index\">\r\n            <td width=\"42px\">\r\n              <salaxy-avatar ng-if=\"row.rowType\" class=\"salaxy-calc-row-type-avatar\"\r\n                avatar=\"{ color: $ctrl.getConfig(row).color, initials: $ctrl.getConfig(row).iconText, entityType: 'company' }\"></salaxy-avatar>\r\n            </td>\r\n            <td width=\"100%\">\r\n              <div class=\"float-end\">{{ $ctrl.getRowTotal(row) | currency }}</div>\r\n              <div>{{row.message || ( \"CalculationRowType.\" + row.rowType | sxyEnum) }}</div>\r\n              <div ng-if=\"row.count && row.count != 1\"><small class=\"text-muted\">{{row.count | sxyCount : row.unit }} * {{ row.price | currency }}</small></div>\r\n              <small class=\"\" ng-if=\"$ctrl.getValidation(row).type == 'default'\">\r\n                {{ $ctrl.getValidation(row).msg | sxyTranslate }}\r\n              </small>\r\n              <span ng-if=\"$ctrl.getValidation(row).type == 'error'\">\r\n                <span class=\"label label-danger\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.validation.note\"></span>\r\n                <small class=\"alert-danger\">{{ $ctrl.getValidation(row).msg | sxyTranslate }}\r\n                  <a href=\"\" ng-click=\"$ctrl.showEdit(row, 'auto')\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.validation.edit\" ps=\"...\"></a>\r\n                </small>\r\n              </span>\r\n            </td>\r\n            <td class=\"right\">\r\n              <button type=\"button\" class=\"edit btn btn-info\" ng-click=\"$ctrl.showEdit(row, 'auto')\"\r\n                title=\"{{'SALAXY.NG1.CalcRowsComponent.editor.buttons.infoIcon' | sxyTranslate}}\">\r\n                <i class=\"bi bi-info-circle-fill\" ng-class=\"$ctrl.current == row ? 'bi-arrow-right-circle-fill' : 'bi-info-circle'\"></i></button>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n      <ng-transclude ng-transclude-slot=\"footer\">\r\n        <footer>\r\n          <p><b>{{'SALAXY.NG1.CalcRowsComponent.editor.addNewRow' | sxyTranslate}}:</b></p>\r\n          <table>\r\n            <tbody>\r\n              <tr>\r\n                <td style=\"width: 100%;\">\r\n                  <salaxy-calc-row-type name=\"newRowType\" model=\"$ctrl.newRow\" placeholder=\"SALAXY.NG1.CalcRowsComponent.editor.calcRowTypePlaceholder\"\r\n                    on-row-changed=\"$ctrl.commitNewRow(true)\" row-types=\"$ctrl.rowTypes\" categories=\"$ctrl.categories\"></salaxy-calc-row-type>\r\n                </td>\r\n                <td>\r\n                  <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showRowTypeSelectionDialog()\"><i class=\"bi bi-info-circle-fill text-primary me-2\"></i> <span\r\n                      sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.buttons.readMore\" ps=\"...\"></span></button>\r\n                </td>\r\n              </tr>\r\n            </tbody>\r\n          </table>\r\n        </footer>\r\n      </ng-transclude>\r\n    </div>\r\n    <div class=\"col-sm-6 d-none d-sm-block salaxy-calc-rows-editor-details-container\">\r\n      <ng-include ng-if=\"$ctrl.current\" src=\"'salaxy-components/calc/rows/CalcRows2019EditDialog.html'\"></ng-include>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/2022/CalcUsecase.html\",`<div class=\"salaxy-component salaxy-calc-usecase\" ng-controller=\"NaviController as $naviCtrl\">\r\n\r\n  <salaxy-spinner ng-if=\"$ctrl.isLoading\"></salaxy-spinner>\r\n  <div class=\"btn-toolbar calc-toolbar\" ng-if=\"$ctrl.current\">\r\n    <div class=\"btn-group dropdown\" ng-if=\"$ctrl.current.worker.employmentId\">\r\n      <button id=\"workerBtn\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\">\r\n        <salaxy-avatar avatar=\"$ctrl.current.worker.avatar\" style=\"font-size: 2em; margin: -5px 5px -5px -10px; width: 1em; height: 1em;\"></salaxy-avatar>  \r\n        {{ $ctrl.current.worker.avatar.displayName }}\r\n      </button>\r\n      <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"workerBtn\">\r\n        \r\n        <li role=\"menuitem\"><a href=\"\" ng-click=\"$ctrl.isWorkerInfoOpen = true\" data-bs-toggle=\"collapse\" data-bs-target=\"#workerInfo\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.CalcUsecase.showAdditionalInfo\"></a></li>\r\n        <li role=\"menuitem\"><a href=\"\" ng-click=\"$ctrl.showWorkerEditDialog()\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.CalcUsecase.editWorker\"></a></li>\r\n        <li role=\"menuitem\"><a href=\"\" ng-click=\"$ctrl.showRefreshAutoTaxcardDialog()\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.CalcUsecase.checkAutomaticTaxCard\"></a></li>\r\n      </ul>\r\n    </div>\r\n   \r\n    <div class=\"ms-auto d-flex calc-actions flex-wrap\" ng-if=\"$ctrl.current.worker.employmentId && !$ctrl.usecases\">\r\n      <salaxy-calc-sharing-receipt-action ng-if=\"$ctrl.showAction('reject')\" button-class=\"btn btn-danger\" model=\"$ctrl\" type=\"'reject'\"></salaxy-calc-sharing-receipt-action>\r\n      <salaxy-calc-sharing-receipt-action ng-if=\"$ctrl.showAction('approve')\"  button-class=\"btn btn-success\" model=\"$ctrl\" type=\"'approve'\"></salaxy-calc-sharing-receipt-action>\r\n      <button ng-if=\"$ctrl.showAction('save')\" ng-disabled=\"$ctrl.isActionDisabled('save')\" type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.save()\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n      <salaxy-pay-button ng-if=\"$ctrl.showAction('pay')\" model=\"$ctrl.current\" mode=\"pay-button\" style=\"display: inline-block\" ng-ref=\"$payButton\" disabled=\"!$payButton.isChannelDefined\"></salaxy-pay-button>\r\n      <salaxy-pay-button ng-if=\"$ctrl.showAction('pay')\" model=\"$ctrl.current\" mode=\"channel-select\" style=\"display: inline-block\"></salaxy-pay-button>\r\n    \r\n      <div class=\"btn-group dropdown\">\r\n        <button id=\"actionsBtn\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\">\r\n          <i class=\"bi bi-three-dots\"></i>\r\n        </button>\r\n        <ul class=\"dropdown-menu dropdown-menu-end\" role=\"menu\" aria-labelledby=\"actionsBtn\">\r\n          <li role=\"menuitem\" ng-if=\"$ctrl.showAction('recalculate')\">\r\n            <a href=\"\" ng-click=\"$ctrl.recalculate()\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.CalcUsecase.recalculate\"></a>\r\n          </li>\r\n          <li role=\"menuitem\"><a href=\"\" ng-click=\"$ctrl.showReportDialog('salarySlip')\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.CalcUsecase.reports\" ps=\"...\"></a></li>\r\n          <li role=\"menuitem\"><a href=\"\" ng-click=\"$ctrl.showUsecaseInfo()\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.CalcUsecase.usecase\"></a></li>\r\n          \r\n          <li role=\"menuitem\" ng-if=\"$ctrl.showAction('cancel')\">\r\n            <a href=\"\" ng-click=\"$ctrl.cancel()\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.CalcUsecase.cancelPayment\"></a>\r\n          </li>\r\n          <li role=\"menuitem\" ng-if=\"$ctrl.showAction('copyAsNew')\">\r\n            <a href=\"\" ng-click=\"$ctrl.showCopyAsNew($ctrl.current)\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.CalcUsecase.copy\"></a>\r\n          </li>\r\n          <li role=\"menuitem\" ng-if=\"$ctrl.showAction('showPaymentDialog')\">\r\n            <a href=\"\" ng-click=\"$ctrl.showPaymentDialog()\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.CalcUsecase.showPaymentInfo\"></a>\r\n          </li>\r\n\r\n          <li role=\"menuitem\" ng-if=\"$ctrl.showAction('delete')\">\r\n            <a href=\"\" ng-click=\"$ctrl.delete()\" ng-disabled=\"$ctrl.isActionDisabled('delete')\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.CalcUsecase.deleteCalc\"></a>\r\n          </li>\r\n          <li role=\"menuitem\" style=\"margin: 5px 20px;\">\r\n            <salaxy-json-formatter key=\"'JSON Data'\" json=\"$ctrl.current\" open=\"2\" type=\"dialog\"></salaxy-json-formatter>\r\n          </li>\r\n        </ul>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  \r\n  <div class=\"worker-info-wrapper collapse\" id=\"workerInfo\">\r\n    <button class=\"btn btn-transparent close-btn btn-sm\" data-bs-toggle=\"collapse\" data-bs-target=\"#workerInfo\"><i class=\"bi bi-x-lg\"></i></button>\r\n    <salaxy-calc-worker-info model=\"$ctrl.current\"></salaxy-calc-worker-info>\r\n  </div>\r\n  <div ng-if=\"$ctrl.usecases\">\r\n    <h2 sxy-text=\"SALAXY.NG1.CalcUsecase.selectCalculationType\" class=\"mt-3\"></h2>\r\n    <div class=\"row g-4\">\r\n      <div class=\"col-sm-6 col-md-4\" ng-repeat=\"usecase in $ctrl.usecases\">\r\n        <div class=\"card\">\r\n          <div class=\"text-center  card-pic-fixed clickable\" style=\"height: 150px;position: relative;\" ng-click=\"$ctrl.setUsecase(usecase.uri)\">\r\n            <img ng-if=\"usecase.data.icon[0] == 'h'\" ng-src=\"{{usecase.data.icon}}\">\r\n            <div ng-if=\"usecase.data.icon[0] != 'h'\" class=\"bg-primary card-pic-icon\">\r\n              <i class=\"fa\" ng-class=\"(usecase.data.icon || 'fa') == 'fa' ? 'bi-currency-euro' : usecase.data.icon\" aria-hidden=\"true\"></i>\r\n            </div>\r\n            <span class=\"badge float-end bg-info\" ng-if=\"usecase.status=='default'\" sxy-text=\"SALAXY.NG1.CalcUsecase.default\"></span>\r\n            <salaxy-avatar avatar=\"usecase.ownerInfo.avatar\" style=\"font-size: 2em; position: absolute; right: 10px; bottom: 10px\"></salaxy-avatar>\r\n          </div>\r\n          <div class=\"card-body p-3\">\r\n            <h3 class=\"truncate\">{{ usecase.shortText }}</h3>\r\n            <p style=\"height: 80px;overflow: hidden\">{{ usecase.data.description }}</p>\r\n            <button type=\"button\" class=\"btn btn-primary mb-2\" ng-click=\"$ctrl.setUsecase(usecase.uri)\" sxy-text=\"SALAXY.UI_Terms.select\"></button>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div ng-if=\"$ctrl.current && !$ctrl.usecases\">\r\n    \r\n    <div ng-if=\"!$ctrl.usecase.defaultView\" style=\"margin-top: 6px\">\r\n      <salaxy-calc model=\"$ctrl\"></salaxy-calc>\r\n    </div>\r\n    <div ng-if=\"$ctrl.usecase.defaultView\">\r\n      <div ng-if=\"!$ctrl.current.worker.employmentId\">\r\n        <div class=\"row\">\r\n          <div class=\"col-12 col-sm-7\">\r\n            <div class=\"intro-text\">\r\n              <h1 sxy-text=\"SALAXY.NG1.CalcDetailsWorkerComponent.selectWorker\"></h1>\r\n              <p sxy-html=\"SALAXY.NG1.CalcDetailsWorkerComponent.myWorkers.description.html\"></p>\r\n            </div>\r\n          </div>\r\n          <div class=\"col-12 col-sm-5\">\r\n            <button type=\"button\" class=\"btn add-new-worker btn-primary float-end-sm\" style=\"margin-bottom:5px;\" ng-click=\"$ctrl.showNewWorkerDialog()\" sxy-text=\"SALAXY.NG1.CalcDetailsWorkerComponent.newWorker.cta\"></button>\r\n          </div>\r\n          <div class=\"col-12\">\r\n            <div class=\"table-responsive\">\r\n              <salaxy-employment-list mode=\"select\" on-list-select=\"$ctrl.updateFromEmployment(item.id, true)\"></salaxy-employment-list>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div>\r\n        \r\n        <ng-include src=\"$ctrl.usecase.defaultView\"></ng-include>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/Calc.html\",`<div class=\"salaxy-component salaxy-calc\">\r\n  <div class=\"salaxy-calc-overview\" ng-if=\"!$ctrl.current\">\r\n    <salaxy-spinner ng-if=\"$ctrl.isLoading\"></salaxy-spinner>\r\n  </div>\r\n\r\n  <!--salaxy-varma-banner calc=\"$ctrl.current\" ng-if=\"('auth' | sxyIsInRole) && ('company' | sxyIsInRole) && $ctrl.current.workflow.status == 'draft'\"></salaxy-varma-banner-->\r\n  <div class=\"row\" sxy-if-role=\"worker\">\r\n    <div class=\"col-12 mb-2\" ng-if=\"$ctrl.current.workflow.status == 'draft' || $ctrl.current.id == null\">\r\n      <p class=\"lead text-center\" sxy-text=\"SALAXY.NG1.CalcComponent.introWorker\"></p>\r\n    </div>\r\n  </div>\r\n  <div ng-if=\"!$ctrl.isReadOnly && $ctrl.current\" class=\"btn-toolbar calc-toolbar w-100\">\r\n    <div class=\"btn-group\" role=\"group\" ng-if=\"!$ctrl.isReadOnly\">\r\n      <div ng-if=\"'company' | sxyIsInRole\" ng-controller=\"CompanyAccountController as $company\" style=\"padding: 8px;\">\r\n        <salaxy-workflow-badge ng-if=\"$company.current\" mode=\"horizontal\" model=\"$company.current\" api-ctrl=\"$company\" wf-types=\"'EmployerMessageRecord'\"></salaxy-workflow-badge>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div class=\"salaxy-calc-overview\" ng-if=\"$ctrl.current\">\r\n    <div sxy-if-role=\"worker\" class=\"visible-xxs\">\r\n      <div class=\"mb-2\" ng-if=\"$ctrl.current.workflow.status == 'draft' || $ctrl.current.workflow.status == 'workerRequested' || $ctrl.current.workflow.status == 'workerRequestAccepted' || $ctrl.current.workflow.status == 'workerRequestDeclined' || $ctrl.current.workflow.status == 'paymentWorkerCopy'\">\r\n        <salaxy-calc-sharing-info model=\"$ctrl\"></salaxy-calc-sharing-info>\r\n      </div>\r\n    </div>\r\n    <div class=\"calc-container\" style=\"display:block;\">\r\n      <div class=\"salaxy-calc-step-container step1\" ng-class=\"{ 'active': $ctrl.calcSections.get('worker').isActive }\">\r\n        <div class=\"card overview-worker salaxy-calc-overview-card\">\r\n          <div class=\"card-header\" ng-click=\"$ctrl.calcSections.toggleActive('worker')\">\r\n            <i class=\"bi bi-x-lg float-end close\"></i> <span class=\"overview-title\" sxy-text=\"SALAXY.NG1.CalcComponent.panelWorker.heading\"></span>\r\n          </div>\r\n          <div class=\"card-body\">\r\n            <div class=\"content-overview\" ng-click=\"$ctrl.calcSections.toggleActive('worker')\">\r\n              <div ng-if=\"!$ctrl.calcSections.get('worker').isSelectionDone\">\r\n                <a href=\"\">\r\n                  <h3 class=\"text-center\" sxy-html=\"SALAXY.NG1.CalcComponent.panelWorker.overview.html\"></h3>\r\n                </a>\r\n              </div>\r\n              <div class=\"salaxy-calc-overview-worker h-100\" ng-if=\"$ctrl.calcSections.get('worker').isSelectionDone\">\r\n                <salaxy-avatar ng-if=\"$ctrl.current.worker.avatar.displayName\" avatar=\"$ctrl.current.worker.avatar\"></salaxy-avatar>\r\n                <strong>{{$ctrl.current.worker.avatar.displayName || (\"SALAXY.NG1.CalcComponent.panelWorker.noSelection\" | sxyTranslate) }}</strong><br />\r\n                <div ng-if=\"!$ctrl.isReadOnly\" ng-controller=\"EmploymentCrudController as $employment\"\r\n                  ng-init=\"$employment.queryResult={};$employment.getOData({ '$filter': 'id eq \\\\'' +  $ctrl.current.worker.employmentId + '\\\\''}, $employment.queryResult)\">\r\n                  <salaxy-workflow-badge mode=\"horizontal\" ng-if=\"$employment.queryResult.items.length > 0\" model=\"$employment.queryResult.items[0]\" api-ctrl=\"$employment\"\r\n                    wf-types=\"'EmployerMessageRecord'\"></salaxy-workflow-badge>\r\n                </div>\r\n                <div class=\"salaxy-calc-worker-info-texts\" ng-if=\"$ctrl.current.worker.avatar.displayName\">\r\n                  <div class=\"text-danger\" ng-if=\"$ctrl.taxUi.status == 'missing'\">\r\n                    {{ $ctrl.taxUi.shortText }}\r\n\r\n                  </div>\r\n                  <div ng-if=\"$ctrl.taxUi.status == 'ok'\">{{ $ctrl.taxUi.shortText }}</div>\r\n                  <div>{{ $ctrl.current.worker.paymentData.ibanNumber ? ('SALAXY.NG1.WorkerInfo.ibanOk'|sxyTranslate) : ('SALAXY.NG1.WorkerInfo.noIbanNumber' | sxyTranslate) }}\r\n                  </div>\r\n                  <div class=\"truncate\">{{ $ctrl.current.info.occupationCode | sxyOccupation : \"code-label\" }}</div>\r\n                  <div class=\"truncate\">{{ $ctrl.getPensionText(true) }}</div>\r\n                </div>\r\n              </div>\r\n            </div>\r\n            <div class=\"content-details\">\r\n              <div ng-if=\"!$ctrl.isReadOnly\" ng-controller=\"EmploymentCrudController as $employment\" class=\"text-end\" style=\"padding: 8px;\"\r\n                ng-init=\"$employment.queryResult={};$employment.getOData({ '$filter': 'id eq \\\\'' +  $ctrl.current.worker.employmentId + '\\\\''}, $employment.queryResult)\">\r\n                <salaxy-workflow-badge mode=\"horizontal\" ng-if=\"$employment.queryResult.items.length > 0\" model=\"$employment.queryResult.items[0]\" api-ctrl=\"$employment\"\r\n                  wf-types=\"'EmployerMessageRecord'\"></salaxy-workflow-badge>\r\n              </div>\r\n              <ng-include src=\"'salaxy-components/calc/details/worker.html'\"></ng-include>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div ng-if=\"$ctrl.isHousehold\" class=\"salaxy-calc-step-container step2\" ng-class=\"{ 'active': $ctrl.calcSections.get('household-usecase').isActive }\">\r\n        <div class=\"card card-warning salaxy-calc-overview-card\">\r\n          <div class=\"card-header\" ng-click=\"$ctrl.calcSections.toggleActive('household-usecase')\">\r\n            <i class=\"bi bi-x-lg float-end close\"></i><span class=\"overview-title\" sxy-text=\"SALAXY.NG1.CalcComponent.panelHouseHold.heading\"></span>\r\n          </div>\r\n          <div class=\"card-body\">\r\n            <div class=\"content-overview\" ng-click=\"$ctrl.calcSections.toggleActive('household-usecase')\">\r\n              <div ng-show=\"!$ctrl.calcSections.get('household-usecase').isSelectionDone\">\r\n                <a href=\"\">\r\n                  <h3 class=\"text-center\" sxy-html=\"SALAXY.NG1.CalcComponent.panelHouseHold.overview.html\"></h3>\r\n                </a>\r\n              </div>\r\n              <div ng-show=\"$ctrl.calcSections.get('household-usecase').isSelectionDone\">\r\n                <div>{{ $ctrl.getUsecaseText() | sxyTranslate}}</div>\r\n              </div>\r\n            </div>\r\n            <div class=\"content-details\">\r\n              <salaxy-calc-household-usecase ng-if=\"$ctrl.currentCalc\" calc=\"$ctrl.currentCalc\"></salaxy-calc-household-usecase>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div ng-if=\"!$ctrl.isHousehold\" class=\"salaxy-calc-step-container step2\" ng-class=\"{ 'active': $ctrl.calcSections.get('worktime').isActive }\">\r\n        <div class=\"card overview-worktime salaxy-calc-overview-card\">\r\n          <div class=\"card-header \" ng-click=\"$ctrl.calcSections.toggleActive('worktime');$ctrl.worktimeCtrl.loadEmployment()\">\r\n            <i class=\"bi bi-x-lg float-end close\"></i><span class=\"overview-title\" sxy-text=\"SALAXY.NG1.CalcComponent.panelWorkTime.heading\"></span>\r\n          </div>\r\n          <div class=\"card-body\">\r\n            <div class=\"content-overview\" ng-click=\"$ctrl.calcSections.toggleActive('worktime');$ctrl.worktimeCtrl.loadEmployment()\">\r\n              <div ng-show=\"!$ctrl.calcSections.get('worktime').isSelectionDone\">\r\n                <a href=\"\">\r\n                  <h3 class=\"text-center\" sxy-html=\"SALAXY.NG1.CalcComponent.panelWorkTime.overview.html\"></h3>\r\n                </a>\r\n              </div>\r\n              <div ng-show=\"$ctrl.calcSections.get('worktime').isSelectionDone\">\r\n                <div><strong>{{ $ctrl.getDatesRangeText() | sxyTranslate }}</strong></div>\r\n                <table>\r\n                  <tbody>\r\n                    <tr>\r\n                      <td sxy-text=\"SALAXY.NG1.CalcComponent.panelWorkTime.overview.salaryDate\"></td>\r\n                      <td class=\"right\" ng-if=\"!$ctrl.currentCalc.workflow.requestedSalaryDate\" sxy-text=\"SALAXY.NG1.CalcComponent.panelWorkTime.overview.now\"></td>\r\n                      <td class=\"right\" ng-if=\"$ctrl.currentCalc.workflow.requestedSalaryDate\">{{ $ctrl.currentCalc.workflow.salaryDate | sxyDate }}</td>\r\n                    </tr>\r\n                  </tbody>\r\n                </table>\r\n                <table>\r\n                  <tbody>\r\n                    <tr>\r\n                      <td sxy-text=\"SALAXY.NG1.CalcComponent.panelWorkTime.overview.leavesDays\"></td>\r\n                      <td class=\"right\">{{ $ctrl.calculatePeriodDays('leavesDays') | sxyCount : 'day' }}</td>\r\n                    </tr>\r\n                    <tr>\r\n                      <td sxy-text=\"SALAXY.NG1.CalcComponent.panelWorkTime.overview.absencesDays\"></td>\r\n                      <td class=\"right\">{{ $ctrl.calculatePeriodDays('absencesDays') | sxyCount : 'day' }}</td>\r\n                    </tr>\r\n                    <tr>\r\n                      <td sxy-text=\"SALAXY.NG1.CalcComponent.panelWorkTime.overview.paidAbsencesDays\"></td>\r\n                      <td class=\"right\">{{ $ctrl.calculatePeriodDays('paidAbsencesDays') | sxyCount : 'day' }}</td>\r\n                    </tr>\r\n                  </tbody>\r\n                </table>\r\n              </div>\r\n            </div>\r\n            <div class=\"content-details\">\r\n              <salaxy-calc-worktime ng-ref=\"$ctrl.worktimeCtrl\" ng-if=\"$ctrl.currentCalc\" calc=\"$ctrl.currentCalc\"></salaxy-calc-worktime>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div class=\"salaxy-calc-step-container step3\" ng-class=\"{ 'active': $ctrl.calcSections.get('salary').isActive }\">\r\n        <div class=\"card overview-salary salaxy-calc-overview-card\">\r\n          <div class=\"card-header\" ng-click=\"$ctrl.calcSections.toggleActive('salary')\">\r\n            <i class=\"bi bi-x-lg float-end close\"></i><span class=\"overview-title\" sxy-text=\"SALAXY.NG1.CalcComponent.panelSalary.heading\"></span>\r\n          </div>\r\n          <div class=\"card-body\">\r\n            <div class=\"content-overview\" ng-click=\"$ctrl.calcSections.toggleActive('salary')\">\r\n              <table>\r\n                <tbody>\r\n                  <tr>\r\n                    <td>\r\n                      {{ $ctrl.calcLogic.hasCompensation ? ('SALAXY.NG1.CalcDetailsExpensesComponent.foreclosurePayment.infoCompensation' | sxyTranslate) :\r\n                      ('SALAXY.NG1.CalcDetailsExpensesComponent.foreclosurePayment.infoSalary' | sxyTranslate) }}\r\n                    </td>\r\n                    <td class=\"right\">{{$ctrl.currentCalc.result.totals.totalBaseSalary || 0 | currency : \"\" : 2}} €</td>\r\n                  </tr>\r\n                  <tr>\r\n                    <td sxy-text=\"SALAXY.NG1.CalcDetailsExpensesComponent.titleAdditions\"></td>\r\n                    <td class=\"right\">{{ ($ctrl.currentCalc.result.totals.totalGrossSalary - $ctrl.currentCalc.result.totals.totalBaseSalary) || 0 | currency : \"\" : 2}} €</td>\r\n                  </tr>\r\n                  <tr class=\"total\">\r\n                    <td sxy-text=\"SALAXY.NG1.GeneralCalcDetailLabels.total\"></td>\r\n                    <td class=\"right\">{{$ctrl.currentCalc.result.totals.totalGrossSalary || 0 | currency : \"\" : 2}} €</td>\r\n                  </tr>\r\n                </tbody>\r\n              </table>\r\n            </div>\r\n            <div class=\"content-details\">\r\n              <ng-include src=\"'salaxy-components/calc/details/salary.html'\"></ng-include>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div class=\"salaxy-calc-step-container step4\" ng-class=\"{ 'active': $ctrl.calcSections.get('expenses').isActive }\">\r\n        <div class=\"card overview-expenses salaxy-calc-overview-card\">\r\n          <div class=\"card-header\" ng-click=\"$ctrl.calcSections.toggleActive('expenses')\">\r\n            <i class=\"bi bi-x-lg float-end close\"></i> <span class=\"overview-title\" sxy-text=\"SALAXY.NG1.CalcComponent.panelExpenses.heading\"></span>\r\n          </div>\r\n          <div class=\"card-body\">\r\n            <div class=\"content-overview\" ng-click=\"$ctrl.calcSections.toggleActive('expenses')\">\r\n              <table>\r\n                <tbody>\r\n                  <tr>\r\n                    <td sxy-text=\"SALAXY.NG1.CalcDetailsExpensesComponent.compensations.title\"></td>\r\n                    <td class=\"right\">{{ $ctrl.currentCalc.result.totals.totalExpenses || 0 | currency : '' : 2}}€</td>\r\n                  </tr>\r\n                  <tr>\r\n                    <td sxy-text=\"SALAXY.NG1.CalcDetailsExpensesComponent.benefits.title\"></td>\r\n                    <td class=\"right\">{{ $ctrl.currentCalc.result.workerCalc.benefits || 0 | currency : '' : 2}}€</td>\r\n                  </tr>\r\n                  <tr>\r\n                    <td sxy-text=\"SALAXY.NG1.CalcDetailsExpensesComponent.deductions\"></td>\r\n                    <td class=\"right\">{{ $ctrl.calcLogic.expensesTotal || 0 | currency : '' : 2}}€</td>\r\n                  </tr>\r\n                  <tr ng-if=\"$ctrl.isHousehold\">\r\n                    <td ng-if=\"$ctrl.calcLogic.childCareSubsidy\">Yks. hoid. tuki</td>\r\n                    <td ng-if=\"$ctrl.calcLogic.childCareSubsidy\" class=\"right\">{{ $ctrl.calcLogic.childCareSubsidy || 0 | currency : '' : 2}}€</td>\r\n                    <td colspan=\"2\" class=\"text-end\" ng-if=\"!$ctrl.calcLogic.childCareSubsidy\">\r\n                      <small>{{ $ctrl.isHouseholdDeductible ? (\"SALAXY.NG1.CalcComponent.panelExpenses.householdExpense\" | sxyTranslate) :\r\n                        (\"SALAXY.NG1.CalcComponent.panelExpenses.noHouseholdExpenses\" | sxyTranslate) }}</small>\r\n                    </td>\r\n                  </tr>\r\n                </tbody>\r\n              </table>\r\n            </div>\r\n            <div class=\"content-details\">\r\n              <ng-include src=\"'salaxy-components/calc/details/expenses.html'\"></ng-include>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <salaxy-calc-new-intro model=\"$ctrl\"></salaxy-calc-new-intro>\r\n  <salaxy-calc-results model=\"$ctrl\"></salaxy-calc-results>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/CalcChart.html\",`<!-- <div class=\"d-none\">{{$ctrl.refresh($ctrl.chart)}}</div> -->\r\n<div ng-if=\"$ctrl.calc\" ng-init=\"$ctrl.init()\" class=\"salaxy-component salaxy-calc-chart chart-container w-100 d-flex justify-content-center\" ng-class=\"'salaxy-calc-chart-' + $ctrl.role + 'salaxy-calc-chart-' + $ctrl.chartType\">\r\n  <canvas class=\"chart\" ng-class=\"$ctrl.chartType ==='bar' ? 'chart-bar' : 'chart-pie'\"></canvas>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/CalcCostAccounting.html\",`<div class=\"salaxy-component salaxy-calc-cost-accounting\">\r\n\r\n  <div ng-if=\"$ctrl.isLegacy\">\r\n\r\n    <fieldset>\r\n      <legend sxy-text=\"SALAXY.NG1.CalcCostAccountingComponent.title\"></legend>\r\n      <table class=\"table\">\r\n        <thead>\r\n          <tr>\r\n            <th>{{('SALAXY.NG1.CalcCostAccountingComponent.defaultLabel') | sxyTranslate}}</th>\r\n            <th class=\"right\">{{\"SALAXY.NG1.CalcCostAccountingComponent.percent\" | sxyTranslate}}</th>\r\n            <th class=\"right\">\r\n              <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-if=\"!$ctrl.isReadOnly\" ng-click=\"$ctrl.costCenter.push({})\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n            </th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr ng-repeat=\"item in $ctrl.costCenter\">\r\n            <td>\r\n              <salaxy-input-typeahead ng-if=\"$ctrl.getOptions('costCenter').length\" ng-model=\"item.id\" label-format=\"text-value\" get-options=\"$ctrl.getOptions('costCenter')\" name=\"{{ 'id' + $index }}\" label-type=\"plain\" read-only=\"$ctrl.isReadOnly\"></salaxy-input-typeahead>\r\n              <salaxy-input ng-if=\"!$ctrl.getOptions('costCenter').length\" ng-model=\"item.id\" name=\"{{ 'id' + $index }}\" label-type=\"plain\" read-only=\"$ctrl.isReadOnly\">\r\n              </salaxy-input>\r\n            </td>\r\n            <td>\r\n              <salaxy-input-number ng-model=\"item.percent\" name=\"{{ 'percent' + $index }}\" label-type=\"plain\" read-only=\"$ctrl.isReadOnly\" unit=\"percent\"></salaxy-input-number>\r\n            </td>\r\n            <td class=\"text-end\">\r\n              <button ng-if=\"!$ctrl.isReadOnly\" type=\"button\" class=\"btn btn-danger\" ng-click=\"$ctrl.costCenter.splice($index, 1)\">\r\n                <i class=\"bi bi-trash\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\"></i>\r\n              </button>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n        <tfoot>\r\n          <tr class=\"total\">\r\n            <td>{{\"SALAXY.UI_Terms.total\" | sxyTranslate}}</td>\r\n            <td class=\"right\">{{ $ctrl.getLegacySum() | sxyCount : 'percent' }}</td>\r\n            <td class=\"right\"></td>\r\n          </tr>\r\n        </tfoot>\r\n      </table>\r\n    </fieldset>\r\n  </div>\r\n\r\n  <div ng-if=\"!$ctrl.isLegacy && ( $ctrl.calc.accounting.dimensions.length > 0 || $ctrl.definitions.length > 0 )\">\r\n    <salaxy-cost-accounting ng-init=\"$ctrl.calc.accounting = ($ctrl.calc.accounting  || $ctrl.isReadOnly) ? $ctrl.calc.accounting : { dimensions: []}\" current=\"$ctrl.calc.accounting.dimensions\" scope=\"calculation\" dimensions=\"$ctrl.dimensions\" read-only=\"$ctrl.isReadOnly\"></salaxy-cost-accounting>\r\n  </div>\r\n  <div ng-if=\"!$ctrl.isLegacy && !( $ctrl.calc.accounting.dimensions.length > 0 || $ctrl.definitions.length > 0 )\">\r\n    <salaxy-input name=\"costCenter\" ng-model=\"$ctrl.calc.info.costCenter\" label=\"SALAXY.NG1.CalcDetailsWorkerComponent.costCenter\" read-only=\"$ctrl.isReadOnly\" input-mode=\"{{$ctrl.inputMode}}\"></salaxy-input>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/CalcDashboard.html\",`<div class=\"salaxy-component salaxy-calc-dashboard\">\r\n  <div class=\"row\">\r\n    <div class=\"col-12 mb-4\" ng-if=\"!$ctrl.hideButton\">\r\n      <salaxy-action-button action=\"'newCalc'\" label=\"SALAXY.NG1.ActionButtonComponent.newCalculation\"></salaxy-action-button>\r\n    </div>\r\n    <div class=\"col-12 col-sm-6 mb-4 mb-sm-0\">\r\n      <salaxy-calc-list category=\"paid\" mode=\"panel\" limit-to=\"5\" read-only=\"$ctrl.readOnly\"></salaxy-calc-list>\r\n    </div>\r\n    <div class=\"col-12 col-sm-6\">\r\n      <salaxy-calc-list category=\"draft\" mode=\"panel\" limit-to=\"5\" read-only=\"$ctrl.readOnly\"></salaxy-calc-list>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/CalcEditor.html\",`<div>\r\n  <salaxy-validation-summary api-validation=\"$ctrl.validation\"></salaxy-validation-summary>\r\n</div>\r\n<div style=\"margin-top:30px; margin-bottom:30px;\">\r\n  \r\n  <h2 class=\"mb-2\" sxy-text=\"SALAXY.NG1.CalcEditorComponent.title\"></h2>\r\n  <!-- spinning icon or similar?-->\r\n  <button class=\"btn btn-primary btn-labeled-right\" ng-click=\"$ctrl.saveEdited()\"><span sxy-text=\"SALAXY.UI_Terms.save\"></span><i class=\"bi bi-floppy\"></i></button>\r\n  <!-- spinning icon or similar?-->\r\n  <button class=\"btn btn-default btn-labeled-right\" ng-click=\"$ctrl.refresh()\"><span sxy-text=\"SALAXY.UI_Terms.refresh\"></span><i class=\"bi bi-arrow-repeat\" ng-class=\"{'bi-spin' : $ctrl.loaders['default'] }\"></i></button>\r\n\r\n  <div class=\"float-end\">Alkuperäinen: {{$ctrl.base.updatedAt | date: 'd.M.yyyy HH:mm:ss'}} <button class=\"btn btn-xs btn-default\" ng-click=\"$ctrl.changeBase()\">Vaihda...</button></div>\r\n</div>\r\n<div ng-if=\"$ctrl.current\" class=\"salaxy-component salaxy-calc-editor\">\r\n  <div class=\"row\">\r\n    <div class=\"col-12 col-xl-6 \" style=\"margin-top:20px;\">\r\n      <div class=\"row mb-2\">\r\n        <div class=\"col-md-6 col-12 calc-editor-worker-details mb-2\">\r\n          <legend>\r\n            <span sxy-text=\"SALAXY.NG1.CalcEditorComponent.workerTitle\"></span>\r\n            <button ng-if=\"'admin' | sxyIsInRole\" class=\"btn btn-xs btn-default float-end\" ng-click=\"$ctrl.refresh('worker')\" title=\"Päivitä työntekijän tiedot\"><i class=\"\" ng-class=\"$ctrl.loaders['worker']  ? 'bi bi-arrow-repeat bi-spin' : 'bi bi-download'\"></i></button>\r\n            <a class=\"btn btn-xs btn-default float-end btn-details\" href=\"#/employments/details/{{$ctrl.current.worker.employmentId}}\" ng-click=\"$ctrl.isRightSidebarOpen = true\" title=\"Tiedot / Muokkaa\" style=\"margin-right:2px;\"><i class=\"bi bi-info-circle-fill\"></i></a>\r\n\r\n          </legend>\r\n          <div class=\"row\">\r\n            <div class=\"col-3\">\r\n              <div class=\"avatar-container\">\r\n                <salaxy-avatar class=\"avatar-sm\" avatar=\"$ctrl.current.worker.avatar\"></salaxy-avatar>\r\n              </div>\r\n            </div>\r\n            <div class=\"col-9\">\r\n              <strong>{{$ctrl.current.worker.avatar.displayName}}</strong>\r\n              <br>\r\n              <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"socialSecurityNumber\" ng-model=\"$ctrl.current.worker.paymentData.socialSecurityNumber\"></salaxy-input>\r\n              <div>&nbsp;</div>\r\n              <br>\r\n            </div>\r\n          </div>\r\n          <div class=\"row\">\r\n            <div class=\"col-12\">\r\n              <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"firstName\" ng-model=\"$ctrl.current.worker.avatar.firstName\"></salaxy-input>\r\n              <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"lastName\" ng-model=\"$ctrl.current.worker.avatar.lastName\"></salaxy-input>\r\n              <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"ibanNumber\" ng-model=\"$ctrl.current.worker.paymentData.ibanNumber\" sxy-iban></salaxy-input>\r\n              <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"email\" ng-model=\"$ctrl.current.worker.contact.email\" sxy-email></salaxy-input>\r\n              <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"telephone\" ng-model=\"$ctrl.current.worker.contact.telephone\" sxy-mobile-phone></salaxy-input>\r\n              <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"street\" ng-model=\"$ctrl.current.worker.contact.street\"></salaxy-input>\r\n              <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"postalCode\" ng-model=\"$ctrl.current.worker.contact.postalCode\" sxy-postal-code-fi></salaxy-input>\r\n              <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"city\" ng-model=\"$ctrl.current.worker.contact.city\"></salaxy-input>\r\n            </div>\r\n          </div>\r\n        </div>\r\n        <div class=\"col-md-6 col-12 calc-editor-employer-details mb-2\">\r\n          <legend>\r\n            <span sxy-text=\"SALAXY.NG1.CalcEditorComponent.employerTitle\"></span>\r\n            <button ng-if=\"'admin' | sxyIsInRole\" class=\"btn btn-xs btn-default float-end\" ng-click=\"$ctrl.refresh('employer')\" title=\"Päivitä omat tiedot\"><i class=\"\"  ng-class=\"$ctrl.loaders['employer']  ? 'bi bi-arrow-repeat bi-spin' : 'bi bi-download'\"></i></button></legend>\r\n          <div class=\"row\">\r\n            <div class=\"col-3\">\r\n              <div class=\"avatar-container\">\r\n                <salaxy-avatar class=\"avatar-sm\" avatar=\"$ctrl.current.employer.avatar\"></salaxy-avatar>\r\n              </div>\r\n            </div>\r\n            <div class=\"col-9\">\r\n              <strong>{{$ctrl.current.employer.avatar.displayName}}</strong>\r\n              <br>\r\n              <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"employerOfficialId\" ng-model=\"$ctrl.current.employer.officialId\"></salaxy-input>\r\n              <div>&nbsp;</div>\r\n              <br>\r\n            </div>\r\n          </div>\r\n          <div class=\"row\">\r\n            <div class=\"col-12\">       \r\n              <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"employerEmail\" ng-model=\"$ctrl.current.employer.contact.email\" sxy-email></salaxy-input>\r\n              <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"employerTelephone\" ng-model=\"$ctrl.current.employer.contact.telephone\"></salaxy-input>\r\n              <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"employerStreet\" ng-model=\"$ctrl.current.employer.contact.street\"></salaxy-input>\r\n              <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"employerPostalCode\" ng-model=\"$ctrl.current.employer.contact.postalCode\"></salaxy-input>\r\n              <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"employerCiy\" ng-model=\"$ctrl.current.employer.contact.city\"></salaxy-input>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div class=\"row mb-2\">\r\n        <div class=\"col-md-6 col-12 mb-2\">\r\n          <form class=\"form-horizontal\" >\r\n            <fieldset>\r\n              <legend>\r\n                <span sxy-text=\"Työsuhteen tiedot\"></span>\r\n\r\n                <button ng-if=\"'admin' | sxyIsInRole\" class=\"btn btn-xs btn-default float-end\" ng-click=\"$ctrl.refresh('employment')\" title=\"Päivitä työsuhdetiedot\"><i ng-class=\"$ctrl.loaders['employment']  ? 'bi bi-arrow-repeat bi-spin' : 'bi bi-download'\"></i></button>\r\n                <a class=\"btn btn-xs btn-default float-end btn-details\" href=\"#/employments/details/{{$ctrl.current.worker.employmentId}}#employment\" ng-click=\"$ctrl.isRightSidebarOpen = true\" title=\"Tiedot / Muokkaa\" style=\"margin-right:2px;\"><i class=\"bi bi-info-circle-fill\"></i></a>\r\n              </legend>\r\n              <salaxy-input-enum input-mode=\"openClose\"  enum=\"PensionCalculation\" name=\"PensionCalculation\" label=\"Sovellettava eläketurva\" ng-model=\"$ctrl.current.result.responsibilities.pensionCalculation\"></salaxy-input-enum>\r\n              <salaxy-input-enum input-mode=\"openClose\"  enum=\"PensionRule\" name=\"PensionRule\" label=\"Eläkemaksun laskentasääntö\" ng-model=\"$ctrl.current.result.responsibilities.pensionRule\"></salaxy-input-enum>\r\n              <salaxy-input-enum input-mode=\"openClose\"  enum=\"EmploymentRelationType\" name=\"EmploymentRelationType\" label=\"Työsuhde\" ng-model=\"$ctrl.current.result.responsibilities.employmentType\"></salaxy-input-enum>\r\n              <salaxy-datepicker-popup input-mode=\"openClose\" name=\"employmentPeriodStart\" ng-model=\"$ctrl.current.worktime.employmentPeriod.start\"\r\n                label=\"Työsuhteen alkupäivä\"></salaxy-datepicker-popup>\r\n              <salaxy-datepicker-popup input-mode=\"openClose\" name=\"employmentPeriodEnd\" ng-model=\"$ctrl.current.worktime.employmentPeriod.end\"\r\n                label=\"Työsuhteen loppupäivä\"></salaxy-datepicker-popup>\r\n              <salaxy-input-enum input-mode=\"openClose\" ng-if=\"$ctrl.current.result.responsibilities.pensionCalculation == 'publicSector'\"  type=\"select\" name=\"employmentRegCodes\" disable-cache=\"true\"\r\n                options=\"$ctrl.getEmploymentRegCodeOptions()\" label=\"SALAXY.NG1.WorkerWizardComponent.employment.employmentRegCode\" ng-model=\"$ctrl.current.result.responsibilities.employmentRegCode\"></salaxy-input-enum>\r\n              <salaxy-input-enum input-mode=\"openClose\" enum=\"TaxcardKind\" name=\"TaxcardKind\" label=\"Työsuhteessa käytettävä verokortti\" ng-model=\"$ctrl.current.result.responsibilities.employmentTaxcard\"></salaxy-input-enum>\r\n              <salaxy-input-enum input-mode=\"openClose\" enum=\"EmploymentRelationSalaryPaymentMethod\" name=\"SalaryPaymentMethod\" label=\"Palkanmaksutapa\" ng-model=\"$ctrl.current.result.responsibilities.salaryPaymentMethod\"></salaxy-input-enum>\r\n              <salaxy-input-enum input-mode=\"openClose\" enum=\"IncomeEarnerType\" name=\"irIncomeEarnerTypes\" label=\"Tulonsaajan tyyppi\" ng-model=\"$ctrl.current.result.responsibilities.irIncomeEarnerTypes\" type=\"multi-select\"></salaxy-input-enum>\r\n              <salaxy-input-occupation-type name=\"occupationCode\" ng-model=\"$ctrl.current.info.occupationCode\" label=\"Ammattiluokka vakuutukseen\" read-only=\"false\">\r\n              </salaxy-input-occupation-type>\r\n              <salaxy-input tooltip-html=\"&lt;a target=&#39;_blank&#39; href=&#39;https://www.keva.fi/tyonantajalle/elakemaksut/ammattinimikkeiden-haku/&#39;&gt;Info&lt;/a&gt;\" ng-if=\"$ctrl.current.result.responsibilities.pensionCalculation == 'publicSector'\"  input-mode=\"openClose\" name=\"occupationCode2\" ng-model=\"$ctrl.current.info.occupationCode2\" label=\"Keva:n ammattiluokka\" read-only=\"false\">\r\n              </salaxy-input>\r\n\r\n            </fieldset>\r\n          </form>\r\n        </div>\r\n      \r\n        <div class=\"col-md-6 col-12 mb-2\">\r\n          <form class=\"form-horizontal\" ng-readonly=\"true\">\r\n            <fieldset>\r\n              <legend>\r\n                <span sxy-text=\"Verokortin tiedot\"></span>\r\n                <button ng-if=\"'admin' | sxyIsInRole\" class=\"btn btn-xs btn-default float-end\" ng-click=\"$ctrl.refresh('taxcard')\" title=\"Päivitä verokortti\"><i  ng-class=\"$ctrl.loaders['taxcard']  ? 'bi bi-arrow-repeat bi-spin' : 'bi bi-download'\"></i></button>\r\n                <a ng-if=\"'admin' | sxyIsInRole\" class=\"btn btn-xs btn-default float-end btn-details\" href=\"#/employments/details/{{$ctrl.current.worker.employmentId}}#taxcards\" ng-click=\"$ctrl.isRightSidebarOpen = true\" title=\"Tiedot / Muokkaa\" style=\"margin-right:2px;\"><i class=\"bi bi-info-circle-fill\"></i></a>\r\n              </legend>\r\n\r\n              <salaxy-input-enum enum=\"TaxcardKind\" name=\"TaxcardKind\" label=\"Verokortti\" ng-model=\"$ctrl.current.worker.tax.snapshot.kind\"></salaxy-input-enum>\r\n              <salaxy-input name=\"forYear\" label=\"Vuodelle\" ng-model=\"$ctrl.current.worker.tax.snapshot.forYear\"></salaxy-input>\r\n           \r\n              <salaxy-form-group name=\"validity\" class=\"salaxy-read-only\" label=\"Voimassa\">\r\n                <div class=\"form-control-plaintext\">\r\n                  {{$ctrl.current.worker.tax.snapshot.validity.start | date}} - {{$ctrl.current.worker.tax.snapshot.validity.end | date}}\r\n                </div>\r\n              </salaxy-form-group>\r\n              <salaxy-input label=\"veroprosentti\" name=\"Veroprosentti\" unit=\"percent\" ng-model=\"$ctrl.current.worker.tax.snapshot.taxPercent\" require=\"true\"></salaxy-input>\r\n              <salaxy-input-number label=\"Tuloraja\" name=\"tuloraja\" unit=\"euro\" ng-model=\"$ctrl.current.worker.tax.snapshot.incomeLimit\" maxlength=\"10\"></salaxy-input-number>\r\n              <salaxy-input label=\"Lisäveroprosentti\" name=\"lisaveroprosentti\" unit=\"percent\" ng-model=\"$ctrl.current.worker.tax.snapshot.taxPercent2\"></salaxy-input>\r\n              <!--for admin, should be nullable-->\r\n              <salaxy-input-number input-mode=\"openClose\" name=\"fixedTaxAmount\" ng-model=\"$ctrl.current.worker.tax.fixedTaxAmount\" label=\"Kiinteä ennakonpidätyksen määrä\" read-only=\"'!admin' | sxyIsInRole\"></salaxy-input-number>\r\n            </fieldset>\r\n          </form>\r\n        </div>\r\n      </div>\r\n      <div class=\"row mb-2\">\r\n        <div class=\"col-md-6 col-12 mb-2\">\r\n          <form class=\"form-horizontal\">\r\n            <fieldset>\r\n              <legend>\r\n                <span sxy-text=\"Vero, eläke- ja vakuutustiedot\"></span>\r\n                <button ng-if=\"'admin' | sxyIsInRole\" class=\"btn btn-xs btn-default float-end\" ng-click=\"$ctrl.refresh('insurances')\" title=\"Päivitä vakuutustiedot\"><i  ng-class=\"$ctrl.loaders['insurances']  ? 'bi bi-arrow-repeat bi-spin' : 'bi bi-download'\"></i></button>\r\n\r\n                <a ng-if=\"'admin' | sxyIsInRole\" class=\"btn btn-xs btn-default float-end btn-details\" href=\"#/settings/pro-settings\" title=\"Katso / Muokkaa\" ng-click=\"$ctrl.isRightSidebarOpen = true\" style=\"margin-right:2px;\"><i class=\"bi bi-info-circle-fill\"></i></a>\r\n\r\n              </legend>\r\n\r\n              <salaxy-input-boolean input-mode=\"openClose\" label=\"Hoidan ennakonpidätyksen maksun itse\" name=\"taxAndSocialSecuritySelfPayment\" ng-model=\"$ctrl.current.result.responsibilities.taxAndSocialSecuritySelfPayment\"></salaxy-input-boolean>\r\n              \r\n              <salaxy-input-enum input-mode=\"openClose\" label=\"Työeläkeyhtiö\" enum=\"PensionCompany\" name=\"PensionCompany\" ng-model=\"$ctrl.current.result.responsibilities.pensionCompany\"></salaxy-input-enum>\r\n              <salaxy-input input-mode=\"openClose\" label=\"Sopimusnumero\" name=\"PensionContractNumber\" ng-model=\"$ctrl.current.result.responsibilities.pensionContractNumber\" sxy-pension-contract-number></salaxy-input>\r\n              <salaxy-input ng-if=\"$ctrl.current.result.responsibilities.pensionCalculation == 'publicSector'\" input-mode=\"openClose\" label=\"SALAXY.MODEL.PensionContract.subOrgCode.title\" name=\"SubOrgCode\" ng-model=\"$ctrl.current.result.responsibilities.subOrgCode\"></salaxy-input>\r\n              <salaxy-input-number input-mode=\"openClose\" ng-model=\"$ctrl.current.result.responsibilities.pensionPercent\" unit=\"percent\" name=\"PensionPercent\" label=\"SALAXY.MODEL.PensionContract.pensionPercent.title\"></salaxy-input-number>\r\n              <salaxy-input-number input-mode=\"openClose\" ng-model=\"$ctrl.current.result.responsibilities.pensionDiscountPercent\" unit=\"percent\" name=\"PensionDiscount\" label=\"SALAXY.MODEL.PensionContract.pensionDiscountPercent.title\"></salaxy-input-number>\r\n              <salaxy-input-boolean input-mode=\"openClose\" ng-model=\"$ctrl.current.result.responsibilities.pensionSelfPayment\" name=\"pensionSelfPayment\" label=\"Hoitaa TyEl-maksut itse\"></salaxy-input-boolean>\r\n\r\n              <salaxy-input-enum input-mode=\"openClose\" ng-model=\"$ctrl.current.result.responsibilities.insuranceCompany\" label=\"Vakuutusyhtiö\" enum=\"InsuranceCompany\" name=\"InsuranceCompany\"></salaxy-input-enum>\r\n              <salaxy-input input-mode=\"openClose\" ng-model=\"$ctrl.current.result.responsibilities.insuranceContractNumber\" name=\"insuranceContractNumber\" label=\"SALAXY.MODEL.InsuranceContract.contractNumber.title\"></salaxy-input>\r\n              <salaxy-input-number input-mode=\"openClose\" label-cols=\"col-sm-6\" ng-model=\"$ctrl.current.result.responsibilities.insurancePercent\" label=\"Tapaturm.vak.maksun arvio-%\" unit=\"percent\" name=\"insurancePercent\"></salaxy-input-number>\r\n              <salaxy-input-number input-mode=\"openClose\" label-cols=\"col-sm-6\" ng-model=\"$ctrl.current.result.responsibilities.groupLifeInsurancePercent\" label=\"SALAXY.MODEL.InsuranceContract.groupLifeInsurancePercent.title\" unit=\"percent\" name=\"groupLifeInsurancePercent\"></salaxy-input-number>\r\n              \r\n              <salaxy-input-boolean input-mode=\"openClose\" read-only=\"true\" label-cols=\"col-sm-6\" ng-model=\"$ctrl.current.result.responsibilities.unemploymentSelfPayment\" name=\"unemploymentSelfPayment\" label=\"Hoitaa työt.vak.maksut itse\"></salaxy-input-boolean>\r\n              <salaxy-input-enum input-mode=\"openClose\" ng-model=\"$ctrl.current.result.responsibilities.unemploymentPayrollLimitStatus\" label=\"Työt.vak.maksun palkkasummaraja\" enum=\"UnemploymentPayrollLimitStatus\" name=\"unemploymentPayrollLimitStatus\">\r\n              </salaxy-input-enum>\r\n\r\n            </fieldset>\r\n          </form>\r\n        </div>\r\n        <div class=\"col-md-6 col-12 calc-editor-payment-details mb-2\">\r\n          <!-- todo fix readOnly-->\r\n          <form class=\"form-horizontal\">\r\n            <legend sxy-text=\"Palkanmaksu\"></legend>\r\n            <salaxy-input-boolean input-mode=\"openClose\"  label=\"Hoitaa nettopalkan maksun itse\" name=\"WorkerSelfPayment\" ng-model=\"$ctrl.current.result.responsibilities.workerSelfPayment\"></salaxy-input-boolean>\r\n            <salaxy-input-enum  input-mode=\"openClose\"  ng-model=\"$ctrl.current.workflow.salaryDateKind\" name=\"salaryDateKind\" enum=\"SalaryDateKind\"  label=\"SALAXY.MODEL.CalcWorkflow.salaryDateKind.title\"></salaxy-input-enum>\r\n            <salaxy-datepicker-popup input-mode=\"openClose\" name=\"salaryDate\" ng-model=\"$ctrl.current.workflow.salaryDate\" label=\"SALAXY.NG1.CalcEditorComponent.paymentInfo.salaryDateLabel\"></salaxy-datepicker-popup>\r\n            <salaxy-datepicker-popup input-mode=\"openClose\" name=\"salaryPaidAt\" ng-model=\"$ctrl.current.workflow.paidAt\" label=\"SALAXY.NG1.CalcEditorComponent.paymentInfo.paymentDateLabel\"></salaxy-datepicker-popup>  \r\n            <salaxy-date-range input-mode=\"openClose\" ng-model=\"$ctrl.dateRange\" class=\"condensed\" name=\"dateRange\" on-change=\"$ctrl.dateRangeChange()\" label=\"SALAXY.CORE.CalcWorktime.salaryPeriod\" label-days-count=\"SALAXY.MODEL.CalcWorktime.workDays.title\"></salaxy-date-range>            \r\n            <salaxy-input-enum  input-mode=\"openClose\"  ng-model=\"$ctrl.current.pricingModel\" name=\"pricingModel\" enum=\"PricingModel\"  label=\"SALAXY.MODEL.ServiceModelPricing.pricingModel.title\"></salaxy-input-enum>\r\n            <salaxy-input-number input-mode=\"openClose\" name=\"fixedFee\" ng-model=\"$ctrl.current.fixedFee\" label=\"SALAXY.MODEL.ServiceModelPricing.fixedFee.title\"></salaxy-input-number>\r\n            <salaxy-input-number input-mode=\"openClose\" read-only=\"true\" label=\"Maksu Palkkaus.fi-palvelulle\" name=\"palkkausFee\" ng-model=\"$ctrl.current.result.employerCalc.palkkaus\" sxy-currency></salaxy-input-number>\r\n            <salaxy-input-enum ng-if=\"'admin' | sxyIsInRole\"  input-mode=\"openClose\"  ng-model=\"$ctrl.current.info.paymentChannel\" name=\"paymentChannel\" enum=\"PaymentChannel\"  label=\"SALAXY.NG1.CalcEditorComponent.paymentInfo.paymentChannel\"></salaxy-input-enum>\r\n          </form>\r\n        </div>\r\n      </div>\r\n\r\n      <div class=\"row mb-2\">\r\n        <div class=\"col-md-6 col-12 mb-2\">\r\n          <form class=\"form-horizontal\" ng-readonly=\"true\">\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.NG1.CalcEditorComponent.messages.title\"></legend>\r\n\r\n              <salaxy-input input-mode=\"openClose\" read-only=\"false\" name=\"workDescription\" ng-model=\"$ctrl.current.info.workDescription\" label=\"SALAXY.NG1.CalcEditorComponent.messages.workDescriptionLabel\"></salaxy-input>\r\n              <salaxy-textarea input-mode=\"openClose\" read-only=\"false\" name=\"salarySlipMessage\" ng-model=\"$ctrl.current.info.salarySlipMessage\" label=\"SALAXY.NG1.CalcEditorComponent.messages.salarySlipMessageLabel\"></salaxy-textarea>\r\n            </fieldset>\r\n          </form>\r\n        </div>\r\n        <div class=\"col-md-6 col-12\" sxy-if-role=\"company\">\r\n          <div class=\"form-horizontal\">\r\n            <salaxy-calc-cost-accounting read-only=\"false\" input-mode=\"openClose\" calc=\"$ctrl.current\"></salaxy-calc-cost-accounting>\r\n          </div>\r\n        </div>\r\n        <div class=\"col-6\" sxy-if-role=\"person\">\r\n          <legend sxy-text=\"SALAXY.NG1.CalcEditorComponent.householdDeduction.title\"></legend>\r\n          <div class=\"row form-horizontal\">\r\n            <div class=\"col-6\">\r\n              <salaxy-input-boolean type=\"checkbox\" name=\"isHouseholdDeductible\" ng-model=\"$ctrl.current.usecase.data.isHouseholdDeductible\" label-type=\"no-label\" />\r\n            </div>\r\n            <div class=\"col-6\">\r\n              <div ng-if=\"!$ctrl.current.usecase.data.isHouseholdDeductible\" class=\"text-danger\" style=\"padding-top:7px;\" sxy-text=\"SALAXY.NG1.CalcEditorComponent.householdDeduction.noDeduction\"></div>\r\n              <div ng-if=\"$ctrl.current.usecase.data.isHouseholdDeductible\">\r\n                <select class=\"form-select\" ng-model=\"$ctrl.current.usecase.data.taxDeductionCategories\">\r\n                  <option hidden value=\"\" sxy-text=\"SALAXY.NG1.CalcEditorComponent.householdDeduction.deductionCategory.select\"></option>\r\n                  <option value=\"none\" sxy-text=\"SALAXY.NG1.CalcEditorComponent.householdDeduction.deductionCategory.none\"></option>\r\n                  <option value=\"householdwork\" sxy-text=\"SALAXY.NG1.CalcEditorComponent.householdDeduction.deductionCategory.householdwork\"></option>\r\n                  <option value=\"carework\" sxy-text=\"SALAXY.NG1.CalcEditorComponent.householdDeduction.deductionCategory.carework\"></option>\r\n                  <option value=\"homeImprovement\" sxy-text=\"SALAXY.NG1.CalcEditorComponent.householdDeduction.deductionCategory.homeImprovement\"></option>\r\n                  <option value=\"oilHeatingReplacementWork\" sxy-text=\"SALAXY.NG1.CalcEditorComponent.householdDeduction.deductionCategory.oilHeatingReplacementWork\"></option>\r\n                </select>\r\n              </div>\r\n              <div ng-if=\"$ctrl.current.usecase.data.isHouseholdDeductible\">\r\n                <select class=\"form-select\" ng-model=\"$ctrl.current.usecase.data.taxDeductionProperty\">\r\n                  <option hidden value=\"\" sxy-text=\"SALAXY.NG1.CalcEditorComponent.householdDeduction.deductionProperty.select\"></option>\r\n                  <option value=\"none\" sxy-text=\"SALAXY.NG1.CalcEditorComponent.householdDeduction.deductionProperty.none\"></option>\r\n                  <option value=\"ownProperty\" sxy-text=\"SALAXY.NG1.CalcEditorComponent.householdDeduction.deductionProperty.ownProperty\"></option>\r\n                  <option value=\"relativesProperty\" sxy-text=\"SALAXY.NG1.CalcEditorComponent.householdDeduction.deductionProperty.relativesProperty\"></option>\r\n                </select>\r\n              </div>\r\n            </div>\r\n          </div>\r\n\r\n        </div>\r\n      </div>\r\n      <div class=\"row calc-editor-calc-rows\">\r\n        <div class=\"col-12\">\r\n          <fieldset>\r\n\r\n            <legend sxy-text=\"SALAXY.NG1.CalcEditorComponent.calcRowsTitle\"></legend>\r\n            <salaxy-calc-rows-2019-editor parent=\"$ctrl.current\" mode=\"edit\" show-gross-totals=\"false\">\r\n            </salaxy-calc-rows-2019-editor>\r\n          </fieldset>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"col-12 col-xl-6\">\r\n      <salaxy-tab-buttons\r\n        current-tab=\"$ctrl.currentTab\"\r\n        options=\"[\r\n          { value: 'edited', text: 'SALAXY.NG1.CalcEditorComponent.editedHeading' },\r\n          { value: 'default', text: 'SALAXY.NG1.CalcEditorComponent.originalHeading' },\r\n          { value: 'paymentreport', text: 'SALAXY.NG1.CalcEditorComponent.diffHeading' },\r\n          { value: 'accounting', text: 'SALAXY.NG1.CalcEditorComponent.diffAccountingHeading' },\r\n          { value: 'cfa', text: 'SALAXY.NG1.CalcEditorComponent.diffCfa', hidden: !('admin' | sxyIsInRole) },\r\n          { value: 'documentflow', text: 'Laskut ja ilmoitukset' }\r\n        ]\"\r\n        tabs-id=\"calcEditor\">\r\n      </salaxy-tab-buttons>\r\n      <div class=\"tab-content\" id=\"tab-content-calcEditor\">\r\n        <div class=\"tab-pane\" id=\"edited-tab\">\r\n          <salaxy-calc-reports calcs=\"[$ctrl.current]\" report-type=\"'salarySlip'\"></salaxy-calc-reports>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"default-tab\">\r\n          <salaxy-calc-reports calcs=\"[$ctrl.base]\" report-type=\"'salarySlip'\"></salaxy-calc-reports>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"paymentreport-tab\">\r\n          <div class=\"payroll-report payroll-report-partial-container\">\r\n            <salaxy-calc-report calc=\"$ctrl.diffCalc\" report-type=\"'paymentReport'\" template-name=\"'paymentTablesV2'\" apply-site-styles=\"true\">\r\n          </div>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"accounting-tab\">\r\n          <salaxy-accounting-report-tools any-expanded=\"$reportRows.anyExpanded\" on-expand-change=\"$reportRows.expand(close)\" on-target-change=\"$ctrl.loadAccountingDiffData(targetId)\" reader=\"$ctrl.accountingDiffDataReader\"></salaxy-accounting-report-tools>\r\n          <salaxy-accounting-report-rows ng-ref=\"$reportRows\" data=\"$ctrl.accountingDiffData\"></salaxy-accounting-report-rows>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"cfa-tab\" ng-if=\"'admin' | sxyIsInRole\">\r\n          <fieldset>\r\n            <legend>\r\n              <span sxy-text=\"Asiakasmaksut\"></span>\r\n            </legend>\r\n          </fieldset>\r\n          <table class=\"table\">\r\n            <tr>\r\n              <th>Erä</th>\r\n              <th class=\"text-right\">Nykyinen summa</th>\r\n              <th class=\"text-right\">Laskettu summa</th>\r\n              <th class=\"text-right\">Laskettu ero</th>\r\n              <th class=\"text-right\">Tallennettava summa</th>\r\n              <th class=\"text-right\">Tallennettava ero</th>\r\n            </tr>\r\n            <tr>\r\n              <td>Nettopalkka</td>\r\n              <td class=\"text-right\">{{ $ctrl.base.cfa ? ($ctrl.base.cfa.net  | currency) : \" - \"}}</td>\r\n              <td class=\"text-right\">{{ ($ctrl.current.result.workerCalc.totalWorkerPayment - $ctrl.current.result.employerCalc.deductionWorkerSelfPayment) | currency}}</td>\r\n              <td class=\"text-right\">{{ (($ctrl.current.result.workerCalc.totalWorkerPayment - $ctrl.current.result.employerCalc.deductionWorkerSelfPayment) - ($ctrl.base.cfa ? $ctrl.base.cfa.net  : 0)) | currency }}</td>\r\n              <td class=\"text-right\">{{ $ctrl.current.cfa ? ($ctrl.current.cfa.net  | currency) : \" - \"}}</td>\r\n              <td class=\"text-right\">{{ $ctrl.current.cfa ? ( ($ctrl.current.cfa.net - $ctrl.base.cfa.net) | currency) : \" - \"}}</td>\r\n            </tr>\r\n            <tr>\r\n              <td>Eläke</td>\r\n              <td class=\"text-right\">{{ $ctrl.base.cfa ? ($ctrl.base.cfa.pension  | currency) : \" - \"}}</td>\r\n              <td class=\"text-right\">{{ ($ctrl.current.result.totals.pension - $ctrl.current.result.employerCalc.deductionPensionSelfPayment) | currency}}</td>\r\n              <td class=\"text-right\">{{ (($ctrl.current.result.totals.pension - $ctrl.current.result.employerCalc.deductionPensionSelfPayment) - ($ctrl.base.cfa ? $ctrl.base.cfa.pension  : 0)) | currency }}</td>\r\n              <td class=\"text-right\">{{ $ctrl.current.cfa ? ($ctrl.current.cfa.pension  | currency) : \" - \"}}</td>\r\n              <td class=\"text-right\">{{ $ctrl.current.cfa ? ( ($ctrl.current.cfa.pension - $ctrl.base.cfa.pension) | currency) : \" - \"}}</td>\r\n            </tr>\r\n            <tr>\r\n              <td>Vero</td>\r\n              <td class=\"text-right\">{{ $ctrl.base.cfa ? ($ctrl.base.cfa.tax  | currency) : \" - \"}}</td>\r\n              <td class=\"text-right\">{{ ($ctrl.current.result.workerCalc.tax + $ctrl.current.result.employerCalc.socialSecurity + $ctrl.current.result.workerCalc.taxAtSource +  $ctrl.current.result.workerCalc.socialSecurity - $ctrl.current.result.employerCalc.deductionTaxAndSocialSecuritySelfPayment) | currency}}</td>\r\n              <td class=\"text-right\">{{ (($ctrl.current.result.workerCalc.tax + $ctrl.current.result.employerCalc.socialSecurity + $ctrl.current.result.workerCalc.taxAtSource +  $ctrl.current.result.workerCalc.socialSecurity - $ctrl.current.result.employerCalc.deductionTaxAndSocialSecuritySelfPayment) - ($ctrl.base.cfa ? $ctrl.base.cfa.tax  : 0)) | currency }}</td>\r\n              <td class=\"text-right\">{{ $ctrl.current.cfa ? ($ctrl.current.cfa.tax  | currency) : \" - \"}}</td>\r\n              <td class=\"text-right\">{{ $ctrl.current.cfa ? ( ($ctrl.current.cfa.tax - $ctrl.base.cfa.tax) | currency) : \" - \"}}</td>\r\n            </tr>\r\n            <tr>\r\n              <td>Palvelumaksu</td>\r\n              <td class=\"text-right\">{{ $ctrl.base.cfa ? ($ctrl.base.cfa.service  | currency) : \" - \"}}</td>\r\n              <td class=\"text-right\">{{ ($ctrl.current.result.employerCalc.service) | currency}}</td>\r\n              <td class=\"text-right\">{{ (($ctrl.current.result.employerCalc.service) - ($ctrl.base.cfa ? $ctrl.base.cfa.service  : 0)) | currency }}</td>\r\n              <td class=\"text-right\">{{ $ctrl.current.cfa ? ($ctrl.current.cfa.service  | currency) : \" - \"}}</td>\r\n              <td class=\"text-right\">{{ $ctrl.current.cfa ? ( ($ctrl.current.cfa.service - $ctrl.base.cfa.service) | currency) : \" - \"}}</td>\r\n            </tr>\r\n            <tr>\r\n              <td>Palkkio</td>\r\n              <td class=\"text-right\">{{ $ctrl.base.cfa ? ($ctrl.base.cfa.fee  | currency) : \" - \"}}</td>\r\n              <td class=\"text-right\">{{ ($ctrl.current.result.employerCalc.palkkaus) | currency}}</td>\r\n              <td class=\"text-right\">{{ (($ctrl.current.result.employerCalc.palkkaus) - ($ctrl.base.cfa ? $ctrl.base.cfa.fee  : 0)) | currency }}</td>\r\n              <td class=\"text-right\">{{ $ctrl.current.cfa ? ($ctrl.current.cfa.fee  | currency) : \" - \"}}</td>\r\n              <td class=\"text-right\">{{ $ctrl.current.cfa ? ( ($ctrl.current.cfa.fee - $ctrl.base.cfa.fee) | currency) : \" - \"}}</td>\r\n            </tr>\r\n            <tr class=\"total\">\r\n              <td>Yhteensä</td>\r\n              <td class=\"text-right\">{{ $ctrl.base.cfa ? ($ctrl.base.cfa.total  | currency) : \" - \"}}</td>\r\n              <td class=\"text-right\">{{ (\r\n                $ctrl.current.result.workerCalc.totalWorkerPayment - $ctrl.current.result.employerCalc.deductionWorkerSelfPayment +\r\n                $ctrl.current.result.totals.pension - $ctrl.current.result.employerCalc.deductionPensionSelfPayment +\r\n                $ctrl.current.result.workerCalc.tax + $ctrl.current.result.employerCalc.socialSecurity + $ctrl.current.result.workerCalc.taxAtSource +  $ctrl.current.result.workerCalc.socialSecurity - $ctrl.current.result.employerCalc.deductionTaxAndSocialSecuritySelfPayment +\r\n                $ctrl.current.result.employerCalc.service +\r\n                $ctrl.current.result.employerCalc.palkkaus\r\n                ) | currency}}</td>\r\n              <td class=\"text-right\">{{ ((\r\n                $ctrl.current.result.workerCalc.totalWorkerPayment - $ctrl.current.result.employerCalc.deductionWorkerSelfPayment +\r\n                $ctrl.current.result.totals.pension - $ctrl.current.result.employerCalc.deductionPensionSelfPayment +\r\n                $ctrl.current.result.workerCalc.tax + $ctrl.current.result.employerCalc.socialSecurity + $ctrl.current.result.workerCalc.taxAtSource +  $ctrl.current.result.workerCalc.socialSecurity - $ctrl.current.result.employerCalc.deductionTaxAndSocialSecuritySelfPayment +\r\n                $ctrl.current.result.employerCalc.service +\r\n                $ctrl.current.result.employerCalc.palkkaus\r\n                ) - ($ctrl.base.cfa ? $ctrl.base.cfa.total  : 0)) | currency }}</td>\r\n              <td class=\"text-right\">{{ $ctrl.current.cfa ? ($ctrl.current.cfa.total  | currency) : \" - \"}}</td>\r\n              <td class=\"text-right\">{{ $ctrl.current.cfa ? ( ($ctrl.current.cfa.total - $ctrl.base.cfa.total) | currency) : \" - \"}}</td>\r\n            </tr>\r\n          </table>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"documentflow-tab\">\r\n          <div ng-if=\"$ctrl.documentFlow.children\">\r\n            <table class=\"table table-striped\">\r\n              <tr ng-repeat=\"doc in $ctrl.documentFlow.children\">\r\n                <td>\r\n                  <salaxy-avatar ng-if=\"doc.item.type != 'payerSummary' && doc.item.type != 'payrollDetails'\" class=\"salaxy-calc-row-type-avatar\" avatar=\"doc.item.otherPartyInfo.avatar\"></salaxy-avatar>\r\n                  <salaxy-avatar ng-if=\"doc.item.type == 'payerSummary' || doc.item.type == 'payrollDetails'\" class=\"salaxy-calc-row-type-avatar\" avatar=\"doc.item.ownerInfo.avatar\"></salaxy-avatar>\r\n                </td>\r\n                <td class=\"middle\">\r\n                  <strong ng-if=\"doc.item.type == 'invoice'\">{{doc.item.shortText}}</strong>\r\n                  <strong ng-if=\"doc.item.type == 'earningsPayment'\">{{'Palkkatietoilmoitus' |sxyTranslate}}</strong>\r\n                  <strong ng-if=\"doc.item.type == 'payrollDetails'\">{{'Palkkalista' |sxyTranslate}}</strong>\r\n                  <strong ng-if=\"doc.item.type == 'payerSummary'\">{{'Erillisilmoitus' |sxyTranslate}}</strong>\r\n                  <strong ng-if=\"doc.item.type == 'taxcard'\">{{'Verokortti' |sxyTranslate}}</strong>\r\n                </td>\r\n                <td>\r\n                  <a ng-if=\"doc.item.type == 'earningsPayment'\" class=\"btn btn-default btn-sm\" ng-href=\"#/irepr/details/{{doc.item.id}}\">Näytä</a>\r\n                  <a ng-if=\"doc.item.type == 'invoice'\" class=\"btn btn-default btn-sm\" ng-href=\"#/invoices/details/{{doc.item.id}}\">\r\n                    {{ 'SALAXY.UI_Terms.show' | sxyTranslate}}</a>\r\n                  <a ng-if=\"doc.item.type == 'payerSummary'\" class=\"btn btn-default btn-sm\" ng-href=\"#/irpsr/details/{{doc.item.id}}\">Näytä</a>\r\n                  <a ng-if=\"doc.item.type == 'payrollDetails'\" class=\"btn btn-default btn-sm\" ng-href=\"#/payroll/details/{{doc.item.id}}\">Näytä</a>\r\n                  <a ng-if=\"doc.item.type == 'taxcard'\" class=\"btn btn-default btn-sm\" ng-href=\"#/taxcards/details/{{doc.item.id}}\">Näytä</a>\r\n                </td>\r\n              </tr>\r\n            </table>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div ng-if=\"'admin' | sxyIsInRole\" class=\"right-sidebar\"  ng-class=\"{'is-open' : $ctrl.isRightSidebarOpen}\">\r\n      <button class=\"btn btn-transparent custom-close\" ng-click=\"$ctrl.isRightSidebarOpen = false\">\r\n        <i class=\"bi bi-x-lg\"></i>\r\n      </button>\r\n      <div ng-view></div>\r\n    </div>\r\n  </div>\r\n \r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/CalcLeaves.html\",`<div class=\"row\">\r\n  <div class=\"col-12\">\r\n    <p class=\"lead\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.details.lead\"></p>\r\n  </div>\r\n</div>\r\n<div class=\"row\">\r\n  <div class=\"col-sm-12\">\r\n    <table class=\"table table-sm\">\r\n      <thead>\r\n        <th></th>\r\n        <th class=\"right\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.annualLeaves.holidaySalariesAndCompensations\"></th>\r\n        <th ng-if=\"$ctrl.logic.worktime.holidaySpec.bonusMethod != 'none'\" class=\"right\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.annualLeaves.bonuses\"></th>\r\n      </thead>\r\n      <tbody>\r\n        <tr>\r\n          <td sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.annualLeaves.accrualRemaining\"></td>\r\n          <td class=\"right\">{{$ctrl.worktime.holidayPayAccrualRemaining}}</td>\r\n          <td ng-if=\"$ctrl.logic.worktime.holidaySpec.bonusMethod != 'none'\" class=\"right\">{{$ctrl.worktime.holidayBonusAccrualRemaining}}</td>\r\n        </tr>\r\n        <tr> \r\n          <td sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.annualLeaves.paidInThisSalary\"></td>\r\n          <td class=\"right\">{{$ctrl.getAccrualRemaningsToBePaid('holidayPay')}}</td>\r\n          <td ng-if=\"$ctrl.logic.worktime.holidaySpec.bonusMethod != 'none'\" class=\"right\">{{$ctrl.getAccrualRemaningsToBePaid('holidayBonus')}}</td>\r\n        </tr>\r\n        <tr>\r\n          <td sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.annualLeaves.newAccrualRemaining\"></td>\r\n          <td class=\"right\">{{$ctrl.worktime.holidayPayAccrualRemaining - $ctrl.getAccrualRemaningsToBePaid('holidayPay')}}</td>\r\n          <td ng-if=\"$ctrl.logic.worktime.holidaySpec.bonusMethod != 'none'\" class=\"right\">{{$ctrl.worktime.holidayBonusAccrualRemaining - $ctrl.getAccrualRemaningsToBePaid('holidayBonus')}}</td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n</div>\r\n<div class=\"row\">\r\n  <div class=\"col-sm-6\">\r\n    <h4 sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.annualLeaves.paidInThisSalary\"></h4>\r\n    <table class=\"table table-sm\" ng-if=\"$ctrl.annualLeavestoBePaid.length\">\r\n      <thead>\r\n        <tr>\r\n          <th width=\"60%\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.annualLeaves.holidayPeriod\"></th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.annualLeaves.days\"></th>\r\n          <th ng-if=\"$ctrl.logic.worktime.holidaySpec.bonusMethod != 'none'\" class=\"right\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.annualLeaves.bonusDays\"></th>\r\n          <th></th>\r\n          <th></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.annualLeavestoBePaid\">\r\n          <td width=\"60%\">\r\n            {{row.period | sxyDateRange}}\r\n          </td>\r\n          <td class=\"right\">\r\n            <salaxy-input-number name=\"daysCount\" ng-model=\"row.period.daysCount\" label-type=\"plain\"></salaxy-input-number>\r\n          </td>\r\n          <td ng-if=\"$ctrl.logic.worktime.holidaySpec.bonusMethod != 'none'\" class=\"right\">\r\n            <salaxy-input-number name=\"bonusDaysCount\" ng-model=\"row.bonusDaysCount\" label-type=\"plain\"></salaxy-input-number>\r\n          </td>\r\n          <td>\r\n            <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showEditDialog(row)\">\r\n              <span><i class=\"bi bi-calendar3\"></i></span>\r\n            </button>\r\n          </td>\r\n          <td>\r\n            <button type=\"button\" class=\"delete btn btn-danger\" ng-click=\"$ctrl.moveItem(row, 'annualLeavesWaitingForPayment')\">\r\n              <span></span><i class=\"bi bi-trash-fill\"></i>\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <div class=\"col-sm-6\">\r\n    <h4 sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.annualLeaves.plannedHolidays\"></h4>\r\n    <table class=\"table table-sm\" ng-if=\"$ctrl.annualLeavesWaitingForPayment.length\">\r\n      <thead>\r\n        <tr>\r\n          <th width=\"40%\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.annualLeaves.startDate\"></th>\r\n          <th width=\"40%\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.annualLeaves.endDate\"></th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.annualLeaves.days\"></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.annualLeavesWaitingForPayment\" ng-style=\"$ctrl.getDisabledStyle(row)\">\r\n          <td width=\"40%\">\r\n            <span>{{row.period.start | sxyDate}}</span>\r\n          </td>\r\n          <td width=\"40%\">\r\n            <span>{{row.period.end | sxyDate}}</span>\r\n          </td>\r\n          <td class=\"right\">\r\n            <span>{{row.period.daysCount}}</span>\r\n          </td>\r\n          <td>\r\n            <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.moveItem(row,'annualLeavestoBePaid')\" ng-disabled=\"$ctrl.isSelectedToBePaid(row)\" sxy-text=\"SALAXY.UI_Terms.select\">\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n</div>\r\n<div class=\"row\">\r\n  <div class=\"col-sm-6\">\r\n    <h4 sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.absencePeriods.absencesToUse\"></h4>\r\n    <table class=\"table table-sm\" ng-if=\"$ctrl.absencesToUse.length\">\r\n      <thead>\r\n        <tr>\r\n          <th width=\"60%\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.absencePeriods.absenceTime\"></th>\r\n          <th sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.absencePeriods.cause\"></th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.annualLeaves.days\"></th>\r\n          <th></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.absencesToUse\">\r\n          <td width=\"60%\">\r\n            {{row.period | sxyDateRange}}\r\n          </td>\r\n          <td>{{ \"AbsenceCauseCode.\" + row.causeCode | sxyEnum }}</td>\r\n          <td class=\"right\">{{row.period.daysCount}}</td>\r\n          <td>\r\n            <button type=\"button\" class=\"delete btn btn-danger\" ng-click=\"$ctrl.moveAbsenceItem(row, 'absencesToReject')\">\r\n              <span></span><i class=\"bi bi-trash-fill\"></i>\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <div class=\"col-6\">\r\n    <h4 sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.absencePeriods.absencesToReject\"></h4>\r\n    <table class=\"table table-sm\" ng-if=\"$ctrl.absencesToReject.length\">\r\n      <thead>\r\n        <tr>\r\n          <th width=\"40%\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.annualLeaves.startDate\"></th>\r\n          <th width=\"40%\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.annualLeaves.endDate\"></th>\r\n          <th sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.absencePeriods.cause\"></th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.annualLeaves.days\"></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.absencesToReject\" ng-style=\"$ctrl.getAbsenceDisabledStyle(row)\">\r\n          <td width=\"40%\">\r\n            <span>{{row.period.start | sxyDate}}</span>\r\n          </td>\r\n          <td width=\"40%\">\r\n            <span>{{row.period.end | sxyDate}}</span>\r\n          </td>\r\n          <td>{{ \"AbsenceCauseCode.\" + row.causeCode | sxyEnum }}</td>\r\n          <td class=\"right\">\r\n            <span>{{row.period.daysCount}}</span>\r\n          </td>\r\n          <td>\r\n            <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.moveAbsenceItem(row,'absencesToUse')\" ng-disabled=\"$ctrl.isAbsenceSelectedToUse(row)\" sxy-text=\"SALAXY.UI_Terms.select\">\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/CalcList.html\",`<div class=\"salaxy-component salaxy-calc-list\">\r\n  <div ng-if=\"($ctrl.mode || 'default') == 'default'\">\r\n    <salaxy-odata-table ng-if=\"$ctrl.category=='draft'\" url=\"/v03/api/calculations/category/editable\" crud-controller=\"CalculationCrudController as $crud\" options=\"{$top:$ctrl.limitTo}\" template-url=\"salaxy-components/odata/lists/CalculationsDrafts.html\" read-only=\"$ctrl.readOnly\">\r\n    </salaxy-odata-table>\r\n    <salaxy-odata-table ng-if=\"$ctrl.category=='paid'\" url=\"/v03/api/calculations/category/readonly\" crud-controller=\"CalculationCrudController as $crud\" options=\"{$top:$ctrl.limitTo}\" template-url=\"salaxy-components/odata/lists/CalculationsPaid.html\" read-only=\"$ctrl.readOnly\">\r\n    </salaxy-odata-table>\r\n    <div ng-if=\"$ctrl.category=='paidIr'\">\r\n      <salaxy-tab-buttons\r\n        current-tab=\"$ctrl.currentTab\"\r\n        options=\"[\r\n          { value: 'paymentsucceeded', text: 'SALAXY.ENUM.CalculationStatus.paymentSucceeded.label' },\r\n          { value: 'paymentstarted', text: 'SALAXY.ENUM.CalculationStatus.paymentStarted.label' }\r\n        ]\"\r\n        tabs-id=\"calcList\">\r\n      </salaxy-tab-buttons>\r\n      <div class=\"tab-content\" id=\"tab-content-calcList\">\r\n        <div class=\"tab-pane\" id=\"paymentsucceeded-tab\">\r\n          <div ng-if=\"$ctrl.currentTab == 'paymentsucceeded'\">\r\n            <salaxy-odata-table url=\"/v03/api/calculations/category/readonly\" crud-controller=\"CalculationCrudController as $crud\" options=\"{$top:$ctrl.limitTo, $filter: 'status eq \\\\'paymentSucceeded\\\\'' }\" template-url=\"salaxy-components/odata/lists/CalculationsPaidIr.html\" read-only=\"$ctrl.readOnly\"></salaxy-odata-table>\r\n          </div>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"paymentstarted-tab\">\r\n          <div ng-if=\"$ctrl.currentTab == 'paymentstarted'\">\r\n            <salaxy-odata-table url=\"/v03/api/calculations/category/readonly\" crud-controller=\"CalculationCrudController as $crud\" options=\"{$top:$ctrl.limitTo, $filter: 'status eq \\\\'paymentStarted\\\\'' }\" template-url=\"salaxy-components/odata/lists/CalculationsPaidIr.html\" read-only=\"$ctrl.readOnly\"></salaxy-odata-table>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>    \r\n    <salaxy-odata-table ng-if=\"$ctrl.category=='shared'\" url=\"/v03/api/calculations/category/shared\" crud-controller=\"CalculationCrudController as $crud\" options=\"{$top: $ctrl.limitTo, $orderby:'createdAt desc'}\" template-url=\"salaxy-components/odata/lists/CalculationsShared.html\"\r\n      read-only=\"$ctrl.readOnly\">\r\n    </salaxy-odata-table>\r\n    <salaxy-odata-table ng-if=\"$ctrl.category=='sent'\" url=\"/v03/api/calculations/category/sent\" crud-controller=\"CalculationCrudController as $crud\" options=\"{$top: $ctrl.limitTo}\" template-url=\"salaxy-components/odata/lists/CalculationsSent.html\" read-only=\"$ctrl.readOnly\">\r\n    </salaxy-odata-table>\r\n    <salaxy-odata-table ng-if=\"$ctrl.category=='received'\" url=\"/v03/api/calculations/category/received\" crud-controller=\"CalculationCrudController as $crud\" options=\"{$top: $ctrl.limitTo}\" template-url=\"salaxy-components/odata/lists/CalculationsReceived.html\"\r\n      read-only=\"$ctrl.readOnly\">\r\n    </salaxy-odata-table>\r\n    <salaxy-odata-table ng-if=\"$ctrl.category=='all'\" crud-controller=\"CalculationCrudController as $crud\" options=\"{$top: $ctrl.limitTo}\" template-url=\"salaxy-components/odata/lists/CalculationsAll.html\" read-only=\"$ctrl.readOnly\">\r\n    </salaxy-odata-table>\r\n    <salaxy-odata-table ng-if=\"$ctrl.category=='error'\" url=\"/v03/api/calculations/category/error\" crud-controller=\"CalculationCrudController as $crud\" options=\"{$top: $ctrl.limitTo}\" template-url=\"salaxy-components/odata/lists/CalculationsAll.html\" read-only=\"$ctrl.readOnly\">\r\n    </salaxy-odata-table>\r\n\r\n    <salaxy-odata-table ng-if=\"$ctrl.category=='allEmployer'\" url=\"/v03/api/calculations/category/all\" crud-controller=\"CalculationCrudController as $crud\" options=\"{ $top: $ctrl.limitTo, $filter: 'status eq \\\\'paymentWorkerCopy\\\\' or status eq \\\\'draft\\\\' or status eq \\\\'workerRequested\\\\' or status eq \\\\'workerRequestAccepted\\\\' or status eq \\\\'workerRequestDeclined\\\\' ' }\"\r\n      template-url=\"salaxy-components/odata/lists/CalculationsEmployerAll.html\">\r\n    </salaxy-odata-table>\r\n  </div>\r\n  <salaxy-odata-table ng-if=\"$ctrl.mode == 'panel'\" url=\"{{ $ctrl.category == 'paid' ? '/v03/api/calculations/category/readonly' : $ctrl.category == 'sent' ? '/v03/api/calculations/category/sent' : $ctrl.category == 'received' ? '/v03/api/calculations/category/received' : $ctrl.category == 'shared' ? '/v03/api/calculations/category/shared' : '/v03/api/calculations/category/editable'}}\"\r\n    crud-controller=\"CalculationCrudController as $crud\" options=\"{$top: $ctrl.limitTo, $filter: $ctrl.filter, $orderby: $ctrl.category == 'shared' ? 'createdAt desc' : null}\" data=\"{ category: $ctrl.category }\" template-url=\"salaxy-components/odata/lists/CalculationsPanel.html\"\r\n    read-only=\"$ctrl.readOnly\">\r\n  </salaxy-odata-table>\r\n  <salaxy-odata-table ng-if=\"$ctrl.mode == 'select'\" url=\"{{ $ctrl.category == 'paid' ? '/v03/api/calculations/category/readonly' : $ctrl.category == 'shared' ? '/v03/api/calculations/category/shared' : '/v03/api/calculations/category/editable'}}\" template-url=\"salaxy-components/odata/lists/Calculations-select.html\" options=\"$ctrl.options\"\r\n    selected-items=\"$ctrl.selectedItems\" on-list-select=\"$ctrl.onListSelect({ value: value, item: item, allItems: allItems });\" crud-controller=\"CalculationCrudController as $crud\"></salaxy-odata-table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/CalcNewIntro.html\",`<div class=\"calc-start-instructions\" ng-if=\"!$ctrl.calcSections.get('result').isSelectionDone\">\r\n  <h1 style=\"font-size: 2em\" class=\"mt-2 text-center mb-5\" sxy-text=\"SALAXY.NG1.CalcNewIntroComponent.title\"></h1>\r\n  <div class=\"row mb-4\">\r\n    <div class=\"col-6 col-sm-3 text-center\" style=\"min-height: 200px; cursor: pointer;\" ng-click=\"$ctrl.calcSections.toggle('worker');\">\r\n      <div class=\"bi-stack-icons bi-7x\">\r\n        <i class=\"bi bi-circle-fill text-info\"></i>\r\n        <span class=\"bi-text-on-top\">1</span>\r\n      </div>\r\n      <strong class=\"uppercase\" sxy-text=\"SALAXY.NG1.CalcNewIntroComponent.stepOne.title\"></strong>\r\n      <p sxy-text=\"SALAXY.NG1.CalcNewIntroComponent.stepOne.description\"></p>\r\n    </div>\r\n    <div class=\"col-6 col-sm-3 text-center\" style=\"min-height: 200px; cursor: pointer;\" ng-click=\"$ctrl.calcSections.toggle('worktime');\">\r\n      <div class=\"bi-stack-icons bi-7x\">\r\n        <i class=\"bi bi-circle-fill text-warning\"></i>\r\n        <span class=\"bi-text-on-top\">2</span>\r\n      </div>\r\n      <strong class=\"uppercase\" sxy-text=\"SALAXY.NG1.CalcNewIntroComponent.stepTwo.title\"></strong>\r\n      <p sxy-text=\"SALAXY.NG1.CalcNewIntroComponent.stepTwo.description\"></p>\r\n    </div>\r\n    <div class=\"col-6 col-sm-3 text-center\" style=\"min-height: 200px; cursor: pointer;\" ng-click=\"$ctrl.calcSections.toggle('salary');\">\r\n      <div class=\"bi-stack-icons bi-7x\">\r\n        <i class=\"bi bi-circle-fill text-success\"></i>\r\n        <span class=\"bi-text-on-top\">3</span>\r\n      </div>\r\n      <strong class=\"uppercase\" sxy-text=\"SALAXY.NG1.CalcNewIntroComponent.stepThree.title\"></strong>\r\n      <p sxy-text=\"SALAXY.NG1.CalcNewIntroComponent.stepThree.description\"></p>\r\n    </div>\r\n    <div class=\"col-6 col-sm-3 text-center\" style=\"min-height: 200px; cursor: pointer;\" ng-click=\"$ctrl.calcSections.toggle('expenses');\">\r\n      <div class=\"bi-stack-icons bi-7x\">\r\n        <i class=\"bi bi-circle-fill text-danger\"></i>\r\n        <span class=\"bi-text-on-top\">4</span>\r\n      </div>\r\n      <strong class=\"uppercase\" sxy-text=\"SALAXY.NG1.CalcNewIntroComponent.stepFour.title\"></strong>\r\n      <p sxy-text=\"SALAXY.NG1.CalcNewIntroComponent.stepFour.description\"></p>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/CalcRepair.html\",`<div class=\"salaxy-component salaxy-calc-repair\" ng-if=\"$ctrl.current && $ctrl.current.workflow.status == 'repair'\">\r\n  <div class=\"row\">\r\n    <div class=\"col-12 col-sm-12 col-md-12 col-lg-6 \">\r\n      <div ng-if=\"$ctrl.current\">\r\n        <div class=\"btn-toolbar calc-toolbar\">\r\n          <div class=\"btn-group\" role=\"group\">\r\n            <!--button class=\"btn btn-default\" ng-click=\"$ctrl.recalculateRepair()\" sxy-text=\"SALAXY.UI_Terms.recalculate\"></button-->\r\n            <button class=\"btn btn-success\" ng-click=\"$ctrl.saveRepair()\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n            <button class=\"btn btn-danger\"ng-click=\"$ctrl.deleteCalc('/calc/repairs')\"  sxy-text=\"SALAXY.UI_Terms.delete\"></button>\r\n          </div>\r\n          <div class=\"btn-group\" role=\"group\">\r\n            <button class=\"btn btn-primary\" type=\"button\" ng-click=\"$ctrl.commitRepair()\" ng-disabled=\"$ctrl.hasChanges\"  sxy-text=\"Korvaa alkuperäinen laskelma\"></button>\r\n          </div>\r\n        </div>\r\n        <div class=\"panel panel-primary\" style=\"padding: 10px\">\r\n          <div class=\"panel-body\">\r\n            <salaxy-validation-summary api-validation=\"$ctrl.validation\"></salaxy-validation-summary>\r\n            <div class=\"row\">\r\n              <div class=\"row calc-editor-calc-rows\">\r\n                <div class=\"col-12\">\r\n                  <fieldset>\r\n                    <legend sxy-text=\"SALAXY.NG1.CalcEditorComponent.calcRowsTitle\"></legend>\r\n                    <salaxy-calc-rows-2019-editor parent=\"$ctrl.current\" mode=\"edit\" show-gross-totals=\"false\">\r\n                    </salaxy-calc-rows-2019-editor>\r\n                  </fieldset>\r\n                </div>\r\n              </div>\r\n              <div class=\"row spacer-bottom salaxy-calc-editor\">\r\n                <div class=\"col-md-6 col-12 calc-editor-worker-details spacer-bottom\">\r\n                  <legend>\r\n                    <span sxy-text=\"SALAXY.NG1.CalcEditorComponent.workerTitle\"></span>\r\n                  </legend>\r\n                  <div class=\"row\">\r\n                    <div class=\"col-3\">\r\n                      <div class=\"avatar-container\">\r\n                        <salaxy-avatar avatar=\"$ctrl.current.worker.avatar\"></salaxy-avatar>\r\n                      </div>\r\n                    </div>\r\n                    <div class=\"col-9\">\r\n                      <strong>{{$ctrl.current.worker.avatar.displayName}}</strong>\r\n                      <br>\r\n                      <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"socialSecurityNumber\"\r\n                        ng-model=\"$ctrl.current.worker.paymentData.socialSecurityNumber\"></salaxy-input>\r\n                      <div>&nbsp;</div>\r\n                      <br>\r\n                    </div>\r\n                  </div>\r\n                  <div class=\"row\">\r\n                    <div class=\"col-12\">\r\n                      <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"firstName\" ng-model=\"$ctrl.current.worker.avatar.firstName\"></salaxy-input>\r\n                      <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"lastName\" ng-model=\"$ctrl.current.worker.avatar.lastName\"></salaxy-input>\r\n                      <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"ibanNumber\" ng-model=\"$ctrl.current.worker.paymentData.ibanNumber\"\r\n                        sxy-iban></salaxy-input>\r\n                      <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"email\" ng-model=\"$ctrl.current.worker.contact.email\" sxy-email></salaxy-input>\r\n                      <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"telephone\" ng-model=\"$ctrl.current.worker.contact.telephone\"\r\n                        sxy-mobile-phone></salaxy-input>\r\n                      <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"street\" ng-model=\"$ctrl.current.worker.contact.street\"></salaxy-input>\r\n                      <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"postalCode\" ng-model=\"$ctrl.current.worker.contact.postalCode\"\r\n                        sxy-postal-code-fi></salaxy-input>\r\n                      <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"city\" ng-model=\"$ctrl.current.worker.contact.city\"></salaxy-input>\r\n                    </div>\r\n                  </div>\r\n                </div>\r\n                <div class=\"col-md-6 col-12 calc-editor-employer-details spacer-bottom\">\r\n                  <legend>\r\n                    <span sxy-text=\"SALAXY.NG1.CalcEditorComponent.employerTitle\"></span>\r\n                  </legend>\r\n                  <div class=\"row\">\r\n                    <div class=\"col-3 \">\r\n                      <div class=\"avatar-container \">\r\n                        <salaxy-avatar avatar=\"$ctrl.current.employer.avatar\"></salaxy-avatar>\r\n                      </div>\r\n                    </div>\r\n                    <div class=\"col-9\">\r\n                      <strong>{{$ctrl.current.employer.avatar.displayName}}</strong>\r\n                      <br>\r\n                      <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"employerOfficialId\"\r\n                        ng-model=\"$ctrl.current.employer.officialId\"></salaxy-input>\r\n                      <div>&nbsp;</div>\r\n                      <br>\r\n                    </div>\r\n                  </div>\r\n                  <div class=\"row\">\r\n                    <div class=\"col-12\">\r\n                      <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"employerEmail\" ng-model=\"$ctrl.current.employer.contact.email\"\r\n                        sxy-email></salaxy-input>\r\n                      <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"employerTelephone\"\r\n                        ng-model=\"$ctrl.current.employer.contact.telephone\"></salaxy-input>\r\n                      <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"employerStreet\"\r\n                        ng-model=\"$ctrl.current.employer.contact.street\"></salaxy-input>\r\n                      <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"employerPostalCode\"\r\n                        ng-model=\"$ctrl.current.employer.contact.postalCode\"></salaxy-input>\r\n                      <salaxy-input label-type=\"plain\" input-mode=\"openClose\" read-only=\"false\" name=\"employerCiy\" ng-model=\"$ctrl.current.employer.contact.city\"></salaxy-input>\r\n                    </div>\r\n                  </div>\r\n                </div>\r\n              </div>\r\n              <div class=\"row spacer-bottom\">\r\n                <div class=\"col-md-6 col-12 spacer-bottom\">\r\n                  <form class=\"form-horizontal\">\r\n                    <fieldset>\r\n                      <legend>\r\n                        <span sxy-text=\"Työsuhteen tiedot\"></span>\r\n                      </legend>\r\n                      <salaxy-input-enum input-mode=\"openClose\" enum=\"PensionCalculation\" name=\"PensionCalculation\" label=\"Sovellettava eläketurva\"\r\n                        ng-model=\"$ctrl.current.result.responsibilities.pensionCalculation\"></salaxy-input-enum>\r\n                      <salaxy-input-enum input-mode=\"openClose\" enum=\"PensionRule\" name=\"PensionRule\" label=\"Eläkemaksun laskentasääntö\"\r\n                        ng-model=\"$ctrl.current.result.responsibilities.pensionRule\"></salaxy-input-enum>\r\n                      <salaxy-input-enum input-mode=\"openClose\" enum=\"EmploymentRelationType\" name=\"EmploymentRelationType\" label=\"Työsuhde\"\r\n                        ng-model=\"$ctrl.current.result.responsibilities.employmentType\"></salaxy-input-enum>\r\n                      <salaxy-datepicker-popup input-mode=\"openClose\" name=\"employmentPeriodStart\" ng-model=\"$ctrl.current.worktime.employmentPeriod.start\"\r\n                        label=\"Työsuhteen alkupäivä\"></salaxy-datepicker-popup>\r\n                      <salaxy-datepicker-popup input-mode=\"openClose\" name=\"employmentPeriodEnd\" ng-model=\"$ctrl.current.worktime.employmentPeriod.end\"\r\n                        label=\"Työsuhteen loppupäivä\"></salaxy-datepicker-popup>\r\n                      <salaxy-input-enum input-mode=\"openClose\" ng-if=\"$ctrl.current.result.responsibilities.pensionCalculation == 'publicSector'\" type=\"select\"\r\n                        name=\"employmentRegCodes\" disable-cache=\"true\" options=\"$ctrl.getEmploymentRegCodeOptions()\"\r\n                        label=\"SALAXY.NG1.WorkerWizardComponent.employment.employmentRegCode\"\r\n                        ng-model=\"$ctrl.current.result.responsibilities.employmentRegCode\"></salaxy-input-enum>\r\n                      <salaxy-input-enum input-mode=\"openClose\" enum=\"TaxcardKind\" name=\"TaxcardKind\" label=\"Työsuhteessa käytettävä verokortti\"\r\n                        ng-model=\"$ctrl.current.result.responsibilities.employmentTaxcard\"></salaxy-input-enum>\r\n                      <salaxy-input-enum input-mode=\"openClose\" enum=\"EmploymentRelationSalaryPaymentMethod\" name=\"SalaryPaymentMethod\" label=\"Palkanmaksutapa\"\r\n                        ng-model=\"$ctrl.current.result.responsibilities.salaryPaymentMethod\"></salaxy-input-enum>\r\n                      <salaxy-input-enum input-mode=\"openClose\" enum=\"IncomeEarnerType\" name=\"irIncomeEarnerTypes\" label=\"Tulonsaajan tyyppi\" ng-model=\"$ctrl.current.result.responsibilities.irIncomeEarnerTypes\" type=\"multi-select\"></salaxy-input-enum>\r\n                      <salaxy-input-occupation-type input-mode=\"openClose\" name=\"occupationCode\" ng-model=\"$ctrl.current.info.occupationCode\" label=\"Ammattiluokka vakuutukseen\"\r\n                        read-only=\"false\">\r\n                      </salaxy-input-occupation-type>\r\n                      <salaxy-input\r\n                        tooltip-html=\"&lt;a target=&#39;_blank&#39; href=&#39;https://www.keva.fi/tyonantajalle/elakemaksut/ammattinimikkeiden-haku/&#39;&gt;Info&lt;/a&gt;\"\r\n                        ng-if=\"$ctrl.current.result.responsibilities.pensionCalculation == 'publicSector'\" input-mode=\"openClose\" name=\"occupationCode2\"\r\n                        ng-model=\"$ctrl.current.info.occupationCode2\" label=\"Keva:n ammattiluokka\" read-only=\"false\">\r\n                      </salaxy-input>\r\n                    </fieldset>\r\n                  </form>\r\n                </div>\r\n                <div class=\"col-md-6 col-12 spacer-bottom\">\r\n                  <div class=\"col-12\">\r\n                    <form class=\"form-horizontal\">\r\n                      <legend sxy-text=\"Palkanmaksu\"></legend>\r\n                      <salaxy-input-enum  input-mode=\"openClose\"  ng-model=\"$ctrl.current.workflow.salaryDateKind\" name=\"salaryDateKind\" enum=\"SalaryDateKind\"  label=\"SALAXY.MODEL.CalcWorkflow.salaryDateKind.title\"></salaxy-input-enum>\r\n                      <salaxy-datepicker-popup input-mode=\"openClose\" name=\"salaryDate\" ng-model=\"$ctrl.current.workflow.salaryDate\"\r\n                        label=\"SALAXY.NG1.CalcEditorComponent.paymentInfo.salaryDateLabel\"></salaxy-datepicker-popup>\r\n                      <salaxy-datepicker-popup read-only=\"!('admin' | sxyIsInRole)\" input-mode=\"openClose\" name=\"salaryPaidAt\" ng-model=\"$ctrl.current.workflow.paidAt\"\r\n                        label=\"SALAXY.NG1.CalcEditorComponent.paymentInfo.paymentDateLabel\"></salaxy-datepicker-popup>\r\n                      <salaxy-date-range input-mode=\"openClose\" ng-model=\"$ctrl.dateRange\" class=\"condensed\" name=\"dateRange\" on-change=\"$ctrl.dateRangeChange()\"\r\n                        label=\"SALAXY.CORE.CalcWorktime.salaryPeriod\" label-days-count=\"SALAXY.MODEL.CalcWorktime.workDays.title\"></salaxy-date-range>\r\n                      <salaxy-input-enum  read-only=\"true\" ng-model=\"$ctrl.current.info.paymentChannel\" name=\"paymentChannel\" enum=\"PaymentChannel\"  label=\"SALAXY.NG1.CalcEditorComponent.paymentInfo.paymentChannel\"></salaxy-input-enum>\r\n\r\n                    </form>\r\n                  </div>\r\n                  <div class=\"col-12\">\r\n                    <form class=\"form-horizontal\" ng-readonly=\"true\">\r\n                      <fieldset>\r\n                        <legend>\r\n                          <span sxy-text=\"Verokortin tiedot\"></span>\r\n                          <button class=\"btn btn-xs btn-default pull-right\" ng-click=\"$ctrl.selectTaxcard()\" sxy-text=\"SALAXY.UI_Terms.change\"></button>\r\n                        </legend>\r\n\r\n                        <salaxy-input-enum enum=\"TaxcardKind\" name=\"TaxcardKind\" label=\"Verokortti\" ng-model=\"$ctrl.current.worker.tax.snapshot.kind\"></salaxy-input-enum>\r\n                        <salaxy-input name=\"forYear\" label=\"Vuodelle\" ng-model=\"$ctrl.current.worker.tax.snapshot.forYear\"></salaxy-input>\r\n\r\n                        <salaxy-form-group name=\"validity\" class=\"salaxy-read-only\" label=\"Voimassa\">\r\n                          <div class=\"salaxy-read-only-value\">\r\n                            {{$ctrl.current.worker.tax.snapshot.validity.start | date}} - {{$ctrl.current.worker.tax.snapshot.validity.end | date}}\r\n                          </div>\r\n                        </salaxy-form-group>\r\n                        <salaxy-input label=\"veroprosentti\" name=\"Veroprosentti\" unit=\"percent\" ng-model=\"$ctrl.current.worker.tax.snapshot.taxPercent\"\r\n                          require=\"true\"></salaxy-input>\r\n                        <salaxy-input-number label=\"Tuloraja\" name=\"tuloraja\" unit=\"euro\" ng-model=\"$ctrl.current.worker.tax.snapshot.incomeLimit\"\r\n                          maxlength=\"10\"></salaxy-input-number>\r\n                        <salaxy-input label=\"Lisäveroprosentti\" name=\"lisaveroprosentti\" unit=\"percent\" ng-model=\"$ctrl.current.worker.tax.snapshot.taxPercent2\"></salaxy-input>\r\n                      </fieldset>\r\n                    </form>\r\n                  </div>\r\n                </div>\r\n              </div>\r\n              <div class=\"row spacer-bottom\">\r\n                <div class=\"col-md-6 col-12 spacer-bottom\">\r\n                  <form class=\"form-horizontal\">\r\n                    <fieldset>\r\n                      <legend>\r\n                        <span sxy-text=\"Vero, eläke- ja vakuutustiedot\"></span>\r\n                      </legend>\r\n                      <salaxy-input-enum input-mode=\"openClose\" label=\"Työeläkeyhtiö\" enum=\"PensionCompany\" name=\"PensionCompany\"\r\n                        ng-model=\"$ctrl.current.result.responsibilities.pensionCompany\"></salaxy-input-enum>\r\n                      <salaxy-input input-mode=\"openClose\" label=\"Sopimusnumero\" name=\"PensionContractNumber\" ng-model=\"$ctrl.current.result.responsibilities.pensionContractNumber\"\r\n                        sxy-pension-contract-number></salaxy-input>\r\n                      <salaxy-input ng-if=\"$ctrl.current.result.responsibilities.pensionCalculation == 'publicSector'\" input-mode=\"openClose\"\r\n                        label=\"SALAXY.MODEL.PensionContract.subOrgCode.title\" name=\"SubOrgCode\" ng-model=\"$ctrl.current.result.responsibilities.subOrgCode\"></salaxy-input>\r\n                      <salaxy-input-number input-mode=\"openClose\" ng-model=\"$ctrl.current.result.responsibilities.pensionPercent\" unit=\"percent\" name=\"PensionPercent\"\r\n                        label=\"SALAXY.MODEL.PensionContract.pensionPercent.title\"></salaxy-input-number>\r\n                      <salaxy-input-number input-mode=\"openClose\" ng-model=\"$ctrl.current.result.responsibilities.pensionDiscountPercent\" unit=\"percent\" name=\"PensionDiscount\"\r\n                        label=\"SALAXY.MODEL.PensionContract.pensionDiscountPercent.title\"></salaxy-input-number>\r\n                      <salaxy-input-boolean input-mode=\"openClose\" ng-model=\"$ctrl.current.result.responsibilities.pensionSelfPayment\" name=\"pensionSelfPayment\"\r\n                        label=\"Hoitaa TyEl-maksut itse\"></salaxy-input-boolean>\r\n\r\n                      <salaxy-input-enum input-mode=\"openClose\" ng-model=\"$ctrl.current.result.responsibilities.insuranceCompany\" label=\"Vakuutusyhtiö\" enum=\"InsuranceCompany\"\r\n                        name=\"InsuranceCompany\"></salaxy-input-enum>\r\n                      <salaxy-input input-mode=\"openClose\" ng-model=\"$ctrl.current.result.responsibilities.insuranceContractNumber\" name=\"insuranceContractNumber\"\r\n                        label=\"SALAXY.MODEL.InsuranceContract.contractNumber.title\"></salaxy-input>\r\n                      <salaxy-input-number input-mode=\"openClose\" label-cols=\"col-sm-6\" ng-model=\"$ctrl.current.result.responsibilities.insurancePercent\"\r\n                        label=\"Tapaturm.vak.maksun arvio-%\" unit=\"percent\" name=\"insurancePercent\"></salaxy-input-number>\r\n                      <salaxy-input-number input-mode=\"openClose\" label-cols=\"col-sm-6\" ng-model=\"$ctrl.current.result.responsibilities.groupLifeInsurancePercent\"\r\n                        label=\"SALAXY.MODEL.InsuranceContract.groupLifeInsurancePercent.title\" unit=\"percent\" name=\"groupLifeInsurancePercent\"></salaxy-input-number>\r\n\r\n                      <salaxy-input-enum input-mode=\"openClose\" ng-model=\"$ctrl.current.result.responsibilities.unemploymentPayrollLimitStatus\"\r\n                        label=\"Työt.vak.maksun palkkasummaraja\" enum=\"UnemploymentPayrollLimitStatus\" name=\"unemploymentPayrollLimitStatus\">\r\n                      </salaxy-input-enum>\r\n\r\n                    </fieldset>\r\n                  </form>\r\n                </div>\r\n                <div class=\"col-md-6 col-12 spacer-bottom\">\r\n                  <div class=\"col-12\">\r\n                    <form class=\"form-horizontal\" ng-readonly=\"true\">\r\n                      <fieldset>\r\n                        <legend sxy-text=\"SALAXY.NG1.CalcEditorComponent.messages.title\"></legend>\r\n                        <salaxy-input input-mode=\"openClose\" read-only=\"false\" name=\"workDescription\" ng-model=\"$ctrl.current.info.workDescription\"\r\n                          label=\"SALAXY.NG1.CalcEditorComponent.messages.workDescriptionLabel\"></salaxy-input>\r\n                        <salaxy-textarea input-mode=\"openClose\" read-only=\"false\" name=\"salarySlipMessage\" ng-model=\"$ctrl.current.info.salarySlipMessage\"\r\n                          label=\"SALAXY.NG1.CalcEditorComponent.messages.salarySlipMessageLabel\"></salaxy-textarea>\r\n                      </fieldset>\r\n                    </form>\r\n                  </div>\r\n                  <div class=\"col-12\">\r\n                    <div class=\"form-horizontal\">\r\n                      <salaxy-calc-cost-accounting read-only=\"false\" input-mode=\"openClose\" calc=\"$ctrl.current\"></salaxy-calc-cost-accounting>\r\n                    </div>\r\n                  </div>\r\n                </div>\r\n              </div>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"col-12 col-sm-12 col-md-12 col-lg-6 \">\r\n      <salaxy-tab-buttons\r\n        current-tab=\"$ctrl.currentTab\"\r\n        options=\"[\r\n          { value: 'edited', text: 'SALAXY.NG1.CalcEditorComponent.editedHeading' },\r\n          { value: 'default', text: 'SALAXY.NG1.CalcEditorComponent.originalHeading' },\r\n          { value: 'paymentreport', text: 'SALAXY.NG1.CalcEditorComponent.diffHeading' },\r\n          { value: 'accounting', text: 'SALAXY.NG1.CalcEditorComponent.diffAccountingHeading' },\r\n          { value: 'cfa', text: 'SALAXY.NG1.CalcEditorComponent.diffCfa', hidden: !('admin' | sxyIsInRole) },\r\n          { value: 'documentflow', text: 'Laskelma, palkkalistat, laskut ja ilmoitukset' },\r\n          { value: 'editedfields', text: 'Muokatut kentät' },\r\n        ]\"\r\n        tabs-id=\"calcRepair\">\r\n      </salaxy-tab-buttons>\r\n      <div class=\"tab-content\" id=\"tab-content-calcRepair\">\r\n        <div class=\"tab-pane\" id=\"edited-tab\">\r\n          <salaxy-calc-reports calcs=\"[$ctrl.current]\" report-type=\"$ctrl.shared.reportType\" on-report-type-change=\"$ctrl.shared.reportType=reportType\"></salaxy-calc-reports>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"default-tab\">\r\n          <salaxy-calc-reports ng-if=\"$ctrl.base\" calcs=\"[$ctrl.base]\" report-type=\"$ctrl.shared.reportType\"\r\n            on-report-type-change=\"$ctrl.shared.reportType=reportType\"></salaxy-calc-reports>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"paymentreport-tab\">\r\n          <div class=\"payroll-report payroll-report-partial-container\">\r\n            <salaxy-calc-report ng-if=\"$ctrl.base\" calc=\"$ctrl.diffCalc\" report-type=\"'paymentReport'\" template-name=\"'paymentTablesV2'\" apply-site-styles=\"true\">\r\n          </div>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"accounting-tab\">\r\n          <salaxy-accounting-report-tools any-expanded=\"$reportRows.anyExpanded\" on-expand-change=\"$reportRows.expand(close)\" on-target-change=\"$ctrl.onTargetChange(targetId)\"\r\n            reader=\"$ctrl.accountingDiffDataReader\"></salaxy-accounting-report-tools>\r\n          <salaxy-accounting-report-rows ng-ref=\"$reportRows\" data=\"$ctrl.accountingDiffData\"></salaxy-accounting-report-rows>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"cfa-tab\" ng-if=\"'admin' | sxyIsInRole\">\r\n          <div>\r\n            <table class=\"table table-striped\">\r\n              <tr>\r\n                <th>Erä</th>\r\n                <th class=\"text-right\">Alkuperäinen summa</th>\r\n                <th class=\"text-right\">Korjattu summa</th>\r\n                <th class=\"text-right\">Ero</th>\r\n              </tr>\r\n              <tr>\r\n                <td>Nettopalkka</td>\r\n                <td class=\"text-right\">{{ $ctrl.baseCfa.net | currency}}</td>\r\n                <td class=\"text-right\">{{ $ctrl.currentCfa.net | currency}}</td>\r\n                <td class=\"text-right\">{{ ($ctrl.currentCfa.net - $ctrl.baseCfa.net) | currency}}</td>\r\n              </tr>\r\n              <tr>\r\n                <td>Eläke</td>\r\n                <td class=\"text-right\">{{ $ctrl.baseCfa.pension | currency}}</td>\r\n                <td class=\"text-right\">{{ $ctrl.currentCfa.pension | currency}}</td>\r\n                <td class=\"text-right\">{{ ($ctrl.currentCfa.pension - $ctrl.baseCfa.pension) | currency}}</td>\r\n              </tr>\r\n              <tr>\r\n                <td>Vero</td>\r\n                <td class=\"text-right\">{{ $ctrl.baseCfa.tax | currency}}</td>\r\n                <td class=\"text-right\">{{ $ctrl.currentCfa.tax | currency}}</td>\r\n                <td class=\"text-right\">{{ ($ctrl.currentCfa.tax - $ctrl.baseCfa.tax) | currency}}</td>\r\n              </tr>\r\n              <tr>\r\n                <td>Palvelumaksu</td>\r\n                <td class=\"text-right\">{{ $ctrl.baseCfa.service | currency}}</td>\r\n                <td class=\"text-right\">{{ $ctrl.currentCfa.service | currency}}</td>\r\n                <td class=\"text-right\">{{ ($ctrl.currentCfa.service - $ctrl.baseCfa.service) | currency}}</td>\r\n              </tr>\r\n              <tr>\r\n                <td>Palkkio</td>\r\n                <td class=\"text-right\">{{ $ctrl.baseCfa.fee | currency}}</td>\r\n                <td class=\"text-right\">{{ $ctrl.currentCfa.fee | currency}}</td>\r\n                <td class=\"text-right\">{{ ($ctrl.currentCfa.fee - $ctrl.baseCfa.fee) | currency}}</td>\r\n              </tr>\r\n              <tr class=\"total\">\r\n                <td>Yhteensä</td>\r\n                <td class=\"text-right\">{{ $ctrl.baseCfa.total | currency}}</td>\r\n                <td class=\"text-right\">{{ $ctrl.currentCfa.total | currency}}</td>\r\n                <td class=\"text-right\">{{ ($ctrl.currentCfa.total - $ctrl.baseCfa.total) | currency}}</td>\r\n              </tr>\r\n            </table>\r\n          </div>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"documentflow-tab\">\r\n          <div>\r\n            <table class=\"table table-striped\">\r\n              <tr ng-if=\"$ctrl.documentFlow.item\">\r\n                <td>\r\n                  <salaxy-avatar class=\"salaxy-calc-row-type-avatar\"\r\n                    avatar=\"$ctrl.documentFlow.item.otherPartyInfo.avatar\"></salaxy-avatar>\r\n                </td>\r\n                <td class=\"middle\">\r\n                  <strong >{{'Palkkalaskelma' |sxyTranslate}}</strong>\r\n                </td>\r\n                <td>\r\n                  <a class=\"btn btn-default btn-sm\" ng-href=\"#/calc/details/{{$ctrl.documentFlow.item.id}}\">Näytä</a>\r\n                </td>\r\n              </tr>\r\n              <tr ng-repeat=\"doc in $ctrl.documentFlow.children\" ng-if=\"$ctrl.documentFlow.children\">\r\n                <td>\r\n                  <salaxy-avatar ng-if=\"doc.item.type != 'payerSummary' && doc.item.type != 'payrollDetails'\" class=\"salaxy-calc-row-type-avatar\"\r\n                    avatar=\"doc.item.otherPartyInfo.avatar\"></salaxy-avatar>\r\n                  <salaxy-avatar ng-if=\"doc.item.type == 'payerSummary' || doc.item.type == 'payrollDetails'\" class=\"salaxy-calc-row-type-avatar\"\r\n                    avatar=\"doc.item.ownerInfo.avatar\"></salaxy-avatar>\r\n                </td>\r\n                <td class=\"middle\">\r\n                  <strong ng-if=\"doc.item.type == 'invoice'\">{{doc.item.shortText}}</strong>\r\n                  <strong ng-if=\"doc.item.type == 'earningsPayment'\">{{'Palkkatietoilmoitus' |sxyTranslate}}</strong>\r\n                  <strong ng-if=\"doc.item.type == 'payrollDetails'\">{{'Palkkalista' |sxyTranslate}}</strong>\r\n                  <strong ng-if=\"doc.item.type == 'payerSummary'\">{{'Erillisilmoitus' |sxyTranslate}}</strong>\r\n                  <strong ng-if=\"doc.item.type == 'taxcard'\">{{'Verokortti' |sxyTranslate}}</strong>\r\n                </td>\r\n                <td>\r\n                  <a ng-if=\"doc.item.type == 'earningsPayment'\" class=\"btn btn-default btn-sm\" ng-href=\"#/irepr/details/{{doc.item.id}}\">Näytä</a>\r\n                  <a ng-if=\"doc.item.type == 'invoice'\" class=\"btn btn-default btn-sm\" ng-href=\"#/invoices/details/{{doc.item.id}}\">\r\n                    {{ 'SALAXY.UI_Terms.show' | sxyTranslate}}</a>\r\n                  <a ng-if=\"doc.item.type == 'payerSummary'\" class=\"btn btn-default btn-sm\" ng-href=\"#/irpsr/details/{{doc.item.id}}\">Näytä</a>\r\n                  <a ng-if=\"doc.item.type == 'payrollDetails'\" class=\"btn btn-default btn-sm\" ng-href=\"#/payroll/details/{{doc.item.id}}\">Näytä</a>\r\n                  <a ng-if=\"doc.item.type == 'taxcard'\" class=\"btn btn-default btn-sm\" ng-href=\"#/taxcards/details/{{doc.item.id}}\">Näytä</a>\r\n                </td>\r\n              </tr>\r\n            </table>\r\n          </div>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"editedfields-tab\">\r\n          <salaxy-json-diff json=\"$ctrl.base\" compare-to=\"$ctrl.current\" exclude-paths=\"$ctrl.excludeDiffPaths\" item-type=\"'Calculation'\"></salaxy-json-diff>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/CalcRepairInfo.html\",`<span ng-if=\"$ctrl.current.workflow.repairedAt\" class=\"salaxy-component salaxy-calc-repair-info\">\r\n  <a class=\"btn-link\"  ng-click=\"$ctrl.showRepaired()\">\r\n     <span>{{'Laskelman aiemmat versiot' | sxyTranslate}}</span>\r\n  </a>\r\n</span>`);\n\n $templateCache.put(\"salaxy-components/calc/CalcReport.html\",`<div ng-if=\"$ctrl.reportType != 'totalsReport'\" class=\"salaxy-component salaxy-calc-report\">\r\n  <div ng-class=\"{'report-table-html': $ctrl.applySiteStyles}\">\r\n    <div ng-bind-html=\"$ctrl.html\" class=\"report-binder table-responsive\"></div>\r\n  </div>\r\n  <p ng-if=\"('person' | sxyIsInRole) && $ctrl.calc.workflow.status !== 'paymentWorkerCopy'\">{{'SALAXY.NG1.CalcReportComponent.palkkausFeeInfo' | sxyTranslate}}</p>\r\n</div>\r\n<div ng-if=\"$ctrl.reportType == 'totalsReport'\" class=\"salaxy-component\">\r\n  <sxy-table ng-ref=\"$ctrl.$sxyTable\" options=\"$ctrl.tableConfig.options\" include=\"$ctrl.tableConfig.include\" data=\"$ctrl.tableConfig.data\"></sxy-table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/CalcReports.html\",`<div class=\"salaxy-component salaxy-calc-reports\">\r\n  <div class=\"btn-toolbar w-100 mb-3\" role=\"toolbar\" aria-label=\"Report options\">\r\n    <div class=\"btn-group btn-group-sm dropdown\">\r\n      <button id=\"single-button\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\" ng-disabled=\"disabled\">\r\n        <span ng-if=\"!($ctrl.reportType == 'irRows' || $ctrl.reportType == 'irFull' || $ctrl.reportType == 'rowsReport')\">\r\n          <span sxy-text=\"SALAXY.NG1.CalcReportsComponent.reportType\" ps=\":\"></span>\r\n          {{ \"ReportType.\" + $ctrl.reportType | sxyEnum }} \r\n        </span>\r\n        <span ng-if=\"$ctrl.reportType == 'irRows'\" >\r\n          <span sxy-text=\"SALAXY.NG1.CalcReportsComponent.reportType\" ps=\":\"></span> {{\"SALAXY.NG1.CalcReportsComponent.irRows\" | sxyTranslate}}\r\n        </span>\r\n        <span ng-if=\"$ctrl.reportType == 'irFull'\" >\r\n          <span sxy-text=\"SALAXY.NG1.CalcReportsComponent.reportType\" ps=\":\"></span> {{\"SALAXY.NG1.CalcReportsComponent.irFull\" | sxyTranslate}}\r\n        </span>\r\n        <span ng-if=\"$ctrl.reportType == 'rowsReport'\" >\r\n          <span sxy-text=\"SALAXY.NG1.CalcReportsComponent.reportType\" ps=\":\"></span> {{\"SALAXY.NG1.CalcReportsComponent.rowsReport\" | sxyTranslate}}\r\n        </span>\r\n      </button>\r\n      <ul class=\"dropdown-menu\"  role=\"menu\" aria-labelledby=\"single-button\">\r\n        <li role=\"menuitem\"><a href=\"\" ng-click=\"$ctrl.reportType = 'salarySlip'\" class=\"dropdown-item\">{{ \"ReportType.salarySlip\" | sxyEnum }}</a></li>\r\n        <li role=\"menuitem\"><a href=\"\" ng-click=\"$ctrl.reportType = 'employerReport'\" class=\"dropdown-item\">{{ \"ReportType.employerReport\" | sxyEnum }}</a></li>\r\n        <li role=\"menuitem\"><a href=\"\" ng-click=\"$ctrl.reportType = 'paymentReport'\" class=\"dropdown-item\" class=\"dropdown-item\">{{ \"ReportType.paymentReport\" | sxyEnum }}</a></li>\r\n        <li role=\"menuitem\"><a href=\"\" ng-click=\"$ctrl.reportType = 'paymentSummaryReport'\" class=\"dropdown-item\">{{ \"ReportType.paymentSummaryReport\" | sxyEnum }}</a></li>\r\n        <li role=\"menuitem\"><a href=\"\" ng-click=\"$ctrl.reportType = 'accountingReport'\" class=\"dropdown-item\">{{ \"ReportType.accountingReport\" | sxyEnum }}</a></li>\r\n        <li role=\"menuitem\"><a href=\"\" ng-click=\"$ctrl.reportType = 'totalsReport'\" class=\"dropdown-item\">{{ \"ReportType.totalsReport\" | sxyEnum }}</a></li>\r\n        <li role=\"menuitem\"><a href=\"\" ng-click=\"$ctrl.reportType = 'rowsReport'\" class=\"dropdown-item\">{{\"SALAXY.NG1.CalcReportsComponent.rowsReport\" | sxyTranslate}}</a></li>\r\n        <li role=\"menuitem\"><a href=\"\" ng-click=\"$ctrl.reportType = 'irRows'\" class=\"dropdown-item\">{{\"SALAXY.NG1.CalcReportsComponent.irRows\" | sxyTranslate}}</a></li>\r\n        <li role=\"menuitem\"><a href=\"\" ng-click=\"$ctrl.reportType = 'irFull'\" class=\"dropdown-item\">{{\"SALAXY.NG1.CalcReportsComponent.irFull\" | sxyTranslate}}</a></li>\r\n        <li role=\"menuitem\" ng-if=\"'test' | sxyIsInRole\"><a href=\"\" ng-click=\"$ctrl.reportType = 'costCenterReport'\" class=\"dropdown-item\">{{\"SALAXY.NG1.CalcReportsComponent.costCenterReport\" | sxyTranslate}}</a></li>\r\n      </ul>\r\n    </div>\r\n    <!-- \r\n      TODO: When implementing, use <salaxy-input-enum type=\"ui-dropdown\">\r\n      Needs some fixes to the component (e.g. btn-group-sm support)\r\n    -->\r\n    <div class=\"btn-group ms-1 btn-group-sm dropdown\">\r\n      <button id=\"single-button2\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\" ng-disabled=\"disabled\">\r\n        <span sxy-text=\"SALAXY.NG1.CalcReportsComponent.reportLanguage\" ps=\":\"></span> {{$ctrl.languageText | sxyTranslate}}\r\n      </button>\r\n      <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"single-button2\">\r\n        <li ng-if=\"$ctrl.reportType == 'salarySlip' || $ctrl.reportType == 'employerReport' || $ctrl.reportType == 'paymentReport'\" role=\"menuitem\">\r\n          <a href=\"\" ng-click=\"$ctrl.setReportLang('default')\" class=\"dropdown-item\"  sxy-text=\"SALAXY.NG1.CalcReportsComponent.reportLanguageWorker\"></a>\r\n        </li>\r\n        <li ng-if=\"!($ctrl.reportType == 'salarySlip' || $ctrl.reportType == 'employerReport' || $ctrl.reportType == 'paymentReport')\" role=\"menuitem\">\r\n          <a href=\"\" ng-click=\"$ctrl.setReportLang('default')\" class=\"dropdown-item\"  sxy-text=\"SALAXY.NG1.CalcReportsComponent.reportLanguageCompany\"></a>\r\n        </li>\r\n        <li role=\"menuitem\">\r\n          <a href=\"\" ng-click=\"$ctrl.setReportLang('fi')\" class=\"dropdown-item\" sxy-text=\"SALAXY.ENUM.Language.fi.label\"></a>\r\n        </li>\r\n        <li role=\"menuitem\">\r\n          <a href=\"\" ng-click=\"$ctrl.setReportLang('en')\" class=\"dropdown-item\" sxy-text=\"SALAXY.ENUM.Language.en.label\"></a>\r\n        </li>\r\n        <li role=\"menuitem\">\r\n          <a href=\"\" ng-click=\"$ctrl.setReportLang('sv')\" class=\"dropdown-item\" sxy-text=\"SALAXY.ENUM.Language.sv.label\"></a>\r\n        </li>\r\n      </ul>\r\n    </div>\r\n    <salaxy-toggle-buttons ng-show=\"$ctrl.reportType !== 'eSalarySpecification' && $ctrl.reportType !== 'totalsReport' && $ctrl.reportType !== 'irRows' && $ctrl.reportType !== 'rowsReport'\" ng-model=\"$ctrl.view\" options=\"[\r\n      { value: 'partial', label: 'SALAXY.NG1.CalcReportsComponent.reportViewPartial' },\r\n      { value: 'page1', label: 'SALAXY.NG1.CalcReportsComponent.reportViewPage1', disabled: ($ctrl.reportType == 'accountingReport') },\r\n      { value: 'full', label: 'SALAXY.NG1.CalcReportsComponent.reportViewFull' }\r\n    ]\" type=\"inline\"></salaxy-toggle-buttons>\r\n    <button ng-show=\"$ctrl.reportType !== 'eSalarySpecification' && $ctrl.reportType !== 'totalsReport' && $ctrl.reportType !== 'irRows' && $ctrl.reportType !== 'rowsReport'\" class=\"btn btn-default btn-sm\" ng-click=\"$ctrl.reload()\"><i class=\"bi bi-arrow-repeat\" aria-hidden=\"true\"></i></button>\r\n\r\n    <div ng-show=\"$ctrl.reportType !== 'eSalarySpecification' && $ctrl.reportType !== 'totalsReport' && $ctrl.reportType !== 'irRows' && $ctrl.reportType !== 'rowsReport' && $ctrl.reportType !== 'accountingReport'\" class=\"btn-group btn-group-sm ms-auto\" role=\"group\" aria-label=\"Pdf\">\r\n      <button sxy-if-role=\"!anon\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showDownloadDialog(true)\">\r\n        <span class=\"d-none d-md-inline-block\" sxy-text=\"SALAXY.UI_Terms.print\"></span>\r\n        <i class=\"bi bi-printer\" aria-hidden=\"true\"></i>\r\n      </button>\r\n      <button sxy-if-role=\"!anon\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showDownloadDialog(false)\">\r\n        <span class=\"d-none d-md-inline-block\" sxy-text=\"SALAXY.UI_Terms.downloadPdf\"></span>\r\n        <i class=\"bi bi-file-earmark-pdf\" aria-hidden=\"true\"></i>\r\n      </button>\r\n    </div>\r\n    <div ng-show=\"$ctrl.reportType == 'totalsReport' || $ctrl.reportType == 'irRows' || $ctrl.reportType == 'rowsReport'\" class=\"btn-group btn-group-sm ms-auto\" role=\"group\" aria-label=\"Excel\">\r\n      <button sxy-if-role=\"!anon\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.downloadExcel()\">\r\n        <span class=\"d-none d-md-inline-block\" sxy-text=\"SALAXY.UI_Terms.downloadExcel\"></span>\r\n        <i class=\"bi bi-file-earmark-excel\" aria-hidden=\"true\"></i>\r\n      </button>\r\n    </div>\r\n  </div>\r\n\r\n  <!-- Results view -->\r\n  <div ng-switch=\"$ctrl.reportType || 'none'\">\r\n    <div ng-switch-when=\"accountingReport\">\r\n      <div class=\"payroll-report\" ng-class=\"{'payroll-accounting-report-partial-container': $ctrl.view == 'partial'}\">\r\n        <salaxy-accounting-report-query ng-if=\"$ctrl.getEmployerLang() && $ctrl.getEmployerLang() !== 'default'\" lang=\"$ctrl.getEmployerLang()\" calcs=\"$ctrl.calcs\"\r\n          view=\"$ctrl.view\">\r\n          </salaxy-accouting-report-query>\r\n      </div>\r\n    </div>\r\n    <div ng-switch-when=\"paymentSummaryReport\">\r\n      <!-- TODO: Below development of new summary report, cleaned/moved later -->\r\n      <div class=\"payroll-report\" ng-class=\"{'payroll-report-partial-container': $ctrl.view == 'partial'}\">\r\n        <salaxy-calc-report ng-if=\"$ctrl.getEmployerLang() && $ctrl.getEmployerLang() !== 'default'\" lang=\"$ctrl.getEmployerLang()\" calc=\"$ctrl.calcs\"\r\n          apply-site-styles=\"$ctrl.view == 'partial'\" report-type=\"$ctrl.reportType\" preview=\"$ctrl.preview\" template-name=\"$ctrl.reports[$ctrl.reportType][$ctrl.view]\">\r\n        </salaxy-calc-report>\r\n      </div>\r\n    </div>\r\n    <div ng-switch-when=\"totalsReport\">\r\n      <!-- TODO: Set preview false or get rid of it -->\r\n      <salaxy-calc-report class=\"report\" ng-ref=\"$ctrl.$calcReports\" ng-if=\"$ctrl.getEmployerLang() && $ctrl.getEmployerLang() !== 'default'\" lang=\"$ctrl.getEmployerLang()\" calc=\"$ctrl.calcs\"\r\n        apply-site-styles=\"$ctrl.view == 'partial'\" report-type=\"$ctrl.reportType\" preview=\"$ctrl.preview\" template-name=\"$ctrl.reports[$ctrl.reportType][$ctrl.view]\">\r\n      </salaxy-calc-report>\r\n    </div>\r\n    <div ng-switch-when=\"rowsReport\">\r\n      <sxy-table ng-ref=\"$ctrl.$sxyTable\" options=\"$ctrl.reportTableConfig.options\" include=\"$ctrl.reportTableConfig.include\"\r\n        data=\"$ctrl.reportTableConfig.data\" class=\"report\"></sxy-table>\r\n    </div>\r\n    <div ng-switch-when=\"irRows\">\r\n      <salaxy-calcs-ir-rows ng-ref=\"$ctrl.$calcsIrRows\" calcs=\"$ctrl.calcs\" lang=\"$ctrl.getEmployerLang()\" class=\"report\"></salaxy-calcs-ir-rows>\r\n    </div>\r\n    <div ng-switch-when=\"irFull\">\r\n      <div ng-repeat=\"calc in $ctrl.calcs\">\r\n        <salaxy-ir-earnings-payment ng-if=\"calc.workflow.status == 'paymentSucceeded'\" calculation=\"calc\"></salaxy-ir-earnings-payment>\r\n        <salaxy-ir-earnings-payment ng-if=\"calc.workflow.status != 'paymentSucceeded' && $ctrl.loadEpr(calc)\" calculation-for=\"calc\" model=\"$ctrl.loadEpr(calc)\" ></salaxy-ir-earnings-payment>\r\n      </div>\r\n    </div>\r\n    <div ng-switch-when=\"costCenterReport\" ng-if=\"'test' | sxyIsInRole\">\r\n      <sxy-table class=\"report\" ng-if=\"$ctrl.reportTableConfig.data\" ng-ref=\"$ctrl.$sxyTable\" options=\"$ctrl.reportTableConfig.options\" include=\"$ctrl.reportTableConfig.include\" data=\"$ctrl.reportTableConfig.data\"></sxy-table>\r\n    </div>\r\n    <div ng-switch-when=\"none\">\r\n      <!-- Report type not selected -->\r\n    </div>\r\n    <div ng-switch-default=\"\">\r\n      <div ng-repeat=\"calc in $ctrl.calcs\" class=\"payroll-report\" ng-class=\"{'payroll-report-partial-container': $ctrl.view == 'partial'}\">\r\n        <salaxy-calc-worker-info model=\"calc\" ng-if=\"$ctrl.view == 'partial'\"></salaxy-calc-worker-info>\r\n        <salaxy-calc-report ng-if=\"$ctrl.getWorkerLang(calc) && $ctrl.getWorkerLang(calc) !== 'default'\" lang=\"$ctrl.getWorkerLang(calc)\" calc=\"calc\"\r\n          apply-site-styles=\"$ctrl.view == 'partial'\" report-type=\"$ctrl.reportType\" preview=\"$ctrl.preview\" template-name=\"$ctrl.reports[$ctrl.reportType][$ctrl.view]\">\r\n        </salaxy-calc-report>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/CalcResults.html\",`<div class=\"result-area\" ng-if=\"$ctrl.currentCalc && $ctrl.calcSections.get('result').isSelectionDone\">\r\n  <div class=\"card border-primary\" style=\"padding: 10px\">\r\n    <div class=\"card-body\">\r\n      <div class=\"row\">\r\n        <div class=\"col-12 col-md-4 order-1 order-md-2 calc-results-actions\">\r\n          <h2 class=\"text-center uppercase text-uppercase fw-normal\"> {{ $ctrl.calcLogic.hasCompensation ? (\"SALAXY.NG1.CalcResultsComponent.calculation\" | sxyTranslate) : (\"SALAXY.NG1.CalcResultsComponent.calculationSalary\" | sxyTranslate) }}</h2>\r\n          <div salaxy-if-role=\"anon\">\r\n            <button type=\"button\" ng-click=\"$ctrl.register()\" class=\"btn btn-info btn-block\" sxy-text=\"SALAXY.UI_Terms.register\"></button>\r\n            <button type=\"button\" ng-click=\"$ctrl.signIn()\" class=\"btn btn-success btn-block\" sxy-text=\"SALAXY.UI_Terms.login\"></button>\r\n          </div>\r\n          \r\n          <salaxy-validation-summary ng-if=\"$ctrl.currentCalc.workflow.status != 'sharedWaiting'\" api-validation=\"$ctrl.validation\"></salaxy-validation-summary>\r\n            \r\n          <p ng-if=\"$ctrl.currentCalc.workflow.status == 'payrollDraft'\" class=\"text-center\">\r\n            <strong class=\"text-success\" sxy-text=\"SALAXY.NG1.CalcResultsComponent.payrollDraft\"></strong><br>\r\n            <span sxy-text=\"SALAXY.NG1.CalcResultsComponent.payrollDraftInfo\"></span>\r\n          </p>\r\n          <p ng-if=\"$ctrl.currentCalc.workflow.status == 'sharedWaiting'\" class=\"text-center\">\r\n            <strong class=\"text-warning\" sxy-text=\"SALAXY.NG1.CalcResultsComponent.sharedWaiting\"></strong>\r\n            <br> <span sxy-text=\"SALAXY.NG1.CalcResultsComponent.sharedWaitingInfo\"></span>\r\n          </p>\r\n          <p ng-if=\"$ctrl.currentCalc.workflow.status == 'sharedApproved'\" class=\"text-center\">\r\n            <strong class=\"text-success\" sxy-text=\"SALAXY.NG1.CalcResultsComponent.sharedApproved\"></strong>\r\n            <br>\r\n            <span ng-if=\"$ctrl.validation.isValid\" sxy-text=\"SALAXY.NG1.CalcResultsComponent.draftInfo\"></span>\r\n          </p>\r\n          <p ng-if=\"$ctrl.currentCalc.workflow.status == 'sharedRejected'\" class=\"text-center\">\r\n            <strong class=\"text-danger\" sxy-text=\"SALAXY.NG1.CalcResultsComponent.sharedRejected\"></strong>\r\n          </p>\r\n          <p ng-if=\"$ctrl.currentCalc.workflow.status == 'paymentStarted'\" class=\"text-center\">\r\n            <strong class=\"text-success\" sxy-text=\"SALAXY.NG1.CalcResultsComponent.paymentStarted\"></strong>\r\n            <br>{{ $ctrl.currentCalc.workflow.paidAt | date }}\r\n            <span ng-if=\"$ctrl.currentCalc.info.paymentChannel != 'undefined'\">, <span sxy-text=\"SALAXY.NG1.CalcResultsComponent.paymentChannelTextPartial\"></span> {{ \"PaymentChannel.\" + $ctrl.currentCalc.info.paymentChannel | sxyEnum }}</span>.\r\n            <span ng-if=\"$ctrl.currentCalc.workflow.salaryDateKind == 'inPast'\">\r\n              {{\"SALAXY.ENUM.SalaryDateKind.\" + ($ctrl.currentCalc.workflow.salaryDateKind) + \".label\" | sxyTranslate  }}.\r\n            </span>\r\n          </p>\r\n          <p ng-if=\"$ctrl.currentCalc.workflow.status == 'paymentSucceeded' || $ctrl.currentCalc.workflow.status == 'paymentCanceled' || $ctrl.currentCalc.workflow.status == 'paymentRefunded' || $ctrl.currentCalc.workflow.status == 'paymentError'\" class=\"text-center\">\r\n            <strong ng-if=\"$ctrl.currentCalc.workflow.status == 'paymentSucceeded'\" class=\"text-success\" sxy-text=\"SALAXY.NG1.CalcResultsComponent.isPaidDate\"></strong>\r\n            <strong ng-if=\"$ctrl.currentCalc.workflow.status == 'paymentError'\" class=\"text-danger\" sxy-text=\"SALAXY.NG1.CalcResultsComponent.paymentError\"></strong>\r\n            <strong ng-if=\"$ctrl.currentCalc.workflow.status == 'paymentRefunded'\" class=\"\" sxy-text=\"SALAXY.NG1.CalcResultsComponent.paymentRefunded\"></strong>\r\n            <strong  ng-if=\"$ctrl.currentCalc.workflow.status == 'paymentCanceled'\" class=\"\" sxy-text=\"SALAXY.NG1.CalcResultsComponent.paymentCanceled\"></strong>\r\n           \r\n            <br>{{ $ctrl.currentCalc.workflow.paidAt | date }}\r\n            <span ng-if=\"$ctrl.currentCalc.info.paymentChannel != 'undefined'\">, <span sxy-text=\"SALAXY.NG1.CalcResultsComponent.paymentChannelTextPartial\"></span> {{ \"PaymentChannel.\" + $ctrl.currentCalc.info.paymentChannel | sxyEnum }}</span>.\r\n            <span ng-if=\"$ctrl.currentCalc.workflow.salaryDateKind == 'inPast'\">\r\n              {{\"SALAXY.ENUM.SalaryDateKind.\" + ($ctrl.currentCalc.workflow.salaryDateKind) + \".label\" | sxyTranslate  }}.\r\n            </span>\r\n            <salaxy-calc-repair-info model=\"$ctrl\" ng-if=\"(('repairs' | sxyIsInRole) || ('admin' | sxyIsInRole)) && $ctrl.currentCalc.workflow.status == 'paymentSucceeded'\"></salaxy-calc-repair-info>\r\n          </p>\r\n          <p ng-if=\"$ctrl.currentCalc.workflow.status == 'draft'\" class=\"text-center\">\r\n            <span ng-if=\"$ctrl.isReadOnly\" sxy-text=\"SALAXY.NG1.CalcResultsComponent.draft\"></span>\r\n            <br>\r\n            <span ng-if=\"$ctrl.validation.isValid  && ('!worker' | sxyIsInRole) && !$ctrl.isReadOnly\" sxy-text=\"SALAXY.NG1.CalcResultsComponent.draftInfo\"></span>\r\n          </p>\r\n          <div ng-if=\"('auth' | sxyIsInRole) && ('!worker' | sxyIsInRole)\">\r\n            <div ng-if=\"$ctrl.showAction('sendToPro')\">\r\n              <p  class=\"text-center\">\r\n                <strong class=\"text-success\" sxy-text=\"SALAXY.NG1.CalcResultsComponent.waitingApproval\"></strong>\r\n                <br>\r\n                <span sxy-text=\"SALAXY.NG1.CalcResultsComponent.waitingApprovalInfo\"></span>\r\n              </p>\r\n              <div class=\"form-horizontal mb-1\">\r\n                <salaxy-textarea  name=\"workflowMessage\" ng-model=\"$ctrl.workflowMessage\" label=\"SALAXY.NG1.CalcResultsComponent.messageToAccountant\" label-type=\"basic\"></salaxy-textarea>\r\n              </div>\r\n              <div class=\"text-center\">\r\n                <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.sendToPro($ctrl.workflowMessage)\" sxy-text=\"SALAXY.NG1.CalcResultsComponent.sendToProBtn\" ps=\"»\"></button>\r\n              </div>\r\n            </div>\r\n            <div ng-if=\"$ctrl.showAction('showPaymentDialog')\" class=\"text-center mb-1\">\r\n              <a href=\"\" ng-click=\"$ctrl.showPaymentDialog()\" sxy-text=\"SALAXY.NG1.CalcResultsComponent.showPaymentDialog\"></a>.\r\n            </div>\r\n            <div ng-if=\"$ctrl.showAction('continuePsdPayment') && ('salaxyPay' | sxyIsInRole)\" ng-controller=\"NewPaymentController as $newPaymentCtrl\" class=\"text-center mb-1\">\r\n              <button type=\"button\" ng-click=\"$newPaymentCtrl.openSalaxyPay($ctrl.currentCalc, 2)\" class=\"btn btn-primary btn-block\" sxy-text=\"SALAXY.NG1.CalcResultsComponent.continuePsdPayment\"></button>\r\n              \r\n            </div>\r\n            <div ng-if=\"!$ctrl.validation.isValid\">\r\n              <salaxy-pay-button ng-if=\"$ctrl.showAction('allowForcePay')\" label=\"SALAXY.UI_Terms.payAllShort\" model=\"$ctrl.currentCalc\" mode=\"button-and-channel\" button-class=\"uppercase\" ng-ref=\"$payButton\" disabled=\"!$payButton.isChannelDefined\" on-payment-channel-change=\"$ctrl.recalculate()\"></salaxy-pay-button>\r\n            </div>\r\n            <div ng-if=\"$ctrl.validation.isValid\">\r\n              <div ng-if=\"$ctrl.showAction('pay')\" class=\"mb-1\">\r\n                <salaxy-pay-button model=\"$ctrl.currentCalc\" mode=\"button-and-channel\" salaxy-if-role=\"employer\" button-class=\"uppercase\" ng-ref=\"$payButton\" disabled=\"!$payButton.isChannelDefined\" on-payment-channel-change=\"$ctrl.recalculate()\"></salaxy-pay-button>\r\n                <salaxy-salary-date-kind-button ng-if=\"$ctrl.showAction('setSalaryDateKind') && ('test,setSalaryDateKind' | sxyIsInRole) && ('employer' | sxyIsInRole)\" button-class=\"btn-block\" model=\"$ctrl.currentCalc\" disabled=\"$ctrl.currentCalc.isReadOnly || $ctrl.isReadOnlyForced\" on-salary-date-kind-change=\"$ctrl.recalculate()\"></salaxy-salary-date-kind-button>\r\n              </div>\r\n            </div> \r\n            <div ng-if=\"$ctrl.showAction('save')\" class=\"mb-1\">\r\n              <button type=\"button\" ng-click=\"$ctrl.save()\" class=\"btn btn-success btn-block\" ng-disabled=\"$ctrl.isActionDisabled('save')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n            </div>\r\n            <div ng-if=\"$ctrl.showAction('reject')\" class=\"mb-1\">\r\n              <salaxy-calc-sharing-receipt-action button-class=\"btn btn-danger btn-block\" model=\"$ctrl\" type=\"'reject'\"></salaxy-calc-sharing-receipt-action>\r\n            </div>\r\n            <div ng-if=\"$ctrl.showAction('approve')\" class=\"mb-1\">\r\n              <salaxy-calc-sharing-receipt-action button-class=\"btn btn-success btn-block\" model=\"$ctrl\" type=\"'approve'\"></salaxy-calc-sharing-receipt-action>\r\n            </div>\r\n            <button ng-if=\"$ctrl.showAction('delete')\" type=\"button\" ng-click=\"$ctrl.deleteCalc()\" ng-disabled=\"$ctrl.isActionDisabled('delete')\" class=\"btn btn-danger btn-block\" sxy-text=\"SALAXY.UI_Terms.delete\"></button>\r\n            <button ng-if=\"$ctrl.showAction('cancel')\" class=\"btn btn-default btn-sm btn-block\" ng-click=\"$ctrl.cancel()\" sxy-text=\"SALAXY.NG1.CalcResultsComponent.cancelPaymentOrChangeChannelBtn\"></button>\r\n            \r\n            <button ng-if=\"$ctrl.showAction('copyAsNew')\" type=\"button\" ng-click=\"$ctrl.copyAsNew()\" class=\"btn btn-primary btn-block\" sxy-text=\"SALAXY.UI_Terms.copyAsNew\" ps=\" »\"></button>\r\n          </div>\r\n          <div sxy-if-role=\"worker\" class=\"row hidden-xxs\">\r\n            <div ng-if=\"$ctrl.showAction('save')\" class=\"col-12\">\r\n              <button type=\"button\" ng-click=\"$ctrl.save()\" class=\"btn btn-success btn-block\" ng-disabled=\"$ctrl.isActionDisabled('save')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n            </div>\r\n            <div ng-if=\"$ctrl.currentCalc.workflow.status == 'draft' || $ctrl.currentCalc.workflow.status == 'workerRequested' || $ctrl.currentCalc.workflow.status == 'workerRequestAccepted' || $ctrl.currentCalc.workflow.status == 'workerRequestDeclined' || $ctrl.currentCalc.workflow.status == 'paymentWorkerCopy'\" class=\"col-12\">\r\n              <salaxy-calc-sharing-info model=\"$ctrl\"></salaxy-calc-sharing-info>\r\n            </div>\r\n            <div ng-if=\"$ctrl.showAction('delete')\" class=\"col-12\">\r\n              <button ng-if=\"$ctrl.showAction('delete')\" type=\"button\" ng-click=\"$ctrl.deleteCalc()\" ng-disabled=\"$ctrl.isActionDisabled('delete')\" class=\"btn btn-danger btn-block\" sxy-text=\"SALAXY.UI_Terms.delete\"></button>\r\n            </div>\r\n          </div>\r\n         \r\n          <div class=\"text-center btn-group-chart\">\r\n            <a ng-click=\"$ctrl.chartType = 'bar'\" class=\"btn-chart me-2\" ng-class=\"{'active' : $ctrl.chartType == 'bar'}\"><i class=\"bi bi-bar-chart-line-fill\"></i></a>\r\n            <a ng-click=\"$ctrl.chartType = 'pie'\" class=\"btn-chart\" ng-class=\"{'active' : $ctrl.chartType == 'pie'}\"><i class=\"bi bi-pie-chart-fill\"></i></a>\r\n          </div>\r\n        </div>\r\n\r\n        <div class=\"col-12 col-sm-6 col-md-4 order-2 order-md-1\">\r\n          <h3 class=\"text-center fw-normal\" sxy-text=\"SALAXY.NG1_Other.Roles.employer\"></h3>\r\n          <salaxy-calc-chart role=\"employer\" scale-y-axis=\"true\" chart-type=\"$ctrl.chartType\" calc=\"$ctrl.currentCalc\"></salaxy-calc-chart>\r\n          <p class=\"text-center\" ng-if=\"$ctrl.isHouseholdDeductible\">\r\n            <span sxy-text=\"SALAXY.NG1.CalcResultsComponent.nowPaying\" ps=\":\"></span> {{ $ctrl.currentCalc.result.employerCalc.totalPayment | currency: \"\":2 }} €\r\n            <br />\r\n            <span sxy-text=\"SALAXY.NG1.CalcResultsComponent.finalCost\" ps=\":\"></span> {{ $ctrl.currentCalc.result.employerCalc.finalCost | currency: \"\":2 }} €\r\n          </p>\r\n          <p class=\"text-center\" ng-if=\"!$ctrl.isHouseholdDeductible\">\r\n            <span sxy-text=\"SALAXY.NG1.CalcDetailsSalaryComponent.paymentTotal.title\" ps=\":\"></span> {{ $ctrl.currentCalc.result.employerCalc.finalCost | currency: \"\":2 }} €\r\n          </p>\r\n        </div>\r\n        <div class=\"col-12 col-sm-6 col-md-4 order-3\">\r\n          <h3 class=\"text-center fw-normal\" sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></h3>\r\n          <salaxy-calc-chart role=\"worker\" scale-y-axis=\"true\" chart-type=\"$ctrl.chartType\" calc=\"$ctrl.currentCalc\"></salaxy-calc-chart>\r\n          <p class=\"text-center\">\r\n            <span sxy-text=\"SALAXY.NG1.CalcResultsComponent.workerGetsPaid\" ps=\":\"></span> {{ $ctrl.currentCalc.result.workerCalc.totalWorkerPayment | currency: \"\":2 }} €\r\n          </p>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"row\">\r\n      <div class=\"col-12 col-sm-4 d-flex justify-content-center\">\r\n        <a class=\"action-link\" ng-click=\"$ctrl.showReportDialog('employerReport')\" sxy-text=\"SALAXY.NG1.CalcResultsComponent.employerReport\"></a>\r\n      </div>\r\n      <div class=\"col-12 col-sm-4 d-flex justify-content-center\">\r\n        <a class=\"action-link\" ng-click=\"$ctrl.showReportDialog('paymentReport')\" sxy-text=\"SALAXY.NG1.CalcResultsComponent.societyReport\"></a>\r\n      </div>\r\n      <div class=\"col-12 col-sm-4 d-flex justify-content-center\">\r\n        <a class=\"action-link\" ng-click=\"$ctrl.showReportDialog('salarySlip')\" sxy-text=\"SALAXY.NG1.CalcResultsComponent.workerReport\"></a>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/CalcRowType.html\",`<div class=\"salaxy-component salaxy-calc-row-type\">\r\n  <div ng-if=\"$ctrl.type == 'read-only'\" class=\"salaxy-calc-row-type-read-only\">\r\n    {{ $ctrl.getRowLabel() | sxyTranslate }}\r\n  </div>\r\n  <div ng-if=\"$ctrl.type == 'typehead'\" class=\"salaxy-calc-row-type-typehead\" style=\"position: relative\">\r\n    <salaxy-input-typeahead\r\n      label-type=\"no-label\"\r\n      ng-model=\"$ctrl.internalValue\"\r\n      name=\"{{ $ctrl.name }}\"\r\n      disable-cache=\"true\"\r\n      clear-on-select=\"$ctrl.clearOnSelect\"\r\n      value-as-object=\"true\"\r\n      placeholder=\"{{ $ctrl.placeholder || 'SALAXY.UI_Terms.select' | sxyTranslate }}\"\r\n      get-options=\"$ctrl.search\">\r\n    </salaxy-input-typeahead>\r\n  </div>\r\n  <div ng-if=\"$ctrl.type == 'list'\" class=\"salaxy-calc-row-type-list\">\r\n    <div class=\"list-group\">\r\n      <div ng-repeat=\"item in $ctrl.getCachedSearch($ctrl.searchText, true)\">\r\n        <a ng-if=\"item.ui.iconText\" class=\"list-group-item clickable d-flex\" ng-click=\"$ctrl.internalValue = item\" ng-class=\"{ 'active': $ctrl.internalValue == item }\">\r\n          <salaxy-avatar class=\"salaxy-calc-row-type-avatar\" avatar=\"{ color: item.ui.color, initials: item.ui.iconText, entityType: 'company' }\"></salaxy-avatar>\r\n          <div>\r\n            <b class=\"salaxy-highlight\" ng-bind-html=\"item.text | uibTypeaheadHighlight:$ctrl.searchText\"></b><br />\r\n            <small class=\"salaxy-highlight\">\r\n              <div ng-bind-html=\"item.title | uibTypeaheadHighlight:$ctrl.searchText\"></div>\r\n            </small>\r\n          </div>\r\n        </a>\r\n        <a ng-if=\"!item.ui.iconText\" class=\"list-group-item clickable salaxy-highlight\" ng-click=\"$ctrl.internalValue = item\" ng-class=\"{ 'active': $ctrl.internalValue == item }\" title=\"{{ enum.title }}\" style=\"display: list-item; list-style-type: disc; list-style-position: inside; padding: 2px 2px 2px 60px\">\r\n          <span ng-bind-html=\"item.text | uibTypeaheadHighlight:query\"></span>\r\n        </a>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div ng-if=\"$ctrl.type == 'table'\" class=\"salaxy-calc-row-type-table\">\r\n    <table class=\"table table-sm\">\r\n      <thead>\r\n        <tr class=\"active\">\r\n          <td>\r\n            <salaxy-avatar class=\"salaxy-calc-row-type-avatar\" avatar=\"{ color: 'rgb(79, 205, 196)', initials: 'type', entityType: 'company' }\"></salaxy-avatar>\r\n          </td>\r\n          <td>\r\n            <div><b sxy-text=\"SALAXY.NG1.CalcRowTypeComponent.rowType\" ps=\" (type)\"></b></div>\r\n            <div sxy-text=\"SALAXY.NG1.CalcRowTypeComponent.rowDescription\"></div>\r\n          </td>\r\n          <td><b sxy-text=\"SALAXY.NG1.CalcRowTypeComponent.rowTypeEn\"></b></td>\r\n        </tr>\r\n        <tr class=\"active\">\r\n          <td></td>\r\n          <td sxy-text=\"SALAXY.NG1.CalcRowTypeComponent.rowKind\" ps=\" (kind)\"></td>\r\n          <td sxy-text=\"SALAXY.NG1.CalcRowTypeComponent.rowKindEn\"></td>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat-start=\"item in $ctrl.getCachedSearch($ctrl.searchText, true)\" ng-if=\"item.ui.iconText\">\r\n          <th rowspan=\"2\">\r\n            <salaxy-avatar class=\"salaxy-calc-row-type-avatar\" avatar=\"{ color: item.ui.color, initials: item.ui.iconText, entityType: 'company' }\"></salaxy-avatar>\r\n          </th>\r\n          <th>\r\n            <div>\r\n              <b class=\"salaxy-highlight\" ng-bind-html=\"item.text | uibTypeaheadHighlight:$ctrl.searchText\"></b>\r\n              <button type=\"button\" class=\"btn btn-xs btn-default\" ng-click=\"$ctrl.showInfoScreen(item)\" style=\"margin-left: 5px\">edit</button>\r\n            </div>\r\n          </th>\r\n          <th>\r\n            <div class=\"salaxy-highlight\" ng-bind-html=\"item.value | uibTypeaheadHighlight:$ctrl.searchText\"></div>\r\n          </th>\r\n        </tr>\r\n        <tr ng-if=\"item.ui.iconText\" class=\"no-border\">\r\n          <td colspan=\"2\" style=\"padding-top: 0;\">\r\n            <div style=\"padding-top: 0;\" class=\"salaxy-highlight\" ng-bind-html=\"item.title | uibTypeaheadHighlight:$ctrl.searchText\"></div>\r\n          </td>\r\n        </tr>\r\n        <tr ng-if=\"!item.ui.iconText\">\r\n          <td></td>\r\n          <td>\r\n            <div class=\"salaxy-highlight\" ng-bind-html=\"item.text | uibTypeaheadHighlight:$ctrl.searchText\"></div>\r\n          </td>\r\n          <td>\r\n            <div class=\"salaxy-highlight\" ng-bind-html=\"item.value.split('.')[1] | uibTypeaheadHighlight:$ctrl.searchText\"></div>\r\n          </td>\r\n        </tr>\r\n        <tr ng-repeat-end=\"item in $ctrl.getList()\" ng-if=\"!item.ui.iconText\" class=\"no-border\">\r\n          <td></td>\r\n          <td colspan=\"2\" style=\"padding-top: 0;\">\r\n            <div class=\"salaxy-highlight\" ng-bind-html=\"item.title | uibTypeaheadHighlight:$ctrl.searchText\"></div>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/CalcRowTypeItem.html\",`<a class=\"clickable d-flex\" ng-if=\"match.model.ui.iconText\">\r\n  <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" \r\n    avatar=\"{ color: match.model.ui.color, initials: match.model.ui.iconText, entityType: 'company' }\"></salaxy-avatar>\r\n  <div>\r\n    <b class=\"salaxy-highlight\" ng-bind-html=\"match.model.text | uibTypeaheadHighlight:query\"></b><br />\r\n    <small class=\"salaxy-highlight\"><div ng-bind-html=\"match.model.title | uibTypeaheadHighlight:query\"></div></small>\r\n  </div>\r\n</a>\r\n<a class=\"clickable\" ng-if=\"!match.model.ui.iconText\"\r\nstyle=\"display: list-item; list-style-type: disc; list-style-position: inside; padding: 2px 2px 2px 60px\">\r\n  <b class=\"salaxy-highlight\" ng-bind-html=\"match.model.text | uibTypeaheadHighlight:query\"></b> \r\n  <small class=\"salaxy-highlight\"><span ng-bind-html=\"match.model.title || '' | uibTypeaheadHighlight:query\"></span></small>\r\n</a>`);\n\n $templateCache.put(\"salaxy-components/calc/CalcSharingReceiptAction.html\",`<span ng-switch=\"$ctrl.type\">\r\n  <button ng-switch-when=\"approve\" class=\"btn {{$ctrl.buttonClass || 'btn-success btn-block btn-sm' }}\" type=\"button\" id=\"approve\" ng-disabled=\"$ctrl.disabled\"\r\n    ng-click=\"$ctrl.approve()\" title=\"{{'SALAXY.NG1.CalcSharingReceiptActionComponent.approveBtnTitle' | sxyTranslate}}\">\r\n    <span ng-if=\"!$ctrl.iconOnly\">{{'SALAXY.NG1.CalcSharingReceiptActionComponent.approveBtn' | sxyTranslate}}&nbsp;</span>\r\n<span ng-show=\"!$ctrl.isLoading\"><i class=\"bi bi-hand-thumbs-up\"></i></span>\r\n<span ng-show=\"$ctrl.isLoading\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span>\r\n</button>\r\n<button ng-switch-when=\"reject\" class=\"btn {{$ctrl.buttonClass || 'btn-danger btn-block btn-sm' }}\" type=\"button\" id=\"reject\" ng-disabled=\"$ctrl.disabled\" ng-click=\"$ctrl.reject()\" title=\"{{'SALAXY.NG1.CalcSharingReceiptActionComponent.rejectBtnTitle' | sxyTranslate}}\">\r\n    <span ng-if=\"!$ctrl.iconOnly\"> {{'SALAXY.NG1.CalcSharingReceiptActionComponent.rejectBtn' | sxyTranslate}}&nbsp;</span>\r\n    <span ng-show=\"!$ctrl.isLoading\"><i class=\"bi bi-hand-thumbs-down\"></i></span>\r\n    <span ng-show=\"$ctrl.isLoading\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span>\r\n  </button>\r\n<span ng-switch-default class=\"alert alert-danger\" sxy-text=\"SALAXY.NG1.CalcSharingReceiptActionComponent.alertUnknown\"></span>\r\n</span>`);\n\n $templateCache.put(\"salaxy-components/calc/CalcWorkerInfo.html\",`<div class=\"salaxy-component salaxy-calc-worker-info\">\r\n  <div class=\"row\">\r\n    <div class=\"col-2 col-md-2 worker-info-avatar-container d-flex align-items-center justify-content-center\">\r\n      <salaxy-avatar avatar=\"$ctrl.current.worker.avatar\"></salaxy-avatar>\r\n    </div>\r\n    <div class=\"col-10 col-md-10 worker-info-col\">\r\n      <h2>{{ $ctrl.current.worker.avatar.displayName || (\"SALAXY.NG1.WorkerInfo.noSelection\" | sxyTranslate) }}</h2>\r\n      <div class=\"row\">\r\n        <div class=\"col-12 col-md-6\">\r\n          <div ng-class=\"{'text-danger': $ctrl.taxUi.status != 'ok'}\">{{ $ctrl.taxUi.text || \"&nbsp;\" }}</div>\r\n          <div ng-if=\"!$ctrl.current.worker.paymentData.ibanNumber\" class=\"text-danger\" sxy-text=\"SALAXY.NG1.WorkerInfo.noIbanNumber\"></div>\r\n          <div ng-if=\"$ctrl.current.worker.paymentData.ibanNumber\">{{ $ctrl.current.worker.paymentData.ibanNumber | sxyIban }}</div>\r\n          <div>{{ $ctrl.getPensionText() || \"&nbsp;\" }}</div>\r\n        </div>\r\n        <div class=\"col-12 col-md-6 \">\r\n          <div ng-if=\"!$ctrl.current.worker.paymentData.socialSecurityNumberValid\" class=\"text-danger\">\r\n            <span sxy-text=\"SALAXY.NG1.PaymentDialogComponent.noSSNumber\"></span>\r\n            <br />\r\n          </div>\r\n          <div ng-if=\"$ctrl.current.worker.paymentData.socialSecurityNumberValid\">{{ $ctrl.current.worker.paymentData.socialSecurityNumberValid }}<br /></div>\r\n          <span ng-if=\"$ctrl.current.worker.paymentData.telephone\">\r\n            {{ $ctrl.current.worker.paymentData.telephone ||  ('SALAXY.NG1.PaymentDialogComponent.noTel' | sxyTranslate) }}\r\n          </span>\r\n          <br />\r\n          <a href=\"{{ 'mailto:' + $ctrl.current.worker.paymentData.email }}\" ng-if=\"$ctrl.current.worker.paymentData.email\">{{ $ctrl.current.worker.paymentData.email }}</a>\r\n          <div ng-if=\"$ctrl.current && !$ctrl.current.worker.paymentData.email\">\r\n            <span sxy-text=\"SALAXY.NG1.PaymentDialogComponent.noEmail\"></span> &nbsp;\r\n            <span class=\"text-warning\" sxy-text=\"SALAXY.NG1.PaymentDialogComponent.noEmailInfo\"></span>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/CalcWorktime.html\",`<style type=\"text/css\">\r\n  .form-condensed .form-group {\r\n    margin-bottom: 1px\r\n  }\r\n\r\n  .form-condensed .form-horizontal .control-label {\r\n    padding-top: 0px;\r\n  }\r\n</style>\r\n<div class=\"salaxy-component salaxy-calc-worktime\" ng-if=\"$ctrl.currentCalc\">\r\n  <form ng-submit=\"$ctrl.submitWorktime()\" name=\"detailsWork2\" class=\"form-horizontal\">\r\n    <div class=\"salaxy-calc-dialog-body\">\r\n      <div class=\"salaxy-calc-dialog-container\">\r\n        <div class=\"row\">\r\n          <div class=\"col-md-6\" >\r\n            <h1 sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.salaryDateTitle\"></h1>\r\n            <p sxy-html=\"SALAXY.NG1.CalcWorktimeComponent.salaryDateDescription.html\"></p>\r\n            <div class=\"form-horizontal\">\r\n              <salaxy-form-group ng-if=\"$ctrl.currentCalc.workflow.salaryDateKind == 'inPast'\" name=\"salaryDateKind\" class=\"salaxy-component salaxy-read-only\" label-cols=\"col-sm-6\" label=\"SALAXY.MODEL.CalcWorkflow.salaryDateKind.title\">\r\n                <div class=\"form-control-plaintext\">{{\"SALAXY.ENUM.SalaryDateKind.\" + ($ctrl.currentCalc.workflow.salaryDateKind) + \".label\" | sxyTranslate  }}</div>\r\n              </salaxy-form-group>\r\n              <salaxy-datepicker-popup name=\"requestedSalaryDate\" ng-model=\"$ctrl.requestedSalaryDate\" label=\"SALAXY.NG1.CalcWorktimeComponent.salaryDateLabel\" label-cols=\"col-sm-6\" date-disabled=\"disable-function\" disable-function=\"$ctrl.isDisabledSalaryDate\" update-disabled-dates=\"($ctrl.currentCalc.workflow.salaryDateKind || '-') + '|' + ($ctrl.currentCalc.info.paymentChannel || '-')\" placeholder=\"SALAXY.NG1.CalcWorktimeComponent.salaryDatePlaceholder\"></salaxy-datepicker-popup>\r\n            </div>\r\n            <h1 sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.worktime.title\"></h1>\r\n            <p ng-if=\"!$ctrl.dateRange.start || !$ctrl.dateRange.start\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.worktime.description\"></p>\r\n            <div class=\"form-horizontal\">\r\n              <salaxy-input-enum ng-model=\"$ctrl.periodShortcut\" require=\"!!$ctrl.isWorkerHolidaysActive\" name=\"periodShortcut\" ng-if=\"!$ctrl.periodShortcut\" label=\"SALAXY.CORE.CalcWorktime.salaryPeriod\" label-cols=\"col-sm-6\" type=\"radio\" options=\"$ctrl.periodShortcuts\"></salaxy-input-enum>\r\n              <salaxy-input-enum ng-model=\"$ctrl.periodShortcut\" require=\"!!$ctrl.isWorkerHolidaysActive\" name=\"periodShortcut\" ng-if=\"$ctrl.periodShortcut\" label=\"SALAXY.CORE.CalcWorktime.salaryPeriod\" label-cols=\"col-sm-6\" type=\"select\" options=\"$ctrl.periodShortcuts\"></salaxy-input-enum>\r\n              <salaxy-date-range ng-model=\"$ctrl.dateRange\" require=\"!!$ctrl.isWorkerHolidaysActive\" class=\"condensed\" name=\"dateRange\" ng-if=\"$ctrl.periodShortcut == 'other'\" on-change=\"$ctrl.dateRangeChange()\" label=\"SALAXY.CORE.CalcWorktime.salaryPeriod\" label-days-count=\"SALAXY.MODEL.CalcWorktime.workDays.title\"\r\n                label-cols=\"col-sm-6\" read-only=\"$ctrl.isReadOnly\"></salaxy-date-range>\r\n              <div ng-if=\"$ctrl.periodShortcut && $ctrl.periodShortcut != 'other'\">\r\n                <salaxy-form-group name=\"periodStartDate\" label=\"SALAXY.MODEL.DateRange.start.title\" label-cols=\"col-sm-6\">\r\n                  <input type=\"text\" class=\"form-control\" autocomplete=\"off\" id=\"periodStartDate\" name=\"periodStartDate\" placeholder=\"{{'SALAXY.UI_Terms.dateFormats.dm' | sxyTranslate}}\" ng-model=\"$ctrl.periodStartDate\" ng-model-options=\"{allowInvalid: true, debounce: 250, updateOn: 'default' }\"\r\n                  />\r\n                  <div ng-if=\"$ctrl.periodStartDateError\" class=\"form-control-plaintext text-danger\">{{ $ctrl.periodStartDateError |sxyTranslate}}</div>\r\n                </salaxy-form-group>\r\n                <salaxy-form-group name=\"formattedRange\" label=\"SALAXY.CORE.CalcWorktime.startAndEndDates\" label-cols=\"col-sm-6\" class=\"salaxy-read-only\">\r\n                  <div class=\"form-control-plaintext\">{{ $ctrl.dateRange | sxyDateRange }}</div>\r\n                </salaxy-form-group>\r\n                <salaxy-input-number name=\"labelDaysCount\" ng-model=\"$ctrl.dateRange.daysCount\" ng-change=\"$ctrl.dateRangeChange()\" require=\"!!$ctrl.isWorkerHolidaysActive\" label=\"SALAXY.MODEL.DateRange.daysCount.title\" label-cols=\"col-sm-6\">\r\n                </salaxy-input-number>\r\n              </div>\r\n            </div>\r\n          </div>\r\n          <div class=\"col-md-6\" ng-if=\"!(('worker' | sxyIsInRole) || ('disableHolidays' | sxyIsInRole))\">\r\n            <h1 sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.absences.title\"></h1>\r\n            <div ng-switch=\"$ctrl.getHolidaysStatus()\">\r\n              <div ng-switch-when=\"noWorker\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.absences.descriptionNoWorker\"></div>\r\n              <div ng-switch-when=\"noPeriod\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.absences.descriptionNoPeriod\"></div>\r\n              <div ng-switch-when=\"loading\">\r\n                <salaxy-spinner full-screen=\"false\" heading=\"SALAXY.UI_Terms.loading\" text=\"SALAXY.NG1.CalcWorktimeComponent.absences.loadingText\"></salaxy-spinner>\r\n              </div>\r\n              <div ng-switch-when=\"ok\">\r\n                <button class=\"btn btn-default float-end salaxy-button-pro\" ng-click=\"$ctrl.showPeriodDetails()\" type=\"button\" title=\"{{'SALAXY.NG1.CalcWorktimeComponent.absences.proTabTitle' | sxyTranslate}}\">Pro</button>\r\n                <salaxy-tab-buttons\r\n                  current-tab=\"$ctrl.currentTab\"\r\n                  options=\"[\r\n                    { value: 'default', text: 'SALAXY.NG1.CalcWorktimeComponent.absences.calculationTabHeading', isDefault: true },\r\n                    { value: 'absences', text: 'SALAXY.NG1.AbsencePeriodsComponent.headerAbsence' },\r\n                    { value: 'leaves', text: 'SALAXY.NG1.CalcWorktimeComponent.absences.leavesTabHeading', hidden: !$ctrl.isHolidayAccrual }  \r\n                  ]\"\r\n                  tabs-id=\"calcWorktime\">\r\n                </salaxy-tab-buttons>\r\n                <div class=\"tab-content\" id=\"tab-content-calcWorktime\">\r\n                  <div class=\"tab-pane\" id=\"default-tab\">\r\n                    <fieldset ng-if=\"$ctrl.accruesHolidays\">\r\n                      <table class=\"table table-striped table-sm\">\r\n                        <thead>\r\n                          <tr>\r\n                            <th sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.holidays.headerHolidays\"></th>\r\n                            <th class=\"right\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.holidays.headerDays\"></th>\r\n                          </tr>\r\n                        </thead>\r\n                        <tbody>\r\n                          <tr ng-repeat=\"month in $ctrl.worktime.accruals\">\r\n                            <td>\r\n                              <strong>{{ $ctrl.getAccrualMonthText('header', month) | sxyTranslate}}</strong><br>\r\n                              <small>\r\n                                <div>\r\n                                  <a href=\"\" ng-click=\"$ctrl.changeTab('absences')\">\r\n                                    <span sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.absences.link\"></span> {{ month.absencesDays | sxyCount : 'day' }}\r\n                                  </a>\r\n                                </div>\r\n                              </small>\r\n                            </td>\r\n                            <td class=\"right\">\r\n                              <strong>{{ month.daysAccrued | sxyCount : 'day' }}</strong><br>\r\n                            </td>\r\n                          </tr>\r\n                        </tbody>\r\n                      </table>\r\n                      <small>\r\n                        <p>{{ $ctrl.getAccrualMonthText(\"description\") | sxyTranslate }}</p>\r\n                      </small>\r\n                    </fieldset>\r\n                    <legend sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.absences.calculationLegend\"></legend>\r\n                      <div>\r\n                        <fieldset>\r\n                          <table class=\"table table-striped table-sm\" ng-if=\"$ctrl.getLogicForLists().getAbcencesForPeriod().length\">\r\n                            <thead>\r\n                              <tr>\r\n                                <th sxy-text=\"SALAXY.NG1.AbsencePeriodsComponent.headerAbsence\"></th>\r\n                                <th class=\"right\" sxy-text=\"SALAXY.NG1.AbsencePeriodsComponent.headerDays\"></th>\r\n                              </tr>\r\n                            </thead>\r\n                            <tbody>\r\n                              <tr ng-repeat=\"row in $ctrl.getLogicForLists().getAbcencesForPeriod()\">\r\n                                <td>\r\n                                  <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" avatar=\"{ color: '#2b507c', initials: (row.period.daysCount + 'pv'), entityType: 'company' }\"></salaxy-avatar>\r\n                                  <strong>{{ \"AbsenceCauseCode.\" + row.causeCode | sxyEnum }}</strong><br />\r\n                                  <div class=\"float-start\" style=\"padding: 0px;\">\r\n                                    {{ row.isPaid ? ('SALAXY.NG1.AbsencePeriodsComponent.isPaid' | sxyTranslate) : ('SALAXY.NG1.AbsencePeriodsComponent.notPaid' |sxyTranslate) }}\r\n                                    <span ng-if=\"row.isPaid != row.isHolidayAccrual\"> {{ row.isHolidayAccrual ? ('SALAXY.NG1.AbsencePeriodsComponent.isAccrual' | sxyTranslate) : ('SALAXY.NG1.AbsencePeriodsComponent.notAccrual' | sxyTranslate) }}</span>\r\n                                  </div>\r\n                                  <div class=\"truncate\" style=\"max-width: 250px; padding: 0px;\">\r\n                                    &nbsp;{{ row.notes }}\r\n                                  </div>\r\n                                </td>\r\n                                <td class=\"right\">\r\n                                  <strong>{{ row.period.daysCount | sxyCount : \"day\" }}</strong><br /> {{ row.period | sxyDateRange }}\r\n                                </td>\r\n                              </tr>\r\n                              <tr class=\"total\">\r\n                                <td>\r\n                                  <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" style=\"margin-bottom: 20px\" avatar=\"{ color: '#2b507c', initials: 'sum', entityType: 'company' }\"></salaxy-avatar>\r\n                                  <strong>\r\n                                    <span sxy-text=\"SALAXY.NG1.AbsencePeriodsComponent.totalUnpaid\"></span><br />\r\n                                    <span sxy-text=\"SALAXY.NG1.AbsencePeriodsComponent.totalPaid\"></span><br />\r\n                                    <span sxy-text=\"SALAXY.NG1.AbsencePeriodsComponent.totalNoHolidayAccrual\"></span><br />\r\n                                  <span sxy-text=\"SALAXY.NG1.AbsencePeriodsComponent.totalAll\"></span><br />\r\n                                  </strong>\r\n                                </td>\r\n                                <td class=\"right\">\r\n                                  <strong>\r\n                                    {{ $ctrl.getLogicForLists().getAbcensePeriodsTotalDays(\"absencesUnpaid\") | sxyCount : \"day\" }}<br />\r\n                                    {{ $ctrl.getLogicForLists().getAbcensePeriodsTotalDays(\"absencesPaid\") | sxyCount : \"day\" }}<br />\r\n                                    {{ $ctrl.getLogicForLists().getAbcensePeriodsTotalDays(\"absencesNoHolidayAccrual\") | sxyCount : \"day\" }}<br />\r\n                                    {{ $ctrl.getLogicForLists().getAbcensePeriodsTotalDays(\"all\") | sxyCount : \"day\" }}<br />\r\n                                  </strong>\r\n                                </td>\r\n                              </tr>\r\n                            </tbody>\r\n                          </table>\r\n                          <p ng-if=\"!$ctrl.getLogicForLists().getAbcencesForPeriod().length\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.absencePeriods.noAbsences\"></p>\r\n                        </fieldset>\r\n                      </div>\r\n                      <div ng-if=\"$ctrl.worktime.holidaySpec.code == 'noHolidays'\">\r\n                        <strong sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.absences.calculationDescriptionNoHolidays\"></strong>\r\n                      </div>\r\n                      <div ng-if=\"$ctrl.worktime.holidaySpec.code == 'holidayCompensation'\">\r\n  \r\n                        <div style=\"margin-bottom: 8px; margin-right: 10px;\">\r\n                          <div class=\"float-end\">{{ $ctrl.worktime.holidaySpec.compensation | sxyCount : 'percent' }}</div>\r\n                          <strong sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.absences.calculationDescriptionHolidayCompensation\"></strong>\r\n                        </div>\r\n                        <div style=\"margin-bottom: 8px; margin-right: 10px;\" ng-if=\"$ctrl.worktime.holidaySpec.bonus > 0\">\r\n  \r\n                          <div class=\"float-end\">{{ $ctrl.worktime.holidaySpec.bonus | sxyCount : 'percent' }}</div>\r\n                          <strong sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.absences.calculationDescriptionHolidayBonus\" pre=\"+ \"></strong>\r\n                        </div>\r\n                        <div ng-if=\"!$ctrl.worktime.holidaySpec.bonus\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.absences.calculationDescriptionNoHolidayBonus\"></div>\r\n                      </div>\r\n                      <div ng-if=\"$ctrl.isHolidayAccrual\">\r\n                      <button ng-if=\"!$ctrl.currentCalc.isReadOnly\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.openCalcLeavesDialog()\">{{\"SALAXY.UI_Terms.edit\" | sxyTranslate}}...</button> \r\n                      <fieldset >\r\n                        <table class=\"table table-striped table-sm\" ng-if=\"$ctrl.getLogicForLists().getAnnualLeavesForPeriod().length\">\r\n                          <thead>\r\n                            <tr>\r\n                              <th sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidays.tableHead.period\"></th>\r\n                              <th class=\"right\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidays.tableHead.daysCount\"></th>\r\n                            </tr>\r\n                          </thead>\r\n                          <tr ng-repeat=\"row in $ctrl.getLogicForLists().getAnnualLeavesForPeriod()\">\r\n                            <td>\r\n                              <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" avatar=\"{ color: '#2b507c', initials: (row.period.daysCount + 'pv'), entityType: 'company' }\"></salaxy-avatar>\r\n                              <strong>{{ row.period | sxyDateRange }}</strong>\r\n                              <br />\r\n                              <small>\r\n                                <div class=\"truncate\" style=\"max-width: 250px;\">{{ $ctrl.getLogicForLists().getAnnualLeaveDescription(row) }}</div>\r\n                              </small>\r\n                            </td>\r\n                            <td class=\"right\">\r\n                              <strong>{{ row.period.daysCount | sxyCount : \"day\"  }}</strong>\r\n                            </td>\r\n                          </tr>\r\n                          <tr class=\"total\">\r\n                            <td>\r\n                              <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" avatar=\"{ color: '#2b507c', initials: 'sum', entityType: 'company' }\"></salaxy-avatar>\r\n                              <strong sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidays.tableBody.total\"></strong>\r\n                              <br />\r\n                              <small>\r\n                                <div class=\"truncate\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidays.tableBody.totalMore\"></div>\r\n                              </small>\r\n                            </td>\r\n                            <td class=\"right\">\r\n                              <strong>{{ $ctrl.getLogicForLists().getAnnualLeavesTotalDays() | sxyCount : \"day\" }}</strong>\r\n                            </td>\r\n                          </tr>\r\n                        </table>\r\n                        <p ng-if=\"!$ctrl.getLogicForLists().getAnnualLeavesForPeriod().length\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.annualLeaves.noAnnualLeaves\"></p>\r\n                      </fieldset>  \r\n                    </div>\r\n                  </div>\r\n                  <div class=\"tab-pane\" id=\"absences-tab\">\r\n                    <div sxy-if-role=\"auth\" ng-controller=\"WorkerAbsencesCrudController as $absencesCtrl\" ng-init=\"$absencesCtrl.employmentId=$ctrl.currentCalc.worker.employmentId\">\r\n                      <salaxy-absence-periods parent=\"$absencesCtrl.current\" condensed=\"true\" on-commit=\"$ctrl.absencesChanged($absencesCtrl)\" ng-if=\"$absencesCtrl.current\" ></salaxy-absence-periods>\r\n                    </div>\r\n                    <div sxy-if-role=\"!auth\">\r\n                      <p sxy-html=\"SALAXY.NG1.CalcWorktimeComponent.anonDemoText.html\"></p>\r\n                      <salaxy-absence-periods parent=\"$ctrl.demoData.absences\" condensed=\"true\" on-commit=\"$ctrl.reloadHolidays()\"></salaxy-absence-periods>\r\n                    </div>\r\n                    <p>&nbsp;</p>\r\n                    <small>\r\n                      <p sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.absences.absencesAttention\"></p>\r\n                    </small>\r\n                  </div>\r\n                  <div class=\"tab-pane\" id=\"leaves-tab\">\r\n                    <div ng-if=\"$ctrl.isHolidayAccrual\">\r\n                      <div ng-controller=\"HolidayYearCrudController as $holidaysCtrl\" ng-init=\"$holidaysCtrl.employmentId=$ctrl.currentCalc.worker.employmentId;$holidaysCtrl.forDate=$ctrl.currentCalc.info.workStartDate\">\r\n                        <salaxy-holiday-year-holidays parent=\"$holidaysCtrl.current\" condensed=\"true\" on-commit=\"$ctrl.holidaysChanged($holidaysCtrl)\" ng-if=\"$holidaysCtrl.current\" ></salaxy-holiday-year-holidays>\r\n                      </div>\r\n                      <p>&nbsp;</p>\r\n                      <small>\r\n                        <p sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.absences.absencesAttention\"></p>\r\n                      </small>\r\n                    </div>\r\n                  </div>\r\n                </div>\r\n              </div>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n\r\n    <button ng-show=\"!$ctrl.currentCalc.isReadOnly\" class=\"btn btn-warning btn-lg salaxy-calc-btn-recalculate\" type=\"submit\">{{ $ctrl.hasHolidaysOrAbsences() ?\r\n      ('SALAXY.NG1.CalcWorktimeComponent.absences.calculateButtonText' | sxyTranslate) : ('SALAXY.UI_Terms.updateCalculation' |sxyTranslate) }}</button>\r\n  </form>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/CostAccounting.html\",`<div class=\"salaxy-component salaxy-cost-accounting\">\r\n  <div ng-if=\"$ctrl.current.length > 0 || $ctrl.definitions.length > 0\">\r\n    <fieldset>\r\n      <legend sxy-text=\"SALAXY.NG1.CalcCostAccountingComponent.title\"></legend>\r\n      <div ng-repeat=\"dimension in $ctrl.definitions\">\r\n        <div ng-if=\"!dimension.allowCostSharing\">\r\n          <div class=\"form-horizontal\">\r\n            <div class=\"row\">\r\n              <div class=\"col-md-11\">\r\n                <salaxy-input-typeahead class=\"text-muted\" ng-if=\"$ctrl.isInherited(dimension.id) && $ctrl.hasOptions(dimension.id, $ctrl.getInheritedSingleValue(dimension.id).value)\" label=\"{{(dimension.label || 'SALAXY.NG1.CalcCostAccountingComponent.defaultLabel') | sxyTranslate}}\" ng-model=\"$ctrl.getInheritedSingleValue(dimension.id).value\"\r\n                  label-format=\"text-value\" get-options=\"$ctrl.getOptions(dimension.id)\" name=\"single\" read-only=\"true\" placeholder=\"{{ 'SALAXY.UI_Terms.notChosen' | sxyTranslate }}\">\r\n                </salaxy-input-typeahead>\r\n                <salaxy-input class=\"text-muted\" ng-if=\"$ctrl.isInherited(dimension.id) && !$ctrl.hasOptions(dimension.id, $ctrl.getInheritedSingleValue(dimension.id).value)\" label=\"{{(dimension.label || 'SALAXY.NG1.CalcCostAccountingComponent.defaultLabel') | sxyTranslate}}\" ng-model=\"$ctrl.getInheritedSingleValue(dimension.id).value\" name=\"single\"\r\n                  read-only=\"true\">\r\n                </salaxy-input>\r\n\r\n                <salaxy-input-typeahead ng-if=\"!$ctrl.isInherited(dimension.id) && $ctrl.hasOptions(dimension.id, $ctrl.getSingleValue(dimension.id).value)\" label=\"{{(dimension.label || 'SALAXY.NG1.CalcCostAccountingComponent.defaultLabel') | sxyTranslate}}\" ng-model=\"$ctrl.getSingleValue(dimension.id).value\"\r\n                  label-format=\"text-value\" options=\"$ctrl.getOptions(dimension.id)\" name=\"single\" read-only=\"$ctrl.readOnly\" input-mode=\"{{$ctrl.inputMode}}\" ng-change=\"$ctrl.setSingleValue(dimension.id, $ctrl.getSingleValue(dimension.id).value)\" placeholder=\"{{ 'SALAXY.UI_Terms.notChosen' | sxyTranslate }}\"></salaxy-input-typeahead>\r\n\r\n                <salaxy-input ng-if=\"!$ctrl.isInherited(dimension.id) && !$ctrl.hasOptions(dimension.id, $ctrl.getSingleValue(dimension.id).value)\" label=\"{{(dimension.label || 'SALAXY.NG1.CalcCostAccountingComponent.defaultLabel') | sxyTranslate}}\" ng-model=\"$ctrl.getSingleValue(dimension.id).value\" name=\"single\"\r\n                read-only=\"$ctrl.readOnly\" input-mode=\"{{$ctrl.inputMode}}\" ng-change=\"$ctrl.setSingleValue(dimension.id, $ctrl.getSingleValue(dimension.id).value)\">\r\n                </salaxy-input>\r\n              </div>\r\n              <div class=\"col-md-1\">\r\n                <div ng-if=\"!$ctrl.readOnly && $ctrl.isInherited(dimension.id)\" class=\"btn float-end\" ng-click=\"$ctrl.setSingleValue(dimension.id, $ctrl.getInheritedSingleValue(dimension.id).value)\">\r\n                  <i class=\"bi bi-pencil-fill clickable\"></i>\r\n                </div>\r\n              </div>\r\n            </div>\r\n          </div>\r\n        </div>\r\n        <div ng-if=\"dimension.allowCostSharing\">\r\n          <div class=\"form-horizontal\">\r\n            <div class=\"row\">\r\n              <div class=\"col-md-11\">    \r\n                <table ng-if=\"$ctrl.isInherited(dimension.id)\" class=\"table\">\r\n                  <thead>\r\n                    <tr>\r\n                      <th class=\"text-muted\">{{(dimension.label || 'SALAXY.NG1.CalcCostAccountingComponent.defaultLabel') | sxyTranslate}}</th>\r\n                      <th class=\"right text-muted\">{{\"SALAXY.NG1.CalcCostAccountingComponent.percent\" | sxyTranslate}}</th>\r\n                      <th class=\"right\">\r\n                      </th>\r\n                    </tr>\r\n                  </thead>\r\n                  <tbody>\r\n                    <tr ng-repeat=\"item in $ctrl.getInheritedValues(dimension.id)\">\r\n                      <td>\r\n                        <salaxy-input-typeahead class=\"text-muted\" ng-if=\"$ctrl.hasOptions(item.id, item.value)\" ng-model=\"item.value\" label-format=\"text-value\" get-options=\"$ctrl.getOptions(dimension.id)\" name=\"{{ 'id' + $index }}\" label-type=\"plain\" read-only=\"true\" placeholder=\"{{ 'SALAXY.UI_Terms.notChosen' | sxyTranslate }}\"></salaxy-input-typeahead>\r\n                        <salaxy-input class=\"text-muted\" ng-if=\"!$ctrl.hasOptions(item.id, item.value)\" ng-model=\"item.value\" name=\"{{ 'id' + $index }}\" label-type=\"plain\" read-only=\"true\"></salaxy-input>\r\n                      </td>\r\n                      <td class=\"right\">\r\n                        <salaxy-input-number class=\"text-muted\" ng-model=\"item.percent\" name=\"{{ 'percent' + $index }}\" label-type=\"plain\" read-only=\"true\" unit=\"percent\"></salaxy-input-number>\r\n                      </td>\r\n                      <td class=\"text-right\">\r\n                      </td>\r\n                    </tr>\r\n                  </tbody>\r\n                  <tfoot>\r\n                    <tr class=\"total\">\r\n                      <td class=\"text-muted\">{{\"SALAXY.UI_Terms.total\" | sxyTranslate}}</td>\r\n                      <td class=\"right text-muted\">{{ $ctrl.getInheritedSum(dimension.id) | sxyCount : 'percent' }}</td>\r\n                      <td class=\"right\"></td>\r\n                    </tr>\r\n                  </tfoot>\r\n                </table>\r\n                <table ng-if=\"!$ctrl.isInherited(dimension.id)\" class=\"table\">\r\n                  <thead>\r\n                    <tr>\r\n                      <th>{{(dimension.label || 'SALAXY.NG1.CalcCostAccountingComponent.defaultLabel') | sxyTranslate}}</th>\r\n                      <th class=\"right\">{{\"SALAXY.NG1.CalcCostAccountingComponent.percent\" | sxyTranslate}}</th>\r\n                      <th class=\"right\">\r\n                        <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-if=\"!$ctrl.readOnly\" ng-click=\"$ctrl.current.push({'id': dimension.id})\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n                      </th>\r\n                    </tr>\r\n                  </thead>\r\n                  <tbody>\r\n                    <tr ng-repeat=\"item in $ctrl.getValues(dimension.id)\">\r\n                      <td>\r\n                        <salaxy-input-typeahead ng-if=\"$ctrl.hasOptions(item.id, item.value)\" ng-model=\"item.value\" label-format=\"text-value\" options=\"$ctrl.getOptions(dimension.id)\" name=\"{{ 'id' + $index }}\" label-type=\"plain\" read-only=\"$ctrl.readOnly\" placeholder=\"{{ 'SALAXY.UI_Terms.notChosen' | sxyTranslate }}\"></salaxy-input-typeahead>\r\n                        <salaxy-input ng-if=\"!$ctrl.hasOptions(item.id, item.value)\" ng-model=\"item.value\" name=\"{{ 'id' + $index }}\" label-type=\"plain\" read-only=\"$ctrl.readOnly\"></salaxy-input>\r\n                      </td>\r\n                      <td class=\"right\">\r\n                        <salaxy-input-number ng-model=\"item.percent\" name=\"{{ 'percent' + $index }}\" label-type=\"plain\" read-only=\"$ctrl.readOnly\" unit=\"percent\"></salaxy-input-number>\r\n                      </td>\r\n                      <td class=\"text-right\">\r\n                        <button ng-if=\"!$ctrl.readOnly\" type=\"button\" class=\"btn btn-danger\" ng-click=\"$ctrl.deleteValue(item)\">\r\n                          <i class=\"bi bi-trash\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\"></i>\r\n                        </button>\r\n                      </td>\r\n                    </tr>\r\n                  </tbody>\r\n                  <tfoot>\r\n                    <tr class=\"total\">\r\n                      <td>{{\"SALAXY.UI_Terms.total\" | sxyTranslate}}</td>\r\n                      <td class=\"right\">{{ $ctrl.getSum(dimension.id) | sxyCount : 'percent' }}</td>\r\n                      <td class=\"right\"></td>\r\n                    </tr>\r\n                  </tfoot>\r\n                </table>\r\n              </div>\r\n              <div class=\"col-md-1\">\r\n                <div class=\"btn btn-padding-right\" ng-if=\"!$ctrl.readOnly && $ctrl.isInherited(dimension.id)\">\r\n                  <i ng-click=\"$ctrl.setValues($ctrl.getInheritedValues(dimension.id))\" class=\"bi bi-pencil-fill clickable\"></i>\r\n                </div>\r\n              </div>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div ng-if=\"$ctrl.hasObsoleteValues\">\r\n        <table class=\"table\">\r\n          <thead>\r\n            <tr>\r\n              <th sxy-text=\"SALAXY.MODEL.CostAccountingDimensionDefinition.id.title\"></th>\r\n              <th sxy-text=\"SALAXY.MODEL.CostAccountingDimensionOption.value.title\"></th>\r\n              <th class=\"right\">{{\"SALAXY.NG1.CalcCostAccountingComponent.percent\" | sxyTranslate}}</th>\r\n              <th class=\"right\"></th>\r\n            </tr>\r\n          </thead>\r\n          <tbody>\r\n            <tr ng-repeat=\"item in $ctrl.obsoleteValues\">\r\n              <td>\r\n                <salaxy-input ng-model=\"item.id\" name=\"{{ 'nameObsolete' + $index }}\" label-type=\"plain\" read-only=\"true\"></salaxy-input>\r\n              </td>\r\n              <td>\r\n                <salaxy-input ng-model=\"item.value\" name=\"{{ 'idObsolete' + $index }}\" label-type=\"plain\" read-only=\"true\"></salaxy-input-enum>\r\n              </td>\r\n              <td>\r\n                <salaxy-input-number ng-if=\"item.percent\" ng-model=\"item.percent\" name=\"{{ 'percentObsolete' + $index }}\" label-type=\"plain\" read-only=\"true\" unit=\"percent\"></salaxy-input-number>\r\n              </td>\r\n              <td class=\"text-end\">\r\n                <button ng-if=\"!$ctrl.readOnly\" type=\"button\" class=\"btn btn-danger\" ng-click=\"$ctrl.deleteValue(item)\">\r\n                    <i class=\"bi bi-trash\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\"></i>\r\n                  </button>\r\n              </td>\r\n            </tr>\r\n          </tbody>\r\n        </table>\r\n      </div>\r\n    </fieldset>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/details/expenses.html\",`<form ng-submit=\"$ctrl.recalculate()\" name=\"detailsExpenses\">\r\n  <div class=\"salaxy-calc-dialog-body\">\r\n    <div class=\"salaxy-calc-dialog-container\">\r\n      <h1 sxy-text=\"SALAXY.NG1.CalcDetailsDialogComponent.allExpenses.title\"></h1>\r\n      <div class=\"form-horizontal\" ng-if=\"$ctrl.isHousehold\">\r\n        <salaxy-input-boolean type=\"checkbox\" name=\"isHouseholdDeductible\" ng-model=\"$ctrl.isHouseholdDeductible\" label=\"SALAXY.NG1.CalcDetailsDialogComponent.deductions.householdDetuction\" label-true=\"{{'SALAXY.NG1.CalcDetailsDialogComponent.deductions.label' | sxyTranslate}}\"></salaxy-input-boolean>\r\n        <salaxy-input-enum label=\"SALAXY.NG1.CalcDetailsDialogComponent.workType\" hidden-options=\"none\" name=\"taxDeductionCategory\" ng-if=\"$ctrl.isHouseholdDeductible\" ng-model=\"$ctrl.taxDeductionCategory\" enum=\"TaxDeductionWorkCategories\" type=\"select\" required></salaxy-input-enum>\r\n      </div>\r\n      <salaxy-calc-rows-2019-editor categories=\"['expenses']\" row-type-select-help=\"expenses\" parent=\"$ctrl.currentCalc\" mode=\"{{$ctrl.isReadOnly ? 'read-only' : 'edit'}}\" title=\"{{'SALAXY.NG1.CalcDetailsDialogComponent.expenses.title' | sxyTranslate}}\"></salaxy-calc-rows-2019-editor>\r\n      <salaxy-calc-rows-2019-editor categories=\"['benefits']\" row-type-select-help=\"benefits\" parent=\"$ctrl.currentCalc\" mode=\"{{$ctrl.isReadOnly ? 'read-only' : 'edit'}}\" title=\"{{ 'SALAXY.NG1.CalcDetailsDialogComponent.benefits.title2' | sxyTranslate}}\"></salaxy-calc-rows-2019-editor>\r\n      <salaxy-calc-rows-2019-editor categories=\"[ 'deductions']\" row-type-select-help=\"deductions\" parent=\"$ctrl.currentCalc\" mode=\"{{$ctrl.isReadOnly ? 'read-only' : 'edit'}}\" title=\"{{ 'SALAXY.NG1.CalcDetailsDialogComponent.deductions.title' |\r\n        sxyTranslate}}\"></salaxy-calc-rows-2019-editor>\r\n      <p>&nbsp;</p>\r\n    </div>\r\n  </div>\r\n  <button ng-if=\"!$ctrl.isReadOnly && $ctrl.currentCalc.workflow.status !='paymentStarted'\" class=\"btn btn-danger btn-lg salaxy-calc-btn-recalculate\" type=\"submit\" sxy-text=\"SALAXY.UI_Terms.recalculate\"></button>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/calc/details/salary.html\",`<form ng-submit=\"$ctrl.recalculate()\" name=\"detailsSalary\">\r\n  <div class=\"salaxy-calc-dialog-body\">\r\n    <div class=\"salaxy-calc-dialog-container\">\r\n      <h1 sxy-text=\"SALAXY.NG1.CalcDetailsDialogComponent.allSalaries.title\"></h1>\r\n      <salaxy-calc-rows-2019-editor row-type-select-help=\"salaries\" categories=\"['salary', 'salaryCalc', 'holidays', 'salaryAdditions']\" parent=\"$ctrl.currentCalc\" mode=\"{{$ctrl.isReadOnly ? 'read-only' : 'edit'}}\" title=\"{{'SALAXY.NG1.CalcDetailsDialogComponent.salaries.title2' | sxyTranslate}}\"></salaxy-calc-rows-2019-editor>\r\n      <p>&nbsp;</p>\r\n\r\n    </div>\r\n  </div>\r\n\r\n  <button ng-if=\"!$ctrl.isReadOnly && $ctrl.currentCalc.workflow.status != 'paymentStarted'\" class=\"btn btn-success btn-lg salaxy-calc-btn-recalculate\" type=\"submit\" sxy-text=\"SALAXY.UI_Terms.recalculate\"></button>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/calc/details/worker.html\",`<form ng-submit=\"$ctrl.recalculate()\" name=\"detailsWork\">\r\n  <div class=\"salaxy-calc-dialog-body\">\r\n    <div class=\"salaxy-calc-dialog-container\">\r\n      <div ng-if=\"!$ctrl.calcSections.get('worker').isSelectionDone\">\r\n\r\n        <div sxy-if-role=\"auth\">\r\n          <div class=\"row\">\r\n            <div class=\"col-12 col-sm-7\">\r\n              <div class=\"intro-text\">\r\n                <h1 sxy-text=\"SALAXY.NG1.CalcDetailsWorkerComponent.selectWorker\"></h1>\r\n                <p sxy-html=\"SALAXY.NG1.CalcDetailsWorkerComponent.myWorkers.description.html\"></p>\r\n              </div>\r\n            </div>\r\n            <div class=\"col-12 col-sm-5\">\r\n              <button type=\"button\" class=\"btn add-new-worker btn-primary float-sm-end mb-1\" ng-click=\"$ctrl.showNewWorkerDialog()\" sxy-text=\"SALAXY.NG1.CalcDetailsWorkerComponent.newWorker.cta\"></button>\r\n            </div>\r\n            <div class=\"col-12\">\r\n              <div class=\"table-responsive\">\r\n                <salaxy-employment-list mode=\"select\" on-list-select=\"$ctrl.updateFromEmployment(item.id, true)\"></salaxy-employment-list>\r\n              </div>\r\n            </div>\r\n          </div>\r\n        </div>\r\n        <div salaxy-if-role=\"anon\">\r\n          <h1 sxy-text=\"SALAXY.NG1.CalcDetailsWorkerComponent.selectWorker\" ps=\" (demo)\"></h1>\r\n          <p sxy-text=\"SALAXY.NG1.CalcDetailsWorkerComponent.notLoggedIn\"></p>\r\n          <p>Selecting an employment relation is not supported in the anonymous calculator. Implement if necessary.</p>\r\n        </div>\r\n      </div>\r\n      <div ng-if=\"$ctrl.calcSections.get('worker').isSelectionDone\">\r\n        <salaxy-calc-worker-info model=\"$ctrl.currentCalc\"></salaxy-calc-worker-info>\r\n        <div class=\"row\">\r\n          <div class=\"col-md-6 col-12 form-horizontal\">\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.NG1.CalcDetailsWorkerComponent.job\"></legend>\r\n              <salaxy-input-occupation-type name=\"occupationCode\" ng-model=\"$ctrl.currentCalc.info.occupationCode\" label=\"SALAXY.MODEL.CalcInfo.occupationCode.title\" read-only=\"$ctrl.isReadOnly\"></salaxy-input-occupation-type>\r\n              <salaxy-input name=\"workDescription\" ng-model=\"$ctrl.currentCalc.info.workDescription\" label=\"SALAXY.MODEL.CalcInfo.workDescription.title\" read-only=\"$ctrl.isReadOnly\"></salaxy-input>\r\n              <salaxy-input-collective-bargain-agreement read-only=\"$ctrl.isReadOnly\" name=\"collectiveBargainAgreement\" ng-model=\"$ctrl.currentCalc.info.cbaCode\" label=\"SALAXY.NG1.WorkerWizardComponent.employment.info.cbaCode\"></salaxy-input-collective-bargain-agreement>\r\n              <salaxy-textarea sxy-if-role=\"!worker\" name=\"salarySlipMessage\" ng-model=\"$ctrl.currentCalc.info.salarySlipMessage\" label=\"SALAXY.MODEL.CalcInfo.salarySlipMessage.title\" read-only=\"$ctrl.isReadOnly\"></salaxy-textarea>\r\n            </fieldset>\r\n          </div>\r\n          <div class=\"col-md-6 col-12 form-horizontal\">\r\n              <salaxy-calc-cost-accounting salaxy-if-role=\"company\" calc=\"$ctrl.current\" read-only=\"$ctrl.isReadOnly\"></salaxy-calc-cost-accounting>\r\n          </div>\r\n        </div>\r\n        <div class=\"row\" sxy-if-role=\"worker\">\r\n          <div class=\"col\">\r\n            <a href=\"#/taxcards\" class=\"btn add-new-worker btn-info\" sxy-text=\"SALAXY.NG1.CalcDetailsWorkerComponent.addSharedTaxCard\"></a>\r\n            <a href=\"#/account\" class=\"btn btn-default\" sxy-text=\"SALAXY.NG1.CalcDetailsWorkerComponent.editAccount\"></a>\r\n          </div>\r\n        </div>\r\n        <div class=\"row\" sxy-if-role=\"!worker\">\r\n          <div class=\"col\">\r\n            <span sxy-if-role=\"auth\">\r\n              <span ng-if=\"$ctrl.currentCalc.worker.tax.snapshot.kind == 'auto'\">\r\n                <span class=\"text-info\" ng-if=\"$ctrl.currentCalc.worker.tax.snapshot.lastChecked != '2000-01-01T00:00:00Z'\"><small>{{'SALAXY.NG1.CalcDetailsWorkerComponent.taxCardChecked' | sxyTranslate}} {{$ctrl.currentCalc.worker.tax.snapshot.lastChecked | date: \"dd.MM.yyyy HH:mm\"}}</small></span>\r\n                <br/>\r\n                <button type=\"button\" ng-disabled=\"$ctrl.loaders['showRefreshAutoTaxcardDialog']\" ng-click=\"$ctrl.showRefreshAutoTaxcardDialog()\" class=\"btn btn-info\" sxy-text=\"SALAXY.NG1.CalcDetailsWorkerComponent.checkAutomaticTaxcard\"></button>\r\n              </span>\r\n              <button type=\"button\" ng-click=\"$ctrl.showWorkerEditDialog()\" class=\"btn add-new-worker btn-default\" sxy-text=\"SALAXY.NG1.CalcDetailsWorkerComponent.workerEdit\"></button>\r\n            </span>\r\n            <button ng-if=\"!$ctrl.isReadOnly &&  $ctrl.currentCalc.workflow.status != 'paymentStarted'\" ng-click=\"$ctrl.resetWorker()\" type=\"button\" class=\"btn add-new-worker btn-default\" sxy-text=\"SALAXY.NG1.CalcDetailsWorkerComponent.resetWorker\"></button>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <button ng-if=\"!$ctrl.isReadOnly\" ng-disabled=\"!$ctrl.calcSections.get('worker').isSelectionDone\" class=\"btn btn-info btn-lg salaxy-calc-btn-recalculate\" type=\"submit\" sxy-text=\"SALAXY.UI_Terms.recalculate\"></button>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/calc/details/worktime-pro.html\",`<div class=\"modal-header bg-primary d-flex\">\r\n  <h1 class=\"d-flex align-items-center m-0\">\r\n    <span class=\"badge bg-secondary text-dark me-2\">Pro</span>\r\n    <span sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.absences.proTabTitle\"></span>\r\n  </h1>\r\n  <button type=\"button\" class=\"btn-close btn-close ms-auto\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n</div>\r\n<div class=\"modal-body\">\r\n  <div class=\"form-horizontal form-condensed\">\r\n    <p class=\"lead\" sxy-text=\"SALAXY.NG1.CalcDetailsWorktimeProComponent.lead.text\"></p>\r\n    <div class=\"row\">\r\n      <div class=\"col-sm-6\">\r\n        <fieldset>\r\n          <legend sxy-text=\"SALAXY.NG1.CalcDetailsWorktimeProComponent.basicInfo\"></legend>\r\n          <salaxy-date-range read-only=\"true\" ng-model=\"$ctrl.data.worktime.workDays\" name=\"workDays\" label=\"SALAXY.NG1.CalcDetailsWorktimeProComponent.workDays\"></salaxy-date-range>\r\n        </fieldset>\r\n        <fieldset>\r\n          <salaxy-input-number ng-model=\"$ctrl.data.worktime.absencesDailySalary\" name=\"absencesDailySalary\" label=\"SALAXY.NG1.CalcWorktimeComponent.lists.absencePeriods.absencesDailySalary\" label-cols=\"col-sm-6\"></salaxy-input-number>\r\n          <table class=\"table table-striped table-sm\" ng-if=\"$ctrl.data.logic.getAbcencesForPeriod().length\">\r\n            <thead>\r\n              <tr>\r\n                <th sxy-text=\"SALAXY.NG1.AbsencePeriodsComponent.headerAbsence\"></th>\r\n                <th class=\"right\" sxy-text=\"SALAXY.NG1.AbsencePeriodsComponent.headerDays\"></th>\r\n              </tr>\r\n            </thead>\r\n            <tbody>\r\n              <tr ng-repeat=\"row in $ctrl.data.logic.getAbcencesForPeriod()\">\r\n                <td>\r\n                  <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" avatar=\"{ color: '#2b507c', initials: (row.period.daysCount + 'pv'), entityType: 'company' }\"></salaxy-avatar>\r\n                  <strong>{{ \"AbsenceCauseCode.\" + row.causeCode | sxyEnum }}</strong><br />\r\n                  <div class=\"float-start\" style=\"padding: 0px;\">\r\n                    {{ row.isPaid ? ('SALAXY.NG1.AbsencePeriodsComponent.isPaid' | sxyTranslate) : ('SALAXY.NG1.AbsencePeriodsComponent.notPaid' |sxyTranslate) }}\r\n                    <span ng-if=\"row.isPaid != row.isHolidayAccrual\"> {{ row.isHolidayAccrual ? ('SALAXY.NG1.AbsencePeriodsComponent.isAccrual' | sxyTranslate) : ('SALAXY.NG1.AbsencePeriodsComponent.notAccrual' | sxyTranslate) }}</span>\r\n                  </div>\r\n                  <div class=\"truncate\" style=\"max-width: 250px; padding: 0px;\">\r\n                    &nbsp;{{ row.notes }}\r\n                  </div>\r\n                </td>\r\n                <td class=\"right\">\r\n                  <strong>{{ row.period.daysCount | sxyCount : \"day\" }}</strong><br /> {{ row.period | sxyDateRange }}\r\n                </td>\r\n              </tr>\r\n              <tr class=\"total\">\r\n                <td>\r\n                  <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" style=\"margin-bottom: 20px\" avatar=\"{ color: '#2b507c', initials: 'sum', entityType: 'company' }\"></salaxy-avatar>\r\n                  <strong>\r\n                    <span sxy-text=\"SALAXY.NG1.AbsencePeriodsComponent.totalUnpaid\"></span><br />\r\n                                <span sxy-text=\"SALAXY.NG1.AbsencePeriodsComponent.totalNoHolidayAccrual\"></span><br />\r\n                                  <span sxy-text=\"SALAXY.NG1.AbsencePeriodsComponent.totalAll\"></span><br />\r\n                  </strong>\r\n                </td>\r\n                <td class=\"right\">\r\n                  <strong>\r\n                    {{ $ctrl.data.logic.getAbcensePeriodsTotalDays(\"absencesUnpaid\") | sxyCount : \"day\" }}<br />\r\n                    {{ $ctrl.data.logic.getAbcensePeriodsTotalDays(\"absencesNoHolidayAccrual\") | sxyCount : \"day\" }}<br />\r\n                    {{ $ctrl.data.logic.getAbcensePeriodsTotalDays(\"all\") | sxyCount : \"day\" }}<br />\r\n                  </strong>\r\n                </td>\r\n              </tr>\r\n            </tbody>\r\n          </table>\r\n          <p ng-if=\"!$ctrl.data.logic.getAbcencesForPeriod().length\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.absencePeriods.noAbsences\"></p>\r\n        </fieldset>\r\n          <fieldset  ng-if=\"$ctrl.data.worktime.holidaySpec.code == 'permanent14Days' || $ctrl.data.worktime.holidaySpec.code == 'permanent35Hours' || $ctrl.data.worktime.holidaySpec.code == 'temporaryTimeOff' || $ctrl.data.worktime.holidaySpec.code == 'other' || $ctrl.data.worktime.holidaySpec.code == 'script'\">\r\n          <table class=\"table table-striped table-sm\" ng-if=\"$ctrl.data.logic.getAnnualLeavesForPeriod().length\">\r\n            <thead>\r\n              <tr>\r\n                <th sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidays.tableHead.period\"></th>\r\n                <th class=\"right\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidays.tableHead.daysCount\"></th>\r\n                <th class=\"right\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidays.tableHead.bonusDaysCount\"></th>\r\n              </tr>\r\n            </thead>\r\n            <tr ng-repeat=\"row in $ctrl.data.logic.getAnnualLeavesForPeriod()\">\r\n              <td>\r\n                <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" avatar=\"{ color: '#2b507c', initials: (row.period.daysCount + 'pv'), entityType: 'company' }\"></salaxy-avatar>\r\n                <strong>{{ row.period | sxyDateRange }}</strong>\r\n                <br />\r\n                <small>\r\n                  <div class=\"truncate\" style=\"max-width: 250px;\">{{ $ctrl.data.logic.getAnnualLeaveDescription(row) }}</div>\r\n                </small>\r\n              </td>\r\n              <td class=\"right\">\r\n                <strong>{{ row.period.daysCount | sxyCount : \"day\"  }}</strong>\r\n              </td>\r\n              <td class=\"right\">\r\n                <strong>{{ row.bonusDaysCount | sxyCount : \"day\"  }}</strong>\r\n              </td>\r\n            </tr>\r\n            <tr class=\"total\">\r\n              <td>\r\n                <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" avatar=\"{ color: '#2b507c', initials: 'sum', entityType: 'company' }\"></salaxy-avatar>\r\n                <strong sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidays.tableBody.total\"></strong>\r\n                <br />\r\n                <small>\r\n                  <div class=\"truncate\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidays.tableBody.totalMore\"></div>\r\n                </small>\r\n              </td>\r\n              <td class=\"right\">\r\n                <strong>{{ $ctrl.data.logic.getAnnualLeavesTotalDays() | sxyCount : \"day\" }}</strong>\r\n              </td>\r\n              <td class=\"right\">\r\n                <strong>{{ $ctrl.data.logic.getAnnualLeavesBonusTotalDays() | sxyCount : \"day\" }}</strong>\r\n              </td>\r\n            </tr>\r\n          </table>\r\n          <p ng-if=\"!$ctrl.data.logic.getAnnualLeavesForPeriod().length\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.lists.annualLeaves.noAnnualLeaves\"></p>\r\n        </fieldset>      \r\n      </div>\r\n      <div class=\"col-sm-6\">\r\n          <fieldset ng-if=\"$ctrl.data.worktime.accrualSpec.code == 'permanent14Days' || $ctrl.data.worktime.accrualSpec.code == 'permanent35Hours' || $ctrl.data.worktime.accrualSpec.code == 'temporaryTimeOff' || $ctrl.data.worktime.accrualSpec.code == 'other' || $ctrl.data.worktime.accrualSpec.code == 'script'\">\r\n          <legend sxy-text=\"SALAXY.NG1.CalcDetailsWorktimeProComponent.holidays\"></legend>\r\n          <table class=\"table table-sm\">\r\n            <thead>\r\n              <th sxy-text=\"SALAXY.NG1.CalcDetailsWorktimeProComponent.headerMonth\"></th>\r\n              <th sxy-text=\"SALAXY.NG1.CalcDetailsWorktimeProComponent.headerHolidays\" class=\"right\"></th>\r\n              <th sxy-text=\"SALAXY.NG1.CalcDetailsWorktimeProComponent.headerAway\" class=\"right\"></th>\r\n              <th sxy-text=\"SALAXY.NG1.CalcDetailsWorktimeProComponent.headerDate\" class=\"right\"></th>\r\n              <th sxy-text=\"SALAXY.NG1.CalcDetailsWorktimeProComponent.headerHours\" class=\"right\"></th>\r\n            </thead>\r\n            <tbody>\r\n              <tr ng-repeat=\"month in $ctrl.data.worktime.accruals\">\r\n                <td>{{ month.month | sxyDate }}</td>\r\n                <td class=\"right\">{{ month.daysAccrued | sxyCount : \"days\" }}</td>\r\n                <td class=\"right\">{{ month.absencesDays | sxyCount : \"days\" }}</td>\r\n                <td class=\"right\">{{ month.workDays | sxyCount : \"days\" }}</td>\r\n                <td class=\"right\">{{ month.workHours | sxyCount : \"hours\" }}</td>\r\n              </tr>\r\n            </tbody>\r\n          </table>\r\n        </fieldset>\r\n        <fieldset ng-if=\"$ctrl.data.worktime.holidaySpec.code != 'undefined'\">\r\n          <legend sxy-text=\"SALAXY.NG1.CalcDetailsWorktimeProComponent.holidayYearSettings\"></legend>\r\n          <salaxy-form-group name=\"employmentPeriod\" class=\"salaxy-read-only\" label-cols=\"col-sm-6\" label=\"SALAXY.NG1.CalcDetailsWorktimeProComponent.employmentPeriod\">\r\n            <div class=\"form-control-plaintext\">\r\n              {{$ctrl.data.worktime.holidaySpec.employmentPeriod | sxyDateRange }}\r\n            </div>\r\n          </salaxy-form-group>\r\n          <salaxy-input-enum disabled=\"true\" ng-model=\"$ctrl.data.worktime.holidaySpec.wageBasis\" name=\"wageBasis\" enum=\"WageBasis\" hidden-options=\"other\" label=\"SALAXY.NG1.CalcDetailsWorktimeProComponent.wageBasis\" label-cols=\"col-sm-6\"></salaxy-input-enum>\r\n          <salaxy-input-enum disabled=\"true\" name=\"holidayPayCalculation\" ng-model=\"$ctrl.data.worktime.holidaySpec.holidayPayCalculation\" label=\"SALAXY.MODEL.HolidaySpecificationForYear.holidayPayCalculation.title\" options=\"$ctrl.data.logic.getholidayPayCalculationOptions()\" disable-cache=\"true\" label-cols=\"col-sm-6\"></salaxy-input-enum>\r\n          <salaxy-input-number ng-model=\"$ctrl.data.worktime.leavesDailySalary\" name=\"leavesDailySalary\" label=\"SALAXY.NG1.CalcDetailsWorktimeProComponent.leavesDailySalary\" label-cols=\"col-sm-6\"></salaxy-input-number>\r\n\r\n          <salaxy-input-number ng-model=\"$ctrl.data.worktime.holidaySpec.compensation\" name=\"compensation\" ng-if=\"$ctrl.data.worktime.holidaySpec.code == 'holidayCompensation'\" label-cols=\"col-sm-6\" unit=\"percent\" required label=\"SALAXY.MODEL.HolidaySpecificationForYear.compensation.label\" ></salaxy-input-number>     \r\n            <salaxy-input-number  ng-model=\"$ctrl.data.worktime.holidaySpec.compensation\" name=\"compensation\" ng-if=\"($ctrl.data.worktime.holidaySpec.code == 'temporaryTimeOff' || $ctrl.data.worktime.holidaySpec.code == 'other' || $ctrl.data.worktime.holidaySpec.code == 'script') && $ctrl.data.worktime.holidaySpec.holidayPayCalculation == 'holidayCompensation'\" label-cols=\"col-sm-6\" unit=\"percent\" required label=\"SALAXY.MODEL.HolidaySpecificationForYear.compensation.title\" ></salaxy-input-number>\r\n        \r\n          <!-- accruals or compensation -->\r\n            <salaxy-input-enum ng-if=\"($ctrl.data.worktime.holidaySpec.code == 'permanent14Days' || $ctrl.data.worktime.holidaySpec.code == 'permanent35Hours' || $ctrl.data.worktime.holidaySpec.code == 'temporaryTimeOff' || $ctrl.data.worktime.holidaySpec.code == 'other' || $ctrl.data.worktime.holidaySpec.code == 'script')\" ng-model=\"$ctrl.data.worktime.holidaySpec.bonusMethod\" name=\"bonusMethod\" filter=\"none,payForHolidaySalary,paySelectedDays\" enum=\"HolidayBonusPaymentMethod\" label=\"SALAXY.NG1.CalcDetailsWorktimeProComponent.bonusMethod\" label-cols=\"col-sm-6\"></salaxy-input-enum>\r\n          <salaxy-input-enum ng-if=\"($ctrl.data.worktime.holidaySpec.code == 'holidayCompensation')\" ng-model=\"$ctrl.data.worktime.holidaySpec.bonusMethod\" name=\"bonusMethod\" filter=\"none,payForHolidaySalary\" enum=\"HolidayBonusPaymentMethod\" label=\"SALAXY.NG1.CalcDetailsWorktimeProComponent.bonusMethod\" label-cols=\"col-sm-6\"></salaxy-input-enum>\r\n            <salaxy-input-number ng-if=\"($ctrl.data.worktime.holidaySpec.code == 'holidayCompensation' || $ctrl.data.worktime.holidaySpec.code == 'permanent14Days' || $ctrl.data.worktime.holidaySpec.code == 'permanent35Hours' || $ctrl.data.worktime.holidaySpec.code == 'temporaryTimeOff' || $ctrl.data.worktime.holidaySpec.code == 'other' || $ctrl.data.worktime.holidaySpec.code == 'script')\" ng-model=\"$ctrl.data.worktime.holidaySpec.bonus\" name=\"bonus\" label=\"SALAXY.NG1.CalcDetailsWorktimeProComponent.bonus\" label-cols=\"col-sm-6\" unit=\"percent\"></salaxy-input-number>\r\n        </fieldset>\r\n          <fieldset ng-if=\"$ctrl.data.worktime.holidaySpec.code == 'permanent14Days' || $ctrl.data.worktime.holidaySpec.code == 'permanent35Hours' || $ctrl.data.worktime.holidaySpec.code == 'temporaryTimeOff' || $ctrl.data.worktime.holidaySpec.code == 'other' || $ctrl.data.worktime.holidaySpec.code == 'script'\">\r\n          <legend sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.availableHolidays.legend\"></legend>\r\n          <salaxy-input-number ng-model=\"$ctrl.data.worktime.holidayPayAccrualRemaining\" name=\"holidayPayAccrualRemaining\" disabled=\"true\" label=\"SALAXY.NG1.CalcWorktimeComponent.availableHolidays.holidayPayAccrualRemaining\" label-cols=\"col-sm-7\"></salaxy-input-number>\r\n          <salaxy-input-number ng-if=\"$ctrl.data.worktime.holidaySpec.bonusMethod != 'none'\" ng-model=\"$ctrl.data.worktime.holidayBonusAccrualRemaining\" name=\"holidayBonusAccrualRemaining\" disabled=\"true\" label=\"SALAXY.NG1.CalcWorktimeComponent.availableHolidays.holidayBonusAccrualRemaining\" label-cols=\"col-sm-7\"></salaxy-input-number>\r\n        </fieldset>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>\r\n<div class=\"modal-footer\"></div>`);\n\n $templateCache.put(\"salaxy-components/calc/PayButton.html\",`<div class=\"salaxy-pay-button salaxy-component\" ng-if=\"!('salaxyPay' | sxyIsInRole)\">\r\n  <button ng-if=\"($ctrl.mode || 'pay-button') != 'channel-select'\" ng-disabled=\"$ctrl.disabled\" type=\"button\" ng-click=\"$ctrl.goToInvoices()\" class=\"btn btn-primary btn-labeled-right btn-pay\" ng-class=\"$ctrl.buttonClass + ($ctrl.mode == 'button-and-channel' ? ' btn-block' : '')\">\r\n    {{ $ctrl.getPaymentButtonText() }} <i class=\"bi bi-currency-euro\"></i>\r\n  </button>\r\n  <div>\r\n    <div ng-if=\"$ctrl.mode == 'button-and-channel'\" class=\"payment-channel-selection-label mt-4\" sxy-text=\"SALAXY.NG1.PayButtonComponent.paymentChannelLabel\" ps=\":\"></div>\r\n    <div ng-if=\"($ctrl.mode || 'pay-button') != 'pay-button'\" class=\"dropdown\" ng-class=\"$ctrl.buttonClass + ($ctrl.mode == 'button-and-channel' ? ' btn-block' : '')\">\r\n      <button id=\"btnChannel\" type=\"button\" class=\"btn btn-default btn-block dropdown-toggle justify-content-start\" data-bs-toggle=\"dropdown\">\r\n        <salaxy-avatar class=\"py-1\" avatar=\"$ctrl.currentChannel\"></salaxy-avatar>\r\n        <span class=\"button-text\">\r\n          {{ $ctrl.currentChannel.displayName }}\r\n        </span>\r\n      </button>\r\n      <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"btnChannel\">\r\n        <li role=\"menuitem\" ng-class=\"{ 'disabled': channel.id == 'zeroPayment' }\" ng-repeat=\"channel in $ctrl.allChannels\">\r\n          <a href=\"\" ng-click=\"$ctrl.setPaymentChannel(channel.id)\" class=\"dropdown-item text-uppercase d-flex p-2\" title=\"{{ channel.description }}\">\r\n            <salaxy-avatar style=\"font-size: 1.8em; margin: -2px 6px -2px 0px;\" avatar=\"channel\"></salaxy-avatar>\r\n            <span class=\"button-text\">{{ channel.displayName }}</span>\r\n          </a>\r\n        </li>\r\n        <li>\r\n          <a href=\"#/settings/payment-channel-settings\" class=\"dropdown-item text-uppercase\" sxy-text=\"SALAXY.NG1.PayButtonComponent.moreOptionsLink\" ps=\"...\"></a>\r\n        </li>\r\n      </ul>\r\n    </div>\r\n  </div>\r\n</div>\r\n<div ng-if=\"('salaxyPay' | sxyIsInRole)\" ng-controller=\"NewPaymentController as $newCtrl\">\r\n  <button ng-disabled=\"$newCtrl.disabled\" type=\"button\" ng-click=\"$newCtrl.openSalaxyPay($ctrl.model)\" class=\"btn btn-primary btn-labeled-right btn-pay btn-block\">\r\n    {{ $newCtrl.getPaymentButtonText($ctrl.label) }} <i class=\"bi bi-currency-euro\"></i>\r\n  </button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/payroll/PayrollCalcs.html\",`<div class=\"salaxy-component salaxy-calc-group-edit\">\r\n  <div class=\"payroll-calculations-container\">\r\n\r\n    <div class=\"dropdown toolbar-top\" ng-if=\"$ctrl.hasCalculations\">\r\n      <ng-include src=\"'salaxy-components/calc/payroll/PayrollCalcs_toolbar.html'\"></ng-include>\r\n    </div>\r\n    \r\n\r\n    <div ng-if=\"!$ctrl.hasCalculations\">\r\n      <div class=\"salaxy-placeholder-empty placeholder-md placeholder-default text-center\">\r\n        <h4 sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.placeholder.title\"></h4>\r\n        <div ng-if=\"$ctrl.mode != 'service'\" class=\"btn-group dropdown\">\r\n          <button type=\"button\" class=\"btn btn-labeled-left btn-primary dropdown-toggle\" data-bs-toggle=\"dropdown\" aria-expanded=\"false\"><i class=\"bi bi-plus-lg\"></i>\r\n            <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.addCalculation\"></span>\r\n          </button>\r\n          <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"addcalculation\">\r\n            <li role=\"menuitem\">\r\n              <a ng-click=\"$ctrl.createNewCalc()\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.addWorker\"></a>\r\n            </li>\r\n            <li role=\"menuitem\">\r\n              <a ng-click=\"$ctrl.addExistingCalc('draft')\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.addDraft\"></a>\r\n            </li>\r\n            <li role=\"menuitem\">\r\n              <a ng-click=\"$ctrl.addExistingCalc('paid')\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.addCopy\"></a>\r\n            </li>\r\n            <li role=\"menuitem\">\r\n              <a ng-click=\"$ctrl.mergePayroll(true)\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.addPayroll\"></a>\r\n            </li>\r\n          </ul>\r\n        </div>\r\n        <button ng-if=\"$ctrl.mode == 'service'\" type=\"button\" class=\"btn btn-labeled-right btn-primary\" ng-click=\"$ctrl.createNewCalc()\">\r\n          <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.addCalculation\"></span><i class=\"bi bi-plus-lg\"></i>\r\n        </button>\r\n      </div>\r\n    </div>\r\n    <div ng-repeat=\"calc in $ctrl.calcs | filter: {worker:{avatar:{displayName:$ctrl.searchByName}}}\">\r\n      \r\n      <div class=\"payroll-single-calculation\" ng-class=\"{'error-container': !$ctrl.getValidation(calc).isValid }\">\r\n        <div class=\"float-end icon-container btn-group\">\r\n          <button class=\"btn btn-transparent btn-xs toggle-details\" ng-click=\"$ctrl.getUi(calc).isCollapsed = !$ctrl.getUi(calc).isCollapsed\">\r\n            <i class=\"bi\" ng-class=\"{'bi-chevron-up' : !$ctrl.getUi(calc).isCollapsed,  'bi-chevron-down' : $ctrl.getUi(calc).isCollapsed}\"\r\n               title=\"{{'SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.toggle' | sxyTranslate}}\">\r\n            </i>\r\n          </button>\r\n          <div class=\"btn-group btn-group-sm\">\r\n            <button class=\"btn btn-transparent btn-xs options dropdown-toggle\" type=\"button\" data-bs-toggle=\"dropdown\" aria-expanded=\"false\" ng-if=\"!$ctrl.isReadOnly\">\r\n              <i class=\"bi bi-three-dots\" title=\"{{'SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.options' | sxyTranslate}}\"></i>\r\n            </button>\r\n            <ul class=\"dropdown-menu\" role=\"menu\" ng-if=\"!$ctrl.isReadOnly\">\r\n              <ng-include src=\"'salaxy-components/calc/payroll/PayrollCalcs_edit_dropdown.html'\"></ng-include>\r\n            </ul>\r\n          </div>\r\n        </div>\r\n        <div class=\"payroll-worker-summary clickable\" ng-if=\"$ctrl.getUi(calc).isCollapsed\" ng-click=\"$ctrl.getUi(calc).isCollapsed = !$ctrl.getUi(calc).isCollapsed\">\r\n          <div class=\"avatar-container\">\r\n            <salaxy-avatar avatar=\"calc.worker.avatar\"></salaxy-avatar>\r\n            <span class=\"worker-name\">{{calc.worker.avatar.displayName}}</span>\r\n            <span class=\"calculation-summary\">{{calc.result.totals.totalGrossSalary | currency }}</span>\r\n            <span ng-if=\"!$ctrl.getValidation(calc).isValid\" class=\"error-summary text-danger d-none d-sm-inline\" sxy-text=\"{{'SALAXY.VALIDATION.' + $ctrl.getValidation(calc).errors[0].code + '.label'}}\"></span>\r\n            <span ng-if=\"!$ctrl.isReadOnly\">\r\n              <span ng-controller=\"EmploymentCrudController as $employment\">\r\n                <salaxy-workflow-badge ng-if=\"$ctrl.employments[calc.worker.employmentId]\" mode=\"horizontal\" model=\"$ctrl.employments[calc.worker.employmentId]\" api-ctrl=\"$employment\" wf-types=\"'EmployerMessageRecord'\"></salaxy-workflow-badge>\r\n              </span>\r\n            </span>\r\n          </div>\r\n        </div>\r\n        <div class=\"payroll-worker-details\" ng-if=\"!$ctrl.getUi(calc).isCollapsed\">\r\n          <div class=\"row payroll-worker-info\">\r\n            <div class=\"col-2 col-sm-2\">\r\n              <div class=\"avatar-container\">\r\n                <salaxy-avatar avatar=\"calc.worker.avatar\"></salaxy-avatar>\r\n              </div>\r\n            </div>\r\n            <div class=\"col-9\">\r\n              <h3 class=\"worker-name clickable\" ng-click=\"$ctrl.getUi(calc).isCollapsed = !$ctrl.getUi(calc).isCollapsed\">{{calc.worker.avatar.displayName}}</h3>\r\n              <div class=\"row\">\r\n                <div class=\"col-12 col-sm-5 worker-info-col\">\r\n                  {{calc.worker.paymentData.email}}<br> {{calc.worker.paymentData.telephone}}\r\n                  <br>\r\n                  <span ng-if=\"calc.worker.paymentData.ibanNumber\">{{calc.worker.paymentData.ibanNumber | sxyIban}}</span>\r\n                  <span ng-if=\"!calc.worker.paymentData.ibanNumber\"><span class=\"text-danger\"\r\n                      sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.workerInfo.noIban\"></span></span>\r\n                  <br>\r\n                  <button class=\"btn btn-secondary btn-xs btn-edit-worker\" ng-click=\"$ctrl.showEditWorkerDialog(calc)\" ng-class=\"{'btn-danger':!calc.worker.paymentData.ibanNumber}\" ng-if=\"!$ctrl.isReadOnly\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.workerInfo.editWorker\"></button>\r\n                </div>\r\n                <div class=\"col-12 col-sm-7 worker-info-col\">\r\n                  <span>\r\n                    <span ng-class=\"{'text-danger': $ctrl.getTaxUi(calc).status != 'ok'}\">{{ $ctrl.getTaxUi(calc).text }}</span>\r\n                    <button ng-if=\"!$ctrl.isReadOnly && $ctrl.getTaxUi(calc).status != 'ok'\" class=\"btn btn-xs btn-default\" ng-click=\"$ctrl.commitCalc(calc, false, true)\"><i class=\"bi bi-arrow-repeat\"></i></button>\r\n                    <button ng-if=\"!$ctrl.isReadOnly && $ctrl.getTaxUi(calc).status == 'missing'\" class=\"btn btn-xs btn-default\" ng-click=\"$ctrl.showAddNewTaxcard(calc)\"><i class=\"bi bi-plus-lg\"></i></button>\r\n                  </span>\r\n                  <span ng-if=\"calc.worker.tax.snapshot.kind == 'auto'\">\r\n                    <br />\r\n                    <span class=\"text-info\" ng-if=\"calc.worker.tax.snapshot.lastChecked != '2000-01-01T00:00:00Z'\"><small>{{'SALAXY.NG1.PayrollComponent.payrollCalcs.taxCard.taxCardChecked' | sxyTranslate}} {{calc.worker.tax.snapshot.lastChecked | date: \"dd.MM.yyyy HH:mm\"}}</small></span>\r\n                  <br/>\r\n                  <button ng-if=\"!$ctrl.isReadOnly\" class=\"btn btn-xs btn-info\" ng-disabled=\"$ctrl.loaders['showRefreshAutoTaxcardDialog']\" ng-click=\"$ctrl.showRefreshAutoTaxcardDialog(calc)\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.taxCard.refreshAutoTaxCard\"></button>\r\n                  </span>\r\n                  <br> <strong sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.workerInfo.salaryPeriod\"></strong>\r\n                  <span>{{ calc.info | sxyDateRange }} ({{ calc.framework.numberOfDays }} <span\r\n                      sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.workerInfo.salaryPeriodDaysCount\"></span>)</span>\r\n                  <button class=\"btn btn-transparent btn-xs\" ng-click=\"$ctrl.showDateRangeForCalculation(calc)\" ng-if=\"!$ctrl.isReadOnly\"><i class=\"bi bi-pencil-fill\"></i></button>\r\n                  <div ng-if=\"$ctrl.isDateDifferent(calc)\">\r\n                    <del class=\"small\">{{ $ctrl.current.input.period | sxyDateRange }} ({{ $ctrl.current.input.period.daysCount }} <span\r\n                        sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.workerInfo.salaryPeriodDaysCount\"></span>)</del>\r\n                  </div>\r\n                  <table ng-if=\"!('disableHolidays' | sxyIsInRole)\" class=\"text-small\">\r\n                    <tbody>\r\n                      <tr>\r\n                        <td sxy-text=\"SALAXY.NG1.CalcComponent.panelWorkTime.overview.leavesDays\"></td>\r\n                        <td class=\"right\">{{ $ctrl.calculatePeriodDays(calc,'leavesDays') | sxyCount : 'day' }}</td>\r\n                      </tr>\r\n                      <tr>\r\n                        <td sxy-text=\"SALAXY.NG1.CalcComponent.panelWorkTime.overview.absencesDays\"></td>\r\n                        <td class=\"right\">{{ $ctrl.calculatePeriodDays(calc,'absencesDays') | sxyCount : 'day' }}</td>\r\n                      </tr>\r\n                      <tr>\r\n                        <td sxy-text=\"SALAXY.NG1.CalcComponent.panelWorkTime.overview.paidAbsencesDays\"></td>\r\n                        <td class=\"right\">{{ $ctrl.calculatePeriodDays(calc,'paidAbsencesDays') | sxyCount : 'day' }}</td>\r\n                      </tr>\r\n                      <tr ng-if=\"$ctrl.showAccruals(calc)\">\r\n                        <td sxy-text=\"SALAXY.NG1.CalcComponent.panelWorkTime.overview.accruedDays\"></td>\r\n                        <td class=\"right\">{{ $ctrl.calculatePeriodDays(calc,'accruedDays') | sxyCount : 'day' }}</td>\r\n                      </tr>\r\n                    </tbody>\r\n                  </table>\r\n                </div>\r\n              </div>\r\n              <div ng-if=\"!$ctrl.isReadOnly\">\r\n                <span ng-controller=\"EmploymentCrudController as $employment\">\r\n                  <salaxy-workflow-badge ng-if=\"$ctrl.employments[calc.worker.employmentId]\" mode=\"horizontal\" model=\"$ctrl.employments[calc.worker.employmentId]\" api-ctrl=\"$employment\" wf-types=\"'EmployerMessageRecord'\"></salaxy-workflow-badge>\r\n                </span>\r\n              </div>\r\n            </div>\r\n          </div>\r\n          <div ng-if=\"!$ctrl.getValidation(calc).isValid\" class=\"text-danger d-flex align-items-baseline\">\r\n            <ul class=\"small\">\r\n              <li ng-if=\"!$ctrl.getValidation(calc)\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.validation.noValidationFound\"></li>\r\n              <li ng-repeat=\"error in $ctrl.getValidation(calc).errors\">\r\n                <strong>{{ 'ApiValidationErrorType.' + error.type | sxyEnum }}:</strong>\r\n                <span sxy-text=\"{{'SALAXY.VALIDATION.' + error.code + '.label'}}\"></span>\r\n              </li>\r\n            </ul>\r\n            <button ng-if=\"$ctrl.getValidation(calc)\" ng-controller=\"ValidationSummaryController as $validation\" class=\"btn btn-xs btn-danger ms-auto\" ng-click=\"$validation.apiValidation=$ctrl.getValidation(calc);$validation.showDetails()\" sxy-text=\"SALAXY.UI_Terms.readMore\" ps=\"...\"></button>\r\n          </div>\r\n          <div class=\"row worker-calculations-row\">\r\n            <div class=\"col-12 table-responsive\">\r\n              <salaxy-calc-rows-2019-editor parent=\"calc\" title=\"{{'SALAXY.NG1.PayrollComponent.payrollCalcs.calcRowEditor.title' | sxyTranslate}}\" mode=\"{{$ctrl.isReadOnly ? 'read-only' : 'read-edit'}}\" show-edit-buttons=\"true\" on-commit=\"$ctrl.commitCalc(calc)\" on-reset=\"$ctrl.resetCalc(calc)\"\r\n                on-start-edit=\"$ctrl.getUi(calc).isInEdit = true\" is-in-edit=\"$ctrl.getUi(calc).isInEdit\" show-gross-totals=\"true\">\r\n              </salaxy-calc-rows-2019-editor>\r\n\r\n            </div>\r\n            <div class=\"col-12 payroll-calculation-footer\">\r\n              <div class=\"btn-group btn-group-sm dropup\" ng-if=\"!$ctrl.isReadOnly\">\r\n                <button type=\"button\" class=\"btn btn-secondary dropdown-toggle\"  data-bs-toggle=\"dropdown\" aria-expanded=\"false\">\r\n                  <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.edit\"></span>\r\n                </button>\r\n                <ul class=\"dropdown-menu\">\r\n                  <ng-include src=\"'salaxy-components/calc/payroll/PayrollCalcs_edit_dropdown.html'\"></ng-include>\r\n                </ul>\r\n              </div>\r\n              <div ng-if=\"$ctrl.mode != 'service'\" class=\"btn-group btn-group-sm float-start float-sm-end dropup\">\r\n                <button id=\"reports\" type=\"button\" class=\"btn btn-transparent dropdown-toggle\" data-bs-toggle=\"dropdown\" aria-expanded=\"false\">\r\n                  <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.viewReports\"></span>\r\n                </button>\r\n                <ul class=\"dropdown-menu dropdown-menu-end\"  role=\"menu\" aria-labelledby=\"reports\">\r\n                  <li role=\"menuitem\">\r\n                    <a href=\"\" ng-click=\"$ctrl.showReport('employerReport', calc)\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.employerReport\"></a>\r\n                  </li>\r\n                  <li role=\"menuitem\">\r\n                    <a href=\"\" ng-click=\"$ctrl.showReport('paymentReport', calc)\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.paymentReport\"></a>\r\n                  </li>\r\n                  <li role=\"menuitem\">\r\n                    <a href=\"\" ng-click=\"$ctrl.showReport('salarySlip', calc)\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.salarySlip\"></a>\r\n                  </li>\r\n                </ul>\r\n              </div>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div ng-if=\"$ctrl.hasCalculations\">\r\n      <div class=\"payroll-totals col-padding\">\r\n        <div class=\"totals-container\">\r\n          <span class=\"total-label\"><span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.payrollTotals.finalCost\"></span><br>\r\n          <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.payrollTotals.grossSalary\"></span><br>\r\n          <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.payrollTotals.totalPayment\"></span>\r\n          </span>\r\n          <span class=\"amount\">\r\n            {{ $ctrl.calcsResult.employerCalc.finalCost | currency }}<br>\r\n            {{ $ctrl.info.totalGrossSalary | currency}}<br>\r\n            {{ $ctrl.info.totalPayment | currency}}\r\n          </span>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"dropup toolbar-bottom\" ng-if=\"$ctrl.hasCalculations\">\r\n      <ng-include src=\"'salaxy-components/calc/payroll/PayrollCalcs_toolbar.html'\"></ng-include>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/payroll/PayrollCalcs_edit_dropdown.html\",`<li class=\"dropdown-header\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.editCalculation\"></li>\r\n<li role=\"menuitem\" ng-class=\"{ 'disabled': $ctrl.getUi(calc).isInEdit }\">\r\n  <a href=\"\" ng-click=\"$ctrl.setRowsEditable(calc)\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.editRows\"></a>\r\n</li>\r\n<li ng-if=\"$ctrl.mode != 'service'\" role=\"menuitem\">\r\n  <a href=\"\" ng-click=\"$ctrl.showEditCalcDialog(calc)\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.openCalculator\"></a>\r\n</li>\r\n<li ng-if=\"$ctrl.mode != 'service'\" role=\"menuitem\">\r\n  <a href=\"\" ng-click=\"$ctrl.showEditCalcDialog(calc, 'ir')\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.openIrRows\"></a>\r\n</li>\r\n<li role=\"menuitem\">\r\n  <a href=\"\" ng-click=\"$ctrl.commitCalc(calc, false, true)\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.save\"></a>\r\n</li>\r\n<li role=\"menuitem\" ng-class=\"{ 'disabled': !$ctrl.hasCalcChanges(calc) && !$ctrl.getUi(calc).isInEdit }\">\r\n  <a href=\"\" ng-click=\"$ctrl.resetCalc(calc)\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.cancel\"></a>\r\n</li>\r\n<li role=\"separator\" class=\"divider\"></li>\r\n<li class=\"dropdown-header\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.rowsEmployment\"></li>\r\n<li role=\"menuitem\">\r\n  <a href=\"\" ng-click=\"$ctrl.importEmploymentData(calc)\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.import\"></a>\r\n</li>\r\n<li role=\"separator\" class=\"divider\"></li>\r\n<li role=\"menuitem\">\r\n  <a href=\"\" ng-click=\"$ctrl.deleteCalc(calc)\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.delete\"></a>\r\n</li>\r\n<li role=\"menuitem\" ng-if=\"$ctrl.mode != 'service'\">\r\n  <a href=\"\" ng-click=\"$ctrl.deleteCalc(calc, true)\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.unlink\"></a>\r\n</li>`);\n\n $templateCache.put(\"salaxy-components/calc/payroll/PayrollCalcs_toolbar.html\",`<div class=\"btn-toolbar\" role=\"toolbar\" aria-label=\"Payroll actions\">\r\n  \r\n\r\n  <div class=\"btn-group dropdown\" ng-if=\"!$ctrl.isReadOnly && $ctrl.mode != 'service'\">\r\n    <button type=\"button\" class=\"btn btn-sm btn-labeled-left btn-primary dropdown-toggle d-flex align-items-center\" data-bs-toggle=\"dropdown\" aria-haspopup=\"true\" aria-expanded=\"false\">\r\n      <i class=\"bi bi-plus-lg h-100\"></i>\r\n      <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.addCalculation\"></span>\r\n    </button>\r\n    <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"addcalculation\">\r\n      <li role=\"menuitem\">\r\n        <a ng-click=\"$ctrl.createNewCalc()\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.addWorker\"></a>\r\n      </li>\r\n      <li role=\"menuitem\">\r\n        <a ng-click=\"$ctrl.addExistingCalc('draft')\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.addDraft\"></a>\r\n      </li>\r\n      <li role=\"menuitem\">\r\n        <a ng-click=\"$ctrl.addExistingCalc('paid')\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.addCopy\"></a>\r\n      </li>\r\n      <li role=\"menuitem\">\r\n        <a ng-click=\"$ctrl.mergePayroll(true)\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.addPayroll\"></a>\r\n      </li>\r\n    </ul>\r\n  </div>\r\n  <input type=\"text\" class=\"form-control input-sm payroll-search-input mx-1\"  id=\"searchText\" name=\"searchText\" placeholder=\"{{'SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.searchByName' | sxyTranslate}}\" ng-model=\"$ctrl.searchByName\" />\r\n \r\n  <button ng-if=\"!$ctrl.isReadOnly && $ctrl.mode == 'service'\" type=\"button\" class=\"btn btn-sm btn-labeled-right btn-primary\" ng-click=\"$ctrl.createNewCalc()\">\r\n    <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.addCalculation\"></span>\r\n    <i class=\"bi bi-plus-lg\"></i>\r\n  </button>\r\n  <div class=\"btn-group btn-group-sm toggle-all-buttons ms-auto\">\r\n    <button ng-if=\"!$ctrl.isReadOnly && !('disableHolidays' | sxyIsInRole)\" class=\"btn btn-secondary toggle-all text-end\" ng-click=\"$ctrl.recalculateWorktimes()\">\r\n      <span class=\"d-none d-sm-inline\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.saveWorktime\"></span>\r\n      <i class=\"bi bi-arrow-repeat\" title=\"{{'SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.saveWorktime' | sxyTranslate}}\"></i>\r\n    </button>\r\n    <button class=\"btn btn-secondary  toggle-all text-end\" ng-click=\"$ctrl.setUiForAll('isCollapsed', false)\">\r\n      <span class=\"d-none d-sm-inline\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.open\"></span>\r\n      <i class=\"bi bi-chevron-down\" title=\"{{'SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.open' | sxyTranslate}}\"></i>\r\n    </button>\r\n    <button class=\"btn btn-secondary  toggle-all text-end\" ng-if=\"!$ctrl.isReadOnly\" ng-click=\"$ctrl.setRowsEditable('all')\">\r\n      <span class=\"d-none d-sm-inline\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.edit\"></span>\r\n      <i class=\"bi bi-pencil-fill\" title=\"{{'SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.edit' | sxyTranslate}}\"></i>\r\n    </button>\r\n    <button class=\"btn btn-secondary toggle-all text-end\" ng-click=\"$ctrl.commitAllCalcs()\" ng-if=\"$ctrl.changedCalcCount && !$ctrl.isReadOnly\">\r\n      <span class=\"d-none d-sm-inline\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.save\"></span> ({{ $ctrl.changedCalcCountCache }}) \r\n      <i class=\"bi bi-floppy text-success\" title=\"{{'SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.save' | sxyTranslate}}\"></i>\r\n    </button>\r\n    <button class=\"btn btn-secondary toggle-all text-end\" ng-click=\"$ctrl.resetAllCalcs()\" ng-if=\"$ctrl.changedCalcCountCache && !$ctrl.isReadOnly\">\r\n      <span class=\"d-none d-sm-inline\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.cancel\"></span> ({{ $ctrl.changedCalcCountCache }}) <i\r\n        class=\"bi bi-x-lg text-danger\" title=\"{{'SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.cancel' | sxyTranslate}}\"></i>\r\n    </button>\r\n    <button class=\"btn btn-secondary  toggle-all text-end\" ng-click=\"$ctrl.setUiForAll('isCollapsed', true);$ctrl.setUiForAll('isInEdit', false)\" ng-if=\"!$ctrl.changedCalcCountCache\">\r\n      <span class=\"d-none d-sm-inline\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.close\"></span>\r\n      <i class=\"bi bi-chevron-up\" title=\"{{'SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.close' | sxyTranslate}}\"></i>\r\n    </button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/payroll/PayrollEdit.html\",`<div class=\"salaxy-component salaxy-payroll\" ng-controller=\"NaviController as $naviCtrl\">\r\n  <salaxy-spinner ng-if=\"$ctrl.isLoading\"></salaxy-spinner>\r\n  <div sxy-if-role=\"auth\">\r\n    <div class=\"dropdown\">\r\n      <ng-include ng-if=\"$ctrl.isNew()\" src=\"'salaxy-components/calc/payroll/PayrollNew.html'\"></ng-include>\r\n    </div>\r\n    <div ng-if=\"!$ctrl.isNew() && $ctrl.current\">\r\n      <ng-include src=\"'salaxy-components/calc/payroll/PayrollEdit_toolbar.html'\"></ng-include>\r\n      <div class=\"row payroll-info-row\">\r\n        <div class=\"col-3 col-sm-2\">\r\n          <salaxy-avatar-placeholder class=\"payroll-avatar\">\r\n            <i class=\"salaxy-avatar bi bi-square-fill text-muted d-flex\" ng-class=\"{'draft-invalid' : $ctrl.current.info.status == 'draft' && !$ctrl.current.info.isReadyForPayment, 'text-success' : $ctrl.current.info.status == 'paymentSucceeded', 'text-warning' : ($ctrl.current.info.status == 'paymentStarted' || $ctrl.current.info.status == 'waitingApproval') , 'text-danger' : $ctrl.current.info.status == 'paymentCancelled'}\">\r\n              <div class=\"avatar-text-wrapper\">\r\n                <strong>{{ $ctrl.calcs.length }}</strong>\r\n                <small>{{ $ctrl.current.info.salaryDate | date : \"d.M.\" }}</small>\r\n              </div>\r\n            </i>\r\n          </salaxy-avatar-placeholder>\r\n        </div>\r\n        <div class=\"col-9 col-sm-10 payroll-info-col\">\r\n          <h3 class=\"payroll-title\">{{ $ctrl.current.input.title }}</h3>\r\n          <div class=\"row\">\r\n            <div class=\"col-12 col-sm-6\">\r\n              <div>\r\n                <span>{{ 'PayrollStatus.' + $ctrl.current.info.status | sxyEnum }}</span>\r\n                <span ng-if=\"$ctrl.current.info.status == 'draft'\" ng-class=\"$ctrl.current.info.isReadyForPayment ? 'text-success' : 'text-danger'\">\r\n                  {{ $ctrl.current.info.isReadyForPayment ? (('SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.readyForPayment' | sxyTranslate)) :\r\n                  (('SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.notReadyForPayment' | sxyTranslate)) }}\r\n                </span>\r\n              </div>\r\n              <div>\r\n                <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.salaryPeriod\" ps=\":\"></span> {{ $ctrl.current.input.period | sxyDateRange }} ({{$ctrl.current.input.period.daysCount}} <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.salaryPeriodDaysCount\"></span>)\r\n              </div>\r\n              <div>\r\n                <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.salaryDate\" ps=\":\"></span> {{ $ctrl.current.info.salaryDate | date }}\r\n                <span class=\"badge bg-info\" ng-if=\"$ctrl.current.info.status != 'paymentSucceeded' && !$ctrl.current.input.salaryDate && $ctrl.current.info.salaryDate\">{{'SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.salaryDateEstimate' | sxyTranslate}}</span>\r\n                <span ng-if=\"$ctrl.current.info.status != 'paymentSucceeded' &&  $ctrl.current.info.salaryDate && $ctrl.current.input.salaryDate && $ctrl.current.input.salaryDate != $ctrl.current.info.salaryDate\"><s>{{ $ctrl.current.input.salaryDate | date }}</s> <span class=\"badge bg-warning\">{{'SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.salaryDateNote' | sxyTranslate}}</span></span>\r\n              </div>\r\n              <div>\r\n                <span ng-if=\"$ctrl.current.input.template\" sxy-html=\"SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.template.html\" params=\"{template: ($ctrl.current.input.template)}\"></span>\r\n              </div>\r\n              <div>\r\n                <small>ID: <code>{{ $ctrl.currentId }}</code></small>\r\n              </div>\r\n            </div>\r\n            <div class=\"col-12 col-sm-6\">\r\n              <span><span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.calcCount\" ps=\":\"></span> {{$ctrl.calcs.length}} </span><br />\r\n              <span><span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.finalCost\" ps=\":\"></span> {{ $ctrl.calcsResult.employerCalc.finalCost | currency }}\r\n              </span><br />\r\n              <span><span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.grossSalary\" ps=\":\"></span> {{ $ctrl.info.totalGrossSalary | currency}}</span><br>\r\n              <span><span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.totalPayment\" ps=\":\"></span> {{ $ctrl.info.totalPayment | currency}}</span>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <salaxy-tab-buttons\r\n        current-tab=\"$ctrl.currentTab\"\r\n        options=\"[\r\n          { value: 'properties', text: 'SALAXY.NG1.PayrollComponent.payrollEdit.tabs.editProperties' },\r\n          { value: 'calculations', text: 'SALAXY.NG1.PayrollComponent.payrollEdit.tabs.calculations' },\r\n          { value: 'reports', text: 'SALAXY.NG1.PayrollComponent.payrollEdit.tabs.reports', disabled: !$ctrl.hasCalculations },\r\n          { value: 'additionalinformation', text: 'SALAXY.NG1.PayrollComponent.payrollCalcs.additionalInformation', disabled: !$ctrl.hasCalculations },\r\n          { value: 'msg', text: 'Viestit / hyväksyntä', hidden: !('partnerMessaging' | sxyIsInRole) }\r\n        ]\"\r\n        tabs-id=\"payrollEdit\">\r\n      </salaxy-tab-buttons>\r\n      <div class=\"tab-content\" id=\"tab-content-payrollEdit\">\r\n        <div class=\"tab-pane\" id=\"properties-tab\">\r\n          <div ng-if=\"$ctrl.currentTab == 'properties'\" class=\"row payroll-edit-properties-container\">\r\n            <form class=\"form-horizontal\" ng-disabled=\"$ctrl.isDisabled\" ng-readonly=\"$ctrl.isReadOnly\">\r\n              <div class=\"col-12 payroll-edit-properties-col\">\r\n                <salaxy-input name=\"title\" label=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.title\" ng-model=\"$ctrl.current.input.title\"></salaxy-input>\r\n                <div class=\"form-group\" ng-if=\"$ctrl.current.info.status == 'paymentSucceeded'\">\r\n                  <label for=\"status\" class=\"col-sm-4 text-start\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.status\"></label>\r\n                  <div class=\"col-sm-8\">{{ 'PayrollStatus.' + $ctrl.current.info.status | sxyEnum | sxyTranslate }}</div>\r\n                </div>\r\n                 <div  ng-if=\"(!$ctrl.isReadOnly || $ctrl.showAction('pay')) && ('test,setSalaryDateKind' | sxyIsInRole)\"  ng-switch=\"$ctrl.current.input.paymentChannel\">\r\n                  <div ng-switch-when=\"palkkausManual|talenomManual|palkkausInvoices|palkkausCfaTest|kitsas|briox|askelma|passeliMerit|ecom|hausvise\" ng-switch-when-separator=\"|\">\r\n                    <salaxy-form-group name=\"salaryDateKind\" label=\"SALAXY.MODEL.PayrollInput.salaryDateKind.title\">       \r\n                      <salaxy-salary-date-kind-button button-class=\"btn-block\" model=\"$ctrl.current\" on-salary-date-kind-change=\"$ctrl.save()\"></salaxy-salary-date-kind-button>\r\n                    </salaxy-form-group>\r\n                  </div>\r\n                </div>\r\n                <salaxy-form-group ng-if=\"($ctrl.isReadOnly && !$ctrl.showAction('pay')) && $ctrl.current.input.salaryDateKind == 'inPast'\" name=\"salaryDateKind\" class=\"salaxy-component salaxy-read-only\" label=\"SALAXY.MODEL.CalcWorkflow.salaryDateKind.title\">\r\n                  <div class=\"form-control-plaintext\">{{\"SALAXY.ENUM.SalaryDateKind.\" + ($ctrl.current.input.salaryDateKind) + \".label\" | sxyTranslate  }}</div>\r\n                </salaxy-form-group>\r\n                <salaxy-datepicker-popup read-only=\"false\" ng-if=\"!$ctrl.isReadOnly || $ctrl.showAction('pay')\" label=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.salaryDate\" name=\"salaryDate\" ng-model=\"$ctrl.current.input.salaryDate\" date-disabled=\"disable-function\" disable-function=\"$ctrl.isDisabledSalaryDate\" update-disabled-dates=\"($ctrl.current.input.salaryDateKind || '-') + '|' + ($ctrl.current.input.paymentChannel || '-')\"></salaxy-datepicker-popup>       \r\n                <div class=\"row py-2\" ng-if=\"$ctrl.isReadOnly && !$ctrl.showAction('pay')\">\r\n                  <div class=\"col-sm-4\"><strong sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.salaryDate\" ps=\":\"></strong> </div>\r\n                  <div class=\"col-sm-8\">\r\n                    {{ $ctrl.current.info.salaryDate | date }}\r\n                    <span class=\"badge bg-info\" ng-if=\"$ctrl.current.info.status != 'paymentSucceeded' && !$ctrl.current.input.salaryDate && $ctrl.current.info.salaryDate\">{{'SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.salaryDateEstimate' | sxyTranslate}}</span>\r\n                    <span ng-if=\"$ctrl.current.info.status != 'paymentSucceeded' &&  $ctrl.current.info.salaryDate && $ctrl.current.input.salaryDate && $ctrl.current.input.salaryDate != $ctrl.current.info.salaryDate\"><s>{{ $ctrl.current.input.salaryDate | date }}</s> <span class=\"badge bg-warning\">{{'SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.salaryDateNote' | sxyTranslate}}</span></span>    \r\n                  </div>\r\n                </div>\r\n                <div class=\"form-group row\">\r\n                  <div class=\"col-sm-4\"><strong sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.salaryPeriod\" ps=\":\"></strong> </div>\r\n                  <div class=\"col-sm-8\">\r\n                    {{ $ctrl.current.input.period | sxyDateRange }} ({{$ctrl.current.input.period.daysCount}} <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.salaryPeriodDaysCount\"></span>)\r\n                    <button class=\"btn btn-transparent btn-xs\" ng-click=\"$ctrl.showDateRange()\" ng-if=\"!$ctrl.isReadOnly || $ctrl.showAction('pay')\"><i class=\"bi bi-pencil-fill \"></i></button>\r\n                  </div>\r\n                </div>\r\n                <salaxy-form-group name=\"paymentChannel\" label=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.paymentChannel\">\r\n                  <salaxy-pay-button ng-if=\"!$ctrl.isReadOnly || $ctrl.showAction('pay')\" model=\"$ctrl.current\" mode=\"channel-select\" ng-ref=\"$ctrl.$payButton\" disabled=\"!$ctrl.$payButton.isChannelDefined\" on-payment-channel-change=\"$ctrl.save()\" button-class=\"btn-block\"></salaxy-pay-button>\r\n                  <div ng-if=\"$ctrl.isReadOnly && !$ctrl.showAction('pay')\">{{ \"PaymentChannel.\" + $ctrl.current.input.paymentChannel | sxyEnum }}</div>\r\n                </salaxy-form-group>\r\n              </div>\r\n            </form>\r\n          </div>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"calculations-tab\">\r\n          <ng-include ng-if=\"$ctrl.currentTab == 'calculations'\" src=\"'salaxy-components/calc/payroll/PayrollCalcs.html'\"></ng-include>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"reports-tab\">\r\n          <salaxy-calc-reports calcs=\"$ctrl.calcs\" ng-if=\"$ctrl.currentTab == 'reports' && $ctrl.hasCalculations\" report-type=\"'salarySlip'\"></salaxy-calc-reports>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"additionalinformation-tab\">\r\n          <div class=\"dropdown toolbar-top\" ng-if=\"$ctrl.currentTab == 'additionalinformation' && $ctrl.hasCalculations\">\r\n            <ng-include src=\"'salaxy-components/calc/payroll/PayrollCalcs_toolbar.html'\"></ng-include>\r\n            <div ng-repeat=\"calc in $ctrl.calcs\">\r\n              <div class=\"payroll-single-calculation \" ng-class=\"{'error-container': !$ctrl.getValidation(calc).isValid }\">\r\n                <div class=\"float-end icon-container btn-group\">\r\n                  <button class=\"btn btn-transparent btn-xs toggle-details\" ng-click=\"$ctrl.getUi(calc).isCollapsed = !$ctrl.getUi(calc).isCollapsed\"><i class=\"bi\"\r\n                      ng-class=\"{'bi-chevron-up' : !$ctrl.getUi(calc).isCollapsed,  'bi-chevron-down' : $ctrl.getUi(calc).isCollapsed}\"\r\n                      title=\"{{'SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.toggle' | sxyTranslate}}\"></i></button>\r\n                </div>\r\n                <div class=\"payroll-worker-summary px-2-g clickable\" ng-if=\"$ctrl.getUi(calc).isCollapsed\" ng-click=\"$ctrl.getUi(calc).isCollapsed = !$ctrl.getUi(calc).isCollapsed\">\r\n                  <div class=\"avatar-container\">\r\n                    <salaxy-avatar avatar=\"calc.worker.avatar\"></salaxy-avatar>\r\n                    <span class=\"worker-name\">{{calc.worker.avatar.displayName}}</span>\r\n                    <span class=\"calculation-summary\">{{calc.result.totals.total | currency }}</span>\r\n                  </div>\r\n                </div>\r\n                <div class=\"payroll-worker-details\" ng-if=\"!$ctrl.getUi(calc).isCollapsed\">\r\n                  <div class=\"row payroll-worker-info\">\r\n                    <div class=\"col-2 col-sm-2\">\r\n                      <div class=\"avatar-container\">\r\n                        <salaxy-avatar avatar=\"calc.worker.avatar\"></salaxy-avatar>\r\n                      </div>\r\n                    </div>\r\n                    <div class=\"col-10\">\r\n                      <h3 class=\"worker-name clickable\" ng-click=\"$ctrl.getUi(calc).isCollapsed = !$ctrl.getUi(calc).isCollapsed\">{{calc.worker.avatar.displayName}}</h3>\r\n                      <div class=\"row\">\r\n                        <div class=\"col-12 col-sm-5 worker-info-col\">\r\n                          {{calc.worker.paymentData.email}}<br> {{calc.worker.paymentData.telephone}}\r\n                        </div>\r\n                        <div class=\"col-12 col-sm-7 worker-info-col\">\r\n                          <!-- additional info -->\r\n                        </div>\r\n                      </div>\r\n                    </div>\r\n                  </div>\r\n                  <div class=\"row worker-calculations-row\">\r\n                    <div class=\"col-sm-6\">\r\n                      <salaxy-calc-cost-accounting salaxy-if-role=\"company\" calc=\"calc\" read-only=\"$ctrl.isReadOnly\"></salaxy-calc-cost-accounting>\r\n                    </div>\r\n                  </div>\r\n                </div>\r\n              </div>\r\n            </div>\r\n          </div>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"msg-tab\" ng-if=\"'partnerMessaging' | sxyIsInRole\">\r\n          <div ng-if=\"!$ctrl.current.info.messageThreadId\" ng-controller=\"MessageThreadCrudController as $msg\" ng-init=\"$msg.model='new'\" class=\"form-horizontal\" style=\"max-width: 600px;\">\r\n            <fieldset sxy-if-role=\"!pro\">\r\n              <p ng-if=\"!$ctrl.current.info.messageThreadId\">Tähän palkkalistaan ei liity viestiketjua / työnkulkua.</p>\r\n              <!--\r\n              <legend>Lähetä tilitoimistolle</legend>\r\n              <p>Luo tästä uusi viestiketju, jolla voit lähettää palkkalistan tilitoimiston käsittelyyn.</p>\r\n              <salaxy-input-enum name=\"action\" label=\"Pyydetään toimintaa\" type=\"radio\" ng-model=\"$msg.current.input.todoAction\" options=\"$ctrl.messageActions\"\r\n                ng-change=\"$msg.current.title = $ctrl.getTitle($msg.current.input.todoAction)\"></salaxy-input-enum>\r\n              <salaxy-input name=\"title\" label=\"SALAXY.NG1.MessageThreadComponent.title\" require=\"true\" disabled=\"!$msg.current.input.todoAction\" ng-model=\"$msg.current.title\"></salaxy-input>\r\n              <salaxy-form-group name=\"msgSubmit\" label-type=\"empty-label\">\r\n                <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.sendPayroll($msg)\">Lähetä</button>\r\n              </salaxy-form-group>\r\n              -->\r\n            </fieldset>\r\n            <fieldset sxy-if-role=\"pro\">\r\n              <legend>Lähetä yritykselle</legend>\r\n              <p>Luo tästä uusi viestiketju, jolla voit lähettää palkkalistan yritykselle hyväksyttäväksi / maksettavaksi.</p>\r\n              <salaxy-input-enum name=\"action\" label=\"Pyydetään toimintaa\" type=\"radio\" ng-model=\"$msg.current.input.todoAction\" options=\"$ctrl.messageActions\" ng-change=\"$msg.current.title = $ctrl.getTitle($msg.current.input.todoAction)\"></salaxy-input-enum>\r\n              <salaxy-input name=\"title\" label=\"SALAXY.NG1.MessageThreadComponent.title\" require=\"true\" disabled=\"!$msg.current.input.todoAction\" ng-model=\"$msg.current.title\"></salaxy-input>\r\n              <salaxy-form-group name=\"msgSubmit\" label-type=\"empty-label\">\r\n                <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.sendPayroll($msg)\">Lähetä</button>\r\n              </salaxy-form-group>\r\n            </fieldset>\r\n          </div>\r\n          <div ng-if=\"$ctrl.current.info.messageThreadId\">\r\n            <button type=\"button\" class=\"btn btn-danger float-end\" ng-click=\"$ctrl.deleteMessage($ctrl.$msg)\"><i class=\"bi bi-trash-fill\" aria-hidden=\"true\"></i></button>\r\n            <salaxy-message-thread model=\"$ctrl.current.info.messageThreadId\" ng-ref=\"$ctrl.$msg\" role=\"{{('pro' | sxyIsInRole) ? 'otherParty' : 'owner' }}\" other-party=\"'partner'\" mark-as-read=\"5\"></salaxy-message-thread>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div class=\"dropup\">\r\n        <ng-include src=\"'salaxy-components/calc/payroll/PayrollEdit_toolbar.html'\"></ng-include>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/payroll/PayrollEdit_toolbar.html\",`<div>\r\n  <div ng-if=\"$ctrl.isReadOnly\" class=\"btn-toolbar w-100\">\r\n    <button ng-if=\"$ctrl.showAction('pay')\" type=\"button\" class=\"btn\" ng-class=\"{ 'btn-primary': $ctrl.hasChanges, 'btn-default': !$ctrl.hasChanges }\" ng-disabled=\"!$ctrl.hasChanges\" ng-click=\"$ctrl.save()\">\r\n      {{ $ctrl.hasChanges ? ('SALAXY.NG1.PayrollComponent.payrollEdit.toolbar.save' | sxyTranslate) : ('SALAXY.NG1.PayrollComponent.payrollEdit.toolbar.saved' | sxyTranslate) }}\r\n    </button>\r\n    <button class=\"btn btn-secondary\" ng-if=\"$ctrl.showAction('copy')\" ng-click=\"$ctrl.showCopyAsNew($ctrl.current)\" ng-style=\"{ visibility: $ctrl.isDisabled ? 'hidden' : 'visible' }\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.toolbar.copyAsNew\"></button>\r\n    <div class=\"ms-sm-auto\" >\r\n      <salaxy-pay-button ng-if=\"$ctrl.showAction('pay')\"\r\n        model=\"$ctrl.current\" mode=\"pay-button\" label=\"SALAXY.NG1.PayrollComponent.payrollPayButton\" ng-ref=\"$payButton\" disabled=\"!$ctrl.current.info.isReadyForPayment || !$ctrl.calcs.length || !$payButton.isChannelDefined\"\r\n        on-payment-channel-change=\"$ctrl.save()\"></salaxy-pay-button>\r\n        <button ng-if=\"$ctrl.showAction('cancel') && ($ctrl.current.info.status == 'paymentStarted' && ($ctrl.current.input.paymentChannel == 'palkkausManual' || $ctrl.current.input.paymentChannel == 'talenomManual' || $ctrl.current.input.paymentChannel == 'palkkausInvoices' || $ctrl.current.input.paymentChannel == 'kitsas' || $ctrl.current.input.paymentChannel == 'palkkausPersonal' || $ctrl.current.input.paymentChannel == 'palkkausCfaPaytrail' || $ctrl.current.input.paymentChannel == 'palkkausEcfaPaytrail' || $ctrl.current.input.paymentChannel == 'palkkausCfaReference'|| $ctrl.current.input.paymentChannel == 'palkkausEcfaReference' || $ctrl.current.input.paymentChannel == 'palkkausCfaFinvoice' || $ctrl.current.input.paymentChannel == 'palkkausEcfaFinvoice' ||  $ctrl.current.input.paymentChannel == 'palkkausCfaTest'))\" class=\"btn btn-secondary  btn-labeled-right\" ng-click=\"$ctrl.cancel()\"><span sxy-text=\"SALAXY.NG1.CalcResultsComponent.cancelPaymentOrChangeChannelBtn\"></span><i class=\"bi bi-x-circle\"></i></button>\r\n        <button ng-if=\"$ctrl.current.info.status != 'waitingApproval' && $ctrl.current.info.status != 'draft'\" class=\"btn btn-secondary  btn-labeled-right\" ng-click=\"$ctrl.showPaymentDialog()\"><span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.toolbar.showPaymentInfo\"></span><i class=\"bi bi-info-circle\"></i></button>\r\n    </div>\r\n    <button type=\"button\" ng-if=\"('partnerMessaging' | sxyIsInRole) && (!('pro' | sxyIsInRole) && $ctrl.current.info.messageThreadId )\"  class=\"btn btn-default float-end\" ng-click=\"$ctrl.activeTab = 'msg'\">Kommentoi</button>\r\n  </div>\r\n  <div ng-if=\"!$ctrl.isReadOnly\" class=\"btn-toolbar calc-toolbar w-100\">\r\n    <button type=\"button\" class=\"btn\" ng-class=\"{ 'btn-primary': $ctrl.hasChanges, 'btn-default': !$ctrl.hasChanges }\" ng-disabled=\"!$ctrl.hasChanges\" ng-click=\"$ctrl.save()\">\r\n      {{ $ctrl.hasChanges ? ('SALAXY.NG1.PayrollComponent.payrollEdit.toolbar.save' | sxyTranslate) : ('SALAXY.NG1.PayrollComponent.payrollEdit.toolbar.saved' | sxyTranslate) }}\r\n    </button>\r\n    <div class=\"btn-group dropdown\"  ng-disabled=\"$ctrl.isDisabled\">\r\n      <button type=\"button\" class=\"btn btn-secondary dropdown-toggle\" data-bs-toggle=\"dropdown\" aria-expanded=\"false\">\r\n        <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.toolbar.options\"></span>\r\n      </button>\r\n      <ul class=\"dropdown-menu\"  role=\"menu\" aria-labelledby=\"actions\">\r\n        <li role=\"menuitem\">\r\n          <a ng-click=\"$ctrl.importEmploymentDataAll()\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.toolbar.importEmploymentCalc\"></a>\r\n        </li>\r\n        <li role=\"menuitem\">\r\n          <a ng-click=\"$ctrl.showCopyAsNew($ctrl.current)\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.toolbar.copyAsNew\"></a>\r\n        </li>\r\n        <li ng-class=\"{ disabled: !$ctrl.hasChanges }\" role=\"menuitem\">\r\n          <a ng-click=\"$ctrl.reset()\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.toolbar.cancel\"></a>\r\n        </li>\r\n        <li role=\"menuitem\">\r\n          <a class=\"text-danger dropdown-item\" ng-click=\"$ctrl.delete()\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.toolbar.delete\"></a>\r\n        </li>\r\n        <li role=\"menuitem\" ng-if=\"( $ctrl.current.owner == 'FI90PRYL0001975846') && ('pro, test' | sxyIsInRole)\">\r\n          <a ng-href=\"#/payroll/import/{{$ctrl.current.id}}\" class=\"dropdown-item\">Import (BETA)</a>\r\n        </li>\r\n      </ul>\r\n    </div>\r\n    <div sxy-if-role=\"pro\" class=\"btn-group\">\r\n      <div class=\"btn-group dropdown ms-1\">\r\n        <!-- HACK: Rewrite workflow buttons as components. Or make PRO calculator a component. -->\r\n        <button class=\"btn btn-default dropdown-toggle\" type=\"button\" data-bs-toggle=\"dropdown\" aria-expanded=\"false\" style=\"font-weight: bold;\">\r\n          {{ \"PayrollStatus.\" + $ctrl.current.info.status | sxyEnum }}\r\n        </button>\r\n        <ul class=\"dropdown-menu\" >\r\n          <li ng-class=\"{ disabled: $ctrl.current.info.status=='draft' }\">\r\n            <a href=\"\" ng-click=\"$ctrl.current.info.status = 'draft';$ctrl.save()\" class=\"dropdown-item\">{{ \"PayrollStatus.draft\" | sxyEnum }}</a>\r\n          </li>\r\n          <li ng-class=\"{ disabled: $ctrl.current.info.status=='template' }\">\r\n            <a href=\"\" ng-click=\"$ctrl.current.info.status = 'template';$ctrl.save()\" class=\"dropdown-item\">{{ \"PayrollStatus.template\" | sxyEnum }}</a>\r\n          </li>\r\n          <li ng-class=\"{ disabled: $ctrl.current.info.status=='handled' }\">\r\n            <a href=\"\" ng-click=\"$ctrl.current.info.status = 'handled';$ctrl.save()\" class=\"dropdown-item\">{{ \"PayrollStatus.handled\" | sxyEnum }}</a>\r\n          </li>\r\n          <li ng-class=\"{ disabled: $ctrl.current.info.status=='waitingApproval' }\">\r\n            <a href=\"\" ng-click=\"$ctrl.current.info.status = 'waitingApproval';$ctrl.save()\" class=\"dropdown-item\">{{ \"PayrollStatus.waitingApproval\" | sxyEnum }}</a>\r\n          </li>\r\n        </ul>\r\n      </div>\r\n      <salaxy-workflow-buttons api-ctrl=\"$ctrl\"></salaxy-workflow-buttons>\r\n    </div>\r\n    <div class=\"btn-group ms-sm-auto\">\r\n      <salaxy-pay-button ng-if=\"$ctrl.current.info.status != 'template'\" model=\"$ctrl.current\" mode=\"pay-button\"  label=\"SALAXY.NG1.PayrollComponent.payrollPayButton\" ng-ref=\"$payButton\" disabled=\"!$ctrl.current.info.isReadyForPayment || !$ctrl.calcs.length || !$payButton.isChannelDefined\"\r\n        on-payment-channel-change=\"$ctrl.save()\"></salaxy-pay-button>\r\n    </div>\r\n  </div>\r\n</div>\r\n<div>\r\n  <div ng-if=\"'company' | sxyIsInRole\" ng-controller=\"CompanyAccountController as $company\" style=\"padding: 8px\">\r\n    <salaxy-workflow-badge ng-if=\"$company.current\" model=\"$company.current\" mode=\"horizontal\" api-ctrl=\"$company\" wf-types=\"'EmployerMessageRecord'\" ></salaxy-workflow-badge>\r\n  </div>\r\n</div>\r\n<div class=\"row\" ng-if=\"$ctrl.showWorkflowMessage\" style=\"margin-top: 4px;margin-bottom: -50px\">\r\n  <div class=\"offset-sm-6 col-sm-6\">\r\n    <salaxy-textarea name=\"workflowMessage\" ng-model=\"$ctrl.workflowMessage\" placeholder=\"{{'SALAXY.NG1.PayrollComponent.payrollEdit.toolbar.workFlowMessage'}}\" rows=\"2\" label-type=\"plain\"></salaxy-textarea>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/payroll/PayrollList.html\",`<div class=\"salaxy-component salaxy-payroll-list\">\r\n  <div class=\"row w-100\" ng-if=\"!$ctrl.hideButton\">\r\n    <div class=\"col-12 action-button-container mb-3\">\r\n      <salaxy-action-button action=\"'newPayroll'\" button-class=\"btn-primary\" style=\"margin-bottom:30px;\"></salaxy-action-button>\r\n    </div>\r\n  </div>\r\n  <salaxy-tab-buttons\r\n    current-tab=\"$ctrl.currentTab\"\r\n    options=\"[\r\n      { value: 'default', text: 'SALAXY.NG1.PayrollComponent.payrollList.tabs.latest' },\r\n      { value: 'templates', text: 'SALAXY.NG1.PayrollComponent.payrollList.tabs.repeated' },\r\n      { value: 'paid', text: 'SALAXY.NG1.PayrollComponent.payrollList.tabs.paid' },\r\n      { value: 'paidcalcs', text: 'SALAXY.NG1.PayrollComponent.payrollList.tabs.paidSalaries' },\r\n      { value: 'draftcalcs', text: 'SALAXY.NG1.PayrollComponent.payrollList.tabs.draftCalcs' }\r\n    ]\"\r\n    tabs-id=\"payrollList\">\r\n  </salaxy-tab-buttons>\r\n  <div class=\"tab-content\" id=\"tab-content-payrollList\">\r\n    <div class=\"tab-pane\" id=\"default-tab\">\r\n      <salaxy-odata-table crud-controller=\"PayrollCrudController as $crud\" options=\"{ $filter: 'status ne \\\\'paymentSucceeded\\\\' and status ne \\\\'paymentStarted\\\\' and status ne \\\\'template\\\\' and status ne \\\\'handled\\\\' and status ne \\\\'paymentCanceled\\\\'' }\" read-only=\"$ctrl.isReadOnlyForced\"></salaxy-odata-table>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"templates-tab\">\r\n      <salaxy-odata-table crud-controller=\"PayrollCrudController as $crud\" options=\"{ $filter: 'status eq \\\\'template\\\\'' }\" read-only=\"$ctrl.isReadOnlyForced\"></salaxy-odata-table>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"paid-tab\">\r\n      <salaxy-odata-table crud-controller=\"PayrollCrudController as $crud\" options=\"{ $filter: 'status eq \\\\'paymentSucceeded\\\\' or status eq \\\\'paymentStarted\\\\' or status eq \\\\'handled\\\\' or status eq \\\\'paymentCanceled\\\\'' }\" read-only=\"$ctrl.isReadOnlyForced\"></salaxy-odata-table>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"paidcalcs-tab\">\r\n      <salaxy-odata-table url=\"/v03/api/calculations/category/readonly\" crud-controller=\"CalculationCrudController as $crud\" options=\"{ $filter: 'status eq \\\\'paymentSucceeded\\\\' and data/payrollId ne null' }\" read-only=\"$ctrl.isReadOnlyForced\"></salaxy-odata-table>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"draftcalcs-tab\">\r\n      <salaxy-odata-table crud-controller=\"CalculationCrudController as $crud\" options=\"{ $filter: 'status eq \\\\'payrollDraft\\\\'' }\" read-only=\"$ctrl.isReadOnlyForced\"></salaxy-odata-table>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/payroll/PayrollNew.html\",`<div>\r\n  <div class=\"h2\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.new.heading\"></div>\r\n  <div class=\"form-horizontal\" ng-controller=\"NaviController as $naviCtrl\">\r\n    <form name=\"newPayrollForm\">\r\n      <salaxy-input name=\"title\" label=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.title\" require=\"true\" ng-model=\"$ctrl.current.input.title\"></salaxy-input>\r\n      <div  ng-if=\"('test,setSalaryDateKind' | sxyIsInRole)\" ng-switch=\"$ctrl.current.input.paymentChannel\">\r\n        <div ng-switch-when=\"palkkausManual|talenomManual|palkkausInvoices|palkkausCfaTest|kitsas|briox|askelma|passeliMerit|ecom|hausvise\" ng-switch-when-separator=\"|\">\r\n          <salaxy-form-group name=\"salaryDateKind\" label=\"SALAXY.MODEL.PayrollInput.salaryDateKind.title\">       \r\n            <salaxy-salary-date-kind-button button-class=\"btn-block\" model=\"$ctrl.current\" disabled=\"$ctrl.isReadOnly\"></salaxy-salary-date-kind-button>\r\n          </salaxy-form-group>\r\n        </div>\r\n      </div>\r\n      <salaxy-datepicker-popup label=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.salaryDate\" name=\"salaryDate\" ng-model=\"$ctrl.current.input.salaryDate\" update-disabled-dates=\"($ctrl.current.input.salaryDateKind || '-') + '|' + ($ctrl.current.input.paymentChannel || '-')\" date-disabled=\"disable-function\" disable-function=\"$ctrl.isDisabledSalaryDate\"></salaxy-datepicker-popup>\r\n      <salaxy-date-range label=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.salaryPeriod\" name=\"period\" ng-model=\"$ctrl.current.input.period\" mode=\"calc\"></salaxy-date-range>\r\n      <salaxy-form-group name=\"paymentChannel\" label=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.paymentChannel\">\r\n        <salaxy-pay-button model=\"$ctrl.current\" mode=\"channel-select\" ng-ref=\"$ctrl.$payButton\" disabled=\"!$ctrl.$payButton.isChannelDefined\" button-class=\"btn-block\"></salaxy-pay-button>\r\n      </salaxy-form-group>\r\n      <div ng-if=\"$ctrl.current.calcs.length\">\r\n        <salaxy-form-group label=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.new.copyingCalcs\" name=\"calcCount\">\r\n          {{ $ctrl.current.calcs.length }} kpl\r\n        </salaxy-form-group>\r\n        <salaxy-input-boolean type=\"select\" placeholder=\"SALAXY.UI_Terms.choose\" name=\"noUpdateFromEmployment\" ng-model=\"$ctrl.current.input.noUpdateFromEmployment\" label=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.new.updateCalcs\" label-false=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.new.updateCalcsFalse\"\r\n          label-true=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.new.updateCalcsTrue\"></salaxy-input-boolean>\r\n      </div>\r\n      <salaxy-form-group label-type=\"empty-label\" name=\"submit\" class=\"no-colon\">\r\n        <button type=\"submit\" class=\"btn btn-primary\" ng-disabled=\"!newPayrollForm.$valid\" ng-click=\"$ctrl.save()\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.new.createPayrollButton\"></button>\r\n      </salaxy-form-group>\r\n    </form>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/payroll/PayrollSelectList.html\",`<div class=\"salaxy-component salaxy-payroll-select-list\">\r\n  <salaxy-odata-table ng-if=\"$ctrl.category=='paid'\"  ng-if=\"$ctrl.mode == 'select'\" template-url=\"salaxy-components/odata/lists/Payrolls-select.html\"  options=\"{ $filter: 'status eq \\\\'paymentSucceeded\\\\' or status eq \\\\'paymentStarted\\\\'' }\"\r\n    selected-items=\"$ctrl.selectedItems\" on-list-select=\"$ctrl.onListSelect({ value: value, item: item, allItems: allItems });\" crud-controller=\"PayrollCrudController as $crud\"></salaxy-odata-table>\r\n  <salaxy-odata-table ng-if=\"$ctrl.category=='draft'\"  ng-if=\"$ctrl.mode == 'select'\" template-url=\"salaxy-components/odata/lists/Payrolls-select.html\"  options=\"{ $filter: 'status eq \\\\'draft\\\\'' }\"\r\n    selected-items=\"$ctrl.selectedItems\" on-list-select=\"$ctrl.onListSelect({ value: value, item: item, allItems: allItems });\" crud-controller=\"PayrollCrudController as $crud\"></salaxy-odata-table>\r\n  </div>`);\n\n $templateCache.put(\"salaxy-components/calc/payrollV4/PayrollAssistant.html\",`\r\n<div class=\"salaxy-component salaxy-payroll-assistant salaxy-message-thread\" ng-if=\"$ctrl.current\">\r\n  <div class=\"messages-container\" >\r\n    <div id=\"openairesponse\" style=\"overflow-y: scroll;overflow-x: hidden; max-height: 300px;\">\r\n      <div class=\"text-end\">\r\n        <salaxy-avatar avatar=\"$ctrl.openAiAvatar\" class=\"float-end\"></salaxy-avatar>\r\n        <div class=\"message-bubble right text\"> \r\n          <div>\r\n            Hei! Olen palkanlaskennan tekoäly. Voin halutessasi muokata tätä palkkalistaa, vastata palkanlaskentaa koskeviin kysymyksiisi tai luoda erilaisia raportteja. Voit myös liittää Excel aineistoja, joita voin käyttää, jos haluat. Miten voin auttaa sinua tänään?\r\n          </div>     \r\n        </div>\r\n      </div>\r\n      <div  ng-repeat=\"item in $ctrl.messages | filter: {hidden: false}\" ng-switch=\"item.type\">\r\n        <div ng-switch-when=\"file\">\r\n          <salaxy-avatar avatar=\"$ctrl.myAvatar\" class=\"float-start\"></salaxy-avatar>\r\n          <div class=\"message-bubble left text\"> \r\n            <span><i class=\"fa fa-file-excel-o\"></i> {{item.file}}</span>    \r\n          </div>\r\n        </div>\r\n        <div ng-switch-when=\"html\"  class=\"text-end\">\r\n          <salaxy-avatar avatar=\"$ctrl.openAiAvatar\" class=\"float-end\"></salaxy-avatar>\r\n          <div class=\"message-bubble right text\"> \r\n            <span class=\"clickable\"  ng-click=\"$ctrl.showReport(item)\"><i class=\"fa fa-file-o\"></i> {{item.file}}</span>    \r\n          </div>\r\n        </div>\r\n        <div ng-switch-default ng-class=\"item.role == 'assistant' ? 'text-end' : ''\">\r\n          <salaxy-avatar ng-if=\"item.role != 'assistant'\" avatar=\"$ctrl.myAvatar\" class=\"float-start\"></salaxy-avatar>\r\n          <salaxy-avatar ng-if=\"item.role == 'assistant'\" avatar=\"$ctrl.openAiAvatar\" class=\"float-end\"></salaxy-avatar>\r\n          <div ng-if=\"item.role != 'assistant'\" class=\"message-bubble left text\"> \r\n            <div>\r\n              {{item.content}}\r\n            </div>     \r\n          </div>\r\n          <div ng-if=\"item.role == 'assistant'\" class=\"message-bubble right text\"> \r\n            <div>\r\n              {{item.content}}\r\n            </div>     \r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div ng-if=\"$ctrl.loading\" class=\"text-end\">\r\n        <salaxy-avatar avatar=\"$ctrl.openAiAvatar\" class=\"float-end\"></salaxy-avatar>\r\n        <div class=\"message-bubble right text\"> \r\n          <span ><span style=\"font-size: large;\"><i class=\"fa fa-refresh fa-spin fa-fw\"></i></span> Valmistellaan vastausta...</span>  \r\n        </div>\r\n      </div>\r\n    </div>\r\n      <div class=\"row  message-actions\">\r\n        <div class=\"col-8 col-sm-8\">\r\n          <textarea name=\"content\" ng-model=\"$ctrl.content\" placeholder=\"Kirjoita viesti palkanlaskennan tekoälylle\" ></textarea>\r\n        </div>\r\n        <div class=\"col-4 col-sm-4 d-flex flex-column\">\r\n          <button type=\"button\" class=\"btn btn-primary btn-labeled-left text-start mb-1\" ng-click=\"$ctrl.chatForPayroll()\">\r\n            <i class=\"bi bi-pencil-fill\"></i>\r\n            <span>Muokkaa</span>\r\n          </button>\r\n          <button type=\"button\" class=\"btn btn-default btn-labeled-left text-start mb-1\" ng-click=\"$ctrl.chatForAdvise()\">\r\n            <i class=\"bi bi-question-circle-fill\"></i>\r\n            <span>Kysy</span>\r\n          </button>\r\n          <button type=\"button\" class=\"btn btn-default btn-labeled-left text-start mb-1\" ng-click=\"$ctrl.chatForReport()\">\r\n            <i class=\"bi bi-table\"></i>\r\n            <span>Raportti</span>\r\n          </button>\r\n          <button type=\"button\" class=\"btn btn-default btn-labeled-left text-start mb-1\" ngf-select=\"$ctrl.readFile($file)\" ngf-multiple=\"false\"  ngf-max-size=\"10MB\">\r\n            <i class=\"bi bi-paperclip\"></i>\r\n            <span>Liitä Excel</span>\r\n          </button>\r\n      </div>\r\n  </div>\r\n  <div>&nbsp;</div>`);\n\n $templateCache.put(\"salaxy-components/calc/payrollV4/PayrollDetails.html\",`<div class=\"salaxy-component salaxy-payroll-details\" ng-if=\"$ctrl.current\">\r\n  <ng-include ng-show=\"!$ctrl.isNew()\" src=\"'salaxy-components/calc/payrollV4/PayrollDetails_info.html'\"></ng-include>\r\n  <ng-include ng-show=\"!$ctrl.isNew()\" src=\"'salaxy-components/calc/payrollV4/PayrollDetails_toolbar.html'\"></ng-include>\r\n  <salaxy-tab-buttons\r\n    current-tab=\"$ctrl.payrollDetailsCurrentTab\"\r\n    default-tab=\"$ctrl.defaultTab\"\r\n    ng-show=\"!$ctrl.isNew()\"\r\n    options=\"[\r\n      { value: 'calculations', text: 'SALAXY.NG1.PayrollComponent.headerViews.calculations' },\r\n      { value: 'rows', text: 'SALAXY.NG1.PayrollComponent.headerViews.rows' },\r\n      { value: 'reports', text: 'SALAXY.NG1.PayrollComponent.headerViews.reports' },\r\n      { value: 'messages', text: 'SALAXY.NG1.PayrollComponent.headerViews.messages', hidden: !('partnerMessaging' | sxyIsInRole) },\r\n      { value: 'ports', text: 'SALAXY.NG1.PayrollComponent.headerViews.ports', hidden: !$ctrl.$import.isSupported },\r\n      { value: 'records', text: 'Tarkistusraportti', hidden: !('aidemo' | sxyIsInRole) },\r\n      { value: 'debug', text: 'Debug', hidden: !('test' | sxyIsInRole) || ('aidemo' | sxyIsInRole) },\r\n    ]\"\r\n    tabs-id=\"payrollDetails\"\r\n    class=\"d-block mt-3\">\r\n  </salaxy-tab-buttons>\r\n  <div class=\"tab-content\" id=\"tab-content-payrollDetails\" ng-show=\"!$ctrl.isNew()\">\r\n    <div class=\"tab-pane\" id=\"calculations-tab\">\r\n      <ng-include ng-if=\"$ctrl.payrollDetailsCurrentTab == 'calculations'\" src=\"'salaxy-components/calc/payrollV4/PayrollDetails_calcs.html'\"></ng-include>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"rows-tab\">\r\n      <div ng-if=\"$ctrl.payrollDetailsCurrentTab == 'rows'\" class=\"row\">\r\n        <div class=\"col\" ng-class=\"$ctrl.hasAssistantKey ? 'col-8' : 'col-12'\">\r\n          <ng-include  ng-if=\"$ctrl.calcs && $ctrl.payrollDetailsCurrentTab == 'rows'\" src=\"'salaxy-components/calc/payrollV4/PayrollDetails_calcs_paged.html'\"></ng-include>\r\n        </div>\r\n        <div ng-show=\"$ctrl.hasAssistantKey\" class=\"col\" ng-class=\"$ctrl.hasAssistantKey ? 'col-4' : 'col-12'\">\r\n          <salaxy-payroll-assistant current=\"$ctrl.current\" page=\"$ctrl.page\"></salaxy-payroll-assistant>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"reports-tab\">\r\n      <div class=\"tab-content-wrapper\" ng-if=\"$ctrl.payrollDetailsCurrentTab == 'reports'\">\r\n        <div ng-show=\"false\" ng-init=\"$ctrl.clearReports()\"></div>\r\n        <ng-include src=\"'salaxy-components/calc/payrollV4/PayrollDetails_reports.html'\"></ng-include>\r\n      </div>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"messages-tab\" ng-if=\"'partnerMessaging' | sxyIsInRole\">\r\n      <ng-include ng-if=\"$ctrl.payrollDetailsCurrentTab == 'messages'\" src=\"'salaxy-components/calc/payrollV4/PayrollDetails_messages.html'\"></ng-include>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"ports-tab\" ng-show=\"$ctrl.$import.isSupported\">\r\n      <ng-include ng-show=\"$ctrl.payrollDetailsCurrentTab == 'ports'\" src=\"'salaxy-components/calc/payrollV4/PayrollDetails_ports.html'\"></ng-include>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"records-tab\" ng-if=\"'aidemo' | sxyIsInRole\">\r\n      <salaxy-records ng-if=\"$ctrl.current && $ctrl.payrollDetailsCurrentTab == 'records'\" read-only=\"false\" api-ctrl=\"$ctrl\" entity-type=\"'payrollDetails'\"></salaxy-records>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"debug-tab\" ng-if=\"('test' | sxyIsInRole) && !('aidemo' | sxyIsInRole)\">\r\n      <ng-include ng-if=\"$ctrl.payrollDetailsCurrentTab == 'debug'\" src=\"'salaxy-components/calc/payrollV4/PayrollDetails_debug.html'\"></ng-include>\r\n    </div>\r\n  </div>\r\n  <ng-include src=\"'salaxy-components/calc/payrollV4/PayrollDetails_calc.html'\"></ng-include>\r\n  <ng-include src=\"'salaxy-components/calc/payrollV4/PayrollDetails_header.html'\"></ng-include>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/payrollV4/PayrollDetailsList.html\",`<div class=\"salaxy-component salaxy-payroll-details-list\">\r\n  <div class=\"row w-100\" ng-if=\"!$ctrl.hideButton\">\r\n    <div class=\"col-12 action-button-container mb-3\">\r\n      <salaxy-action-button action=\"'newPayroll'\" button-class=\"btn-primary\" style=\"margin-bottom:30px;\"></salaxy-action-button>\r\n    </div>\r\n  </div>\r\n  <salaxy-tab-buttons\r\n    current-tab=\"$ctrl.currentTab\"\r\n    options=\"[\r\n      { value: 'default', text: 'SALAXY.NG1.PayrollComponent.payrollList.tabs.latest' },\r\n      { value: 'templates', text: 'SALAXY.NG1.PayrollComponent.payrollList.tabs.repeated' },\r\n      { value: 'paid', text: 'SALAXY.NG1.PayrollComponent.payrollList.tabs.paid' },\r\n      { value: 'paidcalcs', text: 'SALAXY.NG1.PayrollComponent.payrollList.tabs.paidSalaries' },\r\n      { value: 'draftcalcs', text: 'SALAXY.NG1.PayrollComponent.payrollList.tabs.draftCalcs' }\r\n    ]\"\r\n    tabs-id=\"payrollDetailsList\">\r\n  </salaxy-tab-buttons>\r\n  <div class=\"tab-content\" id=\"tab-content-payrollDetailsList\">\r\n    <div class=\"tab-pane\" id=\"default-tab\">\r\n      <salaxy-odata-table crud-controller=\"Payroll4CrudController as $crud\" options=\"{ $filter: 'status ne \\\\'paymentSucceeded\\\\' and status ne \\\\'paymentStarted\\\\' and status ne \\\\'template\\\\' and status ne \\\\'handled\\\\' and status ne \\\\'paymentCanceled\\\\'' }\" read-only=\"$ctrl.isReadOnlyForced\"></salaxy-odata-table>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"templates-tab\">\r\n      <salaxy-odata-table crud-controller=\"Payroll4CrudController as $crud\" options=\"{ $filter: 'status eq \\\\'template\\\\'' }\" read-only=\"$ctrl.isReadOnlyForced\"></salaxy-odata-table>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"paid-tab\">\r\n      <salaxy-odata-table crud-controller=\"Payroll4CrudController as $crud\" options=\"{ $filter: 'status eq \\\\'paymentSucceeded\\\\' or status eq \\\\'paymentStarted\\\\' or status eq \\\\'handled\\\\' or status eq \\\\'paymentCanceled\\\\'' }\" read-only=\"$ctrl.isReadOnlyForced\"></salaxy-odata-table>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"paidcalcs-tab\">\r\n      <salaxy-odata-table url=\"/v03/api/calculations/category/readonly\" crud-controller=\"CalculationCrudController as $crud\" options=\"{ $filter: 'status eq \\\\'paymentSucceeded\\\\' and data/payrollId ne null' }\" read-only=\"$ctrl.isReadOnlyForced\"></salaxy-odata-table>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"draftcalcs-tab\">\r\n      <salaxy-odata-table crud-controller=\"CalculationCrudController as $crud\" options=\"{ $filter: 'status eq \\\\'payrollDraft\\\\'' }\" read-only=\"$ctrl.isReadOnlyForced\"></salaxy-odata-table>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/payrollV4/PayrollDetailsSelectList.html\",`<div class=\"salaxy-component salaxy-payroll-details-select-list\">\r\n  <salaxy-odata-table ng-if=\"$ctrl.category=='paid'\"  ng-if=\"$ctrl.mode == 'select'\" template-url=\"salaxy-components/odata/lists/Payrolls-select.html\"  options=\"{ $filter: 'status eq \\\\'paymentSucceeded\\\\' or status eq \\\\'paymentStarted\\\\'' }\"\r\n    selected-items=\"$ctrl.selectedItems\" on-list-select=\"$ctrl.onListSelect({ value: value, item: item, allItems: allItems });\" crud-controller=\"Payroll4CrudController as $crud\"></salaxy-odata-table>\r\n  <salaxy-odata-table ng-if=\"$ctrl.category=='draft'\"  ng-if=\"$ctrl.mode == 'select'\" template-url=\"salaxy-components/odata/lists/Payrolls-select.html\"  options=\"{ $filter: 'status eq \\\\'draft\\\\'' }\"\r\n    selected-items=\"$ctrl.selectedItems\" on-list-select=\"$ctrl.onListSelect({ value: value, item: item, allItems: allItems });\" crud-controller=\"Payroll4CrudController as $crud\"></salaxy-odata-table>\r\n  </div>`);\n\n $templateCache.put(\"salaxy-components/calc/payrollV4/PayrollDetails_calc.html\",`<div class=\"salaxy-navi-page-container salaxy-payroll-details-calc salaxy-payroll-details-dialog \" ng-style=\"{'max-width': '100%','width': $ctrl.userSettings.ng1Binder('payroll.calcDialogSize').val || '75%'}\" ng-class=\"{ 'offcanvas-show': $ctrl.shouldShowCanvas('calc',$ctrl.calcId) }\">\r\n  <div class=\"modal-header bg-primary\">\r\n    <h3 class=\"modal-title\">{{ $ctrl.calc ? ( $ctrl.calc.worker.avatar.displayName + \", \" + ($ctrl.calc.result.totals.totalGrossSalary | currency) ) : ('SALAXY.UI_Terms.loading' | sxyTranslate) }}\r\n      <span ng-if=\"$ctrl.calc && ('pro' | sxyIsInRole)\" ng-controller=\"CalculationCrudController as $calcCrud\" ng-init=\"$calcCrud.model = $ctrl.calc\">\r\n        <salaxy-workflow-buttons api-ctrl=\"$calcCrud\" on-change=\"$ctrl.refreshAfterWorkflow()\" show-workflow-assign=\"false\"></salaxy-workflow-buttons>\r\n      </span>\r\n    </h3>\r\n    <span class=\"ms-auto\">\r\n      <button type=\"button\" class=\"btn btn-transparent\"  ng-click=\"$ctrl.userSettings.ng1Binder('payroll.calcDialogSize').val = ($ctrl.userSettings.ng1Binder('payroll.calcDialogSize').val == '100%' ? '75%' : '100%')\"><i ng-class=\"$ctrl.userSettings.ng1Binder('payroll.calcDialogSize').val == '100%' ? 'bi bi-arrows-angle-contract' : 'bi bi-arrows-angle-expand'\"></i></button>\r\n      <button type=\"button\" class=\"btn btn-primary\" aria-label=\"Close\" ng-click=\"$ctrl.setCalc()\"><span class=\"bi bi-x-lg\"></span></button>\r\n    </span>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <salaxy-tab-buttons\r\n      current-tab=\"$ctrl.calcTab\"\r\n      options=\"[\r\n        { value: 'calcrows', text: 'SALAXY.NG1.PayrollComponent.calcViews.rows' },\r\n        { value: 'calccalculator', text: 'SALAXY.NG1.PayrollComponent.calcViews.calculator' },\r\n        { value: 'calccostaccounting', text: 'SALAXY.NG1.PayrollComponent.calcViews.costAccounting' },\r\n        { value: 'calcemployment', text: 'SALAXY.NG1.PayrollComponent.calcViews.employment' },\r\n        { value: 'calcreports', text: 'SALAXY.NG1.PayrollComponent.calcViews.reports' },\r\n        { value: 'calcdebug', text: 'Debug', hidden: !('test' | sxyIsInRole) }\r\n      ]\"\r\n      tabs-id=\"payrollDetailsCalc\">\r\n    </salaxy-tab-buttons>\r\n    <div class=\"tab-content\" id=\"tab-content-payrollDetailsCalc\">\r\n      <div class=\"tab-pane\" id=\"calcrows-tab\">\r\n        <salaxy-calc-worker-info ng-if=\"$ctrl.calc\" model=\"$ctrl.calc\"></salaxy-calc-worker-info>\r\n        <div ng-if=\"$ctrl.calc\" class=\"my-2\" ng-controller=\"EmploymentCrudController as $employment\" ng-init=\"$employment.queryResult={};$employment.getOData({ '$filter': 'id eq \\\\'' +  $ctrl.calc.worker.employmentId + '\\\\''}, $employment.queryResult)\">\r\n          <salaxy-workflow-badge mode=\"horizontal\" ng-if=\"$employment.queryResult.items.length > 0\" model=\"$employment.queryResult.items[0]\" api-ctrl=\"$employment\" wf-types=\"'EmployerMessageRecord'\"></salaxy-workflow-badge>\r\n        </div>\r\n        <salaxy-calc-rows-2019-editor ng-if=\"$ctrl.calc\" parent=\"$ctrl.calc\" title=\"{{'SALAXY.NG1.PayrollComponent.payrollCalcs.calcRowEditor.title' | sxyTranslate}}\"\r\n          mode=\"{{($ctrl.calc.isReadOnly || $ctrl.isReadOnly ) ? 'read-only' : 'read-edit'}}\" \r\n          is-in-edit=\"!$ctrl.isReadOnly && !$ctrl.calc.isReadOnly\"\r\n          show-edit-buttons=\"false\" \r\n          show-gross-totals=\"true\"></salaxy-calc-rows-2019-editor>\r\n        <salaxy-spinner ng-if=\"!$ctrl.calc\"></salaxy-spinner>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"calccalculator-tab\">\r\n        <salaxy-calc ng-if=\"$ctrl.calc\" model=\"$ctrl.calc\"></salaxy-calc>\r\n        <salaxy-spinner ng-if=\"!$ctrl.calc\"></salaxy-spinner>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"calccostaccounting-tab\">\r\n        <div ng-class=\"$ctrl.userSettings.ng1Binder('payroll.calcDialogSize').val == '100%' ? 'container' : ''\">\r\n          <salaxy-calc-cost-accounting ng-if=\"$ctrl.calc\" calc=\"$ctrl.calc\" read-only=\"$ctrl.isReadOnly || $ctrl.calc.isReadOnly\"></salaxy-calc-cost-accounting>\r\n          <salaxy-spinner ng-if=\"!$ctrl.calc\"></salaxy-spinner>\r\n      </div>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"calcemployment-tab\">\r\n        <salaxy-employment-details ng-if=\"$ctrl.calc\" ng-ref=\"$ctrl.$employment\" model=\"$ctrl.calc.worker.employmentId\" is-modal=\"true\"></salaxy-employment-details>\r\n        <salaxy-spinner ng-if=\"!$ctrl.calc\"></salaxy-spinner>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"calcreports-tab\">\r\n        <salaxy-calc-reports ng-if=\"$ctrl.calc\" calcs=\"[$ctrl.calc]\" report-type=\"'salarySlip'\"></salaxy-calc-reports>\r\n        <salaxy-spinner ng-if=\"!$ctrl.calc\"></salaxy-spinner>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"calcdebug-tab\">\r\n        <div class=\"row\" ng-if=\"$ctrl.calc\">\r\n          <div class=\"col-sm-6\">\r\n            <salaxy-json-formatter ng-if=\"$ctrl.calc\" key=\"'Calculation'\" open=\"0\" json=\"$ctrl.calc\"></salaxy-json-formatter>\r\n            <salaxy-json-formatter ng-if=\"$ctrl.calcListItem\" key=\"'List item'\" open=\"0\" json=\"$ctrl.calcListItem\"></salaxy-json-formatter>\r\n          </div>\r\n          <div class=\"col-sm-6\">\r\n            <fieldset ng-init=\"$ctrl.initRowsImportParams()\">\r\n              <legend>Vie rivit (Muoto: Työajan tuonti)</legend>\r\n              <salaxy-input name=\"debugTitle\" ng-model=\"$ctrl.rowsImportParams.title\" label=\"Otsikko\"></salaxy-input>\r\n              <salaxy-input name=\"debugPersonalId\" ng-model=\"$ctrl.rowsImportParams.personalId\" label=\"Henkilötunnus\"></salaxy-input>\r\n              <salaxy-input name=\"debugEmploymentType\" ng-model=\"$ctrl.rowsImportParams.employmentType\" label=\"Työsuhteen tyyppi\"></salaxy-input>\r\n              <salaxy-input name=\"debugPayrollId\" ng-model=\"$ctrl.rowsImportParams.payrollId\" label=\"Palkkalistan ID\"></salaxy-input>\r\n              <salaxy-date-range name=\"debugPeriod\" ng-model=\"$ctrl.rowsImportParams.period\" label=\"Palkkakausi\"></salaxy-date-range>\r\n              <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.copyRowsImportData()\">Vie rivit</button>\r\n            </fieldset>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div class=\"modal-footer justify-content-end\">\r\n    <div class=\"me-1\">\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.setCalc()\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n      <div ng-if=\"$ctrl.calcTab=='calcrows' || $ctrl.calcTab=='calccalculator' || $ctrl.calcTab=='calccostaccounting'\" class=\"btn-group dropup\">\r\n        <button type=\"button\" ng-disabled=\"$ctrl.loaders[$ctrl.calc.id]\" class=\"btn btn-secondary dropdown-toggle\" data-bs-toggle=\"dropdown\" aria-haspopup=\"true\" aria-expanded=\"false\">\r\n          <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.options\"></span>\r\n        </button>\r\n        <ul class=\"dropdown-menu dropdown-menu-end\" role=\"menu\" aria-labelledby=\"actions\">\r\n          <li role=\"menuitem\" ng-if=\"!$ctrl.isReadOnlyForced && !$ctrl.calc.isReadOnly\">\r\n            <a href=\"\" ng-click=\"$ctrl.deleteCalc()\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.deletePayrollCalc\" class=\"dropdown-item\"></a>\r\n          </li>\r\n          <li role=\"menuitem\" ng-if=\"!$ctrl.isReadOnlyForced && (!$ctrl.isReadOnly || !$ctrl.calc.isReadOnly)\">\r\n            <a href=\"\" ng-click=\"$ctrl.deleteCalc(true)\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.unlink\" class=\"dropdown-item\"></a>\r\n          </li>\r\n          <li role=\"menuitem\">\r\n            <a href=\"\" ng-click=\"$ctrl.copyCalc()\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.copyAsNew\" class=\"dropdown-item\"></a>\r\n          </li>\r\n          <li role=\"menuitem\" ng-if=\"$ctrl.isReadOnly && !$ctrl.calc.isReadOnly && !$ctrl.isCfa\">\r\n            <a href=\"\" ng-click=\"$ctrl.payCalc()\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.pay\" class=\"dropdown-item\"></a>\r\n          </li>\r\n        </ul>\r\n      </div>\r\n    </div>\r\n    <div>\r\n      <button ng-if=\"$ctrl.page.total > 1 && $ctrl.payrollDetailsCurrentTab !=='calculations'\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.goToPage(true)\"><span><i class=\"bi bi-rewind-fill\"></i></span> <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.previousPage\"></span></button>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.goToCalc(true)\"><span><i class=\"bi bi-caret-left-fill\"></i></span> <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.previousCalc\"></span></button>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.goToCalc(false)\"><span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.nextCalc\"></span> <span><i class=\"bi bi-caret-right-fill\"></i></span></button>\r\n    </div>\r\n\r\n    <button ng-if=\"$ctrl.page.total > 1 && $ctrl.payrollDetailsCurrentTab !=='calculations'\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.goToPage(false)\"><span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.nextPage\"></span> <span><i class=\"bi bi-fast-forward-fill\"></i></span></button>\r\n    <button ng-if=\"$ctrl.calcTab=='calcrows' || $ctrl.calcTab=='calccalculator' || $ctrl.calcTab=='calccostaccounting'\"  type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.saveCalc($ctrl.calc)\" ng-disabled=\"$ctrl.isReadOnly || $ctrl.calc.isReadOnly || $ctrl.loaders[$ctrl.calc.id]\">\r\n      <span ng-if=\"$ctrl.loaders[$ctrl.calc.id]\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span>\r\n      <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.save\"></span>\r\n      <span ng-if=\"$ctrl.hasCalcChange\"> <span class=\"badge\">1<span></span>\r\n    </button>\r\n\r\n    <button ng-if=\"$ctrl.calcTab=='calcemployment'\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.addSalaryDefaultsToCalc($ctrl.calc)\" ng-disabled=\"$ctrl.isReadOnly || $ctrl.calc.isReadOnly || $ctrl.loaders[$ctrl.calc.id + '-add-salary-defaults']\"><span ng-if=\"$ctrl.loaders[$ctrl.calc.id + '-add-salary-defaults']\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span> <span sxy-text=\"SALAXY.NG1.EmploymentTaxcardsComponent.workerEdit.addSalaryDefaults\"></span></button>\r\n    <button ng-if=\"$ctrl.calcTab=='calcemployment'\" type=\"button\" class=\"btn btn-danger\" ng-click=\"$ctrl.saveEmployment($ctrl.$employment.current, true)\" ng-disabled=\"$ctrl.isReadOnly || $ctrl.calc.isReadOnly || $ctrl.loaders[$ctrl.calc.id + '-employment-true']\"><span ng-if=\"$ctrl.loaders[$ctrl.calc.id + '-employment-true']\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span> <span sxy-text=\"SALAXY.NG1.EmploymentTaxcardsComponent.workerEdit.updateWorkerInfoAndSalaryRows\"></span></button>\r\n    <button ng-if=\"$ctrl.calcTab=='calcemployment'\" type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.saveEmployment($ctrl.$employment.current)\" ng-disabled=\"$ctrl.isReadOnly || $ctrl.calc.isReadOnly || $ctrl.loaders[$ctrl.calc.id + '-employment-false']\"><span ng-if=\"$ctrl.loaders[$ctrl.calc.id + '-employment-false']\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span> <span sxy-text=\"SALAXY.NG1.EmploymentTaxcardsComponent.workerEdit.updateWorkerInfo\"></span><span ng-if=\"$ctrl.hasEmploymentChange\"> <span class=\"badge\">1<span></span></button>\r\n    \r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/payrollV4/PayrollDetails_calcs.html\",`<div class=\"table-responsive\">\r\n  <table class=\"table table-striped\">\r\n    <thead>\r\n      <tr>\r\n        <th colspan=\"4\" ng-click=\"$ctrl.orderBy('otherPartyInfo.avatar.sortableName')\" class=\"clickable\">\r\n          <span><span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span> <i ng-if=\"$ctrl.orderField == 'otherPartyInfo.avatar.sortableName'\" class=\"fa\" ng-class=\"$ctrl.orderReverse  ? 'bi-sort-down' : 'bi-sort-up'\"></i></span>\r\n        </th>\r\n        <th class=\"right clickable\" ng-click=\"$ctrl.orderBy('grossSalary')\">\r\n          <span><span sxy-text=\"SALAXY.NG1.CalcListComponent.salary\"></span> <i ng-if=\"$ctrl.orderField == 'grossSalary'\" class=\"fa\" ng-class=\"$ctrl.orderReverse  ? 'bi-sort-down' : 'bi-sort-up'\"></i></span>\r\n        </th>\r\n        <th class=\"right clickable\" ng-click=\"$ctrl.orderBy('data.workerPayment')\">\r\n          <span><span sxy-text=\"SALAXY.NG1.CalcListComponent.net\"></span> <i ng-if=\"$ctrl.orderField == 'data.workerPayment'\" class=\"fa\" ng-class=\"$ctrl.orderReverse  ? 'bi-sort-down' : 'bi-sort-up'\"></i></span>\r\n        </th>\r\n        <th class=\"clickable\" ng-click=\"$ctrl.orderBy('status')\">\r\n          <span><span sxy-text=\"SALAXY.NG1.CalcListComponent.status.title\"></span> <i ng-if=\"$ctrl.orderField == 'status'\" class=\"fa\" ng-class=\"$ctrl.orderReverse  ? 'bi-sort-down' : 'bi-sort-up'\"></i></span>\r\n        </th>\r\n        <th>\r\n          <span sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.records.label\"></span>\r\n        </th>\r\n        <th sxy-if-role=\"pro\">\r\n          <div class=\"d-flex align-items-end\">\r\n            <span sxy-text=\"SALAXY.NG1.CalcListComponent.checked\" class=\"me-2\"></span>\r\n            <salaxy-input-enum class=\"column-filter\" ng-model=\"calculationChecked\" ng-change=\"calculationChecked != null && $ctrl.setColumnFilter('PartnerMessageClosed', calculationChecked)\" placeholder=\"SALAXY.MODEL.PayrollListItem.messages.tableHeading\" name=\"calculationCheckedStatus\" options=\"{ '': 'SALAXY.UI_Terms.showAll', true: 'SALAXY.MODEL.PayrollListItem.messages.tableHeading', false: 'SALAXY.MODEL.PayrollListItem.messages.tableHeadingNotChecked' }\" label-type=\"plain\"></salaxy-input-enum>\r\n          </div>\r\n        </th>\r\n        <th sxy-if-role=\"pro\">\r\n          <div class=\"d-flex align-items-end\">\r\n            <span sxy-text=\"SALAXY.NG1.CalcListComponent.issues\" class=\"me-2\"></span>\r\n            <salaxy-input-enum class=\"column-filter\" ng-model=\"calculationIssue\" ng-change=\"calculationIssue != null && $ctrl.setColumnFilter('PartnerMessageIssue', calculationIssue)\" placeholder=\"SALAXY.MODEL.PayrollListItem.messages.tableHeadingIssues\" name=\"calculationIssuesStatus\" options=\"{ '': 'SALAXY.UI_Terms.showAll', true: 'SALAXY.MODEL.PayrollListItem.messages.tableHeadingIssues', false: 'SALAXY.MODEL.PayrollListItem.messages.tableHeadingNoIssues' }\" label-type=\"plain\"></salaxy-input-enum>\r\n          </div>\r\n        </th>\r\n        <th class=\"right clickable\" ng-click=\"$ctrl.orderBy('data.workStartDate')\" >\r\n          <span><span sxy-text=\"SALAXY.NG1.CalcListComponent.salaryPeriod\"></span> <i ng-if=\"$ctrl.orderField == 'data.workStartDate'\" class=\"fa\" ng-class=\"$ctrl.orderReverse  ? 'bi-sort-down' : 'bi-sort-up'\"></i></span>\r\n        </th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat=\"row in $ctrl.calcs\" class=\"clickable\" ng-class=\"{ 'active-payroll-item': $ctrl.calcId == row.id }\"  ng-click=\"$ctrl.toggleCalc(row.id)\">\r\n        <td class=\"td-avatar middle\">\r\n          <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n        </td>\r\n        <td class=\"td-name middle\">\r\n          <div>\r\n            <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.CalcListComponent.notSelected\"></span>\r\n            <strong>{{row.otherPartyInfo.avatar.displayName}}</strong>\r\n          </div>\r\n          <div>{{ row.otherPartyInfo.officialId }}</div>\r\n        </td>\r\n        <td colspan=\"2\" class=\"middle\">\r\n          <span ng-if=\"$ctrl.getCalcValidity(row)\" class=\"error-summary text-danger\" sxy-text=\"{{'SALAXY.VALIDATION.' + $ctrl.getCalcValidity(row).errors[0].code + '.label'}}\"></span>\r\n          <span ng-if=\"$ctrl.getCalcValidity(row) && $ctrl.getCalcValidity(row).errors[0].code == 'Payroll.Calc.TaxCardType'\">\r\n            <button class=\"btn btn-xs btn-default\" ng-click=\"$ctrl.showAddNewTaxcard($event, row)\">{{ 'SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.workerInfo.addTaxcard' | sxyTranslate}} <i class=\"bi bi-plus-lg\"></i></button>\r\n          </span>\r\n        </td>\r\n        <td class=\"right middle\">{{ row.grossSalary | currency }}</td>\r\n        <td class=\"right middle\">{{ row.data.workerPayment | currency }}</td>\r\n        <td class=\"middle\"><span ng-class=\"$ctrl.rowStatusWarning(row) ? 'badge bg-danger': ''\">{{ \"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate }}<span></td>\r\n        <td>\r\n          <salaxy-workflow-badge mode=\"horizontal\" ng-if=\"$ctrl.employments[row.data.employmentId].messages.length > 0\" model=\"$ctrl.employments[row.data.employmentId]\" api-ctrl=\"$employment\" wf-types=\"'EmployerMessageRecord'\"></salaxy-workflow-badge>\r\n        </td>\r\n        <td sxy-if-role=\"pro\">\r\n          <div ng-repeat=\"message in row.messages\" ng-bind-html=\"message | sxyWorkflowMessage: 'PartnerMessageClosed'\"></div>\r\n        </td>\r\n        <td sxy-if-role=\"pro\">\r\n          <div ng-repeat=\"message in row.messages\" ng-bind-html=\"message | sxyWorkflowMessage: 'PartnerMessageIssue'\"></div>\r\n        </td>\r\n        <td class=\"right middle\">\r\n          <span>{{ { start: row.data.workStartDate, end: row.data.workEndDate, } | sxyDateRange }}</span>\r\n          <div ng-if=\"$ctrl.isDateDifferent(row)\">\r\n            <del class=\"small\">{{ $ctrl.current.input.period | sxyDateRange }}</del>\r\n          </div>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/payrollV4/PayrollDetails_calcs_paged.html\",`<div class=\"text-end\">\r\n  <span class=\"float-start\" ng-if=\"$ctrl.page.total > 1\">{{$ctrl.page.calcRange}}/{{$ctrl.page.totalCalcCount}}</span>\r\n  <button type=\"button\" ng-if=\"!('disableHolidays' | sxyIsInRole)\" class=\"btn btn-secondary\" ng-click=\"$ctrl.saveWorktimes()\" ng-disabled=\"$ctrl.isReadOnly || !$ctrl.current.id  || $ctrl.current.input.calculations.length == 0 || $ctrl.loaders['worktime' + $ctrl.current.id]\"><span ng-if=\"$ctrl.loaders['worktime' + $ctrl.current.id]\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span> <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.saveWorktime\"></span></button>\r\n  <div class=\"btn-group\">\r\n   <salaxy-input-enum  style=\"display: inline-block\" name=\"pageSize\" ng-model=\"$ctrl.pageSizeOption\" label-type=\"plain\" options=\"$ctrl.pageSizeOptions\" ng-change=\"$ctrl.setPageItems()\"></salaxy-input-enum>\r\n   <button ng-if=\"$ctrl.page.total > 1\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.goToPage(true)\"><span><i class=\"bi bi-caret-left-fill\"></i></span> <span sxy-text=\"SALAXY.UI_Terms.previous\"></span></button>\r\n   <button ng-if=\"$ctrl.page.total > 1\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.goToPage(false)\"><span sxy-text=\"SALAXY.UI_Terms.next\"></span> <span><i class=\"bi bi-caret-right-fill\"></i></span></button>\r\n  </div>\r\n  <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.savePageCalcs()\" ng-disabled=\"$ctrl.isReadOnly || $ctrl.numOfChangedPageCalcs == 0 || $ctrl.loaders['pageCalcs' + $ctrl.page.current]\"><span ng-if=\"$ctrl.loaders['pageCalcs' + $ctrl.page.current]\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span> <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.save\"></span><span ng-if=\"$ctrl.numOfChangedPageCalcs > 0\"> <span class=\"badge\">{{$ctrl.numOfChangedPageCalcs}}<span></span></span></button>\r\n</div>\r\n<div class=\"table-responsive\">\r\n  <table class=\"table table-striped\">\r\n    <thead>\r\n      <tr>\r\n        <th colspan=\"4\" sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></th>\r\n        <th class=\"right\" sxy-text=\"SALAXY.NG1.CalcListComponent.salary\"></th>\r\n        <th class=\"right\" sxy-text=\"SALAXY.NG1.CalcListComponent.net\"></th>\r\n        <th class=\"\" sxy-text=\"SALAXY.NG1.CalcListComponent.status.title\"></th>\r\n        <th sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.records.label\"></th>\r\n        <th sxy-if-role=\"pro\" sxy-text=\"SALAXY.NG1.CalcListComponent.checked\"></th>\r\n        <th sxy-if-role=\"pro\" sxy-text=\"SALAXY.NG1.CalcListComponent.issues\"></th>\r\n        <th ng-if=\"!('disableHolidays' | sxyIsInRole)\" class=\"right\" sxy-text=\"SALAXY.NG1.CalcListComponent.worktime\"></th>\r\n        <th class=\"right\" sxy-text=\"SALAXY.NG1.CalcListComponent.salaryPeriod\"></th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat-start=\"row in $ctrl.page.items\" class=\"clickable\" ng-class=\"{ 'active-payroll-item': $ctrl.calcId == row.id }\" ng-click=\"$ctrl.toggleCalc(row.id)\">\r\n        <td class=\"td-avatar middle\">\r\n          <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n        </td>\r\n        <td class=\"td-name middle\">\r\n          <div>\r\n            <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.CalcListComponent.notSelected\"></span>\r\n            <strong>{{row.otherPartyInfo.avatar.displayName}}</strong>\r\n          </div>\r\n          <div>{{ row.otherPartyInfo.officialId }}</div>\r\n        </td>\r\n        <td colspan=\"2\" class=\"middle\">\r\n          <span ng-if=\"$ctrl.getCalcValidity(row)\" class=\"error-summary text-danger\" sxy-text=\"{{'SALAXY.VALIDATION.' + $ctrl.getCalcValidity(row).errors[0].code + '.label'}}\"></span>\r\n          <span ng-if=\"$ctrl.getCalcValidity(row) && $ctrl.getCalcValidity(row).errors[0].code == 'Payroll.Calc.TaxCardType'\">\r\n            <button class=\"btn btn-xs btn-default\" ng-click=\"$ctrl.showAddNewTaxcard($event, row)\">{{ 'SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.workerInfo.addTaxcard' | sxyTranslate}} <i class=\"bi bi-plus-lg\"></i></button>\r\n          </span>\r\n        </td>\r\n        <td class=\"right middle\">{{ row.grossSalary | currency }}</td>\r\n        <td class=\"right middle\">{{ row.data.workerPayment | currency }}</td>\r\n        <td class=\"middle\"><span ng-class=\"$ctrl.rowStatusWarning(row) ? 'badge bg-danger': ''\">{{ \"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate }}<span></td>\r\n        <td class=\"middle\">\r\n          <div ng-if=\"$ctrl.getPageCalc(row)\" ng-controller=\"EmploymentCrudController as $employment\" ng-init=\"$employment.queryResult={};$employment.getOData({ '$filter': 'id eq \\\\'' +  $ctrl.getPageCalc(row).worker.employmentId + '\\\\''}, $employment.queryResult)\">\r\n            <salaxy-workflow-badge mode=\"horizontal\" ng-if=\"$employment.queryResult.items.length > 0\" model=\"$employment.queryResult.items[0]\" api-ctrl=\"$employment\" wf-types=\"'EmployerMessageRecord'\"></salaxy-workflow-badge>\r\n          </div>\r\n        </td>\r\n        <td class=\"middle\" sxy-if-role=\"pro\">\r\n          <div ng-repeat=\"message in row.messages\" ng-bind-html=\"message | sxyWorkflowMessage: 'PartnerMessageClosed'\"></div>\r\n        </td>\r\n        <td class=\"middle\" sxy-if-role=\"pro\">\r\n          <div ng-repeat=\"message in row.messages\" ng-bind-html=\"message | sxyWorkflowMessage: 'PartnerMessageIssue'\"></div>\r\n        </td>\r\n        <td ng-if=\"!('disableHolidays' | sxyIsInRole)\" class=\"right\">\r\n          <table class=\"text-small\" ng-if=\"$ctrl.getPageCalc(row)\">\r\n            <tbody>\r\n              <tr>\r\n                <td sxy-text=\"SALAXY.NG1.CalcComponent.panelWorkTime.overview.leavesDays\"></td>\r\n                <td class=\"right\">{{ $ctrl.calculatePeriodDays($ctrl.getPageCalc(row),'leavesDays') | sxyCount : 'day' }}</td>\r\n              </tr>\r\n              <tr>\r\n                <td sxy-text=\"SALAXY.NG1.CalcComponent.panelWorkTime.overview.absencesDays\"></td>\r\n                <td class=\"right\">{{ $ctrl.calculatePeriodDays($ctrl.getPageCalc(row),'absencesDays') | sxyCount : 'day' }}</td>\r\n              </tr>\r\n              <tr>\r\n                <td sxy-text=\"SALAXY.NG1.CalcComponent.panelWorkTime.overview.paidAbsencesDays\"></td>\r\n                <td class=\"right\">{{ $ctrl.calculatePeriodDays($ctrl.getPageCalc(row),'paidAbsencesDays') | sxyCount : 'day' }}</td>\r\n              </tr>\r\n              <tr ng-if=\"$ctrl.showAccruals($ctrl.getPageCalc(row))\">\r\n                <td sxy-text=\"SALAXY.NG1.CalcComponent.panelWorkTime.overview.accruedDays\"></td>\r\n                <td class=\"right\">{{ $ctrl.calculatePeriodDays($ctrl.getPageCalc(row),'accruedDays') | sxyCount : 'day' }}</td>\r\n              </tr>\r\n            </tbody>\r\n          </table>\r\n        </td>\r\n        <td class=\"right middle\">\r\n          <span>{{ { start: row.data.workStartDate, end: row.data.workEndDate, } | sxyDateRange }}</span>\r\n          <div ng-if=\"$ctrl.isDateDifferent(row)\">\r\n            <del class=\"small\">{{ $ctrl.current.input.period | sxyDateRange }}</del>\r\n          </div>\r\n        </td>\r\n      </tr>\r\n      <tr ng-repeat-end>\r\n        <td colspan=\"12\">\r\n          <salaxy-spinner ng-if=\"!$ctrl.getPageCalc(row)\"></salaxy-spinner>\r\n          <salaxy-calc-rows-2019-editor ng-if=\"$ctrl.getPageCalc(row)\" parent=\"$ctrl.getPageCalc(row)\" title=\"{{'SALAXY.NG1.PayrollComponent.payrollCalcs.calcRowEditor.title' | sxyTranslate}}\" mode=\"{{($ctrl.getPageCalc(row).isReadOnly || $ctrl.isReadOnly ) ? 'read-only' : 'read-edit'}}\" show-edit-buttons=\"false\" is-in-edit=\"!($ctrl.isAiDemoWaitingApproval) && !$ctrl.isReadOnly && !$ctrl.getPageCalc(row).isReadOnly\" show-gross-totals=\"true\" dimension-count=\"2\">\r\n          </salaxy-calc-rows-2019-editor>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n</div>\r\n<div class=\"text-right\">\r\n  <span class=\"float-start\" ng-if=\"$ctrl.page.total > 1\">{{$ctrl.page.calcRange}}/{{$ctrl.page.totalCalcCount}}</span>\r\n  <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.goToPage(true)\"><span><i class=\"bi bi-rewind-fill me-2\"></i></span> <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.previousPage\"></span></button>\r\n  <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.goToPage(false)\"><span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.nextPage\"></span> <span><i class=\"ms-2 bi bi-fast-forward-fill\"></i></span></button>\r\n  <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.savePageCalcs()\" ng-disabled=\"$ctrl.isReadOnly || $ctrl.numOfChangedPageCalcs == 0 || $ctrl.loaders['pageCalcs' + $ctrl.page.current]\"><span ng-if=\"$ctrl.loaders['pageCalcs' + $ctrl.page.current]\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span> <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.calculation.actions.save\"></span><span ng-if=\"$ctrl.numOfChangedPageCalcs > 0\"> <span class=\"badge\">{{$ctrl.numOfChangedPageCalcs}}<span></span></span></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/payrollV4/PayrollDetails_debug.html\",`<salaxy-json-formatter ng-if=\"$ctrl.current\" key=\"'PAYROLL'\" json=\"$ctrl.current\"></salaxy-json-formatter>`);\n\n $templateCache.put(\"salaxy-components/calc/payrollV4/PayrollDetails_header.html\",`<div class=\"salaxy-navi-page-container salaxy-payroll-details-header salaxy-payroll-details-dialog\" ng-style=\"{'max-width': '100%','width': $ctrl.userSettings.ng1Binder('payroll.headerDialogSize').val || '75%'}\" ng-class=\"{ 'offcanvas-show': $ctrl.shouldShowCanvas('header',$ctrl.showHeader || $ctrl.isNew())}\">\r\n  <div class=\"modal-header bg-primary\">\r\n   \r\n    <h3 ng-if=\"$ctrl.isNew()\"  class=\"modal-title\">{{$ctrl.current.input.title || ('SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.new.heading' | sxyTranslate)}}</h3>\r\n    <h3 ng-if=\"!$ctrl.isNew()\"  class=\"modal-title\">{{$ctrl.current.input.title}}</h3>\r\n    <span class=\"ms-auto\">\r\n      <button type=\"button\" class=\"btn btn-transparent\"  ng-click=\"$ctrl.userSettings.ng1Binder('payroll.headerDialogSize').val = ($ctrl.userSettings.ng1Binder('payroll.headerDialogSize').val == '100%' ? '75%' : '100%')\"><i ng-class=\"$ctrl.userSettings.ng1Binder('payroll.headerDialogSize').val == '100%' ? 'bi bi-arrows-angle-contract' : 'bi bi-arrows-angle-expand'\" class=\"text-white\"></i></button>\r\n      <button type=\"button\" class=\"btn btn-transparent\" aria-label=\"Close\" ng-click=\"$ctrl.closeHeader()\"><span class=\"bi bi-x-lg text-white\"></span></button>\r\n    </span>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <div ng-class=\"$ctrl.userSettings.ng1Binder('payroll.headerDialogSize').val == '100%' ? 'container' : ''\">\r\n      <ng-form name=\"$ctrl.payrollDetailsForm\" class=\"form-horizontal\" ng-readonly=\"$ctrl.isReadOnly\">\r\n        <div class=\"col-12 payroll-edit-properties-col\">\r\n          <salaxy-input name=\"title\" label=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.title\" required ng-model=\"$ctrl.current.input.title\"></salaxy-input>\r\n          <salaxy-form-group name=\"paymentChannel\" ng-if=\"!('salaxyPay' | sxyIsInRole)\" label=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.paymentChannel\">\r\n            <salaxy-pay-button ng-if=\"!$ctrl.isReadOnly || $ctrl.showAction('pay')\" model=\"$ctrl.current\" mode=\"channel-select\" button-class=\"btn-block\"></salaxy-pay-button>\r\n            <div ng-if=\"$ctrl.isReadOnly && !$ctrl.showAction('pay')\">{{ \"PaymentChannel.\" + $ctrl.current.input.paymentChannel | sxyEnum }}</div>\r\n          </salaxy-form-group>\r\n          <div ng-if=\"(!$ctrl.isReadOnly || $ctrl.showAction('pay')) && ('test,setSalaryDateKind' | sxyIsInRole) && !('salaxyPay' | sxyIsInRole)\"  ng-switch=\"$ctrl.current.input.paymentChannel\">\r\n            <div ng-switch-when=\"palkkausManual|talenomManual|palkkausInvoices|palkkausCfaTest|kitsas|briox|askelma|passeliMerit|ecom|hausvise\" ng-switch-when-separator=\"|\">\r\n              <salaxy-form-group name=\"salaryDateKind\" label=\"SALAXY.MODEL.PayrollInput.salaryDateKind.title\">       \r\n                <salaxy-salary-date-kind-button button-class=\"btn-block\" model=\"$ctrl.current\" ></salaxy-salary-date-kind-button>\r\n              </salaxy-form-group>\r\n            </div>\r\n          </div>\r\n          <salaxy-form-group ng-if=\"($ctrl.isReadOnly && !$ctrl.showAction('pay')) && $ctrl.current.input.salaryDateKind == 'inPast'\" name=\"salaryDateKind\" class=\"salaxy-component salaxy-read-only\" label=\"SALAXY.MODEL.CalcWorkflow.salaryDateKind.title\">\r\n            <div class=\"form-control-plaintext\">{{\"SALAXY.ENUM.SalaryDateKind.\" + ($ctrl.current.input.salaryDateKind) + \".label\" | sxyTranslate  }}</div>\r\n          </salaxy-form-group>\r\n\r\n          <salaxy-datepicker-popup read-only=\"false\" ng-if=\"!$ctrl.isReadOnly || $ctrl.showAction('pay')\" label=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.salaryDate\" name=\"salaryDate\" ng-model=\"$ctrl.current.input.salaryDate\" update-disabled-dates=\"($ctrl.current.input.salaryDateKind || '-') + '|' + ($ctrl.current.input.paymentChannel || '-')\" date-disabled=\"disable-function\" disable-function=\"$ctrl.isDisabledSalaryDate\"></salaxy-datepicker-popup>\r\n          <div class=\"row py-2\" ng-if=\"$ctrl.isReadOnly && !$ctrl.showAction('pay')\">\r\n            <div class=\"col-sm-4\"><strong sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.salaryDate\" ps=\":\"></strong> </div>\r\n            <div class=\"col-sm-8\">\r\n              {{ $ctrl.current.info.salaryDate | date }}\r\n              <span class=\"badge bg-info\" ng-if=\"$ctrl.current.info.status != 'paymentSucceeded' && !$ctrl.current.input.salaryDate && $ctrl.current.info.salaryDate\">{{'SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.salaryDateEstimate' | sxyTranslate}}</span>\r\n              <span ng-if=\"$ctrl.current.info.status != 'paymentSucceeded' &&  $ctrl.current.info.salaryDate && $ctrl.current.input.salaryDate && $ctrl.current.input.salaryDate != $ctrl.current.info.salaryDate\"><s>{{ $ctrl.current.input.salaryDate | date }}</s> <span class=\"badge bg-warning\">{{'SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.salaryDateNote' | sxyTranslate}}</span></span>    \r\n            </div>\r\n          </div>\r\n          <salaxy-date-range read-only=\"$ctrl.isReadOnly && !$ctrl.showAction('pay')\" label=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.salaryPeriod\" name=\"period\" ng-model=\"$ctrl.current.input.period\" mode=\"calc\"></salaxy-date-range>\r\n\r\n          <salaxy-input name=\"sourceId\" label=\"Source ID (import)\" ng-model=\"$ctrl.current.input.sourceId\"></salaxy-input>\r\n          \r\n          <salaxy-form-group ng-if=\"$ctrl.isNew() && $ctrl.current.input.calculations.length\" label=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.new.copyingCalcs\" name=\"calcCount\">\r\n            {{ $ctrl.current.input.calculations.length }} {{ 'SALAXY.UI_Terms.units.pce' | sxyTranslate}}\r\n          </salaxy-form-group>\r\n          <salaxy-input-boolean ng-if=\"$ctrl.isNew() && $ctrl.current.input.calculations.length\" type=\"select\" required placeholder=\"SALAXY.UI_Terms.choose\" name=\"updateCalcsInCopy\" ng-model=\"$ctrl.updateCalcsInCopy\" label=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.new.updateCalcs\" label-false=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.new.updateCalcsFalse\"\r\n            label-true=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.new.updateCalcsTrue\"></salaxy-input-boolean>\r\n        </div>\r\n      </ng-form>\r\n    </div>\r\n  </div>\r\n  <div class=\"modal-footer\">\r\n    <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.closeHeader()\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n\r\n    <button type=\"button\" ng-if=\"!$ctrl.isNew()\" class=\"btn btn-primary ms-2\" ng-click=\"$ctrl.save()\" ng-disabled=\"($ctrl.isReadOnly && !$ctrl.showAction('pay')) || (!$ctrl.payrollDetailsForm.$valid || !$ctrl.current.input.paymentChannel || $ctrl.current.input.paymentChannel == 'undefined' )  || $ctrl.loaders[$ctrl.current.id || 'new']\"><span\r\n      ng-if=\"$ctrl.loaders[$ctrl.current.id || 'new']\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span> <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.toolbar.save\"></span></button>\r\n    <button type=\"button\" ng-if=\"$ctrl.isNew()\" class=\"btn btn-primary ms-2\" ng-click=\"$ctrl.save({ 'applyEmploymentDefaultRows' : !$ctrl.updateCalcsInCopy})\" ng-disabled=\"(!$ctrl.payrollDetailsForm.$valid || !$ctrl.current.input.paymentChannel || $ctrl.current.input.paymentChannel == 'undefined') || $ctrl.loaders[$ctrl.current.id || 'new']\"><span\r\n        ng-if=\"$ctrl.loaders[$ctrl.current.id || 'new']\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span> <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.editProperties.new.createPayrollButton\"></span></button>\r\n  </div>\r\n</div>\r\n`);\n\n $templateCache.put(\"salaxy-components/calc/payrollV4/PayrollDetails_import_debug.html\",`<div ng-controller=\"ImportStagingController as $import\">\r\n  <div>\r\n    <div class=\"row\">\r\n      <div class=\"col-12\">\r\n        <div class=\"btn-group\" style=\"padding: 5px;\">\r\n          <button \r\n            class=\"btn btn-primary\" \r\n            ng-click=\"$import.uploadTestJson($import.debugJson)\"\r\n            ng-disabled=\"!$import.debugJson\">\r\n            Send JSON\r\n          </button>\r\n          <button \r\n            class=\"btn btn-info\" \r\n            ng-click=\"$import.formatDebugJson($import.debugJson)\"\r\n            ng-disabled=\"!$import.debugJson\"\r\n            style=\"margin-left: 5px;\">\r\n            Format JSON\r\n          </button>\r\n          <button \r\n            class=\"btn btn-info\" \r\n            ng-click=\"$import.debugJsonAddBlank()\"\r\n            style=\"margin-left: 5px;\">\r\n            Add Blank WorktimeImport\r\n          </button>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"row\">\r\n      <div class=\"col-6 col-md-6\">\r\n          <sxy-code-editor ng-model=\"$import.debugJson\" lang=\"json\" height=\"600px\"></sxy-code-editor>\r\n      </div>\r\n      <div class=\"col-6 col-md-6\">\r\n        <div ng-if=\"$import.uploadResults\">\r\n          <salaxy-json-formatter json=\"$import.uploadResults\" key=\"'result'\" open=\"10\"></salaxy-json-formatter>\r\n        </div>\r\n        <div ng-if=\"!$import.uploadResults\">\r\n          <p class=\"text-center text-muted\">\r\n            Results will appear here after sending JSON\r\n          </p>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/payrollV4/PayrollDetails_info.html\",`<div class=\"row w-100 payroll-info-row\">\r\n  <div class=\"col-auto\">\r\n    <salaxy-avatar-placeholder class=\"payroll-avatar\">\r\n      <i class=\"salaxy-avatar bi bi-square-fill text-muted d-flex\" ng-class=\"{'draft-invalid' : $ctrl.current.info.status == 'draft' && !$ctrl.current.info.isReadyForPayment, 'text-success' : $ctrl.current.info.status == 'paymentSucceeded', 'text-warning' : ($ctrl.current.info.status == 'paymentStarted' || $ctrl.current.info.status == 'waitingApproval') , 'text-danger' : $ctrl.current.info.status == 'paymentCancelled'}\">\r\n        <div class=\"avatar-text-wrapper\">\r\n          <strong>{{ $ctrl.current.info.calcCount }}</strong>\r\n          <small>{{ $ctrl.current.info.salaryDate | date : \"d.M.\" }}</small>\r\n        </div>\r\n      </i>\r\n    </salaxy-avatar-placeholder>\r\n  </div>\r\n  <div class=\"col-auto payroll-info-col\">\r\n    <h3 class=\"payroll-title\">{{ $ctrl.current.input.title }}</h3>\r\n    <div class=\"row\">\r\n      <div class=\"col-12 col-sm-6\">\r\n        <div>\r\n          <span>{{ 'PayrollStatus.' + $ctrl.current.info.status | sxyEnum }}</span>\r\n          <span ng-if=\"$ctrl.current.info.status == 'draft'\" ng-class=\"$ctrl.current.info.isReadyForPayment ? 'text-success' : 'text-danger'\">\r\n            {{ $ctrl.current.info.isReadyForPayment ? (('SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.readyForPayment' | sxyTranslate)) :\r\n            (('SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.notReadyForPayment' | sxyTranslate)) }}\r\n          </span>\r\n        </div>\r\n        <div>\r\n          <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.salaryPeriod\" ps=\":\"></span> {{ $ctrl.current.input.period | sxyDateRange }} ({{$ctrl.current.input.period.daysCount}} <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.salaryPeriodDaysCount\"></span>)\r\n        </div>\r\n        <div>\r\n          <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.salaryDate\" ps=\":\"></span> \r\n          {{ $ctrl.current.info.salaryDate | date }}\r\n          <span class=\"badge bg-info\" ng-if=\"$ctrl.current.info.status != 'paymentSucceeded' && !$ctrl.current.input.salaryDate && $ctrl.current.info.salaryDate\">{{'SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.salaryDateEstimate' | sxyTranslate}}</span>\r\n          <span ng-if=\"$ctrl.current.info.status != 'paymentSucceeded' &&  $ctrl.current.info.salaryDate && $ctrl.current.input.salaryDate && $ctrl.current.input.salaryDate != $ctrl.current.info.salaryDate\"><s>{{ $ctrl.current.input.salaryDate | date }}</s> <span class=\"badge bg-warning\">{{'SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.salaryDateNote' | sxyTranslate}}</span></span>\r\n        </div>\r\n        <div>\r\n          <span ng-if=\"$ctrl.current.input.template\" sxy-html=\"SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.template.html\" params=\"{template: ($ctrl.current.input.template)}\"></span>\r\n        </div>\r\n        <div>\r\n          <small>ID: <code>{{ $ctrl.currentId }}</code></small>\r\n        </div>\r\n      </div>\r\n      <div class=\"col-12 col-sm-6\">\r\n        <span><span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.calcCount\" ps=\":\"></span><span ng-style=\"$ctrl.getExceptionStyle($ctrl.info.calcCount.exception)\"> {{ $ctrl.info.calcCount.original }}</span><span ng-if=\"$ctrl.info.calcCount.exception\"> {{ $ctrl.info.calcCount.actual }}</span></span><br />\r\n        <span><span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.grossSalary\" ps=\":\"></span><span ng-style=\"$ctrl.getExceptionStyle($ctrl.info.totalGrossSalary.exception)\"> {{ $ctrl.info.totalGrossSalary.original | currency }}</span><span ng-if=\"$ctrl.info.totalGrossSalary.exception\"> {{ $ctrl.info.totalGrossSalary.actual | currency }}</span></span><br />\r\n        <span><span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.payrollInfo.totalPayment\" ps=\":\"></span><span ng-style=\"$ctrl.getExceptionStyle($ctrl.info.totalPayment.exception)\"> {{ $ctrl.info.totalPayment.original | currency }}</span><span ng-if=\"$ctrl.info.totalPayment.exception\"> {{ $ctrl.info.totalPayment.actual | currency }}</span></span><br />\r\n        <button type=\"button\" class=\"btn btn-xs btn-default\" ng-click=\"$ctrl.showHeader = !$ctrl.showHeader\" ><span sxy-text=\"{{$ctrl.isReadOnly ? 'SALAXY.UI_Terms.show' : 'SALAXY.UI_Terms.edit'}}\"></span> <i ng-class=\"$ctrl.isReadOnly ? 'bi bi-info-circle' : 'bi bi-pencil-fill'\"></i></button>\r\n      </div>\r\n    </div>\r\n    <div ng-if=\"'company' | sxyIsInRole\" ng-controller=\"CompanyAccountController as $company\" style=\"padding: 8px\">\r\n      <salaxy-workflow-badge ng-if=\"$company.current\" model=\"$company.current\" mode=\"horizontal\" api-ctrl=\"$company\" wf-types=\"'EmployerMessageRecord'\"></salaxy-workflow-badge>\r\n    </div>\r\n    <div ng-if=\"$ctrl.showWorkflowMessage\" style=\"margin-bottom: 4px;\">\r\n      <!-- Only shown in Accountor / Finago -->\r\n      <salaxy-textarea name=\"workflowMessage\" ng-model=\"$ctrl.workflowMessage\" placeholder=\"{{'SALAXY.NG1.PayrollComponent.payrollEdit.toolbar.workFlowMessage'}}\" rows=\"2\" label-type=\"plain\"></salaxy-textarea>\r\n    </div>\r\n  </div>\r\n  <div class=\"col ms-auto d-none d-sm-block\" ng-if=\"$ctrl.$import.isSupported && $ctrl.$import.worktimeApi.list\" style=\"max-width: 400px;\">\r\n    <button type=\"button\" class=\"btn btn-primary btn-sm pull-right\" ng-click=\"$ctrl.selectTab('ports')\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.payrollView.btnMoreInfo\"></button>\r\n    <h3 sxy-text=\"SALAXY.NG1.ImportStagingComponent.payrollView.title\" style=\"margin-top: 0\"></h3>\r\n    <table style=\"width: 100%; \">\r\n      <colgroup>\r\n        <col style=\"width: 40%;\">\r\n        <col style=\"width: 10%;\">\r\n        <col style=\"width: 40%;\">\r\n        <col style=\"width: 10%;\">\r\n      </colgroup>\r\n      <tbody>\r\n        <tr>\r\n          <td><div class=\"text-muted\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.status.preview\"></div></td>\r\n          <td class=\"right\"><div class=\"text-muted\">{{ $ctrl.$import.getTotals(\"all\").rows.preview }}</div></td>\r\n          <td style=\"padding-left: 6px;\"><div class=\"\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.list.calcCount\"></div></td>\r\n          <td class=\"right\">{{ $ctrl.$import.getTotals(\"all\").rows.count }}</td>\r\n        </tr>\r\n        <tr>\r\n          <td><div class=\"text-primary\"><b sxy-text=\"SALAXY.NG1.ImportStagingComponent.status.new\"></b></div></td>\r\n          <td ng-if=\"$ctrl.$import.getTotals('all').rows.new\" class=\"right\"><div class=\"bg-primary badge\">&nbsp;&nbsp;{{ $ctrl.$import.getTotals(\"all\").rows.new }}&nbsp;</div></td>\r\n          <td ng-if=\"!$ctrl.$import.getTotals('all').rows.new\" class=\"right\"><div class=\"text-primary\">0</div></td>\r\n          <td style=\"padding-left: 6px;\"><div class=\"\"><b sxy-text=\"SALAXY.NG1.ImportStagingComponent.status.committed\"></b></div></td>\r\n          <td class=\"right\"><b>{{ $ctrl.$import.getTotals(\"all\").rows.committed }}</b></td>\r\n        </tr>\r\n        <tr>\r\n          <td><div class=\"\"><s sxy-text=\"SALAXY.NG1.ImportStagingComponent.status.deleted\"></s></div></td>\r\n          <td class=\"right\"><s>{{ $ctrl.$import.getTotals(\"all\").rows.deleted }}</s></td>\r\n          <td style=\"padding-left: 6px;\"><div class=\"text-muted\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.status.ignored\"></div></td>\r\n          <td class=\"right\"><div class=\"text-muted\">{{ $ctrl.$import.getTotals(\"all\").rows.ignored }}</div></td>\r\n        </tr>\r\n        <tr>\r\n          <td><div class=\"text-danger\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.status.error\"></div></td>\r\n          <td ng-if=\"$ctrl.$import.getTotals('all').rows.error\" class=\"right\"><div class=\"bg-danger badge\">&nbsp;&nbsp;{{ $ctrl.$import.getTotals(\"all\").rows.error }}&nbsp;</div></td>\r\n          <td ng-if=\"!$ctrl.$import.getTotals('all').rows.error\" class=\"right\"><div class=\"text-danger\">0</div></td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/payrollV4/PayrollDetails_messages.html\",`<div ng-if=\"!$ctrl.current.info.messageThreadId\" ng-controller=\"MessageThreadCrudController as $msg\" ng-init=\"$msg.model='new'\" class=\"form-horizontal\" style=\"max-width: 600px;\">\r\n  <fieldset sxy-if-role=\"!pro\">\r\n    <p ng-if=\"!$ctrl.current.info.messageThreadId\">Tähän palkkalistaan ei liity viestiketjua / työnkulkua.</p>\r\n  </fieldset>\r\n  <fieldset sxy-if-role=\"pro\">\r\n    <legend>Lähetä yritykselle</legend>\r\n    <p>Luo tästä uusi viestiketju, jolla voit lähettää palkkalistan yritykselle hyväksyttäväksi / maksettavaksi.</p>\r\n    <salaxy-input-enum name=\"action\" label=\"Pyydetään toimintaa\" type=\"radio\" ng-model=\"$msg.current.input.todoAction\" options=\"$ctrl.messageActions\"\r\n      ng-change=\"$msg.current.title = $ctrl.getMessageTitle($msg.current.input.todoAction)\"></salaxy-input-enum>\r\n    <salaxy-input name=\"title\" label=\"SALAXY.NG1.MessageThreadComponent.title\" require=\"true\" disabled=\"!$msg.current.input.todoAction\"\r\n      ng-model=\"$msg.current.title\"></salaxy-input>\r\n    <salaxy-form-group name=\"msgSubmit\" label-type=\"empty-label\">\r\n      <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.sendPayrollMessage($msg)\">Lähetä</button>\r\n    </salaxy-form-group>\r\n  </fieldset>\r\n</div>\r\n<div class=\"container\" ng-if=\"$ctrl.current.info.messageThreadId\">\r\n  <div ng-if=\"$ctrl.isAiDemoEditable\">\r\n    <div class=\"row\">\r\n      <div class=\"col-sm-12 col-lg-12\">\r\n        <p class=\"lead\">{{\"SALAXY.NG1.PayrollDetailsMessages.payrollStatus\" | sxyTranslate}}: {{ 'PayrollStatus.' + $ctrl.current.info.status | sxyEnum }}</p>\r\n        <p sxy-text=\"SALAXY.NG1.PayrollDetailsMessages.payrollStatusDescription\"></p>\r\n        <p>\r\n          <b sxy-text=\"SALAXY.NG1.PayrollDetailsMessages.payrollStatusDescription1\"></b>\r\n        </p>\r\n        <ul>\r\n          <li sxy-text=\"SALAXY.NG1.PayrollDetailsMessages.payrollStatusDescription1Description\"></li>\r\n        </ul>\r\n        <p>\r\n          <b sxy-text=\"SALAXY.NG1.PayrollDetailsMessages.payrollStatusDescription2\"></b>\r\n        </p>\r\n        <ul>\r\n          <li sxy-text=\"SALAXY.NG1.PayrollDetailsMessages.payrollStatusDescription2Description\"></li>\r\n        </ul>\r\n        <p>\r\n          <b sxy-text=\"SALAXY.NG1.PayrollDetailsMessages.note\"></b>\r\n          <span sxy-text=\"SALAXY.NG1.PayrollDetailsMessages.payrollStatusDescription3\"></span>\r\n        </p>\r\n        <div class=\"btn-group dropdown\">\r\n          <!-- HACK: Rewrite workflow buttons as components. Or make PRO calculator a component. -->\r\n          <button class=\"btn btn-default dropdown-toggle\" type=\"button\" data-bs-toggle=\"dropdown\" aria-haspopup=\"true\" aria-expanded=\"false\" style=\"font-weight: bold;\">\r\n            <span sxy-text=\"SALAXY.NG1.PayrollDetailsMessages.setPayrollStatus\"></span>\r\n          </button>\r\n          <ul class=\"dropdown-menu\">\r\n            <li ng-class=\"{ disabled: $ctrl.current.info.status=='paymentAllowed' }\">\r\n              <a href=\"\" class=\"dropdown-item\" ng-click=\"$ctrl.current.info.status = 'paymentAllowed';$ctrl.save()\">{{ \"PayrollStatus.paymentAllowed\" | sxyEnum }}</a>\r\n            </li>\r\n            <li ng-class=\"{ disabled: $ctrl.current.info.status=='waitingPartnerApproval' }\">\r\n              <a href=\"\" class=\"dropdown-item\" ng-click=\"$ctrl.current.info.status = 'waitingPartnerApproval';$ctrl.save()\">{{ \"PayrollStatus.waitingPartnerApproval\" | sxyEnum }}</a>\r\n            </li>\r\n            <li ng-class=\"{ disabled: $ctrl.current.info.status=='waitingApproval' }\">\r\n              <a href=\"\" class=\"dropdown-item\" ng-click=\"$ctrl.current.info.status = 'waitingApproval';$ctrl.save()\">{{ \"PayrollStatus.waitingApproval\" | sxyEnum }}</a>\r\n            </li>\r\n            <li ng-class=\"{ disabled: $ctrl.current.info.status=='draft' }\">\r\n              <a href=\"\" class=\"dropdown-item\" ng-click=\"$ctrl.current.info.status = 'draft';$ctrl.save()\">{{ \"PayrollStatus.draft\" | sxyEnum }}</a>\r\n            </li>\r\n          </ul>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <p>&nbsp;</p>\r\n  <button type=\"button\" class=\"btn btn-danger float-end\" ng-click=\"$ctrl.deleteMessage($ctrl.$msg)\"><i class=\"bi bi-trash-fill\" aria-hidden=\"true\"></i></button>\r\n  <salaxy-message-thread model=\"$ctrl.current.info.messageThreadId\" ng-ref=\"$ctrl.$msg\" role=\"{{('pro' | sxyIsInRole) ? 'otherParty' : 'owner' }}\" other-party=\"'partner'\"\r\n    mark-as-read=\"5\"></salaxy-message-thread>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/payrollV4/PayrollDetails_ports.html\",`<div> \r\n  <salaxy-import-staging ng-ref=\"$ctrl.$import\" payroll=\"$ctrl.current\" payroll-calcs=\"$ctrl.calcs\"></salaxy-import-staging>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/payrollV4/PayrollDetails_reports.html\",`<div class=\"container\" ng-if=\"$ctrl.calcs.length\" ng-init=\"$ctrl.refreshReports()\">\r\n  <salaxy-calc-reports ng-if=\"$ctrl.reportCalcs.length\" calcs=\"$ctrl.reportCalcs\"  report-type=\"'salarySlip'\"></salaxy-calc-reports>\r\n</div>\r\n`);\n\n $templateCache.put(\"salaxy-components/calc/payrollV4/PayrollDetails_toolbar.html\",`<div ng-if=\"$ctrl.isReadOnly\" class=\"btn-toolbar\">\r\n  <button class=\"btn btn-secondary\" ng-if=\"$ctrl.showAction('copy')\" ng-click=\"$ctrl.showCopyAsNew($ctrl.current)\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.toolbar.copyAsNew\"></button>\r\n  <div class=\"ms-auto\">\r\n    <salaxy-pay-button ng-ref=\"$ctrl.$payButton\" ng-if=\"$ctrl.showAction('pay')\" model=\"$ctrl.current\" mode=\"pay-button\" button-class=\"float-sm-end\"\r\n      label=\"SALAXY.NG1.PayrollComponent.payrollPayButton\" \r\n      disabled=\"!$ctrl.current.info.isReadyForPayment || !$ctrl.current.input.calculations.length || !$ctrl.$payButton.isChannelDefined\" ></salaxy-pay-button>\r\n    <button ng-if=\"$ctrl.showAction('cancel') && ($ctrl.current.info.status == 'paymentStarted' && ($ctrl.current.input.paymentChannel == 'palkkausManual' || $ctrl.current.input.paymentChannel == 'talenomManual' || $ctrl.current.input.paymentChannel == 'palkkausInvoices' || $ctrl.current.input.paymentChannel == 'kitsas' || $ctrl.current.input.paymentChannel == 'palkkausPersonal' || $ctrl.current.input.paymentChannel == 'palkkausCfaPaytrail' || $ctrl.current.input.paymentChannel == 'palkkausEcfaPaytrail' || $ctrl.current.input.paymentChannel == 'palkkausCfaReference' || $ctrl.current.input.paymentChannel == 'palkkausEcfaReference' || $ctrl.current.input.paymentChannel == 'palkkausCfaFinvoice' || $ctrl.current.input.paymentChannel == 'palkkausEcfaFinvoice' ||  $ctrl.current.input.paymentChannel == 'palkkausCfaTest'))\"\r\n      class=\"btn btn-secondary  btn-labeled-right\" ng-click=\"$ctrl.cancelInvoices()\"><span sxy-text=\"SALAXY.NG1.CalcResultsComponent.cancelPaymentOrChangeChannelBtn\"></span><i\r\n        class=\"bi bi-x-circle\"></i></button>\r\n    <button ng-if=\"$ctrl.current.info.status != 'waitingApproval' && $ctrl.current.info.status != 'draft'\" class=\"btn btn-secondary btn-labeled-right\"\r\n      ng-click=\"$ctrl.showPaymentDialog()\"><span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.toolbar.showPaymentInfo\"></span><i class=\"bi bi-info-circle\"></i></button>\r\n  </div>\r\n  <button class=\"btn btn-default float-end\" ng-if=\"('partnerMessaging' | sxyIsInRole) && (!('pro' | sxyIsInRole) && $ctrl.current.info.messageThreadId )\" ng-click=\"$ctrl.selectTab('messages')\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCommentButton\"></button>\r\n</div>\r\n<div ng-if=\"!$ctrl.isReadOnly\" class=\"btn-toolbar calc-toolbar\">\r\n  <div ng-if=\"!$ctrl.isAiDemoWaitingApproval\" class=\"btn-group dropdown\">\r\n    <button type=\"button\" class=\"btn btn-labeled-left btn-primary dropdown-toggle\" data-bs-toggle=\"dropdown\" aria-haspopup=\"true\" aria-expanded=\"false\"><i class=\"bi bi-plus-lg\"></i>\r\n      <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.addCalculation\"></span>\r\n    </button>\r\n    <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"addcalculation\">\r\n      <li role=\"menuitem\">\r\n        <a ng-click=\"$ctrl.addEmployments()\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.addWorker\"></a>\r\n      </li>\r\n      <li role=\"menuitem\">\r\n        <a ng-click=\"$ctrl.addCalcs('draft')\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.addDraft\"></a>\r\n      </li>\r\n      <li role=\"menuitem\">\r\n        <a ng-click=\"$ctrl.addCalcs('shared')\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.addShared\"></a>\r\n      </li>\r\n      <li role=\"menuitem\">\r\n        <a ng-click=\"$ctrl.addCalcs('draft', true, true, true)\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.mergeDraft\"></a>\r\n      </li>\r\n      <li role=\"menuitem\">\r\n        <a ng-click=\"$ctrl.addCalcs('shared', true, true, true)\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.mergeShared\"></a>\r\n      </li>\r\n      <li role=\"menuitem\">\r\n        <a ng-click=\"$ctrl.addCalcs('paid')\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.addCopy\"></a>\r\n      </li>\r\n      <li role=\"menuitem\">\r\n        <a ng-click=\"$ctrl.mergePayroll(true, true)\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollCalcs.toolbar.addPayroll\"></a>\r\n      </li>\r\n    </ul>\r\n  </div>\r\n  <div ng-if=\"!$ctrl.isAiDemoWaitingApproval\" class=\"btn-group dropdown ms-1\" >\r\n    <button type=\"button\" class=\"btn btn-secondary dropdown-toggle\" data-bs-toggle=\"dropdown\" aria-haspopup=\"true\" aria-expanded=\"false\">\r\n      <span sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.toolbar.options\"></span>\r\n    </button>\r\n    <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"actions\">\r\n      <li role=\"menuitem\">\r\n        <a ng-click=\"$ctrl.importEmploymentDataAll()\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.toolbar.importEmploymentCalc\"></a>\r\n      </li>\r\n      <li role=\"menuitem\" salaxy-if-role=\"test\">\r\n        <a ng-click=\"$ctrl.addSalaryDefaultsToAllCalcs()\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.toolbar.addSalaryDefaults\"></a>\r\n      </li>\r\n      <li role=\"menuitem\">\r\n        <a ng-click=\"$ctrl.showCopyAsNew($ctrl.current)\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.toolbar.copyAsNew\"></a>\r\n      </li>\r\n      <li role=\"menuitem\">\r\n        <a ng-click=\"$ctrl.delete()\" class=\"text-danger dropdown-item\" sxy-text=\"SALAXY.NG1.PayrollComponent.payrollEdit.toolbar.delete\"></a>\r\n      </li>\r\n    </ul>\r\n  </div>\r\n  <div sxy-if-role=\"pro\" class=\"btn-group\">\r\n    <div class=\"btn-group align-items-center ms-1 dropdown\">\r\n      <!-- HACK: Rewrite workflow buttons as components. Or make PRO calculator a component. -->\r\n      <button class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\" type=\"button\" aria-haspopup=\"true\" aria-expanded=\"false\" style=\"font-weight: bold;\">\r\n        {{ \"PayrollStatus.\" + $ctrl.current.info.status | sxyEnum }}\r\n      </button>\r\n      <ul class=\"dropdown-menu\" role=\"menu\">\r\n        <li ng-class=\"{ disabled: $ctrl.current.info.status=='draft' }\">\r\n          <a href=\"\" ng-click=\"$ctrl.current.info.status = 'draft';$ctrl.save()\" class=\"dropdown-item\">{{ \"PayrollStatus.draft\" | sxyEnum }}</a>\r\n        </li>\r\n        <li ng-class=\"{ disabled: $ctrl.current.info.status=='template' }\">\r\n          <a href=\"\" ng-click=\"$ctrl.current.info.status = 'template';$ctrl.save()\" class=\"dropdown-item\">{{ \"PayrollStatus.template\" | sxyEnum }}</a>\r\n        </li>\r\n        <li ng-class=\"{ disabled: $ctrl.current.info.status=='handled' }\">\r\n          <a href=\"\" ng-click=\"$ctrl.current.info.status = 'handled';$ctrl.save()\" class=\"dropdown-item\">{{ \"PayrollStatus.handled\" | sxyEnum }}</a>\r\n        </li>\r\n        <li ng-class=\"{ disabled: $ctrl.current.info.status=='waitingApproval' }\">\r\n          <a href=\"\" ng-click=\"$ctrl.current.info.status = 'waitingApproval';$ctrl.save()\" class=\"dropdown-item\">{{ \"PayrollStatus.waitingApproval\" | sxyEnum }}</a>\r\n        </li>\r\n        <li ng-class=\"{ disabled: $ctrl.current.info.status=='waitingPartnerApproval' }\">\r\n          <a href=\"\" ng-click=\"$ctrl.current.info.status = 'waitingPartnerApproval';$ctrl.save()\" class=\"dropdown-item\">{{ \"PayrollStatus.waitingPartnerApproval\" | sxyEnum }}</a>\r\n        </li>\r\n        <li ng-class=\"{ disabled: $ctrl.current.info.status=='paymentAllowed' }\">\r\n          <a href=\"\" ng-click=\"$ctrl.current.info.status = 'paymentAllowed';$ctrl.save()\" class=\"dropdown-item\">{{ \"PayrollStatus.paymentAllowed\" | sxyEnum }}</a>\r\n        </li>\r\n      </ul>\r\n    </div>\r\n    <salaxy-workflow-buttons api-ctrl=\"$ctrl\"></salaxy-workflow-buttons>\r\n  </div>\r\n  <div class=\"btn-group ms-auto\">\r\n    <button class=\"btn btn-primary float-end\" ng-if=\"$ctrl.isAiDemoWaitingApproval\" ng-click=\"$ctrl.showAiDemoApproval()\" sxy-text=\"Hyväksy\"></button>\r\n    <salaxy-pay-button ng-ref=\"$ctrl.$payButton\" ng-if=\"!$ctrl.isAiDemoWaitingApproval && $ctrl.current.info.status != 'template'\" model=\"$ctrl.current\" mode=\"pay-button\" button-class=\"float-sm-end\"\r\n      label=\"SALAXY.NG1.PayrollComponent.payrollPayButton\" \r\n      disabled=\"!$ctrl.current.info.isReadyForPayment || !$ctrl.current.input.calculations.length || !$ctrl.$payButton.isChannelDefined\" ></salaxy-pay-button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/rows/CalcIrRows.html\",`<div class=\"salaxy-calc-ir-rows salaxy-component\">\r\n  <table class=\"table\">\r\n    <thead>\r\n      <tr>\r\n        <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.headerIrCode\"></th>\r\n        <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.headerRowDescription\"></th>\r\n        <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.headerCalc\" class=\"right\"></th>\r\n        <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.headerSum\" class=\"right\"></th>\r\n        <th></th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat=\"row in $ctrl.irRows\">\r\n        <td>\r\n          <div class=\"d-flex\">\r\n            <salaxy-avatar class=\"salaxy-calc-row-type-avatar\" avatar=\"{ color: '#2b507c', initials: row.irData.code, entityType: 'company' }\"></salaxy-avatar>\r\n            <div class=\"flex-column\">\r\n              <b>{{ $ctrl.getIncomeType(row).label }}</b><br />\r\n              <small>\r\n                <div class=\"truncate\" style=\"max-width: 250px;\">\r\n                  {{$ctrl.getIncomeType(row).description}}\r\n                </div>\r\n              </small>\r\n            </div>\r\n          </div>\r\n        </td>\r\n        <td>{{ row.message }}</td>\r\n        <td class=\"right\">\r\n          <span ng-if=\"row.unit != 'one'\">\r\n            {{ row.count | sxyCount : row.unit }} *\r\n          </span> {{ row.price | currency }} =\r\n        </td>\r\n        <td class=\"right\">{{ row.total | currency }}\r\n        </td>\r\n        <td class=\"salaxy-calc-rows-editor-btns\" ng-if=\"row.type=='manual'\">\r\n          <button type=\"button\" class=\"edit btn btn-info\" ng-click=\"$ctrl.setCurrentIrRow(row)\"><i class=\"bi bi-pencil-square\"></i></button>\r\n          <button type=\"button\" class=\"delete btn btn-danger\" ng-click=\"$ctrl.deleteIrRow(row)\"><i class=\"bi bi-trash-fill\"></i></button>\r\n        </td>\r\n        <td class=\"salaxy-calc-rows-editor-btns\" ng-if=\"row.type!='manual'\">\r\n          <button type=\"button\" class=\"edit btn btn-info\" ng-click=\"$ctrl.setCurrentIrRow(row)\"><i class=\"bi bi-info-circle\"></i></button>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n    <tfoot ng-if=\"!$ctrl.isReadOnly\">\r\n      <tr>\r\n        <th colspan=\"6\" class=\"text-end\">\r\n          <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.recalculate()\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.updateCalc\"></button>\r\n          <button type=\"button\" class=\"btn btn-info\" ng-click=\"$ctrl.addIrRow()\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.addNewRow\"></button>\r\n        </th>\r\n      </tr>\r\n    </tfoot>\r\n  </table>\r\n  <h4 sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.chosenRowInfo\"></h4>\r\n  <div ng-if=\"!$ctrl.currentRow\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.chooseRowOrAddNew\"></div>\r\n  <salaxy-tab-buttons\r\n    ng-if=\"$ctrl.currentRow\"\r\n    current-tab=\"$ctrl.currentTab\"\r\n    options=\"[\r\n      { value: 'irbasic', text: 'SALAXY.NG1.CalcRowsComponent.irRows.basicInfo' },\r\n      { value: 'irincometype', text: 'SALAXY.NG1.CalcRowsComponent.irRows.irFlagsInfo' },\r\n      { value: 'irsidecosts', text: 'SALAXY.NG1.CalcRowsComponent.irRows.taxAndSideCosts' },\r\n      { value: 'irjson', text: 'JSON' }\r\n    ]\"\r\n    tabs-id=\"calcIrRows\">\r\n  </salaxy-tab-buttons>\r\n  <div class=\"tab-content\" id=\"tab-content-calcIrRows\">\r\n    <div class=\"tab-pane\" id=\"irbasic-tab\">\r\n      <div class=\"form-horizontal\">\r\n        <div class=\"row\">\r\n          <div class=\"col col-md-12 col-lg-6\">\r\n            <h2 sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.textAndType\"></h2>\r\n            <salaxy-input-income-type name=\"code\" ng-model=\"$ctrl.currentRow.irData.code\" hidden-codes=\"[1]\" label=\"SALAXY.NG1.CalcRowsComponent.irRows.typeLabel\" disabled=\"$ctrl.isIrRowReadOnly\" ng-change=\"$ctrl.updateCurrentRowType()\">\r\n            </salaxy-input-income-type>\r\n            <salaxy-input name=\"message\" ng-model=\"$ctrl.currentRow.message\" label=\"SALAXY.NG1.CalcRowsComponent.irRows.messageLabel\" disabled=\"$ctrl.isIrRowReadOnly\"></salaxy-input>\r\n            <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.irRows.groupingLabel\" disabled=\"$ctrl.isIrRowReadOnly\"\r\n              options=\"$ctrl.groupingOptions\"\r\n              name=\"calcGrouping\" ng-model=\"$ctrl.currentRow.calcData.grouping\" type=\"select\"></salaxy-input-enum>\r\n            <salaxy-form-group label=\"SALAXY.NG1.CalcRowsComponent.irRows.creditTransferLabel\" name=\"paymentDefault\">\r\n              <div ng-if=\"$ctrl.currentRowType.paymentDefault == 1\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.payment\"></div>\r\n              <div ng-if=\"$ctrl.currentRowType.paymentDefault == -1\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.deduction\"></div>\r\n              <div ng-if=\"$ctrl.currentRowType.paymentDefault == 0\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.noPayment\"></div>\r\n            </salaxy-form-group>\r\n          </div>\r\n          <div class=\"col col-md-12 col-lg-6\">\r\n            <h2 sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.calc\"></h2>\r\n            <salaxy-input-number name=\"count\" ng-model=\"$ctrl.currentRow.count\" disabled=\"$ctrl.isIrRowReadOnly\" label=\"SALAXY.NG1.CalcRowsComponent.irRows.countLabel\"></salaxy-input-number>\r\n            <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.irRows.unitLabel\" enum=\"Unit\" name=\"Unit\" disabled=\"$ctrl.isIrRowReadOnly\" ng-model=\"$ctrl.currentRow.unit\" type=\"select\"></salaxy-input-enum>\r\n            <salaxy-input-number name=\"price\" ng-model=\"$ctrl.currentRow.price\" disabled=\"$ctrl.isIrRowReadOnly\" label=\"SALAXY.NG1.CalcRowsComponent.irRows.priceLabel\"></salaxy-input-number>\r\n            <salaxy-form-group name=\"total\" label=\"SALAXY.NG1.CalcRowsComponent.irRows.totalLabel\">\r\n              <p>{{ $ctrl.currentRow.count * $ctrl.currentRow.price | currency }}</p>\r\n            </salaxy-form-group>\r\n          </div>\r\n          <div class=\"col col-md-12 col-lg-6\" ng-if=\"$ctrl.currentRow.irData.code == 304\">\r\n            <h2 sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.carBenefitInfo\"></h2>\r\n            <p sxy-html=\"SALAXY.NG1.CalcRowsComponent.irRows.carBenefitInfoHtml\"></p>\r\n            <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.irRows.carBenefitTypeLabel\" disabled=\"$ctrl.isIrRowReadOnly\" enum=\"CarBenefitCode\" name=\"carBenefitCode\"\r\n              ng-model=\"$ctrl.currentRow.irData.carBenefit.carBenefitCode\" disabled=\"$ctrl.isIrRowReadOnly\" type=\"select\"></salaxy-input-enum>\r\n            <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.irRows.carBenefitAgeGroupLabel\" enum=\"AgeGroupCode\" name=\"ageGroupCode\" disabled=\"$ctrl.isIrRowReadOnly\" ng-model=\"$ctrl.currentRow.irData.carBenefit.ageGroupCode\" type=\"select\">\r\n            </salaxy-input-enum>\r\n            <salaxy-input-number label=\"SALAXY.NG1.CalcRowsComponent.irRows.carBenefitEmissionsValueLabel\" name=\"emissionsValue\" disabled=\"$ctrl.isIrRowReadOnly\" minimum=\"0\" maximum=\"100\" ng-model=\"$ctrl.currentRow.irData.carBenefit.emissionsValue\">\r\n            </salaxy-input-number>\r\n            <salaxy-input-number label=\"SALAXY.NG1.CalcRowsComponent.irRows.carBenefitKilometersLabel\" name=\"kilometers\" disabled=\"$ctrl.isIrRowReadOnly\" ng-model=\"$ctrl.currentRow.irData.carBenefit.kilometers\">\r\n            </salaxy-input-number>\r\n          </div>\r\n          <div class=\"col col-md-12 col-lg-6\" ng-if=\"$ctrl.currentRow.irData.code == 331\">\r\n            <h2 sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.dailyAllowanceAdditionalSelections\"></h2>\r\n            <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.irRows.dailyAllowanceTypeLabel\" disabled=\"$ctrl.isIrRowReadOnly\" enum=\"AllowanceCode\" name=\"dailyAllowance\" type=\"multi-select\"\r\n              ng-model=\"$ctrl.currentRow.irData.dailyAllowance\"></salaxy-input-enum>\r\n          </div>\r\n          <div class=\"col col-md-12 col-lg-6\" ng-if=\"$ctrl.currentRow.irData.code == 334\">\r\n\r\n            <h2 sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.mealBenefitAdditionalSelections\"></h2>\r\n            <p sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.mealBenefitTaxInfo\"></p>\r\n\r\n            <salaxy-input-boolean type=\"checkbox\" name=\"mealBenefitIsTaxValue\" ng-model=\"$ctrl.currentRow.irData.mealBenefitIsTaxValue\" label-type=\"plain\"\r\n              label-true=\"SALAXY.NG1.CalcRowsComponent.irRows.mealBenefitIsTaxValueLabel\" disabled=\"$ctrl.isIrRowReadOnly\"></salaxy-input-boolean>\r\n\r\n          </div>\r\n        </div>\r\n        <div class=\"text-end\" ng-if=\"!$ctrl.isIrRowReadOnly\">\r\n          <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.recalculate()\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.updateCalc\"></button>\r\n          <button type=\"button\" class=\"btn btn-info\" ng-click=\"$ctrl.addIrRow()\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.addNewRow\"></button>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"irincometype-tab\">\r\n      <div class=\"form-horizontal\">\r\n        <h2>{{ $ctrl.currentRowType.label }} ({{ $ctrl.currentRowType.code }})</h2>\r\n        <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.irRows.irFlagsLabel\" enum=\"IrFlags\" name=\"flags\" type=\"multi-select\" disabled=\"$ctrl.isIrRowReadOnly\" ng-model=\"$ctrl.currentRow.irData.flags\">\r\n        </salaxy-input-enum>\r\n        <salaxy-form-group label=\"SALAXY.NG1.CalcRowsComponent.irRows.negativeSupportedLabel\" name=\"isNegativeSupported\">\r\n          <div ng-if=\"$ctrl.currentRowType.isNegativeSupported\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.allowed\"></div>\r\n          <div ng-if=\"!$ctrl.currentRowType.isNegativeSupported\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.notAllowed\"></div>\r\n        </salaxy-form-group>\r\n        <div style=\"white-space: pre-wrap\">{{ $ctrl.currentRowType.description }}</div>\r\n\r\n        <h2 sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.earningPeriod\"></h2>\r\n        <p sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.earningPeriodInfo\"></p>\r\n        <salaxy-datepicker-popup name=\"startDate\" disabled=\"$ctrl.isIrRowReadOnly\" label=\"SALAXY.NG1.CalcRowsComponent.irRows.earningPeriodStartDateLabel\" ng-model=\"$ctrl.currentRow.earningPeriod.start\"></salaxy-datepicker-popup>\r\n        <salaxy-datepicker-popup name=\"endDate\" disabled=\"$ctrl.isIrRowReadOnly\" label=\"SALAXY.NG1.CalcRowsComponent.irRows.earningPeriodEndDateLabel\" ng-model=\"$ctrl.currentRow.earningPeriod.end\"></salaxy-datepicker-popup>\r\n      </div>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"irsidecosts-tab\">\r\n      <div class=\"form-horizontal\">\r\n        <h2>{{ $ctrl.currentRowType.label }}</h2>\r\n        <div style=\"white-space: pre-wrap\">{{ $ctrl.currentRowType.taxAndSidecostsDescr }}</div>\r\n        <table class=\"table\">\r\n          <tbody>\r\n            <tr>\r\n              <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.tax\"></th>\r\n              <td>\r\n                <div ng-if=\"$ctrl.currentRowType.taxDefault == 1\" class=\"text-success\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.withheld\"></div>\r\n                <div ng-if=\"$ctrl.currentRowType.taxDefault == -1\" class=\"text-warning\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.deductionAlt\"></div>\r\n                <div ng-if=\"$ctrl.currentRowType.taxDefault == 0\" class=\"text-danger\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.notwithheld\"></div>\r\n              </td>\r\n              <td></td>\r\n            </tr>\r\n            <tr>\r\n              <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.socialSecurityPayment\"></th><th sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.socialSecurityPayment\">\r\n              <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.toBePaid\"></th>\r\n              <th>\r\n                <!-- TODO: Lisää tähän srakkeeseen tieto poikkeuksen jälkeen-->\r\n              </th>\r\n            </tr>\r\n            <tr>\r\n              <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.occupationPension\"></th>\r\n              <td>\r\n                <span ng-class=\"$ctrl.currentRowType.pensionInsurance ? 'text-success' : 'text-danger'\">\r\n                  {{ $ctrl.currentRowType.pensionInsurance ? (\"SALAXY.UI_Terms.yes\" | sxyTranslate) : (\"SALAXY.UI_Terms.no\" | sxyTranslate) }}\r\n                </span>\r\n              </td>\r\n              <td>\r\n              </td>\r\n            </tr>\r\n            <tr>\r\n              <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.insurancePayment\"></th>\r\n              <td>\r\n                <span ng-class=\"$ctrl.currentRowType.accidentInsurance ? 'text-success' : 'text-danger'\">\r\n                  {{ $ctrl.currentRowType.accidentInsurance ? (\"SALAXY.UI_Terms.yes\" | sxyTranslate) : (\"SALAXY.UI_Terms.no\" | sxyTranslate) }}\r\n                </span>\r\n              </td>\r\n              <td></td>\r\n            </tr>\r\n            <tr>\r\n              <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.unemploymentInsurancePayment\"></th>\r\n              <td>\r\n                <span ng-class=\"$ctrl.currentRowType.unemploymentInsurance ? 'text-success' : 'text-danger'\">\r\n                  {{ $ctrl.currentRowType.unemploymentInsurance ? (\"SALAXY.UI_Terms.yes\" | sxyTranslate) : (\"SALAXY.UI_Terms.no\" | sxyTranslate) }}\r\n                </span>\r\n              </td>\r\n              <td></td>\r\n            </tr>\r\n            <tr>\r\n              <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.healtInsurancePayment\"></th>\r\n              <td>\r\n                <span ng-class=\"$ctrl.currentRowType.healthInsurance ? 'text-success' : 'text-danger'\">\r\n                  {{ $ctrl.currentRowType.healthInsurance ? (\"SALAXY.UI_Terms.yes\" | sxyTranslate) : (\"SALAXY.UI_Terms.no\" | sxyTranslate) }}\r\n                </span>\r\n              </td>\r\n              <td></td>\r\n            </tr>\r\n          </tbody>\r\n        </table>\r\n        <div ng-if=\"!$ctrl.currentRowType.insuranceInformationAllowed\">\r\n          <p sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.insuranceInformationAllowed\"></p>\r\n        </div>\r\n        <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.irRows.IrInsuranceExceptions\" enum=\"IrInsuranceExceptions\" name=\"dailyAllowance\" disabled=\"$ctrl.isIrRowReadOnly\"\r\n          ng-if=\"$ctrl.currentRowType.insuranceInformationAllowed\" ng-model=\"$ctrl.currentRow.irData.insuranceExceptions\" type=\"multi-select\"></salaxy-input-enum>\r\n      </div>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"irjson-tab\">\r\n      <salaxy-json-formatter json=\"$ctrl.currentRow\" open=\"2\"></salaxy-json-formatter>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/rows/CalcRowCostAccounting.html\",`<div class=\"salaxy-component salaxy-calc-cost-accounting\">\r\n  <div ng-if=\"$ctrl.isLegacy\">\r\n    <fieldset>\r\n      <legend sxy-text=\"SALAXY.NG1.CalcCostAccountingComponent.title\"></legend>\r\n      <table class=\"table\">\r\n        <thead>\r\n          <tr>\r\n            <th>{{('SALAXY.NG1.CalcCostAccountingComponent.defaultLabel') | sxyTranslate}}</th>\r\n            <th class=\"right\">{{\"SALAXY.NG1.CalcCostAccountingComponent.percent\" | sxyTranslate}}</th>\r\n            <th class=\"right\">\r\n              <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-if=\"!$ctrl.isReadOnly\" ng-click=\"$ctrl.costCenter.push({})\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n            </th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr ng-repeat=\"item in $ctrl.costCenter\">\r\n            <td>\r\n              <salaxy-input-typeahead ng-if=\"$ctrl.getOptions('costCenter').length\" ng-model=\"item.id\" label-format=\"text-value\"\r\n                options=\"$ctrl.getOptions('costCenter')\" name=\"{{ 'id' + $index }}\" label-type=\"plain\" read-only=\"$ctrl.isReadOnly\"></salaxy-input-typeahead>\r\n              <salaxy-input ng-if=\"!$ctrl.getOptions('costCenter').length\" ng-model=\"item.id\" name=\"{{ 'id' + $index }}\" label-type=\"plain\" read-only=\"$ctrl.isReadOnly\">\r\n              </salaxy-input>\r\n            </td>\r\n            <td>\r\n              <salaxy-input-number ng-model=\"item.percent\" name=\"{{ 'percent' + $index }}\" label-type=\"plain\" read-only=\"$ctrl.isReadOnly\" unit=\"percent\"></salaxy-input-number>\r\n            </td>\r\n            <td class=\"text-end\" >\r\n              <button ng-if=\"!$ctrl.isReadOnly\" type=\"button\" class=\"btn btn-danger\" ng-click=\"$ctrl.costCenter.splice($index, 1)\">\r\n                <i class=\"bi bi-trash\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\"></i>\r\n              </button>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n        <tfoot>\r\n          <tr class=\"total\">\r\n            <td>{{\"SALAXY.UI_Terms.total\" | sxyTranslate}}</td>\r\n            <td class=\"right\">{{ $ctrl.getLegacySum() | sxyCount : 'percent' }}</td>\r\n            <td class=\"right\"></td>\r\n          </tr>\r\n        </tfoot>\r\n      </table>\r\n    </fieldset>\r\n  </div>\r\n  <div ng-if=\"!$ctrl.isLegacy && ($ctrl.row.accounting.dimensions.length > 0 || $ctrl.definitions.length > 0)\">\r\n    <salaxy-cost-accounting ng-init=\"$ctrl.row.accounting = ($ctrl.row.accounting || $ctrl.isReadOnly)  ? $ctrl.row.accounting : { dimensions: []}\" current=\"$ctrl.row.accounting.dimensions\" inherited=\"$ctrl.calc.accounting.dimensions\" scope=\"row\" dimensions=\"$ctrl.dimensions\" read-only=\"$ctrl.isReadOnly\" ></salaxy-cost-accounting>\r\n  </div>\r\n \r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/rows/CalcRowDimensionInput.html\",`<div class=\"d-flex\">\r\n  <salaxy-input-typeahead \r\n    class=\"text-muted flex-grow-1\" \r\n    style=\"flex-grow: 1;\"\r\n    ng-if=\"$ctrl.isInherited() && $ctrl.hasOptions() && !$ctrl.isCostSharingEnabled()\" \r\n    label-type=\"plain\"\r\n    ng-model=\"$ctrl.getInheritedSingleValue().value\"\r\n    label-format=\"text-value\" \r\n    options=\"$ctrl.getOptions()\" \r\n    name=\"single\" \r\n    read-only=\"true\"\r\n    placeholder=\"{{ 'SALAXY.UI_Terms.notChosen' | sxyTranslate }}\">\r\n  </salaxy-input-typeahead>\r\n  <salaxy-input \r\n    class=\"text-muted flex-grow-1\"\r\n    style=\"flex-grow: 1;\"\r\n    ng-if=\"$ctrl.isInherited() && !$ctrl.hasOptions() && !$ctrl.isCostSharingEnabled()\"\r\n    label-type=\"plain\"\r\n    ng-model=\"$ctrl.getInheritedSingleValue().value\"\r\n    name=\"single\"\r\n    read-only=\"true\">\r\n  </salaxy-input>\r\n  <salaxy-input-typeahead \r\n    class=\"flex-grow-1\"\r\n    ng-if=\"!$ctrl.isInherited() && $ctrl.hasOptions() && !$ctrl.isCostSharingEnabled()\"\r\n    label-type=\"plain\"\r\n    ng-model=\"$ctrl.getSingleValue().value\"\r\n    ng-change=\"$ctrl.setSingleValue($ctrl.getSingleValue().value)\"\r\n    label-format=\"text-value\"\r\n    options=\"$ctrl.getOptions()\"\r\n    name=\"single\"\r\n    read-only=\"$ctrl.readOnly\"\r\n    placeholder=\"{{ 'SALAXY.UI_Terms.notChosen' | sxyTranslate }}\">\r\n  </salaxy-input-typeahead>\r\n  <salaxy-input\r\n    class=\"flex-grow-1\"\r\n    ng-if=\"!$ctrl.isInherited() && !$ctrl.hasOptions() && !$ctrl.isCostSharingEnabled()\"\r\n    style=\"flex-grow: 1;\"\r\n    label-type=\"plain\"\r\n    ng-model=\"$ctrl.getSingleValue().value\" \r\n    ng-change=\"$ctrl.setSingleValue($ctrl.getSingleValue().value)\"\r\n    name=\"single\"\r\n    read-only=\"$ctrl.readOnly\">\r\n  </salaxy-input>\r\n  <i ng-if=\"!$ctrl.readOnly && $ctrl.isInherited() && !$ctrl.isCostSharingEnabled()\" ng-click=\"$ctrl.setSingleValue($ctrl.getInheritedSingleValue().value)\" class=\"btn bi bi-pencil-fill clickable\"></i>\r\n  <table ng-if=\"$ctrl.isCostSharingEnabled()\" class=\"text-small\">\r\n    <tbody>\r\n      <tr ng-repeat=\"costCenter in $ctrl.getCostSharingValues()\" ng-class=\"$ctrl.isInherited() ? 'text-muted' : ''\" class=\"\" style=\"line-height: 0.9em;\">\r\n        <td>{{costCenter.text}}</td>\r\n        <td>{{costCenter.value | sxyCount: 'percent'}}</td>\r\n      </tr>    \r\n    </tbody>\r\n  </table>\r\n</div>\r\n`);\n\n $templateCache.put(\"salaxy-components/calc/rows/CalcRowDocumentation.html\",`<div ng-if=\"!$ctrl.showLoader()\">\r\n  <fieldset>\r\n    <legend>\r\n      <span>{{$ctrl.example.description}}</span>\r\n    </legend>\r\n    <salaxy-input-typeahead ng-if=\"$ctrl.row.config.kind.name\" name=\"kind\" label-type=\"horizontal\" label=\"Kind for row\" ng-change=\"$ctrl.generateExampleLocally()\" ng-model=\"$ctrl.selectedKind\" enum=\"{{$ctrl.row.config.kind.name}}\" ></salaxy-input-typeahead>\r\n  </fieldset>\r\n  <div ng-if=\"$ctrl.exampleSamples.length > 0\">\r\n    <salaxy-tab-buttons\r\n      current-tab=\"$ctrl.currentTab\"\r\n      options=\"$ctrl.tabOptions\"\r\n      tabs-id=\"calcRowDocumentation\">\r\n    </salaxy-tab-buttons>\r\n    <div class=\"tab-content\" id=\"tab-content-calcRowDocumentation\">\r\n      <div ng-repeat=\"sample in $ctrl.exampleSamples track by $index\" class=\"tab-pane\" id=\"tab{{ $index + 1 }}-tab\">\r\n        <p>{{sample.description}}</p>\r\n        <sxy-code-editor ng-model=\"sample.code\" editor=\"sample\"></sxy-code-editor>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>\r\n<div ng-if=\"$ctrl.showLoader()\">\r\n  <salaxy-spinner></salaxy-spinner>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/rows/CalcRowFormula.html\",`<div>\r\n  <div ng-if=\"!$ctrl.editingScript\">\r\n    <div class=\"row\">\r\n      <div class=\"col-md-6\">\r\n        <salaxy-input-enum ng-model=\"$ctrl.selectedScriptName\" options=\"$ctrl.scriptNames\" name=\"scriptName\" label=\"Laskukaavat\" label-type=\"plain\"></salaxy-input-enum>\r\n      </div>\r\n      <div class=\"col-md-6\">\r\n        <button class=\"btn btn-primary\" ng-click=\"$ctrl.addScript()\" ng-disabled=\"$ctrl.selectedScriptAdded\">Lisää laskukaava</button>\r\n      </div>\r\n    </div>\r\n    <table style=\"margin-top: 10px;\">\r\n      <thead>\r\n        <tr>\r\n          <th width=\"20%\">Nimi</th>\r\n          <th width=\"20%\">Kuvaus</th>\r\n          <th width=\"50%\">Kaava</th>\r\n          <th width=\"10%\"></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"prop in $ctrl.row.config.scripts\">\r\n          <td width=\"20%\">{{ prop.name }}</td>\r\n          <td width=\"20%\">{{ $ctrl.getDescription(prop.name) }}</td>\r\n          <td width=\"50%\">\r\n            <textarea class=\"form-control\" style=\"width: 100%; height: 48px;\" ng-model=\"prop.script\" readonly></textarea>\r\n          </td>\r\n          <td width=\"10%\">\r\n            <button type=\"button\" class=\"edit btn btn-info btn-sm\" ng-click=\"$ctrl.editScript(prop)\"\r\n              title=\"{{'SALAXY.NG1.CalcRowsComponent.editor.buttons.infoIcon' | sxyTranslate}}\"><i class=\"bi bi-pencil-fill\"></i></button>\r\n            <button type=\"button\" class=\"delete btn btn-danger btn-sm\" ng-click=\"$ctrl.removeScript(prop)\"\r\n              title=\"{{'SALAXY.NG1.CalcRowsComponent.editor.buttons.infoIcon' | sxyTranslate}}\"><i class=\"bi bi-trash-fill\"></i></button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <div ng-if=\"$ctrl.editingScript\">\r\n    <div class=\"row\" ng-if=\"!$ctrl.selectedCalc\">\r\n      <div class=\"col d-flex justify-content-start gap-2\">\r\n        <button ng-click=\"$ctrl.addExistingCalc()\"  class=\"btn btn-default\" sxy-text=\"Lisää laskelma...\"></button>\r\n      </div>\r\n    </div>\r\n    <div class=\"row\">\r\n      <div class=\"col-md-12\">\r\n        <div class=\"table-responsive\" ng-if=\"$ctrl.selectedCalc\">    \r\n          <table class=\"table\">\r\n            <tbody>\r\n              <tr>\r\n                <td class=\"td-avatar hidden-xxs middle\">\r\n                  <salaxy-avatar avatar=\"$ctrl.selectedCalc.worker.avatar\"></salaxy-avatar>\r\n                </td>\r\n                <td class=\"td-name hidden-xxs middle\">\r\n                  <strong>{{$ctrl.selectedCalc.worker.avatar.displayName}}</strong><br />\r\n                </td>\r\n                <td class=\"hidden-xxs middle\">\r\n                  {{ $ctrl.selectedCalc.workflow.status ? (\"SALAXY.ENUM.CalculationStatus.\" + $ctrl.selectedCalc.workflow.status + \".label\" | sxyTranslate) : \"#ERR\" }}<br /> {{ $ctrl.selectedCalc.workflow.salaryDate | date }}\r\n                </td>\r\n                <td class=\"right hidden-xxs middle\">\r\n                  {{ $ctrl.selectedCalc.result.totals.totalGrossSalary | currency }}\r\n                </td>\r\n                <td>\r\n                  <a class=\"btn btn-secondary btn-sm\"  target=\"_blank\" ng-href=\"#/calc/details/{{$ctrl.selectedCalc.id}}\">\r\n                    Avaa laskelma\r\n                </td>\r\n                <td class=\"right middle\">\r\n                  <button class=\"btn btn-sm btn-danger\" type=\"button\" ng-click=\"$ctrl.selectedCalc = undefined;$ctrl.selectedEmployment = undefined;\">\r\n                    <i class=\"bi bi-x-circle\"></i>\r\n                  </button>\r\n                </td>\r\n                \r\n              </tr>\r\n            </tbody>    \r\n          </table>\r\n        </div>\r\n      </div>\r\n      <div ng-if=\"$ctrl.selectedCalc\">\r\n        <salaxy-calc-rows-2019-editor parent=\"$ctrl.selectedCalc\" title=\"{{'SALAXY.NG1.PayrollComponent.payrollCalcs.calcRowEditor.title' | sxyTranslate}}\" mode=\"edit\" show-edit-buttons=\"true\"></salaxy-calc-rows-2019-editor>\r\n      </div>\r\n      <hr>\r\n      <div ng-if=\"$ctrl.selectedEmployment\">\r\n        <div class=\"float-end\">\r\n          <salaxy-json-formatter key=\"'Debug'\" sxy-if-role=\"test\" json=\"$ctrl.selectedEmployment.work.salaryDefaults\" open=\"1\" type=\"dialog\"></salaxy-json-formatter>\r\n        </div>\r\n        <p>Oletuspalkkarivit kopioidaan uudelle laskelmalle sellaisenaan. Päivämäärärajaukset huomioidaan vain tuntien sisääntuonnissa.</p>  \r\n        <salaxy-calc-rows-editor rows=\"$ctrl.selectedEmployment.work.salaryDefaults\" row-sources=\"thisproperty will be removed, just a marker until refactoring\"\r\n          title=\"{{ 'SALAXY.NG1.WorkerDetailsComponent.defaultCalcRows' | sxyTranslate }}\" type=\"salary-defaults-temp2\" mode=\"edit\"></salaxy-calc-rows-editor>\r\n        <hr>\r\n        <p>Hintoja käytetään tällä hetkellä tuntien sisään tuonnissa. Myöhemmissä versioissa oletushintoja käytetään myös laskurissa.</p>\r\n        <salaxy-row-types-settings ng-ref=\"$ctrl.$prices\" mode=\"prices\" model=\"$ctrl.selectedEmployment\"></salaxy-row-types-settings>\r\n      </div>\r\n    </div>\r\n    <sxy-code-editor ng-model=\"$ctrl.editingScript.script\" editor=\"formula\"></sxy-code-editor>\r\n    <div class=\"row\">\r\n      <div class=\"col-md-6\">\r\n        <button class=\"btn btn-primary\" ng-disabled=\"!$ctrl.isScriptEvaluatable()\" ng-click=\"$ctrl.evaluateEditingScript()\">Testaa kaava</button>\r\n      </div>      \r\n      <div class=\"col-md-6\">\r\n        <button class=\"btn btn-default\" ng-click=\"$ctrl.editScript(undefined)\">Sulje kaavan muokkaus</button>\r\n      </div>\r\n    </div>\r\n    <div class=\"row\" ng-if=\"$ctrl.evalResult\">\r\n      <div class=\"col-md-12\">\r\n        <span>Kaavan tulos:</span><pre>{{$ctrl.evalResult}}</pre>\r\n      </div>\r\n    </div>\r\n    \r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/rows/CalcRows2019EditDialog-irIncomeType.html\",`<salaxy-tab-buttons\r\n  current-tab=\"$ctrl.currentTab\"\r\n  options=\"[\r\n    { value: 'basic', text: 'Perustiedot' },\r\n    { value: 'incometype', text: 'SALAXY.NG1.CalcRowsComponent.irRows.irFlagsInfo' },\r\n    { value: 'sidecosts', text: 'SALAXY.NG1.CalcRowsComponent.irRows.taxAndSideCosts' }\r\n  ]\"\r\n  tabs-id=\"irIncomeType\">\r\n</salaxy-tab-buttons>\r\n<div class=\"tab-content\" id=\"tab-content-irIncomeType\">\r\n  <div class=\"tab-pane\" id=\"basic-tab\">\r\n    <div class=\"col\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.textAndIncomeType\"></legend>\r\n        <salaxy-input-income-type name=\"code\" ng-model=\"$ctrl.current.data.irData.code\"  hidden-codes=\"[1]\" label=\"SALAXY.NG1.CalcRowsComponent.irRows.incomeTypeLabel\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\">\r\n        </salaxy-input-income-type>\r\n        <salaxy-input name=\"message\" ng-model=\"$ctrl.current.message\" label=\"SALAXY.NG1.CalcRowsComponent.irRows.messageLabel\" placeholder=\"{{$ctrl.getMessagePlaceholderText($ctrl.current)}}\"></salaxy-input>\r\n\r\n        <salaxy-form-group label=\"SALAXY.NG1.CalcRowsComponent.irRows.paymentToCreditTransferLabel\" name=\"paymentDefault\">\r\n          <!--TODO -->\r\n          <div ng-if=\"$ctrl.getIrCodeData().paymentDefault == 1\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.payment\"></div>\r\n          <div ng-if=\"$ctrl.getIrCodeData().paymentDefault == -1\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.deduction\"></div>\r\n          <div ng-if=\"$ctrl.getIrCodeData().paymentDefault == 0\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.noPayment\"></div>\r\n        </salaxy-form-group>\r\n      </fieldset>\r\n    </div>\r\n    <div class=\"col\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.calc\"></legend>\r\n        <salaxy-input-number name=\"count\" ng-model=\"$ctrl.current.count\" label=\"SALAXY.NG1.CalcRowsComponent.irRows.countLabel\"></salaxy-input-number>\r\n        <salaxy-input-enum name=\"unit\" label=\"SALAXY.NG1.CalcRowsComponent.irRows.unitLabel\" enum=\"Unit\" ng-model=\"$ctrl.current.data.unit\" type=\"select\"></salaxy-input-enum>\r\n        <salaxy-input-number name=\"price\" ng-model=\"$ctrl.current.price\" label=\"SALAXY.NG1.CalcRowsComponent.irRows.priceLabel\"></salaxy-input-number>\r\n        <salaxy-form-group name=\"total\" label=\"SALAXY.NG1.CalcRowsComponent.irRows.totalLabel\">\r\n          <p>{{ $ctrl.current.count * $ctrl.current.price | currency }}</p>\r\n        </salaxy-form-group>\r\n      </fieldset>\r\n    </div>\r\n    <div class=\"col\" ng-if=\"$ctrl.current.data.irData.code == 304\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.carBenefitInfo\"></legend>\r\n        <p sxy-html=\"SALAXY.NG1.CalcRowsComponent.irRows.carBenefitInfoHtml\"></p>\r\n        <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.irRows.carBenefitTypeLabel\" enum=\"CarBenefitCode\" name=\"carBenefitCode\" ng-model=\"$ctrl.current.data.irData.carBenefit.carBenefitCode\"\r\n          type=\"select\"></salaxy-input-enum>\r\n        <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.irRows.carBenefitAgeGroupLabel\" enum=\"AgeGroupCode\" name=\"ageGroupCode\" ng-model=\"$ctrl.current.data.irData.carBenefit.ageGroupCode\" type=\"select\">\r\n        </salaxy-input-enum>\r\n        <salaxy-input-number label=\"SALAXY.NG1.CalcRowsComponent.irRows.carBenefitEmissionsValueLabel\" name=\"emissionsValue\" minimum=\"0\" maximum=\"100\" ng-model=\"$ctrl.current.data.irData.carBenefit.emissionsValue\"></salaxy-input-number>\r\n        <salaxy-input-number label=\"SALAXY.NG1.CalcRowsComponent.irRows.carBenefitKilometersLabel\" name=\"kilometers\" ng-model=\"$ctrl.current.data.irData.carBenefit.kilometers\"></salaxy-input-number>     \r\n      </fieldset>\r\n    </div>\r\n    <div class=\"col\" ng-if=\"$ctrl.current.data.irData.code == 331\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.dailyAllowanceAdditionalSelections\"></legend>\r\n        <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.irRows.dailyAllowanceTypeLabel\" enum=\"AllowanceCode\" name=\"dailyAllowance\" type=\"multi-select\"\r\n          ng-model=\"$ctrl.current.data.irData.dailyAllowance\" require=\"true\"></salaxy-input-enum>\r\n      </fieldset>\r\n    </div>\r\n\r\n    <div class=\"col\" ng-if=\"$ctrl.current.data.irData.code == 334\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.mealBenefitAdditionalSelections\"></legend>\r\n        <p sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.mealBenefitTaxInfo\"></p>\r\n        <salaxy-input-boolean type=\"checkbox\" name=\"mealBenefitIsTaxValue\" ng-model=\"$ctrl.current.data.irData.mealBenefitIsTaxValue\" label-type=\"plain\"\r\n          label-true=\"SALAXY.NG1.CalcRowsComponent.irRows.mealBenefitIsTaxValueLabel\"></salaxy-input-boolean>\r\n      </fieldset>\r\n    </div>\r\n  </div>\r\n  <div class=\"tab-pane\" id=\"incometype-tab\">\r\n    <div class=\"col\">\r\n      <fieldset>\r\n        <legend>{{ $ctrl.getMessagePlaceholderText($ctrl.current) }} ({{ $ctrl.current.data.irData.code }})</legend>\r\n        <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.irRows.irFlagsLabel\" enum=\"IrFlags\" name=\"flags\" type=\"multi-select\" ng-model=\"$ctrl.current.data.irData.flags\"></salaxy-input-enum>\r\n        <salaxy-form-group label=\"SALAXY.NG1.CalcRowsComponent.irRows.negativeSupportedLabel\" name=\"isNegativeSupported\">\r\n          <div ng-if=\"$ctrl.getIrCodeData().isNegativeSupported\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.allowed\"></div>\r\n          <div ng-if=\"!$ctrl.getIrCodeData().isNegativeSupported\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.notAllowed\"></div>\r\n        </salaxy-form-group>\r\n        <div style=\"white-space: pre-wrap\">{{ $ctrl.getIrCodeData().description }}</div>\r\n      </fieldset>\r\n    </div>\r\n    <div class=\"col\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.earningPeriod\"></legend>\r\n        <p sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.earningPeriodInfo\"></p>\r\n        <salaxy-datepicker-popup name=\"startDate\" label=\"SALAXY.NG1.CalcRowsComponent.irRows.earningPeriodStartDateLabel\" ng-model=\"$ctrl.current.data.earningPeriod.start\"></salaxy-datepicker-popup>\r\n        <salaxy-datepicker-popup name=\"endDate\" label=\"SALAXY.NG1.CalcRowsComponent.irRows.earningPeriodEndDateLabel\" ng-model=\"$ctrl.current.data.earningPeriod.end\"></salaxy-datepicker-popup>\r\n      </fieldset>\r\n    </div>\r\n  </div>\r\n  <div class=\"tab-pane\" id=\"sidecosts-tab\">\r\n    <div class=\"col\">\r\n      <fieldset>\r\n        <legend>{{ $ctrl.getMessagePlaceholderText($ctrl.current) }}</legend>\r\n        <div style=\"white-space: pre-wrap\">{{ $ctrl.getIrCodeData().taxAndSidecostsDescr }}</div>\r\n        <table class=\"table\">\r\n          <tbody>\r\n            <tr>\r\n              <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.tax\"></th>\r\n              <td>\r\n                <div ng-if=\"$ctrl.getIrCodeData().taxDefault == 1\" class=\"text-success\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.withheld\"></div>\r\n                <div ng-if=\"$ctrl.getIrCodeData().taxDefault == -1\" class=\"text-warning\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.deductionAlt\"></div>\r\n                <div ng-if=\"$ctrl.getIrCodeData().taxDefault == 0\" class=\"text-danger\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.notwithheld\"></div>\r\n              </td>\r\n              <td></td>\r\n            </tr>\r\n            <tr>\r\n              <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.socialSecurityPayment\"></th>\r\n              <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.toBePaid\"></th>\r\n              <th>\r\n                <!-- TODO: Lisää tähän srakkeeseen tieto poikkeuksen jälkeen-->\r\n              </th>\r\n            </tr>\r\n            <tr>\r\n              <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.occupationPension\"></th>\r\n              <td>\r\n                <span ng-class=\"$ctrl.getIrCodeData().pensionInsurance ? 'text-success' : 'text-danger'\">\r\n                  {{ $ctrl.getIrCodeData().pensionInsurance ? (\"SALAXY.UI_Terms.yes\" | sxyTranslate) : (\"SALAXY.UI_Terms.no\" | sxyTranslate) }}\r\n                </span>\r\n              </td>\r\n              <td>\r\n              </td>\r\n            </tr>\r\n            <tr>\r\n              <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.insurancePayment\"></th>\r\n              <td>\r\n                <span ng-class=\"$ctrl.getIrCodeData().accidentInsurance ? 'text-success' : 'text-danger'\">\r\n                  {{ $ctrl.getIrCodeData().accidentInsurance ? (\"SALAXY.UI_Terms.yes\" | sxyTranslate) : (\"SALAXY.UI_Terms.no\" | sxyTranslate) }}\r\n                </span>\r\n              </td>\r\n              <td></td>\r\n            </tr>\r\n            <tr>\r\n              <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.unemploymentInsurancePayment\"></th>\r\n              <td>\r\n                <span ng-class=\"$ctrl.getIrCodeData().unemploymentInsurance ? 'text-success' : 'text-danger'\">\r\n                  {{ $ctrl.getIrCodeData().unemploymentInsurance ? (\"SALAXY.UI_Terms.yes\" | sxyTranslate) : (\"SALAXY.UI_Terms.no\" | sxyTranslate) }}\r\n                </span>\r\n              </td>\r\n              <td></td>\r\n            </tr>\r\n            <tr>\r\n              <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.healtInsurancePayment\"></th>\r\n              <td>\r\n                <span ng-class=\"$ctrl.getIrCodeData().healthInsurance ? 'text-success' : 'text-danger'\">\r\n                  {{ $ctrl.getIrCodeData().healthInsurance ? (\"SALAXY.UI_Terms.yes\" | sxyTranslate) : (\"SALAXY.UI_Terms.no\" | sxyTranslate) }}\r\n                </span>\r\n              </td>\r\n              <td></td>\r\n            </tr>\r\n          </tbody>\r\n        </table>\r\n        <div ng-if=\"!$ctrl.getIrCodeData().insuranceInformationAllowed\">\r\n          <p sxy-text=\"SALAXY.NG1.CalcRowsComponent.irRows.insuranceInformationAllowed\"></p>\r\n        </div>\r\n        <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.irRows.IrInsuranceExceptions\" enum=\"IrInsuranceExceptions\" name=\"dailyAllowance\" disabled=\"$ctrl.isIrRowReadOnly\"\r\n          ng-if=\"$ctrl.getIrCodeData().insuranceInformationAllowed\" ng-model=\"$ctrl.current.data.irData.insuranceExceptions\" type=\"multi-select\">\r\n        </salaxy-input-enum>\r\n      </fieldset>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/rows/CalcRows2019EditDialog.html\",`<div class=\"salaxy-calc-details-dialog\" ng-style=\"{ 'position': $ctrl.isDialog ? 'absolute' : 'initial' }\">\r\n\r\n  <div class=\"card card-detail\" ng-style=\"{'border-color':$ctrl.getConfig().color}\">\r\n\r\n    <form class=\"form-horizontal\" ng-readonly=\"!$ctrl.isEditable\">\r\n      <div class=\"card-header d-flex\" ng-style=\"{'background-color':$ctrl.getConfig().color, 'border-color':$ctrl.getConfig().color}\">\r\n        <div class=\"avatar-container\">\r\n          <salaxy-avatar avatar=\"{ color: $ctrl.getConfig().color, initials: $ctrl.getConfig().iconText, entityType: 'company' }\">\r\n          </salaxy-avatar>\r\n        </div>\r\n        <div class=\"flex-grow\">\r\n          <h1 class=\"truncate\">\r\n            {{ $ctrl.getConfig().label }}\r\n            <span class=\"smaller\" ng-if=\"$ctrl.current.message\"> - {{$ctrl.current.message}}</span>\r\n          </h1>\r\n          <p class=\"calc-text\">{{$ctrl.current.count}} <span ng-if=\"$ctrl.current.count\">&times;</span> {{$ctrl.current.price}}\r\n            <span class=\"result-text\">{{ $ctrl.getRowTotal($ctrl.current) | currency }}</span>\r\n          </p>\r\n        </div>\r\n        <div class=\"d-flex justify-content-between flex-column ms-auto\">\r\n          <button type=\"button\" class=\"btn-close align-self-end\" ng-click=\"$ctrl.closeEditDialog('cancel', $close)\" aria-label=\"Close\"></button>\r\n          <a ng-show=\"$ctrl.getConfig().moreInfo || $ctrl.getConfig().incomeTypes.length > 0\" class=\"btn-link btn-showmore\" ng-click=\"showInfo = !showInfo\">{{!showInfo ?\r\n            ('SALAXY.NG1.CalcRowsComponent.editDialog.showInfo' | sxyTranslate) : ('SALAXY.NG1.CalcRowsComponent.editDialog.hideInfo' | sxyTranslate)}}\r\n            <i class=\"bi bi-info-circle-fill ms-1\"></i>\r\n          </a>\r\n        </div>\r\n      </div>\r\n      <div class=\"card-body\">\r\n        <p>{{ $ctrl.getConfig().descr }}\r\n          <!-- TODO: We should have full HTML formatting here instead of just white-space: pre-wrap -->\r\n          <span class=\"collapse\" ng-class=\"{show: showInfo}\" style=\"white-space: pre-wrap;\"><br>{{ $ctrl.getConfig().moreInfo }}</span>\r\n        </p>\r\n        <div ng-if=\"showInfo && $ctrl.getConfig().incomeTypes.length > 0\" class=\"mb-3\">\r\n          <p>{{'SALAXY.NG1.CalcRowsComponent.editDialog.incomeTypesInfo' | sxyTranslate}}:</p>\r\n          <div class=\"accordion accordion-flush salaxy-accordion\" id=\"incomeTypes\">\r\n            <div ng-repeat=\"type in $ctrl.getConfig().incomeTypes track by $index\" class=\"accordion-item\">\r\n              <h2 class=\"accordion-header\">\r\n                <button class=\"accordion-button collapsed\" type=\"button\" data-bs-toggle=\"collapse\" data-bs-target=\"#type{{$index}}\">\r\n                  {{$ctrl.getIrCodeDataWithCode(type).code}} {{$ctrl.getIrCodeDataWithCode(type).label}}\r\n                </button>\r\n              </h2>\r\n              <div id=\"type{{$index}}\" class=\"accordion-collapse collapse\" aria-labelledby=\"headingOne\" data-bs-parent=\"#incomeTypes\">\r\n                <div class=\"accordion-body\">\r\n                  <p>{{$ctrl.getIrCodeDataWithCode(type).description}}</p>\r\n                </div>\r\n              </div>\r\n            </div>\r\n          </div>\r\n        </div>\r\n        <div>\r\n          <!-- TODO: The row specific UI's need to be refactored to a better structure soon. -->\r\n          <div ng-switch=\"$ctrl.current.rowType\">\r\n            <div ng-switch-when=\"salary|paidSickLeaveSalary|trainingSalary|monthlySalary|paidSickLeaveMonthlySalary|trainingMonthlySalary|compensation\"\r\n              ng-switch-when-separator=\"|\">\r\n              <!-- Row types that have count hidden, but should be shown in edit -->\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().amount.label}}\" ng-model=\"$ctrl.current.count\" name=\"count\" label-type=\"horizontal\"\r\n                unit=\"{{$ctrl.getConfig().amount.unit}}\" placeholder=\"{{ $ctrl.getPlaceholderText($ctrl.current, 'amount') }}\"></salaxy-input-number>\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().price.label}}\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n                disabled=\"$ctrl.isDisabled($ctrl.current, 'price')\" placeholder=\"{{ $ctrl.getPlaceholderText($ctrl.current, 'price') }}\"  ng-if=\"$ctrl.getConfig().price.input != 'hidden'\"></salaxy-input-number>\r\n            </div>\r\n            <div ng-switch-when=\"irIncomeType\">\r\n              <ng-include src=\"'salaxy-components/calc/rows/CalcRows2019EditDialog-irIncomeType.html'\"></ng-include>\r\n            </div>\r\n            <div ng-switch-when=\"unionPayment\">\r\n              <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.editDialog.unionPaymentLabel\" label-type=\"horizontal\" enum=\"UnionPaymentKind\" hidden-options=\"other,undefined\"\r\n                require=\"true\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\" name=\"UnionPaymentKind\" ng-model=\"$ctrl.current.data.kind\" type=\"select\">\r\n              </salaxy-input-enum>\r\n              <div class=\"alert alert-warning\" ng-if=\"$ctrl.current.data.kind == 'raksaNormal' ||  $ctrl.current.data.kind == 'raksaUnemploymentOnly'\">\r\n                <p sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.raksaInfo\"></p>\r\n              </div>\r\n              <salaxy-input-number ng-if=\"$ctrl.current.data.kind == 'percentage' || $ctrl.current.data.kind == 'raksaNormal' ||\r\n                $ctrl.current.data.kind == 'raksaUnemploymentOnly'\" required=\"true\" ng-model=\"$ctrl.current.count\" name=\"count\" label-type=\"horizontal\" unit=\"percent\"\r\n                label=\"SALAXY.NG1.CalcRowsComponent.editDialog.percentOfSalary\"\r\n                disabled=\"$ctrl.current.data.kind == 'raksaNormal' ||  $ctrl.current.data.kind == 'raksaUnemploymentOnly'\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-number ng-if=\"$ctrl.current.data.kind !='percentageAndLimits'\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n                disabled=\"$ctrl.current.data.kind != 'fixed'\"\r\n                label=\"{{$ctrl.current.data.kind == 'fixed' ? ('SALAXY.NG1.CalcRowsComponent.editDialog.unionPaymentCount' | sxyTranslate) : ('SALAXY.NG1.CalcRowsComponent.editDialog.underTaxSalary' | sxyTranslate)}}\"\r\n                ng-change=\"$ctrl.updateUsecase($ctrl.current)\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-number ng-if=\"$ctrl.current.data.kind == 'percentageAndLimits'\" required=\"true\" ng-model=\"$ctrl.current.data.paymentPercentage\" name=\"paymentPercentage\"\r\n                label-type=\"horizontal\" unit=\"percent\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.percentOfSalary\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-number ng-if=\"$ctrl.current.data.kind =='percentageAndLimits'\" ng-model=\"$ctrl.current.data.minimumPayment\" name=\"minimumPayment\"\r\n                label-type=\"horizontal\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.unionPayment.minimumPayment\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-number ng-if=\"$ctrl.current.data.kind =='percentageAndLimits'\" ng-model=\"$ctrl.current.data.maximumPayment\" name=\"maximumPayment\"\r\n                label-type=\"horizontal\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.unionPayment.maximumPayment\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\">\r\n              </salaxy-input-number>\r\n\r\n              <div class=\"row\">\r\n                <div class=\"input-info offset-4 col-8\">\r\n                  <div class=\"input-info-icon\"><i class=\"bi bi-info-circle-fill text-default\"></i></div>\r\n                  <p class=\"small input-info-text with-icon\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.fillUnionPaymentInformation\"></p>\r\n                </div>\r\n              </div>\r\n              <salaxy-input ng-model=\"$ctrl.current.data.recipientFullName\" name=\"unionFullName\" label-type=\"horizontal\" require=\"false\"\r\n                label=\"SALAXY.NG1.CalcRowsComponent.editDialog.unionLabel\"></salaxy-input>\r\n              <salaxy-input ng-model=\"$ctrl.current.data.iban\" name=\"unionIban\" label-type=\"horizontal\" require=\"false\"\r\n                label=\"SALAXY.NG1.CalcRowsComponent.editDialog.unionIbanLabel\" sxy-iban>\r\n              </salaxy-input>\r\n              <salaxy-input ng-model=\"$ctrl.current.data.referenceNumber\" name=\"unionReferenceNumber\" label-type=\"horizontal\" require=\"false\"\r\n                label=\"SALAXY.NG1.CalcRowsComponent.editDialog.unionReferenceNumberLabel\" sxy-bank-reference-fi></salaxy-input>\r\n            </div>\r\n            <div ng-switch-when=\"foreclosure\">\r\n              <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.editDialog.foreclosureKindLabel\" label-type=\"horizontal\" enum=\"ForeclosureKind\" require=\"true\"\r\n                ng-change=\"$ctrl.updateUsecase($ctrl.current)\" name=\"ForeclosureKind\" ng-model=\"$ctrl.current.data.kind\" type=\"select\"></salaxy-input-enum>\r\n              <salaxy-input-number ng-model=\"$ctrl.current.count\" name=\"count\" label-type=\"horizontal\" unit=\"{{$ctrl.getConfig().amount.unit}}\"\r\n                disabled=\"$ctrl.isDisabled($ctrl.current, 'amount')\" ng-if=\"$ctrl.getConfig().amount.input != 'hidden'\" label=\"{{$ctrl.getConfig().amount.label}}\"\r\n                ng-change=\"$ctrl.updateUsecase($ctrl.current)\"></salaxy-input-number>\r\n              <salaxy-input-number ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n                disabled=\"$ctrl.current.data.kind == 'periodic' || $ctrl.current.data.kind == 'nonPeriodic'\" label=\"{{$ctrl.getConfig().price.label}}\"\r\n                ng-change=\"$ctrl.updateUsecase($ctrl.current)\"></salaxy-input-number>\r\n              <salaxy-input-number ng-if=\"$ctrl.current.data.kind == 'periodic'\" ng-model=\"$ctrl.current.data.periodLength\" name=\"periodLength\" label-type=\"horizontal\"\r\n                disabled=\"true\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.foreclosurePeriodLengthLabel\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\"></salaxy-input-number>\r\n              <salaxy-input-number ng-if=\"$ctrl.current.data.kind == 'periodic'\" ng-model=\"$ctrl.current.data.protectedPortionBase\" name=\"protectedPortionBase\"\r\n                label-type=\"horizontal\" require=\"true\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.foreclosureprotectedPortionBaseLabel\"\r\n                ng-change=\"$ctrl.updateUsecase($ctrl.current)\"></salaxy-input-number>\r\n              <salaxy-input-number ng-if=\"$ctrl.current.data.kind == 'periodic'\" ng-model=\"$ctrl.current.data.protectedPortionDependant\" name=\"protectedPortionDependant\"\r\n                label-type=\"horizontal\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.foreclosureprotectedPortionDependantLabel\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-number ng-if=\"$ctrl.current.data.kind == 'periodic'\" sxy-integer ng-model=\"$ctrl.current.data.dependantsCount\" name=\"dependantsCount\"\r\n                label-type=\"horizontal\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.foreclosuredependantsCountLabel\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-number ng-if=\"$ctrl.current.data.kind == 'periodic'\" ng-model=\"$ctrl.current.data.incomeFromOtherSources\" name=\"incomeFromOtherSources\"\r\n                label-type=\"horizontal\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.foreclosureincomeFromOtherSourcesLabel\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-number ng-if=\"$ctrl.current.data.kind == 'periodic'\" ng-model=\"$ctrl.current.data.additionalAmountLeftToDebtor\" name=\"additionalAmountLeftToDebtor\"\r\n                label-type=\"horizontal\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.foreclosureadditionalAmountLeftToDebtorLabel\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\">\r\n              </salaxy-input-number>\r\n              <div class=\"row\">\r\n                <div class=\"input-info offset-4 col-8\">\r\n                  <div class=\"input-info-icon\"><i class=\"bi bi-info-circle-fill text-default\"></i></div>\r\n                  <p class=\"small input-info-text with-icon\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.foreclosureReferenceNumberInfo\"></p>\r\n                </div>\r\n              </div>\r\n              <salaxy-input ng-model=\"$ctrl.current.data.referenceNumber\" name=\"referenceNumber\" label-type=\"horizontal\" require=\"false\"\r\n                label=\"SALAXY.NG1.CalcRowsComponent.editDialog.foreclosureReferenceNumberLabel\" sxy-bank-reference-fi></salaxy-input>\r\n            </div>\r\n            <div ng-switch-when=\"totalWorkerPayment\">\r\n              <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.editDialog.totalWorkerPaymentKindLabel\" label-type=\"horizontal\" enum=\"TotalWorkerPaymentKind\" require=\"true\"\r\n                ng-change=\"$ctrl.updateUsecase($ctrl.current)\" name=\"TotalWorkerPaymentKind\" ng-model=\"$ctrl.current.data.kind\" type=\"select\"></salaxy-input-enum>\r\n              <salaxy-input-number ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n                label=\"SALAXY.NG1.CalcRowsComponent.editDialog.totalWorkerSumLabel\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\"></salaxy-input-number>\r\n              <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.editDialog.totalWorkerCalculationRowTypeLabel\" label-type=\"horizontal\" enum=\"CalculationRowType\" require=\"true\"\r\n                ng-change=\"$ctrl.updateUsecase($ctrl.current)\" name=\"CalculationRowType\" ng-model=\"$ctrl.current.data.rowType\" filter=\"salary,monthlySalary\" type=\"select\">\r\n              </salaxy-input-enum>\r\n              <salaxy-input ng-model=\"$ctrl.current.data.message\" name=\"message\" label-type=\"horizontal\" require=\"false\"\r\n                label=\"SALAXY.NG1.CalcRowsComponent.editDialog.totalWorkerCalculationMessage\"></salaxy-input>\r\n            </div>\r\n            <div ng-switch-when=\"carBenefit\">\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().price.label}}\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n                disabled=\"$ctrl.isDisabled($ctrl.current, 'price')\" ng-if=\"$ctrl.getConfig().price.input != 'hidden'\"></salaxy-input-number>\r\n              <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.editDialog.carBenefit.carBenefitCode\" label-type=\"horizontal\" enum=\"CarBenefitCode\" require=\"true\"\r\n                ng-change=\"$ctrl.updateUsecase($ctrl.current)\" name=\"CarBenefitCode\" ng-model=\"$ctrl.current.data.kind\" type=\"select\"></salaxy-input-enum>\r\n              <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.editDialog.carBenefit.ageGroupCode\" label-type=\"horizontal\" enum=\"AgeGroupCode\" require=\"true\"\r\n                ng-change=\"$ctrl.updateUsecase($ctrl.current)\" hidden-options=\"undefined,u\" name=\"AgeGroupCode\" ng-model=\"$ctrl.current.data.ageGroup\" type=\"select\">\r\n              </salaxy-input-enum>\r\n              <salaxy-input-boolean type=\"checkbox\" name=\"isKilometersBased\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.carBenefit.kilometersBased\"\r\n                label-true=\"SALAXY.NG1.CalcRowsComponent.editDialog.carBenefit.kilometersBasedTrue\" label-type=\"horizontal\" ng-model=\"$ctrl.current.data.isKilometersBased\">\r\n              </salaxy-input-boolean>\r\n              <salaxy-input-number label=\"SALAXY.NG1.CalcRowsComponent.editDialog.carBenefit.kilometers\" ng-model=\"$ctrl.current.data.kilometers\" name=\"kilometers\"\r\n                label-type=\"horizontal\" require=\"true\" ng-if=\"$ctrl.current.data.isKilometersBased\"></salaxy-input-number>\r\n              <salaxy-input-number label=\"SALAXY.NG1.CalcRowsComponent.editDialog.carBenefit.deduction\" ng-model=\"$ctrl.current.data.deduction\" name=\"deduction\"\r\n                label-type=\"horizontal\"></salaxy-input-number>\r\n              <salaxy-input-number label=\"SALAXY.NG1.CalcRowsComponent.editDialog.carBenefit.emissionsValue\" ng-model=\"$ctrl.current.data.emissionsValue\" name=\"emissionsValue\"\r\n                label-type=\"horizontal\" minimum=\"0\" maximum=\"100\"></salaxy-input-number>\r\n            </div>\r\n            <div ng-switch-when=\"subsidisedCommute\">\r\n              <p sxy-html=\"SALAXY.NG1.CalcRowsComponent.editDialog.subsidisedCommute.info.html\"></p>\r\n              <div ng-init=\"$subsidisedCommute = $ctrl.getUsecaseLogic($ctrl.current)\">\r\n                <salaxy-input-number ng-change=\"$subsidisedCommute.updateUsecase()\" label=\"{{$ctrl.getConfig().price.label}}\" ng-model=\"$ctrl.current.price\" name=\"price\"\r\n                  label-type=\"horizontal\" require=\"true\" disabled=\"$ctrl.isDisabled($ctrl.current, 'price')\"\r\n                  ng-if=\"$ctrl.getConfig().price.input != 'hidden'\"></salaxy-input-number>\r\n                <salaxy-input-enum ng-change=\"$subsidisedCommute.updateUsecase()\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.subsidisedCommute.subsidisedCommuteKind\"\r\n                  label-type=\"horizontal\" enum=\"SubsidisedCommuteKind\" require=\"true\" name=\"SubsidisedCommuteKind\" ng-model=\"$ctrl.current.data.kind\" type=\"select\">\r\n                </salaxy-input-enum>\r\n                <salaxy-input-number ng-change=\"$subsidisedCommute.updateUsecase()\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.subsidisedCommute.deduction\"\r\n                  ng-model=\"$ctrl.current.data.deduction\" name=\"deduction\" label-type=\"horizontal\"\r\n                  ng-if=\"$ctrl.current.data.kind == 'singleDeduction' || $ctrl.current.data.kind == 'periodicalDeduction'\"></salaxy-input-number>\r\n                <salaxy-input-number ng-change=\"$subsidisedCommute.updateUsecase()\" ng-if=\"$ctrl.isEditable && !$subsidisedCommute.isBefore2021\"\r\n                  placeholder=\"{{$subsidisedCommute.calculatedTaxable | number : 2}}\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.subsidisedCommute.taxable\"\r\n                  ng-model=\"$ctrl.current.data.taxable\" name=\"taxable\" label-type=\"horizontal\"\r\n                  ng-if=\"$ctrl.current.data.kind == 'noDeduction' || $ctrl.current.data.kind == 'singleDeduction' || $ctrl.current.data.kind == 'periodicalDeduction'\"></salaxy-input-number>\r\n                <salaxy-input-number ng-if=\"$ctrl.isEditable && !$subsidisedCommute.isBefore2021\" placeholder=\"{{$subsidisedCommute.calculatedTaxfree | number : 2}}\"\r\n                  disabled=\"true\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.subsidisedCommute.taxfree\" ng-model=\"subsidisedCommuteForDisplayOnly\" name=\"taxfree\"\r\n                  label-type=\"horizontal\"\r\n                  ng-if=\"$ctrl.current.data.kind == 'noDeduction' || $ctrl.current.data.kind == 'singleDeduction' || $ctrl.current.data.kind == 'periodicalDeduction'\"></salaxy-input-number>\r\n                <salaxy-input-number ng-if=\"!$ctrl.isEditable && !$subsidisedCommute.isBefore2021\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.subsidisedCommute.taxable\"\r\n                  ng-model=\"$subsidisedCommute.calculatedTaxable\" name=\"taxable\" label-type=\"horizontal\"\r\n                  ng-if=\"$ctrl.current.data.kind == 'noDeduction' || $ctrl.current.data.kind == 'singleDeduction' || $ctrl.current.data.kind == 'periodicalDeduction'\"></salaxy-input-number>\r\n                <salaxy-input-number ng-if=\"!$ctrl.isEditable && !$subsidisedCommute.isBefore2021\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.subsidisedCommute.taxfree\"\r\n                  ng-model=\"$subsidisedCommute.calculatedTaxfree\" name=\"taxfree\" label-type=\"horizontal\"\r\n                  ng-if=\"$ctrl.current.data.kind == 'noDeduction' || $ctrl.current.data.kind == 'singleDeduction' || $ctrl.current.data.kind == 'periodicalDeduction'\"></salaxy-input-number>\r\n                <salaxy-input-number ng-change=\"$subsidisedCommute.updateUsecase()\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.subsidisedCommute.periodDivider\"\r\n                  ng-model=\"$ctrl.current.data.periodDivider\" name=\"periodDivider\" label-type=\"horizontal\"\r\n                  ng-if=\"$ctrl.current.data.kind == 'periodicalDeduction'\"></salaxy-input-number>\r\n              </div>\r\n            </div>\r\n            <div ng-switch-when=\"bicycleBenefit\">\r\n              <div ng-init=\"$bicycleBenefit = $ctrl.getUsecaseLogic($ctrl.current)\">\r\n                <salaxy-input-number ng-change=\"$bicycleBenefit.updateUsecase()\" label=\"{{$ctrl.getConfig().price.label}}\" ng-model=\"$ctrl.current.price\" name=\"price\"\r\n                  label-type=\"horizontal\" require=\"true\" disabled=\"$ctrl.isDisabled($ctrl.current, 'price')\"\r\n                  ng-if=\"$ctrl.getConfig().price.input != 'hidden'\"></salaxy-input-number>\r\n                <salaxy-input-enum ng-change=\"$bicycleBenefit.updateUsecase()\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.bicycleBenefit.bicycleBenefitKind\"\r\n                  label-type=\"horizontal\" enum=\"BicycleBenefitKind\" require=\"true\" name=\"BicycleBenefitKind\" ng-model=\"$ctrl.current.data.kind\" type=\"select\">\r\n                </salaxy-input-enum>\r\n                <salaxy-input-number ng-change=\"$bicycleBenefit.updateUsecase()\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.bicycleBenefit.deduction\"\r\n                  ng-model=\"$ctrl.current.data.deduction\" name=\"deduction\" label-type=\"horizontal\"\r\n                  ng-if=\"$ctrl.current.data.kind == 'singleDeduction' || $ctrl.current.data.kind == 'periodicalDeduction'\"></salaxy-input-number>\r\n                <salaxy-input-number ng-change=\"$bicycleBenefit.updateUsecase()\" ng-if=\"$ctrl.isEditable\" placeholder=\"{{$bicycleBenefit.calculatedTaxable | number : 2}}\"\r\n                  label=\"SALAXY.NG1.CalcRowsComponent.editDialog.bicycleBenefit.taxable\" ng-model=\"$ctrl.current.data.taxable\" name=\"taxable\" label-type=\"horizontal\"\r\n                  ng-if=\"$ctrl.current.data.kind == 'noDeduction' || $ctrl.current.data.kind == 'singleDeduction' || $ctrl.current.data.kind == 'periodicalDeduction'\"></salaxy-input-number>\r\n                <salaxy-input-number ng-if=\"$ctrl.isEditable\" placeholder=\"{{$bicycleBenefit.calculatedTaxfree | number : 2}}\" disabled=\"true\"\r\n                  label=\"SALAXY.NG1.CalcRowsComponent.editDialog.bicycleBenefit.taxfree\" ng-model=\"bicycleBenefitForDisplayOnly\" name=\"taxfree\" label-type=\"horizontal\"\r\n                  ng-if=\"$ctrl.current.data.kind == 'noDeduction' || $ctrl.current.data.kind == 'singleDeduction' || $ctrl.current.data.kind == 'periodicalDeduction'\"></salaxy-input-number>\r\n                <salaxy-input-number ng-if=\"!$ctrl.isEditable\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.bicycleBenefit.taxable\" ng-model=\"$bicycleBenefit.calculatedTaxable\"\r\n                  name=\"taxable\" label-type=\"horizontal\"\r\n                  ng-if=\"$ctrl.current.data.kind == 'noDeduction' || $ctrl.current.data.kind == 'singleDeduction' || $ctrl.current.data.kind == 'periodicalDeduction'\"></salaxy-input-number>\r\n                <salaxy-input-number ng-if=\"!$ctrl.isEditable\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.bicycleBenefit.taxfree\" ng-model=\"$bicycleBenefit.calculatedTaxfree\"\r\n                  name=\"taxfree\" label-type=\"horizontal\"\r\n                  ng-if=\"$ctrl.current.data.kind == 'noDeduction' || $ctrl.current.data.kind == 'singleDeduction' || $ctrl.current.data.kind == 'periodicalDeduction'\"></salaxy-input-number>\r\n                <salaxy-input-number ng-change=\"$bicycleBenefit.updateUsecase()\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.bicycleBenefit.periodDivider\"\r\n                  ng-model=\"$ctrl.current.data.periodDivider\" name=\"periodDivider\" label-type=\"horizontal\"\r\n                  ng-if=\"$ctrl.current.data.kind == 'periodicalDeduction'\"></salaxy-input-number>\r\n              </div>\r\n            </div>\r\n            <div ng-switch-when=\"nonProfitOrg\">\r\n              <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.editDialog.nonProfitOrg.profitOrgKind\" label-type=\"horizontal\" enum=\"NonProfitOrgKind\" require=\"true\"\r\n                ng-change=\"$ctrl.updateUsecase($ctrl.current)\" name=\"NonProfitOrgKind\" ng-model=\"$ctrl.current.data.kind\" type=\"select\"></salaxy-input-enum>\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().amount.label}}\" ng-model=\"$ctrl.current.count\" name=\"count\" label-type=\"horizontal\"\r\n                unit=\"{{$ctrl.getConfig().amount.unit}}\" placeholder=\"1\" disabled=\"$ctrl.isDisabled($ctrl.current, 'amount')\" ng-if=\"$ctrl.getConfig().amount.input != 'hidden'\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().price.label}}\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n                disabled=\"$ctrl.isDisabled($ctrl.current, 'price')\" ng-if=\"$ctrl.getConfig().price.input != 'hidden'\"></salaxy-input-number>\r\n            </div>\r\n            <div ng-switch-when=\"dailyAllowance\">\r\n              <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.editDialog.dailyAllowance.allowanceKind\" hidden-options=\"mealAllowance\" label-type=\"horizontal\"\r\n                enum=\"DailyAllowanceKind\" require=\"true\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\" name=\"DailyAllowanceKind\" ng-model=\"$ctrl.current.data.kind\" type=\"select\">\r\n              </salaxy-input-enum>\r\n              <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.editDialog.dailyAllowance.internationalDailyAllowanceCount\" label-type=\"horizontal\"\r\n                ng-if=\"$ctrl.current.data.kind === 'internationalDailyAllowance'\" options=\"$ctrl.dailyAllowanceRegions\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\"\r\n                name=\"country\" ng-model=\"$ctrl.current.data.country\" type=\"select\">\r\n              </salaxy-input-enum>\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().amount.label}}\" ng-model=\"$ctrl.current.count\" name=\"count\" label-type=\"horizontal\"\r\n                unit=\"{{$ctrl.getConfig().amount.unit}}\" placeholder=\"1\" disabled=\"$ctrl.isDisabled($ctrl.current, 'amount')\" ng-if=\"$ctrl.getConfig().amount.input != 'hidden'\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().price.label}}\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n                disabled=\"$ctrl.isDisabled($ctrl.current, 'price')\" ng-if=\"$ctrl.getConfig().price.input != 'hidden'\"></salaxy-input-number>\r\n            </div>\r\n            <div ng-switch-when=\"mealBenefit\">\r\n              <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.editDialog.mealBenefit.mealBenefitKind\" label-type=\"horizontal\" enum=\"MealBenefitKind\" require=\"true\"\r\n                ng-change=\"$ctrl.updateUsecase($ctrl.current)\" name=\"MealBenefitKind\" ng-model=\"$ctrl.current.data.kind\" type=\"select\"></salaxy-input-enum>\r\n              <p ng-if=\"$ctrl.current.data.kind\" sxy-text=\"{{'SALAXY.ENUM.MealBenefitKind.' + $ctrl.current.data.kind + '.descriptionWithYearlyNumbers'}}\"\r\n                params=\"$ctrl.yearlySideCosts\"></p>\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().amount.label}}\" ng-model=\"$ctrl.current.count\" name=\"count\" label-type=\"horizontal\"\r\n                unit=\"{{$ctrl.getConfig().amount.unit}}\" placeholder=\"1\" disabled=\"$ctrl.isDisabled($ctrl.current, 'amount')\" ng-if=\"$ctrl.getConfig().amount.input != 'hidden'\">\r\n              </salaxy-input-number>\r\n              <div ng-switch=\"$ctrl.current.data.kind\">\r\n                <div ng-switch-when=\"mealAllowance\">\r\n                  <salaxy-input-number label=\"SALAXY.NG1.CalcRowsComponent.editDialog.mealBenefit.mealPrice\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\"\r\n                    ng-change=\"$ctrl.updateUsecase($ctrl.current)\" require=\"true\" disabled=\"$ctrl.isDisabled($ctrl.current)\"></salaxy-input-number>\r\n                </div>\r\n                <div ng-switch-when=\"taxableAmount|collectedReimbursement|undefined\" ng-switch-when-separator=\"|\">\r\n                  <salaxy-input-number label=\"SALAXY.NG1.CalcRowsComponent.editDialog.mealBenefit.mealTaxablePrice\" ng-model=\"$ctrl.current.price\" name=\"price\"\r\n                    label-type=\"horizontal\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\" require=\"true\" disabled=\"$ctrl.isDisabled($ctrl.current)\"></salaxy-input-number>\r\n                </div>\r\n                <div ng-switch-when=\"mealTicket\">\r\n                  <salaxy-input-number label=\"SALAXY.NG1.CalcRowsComponent.editDialog.mealBenefit.mealTicketPrice\" ng-model=\"$ctrl.current.price\" name=\"price\"\r\n                    label-type=\"horizontal\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\" require=\"true\" disabled=\"$ctrl.isDisabled($ctrl.current)\"></salaxy-input-number>\r\n                </div>\r\n                <div ng-switch-when=\"cateringContract|institute|restaurantWorker|teacher\" ng-switch-when-separator=\"|\">\r\n                  <salaxy-input-number disabled=\"true\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.mealBenefit.mealTaxablePrice\" ng-model=\"$ctrl.current.price\" name=\"price\"\r\n                    label-type=\"horizontal\"></salaxy-input-number>\r\n                </div>\r\n              </div>\r\n              <div ng-if=\"$ctrl.current.data.kind != 'mealAllowance'\">\r\n                <salaxy-form-group ng-if=\"$ctrl.current.data.kind != 'collectedReimbursement'\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.mealBenefit.mealPriceAmount\"\r\n                  name=\"taxablePrice\" label-type=\"horizontal\">\r\n                  <label class=\"control-label\">{{ $ctrl.current.data.taxablePrice * ($ctrl.current.count || 1.0) | currency }}</label>\r\n                </salaxy-form-group>\r\n                <salaxy-input-boolean ng-if=\"$ctrl.current.data.kind != 'collectedReimbursement'\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.mealBenefit.workerDeduction\"\r\n                  label-true=\"SALAXY.NG1.CalcRowsComponent.editDialog.mealBenefit.taxValueTrue\" label-false=\"SALAXY.NG1.CalcRowsComponent.editDialog.mealBenefit.taxValueFalse\"\r\n                  name=\"isTaxValue\" type=\"radio\" ng-model=\"$ctrl.current.data.isTaxValue\" label-type=\"horizontal\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\" require=\"true\"\r\n                  disabled=\"$ctrl.isDisabled($ctrl.current)\"></salaxy-input-boolean>\r\n                <salaxy-input-boolean ng-if=\"$ctrl.current.data.kind != 'collectedReimbursement' && $ctrl.current.data.isTaxValue\"\r\n                  label=\"SALAXY.NG1.CalcRowsComponent.editDialog.mealBenefit.isTaxValueDeductionDone\"\r\n                  label-true=\"SALAXY.NG1.CalcRowsComponent.editDialog.mealBenefit.isTaxValueDeductionDoneTrue\"\r\n                  label-false=\"SALAXY.NG1.CalcRowsComponent.editDialog.mealBenefit.isTaxValueDeductionDoneFalse\" name=\"isTaxValueDeductionDone\" type=\"radio\"\r\n                  ng-model=\"$ctrl.current.data.isTaxValueDeductionDone\" label-type=\"horizontal\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\" require=\"true\"\r\n                  disabled=\"$ctrl.isDisabled($ctrl.current)\"></salaxy-input-boolean>\r\n                <salaxy-form-group ng-if=\"$ctrl.current.data.isTaxValue\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.mealBenefit.deduction\" name=\"deductionWhenTaxValue\"\r\n                  label-type=\"horizontal\">\r\n                  <label class=\"control-label\">{{ $ctrl.current.data.taxablePrice * ($ctrl.current.count || 1.0) | currency }}</label>\r\n                </salaxy-form-group>\r\n                <salaxy-input-number ng-if=\"$ctrl.current.data.kind != 'collectedReimbursement' && !$ctrl.current.data.isTaxValue\"\r\n                  label=\"SALAXY.NG1.CalcRowsComponent.editDialog.mealBenefit.deduction\" ng-model=\"$ctrl.current.data.deduction\" name=\"deduction\" label-type=\"horizontal\"\r\n                  ng-change=\"$ctrl.updateUsecase($ctrl.current)\" disabled=\"$ctrl.isDisabled($ctrl.current)\"></salaxy-input-number>\r\n              </div>\r\n            </div>\r\n            <div ng-switch-when=\"board\">\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().amount.label}}\" ng-model=\"$ctrl.current.count\" name=\"count\" label-type=\"horizontal\"\r\n                unit=\"{{$ctrl.getConfig().amount.unit}}\" placeholder=\"1\" disabled=\"$ctrl.isDisabled($ctrl.current, 'amount')\" ng-if=\"$ctrl.getConfig().amount.input != 'hidden'\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().price.label}}\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n                disabled=\"$ctrl.isDisabled($ctrl.current, 'price')\" ng-if=\"$ctrl.getConfig().price.input != 'hidden'\"></salaxy-input-number>\r\n            </div>\r\n            <div ng-switch-when=\"remuneration\">\r\n              <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.editDialog.remuneration.remunerationKind\" label-type=\"horizontal\" enum=\"RemunerationKind\" require=\"true\"\r\n                ng-change=\"$ctrl.updateUsecase($ctrl.current)\" name=\"RemunerationKind\" ng-model=\"$ctrl.current.data.kind\" type=\"select\"></salaxy-input-enum>\r\n              <p>{{ \"RemunerationKind.\" + $ctrl.current.data.kind | sxyEnumDescr }}</p>\r\n              <salaxy-input-number ng-if=\"$ctrl.getConfig().amount.units.length > 1\" on-unit-change=\"$ctrl.current.unit=unit\" label=\"{{$ctrl.getConfig().amount.label}}\"\r\n                ng-model=\"$ctrl.current.count\" name=\"count\" label-type=\"horizontal\" unit=\"{{$ctrl.ensureUnit($ctrl.current)}}\" units=\"$ctrl.getConfig().amount.units\"\r\n                disabled=\"$ctrl.isDisabled($ctrl.current, 'amount')\" ng-if=\"$ctrl.getConfig().amount.input != 'hidden'\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-number ng-if=\"!($ctrl.getConfig().amount.units.length > 1)\" label=\"{{$ctrl.getConfig().amount.label}}\" ng-model=\"$ctrl.current.count\" name=\"count\"\r\n                label-type=\"horizontal\" unit=\"{{$ctrl.getConfig().amount.unit}}\" placeholder=\"1\" disabled=\"$ctrl.isDisabled($ctrl.current, 'amount')\"\r\n                ng-if=\"$ctrl.getConfig().amount.input != 'hidden'\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().price.label}}\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n                disabled=\"$ctrl.isDisabled($ctrl.current, 'price')\" ng-if=\"$ctrl.getConfig().price.input != 'hidden'\"></salaxy-input-number>\r\n            </div>\r\n            <div ng-switch-when=\"otherCompensation\">\r\n              <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.editDialog.otherCompensation.compensationKind\" label-type=\"horizontal\" enum=\"OtherCompensationKind\"\r\n                require=\"true\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\" name=\"OtherCompensationKind\" ng-model=\"$ctrl.current.data.kind\" type=\"select\">\r\n              </salaxy-input-enum>\r\n              <p>{{ \"OtherCompensationKind.\" + $ctrl.current.data.kind | sxyEnumDescr }}</p>\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().amount.label}}\" ng-model=\"$ctrl.current.count\" name=\"count\" label-type=\"horizontal\"\r\n                unit=\"{{$ctrl.getConfig().amount.unit}}\" placeholder=\"1\" disabled=\"$ctrl.isDisabled($ctrl.current, 'amount')\" ng-if=\"$ctrl.getConfig().amount.input != 'hidden'\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().price.label}}\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n                disabled=\"$ctrl.isDisabled($ctrl.current, 'price')\" ng-if=\"$ctrl.getConfig().price.input != 'hidden'\"></salaxy-input-number>\r\n            </div>\r\n            <div ng-switch-when=\"workingTimeCompensation\">\r\n              <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.editDialog.workingTimeCompensation.compensationKind\" label-type=\"horizontal\" enum=\"WorkingTimeCompensationKind\"\r\n                require=\"true\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\" name=\"WorkingTimeCompensation\" ng-model=\"$ctrl.current.data.kind\" type=\"select\">\r\n              </salaxy-input-enum>\r\n              <p>{{ \"WorkingTimeCompensationKind.\" + $ctrl.current.data.kind | sxyEnumDescr }}</p>\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().amount.label}}\" ng-model=\"$ctrl.current.count\" name=\"count\" label-type=\"horizontal\"\r\n                unit=\"{{$ctrl.getConfig().amount.unit}}\" placeholder=\"1\" disabled=\"$ctrl.isDisabled($ctrl.current, 'amount')\" ng-if=\"$ctrl.getConfig().amount.input != 'hidden'\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().price.label}}\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n                disabled=\"$ctrl.isDisabled($ctrl.current, 'price')\" ng-if=\"$ctrl.getConfig().price.input != 'hidden'\"></salaxy-input-number>\r\n            </div>\r\n            <div ng-switch-when=\"employmentTermination\">\r\n              <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.editDialog.employmentTermination.employmentTerminationKind\" label-type=\"horizontal\"\r\n                enum=\"EmploymentTerminationKind\" require=\"true\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\" name=\"EmploymentTermination\" ng-model=\"$ctrl.current.data.kind\"\r\n                type=\"select\"></salaxy-input-enum>\r\n              <p>{{ \"EmploymentTerminationKind.\" + $ctrl.current.data.kind | sxyEnumDescr }}</p>\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().amount.label}}\" ng-model=\"$ctrl.current.count\" name=\"count\" label-type=\"horizontal\"\r\n                unit=\"{{$ctrl.getConfig().amount.unit}}\" placeholder=\"1\" disabled=\"$ctrl.isDisabled($ctrl.current, 'amount')\" ng-if=\"$ctrl.getConfig().amount.input != 'hidden'\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().price.label}}\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n                disabled=\"$ctrl.isDisabled($ctrl.current, 'price')\" ng-if=\"$ctrl.getConfig().price.input != 'hidden'\"></salaxy-input-number>\r\n            </div>\r\n            <div ng-switch-when=\"paidSickLeave\">\r\n              <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.editDialog.paidSickLeave.paidSickLeaveKind\" label-type=\"horizontal\" enum=\"PaidSickLeaveKind\" require=\"true\"\r\n                ng-change=\"$ctrl.updateUsecase($ctrl.current)\" name=\"PaidSickLeaveKind\" ng-model=\"$ctrl.current.data.kind\" type=\"select\"></salaxy-input-enum>\r\n              <p>{{ \"PaidSickLeaveKind.\" + $ctrl.current.data.kind | sxyEnumDescr }}</p>\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().amount.label}}\" ng-model=\"$ctrl.current.count\" name=\"count\" label-type=\"horizontal\"\r\n                unit=\"{{$ctrl.getConfig().amount.unit}}\" placeholder=\"1\" disabled=\"$ctrl.isDisabled($ctrl.current, 'amount')\" ng-if=\"$ctrl.getConfig().amount.input != 'hidden'\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().price.label}}\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n                disabled=\"$ctrl.isDisabled($ctrl.current, 'price')\" ng-if=\"$ctrl.getConfig().price.input != 'hidden'\"></salaxy-input-number>\r\n            </div>\r\n            <div ng-switch-when=\"training\">\r\n              <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.editDialog.training.trainingKind\" label-type=\"horizontal\" enum=\"TrainingKind\" require=\"true\"\r\n                ng-change=\"$ctrl.updateUsecase($ctrl.current)\" name=\"TrainingKind\" ng-model=\"$ctrl.current.data.kind\" type=\"select\"></salaxy-input-enum>\r\n              <p>{{ \"TrainingKind.\" + $ctrl.current.data.kind | sxyEnumDescr }}</p>\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().amount.label}}\" ng-model=\"$ctrl.current.count\" name=\"count\" label-type=\"horizontal\"\r\n                unit=\"{{$ctrl.getConfig().amount.unit}}\" placeholder=\"1\" disabled=\"$ctrl.isDisabled($ctrl.current, 'amount')\" ng-if=\"$ctrl.getConfig().amount.input != 'hidden'\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().price.label}}\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n                disabled=\"$ctrl.isDisabled($ctrl.current, 'price')\" ng-if=\"$ctrl.getConfig().price.input != 'hidden'\"></salaxy-input-number>\r\n            </div>\r\n            <div ng-switch-when=\"hourlySalaryWithWorkingTimeCompensation\">\r\n              <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.editDialog.WorkingTimeCompensationKind\" label-type=\"horizontal\" enum=\"WorkingTimeCompensationKind\"\r\n                require=\"true\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\" name=\"HourlySalaryWithWorkingTimeCompensation\" ng-model=\"$ctrl.current.data.kind\" type=\"select\">\r\n              </salaxy-input-enum>\r\n              <p>{{ \"WorkingTimeCompensationKind.\" + $ctrl.current.data.kind | sxyEnumDescr }}</p>\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().amount.label}}\" ng-model=\"$ctrl.current.count\" name=\"count\" label-type=\"horizontal\"\r\n                unit=\"{{$ctrl.getConfig().amount.unit}}\" placeholder=\"1\" disabled=\"$ctrl.isDisabled($ctrl.current, 'amount')\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\"\r\n                ng-if=\"$ctrl.getConfig().amount.input != 'hidden'\"></salaxy-input-number>\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().price.label}}\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n                disabled=\"$ctrl.isDisabled($ctrl.current, 'price')\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\" ng-if=\"$ctrl.getConfig().price.input != 'hidden'\">\r\n              </salaxy-input-number>\r\n              <style>\r\n                div.input-group-addon {\r\n                  display: none;\r\n                }\r\n\r\n                div.input-group {\r\n                  width: 100%\r\n                }\r\n              </style>\r\n              <div>\r\n                <salaxy-input label=\"SALAXY.NG1.CalcRowsComponent.editDialog.additionalRows.description\" label-type=\"horizontal\" disabled=\"$ctrl.isDisabled($ctrl.current)\"\r\n                  ng-model=\"$ctrl.current.message\" name=\"message\" placeholder=\"{{$ctrl.getMessagePlaceholderText($ctrl.current)}}\"></salaxy-input>\r\n              </div>\r\n              <hr>\r\n              <div ng-repeat=\"cr in $ctrl.current.data.compensationRows\">\r\n                <salaxy-input-number label=\"SALAXY.NG1.CalcRowsComponent.editDialog.hourlySalaryWithWorkingTimeCompensationRowCountLabel\" ng-model=\"cr.count\" name=\"crCount\" label-type=\"horizontal\"\r\n                unit=\"{{$ctrl.getConfig().amount.unit}}\" placeholder=\"{{$ctrl.current.count || 1}}\" disabled=\"$ctrl.isDisabled($ctrl.current, 'amount')\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\"\r\n                ng-if=\"$ctrl.getConfig().amount.input != 'hidden'\"></salaxy-input-number>\r\n                <salaxy-form-group name=\"compensationRow\" label-type=\"form-horizontal\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.hourlySalaryWithWorkingTimeCompensationRowLabel\" required=\"true\">\r\n                  <div class=\"input-group\">\r\n                    <salaxy-input-number ng-if=\"$ctrl.current.data.pricing == 'percent'\" ng-model=\"cr.percent\" class=\"flex-grow-1\" name=\"percent\" label-type=\"plain\" require=\"true\" unit=\"percent\"\r\n                      ng-change=\"$ctrl.updateUsecase($ctrl.current)\"></salaxy-input-number>\r\n                    <salaxy-input-number ng-if=\"$ctrl.current.data.pricing != 'percent'\" ng-model=\"cr.price\" name=\"price\" label-type=\"plain\" require=\"true\"\r\n                      ng-change=\"$ctrl.updateUsecase($ctrl.current)\"></salaxy-input-number>\r\n                    <div class=\"btn-group\">\r\n                      <button id=\"compUnit\" type=\"button\" class=\"btn btn-primary dropdown-toggle\" data-bs-toggle=\"dropdown\" aria-expanded=\"false\">\r\n                        {{ $ctrl.current.data.pricing == 'percent' ? \"%\" : \"€\" }}\r\n                      </button>\r\n                      <ul class=\"dropdown-menu\" aria-labelledby=\"compUnit\">\r\n                        <li><a class=\"dropdown-item\" href=\"\" ng-click=\"$ctrl.current.data.pricing = 'percent'; $ctrl.updateUsecase($ctrl.current)\">%</a></li>\r\n                        <li><a class=\"dropdown-item\" href=\"\" ng-click=\"$ctrl.current.data.pricing = 'fixed'; $ctrl.updateUsecase($ctrl.current)\">€</a></li>\r\n                      </ul>\r\n                    </div>\r\n                  </div>\r\n                </salaxy-form-group>\r\n                <salaxy-input label=\"SALAXY.NG1.CalcRowsComponent.editDialog.hourlySalaryWithWorkingTimeCompensationRowMessageLabel\" label-type=\"horizontal\" disabled=\"$ctrl.isDisabled($ctrl.current)\"\r\n                  ng-model=\"cr.message\" name=\"crMessage\" placeholder=\"{{ 'WorkingTimeCompensationKind.' + $ctrl.current.data.kind | sxyEnum }}\"></salaxy-input>\r\n              </div>\r\n            </div>\r\n            <div ng-switch-when=\"milageOwnCar\">\r\n              <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.editDialog.milageOwnCar.vehicleType\" label-type=\"horizontal\" options=\"$ctrl.getVehicleTypeSelection()\"\r\n                ng-change=\"$ctrl.updateUsecase($ctrl.current)\" name=\"vehicleType\" ng-model=\"$ctrl.current.data.vehicleType\" type=\"select\"></salaxy-input-enum>\r\n              <salaxy-input-enum ng-if=\"$ctrl.current.data.additionsAllowed\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.milageOwnCar.additions\" label-type=\"horizontal\"\r\n                options=\"$ctrl.getVehicleAdditions()\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\" name=\"additions\" ng-model=\"$ctrl.current.data.additions\"\r\n                type=\"select\"></salaxy-input-enum>\r\n              <salaxy-input-number ng-if=\"$ctrl.current.data.passengersAllowed\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.milageOwnCar.passangerCount\" unit=\"count\"\r\n                label-type=\"horizontal\" ng-model=\"$ctrl.current.data.passengerCount\" name=\"passengerCount\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\"></salaxy-input-number>\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().price.label}}\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\"\r\n                disabled=\"$ctrl.current.data.vehicleType != 'custom'\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\"></salaxy-input-number>\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().amount.label}}\" ng-model=\"$ctrl.current.count\" name=\"count\" label-type=\"horizontal\"\r\n                unit=\"{{$ctrl.getConfig().amount.unit}}\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\"></salaxy-input-number>\r\n            </div>\r\n            <div ng-switch-when=\"taxAtSource\">\r\n              <salaxy-input-number label=\"Palkkasumma ennen vähennystä\" ng-model=\"$ctrl.current.data.totalTaxable\" name=\"totalTaxable\" label-type=\"horizontal\"\r\n                disabled=\"true\"></salaxy-input-number>\r\n              <salaxy-input-enum label=\"Vähennyksen tyyppi\" filter=\"{{ $ctrl.current.data.allowedKinds }}\" label-type=\"horizontal\" enum=\"TaxAtSourceKind\"\r\n                ng-change=\"$ctrl.updateUsecase($ctrl.current)\" name=\"taxAtSourceKind\" ng-model=\"$ctrl.current.data.kind\" type=\"select\"></salaxy-input-enum>\r\n              <div ng-if=\"$ctrl.current.data.kind == 'monthlyDeduction' || $ctrl.current.data.kind == 'dailyDeduction'\" class=\"input-info offset-4 col-8\">\r\n                <p>{{ $ctrl.current.data.deductionCount | sxyCount }} * {{ $ctrl.current.data.deductionPrice | currency }} = {{ $ctrl.current.data.deduction | currency }}</p>\r\n              </div>\r\n              <div ng-if=\"$ctrl.current.data.kind == 'fixedValues'\">\r\n                <salaxy-input-number label=\"Kiinteä vähennys\" ng-model=\"$ctrl.current.data.deduction\" name=\"deduction\" unit=\"eur\" label-type=\"horizontal\"\r\n                  ng-change=\"$ctrl.updateUsecase($ctrl.current)\"></salaxy-input-number>\r\n                <salaxy-input-number label=\"Kiinteä lähdevero\" ng-model=\"$ctrl.current.data.taxValue\" name=\"taxValue\" unit=\"eur\" label-type=\"horizontal\"\r\n                  ng-change=\"$ctrl.updateUsecase($ctrl.current)\"></salaxy-input-number>\r\n              </div>\r\n              <div ng-if=\"$ctrl.current.data.kind != 'fixedValues'\">\r\n                <salaxy-input-number label=\"{{$ctrl.getConfig().price.label}}\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\"\r\n                  ng-change=\"$ctrl.updateUsecase($ctrl.current)\" disabled=\"true\"></salaxy-input-number>\r\n                <salaxy-input-number label=\"{{$ctrl.getConfig().amount.label}}\" ng-model=\"$ctrl.current.count\" name=\"count\" label-type=\"horizontal\"\r\n                  unit=\"{{$ctrl.getConfig().amount.unit}}\" disabled=\"true\"></salaxy-input-number>\r\n                <salaxy-input-number label=\"Lähdevero\" ng-model=\"$ctrl.current.data.taxValue\" name=\"taxValue\" label-type=\"horizontal\" unit=\"eur\"\r\n                  disabled=\"true\"></salaxy-input-number>\r\n              </div>\r\n            </div>\r\n            <div ng-switch-when=\"taxWithholding\">\r\n              <salaxy-input-enum label=\"SALAXY.ENUM.TaxWithholdingKind.label\" label-type=\"horizontal\" enum=\"TaxWithholdingKind\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\"\r\n                name=\"taxWithholdingKind\" ng-model=\"$ctrl.current.data.kind\" type=\"select\"></salaxy-input-enum>\r\n              <div ng-switch=\"$ctrl.current.data.kind\">\r\n                <salaxy-input-number ng-switch-when=\"percentage\" label=\"SALAXY.ENUM.TaxWithholdingKind.percentage.label\" ng-model=\"$ctrl.current.data.taxValue\" name=\"percentage\"\r\n                  label-type=\"horizontal\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\" require=\"true\" unit=\"percent\"></salaxy-input-number>\r\n                <salaxy-input-number ng-switch-when=\"fixedValue\" label=\"SALAXY.ENUM.TaxWithholdingKind.fixedValue.label\" ng-model=\"$ctrl.current.data.taxValue\" name=\"fixedvalue\"\r\n                  label-type=\"horizontal\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\" require=\"true\" unit=\"eur\"></salaxy-input-number>\r\n              </div>\r\n            </div>\r\n            <div ng-switch-when=\"absencePeriod\" ng-init=\"$absencesLogic = $ctrl.getUsecaseLogic($ctrl.current)\">\r\n              <salaxy-input-enum name=\"causeCode\" ng-model=\"$ctrl.current.data.kind\" enum=\"AbsenceCauseCode\" label=\"SALAXY.MODEL.WorkerAbsencePeriod.absencesId.title\"\r\n                type=\"select\" ng-change=\"$absencesLogic.updateIsPaid($ctrl.current, true)\" require=\"true\"></salaxy-input-enum>\r\n              <salaxy-datepicker-popup name=\"start\" ng-model=\"$ctrl.current.period.start\" ng-change=\"$absencesLogic.updatePeriodDays($ctrl.current)\"\r\n                label=\"SALAXY.MODEL.DateRange.start.title\"></salaxy-datepicker-popup>\r\n              <salaxy-datepicker-popup name=\"end\" ng-model=\"$ctrl.current.period.end\" ng-change=\"$absencesLogic.updatePeriodDays($ctrl.current)\"\r\n                label=\"SALAXY.MODEL.DateRange.end.title\"></salaxy-datepicker-popup>\r\n              <salaxy-form-group name=\"daysCount\" label=\"SALAXY.MODEL.DateRange.daysCount.title\" ng-if=\"$ctrl.current.period.days == null\">\r\n                <div class=\"input-group\">\r\n                  <input class=\"form-control\" type=\"text\" autocomplete=\"off\" id=\"daysCount\" name=\"daysCount\" ng-model=\"$ctrl.current.period.daysCount\" disabled>\r\n                  <span class=\"input-group-btn\">\r\n                    <button type=\"button\" class=\"btn btn-default\" ng-click=\"$absencesLogic.setDaysSelection($ctrl.current)\"\r\n                      sxy-text=\"SALAXY.NG1.AbsencePeriodsEditDialog.editDatesButtonText\"></button>\r\n                  </span>\r\n                </div>\r\n              </salaxy-form-group>\r\n              <salaxy-datepicker ng-model=\"$ctrl.current.period\" name=\"days\" is-multiple=\"true\" ng-if=\"$ctrl.current.period.days.length > 0\" label=\"SALAXY.MODEL.WorkerAbsencePeriod.period.title\"></salaxy-datepicker>\r\n              <salaxy-input-number ng-if=\"$ctrl.current.data.kind == 'annualLeave'\" label=\"SALAXY.MODEL.WorkerAbsencePeriod.bonusDaysCount.title\" ng-model=\"$ctrl.current.data.bonusDaysCount\" name=\"bonusDaysCount\" label-type=\"horizontal\"></salaxy-input-number>\r\n              <salaxy-input-boolean ng-init=\"$ctrl.current.data.applyPricing = ($ctrl.current.data.applyPricing || false)\" type=\"radio\" name=\"applyPricing\" label=\"SALAXY.MODEL.AbsencePeriodUsecase.applyPricing.title\"\r\n                label-true=\"SALAXY.MODEL.AbsencePeriodUsecase.applyPricing.labelTrue\"\r\n                label-false=\"SALAXY.MODEL.AbsencePeriodUsecase.applyPricing.labelFalse\"\r\n                ng-model=\"$ctrl.current.data.applyPricing\">\r\n              </salaxy-input-boolean>\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().price.label}}\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n               placeholder=\"{{ $ctrl.getPlaceholderText($ctrl.current, 'price') }}\"  ng-if=\"!$ctrl.current.data.applyPricing\"></salaxy-input-number>\r\n              <salaxy-input-boolean type=\"checkbox\" name=\"isPaid\" label=\"SALAXY.MODEL.WorkerAbsencePeriod.isPaid.title\"\r\n                label-true=\"SALAXY.NG1.AbsencePeriodsEditDialog.label.isPaidLabelTrue\" disabled=\"!$absencesLogic.canSelectIsPaid($ctrl.current)\" ng-model=\"$ctrl.current.data.isPaid\"\r\n                ng-change=\"$ctrl.logic.updateIsHolidayAccrual($ctrl.current)\"></salaxy-input-boolean>\r\n\r\n              <salaxy-input-boolean type=\"checkbox\" name=\"isHolidayAccrual\" label=\"SALAXY.MODEL.WorkerAbsencePeriod.isHolidayAccrual.title\"\r\n                label-true=\"SALAXY.NG1.AbsencePeriodsEditDialog.label.isAccrualLabelTrue\" ng-model=\"$ctrl.current.data.isHolidayAccrual\"></salaxy-input-boolean>\r\n            </div>\r\n            <div ng-switch-when=\"expenses\" ng-init=\"$expenseLogic = $ctrl.getUsecaseLogic($ctrl.current)\">\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().price.label}}\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\"\r\n                require=\"true\"></salaxy-input-number>\r\n              <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercent.label\" label-type=\"horizontal\" enum=\"ExpensesVatRate\"\r\n                hidden-options=\"undefined\" require=\"true\" ng-change=\"$expenseLogic.updateUsecase($ctrl.current)\" name=\"ExpensesVatRate\" ng-model=\"$ctrl.current.data.vatRate\"\r\n                type=\"select\"></salaxy-input-enum>\r\n\r\n              <div ng-switch=\"$ctrl.current.data.vatRate\">\r\n                <span ng-switch-when=\"tax255\" class=\"text-success small\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercents.p255.description\"></span>\r\n                <span ng-switch-when=\"tax24\" class=\"text-success small\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercents.p24.description\"></span>\r\n                <span ng-switch-when=\"tax14\" class=\"text-success small\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercents.p14.description\"></span>\r\n                <span ng-switch-when=\"tax135\" class=\"text-success small\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercents.p135.description\"></span>\r\n                <span ng-switch-when=\"tax10\" class=\"text-success small\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercents.p10.description\"></span>\r\n                <span ng-switch-when=\"tax0\" class=\"text-success small\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercents.p0.description\"></span>\r\n              </div>\r\n              <div ng-if=\"$ctrl.current.data.vatRate == 'multiple'\">\r\n                <p class=\"mb-0\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercentsTable.taxableAmountInPercent\" ps=\":\"></p>\r\n                <div class=\"row\">\r\n                  <salaxy-input-number class=\"col-sm-3\" label=\"25,5%\" label-type=\"basic\" name=\"inpt5\" ng-model=\"$ctrl.current.accounting.vatEntries[4].gross\" ng-change=\"$expenseLogic.updateUsecase()\"></salaxy-input-number>\r\n                  <salaxy-input-number class=\"col-sm-3\" label=\"24%\" label-type=\"basic\" name=\"inpt1\" ng-model=\"$ctrl.current.accounting.vatEntries[0].gross\"\r\n                    ng-change=\"$expenseLogic.updateUsecase()\"></salaxy-input-number>\r\n                  <salaxy-input-number class=\"col-sm-3\" label=\"14%\" label-type=\"basic\" name=\"inpt2\" ng-model=\"$ctrl.current.accounting.vatEntries[1].gross\"\r\n                    ng-change=\"$expenseLogic.updateUsecase()\"></salaxy-input-number>\r\n                  <salaxy-input-number class=\"col-sm-3\" label=\"13,5%\" label-type=\"basic\" name=\"inpt6\" ng-model=\"$ctrl.current.accounting.vatEntries[5].gross\"\r\n                    ng-change=\"$expenseLogic.updateUsecase()\"></salaxy-input-number>\r\n                  <salaxy-input-number class=\"col-sm-3\" label=\"10%\" label-type=\"basic\" name=\"inpt3\" ng-model=\"$ctrl.current.accounting.vatEntries[2].gross\"\r\n                    ng-change=\"$expenseLogic.updateUsecase()\"></salaxy-input-number>\r\n                  <salaxy-input-number class=\"col-sm-3\" label=\"0%\" label-type=\"basic\" name=\"inpt4\" ng-model=\"$ctrl.current.accounting.vatEntries[3].gross\"\r\n                    ng-change=\"$expenseLogic.updateUsecase()\"></salaxy-input-number>\r\n                </div>\r\n              </div>\r\n              <salaxy-input-number ng-if=\"$ctrl.current.data.vatRate == 'other'\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercent.label\" label-type=\"horizontal\" name=\"vatRate\" ng-model=\"$ctrl.current.accounting.vatPercent\" unit=\"percent\" ng-change=\"$expenseLogic.updateUsecase()\"></salaxy-input-number>\r\n              <div ng-if=\"$expenseLogic.hasGrossVatEntries\">\r\n                <div class=\"row\">\r\n                  <div class=\"col-12\">\r\n                    <table class=\"table table-sm table-striped\" style=\"font-size: 0.8em\">\r\n                      <thead>\r\n                        <tr>\r\n                          <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercentsTable.vatRate\"></th>\r\n                          <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercentsTable.exemptFromTaxation\" class=\"right\"></th>\r\n                          <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercentsTable.tax\" class=\"right\"></th>\r\n                          <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercentsTable.taxable\" class=\"right\"></th>\r\n                        </tr>\r\n                      </thead>\r\n                      <tbody>\r\n                        <tr ng-repeat=\"item in $ctrl.current.accounting.vatEntries\">\r\n                          <td ng-if=\"!!item.gross\">{{ \"VatRate.\" + item.vatRate | sxyEnum }}</td>\r\n                          <td ng-if=\"!!item.gross\" class=\"right\">{{ item.net | currency }}</td>\r\n                          <td ng-if=\"!!item.gross\" class=\"right\">{{ item.tax | currency }}</td>\r\n                          <td ng-if=\"!!item.gross\" class=\"right\">{{ item.gross | currency }}</td>\r\n                        </tr>\r\n                        <tr ng-if=\"$ctrl.current.data.total\" class=\"total\">\r\n                          <th sxy-text=\"SALAXY.UI_Terms.total\"></th>\r\n                          <td class=\"right\">{{ $ctrl.current.data.total.net | currency}}</td>\r\n                          <td class=\"right\">{{ $ctrl.current.data.total.tax | currency}}</td>\r\n                          <td class=\"right\">{{ $ctrl.current.data.total.gross | currency}}</td>\r\n                        </tr>\r\n                      </tbody>\r\n                    </table>\r\n\r\n                  </div>\r\n                </div>\r\n                <salaxy-datepicker-popup name=\"startDate\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.date\"\r\n                  ng-model=\"$ctrl.current.data.date\"></salaxy-datepicker-popup>\r\n              </div>\r\n              <salaxy-form-group name=\"receiptImage\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.receiptUrlAddress\">\r\n                <div class=\"input-group\">\r\n                  <input class=\"form-control\" type=\"text\" autocomplete=\"off\" id=\"file\" name=\"file\" ng-model=\"$ctrl.current.data.fileUrl\">\r\n                  <span class=\"input-group-btn\">\r\n                    <a class=\"btn btn-default\" ng-disabled=\"!$ctrl.showImagePreview()\" ng-href=\"{{$ctrl.current.data.fileUrl}}\" target=\"_blank\" sxy-text=\"SALAXY.UI_Terms.open\"></a>\r\n                  </span>\r\n                </div>\r\n              </salaxy-form-group>\r\n              <div class=\"text-center\" style=\"margin-bottom: 10px;\" ng-if=\"$ctrl.showImagePreview()\">\r\n                <img style=\"max-width: 560px; max-height: 200px;\" ng-src=\"{{$ctrl.current.data.fileUrl}}\">\r\n              </div>\r\n            </div>\r\n            <div ng-switch-when=\"prepaidExpenses\" ng-init=\"$expenseLogic = $ctrl.getUsecaseLogic($ctrl.current)\">\r\n              <salaxy-input-number label=\"{{$ctrl.getConfig().price.label}}\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\"\r\n                require=\"true\"></salaxy-input-number>\r\n              <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercent.label\" label-type=\"horizontal\" enum=\"ExpensesVatRate\"\r\n                hidden-options=\"undefined\" require=\"true\" ng-change=\"$expenseLogic.updateUsecase($ctrl.current)\" name=\"ExpensesVatRate\" ng-model=\"$ctrl.current.data.vatRate\"\r\n                type=\"select\"></salaxy-input-enum>\r\n\r\n              <div ng-switch=\"$ctrl.current.data.vatRate\">\r\n                <span ng-switch-when=\"tax255\" class=\"text-success small\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercents.p255.description\"></span>\r\n                <span ng-switch-when=\"tax24\" class=\"text-success small\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercents.p24.description\"></span>\r\n                <span ng-switch-when=\"tax14\" class=\"text-success small\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercents.p14.description\"></span>\r\n                <span ng-switch-when=\"tax135\" class=\"text-success small\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercents.p135.description\"></span>\r\n                <span ng-switch-when=\"tax10\" class=\"text-success small\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercents.p10.description\"></span>\r\n                <span ng-switch-when=\"tax0\" class=\"text-success small\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercents.p0.description\"></span>\r\n              </div>\r\n              <div ng-if=\"$ctrl.current.data.vatRate == 'multiple'\">\r\n                <p class=\"mb-0\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercentsTable.taxableAmountInPercent\" ps=\":\"></p>\r\n                <div class=\"row\">\r\n                  <salaxy-input-number class=\"col-sm-3\" label=\"25,5%\" label-type=\"basic\" name=\"inpt5\" ng-model=\"$ctrl.current.accounting.vatEntries[4].gross\" ng-change=\"$expenseLogic.updateUsecase()\"></salaxy-input-number>\r\n                  <salaxy-input-number class=\"col-sm-3\" label=\"24%\" label-type=\"basic\" name=\"inpt1\" ng-model=\"$ctrl.current.accounting.vatEntries[0].gross\"\r\n                    ng-change=\"$expenseLogic.updateUsecase()\"></salaxy-input-number>\r\n                  <salaxy-input-number class=\"col-sm-3\" label=\"14%\" label-type=\"basic\" name=\"inpt2\" ng-model=\"$ctrl.current.accounting.vatEntries[1].gross\"\r\n                    ng-change=\"$expenseLogic.updateUsecase()\"></salaxy-input-number>\r\n                  <salaxy-input-number class=\"col-sm-3\" label=\"13,5%\" label-type=\"basic\" name=\"inpt6\" ng-model=\"$ctrl.current.accounting.vatEntries[5].gross\"\r\n                    ng-change=\"$expenseLogic.updateUsecase()\"></salaxy-input-number>\r\n                  <salaxy-input-number class=\"col-sm-3\" label=\"10%\" label-type=\"basic\" name=\"inpt3\" ng-model=\"$ctrl.current.accounting.vatEntries[2].gross\"\r\n                    ng-change=\"$expenseLogic.updateUsecase()\"></salaxy-input-number>\r\n                  <salaxy-input-number class=\"col-sm-3\" label=\"0%\" label-type=\"basic\" name=\"inpt4\" ng-model=\"$ctrl.current.accounting.vatEntries[3].gross\"\r\n                    ng-change=\"$expenseLogic.updateUsecase()\"></salaxy-input-number>\r\n                </div>\r\n              </div>\r\n              <salaxy-input-number ng-if=\"$ctrl.current.data.vatRate == 'other'\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercent.label\" label-type=\"horizontal\" name=\"vatRate\" ng-model=\"$ctrl.current.accounting.vatPercent\" unit=\"percent\" ng-change=\"$expenseLogic.updateUsecase()\"></salaxy-input-number>\r\n              <div ng-if=\"$expenseLogic.hasGrossVatEntries\">\r\n                <div class=\"row\">\r\n                  <div class=\"col-12\">\r\n                    <table class=\"table table-sm table-striped\" style=\"font-size: 0.8em\">\r\n                      <thead>\r\n                        <tr>\r\n                          <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercentsTable.vatRate\"></th>\r\n                          <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercentsTable.exemptFromTaxation\" class=\"right\"></th>\r\n                          <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercentsTable.tax\" class=\"right\"></th>\r\n                          <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.vatPercentsTable.taxable\" class=\"right\"></th>\r\n                        </tr>\r\n                      </thead>\r\n                      <tbody>\r\n                        <tr ng-repeat=\"item in $ctrl.current.accounting.vatEntries\">\r\n                          <td ng-if=\"!!item.gross\">{{ \"VatRate.\" + item.vatRate | sxyEnum }}</td>\r\n                          <td ng-if=\"!!item.gross\" class=\"right\">{{ item.net | currency }}</td>\r\n                          <td ng-if=\"!!item.gross\" class=\"right\">{{ item.tax | currency }}</td>\r\n                          <td ng-if=\"!!item.gross\" class=\"right\">{{ item.gross | currency }}</td>\r\n                        </tr>\r\n                        <tr ng-if=\"$ctrl.current.data.total\" class=\"total\">\r\n                          <th sxy-text=\"SALAXY.UI_Terms.total\"></th>\r\n                          <td class=\"right\">{{ $ctrl.current.data.total.net | currency}}</td>\r\n                          <td class=\"right\">{{ $ctrl.current.data.total.tax | currency}}</td>\r\n                          <td class=\"right\">{{ $ctrl.current.data.total.gross | currency}}</td>\r\n                        </tr>\r\n                      </tbody>\r\n                    </table>\r\n\r\n                  </div>\r\n                </div>\r\n                <salaxy-datepicker-popup name=\"startDate\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.date\"\r\n                  ng-model=\"$ctrl.current.data.date\"></salaxy-datepicker-popup>\r\n              </div>\r\n            </div>\r\n            <div ng-switch-when=\"holidayBonus|holidaySalary|holidayCompensation\" ng-switch-when-separator=\"|\" ng-init=\"$holidaysLogic = $ctrl.getUsecaseLogic($ctrl.current)\">\r\n              <salaxy-input-number ng-if=\"$ctrl.getConfig().amount.units.length > 1\" label=\"SALAXY.UI_Terms.amount\" ng-model=\"$ctrl.current.count\" name=\"count\" label-type=\"horizontal\"\r\n                unit=\"{{$ctrl.ensureUnit($ctrl.current)}}\" units=\"$ctrl.getConfig().amount.units\" on-unit-change=\"$ctrl.current.unit=unit\" \r\n                disabled=\"$ctrl.isDisabled($ctrl.current, 'amount')\" ng-if=\"$ctrl.getConfig().amount.input != 'hidden'\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-number  ng-if=\"!($ctrl.getConfig().amount.units.length > 1)\" label=\"{{$ctrl.getConfig().price.label}}\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n                disabled=\"$ctrl.isDisabled($ctrl.current, 'price')\" placeholder=\"{{ $ctrl.getPlaceholderText($ctrl.current, 'price') }}\" ng-if=\"$ctrl.getConfig().price.input != 'hidden'\"></salaxy-input-number>\r\n              <salaxy-input-number  ng-if=\"$ctrl.getConfig().amount.units.length > 1\" label=\"SALAXY.UI_Terms.price\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n                disabled=\"$ctrl.isDisabled($ctrl.current, 'price')\" ng-if=\"$ctrl.getConfig().price.input != 'hidden'\"></salaxy-input-number>\r\n              <salaxy-datepicker-popup name=\"start\" ng-model=\"$ctrl.current.period.start\" ng-change=\"$holidaysLogic.updatePeriodDays($ctrl.current)\"\r\n                label=\"SALAXY.MODEL.DateRange.start.title\"></salaxy-datepicker-popup>\r\n              <salaxy-datepicker-popup name=\"end\" ng-model=\"$ctrl.current.period.end\" ng-change=\"$holidaysLogic.updatePeriodDays($ctrl.current)\"\r\n                label=\"SALAXY.MODEL.DateRange.end.title\"></salaxy-datepicker-popup>\r\n              <salaxy-form-group name=\"daysCount\" label=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidaysEditDialog.labelHolidaysCount\" ng-if=\"!$ctrl.current.period.days || $ctrl.current.period.days.length == 0\">\r\n                <div class=\"input-group\">\r\n                  <input class=\"form-control\" type=\"text\" autocomplete=\"off\" id=\"daysCount\" name=\"daysCount\" ng-model=\"$ctrl.current.period.daysCount\" disabled>\r\n                  <span class=\"input-group-btn\">\r\n                    <button type=\"button\" class=\"btn btn-default\" ng-click=\"$holidaysLogic.setDaysSelection($ctrl.current)\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidaysEditDialog.editDatesButtonText\"></button>\r\n                  </span>\r\n                </div>\r\n              </salaxy-form-group>\r\n              <salaxy-datepicker ng-model=\"$ctrl.current.period\" name=\"days\" is-multiple=\"true\" label=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidaysEditDialog.labelHolidaysCount\" min-date=\"$ctrl.current.period.start\" max-date=\"$ctrl.current.period.end\" ng-if=\"$ctrl.current.period.days.length > 0\"></salaxy-date-range>\r\n            </div>\r\n            <div ng-switch-when=\"timeRatePay\">\r\n              <salaxy-input-enum label=\"SALAXY.NG1.CalcRowsComponent.editDialog.timeRatePay.timeRatePayKind\" label-type=\"horizontal\"\r\n                enum=\"TimeRatePayKind\" require=\"true\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\" name=\"timeRatePayKind\" ng-model=\"$ctrl.current.data.kind\"\r\n                type=\"select\"></salaxy-input-enum>\r\n              <p>{{ \"TimeRatePayKind.\" + $ctrl.current.data.kind | sxyEnumDescr }}</p>\r\n              <salaxy-input-number ng-if=\"!($ctrl.getConfig().amount.units.length > 1)\" label=\"{{$ctrl.getConfig().amount.label}}\" ng-model=\"$ctrl.current.count\" name=\"count\" label-type=\"horizontal\"\r\n                unit=\"{{$ctrl.getConfig().amount.unit}}\" placeholder=\"{{ $ctrl.getPlaceholderText($ctrl.current, 'amount') }}\" disabled=\"$ctrl.isDisabled($ctrl.current, 'amount')\" ng-if=\"$ctrl.getConfig().amount.input != 'hidden'\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-number ng-if=\"$ctrl.getConfig().amount.units.length > 1\" label=\"SALAXY.UI_Terms.amount\" ng-model=\"$ctrl.current.count\" name=\"count\" label-type=\"horizontal\"\r\n                unit=\"{{$ctrl.ensureUnit($ctrl.current)}}\" units=\"$ctrl.getConfig().amount.units\" on-unit-change=\"$ctrl.current.unit=unit\" \r\n                 disabled=\"$ctrl.isDisabled($ctrl.current, 'amount')\" ng-if=\"$ctrl.getConfig().amount.input != 'hidden'\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-number  ng-if=\"!($ctrl.getConfig().amount.units.length > 1)\" label=\"{{$ctrl.getConfig().price.label}}\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n                disabled=\"$ctrl.isDisabled($ctrl.current, 'price')\" placeholder=\"{{ $ctrl.getPlaceholderText($ctrl.current, 'price') }}\" ng-if=\"$ctrl.getConfig().price.input != 'hidden'\"></salaxy-input-number>\r\n              <salaxy-input-number  ng-if=\"$ctrl.getConfig().amount.units.length > 1\" label=\"SALAXY.UI_Terms.price\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n                  disabled=\"$ctrl.isDisabled($ctrl.current, 'price')\" ng-if=\"$ctrl.getConfig().price.input != 'hidden'\"></salaxy-input-number>\r\n            </div>\r\n            <div ng-switch-when=\"payStats\">\r\n              <salaxy-input-enum label=\"SALAXY.MODEL.PayStatsTypeDefinition.kind.title\" label-type=\"horizontal\"\r\n                enum=\"PayStatsKind\" require=\"true\" ng-change=\"$ctrl.updateUsecase($ctrl.current)\" name=\"payStatsKind\" ng-model=\"$ctrl.current.data.kind\"\r\n                type=\"select\"></salaxy-input-enum>\r\n              <p>{{ \"PayStatsKind.\" + $ctrl.current.data.kind | sxyEnumDescr }}</p>\r\n              <salaxy-input ng-model=\"$ctrl.current.data.id\" name=\"payStatsId\" label-type=\"horizontal\" require=\"true\"\r\n                label=\"SALAXY.MODEL.PayStatsTypeDefinition.id.title\"></salaxy-input>\r\n              <salaxy-input-enum label=\"SALAXY.MODEL.PayStatsTypeDefinition.periodLength.title\" label-type=\"horizontal\"\r\n                enum=\"PayStatsPeriodLength\" require=\"true\"  name=\"payStatsPeriodLength\" ng-model=\"$ctrl.current.data.periodLength\"\r\n                type=\"select\" filter=\"quarter,month,year\"></salaxy-input-enum>\r\n              <salaxy-input-enum label=\"SALAXY.MODEL.PayStatsTypeDefinition.periodDateKind.title\" label-type=\"horizontal\"\r\n                enum=\"PeriodDateKind\" require=\"true\"  name=\"payStatsPeriodDateKind\" ng-model=\"$ctrl.current.data.periodDateKind\"\r\n                type=\"select\"></salaxy-input-enum>\r\n              <salaxy-input ng-model=\"$ctrl.current.data.salary\" name=\"payStatsSalary\" label-type=\"horizontal\"\r\n              label=\"SALAXY.REPORTS.payStatsReport.salary\"></salaxy-input>\r\n              <salaxy-input ng-model=\"$ctrl.current.data.workingTime\" name=\"payStatsWorkingTime\" label-type=\"horizontal\"\r\n              label=\"SALAXY.REPORTS.payStatsReport.workingTime\"></salaxy-input>\r\n              <salaxy-form-group label=\"SALAXY.UI_Terms.updated\" name=\"payStatsUpdatedAt\"\r\n                label-type=\"horizontal\">\r\n                <label class=\"control-label\">{{ $ctrl.current.data.updatedAt | date: \"dd.MM.yyyy HH:mm\" }}</label>\r\n              </salaxy-form-group>\r\n              <salaxy-input-number ng-if=\"!($ctrl.getConfig().amount.units.length > 1)\" label=\"{{$ctrl.getConfig().amount.label}}\" ng-model=\"$ctrl.current.count\" name=\"count\" label-type=\"horizontal\"\r\n                unit=\"{{$ctrl.getConfig().amount.unit}}\" placeholder=\"{{ $ctrl.getPlaceholderText($ctrl.current, 'amount') }}\" disabled=\"$ctrl.isDisabled($ctrl.current, 'amount')\" ng-if=\"$ctrl.getConfig().amount.input != 'hidden'\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-enum label=\"Arvon lähde\" label-type=\"horizontal\"\r\n                name=\"payStatsSource\" ng-model=\"$ctrl.current.data.source\"\r\n                type=\"select\" options=\"{'':'','calc':'Laskettu','manual':'Päivitetty käsin'}\"></salaxy-input-enum>\r\n              <salaxy-input-number ng-if=\"$ctrl.getConfig().amount.units.length > 1\" label=\"SALAXY.UI_Terms.amount\" ng-model=\"$ctrl.current.count\" name=\"count\" label-type=\"horizontal\"\r\n                unit=\"{{$ctrl.ensureUnit($ctrl.current)}}\" units=\"$ctrl.getConfig().amount.units\" on-unit-change=\"$ctrl.current.unit=unit\" \r\n                 disabled=\"$ctrl.isDisabled($ctrl.current, 'amount')\" ng-if=\"$ctrl.getConfig().amount.input != 'hidden'\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-number  ng-if=\"!($ctrl.getConfig().amount.units.length > 1)\" label=\"{{$ctrl.getConfig().price.label}}\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n                disabled=\"$ctrl.isDisabled($ctrl.current, 'price')\" placeholder=\"{{ $ctrl.getPlaceholderText($ctrl.current, 'price') }}\" ng-if=\"$ctrl.getConfig().price.input != 'hidden'\"></salaxy-input-number>\r\n              <salaxy-input-number  ng-if=\"$ctrl.getConfig().amount.units.length > 1\" label=\"SALAXY.UI_Terms.price\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n                  disabled=\"$ctrl.isDisabled($ctrl.current, 'price')\" ng-if=\"$ctrl.getConfig().price.input != 'hidden'\"></salaxy-input-number>\r\n            </div>\r\n            <div ng-switch-default>\r\n              <salaxy-input-number ng-if=\"!($ctrl.getConfig().amount.units.length > 1)\" label=\"{{$ctrl.getConfig().amount.label}}\" ng-model=\"$ctrl.current.count\" name=\"count\" label-type=\"horizontal\"\r\n                unit=\"{{$ctrl.getConfig().amount.unit}}\" placeholder=\"{{ $ctrl.getPlaceholderText($ctrl.current, 'amount') }}\" disabled=\"$ctrl.isDisabled($ctrl.current, 'amount')\" ng-if=\"$ctrl.getConfig().amount.input != 'hidden'\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-number ng-if=\"$ctrl.getConfig().amount.units.length > 1\" label=\"SALAXY.UI_Terms.amount\" ng-model=\"$ctrl.current.count\" name=\"count\" label-type=\"horizontal\"\r\n                unit=\"{{$ctrl.ensureUnit($ctrl.current)}}\" units=\"$ctrl.getConfig().amount.units\" on-unit-change=\"$ctrl.current.unit=unit\" \r\n                 disabled=\"$ctrl.isDisabled($ctrl.current, 'amount')\" ng-if=\"$ctrl.getConfig().amount.input != 'hidden'\">\r\n              </salaxy-input-number>\r\n              <salaxy-input-number  ng-if=\"!($ctrl.getConfig().amount.units.length > 1)\" label=\"{{$ctrl.getConfig().price.label}}\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n                disabled=\"$ctrl.isDisabled($ctrl.current, 'price')\" placeholder=\"{{ $ctrl.getPlaceholderText($ctrl.current, 'price') }}\" ng-if=\"$ctrl.getConfig().price.input != 'hidden'\"></salaxy-input-number>\r\n              <salaxy-input-number  ng-if=\"$ctrl.getConfig().amount.units.length > 1\" label=\"SALAXY.UI_Terms.price\" ng-model=\"$ctrl.current.price\" name=\"price\" label-type=\"horizontal\" require=\"true\"\r\n                  disabled=\"$ctrl.isDisabled($ctrl.current, 'price')\" ng-if=\"$ctrl.getConfig().price.input != 'hidden'\"></salaxy-input-number>\r\n            </div>\r\n          </div>\r\n          <div ng-if=\"$ctrl.current.rowType != 'irIncomeType'\">\r\n            <hr>\r\n            <salaxy-input ng-if=\"$ctrl.current.rowType != 'hourlySalaryWithWorkingTimeCompensation'\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.additionalRows.description\" label-type=\"horizontal\" disabled=\"$ctrl.isDisabled($ctrl.current)\"\r\n              ng-model=\"$ctrl.current.message\" name=\"message\" placeholder=\"{{$ctrl.getMessagePlaceholderText($ctrl.current)}}\"></salaxy-input>\r\n            <salaxy-input label=\"SALAXY.NG1.CalcRowsComponent.editDialog.additionalRows.additionalRow\" label-type=\"horizontal\" disabled=\"$ctrl.isDisabled($ctrl.current)\"\r\n              ng-model=\"$ctrl.current.data.sxySalarySlipRowComment\" name=\"sxySalarySlipRowComment\"></salaxy-input>\r\n          </div>\r\n          <div ng-if=\"$ctrl.isStandAlone && $ctrl.current.rowType != 'absencePeriod'\">\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.NG1.DateRange.labelStartAndEndDate\"></legend>\r\n              <salaxy-datepicker-popup label=\"SALAXY.MODEL.DateRange.start.title\" name=\"salaryDate\" ng-model=\"$ctrl.current.period.start\"></salaxy-datepicker-popup>\r\n              <salaxy-datepicker-popup label=\"SALAXY.MODEL.DateRange.end.title\" name=\"salaryDate\" ng-model=\"$ctrl.current.period.end\"></salaxy-datepicker-popup>\r\n            </fieldset>\r\n          </div>\r\n          <div ng-if=\"$ctrl.current.rowType != 'taxAtSource'\">\r\n            <salaxy-calc-row-cost-accounting calc=\"$ctrl.parent\" row=\"$ctrl.current\" dimensions=\"$ctrl.dimensions\"></salaxy-calc-row-cost-accounting>\r\n          </div>\r\n          <div>\r\n            <fieldset>\r\n              <legend>\r\n                <div class=\"d-flex justify-content-between\">\r\n                  <a ng-show=\"$ctrl.showAccountingEditing()\" class=\"btn-link text-right text-muted\" ng-click=\"showAccountingEditing = !showAccountingEditing\">\r\n                    <small style=\"font-size: 0.7em;\">{{!showAccountingEditing ?('SALAXY.NG1.CalcRowsComponent.editDialog.accounting.entry.rowAccounting' | sxyTranslate) : ('SALAXY.NG1.CalcRowsComponent.editDialog.accounting.entry.closeRowAccounting' | sxyTranslate)}}</small>\r\n                  </a>\r\n                </div>\r\n              </legend>\r\n              <div ng-if=\"showAccountingEditing\">\r\n                <salaxy-form-group name=\"debitAccountNumber\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.entry.debetAccountNumber\">\r\n                  <div class=\"input-group\">\r\n                    <input ng-readonly=\"!$ctrl.isEditable\" class=\"form-control\" type=\"text\" placeholder=\"{{ 'SALAXY.NG1.CalcRowsComponent.editDialog.accounting.entry.accountNumberPlaceholder' | sxyTranslate }}\" autocomplete=\"off\" id=\"debitAccountNumber\" name=\"debitAccountNumber\" ng-model=\"$ctrl.current.accounting.entry.debitAccountNumber\">\r\n                   \r\n                    <span class=\"input-group-btn\" ng-if=\"$ctrl.isEditable\">\r\n                      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.openAccountingRulesetSelection(true)\">...</button>\r\n                    </span>\r\n                  </div>\r\n                </salaxy-form-group>\r\n                <salaxy-form-group name=\"creditAccountNumber\" label=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.entry.creditAccountNumber\">\r\n                  <div class=\"input-group\">\r\n                    <input  ng-readonly=\"!$ctrl.isEditable\" class=\"form-control\" type=\"text\" placeholder=\"{{ 'SALAXY.NG1.CalcRowsComponent.editDialog.accounting.entry.accountNumberPlaceholder' | sxyTranslate }}\" autocomplete=\"off\" id=\"creditAccountNumber\" name=\"creditAccountNumber\" ng-model=\"$ctrl.current.accounting.entry.creditAccountNumber\">               \r\n                    <span class=\"input-group-btn\" ng-if=\"$ctrl.isEditable\">\r\n                      <button  type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.openAccountingRulesetSelection(false)\">...</button>\r\n                    </span>\r\n                  </div>\r\n                </salaxy-form-group>\r\n                <div class=\"text-right d-flex mb-3\" ng-if=\"$ctrl.isEditable\">\r\n                  <button type=\"button\" class=\"btn btn-secondary btn-sm ms-auto me-1 mt-1\" ng-click=\"$ctrl.showRowAccountingPreview()\">{{'SALAXY.NG1.CalcRowsComponent.editDialog.accounting.entry.showAccountingPreview' | sxyTranslate}}</button>\r\n                </div>\r\n              </div>\r\n             \r\n            </fieldset>\r\n          </div>\r\n        </div>\r\n        <div class=\"text-right d-flex\" ng-if=\"$ctrl.isEditable && !$ctrl.definitionEditor.mode\">\r\n          <button type=\"button\" class=\"btn btn-danger float-start\" ng-click=\"$ctrl.closeEditDialog('delete-no-save', $close)\"\r\n            sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.buttons.delete\"></button>\r\n          <button type=\"button\" ng-if=\"$ctrl.isDialog\" class=\"btn btn-default ms-auto me-1\" ng-click=\"$ctrl.closeEditDialog('cancel', $close)\"\r\n            sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.buttons.cancel\"></button>\r\n          <button type=\"submit\" class=\"btn btn-primary\" ng-click=\"$ctrl.closeEditDialog('ok-no-save', $close)\"\r\n            sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.buttons.save\"></button>\r\n        </div>\r\n        <div ng-if=\"!$ctrl.isEditable\" class=\"text-end\">\r\n          <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.closeEditDialog('cancel', $close)\"\r\n            sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.buttons.close\"></button>\r\n        </div>\r\n      </div>\r\n    </form>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/rows/CalcRows2019Editor.html\",`<div class=\"salaxy-component salaxy-calc-rows-editor salaxy-calc-rows-2019-editor\">\r\n\r\n  <div ng-if=\"$ctrl.isInEdit\">\r\n    <table class=\"table table-sm\">\r\n      <thead>\r\n        <tr>\r\n          <th width=\"42px\" class=\"hidden-xxs th-avatar\"></th>\r\n          <th width=\"40%\" class=\"uppercase th-calc-row-type\">{{ $ctrl.title }}</th>\r\n          <th ng-if=\"$ctrl.showDimension()\" ng-repeat=\"definition in $ctrl.getDimensionsToShow()\">{{definition.label}}</th>\r\n          <th class=\"right\" ng-if=\"$ctrl.hasRows\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.amount\"></th>\r\n          <th class=\"right\" ng-if=\"$ctrl.hasRows\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.price\"></th>\r\n          <th class=\"right th-row-total\" ng-if=\"$ctrl.hasRows\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.total\"></th>\r\n          <th colspan=\"3\" ng-if=\"!$ctrl.hasRows\">&nbsp;</th>\r\n          <th class=\"salaxy-calc-rows-editor-btns\">\r\n            <span ng-if=\"$ctrl.showEditButtons\">\r\n              <button class=\"btn btn-sm btn-transparent\" ng-click=\"$ctrl.commit()\" title=\"{{'SALAXY.NG1.CalcRowsComponent.editor.buttons.okIcon' | sxyTranslate}}\">\r\n                <i class=\"bi bi-check-lg text-success\"></i>\r\n              </button>\r\n              <button class=\"btn btn-sm btn-transparent\" ng-click=\"$ctrl.reset()\" title=\"{{'SALAXY.NG1.CalcRowsComponent.editor.buttons.cancelIcon' | sxyTranslate}}\">\r\n                <i class=\"bi bi-x-lg\"></i>\r\n              </button>\r\n            </span>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat-start=\"row in $ctrl.filteredList track by $index\" ng-class=\"$ctrl.getValidation(row).type ? 'row-before-validation' : ''\">\r\n          <td width=\"42px\" class=\"hidden-xxs td-avatar\" ng-class=\"{'td-no-avatar' : !row.rowType}\">\r\n            <salaxy-avatar ng-if=\"row.rowType\" class=\"salaxy-calc-row-type-avatar\" avatar=\"{ color: $ctrl.getConfig(row).color, initials: $ctrl.getConfig(row).iconText, entityType: 'company' }\"></salaxy-avatar>\r\n          </td>\r\n          <td width=\"40%\" class=\"td-calc-row-type\" ng-class=\"{'td-add-new': !row.rowType}\">\r\n            <salaxy-calc-row-type ng-if=\"!row.rowType\" name=\"rowType\" model=\"row\" row-types=\"$ctrl.rowTypes\" categories=\"$ctrl.categories\" placeholder=\"SALAXY.NG1.CalcRowsComponent.editor.calcRowTypePlaceholder\" on-row-changed=\"$ctrl.rowTypeChanged(row)\"></salaxy-calc-row-type>\r\n            <input class=\"form-control\" ng-if=\"row.rowType\" name=\"message\" type=\"text\" ng-model=\"row.message\" ng-disabled=\"$ctrl.isDisabled(row, 'message')\" placeholder=\"{{$ctrl.getMessagePlaceholderText(row)}}\" />\r\n          </td>\r\n          <td  ng-if=\"$ctrl.showDimension()\" ng-repeat=\"definition in $ctrl.getDimensionsToShow()\">\r\n            <div class=\"truncate\">\r\n              <salaxy-calc-row-dimension-input row=\"row\" definition=\"definition\" inherited=\"$ctrl.parent.accounting.dimensions\" read-only=\"$ctrl.mode == 'read-only'\"></salaxy-calc-row-dimension-input>\r\n            </div>\r\n          </td>\r\n          <td ng-if=\"row.rowType\" class=\"right\">\r\n            <salaxy-input-number ng-if=\"$ctrl.getConfig(row).amount.units.length > 1\" on-unit-change=\"row.unit=unit\" name=\"{{ 'iptCount' + (row.rowIndex < 0 ? 'Salary' : row.rowIndex) }}\" ng-model=\"row.count\" label-type=\"plain\" disabled=\"$ctrl.isDisabled(row, 'amount')\" unit=\"{{$ctrl.ensureUnit(row)}}\" units=\"$ctrl.getConfig(row).amount.units\">\r\n            </salaxy-input-number>\r\n            <salaxy-input-number ng-if=\"!($ctrl.getConfig(row).amount.units.length > 1)\" name=\"{{ 'iptCount' + (row.rowIndex < 0 ? 'Salary' : row.rowIndex) }}\" ng-model=\"row.count\" label-type=\"plain\" placeholder=\"{{ $ctrl.getPlaceholderText(row, 'amount') }}\" disabled=\"$ctrl.isDisabled(row, 'amount')\" unit=\"{{$ctrl.getConfig(row).amount.unit}}\">\r\n            </salaxy-input-number>\r\n          </td>\r\n          <td ng-if=\"row.rowType\" class=\"right\">\r\n            <salaxy-input-number ng-if=\"$ctrl.getConfig(row).amount.units.length > 1\" name=\"{{ 'iptPrice' + (row.rowIndex < 0 ? 'Salary' : row.rowIndex) }}\" ng-model=\"row.price\" label-type=\"plain\"  disabled=\"$ctrl.isDisabled(row, 'price')\" require=\"true\"></salaxy-input-number>\r\n            <salaxy-input-number ng-if=\"!($ctrl.getConfig(row).amount.units.length > 1)\" name=\"{{ 'iptPrice' + (row.rowIndex < 0 ? 'Salary' : row.rowIndex) }}\" ng-change=\"row.rowType == 'hourlySalaryWithWorkingTimeCompensation' ? $ctrl.updateUsecase(row) : null\" ng-model=\"row.price\" label-type=\"plain\" placeholder=\"{{ $ctrl.getPlaceholderText(row, 'price') }}\" disabled=\"$ctrl.isDisabled(row, 'price')\" require=\"true\"></salaxy-input-number>\r\n          </td>\r\n          <td ng-if=\"row.rowType\" class=\"right td-row-total\">\r\n            <div>{{ $ctrl.getRowTotal(row) | currency }}</div>\r\n          </td>\r\n          <td ng-if=\"row.rowType\" class=\"salaxy-calc-rows-editor-btns\">\r\n            <button type=\"button\" class=\"edit btn btn-info btn-sm\" ng-disabled=\"!row.rowType\" ng-click=\"$ctrl.showEditDialog(row)\" title=\"{{'SALAXY.NG1.CalcRowsComponent.editor.buttons.editIcon' | sxyTranslate}}\"><i class=\"bi bi-pencil-fill\"></i></button>\r\n            <button type=\"button\" class=\"delete btn btn-danger btn-sm\" ng-if=\"row.rowIndex >= 0\" ng-click=\"$ctrl.delete(row)\" title=\"{{'SALAXY.NG1.CalcRowsComponent.editor.buttons.deleteIcon' | sxyTranslate}}\"><i class=\"bi bi-trash-fill\"></i></button>\r\n          </td>\r\n          <td ng-if=\"!row.rowType\" colspan=\"2\" class=\"td-add-new-btn\">\r\n            <div>\r\n              <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.createNew()\"><i class=\"bi bi-info-circle-fill text-primary me-2\"></i><span\r\n                  sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.buttons.readMore\" ps=\"...\"></span></button>\r\n            </div>\r\n          </td>\r\n          <td ng-if=\"!row.rowType\" colspan=\"2\" class=\"td-no-btns\">&nbsp;</td>\r\n        </tr>\r\n        <tr ng-if=\"row.rowType == 'hourlySalaryWithWorkingTimeCompensation' && $ctrl.getValidation(row).type != 'error'\" ng-repeat=\"compensationRow in row.data.compensationRows track by $index\" class=\"no-border\">\r\n          <td width=\"42px\" class=\"hidden-xxs td-avatar\">\r\n          </td>\r\n          <td width=\"40%\" class=\"td-calc-row-type\">\r\n            <input class=\"form-control\" name=\"message\" type=\"text\" readonly=\"true\" value=\"{{ compensationRow.message || ('WorkingTimeCompensationKind.' + row.data.kind | sxyEnum) }}, {{ row.data.pricing == 'percent' ? (compensationRow.percent | sxyCount:'percent') : (compensationRow.price | currency) + ' / h' }}\" />\r\n          </td>\r\n          <td  ng-if=\"$ctrl.showDimension()\" ng-repeat=\"definition in $ctrl.getDimensionsToShow()\">\r\n            <div style=\"min-width: 100px\" class=\"truncate\">\r\n              <salaxy-calc-row-dimension-input row=\"row\" definition=\"definition\" inherited=\"$ctrl.parent.accounting.dimensions\" read-only=\"true\"></salaxy-calc-row-dimension-input>\r\n            </div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <salaxy-input-number name=\"{{ 'iptCount' + (row.rowIndex < 0 ? 'Salary' : row.rowIndex) }}\" ng-if=\"compensationRow.count != null\" ng-model=\"compensationRow.count\" label-type=\"plain\" readonly=\"true\">\r\n            </salaxy-input-number>\r\n            <salaxy-input-number name=\"{{ 'iptCount' + (row.rowIndex < 0 ? 'Salary' : row.rowIndex) }}\" ng-if=\"compensationRow.count == null\" ng-model=\"row.count\" label-type=\"plain\" readonly=\"true\"></salaxy-input-number>\r\n            </salaxy-input-number>\r\n          </td>\r\n          <td class=\"right\">\r\n            <salaxy-input-number name=\"{{ 'iptPrice' + (row.rowIndex < 0 ? 'Salary' : row.rowIndex) }}\" ng-model=\"compensationRow.price\" label-type=\"plain\" readonly=\"true\"></salaxy-input-number>\r\n          </td>\r\n          <td class=\"right td-row-total\">\r\n            <div>{{ (compensationRow.price * (compensationRow.count || row.count || 1)) | currency }}</div>\r\n          </td>\r\n          <td></td>\r\n        </tr>\r\n        <tr ng-repeat-end class=\"row-validation no-border\" ng-if=\"row.rowType != 'hourlySalaryWithWorkingTimeCompensation' || $ctrl.getValidation(row).type == 'error'\">\r\n          <td></td>\r\n          <td colspan=\"5\">\r\n            <small class=\"\" ng-if=\"$ctrl.getValidation(row).type == 'default'\">\r\n              {{ $ctrl.getValidation(row).msg | sxyTranslate }}\r\n              <a href=\"\" ng-click=\"$ctrl.showEditDialog(row)\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.validation.edit\" ps=\"...\"></a>\r\n            </small>\r\n            <span ng-if=\"$ctrl.getValidation(row).type == 'error'\">\r\n              <span class=\"label label-danger\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.validation.note\"></span>\r\n            <small class=\"alert-danger\">{{ $ctrl.getValidation(row).msg | sxyTranslate }}\r\n                <a href=\"\" ng-click=\"$ctrl.showEditDialog(row)\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.validation.edit\" ps=\"...\"></a>\r\n              </small>\r\n            </span>\r\n          </td>\r\n        </tr>\r\n        <tr class=\"new-row\">\r\n          <td width=\"42px\" class=\"hidden-xxs td-avatar border-0\" ng-class=\"{'td-no-avatar' : !row.rowType}\">\r\n          </td>\r\n          <td width=\"40%\" class=\"border-0\">\r\n            <salaxy-calc-row-type name=\"newRowType\" model=\"$ctrl.newRow\" placeholder=\"SALAXY.NG1.CalcRowsComponent.editor.calcRowTypePlaceholder\" on-row-changed=\"$ctrl.commitNewRow()\" row-types=\"$ctrl.rowTypes\" categories=\"$ctrl.categories\" clear-on-select=\"true\"></salaxy-calc-row-type>\r\n          </td>\r\n          <td colspan=\"2\" class=\"td-add-new-btn border-0\">\r\n            <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showRowTypeSelectionDialog()\"><i class=\"bi bi-info-circle-fill text-primary me-2\"></i> <span\r\n                sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.buttons.readMore\" ps=\"...\"></span></button>\r\n          </td>\r\n          <td colspan=\"2\" class=\"td-no-btns border-0\">&nbsp;</td>\r\n        </tr>\r\n      </tbody>\r\n      <tfoot ng-if=\"$ctrl.hasRows\">\r\n        <tr class=\"total\">\r\n          <th width=\"42px\" class=\"hidden-xxs\"></th>\r\n          <td>\r\n            <strong sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.totals.finalCost\"></strong>\r\n          </td>\r\n          <td colspan=\"3\" class=\"right\">\r\n            <strong>{{ $ctrl.getFinalCost() | currency }}\r\n              <!--{{ $ctrl.getTotal() | currency }}--></strong>\r\n          </td>\r\n          <td colspan=\"2\"></td>\r\n        </tr>\r\n      </tfoot>\r\n    </table>\r\n\r\n  </div>\r\n  <div ng-if=\"!$ctrl.isInEdit\">\r\n    <table class=\"table table-sm\">\r\n      <thead>\r\n        <tr>\r\n          <th width=\"42px\" class=\"hidden-xxs\"></th>\r\n          <th width=\"40%\" class=\"uppercase\">{{ $ctrl.title || ('SALAXY.NG1.CalcRowsComponent.editor.calcRow' | sxyTranslate) }}</th>\r\n          <th></th>\r\n          <th class=\"right\" ng-if=\"$ctrl.hasRows\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.totals.total\"></th>\r\n          <th class=\"salaxy-calc-rows-editor-btns text-end\">\r\n            <span ng-if=\"$ctrl.showEditButtons && $ctrl.mode != 'read-only'\">\r\n              <button ng-if=\"$ctrl.showEditButtons && $ctrl.mode != 'read-only'\" ng-hide=\"$ctrl.parent.isReadOnly\" ng-disabled=\"!$ctrl.isEditable\" ng-click=\"$ctrl.startEdit()\" type=\"button\" class=\"edit btn btn-info btn-sm\" title=\"{{'SALAXY.NG1.CalcRowsComponent.editor.buttons.editIcon' | sxyTranslate}}\">\r\n                <i class=\"bi bi-pencil-fill\"></i>\r\n              </button>\r\n            </span>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.filteredList track by $index\">\r\n          <td width=\"42px\" class=\"hidden-xxs\">\r\n            <salaxy-avatar ng-if=\"row.rowType\" class=\"salaxy-calc-row-type-avatar\" avatar=\"{ color: $ctrl.getConfig(row).color, initials: $ctrl.getConfig(row).iconText, entityType: 'company' }\"></salaxy-avatar>\r\n          </td>\r\n          <td width=\"50%\">{{$ctrl.getMessagePlaceholderText(row)}}</td>\r\n          <td ng-if=\"row.rowType\" class=\"right\">\r\n            <small class=\"text-muted\" ng-if=\"row.count && row.count != 1\">{{row.count | sxyCount : row.unit }} * {{ row.price | currency }}</small>\r\n          </td>\r\n          <td ng-if=\"row.rowType\" class=\"right\">\r\n            <div>{{ $ctrl.getRowTotal(row) | currency }}</div>\r\n          </td>\r\n          <td ng-if=\"row.rowType\" class=\"salaxy-calc-rows-editor-btns text-end\">\r\n            <button type=\"button\" class=\"edit btn btn-info btn-sm\" ng-disabled=\"!row.rowType\" ng-click=\"$ctrl.showEditDialog(row)\" title=\"{{'SALAXY.NG1.CalcRowsComponent.editor.buttons.infoIcon' | sxyTranslate}}\"><i class=\"bi bi-pencil-fill\"></i></button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n      <tfoot ng-if=\"$ctrl.hasRows && $ctrl.hideFinalCostRow\">\r\n        <tr class=\"total\">\r\n          <td width=\"42px\" class=\"hidden-xxs\"></td>\r\n          <td>\r\n            <strong sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.totals.total\"></strong>\r\n          </td>\r\n          <td></td>\r\n          <td class=\"right\">\r\n            <strong>\r\n              <!--{{ $ctrl.getTotal() | currency }}--></strong>\r\n          </td>\r\n          <td></td>\r\n        </tr>\r\n        <tr ng-if=\"$ctrl.showGrossTotals\">\r\n          <th width=\"42px\" class=\"hidden-xxs\"></th>\r\n          <td>\r\n            <span sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.totals.grossTotal\"></span><br>\r\n            <small class=\"text-muted\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.totals.netSalary\"></small>\r\n          </td>\r\n          <td>\r\n\r\n          </td>\r\n          <td class=\"right\">\r\n            {{ $ctrl.getGrossTotal() | currency }}<br>\r\n            <small class=\"text-muted\">{{ $ctrl.getNetSalary() | currency }}</small>\r\n          </td>\r\n          <td></td>\r\n        </tr>\r\n        <tr ng-if=\"$ctrl.showGrossTotals\" class=\"total\">\r\n          <th width=\"42px\" class=\"hidden-xxs\"></th>\r\n          <td>\r\n            <strong sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.totals.finalCost\"></strong>\r\n            <br>\r\n            <small class=\"text-muted\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.totals.totalPayment\"></small>\r\n          </td>\r\n          <td>\r\n          </td>\r\n          <td class=\"right\">\r\n            <strong>{{ $ctrl.getFinalCost() | currency }}</strong><br>\r\n            <small class=\"text-muted\">{{ $ctrl.getTotalPayment() | currency }}</small>\r\n          </td>\r\n          <td></td>\r\n        </tr>\r\n      </tfoot>\r\n    </table>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/rows/CalcsIrRows.html\",`<div class=\"salaxy-calc-ir-rows salaxy-component\">\r\n  <sxy-table ng-ref=\"$ctrl.$sxyTable\" options=\"$ctrl.tableConfig.options\" include=\"$ctrl.tableConfig.include\" data=\"$ctrl.tableConfig.data\"></sxy-table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/rows/RowTypeEditDialog.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\">Palkkalaji: {{ $ctrl.current.config.label }}</h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n</div>\r\n<div class=\"modal-body\" id=\"modal-body\">\r\n  <salaxy-tab-buttons\r\n    current-tab=\"$ctrl.currentTab\"\r\n    options=\"[\r\n      { 'value': 'default', 'text': 'SALAXY.NG1.WorkerDetailsComponent.workerInfo' },\r\n      { 'value': 'defaultseditor', 'text': 'Oletusarvot' },\r\n      { 'value': 'kinds', 'text': 'Alalajit', disabled: !$ctrl.current.config.kind.values.length },\r\n      { 'value': 'editor', 'text': 'Esikatselu, UI' },\r\n      { 'value': 'json', 'text': 'Esikatselu, data' },\r\n      { 'value': 'formulas', 'text': 'Laskukaavat', 'hidden': !(('bizConfigs' | sxyIsInRole) && $ctrl.definitionEditor.mode != 'builtIn') },\r\n      { 'value': 'examples', 'text': 'Kehittäjälle', 'hidden': !(('!prod' | sxyIsInRole) && $ctrl.definitionEditor.mode == 'builtIn') }\r\n    ]\"\r\n    tabs-id=\"rowTypeEditDialogTabs\">\r\n  </salaxy-tab-buttons>\r\n  <div class=\"tab-content\" id=\"tab-content-rowTypeEditDialogTabs\">\r\n    <div class=\"tab-pane\" id=\"default-tab\">\r\n      <sxy-form open-api=\"salaxy-secure/schemas/v02.json\" type=\"CalcRowConfig\" auto-gen=\"false\" debugger=\"false\"\r\n        model=\"$ctrl.current.config\" read-only=\"{{ $ctrl.definitionEditor.mode == 'builtIn' }}\">\r\n        <div>\r\n          <salaxy-form-group name=\"id\" class=\"salaxy-read-only\" label=\"Koodi\">\r\n            <div class=\"salaxy-read-only-value\">\r\n              <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.copyToClipboard($ctrl.current.config.type)\" title=\"Kopioi ID leikepöydälle\">\r\n                <i class=\"bi bi-clipboard\" aria-hidden=\"true\"></i></button>\r\n              <code>{{ $ctrl.current.config.type }}</code>\r\n            </div>\r\n            <p>Kopioi tämä koodi esim. tuntiraportointijärjestelmään, jotta tiedot lähetetään Palkkaukseen oikealla koodilla.</p>\r\n          </salaxy-form-group>\r\n          <fieldset>\r\n            <legend>Rivityypin kuvaus</legend>\r\n            <sxy-input label=\"Teksti\" id=\"label\" model=\"form.label\"></sxy-input>\r\n            <sxy-input label=\"Kuvaus\" id=\"descr\" model=\"form.descr\"></sxy-input>\r\n            <sxy-input label=\"Kategoria\" id=\"category\" model=\"form.category\" options=\"CalculationRowCategory\"></sxy-input>\r\n            <sxy-input label=\"Suosikki\" id=\"favorite\" model=\"form.favorite\" type=\"integer\"></sxy-input>\r\n            <sxy-input label=\"Väri\" id=\"color\" model=\"form.color\"></sxy-input>\r\n            <sxy-input label=\"Ikonin teksti\" id=\"iconText\" model=\"form.iconText\" format=\"color\"></sxy-input>\r\n          </fieldset>\r\n          <div class=\"row\">\r\n            <div class=\"col-sm-6\">\r\n              <fieldset>\r\n                <legend>Hinta</legend>\r\n                <sxy-input label=\"Teksti\" id=\"price.label\" model=\"form.price.label\"></sxy-input>\r\n                <!-- TODO: Fix options to be drop-down -->\r\n                <sxy-input label=\"Kentän tyyppi\" id=\"price.input\" model=\"form.price.input\" options=\"['number','hidden','readOnly']\" format=\"select\"></sxy-input>\r\n                <sxy-input label=\"Oletus\" id=\"price.default\" model=\"form.price.default\"></sxy-input>\r\n              </fieldset>\r\n            </div>\r\n            <div class=\"col-sm-6\">\r\n              <fieldset>\r\n                <legend>Määrä</legend>\r\n                <sxy-input label=\"Teksti\" id=\"amount.label\" model=\"form.amount.label\"></sxy-input>\r\n                <sxy-input label=\"Kentän tyyppi\" id=\"amount.input\" model=\"form.amount.input\" options=\"['number','hidden','readOnly']\" format=\"select\"></sxy-input>\r\n                <sxy-input label=\"Oletus\" id=\"amount.default\" model=\"form.amount.default\"></sxy-input>\r\n              </fieldset>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </sxy-form>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"defaultseditor-tab\">\r\n      <div>\r\n        <ng-include src=\"'salaxy-components/calc/rows/CalcRows2019EditDialog.html'\"></ng-include>\r\n      </div>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"kinds-tab\">\r\n      <table>\r\n        <thead>\r\n          <tr>\r\n            <th>Nro</th>\r\n            <th>Teksti</th>\r\n            <th>Kuvaus</th>\r\n            <th></th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr ng-repeat-start=\"kind in $ctrl.current.config.kind.values\">\r\n            <td>{{ kind.order }}</td>\r\n            <td>{{ kind.label }}</td>\r\n            <td>{{ kind.descr }}</td>\r\n            <td rowspan=\"2\">\r\n              <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.copyToClipboard($ctrl.current.config.type + '/' + kind.name)\" title=\"Kopioi ID leikepöydälle\">\r\n                <i class=\"bi bi-clipboard\" aria-hidden=\"true\"></i></button>\r\n            </td>\r\n          </tr>\r\n          <tr ng-repeat-end>\r\n            <td></td>\r\n            <td colspan=\"2\">\r\n              <code>{{ $ctrl.current.config.type }}/{{ kind.name }}</code>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"editor-tab\">\r\n      <div>\r\n        <div class=\"alert alert-warning\">\r\n          <strong>Huom!</strong> Tuotteen palkkalajeja ei voi muokata. Tämä näkymä on vain esikatselua varten.\r\n        </div>\r\n        <ng-include src=\"'salaxy-components/calc/rows/CalcRows2019EditDialog.html'\"></ng-include>\r\n      </div>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"json-tab\">\r\n      <div ng-if=\"true || $ctrl.currentTab == 'json'\">\r\n        <salaxy-json-formatter key=\"'Data'\" json=\"$ctrl.current\" open=\"2\"></salaxy-json-formatter>\r\n      </div>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"formulas-tab\" heading=\"Laskukaavat\">\r\n      <div ng-if=\"$ctrl.currentTab == 'formulas'\">\r\n        <salaxy-calc-row-formula row=\"$ctrl.current\"></salaxy-calc-row-formula>\r\n      </div>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"examples-tab\">\r\n      <div ng-if=\"$ctrl.currentTab == 'examples'\">\r\n        <salaxy-calc-row-documentation row=\"$ctrl.current\"></salaxy-calc-row-documentation>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button type=\"button\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n  <button type=\"button\" ng-if=\"$ctrl.definitionEditor.mode == 'custom'\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/SalaryDateKindButton.html\",`<div class=\"salaxy-date-kind-button salaxy-component\" ng-if=\"!('salaxyPay' | sxyIsInRole)\">\r\n  <div class=\"dropdown\" ng-class=\"$ctrl.buttonClass\">\r\n    <button id=\"btnSalaryDateKind\" type=\"button\" ng-disabled=\"$ctrl.disabled\" class=\"btn btn-default btn-block dropdown-toggle justify-content-start\" data-bs-toggle=\"dropdown\">\r\n      <salaxy-avatar class=\"py-1\" avatar=\"$ctrl.currentSalaryDateKind.avatar\" template-url=\"iconAvatar.html\"></salaxy-avatar>\r\n      <span class=\"button-text\">\r\n        {{ $ctrl.currentSalaryDateKind.text | sxyTranslate}}\r\n      </span>\r\n    </button>\r\n    <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"btnSalaryDateKind\">\r\n      <li role=\"menuitem\" ng-class=\"{ 'disabled': $ctrl.disabled }\" ng-repeat=\"salaryDateKind in $ctrl.salaryDateKinds\">\r\n        <a href=\"\" ng-click=\"$ctrl.setSalaryDateKind(salaryDateKind.value)\" class=\"dropdown-item d-flex align-items-center\">\r\n          <salaxy-avatar avatar=\"salaryDateKind.avatar\" class=\"me-2\" template-url=\"iconAvatar.html\"></salaxy-avatar>\r\n          <span class=\"button-text\">\r\n            {{ salaryDateKind.text | sxyTranslate }}\r\n          </span>\r\n        </a>\r\n      </li>\r\n    </ul>\r\n  </div>\r\n</div>\r\n<div ng-if=\"('salaxyPay' | sxyIsInRole)\" ng-controller=\"NewPaymentController as $newCtrl\">\r\n<!-- When using salaxy pay, we don't need to show the salary date kind button -->\r\n</div>\r\n<script type=\"text/ng-template\" id=\"iconAvatar.html\">\r\n  <i class=\"salaxy-avatar bi\" ng-class=\"$ctrl.avatar.icon\" ng-style=\"{color: $ctrl.avatar.color }\"></i>\r\n</script>`);\n\n $templateCache.put(\"salaxy-components/calc/usecases/household-childCare.html\",`<div>\r\n  <div ng-if=\"$ctrl.usecaseData.id == 'childCare/mll'\">\r\n    <div class=\"card-header childcare\">\r\n      <span class=\"float-start\">\r\n        <div class=\"icon-wrapper salaxy-household-usecase-avatar\">\r\n          <div class=\"main-icon-wrapper\" ng-if=\"$ctrl.usecaseData.icon\">\r\n            <img ng-src=\"{{$ctrl.usecaseData.icon}}\">\r\n          </div>\r\n          <div ng-if=\"$ctrl.usecaseData.badge\" class=\"badge-image-wrapper\">\r\n            <img ng-src=\"{{$ctrl.usecaseData.badge}}\">\r\n          </div>\r\n        </div>\r\n      </span>\r\n      <h1>{{$ctrl.usecaseData.label}}</h1>\r\n      <p class=\"calc-text\">\r\n        {{$ctrl.salaryRow.count || 0}} h x {{$ctrl.salaryRow.price || '9,5'}} € <span ng-if=\"$ctrl.usecaseData.isSunday\" sxy-text=\"SALAXY.NG1.HouseholdUsecaseComponent.base.hoursPerPriceWithSunday\"></span>\r\n        <span class=\"result-text\" ng-if=\"!$ctrl.usecaseData.isSunday\">{{ ($ctrl.salaryRow.count || 0) * ($ctrl.salaryRow.price || 9.5) | currency }}</span>\r\n        <span class=\"result-text\" ng-if=\"$ctrl.usecaseData.isSunday\">{{ ($ctrl.salaryRow.count || 0) * ($ctrl.salaryRow.price || 9.5) * 2 | currency }}</span>\r\n      </p>\r\n      <a class=\"btn-link btn-showmore\" ng-click=\"showInfo = !showInfo\"><span sxy-text=\"SALAXY.UI_Terms.showMore\"></span><i class=\"bi bi-info-circle-fill\"></i></a>\r\n    </div>\r\n    <div class=\"card-body\">\r\n      <p sxy-html=\"SALAXY.NG1.HouseholdUsecaseComponent.mll.shortInfoText.html\"></p>\r\n      <span class=\"collapse\" ng-class=\"{show: showInfo}\">\r\n        <p sxy-html=\"SALAXY.NG1.HouseholdUsecaseComponent.mll.longInfoText.html\"></p>\r\n      </span>\r\n      <div class=\"form-horizontal\">\r\n        <salaxy-input-number name=\"hours\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.base.hourCount\" ng-model=\"$ctrl.salaryRow.count\" label-cols=\"col-sm-6\" required>\r\n        </salaxy-input-number>\r\n        <salaxy-input-boolean name=\"isSunday\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.base.isSunday\" type=\"switch\" ng-model=\"$ctrl.usecaseData.isSunday\" label-true=\"SALAXY.UI_Terms.yes\" label-false=\"SALAXY.UI_Terms.no\" label-cols=\"col-sm-6\"></salaxy-input-boolean>\r\n        <salaxy-input-boolean name=\"useCustomPrice\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.mll.useCustomPrice\" type=\"switch\" ng-model=\"$ctrl.usecaseData.useCustomPrice\" label-true=\"SALAXY.UI_Terms.yes\" label-false=\"SALAXY.UI_Terms.no\" label-cols=\"col-sm-6\">\r\n        </salaxy-input-boolean>\r\n        <salaxy-input-number ng-if=\"$ctrl.usecaseData.useCustomPrice\" name=\"price\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.base.eurPerH\" ng-model=\"$ctrl.salaryRow.price\" label-cols=\"col-sm-6\"></salaxy-input-number>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div ng-if=\"$ctrl.usecaseData.id != 'childCare/mll'\">\r\n    <div class=\"card-header childcare\">\r\n      <span class=\"float-start\">\r\n        <div class=\"icon-wrapper salaxy-household-usecase-avatar\">\r\n          <div class=\"main-icon-wrapper\" ng-if=\"$ctrl.usecaseData.icon\">\r\n            <img ng-src=\"{{$ctrl.usecaseData.icon}}\" type=\"image/svg+xml\">\r\n          </div>\r\n          <div ng-if=\"$ctrl.usecaseData.badge\" class=\"badge-image-wrapper\">\r\n            <img ng-src=\"{{$ctrl.usecaseData.badge}}\">\r\n          </div>\r\n        </div>\r\n      </span>\r\n\r\n      <h1>{{$ctrl.usecaseData.label}}</h1>\r\n      <p class=\"calc-text\">\r\n        <span ng-if=\"$ctrl.salaryRow.rowType=='hourlySalary' || $ctrl.salaryRow.rowType == 'unknown'\">{{$ctrl.salaryRow.count || 0}} h x\r\n          {{$ctrl.salaryRow.price || 0}} €</span>\r\n        <span ng-if=\"$ctrl.salaryRow.rowType=='monthlySalary'\">{{$ctrl.salaryRow.price || 0}} <span sxy-text=\"SALAXY.NG1.HouseholdUsecaseComponent.base.eurPerMonth\"></span></span>\r\n        <span ng-if=\"$ctrl.usecaseData.isChildcareSubsidy\">+ {{ $ctrl.usecaseData.subsidyAmount || 0 }} <span\r\n            sxy-test=\"SALAXY.NG1.HouseholdUsecaseComponent.childCare.isChildCareSubsidy\"></span></span>\r\n        <span ng-if=\"$ctrl.isHouseholdDeductible\" sxy-text=\"SALAXY.NG1.HouseholdUsecaseComponent.base.isHouseholdDeductible\"></span>\r\n        <span class=\"result-text\" ng-if=\"$ctrl.salaryRow.rowType=='hourlySalary' || $ctrl.salaryRow.rowType == 'unknown'\">{{ ($ctrl.salaryRow.count || 0) * ($ctrl.salaryRow.price || 0) }}\r\n          €</span>\r\n        <span class=\"result-text\" ng-if=\"$ctrl.salaryRow.rowType=='monthlySalary'\">{{ $ctrl.salaryRow.price || 0}} €</span>\r\n      </p>\r\n      <a class=\"btn-link btn-showmore\" ng-click=\"showInfo = !showInfo\"><span sxy-text=\"SALAXY.UI_Terms.showMore\"></span><i class=\"bi bi-info-circle-fill\"></i></a>\r\n    </div>\r\n    <div class=\"card-body\">\r\n      <p sxy-text=\"SALAXY.NG1.HouseholdUsecaseComponent.childCare.shortInfoText.html\"></p>\r\n      <span class=\"collapse\" ng-class=\"{show: showInfo}\">\r\n\r\n        <p ng-if=\"$ctrl.usecaseData.isChildcareSubsidy\" sxy-html=\"SALAXY.NG1.HouseholdUsecaseComponent.childCare.longInfoTextIfchildCareSubsidy.html\"></p>\r\n        \r\n        <p ng-if=\"!$ctrl.usecaseData.isChildcareSubsidy\" sxy-html=\"SALAXY.NG1.HouseholdUsecaseComponent.childCare.longInfoTextIfNotchildCareSubsidy.html\"></p>\r\n\r\n        \r\n      </span>\r\n      <div class=\"form-horizontal\">\r\n        <salaxy-input-number ng-show=\"$ctrl.usecaseData.isChildcareSubsidy\" name=\"subsidyAmount\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.childCare.childCareSubsidy\" ng-model=\"$ctrl.usecaseData.subsidyAmount\" label-cols=\"col-sm-6\">\r\n        </salaxy-input-number>\r\n        <salaxy-input-enum type=\"select\" name=\"mainRowType\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.base.salaryKind\" ng-model=\"$ctrl.salaryRow.rowType\" options=\"{'hourlySalary': ('SALAXY.ENUM.SalaryKind.hourlySalary.label' | sxyTranslate),'monthlySalary':('SALAXY.ENUM.SalaryKind.monthlySalary.label'| sxyTranslate)}\"\r\n          ng-change=\"$ctrl.changeRowType()\" label-cols=\"col-sm-6\" required></salaxy-input-enum>\r\n        <salaxy-input-number name=\"price\" label=\"{{$ctrl.usecaseData.isChildcareSubsidy ? $ctrl.priceLabel + ( 'SALAXY.NG1.HouseholdUsecaseComponent.childCare.inAdditionToBenefits'|sxyTranslate) : $ctrl.priceLabel}}\" ng-model=\"$ctrl.salaryRow.price\" label-cols=\"col-sm-6\"></salaxy-input-number>\r\n        <salaxy-input-number ng-if=\"$ctrl.salaryRow.rowType=='hourlySalary'\" name=\"amount\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.base.hourCount\" ng-model=\"$ctrl.salaryRow.count\" required label-cols=\"col-sm-6\"></salaxy-input-number>\r\n\r\n        <salaxy-input-boolean ng-if=\"!$ctrl.usecaseData.isChildcareSubsidy\" name=\"isHouseholdDeductible\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.base.householdDeduction\" type=\"radio\" ng-model=\"$ctrl.isHouseholdDeductible\" label-true=\"SALAXY.NG1.HouseholdUsecaseComponent.base.householdDeductionTrue\"\r\n          label-false=\"SALAXY.NG1.HouseholdUsecaseComponent.base.householdDeductionFalse\" label-cols=\"col-sm-6\"></salaxy-input-boolean>\r\n        <div class=\"form-group\" ng-if=\"$ctrl.usecaseData.isChildcareSubsidy\">\r\n          <div class=\"col-sm-6\"><strong sxy-text=\"SALAXY.NG1.HouseholdUsecaseComponent.childCare.workerTotalPayment\"></strong></div>\r\n          <div class=\"col-sm-6 text-end\" ng-if=\"$ctrl.salaryRow.rowType=='hourlySalary'\">\r\n            {{ ($ctrl.salaryRow.price || 0) * ($ctrl.salaryRow.count || 0) + ($ctrl.usecaseData.subsidyAmount || 0) }}</div>\r\n          <div class=\"col-sm-6 text-end\" ng-if=\"$ctrl.salaryRow.rowType=='monthlySalary'\">\r\n            {{ ($ctrl.salaryRow.price || 0) + ($ctrl.usecaseData.subsidyAmount || 0) }}</div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/usecases/household-cleaning.html\",`<div>\r\n  <div class=\"card-header cleaning\">\r\n    <span class=\"float-start\">\r\n      <div class=\"icon-wrapper salaxy-household-usecase-avatar\">\r\n        <div class=\"main-icon-wrapper\">\r\n          <img ng-src=\"{{$ctrl.usecaseData.icon}}\">\r\n        </div>\r\n      </div>\r\n    </span>\r\n    <h1>{{$ctrl.usecaseData.label}}</h1>\r\n    <p class=\"calc-text\">\r\n\r\n      <span ng-if=\"$ctrl.salaryRow.rowType=='hourlySalary' || $ctrl.salaryRow.rowType == 'unknown'\">{{$ctrl.salaryRow.count || 0}} h x {{$ctrl.salaryRow.price || 0}}\r\n        €</span>\r\n      <span ng-if=\"$ctrl.salaryRow.rowType=='salary' || $ctrl.salaryRow.rowType=='monthlySalary'\">{{$ctrl.salaryRow.price || 0}} € <span\r\n          ng-if=\"$ctrl.salaryRow.rowType=='monthlySalary'\" sxy-text=\"SALAXY.NG1.HouseholdUsecaseComponent.base.pricePerMonth\"></span></span>\r\n\r\n      <span ng-if=\"$ctrl.isHouseholdDeductible\" sxy-text=\"SALAXY.NG1.HouseholdUsecaseComponent.base.isHouseholdDeductible\"></span>\r\n\r\n      <span class=\"result-text\" ng-if=\"$ctrl.salaryRow.rowType=='hourlySalary' || $ctrl.salaryRow.rowType == 'unknown'\">{{ ($ctrl.salaryRow.count || 0) * ($ctrl.salaryRow.price || 0) }}\r\n        €</span>\r\n      <span class=\"result-text\" ng-if=\"$ctrl.salaryRow.rowType=='salary' || $ctrl.salaryRow.rowType=='monthlySalary'\">{{ $ctrl.salaryRow.price || 0}} € </span>\r\n    </p>\r\n    <a class=\"btn-link btn-showmore\" ng-click=\"showInfo = !showInfo\"><span sxy-text=\"SALAXY.UI_Terms.showMore\"></span><i class=\"bi bi-info-circle-fill\"></i></a>\r\n  </div>\r\n  <div class=\"card-body\">\r\n    <p sxy-html=\"SALAXY.NG1.HouseholdUsecaseComponent.cleaning.shortInfoText.html\"></p>\r\n    <span class=\"collapse\" ng-class=\"{show: showInfo}\" sxy-html=\"SALAXY.NG1.HouseholdUsecaseComponent.cleaning.longInfoText.html\"></span>\r\n    <div class=\"form-horizontal\">\r\n      <salaxy-textarea ng-if=\"$ctrl.usecaseData.subType == 'other'\" name=\"workTypeOtherMessage\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.base.workDescription\" ng-model=\"$ctrl.usecaseData.workTypeOtherMessage\" label-cols=\"col-sm-6\"></salaxy-textarea>\r\n      <salaxy-input-enum type=\"select\" name=\"mainRowType\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.base.salaryKind\" ng-model=\"$ctrl.salaryRow.rowType\" options=\"{'salary':('SALAXY.ENUM.SalaryKind.salary.label'| sxyTranslate),'hourlySalary':('SALAXY.ENUM.SalaryKind.hourlySalary.label' | sxyTranslate),'monthlySalary':('SALAXY.ENUM.SalaryKind.monthlySalary.label' | sxyTranslate)}\"\r\n        ng-change=\"$ctrl.changeRowType()\" label-cols=\"col-sm-6\" required></salaxy-input-enum>\r\n      <salaxy-input-number name=\"price\" label=\"{{$ctrl.priceLabel}}\" ng-model=\"$ctrl.salaryRow.price\" label-cols=\"col-sm-6\" required></salaxy-input-number>\r\n      <salaxy-input-number ng-if=\"$ctrl.salaryRow.rowType == 'hourlySalary'\" name=\"hours\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.base.hourCount\" ng-model=\"$ctrl.salaryRow.count\" required label-cols=\"col-sm-6\"></salaxy-input-number>\r\n\r\n      <salaxy-input-boolean name=\"isContractLessThanYear\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.cleaning.contractLastedLessThanYear\" type=\"switch\" ng-model=\"$ctrl.usecaseData.isContractLessThanYear\" label-true=\"SALAXY.UI_Terms.yes\" label-false=\"SALAXY.UI_Terms.no\"\r\n        label-cols=\"col-sm-6\">\r\n      </salaxy-input-boolean>\r\n      <salaxy-input-boolean name=\"isFullTime\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.cleaning.fullTime\" type=\"switch\" ng-model=\"$ctrl.usecaseData.isFullTime\" label-true=\"SALAXY.UI_Terms.yes\" label-false=\"SALAXY.UI_Terms.no\" label-cols=\"col-sm-6\">\r\n      </salaxy-input-boolean>\r\n\r\n      <salaxy-input-boolean name=\"isHouseholdDeductible\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.base.householdDeduction\" type=\"radio\" ng-model=\"$ctrl.isHouseholdDeductible\" label-true=\"SALAXY.NG1.HouseholdUsecaseComponent.base.householdDeductionTrue\" label-false=\"SALAXY.NG1.HouseholdUsecaseComponent.base.householdDeductionFalse\"\r\n        label-cols=\"col-sm-6\"></salaxy-input-boolean>\r\n      <div ng-if=\"$ctrl.usecaseData.isFullTime\" class=\"text-danger\" sxy-html=\"SALAXY.NG1.HouseholdUsecaseComponent.cleaning.footnote.html\"></div>\r\n    </div>\r\n  </div>\r\n\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/usecases/household-construction.html\",`<div>\r\n  <div class=\"card-header construction\">\r\n    <span class=\"float-start\">\r\n      <div class=\"icon-wrapper salaxy-household-usecase-avatar\">\r\n        <div class=\"main-icon-wrapper\">\r\n          <img ng-src=\"{{$ctrl.usecaseData.icon}}\">\r\n        </div>\r\n      </div>\r\n    </span>\r\n    <h1>{{$ctrl.usecaseData.label}}</h1>\r\n    <p class=\"calc-text\">\r\n      <span ng-if=\"$ctrl.salaryRow.rowType=='hourlySalary' || $ctrl.salaryRow.rowType == 'unknown'\">{{$ctrl.salaryRow.count || 0}} h x {{$ctrl.salaryRow.price || 0}}\r\n        €</span>\r\n      <span ng-if=\"$ctrl.salaryRow.rowType=='salary' || $ctrl.salaryRow.rowType=='monthlySalary'\">{{$ctrl.salaryRow.price || 0}} € <span\r\n          ng-if=\"$ctrl.salaryRow.rowType=='monthlySalary'\"></span></span>\r\n      <span sxy-text=\"SALAXY.NG1.HouseholdUsecaseComponent.construction.subtitlePlusExpenses\"></span>\r\n      <span ng-if=\"$ctrl.isHouseholdDeductible\" sxy-text=\"SALAXY.NG1.HouseholdUsecaseComponent.base.isHouseholdDeductible\"></span>\r\n      <span class=\"result-text\" ng-if=\"$ctrl.salaryRow.rowType=='hourlySalary' || $ctrl.salaryRow.rowType == 'unknown'\">{{ ($ctrl.salaryRow.count || 0) * ($ctrl.salaryRow.price ||\r\n        0) }}\r\n        €</span>\r\n      <span class=\"result-text\" ng-if=\"$ctrl.salaryRow.rowType=='salary' || $ctrl.salaryRow.rowType=='monthlySalary'\">{{ $ctrl.salaryRow.price || 0}} €</span>\r\n    </p>\r\n    <a class=\"btn-link btn-showmore\" ng-click=\"showInfo = !showInfo\"><span sxy-text=\"SALAXY.UI_Terms.showMore\"></span><i class=\"bi bi-info-circle-fill\"></i></a>\r\n  </div>\r\n  <div class=\"card-body\">\r\n    <p sxy-html=\"SALAXY.NG1.HouseholdUsecaseComponent.construction.shortInfoText.html\"></p>\r\n    <span class=\"collapse\" ng-class=\"{show: showInfo}\" sxy-html=\"SALAXY.NG1.HouseholdUsecaseComponent.construction.longInfoText.html\"></span>\r\n    <div class=\"form-horizontal\">\r\n      <salaxy-input-enum type=\"select\" name=\"mainRowType\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.base.salaryKind\" ng-model=\"$ctrl.salaryRow.rowType\" options=\"{'salary':('SALAXY.ENUM.SalaryKind.salary.label'| sxyTranslate),'hourlySalary':('SALAXY.ENUM.CalculationRowType.hourlySalary.label' | sxyTranslate),'monthlySalary':('SALAXY.ENUM.CalculationRowType.monthlySalary.label' | sxyTranslate),'totalEmployerPayment':('SALAXY.ENUM.CalculationRowType.totalEmployerPayment.label' | sxyTranslate)}\"\r\n        ng-change=\"$ctrl.changeRowType()\" label-cols=\"col-sm-6\" required ng-change=\"$ctrl.submitHouseholdUsecase()\"></salaxy-input-enum>\r\n      <salaxy-input-number name=\"price\" label=\"{{$ctrl.priceLabel}}\" ng-model=\"$ctrl.salaryRow.price\" label-cols=\"col-sm-6\" required ng-change=\"$ctrl.submitHouseholdUsecase()\"></salaxy-input-number>\r\n      <salaxy-input-number ng-if=\"$ctrl.salaryRow.rowType == 'hourlySalary'\" name=\"hours\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.base.hourCount\" ng-model=\"$ctrl.salaryRow.count\" required label-cols=\"col-sm-6\" ng-change=\"$ctrl.submitHouseholdUsecase()\"></salaxy-input-number>\r\n      <salaxy-input-boolean name=\"isHouseholdDeductible\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.base.householdDeduction\" type=\"radio\" ng-model=\"$ctrl.isHouseholdDeductible\" label-true=\"SALAXY.NG1.HouseholdUsecaseComponent.base.householdDeductionTrue\" label-false=\"SALAXY.NG1.HouseholdUsecaseComponent.base.householdDeductionFalse\"\r\n        label-cols=\"col-sm-6\" ng-change=\"$ctrl.submitHouseholdUsecase()\"></salaxy-input-boolean>\r\n      <div ng-if=\"$ctrl.salaryRow.rowType == 'totalEmployerPayment'\" class=\"alert alert-info\" sxy-text=\"SALAXY.NG1.HouseholdUsecaseComponent.base.totalEmployerPaymentAlert\"></div>\r\n      <div ng-if=\"$ctrl.salaryRow.rowType == 'salary'\" class=\"alert alert-info\" sxy-text=\"SALAXY.NG1.HouseholdUsecaseComponent.base.salaryAlert\"></div>\r\n      <div ng-if=\"$ctrl.salaryRow.rowType != 'totalEmployerPayment'\">\r\n        <salaxy-input-boolean name=\"isTesIncludedInSalary\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.base.tesInclusions\" type=\"radio\" ng-model=\"$ctrl.usecaseData.isTesIncludedInSalary\" label-cols=\"col-sm-6\" label-false=\"SALAXY.NG1.HouseholdUsecaseComponent.base.noCalcAuto\"\r\n          label-true=\"SALAXY.NG1.HouseholdUsecaseComponent.base.yesAgreedTotalPayment\" ng-change=\"$ctrl.submitHouseholdUsecase()\"></salaxy-input-boolean>\r\n        <salaxy-input-boolean name=\"isExpensesCustom\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.construction.expensesCustom\" type=\"radio\" ng-model=\"$ctrl.usecaseData.isExpensesCustom\" label-cols=\"col-sm-6\" label-false=\"SALAXY.NG1.HouseholdUsecaseComponent.base.noByTes\"\r\n          label-true=\"SALAXY.NG1.HouseholdUsecaseComponent.base.yesAgreedPerDay\" ng-change=\"$ctrl.submitHouseholdUsecase()\"></salaxy-input-boolean>\r\n        <salaxy-input-number ng-if=\"!$ctrl.usecaseData.isExpensesCustom\" name=\"dailyTravelExpensesKm\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.construction.dailyTravelExpensesKm\" ng-model=\"$ctrl.usecaseData.dailyTravelExpensesKm\" label-cols=\"col-sm-6\" ng-change=\"$ctrl.submitHouseholdUsecase()\">\r\n        </salaxy-input-number>\r\n        <div ng-if=\"$ctrl.usecaseData.isExpensesCustom\">\r\n          <salaxy-input-number name=\"dailyExpenses\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.construction.dailyExpenses\" ng-model=\"$ctrl.usecaseData.dailyExpenses\" label-cols=\"col-sm-6\" ng-change=\"$ctrl.submitHouseholdUsecase()\"></salaxy-input-number>\r\n          <salaxy-input-number name=\"dailyTravelExpenses\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.construction.dailyTravelExpenses\" ng-model=\"$ctrl.usecaseData.dailyTravelExpenses\" label-cols=\"col-sm-6\" ng-change=\"$ctrl.submitHouseholdUsecase()\"></salaxy-input-number>\r\n          <div ng-if=\"!$ctrl.isReadOnly\" class=\"alert alert-info\" sxy-text=\"SALAXY.NG1.HouseholdUsecaseComponent.construction.taxFreeMilageAlert\"></div>\r\n        </div>\r\n      </div>\r\n      <salaxy-textarea ng-if=\"$ctrl.usecaseData.id == 'construction/new' || $ctrl.usecaseData.id == 'construction/renovation'\" name=\"workTypeOtherMessage\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.base.workDescription\" ng-model=\"$ctrl.usecaseData.workTypeOtherMessage\"\r\n        label-cols=\"col-sm-6\">\r\n      </salaxy-textarea>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/calc/usecases/household-other.html\",`<div>\r\n  <div class=\"card-header cleaning\">\r\n    <span class=\"float-start\">\r\n      <div class=\"icon-wrapper salaxy-household-usecase-avatar\">\r\n        <div class=\"main-icon-wrapper\">\r\n          <img ng-src=\"{{$ctrl.usecaseData.icon}}\">\r\n        </div>\r\n      </div>\r\n    </span>\r\n    <h1>{{$ctrl.usecaseData.label}}</h1>\r\n    <p class=\"calc-text\">\r\n      <span ng-if=\"$ctrl.salaryRow.rowType=='hourlySalary' || $ctrl.salaryRow.rowType == 'unknown'\">\r\n        {{$ctrl.salaryRow.count || 0}} h x {{$ctrl.salaryRow.price || 0}} €</span>\r\n      <span ng-if=\"!($ctrl.salaryRow.rowType=='hourlySalary' || $ctrl.salaryRow.rowType == 'unknown')\">\r\n        {{$ctrl.salaryRow.price || 0}} €\r\n        <span ng-if=\"$ctrl.salaryRow.rowType=='monthlySalary'\" sxy-text=\"SALAXY.NG1.HouseholdUsecaseComponent.base.pricePerMonth\"></span>\r\n      </span>\r\n      <span ng-if=\"$ctrl.isHouseholdDeductible\" sxy-text=\"SALAXY.NG1.HouseholdUsecaseComponent.base.isHouseholdDeductible\"></span>\r\n      <span class=\"result-text\" ng-if=\"$ctrl.salaryRow.rowType=='hourlySalary' || $ctrl.salaryRow.rowType == 'unknown'\">\r\n        {{ ($ctrl.salaryRow.count || 0) * ($ctrl.salaryRow.price || 0) }} €\r\n      </span>\r\n      <span class=\"result-text\" ng-if=\"!($ctrl.salaryRow.rowType=='hourlySalary' || $ctrl.salaryRow.rowType == 'unknown')\">\r\n        {{ $ctrl.salaryRow.price || 0}} €\r\n      </span>\r\n    </p>\r\n    <a class=\"btn-link btn-showmore\" ng-click=\"showInfo = !showInfo\"><span sxy-text=\"SALAXY.UI_Terms.showMore\"></span><i class=\"bi bi-info-circle-fill\"></i></a>\r\n  </div>\r\n  <div class=\"card-body\">\r\n    <p sxy-html=\"SALAXY.NG1.HouseholdUsecaseComponent.base.shortInfoText.html\"></p>\r\n    <span class=\"collapse\" ng-class=\"{show: showInfo}\" sxy-html=\"SALAXY.NG1.HouseholdUsecaseComponent.base.longInfoText.html\"></span>\r\n    <div class=\"form-horizontal\">\r\n\r\n      <salaxy-input-enum type=\"select\" name=\"mainRowType\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.base.salaryKind\" placeholder=\"SALAXY.UI_Terms.select\" ng-model=\"$ctrl.salaryRow.rowType\" options=\"{salary:('SALAXY.ENUM.SalaryKind.salary.label'| sxyTranslate),hourlySalary:('SALAXY.ENUM.CalculationRowType.hourlySalary.label' | sxyTranslate),monthlySalary:('SALAXY.ENUM.CalculationRowType.monthlySalary.label' | sxyTranslate),totalEmployerPayment:('SALAXY.ENUM.CalculationRowType.totalEmployerPayment.label' | sxyTranslate)}\"\r\n        ng-change=\"$ctrl.changeRowType()\" label-cols=\"col-sm-6\" hidden-options=\"unknown\" enum=\"CalculationRowType\" required ng-change=\"$ctrl.submitHouseholdUsecase()\"></salaxy-input-enum>\r\n\r\n\r\n      <salaxy-input-number name=\"price\" label=\"{{$ctrl.priceLabel}}\" ng-model=\"$ctrl.salaryRow.price\" label-cols=\"col-sm-6\" required ng-change=\"$ctrl.submitHouseholdUsecase()\"></salaxy-input-number>\r\n      <salaxy-input-number ng-if=\"$ctrl.salaryRow.rowType == 'hourlySalary'\" name=\"hours\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.base.hourCount\" ng-model=\"$ctrl.salaryRow.count\" required label-cols=\"col-sm-6\" ng-change=\"$ctrl.submitHouseholdUsecase()\"></salaxy-input-number>\r\n      <salaxy-input-occupation-type name=\"occupationType\" ng-model=\"$ctrl.usecaseData.occupation\" label-cols=\"col-sm-6\" label=\"SALAXY.NG1.WorkerWizardComponent.employment.work.occupationCode\" require=\"$ctrl.usecaseData.id == 'construction/other'\" ng-change=\"$ctrl.submitHouseholdUsecase()\"></salaxy-input-occupation-type>\r\n\r\n      <salaxy-input-boolean name=\"isHouseholdDeductible\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.base.householdDeduction\" type=\"radio\" ng-model=\"$ctrl.isHouseholdDeductible\" label-true=\"SALAXY.NG1.HouseholdUsecaseComponent.base.householdDeductionTrue\" label-false=\"SALAXY.NG1.HouseholdUsecaseComponent.base.householdDeductionFalse\"\r\n        label-cols=\"col-sm-6\" ng-change=\"$ctrl.submitHouseholdUsecase()\"></salaxy-input-boolean>\r\n      <div ng-if=\"$ctrl.salaryRow.rowType == 'totalEmployerPayment'\" class=\"alert alert-info\" sxy-text=\"SALAXY.NG1.HouseholdUsecaseComponent.base.totalEmployerPaymentAlert\"></div>\r\n      <div ng-if=\"$ctrl.salaryRow.rowType == 'salary'\" class=\"alert alert-info\" sxy-text=\"SALAXY.NG1.HouseholdUsecaseComponent.base.salaryAlert\"></div>\r\n      <salaxy-input-enum label=\"SALAXY.NG1.HouseholdUsecaseComponent.base.taxDeductionCategories\" hidden-options=\"none\" label-cols=\"col-sm-6\" name=\"taxDeductionCategories\" ng-if=\"$ctrl.isHouseholdDeductible\" ng-model=\"$ctrl.usecaseData.taxDeductionCategories\"\r\n        enum=\"TaxDeductionWorkCategories\" type=\"select\" required ng-change=\"$ctrl.submitHouseholdUsecase()\"></salaxy-input-enum>\r\n\r\n      <salaxy-textarea name=\"message\" label=\"SALAXY.NG1.HouseholdUsecaseComponent.base.salaryMessage\" ng-model=\"$ctrl.salaryRow.message\" label-cols=\"col-sm-6\">\r\n      </salaxy-textarea>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/communications/ContactInfo.html\",`<div class=\"salaxy-component salaxy-contact-info\">\r\n  <div class=\"row contact-info-row\">\r\n    <div class=\"salaxy-alert col-12\">\r\n      <div class=\"alert alert-primary\">\r\n        <div class=\"icon-container hidden-xxs\">\r\n          <span class=\"icon\">\r\n            <i class=\"bi bi-question-lg\"></i>\r\n          </span>\r\n        </div>\r\n        <div class=\"contact-info-text\" ng-if=\"!$ctrl.showShortContent\">\r\n          <p ng-if=\"!$ctrl.hideContactInfo\" sxy-html=\"SALAXY.NG1.ContactInfoComponent.contactInfo.html\"></p>\r\n          <p sxy-html=\"SALAXY.NG1.ContactInfoComponent.defaultContent.html\"></p>\r\n        </div>\r\n        <div class=\"contact-info-text\" ng-if=\"$ctrl.showShortContent\">\r\n          <p sxy-html=\"SALAXY.NG1.ContactInfoComponent.shortContent.html\"></p>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/communications/messages/message-types/ExpenseReport.html\",`<salaxy-calc-rows-editor dimensions=\"$ctrl.crudController.employingRelation.settings.costAccounting.dimensions\" row-types=\"$ctrl.getRowTypes()\" parent=\"$ctrl.getCalcRowMessage().contentData\"></salaxy-calc-rows-editor>\r\n<button type=\"button\" ng-disabled=\"$ctrl.crudController.isNew()\" class=\"btn btn-primary btn-labeled-left\" style=\"width: 20%; text-align: left; margin-bottom: 4px\" ngf-select=\"$ctrl.crudController.uploadFiles($files)\" ngf-multiple=\"true\" ngf-max-size=\"10MB\" xxngf-pattern=\"$ctrl.crudController.supportedFilesPattern\"><i class=\"bi bi-paperclip\" style=\"width: 38px\"></i>\r\n  <span sxy-text=\"SALAXY.NG1.MessageThreadComponent.fileBtn\"></span>\r\n</button>\r\n<div class=\"row\" style=\"margin-top: 10px;\" ng-repeat=\"item in $ctrl.list\">\r\n  <div ng-switch=\"item.type\">\r\n    <div ng-switch-when=\"blobFile\" style=\"min-width: 600px\">\r\n      <div ng-if=\"item.showPreview\">\r\n        <div class=\"float-end\">\r\n          <button type=\"button\" class=\"btn btn-default btn-xs\" ng-click=\"item.showPreview=false\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n          <a class=\"btn btn-default btn-xs\" ng-href=\"{{$ctrl.crudController.getFileInfo(item).downloadUrl}}\" target=\"_blank\" sxy-text=\"SALAXY.UI_Terms.download\"></a>\r\n        </div>\r\n        <div style=\"font-weight: bold;font-size: 1.5em;\">{{ item.content }}</div>\r\n        <img class=\"img-responsive img-thumbnail\" ng-src=\"{{$ctrl.crudController.getFileInfo(item).previewUrl}}\" />\r\n      </div>\r\n      <div ng-if=\"!item.showPreview\">\r\n        <div class=\"float-start\" style=\"margin-right: 10px;max-height: 100px; overflow-y:hidden;\" ng-if=\"$ctrl.crudController.getFileInfo(item).previewUrl\">\r\n          <img ng-src=\"{{$ctrl.crudController.getFileInfo(item).previewUrl}}\" class=\"img-thumbnail\" style=\"max-width: 200px;\" />\r\n        </div>\r\n        <i ng-if=\"!$ctrl.crudController.getFileInfo(item).previewUrl\" class=\"bi {{ $ctrl.crudController.getFileInfo(item).icon }} text-primary float-start\" aria-hidden=\"true\" style=\"font-size: 104px; font-weight: bold\"></i>\r\n        <div style=\"font-weight: bold; font-size: 1.5em;\">{{ item.content }}</div>\r\n        <div>\r\n          <button type=\"button\" class=\"btn btn-default btn-xs\" ng-click=\"item.showPreview=true\" ng-if=\"$ctrl.crudController.getFileInfo(item).previewUrl\" sxy-text=\"SALAXY.UI_Terms.seePreviewAlt\"></button>\r\n          <a class=\"btn btn-default btn-xs\" ng-href=\"{{$ctrl.crudController.getFileInfo(item).downloadUrl}}\" target=\"_blank\" sxy-text=\"SALAXY.UI_Terms.download\"></a>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  \r\n</div>`);\n\n $templateCache.put(\"salaxy-components/communications/messages/message-types/HourlyReport.html\",`<div class=\"salaxy-component salaxy-hourly-report\">\r\n  <div class=\"list-group\">\r\n    <div class=\"list-group-item bg-primary\">\r\n      <h4 class=\"list-group-item-heading text-center\">\r\n        <div ng-if=\"$ctrl.reportType === 'hourlyReport'\">Tuntiraportti</div>\r\n        <div ng-if=\"$ctrl.reportType === 'timeReport'\">Työaikaraportti</div>\r\n        <i ng-click=\"$ctrl.changeWeek(false)\" class=\"bi bi-arrow-left-circle-fill bi-2x float-start\" aria-hidden=\"true\"></i>\r\n        <i ng-click=\"$ctrl.changeWeek(true)\" class=\"bi bi-arrow-right-circle-fill bi-2x float-end\" aria-hidden=\"true\"></i>\r\n        <div>Viikko {{$ctrl.currentWeekNumber}}</div>\r\n        <div>{{$ctrl.firstDayOfCurrentWeekFormatted}} - {{$ctrl.lastDayOfCurrentWeekFormatted}}</div>\r\n      </h4>\r\n    </div>\r\n    <div class=\"list-group-item\" ng-repeat=\"day in $ctrl.currentWeek\">\r\n      <div class=\"text-center float-start text-uppercase week-icon\" ng-class=\"$ctrl.getDateStyle(day.date)\">\r\n        {{ day.dayName }}<br> {{ day.displayDate }}\r\n      </div>\r\n      <div class=\"float-end\" style=\"margin-top: 6px\">\r\n        <button ng-if=\"$ctrl.showExpandButton(day.date)\" ng-click=\"$ctrl.setHourlyRecordsVisible(day.date)\" type=\"button\" class=\"btn btn-default\">\r\n          <i class=\"bi\" ng-class=\"{'bi-chevron-up' : !day.isCollapsed,  'bi-chevron-down' : day.isCollapsed}\"></i>\r\n        </button>\r\n        <button ng-click=\"$ctrl.showEditDialog($ctrl.getEditDialogItem(day.date), true)\" type=\"button\" class=\"btn btn-default\"><i class=\"bi bi-plus-lg\"></i></button>\r\n      </div>\r\n      <p class=\"list-group-item-text\">{{$ctrl.countDailyHours(day.date) | sxyTotalTime : \"minutes\"}}</p>\r\n      <div ng-if=\"!day.isCollapsed\">\r\n        <div ng-if=\"$ctrl.reportType == 'hourlyReport'\" style=\"margin-bottom: 5px;\" ng-repeat=\"message in $ctrl.list | filter: { contentData: {period: {start: day.date}} }\">\r\n          <div>\r\n            <span style=\"padding-top: 2px;\"><strong>{{$ctrl.getDimensionOptionText(message.contentData.project)}}</strong> ({{message.contentData.totalTime | sxyTotalTime : \"minutes\"}} h)</span><br>\r\n            <span class=\"small text-overflow-80pc\" style=\"padding-top: 2px;\">{{message.contentData.projectText}}</span>\r\n            <div class=\"float-end\">\r\n              <button ng-click=\"$ctrl.showEditDialog(message, false)\" type=\"button\" class=\"btn btn-default btn-xs\"><i class=\"bi bi-pencil-fill\"></i></button>\r\n            </div>\r\n          </div>\r\n        </div>\r\n        <div ng-if=\"$ctrl.reportType == 'timeReport'\" style=\"margin-bottom: 5px;\" ng-repeat=\"message in $ctrl.list | filter: { contentData: {period: {start: day.date}} }\">\r\n          <div>\r\n            <span style=\"padding-top: 2px;\"><strong>{{message.contentData.project}}</strong> ({{message.contentData.startTime | date:'HH:mm'}} - {{message.contentData.endTime | date:'HH:mm'}})</span><br>\r\n            <span class=\"small text-overflow-80pc\" style=\"padding-top: 2px;\">{{message.contentData.projectText}}</span>\r\n            <div class=\"float-end\">\r\n              <button ng-click=\"$ctrl.showEditDialog(message, false)\" type=\"button\" class=\"btn btn-default btn-xs\"><i class=\"bi bi-pencil-fill\"></i></button>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"list-group-item\">\r\n      <h4 class=\"list-group-item-heading\">\r\n        <div class=\"text-center float-start text-uppercase btn btn-default week-icon\">\r\n          <small>Viikko</small><br> {{$ctrl.currentWeekNumber}}\r\n        </div>\r\n        <div class=\"float-end\" style=\"margin-top: 10px\">Yhteensä</div>\r\n        <p class=\"list-group-item-text\" style=\"height: 40px; padding-left: 80px; padding-top: 10px;\">{{$ctrl.weeklyHours | sxyTotalTime : \"minutes\"}}</p>\r\n      </h4>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/communications/messages/message-types/Timer.html\",`<div class=\"salaxy-component salaxy-timer\">\r\n  <div ng-if=\"$ctrl.timerMode == 'mini'\">\r\n    <div class=\"card card-panel panel-solid\" ng-class=\"$ctrl.isTimerOnFromDayBefore ? 'panel-warning' : 'panel-primary'\">\r\n      <div class=\"card-header\">\r\n        <div class=\"float-start icon-container\" style=\"padding-left: 0;\">\r\n          <i class=\"bi \" ng-class=\"$ctrl.isTimerOn ? 'bi-exclamation-lg' : 'bi-clock'\">\r\n          </i>\r\n        </div>\r\n        <h3 class=\"card-title\">Olet leimannut sisään kellokorttiin</h3>\r\n        <div class=\"date\">{{$ctrl.getTimerMessage().contentData.period.start | date : \"d.M.yyyy\"}}</div>\r\n      </div>\r\n      <div class=\"card-content card-body\">\r\n        <div class=\"text-center\">\r\n          <div class=\"otherparty-container\">\r\n            <salaxy-avatar avatar=\"$ctrl.parent.ownerInfo\"></salaxy-avatar>\r\n            <span>{{$ctrl.parent.ownerInfo.displayName}}</span>\r\n          </div>\r\n          <div class=\"clock-text card-main text-white\">\r\n            <i class=\"bi bi-clock\" aria-hidden=\"true\"></i> {{ $ctrl.getTimerMessage().contentData.totalTimeInSeconds | sxyTotalTime : \"seconds\"}}\r\n          </div>\r\n          <div class=\"card-details-title\" ng-if=\"$ctrl.getTimerMessage().contentData.project\">\r\n            \r\n            {{$ctrl.getDimensionOptionText($ctrl.getTimerMessage().contentData.project)}}\r\n          </div>\r\n          <span ng-if=\"$ctrl.getTimerMessage().contentData.projectText\" class=\"card-details\">\r\n            {{$ctrl.getTimerMessage().contentData.projectText}}\r\n          </span>\r\n        </div>\r\n\r\n      </div>\r\n      <div class=\"card-footer\">\r\n        <button ng-click=\"$ctrl.crudController.showDetails($ctrl.parent)\" class=\"btn btn-sm btn-white\">Muokkaa</button>\r\n      </div>\r\n    </div>\r\n  </div>\r\n\r\n  <div ng-if=\"$ctrl.timerMode != 'mini' && $ctrl.timerMode != 'edit'\">\r\n    <div class=\"thumbnail thumbnail-timer\">\r\n      <form name=\"timerForm\">\r\n\r\n        <div class=\"text-center timer-container\" ng-class=\"$ctrl.isTimerOnFromDayBefore ? 'bg-warning' : 'bg-primary'\">\r\n          <h3>Kellokortti</h3>\r\n          <div class=\"clock-text\">\r\n            <i class=\"bi bi-clock\" aria-hidden=\"true\"></i> {{$ctrl.getTimerMessage().contentData.totalTimeInSeconds | sxyTotalTime : \"seconds\"}}\r\n          </div>\r\n          <div class=\"text-center form-inline\">\r\n            Aloitus:\r\n            <span ng-if=\"!$ctrl.editStartTime\" class=\"timer-time-input-read-only\">{{ $ctrl.getTimerMessage().contentData.startTime}}</span>\r\n            <salaxy-input-time ng-if=\"$ctrl.editStartTime\" name=\"startTime\" label=\"Työaika\" type=\"time\" ng-model=\"$ctrl.getTimerMessage().contentData.startTime\"></salaxy-input-time>\r\n            <button type=\"button\" class=\"btn btn-sm btn-transparent\" ng-click=\"$ctrl.editStartTime=!$ctrl.editStartTime\"><i class=\"bi bi-pencil-fill\"></i></button>\r\n          </div>\r\n          <div>Yhteensä tänään {{ $ctrl.getAndFormatTotal()}}</div>\r\n          <div style=\"padding: 10px;\">\r\n            <div ng-if=\"$ctrl.crudController.employingRelation.settings.costAccounting.dimensions\"  ng-controller=\"CostAccountingController as $cost\" ng-init=\"$cost.dimensions=$ctrl.crudController.employingRelation.settings.costAccounting.dimensions\">\r\n              <salaxy-input-typeahead ng-if=\"$cost.getDefinition('lk1')\"  label-type=\"plain\" placeholder=\"{{($cost.getDefinition('lk1').label || 'SALAXY.NG1.CalcCostAccountingComponent.defaultLabel') | sxyTranslate}}\" label-format=\"text-value\" name=\"options_project\" ng-model=\"$ctrl.getTimerMessage().contentData.project\" options=\"$cost.getDefinition('lk1').options\" required=\"true\"></salaxy-input-typeahead>\r\n            </div>\r\n            <salaxy-input label-type=\"plain\" placeholder=\"Kommentti\"  name=\"comment\" ng-model=\"$ctrl.getTimerMessage().contentData.projectText\" class=\"timer-comment-input\"></salaxy-input>\r\n          </div>\r\n          <div>\r\n            <button ng-if=\"!$ctrl.isTimerOn\" class=\"btn btn-lg btn-primary btn-timer-start\" ng-click=\"$ctrl.startTimer()\">\r\n          <i class=\"bi bi-play-fill bi-2x\"></i>\r\n        </button>\r\n            <button ng-if=\"$ctrl.isTimerOn\" class=\"btn btn-lg btn-danger btn-timer-stop\" ng-click=\"$ctrl.stopTimer()\">\r\n          <i class=\"bi bi-stop-fill bi-2x\"></i>\r\n        </button>\r\n          </div>\r\n        </div>\r\n      </form>\r\n    </div>\r\n  </div>\r\n  <div ng-if=\"$ctrl.timerMode != 'mini' && $ctrl.list.length\" class=\"list-group list-group-timer\">\r\n    <div class=\"list-group-item item-today\">\r\n      <div class=\"list-group-item-heading\">\r\n        TÄNÄÄN, {{ \"today\" | sxyDate }}\r\n      </div>\r\n    </div>\r\n    <div class=\"list-group-item\" ng-repeat=\"message in $ctrl.list\">\r\n      <div class=\"list-group-item-heading\">\r\n        <div class=\"float-end\">\r\n          {{ message.contentData.totalTime | sxyTotalTime : \"minutes\"}} h\r\n          <button type=\"button\" class=\"btn btn-xs btn-transparent\" ng-click=\"$ctrl.showEditDialog(message, false)\"><i class=\"bi bi-pencil-fill\"></i></button>\r\n        </div>\r\n        {{ message.contentData.startTime}}-{{ message.contentData.endTime}}\r\n        <br>\r\n      </div>\r\n     <!--  <div class=\"float-end\">\r\n        <button type=\"button\" class=\"btn btn-xs btn-transparent\" ng-click=\"$ctrl.showEditDialog(message, false)\"><i class=\"bi bi-pencil-fill\"></i></button>\r\n      </div> -->\r\n      <p class=\"list-group-item-text\">{{ $ctrl.getDimensionOptionText(message.contentData.project) }}</p>\r\n      <p class=\"list-group-item-text\" ng-if=\"message.contentData.projectText\">{{ message.contentData.projectText }}</p>\r\n      <salaxy-validation-summary api-validation=\"message.validation\" layout=\"minimal\" class=\"text-danger\"></salaxy-validation-summary>\r\n    </div>\r\n    <div class=\"list-group-item list-group-item-footer text-end\">\r\n      <button class=\"btn btn-sm btn-primary\" ng-click=\"$ctrl.showEditDialog('new', true)\">Lisää uusi merkintä <span class=\"bi bi-plus-lg\"></span></button>\r\n    </div>\r\n    <div class=\"list-group-item list-group-item-footer\">\r\n      <div class=\"float-end\">{{ $ctrl.getAndFormatTotal() }}</div>\r\n      Yhteensä\r\n    </div>\r\n  </div>\r\n\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/communications/messages/MessageContent.html\",`<div ng-switch=\"item.type\">\r\n  <div ng-switch-when=\"blobFile\" style=\"min-width: 600px\">\r\n    <div ng-if=\"item.showPreview\">\r\n      <div class=\"float-end\">\r\n        <button type=\"button\" class=\"btn btn-default btn-xs\" ng-click=\"item.showPreview=false\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n        <a class=\"btn btn-default btn-xs\" ng-href=\"{{$ctrl.getFileInfo(item).downloadUrl}}\" target=\"_blank\" sxy-text=\"SALAXY.UI_Terms.download\"></a>\r\n      </div>\r\n      <div style=\"font-weight: bold;font-size: 1.5em;\">{{ item.content }}</div>\r\n      <img class=\"img-fluid img-thumbnail\" ng-src=\"{{$ctrl.getFileInfo(item).previewUrl}}\" />\r\n    </div>\r\n    <div ng-if=\"!item.showPreview\">\r\n      <div class=\"float-start\" style=\"margin-right: 10px;max-height: 100px; overflow-y:hidden;\" ng-if=\"$ctrl.getFileInfo(item).previewUrl\">\r\n        <img ng-src=\"{{$ctrl.getFileInfo(item).previewUrl}}\" class=\"img-thumbnail\" style=\"max-width: 200px;\" />\r\n      </div>\r\n      <i ng-if=\"!$ctrl.getFileInfo(item).previewUrl\" class=\"bi {{ $ctrl.getFileInfo(item).icon }} text-primary float-start\" aria-hidden=\"true\" style=\"font-size: 104px; font-weight: bold\"></i>\r\n      <div style=\"font-weight: bold; font-size: 1.5em;\">{{ item.content }}</div>\r\n      <div>\r\n        <button type=\"button\" class=\"btn btn-default btn-xs\" ng-click=\"item.showPreview=true\" ng-if=\"$ctrl.getFileInfo(item).previewUrl\" sxy-text=\"SALAXY.UI_Terms.seePreviewAlt\"></button>\r\n        <a class=\"btn btn-default btn-xs\" ng-href=\"{{$ctrl.getFileInfo(item).downloadUrl}}\" target=\"_blank\" sxy-text=\"SALAXY.UI_Terms.download\"></a>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div ng-switch-when=\"calculation\" ng-controller=\"CalculationCrudController as $calcCtrl\" ng-init=\"$calcCtrl.model=(item.contentId || item.content)\">\r\n    <salaxy-spinner ng-if=\"$calcCtrl.isLoading\"></salaxy-spinner>\r\n    <div ng-if=\"$calcCtrl.current\">\r\n      <div>\r\n        <table class=\"table table-borderless bg-transparent\">\r\n          <tbody>\r\n            <tr>\r\n              <td class=\"td-avatar middle\">\r\n                <salaxy-avatar avatar=\"$calcCtrl.current.worker.avatar\"></salaxy-avatar>\r\n              </td>\r\n              <td class=\"td-name middle\">\r\n                <span ng-if=\"!$calcCtrl.current.worker.avatar.displayName\" sxy-text=\"SALAXY.NG1.MessageThreadComponent.messageContent.notSelected\"></span>\r\n                <strong>{{$calcCtrl.current.worker.avatar.displayName}}</strong><br /> {{ \"SALAXY.ENUM.CalculationStatus.\" + $calcCtrl.current.workflow.status + \".label\" | sxyTranslate }} {{$calcCtrl.current.workflow.paidAt | date}}\r\n              </td>\r\n              <td class=\"right middle\">\r\n                <span sxy-text=\"SALAXY.NG1.MessageThreadComponent.messageContent.salary\" ps=\":\"></span> {{ $calcCtrl.current.result.totals.totalGrossSalary | currency }}<br /> <span sxy-text=\"SALAXY.NG1.MessageThreadComponent.messageContent.payment\" ps=\":\"></span>                {{ $calcCtrl.current.result.employerCalc.totalPayment | currency }}\r\n              </td>\r\n              <td class=\"middle\">\r\n                <a ng-href=\"{{$calcCtrl.getPdfUrl($calcCtrl.current)}}\" target=\"_blank\" class=\"btn btn-sm btn-primary btn-block\" sxy-text=\"SALAXY.NG1.MessageThreadComponent.messageContent.report\"></a>\r\n              </td>\r\n              <td class=\" middle\">\r\n                <a ng-href=\"#/calc/details/{{ $calcCtrl.current.id }}\" class=\"btn btn-sm btn-default btn-block\">\r\n                  {{ $calcCtrl.current.workflow.status == 'draft' ? ('SALAXY.NG1.MessageThreadComponent.messageContent.editPay' |sxyTranslate) : ('SALAXY.NG1.MessageThreadComponent.messageContent.showCalc' |sxyTranslate) }}\r\n                </a>\r\n                <a ng-if=\"$calcCtrl.current.data.payrollId\" class=\"btn btn-sm btn-primary btn-block\" ng-href=\"#/payroll/details/{{ $calcCtrl.current.data.payrollId }}\">\r\n                  <i class=\"bi bi-list-task d-sm-none d-inline-block\"></i>\r\n                  <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.NG1.MessageThreadComponent.messageContent.payroll\"></span>\r\n                </a>\r\n              </td>\r\n            </tr>\r\n          </tbody>\r\n        </table>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <!-- TODO: change the preview to be based on index not on actual object -->\r\n  <div ng-switch-when=\"payroll\" ng-controller=\"PayrollCrudController as $payrollCtrl\" ng-init=\"$payrollCtrl.model=(item.contentId || item.content)\">\r\n    <salaxy-spinner ng-if=\"$payrollCtrl.isLoading\"></salaxy-spinner>\r\n    <div ng-if=\"$payrollCtrl.current\">\r\n      <div>\r\n        <table class=\"table table-borderless bg-transparent\">\r\n          <tbody>\r\n            <tr>\r\n              <td class=\"middle salaxy-component salaxy-payroll\">\r\n                <div class=\"payroll-info-row\" style=\"margin-top:0px\">\r\n                  <salaxy-avatar-placeholder class=\"payroll-avatar\">\r\n                    <i class=\"salaxy-avatar bi bi-square-fill d-flex\" style=\"color:#FDC338;\">\r\n                      <div class=\"avatar-text-wrapper\">\r\n                        <strong>{{ $payrollCtrl.calcs.length }}</strong>\r\n                        <small>{{ $payrollCtrl.current.info.salaryDate | date : \"d.M.\" }}</small>\r\n                      </div>\r\n                    </i>\r\n                  </salaxy-avatar-placeholder>\r\n                </div>\r\n              </td>\r\n              <td class=\"td-name middle\">\r\n                <strong>{{$payrollCtrl.current.input.title}}</strong><br /> {{ \"SALAXY.ENUM.PayrollStatus.\" + $payrollCtrl.current.info.status + \".label\" | sxyTranslate }}\r\n              </td>\r\n              <td class=\"right middle\">\r\n                <span sxy-text=\"SALAXY.NG1.MessageThreadComponent.messageContent.salary\" ps=\":\"></span> {{ $payrollCtrl.info.totalGrossSalary | currency }}<br /> <span sxy-text=\"SALAXY.NG1.MessageThreadComponent.messageContent.payment\" ps=\":\"></span>                {{ $payrollCtrl.info.totalPayment | currency }}\r\n              </td>\r\n              <td class=\"middle\">\r\n                <a ng-href=\"{{$payrollCtrl.getPdfUrl()}}\" target=\"_blank\" class=\"btn btn-sm btn-default btn-block\" sxy-text=\"PDF\"></a>\r\n              </td>\r\n              <td class=\" middle\">\r\n                <a ng-href=\"#/payroll/details/{{ $payrollCtrl.current.id }}\" class=\"btn btn-sm btn-primary btn-block\">\r\n                  {{ $payrollCtrl.current.info.status == 'draft' ? ('SALAXY.UI_Terms.edit' |sxyTranslate) : ('SALAXY.UI_Terms.show' |sxyTranslate) + \" &raquo;\"   }}\r\n                </a>\r\n              </td>\r\n            </tr>\r\n          </tbody>\r\n        </table>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div ng-switch-when=\"text\">\r\n    <div class=\"message-content\" ng-if=\"!$ctrl.isInEdit\">{{ item.content }}</div>\r\n    <div ng-if=\"$ctrl.isInEdit\">\r\n      <textarea ng-model=\"item.content\"></textarea>\r\n    </div>\r\n  </div>\r\n  <div ng-switch-when=\"email\">\r\n    <div class=\"message-content\">\r\n      <span sxy-text=\"SALAXY.NG1.MessageThreadComponent.messageContent.toEmail\" ps=\":\"></span> <a href=\"mailto:{{ item.content }}\">{{ item.content }}</a>\r\n    </div>\r\n  </div>\r\n  <div ng-switch-when=\"absence\">\r\n    <salaxy-absence-periods parent=\"item.contentData\" condensed=\"true\"></salaxy-absence-periods>\r\n  </div>\r\n  <div ng-switch-default class=\"alert alert-danger\">\r\n    {{ item.type }}: {{ item.content }}\r\n  </div>\r\n  <div class=\"edit-toolbar btn-toolbar\" role=\"toolbar\" ng-if=\"$ctrl.isInEdit\">\r\n    <div class=\"btn-group\" role=\"group\">\r\n      <button class=\"btn btn-xs btn-danger\" ng-click=\"$ctrl.deleteMessage(item)\" sxy-text=\"SALAXY.UI_Terms.delete\"></button>\r\n      <button class=\"btn btn-xs btn-primary\" ng-click=\"$ctrl.markItemAsRead(item, true)\" ng-if=\"!$ctrl.getReadTime(item)\" sxy-text=\"SALAXY.NG1.MessageThreadComponent.markAsReadBtn\"></button>\r\n      <button class=\"btn btn-xs btn-primary\" ng-click=\"$ctrl.markItemAsRead(item, false)\" ng-if=\"$ctrl.getReadTime(item)\" sxy-text=\"SALAXY.NG1.MessageThreadComponent.markAsUnreadBtn\"></button>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/communications/messages/proto-usecase/calc.html\",`<h1>calc here</h1>`);\n\n $templateCache.put(\"salaxy-components/communications/messages/proto-usecase/default.html\",`<div ng-if=\"$ctrl.isNew()\">\r\n  <salaxy-input name=\"title\" label=\"SALAXY.NG1.MessageThreadComponent.title\" require=\"true\" ng-model=\"$ctrl.current.title\"></salaxy-input>\r\n  <salaxy-form-group label=\"\" name=\"submit\" class=\"no-colon\">\r\n    <button type=\"submit\" class=\"btn btn-primary\" ng-disabled=\"!newMessageThread.$valid\" ng-click=\"$ctrl.save()\"\r\n      sxy-text=\"SALAXY.NG1.MessageThreadComponent.ui.newMessageThreadBtn\"></button>\r\n  </salaxy-form-group>\r\n</div>\r\n<div ng-if=\"!$ctrl.isNew()\"> \r\n  <p ng-if=\"$ctrl.current.messages.length == 0\">&nbsp;</p>\r\n  <div class=\"messages-container\" ng-if=\"$ctrl.current.messages\">\r\n    <div ng-repeat=\"item in $ctrl.current.messages\" ng-switch=\"item.fromParty\">\r\n      <div ng-switch-when=\"owner,undefined\" ng-switch-when-separator=\",\">\r\n        <salaxy-avatar avatar=\"$ctrl.current.ownerInfo\" class=\"float-start\"></salaxy-avatar>\r\n        <div class=\"message-bubble left\" ng-class=\"{ 'in-edit': $ctrl.isInEdit, 'unread': !$ctrl.getReadTime(item)  }\">\r\n          <ng-include src=\"'salaxy-components/communications/messages/MessageContent.html'\"></ng-include>\r\n          <span class=\"updated-at\">{{ item.time | sxyTime }}, {{ $ctrl.getReadTime(item) ? (('SALAXY.NG1.MessageThreadComponent.read' |sxyTranslate) + ' ' + ($ctrl.getReadTime(item) |\r\n            sxyTime)) : ('SALAXY.NG1.MessageThreadComponent.unread' |sxyTranslate) }}</span>\r\n        </div>\r\n      </div>\r\n      <div ng-switch-when=\"otherParty\" class=\"text-end\">\r\n        <salaxy-avatar avatar=\"$ctrl.current.otherPartyInfo\" class=\"float-end\"></salaxy-avatar>\r\n        <div class=\"message-bubble right {{item.type}}\" ng-class=\"{ 'in-edit': $ctrl.isInEdit, 'unread': !$ctrl.getReadTime(item) }\">\r\n          <ng-include src=\"'salaxy-components/communications/messages/MessageContent.html'\"></ng-include>\r\n          <span class=\"updated-at\" ng-if=\"item.type != 'email'\">{{ item.time | sxyTime }}, {{ $ctrl.getReadTime(item) ? (('SALAXY.NG1.MessageThreadComponent.read' |sxyTranslate) + ' ' +\r\n            ($ctrl.getReadTime(item) | sxyTime)) : ('SALAXY.NG1.MessageThreadComponent.unread' |sxyTranslate)}}</span>\r\n          <span class=\"updated-at\" ng-if=\"item.type == 'email'\">{{ item.time | sxyTime }}</span>\r\n        </div>\r\n      </div>\r\n      <div ng-switch-default class=\"alert alert-danger\">\r\n        <ng-include src=\"'salaxy-components/communications/MessageThread_MessageContent.html'\"></ng-include>\r\n      </div>\r\n    </div>\r\n    <div class=\"padding\">\r\n      <div ng-if=\"$ctrl.isReadOnly\" class=\"alert alert-info\">\r\n        <p>\r\n          <strong>Viestiketju on suljettu</strong>\r\n          <!-- TODO: Onko reopen mahdollinen myös työntekijälle? -->\r\n        </p>\r\n      </div>\r\n      <div class=\"row\" ng-if=\"!$ctrl.isReadOnly\">\r\n        <div class=\"col-8 col-sm-9\" ng-switch=\"$ctrl.newMessage.type\">\r\n          <div ng-switch-when=\"absence\">\r\n            <salaxy-absence-periods parent=\"$ctrl.newMessage.contentData\" condensed=\"true\"></salaxy-absence-periods>\r\n          </div>\r\n          <div ng-switch-when=\"annualLeave\">\r\n            <salaxy-holiday-year-holidays parent=\"$ctrl.newMessage.contentData\" condensed=\"true\"></salaxy-holiday-year-holidays>\r\n          </div>\r\n          <textarea ng-switch-default placeholder=\"{{'SALAXY.NG1.MessageThreadComponent.writeOrPaste' |sxyTranslate}}\" ng-model=\"$ctrl.newMessage.content\"></textarea>\r\n        </div>\r\n        <div class=\"col-4 col-sm-3\" ng-if=\"!$ctrl.isReadOnly\">\r\n          <button type=\"button\" class=\"btn btn-primary btn-labeled-left test-start\" style=\"width: 100%;  margin-bottom: 4px\" ng-click=\"$ctrl.sendMessage()\"\r\n            ng-disabled=\"!$ctrl.newMessage.content\">\r\n            <i class=\"bi bi-send-fill\"></i>\r\n            <span sxy-text=\"SALAXY.UI_Terms.send\"></span>\r\n          </button>\r\n          <button type=\"button\" class=\"btn btn-primary btn-labeled-left text-start\" style=\"width: 100%;  margin-bottom: 4px\" ngf-select=\"$ctrl.uploadFiles($files)\"\r\n            ngf-multiple=\"true\" ngf-max-size=\"10MB\">\r\n            <i class=\"bi bi-paperclip\"></i>\r\n            <span sxy-text=\"SALAXY.NG1.MessageThreadComponent.fileBtn\"></span>\r\n          </button>\r\n          <div class=\"btn-group btn-block dropup\">\r\n            <button type=\"button\" class=\"btn btn-secondary dropdown-toggle btn-labeled-left text-start mt-1 w-100\" data-bs-toggle=\"dropdown\" aria-haspopup=\"true\" aria-expanded=\"false\">\r\n              <i class=\"bi bi-chevron-up\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.NG1.MessageThreadComponent.moreFeaturesBtn\"></span>\r\n            </button>\r\n            <ul class=\"dropdown-menu dropdown-menu-end\" role=\"menu\">\r\n              <li role=\"menuitem\">\r\n                <a ng-click=\"$ctrl.delete(null, ('SALAXY.NG1.MessageThreadComponent.deleteThreadAlert' | sxyTranslate ))\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.MessageThreadComponent.deleteThread\"></a>\r\n              </li>\r\n              <li role=\"separator\" class=\"divider\"></li>\r\n              <li role=\"menuitem\">\r\n                <a ng-click=\"$ctrl.setType('absence')\" class=\"dropdown-item\">Lisää poissaoloja</a>\r\n              </li>\r\n              <li role=\"menuitem\">\r\n                <a ng-click=\"$ctrl.setType('annualLeave')\" class=\"dropdown-item\">Lisää lomapyyntö</a>\r\n              </li>\r\n              <li role=\"menuitem\">\r\n                <a ng-click=\"$ctrl.setType('calcRow')\" class=\"dropdown-item\">Lisää palkkarivejä</a>\r\n              </li>\r\n              <li role=\"menuitem\">\r\n                <a ng-click=\"$ctrl.setType('text')\" class=\"dropdown-item\">Teksti tai tiedosto (oletus)</a>\r\n              </li>\r\n            </ul>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div id=\"messageContainerBottom\">&nbsp;</div>\r\n  </div>\r\n</div>\r\n`);\n\n $templateCache.put(\"salaxy-components/communications/messages/proto-usecase/expenses.html\",`<h1>Kulukorvaukset tänne</h1>`);\n\n $templateCache.put(\"salaxy-components/communications/messages/proto-usecase/timer.html\",`<div>\r\n  <h3>Kellokortti</h3>\r\n    <div class=\"thumbnail\" style=\"max-width:400px; height: 320px; margin: auto;\" >\r\n      <div style=\"width: 100%; height: 100%;\" class=\"bg-primary text-center\">\r\n        <div style=\"font-size: 3.5em; padding-top: 20px;\">\r\n          <i class=\"bi bi-clock\" aria-hidden=\"true\"></i>\r\n          {{ $ctrl.currentEntry.total | date : \"HH:mm:ss\" : \"UTC\" }}\r\n        </div>\r\n        <div class=\"d-flex justify-content-center\">\r\n          Aloitus: \r\n          <span ng-if=\"!$ctrl.editStartTime\">{{ $ctrl.currentEntry.start | date : \"HH:mm\" }}</span>\r\n          <input ng-if=\"$ctrl.editStartTime\" class=\"form-control input-sm\" style=\"display: inline;width: 100px;\" type=\"time\" id=\"appt\" name=\"appt\" ng-model=\"$ctrl.currentEntry.start\" ng-model-options=\"{allowInvalid: true, debounce: 1000}\" required>\r\n          <button type=\"button\" class=\"btn btn-xs btn-primary\" ng-click=\"$ctrl.editStartTime=!$ctrl.editStartTime\"><i class=\"bi bi-pencil-fill\"></i></button>\r\n        </div>\r\n        <div>Yhteensä tänään 01:20</div>\r\n        <div style=\"padding: 10px;\">\r\n          <salaxy-input-typeahead label=\"Valitse projekti\" placeholder=\"Valitse projekti\" label-type=\"plain\" name=\"project\" ng-model=\"$ctrl.currentEntry.project\" options=\"$ctrl.projects\"></salaxy-input-typeahead>\r\n          <salaxy-input placeholder=\"Kommentti\" label-type=\"plain\" name=\"comment\" ng-model=\"$ctrl.currentEntry.comment\"></salaxy-input>\r\n        </div>\r\n        <div>\r\n          <a ng-if=\"!$ctrl.currentEntry.isStarted\" class=\"btn btn-lg btn-success\" href=\"\" ng-click=\"$ctrl.startTimer()\">\r\n            <i class=\"bi bi-play-fill bi-2x\"></i>\r\n          </a>\r\n          <a ng-if=\"$ctrl.currentEntry.isStarted\" class=\"btn btn-lg btn-danger\" href=\"\" ng-click=\"$ctrl.stopTimer()\">\r\n            <i class=\"bi bi-stop-fill bi-2x\"></i>\r\n          </a>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"list-group\">\r\n      <div class=\"list-group-item\" style=\"margin-top: 10px;padding-bottom: 0px\" ng-if=\"$ctrl.entries.length\">\r\n        <div class=\"list-group-item-heading\">\r\n          TÄNÄÄN, {{ \"today\" | sxyDate }}\r\n        </div>\r\n      </div>\r\n      <a href=\"\" class=\"list-group-item\" ng-repeat=\"entry in $ctrl.entries\">\r\n        <h4 class=\"list-group-item-heading\">\r\n          <div class=\"float-end\">{{ entry.total | date : \"HH:mm\" : \"UTC\" }}</div>\r\n          {{ entry.start | date : \"HH:mm\" }}-{{ entry.end | date : \"HH:mm\" }}\r\n        </h4>\r\n        <div class=\"float-end\">\r\n          <button type=\"button\" class=\"btn btn-xs btn-primary\"><i class=\"bi bi-pencil-fill\"></i></button>\r\n          <button type=\"button\" class=\"btn btn-xs btn-danger\"><i class=\"bi bi-trash-fill\"></i></button>\r\n        </div>\r\n        <p class=\"list-group-item-text\">{{ $ctrl.getProjectText(entry.project) }}</p>\r\n        <p class=\"list-group-item-text\" ng-if=\"entry.comment\">{{ entry.comment }}</p>\r\n      </a>\r\n      <div class=\"list-group-item\" style=\"\" ng-if=\"$ctrl.entries.length\">\r\n        <div class=\"list-group-item-footer\">\r\n          <div class=\"float-end\">{{ $ctrl.getTotal() | date : \"HH:mm\" : \"UTC\" }}</div>\r\n          Yhteensä\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <pre>{{ $ctrl.current | json }}</pre>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/communications/messages/proto-usecase/timesheet.html\",`<div>\r\n  <h3>Tuntiraportti</h3>\r\n  <div class=\"list-group\">\r\n    <div class=\"list-group-item bg-primary\">\r\n      <h4 class=\"list-group-item-heading text-center\">\r\n        <div>Viikko 18</div>\r\n        <i class=\"bi bi-arrow-left-circle-fill float-start\" aria-hidden=\"true\"></i>\r\n        <i class=\"bi bi-arrow-right-circle-fill float-end\" aria-hidden=\"true\"></i>\r\n        <div>2.-8.5.2022</div>\r\n      </h4>\r\n    </div>\r\n    <div class=\"list-group-item\" ng-repeat=\"day in $ctrl.calendarDemoData\">\r\n      <h4 class=\"list-group-item-heading\">\r\n        <div class=\"text-center float-start text-uppercase\" ng-class=\"day.isHoliday ? 'btn btn-default' : 'bg-primary'\" style=\"margin-left: -10px;margin-top:-5px;height: 55px; padding-top: 10px;width: 60px;\">\r\n          {{ day.day }}<br>\r\n          {{ day.date }}\r\n        </div>\r\n        <div class=\"float-end\" style=\"margin-top: 6px\">\r\n          <button type=\"button\" class=\"btn btn-default\"><i class=\"bi bi-pencil-fill\"></i></button>\r\n          <button type=\"button\" class=\"btn btn-default\"><i class=\"bi bi-plus-lg\"></i></button>\r\n        </div>\r\n        <p class=\"list-group-item-text\" style=\"height: 40px; padding-left: 80px; padding-top: 10px;\">{{ day.hours }}</p>\r\n      </h4>\r\n    </div>\r\n    <div class=\"list-group-item\">\r\n      <h4 class=\"list-group-item-heading\">\r\n        <div class=\"text-center float-start text-uppercase btn btn-default\" style=\"margin-left: -10px;margin-top:-5px;height: 55px; padding-top: 10px;width: 60px;\">\r\n          <small>Viikko</small><br>\r\n          18\r\n        </div>\r\n        <div class=\"float-end\" style=\"margin-top: 10px\">yhteensä</div>\r\n        <p class=\"list-group-item-text\" style=\"height: 40px; padding-left: 80px; padding-top: 10px;\">15:00 h</p>\r\n      </h4>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/communications/messages/proto-usecase/travel.html\",`<h1>Travel here</h1>`);\n\n $templateCache.put(\"salaxy-components/communications/MessageThread.html\",`<div class=\"salaxy-component salaxy-message-thread\">\r\n  <salaxy-spinner ng-if=\"$ctrl.isLoading\"></salaxy-spinner>\r\n  <div ng-if=\"$ctrl.status == 'loadError'\" class=\"alert alert-danger\" sxy-text=\"SALAXY.NG1.MessageThreadComponent.error\"></div>\r\n  <div>\r\n    <!-- ng-transclude does not work in include -->\r\n    <div ng-if=\"$ctrl.isNew()\">\r\n      <form name=\"newMessageThread\" ng-readonly=\"$ctrl.isReadOnly\" class=\"form-horizontal\">\r\n        <ng-transclude ng-transclude-slot=\"headerNew\">\r\n          <h1 sxy-text=\"SALAXY.NG1.MessageThreadComponent.newMessage.headerTitle\"></h1>\r\n          <p class=\"lead\" sxy-html=\"SALAXY.NG1.MessageThreadComponent.newMessage.headerDescription.html\"></p>\r\n        </ng-transclude>\r\n        <salaxy-input name=\"title\" label=\"SALAXY.NG1.MessageThreadComponent.title\" require=\"true\" ng-model=\"$ctrl.current.title\"></salaxy-input>\r\n        <salaxy-input-enum name=\"otherParty\" ng-model=\"$ctrl.otherParty\" ng-if=\"$ctrl.otherPartyOptions\" label=\"SALAXY.NG1.MessageThreadComponent.receiver\" type=\"select\" placeholder=\"SALAXY.UI_Terms.choose\" required options=\"$ctrl.otherPartyOptions\"></salaxy-input-enum>\r\n        <salaxy-input-enum name=\"msgType\" ng-model=\"$ctrl.msgType\" label=\"SALAXY.NG1.MessageThreadComponent.subject\" type=\"radio\" ng-init=\"$ctrl.msgType = 'salary'\" options=\"{ salary: ('SALAXY.NG1.MessageThreadComponent.subjectOptionSalary' | sxyTranslate), other:  ('SALAXY.NG1.MessageThreadComponent.subjectOptionOther' | sxyTranslate) }\"></salaxy-input-enum>\r\n        <salaxy-datepicker name=\"salaryDate\" ng-model=\"$ctrl.current.ownerWorkflow.salaryDate\" label=\"{{ $ctrl.msgType == 'salary' ? 'SALAXY.NG1.MessageThreadComponent.salaryDate' : 'SALAXY.NG1.MessageThreadComponent.replyDate'}}\" date-disabled=\"next-weekday\" require=\"$ctrl.msgType == 'salary'\" show-buttons=\"false\"></salaxy-datepicker>\r\n        <salaxy-form-group label-type=\"empty-label\" name=\"submit\" class=\"no-colon\">\r\n          <button type=\"submit\" class=\"btn btn-primary\" ng-disabled=\"!newMessageThread.$valid\" ng-click=\"$ctrl.save()\" sxy-text=\"SALAXY.NG1.MessageThreadComponent.ui.newMessageThreadBtn\"></button>\r\n        </salaxy-form-group>\r\n      </form>\r\n    </div>\r\n    <div ng-if=\"!$ctrl.isNew() && $ctrl.current\">\r\n      <ng-transclude ng-transclude-slot=\"header\">\r\n        <h2>\r\n          {{ $ctrl.current.title }}<small>, <span sxy-text=\"SALAXY.NG1.MessageThreadComponent.salaryDate\"></span> {{ $ctrl.current.ownerWorkflow.salaryDate | sxyDate }}</small>\r\n        </h2>\r\n      </ng-transclude>\r\n      <p ng-if=\"$ctrl.current.messages.length == 0\">&nbsp;</p>\r\n      <div class=\"messages-container\" ng-if=\"$ctrl.current.messages\">\r\n        <div ng-repeat=\"item in $ctrl.current.messages\" ng-switch=\"item.fromParty\">\r\n          <div ng-switch-when=\"owner,undefined\" ng-switch-when-separator=\",\">\r\n            <salaxy-avatar avatar=\"$ctrl.current.ownerInfo\" class=\"float-start\"></salaxy-avatar>\r\n            <div class=\"message-bubble left\" ng-class=\"{ 'in-edit': $ctrl.isInEdit, 'unread': !$ctrl.getReadTime(item)  }\">\r\n              <ng-include src=\"'salaxy-components/communications/messages/MessageContent.html'\"></ng-include>\r\n              <span class=\"updated-at\">{{ item.time | sxyTime }}, {{ $ctrl.getReadTime(item) ? (('SALAXY.NG1.MessageThreadComponent.read' |sxyTranslate) + ' ' + ($ctrl.getReadTime(item) | sxyTime)) : ('SALAXY.NG1.MessageThreadComponent.unread' |sxyTranslate) }}</span>\r\n            </div>\r\n          </div>\r\n          <div ng-switch-when=\"otherParty\" class=\"text-end\">\r\n            <salaxy-avatar avatar=\"$ctrl.current.otherPartyInfo\" class=\"float-end\"></salaxy-avatar>\r\n            <div class=\"message-bubble right {{item.type}}\" ng-class=\"{ 'in-edit': $ctrl.isInEdit, 'unread': !$ctrl.getReadTime(item) }\">\r\n              <ng-include src=\"'salaxy-components/communications/messages/MessageContent.html'\"></ng-include>\r\n              <span class=\"updated-at\" ng-if=\"item.type != 'email'\">{{ item.time | sxyTime }}, {{ $ctrl.getReadTime(item) ? (('SALAXY.NG1.MessageThreadComponent.read' |sxyTranslate) + ' ' + ($ctrl.getReadTime(item) | sxyTime)) : ('SALAXY.NG1.MessageThreadComponent.unread' |sxyTranslate)}}</span>\r\n              <span class=\"updated-at\" ng-if=\"item.type == 'email'\">{{ item.time | sxyTime }}</span>\r\n            </div>\r\n          </div>\r\n          <div ng-switch-default class=\"alert alert-danger\">\r\n            <ng-include src=\"'salaxy-components/communications/MessageThread_MessageContent.html'\"></ng-include>\r\n          </div>\r\n        </div>\r\n        <div class=\"padding message-actions\">\r\n          <div class=\"btn-toolbar mb-2\" role=\"toolbar\" ng-if=\"$ctrl.role == 'otherParty'\">\r\n            <salaxy-workflow-buttons api-ctrl=\"$ctrl\"></salaxy-workflow-buttons>\r\n            <div class=\"btn-group\" role=\"group\">\r\n              <button class=\"btn btn-primary\" ng-class=\"{ 'disabled': $ctrl.getReadTime()}\" ng-click=\"$ctrl.markAllAsRead()\" sxy-text=\"SALAXY.NG1.MessageThreadComponent.markAsReadBtn\"></button>\r\n            </div>\r\n            <button ng-if=\"$ctrl.role == 'otherParty'\" ng-click=\"$ctrl.sendNotification()\" class=\"btn btn-default\" sxy-text=\"SALAXY.NG1.MessageThreadComponent.sendtoEmailBtn\"></button>\r\n            <div class=\"btn-group\" role=\"group\">\r\n              <button class=\"btn btn-default\" ng-click=\"$ctrl.reload()\" sxy-text=\"SALAXY.NG1.MessageThreadComponent.reloadBtn\"></button>\r\n              <button class=\"btn btn-default\" ng-click=\"$ctrl.isInEdit=true\" ng-class=\"{ 'disabled': $ctrl.isInEdit }\" sxy-text=\"SALAXY.UI_Terms.edit\"></button>\r\n              <button class=\"btn\" ng-click=\"$ctrl.save();$ctrl.isInEdit=false\" ng-class=\"{ 'btn-primary': $ctrl.hasChanges, 'btn-default': !$ctrl.hasChanges }\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n              <button class=\"btn btn-default\" ng-class=\"{ 'disabled': !$ctrl.isInEdit }\" ng-click=\"$ctrl.reset();$ctrl.isInEdit=false\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n            </div>\r\n            <div ng-if=\"$ctrl.current.status == 'active' || $ctrl.current.status == 'approved' || $ctrl.current.status == 'rejected'\" class=\"btn-group btn-group-sm\" role=\"group\" aria-label=\"Approval toolbar\">\r\n              <button type=\"button\" class=\"btn btn-success\" ng-click=\"$ctrl.current.status = 'approved';$ctrl.save()\"\r\n                ng-disabled=\"$ctrl.current.status == 'approved'\">Hyväksy</button>\r\n              <button type=\"button\" class=\"btn btn-danger\" ng-click=\"$ctrl.current.status = 'rejected';$ctrl.save()\"\r\n                ng-disabled=\"$ctrl.current.status == 'rejected'\">Hylkää</button>\r\n              <button type=\"button\" class=\"btn btn-danger\" ng-click=\"$ctrl.current.status = 'active';$ctrl.save()\"\r\n                ng-disabled=\"$ctrl.current.status == 'active'\">Poista hyväksyntä/hylkäys</button>\r\n            </div>\r\n          </div>\r\n          <div ng-if=\"$ctrl.isReadOnly\" class=\"alert alert-info\">\r\n            <p>\r\n              <strong sxy-text=\"SALAXY.NG1.MessageThreadComponent.handledInfo\"></strong>\r\n              <br>\r\n              <salaxy-workflow-reopen api-ctrl=\"$ctrl\"></salaxy-workflow-reopen>\r\n            </p>\r\n          </div>\r\n          <div class=\"row\" ng-if=\"!$ctrl.isReadOnly\">\r\n            <div class=\"col-8 col-sm-9\">\r\n              <textarea placeholder=\"{{'SALAXY.NG1.MessageThreadComponent.writeOrPaste' |sxyTranslate}}\" ng-model=\"$ctrl.newMessage.content\"></textarea>\r\n            </div>\r\n            <div class=\"col-4 col-sm-3 d-flex flex-column\" ng-if=\"!$ctrl.isReadOnly\">\r\n              <button type=\"button\" class=\"btn btn-primary btn-labeled-left text-start mb-1\" ng-click=\"$ctrl.sendMessage()\" ng-disabled=\"!$ctrl.newMessage.content\">\r\n                <i class=\"bi bi-send-fill\"></i>\r\n                <span sxy-text=\"SALAXY.UI_Terms.send\"></span>\r\n              </button>\r\n              <button type=\"button\" class=\"btn btn-primary btn-labeled-left text-start mb-1\" ng-disabled=\"$ctrl.newMessage.content.length > 0\" ngf-select=\"$ctrl.uploadFiles($files)\" ngf-multiple=\"true\" ngf-max-size=\"10MB\" xxngf-pattern=\"$ctrl.supportedFilesPattern\">\r\n                <i class=\"bi bi-paperclip\"></i>\r\n                <span sxy-text=\"SALAXY.NG1.MessageThreadComponent.fileBtn\"></span>\r\n              </button>\r\n              <div class=\"btn-group btn-block dropup\" ng-if=\"$ctrl.role == 'otherParty'\">\r\n                <button type=\"button\" class=\"btn btn-secondary dropdown-toggle text-start w-100\" data-bs-toggle=\"dropdown\" aria-haspopup=\"true\" aria-expanded=\"false\">\r\n                  <span sxy-text=\"SALAXY.NG1.MessageThreadComponent.moreFeaturesBtn\"></span>\r\n                </button>\r\n                <ul class=\"dropdown-menu dropdown-menu-end\" role=\"menu\">\r\n                  <li role=\"menuitem\">\r\n                    <a ng-click=\"$ctrl.delete(null, ('SALAXY.NG1.MessageThreadComponent.deleteThreadAlert' | sxyTranslate ))\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.MessageThreadComponent.deleteThread\"></a>\r\n                  </li>\r\n                  <li role=\"separator\" class=\"divider\"></li>\r\n                  <li role=\"menuitem\">\r\n                    <a ng-click=\"$ctrl.addExistingCalc('draft')\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.MessageThreadComponent.addDraft\"></a>\r\n                  </li>\r\n                  <li role=\"menuitem\">\r\n                    <a ng-click=\"$ctrl.addExistingCalc('paid')\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.MessageThreadComponent.addPaid\"></a>\r\n                  </li>\r\n                  <li role=\"separator\" class=\"divider\"  salaxy-if-role=\"test\"></li>\r\n                  <li role=\"menuitem\" salaxy-if-role=\"test\">\r\n                    <a ng-click=\"$ctrl.addExistingPayroll('draft')\" class=\"dropdown-item\" sxy-text=\"Palkkalistaluonnos\"></a>\r\n                  </li>\r\n                  <li role=\"menuitem\"  salaxy-if-role=\"test\">\r\n                    <a ng-click=\"$ctrl.addExistingPayroll('paid')\" class=\"dropdown-item\" sxy-text=\"Maksettu palkkalista\"></a>\r\n                  </li>\r\n                </ul>\r\n              </div>\r\n            </div>\r\n          </div>\r\n        </div>\r\n        <div id=\"messageContainerBottom\">&nbsp;</div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/communications/MessageThreadList.html\",`<div class=\"salaxy-component salaxy-message-thread-list\">\r\n  <div class=\"btn-toolbar\" role=\"toolbar\">\r\n    <div class=\"btn-group btn-group-sm\">\r\n      <button type=\"button\" class=\"btn btn-default\"\r\n        ng-click=\"$ctrl.$odata.options.$filter = 'status eq \\\\'active\\\\' or ( status eq \\\\'draft\\\\' and data/otherPartyUnreadCount gt 0 )';$ctrl.$odata.searchChanged()\"\r\n        ng-class=\"{ active: $ctrl.$odata.options.$filter == 'status eq \\\\'active\\\\' or ( status eq \\\\'draft\\\\' and data/otherPartyUnreadCount gt 0 )' }\">Aktiiviset</button>\r\n      <button type=\"button\" class=\"btn btn-default\"\r\n        ng-click=\"$ctrl.$odata.options.$filter = '(status eq \\\\'approved\\\\' or status eq \\\\'rejected\\\\' or status eq \\\\'active\\\\' or status eq \\\\'draft\\\\')';$ctrl.$odata.searchChanged()\"\r\n        ng-class=\"{ active: $ctrl.$odata.options.$filter == '(status eq \\\\'approved\\\\' or status eq \\\\'rejected\\\\' or status eq \\\\'active\\\\' or status eq \\\\'draft\\\\')' }\">Kaikki</button>\r\n    </div>\r\n    <div class=\"btn-group btn-group-sm ms-1\" ng-if=\"!$ctrl.readOnly\" ng-controller=\"SessionController as $sessionCtrl\">\r\n        <salaxy-action-button button-class=\"btn-sm btn-primary\" action=\"'newMessage'\" label=\"SALAXY.NG1.ActionButtonComponent.startNewMessage\" disabled=\"!$sessionCtrl.session.settings.partner.accountId\">\r\n        </salaxy-action-button>\r\n    </div>\r\n  </div>\r\n\r\n  <salaxy-odata-table crud-controller=\"MessageThreadCrudController as $crud\" ng-ref=\"$ctrl.$odata\"\r\n    options=\"{ $top: $ctrl.limitTo, $filter: 'status eq \\\\'active\\\\' or ( status eq \\\\'draft\\\\' and data/otherPartyUnreadCount gt 0 )' }\" template-url=\"salaxy-components/odata/lists/MessageThreads.html\">\r\n  </salaxy-odata-table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/communications/VarmaBanner.html\",`<div class=\"salaxy-component salaxy-varma-banner\">\r\n  <div ng-if=\"$ctrl.varmaPensionBanners.isReady\" ng-init=\"$ctrl.showVarmaPopup()\">\r\n\r\n\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/communications/Welcome.html\",`<div class=\"salaxy-component salaxy-welcome\">\r\n  <div ng-controller=\"SessionController as $sessionCtrl\">\r\n    <div ng-if=\"$ctrl.hasSystemAlert\" class=\"salaxy-welcome-system-alert alert-has-system-alert\" ng-bind-html=\"$ctrl.systemAlertHtml\"></div>\r\n    <salaxy-alert ng-if=\"$ctrl.tutorials.showAnon\" type=\"danger\" icon=\"bi-box-arrow-in-right\" class=\"alert-anon\">\r\n      <main sxy-html=\"SALAXY.NG1.WelcomeComponent.showAnon.main.html\"></main>\r\n    </salaxy-alert>\r\n    <salaxy-alert ng-if=\"$ctrl.tutorials.showInsurance || $ctrl.tutorials.showPension\" type=\"warning\" class=\"alert-insurance-and-pension\">\r\n      <main>\r\n        <div class=\"row\">\r\n          <div class=\"col-sm-8 col-lg-9\">\r\n            <p class=\"lead lead-with-text\" sxy-html=\"SALAXY.NG1.WelcomeComponent.showSettings.lead.html\"></p>\r\n            <p sxy-html=\"SALAXY.NG1.WelcomeComponent.showSettings.main\"></p>\r\n          </div>\r\n          <div class=\"col-sm-4 col-lg-3\">\r\n            <a href=\"#/settings/insurances\" class=\"btn btn-warning float-end-sm btn-block btn-edit-settings\" style=\"margin-bottom:10px;\" sxy-text=\"SALAXY.NG1.WelcomeComponent.showSettings.settings.cta\"></a>\r\n          </div>\r\n        </div>\r\n      </main>\r\n    </salaxy-alert>\r\n    <salaxy-alert ng-if=\"$ctrl.tutorials.showSign\" class=\"alert-sign\" type=\"warning\">\r\n      <main>\r\n        <div class=\"row\">\r\n          <div class=\"col-sm-8 col-lg-9\">\r\n            <p class=\"lead lead-with-text\" sxy-text=\"SALAXY.NG1.WelcomeComponent.showSign.lead\"></p>\r\n            <p sxy-html=\"SALAXY.NG1.WelcomeComponent.showSign.main.html\"></p>\r\n          </div>\r\n          <div class=\"col-sm-4 col-lg-3\">\r\n            <button sxy-if-role=\"person\" ng-controller=\"WorkerOnboardingController as wizard\" class=\"btn btn-warning btn-add-signature float-end btn-block\" ng-click=\"wizard.launch()\" sxy-text=\"SALAXY.NG1.WelcomeComponent.showSign.main.cta\"></button>\r\n            <button sxy-if-role=\"company\" ng-controller=\"CompanyOnboardingController as wizard\" class=\"btn btn-warning btn-add-signature float-end btn-block\" ng-click=\"wizard.launch()\" sxy-text=\"SALAXY.NG1.WelcomeComponent.showSign.main.cta\"></button>\r\n          </div>\r\n        </div>\r\n      </main>\r\n    </salaxy-alert>\r\n    <salaxy-invoice-alerts ng-if=\"'auth' | sxyIsInRole\" payment-channels=\"['palkkausManual', 'holvi', 'talenomOnline']\"></salaxy-invoice-alerts>    \r\n    <salaxy-alert ng-if=\"$ctrl.tutorials.showTryPayroll\" type=\"primary\" class=\"alert-try-payroll\">\r\n      <main>\r\n        <div class=\"row\">\r\n          <div class=\"col-sm-8 col-lg-9\">\r\n            <p class=\"lead\" sxy-text=\"SALAXY.NG1.WelcomeComponent.showTryPayroll.main\"></p>\r\n          </div>\r\n          <div class=\"col-sm-4 col-lg-3\">\r\n            <a class=\"btn btn-info btn-block\" href=\"#/payroll\" sxy-text=\"SALAXY.NG1.WelcomeComponent.showTryPayroll.cta\"></a>\r\n          </div>\r\n        </div>\r\n      </main>\r\n    </salaxy-alert>\r\n    <salaxy-alert ng-if=\"$ctrl.showAutoTaxcardInfobox()\" type=\"warning\" class=\"taxcard-info\">\r\n      <main>\r\n        <div class=\"row\">\r\n          <div class=\"col-sm-8 col-lg-9\">\r\n            <p class=\"lead\" sxy-html=\"SALAXY.NG1.WelcomeComponent.autoTaxcard.lead.html\"></p>\r\n          </div>\r\n          <div class=\"col-sm-4 col-lg-3\">\r\n            <a ng-href=\"#/workers\" class=\"btn btn-warning btn-add btn-add-taxcard btn-block\" title=\"{{'SALAXY.NG1.WorkerListComponent.activeAutoTaxcard' | sxyTranslate}}\" sxy-text=\"SALAXY.NG1.WorkerListComponent.autoTaxcard\"></a>\r\n          </div>\r\n        </div>\r\n      </main>\r\n    </salaxy-alert>\r\n    <salaxy-alert ng-if=\"$ctrl.tutorials.showAddCalculation\" type=\"primary\" class=\"alert-add-calculation\">\r\n      <main>\r\n        <div class=\"row\">\r\n          <div class=\"col-sm-8 col-lg-9\">\r\n            <p class=\"lead\" sxy-html=\"SALAXY.NG1.WelcomeComponent.showAddCalculation.main.html\"></p>\r\n            <salaxy-input-typeahead\r\n              label-type=\"no-label\"\r\n              ng-model=\"$ctrl.employmentId\"\r\n              name=\"options_type\"\r\n              disable-cache=\"true\"\r\n              placeholder=\"{{'SALAXY.NG1.WelcomeComponent.showAddCalculation.selectWorkerPlaceholder' | sxyTranslate}}\"\r\n              get-options=\"$ctrl.filterWorkers\"\r\n              on-select-function=\"$ctrl.createNewCalculationFor\"\r\n              input-formatter=\"$ctrl.getWorkerName\">\r\n            </salaxy-input-typeahead>\r\n          </div>\r\n          <div class=\"col-sm-4 col-lg-3\">\r\n            <button class=\"btn btn-info btn-add btn-add-worker btn-block mb-2\" ng-click=\"$ctrl.launchEmploymentWizard()\" sxy-text=\"SALAXY.NG1.WelcomeComponent.showAddWorker.main.cta\"></button>\r\n            <a class=\"btn btn-default btn-block btn-try-payroll\" href=\"#/payroll\" sxy-text=\"SALAXY.NG1.WelcomeComponent.showAddWorker.tryPayroll.cta\"></a>\r\n          </div>\r\n        </div>\r\n      </main>\r\n    </salaxy-alert>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/form-controls/Datepicker.html\",`<salaxy-form-group ng-if=\"$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n  <div class=\"form-control-plaintext\">{{ $ctrl.datepickerValue }} </div>\r\n</salaxy-form-group>\r\n<ng-form name=\"{{$ctrl.name}}Form\" class=\"salaxy-component salaxy-datepicker\" ng-if=\"!$ctrl.getReadOnly()\">\r\n  <salaxy-form-group name=\"{{$ctrl.name}}\" require=\"$ctrl.require\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <div class=\"form-control datepicker-input\" ng-model=\"$ctrl.datepickerValue\" id=\"{{$ctrl.name}}\" name=\"{{$ctrl.name}}\" ng-change=\"$ctrl.onChange()\" ng-required=\"$ctrl.require\" ng-readonly=\"$ctrl.readonly\" ng-disabled=\"$ctrl.getDisabled()\"></div>\r\n    <div ng-show=\"!$ctrl.disableValidationErrors && ($ctrl.validationErrors.length > 0 && ({{$ctrl.name}}Form.{{$ctrl.name}}.$touched || {{$ctrl.name}}Form.$$parentForm.$submitted))\" class=\"input-errors\">\r\n      <span class=\"salaxy-validation-error text-danger small\" ng-repeat=\"validationError in $ctrl.validationErrors\" sxy-text=\"{{ validationError }}\" params=\"{ minlength: $ctrl.minlength, maxlength: $ctrl.maxlength }\"></span><br/>\r\n    </div>\r\n  </salaxy-form-group>\r\n</ng-form>\r\n<salaxy-form-group ng-if=\"$ctrl.isMultiple\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{ $ctrl.labelDaysCount || 'SALAXY.NG1.DateRange.labelDaysCount' }}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n  <div class=\"form-control-plaintext\">{{ $ctrl.datepickerValue.daysCount }}</div>\r\n</salaxy-form-group>`);\n\n $templateCache.put(\"salaxy-components/form-controls/DatepickerPopup.html\",`<style>\r\n  input.datepicker-popup,\r\n  input.datepicker-input {\r\n    background-image: url('data:image/svg+xml,%3Csvg xmlns=\"http://www.w3.org/2000/svg\" width=\"16\" height=\"16\" fill=\"currentColor\" fill-opacity=\"0.54\" viewBox=\"0 0 16 16\"%3E%3Cpath d=\"M14 0H2a2 2 0 0 0-2 2v12a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V2a2 2 0 0 0-2-2M1 3.857C1 3.384 1.448 3 2 3h12c.552 0 1 .384 1 .857v10.286c0 .473-.448.857-1 .857H2c-.552 0-1-.384-1-.857z\"/%3E%3Cpath d=\"M6.5 7a1 1 0 1 0 0-2 1 1 0 0 0 0 2m3 0a1 1 0 1 0 0-2 1 1 0 0 0 0 2m3 0a1 1 0 1 0 0-2 1 1 0 0 0 0 2m-9 3a1 1 0 1 0 0-2 1 1 0 0 0 0 2m3 0a1 1 0 1 0 0-2 1 1 0 0 0 0 2m3 0a1 1 0 1 0 0-2 1 1 0 0 0 0 2m3 0a1 1 0 1 0 0-2 1 1 0 0 0 0 2m-9 3a1 1 0 1 0 0-2 1 1 0 0 0 0 2m3 0a1 1 0 1 0 0-2 1 1 0 0 0 0 2m3 0a1 1 0 1 0 0-2 1 1 0 0 0 0 2\"/%3E%3C/svg%3E');\r\n    background-repeat: no-repeat;\r\n    background-position: center;\r\n    background-size: 16px;\r\n    width: 3.5em !important;\r\n    cursor: pointer;\r\n    caret-color: transparent;\r\n    color: transparent !important;\r\n    user-select: none !important;\r\n  }\r\n\r\n  input.datepicker-input::selection {\r\n    background: transparent;\r\n    color: transparent;\r\n  }\r\n  .datepicker-text-input.validation-error {\r\n    border-color: rgba(255, 0, 0, 0.25) !important;\r\n    z-index: 1;\r\n  }\r\n\r\n  .datepicker-text-input.validation-error:active,\r\n  .datepicker-text-input.validation-error:focus {\r\n    box-shadow: 0 0 0 0.25rem rgba(255, 0, 0, 0.25) !important;\r\n    z-index: 1;\r\n  }\r\n</style>\r\n<salaxy-form-group ng-if=\"$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n  <div class=\"form-control-plaintext\">{{ $ctrl.datepickerValue }} </div>\r\n</salaxy-form-group>\r\n<ng-form ng-show=\"!$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}Form\" class=\"salaxy-component salaxy-datepicker-popup\">\r\n  <salaxy-form-group ng-if=\"$ctrl.inputMode == 'openClose' && !$ctrl.isOpen\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <div class=\"form-control-plaintext\">{{ $ctrl.datepickerValue }}\r\n      <span class=\"float-end btn-padding-right\">\r\n        <i ng-click=\"$ctrl.isOpen = !$ctrl.isOpen\" class=\"bi bi-pencil-fill clickable\"></i>\r\n      </span>\r\n    </div>\r\n  </salaxy-form-group>\r\n  <salaxy-form-group ng-show=\"!$ctrl.inputMode || ($ctrl.inputMode == 'openClose' && $ctrl.isOpen)\" name=\"{{$ctrl.name}}\" require=\"$ctrl.require\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <div class=\"input-group\">\r\n      <input ng-focus=\"$ctrl.initDatepicker(true)\" class=\"form-control datepicker-text-input\" ng-class=\"$ctrl.validationError ? 'validation-error' : ''\" type=\"text\" autocomplete=\"off\" ng-model-options=\"{ debounce: 1000 }\" name=\"datepicker-popup-text-input\" placeholder=\"{{ $ctrl.placeholder ? ($ctrl.placeholder | sxyTranslate) : ('SALAXY.NG1.DatepickerPopupComponent.placeholder' | sxyTranslate) }}\" ng-model=\"$ctrl.datepickerValue\" ng-change=\"$ctrl.changeManualDate()\" ng-required=\"$ctrl.require\"\r\n        ng-readonly=\"$ctrl.readonly\" ng-disabled=\"$ctrl.disabled\" salaxy-datepicker-input-validation>\r\n      <input ng-focus=\"$ctrl.initDatepicker()\" class=\"form-control datepicker-popup datepicker-input p-0 flex-grow-0\" type=\"text\" autocomplete=\"off\" name=\"datepicker-popup\" ng-model=\"$ctrl.datepickerValue\" ng-required=\"$ctrl.require\"\r\n        ng-readonly=\"$ctrl.readonly\" ng-disabled=\"$ctrl.disabled\" salaxy-datepicker-input-validation>\r\n      <span class=\"input-group-btn\">\r\n        <button ng-if=\"$ctrl.getToolTipHtml()\" type=\"button\" class=\"btn btn-default\" data-bs-toggle=\"popover\" data-bs-container=\"body\" aria-label=\"Info\" data-bs-html=\"true\" data-bs-title=\"'Info'\" data-bs-content=\"$ctrl.getToolTipHtml()\" data-bs-placement=\"'{{$ctrl.tooltipPlacement}}'\" sxy-bs5-popover>\r\n          <span class=\"bi bi-question-circle-fill\"></span>\r\n        </button>\r\n        <button ng-if=\"$ctrl.inputMode == 'openClose'\" class=\"btn btn-transparent\" ng-click=\"$ctrl.isOpen = !$ctrl.isOpen\">\r\n          <i class=\"bi bi-pencil-fill\"></i>\r\n        </button>\r\n      </span>\r\n    </div>\r\n    <div ng-if=\"$ctrl.validationError\" class=\"input-errors\">\r\n      <span class=\"salaxy-validation-error text-danger small\" sxy-text=\"{{ $ctrl.validationError }}\"></span>\r\n    </div>\r\n  </salaxy-form-group>\r\n</ng-form>`);\n\n $templateCache.put(\"salaxy-components/form-controls/DateRange.html\",`<style>\r\n  .datepicker-text-input.validation-error {\r\n    border-color: rgba(255, 0, 0, 0.25) !important;\r\n    z-index: 1;\r\n  }\r\n\r\n  .datepicker-text-input.validation-error:active,\r\n  .datepicker-text-input.validation-error:focus {\r\n    box-shadow: 0 0 0 0.25rem rgba(255, 0, 0, 0.25) !important;\r\n    z-index: 1;\r\n  }\r\n</style>\r\n<salaxy-form-group ng-if=\"$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n  <div class=\"form-control-plaintext\">{{ $ctrl.dateRangeValues.formattedRange || \"-\" }}</div>\r\n</salaxy-form-group>\r\n<ng-form ng-if=\"!$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}Form\" class=\"salaxy-component salaxy-date-range mode-{{ $ctrl.mode || 'range' }}\">\r\n  <salaxy-form-group ng-if=\"$ctrl.inputMode == 'openClose' && !$ctrl.isOpen\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <div class=\"form-control-plaintext\">{{ $ctrl.dateRangeValues.formattedRange || \"-\" }}\r\n      <span class=\"float-end btn-padding-right\">\r\n        <i ng-click=\"$ctrl.isOpen = !$ctrl.isOpen\" class=\"bi bi-pencil-fill clickable\"></i>\r\n      </span>\r\n    </div>\r\n  </salaxy-form-group>\r\n  <div ng-show=\"!$ctrl.inputMode || ($ctrl.inputMode == 'openClose' && $ctrl.isOpen)\">\r\n    <salaxy-input-enum ng-if=\"$ctrl.mode == 'calc' && !$ctrl.periodShortcut\" ng-model=\"$ctrl.periodShortcut\" name=\"periodShortcut\" label=\"SALAXY.NG1.DateRange.salaryPeriod\" label-cols=\"{{$ctrl.labelCols}}\" type=\"radio\" options=\"$ctrl.periodShortcuts\"></salaxy-input-enum>\r\n    <salaxy-input-enum ng-if=\"$ctrl.mode == 'calc' && $ctrl.periodShortcut\" ng-model=\"$ctrl.periodShortcut\" name=\"periodShortcut\" label=\"SALAXY.NG1.DateRange.salaryPeriod\" label-cols=\"{{$ctrl.labelCols}}\" type=\"select\" options=\"$ctrl.periodShortcuts\"></salaxy-input-enum>\r\n    <salaxy-form-group ng-show=\"$ctrl.mode != 'calc' || $ctrl.periodShortcut == 'other'\" ng-init=\"$ctrl.selectedDates = []\" name=\"{{ $ctrl.name + '_datepicker' }}\" label=\"{{$ctrl.label}}\" require=\"$ctrl.require\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n      <div class=\"salaxy-read-only\">\r\n        <div class=\"form-control-plaintext\">\r\n          {{ $ctrl.dateRangeValues.formattedRange || \"-\" }}\r\n          <span class=\"float-end btn-padding-right\" ng-if=\"$ctrl.inputMode == 'openClose'\">\r\n            <i ng-click=\"$ctrl.isOpen = !$ctrl.isOpen\" class=\"bi bi-pencil-fill clickable\"></i>\r\n          </span>\r\n        </div>\r\n      </div>\r\n      <div class=\"d-flex gap-2 align-items-center\">\r\n        <label>\r\n          {{ 'SALAXY.MODEL.DateRange.start.title' | sxyTranslate }}\r\n          <input type=\"text\" class=\"form-control datepicker-text-input\" ng-model=\"$ctrl.datepickerValueStart\" ng-model-options=\"{ debounce: 1000 }\" ng-change=\"$ctrl.changeManualDate()\" ng-class=\"$ctrl.validationError ? 'validation-error' : ''\">\r\n        </label>\r\n        <span class=\"mt-4\">-</span>\r\n        <label>\r\n          {{ 'SALAXY.MODEL.DateRange.end.title' | sxyTranslate }}\r\n          <input type=\"text\" class=\"form-control datepicker-text-input\" ng-model=\"$ctrl.datepickerValueEnd\" ng-model-options=\"{ debounce: 1000 }\" ng-change=\"$ctrl.changeManualDate()\" ng-class=\"$ctrl.validationError ? 'validation-error' : ''\">\r\n        </label>\r\n      </div>\r\n      <div ng-if=\"$ctrl.validationError\" class=\"input-errors\">\r\n        <span class=\"salaxy-validation-error text-danger small\" sxy-text=\"{{ $ctrl.validationError }}\"></span>\r\n      </div>\r\n      <div class=\"form-control input-daterange\" ng-model=\"$ctrl.dateRangeValues\" id=\"{{$ctrl.name}}\" name=\"{{$ctrl.name}}\" ng-required=\"$ctrl.require\" ng-readonly=\"$ctrl.readonly\" on-change=\"$ctrl.dateRangeChange()\" ng-disabled=\"$ctrl.getDisabled()\"></div>\r\n    </salaxy-form-group>\r\n    <div ng-if=\"$ctrl.mode == 'calc' && $ctrl.periodShortcut && $ctrl.periodShortcut != 'other'\">\r\n      <salaxy-form-group name=\"{{$ctrl.name}}_periodStartDate\" label=\"SALAXY.NG1.DateRange.startDate\" label-cols=\"{{$ctrl.labelCols}}\">\r\n        <input type=\"text\" class=\"form-control\" autocomplete=\"off\" id=\"{{$ctrl.name}}_periodStartDate\" name=\"{{$ctrl.name}}_periodStartDate\" placeholder=\"{{'SALAXY.UI_Terms.dateFormats.dm' | sxyTranslate}}\" ng-model=\"$ctrl.periodStartDate\" ng-model-options=\"{allowInvalid: true, debounce: 250, updateOn: 'default' }\"\r\n        />\r\n        <div ng-if=\"$ctrl.periodStartDateError\" class=\"form-control-plaintext text-danger\">{{ $ctrl.periodStartDateError | sxyTranslate }}</div>\r\n      </salaxy-form-group>\r\n      <salaxy-form-group name=\"formattedRange\" label=\"SALAXY.NG1.DateRange.labelStartAndEndDate\" label-cols=\"{{$ctrl.labelCols}}\" class=\"salaxy-read-only\">\r\n        <div class=\"form-control-plaintext\">{{ $ctrl.dateRangeValues.formattedRange }}</div>\r\n      </salaxy-form-group>\r\n    </div>\r\n  </div>\r\n  <div>\r\n    <salaxy-form-group ng-if=\"$ctrl.inputMode == 'openClose' && !$ctrl.isOpen\" name=\"{{$ctrl.name}}\" label=\"{{ $ctrl.labelDaysCount || 'SALAXY.NG1.DateRange.labelDaysCount' }}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\" class=\"salaxy-read-only\">\r\n      <div class=\"form-control-plaintext\">{{ $ctrl.dateRangeValues.daysCount }}\r\n        <span class=\"float-end btn-padding-right\">\r\n          <i ng-click=\"$ctrl.isOpen = !$ctrl.isOpen\" class=\"bi bi-pencil-fill clickable\"></i>\r\n        </span>\r\n      </div>\r\n    </salaxy-form-group>\r\n    <salaxy-form-group ng-if=\"!$ctrl.inputMode || ($ctrl.inputMode == 'openClose' && $ctrl.isOpen)\" name=\"{{$ctrl.name}}\" require=\"$ctrl.require\" label=\"{{ $ctrl.labelDaysCount || 'SALAXY.NG1.DateRange.labelDaysCount' }}\" label-type=\"{{$ctrl.labelType}}\"\r\n      label-cols=\"{{$ctrl.labelCols}}\">\r\n      <div ng-class=\"{'input-group': $ctrl.inputMode == 'openClose'}\">\r\n        <input type=\"text\" class=\"form-control\" autocomplete=\"off\" id=\"{{$ctrl.name}}\" name=\"{{$ctrl.name}}\" placeholder=\"{{ $ctrl.getPlaceholder() | sxyTranslate}}\" ng-model=\"$ctrl.dateRangeValues.daysCount\" ng-model-options=\"{allowInvalid: true, debounce: 250}\" ng-change=\"$ctrl.onDaysCountChange()\"\r\n          ng-pattern=\"$ctrl.pattern\" ng-required=\"$ctrl.require\" ng-readonly=\"$ctrl.readonly\" ng-disabled=\"$ctrl.getDisabled()\" ng-minlength=\"$ctrl.minlength\" ng-maxlength=\"$ctrl.maxlength\" maxlength=\"{{$ctrl.maxlength}}\" />\r\n        <div class=\"input-group-btn\" ng-if=\"$ctrl.inputMode == 'openClose'\">\r\n          <button class=\"btn btn-transparent float-end\" ng-click=\"$ctrl.isOpen = !$ctrl.isOpen\">\r\n            <i class=\"bi bi-pencil-fill\"></i>\r\n          </button>\r\n        </div>\r\n      </div>\r\n    </salaxy-form-group>\r\n  </div>\r\n</ng-form>\r\n<salaxy-form-group ng-if=\"$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{ $ctrl.labelDaysCount || 'SALAXY.NG1.DateRange.labelDaysCount' }}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n  <div class=\"form-control-plaintext\">{{ $ctrl.dateRangeValues.daysCount }}</div>\r\n</salaxy-form-group>`);\n\n $templateCache.put(\"salaxy-components/form-controls/FormGroup.html\",`<div ng-if=\"$ctrl.getLabelType() == 'basic'\" class=\"row\">\r\n  <label for=\"{{$ctrl.name}}\" class=\"col-12 col-form-label\"><span class=\"label-text\">{{$ctrl.label | sxyTranslate}}</span><span class=\"salaxy-form-group-required-indicator\"\r\n    ng-show=\"!!$ctrl.require\">*</span>\r\n  </label>\r\n  <div class=\"col-12\">\r\n    <ng-transclude></ng-transclude>\r\n  </div>\r\n</div>\r\n<div ng-if=\"$ctrl.getLabelType() == 'empty-label'\" class=\"row\">\r\n  <div class=\"{{ $ctrl.getLabelCols('label') }} col-form-label\"></div>\r\n  <div class=\"{{ $ctrl.getLabelCols('value') }}\">\r\n    <ng-transclude></ng-transclude>\r\n  </div>\r\n</div>\r\n<div ng-if=\"$ctrl.getLabelType() == 'no-label'\">\r\n  <div class=\"{{ $ctrl.getLabelCols('no-label') }}\">\r\n    <ng-transclude></ng-transclude>\r\n  </div>\r\n</div>\r\n<span ng-if=\"$ctrl.getLabelType() == 'plain'\" class=\"salaxy-form-group-plain\">\r\n  <ng-transclude></ng-transclude>\r\n</span>\r\n<div ng-if=\"$ctrl.getLabelType() == 'horizontal'\" class=\"row mb-1\">\r\n  <label for=\"{{$ctrl.name}}\" class=\"{{ $ctrl.getLabelCols('label') }} col-form-label\">\r\n    <span class=\"label-text\">{{$ctrl.label | sxyTranslate}}</span><span class=\"salaxy-form-group-required-indicator\"\r\n      ng-show=\"!!$ctrl.require\">*</span>\r\n  </label>\r\n  <div class=\"{{ $ctrl.getLabelCols('value') }}\">\r\n    <ng-transclude class=\"w-100\"></ng-transclude>\r\n  </div>\r\n</div>\r\n<div ng-if=\"$ctrl.getLabelType() == 'inline'\" class=\"row mb-1\">\r\n  <label for=\"{{$ctrl.name}}\" class=\"{{ $ctrl.getLabelCols('label') }} col-form-label\">\r\n    <span class=\"label-text\">{{$ctrl.label | sxyTranslate}}</span>\r\n    <span class=\"salaxy-form-group-required-indicator\" ng-show=\"!!$ctrl.require\">*</span>\r\n  </label>\r\n  <ng-transclude class=\"inline-salaxy-input {{ $ctrl.getLabelCols('value') }}\"></ng-transclude>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/form-controls/Input.html\",`<salaxy-form-group ng-if=\"$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n  <div class=\"form-control-plaintext\">{{ $ctrl.value }}\r\n\r\n  </div>\r\n\r\n</salaxy-form-group>\r\n\r\n<ng-form ng-if=\"!$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}Form\" class=\"salaxy-component salaxy-input\">\r\n  <salaxy-form-group ng-if=\"$ctrl.inputMode == 'openClose' &&  !$ctrl.isOpen\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <div class=\"form-control-plaintext\">{{ $ctrl.value || \"\\\\u00A0\" }}\r\n      <span class=\"float-end btn-padding-right\">\r\n          <i ng-click=\"$ctrl.isOpen = !$ctrl.isOpen\" class=\"bi bi-pencil-fill clickable\"></i>\r\n      </span>\r\n    </div>\r\n  </salaxy-form-group>\r\n\r\n  <salaxy-form-group ng-if=\"!$ctrl.inputMode || ($ctrl.inputMode == 'openClose' && $ctrl.isOpen)\" name=\"{{$ctrl.name}}\" label=\"{{$ctrl.label}}\" require=\"$ctrl.require\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <div ng-if=\"$ctrl.getToolTipHtml()\" class=\"input-group\">\r\n      <input type=\"{{$ctrl.type || 'text'}}\" class=\"form-control\" autocomplete=\"off\" id=\"{{$ctrl.name}}\" name=\"{{$ctrl.name}}\" placeholder=\"{{ $ctrl.getPlaceholder() | sxyTranslate }}\" ng-model=\"$ctrl.value\" ng-model-options=\"{allowInvalid: true, debounce: 250, updateOn: 'default' }\"\r\n        ng-change=\"$ctrl.onChange()\" ng-pattern=\"$ctrl.pattern\" ng-required=\"$ctrl.require\" ng-readonly=\"$ctrl.readonly\" ng-disabled=\"$ctrl.getDisabled()\" ng-minlength=\"$ctrl.minlength\" ng-maxlength=\"$ctrl.maxlength\" maxlength=\"{{$ctrl.maxlength}}\" />\r\n      <div class=\"input-group-btn\">\r\n        <button type=\"button\" class=\"btn btn-default\" data-bs-container=\"body\" aria-label=\"Info\" data-bs-toggle=\"popover\" data-bs-html=\"true\" data-bs-title=\"'Info'\" data-bs-content=\"$ctrl.getToolTipHtml()\" data-bs-placement=\"'{{$ctrl.tooltipPlacement}}'\" sxy-bs5-popover>\r\n          <span class=\"bi bi-question-circle-fill\"></span>\r\n        </button>\r\n        <button ng-if=\"$ctrl.inputMode == 'openClose'\" class=\"btn btn-transparent\" ng-click=\"$ctrl.isOpen = !$ctrl.isOpen\">\r\n          <i class=\"bi bi-pencil-fill\"></i>\r\n        </button>\r\n      </div>\r\n    </div>\r\n    <div ng-if=\"!$ctrl.getToolTipHtml()\" ng-class=\"{'input-group': $ctrl.inputMode == 'openClose'}\">\r\n      <input type=\"{{$ctrl.type || 'text'}}\" class=\"form-control\" autocomplete=\"off\" id=\"{{$ctrl.name}}\" name=\"{{$ctrl.name}}\" placeholder=\"{{ $ctrl.getPlaceholder() | sxyTranslate }}\" ng-model=\"$ctrl.value\" ng-model-options=\"{allowInvalid: true, debounce: 250, updateOn: 'default' }\"\r\n        ng-change=\"$ctrl.onChange()\" ng-pattern=\"$ctrl.pattern\" ng-required=\"$ctrl.require\" ng-readonly=\"$ctrl.readonly\" ng-disabled=\"$ctrl.getDisabled()\" ng-minlength=\"$ctrl.minlength\" ng-maxlength=\"$ctrl.maxlength\" maxlength=\"{{$ctrl.maxlength}}\" />\r\n      <div class=\"input-group-btn\" ng-if=\"$ctrl.inputMode == 'openClose'\">\r\n        <button class=\"btn btn-transparent float-end\" ng-click=\"$ctrl.isOpen = !$ctrl.isOpen\">\r\n          <i class=\"bi bi-pencil-fill\"></i>\r\n        </button>\r\n      </div>\r\n    </div>\r\n\r\n    <div ng-show=\"!$ctrl.disableValidationErrors && ($ctrl.validationErrors.length > 0 && ({{$ctrl.name}}Form.{{$ctrl.name}}.$touched || {{$ctrl.name}}Form.$$parentForm.$submitted))\" class=\"input-errors\">\r\n      <span class=\"salaxy-validation-error text-danger small\" ng-repeat=\"validationError in $ctrl.validationErrors\" sxy-text=\"{{ validationError}}\" params=\"{ minlength: $ctrl.minlength, maxlength: $ctrl.maxlength }\"></span><br/>\r\n    </div>\r\n  </salaxy-form-group>\r\n\r\n</ng-form>`);\n\n $templateCache.put(\"salaxy-components/form-controls/InputAccountingTarget.html\",`<ng-form name=\"{{$ctrl.name}}Form\" class=\"salaxy-component salaxy-input-accounting-target\">\r\n  <salaxy-form-group ng-if=\"$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <div class=\"form-control-plaintext\">{{ $ctrl.value }}</div>\r\n  </salaxy-form-group>\r\n  <salaxy-form-group ng-if=\"!$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}\" require=\"$ctrl.require\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\" ng-init=\"refresher = [0]\">\r\n    <div ng-repeat=\"item in refresher\">\r\n      <salaxy-input-typeahead\r\n        label-type=\"no-label\"\r\n        ng-model=\"$ctrl.value\"\r\n        name=\"{{ $ctrl.name }}\"\r\n        disable-cache=\"true\"\r\n        placeholder=\"{{ $ctrl.placeholder }}\"\r\n        get-options=\"$ctrl.queryAccountingTargets($viewValue)\"\r\n        input-formatter=\"$ctrl.queryAccountingTargetDisplayName($model, refresher)\">\r\n      </salaxy-input-typeahead>\r\n    </div>\r\n  </salaxy-form-group>\r\n</ng-form>`);\n\n $templateCache.put(\"salaxy-components/form-controls/InputBoolean.html\",`<salaxy-form-group ng-if=\"$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n  <div class=\"form-control-plaintext\">\r\n    <span ng-if=\"$ctrl.value==true\">{{$ctrl.labelTrue || 'SALAXY.UI_Terms.yes' | sxyTranslate}} </span>\r\n    <span ng-if=\"$ctrl.value==false && $ctrl.labelType != 'no-label'\">{{$ctrl.labelFalse || 'SALAXY.UI_Terms.no' | sxyTranslate}} </span>\r\n  </div>\r\n</salaxy-form-group>\r\n<ng-form name=\"{{$ctrl.name}}Form\" ng-if=\"!$ctrl.getReadOnly()\">\r\n  <salaxy-form-group ng-if=\"$ctrl.inputMode == 'openClose' &&  !$ctrl.isOpen && $ctrl.type != 'switch'\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <div class=\"form-control-plaintext\">\r\n      <span ng-if=\"$ctrl.value==true\">{{$ctrl.labelTrue || 'SALAXY.UI_Terms.yes' | sxyTranslate}} </span>\r\n      <span ng-if=\"$ctrl.value==false\">{{$ctrl.labelFalse || 'SALAXY.UI_Terms.no' | sxyTranslate}} </span>\r\n      <span class=\"float-end btn-padding-right\">\r\n          <i ng-click=\"$ctrl.isOpen = !$ctrl.isOpen\" class=\"bi bi-pencil-fill clickable\"></i>\r\n      </span>\r\n    </div>\r\n  </salaxy-form-group>\r\n  <salaxy-form-group ng-if=\"($ctrl.type == 'radio' || !$ctrl.type) && (!$ctrl.inputMode || ($ctrl.inputMode == 'openClose' && $ctrl.isOpen))\" name=\"{{$ctrl.name}}\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\" require=\"$ctrl.require\" class=\"salaxy-component salaxy-input-boolean boolean-radio\">\r\n    <div ng-class=\"{'input-group': $ctrl.inputMode == 'openClose'}\">\r\n      <div class=\"radio form-check d-flex\" ng-class=\"$ctrl.horizontal ? 'form-check-inline' : null\">\r\n        <input class=\"form-check-input me-2 mt-0.5\" type=\"radio\" ng-disabled=\"$ctrl.getDisabled()\" name=\"{{$ctrl.name}}Radio\" id=\"{{$ctrl.name}}True\" ng-change=\"$ctrl.onChange()\" ng-model=\"$ctrl.value\" value=\"true\" sxy-enum-as-boolean>\r\n        <label class=\"form-check-label\" for=\"{{$ctrl.name}}True\">{{$ctrl.labelTrue || 'SALAXY.UI_Terms.yes' | sxyTranslate}}</label>\r\n      </div>\r\n      <div class=\"radio form-check d-flex\" ng-class=\"$ctrl.horizontal ? 'form-check-inline' : null\">\r\n        <input class=\"form-check-input me-2 mt-0.5\" type=\"radio\" ng-disabled=\"$ctrl.getDisabled()\" name=\"{{$ctrl.name}}Radio\" id=\"{{$ctrl.name}}False\" ng-change=\"$ctrl.onChange()\" ng-model=\"$ctrl.value\" value=\"false\" sxy-enum-as-boolean>\r\n        <label class=\"form-check-label\" for=\"{{$ctrl.name}}False\">{{$ctrl.labelFalse || 'SALAXY.UI_Terms.no' | sxyTranslate}}</label>\r\n      </div>\r\n      <div class=\"input-group-btn ms-auto\" ng-if=\"$ctrl.inputMode == 'openClose'\">\r\n        <button class=\"btn btn-transparent\" ng-click=\"$ctrl.isOpen = !$ctrl.isOpen\">\r\n          <i class=\"bi bi-pencil-fill\"></i>\r\n        </button>\r\n      </div>\r\n    </div>\r\n    <div ng-show=\"!$ctrl.disableValidationErrors && ($ctrl.validationErrors.length > 0 && ({{$ctrl.name}}Form.{{$ctrl.name}}.$touched || {{$ctrl.name}}Form.$$parentForm.$submitted))\" class=\"input-errors\">\r\n      <span class=\"salaxy-validation-error text-danger small\" ng-repeat=\"validationError in $ctrl.validationErrors\" sxy-text=\"{{ validationError}}\" params=\"{ minlength: $ctrl.minlength, maxlength: $ctrl.maxlength }\"></span><br />\r\n    </div>\r\n  </salaxy-form-group>\r\n  <salaxy-form-group ng-if=\"$ctrl.type == 'checkbox' && (!$ctrl.inputMode || ($ctrl.inputMode == 'openClose' && $ctrl.isOpen))\" name=\"{{$ctrl.name}}\" label=\"{{$ctrl.label}}\" require=\"$ctrl.require\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\" class=\"salaxy-component salaxy-input-boolean boolean-checkbox\">\r\n    <div ng-class=\"{'input-group': $ctrl.inputMode == 'openClose'}\">\r\n      <div class=\"checkbox\">\r\n        <div class=\"{{$ctrl.offsetCols}} form-check d-flex align-items-start\" ng-class=\"{'col-woffset' : $ctrl.offsetCols}\">\r\n          <label class=\"form-check-label\" ng-class=\"{ 'disabled': $ctrl.getDisabled() }\">\r\n            <input class=\"form-check-input me-2 mt-0.5\" type=\"checkbox\" ng-disabled=\"$ctrl.getDisabled()\" ng-required=\"$ctrl.require\" ng-model=\"$ctrl.value\" ng-change=\"$ctrl.onChange()\" name=\"{{$ctrl.name}}\" id=\"{{$ctrl.name}}\" title=\"true\">\r\n            {{$ctrl.labelTrue || 'SALAXY.UI_Terms.yes' | sxyTranslate}}\r\n          </label>\r\n        </div>\r\n      </div>\r\n      <div class=\"input-group-btn ms-auto\" ng-if=\"$ctrl.inputMode == 'openClose'\">\r\n        <button class=\"btn btn-transparent\" ng-click=\"$ctrl.isOpen = !$ctrl.isOpen\">\r\n          <i class=\"bi bi-pencil-fill\"></i>\r\n        </button>\r\n      </div>\r\n    </div>\r\n    <div ng-show=\"!$ctrl.disableValidationErrors && ($ctrl.validationErrors.length > 0 && ({{$ctrl.name}}Form.{{$ctrl.name}}.$touched || {{$ctrl.name}}Form.$$parentForm.$submitted))\" class=\"input-errors\">\r\n      <span class=\"salaxy-validation-error text-danger small\" ng-repeat=\"validationError in $ctrl.validationErrors\" sxy-text=\"{{ validationError}}\" params=\"{ minlength: $ctrl.minlength, maxlength: $ctrl.maxlength }\"></span><br />\r\n    </div>\r\n  </salaxy-form-group>\r\n  <salaxy-form-group ng-if=\"$ctrl.type == 'switch'\" name=\"{{$ctrl.name}}\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\" require=\"$ctrl.require\" class=\"salaxy-component salaxy-input-boolean boolean-switch\">\r\n    <div class=\"form-check form-switch d-flex align-items-center\" ng-class=\"{ 'disabled': $ctrl.getDisabled() }\">\r\n      <input class=\"form-check-input ms-1 me-2\" type=\"checkbox\" id=\"{{$ctrl.name}}\" name=\"{{$ctrl.name}}\" ng-model=\"$ctrl.value\" ng-change=\"$ctrl.onChange()\" />\r\n      <label class=\"form-check-label\" for=\"{{$ctrl.name}}\" ng-if=\"$ctrl.value\">{{$ctrl.labelTrue || 'SALAXY.UI_Terms.yes' | sxyTranslate}}</label>\r\n      <label class=\"form-check-label\" for=\"{{$ctrl.name}}\" ng-if=\"!$ctrl.value || $ctrl.value == false\">{{$ctrl.labelFalse || 'SALAXY.UI_Terms.no' | sxyTranslate}}</label>\r\n    </div>\r\n    <div ng-show=\"!$ctrl.disableValidationErrors && ($ctrl.validationErrors.length > 0 && ({{$ctrl.name}}Form.{{$ctrl.name}}.$touched || {{$ctrl.name}}Form.$$parentForm.$submitted))\" class=\"input-errors\">\r\n      <span class=\"salaxy-validation-error text-danger small\" ng-repeat=\"validationError in $ctrl.validationErrors\" sxy-text=\"{{ validationError}}\" params=\"{ minlength: $ctrl.minlength, maxlength: $ctrl.maxlength }\"></span><br />\r\n    </div>\r\n  </salaxy-form-group>\r\n  <salaxy-form-group ng-if=\"$ctrl.type == 'switch-xl'\" name=\"{{$ctrl.name}}\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\" require=\"$ctrl.require\" class=\"salaxy-component salaxy-input-boolean boolean-switch\">\r\n    <div class=\"form-check form-switch fs-3\">\r\n      <input class=\"form-check-input\" type=\"checkbox\" id=\"{{$ctrl.id}}\" name=\"{{$ctrl.name}}\" ng-model=\"$ctrl.value\" ng-disabled=\"$ctrl.getDisabled()\" ng-change=\"$ctrl.onChange()\">\r\n    </div>\r\n    <span class=\"switch-text\"></span>\r\n      <span class=\"on\" ng-if=\"$ctrl.labelTrue\"> {{$ctrl.labelTrue || 'SALAXY.UI_Terms.yes' | sxyTranslate}}</span>\r\n      <span class=\"off\" ng-if=\"$ctrl.labelFalse\"> {{$ctrl.labelFalse || 'SALAXY.UI_Terms.no' | sxyTranslate}}</span>\r\n    </span>\r\n    <div ng-show=\"!$ctrl.disableValidationErrors && ($ctrl.validationErrors.length > 0 && ({{$ctrl.name}}Form.{{$ctrl.name}}.$touched || {{$ctrl.name}}Form.$$parentForm.$submitted))\" class=\"input-errors\">\r\n      <span class=\"salaxy-validation-error text-danger small\" ng-repeat=\"validationError in $ctrl.validationErrors\" sxy-text=\"{{ validationError}}\" params=\"{ minlength: $ctrl.minlength, maxlength: $ctrl.maxlength }\"></span><br />\r\n    </div>\r\n  </salaxy-form-group>\r\n  <salaxy-form-group ng-if=\"$ctrl.type=='select'\" name=\"{{$ctrl.name}}\" require=\"$ctrl.require\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\" class=\"salaxy-component salaxy-input-boolean boolean-select\">\r\n    <select ng-disabled=\"$ctrl.getDisabled()\" id=\"{{$ctrl.name}}\" name=\"{{$ctrl.name}}\" ng-change=\"$ctrl.onChange()\" ng-model=\"$ctrl.value\" class=\"form-select\" sxy-enum-as-boolean>\r\n      <option ng-if=\"$ctrl.value == null\" value=\"{{$ctrl.value}}\" selected disabled>{{ $ctrl.placeholder || 'SALAXY.UI_Terms.select' | sxyTranslate }}</option>\r\n      <option value=\"true\" title=\"{{$ctrl.labelTrue}}\">{{$ctrl.labelTrue || 'SALAXY.UI_Terms.yes' | sxyTranslate}}</option>\r\n      <option value=\"false\" title=\"{{$ctrl.labelFalse}}\">{{$ctrl.labelFalse || 'SALAXY.UI_Terms.no' | sxyTranslate}}</option>\r\n    </select>\r\n    <div ng-show=\"!$ctrl.disableValidationErrors && ($ctrl.validationErrors.length > 0 && ({{$ctrl.name}}Form.{{$ctrl.name}}.$touched || {{$ctrl.name}}Form.$$parentForm.$submitted))\" class=\"input-errors\">\r\n      <span class=\"salaxy-validation-error text-danger small\" ng-repeat=\"validationError in $ctrl.validationErrors\" sxy-text=\"{{ validationError}}\" params=\"{ minlength: $ctrl.minlength, maxlength: $ctrl.maxlength }\"></span><br />\r\n    </div>\r\n  </salaxy-form-group>\r\n</ng-form>`);\n\n $templateCache.put(\"salaxy-components/form-controls/InputCollectiveBargainAgreement.html\",`<salaxy-form-group ng-if=\"$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n  <div class=\"form-control-plaintext\">{{ $ctrl.getCbaLabel($ctrl.value) }}</div>\r\n</salaxy-form-group>\r\n<ng-form ng-if=\"!$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}Form\" class=\"salaxy-component salaxy-input-collective-bargain-agreement\">\r\n  <salaxy-form-group ng-if=\"$ctrl.inputMode == 'openClose' &&  !$ctrl.isOpen\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <div class=\"form-control-plaintext\">{{ $ctrl.getCbaLabel($ctrl.value) }}\r\n      <span class=\"pull-right btn-padding-right\">\r\n          <i ng-click=\"$ctrl.isOpen = !$ctrl.isOpen\" class=\"bi bi-pencil-fill clickable\"></i>\r\n      </span>\r\n    </div>\r\n  </salaxy-form-group>\r\n  <salaxy-form-group name=\"{{$ctrl.name}}\" require=\"$ctrl.require\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <salaxy-input-typeahead\r\n      label-type=\"no-label\"\r\n      ng-model=\"$ctrl.value\"\r\n      ng-change=\"$ctrl.onChange()\"\r\n      name=\"{{ $ctrl.name }}\"\r\n      disable-cache=\"true\"\r\n      placeholder=\"{{ $ctrl.getPlaceholder() | sxyTranslate }}\"\r\n      get-options=\"$ctrl.getCbaCodes\"\r\n      input-formatter=\"$ctrl.getCbaLabel\"\r\n      tooltip-html=\"{{$ctrl.getToolTipHtml()}}\">\r\n    </salaxy-input-typeahead>\r\n    <div ng-show=\"{{$ctrl.name}}Form.{{$ctrl.name}}.$invalid && $ctrl.validationError && ({{$ctrl.name}}Form.{{$ctrl.name}}.$touched || {{$ctrl.name}}Form.$$parentForm.$submitted)\">\r\n      {{$ctrl.validationError | sxyTranslate}}\r\n    </div>\r\n  </salaxy-form-group>\r\n</ng-form>`);\n\n $templateCache.put(\"salaxy-components/form-controls/InputDuration.html\",`<salaxy-form-group ng-if=\"$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n  <div class=\"form-control-plaintext\">{{ $ctrl.value | sxyDuration }} </div>\r\n</salaxy-form-group>\r\n<ng-form name=\"{{$ctrl.name}}Form\" class=\"salaxy-component salaxy-input-duration\" ng-if=\"!$ctrl.getReadOnly()\">\r\n  <salaxy-form-group ng-if=\"!$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}\" require=\"$ctrl.require\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <salaxy-input-number name=\"{{$ctrl.name}}Days\" ng-model=\"$ctrl.innerValue.days\" ng-change=\"$ctrl.onChange()\" label-type=\"plain\" unit=\"days\"></salaxy-input-number>\r\n    <salaxy-input-boolean type=\"select\" name=\"{{$ctrl.name}}Negative\" ng-model=\"$ctrl.innerValue.isNegative\" ng-change=\"$ctrl.onChange()\" label-true=\"SALAXY.NG1.InputDurationComponent.labelTrue\" label-false=\"SALAXY.NG1.InputDurationComponent.labelFalse\" label-type=\"plain\"></salaxy-input-boolean>\r\n    <div ng-show=\"!$ctrl.disableValidationErrors && ($ctrl.validationErrors.length > 0 && ({{$ctrl.name}}Form.{{$ctrl.name}}.$touched || {{$ctrl.name}}Form.$$parentForm.$submitted))\" class=\"input-errors\">\r\n      <span class=\"salaxy-validation-error text-danger small\" ng-repeat=\"validationError in $ctrl.validationErrors\" sxy-text=\"{{ validationError}}\" params=\"{ minlength: $ctrl.minlength, maxlength: $ctrl.maxlength }\"></span><br/>\r\n    </div>\r\n  </salaxy-form-group>\r\n</ng-form>`);\n\n $templateCache.put(\"salaxy-components/form-controls/InputEnum.html\",`<salaxy-form-group ng-if=\"$ctrl.getReadOnly() && $ctrl.type != 'multi-select'\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n  <div class=\"form-control-plaintext\">{{ $ctrl.getEnumerationLabel($ctrl.value) }}</div>\r\n</salaxy-form-group>\r\n<salaxy-form-group ng-if=\"$ctrl.getReadOnly() && $ctrl.type == 'multi-select'\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n  <div ng-repeat=\"x in $ctrl.value\" class=\"form-control-plaintext\">{{ $ctrl.getEnumerationLabel(x)}}</div>\r\n</salaxy-form-group>\r\n<ng-form name=\"{{$ctrl.name}}Form\" ng-if=\"!$ctrl.getReadOnly()\" class=\"salaxy-input-enum\">\r\n  <salaxy-form-group ng-if=\"$ctrl.inputMode == 'openClose' && !$ctrl.isOpen\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <div class=\"form-control-plaintext\">\r\n      <span ng-if=\"$ctrl.type != 'multi-select'\">\r\n        {{ $ctrl.getEnumerationLabel($ctrl.value) }}\r\n      </span>\r\n      <span ng-if=\"$ctrl.type == 'multi-select'\" ng-repeat=\"option in $ctrl.value track by $index\">\r\n        {{ $ctrl.getEnumerationLabel(option) }}<span ng-if=\"!$last\">, </span>\r\n      </span>\r\n      <span class=\"float-end btn-padding-right\">\r\n        <i ng-click=\"$ctrl.isOpen = !$ctrl.isOpen\" class=\"bi bi-pencil-fill clickable\"></i>\r\n      </span>\r\n    </div>\r\n  </salaxy-form-group>\r\n  <salaxy-form-group ng-if=\"($ctrl.type || 'select')=='select' && (!$ctrl.inputMode || ($ctrl.inputMode == 'openClose' && $ctrl.isOpen))\" name=\"{{$ctrl.name}}\" require=\"$ctrl.require\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <div ng-class=\"{'input-group': $ctrl.inputMode == 'openClose'}\">\r\n      <select ng-disabled=\"$ctrl.getDisabled()\" id=\"{{$ctrl.name}}\" name=\"{{$ctrl.name}}\" ng-change=\"$ctrl.setStoredValue($ctrl.name, $ctrl.value);$ctrl.onChange()\" ng-model=\"$ctrl.value\" class=\"form-select\" ng-required=\"$ctrl.require\" sxy-exclude-unknowns=\"$ctrl.require ? $ctrl.invalidEnums : ''\">\r\n        <option ng-if=\"$ctrl.showPlaceholder\" value=\"{{$ctrl.value}}\" disabled selected>{{ $ctrl.placeholder || 'SALAXY.UI_Terms.select' | sxyTranslate }}</option>\r\n        <option ng-repeat=\"x in $ctrl.getEnumerations()\" value=\"{{x.value}}\" title=\"{{x.title}}\">{{$ctrl.formatLabel(x)}}</option>\r\n      </select>\r\n      <div class=\"input-group-btn ms-auto\" ng-if=\"$ctrl.inputMode == 'openClose'\">\r\n        <button class=\"btn btn-transparent\" ng-click=\"$ctrl.isOpen = !$ctrl.isOpen\">\r\n          <i class=\"bi bi-pencil-fill\"></i>\r\n        </button>\r\n      </div>\r\n    </div>\r\n  </salaxy-form-group>\r\n  <salaxy-form-group ng-if=\"$ctrl.type=='radio'\" name=\"{{$ctrl.name}}\" require=\"$ctrl.require\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\" class=\"enum-radio\">\r\n    <div class=\"radio form-check d-flex\" ng-repeat=\"x in $ctrl.getEnumerations()\">\r\n      <input class=\"form-check-input me-2 mt-0.5\" ng-disabled=\"$ctrl.getDisabled()\" ng-required=\"$ctrl.require\" type=\"radio\" ng-model=\"$ctrl.value\" ng-change=\"$ctrl.onChange()\" name=\"{{$ctrl.label}}\" id=\"{{x.value}}\" value=\"{{x.value}}\" title=\"{{x.title}}\">\r\n      <label class=\"form-check-label radio-label\" for=\"{{x.value}}\">{{$ctrl.formatLabel(x)}}</label>\r\n    </div>\r\n  </salaxy-form-group>\r\n  <salaxy-form-group ng-if=\"$ctrl.type == 'multi-select' && (!$ctrl.inputMode || ($ctrl.inputMode == 'openClose' && $ctrl.isOpen))\" name=\"{{$ctrl.name}}\" require=\"$ctrl.require\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <select ng-disabled=\"$ctrl.getDisabled()\" id=\"{{$ctrl.name}}\" name=\"{{$ctrl.name}}\" multiple ng-change=\"$ctrl.onChange()\" ng-model=\"$ctrl.value\" class=\"form-select\">\r\n      <option ng-repeat=\"x in $ctrl.getEnumerations()\" value=\"{{x.value}}\" title=\"{{x.title}}\">{{$ctrl.formatLabel(x)}}</option>\r\n    </select>\r\n    <div class=\"input-group-btn ms-auto\" ng-if=\"$ctrl.inputMode == 'openClose'\">\r\n      <button class=\"btn btn-transparent\" ng-click=\"$ctrl.isOpen = !$ctrl.isOpen\">\r\n        <i class=\"bi bi-pencil-fill\"></i>\r\n      </button>\r\n    </div>\r\n  </salaxy-form-group>\r\n  <salaxy-form-group ng-if=\"$ctrl.type=='dropdown'\" name=\"{{$ctrl.name}}\" require=\"$ctrl.require\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <div class=\"dropdown\" role=\"group\">\r\n      <button id=\"{{$ctrl.name}}\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\" aria-haspopup=\"true\" aria-expanded=\"false\" ng-disabled=\"$ctrl.getDisabled()\">\r\n        {{ $ctrl.getEnumerationLabel($ctrl.value) || $ctrl.placeholder || 'SALAXY.UI_Terms.select' | sxyTranslate }}\r\n      </button>\r\n      <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"{{$ctrl.name}}\">\r\n        <li><a href=\"\" ng-click=\"$ctrl.value=x.value;$ctrl.setStoredValue($ctrl.name, $ctrl.value);$ctrl.onChange()\" ng-repeat=\"x in $ctrl.getEnumerations()\" class=\"dropdown-item\">{{$ctrl.formatLabel(x)}}</a></li>\r\n      </ul>\r\n    </div>\r\n  </salaxy-form-group>\r\n</ng-form>`);\n\n $templateCache.put(\"salaxy-components/form-controls/InputEnumTypeaheadMatch.html\",`<a ng-if=\"match.model.ui.avatar\" class=\"clickable salaxy-component salaxy-worker-item\" style=\"padding: 10px 10px 5px 10px;\">\r\n  <salaxy-avatar style=\"font-size: 30px; vertical-align: middle; margin-right: 10px;\" avatar=\"match.model.ui.avatar\"></salaxy-avatar>\r\n  <b class=\"salaxy-highlight\" ng-bind-html=\"match.label | uibTypeaheadHighlight:query\"></b><br />\r\n</a>\r\n<a ng-if=\"!match.model.ui.avatar\" href\r\n   tabindex=\"-1\"\r\n   ng-bind-html=\"match.label | uibTypeaheadHighlight:query\"\r\n   ng-attr-title=\"{{match.model.title}}\">\r\n</a>`);\n\n $templateCache.put(\"salaxy-components/form-controls/InputHolidayMultipliers.html\",`<salaxy-form-group ng-if=\"$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n  <div class=\"salaxy-read-only-value\">\r\n    <table ng-if=\"$ctrl.value\" class=\"table table-condensed table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th class=\"right\" sxy-terms=\"SALAXY.NG1.WorkerHolidaysComponent.UI.inputs.days\"></th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.inputs.multiplier\"></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"(key, value) in $ctrl.value track by $index\">\r\n          <td class=\"right\">{{key}}</td>\r\n          <td class=\"right\">{{value}}</td>\r\n        </tr>\r\n    </table>\r\n  </div>\r\n</salaxy-form-group>\r\n\r\n<ng-form ng-if=\"!$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}Form\" class=\"salaxy-component salaxy-input form-condensed\">\r\n  <salaxy-form-group name=\"{{$ctrl.name}}\" label=\"{{$ctrl.label}}\" require=\"$ctrl.require\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <div>\r\n      <table class=\"table table-condensed table-striped\">\r\n        <thead>\r\n          <tr>\r\n            <th class=\"right\" sxy-terms=\"SALAXY.NG1.WorkerHolidaysComponent.UI.inputs.days\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.inputs.multiplier\"></th>\r\n            <th class=\"text-right\">\r\n              <button type=\"button\" class=\"btn btn-primary btn-xs\"  ng-click=\"$ctrl.createNew({})\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n            </th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr ng-repeat=\"(key, value) in $ctrl.value\">\r\n            <td ng-init=\"editableKey=key\" class=\"right\"><salaxy-input-number name=\"Key{{key}}\" label-type=\"no-label\" ng-model=\"editableKey\" ng-change=\"$ctrl.onKeyChanged(key, editableKey)\" sxy-integer></salaxy-input-number></td>\r\n            <td class=\"right\"><salaxy-input-number name=\"Value{{key}}\" label-type=\"no-label\" ng-model=\"$ctrl.value[key]\" ng-change=\"$ctrl.onChange()\"></salaxy-input-number></td>\r\n            <td class=\"text-right\">\r\n              <button type=\"button\" class=\"btn btn-danger btn-xs\" ng-click=\"$ctrl.delete(key)\">\r\n                <i class=\"bi bi-trash\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\"></i>\r\n              </button>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n    <div ng-show=\"!$ctrl.disableValidationErrors && ($ctrl.validationErrors.length > 0 && ({{$ctrl.name}}Form.{{$ctrl.name}}.$touched || {{$ctrl.name}}Form.$$parentForm.$submitted))\" class=\"input-errors\">\r\n      <span class=\"salaxy-validation-error text-danger small\" ng-repeat=\"validationError in $ctrl.validationErrors\" sxy-text=\"{{ validationError}}\" params=\"{ minlength: $ctrl.minlength, maxlength: $ctrl.maxlength }\"></span><br/>\r\n    </div>\r\n  </salaxy-form-group>\r\n</ng-form>`);\n\n $templateCache.put(\"salaxy-components/form-controls/InputIncomeType.html\",`<salaxy-form-group ng-if=\"$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n  <div class=\"form-control-plaintext\">{{ $ctrl.getRowLabel($ctrl.value) }}</div>\r\n</salaxy-form-group>\r\n<ng-form name=\"{{$ctrl.name}}Form\" ng-if=\"!$ctrl.getReadOnly()\">\r\n  <salaxy-form-group name=\"{{$ctrl.name}}\" ng-if=\"!$ctrl.type || $ctrl.type == 'typehead'\" require=\"$ctrl.require\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <salaxy-input-typeahead\r\n      ng-model=\"$ctrl.value\"\r\n      label-type=\"no-label\"\r\n      name=\"{{ $ctrl.name }}\"\r\n      get-options=\"$ctrl.getIncomeTypes\"\r\n      ng-change=\"$ctrl.onChange()\"\r\n      disable-cache=\"true\"\r\n      placeholder=\"{{ $ctrl.getPlaceholder() | sxyTranslate }}\"\r\n      ng-disabled=\"$ctrl.getDisabled()\"\r\n      input-formatter=\"$ctrl.getRowLabel\">\r\n    </salaxy-input-typeahead>\r\n    <div ng-show=\"{{$ctrl.name}}Form.{{$ctrl.name}}.$invalid && $ctrl.validationError && ({{$ctrl.name}}Form.{{$ctrl.name}}.$touched || {{$ctrl.name}}Form.$$parentForm.$submitted)\">\r\n      {{$ctrl.validationError | sxyTranslate}}\r\n    </div>\r\n  </salaxy-form-group>\r\n  <salaxy-form-group name=\"{{$ctrl.name}}\" ng-if=\"$ctrl.type == 'list'\" require=\"$ctrl.require\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <input type=\"hidden\" ng-model=\"$ctrl.value\" id=\"{{$ctrl.name}}\" name=\"{{$ctrl.name}}\" ng-required=\"$ctrl.require\">\r\n    <div class=\"list-group\">\r\n      <a ng-repeat=\"type in $ctrl.getIncomeTypes()\" ng-click=\"$ctrl.selectionClicked(type.code)\" class=\"list-group-item clickable\" ng-class=\"{ 'active': $ctrl.value == type.code, 'clickable': !$ctrl.readonly && !$ctrl.disabled }\">\r\n        <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" avatar=\"{ color: '#2b507c', initials: type.code, entityType: 'company' }\"></salaxy-avatar>\r\n        <b class=\"salaxy-highlight\" ng-bind-html=\"$ctrl.getRowLabel(type.code) | uibTypeaheadHighlight:$ctrl.searchText\"></b><br />\r\n        <small class=\"salaxy-highlight\">\r\n          <div ng-bind-html=\"type.description | uibTypeaheadHighlight:$ctrl.searchText\" style=\"white-space: nowrap; overflow: hidden; text-overflow: ellipsis;\"></div>\r\n        </small>\r\n      </a>\r\n    </div>\r\n    <div ng-show=\"{{$ctrl.name}}Form.{{$ctrl.name}}.$invalid && $ctrl.validationError && ({{$ctrl.name}}Form.{{$ctrl.name}}.$touched || {{$ctrl.name}}Form.$$parentForm.$submitted)\">\r\n      {{$ctrl.validationError | sxyTranslate}}\r\n    </div>\r\n  </salaxy-form-group>\r\n</ng-form>`);\n\n $templateCache.put(\"salaxy-components/form-controls/InputIncomeTypeItem.html\",`<a class=\"clickable\">\r\n    <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" \r\n    avatar=\"{ color: '#2b507c', initials: match.model.code, entityType: 'company' }\"></salaxy-avatar>\r\n    \r\n    <b class=\"salaxy-highlight\" ng-bind-html=\"(match.label + ' (' + match.model.code + ')') | uibTypeaheadHighlight:query\"></b><br />\r\n    <small class=\"salaxy-highlight\"><div ng-bind-html=\"match.model.description | uibTypeaheadHighlight:query\"></div></small>\r\n</a>`);\n\n $templateCache.put(\"salaxy-components/form-controls/InputMarkdown.html\",`<salaxy-form-group ng-if=\"$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-input-markdown salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n  <salaxy-markdown-viewer name=\"{{ $ctrl.name }}\" ng-model=\"$ctrl.value\"></salaxy-markdown-viewer>\r\n</salaxy-form-group>\r\n<ng-form ng-if=\"!$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}Form\" class=\"salaxy-component salaxy-input-markdown\">\r\n  <salaxy-form-group name=\"{{$ctrl.name}}\" require=\"$ctrl.require\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <salaxy-markdown-editor\r\n      ng-model=\"$ctrl.value\"\r\n      ng-change=\"$ctrl.onChange()\"\r\n      name=\"{{ $ctrl.name }}\">\r\n    </salaxy-markdown-editor>\r\n  </salaxy-form-group>\r\n</ng-form>`);\n\n $templateCache.put(\"salaxy-components/form-controls/InputNumber.html\",`<salaxy-form-group ng-if=\"$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n  <div class=\"form-control-plaintext \">{{ $ctrl.viewValue + ($ctrl.getUnitIndicator() ? \" \" + $ctrl.getUnitIndicator() : \"\") }}</div>\r\n</salaxy-form-group>\r\n<ng-form ng-if=\"!$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}Form\" class=\"salaxy-component salaxy-read-only salaxy-input-number salaxy-input\">\r\n  <salaxy-form-group ng-if=\"(!$ctrl.type || $ctrl.type == 'default') && $ctrl.inputMode == 'openClose' &&  !$ctrl.isOpen\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <div class=\"form-control-plaintext\">{{ $ctrl.value }}\r\n      <span class=\"float-end btn-padding-right\">\r\n          <i ng-click=\"$ctrl.isOpen = !$ctrl.isOpen\" class=\"bi bi-pencil-fill clickable\"></i>\r\n      </span>\r\n    </div>\r\n  </salaxy-form-group>\r\n\r\n  <salaxy-form-group ng-if=\"(!$ctrl.type || $ctrl.type == 'default') && !$ctrl.inputMode || ($ctrl.inputMode == 'openClose' && $ctrl.isOpen)\" name=\"{{$ctrl.name}}\" require=\"$ctrl.require\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <div ng-if=\"$ctrl.getUnitIndicator()\" class=\"input-group\">\r\n      <div ng-if=\"!$ctrl.units\" class=\"input-group-text\">{{ $ctrl.getUnitIndicator() }}</div>\r\n      <div ng-if=\"$ctrl.units\" class=\"input-group-btn dropdown\">\r\n        <button id=\"units\" type=\"button\" class=\"btn btn-secondary dropdown-toggle\" data-bs-toggle=\"dropdown\">\r\n          {{ $ctrl.getUnitIndicator() }}\r\n        </button>\r\n        <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"units\">\r\n          <li ng-repeat=\"unit in $ctrl.units\" role=\"menuitem\">\r\n            <a href=\"\" ng-click=\"$ctrl.changeUnit(unit)\" class=\"dropdown-item\">{{$ctrl.getUnitIndicator(unit)}}</a>\r\n          </li>\r\n        </ul>\r\n      </div>\r\n      <input type=\"text\" class=\"form-control text-end\" autocomplete=\"off\" id=\"{{$ctrl.name}}\" name=\"{{$ctrl.name}}\" placeholder=\"{{ $ctrl.getPlaceholder() | sxyTranslate}}\" ng-model=\"$ctrl.viewValue\" ng-model-options=\"{allowInvalid: true, updateOn: 'blur' }\"\r\n        ng-required=\"$ctrl.require\" ng-readonly=\"$ctrl.readonly\" ng-disabled=\"$ctrl.getDisabled()\" sxy-min=\"$ctrl.minimum\" sxy-max=\"$ctrl.maximum\" />\r\n      <div ng-if=\"$ctrl.getToolTipHtml() || $ctrl.inputMode == 'openClose'\" class=\"input-group-btn\">\r\n        <a ng-if=\"$ctrl.getToolTipHtml()\" tabindex=\"0\" type=\"button\" class=\"btn btn-default\" data-bs-toggle=\"popover\" data-bs-container=\"body\" aria-label=\"Info\" data-bs-html=\"true\" data-bs-title=\"'Info'\" data-bs-content=\"$ctrl.getToolTipHtml()\" data-bs-placement=\"'{{$ctrl.tooltipPlacement}}'\" sxy-bs5-popover>\r\n          <span class=\"bi bi-question-circle-fill\"></span>\r\n        </a>\r\n        <button ng-if=\"$ctrl.inputMode == 'openClose'\" class=\"btn btn-transparent\" ng-click=\"$ctrl.isOpen = !$ctrl.isOpen\">\r\n          <i class=\"bi bi-pencil-fill\"></i>\r\n        </button>\r\n        \r\n      </div>\r\n    </div>\r\n    <div ng-if=\"!$ctrl.getUnitIndicator() && !$ctrl.getToolTipHtml()\" ng-class=\"{'input-group': $ctrl.inputMode == 'openClose'}\">\r\n\r\n      <input type=\"text\" class=\"form-control text-end\" autocomplete=\"off\" id=\"{{$ctrl.name}}\" name=\"{{$ctrl.name}}\" placeholder=\"{{ $ctrl.getPlaceholder() | sxyTranslate}}\" ng-model=\"$ctrl.viewValue\" ng-model-options=\"{allowInvalid: true, updateOn: 'blur'}\"\r\n        ng-required=\"$ctrl.require\" ng-readonly=\"$ctrl.readonly\" ng-disabled=\"$ctrl.getDisabled()\" sxy-min=\"$ctrl.minimum\" sxy-max=\"$ctrl.maximum\" />\r\n      <div class=\"input-group-btn\" ng-if=\"$ctrl.inputMode == 'openClose'\">\r\n\r\n        <button class=\"btn btn-transparent float-end\" ng-click=\"$ctrl.isOpen = !$ctrl.isOpen\">\r\n          <i class=\"bi bi-pencil-fill\"></i>\r\n        </button>\r\n      </div>\r\n    </div>\r\n    <div ng-if=\"!$ctrl.getUnitIndicator() && $ctrl.getToolTipHtml()\" class=\"input-group\">\r\n\r\n      <input type=\"text\" class=\"form-control text-end\" autocomplete=\"off\" id=\"{{$ctrl.name}}\" name=\"{{$ctrl.name}}\" placeholder=\"{{ $ctrl.getPlaceholder() | sxyTranslate}}\" ng-model=\"$ctrl.viewValue\" ng-model-options=\"{allowInvalid: true, updateOn: 'blur'}\"\r\n        ng-required=\"$ctrl.require\" ng-readonly=\"$ctrl.readonly\" ng-disabled=\"$ctrl.getDisabled()\" sxy-min=\"$ctrl.minimum\" sxy-max=\"$ctrl.maximum\" sxy-multiple-of=\"$ctrl.multipleOf\" />\r\n\r\n      <div class=\"input-group-btn\">\r\n        <button type=\"button\" class=\"btn btn-default\" data-bs-container=\"body\" aria-label=\"Info\" data-bs-toggle=\"popover\" data-bs-html=\"true\" data-bs-title=\"'Info'\" data-bs-content=\"$ctrl.getToolTipHtml()\" data-bs-placement=\"'{{$ctrl.tooltipPlacement}}'\" sxy-bs5-popover>\r\n          <span class=\"bi bi-question-circle-fill\"></span>\r\n        </button>\r\n        <button ng-if=\"$ctrl.inputMode == 'openClose'\" class=\"btn btn-transparent\" ng-click=\"$ctrl.isOpen = !$ctrl.isOpen\">\r\n          <i class=\"bi bi-pencil-fill\"></i> \r\n        </button>\r\n      </div>\r\n    </div>\r\n    <div ng-show=\"$ctrl.validationErrors.length > 0 && ({{$ctrl.name}}Form.{{$ctrl.name}}.$touched || {{$ctrl.name}}Form.$$parentForm.$submitted)\" class=\"input-errors\">\r\n      <span class=\"salaxy-validation-error text-danger small\" ng-repeat=\"validationError in $ctrl.validationErrors\" sxy-text=\"{{ validationError}}\" params=\"{ minlength: $ctrl.minlength, maxlength: $ctrl.maxlength }\"></span><br/>\r\n    </div>\r\n  </salaxy-form-group>\r\n  <salaxy-form-group ng-if=\"$ctrl.type == 'slider'\" name=\"{{$ctrl.name}}\" require=\"$ctrl.require\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n     <input type=\"range\" class=\"form-control text-end\" id=\"{{$ctrl.name}}\" name=\"{{$ctrl.name}}\" min=\"{{$ctrl.minimum}}\" max=\"{{$ctrl.maximum}}\" step=\"{{$ctrl.sliderStep}}\" ng-model=\"$ctrl.value\" ng-change=\"$ctrl.onChange()\"/>\r\n  </salaxy-form-group>\r\n</ng-form>`);\n\n $templateCache.put(\"salaxy-components/form-controls/InputOccupationType.html\",`<salaxy-form-group ng-if=\"$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n  <div class=\"form-control-plaintext\">{{ $ctrl.getOccupationLabel($ctrl.value) }}</div>\r\n</salaxy-form-group>\r\n<ng-form ng-if=\"!$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}Form\" class=\"salaxy-component salaxy-input-occupation-type\">\r\n  <salaxy-form-group name=\"{{$ctrl.name}}\" require=\"$ctrl.require\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <salaxy-input-typeahead\r\n      label-type=\"no-label\"\r\n      ng-model=\"$ctrl.value\"\r\n      ng-change=\"$ctrl.onChange()\"\r\n      name=\"{{ $ctrl.name }}\"\r\n      disable-cache=\"true\"\r\n      placeholder=\"{{ $ctrl.getPlaceholder() | sxyTranslate }}\"\r\n      get-options=\"$ctrl.getOccupations\"\r\n      input-formatter=\"$ctrl.getOccupationLabel\">\r\n    </salaxy-input-typeahead>\r\n    <div ng-show=\"{{$ctrl.name}}Form.{{$ctrl.name}}.$invalid && $ctrl.validationError && ({{$ctrl.name}}Form.{{$ctrl.name}}.$touched || {{$ctrl.name}}Form.$$parentForm.$submitted)\">\r\n      {{$ctrl.validationError | sxyTranslate}}\r\n    </div>\r\n  </salaxy-form-group>\r\n</ng-form>`);\n\n $templateCache.put(\"salaxy-components/form-controls/InputPayStatsRowType.html\",`<salaxy-form-group ng-if=\"$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n  <div class=\"salaxy-read-only-value\">\r\n    <span class=\"badge bg-default\" ng-if=\"!$ctrl.isExclusive\">{{ $ctrl.text }}</span>\r\n    <span class=\"badge bg-danger\" ng-if=\"$ctrl.isExclusive\"><s>{{ $ctrl.text }}</s></span>\r\n  </div>\r\n</salaxy-form-group>\r\n\r\n<ng-form ng-if=\"!$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}Form\" class=\"salaxy-component salaxy-input\">\r\n  <salaxy-form-group name=\"{{$ctrl.name}}\" label=\"{{$ctrl.label}}\" require=\"$ctrl.require\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <div class=\"clickable\" ng-click=\"$ctrl.edit()\">\r\n      <span class=\"badge bg-default\" ng-if=\"!$ctrl.isExclusive\">{{ $ctrl.text || ('SALAXY.UI_Terms.new' | sxyTranslate) }}</span> \r\n      <span class=\"badge bg-danger\" ng-if=\"$ctrl.isExclusive\"><s>{{ $ctrl.text || ('SALAXY.UI_Terms.new' | sxyTranslate)}}</s></span>\r\n    </div>\r\n    <div ng-show=\"!$ctrl.disableValidationErrors && ($ctrl.validationErrors.length > 0 && ({{$ctrl.name}}Form.{{$ctrl.name}}.$touched || {{$ctrl.name}}Form.$$parentForm.$submitted))\" class=\"input-errors\">\r\n      <span class=\"salaxy-validation-error text-danger small\" ng-repeat=\"validationError in $ctrl.validationErrors\" sxy-text=\"{{ validationError}}\" params=\"{ minlength: $ctrl.minlength, maxlength: $ctrl.maxlength }\"></span><br/>\r\n    </div>\r\n  </salaxy-form-group>\r\n</ng-form>`);\n\n $templateCache.put(\"salaxy-components/form-controls/InputProfileItem.html\",`<a class=\"clickable salaxy-component salaxy-avatar-item\">\r\n  <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" \r\n  avatar=\"match.model\"></salaxy-avatar>\r\n  <b class=\"salaxy-highlight\" ng-bind-html=\"match.label | uibTypeaheadHighlight:query\"></b><br />\r\n  <small class=\"salaxy-highlight\"><div ng-bind-html=\"(match.model.description || '') | uibTypeaheadHighlight:query\"></div></small>\r\n</a>`);\n\n $templateCache.put(\"salaxy-components/form-controls/InputRrule.html\",`<salaxy-form-group ng-if=\"$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n  <div class=\"form-control-plaintext\">{{ $ctrl.getRRuleText($ctrl.value) }} </div>\r\n</salaxy-form-group>\r\n<ng-form name=\"{{$ctrl.name}}Form\" class=\"salaxy-component salaxy-input-duration\" ng-if=\"!$ctrl.getReadOnly()\">\r\n  <salaxy-form-group ng-if=\"!$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}\" require=\"$ctrl.require\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\" class=\"salaxy-read-only\">\r\n    <!-- TODO: Better UI -->\r\n    <div class=\"form-control-plaintext\">\r\n      <a href=\"\" ng-click=\"$ctrl.showRRule = !$ctrl.showRRule\">{{ $ctrl.getRRuleText($ctrl.value) }}</a>\r\n      <salaxy-input ng-if=\"$ctrl.showRRule\" name=\"{{$ctrl.name}}Inner\" ng-model=\"$ctrl.value\" ng-change=\"$ctrl.onChange()\" label-type=\"plain\"></salaxy-input>\r\n    </div>\r\n    <div ng-show=\"!$ctrl.disableValidationErrors && ($ctrl.validationErrors.length > 0 && ({{$ctrl.name}}Form.{{$ctrl.name}}.$touched || {{$ctrl.name}}Form.$$parentForm.$submitted))\" class=\"input-errors\">\r\n      <span class=\"salaxy-validation-error text-danger small\" ng-repeat=\"validationError in $ctrl.validationErrors\" sxy-text=\"{{ validationError}}\" params=\"{ minlength: $ctrl.minlength, maxlength: $ctrl.maxlength }\"></span><br/>\r\n    </div>\r\n  </salaxy-form-group>\r\n</ng-form>`);\n\n $templateCache.put(\"salaxy-components/form-controls/InputTime.html\",`<salaxy-form-group ng-if=\"$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n  <div class=\"form-control-plaintext\">{{ $ctrl.viewValue }}</div>\r\n</salaxy-form-group>\r\n<ng-form ng-if=\"!$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}Form\" class=\"salaxy-component salaxy-input  salaxy-input-number salaxy-input-time\">\r\n  <salaxy-form-group ng-if=\"$ctrl.type == 'minutes'\" name=\"{{$ctrl.name}}\" require=\"$ctrl.require\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <input type=\"time\" id=\"{{$ctrl.name}}\" name=\"{{$ctrl.name}}\" ng-model=\"$ctrl.viewValue\" ng-model-options=\"{allowInvalid: true, debounce: 1000}\" ng-required=\"$ctrl.require\" class=\"form-control\">\r\n  </salaxy-form-group>\r\n  <salaxy-form-group ng-if=\"$ctrl.type == 'time'\" name=\"{{$ctrl.name}}\" require=\"$ctrl.require\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <input type=\"time\" id=\"{{$ctrl.name}}\" name=\"{{$ctrl.name}}\" ng-model=\"$ctrl.viewValue\" ng-model-options=\"{allowInvalid: true, debounce: 1000}\" ng-required=\"$ctrl.require\" class=\"form-control\">\r\n  </salaxy-form-group>\r\n</ng-form>`);\n\n $templateCache.put(\"salaxy-components/form-controls/InputTypeahead.html\",`<style>\r\n  .dropdown-menu > .input-typeahead-option.keyboard-selected {\r\n    color: #fff;\r\n    background-color: #009fd8;\r\n  }\r\n  .typeahead-result-list.no-results .dropdown-item:not(.search-item) {\r\n    opacity: 0.6;\r\n    pointer-events: none;\r\n  }\r\n  .typeahead-result-list .dropdown-item.search-item:active {\r\n    background-color: #fff;\r\n  }\r\n  .form-control[readonly].input-select {\r\n    background-color: #fff;\r\n    cursor: pointer;\r\n  }\r\n  salaxy-input-typeahead.text-muted .form-control-plaintext {\r\n    color: #55585c !important;\r\n  }\r\n</style>\r\n<salaxy-form-group ng-if=\"$ctrl.getReadOnly()\" name=\"{{ $ctrl.name }}\" class=\"salaxy-component salaxy-read-only\" label=\"{{ $ctrl.label }}\" label-type=\"{{ $ctrl.labelType }}\" label-cols=\"{{ $ctrl.labelCols }}\">\r\n  <div class=\"form-control-plaintext\">{{ $ctrl.getEnumerationLabel($ctrl.value) }}</div>\r\n</salaxy-form-group>\r\n<ng-form name=\"{{$ctrl.name}}Form\" ng-if=\"!$ctrl.getReadOnly()\" class=\"salaxy-input-typeahead\">\r\n  <salaxy-form-group name=\"{{ $ctrl.name }}\" require=\"$ctrl.require\" label=\"{{ $ctrl.label }}\" label-type=\"{{ $ctrl.labelType }}\" label-cols=\"{{ $ctrl.labelCols }}\">\r\n    <div class=\"typeahead-wrapper d-flex\">\r\n      <div class=\"position-relative w-100\">\r\n        <input\r\n          type=\"text\"\r\n          readonly\r\n          name=\"search_{{ $ctrl.name }}\"\r\n          class=\"form-control input-select\"\r\n          ng-model=\"$ctrl.displayText\"\r\n          ng-focus=\"$ctrl.openResultsList()\"\r\n          get-options=\"$ctrl.getOptions\"\r\n          ng-disabled=\"$ctrl.getDisabled()\"\r\n          ng-required=\"$ctrl.require\"\r\n          placeholder=\"{{ $ctrl.placeholder }}\"\r\n        >\r\n        <ul class=\"typeahead-menu dropdown-menu typeahead-result-list d-none pt-1\">\r\n          <li class=\"dropdown-item p-2 search-item\">\r\n            <input\r\n              type=\"text\"\r\n              class=\"form-control typeahead-input\"\r\n              ng-model=\"$ctrl.searchText\"\r\n              name=\"{{ $ctrl.name }}\"\r\n              placeholder=\"{{ $ctrl.placeholder }}\"\r\n              ng-change=\"$ctrl.onInputChange()\"\r\n              ng-model-options=\"{ allowInvalid: true, debounce: 250 }\"\r\n              autocomplete=\"off\"\r\n            />\r\n          </li>\r\n          <li ng-if=\"$ctrl.allowCustomValues && $ctrl.searchText\" class=\"dropdown-item clickable px-2 input-typeahead-option d-flex align-items-center py-1\" ng-click=\"$ctrl.selectItem({ value: $ctrl.searchText, text: $ctrl.searchText }, true)\">\r\n            <div class=\"typeahead-result\">\r\n              <div class=\"salaxy-highlight\">{{ $ctrl.searchText }}</div>\r\n            </div>\r\n          </li>\r\n          <li class=\"dropdown-item clickable px-2 input-typeahead-option d-flex align-items-center\" ng-repeat=\"item in $ctrl.filteredItems\" ng-click=\"$ctrl.selectItem(item)\" ng-class=\"item.ui.isChild ? 'typeahead-child-result py-0' : 'py-1'\">\r\n            <salaxy-avatar ng-if=\"item.ui || item.ui.avatar\" class=\"salaxy-calc-row-type-avatar\" ng-class=\"item.ui.isChild ? 'invisible' : ''\" avatar=\"item.ui\"></salaxy-avatar>\r\n            <div class=\"typeahead-result\">\r\n              <i ng-if=\"item.ui.isChild\" class=\"bi bi-square-fill me-2\"></i>\r\n              <b ng-if=\"item.ui\" class=\"salaxy-highlight display-block\">{{ item.text }}</b>\r\n              <div ng-if=\"!item.ui\" class=\"salaxy-highlight\">\r\n                {{ item.text || item.value + ' (' + item.value + ')' }}\r\n              </div>\r\n              <small ng-if=\"item.title\" class=\"salaxy-highlight\">\r\n                <span ng-if=\"!item.ui.isChild\" ng-bind-html=\"item.title\" class=\"text-truncate d-block\"></span>\r\n                <span ng-if=\"item.ui.isChild\" ng-bind-html=\"item.title\" class=\"text-truncate\"></span>\r\n              </small>\r\n            </div>\r\n          </li>\r\n        </ul>\r\n        <button type=\"button\" class=\"clear btn-close\" ng-if=\"$ctrl.value && !$ctrl.getDisabled()\" ng-click=\"$ctrl.clearValue(true); $ctrl.openResultsList();\"></button>\r\n      </div>\r\n      <div class=\"input-group-btn\">\r\n        <button ng-if=\"$ctrl.getToolTipHtml()\" type=\"button\" class=\"btn btn-default\" data-bs-toggle=\"popover\" data-bs-container=\"body\" aria-label=\"Info\" data-bs-html=\"true\" data-bs-title=\"'Info'\" data-bs-content=\"$ctrl.getToolTipHtml()\" sxy-bs5-popover>\r\n          <span class=\"bi bi-question-circle-fill\"></span>\r\n        </button>\r\n      </div>\r\n    </div>\r\n  </salaxy-form-group>\r\n</ng-form>`);\n\n $templateCache.put(\"salaxy-components/form-controls/InputWorkerItem.html\",`<a class=\"clickable salaxy-component salaxy-worker-item\">\r\n    <salaxy-avatar class=\"salaxy-calc-row-type-avatar pull-left\" \r\n    avatar=\"match.model\"></salaxy-avatar>\r\n    <b class=\"salaxy-highlight\" ng-bind-html=\"match.label + ' (' + match.model.displayId + ')' | uibTypeaheadHighlight:query\"></b><br />\r\n    <small class=\"salaxy-highlight\"><div ng-bind-html=\"match.model.description | uibTypeaheadHighlight:query\"></div></small>\r\n</a>`);\n\n $templateCache.put(\"salaxy-components/form-controls/MarkdownEditor.html\",`<div id=\"editor\"></div>\r\n`);\n\n $templateCache.put(\"salaxy-components/form-controls/MarkdownViewer.html\",`<div id=\"viewer\"></div>`);\n\n $templateCache.put(\"salaxy-components/form-controls/Textarea.html\",`<salaxy-form-group ng-if=\"$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n  <div class=\"form-control-plaintext\">{{ $ctrl.value }}</div>\r\n</salaxy-form-group>\r\n<ng-form ng-if=\"!$ctrl.getReadOnly()\" name=\"{{$ctrl.name}}Form\" class=\"salaxy-component salaxy-textarea\">\r\n  <salaxy-form-group ng-if=\"$ctrl.inputMode == 'openClose' &&  !$ctrl.isOpen\" name=\"{{$ctrl.name}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <div class=\"\">\r\n      <span class=\"form-control-plaintext\" style=\"max-width:90%; display:inline-block;\">{{ $ctrl.value }}</span>\r\n      <span class=\"float-end btn-padding-right\" style=\"padding-top:7px;\">\r\n        <i ng-click=\"$ctrl.isOpen = !$ctrl.isOpen\" class=\"bi bi-pencil-fill clickable\"></i>\r\n      </span>\r\n    </div>\r\n\r\n  </salaxy-form-group>\r\n  <salaxy-form-group ng-if=\"!$ctrl.inputMode || ($ctrl.inputMode == 'openClose' && $ctrl.isOpen)\" name=\"{{$ctrl.name}}\" label=\"{{$ctrl.label}}\" require=\"$ctrl.require\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <div ng-if=\"$ctrl.getToolTipHtml()\" class=\"input-group\">\r\n      <textarea class=\"form-control\" autocomplete=\"off\" id=\"{{$ctrl.name}}\" name=\"{{$ctrl.name}}\" placeholder=\"{{ $ctrl.getPlaceholder() | sxyTranslate }}\" ng-model=\"$ctrl.value\" ng-model-options=\"{allowInvalid: true, debounce: 250, updateOn: 'default' }\" ng-change=\"$ctrl.onChange()\"\r\n        ng-pattern=\"$ctrl.pattern\" ng-required=\"$ctrl.require\" ng-readonly=\"$ctrl.readonly\" ng-disabled=\"$ctrl.getDisabled()\" ng-minlength=\"$ctrl.minlength\" ng-maxlength=\"$ctrl.maxlength\" maxlength=\"{{$ctrl.maxlength}}\" rows=\"{{ $ctrl.rows || 3 }}\"></textarea>\r\n      <div class=\"input-group-btn\">\r\n        <button type=\"button\" class=\"btn btn-default\" data-bs-container=\"body\" aria-label=\"Info\" data-bs-toggle=\"popover\" data-bs-html=\"true\" data-bs-title=\"'Info'\" data-bs-content=\"$ctrl.getToolTipHtml()\" data-bs-placement=\"'{{$ctrl.tooltipPlacement}}'\" sxy-bs5-popover>\r\n          <span class=\"bi bi-question-circle-fill\"></span>\r\n        </button>\r\n        <button ng-if=\"$ctrl.inputMode == 'openClose'\" class=\"btn btn-transparent\" ng-click=\"$ctrl.isOpen = !$ctrl.isOpen\">\r\n          <i class=\"bi bi-pencil-fill\"></i>\r\n        </button>\r\n      </div>\r\n    </div>\r\n    <div ng-class=\"{'input-group': $ctrl.inputMode == 'openClose'}\">\r\n      <textarea ng-if=\"!$ctrl.getToolTipHtml()\" class=\"form-control\" autocomplete=\"off\" id=\"{{$ctrl.name}}\" name=\"{{$ctrl.name}}\" placeholder=\"{{ $ctrl.getPlaceholder() | sxyTranslate }}\" ng-model=\"$ctrl.value\" ng-model-options=\"{allowInvalid: true, debounce: 250, updateOn: 'default' }\"\r\n        ng-change=\"$ctrl.onChange()\" ng-pattern=\"$ctrl.pattern\" ng-required=\"$ctrl.require\" ng-readonly=\"$ctrl.readonly\" ng-disabled=\"$ctrl.getDisabled()\" ng-minlength=\"$ctrl.minlength\" ng-maxlength=\"$ctrl.maxlength\" maxlength=\"{{$ctrl.maxlength}}\" rows=\"{{ $ctrl.rows || 3 }}\"></textarea>\r\n      <div class=\"input-group-btn\" ng-if=\"$ctrl.inputMode == 'openClose'\">\r\n        <button class=\"btn btn-transparent float-end\" ng-click=\"$ctrl.isOpen = !$ctrl.isOpen\">\r\n          <i class=\"bi bi-pencil-fill\"></i>\r\n        </button>\r\n      </div>\r\n    </div>\r\n    <div ng-show=\"!$ctrl.disableValidationErrors && ($ctrl.validationErrors.length > 0 && ({{$ctrl.name}}Form.{{$ctrl.name}}.$touched || {{$ctrl.name}}Form.$$parentForm.$submitted))\" class=\"input-errors\">\r\n      <span class=\"salaxy-validation-error text-danger small\" ng-repeat=\"validationError in $ctrl.validationErrors\" sxy-text=\"{{ validationError}}\" params=\"{ minlength: $ctrl.minlength, maxlength: $ctrl.maxlength }\"></span><br/>\r\n    </div>\r\n  </salaxy-form-group>\r\n</ng-form>`);\n\n $templateCache.put(\"salaxy-components/form-controls/ToggleButtons.html\",`<div class=\"salaxy-component salaxy-toggle-buttons btn-group\" role=\"group\" \r\n     ng-class=\"{\r\n         'd-block': $ctrl.type === 'block',\r\n         'row': $ctrl.type === 'row',\r\n         'd-inline-block': $ctrl.type === 'inline'\r\n     }\">\r\n  <div ng-repeat=\"item in $ctrl.options track by $index\" index=\"$index\" class=\"toggle-button-wrapper\" ng-if=\"!item.hidden\"\r\n       ng-class=\"{\r\n           'd-block': $ctrl.type === 'block',\r\n           'col-2': $ctrl.type === 'row',\r\n           'd-inline-block': $ctrl.type === 'inline'\r\n       }\">\r\n    <input type=\"radio\" class=\"btn-check\" name=\"btn-toggle\" id=\"btn-toggle-{{ item.value }}\" autocomplete=\"off\" ng-model=\"$ctrl.model.$viewValue\" ng-value=\"item.value\" ng-disabled=\"item.disabled\">\r\n    <label class=\"btn btn-sm btn-outline-primary toggle-button\" for=\"btn-toggle-{{ item.value }}\" ng-click=\"$ctrl.onClick(item.value)\" \r\n           ng-class=\"{\r\n               'btn-primary': $ctrl.model.$viewValue == item.value,\r\n               'btn-default': $ctrl.model.$viewValue != item.value,\r\n               'btn-block': $ctrl.type === 'block',\r\n               'd-inline-block': $ctrl.type === 'inline',\r\n               'flex-fill': $ctrl.type === 'row'\r\n           }\">\r\n      <img ng-if=\"item.imgSrc\" class=\"toggle-button-image me-2\" ng-src=\"{{ item.imgSrc }}\"/>\r\n      <span class=\"toggle-button-label\">{{ item.label | sxyTranslate }}</span>\r\n    </label>\r\n  </div>\r\n</div>\r\n`);\n\n $templateCache.put(\"salaxy-components/form-controls/ValidationSummary.html\",`<div ng-if=\"!$ctrl.hasValidation\" ng-bind-html=\"$ctrl.loadingHtml\"></div>\r\n<div ng-if=\"$ctrl.hasValidation\" class=\"salaxy-component salaxy-validation-summary\">\r\n  <ng-transclude ng-if=\"$ctrl.isValid\"></ng-transclude>\r\n  <div ng-if=\"$ctrl.layout != 'minimal'\">\r\n    <div ng-if=\"!$ctrl.isValid && !$ctrl.hasWarningsOnly\" class=\"alert alert-danger\">\r\n      <div ng-if=\"$ctrl.hasValidationOrGeneralErrors\">\r\n        <h4 sxy-text=\"SALAXY.NG1.ValidationSummaryComponent.checkForErrors\" ps=\":\"></h4>\r\n        <ul class=\"validation-error-list\">\r\n          <li ng-repeat=\"error in $ctrl.getErrors('!required') | limitTo:3\" ng-class=\"error.type\">{{ $ctrl.getLabel(error) }}</li>\r\n        </ul>\r\n      </div>\r\n      <div ng-if=\"!$ctrl.hasAllRequiredFields\">\r\n        <h4 sxy-text=\"SALAXY.NG1.ValidationSummaryComponent.missingRequired\" ps=\":\"></h4>\r\n        <ul class=\"validation-error-list\">\r\n          <li ng-repeat=\"error in $ctrl.getErrors('required') | limitTo:3\" class=\"warning\">{{ $ctrl.getLabel(error) }}</li>\r\n        </ul>\r\n      </div>\r\n      <button class=\"btn btn-xs btn-danger float-end\" ng-click=\"$ctrl.showDetails()\" sxy-text=\"SALAXY.UI_Terms.readMore\" ps=\"...\"></button>\r\n    </div>\r\n    <div ng-if=\"$ctrl.hasWarningsOnly\" class=\"alert alert-warning\">\r\n      <h4>Varoituksia:</h4>\r\n      <ul>\r\n        <li ng-repeat=\"error in $ctrl.getErrors('warning') | limitTo:3\">{{ $ctrl.getLabel(error) }}</li>\r\n      </ul>\r\n      <button class=\"btn btn-xs btn-warning float-end\" ng-click=\"$ctrl.showDetails()\" sxy-text=\"SALAXY.UI_Terms.readMore\" ps=\"...\"></button>\r\n    </div>\r\n  </div>\r\n  <span ng-if=\"$ctrl.layout == 'minimal' && (!$ctrl.isValid || $ctrl.hasWarningsOnly)\" class=\"validation-container\">\r\n    <span ng-if=\"$ctrl.hasValidationOrGeneralErrors\"><span ng-repeat=\"error in $ctrl.getErrors('!required') | limitTo:3\" class=\"validation-error-item\" ng-class=\"error.type\">{{ $ctrl.getLabel(error) }}</span></span>\r\n  <span ng-if=\"!$ctrl.hasAllRequiredFields\"><span ng-repeat=\"error in $ctrl.getErrors('required') | limitTo:3\" class=\"validation-error-item\" ng-class=\"error.type\">{{ $ctrl.getLabel(error) }}</span></span>\r\n  <span ng-if=\"!$ctrl.hasWarningsOnly\"><span ng-repeat=\"error in $ctrl.getErrors('warning') | limitTo:3\" class=\"validation-error-item\" ng-class=\"error.type\">{{ $ctrl.getLabel(error) }}</span></span>\r\n  </span>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/form-controls/ValidationSummaryDetails.html\",`<style type=\"text/css\">\r\n  .panel-validation {\r\n    border-color: var(--salaxy-brand-danger);\r\n  }\r\n  \r\n  .panel-heading-validation {\r\n    border-color: var(--salaxy-brand-danger);\r\n    background-color: var(--salaxy-brand-danger);\r\n  }\r\n</style>\r\n<div class=\"salaxy-component salaxy-calc-details-dialog card-validation\">\r\n  <div class=\"modal-header card-header-validation\">\r\n    <h2 sxy-text=\"SALAXY.NG1.ValidationSummaryDetailsComponent.moreInfoTitle\"></h2>\r\n    <button type=\"button\" class=\"btn-close float-end\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <div ng-repeat=\"error in $ctrl.data.controller().getErrors()\" class=\"alert\" ng-class=\"error.type=='warning' ? 'alert-warning' : 'alert-danger'\" role=\"alert\">\r\n      <b>{{$ctrl.data.controller().getLabel(error)}}</b>\r\n      <br/>{{$ctrl.data.controller().getDescription(error)}}\r\n    </div>\r\n  </div>\r\n  <div class=\"modal-footer\">\r\n    <button class=\"btn btn-primary float-end\" ng-click=\"$close('ok')\">OK</button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/helpers/ActionButton.html\",`<span class=\"d-flex\" ng-switch=\"$ctrl.action\">\r\n  <a ng-switch-when=\"newCalc\" href=\"#/calc/details/new\" class=\"btn salaxy-action-button btn-new-calc btn-labeled-right\" ng-class=\"$ctrl.buttonClass\" ng-disabled=\"$ctrl.disabled\"\r\n    type=\"button\" id=\"new-calc\">\r\n    {{$ctrl.label || 'SALAXY.NG1.ActionButtonComponent.newCalculation' | sxyTranslate}}<i class=\"bi bi-plus-lg\"></i>\r\n  </a>\r\n  <span ng-switch-when=\"newRepair\" ng-controller=\"CalculationCrudController as $calculationCtrl\">\r\n    <button ng-click=\"$calculationCtrl.launchCreateRepair($ctrl.onAfterAction)\" class=\"btn salaxy-action-button btn-new-repair btn-labeled-right\" ng-class=\"$ctrl.buttonClass\"\r\n      ng-disabled=\"$ctrl.disabled\" type=\"button\" id=\"new-repair\">\r\n      {{$ctrl.label || 'SALAXY.NG1.ActionButtonComponent.newRepair' | sxyTranslate}}<i class=\"bi bi-plus-lg\"></i>\r\n    </button>\r\n  </span>\r\n  <div ng-switch-when=\"newCalcForEmployment\" class=\"btn-group btn-new-calc-for-employment dropdown\" ng-class=\"$ctrl.buttonClass\" id=\"new-calc-for-employment\">\r\n    <a class=\"btn btn-primary\" href=\"#/calc/details/{{$ctrl.options.id}}/new-for-employment\">{{$ctrl.label || 'SALAXY.NG1.ActionButtonComponent.newCalculation' | sxyTranslate}}</a>\r\n    <button type=\"button\" class=\"btn btn-primary dropdown-toggle\" data-bs-toggle=\"dropdown\" aria-haspopup=\"true\" aria-expanded=\"false\">\r\n      <span class=\"sr-only\"sxy-text=\"SALAXY.NG1.ActionButtonComponent.addCalcTypes\" ps=\"...\"></span>\r\n    </button>\r\n    <ul class=\"dropdown-menu\">\r\n      <li><a href=\"#/calc/details/{{$ctrl.options.id}}/new-for-employment\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.ActionButtonComponent.commonCalc\"></a></li>\r\n      <li><a href=\"#/calc/history/{{$ctrl.options.id}}/new-for-employment\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.ActionButtonComponent.historicalCalc\"></a></li>\r\n    </ul>\r\n  </div>\r\n  <a ng-switch-when=\"newMessage\" href=\"#/messages/details/new\" class=\"btn salaxy-action-button btn-new-message btn-labeled-right\" ng-class=\"$ctrl.buttonClass\"\r\n    ng-disabled=\"$ctrl.disabled\" type=\"button\" id=\"new-message\">\r\n    {{$ctrl.label || 'SALAXY.NG1.ActionButtonComponent.startNewMessage' | sxyTranslate}}<i class=\"bi bi-plus-lg\"></i>\r\n  </a>\r\n  <a ng-switch-when=\"newPayroll\" href=\"#/payroll/details/new\" class=\"btn salaxy-action-button btn-new-payroll btn-labeled-right\" ng-class=\"$ctrl.buttonClass\"\r\n    ng-disabled=\"$ctrl.disabled\" type=\"button\" id=\"new-payroll\">\r\n    {{$ctrl.label || 'SALAXY.NG1.ActionButtonComponent.newPayroll' | sxyTranslate}}<i class=\"bi bi-plus-lg\"></i>\r\n  </a>\r\n  <span ng-switch-when=\"newWorker\" ng-controller=\"EmploymentCrudController as $employmentCtrl\">\r\n    <button ng-click=\"$employmentCtrl.launchCreateEmploymentWizard()\" class=\"btn salaxy-action-button btn-new-worker btn-labeled-right\" ng-class=\"$ctrl.buttonClass\"\r\n      ng-disabled=\"$ctrl.disabled\" type=\"button\" id=\"new-worker\">\r\n      {{$ctrl.label || 'SALAXY.NG1.ActionButtonComponent.newWorker' | sxyTranslate}}<i class=\"bi bi-plus-lg\"></i>\r\n    </button>\r\n  </span>\r\n  <span ng-switch-when=\"newTaxcard\">\r\n    <a href=\"#/taxcards\" class=\"btn salaxy-action-button btn-new-payroll btn-labeled-right\" ng-class=\"$ctrl.buttonClass\" ng-disabled=\"$ctrl.disabled\" type=\"button\"\r\n      id=\"new-taxcard\">\r\n      {{$ctrl.label || 'SALAXY.NG1.ActionButtonComponent.sendTaxCard' | sxyTranslate}}<i class=\"bi bi-plus-lg\"></i>\r\n    </a>\r\n  </span>\r\n  <span ng-switch-default class=\"alert alert-danger\" sxy-text=\"SALAXY.NG1.ActionButtonComponent.error\"></span>\r\n</span>`);\n\n $templateCache.put(\"salaxy-components/helpers/Alert.html\",`<div class=\"salaxy-component salaxy-alert\">\r\n  <div ng-class=\"'alert alert-' + $ctrl.type\">\r\n    <div>\r\n      <table style=\"width: 100%; border-collapse:separate;\">\r\n        <!-- TODO: Switch this to position:absolute & margins or flex-grid -->\r\n        <tr>\r\n          <td class=\"icon-container hidden-xxs\" ng-if=\"$ctrl.getIcon()\">\r\n            <span class=\"icon\"><i class=\"bi {{ $ctrl.getIcon() }}\"></i></span>\r\n          </td>\r\n          <td>\r\n            <div class=\"main ps-3\">\r\n              <ng-transclude ng-transclude-slot=\"main\">\r\n                <p>{{ $ctrl.text }}</p>\r\n              </ng-transclude>\r\n            </div>\r\n          </td>\r\n          <td ng-if=\"$ctrl.hasMoreInfo && !$ctrl.forceMoreInfo\" class=\"text-end\">\r\n            <button class=\"btn btn-info btn-main\" ng-click=\"$ctrl.showMoreInfo = !$ctrl.showMoreInfo\" sxy-text=\"SALAXY.UI_Terms.learnMore\"></button>\r\n          </td>\r\n        </tr>\r\n      </table>\r\n      <div class=\"collapse\" ng-if=\"$ctrl.hasMoreInfo\" ng-class=\"{ show: ($ctrl.showMoreInfo || $ctrl.forceMoreInfo) }\">\r\n        <ng-transclude ng-transclude-slot=\"aside\"></ng-transclude>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/helpers/Avatar.html\",`<i class=\"salaxy-avatar bi\" ng-class=\"{'bi-person-fill': $ctrl.isPersonIcon, 'bi-square-fill': $ctrl.isCompanyIcon }\" ng-style=\"{ color: $ctrl.color }\">\r\n  <img ng-src=\"{{ $ctrl.avatar.url }}\" ng-show=\"$ctrl.isImage\" />\r\n  <strong ng-show=\"!$ctrl.isImage\" ng-style=\"{'text-shadow': '1px 1px 0 ' + ($ctrl.color || 'black') + ', -1px -1px 0 ' + ($ctrl.color || 'black') + ', 1px -1px 0 ' + ($ctrl.color || 'black') + ', -1px 1px 0 ' + ($ctrl.color || 'black')}\">\r\n    {{ $ctrl.initials !== '-' ? $ctrl.initials : $ctrl.avatar.iconText }}\r\n  </strong>\r\n</i>`);\n\n $templateCache.put(\"salaxy-components/helpers/Calendar.html\",`<div class=\"salaxy-component salaxy-calendar\">\r\n  <button ng-if=\"$ctrl.showExport\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.exportCalendarPdf()\">\r\n    <span class=\"d-none d-md-inline-block\" sxy-text=\"SALAXY.UI_Terms.downloadPdf\"></span>\r\n    <i class=\"bi bi-file-earmark-pdf\" aria-hidden=\"true\"></i>\r\n  </button>\r\n  <button ng-if=\"$ctrl.showExport\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.exportCalendarExcel()\">\r\n    <span class=\"d-none d-md-inline-block\" sxy-text=\"SALAXY.UI_Terms.downloadExcel\"></span>\r\n    <i class=\"bi bi-file-earmark-excel\" aria-hidden=\"true\"></i>\r\n  </button>\r\n  <div ng-if=\"$ctrl.mode == 'align-weekdays'\">\r\n    <table class=\"calendar\">\r\n      <thead>\r\n        <tr>\r\n          <th class=\"calendar-title\">\r\n            {{ $ctrl.start | date : \"yyyy\" }}\r\n            <span ng-if=\"($ctrl.start | date : 'yyyy') != ($ctrl.end | date : 'yyyy')\">- {{ $ctrl.end | date : \"yyyy\" }}</span>\r\n          </th>\r\n          <th class=\"day day-of-week-{{ day.weekday }}\" ng-repeat=\"day in $ctrl.weekdaysForMonth track by $index\">{{ day.text }}</th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"month in $ctrl.months\">\r\n          <td class=\"month-title\">{{ month.title }}</td>\r\n          <td class=\"beginning-spacer\" ng-if=\"month.firstDayDayOfWeek > 1\" colspan=\"{{ month.firstDayDayOfWeek - 1}}\"></td>\r\n          <td class=\"day day-of-week-{{ day.weekday }} day-type-{{ day.dayType }} clickable\" ng-repeat=\"day in month.days\" ng-click=\"$ctrl.dateClicked(day, $ctrl.series[0], $event)\">\r\n            <div ng-repeat=\"ev in day.periods[0]\" ng-class=\"$ctrl.getCssClass(ev)\" ng-click=\"$ctrl.eventClicked(ev, day, null, $event)\" data-bs-toggle=\"tooltip\" data-bs-title=\"'{{ ev.summary }}'\" data-bs-container=\"body\" ng-style=\"$ctrl.getEventStyle(ev, day.periods[0])\" sxy-bs5-tooltip></div>\r\n            <i ng-repeat=\"ev in day.singleDays[0]\" ng-class=\"$ctrl.getCssClass(ev)\" ng-style=\"$ctrl.getEventStyle(ev, day.singleDays[0])\" ng-click=\"$ctrl.eventClicked(ev, day, null, $event)\" data-bs-toggle=\"tooltip\" data-bs-title=\"'{{ ev.summary }}'\" data-bs-container=\"body\" sxy-bs5-tooltip></i>\r\n            <span class=\"day-number\">{{ day.day }}</span><br />\r\n          </td>\r\n          <td class=\"day end-spacer\" ng-if=\"(38 - month.firstDayDayOfWeek - month.daysInMonth) > 0\" colspan=\"{{ 38 - month.firstDayDayOfWeek - month.daysInMonth  }}\"></td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <div ng-if=\"$ctrl.mode == 'align-left'\">\r\n    <table class=\"calendar\">\r\n      <thead>\r\n        <tr>\r\n          <th class=\"calendar-title\">\r\n            {{ $ctrl.start | date : \"yyyy\" }}\r\n            <span ng-if=\"($ctrl.start | date : 'yyyy') != ($ctrl.end | date : 'yyyy')\">- {{ $ctrl.end | date : \"yyyy\" }}</span>\r\n          </th>\r\n          <th class=\"day\" ng-repeat=\"day in $ctrl.weekdaysForMonth track by $index\">{{ day.text }}</th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"month in $ctrl.months\">\r\n          <td class=\"month-title\">{{ month.title }}</td>\r\n          <td class=\"day day-of-week-{{ day.weekday }} day-type-{{ day.dayType }} clickable\" ng-repeat=\"day in month.days\" ng-click=\"$ctrl.dateClicked(day, $ctrl.series[0], $event)\">\r\n            <div ng-repeat=\"ev in day.periods[0]\" ng-class=\"$ctrl.getCssClass(ev)\"  ng-style=\"$ctrl.getEventStyle(ev, day.periods[0])\" ng-click=\"$ctrl.eventClicked(ev, day, null, $event)\" data-bs-toggle=\"tooltip\" data-bs-title=\"'{{ ev.summary }}'\" data-bs-container=\"body\" sxy-bs5-tooltip></div>\r\n            <i ng-repeat=\"ev in day.singleDays[0]\" ng-class=\"$ctrl.getCssClass(ev)\" ng-style=\"$ctrl.getEventStyle(ev, day.singleDays[0])\" ng-click=\"$ctrl.eventClicked(ev, day, null, $event)\" data-bs-toggle=\"tooltip\" data-bs-title=\"'{{ ev.summary }}'\" data-bs-container=\"body\" sxy-bs5-tooltip></i>\r\n            <span class=\"day-number\">{{ day.weekdayText }}</span><br />\r\n          </td>\r\n          <td class=\"day end-spacer\" ng-if=\"(31 - month.daysInMonth) > 0\" colspan=\"{{ 31 - month.daysInMonth }}\"></td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <div ng-if=\"$ctrl.mode == 'horizontal'\" class=\"calendar-horizontal\">\r\n    <table class=\"calendar\" style=\"width: max-content;margin-bottom: 10px;\">\r\n      <thead>\r\n        <tr>\r\n          <th class=\"calendar-title\" rowspan=\"2\">\r\n            {{ $ctrl.start | date : \"yyyy\" }}\r\n            <span ng-if=\"($ctrl.start | date : 'yyyy') != ($ctrl.end | date : 'yyyy')\">- {{ $ctrl.end | date : \"yyyy\" }}</span>\r\n          </th>\r\n          <th class=\"month-title\" ng-repeat=\"month in $ctrl.months\" colspan=\"{{ month.daysInMonth }}\">{{ month.title }} {{ month.year }}</th>\r\n        </tr>\r\n        <tr>\r\n          <th class=\"day day-of-week-{{ day.weekday }} day-type-{{ day.dayType }}\" ng-click=\"$ctrl.dateClicked(day, null, $event)\" ng-repeat=\"day in $ctrl.allDays\">\r\n            {{ day.weekdayText }}<br />\r\n            {{ day.day }}\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"series in $ctrl.series\" ng-init=\"seriesIndex = $index\">\r\n          <td class=\"series-title clickable\" ng-class=\"{ 'has-avatar': series.avatar }\" ng-click=\"$ctrl.seriesClicked(series, $event)\">\r\n            <salaxy-avatar avatar=\"series.avatar\" ng-if=\"series.avatar\"\r\n              style=\"font-size: 30px;left: 2px;position: absolute;top: 2px;\"></salaxy-avatar>\r\n            <div><strong>{{ series.title }}</strong></div>\r\n            <div>{{ series.description }}</div>\r\n          </td>\r\n          <td class=\"day day-of-week-{{ day.weekday }} day-type-{{ day.dayType }} clickable\"\r\n            ng-repeat=\"day in $ctrl.allDays\" ng-click=\"$ctrl.dateClicked(day, series, $event)\">\r\n            <div ng-repeat=\"ev in day.periods[seriesIndex]\" ng-class=\"$ctrl.getCssClass(ev)\" ng-style=\"$ctrl.getEventStyle(ev, day.periods[seriesIndex])\" ng-click=\"$ctrl.eventClicked(ev, day, series, $event)\" data-bs-toggle=\"tooltip\" title=\"{{ ev.summary }}\" data-bs-container=\"body\" sxy-bs5-tooltip></div>\r\n            <i ng-repeat=\"ev in day.singleDays[seriesIndex]\" ng-class=\"$ctrl.getCssClass(ev)\" ng-style=\"$ctrl.getEventStyle(ev, day.singleDays[seriesIndex])\" ng-click=\"$ctrl.eventClicked(ev, day, series, $event)\" data-bs-toggle=\"tooltip\" title=\"{{ ev.summary }}\" data-bs-container=\"body\" sxy-bs5-tooltip></i>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <div ng-if=\"$ctrl.mode == 'list'\">\r\n    <h3>TODO: List layout</h3>\r\n    <p>Period: {{ { start: $ctrl.start, end: $ctrl.end } | sxyDateRange }}</p>\r\n    <fieldset ng-repeat=\"month in $ctrl.monthlyList\">\r\n      <legend>{{ month.title }} / {{ month.year }}</legend>\r\n      <table class=\"table\">\r\n        <thead>\r\n          <tr>\r\n            <th>Date</th>\r\n            <th>Weekday</th>\r\n            <th>Events</th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr ng-repeat=\"day in month.days\">\r\n            <td>{{ day.day }}</td>\r\n            <td>\r\n              {{ day.weekdayText }}\r\n              <span ng-if=\"day.dayType != 'normal'\">{{ day.dayType }}</span>\r\n            </td>\r\n            <td>\r\n              <ul ng-repeat=\"eventArr in day.events\" ng-init=\"seriesIndex = $index\">\r\n                <li ng-repeat=\"period in eventArr\"><strong>{{ $ctrl.series[$index].title || $ctrl.series[$index].key }}: {{ period | sxyDateRange }}</strong> {{ period.title }}: {{ period.description }}</li>\r\n              </ul>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </fieldset>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/helpers/Chart.html\",`\r\n<div ng-if=\"$ctrl.config\" ng-init=\"$ctrl.init()\" class=\"salaxy-component salaxy-chart\" ng-class=\"$ctrl.customClass\" ng-style=\"{width: $ctrl.customWidth, height: $ctrl.customHeight}\">\r\n  <canvas class=\"chart\" ng-class=\"$ctrl.chart.config.type ==='line' ? 'chart-line' : 'chart-pie'\"></canvas>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/helpers/DataMapper.html\",`<div class=\"salaxy-component salaxy-data-mapper\">\r\n  <div ng-if=\"!$ctrl.model\" class=\"alert alert-danger\">Data mapper not found</div>\r\n  <div ng-if=\"$ctrl.model\" ng-switch=\"$ctrl.type || 'value-map'\">\r\n    <div ng-switch-when=\"value-map\">\r\n      <table class=\"table table-sm\">\r\n        <thead>\r\n          <tr>\r\n            <th ng-repeat=\"selector in $ctrl.model.map\" style=\"padding: 0;\">\r\n              <salaxy-input readonly=\"true\" label=\"header\" label-type=\"plain\" name=\"header\" ng-model=\"selector.source\"></salaxy-input>\r\n            </th>\r\n          </tr>\r\n          <tr ng-if=\"$ctrl.model\">\r\n            <th ng-repeat=\"selector in $ctrl.model.map\" style=\"padding: 0;\">\r\n              <salaxy-input-enum name=\"parserMapperSource\" label-type=\"plain\" options=\"$ctrl.model.target.allKeys\" ng-model=\"selector.target\" type=\"select\"\r\n                  ng-change=\"selector.resolve($ctrl.model.source.getSchema(), $ctrl.model.target.getSchema())\"></salaxy-input-enum>\r\n            </th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr ng-repeat=\"row in $ctrl.model.source.value\">\r\n            <td ng-repeat=\"selector in $ctrl.model.map\">{{row[selector.source]}}</td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n    <div ng-switch-when=\"debug\">\r\n      <salaxy-tab-buttons\r\n        current-tab=\"$ctrl.currentTab\"\r\n        options=\"[\r\n          { value: 'info', text: 'Basic info' },\r\n          { value: 'mapping', text: 'Mapping' },\r\n          { value: 'source', text: 'Source data' },\r\n          { value: 'target', text: 'Target data' },\r\n          { value: 'json', text: 'JSON' }\r\n        ]\"\r\n        tabs-id=\"dataMapper\">\r\n      </salaxy-tab-buttons>\r\n      <div class=\"tab-content\" id=\"tab-content-dataMapper\">\r\n        <div class=\"tab-pane\" id=\"info-tab\">\r\n          <fieldset class=\"form-horizontal\" style=\"max-width: 800px;\">\r\n            <salaxy-input name=\"title\" ng-model=\"$ctrl.model.title\" label=\"Title\"></salaxy-input>\r\n            <salaxy-input name=\"uri\" ng-model=\"$ctrl.model.uri\" label=\"Uri\"></salaxy-input>\r\n            <salaxy-input-boolean name=\"isSourceAList\" ng-model=\"$ctrl.model.isSourceAList\" label=\"Source is a list\"></salaxy-input-boolean>\r\n            <button type=\"button\" ng-click=\"$ctrl.model.doMap()\" class=\"btn btn-default\">Do map</button>\r\n          </fieldset>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"mapping-tab\">\r\n          <table class=\"table table-striped\">\r\n            <thead>\r\n              <th>{{$ctrl.model.source.name || \"Source unknown\"}} ({{$ctrl.model.source.schema.format || \"format unknown\"}})</th>\r\n              <th>Type / format</th>\r\n              <th class=\"text-center\">Mapping</th>\r\n              <th>{{$ctrl.model.target.name || \"Target unknown\"}} ({{$ctrl.model.target.schema.format || \"format unknown\"}})</th>\r\n              <th>Type / format</th>\r\n            </thead>\r\n            <tbody>\r\n              <tr ng-repeat=\"selector in $ctrl.model.map\">\r\n                <td>\r\n                  <salaxy-input-enum name=\"parserMapperSource\" label-type=\"plain\" options=\"$ctrl.model.source.allKeys\" ng-model=\"selector.source\" type=\"select\"\r\n                    ng-change=\"selector.resolve($ctrl.model.source.getSchema(), $ctrl.model.target.getSchema())\"></salaxy-input-enum>\r\n                </td>\r\n                <td ng-if=\"selector.sourceProp\">\r\n                  <span>{{ selector.sourceProp.schema.type }} / {{ selector.sourceProp.schema.format || \"-\" }}</span>\r\n                  <salaxy-json-formatter json=\"selector.sourceProp\" key=\"'...'\" type=\"dialog\"></salaxy-json-formatter>\r\n                </td>\r\n                <td ng-if=\"!selector.sourceProp\" class=\"text-danger\">Not found!</td>\r\n                <td class=\"text-center middle\">\r\n                  <i ng-if=\"selector.flatten.length\" class=\"text-primary bi bi-diagram-3-fill\" aria-hidden=\"true\"></i>\r\n                  <i ng-if=\"!selector.flatten.length && !selector.func\" class=\"bi bi-arrow-left-circle-fill\" aria-hidden=\"true\"></i>\r\n                  <i ng-if=\"!selector.flatten.length && selector.func\" class=\"bi bi-gear-fill bi-spin text-primary\" aria-hidden=\"true\"></i>\r\n                </td>\r\n                <td ng-if=\"!selector.flatten.length\">\r\n                  <salaxy-input-enum name=\"parserMapperTarget\" label-type=\"plain\" options=\"$ctrl.model.target.allKeys\" ng-model=\"selector.target\" type=\"select\"\r\n                    ng-change=\"selector.resolve($ctrl.model.source.getSchema(), $ctrl.model.target.getSchema())\"></salaxy-input-enum>\r\n                </td>\r\n                <td ng-if=\"!selector.flatten.length && selector.targetProp\">\r\n                  <span>{{ selector.targetProp.schema.type }} / {{ selector.targetProp.schema.format || \"-\" }}</span>\r\n                  <salaxy-json-formatter json=\"selector.targetProp\" key=\"'...'\" type=\"dialog\"></salaxy-json-formatter>\r\n                </td>\r\n                <td ng-if=\"!selector.flatten.length && !selector.targetProp\" class=\"text-danger\">Not found!</td>\r\n                <td ng-if=\"selector.flatten.length\" colspan=\"2\">\r\n                  <table>\r\n                    <tr ng-repeat=\"flattenSelector in selector.flatten\">\r\n                      <td>\r\n                        <salaxy-input-enum name=\"parserMapperTarget\" label-type=\"plain\" options=\"$ctrl.model.target.allKeys\" ng-model=\"flattenSelector.target\" type=\"select\"\r\n                          ng-change=\"flattenSelector.resolve(flattenSelector.sourceProp.schema.items, $ctrl.model.target.getSchema())\"></salaxy-input-enum>\r\n                      </td>\r\n                      <td>\r\n                        <span>{{ flattenSelector.targetProp.schema.type }} / {{ flattenSelector.targetProp.schema.format || \"-\" }}</span>\r\n                        <salaxy-json-formatter json=\"flattenSelector.targetProp\" key=\"'...'\" type=\"dialog\"></salaxy-json-formatter>\r\n                      </td>\r\n                    </tr>\r\n                  </table>\r\n                </td>\r\n              </tr>\r\n            </tbody>\r\n          </table>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"source-tab\">\r\n          <salaxy-data-mapper model=\"$ctrl.model\" type=\"source-value\"></salaxy-data-mapper>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"target-tab\">\r\n          <salaxy-data-mapper model=\"$ctrl.model\" type=\"target-value\"></salaxy-data-mapper>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"json-tab\">\r\n          <div class=\"row\">\r\n            <div class=\"col-sm-4\">\r\n              <h3>Source</h3>\r\n              <salaxy-json-formatter json=\"$ctrl.model.source\" open=\"3\"></salaxy-json-formatter>\r\n            </div>\r\n            <div class=\"col-sm-4\">\r\n              <h3>Mapper</h3>\r\n              <salaxy-json-formatter json=\"$ctrl.model.map\" open=\"3\"></salaxy-json-formatter>\r\n            </div>\r\n            <div class=\"col-sm-4\">\r\n              <h3>Target</h3>\r\n              <salaxy-json-formatter json=\"$ctrl.model.target\" open=\"3\"></salaxy-json-formatter>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div ng-switch-when=\"source-value\">\r\n      <table class=\"table table-sm\">\r\n        <thead>\r\n          <tr>\r\n            <th sxy-text=\"SALAXY.NG1.ODataImportComponent.step3.okey\"></th>\r\n            <th ng-repeat=\"header in $ctrl.model.source.keys\">\r\n              {{header}}\r\n              (<span>{{ $ctrl.model.source.schema.properties[header].type || \"-\" }} / {{ $ctrl.model.source.schema.properties[header].format || \"-\" }}</span>\r\n              <salaxy-json-formatter json=\"$ctrl.model.source.schema.properties[header]\" key=\"'...'\" type=\"dialog\"></salaxy-json-formatter>)\r\n            </th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr ng-repeat=\"row in $ctrl.model.source.value\">\r\n            <td>\r\n              <div ng-if=\"row.validation && row.validation.errors && row.validation.errors.length\" ng-repeat=\"error in row.validation.errors\">\r\n                <button data-bs-toggle=\"popover\" data-bs-content=\"{{ error.msg }}\" data-bs-title=\"{{ error.code }}\" type=\"button\" class=\"btn btn-danger\" sxy-bs5-popover>{{ error.type }}</button><br>\r\n              </div>\r\n              \r\n              <div ng-if=\"row.validation && row.validation.isValid\">\r\n                <span class=\"text-success\" sxy-text=\"SALAXY.NG1.ODataImportComponent.step3.okey\"></span>\r\n              </div>\r\n            </td>\r\n            <td ng-repeat=\"header in $ctrl.model.source.keys\">{{row[header]}}</td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n    <div ng-switch-when=\"target-value\">\r\n      <table class=\"table table-sm\">\r\n        <thead>\r\n          <tr>\r\n            <th sxy-text=\"SALAXY.NG1.ODataImportComponent.step3.okey\"></th>\r\n            <th ng-repeat=\"header in $ctrl.model.target.keys\">\r\n              {{header}}\r\n              (<span>{{ $ctrl.model.target.schema.properties[header].type || \"-\" }} / {{ $ctrl.model.target.schema.properties[header].format || \"-\" }}</span>\r\n              <salaxy-json-formatter json=\"$ctrl.model.target.schema.properties[header]\" key=\"'...'\" type=\"dialog\"></salaxy-json-formatter>)\r\n            </th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr ng-repeat=\"row in $ctrl.model.target.value\">\r\n            <td>\r\n              <div ng-if=\"row.validation.errors.length\" ng-repeat=\"error in row.validation.errors\">\r\n                <button data-bs-toggle=\"popover\" data-bs-content=\"{{ error.msg }}\" data-bs-title=\"{{ error.code }}\" type=\"button\" class=\"btn btn-danger\" sxy-bs5-popover>{{ error.type }}</button><br>\r\n              </div>\r\n              <div ng-if=\"row.validation && row.validation.isValid\">\r\n                <span class=\"text-success\" sxy-text=\"SALAXY.NG1.ODataImportComponent.step3.okey\"></span>\r\n              </div>\r\n            </td>\r\n            <td ng-repeat=\"header in $ctrl.model.target.keys\">{{row[header]}}</td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/helpers/import/CalcImportOptions.html\",`<div class=\"salaxy-component salaxy-calc-import-options\">\r\n  <div class=\"row\">\r\n    <form class=\"form-horizontal col-sm-6\" name=\"$ctrl.optionsForm\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.CalcImport.options.title\"></legend>\r\n        <div class=\"row\">\r\n          <div class=\"col col-sm-6\">\r\n            <salaxy-input-enum options=\"{\r\n            addRows: 'SALAXY.NG1.CalcImport.options.addRows',\r\n            removeAllRows: 'SALAXY.NG1.CalcImport.options.removeAllRows',\r\n            removeImportedRows: 'SALAXY.NG1.CalcImport.options.removeImportedRows'}\" label-type=\"plain\" name=\"customOptions\" ng-model=\"$ctrl.customOptions\" type=\"radio\"\r\n              ng-change=\"$ctrl.updateOptions()\"></salaxy-input-enum>\r\n            <salaxy-input-boolean type=\"checkbox\" name=\"applyEmploymentDefaultRows\" label-type=\"plain\" label-true=\"SALAXY.NG1.CalcImport.options.applyEmploymentDefaultRows\"\r\n              ng-model=\"$ctrl.options.applyEmploymentDefaultRows\"></salaxy-input-boolean>\r\n          </div>\r\n          <div class=\"col col-sm-6\">\r\n            <salaxy-input ng-if=\"true\" require=\"$ctrl.options.rowMergeOption == 'removeImportedRows'\" ng-model=\"$ctrl.options.sourceId\" name=\"sourceId\"\r\n              label=\"SALAXY.NG1.CalcImport.options.sourceId\"></salaxy-input>\r\n          </div>\r\n        </div>\r\n      </fieldset>\r\n    </form>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/helpers/import/DataImport.html\",`<div class=\"salaxy-component salaxy-data-import\">\r\n  <div class=\"salaxy-wizard\">\r\n    <div class=\"wizard-steps\">\r\n      <div class=\"wizard-step\" ng-class=\"{'active': $ctrl.action == 'upload'}\">\r\n        <span class=\"salaxy-avatar\">\r\n          <div class=\"wizard-icons-wrapper\">\r\n            <i class=\"bi\" ng-class=\"$ctrl.action == 'upload' ? 'bi-circle-fill' : 'bi-circle'\"></i>\r\n            <i class=\"bi bi-circle-fill\"></i>\r\n          </div>\r\n          <strong class=\"number\">1</strong>\r\n        </span>\r\n        <span class=\"step-text\" sxy-text=\"SALAXY.NG1.DataImport.stepUpload.title\"></span>\r\n      </div>\r\n      <div class=\"wizard-step\" ng-class=\"{'active': $ctrl.action == 'validate'}\">\r\n        <span class=\"salaxy-avatar\">\r\n          <div class=\"wizard-icons-wrapper\">\r\n            <i class=\"bi\" ng-class=\"$ctrl.action == 'validate' ? 'bi-circle-fill' : 'bi-circle'\"></i>\r\n            <i class=\"bi bi-circle-fill\"></i>\r\n          </div>\r\n          <strong class=\"number\">2</strong>\r\n        </span>\r\n        <span class=\"step-text\" sxy-text=\"SALAXY.NG1.DataImport.stepValidate.title\"></span>\r\n      </div>\r\n      <div class=\"wizard-step\" ng-class=\"{'active': $ctrl.action == 'import'}\">\r\n        <span class=\"salaxy-avatar\">\r\n          <div class=\"wizard-icons-wrapper\">\r\n            <i class=\"bi\" ng-class=\"$ctrl.action == 'import' ? 'bi-circle-fill' : 'bi-circle'\"></i>\r\n            <i class=\"bi bi-circle-fill\"></i>\r\n          </div>\r\n          <strong class=\"number\">3</strong>\r\n        </span>\r\n        <span class=\"step-text\" sxy-text=\"SALAXY.NG1.DataImport.stepImport.title\"></span>\r\n      </div>\r\n    </div>\r\n    <div class=\"wizard-strikethrough\"></div>\r\n  </div>\r\n  <ng-include ng-if=\"$ctrl.optionsTemplate\" src=\"$ctrl.optionsTemplate\"></ng-include>\r\n  <div ng-switch=\"$ctrl.action\">\r\n    <div ng-switch-when=\"upload\">\r\n      <p sxy-text=\"SALAXY.NG1.DataImport.stepUpload.intro\"></p>\r\n      <p>\r\n        <span class=\"badge bg-primary\" ng-if=\"$ctrl.sourceData.length\">{{'SALAXY.NG1.DataImport.badgeUploadedLabel' | sxyTranslate }} {{$ctrl.sourceData.length}} {{'SALAXY.NG1.DataImport.badgeUnit' | sxyTranslate }}</span>\r\n      </p>\r\n      <div class=\"modal-footer mb-3\">\r\n        <button id=\"info\" ng-disabled=\"$ctrl.isImporting\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.help()\">\r\n          <span>{{'SALAXY.NG1.DataImport.stepUpload.buttonHelp' | sxyTranslate}} <i class=\"bi bi-info-circle\"></i></span>\r\n        </button>\r\n        <button id=\"upload\" ng-disabled=\"$ctrl.isImporting\" type=\"button\" class=\"btn btn-default\" ngf-select=\"$ctrl.upload($files)\" ngf-multiple=\"false\" ngf-max-size=\"10MB\">\r\n          <span>{{'SALAXY.NG1.DataImport.stepUpload.buttonUpload' | sxyTranslate}} <i class=\"bi bi-file-earmark-excel\"></i></span>\r\n        </button>\r\n        <button id=\"paste\" ng-disabled=\"$ctrl.isImporting\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.paste()\">\r\n          <span>{{'SALAXY.NG1.DataImport.stepUpload.buttonPaste' | sxyTranslate}} <i class=\"bi bi-clipboard\"></i></span>\r\n        </button>\r\n        <button id=\"reset\" ng-disabled=\"$ctrl.isImporting\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.reset(true)\">\r\n          {{'SALAXY.NG1.DataImport.stepUpload.buttonReset' | sxyTranslate}}\r\n        </button>\r\n        <button class=\"btn btn-primary ms-auto\" sxy-text=\"SALAXY.UI_Terms.next\" ng-click=\"$ctrl.action='validate';$ctrl.validate()\"></button>\r\n      </div>\r\n    </div>\r\n    <div ng-switch-when=\"validate\">\r\n      <p sxy-text=\"SALAXY.NG1.DataImport.stepValidate.intro\"></p>\r\n      <p>\r\n        <span ng-if=\"$ctrl.validationUndoneRows\"><span class=\"badge bg-default\">{{'SALAXY.NG1.DataImport.badgeUndoneLabel' | sxyTranslate }} {{$ctrl.validationUndoneRows}} {{'SALAXY.NG1.DataImport.badgeUnit' | sxyTranslate }}</span></span>\r\n        <span ng-if=\"$ctrl.validationErrorRows\"><span class=\"badge bg-danger\">{{'SALAXY.NG1.DataImport.badgeErrorLabel' | sxyTranslate }} {{$ctrl.validationErrorRows}} {{'SALAXY.NG1.DataImport.badgeUnit' | sxyTranslate }}</span></span>\r\n        <span ng-if=\"$ctrl.validationSuccessRows\"><span class=\"badge bg-success\">{{'SALAXY.NG1.DataImport.badgeSuccessLabel' | sxyTranslate }} {{$ctrl.validationSuccessRows}} {{'SALAXY.NG1.DataImport.badgeUnit' | sxyTranslate }}</span></span>\r\n      </p>\r\n      <div class=\"modal-footer mb-3\">\r\n        <button class=\"btn btn-default\" sxy-text=\"SALAXY.UI_Terms.previous\" ng-click=\"$ctrl.action='upload'\"></button>\r\n        <button id=\"validate\" ng-disabled=\"$ctrl.isImporting\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.validate()\">\r\n          {{'SALAXY.NG1.DataImport.stepValidate.buttonValidate' | sxyTranslate}}\r\n        </button>\r\n        <button  ng-repeat=\"validator in $ctrl.getExtraValidators()\"  ng-disabled=\"$ctrl.isImporting || $ctrl.isValidating\" type=\"button\" class=\"btn btn-default\"\r\n          ng-click=\"validator.validate()\">\r\n          {{ validator.buttonLabel }}\r\n        </button>\r\n        <button  ng-repeat=\"enricher in $ctrl.getDataEnrichers()\"  ng-disabled=\"$ctrl.isImporting\" type=\"button\" class=\"btn btn-default\"\r\n        ng-click=\"enricher.enrich()\">\r\n        {{ enricher.buttonLabel }}\r\n       </button>\r\n        <button class=\"btn btn-primary ms-auto\" sxy-text=\"SALAXY.UI_Terms.next\" ng-click=\"$ctrl.action='import'\"></button>\r\n      </div>\r\n    </div>\r\n    <div ng-switch-when=\"import\">\r\n      <p sxy-text=\"SALAXY.NG1.DataImport.stepImport.intro\"></p>\r\n      <p>\r\n      <div class=\"progress\" ng-if=\"$ctrl.importTotal\">\r\n        <div style=\"min-width: 10em;\" ng-style=\"{'width': ($ctrl.importCurrent * 100 / $ctrl.importTotal) + '%' }\" class=\"progress-bar\" role=\"progressbar\"\r\n          aria-valuenow=\"{{$ctrl.importCurrent}}\" aria-valuemin=\"0\" aria-valuemax=\"{{$ctrl.importTotal}}\">\r\n          <span><span ng-if=\"$ctrl.importCurrent != $ctrl.importTotal\"><span ng-if=\"$ctrl.isImporting\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span></span>\r\n            {{$ctrl.importCurrent}}/{{$ctrl.importTotal}}</span>\r\n        </div>\r\n      </div>\r\n      <span ng-if=\"$ctrl.importIgnoredRows\"><span class=\"badge bg-default\">{{'SALAXY.NG1.DataImport.badgeIgnoredLabel' | sxyTranslate }} {{$ctrl.importIgnoredRows}} {{'SALAXY.NG1.DataImport.badgeUnit' | sxyTranslate }}</span></span>\r\n      <span ng-if=\"$ctrl.importSuccessRows\"><span class=\"badge bg-success\">{{'SALAXY.NG1.DataImport.badgeFinishedLabel' | sxyTranslate }} {{$ctrl.importSuccessRows}} {{'SALAXY.NG1.DataImport.badgeUnit' | sxyTranslate }}</span></span>\r\n      <span ng-if=\"$ctrl.importWarningRows\"><span class=\"badge bg-warning\">{{'SALAXY.NG1.DataImport.badgeWarningLabel' | sxyTranslate }} {{$ctrl.importWarningRows}} {{'SALAXY.NG1.DataImport.badgeUnit' | sxyTranslate }}</span></span>\r\n      <span ng-if=\"$ctrl.importErrorRows\"><span class=\"badge bg-danger\">{{'SALAXY.NG1.DataImport.badgeErrorLabel' | sxyTranslate }} {{$ctrl.importErrorRows}} {{'SALAXY.NG1.DataImport.badgeUnit' | sxyTranslate }}</span></span>\r\n      </p>\r\n      <div class=\"modal-footer mb-3\">\r\n        <button class=\"btn btn-default\" sxy-text=\"SALAXY.UI_Terms.previous\" ng-click=\"$ctrl.action='validate';$ctrl.validate()\"></button>\r\n        <div class=\"ms-auto\">\r\n          <button id=\"cancel\" ng-disabled=\"!$ctrl.isImporting\" type=\"button\" class=\"btn btn-danger\" ng-click=\"$ctrl.cancel()\">\r\n            {{'SALAXY.NG1.DataImport.stepImport.buttonCancel' | sxyTranslate}}\r\n          </button>\r\n          <button id=\"import\" ng-disabled=\"$ctrl.isImporting || $ctrl.hasInvalidOptions()\" type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.import()\">\r\n            {{'SALAXY.NG1.DataImport.stepImport.buttonImport' | sxyTranslate}}\r\n          </button>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div id=\"import-table\"></div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/helpers/import/EInvoiceAddressSelect.html\",`<div class=\"modal-eInvoiceAddress-select\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.CompanyImport.enrichEInvoiceAddressesSelectionMessage\"></h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <div class=\"table-responsive\" style=\"max-height: calc(100vh - 300px)\">\r\n      <table class=\"table table-striped\">\r\n        <thead>\r\n          <tr>\r\n            <th sxy-text=\"SALAXY.NG1.EInvoiceAddressListComponent.name\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.EInvoiceAddressListComponent.receiver\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.EInvoiceAddressListComponent.intermediator\"></th>\r\n            <th class=\"right\">              \r\n            </th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr ng-repeat=\"row in $ctrl.logic.addresses\">\r\n            <td>\r\n              <span>{{row.receiverName}}</span><br>\r\n              <small>{{row.receiverOfficialId}}</small>\r\n            </td>\r\n            <td>\r\n              <span>{{row.receiver}}</span><br>\r\n            </td>\r\n            <td>\r\n              <span>{{row.intermediatorName}}</span><br>\r\n              <small>{{row.intermediator}}</small>\r\n            </td>\r\n            <td class=\"right middle\">\r\n              <button class=\"btn btn-sm btn-default\" type=\"button\"\r\n                ng-click=\"$ctrl.logic.select($ctrl.current, row, $close)\">{{ 'SALAXY.UI_Terms.select' | sxyTranslate }}\r\n              </button>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n  </div>\r\n  <div class=\"modal-footer text-end\">\r\n    <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/helpers/import/staging/ImportStaging.html\",`<div class=\"salaxy-component salaxy-import-staging\">\r\n  <div class=\"pull-right\"><small>{{ $ctrl.serverUrl }}</small></div>\r\n  <div class=\"toolbar\">\r\n    <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.reloadUi()\"><i class=\"bi bi-arrow-repeat\" aria-hidden=\"true\"></i></button>\r\n    <div style=\"display: inline-block; width: 240px; vertical-align: middle;\" ng-if=\"$ctrl.worktimeApi.payrolls && !$ctrl.payroll\">\r\n      <salaxy-input-typeahead options=\"$ctrl.worktimeApi.payrolls\" name=\"payrollId\" label-type=\"plain\"\r\n        placeholder=\"{{ 'SALAXY.NG1.ImportStagingComponent.toolbar.selectPayroll' | sxyTranslate }}\"\r\n        ng-model=\"$ctrl.payrollId\"></salaxy-input-typeahead>\r\n    </div>\r\n    <button type=\"button\" class=\"btn btn-primary\" ng-disabled=\"!$ctrl.payrollId\" ng-click=\"$ctrl.commitPayroll('payroll')\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.toolbar.commitPayroll\"></button>\r\n    <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.recalculateAllWorktimes()\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.toolbar.recalculateAll\"></button>\r\n  </div>\r\n  <ng-include src=\"'salaxy-components/helpers/import/staging/ImportStaging_list.html'\"></ng-include>\r\n  <!-- TODO: Move to a dialog -->\r\n  <ng-include src=\"'salaxy-components/helpers/import/staging/ImportStaging_test_data.html'\"></ng-include>\r\n</div>\r\n<ng-include ng-if=\"$ctrl.worktimeApi.current\" src=\"'salaxy-components/helpers/import/staging/ImportStaging_details.html'\"></ng-include>`);\n\n $templateCache.put(\"salaxy-components/helpers/import/staging/ImportStaging_details.html\",`<div class=\"salaxy-payroll-details-calc salaxy-payroll-details-dialog\"\r\n  ng-style=\"{'max-width': 'calc(100vw - 260px)','width': $ctrl.userSettings.ng1Binder('worktimeImport.calcDialogSize').val || '60%'}\"\r\n  ng-class=\"{ 'offcanvas-show': $ctrl.showOffcanvas }\">\r\n  <div class=\"modal-header bg-primary d-flex justify-content-between\">\r\n    <div ng-if=\"$ctrl.worktimeApi.current\" class=\"d-flex\">\r\n      <salaxy-avatar class=\"align-self-center ms-2 me-3\" avatar=\"$ctrl.worktimeApi.current.preview.employments[0].personalInfo.avatar\"></salaxy-avatar>\r\n      <div class=\"d-flex flex-column\">\r\n        <h3 class=\"modal-title\">{{ $ctrl.worktimeApi.current.preview.employments[0].personalInfo.avatar.displayName }}</h3>\r\n        <div>{{ $ctrl.worktimeApi.current.preview.employments[0].identity.personalId }} ({{ \"EmploymentRelationType.\" + $ctrl.worktimeApi.current.preview.employments[0].info.type |\r\n          sxyEnum }})\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div>\r\n      <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.userSettings.ng1Binder('worktimeImport.calcDialogSize').val = ($ctrl.userSettings.ng1Binder('worktimeImport.calcDialogSize').val == '100%' ? '60%' : '100%')\">\r\n        <i ng-class=\"$ctrl.userSettings.ng1Binder('worktimeImport.calcDialogSize').val == '100%' ? 'bi bi-arrows-angle-contract' : 'bi bi-arrows-angle-expand'\"></i>\r\n      </button>\r\n      <button type=\"button\" class=\"btn btn-primary\" aria-label=\"Close\" ng-click=\"$ctrl.showDetails()\"><span class=\"bi bi-x-lg\"></span></button>\r\n    </div>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <table style=\"width: 100%\">\r\n      <tr>\r\n        <td width=\"20%\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.details.payroll\"></td>\r\n        <td width=\"50%\">\r\n          <div>{{ $ctrl.worktimeApi.detailsPayroll.text || $ctrl.worktimeApi.detailsPayrollId || (\"SALAXY.NG1.ImportStagingComponent.details.noPayroll\" | sxyTranslate) }}</div>\r\n          <div ng-if=\"$ctrl.payrollId && $ctrl.payrollId != $ctrl.worktimeApi.detailsPayrollId\">\r\n            <span class=\"text-danger\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.details.notTheSameAsSelectedPayroll\"></span>\r\n            <a href=\"\" ng-click=\"$ctrl.worktimeApi.detailsPayrollId = $ctrl.payrollId\" sxy-text=\"SALAXY.UI_Terms.back\"></a>\r\n          </div>\r\n        </td>\r\n        <td width=\"30%\" rowspan=\"2\">\r\n          <salaxy-input-typeahead options=\"$ctrl.worktimeApi.payrolls\" name=\"payrollId\" label-type=\"plain\"\r\n            placeholder=\"{{ 'SALAXY.NG1.ImportStagingComponent.toolbar.selectPayroll' | sxyTranslate }}\" ng-model=\"$ctrl.worktimeApi.detailsPayrollId\"></salaxy-input-typeahead>\r\n          <div class=\"text-danger\" ng-if=\"$ctrl.worktimeApi.rowsOutsidePayrollCount\">\r\n            <small>\r\n              {{\"SALAXY.NG1.ImportStagingComponent.details.rowsOutsidePayrollCountLeadText\" | sxyTranslate}} {{ $ctrl.worktimeApi.rowsOutsidePayrollCount }} {{\"SALAXY.NG1.ImportStagingComponent.details.rowsOutsidePayrollCountEndText\" | sxyTranslate}}\r\n              <a href=\"\" ng-click=\"$ctrl.worktimeApi.detailsPayrollId = 'unknown'\" sxy-text=\"SALAXY.UI_Terms.show\"></a>\r\n            </small>\r\n          </div>\r\n        </td>\r\n      </tr>\r\n      <tr>\r\n        <td sxy-text=\"SALAXY.NG1.ImportStagingComponent.details.period\"></td>\r\n        <td>\r\n          <div>{{ $ctrl.worktimeApi.detailsPayroll.ui | sxyDateRange }} / {{ $ctrl.worktimeApi.detailsPayroll.ui.date | sxyDate }}</div>\r\n          <div>{{ $ctrl.worktimeApi.detailsPayroll.ui.calcCount }} {{\"SALAXY.NG1.ImportStagingComponent.details.leftCalculations\" | sxyTranslate}} / {{ $ctrl.worktimeApi.detailsPayroll.ui.rowCount }} {{\"SALAXY.NG1.ImportStagingComponent.details.leftRows\" | sxyTranslate}}</div>\r\n        </td>\r\n      </tr>\r\n    </table>\r\n    <salaxy-tab-buttons\r\n      current-tab=\"$ctrl.currentTab\"\r\n      options=\"[\r\n        { 'value': 'rawrows', 'text': 'SALAXY.NG1.ImportStagingComponent.details.rawRows' },\r\n        { 'value': 'processrows', 'text': 'SALAXY.NG1.ImportStagingComponent.details.editRows' },\r\n        { 'value': 'manual', 'text': 'SALAXY.NG1.ImportStagingComponent.details.manualRows' },\r\n        { 'value': 'reports', 'text': 'SALAXY.NG1.ImportStagingComponent.details.reports' },\r\n        { 'value': 'preview', 'text': 'SALAXY.NG1.ImportStagingComponent.details.preview' },\r\n        { 'value': 'salaryslips', 'text': 'SALAXY.NG1.ImportStagingComponent.details.salarySlips' },\r\n        { 'value': 'debug', 'text': 'SALAXY.NG1.ImportStagingComponent.details.debug' }\r\n      ]\"\r\n      tabs-id=\"importStagingDetails\">\r\n    </salaxy-tab-buttons>\r\n    <div class=\"tab-content\" id=\"tab-content-importStagingDetails\">\r\n      <div class=\"tab-pane\" id=\"rawrows-tab\">\r\n        <div ng-if=\"$ctrl.currentTab == 'rawrows'\">\r\n          <ng-include src=\"'salaxy-components/helpers/import/staging/ImportStaging_rawRows.html'\"></ng-include>\r\n        </div>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"manual-tab\">\r\n        <div ng-if=\"$ctrl.currentTab == 'manual'\">\r\n          <salaxy-calc-rows-2019-editor ng-if=\"$ctrl.worktimeApi.current\" rows=\"$ctrl.worktimeApi.editableRows\" mode=\"edit\"\r\n          title=\"{{'SALAXY.NG1.ImportStagingComponent.details.manuallyEditableRows' | sxyTranslate}}\"></salaxy-calc-rows-2019-editor>\r\n          <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.saveManualRows()\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n        </div>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"preview-tab\">\r\n        <div ng-if=\"$ctrl.currentTab == 'preview'\">\r\n          <div ng-if=\"!$ctrl.worktimeApi.currentCalc\">{{\"SALAXY.NG1.ImportStagingComponent.details.noPreviewCalc\" | sxyTranslate}}</div>\r\n          <div ng-if=\"$ctrl.worktimeApi.currentCalc\">\r\n            <div class=\"alert alert-warning\">\r\n              {{\"SALAXY.NG1.ImportStagingComponent.details.previewWarning\" | sxyTranslate}}\r\n              {{\"SALAXY.NG1.ImportStagingComponent.details.previewWarning2\" | sxyTranslate}}\r\n            </div>\r\n            <salaxy-tab-buttons\r\n              current-tab=\"$ctrl.currentSubTab\"\r\n              options=\"[\r\n                { 'value': 'rows', 'text': 'SALAXY.NG1.ImportStagingComponent.details.rows' },\r\n                { 'value': 'calculator', 'text': 'SALAXY.NG1.ImportStagingComponent.details.calculator' }\r\n              ]\"\r\n              tabs-id=\"importStagingDetailsPreview\">\r\n            </salaxy-tab-buttons>\r\n            <div class=\"tab-content\" id=\"tab-content-importStagingDetailsPreview\">\r\n              <div class=\"tab-pane\" id=\"rows-tab\">\r\n                <div ng-if=\"$ctrl.currentSubTab == 'rows'\">\r\n                  <salaxy-calc-rows-2019-editor parent=\"$ctrl.worktimeApi.currentCalc\" title=\"{{'SALAXY.NG1.PayrollComponent.payrollCalcs.calcRowEditor.title' | sxyTranslate}}\"\r\n                    mode=\"edit\" show-edit-buttons=\"false\" show-gross-totals=\"true\"></salaxy-calc-rows-2019-editor>\r\n                </div>\r\n              </div>\r\n              <div class=\"tab-pane\" id=\"calculator-tab\">\r\n                <div ng-if=\"$ctrl.currentSubTab == 'calculator'\">\r\n                  <salaxy-calc ng-if=\"$ctrl.worktimeApi.currentCalc\" model=\"$ctrl.worktimeApi.currentCalc\"></salaxy-calc>\r\n                </div>\r\n              </div>\r\n            </div>\r\n            <div ng-switch=\"$ctrl.previewView\">\r\n              <div ng-switch-when=\"rows\">\r\n                <salaxy-calc-rows-2019-editor parent=\"$ctrl.worktimeApi.currentCalc\" title=\"{{'SALAXY.NG1.PayrollComponent.payrollCalcs.calcRowEditor.title' | sxyTranslate}}\"\r\n                mode=\"edit\" show-edit-buttons=\"false\" show-gross-totals=\"true\"></salaxy-calc-rows-2019-editor>\r\n              </div>\r\n              <div ng-switch-when=\"calculator\">\r\n                <salaxy-calc ng-if=\"$ctrl.worktimeApi.currentCalc\" model=\"$ctrl.worktimeApi.currentCalc\"></salaxy-calc>\r\n              </div>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"salaryslips-tab\">\r\n        <div ng-if=\"$ctrl.currentTab == 'salaryslips'\">\r\n          <ng-include src=\"'salaxy-components/helpers/import/staging/ImportStaging_salarySlipsList.html'\"></ng-include>\r\n        </div>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"processrows-tab\">\r\n        <div ng-if=\"$ctrl.currentTab == 'processrows'\">\r\n          <ng-include src=\"'salaxy-components/helpers/import/staging/ImportStaging_processRows.html'\"></ng-include>\r\n        </div>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"reports-tab\">\r\n        <div ng-if=\"$ctrl.currentTab == 'reports'\">\r\n          <div ng-if=\"!$ctrl.worktimeApi.currentCalc\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.details.noPreviewCalc\"></div>\r\n          <salaxy-calc-reports ng-if=\"$ctrl.worktimeApi.currentCalc\" calcs=\"[$ctrl.worktimeApi.currentCalc]\" preview=\"true\" view=\"page1\"\r\n          report-type=\"'salarySlip'\"></salaxy-calc-reports>\r\n        </div>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"debug-tab\">\r\n        <div ng-if=\"$ctrl.currentTab == 'debug' && $ctrl.worktimeApi.currentJson\">\r\n          <div class=\"toolbar\">\r\n            <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.worktimeApi.saveJson()\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n            <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.deleteWorktime()\" sxy-text=\"SALAXY.UI_Terms.delete\"></button>\r\n          </div>\r\n          <div ng-if=\"$ctrl.worktimeApi.error\">\r\n            <h2 sxy-text=\"SALAXY.UI_Terms.error\"></h2>\r\n            <salaxy-json-formatter json=\"$ctrl.worktimeApi.error\"></salaxy-json-formatter>\r\n            <textarea style=\"width: 100%; height: 400px;\">{{ $ctrl.worktimeApi.error | json }}</textarea>\r\n            <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.worktimeApi.error = ''\" sxy-text=\"SALAXY.UI_Terms.clear\"></button>\r\n          </div>\r\n          <sxy-code-editor ng-model=\"$ctrl.worktimeApi.currentJson\" lang=\"json\" height=\"calc(100vh - 372px)\"></sxy-code-editor>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div class=\"modal-footer\">\r\n    <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showDetails()\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/helpers/import/staging/ImportStaging_list.html\",`<div>\r\n  <table class=\"table\">\r\n    <thead>\r\n      <tr>\r\n        <th></th>\r\n        <th>\r\n          <div sxy-text=\"SALAXY.NG1.ImportStagingComponent.list.title\"></div>\r\n          <div sxy-text=\"SALAXY.NG1.ApiCrudObjectComponent.id\"></div>\r\n        </th>\r\n        <th class=\"right\">\r\n          <div sxy-text=\"SALAXY.NG1.ImportStagingComponent.list.grossSalary\"></div>\r\n        </th>\r\n        <th class=\"right\">\r\n          <div sxy-text=\"SALAXY.NG1.ImportStagingComponent.list.netSalary\"></div>\r\n        </th>\r\n        <th class=\"right\">\r\n          <div sxy-text=\"SALAXY.UI_Terms.created\"></div>\r\n          <div sxy-text=\"SALAXY.UI_Terms.updated\"></div>\r\n        </th>\r\n        <th class=\"right\">\r\n          <small>\r\n            <div class=\"text-muted\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.status.preview\"></div>\r\n            <div class=\"text-primary\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.status.new\"><b></b></div>\r\n            <div class=\"\"><s sxy-text=\"SALAXY.NG1.ImportStagingComponent.status.deleted\"></s></div>\r\n            <div class=\"text-danger\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.status.error\"></div>\r\n          </small>\r\n        </th>\r\n        <th class=\"right\">\r\n          <small>\r\n            <div class=\"\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.list.total\"></div>\r\n            <div class=\"\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.status.committed\"><b></b></div>\r\n            <div class=\"text-muted\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.status.ignored\"></div>\r\n          </small>\r\n        </th>\r\n        <th class=\"right\">\r\n          <div sxy-text=\"SALAXY.NG1.ImportStagingComponent.list.calcCount\"></div>\r\n        </th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat=\"emp in $ctrl.worktimeApi.getFilteredList($ctrl.payrollId)\" class=\"clickable\" ng-click=\"$ctrl.showDetails(emp.id)\">\r\n        <td>\r\n          <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" avatar=\"emp.avatar\"></salaxy-avatar>\r\n        </td>\r\n        <td>\r\n          <div><b>{{ emp.sortableName }}</b></div>\r\n          <div>{{ emp.personalId }} ({{ \"EmploymentRelationType.\" + emp.employmentType | sxyEnum }})</div>\r\n          <div ng-if=\"emp.payrolls.unknown\" class=\"text-danger\"><small>Palkkalistojen ulkopuolella {{ emp.payrolls.unknown.rows.count }} riviä.</small></div>\r\n        </td>\r\n        <td class=\"right\">\r\n          <div>{{ $ctrl.getTotals(emp).calcs.gross | currency }}</div>\r\n          <div><s>{{ $ctrl.getTotals(emp).committed.gross | currency }}</s></div>\r\n        </td>\r\n        <td class=\"right\">\r\n          <div>{{ $ctrl.getTotals(emp).calcs.net | currency }}</div>\r\n          <div><s>{{ $ctrl.getTotals(emp).committed.net | currency }}</s></div>\r\n        </td>\r\n        <td class=\"right\">\r\n          <div>{{ emp.createdAt | sxyTime }}</div>\r\n          <div>{{ emp.updatedAt | sxyTime }}</div>\r\n        </td>\r\n        <td class=\"right\">\r\n          <small>\r\n            <div class=\"text-muted\">{{ $ctrl.getTotals(emp).rows.preview }}</div>\r\n            <div ng-if=\"$ctrl.getTotals(emp).rows.new\" class=\"bg-primary badge\">&nbsp;&nbsp;<b>{{ $ctrl.getTotals(emp).rows.new }}</b>&nbsp;</div>\r\n            <div ng-if=\"!$ctrl.getTotals(emp).rows.new\" class=\"text-primary\"><b>0</b></div>\r\n            <div class=\"\"><s>{{ $ctrl.getTotals(emp).rows.deleted || \"&nbsp;\" }}</s></div>\r\n            <div ng-if=\"$ctrl.getTotals(emp).rows.error\" class=\"bg-danger badge\">&nbsp;&nbsp;<b>{{ $ctrl.getTotals(emp).rows.error }}</b>&nbsp;</div>\r\n            <div ng-if=\"!$ctrl.getTotals(emp).rows.error\" class=\"text-danger\"><b>0</b></div>\r\n          </small>\r\n        </td>\r\n        <td class=\"right\">\r\n          <small>\r\n            <div class=\"\">{{ $ctrl.getTotals(emp).rows.count }}</div>\r\n            <div class=\"\"><b>{{ $ctrl.getTotals(emp).rows.committed }}</b></div>\r\n            <div class=\"text-muted\">{{ $ctrl.getTotals(emp).rows.ignored }}</div>\r\n          </small>\r\n        </td>\r\n        <td class=\"right\">\r\n          <div>{{ $ctrl.getTotals(emp).calcs.count }}</div>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/helpers/import/staging/ImportStaging_overview.html\",`<div>\r\n  <div ng-if=\"$ctrl.serverUrl\">\r\n    <salaxy-tab-buttons\r\n      current-tab=\"$ctrl.currentTab\"\r\n      options=\"[\r\n        { 'value': 'default', 'text': 'Overview' },\r\n        { 'value': 'tests', 'text': 'Tests' }\r\n      ]\"\r\n      tabs-id=\"importStagingOverview\">\r\n    </salaxy-tab-buttons>\r\n    <div class=\"tab-content\" id=\"tab-content-importStagingOverview\">\r\n      <div class=\"tab-pane\" id=\"default-tab\">\r\n        <div ng-if=\"$ctrl.currentTab == 'default'\">\r\n          <div>Current staging server: <a ng-href=\"{{ $ctrl.serverUrl }}\" target=\"_blank\">{{ $ctrl.serverUrl }}</a></div>\r\n        </div>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"tests-tab\">\r\n        <div ng-if=\"$ctrl.currentTab == 'tests'\">\r\n          <fieldset>\r\n            <legend>Upload test data</legend>\r\n            <p class=\"lead\">\r\n              Upload a test file to the staging server.\r\n              The file should be a JSON file with employment relations or rows: The same structure that an integration sends.\r\n            </p>\r\n            <div class=\"row\">\r\n              <div class=\"col-md-6\">\r\n                <form ng-submit=\"$ctrl.uploadTestFile($event)\">\r\n                  <input type=\"file\" class=\"form-control\" />\r\n                  <button type=\"submit\" class=\"btn btn-primary\">Process uploaded file</button>\r\n                <button type=\"submit\" class=\"btn btn-default\" ng-click=\"$ctrl.uploadTestFile('clipboard')\">Process from clipboard</button>\r\n                </form>\r\n              </div>\r\n              <div class=\"col-md-6\">\r\n                <p>Get demo files:</p>\r\n                <ul>\r\n                  <li>Rows: check the personal ID before processing</li>\r\n                  <ul>\r\n                    <li><a ng-href=\"{{ $ctrl.serverUrl + '/test-data/rows_2023-09-01_2023-12-22.json' }}\" target=\"_blank\">2023-09-01 - 2023-12-22</a></li>\r\n                    <li><a ng-href=\"{{ $ctrl.serverUrl + '/test-data/rows_2023-11-01_2023-11-30.json' }}\" target=\"_blank\">2023-11-01 - 2023-11-30</a></li>\r\n                  </ul>\r\n                  <li><a ng-href=\"{{ $ctrl.serverUrl + '/test-data/employment-190372-942M.json' }}\" target=\"_blank\">Employment, Pauliina Palkkanen, 190372-942M</a>.</li>\r\n                </ul>\r\n              </div>\r\n            </div>\r\n            <salaxy-json-formatter json=\"$ctrl.uploadResults\" key=\"'result'\" open=\"0\"></salaxy-json-formatter>\r\n          </fieldset>\r\n          <fieldset>\r\n            <legend>Create a Payroll / Nepton Payment Period</legend>\r\n            <div class=\"btn-toolbar\">\r\n              <div class=\"btn-goup\">\r\n                <p>TODO: Add possibility for setting the values and creating the Payroll</p>\r\n                <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.runTest('createUpdatePaymentPeriod')\">Demo button (fixed ID)</button>\r\n              </div>\r\n            </div>\r\n          </fieldset>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div ng-if=\"!$ctrl.serverUrl\" class=\"container\">\r\n    <div class=\"alert alert-info\">\r\n      Integrations has not been set up for this environment.\r\n      Please specify the integration server in the settings (PRO settings => other)\r\n      or contact customer services.\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/helpers/import/staging/ImportStaging_processRows.html\",`<div class=\"btn-toolbar\">\r\n  <div class=\"btn-group\">\r\n    <button type=\"button\" class=\"btn btn-default\" ng-repeat=\"group in $ctrl.statusGroups\" ng-click=\"$ctrl.statusGroup = group\" ng-disabled=\"group.active\">{{ group.text |\r\n      sxyTranslate }}</button>\r\n  </div>\r\n  <div class=\"btn-group\">\r\n    <button id=\"single-button\" type=\"button\" class=\"btn dropdown-toggle\" ng-class=\"$ctrl.$ctrlRows.getSelectedRows().length ? 'btn-primary' : 'btn-default'\" data-bs-toggle=\"dropdown\" aria-expanded=\"false\">\r\n      {{'SALAXY.UI_Terms.selected' | sxyTranslate}} ({{ $ctrl.$ctrlRows.getSelectedRows().length }})\r\n    </button>\r\n    <ul class=\"dropdown-menu\" aria-labelledby=\"single-button\">\r\n      <li><a class=\"dropdown-item\" href=\"\" ng-click=\"$ctrl.$ctrlRows.toggleSelectedRow('all', true)\">{{'SALAXY.UI_Terms.selectAll' | sxyTranslate}}</a></li>\r\n      <li><a class=\"dropdown-item\" href=\"\" ng-click=\"$ctrl.$ctrlRows.toggleSelectedRow('all', false)\">{{'SALAXY.UI_Terms.removeSelections' | sxyTranslate}}</a></li>\r\n    </ul>\r\n  </div>\r\n</div>\r\n<div class=\"btn-toolbar\">\r\n  <div class=\"btn-group\">\r\n    <div style=\"width: 240px; vertical-align: middle;float: left;\">\r\n      <salaxy-input-typeahead options=\"$ctrl.worktimeApi.payrolls\" name=\"payrollId\" label-type=\"plain\"\r\n        placeholder=\"{{ 'SALAXY.NG1.ImportStagingComponent.toolbar.selectPayroll' | sxyTranslate }}\" ng-model=\"$ctrl.payrollMoveTarget\"></salaxy-input-typeahead>\r\n    </div>\r\n    <button type=\"button\" class=\"btn btn-primary\" ng-disabled=\"!$ctrl.$ctrlRows.getSelectedRows().length || !$ctrl.payrollMoveTarget\"\r\n      ng-click=\"$ctrl.moveToPayroll($ctrl.$ctrlRows.getSelectedRows(), $ctrl.payrollMoveTarget)\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.toolbar.moveToPayroll\"></button>\r\n    <button type=\"button\" class=\"btn btn-default\" ng-disabled=\"!$ctrl.payrollMoveTarget\"\r\n      ng-click=\"$ctrl.$ctrlRows.toggleSelectedRow('all', true);$ctrl.moveToPayroll($ctrl.$ctrlRows.getSelectedRows(), $ctrl.payrollMoveTarget)\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.toolbar.selectAndMove\"></button>\r\n  </div>\r\n  <button type=\"button\" class=\"btn btn-default\" ng-disabled=\"!$ctrl.$ctrlRows.getSelectedRows().length\" ng-click=\"$ctrl.deleteRows($ctrl.$ctrlRows.getSelectedRows())\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.toolbar.deleteFromData\"></button>\r\n  <div class=\"btn-group\">\r\n    <div style=\"vertical-align: middle;float: left;line-height: 26px; padding: 4px\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.toolbar.moveToStatus\"></div>\r\n    <button type=\"button\" class=\"btn btn-default\" ng-disabled=\"!$ctrl.$ctrlRows.getSelectedRows().length\" ng-click=\"$ctrl.setStatus($ctrl.$ctrlRows.getSelectedRows(), 'ignored')\"\r\n      sxy-text=\"SALAXY.NG1.ImportStagingComponent.status.ignored\"></button>\r\n    <button type=\"button\" class=\"btn btn-default\" ng-disabled=\"!$ctrl.$ctrlRows.getSelectedRows().length\" ng-click=\"$ctrl.setStatus($ctrl.$ctrlRows.getSelectedRows(), 'new')\"\r\n      sxy-text=\"SALAXY.NG1.ImportStagingComponent.statusGroup.todo\"></button>\r\n  </div>\r\n</div>\r\n<salaxy-calc-rows-editor ng-if=\"$ctrl.worktimeApi.current\" type=\"worktime-import-employment\" rows=\"$ctrl.worktimeApi.filteredRows\" title=\"{{'SALAXY.NG1.ImportStagingComponent.toolbar.rowsInImport' | sxyTranslate}}\" ng-ref=\"$ctrl.$ctrlRows\"\r\n  mode=\"read-only\" statuses=\"$ctrl.statusGroup.statuses\" show-row-selection=\"true\"></salaxy-calc-rows-editor>`);\n\n $templateCache.put(\"salaxy-components/helpers/import/staging/ImportStaging_rawRows.html\",`<div class=\"btn-toolbar\">\r\n  <div class=\"btn-group\">\r\n    <button type=\"button\" class=\"btn btn-default\" ng-repeat=\"group in $ctrl.statusGroups\" ng-click=\"$ctrl.statusGroup = group\"\r\n      ng-disabled=\"group.active\">{{ group.text | sxyTranslate }} <div class=\"badge\">{{ group.count ? group.count : '' }}</div></button>\r\n  </div>\r\n  <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.recalculateWorktime()\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.details.recalculate\"></button>\r\n  <button type=\"button\" class=\"btn btn-primary\" ng-disabled=\"!$ctrl.worktimeApi.detailsPayrollId\" ng-click=\"$ctrl.commitPayroll('employment')\"\r\n    sxy-text=\"SALAXY.NG1.ImportStagingComponent.details.commitPayroll\"></button>\r\n</div>\r\n<salaxy-calc-rows-editor ng-if=\"$ctrl.worktimeApi.current\" type=\"worktime-import-employment\"\r\n  rows=\"$ctrl.worktimeApi.filteredRows\" title=\"Rivit importissa\" ng-ref=\"$ctrl.$ctrlRows\"\r\n  mode=\"read-only\" statuses=\"$ctrl.statusGroup.statuses\"></salaxy-calc-rows-editor>`);\n\n $templateCache.put(\"salaxy-components/helpers/import/staging/ImportStaging_salarySlipsList.html\",`<div ng-if=\"!$ctrl.currentEmploymentPdf\">\r\n  <div class=\"btn-toolbar\">\r\n    <div class=\"btn-group\">\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.salarySlipListType = 'all'\" ng-disabled=\"$ctrl.salarySlipListType == 'all'\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.salarySlipList.type.all\"></button>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.salarySlipListType = 'preview'\" ng-disabled=\"$ctrl.salarySlipListType == 'preview'\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.salarySlipList.type.preview\"></button>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.salarySlipListType = 'committed'\" ng-disabled=\"$ctrl.salarySlipListType == 'committed'\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.salarySlipList.type.committed\"></button>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.salarySlipListType = 'distinct'\" ng-disabled=\"$ctrl.salarySlipListType == 'distinct'\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.salarySlipList.type.distinct\"></button>\r\n    </div>\r\n  </div>\r\n  <table class=\"table table-condenced\">\r\n    <thead>\r\n      <tr>\r\n        <th>\r\n          <div sxy-text=\"SALAXY.NG1.ImportStagingComponent.salarySlipList.status\"></div>\r\n          <div sxy-text=\"SALAXY.NG1.ImportStagingComponent.salarySlipList.id\"></div>\r\n        </th>\r\n        <th class=\"right\" style=\"font-size: 0.75em;\">\r\n          <div sxy-text=\"SALAXY.ENUM.CalcGroup.baseSalary.label\"></div>\r\n          <div sxy-text=\"SALAXY.ENUM.CalcGroup.salaryAdditions.label\"></div>\r\n          <div sxy-text=\"SALAXY.ENUM.CalcGroup.benefits.label\"></div>\r\n          <div sxy-text=\"SALAXY.ENUM.CalcGroup.deductions.label\"></div>\r\n          <div sxy-text=\"SALAXY.ENUM.CalcGroup.expenses.label\"></div> \r\n        </th>\r\n        <th class=\"right\">\r\n          <div sxy-text=\"SALAXY.NG1.ImportStagingComponent.salarySlipList.grossSalary\"></div>\r\n          <div sxy-text=\"SALAXY.NG1.ImportStagingComponent.salarySlipList.netSalary\"></div>\r\n        </th>\r\n        <th class=\"right\">\r\n          <div sxy-text=\"SALAXY.NG1.ImportStagingComponent.salarySlipList.salaryDate\"></div>\r\n          <div sxy-text=\"SALAXY.NG1.ImportStagingComponent.salarySlipList.period\"></div>\r\n        </th>\r\n        <th></th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat=\"calc in $ctrl.currentEmploymentCalcs\">\r\n        <td>\r\n          <div>\r\n            {{ \"CalculationStatus.\" + calc.status | sxyEnum }}\r\n            <span ng-if=\"calc.status == 'payrollDraft'\"><a ng-href=\"{{ '#/payroll/details/' + calc.data.payrollId }}\" sxy-text=\"SALAXY.NG1.ImportStagingComponent.salarySlipList.payrollLink\"></a></span>\r\n            <!-- TODO: Add links when paid etc. -->\r\n          </div>\r\n          <div class=\"small truncate\" style=\"max-width: 256px;\"><code>{{ calc.id }}</code></div>\r\n        </td>\r\n        <td class=\"right\" style=\"font-size: 0.75em;\">\r\n          <div>{{ calc.data.salary | currency }}</div>\r\n          <div>{{ calc.data.allowances | currency }}</div>\r\n          <div>{{ calc.data.benefits | currency }}</div>\r\n          <div>{{ calc.data.deductions | currency }}</div>\r\n          <div>{{ calc.data.expenses | currency }}</div>\r\n        </td>\r\n        <td class=\"right\">\r\n          <div>{{ calc.grossSalary | currency }}</div>\r\n          <div>{{ calc.data.workerPayment | currency }}</div>\r\n        </td>\r\n        <td class=\"right\">\r\n          <div>{{ calc.salaryDate | sxyDate }}</div>\r\n          <div>{{ calc.data | sxyDateRange }}</div>\r\n        </td>\r\n        <td class=\"right\">\r\n          <button class=\"btn btn-primary\" ng-click=\"$ctrl.showReportDialog(calc.id)\"><i class=\"bi bi-search\"></i> <span sxy-text=\"SALAXY.UI_Terms.show\"></span></button>\r\n          <button class=\"btn btn-default\" ng-click=\"$ctrl.showSalarySlipPdf(calc.id)\"><i class=\"bi bi-file-earmark-pdf\"></i> <span sxy-text=\"SALAXY.UI_Terms.downloadPdf\"></span></button>\r\n          <button class=\"btn btn-default\" sxy-if-role=\"test\" ng-click=\"$ctrl.showSalarySlipHtml(calc.id)\">TEST: html</span></button>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n</div>\r\n\r\n<div ng-if=\"$ctrl.currentEmploymentPdf\">\r\n  <div class=\"btn-toolbar\">\r\n    <button class=\"btn btn-default pull-right\" ng-click=\"$ctrl.showSalarySlipPdf(undefined)\"><i class=\"bi bi-x-lg\"></i> <span sxy-text=\"SALAXY.UI_Terms.close\"></span></button>\r\n  </div>\r\n  <salaxy-spinner ng-if=\"$ctrl.currentEmploymentPdf == 'loading'\"></salaxy-spinner>\r\n  <iframe ng-if=\"$ctrl.currentEmploymentPdf != 'loading'\" style=\"width:100%;height:200vh\" ng-src=\"{{ $ctrl.currentEmploymentPdf }}\"></iframe>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/helpers/import/staging/ImportStaging_test_data.html\",`<div sxy-if-role=\"test\">\r\n  <p>&nbsp;</p>\r\n  <hr />\r\n  <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showDebug = !$ctrl.showDebug\">TEST ONLY: show/hide debug upload</button>\r\n  <div style=\"max-width: 800px;\">\r\n    <fieldset ng-if=\"$ctrl.showDebug\">\r\n      <legend>Upload test data</legend>\r\n      <p class=\"lead\">\r\n        Upload a test file to the staging server.\r\n        The file should be a JSON file with employment relations or rows: The same structure that an integration sends.\r\n      </p>\r\n      <div class=\"row\">\r\n        <div class=\"col-md-6\">\r\n          <form ng-submit=\"$ctrl.uploadTestFile($event)\">\r\n            <input type=\"file\" class=\"form-control\" />\r\n            <button type=\"submit\" class=\"btn btn-primary\">Process uploaded file</button>\r\n            <button type=\"submit\" class=\"btn btn-default\" ng-click=\"$ctrl.uploadTestFile('clipboard')\">Process from clipboard</button>\r\n          </form>\r\n        </div>\r\n        <div class=\"col-md-6\">\r\n          <p>Get demo files:</p>\r\n          <ul>\r\n            <li>Rows: check the personal ID before processing</li>\r\n            <ul>\r\n              <li><a ng-href=\"{{ $ctrl.serverUrl + '/test-data/rows_2023-09-01_2023-12-22.json' }}\" target=\"_blank\">2023-09-01 - 2023-12-22</a></li>\r\n              <li><a ng-href=\"{{ $ctrl.serverUrl + '/test-data/rows_2023-11-01_2023-11-30.json' }}\" target=\"_blank\">2023-11-01 - 2023-11-30</a></li>\r\n            </ul>\r\n            <li><a ng-href=\"{{ $ctrl.serverUrl + '/test-data/employment-190372-942M.json' }}\" target=\"_blank\">Employment, Pauliina Palkkanen, 190372-942M</a>.</li>\r\n          </ul>\r\n        </div>\r\n      </div>\r\n      <salaxy-json-formatter json=\"$ctrl.uploadResults\" key=\"'result'\" open=\"0\"></salaxy-json-formatter>\r\n    </fieldset>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/helpers/import/WorktimeImport.html\",`<div class=\"salaxy-component salaxy-worktime-import\">\r\n  <h1 sxy-text=\"SALAXY.NG1_Sitemap.pro-service.worktime-imports.details\"></h1>\r\n  <div ng-if=\"$ctrl.current\">\r\n    <div class=\"btn-toolbar\" role=\"toolbar\">\r\n      <div class=\"btn-group\" role=\"group\">\r\n        <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.process('parse')\">Parse</button>\r\n        <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.process('validate')\">Validate</button>\r\n        <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.process('preview')\">Preview</button>\r\n        <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.process('previewWithEmployments')\">Preview (commit employments)</button>\r\n        <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.process('import')\">Import</button>\r\n      </div>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.save()\">Save</button>\r\n      <a href=\"#/worktime-imports\" class=\"btn btn-default\">Back to list</a>\r\n    </div>\r\n    <sxy-form ng-ref=\"$frm\" open-api=\"http://localhost:82/schemas/v02.json\" xx-open-api=\"salaxy-secure/schemas/v02.json\" type=\"WorktimeImport\" model=\"$ctrl.current\">\r\n      <div>\r\n        <salaxy-tab-buttons\r\n          current-tab=\"$ctrl.currentTab\"\r\n          options=\"[\r\n            { value: 'default', text: 'Perustiedot' },\r\n            { value: 'files', text: 'Tiedostot' },\r\n            { value: 'employmentrelations', text: 'Employment relations' },\r\n            { value: 'salaryrows', text: 'Salary rows' },\r\n            { value: 'previewemployment', text: 'Preview: Employment' },\r\n            { value: 'preview', text: 'Preview' },\r\n            { value: 'debug', text: 'Debugger' }\r\n          ]\"\r\n          tabs-id=\"worktimeImport\">\r\n        </salaxy-tab-buttons>\r\n        <div class=\"tab-content\" id=\"tab-content-worktimeImport\">\r\n          <div class=\"tab-pane\" id=\"default-tab\">\r\n            <div class=\"row\">\r\n              <div class=\"col-sm-6\">\r\n                <fieldset>\r\n                  <legend>Basic data</legend>\r\n                  <sxy-input model=\"form.id\"></sxy-input>\r\n                  <sxy-input model=\"form.createdAt\"></sxy-input>\r\n                  <sxy-input model=\"form.updatedAt\"></sxy-input>\r\n                  <sxy-input model=\"form.header.status\"></sxy-input>\r\n                </fieldset>\r\n              </div>\r\n              <div class=\"col-sm-6\">\r\n                <fieldset>\r\n                  <legend>Control data</legend>\r\n                  <sxy-input model=\"form.header.payrollId\" label=\"Palkkalistan ID\"></sxy-input>\r\n                  <sxy-input model=\"form.header.sourceId\" label=\"ID (lähde)\"></sxy-input>\r\n                  <sxy-input model=\"form.header.salaryDate\" format=\"date\" label=\"Palkkapäivä\"></sxy-input>\r\n                  <sxy-input model=\"form.header.period\" label=\"Palkkakausi\"></sxy-input>\r\n                </fieldset>\r\n              </div>\r\n            </div>\r\n            <div class=\"tab-pane\" id=\"files-tab\"></div>\r\n            <table class=\"table\">\r\n              <thead>\r\n                <tr>\r\n                  <th>\r\n                    File<br />\r\n                    File type (mime type)\r\n                  </th>\r\n                  <th>Data</th>\r\n                </tr>\r\n              </thead>\r\n              <tbody>\r\n                <tr ng-repeat=\"file in $ctrl.current.files\">\r\n                  <td style=\"width: 50%;\">\r\n                    <salaxy-input name=\"fileName\" ng-model=\"file.name\" label-type=\"plain\"></salaxy-input>\r\n                    <salaxy-input name=\"fileMimeType\" ng-model=\"file.mimeType\" label-type=\"plain\"></salaxy-input>\r\n                    <salaxy-input name=\"fileUsecaseUri\" label=\"Usecase\" ng-model=\"file.usecase.uri\"></salaxy-input>\r\n                  </td>\r\n                  <td style=\"width: 50%;\">\r\n                    <salaxy-textarea name=\"fileData\" ng-model=\"file.data\" rows=\"5\" label-type=\"plain\"></salaxy-textarea>\r\n                  </td>\r\n                </tr>\r\n              </tbody>\r\n            </table>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"employmentrelations-tab\">\r\n            <sxy-table ng-if=\"!$ctrl.isLoading\" doc=\"http://localhost:82/schemas/v02.json\" schema=\"WorktimeImportEmployment\"\r\n            data=\"$ctrl.current.employments\" include=\"$ctrl.employmentsCols\"></sxy-table>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"salaryrows-tab\">\r\n            <salaxy-calc-rows-editor ng-if=\"!$ctrl.isLoading\" rows=\"$ctrl.current.rows\" title=\"Import rows\" type=\"worktime-import\"></salaxy-calc-rows-editor>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"previewemployment-tab\">\r\n            TODO: Employment preview UI here\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"preview-tab\">\r\n            TODO: Calc preview (also absences & holidays?)\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"debug-tab\">\r\n            <salaxy-json-formatter json=\"$ctrl.current\"></salaxy-json-formatter>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </sxy-form>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/helpers/JsonDiff.html\",`<div class=\"salaxy-component salaxy-json-diff-table\">\r\n  <div ng-if=\"$ctrl.isLoading\" class=\"text-center p-3 text-muted\">\r\n    <p>Loading schema...</p>\r\n  </div>\r\n  <div ng-if=\"!$ctrl.isLoading && $ctrl.tableConfig.data.length === 0\" class=\"text-center p-3 text-muted\">\r\n    <p>No differences found between the objects.</p>\r\n  </div>\r\n  <div ng-show=\"!$ctrl.isLoading && $ctrl.tableConfig.data.length > 0\">\r\n    <sxy-table ng-ref=\"$ctrl.$sxyTable\" options=\"$ctrl.tableConfig.options\" include=\"$ctrl.tableConfig.include\" data=\"$ctrl.tableConfig.data\"></sxy-table>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/helpers/JsonFormatter.html\",`<button ng-class=\"$ctrl.btnClass ? $ctrl.btnClass : 'btn btn-default btn-xs'\" ng-if=\"$ctrl.type == 'dialog'\" ng-click=\"$ctrl.showDialog()\">\r\n  <span ng-if=\"$ctrl.hasKey\"><span class=\"key-text\">{{ $ctrl.key }}</span></span>\r\n  <span ng-if=\"!$ctrl.hasKey && $ctrl.isArray()\"><span class=\"bracket\">[</span><span class=\"number\">{{$ctrl.json.length}}</span><span class=\"bracket\">]</span></span>\r\n  <span ng-if=\"!$ctrl.hasKey && !$ctrl.isArray()\"><span class=\"bracket\">{</span><span class=\"number\">{{$ctrl.getKeys().length}}</span><span class=\"bracket\">}</span></span>\r\n</button>\r\n<div class=\"json-formatter-row\" ng-if=\"$ctrl.type != 'dialog'\">\r\n  <a ng-click=\"$ctrl.toggleOpen()\">\r\n    <span class=\"toggler {{ $ctrl.isOpen ? 'open' : ''}}\" ng-if=\"$ctrl.isObject()\"></span>\r\n    <span class=\"key {{$ctrl.changes.type}}\" ng-if=\"$ctrl.hasKey\"><span class=\"key-text\">{{ $ctrl.key }}</span><span ng-if=\"$ctrl.changes\"> ({{ $ctrl.changes.icon }})</span><span class=\"colon\">:</span></span>\r\n    <span class=\"value\">\r\n      <span ng-if=\"$ctrl.isObject()\">\r\n        <span ng-if=\"$ctrl.isArray()\"><span class=\"bracket\">[</span><span class=\"number\">{{$ctrl.json.length}}</span><span class=\"bracket\">]</span></span>\r\n        <span ng-if=\"!$ctrl.isArray()\"><span class=\"bracket\">{</span><span class=\"number\">{{$ctrl.getKeys().length}}</span><span class=\"bracket\">}</span></span>\r\n      </span>\r\n      <span ng-if=\"!$ctrl.isObject()\" ng-click=\"$ctrl.openLink($ctrl.isUrl)\" class=\"{{ $ctrl.jsonType }}\"\r\n        ng-class=\"{ date: $ctrl.isDate, url: $ctrl.isUrl }\">{{$ctrl.parseValue($ctrl.json)}}<del\r\n        ng-if=\"$ctrl.changes\">{{$ctrl.changes.oldValue}}</del></span>\r\n    </span>\r\n    <span ng-if=\"$ctrl.showThumbnail()\" class=\"thumbnail-text\">{{$ctrl.getThumbnail()}}</span>\r\n  </a>\r\n  <div class=\"children\" ng-if=\"$ctrl.getKeys().length && $ctrl.isOpen\">\r\n    <salaxy-json-formatter ng-repeat=\"key in $ctrl.getKeys() track by $index\" key=\"key\" open=\"$ctrl.childrenOpen()\"\r\n      json=\"$ctrl.json[key]\" compare=\"$ctrl.compare\" compare-to=\"$ctrl.compareTo[key]\"></salaxy-json-formatter>\r\n    <salaxy-json-formatter ng-repeat=\"key in $ctrl.deletedKeys track by $index\" key=\"key\" open=\"$ctrl.childrenOpen()\"\r\n      json=\"$ctrl.json[key]\" compare=\"$ctrl.compare\" compare-to=\"$ctrl.compareTo[key]\"></salaxy-json-formatter>\r\n  </div>\r\n  <div class=\"children empty object\" ng-if=\"$ctrl.isEmptyObject()\"></div>\r\n  <div class=\"children empty array\" ng-if=\"$ctrl.getKeys() && !$ctrl.getKeys().length && $ctrl.isOpen && $ctrl.isArray()\"></div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/helpers/JsonFormatterDialog.html\",`<div class=\"modal-calc-list\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{ $ctrl.logic.title }}</h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <salaxy-json-formatter json=\"$ctrl.current\" type=\"{{ $ctrl.logic.type }}\" open=\"$ctrl.logic.open\" compare=\"$ctrl.logic.compare\" compare-to=\"$ctrl.logic.compareTo\" key=\"$ctrl.logic.key\"></salaxy-json-formatter>\r\n    <div class=\"text-end\">\r\n      <button type=\"reset\" class=\"btn btn-primary\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/helpers/NaviSitemap.html\",`\r\n<div class=\"salaxy-component salaxy-navi-sitemap\" ng-if=\"$ctrl.mode != 'horizontal'\">\r\n\r\n  <ul class=\"list-group\" ng-class=\"{'salaxy-navi-3-level': $ctrl.mode == '3-level'}\">\r\n    <li ng-repeat=\"section in $ctrl.filterHidden($ctrl.sitemap)\" class=\"list-group-item\">\r\n      <a ng-href=\"{{section.url}}\" ng-click=\"!$ctrl.hasChildren(section) ? $ctrl.toggleNavi() : return\" ng-class=\"{ 'active' : $ctrl.isCurrent(section)}\">\r\n        <span ng-if=\"$ctrl.mode != 'default' && $ctrl.hasChildren(section)\">\r\n          <i aria-hidden=\"true\" class=\"bi float-end\" ng-class=\"$ctrl.isCurrent(section) ? 'bi-chevron-up' : 'bi-chevron-down' \"></i>\r\n        </span> {{section.title | sxyTranslate}} <span ng-if=\"$ctrl.isTest(section)\" class=\"badge bg-primary float-end\"><span class=\"small\">test</span></span>\r\n      </a>\r\n      <ul ng-if=\"$ctrl.hasChildren(section) && ($ctrl.mode == 'default' || $ctrl.isCurrent(section))\">\r\n        <li ng-repeat=\"subNavi in $ctrl.filterHidden(section.children)\">\r\n          <a ng-href=\"{{ $ctrl.getUrl(subNavi) }}\" ng-click=\"$ctrl.toggleNavi()\" ng-class=\"{ 'active' : $ctrl.isCurrent(subNavi)}\">{{subNavi.title | sxyTranslate}} <span ng-if=\"$ctrl.isTest(subNavi)\" class=\"badge bg-primary\"><span class=\"small\">test</span></span></a>\r\n\r\n          <ul ng-if=\"$ctrl.mode == '3-level' && $ctrl.isCurrent(subNavi) && $ctrl.hasChildren(subNavi)\">\r\n            <li ng-repeat=\"naviLevel3 in $ctrl.filterHidden(subNavi.children)\">\r\n              <a ng-href=\"{{ $ctrl.getUrl(naviLevel3) }}\" ng-click=\"$ctrl.toggleNavi()\" ng-class=\"{'active' : $ctrl.isCurrent(naviLevel3)}\">{{naviLevel3.title | sxyTranslate}} <span ng-if=\"$ctrl.isTest(naviLevel3)\" class=\"badge bg-primary\"><span class=\"small\">test</span></span></a>\r\n            </li>\r\n          </ul>\r\n        </li>\r\n      </ul>\r\n    </li>\r\n  </ul>\r\n  <div class=\"poweredby\">\r\n    <span class=\"poweredby-image\"></span>\r\n  </div>\r\n</div>\r\n\r\n<div class=\"salaxy-component salaxy-navi-sitemap\" ng-if=\"$ctrl.mode == 'horizontal'\">\r\n  <header class=\"salaxy-navi-header-horizontal\">\r\n    <div class=\"container-fluid\">\r\n      <div class=\"d-md-none align-items-center d-flex\">\r\n        <span class=\"page-title-sm\">\r\n          <span class=\"uppercase\"><strong>{{ $ctrl.currentPath[0].title | sxyTranslate }}</strong></span>\r\n          <span class=\"small\" ng-if=\"$ctrl.hasChildren($ctrl.currentPath[0])\">/ {{$ctrl.current.title | sxyTranslate}}</span>\r\n        </span>\r\n        <button type=\"button\" class=\"navbar-toggle btn btn-lg ms-auto\" data-bs-toggle=\"collapse\" data-bs-target=\"#navbar-content\">\r\n          <i class=\"bi bi-list\" aria-hidden=\"true\"></i>\r\n        </button>\r\n      </div>\r\n      <nav class=\"navbar navbar-expand-md\">\r\n        <div class=\"collapse navbar-collapse\" id=\"navbar-content\">\r\n          <ul class=\"navbar-nav\">\r\n            <li ng-repeat=\"section in $ctrl.filterHidden($ctrl.sitemap)\" class=\"nav-item dropdown\" ng-class=\"{ 'active' : $ctrl.isCurrentSection(section)}\">\r\n              <a ng-if=\"!$ctrl.hasChildren(section)\" ng-href=\"{{section.url}}\" class=\"nav-link\">{{section.title | sxyTranslate}}</a>\r\n              <a ng-if=\"$ctrl.hasChildren(section)\" class=\"nav-link dropdown-toggle\" data-bs-toggle=\"dropdown\" role=\"button\">{{section.title | sxyTranslate}}</a>\r\n              <ul ng-if=\"$ctrl.hasChildren(section)\" class=\"dropdown-menu\">\r\n                <li ng-repeat=\"subNavi in $ctrl.filterHidden(section.children)\">\r\n                  <a ng-href=\"{{ $ctrl.getUrl(subNavi) }}\" ng-click=\"$ctrl.toggleNavi()\" class=\"dropdown-item\" ng-class=\"{'active' : $ctrl.isCurrent(subNavi)}\">\r\n                    {{subNavi.title | sxyTranslate}} \r\n                    <span ng-if=\"$ctrl.isTest(subNavi)\" class=\"badge bg-info\"><span class=\"small\">test</span></span>\r\n                  </a>\r\n                </li>\r\n              </ul>\r\n            </li>\r\n          </ul>\r\n        </div>\r\n      </nav>\r\n    </div>\r\n  </header>\r\n  <div class=\"d-none d-sm-block breadcrumb-container mt-2 ps-5 mb-4\">\r\n    <span class=\"text-primary\"><span class=\"text-uppercase\"><strong>{{ $ctrl.currentPath[0].title | sxyTranslate }}</strong></span> <span class=\"small\" ng-if=\"$ctrl.hasChildren($ctrl.currentPath[0])\">/ {{$ctrl.current.title | sxyTranslate}}</span></span>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/helpers/NaviStarterLayout.html\",`<salaxy-spinner ng-if=\"$ctrl.showFullPageLoader\" full-screen=\"true\" heading=\"SALAXY.UI_Terms.loading\"></salaxy-spinner>\r\n<div ng-if=\"!$ctrl.showFullPageLoader && (!$ctrl.layout || $ctrl.layout == 'default')\" ng-cloak class=\"salaxy-component salaxy-navi-page-container\" ng-class=\"{ 'salaxy-navi-sm-opened': $ctrl.isNaviOpen }\">\r\n\r\n  <ng-transclude ng-transclude-slot=\"nav\">\r\n    <nav class=\"salaxy-navi-sidebar d-print-none\">\r\n      <div class=\"salaxy-logo-container\">\r\n        <a href=\"/#/\"></a>\r\n      </div>\r\n      <div class=\"d-block d-md-none mobile-login-container text-center\">\r\n        <salaxy-login-button></salaxy-login-button>\r\n      </div>\r\n      <salaxy-navi-sitemap mode=\"accordion\"></salaxy-navi-sitemap>\r\n    </nav>\r\n  </ng-transclude>\r\n  <header class=\"salaxy-navi-header-mobile d-block d-md-none\" style=\"width: 100vw;\">\r\n    <button type=\"button\" class=\"salaxy-navi-hamburger d-print-none btn btn-default float-end\" ng-click=\"$ctrl.toggleNavi()\">\r\n      <span class=\"sr-only\" sxy-text=\"SALAXY.UI_Terms.navigation\"></span>\r\n      <i class=\"bi bi-list m-0\" aria-hidden=\"true\"></i>\r\n    </button>\r\n    <h1>{{ $ctrl.title | sxyTranslate }}</h1>\r\n  </header>\r\n  <div class=\"salaxy-navi-main-container\">\r\n    <content>\r\n      <ng-transclude ng-transclude-slot=\"header\">\r\n        <header class=\"salaxy-navi-header-default d-none d-md-block\">\r\n          <div ng-class=\"$ctrl.current.isFullWidth ? 'container-fluid' : 'container-md'\" class=\"h-100\">\r\n            <div class=\"d-flex justify-content-between align-items-center h-100\">\r\n              <h1 class=\"page-title m-0\">\r\n                {{ $ctrl.title | sxyTranslate }}\r\n              </h1>\r\n              <div class=\"d-print-none\">\r\n                <salaxy-login-button class='float-end'></salaxy-login-button>\r\n              </div>\r\n            </div>\r\n          </div>\r\n        </header>\r\n      </ng-transclude>\r\n      <div id=\"salaxy-alert-container\"></div>\r\n      <ng-transclude ng-transclude-slot=\"main\">\r\n        <main class=\"pt-3\">\r\n          <div ng-class=\"$ctrl.current.isFullWidth ? 'container-fluid' : 'container-md'\" ng-if=\"!$ctrl.getDisabled()\" ng-view autoscroll=\"true\"></div>\r\n          <div class=\"container\" ng-if=\"$ctrl.getDisabled()\">\r\n            <div class=\"alert alert-info\" sxy-text=\"SALAXY.UI_Terms.pageDisabledAlert\"></div>\r\n          </div>\r\n        </main>\r\n      </ng-transclude>\r\n    </content>\r\n  </div>\r\n</div>\r\n\r\n<div ng-if=\"!$ctrl.showFullPageLoader && $ctrl.layout == 'iframe'\" ng-cloak class=\"salaxy-component salaxy-navi-page-container iframe-container\">\r\n  <div class=\"salaxy-navi-main-container\">\r\n    <content>\r\n      <ng-transclude ng-transclude-slot=\"header\" ng-if=\"$ctrl.mode != 'horizontal'\">\r\n\r\n        <header class=\"salaxy-navi-header-default\">\r\n          <div class=\"container-fluid\">\r\n            <div class=\"d-flex align-items-center\">\r\n              <h1 class=\"page-title\">\r\n                {{ $ctrl.title | sxyTranslate }}\r\n              </h1>\r\n              <div class=\"ms-auto\" ng-if=\"$ctrl.hasChildren($ctrl.currentPath[0])\" style=\"margin-left:10px;\">\r\n                <div class=\"btn-group dropdown\">\r\n                  <button class=\"btn btn-default dropdown-toggle btn-submenu\" data-bs-toggle=\"dropdown\" aria-haspopup=\"true\" aria-expanded=\"false\">\r\n                    <span class=\"d-none d-sm-inline-block\">{{ ($ctrl.currentPath[0].subMenuTitle || 'SALAXY.UI_Terms.menu') | sxyTranslate }}</span>\r\n                    <i class=\"bi bi-list d-inline-block d-sm-none\" aria-hidden=\"true\"></i>\r\n                  </button>\r\n                  <ul class=\"dropdown-menu dropdown-menu-end\" menu role=\"menu\">\r\n                    <li ng-repeat=\"subNavi in $ctrl.filterHidden($ctrl.currentPath[0].children)\">\r\n                      <a class=\"dropdown-item\" ng-href=\"{{subNavi.url}}\" class=\"dropdown-item\">{{ subNavi.title | sxyTranslate }}</a>\r\n                    </li>\r\n                  </ul>\r\n                </div>\r\n              </div>\r\n            </div>\r\n          </div>\r\n        </header>\r\n      </ng-transclude>\r\n      <ng-transclude ng-transclude-slot=\"nav\" ng-if=\"$ctrl.mode == 'horizontal'\">\r\n\r\n        <salaxy-navi-sitemap mode=\"{{$ctrl.mode}}\"></salaxy-navi-sitemap>\r\n      </ng-transclude>\r\n\r\n\r\n      <div id=\"salaxy-alert-container\"></div>\r\n      <ng-transclude ng-transclude-slot=\"main\">\r\n        <main salaxy-if-role=\"company\">\r\n          <div ng-class=\"$ctrl.current.isFullWidth ? 'container-fluid' : 'container-md'\" ng-if=\"!$ctrl.getDisabled()\" ng-view autoscroll=\"true\"></div>\r\n          <div class=\"container\" ng-if=\"$ctrl.getDisabled()\">\r\n            <div class=\"alert alert-info\" sxy-text=\"SALAXY.UI_Terms.pageDisabledAlert\"></div>\r\n          </div>\r\n        </main>\r\n        <main salaxy-if-role=\"!company\">\r\n          <div class=\"salaxy-navi-page-container salaxy-component salaxy-tpl-iframe-anon\" style=\"padding-left: 0;\">\r\n            <div class=\"container\" style=\"max-width: 600px; margin-top: 10vh;\">\r\n              <div class=\"alert alert-danger\">\r\n                <h2 sxy-text=\"SALAXY.UI_Terms.sessionExpired\"></h2>\r\n                <p class=\"lead text-muted\" sxy-text=\"SALAXY.UI_Terms.sessionExpiredEmbedded\"></p>\r\n                <div sxy-if-role=\"person\">\r\n                  <p>&nbsp;</p>\r\n                  <pre><small>ERROR: Authenticated as personal, not supported.</small></pre>\r\n                </div>\r\n                <div sxy-if-role=\"test\">\r\n                  \r\n                  <small>Test only:</small> <salaxy-login-button></salaxy-login-button>\r\n                </div>\r\n              </div>\r\n            </div>\r\n          </div>\r\n        </main>\r\n      </ng-transclude>\r\n    </content>\r\n  </div>\r\n</div>\r\n<div ng-if=\"!$ctrl.showFullPageLoader && $ctrl.layout == 'pro-customer'\" ng-cloak class=\"salaxy-component salaxy-navi-page-container iframe-container\">\r\n  <div class=\"salaxy-navi-main-container\">\r\n    <content>\r\n      <ng-transclude ng-transclude-slot=\"header\">\r\n      </ng-transclude>\r\n      <div id=\"salaxy-alert-container\"></div>\r\n      <ng-transclude ng-transclude-slot=\"main\">\r\n        <main class=\"pt-2\">\r\n          <div ng-class=\"$ctrl.current.isFullWidth ? 'container-fluid' : 'container-md'\"  ng-if=\"!$ctrl.getDisabled()\" ng-view autoscroll=\"true\"></div>\r\n          <div class=\"container-md\" ng-if=\"$ctrl.getDisabled()\">\r\n            <div class=\"alert alert-info\" sxy-text=\"SALAXY.UI_Terms.pageDisabledAlert\"></div>\r\n          </div>\r\n        </main>\r\n      </ng-transclude>\r\n    </content>\r\n  </div>\r\n</div>\r\n</div>\r\n</main>\r\n</ng-transclude>\r\n</content>\r\n</div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/helpers/Spinner.html\",`<div ng-cloak ng-class=\"{'sxy-spinner-full-screen-container': $ctrl.fullScreen, 'salaxy-component': true, 'salaxy-spinner': true, }\">\r\n  <div class=\"sxy-spinner-container\">\r\n    <div class=\"sxy-spinner\">\r\n      <svg class=\"sxy-spinner-bg\" viewBox=\"0 0 64 64\"><circle cx=\"32\" cy=\"32\" r=\"26\"></circle></svg>\r\n      <svg class=\"sxy-spinner-spin\" viewBox=\"0 0 64 64\">\r\n        <circle transform=\"translate(32,32)\" r=\"26\"></circle>\r\n      </svg>\r\n    </div>\r\n    <h3 ng-if=\"$ctrl.heading\" class=\"spinner-heading\">{{$ctrl.getHeading()}}</h3>\r\n    <p style=\"white-space: pre;\" ng-if=\"$ctrl.text\" class=\"spinner-text\">{{$ctrl.text | sxyTranslate}}</p>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/helpers/Tab.html\",`<div class=\"tabpane\" ng-class=\"{ active: $ctrl.selected}\" ng-show=\"$ctrl.selected\" ng-transclude=\"content\"></div>\r\n<div ng-transclude=\"heading\"></div>\r\n`);\n\n $templateCache.put(\"salaxy-components/helpers/TabButtons.html\",`<div class=\"tabs-buttons\" id=\"tabs-buttons-{{$ctrl.tabsId}}\">\r\n  <ul class=\"nav nav-tabs\">\r\n    <li class=\"nav-item\" ng-repeat=\"tab in $ctrl.options\" ng-if=\"!tab.hidden\">\r\n      <button\r\n        class=\"nav-link\"\r\n        id=\"{{ tab.value }}-tab-button\"\r\n        ng-disabled=\"tab.disabled\"\r\n        type=\"button\"\r\n        ng-click=\"$ctrl.showTab(tab.value)\"\r\n        ng-class=\"{ active: $ctrl.currentTab === tab.value }\">\r\n        {{ $ctrl.getTabText(tab.text) }}\r\n      </button>\r\n    </li>\r\n  </ul>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/helpers/Tabs.html\",`<div>\r\n    <ul class=\"nav nav-tabs\">\r\n        <li ng-repeat=\"tab in $ctrl.tabs\" ng-class=\"{ active: tab.selected, disabled: tab.disable}\" class=\"nav-item\">\r\n            <a href class=\"nav-link\" ng-click=\"$ctrl.select(tab, $event)\" salaxy-append-node=\"tab.headingElement\">{{tab.heading}}</a>\r\n        </li>\r\n    </ul>\r\n    <div class=\"tab-content\">\r\n        <ng-transclude></ng-transclude>\r\n    </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/helpers/UiTranslator.html\",`<div class=\"salaxy-component salaxy-ui-translator\">\r\n  <salaxy-spinner ng-if=\"$ctrl.isLoading\" heading=\"SALAXY.UI_Terms.loading\" text=\"SALAXY.UI_Terms.pleaseWait\"></salaxy-spinner>\r\n  <div ng-if=\"!$ctrl.isLoading && $ctrl.allKeyValues.length &lt; 1\" class=\"alert alert-danger\">\r\n    No rows for filter: {{$ctrl.filter}}\r\n  </div>\r\n  <div ng-if=\"$ctrl.allKeyValues.length > 0\">\r\n    <div ng-if=\"$ctrl.mode == 'fieldset'\">\r\n      <fieldset class=\"form-horizontal\" ng-repeat=\"row in $ctrl.allKeyValues | limitTo: 10\">\r\n        <legend>\r\n          <button ng-if=\"$ctrl.canDeleteFromText(row.fullKey)\" ng-click=\"$ctrl.removeFromTexts(row.fullKey)\" class=\"btn btn-danger btn-xs float-end\"><i class=\"bi bi-trash\"></i></button>\r\n          {{row.fullKey}}\r\n        </legend>\r\n        <salaxy-input ng-if=\"$ctrl.checkIfExistsInTexts(row.fullKey, 'fi')\" name=\"fi\" ng-change=\"$ctrl.updateTexts()\" placeholder=\"{{row.fi}}\" ng-model=\"$ctrl.getEditableText(row.fullKey).fi\" label=\"Suomi\"></salaxy-input>\r\n        <salaxy-input ng-if=\"!$ctrl.checkIfExistsInTexts(row.fullKey, 'fi')\" name=\"fi\" ng-click=\"$ctrl.addToTexts(row.fullKey, 'fi')\" ng-model=\"row.fi\" read-only=\"true\" label=\"Suomi\"></salaxy-input>\r\n        <salaxy-input ng-if=\"$ctrl.checkIfExistsInTexts(row.fullKey, 'en')\" name=\"en\" ng-change=\"$ctrl.updateTexts()\" placeholder=\"{{row.en}}\" ng-model=\"$ctrl.getEditableText(row.fullKey).en\" label=\"English\"></salaxy-input>\r\n        <salaxy-input ng-if=\"!$ctrl.checkIfExistsInTexts(row.fullKey, 'en')\" name=\"en\" ng-click=\"$ctrl.addToTexts(row.fullKey, 'en')\" ng-model=\"row.en\" read-only=\"true\" label=\"English\"></salaxy-input>\r\n        <salaxy-input ng-if=\"$ctrl.checkIfExistsInTexts(row.fullKey, 'sv')\" name=\"sv\" ng-change=\"$ctrl.updateTexts()\" placeholder=\"{{row.sv}}\" ng-model=\"$ctrl.getEditableText(row.fullKey).sv\" label=\"Svenska\"></salaxy-input>\r\n        <salaxy-input ng-if=\"!$ctrl.checkIfExistsInTexts(row.fullKey, 'sv')\" name=\"sv\" ng-click=\"$ctrl.addToTexts(row.fullKey, 'sv')\" ng-model=\"row.sv\" read-only=\"true\" label=\"Svenska\"></salaxy-input>\r\n      </fieldset>\r\n      <div class=\"alert alert-warning\" ng-if=\"$ctrl.allKeyValues.length > 10\">ERR: More than 10 translation key values, showing max 10.</div>\r\n    </div>\r\n    <div ng-if=\"$ctrl.mode != 'fieldset'\">\r\n      <div class=\"btn-toolbar\" role=\"toolbar\" aria-label=\"Report options\">\r\n        <div class=\"btn-group btn-group-sm dropdown\">\r\n          <button id=\"single-button\" type=\"button\" class=\"btn btn-secondary dropdown-toggle\" data-bs-toggle=\"dropdown\" ng-disabled=\"disabled\">\r\n            Avaimet:\r\n          </button>\r\n          <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"single-button\">\r\n            <li role=\"menuitem\">\r\n              <a href=\"\" ng-click=\"$ctrl.showCols.fullKey = !$ctrl.showCols.fullKey\" class=\"dropdown-item\">\r\n                <i ng-if=\"$ctrl.showCols.fullKey\" class=\"bi bi-x-lg\" aria-hidden=\"true\"></i>\r\n                Koko avain\r\n              </a>\r\n            </li>\r\n            <li role=\"menuitem\">\r\n              <a href=\"\" ng-click=\"$ctrl.showCols.shortKey = !$ctrl.showCols.shortKey\" class=\"dropdown-item\">\r\n                <i ng-if=\"$ctrl.showCols.shortKey\" class=\"bi bi-x-lg\" aria-hidden=\"true\"></i>\r\n                Lyhyt avain\r\n              </a>\r\n            </li>\r\n            <li role=\"menuitem\">\r\n              <a href=\"\" ng-click=\"$ctrl.showCols.fileName = !$ctrl.showCols.fileName\" class=\"dropdown-item\">\r\n                <i ng-if=\"$ctrl.showCols.fileName\" class=\"bi bi-x-lg\" aria-hidden=\"true\"></i>\r\n                Käännöstiedosto / pääryhmä\r\n              </a>\r\n              </li>\r\n            <li role=\"menuitem\">\r\n              <a href=\"\" ng-click=\"$ctrl.showCols.keyComponent = !$ctrl.showCols.keyComponent\" class=\"dropdown-item\">\r\n                <i ng-if=\"$ctrl.showCols.keyComponent\" class=\"bi bi-x-lg\" aria-hidden=\"true\"></i>\r\n                Komponentti / tiedoston ryhmittely\r\n              </a>\r\n            </li>\r\n            <li role=\"menuitem\">\r\n              <a href=\"\" ng-click=\"$ctrl.showCols.keyValue = !$ctrl.showCols.keyValue\" class=\"dropdown-item\">\r\n                <i ng-if=\"$ctrl.showCols.keyValue\" class=\"bi bi-x-lg\" aria-hidden=\"true\"></i>\r\n                3. taso (1. avain)\r\n              </a>\r\n            </li>\r\n          </ul>\r\n        </div>\r\n        <div class=\"btn-group btn-group-sm dropdown ms-1\">\r\n          <button id=\"single-button\" type=\"button\" class=\"btn btn-secondary dropdown-toggle\" data-bs-toggle=\"dropdown\" ng-disabled=\"disabled\">\r\n            Kieli:\r\n          </button>\r\n          <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"single-button\">\r\n            <li role=\"menuitem\">\r\n              <a href=\"\" ng-click=\"$ctrl.showCols.fi = !$ctrl.showCols.fi\" class=\"dropdown-item\">\r\n                <i ng-if=\"$ctrl.showCols.fi\" class=\"bi bi-x-lg\" aria-hidden=\"true\"></i> \r\n                Suomi\r\n              </a>\r\n            </li>\r\n            <li role=\"menuitem\">\r\n              <a href=\"\" ng-click=\"$ctrl.showCols.en = !$ctrl.showCols.en\" class=\"dropdown-item\">\r\n                <i ng-if=\"$ctrl.showCols.en\" class=\"bi bi-x-lg\" aria-hidden=\"true\"></i> \r\n                Englanti\r\n              </a>\r\n            </li>\r\n            <li role=\"menuitem\">\r\n              <a href=\"\" ng-click=\"$ctrl.showCols.sv = !$ctrl.showCols.sv\" class=\"dropdown-item\">\r\n                <i ng-if=\"$ctrl.showCols.sv\" class=\"bi bi-x-lg\" aria-hidden=\"true\"></i> \r\n                Ruotsi\r\n              </a>\r\n            </li>\r\n          </ul>\r\n        </div>\r\n        <div class=\"btn-group btn-group-sm ms-sm-auto\" role=\"group\" aria-label=\"Json\">\r\n          <button sxy-if-role=\"!anon\" type=\"button\" class=\"btn btn-secondary\" ng-click=\"$ctrl.downloadTexts()\">\r\n            <span class=\"d-none d-md-inline-block\">Lataa muutos JSON</span>\r\n            <i class=\"bi bi-file-earmark\" aria-hidden=\"true\"></i>\r\n          </button>\r\n        </div>\r\n      </div>\r\n      <table class=\"table table-striped\">\r\n        <thead>\r\n          <tr>\r\n            <th ng-if=\"$ctrl.showCols.fullKey\">\r\n              <salaxy-input label-type=\"basic\" name=\"fullKey\" label=\"Koko avain\" ng-model=\"$ctrl.listFilter.fullKey\"></salaxy-input>\r\n            </th>\r\n            <th ng-if=\"$ctrl.showCols.shortKey\">\r\n              <salaxy-input label-type=\"basic\" name=\"shortKey\" label=\"Lyhyt avain\" ng-model=\"$ctrl.listFilter.shortKey\"></salaxy-input>\r\n            </th>\r\n            <th ng-if=\"$ctrl.showCols.keyComponent\">\r\n              <salaxy-input label-type=\"basic\" name=\"keyComponent\" label=\"Komponenttiavain\" ng-model=\"$ctrl.listFilter.keyComponent\"></salaxy-input>\r\n            </th>\r\n            <th ng-if=\"$ctrl.showCols.fi\">\r\n              <salaxy-input label-type=\"basic\" name=\"fi\" label=\"Suomi\" ng-model=\"$ctrl.listFilter.fi\"></salaxy-input>\r\n            </th>\r\n            <th ng-if=\"$ctrl.showCols.en\">\r\n              <salaxy-input label-type=\"basic\" name=\"en\" label=\"Englanti\" ng-model=\"$ctrl.listFilter.en\"></salaxy-input>\r\n            </th>\r\n            <th ng-if=\"$ctrl.showCols.sv\">\r\n              <salaxy-input label-type=\"basic\" name=\"sv\" label=\"Ruotsi\" ng-model=\"$ctrl.listFilter.sv\"></salaxy-input>\r\n            </th>\r\n            <th></th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr ng-repeat=\"row in $ctrl.allKeyValues | filter: $ctrl.listFilter | limitTo: 100 \">\r\n            <td style=\"word-break:break-word;\" ng-if=\"$ctrl.showCols.fullKey\">{{row.fullKey}}</td>\r\n            <td style=\"word-break:break-word;\" ng-if=\"$ctrl.showCols.shortKey\">{{row.shortKey}}</td>\r\n            <td style=\"word-break:break-word;\" ng-if=\"$ctrl.showCols.keyComponent\">{{row.keyComponent}}</td>\r\n            <td style=\"word-break:break-word;\" ng-if=\"$ctrl.showCols.keyValue\">{{row.keyValue}}</td>\r\n            <td style=\"word-break:break-word;\" ng-if=\"$ctrl.showCols.fi && $ctrl.checkIfExistsInTexts(row.fullKey, 'fi')\">\r\n              <salaxy-input name=\"fi\" ng-change=\"$ctrl.updateTexts()\" placeholder=\"{{row.fi}}\" ng-model=\"$ctrl.getEditableText(row.fullKey).fi\" label-type=\"plain\"></salaxy-input>\r\n            </td>\r\n            <td style=\"word-break:break-word;\" ng-if=\"$ctrl.showCols.fi && !$ctrl.checkIfExistsInTexts(row.fullKey, 'fi')\" ng-click=\"$ctrl.addToTexts(row.fullKey, 'fi')\">{{row.fi}}\r\n            </td>\r\n  \r\n            <td style=\"word-break:break-word;\" ng-if=\"$ctrl.showCols.en && $ctrl.checkIfExistsInTexts(row.fullKey, 'en')\">\r\n              <salaxy-input name=\"en\" ng-change=\"$ctrl.updateTexts()\" placeholder=\"{{row.en}}\" ng-model=\"$ctrl.getEditableText(row.fullKey).en\" label-type=\"plain\"></salaxy-input>\r\n            </td>\r\n            <td style=\"word-break:break-word;\" ng-if=\"$ctrl.showCols.en && !$ctrl.checkIfExistsInTexts(row.fullKey, 'en')\" ng-click=\"$ctrl.addToTexts(row.fullKey, 'en')\">{{row.en}}\r\n            </td>\r\n            <td style=\"word-break:break-word;\" ng-if=\"$ctrl.showCols.sv && $ctrl.checkIfExistsInTexts(row.fullKey, 'sv')\">\r\n              <salaxy-input name=\"sv\" ng-change=\"$ctrl.updateTexts()\" placeholder=\"{{row.sv}}\" ng-model=\"$ctrl.getEditableText(row.fullKey).sv\" label-type=\"plain\"></salaxy-input>\r\n            </td>\r\n            <td style=\"word-break:break-word;\" ng-if=\"$ctrl.showCols.sv && !$ctrl.checkIfExistsInTexts(row.fullKey, 'sv')\" ng-click=\"$ctrl.addToTexts(row.fullKey, 'sv')\">{{row.sv}}\r\n            </td>\r\n            <td ng-if=\"$ctrl.canDeleteFromText(row.fullKey)\"><button ng-click=\"$ctrl.removeFromTexts(row.fullKey)\" class=\"btn btn-danger\"><i class=\"bi bi-trash\"></i></button>\r\n            </td>\r\n            <td ng-if=\"!$ctrl.canDeleteFromText(row.fullKey)\"></td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/invoices/CompanyInvoices.html\",`<div class=\"salaxy-component salaxy-company-invoices\">\r\n  <salaxy-odata-table crud-controller=\"CompanyInvoicesController as $crud\" options=\"$ctrl.getListOptions()\" crud-bindings=\"{ channel: $ctrl.channel }\"\r\n    template-url=\"salaxy-components/odata/lists/InvoicesCompany.html\">\r\n  </salaxy-odata-table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/invoices/CreditTransfer.html\",`<div class=\"salaxy-component salaxy-credit-transfer\">\r\n  <div class=\"salaxy-credit-transfer-official\" ng-if=\"$ctrl.mode != 'barcode-copy'\">\r\n    <div class=\"sct-row sct-row1\">\r\n      <div class=\"sct-col sct-col1\">\r\n        <div class=\"sct-row sct-row1\" sxy-html=\"SALAXY.NG1.CreditTransferComponent.receiverIban.html\"></div>\r\n        <div class=\"sct-row sct-row2\" sxy-html=\"SALAXY.NG1.CreditTransferComponent.receiver.html\"></div>\r\n        <div class=\"sct-row sct-row3\">\r\n          <div class=\"sct-label-payer\" sxy-html=\"SALAXY.NG1.CreditTransferComponent.payerInfo.html\"></div>\r\n          <div class=\"sct-label-credit-transfer\" sxy-text=\"SALAXY.NG1.CreditTransferComponent.creditTransfer\"></div>\r\n          <div class=\"sct-label-signature\" sxy-html=\"SALAXY.NG1.CreditTransferComponent.signature.html\"></div>\r\n        </div>\r\n        <div class=\"sct-row sct-row4\" sxy-html=\"SALAXY.NG1.CreditTransferComponent.fromAccount.html\"></div>\r\n      </div>\r\n      <div class=\"sct-col sct-col2\">\r\n        <div class=\"sct-row sct-row1\">\r\n          <!-- Recipient account numbers (IBAN), max 4 lines -->\r\n          <div class=\"sct-label-iban\" sxy-text=\"SALAXY.NG1.CreditTransferComponent.iban\"></div>\r\n          <div class=\"sct-filled-content\">\r\n            {{ $ctrl.invoice.recipient.iban | sxyIban }}\r\n          </div>\r\n          <div class=\"sct-label-iban\" sxy-text=\"BIC\"></div>\r\n          <div class=\"sct-filled-content\">\r\n            {{ $ctrl.getBicForIban($ctrl.invoice.recipient.iban) }}\r\n          </div>\r\n        </div>\r\n        <div class=\"sct-row sct-row2\">\r\n          <div class=\"sct-filled-content sct-filled-content-main\">\r\n            <!-- Recipient, max 3 lines -->\r\n            {{ $ctrl.invoice.recipient.fullName }}<br> {{ $ctrl.invoice.recipient.contact.street }} {{ $ctrl.invoice.recipient.contact.postalCode }} {{ $ctrl.invoice.recipient.contact.city }}\r\n          </div>\r\n        </div>\r\n        <div class=\"sct-row sct-row3\">\r\n          <div class=\"sct-filled-content sct-filled-content-main\">\r\n            <!-- Payer’s name and address -->\r\n            {{ $ctrl.invoice.payer.avatar.displayName }}<br> {{ $ctrl.invoice.payer.contact.street }}<br> {{ $ctrl.invoice.payer.contact.postalCode }} {{ $ctrl.invoice.payer.contact.city }}\r\n          </div>\r\n          <div class=\"sct-filled-content sct-signature\">\r\n            <!-- Signature -->\r\n          </div>\r\n          <div class=\"sct-guideline-signature\"></div>\r\n        </div>\r\n        <div class=\"sct-row sct-row4\">\r\n          <div class=\"sct-filled-content sct-filled-content-main\">\r\n            <!-- From account no. -->\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div class=\"sct-col sct-col3\">\r\n        <div class=\"sct-row sct-row1\" ng-if=\"$ctrl.getQrCode(row) !== 'loading' && $ctrl.getQrCode(row) !== 'error'\">\r\n          <div class=\"sct-qrcode\" >\r\n            <div ng-bind-html=\"$ctrl.getQrCode(row)\"></div>\r\n          </div>\r\n          <div class=\"sct-filled-content-message\">\r\n            <ng-transclude ng-transclude-slot=\"message\">\r\n              <span>{{ $ctrl.invoice.header.message }}</span>\r\n            </ng-transclude>\r\n          </div>\r\n        </div>\r\n        <div class=\"sct-row sct-row1\" ng-if=\"$ctrl.getQrCode(row) === 'error'\">\r\n          <div class=\"sct-filled-content sct-filled-content-main\">\r\n            <ng-transclude ng-transclude-slot=\"message\">\r\n              <span>{{ $ctrl.invoice.header.message }}</span>\r\n            </ng-transclude>\r\n          </div>\r\n        </div>\r\n        <div class=\"sct-row sct-row2\">\r\n          <div class=\"sct-col sct-col1\" sxy-html=\"SALAXY.NG1.CreditTransferComponent.refNumber.html\"></div>\r\n          <div class=\"sct-col sct-col2\">\r\n            <div class=\"sct-filled-content sct-filled-content-main\">\r\n              <!-- Ref. nr -->\r\n              {{ $ctrl.invoice.header.referenceNumber | sxyIban }}\r\n            </div>\r\n          </div>\r\n        </div>\r\n        <div class=\"sct-row sct-row3\">\r\n          <div class=\"sct-col sct-col1\" sxy-html=\"SALAXY.NG1.CreditTransferComponent.dueDate.html\"></div>\r\n          <div class=\"sct-col sct-col2\">\r\n            <div class=\"sct-filled-content sct-filled-content-main\">\r\n              <!-- Due date -->\r\n              {{ $ctrl.invoice.header.dueDate | sxyDate }}\r\n            </div>\r\n          </div>\r\n          <div class=\"sct-col sct-col3\">\r\n            <div class=\"sct-label-euro\" sxy-text=\"SALAXY.NG1.CreditTransferComponent.euro\"></div>\r\n            <div class=\"sct-filled-content sct-filled-content-main\">\r\n              <!-- Euro amount -->\r\n              {{ $ctrl.invoice.header.total | currency }}\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"sct-row sct-row2\">\r\n      <div id=\"barcode\">\r\n        <!-- Barcode can be shown only with FI IBAN -->\r\n         <div ng-bind-html=\"$ctrl.getBarcode()\"></div>\r\n      </div>\r\n      <!--\r\n        NOTE: Terms of clearance is part of original specification: https://www.finanssiala.fi/wp-content/uploads/2021/03/Tilisiirto-opas.pdf.\r\n        It is removed because it has no real value today and it makes reading barcode difficult.\r\n      -->\r\n      <!--\r\n        <div id=\"terms-of-clearance\">\r\n          Maksu välitetään saajalle maksujenvälityksen ehtojen mukaisesti ja vain maksajan ilmoittaman tilinumeron perusteella.\r\n          <br> Betalningen förmedlas till mottagaren engligt villkoren för betalningsförmedling och endast till det kontonummer som betalaren angivit.\r\n        </div>\r\n      -->\r\n    </div>\r\n  </div>\r\n  <div class=\"barcodeform-container d-print-none\" ng-if=\"$ctrl.mode != 'official'\">\r\n    <form name=\"barcodeForm\" id=\"barcodeForm\" class=\"form-horizontal\">\r\n      <p sxy-text=\"SALAXY.NG1.CreditTransferComponent.transferDescription\" ng-if=\"$ctrl.mode != 'barcode-copy' && !$ctrl.isInternationalIban()\"></p>\r\n      <p ng-if=\"$ctrl.mode != 'barcode-copy' && $ctrl.isInternationalIban()\">&nbsp;</p>    \r\n      <div class=\"row\" ng-if=\"!$ctrl.isInternationalIban()\">\r\n        <div class=\"col-sm-10\">\r\n          <salaxy-input name=\"{{ 'barcode' + $ctrl.getId() }}\" label=\"SALAXY.NG1.CreditTransferComponent.barcodeLabel\" readonly=\"true\" label-cols=\"col-sm-4\" ng-model=\"$ctrl.bcValue\"></salaxy-input>\r\n        </div>\r\n        <div class=\"col-sm-2\">\r\n          <button class=\"btn btn-default btn-block\" ng-click=\"$ctrl.copyBarcode()\" sxy-text=\"SALAXY.UI_Terms.copyToClipboard\"></button>\r\n        </div>\r\n      </div>\r\n    </form>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/invoices/InvoiceAlerts.html\",`<div class=\"row payment-started-alert\">\r\n  <div class=\"col-xs-12\">\r\n    <salaxy-alert type=\"warning\" ng-repeat=\"paymentChannel in $ctrl.groupedPaymentChannelResult\">\r\n      <main>\r\n        <div ng-bind-html=\"$ctrl.getpaymentChannelInfoHtml(paymentChannel)\"></div>\r\n      </main>\r\n    </salaxy-alert>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/invoices/InvoiceEdit.html\",`<div class=\"salaxy-component salaxy-invoice-edit\">\r\n  <salaxy-spinner ng-if=\"$ctrl.isLoading\"></salaxy-spinner>\r\n  <div class=\"alert alert-danger\" ng-if=\"!$ctrl.isLoading && !$ctrl.current\" sxy-text=\"SALAXY.NG1.InvoiceEditComponent.error\"></div>\r\n  <form name=\"statusForm\" ng-if=\"$ctrl.current\" ng-submit=\"$ctrl.requestStatusUpdate()\">\r\n    <div class=\"form-horizontal\">\r\n      <h2 sxy-text=\"SALAXY.NG1.InvoiceEditComponent.headingAlt\"></h2>\r\n      <p sxy-text=\"SALAXY.NG1.InvoiceEditComponent.headingInfoAlt\"></p>\r\n      <salaxy-input-enum label=\"SALAXY.NG1.InvoiceEditComponent.channel\" read-only=\"true\" name=\"paymentChannel\" ng-model=\"$ctrl.current.header.channel\" enum=\"PaymentChannel\"></salaxy-input-enum>\r\n      <salaxy-input-enum label=\"SALAXY.NG1.InvoiceEditComponent.invoiceStatus\" read-only=\"!( ( ('test' | sxyIsInRole) || ('pro' | sxyIsInRole) ) && ($ctrl.current.header.channel == 'palkkausManual' || $ctrl.current.header.channel == 'talenomManual' || $ctrl.current.header.channel == 'palkkausInvoices' || $ctrl.current.header.channel == 'kitsas' || $ctrl.current.header.channel == 'palkkausWS' || $ctrl.current.header.channel == 'palkkausPSD'))\" name=\"requestedStatus\" ng-model=\"$ctrl.requestedStatus\" enum=\"InvoiceStatus\" required></salaxy-input-enum>\r\n    </div>\r\n    <div>\r\n      <button type=\"submit\" class=\"btn btn-primary float-end\" ng-disabled=\"!statusForm.$valid || !( ( ('test' | sxyIsInRole) || ('pro' | sxyIsInRole) ) && ($ctrl.current.header.channel == 'palkkausManual' || $ctrl.current.header.channel == 'talenomManual' || $ctrl.current.header.channel == 'palkkausInvoices' || $ctrl.current.header.channel == 'kitsas' || $ctrl.current.header.channel == 'palkkausWS' || $ctrl.current.header.channel == 'palkkausPSD'))\" sxy-text=\"SALAXY.NG1.InvoiceEditComponent.updateStatusBtn\"></button>\r\n      <button ng-if=\"'test' | sxyIsInRole\" type=\"button\" ng-click=\"$ctrl.delete()\" class=\"btn btn-danger\" sxy-text=\"SALAXY.NG1.InvoiceEditComponent.deleteInvoice\" pre=\"(Test only): \"></button>\r\n      <button ng-if=\"'test' | sxyIsInRole\" type=\"button\" ng-click=\"$ctrl.deleteWithBusinessObjects()\" class=\"btn btn-danger\" sxy-text=\"SALAXY.NG1.InvoiceEditComponent.deleteInvoiceWithCals\" pre=\"(Test only): \"></button>\r\n    </div>\r\n  </form>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/invoices/InvoiceList.html\",`<div class=\"salaxy-component salaxy-invoice-list\" ng-switch=\"$ctrl.mode\">\r\n  <salaxy-odata-table ng-switch-when=\"panel\" crud-controller=\"InvoiceCrudController as $crud\" options=\"$ctrl.getListOptions()\"\r\n    template-url=\"salaxy-components/odata/lists/InvoicesPanel.html\">\r\n  </salaxy-odata-table>\r\n\r\n  <salaxy-odata-table ng-switch-when=\"sepa\" crud-controller=\"InvoiceSepaController as $crud\"\r\n    template-url=\"salaxy-components/odata/lists/InvoicesSepa.html\">\r\n  </salaxy-odata-table>\r\n\r\n  <salaxy-odata-table ng-switch-when=\"person\" crud-controller=\"InvoiceCrudController as $crud\" options=\"$ctrl.getListOptions()\"\r\n    template-url=\"salaxy-components/odata/lists/InvoicesPerson.html\">\r\n  </salaxy-odata-table>\r\n  \r\n  <div ng-switch-default>\r\n    <salaxy-odata-table crud-controller=\"InvoiceCrudController as $crud\" options=\"$ctrl.getListOptions()\" template-url=\"salaxy-components/odata/lists/Invoices.html\">\r\n    </salaxy-odata-table>\r\n  </div>\r\n\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/invoices/InvoicePaymentList.html\",`<div class=\"salaxy-component salaxy-invoice-list\">\r\n  <salaxy-odata-table crud-controller=\"InvoicePaymentListController as $crud\"\r\n    template-url=\"salaxy-components/odata/lists/InvoicePaymentList.html\">\r\n  </salaxy-odata-table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/invoices/InvoicePreview.html\",`<div ng-init=\"$ctrl.view = 'full'\">\r\n  <salaxy-spinner ng-if=\"!$ctrl.current && $ctrl.isLoading\"></salaxy-spinner>\r\n  <div class=\"alert alert-danger\" ng-if=\"!$ctrl.isLoading && !$ctrl.current\" sxy-text=\"SALAXY.NG1.InvoicePreviewComponent.error\"></div>\r\n  \r\n  <div ng-if=\"$ctrl.current\">\r\n    <div class=\"mb-3\">\r\n      <div class=\"btn-group btn-group-sm\" role=\"group\">\r\n        <salaxy-toggle-buttons\r\n          ng-model=\"$ctrl.view\"\r\n          options=\"[\r\n            { value: 'full', label: 'SALAXY.NG1.InvoicePreviewComponent.fullInvoice' },\r\n            { value: 'partial', label: 'SALAXY.NG1.InvoicePreviewComponent.tableInvoice' }\r\n          ]\"\r\n          type=\"inline\"></salaxy-toggle-buttons>\r\n      </div>\r\n      <a ng-href=\"{{$ctrl.getContentUrl($ctrl.current.id, true)}}\" target=\"_blank\"class=\"btn btn-primary float-end\">\r\n        <i class=\"bi bi-file-earmark-pdf\"></i> <span sxy-text=\"SALAXY.NG1.InvoicePreviewComponent.showFile\"></span>\r\n      </a>\r\n    </div>\r\n    <salaxy-invoice-report invoice=\"$ctrl.current\" apply-site-styles=\"$ctrl.view == 'partial'\"></salaxy-invoice-report>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/invoices/InvoiceReport.html\",`<div class=\"salaxy-component salaxy-calc-report\">\r\n  <div class=\"row\" ng-if=\"$ctrl.applySiteStyles\">\r\n    <div class=\"col-sm-6\">\r\n      <table>\r\n        <tr>\r\n          <td colspan=\"2\"><small><strong sxy-text=\"SALAXY.NG1.InvoicePreviewComponent.recipient\" ps=\":\"></strong></small></td>\r\n        </tr>\r\n        <tr>\r\n          <td>\r\n            <salaxy-avatar avatar=\"$ctrl.invoice.recipient.beneficiary.avatar\" style=\"font-size: 64px;\"></salaxy-avatar>\r\n          </td>\r\n          <td>\r\n            <div><strong>{{ $ctrl.invoice.recipient.fullName }}</strong></div>\r\n            <div>\r\n              {{ $ctrl.invoice.recipient.contact.street }}<br /> {{ $ctrl.invoice.recipient.contact.postalCode }} {{ $ctrl.invoice.recipient.contact.city }}\r\n            </div>\r\n          </td>\r\n        </tr>\r\n        <tr>\r\n          <td>&nbsp;</td>\r\n        </tr>\r\n        <tr>\r\n          <td colspan=\"2\"><small><strong sxy-text=\"SALAXY.NG1.InvoicePreviewComponent.payer\" ps=\":\"></strong></small></td>\r\n        </tr>\r\n        <tr>\r\n          <td>\r\n            <salaxy-avatar avatar=\"$ctrl.invoice.payer.avatar\" style=\"font-size: 64px;\"></salaxy-avatar>\r\n          </td>\r\n          <td>\r\n            <div><strong>{{ $ctrl.invoice.payer.avatar.displayName }}</strong></div>\r\n            <div>\r\n              {{ $ctrl.invoice.payer.contact.street }}<br /> {{ $ctrl.invoice.payer.contact.postalCode }} {{ $ctrl.invoice.payer.contact.city }}\r\n            </div>\r\n          </td>\r\n        </tr>\r\n      </table>\r\n    </div>\r\n    <div class=\"col-sm-6\">\r\n      <p style=\"font-size: 24px; font-weight: bold; text-transform: uppercase;\">{{ \"SALAXY.NG1.InvoiceReportComponent.invoice.title\" | sxyTranslate }}</p>\r\n      <p style=\"font-size: 16px; font-weight: bold; text-transform: uppercase;\">{{ (\"SALAXY.ENUM.InvoiceType.\" + $ctrl.invoice.header.type + \".label\") | sxyTranslate }}</p>\r\n      <div > </div>\r\n      <table>\r\n        <tr>\r\n          <td sxy-text=\"SALAXY.NG1.InvoicePreviewComponent.date\" ps=\":\"></td>\r\n          <td>{{ $ctrl.invoice.header.date | sxyDate }}</td>\r\n        </tr>\r\n        <tr>\r\n          <td sxy-text=\"SALAXY.NG1.InvoicePreviewComponent.dueDate\" ps=\":\"></td>\r\n          <td>{{ $ctrl.invoice.header.dueDate | sxyDate }}</td>\r\n        </tr>\r\n        <tr>\r\n          <td sxy-text=\"SALAXY.NG1.InvoicePreviewComponent.referenceNumber\" ps=\":\"></td>\r\n          <td>{{ $ctrl.invoice.header.referenceNumber || \"-\" }}</td>\r\n        </tr>\r\n        <tr>\r\n          <td sxy-text=\"SALAXY.NG1.InvoicePreviewComponent.iban\" ps=\":\"></td>\r\n          <td ng-if=\"!$ctrl.isPreviewInvoice()\">{{ $ctrl.invoice.recipient.iban | sxyIban }}</td>\r\n          <td ng-if=\"$ctrl.isPreviewInvoice()\">{{ 'SALAXY.REPORTS.invoice.heading.preview' | sxyTranslate }}</td>\r\n        </tr>\r\n        <tr>\r\n          <td sxy-text=\"SALAXY.NG1.InvoicePreviewComponent.status\" ps=\":\"></td>\r\n          <td>{{ \"InvoiceStatus.\" + $ctrl.invoice.header.status | sxyEnum }}</td>\r\n        </tr>\r\n      </table>\r\n    </div>\r\n  </div>\r\n  <div ng-class=\"{'report-table-html': $ctrl.applySiteStyles}\"></div>\r\n    <div ng-bind-html=\"$ctrl.html\" class=\"report-binder table-responsive\"></div>\r\n  </div>\r\n</div>\r\n`);\n\n $templateCache.put(\"salaxy-components/invoices/InvoicesCreate.html\",`<div class=\"salaxy-component salaxy-invoices-create\">\r\n  <div ng-if=\"!$ctrl.currentType\" class=\"alert alert-error\">Error: {{ $ctrl.current ? \"Invalid object\" : \"No object\" }} bound in InvoicesCreateController</div>\r\n  <div ng-if=\"$ctrl.currentType\">\r\n    <div ng-switch=\"$ctrl.uiStatus\">\r\n      <div ng-switch-when=\"invalid\">\r\n        <salaxy-validation-summary api-validation=\"$ctrl.current.result.validation\">\r\n          <div class=\"alert alert-danger\" sxy-text=\"SALAXY.NG1.InvoicesCreateComponent.uiStatusInvalid\"></div>\r\n        </salaxy-validation-summary>\r\n      </div>\r\n      <div ng-switch-when=\"loading\">\r\n        <salaxy-spinner heading=\"SALAXY.NG1.InvoicesCreateComponent.uiStatusLoading\"></salaxy-spinner>\r\n      </div>\r\n      <div ng-switch-when=\"created\" ng-switch=\"$ctrl.paymentStatus\">\r\n        <p class=\"lead\" ng-switch-when=\"inProgress\" sxy-html=\"SALAXY.NG1.InvoicesCreateComponent.uiStatusCreated.inProgress.html\"></p>\r\n        <div class=\"alert alert-success\" ng-switch-when=\"paid\" sxy-text=\"SALAXY.NG1.InvoicesCreateComponent.uiStatusCreated.paid\" ps=\".\"></div>\r\n        <div class=\"alert alert-danger\" ng-switch-when=\"exceptions\" sxy-text=\"SALAXY.NG1.InvoicesCreateComponent.uiStatusCreated.exceptions\"></div>\r\n        <div class=\"alert alert-danger\" ng-switch-when=\"canceled\" sxy-text=\"SALAXY.NG1.InvoicesCreateComponent.uiStatusCreated.canceled\"></div>\r\n        <ng-include src=\"'salaxy-components/invoices/InvoicesCreate_Table.html'\"></ng-include>\r\n      </div>\r\n      <div ng-switch-when=\"supportedChannel\">\r\n        <div sxy-html=\"{{$ctrl.intro}}\"></div>\r\n        <ng-include src=\"'salaxy-components/invoices/InvoicesCreate_Table.html'\"></ng-include>\r\n      </div>\r\n      <div ng-switch-when=\"undefined\">\r\n        <div class=\"alert alert-error\" sxy-text=\"SALAXY.NG1.InvoicesCreateComponent.uiStatusDefault\"></div>\r\n      </div>\r\n      <div ng-switch-when=\"userCanceled\">\r\n        <div class=\"alert alert-error\" sxy-text=\"SALAXY.NG1.InvoicesCreateComponent.uiStatusUserCanceled\"></div>\r\n      </div>\r\n      <div ng-switch-default>\r\n        <div class=\"alert alert-error\" sxy-text=\"SALAXY.NG1.InvoicesCreateComponent.uiStatusDefault\"></div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/invoices/InvoicesCreate_Table.html\",`<table class=\"table\">\r\n  <thead>\r\n    <tr>\r\n      <th colspan=\"2\" sxy-text=\"SALAXY.NG1.InvoicesCreateTableComponent.receiverInvoiceType\"></th>\r\n      <th sxy-text=\"SALAXY.NG1.InvoicesCreateTableComponent.comingToPay\"></th>\r\n      <th class=\"right\" sxy-html=\"SALAXY.NG1.InvoicesCreateTableComponent.invoiceDate.html\"></th>\r\n      <th class=\"right\" sxy-text=\"SALAXY.NG1.InvoicesCreateTableComponent.invoiceSum\"></th>\r\n    </tr>\r\n  </thead>\r\n  <tbody>\r\n    <tr ng-repeat=\"row in $ctrl.invoices\" ng-class=\"{ 'success': $ctrl.getDueDateType(row) == 'default' || $ctrl.getDueDateType(row) == 'paid'}\">\r\n      <td class=\"td-avatar middle\">\r\n        <salaxy-avatar class=\"salaxy-calc-row-type-avatar\" avatar=\"row.invoice.otherPartyInfo.avatar\"></salaxy-avatar>\r\n      </td>\r\n      <td class=\"middle\">\r\n        {{ row.invoice.otherPartyInfo.avatar.sortableName }}<br>\r\n        <small class=\"hidden-xxs\">{{(\"SALAXY.ENUM.InvoiceType.\" + row.invoice.entityType + \".label\") | sxyTranslate}}</small>\r\n      </td class=\"middle\">\r\n      <td class=\"middle\">\r\n        <div ng-switch=\"$ctrl.getDueDateType(row)\">\r\n          <span ng-switch-when=\"preview\" class=\"disabled\">{{$ctrl.getPreviewText(row)}}</span>\r\n          <span ng-switch-when=\"zero\" class=\"disabled\" sxy-text=\"SALAXY.NG1.InvoicesCreateTableComponent.dueDateTypeZero\" ps=\".\"></span>\r\n          <span ng-switch-when=\"estimation\">{{$ctrl.getEstimationText(row)}}</span>\r\n          <span ng-switch-when=\"forecast\">{{ row.invoice.otherPartyInfo.avatar.sortableName }} {{'SALAXY.NG1.InvoicesCreateTableComponent.sendsInvoice' | sxyTranslate}}</span>\r\n          <strong ng-switch-when=\"paid\" sxy-text=\"SALAXY.NG1.InvoicesCreateTableComponent.dueDateTypePaid\"></strong>\r\n          <span ng-switch-when=\"inProgress\" sxy-text=\"SALAXY.ENUM.InvoiceStatus.read.label\"></span>\r\n          <strong ng-switch-when=\"default\" sxy-text=\"SALAXY.NG1.InvoicesCreateTableComponent.dueDateTypeDefault\"></strong>\r\n          <span ng-switch-when=\"unknown\"></span>\r\n          <span ng-switch-when=\"canceled\">{{\"SALAXY.ENUM.InvoiceStatus.\" + row.invoice.status + \".label\" | sxyTranslate }}</span>\r\n        </div>\r\n        <div ng-if=\"row.invoice.businessObjects.length > 1\">\r\n          {{'SALAXY.NG1.InvoicesCreateTableComponent.totalSalaries' | sxyTranslate}} {{ row.invoice.businessObjects.length }}\r\n        </div>\r\n      </td>\r\n      <td class=\"middle right\">\r\n        <div>{{ row.invoice.startAt | sxyDate }}</div>\r\n        <div ng-switch=\"$ctrl.getDueDateType(row)\">\r\n          <span ng-switch-when=\"estimation\">{{ \"SALAXY.ENUM.CalendarMonth.month\" + (row.invoice.endAt | date : 'M') + \".label\" | sxyTranslate }}</span>\r\n          <span ng-switch-when=\"zero\">-</span>\r\n          <span ng-switch-when=\"preview\">{{ row.invoice.endAt | sxyDate }}</span>\r\n          <span ng-switch-when=\"forecast\">{{ row.invoice.endAt | sxyDate }}</span>\r\n          <span ng-switch-when=\"paid\">{{ row.invoice.endAt | sxyDate }}</span>\r\n          <span ng-switch-when=\"default\">{{ row.invoice.endAt | sxyDate }}</span>\r\n          <span ng-switch-when=\"unknown\">{{ row.invoice.endAt | sxyDate }}</span>\r\n          <span ng-switch-when=\"canceled\">{{ row.invoice.endAt | sxyDate }}</span>\r\n        </div>\r\n      </td>\r\n      <td class=\"middle right\">\r\n        <strong ng-if=\"row.invoice.status != 'canceled'\">{{ row.invoice.payment | currency }}</strong>\r\n        <s ng-if=\"row.invoice.status == 'canceled'\">{{ row.invoice.payment | currency }}</s>\r\n      </td>\r\n    </tr>\r\n  </tbody>\r\n</table>`);\n\n $templateCache.put(\"salaxy-components/invoices/InvoiceTools.html\",`<div class=\"salaxy-component salaxy-invoice-tools\">\r\n\r\n  <div class=\"btn-toolbar\" role=\"toolbar\" aria-label=\"Invoice options\">\r\n    <div class=\"btn-group\">\r\n      <salaxy-input-enum type=\"dropdown\" name=\"fileType\" label-type=\"plain\" ng-model=\"$ctrl.fileTypeId\" options=\"$ctrl.fileTypeOptions\" remember=\"invoice\"></salaxy-input-enum>\r\n\r\n    </div>\r\n    <div class=\"btn-group\">\r\n      <button ng-disabled=\"$ctrl.reader.disabled()\" id=\"reportExport\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.export()\">\r\n        {{ $ctrl.reader.exportLabel || ('SALAXY.NG1.AccountingReportToolsComponent.createExport' | sxyTranslate) }}\r\n      </button>\r\n    </div>\r\n\r\n    <div ng-if=\"'test' | sxyIsInRole\" class=\"btn-group\">\r\n      <salaxy-input-enum type=\"dropdown\" name=\"channel\" label-type=\"plain\" ng-model=\"channel\" enum=\"PaymentChannel\" ></salaxy-input-enum>\r\n      <button ng-disabled=\"!channel || channel=='undefined'\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.createSingleInvoice(channel,'verification')\">Luo avauslasku</button>\r\n      <button ng-disabled=\"!channel || channel=='undefined'\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.createSingleInvoice(channel, 'tax')\">Luo verolasku kuluvalle kuulle</button>\r\n    </div>\r\n\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/account/AccountAvatarEdit.html\",`\r\n<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.AccountInfoComponent.changeAvatar\"></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n</div>\r\n<div class=\"modal-body\" id=\"modal-body\">\r\n  <form name=\"avatarForm\" class=\"form-horizontal\" ng-if=\"$ctrl.current\" >\r\n    <div class=\"row mb-2\">\r\n      <div class=\"col-12 col-sm-4\">\r\n        <label for=\"avatarPreview\" class=\"col-form-label\" sxy-text=\"SALAXY.NG1.AccountAvatarEditPersonComponent.avatarLabel\"></label>\r\n      </div>\r\n      <div class=\"col-12 col-sm-8\">\r\n        <div class=\"worker-avatar-col\">\r\n          <salaxy-avatar class=\"avatar-xxl\" avatar=\"$ctrl.current.avatar\"></salaxy-avatar>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"row mb-2\">\r\n      <div class=\"col-12 col-sm-4\">\r\n        <label for=\"avatarPictureType\" class=\"col-form-label\" sxy-text=\"SALAXY.NG1.AccountAvatarEditPersonComponent.avatarTypeLabel\"></label>\r\n      </div>\r\n      <div class=\"col-12 col-sm-8\">\r\n        <select class=\"form-select\" id=\"avatarPictureType\" ng-model=\"$ctrl.current.avatar.pictureType\" ng-change=\"$ctrl.logic.typeForAvatarChanged($ctrl.current)\">\r\n          <option value=\"\" disabled sxy-text=\"SALAXY.NG1.AccountAvatarEditPersonComponent.optionChoose\"></option>\r\n          <option value=\"icon\" sxy-text=\"SALAXY.NG1.AccountAvatarEditPersonComponent.optionIcon\"></option>\r\n          <option value=\"uploaded\" sxy-text=\"SALAXY.NG1.AccountAvatarEditPersonComponent.optionUploaded\"></option>\r\n          <option hidden value=\"gravatar\" sxy-text=\"SALAXY.NG1.AccountAvatarEditPersonComponent.optionGravatar\"></option>\r\n        </select>\r\n      </div>\r\n    </div>\r\n    <div ng-if=\"$ctrl.current.avatar.pictureType == 'gravatar'\" class=\"row\">\r\n      <div class=\"input-info col-sm-8 offset-sm-4\">\r\n        <div class=\"input-info-icon\"><i class=\"bi bi-info-circle-fill text-default\"></i></div>\r\n        <p class=\"small input-info-text with-icon\" sxy-html=\"SALAXY.NG1.AccountAvatarEditPersonComponent.gravatarInfo.html\"></p>\r\n      </div>\r\n    </div>\r\n    <div ng-if=\"$ctrl.current.avatar.pictureType == 'icon'\">\r\n      <salaxy-input name=\"avatarInitials\" label=\"SALAXY.NG1.AccountAvatarEditPersonComponent.initialsLabel\" ng-model=\"$ctrl.current.avatar.initials\" max-length=\"2\"></salaxy-input>\r\n      <div class=\"row\">\r\n        <div class=\"col-12 col-sm-4\">\r\n          <label for=\"avatarPictureColor\" class=\"col-form-label\"  sxy-text=\"SALAXY.NG1.AccountAvatarEditPersonComponent.colorLabel\"></label>\r\n        </div>\r\n        <div class=\"col-12 col-sm-8\">\r\n          <input class=\"form-control\" type=\"color\" id=\"avatarPictureColor\" ng-model=\"$ctrl.current.avatar.color\" />\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"row\" ng-if=\"$ctrl.current.avatar.pictureType == 'uploaded'\">\r\n      <div class=\"col-12 col-sm-4\">\r\n        <label for=\"avatarImageUpload\" class=\"col-form-label\" sxy-text=\"SALAXY.NG1.AccountAvatarEditPersonComponent.uploadImageLabel\"></label>\r\n      </div>\r\n      <div class=\"col-12 col-sm-8\">\r\n        <div name=\"avatarImageUpload\" ng-model=\"avatarImage\" ngf-drop=\"$ctrl.logic.uploadAvatarImage($file, $ctrl.current)\" ngf-select=\"$ctrl.logic.uploadAvatarImage($file, $ctrl.current)\" class=\"salaxy-drop-box\" ngf-drag-over-class=\"'salaxy-drag-over'\" ngf-multiple=\"false\" ngf-min-size=\"5KB\" ngf-max-size=\"10MB\"\r\n          ngf-pattern=\"'image/*'\" ngf-model-invalid=\"invalidFile\" ng-class=\"invalidFile.$error != null ? 'error' : ''\">\r\n          <span sxy-html=\"SALAXY.NG1.AccountAvatarEditPersonComponent.uploadImage.html\"></span>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </form>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button type=\"button\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n  <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/account/AccountContactEdit.html\",`\r\n<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.AccountInfoComponent.editContactInfo\"></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n</div>\r\n<div class=\"modal-body\" id=\"modal-body\">\r\n  <form name=\"contactForm\" class=\"form-horizontal\" ng-if=\"$ctrl.current\">\r\n    <div class=\"row\">\r\n      <div class=\"col-12\">\r\n        <salaxy-input name=\"email\" label=\"SALAXY.MODEL.PersonAccount.contact.email.title\" sxy-email ng-model=\"$ctrl.current.contact.email\" ng-change=\"$ctrl.logic.emailForAvatarChanged($ctrl.current)\">\r\n        </salaxy-input>\r\n        <salaxy-input name=\"telephone\" label=\"SALAXY.MODEL.PersonAccount.contact.telephone.title\" sxy-mobile-phone ng-model=\"$ctrl.current.contact.telephone\"></salaxy-input>\r\n        <salaxy-input name=\"street\" label=\"SALAXY.MODEL.PersonAccount.contact.street.title\" ng-model=\"$ctrl.current.contact.street\" ng-required=\"('household' | sxyIsInRole) || ('company' | sxyIsInRole)\"></salaxy-input>\r\n        <salaxy-input name=\"postalCode\" label=\"SALAXY.MODEL.PersonAccount.contact.postalCode.title\" sxy-postal-code-fi ng-model=\"$ctrl.current.contact.postalCode\" ng-required=\"('household' | sxyIsInRole) || ('company' | sxyIsInRole)\"></salaxy-input>\r\n        <salaxy-input name=\"city\" label=\"SALAXY.MODEL.PersonAccount.contact.city.title\" ng-model=\"$ctrl.current.contact.city\" ng-required=\"('household' | sxyIsInRole) || ('company' | sxyIsInRole)\"></salaxy-input>\r\n        <salaxy-input-enum type=\"select\" label=\"SALAXY.MODEL.PersonAccount.contact.countryCode.title\" ng-model=\"$ctrl.current.contact.countryCode\" name=\"country\" read-only=\"true\" enum=\"Country\"></salaxy-input-enum>\r\n      </div>\r\n    </div>\r\n  </form>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button type=\"button\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n  <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/account/Authorization.html\",`<div class=\"modal-header\">\r\n  <div>\r\n    <h2 class=\"modal-title\" id=\"salaxyProductDialogLabel\">{{ $ctrl.currentPartnerSite.title | sxyTranslate }}</h2>\r\n    <h4 class=\"subtitle\">{{ $ctrl.currentPartnerSite.status | sxyTranslate}}</h4>\r\n  </div>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n</div>\r\n<div class=\"modal-body\">\r\n  <div class=\"form-horizontal\">\r\n    <div class=\"salaxy-product-info-headers\">\r\n      <div class=\"row\">\r\n        <div class=\"col-12 col-sm-4\">\r\n          <i class=\"salaxy-avatar\" style=\"font-size: 140px;\">\r\n            <img ng-src=\"{{$ctrl.currentPartnerSite.img}}\" />\r\n          </i>\r\n        </div>\r\n        <div class=\"col-12 col-sm-8\">\r\n          <div class=\"salaxy-product-description\">\r\n            <p>{{ 'SALAXY.NG1.AuthInfoHeadersComponent.' + $ctrl.currentPartnerSite.id + '.description' | sxyTranslate }}</p>\r\n            <a class=\"btn btn-primary\" target=\"_blank\" href=\"{{'SALAXY.NG1.AuthInfoHeadersComponent.' + $ctrl.currentPartnerSite.id + '.link' | sxyTranslate}}\">\r\n              {{ 'SALAXY.NG1.AuthInfoHeadersComponent.' + $ctrl.currentPartnerSite.id + '.cta' | sxyTranslate }} »</a>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <br />\r\n    <div sxy-if-role=\"auth\">\r\n      <div ng-if=\"$ctrl.currentPartnerSite.id == 'holvi'\" sxy-html=\"SALAXY.NG1.AuthorizationDialogsComponent.holvi.html\"></div>\r\n      <div ng-if=\"$ctrl.currentPartnerSite.id == 'isolta'\" sxy-html=\"SALAXY.NG1.AuthorizationDialogsComponent.isolta.html\"></div>\r\n      <div ng-if=\"$ctrl.currentPartnerSite.id == 'accountor'\" sxy-html=\"SALAXY.NG1.AuthorizationDialogsComponent.accountor.html\"></div>\r\n      <div ng-if=\"$ctrl.currentPartnerSite.id == 'finago'\" sxy-html=\"SALAXY.NG1.AuthorizationDialogsComponent.finago.html\"></div>\r\n      <div ng-if=\"$ctrl.currentPartnerSite.id == 'briox'\" sxy-html=\"SALAXY.NG1.AuthorizationDialogsComponent.briox.html\"></div>\r\n    </div>\r\n    <div class=\"row\">\r\n      <div class=\"col-12 mb-2\">\r\n        <div class=\"d-flex justify-content-end\">\r\n          <salaxy-input-boolean class=\"authorization-switch\" sxy-if-role=\"auth\" ng-change=\"$ctrl.switchAuthorization()\" name=\"{{$ctrl.currentPartnerSite.id}}\" id=\"{{$ctrl.currentPartnerSite.id}}\" type=\"switch\" ng-model=\"$ctrl.currentPartnerSite.enabled\" label-type=\"no-label\" label-true=\"on\" label-false=\"off\"></salaxy-input-boolean>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>\r\n<div class=\"modal-footer text-end\">\r\n  <button type=\"button\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/account/AuthorizedAccountAdd.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.AuthoringAccountComponent.authorize\"></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n</div>\r\n<div class=\"modal-body\" id=\"modal-body\">\r\n  <form name=\"authorizedAccountAddDialogForm\">\r\n    <div class=\"form-horizontal\">\r\n      <legend sxy-text=\"SALAXY.NG1.AuthoringAccountComponent.authorizeTitle\"></legend>\r\n      <p sxy-text=\"SALAXY.NG1.AuthoringAccountComponent.authorizeDescription\"></p>\r\n      <salaxy-input name=\"accountId\" label=\"SALAXY.NG1.AuthoringAccountComponent.palkkausAccount\" ng-model=\"$ctrl.current.id\" require=\"true\"></salaxy-input>\r\n      <salaxy-input name=\"scope\" label=\"SALAXY.NG1.AuthoringAccountComponent.scope\" placeholder=\"SALAXY.NG1.AuthoringAccountComponent.defaultScope\" ng-model=\"$ctrl.current.scope\"></salaxy-input>\r\n      <salaxy-input  ng-if=\"('admin' | sxyIsInRole)\" name=\"partnerKey\" label=\"Partnerin antama ID\"  ng-model=\"$ctrl.current.partnerKey\"></salaxy-input>\r\n    </div>\r\n  </form>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button type=\"button\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n  <button type=\"button\" class=\"btn btn-primary\" ng-disabled=\"!authorizedAccountAddDialogForm.$valid\" ng-click=\"$ctrl.saveCurrent($close)\" sxy-text=\"SALAXY.NG1.AuthoringAccountComponent.authorize\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/account/CertificateAdd.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.CertificateAddComponent.title\"></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n</div>\r\n<div class=\"modal-body\" id=\"modal-body\">\r\n  <div sxy-html=\"SALAXY.NG1.CertificateAddComponent.html\"></div>\r\n  <form name=\"certificateAddDialogForm\">\r\n    <div ng-if=\"!$ctrl.result.thumbprint\" class=\"row\">\r\n      <div class=\"col-12\">\r\n        <salaxy-input name=\"title\" label=\"SALAXY.NG1.CertificatesComponent.name\" ng-model=\"$ctrl.current.title\" require=\"true\"></salaxy-input>\r\n        <salaxy-input-enum name=\"certFormat\" ng-model=\"$ctrl.certFormat\" require=\"true\" label=\"Sertifikaatin tyyppi\"\r\n        options=\"$ctrl.certFormats\"></salaxy-input-enum>\r\n        <div class=\"form-group row\" ng-if=\"$ctrl.certFormat == 'pfx'\">\r\n          <label for=\"salasana\" class=\"col-sm-4 col-form-label\" style=\"text-align:left\">\r\n            <span sxy-text=\"SALAXY.NG1.CertificateAddComponent.password\" ps=\"*\"></span>\r\n          </label>\r\n          <div class=\"col-sm-8\">\r\n            <input type=\"password\" class=\"form-control\" id=\"password\" name=\"password\" placeholder=\"{{'SALAXY.NG1.CertificateAddComponent.password' | sxyTranslate}}\" ng-model=\"$ctrl.current.password\" ng-required=\"true\" autocomplete=\"off\" />\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </form>\r\n  <div ng-if=\"$ctrl.result.thumbprint\">\r\n    <strong sxy-text=\"SALAXY.NG1.CertificateAddComponent.createdSertificate\"></strong><br />\r\n    <a ng-click=\"$ctrl.downloadCertFile()\">{{ \"SALAXY.NG1.CertificateAddComponent.downloadBase64\" |sxyTranslate }} (.{{ $ctrl.certFormat == 'pem' ? 'zip' : $ctrl.certFormat }})</a><br />\r\n    <b></b>{{ \"SALAXY.NG1.CertificateAddComponent.base64\" |sxyTranslate }} ({{ $ctrl.certFormat }})<br />\r\n    <textarea readonly rows=\"15\" id=\"certificate-bytes\" style=\"width:100%;\">{{$ctrl.result.text }}</textarea>\r\n  </div>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button type=\"button\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n  <button ng-if=\"$ctrl.result.thumbprint\" type=\"button\" class=\"btn btn-info\" onclick='document.getElementById(\"certificate-bytes\").select(); document.execCommand(\"copy\");'\r\n    sxy-text=\"SALAXY.NG1.CertificateAddComponent.copyBase64\"></button>\r\n  <button ng-if=\"!$ctrl.result.thumbprint\" type=\"button\" class=\"btn btn-primary\" ng-disabled=\"!certificateAddDialogForm.$valid\" ng-click=\"$ctrl.createCert()\"\r\n    sxy-text=\"SALAXY.NG1.CertificateAddComponent.createSertificate\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/account/EInvoiceAddressList.html\",`<div class=\"modal-worker-list\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{$ctrl.logic.title}}</h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <div class=\"table-responsive\" style=\"max-height: calc(100vh - 300px)\">\r\n      <table class=\"table table-striped\">\r\n        <thead>\r\n          <tr>\r\n            <th sxy-text=\"SALAXY.NG1.EInvoiceAddressListComponent.name\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.EInvoiceAddressListComponent.receiver\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.EInvoiceAddressListComponent.intermediator\"></th>\r\n            <th class=\"right\">\r\n              <form name=\"searchForm\">\r\n                <salaxy-form-group name=\"search\" label-type=\"plain\">\r\n                  <div class=\"input-group\">\r\n                    <input class=\"form-control\" type=\"text\" autocomplete=\"off\" id=\"searchAddress\" name=\"searchAddress\" ng-model=\"$ctrl.logic.officialId\" sxy-company-id-fi>\r\n                    <span class=\"input-group-btn\">\r\n                      <button type=\"submit\" ng-disabled=\"!searchForm.$valid\" class=\"btn btn-default\" ng-click=\"$ctrl.logic.search()\">\r\n                        <span ng-show=\"$ctrl.logic.isLoading\">\r\n                          <i class=\"bi bi-arrow-repeat bi-spin\"></i>\r\n                        </span>\r\n                        <span ng-show=\"!$ctrl.logic.isLoading\">\r\n                          <i class=\"bi bi-search\"></i>\r\n                        </span>\r\n                      </button>\r\n                    </span>\r\n                  </div>\r\n              </form>\r\n              </salaxy-form-group>\r\n            </th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr ng-repeat=\"row in $ctrl.logic.addresses\">\r\n            <td>\r\n              <span>{{row.receiverName}}</span><br>\r\n              <small>{{row.receiverOfficialId}}</small>\r\n            </td>\r\n            <td>\r\n              <span>{{row.receiver}}</span><br>\r\n            </td>\r\n            <td>\r\n              <span>{{row.intermediatorName}}</span><br>\r\n              <small>{{row.intermediator}}</small>\r\n            </td>\r\n            <td class=\"right middle\">\r\n              <button class=\"btn btn-sm\" type=\"button\" ng-class=\"$ctrl.logic.isSelected($ctrl.current, row) ? 'btn-success' : 'btn-default'\" ng-click=\"$ctrl.logic.setCurrent($ctrl.current, row)\">\r\n                {{ $ctrl.logic.isSelected($ctrl.current, row) ? ('SALAXY.UI_Terms.chosen' | sxyTranslate) : ('SALAXY.UI_Terms.select' | sxyTranslate) }}\r\n              </button>\r\n            </td>\r\n          </tr>\r\n          <tr ng-if=\"$ctrl.logic.addresses.length == 0\">\r\n            <td colspan=\"4\" sxy-text=\"SALAXY.NG1.EInvoiceAddressListComponent.receiverNotFound\"></td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n  </div>\r\n  <div class=\"modal-footer text-end\">\r\n    <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n    <button type=\"button\" class=\"btn btn-danger\" ng-click=\"$close('reset')\" sxy-text=\"SALAXY.NG1.EInvoiceAddressListComponent.dontUseAnyAddress\"></button>\r\n    <button type=\"button\" ng-disabled=\"!$ctrl.logic.isAnySelected($ctrl.current)\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.NG1.EInvoiceAddressListComponent.useSelectedAddress\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/account/Insurance.html\",`<div class=\"localtapiola-modal-wrapper\">\r\n  <!-- Import LocalTapiola fonts -->\r\n  <link rel=\"stylesheet\" href=\"https://cdn.duetds.com/api/fonts/1.3.14/lib/localtapiola.css\" integrity=\"sha384-5JYmtSD7nykpUvSmTW1CHMoBDkBZUpUmG0vuh+NUVtZag3F75Kr7+/JU3J7JV6Wq\"\r\n    crossorigin=\"anonymous\" />\r\n  <div class=\"localtapiola-modal\">\r\n    <div class=\"modal-header\">\r\n      <div class=\"logo-wrapper\">\r\n        <img src=\"https://cdn.salaxy.com/ng1/localtapiola-modal/localtapiola-white-logo.png\" class=\"img-responsive logo-img\" alt=\"LähiTapiola\" />\r\n      </div>\r\n      <button class=\"btn-close ms-auto\" ng-click=\"$close('cancel')\" aria-label=\"Close\">{{'SALAXY.UI_Terms.close' | sxyTranslate}}</button>\r\n    </div>\r\n    <div class=\"modal-body salaxy-wizard\">\r\n      <ng-include src=\"$ctrl.currentStep.view || 'salaxy-components/modals/localTapiola/Start.html'\"></ng-include>\r\n    </div>\r\n    <div class=\"modal-footer\" ng-if=\"$ctrl.currentStep.buttonsView\">\r\n      <div class=\"footer-content w-100\">\r\n        <ng-include src=\"$ctrl.currentStep.buttonsView || 'salaxy-components/modals/localTapiola/buttons-default.html'\" class=\"d-flex justify-content-between\"></ng-include>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>\r\n<style>\r\n  .datepicker .datepicker-cell.focused {\r\n    background-color: #0077b3;\r\n    box-shadow: none;\r\n    color: #fff;\r\n  }\r\n  \r\n  .datepicker .today-button,\r\n  .datepicker .today-button:hover,\r\n  .datepicker .today-button:focus,\r\n  .datepicker .clear-button,\r\n  .datepicker .clear-button:hover,\r\n  .datepicker .clear-button:focus {\r\n    color: #009fd8 !important;\r\n    border-color: transparent !important;\r\n    background-color: transparent !important;\r\n    font-family: \"localtapiola-sans\" !important;\r\n    font-size: 14px !important;\r\n    outline: none !important;\r\n    font-weight: 600 !important;\r\n  }\r\n</style>`);\n\n $templateCache.put(\"salaxy-components/modals/account/PrimaryPartner.html\",`<div class=\"modal-header\">\r\n  <div>\r\n    <h2 class=\"modal-title\" id=\"salaxyProductDialogLabel\">{{ $ctrl.current.name }}</h2>\r\n    <h4 class=\"subtitle\">{{ $ctrl.current.description }}</h4>\r\n  </div>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n</div>\r\n<div class=\"modal-body\">\r\n  <div class=\"form-horizontal\">\r\n    <div class=\"salaxy-component salaxy-product-info-headers\">\r\n      <div class=\"row\">\r\n        <div class=\"col-12 col-sm-4\">\r\n          <i class=\"salaxy-avatar\" style=\"font-size: 140px;\">\r\n            <img ng-src=\"{{ $ctrl.current.branding.logo }}\" />\r\n          </i>\r\n        </div>\r\n        <div class=\"col-12 col-sm-8\">\r\n          <div class=\"salaxy-product-description\">\r\n            <p>\r\n              {{ $ctrl.current.branding.text }}\r\n            </p>\r\n            <a ng-if=\"$ctrl.current.branding.url\" class=\"btn btn-primary\" target=\"_blank\" ng-href=\"{{$ctrl.current.branding.url}}\">{{'SALAXY.NG1.PrimaryPartnerComponent.moreInfo' | sxyTranslate}} »</a>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div class=\"row\" ng-if=\"!$ctrl.current.isAuthorized\">\r\n        <div class=\"col-12 input-info\">\r\n          <div class=\"input-info-icon\"><i class=\"bi bi-info-circle-fill text-default\"></i></div>\r\n          <p class=\"small input-info-text with-icon\" sxy-html=\"SALAXY.NG1.PrimaryPartnerComponent.notAuthorized.html\"></p>\r\n        </div>\r\n      </div>\r\n      <div class=\"row\" ng-if=\"!$ctrl.current.isAuthorized\">\r\n        <div class=\"col-12 input-info\">\r\n          <div class=\"input-info-icon\"><i class=\"bi bi-info-circle-fill text-default\"></i></div>\r\n          <p class=\"small input-info-text with-icon\" sxy-text=\"SALAXY.NG1.PrimaryPartnerComponent.notAuthorized.text\"></p>\r\n        </div>\r\n      </div>\r\n\r\n      <div class=\"row\" ng-if=\"$ctrl.current.isAuthorized\">\r\n        <div class=\"col-12 input-info\">\r\n          <div class=\"input-info-icon\"><i class=\"bi bi-info-circle-fill text-default\"></i></div>\r\n          <p class=\"small input-info-text with-icon\" sxy-html=\"SALAXY.NG1.PrimaryPartnerComponent.authorized.html\"></p>\r\n        </div>\r\n      </div>\r\n      <div class=\"row\" ng-if=\"$ctrl.current.isAuthorized\">\r\n        <div class=\"col-12 input-info\">\r\n          <div class=\"input-info-icon\"><i class=\"bi bi-info-circle-fill text-default\"></i></div>\r\n          <p class=\"small input-info-text with-icon\" sxy-text=\"SALAXY.NG1.PrimaryPartnerComponent.authorized.text\"></p>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>\r\n<div class=\"modal-footer text-end\">\r\n  <button type=\"button\" class=\"btn btn-danger\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n  <button ng-if=\"!$ctrl.current.isAuthorized\" type=\"button\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.NG1.PrimaryPartnerComponent.setPrimaryPartner\"></button>\r\n  <button ng-if=\"$ctrl.current.isAuthorized\" type=\"button\" class=\"btn btn-danger\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.NG1.PrimaryPartnerComponent.removePrimaryPartnerCredential\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/account/VismaModal.html\",`<div id=\"salaxyDialog\" class=\"salaxy-component salaxy-dialog modal-dialog visma-modal {{size ? 'modal-' + size : ''}}\" aria-labelledby=\"salaxyDialogLabel\" role=\"dialog\">\r\n  <link href=\"https://fonts.googleapis.com/css?family=Exo:400,700\" rel=\"stylesheet\">\r\n  <div class=\"modal-content\" role=\"document\" uib-modal-transclude></div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/accounting-target/accounting-targets.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"visible-xxs\">\r\n    <div class=\"table-filter-container-mobile\">\r\n      <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n      </salaxy-input>\r\n    </div>\r\n  </div>\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\">\r\n            <div sxy-orderby=\"shortText\" sxy-text=\"SALAXY.NG1.AccountingTargetsComponent.exportDefinition\"></div>\r\n            <div sxy-text=\"SALAXY.NG1.AccountingTargetsComponent.targetChannel\"></div>\r\n          </th>\r\n          <th sxy-orderby=\"owner\" colspan=\"2\">\r\n            <div sxy-text=\"SALAXY.NG1.AccountingTargetsComponent.owner\"></div>\r\n            <div sxy-text=\"SALAXY.NG1.AccountingTargetsComponent.status\"></div>\r\n          </th>\r\n\r\n          <th class=\"right hidden-xxs\" colspan=\"2\">\r\n            <div class=\"table-filter-container\">\r\n              <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" class=\"salaxy-odata-table-search\" placeholder=\"SALAXY.UI_Terms.textSearch\" label-type=\"plain\"></salaxy-input>\r\n            </div>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar middle\">\r\n            <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"middle\">\r\n            <div title=\"{{ row.shortText }} ({{ row.id }})\">\r\n              <strong>{{ row.otherPartyInfo.avatar.displayName }}</strong>\r\n            </div>\r\n          </td>\r\n          <td class=\"td-avatar middle\">\r\n            <salaxy-avatar avatar=\"row.ownerInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"middle\">\r\n            <div>{{ row.ownerInfo.avatar.displayName }}</div>\r\n            <div>{{ \"AccountingTargetStatus.\" + row.status | sxyEnum }}</div>\r\n          </td>\r\n          <td class=\"right middle\">\r\n            <button class=\"btn btn-sm\" type=\"button\" ng-class=\"$ctrl.isSelected(row) ? 'btn-danger' : 'btn-info'\" ng-click=\"$ctrl.setSelected(row, 'toggle')\">\r\n              {{ $ctrl.isSelected(row) ? ('SALAXY.UI_Terms.unselect' | sxyTranslate) : ('SALAXY.UI_Terms.select' | sxyTranslate) }}\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/batch/default.html\",`﻿<div class=\"salaxy-batch-default\">\r\n  <button ng-if=\"!$ctrl.autoStart\" type=\"button\" class=\"btn btn-primary\" ng-disabled=\"$ctrl.isProcessStarted\" ng-click=\"$ctrl.startProcess()\">Aloita prosessi</button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/batch/dialog.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\">{{ $ctrl.dialogHeader }}</h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n</div>\r\n<div class=\"modal-body\" id=\"modal-body\">\r\n  <div class=\"salaxy-batch-content\" ng-include=\"$ctrl.batchTemplateUrl\"></div>\r\n  <hr/>\r\n  <sxy-table ng-if=\"$ctrl.isReady\" data=\"$ctrl.list\" options=\"$ctrl.tableOptions\" include=\"$ctrl.columns\" ng-ref=\"$ctrl.$table\"></sxy-table>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <h2 class=\"float-start\" style=\"margin: 0\" ng-if=\"$ctrl.processCounter.isProcessing || $ctrl.processCounter.isDone\">\r\n    {{ $ctrl.processCounter.isDone ? ('SALAXY.NG1.BatchProcessComponent.dialog.done' | sxyTranslate) : ('SALAXY.NG1.BatchProcessComponent.dialog.processing' | sxyTranslate) }}: {{ $ctrl.processCounter.processedCount }} / {{ $ctrl.processCounter.totalCount }}\r\n    <span class=\"bg-danger\" ng-if=\"$ctrl.processCounter.errorsCount\">{{'SALAXY.NG1.BatchProcessComponent.dialog.errors' | sxyTranslate}}: {{ $ctrl.processCounter.errorsCount }}</span>\r\n    <span class=\"bg-warning\" ng-if=\"$ctrl.processCounter.canceling\" sxy-text=\"SALAXY.NG1.BatchProcessComponent.dialog.canceling\"></span>\r\n  </h2>\r\n  <h2 class=\"float-start\" style=\"margin: 0\" ng-if=\"!($ctrl.processCounter.isProcessing || $ctrl.processCounter.isDone)\">\r\n    {{'SALAXY.NG1.BatchProcessComponent.dialog.count' | sxyTranslate}}: {{ $ctrl.processCounter.totalCount }} ({{ $ctrl.list.length }})\r\n  </h2>\r\n  <button type=\"button\" class=\"btn btn-danger\" ng-click=\"$ctrl.cancelProcess()\" ng-if=\"$ctrl.processCounter.isProcessing\" sxy-text=\"SALAXY.NG1.BatchProcessComponent.dialog.stopProcessing\"></button>\r\n  <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.close()\" ng-if=\"!$ctrl.processCounter.isProcessing\">{{'SALAXY.UI_Terms.close' | sxyTranslate}}</button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/Calc.html\",`<div class=\"modal-calc-list\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{$ctrl.logic.title}}</h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <salaxy-calc model=\"$ctrl.current\"></salaxy-calc>\r\n  </div>\r\n  <div class=\"modal-footer\">\r\n    <button type=\"button\" class=\"btn btn-danger\" ng-click=\"$close('delete')\" sxy-text=\"SALAXY.UI_Terms.delete\"></button>\r\n    <button type=\"reset\" class=\"btn btn-default float-end\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n    <button type=\"submit\" class=\"btn btn-primary float-end\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/CalcAccountingReportQuery.html\",`<div class=\"modal-version-list\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{$ctrl.logic.title | sxyTranslate}}</h2>\r\n\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <salaxy-accounting-report-query lang=\"$ctrl.logic.lang\" calcs=\"$ctrl.logic.calcs\" view=\"$ctrl.logic.view\"></salaxy-accouting-report-query>\r\n  </div>\r\n  <div class=\"modal-footer text-end\">\r\n    <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/CalcIr.html\",`<div class=\"modal-calc-list\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{$ctrl.logic.title}}</h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <salaxy-calcs-ir-rows calcs=\"[$ctrl.current]\" class=\"report\"></salaxy-calcs-ir-rows>\r\n  </div>\r\n  <div class=\"modal-footer\">\r\n    <button type=\"submit\" class=\"btn btn-primary float-end\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/CalcLeaves.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.absences.calculationLegend\"></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close(null)\" aria-label=\"Close\"></button>\r\n</div>\r\n<div class=\"modal-body\">\r\n  <salaxy-calc-leaves ng-ref=\"$calcLeaves\" calc=\"$ctrl.current.calc\" worktime=\"$ctrl.current.worktime\"></salaxy-calc-leaves>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button type=\"button\" class=\"btn btn-default float-end\" ng-click=\"$close(null)\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n  <button type=\"button\" class=\"btn btn-primary float-end\" ng-click=\"$close({absencesPeriods: $calcLeaves.getAbsencesPeriods()})\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/CalcList.html\",`<div class=\"modal-worker-list\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{$ctrl.logic.title | sxyTranslate}}</h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <div class=\"table-responsive\" style=\"max-height: calc(100vh - 300px)\">\r\n      <salaxy-calc-list category=\"{{ $ctrl.logic.category || 'draft' }}\" options=\"$ctrl.logic.options\" mode=\"select\" selected-items=\"$ctrl.current\"></salaxy-calc-list>\r\n    </div>\r\n    <div class=\"text-end\">\r\n      <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"{{ $ctrl.logic.cancelButtonText || 'SALAXY.UI_Terms.cancel'}}\"></button>\r\n      <button type=\"submit\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"{{ $ctrl.logic.okButtonText || 'SALAXY.UI_Terms.save'}}\"></button>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/CalcRepaired.html\",`<div class=\"modal-worker-list\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{'SALAXY.ENUM.CalculationStatus.paymentRepairCopy.label' | sxyTranslate}}</h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <div class=\"table-responsive\" style=\"max-height: calc(100vh - 300px)\">\r\n        <table class=\"table table-striped\">\r\n          <thead>\r\n            <tr>\r\n              <th colspan=\"2\">\r\n                <span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span>\r\n              </th>\r\n              <th class=\"hidden-xxs\">\r\n                <span sxy-text=\"SALAXY.UI_Terms.updated\"></span><br />\r\n                <span><span sxy-text=\"SALAXY.NG1.CalculationsWithSalaryDateSelectComponent.salaryDate\"></span></span>\r\n              </th>\r\n              <th class=\"right hidden-xxs\" colspan=\"2\">\r\n              </th>\r\n            </tr>\r\n          </thead>\r\n          <tbody>\r\n            <tr ng-repeat=\"row in $ctrl.current\">\r\n              <td class=\"td-avatar visible-xxs middle\">\r\n                <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n              </td>\r\n              <td class=\"td-name visible-xxs middle\">\r\n                <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br /> {{ row.updatedAt | date }}\r\n                <br /> {{ row.salaryDate | date }}\r\n              </td>\r\n              <td class=\"right visible-xxs bottom\">\r\n                <a ng-href=\"#/calc/details/{{row.id}}\">\r\n                  {{ row.grossSalary | currency }}\r\n                </a>\r\n              </td>\r\n              <td class=\"td-avatar hidden-xxs middle\">\r\n                <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n              </td>\r\n              <td class=\"td-name hidden-xxs middle\">\r\n                <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br />\r\n              </td>\r\n              <td class=\"hidden-xxs middle\">\r\n                {{ row.updatedAt | date }}<br /> {{ row.salaryDate | date }}\r\n              </td>\r\n              <td class=\"right hidden-xxs middle\">\r\n                {{ row.grossSalary | currency }}\r\n              </td>\r\n              <td class=\"right middle\">\r\n                  <a ng-href=\"#/calc/details/{{row.id}}\" class=\"btn btn-sm btn-default btn-block\">\r\n                    <i class=\"bi bi-info-lg visible-xs me-1\"></i><span class=\"hidden-xs\" sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n                  </a>\r\n              </td>\r\n            </tr>\r\n          </tbody>\r\n        </table>\r\n    </div>\r\n    <div class=\"text-end\">\r\n      <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close()\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/CalcReports.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.CalcReportsComponent.calcReports\" ></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n</div>\r\n<div class=\"modal-body \">\r\n  <salaxy-calc-reports calcs=\"$ctrl.data.calcs\" preview=\"$ctrl.data.preview\" view=\"{{ $ctrl.data.view || 'page1' }}\" report-type=\"$ctrl.data.reportType\"></salaxy-calc-reports>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/CfaPaymentOverview.html\",`<div class=\"modal-calc-list\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{ $ctrl.logic.title }}</h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n  </div>\r\n  <div class=\"modal-body\">\r\n\r\n    <style type=\"text/css\">\r\n      .left.carousel-control {\r\n        background-image: none;\r\n      }\r\n      \r\n      .right.carousel-control {\r\n        background-image: none;\r\n      }\r\n      \r\n      .right.carousel-control>span.glyphicon.glyphicon-chevron-right {\r\n        color: var(--salaxy-brand-primary)\r\n      }\r\n      \r\n      .left.carousel-control>span.glyphicon.glyphicon-chevron-left {\r\n        color: var(--salaxy-brand-primary)\r\n      }\r\n      \r\n      .carousel-indicators .active {\r\n        background-color: var(--salaxy-brand-primary);\r\n      }\r\n      \r\n      .carousel-indicators li {\r\n        border-color: var(--salaxy-brand-primary);\r\n      }\r\n    </style>\r\n      \r\n    <p class=\"lead\" sxy-text=\"SALAXY.NG1.CfaPaymentOverviewComponent.lead\" ng-if=\"$ctrl.logic.isReadyForPayment\"></p>\r\n    <div class=\"alert alert-danger\" ng-if=\"!$ctrl.logic.isReadyForPayment()\">\r\n      <p class=\"lead\" sxy-html=\"SALAXY.NG1.PaymentDialogComponent.alert.html\"></p>\r\n    </div>\r\n    <p class=\"lead\" ng-if=\"$ctrl.logic.isReadyForPayment() && $ctrl.logic.instructions\">\r\n      {{ $ctrl.logic.instructions }}\r\n    </p>\r\n    <div ng-if=\"$ctrl.logic.type == 'calc'\">\r\n      <salaxy-calc-worker-info model=\"$ctrl.current\"></salaxy-calc-worker-info>\r\n      <p >\r\n        <strong sxy-text=\"SALAXY.NG1.CalcDetailsWorkComponent.workEndStartDate\" ps=\":\"></strong> {{$ctrl.current.info.workStartDate | date : 'dd.MM.yyyy'}}{{ $ctrl.current.info.workStartDate ? ' - ': ''}} {{$ctrl.current.info.workEndDate\r\n        | date: 'dd.MM.yyyy'}}, {{$ctrl.current.framework.numberOfDays > 0 ? $ctrl.current.framework.numberOfDays : '?' }} {{'SALAXY.NG1.CfaPaymentOverviewComponent.days' | sxyTranslate}}.\r\n      </p>\r\n      <hr />\r\n      <div class=\"table-responsive\"> \r\n        <salaxy-calc-report apply-site-styles=\"true\" calc=\"$ctrl.current\" report-type=\"'paymentReport'\" template-name=\"'paymentTablesV2'\"></salaxy-calc-report>\r\n      </div>\r\n      <p sxy-html=\"SALAXY.NG1.PaymentDialogComponent.afterPayment.html\" params=\"{totalPayment: ($ctrl.current.result.employerCalc.totalPayment | currency)}\"></p>\r\n      <p ng-if=\"$ctrl.current.result.employerCalc.householdDeduction > 0\" sxy-html=\"SALAXY.NG1.PaymentDialogComponent.household.html\" params=\"{householdDeduction: ($ctrl.current.result.employerCalc.householdDeduction | currency) }\">\r\n      </p>\r\n    </div>\r\n    <div ng-if=\"$ctrl.logic.type != 'calc'\">\r\n      <strong>{{'SALAXY.NG1.CfaPaymentOverviewComponent.totalPayments' | sxyTranslate}}: {{$ctrl.current.info.totalPayment | currency}}</strong><br />\r\n      <strong>{{'SALAXY.NG1.CfaPaymentOverviewComponent.calculations' | sxyTranslate}}: {{$ctrl.current.calcs.length}}</strong><br />\r\n      <hr />\r\n      <div id=\"payroll-calcs-carousel\" class=\"carousel carousel-dark slide\" data-bs-interval=\"false\">\r\n        <div class=\"carousel-controls d-flex align-items-center justify-content-between mb-3\">\r\n          <button class=\"carousel-control-prev\" type=\"button\" data-bs-target=\"#payroll-calcs-carousel\" data-bs-slide=\"prev\">\r\n            <span class=\"carousel-control-prev-icon\" aria-hidden=\"true\"></span>\r\n          </button>\r\n          <button class=\"carousel-control-next\" type=\"button\" data-bs-target=\"#payroll-calcs-carousel\" data-bs-slide=\"next\">\r\n            <span class=\"carousel-control-next-icon\" aria-hidden=\"true\"></span>\r\n          </button>\r\n        </div>\r\n        <div class=\"carousel-inner\">\r\n          <div ng-repeat=\"calc in $ctrl.current.calcs track by $index\" index=\"$index\" class=\"carousel-item\" ng-class=\"{'active': $index == 0}\">\r\n            <strong>{{$index + 1}}/{{$ctrl.current.calcs.length}} {{calc.worker.avatar.sortableName}}</strong>\r\n            <salaxy-calc-report calc=\"calc\" apply-site-styles=\"true\" report-type=\"'paymentReport'\" template-name=\"'paymentTablesV2'\"></salaxy-calc-report>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <p sxy-html=\"SALAXY.NG1.PaymentDialogComponent.afterPayment.html\" params=\"{totalPayment: ($ctrl.current.info.totalPayment | currency)}\"></p>\r\n    </div>\r\n    <div ng-if=\"$ctrl.logic.channel == 'palkkausCfaPaytrail' || $ctrl.logic.channel == 'palkkausEcfaPaytrail'\">\r\n      <p sxy-text=\"SALAXY.NG1.CfaPaymentOverviewComponent.palkkausCfaPaytrailInfo\"></p>\r\n      <p sxy-text=\"SALAXY.NG1.CfaPaymentOverviewComponent.palkkausCfaPaytrailInfoAlt\"></p>\r\n    </div>\r\n  </div>\r\n  <div class=\"modal-footer text-end\">\r\n    <button ng-if=\"$ctrl.logic.channel != 'palkkausCfaPaytrail' && $ctrl.logic.channel != 'palkkausEcfaPaytrail'\" type=\"submit\" class=\"btn btn-primary float-end\" ng-disabled=\"!$ctrl.logic.isReadyForPayment()\" ng-click=\"$close('ok')\">\r\n      {{ $ctrl.logic.okButtonText}}\r\n    </button>\r\n    <button ng-if=\"$ctrl.logic.channel == 'palkkausCfaPaytrail' || $ctrl.logic.channel == 'palkkausEcfaPaytrail'\" type=\"submit\" class=\"btn btn-primary float-end\" ng-disabled=\"!$ctrl.logic.isReadyForPayment()\" ng-click=\"$ctrl.logic.paymentFunc($ctrl.current);$close('ok')\">\r\n      {{ $ctrl.logic.okButtonText}}\r\n    </button>\r\n    <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/EditorConfirm.html\",`<div class=\"modal-editor-confirm\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\" sxy-text=\"Oletko varma?\"></h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <p sxy-text=\"Hyväksynnän jälkeen päivitämme tulosteet ja raportoimme muutokset tulorekisteriin.\"></p>\r\n    <p>&nbsp;</p>\r\n    <form name=\"snapshotForm\" class=\"form-horizontal\">\r\n      <salaxy-input-enum label=\"Syykoodi\" name=\"reasonCode\" ng-model=\"$ctrl.current.reasonCode\" options=\"{\r\n        1: 'Asiakkaan korjauspyyntö',\r\n        2: 'Virheellinen laskelma',\r\n        3: 'Palkkaus ohjelmistovirhe',\r\n        4: 'Uusi ilmoitus/peruminen tulorekisteriin',\r\n        }\"></salaxy-input-enum>\r\n      <salaxy-input-enum label=\"Vakavuusaste\" name=\"severityCode\" type=\"radio\" ng-model=\"$ctrl.current.severityCode\" options=\"{ 1:'1', 2:'2', 3 :'3', 4 :'4', 5:'5' }\">\r\n      </salaxy-input-enum>\r\n      <div class=\"row\">\r\n        <label for=\"\" class=\"col-4 col-form-label\">\r\n          <span class=\"label-text\">Kategoriat</span>\r\n        </label>\r\n        <div class=\"col-8\">\r\n          <table>\r\n            <tr>\r\n              <td colspan=\"2\" class=\"text-end\"><button type=\"button\" class=\"btn btn-primary btn-xs\" ng-click=\"$ctrl.current.categories.push('')\">Uusi kategoria</button></td>\r\n            </tr>\r\n            <tr>\r\n              <td colspan=\"2\">&nbsp;</td>\r\n            </tr>\r\n            <tr ng-repeat=\"category in $ctrl.current.categories track by $index\">\r\n              <td>\r\n                  <salaxy-form-group name=\"category{{$index}}\" label-type=\"plain\">\r\n                      <div>\r\n                          <salaxy-input-typeahead\r\n                            label-type=\"no-label\"\r\n                            ng-model=\"$ctrl.current.categories[$index]\"\r\n                            name=\"worker\"\r\n                            disable-cache=\"true\"\r\n                            placeholder=\"\"\r\n                            options=\"$ctrl.logic.categories\">\r\n                          </salaxy-input-typeahead>\r\n                      </div>\r\n                  </salaxy-form-group>\r\n              </td>\r\n              <td>\r\n                  <button type=\"button\" class=\"btn btn-danger btn-sm\" ng-click=\"$ctrl.current.categories.splice($index,1)\" title=\"{{'SALAXY.UI_Terms.deleteRow' | sxyTranslate}}\"><i class=\"bi bi-trash-fill\"></i></button>\r\n              </td>\r\n          </tr>\r\n          </table>\r\n        </div>\r\n      </div>\r\n\r\n      <salaxy-textarea label=\"Kuvaus\" name=\"description\" ng-model=\"$ctrl.current.description\"></salaxy-textarea>\r\n    </form>\r\n  </div>\r\n  <div class=\"modal-footer\">\r\n    <button type=\"button\" class=\"btn btn-danger\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n    <button type=\"submit\" class=\"btn btn-primary\" ng-disabled=\"!snapshotForm.$valid\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.ok\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/EmailSharing.html\",`<div class=\"modal-email-sharing\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.EmailSharingComponent.title\"></h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <p sxy-html=\"SALAXY.NG1.EmailSharingComponent.body.html\"></p>\r\n    <form name=\"emailForm\" class=\"form-horizontal\">\r\n      <salaxy-input label=\"SALAXY.NG1.EmailSharingComponent.emailTo\" name=\"to\" type=\"text\" require=\"true\" ng-model=\"$ctrl.current.to\" sxy-email></salaxy-input>\r\n      <salaxy-input label=\"SALAXY.NG1.EmailSharingComponent.emailCC\" name=\"cc\" type=\"text\" ng-model=\"$ctrl.current.cc\" sxy-email></salaxy-input>\r\n      <salaxy-textarea label=\"SALAXY.NG1.EmailSharingComponent.message\" name=\"message\" ng-model=\"$ctrl.current.message\"></salaxy-textarea>\r\n    </form>\r\n  </div>\r\n  <div class=\"modal-footer\">\r\n    <button type=\"button\" class=\"btn btn-danger\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n    <button type=\"submit\" class=\"btn btn-primary\" ng-disabled=\"!emailForm.$valid\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.NG1.EmailSharingComponent.sendEmail\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/PalkkausPersonalPaymentOverview.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\">{{ $ctrl.editDialogParameters.logic.isInspectingPaidInvoices ? ('SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.titleInspect' | sxyTranslate) : ('SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.title' | sxyTranslate) }}</h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n</div>\r\n<div class=\"modal-body\" ng-controller=\"InvoicesCreateController as $invCreate\">\r\n  <div class=\"d-block d-md-none d-print-none\" ng-init=\"$invCreate.model=$ctrl.model\">\r\n    <h4><span sxy-text=\"SALAXY.NG1.WorkerWizardComponent.wizard.step\"></span> {{$ctrl.currentStep.number}}/{{$ctrl.steps.length}}</h4>\r\n  </div>\r\n  <div class=\"salaxy-wizard d-print-none\">\r\n    <div class=\"wizard-steps\">\r\n      <div class=\"wizard-step\" ng-repeat=\"step in $ctrl.steps\" ng-class=\"{'active': step.active, 'disabled': step.disabled}\">\r\n        <span class=\"salaxy-avatar\">\r\n          <div class=\"wizard-icons-wrapper\">\r\n            <i class=\"bi\" ng-class=\"step.active ? 'bi-circle-fill' : 'bi-circle'\"></i>\r\n            <i class=\"bi bi-circle-fill\"></i>\r\n          </div>\r\n          <strong class=\"number\">{{ step.number }}</strong>\r\n        </span>\r\n        <span class=\"step-text\">{{ step.title | sxyTranslate }}</span>\r\n      </div>\r\n    </div>\r\n    <div class=\"wizard-strikethrough\"></div>\r\n  </div>\r\n  <div class=\"worker-wizard-content\">\r\n    <ng-include src=\"$ctrl.currentStep.view\"></ng-include>\r\n  </div>\r\n</div>\r\n<div class=\"modal-footer d-print-none\">\r\n  <button ng-if=\"$ctrl.step < 2 && !$ctrl.editDialogParameters.logic.isInspectingPaidInvoices\" ng-click=\"$close('cancel')\" class=\"btn float-start btn-default\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n  <button ng-if=\"$ctrl.editDialogParameters.logic.isInspectingPaidInvoices && $ctrl.step == 3\" ng-click=\"$close('cancel')\" class=\"btn btn-default\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n  <button ng-if=\"$ctrl.step >= 2\" ng-click=\"$ctrl.goPrevious()\" ng-disabled=\"!$ctrl.canGoPrevious\" class=\"btn float-start btn-default\" sxy-text=\"SALAXY.UI_Terms.previous\"></button>\r\n  <button ng-if=\"$ctrl.step &lt; $ctrl.steps.length\" ng-click=\"$ctrl.goNext()\" ng-disabled=\"!$ctrl.canGoNext\" class=\"btn btn-primary\" sxy-text=\"SALAXY.UI_Terms.next\"></button>\r\n</div>\r\n`);\n\n $templateCache.put(\"salaxy-components/modals/calc/PaymentOverview.html\",`<div class=\"modal-calc-list\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{ $ctrl.$invCreate.title }}</h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body overflow-auto\">\r\n    <salaxy-invoices-create model=\"$ctrl.current\" ng-ref=\"$ctrl.$invCreate\"></salaxy-invoices-create>\r\n  </div>\r\n  <div class=\"modal-footer text-start\">\r\n    <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n    <button type=\"submit\" class=\"btn btn-primary float-end\" ng-if=\"$ctrl.$invCreate.getOkBtn()\" ng-click=\"$ctrl.$invCreate.createInvoices($close)\">\r\n      {{ $ctrl.$invCreate.getOkBtn() }}\r\n    </button>\r\n    <div ng-if=\"$ctrl.logic.channel == 'palkkausPersonal'\">\r\n      <div>\r\n        <b>Debug</b><br>\r\n        <salaxy-json-formatter json=\"$ctrl.$invCreate.invoices\" open=\"1\"></salaxy-json-formatter>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/personal-payment/Approval.html\",`<div ng-controller=\"InvoicesCreateController as $invCreate\" ng-init=\"$invCreate.model=$ctrl.model\">\r\n  <section>\r\n    <h3 sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.steps.step4.title\"></h3>\r\n    <p class=\"lead\" sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.steps.step4.text\"></p>      \r\n  </section>\r\n  <section>\r\n    <h3 sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.steps.step4.buttonInfoText\"></h3>\r\n    <p class=\"lead\" sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.steps.step4.irInfo\"></p>\r\n  </section>\r\n  <section ng-if=\"$ctrl.eprPaymentWarning && $invCreate.primaryCalcNetInvoicePreview && $invCreate.primaryCalcNetInvoicePreview.invoice.status !== 'paid'\">\r\n    <p class=\"lead\">{{$ctrl.eprPaymentWarning}}</p>\r\n  </section>\r\n  <section ng-if=\"$ctrl.eprCancelWarning && $invCreate.primaryCalcNetInvoicePreview && $invCreate.primaryCalcNetInvoicePreview.invoice.status === 'paid'\">\r\n    <p class=\"lead\">{{$ctrl.eprCancelWarning}}</p>\r\n  </section>\r\n \r\n  <button ng-click=\"$close('paid')\" ng-if=\"$invCreate.primaryCalcNetInvoicePreview && ( $invCreate.primaryCalcNetInvoicePreview.invoice.status == 'unread' || $invCreate.primaryCalcNetInvoicePreview.invoice.status == 'read' ||  $invCreate.primaryCalcNetInvoicePreview.invoice.status == 'waitingConfirmation' )\"\r\n  type=\"button\" class=\"btn btn-success\" sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.steps.step4.acceptButton\"></button>\r\n  <button ng-click=\"$close('cancel')\" ng-if=\"$invCreate.primaryCalcNetInvoicePreview && $invCreate.primaryCalcNetInvoicePreview.exists == false\" type=\"button\" class=\"btn btn-danger\"  sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.notPaidInfo\"></button>\r\n  <button ng-click=\"$close('canceled')\" ng-if=\"$invCreate.primaryCalcNetInvoicePreview &&  $invCreate.primaryCalcNetInvoicePreview.exists == true && ( $invCreate.primaryCalcNetInvoicePreview.invoice.status == 'unread' || $invCreate.primaryCalcNetInvoicePreview.invoice.status == 'read' ||  $invCreate.primaryCalcNetInvoicePreview.invoice.status == 'waitingConfirmation' )\"\r\n    type=\"button\" class=\"btn btn-danger\"  sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.steps.step4.declineButton\"></button>\r\n  <button ng-click=\"$close('canceled')\" ng-if=\"$invCreate.primaryCalcNetInvoicePreview && $invCreate.primaryCalcNetInvoicePreview.invoice.status == 'paid'\" type=\"button\" class=\"btn btn-danger\"  sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.cancelInfo\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/personal-payment/SideCosts.html\",`<section>\r\n  <h3 sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.steps.step3.title\"></h3>\r\n  <p class=\"lead\" sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.steps.step3.text\"></p>   \r\n  <ul>\r\n    <li sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.steps.step3.listItem1\"></li>\r\n    <li sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.steps.step3.listItem2\"></li>\r\n    <li sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.steps.step3.listItem3\"></li>\r\n  </ul>\r\n  <p class=\"lead\" sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.steps.step3.textAlt\"></p>\r\n</section>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/personal-payment/Tax.html\",`<div ng-controller=\"InvoicesCreateController as $invCreate\" ng-init=\"$invCreate.model=$ctrl.model\">\r\n  <div class=\"d-print-none\" ng-if=\"$invCreate.primaryCalcNetInvoicePreview.invoice.status == 'paid'\">\r\n    <p class=\"lead\">\r\n      <button type=\"button\" class=\"btn btn-primary float-end\" onclick=\"window.print()\" sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.printInvoices\"></button> {{'SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.paid.paidInspectTax' |\r\n      sxyTranslate}}\r\n    </p>\r\n    <div ng-if=\"$invCreate.primaryCalcTaxInvoicePreview\" class=\"credit-transfer-container\">\r\n      <salaxy-credit-transfer invoice-preview=\"$invCreate.primaryCalcTaxInvoicePreview\" mode=\"official\">\r\n        <message>\r\n          <p sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.mobileBanking.tax\"></p>\r\n          <p style=\"text-transform: none;\" sxy-html=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.mobileBanking.taxInfo.html\"></p>\r\n        </message>\r\n      </salaxy-credit-transfer>\r\n    </div>\r\n  </div>\r\n  <div class=\"d-print-none\" ng-if=\"$invCreate.primaryCalcNetInvoicePreview && $invCreate.primaryCalcNetInvoicePreview.invoice.status != 'paid'\">\r\n    <section>\r\n      <h3 sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.steps.step2.title\"></h3>\r\n      <button type=\"button\" class=\"btn btn-primary float-end\" onclick=\"window.print()\" sxy-text=\"Tulosta\"></button>\r\n      <p class=\"lead\" sxy-html=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.steps.step2.text.html\"></p>\r\n    </section>\r\n    <table class=\"table\">\r\n      <thead>\r\n        <tr>\r\n          <th></th>\r\n          <th sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.preview.receiver\"></th>\r\n          <th sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.preview.iban\"></th>\r\n          <th sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.preview.reference\"></th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.preview.dueDate\"></th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.preview.sum\"></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr>\r\n          <th rowspan=\"2\" style=\"font-size: 2em;\"></th>\r\n          <th>{{ $invCreate.primaryCalcTaxInvoicePreview.invoice.otherPartyInfo.avatar.displayName }}</th>\r\n          <th>{{ $invCreate.primaryCalcTaxInvoicePreview.invoice.otherPartyInfo.ibanNumber }}</th>\r\n          <th sxy-if-role=\"test\">{{ $invCreate.primaryCalcTaxInvoicePreview.invoice.reference || \"RF02 TEST 1234\" }}</th>\r\n          <th sxy-if-role=\"!test\">{{ $invCreate.primaryCalcTaxInvoicePreview.invoice.reference || ('SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.preview.checkReference' | sxyTranslate) }}</th>\r\n          <th class=\"right\">{{ $invCreate.primaryCalcTaxInvoicePreview.invoice.data.dueDate | sxyDate }}</th>\r\n          <th class=\"right\">{{ $invCreate.primaryCalcTaxInvoicePreview.invoice.payment | currency }}</th>\r\n        </tr>\r\n        <tr class=\"no-border\">\r\n          <td colspan=\"5\">\r\n            <salaxy-credit-transfer invoice-preview=\"$invCreate.primaryCalcTaxInvoicePreview\" mode=\"barcode-copy\">\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n    <div ng-if=\"$invCreate.primaryCalcTaxInvoicePreview\" class=\"credit-transfer-container\">\r\n\r\n      <salaxy-credit-transfer invoice-preview=\"$invCreate.primaryCalcTaxInvoicePreview\" mode=\"official\">\r\n        <message>\r\n          <p sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.mobileBanking.tax\"></p>\r\n          <p style=\"text-transform: none;\" sxy-html=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.mobileBanking.taxInfo.html\"></p>\r\n        </message>\r\n      </salaxy-credit-transfer>\r\n    </div>\r\n  </div>\r\n  <div class=\"d-none d-print-block\">\r\n    <h1 ng-if=\"!$ctrl.editDialogParameters.logic.isInspectingPaidInvoices\" sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.mobileBanking.heading\"></h1>\r\n    <div ng-if=\"$invCreate.primaryCalcTaxInvoicePreview\" class=\"credit-transfer-container\">\r\n      <salaxy-credit-transfer invoice-preview=\"$invCreate.primaryCalcTaxInvoicePreview\" mode=\"official\">\r\n        <message>\r\n          <p>Ennakonpidätys</p>\r\n          <p style=\"text-transform: none;\" sxy-html=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.mobileBanking.taxInfo.html\"></p>\r\n        </message>\r\n      </salaxy-credit-transfer>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/personal-payment/TotalWorkerPayment.html\",`<div ng-controller=\"InvoicesCreateController as $invCreate\" ng-init=\"$invCreate.model=$ctrl.model\">\r\n  <div ng-if=\"!$invCreate.isValid\">\r\n    <p sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.invalidCalc\"></p>\r\n    <salaxy-validation-summary api-validation=\"$invCreate.current.result.validation\"></salaxy-validation-summary>\r\n  </div>\r\n  <div ng-if=\"$invCreate.paymentStatus == 'canceled'\">\r\n    <p class=\"lead\" sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.canceled.lead\"></p>\r\n    <p sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.canceled.salaryAlreadyPaid\"></p>\r\n    <ul>\r\n      <li sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.canceled.salaryAlreadyPaidInfo1\"></li>\r\n      <li sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.canceled.salaryAlreadyPaidInfo2\"></li>\r\n      <li sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.canceled.salaryAlreadyPaidInfo3\"></li>\r\n      <li sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.canceled.salaryAlreadyPaidInfo4\"></li>\r\n    </ul>\r\n  </div>\r\n  <div class=\"d-print-none\" ng-if=\"$invCreate.primaryCalcNetInvoicePreview.invoice.status == 'paid'\">\r\n    <p class=\"lead\">\r\n      <button type=\"button\" class=\"btn btn-primary float-end\" onclick=\"window.print()\" sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.printInvoices\"></button> {{'SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.paid.paidInspectNet' |\r\n      sxyTranslate}}\r\n    </p>\r\n    <div ng-if=\"$invCreate.primaryCalcNetInvoicePreview\" class=\"credit-transfer-container\">\r\n      <salaxy-credit-transfer invoice-preview=\"$invCreate.primaryCalcNetInvoicePreview\" mode=\"official\">\r\n        <message>\r\n          <p sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.mobileBanking.salary\"></p>\r\n          <p style=\"text-transform: none;\" sxy-html=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.mobileBanking.salaryInfo.html\"></p>\r\n        </message>\r\n      </salaxy-credit-transfer>\r\n    </div>\r\n  </div>\r\n  <div class=\"d-print-none\" ng-if=\"$invCreate.primaryCalcNetInvoicePreview && $invCreate.primaryCalcNetInvoicePreview.invoice.status != 'paid'\">\r\n    <section>\r\n      <h3 sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.steps.step1.title\"></h3>\r\n      <button type=\"button\" class=\"btn btn-primary float-end\" onclick=\"window.print()\" sxy-text=\"Tulosta\"></button>\r\n      <p class=\"lead\" sxy-html=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.steps.step1.text.html\"></p>\r\n    </section>\r\n    <table class=\"table\">\r\n      <thead>\r\n        <tr>\r\n          <th></th>\r\n          <th sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.preview.receiver\"></th>\r\n          <th sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.preview.iban\"></th>\r\n          <th sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.preview.reference\"></th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.preview.dueDate\"></th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.preview.sum\"></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr>\r\n          <th rowspan=\"2\" style=\"font-size: 2em;\"></th>\r\n          <th>{{ $invCreate.primaryCalcNetInvoicePreview.invoice.otherPartyInfo.avatar.displayName }}</th>\r\n          <th>{{ $invCreate.primaryCalcNetInvoicePreview.invoice.otherPartyInfo.ibanNumber }}</th>\r\n          <th sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.preview.salary\"></th>\r\n          <th class=\"right\">{{ $invCreate.primaryCalcNetInvoicePreview.invoice.data.dueDate | sxyDate }}</th>\r\n          <th class=\"right\">{{ $invCreate.primaryCalcNetInvoicePreview.invoice.payment | currency }}</th>\r\n        </tr>\r\n        <tr class=\"no-border\">\r\n          <td colspan=\"5\">\r\n            <salaxy-credit-transfer invoice-preview=\"$invCreate.primaryCalcNetInvoicePreview\" mode=\"barcode-copy\">\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n    <div ng-if=\"$invCreate.primaryCalcNetInvoicePreview\" class=\"credit-transfer-container\">\r\n      <salaxy-credit-transfer invoice-preview=\"$invCreate.primaryCalcNetInvoicePreview\" mode=\"official\">\r\n        <message>\r\n          <p sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.mobileBanking.salary\"></p>\r\n          <p style=\"text-transform: none;\" sxy-html=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.mobileBanking.salaryInfo.html\"></p>\r\n        </message>\r\n      </salaxy-credit-transfer>\r\n    </div>\r\n  </div>\r\n  <div class=\"d-none d-print-block\">\r\n    <h1 ng-if=\"!$ctrl.editDialogParameters.logic.isInspectingPaidInvoices\" sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.mobileBanking.heading\"></h1>\r\n    <div ng-if=\"$invCreate.primaryCalcNetInvoicePreview\" class=\"credit-transfer-container\">\r\n      <salaxy-credit-transfer invoice-preview=\"$invCreate.primaryCalcNetInvoicePreview\" mode=\"official\">\r\n        <message>\r\n          <p>Palkka</p>\r\n          <p style=\"text-transform: none;\" sxy-html=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.statuses.mobileBanking.salaryInfo.html\"></p>\r\n        </message>\r\n      </salaxy-credit-transfer>\r\n    </div>\r\n  </div>\r\n\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/PSDPaymentOverview.html\",`<div class=\"modal-calc-list\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{ $ctrl.$invCreate.title }}</h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <salaxy-invoices-create model=\"$ctrl.current\" ng-ref=\"$ctrl.$invCreate\"></salaxy-invoices-create>\r\n  </div>\r\n  <div class=\"modal-footer\">\r\n    <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n    \r\n    <button type=\"submit\" class=\"btn btn-secondary ms-auto\" ng-disabled=\"!$ctrl.logic.isReadyForPayment()\" ng-click=\"$close('create-invoices-pay-later')\">\r\n      Luo maksut ja maksa myöhemmin\r\n    </button>\r\n    <button type=\"submit\" class=\"btn btn-primary\" ng-disabled=\"!$ctrl.logic.isReadyForPayment()\" ng-click=\"$close('create-invoices-pay-now')\">\r\n      Maksa nyt\r\n    </button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/row-type-select.html\",`<div class=\"salaxy-component salaxy-calc-details-dialog\">\r\n  <div class=\"card card-list\" ng-class=\"'card-' + ($ctrl.logic.rowTypeSelectHelp || 'primary')\">\r\n    <div class=\"card-header d-flex align-items-center p-3\">\r\n      <h1>{{ \"SALAXY.NG1.CalcDetailsDialogComponent.\" + ($ctrl.logic.rowTypeSelectHelp || \"all\") + \".title\" | sxyTranslate }}</h1>\r\n      <button type=\"button\" class=\"btn-close ms-auto\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n    </div>\r\n    <div class=\"card-body\" ng-if=\"$ctrl.logic.rowTypeSelectHelp\">\r\n      <p>{{ \"SALAXY.NG1.CalcDetailsDialogComponent.\" + ($ctrl.logic.rowTypeSelectHelp || \"all\") + \".intro\" | sxyTranslate }}</p>\r\n    </div>\r\n    <salaxy-calc-row-type name=\"rowType\" type=\"list\" model=\"$ctrl.current\"\r\n      categories=\"$ctrl.logic.categories\"\r\n      row-types=\"$ctrl.logic.rowTypes\"\r\n      on-row-changed=\"$close('ok')\" label-type=\"plain\"></salaxy-calc-row-type>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/SalaryDateKind.html\",`<div class=\"modal-body modal-salary-date-kind\">\r\n  <form class=\"mb-2 form-horizontal\">\r\n    <legend sxy-text=\"{{$ctrl.logic.text}}\"></legend>\r\n    <p sxy-html=\"{{$ctrl.logic.title}}\"></p>\r\n  </form>\r\n  <div class=\"text-end\">\r\n    <button class=\"btn btn-sm btn-default\" ng-click=\"$dismiss()\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n    <button class=\"btn btn-sm btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.select\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/SalaryDateKindInputEnum.html\",`<ng-form name=\"{{$ctrl.name}}Form\" class=\"salaxy-input-enum\">\r\n  <salaxy-form-group ng-if=\"$ctrl.type=='radio'\" name=\"{{$ctrl.name}}\" require=\"$ctrl.require\" label=\"{{$ctrl.label}}\" label-type=\"{{$ctrl.labelType}}\" label-cols=\"{{$ctrl.labelCols}}\">\r\n    <div class=\"radio\" ng-repeat=\"x in $ctrl.getEnumerations()\">\r\n      <label class=\"control-label radio-label\" for=\"{{x.value}}\">\r\n        <input ng-disabled=\"$ctrl.getDisabled()\" type=\"radio\" ng-model=\"$ctrl.value\" ng-change=\"$ctrl.onChange()\" class=\"\" name=\"{{$ctrl.label}}\" id=\"{{x.value}}\" value=\"{{x.value}}\"\r\n          title=\"{{x.title | sxyTranslate}}\">\r\n          <strong>{{$ctrl.formatLabel(x)}}</strong>\r\n          <p ng-if=\"x.title\" class=\"text-small\">{{ x.title | sxyTranslate }}</p>\r\n      </label>\r\n    </div>\r\n  </salaxy-form-group>\r\n</ng-form>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/SelectRuleset.html\",`\r\n<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\">{{$ctrl.logic.title | sxyTranslate}}</h2>\r\n\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n</div>\r\n<div class=\"modal-body\" style=\"max-height: calc(100vh - 300px); overflow-y: auto;\">\r\n  <table class=\"table table-sm table-hover\">\r\n    <thead>\r\n      <tr>\r\n        <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.entry.rulesetSelection.account\"></th>\r\n        <th sxy-text=\"SALAXY.NG1.CalcRowsComponent.editDialog.accounting.entry.rulesetSelection.description\"></th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat=\"ruleset in $ctrl.logic.items\" class=\"clickable\"  ng-click=\"$close(ruleset)\">\r\n        <td>{{ruleset.account}}</td>\r\n        <td>{{ruleset.text}}</td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n  <salaxy-spinner ng-if=\"!$ctrl.logic.items.length\"></salaxy-spinner>\r\n</div>\r\n<div class=\"modal-footer text-end\">\r\n  <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/SelectVersion.html\",`<div class=\"modal-version-list\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{\"Valitse versio\" | sxyTranslate}}</h2>\r\n\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <style>\r\n      .table-hover>tbody>tr:hover>td,\r\n      .table-hover>tbody>tr:hover>th {\r\n        background-color: var(--salaxy-brand-info);\r\n        ;\r\n        text-decoration: none;\r\n      }\r\n    </style>\r\n    <table class=\"table table-sm table-hover\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\" sxy-text=\"SALAXY.NG1.CalcComponent.versions.creator\"></th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.CalcComponent.versions.date\"></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.data.versions\" class=\"clickable\" ng-class=\"{ 'bg-success': $ctrl.data.versionId == row.versionId }\" ng-click=\"$close(row)\">\r\n          <td class=\"align-middle td-avatar\">\r\n            <salaxy-avatar avatar=\"row.userAccount\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"td-name\">\r\n            {{row.userAccount.displayName}}\r\n          </td>\r\n          <td class=\"right\">\r\n            <span>{{row.date | date: 'd.M.yyyy HH:mm:ss' }}</span><br />\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n    <salaxy-spinner ng-if=\"!$ctrl.data.versions.length\"></salaxy-spinner>\r\n  </div>\r\n  <div class=\"modal-footer text-end\">\r\n    <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/TaxcardSelect.html\",`<div class=\"modal-taxcard-list\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{$ctrl.logic.title | sxyTranslate}}</h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <div class=\"table-responsive\" style=\"max-height: calc(100vh - 300px)\">\r\n      <salaxy-taxcard-list mode=\"select\" selected-items=\"$ctrl.current\" options=\"$ctrl.logic.options\" ng-ref=\"$taxcardList\" on-list-select=\"$taxcardList.selectedItems.splice(0, $taxcardList.selectedItems.length);(value == true ? $taxcardList.selectedItems.push(item) : null);\"></salaxy-taxcard-list>\r\n    </div>\r\n    <div class=\"text-right\">\r\n      <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"{{ $ctrl.logic.cancelButtonText || 'SALAXY.UI_Terms.cancel'}}\"></button>\r\n      <button type=\"submit\" ng-disabled=\"$taxcardList.selectedItems.length != 1\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"{{ $ctrl.logic.okButtonText || 'SALAXY.UI_Terms.save'}}\"></button>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/WorkerList.html\",`<div class=\"modal-worker-list\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{$ctrl.logic.title | sxyTranslate}}</h2>\r\n\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <span ng-if=\"$ctrl.logic.infoHtml\" sxy-html=\"{{$ctrl.logic.infoHtml}}\"></span>\r\n    <div class=\"list-content\">\r\n      <salaxy-employment-list mode=\"multiselect\" selected-items=\"$ctrl.current\"></salaxy-employment-list>\r\n    </div>\r\n    <div class=\"text-end\">\r\n      <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n      <button type=\"submit\" class=\"btn btn-primary\" ng-click=\"$close('ok')\">{{$ctrl.logic.okButtonText ? ($ctrl.logic.okButtonText | sxyTranslate) : ('SALAXY.UI_Terms.save' | sxyTranslate)}}</button>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/WorkerSelect.html\",`<div class=\"modal-worker-list\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{$ctrl.logic.title | sxyTranslate}}</h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <span ng-if=\"$ctrl.logic.infoHtml\" sxy-html=\"{{$ctrl.logic.infoHtml}}\"></span>\r\n    <div class=\"list-content\">\r\n      <salaxy-employment-list mode=\"select\" selected-items=\"$ctrl.current\" ng-ref=\"$employmentsList\" on-list-select=\"$employmentsList.selectedItems.splice(0, $employmentsList.selectedItems.length);(value == true ? $employmentsList.selectedItems.push(item) : null);\"></salaxy-employment-list>\r\n    </div>\r\n    <div class=\"text-end\">\r\n      <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n      <button type=\"submit\" class=\"btn btn-primary\" ng-click=\"$close('ok')\">{{$ctrl.logic.okButtonText ? ($ctrl.logic.okButtonText | sxyTranslate) : ('SALAXY.UI_Terms.save' | sxyTranslate)}}</button>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/calc/WSPaymentOverview.html\",`<div class=\"modal-calc-list\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{ $ctrl.$invCreate.title }}</h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <salaxy-invoices-create model=\"$ctrl.current\" ng-ref=\"$ctrl.$invCreate\"></salaxy-invoices-create>\r\n  </div>\r\n  <div class=\"modal-footer\">\r\n    <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n    <button type=\"submit\" class=\"btn btn-primary ms-auto\" ng-if=\"$ctrl.$invCreate.getOkBtn()\" ng-click=\"$ctrl.$invCreate.createInvoices($close)\">\r\n      {{ $ctrl.$invCreate.getOkBtn() }}     \r\n    </button>\r\n    \r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/communications/VarmaPopup.html\",`<div class=\"modal-ui-translation\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{$ctrl.current.title}}</h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n\r\n  <div class=\"modal-body\">\r\n    <p ng-bind-html=\"$ctrl.current.message\"></p>\r\n    <div class=\"row\">\r\n      <div class=\"col-12 mt-2\">\r\n        <button class=\"btn btn-default float-start\" sxy-text=\"SALAXY.UI_Terms.close\" ng-click=\"$close('cancel')\"></button>\r\n        <a class=\"btn btn-primary float-end\" href=\"{{$ctrl.current.varmaShopLink}}\" target=\"_blank\" sxy-text=\"{{$ctrl.current.btnText}}\"></a>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/date-range/DateRange.html\",`<div class=\"modal-body modal-date-range\">\r\n  <form class=\"mb-2 form-horizontal\">\r\n    <salaxy-date-range ng-model=\"$ctrl.current\" label=\"{{ $ctrl.logic.title }}\" name=\"dateRange\" label-type=\"basic\"></salaxy-date-range>\r\n  </form>\r\n  <div class=\"text-end\">\r\n    <button class=\"btn btn-sm btn-default\" ng-click=\"$dismiss()\" sxy-text=\"{{ $ctrl.logic.cancelText }}\"></button>\r\n    <button class=\"btn btn-sm btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"{{ $ctrl.logic.okText }}\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/export/Export.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" id=\"salaxyODataExportTitle\">{{ 'SALAXY.NG1.ODataExportComponent.heading' | sxyTranslate }}</h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n</div>\r\n<div class=\"modal-body\" id=\"modal-body\">\r\n  <div class=\"btn-toolbar\" role=\"toolbar\" aria-label=\"Export options\">\r\n    <div class=\"btn-group dropdown\">\r\n      <button id=\"exportMapper\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\">\r\n        {{ $ctrl.data.$parent.mapper.title }}\r\n      </button>\r\n      <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"exportMapper\">\r\n        <li role=\"menuitem\" ng-repeat=\"mapper in $ctrl.data.$parent.allMappers\">\r\n          <a href=\"\" ng-click=\"$ctrl.data.$parent.setExportMapper(mapper)\" class=\"dropdown-item\">{{mapper.title}}</a></li>\r\n      </ul>\r\n    </div>\r\n    <div class=\"btn-group dropdown ms-1\">\r\n      <button id=\"exportFileType\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\">\r\n        {{ $ctrl.data.$parent.currentExporter.label }}\r\n      </button>\r\n      <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"exportFileType\">\r\n        <li role=\"menuitem\" ng-repeat=\"exporter in $ctrl.data.$parent.exporters\">\r\n          <a href=\"\" ng-click=\"$ctrl.data.$parent.currentExporter = exporter\" class=\"dropdown-item\">{{ exporter.label }}</a></li>\r\n      </ul>\r\n    </div>\r\n    <salaxy-input-enum name=\"localeId\" type=\"dropdown\" enum=\"Culture\" label-type=\"plain\" label-format=\"title\" ng-model=\"$ctrl.data.$parent.localeId\"\r\n      ng-if=\"$ctrl.data.$parent.currentExporter.hasLocales\"></salaxy-input-enum>\r\n    <salaxy-input-enum name=\"maxCount\" type=\"dropdown\" label-type=\"plain\" label-format=\"title\" ng-model=\"$ctrl.data.$parent.maxCount\"\r\n      options=\"$ctrl.data.$parent.maxCountOptions\"></salaxy-input-enum>\r\n    <div class=\"btn-group ms-auto\" sxy-if-role=\"test\">\r\n      <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.data.$parent.toggleDebug()\">Debug <span class=\"badge\">test</span></button>\r\n    </div>\r\n  </div>\r\n  <div ng-if=\"$ctrl.data.$parent.isDebug\">\r\n    <salaxy-data-mapper model=\"$ctrl.data.$parent.mapper\" type=\"debug\"></salaxy-data-mapper>\r\n  </div>\r\n  <div class=\"table-responsive\" style=\"padding-top: 5vh; text-align:center\">\r\n    <button id=\"exportNonQuick\" type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.data.$parent.export()\">\r\n      <span ng-show=\"!$ctrl.data.$parent.isExporting\">{{ 'SALAXY.NG1.ODataExportComponent.createMaterial' | sxyTranslate }} <i class=\"bi bi-download\"></i></span>\r\n      <span ng-show=\"$ctrl.data.$parent.isExporting\">{{ 'SALAXY.NG1.ODataExportComponent.createMaterial' | sxyTranslate }} <i class=\"bi bi-arrow-repeat bi-spin\"></i></span>\r\n    </button>\r\n    <div ng-show=\"$ctrl.data.$parent.isExporting\"><small>&nbsp;{{$ctrl.data.$parent.exportMessage}}</small></div>\r\n  </div>\r\n</div>\r\n\r\n<div class=\"modal-footer\">\r\n  <button type=\"button\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/form-controls/PayStatsRowTypeEdit.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" id=\"payStatsRowTypeHeader\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.inputs.type\"></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$dismiss()\" aria-label=\"Close\"></button>\r\n</div>\r\n<div class=\"modal-body\">\r\n  <form name=\"payStatsRowType\" class=\"form-horizontal\" ng-readonly=\"$ctrl.logic.readOnly\">\r\n    <salaxy-input-enum label=\"SALAXY.NG1.WorkerHolidaysComponent.UI.inputs.type\" name=\"baseType\" type=\"radio\" options=\"{'incomeType': 'SALAXY.NG1.WorkerHolidaysComponent.UI.inputs.incomeType', 'rowType' : 'SALAXY.NG1.WorkerHolidaysComponent.UI.inputs.rowType', 'type': 'SALAXY.NG1.WorkerHolidaysComponent.UI.inputs.wageType'}\" ng-model=\"$ctrl.current.baseType\" require=\"true\"></salaxy-input-enum>\r\n    <salaxy-input-income-type ng-if=\"$ctrl.current.baseType == 'incomeType'\" label=\"SALAXY.NG1.WorkerHolidaysComponent.UI.inputs.incomeType\" name=\"code\" ng-model=\"$ctrl.current.type\" hidden-codes=\"[1]\">\r\n    </salaxy-input-income-type>\r\n    <salaxy-form-group ng-if=\"$ctrl.current.baseType == 'rowType'\" name=\"rowTypeLabel\" label=\"SALAXY.NG1.WorkerHolidaysComponent.UI.inputs.rowType\">\r\n      <salaxy-calc-row-type label=\"SALAXY.NG1.WorkerHolidaysComponent.UI.inputs.rowType\" name=\"rowType\" model=\"$ctrl.logic.asUserDefinedRow($ctrl.current)\" clear-on-select=\"false\"></salaxy-calc-row-type>\r\n    </salaxy-form-group>\r\n    <salaxy-form-group ng-if=\"$ctrl.current.baseType == 'type'\" name=\"type\" label=\"SALAXY.NG1.WorkerHolidaysComponent.UI.inputs.wageType\">\r\n      <salaxy-calc-row-type label=\"SALAXY.NG1.WorkerHolidaysComponent.UI.inputs.wageType\" name=\"type\" model=\"$ctrl.logic.asUserDefinedRow($ctrl.current)\" clear-on-select=\"false\"></salaxy-calc-row-type>\r\n    </salaxy-form-group>\r\n    <salaxy-input-boolean label=\"SALAXY.NG1.WorkerHolidaysComponent.UI.inputs.exclusive\" name=\"isExclusive\" ng-model=\"$ctrl.current.isExclusive\"></salaxy-input-boolean>\r\n    <salaxy-input-enum ng-if=\"$ctrl.current.baseType == 'incomeType' && $ctrl.current.type == '201'\" label=\"SALAXY.NG1.WorkerHolidaysComponent.UI.inputs.unit\" enum=\"CalculationRowUnit\" hidden-options=\"[]\" filter=\"undefined,hours\" name=\"unit\" ng-model=\"$ctrl.current.unit\"></salaxy-input-enum>\r\n  </form>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button type=\"reset\" ng-if=\"!$ctrl.logic.readOnly\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n  <button type=\"button\" ng-if=\"$ctrl.logic.readOnly\" class=\"btn btn-primary\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n  <button type=\"button\" ng-if=\"!$ctrl.logic.readOnly\" class=\"btn btn-primary\" ng-disabled=\"!payStatsRowType.$valid\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n</div>\r\n`);\n\n $templateCache.put(\"salaxy-components/modals/import/Import.html\",`<div>\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\" id=\"salaxyODataExportTitle\">{{'SALAXY.NG1.ODataImportComponent.heading' | sxyTranslate}} {{$ctrl.currentStep.number}}/{{$ctrl.steps.length}}</h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\" id=\"modal-body\">\r\n    <div class=\"salaxy-wizard\">\r\n      <div class=\"wizard-steps\">\r\n        <div class=\"wizard-step\" ng-repeat=\"step in $ctrl.steps\" ng-class=\"{'active': step.active, 'disabled': step.disabled}\">\r\n          <span class=\"salaxy-avatar\">\r\n            <div class=\"wizard-icons-wrapper\">\r\n              <i class=\"bi\" ng-class=\"step.active ? 'bi-circle-fill' : 'bi-circle'\"></i>\r\n              <i class=\"bi bi-circle-fill\"></i>\r\n            </div>\r\n            <strong class=\"number\">{{ step.number }}</strong>\r\n          </span>\r\n          <span class=\"step-text\">{{ step.title | sxyTranslate }}</span>\r\n        </div>\r\n      </div>\r\n      <div class=\"wizard-strikethrough\"></div>\r\n    </div>\r\n    <div class=\"wizard-content\">\r\n      <ng-include src=\"$ctrl.currentStep.view\"></ng-include>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/import/ImportStep1.html\",`<div ng-if=\"!$ctrl.data.$parent.api\" class=\"alert alert-danger\">\r\n  ERROR: No API selected.\r\n</div>\r\n<div ng-if=\"$ctrl.data.$parent.api\">\r\n  <div ng-if=\"$ctrl.data.$parent.api\" class=\"btn-toolbar\" role=\"toolbar\" aria-label=\"Data options\">\r\n    <div class=\"btn-group\" role=\"group\">\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.data.$parent.pasteFromClipboard()\">\r\n        <span>{{'SALAXY.NG1.ODataImportComponent.step1.pasteFromDesktop' | sxyTranslate}} <i class=\"bi bi-clipboard\"></i></span></button>\r\n      <button type=\"button\" class=\"btn btn-default\" ngf-select=\"$ctrl.data.$parent.readFile($file)\" ngf-multiple=\"false\" ngf-max-size=\"10MB\">\r\n        <span>{{'SALAXY.NG1.ODataImportComponent.step1.downloadFile' | sxyTranslate}}... <i class=\"bi bi-file-earmark-text\"></i></span>\r\n      </button>\r\n    </div>\r\n  </div>\r\n  <textarea ng-model=\"$ctrl.data.$parent.batch.rawData\" style=\"width: 100%; height: 300px;\" placeholder=\"{{'SALAXY.NG1.ODataImportComponent.step1.copyExcelFileFromClipboard' | sxyTranslate}}\"></textarea>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button ng-disabled=\"!$ctrl.data.$parent.batch.rawData\" ng-click=\"$ctrl.data.$parent.readBatch();$ctrl.goNext()\" class=\"btn btn-primary\" sxy-text=\"SALAXY.UI_Terms.next\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/import/ImportStep2.html\",`<salaxy-validation-summary api-validation=\"$ctrl.data.$parent.lastResult\"></salaxy-validation-summary>\r\n<div class=\"btn-toolbar\" role=\"toolbar\" aria-label=\"Read options\">\r\n  <div class=\"btn-group dropdown\">\r\n    <button id=\"importMapper\" type=\"button\" class=\"btn dropdown-toggle\" ng-class=\"$ctrl.data.$parent.mapper ? 'btn-primary' : 'btn-danger'\" data-bs-toggle=\"dropdown\">\r\n      {{$ctrl.data.$parent.mapper ? $ctrl.data.$parent.mapper.title : ('SALAXY.NG1.ODataImportComponent.step2.chooseMaterial' | sxyTranslate) }}\r\n    </button>\r\n    <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"importMapper\">\r\n      <li role=\"menuitem\" ng-repeat=\"mapper in $ctrl.data.$parent.objectMappers\">\r\n        <a href=\"\" ng-click=\"$ctrl.data.$parent.setMapper(mapper.value)\" class=\"dropdown-item\">{{mapper.text}}</a>\r\n      </li>\r\n    </ul>\r\n  </div>\r\n  <div class=\"btn-group dropdown ms-1\">\r\n    <button id=\"importFileType\" type=\"button\" class=\"btn dropdown-toggle\" ng-class=\"$ctrl.data.$parent.currentFileParser ? 'btn-primary' : 'btn-danger'\" data-bs-toggle=\"dropdown\">\r\n      {{ $ctrl.data.$parent.currentFileParser.label || ('SALAXY.NG1.ODataImportComponent.step2.chooseFiletype' | sxyTranslate) }}\r\n    </button>\r\n    <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"importFileType\">\r\n      <li role=\"menuitem\" ng-repeat=\"parser in $ctrl.data.$parent.fileParsers\">\r\n        <a href=\"\" ng-click=\"$ctrl.data.$parent.currentFileParser = parser;$ctrl.data.$parent.readBatch()\" class=\"dropdown-item\">{{ parser.label }}</a>\r\n      </li>\r\n    </ul>\r\n  </div>\r\n  <salaxy-input-enum name=\"localeId\" type=\"dropdown\" enum=\"Culture\" label-type=\"plain\" label-format=\"title\" ng-model=\"$ctrl.data.$parent.localeId\"\r\n    ng-change=\"$ctrl.data.$parent.readBatch()\"\r\n    ng-if=\"$ctrl.data.$parent.currentFileParser.hasLocales\"></salaxy-input-enum>\r\n  <div class=\"btn-group ms-auto\" sxy-if-role=\"test\">\r\n    <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.data.$parent.toggleDebug()\">Debug <span class=\"badge\">test</span></button>\r\n  </div>\r\n</div>\r\n<div ng-if=\"!$ctrl.data.$parent.batch.unmappedData.data.length\" class=\"table-responsive\" style=\"padding-top: 5vh; padding-bottom: 10vh; text-align:center\">\r\n  <span></span>\r\n</div>\r\n<div ng-if=\"$ctrl.data.$parent.batch.unmappedData.data.length\" class=\"table-responsive\" style=\"width: 100%; min-height: 300px; max-height: calc(100vh - 450px);\">\r\n  <salaxy-data-mapper ng-if=\"!$ctrl.data.$parent.isDebug\" model=\"$ctrl.data.$parent.batch.parserMapper\"></salaxy-data-mapper>\r\n  <salaxy-data-mapper ng-if=\"$ctrl.data.$parent.isDebug\" model=\"$ctrl.data.$parent.batch.parserMapper\" type=\"debug\"></salaxy-data-mapper>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button ng-click=\"$ctrl.goPrevious()\" class=\"btn float-start btn-default\" sxy-text=\"SALAXY.UI_Terms.previous\"></button>\r\n  <button ng-click=\"$ctrl.data.$parent.mapBatch();$ctrl.goNext()\" ng-disabled=\"!$ctrl.data.$parent.batch.unmappedData.data.length || !$ctrl.data.$parent.mapper\" class=\"btn btn-primary\" sxy-text=\"SALAXY.UI_Terms.next\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/import/ImportStep3.html\",`<div ng-init=\"$ctrl.data.$parent.validateBatch()\">\r\n  <div class=\"alert alert-danger\" ng-if=\"$ctrl.data.$parent.batch.hasDataValidationErrors\" sxy-text=\"SALAXY.NG1.ODataImportComponent.step3.error\"></div>\r\n  <div class=\"btn-toolbar\" role=\"toolbar\" aria-label=\"Validation options\">\r\n    <div class=\"btn-group\" role=\"group\">\r\n      <button id=\"validate\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.data.$parent.validateBatch()\">\r\n        <span>{{ 'SALAXY.NG1.ODataImportComponent.step3.check' | sxyTranslate }}\r\n          <i class=\"bi\" ng-class=\"$ctrl.data.$parent.progress ? 'bi-arrow-repeat bi-spin' : 'bi-check-lg'\"></i></span>\r\n      </button>\r\n      <div ng-show=\"$ctrl.data.$parent.progress\"><small>&nbsp;{{$ctrl.data.$parent.progressMessage}}</small></div>\r\n    </div>\r\n    <div class=\"btn-group ms-1\">\r\n      <button class=\"btn btn-default\" ng-click=\"$ctrl.showTarget = false\" ng-class=\"{ active: !$ctrl.showTarget }\">Lähdedata</button>\r\n      <button class=\"btn btn-default\" ng-click=\"$ctrl.showTarget = true\" ng-class=\"{ active: $ctrl.showTarget }\">Kohdedata</button>\r\n    </div>\r\n    <div class=\"btn-group ms-auto\" sxy-if-role=\"test\">\r\n      <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.data.$parent.toggleDebug()\">Debug <span class=\"badge\">test</span></button>\r\n    </div>\r\n  </div>\r\n  <div ng-if=\"$ctrl.data.$parent.isDebug\">\r\n    <salaxy-data-mapper model=\"$ctrl.data.$parent.batch.mapper\" type=\"debug\"></salaxy-data-mapper>\r\n  </div>\r\n  <div ng-if=\"$ctrl.showTarget && $ctrl.data.$parent.batch.data.length\" class=\"table-responsive\" style=\"width: 100%; min-height: 300px; max-height: calc(100vh - 450px);\">\r\n    <salaxy-data-mapper model=\"$ctrl.data.$parent.batch.mapper\" type=\"target-value\"></salaxy-data-mapper>\r\n  </div>\r\n  <div ng-if=\"!$ctrl.showTarget && $ctrl.data.$parent.batch.data.length\" class=\"table-responsive\" style=\"width: 100%; min-height: 300px; max-height: calc(100vh - 450px);\">\r\n    <salaxy-data-mapper model=\"$ctrl.data.$parent.batch.mapper\" type=\"source-value\"></salaxy-data-mapper>\r\n  </div>\r\n  <div class=\"modal-footer\">\r\n    <button ng-click=\"$ctrl.goPrevious()\" class=\"btn float-start btn-default\" sxy-text=\"SALAXY.UI_Terms.previous\"></button>\r\n    <button ng-click=\"$ctrl.data.$parent.clearLastResult();$ctrl.goNext()\" ng-disabled=\"!$ctrl.data.$parent.batch.isDataValid\" class=\"btn btn-primary ms-auto\" sxy-text=\"SALAXY.UI_Terms.next\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/import/ImportStep4.html\",`<div class=\"alert alert-danger\" ng-if=\"$ctrl.data.$parent.batch.hasDataValidationErrors\" sxy-text=\"SALAXY.NG1.ODataImportComponent.step4.error\"></div>\r\n<div class=\"btn-toolbar\" role=\"toolbar\" aria-label=\"Import options\">\r\n  <div class=\"btn-group\" role=\"group\">\r\n    <div ng-show=\"$ctrl.data.$parent.progress\"><small>&nbsp;{{$ctrl.data.$parent.progressMessage}}</small></div>\r\n  </div>\r\n</div>\r\n<div ng-if=\"$ctrl.data.$parent.batch.data.length\" class=\"table-responsive\" style=\"width: 100%; min-height: 300px; max-height: calc(100vh - 450px);\">\r\n  <table class=\"table table-sm\">\r\n    <thead>\r\n      <tr>\r\n        <th sxy-text=\"SALAXY.NG1.ODataImportComponent.step4.okey\"></th>\r\n        <th ng-repeat=\"header in $ctrl.data.$parent.mapper.target.keys\">{{header}}</th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat=\"row in $ctrl.data.$parent.batch.data\">\r\n        <td>\r\n          <div ng-if=\"row.validation && row.validation.errors && row.validation.errors.length\" ng-repeat=\"error in row.validation.errors\">\r\n            <button type=\"button\" class=\"btn btn-danger\" data-bs-toggle=\"popover\" data-bs-html=\"true\" data-bs-content=\"{{ error.msg }}\" data-bs-title=\"{{ error.code }}\" sxy-bs5-popover>{{ error.code }}</button><br>\r\n          </div>\r\n          <div ng-if=\"row.validation && row.validation.isValid\">\r\n            <span class=\"text-success\" sxy-text=\"SALAXY.NG1.ODataImportComponent.step4.okey\"></span>\r\n          </div>\r\n        </td>\r\n        <td ng-repeat=\"header in $ctrl.data.$parent.mapper.target.keys\" ng-switch=\"header\">\r\n          <!-- HACK: use type information instead of field name to format (or use sxyGrid.) -->\r\n          <span ng-switch-when=\"employment\">\r\n            <salaxy-avatar style=\"font-size: 18px;\" avatar=\"row.employment.personalInfo.avatar\"></salaxy-avatar>\r\n            {{ row.employment.personalInfo.avatar.displayName }}\r\n          </span>\r\n          <span ng-switch-default>{{row[header]}}</span>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button id=\"import\" type=\"button\" class=\"btn btn-default ms-auto\" ng-click=\"$ctrl.data.$parent.importBatch($close)\">\r\n    <span>{{ 'SALAXY.UI_Terms.save' | sxyTranslate }}\r\n      <i class=\"bi\" ng-class=\"$ctrl.data.$parent.progress ? 'bi-arrow-repeat bi-spin' : 'bi-upload'\"></i>\r\n    </span>\r\n  </button>\r\n  <button ng-click=\"$ctrl.data.$parent.clearLastResult();$ctrl.goPrevious()\" class=\"btn float-start btn-default\" sxy-text=\"SALAXY.UI_Terms.previous\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/invoices/company-invoice-dialog.html\",`<div class=\"modal-invoice-group-dialog\" ng-controller=\"InvoiceToolsController as $invoiceTools\" ng-init=\"$invoiceTools.setFileTypes(['pdfFile'])\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.InvoiceDialog.paymentInformation\"></h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <h2 class=\"visible-print-block\" sxy-text=\"SALAXY.NG1.InvoiceDialog.paymentInformation\"></h2>\r\n    <div class=\"row\">\r\n      <div class=\"col-sm-6\">\r\n        <fieldset>\r\n          <legend sxy-text=\"SALAXY.NG1.InvoiceDialog.paymentReceiver\"></legend>\r\n          <salaxy-avatar avatar=\"$ctrl.current.otherPartyInfo.avatar\" class=\"pull-left\" style=\"font-size: 64px; border-bottom: 32px; margin-right:15px;\"></salaxy-avatar>\r\n          <div><strong>{{ $ctrl.current.otherPartyInfo.avatar.displayName }}</strong></div>\r\n          <div>{{ $ctrl.current.otherPartyInfo.officialId }}</div>\r\n          <div ng-if=\"$ctrl.current.otherPartyInfo.ibanNumber\">{{ $ctrl.current.otherPartyInfo.ibanNumber | sxyIban }}</div>\r\n          <div ng-if=\"!$ctrl.current.otherPartyInfo.ibanNumber\" class=\"alert-danger\" sxy-text=\"SALAXY.NG1.InvoiceDialog.noIban\"></div>\r\n        </fieldset>\r\n        <fieldset>\r\n          <legend sxy-text=\"SALAXY.NG1.InvoiceDialog.payer\"></legend>\r\n          <salaxy-avatar avatar=\"$ctrl.current.ownerInfo.avatar\" class=\"pull-left\" style=\"font-size: 64px; border-bottom: 32px; margin-right:15px;\"></salaxy-avatar>\r\n          <div><strong>{{ $ctrl.current.ownerInfo.avatar.displayName }}</strong></div>\r\n          <div>{{ $ctrl.current.ownerInfo.officialId }}</div>\r\n          <div ng-if=\"$ctrl.current.ownerInfo.ibanNumber\">{{ $ctrl.current.ownerInfo.ibanNumber | sxyIban }}</div>\r\n          <div ng-if=\"!$ctrl.current.ownerInfo.ibanNumber\" class=\"alert-danger\" sxy-text=\"SALAXY.NG1.InvoiceDialog.noIban\"></div>\r\n        </fieldset>\r\n      </div>\r\n      <div class=\"col-sm-6 form-horizontal\">\r\n        <fieldset>\r\n          <legend>\r\n            {{\"SALAXY.NG1.InvoiceDialog.invoiceStatus\" | sxyTranslate}}: {{ \"InvoiceStatus.\" + $ctrl.current.status | sxyEnum }}\r\n          </legend>\r\n            <button ng-if=\"$ctrl.logic.parent.showMarkAsPaidButton($ctrl.current)\" class=\"btn btn-primary\" ng-click=\"$ctrl.logic.parent.updateInvoiceStatus($ctrl.current,'paid')\">\r\n              <i class=\"bi bi-check-lg visible-xs me-1\"></i><span class=\"hidden-xs\" sxy-text=\"SALAXY.NG1.InvoicesCompany.setAsPaid\"></span>\r\n            </button> \r\n            <button class=\"btn btn-danger\" ng-if=\"$ctrl.logic.parent.showMarkAsCanceledButton($ctrl.current)\" ng-click=\"$ctrl.logic.parent.updateInvoiceStatus($ctrl.current,'canceled')\">\r\n              <i class=\"bi bi-x-lg visible-xs me-1\"></i><span class=\"hidden-xs\" sxy-text=\"SALAXY.NG1.InvoicesCompany.cancelPayment\"></span>\r\n            </button>\r\n            <p ng-if=\"$ctrl.logic.parent.showIrCancelInfoText($ctrl.current)\" class=\"text-center\" sxy-text=\"SALAXY.NG1.InvoicesCompany.cancelInfoText\"></p>\r\n        </fieldset>\r\n        <div class=\"pull-right\" style=\"width: 160px\" ng-if=\"$ctrl.current.status != 'paid' && $ctrl.current.status != 'canceled' && $ctrl.logic.parent.getQrCode($ctrl.current) !== 'loading' && $ctrl.logic.parent.getQrCode($ctrl.current) !== 'error'\">\r\n          <div height=\"160px\" ng-bind-html=\"$ctrl.logic.parent.getQrCode($ctrl.current)\" ></div>\r\n        </div>\r\n        <div ng-if=\"$ctrl.current.data.totalPaid && $ctrl.current.data.totalPaid != $ctrl.current.payment\">\r\n          \r\n            <h4 style=\"text-decoration: line-through;\">{{'SALAXY.NG1.InvoicesCompany.sum' | sxyTranslate}} {{ $ctrl.current.payment | currency }}</h4>\r\n            <h4>{{'SALAXY.NG1.InvoicesCompany.alreadyPaid' | sxyTranslate}} {{ $ctrl.current.data.totalPaid | currency }}</h4>\r\n            <h4 class=\"total\" style=\"font-weight: bold;\">{{'SALAXY.NG1.InvoicesCompany.payable' | sxyTranslate}} {{ ($ctrl.current.payment - $ctrl.current.data.totalPaid) | currency }}</h4>\r\n          \r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div ng-switch=\"$ctrl.current.status\">\r\n      <div class=\"alert alert-info\" ng-switch-when=\"paid|paymentStarted|read\" ng-switch-when-separator=\"|\" sxy-html=\"SALAXY.NG1.InvoiceDialog.statuses.paidPaymentStartedRead.html\"></div>\r\n      <div class=\"alert alert-info\" ng-switch-when=\"canceled\" sxy-html=\"SALAXY.NG1.InvoiceDialog.statuses.canceled.html\"></div>\r\n      <div class=\"alert alert-danger\" ng-switch-when=\"preview\" sxy-html=\"SALAXY.NG1.InvoiceDialog.statuses.preview.html\"></div>\r\n    </div>\r\n    <div class=\"table-responsive\" ng-if=\"$ctrl.current.status !== 'canceled'\">\r\n      <table class=\"table\">\r\n        <thead>\r\n          <tr>\r\n            <th sxy-text=\"SALAXY.NG1.InvoiceDialog.table.receiver\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.InvoiceDialog.table.receiverIban\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.InvoiceDialog.table.reference\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.InvoiceDialog.table.message\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.InvoiceDialog.table.amount\" class=\"right\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.InvoiceDialog.table.dueDate\" class=\"right\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.InvoiceDialog.table.barcode\" class=\"d-print-none\"></th>\r\n            <th class=\"d-print-none\">PDF</th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr>\r\n            <td>{{ $ctrl.current.otherPartyInfo.avatar.displayName }}</td>\r\n            <td>{{ $ctrl.current.otherPartyInfo.ibanNumber }}</td>\r\n            <td>{{ $ctrl.current.entityType == 'net' ? '' : $ctrl.current.reference }}</td>\r\n            <td>{{ (\"SALAXY.ENUM.InvoiceType.\" + $ctrl.current.entityType + \".label\") | sxyTranslate }}</td>\r\n            <td class=\"right\">{{ $ctrl.logic.parent.getInvoicePayment($ctrl.current) | currency }}</td>\r\n            <td class=\"right\">{{ $ctrl.current.data.dueDate | sxyDate }}</td>\r\n            <td class=\"d-print-none\">\r\n              <a type=\"button\" class=\"btn btn-default btn-block\" ng-href=\"{{$ctrl.logic.parent.getPdfUrl($ctrl.current)}}\"><i class=\"bi bi-file-earmark-pdf text-danger me-1\" title=\"Lataa PDF\"></i>pdf</a>\r\n            </td>\r\n          </tr>\r\n          <tr>\r\n            <td colspan=\"6\" class=\"text-right\" style=\"border-top: 0;padding: 0px;\">\r\n              <div ng-init=\"$ctrl.current.barcode = $ctrl.logic.parent.getBarcodeValue($ctrl.current)\" ng-bind-html=\"$ctrl.logic.parent.getBarcode($ctrl.current)\"></div>\r\n            </td>\r\n            <td class=\"d-print-none\" style=\"border-top: 0;padding: 0px 8px;\">\r\n              <button type=\"button\" class=\"btn btn-default btn-block\" ng-click=\"$ctrl.logic.parent.copyBarcode($ctrl.current)\" sxy-text=\"SALAXY.UI_Terms.copyToClipboard\"></button>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n  </div>\r\n  <div class=\"modal-footer\">\r\n    <button type=\"button\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n    <button type=\"submit\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.ok\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/invoices/company-invoices-date-filter-dialog.html\",`\r\n<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.InvoicesCompany.dateFilterDialogHeading\"></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n</div>\r\n<div class=\"modal-body\" id=\"modal-body\">\r\n<form name=\"dateFilterForm\" class=\"form-horizontal\">\r\n  <div class=\"row\">\r\n    <div class=\"col-sm-12\">\r\n      <salaxy-datepicker-popup label=\"SALAXY.NG1.InvoicesCompany.dateFilterDialogStart\" name=\"startDate\" ng-model=\"$ctrl.logic.startDate\"></salaxy-datepicker-popup>\r\n      <salaxy-datepicker-popup label=\"SALAXY.NG1.InvoicesCompany.dateFilterDialogEnd\" name=\"endDate\" ng-model=\"$ctrl.logic.endDate\"></salaxy-datepicker-popup>\r\n    </div>\r\n  </div>\r\n</form>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button type=\"button\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n  <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.select\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/invoices/invoice-dialog.html\",`<div class=\"modal-invoice-group-dialog\" ng-controller=\"InvoiceToolsController as $invoiceTools\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.InvoiceDialog.paymentInformation\"></h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <h2 class=\"d-none d-print-block\" sxy-text=\"SALAXY.NG1.InvoiceDialog.paymentInformation\"></h2>\r\n    <div class=\"row\">\r\n      <div class=\"col-sm-6\">\r\n        <fieldset>\r\n          <legend sxy-text=\"SALAXY.NG1.InvoiceDialog.paymentReceiver\"></legend>\r\n          <salaxy-avatar avatar=\"$ctrl.current.otherPartyInfo.avatar\" class=\"float-start\" style=\"font-size: 64px; border-bottom: 32px; margin-right:15px;\"></salaxy-avatar>\r\n          <div><strong>{{ $ctrl.current.otherPartyInfo.avatar.displayName }}</strong></div>\r\n          <div>{{ $ctrl.current.otherPartyInfo.officialId }}</div>\r\n          <div ng-if=\"$ctrl.current.otherPartyInfo.ibanNumber\">{{ $ctrl.current.otherPartyInfo.ibanNumber | sxyIban }}</div>\r\n          <div ng-if=\"!$ctrl.current.otherPartyInfo.ibanNumber\" class=\"alert-danger\" sxy-text=\"SALAXY.NG1.InvoiceDialog.noIban\"></div>\r\n        </fieldset>\r\n        <fieldset>\r\n          <legend>Maksaja</legend>\r\n          <salaxy-avatar avatar=\"$ctrl.current.ownerInfo.avatar\" class=\"float-start\" style=\"font-size: 64px; border-bottom: 32px; margin-right:15px;\"></salaxy-avatar>\r\n          <div><strong>{{ $ctrl.current.ownerInfo.avatar.displayName }}</strong></div>\r\n          <div>{{ $ctrl.current.ownerInfo.officialId }}</div>\r\n          <div ng-if=\"$ctrl.current.ownerInfo.ibanNumber\">{{ $ctrl.current.ownerInfo.ibanNumber | sxyIban }}</div>\r\n          <div ng-if=\"!$ctrl.current.ownerInfo.ibanNumber\" class=\"alert-danger\" sxy-text=\"SALAXY.NG1.InvoiceDialog.noIban\"></div>\r\n        </fieldset>\r\n      </div>\r\n      <div class=\"col-sm-6 form-horizontal\">\r\n        <fieldset>\r\n          <legend>{{\"SALAXY.NG1.InvoiceDialog.invoiceStatus\" | sxyTranslate}}: {{ \"InvoiceStatus.\" + $ctrl.current.status | sxyEnum }}</legend>\r\n          <salaxy-form-group name=\"paymentChannel\" label=\"{{'SALAXY.NG1.InvoiceDialog.paymentChannel' | sxyTranslate}}\">\r\n            <div style=\"height:100%\">\r\n              <div style=\"display: inline-block;vertical-align: middle;\">\r\n                <salaxy-avatar style=\"font-size: 2.8em\" avatar=\"$ctrl.logic.parent.getChannelAvatar($ctrl.current.data.channel)\"></salaxy-avatar>\r\n              </div>\r\n              <div style=\"display: inline-block;vertical-align: middle;\">{{ $ctrl.logic.parent.getChannelAvatar($ctrl.current.data.channel).displayName }}</div>\r\n            </div>\r\n          </salaxy-form-group>\r\n          <div class=\"d-print-none\" ng-init=\"$ctrl.logic.newStatus = $ctrl.current.status\">\r\n            <salaxy-input-enum label=\"{{'SALAXY.NG1.InvoiceDialog.changeStatus' | sxyTranslate}}\" name=\"requestedStatus\" options=\"{'unread': ('SALAXY.ENUM.InvoiceStatus.unread.label' | sxyTranslate),'read': ('SALAXY.ENUM.InvoiceStatus.read.label' | sxyTranslate),'waitingConfirmation': ('SALAXY.ENUM.InvoiceStatus.waitingConfirmation.label' | sxyTranslate),'paid': ('SALAXY.ENUM.InvoiceStatus.paid.label' | sxyTranslate),'canceled': ('SALAXY.ENUM.InvoiceStatus.canceled.label' | sxyTranslate)}\" ng-model=\"$ctrl.logic.newStatus\" enum=\"InvoiceStatus\">\r\n            </salaxy-input-enum>\r\n            <salaxy-form-group name=\"statusButton\" label-type=\"empty-label\">\r\n              <button type=\"button\" class=\"btn btn-default float-end\" ng-click=\"$ctrl.logic.parent.updateInvoiceGroupItemStatus($ctrl.current,$ctrl.logic.newStatus)\" sxy-text=\"SALAXY.NG1.InvoiceDialog.change\"></button>\r\n            </salaxy-form-group>\r\n\r\n            <salaxy-input-enum name=\"fileType\" label=\"{{'SALAXY.NG1.InvoiceDialog.downloadInvoice' | sxyTranslate}}\" ng-model=\"$invoiceTools.fileTypeId\" options=\"$invoiceTools.fileTypeOptions\" remember=\"invoice\"></salaxy-input-enum>\r\n\r\n            <salaxy-form-group name=\"exportButton\" label-type=\"empty-label\">\r\n              <button type=\"button\" class=\"btn btn-default float-end\" ng-disabled=\"!$invoiceTools.fileTypeId\" ng-click=\"$invoiceTools.export($ctrl.logic.parent.getGroupItemDataReader($ctrl.current,null),false)\" sxy-text=\"SALAXY.NG1.InvoiceDialog.download\"></button>\r\n            </salaxy-form-group>\r\n          </div>\r\n        </fieldset>\r\n      </div>\r\n    </div>\r\n    <div ng-switch=\"$ctrl.current.status\">\r\n      <div class=\"alert alert-info\" ng-switch-when=\"paid|paymentStarted|read\" ng-switch-when-separator=\"|\" sxy-html=\"SALAXY.NG1.InvoiceDialog.statuses.paidPaymentStartedRead.html\"></div>\r\n      <div class=\"alert alert-info\" ng-switch-when=\"canceled\" sxy-html=\"SALAXY.NG1.InvoiceDialog.statuses.canceled.html\"></div>\r\n      <div class=\"alert alert-danger\" ng-switch-when=\"forecast\" sxy-html=\"SALAXY.NG1.InvoiceDialog.statuses.forecast.html\"></div>\r\n      <div class=\"alert alert-danger\" ng-switch-when=\"preview\" sxy-html=\"SALAXY.NG1.InvoiceDialog.statuses.preview.html\"></div>\r\n    </div>\r\n    <div class=\"table-responsive\">\r\n      <table class=\"table\">\r\n        <thead>\r\n          <tr>\r\n            <th sxy-text=\"SALAXY.NG1.InvoiceDialog.table.receiver\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.InvoiceDialog.table.receiverIban\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.InvoiceDialog.table.reference\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.InvoiceDialog.table.message\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.InvoiceDialog.table.amount\" class=\"right\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.InvoiceDialog.table.dueDate\" class=\"right\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.InvoiceDialog.table.barcode\" class=\"d-print-none\"></th>\r\n            <th class=\"d-print-none\">PDF</th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr>\r\n            <td>{{ $ctrl.current.otherPartyInfo.avatar.displayName }}</td>\r\n            <td ng-if=\"$ctrl.logic.parent.hideBarCode($ctrl.current)\">{{ 'SALAXY.REPORTS.invoice.heading.preview' | sxyTranslate }}</td>\r\n            <td ng-if=\"!$ctrl.logic.parent.hideBarCode($ctrl.current)\">{{ $ctrl.current.otherPartyInfo.ibanNumber }}</td>\r\n            <td>{{ $ctrl.current.reference }}</td>\r\n            <td>{{ (\"SALAXY.ENUM.InvoiceType.\" + $ctrl.current.entityType + \".label\") | sxyTranslate }}</td>\r\n            <td class=\"right\">{{ $ctrl.current.payment | currency }}</td>\r\n            <td class=\"right\">{{ $ctrl.current.data.dueDate | sxyDate }}</td>\r\n            <td class=\"d-print-none\">\r\n              <a type=\"button\" class=\"btn btn-default btn-block\" ng-href=\"{{$ctrl.logic.parent.getPdfUrl($ctrl.current)}}\"><i class=\"bi bi-file-earmark-pdf text-danger me-1\" title=\"Lataa PDF\"></i>pdf</a>\r\n            </td>\r\n          </tr>\r\n          <tr ng-if=\"!$ctrl.logic.parent.hideBarCode($ctrl.current)\">\r\n            <td class=\"qrCode-column\" colspan=\"1\" style=\"border-top: 0; padding: 0px; width: 150px;\">\r\n              <div class=\"text-end\" ng-if=\"$ctrl.logic.parent.getQrCode($ctrl.current) !== 'loading' && $ctrl.logic.parent.getQrCode($ctrl.current) !== 'error'\">\r\n                <div ng-bind-html=\"$ctrl.logic.parent.getQrCode($ctrl.current)\" ></div>\r\n              </div>\r\n            </td>\r\n            <td colspan=\"5\" class=\"text-end\" style=\"border-top: 0;padding: 0px;\">\r\n              <span style=\"font-family: 'Courier New', Courier, monospace; font-size: 1.15em;\">{{$ctrl.logic.parent.getBarcodeValue($ctrl.current)}}</span>\r\n            </td>\r\n            <td class=\"d-print-none\" style=\"border-top: 0;padding: 0px 8px;\">\r\n              <button type=\"button\" class=\"btn btn-default btn-block\" ng-click=\"$ctrl.logic.parent.copyBarcode($ctrl.current)\" sxy-text=\"SALAXY.UI_Terms.copyToClipboard\"></button>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n  </div>\r\n  <div class=\"modal-footer d-print-none\">\r\n    <button type=\"button\" class=\"btn btn-default float-start\" onClick=\"window.print()\" sxy-text=\"SALAXY.UI_Terms.print\"></button>\r\n    <button type=\"button\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n    <button type=\"submit\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.ok\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/invoices/invoice-group-dialog.html\",`<div class=\"modal-invoice-group-dialog\" ng-controller=\"InvoiceToolsController as $invoiceTools\" ng-init=\"($ctrl.current.invoices[0].data.channel == 'palkkausInvoices' || $ctrl.current.invoices[0].data.channel == 'kitsas') ? $invoiceTools.setFileTypes(['pdfFile']) : null\">\r\n  <style>\r\n    @media print {\r\n      #launcher {\r\n        display: none;\r\n      }\r\n      @page {\r\n        margin-bottom: 20mm;\r\n      }\r\n    }\r\n  </style>\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">Maksuaineiston tiedot</h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <h2 class=\"d-none d-print-block\">Maksuaineiston tiedot</h2>\r\n    <div class=\"row\">\r\n      <div class=\"col-sm-6\">\r\n        <fieldset>\r\n          <legend>Maksaja</legend>\r\n          <salaxy-avatar avatar=\"$ctrl.current.ownerInfo.avatar\" class=\"float-start\" style=\"font-size: 64px; border-bottom: 32px; margin-right:15px;\"></salaxy-avatar>\r\n          <div><strong>{{ $ctrl.current.ownerInfo.avatar.displayName }}</strong></div>\r\n          <div>{{ $ctrl.current.ownerInfo.officialId }}</div>\r\n          <div ng-if=\"$ctrl.current.ownerInfo.ibanNumber\">{{ $ctrl.current.ownerInfo.ibanNumber | sxyIban }}</div>\r\n          <div ng-if=\"!$ctrl.current.ownerInfo.ibanNumber\" class=\"alert-danger\" sxy-text=\"SALAXY.NG1.WorkerInfo.noIbanNumber\"></div>\r\n        </fieldset>\r\n      </div>\r\n      <div class=\"col-sm-6 form-horizontal\">\r\n        <fieldset>\r\n          <legend>Aineiston tila: {{ \"InvoiceStatus.\" + $ctrl.current.status | sxyEnum }}</legend>\r\n          <salaxy-form-group name=\"paymentChannel\" label=\"Maksukanava\">\r\n            <div style=\"height:100%\">\r\n              <div style=\"display: inline-block;vertical-align: middle;\">\r\n                <salaxy-avatar style=\"font-size: 2.8em\" avatar=\"$ctrl.logic.parent.getChannelAvatar($ctrl.current.invoices[0].data.channel)\"></salaxy-avatar>\r\n              </div>\r\n              <div style=\"display: inline-block;vertical-align: middle;\">{{ $ctrl.logic.parent.getChannelAvatar($ctrl.current.invoices[0].data.channel).displayName }}</div>\r\n            </div>\r\n          </salaxy-form-group>\r\n          <div class=\"d-print-none\" ng-init=\"$ctrl.logic.newStatus = $ctrl.current.status\">\r\n            <salaxy-input-enum label=\"Vaihda tilaa\" name=\"requestedStatus\" hidden-options=\"undefined,forecast,preview,waitingPalkkaus\" ng-model=\"$ctrl.logic.newStatus\" enum=\"InvoiceStatus\">\r\n            </salaxy-input-enum>\r\n            <salaxy-form-group name=\"statusButton\" label-type=\"empty-label\">\r\n              <button type=\"button\" class=\"btn btn-default float-end\" ng-click=\"$ctrl.logic.parent.updateInvoiceGroupStatus($ctrl.current,$ctrl.logic.newStatus)\">Vaihda</button>\r\n            </salaxy-form-group>\r\n\r\n            <salaxy-input-enum name=\"fileType\" label=\"Lataa aineisto\" ng-model=\"$invoiceTools.fileTypeId\" options=\"$invoiceTools.fileTypeOptions\" remember=\"invoice\"></salaxy-input-enum>\r\n\r\n            <salaxy-form-group name=\"exportButton\" label-type=\"empty-label\">\r\n              <button type=\"button\" class=\"btn btn-default float-end\" ng-disabled=\"!$invoiceTools.fileTypeId\" ng-click=\"$invoiceTools.export($ctrl.logic.parent.getGroupDataReader($ctrl.current,null),false)\">Lataa</button>\r\n            </salaxy-form-group>\r\n          </div>\r\n        </fieldset>\r\n      </div>\r\n    </div>\r\n    <div ng-switch=\"$ctrl.current.status\">\r\n      <div class=\"alert alert-info\" ng-switch-when=\"paid|paymentStarted\" ng-switch-when-separator=\"|\">\r\n        <strong>HUOM</strong>: Aineisto on jo merkitty maksetuksi!<br /> Jos maksat tai lähetät aineiston / maksun uudelleen, varmistathan, ettei maksua makseta kahteen kertaan.\r\n      </div>\r\n      <div class=\"alert alert-info\" ng-switch-when=\"read\">\r\n        <strong>HUOM</strong>: Aineisto on jo merkitty lähetetyksi.<br /> Jos maksat tai lähetät aineiston / maksun uudelleen, varmistathan, ettei maksua makseta kahteen kertaan.\r\n      </div>\r\n      <div class=\"alert alert-info\" ng-switch-when=\"canceled\">\r\n        Aineisto maksut on merkitty perutuksi.<br />\r\n      </div>\r\n      <div class=\"alert alert-info\" ng-switch-when=\"canceled\">\r\n        Aineiston edellisessä maksussa on tapahtunut virheitä.<br />\r\n      </div>\r\n      <div class=\"alert alert-danger\" ng-switch-when=\"forecast\">\r\n        <strong>HUOM</strong>: Aineisto on <strong>Arvio</strong> (forecast).<br /> Tyypillisesti nämä ainestot ovat vain kassavirran suunnittelua varten. Niitä ei ole tarkoitus maksaa, vaan lopullinen lasku tulee laskuttajalta (esim. Työllisyysrahasto).\r\n      </div>\r\n      <div class=\"alert alert-danger\" ng-switch-when=\"preview\">\r\n        <strong>HUOM</strong>: Aineisto on <strong>Esikatselu</strong>-tilassa.<br /> Aineistoon (esim. ennakonpidätys) voi olla vielä tulossa muutoksia. Jos maksat aineiston, varmistathan ettei aineistoon tule enää muutoksia (esim. lisää palkkoja samassa\r\n        kuussa).\r\n      </div>\r\n    </div>\r\n    <div class=\"table-responsive\">\r\n      <table class=\"table\">\r\n        <thead>\r\n          <tr>\r\n            <th>Saajan nimi</th>\r\n            <th>Saajan IBAN</th>\r\n            <th>Viite</th>\r\n            <th>Viesti</th>\r\n            <th class=\"right\">Summa</th>\r\n            <th class=\"right\">Eräpäivä</th>\r\n            <th class=\"d-print-none\"></th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr ng-repeat-start=\"invoice in $ctrl.current.invoices\">\r\n            <td>{{ invoice.otherPartyInfo.avatar.displayName }}</td>\r\n            <td>{{ invoice.otherPartyInfo.ibanNumber }}</td>\r\n            <td>{{ invoice.reference }}</td>\r\n            <td>{{ (\"SALAXY.ENUM.InvoiceType.\" + invoice.entityType + \".label\") | sxyTranslate }}</td>\r\n            <td class=\"right\">{{ invoice.payment | currency }}</td>\r\n            <td class=\"right\">{{ invoice.data.dueDate | sxyDate }}</td>\r\n            <td class=\"d-print-none\"><a type=\"button\" class=\"btn btn-default btn-block\" ng-href=\"{{$ctrl.logic.parent.getPdfUrl(invoice)}}\"><i class=\"bi bi-file-earmark-pdf text-danger me-1\" title=\"Lataa PDF\"></i>pdf</a></td>\r\n          </tr>\r\n          <tr ng-repeat-end>\r\n            <td class=\"qrCode-column\" colspan=\"1\" style=\"border-top: 0;padding: 0px; width: 150px;\">\r\n              <div class=\"text-end\"  ng-if=\"$ctrl.logic.parent.getQrCode(invoice) !== 'loading' && $ctrl.logic.parent.getQrCode(invoice) !== 'error'\">\r\n                <div ng-bind-html=\"$ctrl.logic.parent.getQrCode(invoice)\" ></div>\r\n              </div>\r\n            </td>\r\n            <td colspan=\"5\" style=\"border-top: 0;padding: 0px;\" class=\"text-end\">\r\n              <span style=\"font-family: 'Courier New', Courier, monospace; font-size: 1.15em;\">{{$ctrl.logic.parent.getBarcodeValue(invoice)}}</span>\r\n            </td>\r\n            <td class=\"d-print-none\" style=\"border-top: 0;padding: 0px 8px;\">\r\n              <button type=\"button\" class=\"btn btn-default btn-block\" ng-click=\"$ctrl.logic.parent.copyBarcode(invoice)\">Kopioi</button>\r\n            </td>\r\n          </tr>\r\n          <tr>\r\n            <td></td>\r\n            <td></td>\r\n            <td></td>\r\n            <td></td>\r\n            <td class=\"right\">{{ $ctrl.logic.parent.sumInvoicePayments($ctrl.current.invoices) | currency }}</td>\r\n            <td></td>\r\n            <td></td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n  </div>\r\n  <div class=\"modal-footer d-print-none\">\r\n    <button type=\"button\" class=\"btn btn-default float-start\" onClick=\"window.print()\" sxy-text=\"SALAXY.UI_Terms.print\"></button>\r\n    <button type=\"button\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n    <button type=\"submit\" class=\"btn btn-primary\" ng-click=\"$close('ok')\">OK</button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/invoices/invoice-payment-list-dialog.html\",`<div class=\"modal-invoice-group-dialog\" ng-controller=\"InvoiceToolsController as $invoiceTools\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.InvoiceDialog.paymentInformation\"></h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <h2 class=\"visible-print-block\" sxy-text=\"SALAXY.NG1.InvoiceDialog.paymentInformation\"></h2>\r\n    <div class=\"row\">\r\n      <div class=\"col-sm-6\">\r\n        <fieldset>\r\n          <legend sxy-text=\"SALAXY.NG1.InvoiceDialog.paymentReceiver\"></legend>\r\n          <salaxy-avatar avatar=\"$ctrl.current.otherPartyInfo.avatar\" class=\"pull-left\" style=\"font-size: 64px; border-bottom: 32px; margin-right:15px;\"></salaxy-avatar>\r\n          <div><strong>{{ $ctrl.current.otherPartyInfo.avatar.displayName }}</strong></div>\r\n          <div>{{ $ctrl.current.otherPartyInfo.officialId }}</div>\r\n          <div ng-if=\"$ctrl.current.otherPartyInfo.ibanNumber\">{{ $ctrl.current.otherPartyInfo.ibanNumber | sxyIban }}</div>\r\n          <div ng-if=\"!$ctrl.current.otherPartyInfo.ibanNumber\" class=\"alert-danger\" sxy-text=\"SALAXY.NG1.InvoiceDialog.noIban\"></div>\r\n        </fieldset>\r\n        <fieldset>\r\n          <legend>Maksaja</legend>\r\n          <salaxy-avatar avatar=\"$ctrl.current.ownerInfo.avatar\" class=\"pull-left\" style=\"font-size: 64px; border-bottom: 32px; margin-right:15px;\"></salaxy-avatar>\r\n          <div><strong>{{ $ctrl.current.ownerInfo.avatar.displayName }}</strong></div>\r\n          <div>{{ $ctrl.current.ownerInfo.officialId }}</div>\r\n          <div ng-if=\"$ctrl.current.ownerInfo.ibanNumber\">{{ $ctrl.current.ownerInfo.ibanNumber | sxyIban }}</div>\r\n          <div ng-if=\"!$ctrl.current.ownerInfo.ibanNumber\" class=\"alert-danger\" sxy-text=\"SALAXY.NG1.InvoiceDialog.noIban\"></div>\r\n        </fieldset>\r\n      </div>\r\n      <div class=\"col-sm-6 form-horizontal\">\r\n        <fieldset>\r\n          <legend>{{\"SALAXY.NG1.InvoiceDialog.invoiceStatus\" | sxyTranslate}}: {{ \"InvoiceStatus.\" + $ctrl.current.status | sxyEnum }}</legend>\r\n          <salaxy-form-group name=\"paymentChannel\" label=\"{{'SALAXY.NG1.InvoiceDialog.paymentChannel' | sxyTranslate}}\">\r\n            <div style=\"height:100%\">\r\n              <div style=\"display: inline-block;vertical-align: middle;\">\r\n                <salaxy-avatar style=\"font-size: 2.8em\" avatar=\"$ctrl.logic.parent.getChannelAvatar($ctrl.current.data.channel)\"></salaxy-avatar>\r\n              </div>\r\n              <div style=\"display: inline-block;vertical-align: middle;\">{{ $ctrl.logic.parent.getChannelAvatar($ctrl.current.data.channel).displayName }}</div>\r\n            </div>\r\n          </salaxy-form-group>\r\n          <div class=\"d-print-none\" ng-init=\"$ctrl.logic.newStatus = $ctrl.current.status\">\r\n            <salaxy-input-enum name=\"fileType\" label=\"{{'SALAXY.NG1.InvoiceDialog.downloadInvoice' | sxyTranslate}}\" ng-model=\"$invoiceTools.fileTypeId\" options=\"$invoiceTools.fileTypeOptions\" remember=\"invoice\"></salaxy-input-enum>\r\n            <salaxy-form-group name=\"exportButton\" label-type=\"empty-label\">\r\n              <button type=\"button\" class=\"btn btn-default pull-right\" ng-disabled=\"!$invoiceTools.fileTypeId\" ng-click=\"$invoiceTools.export($ctrl.logic.parent.getGroupItemDataReader($ctrl.current,null, $invoiceTools.fileTypeId),false)\" sxy-text=\"SALAXY.NG1.InvoiceDialog.download\"></button>\r\n            </salaxy-form-group>\r\n          </div>\r\n        </fieldset>\r\n      </div>\r\n    </div>\r\n    <div ng-switch=\"$ctrl.current.status\">\r\n      <div class=\"alert alert-info\" ng-switch-when=\"paid|paymentStarted|read\" ng-switch-when-separator=\"|\" sxy-html=\"SALAXY.NG1.InvoiceDialog.statuses.paidPaymentStartedRead.html\"></div>\r\n      <div class=\"alert alert-info\" ng-switch-when=\"canceled\" sxy-html=\"SALAXY.NG1.InvoiceDialog.statuses.canceled.html\"></div>\r\n      <div class=\"alert alert-danger\" ng-switch-when=\"forecast\" sxy-html=\"SALAXY.NG1.InvoiceDialog.statuses.forecast.html\"></div>\r\n      <div class=\"alert alert-danger\" ng-switch-when=\"preview\" sxy-html=\"SALAXY.NG1.InvoiceDialog.statuses.preview.html\"></div>\r\n    </div>\r\n    <div class=\"table-responsive\">\r\n      <table class=\"table\">\r\n        <thead>\r\n          <tr>\r\n            <th sxy-text=\"SALAXY.NG1.InvoiceDialog.table.receiver\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.InvoiceDialog.table.receiverIban\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.InvoiceDialog.table.reference\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.InvoiceDialog.table.message\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.InvoiceDialog.table.amount\" class=\"right\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.InvoiceDialog.table.dueDate\" class=\"right\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.InvoiceDialog.table.barcode\" class=\"d-print-none\"></th>\r\n            <th class=\"d-print-none\">PDF</th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr>\r\n            <td>{{ $ctrl.current.otherPartyInfo.avatar.displayName }}</td>\r\n            <td ng-if=\"$ctrl.logic.parent.hideBarCode($ctrl.current)\">{{ 'SALAXY.REPORTS.invoice.heading.preview' | sxyTranslate }}</td>\r\n            <td ng-if=\"!$ctrl.logic.parent.hideBarCode($ctrl.current)\">{{ $ctrl.current.otherPartyInfo.ibanNumber }}</td>\r\n            <td>{{ ($ctrl.current.entityType !== 'net' && $ctrl.current.reference) ? $ctrl.current.reference : '' }}</td>\r\n            <td>{{ (\"SALAXY.ENUM.InvoiceType.\" + $ctrl.current.entityType + \".label\") | sxyTranslate }}</td>\r\n            <td class=\"right\">{{ $ctrl.current.payment | currency }}</td>\r\n            <td class=\"right\">{{ $ctrl.current.data.dueDate | sxyDate }}</td>\r\n            <td class=\"d-print-none\">\r\n              <a type=\"button\" class=\"btn btn-default btn-block\" ng-href=\"{{$ctrl.logic.parent.getPdfUrl($ctrl.current)}}\"><i class=\"bi bi-file-earmark-pdf text-danger me-1\" title=\"Lataa PDF\"></i>pdf</a>\r\n            </td>\r\n          </tr>\r\n          <tr ng-if=\"!$ctrl.logic.parent.hideBarCode($ctrl.current)\">\r\n            <td class=\"qrCode-column\" colspan=\"1\" style=\"border-top: 0; padding: 0px; width: 150px;\">\r\n              <div class=\"text-right\"  ng-if=\"$ctrl.logic.parent.getQrCode($ctrl.current) !== 'loading' && $ctrl.logic.parent.getQrCode($ctrl.current) !== 'error'\">\r\n                <div ng-bind-html=\"$ctrl.logic.parent.getQrCode($ctrl.current)\" ></div>\r\n              </div>\r\n            </td>\r\n            <td colspan=\"5\" style=\"border-top: 0;padding: 0px;\" class=\"text-right\">\r\n              <span style=\"font-family: 'Courier New', Courier, monospace; font-size: 1.15em;\">{{$ctrl.logic.parent.getBarcodeValue($ctrl.current)}}</span>\r\n            </td>\r\n            <td class=\"d-print-none\" style=\"border-top: 0;padding: 0px 8px;\">\r\n              <button type=\"button\" class=\"btn btn-default btn-block\" ng-click=\"$ctrl.logic.parent.copyBarcode($ctrl.current)\" sxy-text=\"SALAXY.UI_Terms.copyToClipboard\"></button>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n  </div>\r\n  <div class=\"modal-footer\">\r\n    <button type=\"button\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n    <button type=\"button\" class=\"btn btn-default ms-auto\" onClick=\"window.print()\" sxy-text=\"SALAXY.UI_Terms.print\"></button>\r\n    <button type=\"submit\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.ok\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/localTapiola/Beneficiary-info.html\",`<form name=\"currentForm\" class=\"form-horizontal\" model=\"temp\">\r\n  <span class=\"d-none\">{{ $ctrl.formDataValidity = currentForm.$valid }}</span>\r\n\r\n  <div class=\"text-center intro-col\">\r\n    <h1>{{ $ctrl.currentStep.title }}</h1>\r\n    <h2 class=\"subtitle\" ng-if=\"$ctrl.currentStep.heading != ''\">{{ $ctrl.currentStep.heading }}</h2>\r\n    <p class=\"intro\" ng-if=\"$ctrl.currentStep.intro != ''\">{{ $ctrl.currentStep.intro }}</p>\r\n  </div>\r\n\r\n  <fieldset>\r\n    <legend sxy-text=\"SALAXY.NG1.InsuranceComponent.beneficiaryInfo.wizard.label\"></legend>\r\n    <div class=\"row\" ng-repeat=\"item in $ctrl.current.company.beneficiaries\">\r\n\r\n      <div class=\"col-sm-6\">\r\n        <salaxy-input ng-model=\"item.avatar.displayName\" name=\"beneficiaryName{{$index}}\" label=\"SALAXY.NG1.InsuranceComponent.common.name\" label-type=\"basic\"></salaxy-input>\r\n      </div>\r\n      <div class=\"col-sm-3\">\r\n        <salaxy-input ng-model=\"item.officialId\" name=\"beneficiaryPersonalId{{$index}}\" label=\"SALAXY.NG1.InsuranceComponent.common.ssNumber\" sxy-personal-id-fi label-type=\"basic\"></salaxy-input>\r\n      </div>\r\n      <div class=\"col-sm-3\">\r\n        <salaxy-input ng-model=\"item.nationality\" name=\"beneficiaryNationality{{$index}}\" label=\"SALAXY.NG1.InsuranceComponent.common.nationality\" label-type=\"basic\"></salaxy-input>\r\n      </div>\r\n      <div class=\"col-12 text-end\">\r\n        <button class=\"btn btn-lt btn-danger btn-sm\" ng-click=\"$ctrl.current.company.beneficiaries.splice($index,1)\"><i class=\"bi bi-trash-fill\"></i> <span class=\"d-none d-sm-inline\" sxy-text=\"SALAXY.UI_Terms.delete\"></span></button>\r\n      </div>\r\n      <div class=\"col-12\">\r\n        <hr>\r\n      </div>\r\n    </div>\r\n    <div class=\"row\">\r\n      <div class=\"col-12\">\r\n        <button class=\"btn btn-lt btn-secondary btn-sm\" ng-click=\"$ctrl.current.company.beneficiaries.push({ avatar: {}})\"><i class=\"bi bi-plus-lg\" style=\"margin-right:5px\"></i> {{'SALAXY.NG1.InsuranceComponent.beneficiaryInfo.beneficiariesAdd' | sxyTranslate}}</button>\r\n      </div>\r\n    </div>\r\n  </fieldset>\r\n\r\n\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/localTapiola/buttons-default.html\",`<div class=\"col-6 col-sm-4 text-start\">\r\n  <button ng-click=\"$ctrl.goPrevious()\" class=\"btn btn-lt btn-sm btn-link navi-link\"><i class=\"bi bi-chevron-left\"></i> {{'SALAXY.UI_Terms.previous' | sxyTranslate}}</button>\r\n</div>\r\n<div class=\"col-sm-4 d-none d-sm-block text-center txt-index\">\r\n  <div>{{$ctrl.currentStep.number-1}}/{{$ctrl.steps.length-1}}</div>\r\n</div>\r\n<div class=\"col-6 col-sm-4 text-end\">\r\n\r\n  <button ng-click=\"$ctrl.goNext()\" ng-disabled=\"!$ctrl.canGoNext\" class=\"btn btn-lt btn-sm btn-link navi-link\">{{'SALAXY.UI_Terms.next' | sxyTranslate}} <i class=\"bi bi-chevron-right\"></i></button>\r\n  <!--button ng-click=\"$ctrl.goNext()\" ng-disabled=\"!$ctrl.canGoNext\" class=\"btn-link navi-link\">Seuraava <i class=\"bi bi-chevron-right\"></i></button-->\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/localTapiola/buttons-send.html\",`<div class=\"col-6 col-sm-4 text-start\">\r\n  <button ng-click=\"$ctrl.goPrevious()\" class=\"btn btn-lt btn-sm btn-link navi-link\"><i class=\"bi bi-chevron-left\"></i> {{'SALAXY.UI_Terms.previous' | sxyTranslate}}</button>\r\n</div>\r\n<div class=\"col-sm-4 d-none d-sm-block text-center txt-index\">\r\n  <div>{{$ctrl.currentStep.number-1}}/{{$ctrl.steps.length-1}}</div>\r\n\r\n</div>\r\n<div class=\"col-6 col-sm-4 text-end\">\r\n\r\n  <span>\r\n    <button ng-click=\"$ctrl.send()\" ng-disabled=\"!$ctrl.canGoNext\" class=\"btn btn-lt btn-sm btn-primary\" sxy-text=\"SALAXY.UI_Terms.send\"></button>\r\n  </span>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/localTapiola/ContactInfo-entrepreneur.html\",`<form name=\"currentForm\" class=\"form-horizontal\" ng-model=\"temp\">\r\n\r\n  <span class=\"d-none\">{{ $ctrl.formDataValidity = currentForm.$valid }}</span>\r\n\r\n  <div class=\"text-center intro-col\">\r\n    <h1>{{ $ctrl.currentStep.title }}</h1>\r\n    <h2 class=\"subtitle\" ng-if=\"$ctrl.currentStep.heading != ''\">{{ $ctrl.currentStep.heading }}\r\n    </h2>\r\n\r\n  </div>\r\n\r\n  <fieldset>\r\n    <legend sxy-text=\"SALAXY.NG1.InsuranceComponent.common.insuranceContactPerson\"></legend>\r\n    <div class=\"content row\">\r\n      <div class=\"col-sm-8\">\r\n        <salaxy-input ng-model=\"$ctrl.current.company.contactPerson.avatar.displayName\" name=\"contactName\" label=\"SALAXY.NG1.InsuranceComponent.common.name\" required label-type=\"basic\"></salaxy-input>\r\n      </div>\r\n      <div class=\"col-sm-4\">\r\n        <salaxy-input ng-model=\"$ctrl.current.company.contactPerson.officialId\" name=\"contactSSNumber\" label=\"SALAXY.NG1.InsuranceComponent.common.ssNumber\" required sxy-personal-id-fi label-type=\"basic\"></salaxy-input>\r\n\r\n      </div>\r\n      <div class=\"col-sm-4\">\r\n        <salaxy-input ng-model=\"$ctrl.current.company.contactPerson.telephone\" name=\"contactTelephone\" label=\"SALAXY.NG1.InsuranceComponent.common.telephone\" required sxy-mobile-phone label-type=\"basic\"></salaxy-input>\r\n      </div>\r\n      <div class=\"col-sm-4\">\r\n        <salaxy-input ng-model=\"$ctrl.current.company.contactPerson.email\" name=\"contactEmail\" label=\"SALAXY.NG1.InsuranceComponent.common.email\" required sxy-email label-type=\"basic\"> </salaxy-input>\r\n      </div>\r\n      <div class=\"col-sm-4\">\r\n        <salaxy-input-enum type=\"select\" ng-model=\"$ctrl.current.company.contactPerson.authorizationType\" options=\"{procuration: ('SALAXY.NG1.InsuranceComponent.enums.procurationEnum' | sxyTranslate), powerOfAttorney: ('SALAXY.NG1.InsuranceComponent.enums.powerOfAttorneyEnum' | sxyTranslate), apparentAuthority: ('SALAXY.NG1.InsuranceComponent.enums.apparentAuthorityEnum' | sxyTranslate), other: ('SALAXY.NG1.InsuranceComponent.enums.otherEnum' | sxyTranslate)}\"\r\n          name=\"DelegateType\" enum=\"DelegateType\" label=\"SALAXY.NG1.InsuranceComponent.enums.authorizationTypeLabel\" required label-type=\"basic\"></salaxy-input-enum>\r\n      </div>\r\n    </div>\r\n  </fieldset>\r\n  <fieldset>\r\n    <legend sxy-html=\"SALAXY.NG1.InsuranceComponent.principalBusinessAddress.label.html\"></legend>\r\n    <button class=\"btn btn-lt btn-xs btn-secondary\" ng-click=\"$ctrl.current.company.hasPrincipalBusinessAddress = !$ctrl.current.company.hasPrincipalBusinessAddress\"><i class=\"bi\" style=\"margin-right:5px\" ng-class=\"!$ctrl.current.company.hasPrincipalBusinessAddress ? 'bi bi-plus-lg' : 'bi-x-lg'\"></i> <span ng-if=\"!$ctrl.current.company.hasPrincipalBusinessAddress\" sxy-text=\"SALAXY.NG1.InsuranceComponent.common.addAddressBtn\"></span><span ng-if=\"$ctrl.current.company.hasPrincipalBusinessAddress\" sxy-text=\"SALAXY.UI_Terms.cancelAlt\">Peru</span></button>\r\n\r\n    <div class=\"content row\" ng-if=\"$ctrl.current.company.hasPrincipalBusinessAddress\">\r\n      <div class=\"col-sm-12\">\r\n        <salaxy-input ng-model=\"$ctrl.current.company.principalBusinessAddress.street\" name=\"streetAddress\" label=\"SALAXY.NG1.InsuranceComponent.common.streetAddress\" label-type=\"basic\"></salaxy-input>\r\n      </div>\r\n      <div class=\"col-sm-4\">\r\n        <salaxy-input ng-model=\"$ctrl.current.company.principalBusinessAddress.postalCode\" name=\"postalCode\" label=\"SALAXY.NG1.InsuranceComponent.common.postalCode\" label-type=\"basic\"></salaxy-input>\r\n      </div>\r\n      <div class=\"col-sm-4\">\r\n        <salaxy-input ng-model=\"$ctrl.current.company.principalBusinessAddress.city\" name=\"city\" label=\"SALAXY.NG1.InsuranceComponent.common.city\" label-type=\"basic\"></salaxy-input>\r\n      </div>\r\n      <div class=\"col-sm-4\">\r\n        <salaxy-input-enum options=\"$ctrl.countryCodes\" ng-model=\"$ctrl.current.company.principalBusinessAddress.countryCode\" name=\"country\" label=\"SALAXY.NG1.InsuranceComponent.common.country\" label-type=\"basic\" disable-cache=\"true\"></salaxy-input>\r\n      </div>\r\n    </div>\r\n  </fieldset>\r\n\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/localTapiola/ContactInfo.html\",`<form name=\"currentForm\" class=\"form-horizontal\" ng-model=\"temp\">\r\n\r\n  <span class=\"d-none\">{{ $ctrl.formDataValidity = currentForm.$valid }}</span>\r\n\r\n  <div class=\"text-center intro-col\">\r\n    <h1>{{ $ctrl.currentStep.title }}</h1>\r\n    <h2 class=\"subtitle\" ng-if=\"$ctrl.currentStep.heading != ''\">{{ $ctrl.currentStep.heading }}\r\n    </h2>\r\n    <p class=\"intro\">\r\n      <span ng-if=\"$ctrl.action == 'moveInsurance'\" sxy-text=\"SALAXY.NG1.InsuranceComponent.contactInfo.moveInsuranceInfo\"></span>\r\n    </p>\r\n  </div>\r\n\r\n\r\n  <div class=\"content row\">\r\n    <div class=\"col-12 col-sm-6\">\r\n      <fieldset>\r\n        <legend>Yrityksen tiedot</legend>\r\n        <salaxy-input ng-model=\"$ctrl.current.company.details.avatar.displayName\" name=\"companyName\" label=\"SALAXY.NG1.InsuranceComponent.common.companyName\" readonly=\"true\" label-type=\"basic\"> </salaxy-input>\r\n        <salaxy-input ng-model=\"$ctrl.current.company.details.officialId\" name=\"vatNumber\" label=\"SALAXY.NG1.InsuranceComponent.common.vatNumber\" readonly=\"true\" label-type=\"basic\"></salaxy-input>\r\n        <salaxy-input ng-model=\"$ctrl.current.company.address.street\" name=\"streetAddress\" label=\"SALAXY.NG1.InsuranceComponent.common.streetAddress\" readonly=\"true\" label-type=\"basic\"></salaxy-input>\r\n        <salaxy-input ng-model=\"$ctrl.current.company.address.postalCode\" name=\"postalCode\" label=\"SALAXY.NG1.InsuranceComponent.common.postalCode\" readonly=\"true\" label-type=\"basic\"></salaxy-input>\r\n        <salaxy-input ng-model=\"$ctrl.current.company.address.city\" name=\"city\" label=\"SALAXY.NG1.InsuranceComponent.common.city\" readonly=\"true\" label-type=\"basic\"></salaxy-input>\r\n      </fieldset>\r\n      <fieldset>\r\n        <legend sxy-html=\"SALAXY.NG1.InsuranceComponent.principalBusinessAddress.label.html\"></legend>\r\n        <button class=\"btn btn-lt btn-xs btn-secondary\" ng-click=\"$ctrl.current.company.hasPrincipalBusinessAddress = !$ctrl.current.company.hasPrincipalBusinessAddress\"><i class=\"bi\" style=\"margin-right:5px\" ng-class=\"!$ctrl.current.company.hasPrincipalBusinessAddress ? 'bi bi-plus-lg' : 'bi-x-lg'\"></i> <span ng-if=\"!$ctrl.current.company.hasPrincipalBusinessAddress\" sxy-text=\"SALAXY.NG1.InsuranceComponent.common.addAddressBtn\"></span><span ng-if=\"$ctrl.current.company.hasPrincipalBusinessAddress\"  sxy-text=\"SALAXY.UI_Terms.cancelAlt\">Peru</span></button>\r\n\r\n        <div ng-if=\"$ctrl.current.company.hasPrincipalBusinessAddress\">\r\n          <salaxy-input ng-model=\"$ctrl.current.company.principalBusinessAddress.street\" name=\"streetAddress\" label=\"SALAXY.NG1.InsuranceComponent.common.streetAddress\" label-type=\"basic\"></salaxy-input>\r\n          <salaxy-input ng-model=\"$ctrl.current.company.principalBusinessAddress.postalCode\" name=\"postalCode\" label=\"SALAXY.NG1.InsuranceComponent.common.postalCode\" label-type=\"basic\"></salaxy-input>\r\n          <salaxy-input ng-model=\"$ctrl.current.company.principalBusinessAddress.city\" name=\"city\" label=\"SALAXY.NG1.InsuranceComponent.common.city\" label-type=\"basic\"></salaxy-input>\r\n          <salaxy-input-typeahead options=\"$ctrl.countryCodes\" ng-model=\"$ctrl.current.company.principalBusinessAddress.countryCode\" name=\"country\" label=\"SALAXY.NG1.InsuranceComponent.common.country\" label-type=\"basic\"></salaxy-typeahead>\r\n        </div>\r\n      </fieldset>\r\n\r\n    </div>\r\n    <div class=\"col-12 col-sm-6\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.InsuranceComponent.common.insuranceContactPerson\"></legend>\r\n        <salaxy-input ng-model=\"$ctrl.current.company.contactPerson.avatar.displayName\" name=\"contactName\" label=\"SALAXY.NG1.InsuranceComponent.common.name\" required label-type=\"basic\"></salaxy-input>\r\n        <salaxy-input ng-model=\"$ctrl.current.company.contactPerson.officialId\" name=\"contactSSNumber\" label=\"SALAXY.NG1.InsuranceComponent.common.ssNumber\" required sxy-personal-id-fi label-type=\"basic\"></salaxy-input>\r\n        <salaxy-input ng-model=\"$ctrl.current.company.contactPerson.telephone\" name=\"contactTelephone\" label=\"SALAXY.NG1.InsuranceComponent.common.telephone\" required sxy-mobile-phone label-type=\"basic\"></salaxy-input>\r\n        <salaxy-input ng-model=\"$ctrl.current.company.contactPerson.email\" name=\"contactEmail\" label=\"SALAXY.NG1.InsuranceComponent.common.email\" required sxy-email label-type=\"basic\"> </salaxy-input>\r\n        <salaxy-input-enum type=\"select\" ng-model=\"$ctrl.current.company.contactPerson.authorizationType\" options=\"{procuration: ('SALAXY.NG1.InsuranceComponent.enums.procurationEnum' | sxyTranslate), powerOfAttorney: ('SALAXY.NG1.InsuranceComponent.enums.powerOfAttorneyEnum' | sxyTranslate), apparentAuthority: ('SALAXY.NG1.InsuranceComponent.enums.apparentAuthorityEnum' | sxyTranslate), other: ('SALAXY.NG1.InsuranceComponent.enums.otherEnum' | sxyTranslate)}\"\r\n          name=\"DelegateType\" enum=\"DelegateType\" label=\"SALAXY.NG1.InsuranceComponent.common.procura\" required label-type=\"basic\"></salaxy-input-enum>\r\n      </fieldset>\r\n    </div>\r\n  </div>\r\n\r\n\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/localTapiola/Entrepreneur.html\",`<form name=\"currentForm\" class=\"form-horizontal\" ng-model=\"temp\">\r\n\r\n  <span class=\"d-none\">{{ $ctrl.formDataValidity = currentForm.$valid }}</span>\r\n\r\n  <div class=\"text-center intro-col\">\r\n    <h1>{{ $ctrl.currentStep.title }}</h1>\r\n    <h2 class=\"subtitle\" ng-if=\"$ctrl.currentStep.heading != ''\">{{ $ctrl.currentStep.heading }}\r\n      </h23>\r\n      <p class=\"intro\" ng-if=\"$ctrl.currentStep.intro != ''\">{{ $ctrl.currentStep.intro }}\r\n      </p>\r\n  </div>\r\n  <fieldset>\r\n    <legend sxy-text=\"SALAXY.NG1.InsuranceComponent.entrepreneur.companyInfo\"></legend>\r\n    <div class=\"row\">\r\n      <div class=\"col-sm-8\">\r\n        <salaxy-input ng-model=\"$ctrl.current.company.details.avatar.displayName\" name=\"companyName\" label=\"SALAXY.NG1.InsuranceComponent.common.companyName\" readonly=\"true\" label-type=\"basic\"> </salaxy-input>\r\n      </div>\r\n      <div class=\"col-sm-4\">\r\n        <salaxy-input ng-model=\"$ctrl.current.company.details.officialId\" name=\"vatNumber\" label=\"SALAXY.NG1.InsuranceComponent.common.vatNumber\" readonly=\"true\" label-type=\"basic\" sxy-company-id-fi></salaxy-input>\r\n      </div>\r\n    </div>\r\n  </fieldset>\r\n  <fieldset>\r\n    <legend sxy-text=\"SALAXY.NG1.InsuranceComponent.entrepreneur.entrepreneurInsuranceInfo\"></legend>\r\n    <div class=\"row\" ng-repeat=\"item in $ctrl.current.items\">\r\n      <div class=\"col-sm-8\">\r\n        <salaxy-input ng-model=\"item.insuredName\" name=\"entrepreneurName{{$index}}\" label=\"SALAXY.NG1.InsuranceComponent.entrepreneur.entrepreneurName\" required label-type=\"basic\"></salaxy-input>\r\n      </div>\r\n      <div class=\"col-sm-4\">\r\n        <salaxy-input ng-model=\"item.insuredOfficialId\" name=\"entrepreneurSSNumber{{$index}}\" label=\"SALAXY.NG1.InsuranceComponent.common.ssNumber\" required label-type=\"basic\" sxy-personal-id-fi></salaxy-input>\r\n      </div>\r\n      <div class=\"col-sm-8\">\r\n        <salaxy-input-enum type=\"select\" ng-model=\"item.orderType\" options=\"{newEntrepreneurInsurance: ('SALAXY.NG1.InsuranceComponent.entrepreneur.newEntrepreneurInsuranceEnum' | sxyTranslate), moveEntrepreneurInsurance: ('SALAXY.NG1.InsuranceComponent.entrepreneur.moveEntrepreneurInsuranceEnum' | sxyTranslate)}\"\r\n          name=\"InsuranceOrder{{$index}}\" enum=\"InsuranceOrder\" label=\"SALAXY.NG1.InsuranceComponent.entrepreneur.insuranceLabel\" required label-type=\"basic\"></salaxy-input-enum>\r\n      </div>\r\n      <div class=\"col-sm-4\">\r\n        <salaxy-input ng-if=\"item.orderType == 'moveEntrepreneurInsurance'\" ng-model=\"item.oldInsuranceCompany\" label=\"SALAXY.NG1.InsuranceComponent.common.oldInsuranceCompany\" name=\"insuranceCompany{{$index}}\" label-type=\"basic\" required></salaxy-input>\r\n      </div>\r\n\r\n      <div class=\"col-sm-8\">\r\n        <salaxy-datepicker-popup ng-if=\"item.orderType == 'newEntrepreneurInsurance'\" ng-model=\"item.startDate\" name=\"insuranceForEntrepreneurStartDate{{$index}}\" placeholder=\"pp.kk.vvvv\" label=\"SALAXY.NG1.InsuranceComponent.common.startDate\"\r\n          min-date=\"$ctrl.today\" label-type=\"basic\" tooltip-html=\"{{'SALAXY.NG1.InsuranceComponent.common.startDateToolTip' | sxyTranslate}}\" require=\"true\"></salaxy-datepicker-popup>\r\n        <salaxy-input-enum ng-if=\"item.orderType == 'moveEntrepreneurInsurance'\" label=\"SALAXY.NG1.InsuranceComponent.common.startDate\" type=\"select\" options=\"$ctrl.insuranceStartingPointDateOptions\" placeholder=\"SALAXY.UI_Terms.select\" ng-model=\"item.startDate\"\r\n          name=\"insuranceMoveForEntrepreneurStartDate{{$index}}\" label-type=\"basic\" required></salaxy-input-enum>\r\n      </div>\r\n      <div class=\"col-sm-4\">\r\n        <salaxy-input-enum label=\"SALAXY.NG1.InsuranceComponent.common.billingInterval\" options=\"{1:'1', 2:'2', 3:'3', 4:'4'}\" ng-model=\"item.billingInterval\" name=\"billing{{$index}}\" label-type=\"basic\" required></salaxy-input-enum>\r\n      </div>\r\n\r\n\r\n      <div class=\"col-sm-8\">\r\n        <salaxy-input-occupation-type name=\"occupationType{{$index}}\" ng-model=\"item.occupations[0].occupationCode\" label=\"SALAXY.NG1.InsuranceComponent.common.occupationCode\" label-type=\"basic\" required></salaxy-input-occupation-type>\r\n      </div>\r\n      <div class=\"col-sm-4 \">\r\n        <salaxy-input ng-model=\"item.occupations[0].estimatedIncome\" name=\"YELincome{{$index}}\" label=\"SALAXY.NG1.InsuranceComponent.entrepreneur.estimatedIncome\" label-type=\"basic\" required></salaxy-input>\r\n      </div>\r\n      <div class=\"col-12 text-end\">\r\n        <button class=\"btn-lt btn-sm btn-danger\" ng-click=\"$ctrl.current.items.splice($index,1)\"><i class=\"bi bi-trash-fill\"></i> <span sxy-text=\"SALAXY.UI_Terms.delete\"></span></button>\r\n      </div>\r\n      <div class=\"col-12\">\r\n        <hr>\r\n      </div>\r\n    </div>\r\n    <div class=\"row\">\r\n      <div class=\"col-12\">\r\n        <button class=\"btn btn-lt btn-secondary btn-sm\" ng-click=\"$ctrl.current.items.push({ occupations: [{}]})\"><i class=\"bi bi-plus-lg\" style=\"margin-right:5px\"></i> {{'SALAXY.NG1.InsuranceComponent.entrepreneur.addEntrepreneur' | sxyTranslate}}</button>\r\n      </div>\r\n    </div>\r\n  </fieldset>\r\n\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/localTapiola/InsuranceInfo-move.html\",`<form name=\"currentForm\" class=\"form-horizontal\" ng-model=\"temp\">\r\n\r\n  <span class=\"d-none\">{{ $ctrl.formDataValidity = currentForm.$valid }}</span>\r\n\r\n  <div class=\" text-center intro-col\">\r\n    <h1>{{ $ctrl.currentStep.title }}</h1>\r\n    <h2 class=\"subtitle\" ng-if=\"$ctrl.currentStep.heading != ''\">{{ $ctrl.currentStep.heading }}\r\n    </h2>\r\n    <p class=\"intro\" sxy-text=\"SALAXY.NG1.InsuranceComponent.insuranceMove.intro\" ps=\".\"></p>\r\n  </div>\r\n\r\n  <div class=\"row\">\r\n    <div class=\"col-sm-6\">\r\n      <salaxy-input-enum label=\"SALAXY.NG1.InsuranceComponent.common.startDate\" type=\"select\" options=\"$ctrl.insuranceStartingPointDateOptions\" placeholder=\"SALAXY.UI_Terms.select\" ng-model=\"$ctrl.current.items[0].startDate\" name=\"insuranceStartDate\" label-type=\"basic\"\r\n        required></salaxy-input-enum>\r\n    </div>\r\n    <div class=\"col-sm-6\">\r\n      <salaxy-input-enum label=\"SALAXY.NG1.InsuranceComponent.common.billingInterval\" options=\"{1:'1', 2:'2', 3:'3', 4:'4'}\" ng-model=\"$ctrl.current.items[0].billingInterval\" name=\"billing\" label-type=\"basic\" required></salaxy-input-enum>\r\n    </div>\r\n    <div class=\"col-sm-6\">\r\n      <salaxy-input ng-model=\"$ctrl.current.items[0].oldInsuranceCompany\" label=\"SALAXY.NG1.InsuranceComponent.common.oldInsuranceCompany\" name=\"insuranceCompany\" label-type=\"basic\" required></salaxy-input>\r\n    </div>\r\n    <div class=\"col-sm-6\">\r\n      <salaxy-input ng-model=\"$ctrl.current.items[0].industry\" name=\"industry\" label=\"SALAXY.NG1.InsuranceComponent.common.industry.label\" label-type=\"basic\" required tooltip-html=\"{{'SALAXY.NG1.InsuranceComponent.common.industry.html' | sxyTranslate}}\" tooltip-placement=\"right\"></salaxy-input>\r\n\r\n    </div>\r\n  </div>\r\n  <div class=\"row\" ng-repeat=\"item in $ctrl.current.items[0].occupations\">\r\n    <div class=\"col-sm-6\">\r\n      <salaxy-input-occupation-type name=\"occupationType\" ng-model=\"item.occupationCode\" label=\"SALAXY.NG1.InsuranceComponent.common.occupationCode\" label-type=\"basic\" required></salaxy-input-occupation-type>\r\n    </div>\r\n    <div class=\"col-sm-4 col-9\">\r\n      <salaxy-input ng-model=\"item.estimatedIncome\" name=\"salary\" label=\"SALAXY.NG1.InsuranceComponent.common.salaryLabel\" sxy-currency label-type=\"basic\" required></salaxy-input>\r\n    </div>\r\n    <div class=\"col-sm-2 col-3 text-end delete-row-col\">\r\n      <button class=\"btn btn-lt btn-danger btn-sm\" ng-click=\"$ctrl.current.items[0].occupations.splice($index,1)\"><i class=\"bi bi-trash-fill\"></i> <span class=\"d-none d-sm-inline\" sxy-text=\"SALAXY.UI_Terms.delete\"></span></button>\r\n    </div>\r\n  </div>\r\n  <div class=\"row\">\r\n    <div class=\"col-12\">\r\n      <button class=\"btn btn-lt btn-secondary btn-sm\" ng-click=\"$ctrl.current.items[0].occupations.push({})\"><i class=\"bi bi-plus-lg\" style=\"margin-right:5px\"></i> {{'SALAXY.NG1.InsuranceComponent.common.addOccupation' | sxyTranslate}}</button>\r\n    </div>\r\n  </div>\r\n\r\n\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/localTapiola/InsuranceInfo-new.html\",`<form name=\"currentForm\" class=\"form-horizontal\" model=\"temp\">\r\n  <span class=\"d-none\">{{ $ctrl.formDataValidity = currentForm.$valid }}</span>\r\n  <div class=\"text-center intro-col\">\r\n    <h1>{{ $ctrl.currentStep.title }}</h1>\r\n    <h2 class=\"subtitle\" ng-if=\"$ctrl.currentStep.heading != ''\">{{ $ctrl.currentStep.heading }}\r\n    </h2>\r\n    <p class=\"intro\" ng-if=\"$ctrl.currentStep.intro != ''\">{{ $ctrl.currentStep.intro }}</p>\r\n  </div>\r\n  <div class=\"row\">\r\n    <div class=\"col-md-5\">\r\n      <salaxy-datepicker-popup ng-model=\"$ctrl.current.items[0].startDate\" placeholder=\"pp.kk.vvvv\" name=\"insuranceStartDate\" label=\"SALAXY.NG1.InsuranceComponent.common.startDate\" min-date=\"$ctrl.today\"\r\n        label-type=\"basic\" require=\"true\" tooltip-html=\"{{'SALAXY.NG1.InsuranceComponent.common.startDateToolTip' | sxyTranslate}}\"></salaxy-datepicker-popup>\r\n    </div>\r\n    <div class=\"col-md-4\">\r\n      <salaxy-input-enum label=\"SALAXY.NG1.InsuranceComponent.common.billingInterval\" options=\"{1:'1', 2:'2', 3:'3', 4:'4'}\" ng-model=\"$ctrl.current.items[0].billingInterval\" name=\"billing\" label-type=\"basic\" required></salaxy-input-enum>\r\n    </div>\r\n    <div class=\"col-md-3\">\r\n      <salaxy-input ng-model=\"$ctrl.current.items[0].industry\" name=\"industry\" label=\"SALAXY.NG1.InsuranceComponent.common.industry.label\" label-type=\"basic\" required tooltip-html=\"{{'SALAXY.NG1.InsuranceComponent.common.industry.html' | sxyTranslate}}\" tooltip-placement=\"top-right\"></salaxy-input>\r\n    </div>\r\n  </div>\r\n  <div class=\"row\" ng-repeat=\"item in $ctrl.current.items[0].occupations\">\r\n    <div class=\"col-md-6\">\r\n      <salaxy-input-occupation-type name=\"occupationType\" ng-model=\"item.occupationCode\" label=\"SALAXY.NG1.InsuranceComponent.common.occupationCode\" label-type=\"basic\" required></salaxy-input-occupation-type>\r\n    </div>\r\n    <div class=\"col-md-4 col-9\">\r\n      <salaxy-input ng-model=\"item.estimatedIncome\" name=\"salary\" label=\"SALAXY.NG1.InsuranceComponent.common.salaryLabel\" sxy-currency label-type=\"basic\" required></salaxy-input>\r\n    </div>\r\n    <div class=\"col-md-2 col-3 text-end delete-row-col\">\r\n      <button class=\"btn-lt btn-danger btn-sm\" ng-click=\"$ctrl.current.items[0].occupations.splice($index,1)\"><i class=\"bi bi-trash-fill\" ></i> <span class=\"d-none d-sm-inline\" sxy-text=\"SALAXY.UI_Terms.delete\"></span></button>\r\n    </div>\r\n  </div>\r\n  <div class=\"row\">\r\n    <div class=\"col-12\">\r\n      <button class=\"btn btn-lt btn-secondary btn-sm\" ng-click=\"$ctrl.current.items[0].occupations.push({})\"><i class=\"bi bi-plus-lg\" style=\"margin-right:5px\"></i> {{'SALAXY.NG1.InsuranceComponent.common.addOccupation' | sxyTranslate}}</button>\r\n    </div>\r\n  </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/localTapiola/Owner-info.html\",`<form name=\"currentForm\" class=\"form-horizontal\" model=\"temp\">\r\n  <span class=\"d-none\">{{ $ctrl.formDataValidity = currentForm.$valid }}</span>\r\n\r\n  <div class=\"text-center intro-col\">\r\n    <h1>{{ $ctrl.currentStep.title }}</h1>\r\n    <h2 class=\"subtitle\" ng-if=\"$ctrl.currentStep.heading != ''\">{{ $ctrl.currentStep.heading }}\r\n    </h2>\r\n    <p class=\"intro\" sxy-text=\"SALAXY.NG1.InsuranceComponent.ownerInfo.intro\" ps=\".\"></p>\r\n    <p sxy-text=\"SALAXY.NG1.InsuranceComponent.ownerInfo.introInfo\" ps=\".\"></p>\r\n  </div>\r\n\r\n\r\n\r\n  <fieldset>\r\n    <legend sxy-text=\"SALAXY.NG1.InsuranceComponent.ownerInfo.ownerInfo\"></legend>\r\n\r\n    <div class=\"row\" ng-repeat=\"item in $ctrl.current.company.owners\">\r\n      <div class=\"col-sm-8\">\r\n        <salaxy-input ng-model=\"item.avatar.displayName\" name=\"ownerName{{$index}}\" label=\"SALAXY.NG1.InsuranceComponent.ownerInfo.displayName\" label-type=\"basic\"></salaxy-input>\r\n      </div>\r\n      <div class=\"col-sm-4\">\r\n        <salaxy-input ng-model=\"item.officialId\" name=\"ownerPersonalId{{$index}}\" label=\"SALAXY.NG1.InsuranceComponent.ownerInfo.officialId\" label-type=\"basic\"></salaxy-input>\r\n      </div>\r\n      <div class=\"col-sm-8\">\r\n        <salaxy-input ng-model=\"item.address\" name=\"ownerAddress{{$index}}\" label=\"SALAXY.NG1.InsuranceComponent.ownerInfo.address\" label-type=\"basic\"></salaxy-input>\r\n      </div>\r\n      <div class=\"col-sm-4\">\r\n        <salaxy-input ng-model=\"item.percentOfShares\" name=\"ownerShare{{$index}}\" label=\"SALAXY.NG1.InsuranceComponent.ownerInfo.percentOfShares\" label-type=\"basic\"></salaxy-input>\r\n      </div>\r\n      <div class=\"col-12 text-end\">\r\n        <button class=\"btn btn-lt btn-danger btn-sm\" ng-click=\"$ctrl.current.company.owners.splice($index,1)\"><i class=\"bi bi-trash-fill\"></i> {{'SALAXY.UI_Terms.delete' | sxyTranslate}}</button>\r\n      </div>\r\n      <div class=\"col-12\">\r\n        <hr>\r\n      </div>\r\n\r\n    </div>\r\n\r\n    <div class=\"row\">\r\n      <div class=\"col-12 \">\r\n        <button class=\"btn btn-lt btn-secondary btn-sm\" ng-click=\"$ctrl.current.company.owners.push({ avatar: {}})\"><i class=\"bi bi-plus-lg\" style=\"margin-right:5px\"></i>{{'SALAXY.NG1.InsuranceComponent.ownerInfo.addOwner' | sxyTranslate}}</button>\r\n      </div>\r\n    </div>\r\n  </fieldset>\r\n  <fieldset>\r\n    <legend sxy-text=\"SALAXY.NG1.InsuranceComponent.ownerInfo.additionalOwnerInfo\"></legend>\r\n    <salaxy-input-boolean ng-model=\"$ctrl.current.company.complexOwnerStructure\" label-type=\"no-label\" name=\"additionalOwnerInfo\" type=\"checkbox\" label-true=\"SALAXY.NG1.InsuranceComponent.ownerInfo.additionalOwnerInfoLabel\"></salaxy-input-boolean>\r\n  </fieldset>\r\n\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/localTapiola/Start.html\",`<div class=\"row row-video\">\r\n  <div class=\"col-sm-6\">\r\n    <h1 class=\"text-center\" sxy-text=\"SALAXY.NG1.InsuranceComponent.start.wizard.title2\"></h1>\r\n  </div>\r\n  <div class=\"col-sm-6\" class=\"text-center\">\r\n    <div class=\"video-wrapper\">\r\n      <div class=\"videoWrapper\">\r\n        <iframe src=\"https://www.youtube.com/embed/LDuzMEsPz4o\" frameborder=\"0\" allow=\"autoplay; encrypted-media\" allowfullscreen></iframe>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>\r\n<div class=\"row\">\r\n  <div class=\"col-12 mb-2\">\r\n    <h2 class=\"start-subtitle text-center\" sxy-text=\"SALAXY.NG1.InsuranceComponent.start.heading\"></h2>\r\n    <p class=\"text-center\" sxy-text=\"SALAXY.NG1.InsuranceComponent.start.infoText\" ps=\".\"></p>\r\n  </div>\r\n  <div class=\"col-12 col-sm-6 text-center mb-2\">\r\n    <button type=\"button\" class=\"btn btn-lt btn-primary btn-sm\" ng-click=\"$ctrl.setInsuranceAction('newInsurance'); $ctrl.goNext()\" sxy-text=\"SALAXY.NG1.InsuranceComponent.start.newInsurance\"></button>\r\n  </div>\r\n  <div class=\"col-12 col-sm-6 text-center mb-2\">\r\n    <button type=\"button\" class=\"btn btn-lt btn-primary btn-sm\" ng-click=\"$ctrl.setInsuranceAction('moveInsurance'); $ctrl.goNext()\" sxy-text=\"SALAXY.NG1.InsuranceComponent.start.moveInsurance\"></button>\r\n  </div>\r\n  <div class=\"col-12 text-center mb-2\">\r\n    <button type=\"button\" class=\"btn btn-lt btn-primary btn-sm\" ng-click=\"$ctrl.setInsuranceAction('newInsuranceForEntrepreneur'); $ctrl.goNext()\" sxy-text=\"SALAXY.NG1.InsuranceComponent.start.newInsuranceForEntrepreneur\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/localTapiola/ThankYou.html\",`<div class=\"text-center mb-2\">\r\n  <h1>\r\n    {{ $ctrl.currentStep.title }}\r\n  </h1>\r\n\r\n\r\n  <p class=\"intro\" sxy-text=\"SALAXY.NG1.InsuranceComponent.thankYou.intro\" ps=\".\"></p>\r\n\r\n  <p ng-if=\"$ctrl.action == 'newInsurance' || $ctrl.action == 'moveInsurance'\" sxy-html=\"SALAXY.NG1.InsuranceComponent.thankYou.notNewInsuranceForEntrepreneur.html\"></p>\r\n  <p ng-if=\"$ctrl.action == 'newInsuranceForEntrepreneur'\" sxy-html=\"SALAXY.NG1.InsuranceComponent.thankYou.newInsuranceForEntrepreneur.html\"></p>\r\n</div>\r\n\r\n<div class=\"row\" ng-if=\"$ctrl.action == 'newInsurance' || $ctrl.action == 'moveInsurance'\" style=\"margin-top:30px;\">\r\n  <div class=\"col-12 col-sm-6  mb-2 text-center\">\r\n    <button class=\"btn btn-lt btn-primary btn-sm\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n  </div>\r\n  <div class=\"col-sm-6 mb-2 text-center\">\r\n    <button class=\"btn btn-lt btn-primary btn-sm\" ng-click=\"$ctrl.setInsuranceAction('newInsuranceForEntrepreneur');  $ctrl.goNext()\" sxy-text=\"SALAXY.NG1.InsuranceComponent.thankYou.newInsuranceForEntrepreneur.text\"></button>\r\n  </div>\r\n</div>\r\n\r\n<div class=\"row\" ng-if=\"$ctrl.action == 'newInsuranceForEntrepreneur'\" style=\"margin-top:30px;\">\r\n  <div class=\"col-12 col-sm-6 mb-2 text-center\">\r\n    <button class=\"btn btn-lt btn-primary btn-sm\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n  </div>\r\n  <div class=\"col-sm-6 mb-2 text-center\">\r\n    <button class=\"btn btn-lt btn-primary btn-sm\" ng-click=\"$ctrl.setInsuranceAction('newInsurance'); $ctrl.goNext()\" sxy-text=\"SALAXY.NG1.InsuranceComponent.thankYou.notNewInsuranceForEntrepreneur.text\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/company/company-legal.html\",`﻿<form name=\"companyLegalForm\" class=\"form-horizontal\">\r\n  <!-- Updating formDataValidity to use in controller -->\r\n  <span class=\"d-none\">{{ wizard.formDataValidity = companyLegalForm.$valid && (wizard.showCompanySelection || wizard.model.signature.isProcura)}}</span>\r\n  <div class=\"row\">\r\n    <div class=\"col-md-6\">\r\n      <legend sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyLegal.legalLegend\"></legend>\r\n      <div class=\"mb-4\">\r\n        <p>\r\n          <span sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyLegal.pep\" ps=\"*\"></span>\r\n          <i class=\"bi bi-info-circle-fill\" type=\"button\" data-bs-toggle=\"popover\" data-bs-html=\"true\" data-bs-title=\"'SALAXY.NG1.CompanyOnboardingComponent.stepCompanyLegal.pepTitle' | sxyTranslate\" data-bs-content=\"'SALAXY.NG1.CompanyOnboardingComponent.stepCompanyLegal.pepPopOver' | sxyTranslate\" data-bs-container=\"body\"\r\n            data-bs-placement=\"top\" sxy-bs5-popover></i>\r\n        </p>\r\n        \r\n        <salaxy-input-boolean type=\"radio\" name=\"identityPep\" label=\"\" label-type=\"plain\" label-true=\"SALAXY.UI_Terms.yes\" label-false=\"SALAXY.UI_Terms.no\" ng-model=\"wizard.model.signature.isPep\" required></salaxy-input-boolean>\r\n      </div>\r\n      <div ng-if=\"wizard.model.company.companyType != 'fiRy'\" class=\"mb-4\">\r\n        <p>\r\n          <span sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyLegal.owner\" ps=\"*\"></span>\r\n          <i class=\"bi bi-info-circle-fill\" type=\"button\" data-bs-toggle=\"popover\" data-bs-html=\"true\" data-bs-title=\"'SALAXY.NG1.CompanyOnboardingComponent.stepCompanyLegal.ownerTitle' | sxyTranslate\" data-bs-content=\"'SALAXY.NG1.CompanyOnboardingComponent.stepCompanyLegal.ownerPopOver' | sxyTranslate\" data-bs-container=\"body\"\r\n            data-bs-placement=\"top\" sxy-bs5-popover></i>\r\n        </p>\r\n        <salaxy-input-boolean type=\"radio\" name=\"Ownership.IsRequiredTracking\" label=\"\" label-type=\"plain\" label-true=\"SALAXY.UI_Terms.yes\" label-false=\"SALAXY.UI_Terms.no\" ng-model=\"wizard.model.company.ownership.isRequiredTracking\" required></salaxy-input-boolean>\r\n\r\n      </div>\r\n      <div ng-if=\"!wizard.showCompanySelection\" class=\"mb-4\">\r\n        <p>\r\n          <span sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyLegal.procura\" ps=\"*\"></span>\r\n          <i class=\"bi bi-info-circle-fill\" type=\"button\" data-bs-toggle=\"popover\" data-bs-html=\"true\" data-bs-title=\"'SALAXY.NG1.CompanyOnboardingComponent.stepCompanyLegal.procuraTitle' | sxyTranslate\" data-bs-content=\"'SALAXY.NG1.CompanyOnboardingComponent.stepCompanyLegal.procuraPopOver' | sxyTranslate\" data-bs-container=\"body\"\r\n            data-bs-placement=\"top\" sxy-bs5-popover></i>\r\n           \r\n        </p>\r\n        <salaxy-input-boolean type=\"radio\" name=\"procuraOptions\" label=\"\" label-type=\"plain\" label-true=\"SALAXY.UI_Terms.yes\" label-false=\"SALAXY.UI_Terms.no\" ng-model=\"wizard.model.signature.isProcura\" required></salaxy-input-boolean>\r\n        <br />\r\n        <div ng-if=\"!wizard.model.signature.isProcura\" class=\"alert alert-danger\">\r\n          <p sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyLegal.procuraText\"></p>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"col-md-6\">\r\n      <div ng-if=\"!wizard.model.company.ownership.isRequiredTracking\">\r\n        <legend sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyLegal.fiva\"></legend>\r\n        <p sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyLegal.fivaText\"></p>\r\n      </div>\r\n      <div ng-if=\"wizard.model.company.ownership.isRequiredTracking\">\r\n        <fieldset class=\"form-horizontal\">\r\n          <legend sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyLegal.shareHolderTitle\"></legend>\r\n          <p sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyLegal.shareHolderText\" ps=\":\"></p>\r\n          <salaxy-input type=\"text\" name=\"shareholder1\" label=\"{{'SALAXY.NG1.CompanyOnboardingComponent.stepCompanyLegal.shareHolder' | sxyTranslate}} 1\" label-cols=\"col-sm-4 col-md-3 col-lg-4\" ng-model=\"wizard.model.company.ownership.shareHolders[0].name\" require=\"true\"></salaxy-input>\r\n          <salaxy-input type=\"text\" name=\"shareholder2\" label=\"{{'SALAXY.NG1.CompanyOnboardingComponent.stepCompanyLegal.shareHolder' | sxyTranslate}} 2\" label-cols=\"col-sm-4 col-md-3 col-lg-4\" ng-model=\"wizard.model.company.ownership.shareHolders[1].name\">\r\n          </salaxy-input>\r\n          <salaxy-input type=\"text\" name=\"shareholder3\" label=\"{{'SALAXY.NG1.CompanyOnboardingComponent.stepCompanyLegal.shareHolder' | sxyTranslate}} 3\" label-cols=\"col-sm-4 col-md-3 col-lg-4\" ng-model=\"wizard.model.company.ownership.shareHolders[2].name\">\r\n          </salaxy-input>\r\n          <salaxy-input type=\"text\" name=\"shareholder4\" label=\"{{'SALAXY.NG1.CompanyOnboardingComponent.stepCompanyLegal.shareHolder' | sxyTranslate}} 4\" label-cols=\"col-sm-4 col-md-3 col-lg-4\" ng-model=\"wizard.model.company.ownership.shareHolders[3].name\">\r\n          </salaxy-input>\r\n        </fieldset>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/company/company.html\",`﻿<form name=\"companyForm\" class=\"form-horizontal\">\r\n  <!-- Updating formDataValidity to use in controller -->\r\n  <span class=\"d-none\">{{ wizard.formDataValidity = companyForm.$valid && ( wizard.showCompanySelection || (wizard.model.company.resolvedId == (sessionCtrl.session.hasCurrentAccount ? sessionCtrl.session.currentAccount.id:null)))}}</span>\r\n  <div class=\"\">\r\n    <br />\r\n    <p>{{wizard.currentStep.intro | sxyTranslate}}</p>\r\n    <br />\r\n  </div>\r\n  <div>\r\n    <div class=\"alert alert-danger\" ng-if=\"wizard.showCompanySelection && wizard.existingCompanyAlert\">\r\n      <p sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.existingCompanyAlert\"></p>\r\n      <p>\r\n        <a ng-href=\"{{wizard.model.ui.successUrl}}\" sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.loginLink\"></a>\r\n      </p>\r\n    </div>\r\n  </div>\r\n  <div ng-if=\"!wizard.showCompanySelection && ( wizard.model.company.resolvedId != (sessionCtrl.session.hasCurrentAccount ? sessionCtrl.session.currentAccount.id:null))\">\r\n    <div class=\"alert alert-danger\">\r\n      <p sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.existingBusinessIdAlert\" params=\"{businessId: wizard.model.company.businessId}\"></p>\r\n      <p>\r\n        <a ng-href=\"{{wizard.model.ui.successUrl}}\" sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.loginLink2\"></a>\r\n      </p>\r\n      <p sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.existingBusinessIdAlert2\"></p>\r\n    </div>\r\n  </div>\r\n  <div class=\"row\">\r\n\r\n    <div ng-if=\"wizard.showCompanySelection\" class=\"col-md-6\">\r\n      <legend sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyInfo\"></legend>\r\n      <salaxy-input readonly=\"true\" label=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyBusinessId\" name=\"businessId\" ng-model=\"wizard.model.company.businessId\" tooltip-html=\"Tarvitset käyttäjätilin luomiseen Y-tunnuksen. Jos käytät palveluamme yhdistyksen palkanmaksuun, yhdistyksellä on oltava Y-tunnus. Yhdistys voi hakea Y-tunnuksen tekemällä perustamisilmoituksen Verohallintoon (lomakkeella Y1).\" ng-required=\"true\"></salaxy-input>\r\n      <salaxy-input salaxy-if-role=\"!test\" readonly=\"true\" label=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyName\" name=\"name\" ng-model=\"wizard.model.company.name\" ng-required=\"true\"></salaxy-input>\r\n      <salaxy-input salaxy-if-role=\"test\" label=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyName\" name=\"name\" ng-model=\"wizard.model.company.name\" ng-required=\"true\"></salaxy-input>\r\n      <div class=\"row mb-2\" salaxy-if-role=\"!test\">\r\n        <label for=\"Yritysmuoto\" class=\"col-sm-4 control-label\" style=\"text-align:left\">\r\n          <span sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyType\" ps=\"*\"></span>\r\n        </label>\r\n        <div class=\"col-sm-8\">\r\n          <input type=\"text\" class=\"form-control\" id=\"Yritysmuoto\" name=\"Yritysmuoto\" placeholder=\"{{'SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyType' | sxyTranslate | lowercase}}\" readonly=\"true\" autocomplete=\"off\" value=\"{{ !wizard.model.company.companyType ? '' : ('SALAXY.ENUM.CompanyType.' + wizard.model.company.companyType +'.label' | sxyTranslate) }}\"/>\r\n        </div>\r\n      </div>\r\n      <salaxy-input-enum salaxy-if-role=\"test\" label=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyType\" name=\"companyType\" ng-model=\"wizard.model.company.companyType\" enum=\"CompanyType\" type=\"select\" placeholder=\"SALAXY.UI_Terms.select\" ng-required=\"true\"></salaxy-input-enum>\r\n    </div>\r\n\r\n    <div ng-if=\"!wizard.showCompanySelection\" class=\"col-md-6\">\r\n      <legend sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyInfo\"></legend>\r\n      <div class=\"row mb-2\">\r\n        <label for=\"businessId\" class=\"col-sm-4 col-md-3 col-lg-4 control-label\" style=\"text-align: left\">\r\n         <span sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyBusinessId\" ps=\"*\"></span>\r\n          <i class=\"bi bi-info-circle-fill\" \r\n            type=\"button\" \r\n            data-bs-toggle=\"popover\" \r\n            data-bs-html=\"true\" \r\n            data-bs-title=\"'SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyBusinessId' | sxyTranslate\" \r\n            data-bs-content=\"'SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.businessIdPopOver' | sxyTranslate\" \r\n            data-bs-container=\"body\" \r\n            data-bs-placement=\"top\" sxy-bs5-popover>\r\n          </i>\r\n        </label>\r\n        <div class=\"col-sm-8 col-md-9 col-lg-8\">\r\n          <div class=\"input-group\">\r\n            <input ng-disabled=\"sessionCtrl.session.hasCurrentAccount\" type=\"text\" id=\"businessId\" class=\"form-control\" ng-model=\"wizard.model.company.businessId\" sxy-company-id-fi ng-required=\"true\">\r\n            <div class=\"input-group-btn\">\r\n              <button \r\n                ng-disabled=\"sessionCtrl.session.hasCurrentAccount\" \r\n                ng-click=\"wizard.searchYtj('businessId')\" \r\n                class=\"btn btn-default form-control\" \r\n                type=\"button\" \r\n                data-bs-toggle=\"popover\" \r\n                data-bs-html=\"true\" \r\n                data-bs-title=\"'SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.ytjSearchTitle' | sxyTranslate\" \r\n                data-bs-content=\"'SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.ytjPopOver' | sxyTranslate\" \r\n                data-bs-container=\"body\" \r\n                data-bs-placement=\"top\" \r\n                data-bs-trigger=\"hover\"\r\n                sxy-bs5-popover>\r\n                <span sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.ytjSearchBtn\"></span>\r\n                <span class=\"d-none d-md-inline\" sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.ytjSearchBtn2\"></span>\r\n              </button>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n\r\n      <div class=\"row mb-2\">\r\n        <label for=\"name\" class=\"col-sm-4 col-md-3 col-lg-4 control-label\" style=\"text-align: left\" sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyName\" ps=\"*\"></label>\r\n        <div class=\"col-sm-8 col-md-9 col-lg-8\">\r\n          <div class=\"input-group\">\r\n            <input ng-disabled=\"sessionCtrl.session.hasCurrentAccount\" type=\"text\" class=\"form-control\" id=\"name\" ng-model=\"wizard.model.company.name\" ng-required=\"true\">\r\n            <div class=\"input-group-btn\">\r\n              <button \r\n                ng-disabled=\"sessionCtrl.session.hasCurrentAccount\" \r\n                class=\"btn btn-default form-control\" \r\n                type=\"button\" \r\n                ng-click=\"wizard.searchYtj('name')\"\r\n                data-bs-toggle=\"popover\" \r\n                data-bs-html=\"true\" \r\n                data-bs-title=\"{{'SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.ytjSearchTitle' | sxyTranslate}}\"\r\n                data-bs-content=\"{{'SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.ytjPopOver' | sxyTranslate}}\" \r\n                data-bs-container=\"body\" \r\n                data-bs-placement=\"top\"  \r\n                data-bs-trigger=\"hover\"\r\n                sxy-bs5-popover>\r\n                <span sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.ytjSearchBtn\"></span>\r\n                <span class=\"d-none d-md-inline\" sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.ytjSearchBtn2\"></span>\r\n              </button>\r\n            </div>\r\n          </div>\r\n\r\n        </div>\r\n      </div>\r\n      <!-- HUOM! Tästä kentästä on mobiiliversio edempänä koodissa -->\r\n      <salaxy-input-enum class=\"d-none d-sm-block\" label=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyType2\" label-cols=\"col-sm-4 col-md-3 col-lg-4\" enum=\"CompanyType\" options=\"{'fiOy':('SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyTypeFiOy' | sxyTranslate),'fiTm':('SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyTypeFiTm' | sxyTranslate),'fiRy':('SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyTypeFiRy' | sxyTranslate),'fiYy':('SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyTypeFiYy' | sxyTranslate)}\" name=\"companyType\" ng-model=\"wizard.model.company.companyType\" disabled=\"sessionCtrl.session.hasCurrentAccount\" require=\"true\"></salaxy-input-enum>\r\n    </div>\r\n\r\n    <!-- MOBIILIVERSIO YTJ haun tulokset/virheet -->\r\n    <div ng-if=\"!wizard.showCompanySelection\" class=\"d-sm-none col-12\">\r\n      <!--Näytetään y-tunnuksesta johtuvat virheet, jos niitä on -->\r\n      <div ng-if=\"wizard.getValidationError('Company.BusinessId') && wizard.getValidationError('Company.BusinessId').type=='invalid'\">\r\n        <h3 sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.ytjSearchResultTitle\" ps=\":\"></h3>\r\n        <p>{{ wizard.getValidationError('Company.BusinessId').msg | sxyTranslate}}</p>\r\n      </div>\r\n\r\n      <div ng-if=\"wizard.model.company.ytjSearch != null\">\r\n        <h3>\r\n          <span sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.ytjSearchResultTitle\" ps=\":\"></span>\r\n          <span ng-if=\"wizard.model.company.ytjSearch && wizard.model.company.ytjSearch.result.length != 0\">\r\n            ({{wizard.model.company.ytjSearch.result.length}} kpl)\r\n          </span>\r\n        </h3>\r\n        <!--Näytetään ytj-hausta johtuvat virheet, jos niitä on -->\r\n        <div ng-if=\"wizard.model.company.ytjSearch.userMessage != null\">\r\n          <p>{{ wizard.model.company.ytjSearch.userMessage }}</p>\r\n        </div>\r\n        <div ng-if=\"wizard.model.company.ytjSearch.isSuccess\">\r\n          <!--Näytetään että tiedot syötetty jos yrityksiä oli tasan yksi -->\r\n          <div ng-if=\"wizard.model.company.ytjSearch.result.length == 1\">\r\n            <p sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.ytjSearchResultText\"></p>\r\n          </div>\r\n          <!--Näytetään viestit jos yrityksiä on nolla-->\r\n          <div ng-if=\"wizard.model.company.ytjSearch.result.length == 0 && wizard.model.validation.isOfficialIdValid\">\r\n            <p>{{wizard.model.company.ytjSearch.userMessage}}</p>\r\n          </div>\r\n          <div ng-if=\"wizard.model.company.ytjSearch.result.length != 0\">\r\n            <div class=\"accordion accordion-flush salaxy-accordion\" id=\"companies\">\r\n              <div ng-repeat=\"company in wizard.model.company.ytjSearch.result track by $index\" class=\"accordion-item\">\r\n                <h2 class=\"accordion-header\">\r\n                  <button class=\"accordion-button collapsed\" type=\"button\" data-bs-toggle=\"collapse\" data-bs-target=\"#company{{$index}}\">\r\n                    {{company.name}}\r\n                  </button>\r\n                </h2>\r\n                <div id=\"company{{$index}}\" class=\"accordion-collapse collapse\" aria-labelledby=\"headingOne\" data-bs-parent=\"#companies\">\r\n                  <div class=\"accordion-body\">\r\n                    <p>{{company.businessId}}<br /> {{company.type}} <br />\r\n                      <button class=\"btn btn-primary\" ng-click=\"wizard.chooseBusinessId(company.businessId)\" sxy-text=\"SALAXY.UI_Terms.select\"></button>\r\n                    </p>\r\n                  </div>\r\n                </div>\r\n              </div>\r\n            </div>\r\n            \r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n\r\n    <div class=\"col-md-6\">\r\n      <legend sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyContact\"></legend>\r\n      <salaxy-input label=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyStreet\" name=\"Katuosoite\" ng-model=\"wizard.model.company.contact.street\" ng-required=\"true\"></salaxy-input>\r\n      <salaxy-input label=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyPostalCode\" name=\"Postinumero\" sxy-postal-code-fi ng-model=\"wizard.model.company.contact.postalCode\" ng-required=\"true\"></salaxy-input>\r\n      <salaxy-input label=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyCity\" name=\"Postitoimipaikka\" ng-model=\"wizard.model.company.contact.city\" ng-required=\"true\"></salaxy-input>\r\n      <salaxy-input label=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyEmail\" name=\"Sahkoposti\" ng-model=\"wizard.model.company.contact.email\" ng-required=\"true\" sxy-email></salaxy-input>\r\n      <salaxy-input label=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyPhone\" name=\"Puhelinnumero\" ng-model=\"wizard.model.company.contact.telephone\" ng-required=\"true\" sxy-mobile-phone></salaxy-input>\r\n      <!-- HUOM! Tästä kentästä on mobiiliversio ylempänä koodissa -->\r\n      <div ng-if=\"!wizard.showCompanySelection\" class=\"d-block d-sm-none\">\r\n        <salaxy-input-enum label=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyType2\" label-cols=\"col-sm-4 col-md-3 col-lg-4\" enum=\"CompanyType\" options=\"{'fiOy':('SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyTypeFiOy' | sxyTranslate),'fiTm':('SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyTypeFiTm' | sxyTranslate),'fiRy':('SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyTypeFiRy' | sxyTranslate),'fiYy':('SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyTypeFiYy' | sxyTranslate)}\"\r\n          name=\"companyTypeMobile\" ng-model=\"wizard.model.company.companyType\" disabled=\"sessionCtrl.session.hasCurrentAccount\" require=\"true\"></salaxy-input-enum>\r\n      </div>\r\n    </div>\r\n\r\n    <!-- YTJ haun tulokset/virheet -->\r\n    <div ng-if=\"!wizard.showCompanySelection\" class=\"d-none d-sm-block col-12\">\r\n      <!-- Näytetään y-tunnuksesta johtuvat virheet, jos niitä on -->\r\n      <div ng-if=\"wizard.getValidationError('Company.BusinessId') && wizard.getValidationError('Company.BusinessId').type=='invalid'\">\r\n        <h3 sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.ytjSearchResultTitle\" ps=\":\"></h3>\r\n        <p>{{ wizard.getValidationError('Company.BusinessId').msg | sxyTranslate}}</p>\r\n      </div>\r\n\r\n      <div ng-if=\"wizard.model.company.ytjSearch != null\">\r\n        <h3>\r\n          <span sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.ytjSearchResultTitle\" ps=\":\"></span>\r\n          <span ng-if=\"wizard.model.company.ytjSearch && wizard.model.company.ytjSearch.result.length != 0\">\r\n            ({{wizard.model.company.ytjSearch.result.length}} kpl)\r\n          </span>\r\n        </h3>\r\n        <!--Näytetään ytj-hausta johtuvat virheet, jos niitä on -->\r\n        <div ng-if=\"wizard.model.company.ytjSearch.userMessage != null\">\r\n          <p>{{ wizard.model.company.ytjSearch.userMessage }}</p>\r\n        </div>\r\n\r\n\r\n        <!-- Haku onnistui -->\r\n        <div ng-if=\"wizard.model.company.ytjSearch.isSuccess\">\r\n          <!--Näytetään viestit jos yrityksiä on nolla-->\r\n          <div ng-if=\"wizard.model.company.ytjSearch.result.length == 0 && wizard.model.validation.isOfficialIdValid\">\r\n            <p>{{wizard.model.company.ytjSearch.userMessage}}</p>\r\n          </div>\r\n          <div ng-if=\"wizard.model.company.ytjSearch.result.length != 0\" class=\"table-responsive\" style=\"max-height: 300px; overflow-y: auto;\">\r\n\r\n            <table class=\"table table-hover table-bordered\" style=\"overflow-wrap: break-word\">\r\n              <thead>\r\n                <tr>\r\n                  <th>\r\n                    <span sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyName2\"></span>\r\n                    <br />\r\n                    <span sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyBusinessId\"></span>\r\n                  </th>\r\n                  <th class=\"d-none d-sm-table-cell\" sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepCompanyInfo.companyType\"></th>\r\n                  <th></th>\r\n                </tr>\r\n              </thead>\r\n              <tbody>\r\n                <tr ng-repeat=\"company in wizard.model.company.ytjSearch.result\">\r\n                  <td>\r\n                    {{company.name}}\r\n                    <br /> {{company.businessId}}\r\n                  </td>\r\n                  <td class=\"d-none d-sm-table-cell\">{{company.type}}</td>\r\n                  <td>\r\n                    <a class=\"btn btn-primary\" ng-click=\"wizard.chooseBusinessId(company.businessId)\" sxy-text=\"SALAXY.UI_Terms.select\"></a>\r\n                  </td>\r\n                </tr>\r\n              </tbody>\r\n            </table>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/company/contract.html\",`﻿<form name=\"contractForm\">\r\n  <span class=\"d-none\">{{ wizard.formDataValidity = contractForm.$valid}}</span>\r\n  \r\n  <p sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepContract.intro\"></p>\r\n\r\n  <p sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepContract.info\"></p>\r\n\r\n  <div class=\"row\" ng-controller=\"SignatureController as sign\">\r\n    <div class=\"col-md-6\">\r\n      <fieldset ng-if=\"!wizard.showCompanySelection\">\r\n        <legend sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepContract.yourPersonalId\"></legend>\r\n        <div>\r\n          <salaxy-input name=\"personalId\" label-type=\"plain\" type=\"text\" style=\"width:150px\" placeholder=\"SALAXY.NG1.CompanyOnboardingComponent.stepContract.personalIdExample\" ng-model=\"wizard.model.signature.personalId\" require=\"true\" sxy-personal-id-fi></salaxy-input>\r\n        </div>\r\n      </fieldset>\r\n\r\n      <div class=\"mb-2\">\r\n        <input ng-init=\"wizard.model.signature.terms = false\" name=\"terms\" type=\"checkbox\" require=\"true\" ng-model=\"wizard.model.signature.terms\"></input>\r\n        <span sxy-html=\"SALAXY.NG1.CompanyOnboardingComponent.stepContract.termsText.html\"></span>\r\n        <a ng-href=\"{{ wizard.getPdfPreviewAddress() }}\" target=\"_blank\" sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepContract.termsText2\"></a> <span sxy-html=\"SALAXY.NG1.CompanyOnboardingComponent.stepContract.termsText3.html\"></span>\r\n      </div>\r\n\r\n      <fieldset>\r\n        <div ng-if=\"wizard.model.accountType == 'company'\">\r\n          <p sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepContract.usePersonalBank\"></p>\r\n        </div>\r\n\r\n        <p sxy-html=\"SALAXY.NG1.CompanyOnboardingComponent.stepContract.privacyPolicy.html\"></p>\r\n        \r\n        <div sxy-if-role=\"test\">\r\n          <h3>TEST: Huomaa HETU:sta!</h3>\r\n          <p class=\"text-warning\">\r\n            Allekirjoitus ohjaa nyt testiympäristöön, jossa\r\n            <strong>HETU tarkistetaan</strong>.\r\n            Katso testiympäristön\r\n            <a href=\"https://gist.github.com/ykarikos/e43e567eb7b9e05432d4bd9d0b51ef35\" target=\"_blank\">HETU:t täältä</a>\r\n            (valitse validi hetu).\r\n          </p>\r\n        </div>\r\n      </fieldset>\r\n    </div>\r\n\r\n    <div class=\"col-md-6 d-none d-sm-block\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepContract.pdfPreviewTitle\"></legend>\r\n        <small><a ng-href=\"{{ wizard.getPdfPreviewAddress() }}\" target=\"_blank\" sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepContract.downloadHereLink\"></a></small>\r\n\r\n        <iframe ng-src=\"{{ wizard.getPdfPreviewAddress() }}\" style=\"width: 100%; height: 300px\"></iframe>\r\n      </fieldset>\r\n    </div>\r\n    <div class=\"col-md-6 d-block d-sm-none\">\r\n      <a ng-href=\"{{ wizard.getPdfPreviewAddress() }}\" target=\"_blank\" sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepContract.pdfPreviewLink\"></a>\r\n    </div>\r\n\r\n  </div>\r\n\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/company/contractButtons.html\",`﻿<button ng-click=\"wizard.goPrevious()\" ng-disabled=\"!wizard.canGoPrevious\" class=\"btn btn-default\" sxy-text=\"SALAXY.UI_Terms.previous\"></button>\r\n<div salaxy-loader class=\"spinner\">\r\n  <div class=\"bounce1\"></div>\r\n  <div class=\"bounce2\"></div>\r\n  <div class=\"bounce3\"></div>\r\n</div>\r\n\r\n<button ng-if=\"wizard.model.signature.personalId == null || wizard.model.signature.terms == false\" ng-disabled=\"true\" class=\"btn btn-primary\" sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepContract.signBtn\"></button>\r\n<a ng-if=\"!(wizard.model.signature.personalId == null || wizard.model.signature.terms == false)\" ng-href=\"{{wizard.vismaSignUrl}}\" target=\"_top\" class=\"btn btn-primary\" sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepContract.signBtn\"></a>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/company/defaultWizardButtons.html\",`﻿<button ng-click=\"wizard.goPrevious()\" ng-disabled=\"!wizard.canGoPrevious\" class=\"btn btn-default\" sxy-text=\"SALAXY.UI_Terms.previous\"></button>\r\n<div salaxy-loader class=\"spinner\">\r\n  <div class=\"bounce1\"></div>\r\n  <div class=\"bounce2\"></div>\r\n  <div class=\"bounce3\"></div>\r\n</div>\r\n<button ng-click=\"wizard.goNext()\" ng-disabled=\"!wizard.canGoNext\" class=\"btn btn-primary\" sxy-text=\"SALAXY.UI_Terms.next\"></button>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/company/firstPageButtons.html\",`﻿<!--a ng-if=\"wizard.model.ui.cancelUrl\" ng-href=\"{{wizard.model.ui.cancelUrl}}\"  class=\"btn btn-default\">Takaisin etusivulle</a-->\r\n<button class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.backToFront\"></button>\r\n<div salaxy-loader class=\"spinner\">\r\n  <div class=\"bounce1\"></div>\r\n  <div class=\"bounce2\"></div>\r\n  <div class=\"bounce3\"></div>\r\n</div>\r\n<button ng-click=\"wizard.goNext()\" ng-disabled=\"!wizard.canGoNext\" class=\"btn btn-primary\" sxy-text=\"SALAXY.UI_Terms.next\"></button>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/company/index.html\",`<div ng-controller=\"SessionController as sessionCtrl\" class=\"company-onboarding\">\r\n  <div ng-controller=\"CompanyOnboardingController as wizard\">\r\n    <div ng-controller=\"NaviController as $naviCtrl\">\r\n      <div ng-if=\"!$naviCtrl.showFullPageLoader\">\r\n        <div class=\"modal-header bg-primary\">\r\n          <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.modalTitle\"></h2>\r\n          <button type=\"button\" class=\"btn-close btn-close-white\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n        </div>\r\n        <div class=\"modal-body\">\r\n          <div class=\"d-block d-md-none\">\r\n            <h4><span sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.step\"></span> {{ wizard.currentStep.number }}/{{ wizard.steps.length }}</h4>\r\n          </div>\r\n          <div class=\"salaxy-wizard\">\r\n            <div class=\"wizard-steps\">\r\n              <div class=\"wizard-step\" ng-repeat=\"step in wizard.steps\" ng-class=\"{'active': step.active, 'disabled': step.disabled}\">\r\n                <span class=\"salaxy-avatar\">\r\n                  <div class=\"wizard-icons-wrapper\">\r\n                    <i class=\"bi\" ng-class=\"step.active ? 'bi-circle-fill' : 'bi-circle'\"></i>\r\n                    <i class=\"bi bi-circle-fill\"></i>\r\n                  </div>\r\n                  <strong class=\"number\">{{ step.number }}</strong>\r\n                </span>\r\n                <span class=\"step-text\">{{ step.title | sxyTranslate }}</span>\r\n              </div>\r\n            </div>\r\n            <div class=\"wizard-strikethrough\"></div>\r\n          </div>\r\n          <ng-include src=\"wizard.currentStep.view\"></ng-include>\r\n        </div>\r\n        <div class=\"modal-footer\">\r\n          <ng-include class=\"d-flex justify-content-between w-100\" src=\"wizard.currentStep.buttonsView\"></ng-include>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/company/suomifi.html\",`<form name=\"currentForm\">\r\n  <!-- Hidden ariable formDataValidity to use in controller -->\r\n  <span class=\"d-none\">{{ wizard.formDataValidity = currentForm.$valid }}</span>\r\n  <div class=\"\">\r\n    <br />\r\n    <p>{{wizard.currentStep.intro | sxyTranslate}}</p>\r\n    <br />\r\n  </div>\r\n  <div class=\"row\">\r\n    <div class=\"col-md-6\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepSuomiFi.infoText\"></legend>\r\n        <div class=\"form-horizontal\">\r\n          <salaxy-input label=\"SALAXY.NG1.CompanyOnboardingComponent.stepSuomiFi.personalId\" name=\"personalId\" ng-model=\"wizard.model.signature.personalId\" ng-required=\"true\" sxy-personal-id-fi></salaxy-input>\r\n        </div>\r\n      </fieldset>\r\n    </div>\r\n  </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/company/suomifiButtons.html\",`﻿<button ng-click=\"wizard.goPrevious()\" ng-disabled=\"!wizard.canGoPrevious\" class=\"btn btn-default\" sxy-text=\"SALAXY.UI_Terms.previous\"></button>\r\n<div salaxy-loader class=\"spinner\">\r\n  <div class=\"bounce1\"></div>\r\n  <div class=\"bounce2\"></div>\r\n  <div class=\"bounce3\"></div>\r\n</div>\r\n<button ng-click=\"wizard.goToSuomifi()\" ng-disabled=\"!wizard.canGoNext\" class=\"btn btn-primary\" sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.stepSuomiFi.goToSuomiFiBtn\"></button>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/company/wizard_index.html\",`﻿<form name=\"currentForm\" class=\"form-horizontal\">\r\n  <!-- Hidden ariable formDataValidity to use in controller -->\r\n  <span class=\"d-none\">{{ wizard.formDataValidity = currentForm.$valid }}</span>\r\n  <div class=\"\">\r\n    <br />\r\n    <p>{{wizard.currentStep.intro | sxyTranslate}}</p>\r\n    <br />\r\n  </div>\r\n  <div class=\"row\">\r\n    <div class=\"col-md-6\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.step1.personInfo\"></legend>\r\n        <salaxy-input label=\"SALAXY.NG1.CompanyOnboardingComponent.step1.personFirstName\" name=\"Etunimi\" ng-model=\"wizard.model.person.firstName\" ng-required=\"true\"></salaxy-input>\r\n        <salaxy-input label=\"SALAXY.NG1.CompanyOnboardingComponent.step1.personLastName\" name=\"Sukunimi\" ng-model=\"wizard.model.person.lastName\" ng-required=\"true\"></salaxy-input>\r\n      </fieldset>\r\n    </div>\r\n    <div class=\"col-md-6\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.CompanyOnboardingComponent.step1.personContact\"></legend>\r\n        <salaxy-input label=\"SALAXY.NG1.CompanyOnboardingComponent.step1.personEmail\" name=\"Sahkoposti\" ng-model=\"wizard.model.person.contact.email\" ng-required=\"true\" sxy-email></salaxy-input>\r\n        <salaxy-input label=\"SALAXY.NG1.CompanyOnboardingComponent.step1.personPhone\" name=\"Puhelinnumero\" ng-model=\"wizard.model.person.contact.telephone\" ng-required=\"true\" sxy-mobile-phone></salaxy-input>\r\n      </fieldset>\r\n    </div>\r\n  </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/customer/buttons.html\",`﻿<button ng-click=\"wizard.goPrevious()\" ng-disabled=\"!wizard.canGoPrevious\" class=\"btn btn-default\" sxy-text=\"SALAXY.UI_Terms.previous\"></button>\r\n<div salaxy-loader class=\"spinner\">\r\n  <div class=\"bounce1\"></div>\r\n  <div class=\"bounce2\"></div>\r\n  <div class=\"bounce3\"></div>\r\n</div>\r\n<button ng-click=\"wizard.goNext()\" ng-disabled=\"!wizard.canGoNext\" class=\"btn btn-primary\" sxy-text=\"SALAXY.UI_Terms.next\"></button>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/customer/commit-buttons.html\",`<button ng-click=\"wizard.goPrevious()\" ng-disabled=\"!wizard.canGoPrevious\" class=\"btn btn-danger\" sxy-text=\"SALAXY.UI_Terms.previous\"></button>\r\n<div salaxy-loader class=\"spinner\">\r\n  <div class=\"bounce1\"></div>\r\n  <div class=\"bounce2\"></div>\r\n  <div class=\"bounce3\"></div>\r\n</div>\r\n<button ng-click=\"wizard.commit()\" ng-disabled=\"!wizard.canGoNext\" class=\"btn btn-primary\" sxy-text=\"SALAXY.UI_Terms.next\"></button>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/customer/company-legal.html\",`<form name=\"currentForm\" class=\"form-horizontal\">\r\n  <span class=\"d-none\">{{ wizard.formDataValidity = currentForm.$valid }}</span>\r\n  <div class=\"row\">\r\n    <div class=\"col-12 col-md-6\">\r\n      <legend sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyLegal.legalTitle\"></legend>\r\n      <div class=\"mb-4\">\r\n        <p>\r\n          <span sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyLegal.pep\" ps=\"*\"></span>\r\n          <i class=\"bi bi-info-circle-fill\"\r\n            type=\"button\" \r\n            data-bs-toggle=\"popover\" \r\n            data-bs-html=\"true\"\r\n            data-bs-title=\"'SALAXY.NG1.CustomerOnboardingComponent.stepCompanyLegal.pepTitle' | sxyTranslate\" \r\n            data-bs-content=\"'SALAXY.NG1.CustomerOnboardingComponent.stepCompanyLegal.pepPopOver' | sxyTranslate\" \r\n            data-bs-container=\"body\" \r\n            data-bs-placement=\"top\" sxy-bs5-popover>\r\n          </i>\r\n        </p>\r\n        <!-- TODO: test-->\r\n        <salaxy-input-boolean type=\"radio\" name=\"identityPep\" label=\"\" label-type=\"plain\" label-true=\"SALAXY.UI_Terms.yes\" label-false=\"SALAXY.UI_Terms.no\" ng-model=\"wizard.model.signature.isPep\" require=\"true\"></salaxy-input-boolean>\r\n      </div>\r\n    \r\n      <div cng-hide=\"!(wizard.model.company.companyType == 'fiOy' || wizard.model.company.companyType == 'fiYy')\" class=\"mb-4\">\r\n        <p>\r\n          <span sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyLegal.owner\" ps=\"*\"></span>\r\n          <i class=\"bi bi-info-circle-fill\"\r\n            type=\"button\" \r\n            data-bs-toggle=\"popover\" \r\n            data-bs-html=\"true\"\r\n            data-bs-title=\"'SALAXY.NG1.CustomerOnboardingComponent.stepCompanyLegal.ownerTitle' | sxyTranslate\" \r\n            data-bs-content=\"'SALAXY.NG1.CustomerOnboardingComponent.stepCompanyLegal.ownerPopOver' | sxyTranslate\" \r\n            data-bs-container=\"body\" \r\n            data-bs-placement=\"top\" sxy-bs5-popover>\r\n          </i>\r\n        </p>\r\n        <div class=\"radio\">\r\n          <label class=\"radio-inline\" for=\"IsRequiredTracking-true\">\r\n            <input type=\"radio\" id=\"IsRequiredTracking-true\" name=\"Ownership.IsRequiredTracking\" ng-value=\"true\" ng-model=\"wizard.model.company.ownership.isRequiredTracking\" required> <span sxy-text=\"SALAXY.UI_Terms.yes\"></span>\r\n          </label>\r\n          <label class=\"radio-inline\" for=\"IsRequiredTracking-false\">\r\n            <input type=\"radio\" id=\"IsRequiredTracking-false\" name=\"Ownership.IsRequiredTracking\" ng-value=\"false\" ng-model=\"wizard.model.company.ownership.isRequiredTracking\" required><span sxy-text=\"SALAXY.UI_Terms.no\"></span>\r\n          </label>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"col-12 col-md-6\">\r\n      <div ng-hide=\"wizard.model.company.ownership.isRequiredTracking\">\r\n        <legend sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyLegal.fiva\"></legend>\r\n        <p sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyLegal.fivaText\"></p>\r\n      </div>\r\n      <div ng-hide=\"!wizard.model.company.ownership.isRequiredTracking\">\r\n        <fieldset class=\"form-horizontal\">\r\n          <legend sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyLegal.shareHolderTitle\"></legend>\r\n          <p sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyLegal.shareHolderText\"></p>\r\n          <div class=\"row mb-2\">\r\n            <label class=\"col-sm-4 col-md-3 col-lg-4 col-form-label\" for=\"shareholder1\" sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyLegal.shareHolder\" ps=\" 1*\"></label>\r\n            <div class=\"col-sm-8 col-md-9 col-lg-8\">\r\n              <input class=\"form-control\" id=\"shareholder1\" name=\"shareholder1\" type=\"text\" ng-model=\"wizard.model.company.ownership.shareHolders[0].name\" value=\"\" ng-required=\"wizard.model.company.ownership.isRequiredTracking == true\">\r\n            </div>\r\n          </div>\r\n          <div class=\"row mb-2\">\r\n            <label class=\"col-sm-4 col-md-3 col-lg-4 col-form-label\" for=\"shareholder2\" sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyLegal.shareHolder\" ps=\" 2 \"></label>\r\n            <div class=\"col-sm-8 col-md-9 col-lg-8\">\r\n              <input class=\"form-control\" id=\"shareholder2\" name=\"shareholder2\" type=\"text\" ng-model=\"wizard.model.company.ownership.shareHolders[1].name\" value=\"\">\r\n            </div>\r\n          </div>\r\n          <div class=\"row mb-2\">\r\n            <label class=\"col-sm-4 col-md-3 col-lg-4 col-form-label\" for=\"shareholder3\" sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyLegal.shareHolder\" ps=\" 3 \"></label>\r\n            <div class=\"col-sm-8 col-md-9 col-lg-8\">\r\n              <input class=\"form-control\" id=\"shareholder3\" name=\"shareholder3\" type=\"text\" ng-model=\"wizard.model.company.ownership.shareHolders[2].name\" value=\"\">\r\n            </div>\r\n          </div>\r\n          <div class=\"row mb-2\">\r\n            <label class=\"col-sm-4 col-md-3 col-lg-4 col-form-label\" for=\"shareholder4\" sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyLegal.shareHolder\" ps=\" 4 \"></label>\r\n            <div class=\"col-sm-8 col-md-9 col-lg-8\">\r\n              <input class=\"form-control\" id=\"shareholder4\" name=\"shareholder4\" type=\"text\" ng-model=\"wizard.model.company.ownership.shareHolders[3].name\" value=\"\">\r\n            </div>\r\n          </div>\r\n        </fieldset>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  \r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/customer/company.html\",`<form name=\"currentForm\">\r\n  <span class=\"d-none\">{{ wizard.formDataValidity = currentForm.$valid }}</span>\r\n  <div>\r\n    <div class=\"alert alert-danger\" ng-if=\"wizard.existingCompanyAlert\">\r\n      <p sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyInfo.existingCompanyAlert\"></p>\r\n    </div>\r\n  </div>\r\n  <div class=\"row\">\r\n    <div class=\"col-12 col-md-6\">\r\n      <legend sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyInfo.companyInfo\"></legend>\r\n      <div class=\"form-horizontal\">\r\n        <salaxy-input salaxy-if-role=\"!test\" readonly=\"true\" label=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyInfo.companyBusinessId\" name=\"Ytunnus\" ng-required=\"true\" ng-model=\"wizard.model.company.businessId\"></salaxy-input>\r\n        <salaxy-input salaxy-if-role=\"test\" label=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyInfo.companyBusinessId\" name=\"Ytunnus\" ng-required=\"true\" ng-model=\"wizard.model.company.businessId\"></salaxy-input>\r\n        <salaxy-input salaxy-if-role=\"!test\" readonly=\"true\" label=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyInfo.companyName\" name=\"Nimi\" ng-required=\"true\" ng-model=\"wizard.model.company.name\"></salaxy-input>\r\n        <salaxy-input salaxy-if-role=\"test\" label=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyInfo.companyName\" name=\"Nimi\" ng-required=\"true\" ng-model=\"wizard.model.company.name\"></salaxy-input>\r\n        <div class=\"row\" salaxy-if-role=\"!test\">\r\n          <label for=\"Yritysmuoto\" class=\"col-12 col-sm-4 col-form-label\">\r\n            <span sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyInfo.companyType\" ps=\"*\"></span>\r\n          </label>\r\n          <div class=\"col-12 col-sm-8\">\r\n            <input type=\"text\" class=\"form-control\" id=\"Yritysmuoto\" name=\"Yritysmuoto\" placeholder=\"{{'SALAXY.NG1.CustomerOnboardingComponent.stepCompanyInfo.companyType' | sxyTranslate | lowercase}}\" readonly=\"true\" autocomplete=\"off\" value=\"{{ !wizard.model.company.companyType ? '' : ('SALAXY.ENUM.CompanyType.' + wizard.model.company.companyType +'.label' | sxyTranslate) }}\"\r\n            />\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <salaxy-input-enum sxy-if-role=\"test\" label=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyInfo.companyType\" name=\"companyType\" ng-model=\"wizard.model.company.companyType\" enum=\"CompanyType\" type=\"select\" placeholder=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyInfo.companyType\"\r\n        required></salaxy-input-enum>\r\n    </div>\r\n    <div class=\"col-12 col-md-6\">\r\n      <legend sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyInfo.companyContact\"></legend>\r\n      <div class=\"form-horizontal\">\r\n        <salaxy-input label=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyInfo.companyStreet\" name=\"Katuosoite\" ng-model=\"wizard.model.company.contact.street\" ng-required=\"true\"></salaxy-input>\r\n        <salaxy-input label=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyInfo.companyPostalCode\" name=\"Postinumero\" sxy-postal-code-fi ng-model=\"wizard.model.company.contact.postalCode\" ng-required=\"true\"></salaxy-input>\r\n        <salaxy-input label=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyInfo.companyCity\" name=\"Postitoimipaikka\" ng-model=\"wizard.model.company.contact.city\" ng-required=\"true\"></salaxy-input>\r\n        <salaxy-input label=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyInfo.companyEmail\" name=\"Sahkoposti\" ng-model=\"wizard.model.company.contact.email\" ng-required=\"true\" sxy-email></salaxy-input>\r\n        <salaxy-input label=\"SALAXY.NG1.CustomerOnboardingComponent.stepCompanyInfo.companyPhone\" name=\"Puhelinnumero\" ng-model=\"wizard.model.company.contact.telephone\" ng-required=\"true\" sxy-mobile-phone></salaxy-input>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/customer/finish-buttons.html\",`<div class=\"btn-group\" role=\"group\">\r\n  <button ng-click=\"wizard.goPrevious()\" ng-disabled=\"!wizard.canGoPrevious\" class=\"btn btn-danger\" sxy-text=\"SALAXY.UI_Terms.previous\"></button>\r\n</div>\r\n<div salaxy-loader class=\"spinner\">\r\n  <div class=\"bounce1\"></div>\r\n  <div class=\"bounce2\"></div>\r\n  <div class=\"bounce3\"></div>\r\n</div>\r\n<div class=\"btn-group\">\r\n  <button class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n  <button class=\"btn btn-success\" ng-click=\"$close('ok');wizard.launch()\" sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.newAccountBtn\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/customer/finish.html\",`﻿<form name=\"currentForm\">\r\n  <span class=\"d-none\">{{ wizard.formDataValidity = currentForm.$valid }}</span>\r\n  <div class=\"row\">\r\n    <div class=\"col-md-12\" sxy-html=\"SALAXY.NG1.CustomerOnboardingComponent.stepInviteCompany.html\" params=\"{sharingLink :wizard.sharingLink, mailToLink : wizard.mailtoLink}\"></div>\r\n  </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/customer/index.html\",`<div ng-controller=\"SessionController as sessionCtrl\">\r\n  <div ng-controller=\"CustomerOnboardingController as wizard\">\r\n    <div ng-controller=\"NaviController as $naviCtrl\">\r\n      <div ng-if=\"!$naviCtrl.showFullPageLoader\">\r\n        <div class=\"modal-header bg-primary\">\r\n          <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.modalTitle\"></h2>\r\n          <button type=\"button\" class=\"btn-close btn-close-white\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n        </div>\r\n        <div class=\"modal-body\">       \r\n          <div class=\"d-block d-md-none\">\r\n            <h4><span sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.step\"></span> {{wizard.currentStep.number}}/{{wizard.steps.length}}</h4>\r\n          </div>\r\n          <div class=\"salaxy-wizard\">\r\n            <div class=\"wizard-steps\">\r\n              <div class=\"wizard-step\" ng-repeat=\"step in $ctrl.steps\" ng-class=\"{'active': step.active, 'disabled': step.disabled}\">\r\n                <span class=\"salaxy-avatar\">\r\n                  <div class=\"wizard-icons-wrapper\">\r\n                    <i class=\"bi\" ng-class=\"step.active ? 'bi-circle-fill' : 'bi-circle'\"></i>\r\n                    <i class=\"bi bi-circle-fill\"></i>\r\n                  </div>\r\n                  <strong class=\"number\">{{ step.number }}</strong>\r\n                </span>\r\n                <span class=\"step-text\">{{ step.title | sxyTranslate }}</span>\r\n              </div>\r\n            </div>\r\n            <div class=\"wizard-strikethrough\"></div>\r\n          </div>\r\n          <ng-include src=\"wizard.currentStep.view\"></ng-include>\r\n        </div>\r\n        <div class=\"modal-footer\">\r\n          <ng-include class=\"d-flex justify-content-between w-100\" src=\"wizard.currentStep.buttonsView\"></ng-include>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/customer/insurance.html\",`<form name=\"currentForm\">\r\n\r\n  <span class=\"d-none\">{{ wizard.formDataValidity = currentForm.$valid}}</span>\r\n\r\n  <div class=\"row\">\r\n    <div class=\"col-md-6\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.pensionTitle\"></legend>\r\n        <div class=\"form-horizontal\">\r\n          <salaxy-input-boolean label=\"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.pensionText\" type=\"radio\" name=\"isPensionContractDone\" ng-model=\"wizard.model.products.pension.isPensionContractDone\" label-type=\"basic\" label-true=\"SALAXY.UI_Terms.yes\"\r\n            label-false=\"SALAXY.UI_Terms.no\" ng-change=\"wizard.checkPensionCompanySelection()\"></salaxy-input-boolean>\r\n        </div>\r\n        <div ng-if=\"!wizard.model.products.pension.isPensionContractDone\">\r\n          <p sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.hasPension\"></p>\r\n        </div>\r\n        <div ng-if=\"wizard.model.products.pension.isPensionContractDone\" class=\"form-horizontal\">\r\n          <salaxy-input-enum label=\"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.pensionCompany\" name=\"pensionCompany\" enum=\"PensionCompany\" filter=\"varma,elo,ilmarinen,veritas,apteekkien,verso,valio,kevaMunicipal,kevaAland,kevaChurch,kevaKela,kevaState\" ng-model=\"wizard.model.products.pension.pensionCompany\"\r\n            ng-change=\"wizard.checkPensionCompanySelection(); wizard.model.products.pension.pensionContractNumber = null;\" require=\"true\"></salaxy-input-enum>\r\n\r\n          <main salaxy-if-role=\"test\" class=\"test-number\">\r\n            <div class=\"row\" ng-if=\"wizard.model.products.pension.pensionCompany != 'null' && wizard.model.products.pension.pensionCompany != 'none'\">\r\n              <div class=\"col-sm-8 offset-sm-4 mb-2 text-end text-sm-start\">\r\n                <span><span sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.testOnly\"></span> <button class=\"btn btn-secondary  btn-xs\" ng-click=\"wizard.setPensionNumberForTest()\" sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.testGenerateNumberBtn\"></button></span>\r\n              </div>\r\n            </div>\r\n          </main>\r\n          <div ng-if=\"wizard.model.products.pension.pensionCompany != 'other'\">\r\n            <salaxy-input label=\"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.pensionContractNumber\" require=\"true\" type=\"text\" name=\"pensionContractNumber\" id=\"pensionContractNumber\" ng-model=\"wizard.model.products.pension.pensionContractNumber\" tooltip-html=\"{{'SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.pensionContractNumberToolTip.html' | sxyTranslate}}\"\r\n              tooltip-placement=\"right\" sxy-pension-contract-number=\"wizard.model.products.pension.pensionCompany\"></salaxy-input>\r\n\r\n            <div class=\"row\" ng-show=\"currentForm.pensionContractNumber.$error.sxyTemporaryPensionContractNumber\">\r\n              <div class=\"col-12 input-info text-danger\">\r\n                <div class=\"input-info-icon\"><i class=\"bi bi-exclamation-triangle-fill\"></i></div>\r\n                <p class=\"small input-info-text with-icon\" sxy-html=\"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.pensionContractNumberTemporaryToolTip.html\"></p>\r\n              </div>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </fieldset>\r\n    </div>\r\n    <div class=\"col-sm-6 col-12\" ng-if=\"wizard.model.products.pension.isPensionContractDone\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.pensionHandling\"></legend>\r\n        <div class=\"input-wrapper\">\r\n          <div class=\"form-group\">\r\n            <div>\r\n              <p sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.pensionSelfHandleDescription\"></p>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </fieldset>\r\n    </div>\r\n  </div>\r\n  <div class=\"row\">\r\n    <div class=\"col-md-6\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.insuranceTitle\"></legend>\r\n        <div class=\"form-horizontal\">\r\n          <salaxy-input-boolean type=\"radio\" label=\"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.insuranceText\" label-type=\"basic\" label-true=\"SALAXY.UI_Terms.yes\" label-false=\"SALAXY.UI_Terms.no\" ng-model=\"wizard.model.products.insurance.isInsuranceContractDone\"\r\n            name=\"isInsuranceContractDone\" ng-change=\"wizard.checkInsuranceCompanySelection()\"></salaxy-input-boolean>\r\n        </div>\r\n        <div ng-if=\"wizard.model.products.insurance.isInsuranceContractDone\" class=\"form-horizontal\">\r\n          <salaxy-input-enum enum=\"InsuranceCompany\" filter=\"if,fennia,lähiTapiola,pohjantähti,pohjola,turva,aVakuutus,folksam,alandia,ålands\" name=\"InsuranceCompany\" label=\"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.insuranceCompany\" ng-model=\"wizard.model.products.insurance.insuranceCompany\"\r\n            require=\"true\"></salaxy-input-enum>\r\n          <salaxy-input label=\"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.insuranceContractNumber\" require=\"true\" name=\"insuranceContractNumber\" ng-model=\"wizard.model.products.insurance.insuranceContractNumber\"></salaxy-input>\r\n        </div>\r\n        <div ng-if=\"!wizard.model.products.insurance.isInsuranceContractDone && !wizard.model.products.insurance.isPartnerInsurance\">\r\n          <p sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.noInsuranceAlert\"></p>\r\n        </div>\r\n      </fieldset>\r\n    </div>\r\n    <div class=\"col-md-6\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.taxTitle\"></legend>\r\n\r\n        <p sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.taxText\"></p>\r\n        <div class=\"form-horizontal\">\r\n          <salaxy-input-enum ng-model=\"wizard.model.products.tax.irReporting\" name=\"irReporting\" label=\"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.irReporting\" options=\"{ default: ('SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.irReportingDefault' | sxyTranslate), noMonthlyReport: ('SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.irReportingNoMonthlyReport' | sxyTranslate), always: ('SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.irReportingAlways' | sxyTranslate)}\"></salaxy-input-enum>\r\n        </div>\r\n      </fieldset>\r\n    </div>\r\n  </div>\r\n  <div class=\"row\">\r\n    <div class=\"col-md-6\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.employmentTitle\"></legend>\r\n        <p sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.employmentText\"></p>\r\n      </fieldset>\r\n    </div>\r\n    <div class=\"col-md-6\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.reportTitle\"></legend>\r\n        <p sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.reportText\"></p>\r\n        <div class=\"form-horizontal\">\r\n          <salaxy-input label=\"SALAXY.NG1.CustomerOnboardingComponent.stepInsurance.accountantEmail\" name=\"Sahkopostiosoite\" ng-model=\"wizard.model.products.accounting.accountantEmail\" sxy-email></salaxy-input>\r\n        </div>\r\n      </fieldset>\r\n    </div>\r\n  </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/customer/invitation.html\",`﻿\r\n\r\n<div ng-controller=\"SessionController as sessionCtrl\">\r\n  <div ng-controller=\"NaviController as $naviCtrl\">\r\n    <div ng-if=\"!$naviCtrl.showFullPageLoader\">\r\n        <div class=\"modal-header bg-primary\">\r\n          <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.invitation.title\"></h2>\r\n          <button type=\"button\" class=\"btn-close btn-close-white\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n        </div>\r\n        <div class=\"modal-body salaxy-wizard\">\r\n          <form name=\"currentForm\">\r\n            <div class=\"row\">\r\n              <div class=\"col-md-12\" sxy-html=\"SALAXY.NG1.CustomerOnboardingComponent.invitation.html\" params=\"{signingLink : $ctrl.signingLink}\"></div>\r\n              <div class=\"col-md-12 text-end\">\r\n                <button \r\n                  type=\"button\" \r\n                  class=\"btn btn-primary\" \r\n                  ng-click=\"$ctrl.copyLink($ctrl.signingLink)\" \r\n                  data-bs-toggle=\"popover\" \r\n                  data-bs-html=\"true\" \r\n                  data-bs-title=\"Info\"\r\n                  data-bs-content=\"{{ !!$ctrl.linkCopied ? ('SALAXY.UI_Terms.copiedToClipboard' | sxyTranslate) : ('SALAXY.UI_Terms.copyToClipboard' | sxyTranslate)}}\" \r\n                  data-bs-container=\"body\" \r\n                  data-bs-placement=\"top\" \r\n                  data-bs-trigger=\"hover\"\r\n                  sxy-bs5-popover>\r\n                  <i class=\"bi bi-clipboard me-1\"></i>\r\n                  <span sxy-text=\"SALAXY.UI_Terms.copyToClipboard\"></span>\r\n                </button>\r\n              </div>\r\n            </div>\r\n          </form>\r\n        </div>\r\n        <div class=\"modal-footer text-start\">\r\n          <button class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n        </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/customer/user-buttons.html\",`<button ng-click=\"$close('cancel')\" class=\"btn btn-default\" sxy-text=\"SALAXY.UI_Terms.backToFront\"></button>\r\n<div salaxy-loader class=\"spinner\">\r\n  <div class=\"bounce1\"></div>\r\n  <div class=\"bounce2\"></div>\r\n  <div class=\"bounce3\"></div>\r\n</div>\r\n<button ng-disabled=\"!wizard.canGoNext\" ng-click=\"wizard.goToCompanySelection()\" class=\"btn btn-primary\" sxy-text=\"SALAXY.UI_Terms.next\"></button>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/customer/user.html\",`﻿<form name=\"currentForm\" class=\"form-horizontal\">\r\n  <span class=\"d-none\">{{ wizard.formDataValidity = currentForm.$valid }}</span>\r\n  <div class=\"row\">\r\n    <div class=\"col-12 col-md-6\">\r\n      <legend sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepUserInfo.userInfo\"></legend>\r\n      <salaxy-input label=\"SALAXY.NG1.CustomerOnboardingComponent.stepUserInfo.userFirstName\" name=\"Etunimi\" ng-model=\"wizard.model.person.firstName\" ng-required=\"true\"></salaxy-input>\r\n      <salaxy-input label=\"SALAXY.NG1.CustomerOnboardingComponent.stepUserInfo.userLastName\" name=\"Sukunimi\" ng-model=\"wizard.model.person.lastName\" ng-required=\"true\"></salaxy-input>\r\n      <salaxy-input label=\"SALAXY.NG1.CustomerOnboardingComponent.stepUserInfo.userEmail\" name=\"Sahkoposti\" ng-model=\"wizard.model.person.contact.email\" ng-required=\"true\" sxy-email></salaxy-input>\r\n      <salaxy-input label=\"SALAXY.NG1.CustomerOnboardingComponent.stepUserInfo.userPhone\" name=\"Puhelinnumero\" ng-model=\"wizard.model.person.contact.telephone\" ng-required=\"true\" sxy-mobile-phone></salaxy-input>\r\n    </div>\r\n\r\n    <div class=\"col-12 col-md-6\">\r\n      <legend sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepUserInfo.signeratureTitle\"></legend>\r\n      <p sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepUserInfo.signeratureText\"></p>\r\n      <div class=\"form-horizontal\">\r\n        <salaxy-input label=\"SALAXY.NG1.CustomerOnboardingComponent.stepUserInfo.userPersonalId\" name=\"Henkilotunnus\" sxy-personal-id-fi placeholder=\"SALAXY.NG1.CustomerOnboardingComponent.stepUserInfo.personalIdExample\" ng-model=\"wizard.model.signature.personalId\"\r\n          ng-required=\"true\"></salaxy-input>\r\n      </div>\r\n      <div class=\"alert alert-danger\" sxy-text=\"SALAXY.NG1.CustomerOnboardingComponent.stepUserInfo.checkSignatureAlert\"></div>\r\n\r\n      <div class=\"form-horizontal\">\r\n        <salaxy-input label=\"SALAXY.NG1.CustomerOnboardingComponent.stepUserInfo.businessId\" name=\"Ytunnus\" ng-model=\"wizard.model.company.businessId\" sxy-company-id-fi ng-required=\"true\"></salaxy-input>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/generic/index.html\",`<div ng-controller=\"SessionController as sessionCtrl\">\r\n  <div ng-controller=\"NaviController as $naviCtrl\">\r\n    <div ng-if=\"!$naviCtrl.showFullPageLoader\">\r\n      <div class=\"modal-header bg-primary\">\r\n        <img src=\"https://cdn.salaxy.com/img/palkkaus/logo/palkkaus-www-logo-white-border.png\" class=\"img-responsive d-none d-sm-inline-block modal-logo\" />\r\n        <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.GenericOnboardingComponent.modalTitle\"></h2>\r\n        <button type=\"button\" class=\"btn-close btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n      </div>\r\n      <div class=\"modal-body salaxy-wizard\">\r\n        <div>\r\n          <fieldset>\r\n            <legend sxy-text=\"SALAXY.NG1.GenericOnboardingComponent.roleTitle\" ps=\"*\"></legend>\r\n            <div class=\"form-horizontal\">\r\n              <div class=\"radio\" ng-repeat=\"accountType in ['company', 'worker']\">\r\n                <label ng-if=\"accountType == 'company'\">\r\n                  <input type=\"radio\" name=\"wizardType\" ng-model=\"$ctrl.data.model.accountType\" value=\"company\" ng-disabled=\"sessionCtrl.session.hasCurrentAccount\" /> \r\n                  <span sxy-text=\"SALAXY.NG1.GenericOnboardingComponent.roleCompany\"></span>\r\n                </label>\r\n                <label ng-if=\"accountType == 'worker'\">\r\n                  <input type=\"radio\" name=\"wizardType\" ng-model=\"$ctrl.data.model.accountType\" value=\"worker\" ng-disabled=\"sessionCtrl.session.hasCurrentAccount\" />\r\n                  <span sxy-text=\"SALAXY.NG1.GenericOnboardingComponent.roleWorker\"></span>\r\n                </label>\r\n              </div>\r\n            </div>\r\n          </fieldset>\r\n        </div>\r\n      </div>\r\n      <div class=\"modal-footer\">\r\n        <button ng-click=\"$ctrl.data.launch($close)\" ng-disabled=\"!$ctrl.data.model.accountType || $ctrl.data.model.accountType == 'none'\" class=\"btn btn-primary\" sxy-text=\"SALAXY.NG1.GenericOnboardingComponent.launchBtn\"></button>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/household/contract.html\",`﻿<form name=\"contractForm\">\r\n  <span class=\"d-none\">{{ wizard.formDataValidity = contractForm.$valid}}</span>\r\n\r\n  <h3>Palvelusopimus ja valtuutus</h3>\r\n  <p>\r\n    Rakennusliitto tarjoaa Palkkamylly-palvelun jäsenilleen ja heidän työnantajilleen. Palvelun tuottaa Suomen Palkanlaskenta Oy (Palkkaus.fi).\r\n  </p>\r\n  <p>\r\n    Jotta Palkkamylly voi hoitaa puolestasi palkanmaksuun liittyviä velvoitteita, sinun täytyy allekirjoittaa <a ng-href=\"{{ wizard.getPdfPreviewAddress() }}\" target=\"_blank\">oheinen valtakirja</a>. Se pitää allekirjoittaa vain kerran.\r\n  </p>\r\n  <p>\r\n    Kirjoita henkilötunnuksesi ja valitse pankkisi. Siirryt pankkisi verkkopalveluun, jossa varsinainen tunnistautuminen tapahtuu. Sen jälkeen palaat Palkkamylly-palveluun ja olet valmis aloittamaan käytön.\r\n  </p>\r\n\r\n\r\n  <div class=\"row\" ng-controller=\"SignatureController as sign\">\r\n    <div class=\"col-md-6\">\r\n      <fieldset>\r\n        <legend>Allekirjoita henkilötunnuksellasi</legend>\r\n        <div class=\"mb-3\">\r\n          <salaxy-input name=\"personalId\" label-type=\"plain\" type=\"text\" style=\"width:150px\" placeholder=\"PPKKVV-NNNX\" ng-model=\"wizard.model.signature.personalId\" require=\"true\" sxy-personal-id-fi></salaxy-input>\r\n        </div>\r\n      </fieldset>\r\n      <fieldset>\r\n        <legend>Valitse verkkopankkisi</legend>\r\n        <div ng-if=\"wizard.model.accountType == 'company'\">\r\n          <p>\r\n            Et voi käyttää yrityksen tai yhdistyksen verkkopankkitunnuksia valtakirjan allekirjoittamiseen. Sinun täytyy käyttää henkilökohtaisia verkkopankkitunnuksiasi\r\n          </p>\r\n        </div>\r\n        <div id=\"bankButtonRow\">\r\n          <div class=\"btn-group\" id=\"mostUsedBanks\">\r\n            <salaxy-toggle-buttons \r\n              ng-model=\"wizard.model.signature.method\" \r\n              options=\"$ctrl.visibleSignatureMethods\" \r\n              type=\"inline\">\r\n            </salaxy-toggle-buttons>\r\n          </div>\r\n          <div class=\"btn-group group-dropdown dropdown\">\r\n            <a class=\"btn btn-default dropdown-toggle\" id=\"other-banks-button\" data-bs-toggle=\"dropdown\" ng-class=\"(wizard.model.signature.method != null && sign.getMethod(wizard.model.signature.method).isPopular == false) ? 'bank-chosen': ''\">\r\n              <span ng-if=\"wizard.model.signature.method == null || sign.getMethod(wizard.model.signature.method).isPopular == true\">Muut verkkopankit</span>\r\n              <span ng-if=\"wizard.model.signature.method != null && sign.getMethod(wizard.model.signature.method).isPopular == false\">\r\n                <img ng-src=\"{{ sign.getMethod(wizard.model.signature.method).img }}\" style=\"max-height: 20px; max-width: 85px\"/> {{sign.getMethod(wizard.model.signature.method).title}}\r\n              </span> &nbsp; \r\n            </a>\r\n            <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"other-banks-button\">\r\n              <li ng-repeat=\"signMethod in sign.getMethods('telia') | filter: {isPopular:false}\" role=\"menuitem\" ng-class=\"wizard.model.signature.method == signMethod.value ? 'active' : ''\">\r\n                <a ng-click=\"wizard.model.signature.method = signMethod.value\" class=\"dropdown-item\">\r\n                  <img ng-src=\"{{signMethod.img}}\" style=\"max-height: 20px; max-width: 85px\" /> {{signMethod.title}}\r\n                </a>\r\n              </li>\r\n            </ul>\r\n          </div>\r\n        </div>\r\n      </fieldset>\r\n      <p class=\"mt-3\">\r\n\r\n        <strong>HUOM:</strong> Palkkamyllyn tarjoaa Rakennusliitto ry, joka toimii henkilötietojen käsittelijänä ja vastaa myös asiakaspalvelusta. Palvelun tuottajana ja teknisenä toteuttajana ja myös henkilötietojen käsittelijä toimii Suomen Palkanlaskenta\r\n        Oy (Palkkaus.fi).\r\n\r\n      </p>\r\n      <p>\r\n        Tunnistautumalla hyväksyt:<br>\r\n        <a href=\"https://storage.googleapis.com/rakennusliitto-production-uploads/content_management/documents/Palkkamylly_Kayttoehdot_Oct2021.pdf?Expires=1795336880&GoogleAccessId=cloud-run-service-account%40rakennusliitto.iam.gserviceaccount.com&Signature=dTZrDk4AgZv29ldlizR%2Bfe9uv5NgXtAU%2BZBr%2FgbO7p%2FWpoyc4rtUnbUyoRwqLE2OSJ2ZUIRvPucZt7jUhGiAmXEpsG7vsieoBHX9C1P%2F79VoJdIvLG9sqe4wOIQG0t0KUhNxv4I3dpymLV1F16T%2FKLN94vSGRLv6pNHblNqc3iGpoIw11d3dG3%2BhVL%2Fnajwcfirh7m7V7PLIn4fHNY6Q6PbfhbVRpeLprM37sUKTlCBLwdEihZJ7bNcoRvWG4CWfZMk9hRaV66YYadNxEEnBd6EOQZZ5%2B0S2%2F%2FSOLWT5d9amM%2F8S0IW7wOcwr3crCs%2BcroZ6aYSFrZ1H6TCTdRUkNA%3D%3D\"\r\n          target=\"_blank\">Palkkamyllyn käyttöehdot</a><br>\r\n        <a href=\"https://storage.googleapis.com/rakennusliitto-production-uploads/content_management/documents/Palkkamylly_Sopimus_henkilotietojen_kasittelysta_Oct2021.pdf?Expires=1795336940&GoogleAccessId=cloud-run-service-account%40rakennusliitto.iam.gserviceaccount.com&Signature=gcO62AB17YCjv5mVTtSP%2FtgG2RxGUSnaGpfK0GencENWGoq8FF1F5MlXEfyZ5pM6eW9tEubAWd8WkxP7WpmX63mtcvdnCViiz52TQjYiK%2BSjJw6ZD6QB%2F%2FPQRVQGsoKilFVJZ4HVshOWcsvOVrcR1ci6dlsFOQPnFQXQhalCaJHiFzGJzxsRtPEaD1GMtqANqzdcmZbqR6ULEE73G2WxYVJ4%2FeK1bpd0qAKlBvs%2Fh9DlDd8RDx5M3BSJj7q43KHP5kT8mOq2bky4xNnq7q31jgnub%2BVO1a4X7RAKzbKabW4D6y%2BlDKzK%2FJgnmbPsS8TzYFuSkH81aiqu5MGR2zfn9A%3D%3D\"\r\n          target=\"_blank\">Sopimuksen henkilötietojen käsittelystä</a><br>\r\n        <a href=\"https://storage.googleapis.com/rakennusliitto-production-uploads/content_management/documents/Palkkamylly_Tietosuojaseloste_Oct2021.pdf?Expires=1793455095&GoogleAccessId=cloud-run-service-account%40rakennusliitto.iam.gserviceaccount.com&Signature=dVqt3NenZZwBOPmmKz15jrIlgUOv2J2QE39Ltl7sK9t6iUC6YSXpnRifRoJLdcCrJpgt8KBpw%2FDXLm9olu5wzBFhSXKa1b4LRclyVjpzs27e9%2BMJceizLURvLWeKyZsyuYc%2BU3U7V0vkN0S%2B4nqkcDqskXCtvccmcBg0BgPYaslcSwLu4NUztiR2vA5qUj%2FL6hBelLqjKyqA%2FwDHahcTp07de6WqkEDud46W9Fv1oEJDioiho9W3%2F2W5kpVe2JxA3VB6D9j7Fwt45LBsDZC5opFiwnzWuahr7zEyn9UVuf4nLOJ83PcfYIsRo0pZWAPIgScsH%2BcAOXFgbnr5OkTu2A%3D%3D\"\r\n          target=\"_blank\">Tietosuojaselosteen</a>\r\n      </p>\r\n    </div>\r\n\r\n    <div class=\"col-md-6 d-none d-sm-block\">\r\n      <fieldset>\r\n        <legend>Valtakirjan esikatselu</legend>\r\n\r\n        <small><a ng-href=\"{{ wizard.getPdfPreviewAddress() }}\" target=\"_blank\">Lataa tästä, jos et näe esikatselua</a></small>\r\n\r\n        <iframe ng-src=\"{{ wizard.getPdfPreviewAddress() }}\" style=\"width: 100%; height: 300px\"></iframe>\r\n      </fieldset>\r\n    </div>\r\n\r\n\r\n  </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/household/contractButtons.html\",`﻿<button ng-click=\"wizard.goPrevious()\" ng-disabled=\"!wizard.canGoPrevious\" class=\"btn btn-default\">Edellinen</button>\r\n<div salaxy-loader class=\"spinner\">\r\n    <div class=\"bounce1\"></div>\r\n    <div class=\"bounce2\"></div>\r\n    <div class=\"bounce3\"></div>\r\n</div>\r\n\r\n<button ng-if=\"wizard.model.signature.personalId == null || wizard.model.signature.method == null\"  ng-disabled=\"true\" class=\"btn btn-primary\">Allekirjoita valtakirja<span class=\"d-none d-sm-inline\" ng-if=\"wizard.model.accountType != 'worker'\"> ja voit maksaa palkkaa</span></button>\r\n<a ng-if=\"!(wizard.model.signature.personalId == null || wizard.model.signature.method == null)\" ng-href=\"{{wizard.vismaSignUrl}}\" target=\"_top\"  class=\"btn btn-primary\">Allekirjoita valtakirja<span class=\"d-none d-sm-inline\" ng-if=\"wizard.model.accountType != 'worker'\"> ja voit maksaa palkkaa</span></a>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/household/firstPageButtons.html\",`﻿<!--a ng-if=\"wizard.model.ui.cancelUrl\" ng-href=\"{{wizard.model.ui.cancelUrl}}\"  class=\"btn btn-default\">Takaisin etusivulle</a-->\r\n\r\n<div salaxy-loader class=\"spinner\">\r\n  <div class=\"bounce1\"></div>\r\n  <div class=\"bounce2\"></div>\r\n  <div class=\"bounce3\"></div>\r\n</div>\r\n<button ng-click=\"wizard.goNext()\" ng-disabled=\"!wizard.canGoNext\" class=\"btn btn-primary\">Seuraava</button>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/household/household.html\",`﻿<form name=\"householdForm\" class=\"form-horizontal\">\r\n  <!-- Hidden variable formDataValidity to use in controller -->\r\n  <span class=\"d-none\">{{ wizard.formDataValidity = householdForm.$valid}}</span>\r\n  <div class=\"row\">\r\n    <div class=\"col-md-6\">\r\n      <fieldset>\r\n        <legend> Yhteystiedot \r\n          <i class=\"bi bi-info-circle-fill\"\r\n            type=\"button\" \r\n            data-bs-toggle=\"popover\" \r\n            data-bs-title=\"'Miksi kysymme osoitetietojasi?'\" \r\n            data-bs-content=\"'Lähetämme puolestasi tietoja ja erilaisia lomakkeita eri viranomaisille. Jotkut näistä viranomaisista vaativat joissain lomakkeissa osoitetiedot pakollisina tietoina.'\"\r\n            data-bs-container=\"body\" \r\n            data-bs-placement=\"top\" \r\n            sxy-bs5-popover>\r\n          </i>\r\n        </legend>\r\n        <div class=\"form-horizontal\">\r\n          <salaxy-input label=\"Katuosoite\" name=\"Katuosoite\" ng-model=\"wizard.model.person.contact.street\" require=\"true\"></salaxy-input>\r\n          <salaxy-input label=\"Postinumero\" name=\"Postinumero\" ng-model=\"wizard.model.person.contact.postalCode\" require=\"true\" sxy-postal-code-fi></salaxy-input>\r\n          <salaxy-input label=\"Postitoimipaikka\" name=\"Postitoimipaikka\" ng-model=\"wizard.model.person.contact.city\" require=\"true\"></salaxy-input>\r\n        </div>\r\n      </fieldset>\r\n    </div>\r\n    <div class=\"col-md-6\">\r\n      <fieldset>\r\n        <legend>Palkanmaksuun tarvittavat tiedot</legend>\r\n        <p>\r\n          Osoitetietojasi työnantajana tarvitaan tulorekisteri-ilmoitukseen, näin esim. työttömyysvakuutuslaskujen lähettäminen sinulle onnistuu.\r\n        </p>\r\n      </fieldset>\r\n    </div>\r\n  </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/household/householdButtons.html\",`﻿\r\n<button ng-click=\"wizard.goPrevious()\" ng-disabled=\"!wizard.canGoPrevious\" class=\"btn btn-default\">Edellinen</button>\r\n<div salaxy-loader class=\"spinner\">\r\n    <div class=\"bounce1\"></div>\r\n    <div class=\"bounce2\"></div>\r\n    <div class=\"bounce3\"></div>\r\n</div>\r\n<button ng-click=\"wizard.goNext()\" ng-disabled=\"!wizard.canGoNext\" class=\"btn btn-primary\">Seuraava</button>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/household/index.html\",`<div ng-controller=\"SessionController as sessionCtrl\">\r\n  <div ng-controller=\"HouseholdOnboardingController as wizard\">\r\n    <div ng-controller=\"NaviController as $naviCtrl\">\r\n\r\n      <div ng-if=\"!$naviCtrl.showFullPageLoader\">\r\n        <div class=\"modal-header bg-primary\">\r\n          <h2 class=\"modal-title\">Palkkamylly / Käyttöönotto</h2>\r\n          <button type=\"button\" class=\"btn-close btn-close-white\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n          <!--\r\n        TODO: Consider adding back with skinning. But perhaps not needed?\r\n        <img src=\"https://cdn.salaxy.com/img/palkkaus/logo/palkkaus-www-logo-white-border.png\" class=\"img-responsive d-none d-sm-inline modal-logo\" />\r\n      -->\r\n        </div>\r\n        <div class=\"modal-body\">\r\n          <div class=\"d-block d-md-none\">\r\n            <h4>Vaihe {{wizard.currentStep.number}}/{{wizard.steps.length}}</h4>\r\n          </div>\r\n          <div class=\"salaxy-wizard\">\r\n            <div class=\"wizard-steps\">\r\n              <div class=\"wizard-step\" ng-repeat=\"step in $ctrl.steps\" ng-class=\"{'active': step.active, 'disabled': step.disabled}\">\r\n                <span class=\"salaxy-avatar\">\r\n                  <div class=\"wizard-icons-wrapper\">\r\n                    <i class=\"bi\" ng-class=\"step.active ? 'bi-circle-fill' : 'bi-circle'\"></i>\r\n                    <i class=\"bi bi-circle-fill\"></i>\r\n                  </div>\r\n                  <strong class=\"number\">{{ step.number }}</strong>\r\n                </span>\r\n                <span class=\"step-text\">{{ step.title | sxyTranslate }}</span>\r\n              </div>\r\n            </div>\r\n            <div class=\"wizard-strikethrough\"></div>\r\n          </div>\r\n          <ng-include src=\"wizard.currentStep.view\"></ng-include>\r\n        </div>\r\n        <div class=\"modal-footer\">\r\n          <ng-include class=\"d-flex justify-content-between w-100\" src=\"wizard.currentStep.buttonsView\"></ng-include>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/household/wizard_index.html\",`﻿<form name=\"currentForm\" class=\"form-horizontal\">\r\n  <!-- Hidden ariable formDataValidity to use in controller -->\r\n  <span class=\"d-none\">{{ wizard.formDataValidity = currentForm.$valid }}</span>\r\n  <div class=\"\">\r\n    <br/>\r\n    <p>{{wizard.currentStep.intro | sxyTranslate}}</p>\r\n\r\n    <br/>\r\n  </div>\r\n  <div class=\"row\">\r\n    <div class=\"col-md-6\">\r\n      <fieldset>\r\n        <legend>Henkilötiedot</legend>\r\n        <salaxy-input label=\"Etunimi\" name=\"Etunimi\" ng-model=\"wizard.model.person.firstName\" ng-required=\"true\"></salaxy-input>\r\n        <salaxy-input label=\"Sukunimi\" name=\"Sukunimi\" ng-model=\"wizard.model.person.lastName\" ng-required=\"true\"></salaxy-input>\r\n      </fieldset>\r\n    </div>\r\n    <div class=\"col-md-6\">\r\n      <fieldset>\r\n        <legend>Yhteystiedot</legend>\r\n        <salaxy-input label=\"Sähköposti\" name=\"Sahkoposti\" ng-model=\"wizard.model.person.contact.email\" ng-required=\"true\" sxy-email read-only=\"!!wizard.model.person.contact.email\"></salaxy-input>\r\n        <salaxy-input label=\"Puhelinnumero\" name=\"Puhelinnumero\" ng-model=\"wizard.model.person.contact.telephone\" ng-required=\"true\" sxy-mobile-phone></salaxy-input>\r\n      </fieldset>\r\n    </div>\r\n  </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/palkkamylly/federate-sign.html\",`<div ng-controller=\"SessionController as sessionCtrl\" class=\"worker-onboarding-wizard\">\r\n  <div ng-controller=\"WorkerOnboardingController as wizard\">\r\n    <div class=\"modal-header bg-primary\">\r\n      <h2 class=\"modal-title\">Palkkamylly käyttöönotto</h2>\r\n      <button type=\"button\" class=\"btn-close btn-close-white\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n    </div>\r\n    <div class=\"modal-body salaxy-wizard\">\r\n      <form name=\"contractForm\">\r\n        <span class=\"d-none\">{{ wizard.formDataValidity = contractForm.$valid && !wizard.model.signature.personalId && !wizard.model.signature.method}}</span>\r\n        <div ng-controller=\"SignatureController as sign\">\r\n          <h3>Palvelusopimus ja valtuutus</h3>\r\n          <p>\r\n            Rakennusliitto tarjoaa Palkkamylly-palvelun jäsenilleen ja heidän työnantajilleen. Palvelun tuottaa Suomen Palkanlaskenta Oy (Palkkaus.fi).\r\n          </p>\r\n          <p>\r\n            Jotta Palkkamylly voi hoitaa puolestasi palkanmaksuun liittyviä velvoitteita, sinun täytyy allekirjoittaa <a ng-href=\"{{ wizard.getPdfPreviewAddress() }}\" target=\"_blank\">oheinen valtakirja</a>. Se pitää allekirjoittaa vain kerran.\r\n          </p>\r\n          <p>Kirjoita henkilötunnuksesi, valitse pankkisi ja paina Tunnistaudu-nappia. Siirryt pankkisi verkkopalveluun, jossa varsinainen tunnistautuminen tapahtuu. Sen jälkeen palaat Palkkamylly-palveluun ja olet valmis aloittamaan käytön.</p>\r\n          <div class=\"row form-horizontal\" ng-init=\"ui.telephone = wizard.model.person.contact.telephone\">\r\n            <div class=\"\" ng-init=\"wizard.model.signature.personalId = wizard.model.person.personalId\" ng-class=\"{'col-sm-6': ui.telephone, 'col-sm-8': !ui.telephone}\">\r\n              <salaxy-input label=\"Tarkista henkilötunnuksesi\" label-type=\"basic\" name=\"personalId\" placeholder=\"PPKKVV-NNNX\" ng-model=\"wizard.model.signature.personalId\" sxy-personal-id-fi ng-required=\"true\"></salaxy-input>\r\n            </div>\r\n            <div ng-if=\"ui.telephone\" class=\"col-sm-6\">\r\n              <salaxy-input label=\"Tarkista puhelinnumerosi\" name=\"telephone\" ng-model=\"wizard.model.person.contact.telephone\" sxy-mobile-phone label-type=\"basic\" ng-required=\"true\"></salaxy-input>\r\n            </div>\r\n            <div ng-if=\"!ui.telephone\" class=\"col-sm-4\">\r\n              <salaxy-input label=\"Puhelinnumero\" name=\"telephone\" ng-model=\"wizard.model.person.contact.telephone\" sxy-mobile-phone label-type=\"basic\" ng-required=\"true\"></salaxy-input>\r\n            </div>\r\n          </div>\r\n\r\n          <div class=\"row form-horizontal\">\r\n            <div class=\"col-sm-4\">\r\n              <salaxy-input label=\"Etunimi\" name=\"firstName\" ng-model=\"wizard.model.person.firstName\" label-type=\"basic\" readonly=\"true\"></salaxy-input>\r\n            </div>\r\n            <div class=\"col-sm-4\">\r\n              <salaxy-input label=\"Sukunimi\" name=\"lastName\" ng-model=\"wizard.model.person.lastName\" label-type=\"basic\" readonly=\"true\"></salaxy-input>\r\n            </div>\r\n            <div class=\"col-sm-4\">\r\n              <salaxy-input label=\"Sähköpostiosoite\" name=\"email\" ng-model=\"wizard.model.person.contact.email\" label-type=\"basic\" readonly=\"true\"></salaxy-input>\r\n            </div>\r\n          </div>\r\n\r\n          <div class=\"row mb-2\" ng-if=\"wizard.isOtherIdentifier(wizard.model.signature.personalId)\">\r\n            <div class=\"col-12\">\r\n              <h5><strong>Osoite</strong></h5>\r\n            </div>\r\n            <salaxy-input ng-model=\"wizard.model.person.contact.street\" placeholder=\"Katuosoite\" name=\"street\" class=\"col-sm-4\" label-type=\"plain\" ng-required=\"true\"></salaxy-input>\r\n            <salaxy-input ng-model=\"wizard.model.person.contact.postalCode\" placeholder=\"Postinumero\" name=\"postalCode\" class=\"col-sm-4\" label-type=\"plain\" ng-required=\"true\"></salaxy-input>\r\n            <salaxy-input ng-model=\"wizard.model.person.contact.city\" placeholder=\"Toimipaikka\" name=\"city\" class=\"col-sm-4\" label-type=\"plain\" ng-required=\"true\"></salaxy-input>\r\n          </div>\r\n\r\n          <h4>\r\n            Ja valitse verkkopankkisi\r\n            <small>\r\n              <i class=\"bi bi-info-circle-fill\"\r\n                type=\"button\" \r\n                data-bs-toggle=\"popover\" \r\n                data-bs-content=\"'Kun olet valinnut pankkisi ja painat \\\\'Tunnistaudu\\\\'- nappia, siirryt tekemään sähköisen allekirjoituksen verkkopankkitunnuksillasi. Tunnistautumisen jälkeen palaat Palkkaus.fi-palveluun.'\"\r\n                data-bs-container=\"body\" \r\n                sxy-bs5-popover>\r\n              </i>\r\n            </small>\r\n          </h4>\r\n          <div id=\"bankButtonRow\">\r\n            <salaxy-toggle-buttons \r\n              ng-model=\"wizard.model.signature.method\" \r\n              options=\"$ctrl.signatureMethods\" \r\n              type=\"row\">\r\n            </salaxy-toggle-buttons>\r\n          </div>\r\n          <br/>\r\n          <p class=\"mt-3\">\r\n            <strong>HUOM:</strong> Palkkamyllyn tarjoaa Rakennusliitto ry, joka toimii henkilötietojen käsittelijänä ja vastaa myös asiakaspalvelusta. Palvelun tuottajana ja teknisenä toteuttajana ja myös henkilötietojen käsittelijä toimii Suomen Palkanlaskenta\r\n            Oy (Palkkaus.fi).\r\n          </p>\r\n          <p>Tunnistautumalla hyväksyt:<br>\r\n            <a href=\"https://storage.googleapis.com/rakennusliitto-production-uploads/content_management/documents/Palkkamylly_Kayttoehdot_Oct2021.pdf?Expires=1795336880&GoogleAccessId=cloud-run-service-account%40rakennusliitto.iam.gserviceaccount.com&Signature=dTZrDk4AgZv29ldlizR%2Bfe9uv5NgXtAU%2BZBr%2FgbO7p%2FWpoyc4rtUnbUyoRwqLE2OSJ2ZUIRvPucZt7jUhGiAmXEpsG7vsieoBHX9C1P%2F79VoJdIvLG9sqe4wOIQG0t0KUhNxv4I3dpymLV1F16T%2FKLN94vSGRLv6pNHblNqc3iGpoIw11d3dG3%2BhVL%2Fnajwcfirh7m7V7PLIn4fHNY6Q6PbfhbVRpeLprM37sUKTlCBLwdEihZJ7bNcoRvWG4CWfZMk9hRaV66YYadNxEEnBd6EOQZZ5%2B0S2%2F%2FSOLWT5d9amM%2F8S0IW7wOcwr3crCs%2BcroZ6aYSFrZ1H6TCTdRUkNA%3D%3D\"\r\n              target=\"_blank\">Palkkamyllyn käyttöehdot</a><br>\r\n            <a href=\"https://storage.googleapis.com/rakennusliitto-production-uploads/content_management/documents/Palkkamylly_Sopimus_henkilotietojen_kasittelysta_Oct2021.pdf?Expires=1795336940&GoogleAccessId=cloud-run-service-account%40rakennusliitto.iam.gserviceaccount.com&Signature=gcO62AB17YCjv5mVTtSP%2FtgG2RxGUSnaGpfK0GencENWGoq8FF1F5MlXEfyZ5pM6eW9tEubAWd8WkxP7WpmX63mtcvdnCViiz52TQjYiK%2BSjJw6ZD6QB%2F%2FPQRVQGsoKilFVJZ4HVshOWcsvOVrcR1ci6dlsFOQPnFQXQhalCaJHiFzGJzxsRtPEaD1GMtqANqzdcmZbqR6ULEE73G2WxYVJ4%2FeK1bpd0qAKlBvs%2Fh9DlDd8RDx5M3BSJj7q43KHP5kT8mOq2bky4xNnq7q31jgnub%2BVO1a4X7RAKzbKabW4D6y%2BlDKzK%2FJgnmbPsS8TzYFuSkH81aiqu5MGR2zfn9A%3D%3D\"\r\n              target=\"_blank\">Sopimuksen henkilötietojen käsittelystä</a><br>\r\n            <a href=\"https://storage.googleapis.com/rakennusliitto-production-uploads/content_management/documents/Palkkamylly_Tietosuojaseloste_Oct2021.pdf?Expires=1793455095&GoogleAccessId=cloud-run-service-account%40rakennusliitto.iam.gserviceaccount.com&Signature=dVqt3NenZZwBOPmmKz15jrIlgUOv2J2QE39Ltl7sK9t6iUC6YSXpnRifRoJLdcCrJpgt8KBpw%2FDXLm9olu5wzBFhSXKa1b4LRclyVjpzs27e9%2BMJceizLURvLWeKyZsyuYc%2BU3U7V0vkN0S%2B4nqkcDqskXCtvccmcBg0BgPYaslcSwLu4NUztiR2vA5qUj%2FL6hBelLqjKyqA%2FwDHahcTp07de6WqkEDud46W9Fv1oEJDioiho9W3%2F2W5kpVe2JxA3VB6D9j7Fwt45LBsDZC5opFiwnzWuahr7zEyn9UVuf4nLOJ83PcfYIsRo0pZWAPIgScsH%2BcAOXFgbnr5OkTu2A%3D%3D\"\r\n              target=\"_blank\">Tietosuojaselosteen</a>\r\n          </p>\r\n        </div>\r\n      </form>\r\n    </div>\r\n    <div class=\"modal-footer\">\r\n      <div salaxy-loader class=\"spinner\">\r\n        <div class=\"bounce1\"></div>\r\n        <div class=\"bounce2\"></div>\r\n        <div class=\"bounce3\"></div>\r\n      </div>\r\n      <button ng-if=\"wizard.model.signature.personalId == null || wizard.model.signature.method == null\" ng-disabled=\"true\" class=\"btn btn-primary\">Tunnistaudu</button>\r\n      <a ng-if=\"!(wizard.model.signature.personalId == null || wizard.model.signature.method == null)\" ng-href=\"{{wizard.vismaSignUrl}}\" target=\"_top\" class=\"btn btn-primary\">Tunnistaudu</a>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/worker/contract-worker.html\",`﻿<form name=\"contractForm\">\r\n  <span class=\"d-none\">{{ wizard.formDataValidity = contractForm.$valid && !wizard.model.signature.personalId && !wizard.model.signature.method}}</span>\r\n  <div ng-controller=\"SignatureController as sign\">\r\n\r\n    <h3 sxy-text=\"SALAXY.NG1.WorkerOnboardingComponent.stepContract.title\"></h3>\r\n    <p sxy-text=\"SALAXY.NG1.WorkerOnboardingComponent.stepContract.signatureText\"></p>\r\n    <p sxy-text=\"SALAXY.NG1.WorkerOnboardingComponent.stepContract.signatureText2\"></p>\r\n    <fieldset>\r\n      <legend sxy-text=\"SALAXY.NG1.WorkerOnboardingComponent.stepContract.personalId\"></legend>\r\n      <div class=\"row\" style=\"max-width:150px;\">\r\n        <salaxy-input name=\"personalId\" label-type=\"plain\" type=\"text\" style=\"width:150px\" sxy-personal-id-fi ng-required=\"true\" placeholder=\"SALAXY.NG1.WorkerOnboardingComponent.stepContract.personalIdExample\" ng-model=\"wizard.model.signature.personalId\" sxy-personal-id-fi>\r\n      </div>\r\n      <div class=\"mb-2\">\r\n        <input ng-init=\"wizard.model.signature.terms = false\" name=\"terms\" type=\"checkbox\" require=\"true\" ng-model=\"wizard.model.signature.terms\"></input>\r\n        <span style=\"margin-left: 5px;\" sxy-html=\"SALAXY.NG1.WorkerOnboardingComponent.stepContract.termsText.html\"></span> <a ng-href=\"{{ wizard.getPdfPreviewAddress() }}\" target=\"_blank\"><span sxy-text=\"SALAXY.NG1.WorkerOnboardingComponent.stepContract.termsText2\"></span></a>\r\n        <span sxy-html=\"SALAXY.NG1.WorkerOnboardingComponent.stepContract.termsText3.html\"></span>\r\n      </div>\r\n    </fieldset>\r\n    <fieldset>\r\n      <legend sxy-text=\"SALAXY.NG1.WorkerOnboardingComponent.stepContract.chooseBank\"></legend>\r\n      <div id=\"bankButtonRow\">\r\n        <salaxy-toggle-buttons \r\n          ng-model=\"wizard.model.signature.method\" \r\n          options=\"$ctrl.signatureMethods\" \r\n          type=\"row\">\r\n        </salaxy-toggle-buttons>\r\n      </div>\r\n    </fieldset>\r\n    <p sxy-html=\"SALAXY.NG1.WorkerOnboardingComponent.stepContract.privacyPolicy.html\"></p>\r\n\r\n    <p>\r\n      <span sxy-text=\"SALAXY.NG1.WorkerOnboardingComponent.stepContract.savePdfText\"></span>\r\n      <a ng-href=\"{{ wizard.getPdfPreviewAddress() }}\" target=\"_blank\">\r\n        <span sxy-text=\"SALAXY.NG1.WorkerOnboardingComponent.stepContract.savePdfLink\"></span>\r\n      </a>\r\n      <span sxy-text=\"SALAXY.NG1.WorkerOnboardingComponent.stepContract.savePdfText2\"></span>\r\n    </p>\r\n\r\n  </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/worker/contractButtons.html\",`﻿<button ng-click=\"wizard.goPrevious()\" ng-disabled=\"!wizard.canGoPrevious\" class=\"btn btn-default\">{{'SALAXY.UI_Terms.previous' | sxyTranslate}}</button>\r\n<div salaxy-loader class=\"spinner\">\r\n  <div class=\"bounce1\"></div>\r\n  <div class=\"bounce2\"></div>\r\n  <div class=\"bounce3\"></div>\r\n</div>\r\n<button ng-if=\"wizard.model.signature.personalId == null || wizard.model.signature.method == null || wizard.model.signature.terms == false\" ng-disabled=\"true\" class=\"btn btn-primary\">{{'SALAXY.NG1.WorkerOnboardingComponent.signBtn' | sxyTranslate}}</button>\r\n<a ng-if=\"!(wizard.model.signature.personalId == null || wizard.model.signature.method == null || wizard.model.signature.terms == false)\" ng-href=\"{{wizard.vismaSignUrl}}\" target=\"_top\" class=\"btn btn-primary\">{{'SALAXY.NG1.WorkerOnboardingComponent.signBtn' | sxyTranslate}}</a>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/worker/firstPageButtons.html\",`﻿<button class=\"btn btn-default\" ng-click=\"$close('cancel')\">{{'SALAXY.UI_Terms.backToFront' | sxyTranslate}}</button>\r\n<div salaxy-loader class=\"spinner\">\r\n  <div class=\"bounce1\"></div>\r\n  <div class=\"bounce2\"></div>\r\n  <div class=\"bounce3\"></div>\r\n</div>\r\n\r\n<button ng-click=\"wizard.goNext()\" class=\"btn btn-primary\" ng-disabled=\"!wizard.canGoNext\">{{'SALAXY.UI_Terms.next' | sxyTranslate}}</button>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/worker/index.html\",`<div ng-controller=\"SessionController as sessionCtrl\" class=\"worker-onboarding-wizard\">\r\n  <div ng-controller=\"WorkerOnboardingController as wizard\">\r\n    <div ng-controller=\"NaviController as $naviCtrl\">\r\n      <div ng-if=\"!$naviCtrl.showFullPageLoader\">\r\n        <div class=\"modal-header bg-primary\">\r\n          <img src=\"https://cdn.salaxy.com/img/palkkaus/logo/palkkaus-www-logo-white-border.png\" class=\"img-responsive d-none b-sm-inline-block modal-logo\" />\r\n          <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.WorkerOnboardingComponent.title\"></h2>\r\n          <button type=\"button\" class=\"btn-close btn-close-white\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n          \r\n        </div>\r\n        <div class=\"modal-body\">\r\n          <div class=\"d-block d-md-none\">\r\n            <h4><span sxy-text=\"SALAXY.NG1.WorkerOnboardingComponent.step\"></span> {{wizard.currentStep.number}}/{{wizard.steps.length}}</h4>\r\n          </div>\r\n          <div class=\"salaxy-wizard\">\r\n            <div class=\"wizard-steps\">\r\n              <div class=\"wizard-step\" ng-repeat=\"step in $ctrl.steps\" ng-class=\"{'active': step.active, 'disabled': step.disabled}\">\r\n                <span class=\"salaxy-avatar\">\r\n                  <div class=\"wizard-icons-wrapper\">\r\n                    <i class=\"bi\" ng-class=\"step.active ? 'bi-circle-fill' : 'bi-circle'\"></i>\r\n                    <i class=\"bi bi-circle-fill\"></i>\r\n                  </div>\r\n                  <strong class=\"number\">{{ step.number }}</strong>\r\n                </span>\r\n                <span class=\"step-text\">{{ step.title | sxyTranslate }}</span>\r\n              </div>\r\n            </div>\r\n            <div class=\"wizard-strikethrough\"></div>\r\n          </div>\r\n          <ng-include src=\"wizard.currentStep.view\"></ng-include>\r\n        </div>\r\n        <div class=\"modal-footer\">\r\n          <ng-include class=\"d-flex justify-content-between w-100\" src=\"wizard.currentStep.buttonsView\"></ng-include>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/onboarding/worker/user-info.html\",`﻿<form name=\"currentForm\">\r\n  <!-- Hidden ariable formDataValidity to use in controller -->\r\n  <span class=\"d-none\">{{ wizard.formDataValidity = currentForm.$valid }}</span>\r\n\r\n  <br/>\r\n  <p sxy-text=\"SALAXY.NG1.WorkerOnboardingComponent.stepUserInfo.registerText\"></p>\r\n  <br>\r\n  <div class=\"row\">\r\n    <div class=\"col-12 col-md-6\">\r\n      <div class=\"form-horizontal\">\r\n        <salaxy-input label=\"SALAXY.NG1.WorkerOnboardingComponent.stepUserInfo.firstName\" name=\"Etunimi\" ng-model=\"wizard.model.person.firstName\" ng-required=\"true\"></salaxy-input>\r\n        <salaxy-input label=\"SALAXY.NG1.WorkerOnboardingComponent.stepUserInfo.lastName\" name=\"Sukunimi\" ng-model=\"wizard.model.person.lastName\" ng-required=\"true\"></salaxy-input>\r\n        <salaxy-input label=\"SALAXY.NG1.WorkerOnboardingComponent.stepUserInfo.email\" name=\"Sahkoposti\" ng-model=\"wizard.model.person.contact.email\" ng-required=\"true\" sxy-email></salaxy-input>\r\n      </div>\r\n    </div>\r\n    <div class=\"col-12 col-md-6\">\r\n      <div class=\"row language-selection mb-2\" ng-controller=\"SessionController as $session\">\r\n        <div class=\"col-4 control-label\"><strong class=\"\" sxy-text=\"SALAXY.NG1.WorkerOnboardingComponent.stepUserInfo.language\" ps=\":\"></strong></div>\r\n\r\n        <div class=\"col-8\">\r\n          <div class=\"btn-group btn-group-sm float-end\" role=\"group\">\r\n            <button class=\"btn btn-default\" ng-class=\"{'active btn-primary' : $session.getLanguage() == 'fi'}\" ng-click=\"$session.setLanguage('fi'); wizard.model.person.language = 'fi'\">{{'SALAXY.ENUM.Language.fi.label' | sxyTranslate}}</button>\r\n            <button class=\"btn btn-default \" ng-class=\"{'active btn-primary' : $session.getLanguage() == 'en'}\" ng-click=\"$session.setLanguage('en'); wizard.model.person.language = 'en'\">{{'SALAXY.ENUM.Language.en.label' | sxyTranslate}}</button>\r\n            <button class=\"btn btn-default\" ng-class=\"{'active btn-primary' : $session.getLanguage() == 'sv'}\" ng-click=\"$session.setLanguage('sv'); wizard.model.person.language = 'sv'\">{{'SALAXY.ENUM.Language.sv.label' | sxyTranslate}}</button>\r\n          </div>\r\n        </div>\r\n\r\n      </div>\r\n      <div class=\"form-horizontal\">\r\n        <salaxy-input label=\"SALAXY.NG1.WorkerOnboardingComponent.stepUserInfo.phoneNumber\" name=\"Puhelinnumero\" ng-model=\"wizard.model.person.contact.telephone\" ng-required=\"true\" sxy-mobile-phone></salaxy-input>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/payment/cfa/EInvoice.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" id=\"salaxyEInvoiceLabel\" sxy-text=\"SALAXY.NG1.NewPaymentComponent.einvoice.title\"></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n</div>\r\n<div class=\"modal-body\">\r\n  <p sxy-text=\"SALAXY.NG1.NewPaymentComponent.einvoice.description\"></p>\r\n  <form name=\"address\" class=\"form-horizontal\">\r\n    <salaxy-form-group name=\"eInvoiceReceiver\" label=\"SALAXY.NG1.PaymentSettingsComponent.einvoice.invoiceAddress\">\r\n      <div class=\"input-group\">\r\n        <input required class=\"form-control\" type=\"text\" autocomplete=\"off\" id=\"eInvoiceReceiver\" name=\"eInvoiceReceiver\" ng-disabled=\"true\" ng-model=\"$ctrl.current.eInvoiceReceiver\" >\r\n        <span class=\"input-group-btn\">\r\n          <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.logic.selectEInvoiceAddress($ctrl.current)\" sxy-text=\"Valitse...\"></button>\r\n        </span>\r\n      </div>\r\n    </salaxy-form-group>\r\n    <salaxy-input require=\"true\" disabled=\"true\" name=\"intermediator\" ng-model=\"$ctrl.current.eInvoiceIntermediator\" label=\"SALAXY.NG1.NewPaymentComponent.einvoice.intermediatorLabel\"></salaxy-input>\r\n  </form>\r\n</div>\r\n<div class=\"modal-footer text-start\">\r\n  <button type=\"submit\" class=\"btn btn-primary float-end\" ng-disabled=\"!address.$valid\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.send\"></button>\r\n  <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/payment/cfa/Transfer.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" id=\"salaxyTransferLabel\" sxy-text=\"SALAXY.NG1.NewPaymentComponent.selection.creditTransferTitle\"></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n</div>\r\n<div class=\"modal-body\" id=\"modal-body\">\r\n  <div class=\"credit-transfer-container\">\r\n    <div class=\"text-end d-print-none\">\r\n      <button type=\"button\" class=\"btn btn-default btn-sm\" ng-click=\"$ctrl.logic.print('sxyFullPrint')\" sxy-text=\"SALAXY.UI_Terms.print\"></button>\r\n      <button type=\"button\" class=\"btn btn-default btn-sm\" ng-click=\"$ctrl.logic.print('sxySecurePrint')\" sxy-text=\"SALAXY.NG1.NewPaymentComponent.creditTransfer.securePrint\"></button>\r\n    </div>\r\n    <salaxy-credit-transfer invoice=\"$ctrl.current\">\r\n      <message>\r\n        <p sxy-text=\"SALAXY.NG1.NewPaymentComponent.creditTransfer.mainContent\"></p>\r\n      </message>\r\n    </salaxy-credit-transfer>\r\n    <div class=\"payment-per-worker-container table-responsive\" ng-class=\"$ctrl.logic.printClass\">\r\n      <h4 sxy-text=\"SALAXY.NG1.NewPaymentComponent.creditTransfer.calcsBreakdown\"></h4>\r\n      <table>\r\n        <thead>\r\n          <tr>\r\n            <th class=\"align-bottom\" sxy-text=\"SALAXY.NG1.NewPaymentComponent.creditTransfer.worker\"></th>\r\n            <th class=\"right\"><strong sxy-text=\"SALAXY.NG1.NewPaymentComponent.creditTransfer.totalGrossSalary\"></strong></th>\r\n            <th class=\"right\"> <strong sxy-text=\"SALAXY.NG1.NewPaymentComponent.creditTransfer.payNow\"></strong></th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr class=\"payment-per-worker\" ng-repeat=\"calc in $ctrl.logic.calculations\">\r\n            <td class=\"align-middle\"> {{calc.worker.avatar.sortableName}}</td>\r\n            <td class=\"right\">{{calc.result.totals.totalGrossSalary | currency}}</td>\r\n            <td class=\"right\">\r\n              {{calc.result.employerCalc.totalPayment| currency}}\r\n            </td>\r\n          </tr>\r\n          <tr class=\"total\">\r\n            <td><strong sxy-text=\"SALAXY.NG1.NewPaymentComponent.creditTransfer.paymentPerWorkerTable.total\"></strong><br><span sxy-text=\"SALAXY.NG1.NewPaymentComponent.creditTransfer.paymentPerWorkerTable.palkkausFee\"></span></td>\r\n            <td class=\"right\">{{$ctrl.logic.totalResultCalculation.result.totals.totalGrossSalary | currency}}</td>\r\n            <td class=\"right\">\r\n              {{$ctrl.logic.totalResultCalculation.result.employerCalc.totalPayment | currency}}<br>{{$ctrl.logic.totalResultCalculation.result.employerCalc.palkkaus | currency}}</td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n\r\n    <div sxy-if-role=\"!household\" class=\"table-responsive\">\r\n      <h4 sxy-text=\"SALAXY.NG1.NewPaymentComponent.creditTransfer.paymentTable\"></h4>\r\n      <salaxy-calc-report apply-site-styles=\"true\" calc=\"$ctrl.logic.totalResultCalculation\" report-type=\"'paymentReport'\" template-name=\"'paymentTablesV2'\"></salaxy-calc-report>\r\n    </div>\r\n  </div>\r\n</div>\r\n<div class=\"modal-footer text-start d-print-none\">\r\n  <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/payment/PaymentCancel.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" id=\"salaxyPaymentCancelDialogLabel\" sxy-text=\"SALAXY.NG1.PaymentCancelDialogComponent.paymentCancelled\"></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n</div>\r\n<div class=\"modal-body\">\r\n  <p sxy-text=\"SALAXY.NG1.PaymentCancelDialogComponent.paymentCancelledBank\"></p>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button type=\"button\" class=\"btn btn-danger\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/payment/PaymentConfirm.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" id=\"salaxyPaymentConfirmDialogLabel\" sxy-text=\"SALAXY.NG1.PaymentConfirmDialogComponent.paymentConfirmed\"></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n</div>\r\n<div class=\"modal-body\">\r\n  <p sxy-text=\"SALAXY.NG1.PaymentConfirmDialogComponent.paymentConfirmedInfo\"></p>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button type=\"button\" class=\"btn btn-danger\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/payment/PaymentError.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" id=\"salaxyPaymentErrorDialogLabel\" sxy-text=\"Maksaminen keskeytetty\"></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n</div>\r\n<div class=\"modal-body\">\r\n  <p sxy-text=\"Maksaminen keskeytyi virheen vuoksi. Yritä uudelleen tai käytä muuta maksua.\"></p>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button type=\"button\" class=\"btn btn-danger\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/payment/psd/BankSelection.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" id=\"salaxyPaymentConfirmDialogLabel\" sxy-text=\"Valitse pankki\"></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n</div>\r\n<div class=\"modal-body\">\r\n  <div class=\"d-flex flex-column align-items-start\">\r\n    <p sxy-text=\"Valitse pankki, josta haluat suorittaa PSD-maksun\"></p>\r\n    <div ng-click=\"$ctrl.logic.selectBank(bank.id)\" ng-repeat=\"bank in $ctrl.logic.banks\" class=\"btn btn-default mb-2\" style=\"width: 400px; height: 50px;\" ng-class=\"{'active': $ctrl.logic.selectedBank === bank.id}\" aria-label=\"{{bank.name}}\">\r\n      <img ng-src=\"{{bank.logo}}\" style=\"max-height: 20px; max-width: 85px\" />\r\n        {{bank.name}}\r\n    </div>\r\n  </div>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n  <button type=\"submit\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.select\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/payroll/PayrollDetailsList.html\",`<div class=\"modal-worker-list\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{$ctrl.logic.title}}</h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <div class=\"table-responsive\" style=\"max-height: calc(100vh - 300px)\">\r\n      <salaxy-payroll-details-select-list category=\"{{ $ctrl.logic.category || 'draft' }}\" mode=\"select\" selected-items=\"$ctrl.current\"></salaxy-payroll-details-select-list>\r\n    </div>\r\n    <div class=\"text-end\">\r\n      <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n      <button type=\"submit\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/payroll/PayrollList.html\",`<div class=\"modal-worker-list\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{$ctrl.logic.title}}</h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <div class=\"table-responsive\" style=\"max-height: calc(100vh - 300px)\">\r\n      <salaxy-payroll-select-list category=\"{{ $ctrl.logic.category || 'draft' }}\" mode=\"select\" selected-items=\"$ctrl.current\"></salaxy-payroll-select-list>\r\n    </div>\r\n    <div class=\"text-end\">\r\n      <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n      <button type=\"submit\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/records/Record.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\">{{ $ctrl.logic.title }}</h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n</div>\r\n<div class=\"modal-body\">\r\n  <form class=\"form-horizontal\" name=\"record\" ng-readonly=\"$ctrl.logic.readOnly\">\r\n    <fieldset>\r\n      <div class=\"subtext\">\r\n        {{ 'SALAXY.NG1.WorkerDetailsComponent.records.createTypeInfo' | sxyTranslate }}\r\n      </div>\r\n      <salaxy-form-group ng-if=\"!$ctrl.logic.readOnly\" name=\"recordType\" label=\"SALAXY.NG1.WorkerDetailsComponent.records.recordType\">\r\n        <div class=\"input-group\">\r\n          <input ng-model=\"$ctrl.current.record.recordType\" type=\"text\" class=\"form-control\">\r\n          <div class=\"input-group-btn dropdown\">\r\n            <button type=\"button\" class=\"btn btn-default dropdown-toggle h-100\" data-bs-toggle=\"dropdown\"></button>\r\n            <ul class=\"dropdown-menu dropdown-menu-end\">\r\n              <li ng-repeat=\"recordType in $ctrl.logic.recordTypes\">\r\n                <a href=\"\" ng-click=\"$ctrl.current.record.recordType = recordType\" class=\"dropdown-item\">{{recordType}}</a>\r\n              </li>\r\n              <li ng-if=\"!$ctrl.logic.recordTypes\">\r\n                <a href=\"\" class=\"dropdown-item disabled\" style=\"font-style: italic;\">\r\n                  {{ 'SALAXY.NG1.WorkerDetailsComponent.records.noTypes' | sxyTranslate }}\r\n                </a>\r\n              </li>\r\n            </ul>\r\n          </div>\r\n        </div>\r\n      </salaxy-form-group>\r\n      <salaxy-input ng-if=\"$ctrl.logic.readOnly\" ng-model=\"$ctrl.current.record.recordType\" label=\"SALAXY.NG1.WorkerDetailsComponent.records.recordType\" name=\"recordType\"></salaxy-input>\r\n      <salaxy-input ng-model=\"$ctrl.current.record.title\" label=\"SALAXY.NG1.WorkerDetailsComponent.records.title\" name=\"title\"></salaxy-input>\r\n      <salaxy-textarea ng-if=\"!('markdown' | sxyIsInRole)\" ng-model=\"$ctrl.current.record.text\" label=\"SALAXY.NG1.WorkerDetailsComponent.records.text\" name=\"text\"></salaxy-textarea>\r\n      <salaxy-input-markdown ng-if=\"('markdown' | sxyIsInRole)\" ng-model=\"$ctrl.current.record.text\" label=\"SALAXY.NG1.WorkerDetailsComponent.records.text\" name=\"text\" label-type=\"plain\"></salaxy-input-markdown>\r\n      <salaxy-form-group name=\"attachments\" label=\"SALAXY.NG1.WorkerDetailsComponent.records.attachments\">\r\n        <table>\r\n          <tr ng-repeat=\"attachment in $ctrl.current.record.attachments\">\r\n            <td><i class=\"bi {{ $ctrl.logic.getAttachmentIcon(attachment) }} text-primary float-start me-1\"></i> <a target=\"_blank\"\r\n                ng-href=\"{{$ctrl.logic.getAttachmentDownloadUrl(attachment)}}\">{{attachment.fileName}}</a></td>\r\n            <td class=\"text-end\">\r\n              <button type=\"button\" class=\"btn btn-danger btn-xs\" ng-if=\"!$ctrl.logic.readOnly\" ng-click=\"$ctrl.current.record.attachments.splice($index, 1)\"><i class=\"bi bi-trash\"\r\n                  title=\"{{'SALAXY.UI_Terms.removeAttachment' | sxyTranslate}}\"></i></button>\r\n            </td>\r\n          </tr>\r\n          <tr>\r\n            <td></td>\r\n            <td class=\"text-end\">\r\n              <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-if=\"!$ctrl.logic.readOnly\" ngf-select=\"$ctrl.logic.uploadAttachments($files, $ctrl.current.record.attachments)\"\r\n                ngf-multiple=\"true\" ngf-max-size=\"10MB\"><i class=\"bi bi-paperclip\" title=\"{{'SALAXY.UI_Terms.addAttachment' | sxyTranslate}}\"></i></button>\r\n            </td>\r\n          </tr>\r\n        </table>\r\n      </salaxy-form-group>\r\n      <salaxy-datepicker-popup ng-model=\"$ctrl.current.record.startDate\" label=\"SALAXY.NG1.WorkerDetailsComponent.records.startDate\" name=\"startDate\"></salaxy-datepicker-popup>\r\n    </fieldset>\r\n    <fieldset>\r\n      <legend sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.records.badge\"></legend>\r\n      <div class=\"badge bg-danger\">\r\n        {{ 'SALAXY.NG1.WorkerDetailsComponent.records.badgeInfo' | sxyTranslate }}\r\n      </div>\r\n      <salaxy-input label=\"SALAXY.NG1.WorkFlowEventEditComponent.description\" name=\"message\" ng-model=\"$ctrl.current.wfEvent.message\"></salaxy-input>\r\n      <salaxy-input-enum type=\"select\" enum=\"BootstrapStyle\" label=\"SALAXY.NG1.WorkFlowEventEditComponent.ui\" name=\"ui\" require=\"$ctrl.current.wfEvent.message\" ng-model=\"$ctrl.current.wfEvent.ui\"></salaxy-input-enum>\r\n    </fieldset>\r\n  </form>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button type=\"reset\" ng-if=\"!$ctrl.logic.readOnly\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n  <button type=\"button\" ng-if=\"$ctrl.logic.readOnly\" class=\"btn btn-primary\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n  <button type=\"button\" ng-if=\"!$ctrl.logic.readOnly\" class=\"btn btn-primary\" ng-disabled=\"!record.$valid\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/report/AccountingReport.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.AccountingReportComponent.accountingReports\"></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n</div>\r\n<div class=\"modal-body\">\r\n  <salaxy-accounting-report-tools any-expanded=\"$reportRows.anyExpanded\" on-expand-change=\"$reportRows.expand(close)\" on-target-change=\"$ctrl.data.loadCurrent(targetId)\"  reader=\"$ctrl.data.reader\"></salaxy-accounting-report-tools>\r\n  <salaxy-accounting-report-rows ng-show=\"!$ctrl.data.isLoading\" ng-ref=\"$reportRows\" data=\"$ctrl.data.accountingData\"></salaxy-accounting-report-rows>\r\n  <salaxy-spinner ng-if=\"$ctrl.data.isLoading\" full-screen=\"false\" heading=\"SALAXY.UI_Terms.loading\" text=\"SALAXY.NG1.AccountingReportComponent.loadingReport\"></salaxy-spinner>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/report/SummaryReport.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.SummaryReportComponent.summaryReport\"></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n</div>\r\n<div class=\"modal-body \">\r\n  <salaxy-spinner ng-if=\"$ctrl.data.isLoading\" full-screen=\"false\" heading=\"SALAXY.UI_Terms.loading\" text=\"SALAXY.NG1.SummaryReportComponent.loadingReport\"></salaxy-spinner>\r\n  <salaxy-summary-report ng-if=\"!$ctrl.data.isLoading\" data=\"$ctrl.data.summaryReportData\"></salaxy-summary-report>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/report/WorkerSummaryReport.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.SummaryReportComponent.summaryReport\"></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n</div>\r\n<div class=\"modal-body\">\r\n  <salaxy-spinner ng-if=\"$ctrl.data.isLoading\" full-screen=\"false\" heading=\"SALAXY.UI_Terms.loading\" text=\"SALAXY.NG1.SummaryReportComponent.loadingReport\"></salaxy-spinner>\r\n  <salaxy-worker-summary-report ng-if=\"!$ctrl.data.isLoading\" data=\"$ctrl.data.workerSummaryReportData\"></salaxy-worker-summary-report>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/settings/AccountantSelection.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.AccountantSelectionComponent.heading\"></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n</div>\r\n\r\n<div class=\"modal-body\">\r\n  <div ng-if=\"!$ctrl.logic.selected\" class=\"row\">\r\n    <div class=\"col-12\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.AccountantSelectionComponent.accountantType\"></legend>\r\n        <salaxy-input-enum ng-model=\"$ctrl.logic.type\" type=\"radio\" name=\"logicType\" label=\"SALAXY.NG1.AccountantSelectionComponent.companyOrPerson\" options=\"{ \r\n                          company: ('SALAXY.NG1.AccountantSelectionComponent.companyEnum' | sxyTranslate),\r\n                          none: ('SALAXY.NG1.AccountantSelectionComponent.personEnum' | sxyTranslate)}\">\r\n        </salaxy-input-enum>\r\n      </fieldset>\r\n    </div>\r\n  </div>\r\n  <form name=\"personAccountantForm\" class=\"form-horizontal\">\r\n    <div ng-if=\"$ctrl.logic.type == 'none'\" class=\"row\">\r\n      <div class=\"col-12\">\r\n        <fieldset>\r\n          <salaxy-input name=\"firstName\" label=\"SALAXY.NG1.AccountantSelectionComponent.personAccountantForm.firstName\" ng-model=\"$ctrl.current.info.avatar.firstName\"></salaxy-input>\r\n          <salaxy-input name=\"lastName\" label=\"SALAXY.NG1.AccountantSelectionComponent.personAccountantForm.lastName\"  ng-model=\"$ctrl.current.info.avatar.lastName\"></salaxy-input>\r\n          <salaxy-input name=\"email\" label=\"SALAXY.NG1.AccountantSelectionComponent.personAccountantForm.email\"  sxy-email ng-model=\"$ctrl.current.info.email\"></salaxy-input>\r\n          <salaxy-input name=\"telephone\" label=\"SALAXY.NG1.AccountantSelectionComponent.personAccountantForm.telephone\"  sxy-mobile-phone ng-model=\"$ctrl.current.info.telephone\"></salaxy-input>\r\n        </fieldset>\r\n      </div>\r\n    </div>\r\n  </form>\r\n  <div ng-if=\"!$ctrl.logic.selected && $ctrl.logic.type == 'company'\" class=\"row\">\r\n    <div class=\"col-12\">\r\n      <legend sxy-text=\"SALAXY.NG1.AccountantSelectionComponent.searchAccountingFirm\"></legend>\r\n    </div>\r\n  </div>\r\n  <div ng-if=\"!$ctrl.logic.selected && $ctrl.logic.type == 'company'\" class=\"table-responsive\" style=\"max-height: calc(100vh - 200px)\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\" sxy-text=\"SALAXY.NG1.AccountantSelectionComponent.name\"></th>\r\n          <th sxy-text=\"SALAXY.NG1.AccountantSelectionComponent.officialId\"></th>\r\n          <th class=\"right\">\r\n            <form name=\"searchForm\">\r\n              <salaxy-form-group name=\"search\" label-type=\"plain\">\r\n                <div class=\"input-group\">\r\n                  <input class=\"form-control\" type=\"text\" autocomplete=\"off\" id=\"searchAccountant\" name=\"searchAccountant\" ng-model=\"$ctrl.logic.searchInput\" require=\"true\" ng-minlength=\"3\">\r\n                  <span class=\"input-group-btn\">\r\n                    <button type=\"submit\" ng-disabled=\"!searchForm.$valid\" class=\"btn btn-default\"\r\n                      ng-click=\"$ctrl.logic.search($ctrl.logic.searchInput)\"><span ng-show=\"$ctrl.logic.isLoading\"><i\r\n                          class=\"bi bi-arrow-repeat bi-spin\"></i></span><span ng-show=\"!$ctrl.logic.isLoading\"><i class=\"bi bi-search\"></i></span></button>\r\n                  </span>\r\n                </div>\r\n            </form>\r\n            </salaxy-form-group>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.logic.searchResult\">\r\n          <td class=\"td-avatar middle\">\r\n            <salaxy-avatar avatar=\"row.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"td-name  middle\">\r\n            <strong>{{row.avatar.displayName}}</strong><br />\r\n          </td>\r\n          <td class=\"td-name  middle\">\r\n            <strong>{{row.officialId}}</strong><br />\r\n          </td>\r\n          <td class=\"right middle\">\r\n            <button class=\"btn btn-sm btn-default\" type=\"button\" ng-click=\"$ctrl.logic.select($ctrl.current, row)\">\r\n              {{ 'SALAXY.UI_Terms.select' | sxyTranslate }}\r\n            </button>\r\n          </td>\r\n        </tr>\r\n        <tr ng-if=\"$ctrl.logic.searchResult.length == 0\">\r\n          <td colspan=\"4\" sxy-text=\"SALAXY.NG1.AccountantSelectionComponent.noSearchResult\"></td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <form name=\"companyAccountantForm\" class=\"form-horizontal\">\r\n    <div ng-if=\"$ctrl.logic.selected && $ctrl.logic.type == 'company'\">\r\n      <div class=\"container-fixed salaxy-component salaxy-accountant-info\">\r\n        <button ng-if=\"$ctrl.current.type != 'primaryPartner'\" class=\"btn btn-default float-end\" ng-click=\"$ctrl.logic.reset($ctrl.current)\" sxy-text=\"SALAXY.NG1.AccountantSelectionComponent.companyAccountantForm.search\"></button>\r\n        <div class=\"table\">\r\n          <table>\r\n            <tr class=\"border-0\">\r\n              <td>\r\n                <salaxy-avatar style=\"margin-right: 40px;\" class=\"avatar-xl\" avatar=\"$ctrl.current.info.avatar\"></salaxy-avatar>\r\n              </td>\r\n              <td ng-if=\"$ctrl.current.type != 'primaryPartner'\">\r\n                <p class=\"lead\" sxy-text=\"SALAXY.NG1.AccountantSelectionComponent.companyAccountantForm.notPrimaryPartner.lead\" ps=\".\"></p>\r\n\r\n                <div class=\"input-info\">\r\n                  <div class=\"input-info-icon\"><i class=\"bi bi-info-circle-fill text-default\"></i></div>\r\n                  <p ng-if=\"$ctrl.current.info.avatar.id\" class=\"input-info-text with-icon\" sxy-text=\"SALAXY.NG1.AccountantSelectionComponent.companyAccountantForm.notPrimaryPartner.partnerInfo\" ps=\".\"></p>\r\n                  <p ng-if=\"!$ctrl.current.info.avatar.id\" class=\"input-info-text with-icon\" sxy-text=\"SALAXY.NG1.AccountantSelectionComponent.companyAccountantForm.notPrimaryPartner.notPartnerInfo\" ps=\".\"></p>\r\n                </div>\r\n              </td>\r\n              <td ng-if=\"$ctrl.current.type == 'primaryPartner'\">\r\n                <p class=\"lead\" sxy-text=\"SALAXY.NG1.AccountantSelectionComponent.companyAccountantForm.primaryPartner.lead\" ps=\".\"></p>\r\n\r\n                <div class=\"input-info\">\r\n                  <div class=\"input-info-icon\"><i class=\"bi bi-info-circle-fill text-default\"></i></div>\r\n                  <p ng-if=\"$ctrl.current.info.avatar.id\" class=\"input-info-text with-icon\" sxy-text=\"SALAXY.NG1.AccountantSelectionComponent.companyAccountantForm.primaryPartner.partnerInfo\" ps=\".\"></p>\r\n                </div>\r\n              </td>\r\n            </tr>\r\n          </table>\r\n        </div>\r\n        <div class=\"table-responsive\">\r\n          <table class=\"table\">\r\n            <tr>\r\n              <th sxy-text=\"Nimi\" ps=\":\"></th>\r\n              <td>{{ $ctrl.current.info.avatar.displayName}}</td>\r\n            </tr>\r\n            <tr>\r\n              <th sxy-text=\"Y-tunnus\" ps=\":\"></th>\r\n              <td>{{ $ctrl.current.info.officialId}}</td>\r\n            </tr>\r\n            <tr ng-if=\"!$ctrl.current.info.avatar.id\">\r\n              <th sxy-text=\"SALAXY.NG1.AccountantSelectionComponent.companyAccountantForm.accountantPermissions\" ps=\":\"></th>\r\n              <td>\r\n                <salaxy-input-enum disabled=\"true\" ng-model=\"$ctrl.current.type\" type=\"radio\" name=\"partnerType\" label=\"\" label-type=\"plain\" options=\"{ \r\n                unlinkedPrimaryPartner: ('SALAXY.NG1.AccountantSelectionComponent.companyAccountantForm.unlinkedPrimaryPartnerEnum' | sxyTranslate),\r\n                unlinkedAccountingOnly: ('SALAXY.NG1.AccountantSelectionComponent.companyAccountantForm.unlinkedAccountingOnlyEnum' | sxyTranslate)}\">\r\n                </salaxy-input-enum>\r\n              </td>\r\n            </tr>\r\n            <tr ng-if=\"$ctrl.current.info.avatar.id\">\r\n              <th sxy-text=\"SALAXY.NG1.AccountantSelectionComponent.companyAccountantForm.accountantPermissions\" ps=\":\"></th>\r\n              <td>\r\n                <salaxy-input-enum  ng-if=\"$ctrl.current.type != 'primaryPartner'\" ng-model=\"$ctrl.current.type\" type=\"radio\" name=\"partnerType\" label=\"\" label-type=\"plain\" options=\"{ \r\n                pendingPrimaryPartner: ('SALAXY.NG1.AccountantSelectionComponent.companyAccountantForm.pendingPrimaryPartnerEnum' | sxyTranslate),\r\n                unlinkedAccountingOnly: ('SALAXY.NG1.AccountantSelectionComponent.companyAccountantForm.unlinkedAccountingOnlyEnum' | sxyTranslate)}\">\r\n                </salaxy-input-enum>\r\n                <salaxy-input-enum ng-if=\"$ctrl.current.type == 'primaryPartner'\" read-only=\"true\" ng-model=\"$ctrl.current.type\" type=\"radio\" name=\"partnerType\" label=\"\" label-type=\"plain\" options=\"{ \r\n                  primaryPartner: ('SALAXY.NG1.AccountantSelectionComponent.companyAccountantForm.primaryPartnerEnum' | sxyTranslate)}\">\r\n                </salaxy-input-enum>\r\n              </td>\r\n            </tr>\r\n            <tr>\r\n              <th sxy-text=\"SALAXY.NG1.AccountantSelectionComponent.personAccountantForm.email\" ps=\":\"></th>\r\n              <td>\r\n                <salaxy-input name=\"email\" label=\"\" label-type=\"plain\" sxy-email ng-model=\"$ctrl.current.info.email\"></salaxy-input>\r\n              </td>\r\n            </tr>\r\n            <tr>\r\n              <th sxy-text=\"SALAXY.NG1.AccountantSelectionComponent.personAccountantForm.telephone\" ps=\":\"></th>\r\n              <td>\r\n                <salaxy-input name=\"telephone\" label=\"\" label-type=\"plain\" sxy-mobile-phone ng-model=\"$ctrl.current.info.telephone\"></salaxy-input>\r\n              </td>\r\n            </tr>\r\n          </table>\r\n        </div>\r\n\r\n      </div>\r\n    </div>\r\n  </form>\r\n</div>\r\n\r\n<div class=\"modal-footer text-end\">\r\n  <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n  <button type=\"button\" ng-if=\"$ctrl.current.type != 'primaryPartner'\" class=\"btn btn-danger\" ng-click=\"$close('remove')\" sxy-text=\"SALAXY.UI_Terms.delete\"></button>\r\n  <button type=\"button\" ng-if=\"$ctrl.current.type == 'primaryPartner' && !$ctrl.logic.removalDisabled\" class=\"btn btn-danger\" ng-click=\"$close('removePrimaryPartner')\" sxy-text=\"SALAXY.NG1.AccountantSelectionComponent.companyAccountantForm.deletePrimaryPartner\"></button>\r\n  <button type=\"button\" ng-disabled=\"(!$ctrl.logic.selected && $ctrl.logic.type == 'company') || personAccountantForm.$invalid || companyAccountantForm.$invalid\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n</div>\r\n`);\n\n $templateCache.put(\"salaxy-components/modals/settings/BrandSelection.html\",`<form name=\"brandForm\" class=\"form-horizontal\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.BrandSelectionComponent.title\"></h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <div class=\"table-responsive\" style=\"max-height: calc(100vh - 300px)\">\r\n      <salaxy-odata-table \r\n        url=\"/v03/api/settings/brands\" \r\n        template-url=\"salaxy-components/odata/lists/BrandList.html\" \r\n        options=\"{ $filter: 'data/skin ne null and data/skin ne \\\\'\\\\'' }\"\r\n        selected-items=\"selectedItems\"\r\n        on-list-select=\"($ctrl.current.brand = value == true ? item : null);( selectedItems = value == true? [item ]: []);\">\r\n    </salaxy-odata-table>\r\n    </div>\r\n  </div>\r\n  <div class=\"modal-footer\">\r\n      <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$close('set-default')\" sxy-text=\"SALAXY.NG1.BrandSelectionComponent.useDefaultStyle\"></button>\r\n      <button type=\"submit\" class=\"btn btn-primary\" ng-disabled=\"!$ctrl.current.brand\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n  </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/settings/EntryCodes.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.EntryCodesComponent.title\"></h2>\r\n  <button type=\"button\" class=\"ms-auto btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n</div>\r\n<div class=\"modal-body\" id=\"modal-body\" ng-init=\"$ctrl.logic.currentItem = $ctrl.current\">\r\n  <form name=\"entryCodesForm\" class=\"form-horizontal\">\r\n    <div class=\"row\">\r\n      <div class=\"col-12\">\r\n        <salaxy-input-typeahead label=\"SALAXY.NG1.EntryCodesComponent.entryCodeGroupLabel\" name=\"EntryCodeGroup\" ng-model=\"$ctrl.current.entryCodeGroup\" options=\"$ctrl.logic.entryCodeGroups\" on-select-function=\"$ctrl.logic.onEntryCodeGroupChange\"></salaxy-input-typeahead>\r\n      </div>\r\n    </div>\r\n    <div class=\"row\">\r\n      <div class=\"col-12\">\r\n        <salaxy-input-typeahead label=\"SALAXY.NG1.EntryCodesComponent.incomeTypeLabel\" name=\"IncomeType\" disable-cache=\"true\" ng-model=\"$ctrl.current.entryCode\" options=\"$ctrl.logic.optionTypes\"></salaxy-input-typeahead>\r\n      </div>\r\n    </div>\r\n  </form>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button type=\"button\" class=\"btn btn-default float-end\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n  <button type=\"button\" class=\"btn btn-primary float-end\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/settings/Flags.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.additionalSelectionsHead\"></h2>\r\n  <button type=\"button\" class=\"ms-auto btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n</div>\r\n<div class=\"modal-body\" id=\"modal-body\">\r\n  <div class=\"table-responsive\" style=\"max-height: 40vh;\">\r\n    <table class=\"table table-sm\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\" sxy-text=\"SALAXY.NG1.FlagsComponent.flag\"></th>\r\n          <th class=\"text-right\">\r\n            <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-click=\"$ctrl.logic.addFlag($ctrl.current)\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"item in $ctrl.current.flags track by $index\">\r\n          <td><span class=\"badge\" ng-class=\"$ctrl.logic.getFlagText(item).found ? 'bg-success' : 'bg-warning'\">{{$ctrl.logic.getFlagText(item).text}}</span></td>\r\n          <td>\r\n            <salaxy-input ng-model=\"$ctrl.current.flags[$index]\" name=\"{{ 'flag' + $index }}\" label-type=\"plain\"  ></salaxy-input>\r\n          </td>\r\n          <td class=\"text-right\">\r\n            <button type=\"button\" class=\"btn btn-danger btn-xs\" ng-click=\"$ctrl.current.flags.splice($index,1)\" title=\"{{'SALAXY.UI_Terms.deleteRow' | sxyTranslate}}\"><i class=\"bi bi-trash-fill\"></i></button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button type=\"button\" class=\"btn btn-default float-end\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n  <button type=\"button\" class=\"btn btn-primary float-end\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/settings/FlagSelection.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.FlagsComponent.title\"></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n</div>\r\n<div class=\"modal-body\" id=\"modal-body\">\r\n  <form name=\"FlagForm\" class=\"form-horizontal\">\r\n    <div class=\"row\">\r\n      <div class=\"col-xs-12\">\r\n        <salaxy-input-enum require=\"true\" label=\"SALAXY.NG1.FlagsComponent.prefix\" name=\"Prefix\" ng-model=\"$ctrl.current.prefix\" options=\"$ctrl.logic.prefixOptions\" type=\"radio\"></salaxy-input-enum>\r\n      </div>\r\n    </div>\r\n    <div class=\"row\">\r\n      <div class=\"col-xs-12\" ng-switch=\"$ctrl.current.prefix\">\r\n        <salaxy-input-enum require=\"true\" ng-switch-when=\"employmentType\" label=\"SALAXY.NG1.EmploymentRelation.employmentRelation\"  name=\"EmploymentType\" ng-model=\"$ctrl.current.value\" enum=\"EmploymentRelationType\" type=\"select\"></salaxy-input-enum>\r\n        <salaxy-input-enum require=\"true\" ng-switch-when=\"pensionCalculation\" label=\"SALAXY.NG1.WorkerWizardComponent.employment.pension.title\"  name=\"PensionCalculation\" ng-model=\"$ctrl.current.value\" options=\"$ctrl.logic.pensionCalculation\" type=\"select\"></salaxy-input-enum>\r\n        <salaxy-calc-row-type ng-switch-when=\"rowType\" label=\"SALAXY.NG1.CalcRowTypeComponent.rowType\"  name=\"rowType\" model=\"$ctrl.logic.asUserDefinedRow($ctrl.current)\" ></salaxy-calc-row-type>\r\n        <salaxy-calc-row-type ng-switch-when=\"type\" label=\"SALAXY.NG1.CalcRowTypeComponent.wageType\"  name=\"type\" model=\"$ctrl.logic.asUserDefinedRow($ctrl.current)\" ></salaxy-calc-row-type>\r\n        <salaxy-input-enum require=\"true\" ng-switch-when=\"dimension\" label=\"SALAXY.MODEL.CostAccountingSettings.title\"  name=\"Dimension\" ng-model=\"$ctrl.current.value\" options=\"$ctrl.logic.dimension\" type=\"select\"></salaxy-input-enum>\r\n        <salaxy-input require=\"true\" ng-switch-when=\"dimension\" label=\"SALAXY.MODEL.CostAccountingDimensionOption.value.title\"  name=\"dimensionValue\" ng-model=\"$ctrl.current.dimensionValue\"></salaxy-input>\r\n        <salaxy-input-enum require=\"true\" ng-switch-when=\"selfPayment\" label=\"SelfPayment\"  name=\"SelfPayment\" ng-model=\"$ctrl.current.value\" options=\"$ctrl.logic.selfPayment\" type=\"select\"></salaxy-input-enum>\r\n        <salaxy-input-enum require=\"true\" ng-switch-when=\"behavior\" label=\"Behavior\"  name=\"Behavior\" ng-model=\"$ctrl.current.value\" enum=\"CalculationFlag\" type=\"select\"></salaxy-input-enum>\r\n        <salaxy-input require=\"true\" ng-switch-when=\"regex\" label=\"Regex\"  name=\"regex\" ng-model=\"$ctrl.current.value\"></salaxy-input>\r\n      </div>\r\n    </div>\r\n  </form>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button type=\"button\" class=\"btn btn-default float-end\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n  <button type=\"button\" class=\"btn btn-primary float-end\" ng-disabled=\"!FlagForm.$valid || ( ($ctrl.current.prefix == 'rowType' || $ctrl.current.prefix == 'type' )  && !$ctrl.current.value)\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/settings/PaymentChannel.html\",`<form name=\"periodForm\" class=\"form-horizontal\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{ $ctrl.logic.channelAvatar.displayName }}, asetukset</h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <div class=\"form-horizontal\">\r\n      <p class=\"lead\">\r\n        <strong>{{ $ctrl.logic.channelAvatar.displayName }}</strong>: {{ $ctrl.logic.channelAvatar.description }}\r\n      </p>\r\n      <div ng-switch=\"$ctrl.current.id\">\r\n        <fieldset ng-switch-when=\"palkkausCfaFinvoice|palkkausEcfaFinvoice\"  ng-switch-when-separator=\"|\">\r\n          <legend sxy-text=\"SALAXY.NG1.PaymentChannelDialogComponent.palkkausCfaFinvoice.legend\"></legend>\r\n          <salaxy-form-group name=\"eInvoiceReceiver\" label=\"SALAXY.NG1.PaymentChannelDialogComponent.palkkausCfaFinvoice.eInvoiceAddress\">\r\n            <div class=\"input-group\">\r\n              <input class=\"form-control\" type=\"text\" autocomplete=\"off\" id=\"eInvoiceReceiver\" name=\"eInvoiceReceiver\" ng-disabled=\"true\" ng-model=\"$ctrl.current.invoiceSettings.eInvoiceReceiver\">\r\n              <span class=\"input-group-btn\">\r\n                <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.logic.selectEInvoiceAddress($ctrl.current.invoiceSettings)\" sxy-text=\"SALAXY.UI_Terms.choose\"></button>\r\n              </span>\r\n            </div>\r\n          </salaxy-form-group>\r\n          <salaxy-input disabled=\"true\" name=\"intermediator\" ng-model=\"$ctrl.current.invoiceSettings.eInvoiceIntermediator\" label=\"SALAXY.NG1.PaymentChannelDialogComponent.palkkausCfaFinvoice.intermediator\"></salaxy-input>\r\n        </fieldset>\r\n        <fieldset ng-switch-when=\"palkkausCfaPaytrail|palkkausEcfaPaytrail|palkkausCfaReference|palkkausEcfaReference|palkkausCfaFinvoice|palkkausEcfaFinvoice|palkkausCfaTest\" ng-switch-when-separator=\"|\">\r\n          <fieldset>\r\n            <legend sxy-text=\"SALAXY.NG1.PaymentChannelDialogComponent.palkkausCfaPaytrail.legend\"></legend>\r\n            <p sxy-text=\"SALAXY.NG1.PaymentChannelDialogComponent.palkkausCfaPaytrail.infoText\"></p>\r\n            <salaxy-input-boolean type=\"checkbox\" name=\"isTaxAndSocialSecuritySelfHandling\" label-type=\"plain\" label-true=\"SALAXY.NG1.PaymentChannelDialogComponent.palkkausCfaPaytrail.isTaxAndSocialSecuritySelfHandling\" ng-model=\"$ctrl.current.customerFundsSettings.isTaxAndSocialSecuritySelfHandling\"></salaxy-input-boolean>\r\n            <salaxy-input-boolean type=\"checkbox\" name=\"isWorkerSelfHandling\" label-type=\"plain\" label-true=\"SALAXY.NG1.PaymentChannelDialogComponent.palkkausCfaPaytrail.isWorkerSelfHandling\" ng-model=\"$ctrl.current.customerFundsSettings.isWorkerSelfHandling\"></salaxy-input-boolean>\r\n            <div>&nbsp;</div>\r\n            <div class=\"alert alert-warning\" sxy-html=\"SALAXY.NG1.PaymentChannelDialogComponent.palkkausCfaPaytrail.alert.html\"></div>\r\n          </fieldset>\r\n        </fieldset>\r\n        <fieldset ng-switch-when=\"palkkausManual|talenomManual|hausvise|passeliMerit\" ng-switch-when-separator=\"|\">\r\n          <legend sxy-text=\"SALAXY.NG1.PaymentChannelDialogComponent.palkkausManual.legend\"></legend>\r\n          <salaxy-input label-cols=\"col-sm-6\" name=\"ibanNumber\" label=\"SALAXY.NG1.PaymentChannelDialogComponent.palkkausManual.ibanNumber\" sxy-iban ng-model=\"$ctrl.current.invoiceSettings.ibanNumber\"></salaxy-input>\r\n          <salaxy-input label-cols=\"col-sm-6\" name=\"sepaBankPartyId\" label=\"SALAXY.NG1.PaymentChannelDialogComponent.palkkausManual.sepaBankPartyId\" ng-model=\"$ctrl.current.invoiceSettings.sepaBankPartyId\"></salaxy-input>\r\n        </fieldset>\r\n        <!--fieldset ng-switch-when=\"palkkausInvoices\">\r\n          <legend sxy-text=\"SALAXY.NG1.PaymentChannelDialogComponent.palkkausInvoices.legend\"></legend>\r\n          <salaxy-input name=\"creditCard\" disabled=\"true\" label=\"SALAXY.NG1.PaymentChannelDialogComponent.palkkausInvoices.creditCard\" ng-model=\"dummy\"></salaxy-input     \r\n        </fieldset-->\r\n        <fieldset ng-switch-default>\r\n          <div class=\"alert alert-info\" sxy-text=\"SALAXY.NG1.PaymentChannelDialogComponent.default.info\"></div>\r\n        </fieldset>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div class=\"modal-footer d-flex\">\r\n    <button type=\"button\" ng-if=\"$ctrl.current.settings.isEnabled && $ctrl.current.settings.isAvailable\" class=\"btn btn-danger\" ng-disabled=\"$ctrl.current.isReadOnly\" ng-click=\"$close('delete')\" sxy-text=\"SALAXY.UI_Terms.unenable\"></button>\r\n    <button type=\"reset\" ng-click=\"$close('cancel')\" class=\"btn btn-default ms-auto\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n    <button type=\"button\" ng-if=\"!$ctrl.current.isDefault  && $ctrl.current.settings.isAvailable\" class=\"btn btn-default\" ng-disabled=\"$ctrl.current.isReadOnly && !$ctrl.current.settings.isEnabled\" ng-click=\"$close('set-default')\" sxy-text=\"SALAXY.UI_Terms.setDefault\"></button>\r\n    <button type=\"submit\" ng-if=\"$ctrl.current.settings.isEnabled  && $ctrl.current.settings.isAvailable\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n    <button type=\"button\" ng-if=\"!$ctrl.current.settings.isEnabled  && $ctrl.current.settings.isAvailable\" class=\"btn btn-primary\" ng-disabled=\"$ctrl.current.isReadOnly\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.enable\"></button>\r\n  </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/modals/settings/UiTranslator.html\",`\r\n<div class=\"modal-ui-translation\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{$ctrl.logic.title}}</h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <salaxy-ui-translator></salaxy-ui-translator>\r\n    <div>\r\n      <button type=\"submit\" class=\"btn btn-primary float-end\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n      <button type=\"reset\" class=\"btn btn-default float-end\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/templates/TemplateSelect.html\",`<div class=\"modal-template-list\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{$ctrl.logic.title | sxyTranslate}}</h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <div class=\"table-responsive\" style=\"max-height: calc(100vh - 300px)\">\r\n      <div class=\"salaxy-component\">\r\n        <salaxy-odata-table ng-ref=\"$templateList\" select-mode=\"'select'\" url=\"/v03/api/templates\"\r\n          options=\"$ctrl.logic.options\"\r\n          selected-items=\"$ctrl.current\"\r\n          template-url=\"salaxy-components/odata/lists/Templates-select.html\"\r\n          on-list-select=\"$templateList.selectedItems.splice(0, $templateList.selectedItems.length);(value == true ? $templateList.selectedItems.push(item) : null);\"\r\n          crud-controller=\"TemplateCrudController as $crud\"></salaxy-odata-table>\r\n      </div>\r\n    </div>\r\n    <div class=\"text-right\">\r\n      <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"{{ $ctrl.logic.cancelButtonText || 'SALAXY.UI_Terms.cancel'}}\"></button>\r\n      <button type=\"submit\" ng-disabled=\"$templateList.selectedItems.length != 1\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"{{ $ctrl.logic.okButtonText || 'SALAXY.UI_Terms.save'}}\"></button>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/ui/Alert.html\",`<div class=\"modal-header\">\r\n  <h3 class=\"modal-title\" id=\"modal-title\">{{$ctrl.data.heading | sxyTranslate}}</h3>\r\n</div>\r\n<div ng-if=\"$ctrl.data.text\" class=\"modal-body salaxy-component\" id=\"modal-body\">\r\n  <p class=\"pre-wrap\">{{$ctrl.data.text | sxyTranslate}}</p>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button class=\"btn btn-primary\" type=\"button\" ng-click=\"$close('ok')\">{{$ctrl.data.okText | sxyTranslate}}</button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/ui/Confirm.html\",`<div class=\"modal-header\">\r\n  <h3 class=\"modal-title\" id=\"modal-title\">{{$ctrl.data.heading | sxyTranslate}}</h3>\r\n</div>\r\n<div ng-if=\"$ctrl.data.text || $ctrl.data.html\" class=\"modal-body\" id=\"modal-body\">\r\n  <p ng-if=\"!$ctrl.data.html\" class=\"pre-wrap\">{{$ctrl.data.text | sxyTranslate}}</p>\r\n  <div ng-if=\"$ctrl.data.html\" sxy-html=\"{{$ctrl.data.html}}\"></div>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button class=\"btn btn-default\" type=\"button\" ng-click=\"$close(false)\">{{$ctrl.data.cancelText | sxyTranslate}}</button>\r\n  <button class=\"btn btn-primary\" type=\"button\" ng-click=\"$close(true)\">{{$ctrl.data.okText | sxyTranslate}}</button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/ui/DialogWindow.html\",`<div id=\"salaxyDialog\" class=\"salaxy-component salaxy-dialog modal-dialog {{size ? 'modal-' + size : ''}}\" aria-labelledby=\"salaxyDialogLabel\" role=\"dialog\">\r\n        <div class=\"modal-content\" role=\"document\" uib-modal-transclude></div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/ui/DocumentPreviewWindow.html\",`<div class=\"salaxy-component container-document-print salaxy-rpt\" role=\"dialog\">\r\n    <div class=\"document-preview\" id=\"document-preview\">\r\n        <div style=\"height:auto;min-height:277mm\" class=\"modal-content document a4portrait\" role=\"document\" uib-modal-transclude></div>\r\n    </div>\r\n</div>\r\n`);\n\n $templateCache.put(\"salaxy-components/modals/ui/Download.html\",`<div class=\"modal-body\" id=\"modal-body\">\r\n  <div class=\"sxy-spinner\" ng-if=\"!$ctrl.data.isReady\">\r\n      <svg class=\"sxy-spinner-bg\" viewBox=\"0 0 64 64\"><circle cx=\"32\" cy=\"32\" r=\"26\"></circle></svg>\r\n      <svg class=\"sxy-spinner-spin\" viewBox=\"0 0 64 64\">\r\n          <circle transform=\"translate(32,32)\" r=\"26\"></circle>\r\n      </svg>\r\n  </div>\r\n  \r\n  <div style=\"text-align: center;\">\r\n      <h3 ng-if=\"!$ctrl.data.isReady\" >{{$ctrl.data.waitHeading | sxyTranslate}}</h3>\r\n      <h3 ng-if=\"$ctrl.data.isReady\" >{{$ctrl.data.readyHeading | sxyTranslate}}</h3>\r\n      <p  ng-if=\"!$ctrl.data.isReady\" style=\"white-space: pre;\">{{$ctrl.data.waitText | sxyTranslate}}</p>\r\n      <p ng-if=\"$ctrl.data.isReady\">\r\n        {{$ctrl.data.readyText | sxyTranslate}} \r\n        <a ng-if=\"$ctrl.data.target\" ng-click=\"$close('ok')\" ng-href=\"{{$ctrl.data.url}}\" target=\"{{$ctrl.data.target}}\" >{{$ctrl.data.openText | sxyTranslate}}</a>\r\n        <a ng-if=\"!$ctrl.data.target\" ng-click=\"$close('ok')\" ng-href=\"{{$ctrl.data.url}}\" >{{$ctrl.data.openText | sxyTranslate}}</a>\r\n      </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/ui/Html.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\">{{$ctrl.data.title}}</h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n</div>\r\n<div class=\"modal-body \">\r\n  <div ng-bind-html=\"$ctrl.data.html\"></div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/ui/Loading.html\",`<div class=\"modal-body\" id=\"modal-body\" style=\"text-align:center;\">\r\n  <div class=\"sxy-spinner\">\r\n    <svg class=\"sxy-spinner-bg\" viewBox=\"0 0 64 64\"><circle cx=\"32\" cy=\"32\" r=\"26\"></circle></svg>\r\n    <svg class=\"sxy-spinner-spin\" viewBox=\"0 0 64 64\">\r\n            <circle transform=\"translate(32,32)\" r=\"26\"></circle>\r\n        </svg>\r\n  </div>\r\n  <div style=\"text-align: center;\">\r\n    <h3 ng-if=\"$ctrl.data.heading\">{{$ctrl.data.heading | sxyTranslate}}</h3>\r\n    <p class=\"pre-wrap\" ng-if=\"$ctrl.data.text\">{{$ctrl.data.text | sxyTranslate}}</p>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/ui/SelectListItem.html\",`<div class=\"modal-worker-list\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{$ctrl.logic.title | sxyTranslate}}</h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <p ng-if=\"$ctrl.logic.infoHtml\" sxy-html=\"{{$ctrl.logic.infoHtml}}\"></p>\r\n    <div class=\"table-responsive\" style=\"max-height: calc(100vh - 300px)\">\r\n      <salaxy-odata-table\r\n        template-url=\"salaxy-components/odata/lists/SelectListItem.html\"\r\n        selected-items=\"$ctrl.current\" on-list-select=\"$close('ok')\"\r\n        crud-controller=\"DatasetsCrudController as $crud\"></salaxy-odata-table>\r\n    </div>\r\n    <div class=\"text-end\">\r\n      <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n      <button type=\"submit\" class=\"btn btn-primary\" ng-click=\"$close('ok')\">{{$ctrl.logic.okButtonText ? ($ctrl.logic.okButtonText | sxyTranslate) : ('SALAXY.UI_Terms.save' |\r\n        sxyTranslate)}}</button>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/worker/taxcard-income-log.html\",`<div class=\"modal-taxcard-new\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.EmploymentTaxcardsComponent.taxCardIncomeLog.addPaidSalaries\"></h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <div class=\"alert alert-info\" ng-if=\"$ctrl.$incomeLog.hasDiff\">\r\n      <button type=\"button\" class=\"btn btn-primary float-end\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.NG1.EmploymentTaxcardsComponent.taxCardIncomeLog.addSalaries\"></button>\r\n      <span sxy-text=\"SALAXY.NG1.EmploymentTaxcardsComponent.taxCardIncomeLog.addSalariesToTaxCard\" params=\"{validity: ($ctrl.current.card.validity | sxyDateRange)}\">\r\n      </span>\r\n    </div>\r\n    <salaxy-taxcard-income-log parent=\"$ctrl.current\" editable=\"$ctrl.logic.editable\" ng-ref=\"$ctrl.$incomeLog\"></salaxy-taxcard-income-log>\r\n  </div>\r\n  <div class=\"modal-footer\">\r\n    <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n    <button type=\"submit\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.NG1.EmploymentTaxcardsComponent.taxCardIncomeLog.addSalaries\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/worker/taxcard-min-percent.html\",`<div class=\"modal-taxcard-min-percent\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.EmploymentTaxcardsComponent.taxCardMinPercent.minimumPercent\"></h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n  </div>\r\n  <div class=\"modal-body form-horizontal\">\r\n    <p class=\"lead\" sxy-html=\"SALAXY.NG1.EmploymentTaxcardsComponent.taxCardMinPercent.lead.html\"></p>\r\n    <p sxy-text=\"SALAXY.NG1.EmploymentTaxcardsComponent.taxCardMinPercent.biggerTaxPercentThanInTaxCard\"></p>\r\n    <p sxy-text=\"SALAXY.NG1.EmploymentTaxcardsComponent.taxCardMinPercent.taxPercentMinimum\"></p>\r\n    <salaxy-input-number name=\"taxPercentMin\" ng-model=\"$ctrl.current.taxPercentMin\" label=\"SALAXY.NG1.EmploymentTaxcardsComponent.taxCardMinPercent.minimumPercent\"></salaxy-input-number>\r\n  </div>\r\n  <div class=\"modal-footer\">\r\n    <button class=\"btn btn-default\" type=\"button\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n    <button class=\"btn btn-primary\" type=\"button\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/worker/taxcard-new.html\",`<div class=\"modal-taxcard-new\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.EmploymentTaxcardsComponent.taxCardNew.addTaxCard\"></h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n  </div>\r\n  <div style=\"min-height: 440px;\" class=\"modal-body\">\r\n    <salaxy-taxcard-manual-edit ng-ref=\"$edit\" current=\"$ctrl.current\"></salaxy-taxcard-manual-edit>\r\n  </div>\r\n  <div class=\"modal-footer\">\r\n    <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.NG1.AbsencePeriodsEditDialog.cancelButtonText\"></button>\r\n    <button type=\"submit\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" ng-disabled=\"!$edit.isFormValid\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/workflow/UsecaseInfo.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\">\r\n    <i ng-if=\"$ctrl.current.icon[0] == 'f'\" class=\"bi\" ng-class=\"$ctrl.current.icon\" aria-hidden=\"true\" style=\"padding-right: 20px\"></i>\r\n    Käyttötapaus: {{ $ctrl.current.label || $ctrl.logic.objUsecase.label || \"Ei käyttötapausta\" }}\r\n  </h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$dismiss()\" aria-label=\"Close\"></button>\r\n\r\n</div>\r\n<div class=\"modal-body\">\r\n  <p class=\"lead\">{{ $ctrl.current.description || $ctrl.logic.objUsecase.description }}</p>\r\n  <p><code>{{ $ctrl.logic.objUsecase.uri }}</code></p>\r\n  <div class=\"alert alert-danger\" ng-if=\"!$ctrl.current\">\r\n    <strong>Ei käyttötapausta!</strong>\r\n    Tällä tietuella ei ole määritettyä käyttötapausta.\r\n  </div>\r\n  <div ng-if=\"$ctrl.current\">\r\n    <div class=\"row\">\r\n      <div class=\"col-sm-6\">\r\n        <fieldset>\r\n          <legend>Käyttötapaus</legend>\r\n          <div ng-if=\"!$ctrl.current.defaultView\">Ei räätälöityä näkymää.</div>\r\n          <div ng-if=\"$ctrl.current.defaultView\">\r\n            <p>Näkymät (<a href=\"{{ $ctrl.current.defaultView }}\" target=\"_blank\">linkki oletusnäkymään</a>)</p>\r\n            <ul>\r\n              <li ng-repeat=\"view in $ctrl.current.views\">\r\n                <strong>{{ view.label }}</strong> {{ view.description }}\r\n              </li>\r\n            </ul>\r\n          </div>\r\n          <!-- TODO: Show actions, schemas and workflowData / flow if necessary. -->\r\n        </fieldset>\r\n      </div>\r\n      <div class=\"col-sm-6\">\r\n        <fieldset>\r\n          <legend>Objektiin tallennettu data</legend>\r\n          <salaxy-json-formatter json=\"$ctrl.logic.objUsecase.data\" key=\"'JSON'\"></salaxy-json-formatter>\r\n        </fieldset>\r\n      </div>\r\n    </div>\r\n    <salaxy-json-formatter json=\"$ctrl.current\" key=\"'JSON'\" open=\"0\"></salaxy-json-formatter>\r\n  </div>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button class=\"btn btn-danger float-start\" ng-if=\"$ctrl.logic.canDelete\" ng-click=\"$close('delete')\" sxy-text=\"SALAXY.UI_Terms.delete\"></button>\r\n  <button class=\"btn btn-default ms-auto\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.ok\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/workflow/WorkflowBadgeDetails.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" id=\"salaxyWorkflowBadgeDetailsTitle\" sxy-text=\"{{'SALAXY.ENUM.BootstrapStyle.' + $ctrl.current.event.ui + '.label' }}\"></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$dismiss()\" aria-label=\"Close\"></button>\r\n</div>\r\n<div class=\"modal-body\">\r\n\r\n  <form class=\"form-horizontal\" name=\"eventAndRecord\" ng-readonly=\"true\">\r\n    <salaxy-form-group name=\"time\" label=\"SALAXY.UI_Terms.updated\">\r\n      <span>{{$ctrl.current.event.time | sxyTime }}</span>\r\n    </salaxy-form-group>\r\n    <salaxy-input-enum type=\"select\" enum=\"BootstrapStyle\" label=\"SALAXY.NG1.WorkFlowEventEditComponent.ui\" name=\"ui\" ng-model=\"$ctrl.current.event.ui\"></salaxy-input-enum>\r\n    <salaxy-input label=\"SALAXY.NG1.WorkFlowEventEditComponent.description\" name=\"message\" require=\"true\" ng-model=\"$ctrl.current.event.message\"></salaxy-input>\r\n    <div ng-if=\"$ctrl.current.record\">\r\n      <salaxy-input ng-if=\"$ctrl.current.record.recordType\" ng-model=\"$ctrl.current.record.recordType\" label=\"SALAXY.NG1.WorkerDetailsComponent.records.recordType\" name=\"recordType\"></salaxy-input>\r\n      <salaxy-input ng-if=\"$ctrl.current.record.title\" ng-model=\"$ctrl.current.record.title\" label=\"SALAXY.NG1.WorkerDetailsComponent.records.title\" name=\"title\"></salaxy-input>\r\n      <salaxy-textarea ng-if=\"$ctrl.current.record.text && !('markdown' | sxyIsInRole)\" ng-model=\"$ctrl.current.record.text\" label=\"SALAXY.NG1.WorkerDetailsComponent.records.text\" name=\"text\"></salaxy-textarea>\r\n      <salaxy-input-markdown ng-if=\"$ctrl.current.record.text && ('markdown' | sxyIsInRole)\" ng-model=\"$ctrl.current.record.text\" label=\"SALAXY.NG1.WorkerDetailsComponent.records.text\" name=\"text\" label-type=\"plain\"></salaxy-input-markdown>\r\n      <salaxy-form-group ng-if=\"$ctrl.current.record.attachments.length > 0\" name=\"attachments\" label=\"SALAXY.NG1.WorkerDetailsComponent.records.attachments\">\r\n        <table>\r\n          <tr ng-repeat=\"attachment in $ctrl.current.record.attachments\">\r\n            <td>\r\n              <i class=\"bi {{ $ctrl.logic.getAttachmentIcon(attachment) }} text-primary float-start me-1\"></i>\r\n              <a target=\"_blank\" ng-href=\"{{$ctrl.logic.getAttachmentDownloadUrl(attachment)}}\">{{attachment.fileName}}</a>\r\n            </td>\r\n          </tr>\r\n        </table>\r\n      </salaxy-form-group>\r\n      <salaxy-datepicker-popup ng-if=\"$ctrl.current.record.startDate\" ng-model=\"$ctrl.current.record.startDate\" label=\"SALAXY.NG1.WorkerDetailsComponent.records.startDate\" name=\"startDate\"></salaxy-datepicker-popup>\r\n    </div>\r\n  </form>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/modals/workflow/WorkflowEventEdit.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" id=\"salaxyWorkflowEventEditTitle\" sxy-text=\"{{$ctrl.logic.title}}\"></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$dismiss()\" aria-label=\"Close\"></button>\r\n\r\n</div>\r\n<div class=\"modal-body\">\r\n  <form name=\"event\" class=\"form-horizontal\" ng-readonly=\"$ctrl.logic.readOnly\">\r\n    <salaxy-input label=\"SALAXY.NG1.WorkFlowEventEditComponent.description\" name=\"message\" require=\"true\" ng-model=\"$ctrl.current.message\"></salaxy-input>\r\n    <salaxy-input-enum ng-if=\"$ctrl.logic.showUi\" type=\"select\" enum=\"BootstrapStyle\" label=\"SALAXY.NG1.WorkFlowEventEditComponent.ui\" name=\"ui\" require=\"true\" ng-model=\"$ctrl.current.ui\"></salaxy-input-enum>\r\n  </form>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button type=\"reset\" ng-if=\"!$ctrl.logic.readOnly\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n  <button type=\"button\" ng-if=\"$ctrl.logic.readOnly\" class=\"btn btn-primary\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n  <button type=\"button\" ng-if=\"!$ctrl.logic.readOnly\" class=\"btn btn-primary\" ng-disabled=\"!event.$valid\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n</div>\r\n`);\n\n $templateCache.put(\"salaxy-components/odata/lists/AbsencePeriods.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <!-- TODO: This list is currenlty not in use - may be taken to use (or remove Q1/2020) -->\r\n  <table class=\"table\">\r\n    <thead>\r\n      <tr>\r\n        <th colspan=\"2\" sxy-orderby=\"otherPartyInfo/avatar/displayName\">\r\n          <span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span>\r\n        </th>\r\n        <th sxy-orderby=\"causeCode\">{{ \"SALAXY.NG1.AbsencePeriodsComponent.headerAbsence\" | sxyTranslate }}</th>\r\n        <th sxy-orderby=\"period/start\" class=\"right\" sxy-text=\"SALAXY.NG1.AbsencePeriodsComponent.wholeAbsence\"></th>\r\n        <th sxy-orderby=\"period/daysCount\" class=\"right\" sxy-html=\"SALAXY.NG1.AbsencePeriodsComponent.periodDaysCount.html\"></th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat=\"row in $ctrl.items\">\r\n        <td class=\"align-middle td-avatar\">\r\n          <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n        </td>\r\n        <td class=\"td-name middle\">\r\n          <strong>{{ row.otherPartyInfo.avatar.displayName }}</strong><br /> {{ row.worker.description }}\r\n        </td>\r\n        <td>\r\n          <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" avatar=\"{ color: '#2b507c', initials: (row.period.daysCount + 'pv'), entityType: 'company' }\"></salaxy-avatar>\r\n          <strong>{{ \"AbsenceCauseCode.\" + row.causeCode | sxyEnum }}</strong><br />\r\n          <div class=\"float-start\" style=\"padding: 0px;\">\r\n            {{ row.isPaid ? ('SALAXY.NG1.AbsencePeriodsComponent.isPaid' | sxyTranslate) : ('SALAXY.NG1.AbsencePeriodsComponent.notPaid' | sxyTranslate) }}\r\n            <span ng-if=\"row.isPaid != row.isHolidayAccrual\"> {{ row.isHolidayAccrual ? ('SALAXY.NG1.AbsencePeriodsComponent.isAccrual' | sxyTranslate) : ('SALAXY.NG1.AbsencePeriodsComponent.notAccrual' | sxyTranslate) }}</span>\r\n          </div>\r\n          <div class=\"truncate\" style=\"max-width: 250px; padding: 0px;\">\r\n            &nbsp;{{ row.notes }}\r\n          </div>\r\n        </td>\r\n        <td class=\"right\">\r\n          <strong>{{ row.period.daysCount | sxyCount : \"day\" }}</strong><br /> {{ row.period.start | date : 'dd.MM.' }}-{{ row.period.end | date : 'dd.MM.' }}\r\n        </td>\r\n        <td class=\"right\">\r\n          <strong>{{ (row.isPaid ? 0 : row.period.daysCount) | sxyCount : \"day\" }}</strong><br />\r\n          <strong>{{ (row.isHolidayAccrual ? 0 : row.period.daysCount) | sxyCount : \"day\" }}</strong><br />\r\n        </td>\r\n        <td class=\"hidden-xxs middle\">\r\n          <button ng-click=\"$ctrl.data.$payrollCtrl.showEditWorkerDialog(row.worker.id, 'absences')\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-primary btn-block\">\r\n            <i class=\"bi bi-pencil-fill d-inline d-sm-none\"></i>\r\n            <span class=\"d-none d-sm-inline\" sxy-text=\"SALAXY.UI_Terms.edit\"></span>\r\n          </button>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/Absences.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <table class=\"table\">\r\n    <thead>\r\n      <tr>\r\n        <th colspan=\"2\" sxy-orderby=\"otherPartyInfo/avatar/displayName\">\r\n          <span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span>\r\n        </th>\r\n        <th class=\"right\">\r\n          <span sxy-orderby=\"startAt\" sxy-text=\"SALAXY.NG1.AbsencesComponent.first\"></span><br />\r\n          <span sxy-orderby=\"endAt\" sxy-text=\"SALAXY.NG1.AbsencesComponent.first\">Viimeisin</span>\r\n        </th>\r\n        <th class=\"right\" sxy-text=\"SALAXY.NG1.AbsencesComponent.salaried\"></th>\r\n        <th class=\"right\" sxy-text=\"SALAXY.NG1.AbsencesComponent.unpaid\">Palkattomat</th>\r\n        <th>\r\n          <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\"></salaxy-input>\r\n        </th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat=\"row in $ctrl.items\">\r\n        <td class=\"align-middle td-avatar\">\r\n          <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n        </td>\r\n        <td class=\"td-name middle\">\r\n          <strong>{{ row.otherPartyInfo.avatar.displayName }}</strong><br /> {{ row.data.count }} {{'SALAXY.NG1.AbsencesComponent.absence' | sxyTranslate}}, {{ row.data.days }} {{'SALAXY.NG1.AbsencesComponent.day' | sxyTranslate}}<br />\r\n          <span ng-if=\"!row.data.employmentId\" class=\"label label-danger\" sxy-text=\"SALAXY.NG1.AbsencesComponent.error\"></span>\r\n        </td>\r\n        <td class=\"right\">\r\n          {{ row.startAt | sxyDate }}<br /> {{ row.endAt | sxyDate }}\r\n        </td>\r\n        <td class=\"right\">\r\n          {{ row.data.paidCount }} {{'SALAXY.NG1.AbsencesComponent.pce' | sxyTranslate}}<br /> {{ row.data.paidDays }} {{'SALAXY.NG1.AbsencesComponent.d' | sxyTranslate}}\r\n        </td>\r\n        <td class=\"right\">\r\n          {{ row.data.unpaidCount }} {{'SALAXY.NG1.AbsencesComponent.pce' | sxyTranslate}}<br /> {{ row.data.unpaidDays }} {{'SALAXY.NG1.AbsencesComponent.d' | sxyTranslate}}\r\n        </td>\r\n        <td class=\"hidden-xxs middle\">\r\n          <button ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-primary btn-block\">\r\n            <i class=\"bi bi-pencil-fill d-sm-none d-inline\"></i>\r\n            <span class=\"d-none d-sm-inline\" sxy-text=\"SALAXY.UI_Terms.edit\"></span>\r\n          </button>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/AccountingReports.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n\r\n  <salaxy-accounting-report-tools ng-ref=\"$reportTools\" reader=\"$crud.selectionDataReader\"></salaxy-accounting-report-tools>\r\n\r\n  <div class=\"visible-xxs\">\r\n    <div class=\"table-filter-container-mobile\">\r\n      <salaxy-datepicker-popup name=\"year\" placeholder=\"{{'SALAXY.NG1.AccountingReportsComponent.year'}}\" ng-change=\"$crud.logicalDateChanged()\" format=\"year\" ng-model=\"$crud.logicalDate\" label-type=\"plain\" require=\"true\"></salaxy-datepicker-popup>\r\n    </div>\r\n  </div>\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\" sxy-orderby=\"ownerInfo/avatar/displayName\">\r\n            <span>{{ 'SALAXY.NG1_Other.Roles.employer' | sxyTranslate }}</span>\r\n          </th>\r\n          <th>\r\n            <span sxy-orderby=\"logicalDate\">{{ 'SALAXY.NG1.AccountingReportsComponent.period' | sxyTranslate }}</span>\r\n          </th>\r\n          <th class=\"right \">\r\n            <span sxy-orderby=\"grossSalary\">{{ 'SALAXY.NG1.AccountingReportsComponent.salaries' | sxyTranslate }}</span><br />\r\n            <span sxy-orderby=\"payment\">{{ 'SALAXY.NG1.AccountingReportsComponent.payments' | sxyTranslate }}</span>\r\n          </th>\r\n          <th class=\"right \">\r\n            <span>{{ 'SALAXY.NG1.AccountingReportsComponent.salariesAlt' | sxyTranslate }}</span><br />\r\n            <span>{{ 'SALAXY.NG1.AccountingReportsComponent.workers' | sxyTranslate }}</span>\r\n          </th>\r\n          <th sxy-text=\"SALAXY.NG1.AccountingReportsComponent.material\"></th>\r\n          <th sxy-text=\"SALAXY.NG1.AccountingReportsComponent.responsiblePerson\"></th>\r\n          <th class=\"middle hidden-xxs\">\r\n            <salaxy-datepicker-popup ng-model=\"$crud.logicalDate\" ng-change=\"$crud.logicalDateChanged()\" name=\"year\" placeholder=\"{{'SALAXY.NG1.AccountingReportsComponent.year'}}\" format=\"year\" label-type=\"plain\" require=\"true\"></salaxy-datepicker-popup>\r\n          </th>\r\n          <th class=\"middle hidden-xxs\">\r\n            <button title=\"{{'SALAXY.NG1.AccountingReportsComponent.chooseAll' | sxyTranslate}}\" class=\"btn btn-block btn-transparent\" type=\"button\" ng-if=\"$ctrl.selectedItems.length == 0\" ng-disabled=\"$ctrl.selectedItems.length == $ctrl.items.length\" ng-click=\"$crud.selectAll()\">\r\n              <i class=\"bi bi-square\"></i>\r\n            </button>\r\n            <button title=\"{{'SALAXY.UI_Terms.unselect' | sxyTranslate}}\" class=\"btn btn-block btn-transparent\" type=\"button\" ng-if=\"$ctrl.selectedItems.length > 0\" ng-disabled=\"$ctrl.selectedItems.length == 0\" ng-click=\"$crud.unselectAll()\">\r\n              <i class=\"bi bi-check-square\"></i>\r\n            </button>\r\n          </th>\r\n          <th class=\"middle hidden-xxs\"></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar middle\">\r\n            <salaxy-avatar avatar=\"row.ownerInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"td-name middle\">\r\n            <span ng-if=\"row.ownerInfo.avatar.displayName == ''\">{{ 'SALAXY.NG1.AccountingReportsComponent.notSelected' | sxyTranslate }}</span>\r\n            <strong>{{row.ownerInfo.avatar.displayName}}</strong><br /> {{row.data.officialId}}\r\n          </td>\r\n          <td class=\"middle\">\r\n            {{ row.logicalDate | date:'yyyy-MM' }}\r\n          </td>\r\n          <td class=\"right middle\">\r\n            {{ row.grossSalary | currency }}<br /> {{ row.payment | currency }}\r\n          </td>\r\n          <td class=\"right middle\">\r\n            {{ row.data.calculationCount }} {{'SALAXY.NG1.AccountingReportsComponent.pce' | sxyTranslate}}<br /> {{ row.data.workerCount }} {{'SALAXY.NG1.AccountingReportsComponent.pce' | sxyTranslate}}\r\n          </td>\r\n          <td class=\"middle\">\r\n            <div ng-repeat=\"message in row.messages\" ng-bind-html=\"message | sxyWorkflowMessage: 'PartnerMessageIssue,PartnerMessageClosed'\"></div>\r\n          </td>\r\n          <td class=\"middle\">\r\n            <span ng-if=\"row.data.partnerMessageAssignedTo\" ng-controller=\"WorkflowController as $workflowCtrl\" title=\"{{ $workflowCtrl.getCredential(row.data.partnerMessageAssignedTo).email || $workflowCtrl.getCredential(row.data.partnerMessageAssignedTo).avatar.displayName }}\">\r\n              <salaxy-avatar style=\"font-size:45px\" avatar=\"$workflowCtrl.getCredential(row.data.partnerMessageAssignedTo).avatar\"></salaxy-avatar>\r\n            </span>\r\n          </td>\r\n          <td class=\"middle hidden-xxs\">\r\n            <button class=\"btn btn-sm btn-block btn-default\" ng-disabled=\"row.isReading\" type=\"button\" ng-click=\"$reportTools.export($crud.getItemDataReader(row),true)\">\r\n              <span ng-show=\"row.isReading\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span>\r\n              <span ng-show=\"!row.isReading\">{{ 'SALAXY.NG1.AccountingReportsComponent.createMaterial' | sxyTranslate }}</span>\r\n            </button>\r\n          </td>\r\n          <td class=\"middle hidden-xxs\">\r\n            <button title=\"{{'SALAXY.UI_Terms.select' | sxyTranslate}}\" class=\"btn btn-block btn-transparent\" type=\"button\" ng-if=\"!$ctrl.isSelected(row)\" ng-click=\"$ctrl.setSelected(row, 'toggle')\">\r\n              <i class=\"bi bi-square\"></i>\r\n            </button>\r\n            <button title=\"{{'SALAXY.UI_Terms.unselect' | sxyTranslate}}\" class=\"btn btn-block btn-transparent\" type=\"button\" ng-if=\"$ctrl.isSelected(row)\" ng-click=\"$ctrl.setSelected(row, 'toggle')\">\r\n              <i class=\"bi bi-check-square\"></i>\r\n            </button>\r\n          </td>\r\n          <td class=\"middle hidden-xxs\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n              <i class=\"bi bi-info-circle d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.show\"></span></a>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/AccountingReportsPanel.html\",`<div class=\"salaxy-odata-card list-card report-list-card card card-sm card-secondary\">\r\n  <div class=\"card-header d-flex align-items-center\">\r\n    {{'SALAXY.NG1.AccountingReportsComponent.accountingReports' | sxyTranslate}}\r\n    <button ng-style=\"{'visibility': $ctrl.items.length > 0 ? 'visible' : 'hidden'}\" class=\"btn btn-secondary btn-xs ms-auto\" ng-click=\"hideFilter = !hideFilter\" title=\"{{'SALAXY.NG1.AccountingReportsComponent.showFilters' | sxyTranslate}}\">\r\n      <i class=\"bi bi-funnel-fill\"></i>\r\n    </button>\r\n  </div>\r\n  <div class=\"card-body filters text-end\" ng-class=\"{'showfilters' : hideFilter}\">\r\n    <div class=\"filter-buttons\">\r\n      <button class=\"btn btn-xs btn-secondary text-end\" sxy-orderby=\"logicalDate\">{{'SALAXY.NG1.AccountingReportsComponent.mm' | sxyTranslate}}</button>\r\n    </div>\r\n    <salaxy-input name=\"search1cp{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search hidden-xxs\" label-type=\"plain\"></salaxy-input>\r\n  </div>\r\n  <div ng-class=\"$ctrl.getCssClass()\">\r\n    <div class=\"visible-xxs\" ng-if=\"$ctrl.items.length > 0\">\r\n      <div class=\"table-filter-container-mobile\">\r\n        <salaxy-input name=\"search2cp{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n        </salaxy-input>\r\n      </div>\r\n    </div>\r\n    <div class=\"card-body text-center card-content lg-height align-middle\" ng-show=\"$ctrl.items.length == 0 && !$ctrl.isLoading\">\r\n      <div>\r\n        <h3 sxy-text=\"SALAXY.NG1.AccountingReportsComponent.noAccountingReports\"></h3>\r\n      </div>\r\n    </div>\r\n    <div class=\"table-responsive\">\r\n      <table class=\"table\" ng-if=\"$ctrl.items.length > 0\">\r\n        <tbody>\r\n          <tr ng-repeat=\"row in $ctrl.items\">\r\n            <td class=\"middle\">\r\n              {{ row.logicalDate | date:'yyyy-MM' }}\r\n            </td>\r\n            <td class=\"middle right\">\r\n              {{ row.grossSalary | currency }}<br /> {{ row.payment | currency }}\r\n            </td>\r\n            <td class=\"middle right\">\r\n              {{row.data.calculationCount}} <i class=\"bi bi-list-task\" title=\"{{'SALAXY.NG1.AccountingReportsComponent.calcs' | sxyTranslate}}\"></i>\r\n              <br/> {{row.data.workerCount}} <i class=\"bi bi-person-fill\" title=\"{{'SALAXY.NG1.AccountingReportsComponent.workersAlt' | sxyTranslate}}\"></i>\r\n            </td>\r\n            <td class=\"middle right\">\r\n              <a href=\"\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-secondary\"><i\r\n              class=\"bi bi-info-circle \"></i></a>\r\n            </td>\r\n\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n      <div class=\"salaxy-odata-footer\">\r\n        <salaxy-spinner></salaxy-spinner>\r\n      </div>\r\n    </div>\r\n\r\n  </div>\r\n  <div class=\"card-footer text-center\">\r\n    <a ng-href=\"#{{$crud.getDefaults().listUrl}}\" class=\"btn btn-primary btn-sm\" sxy-text=\"SALAXY.UI_Terms.showAll\"></a>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/AccountingTargets.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\">\r\n            <div sxy-orderby=\"shortText\" sxy-text=\"SALAXY.NG1.AccountingTargetsComponent.exportDefinition\"></div>\r\n            <div sxy-text=\"SALAXY.NG1.AccountingTargetsComponent.targetChannel\"></div>\r\n          </th>\r\n          <th colspan=\"2\">\r\n            <div sxy-orderby=\"ownerInfo/avatar/displayName\" sxy-text=\"SALAXY.NG1.AccountingTargetsComponent.owner\"></div>\r\n            <div sxy-orderby=\"status\" sxy-text=\"SALAXY.NG1.AccountingTargetsComponent.status\"></div>\r\n          </th>\r\n          <th class=\"right\">\r\n            <div sxy-orderby=\"createdAt\" sxy-text=\"SALAXY.UI_Terms.created\"></div>\r\n            <div sxy-orderby=\"updatedAt\" sxy-text=\"SALAXY.UI_Terms.updated\"></div>\r\n          </th>\r\n          <th class=\"right hidden-xxs\" colspan=\"2\">\r\n            <div class=\"table-filter-container\">\r\n              <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" class=\"salaxy-odata-table-search\" placeholder=\"SALAXY.UI_Terms.textSearch\" label-type=\"plain\"></salaxy-input>\r\n            </div>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar middle\">\r\n            <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"middle\">\r\n            <div title=\"{{ row.shortText }} ({{ row.id }})\">\r\n              <strong>{{ row.otherPartyInfo.avatar.displayName }}</strong>\r\n            </div>\r\n          </td>\r\n          <td class=\"td-avatar middle\">\r\n            <salaxy-avatar avatar=\"row.ownerInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"middle\">\r\n            <div>{{ row.ownerInfo.avatar.displayName }}</div>\r\n            <div>{{ \"AccountingTargetStatus.\" + row.status | sxyEnum }}</div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <div title=\"{{ row.createdAt }}\">{{ row.createdAt | sxyDate }}</div>\r\n            <div title=\"{{ row.updatedAt }}\">{{ row.updatedAt | sxyDate }}</div>\r\n            <div></div>\r\n          </td>\r\n          <td class=\"middle hidden-xxs\">\r\n            <button ng-if=\"!row.isReadOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-primary btn-block\">\r\n              <i class=\"bi bi-pencil-fill d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.edit\"></span>\r\n            </button>\r\n            <button ng-if=\"row.isReadOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n              <i class=\"bi bi-info-circle d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n            </button>\r\n          </td>\r\n          <td class=\"middle hidden-xxs\">\r\n            <button ng-if=\"!row.isReadOnly\" ng-click=\"$crud.delete(row)\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\" class=\"btn btn-sm btn-danger btn-block\">\r\n              <i class=\"bi bi-trash-fill d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.delete\"></span>\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>\r\n`);\n\n $templateCache.put(\"salaxy-components/odata/lists/AccountingTargetSelect.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"visible-xxs\">\r\n    <div class=\"table-filter-container-mobile\">\r\n      <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n      </salaxy-input>\r\n    </div>\r\n  </div>\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\">\r\n            <div sxy-orderby=\"shortText\" sxy-text=\"SALAXY.NG1.AccountingTargetsComponent.exportDefinition\"></div>\r\n            <div sxy-text=\"SALAXY.NG1.AccountingTargetsComponent.targetChannel\"></div>\r\n          </th>\r\n          <th sxy-orderby=\"owner\" colspan=\"2\">\r\n            <div sxy-text=\"SALAXY.NG1.AccountingTargetsComponent.owner\"></div>\r\n          </th>\r\n          <th class=\"right hidden-xxs\" colspan=\"3\">\r\n            <div class=\"table-filter-container\">\r\n              <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" class=\"salaxy-odata-table-search\" placeholder=\"SALAXY.UI_Terms.textSearch\" label-type=\"plain\"></salaxy-input>\r\n            </div>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar middle\">\r\n            <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"middle\">\r\n            <div title=\"{{ row.shortText }} ({{ row.id }})\">\r\n              <strong>{{ row.otherPartyInfo.avatar.displayName }}</strong>\r\n            </div>\r\n          </td>\r\n          <td class=\"td-avatar middle\">\r\n            <salaxy-avatar avatar=\"row.ownerInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"middle\">\r\n            <div>{{ row.ownerInfo.avatar.displayName }}</div>\r\n          </td>\r\n          <td></td>\r\n          <td class=\"right middle\">\r\n            <button class=\"btn btn-sm\" type=\"button\" ng-class=\"$ctrl.isSelected(row) ? 'btn-danger' : 'btn-info'\" ng-click=\"$ctrl.setSelected(row, 'toggle')\">\r\n              {{ $ctrl.isSelected(row) ? ('SALAXY.UI_Terms.unselect' | sxyTranslate) : ('SALAXY.UI_Terms.select' | sxyTranslate) }}\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/ApiCrudObject.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <table class=\"table\">\r\n    <thead>\r\n      <tr>\r\n        <th sxy-orderby=\"id\">\r\n          <div sxy-text=\"SALAXY.NG1.ApiCrudObjectComponent.id\"></div>\r\n        </th>\r\n        <th sxy-orderby=\"status\"  sxy-text=\"SALAXY.UI_Terms.status\"></th>\r\n        <th class=\"right\">\r\n          <div sxy-orderby=\"createdAt\" sxy-text=\"SALAXY.UI_Terms.created\"></div>\r\n          <div sxy-orderby=\"updatedAt\" sxy-text=\"SALAXY.UI_Terms.updated\"></div>\r\n        </th>\r\n        <th sxy-orderby=\"owner\" sxy-text=\"SALAXY.NG1.ApiCrudObjectComponent.owner\"></th>\r\n        <th sxy-orderby=\"isReadOnly\" sxy-text=\"SALAXY.NG1.ApiCrudObjectComponent.readOnly\"></th>\r\n        <th sxy-orderby=\"partner\" sxy-text=\"SALAXY.NG1.ApiCrudObjectComponent.partner\"></th>\r\n        <th colspan=\"2\"></th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat=\"row in $ctrl.items\">\r\n        <td>\r\n          <div>{{ row.shortText }}</div>\r\n          <div><code><small>{{ row.id }}</small></code></div>\r\n        </td>\r\n        <td>{{ row.status }}</td>\r\n        <td class=\"right\">\r\n          <div>{{ row.createdAt | sxyDate }}</div>\r\n          <div>{{ row.updatedAt | sxyDate }}</div>\r\n        </td>\r\n        <td class=\"td-avatar\">\r\n          <salaxy-avatar avatar=\"row.ownerInfo.avatar\" title=\"row.owner\"></salaxy-avatar>\r\n        </td>\r\n        <td>{{ row.isReadOnly }}</td>\r\n        <td>{{ row.partner }}</td>\r\n        <td>\r\n          <button ng-if=\"!row.isReadOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-primary btn-block\">\r\n            <i class=\"bi bi-pencil-fill d-sm-none d-inline\"></i>\r\n            <span class=\"d-none d-sm-inline\" sxy-text=\"SALAXY.UI_Terms.edit\"></span>\r\n          </button>\r\n          <button ng-if=\"row.isReadOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n            <i class=\"bi bi-info-circle d-sm-none d-inline\"></i>\r\n            <span class=\"d-none d-sm-inline\" sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n          </button>\r\n        </td>\r\n        <td>\r\n          <button ng-if=\"!row.isReadOnly\" ng-click=\"$crud.delete(row)\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\" class=\"btn btn-sm btn-danger btn-block\">\r\n            <i class=\"bi bi-trash-fill d-sm-none d-inline\"></i>\r\n            <span class=\"d-none d-sm-inline\" sxy-text=\"SALAXY.UI_Terms.delete\"></span>\r\n          </button>\r\n          <button ng-if=\"row.isReadOnly\" ng-click=\"$crud.showCopyAsNew(row)\" title=\"{{ 'SALAXY.UI_Terms.copyAsNew' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n            <i class=\"bi bi-copy d-sm-none d-inline\"></i>\r\n            <span class=\"d-none d-sm-inline\" sxy-text=\"SALAXY.UI_Terms.copyAsNew\"></span>\r\n           </button>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/BrandList.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"visible-xxs\">\r\n    <div class=\"table-filter-container-mobile\">\r\n      <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n      </salaxy-input>\r\n    </div>\r\n  </div>\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\" sxy-orderby=\"ownerInfo/avatar/displayName\">\r\n            <span sxy-text=\"SALAXY.NG1.BrandListComponent.partner\"></span>\r\n          </th>\r\n          <th class=\"right\" colspan=\"2\">\r\n            <div class=\"table-filter-container\">\r\n              <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" class=\"salaxy-odata-table-search\" placeholder=\"SALAXY.UI_Terms.textSearch\" label-type=\"plain\"></salaxy-input>\r\n            </div>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar middle\">\r\n            <i class=\"salaxy-avatar\" style=\"font-size: 74px;\"><img ng-src=\"{{ row.data.logo }}\" /></i>\r\n          </td>\r\n          <td class=\"td-name middle\">\r\n            <strong>{{row.data.webAppName || row.ownerInfo.avatar.displayName}}</strong>\r\n          </td>\r\n          <td class=\"right middle\">\r\n            <button class=\"btn\" ng-class=\"$ctrl.isSelected(row) ? 'btn-danger' : 'btn-info'\" type=\"button\" ng-click=\"$ctrl.setSelected(row, 'toggle')\">\r\n              {{ $ctrl.isSelected(row) ? ('SALAXY.UI_Terms.unselect' | sxyTranslate) : ('SALAXY.UI_Terms.select' | sxyTranslate) }}\r\n            </button>\r\n\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/Calculations-select.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"visible-xxs\">\r\n    <div class=\"table-filter-container-mobile\">\r\n      <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n      </salaxy-input>\r\n    </div>\r\n  </div>\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\">\r\n            <span sxy-orderby=\"otherPartyInfo/avatar/displayName\" sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span>\r\n            <span class=\"label label-primary clickable\" ng-if=\"$ctrl.selectedItems.length\" ng-click=\"$ctrl.selectedItems.splice(0,$ctrl.selectedItems.length)\"> {{'SALAXY.UI_Terms.chosen' | sxyTranslate}}: {{ $ctrl.selectedItems.length }} <i class=\"bi bi-x-circle\"></i></span>\r\n          </th>\r\n          <th class=\"hidden-xxs\">\r\n            <span sxy-text=\"SALAXY.NG1.CalcListComponent.status.title\"></span><br />\r\n            <span sxy-orderby=\"salaryDate\"><span sxy-text=\"SALAXY.NG1.CalculationsWithSalaryDateSelectComponent.salaryDate\"></span></span>\r\n          </th>\r\n          <th class=\"right hidden-xxs\" colspan=\"2\">\r\n            <div class=\"table-filter-container\">\r\n              <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" class=\"salaxy-odata-table-search\" placeholder=\"SALAXY.UI_Terms.textSearch\" label-type=\"plain\"></salaxy-input>\r\n            </div>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar visible-xxs middle\">\r\n            <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"td-name visible-xxs middle\">\r\n            <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.CalcListComponent.notSelected\"></span>\r\n            <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br /> {{ \"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate }}\r\n            <br /> {{ row.salaryDate | date }}\r\n          </td>\r\n          <td class=\"right visible-xxs bottom\">\r\n            <a ng-href=\"#/calc/details/{{row.id}}\">\r\n              {{ row.grossSalary | currency }}\r\n            </a>\r\n          </td>\r\n          <td class=\"td-avatar hidden-xxs middle\">\r\n            <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"td-name hidden-xxs middle\">\r\n            <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.CalcListComponent.notSelected\"></span>\r\n            <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br />\r\n          </td>\r\n          <td class=\"hidden-xxs middle\">\r\n            {{ row.status ? (\"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate) : \"#ERR\" }}<br /> {{ row.salaryDate | date }}\r\n          </td>\r\n          <td class=\"right hidden-xxs middle\">\r\n            {{ row.grossSalary | currency }}\r\n          </td>\r\n          <td class=\"right middle\">\r\n            <button class=\"btn btn-sm\" type=\"button\" ng-class=\"$ctrl.isSelected(row) ? 'btn-danger' : 'btn-info'\" ng-click=\"$ctrl.setSelected(row, 'toggle')\">\r\n              {{ $ctrl.isSelected(row) ? ('SALAXY.UI_Terms.unselect' | sxyTranslate) : ('SALAXY.UI_Terms.select' | sxyTranslate) }}\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/CalculationsAll.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"visible-xxs\">\r\n    <div class=\"table-header-container-mobile\" ng-show=\"!$ctrl.readOnly\">\r\n      <a class=\"btn btn-sm btn-block btn-primary\" href=\"#/calc/details/new\" sxy-text=\"SALAXY.UI_Terms.createNew\"></a>\r\n    </div>\r\n    <div class=\"table-filter-container-mobile\">\r\n      <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n      </salaxy-input>\r\n    </div>\r\n  </div>\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\" sxy-orderby=\"otherPartyInfo/avatar/displayName\">\r\n            <span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span>\r\n          </th>\r\n          <th class=\"hidden-xxs\">\r\n            <span sxy-orderby=\"status\"><span sxy-text=\"SALAXY.NG1.CalcListComponent.status.title\"></span></span><br />\r\n            <span sxy-orderby=\"endAt\"><span sxy-text=\"SALAXY.NG1.CalcListComponent.payment\" ></span></span>\r\n          </th>\r\n          <th class=\"right \">\r\n            <span sxy-orderby=\"grossSalary\"><span sxy-text=\"SALAXY.NG1.CalcListComponent.salary\"></span></span><br />\r\n            <span sxy-orderby=\"payment\"><span sxy-text=\"SALAXY.NG1.CalcListComponent.payment\" ></span></span>\r\n          </th>\r\n          <th class=\"right hidden-xxs\" colspan=\"2\">\r\n            <salaxy-odata-actions show-export=\"true\"></salaxy-odata-actions>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar visible-xxs middle\">\r\n            <a href=\"\">\r\n              <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n            </a>\r\n          </td>\r\n          <td class=\"td-name visible-xxs middle\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\">\r\n              <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.CalcListComponent.notSelected\"></span>\r\n              <strong>{{row.otherPartyInfo.avatar.displayName}}</strong>\r\n              <br /> {{ \"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate }}\r\n              <br /> {{row.endAt | date}}\r\n            </a>\r\n          </td>\r\n          <td class=\"right visible-xxs bottom\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\">\r\n              {{ row.grossSalary | currency }}\r\n              <br />\r\n              {{ row.payment | currency }}\r\n            </a>\r\n          </td>\r\n          <td class=\"td-avatar hidden-xxs middle\">\r\n            <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"td-name hidden-xxs middle\">\r\n            <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.CalcListComponent.notSelected\"></span>\r\n            <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br />\r\n          </td>\r\n          <td class=\"hidden-xxs middle\">\r\n            {{ \"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate }}\r\n            <br /> {{row.endAt | date}}\r\n          </td>\r\n          <td class=\"right hidden-xxs middle\">\r\n            {{ row.grossSalary | currency }}<br /> {{ row.payment | currency }}\r\n          </td>\r\n          <td class=\"hidden-xxs middle\">\r\n            <button ng-click=\"$crud.showDetails(row)\" ng-if=\"row.status == 'draft'\" class=\"btn btn-sm btn-primary btn-block\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\">\r\n              <i class=\"bi bi-pencil-fill d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.edit\"></span>\r\n            </button>\r\n            <button ng-click=\"$crud.showDetails(row)\" ng-if=\"row.status != 'draft'\" class=\"btn btn-sm btn-default btn-block\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\">\r\n              <i class=\"bi bi-info-circle d-inline-block d-sm-none\"></i></a>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.show\" ng-if=\"!row.data.payrollId\"></span>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.NG1.CalcListComponent.calculation\" ng-if=\"row.data.payrollId\"></span>\r\n            </button>\r\n          </td>\r\n          <td class=\"hidden-xxs middle\">\r\n            <button ng-if=\"row.status == 'draft'\" ng-click=\"$crud.delete(row)\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\" class=\"btn btn-sm btn-danger btn-block\">\r\n              <i class=\"bi bi-trash-fill d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.delete\"></span>\r\n            </button>\r\n            <button ng-if=\"!row.data.payrollId && (row.status == 'paymentSucceeded' || row.status == 'paymentStarted')\" ng-click=\"$crud.showCopyAsNew(row)\" class=\"btn btn-sm btn-default btn-block\" title=\"{{ 'SALAXY.UI_Terms.copyAsNew' | sxyTranslate}}\">\r\n              <i class=\"bi bi-copy d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.copyAsNew\"></span>\r\n            </button>\r\n            <a ng-if=\"row.data.payrollId\" class=\"btn btn-sm btn-primary btn-block\" ng-href=\"#/payroll/details/{{ row.data.payrollId }}\">\r\n              <i class=\"bi bi-list-task d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.NG1.CalcListComponent.payroll\"></span>\r\n            </a>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/CalculationsDrafts.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n\r\n\r\n  <div class=\"visible-xxs\">\r\n    <div class=\"table-header-container-mobile\" ng-show=\"!$ctrl.readOnly\">\r\n      <a class=\"btn btn-sm btn-block btn-primary\" href=\"#/calc/details/new\" sxy-text=\"SALAXY.UI_Terms.createNew\"></a>\r\n    </div>\r\n    <div class=\"table-filter-container-mobile\">\r\n      <salaxy-input name=\"search1x{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n      </salaxy-input>\r\n    </div>\r\n  </div>\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\" sxy-if-role=\"!worker\">\r\n            <span sxy-orderby=\"otherPartyInfo/avatar/displayName\" sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span>\r\n          </th>\r\n          <th sxy-if-role=\"worker\">\r\n            <span sxy-orderby=\"endAt\" sxy-text=\"SALAXY.NG1.CalcListComponent.date\"></span>\r\n          </th>\r\n          <th class=\"hidden-xxs\" sxy-if-role=\"!worker\">\r\n            <span sxy-text=\"SALAXY.NG1.CalcListComponent.status.title\"></span><br />\r\n            <span sxy-orderby=\"endAt\"><span sxy-text=\"SALAXY.NG1.CalcListComponent.date\"></span></span>\r\n          </th>\r\n          <th class=\"right \">\r\n            <span sxy-orderby=\"grossSalary\"><span sxy-text=\"SALAXY.NG1.CalcListComponent.salary\" ></span></span><br />\r\n            <span sxy-orderby=\"payment\"><span sxy-text=\"SALAXY.NG1.CalcListComponent.payment\" ></span></span>\r\n          </th>\r\n          <th class=\"right hidden-xxs\" colspan=\"2\">\r\n            <salaxy-odata-actions show-export=\"true\"></salaxy-odata-actions>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar visible-xxs middle\" sxy-if-role=\"!worker\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\">\r\n              <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n            </a>\r\n          </td>\r\n          <td class=\"td-name visible-xxs middle\" sxy-if-role=\"!worker\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\">\r\n              <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.CalcListComponent.notSelected\"></span>\r\n              <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br /> {{ \"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate }}\r\n              <br />{{ row.endAt | date }}\r\n            </a>\r\n          </td>\r\n          <td class=\"td-name visible-xxs middle\" sxy-if-role=\"worker\" ng-click=\"$crud.showDetails(row)\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\">\r\n              {{ row.endAt | date }}\r\n            </a>\r\n          </td>\r\n          <td class=\"right visible-xxs bottom\" ng-click=\"$crud.showDetails(row)\">\r\n\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\">\r\n              {{ row.grossSalary | currency }}<br />\r\n              {{ row.payment | currency }}\r\n            </a>\r\n          </td>\r\n          <td class=\"td-avatar hidden-xxs middle\" sxy-if-role=\"!worker\">\r\n            <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"td-name hidden-xxs middle\" sxy-if-role=\"!worker\">\r\n            <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.CalcListComponent.notSelected\"></span>\r\n            <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br />\r\n          </td>\r\n          <td class=\"hidden-xxs middle\">\r\n            {{ \"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate }}<br /> {{ row.endAt | date }}\r\n          </td>\r\n          <td class=\"right hidden-xxs middle\">\r\n            {{ row.grossSalary | currency }}<br /> {{ row.payment | currency }}\r\n          </td>\r\n          <td class=\"hidden-xxs middle\" colspan=\"{{$ctrl.readOnly ? 2 : 1}}\">\r\n\r\n            <button ng-if=\"!row.isReadOnly && !$ctrl.readOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-primary btn-block\">\r\n              <i class=\"bi bi-pencil-fill d-inline-block d-sm-none\"></i><span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.edit\"></span>\r\n            </button>\r\n            <button ng-if=\"!row.isReadOnly && $ctrl.readOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n              <i class=\"bi bi-info-circle d-inline-block d-sm-none\"></i><span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n            </button>\r\n          </td>\r\n          <td class=\"hidden-xxs middle\" ng-if=\"!$ctrl.readOnly\">\r\n            <button ng-click=\"$crud.delete(row)\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\" class=\"btn btn-sm btn-danger btn-block\"><i\r\n                class=\"bi bi-trash-fill d-inline-block d-sm-none\"></i><span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.delete\"></span></button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/CalculationsEmployer.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n\r\n\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n\r\n          <th>\r\n            <span sxy-orderby=\"status\">\r\n              <span sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.calculationsWorker.status\"></span>\r\n            </span>\r\n            <br />\r\n            <span sxy-orderby=\"endAt\">\r\n              <span sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.calculationsWorker.date\"></span>\r\n            </span>\r\n          </th>\r\n          <th class=\"right\">\r\n            <span sxy-orderby=\"grossSalary\"><span sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.calculationsWorker.salary\"></span></span><br />\r\n            <span sxy-orderby=\"payment\"><span sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.calculationsWorker.payment\"></span></span>\r\n          </th>\r\n          <th class=\"right\">\r\n\r\n\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n\r\n          <td>\r\n            <div ng-switch=\"row.status\">\r\n              <span ng-switch-when=\"paymentWorkerCopy\" class=\"text-success\">\r\n                Maksettu\r\n              </span>\r\n              <span ng-switch-when=\"workerRequested\">\r\n                Lähetetty\r\n              </span>\r\n              <span ng-switch-when=\"workerRequestAccepted\">\r\n                Hyväksytty\r\n              </span>\r\n              <span ng-switch-when=\"workerRequestDeclined\" class=\"text-warning\">\r\n                Hylätty\r\n              </span>\r\n\r\n            </div>\r\n            <!--TODO add better status descriptons-->\r\n            <!--br> {{ \"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate }}-->\r\n            {{ (row.salaryDate || row.endAt) | date}}\r\n          </td>\r\n          <td class=\"right\">\r\n            {{ row.grossSalary | currency }}\r\n            <br /> {{ row.payment | currency }}\r\n          </td>\r\n          <td class=\"right middle\">\r\n            <button ng-click=\"$crud.showDetails(row)\" class=\"btn btn-sm btn-default\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\">\r\n              <i class=\"bi bi-info-circle d-inline-block d-sm-none\"></i>\r\n              \r\n              <span class=\"d-sm-inline-block d-none\" sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n            </button>\r\n\r\n            <a ng-href=\"{{$crud.getPdfUrl(row)}}\" target=\"_blank\" title=\"{{ 'SALAXY.UI_Terms.printable' | sxyTranslate}}\" class=\"btn btn-sm btn-default\">\r\n              <i class=\"bi bi-file-earmark-pdf d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-sm-inline-block d-none\" sxy-text=\"SALAXY.UI_Terms.printable\"></span>\r\n            </a>\r\n          </td>\r\n\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/CalculationsEmployerAll.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n\r\n\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\">\r\n            <span sxy-text=\"SALAXY.NG1_Other.Roles.employer\"></span>\r\n          </th>\r\n          <th>\r\n            <span sxy-orderby=\"status\">\r\n              <span sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.calculationsWorker.status\"></span>\r\n            </span>\r\n            <br />\r\n            <span sxy-orderby=\"endAt\">\r\n              <span sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.calculationsWorker.date\"></span>\r\n            </span>\r\n          </th>\r\n          <th class=\"right\">\r\n            <span sxy-orderby=\"grossSalary\"><span sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.calculationsWorker.salary\"></span></span><br />\r\n            <span sxy-orderby=\"payment\"><span sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.calculationsWorker.payment\"></span></span>\r\n          </th>\r\n          <th class=\"right\">\r\n\r\n\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar  middle\">\r\n            <div ng-if=\"row.status != 'draft'\">\r\n\r\n              <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n            </div>\r\n            <div ng-if=\"row.status == 'draft'\">\r\n              <i class=\"bi bi-question-circle-fill\" style=\"font-size: 45px;color: #d0d0d0;\"></i>\r\n            </div>\r\n          </td>\r\n          <td class=\"td-name  middle\">\r\n            <div ng-if=\"row.status == 'draft'\">\r\n              <span class=\"small\" sxy-html=\"Luonnoslaskelma<br>Ei työnantajaa\"></span>\r\n            </div>\r\n            <div ng-if=\"row.status != 'draft'\">\r\n\r\n              <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br>\r\n              <small>{{row.otherPartyInfo.email}}</small>\r\n            </div>\r\n          </td>\r\n          <td>\r\n            <div ng-switch=\"row.status\">\r\n              <span ng-switch-when=\"draft\">\r\n                Luonnos\r\n              </span>\r\n              <span ng-switch-when=\"paymentWorkerCopy\" class=\"text-success\">\r\n                Maksettu\r\n              </span>\r\n              <span ng-switch-when=\"workerRequested\">\r\n                Lähetetty\r\n              </span>\r\n              <span ng-switch-when=\"workerRequestAccepted\" class=\"text-warning\">\r\n                Hyväksytty\r\n              </span>\r\n              <span ng-switch-when=\"workerRequestDeclined\" class=\"text-danger\">\r\n                Hylätty\r\n              </span>\r\n\r\n            </div>\r\n            <!--TODO add better status descriptons-->\r\n            <!--br> {{ \"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate }}-->\r\n            {{ (row.salaryDate || row.endAt) | date}}\r\n          </td>\r\n          <td class=\"right\">\r\n            {{ row.grossSalary | currency }}\r\n            <br /> {{ row.payment | currency }}\r\n          </td>\r\n          <td class=\"right middle\">\r\n            <button ng-click=\"$crud.showDetails(row)\" class=\"btn btn-sm btn-default\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\">\r\n              <i class=\"bi bi-info-circle d-inline-block d-sm-none\"></i>\r\n              \r\n              <span class=\"d-sm-inline-block d-none\" sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n            </button>\r\n\r\n            <a ng-href=\"{{$crud.getPdfUrl(row)}}\" target=\"_blank\" title=\"{{ 'SALAXY.UI_Terms.printable' | sxyTranslate}}\" class=\"btn btn-sm btn-default\">\r\n              <i class=\"bi bi-file-earmark-pdf d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-sm-inline-block d-none\" sxy-text=\"SALAXY.UI_Terms.printable\"></span>\r\n            </a>\r\n          </td>\r\n\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/CalculationsPaid.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"visible-xxs\">\r\n    <div class=\"table-header-container-mobile\" ng-show=\"!$ctrl.readOnly\">\r\n      <a class=\"btn btn-sm btn-block btn-primary\" href=\"#/calc/details/new\" sxy-text=\"SALAXY.UI_Terms.createNew\"></a>\r\n    </div>\r\n    <div class=\"table-filter-container-mobile\">\r\n      <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n      </salaxy-input>\r\n    </div>\r\n  </div>\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\" sxy-orderby=\"otherPartyInfo/avatar/displayName\">\r\n            <span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span>\r\n          </th>\r\n          <th class=\"hidden-xxs\">\r\n            <span sxy-orderby=\"status\"><span sxy-text=\"SALAXY.NG1.CalcListComponent.status.title\"></span></span><br />\r\n            <span sxy-orderby=\"endAt\"><span sxy-text=\"SALAXY.NG1.CalcListComponent.payment\"></span></span>\r\n          </th>\r\n          <th class=\"right \">\r\n            <span sxy-orderby=\"grossSalary\"><span sxy-text=\"SALAXY.NG1.CalcListComponent.salary\"></span></span><br />\r\n            <span sxy-orderby=\"payment\"><span sxy-text=\"SALAXY.NG1.CalcListComponent.payment\"></span></span>\r\n          </th>\r\n          <th class=\"right hidden-xxs\" colspan=\"3\">\r\n            <salaxy-odata-actions show-export=\"true\"></salaxy-odata-actions>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar visible-xxs middle\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\">\r\n              <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n            </a>\r\n          </td>\r\n          <td class=\"td-name visible-xxs middle\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\">\r\n              <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.CalcListComponent.notSelected\"></span>\r\n              <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br /> {{ \"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate }}\r\n              <br /> {{ row.endAt | date }}\r\n            </a>\r\n          </td>\r\n          <td class=\"right visible-xxs bottom\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\">\r\n              {{ row.grossSalary | currency }}<br />\r\n              {{ row.payment | currency }}\r\n            </a>\r\n          </td>\r\n          <td class=\"td-avatar hidden-xxs middle\">\r\n            <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"td-name hidden-xxs middle\">\r\n            <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.CalcListComponent.notSelected\"></span>\r\n            <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br />\r\n          </td>\r\n          <td class=\"hidden-xxs middle\">\r\n            {{ \"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate }}<br /> {{ row.endAt | date }}\r\n          </td>\r\n          <td class=\"right hidden-xxs middle\">\r\n            {{ row.grossSalary | currency }}<br /> {{ row.payment | currency }}\r\n          </td>\r\n          <td class=\"hidden-xxs middle\" colspan=\"{{$ctrl.readOnly ? 2 : 1 }}\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n              <i class=\"bi bi-info-circle d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n            </a>\r\n          </td>\r\n          <td class=\"hidden-xxs middle\" ng-if=\"!$ctrl.readOnly\">\r\n            <button ng-click=\"$crud.showCopyAsNew(row)\" title=\"{{ 'SALAXY.UI_Terms.copyAsNew' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n              <i class=\"bi bi-copy d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.copyAsNew\"></span>\r\n            </button>\r\n          </td>\r\n          <td class=\"hidden-xxs middle\">\r\n            <a ng-href=\"{{$crud.getPdfUrl(row)}}\" target=\"_blank\" title=\"{{ 'SALAXY.UI_Terms.printable' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n              <i class=\"bi bi-file-earmark-pdf d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.printable\"></span>\r\n            </a>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/CalculationsPaidIr.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"visible-xxs\">\r\n    <div class=\"table-filter-container-mobile\">\r\n      <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n      </salaxy-input>\r\n    </div>\r\n  </div>\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\" sxy-orderby=\"otherPartyInfo/avatar/displayName\">\r\n            <span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span>\r\n          </th>\r\n          <th class=\"hidden-xxs\">\r\n            <span sxy-orderby=\"salaryDate\"><span sxy-text=\"SALAXY.NG1.PayrollListComponent.salaryDate\"></span></span><br />\r\n          </th>\r\n          <th class=\"right \">\r\n            <span sxy-orderby=\"grossSalary\"><span sxy-text=\"SALAXY.NG1.CalcListComponent.salary\"></span></span><br />\r\n          </th>\r\n          <th class=\"hidden-xxs\">\r\n            <span sxy-orderby=\"endAt\"><span sxy-text=\"SALAXY.NG1.PayrollListComponent.paymentDate\"></span></span><br />\r\n          </th>\r\n          <th class=\"hidden-xxs\" colspan=\"2\">\r\n            <span sxy-text=\"Ilmoitus\"></span>\r\n          </th>\r\n          <th class=\"right hidden-xxs\" colspan=\"4\">\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar visible-xxs middle\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\">\r\n              <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n            </a>\r\n          </td>\r\n          <td class=\"td-name visible-xxs middle\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\">\r\n              <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.CalcListComponent.notSelected\"></span>\r\n              <strong>{{row.otherPartyInfo.avatar.displayName}}</strong>\r\n              <br /> {{ row.salaryDate | date }}\r\n            </a>\r\n          </td>\r\n          <td class=\"right visible-xxs bottom\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\">\r\n              {{ row.grossSalary | currency }}\r\n              <br /> {{ row.endAt | date }}\r\n            </a>\r\n          </td>\r\n          <td class=\"td-avatar hidden-xxs middle\">\r\n            <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"td-name hidden-xxs middle\">\r\n            <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.CalcListComponent.notSelected\"></span>\r\n            <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br />\r\n          </td>\r\n          <td class=\"hidden-xxs middle\">\r\n            {{ row.salaryDate | date }}\r\n          </td>\r\n          <td class=\"right hidden-xxs middle\">\r\n            {{ row.grossSalary | currency }}\r\n          </td>\r\n          <td class=\"hidden-xxs middle\">\r\n            {{ row.endAt | date }}\r\n          </td>\r\n          <td class=\"hidden-xxs middle\">\r\n            <div ng-repeat=\"message in row.messages\" ng-bind-html=\"message | sxyWorkflowMessage: 'SystemMessageReportInvalid,SystemMessageReportScheduled,SystemMessageReportDelivered,SystemMessageReportCanceled,SystemMessageReportError'\"></div>\r\n          </td>\r\n          <td class=\"hidden-xxs middle\">\r\n            <span ng-if=\"row.status == 'paymentSucceeded' && row.data.repairedAt\"><i class=\"bi bi-bandaid\"></i></span>\r\n          </td>\r\n          <td class=\"hidden-xxs middle\" ng-show=\"row.status == 'paymentSucceeded'\">\r\n            <a href=\"\" ng-click=\"$crud.showEpr(row)\" title=\"{{ 'SALAXY.NG1.CalcReportsComponent.irFull' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n              <i class=\"bi bi-info-lg visible-xs me-1\"></i><span class=\"hidden-xs\" sxy-text=\"Ilmoitus\"></span>\r\n            </a>\r\n          </td>\r\n          <td class=\"hidden-xxs middle\" colspan=\"{{$ctrl.readOnly ? 2 : 1 }}\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n              <i class=\"bi bi-info-lg visible-xs me-1\"></i><span class=\"hidden-xs\" sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n            </a>\r\n          </td>\r\n          <td class=\"hidden-xxs middle\" ng-if=\"!$ctrl.readOnly\">\r\n            <button ng-click=\"$crud.showCopyAsNew(row)\" title=\"{{ 'SALAXY.UI_Terms.copyAsNew' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n              <i class=\"bi bi-copy visible-xs me-1\"></i><span class=\"hidden-xs\" sxy-text=\"SALAXY.UI_Terms.copy\"></span>\r\n            </button>\r\n          </td>\r\n          <td class=\"hidden-xxs middle\">\r\n            <a ng-href=\"{{$crud.getPdfUrl(row)}}\" target=\"_blank\" title=\"{{ 'SALAXY.UI_Terms.printable' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n              <i class=\"bi bi-file-earmark-pdf visible-xs me-1\"></i><span class=\"hidden-xs\" sxy-text=\"SALAXY.UI_Terms.printable\"></span>\r\n            </a>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>\r\n`);\n\n $templateCache.put(\"salaxy-components/odata/lists/CalculationsPanel.html\",`<div class=\"salaxy-odata-card card list-card calc-list-card  card-sm card-secondary\" ng-init=\"hideFilter = false\">\r\n  \r\n\r\n  <div class=\"card-header\">\r\n    {{'SALAXY.NG1.CalcListComponent.panel.' + $ctrl.data.category + '.heading' | sxyTranslate}}\r\n    <div class=\"float-end\" ng-show=\"$ctrl.data.category != 'sentAndDraft'\">\r\n      <button class=\"btn btn-secondary btn-xs\" ng-click=\"hideFilter = !hideFilter\" title=\"{{'SALAXY.NG1.CalculationsPanelComponent.showFilters' | sxyTranslate}}\">\r\n        <i class=\"bi bi-funnel-fill\"></i>\r\n      </button>\r\n    </div>\r\n    <div class=\"float-end\" ng-if=\"$ctrl.data.category == 'sentAndDraft'\">\r\n      <salaxy-action-button action=\"'newCalc'\" button-class=\"btn-primary btn-labeled-right btn-xs\" label=\"{{'SALAXY.NG1.CalculationsPanelComponent.newCalc' | sxyTranslate}}\"></salaxy-action-button>\r\n    </div>\r\n  </div>\r\n\r\n  <div class=\"card-body filters text-end\" ng-class=\"{showfilters: hideFilter}\" ng-if=\"$ctrl.data.category != 'sentAndDraft'\">\r\n    <div class=\"\">\r\n      <div class=\"filter-buttons\">\r\n        <button class=\"btn btn-xs btn-secondary text-end\" sxy-orderby=\"otherPartyInfo/avatar/displayName\" sxy-text=\"SALAXY.UI_Terms.abc\"></button>\r\n        <button class=\"btn btn-xs btn-secondary text-end\" sxy-orderby=\"endAt\">\r\n          <i class=\"bi bi-calendar3\"></i>\r\n        </button>\r\n        <button ng-if=\"$ctrl.data.category == 'paid' || $ctrl.data.category == 'sent'\" class=\"btn btn-xs btn-secondary text-end\" sxy-orderby=\"status\" sxy-text=\"SALAXY.NG1.CalculationsPanelComponent.status\"></button>\r\n        <button class=\"btn btn-xs btn-secondary text-end\" sxy-orderby=\"grossSalary\">\r\n          €\r\n        </button>\r\n      </div>\r\n      <salaxy-input name=\"search1cp{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search d-none d-sm-inline-block\" label-type=\"plain\">\r\n      </salaxy-input>\r\n    </div>\r\n\r\n  </div>\r\n\r\n  <div ng-class=\"$ctrl.getCssClass()\" ng-if=\"$ctrl.data.category != 'shared' && $ctrl.data.category != 'sentAndDraft' \">\r\n    <div class=\"d-block d-sm-none\">\r\n      <div class=\"table-filter-container-mobile\">\r\n        <salaxy-input name=\"search2cp{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n        </salaxy-input>\r\n      </div>\r\n    </div>\r\n    <div class=\"table-responsive\">\r\n      <table class=\"table\">\r\n        <tbody>\r\n          <tr ng-repeat=\"row in $ctrl.items\">\r\n            <td class=\"td-avatar middle hidden-xxs\">\r\n              <salaxy-avatar ng-if=\"$ctrl.data.category != 'sent'\" avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n              <salaxy-avatar ng-if=\"$ctrl.data.category == 'sent'\" avatar=\"row.ownerInfo.avatar\"></salaxy-avatar>\r\n            </td>\r\n            <td class=\"middle\">\r\n              <strong ng-if=\"$ctrl.data.category != 'sent'\">{{row.otherPartyInfo.avatar.displayName}}</strong>\r\n              <strong ng-if=\"$ctrl.data.category == 'sent'\">{{row.ownerInfo.avatar.displayName}}</strong>\r\n              <br /> {{ row.endAt | date }}\r\n            </td>\r\n            <td class=\"middle right\">\r\n              {{ row.grossSalary | currency }}\r\n              <br />\r\n              <span ng-if=\"row.status != 'workerRequestAccepted' && row.status != 'workerRequestDeclined' && row.status != 'workerRequested' && row.status != 'paymentWorkerCopy'\" class=\"row-status\" ng-class=\"{'text-warning' : row.status == 'paymentStarted', 'text-success' : row.status == 'paymentSucceeded'}\">{{ \"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate }}</span>\r\n              <span ng-if=\"row.status == 'workerRequestAccepted' \" class=\"row-status text-success\" sxy-text=\"SALAXY.NG1.CalculationsPanelComponent.accepted\"></span>\r\n              <span ng-if=\"row.status == 'workerRequestDeclined' \" class=\"row-status text-danger\" sxy-text=\"SALAXY.NG1.CalculationsPanelComponent.declined\"></span>\r\n            </td>\r\n            <td class=\"right middle\">\r\n              <button ng-if=\"$ctrl.data.category == 'draft'\" ng-click=\"$crud.showDetails(row)\" title=\"{{'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm\" ng-class=\"$ctrl.readOnly ? 'btn-secondary' : 'btn-primary'\">\r\n                <i class=\"bi\" ng-class=\"$ctrl.readOnly ? 'bi-file-text' : 'bi-pencil-fill'\"></i>\r\n              </button>\r\n              <button ng-if=\"$ctrl.data.category == 'paid' || $ctrl.data.category == 'sent' || $ctrl.data.category == 'received'\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-secondary\">\r\n                <i class=\"bi bi-file-text\"></i>\r\n              </button>\r\n              <button ng-if=\"$ctrl.data.category == 'paid' && !$ctrl.readOnly\" ng-click=\"$crud.showCopyAsNew(row)\" title=\"{{ 'SALAXY.UI_Terms.copyAsNew' | sxyTranslate}}\" class=\"btn btn-sm btn-secondary\">\r\n                <i class=\"bi bi-copy\"></i>\r\n              </button>\r\n              <a ng-if=\"$ctrl.data.category == 'paid' || $ctrl.data.category == 'sent' || $ctrl.data.category == 'received'\" ng-href=\"{{$crud.getPdfUrl(row)}}\" target=\"_blank\" title=\"{{ 'SALAXY.UI_Terms.printable' | sxyTranslate}}\" class=\"btn btn-sm btn-secondary\">\r\n                <i class=\"bi bi-file-earmark-pdf\"></i>\r\n              </a>\r\n            </td>\r\n\r\n          </tr>\r\n        </tbody>\r\n\r\n      </table>\r\n      <div class=\"salaxy-odata-footer\">\r\n        <salaxy-spinner></salaxy-spinner>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <!-- IF category is Shared -->\r\n  <div ng-class=\"$ctrl.getCssClass()\" ng-if=\"$ctrl.data.category == 'shared' \">\r\n    <div class=\"d-block d-sm-none\">\r\n      <div class=\"table-filter-container-mobile\">\r\n        <salaxy-input name=\"search2cp{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n        </salaxy-input>\r\n      </div>\r\n    </div>\r\n\r\n    <div class=\"table-responsive\">\r\n      <table class=\"table\">\r\n        <tbody>\r\n          <tr ng-repeat=\"row in $ctrl.items\">\r\n            <td class=\"td-avatar middle hidden-xxs\">\r\n              <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n            </td>\r\n            <td class=\"middle\">\r\n              <strong>{{row.otherPartyInfo.avatar.displayName}}</strong>\r\n              <br /> {{ row.endAt | date }}\r\n            </td>\r\n            <td class=\"middle\">\r\n              <span class=\"text-success\" ng-if=\"row.status == 'sharedApproved'\" sxy-text=\"SALAXY.NG1.CalculationsPanelComponent.accepted\"></span>\r\n              <span class=\"text-warning\" ng-if=\"row.status == 'sharedWaiting'\" sxy-text=\"SALAXY.NG1.CalculationsPanelComponent.waiting\" ps=\"...\"></span>\r\n\r\n\r\n            </td>\r\n            <td class=\"middle right\">\r\n              {{ row.grossSalary | currency }}\r\n              <br /> {{ row.payment | currency }}\r\n\r\n            </td>\r\n            <td class=\"right middle\">\r\n              <button ng-if=\"!$ctrl.readOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-primary\">\r\n                <i class=\"bi bi-pencil-fill\"></i>\r\n              </button>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n      <div class=\"salaxy-odata-footer\">\r\n        <salaxy-spinner></salaxy-spinner>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <!-- IF category is Sent or Draft-->\r\n  <div ng-class=\"$ctrl.getCssClass()\" ng-if=\"$ctrl.data.category == 'sentAndDraft'\">\r\n\r\n\r\n    <div class=\"table-responsive\">\r\n      <table class=\"table\">\r\n        <tbody>\r\n          <tr ng-repeat=\"row in $ctrl.items\">\r\n            <td class=\"td-avatar middle hidden-xxs\">\r\n              <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n            </td>\r\n            <td class=\"middle\">\r\n              <strong>{{row.otherPartyInfo.avatar ? row.otherPartyInfo.avatar.displayName : 'SALAXY.UI_Terms.notChosen' | sxyTranslate}}</strong>\r\n              <br /> {{ row.endAt | date }}\r\n            </td>\r\n            <td class=\"middle\">\r\n              <span class=\"text-warning\" ng-if=\"row.status == 'workerRequested'\" sxy-text=\"SALAXY.NG1.CalculationsPanelComponent.sent\"></span>\r\n\r\n              <span ng-if=\"row.status == 'draft'\" sxy-text=\"SALAXY.NG1.CalculationsPanelComponent.draft\"></span>\r\n\r\n            </td>\r\n            <td class=\"middle right\">\r\n              {{ row.grossSalary | currency }}\r\n              <br /> {{ row.payment | currency }}\r\n\r\n            </td>\r\n            <td class=\"right middle\">\r\n              <button ng-if=\"!$ctrl.readOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-primary\">\r\n                <i class=\"bi bi-pencil-fill\"></i>\r\n              </button>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n      <div class=\"salaxy-odata-footer\">\r\n        <salaxy-spinner></salaxy-spinner>\r\n      </div>\r\n    </div>\r\n  </div>\r\n\r\n\r\n\r\n  <!--TODO add binding showAllUrl -->\r\n\r\n  <div class=\"card-footer text-center\">\r\n    <a ng-if=\"$ctrl.data.category != 'received' && $ctrl.data.category != 'sent' && $ctrl.data.category != 'sentAndDraft'\" class=\"btn btn-primary btn-sm\" href=\"#/calc/{{$ctrl.data.category}}\" sxy-text=\"SALAXY.NG1.CalculationsPanelComponent.showWholeList\"></a>\r\n\r\n    <a ng-if=\"$ctrl.data.category == 'sent'\" class=\"btn btn-primary btn-sm\" href=\"#/calc/sent\" sxy-text=\"SALAXY.NG1.CalculationsPanelComponent.sentAlt\"></a>\r\n    <a ng-if=\"$ctrl.data.category == 'sent'\" class=\"btn btn-primary btn-sm\" href=\"#/calc/draft\" sxy-text=\"SALAXY.NG1.CalculationsPanelComponent.drafts\"></a>\r\n    <a ng-if=\"$ctrl.data.category == 'received'\" class=\"btn btn-secondary btn-sm\" href=\"#/calc/paid\" sxy-text=\"SALAXY.NG1.CalculationsPanelComponent.allPaid\"></a>\r\n    <span class=\"\" ng-if=\"$ctrl.data.category == 'sentAndDraft'\">\r\n      <a class=\"btn btn-secondary btn-sm\" href=\"#/calc/sent\" sxy-text=\"SALAXY.NG1.CalculationsPanelComponent.allSent\"></a>\r\n      <a class=\"btn btn-secondary btn-sm\" href=\"#/calc/draft\" sxy-text=\"SALAXY.NG1.CalculationsPanelComponent.allDrafts\"></a>\r\n    </span>\r\n  </div>\r\n\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/CalculationsPaymentStartedPanel.html\",`<div class=\"salaxy-odata-card card list-card with-footer calc-list-card card-sm card-secondary\">\r\n  <div class=\"card-header\">\r\n    {{'SALAXY.NG1.CalcListComponent.panel.paymentStarted.heading' | sxyTranslate}}\r\n  </div>\r\n\r\n  <div ng-class=\"$ctrl.getCssClass()\">\r\n    <div class=\"table-responsive\">\r\n      <table class=\"table table-striped\">\r\n        <tbody>\r\n          <tr ng-repeat=\"row in $ctrl.items\">\r\n            <td class=\"td-avatar  middle\">\r\n              <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n            </td>\r\n            <td class=\"td-name middle\">\r\n              <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.CalcListComponent.notSelected\"></span>\r\n              <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br />\r\n              {{ row.salaryDate | date }}\r\n            </td>\r\n            <td class=\"right\">\r\n              {{ row.grossSalary | currency }}<br />\r\n              <span class=\"text-warning\">{{ \"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate }}</span>              \r\n            </td>\r\n            <td class=\"middle right\">\r\n              <a href=\"\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-secondary\"><i class=\"bi bi-info-circle \"></i></a>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n    <div class=\"card-footer text-center bg-secondary\">\r\n      <salaxy-odata-footer></salaxy-odata-footer>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/CalculationsReceived.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"visible-xxs\">\r\n    <div class=\"table-header-container-mobile\" ng-show=\"!$ctrl.readOnly\">\r\n      <a class=\"btn btn-sm btn-block btn-primary\" href=\"#/calc/details/new\" sxy-text=\"SALAXY.UI_Terms.createNew\"></a>\r\n    </div>\r\n    <div class=\"table-filter-container-mobile\">\r\n      <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n      </salaxy-input>\r\n    </div>\r\n  </div>\r\n  <div class=\"table-responsive light-bg\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\" sxy-orderby=\"otherPartyInfo/avatar/displayName\">\r\n            <span sxy-text=\"SALAXY.NG1_Other.Roles.employer\"></span>\r\n          </th>\r\n          <th class=\"hidden-xxs right\">\r\n            <span sxy-orderby=\"endAt\"><span sxy-text=\"SALAXY.NG1.CalcListComponent.date\"></span></span>\r\n          </th>\r\n          <th class=\"right\">\r\n            <span sxy-orderby=\"grossSalary\"><span sxy-text=\"SALAXY.NG1.CalcListComponent.salary\"></span></span><br />\r\n            <span sxy-orderby=\"payment\"><span sxy-text=\"SALAXY.NG1.CalcListComponent.payment\"></span></span>\r\n          </th>\r\n          <th class=\"right hidden-xxs\" colspan=\"2\">\r\n            <salaxy-odata-actions show-export=\"true\"></salaxy-odata-actions>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar visible-xxs middle\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\">\r\n              <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n            </a>\r\n          </td>\r\n          <td class=\"td-name visible-xxs middle\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\">\r\n              <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.CalcListComponent.notSelected\"></span>\r\n              <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br /> {{ \"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate }}\r\n              <br /> {{ row.endAt | date }}\r\n            </a>\r\n          </td>\r\n          <td class=\"right visible-xxs bottom\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\">\r\n              {{ row.grossSalary | currency }}<br />\r\n              {{ row.data.workerPayment | currency }}\r\n            </a>\r\n          </td>\r\n          <td class=\"td-avatar hidden-xxs middle\">\r\n            <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"td-name hidden-xxs middle\">\r\n            <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.CalcListComponent.notSelected\"></span>\r\n            <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br />\r\n            <a href=\"mailto:{{row.otherPartyInfo.email}}\">{{row.otherPartyInfo.email}}</a><br /> Puh: {{row.otherPartyInfo.telephone || \"-\"}}<br />\r\n          </td>\r\n          <td class=\"hidden-xxs middle right\">\r\n            {{ row.endAt | date }}\r\n          </td>\r\n          <td class=\"right hidden-xxs middle\">\r\n            {{ row.grossSalary | currency }}<br /> {{ row.data.workerPayment | currency }}\r\n          </td>\r\n          <td class=\"hidden-xxs middle\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n              <i class=\"bi bi-info-circle d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n            </a>\r\n          </td>\r\n          <td class=\"hidden-xxs middle\">\r\n            <a ng-href=\"{{$crud.getPdfUrl(row)}}\" target=\"_blank\" title=\"{{ 'SALAXY.UI_Terms.printable' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n              <i class=\"bi bi-file-earmark-pdf\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" pre=\" \" sxy-text=\"SALAXY.UI_Terms.printable\"></span>\r\n            </a>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/CalculationsRepairs.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"visible-xxs\">\r\n    <div class=\"table-filter-container-mobile\">\r\n      <salaxy-input name=\"search1x{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n      </salaxy-input>\r\n    </div>\r\n  </div>\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\">\r\n            <span sxy-orderby=\"otherPartyInfo/avatar/displayName\" sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span>\r\n          </th>\r\n          <th class=\"hidden-xxs\" sxy-if-role=\"!worker\">\r\n            <span sxy-text=\"SALAXY.NG1.CalcListComponent.status.title\"></span><br />\r\n            <span sxy-orderby=\"salaryDate\"><span sxy-text=\"SALAXY.NG1.CalculationsWithSalaryDateSelectComponent.salaryDate\"></span></span>\r\n          </th>\r\n          <th class=\"right \">\r\n            <span sxy-orderby=\"grossSalary\"><span sxy-text=\"SALAXY.NG1.CalcListComponent.salary\" ></span></span><br />\r\n          </th>\r\n          <th class=\"right hidden-xxs\" colspan=\"2\">\r\n            <salaxy-odata-actions></salaxy-odata-actions>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar visible-xxs middle\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\">\r\n              <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n            </a>\r\n          </td>\r\n          <td class=\"td-name visible-xxs middle\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\">\r\n              <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.CalcListComponent.notSelected\"></span>\r\n              <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br /> {{ \"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate }}\r\n              <br />{{ row.salaryDate | date }}\r\n            </a>\r\n          </td>\r\n          <td class=\"right visible-xxs bottom\" ng-click=\"$crud.showDetails(row)\">\r\n\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\">\r\n              {{ row.grossSalary | currency }}\r\n            </a>\r\n          </td>\r\n          <td class=\"td-avatar hidden-xxs middle\">\r\n            <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"td-name hidden-xxs middle\">\r\n            <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.CalcListComponent.notSelected\"></span>\r\n            <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br />\r\n          </td>\r\n          <td class=\"hidden-xxs middle\">\r\n            {{ \"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate }}<br /> {{ row.salaryDate | date }}\r\n          </td>\r\n          <td class=\"right hidden-xxs middle\">\r\n            {{ row.grossSalary | currency }}\r\n          </td>\r\n          <td class=\"hidden-xxs middle\" colspan=\"{{$ctrl.readOnly ? 2 : 1}}\">\r\n            <button ng-if=\"!row.isReadOnly && !$ctrl.readOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-primary btn-block\">\r\n              <span class=\"hidden-xs\" sxy-text=\"SALAXY.UI_Terms.edit\"></span>\r\n            </button>\r\n            <button ng-if=\"!row.isReadOnly && $ctrl.readOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n              <span class=\"hidden-xs\" sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n            </button>\r\n          </td>\r\n          <td class=\"hidden-xxs middle\" ng-if=\"!$ctrl.readOnly\">\r\n            <button ng-click=\"$crud.delete(row)\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\" class=\"btn btn-sm btn-danger btn-block\">\r\n              <span class=\"hidden-xs\" sxy-text=\"SALAXY.UI_Terms.delete\"></span></button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/CalculationsSent.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"visible-xxs\">\r\n    <div class=\"table-header-container-mobile\">\r\n      <a class=\"btn btn-sm btn-block btn-primary\" href=\"#/calc/details/new\" sxy-text=\"SALAXY.UI_Terms.createNew\"></a>\r\n    </div>\r\n    <div class=\"table-filter-container-mobile\">\r\n      <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n      </salaxy-input>\r\n    </div>\r\n  </div>\r\n  <div class=\"table-responsive light-bg\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\" sxy-orderby=\"otherPartyInfo/avatar/displayName\">\r\n            <span sxy-text=\"SALAXY.NG1_Other.Roles.employer\"></span>\r\n          </th>\r\n          <th class=\"hidden-xxs\">\r\n            <span sxy-orderby=\"status\"><span sxy-text=\"SALAXY.NG1.CalcListComponent.status.title\"></span></span><br />\r\n            <span sxy-orderby=\"endAt\"><span sxy-text=\"SALAXY.NG1.CalcListComponent.payment\" ></span></span>\r\n          </th>\r\n          <th class=\"right \">\r\n            <span sxy-orderby=\"grossSalary\"><span sxy-text=\"SALAXY.NG1.CalcListComponent.salary\" ></span></span><br />\r\n            <span sxy-orderby=\"payment\"><span sxy-text=\"SALAXY.NG1.CalcListComponent.payment\" ></span></span>\r\n          </th>\r\n          <th class=\"right hidden-xxs\" colspan=\"2\">\r\n            <div class=\"table-filter-container\">\r\n              <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" class=\"salaxy-odata-table-search\" placeholder=\"SALAXY.UI_Terms.textSearch\" label-type=\"plain\"></salaxy-input>\r\n            </div>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar visible-xxs middle\">\r\n\r\n            <a ng-click=\"$crud.showDetails(row)\">\r\n              <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n            </a>\r\n          </td>\r\n          <td class=\"td-name visible-xxs middle\">\r\n            <a ng-click=\"$crud.showDetails(row)\">\r\n              <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"(Ei työnantajaa)\"></span>\r\n              <strong>{{row.otherPartyInfo.avatar.displayName}}</strong>\r\n              <br /> {{ \"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate }}\r\n              <br /> {{row.endAt | date}}\r\n            </a>\r\n          </td>\r\n          <td class=\"right visible-xxs bottom\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\">\r\n              {{ row.grossSalary | currency }}\r\n              <br />\r\n              {{ row.payment | currency }}\r\n            </a>\r\n          </td>\r\n          <td class=\"td-avatar hidden-xxs middle\">\r\n\r\n            <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"td-name hidden-xxs middle\">\r\n            <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.CalculationsSentComponent.noEmployee\"></span>\r\n            <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br />\r\n          </td>\r\n          <td class=\"hidden-xxs middle\">\r\n            <span ng-if=\"row.status == 'workerRequested'\" class=\"text-warning\" sxy-text=\"SALAXY.NG1.CalculationsSentComponent.waitingForAcception\" ps=\"...\"></span>\r\n            <span ng-if=\"row.status == 'workerRequestDeclined'\" class=\"text-danger\" sxy-text=\"SALAXY.NG1.CalculationsSentComponent.declined\"></span>\r\n            <span ng-if=\"row.status == 'workerRequestAccepted'\" class=\"text-success\" sxy-text=\"SALAXY.NG1.CalculationsSentComponent.accepted\"></span>\r\n            <br /> {{row.endAt | date}}\r\n          </td>\r\n          <td class=\"right hidden-xxs middle\">\r\n            {{ row.grossSalary | currency }}<br /> {{ row.payment | currency }}\r\n          </td>\r\n          <td class=\"hidden-xxs middle\">\r\n            <button ng-click=\"$crud.showDetails(row)\" ng-if=\"row.status == 'draft'\" class=\"btn btn-sm btn-primary btn-block\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\">\r\n              <i class=\"bi bi-pencil-fill d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.edit\"></span>\r\n            </button>\r\n            <button ng-click=\"$crud.showDetails(row)\" ng-if=\"row.status != 'draft'\" class=\"btn btn-sm btn-default btn-block\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\">\r\n              <i class=\"bi bi-info-circle d-inline-block d-sm-none\"></i></a>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.show\" ng-if=\"!row.data.payrollId\"></span>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.NG1.CalcListComponent.calculation\" ng-if=\"row.data.payrollId\"></span>\r\n            </button>\r\n          </td>\r\n          <td class=\"hidden-xxs middle\">\r\n            <button ng-if=\"row.status == 'draft'\" ng-click=\"$crud.delete(row)\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\" class=\"btn btn-sm btn-danger btn-block\">\r\n              <i class=\"bi bi-trash-fill d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.delete\"></span></button>\r\n            <button ng-if=\"!row.data.payrollId && (row.status == 'paymentSucceeded' || row.status == 'paymentStarted')\" ng-click=\"$crud.showCopyAsNew(row)\" class=\"btn btn-sm btn-default btn-block\" title=\"{{ 'SALAXY.UI_Terms.copyAsNew' | sxyTranslate}}\">\r\n              <i class=\"bi bi-copy d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.copyAsNew\"></span>\r\n            </button>\r\n            <a ng-if=\"row.data.payrollId\" class=\"btn btn-sm btn-primary btn-block\" ng-href=\"#/payroll/details/{{ row.data.payrollId }}\">\r\n              <i class=\"bi bi-list-task d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.NG1.CalcListComponent.payroll\"></span>\r\n            </a>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/CalculationsShared.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"visible-xxs\">\r\n\r\n    <div class=\"table-filter-container-mobile\">\r\n      <salaxy-input name=\"search1x{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n      </salaxy-input>\r\n    </div>\r\n  </div>\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\" sxy-orderby=\"otherPartyInfo/avatar/displayName\">\r\n            <span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span>\r\n          </th>\r\n          <th class=\"hidden-xxs\">\r\n            <span sxy-text=\"SALAXY.NG1.CalcListComponent.status.title\"></span><br />\r\n            <span sxy-orderby=\"endAt\"><span sxy-text=\"SALAXY.NG1.CalcListComponent.date\"></span></span>\r\n          </th>\r\n          <th class=\"right \">\r\n            <span sxy-orderby=\"grossSalary\"><span sxy-text=\"SALAXY.NG1.CalcListComponent.salary\" ></span></span><br />\r\n            <span sxy-orderby=\"payment\"><span sxy-text=\"SALAXY.NG1.CalcListComponent.payment\" ></span></span>\r\n          </th>\r\n          <th class=\"right hidden-xxs\">\r\n            <salaxy-odata-actions show-export=\"true\"></salaxy-odata-actions>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar visible-xxs middle\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\">\r\n              <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n            </a>\r\n          </td>\r\n          <td class=\"td-name visible-xxs middle\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\">\r\n              <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.CalcListComponent.notSelected\"></span>\r\n              <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br />\r\n\r\n              <span ng-switch=\"row.status\">\r\n               \r\n              <span ng-switch-when=\"sharedApproved\" class=\"status text-success small\" sxy-text=\"SALAXY.NG1.CalculationsSharedComponent.accepted\"></span>\r\n              <span ng-switch-when=\"sharedWaiting\" class=\"status text-warning small\" sxy-text=\"SALAXY.NG1.CalculationsSharedComponent.waitingForHandling\"></span>\r\n              <span ng-switch-when=\"sharedRejected\" class=\"status text-danger small\" sxy-text=\"SALAXY.NG1.CalculationsSharedComponent.declined\"></span>\r\n              <br />{{ row.endAt | date }}\r\n            </a>\r\n          </td>\r\n          <td class=\"right visible-xxs bottom\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\">\r\n              {{ row.grossSalary | currency }}<br />\r\n              {{ row.payment | currency }}\r\n            </a>\r\n          </td>\r\n          <td class=\"td-avatar hidden-xxs middle\">\r\n            <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"td-name hidden-xxs middle\">\r\n            <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.CalcListComponent.notSelected\"></span>\r\n            <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br />\r\n          </td>\r\n          <td class=\"hidden-xxs middle\">\r\n            <span ng-switch=\"row.status\">\r\n              <span ng-switch-when=\"sharedWaiting\" class=\"status text-warning small\" sxy-text=\"SALAXY.NG1.CalculationsSharedComponent.waitingForHandling\"></span>\r\n            <span ng-switch-when=\"sharedApproved\" class=\"status text-success small\" sxy-text=\"SALAXY.NG1.CalculationsSharedComponent.accepted\"></span>\r\n            \r\n            <span ng-switch-when=\"sharedRejected\" class=\"status text-danger small\" sxy-text=\"SALAXY.NG1.CalculationsSharedComponent.declined\"></span>\r\n            <br /> {{ row.endAt | date }}\r\n          </td>\r\n          <td class=\"right hidden-xxs middle\">\r\n            {{ row.grossSalary | currency }}<br /> {{ row.payment | currency }}\r\n          </td>\r\n          <td class=\"middle right\">\r\n            <button ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-secondary\">\r\n              <i class=\"bi bi-info-circle d-inline-block d-sm-none\"></i><span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n            </button>\r\n          </td>\r\n          <!-- <td class=\"hidden-xxs middle\">\r\n            <button ng-click=\"$crud.delete(row)\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\" class=\"btn btn-sm btn-danger btn-block\"><i\r\n                class=\"bi bi-trash-fill d-inline-block d-sm-none\"></i><span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.delete\"></span></button>\r\n          </td>-->\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/CalculationsWithSalaryDate-select.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"visible-xxs\">\r\n    <div class=\"table-filter-container-mobile\">\r\n      <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n      </salaxy-input>\r\n    </div>\r\n  </div>\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\">\r\n            <span sxy-orderby=\"otherPartyInfo/avatar/displayName\" sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span>\r\n            <span class=\"label label-primary clickable\" ng-if=\"$ctrl.selectedItems.length\" ng-click=\"$ctrl.selectedItems.splice(0,$ctrl.selectedItems.length)\"> {{'SALAXY.UI_Terms.chosen' | sxyTranslate}}: {{ $ctrl.selectedItems.length }} <i class=\"bi bi-x-circle\"></i></span>\r\n          </th>\r\n          <th class=\"hidden-xxs\">\r\n            <span sxy-text=\"SALAXY.NG1.CalcListComponent.status.title\"></span><br />\r\n            <span sxy-orderby=\"salaryDate\"><span sxy-text=\"SALAXY.NG1.CalculationsWithSalaryDateSelectComponent.salaryDate\"></span></span>\r\n          </th>\r\n          <th class=\"hidden-xxs\">\r\n            <span sxy-text=\"SALAXY.NG1.CalculationsWithSalaryDateSelectComponent.start\"></span><br />\r\n            <span sxy-text=\"SALAXY.NG1.CalculationsWithSalaryDateSelectComponent.end\"></span>\r\n          </th>\r\n          <th class=\"right hidden-xxs\" colspan=\"2\">\r\n            <div class=\"table-filter-container\">\r\n              <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" class=\"salaxy-odata-table-search\" placeholder=\"SALAXY.UI_Terms.textSearch\" label-type=\"plain\"></salaxy-input>\r\n            </div>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar visible-xxs middle\">\r\n            <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"td-name visible-xxs middle\">\r\n            <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.CalcListComponent.notSelected\"></span>\r\n            <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br /> {{ \"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate }}\r\n            <br /> {{ row.salaryDate | date }}\r\n          </td>\r\n          <td class=\"right visible-xxs bottom\">\r\n            <a href=\"\" ng-click=\"$crud.showDetails(row)\">\r\n              {{ row.grossSalary | currency }}<br />\r\n              {{ row.payment | currency }}\r\n            </a>\r\n          </td>\r\n          <td class=\"td-avatar hidden-xxs middle\">\r\n            <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"td-name hidden-xxs middle\">\r\n            <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.CalcListComponent.notSelected\"></span>\r\n            <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br />\r\n          </td>\r\n          <td class=\"hidden-xxs middle\">\r\n            {{ row.status ? (\"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate) : \"#ERR\" }}<br /> {{ row.salaryDate | date }}\r\n          </td>\r\n          <td class=\"hidden-xxs middle\">\r\n            {{ row.data.workStartDate | date}}<br /> {{ row.data.workEndDate | date }}\r\n          </td>\r\n          <td class=\"right hidden-xxs middle\">\r\n            {{ row.grossSalary | currency }}<br /> {{ row.payment | currency }}\r\n          </td>\r\n          <td class=\"right middle\">\r\n            <button class=\"btn btn-sm\" type=\"button\" ng-class=\"$ctrl.isSelected(row) ? 'btn-danger' : 'btn-info'\" ng-click=\"$ctrl.setSelected(row, 'toggle')\">\r\n              {{ $ctrl.isSelected(row) ? ('SALAXY.UI_Terms.unselect' | sxyTranslate) : ('SALAXY.UI_Terms.select' | sxyTranslate) }}\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/CalculationsWorker.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n\r\n  <div class=\"visible-xxs\">\r\n    <div class=\"table-header-container-mobile\" ng-show=\"!$ctrl.readOnly\">\r\n      <a class=\"btn btn-sm btn-block btn-primary\" href=\"#/calc/details/new\" sxy-text=\"SALAXY.UI_Terms.createNew\"></a>\r\n    </div>\r\n    <div class=\"table-filter-container-mobile\">\r\n      <salaxy-input name=\"searchMobile{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n      </salaxy-input>\r\n    </div>\r\n  </div>\r\n  <div id=\"calculations-worker-table\" class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th>\r\n            <span sxy-orderby=\"status\">\r\n              <span sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.calculationsWorker.status\"></span>\r\n            </span>\r\n            <br />\r\n            <span sxy-orderby=\"endAt\">\r\n              <span sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.calculationsWorker.date\"></span>\r\n            </span>\r\n          </th>\r\n          <th></th>\r\n          <th class=\"right\">\r\n            <span sxy-orderby=\"grossSalary\"><span sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.calculationsWorker.salary\"></span></span><br />\r\n            <span sxy-orderby=\"payment\"><span sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.calculationsWorker.payment\"></span></span>\r\n          </th>\r\n          <th class=\"right\" colspan=\"{{$ctrl.readOnly ? 2 : 3}}\">\r\n            <salaxy-odata-actions show-export=\"true\"></salaxy-odata-actions>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td>\r\n            {{ \"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate }}\r\n            <br /> {{ (row.salaryDate || row.endAt) | date}}\r\n          </td>\r\n          <td>\r\n            <div ng-if=\"$ctrl.logic.isNotCurrentEmployment(row)\">\r\n              Ei tämä työsuhde!<br />\r\n              <a ng-href=\"#/employments/details/{{ row.data.employmentId }}\" class=\"btn btn-xs btn-default\">Näytä työsuhde...</a>\r\n            </div>\r\n          </td>\r\n          <td class=\"right\">\r\n            {{ row.grossSalary | currency }}\r\n            <br /> {{ row.payment | currency }}\r\n          </td>\r\n          <td class=\"middle\">\r\n            <button ng-click=\"$crud.showDetails(row)\" ng-if=\"row.status == 'draft'\" class=\"btn btn-sm btn-block\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" ng-class=\"$ctrl.readOnly ? 'btn-default' : 'btn-primary'\">\r\n              <i class=\"bi d-inline-block d-sm-none\" ng-class=\"$ctrl.readOnly ? 'bi-info-lg' : 'bi-pencil-fill'\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.edit\" ng-if=\"!$ctrl.readOnly\"></span>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.show\" ng-if=\"$ctrl.readOnly\"></span>\r\n            </button>\r\n            <button ng-click=\"$crud.showDetails(row)\" ng-if=\"row.status != 'draft'\" class=\"btn btn-sm btn-default btn-block\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\">\r\n              <i class=\"bi bi-info-circle d-inline-block d-sm-none\"></i></a>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.show\" ng-if=\"!row.data.payrollId\"></span>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.calculationsWorker.calculation\" ng-if=\"row.data.payrollId\"></span>\r\n            </button>\r\n            \r\n          </td>\r\n          <td class=\"middle\" ng-if=\"!$ctrl.readOnly\">\r\n            <button ng-if=\"row.status == 'draft' || row.status == 'history'\" ng-click=\"$crud.delete(row)\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\" class=\"btn btn-sm btn-danger btn-block\">\r\n              <i class=\"bi bi-trash-fill d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.delete\"></span>\r\n            </button>\r\n            <button ng-if=\"!row.data.payrollId && (row.status == 'paymentSucceeded' || row.status == 'paymentStarted') && ('employments.calcs.copyAsNew' | sxyShow: 'workers.details')\" ng-click=\"$crud.showCopyAsNew(row)\" class=\"btn btn-sm btn-default btn-block\" title=\"{{ 'SALAXY.UI_Terms.copyAsNew' | sxyTranslate}}\">\r\n              <i class=\"bi bi-copy d-inline-block d-sm-none\"></i><span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.copyAsNew\"></span>\r\n            </button>\r\n            <a ng-if=\"row.data.payrollId\" class=\"btn btn-sm btn-primary btn-block\" ng-href=\"#/payroll/details/{{ row.data.payrollId }}\">\r\n              <i class=\"bi bi-list-task d-inline-block d-sm-none text-white\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.calculationsWorker.payroll\"></span>\r\n            </a>\r\n          </td>\r\n          <td class=\"middle\">\r\n            <a ng-href=\"{{$crud.getPdfUrl(row)}}\" target=\"_blank\" title=\"{{ 'SALAXY.UI_Terms.printable' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n              <i class=\"bi bi-file-earmark-pdf d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.printable\"></span>\r\n            </a>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/calendar/Events.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <table class=\"table\">\r\n    <thead>\r\n      <tr>\r\n        <th sxy-text=\"SALAXY.NG1.ODataCalendarEventComponent.description\"></th>\r\n        <th sxy-text=\"SALAXY.NG1.ODataCalendarEventComponent.categories\"></th>\r\n        <th sxy-orderby=\"logicalDate\" sxy-text=\"SALAXY.NG1.ODataCalendarEventComponent.period\"></th>\r\n        <th sxy-text=\"SALAXY.NG1.ODataCalendarEventComponent.duration\"></th>\r\n        <th>\r\n        </th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat=\"row in $ctrl.items\">\r\n        <td>{{ row.shortText }}</td>\r\n        <td><small ng-repeat=\"cat in row.flags\">{{ cat + ($last ? \"\" : \", \") }}</small></td>\r\n        <td>{{ row.data | sxyDateRange }}</td>\r\n        <td>{{ row.data.duration | sxyDuration }}</td>\r\n        <td>\r\n            <button ng-if=\"!row.isReadOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-primary btn-block\">\r\n              <i class=\"bi bi-pencil-fill d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.edit\"></span>\r\n            </button>\r\n            <button ng-if=\"row.isReadOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n              <i class=\"bi bi-info-circle d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n            </button>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/CustomerInvoices.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <table class=\"table\">\r\n    <thead>\r\n      <tr>\r\n        <th sxy-orderby=\"id\" sxy-text=\"SALAXY.NG1.ApiCrudObjectComponent.id\"></th>\r\n        <th sxy-orderby=\"createdAt\"  sxy-text=\"SALAXY.UI_Terms.created\"></th>\r\n        <th sxy-orderby=\"updatedAt\" sxy-text=\"SALAXY.UI_Terms.updated\"></th>\r\n        <th sxy-orderby=\"owner\" sxy-text=\"SALAXY.NG1.ApiCrudObjectComponent.owner\"></th>\r\n        <th sxy-orderby=\"isReadOnly\" sxy-text=\"SALAXY.NG1.ApiCrudObjectComponent.readOnly\"></th>\r\n        <th sxy-orderby=\"partner\" sxy-text=\"SALAXY.NG1.ApiCrudObjectComponent.partner\"></th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat=\"row in $ctrl.items\">\r\n        <td>{{ row.id }}</td>\r\n        <td>{{ row.createdAt | sxyDate }}</td>\r\n        <td>{{ row.updatedAt | sxyDate }}</td>\r\n        <td>{{ row.owner }}</td>\r\n        <td>{{ row.isReadOnly }}</td>\r\n        <td>{{ row.partner }}</td>\r\n        <td class=\"middle hidden-xxs\">\r\n          <button ng-if=\"!row.isReadOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-primary btn-block\">\r\n            <i class=\"bi bi-pencil-fill d-inline-block d-sm-none\"></i>\r\n            <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.edit\"></span>\r\n          </button>\r\n          <button ng-if=\"row.isReadOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n            <i class=\"bi bi-info-circle d-inline-block d-sm-none\"></i>\r\n            <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n          </button>\r\n        </td>\r\n        <td class=\"middle hidden-xxs\">\r\n          <button ng-if=\"!row.isReadOnly\" ng-click=\"$crud.delete(row)\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\" class=\"btn btn-sm btn-danger btn-block\">\r\n            <i class=\"bi bi-trash-fill d-inline-block d-sm-none\"></i>\r\n            <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.delete\"></span>\r\n          </button>\r\n          <button ng-if=\"row.isReadOnly\" ng-click=\"$crud.showCopyAsNew(row)\" title=\"{{ 'SALAXY.UI_Terms.copyAsNew' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n            <i class=\"bi bi-copy d-inline-block d-sm-none\"></i>\r\n            <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.copyAsNew\"></span>\r\n          </button>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/Datasets.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <table class=\"table\">\r\n    <thead>\r\n      <tr>\r\n        <th sxy-orderby=\"shortText\" sxy-text=\"Teksti\"></th>\r\n        <th class=\"right\">\r\n          <div sxy-orderby=\"createdAt\" sxy-text=\"SALAXY.UI_Terms.created\"></div>\r\n          <div sxy-orderby=\"updatedAt\" sxy-text=\"SALAXY.UI_Terms.updated\"></div>\r\n        </th>\r\n        <th sxy-orderby=\"isReadOnly\" sxy-text=\"SALAXY.NG1.ApiCrudObjectComponent.readOnly\"></th>\r\n        <th class=\"right hidden-xxs\" colspan=\"2\">\r\n          <div class=\"table-filter-container\">\r\n            <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" class=\"salaxy-odata-table-search\" placeholder=\"SALAXY.UI_Terms.textSearch\" label-type=\"plain\"></salaxy-input>\r\n          </div>\r\n        </th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat=\"row in $ctrl.items\">\r\n        <td>{{ row.shortText }}</td>\r\n        <td class=\"right\">\r\n          <div>{{ row.createdAt | sxyDate }}</div>\r\n          <div>{{ row.updatedAt | sxyDate }}</div>\r\n        </td>\r\n        <td>{{ row.isReadOnly }}</td>\r\n        <td class=\"middle hidden-xxs\">\r\n          <button ng-if=\"!row.isReadOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-primary btn-block\">\r\n            <i class=\"bi bi-pencil-fill d-inline-block d-sm-none\"></i>\r\n            <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.edit\"></span>\r\n            </button>\r\n          <button ng-if=\"row.isReadOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n            <i class=\"bi bi-info-circle d-inline-block d-sm-none\"></i>\r\n            <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n          </button>\r\n        </td>\r\n        <td class=\"middle hidden-xxs\">\r\n          <button ng-if=\"!row.isReadOnly\" ng-click=\"$crud.delete(row)\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\" class=\"btn btn-sm btn-danger btn-block\"><i\r\n              class=\"bi bi-trash-fill d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.delete\"></span>\r\n          </button>\r\n          <button ng-if=\"row.isReadOnly\" ng-click=\"$crud.showCopyAsNew(row)\" title=\"{{ 'SALAXY.UI_Terms.copyAsNew' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n            <i class=\"bi bi-copy d-inline-block d-sm-none\"></i>\r\n            <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.copyAsNew\"></span>\r\n          </button>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/EarningsPayments.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\" class=\"hidden-xxs\">\r\n            <span sxy-orderby=\"otherPartyInfo/avatar/displayName\" class=\"clickable\"><span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span><i ng-if=\"$odata.getColumnOrder('avatar/displayName')\" class=\"bi bi-sort-{{ $odata.getColumnOrder('avatar/displayName') }}\"\r\n              aria-hidden=\"true\"></i></span>\r\n          </th>\r\n          <th class=\"visible-xxs\">\r\n            <span sxy-orderby=\"otherPartyInfo/avatar/displayName\" class=\"clickable\"><span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span><i ng-if=\"$odata.getColumnOrder('avatar/displayName')\" class=\"bi bi-sort-{{ $odata.getColumnOrder('avatar/displayName') }}\"\r\n              aria-hidden=\"true\"></i></span>\r\n          </th>\r\n          <th>\r\n            <span sxy-orderby=\"status\" class=\"clickable\"><span sxy-text=\"Tila\"></span></span>\r\n          </th>\r\n          <th class=\"right\">\r\n            <span sxy-orderby=\"payment\" class=\"clickable\"><span sxy-text=\"Maksu\"></span></span>\r\n\r\n          </th>\r\n          <th class=\"right\">\r\n            <span sxy-orderby=\"startAt\" class=\"clickable\"><span sxy-text=\"Kausi\"></span></span>\r\n          </th>\r\n          <th class=\"right\">\r\n            <div class=\"table-filter-container\">\r\n              <salaxy-input name=\"searchx{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"sort-by-text\" label-type=\"plain\">\r\n              </salaxy-input>\r\n            </div>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar middle hidden-xxs\">\r\n            <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"td-name middle\">\r\n            <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\">{{ 'SALAXY.NG1.CalcListComponent.notSelected' | sxyTranslate }}</span>\r\n            <strong>{{row.otherPartyInfo.avatar.displayName}}</strong>\r\n          </td>\r\n          <td class=\"middle td-status\">\r\n            <span ng-if=\"row.status == 'new'\" class=\"text-warning small status\">\r\n                Käsitelyssä\r\n            </span>\r\n            <span ng-if=\"row.status == 'succeeded'\" class=\"text-success small status\">\r\n                Hyväksytty\r\n            </span>\r\n            <span ng-if=\"row.status == 'cancelled'\" class=\"text-danger small status\">\r\n                Hylätty\r\n            </span>\r\n          </td>\r\n          <td class=\"middle right\">\r\n            {{row.payment | currency}}<br>\r\n            <span class=\"small\">{{ row.endAt | date }}</span>\r\n          </td>\r\n          <td class=\"right\">{{row.startAt | date}} - <br>{{row.endAt | date}}</td>\r\n          <td class=\"middle right\">\r\n            <a ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-secondary\"><i\r\n              class=\"bi bi-info-circle visible-xxs\"></i><span class=\"hidden-xxs\">Näytä</span></a>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/EarningsPaymentsPanel.html\",`<div class=\"card salaxy-odata-card list-card report-list-card  card-sm card-secondary\">\r\n  <div class=\"card-header\">\r\n    {{('Tulorekisteri-ilmoitukset' | sxyTranslate) }}\r\n    <div class=\"float-end\" ng-show=\"$ctrl.items.length > 0\">\r\n      <button class=\"btn btn-secondary btn-xs\" ng-click=\"hideFilter = !hideFilter\" title=\"Näytä suodattimet\">\r\n        <i class=\"bi bi-funnel-fill\"></i>\r\n      </button>\r\n    </div>\r\n  </div>\r\n  <div class=\"card-body filters text-end\" ng-class=\"{'showfilters' : hideFilter}\">\r\n    <div class=\"filter-buttons\">\r\n      <button class=\"btn btn-xs btn-secondary text-end\" sxy-orderby=\"otherPartyInfo/avatar/displayName\" sxy-text=\"SALAXY.UI_Terms.abc\"></button>\r\n      <button class=\"btn btn-xs btn-secondary text-end\" sxy-orderby=\"status\"> Tila</button>\r\n      <button class=\"btn btn-xs btn-secondary text-end\" sxy-orderby=\"endAt\">\r\n        <i class=\"bi bi-calendar3\"></i>\r\n      </button>\r\n      <button class=\"btn btn-xs btn-secondary text-end\" sxy-orderby=\"payment\">€</button>\r\n    </div>\r\n    <salaxy-input name=\"search1cp{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search hidden-xxs\" label-type=\"plain\">\r\n    </salaxy-input>\r\n  </div>\r\n  <div ng-class=\"$ctrl.getCssClass()\">\r\n    <div class=\"visible-xxs\" ng-if=\"$ctrl.items.length > 0\">\r\n      <div class=\"table-filter-container-mobile\">\r\n        <salaxy-input name=\"search2cp{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n        </salaxy-input>\r\n      </div>\r\n    </div>\r\n    <div class=\"card-body text-center card-content lg-height align-middle\" ng-show=\"$ctrl.items.length == 0 && !$ctrl.isLoading\">\r\n      <div>\r\n        <h3>Ei Tulorekisteri-ilmoituksia</h3>\r\n      </div>\r\n    </div>\r\n    <div class=\"table-responsive\">\r\n      <table class=\"table\" ng-if=\"$ctrl.items.length > 0\">\r\n        <tbody>\r\n          <tr ng-repeat=\"row in $ctrl.items\">\r\n            <td class=\"d-none\"><pre class=\"small\">{{row | json}}</pre></td>\r\n            <td class=\"td-avatar middle hidden-xxs\">\r\n              <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n            </td>\r\n            <td class=\"td-name middle\">\r\n              <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\">{{ 'SALAXY.NG1.CalcListComponent.notSelected' | sxyTranslate }}</span>\r\n              <strong>{{row.otherPartyInfo.avatar.displayName}}</strong>\r\n            </td>\r\n            <td class=\"middle td-status\">\r\n              <span ng-if=\"row.status == 'new'\" class=\"text-warning small status\">\r\n                Käsitelyssä\r\n              </span>\r\n              <span ng-if=\"row.status == 'succeeded'\" class=\"text-success small status\">\r\n                Hyväksytty\r\n              </span>\r\n              <span ng-if=\"row.status == 'cancelled'\" class=\"text-danger small status\">\r\n                Hylätty\r\n              </span>\r\n            </td>\r\n            <td class=\"middle right\">\r\n              {{row.payment | currency}}<br>\r\n              <span class=\"small\">{{ row.endAt | date }}</span>\r\n            </td>\r\n\r\n            <td class=\"middle right\">\r\n              <a ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-secondary\"><i\r\n              class=\"bi bi-info-circle\"></i></a>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n      <div class=\"salaxy-odata-footer\">\r\n        <salaxy-spinner></salaxy-spinner>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div class=\"card-footer text-center\">\r\n    <a ng-href=\"#{{$crud.getDefaults().listUrl}}\" class=\"btn btn-primary btn-sm\">Näytä kaikki</a> {{$crud.listUrl}}\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/Employments-select.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"btn-toolbar\" role=\"toolbar\">\r\n    <div class=\"btn-group btn-group-sm dropdown\">\r\n      <button id=\"single-button2\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\" ng-disabled=\"disabled\">\r\n       {{'SALAXY.NG1.WorkerListComponent.employments' | sxyTranslate}}:\r\n       {{ ($ctrl.url == '/v03/api/employments' ? 'SALAXY.NG1.WorkerListComponent.all' : 'SALAXY.NG1.WorkerListComponent.active') | sxyTranslate }}\r\n      </button>\r\n      <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"single-button2\">\r\n        <li role=\"menuitem\">\r\n          <a href=\"\" ng-click=\"$ctrl.setUrl('/v03/api/employments')\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.WorkerListComponent.all\"></a>\r\n        </li>\r\n        <li role=\"menuitem\">\r\n          <a href=\"\" ng-click=\"$ctrl.setUrl('/v03/api/employments?activeDate=today')\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.WorkerListComponent.active\"></a>\r\n        </li>\r\n      </ul>\r\n    </div>\r\n    <button ng-if=\"$ctrl.selectMode === 'multiselect'\" ng-click=\"$ctrl.selectAll()\" class=\"btn btn-default btn-sm\" sxy-text=\"SALAXY.NG1.WorkerListComponent.selectAll\"></button>\r\n  </div>\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr class=\"\">\r\n          <th class=\"d-sm-none\">\r\n            <span sxy-orderby=\"otherPartyInfo/avatar/displayName\" class=\"clickable\"><span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span><i ng-if=\"$odata.getColumnOrder('avatar/displayName')\" class=\"bi bi-sort-{{ $odata.getColumnOrder('avatar/displayName') }}\"\r\n              aria-hidden=\"true\"></i></span>\r\n            <span class=\"label label-primary clickable\" ng-if=\"$ctrl.selectedItems.length\" ng-click=\"$ctrl.selectedItems.splice(0,$ctrl.selectedItems.length)\"> {{'SALAXY.UI_Terms.chosen' | sxyTranslate}}: {{ $ctrl.selectedItems.length }} <i class=\"bi bi-x-circle\"></i></span>\r\n          </th>\r\n          <th colspan=\"2\" class=\"d-none d-sm-table-cell\">\r\n            <span sxy-orderby=\"otherPartyInfo/avatar/displayName\" class=\"clickable\"><span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span><i ng-if=\"$odata.getColumnOrder('avatar/displayName')\" class=\"bi bi-sort-{{ $odata.getColumnOrder('avatar/displayName') }}\"\r\n              aria-hidden=\"true\"></i></span>\r\n            <span class=\"label label-primary clickable\" ng-if=\"$ctrl.selectedItems.length\" ng-click=\"$ctrl.selectedItems.splice(0,$ctrl.selectedItems.length)\"> {{'SALAXY.UI_Terms.chosen' | sxyTranslate}}: {{ $ctrl.selectedItems.length }} <i class=\"bi bi-x-circle\"></i></span>\r\n          </th>\r\n          <th class=\"right hidden-xxs\">\r\n            <span sxy-text=\"SALAXY.NG1.WorkerListComponent.employment\"></span><br/>\r\n            <span sxy-orderby=\"updatedAt\" class=\"clickable\" sxy-text=\"SALAXY.UI_Terms.updated\"></span>\r\n          </th>\r\n          <th class=\"right\">\r\n            <div class=\"table-filter-container\">\r\n              <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"sort-by-text\" label-type=\"plain\">\r\n              </salaxy-input>\r\n            </div>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar middle d-none d-sm-table-cell\">\r\n            <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"td-name middle\">\r\n            <div>\r\n              <strong>{{row.otherPartyInfo.avatar.displayName}}</strong>\r\n            </div>\r\n            <div class=\"sm-description\">\r\n              {{$crud.getEmploymentDescription(row)}}\r\n            </div>\r\n          </td>\r\n          <td class=\"middle right hidden-xxs\">\r\n            <div ng-class=\"{'text-danger': !row.data.isActive }\">{{ row.data | sxyDateRange }}</div>\r\n            <div>{{ row.updatedAt | date}}</div>\r\n          </td>\r\n          <td class=\"middle right\">\r\n            <button class=\"btn btn-sm\" type=\"button\" ng-class=\"$ctrl.isSelected(row) ? 'btn-danger' : 'btn-info'\" ng-click=\"$ctrl.setSelected(row, 'toggle')\">\r\n              {{ $ctrl.isSelected(row) ? (\"SALAXY.UI_Terms.unselect\" | sxyTranslate) : (\"SALAXY.UI_Terms.select\" | sxyTranslate) }}\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/Employments.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div ng-if=\"$ctrl.logic.showToolbar\" class=\"btn-toolbar\" role=\"toolbar\">\r\n    <salaxy-action-button label=\"SALAXY.NG1_Pages.Workers.newWorker\" action=\"'newWorker'\" button-class=\"btn-sm btn-primary\" ng-if=\"!$ctrl.readOnly && ('!assureWorkerAccount' | sxyIsInRole)\"></salaxy-action-button>\r\n    <div class=\"btn-group btn-group-sm dropdown\">\r\n      <button id=\"single-button2\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\" ng-disabled=\"disabled\">\r\n       {{'SALAXY.NG1.WorkerListComponent.employments' | sxyTranslate}}:\r\n       {{ ($ctrl.url == '/v03/api/employments' ? 'SALAXY.NG1.WorkerListComponent.all' : 'SALAXY.NG1.WorkerListComponent.active') | sxyTranslate }}\r\n      </button>\r\n      <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"single-button2\">\r\n        <li role=\"menuitem\">\r\n          <a href=\"\" ng-click=\"$ctrl.setUrl('/v03/api/employments')\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.WorkerListComponent.all\"></a>\r\n        </li>\r\n        <li role=\"menuitem\">\r\n          <a href=\"\" ng-click=\"$ctrl.setUrl('/v03/api/employments?activeDate=today')\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.WorkerListComponent.active\"></a>\r\n        </li>\r\n      </ul>\r\n    </div>\r\n    <div class=\"btn-group btn-group-sm ms-1\" ng-controller=\"ExportController as $export\" ng-init=\"$export.api = $crud.getExportable()\">\r\n      <button ng-repeat=\"mapper in $export.listItemMappers\" class=\"btn btn-default \" ng-click=\"$export.quickExport('copyExcel', null, mapper)\">{{mapper.title}} {{'SALAXY.NG1.ODataActionsComponent.toExcel' | sxyTranslate}}</button>\r\n      <button class=\"btn btn-default\" ng-click=\"$export.showExport()\" sxy-text=\"SALAXY.NG1.ODataActionsComponent.export\"></button>\r\n    </div>\r\n    <button class=\"btn btn-default btn-sm ms-1\" ng-click=\"$crud.selectAutoTaxcardForEmployments($ctrl.items)\" title=\"{{'SALAXY.NG1.WorkerListComponent.activeAutoTaxcard' | sxyTranslate}}\" sxy-text=\"SALAXY.NG1.WorkerListComponent.autoTaxcard\"></button>\r\n  </div>\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr class=\"\">\r\n          <th colspan=\"2\">\r\n            <span sxy-orderby=\"otherPartyInfo/avatar/displayName\" class=\"clickable\"><span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span><i ng-if=\"$odata.getColumnOrder('avatar/displayName')\" class=\"bi bi-sort-{{ $odata.getColumnOrder('avatar/displayName') }}\"\r\n              aria-hidden=\"true\"></i></span>\r\n          </th>\r\n          <th class=\"hidden-xxs\">\r\n            <span><span sxy-text=\"SALAXY.NG1.WorkerListComponent.employment\"></span></span><br />\r\n            <span sxy-orderby=\"updatedAt\" class=\"clickable\"><span sxy-text=\"SALAXY.UI_Terms.updated\"></span></span>\r\n          </th>\r\n          <th ng-if=\"'workers.employments.records.badge' | sxyShow: 'workers.index'\" sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.records.badge\"></th>\r\n          <th ng-if=\"'workers.employments.taxcard' | sxyShow: 'workers.index'\" sxy-text=\"SALAXY.NG1.WorkerListComponent.taxcard\"></th>\r\n          <th class=\"right hidden-xxs\">\r\n            <div>\r\n              <div>\r\n                <div>\r\n                  <span class=\"salaxy-form-group-plain\">\r\n                    <input type=\"text\" ng-model=\"$ctrl.rawSearchStringOther\"  ng-change=\"$ctrl.searchChanged('other')\" class=\"form-control\" autocomplete=\"off\"\r\n                      id=\"searchx111\" name=\"searchx111\" placeholder=\"{{'SALAXY.UI_Terms.textSearch' | sxyTranslate}}\"\r\n                      ng-model-options=\"{allowInvalid: true, debounce: 250, updateOn: 'default' }\" maxlength=\"1024\">\r\n                  </span>\r\n                </div>\r\n              </div>\r\n            </div>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar middle\">\r\n            <a href=\"#/employments/details/{{row.id}}\" class=\"cell-link\" title=\"{{'SALAXY.NG1.WorkerListComponent.editWorker' | sxyTranslate}}\">\r\n              <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n            </a>\r\n          </td>\r\n          <td class=\"td-name d-none d-sm-table-cell middle\">\r\n            <div>\r\n              <strong>{{row.otherPartyInfo.avatar.displayName}}</strong>\r\n              <img ng-if=\"row.otherPartyInfo.avatar.owner == row.otherId\" src=\"https://cdn.salaxy.com/img/elems/logo/square50x50logo.png\"\r\n                class=\"registered-user\" style=\"width: 16px; position: relative; top: -6px;\" title=\"{{'SALAXY.NG1.WorkerListComponent.registeredUser' | sxyTranslate}}\">\r\n            </div>\r\n            <div class=\"sm-description\">\r\n              {{$crud.getEmploymentDescription(row)}}\r\n            </div>\r\n          </td>\r\n          <td class=\"td-name d-table-cell d-sm-none  middle\"> \r\n            <a href=\"#/employments/details/{{row.id}}\" class=\"cell-link\" title=\"{{'SALAXY.NG1.WorkerListComponent.editWorker' | sxyTranslate}}\">\r\n              <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br />\r\n              <span class=\"sm-description\" ng-if=\"row.otherPartyInfo.ibanNumber\">{{$crud.getEmploymentDescription(row)}}</span>\r\n              <span class=\"text-danger missing-info\" ng-if=\"!row.otherPartyInfo.ibanNumber\" sxy-text=\"SALAXY.NG1.WorkerListComponent.addIban\"></span>\r\n            </a>\r\n          </td>\r\n          <td class=\"hidden-xxs middle\" colspan=\"{{$ctrl.readOnly ? 2 : ''}}\" title=\"{{ $crud.getActiveText(row) }}\">\r\n          <div style=\"white-space: nowrap; overflow: hidden;text-overflow: ellipsis;\" ng-class=\"{'text-danger': !row.data.isActive }\">{{ row.data | sxyDateRange }}</div>\r\n            <div>{{ row.updatedAt | date}}</div>\r\n          </td>\r\n          <td ng-if=\"'workers.employments.records.badge' | sxyShow: 'workers.index'\" class=\"middle\">\r\n            <salaxy-workflow-badge model=\"row\" api-ctrl=\"$crud\"  wf-types=\"'EmployerMessageRecord'\"></salaxy-workflow-badge>\r\n          </td>\r\n          <td ng-if=\"'workers.employments.taxcard' | sxyShow: 'workers.index'\" class=\"middle\">\r\n            <span>{{ $crud.getTaxcardBadge(row.data.taxcard) }}</span>\r\n          </td>\r\n          <td class=\"right middle hidden-xxs\" style=\"white-space: nowrap;\">\r\n            <a ng-if=\"('workers.employments.buttons.newCalc' | sxyShow: 'workers.index') && !$ctrl.readOnly\" href=\"#/calc/details/{{row.id}}/new-for-employment\" class=\"btn btn-default btn-sm\" sxy-text=\"SALAXY.UI_Terms.newCalculation\"></a>\r\n            <a href=\"#/employments/details/{{row.id}}?tab=calculations\" class=\"btn btn-sm btn-default d-none d-sm-inline-block\" title=\"{{'SALAXY.UI_Terms.calculations' | sxyTranslate}}\">\r\n              <i class=\"bi bi-list-task\" aria-hidden=\"true\"></i>\r\n            </a>\r\n            <a class=\"btn btn-sm btn-primary\" href=\"#/employments/details/{{row.id}}\" sxy-text=\"SALAXY.UI_Terms.edit\"></a>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/Holidays.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <table class=\"table\">\r\n    <thead>\r\n      <tr>\r\n        <th colspan=\"2\" sxy-orderby=\"otherPartyInfo/avatar/displayName\">\r\n          <span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span>\r\n        </th>\r\n        <th sxy-html=\"SALAXY.NG1.HolidaysComponent.holidayType.html\"></th>\r\n        <th sxy-orderby=\"endAt\" class=\"right\" sxy-text=\"SALAXY.NG1.HolidaysComponent.year\"></th>\r\n        <th class=\"right\" sxy-html=\"SALAXY.NG1.HolidaysComponent.holidays.html\"></th>\r\n        <th>\r\n          <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\"></salaxy-input>\r\n        </th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat=\"row in $ctrl.items\">\r\n        <td class=\"align-middle td-avatar\">\r\n          <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n        </td>\r\n        <td class=\"td-workerSnapshot-name\">\r\n          <strong>{{ row.otherPartyInfo.avatar.displayName }}</strong><br /> {{ \"WageBasis.\" + row.data.wageBasis | sxyEnum }}<br />\r\n          <span ng-if=\"!row.data.employmentId\" class=\"label label-danger\" sxy-text=\"SALAXY.NG1.HolidaysComponent.error\"></span>\r\n        </td>\r\n        <td>\r\n          {{ \"HolidayCode.\" + row.data.code | sxyEnum }}\r\n          <span ng-if=\"row.data.code == 'holidayCompensation'\">({{ row.data.compensation | sxyCount : 'percent' }})</span>\r\n          <div ng-if=\"row.data.bonusMethod != 'none'\">\r\n            {{ \"HolidayBonusPaymentMethod.\" + row.data.bonusMethod | sxyEnum }}\r\n            <span>({{ row.data.bonus | sxyCount : 'percent' }})</span>\r\n          </div>\r\n        </td>\r\n        <td class=\"right\">{{ row.data.year }}</td>\r\n        <td class=\"right\">\r\n          {{ row.data.plannedDays | sxyCount : 'days' }}<br /> {{ row.data.accrualDays | sxyCount : 'days' }}\r\n        </td>\r\n        <td class=\"hidden-xxs middle\">\r\n          <button ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-primary btn-block\">\r\n            <i class=\"bi bi-pencil-fill d-inline-block d-none\"></i>\r\n            <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.edit\"></span></button>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/HouseholdYears.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th sxy-orderby=\"logicalDate\" class=\"right\" sxy-text=\"SALAXY.NG1.HouseHoldYearsComponent.year\"></th>\r\n          <th sxy-orderby=\"status\" sxy-text=\"SALAXY.NG1.HouseHoldYearsComponent.answer\"></th>\r\n          <th class=\"right\" sxy-orderby=\"endAt\" sxy-text=\"SALAXY.NG1.HouseHoldYearsComponent.latestSaving\"></th>\r\n          <th sxy-orderby=\"backOfficeStatus\" sxy-text=\"SALAXY.NG1.HouseHoldYearsComponent.backOfficeStatus\"></th>\r\n          <th class=\"right\">\r\n            <div sxy-orderby=\"createdAt\" sxy-text=\"SALAXY.UI_Terms.created\"></div>\r\n            <div sxy-orderby=\"updatedAt\" sxy-text=\"SALAXY.UI_Terms.updated\"></div>\r\n          </th>\r\n          <th class=\"right hidden-xxs\" colspan=\"2\">\r\n            <div class=\"table-filter-container\">\r\n              <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" class=\"salaxy-odata-table-search\" placeholder=\"SALAXY.UI_Terms.textSearch\" label-type=\"plain\"></salaxy-input>\r\n            </div>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"right\">\r\n            {{ row.logicalDate | date:'yyyy' }}\r\n          </td>\r\n          <td>\r\n            {{ 'HouseholdYearStatus.' + row.status | sxyEnum }}\r\n          </td>\r\n          <td class=\"right\">\r\n            {{ row.endAt | sxyDate }}\r\n          </td>\r\n          <td>\r\n            {{ 'HouseholdYearProcessingStatus.' + row.backOfficeStatus | sxyEnum }}\r\n          </td>\r\n          <td class=\"right\">\r\n            <div>{{ row.createdAt | sxyDate }}</div>\r\n            <div>{{ row.updatedAt | sxyDate }}</div>\r\n          </td>\r\n          <td class=\"middle hidden-xxs\">\r\n            <button ng-if=\"row.isReadOnly\" ng-click=\"$crud.showDetails(row)\" class=\"btn btn-sm btn-primary btn-block\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\">\r\n              <i class=\"bi bi-info-circle d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n            </button>\r\n            <button ng-if=\"!row.isReadOnly\" ng-click=\"$crud.showDetails(row)\" class=\"btn btn-sm btn-primary btn-block\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\">\r\n              <i class=\"bi bi-pencil-fill d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.edit\"></span>\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/InvoicePaymentList.html\",`<div ng-class=\"$ctrl.getCssClass()\"> \r\n  <salaxy-alert type=\"warning\" ng-if=\"$crud.paymentChannel === 'palkkausWS' && !$crud.isStronglyAuthorizedPayer()\">\r\n    <main>\r\n      <div class=\"row\">\r\n        <div class=\"col-sm-8 col-lg-9\">\r\n          <p class=\"lead\">Vahva tunnistautuminen tarvitaan</p>\r\n          <p>Maksujen maksuun vienti vaatii vahvan tunnistautumisen. Lisäksi sinun tulee olla merkittynä maksajana yritykseesi.</p>\r\n        </div>\r\n        <div class=\"col-sm-4 col-lg-3\">\r\n          \r\n          <button type=\"button\" ng-click=\"$crud.openStrongAuthDialog()\" class=\"btn btn-warning btn-add btn-add-taxcard btn-block\">Käynnistä vahva tunnistautuminen</button>\r\n        </div>\r\n      </div>\r\n    </main>\r\n  </salaxy-alert>\r\n  <div ng-controller=\"InvoiceToolsController as $invoiceTools\">    \r\n    <div class=\"btn-toolbar mb-3\">\r\n      <div class=\"btn-group dropdown\">\r\n        <button id=\"btnHide\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\" aria-expanded=\"false\">\r\n          {{ ('SALAXY.MODEL.InvoiceListItem.status.title' | sxyTranslate) }}: {{$crud.statusFilter.text}}\r\n        </button>\r\n        <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"btnHide\">\r\n          <li role=\"menuitem\" ng-repeat=\"statusFilter in $crud.statusFilters\">\r\n            <a class=\"dropdown-item\" href=\"\" ng-click=\"$crud.statusFilter = statusFilter\">{{statusFilter.text}}</a>\r\n          </li>\r\n        </ul>\r\n      </div>\r\n      <div class=\"btn-group\">\r\n        <salaxy-datepicker-popup style=\"width: 150px;\" name=\"year\" label-type=\"plain\" format=\"year\" ng-model=\"$crud.queryYear\"></salaxy-datepicker-popup>\r\n      </div>\r\n      <button type=\"button\" ng-click=\"$crud.loadData()\" class=\"btn btn-primary\">Hae</button>\r\n      <button type=\"button\" ng-if=\"$crud.supportItemMultiSelect()\" ng-disabled=\"$crud.selectedInvoices.length === 0\" ng-click=\"$crud.paymentChannelConfig.multiSelectAction().onClick()\" class=\"btn btn-primary\">{{$crud.paymentChannelConfig.multiSelectAction().text}}</button>\r\n      <div sxy-if-role=\"test\" class=\"btn-group dropdown\">\r\n        <button id=\"btnHide\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\" aria-expanded=\"false\">\r\n          Maksukanava: {{$crud.paymentChannel}}\r\n        </button>\r\n        <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"btnHide\">\r\n          <li role=\"menuitem\">\r\n            <a class=\"dropdown-item\" href=\"\" ng-click=\"$crud.paymentChannel = 'palkkausWS'; $crud.loadData()\">WS</a>\r\n          </li>\r\n          <li role=\"menuitem\">\r\n            <a class=\"dropdown-item\" href=\"\" ng-click=\"$crud.paymentChannel = 'palkkausPSD'; $crud.loadData()\">PSD</a>\r\n          </li>\r\n        </ul>\r\n      </div>\r\n    </div>\r\n    <fieldset>\r\n      <legend>Maksaja</legend>\r\n      <div class=\"d-flex\">\r\n        <salaxy-avatar avatar=\"$crud.companyAccount.avatar\" class=\"pull-left\" style=\"font-size: 64px; border-bottom: 32px; margin-right:15px;\"></salaxy-avatar>\r\n        <div class=\"d-flex flex-column\">\r\n          <div><strong>{{ $crud.companyAccount.avatar.displayName }}</strong></div>\r\n          <div>{{ $crud.companyAccount.identity.officialId }}</div>\r\n          <div ng-if=\"$crud.companyAccount.ibanNumber\">{{ $crud.companyAccount.ibanNumber | sxyIban }}</div>\r\n          <div ng-if=\"!$crud.companyAccount.ibanNumber\" class=\"alert-danger\" sxy-text=\"SALAXY.NG1.InvoiceDialog.noIban\"></div>\r\n        </div>\r\n      </div>\r\n    </fieldset>\r\n    <salaxy-tab-buttons\r\n      current-tab=\"$crud.currentTab\"\r\n      options=\"[\r\n        { value: 'netpaymentsandforeclosure', text: 'Nettopalkat ja ulosotot' },\r\n        { value: 'monthlypayments', text: 'Kuukauden maksut' }\r\n      ]\"\r\n      tabs-id=\"invoicePaymentList\"\r\n    ></salaxy-tab-buttons>\r\n    <div class=\"tab-content\" id=\"tab-content-invoicePaymentList\">\r\n      <div class=\"tab-pane\" id=\"netpaymentsandforeclosure-tab\" ng-click=\"$crud.selectTab('netpaymentsandforeclosure')\">\r\n        <div ng-if=\"$crud.currentTab === 'netpaymentsandforeclosure'\">\r\n          <ng-include src=\"'salaxy-components/odata/lists/InvoicePaymentListTable.html'\"></ng-include>\r\n        </div>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"monthlypayments-tab\" ng-click=\"$crud.selectTab('monthlypayments')\">\r\n        <div ng-if=\"$crud.currentTab === 'monthlypayments'\">\r\n          <ng-include src=\"'salaxy-components/odata/lists/InvoicePaymentListTable.html'\"></ng-include>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/InvoicePaymentListTable.html\",`<table class=\"table\" style=\"min-height: 250px;\">\r\n  <thead>\r\n    <tr>\r\n      <th ng-if=\"$crud.supportItemMultiSelect()\">\r\n        <span>Valittu</span>\r\n      </th>\r\n      <th colspan=\"2\">\r\n        <span>Ryhmä</span>\r\n      </th>\r\n      <th colspan=\"1\">\r\n        <span>                \r\n          <input type=\"text\" ng-model=\"$crud.otherPartyNameFilter\" class=\"form-control\" autocomplete=\"off\" id=\"otherPartyName\" name=\"otherPartyName\" placeholder=\"{{'SALAXY.NG1.InvoicesComponent.receiver' | sxyTranslate}}\">\r\n        </span>\r\n      </th>\r\n      <th colspan=\"1\">\r\n        <span>                \r\n          <input type=\"text\" ng-model=\"$crud.ibanFilter\" class=\"form-control\" autocomplete=\"off\" id=\"iban\" name=\"iban\" placeholder=\"{{'SALAXY.NG1.InvoicesComponent.iban' | sxyTranslate}}\">\r\n        </span>\r\n      </th>\r\n      <th>\r\n        <div class=\"btn-group dropdown\">\r\n          <button id=\"btnHide\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\" aria-expanded=\"false\">\r\n            {{ ('SALAXY.NG1.InvoicesComponent.invoiceType' | sxyTranslate) }}: {{$crud.invoiceEntityType.label}}\r\n          </button>\r\n          <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"btnHide\">\r\n            <li role=\"menuitem\" ng-repeat=\"invoiceEntityType in $crud.invoiceEntityTypes\">\r\n              <a class=\"dropdown-item\" href=\"\" ng-click=\"$crud.invoiceEntityType = invoiceEntityType\">{{invoiceEntityType.label}}</a>\r\n            </li>\r\n          </ul>\r\n        </div>\r\n      </th>\r\n      <th>\r\n        <span sxy-text=\"SALAXY.MODEL.InvoiceListItem.status.title\"></span>\r\n      </th>\r\n      <th ng-if=\"$crud.hasExternalSystemMessagesEnabled()\">\r\n        <span sxy-text=\"Maksun tila\"></span>\r\n      </th>\r\n      <th colspan=\"1\">\r\n        <span>                \r\n          <input type=\"text\" ng-model=\"$crud.referenceFilter\" class=\"form-control\" autocomplete=\"off\" id=\"reference\" name=\"reference\" placeholder=\"{{'SALAXY.MODEL.InvoiceListItem.reference.title' | sxyTranslate}}\">\r\n        </span>\r\n      </th>\r\n      <th class=\"right clickable\" ng-click=\"$crud.changeSortMode()\">\r\n        <span sxy-text=\"SALAXY.MODEL.InvoiceData.dueDate.tableHeading\"></span>\r\n        <i class=\"bi bi-sort-{{$crud.sortMode === 'asc' ? 'up' : 'down'}}\"></i>\r\n      </th>\r\n      <th class=\"right\">\r\n        <span sxy-text=\"SALAXY.MODEL.InvoiceListItem.payment.title\"></span>\r\n      </th>\r\n      <th colspan=\"2\">\r\n      </th>\r\n    </tr>\r\n  </thead>\r\n  <tbody>\r\n    <tr ng-repeat-start=\"group in $crud.getGroupedItems()\" class=\"active\">\r\n      <td ng-if=\"$crud.supportItemMultiSelect()\"></td>\r\n      <td colspan=\"3\">  \r\n        <span>\r\n            <a ng-if=\"group.groupType === 'payroll'\" target=\"_blank\" ng-href=\"#/payroll/details/{{ group.businessObjectId }}\">\r\n              {{group.title}}\r\n            </a>\r\n            <a ng-if=\"group.groupType === 'calculation'\" target=\"_blank\" ng-href=\"#/calc/details/{{ group.businessObjectId }}\">\r\n              {{group.title}}\r\n            </a>\r\n            <span ng-if=\"group.groupType === 'monthly'\">\r\n              {{group.title}}\r\n            </span>\r\n        </span>\r\n      </td>\r\n      <td ng-if=\"$crud.hasExternalSystemMessagesEnabled()\"></td>             \r\n      <td colspan=\"7\"></td>\r\n      <td class=\"middle\">\r\n        <div ng-if=\"$crud.paymentChannelConfig.rowGroupActions(group).length > 0\" class=\"btn-group btn-group-sm dropup dropdown\">\r\n          <button id=\"actionsButton\" type=\"button\" class=\"btn\" ng-disabled=\"$crud.selectedInvoices.length > 0\" style=\"background-color: transparent; border-color: transparent;\" data-bs-toggle=\"dropdown\" aria-expanded=\"false\">\r\n            <i class=\"bi bi-three-dots-vertical\" style=\"font-size: 20px;\"></i>\r\n          </button>\r\n          <ul class=\"dropdown-menu dropdown-menu-end\" role=\"menu\" aria-labelledby=\"actionsButton\">\r\n            <li role=\"menuitem\" ng-repeat=\"action in $crud.paymentChannelConfig.rowGroupActions(group)\">\r\n              <a class=\"dropdown-item\" href=\"\" ng-click=\"action.onClick(group)\">\r\n                {{action.text}}\r\n              </a>\r\n            </li>\r\n          </ul>\r\n        </div>\r\n      </td>\r\n    </tr>\r\n    <tr ng-repeat-end ng-repeat=\"invoice in group.invoices | filter: $crud.filterInvoices\" >\r\n      <td ng-if=\"$crud.supportItemMultiSelect()\" class=\"left\">\r\n         <button title=\"{{'SALAXY.UI_Terms.select' | sxyTranslate}}\" class=\"btn btn-transparent pull-right\" type=\"button\" ng-if=\"!$crud.isSelected(invoice) && $crud.isItemSelectable(invoice)\" ng-click=\"$crud.setSelected(invoice, 'toggle')\">\r\n            <i class=\"bi bi-square\"></i>\r\n          </button>\r\n          <button title=\"{{'SALAXY.UI_Terms.unselect' | sxyTranslate}}\" class=\"btn btn-transparent pull-right\" type=\"button\" ng-if=\"$crud.isSelected(invoice)\" ng-click=\"$crud.setSelected(invoice, 'toggle')\">\r\n            <i class=\"bi bi-check-square\"></i>\r\n          </button>\r\n      </td>\r\n      <td></td>\r\n      <td class=\"td-avatar-1line middle\">\r\n        <salaxy-avatar avatar=\"invoice.otherPartyInfo.avatar\"></salaxy-avatar>\r\n      </td>\r\n      <td class=\"td-name middle\">\r\n        <div><strong>{{invoice.otherPartyInfo.avatar.displayName}}</strong></div>\r\n        <small ng-switch=\"invoice.entityType\">\r\n        <span ng-switch-when=\"net|gross|foreclosure\" ng-switch-when-separator=\"|\">{{(\"SALAXY.ENUM.InvoiceType.\" + invoice.entityType + \".label\") | sxyTranslate}} {{ invoice.logicalDate | sxyDate }}</span>\r\n        <span ng-switch-when=\"unemployment\">{{(\"SALAXY.ENUM.InvoiceType.\" + invoice.entityType + \".label\") | sxyTranslate}}<br/>{{ { start: invoice.data.periodStart, end: invoice.data.periodEnd } | sxyDateRange }}</span>\r\n        <span ng-switch-default>{{(\"SALAXY.ENUM.InvoiceType.\" + invoice.entityType + \".label\") | sxyTranslate}} {{ { start: invoice.data.periodStart, end: invoice.data.periodEnd } | sxyDateRange }}</span>\r\n      </small>\r\n      </td>\r\n      <td class=\"middle\">\r\n        <span ng-if=\"invoice.otherPartyInfo.ibanNumber\">{{ invoice.otherPartyInfo.ibanNumber }}</span>\r\n        <span ng-if=\"!invoice.otherPartyInfo.ibanNumber\" class=\"alert-danger\" sxy-text=\"SALAXY.NG1.InvoicesComponent.noIbanNumber\"></span>\r\n      </td>\r\n      <td class=\"middle\">\r\n        {{(\"SALAXY.ENUM.InvoiceType.\" + invoice.entityType + \".label\") | sxyTranslate}}\r\n      </td>\r\n      <td class=\"middle\">\r\n        <strong ng-class=\"{ 'bg-danger': invoice.status == 'canceled', 'bg-success': invoice.status == 'paid' }\" title=\"{{ 'InvoiceStatus.' + invoice.status | sxyEnumDescr }}\">\r\n          {{ \"InvoiceStatus.\" + invoice.status | sxyEnum }}\r\n        </strong>\r\n      </td>\r\n      <td ng-if=\"$crud.hasExternalSystemMessagesEnabled()\">\r\n        <span ng-class=\"$crud.getBadgeClass(invoice.data.externalStatus)\">{{invoice.data.externalStatus}}</span> <br/>\r\n        <small>{{invoice.data.externalStatusAt | date: \"dd.MM.yyyy HH:mm\"}}</small>\r\n      </td>\r\n      <td class=\"middle\">\r\n        <span>{{ invoice.entityType !== 'net' && invoice.reference ? invoice.reference : '' }}</span>\r\n      </td>\r\n      <td class=\"middle right\">\r\n        {{ invoice.data.dueDate | sxyDate }}\r\n      </td>\r\n      <td class=\"middle right\">\r\n        {{ invoice.payment | currency }}\r\n      </td>\r\n      <td class=\"middle\">\r\n        <button ng-click=\"$crud.showInvoiceDialog(invoice)\" title=\"{{ 'SALAXY.NG1.InvoicesComponent.detailsBtn' | sxyTranslate}}\" class=\"btn btn-xs btn-default btn-block\" sxy-text=\"SALAXY.NG1.InvoicesComponent.detailsBtn\">\r\n        \r\n      </button>\r\n      </td>\r\n      <td class=\"middle\">\r\n        <div ng-if=\"$crud.paymentChannelConfig.rowActions(invoice).length > 0\" class=\"btn-group btn-group-sm dropup dropdown\">\r\n          <button id=\"actionsButton\" type=\"button\" class=\"btn\" ng-disabled=\"$crud.selectedInvoices.length > 0\" style=\"color: #000; background-color: transparent; border-color: transparent;\" data-bs-toggle=\"dropdown\" aria-expanded=\"false\">\r\n            <i class=\"bi bi-three-dots-vertical\" style=\"font-size: 20px;\"></i>\r\n          </button>\r\n          <ul class=\"dropdown-menu dropdown-menu-end\" role=\"menu\" aria-labelledby=\"actionsButton\">\r\n            <li role=\"menuitem\" ng-repeat=\"action in $crud.paymentChannelConfig.rowActions(invoice)\">\r\n              <a class=\"dropdown-item\" href=\"\" ng-click=\"action.onClick(invoice)\">\r\n                {{action.text}}\r\n              </a>\r\n            </li>\r\n          </ul>\r\n        </div>\r\n      </td>\r\n    </tr>\r\n  </tbody>\r\n</table>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/Invoices.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <table class=\"table\">\r\n    <thead>\r\n      <tr>\r\n        <th colspan=\"2\"><span sxy-orderby=\"otherPartyInfo/avatar/displayName\" sxy-text=\"SALAXY.NG1.InvoicesComponent.receiverAndType\"></span></th>\r\n        <th>\r\n          <span sxy-orderby=\"status\" sxy-text=\"SALAXY.NG1.InvoicesComponent.status\"></span><br />\r\n          <small sxy-text=\"SALAXY.NG1.InvoicesComponent.channel\"></small>\r\n        </th>\r\n        <th class=\"right\">\r\n          <span sxy-orderby=\"startAt\" sxy-text=\"SALAXY.NG1.InvoicesComponent.invoiceDate\"></span><br/>\r\n          <span sxy-orderby=\"endAt\" sxy-text=\"SALAXY.NG1.InvoicesComponent.dueDate\"></span>\r\n        </th>\r\n        <th class=\"right\">\r\n          <span sxy-orderby=\"createdAt\" sxy-text=\"SALAXY.UI_Terms.created\"></span><br />\r\n          <span sxy-orderby=\"updatedAt\" sxy-text=\"SALAXY.UI_Terms.updated\"></span>\r\n        </th>\r\n        <th class=\"right\"><span sxy-orderby=\"payment\" sxy-text=\"SALAXY.NG1.InvoicesComponent.sum\"></span></th>        \r\n        <th class=\"right\" colspan=\"2\">\r\n          <div class=\"table-filter-container hidden-xxs\">\r\n            <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" class=\"salaxy-odata-table-search\" placeholder=\"SALAXY.UI_Terms.textSearch\" label-type=\"plain\"></salaxy-input>\r\n          </div>\r\n        </th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat=\"row in $ctrl.items\" ng-show=\"$ctrl.items.length > 0\">\r\n        <td class=\"td-avatar middle\">\r\n          <salaxy-avatar class=\"salaxy-calc-row-type-avatar\" avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n        </td>\r\n        <td class=\"middle\">\r\n          <div>{{ row.otherPartyInfo.avatar.displayName }}</div>\r\n          <small class=\"hidden-xxs\" ng-switch=\"row.entityType\">\r\n            <span ng-switch-when=\"net|gross|foreclosure|verification\" ng-switch-when-separator=\"|\">{{(\"SALAXY.ENUM.InvoiceType.\" + row.entityType + \".label\") | sxyTranslate}} {{ row.logicalDate | sxyDate }}</span>\r\n            <span ng-switch-when=\"unemployment\">{{(\"SALAXY.ENUM.InvoiceType.\" + row.entityType + \".label\") | sxyTranslate}}<br/>{{ { start: row.data.periodStart, end: row.data.periodEnd } | sxyDateRange }}</span>\r\n            <span ng-switch-default>{{(\"SALAXY.ENUM.InvoiceType.\" + row.entityType + \".label\") | sxyTranslate}} {{ { start: row.data.periodStart, end: row.data.periodEnd } | sxyDateRange }}</span>\r\n          </small>\r\n        </td class=\"middle\">\r\n        <td class=\"middle\">\r\n          <span ng-class=\"{ 'bg-danger': row.status == 'canceled', 'bg-success': row.status == 'paid' }\" title=\"{{ 'InvoiceStatus.' + row.status | sxyEnumDescr }}\">\r\n            {{ \"InvoiceStatus.\" + row.status | sxyEnum }}\r\n          </span><br />\r\n          <small>{{ \"PaymentChannel.\" + row.data.channel | sxyEnum }}</small>\r\n        </td>\r\n        <td class=\"middle right\">\r\n          <div>{{ row.startAt | sxyDate }}</div>\r\n          <div ng-switch=\"$crud.getDueDateType(row)\">\r\n            <span ng-switch-when=\"estimation\">{{ row.endAt | date: 'MMMM' }}</span>\r\n            <del ng-switch-when=\"canceled\" class=\"\">{{ row.endAt | sxyDate }}</del>\r\n            <span ng-switch-when=\"overdue\" class=\"bg-danger\">{{ row.endAt | sxyDate }}</span>\r\n            <em ng-switch-when=\"future\" class=\"disabled\">{{ row.endAt | sxyDate }}</em>\r\n            <span ng-switch-when=\"default\">{{ row.endAt | sxyDate }}</span>\r\n            <span ng-switch-when=\"unknown\">{{ row.endAt | sxyDate }}</span>\r\n          </div>\r\n        </td>\r\n        <td class=\"middle right\">\r\n          {{ row.createdAt | sxyDate }}<br /> {{ row.updatedAt | sxyDate }}\r\n        </td>\r\n        <td class=\"middle right\">\r\n          {{ row.payment | currency }}\r\n        </td>       \r\n        <td class=\"middle right\">\r\n          <a href=\"\" ng-click=\"$crud.showDetails(row)\" class=\"btn btn-primary\">\r\n            {{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\r\n          </a>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n  <div class=\"salaxy-odata-footer\">\r\n    <salaxy-spinner></salaxy-spinner>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/InvoicesCompany.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <h1 sxy-text=\"SALAXY.NG1.InvoicesCompany.heading\"></h1>\r\n  <style>\r\n    .invoice-label {\r\n      display: inline-block;\r\n      width: 100px;\r\n    }\r\n  </style>\r\n  <div class=\"btn-toolbar\">\r\n    <div class=\"btn-group dropdown\">\r\n      <button id=\"btnHide\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\" aria-expanded=\"false\">\r\n        {{ $crud.queryOption.text }}\r\n      </button>\r\n      <ul class=\"dropdown-menu\" aria-labelledby=\"btnHide\">\r\n        <li ng-repeat=\"queryOption in $crud.queryOptions\">\r\n          <a class=\"dropdown-item\" href=\"\" ng-click=\"$crud.queryOption = queryOption;$crud.doQuery()\">{{queryOption.text}}</a>\r\n        </li>\r\n      </ul>\r\n    </div>\r\n    <button type=\"button\" class=\"btn btn-secondary\" ng-click=\"$crud.showloadPfd($ctrl.items)\" sxy-text=\"SALAXY.UI_Terms.downloadPdf\"></button>\r\n    <div ng-if=\"$crud.queryOption.value != 'unpaid'\" class=\"btn-group dropdown\">\r\n      <button id=\"btnHide\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\" aria-expanded=\"false\">\r\n        {{ $crud.dateFilterQueryOption.text }}\r\n      </button>\r\n      <ul class=\"dropdown-menu\" aria-labelledby=\"btnHide\">\r\n        <li ng-repeat=\"queryOption in $crud.queryDateFilterOptions\">\r\n          <a class=\"dropdown-item\" href=\"\" ng-click=\"$crud.setDateFilterQueryOption(queryOption)\">{{queryOption.text}}</a>\r\n        </li>\r\n      </ul>\r\n    </div>\r\n    <div ng-if=\"$crud.queryOption.value == 'unpaid' && $ctrl.items.length > 0\" class=\"btn-group dropdown float-end ms-auto\">\r\n      <button id=\"btnHide\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\" aria-expanded=\"false\">\r\n        {{'SALAXY.NG1.InvoicesCompany.selectInvoices' | sxyTranslate}}\r\n      </button>\r\n      <ul class=\"dropdown-menu\" aria-labelledby=\"btnHide\">\r\n        <li ng-repeat=\"option in $crud.getMarkAsPaidOptions($ctrl.items)\">\r\n          <a class=\"dropdown-item\" href=\"\" ng-click=\"$crud.selectInvoicesByType(option.value)\">{{option.text}}</a>\r\n        </li>\r\n      </ul>\r\n    </div>\r\n    <button type=\"button\" class=\"btn btn-primary pull-right\" ng-if=\"$crud.queryOption.value == 'unpaid' && $ctrl.items.length > 0\"\r\n      ng-click=\"$crud.markInvoicesAsPaid()\" ng-disabled=\"!$ctrl.selectedItems || $ctrl.selectedItems.length == 0\" sxy-text=\"SALAXY.NG1.InvoicesCompany.setAsPaid\">\r\n    </button>\r\n  </div>\r\n  <table class=\"table\">\r\n    <thead>\r\n      <tr>\r\n        <th colspan=\"2\"><span sxy-text=\"SALAXY.NG1.InvoicesCompany.receiverAndType\"></span></th>\r\n        <th ng-if=\"$crud.queryOption.value == 'unpaid'\" class=\"right\">\r\n          <span sxy-text=\"SALAXY.NG1.InvoicesCompany.sum\"></span>/ <br/>\r\n          <span sxy-text=\"SALAXY.UI_Terms.chosen\"></span>\r\n        </th>\r\n        <th ng-if=\"$crud.queryOption.value != 'unpaid'\" class=\"right\">\r\n          <span sxy-text=\"SALAXY.NG1.InvoicesCompany.sum\"></span>\r\n        </th>          \r\n        <th class=\"right\" colspan=\"2\">\r\n          <div class=\"table-filter-container hidden-xxs\">\r\n            <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" class=\"salaxy-odata-table-search\"\r\n             placeholder=\"SALAXY.UI_Terms.textSearch\" label-type=\"plain\">\r\n            </salaxy-input>\r\n          </div>\r\n        </th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat-start=\"row in $ctrl.items\" ng-show=\"$ctrl.items.length > 0\" class=\"active\">\r\n        <td class=\"middle\" colspan=\"3\">\r\n          <div class=\"d-flex\">\r\n            <div class=\"flex-grow-1\">\r\n              <div class=\"d-flex align-items-center\">\r\n                <salaxy-avatar class=\"salaxy-calc-row-type-avatar\" avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n                <span style=\"font-size: 1.4em; font-weight: bold;\">\r\n                  {{ row.otherPartyInfo.avatar.displayName }}:\r\n                  <span ng-switch=\"row.entityType\">\r\n                    <span ng-switch-when=\"net|gross|foreclosure|verification\" ng-switch-when-separator=\"|\">{{(\"SALAXY.ENUM.InvoiceType.\" + row.entityType + \".label\") | sxyTranslate}} {{ row.logicalDate | sxyDate }}</span>\r\n                    <span ng-switch-default>{{(\"SALAXY.ENUM.InvoiceType.\" + row.entityType + \".label\") | sxyTranslate}} {{ { start: row.data.periodStart, end: row.data.periodEnd } | sxyDateRange }}</span>\r\n                  </span>\r\n                </span>\r\n              </div>\r\n              <div ng-if=\"row.entityType == 'net'\" class=\"mt-2\" ng-switch=\"row.status\">\r\n                <span ng-switch-when=\"paid\" class=\"text-success\" ng-switch-when-separator=\"|\" sxy-text=\"SALAXY.NG1.InvoicesCompany.paidNetPaymentInfo\"></span>\r\n                <span ng-switch-default  class=\"text-danger\" sxy-text=\"SALAXY.NG1.InvoicesCompany.unPaidNetPaymentInfo\"></span>\r\n              </div>\r\n            </div>\r\n            <div class=\"row-buttons align-items-end\">\r\n              <button title=\"{{'SALAXY.UI_Terms.select' | sxyTranslate}}\" class=\"btn btn-transparent pull-right\" type=\"button\" ng-if=\"!$ctrl.isSelected(row) && $crud.queryOption.value == 'unpaid' && $crud.showMarkAsPaidButton(row)\" ng-click=\"$ctrl.setSelected(row, 'toggle')\">\r\n                <i class=\"bi bi-square\"></i>\r\n              </button>\r\n              <button title=\"{{'SALAXY.UI_Terms.unselect' | sxyTranslate}}\" class=\"btn btn-transparent pull-right\" type=\"button\" ng-if=\"$ctrl.isSelected(row) && $crud.queryOption.value == 'unpaid' && $crud.showMarkAsPaidButton(row)\" ng-click=\"$ctrl.setSelected(row, 'toggle')\">\r\n                <i class=\"bi bi-check-square\"></i>\r\n              </button>\r\n            </div>\r\n          </div>\r\n        </td>\r\n        <td class=\"right\">\r\n          <button ng-if=\"row.status != 'canceled'\" class=\"btn btn-default\" ng-click=\"$crud.showInvoiceDialog(row)\">\r\n            <span class=\"hidden-xs\" sxy-text=\"SALAXY.NG1.InvoicesCompany.showInvoiceDetails\"></span>\r\n          </button>\r\n          <a ng-if=\"$crud.calculationHref(row)\" ng-href=\"{{$crud.calculationHref(row)}}\" class=\"btn btn-default\" sxy-text=\"SALAXY.NG1.InvoicesCompany.openCalculation\"></a>\r\n        </td>\r\n      </tr>\r\n      <tr>\r\n        <td class=\"td-avatar hidden-xxs\" style=\"width: 160px;padding: 0px;\" ng-if=\"row.status != 'paid' && row.status != 'canceled' && $crud.getQrCode(row) !== 'loading' && $crud.getQrCode(row) !== 'error'\">\r\n          <div style=\"margin: 8px;\" height=\"160px\" ng-bind-html=\"$crud.getQrCode(row)\" ></div>\r\n        </td>\r\n        <td class=\"td-avatar hidden-xxs\" style=\"min-width: 160px;vertical-align: middle; text-align: center; height: 160px;\" ng-if=\"row.status != 'paid' && row.status != 'canceled' && $crud.getQrCode(row) === 'error'\">\r\n          <div style=\"height: 100%; display: flex;align-items: center;justify-content: center; background-color: #e9d310;\">\r\n            <div>\r\n              <small sxy-text=\"SALAXY.NG1.InvoicesCompany.qrCodeNotAvailable\"></small>\r\n            </div>\r\n          </div>\r\n        </td>\r\n        <td class=\"td-avatar hidden-xxs\" style=\"vertical-align: middle; text-align: center; height: 160px; width: 160px;\" ng-if=\"row.status == 'paid'\">\r\n          <div class=\"bg-success\" style=\"height: 100%; display: flex;align-items: center;justify-content: center; font-size: 1.5em;\">\r\n            <div>\r\n              <b>\r\n                {{ \"SALAXY.ENUM.InvoiceStatus.\" + row.status + \".label\" | sxyTranslate}} <br/>\r\n                {{(row.data.statusAt || row.updatedAt) | date}}\r\n              </b>\r\n            </div>\r\n          </div>\r\n        </td>\r\n        <td class=\"td-avatar hidden-xxs\" style=\"vertical-align: middle; text-align: center; height: 160px; width: 160px;\" ng-if=\"row.status == 'canceled'\">\r\n          <div class=\"bg-danger\" style=\"height: 100%; display: flex;align-items: center;justify-content: center; font-size: 1.5em;\">\r\n            <b>\r\n              {{ \"SALAXY.ENUM.InvoiceStatus.\" + row.status + \".label\" | sxyTranslate}} <br/>\r\n              {{(row.data.statusAt || row.updatedAt) | date}}\r\n            </b>\r\n          </div>\r\n        </td>\r\n        <td>\r\n          <div class=\"row\">\r\n            <div class=\"col-3\" sxy-text=\"SALAXY.NG1.InvoicesCompany.iban\" ps=\":\"></div>\r\n            <div class=\"col-9\">\r\n              {{ row.otherPartyInfo.ibanNumber  }}\r\n            </div>\r\n          </div>\r\n          <div class=\"row\">\r\n            <div class=\"col-3\" sxy-text=\"SALAXY.NG1.InvoicesCompany.name\" ps=\":\"></div>\r\n            <div class=\"col-9\">\r\n              {{ row.otherPartyInfo.avatar.displayName }}\r\n            </div>\r\n          </div>\r\n          <div class=\"row\">\r\n            <div class=\"col-3\" sxy-text=\"SALAXY.NG1.InvoicesCompany.dueDate\" ps=\":\"></div>\r\n            <div class=\"col-9\" ng-switch=\"$crud.getDueDateType(row)\">\r\n              <span ng-switch-when=\"estimation\">{{ row.endAt | sxyDate }}</span>\r\n              <del ng-switch-when=\"canceled\" class=\"\">{{ row.endAt | sxyDate }}</del>\r\n              <span ng-switch-when=\"overdue\" class=\"bg-danger\">{{ row.endAt | sxyDate }}</span>\r\n              <em ng-switch-when=\"future\" class=\"disabled\">{{ row.endAt | sxyDate }}</em>\r\n              <span ng-switch-when=\"default\">{{ row.endAt | sxyDate }}</span>\r\n              <span ng-switch-when=\"unknown\">{{ row.endAt | sxyDate }}</span>\r\n            </div>\r\n          </div>\r\n          <div class=\"row\">\r\n            <div class=\"col-3\">\r\n              {{row.entityType === 'net' || row.entityType === 'gross' ? ('SALAXY.NG1.InvoicesCompany.message' | sxyTranslate) : ('SALAXY.NG1.InvoicesCompany.reference' | sxyTranslate)}}\r\n            </div>\r\n            <div class=\"col-9\">\r\n              <span ng-if=\"row.entityType === 'net' || row.entityType === 'gross'\">{{(\"SALAXY.ENUM.InvoiceType.\" + row.entityType + \".label\") | sxyTranslate}} {{ { start: row.data.periodStart, end: row.data.periodEnd } | sxyDateRange }}</span>\r\n              <span ng-if=\"row.entityType !== 'net' && row.entityType !== 'gross'\">{{row.reference}}</span>\r\n            </div>\r\n          </div>\r\n          <div class=\"row\" ng-if=\"row.entityType == 'tax' || row.entityType == 'union'\">\r\n            <div class=\"col-3\" sxy-text=\"SALAXY.NG1.InvoicesCompany.netPaymentCount\" ps=\":\"></div>\r\n            <div class=\"col-9\">\r\n              {{row.businessObjects.length}}\r\n            </div>\r\n          </div>\r\n        </td>\r\n        <td class=\"right\" ng-if=\"!row.data.totalPaid\">\r\n          <h4 style=\"font-weight: bold;\">{{ row.payment | currency }}</h4>\r\n        </td>\r\n        <td class=\"right\" ng-if=\"row.data.totalPaid && row.data.totalPaid != row.payment\">\r\n          <h4 style=\"text-decoration: line-through;\">{{'SALAXY.NG1.InvoicesCompany.sum' | sxyTranslate}} {{ row.payment | currency }}</h4>\r\n          <h4>{{'SALAXY.NG1.InvoicesCompany.alreadyPaid' | sxyTranslate}} {{ row.data.totalPaid | currency }}</h4>\r\n          <h4 class=\"total\" style=\"font-weight: bold;\">{{'SALAXY.NG1.InvoicesCompany.payable' | sxyTranslate}} {{ (row.payment - row.data.totalPaid) | currency }}</h4>\r\n        </td>\r\n        <td class=\"right\" ng-if=\"row.data.totalPaid && row.payment == row.data.totalPaid\">\r\n          <h4 style=\"font-weight: bold;\">{{ row.payment | currency }}</h4>\r\n        </td>\r\n        <td class=\"right\">\r\n          <button ng-if=\"$crud.showMarkAsPaidButton(row)\" class=\"btn btn-primary\" ng-click=\"$crud.updateInvoiceStatus(row,'paid')\">\r\n            <span class=\"hidden-xs\" sxy-text=\"SALAXY.NG1.InvoicesCompany.setAsPaid\"></span>\r\n          </button> \r\n          <div style=\"height: 10px;\" ng-if=\"$crud.showMarkAsPaidButton(row) && $crud.showMarkAsCanceledButton(row)\"> <br/> </div>         \r\n          <button class=\"btn btn-danger\" ng-if=\"$crud.showMarkAsCanceledButton(row)\" ng-click=\"$crud.updateInvoiceStatus(row,'canceled')\">\r\n            </i><span class=\"hidden-xs\" sxy-text=\"SALAXY.NG1.InvoicesCompany.cancelPayment\"></span>\r\n          </button>\r\n          <div ng-if=\"$crud.showIrCancelInfoText(row)\" class=\"text-center\" style=\"width: 140px; margin: auto; margin-top: 6px;\" sxy-text=\"SALAXY.NG1.InvoicesCompany.cancelInfoText\"></div>\r\n          <div ng-if=\"row.status == 'preview'\" class=\"text-center\" style=\"width: 140px; margin: auto; margin-top: 6px;\">\r\n            {{(row.data.paidBusinessObjectsCount || 0) }} / {{row.businessObjects.length}} {{'SALAXY.NG1.InvoicesCompany.unpaidNetSalaries' | sxyTranslate}}<br/>\r\n            {{ { start: row.data.periodStart, end: row.data.periodEnd } | sxyDateRange }}\r\n          </div>\r\n        </td>\r\n      </tr>\r\n      <tr ng-repeat-end ng-if=\"row.status != 'paid' && row.status != 'canceled'\">\r\n        <td colspan=\"4\">\r\n          <button type=\"button\" class=\"btn btn-default btn-sm\" ng-click=\"$crud.copyBarcode(row)\">\r\n            <span><i class=\"bi bi-clipboard\"></i></span>\r\n          </button>\r\n          <span style=\"font-family: 'Courier New', Courier, monospace; font-size: 1.15em;\">{{$crud.getBarcodeValue(row)}}</span>          \r\n        </td>        \r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n  <div class=\"salaxy-odata-footer\">\r\n    <salaxy-spinner></salaxy-spinner>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/InvoicesPanel.html\",`<div class=\"salaxy-odata-panel list-panel report-list-panel panel panel-sm panel-secondary\">\r\n  <div class=\"card-header\">\r\n    {{('SALAXY.NG1.InvoicesComponent.invoices' | sxyTranslate) }}\r\n  </div>\r\n  <div ng-class=\"$ctrl.getCssClass()\">\r\n    <div class=\"card-body text-center card-content lg-height align-middle\" ng-show=\"$ctrl.items.length == 0 && !$ctrl.isLoading\">\r\n      <div>\r\n        <h3 sxy-text=\"SALAXY.NG1.InvoicesComponent.noInvoices\"></h3>\r\n      </div>\r\n    </div>\r\n    <div class=\"table-responsive\">\r\n      <table class=\"table\">\r\n        <tbody>\r\n          <tr ng-repeat=\"row in $ctrl.items\" ng-show=\"$ctrl.items.length > 0\">\r\n            <td class=\"td-avatar middle hidden-xxs\">\r\n              <salaxy-avatar class=\"salaxy-calc-row-type-avatar\" avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n            </td>\r\n            <td class=\"middle\">\r\n              {{ row.otherPartyInfo.avatar.displayName }}<br>\r\n              <small class=\"hidden-xxs\">{{(\"SALAXY.ENUM.InvoiceType.\" + row.entityType + \".label\") | sxyTranslate}}</small>\r\n            </td>\r\n            <td class=\"middle right\">\r\n              {{ row.endAt | date }}\r\n              <span ng-if=\"row.status=='paid'\" class=\"text-success status small\"><br>{{'SALAXY.NG1.InvoicesComponent.paid' | sxyTranslate}}</span>\r\n            </td>\r\n            <td class=\"middle right\">\r\n              {{ row.payment | currency }}\r\n            </td>\r\n            <td class=\"middle right\">\r\n              <a ng-href=\"{{$crud.getContentUrl(row.id, true)}}\" target=\"_blank\" title=\"{{ 'SALAXY.UI_Terms.printable' | sxyTranslate}}\" class=\"btn btn-sm btn-secondary\"><i\r\n              class=\"bi bi-file-earmark-pdf\"></i></a>\r\n              <button href=\"\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-secondary\"><i class=\"bi bi-info-circle\"></i></button>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n      <div class=\"salaxy-odata-footer\">\r\n        <salaxy-spinner></salaxy-spinner>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div class=\"card-footer text-center footer-empty\">\r\n    <a ng-href=\"#{{$crud.getDefaults().listUrl}}\" title=\"Näytä kaikki\" class=\"btn btn-primary btn-sm\" sxy-text=\"SALAXY.UI_Terms.showAll\"></a>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/InvoicesPaymentChannel.html\",`<div ng-class=\"$ctrl.getCssClass()\" ng-controller=\"InvoiceToolsController as $invoiceTools\" ng-init=\"$invoiceTools.reader = $crud.selectionDataReader\">\r\n  <div ng-show=\"'test' | sxyIsInRole\" class=\"salaxy-component salaxy-invoice-tools\" >\r\n    <div class=\"btn-toolbar\" role=\"toolbar\" aria-label=\"Invoice options\">\r\n      <div class=\"btn-group\">\r\n        <salaxy-input-enum type=\"dropdown\" name=\"fileType\" label-type=\"plain\" ng-model=\"$invoiceTools.fileTypeId\" options=\"$invoiceTools.fileTypeOptions\" remember=\"invoice\"></salaxy-input-enum>\r\n      </div>\r\n      <div class=\"btn-group\">\r\n        <button ng-disabled=\"$invoiceTools.reader.disabled()\" id=\"reportExport\" type=\"button\" class=\"btn btn-default\" ng-click=\"$invoiceTools.export()\">\r\n          {{ $invoiceTools.reader.exportLabel || ('SALAXY.NG1.AccountingReportToolsComponent.createExport' | sxyTranslate) }}\r\n        </button>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <table class=\"table\">\r\n    <thead>\r\n      <tr>\r\n        <th colspan=\"2\"><span sxy-orderby=\"otherPartyInfo/avatar/displayName\" sxy-text=\"SALAXY.NG1.InvoicesComponent.receiverAndType\"></span></th>\r\n        <th>\r\n          <span sxy-orderby=\"status\" sxy-text=\"SALAXY.NG1.InvoicesComponent.status\"></span><br />\r\n          <small sxy-text=\"SALAXY.NG1.InvoicesComponent.channel\"></small>\r\n        </th>\r\n        <th class=\"right\">\r\n          <span sxy-orderby=\"startAt\" sxy-text=\"SALAXY.NG1.InvoicesComponent.invoiceDate\"></span><br/>\r\n          <span sxy-orderby=\"endAt\" sxy-text=\"SALAXY.NG1.InvoicesComponent.dueDate\"></span>\r\n        </th>\r\n        <th class=\"right\">\r\n          <span sxy-orderby=\"createdAt\" sxy-text=\"SALAXY.UI_Terms.created\"></span><br />\r\n          <span sxy-orderby=\"updatedAt\" sxy-text=\"SALAXY.UI_Terms.updated\"></span>\r\n        </th>\r\n        <th class=\"right\"><span sxy-orderby=\"payment\" sxy-text=\"SALAXY.NG1.InvoicesComponent.sum\"></span></th>\r\n        <th class=\"middle\" ng-if=\"'test' | sxyIsInRole\">\r\n          <button title=\"{{'SALAXY.UI_Terms.chooseAll' | sxyTranslate}}\" class=\"btn btn-block btn-transparent\" type=\"button\" ng-if=\"$ctrl.selectedItems.length == 0\" ng-disabled=\"$ctrl.selectedItems.length == $ctrl.items.length\" ng-click=\"$crud.selectAll()\">\r\n            <i class=\"bi bi-square\"></i>\r\n          </button>\r\n          <button title=\"{{'SALAXY.UI_Terms.unselectAll' | sxyTranslate}}\" class=\"btn btn-block btn-transparent\" type=\"button\" ng-if=\"$ctrl.selectedItems.length > 0\" ng-disabled=\"$ctrl.selectedItems.length == 0\" ng-click=\"$crud.unselectAll()\">\r\n            <i class=\"bi bi-check-square\"></i>\r\n          </button>\r\n        </th>\r\n        <th class=\"right\" colspan=\"2\">\r\n          <div class=\"table-filter-container hidden-xxs\">\r\n            <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" class=\"salaxy-odata-table-search\" placeholder=\"SALAXY.UI_Terms.textSearch\" label-type=\"plain\"></salaxy-input>\r\n          </div>\r\n        </th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat=\"row in $ctrl.items\" ng-show=\"$ctrl.items.length > 0\">\r\n        <td class=\"td-avatar middle\">\r\n          <salaxy-avatar class=\"salaxy-calc-row-type-avatar\" avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n        </td>\r\n        <td class=\"middle\">\r\n          <div>{{ row.otherPartyInfo.avatar.displayName }}</div>\r\n          <small class=\"hidden-xxs\" ng-switch=\"row.entityType\">\r\n            <span ng-switch-when=\"net|gross|foreclosure|verification\" ng-switch-when-separator=\"|\">{{(\"SALAXY.ENUM.InvoiceType.\" + row.entityType + \".label\") | sxyTranslate}} {{ row.logicalDate | sxyDate }}</span>\r\n            <span ng-switch-when=\"unemployment\">{{(\"SALAXY.ENUM.InvoiceType.\" + row.entityType + \".label\") | sxyTranslate}}<br/>{{ { start: row.data.periodStart, end: row.data.periodEnd } | sxyDateRange }}</span>\r\n            <span ng-switch-default>{{(\"SALAXY.ENUM.InvoiceType.\" + row.entityType + \".label\") | sxyTranslate}} {{ { start: row.data.periodStart, end: row.data.periodEnd } | sxyDateRange }}</span>\r\n          </small>\r\n        </td class=\"middle\">\r\n        <td class=\"middle\">\r\n          <span ng-class=\"{ 'bg-danger': row.status == 'canceled', 'bg-success': row.status == 'paid' }\" title=\"{{ 'InvoiceStatus.' + row.status | sxyEnumDescr }}\">\r\n            {{ \"InvoiceStatus.\" + row.status | sxyEnum }}\r\n          </span><br />\r\n          <small>{{ \"PaymentChannel.\" + row.data.channel | sxyEnum }}</small>\r\n        </td>\r\n        <td class=\"middle right\">\r\n          <div>{{ row.startAt | sxyDate }}</div>\r\n          <div>{{ row.endAt | sxyDate }}</div>\r\n        </td>\r\n        <td class=\"middle right\">\r\n          {{ row.createdAt | sxyDate }}<br /> {{ row.updatedAt | sxyDate }}\r\n        </td>\r\n        <td class=\"middle right\">\r\n          {{ row.payment | currency }}\r\n        </td>\r\n        <td class=\"middle\" ng-if=\"'test' | sxyIsInRole\">\r\n          <button title=\"{{'SALAXY.UI_Terms.select' | sxyTranslate}}\" class=\"btn btn-block btn-transparent\" type=\"button\" ng-if=\"!$ctrl.isSelected(row)\" ng-click=\"$ctrl.setSelected(row, 'toggle')\">\r\n            <i class=\"bi bi-square\"></i>\r\n          </button>\r\n          <button title=\"{{'SALAXY.UI_Terms.unselect' | sxyTranslate}}\" class=\"btn btn-block btn-transparent\" type=\"button\" ng-if=\"$ctrl.isSelected(row)\" ng-click=\"$ctrl.setSelected(row, 'toggle')\">\r\n            <i class=\"bi bi-check-square\"></i>\r\n          </button>\r\n        </td>\r\n        <td class=\"middle\" ng-if=\"'test' | sxyIsInRole\">\r\n          <button class=\"btn btn-sm btn-block btn-default\" ng-disabled=\"row.isReading\" type=\"button\" ng-click=\"$invoiceTools.export($crud.getItemDataReader(row),true)\">\r\n            <span ng-show=\"row.isReading\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span>\r\n            <span ng-show=\"!row.isReading\">{{ 'SALAXY.NG1.AccountingReportToolsComponent.createExport' | sxyTranslate }}</span>\r\n          </button>\r\n        </td>\r\n        <td class=\"middle right\">\r\n          <a href=\"\" ng-click=\"$crud.showDetails(row)\" class=\"btn btn-primary\">\r\n            {{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\r\n          </a>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n  <div class=\"salaxy-odata-footer\">\r\n    <salaxy-spinner></salaxy-spinner>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/InvoicesPerson.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"salaxy-component salaxy-invoice-tools\" ng-controller=\"InvoiceToolsController as $invoiceTools\" ng-init=\"$invoiceTools.reader = $crud.selectionDataReaderPerson\">\r\n    <div class=\"btn-toolbar\" role=\"toolbar\" aria-label=\"Invoice options\">\r\n      <div class=\"btn-group btn-group-sm dropdown\">\r\n        <button id=\"invoiceOptionsFileType\" type=\"button\" class=\"btn btn-primary dropdown-toggle\" data-bs-toggle=\"dropdown\">\r\n          <i class=\"bi bi-file-earmark-pdf\"></i>&nbsp;{{'SALAXY.ENUM.ExportMethod.filePdf.label' | sxyTranslate}}\r\n        </button>\r\n      </div>\r\n      <div class=\"btn-group btn-group-sm ms-1\">\r\n        <button ng-disabled=\"$crud.selectionDataReaderPerson.disabled()\" id=\"reportExport\" type=\"button\" class=\"btn btn-default\" ng-click=\"$invoiceTools.export()\">\r\n          {{'SALAXY.NG1.AccountingReportToolsComponent.createExport' | sxyTranslate}}\r\n        </button>\r\n      </div>\r\n    </div>\r\n  </div>\r\n\r\n  <table class=\"table\">\r\n    <thead>\r\n      <tr>\r\n        <th colspan=\"2\"><span sxy-orderby=\"otherPartyInfo/avatar/displayName\" sxy-text=\"SALAXY.NG1.InvoicesComponent.receiverAndType\"></span></th>\r\n        <th>\r\n          <span sxy-orderby=\"status\" sxy-text=\"SALAXY.NG1.InvoicesComponent.status\"></span><br />\r\n        </th>\r\n        <th class=\"right\">\r\n          <span sxy-orderby=\"startAt\" sxy-text=\"SALAXY.NG1.InvoicesComponent.invoiceDate\"></span><br/>\r\n          <span sxy-orderby=\"endAt\" sxy-text=\"SALAXY.NG1.InvoicesComponent.dueDate\"></span>\r\n        </th>\r\n        <th class=\"right\">\r\n          <span sxy-orderby=\"createdAt\" sxy-text=\"SALAXY.UI_Terms.created\"></span><br />\r\n          <span sxy-orderby=\"updatedAt\" sxy-text=\"SALAXY.UI_Terms.updated\"></span>\r\n        </th>\r\n        <th class=\"right\"><span sxy-orderby=\"payment\" sxy-text=\"SALAXY.NG1.InvoicesComponent.sum\"></span></th>\r\n        <th class=\"middle\">\r\n          <button title=\"{{'SALAXY.UI_Terms.chooseAll' | sxyTranslate}}\" class=\"btn btn-block btn-transparent\" type=\"button\" ng-if=\"$ctrl.selectedItems.length == 0\" ng-disabled=\"$ctrl.selectedItems.length == $ctrl.items.length\" ng-click=\"$crud.selectAll()\">\r\n            <i class=\"bi bi-square\"></i>\r\n          </button>\r\n          <button title=\"{{'SALAXY.UI_Terms.unselectAll' | sxyTranslate}}\" class=\"btn btn-block btn-transparent\" type=\"button\" ng-if=\"$ctrl.selectedItems.length > 0\" ng-disabled=\"$ctrl.selectedItems.length == 0\" ng-click=\"$crud.unselectAll()\">\r\n            <i class=\"bi bi-check-square\"></i>\r\n          </button>\r\n        </th>\r\n        <th class=\"right\" colspan=\"2\">\r\n          <div class=\"table-filter-container hidden-xxs\">\r\n            <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" class=\"salaxy-odata-table-search\" placeholder=\"SALAXY.UI_Terms.textSearch\" label-type=\"plain\"></salaxy-input>\r\n          </div>\r\n        </th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat=\"row in $ctrl.items\" ng-show=\"$ctrl.items.length > 0\">\r\n        <td class=\"td-avatar middle\">\r\n          <salaxy-avatar class=\"salaxy-calc-row-type-avatar\" avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n        </td>\r\n        <td class=\"middle\">\r\n          <div>{{ row.otherPartyInfo.avatar.displayName }}</div>\r\n          <small class=\"hidden-xxs\" ng-switch=\"row.entityType\">\r\n            <span ng-switch-when=\"net|gross|foreclosure\" ng-switch-when-separator=\"|\">{{(\"SALAXY.ENUM.InvoiceType.\" + row.entityType + \".label\") | sxyTranslate}} {{ row.logicalDate | sxyDate }}</span>\r\n            <span ng-switch-when=\"unemployment\">{{(\"SALAXY.ENUM.InvoiceType.\" + row.entityType + \".label\") | sxyTranslate}}<br/>{{ { start: row.data.periodStart, end: row.data.periodEnd } | sxyDateRange }}</span>\r\n            <span ng-switch-default>{{(\"SALAXY.ENUM.InvoiceType.\" + row.entityType + \".label\") | sxyTranslate}} {{ { start: row.data.periodStart, end: row.data.periodEnd } | sxyDateRange }}</span>\r\n          </small>\r\n        </td class=\"middle\">\r\n        <td class=\"middle\" ng-if=\"row.entityType !== 'tax' && row.entityType !== 'net'\">\r\n          <span title=\"{{ 'InvoiceStatus.' + row.status | sxyEnumDescr }}\">\r\n            {{ \"InvoiceStatus.forecast\" | sxyEnum }}\r\n          </span><br />\r\n          <small>{{ row.otherPartyInfo.avatar.displayName }} {{'SALAXY.NG1.InvoicesCreateTableComponent.sendsInvoice' | sxyTranslate}}</small>\r\n        </td>\r\n        <td class=\"middle\" ng-if=\"row.entityType === 'tax' || row.entityType === 'net'\">\r\n          <span ng-class=\"{ 'bg-danger': row.status == 'canceled', 'bg-success': row.status == 'paid' }\" title=\"{{ 'InvoiceStatus.' + row.status | sxyEnumDescr }}\">\r\n            {{ \"InvoiceStatus.\" + row.status | sxyEnum }}\r\n          </span><br />\r\n          <small>{{ \"PaymentChannel.\" + row.data.channel | sxyEnum }}</small>\r\n        </td>\r\n        <td class=\"middle right\">\r\n          <div>{{ row.startAt | sxyDate }}</div>\r\n          <div ng-switch=\"$crud.getDueDateType(row)\">\r\n            <span ng-switch-when=\"estimation\">{{ row.endAt | date: 'MMMM' }}</span>\r\n            <del ng-switch-when=\"canceled\" class=\"\">{{ row.endAt | sxyDate }}</del>\r\n            <span ng-switch-when=\"overdue\" class=\"bg-danger\">{{ row.endAt | sxyDate }}</span>\r\n            <em ng-switch-when=\"future\" class=\"disabled\">{{ row.endAt | sxyDate }}</em>\r\n            <span ng-switch-when=\"default\">{{ row.endAt | sxyDate }}</span>\r\n            <span ng-switch-when=\"unknown\">{{ row.endAt | sxyDate }}</span>\r\n          </div>\r\n        </td>\r\n        <td class=\"middle right\">\r\n          {{ row.createdAt | sxyDate }}<br /> {{ row.updatedAt | sxyDate }}\r\n        </td>\r\n        <td class=\"middle right\">\r\n          {{ row.payment | currency }}\r\n        </td>\r\n        <td class=\"middle\" ng-if=\"row.entityType === 'tax' || row.entityType === 'net'\">\r\n          <button title=\"{{'SALAXY.UI_Terms.select' | sxyTranslate}}\" class=\"btn btn-block btn-transparent\" type=\"button\" ng-if=\"!$ctrl.isSelected(row)\" ng-click=\"$ctrl.setSelected(row, 'toggle')\">\r\n            <i class=\"bi bi-square\"></i>\r\n          </button>\r\n          <button title=\"{{'SALAXY.UI_Terms.unselect' | sxyTranslate}}\" class=\"btn btn-block btn-transparent\" type=\"button\" ng-if=\"$ctrl.isSelected(row)\" ng-click=\"$ctrl.setSelected(row, 'toggle')\">\r\n            <i class=\"bi bi-check-square\"></i>\r\n          </button>\r\n        </td>\r\n        <td class=\"middle\" ng-if=\"row.entityType !== 'tax' && row.entityType !== 'net'\"></td>\r\n        <td class=\"middle\">\r\n          <button ng-click=\"$crud.showPaymentDialog(row)\" ng-if=\"row.entityType === 'net' && (row.status === 'paid' || row.status === 'unread')\" class=\"btn btn-sm btn-block btn-default\" ng-disabled=\"row.isReading\" type=\"button\">\r\n            <span ng-if=\"row.status === 'paid'\">{{ 'SALAXY.NG1.InvoicesCreateTableComponent.cancelInvoice' | sxyTranslate }}</span>\r\n            <span ng-if=\"row.status === 'unread'\">{{ 'SALAXY.NG1.InvoicesCreateTableComponent.payInvoice' | sxyTranslate }}</span>\r\n          </button>\r\n        </td>\r\n        <td class=\"middle right\">\r\n          <a ng-if=\"row.entityType === 'tax' || row.entityType === 'net'\" ng-href=\"{{$crud.getContentUrl(row.id, true)}}\" target=\"_blank\" title=\"{{ 'SALAXY.UI_Terms.printable' | sxyTranslate}}\" class=\"btn btn-sm btn-secondary\"><i\r\n            class=\"bi bi-file-earmark-pdf\"></i></a>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n  <div class=\"salaxy-odata-footer\">\r\n    <salaxy-spinner></salaxy-spinner>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/InvoicesSepa.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div ng-controller=\"InvoiceToolsController as $invoiceTools\">\r\n    <div class=\"btn-toolbar\">\r\n      <div class=\"btn-group\">\r\n        <salaxy-input-enum type=\"dropdown\" name=\"fileType\" label-type=\"plain\" ng-model=\"$invoiceTools.fileTypeId\" options=\"$invoiceTools.fileTypeOptions\" remember=\"invoice\"></salaxy-input-enum>\r\n      </div>\r\n      <div class=\"btn-group dropdown\">\r\n        <button id=\"btnHide\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\">\r\n          {{ ('SALAXY.MODEL.InvoiceListItem.status.title' | sxyTranslate) }}: {{$crud.statusFilter.text}}\r\n        </button>\r\n        <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"btnHide\">\r\n          <li role=\"menuitem\" ng-repeat=\"statusFilter in $crud.statusFilters\">\r\n            <a href=\"\" ng-click=\"$crud.statusFilter = statusFilter\" class=\"dropdown-item\">{{statusFilter.text}}</a>\r\n          </li>\r\n        </ul>\r\n      </div>\r\n      <div class=\"btn-group ms-1\">\r\n        <salaxy-datepicker-popup name=\"refDateMonth\" label-type=\"plain\" format=\"year\" ng-model=\"$crud.queryYear\"></salaxy-datepicker-popup>\r\n      </div>\r\n      <button type=\"button\" ng-click=\"$crud.loadData()\" class=\"btn btn-primary\">Hae</button>\r\n    </div>\r\n    <div class=\"table-responsive\">\r\n      <table class=\"table\" style=\"min-height: 250px;\">\r\n        <thead>\r\n          <tr>\r\n            <th colspan=\"1\">\r\n              <span sxy-text=\"SALAXY.NG1.InvoicesComponent.payer\"></span>\r\n            </th>\r\n            <th colspan=\"2\">\r\n              <span>                \r\n                <input type=\"text\" ng-model=\"$crud.otherPartyNameFilter\" class=\"form-control\" autocomplete=\"off\" id=\"otherPartyName\" name=\"otherPartyName\" placeholder=\"{{'SALAXY.NG1.InvoicesComponent.receiver' | sxyTranslate}}\">\r\n              </span>\r\n            </th>\r\n            <th>\r\n              <span sxy-text=\"SALAXY.MODEL.InvoiceData.channel.title\"></span><br />\r\n              <span sxy-text=\"SALAXY.NG1.InvoicesComponent.iban\"></span>\r\n            </th>\r\n            <th>\r\n              <div class=\"btn-group dropdown\">\r\n                <button id=\"btnHide\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\">\r\n                  {{ ('SALAXY.NG1.InvoicesComponent.invoiceType' | sxyTranslate) }}: {{$crud.invoiceEntityType.label}}\r\n                </button>\r\n                <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"btnHide\">\r\n                  <li role=\"menuitem\" ng-repeat=\"invoiceEntityType in $crud.invoiceEntityTypes\">\r\n                    <a href=\"\" ng-click=\"$crud.invoiceEntityType = invoiceEntityType\" class=\"dropdown-item\">{{invoiceEntityType.label}}</a>\r\n                  </li>\r\n                </ul>\r\n              </div>\r\n            </th>\r\n            <th>\r\n              <span sxy-orderby=\"status\" sxy-text=\"SALAXY.MODEL.InvoiceListItem.status.title\"></span><br />\r\n              <span sxy-text=\"SALAXY.MODEL.InvoiceListItem.reference.title\"></span>/<span sxy-text=\"SALAXY.MODEL.InvoiceListItem.messages.title\"></span>\r\n            </th>\r\n            <th class=\"right\">\r\n              <span sxy-orderby=\"endAt\" sxy-text=\"SALAXY.MODEL.InvoiceData.dueDate.tableHeading\"></span><br />\r\n              <span sxy-text=\"SALAXY.MODEL.InvoiceData.date.title\"></span>\r\n            </th>\r\n            <th class=\"right\">\r\n              <span sxy-text=\"SALAXY.MODEL.InvoiceListItem.payment.tableHeading\"></span><br />\r\n              <span sxy-text=\"SALAXY.MODEL.InvoiceListItem.payment.title\"></span>\r\n            </th>\r\n            <th colspan=\"2\">\r\n              <span sxy-text=\"SALAXY.NG1.InvoicesComponent.createInvoices\"></span><br />\r\n              <span sxy-text=\"SALAXY.NG1.InvoicesComponent.markAsPaid\"></span>\r\n            </th>\r\n            <th></th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr ng-repeat-start=\"group in $crud.getGroupedItems() | filter: $crud.invoiceFilter\" class=\"active\">\r\n            <td class=\"td-avatar middle\">\r\n              <salaxy-avatar avatar=\"group.ownerInfo.avatar\"></salaxy-avatar>\r\n            </td>\r\n            <td class=\"td-name middle\" colspan=\"2\">\r\n              <strong>{{group.ownerInfo.avatar.displayName}}</strong><br />\r\n              <span>{{group.ownerInfo.officialId}}</span>\r\n            </td>\r\n            <td class=\"middle\">\r\n              <span>{{ \"PaymentChannel.\" + group.channel | sxyEnum }}</span>\r\n            </td>\r\n            <td>\r\n              <span>{{(\"SALAXY.ENUM.InvoiceType.\" + group.invoiceType + \".label\") | sxyTranslate}}</span>\r\n            </td>\r\n            <td class=\"middle\" ng-if=\"!$crud.groupHasDuplicateInvoices(group)\">\r\n              <strong ng-class=\"{ 'bg-danger': group.status == 'canceled', 'bg-success': group.status == 'paid' }\" title=\"{{ 'InvoiceStatus.' + group.status | sxyEnumDescr }}\">\r\n              {{ \"InvoiceStatus.\" + group.status | sxyEnum }}\r\n              </strong>\r\n            </td>\r\n            <td class=\"middle\" ng-if=\"$crud.groupHasDuplicateInvoices(group)\">\r\n              <strong class=\"text-danger\">\r\n                {{ 'SALAXY.NG1.InvoicesComponent.duplicateInvoices' | sxyTranslate }}\r\n              </strong>\r\n            </td>\r\n            <td class=\"middle right\">\r\n              <strong>{{ group.dueDate | sxyDate }}</strong>\r\n            </td>\r\n            <td class=\"middle right\">\r\n              <strong>{{ group.payment | currency }}</strong>\r\n            </td>\r\n            <td class=\"middle\">\r\n              <button class=\"btn btn-default btn-block\" ng-if=\"group.status == 'unread' || group.status == 'read' || group.status== 'waitingConfirmation'\" ng-disabled=\"group.isReadingread || group.isReadingpaid || $crud.groupHasDuplicateInvoices(group)\" ng-click=\"$invoiceTools.export($crud.getGroupDataReader(group,'waitingConfirmation'),true)\">\r\n              <span ng-show=\"group.isReadingwaitingConfirmation\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span>\r\n              <span ng-show=\"!group.isReadingwaitingConformation\" sxy-text=\"SALAXY.NG1.InvoicesComponent.createInvoiceBtn\"></span>\r\n            </button>\r\n            </td>\r\n            <td class=\"middle\">\r\n              <button class=\"btn btn-default btn-block\" ng-if=\"group.status == 'unread' || group.status == 'read' || group.status== 'waitingConfirmation'\" ng-disabled=\"group.isReadingread || group.isReadingpaid || $crud.groupHasDuplicateInvoices(group)\" ng-click=\"$invoiceTools.export($crud.getGroupDataReader(group,'paid'),true)\">\r\n              <span ng-show=\"group.isReadingpaid\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span>\r\n              <span ng-show=\"!group.isReadingpaid\" sxy-text=\"SALAXY.NG1.InvoicesComponent.markAsPaidBtn\"></span>\r\n            </button>\r\n            </td>\r\n            <td class=\"middle\">\r\n              <button class=\"btn btn-default btn-block\" ng-click=\"$crud.showGroupDialog(group)\" sxy-text=\"SALAXY.NG1.InvoicesComponent.detailsBtn\"></button>\r\n            </td>\r\n          </tr>\r\n          <tr ng-repeat-end ng-repeat=\"invoice in group.invoices | filter: {otherPartyInfo:{avatar:{displayName: $crud.otherPartyNameFilter}}}\" >\r\n            <td></td>\r\n            <td class=\"td-avatar-1line middle\">\r\n              <salaxy-avatar avatar=\"invoice.otherPartyInfo.avatar\"></salaxy-avatar>\r\n            </td>\r\n            <td class=\"td-name middle\">\r\n              <div><strong>{{invoice.otherPartyInfo.avatar.displayName}}</strong></div>\r\n              <small ng-switch=\"invoice.entityType\">\r\n              <span ng-switch-when=\"net|gross|foreclosure\" ng-switch-when-separator=\"|\">{{(\"SALAXY.ENUM.InvoiceType.\" + invoice.entityType + \".label\") | sxyTranslate}} {{ invoice.logicalDate | sxyDate }}</span>\r\n              <span ng-switch-when=\"unemployment\">{{(\"SALAXY.ENUM.InvoiceType.\" + invoice.entityType + \".label\") | sxyTranslate}}<br/>{{ { start: invoice.data.periodStart, end: invoice.data.periodEnd } | sxyDateRange }}</span>\r\n              <span ng-switch-default>{{(\"SALAXY.ENUM.InvoiceType.\" + invoice.entityType + \".label\") | sxyTranslate}} {{ { start: invoice.data.periodStart, end: invoice.data.periodEnd } | sxyDateRange }}</span>\r\n            </small>\r\n            </td>\r\n            <td class=\"middle\">\r\n              <span ng-if=\"invoice.otherPartyInfo.ibanNumber\">{{ invoice.otherPartyInfo.ibanNumber }}</span>\r\n              <span ng-if=\"!invoice.otherPartyInfo.ibanNumber\" class=\"alert-danger\" sxy-text=\"SALAXY.NG1.InvoicesComponent.noIbanNumber\"></span>\r\n            </td>\r\n            <td class=\"middle\">\r\n              {{(\"SALAXY.ENUM.InvoiceType.\" + invoice.entityType + \".label\") | sxyTranslate}}\r\n            </td>\r\n            <td class=\"middle\">\r\n              {{ invoice.reference || (\"SALAXY.ENUM.InvoiceType.\" + invoice.entityType + \".label\") | sxyTranslate }}\r\n            </td>\r\n            <td class=\"middle right\">\r\n              {{ invoice.data.date | sxyDate }}\r\n            </td>\r\n            <td class=\"middle right\">\r\n              {{ invoice.payment | currency }}\r\n            </td>\r\n            <td class=\"middle\">\r\n              <button class=\"btn btn-default btn-xs btn-block\" ng-if=\"invoice.status == 'unread'  || invoice.status == 'read' || invoice.status== 'waitingConfirmation'\" ng-disabled=\"invoice.isReadingwaitingConfirmation || invoice.isReadingpaid || $crud.groupHasDuplicateInvoices(group)\" ng-click=\"$invoiceTools.export($crud.getGroupItemDataReader(invoice,'waitingConfirmation'),true)\">\r\n              <span ng-show=\"invoice.isReadingwaitingConfirmation\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span>\r\n              <span ng-show=\"!invoice.isReadingwaitingConfirmation\" sxy-text=\"SALAXY.NG1.InvoicesComponent.createInvoiceBtn\"></span>\r\n            </button>\r\n            </td>\r\n            <td class=\"middle\">\r\n              <button class=\"btn btn-default btn-xs btn-block\" ng-if=\"invoice.status == 'unread' || invoice.status == 'read' || invoice.status== 'waitingConfirmation'\" ng-disabled=\"invoice.isReadingwaitingConfirmation || invoice.isReadingpaid || $crud.groupHasDuplicateInvoices(group)\" ng-click=\"$invoiceTools.export($crud.getGroupItemDataReader(invoice,'paid'),true)\">\r\n              <span ng-show=\"invoice.isReadingpaid\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span>\r\n              <span ng-show=\"!invoice.isReadingpaid\" sxy-text=\"SALAXY.NG1.InvoicesComponent.markAsPaidBtn\"></span>\r\n            </button>\r\n            </td>\r\n            <td class=\"middle\">\r\n              <button ng-click=\"$crud.showInvoiceDialog(invoice)\" title=\"{{ 'SALAXY.NG1.InvoicesComponent.detailsBtn' | sxyTranslate}}\" class=\"btn btn-xs btn-default btn-block\" sxy-text=\"SALAXY.NG1.InvoicesComponent.detailsBtn\">\r\n              \r\n            </button>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/IrEpr.html\",`<div ng-class=\"$ctrl.getCssClass()\">  \r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\">\r\n            <input type=\"text\" ng-model=\"$ctrl.rawSearchStringOther\"  ng-change=\"$ctrl.searchChanged('both')\" class=\"form-control\" autocomplete=\"off\"\r\n            id=\"searchx111\" name=\"searchx111\" placeholder=\"{{'SALAXY.NG1_Other.Roles.worker' | sxyTranslate}}\"\r\n            ng-model-options=\"{allowInvalid: true, debounce: 250, updateOn: 'default' }\" maxlength=\"1024\">\r\n          </th>\r\n          <th><salaxy-input-enum ng-model=\"irEprStatus\" ng-change=\"$ctrl.setFilter('status', irEprStatus, 'eq', $ctrl.originalFilter)\" placeholder=\"SALAXY.MODEL.EarningsPaymentListItem.status.title\" name=\"status\" enum=\"EarningsPaymentReportStatus\" options=\"{ '': 'SALAXY.UI_Terms.showAll','new': 'SALAXY.ENUM_IR.EarningsPaymentReportStatus.new.label', 'succeeded': 'SALAXY.ENUM_IR.EarningsPaymentReportStatus.succeeded.label', 'canceled' : 'SALAXY.ENUM_IR.EarningsPaymentReportStatus.canceled.label' , 'error': 'SALAXY.ENUM_IR.EarningsPaymentReportStatus.error.label', 'invalid': 'SALAXY.ENUM_IR.EarningsPaymentReportStatus.invalid.label', 'scheduled': 'SALAXY.ENUM_IR.EarningsPaymentReportStatus.scheduled.label' }\" label-type=\"plain\"></salaxy-input-enum> </th>\r\n          <th class=\"right\"><span sxy-orderby=\"salaryDate\" sxy-text=\"SALAXY.NG1.IrEprComponent.salaryDate\"></span></th>\r\n          <th class=\"right\"><span sxy-orderby=\"endAt\" sxy-text=\"SALAXY.NG1.IrEprComponent.sendTime\"></span></th>\r\n          <th class=\"right \">\r\n            <span sxy-orderby=\"payment\" sxy-text=\"SALAXY.NG1.IrEprComponent.payment\"></span><br />\r\n            <span sxy-orderby=\"grossSalary\" sxy-text=\"SALAXY.NG1.IrEprComponent.grossSalary\"></span>\r\n          </th>\r\n          <th class=\"right\" colspan=\"2\"></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar middle\">\r\n            <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"td-name middle\">\r\n            <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br />\r\n            <span>{{row.otherPartyInfo.email}}</span>\r\n          </td>\r\n          <td class=\"middle\">\r\n            {{ \"SALAXY.ENUM_IR.EarningsPaymentReportStatus.\" + row.status + \".label\" | sxyTranslate }}\r\n            <div ng-if=\"$crud.isIrModified(row)\"><span class=\"badge bg-danger\" title=\"{{'SALAXY.NG1.IrEprComponent.irModified' | sxyTranslate}}\" sxy-text=\"SALAXY.NG1.IrEprComponent.modified\" ps=\"!\"></span></div>\r\n            <div ng-if=\"$crud.isDelayed(row)\"><span class=\"badge bg-danger\" title=\"Myöhässä\" sxy-text=\"SALAXY.NG1.IrEprComponent.delayed\" ps=\"!\"></span></div>\r\n          </td>\r\n          <td class=\"middle right\">\r\n            {{ row.salaryDate | date }}\r\n          </td>\r\n          <td class=\"middle right\">\r\n            <div ng-if=\"row.data.firstDeliveredAt\" title=\"{{'SALAXY.NG1.IrEprComponent.firstDelivery' | sxyTranslate}}\">\r\n              <span>{{ row.data.firstDeliveredAt | date}}</span>\r\n            </div>\r\n            <div ng-if=\"!row.data.scheduledFor && row.data.lastDeliveredAt && row.data.firstDeliveredAt != row.data.lastDeliveredAt\" title=\"{{'SALAXY.NG1.IrEprComponent.latestDelivery' | sxyTranslate}}\">\r\n              <span>{{ row.data.lastDeliveredAt | date}}</span>\r\n            </div>\r\n            <div ng-if=\"row.data.scheduledFor\" title=\"{{'SALAXY.NG1.IrEprComponent.latestDelivery' | sxyTranslate}}\">\r\n              <span class=\"badge bg-warning\">{{ row.data.scheduledFor | date}}</span>\r\n            </div>\r\n          </td>\r\n          <td class=\"right middle\">\r\n            {{ row.payment | currency }}<br /> {{ row.grossSalary | currency }}\r\n          </td>\r\n          <td class=\"middle\">\r\n            <a ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-default\"><i\r\n              class=\"bi bi-info-circle visible-xxs\"></i><span class=\"hidden-xxs\" sxy-text=\"SALAXY.UI_Terms.show\"></span></a>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/IrPsr.html\",`<div ng-class=\"$ctrl.getCssClass()\">  \r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th sxy-text=\"SALAXY.NG1.IrPsrComponent.notificationType\"></th>\r\n          <th sxy-text=\"SALAXY.NG1.IrPsrComponent.status\"></th>\r\n          <th sxy-text=\"SALAXY.NG1.IrPsrComponent.month\" class=\"right\"><span sxy-orderby=\"logicalDate\"></span></th>\r\n          <th sxy-text=\"SALAXY.NG1.IrPsrComponent.sendTime\" class=\"right\"><span sxy-orderby=\"endAt\"></span></th>\r\n          <th sxy-text=\"SALAXY.NG1.IrPsrComponent.savaPayment\" class=\"right\"><span sxy-orderby=\"payment\"></span></th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.IrPsrComponent.expense\"></th>\r\n          <th class=\"right\" colspan=\"2\"></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"middle\">{{ \"SALAXY.ENUM_IR.SummaryTransactionCode.\" + row.entityType + \".label\" | sxyTranslate }}</td>\r\n          <td class=\"middle\">\r\n            {{ \"SALAXY.ENUM_IR.PayerSummaryReportStatus.\" + row.status + \".label\" | sxyTranslate }}\r\n            <div ng-if=\"$crud.isIrModified(row)\"><span class=\"badge bg-danger\" title=\"Ilmoitusta on muokattu käsin\" sxy-text=\"SALAXY.NG1.IrPsrComponent.modified\" ps=\"!\"></span></div>\r\n            <div ng-if=\"$crud.isDelayed(row)\"><span class=\"badge bg-danger\" title=\"Myöhässä\" sxy-text=\"SALAXY.NG1.IrPsrComponent.delayed\" ps=\"!\"></span></div>\r\n          </td>\r\n          <td class=\"middle right\">\r\n            {{ row.logicalDate | date : 'MM/yyyy' }}\r\n          </td>\r\n          <td class=\"middle right\">\r\n            <div ng-if=\"row.data.firstDeliveredAt\" title=\"{{'SALAXY.NG1.IrPsrComponent.firstDelivery' | sxyTranslate}}\">\r\n              <span>{{ row.data.firstDeliveredAt | date}}</span>\r\n            </div>\r\n            <div ng-if=\"!row.data.scheduledFor && row.data.lastDeliveredAt && row.data.firstDeliveredAt != row.data.lastDeliveredAt\" title=\"{{'SALAXY.NG1.IrPsrComponent.latestDelivery' | sxyTranslate}}\">\r\n              <span>{{ row.data.lastDeliveredAt | date}}</span>\r\n            </div>\r\n            <div ng-if=\"row.data.scheduledFor\" title=\"{{'SALAXY.NG1.IrPsrComponent.latestDelivery' | sxyTranslate}}\">\r\n              <span class=\"badge bg-warning\">{{ row.data.scheduledFor | date}}</span>\r\n            </div>\r\n          </td>\r\n          <td class=\"right middle\">\r\n            {{ row.payment | currency }}\r\n          </td>\r\n          <td class=\"right middle\">{{ row.data.socialSecurityDeduction | currency }}</td>\r\n          <td class=\"middle\">\r\n            <a ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-default\"><i class=\"bi bi-info-circle visible-xxs\"></i><span\r\n              class=\"hidden-xxs\" sxy-text=\"SALAXY.UI_Terms.show\"></span></a>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/MessageThreads.html\",`<div ng-class=\"$ctrl.getCssClass()\" class=\"table-responsive\">\r\n  <table class=\"table\">\r\n    <thead>\r\n      <tr>\r\n        <th>&nbsp;</th>\r\n        <th>\r\n          <span><span sxy-text=\"SALAXY.NG1.MessageThreadsComponent.title\"></span></span><br/>\r\n          <span sxy-orderby=\"otherPartyInfo/avatar/displayName\"><span sxy-text=\"SALAXY.NG1.MessageThreadsComponent.sender\"></span></span>\r\n        </th>\r\n        <th class=\"right\">\r\n          <span sxy-orderby=\"salaryDate\"><span sxy-text=\"SALAXY.NG1.MessageThreadComponent.salaryDate\"></span></span><br/>\r\n          <span><span sxy-text=\"SALAXY.NG1_Pages.Service.ApprovePayrollList.period\"></span></span><br/>\r\n          <span><span sxy-text=\"SALAXY.NG1.MessageThreadsComponent.answered\"></span></span>\r\n        </th>\r\n        <th class=\"right \">\r\n          <span sxy-orderby=\"grossSalary\"><span sxy-text=\"SALAXY.NG1_Pages.Service.ApproveCalculationList.salary\" ></span></span><br />\r\n          <span sxy-orderby=\"payment\"><span sxy-text=\"SALAXY.NG1_Pages.Service.ApproveCalculationList.payment\" ></span></span><br/>\r\n          <span><span sxy-text=\"SALAXY.NG1_Pages.Service.ApprovePayrollList.calculations\"></span></span>\r\n        </th>\r\n        <th class=\"right\">\r\n          <span sxy-orderby=\"status\"><span sxy-text=\"SALAXY.NG1.MessageThreadsComponent.status\"></span></span><br />\r\n          <span sxy-orderby=\"createdAt\"><span sxy-text=\"SALAXY.UI_Terms.created\"></span></span><br />\r\n          <span sxy-orderby=\"updatedAt\"><span sxy-text=\"SALAXY.UI_Terms.updated\"></span></span>\r\n        </th>\r\n        <th></th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat=\"row in $ctrl.items\">\r\n        <td class=\"td-avatar middle\">\r\n          <salaxy-avatar class=\"float-end\" avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n        </td>\r\n        <td class=\"middle\">\r\n          <span>\r\n            <b>{{row.data.title}}</b>\r\n          </span>\r\n          <span class=\"label label-primary\" ng-if=\"row.data.otherPartyUnreadCount\">\r\n            {{ row.data.otherPartyUnreadCount }}\r\n            <i class=\"bi bi-chat-fill\" aria-hidden=\"true\"></i>\r\n          </span>\r\n          <div>{{row.otherPartyInfo.avatar.displayName}}</div>\r\n          <div class=\"truncate\" style=\"max-width: 300px; font-size: 0.9em;\"><i>{{ row.data.otherPartyLastMessage }}</i></div>\r\n        </td>\r\n        <td class=\"right\">\r\n          {{ row.salaryDate | date }}<br /> {{ { start: row.data.periodStart, end: row.data.periodEnd } | sxyDateRange }}<br/> {{ row.data.otherPartyUpdatedAt | sxyTime }}\r\n        </td>\r\n        <td class=\"right\">\r\n          {{ row.grossSalary | currency }}<br /> {{ row.payment | currency }}<br/> {{ row.data.calcCount ? (row.data.calcCount + \" \" + (\"SALAXY.NG1.MessageThreadsComponent.pce\" | sxyTranslate)) : \"-\" }}\r\n        </td>\r\n        <td class=\"middle right\">\r\n          <div ng-class=\"{ 'text-success': row.status == 'approved', 'text-danger': row.status == 'rejected' }\">\r\n            <span ng-switch=\"row.status\">\r\n              <span ng-switch-when=\"draft\" sxy-text=\"SALAXY.NG1.MessageThreadsComponent.message\"></span>\r\n            <span ng-switch-when=\"active\" sxy-text=\"SALAXY.NG1.MessageThreadsComponent.waiting\"></span>\r\n            <span ng-switch-default>{{ \"MessageThreadStatus.\" + row.status | sxyEnum }}</span>\r\n            </span>\r\n          </div>\r\n          {{ row.createdAt | sxyTime }}<br /> {{ row.updatedAt | sxyTime }}\r\n        </td>\r\n        <td class=\"middle\">\r\n          <a ng-if=\"!('aidemo' | sxyIsInRole)\" href=\"#{{$crud.getDefaults().detailsUrl}}{{ row.id }}\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-primary btn-block\">\r\n            <i class=\"bi bi-chat-fill d-inline-block d-sm-none\"></i>\r\n            <span sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n          </a>\r\n          <button ng-if=\"('aidemo' | sxyIsInRole)\" ng-click=\"$crud.navigateToBusinessObject(row, $crud.getDefaults().detailsUrl)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-primary btn-block\">\r\n            <i class=\"bi bi-chat-fill d-inline-block d-sm-none\"></i>\r\n            <span sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n          </button>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/MessageThreadsApproval.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <table class=\"table\">\r\n    <thead>\r\n      <tr>\r\n        <th>&nbsp;</th>\r\n        <th sxy-orderby=\"data/title\">\r\n          <span sxy-text=\"SALAXY.NG1.MessageThreadsComponent.title\"></span>\r\n          <div>Lähettäjä</div>\r\n        </th>\r\n        <th class=\"right\">Tila</th>\r\n        <th class=\"right\">\r\n          <span sxy-orderby=\"createdAt\"><span sxy-text=\"SALAXY.UI_Terms.created\"></span></span><br />\r\n          <span sxy-orderby=\"updatedAt\"><span sxy-text=\"SALAXY.UI_Terms.updated\"></span></span>\r\n        </th>\r\n        <th class=\"hidden-xxs\"></th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat=\"row in $ctrl.items\">\r\n        <td class=\"td-avatar middle\">\r\n          <salaxy-avatar class=\"float-end\" avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n        </td>\r\n        <td class=\"middle\">\r\n          <span ng-switch=\"row.data.usecaseUri\">\r\n            <b ng-switch-when=\"palkkaus.fi/testing/messages-proto/timer\">Kellokortti</b>\r\n            <b ng-switch-when=\"palkkaus.fi/testing/messages-proto/timeReport\">Työaikaraportti</b>\r\n            <b ng-switch-when=\"palkkaus.fi/testing/messages-proto/hourlyReport\">Tuntiraportti</b>\r\n            <b ng-switch-when=\"palkkaus.fi/testing/messages-proto/calcRow\">Palkkarivit</b>\r\n            <b ng-switch-default>{{ row.data.title || row.data.usecaseUri }}</b>\r\n          </span>\r\n          \r\n          <span class=\"label label-primary\" ng-if=\"row.data.otherPartyUnreadCount\">\r\n            {{ row.data.otherPartyUnreadCount }}\r\n            <i class=\"bi bi-chat-fill\" aria-hidden=\"true\"></i>\r\n          </span>\r\n\r\n          <div>{{row.otherPartyInfo.avatar.displayName}}</div>\r\n        </td>\r\n        <td class=\"right\">\r\n          <div ng-class=\"{ 'text-success': row.status == 'approved', 'text-danger': row.status == 'rejected' }\">{{ \"MessageThreadStatus.\" + row.status | sxyEnum }}</div>\r\n        </td>\r\n        <td class=\"middle right\">\r\n          {{ row.createdAt | sxyTime }}<br /> {{ row.updatedAt | sxyTime }}\r\n        </td>\r\n        <td class=\"middle\">\r\n          <a href=\"#{{$crud.getDefaults().approvalUrl}}{{ row.id }}\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-primary btn-block\">\r\n            <i class=\"bi bi-chat-fill d-inline-block d-sm-none\"></i>\r\n            <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n          </a>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/PaymentChannelSelect.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"visible-xxs\">\r\n    <div class=\"table-filter-container-mobile\">\r\n      <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n      </salaxy-input>\r\n    </div>\r\n  </div>\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\">\r\n            <div sxy-orderby=\"shortText\"><span sxy-text=\"SALAXY.NG1.PaymentChannelSelectComponent.exportDefinition\"></span></div>\r\n            <div sxy-text=\"SALAXY.NG1.PaymentChannelSelectComponent.targetChannel\"></div>\r\n          </th>\r\n          <th sxy-orderby=\"owner\" colspan=\"2\">\r\n            <div sxy-text=\"SALAXY.NG1.ApiCrudObjectComponent.owner\"></div>\r\n            <div sxy-text=\"SALAXY.NG1.ApiCrudObjectComponent.status\"></div>\r\n          </th>\r\n\r\n          <th class=\"right hidden-xxs\" colspan=\"2\">\r\n            <div class=\"table-filter-container\">\r\n              <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" class=\"salaxy-odata-table-search\" placeholder=\"SALAXY.UI_Terms.textSearch\" label-type=\"plain\"></salaxy-input>\r\n            </div>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar middle\">\r\n            <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"middle\">\r\n            <div title=\"{{ row.shortText }} ({{ row.id }})\">\r\n              <strong>{{ row.otherPartyInfo.avatar.displayName }}</strong>\r\n            </div>\r\n          </td>\r\n          <td class=\"td-avatar middle\">\r\n            <salaxy-avatar avatar=\"row.ownerInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"middle\">\r\n            <div>{{ row.ownerInfo.avatar.displayName }}</div>\r\n            <div>{{ \"AccountingTargetStatus.\" + row.status | sxyEnum }}</div>\r\n          </td>\r\n          <td class=\"right middle\">\r\n            <button class=\"btn btn-sm\" type=\"button\" ng-class=\"$ctrl.isSelected(row) ? 'btn-danger' : 'btn-info'\" ng-click=\"$ctrl.setSelected(row, 'toggle')\">\r\n              {{ $ctrl.isSelected(row) ? ('SALAXY.UI_Terms.unselect' | sxyTranslate) : ('SALAXY.NG1.UI_Terms.select' | sxyTranslate) }}\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/Payrolls-select.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"table-responsive\">\r\n    <div class=\"visible-xxs\">\r\n      <div class=\"table-filter-container-mobile\">\r\n        <salaxy-input name=\"search_xxs{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n        </salaxy-input>\r\n      </div>\r\n    </div>\r\n    <table class=\"table\">\r\n      <thead>\r\n        <tr>\r\n          <th>\r\n            <span sxy-text=\"SALAXY.NG1.PayrollListComponent.description\"></span>\r\n            <span class=\"label label-primary clickable\" ng-if=\"$ctrl.selectedItems.length\" ng-click=\"$ctrl.selectedItems.splice(0,$ctrl.selectedItems.length)\"> {{'SALAXY.UI_Terms.chosen' | sxyTranslate}}: {{ $ctrl.selectedItems.length }} <i class=\"bi bi-x-circle\"></i></span>\r\n            <div>\r\n              <span sxy-text=\"SALAXY.NG1.PayrollListComponent.salaryDate\"></span>\r\n            </div>\r\n          </th>\r\n          <th sxy-orderby=\"status\">\r\n            <span sxy-text=\"SALAXY.NG1.PayrollListComponent.status\"></span>\r\n          </th>\r\n          <th class=\"right\">\r\n            <div sxy-orderby=\"endAt\">\r\n              <span sxy-text=\"SALAXY.NG1.PayrollListComponent.period\"></span>\r\n            </div>\r\n          </th>\r\n          <th class=\"right\">\r\n            <span sxy-text=\"SALAXY.NG1.PayrollListComponent.paymentDate\"></span>\r\n          </th>\r\n          <th class=\"right\">\r\n            <span sxy-text=\"SALAXY.NG1.PayrollListComponent.calculations\"></span>\r\n            <div sxy-orderby=\"grossSalary\">\r\n              <span sxy-text=\"SALAXY.NG1.PayrollListComponent.grossSalaries\"></span>\r\n            </div>\r\n          </th>\r\n          <th class=\"right\" colspan=\"2\">\r\n            <div class=\"table-filter-container\">\r\n              <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" class=\"salaxy-odata-table-search\" placeholder=\"SALAXY.UI_Terms.textSearch\" label-type=\"plain\"></salaxy-input>\r\n            </div>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"\">\r\n            <div class=\"payroll-title\"><strong>{{ row.data.title }}</strong></div>\r\n            <div class=\"payroll-info\">{{ row.salaryDate | date }}</div>\r\n          </td>\r\n          <td class=\"\">\r\n            <div>\r\n              {{ 'PayrollStatus.' + row.status | sxyEnum }}\r\n              <span ng-if=\"row.data.calendarEvent\" class=\"badge bg-primary\">\r\n                <i class=\"bi bi-calendar3\" aria-hidden=\"true\"></i>\r\n                <span sxy-text=\"SALAXY.NG1.PayrollListComponent.calendarEvent\"></span>\r\n              </span>\r\n              <i ng-if=\"row.data.calendarOccurence\" class=\"bi bi-calendar3 text-primary\" aria-hidden=\"true\" title=\"{{ 'SALAXY.NG1.PayrollListComponent.calendarOccurence' | sxyTranslate }}\"></i>\r\n              <i ng-if=\"!row.data.calendarOccurence && row.data.template\" class=\"bi bi-copy text-primary\" aria-hidden=\"true\" title=\"{{ 'SALAXY.NG1.PayrollListComponent.template' | sxyTranslate }}\"></i>\r\n            </div>\r\n            <span ng-if=\"row.status == 'draft'\" class=\"small\" ng-class=\"{'text-danger' : !row.data.isReady }\">\r\n              {{ row.data.isReady ? ('SALAXY.NG1.PayrollListComponent.readyForPayment' | sxyTranslate) : ('SALAXY.NG1.PayrollListComponent.notReadyForPayment' | sxyTranslate)  }}\r\n            </span>\r\n          </td>\r\n          <td class=\"right\">\r\n            {{ row.startAt | date }}<br /> {{ row.endAt | date }}\r\n          </td>\r\n          <td class=\"right\">\r\n            {{ row.data.paymentDate || row.data.dueDate | date }}\r\n          </td>\r\n          <td class=\"right\">\r\n            {{ row.data.calcCount ? (row.data.calcCount + \" \" + (\"SALAXY.UI_Terms.pcs\" | sxyTranslate)) : \"-\" }}<br /> {{ row.grossSalary | currency }}\r\n          </td>\r\n          <td class=\"middle right\">\r\n            <button class=\"btn btn-sm\" type=\"button\" ng-class=\"$ctrl.isSelected(row) ? 'btn-danger' : 'btn-info'\" ng-click=\"$ctrl.setSelected(row, 'toggle')\">\r\n              {{ $ctrl.isSelected(row) ? (\"SALAXY.UI_Terms.unselect\" | sxyTranslate) : (\"SALAXY.UI_Terms.select\" | sxyTranslate) }}\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/Payrolls.html\",`<div ng-class=\"$ctrl.getCssClass()\" class=\"table-responsive\">\r\n\r\n  <div class=\"visible-xxs\">\r\n    <div class=\"table-filter-container-mobile\">\r\n      <salaxy-input name=\"search_xxs{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n      </salaxy-input>\r\n    </div>\r\n  </div>\r\n  <table class=\"table\">\r\n    <thead>\r\n      <tr>\r\n        <th><span sxy-text=\"SALAXY.NG1.PayrollListComponent.description\"></span></th>\r\n        <th sxy-orderby=\"status\"><span sxy-text=\"SALAXY.NG1.PayrollListComponent.status\"></span></th>\r\n        <th class=\"right\">\r\n          <span sxy-orderby=\"endAt\">\r\n            <span sxy-text=\"SALAXY.NG1.PayrollListComponent.period\"></span>\r\n          </span>\r\n        </th>\r\n        <th sxy-orderby=\"salaryDate\" class=\"right\"><span sxy-text=\"SALAXY.NG1.PayrollListComponent.salaryDate\"></span></th>\r\n        <th class=\"right\"><span sxy-text=\"SALAXY.NG1.PayrollListComponent.dueDate\"></span></th>\r\n        <th class=\"right\"><span sxy-text=\"SALAXY.NG1.PayrollListComponent.paymentDate\"></span></th>\r\n        <th class=\"right hidden-xxs\">\r\n          <span sxy-text=\"SALAXY.NG1.PayrollListComponent.calculations\"></span>\r\n\r\n          <div sxy-orderby=\"grossSalary\">\r\n            <span sxy-text=\"SALAXY.NG1.PayrollListComponent.grossSalaries\"></span>\r\n          </div>\r\n        </th>\r\n        <th ng-if=\"'aidemo' | sxyIsInRole\" sxy-text=\"SALAXY.NG1.CalcListComponent.issues\"></th>\r\n        <th class=\"right hidden-xxs\" colspan=\"2\">\r\n          <div class=\"table-filter-container\">\r\n            <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" class=\"salaxy-odata-table-search\" placeholder=\"SALAXY.UI_Terms.textSearch\" label-type=\"plain\"></salaxy-input>\r\n          </div>\r\n        </th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat=\"row in $ctrl.items\">\r\n        <td ng-click=\"$crud.showDetails(row)\" class=\"d-table-cell d-sm-none clickable\" title=\"Siirry palkkalistaan\">\r\n          <span class=\"payroll-title\"><strong>{{ row.data.title }}</strong></span>\r\n        </td>\r\n        <td class=\"d-none d-sm-table-cell\">\r\n          <span class=\"payroll-title\"><strong>{{ row.data.title }}</strong></span>\r\n        </td>\r\n        <td class=\"\">\r\n          <div>\r\n            {{ 'PayrollStatus.' + row.status | sxyEnum }}\r\n            <span ng-if=\"row.data.calendarEvent\" class=\"badge bg-primary\">\r\n              <i class=\"bi bi-calendar3\" aria-hidden=\"true\"></i>\r\n              <span sxy-text=\"SALAXY.NG1.PayrollListComponent.calendarEvent\"></span>\r\n            </span>\r\n            <i ng-if=\"row.data.calendarOccurence\" class=\"bi bi-calendar3 text-primary\" aria-hidden=\"true\" title=\"{{ 'SALAXY.NG1.PayrollListComponent.calendarOccurence' | sxyTranslate }}\"></i>\r\n            <i ng-if=\"!row.data.calendarOccurence && row.data.template\" class=\"bi bi-copy text-primary\" aria-hidden=\"true\" title=\"{{ 'SALAXY.NG1.PayrollListComponent.template' | sxyTranslate }}\"></i>\r\n          </div>\r\n          <span ng-if=\"row.status == 'draft'\" class=\"small\" ng-class=\"{'text-danger' : !row.data.isReady }\">\r\n            {{ row.data.isReady ? ('SALAXY.NG1.PayrollListComponent.readyForPayment' | sxyTranslate) : ('SALAXY.NG1.PayrollListComponent.notReadyForPayment' | sxyTranslate)  }}\r\n          </span>\r\n        </td>\r\n        <td class=\"right\">\r\n          {{ row.startAt | date }}<br /> {{ row.endAt | date }}\r\n        </td>\r\n        <td class=\"right\">\r\n          <span class=\"payroll-info\">{{ row.salaryDate | date }}</span>\r\n        </td>\r\n        <td class=\"right\">\r\n          {{ row.status != 'paymentSucceeded' ? (row.data.dueDate | date) : '' }}\r\n        </td>\r\n        <td class=\"right\">\r\n          {{ ['paymentStarted', 'draft', 'waitingApproval', 'waitingPartnerApproval'].includes(row.status) ? '' : (row.data.paymentDate | date) }}\r\n        </td>\r\n        <td class=\"right hidden-xxs\">\r\n          {{ row.data.calcCount ? (row.data.calcCount + \" \" +(\"SALAXY.UI_Terms.pcs\" | sxyTranslate)) : \"-\" }}<br /> {{ row.grossSalary | currency }}\r\n        </td>\r\n        <td ng-if=\"'aidemo' | sxyIsInRole\" class=\"middle\">\r\n            <salaxy-workflow-badge model=\"row\" api-ctrl=\"$crud\"  wf-types=\"'EmployerMessageRecord'\"></salaxy-workflow-badge>\r\n        </td>\r\n        <td class=\"middle hidden-xxs\">\r\n          <button ng-if=\"!(row.isReadOnly || row.status == 'paymentStarted') && !$ctrl.readOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-primary btn-block\">\r\n            <i class=\"bi bi-pencil-fill d-inline-block d-sm-none\"></i>\r\n            <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.edit\"></span>\r\n          </button>\r\n          <button ng-if=\"(row.isReadOnly || row.status == 'paymentStarted') || $ctrl.readOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n            <i class=\"bi bi-info-circle d-inline-block d-sm-none\"></i>\r\n            <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n          </button>\r\n        </td>\r\n        <td class=\"middle hidden-xxs\">\r\n          <button ng-if=\"!(row.isReadOnly || row.status == 'paymentStarted') && !$ctrl.readOnly\" ng-click=\"$crud.delete(row)\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\" class=\"btn btn-sm btn-danger btn-block\">\r\n            <i class=\"bi bi-trash-fill d-inline-block d-sm-none\"></i>\r\n            <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.delete\"></span>\r\n          </button>\r\n          <button ng-if=\"(row.isReadOnly || row.status == 'paymentStarted') && !$ctrl.readOnly\" ng-click=\"$crud.showCopyAsNew(row)\" title=\"{{ 'SALAXY.UI_Terms.copyAsNew' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n            <i class=\"bi bi-copy d-inline-block d-sm-none\"></i>\r\n            <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.copyAsNew\"></span>\r\n          </button>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/ReferenceObjects.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th></th>\r\n          <th sxy-orderby=\"status\">Status</th>\r\n          <th sxy-orderby=\"shortText\">Description</th>\r\n          <th sxy-orderby=\"logicalDate\">Reference date</th>\r\n          <th class=\"right\">\r\n            <div sxy-orderby=\"createdAt\" sxy-text=\"SALAXY.UI_Terms.created\"></div>\r\n            <div sxy-orderby=\"updatedAt\" sxy-text=\"SALAXY.UI_Terms.updated\"></div>\r\n          </th>\r\n          <th></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar middle\">\r\n            <salaxy-avatar avatar=\"row.ownerInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"middle\">{{ row.status  }}</td>\r\n          <td class=\"middle\">{{ row.shortText  }}</td>\r\n          <td class=\"middle\">{{ row.logicalDate | sxyDate }}</td>\r\n          <td class=\"right\">\r\n            <div title=\"{{ row.createdAt }}\">{{ row.createdAt | sxyDate }}</div>\r\n            <div title=\"{{ row.updatedAt }}\">{{ row.updatedAt | sxyDate }}</div>\r\n            <div></div>\r\n          </td>\r\n          <td class=\"middle hidden-xxs\">\r\n            <button ng-if=\"!row.isReadOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-primary btn-block\">\r\n              <i class=\"bi bi-pencil-fill d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.edit\"></span>\r\n            </button>\r\n            <button ng-if=\"row.isReadOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n              <i class=\"bi bi-info-circle d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/SalaryReports.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"table-responsive\">\r\n    <div ng-controller=\"SalarySlipDownloadController as $downloadCtrl\">\r\n      <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$downloadCtrl.export($ctrl.selectedItems)\" ng-disabled=\"$ctrl.selectedItems.length == 0\" sxy-text=\"SALAXY.UI_Terms.downloadSelected\"></button>\r\n    </div>\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\" class=\"hidden-xxs\">\r\n            <span sxy-orderby=\"otherPartyInfo/avatar/displayName\" class=\"clickable\"><span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span><i ng-if=\"$odata.getColumnOrder('avatar/displayName')\" class=\"bi bi-sort-{{ $odata.getColumnOrder('avatar/displayName') }}\"\r\n              aria-hidden=\"true\"></i></span>\r\n          </th>\r\n          <th class=\"visible-xxs\">\r\n            <span sxy-orderby=\"otherPartyInfo/avatar/displayName\" class=\"clickable\"><span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span><i ng-if=\"$odata.getColumnOrder('avatar/displayName')\" class=\"bi bi-sort-{{ $odata.getColumnOrder('avatar/displayName') }}\"\r\n              aria-hidden=\"true\"></i></span>\r\n          </th>\r\n          <th class=\"right\">\r\n            <span sxy-orderby=\"endAt\" class=\"clickable\"><span sxy-text=\"Pvm\"></span></span>\r\n          </th>\r\n          <th class=\"right\">\r\n            <span sxy-orderby=\"payment\" sxy-text=\"SALAXY.NG1.SalaryReportsComponent.payment\"></span><br>\r\n            <span sxy-orderby=\"grossSalary\" sxy-text=\"SALAXY.NG1.SalaryReportsComponent.grossSalary\"></span>\r\n          </th>\r\n          <th class=\"middle hidden-xxs\">\r\n            <button title=\"{{'SALAXY.NG1.AccountingReportsComponent.chooseAll' | sxyTranslate}}\" class=\"btn btn-block btn-transparent\" type=\"button\" ng-if=\"$ctrl.selectedItems.length == 0\" ng-disabled=\"$ctrl.selectedItems.length == $ctrl.items.length\" ng-click=\"$crud.selectAll()\">\r\n              <i class=\"bi bi-square\"></i>\r\n            </button>\r\n            <button title=\"{{'SALAXY.UI_Terms.unselect' | sxyTranslate}}\" class=\"btn btn-block btn-transparent\" type=\"button\" ng-if=\"$ctrl.selectedItems.length > 0\" ng-disabled=\"$ctrl.selectedItems.length == 0\" ng-click=\"$crud.unselectAll()\">\r\n              <i class=\"bi bi-check-square\"></i>\r\n            </button>\r\n          </th>\r\n          <th class=\"right \" colspan=\"2\">\r\n            <div class=\"table-filter-container\">\r\n              <salaxy-input name=\"searchx{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"sort-by-text\" label-type=\"plain\">\r\n              </salaxy-input>\r\n            </div>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar middle hidden-xxs\">\r\n            <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"td-name middle\">\r\n            <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\">{{ 'SALAXY.NG1.SalaryReportsComponent.notSelected' | sxyTranslate }}</span>\r\n            <strong>{{row.otherPartyInfo.avatar.displayName}}</strong>\r\n          </td>\r\n          <td class=\"right middle\">{{ row.endAt | date }}</td>\r\n          <td class=\"right\">\r\n            {{ row.payment | currency }}<br> {{ row.grossSalary | currency }}\r\n          </td>\r\n          <td class=\"middle hidden-xxs\">\r\n            <button title=\"{{'SALAXY.UI_Terms.select' | sxyTranslate}}\" class=\"btn btn-block btn-transparent\" type=\"button\" ng-if=\"!$ctrl.isSelected(row)\" ng-click=\"$ctrl.setSelected(row, 'toggle')\">\r\n              <i class=\"bi bi-square\"></i>\r\n            </button>\r\n            <button title=\"{{'SALAXY.UI_Terms.unselect' | sxyTranslate}}\" class=\"btn btn-block btn-transparent\" type=\"button\" ng-if=\"$ctrl.isSelected(row)\" ng-click=\"$ctrl.setSelected(row, 'toggle')\">\r\n              <i class=\"bi bi-check-square\"></i>\r\n            </button>\r\n          </td>\r\n          <td class=\"middle \">\r\n            <a ng-href=\"{{$crud.getPdfUrl(row)}}\" target=\"_blank\" title=\"{{ 'SALAXY.UI_Terms.printable' | sxyTranslate}}\" class=\"btn btn-sm btn-block btn-default\">\r\n              <i class=\"bi bi-file-earmark-pdf d-sm-none d-inline-block\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.printable\" pre=\" \"></span>\r\n            </a>\r\n          </td>\r\n          <td class=\"middle \">\r\n            <button ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-block btn-default\">\r\n              <i class=\"bi bi-info-circle-fill d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.show\" pre=\" \"></span>\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/SalaryReportsPanel.html\",`<div class=\"salaxy-odata-card list-card report-list-card card card-sm card-secondary\" ng-init=\"hideFilter = false\">\r\n  <div class=\"card-header d-flex align-items-center\">\r\n    {{('SALAXY.NG1.SalaryReportsComponent.calculations' | sxyTranslate) }}\r\n    <button ng-show=\"$ctrl.items.length > 0\" class=\"btn btn-secondary btn-xs ms-auto\" ng-click=\"hideFilter = !hideFilter\" title=\"Näytä suodattimet\">\r\n      <i class=\"bi bi-funnel-fill\"></i>\r\n    </button>\r\n  </div>\r\n  <div class=\"card-body filters text-end\" ng-class=\"{'showfilters' : hideFilter}\">\r\n    <div class=\"filter-buttons\">\r\n      <button class=\"btn btn-xs btn-secondary text-end\" sxy-orderby=\"otherPartyInfo/avatar/displayName\" sxy-text=\"SALAXY.UI_Terms.abc\"></button>\r\n      <button class=\"btn btn-xs btn-secondary text-end\" sxy-orderby=\"endAt\">\r\n          <i class=\"bi bi-calendar3\"></i>\r\n      </button>\r\n      <button class=\"btn btn-xs btn-secondary text-end\" sxy-orderby=\"grossSalary\">€</button>\r\n    </div>\r\n    <salaxy-input name=\"search1cp{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search hidden-xxs\" label-type=\"plain\">\r\n    </salaxy-input>\r\n  </div>\r\n  <div ng-class=\"$ctrl.getCssClass()\">\r\n    <div class=\"visible-xxs\" ng-if=\"$ctrl.items.length > 0\">\r\n      <div class=\"table-filter-container-mobile\">\r\n        <salaxy-input name=\"search2cp{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n        </salaxy-input>\r\n      </div>\r\n    </div>\r\n    <div class=\"card-body text-center card-content lg-height align-middle\" ng-show=\"$ctrl.items.length == 0 && !$ctrl.isLoading\">\r\n      <div>\r\n        <h3 sxy-text=\"SALAXY.NG1.SalaryReportsComponent.noCalculations\"></h3>\r\n      </div>\r\n    </div>\r\n    <div class=\"table-responsive\">\r\n      <table class=\"table\" ng-if=\"$ctrl.items.length > 0\">\r\n        <tbody>\r\n          <tr ng-repeat=\"row in $ctrl.items\">\r\n\r\n            <td class=\"td-avatar middle  hidden-xxs\">\r\n              <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n            </td>\r\n            <td class=\"td-name middle\">\r\n              <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\">{{ 'SALAXY.NG1.SalaryReportsComponent.notSelected' | sxyTranslate }}</span>\r\n              <strong>{{row.otherPartyInfo.avatar.displayName}}</strong>\r\n            </td>\r\n            <td class=\"right\">\r\n              {{ row.grossSalary | currency }}\r\n              <br>\r\n              <small>{{ row.endAt | date }}</small>\r\n            </td>\r\n\r\n            <td class=\"middle right\">\r\n              <a ng-href=\"{{$crud.getPdfUrl(row)}}\" target=\"_blank\" title=\"{{ 'SALAXY.UI_Terms.printable' | sxyTranslate}}\" class=\"btn btn-sm btn-secondary\"><i class=\"bi bi-file-earmark-pdf\"></i></a>\r\n              <button href=\"\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-secondary\"><i class=\"bi bi-info-circle\"></i></button>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n      <div class=\"salaxy-odata-footer\">\r\n        <salaxy-spinner></salaxy-spinner>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div class=\"card-footer text-center\">\r\n    <a ng-href=\"#{{$crud.getDefaults().listUrl}}\" title=\"Näytä kaikki\" class=\"btn btn-primary btn-sm\" sxy-text=\"SALAXY.UI_Terms.showAll\"></a>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/SelectListItem.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"visible-xxs\">\r\n    <div class=\"table-filter-container-mobile\">\r\n      <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"{{'SALAXY.UI_Terms.textSearch' |sxyTranslate}}\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n      </salaxy-input>\r\n    </div>\r\n  </div>\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th></th>\r\n          <th>\r\n            <div><span class=\"label label-primary clickable\" ng-if=\"$ctrl.selectedItems.length\" ng-click=\"$ctrl.selectedItems.splice(0,$ctrl.selectedItems.length)\"> {{'SALAXY.UI_Terms.chosen' | sxyTranslate}}: {{ $ctrl.selectedItems.length }} <i class=\"bi bi-x-circle\"></i></span></div>\r\n            <div sxy-orderby=\"shortText\">Teksti</div>\r\n          </th>\r\n          <th class=\"right\">\r\n            <div sxy-orderby=\"createdAt\"  sxy-text=\"SALAXY.UI_Terms.created\"></div>\r\n            <div sxy-orderby=\"updatedAt\"  sxy-text=\"SALAXY.UI_Terms.updated\"></div>\r\n          </th>\r\n          <th>\r\n            <div sxy-orderby=\"status\">Tila</div>\r\n          </th>\r\n          <th class=\"right hidden-xxs\" colspan=\"2\">\r\n            <div class=\"table-filter-container\">\r\n              <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" class=\"salaxy-odata-table-search\" placeholder=\"{{'SALAXY.UI_Terms.textSearch' |sxyTranslate}}\" label-type=\"plain\"></salaxy-input>\r\n            </div>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar middle\">\r\n            <salaxy-avatar ng-if=\"row.otherPartyInfo.avatar.displayName\" avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"td-name middle\">\r\n            <div><strong>{{row.shortText }}</strong></div>\r\n            <div>{{ row.otherPartyInfo.avatar.displayName }}</div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <div>{{ row.createdAt | sxyDate }}</div>\r\n            <div>{{ row.updatedAt | sxyDate }}</div>\r\n          </td>\r\n          <td class=\"middle\">\r\n            <div>{{ row.status }}</div>\r\n          </td>\r\n          <td class=\"right middle\">\r\n            <button class=\"btn btn-sm\" type=\"button\" ng-class=\"$ctrl.isSelected(row) ? 'btn-danger' : 'btn-info'\" ng-click=\"$ctrl.setSelected(row, 'toggle')\">\r\n              {{ $ctrl.isSelected(row) ? ('SALAXY.UI_Terms.unselect' | sxyTranslate) : ('SALAXY.UI_Terms.select' | sxyTranslate) }}\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/ServiceModels.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th></th>\r\n          <th sxy-text=\"SALAXY.NG1.ServiceModelsComponent.serviceModel\"></th>\r\n          <th class=\"right\">\r\n            <div sxy-orderby=\"createdAt\" sxy-text=\"SALAXY.UI_Terms.created\"></div>\r\n            <div sxy-orderby=\"updatedAt\" sxy-text=\"SALAXY.UI_Terms.updated\"></div>\r\n          </th>\r\n          <th></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"middle\">\r\n            <img ng-if=\"row.data.icon || row.ownerInfo.avatar.url\" ng-src=\"{{row.data.icon || row.ownerInfo.avatar.url}}\" style=\"width: 45px; height: 45px;\" />\r\n          </td>\r\n          <td class=\"middle\">\r\n            <div ng-if=\"row.id == row.ownerInfo.avatar.id\">\r\n              <strong ng-if=\"!row.shortText\">{{'SALAXY.NG1.ServiceModelsComponent.defaultModel' | sxyTranslate}}  {{ row.ownerInfo.avatar.displayName }}</strong>\r\n              <strong ng-if=\"row.shortText\">{{ row.shortText || ('SALAXY.NG1.ServiceModelsComponent.nameless' | sxyTranslate) }}</strong>\r\n            </div>\r\n            <div ng-if=\"row.id != row.ownerInfo.avatar.id\">\r\n              <strong>{{ row.shortText || ('SALAXY.NG1.ServiceModelsComponent.nameless' | sxyTranslate) }}</strong>\r\n            </div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <div title=\"{{ row.createdAt }}\">{{ row.createdAt | sxyDate }}</div>\r\n            <div title=\"{{ row.updatedAt }}\">{{ row.updatedAt | sxyDate }}</div>\r\n            <div></div>\r\n          </td>\r\n          <td class=\"middle hidden-xxs\">\r\n            <button ng-if=\"!row.isReadOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-primary btn-block\">\r\n              <i class=\"bi bi-pencil-fill d-sm-none d-inline-block\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.edit\"></span>\r\n            </button>\r\n            <button ng-if=\"row.isReadOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n              <i class=\"bi bi-info-circle d-sm-none d-inline-block\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.show\"></span></button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/Taxcards-select.html\",`\r\n<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead class=\"\">\r\n        <tr>\r\n          <th colspan=\"2\"><span sxy-orderby=\"otherPartyInfo/avatar/displayName\" sxy-text=\"SALAXY.NG1.TaxcardsListComponent.worker\"></span></th>\r\n          <th class=\"right\">\r\n            <span sxy-orderby=\"endAt\" sxy-text=\"SALAXY.NG1.TaxcardsListComponent.year\"></span><br />\r\n            </td>\r\n            <th class=\"right\">\r\n              <span sxy-orderby=\"startAt\" sxy-text=\"SALAXY.NG1.TaxcardsListComponent.valid\"></span><br />\r\n              <span sxy-orderby=\"endAt\" sxy-text=\"SALAXY.NG1.TaxcardsListComponent.validTill\"></span><br />\r\n              </td>\r\n              <th class=\"right\">\r\n                <span sxy-text=\"SALAXY.NG1.TaxcardsListComponent.paid\"></span><br>\r\n                <span sxy-text=\"SALAXY.NG1.TaxcardsListComponent.incomeLimit\"></span>\r\n              </th>\r\n              <th>\r\n              </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"align-middle td-avatar\">\r\n            <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"td-name\">\r\n            <strong ng-if=\"row.otherPartyInfo.avatar.displayName\">{{row.otherPartyInfo.avatar.displayName}}</strong>\r\n            <strong ng-if=\"!row.otherPartyInfo.avatar.displayName\">{{'SALAXY.NG1.TaxcardsListComponent.unknown' | sxyTranslate}}</strong>\r\n            <br /> {{ \"SALAXY.ENUM.TaxcardKind.\" + row.data.kind + \".label\" | sxyTranslate}}\r\n            <span ng-if=\"row.data.kind !== 'noTaxCard' && row.data.kind !== 'noWithholdingHousehold' && row.data.kind !== 'undefined'\">{{row.data.taxPercent}} %</span>\r\n            <span ng-if=\"row.data.taxPercent2\">\r\n              <br />{{'SALAXY.NG1.TaxcardsListComponent.taxPercent2' | sxyTranslate}} {{row.data.taxPercent2}} %\r\n            </span>\r\n          </td>\r\n          <td class=\"right\">\r\n            <span>{{row.data.forYear}}</span><br />\r\n          </td>\r\n          <td class=\"right\">\r\n            <span>{{row.data.start | sxyDate}}</span><br />\r\n            <span>{{row.data.end | sxyDate}}</span><br />\r\n          </td>\r\n          <td class=\"right\">\r\n            <span class=\"small paidsalaries\">{{ row.data.totalIncome | currency}}</span>\r\n            <span class=\"small incomelimit\">{{(row.data.incomeLimit | currency) || '-'}}</span>\r\n          </td>\r\n          <td class=\"middle right\">\r\n            <button class=\"btn btn-sm\" type=\"button\" ng-class=\"$ctrl.isSelected(row) ? 'btn-danger' : 'btn-info'\" ng-click=\"$ctrl.setSelected(row, 'toggle')\">\r\n              {{ $ctrl.isSelected(row) ? (\"SALAXY.UI_Terms.unselect\" | sxyTranslate) : (\"SALAXY.UI_Terms.select\" | sxyTranslate) }}\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/Taxcards.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead class=\"\">\r\n        <tr>\r\n          <th colspan=\"2\"><span sxy-orderby=\"otherPartyInfo/avatar/displayName\" sxy-text=\"SALAXY.NG1.TaxcardsListComponent.worker\"></span></th>\r\n          <th class=\"right\">\r\n            <span sxy-orderby=\"endAt\" sxy-text=\"SALAXY.NG1.TaxcardsListComponent.year\"></span><br />\r\n            </td>\r\n            <th class=\"right\">\r\n              <span sxy-orderby=\"startAt\" sxy-text=\"SALAXY.NG1.TaxcardsListComponent.valid\"></span><br />\r\n              <span sxy-orderby=\"endAt\" sxy-text=\"SALAXY.NG1.TaxcardsListComponent.validTill\"></span><br />\r\n              </td>\r\n              <th class=\"right\">\r\n                <span sxy-text=\"SALAXY.NG1.TaxcardsListComponent.paid\"></span><br>\r\n                <span sxy-text=\"SALAXY.NG1.TaxcardsListComponent.incomeLimit\"></span>\r\n              </th>\r\n              <th>\r\n                <!--div class=\"table-filter-container text-end\">\r\n                  <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" label-type=\"plain\" placeholder=\"SALAXY.UI_Terms.textSearch\"></salaxy-input>\r\n                </div-->\r\n              </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"align-middle td-avatar\">\r\n            <a href=\"#/employments/details/{{row.data.employmentId}}\" class=\"cell-link\" title=\"{{'SALAXY.NG1.WorkerListComponent.editWorker' | sxyTranslate}}\">\r\n              <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n            </a>\r\n          </td>\r\n          <td class=\"td-name\">\r\n            <strong ng-if=\"row.otherPartyInfo.avatar.displayName\">{{row.otherPartyInfo.avatar.displayName}}</strong>\r\n            <strong ng-if=\"!row.otherPartyInfo.avatar.displayName && row.otherPartyInfo.officialId\">{{'SALAXY.NG1.TaxcardsListComponent.personalId' | sxyTranslate}} : {{row.otherPartyInfo.officialId}}</strong>\r\n            <strong ng-if=\"!row.otherPartyInfo.avatar.displayName && !row.otherPartyInfo.officialId\">{{'SALAXY.NG1.TaxcardsListComponent.unknown' | sxyTranslate}}</strong>\r\n            <br /> {{ \"SALAXY.ENUM.TaxcardKind.\" + row.data.kind + \".label\" | sxyTranslate}}\r\n            <span ng-if=\"row.data.kind !== 'noTaxCard' && row.data.kind !== 'noWithholdingHousehold' && row.data.kind !== 'undefined'\">{{row.data.taxPercent}} %</span>\r\n            <span ng-if=\"row.data.taxPercent2\">\r\n              <br />{{'SALAXY.NG1.TaxcardsListComponent.taxPercent2' | sxyTranslate}} {{row.data.taxPercent2}} %\r\n            </span>\r\n          </td>\r\n          <td class=\"right\">\r\n            <span>{{row.data.forYear}}</span><br />\r\n          </td>\r\n          <td class=\"right\">\r\n            <span>{{row.data.start | sxyDate}}</span><br />\r\n            <span>{{row.data.end | sxyDate}}</span><br />\r\n          </td>\r\n          <td class=\"right\">\r\n            <span class=\"small paidsalaries\">{{ row.data.totalIncome | currency: ' €' : 0 }}</span>\r\n            <span class=\"small incomelimit\">{{(row.data.incomeLimit | currency: ' €' : 0) || '-'}}</span>\r\n            <span class=\"d-inline d-md-none\"></span>\r\n          </td>\r\n          <td class=\"right\">\r\n            <div class=\"btn-group-sm\">\r\n              <button class=\"btn btn-primary\" ng-disabled=\"$ctrl.loaders['showTaxCardAddDialogForTaxCardsList']\" ng-click=\"$crud.showTaxCardAddDialogForTaxCardsList(row);\" ng-if=\"row.otherId && ('!household' | sxyIsInRole)\" sxy-text=\"SALAXY.UI_Terms.addNew\"></button>\r\n              <button title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" ng-click=\"$crud.showDetails(row)\" class=\"btn btn-default\" ng-if=\"'!household' | sxyIsInRole\">\r\n                <i class=\"bi bi-pencil-fill d-sm-none d-inline-block\"></i>\r\n                <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.show\"></span></button>\r\n            </div>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/Templates-select.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\"></th>\r\n          <th sxy-orderby=\"shortText\">Nimi</th>\r\n          <th>Kuvaus</th>\r\n          <th class=\"right\" sxy-orderby=\"createdAt\" sxy-text=\"SALAXY.UI_Terms.created\"></th>\r\n          <th class=\"right\" sxy-orderby=\"updatedAt\" sxy-text=\"SALAXY.UI_Terms.updated\"></th>\r\n          <th></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar middle\">\r\n            <salaxy-avatar avatar=\"row.ownerInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"middle\">\r\n            <div>{{ row.ownerInfo.avatar.displayName }}</div>\r\n          </td>\r\n          <td class=\"middle\">{{ row.shortText  }}</td>\r\n          <td class=\"middle\">{{ row.data.description}}</td>\r\n          <td class=\"right\" title=\"{{ row.createdAt }}\">{{ row.createdAt | sxyDate }}</div>\r\n          <td class=\"right\" title=\"{{ row.updatedAt }}\">{{ row.updatedAt | sxyDate }}</div>\r\n          <td class=\"middle\">\r\n            <button class=\"btn btn-sm\" type=\"button\" ng-class=\"$ctrl.isSelected(row) ? 'btn-danger' : 'btn-info'\" ng-click=\"$ctrl.setSelected(row, 'toggle')\">\r\n              {{ $ctrl.isSelected(row) ? (\"SALAXY.UI_Terms.unselect\" | sxyTranslate) : (\"SALAXY.UI_Terms.select\" | sxyTranslate) }}\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/Templates.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\"></th>\r\n          <th sxy-orderby=\"shortText\">Nimi</th>\r\n          <th>Kuvaus</th>\r\n          <th class=\"right\" sxy-orderby=\"createdAt\" sxy-text=\"SALAXY.UI_Terms.created\"></th>\r\n          <th class=\"right\" sxy-orderby=\"updatedAt\" sxy-text=\"SALAXY.UI_Terms.updated\"></th>\r\n          <th></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar middle\">\r\n            <salaxy-avatar avatar=\"row.ownerInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"middle\">\r\n            <div>{{ row.ownerInfo.avatar.displayName }}</div>\r\n          </td>\r\n          <td class=\"middle\">{{ row.shortText  }}</td>\r\n          <td class=\"middle\">{{ row.data.description}}</td>\r\n          <td class=\"right\" title=\"{{ row.createdAt }}\">{{ row.createdAt | sxyDate }}</div>\r\n          <td class=\"right\" title=\"{{ row.updatedAt }}\">{{ row.updatedAt | sxyDate }}</div>\r\n          <td class=\"middle\">\r\n            <button ng-if=\"!row.isReadOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-primary btn-block\">\r\n              <i class=\"bi bi-pencil-fill d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.edit\"></span>\r\n            </button>\r\n            <button ng-if=\"row.isReadOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n              <i class=\"bi bi-info-circle d-inline-block d-sm-none\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/Usecases.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th></th>\r\n          <th sxy-orderby=\"shortText\" sxy-text=\"SALAXY.NG1.ApiCrudObjectComponent.description\"></th>\r\n          <th sxy-orderby=\"entityType\" sxy-text=\"SALAXY.NG1.ApiCrudObjectComponent.entityType\"></th>\r\n          <th class=\"hidden-xxs\" sxy-text=\"SALAXY.NG1.ApiCrudObjectComponent.owner\"></th>\r\n          <th class=\"right\">\r\n            <div sxy-orderby=\"createdAt\" sxy-text=\"SALAXY.UI_Terms.created\"></div>\r\n            <div sxy-orderby=\"updatedAt\" sxy-text=\"SALAXY.UI_Terms.updated\"></div>\r\n          </th>\r\n          <th class=\"right hidden-xxs\" colspan=\"2\">\r\n            <div class=\"table-filter-container\">\r\n              <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" class=\"salaxy-odata-table-search\" placeholder=\"SALAXY.UI_Terms.textSearch\" label-type=\"plain\"></salaxy-input>\r\n            </div>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td style=\"width: 86px;\">\r\n            <div class=\"thumbnail\" style=\"margin-bottom: 0;\">\r\n              <div class=\"text-center thumbnail-pic-fixed\" style=\"width: 60px;height: 60px\">\r\n                <img ng-if=\"row.data.icon[0] == 'h'\" ng-src=\"{{row.data.icon}}\">\r\n                <div ng-if=\"row.data.icon[0] != 'h'\" class=\"bg-primary thumbnail-pic-icon\" style=\"font-size: 32px\">\r\n                  <i class=\"fa\" ng-class=\"row.data.icon || 'bi-currency-euro'\" aria-hidden=\"true\"></i>\r\n                </div>\r\n              </div>\r\n            </div>\r\n          </td>\r\n          <td>\r\n            <div><strong>{{ row.shortText }}</strong></div>\r\n            <div>{{ row.data.description }}</div>\r\n          </td>\r\n          <td>\r\n            <div>{{ \"ApiItemType.\" + row.entityType | sxyEnum }}</div>\r\n            <div ng-switch=\"row.status\">\r\n              <span class=\"badge\" ng-class=\"$crud.getStatusBgColor(row.status)\">{{ \"UsecaseStatus.\" + row.status | sxyEnum }}</span>\r\n            </div>\r\n          </td>\r\n          <td class=\"align-middle td-avatar hidden-xxs\" title=\"{{ row.ownerInfo.avatar.displayName }}\">\r\n            <salaxy-avatar avatar=\"row.ownerInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"right\">\r\n            <div>{{ row.createdAt | sxyDate }}</div>\r\n            <div>{{ row.updatedAt | sxyDate }}</div>\r\n          </td>\r\n          <td class=\"middle hidden-xxs\">\r\n            <button ng-if=\"!row.isReadOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-primary btn-block\">\r\n              <i class=\"bi bi-pencil-fill d-sm-none d-inline-block\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.edit\"></span>\r\n            </button>\r\n            <button ng-if=\"row.isReadOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n              <i class=\"bi bi-info-circle d-sm-none d-inline-block\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n            </button>\r\n          </td>\r\n          <td class=\"middle hidden-xxs\">\r\n            <button ng-if=\"!row.isReadOnly\" ng-click=\"$crud.delete(row)\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\" class=\"btn btn-sm btn-danger btn-block\">\r\n              <i class=\"bi bi-trash-fill d-sm-none d-inline-block\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.delete\"></span>\r\n            </button>\r\n            <button ng-if=\"row.isReadOnly\" ng-click=\"$crud.showCopyAsNew(row)\" title=\"{{ 'SALAXY.UI_Terms.copyAsNew' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n              <i class=\"bi bi-copy d-sm-none d-inline-block\"></i>\r\n              <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.copyAsNew\"></span>\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/UsecasesAdHocReport.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"row g-4\">\r\n    <div class=\"col\" ng-repeat=\"row in $ctrl.items | orderBy: $crud.getOrder\" ng-if=\"$crud.getActive(row) != 'inactive'\">\r\n      <div class=\"card\">\r\n        <div class=\"text-center card-pic-fixed\">\r\n          <img ng-if=\"row.data.icon[0] == 'h'\" ng-src=\"{{row.data.icon}}\">\r\n          <div ng-if=\"row.data.icon[0] != 'h'\" class=\"bg-primary card-pic-icon\">\r\n            <i class=\"fa\" ng-class=\"row.data.icon || 'bi-currency-euro'\" aria-hidden=\"true\"></i>\r\n          </div>\r\n        </div>\r\n        <div class=\"card-body\">\r\n          <h3 class=\"truncate\">{{ row.shortText }}</h3>\r\n          <p style=\"height: 80px;overflow: hidden\">{{ row.data.description }}</p>\r\n          <p ng-switch=\"row.entityType\">\r\n            <a ng-switch-when=\"dataset\" ng-href=\"#/reports/ad-hoc/new?usecase=%2FUsecaseDefinition%2F{{ row.owner }}%2F{{ row.id }}\" class=\"btn btn-primary\" role=\"button\" style=\"color: white\" sxy-text=\"SALAXY.UI_Terms.select\" ps=\"...\"></a>\r\n            <a ng-switch-default class=\"btn btn-primary\" role=\"button\" style=\"color: white\" sxy-text=\"TODO\" ps=\"...\"></a>\r\n          </p>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/UsecasesCalc.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"row g-4\">\r\n    <div class=\"col-sm-6 col-md-4\" ng-repeat=\"row in $ctrl.items\" ng-if=\"$crud.getActive(row) != 'inactive'\">\r\n      <div class=\"card\">\r\n        <div class=\"text-center card-pic-fixed\" style=\"height: 150px;\">\r\n          <img ng-if=\"row.data.icon[0] == 'h'\" ng-src=\"{{row.data.icon}}\">\r\n          <div ng-if=\"row.data.icon[0] != 'h'\" class=\"bg-primary card-pic-icon\">\r\n            <i class=\"fa\" ng-class=\"row.data.icon || 'bi-currency-euro'\" aria-hidden=\"true\"></i>\r\n          </div>\r\n          <span class=\"badge float-end\" ng-class=\"$crud.getStatusBgColor($crud.getActive(row))\">{{ \"UsecaseStatus.\" + $crud.getActive(row) | sxyEnum }}</span>\r\n        </div>\r\n        <div class=\"card-body\">\r\n          <h3 class=\"truncate\">{{ row.shortText }}</h3>\r\n          <p style=\"height: 80px;overflow: hidden\">{{ row.data.description }}</p>\r\n          <p ng-switch=\"row.entityType\">\r\n            <a ng-switch-when=\"calculation\" ng-href=\"#/calc/usecase/new?usecase=%2FUsecaseDefinition%2F{{ row.owner }}%2F{{ row.id }}\" class=\"btn btn-primary\" role=\"button\" style=\"color: white\" sxy-text=\"SALAXY.UI_Terms.createNew\" ps=\"...\"></a>\r\n            <a ng-switch-default class=\"btn btn-primary\" role=\"button\" style=\"color: white\" sxy-text=\"TODO\" ps=\"...\"></a>\r\n          </p>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/UsecaseSelect.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <div class=\"visible-xxs\">\r\n    <div class=\"table-filter-container-mobile\">\r\n      <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" placeholder=\"SALAXY.UI_Terms.textSearch\" class=\"salaxy-odata-table-search\" label-type=\"plain\">\r\n      </salaxy-input>\r\n    </div>\r\n  </div>\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\">\r\n            <div sxy-orderby=\"shortText\" sxy-text=\"SALAXY.NG1.ApiCrudObjectComponent.name\"></div>\r\n          </th>\r\n          <th sxy-orderby=\"owner\" colspan=\"2\">\r\n            <div sxy-text=\"SALAXY.NG1.ApiCrudObjectComponent.owner\"></div>\r\n          </th>\r\n          <th class=\"right hidden-xxs\" colspan=\"3\">\r\n            <div class=\"table-filter-container\">\r\n              <salaxy-input name=\"search{{::$id}}\" ng-model=\"$ctrl.options.$search\" ng-change=\"$ctrl.searchChanged()\" class=\"salaxy-odata-table-search\" placeholder=\"SALAXY.UI_Terms.textSearch\" label-type=\"plain\"></salaxy-input>\r\n            </div>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.items\">\r\n          <td class=\"td-avatar middle\">\r\n            <div>\r\n              <strong>{{ row.shortText }}</strong>\r\n            </div>\r\n          </td>\r\n          <td class=\"middle\">\r\n            <div title=\"{{ row.shortText }} ({{ row.id }})\">\r\n              <strong>{{ row.otherPartyInfo.avatar.displayName }}</strong>\r\n            </div>\r\n          </td>\r\n          <td class=\"td-avatar middle\">\r\n            <salaxy-avatar avatar=\"row.ownerInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"middle\">\r\n            <div>{{ row.ownerInfo.avatar.displayName }}</div>\r\n          </td>\r\n          <td></td>\r\n          <td class=\"right middle\">\r\n            <button class=\"btn btn-sm\" type=\"button\" ng-class=\"$ctrl.isSelected(row) ? 'btn-danger' : 'btn-info'\" ng-click=\"$ctrl.setSelected(row, 'toggle')\">\r\n              {{ $ctrl.isSelected(row) ? ('SALAXY.UI_Terms.unselect' | sxyTranslate) : ('SALAXY.UI_Terms.select' | sxyTranslate) }}\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/WorktimeImport.html\",`<div ng-class=\"$ctrl.getCssClass()\">\r\n  <table class=\"table\">\r\n    <thead>\r\n      <tr>\r\n        <th sxy-orderby=\"id\">\r\n          <div>Title</div>\r\n          <div sxy-text=\"SALAXY.NG1.ApiCrudObjectComponent.id\"></div>\r\n        </th>\r\n        <th sxy-orderby=\"status\"  sxy-text=\"SALAXY.UI_Terms.status\"></th>\r\n        <th class=\"right\">\r\n          <div sxy-orderby=\"createdAt\" sxy-text=\"SALAXY.UI_Terms.created\"></div>\r\n          <div sxy-orderby=\"updatedAt\" sxy-text=\"SALAXY.UI_Terms.updated\"></div>\r\n        </th>\r\n        <th class=\"right\">Files</th>\r\n        <th class=\"right\">\r\n          <div>Empl.</div>\r\n          <div>Rows</div>\r\n        </th>\r\n        <th class=\"right\">\r\n          Errors\r\n        </th>\r\n        <th class=\"right\">\r\n          <div>Period</div>\r\n          <div>Salary date</div>\r\n        </th>\r\n        <th colspan=\"2\"></th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat=\"row in $ctrl.items\">\r\n        <td>\r\n          <div>{{ row.shortText || \"-\" }}</div>\r\n          <div><code><small>{{ row.id }}</small></code></div>\r\n        </td>\r\n        <td>{{ row.status }}</td>\r\n        <td class=\"right\">\r\n          <div>{{ row.createdAt | sxyTime }}</div>\r\n          <div>{{ row.updatedAt | sxyTime }}</div>\r\n        </td>\r\n        <td class=\"right\">{{ row.data.filesCount || \"-\" }}</td>\r\n        <td class=\"right\">\r\n          <div>{{ row.data.employmentsCount || \"-\" }}</div>\r\n          <div>{{ row.data.rowsCount || \"-\" }}</div>\r\n        </td>\r\n        <td class=\"right\">\r\n          <div ng-class=\"row.data.employmentsErrors ? 'text-danger' : 'text-success'\">{{ row.data.employmentsErrors || \"OK\" }}</div>\r\n          <div ng-class=\"row.data.employmentsErrors ? 'text-danger' : 'text-success'\">{{ row.data.rowsErrors || \"OK\" }}</div>\r\n        </td>\r\n        <td class=\"right\">\r\n          <div>{{ row | sxyDateRange }}</div>\r\n          <div>{{ row.salaryDate | sxyDate }}</div>\r\n        </td>\r\n        <td>\r\n          <button ng-if=\"!row.isReadOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-primary btn-block\">\r\n            <i class=\"bi bi-pencil-fill d-s-none d-inline-block\"></i>\r\n            <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.edit\"></span>\r\n          </button>\r\n          <button ng-if=\"row.isReadOnly\" ng-click=\"$crud.showDetails(row)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n            <i class=\"bi bi-info-circle d-sm-none d-inline-block\"></i>\r\n            <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n          </button>\r\n        </td>\r\n        <td>\r\n          <button ng-if=\"!row.isReadOnly\" ng-click=\"$crud.delete(row)\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\" class=\"btn btn-sm btn-danger btn-block\">\r\n            <i class=\"bi bi-trash-fill d-sm-none d-inline-block\"></i>\r\n            <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.delete\"></span>\r\n          </button>\r\n          <button ng-if=\"row.isReadOnly\" ng-click=\"$crud.showCopyAsNew(row)\" title=\"{{ 'SALAXY.UI_Terms.copyAsNew' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\">\r\n            <i class=\"bi bi-copy d-sm-none d-inline-block\"></i>\r\n            <span class=\"d-none d-sm-inline-block\" sxy-text=\"SALAXY.UI_Terms.copyAsNew\"></span>\r\n          </button>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n  <salaxy-odata-footer></salaxy-odata-footer>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/lists/_default.html\",`<ng-include src=\"$ctrl.$crudController.getDefaults().oDataTemplateUrl || 'salaxy-components/odata/lists/ApiCrudObject.html'\"></ng-include>`);\n\n $templateCache.put(\"salaxy-components/odata/OdataActions.html\",`<div class=\"salaxy-component salaxy-odata-actions d-flex justify-content-end\" ng-init=\"$ctrl.$crud = $ctrl.$odata.$crudController\">\r\n  <div class=\"me-2\">\r\n    <span class=\"salaxy-form-group-plain\">\r\n      <input type=\"text\" ng-model=\"$ctrl.$odata.options.$search\" ng-change=\"$ctrl.$odata.searchChanged()\" class=\"form-control\" autocomplete=\"off\"\r\n        id=\"searchx111\" name=\"searchx111\" placeholder=\"{{'SALAXY.UI_Terms.textSearch' | sxyTranslate}}\"\r\n        ng-model-options=\"{allowInvalid: true, debounce: 250, updateOn: 'default' }\" maxlength=\"1024\">\r\n    </span>\r\n  </div>\r\n  <div ng-if=\"$ctrl.showExport\" class=\"btn-group dropdown\">\r\n    <button id=\"single-button\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\">\r\n      <i class=\"bi bi-three-dots\" aria-hidden=\"true\"></i>\r\n    </button>\r\n    <ul class=\"dropdown-menu dropdown-menu-end\" aria-labelledby=\"single-button\">\r\n      <li>\r\n        <a href=\"\" ng-controller=\"ExportController as $export\" ng-click=\"$export.showExport($ctrl.getExportable())\" sxy-text=\"SALAXY.NG1.ODataActionsComponent.export\" class=\"dropdown-item\"></a>\r\n      </li>\r\n    </ul>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/odata/OdataFooter.html\",`<div class=\"salaxy-component salaxy-odata-footer\">\r\n  <salaxy-spinner></salaxy-spinner>\r\n  <div ng-if=\"$ctrl.getNoItemsMessage()\" class=\"salaxy-odata-no-data\">\r\n    <div ng-class=\"$ctrl.getNoItemsCssClass()\">{{ $ctrl.getNoItemsMessage() | sxyTranslate }}</div>\r\n  </div>\r\n  <div ng-if=\"$ctrl.getPagingView() == 'nextPageLink'\">\r\n    {{'SALAXY.NG1.ODataFooterComponent.showing' | sxyTranslate}} {{ $ctrl.$odata.count ? ($ctrl.$odata.items.length + \"/\" + $ctrl.$odata.count) : $ctrl.$odata.items.length }} {{'SALAXY.NG1.ODataFooterComponent.rows' | sxyTranslate}}.\r\n    <a href=\"\" ng-click=\"$ctrl.$odata.loadNextPage(true)\" sxy-text=\"SALAXY.NG1.ODataFooterComponent.downloadMore\" ps=\"...\"></a>\r\n  </div>\r\n  <div ng-if=\"$ctrl.getPagingView() == 'clientLimit'\">\r\n    {{'SALAXY.NG1.ODataFooterComponent.showing' | sxyTranslate}} {{ $ctrl.$odata.count ? ($ctrl.$odata.items.length + \"/\" + $ctrl.$odata.count) : $ctrl.$odata.items.length }} {{'SALAXY.NG1.ODataFooterComponent.rows' | sxyTranslate}}.\r\n    <a href=\"\" ng-click=\"$ctrl.$odata.options.$top = null; $ctrl.$odata.reload()\" sxy-text=\"SALAXY.NG1.ODataFooterComponent.downloadMore\" ps=\"...\"></a>\r\n  </div>\r\n  <div ng-if=\"$ctrl.getPagingView() == 'url'\">\r\n    {{'SALAXY.NG1.ODataFooterComponent.showing' | sxyTranslate}} {{ $ctrl.$odata.count ? ($ctrl.$odata.items.length + \"/\" + $ctrl.$odata.count) : $ctrl.$odata.items.length }} {{'SALAXY.NG1.ODataFooterComponent.rows' | sxyTranslate}}.\r\n    <a ng-href=\"{{$ctrl.nextPageUrl}}\" sxy-text=\"SALAXY.NG1.ODataFooterComponent.showAll\" ps=\"...\"></a>\r\n  </div>\r\n  <div ng-if=\"$ctrl.getPagingView() == 'server'\">\r\n    {{'SALAXY.NG1.ODataFooterComponent.showingRows' | sxyTranslate}} rivit {{ ($ctrl.$odata.options.$skip || 0) + 1 }} - {{ ($ctrl.$odata.options.$skip || 0) + $ctrl.$odata.items.length }}\r\n    <span ng-if=\"$ctrl.count\"> {{'SALAXY.NG1.ODataFooterComponent.total' | sxyTranslate}} {{ $ctrl.$odata.count }} {{'SALAXY.NG1.ODataFooterComponent.rows' | sxyTranslate}}</span>\r\n    <a href=\"\" ng-click=\"$ctrl.loadNextPage(false)\" sxy-text=\"SALAXY.NG1.ODataFooterComponent.nextPage\" ps=\"...\"></a>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages/accounting/details.html\",`<main class=\"salaxy-content sxytpl-accounting-report-viewer\">\r\n  <section>\r\n    <salaxy-accounting-report-viewer model=\"'url'\"></salaxy-accounting-report-viewer>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/accounting/holiday-pay-debt-query.html\",`<main class=\"salaxy-content sxytpl-accounting-holiday-pay-debt-report-query\">\r\n  <section>\r\n    <salaxy-accounting-holiday-pay-debt-report-query></salaxy-accounting-holiday-pay-debt-report-query>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/accounting/index.html\",`<main class=\"salaxy-content sxytpl-accounting-report-list\">\r\n  <section class=\"d-flex flex-column align-items-end\">\r\n    <a class=\"btn btn-default d-block mb-2\" href=\"#/accounting/query\" >{{ \"SALAXY.NG1_Sitemap.reports.accountingQuery\" | sxyTranslate}}...</a>\r\n    <a ng-if=\"!('hideHolidayDebt' | sxyIsInRole)\" class=\"btn btn-default d-block\" href=\"#/accounting/holiday-pay-debt-query\" >{{ \"SALAXY.NG1_Sitemap.reports.accountingHolidayPayDebtQuery\" | sxyTranslate}}...</a>\r\n  </section>\r\n  <section>\r\n    <salaxy-accounting-report-list></salaxy-accounting-report-list>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/accounting/query.html\",`<main class=\"salaxy-content sxytpl-accounting-report-query\">\r\n  <section>\r\n    <salaxy-accounting-report-query></salaxy-accounting-report-query>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/accounting-targets/details.html\",`<main class=\"salaxy-content sxytpl-accounting-target-details\">\r\n  <section class=\"pt-4\">\r\n    <salaxy-accounting-target-details model=\"'url'\"></salaxy-accounting-target-details>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/accounting-targets/index.html\",`<main class=\"salaxy-content sxytpl-accounting-target-list\">\r\n  <section>\r\n    <div class=\"salaxy-component salaxy-accounting-target-list\">\r\n      <salaxy-odata-table crud-controller=\"AccountingTargetCrudController as $crud\">\r\n      </salaxy-odata-table>\r\n    </div>\r\n  </section>\r\n</main>\r\n \r\n `);\n\n $templateCache.put(\"salaxy-components/pages/calc/all.html\",`<main class=\"salaxy-content sxytpl-calculations-all-list\">\r\n  <section>\r\n    <salaxy-action-button action=\"'newCalc'\" label=\"SALAXY.NG1.ActionButtonComponent.newCalculation\"></salaxy-action-button>\r\n    <salaxy-calc-list category=\"all\"></salaxy-calc-list>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/calc/details.html\",`<main class=\"salaxy-content sxytpl-calc-details\">\r\n  <section>\r\n    <salaxy-calc-usecase ng-if=\"'test' | sxyIsInRole\" model=\"'url'\" is-read-only-forced=\"$ctrl.route.readOnly\"></salaxy-calc-usecase>\r\n    <salaxy-calc ng-if=\"!('test' | sxyIsInRole)\" model=\"'url'\" is-read-only-forced=\"$ctrl.route.readOnly\"></salaxy-calc>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/calc/draft.html\",`<main class=\"salaxy-content sxytpl-calculations-draft-list\">\r\n  <section>\r\n    <salaxy-action-button ng-if=\"!$ctrl.route.readOnly\" action=\"'newCalc'\" label=\"SALAXY.NG1.ActionButtonComponent.newCalculation\"></salaxy-action-button>\r\n    <salaxy-calc-list category=\"draft\" read-only=\"$ctrl.route.readOnly\"></salaxy-calc-list>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/calc/editor.html\",`<salaxy-calc-editor model=\"'url'\">\r\n</salaxy-calc-editor>`);\n\n $templateCache.put(\"salaxy-components/pages/calc/error.html\",`<main class=\"salaxy-content sxytpl-calculations-error-list\">\r\n  <section>\r\n    <salaxy-calc-list category=\"error\"></salaxy-calc-list>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/calc/history.html\",`<div ng-controller=\"Calculator2022Controller as $ctrl\" ng-init=\"$ctrl.updateRows = false;$ctrl.model = 'url';\">\r\n  <!-- TODO: Move texts to the model as much as possible. -->\r\n  <h2 sxy-text=\"SALAXY.NG1_Pages.Calc.History.heading\"></h2>\r\n  <p class=\"lead\" sxy-text=\"SALAXY.NG1_Pages.Calc.History.lead\"></p>\r\n  <div ng-if=\"$ctrl.current\">\r\n    <sxy-form open-api=\"salaxy-secure/schemas/v02.json\" type=\"Calculation\" auto-gen=\"false\" debugger=\"false\" model=\"$ctrl.current\">\r\n      <div>\r\n        <fieldset>\r\n          <legend sxy-text=\"SALAXY.NG1_Pages.Calc.History.workerJobLabel\"></legend>\r\n          <salaxy-calc-employment model=\"$ctrl\" update-rows=\"false\"></salaxy-calc-employment>\r\n        </fieldset>\r\n        <fieldset>\r\n          <legend sxy-text=\"SALAXY.NG1_Pages.Calc.History.payrollInfo\"></legend>\r\n          <sxy-input label=\"SALAXY.NG1_Pages.Calc.History.salaryDateLabel\" model=\"form.workflow.salaryDate\"></sxy-input>\r\n          <sxy-input label=\"SALAXY.NG1_Pages.Calc.History.workStartDateLabel\" model=\"form.info.workStartDate\"></sxy-input>\r\n          <sxy-input label=\"SALAXY.NG1_Pages.Calc.History.workEndDateLabel\" model=\"form.info.workEndDate\"></sxy-input>\r\n          <sxy-input label=\"SALAXY.NG1_Pages.Calc.History.statusLabel\" model=\"form.workflow.status\" read-only=\"true\"></sxy-input>\r\n          <sxy-input label=\"SALAXY.NG1_Pages.Calc.History.fixedTaxAmountLabel\" model=\"form.worker.tax.fixedTaxAmount\" format=\"euro\"></sxy-input>\r\n        </fieldset>\r\n        <fieldset>\r\n          <legend sxy-text=\"SALAXY.NG1_Pages.Calc.History.rows\"></legend>\r\n          <salaxy-calc-rows-2019-editor parent=\"$ctrl.current\" title=\"{{'SALAXY.NG1_Pages.Calc.History.payrollRows' | sxyTranslate}}\" on-commit=\"$ctrl.historyUsecase.recalculate()\" show-edit-buttons=\"false\" show-gross-totals=\"false\"\r\n            is-in-edit=\"!$ctrl.current.isReadOnly\"></salaxy-calc-rows-2019-editor>\r\n        </fieldset>\r\n        <div class=\"text-end\">\r\n          <button ng-if=\"$ctrl.showAction('recalculate')\" type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.historyUsecase.recalculate()\" sxy-text=\"SALAXY.NG1_Pages.Calc.History.reCalculate\"></button>\r\n        </div>\r\n        <fieldset>\r\n          <legend sxy-text=\"SALAXY.NG1_Pages.Calc.History.cumulativePayrollRows\"></legend>\r\n          <p sxy-html=\"SALAXY.NG1_Pages.Calc.History.cumulativePayrollInfo.html\"></p>\r\n          <table class=\"table\">\r\n            <colgroup>\r\n              <col width=\"35%\">\r\n              <col width=\"15%\">\r\n              <col width=\"35%\">\r\n              <col width=\"15%\">\r\n            </colgroup>\r\n            <tbody>\r\n              <tr>\r\n                <th sxy-text=\"SALAXY.NG1_Pages.Calc.History.totalGrossSalary\"></th>\r\n                <td class=\"right\">{{ $ctrl.current.result.totals.totalGrossSalary | currency }}</td>\r\n                <th sxy-text=\"SALAXY.NG1_Pages.Calc.History.benefits\"></th>\r\n                <td class=\"right\">{{ $ctrl.current.result.workerCalc.benefits | currency }}</td>\r\n              </tr>\r\n              <tr>\r\n                <th sxy-text=\"SALAXY.NG1_Pages.Calc.History.holidayCompensation\" ps=\"*\"></th>\r\n                <td class=\"right\">{{ $ctrl.getRowTotal(\"holidayCompensation\") | currency }}</td>\r\n                <th sxy-text=\"SALAXY.NG1_Pages.Calc.History.holidayBonus\" ps=\"*\"></th>\r\n                <td class=\"right\">{{ $ctrl.getRowTotal(\"holidayBonus\") | currency }}</td>\r\n              </tr>\r\n              <tr>\r\n                <th sxy-text=\"SALAXY.NG1_Pages.Calc.History.holidaySalary\" ps=\"*\"></th>\r\n                <td class=\"right\">{{ $ctrl.getRowTotal(\"holidaySalary\") | currency }}</td>\r\n                <th sxy-text=\"SALAXY.NG1_Pages.Calc.History.totalTaxable\" ps=\"*\"></th>\r\n                <td class=\"right\">{{ $ctrl.current.result.totals.totalTaxable | currency }}</td>\r\n              </tr>\r\n              <tr>\r\n                <th sxy-text=\"SALAXY.NG1_Pages.Calc.History.tax\" ps=\"*\"></th>\r\n                <td class=\"right\">{{ $ctrl.current.result.workerCalc.tax | currency }}</td>\r\n                <th sxy-text=\"SALAXY.NG1_Pages.Calc.History.pension\"></th>\r\n                <td class=\"right\">{{ $ctrl.current.result.workerCalc.pension | currency }}</td>\r\n              </tr>\r\n              <tr>\r\n                <th sxy-text=\"SALAXY.NG1_Pages.Calc.History.unemploymentInsurance\"></th>\r\n                <td class=\"right\">{{ $ctrl.current.result.workerCalc.unemploymentInsurance | currency }}</td>\r\n                <th sxy-text=\"SALAXY.NG1_Pages.Calc.History.deductions\"></th>\r\n                <td class=\"right\">{{ $ctrl.current.result.workerCalc.deductions | currency }}</td>\r\n              </tr>\r\n              <tr>\r\n                <th sxy-text=\"SALAXY.NG1_Pages.Calc.History.totalExpenses\"></th>\r\n                <td class=\"right\">{{ $ctrl.current.result.totals.totalExpenses | currency }}</td>\r\n                <th sxy-text=\"SALAXY.NG1_Pages.Calc.History.salaryPayment\"></th>\r\n                <td class=\"right\">{{ $ctrl.current.result.workerCalc.salaryPayment | currency }}</td>\r\n              </tr>\r\n            </tbody>\r\n          </table>\r\n        </fieldset>\r\n        <div class=\"text-end\" ng-if=\"$ctrl.showAction('save')\">\r\n          <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.historyUsecase.save()\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n        </div>\r\n      </div>\r\n    </sxy-form>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages/calc/import-calcs.html\",`<main class=\"salaxy-content\">\r\n  <section>\r\n    <!-- Forcing isFullWidth  -->\r\n    <div style=\"display: none;\" ng-init=\"$ctrl.current.isFullWidth = true\"></div>\r\n    <salaxy-tab-buttons\r\n      current-tab=\"$ctrl.currentTab\"\r\n      options=\"[\r\n        { value: 'default', text: 'Palkkalaskelmien tuonti' },\r\n        { value: 'list', text: 'Palkkalistat' },\r\n      ]\"\r\n      tabs-id=\"importCalcs\">\r\n    </salaxy-tab-buttons>\r\n    <div class=\"tab-content\" id=\"tab-content-importCalcs\">\r\n      <div class=\"tab-pane\" id=\"default-tab\">\r\n        <salaxy-calc-import></salaxy-calc-import>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"list-tab\">\r\n        <salaxy-payroll-list details-url=\"/payroll/details/\" hide-button=\"$ctrl.route.readOnly\" is-read-only-forced=\"$ctrl.route.readOnly\"></salaxy-payroll-list>\r\n      </div>\r\n    </div>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/calc/index.html\",`<main class=\"salaxy-content sxytpl-calculations-dashboard\">\r\n  <section>\r\n    <salaxy-calc-dashboard hide-button=\"$ctrl.route.readOnly\" read-only=\"$ctrl.route.readOnly\"></salaxy-calc-dashboard>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/calc/ircalc.html\",`<salaxy-ir-calc model=\"'url'\"></salaxy-ir-calc>`);\n\n $templateCache.put(\"salaxy-components/pages/calc/paid-ir.html\",`<main class=\"salaxy-content sxytpl-calculations-paid-list\">\r\n  <section>\r\n    <salaxy-calc-list category=\"paidIr\" read-only=\"$ctrl.route.readOnly\" ></salaxy-calc-list>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/calc/paid.html\",`<main class=\"salaxy-content sxytpl-calculations-paid-list\">\r\n  <section>\r\n    <salaxy-action-button ng-if=\"!$ctrl.route.readOnly\" class=\"mb-3 d-block\" action=\"'newCalc'\" label=\"SALAXY.NG1.ActionButtonComponent.newCalculation\"></salaxy-action-button>\r\n    <salaxy-calc-list category=\"paid\" read-only=\"$ctrl.route.readOnly\"></salaxy-calc-list>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/calc/payment.html\",`<main class=\"salaxy-content sxytpl-calc-payment\">\r\n  <section>\r\n    <div class=\"container\" ng-controller=\"CalculationCrudController as $calc\" ng-init=\"$calc.model='url'\">\r\n      <salaxy-invoices-create ng-if=\"$calc.current\" model=\"$calc.current\"></salaxy-invoices-create>\r\n    </div>\r\n  </section>\r\n</main>\r\n`);\n\n $templateCache.put(\"salaxy-components/pages/calc/repair.html\",`<main class=\"salaxy-content sxytpl-calc-repair\">\r\n  <section>\r\n    <salaxy-calc-repair model=\"'url'\" is-read-only-forced=\"$ctrl.route.readOnly\"></salaxy-calc-repair>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/calc/repairs.html\",`<main class=\"salaxy-content sxytpl-calc-repairs\">\r\n  <section>\r\n    <salaxy-action-button action=\"'newRepair'\" on-after-action=\"$list.reload()\"></salaxy-action-button>\r\n    <salaxy-odata-table ng-ref=\"$list\" url=\"/v03/api/calculations/category/all\" crud-controller=\"CalculationCrudController as $crud\" options=\"{$filter: 'status eq \\\\'repair\\\\''}\" template-url=\"salaxy-components/odata/lists/CalculationsRepairs.html\" read-only=\"$ctrl.route.readOnly\">\r\n    </salaxy-odata-table>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/calc/shared.html\",`<main class=\"salaxy-content sxytpl-calculations-shared-list\">\r\n  <section>\r\n    <salaxy-calc-list category=\"shared\" read-only=\"$ctrl.route.readOnly\"></salaxy-calc-list>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/calc/travel.html\",`<div ng-controller=\"Calculator2022Controller as $ctrl\" ng-init=\"$ctrl.updateRows = false;$ctrl.model = 'url';\">\r\n  <!-- TODO: Move texts to the model as much as possible. -->\r\n  <h2>Matkalasku</h2>\r\n  <p class=\"lead\"></p>\r\n  <salaxy-spinner ng-if=\"!$ctrl.current\"></salaxy-spinner>\r\n  <div ng-if=\"$ctrl.current\">\r\n    <sxy-form open-api=\"salaxy-secure/schemas/v02.json\" type=\"Calculation\" auto-gen=\"false\" debugger=\"false\" model=\"$ctrl.current\">\r\n      <div>\r\n        <fieldset>\r\n          <legend sxy-text=\"SALAXY.NG1_Pages.Calc.History.workerJobLabel\"></legend>\r\n          <salaxy-calc-employment model=\"$ctrl\" update-rows=\"false\"></salaxy-calc-employment>\r\n        </fieldset>\r\n        <fieldset>\r\n          <legend sxy-text=\"SALAXY.NG1_Pages.Calc.History.payrollInfo\"></legend>\r\n          <sxy-input label=\"Matkan alku\" model=\"form.info.workStartDate\"></sxy-input>\r\n          <sxy-input label=\"SALAXY.NG1_Pages.Calc.History.workEndDateLabel\" model=\"form.info.workEndDate\"></sxy-input>\r\n          <sxy-input label=\"SALAXY.NG1_Pages.Calc.History.statusLabel\" model=\"form.workflow.status\" read-only=\"true\"></sxy-input>\r\n        </fieldset>\r\n        <salaxy-calc-rows-editor parent=\"$ctrl.current\" title=\"Matkalaskun rivit\" on-commit=\"$ctrl.recalculate()\"\r\n          show-edit-buttons=\"false\" show-gross-totals=\"true\" ng-ref=\"$rows\"\r\n          is-in-edit=\"!$ctrl.current.isReadOnly\">\r\n          <footer>\r\n            <p>Lisää matkalaskun rivi:</p>\r\n            <button class=\"btn btn-default\" ng-click=\"$rows.showEdit({ rowType: 'expenses' })\">Kulu</button>\r\n            <button class=\"btn btn-default\" ng-click=\"$rows.showEdit({ rowType: 'milageOwnCar' })\">Kilometrikorvaus</button>\r\n            <button class=\"btn btn-default\" ng-click=\"$rows.showEdit({ rowType: 'dailyAllowance' })\">Päiväraha</button>\r\n          </footer>\r\n        </salaxy-calc-rows-editor>\r\n        <div class=\"text-end\">\r\n          <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.recalculate()\" sxy-text=\"SALAXY.NG1_Pages.Calc.History.reCalculate\"></button>\r\n          <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.save()\" sxy-text=\"SALAXY.UI_Terms.send\"></button>\r\n        </div>\r\n      </div>\r\n    </sxy-form>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages/calendar/details.html\",`<main class=\"salaxy-content sxytpl-calendar-details\">\r\n  <section>\r\n    <salaxy-calendar-event-details  model=\"'url'\" is-read-only-forced=\"$ctrl.route.readOnly\"></salaxy-calendar-event-details >\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/calendar/index.html\",`<main class=\"salaxy-content sxytpl-calendar-index\">\r\n  <div class=\"text-end\">\r\n    <a class=\"btn btn-primary\" ng-href=\"#{{$odata.$crudController.getDefaults().detailsUrl}}new\" sxy-text=\"Uusi\"></a>\r\n  </div>\r\n\r\n  <section>\r\n    <div ng-show=\"$odata.items.length\">\r\n      <salaxy-odata-table ng-ref=\"$odata\" crud-controller=\"CalendarEventsCrudController as $crud\">\r\n      </salaxy-odata-table>\r\n    </div>\r\n  </section>\r\n\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/customer-invoices/details.html\",`<main class=\"salaxy-content sxytpl-datasets-details\">\r\n  <section>\r\n    <h1>TODO: Laskunäkymä</h1>\r\n    <div ng-controller=\"CustomerInvoiceCrudController as $ctrl\" ng-init=\"$ctrl.model = 'url'\">\r\n      <salaxy-spinner ng-if=\"!$ctrl.current\"></salaxy-spinner>\r\n      <div ng-if=\"$ctrl.current\">\r\n        <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.save()\">Tallenna</button>\r\n        <sxy-form open-api=\"salaxy-secure/schemas/v02.json\" type=\"CustomerInvoice\" auto-gen=\"true\" debugger=\"true\" model=\"$ctrl.current\">\r\n      </div>\r\n    </div>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/customer-invoices/index.html\",`<main class=\"salaxy-content sxytpl-datasets-list\">\r\n  <section>\r\n    <a href=\"#/customer-invoices/details/new\" class=\"btn btn-primary\" sxy-text=\"Luo uusi\"></a>\r\n    <salaxy-odata-table crud-controller=\"CustomerInvoiceCrudController as $crud\"></salaxy-odata-table>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/datasets/details.html\",`<main class=\"salaxy-content sxytpl-datasets-details\">\r\n  <section>\r\n    <salaxy-dataset-details mode=\"full-edit\" model=\"'url'\"></salaxy-dataset-details>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/datasets/index.html\",`<main class=\"salaxy-content sxytpl-datasets-list\">\r\n  <section>\r\n    <a href=\"#/datasets/details/new\" class=\"btn btn-primary float-end\" sxy-text=\"Luo uusi\"></a>\r\n    <h1>{{'Datasets' | sxyTranslate}}<span class=\"badge bg-primary\">BETA</span></h1>\r\n    <salaxy-odata-table crud-controller=\"DatasetsCrudController as $crud\"></salaxy-odata-table>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/employments/details.html\",`<main class=\"salaxy-content sxytpl-workers-details\">\r\n  <section>\r\n    <salaxy-employment-details model=\"'url'\" list-url=\"/employments/index\" is-read-only-forced=\"$ctrl.route.readOnly\" hide-buttons=\"$ctrl.route.readOnly\"></salaxy-employment-details>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/employments/index.html\",`<main class=\"salaxy-content sxytpl-workers-list\">\r\n  <section>\r\n    <salaxy-employment-list show-toolbar=\"true\" read-only=\"$ctrl.route.readOnly\"></salaxy-employment-list>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/employments/taxcards.html\",`<main class=\"salaxy-content sxytpl-workers-taxcardslist\">\r\n  <section class=\"sxytpl-intro\">\r\n    <p class=\"lead\" sxy-text=\"SALAXY.NG1_Pages.Workers.Taxcards.lead\"></p>\r\n  </section>\r\n  <section class=\"sxytpl-list\">\r\n    <salaxy-tax-cards-list></salaxy-tax-cards-list>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/home/error404.html\",`<main class=\"salaxy-content sxytpl-home-error404\">\r\n  <section>\r\n    <h1 class=\"page-header\" sxy-text=\"SALAXY.NG1_Pages.Home.Error.pageNotFound\"></h1>\r\n    <p class=\"lead\" sxy-html=\"SALAXY.NG1_Pages.Home.Error.lead.html\"></p>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/home/index.html\",`<main class=\"salaxy-content sxytpl-home-index\" salaxy-if-role=\"auth\">\r\n  <salaxy-signing ng-ref=\"$ctrl.$signing\" show-in-popup=\"true\"></salaxy-signing>\r\n  \r\n  <div ng-if=\"$ctrl.$signing.isSigningOk\">\r\n    <section ng-if=\"$ctrl.showKyc\">\r\n      <salaxy-alert type=\"warning\" class=\"alert-insurance-and-pension\" force-more-info=\"true\">\r\n        <main>\r\n          <div class=\"row\">\r\n            <div class=\"col-sm-11\">\r\n              <p class=\"lead lead-with-text\">Asiakkaan tuntemistiedot (KYC)</p>            \r\n            </div>\r\n          </div>\r\n        </main>\r\n        <aside>\r\n          <div class=\"row\">\r\n            <div class=\"col-sm-11\">\r\n              <p>\r\n                <span>\r\n                 Asiakasvaratilin kautta maksaminen (esim. Paytrail, viitemaksu) edellyttää asiakkaan tuntemistietojen (KYC) päivittämisen. Päivityksen voi tehdä nimenkirjoitusoikeudellinen henkilö “Päivitä asiakkaan tuntemistiedot nyt” -linkin kautta. Sivulta “Lue ohjeet” löytyy tarkat ohjeet ja linkki päivityksen tekijälle toimitettavaksi, jos et itse voi tehdä päivitystä.\r\n                </span>\r\n              </p>\r\n              <p>\r\n                <span>\r\n                  KYC-tietojen päivitys on voimassa vuoden kerrallaan ja tiedot voi käydä päivittämässä etukäteen. Näet tilin tiedoista (Asetukset → Tilin tiedot → Palkkaus.fi-tilin tiedot) milloin viimeistään tuntemistiedot (KYC) tulee päivittää.\r\n                </span>\r\n              </p>\r\n            </div>\r\n            <div class=\"col-sm-11\">\r\n              <a href=\"https://help.palkkaus.fi/hc/fi/articles/19590957330589-Asiakkaan-tuntemistietojen-päivitys-KYC\" target=\"_blank\" class=\"btn btn-primary\" role=\"button\">Lue ohjeet </a>\r\n              <a ng-href=\"{{('test' | sxyIsInRole) ? 'https://rc-iam.palkkaus.fi/wizard/index.html' : 'https://iam.palkkaus.fi/wizard/index.html'}}\" target=\"_blank\" class=\"btn btn-primary\" role=\"button\">Päivitä asiakkaan tuntemistiedot nyt</a>\r\n            </div>\r\n          </div>\r\n        </aside>\r\n      </salaxy-alert>\r\n    </section>\r\n    <section ng-if=\"$ctrl.getRoute('#/').getFlag('features','welcome')\" class=\"sxytpl-welcome\">\r\n      <salaxy-welcome settings-by-proxy=\"false\"></salaxy-welcome>\r\n    </section>\r\n    <section ng-if=\"$ctrl.getRoute('#/').getFlag('features', 'messages')\" class=\"sxytpl-list\">\r\n      <div>\r\n        <h3 class=\"section-title list-title\">Toimenpiteitä odottavat...</h3>\r\n        <salaxy-message-thread-list limit-to=\"10\" read-only=\"$ctrl.route.node.newMessageThreadDisabled\"></salaxy-message-thread-list>\r\n      </div>\r\n    </section>\r\n    <section ng-if=\"$ctrl.getRoute('#/').getFlag('features', 'workerList')\" class=\"sxytpl-list\">\r\n      <salaxy-employment-list limit-to=\"10\" read-only=\"$ctrl.route.node.newCalcDisabled\"></salaxy-employment-list>\r\n    </section>\r\n  </div>\r\n  <section ng-if=\"$ctrl.getRoute('#/').getFlag('features', 'contact')\" class=\"sxytpl-contact-info\">\r\n    <p>&nbsp;</p>\r\n    <salaxy-contact-info hide-contact-info=\"'contactInfoComponent.hideContactInfo' | sxyIsInRole\"></salaxy-contact-info>\r\n  </section>\r\n  <p>&nbsp;</p>\r\n  <p>&nbsp;</p>\r\n\r\n  <p class=\"copyright-text\"><small sxy-text=\"SALAXY.NG1_Pages.Home.copyRight\"></small> <small class=\"copyright-year\">{{$ctrl.getCurrentYear()}}</small></p>\r\n\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/household-years/active.html\",`\r\n<div ng-controller=\"HouseholdYearCrudController as $ctrl\" ng-init=\"$ctrl.setActiveYear()\">\r\n  <salaxy-household-year-details  model=\"$ctrl\" ></salaxy-household-year-details>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages/household-years/details.html\",`<salaxy-household-year-details model=\"'url'\" ></salaxy-household-year-details>`);\n\n $templateCache.put(\"salaxy-components/pages/household-years/index.html\",`<salaxy-household-year-list></salaxy-household-year-list>`);\n\n $templateCache.put(\"salaxy-components/pages/info/abc.html\",`<div class=\"row\">\r\n  <div class=\"col-12\">\r\n    <h3>Käyttöohjeet</h3>\r\n    <p class=\"\">\r\n      Ohjelman käyttöohjeet löytyvät tukisivustolta osoitteesta <a href=\"https://help.palkkaus.fi/hc/fi\" target=\"_blank\">help.palkkaus.fi</a>.\r\n    </p>\r\n    <p>Pääset ohjeisiin myös oikean alakulman Apua-napin kautta. Kirjoita hakusana hakukenttään niin saat listauksen siihen liittyvistä ohjeista. Voit siirtyä tukisivustolle ohjeen yläkulmassa olevan nuoli-ikonin kautta. Jos et löydä sopivaa ohjetta, voit\r\n      olla yhteydessä asiakaspalveluumme Apua-napin kautta, sähköpostitse tai puhelimitse, niin autamme sinua!\r\n    </p>\r\n  </div>\r\n\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages/info/index.html\",`<div class=\"row mb-4\">\r\n  <div class=\"col-12\">\r\n    <h1 sxy-text=\"SALAXY.NG1_Pages.Info.instructions\"></h1>\r\n    <p class=\"\" sxy-html=\"SALAXY.NG1_Pages.Info.infoText.html\"></p>\r\n    <p sxy-text=\"SALAXY.NG1_Pages.Info.infoText.info\"></p>\r\n  </div>\r\n\r\n  <div class=\"col-12\" ng-if=\"!$ctrl.route.node.hideButtons\">\r\n    <span sxy-html=\"SALAXY.NG1_Pages.Info.buttons.web.html\"></span>\r\n    <span sxy-html=\"SALAXY.NG1_Pages.Info.buttons.dataProtection.html\"></span>\r\n    <span sxy-html=\"SALAXY.NG1_Pages.Info.buttons.termsOfService.html\"></span>\r\n  </div>\r\n</div>\r\n<div class=\"row\" ng-if=\"!$ctrl.route.node.hideContactInfo\">\r\n  <div class=\"col-12\">\r\n    <h2 sxy-text=\"SALAXY.NG1_Pages.Info.customerService.title\"></h2>\r\n  </div>\r\n  <div class=\"col-12\">\r\n\r\n    <salaxy-contact-info hide-contact-info=\"'contactInfoComponent.hideContactInfo' | sxyIsInRole\"></salaxy-contact-info>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages/invoices/company.html\",`<main class=\"salaxy-content sxytpl-company-invoices\">\r\n  <section>  \r\n    <salaxy-company-invoices></salaxy-company-invoices>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/invoices/details.html\",`<main class=\"salaxy-content sxytpl-invoice-details\">\r\n\r\n  <style>\r\n    @media print {\r\n      /*Move to less*/\r\n      .nav-tabs,\r\n      #launcher {\r\n        display: none;\r\n      }\r\n    }\r\n  </style>\r\n  <section ng-controller=\"InvoiceCrudController as $invoice\" ng-init=\"$invoice.model = 'url'\">\r\n    <salaxy-tab-buttons\r\n      current-tab=\"$ctrl.currentTab\"\r\n      options=\"[\r\n        { value: 'default', text: 'SALAXY.NG1_Pages.Invoices.preview', hidden: !$ctrl.route.getFlag('features', 'preview') },\r\n        { value: 'calc', text: 'SALAXY.NG1_Pages.Invoices.calcs', hidden: !($invoice.current && $ctrl.route.getFlag('features', 'calc') && ($invoice.current.header.type == 'foreclosure' || $invoice.current.header.type == 'net' || $invoice.current.header.type == 'gross') && $invoice.getReportCalcs().length) },\r\n        { value: 'printandbarcode', text: 'SALAXY.NG1_Pages.Invoices.printAndBarCode', hidden: !$ctrl.route.getFlag('features', 'printAndBarCode') },\r\n        { value: 'actions', text: 'SALAXY.NG1_Pages.Invoices.actions', hidden: !(('test' | sxyIsInRole ) && ( $invoice.current.header.channel == 'palkkausWS' ||  $invoice.current.header.channel == 'palkkausPSD') || $ctrl.route.getFlag('features', 'actions')) },\r\n        { value: 'debug', text: 'Debug', hidden: !('test' | sxyIsInRole) }\r\n      ]\"\r\n      tabs-id=\"invoicesDetails\">\r\n    </salaxy-tab-buttons>\r\n    <div class=\"tab-content\" id=\"tab-content-invoicesDetails\">\r\n      <div class=\"tab-pane\" id=\"default-tab\">\r\n        <salaxy-invoice-preview model=\"$invoice\" ng-if=\"$ctrl.route.getFlag('features', 'preview')\"></salaxy-invoice-preview>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"calc-tab\">\r\n        <salaxy-calc-reports calcs=\"$invoice.getReportCalcs()\" report-type=\"'salarySlip'\" ng-if=\"$invoice.current && $ctrl.route.getFlag('features', 'calc') && ($invoice.current.header.type == 'foreclosure' || $invoice.current.header.type == 'net' || $invoice.current.header.type == 'gross') && $invoice.getReportCalcs().length\"></salaxy-calc-reports>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"printandbarcode-tab\">\r\n        <div ng-if=\"$ctrl.route.getFlag('features', 'printAndBarCode')\">\r\n          <p class=\"lead\">\r\n            <button type=\"button\" class=\"btn btn-primary float-end\" onclick=\"window.print()\" sxy-text=\"SALAXY.NG1.PalkkausPersonalPaymentOverviewComponent.printInvoices\"></button>\r\n          </p>\r\n          <div class=\"credit-transfer-container\" ng-if=\"$invoice.current\">\r\n            <salaxy-credit-transfer invoice=\"$invoice.current\"></salaxy-credit-transfer>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div class='tab-pane' id='actions-tab'>\r\n        <salaxy-invoice-edit model=\"$invoice\" ng-if=\"('test' | sxyIsInRole ) && ( $invoice.current.header.channel == 'palkkausWS' ||  $invoice.current.header.channel == 'palkkausPSD') || $ctrl.route.getFlag('features', 'actions')\"></salaxy-invoice-edit>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"debug-tab\">\r\n        <p ng-if=\"'test' | sxyIsInRole\">\r\n          <span class=\"badge bg-primary\">test</span> Debug-toiminnot vain testissä.\r\n        </p>\r\n        <salaxy-json-formatter json=\"$invoice.current\" open=\"1\"></salaxy-json-formatter>\r\n      </div>\r\n    </div>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/invoices/index.html\",`<main class=\"salaxy-content sxytpl-invoices-list\">\r\n  <section>  \r\n    <salaxy-invoice-list ng-if=\"'!person' | sxyIsInRole\"></salaxy-invoice-list>\r\n    <salaxy-invoice-list ng-if=\"'person' | sxyIsInRole\" mode=\"person\"></salaxy-invoice-list>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/invoices/payment-list.html\",`<main class=\"salaxy-content sxytpl-payment-list\">\r\n  <section>  \r\n    <salaxy-invoice-payment-list></salaxy-invoice-payment-list>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/invoices/sepa.html\",`<main class=\"salaxy-content sxytpl-invoices-list\">\r\n  <section>  \r\n    <salaxy-invoice-list mode=\"sepa\"></salaxy-invoice-list>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/irepr/details.html\",`<main class=\"salaxy-content sxytpl-ir-earnings-payment\">\r\n  <section>\r\n    <salaxy-ir-earnings-payment model=\"'url'\"></salaxy-ir-earnings-payment>\r\n  </section>\r\n</main>\r\n`);\n\n $templateCache.put(\"salaxy-components/pages/irepr/index.html\",`<main class=\"salaxy-content sxytpl-ir-earnings-payment-list\">\r\n  <section>\r\n    <salaxy-ir-earnings-payment-list></salaxy-ir-earnings-payment-list>\r\n  </section>\r\n</main>\r\n \r\n `);\n\n $templateCache.put(\"salaxy-components/pages/irpsr/details.html\",`<main class=\"salaxy-content sxytpl-ir-payer-summary\">\r\n  <section>\r\n    <salaxy-ir-payer-summary model=\"'url'\"></salaxy-ir-payer-summary>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/irpsr/index.html\",`<main class=\"salaxy-content sxytpl-ir-payer-summary-list\">\r\n  <section>\r\n    <salaxy-ir-payer-summary-list></salaxy-ir-payer-summary-list>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/messages/approval-list.html\",`<div>\r\n  <div class=\"btn-toolbar\">\r\n    <div class=\"btn-group\">\r\n      <button type=\"button\" class=\"btn btn-default\"\r\n        ng-click=\"$ctrl.$odata.options.$filter = 'status eq \\\\'active\\\\'';$ctrl.$odata.searchChanged()\"\r\n        ng-class=\"{ active: $ctrl.$odata.options.$filter != null }\">Aktiiviset</button>\r\n      <button type=\"button\" class=\"btn btn-default\"\r\n        ng-click=\"$ctrl.$odata.options.$filter = null;$ctrl.$odata.searchChanged()\"\r\n        ng-class=\"{ active: $ctrl.$odata.options.$filter == null }\">Kaikki</button>\r\n    </div>\r\n  </div>\r\n  <salaxy-odata-table crud-controller=\"MessageThreadCrudController as $crud\" ng-ref=\"$ctrl.$odata\"\r\n    options=\"{ $filter: 'status eq \\\\'active\\\\'' }\"\r\n    template-url=\"salaxy-components/odata/lists/MessageThreadsApproval.html\"></salaxy-odata-table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages/messages/approval.html\",`<main class=\"salaxy-content sxytpl-messages-details\">\r\n  <section>\r\n    <h3>Hyväksy / hylkää aineisto</h3>\r\n    <main>\r\n      <div ng-controller=\"MessageThreadCrudController as $ctrl\" ng-init=\"$ctrl.createCalc=true;$ctrl.model = 'url'\">\r\n        <div class=\"row\">\r\n          <div class=\"col-sm-4\">\r\n            <div class=\"btn-toolbar\" role=\"toolbar\" aria-label=\"Incoming message toolbar\">\r\n              <div class=\"btn-group\" role=\"group\" aria-label=\"Approval toolbar\">\r\n                <button type=\"button\" class=\"btn btn-success\" ng-click=\"$ctrl.current.status = 'approved';$ctrl.save()\"\r\n                  ng-disabled=\"$ctrl.current.status == 'approved'\">Hyväksy</button>\r\n                <button type=\"button\" class=\"btn btn-danger\" ng-click=\"$ctrl.current.status = 'rejected';$ctrl.save()\"\r\n                  ng-disabled=\"$ctrl.current.status == 'rejected'\">Hylkää</button>\r\n              </div>\r\n              <div class=\"btn-group\" role=\"group\" aria-label=\"Update toolbar\">\r\n                <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.save()\">Tallenna</button>\r\n              </div>\r\n            </div>\r\n            <div ng-switch=\"$ctrl.current.usecase.data.protoId\">\r\n              <div ng-switch-when=\"timer\">\r\n                <salaxy-timer ng-if=\"$ctrl.current\" timer-mode=\"edit\" parent=\"$ctrl.current\" crud-controller=\"$ctrl\"></salaxy-timer>\r\n              </div>\r\n              <div ng-switch-when=\"hourlyReport\">\r\n                <salaxy-hourly-report ng-if=\"$ctrl.current\" parent=\"$ctrl.current\" report-type=\"$ctrl.current.usecase.data.protoId\" crud-controller=\"$ctrl\"></salaxy-hourly-report>\r\n              </div>\r\n              <div ng-switch-when=\"timeReport\">\r\n                <salaxy-hourly-report ng-if=\"$ctrl.current\" parent=\"$ctrl.current\" report-type=\"$ctrl.current.usecase.data.protoId\" crud-controller=\"$ctrl\"></salaxy-hourly-report>\r\n              </div>\r\n              <div ng-switch-when=\"absence\">\r\n                <salaxy-absence-periods ng-if=\"$ctrl.current\" parent=\"$ctrl.getMessage().contentData\" condensed=\"true\"></salaxy-absence-periods>\r\n              </div>\r\n              <div ng-switch-when=\"annualLeave\">\r\n                <salaxy-holiday-year-holidays ng-if=\"$ctrl.current\" parent=\"$ctrl.getMessage().contentData\" condensed=\"true\"></salaxy-holiday-year-holidays>\r\n              </div>\r\n              <div ng-switch-when=\"calcRow\">\r\n                <salaxy-calc-rows-editor ng-if=\"$ctrl.current\" parent=\"$ctrl.getMessage().contentData\">\r\n                </salaxy-calc-rows-editor>\r\n              </div>\r\n              <div ng-switch-when=\"expense\">\r\n                <salaxy-expense-report ng-if=\"$ctrl.current\" parent=\"$ctrl.current\" report-type=\"$ctrl.current.usecase.data.protoId\" crud-controller=\"$ctrl\">\r\n                </salaxy-expense-report>\r\n              </div>\r\n              <div ng-switch-when=\"travel\">\r\n                <salaxy-expense-report ng-if=\"$ctrl.current\" parent=\"$ctrl.current\" report-type=\"$ctrl.current.usecase.data.protoId\" crud-controller=\"$ctrl\">\r\n                </salaxy-expense-report>\r\n              </div>\r\n              <div ng-switch-when=\"default\">\r\n                <div ng-if=\"$ctrl.isNew()\">\r\n                  <h2>Temp UI: This will be replaced!</h2>\r\n                  <salaxy-input name=\"title\" label=\"SALAXY.NG1.MessageThreadComponent.title\" require=\"true\" ng-model=\"$ctrl.current.title\"></salaxy-input>\r\n                  <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.save()\">\r\n                    <span sxy-text=\"SALAXY.UI_Terms.save\"></span>\r\n                  </button>\r\n                  <hr />\r\n                </div>\r\n                <div class=\"messages-container\" ng-if=\"$ctrl.current.messages && !$ctrl.isNew()\">\r\n                  <h2>{{ $ctrl.current.title }}</h2>\r\n                  <div ng-repeat=\"item in $ctrl.current.messages\" ng-switch=\"item.fromParty\">\r\n                    <div ng-switch-when=\"owner,undefined\" ng-switch-when-separator=\",\">\r\n                      <salaxy-avatar avatar=\"$ctrl.current.ownerInfo\" class=\"float-start\"></salaxy-avatar>\r\n                      <div class=\"message-bubble left\" ng-class=\"{ 'in-edit': $ctrl.isInEdit, 'unread': !$ctrl.getReadTime(item)  }\">\r\n                        <ng-include src=\"'salaxy-components/communications/messages/MessageContent.html'\"></ng-include>\r\n                        <span class=\"updated-at\">{{ item.time | sxyTime }}, {{ $ctrl.getReadTime(item) ? (('SALAXY.NG1.MessageThreadComponent.read' |sxyTranslate) + ' ' +\r\n                          ($ctrl.getReadTime(item) | sxyTime)) : ('SALAXY.NG1.MessageThreadComponent.unread' |sxyTranslate) }}</span>\r\n                      </div>\r\n                    </div>\r\n                    <div ng-switch-when=\"otherParty\" class=\"text-end\">\r\n                      <salaxy-avatar avatar=\"$ctrl.current.otherPartyInfo\" class=\"float-end\"></salaxy-avatar>\r\n                      <div class=\"message-bubble right {{item.type}}\" ng-class=\"{ 'in-edit': $ctrl.isInEdit, 'unread': !$ctrl.getReadTime(item) }\">\r\n                        <ng-include src=\"'salaxy-components/communications/messages/MessageContent.html'\"></ng-include>\r\n                        <span class=\"updated-at\" ng-if=\"item.type != 'email'\">{{ item.time | sxyTime }}, {{ $ctrl.getReadTime(item) ? (('SALAXY.NG1.MessageThreadComponent.read'\r\n                          |sxyTranslate) + ' ' + ($ctrl.getReadTime(item) | sxyTime)) : ('SALAXY.NG1.MessageThreadComponent.unread' |sxyTranslate)}}</span>\r\n                        <span class=\"updated-at\" ng-if=\"item.type == 'email'\">{{ item.time | sxyTime }}</span>\r\n                      </div>\r\n                    </div>\r\n                    <div ng-switch-default class=\"alert alert-danger\">\r\n                      <ng-include src=\"'salaxy-components/communications/MessageThread_MessageContent.html'\"></ng-include>\r\n                    </div>\r\n                  </div>\r\n                  <div>\r\n                    <div ng-if=\"$ctrl.isReadOnly\" class=\"alert alert-info\">\r\n                      <p><strong>Työnantaja on merkinnyt viestiketjun käsitellyksi.</strong></p>\r\n                    </div>\r\n                    <div class=\"row\">\r\n                      <div class=\"col-8 col-sm-9\">\r\n                        <textarea placeholder=\"{{'SALAXY.NG1.MessageThreadComponent.writeOrPaste' |sxyTranslate}}\" ng-model=\"$ctrl.newMessage.content\"></textarea>\r\n                      </div>\r\n                      <div class=\"col-4 col-sm-3\">\r\n                        <button type=\"button\" class=\"btn btn-primary btn-labeled-left\" style=\"width: 100%; text-align: left; margin-bottom: 4px\" ng-click=\"$ctrl.sendMessage()\"\r\n                          ng-disabled=\"!$ctrl.newMessage.content\">\r\n                          <i class=\"bi bi-send-fill\"></i>\r\n                          <span sxy-text=\"SALAXY.UI_Terms.send\"></span>\r\n                        </button>\r\n                      </div>\r\n                    </div>\r\n                  </div>\r\n                  <div id=\"messageContainerBottom\">&nbsp;</div>\r\n                </div>\r\n              </div>\r\n              <div ng-switch-default>\r\n                TODO: Handle {{ $ctrl.current.usecase.uri }} / {{ $ctrl.current.usecase.data.protoId }}.\r\n              </div>\r\n            </div>\r\n          </div>\r\n          <div class=\"col-sm-8\">\r\n            <div class=\"btn-toolbar\" role=\"toolbar\" aria-label=\"Calculator toolbar\">\r\n              <div class=\"btn-group\" role=\"group\" aria-label=\"Update\">\r\n                <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.updateCalc()\">Päivitä rivit</button>\r\n                <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.recalculate()\">Laske uudelleen</button>\r\n              </div>\r\n              <div class=\"btn-group\" role=\"group\" aria-label=\"Select calc / payroll\">\r\n                <button type=\"button\" class=\"btn btn-default\">Valitse palkkalista...</button>\r\n                <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.selectCalc()\">...laskelma</button>\r\n              </div>\r\n              <div class=\"btn-group\" role=\"group\" aria-label=\"Process calculation\">\r\n                <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.saveCalc()\">Tallenna</button>\r\n                <a ng-href=\"#/calc/details/{{ $ctrl.calc.id }}\" ng-disabled=\"!$ctrl.calc.id\" class=\"btn btn-default\">Siirry laskelmaan</a>\r\n              </div>\r\n            </div>\r\n            <salaxy-calc-rows-2019-editor parent=\"$ctrl.calc\" mode=\"edit\" title=\"Laskelman rivit\"></salaxy-calc-rows-2019-editor>\r\n            <div ng-if=\"$ctrl.calc.result.totals\">\r\n              <salaxy-calc-reports calcs=\"[$ctrl.calc]\" report-type=\"'salarySlip'\"></salaxy-calc-reports>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </main>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/messages/details-partner.html\",`<main class=\"salaxy-content sxytpl-messages-details\" ng-init=\"$ctrl.role = 'otherParty'\">\r\n  <section>\r\n    <div class=\"container\" ng-controller=\"SessionController as $sessionCtrl\">\r\n      <div ng-controller=\"MessageThreadCrudController as $msg\" ng-init=\"$msg.model = 'url'\">\r\n        <salaxy-message-thread model=\"$msg\" role=\"{{ $ctrl.role }}\" other-party=\"$sessionCtrl.session.settings.partner.accountId\" other-party-options=\"{ [$sessionCtrl.session.settings.partner.accountId]: $sessionCtrl.session.settings.partner.info.avatar.displayName }\">\r\n          <header-new>\r\n            <h3 sxy-text=\"SALAXY.PRO_Pages.messages.details.newMessage\"></h3>\r\n            {{\"SALAXY.PRO_Pages.messages.details.partner\" | sxyTranslate}}: {{$sessionCtrl.session.settings.partner.info.avatar.displayName}}<br />\r\n            <salaxy-input name=\"owner\" label=\"SALAXY.PRO_Pages.messages.details.company\" ng-model=\"$sessionCtrl.session.currentAccount.avatar.displayName\" disabled=\"true\"></salaxy-input>\r\n          </header-new>\r\n          <header>\r\n            <h2 class=\"d-flex justify-content-between\">\r\n              <div>{{ $msg.current.ownerWorkflow.salaryDate | sxyDate }}</div>\r\n              <div>{{ $msg.current.title }}</div>\r\n            </h2>\r\n            <div class=\"row\">\r\n              <div class=\"col-sm-6 d-flex\">\r\n                <salaxy-avatar avatar=\"$sessionCtrl.session.currentAccount.avatar\" class=\"\"></salaxy-avatar>\r\n                <div class=\"ms-3\">\r\n                  <h3>{{ $sessionCtrl.session.currentAccount.avatar.displayName }}</h3>\r\n                  <code>{{ $sessionCtrl.session.currentAccount.avatar.id | sxyIban }}</code><br />\r\n                  <a href=\"mailto:{{ $sessionCtrl.session.currentAccount.contact.email }}\">{{ $sessionCtrl.session.currentAccount.contact.email }}</a><br /> {{'SALAXY.PRO_Pages.messages.details.phone' | sxyTranslate}}: {{ $sessionCtrl.session.currentAccount.contact.telephone || \"-\" }}\r\n                </div>\r\n              </div>\r\n              <div class=\"col-sm-6\">\r\n                <h3>{{ $sessionCtrl.session.currentAccount.identity.contract.authorizedBy.name || ('SALAXY.PRO_Pages.messages.details.noContactPerson' | sxyTranslate) }}</h3>\r\n                <p>\r\n                  <a href=\"mailto:{{ $sessionCtrl.session.currentAccount.identity.contract.authorizedBy.email }}\">{{ $sessionCtrl.session.currentAccount.identity.contract.authorizedBy.email }}</a><br /> {{'SALAXY.PRO_Pages.messages.details.phone' | sxyTranslate}}: {{ $sessionCtrl.session.currentAccount.identity.contract.authorizedBy.telephone\r\n                  || \"-\" }}<br /> {{ $sessionCtrl.session.currentAccount.identity.contract.isSigned ? ('SALAXY.PRO_Pages.messages.details.signed' | sxyTranslate) + ' ' + ($sessionCtrl.session.currentAccount.identity.contract.signedAt | sxyTime) : ('SALAXY.PRO_Pages.messages.details.notSigned' |\r\n                  sxyTranslate) }}\r\n                </p>\r\n              </div>\r\n            </div>\r\n            <hr />\r\n          </header>\r\n        </salaxy-message-thread>\r\n      </div>\r\n    </div>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/messages/details.html\",`<main class=\"salaxy-content sxytpl-messages-details\">\r\n  <section>\r\n    <salaxy-assure-partner>\r\n      <main>\r\n        <salaxy-message-thread model=\"'url'\" role=\"owner\" other-party=\"'partner'\" mark-as-read=\"5\">\r\n          <header-new>\r\n            <h2 sxy-text=\"SALAXY.NG1_Pages.Messages.newMessageDetails.title\"></h2>\r\n            <p class=\"lead\" sxy-html=\"SALAXY.NG1_Pages.Messages.newMessageDetails.description.html\"></p>\r\n          </header-new>\r\n        </salaxy-message-thread>\r\n      </main>\r\n    </salaxy-assure-partner>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/messages/index.html\",`<main class=\"salaxy-content sxytpl-message-thread-list\">\r\n  <section>\r\n    <salaxy-message-thread-list read-only=\"$ctrl.route.readOnly\"></salaxy-message-thread-list>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/messages/omapalkka.html\",`<div ng-controller=\"OmapalkkaController as $ctrl\">\r\n  <iframe ng-if=\"$ctrl.url\" ng-src=\"{{$ctrl.url}}\" style=\"width: 100%; height: calc(100vh - 180px); margin-bottom: -100px; border: 0;\"></iframe>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages/partners/assure-worker-account.html\",`<main class=\"salaxy-content sxytpl-partners-worker-assure\">\r\n    <section>\r\n        <salaxy-worker-assure></salaxy-worker-assure>\r\n    </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/payment-channel/details.html\",`<main class=\"salaxy-content sxytpl-invoices-list\">\r\n  <section ng-controller=\"PaymentChannelController as $ctrl\" ng-init=\"$ctrl.model = 'url'\">\r\n    <div ng-if=\"$ctrl.channel\">\r\n      <salaxy-avatar class=\"salaxy-calc-row-type-avatar salaxy-input-enum-avatar float-start\" avatar=\"$ctrl.getChannelAvatar()\"></salaxy-avatar>\r\n      <div class=\"salaxy-input-enum-text\"><strong>{{\"PaymentChannel.\" + $ctrl.channel | sxyEnum}}</strong></div>\r\n      <div class=\"salaxy-input-enum-title\">{{ \"PaymentChannel.\" + $ctrl.channel | sxyEnumDescr }}</div>\r\n      <salaxy-tab-buttons\r\n        current-tab=\"$ctrl.currentTab\"\r\n        options=\"[\r\n          { value: 'default', text: 'Esikatselu' },\r\n          { value: 'status', text: 'Tilan päivitys', hidden: !('test' | sxyIsInRole) },\r\n          { value: 'edit', text: 'Laskun muokkaus', hidden: !('test' | sxyIsInRole) },\r\n          { value: 'debug', text: 'Debug', hidden: !('test' | sxyIsInRole) }\r\n        ]\"\r\n        tabs-id=\"paymentChannelDetails\">\r\n      </salaxy-tab-buttons>\r\n      <div class=\"tab-content\" id=\"tab-content-paymentChannelDetails\">\r\n        <div class=\"tab-pane\" id=\"default-tab\">\r\n          <salaxy-spinner ng-if=\"!$ctrl.current && $ctrl.isLoading\"></salaxy-spinner>\r\n          <salaxy-payment-channel-invoice-preview ng-if=\"$ctrl.current\" model=\"$ctrl\"></salaxy-payment-channel-invoice-preview>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"status-tab\" ng-if=\"'test' | sxyIsInRole\">\r\n          <div class=\"alert alert-danger\" ng-if=\"!$ctrl.isLoading && !$ctrl.current\">Laskua ei löydy</div>\r\n            <form ng-if=\"$ctrl.current\" ng-submit=\"$ctrl.updateStatus()\">\r\n              <div class=\"form-horizontal\" ng-init=\"$ctrl.resetStatusData()\">\r\n                <h2>Päivitä tila</h2>\r\n                <p>Testilomake tilan päivitykseen. Alta voit myös poistaa laskun.</p>\r\n                <salaxy-input name=\"statusId\" ng-model=\"$ctrl.statusData.id\" label=\"Id\" disabled=\"true\"></salaxy-input>\r\n                <salaxy-input name=\"statusExternalId\" ng-model=\"$ctrl.statusData.externalId\" label=\"ID maksukanavassa\"></salaxy-input>\r\n                <salaxy-input-enum label=\"Maksun tila\" name=\"statusStatus\" ng-model=\"$ctrl.statusData.status\" enum=\"InvoiceStatus\" required></salaxy-input-enum>\r\n                <salaxy-datepicker-popup name=\"statusDate\" ng-model=\"$ctrl.statusData.date\" label=\"Maksupäivä\"></salaxy-datepicker-popup>\r\n                <salaxy-input-number name=\"statusAmount\" ng-model=\"$ctrl.statusData.amount\" label=\"Maksettu summa\"></salaxy-input-number>\r\n                <salaxy-input name=\"statusReceiverFullName\" ng-model=\"$ctrl.statusData.receiverFullName\" label=\"Vastaanottajan nimi\"></salaxy-input>\r\n                <salaxy-input name=\"statusReceiverIban\" ng-model=\"$ctrl.statusData.receiverIban\" label=\"Vastaanottajan tilinumero\"></salaxy-input>\r\n                <salaxy-input name=\"statusReferenceNumber\" ng-model=\"$ctrl.statusData.referenceNumber\" label=\"Viitenumero\"></salaxy-input>\r\n              </div>\r\n              <div>\r\n                <button type=\"submit\" class=\"btn btn-primary float-end\">Päivitä tila</button>\r\n                <button type=\"button\" ng-click=\"$ctrl.delete()\" class=\"btn btn-danger\">Poista lasku</button>\r\n              </div>\r\n            </form>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"edit-tab\" ng-if=\"'test' | sxyIsInRole\">\r\n          <div class=\"alert alert-danger\" ng-if=\"!$ctrl.isLoading && !$ctrl.current\">Laskua ei löydy</div>\r\n            <form ng-if=\"$ctrl.current\" ng-submit=\"$ctrl.save()\">\r\n              <div class=\"form-horizontal\">\r\n                <h2>Muokkaa laskua</h2>\r\n                <p>Testilomake laskun muokkaukseen. Alta voit myös poistaa laskun.</p>\r\n                <salaxy-datepicker-popup name=\"date\" ng-model=\"$ctrl.current.header.date\" label=\"Laskun päivä\"></salaxy-datepicker-popup>\r\n                <salaxy-datepicker-popup name=\"dueDate\" ng-model=\"$ctrl.current.header.dueDate\" label=\"Eräpäivä\"></salaxy-datepicker-popup>\r\n                <salaxy-datepicker-popup name=\"logicalDate\" ng-model=\"$ctrl.current.header.logicalDate\" label=\"Looginen päivä\"></salaxy-datepicker-popup>\r\n                <salaxy-input name=\"message\" ng-model=\"$ctrl.current.header.message\" label=\"Viesti\"></salaxy-input>\r\n              </div>\r\n              <div>\r\n                <button type=\"submit\" class=\"btn btn-primary float-end\">Tallenna</button>\r\n                <button type=\"button\" ng-click=\"$ctrl.delete()\" class=\"btn btn-danger\">Poista lasku</button>\r\n              </div>\r\n            </form>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"debug-tab\" ng-if=\"'test' | sxyIsInRole\">\r\n          <salaxy-json-formatter  ng-if=\"$ctrl.current\" json=\"$ctrl.current\" open=\"1\"></salaxy-json-formatter>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div ng-if=\"!$ctrl.channel && !$ctrl.isLoading\">\r\n      <div class=\"alert alert-danger\">Käyttäjätilillä ei ole omaa maksukanavaa</div>\r\n    </div>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/payment-channel/index.html\",`<main class=\"salaxy-content sxytpl-payment-channel\">\r\n  <section ng-controller=\"PaymentChannelController as $ctrl\">\r\n    <div ng-if=\"$ctrl.channel\">\r\n      <salaxy-avatar class=\"salaxy-calc-row-type-avatar salaxy-input-enum-avatar float-start\" avatar=\"$ctrl.getChannelAvatar()\"></salaxy-avatar>\r\n      <div class=\"salaxy-input-enum-text\"><strong>{{\"PaymentChannel.\" + $ctrl.channel | sxyEnum}}</strong></div>\r\n      <div class=\"salaxy-input-enum-title\">{{ \"PaymentChannel.\" + $ctrl.channel | sxyEnumDescr }}</div>\r\n      <salaxy-tab-buttons\r\n        current-tab=\"$ctrl.currentTab\"\r\n        options=\"[\r\n          { value: 'odata', text: 'All items' },\r\n          { value: 'fulldata', text: 'Unread items' },\r\n        ]\"\r\n        tabs-id=\"paymentChannelIndex\">\r\n      </salaxy-tab-buttons>\r\n      <div class=\"tab-content\" id=\"tab-content-paymentChannelIndex\">\r\n        <div class=\"tab-pane\" id=\"odata-tab\">\r\n          <salaxy-odata-table crud-controller=\"PaymentChannelController as $crud\" options=\"{ $orderby: 'endAt desc'}\" template-url=\"salaxy-components/odata/lists/InvoicesPaymentChannel.html\"></salaxy-odata-table>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"fulldata-tab\">\r\n          <div>\r\n            <table class=\"table\">\r\n              <thead>\r\n                <tr>\r\n                  <th colspan=\"2\">Payer</th>\r\n                  <th colspan=\"2\">\r\n                    Receiver<br /> Payment type\r\n                  </th>\r\n                  <th class=\"right\">\r\n                    Date<br /> Due date\r\n                  </th>\r\n                  <th class=\"right\">\r\n                    Created<br /> Updated\r\n                  </th>\r\n                  <th class=\"right\">Payment</th>\r\n                  <th></th>\r\n                </tr>\r\n              </thead>\r\n              <tbody>\r\n                <tr ng-repeat=\"item in $ctrl.unreadInvoices\">\r\n                  <td class=\"td-avatar middle\">\r\n                    <salaxy-avatar class=\"salaxy-calc-row-type-avatar\" avatar=\"item.payer.avatar\"></salaxy-avatar>\r\n                  </td>\r\n                  <td class=\"middle\">\r\n                    {{ item.payer.avatar.displayName }}<br>\r\n                    <small class=\"hidden-xxs\">{{ item.payer.officialId }}, {{ item.payer.partnerKey }}</small>\r\n                  </td class=\"middle\">\r\n                  <td class=\"td-avatar middle\">\r\n                    <salaxy-avatar class=\"salaxy-calc-row-type-avatar\" avatar=\"item.recipient.beneficiary.avatar\"></salaxy-avatar>\r\n                  </td>\r\n                  <td class=\"middle\">\r\n                    {{ item.recipient.beneficiary.avatar.displayName }}<br>\r\n                    <small class=\"hidden-xxs\">{{ item.header.message }}</small>\r\n                  </td class=\"middle\">\r\n                  <td class=\"middle right\">\r\n                    {{ item.header.date | sxyDate }}<br /> {{ item.header.dueDate | sxyDate }}\r\n                  </td>\r\n                  <td class=\"right\">\r\n                    {{ item.createdAt | sxyDate }}<br /> {{ item.updatedAt | sxyDate }}\r\n                  </td>\r\n                  <td class=\"middle right\">\r\n                    {{ item.header.total | currency }}\r\n                  </td>\r\n                  <td class=\"middle right\">\r\n                    <a ng-href=\"#{{$ctrl.getDefaults().detailsUrl}}{{ item.id }}\" class=\"btn btn-primary\">\r\n                      {{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\r\n                    </a>\r\n                  </td>\r\n                </tr>\r\n              </tbody>\r\n            </table>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div ng-if=\"!$ctrl.channel\">\r\n      <div class=\"alert alert-danger\">Käyttäjätilillä ei ole omaa maksukanavaa</div>\r\n    </div>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/payroll/details.html\",`<main class=\"salaxy-content sxytpl-calculations-payroll-edit\">\r\n  <div ng-if=\"$ctrl.newPayrollVersion.show\" class=\"d-none d-md-block salaxy-payroll-v4 form-horizontal\">\r\n    <salaxy-input-boolean name=\"newPayrollSwitch\" type=\"switch\" ng-model=\"$ctrl.newPayrollVersionUse\" label=\"SALAXY.NG1.PayrollComponent.newVersion\" label-cols=\"col-7\" label-true=\"on\" label-false=\"off\"></salaxy-input-boolean>\r\n  </div>\r\n  <section ng-if=\"$ctrl.newPayrollVersion.use\">\r\n    <!-- Switching isFullWidth as long as the two UI are in same URL. -->\r\n    <div style=\"display: none;\" ng-init=\"$ctrl.current.isFullWidth = true\"></div>\r\n    <salaxy-payroll-details model=\"'url'\" is-read-only-forced=\"$ctrl.route.readOnly\" actions=\"$ctrl.route.getParam('actions')\"></salaxy-payroll-details>\r\n  </section>\r\n  <section ng-if=\"!$ctrl.newPayrollVersion.use\">\r\n    <div style=\"display: none;\" ng-init=\"$ctrl.current.isFullWidth = false\"></div>\r\n    <salaxy-payroll-edit model=\"'url'\" is-read-only-forced=\"$ctrl.route.readOnly\"\r\n      actions=\"$ctrl.route.getParam('actions')\"></salaxy-payroll-edit>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/payroll/import.html\",`<main class=\"salaxy-content sxytpl-calculations-payroll-import\">\r\n  <section>\r\n    <div ng-controller=\"SalaryBasesController as $ctrl\">\r\n      <div ng-if=\"!$ctrl.datasets\" class=\"container\">\r\n        <salaxy-spinner title=\"Ladataan määrittelyjä...\"></salaxy-spinner>\r\n      </div>\r\n      <div ng-if=\"$ctrl.datasets && !$ctrl.datasets.length\" class=\"alert alert-danger container\">  \r\n        <strong>BETA:</strong>\r\n        Tietojen tuonti (import) on rajoitetussa testauksessa PRO-palvelussa ja tuodaan tuotantoon syksyllä.\r\n        Kysy asiakaspalvelusta lisätietoja ennen kuin käytät tätä toimintoa.\r\n      </div>\r\n      <div ng-if=\"$ctrl.datasets.length && !$ctrl.dataset\" class=\"container\">\r\n        <h3>Valitse Import-tyyppi</h3>\r\n        <div style=\"max-width: 600px;\">\r\n          <label ng-repeat=\"ds in $ctrl.datasets\" class=\"btn btn-block btn-default\" ng-click=\"$ctrl.loadDataset(ds)\">{{ ds.shortText }}</label>\r\n        </div>\r\n      </div>\r\n      <div ng-if=\"$ctrl.dataset\">\r\n        <div class=\"btn-toolbar\">\r\n          <div class=\"btn-group\">\r\n            <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.getEmployments()\">1. Hae työsuhteet</button>\r\n            <button type=\"button\" class=\"btn btn-default\" ng-controller=\"ImportController as $import\" ng-click=\"$import.showImport($ctrl.getImportable())\">2. Lataa data</button>\r\n            <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.processImport()\">3. Käsittele data (mapper)</button>\r\n            <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.saveToPayroll()\">4. Tallenna palkkalistaan</button>\r\n          </div>\r\n        </div>\r\n        <salaxy-tab-buttons\r\n          ng-if=\"$ctrl.current\"\r\n          current-tab=\"$ctrl.currentTab\"\r\n          options=\"[\r\n            { value: 'payroll', text: 'Palkkalista' },\r\n            { value: 'employments', text: 'Työsuhteet' },\r\n            { value: 'rowtypemapnew', text: 'Säännöt (rivityypit)' },\r\n            { value: 'rows', text: 'Rivit' },\r\n            { value: 'src', text: 'Debug' }\r\n          ]\"\r\n          tabs-id=\"payrollImport\">\r\n        </salaxy-tab-buttons>\r\n        <div class=\"tab-content\" id=\"tab-content-payrollImport\">\r\n          <div class=\"tab-pane\" id=\"payroll-tab\">\r\n            <salaxy-payroll-edit model=\"'url'\" ng-ref=\"$ctrl.payrollController\"></salaxy-payroll-edit>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"employments-tab\">\r\n            <table class=\"table table-sm\">\r\n              <thead>\r\n                <tr>\r\n                  <th></th>\r\n                  <th>\r\n                    <div>Työntekijän nimi (Palkkaus.fi)</div>\r\n                    <div><small>Työsuhteen tyyppi</small></div>\r\n                  </th>\r\n                  <th class=\"right\">\r\n                    <div>ID lähteessä</div>\r\n                    <div>Tuntia / kk</div>\r\n                  </th>\r\n                  <th>Rivit</th>\r\n                  <th></th>\r\n                </tr>\r\n              </thead>\r\n              <tbody>\r\n                <tr ng-repeat=\"emp in $ctrl.employments\">\r\n                  <td>\r\n                    <salaxy-avatar style=\"font-size: 50px;\" avatar=\"emp.personalInfo.avatar\"></salaxy-avatar>\r\n                  </td>\r\n                  <td>\r\n                    <div><strong>{{ emp.personalInfo.avatar.displayName }}</strong> ({{ emp.personalInfo.officialId }})</div>\r\n                    <div><small>{{ emp.work.wageBasis }}</small></div>\r\n                    <div><small>{{ emp.updatedAt }}</small></div>\r\n                  </td>\r\n                  <td class=\"right\">\r\n                    <div>{{ emp.info.sourceId || \"-\" }}</div>\r\n                    <div ng-if=\"emp.work.monthlyHours\"><strong>{{ emp.work.monthlyHours }}</strong></div>\r\n                    <div ng-if=\"!emp.work.monthlyHours\" class=\"text-muted\">160</div>\r\n                  </td>\r\n                  <td>\r\n                    <table class=\"table table-sm\">\r\n                      <tr ng-repeat=\"row in emp.work.salaryDefaults\">\r\n                        <td>{{ \"CalculationRowType.\" + row.rowType | sxyEnum }}</td>\r\n                        <td class=\"right\">{{ row.count | number }} * {{ row.price ? (row.price | currency) : \"-\" }}</td>\r\n                      </tr>\r\n                    </table>                  \r\n                  </td>\r\n                  <td>\r\n                    <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.editEmployment(emp)\">Muokkaa</button>\r\n                  </td>\r\n                </tr>\r\n              </tbody>\r\n            </table>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"rowtypemapnew-tab\">\r\n            <div class=\"btn-toolbar\">\r\n              <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.save()\">Tallenna</button>\r\n            </div>\r\n            <table class=\"table\" ng-controller=\"CalcRows2019Controller as $rows\" ng-init=\"$rows.rows=$ctrl.getRowTypeMapper()\">\r\n              <thead>\r\n                <tr>\r\n                  <th colspan=\"2\">Lähdedata</th>\r\n                  <th></th>\r\n                  <th colspan=\"2\">Kohde</th>\r\n                </tr>\r\n                <tr>\r\n                  <th>Haku</th>\r\n                  <th>RegEx</th>\r\n                  <th>Toiminto</th>\r\n                  <th>\r\n                    <div>Palkkalaji (rowType)</div>\r\n                    <div>Alalaji (kind)</div>\r\n                  </th>\r\n                  <th class=\"right\">\r\n                    <div>Hinta/kerroin</div>\r\n                    <div>Määrä</div>\r\n                  </th>\r\n                  <th>Viesti palkkalaskelmaan</th>\r\n                  <th>Kommentti</th>\r\n                  <th>\r\n                    <button type=\"button\" class=\"btn btn-default\" ng-click=\"$rows.showRowTypeSelectionDialog()\">Luo uusi</button>\r\n                  </th>\r\n                </tr>\r\n              </thead>\r\n              <tbody>\r\n                <tr ng-repeat=\"match in $rows.list\">\r\n                  <td ng-if=\"!match.$edit\">{{ match.search }}</td>\r\n                  <td ng-if=\"!match.$edit\">{{ match.searchType }}</td>\r\n                  <td ng-if=\"!match.$edit\">{{ match.type }}</td>\r\n  \r\n                  <td ng-if=\"match.$edit\"><salaxy-input name=\"searh{{ $index }}\" label-type=\"plain\" ng-model=\"match.search\"></salaxy-input></td>\r\n                  <td ng-if=\"match.$edit\"><input type=\"checkbox\" ng-checked=\"match.searchType == 'regExp'\" ng-click=\"match.searchType = (match.searchType != 'regExp' ? 'regExp' : 'string')\"></td>\r\n                  <td ng-if=\"match.$edit\">\r\n                    <salaxy-input-enum options=\"$ctrl.matchTypes\" name=\"type{{ $index }}\" label-type=\"plain\" ng-model=\"match.type\"></salaxy-input-enum>\r\n                  </td>\r\n                  \r\n                  <td>\r\n                    <div>{{ match.rowType }}</div>\r\n                    <div>{{ match.data.kind }}</div>\r\n                  </td>\r\n                  <td class=\"right\">\r\n                    <div>{{ match.price || \"-\" }}</div>\r\n                    <div>{{ match.count || \"-\" }}</div>\r\n                  </td>\r\n                  <td>{{ match.message }}</td>\r\n  \r\n                  <td ng-if=\"!match.$edit\">{{ match.comment }}</td>\r\n                  <td ng-if=\"match.$edit\"><salaxy-input name=\"comment{{ $index }}\" label-type=\"plain\" ng-model=\"match.comment\"></salaxy-input></td>\r\n  \r\n                  <td>\r\n                    <button type=\"button\" class=\"btn btn-default\" ng-disabled=\"!match.rowType\" ng-click=\"match.rowIndex = $index;$rows.showEdit(match)\"><i class=\"bi bi-list-task\" aria-hidden=\"true\"></i></button>\r\n                    <button type=\"button\" class=\"btn btn-primary\" ng-click=\"match.$edit = !match.$edit\"><i class=\"bi bi-pencil-fill\" aria-hidden=\"true\"></i></button>\r\n                    <button type=\"button\" class=\"btn btn-danger\" ng-click=\"$rows.delete(match)\"><i class=\"bi bi-trash-fill\" aria-hidden=\"true\"></i></button>\r\n                  </td>\r\n                </tr>\r\n              </tbody>\r\n            </table>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"rows-tab\">\r\n            <table class=\"table table-sm\">\r\n              <thead>\r\n                <tr>\r\n                  <th></th>\r\n                  <th colspan=\"2\">Lähde</th>\r\n                  <th colspan=\"2\">Palkkaus.fi</th>\r\n                  <th colspan=\"3\"></th>\r\n                </tr>\r\n                <tr>\r\n                  <th>Päivä</th>\r\n                  <th>Henk. nro</th>\r\n                  <th>Rivikoodi</th>\r\n                  <th>Työntekijä</th>\r\n                  <th>Palkkalaji</th>\r\n                  <th>Alalaji</th>\r\n                  <th class=\"right\">Määrä</th>\r\n                  <th class=\"right\">Hinta</th>\r\n                  <th class=\"right\">Kustannusp.</th>\r\n                </tr>\r\n              </thead>\r\n              <tbody>\r\n                <tr ng-repeat=\"row in $ctrl.current.rows\">\r\n                  <td>{{ row.date | sxyDate }}</td>\r\n                  <td>{{ row.srcEmploymentId }}</td>\r\n                  <td>{{ row.srcRowTypeId }}</td>\r\n                  <td>\r\n                    <div ng-if=\"row.employment\">\r\n                      <salaxy-avatar style=\"font-size: 18px;\" avatar=\"row.employment.personalInfo.avatar\"></salaxy-avatar>\r\n                      {{ row.employment.personalInfo.avatar.displayName }}\r\n                    </div>\r\n                    <div ng-if=\"!row.employment\" class=\"text-danger\">{{ row.employmentId || \"Puuttuu!\" }}</div>\r\n                  </td>\r\n                  <td>{{ (\"CalculationRowType.\" + (row.rowType || \"\") | sxyEnum) || \"-\" }}</td>\r\n                  <td>{{ row.data.kind || row.message }}</td>\r\n                  <td class=\"right\">{{ row.count | sxyCount }}</td>\r\n                  <td class=\"right\">{{ row.price ? (row.price | currency) : \"-\" }}</td>\r\n                  <td class=\"right\">{{ row.costCenter }}</td>\r\n                </tr>\r\n              </tbody>\r\n            </table>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"src-tab\">\r\n            <salaxy-json-formatter json=\"$ctrl.getRowTypeMapper()\" key=\"'Source'\"></salaxy-json-formatter>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/payroll/index.html\",`<main class=\"salaxy-content sxytpl-calculations-payroll\">\r\n  <div ng-if=\"$ctrl.newPayrollVersion.show\" class=\"d-none d-md-flex salaxy-payroll-v4 form-horizontal d-flex justify-content-end\">\r\n    <salaxy-input-boolean name=\"newPayrollSwitch\" type=\"switch\" ng-model=\"$ctrl.newPayrollVersionUse\" label=\"SALAXY.NG1.PayrollComponent.newVersion\" label-cols=\"col-7\" label-true=\"on\" label-false=\"off\"></salaxy-input-boolean>\r\n  </div>\r\n  <section class=\"sxytpl-intro d-none d-md-block\" ng-if=\"$ctrl.newPayrollVersion.show\">\r\n    <h3 sxy-text=\"SALAXY.NG1.PayrollComponent.payrollVersions.header\"></h3>\r\n    <p sxy-html=\"SALAXY.NG1.PayrollComponent.payrollVersions.html\"></p>\r\n  </section>\r\n  <section class=\"sxytpl-list\" ng-if=\"$ctrl.newPayrollVersion.use\">\r\n    <salaxy-payroll-details-list  details-url=\"/payroll/details/\" hide-button=\"$ctrl.route.readOnly\" is-read-only-forced=\"$ctrl.route.readOnly\"></salaxy-payroll-details-list>\r\n  </section>\r\n  <section class=\"sxytpl-list\" ng-if=\"!$ctrl.newPayrollVersion.use\">\r\n    <salaxy-payroll-list  details-url=\"/payroll/details/\" hide-button=\"$ctrl.route.readOnly\" is-read-only-forced=\"$ctrl.route.readOnly\"></salaxy-payroll-list>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/reference-objects/details.html\",`<main class=\"salaxy-content sxytpl-reference-object-details\">\r\n  <section>\r\n    <!-- This should be a component -->\r\n    <!--salaxy-reference-object model=\"'url'\"></salaxy-reference-object -->\r\n\r\n    <div class=\"salaxy-component salaxy-reference-object\" ng-controller=\"ReferenceObjectCrudController as $ctrl\" ng-init=\"$ctrl.model='url'\">\r\n      <div ng-if=\"$ctrl.current\">\r\n        <sxy-form open-api=\"salaxy-secure/schemas/v02.json\" type=\"ReferenceObject\" auto-gen=\"false\" debugger=\"false\" model=\"$ctrl.current\">\r\n          <div class=\"col-12\">\r\n            <fieldset>\r\n              <legend>Header</legend>\r\n              <sxy-input  model=\"form.header.status\"></sxy-input>\r\n              <sxy-input model=\"form.header.referenceDate\"></sxy-input>\r\n              <sxy-input model=\"form.header.description\"></sxy-input>\r\n            </fieldset>\r\n            <fieldset>\r\n              <legend>Events</legend>\r\n              <sxy-input model=\"form.events\">\r\n                <form>\r\n                  <fieldset>\r\n                    <legend>Event</legend>\r\n                    <sxy-input model=\"form.name\" ></sxy-input>\r\n                    <sxy-input model=\"form.date\" ></sxy-input>\r\n                    <sxy-input model=\"form.result\" ></sxy-input>\r\n                  </fieldset>\r\n                </form>\r\n              </sxy-input>\r\n            </fieldset>\r\n          </div>\r\n        </sxy-form>\r\n        <div class=\"row\">\r\n          <div class=\"col-12 text-end\">\r\n            <button class=\"btn btn-danger\" ng-click=\"$ctrl.delete($ctrl.current)\">Poista</button>\r\n            <button class=\"btn btn-primary\" ng-click=\"$ctrl.save()\">Tallenna</button>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/reference-objects/index.html\",`<main class=\"salaxy-content sxytpl-reference-object-list\">\r\n  <div class=\"text-end\">\r\n    <a class=\"btn btn-primary\" ng-href=\"#{{$odata.$crudController.getDefaults().detailsUrl}}new\" sxy-text=\"Uusi\"></a>\r\n  </div>\r\n  \r\n  <section>\r\n    <div ng-show=\"$odata.items.length\" >\r\n      <salaxy-odata-table ng-ref=\"$odata\" crud-controller=\"ReferenceObjectCrudController as $crud\">\r\n      </salaxy-odata-table>\r\n    </div>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/reports/absences.html\",`<div ng-controller=\"WorkerAbsencesCrudController as $ctrl\" ng-init=\"$ctrl.testYear=2021;$ctrl.getAbsences()\">\r\n  <h1 class=\"d-print-none\" sxy-text=\"SALAXY.NG1_Pages.Reports.Absences.heading\"></h1>\r\n  <h2 class=\"d-none d-print-block\">{{'SALAXY.NG1_Pages.Reports.Absences.heading' | sxyTranslate}} ({{ $ctrl.reportParams | sxyDateRange }})</h2>\r\n  <div class=\"btn-toolbar d-print-none mb-3 mt-3\" role=\"toolbar\" aria-label=\"Calendar buttons\">\r\n    <div class=\"btn-group\" role=\"group\" aria-label=\"Views\">\r\n      <button type=\"button\" class=\"btn btn-default\" ng-class=\"{ active: !$ctrl.view || $ctrl.reportView == 'calendar' }\" ng-click=\"$ctrl.view = 'calendar'\" sxy-text=\"SALAXY.NG1_Pages.Reports.Absences.calendar\"></button>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-class=\"{ active: $ctrl.view == 'list' }\" ng-click=\"$ctrl.view = 'list'\" sxy-text=\"SALAXY.NG1_Pages.Reports.Absences.list\"></button>\r\n    </div>\r\n    <div class=\"btn-group ms-1\" role=\"group\" aria-label=\"Periods\">\r\n      <button type=\"button\" class=\"btn btn-default\" ng-class=\"{ active: !$ctrl.reportView || $ctrl.reportView == 'thisYear' }\" ng-click=\"$ctrl.reportView = 'thisYear'\" sxy-text=\"SALAXY.NG1_Pages.Reports.Absences.thisYear\"></button>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-class=\"{ active: $ctrl.reportView == 'lastYear' }\" ng-click=\"$ctrl.reportView = 'lastYear'\" sxy-text=\"SALAXY.NG1_Pages.Reports.Absences.lastYear\"></button>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-class=\"{ active: $ctrl.reportView == 'thisMonth' }\" ng-click=\"$ctrl.reportView = 'thisMonth'\" sxy-text=\"SALAXY.NG1_Pages.Reports.Absences.thisMonth\"></button>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-class=\"{ active: $ctrl.reportView == 'lastMonth' }\" ng-click=\"$ctrl.reportView = 'lastMonth'\" sxy-text=\"SALAXY.NG1_Pages.Reports.Absences.lastMonth\"></button>\r\n    </div>\r\n    <div class=\"d-flex ms-1\" aria-label=\"{{'SALAXY.NG1_Pages.Reports.Absences.dates' | sxyTranslate}}\">\r\n        <salaxy-datepicker-popup ng-model=\"$ctrl.reportParams.start\" name=\"start\" label=\"SALAXY.NG1_Pages.Reports.Absences.dates\" label-type=\"inline\"></salaxy-datepicker-popup>\r\n        <salaxy-datepicker-popup ng-model=\"$ctrl.reportParams.end\" name=\"end\" label=\"\" label-type=\"no-label\" class=\"ms-1 \"></salaxy-datepicker-popup>\r\n    </div>\r\n    \r\n    <div class=\"btn-group ms-1\" role=\"group\" aria-label=\"Actions\">\r\n      <button ng-click=\"$ctrl.showAddWorker()\" class=\"btn btn-default\" sxy-text=\"SALAXY.NG1_Pages.Reports.Absences.addWorker\"></button>\r\n    </div>\r\n  </div>\r\n  <salaxy-spinner ng-if=\"!$ctrl.allAbsences\"></salaxy-spinner>\r\n  <div ng-if=\"$ctrl.allAbsences.length === 0\" sxy-text=\"SALAXY.NG1_Pages.Reports.Absences.employeeNoAnsences\"></div>\r\n  <div ng-if=\"$ctrl.allAbsences.length &gt; 0\">\r\n    <salaxy-absence-periods style=\"display: none;\" ng-ref=\"$ctrl.$periodList\" on-commit=\"$ctrl.saveAbsences(parent)\"></salaxy-absence-periods>\r\n    <div ng-if=\"$ctrl.view != 'list'\">\r\n      <salaxy-calendar on-list-select=\"type == 'series' ? $ctrl.showEditDialog(series.data) : null\" data=\"$ctrl.allAbsences\" mode=\"horizontal\" mapper=\"$ctrl.mapToCalendar\" list-controller=\"$ctrl.$periodList\" start=\"$ctrl.reportParams.start\" end=\"$ctrl.reportParams.end\"></salaxy-calendar>\r\n    </div>\r\n    <div ng-if=\"$ctrl.view == 'list'\">\r\n      <table class=\"table\">\r\n        <thead>\r\n          <tr>\r\n            <th colspan=\"2\">\r\n              <span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span>\r\n            </th>\r\n            <th class=\"right\">\r\n              <span sxy-text=\"SALAXY.NG1_Pages.Reports.Absences.first\"></span><br />\r\n              <span sxy-text=\"SALAXY.NG1_Pages.Reports.Absences.latest\"></span>\r\n            </th>\r\n            <th class=\"right\">\r\n              <div sxy-text=\"SALAXY.NG1_Pages.Reports.Absences.absencesPaid\"></div>\r\n              <div sxy-text=\"SALAXY.NG1_Pages.Reports.Absences.absencesUnpaid\"></div>\r\n            </th>\r\n            <th class=\"right\">\r\n              <div sxy-text=\"SALAXY.NG1_Pages.Reports.Absences.absencesHolidayAccrual\"></div>\r\n              <div sxy-text=\"SALAXY.NG1_Pages.Reports.Absences.absencesNoHolidayAccrual\"></div>\r\n            </th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr ng-repeat=\"row in $ctrl.allAbsences\">\r\n            <td class=\"align-middle td-avatar clickable\"  ng-click=\"$ctrl.showEditDialog(row)\">\r\n              <salaxy-avatar avatar=\"row.workerSnapshot\"></salaxy-avatar>\r\n            </td>\r\n            <td class=\"td-name middle clickable\"  ng-click=\"$ctrl.showEditDialog(row)\">\r\n              <div><strong>{{ row.workerSnapshot.displayName }}</strong></div>\r\n              <div>{{ $ctrl.getPeriodCalculation(row, \"length\") }} {{'SALAXY.NG1_Pages.Reports.Absences.absence' | sxyTranslate}}, {{ $ctrl.getPeriodCalculation(row, \"all\") | sxyCount : \"day\" }}</div>\r\n            </td>\r\n            <td class=\"right\">\r\n              <div>{{ $ctrl.getPeriodCalculation(row, \"firstPeriod\") | sxyDateRange }}</div>\r\n              <div>{{ $ctrl.getPeriodCalculation(row, \"lastPeriod\") | sxyDateRange }}</div>\r\n            </td>\r\n            <td class=\"right\">\r\n              <div>{{ $ctrl.getPeriodCalculation(row, \"absencesPaid\") | sxyCount : \"day\" }}</div>\r\n              <div>{{ $ctrl.getPeriodCalculation(row, \"absencesUnpaid\") | sxyCount : \"day\" }}</div>\r\n            </td>\r\n            <td class=\"right\">\r\n              <div>{{ $ctrl.getPeriodCalculation(row, \"absencesHolidayAccrual\") | sxyCount : \"day\" }}</div>\r\n              <div>{{ $ctrl.getPeriodCalculation(row, \"absencesNoHolidayAccrual\") | sxyCount : \"day\" }}</div>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages/reports/accounting-legacy.html\",`<main class=\"salaxy-content sxytpl-reports-accounting\">\r\n  <section class=\"sxytpl-intro\">\r\n    <p class=\"lead\"> {{ 'SALAXY.NG1_Pages.Reports.accountingIntro' | sxyTranslate }}\r\n    </p>\r\n  </section>\r\n  <section class=\"sxytpl-list\">\r\n    <h2>{{ 'SALAXY.NG1_Pages.Reports.accountingMonthly' | sxyTranslate }}</h2>\r\n    <salaxy-report-list report-type=\"'monthlyDetails'\"></salaxy-report-list>\r\n    <salaxy-report-list report-type=\"'monthlyLiikekirjuri'\"></salaxy-report-list>\r\n  </section>\r\n  <section class=\"sxytpl-list\">\r\n    <h2>{{ 'SALAXY.NG1_Pages.Reports.accountingYearly' | sxyTranslate }}</h2>\r\n    <salaxy-report-list report-type=\"'yearlyDetails'\"></salaxy-report-list>\r\n  </section>\r\n  <section class=\"sxytpl-list\">\r\n    <h2>{{ 'SALAXY.NG1_Sitemap.reports.archive' | sxyTranslate }}</h2>\r\n    <a href=\"#/reports/archive-2018\">{{ 'SALAXY.UI_Terms.show' | sxyTranslate }}...</a>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/reports/accounting-row-report.html\",`<main class=\"salaxy-content sxytpl-accounting-row-report\">\r\n  <section style=\"height: calc(100vh - 150px)\">\r\n    <salaxy-accounting-row-report template-id=\"'holidays'\"></salaxy-accounting-row-report>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/reports/ad-hoc-list.html\",`<salaxy-odata-table crud-controller=\"UsecasesCrudController as $crud\" options=\"{ $filter: 'entityType eq \\\\'dataset\\\\'' }\" template-url=\"salaxy-components/odata/lists/UsecasesAdHocReport.html\"></salaxy-odata-table>`);\n\n $templateCache.put(\"salaxy-components/pages/reports/ad-hoc.html\",`<main class=\"salaxy-content sxytpl-reports-ad-hoc\">\r\n  <section>\r\n    <div ng-controller=\"DatasetsCrudController as $ctrl\" ng-init=\"$ctrl.model='url'\">\r\n      <salaxy-spinner ng-if=\"!$ctrl.usecase\"></salaxy-spinner>\r\n      <div ng-if=\"$ctrl.usecase && !$ctrl.usecase.defaultView\" class=\"alert alert-danger\">\r\n        ERROR: This usecase {{ $ctrl.usecase.uri }} does not have user interface (view) defined.\r\n      </div>\r\n      <div ng-if=\"$ctrl.usecase && $ctrl.usecase.defaultView\">\r\n        <ng-include src=\"$ctrl.usecase.defaultView\"></ng-include>\r\n      </div>\r\n    </div>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/reports/archive-2018.html\",`<main class=\"salaxy-content sxytpl-reports-archive-2018\">\r\n  <section class=\"sxytpl-intro\">\r\n    <h2 sxy-text=\"SALAXY.NG1_Pages.Reports.Archive.heading\"></h2>\r\n    <p class=\"lead\" sxy-text=\"SALAXY.NG1_Pages.Reports.Archive.lead\"></p>\r\n  </section>\r\n  <h3 sxy-text=\"SALAXY.NG1_Pages.Reports.Archive.unemploymentInsuranceFund\"></h3>\r\n  <section class=\"sxytpl-list\">\r\n    <div ng-controller=\"ReportsController as $ctrl\" ng-init=\"rptType = 'unemployment'\">\r\n      <salaxy-report-list report-type=\"'unemployment'\"></salaxy-report-list>\r\n    </div>\r\n  </section>\r\n  <h3 sxy-text=\"SALAXY.NG1_Pages.Reports.Archive.taxYearlyNotification\"></h3>\r\n  <section class=\"sxytpl-list\">\r\n    <salaxy-report-list report-type=\"'taxYearly7801'\"></salaxy-report-list>\r\n  </section>\r\n  <h3 sxy-text=\"SALAXY.NG1_Pages.Reports.Archive.taxMonthlyNotification\"></h3>\r\n  <section class=\"sxytpl-list\">\r\n    <salaxy-report-list report-type=\"'taxMonthly4001'\"></salaxy-report-list>\r\n  </section>\r\n  <h3 sxy-text=\"SALAXY.NG1_Pages.Reports.Archive.pension\"></h3>\r\n  <section class=\"sxytpl-list\">\r\n    <salaxy-report-list report-type=\"'insurance'\"></salaxy-report-list>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/reports/calculation-report.html\",`<main class=\"salaxy-content sxytpl-calculation-report\">\r\n  <section style=\"height: calc(100vh - 150px)\">\r\n    <salaxy-calculation-report template-id=\"'incomeTypes'\"></salaxy-calculation-report>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/reports/holiday-pay-report-query.html\",`<main class=\"salaxy-content sxytpl-holiday-pay-report-query\">\r\n  <section>\r\n    <salaxy-holiday-pay-report-query></salaxy-holiday-pay-report-query>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/reports/holiday-report.html\",`<main class=\"salaxy-content sxytpl-holiday-report\">\r\n  <section>\r\n    <salaxy-holiday-report></salaxy-holiday-report>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/reports/holidays.html\",`<div ng-controller=\"HolidayYearCrudController as $ctrl\" ng-init=\"$ctrl.getHolidayYears()\">\r\n  <h1 class=\"d-print-none\" sxy-text=\"SALAXY.NG1_Pages.Reports.Holidays.holidayList\"></h1>\r\n  <h2 class=\"d-none d-print-block\">{{'SALAXY.NG1_Pages.Reports.Holidays.holidayYear' | sxyTranslate}} {{ $ctrl.reportYear }} ({{ $ctrl.reportParams | sxyDateRange }})</h2>\r\n  <div class=\"btn-toolbar d-print-none  mb-3 mt-3\" role=\"toolbar\" aria-label=\"Calendar buttons\">\r\n    <div class=\"btn-group\" role=\"group\" aria-label=\"{{'SALAXY.NG1_Pages.Reports.Holidays.holidayYear' | sxyTranslate}}\">\r\n      <salaxy-form-group name=\"year\" label=\"SALAXY.NG1_Pages.Reports.Holidays.holidayYear\" class=\"me-2\" label-type=\"inline\">\r\n        <select id=\"year\" name=\"year\" ng-model=\"$ctrl.reportYear\" class=\"ms-2 form-select\" ng-change=\"$ctrl.getHolidayYears()\" ng-options=\"item as item for item in $ctrl.reportParams.years\">\r\n        </select>\r\n      </salaxy-form-group>\r\n    </div>\r\n    <div class=\"d-flex ms-1\" role=\"group\" aria-label=\"{{'SALAXY.NG1_Pages.Reports.Holidays.show' | sxyTranslate}}\">\r\n        <salaxy-datepicker-popup ng-model=\"$ctrl.reportParams.start\" name=\"start\" label=\"SALAXY.NG1_Pages.Reports.Holidays.show\" label-type=\"inline\" min-date=\"$ctrl.reportParams.yearStart\" max-date=\"$ctrl.reportParams.yearEnd\"></salaxy-datepicker-popup>\r\n        <salaxy-datepicker-popup ng-model=\"$ctrl.reportParams.end\" name=\"end\" label=\"\" label-type=\"no-label\" label-cols=\"none\" min-date=\"$ctrl.reportParams.yearStart\" max-date=\"$ctrl.reportParams.yearEnd\" class=\"ms-1\"></salaxy-datepicker-popup>\r\n    </div>\r\n    <div class=\"btn-group ms-1\" role=\"group\" aria-label=\"Views\">\r\n      \r\n      <button type=\"button\" class=\"btn btn-default\" ng-class=\"{ active: $ctrl.reportView == 'summerPeriod' }\" ng-click=\"$ctrl.reportView = 'summerPeriod'\" sxy-text=\"SALAXY.NG1_Pages.Reports.Holidays.summerPeriod\"></button>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-class=\"{ active: $ctrl.reportView == 'winterPeriod' }\" ng-click=\"$ctrl.reportView = 'winterPeriod'\" sxy-text=\"SALAXY.NG1_Pages.Reports.Holidays.winterPeriod\"></button>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-class=\"{ active: $ctrl.reportView == 'otherPeriod' }\" ng-click=\"$ctrl.reportView = 'otherPeriod'\" sxy-text=\"Muu\"></button>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-class=\"{ active: $ctrl.reportView == 'list' }\" ng-click=\"$ctrl.reportView = 'list'\" sxy-text=\"SALAXY.NG1_Pages.Reports.Holidays.list\"></button>\r\n      \r\n    </div>\r\n    <div class=\"btn-group ms-1\" role=\"group\" aria-label=\"Actions\">\r\n      <button ng-click=\"$ctrl.showAddWorker()\" class=\"btn btn-default\" sxy-text=\"SALAXY.NG1_Pages.Reports.Holidays.addWorker\"></button>\r\n    </div>\r\n  </div>\r\n  <salaxy-spinner ng-if=\"!$ctrl.allYears\"></salaxy-spinner>\r\n  <div ng-if=\"$ctrl.allYears.length === 0\" sxy-text=\"SALAXY.NG1_Pages.Reports.Holidays.employeeNoHolidays\"></div>\r\n  <div ng-if=\"$ctrl.allYears.length &gt; 0\">\r\n    <salaxy-holiday-year-holidays style=\"display: none;\" ng-ref=\"$ctrl.$holidayList\" on-commit=\"$ctrl.saveYear(parent)\"></salaxy-holiday-year-holidays>\r\n    <div ng-if=\"$ctrl.reportView != 'list'\">\r\n      <salaxy-calendar show-export=\"true\" on-list-select=\"type == 'series' ? $ctrl.showEditDialog(series.data) : null\" data=\"$ctrl.allYears\" mode=\"horizontal\" mapper=\"$ctrl.mapToCalendar\" list-controller=\"$ctrl.$holidayList\" start=\"$ctrl.reportParams.start\" end=\"$ctrl.reportParams.end\"></salaxy-calendar>\r\n    </div>\r\n    <div ng-if=\"$ctrl.reportView == 'list'\">\r\n      <table class=\"table\">\r\n        <thead>\r\n          <tr>\r\n            <th colspan=\"2\"><span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span></th>\r\n            <th sxy-html=\"SALAXY.NG1_Pages.Reports.Holidays.holidayCompensation.html\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1_Pages.Reports.Holidays.year\"></th>\r\n            <th class=\"right\" sxy-html=\"SALAXY.NG1_Pages.Reports.Holidays.planned.html\"></th>\r\n            <th class=\"right\" sxy-html=\"SALAXY.NG1_Pages.Reports.Holidays.summerWinter.html\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1_Pages.Reports.Holidays.endSaldo\"></th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr ng-repeat=\"year in $ctrl.allYears\">\r\n            <td class=\"align-middle td-avatar clickable\" ng-click=\"$ctrl.showEditDialog(year)\">\r\n              <salaxy-avatar avatar=\"year.workerSnapshot\"></salaxy-avatar>\r\n            </td>\r\n            <td class=\"td-workerSnapshot-name clickable\" ng-click=\"$ctrl.showEditDialog(year)\">\r\n              <strong>{{ year.workerSnapshot.displayName }}</strong><br /> {{ \"WageBasis.\" + year.spec.wageBasis | sxyEnum }}<br />\r\n            </td>\r\n            <td>\r\n              {{ \"HolidayCode.\" + year.spec.code | sxyEnum }}\r\n              <span ng-if=\"year.spec.code == 'holidayCompensation'\">({{ year.spec.compensation | sxyCount : 'percent' }})</span>\r\n              <div ng-if=\"year.spec.bonusMethod != 'none'\">\r\n                {{ \"HolidayBonusPaymentMethod.\" + year.spec.bonusMethod | sxyEnum }}\r\n                <span>({{ year.spec.bonus | sxyCount : 'percent' }})</span>\r\n              </div>\r\n            </td>\r\n            <td class=\"right\">{{ year.year }}</td>\r\n            <td class=\"right\">\r\n              {{ $ctrl.getTotalDays(\"all\", year) | sxyCount : 'days' }}<br /> {{ year.leaves.planned.length | sxyCount : 'count' }}\r\n            </td>\r\n            <td class=\"right\">\r\n              {{ $ctrl.getTotalDays(\"summer\", year) | sxyCount : 'days' }}<br /> {{ $ctrl.getTotalDays(\"winter\", year) | sxyCount : 'days' }}\r\n            </td>\r\n            <td class=\"right\">\r\n              {{ year.accrual.endSaldo | sxyCount : 'days' }}\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n      <p>&nbsp;</p>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages/reports/index.html\",`<main class=\"salaxy-content sxytpl-reports-dashboard\">\r\n  <section class=\"sxytpl-intro\">\r\n    <p class=\"lead\">\r\n      {{ 'SALAXY.NG1_Pages.Reports.latestReports' | sxyTranslate }}\r\n    </p>\r\n  </section>\r\n  <section class=\"sxytpl-report-panels\">\r\n    <div class=\"row\">\r\n      <div class=\"col-12 col-sm-6\" ng-if=\"$ctrl.route.getFlag('features', 'salaryReportList')\">\r\n        <salaxy-salary-report-list mode=\"panel\"></salaxy-salary-report-list>\r\n      </div>\r\n      <div class=\"col-12 col-sm-6\" ng-if=\"$ctrl.route.getFlag('features', 'accountingReportList')\">\r\n        <salaxy-accounting-report-list mode=\"panel\"></salaxy-accounting-report-list>\r\n      </div>\r\n      <div class=\"col-12 col-sm-6\" ng-if=\"$ctrl.route.getFlag('features', 'invoiceList') || ('pro' | sxyIsInRole)\">\r\n        <salaxy-invoice-list mode=\"panel\"></salaxy-invoice-list>\r\n      </div>\r\n    </div>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/reports/pay-certificate.html\",`<main class=\"salaxy-content sxytpl-pay-certificate\">\r\n  <section class=\"sxytpl-intro\">\r\n    <p sxy-text=\"SALAXY.NG1_Pages.Reports.PayCertificate.intro.text\"></p>\r\n    <p sxy-text=\"SALAXY.NG1_Pages.Reports.PayCertificate.intro.payCertificateInfo\"></p>\r\n  </section>\r\n  <section>\r\n    <salaxy-pay-certificate></salaxy-pay-certificate>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/reports/pay-stats-report-query.html\",`<main class=\"salaxy-content sxytpl-pay-stats-report-query\">\r\n  <section>\r\n    <salaxy-pay-stats-report-query></salaxy-pay-stats-report-query>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/reports/salary-reports.html\",`<main class=\"salaxy-content sxytpl-salary-reports\">\r\n  <section class=\"sxytpl-list\">\r\n    <salaxy-salary-report-list>\r\n    </salaxy-salary-report-list>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/reports/summary-report-query.html\",`<main class=\"salaxy-content sxytpl-summary-report-query\">\r\n  <section>\r\n    <salaxy-summary-report-query></salaxy-summary-report-query>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/reports/yearly-summary.html\",`<main class=\"salaxy-content sxytpl-reports-yearly-summary\">\r\n  <section class=\"sxytpl-intro\">\r\n    <p class=\"lead\">\r\n      {{ 'SALAXY.NG1_Pages.Reports.yearlySummary' | sxyTranslate }}\r\n    </p>\r\n\r\n  </section>\r\n  <section class=\"sxytpl-list\">\r\n    <h2>{{ 'SALAXY.NG1_Pages.Reports.yearlyTitle' | sxyTranslate }}</h2>\r\n    <salaxy-report-list report-type=\"'yearlyWorkerSummary'\"></salaxy-report-list>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/service-models/current.html\",`<main class=\"salaxy-content sxytpl-service-model-current\">\r\n  <section>\r\n    <h1>TODO: Current service model</h1>\r\n    <p class=\"lead\" sxy-text=\"SALAXY.NG1_Pages.ServiceModels.Current.lead\"></p>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/service-models/details.html\",`<main class=\"salaxy-content sxytpl-service-model-details\">\r\n  <section>\r\n    <salaxy-service-model-details model=\"'url'\"></salaxy-service-model-details>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/service-models/index.html\",`<main class=\"salaxy-content sxytpl-service-model-list\">\r\n  <a class=\"btn btn-primary float-end\" ng-href=\"#{{$odata.$crudController.getDefaults().detailsUrl}}new\" sxy-text=\"SALAXY.NG1_Pages.ServiceModels.addServiceModel\"></a>\r\n  <p class=\"lead\">\r\n    {{'SALAXY.NG1_Pages.ServiceModels.lead' | sxyTranslate}} <a href=\"\">Ota yhteys myyntiimme</a>.\r\n  </p>\r\n  <section>\r\n    <div ng-show=\"$odata.items.length\" class=\"salaxy-component salaxy-service-model-list\">\r\n      <salaxy-odata-table ng-ref=\"$odata\" crud-controller=\"ServiceModelCrudController as $crud\">\r\n      </salaxy-odata-table>\r\n    </div>\r\n    <div ng-if=\"$odata.status == 'loaded' && !$odata.items.length\" class=\"salaxy-placeholder-empty placeholder-md placeholder-default text-center\">\r\n      <a class=\"btn btn-primary\" ng-href=\"#{{$odata.$crudController.getDefaults().detailsUrl}}new\" sxy-text=\"SALAXY.NG1_Pages.ServiceModels.addServiceModel\"></a>\r\n    </div>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/service-models/read-only.html\",`<main class=\"salaxy-content sxytpl-service-model-details\">\r\n  <section>\r\n    <salaxy-service-model-details is-read-only-forced=\"true\" model=\"'url'\"></salaxy-service-model-details>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/settings/account-reset.html\",`<main class=\"salaxy-content sxytpl-settings-account-reset\">\r\n  <section class=\"sxytpl-account-reset\">\r\n    <salaxy-account-reset></salaxy-account-reset>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/settings/accountants.html\",`<main class=\"salaxy-content sxytpl-partners-accountants\">\r\n  <section>\r\n    <div class=\"content settings\">\r\n\r\n      <salaxy-accountant removal-disabled=\"$ctrl.route.node.accountantRemovalDisabled || 'accountantComponent.removalDisabled' | sxyIsInRole\"></salaxy-accountant>\r\n\r\n    </div>\r\n  </section>\r\n  <section sxy-if-role=\"test\">\r\n    <div class=\"row\" ng-controller=\"PartnerController as $partnerCtrl\">\r\n      <div class=\"col-md-6\">\r\n        <div class=\"alert alert-danger\">\r\n          <b>Testiympäristö</b>\r\n          <p>Vaihda tyyli tätä sessiota varten!</p>\r\n          <button id=\"style\" type=\"button\" class=\"btn btn-primary\" ng-click=\"$partnerCtrl.showSwitchCss()\">\r\n            Vaihda tyyli (CDN)\r\n          </button>\r\n          <button id=\"style\" type=\"button\" class=\"btn btn-secondary\" ng-click=\"$partnerCtrl.showSwitchCssDev()\">\r\n            Vaihda tyyli <span class=\"small\">(DEV)</span>\r\n          </button>\r\n          <hr />\r\n          <div>Brand ID: {{ $partnerCtrl.brandId || \"-\" }}</div>\r\n          <div>Skin: {{ $partnerCtrl.skin || \"-\" }}</div>\r\n          <a ng-href=\"{{ $partnerCtrl.getLoginUrl() }}\" target=\"_blank\" class=\"btn btn-default\">Näytä login</a>\r\n          <a ng-href=\"{{ $partnerCtrl.getOnboardingUrl() }}\" target=\"_blank\" class=\"btn btn-default\">Näytä onboarding</a>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/settings/accounting-target-settings.html\",`<main class=\"salaxy-content sxytpl-accounting-targets\">\r\n  <section>\r\n    <salaxy-accounting-settings></salaxy-accounting-settings>\r\n  </section>\r\n  <section>\r\n    <div>\r\n      <salaxy-accountant template-url=\"salaxy-components/settings/AccountantInfo.html\"></salaxy-accountant>\r\n    </div>\r\n  </section>\r\n  <section>\r\n    <salaxy-cost-accounting-settings></salaxy-cost-accounting-settings>\r\n  </section>\r\n  <section>\r\n    <salaxy-holiday-settings></salaxy-holiday-settings>\r\n  </section>\r\n  <section ng-if=\"'bizConfigs' | sxyIsInRole\">\r\n    <salaxy-pay-stats-settings></salaxy-pay-stats-settings>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/settings/authorizations.html\",`<main class=\"salaxy-content sxytpl-settings-certificates settings content\">\r\n  <section class=\"sxytpl-credentials mb-4\">\r\n    <salaxy-credentials></salaxy-credentials>\r\n  </section>\r\n  <section class=\"sxytpl-certificates mb-4\">\r\n    <salaxy-certificates></salaxy-certificates>\r\n  </section>\r\n  <section class=\"sxytpl-authorized-accounts mb-4\">\r\n    <!-- <p class=\"lead\">{{ 'SALAXY.NG1_Pages.Settings.Authorizations.lead' | sxyTranslate}}</p> -->\r\n    <salaxy-authorized-accounts></salaxy-authorized-accounts>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/settings/index.html\",`<main class=\"salaxy-content sxytpl-settings-dashboard\" ng-controller=\"SessionController as $session\">\r\n  <section class=\"sxytpl-settings-panels\">\r\n    <div class=\"row\">\r\n\r\n      <div class=\"col-12 mb-4\" ng-if=\"$ctrl.route.getFlag('features', 'account')\">\r\n        <div class=\"salaxy-odata-card list-card settings-list-card card card-sm card-secondary\">\r\n          <div class=\"card-header\" sxy-text=\"SALAXY.NG1_Pages.Settings.accountTitle\">\r\n\r\n          </div>\r\n          <div class=\"card-body card-content\">\r\n            <div class=\"row table-row\">\r\n\r\n              <div class=\"col-4\">\r\n                <span sxy-text=\"SALAXY.NG1_Pages.Settings.languageLabel\" ps=\":\"></span>\r\n              </div>\r\n\r\n              <div class=\"col-8 text-end\">\r\n                {{(\"Language.\" + $session.session.currentAccount.language | sxyEnum) || \"-\" }}\r\n              </div>\r\n            </div>\r\n\r\n            <div class=\"row\">\r\n              <div class=\"col-md-6\">\r\n                <div class=\"row table-row\">\r\n                  <div class=\"col-12\">\r\n                    <strong sxy-text=\"SALAXY.NG1_Pages.Settings.contactLabel\"></strong>\r\n                  </div>\r\n                </div>\r\n\r\n                <div class=\"row table-row\">\r\n                  <div class=\"col-4\">\r\n                    <span sxy-text=\"SALAXY.NG1.AccountInfoComponent.email\" ps=\":\"></span>\r\n\r\n                  </div>\r\n                  <div class=\"col-8 text-end\">\r\n                    {{ $session.company.contact.email }}\r\n                  </div>\r\n                </div>\r\n                <div class=\"row table-row\">\r\n                  <div class=\"col-4\">\r\n                    <span sxy-text=\"SALAXY.NG1.AccountInfoComponent.phone\" ps=\":\"></span>\r\n\r\n                  </div>\r\n                  <div class=\"col-8 text-end\">\r\n                    {{ $session.company.contact.telephone }}\r\n                  </div>\r\n                </div>\r\n                <div class=\"row table-row\">\r\n                  <div class=\"col-4\">\r\n                    <span sxy-text=\"SALAXY.NG1.AccountInfoComponent.address\" ps=\":\"></span>\r\n\r\n                  </div>\r\n                  <div class=\"col-8 text-end\">\r\n                    {{ $session.company.contact.street }}<br /> {{ $session.company.contact.postalCode }} {{ $session.company.contact.city }}\r\n                  </div>\r\n                </div>\r\n              </div>\r\n              <div class=\"col-md-6\">\r\n                <div class=\"row table-row\">\r\n                  <div class=\"col-12\">\r\n                    <strong sxy-text=\"SALAXY.NG1_Pages.Settings.userLabel\"></strong>\r\n                  </div>\r\n                </div>\r\n\r\n                <div class=\"row table-row\" ng-if=\"$session.session.currentCredential.authenticationMethod != 'salaxy' && $session.session.currentCredential.authenticationMethod != 'x509'\">\r\n                  <div class=\"col-4\">\r\n                    <span sxy-text=\"SALAXY.NG1.UserInfoComponent.email\" ps=\":\"></span>\r\n\r\n                  </div>\r\n                  <div class=\"col-8 text-end\">\r\n\r\n                    {{ $session.session.currentCredential.email }}\r\n                  </div>\r\n                </div>\r\n                <div class=\"row table-row\">\r\n                  <div class=\"col-4\">\r\n                    <span sxy-text=\"SALAXY.NG1.UserInfoComponent.name\" ps=\":\"></span>\r\n                  </div>\r\n                  <div class=\"col-8 text-end\">\r\n                    {{ $session.session.currentCredential.avatar.displayName }}\r\n                  </div>\r\n                </div>\r\n              </div>\r\n            </div>\r\n\r\n          </div>\r\n          <div class=\"card-footer text-center\">\r\n            <a href=\"#/settings/service-settings\" title=\"{{'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-primary\" sxy-text=\"SALAXY.UI_Terms.edit\"></a>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div class=\"col-sm-6 col-12 mb-4\" ng-if=\"$ctrl.route.getFlag('features', 'insurances')\" ng-controller=\"CompanySettingsController as $settings\">\r\n        <div class=\"salaxy-odata-card list-card settings-list-card card card-sm card-secondary\">\r\n          <div class=\"card-header\" sxy-text=\"SALAXY.NG1_Pages.Settings.insurancesTitle\">\r\n\r\n          </div>\r\n          <div class=\"card-body card-content lg-height\">\r\n\r\n            <div class=\"row table-row\">\r\n              <div class=\"col-6\" ng-class=\"$session.session.settings.pensionContracts == '' ? 'col-6' : 'col-12'\">\r\n                <strong sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.pension.titleLong\"></strong>\r\n              </div>\r\n\r\n              <div class=\"col-6 text-end\" ng-if=\"$session.session.settings.pensionContracts == ''\">\r\n                <a href=\"#/settings/payment-settings\" class=\"btn btn-danger btn-xs\" sxy-text=\"SALAXY.NG1_Pages.Settings.insuranceMissing\"></a>\r\n              </div>\r\n            </div>\r\n            <div class=\"row-wrapper\" ng-repeat=\"item in $settings.pensionContracts\" ng-if=\"$settings.isVisibleContract(item, $settings.pensionContracts)\">\r\n              <div class=\"row table-row\">\r\n                <div class=\"col-4\" ps=\":\" sxy-text=\"SALAXY.MODEL.PensionContract.company.title\">\r\n  \r\n                </div>\r\n                <div class=\"col-8 text-end\">\r\n                  {{(\"PensionCompany.\" + item.company | sxyEnum) || '-'}}\r\n                </div>\r\n              </div>\r\n              \r\n              <div class=\"row table-row\">\r\n                <div class=\"col-4\" sxy-text=\"SALAXY.MODEL.PensionContract.contractNumber.title\" ps=\":\">\r\n  \r\n                </div>\r\n                <div class=\"col-8 text-end\">\r\n                  {{item.contractNumber || '-'}}\r\n                </div>\r\n              </div>\r\n            </div>\r\n          \r\n            <div class=\"row-wrapper\" ng-repeat=\"item in $settings.insuranceContracts\" ng-if=\"$settings.isVisibleContract(item, $settings.insuranceContracts)\">\r\n              <div class=\"row table-row\">\r\n                <div class=\"col-6\" ng-class=\"$session.session.settings.insuranceContracts == '' ? 'col-6' : 'col-12'\">\r\n                  <strong sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.insurance.title\"></strong>\r\n                </div>\r\n\r\n                <div class=\"col-6 text-end\" ng-if=\"$session.session.settings.insuranceContracts == ''\">\r\n                  <a href=\"#/settings/payment-settings\" class=\"btn btn-danger btn-xs\" sxy-text=\"SALAXY.NG1_Pages.Settings.insuranceMissing\"></a>\r\n                </div>\r\n              </div>\r\n              <div class=\"row table-row\">\r\n                <div class=\"col-4\" sxy-text=\"SALAXY.MODEL.InsuranceContract.company.title\" ps=\":\">\r\n\r\n                </div>\r\n                <div class=\" col-8 text-end\">\r\n                  {{(\"InsuranceCompany.\" + item.company | sxyEnum) || '-'}}\r\n                </div>\r\n              </div>\r\n              <div class=\"row table-row\">\r\n                <div class=\"col-4\" sxy-text=\"SALAXY.MODEL.InsuranceContract.contractNumber.title\" ps=\":\">\r\n\r\n                </div>\r\n                <div class=\"col-8 text-end\">\r\n                  {{item.contractNumber || '-'}}\r\n                </div>\r\n              </div>\r\n            </div>\r\n          </div>\r\n          <div class=\"card-footer text-center\">\r\n            <a href=\"#/settings/insurances\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-primary\" sxy-text=\"SALAXY.UI_Terms.edit\"></a>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div class=\"col-sm-6 col-12 mb-4\" ng-if=\"$ctrl.route.getFlag('features', 'accountant')\">\r\n        <div class=\"salaxy-odata-card list-card settings-list-card card card-sm card-secondary\">\r\n          <div class=\"card-header\">\r\n            {{'SALAXY.NG1_Pages.Settings.accountantTitle' | sxyTranslate }}\r\n          </div>\r\n          <div class=\"card-body card-content lg-height text-center align-middle\" ng-if=\"!$session.session.settings.partner\">\r\n            <div>\r\n              <h3 sxy-text=\"SALAXY.NG1_Pages.Settings.noAccountant\"></h3>\r\n            </div>\r\n          </div>\r\n          <div class=\"card-body card-content lg-height\" ng-if=\"$session.session.settings.partner\">\r\n            <div class=\"row table-row\">\r\n              <div class=\"col-4\" sxy-text=\"SALAXY.NG1.AccountantComponent.name\" ps=\":\">\r\n              </div>\r\n              <div class=\"col-8 d-flex align-items-center justify-content-end\">\r\n                <salaxy-avatar style=\"font-size: 20px; margin-right: 12px;\" avatar=\"$session.session.settings.partner.info.avatar\"></salaxy-avatar>\r\n                <span>{{ $session.session.settings.partner.info.avatar.displayName}}</span>\r\n              </div>\r\n            </div>\r\n\r\n            <div class=\"row table-row\" ng-if=\"$session.session.settings.partner.info.officialId\">\r\n              <div class=\"col-4\" sxy-text=\"SALAXY.NG1.AccountantComponent.officialId\" ps=\":\"></div>\r\n              <div class=\"col-8 text-end\">{{ $session.session.settings.partner.info.officialId}}</div>\r\n            </div>\r\n            <div class=\"row table-row\" ng-if=\"$session.session.settings.partner.info.email\">\r\n              <div class=\"col-4\" sxy-text=\"SALAXY.NG1.AccountantComponent.email\" ps=\":\"></div>\r\n              <div class=\"col-8 text-end\">{{ $session.session.settings.partner.info.email }}</div>\r\n            </div>\r\n            <div class=\"row table-row\" ng-if=\"$session.session.settings.partner.info.telephone\">\r\n              <div class=\"col-4\" sxy-text=\"SALAXY.NG1.AccountantComponent.phone\" ps=\":\"></div>\r\n              <div class=\"col-8 text-end\">{{ $session.session.settings.partner.info.telephone }}</div>\r\n            </div>\r\n            <div class=\"row table-row\" ng-if=\"$session.session.settings.partner.type=='primaryPartner' || $session.session.settings.partner.type=='pendingPrimaryPartner' || $session.session.settings.partner.type=='unlinkedPrimaryPartner' || $session.session.settings.partner.type=='unlinkedAccountingOnly'\">\r\n              <div class=\"col-4\" sxy-text=\"SALAXY.NG1.AccountantComponent.accountantType\" ps=\":\">\r\n              </div>\r\n              <div class=\"col-8 text-end\">\r\n                <span ng-if=\"$session.session.settings.partner.type=='primaryPartner'\" sxy-text=\"SALAXY.NG1.AccountantComponent.primaryPartner\"></span>\r\n                <span ng-if=\"$session.session.settings.partner.type=='pendingPrimaryPartner'\" sxy-text=\"SALAXY.NG1.AccountantComponent.pendingPrimaryPartner\"></span>\r\n                <span ng-if=\"$session.session.settings.partner.type=='unlinkedPrimaryPartner'\" sxy-text=\"SALAXY.NG1.AccountantComponent.unlinkedPrimaryPartner\"></span>\r\n                <span ng-if=\"$session.session.settings.partner.type=='unlinkedAccountingOnly'\" sxy-text=\"SALAXY.NG1.AccountantComponent.unlinkedAccountingOnly\"></span>\r\n              </div>\r\n            </div>\r\n          </div>\r\n\r\n          <div class=\"card-footer text-center\">\r\n            <a href=\"#/settings/accountants\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-primary\" sxy-text=\"SALAXY.UI_Terms.edit\"></a>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div class=\"col-sm-6 col-12 mb-4\" ng-if=\"$session.session.settings.paymentChannels && $ctrl.route.getFlag('features', 'paymentChannels')\">\r\n        <div class=\"salaxy-odata-card list-card settings-list-card card card-sm card-secondary\">\r\n          <div class=\"card-header\" sxy-text=\"SALAXY.NG1_Pages.Settings.paymentChannelsTitle\">\r\n\r\n          </div>\r\n          <div class=\"card-body card-content lg-height\">\r\n            <div class=\"row table-row\">\r\n              <div class=\"col-6\">\r\n                <strong sxy-text=\"SALAXY.NG1_Pages.Settings.defaultChannelLabel\" ps=\":\"></strong>\r\n              </div>\r\n              <div class=\"col-6 text-end\">\r\n                {{\"PaymentChannel.\" + $session.session.settings.defaultPaymentChannel | sxyEnum}}\r\n              </div>\r\n            </div>\r\n            <div class=\"row table-row\">\r\n              <div class=\"col-12\">\r\n                <strong sxy-text=\"SALAXY.NG1.PaymentChannelSettingsComponent.title\" ps=\":\"></strong>\r\n              </div>\r\n            </div>\r\n            <div class=\"row table-row\" ng-repeat=\"channel in $session.session.settings.paymentChannels\">\r\n\r\n              <div class=\"col-12\">\r\n\r\n                {{\"PaymentChannel.\" + channel | sxyEnum}}<br>\r\n              </div>\r\n            </div>\r\n          </div>\r\n          <div class=\"card-footer text-center\">\r\n            <a href=\"#/settings/payment-channel-settings\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-primary\" sxy-text=\"SALAXY.UI_Terms.edit\"></a>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/settings/insurances.html\",`<main class=\"salaxy-content sxytpl-insurance-settings\">\r\n  <section>\r\n    <salaxy-insurance-settings is-read-only-forced=\"$ctrl.route.readOnly\"></salaxy-insurance-settings>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/settings/integrations.html\",`<main class=\"salaxy-content sxytpl-partners-integrations\">\r\n  <section class=\"sxytpl-intro\">\r\n    <p class=\"lead\">\r\n      {{ 'SALAXY.NG1_Pages.Settings.Integrations.lead' | sxyTranslate }}\r\n    </p>\r\n  </section>\r\n  <section class=\"sxytpl-cards\">\r\n    <div ng-controller=\"AccountAuthorizationController as authCtrl\">\r\n      <div class=\"row align-items-stretch w-100\">\r\n        <div class=\"sxytpl-card col-12 col-sm-4 col-md-4 col-lg-3 m-3\" ng-repeat=\"site in authCtrl.partnerIntegrationSites\">\r\n          <salaxy-auth-card class=\"d-flex h-100\" auth-id=\"site.id\"></salaxy-auth-card>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/settings/ir-delivery-settings.html\",`<main class=\"salaxy-content sxytpl-ir-delivery-settings\">\r\n  <section>\r\n    <salaxy-ir-delivery-settings is-read-only-forced=\"$ctrl.route.readOnly\"></salaxy-ir-delivery-settings>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/settings/open-ai.html\",`<div class=\"content settings\"  ng-controller=\"CompanySettingsController as $ctrl\">\r\n  <div class=\"panel open-ai-settings panel-default\" ng-if=\"$ctrl.current\">\r\n    <div>\r\n      <div class=\"panel-heading icon-panel\">\r\n        <h2 sxy-text=\"OPEN AI\"></h2>\r\n      </div>\r\n      <div class=\"panel-body\">\r\n        <div class=\"row\">\r\n          <ng-form name=\"$openAi\" class=\"form-horizontal\">\r\n            <div>\r\n              <fieldset>\r\n                <legend>API Avain</legend>\r\n                <salaxy-input label=\"Avain\" name=\"key\"\r\n                  ng-model=\"$ctrl.openAiKey\"></salaxy-input>\r\n              </fieldset>\r\n            </div>\r\n          </ng-form>\r\n        </div>\r\n      </div>\r\n      <div class=\"panel-footer\">\r\n        <div class=\"row\">\r\n          <div class=\"col-xs-12 text-right\">\r\n            <button type=\"submit\"\r\n              class=\"btn btn-primary\" ng-click=\"$ctrl.saveOpenAiKey()\">\r\n              <span sxy-text=\"SALAXY.UI_Terms.save\"></span>\r\n            </button>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages/settings/owner-settings.html\",`<salaxy-owner-settings is-read-only-forced=\"$ctrl.route.readOnly\"></salaxy-owner-settings>`);\n\n $templateCache.put(\"salaxy-components/pages/settings/payment-channel-settings.html\",`<main class=\"salaxy-content sxytpl-payment-channel-settings\">\r\n  <section>\r\n    <salaxy-payment-channel-settings></salaxy-payment-channel-settings>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/settings/payment-settings.html\",`<main class=\"salaxy-content sxytpl-payment-settings\">\r\n\r\n  <section>\r\n    <salaxy-payment-settings is-read-only-forced=\"$ctrl.route.readOnly\"></salaxy-payment-settings>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/settings/pro-settings.html\",`<main class=\"salaxy-content sxytpl-pro-settings\">\r\n  <section>\r\n    <salaxy-pro-settings></salaxy-pro-settings>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/settings/records.html\",`<main class=\"salaxy-content sxytpl-settings-records settings content\">\r\n  <section class=\"sxytpl-account-records mb-4\">\r\n    <div class=\"card account-records card-default\">\r\n      <!--div class=\"card-header\">\r\n        <h2>{{'SALAXY.NG1.WorkerDetailsComponent.records.label' | sxyTranslate}}</h2>\r\n      </div-->\r\n      <div class=\"card-body\">\r\n        <div ng-if=\"'person' | sxyIsInRole\" ng-controller=\"PersonAccountController as $person\">\r\n          <salaxy-records ng-if=\"$person.current\" read-only=\"$ctrl.route.readOnly\" api-ctrl=\"$person\" entity-type=\"'account'\"></salaxy-records>\r\n        </div>\r\n        <div ng-if=\"'company' | sxyIsInRole\" ng-controller=\"CompanyAccountController as $company\">\r\n          <salaxy-records ng-if=\"$company.current\" read-only=\"$ctrl.route.readOnly\" api-ctrl=\"$company\" entity-type=\"'account'\"></salaxy-records>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/settings/row-types-settings.html\",`<main class=\"salaxy-content sxytpl-row-types-settings\">\r\n  <section>\r\n    <salaxy-tab-buttons \r\n      current-tab=\"$ctrl.currentTab\"\r\n      options=\"[\r\n        { value: 'builtin', text: 'Tuotteen palkkalajit' },\r\n        { value: 'custom', text: 'Yrityskohtaiset palkkalajit' },\r\n        { value: 'prices', text: 'Oletushinnat' },\r\n        { value: 'copy', text: 'Kopioitavat rivit' },\r\n        { value: 'json', text: 'Debug' }\r\n      ]\"\r\n      tabs-id=\"rowTypesSettings\">\r\n    </salaxy-tab-buttons>\r\n    <div class=\"tab-content\" id=\"tab-content-rowTypesSettings\">\r\n      <div class=\"tab-pane\" id=\"builtin-tab\">\r\n        <p>\r\n          Tuotteen palkkalajit listaa kaikki palkkalajit, jotka on määritetty suoraan tuotteeseen.\r\n          Niitä ei voi muokata. <strong>Klikkaa räätälöi luodaksesi uusi yrityskohtainen palkkalaji.</strong>\r\n        </p>\r\n        <salaxy-row-types-settings mode=\"builtIn\"></salaxy-row-types-settings>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"custom-tab\">\r\n        <p>\r\n          Voit luoda uuden yrityskohtaisen palkkalajin valitsemalla tuotteen palkkalajin ensimmäiseltä välilehdeltä ja klikkaamalla \"räätälöi\".\r\n          <br />\r\n          <strong>HUOM: Tässä versiossa yrityskohtaiset palkkalajit toimivat vain tuntitiedon tuonnissa (esim. Nepton, EASoft).</strong>\r\n          Myöhemmissä versioissa ne tulevat mukaan myös laskuriin.\r\n        </p>\r\n        <div>\r\n          <salaxy-row-types-settings mode=\"custom\"></salaxy-row-types-settings>\r\n        </div>\r\n        <!--div ng-if=\"('bizConfigs' | sxyIsInRole)\" ng-controller=\"TemplateCrudController as $templateCrudCtrl\">\r\n          <button type=\"button\" class=\"btn btn-sm btn-default\"\r\n            ng-click=\"$templateCrudCtrl.selectTemplate()\">\r\n            <i class=\"bi bi-plus\"></i> <span sxy-text=\"Lisää valmiista mallista...\"></span>\r\n          </button>\r\n        </div-->\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"prices-tab\">\r\n        <div class=\"float-end\">\r\n          <button class=\"btn btn-primary\" ng-click=\"$ctrl.$prices.save()\"></span> <span sxy-text=\"SALAXY.UI_Terms.save\"></span></button>\r\n        </div>\r\n        <p style=\"min-height: 24px;\">Hintoja käytetään tällä hetkellä tuntien sisään tuonnissa. Myöhemmissä versioissa oletushintoja käytetään myös laskurissa.</p>\r\n        <salaxy-row-types-settings ng-ref=\"$ctrl.$prices\" mode=\"prices\"></salaxy-row-types-settings>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"copy-tab\">\r\n        <div class=\"float-end\">\r\n          <button class=\"btn btn-primary\" ng-click=\"$ctrl.$copyRows.save()\"></span> <span sxy-text=\"SALAXY.UI_Terms.save\"></span></button>\r\n        </div>\r\n        <p style=\"min-height: 24px;\">Rivit päivitetään laskelmalle työsuhteen päivityksen yhteydessä.</p>\r\n        <salaxy-row-types-settings ng-ref=\"$ctrl.$copyRows\" mode=\"copy\" ng-if=\"$ctrl.currentTab == 'copy'\"></salaxy-row-types-settings>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"json-tab\">\r\n        <salaxy-row-types-settings mode=\"debugger\"></salaxy-row-types-settings>\r\n      </div>\r\n    </div>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/settings/service-settings.html\",`<main class=\"salaxy-content sxytpl-settings-service-settings settings content\">\r\n  <section class=\"sxytpl-language-selection mb-4\">\r\n    <salaxy-language-selector></salaxy-language-selector>\r\n  </section>\r\n  <section class=\"sxytpl-account-info mb-4\">\r\n    <div class=\"card account-info card-secondary\">\r\n      <div class=\"card-header\">\r\n        <h2>{{'SALAXY.NG1_Pages.Settings.ServiceSettings.heading' | sxyTranslate}}</h2>\r\n      </div>\r\n      <div class=\"card-body\">\r\n        <salaxy-account-info></salaxy-account-info>\r\n      </div>\r\n    </div>\r\n  </section>\r\n  <section class=\"sxytpl-user-info mb-4\" salaxy-if-role=\"test\">\r\n    <div class=\"card user-info card-default\">\r\n      <div class=\"card-header\">\r\n        <h2>{{'SALAXY.NG1.UserInfoComponent.panelTitle' | sxyTranslate}} (TEST ONLY)</h2>\r\n      </div>\r\n      <div class=\"card-body\">\r\n        <salaxy-user-info></salaxy-user-info>\r\n      </div>\r\n    </div>\r\n  </section>\r\n  <section class=\"sxytpl-account-records mb-4\">\r\n    <div class=\"card account-records card-default\">\r\n      <div class=\"card-header\">\r\n        <h2>{{'SALAXY.NG1.WorkerDetailsComponent.records.label' | sxyTranslate}}</h2>\r\n      </div>\r\n      <div class=\"card-body\">\r\n        <div ng-if=\"'person' | sxyIsInRole\" ng-controller=\"PersonAccountController as $person\">\r\n          <salaxy-records ng-if=\"$person.current\" read-only=\"$ctrl.route.readOnly\" api-ctrl=\"$person\" entity-type=\"'account'\"></salaxy-records>\r\n        </div>\r\n        <div ng-if=\"'company' | sxyIsInRole\" ng-controller=\"CompanyAccountController as $company\">\r\n          <salaxy-records ng-if=\"$company.current\" read-only=\"$ctrl.route.readOnly\" api-ctrl=\"$company\" entity-type=\"'account'\"></salaxy-records>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/settings/signing-cancel.html\",`<div class=\"text-center\" style=\"height: 100vh; padding-top: 30vh;\">\r\n  <div>\r\n    <h1>Allekirjoitus peruttu / Digital signature canceled / \r\n      Digital signatur avbröts</h1>\r\n    <button type=\"button\" class=\"btn btn-primary\" onclick=\"closePopup()\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n  </div>\r\n</div>\r\n`);\n\n $templateCache.put(\"salaxy-components/pages/settings/signing-new.html\",`<main class=\"salaxy-content sxytpl-settings-signing\">\r\n  <h1>Signing tester</h1>\r\n  <salaxy-signing ng-ref=\"$ctrl.$signing\" show-in-popup=\"true\" show-always=\"true\"></salaxy-signing>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages/settings/signing-success.html\",`<div class=\"text-center\" style=\"height: 100vh; padding-top: 30vh;\">\r\n  <div>\r\n    <h1 sxy-text=\"SALAXY.NG1_Pages.Settings.SigningSuccess.success\"></h1>\r\n    <button type=\"button\" class=\"btn btn-primary\" onclick=\"closePopup()\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n  </div>\r\n</div>\r\n`);\n\n $templateCache.put(\"salaxy-components/pages/settings/signing.html\",`<div ng-cloak ng-controller=\"NaviController as $ctrl\">\r\n  <salaxy-spinner ng-if=\"$ctrl.showFullPageLoader\" full-screen=\"true\" heading=\"SALAXY.UI_Terms.loading\">\r\n  </salaxy-spinner>\r\n  <div class=\"salaxy-component\" ng-if=\"!$ctrl.showFullPageLoader\">\r\n    <div ng-controller=\"CompanyOnboardingController as $onBoarding\">\r\n      <div ng-if=\"'auth' | sxyIsInRole\" ng-init=\"$onBoarding.launchSigningWizard()\"></div>\r\n      <div class=\"text-center\" style=\"margin-top:100px;\">\r\n        <a onClick=\"window.opener.postMessage({ action: 'refresh' },'*');window.close()\" href=\"#\" sxy-text=\"SALAXY.UI_Terms.close\"></a>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>\r\n\r\n   `);\n\n $templateCache.put(\"salaxy-components/pages/settings/translate.html\",`<salaxy-ui-translator></salaxy-ui-translator>`);\n\n $templateCache.put(\"salaxy-components/pages/taxcards/details.html\",`<div class=\"container\">\r\n  <h2>{{'SALAXY.NG1_Pages.Taxcards.Details.heading' | sxyTranslate}}: {{ $ctrl.$taxcardCtrl.current.worker.displayName }}</h2>\r\n  <p class=\"lead\" ng-if=\"$ctrl.$taxcardCtrl.current\">\r\n    <strong>{{ \"TaxcardKind.\" + $ctrl.$taxcardCtrl.current.card.kind | sxyEnum }}, {{ $ctrl.$taxcardCtrl.current.card.validity | sxyDateRange }}</strong>. {{'SALAXY.NG1_Pages.Taxcards.Details.heading' | sxyTranslate}}\r\n  </p>\r\n  <salaxy-tab-buttons\r\n    current-tab=\"$ctrl.currentTab\"\r\n    options=\"[\r\n      { value: 'overview', text: 'SALAXY.NG1_Pages.Taxcards.Details.overview' },\r\n      { value: 'pro', text: 'SALAXY.NG1_Pages.Taxcards.Details.editing' },\r\n      { value: 'alltaxcards', text: 'SALAXY.NG1_Pages.Taxcards.Details.allTaxcards' },\r\n      { value: 'debug', text: 'Json / debug' }\r\n    ]\"\r\n    tabs-id=\"taxcardsDetails\">\r\n  </salaxy-tab-buttons>\r\n  <div class=\"tab-content\" id=\"tab-content-taxcardsDetails\">\r\n    <div class=\"tab-pane\" id=\"overview-tab\">\r\n      <salaxy-spinner heading=\"SALAXY.UI_Terms.loading\" ng-if=\"$ctrl.$taxcardCtrl.isLoading\"></salaxy-spinner>\r\n        <div ng-if=\"$ctrl.$taxcardCtrl.current && $ctrl.$taxcardCtrl.currentId\">\r\n          <salaxy-taxcard-details model=\"$ctrl.$taxcardCtrl.current\" hide-buttons=\"true\"></salaxy-taxcard-details>\r\n          <div class=\"text-center\" ng-if=\"!$ctrl.$taxcardCtrl.getTaxcardDownloadUrl()\" sxy-text=\"SALAXY.NG1_Pages.Taxcards.Details.noAttachment\"></div>\r\n          <a ng-if=\"$ctrl.$taxcardCtrl.getTaxcardDownloadUrl()\" ng-href=\"{{$ctrl.$taxcardCtrl.getTaxcardDownloadUrl()}}\" target=\"_blank\" class=\"btn btn-xs btn-primary float-end\" sxy-text=\"SALAXY.NG1_Pages.Taxcards.Details.download\">Download</a>\r\n          <div ng-if=\"$ctrl.$taxcardCtrl.getTaxcardPreviewUrl()\" class=\"document-preview text-center\">\r\n            <img ng-src=\"{{ $ctrl.$taxcardCtrl.getTaxcardPreviewUrl() }}\" class=\"img-responsive\" style=\"display: inline;\" />\r\n          </div>\r\n        </div>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"pro-tab\">\r\n      <salaxy-taxcard-details model=\"'url'\" list-url=\"/taxcards\" ng-ref=\"$ctrl.$taxcardCtrl\" mode=\"pro\"></salaxy-taxcard-details>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"alltaxcards-tab\">\r\n      <div ng-if=\"$ctrl.currentTab == 'alltaxcards'\">\r\n        <salaxy-employment-taxcards employment-id=\"$ctrl.$taxcardCtrl.current.employmentId\" ng-ref=\"$ctrl.$allTaxcardsCtrl\" mode=\"list\"></salaxy-employment-taxcards>\r\n      </div>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"debug-tab\">\r\n      <p class=\"clearfix\" sxy-if-role=\"test\">\r\n        <button type=\"button\" class=\"btn btn-danger float-end\" ng-click=\"$ctrl.$taxcardCtrl.delete()\" sxy-text=\"SALAXY.NG1_Pages.Taxcards.Details.deleteButton\">Poista (test)</button> {{'SALAXY.NG1_Pages.Taxcards.Details.deleteButtonInfo' | sxyTranslate}}\r\n      </p>\r\n      <salaxy-json-formatter open=\"1\" json=\"$ctrl.$taxcardCtrl.current\"></salaxy-json-formatter>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages/taxcards/index.html\",`<div class=\"container\">\r\n  <h2 sxy-text=\"SALAXY.NG1_Pages.Taxcards.heading\"></h2>\r\n  <p class=\"lead\" sxy-if-role=\"!worker\" sxy-html=\"SALAXY.NG1_Pages.Taxcards.lead.noWorkerHtml\"></p>\r\n  <p class=\"lead\" sxy-if-role=\"worker\" sxy-html=\"SALAXY.NG1_Pages.Taxcards.lead.workerHtml\"></p>\r\n  <salaxy-odata-table crud-controller=\"TaxcardCrudController as $crud\" crud-bindings=\"{ detailsUrl: '/taxcards/details/'}\"></salaxy-odata-table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages/templates/details.html\",`<main class=\"salaxy-content sxytpl-template-details\">\r\n  <section>\r\n    <div class=\"salaxy-component salaxy-template-details\" ng-controller=\"TemplateCrudController as $ctrl\" ng-init=\"$ctrl.model='url'\">\r\n      <div ng-if=\"$ctrl.current\">\r\n        <sxy-form open-api=\"salaxy-secure/schemas/v02.json\" type=\"Template\" auto-gen=\"false\" debugger=\"false\" model=\"$ctrl.current\">\r\n          <div class=\"col-12\">\r\n            <fieldset>\r\n              <legend>Perustiedot</legend>\r\n              <sxy-input  model=\"form.name\"></sxy-input>\r\n              <sxy-input model=\"form.description\"></sxy-input>\r\n            </fieldset>\r\n          </div>\r\n        </sxy-form>\r\n        <div class=\"row\">\r\n          <div class=\"col-12 text-end\">\r\n            <button class=\"btn btn-danger\" ng-click=\"$ctrl.delete($ctrl.current)\">Poista</button>\r\n            <button class=\"btn btn-primary\" ng-click=\"$ctrl.save()\">Tallenna</button>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/templates/index.html\",`<main class=\"salaxy-content sxytpl-template-list\">\r\n  <div class=\"text-end\">\r\n    <a class=\"btn btn-primary\" ng-href=\"#{{$odata.$crudController.getDefaults().detailsUrl}}new\" sxy-text=\"Uusi\"></a>\r\n  </div>\r\n  \r\n  <section>\r\n    <div ng-show=\"$odata.items.length\" class=\"salaxy-component salaxy-template-list\">\r\n      <salaxy-odata-table ng-ref=\"$odata\" crud-controller=\"TemplateCrudController as $crud\">\r\n      </salaxy-odata-table>\r\n    </div>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/test/account-reset.html\",`<main class=\"salaxy-content sxytpl-settings-account-reset\">\r\n  <section class=\"sxytpl-account-reset\">\r\n    <salaxy-account-reset></salaxy-account-reset>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/test/markdown.html\",`<main class=\"salaxy-content sxytpl-test-markdown\">\r\n  <section class=\"sxytpl-test-markdown\">\r\n    <div ng-init=\"test = { 'text': 'tekstiä', 'title': 'Titteli', 'ro': true, 're': false }\">\r\n      <salaxy-input-boolean name=\"ro\" label=\"Read Only\" ng-model=\"test.ro\"></salaxy-input-boolean>\r\n      <salaxy-input-boolean name=\"req\" label=\"Require\" ng-model=\"test.re\"></salaxy-input-boolean>\r\n      <salaxy-input name=\"txt2\" label=\"Text 2\" ng-model=\"test.text\"></salaxy-input>\r\n      <form name=\"markdownTest\" ng-readonly=\"test.ro\" class=\"form-horizontal\">\r\n        <salaxy-input name=\"title\" label=\"Titteli\" require=\"test.re\" ng-model=\"test.title\"></salaxy-input>\r\n        <pre>{{ test.text | json}}</pre>\r\n        <salaxy-input-markdown name=\"text\" label=\"Sisältö\" require=\"test.re\" ng-model=\"test.text\"></salaxy-input-markdown>\r\n      </form>\r\n    </div>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/test/smoke.html\",`<main class=\"salaxy-content sxytpl-test-smoke\">\r\n  <section class=\"sxytpl-test-smoke\">\r\n    <h1>Salaxy tester page</h1>\r\n      <p class=\"lead\">\r\n        This page tests whether <code>@salaxy</code> functionality is working.\r\n        <br />\r\n        <a href=\"/ng1/\">Go to AngularJS Components</a>\r\n      </p>\r\n      <fieldset>\r\n        <legend>AngularJS</legend>\r\n        <p>Expressions: 1 + 2 = {{ 1 + 2 }} <i>(result should be \"3\")</i></p>\r\n        <p>\r\n          Ng-if: <span style=\"background-color: red; color: white;\" ng-if=\"false\">FAILURE</span>\r\n          <i>(should NOT show text \"failure\" in red background).</i>\r\n        </p>\r\n        <p>\r\n          Directive (ng-style): <span style=\"background-color: red; color: white;\" ng-style=\"{ 'background-color': 'green' }\">This text should be in GREEN backgroung</span>\r\n        </p>\r\n      </fieldset>\r\n      <fieldset>\r\n        <legend>Salaxy styles (LESS)</legend>\r\n        <p>The following buttons should be in Bootstrap colors:</p>\r\n        <div class=\"btn-toolbar\">\r\n          <button type=\"button\" class=\"btn btn-default\">Default</button>\r\n          <button type=\"button\" class=\"btn btn-primary\">Primary</button>\r\n          <a href=\"\" class=\"btn btn-success\">Success a-href</a>\r\n          <button type=\"button\" class=\"btn btn-info\">Info</button>\r\n          <a href=\"\" class=\"btn btn-warning\">Warning a-href</a>\r\n          <button type=\"button\" class=\"btn btn-danger\">Danger</button>\r\n          <button type=\"button\" class=\"btn btn-link\">Link</button>\r\n        </div>\r\n        <p style=\"margin-top: 10px;\">...if this is not the case, rest of the tests may be difficult to read (no red / green etc.)</p>\r\n      </fieldset>\r\n      <p style=\"background-color: red; color: white; margin-top: 10px;\" ng-if=\"false\">\r\n        FAILURE: Angular not available: Rest of tests will not show!\r\n      </p>\r\n      <salaxy-smoke-test mode=\"core\"></salaxy-smoke-test>\r\n      <salaxy-smoke-test mode=\"reports\"></salaxy-smoke-test>\r\n      <salaxy-smoke-test mode=\"ng1\"></salaxy-smoke-test>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/usecases/details.html\",`<main class=\"salaxy-content sxytpl-usecase-details\">\r\n  <section>\r\n    <salaxy-usecase-details model=\"'url'\"></salaxy-usecase-details>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/usecases/index.html\",`<main class=\"salaxy-content sxytpl-usecase-list\">\r\n  <section>\r\n    <a ng-href=\"#{{$ctrl.$odata.$crudController.getDefaults().detailsUrl}}new\" class=\"btn btn-primary float-end\" sxy-text=\"SALAXY.NG1_Pages.Usecases.createNewUsecase\"></a>\r\n    <h1>{{'SALAXY.NG1_Pages.Usecases.usecase' | sxyTranslate}}<span class=\"badge bg-primary\">BETA</span></h1>\r\n    <p class=\"lead\" sxy-text=\"SALAXY.NG1_Pages.Usecases.lead\"></p>\r\n    <div class=\"btn-toolbar\">\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.$odata.setFilter(null)\">Näytä kaikki</button>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.$odata.setFilter('entityType', 'calculation')\">Laskelmat</button>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.$odata.setFilter('entityType', 'dataset')\">Dataset</button>\r\n    </div>\r\n    <salaxy-odata-table crud-controller=\"UsecasesCrudController as $crud\" ng-ref=\"$ctrl.$odata\"></salaxy-odata-table>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/workers/details.html\",`<main class=\"salaxy-content sxytpl-workers-details\">\r\n  <section>\r\n    <salaxy-worker-details model=\"'url'\" is-read-only-forced=\"$ctrl.route.readOnly\" hide-buttons=\"$ctrl.route.readOnly\"></salaxy-worker-details>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/workers/import-workers.html\",`<main class=\"salaxy-content\">\r\n  <section>\r\n    <!-- Forcing isFullWidth  -->\r\n    <div style=\"display: none;\" ng-init=\"$ctrl.current.isFullWidth = true\"></div>\r\n    <salaxy-tab-buttons\r\n      current-tab=\"$ctrl.currentTab\"\r\n      options=\"[\r\n        { value: 'default', text: 'Työntekijöiden tuonti' },\r\n        { value: 'list', text: 'Työntekijät' },\r\n      ]\"\r\n      tabs-id=\"importWorkers\">\r\n    </salaxy-tab-buttons>\r\n    <div class=\"tab-content\" id=\"tab-content-importWorkers\">\r\n      <div class=\"tab-pane\" id=\"default-tab\">\r\n        <salaxy-worker-import></salaxy-worker-import>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"list-tab\">\r\n        <salaxy-employment-list show-toolbar=\"true\" read-only=\"$ctrl.route.readOnly\"></salaxy-employment-list>\r\n      </div>\r\n    </div>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/workers/index.html\",`<main class=\"salaxy-content sxytpl-workers-list\">\r\n  <section>\r\n    <salaxy-employment-list show-toolbar=\"true\" read-only=\"$ctrl.route.readOnly\" ng-ref=\"$odata\"></salaxy-employment-list>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/workers/taxcards.html\",`<main class=\"salaxy-content sxytpl-workers-taxcardslist\">\r\n  <section class=\"sxytpl-intro\">\r\n    <p class=\"lead\" sxy-text=\"SALAXY.NG1_Pages.Workers.Taxcards.lead\"></p>\r\n  </section>\r\n  <section class=\"sxytpl-list\">\r\n    <salaxy-tax-cards-list></salaxy-tax-cards-list>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages/worktime-imports/index.html\",`<main class=\"salaxy-content sxytpl-usecase-list\">\r\n  <section ng-controller=\"ImportStagingController as $ctrl\">\r\n    <div ng-if=\"$ctrl.isSupported\">\r\n      <salaxy-import-staging></salaxy-import-staging>\r\n    </div>\r\n    <div ng-if=\"!$ctrl.isSupported\" class=\"container\">\r\n      <h1>Työajan tuonti ei käytössä</h1>\r\n      <p class=\"lead\">\r\n        Työajan tuonti ei ole käytössä tälle asiakastilille.\r\n        Ominaisuus on käytössä ensimmäisillä kumppaneilla.\r\n        Kysy asiakaspalvelusta miten voit ottaa tuonnin käyttöön.\r\n      </p>\r\n      <p>\r\n        <strong>HUOM:</strong>\r\n        Jos tiedossasi on jo organisaatiosi Staging-palvelimen osoite\r\n        ,<a href=\"#/settings/pro-settings\">voit määrittää sen asetuksissa</a> => Välilehti   \"Muut\".\r\n      </p>\r\n    </div>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/account/authorizations.html\",`<main class=\"salaxy-content sxytpl-settings-certificates settings content\">\r\n  <section class=\"sxytpl-credentials\">\r\n    <salaxy-credentials></salaxy-credentials>\r\n  </section>\r\n  <section class=\"sxytpl-certificates\">\r\n    <salaxy-certificates></salaxy-certificates>\r\n  </section>\r\n  <section class=\"sxytpl-authorized-accounts\">\r\n    <salaxy-authorized-accounts></salaxy-authorized-accounts>\r\n  </section>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/account/index.html\",`<salaxy-account-details-person></salaxy-account-details-person>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/archive/employer-archive.html\",`<div>\r\n  <p class=\"lead\" sxy-html=\"SALAXY.NG1_PagesPersonal.employerArchive.intro.html\"></p>\r\n  <ul>\r\n    <li><a href=\"#/archive/employer-paid\" sxy-text=\"SALAXY.NG1_Sitemap.personalWeb.employerArchive.employerPaid\"></a></li>\r\n    <li><a href=\"#/archive/employer-report\" sxy-text=\"SALAXY.NG1_Sitemap.personalWeb.employerArchive.employerReport\"></a></li>\r\n    <li><a href=\"#/household-years/active\" sxy-text=\"SALAXY.NG1_Sitemap.personalWeb.employerArchive.householdYears.main\"></a></li>\r\n  </ul>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/archive/employer-paid.html\",`<salaxy-calc-list category=\"paid\" read-only=\"true\"></salaxy-calc-list>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/archive/employer-report.html\",`<salaxy-employer-report></salaxy-employer-report>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/archive/household-deduction-report.html\",`<div>\r\n  <salaxy-household-deduction-report></salaxy-household-deduction-report>\r\n</div>\r\n`);\n\n $templateCache.put(\"salaxy-components/pages-personal/archive/index.html\",`<div class=\"embed loader\" salaxy-if-role=\"auth\">\r\n  <salaxy-spinner full-screen=\"true\" id=\"iFrameLoader\" heading=\"Ladataan tietoja arkistosta...\"></salaxy-spinner>\r\n  <iframe src=\"/Yearly\" onload=\"document.getElementById('iFrameLoader').style.display = 'none'\"></iframe>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/archive/worker-report.html\",`<salaxy-worker-report></salaxy-worker-report>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/calc/details.html\",`<div class=\"container-fixed\">\r\n  <salaxy-calc ng-ref=\"$calc\" model=\"'url'\" ng-hide=\"$calc.currentCalc.workflow.status == 'paymentStarted' || $calc.currentCalc.workflow.status == 'paymentSucceeded'\"></salaxy-calc>\r\n  <div class=\"light-bg\" ng-if=\"$calc.currentCalc.workflow.status == 'paymentStarted' || $calc.currentCalc.workflow.status == 'paymentSucceeded'\">\r\n    <salaxy-calc-reports calcs=\"[$calc.currentCalc]\" report-type=\"'salarySlip'\"></salaxy-calc-reports>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/calc/draft.html\",`<salaxy-action-button sxy-if-role=\"!household\" action=\"'newCalc'\" label=\"SALAXY.NG1.ActionButtonComponent.newCalculation\" button-class=\"btn-primary mb-2 hidden-xxs\"></salaxy-action-button>\r\n<salaxy-calc-list category=\"draft\" class=\"worker-drafts\" read-only=\"'household' | sxyIsInRole\"></salaxy-calc-list>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/calc/error.html\",`<salaxy-calc-list category=\"error\"></salaxy-calc-list>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/calc/index.html\",`<div class=\"row d-sm-none d-block\">\r\n  <div class=\"col-xs-12\" ng-if=\"!$ctrl.hideButton\">\r\n    <div style=\"margin-bottom:15px;\">\r\n      <salaxy-action-button action=\"'newCalc'\" label=\"Luo uusi palkkalaskelma\"></salaxy-action-button>\r\n    </div>\r\n  </div>\r\n</div>\r\n<div class=\"row\">\r\n  <div class=\"col-sm-6 col-xs-12 mb-4 mb-sm-0\">\r\n    <salaxy-calc-list category=\"received\" mode=\"panel\" limit-to=\"5\" read-only=\"'household' | sxyIsInRole\"></salaxy-calc-list>\r\n  </div>\r\n  <div class=\"col-sm-6 col-xs-12\">\r\n    <salaxy-odata-table url=\"/v03/api/calculations/category/all\" crud-controller=\"CalculationCrudController as $crud\" options=\"{$top: 5, $filter: 'status eq \\\\'workerRequested\\\\' or status eq \\\\'workerRequestAccepted\\\\' or status eq \\\\'workerRequestDeclined\\\\' or status eq \\\\'draft\\\\'', $orderby:  'createdAt desc'}\"\r\n      template-url=\"salaxy-components/odata/lists/CalculationsPanel.html\" data=\"{ category: 'sentAndDraft' }\">\r\n    </salaxy-odata-table>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/calc/paid-household.html\",`<salaxy-action-button action=\"'newCalc'\" label=\"SALAXY.NG1.ActionButtonComponent.newCalculation\" button-class=\"btn-primary mb-2 hidden-xxs\" sxy-if-role=\"!household\"></salaxy-action-button>\r\n<div>\r\n  <salaxy-calc-list category=\"paid\" read-only=\"true\"></salaxy-calc-list>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/calc/paid-worker.html\",`<salaxy-action-button action=\"'newCalc'\" label=\"SALAXY.NG1.ActionButtonComponent.newCalculation\" button-class=\"btn-primary mb-2 hidden-xxs\" sxy-if-role=\"!household\"></salaxy-action-button>\r\n<div>\r\n  <salaxy-calc-list category=\"received\"></salaxy-calc-list>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/calc/paid.html\",`<salaxy-action-button action=\"'newCalc'\" label=\"SALAXY.NG1.ActionButtonComponent.newCalculation\" button-class=\"btn-primary mb-2 hidden-xxs\"></salaxy-action-button>\r\n<salaxy-calc-list category=\"received\"></salaxy-calc-list>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/calc/sent.html\",`<p class=\"lead\">\r\n  Olet lähettänyt nämä palkkalaskelmat työnantajalle maksettavaksi.\r\n</p>\r\n<salaxy-action-button action=\"'newCalc'\" label=\"SALAXY.NG1.ActionButtonComponent.newCalculation\" button-class=\"btn-primary mb-2 hidden-xxs\" sxy-if-role=\"!household\"></salaxy-action-button>\r\n<salaxy-calc-list category=\"sent\"></salaxy-calc-list>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/calc/shared.html\",`<salaxy-calc-list category=\"shared\" read-only=\"true\"></salaxy-calc-list>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/calc/sharing.html\",`<salaxy-calc-sharing model=\"'url'\"></salaxy-calc-sharing>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/employers/index.html\",`<!--\r\n  This is currently in test only and Palkkamylly\r\n  TODO: Move component to Palkkamylly and remove from NG1 (may be recreated in Omapalkka)\r\n-->\r\n<salaxy-employer-list></salaxy-employer-list>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/home/error404.html\",`<div class=\"alert alert-danger\">\r\n  <span sxy-text=\"SALAXY.NG1_PagesPersonal.error404\"></span><br />\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/home/index.html\",`<div ng-controller=\"WelcomeController as $welcomeCtrl\">\r\n\r\n  <div sxy-if-role=\"anon\" class=\"alert alert-danger\" sxy-html=\"SALAXY.NG1_PagesPersonal.index.alert.anon.html\"></div>\r\n  <div sxy-if-role=\"company\" class=\"alert alert-danger\" sxy-html=\"SALAXY.NG1_PagesPersonal.index.alert.company.html\"></div>\r\n  <div sxy-if-role=\"person\">\r\n    <div class=\"salaxy-component salaxy-component-welcome\">\r\n      <div class=\"\" ng-if=\"!$welcomeCtrl.workerDataNew.timeline\">\r\n        <salaxy-spinner></salaxy-spinner>\r\n      </div>\r\n\r\n      <div class=\"timeline my-5 mx-auto px-2\">\r\n        <div ng-if=\"$welcomeCtrl.hasSystemAlert\">\r\n          <div>\r\n            <div class=\"salaxy-welcome-system-alert alert-has-system-alert\" ng-bind-html=\"$welcomeCtrl.systemAlertHtml\"></div>\r\n          </div>\r\n        </div>\r\n        <div ng-if=\"$welcomeCtrl.workerDataNew.timeline\" class=\"d-sm-none d-block timeline-topbar\">\r\n          <div class=\"row mb-3\">\r\n            <div class=\"col-6\">\r\n              <salaxy-action-button action=\"'newTaxcard'\" label=\"SALAXY.NG1.WelcomeComponent.taxcard\" button-class=\"btn-labeled-right btn-primary btn-block\"></salaxy-action-button>\r\n            </div>\r\n            <div class=\"col-6\">\r\n              <salaxy-action-button action=\"'newCalc'\" label=\"SALAXY.NG1.ActionButtonComponent.newCalculationAlt\" button-class=\"btn-labeled-right btn-secondary btn-block\"></salaxy-action-button>\r\n            </div>\r\n          </div>\r\n          <div class=\"list-panel panel panel-sm panel-secondary panel-own-taxcard panel-secondary\">\r\n            <div ng-show=\"$welcomeCtrl.workerUI.taxCardAdded\" class=\"salaxy-component table-responsive panel-content md-height\">\r\n              <div class=\"panel-content md-height\">\r\n                <div class=\"panel-body no-vertical-padding salaxy-tax-card-chart chart-container\" style=\"max-height:216px; padding-top:0; padding-bottom:0; padding-left:5px;padding-right:5px;\">               \r\n                  <salaxy-chart ng-if=\"$welcomeCtrl.taxcardChartData.limits.hasLimit == true\" custom-height=\"210px\" config=\"$welcomeCtrl.taxcardMobileChartData\"></salaxy-chart>\r\n                  <salaxy-chart ng-if=\"$welcomeCtrl.taxcardChartData.limits.hasLimit == false || !$welcomeCtrl.taxcardChartData.limits.hasLimit\" custom-height=\"200px\" config=\"$welcomeCtrl.taxcardChartData.config\"></salaxy-chart>\r\n                </div>\r\n              </div>\r\n            </div>\r\n          </div>\r\n        </div>\r\n\r\n        <div ng-repeat=\"item in $welcomeCtrl.workerDataNew.timeline\" class=\"mb-3\">\r\n          <div class=\"card personal-timeline-card\" ng-class=\"{'card-paid' : item.type == 'calculationPaid'}\">\r\n            <div class=\"card-header d-flex\">\r\n              <div class=\"icon-container d-flex justify-content-center align-items-center\" ng-class=\"{\r\n                'accepted': (item.status == 'workerRequestAccepted' || item.status == 'sharedApproved'), \r\n                'requested': (item.status == 'workerRequested'|| item.status == 'shared'), \r\n                'paid' : item.type == 'calculationPaid', \r\n                'rejected' : (item.status == 'workerRequestDeclined' || item.status == 'sharedRejected' || item.status == 'sharedRejectedWithoutOpen')\r\n              }\">\r\n                <i class=\"bi\" ng-class=\"{\r\n                  'bi-person-vcard': item.type == 'employment', \r\n                  'bi-person-fill': item.type == 'personAccount', \r\n                  'bi-calculator-fill': (item.type == 'calculation' && item.status != 'workerRequestAccepted' && item.status != 'workerRequestDeclined' && item.status != 'workerRequested' ),\r\n                  'bi-reply-fill' : (item.status == 'workerRequestAccepted' || item.status == 'sharedApproved'), \r\n                  'bi-file-earmark-text': (item.type == 'taxcard' && item.status != 'shared' && item.status != 'sharedApproved' && item.status != 'sharedRejected' && item.status != 'sharedRejectedWithoutOpen'), \r\n                  'bi-arrow-90deg-right' : (item.status == 'shared' || item.status == 'workerRequested'), \r\n                  'bi-check-lg' : item.type == 'calculationPaid',\r\n                  'bi-x-lg' : (item.status == 'workerRequestDeclined' || item.status == 'sharedRejected' || item.status == 'sharedRejectedWithoutOpen'),\r\n                }\">\r\n                </i>\r\n              </div>\r\n              <!--<div class=\"float-end actions-container clickable text-center\">\r\n              <i class=\"bi bi-three-dots\" style=\"font-size:1.3em;\"></i></div>-->\r\n              <div>\r\n                <h3 class=\"card-title mb-0\">{{ item.shortText }}</h3>\r\n                <div class=\"date\">{{ item.logicalDate | sxyDate }}</div>\r\n              </div>\r\n            </div>\r\n            <div class=\"card-body\" ng-class=\"{'card-body' : !$welcomeCtrl.getPreviewUrl(item)}\">\r\n              <div ng-if=\"$welcomeCtrl.getPreviewUrl(item)\" style=\"max-height: 200px; overflow: hidden;\">\r\n                <img ng-src=\"{{$welcomeCtrl.getPreviewUrl(item)}}\" style=\"width: 100%;\" />\r\n              </div>\r\n              <div ng-if=\"!$welcomeCtrl.getPreviewUrl(item)\" ng-switch=\"item.type\">\r\n                <div ng-switch-when=\"calculation\">\r\n                  <div ng-if=\"item.status != 'draft'\" class=\"otherparty-container\">\r\n                    <salaxy-avatar avatar=\"item.otherPartyInfo.avatar\"></salaxy-avatar>\r\n                    <span>{{item.otherPartyInfo.avatar.displayName}}</span>\r\n                  </div>\r\n\r\n                  <div class=\"card-main text-center\" ng-class=\"{'accepted': item.status == 'workerRequestAccepted', 'requested' : item.status == 'workerRequested', 'rejected' : item.status == 'workerRequestDeclined' }\">\r\n                    <span class=\"\">{{item.grossSalary | currency}}</span>\r\n                  </div>\r\n                  <div class=\"card-details-title\" sxy-text=\"SALAXY.NG1_PagesPersonal.index.calculation.grossSalary\"></div>\r\n                  <div class=\"card-details text-center\">\r\n                    <span><span sxy-text=\"SALAXY.NG1_PagesPersonal.index.calculation.netSalary\"></span>: {{ item.data.workerPayment | currency }}</span><br>\r\n                    <span><span sxy-text=\"SALAXY.NG1_PagesPersonal.index.calculation.taxes\"></span>: {{ item.data.taxPayment | currency }}</span>\r\n                  </div>\r\n                </div>\r\n                <div ng-switch-when=\"calculationPaid\">\r\n                  <div class=\"otherparty-container\">\r\n                    <salaxy-avatar avatar=\"item.otherPartyInfo.avatar\"></salaxy-avatar>\r\n                    <span>{{item.otherPartyInfo.avatar.displayName}}</span>\r\n                  </div>\r\n\r\n                  <div class=\"card-main text-center paid-calc\">\r\n                    <span class=\"\">{{item.grossSalary | currency}}</span>\r\n                  </div>\r\n                  <div class=\"card-details-title\" sxy-text=\"SALAXY.NG1_PagesPersonal.index.calculation.grossSalary\"></div>\r\n                  <div class=\"card-details text-center\">\r\n                    <span><span sxy-text=\"SALAXY.NG1_PagesPersonal.index.calculation.netSalary\"></span>: {{ item.data.workerPayment | currency }}</span><br>\r\n                    <span><span sxy-text=\"SALAXY.NG1_PagesPersonal.index.calculation.taxes\"></span>: {{ item.data.taxPayment | currency }}</span>\r\n                  </div>\r\n                </div>\r\n                <div ng-switch-when=\"taxcard\">\r\n                  <div ng-if=\"item.status == 'sharedApproved' || item.status == 'sharedRejected' || item.status == 'sharedRejectedWithoutOpen'\" class=\"otherparty-container\">\r\n                    <salaxy-avatar avatar=\"item.ownerInfo.avatar\"></salaxy-avatar>\r\n                    <span>{{item.ownerInfo.avatar.displayName}}</span>\r\n                  </div>\r\n                  <div ng-if=\"item.data.taxPercent\" class=\"card-main text-center\" ng-class=\"{'accepted' : item.status == 'sharedApproved', 'requested' : item.status == 'shared', 'rejected' : (item.status == 'sharedRejected' || item.status == 'sharedRejectedWithoutOpen') }\">\r\n                    <span class=\"\">{{item.data.taxPercent || \"-\"}} %</span>\r\n                  </div>\r\n                  <div class=\"card-details-title\" ng-if=\"item.data.taxPercent\" sxy-text=\"SALAXY.NG1_PagesPersonal.index.taxcard.taxPercent\"></div>\r\n                  <div ng-if=\"item.data.taxPercent\" class=\"card-details text-center\">\r\n                    <strong> {{ \"TaxcardKind.\" + item.data.kind | sxyEnum }}</strong><br>\r\n                    <span ng-if=\"item.data.incomeLimit\"><span sxy-text=\"SALAXY.NG1_PagesPersonal.index.taxcard.incomeLimit\"></span>: {{ item.data.incomeLimit | currency }}</span><br>\r\n                    <span ng-if=\"item.data.taxPercent2\"><span sxy-text=\"SALAXY.NG1_PagesPersonal.index.taxcard.taxPercent2\"></span>: {{ item.data.taxPercent2 }} %</span>\r\n                  </div>\r\n                </div>\r\n                <div ng-switch-when=\"personAccount\">\r\n                  <div class=\"text-primary\">{{ item.ownerInfo.displayName }}</div>\r\n                  <div><a href=\"mailto:{{ item.ownerInfo.email }}\">{{ item.ownerInfo.email }}</a></div>\r\n                  <div><span sxy-text=\"SALAXY.NG1_PagesPersonal.index.account.iban\"></span>: {{ item.ownerInfo.ibanNumber | sxyIban }}</div>\r\n                  <div><span sxy-text=\"SALAXY.NG1_PagesPersonal.index.account.phone\"></span>: {{ item.ownerInfo.telephone }}</div>\r\n                </div>\r\n                <div ng-switch-when=\"employment\">\r\n                  <div class=\"row\">\r\n                    <div class=\"col-6 text-center\">\r\n                      <div class=\"otherparty-container\">\r\n                        <salaxy-avatar avatar=\"item.ownerInfo.avatar\"></salaxy-avatar>\r\n                      </div>\r\n                      <span> {{ item.ownerInfo.avatar.displayName}}</span>\r\n                    </div>\r\n                    <div class=\"col-6 text-center\">\r\n                      <div class=\"otherparty-container\">\r\n                        <salaxy-avatar avatar=\"item.otherPartyInfo.avatar\"></salaxy-avatar>\r\n                      </div>\r\n                      <span> {{ item.otherPartyInfo.avatar.displayName}}</span>\r\n                    </div>\r\n                  </div>\r\n                </div>\r\n                <div ng-switch-default>\r\n                  <!--TODO: Handle {{ item.type }}-->\r\n                </div>\r\n              </div>\r\n              <div class=\"collapse small\" ng-class=\"{show: item.showInfo}\">\r\n                <pre>{{ item | json }}</pre>\r\n              </div>\r\n            </div>\r\n            <div class=\"card-footer\">\r\n              <span ng-switch=\"item.type\">\r\n                <span ng-switch-when=\"calculationPaid\">\r\n                  <a class=\"btn btn-sm btn-white\" target=\"_blank\" ng-href=\"{{$welcomeCtrl.getPdfUrl(item, true)}}\" sxy-text=\"SALAXY.NG1_PagesPersonal.index.calculation.buttons.openCalculationBtn\"></a>\r\n                  <a ng-href=\"{{$welcomeCtrl.getPdfUrl(item)}}\" class=\"btn btn-sm btn-white\" title=\"tuloste\" sxy-text=\"SALAXY.NG1_PagesPersonal.index.calculation.buttons.downloadPdfBtn\"></a>\r\n                </span>\r\n              <a ng-switch-when=\"calculation\" href=\"#/calc/details/{{item.id}}\" class=\"btn btn-secondary btn-sm\" sxy-text=\"SALAXY.NG1_PagesPersonal.index.calculation.buttons.showCalculationBtn\"></a>\r\n              <a ng-switch-when=\"taxcard\" href=\"#/taxcards\" class=\"btn btn-secondary btn-sm\" sxy-text=\"SALAXY.NG1_PagesPersonal.index.taxcard.buttons.showTaxcardsBtn\"></a>\r\n              <a ng-switch-when=\"personAccount\" href=\"#/account\" class=\"btn btn-secondary btn-sm\" sxy-text=\"SALAXY.NG1_PagesPersonal.index.account.showAccountInfoBtn\"></a>\r\n              </span>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/taxcards/household.html\",`<div>\r\n  <salaxy-tax-cards-list></salaxy-tax-cards-list>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/taxcards/index.html\",`<div class=\"salaxy-my-taxcards\">\r\n  <div ng-controller=\"MyTaxcardsController as $ctrl\">\r\n    <salaxy-spinner ng-if=\"!$ctrl.current\"></salaxy-spinner>\r\n    <div ng-if=\"$ctrl.current\" class=\"light-bg mb-2\">\r\n      <div ng-if=\"!$ctrl.current.active\">\r\n        <p class=\"lead\">\r\n          <span sxy-html=\"SALAXY.NG1_PagesPersonal.taxcards.introGetAutoTaxcard.html\"></span>\r\n        </p>\r\n        <div class=\"salaxy-placeholder-empty placeholder-md text-center\">\r\n          <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.setSharedAutoForSelf()\"\r\n            sxy-text=\"SALAXY.NG1_PagesPersonal.taxcards.buttons.getTaxPercentsBtn\"></button>\r\n        </div>\r\n      </div>\r\n      <div ng-if=\"$ctrl.current.active\">\r\n        <div ng-if=\"$ctrl.current.active.card.kind != 'auto'\">\r\n          <p class=\"lead\">\r\n            <span sxy-html=\"SALAXY.NG1_PagesPersonal.taxcards.introGetAutoTaxcard.html\"></span>\r\n            <a href=\"\" ng-click=\"$ctrl.showMoreText = true\" ng-if=\"!$ctrl.showMoreText\" sxy-text=\"SALAXY.UI_Terms.readMore\"></a>\r\n          </p>\r\n        </div>\r\n        <div ng-if=\"$ctrl.current.active.card.kind == 'auto'\" sxy-html=\"SALAXY.NG1_PagesPersonal.taxcards.intro.html\"></div>\r\n        <button type=\"button\" class=\"btn btn-default float-end\" ng-click=\"$ctrl.setSharedAutoForSelf()\"\r\n          sxy-text=\"SALAXY.NG1_PagesPersonal.taxcards.buttons.checkTaxPercentsBtn\"></button>\r\n        <h3 sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.currentTaxCard\"></h3>\r\n        <ng-include src=\"'salaxy-components/pages-personal/taxcards/TaxcardDetails_Personal.html'\"></ng-include>\r\n      </div>\r\n    </div>\r\n    <div ng-if=\"$ctrl.current\" class=\"light-bg\">\r\n      <salaxy-tab-buttons\r\n        current-tab=\"$ctrl.currentTab\"\r\n        options=\"[\r\n          { value: 'calc', text: 'SALAXY.NG1_PagesPersonal.taxcards.calcsPaidForCardTabHeading', hidden: !$ctrl.current.active },\r\n          { value: 'employers', text: 'SALAXY.NG1_PagesPersonal.taxcards.employersTabHeading', hidden: !$ctrl.current.employers },\r\n          { value: 'history', text: 'SALAXY.NG1_PagesPersonal.taxcards.earlierTaxCardsTabHeading', hidden: !$ctrl.current.list.length > 0 },\r\n        ]\"\r\n        tabs-id=\"taxcardsIndex\">\r\n      </salaxy-tab-buttons>\r\n      <div class=\"tab-content\" id=\"tab-content-taxcardsIndex\">\r\n        <div class=\"tab-pane\" id=\"calc-tab\" ng-if=\"$ctrl.current.active\">\r\n          <salaxy-taxcard-income-log parent=\"$ctrl.current.active\" ng-ref=\"$ctrl.$incomeLog\"></salaxy-taxcard-income-log>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"employers-tab\" ng-if=\"$ctrl.current.employers\">\r\n          <table class=\"table table-striped\">\r\n            <thead>\r\n              <tr>\r\n                <th class=\"th-xxs\" colspan=\"2\">\r\n                  <div sxy-text=\"SALAXY.NG1_PagesPersonal.taxcards.employerTableHeading\"></div>\r\n                  <div sxy-text=\"SALAXY.NG1_PagesPersonal.taxcards.typeTableHeading\"></div>\r\n                </th>\r\n                <th class=\"d-none d-md-table-cell \" sxy-text=\"SALAXY.NG1_PagesPersonal.taxcards.yearTableHeading\"></th>\r\n                <th class=\"d-none d-md-table-cell text-end\">\r\n                  <div sxy-text=\"SALAXY.MODEL.TaxcardData.taxPercent.title\"></div>\r\n                  <div sxy-text=\"SALAXY.MODEL.TaxcardData.taxPercent2.title\"></div>\r\n                </th>\r\n                <th class=\"text-end\">\r\n                  <div sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.salariesPaid\"></div>\r\n                  <div sxy-text=\"SALAXY.NG1_PagesPersonal.taxcards.incomeLimitTableHeading\"></div>\r\n                </th>\r\n                <th class=\"text-end\">\r\n                  <div sxy-text=\"SALAXY.NG1_PagesPersonal.taxcards.validDateTableHeading\"></div>\r\n                  <div sxy-text=\"SALAXY.NG1_PagesPersonal.taxcards.startDateTableHeading\"></div>\r\n                </th>\r\n              </tr>\r\n            </thead>\r\n            <tbody>\r\n              <tr ng-repeat=\"taxCard in $ctrl.current.employers\">\r\n                <td class=\"align-middle td-avatar\">\r\n                  <salaxy-avatar avatar=\"taxCard.ownerInfo.avatar\"></salaxy-avatar>\r\n                </td>\r\n                <td>\r\n                  <div class=\"d-md-none\"><strong>{{taxCard.ownerInfo.avatar.displayName}}</strong></div>\r\n                  <div class=\"d-md-none\">\r\n                    <strong>{{ \"TaxcardKind.\" + taxCard.data.kind | sxyEnum }} {{ taxCard.data.forYear }}</strong>\r\n                    {{taxCard.data.taxPercent}} %\r\n                    <span ng-if=\"taxCard.data.taxPercent2 != null\">({{ taxCard.data.taxPercent2 }} %)</span>\r\n                  </div>\r\n                  <div class=\"d-none d-md-block\"><strong>{{taxCard.ownerInfo.avatar.displayName}}</strong></div>\r\n                  <div class=\"d-none d-md-block\">{{ \"TaxcardKind.\" + taxCard.data.kind | sxyEnum }}</div>\r\n                </td>\r\n                <td class=\"d-none d-md-table-cell \">{{ taxCard.data.forYear }}</td>\r\n                <td class=\"d-none d-md-table-cell text-end\">\r\n                  <div>{{taxCard.data.taxPercent}} %</div>\r\n                  <div>{{taxCard.data.taxPercent2 != null ? (taxCard.data.taxPercent2 + ' %') : '-'}}</div>\r\n                </td>\r\n                <td class=\"text-end\">\r\n                  <div>{{ taxCard.data.totalIncome | currency: ' €' : 0 }}</div>\r\n                  <div>{{(taxCard.data.incomeLimit | currency: ' €' : 0) || '-'}}</div>\r\n                </td>\r\n                <td class=\"text-end\">\r\n                  <div>{{ taxCard.data | sxyDateRange }}</div>\r\n                  <div>{{ taxCard.createdAt | sxyTime }}</div>\r\n                </td>\r\n              </tr>\r\n            </tbody>\r\n          </table>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"history-tab\" ng-if=\"$ctrl.current.list.length > 0\">\r\n          <table class=\"table table-striped\">\r\n            <thead>\r\n              <tr>\r\n                <th>\r\n                  <div sxy-text=\"SALAXY.NG1_PagesPersonal.taxcards.validDateTableHeading\"></div>\r\n                  <div sxy-text=\"SALAXY.NG1_PagesPersonal.taxcards.startDateTableHeading\"></div>\r\n                </th>\r\n                <th sxy-text=\"SALAXY.NG1_PagesPersonal.taxcards.yearTableHeading\"></th>\r\n                <th class=\"d-none d-md-table-cell text-end\">\r\n                  <div sxy-text=\"SALAXY.MODEL.TaxcardData.taxPercent.title\"></div>\r\n                  <div sxy-text=\"SALAXY.MODEL.TaxcardData.taxPercent2.title\"></div>\r\n                </th>\r\n                <th class=\"d-table-cell d-md-none text-end\">%</th>\r\n                <th class=\"d-table-cell d-md-none text-end\" colspan=\"2\">\r\n                  <div sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.salariesPaid\"></div>\r\n                  <div sxy-text=\"SALAXY.NG1_PagesPersonal.taxcards.incomeLimitTableHeading\"></div>\r\n                </th>\r\n                <th class=\"d-none d-md-table-cell text-end\">\r\n                  <div sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.salariesPaid\"></div>\r\n                  <div sxy-text=\"SALAXY.NG1_PagesPersonal.taxcards.incomeLimitTableHeading\"></div>\r\n                </th>\r\n                <th class=\"d-none d-md-table-cell text-end\"></th>\r\n              </tr>\r\n            </thead>\r\n            <tbody>\r\n              <tr ng-repeat=\"taxCard in $ctrl.current.list\">\r\n                <td>\r\n                  <div>{{ taxCard.data | sxyDateRange }}</div>\r\n                  <div>{{ taxCard.createdAt | sxyTime }}</div>\r\n                </td>\r\n                <td>{{ taxCard.data.forYear }}</td>\r\n                <td class=\"text-end\">\r\n                  <div>{{taxCard.data.taxPercent}}&nbsp;%</div>\r\n                  <div>{{taxCard.data.taxPercent2 != null ? (taxCard.data.taxPercent2 + '&nbsp;%') : '-'}}</div>\r\n                </td>\r\n                <td class=\"text-end\">\r\n                  <div>{{ taxCard.data.totalIncome | currency: ' €' : 0 }}</div>\r\n                  <div>{{(taxCard.data.incomeLimit | currency: ' €' : 0) || '-'}}</div>\r\n                </td>\r\n                <td class=\"middle-align text-end\" ng-if=\"!taxCard.isReadOnly\">\r\n                  <button class=\"btn btn-danger btn-sm\" ng-click=\"$ctrl.deleteTaxCard(taxCard.id)\">\r\n                    <span title=\"{{'SALAXY.UI_Terms.delete' | sxyTranslate}}\">&times;</span>\r\n                  </button>\r\n                </td>\r\n              </tr>\r\n            </tbody>\r\n          </table>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/taxcards/TaxcardDetails_Personal.html\",`<div>\r\n  <div class=\"row\">\r\n    <div class=\"col-md-7 col-lg-7\" ng-switch=\"$ctrl.chartType\">\r\n      <div ng-switch-when=\"full\" class=\"salaxy-tax-card-chart chart-container\">    \r\n          <salaxy-chart custom-height=\"400px\" config=\"$ctrl.getMainChartConfig($ctrl.current.active)\"></salaxy-chart>\r\n      </div>\r\n      <div ng-switch-when=\"pie\" class=\"salaxy-tax-card-chart chart-container text-center\">      \r\n          <salaxy-chart style=\"height: 400px; position: relative;\" config=\"$ctrl.getPieChartConfig($ctrl.current.active)\"></salaxy-chart>\r\n      </div>\r\n    </div>\r\n    <div class=\"col-md-5 col-lg-5\">\r\n      <div class=\"row current-taxcard-row table-row\">\r\n        <div class=\"col-xs-12\">\r\n          <strong sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.taxCardKind\"></strong><br /> {{ 'TaxcardKind.' + $ctrl.current.active.card.kind | sxyEnum }}\r\n          ({{$ctrl.current.active.card.forYear}})\r\n        </div>\r\n      </div>\r\n      <div class=\"row current-taxcard-row table-row\">\r\n        <div class=\"col-xs-8\">\r\n          <strong sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.validDate\"></strong><br /> {{$ctrl.current.active.card.validity.start | date}} - {{$ctrl.current.active.card.validity.end | date}}\r\n        </div>\r\n        <div class=\"col-xs-4 text-right\">\r\n          <strong sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.taxCardAdded\"></strong><br />\r\n          <span title=\"{{ $ctrl.current.active.createdAt | date : 'short' }}\">{{ $ctrl.current.active.createdAt | sxyDate }}</span>\r\n        </div>\r\n      </div>\r\n      <table class=\"table table-sm\" style=\"margin-bottom: 0; margin-top: 6px\">\r\n        <thead>\r\n          <tr>\r\n            <th colspan=\"2\" style=\"padding-left: 0;\"><span sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.mainTaxPercent2\"></span></th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr>\r\n            <td sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.basicPercent\"></td>\r\n            <td class=\"right\">{{ $ctrl.current.active.card.taxPercent }} %</td>\r\n          </tr>\r\n          <tr ng-if=\"!$ctrl.current.active.card.incomeLimit\">\r\n            <td colspan=\"2\"><span sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.noIncomeLimit\"></span></td>\r\n          </tr>\r\n          <tr ng-if=\"$ctrl.current.active.card.incomeLimit\">\r\n            <td><span sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.taxPercent2.name\"></span> <small>(tulorajan {{ $ctrl.current.active.card.incomeLimit | currency : '€' : 0 }}\r\n                {{'SALAXY.NG1.CurrentTaxCardComponent.after' | sxyTranslate}})</small></td>\r\n            <td class=\"right\">{{ $ctrl.current.active.card.taxPercent2 || \"-\" }} %</td>\r\n          </tr>\r\n          <tr ng-if=\"$ctrl.current.active.card.taxPercentMin\">\r\n            <!-- Only needed if the view is used for showing Employer taxcards: Worker taxcards no longer can have a minimum. -->\r\n            <td>\r\n              <span sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.taxPercentMin.title\"></span>\r\n            </td>\r\n            <td class=\"right\">\r\n              <span>{{ $ctrl.current.active.card.taxPercentMin || \"-\" }} %</span>\r\n            </td>\r\n          </tr>\r\n          <tr ng-if=\"$ctrl.current.active.card.kind == 'auto'\">\r\n            <td colspan=\"2\">\r\n              <span class=\"text-info\" ng-if=\"$ctrl.current.active.card.lastChecked != '2000-01-01T00:00:00Z'\"><small>{{'SALAXY.NG1.CurrentTaxCardComponent.taxCardChecked' | sxyTranslate}}\r\n                  {{$ctrl.current.active.card.lastChecked | date: \"dd.MM.yyyy HH:mm\"}}</small></span>\r\n              <br />\r\n              <button type=\"button\" ng-click=\"$ctrl.setSharedAutoForSelf()\"\r\n                class=\"btn btn-info\">{{'SALAXY.NG1.CurrentTaxCardComponent.checkAutomaticTaxCard' | sxyTranslate}}</button>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n      <table class=\"table table-sm\" style=\"margin-top: 6px\" ng-if=\"$ctrl.current.active.card.incomeLimit\">\r\n        <thead>\r\n          <tr>\r\n            <th colspan=\"2\" style=\"padding-left: 0;\"><strong sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.incomeLimit\"></strong></th>\r\n            <th class=\"right\">{{ $ctrl.current.active.card.incomeLimit | currency : '€' : 0 }}</th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr>\r\n            <td style=\"width: 20px;\" class=\"text-center\">-</td>\r\n            <td><span sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.salariesPaid\"></span></td>\r\n            <td class=\"right\">{{ $ctrl.current.active.result.totalIncome | currency }}</td>\r\n          </tr>\r\n          <tr ng-if=\"$ctrl.current.active.result.totalIncomeJanuary\">\r\n            <td></td>\r\n            <td>...<span sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.inJanuary\"></span></td>\r\n            <td class=\"right\">{{ $ctrl.current.active.result.totalIncomeJanuary | currency }}</td>\r\n          </tr>\r\n          <tr class=\"total\">\r\n            <td colspan=\"2\"><span sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.beforeIncomeLimit\"></span></td>\r\n            <td class=\"right\">{{ $ctrl.current.active.card.incomeLimit - $ctrl.current.active.result.totalIncome | currency }}</td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/templates/WorkerLayout.html\",`<div ng-cloak class=\"salaxy-component salaxy-navi-page-container container-personal d-flex\" ng-class=\"($ctrl.isNaviOpen ? 'salaxy-navi-sm-opened ' : '') + $ctrl.current.cssClass\" ng-if=\"!$ctrl.showFullPageLoader\">\r\n  <div class=\"salaxy-navi-sidebar d-print-none\" ng-if=\"!$ctrl.showFullPageLoader\">\r\n    <div class=\"salaxy-logo-container\">\r\n      <a href=\"/#/\"><!--<img src=\"/img/navi-logo.png\" />--></a>\r\n    </div>\r\n    <div ng-controller=\"SessionController as $session\">\r\n      <div class=\"salaxy-login-button text-center\" style=\"padding:7px;\" ng-hide=\"$session.isAuthenticated\">\r\n        <button ng-click=\"$session.signIn()\" class=\"btn btn-default salaxy-login-button-login\">\r\n        <i class=\"bi bi-lock-fill me-2\"></i>\r\n        <span class=\"salaxy-login-button-text\">{{ $session.isSessionChecking ?  ('SALAXY.NG1.LoginButtonComponent.searching' | sxyTranslate) : ('SALAXY.UI_Terms.login' | sxyTranslate) }}</span>\r\n      </button>\r\n      </div>\r\n      <div class=\"salaxy-login-button-personal p-2\" ng-controller=\"PersonalWebLegacyController as $legacy\">\r\n        <div ng-show=\"$session.isAuthenticated\" class=\"salaxy-login-button-logout d-flex\" ng-init=\"isNavCollapsed = true\">\r\n          <salaxy-avatar avatar=\"$session.avatar\"></salaxy-avatar>\r\n          <div class=\"login-text ms-2\">\r\n            <div class=\"salaxy-login-button-text\">\r\n            {{ $session.isAuthenticated ? $session.avatar.displayName : ('SALAXY.NG1.LoginButtonComponent.authenticating' | sxyTranslate) }}\r\n            </div>\r\n            <div class=\"d-flex flex-column align-items-start\">\r\n              <button ng-if=\"$session.isAuthenticated\" ng-click=\"$legacy.signOut()\" class=\"btn btn-transparent btn-xs\"><i class=\"bi bi-box-arrow-right me-1\" aria-hidden=\"true\" style=\"font-size: 150%;\"></i> <span class=\"\" sxy-text=\"SALAXY.UI_Terms.logout\"></span></button>\r\n              <div class=\"btn-group language-selection btn-group-xs dropdown\" ng-show=\"'test' | sxyIsInRole\" ng-controller=\"PersonAccountController as $accountCtrl\">\r\n                <button type=\"button\" class=\"btn btn-transparent dropdown-toggle\" data-bs-toggle=\"dropdown\">\r\n                  <i class=\"bi bi-globe-americas me-1\" style=\"font-size:1.1em;\"></i>\r\n                  <span> {{\"SALAXY.ENUM.Language.\" + $accountCtrl.getAccountLanguage() + \".label\" | sxyTranslate}}</span> \r\n                  <i class=\"bi bi-chevron-down\"></i>\r\n                </button>\r\n                <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"single-button\">\r\n                  <li role=\"menuitem\" ng-if=\"$accountCtrl.getAccountLanguage() != 'fi'\"><a ng-click=\"$accountCtrl.current.language = 'fi'; $accountCtrl.saveCurrent()\">Suomi</a></li>\r\n                  <li role=\"menuitem\" ng-if=\"$accountCtrl.getAccountLanguage() != 'en'\"><a ng-click=\"$accountCtrl.current.language = 'en'; $accountCtrl.saveCurrent()\">English</a></li>\r\n                  <li role=\"menuitem\" ng-if=\"$accountCtrl.getAccountLanguage() != 'sv'\"><a ng-click=\"$accountCtrl.current.language = 'sv';$accountCtrl.saveCurrent()\">Svenska</a></li>\r\n                </ul>\r\n              </div>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <salaxy-navi-sitemap template-url=\"salaxy-components/pages-personal/templates/WorkerSitemap.html\" mode=\"accordion\"></salaxy-navi-sitemap>\r\n  </div>\r\n  <header class=\"salaxy-navi-header-mobile align-items-center\">\r\n    <h1 class=\"d-inline\">{{ $ctrl.title | sxyTranslate }}</h1>\r\n    <div class=\"btn-group btn-group-login-button dropdown ms-auto\" ng-controller=\"SessionController as $session\">\r\n      <button ng-hide=\"$session.isAuthenticated\" ng-click=\"$session.signIn()\" class=\"btn btn-default salaxy-login-button-login\">\r\n        <i class=\"bi bi-lock-fill me-2\"></i>\r\n        <span class=\"salaxy-login-button-text\">{{ $ctrl.isSessionChecking ?  ('SALAXY.NG1.LoginButtonComponent.searching' | sxyTranslate) : ('SALAXY.UI_Terms.login' | sxyTranslate) }}</span>\r\n      </button>\r\n      <div class=\"login-button d-flex align-items-center dropdown-toggle\" type=\"button\" data-bs-toggle=\"dropdown\" ng-show=\"$session.isAuthenticated\">\r\n        <salaxy-avatar avatar=\"$session.avatar\" style=\"font-size: 2em;\"></salaxy-avatar>\r\n      </div>\r\n      <ul ng-controller=\"PersonalWebLegacyController as $legacy\" class=\"dropdown-menu\" role=\"menu\">\r\n        <li>\r\n          <a class=\"dropdown-item\" href=\"#\" ng-click=\"$legacy.signOut()\" sxy-text=\"SALAXY.UI_Terms.logout\"></a>\r\n        </li>\r\n      </ul>\r\n    </div>\r\n    <button type=\"button\" class=\"salaxy-navi-hamburger btn btn-default ms-2\" ng-click=\"$ctrl.toggleNavi()\">\r\n      <span class=\"sr-only\" sxy-text=\"SALAXY.UI_Terms.navigation\"></span>\r\n      <i class=\"bi bi-list m-0\" aria-hidden=\"true\"></i>\r\n    </button>\r\n  </header>\r\n  <div class=\"salaxy-navi-main-container pb-5\">\r\n    <content>\r\n      <ng-transclude ng-transclude-slot=\"header\">\r\n      </ng-transclude>\r\n      <div id=\"salaxy-alert-container\"></div>\r\n      <ng-transclude ng-transclude-slot=\"main\">\r\n        <main>\r\n          <div class=\"d-none d-md-block\">\r\n            <div ng-class=\"$ctrl.current.isFullWidth ? 'container-fluid' : 'container'\">\r\n\r\n              <div class=\"row\" ng-if=\"$ctrl.current.id != 'home'\">\r\n                <div class=\"col-xs-12\">\r\n                  <h1 class=\"page-title\">\r\n                    {{ $ctrl.title | sxyTranslate }}\r\n                  </h1>\r\n                </div>\r\n              </div>\r\n            </div>\r\n          </div>\r\n          <div ng-class=\"$ctrl.current.isFullWidth ? 'container-fluid' :  'container'\" ng-view autoscroll=\"true\"></div>\r\n        </main>\r\n      </ng-transclude>\r\n    </content>\r\n  </div>\r\n  <div ng-if=\"$ctrl.current.id == 'home'\">\r\n    <div ng-controller=\"WelcomeController as $welcomeCtrl\" sxy-if-role=\"worker\">\r\n      <div ng-if=\"$welcomeCtrl.workerDataNew.timeline\" class=\"timeline-sidebar d-none d-sm-block position-fixed me-3 mt-3\">\r\n        <div class=\"list-card card card-sm card-secondary card-own-taxcard card-secondary mb-4\">\r\n          <div class=\"card-header\" sxy-text=\"SALAXY.NG1.WelcomeComponent.taxcard\"></div>\r\n          <div ng-show=\"$welcomeCtrl.workerUI.taxCardAdded\" class=\"salaxy-component table-responsive card-content md-height\">\r\n            <div class=\"card-content md-height\">\r\n              <div class=\"card-body no-vertical-padding salaxy-tax-card-chart chart-container\" style=\"max-height:230px; padding-top:0; padding-bottom:0; padding-left:5px;padding-right:5px;\">              \r\n                <salaxy-chart ng-if=\"$welcomeCtrl.taxcardChartData.limits.hasLimit == true\" custom-height=\"210px\" config=\"$welcomeCtrl.taxcardChartData.config\"></salaxy-chart>             \r\n                <salaxy-chart ng-if=\"$welcomeCtrl.taxcardChartData.limits.hasLimit == false || !$welcomeCtrl.taxcardChartData.limits.hasLimit\" config=\"$welcomeCtrl.taxcardChartData.config\"></salaxy-chart>\r\n              </div>\r\n            </div>\r\n          </div>\r\n          <div ng-show=\"!$welcomeCtrl.workerUI.taxCardAdded\" class=\"card-body card-content md-height align-middle\">\r\n            <div class=\"text-center\">\r\n              <p sxy-text=\"SALAXY.NG1_PagesPersonal.taxcards.buttons.getTaxPercentsBtn\"></p>\r\n            </div>\r\n          </div>\r\n          <div class=\"card-footer text-center\">\r\n            <a class=\"btn btn-primary btn-sm\" href=\"#/taxcards\" sxy-text=\"SALAXY.NG1.WelcomeComponent.taxcard\"></a>\r\n\r\n          </div>\r\n        </div>\r\n        <div class=\"list-card card card-sm card-secondary card-new-calculation\">\r\n          <div class=\"card-header\" sxy-text=\"SALAXY.NG1_PagesPersonal.index.sendCalculation.panelHeading\"></div>\r\n          <div class=\"card-body card-content\">\r\n            <div class=\"text-center\">\r\n              <h3 class=\"text-warning\" sxy-text=\"SALAXY.NG1_PagesPersonal.index.sendCalculation.panelTitle\"></h3>\r\n              <p sxy-text=\"SALAXY.NG1_PagesPersonal.index.sendCalculation.panelText\"></p>\r\n            </div>\r\n          </div>\r\n          <div class=\"card-footer text-center\">\r\n            <a class=\"btn btn-primary btn-sm\" href=\"#/calc/details/new\" sxy-text=\"SALAXY.NG1_PagesPersonal.index.sendCalculation.button\"></a>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/templates/WorkerSitemap.html\",`<div class=\"salaxy-component salaxy-navi-sitemap\">\r\n  <ul class=\"list-group\">\r\n    <li ng-repeat=\"section in $ctrl.sitemap | filter:{ hidden: '!true' }\" class=\"list-group-item\">\r\n      <a ng-href=\"{{section.id != 'abc' ? section.url : 'https://help.palkkaus.fi/hc/fi'}}\" ng-attr-target=\"{{section.id == 'abc' ? '_blank' : undefined}}\" ng-click=\"!section.children || !section.children.length ? $ctrl.toggleNavi() : return\" ng-class=\"{ 'active' : $ctrl.isCurrent(section)}\">\r\n        <span ng-if=\"$ctrl.mode=='accordion' && section.children && section.children.length\">\r\n          <i class=\"bi bi-chevron-down float-end\" ng-class=\"{'upside' : $ctrl.getSectionId() == section.id}\" aria-hidden=\"true\"></i>\r\n        </span> {{section.title | sxyTranslate}}\r\n      </a>\r\n      <ul ng-hide=\"!section.children.length || ($ctrl.mode=='accordion' && $ctrl.getSectionId() != section.id)\">\r\n        <li class=\"d-sm-none d-block\">\r\n          <strong ng-show=\"$ctrl.isCurrent(section)\">\r\n            <a ng-href=\"{{section.url}}\" ng-click=\"$ctrl.toggleNavi()\">{{section.title | sxyTranslate}}</a>\r\n          </strong>\r\n          <span ng-hide=\"$ctrl.isCurrent(section)\">\r\n            <a ng-href=\"{{section.url}}\" ng-click=\"$ctrl.toggleNavi()\">{{section.title | sxyTranslate}}</a>\r\n          </span>\r\n        </li>\r\n        <li ng-repeat=\"subNavi in section.children | filter:{ hidden: '!true' }\">\r\n          <strong ng-show=\"$ctrl.isCurrent(subNavi)\">\r\n            <a ng-href=\"{{subNavi.url}}\" ng-click=\"$ctrl.toggleNavi()\">{{subNavi.title | sxyTranslate}}</a>\r\n          </strong>\r\n          <span ng-hide=\"$ctrl.isCurrent(subNavi)\">\r\n            <a ng-href=\"{{subNavi.url}}\" ng-click=\"$ctrl.toggleNavi()\">{{subNavi.title | sxyTranslate}}</a>\r\n          </span>\r\n        </li>\r\n      </ul>\r\n    </li>\r\n  </ul>\r\n\r\n  <div class=\"poweredby\">\r\n    <span class=\"poweredby-image\"></span>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/workers/details.html\",`<salaxy-worker-details model=\"'url'\" is-read-only-forced=\"$ctrl.route.readOnly\" hide-button=\"$ctrl.route.readOnly\"></salaxy-worker-details>`);\n\n $templateCache.put(\"salaxy-components/pages-personal/workers/index.html\",`<salaxy-employment-list read-only=\"'household' | sxyIsInRole\"></salaxy-employment-list>`);\n\n $templateCache.put(\"salaxy-components/personal/AccountAuthorizationPerson.html\",`﻿<div class=\"salaxy-component salaxy-account-authorization-person\">\r\n  <form name=\"accountAuthorization\" sxy-if-role=\"auth\">\r\n    <div class=\"row\">\r\n      <div class=\"col-12 col-sm-6 col-md-12\">\r\n        <legend sxy-text=\"SALAXY.NG1.AccountAuthorizationPersonComponent.identificationTitle\"></legend>\r\n        <div class=\"row table-row\" ng-if=\"!$ctrl.session.currentAccount.identity.contract.isSigned\">\r\n          <div class=\"col-12 \" ng-controller=\"WorkerOnboardingController as $wizard\">\r\n            <strong sxy-text=\"SALAXY.NG1.AccountAuthorizationPersonComponent.notIdentified\"></strong><br>\r\n            <button class=\"btn btn-primary\" ng-click=\"$wizard.launch()\" sxy-text=\"SALAXY.NG1.AccountAuthorizationPersonComponent.identifyBtn\"></button>\r\n          </div>\r\n        </div>\r\n        <div class=\"row table-row\" ng-if=\"$ctrl.session.currentAccount.identity.contract.isSigned\">\r\n          <div class=\"col-12\">\r\n            <strong><span sxy-text-=\"SALAXY.NG1.AccountAuthorizationPersonComponent.haveIdentified\"></span> {{$ctrl.session.currentAccount.identity.contract.signedAt | date}}.</strong>\r\n          </div>\r\n        </div>\r\n        <div class=\"row table-row\">\r\n          <div class=\"col-12 col-sm-4\">\r\n            <strong sxy-text=\"SALAXY.NG1.AccountAuthorizationPersonComponent.credentialLabel\"></strong>\r\n          </div>\r\n          <div class=\"col-12 col-sm-8\">\r\n            {{$ctrl.session.currentCredential.avatar.id}}\r\n          </div>\r\n        </div>\r\n        <div class=\"row table-row\">\r\n          <div class=\"col-12 col-sm-4\">\r\n            <strong sxy-text=\"SALAXY.NG1.AccountAuthorizationPersonComponent.authorizationTypeLabel\"></strong>\r\n          </div>\r\n          <div class=\"col-12 col-sm-4\">\r\n            {{'SALAXY.ENUM.AuthorizationType.' + $ctrl.session.currentAccount.identity.contract.authorizationType + '.label' |sxyTranslate}}\r\n          </div>\r\n          <div class=\"col-12 col-sm-4  text-end\" ng-if=\"$ctrl.session.currentAccount.identity.contract.authorizationType == 'employerAuthorization'\">\r\n            <a class=\"\" ng-href=\"{{$ctrl.authorizationPdfUrl}}\" target=\"_blank\" sxy-text=\"SALAXY.UI_Terms.seePreview\"></a>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div class=\"col-12 col-sm-6 col-md-12 mt-4\">\r\n        <legend sxy-text=\"SALAXY.NG1.AccountAuthorizationPersonComponent.userInfoTitle\"></legend>\r\n        <div class=\"row table-row\">\r\n          <div class=\"col-12 col-sm-4\">\r\n            <strong sxy-text=\"SALAXY.NG1.AccountAuthorizationPersonComponent.userNameLabel\"></strong>\r\n          </div>\r\n          <div class=\"col-12 col-sm-8\">\r\n            {{$ctrl.session.currentCredential.email}}\r\n          </div>\r\n        </div>\r\n        <div class=\"row table-row\">\r\n          <div class=\"col-12 col-sm-4\">\r\n            <strong sxy-text=\"SALAXY.NG1.AccountAuthorizationPersonComponent.authMethodLabel\"></strong>\r\n          </div>\r\n          <div class=\"col-12 col-sm-8\">\r\n            {{'SALAXY.ENUM.AuthenticationMethod.' + $ctrl.session.currentCredential.authenticationMethod + '.label' |sxyTranslate}}\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div class=\"col-12 col-sm-6 col-md-12 mt-4\">\r\n        <legend sxy-text=\"SALAXY.NG1.AccountAuthorizationPersonComponent.termsAndPrivacyTitle\"></legend>\r\n        <div class=\"row table-row\">\r\n          <div class=\"col-12 col-sm-8\">\r\n            <strong sxy-text=\"SALAXY.NG1.AccountAuthorizationPersonComponent.termsLabel\"></strong>\r\n          </div>\r\n          <div class=\"col-12 col-sm-4 text-end\">\r\n            <span sxy-html=\"SALAXY.NG1.AccountAuthorizationPersonComponent.termsBtn.html\"></span>\r\n          </div>\r\n        </div>\r\n        <div class=\"row table-row\">\r\n          <div class=\"col-12 col-sm-8\">\r\n            <strong sxy-text=\"SALAXY.NG1.AccountAuthorizationPersonComponent.privacyLabel\"></strong>\r\n          </div>\r\n          <div class=\"col-12 col-sm-4 text-end\">\r\n            <span sxy-html=\"SALAXY.NG1.AccountAuthorizationPersonComponent.privacyBtn.html\"></span>\r\n\r\n          </div>\r\n        </div>\r\n        <div class=\"row table-row\">\r\n          <div class=\"col-12 col-sm-8\">\r\n            <strong sxy-text=\"SALAXY.NG1.AccountAuthorizationPersonComponent.privacyStatementLabel\"></strong>\r\n          </div>\r\n          <div class=\"col-12 col-sm-4 text-end\">\r\n\r\n            <span sxy-html=\"SALAXY.NG1.AccountAuthorizationPersonComponent.privacyStatementBtn.html\"></span>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </form>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/personal/AccountAvatarEditPerson.html\",`<div class=\"salaxy-component salaxy-account-avatar-edit-person\">\r\n  <form name=\"workerForm\" class=\"form-horizontal\" ng-if=\"$ctrl.current\">\r\n    <div class=\"form-group row\">\r\n      <div class=\"col-4\">\r\n        <label for=\"avatarPreview\" class=\"control-label\" style=\"text-align:left\" sxy-text=\"SALAXY.NG1.AccountAvatarEditPersonComponent.avatarLabel\"></label>\r\n      </div>\r\n      <div class=\"col-8\">\r\n        <div class=\"worker-avatar-col\">\r\n          <salaxy-avatar style=\"font-size: 130px\" avatar=\"$ctrl.current.avatar\"></salaxy-avatar>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"form-group row\">\r\n      <div class=\"col-4\">\r\n        <label for=\"avatarPictureType\" class=\"control-label\" style=\"text-align:left\" sxy-text=\"SALAXY.NG1.AccountAvatarEditPersonComponent.avatarTypeLabel\"></label>\r\n      </div>\r\n      <div class=\"col-8\">\r\n        <select class=\"form-select\" id=\"avatarPictureType\" ng-model=\"$ctrl.current.avatar.pictureType\" ng-change=\"$ctrl.typeForAvatarChanged()\">\r\n          <option value=\"\" disabled sxy-text=\"SALAXY.NG1.AccountAvatarEditPersonComponent.optionChoose\"></option>\r\n          <option value=\"icon\" sxy-text=\"SALAXY.NG1.AccountAvatarEditPersonComponent.optionIcon\"></option>\r\n          <option value=\"uploaded\" sxy-text=\"SALAXY.NG1.AccountAvatarEditPersonComponent.optionUploaded\"></option>\r\n          <option value=\"gravatar\" sxy-text=\"SALAXY.NG1.AccountAvatarEditPersonComponent.optionGravatar\"></option>\r\n        </select>\r\n      </div>\r\n    </div>\r\n    <div ng-if=\"$ctrl.current.avatar.pictureType == 'gravatar'\" class=\"row\">\r\n      <div class=\"input-info col-sm-8 offset-sm-4\">\r\n        <div class=\"input-info-icon\"><i class=\"bi bi-info-circle-fill text-default\"></i></div>\r\n        <p class=\"small input-info-text with-icon \" sxy-html=\"SALAXY.NG1.AccountAvatarEditPersonComponent.gravatarInfo.html\"></p>\r\n      </div>\r\n    </div>\r\n    <div ng-if=\"$ctrl.current.avatar.pictureType == 'icon'\">\r\n      <salaxy-input name=\"avatarInitials\" label=\"SALAXY.NG1.AccountAvatarEditPersonComponent.initialsLabel\" ng-model=\"$ctrl.current.avatar.initials\" max-length=\"2\"></salaxy-input>\r\n      <salaxy-input-enum ng-model=\"$ctrl.current.avatar.color\" name=\"avatarColor\" label=\"SALAXY.NG1.AccountAvatarEditPersonComponent.colorLabel\" options=\"{ '#7F2C2A': ('SALAXY.NG1.AccountAvatarEditPersonComponent.colorBrown' | sxyTranslate), '#91D214': ('SALAXY.NG1.AccountAvatarEditPersonComponent.colorLime' | sxyTranslate), '#61703B': ('SALAXY.NG1.AccountAvatarEditPersonComponent.colorDarkGreen' | sxyTranslate), '#D10074': ('SALAXY.NG1.AccountAvatarEditPersonComponent.colorPink' | sxyTranslate)}\">\r\n      </salaxy-input-enum>\r\n    </div>\r\n    <div class=\"form-group\">\r\n      <div ng-if=\"$ctrl.current.avatar.pictureType == 'uploaded'\" class=\"row\">\r\n        <div class=\"col-4\">\r\n          <label for=\"avatarImageUpload\" sxy-text=\"SALAXY.NG1.AccountAvatarEditPersonComponent.uploadImageLabel\"></label>\r\n        </div>\r\n        <div class=\"col-8\">\r\n          <div name=\"avatarImageUpload\" ng-model=\"avatarImage\" ngf-drop=\"$ctrl.uploadAvatarImage($file)\" ngf-select=\"$ctrl.uploadAvatarImage($file)\" class=\"salaxy-drop-box\" ngf-drag-over-class=\"'salaxy-drag-over'\" ngf-multiple=\"false\" ngf-min-size=\"5KB\" ngf-max-size=\"10MB\"\r\n            ngf-pattern=\"'image/*'\" ngf-model-invalid=\"invalidFile\" ng-class=\"invalidFile.$error != null ? 'error' : ''\">\r\n            <span sxy-html=\"SALAXY.NG1.AccountAvatarEditPersonComponent.uploadImage.html\"></span>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"row\">\r\n      <div class=\"col-sm-8 offset-sm-4 input-info\">\r\n        <div class=\"input-info-icon\"><i class=\"bi bi-info-circle-fill text-default\"></i></div>\r\n        <p class=\"small input-info-text with-icon\" sxy-html=\"SALAXY.NG1.AccountAvatarEditPersonComponent.avatarDescription.html\" style=\"padding-top:0.4em;\"></p>\r\n      </div>\r\n    </div>\r\n    <div class=\"text-end\">\r\n      <button ng-click=\"$ctrl.saveCurrent()\" ng-disabled=\"workerForm.$invalid\" class=\"btn btn-primary\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n    </div>\r\n  </form>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/personal/AccountContactEditPerson.html\",`<div class=\"salaxy-component salaxy-account-contact-edit-person\">\r\n  <form name=\"workerForm\" class=\"form-horizontal\" ng-if=\"$ctrl.current\">\r\n    <div class=\"row\">\r\n      <div class=\"col-12\">\r\n        <salaxy-input name=\"email\" label=\"SALAXY.MODEL.PersonAccount.contact.email.title\" sxy-email ng-model=\"$ctrl.current.contact.email\" ng-change=\"$ctrl.emailForAvatarChanged()\">\r\n        </salaxy-input>\r\n        <salaxy-input name=\"telephone\" label=\"SALAXY.MODEL.PersonAccount.contact.telephone.title\" sxy-mobile-phone ng-model=\"$ctrl.current.contact.telephone\"></salaxy-input>\r\n        <salaxy-input name=\"street\" label=\"SALAXY.MODEL.PersonAccount.contact.street.title\" ng-model=\"$ctrl.current.contact.street\" ng-required=\"'household' | sxyIsInRole\"></salaxy-input>\r\n        <div class=\"address-info-text row mb-3\">\r\n          <div class=\"col-sm-8 offset-sm-4 input-info d-flex align-items-center\">\r\n            <i class=\"bi bi-info-circle-fill text-default me-2\"></i>\r\n            <div class=\"small input-info-text\" sxy-text=\"SALAXY.NG1.AccountContactEditPersonComponent.addressInfo\"></div>\r\n          </div>\r\n        </div>\r\n        <salaxy-input name=\"postalCode\" label=\"SALAXY.MODEL.PersonAccount.contact.postalCode.title\" sxy-postal-code-fi ng-model=\"$ctrl.current.contact.postalCode\" ng-required=\"'household' | sxyIsInRole\"></salaxy-input>\r\n        <salaxy-input name=\"city\" label=\"SALAXY.MODEL.PersonAccount.contact.city.title\" ng-model=\"$ctrl.current.contact.city\" ng-required=\"'household' | sxyIsInRole\"></salaxy-input>\r\n      </div>\r\n    </div>\r\n    <div class=\"text-end\">\r\n      <button ng-click=\"$ctrl.saveCurrent()\" ng-disabled=\"workerForm.$invalid\" class=\"btn btn-primary\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n    </div>\r\n  </form>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/personal/AccountDetailsEditPerson.html\",`<div class=\"salaxy-component salaxy-account-details-edit-person\">\r\n  <form name=\"workerForm\" class=\"form-horizontal\" ng-if=\"$ctrl.current\">\r\n    <div class=\"row language-selection mb-2\" ng-controller=\"SessionController as $session\">\r\n      <div class=\"col-4 control-label\"><strong class=\"\" sxy-text=\"SALAXY.NG1.LanguageSelectionComponent.languageSelectionLabel\"></strong></div>\r\n      <div class=\"col-8\">\r\n\r\n        <div class=\"btn-group btn-group-sm float-end\" role=\"group\">\r\n\r\n          <button class=\"btn\" ng-class=\"$ctrl.getAccountLanguage() == 'fi' ? 'active btn-primary disabled' : 'btn-default'\" ng-click=\"$ctrl.current.language='fi'\" sxy-text=\"SALAXY.ENUM.Language.fi.label\"></button>\r\n          <button class=\"btn\" ng-class=\"$ctrl.getAccountLanguage() == 'en' ? 'active btn-primary disabled' : 'btn-default'\" ng-click=\"$ctrl.current.language='en'\" sxy-text=\"SALAXY.ENUM.Language.en.label\"></button>\r\n          <button class=\"btn\" ng-class=\"$ctrl.getAccountLanguage() == 'sv' ? 'active btn-primary disabled' : 'btn-default'\" ng-click=\"$ctrl.current.language='sv'\" sxy-text=\"SALAXY.ENUM.Language.sv.label\"></button>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"row\">\r\n      <div class=\"col-12\">\r\n\r\n        <salaxy-input name=\"firstName\" label=\"SALAXY.MODEL.PersonAccount.identity.firstName.title\" readonly=\"true\" ng-model=\"$ctrl.current.identity.firstName\"></salaxy-input>\r\n        <salaxy-input name=\"lastName\" label=\"SALAXY.MODEL.PersonAccount.identity.lastName.title\" readonly=\"true\" ng-model=\"$ctrl.current.identity.lastName\"></salaxy-input>\r\n        <div class=\"row\">\r\n          <div class=\"col-sm-6 offset-sm-4 input-info\">\r\n            <div class=\"input-info-icon\"><i class=\"bi bi-info-circle-fill text-default\"></i></div>\r\n            <p class=\"small input-info-text with-icon \" sxy-html=\"SALAXY.NG1.AccountDetailsEditPersonComponent.nameDecription.html\"></p>\r\n          </div>\r\n          <div class=\"col-sm-2\">\r\n            <button class=\"btn btn-default float-end btn-sm\" ng-controller=\"WorkerOnboardingController as $wizard\" ng-click=\"$wizard.launch()\" sxy-text=\"SALAXY.NG1.AccountDetailsEditPersonComponent.launchWizardBtn\"></button>\r\n          </div>\r\n        </div>\r\n        <salaxy-input name=\"officialPersonId\" label=\"SALAXY.MODEL.PersonAccount.identity.officialId.title\" sxy-personal-id-fi readonly=\"true\" ng-model=\"$ctrl.current.identity.officialId\">\r\n        </salaxy-input>\r\n        <div class=\"row\">\r\n          <div class=\"col-sm-8 offset-sm-4 input-info\">\r\n            <div class=\"input-info-icon\"><i class=\"bi bi-info-circle-fill text-default\"></i></div>\r\n            <p class=\"small input-info-text with-icon\" sxy-html=\"SALAXY.NG1.AccountDetailsEditPersonComponent.personalIdDescription.html\"></p>\r\n          </div>\r\n        </div>\r\n        <salaxy-input name=\"ibanNumber\" label=\"SALAXY.MODEL.PersonAccount.identity.ibanNumber.title\" sxy-iban ng-model=\"$ctrl.current.identity.ibanNumber\"></salaxy-input>\r\n      </div>\r\n      <div class=\"col-12 text-end\">\r\n        <button ng-click=\"$ctrl.saveCurrent()\" ng-disabled=\"workerForm.$invalid\" class=\"btn btn-primary\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n      </div>\r\n    </div>\r\n  </form>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/personal/AccountDetailsPerson.html\",`<div class=\"salaxy-component salaxy-account-details-person\">\r\n  <div class=\"row\">\r\n    <div class=\"col-12  col-md-4 account-info-container\">\r\n      <div class=\"light-bg\">\r\n        <div class=\"worker-avatar-wrapper\">\r\n          <salaxy-account-info-person></salaxy-account-info-person>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"col-12 col-md-8\" ng-if=\"$ctrl.current\">\r\n      <div>\r\n        <salaxy-tab-buttons\r\n          current-tab=\"$ctrl.currentTab\"\r\n          options=\"[\r\n            { value: 'default', text: 'SALAXY.NG1.AccountDetailsPersonComponent.personalInfoTabHeading' },\r\n            { value: 'contact', text: 'SALAXY.NG1.AccountDetailsPersonComponent.contactInfoTabHeading' },\r\n            { value: 'avatar', text: 'SALAXY.NG1.AccountDetailsPersonComponent.avatarTabHeading' },\r\n            { value: 'identity', text: 'SALAXY.NG1.AccountDetailsPersonComponent.authorizationTabHeading' },\r\n            { value: 'insurance', text: 'SALAXY.NG1.AccountDetailsPersonComponent.insurancesTabHeading', hidden: !('household' | sxyIsInRole) }\r\n          ]\"\r\n          tabs-id=\"accountDetailsPerson\">\r\n        </salaxy-tab-buttons>\r\n        <div class=\"tab-content\" id=\"tab-content-accountDetailsPerson\">\r\n          <div class=\"tab-pane\" id=\"default-tab\">\r\n            <salaxy-account-details-edit-person current=\"$ctrl.current\"></salaxy-account-details-edit-person>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"contact-tab\">\r\n            <salaxy-account-contact-edit-person current=\"$ctrl.current\"></salaxy-account-contact-edit-person>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"avatar-tab\">\r\n            <salaxy-account-avatar-edit-person current=\"$ctrl.current\"></salaxy-account-avatar-edit-person>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"identity-tab\">\r\n            <salaxy-account-authorization-person></salaxy-account-authorization-person>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"insurance-tab\" ng-if=\"'household' | sxyIsInRole\">\r\n            <salaxy-account-insurance-edit-person></salaxy-account-insurance-edit-person>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"col-12\" sxy-if-role=\"test\">\r\n      <hr />\r\n      <p>Test only:</p>\r\n      <ul ng-controller=\"SessionController as $session\">\r\n        <li>\r\n          Last login as (session):\r\n          <strong>{{ $session.person.lastLoginAs }}</strong> (isEmployer: {{$session.person.isEmployer}}, isWorker: {{$session.person.isWorker}})\r\n        </li>\r\n        <li>\r\n          Server-side:\r\n          <strong>{{ $ctrl.current.lastLoginAs }}</strong> (isEmployer: {{$ctrl.current.isEmployer}}, isWorker: {{$ctrl.current.isWorker}})\r\n        </li>\r\n        <li>\r\n          Vaihda roolia:\r\n          <a ng-click=\"$session.switchRole('household')\">Kotitalous</a>\r\n          <a ng-click=\"$session.switchRole('worker')\">Työntekijä</a>\r\n        </li>\r\n      </ul>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/personal/AccountInfoPerson.html\",`<div class=\"salaxy-component salaxy-account-info-person d-flex\">\r\n  <div class=\"worker-avatar-wrapper\">\r\n    <salaxy-avatar avatar=\"$ctrl.avatar\"></salaxy-avatar>\r\n  </div>\r\n  <div class=\"info-wrapper w-100 ms-2 ms-sm-0\">\r\n    <h2>{{ $ctrl.person.avatar.displayName || (\"SALAXY.NG1.AccountInfoPersonComponent.noSelection\" | sxyTranslate) }}</h2>\r\n    <div class=\"account-info-contact-details\">\r\n      <span ng-if=\"$ctrl.person.contact.telephone\">{{$ctrl.person.contact.telephone}}</span>\r\n      <br /> {{ $ctrl.person.contact.email }}\r\n      <br />\r\n      <span ng-if=\"$ctrl.person.identity.ibanNumber\">\r\n        {{ $ctrl.person.identity.ibanNumber | sxyIban }}\r\n      </span>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/personal/AccountInsuranceEditPerson.html\",`<div class=\"salaxy-component salaxy-account-insurance-edit-person\">\r\n  <form name=\"insuranceForm\" class=\"form-horizontal\">\r\n    <legend>Tapaturmavakuutus</legend>\r\n    <div class=\"input-info\">\r\n      <div class=\"input-info-icon\"><i class=\"bi bi-info-circle-fill text-default\"></i></div>\r\n      <p class=\"small input-info-text with-icon\">\r\n        Lakisääteinen tapaturmavakuutus on työnantajalle pakollinen, jos maksat palkkaa kaikille työntekijöillesi yhteensä\r\n        <strong>väh. 1500€</strong> kalenterivuoden aikana. Vakuutus on työnantajan vakuutus, joka kattaa kaikki hänen työntekijänsä.\r\n      </p>\r\n      <p class=\"small input-info-text with-icon\" ng-if=\"($ctrl.personal.insurance.company || 'none') == 'none'\">\r\n        Saat hankittua työnantajan lakisääteisen työtapaturmavakuutuksen omasta vakuutusyhtiöstäsi.\r\n        <strong>HUOM:</strong> Vakuutus pitää olla voimassa ennen töiden aloittamista.\r\n      </p>\r\n    </div>\r\n    <div>\r\n      <p>\r\n        <b>Anna voimassa olevan vakuutuksen tiedot.</b> Valitse \"Ei yhtiötä\", jos sinulla ei ole vakuutusta.\r\n      </p>\r\n      <salaxy-input-enum ng-model=\"$ctrl.personal.insurance.company\" type=\"select\" enum=\"InsuranceCompany\" filter=\"none,fennia,if,lähiTapiola,pohjantähti,pohjola,turva,aVakuutus,folksam,alandia,ålands\" label=\"SALAXY.MODEL.InsuranceContract.company.editLabel\"\r\n        name=\"insurance-company\" require=\"true\"></salaxy-input-enum>\r\n      <div ng-if=\"($ctrl.personal.insurance.company || 'none') != 'none'\">\r\n        <salaxy-input ng-model=\"$ctrl.personal.insurance.contractNumber\" require=\"true\" name=\"insuranceContractNumber\" label=\"SALAXY.MODEL.InsuranceContract.contractNumber.title\">\r\n        </salaxy-input>\r\n        <salaxy-form-group name=\"insuranceWarning\" label-type=\"empty-label\">\r\n          <small>Tähän syötetyt vakuutustiedot näkyvät myös työntekijän palkkalaskelmassa.</small>\r\n        </salaxy-form-group>\r\n      </div>\r\n    </div>\r\n    <div class=\"text-end\">\r\n      <button ng-disabled=\"!$ctrl.personal.insurance.company || $ctrl.isSaving('insuranceContracts')\" class=\"btn btn-primary\" ng-click=\"$ctrl.save('insuranceContracts')\"><i\r\n          ng-if=\"$ctrl.isSaving('insuranceContracts')\" class=\"bi bi-arrow-repeat bi-spin\"></i>\r\n        <span sxy-text=\"SALAXY.UI_Terms.save\"></span></button>\r\n    </div>\r\n  </form>\r\n  <form name=\"pensionForm\" class=\"form-horizontal\">\r\n    <legend>TYEL-sopimus</legend>\r\n    <div class=\"input-info\">\r\n      <div class=\"input-info-icon\"><i class=\"bi bi-info-circle-fill text-default\"></i></div>\r\n      <p class=\"small input-info-text with-icon\">\r\n        Palkkaus.fi-palvelu ilmoittaa TyEL-ilmoitukset tulorekisteriin oletuksena suoraan työeläkeyhtiö Varman kautta ja Varma lähettää näistä laskun jälkikäteen.\r\n        <strong>Tilapäinen työnantaja ei tarvitse siihen sopimusta.</strong>\r\n        <br> Jos sinulla on jatkuva työsopimus tai maksat palkkaa yli {{ $ctrl.sideCosts.tyelContractEmployerLimit | currency}} puolessa vuodessa, suosittelemme tekemään sopimuksen työeläkeyhtiön kanssa.\r\n      </p>\r\n    </div>\r\n    <div>\r\n      <p>\r\n        <b>Anna voimassa olevan sopimuksen tiedot.</b> Valitse \"Ei yhtiötä\", jos olet tilapäinen työnantaja.\r\n      </p>\r\n      <salaxy-input-enum ng-model=\"$ctrl.personal.pension.company\" type=\"select\" label=\"SALAXY.MODEL.PensionContract.company.editLabel\" name=\"pensionCompany\" enum=\"PensionCompany\" filter=\"none,varma,elo,ilmarinen,veritas,apteekkien,verso,valio,kevaMunicipal,kevaAland,kevaChurch,kevaKela,kevaState\" require=\"true\"></salaxy-input-enum>\r\n      <div salaxy-if-role=\"test\" class=\"test-number\">\r\n        <div class=\"form-group\" ng-if=\"$ctrl.personal.pension.company && $ctrl.personal.pension.company != 'none'\">\r\n          <div class=\"col-sm-8 offset-sm-4 text-sm-end\">\r\n            <span>Test only: <button class=\"btn btn-secondary btn-xs\" ng-click=\"$ctrl.setPensionNumberForTest($ctrl.personal.pension)\"> Generoi numero </button></span>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <salaxy-input ng-if=\"$ctrl.personal.pension.company && $ctrl.personal.pension.company != 'none'\" require=\"true\" name=\"pensionContractNumber\" label=\"SALAXY.MODEL.PensionContract.contractNumber.title\" ng-model=\"$ctrl.personal.pension.contractNumber\" tooltip-html=\"{{'SALAXY.NG1.InsuranceSettingsComponent.pension.errors.sxyPensionContractNumber.html' | sxyTranslate}}\"\r\n        tooltip-placement=\"right\" sxy-pension-contract-number></salaxy-input>\r\n    </div>\r\n    <div ng-show=\"pensionForm.pensionContractNumber.$error.sxyTemporaryPensionContractNumber\">\r\n      <div class=\"input-info text-danger\">\r\n        <div class=\"input-info-icon\"><i class=\"bi bi-exclamation-triangle-fill \"></i></div>\r\n        <p class=\"small input-info-text with-icon\" sxy-html=\"SALAXY.NG1.InsuranceSettingsComponent.pension.errors.sxyTemporaryPensionContractNumber.html\"></p>\r\n      </div>\r\n    </div>\r\n    <div class=\"text-end\">\r\n      <button ng-disabled=\"!$ctrl.personal.pension.company || pensionForm.$invalid || $ctrl.isSaving('pensionContracts')\" class=\"btn btn-primary\" ng-click=\"$ctrl.save('pensionContracts')\"><i ng-if=\"$ctrl.isSaving('pensionContracts')\" class=\"bi bi-arrow-repeat bi-spin\"></i>\r\n        <span sxy-text=\"SALAXY.UI_Terms.save\"></span></button>\r\n    </div>\r\n  </form>\r\n  <div>\r\n    <legend>Työttömyysvakuutus</legend>\r\n    <div class=\"input-info\">\r\n      <div class=\"input-info-icon\"><i class=\"bi bi-info-circle-fill text-default\"></i></div>\r\n      <p class=\"small input-info-text with-icon\">\r\n        Työttömyysvakuutusmaksuja ei voi maksaa Palkkaus.fi-palvelun kautta, koska <a href=\"https://www.tyollisyysrahasto.fi/\" target=\"_blank\">Työllisyysrahasto</a> laskuttaa työnantajia suoraan neljännesvuosittain, jos työnantaja maksaa palkkaa vähintään\r\n        1500€ kalenterivuoden aikana.\r\n      </p>\r\n      <p class=\"small input-info-text with-icon\">\r\n        Maksut näkyvät laskelmilla, ne ilmoitetaan tulorekisteriin eikä niiden takia tarvitse tehdä mitään muuta, kuin maksaa Työllisyysrahastolta aikanaan tulevat laskut.\r\n      </p>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/personal/CalcHouseholdUsecase.html\",`<div class=\"salaxy-component salaxy-calc-household-usecase\">\r\n  <form ng-submit=\"$ctrl.submitHouseholdUsecase()\" ng-readonly=\"$ctrl.isReadOnly\" name=\"detailsUsecase\" class=\"form-horizontal\">\r\n    <div class=\"salaxy-calc-dialog-body\">\r\n      <div class=\"salaxy-calc-dialog-container\">\r\n        <div class=\"row\">\r\n          <div class=\"col-md-5 col-12\" ng-if=\"$ctrl.isReadOnly\">\r\n            <button type=\"button\" class=\"btn btn-primary btn-sm\" ng-click=\"$ctrl.startEdit()\" sxy-text=\"SALAXY.UI_Terms.edit\"></button>\r\n          </div>\r\n          <div class=\"col-md-5 col-12\" ng-if=\"!$ctrl.isReadOnly\">\r\n            <h1 ng-if=\"!$ctrl.isUsecaseSelected\" sxy-text=\"SALAXY.NG1.HouseholdUsecaseComponent.ui.selectionTitle\" class=\"choose-usecase\"></h1>\r\n            <div ng-if=\"$ctrl.isUsecaseSelected\" class=\"mb-2 \">\r\n              <div ng-if=\"$ctrl.showSave\" class=\"mb-2\">\r\n                <button type=\"button\" class=\"btn btn-primary btn-sm\" ng-click=\"$ctrl.saveEmployment()\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n                <button type=\"button\" class=\"btn btn-secondary btn-sm\" ng-click=\"$ctrl.resetEmployment()\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n                <button ng-if=\"$ctrl.isUsecaseSelected\" class=\"btn btn-secondary btn-sm\" type=\"button\" ng-click=\"$ctrl.resetUsecase()\"><span\r\n                  HouseholdUsecaseComponent></span></button>\r\n              </div>\r\n              <button ng-if=\"$ctrl.isUsecaseSelected && !$ctrl.showSave\" class=\"btn btn-secondary btn-sm btn-labeled-left\" type=\"button\" ng-click=\"$ctrl.resetUsecase()\"><i\r\n                  class=\"bi bi-chevron-left\"></i><span sxy-text=\"SALAXY.NG1.HouseholdUsecaseComponent.ui.changeSelection\"></span></button>\r\n            </div>\r\n            <div ng-if=\"$ctrl.isUsecaseSelected && !$ctrl.isEmployment\" style=\"padding-top:15px;\">\r\n              <h1 sxy-text=\"SALAXY.NG1.HouseholdUsecaseComponent.ui.salaryDate\"></h1>\r\n              <p sxy-text=\"SALAXY.NG1.HouseholdUsecaseComponent.ui.salaxyDateInfo.html\"></p>\r\n              <div class=\"form-horizontal\">\r\n                <salaxy-datepicker-popup name=\"requestedSalaryDate\" ng-model=\"$ctrl.requestedSalaryDate\" label=\"SALAXY.NG1.CalcWorktimeComponent.salaryDateLabel\" label-cols=\"col-sm-6\" date-disabled=\"salary\" placeholder=\"SALAXY.NG1.HouseholdUsecaseComponent.datePickerPlaceHolder\"\r\n                zero-payment=\"$ctrl.isCurrentZeroPayment\" payment-channel=\"$ctrl.calc.info.paymentChannel\"></salaxy-datepicker-popup>\r\n              </div>\r\n              <h1 sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.worktime.title\"></h1>\r\n              <p ng-if=\"!$ctrl.dateRange.start || !$ctrl.dateRange.start\" sxy-text=\"SALAXY.NG1.CalcWorktimeComponent.worktime.description\"></p>\r\n              <div class=\"form-horizontal\">\r\n                <salaxy-input-enum ng-model=\"$ctrl.periodShortcut\" name=\"periodShortcut\" ng-if=\"!$ctrl.periodShortcut\" label=\"SALAXY.NG1.CalcWorktimeComponent.worktime.periodShortcut.label\" label-cols=\"col-sm-6\" type=\"radio\" options=\"$ctrl.periodShortcuts\"></salaxy-input-enum>\r\n                <salaxy-input-enum ng-model=\"$ctrl.periodShortcut\" name=\"periodShortcut\" ng-if=\"$ctrl.periodShortcut\" label=\"SALAXY.NG1.CalcWorktimeComponent.worktime.periodShortcut.label\" label-cols=\"col-sm-6\" type=\"select\" options=\"$ctrl.periodShortcuts\"></salaxy-input-enum>\r\n                <salaxy-date-range ng-model=\"$ctrl.dateRange\" class=\"condensed\" name=\"dateRange\" ng-if=\"$ctrl.periodShortcut == 'other'\" on-change=\"$ctrl.dateRangeChange()\" label=\"SALAXY.NG1.CalcWorktimeComponent.worktime.periodShortcut.label\" label-days-count=\"SALAXY.NG1.CalcWorktimeComponent.worktime.periodShortcut.labelDaysCount\"\r\n                  label-cols=\"col-sm-6\" read-only=\"$ctrl.isReadOnly\"></salaxy-date-range>\r\n                <div ng-if=\"$ctrl.periodShortcut && $ctrl.periodShortcut != 'other'\">\r\n                  <salaxy-form-group name=\"periodStartDate\" label=\"SALAXY.NG1.CalcWorktimeComponent.worktime.periodShortcut.labelStartDate\" label-cols=\"col-sm-6\">\r\n                    <input type=\"text\" class=\"form-control\" autocomplete=\"off\" id=\"periodStartDate\" name=\"periodStartDate\" placeholder=\"{{'SALAXY.UI_Terms.dateFormats.dm' | sxyTranslate}}\" ng-model=\"$ctrl.periodStartDate\" ng-model-options=\"{allowInvalid: true, debounce: 250, updateOn: 'default' }\"\r\n                    />\r\n                    <div ng-if=\"$ctrl.periodStartDateError\" class=\"form-control-plaintext text-danger\">{{ $ctrl.periodStartDateError | sxyTranslate }}</div>\r\n                  </salaxy-form-group>\r\n                  <salaxy-form-group name=\"formattedRange\" label=\"SALAXY.NG1.CalcWorktimeComponent.worktime.periodShortcut.labelStartAndEndDate\" label-cols=\"col-sm-6\" class=\"salaxy-read-only\">\r\n                    <div class=\"form-control-plaintext\">{{ $ctrl.dateRange | sxyDateRange }}</div>\r\n                  </salaxy-form-group>\r\n                  <salaxy-input-number name=\"labelDaysCount\" ng-model=\"$ctrl.dateRange.daysCount\" ng-change=\"$ctrl.dateRangeChange()\" label=\"SALAXY.NG1.CalcWorktimeComponent.worktime.periodShortcut.labelWorkDaysCount\" label-cols=\"col-sm-6\">\r\n                  </salaxy-input-number>\r\n                </div>\r\n              </div>\r\n            </div>\r\n            <div class=\"accordion salaxy-accordion\" ng-if=\"!$ctrl.isUsecaseSelected\">\r\n              <div class=\"accordion-item\" ng-repeat=\"group in $ctrl.tree\">\r\n                <h2 class=\"accordion-header\">\r\n                  <button class=\"accordion-button\" type=\"button\" data-bs-toggle=\"collapse\" data-bs-target=\"#group{{ $index }}\" aria-expanded=\"false\">\r\n                    {{group.label}} <i class=\"float-end bi\" ng-class=\"{'bi-chevron-up': status.open, 'bi-chevron-down': !status.open}\"></i>\r\n                    <br><small>{{group.descr}}</small>\r\n                  </button>\r\n                </h2>\r\n                <div id=\"group{{ $index }}\" class=\"accordion-collapse collapse\" ng-class=\"{'show': status.open}\">\r\n                  <div class=\"accordion-body\" id=\"child-list\">\r\n                    <div ng-repeat=\"child in group.children\" ng-click=\"$ctrl.selectUsecase(child)\" class=\"clickable usecase-selection\">\r\n                      <div class=\"icon-wrapper salaxy-household-usecase-avatar\">\r\n                        <div class=\"main-icon-wrapper\">\r\n                          <img ng-src=\"{{child.icon}}\">\r\n                        </div>\r\n                        <div ng-if=\"child.badge\" class=\"badge-image-wrapper\">\r\n                          <img ng-src=\"{{child.badge}}\">\r\n                        </div>\r\n                      </div>\r\n                      <strong class=\"usecase-title\">{{child.label}}</strong>\r\n                      <small>{{child.descr |sxyTranslate}}</small>\r\n                    </div>\r\n                  </div>\r\n                </div>\r\n              </div>\r\n            </div>\r\n          </div>\r\n          <div class=\"col-md-7 col-12 panel-detail usecase-details\" ng-if=\"$ctrl.isUsecaseSelected\">\r\n            <ng-include src=\"$ctrl.getTemplate()\"></ng-include>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <button ng-if=\"!$ctrl.isReadOnly && !$ctrl.isEmployment\" class=\"btn btn-warning btn-lg salaxy-calc-btn-recalculate\" type=\"submit\" sxy-text=\"SALAXY.UI_Terms.updateCalculation\"></button>\r\n  </form>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/personal/CalcSharing.html\",`<div class=\"salaxy-component salaxy-calc-sharing\">\r\n  <button class=\"btn btn-secondary btn-labeled-left btn-sm mb-2\" ng-click=\"$ctrl.showDetails($ctrl.current)\"><i class=\"bi bi-chevron-left\"></i> <span sxy-text=\"SALAXY.NG1.CalcSharingComponent.backBtn\"></span></button>\r\n  <p ng-if=\"$ctrl.showLinkSharing\" class=\"calc-sharing-instructions\" sxy-html=\"SALAXY.NG1.CalcSharingComponent.intro.html\"></p>\r\n  <div class=\"mb-2\" ng-if=\"$ctrl.showLinkSharing\">\r\n\r\n    <h3 sxy-text=\"SALAXY.NG1.CalcSharingComponent.sharing.title\"></h3>\r\n    <p class=\"mb-2\" sxy-text=\"SALAXY.NG1.CalcSharingComponent.sharing.description\"></p>\r\n    <button ng-click=\"$ctrl.share('url')\" class=\"btn btn-primary btn-sm\">\r\n      <span ng-show=\"$ctrl.isSharing('url')\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span> <span sxy-text=\"SALAXY.NG1.CalcSharingComponent.sharing.createLinkBtn\"></span>\r\n     </button>\r\n\r\n  </div>\r\n\r\n  <h3 sxy-text=\"SALAXY.NG1.CalcSharingComponent.select.title\"></h3>\r\n  <p sxy-text=\"SALAXY.NG1.CalcSharingComponent.select.description\"></p>\r\n\r\n  <div class=\"table-responsive salaxy-odata-table\">\r\n    <table class=\"table table-striped\">\r\n      <thead>\r\n        <tr class=\"\">\r\n          <th colspan=\"2\">\r\n            <span sxy-text=\"SALAXY.NG1_Other.Roles.employer\"></span>\r\n          </th>\r\n          <th></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.employingRelations\">\r\n          <td class=\"td-avatar middle\">\r\n            <salaxy-avatar avatar=\"row.ownerInfo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td class=\"middle\">\r\n            <strong>{{row.ownerInfo.avatar.displayName}}</strong><br />\r\n\r\n          </td>\r\n          <td class=\"middle right\">\r\n            <button class=\"btn btn-sm btn-primary\" type=\"button\" ng-click=\"$ctrl.share('employer', row)\">\r\n               <span sxy-text=\"SALAXY.UI_Terms.select\"></span>  <span ng-show=\"$ctrl.isSharing('employer'+row.ownerId)\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span>\r\n              </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n\r\n\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/personal/CalcSharingInfo.html\",`<div class=\"salaxy-component salaxy-calc-sharing-info\">\r\n  <div ng-if=\"$ctrl.current.workflow.status == 'paymentWorkerCopy'\">\r\n    <p class=\"text-center\">\r\n      <span sxy-text=\"SALAXY.NG1.CalcSharingInfoComponent.paidDate\"></span> {{ $ctrl.current.workflow.paidAt | date }}\r\n    </p>\r\n    <p>\r\n      <button type=\"button\" ng-click=\"$ctrl.showCopyAsNew($ctrl.current)\" class=\"btn btn-primary btn-block\" sxy-text=\"SALAXY.UI_Terms.copyAsNew\"></button>\r\n    </p>\r\n  </div>\r\n  <div ng-if=\"$ctrl.current.sharing.type == 'url'\">\r\n    <div ng-if=\"$ctrl.current.workflow.status == 'workerRequested'\">\r\n      <p class=\"text-center\">\r\n        <strong sxy-text=\"SALAXY.NG1.CalcSharingInfoComponent.sharedViaLink\"></strong><br>\r\n        <strong class=\"small\" ng-if=\"$ctrl.current.sharing.lastSharedTo\"><span sxy-text=\"SALAXY.NG1.CalcSharingInfoComponent.sharedViaEmail\"></span> {{$ctrl.current.sharing.lastSharedTo}}</strong> <br>\r\n        <span sxy-text=\"SALAXY.NG1.CalcSharingInfoComponent.shareToEmployer\"></span>\r\n      </p>\r\n      <form class=\"form-inline mb-2\">\r\n        <div class=\"form-group copy-share-url\">\r\n          <div class=\"input-group \" ng-class=\"{'has-success': $ctrl.uriCopied}\">\r\n            <div class=\"input-group-text clickable\" title=\"{{'SALAXY.NG1.CalcSharingInfoComponent.copyToClipBoard' | sxyTranslate}}\" type=\"button\" ng-click=\"$ctrl.copyUri()\">\r\n              <i class=\"bi bi-clipboard\"></i>\r\n              <span class=\"text-success text-center text-indicate\" ng-if=\"$ctrl.uriCopied\"><br><span sxy-text=\"SALAXY.NG1.CalcSharingInfoComponent.linkCopied\"></span></span>\r\n            </div>\r\n            <textarea class=\"form-control\" rows=\"1\" wrap=\"off\">{{$ctrl.current.sharing.uri}}</textarea>\r\n          </div>\r\n        </div>\r\n      </form>\r\n\r\n      <div ng-if=\"!$ctrl.isMobileSharingEnabled\" class=\"mb-2 text-center\">\r\n        <div ng-repeat=\"target in $ctrl.webSharingTargets\" style=\"display:inline\">\r\n          <a ng-if=\"target.action\" class=\"btn btn-transparent btn-share-calc\" title=\"{{target.title}}\" ng-click=\"target.action()\"><i style=\"font-size: xx-large\" class=\"fa\" ng-class=\"target.icon\"></i>\r\n          </a>\r\n          <a ng-if=\"!target.action\" class=\"btn btn-transparent btn-share-calc\" title=\"{{target.title}}\" ng-href=\"{{target.getUrl()}}\" target=\"_blank\"><i style=\"font-size: xx-large\" class=\"fa\" ng-class=\"target.icon\"></i>\r\n         </a>\r\n        </div>\r\n      </div>\r\n      <div ng-if=\"$ctrl.isMobileSharingEnabled\" class=\"mb-2 text-center\">\r\n        <div ng-repeat=\"target in $ctrl.mobileSharingTargets\" style=\"display:inline\">\r\n          <a ng-if=\"target.action\" class=\"btn btn-transparent btn-share-calc\" title=\"{{target.title}}\" ng-click=\"target.action()\"><i style=\"font-size: xx-large\" class=\"fa\" ng-class=\"target.icon\"></i>\r\n          {{target.title}}\r\n          </a>\r\n          <a ng-if=\"!target.action\" class=\"btn btn-transparent btn-share-calc\" title=\"{{target.title}}\" ng-href=\"{{target.getUrl()}}\" target=\"_blank\"><i style=\"font-size: xx-large\" class=\"fa\" ng-class=\"target.icon\"></i>\r\n          {{target.title}}\r\n         </a>\r\n        </div>\r\n      </div>\r\n      <div class=\"text-center mb-2\">\r\n        <button class=\"btn btn-secondary btn-sm\" ng-click=\"$ctrl.share('undefined')\"><span sxy-text=\"SALAXY.NG1.CalcSharingInfoComponent.deleteLinkBtn\"></span><span ng-show=\"$ctrl.isSharing('undefined')\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span></button>\r\n        <button class=\"btn btn-primary btn-sm\" ng-click=\"$ctrl.showCopyAsNew($ctrl.current)\" sxy-text=\"SALAXY.UI_Terms.copyAsNew\"></button>\r\n      </div>\r\n    </div>\r\n    <div ng-if=\"$ctrl.current.workflow.status == 'workerRequestAccepted'\">\r\n      <p class=\"text-center\">\r\n        <strong class=\"text-success\" sxy-text=\"SALAXY.NG1.CalcSharingInfoComponent.statusText.workerRequestAccepted\"></strong>\r\n      </p>\r\n      <div ng-if=\"$ctrl.employer\" class=\"mb-2\">\r\n        <salaxy-avatar style=\"font-size:45px;\" avatar=\"$ctrl.employer.ownerInfo.avatar\"></salaxy-avatar>\r\n        <div>\r\n          <strong>&nbsp;{{$ctrl.employer.ownerInfo.avatar.displayName}}</strong>\r\n        </div>\r\n      </div>\r\n      <div class=\"text-center mb-2\">\r\n\r\n        <button class=\"btn btn-primary btn-sm\" ng-click=\"$ctrl.showCopyAsNew($ctrl.current)\" sxy-text=\"SALAXY.UI_Terms.copyAsNew\"></button>\r\n      </div>\r\n    </div>\r\n    <div ng-if=\"$ctrl.current.workflow.status == 'workerRequestDeclined'\">\r\n      <p class=\"text-center\">\r\n        <strong class=\"text-danger\" sxy-text=\"SALAXY.NG1.CalcSharingInfoComponent.statusText.workerRequestDeclined\"></strong>\r\n      </p>\r\n      <form ng-if=\"!$ctrl.isMobileSharingEnabled\" class=\"form-inline mb-2\">\r\n        <div class=\"form-group copy-share-url\">\r\n          <div class=\"input-group \" ng-class=\"{'has-success': $ctrl.uriCopied}\">\r\n            <div class=\"input-group-text clickable\" title=\"{{'SALAXY.NG1.CalcSharingInfoComponent.copyToClipBoard' | sxyTranslate}}\" type=\"button\" ng-click=\"$ctrl.copyUri()\">\r\n              <i class=\"bi bi-clipboard\"></i>\r\n              <span class=\"text-success text-center text-indicate\" ng-if=\"$ctrl.uriCopied\"><br><span sxy-text=\"SALAXY.NG1.CalcSharingInfoComponent.linkCopied\"></span></span>\r\n            </div>\r\n            <textarea class=\"form-control\" rows=\"1\" wrap=\"off\">{{$ctrl.current.sharing.uri}}</textarea>\r\n          </div>\r\n        </div>\r\n      </form>\r\n\r\n      <div ng-if=\"!$ctrl.isMobileSharingEnabled\" class=\"mb-2 text-center\">\r\n        <div ng-repeat=\"target in $ctrl.webSharingTargets\" style=\"display:inline\">\r\n          <a ng-if=\"target.action\" class=\"btn btn-transparent btn-share-calc\" title=\"{{target.title}}\" ng-click=\"target.action()\"><i style=\"font-size: xx-large\" class=\"fa\" ng-class=\"target.icon\"></i>\r\n          </a>\r\n          <a ng-if=\"!target.action\" class=\"btn btn-transparent btn-share-calc\" title=\"{{target.title}}\" ng-href=\"{{target.getUrl()}}\" target=\"_blank\"><i style=\"font-size: xx-large\" class=\"fa\" ng-class=\"target.icon\"></i>\r\n         </a>\r\n        </div>\r\n      </div>\r\n      <div ng-if=\"$ctrl.isMobileSharingEnabled\" class=\"mb-2 text-center\">\r\n        <div ng-repeat=\"target in $ctrl.mobileSharingTargets\" style=\"display:inline\">\r\n          <a ng-if=\"target.action\" class=\"btn btn-transparent btn-share-calc\" title=\"{{target.title}}\" ng-click=\"target.action()\"><i style=\"font-size: xx-large\" class=\"fa\" ng-class=\"target.icon\"></i>\r\n          {{target.title}}\r\n          </a>\r\n          <a ng-if=\"!target.action\" class=\"btn btn-transparent btn-share-calc\" title=\"{{target.title}}\" ng-href=\"{{target.getUrl()}}\" target=\"_blank\"><i style=\"font-size: xx-large\" class=\"fa\" ng-class=\"target.icon\"></i>\r\n          {{target.title}} \r\n         </a>\r\n        </div>\r\n      </div>\r\n      <div class=\"text-center mb-2\">\r\n        <button class=\"btn btn-secondary btn-sm\" ng-click=\"$ctrl.share('undefined')\"><span sxy-text=\"SALAXY.NG1.CalcSharingInfoComponent.deleteLinkBtn\"></span><span ng-show=\"$ctrl.isSharing('undefined')\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span></button>\r\n        <button class=\"btn btn-primary btn-sm\" ng-click=\"$ctrl.showCopyAsNew($ctrl.current)\" sxy-text=\"SALAXY.UI_Terms.copyAsNew\"></button>\r\n      </div>\r\n    </div>\r\n  </div>\r\n\r\n  <div ng-if=\"$ctrl.current.sharing.type == 'employer'\" class=\"text-center\">\r\n    <div ng-if=\"$ctrl.current.workflow.status == 'workerRequested'\">\r\n      <p class=\"text-center\"><strong class=\"text-warning\" sxy-text=\"SALAXY.NG1.CalcSharingInfoComponent.statusText.workerRequested\"></strong></p>\r\n      <div ng-if=\"$ctrl.employer\" class=\"mb-2\">\r\n        <salaxy-avatar style=\"font-size:45px;\" avatar=\"$ctrl.employer.ownerInfo.avatar\"></salaxy-avatar>\r\n        <div>\r\n          <strong>&nbsp;{{$ctrl.employer.ownerInfo.avatar.displayName}}</strong>\r\n        </div>\r\n      </div>\r\n      <button class=\"btn btn-secondary btn-sm\" ng-click=\"$ctrl.share('undefined')\"><span sxy-text=\"SALAXY.NG1.CalcSharingInfoComponent.cancelDeliveryBtn\"></span> <span ng-show=\"$ctrl.isSharing('undefined')\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span></button>\r\n      <button class=\"btn btn-primary btn-sm\" ng-click=\"$ctrl.showCopyAsNew($ctrl.current)\" sxy-text=\"SALAXY.UI_Terms.copyAsNew\"></button>\r\n\r\n    </div>\r\n    <div ng-if=\"$ctrl.current.workflow.status == 'workerRequestAccepted'\">\r\n      <p class=\"text-center\"><strong class=\"text-success\" sxy-text=\"SALAXY.NG1.CalcSharingInfoComponent.statusText.workerRequestAccepted\"></strong></p>\r\n      <div ng-if=\"$ctrl.employer\" class=\"mb-2\">\r\n        <salaxy-avatar style=\"font-size:45px;\" avatar=\"$ctrl.employer.ownerInfo.avatar\"></salaxy-avatar>\r\n        <div>\r\n          <strong>&nbsp;{{$ctrl.employer.ownerInfo.avatar.displayName}}</strong>\r\n        </div>\r\n      </div>\r\n\r\n      <button class=\"btn btn-primary btn-sm\" ng-click=\"$ctrl.showCopyAsNew($ctrl.current)\" sxy-text=\"SALAXY.UI_Terms.copyAsNew\"></button>\r\n    </div>\r\n    <div ng-if=\"$ctrl.current.workflow.status == 'workerRequestDeclined'\">\r\n      <p class=\"text-center\"><strong class=\"text-danger\" sxy-text=\"SALAXY.NG1.CalcSharingInfoComponent.statusText.workerRequestDeclined\"></strong></p>\r\n      <div ng-if=\"$ctrl.employer\" class=\"mb-2\">\r\n        <salaxy-avatar style=\"font-size:45px;\" avatar=\"$ctrl.employer.ownerInfo.avatar\"></salaxy-avatar>\r\n        <div>\r\n          <strong>&nbsp;{{$ctrl.employer.ownerInfo.avatar.displayName}}</strong>\r\n        </div>\r\n      </div>\r\n      <button class=\"btn btn-secondary btn-sm\" ng-click=\"$ctrl.share('undefined')\"><span sxy-text=\"SALAXY.NG1.CalcSharingInfoComponent.cancelDeliveryBtn\"></span> <span ng-show=\"$ctrl.isSharing('undefined')\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span></button>\r\n      <button class=\"btn btn-primary btn-sm\" ng-click=\"$ctrl.showCopyAsNew($ctrl.current)\" sxy-text=\"SALAXY.UI_Terms.copyAsNew\"></button>\r\n    </div>\r\n  </div>\r\n  <div ng-if=\"$ctrl.current.sharing.type == 'undefined'\">\r\n    <p ng-if=\"$ctrl.current.workflow.status == 'workerRequested'\" class=\"text-center\"><strong sxy-text=\"SALAXY.NG1.CalcSharingInfoComponent.statusText.workerRequestedAlt\"></strong></p>\r\n    <p ng-if=\"$ctrl.current.workflow.status == 'workerRequestAccepted'\" class=\"text-center\"><strong class=\"text-success\" sxy-text=\"SALAXY.NG1.CalcSharingInfoComponent.statusText.workerRequestAccepted\"></strong></p>\r\n    <p ng-if=\"$ctrl.current.workflow.status == 'workerRequestDeclined'\" class=\"text-center\"><strong class=\"text-danger\" sxy-text=\"SALAXY.NG1.CalcSharingInfoComponent.statusText.workerRequestDeclined\"></strong></p>\r\n    <button ng-if=\"$ctrl.validation.isValid && ( !$ctrl.current.isReadOnly || $ctrl.current.workflow.status == 'workerRequestDeclined')\" class=\"btn btn-primary btn-block\" ng-click=\"$ctrl.showSharing()\" sxy-text=\"SALAXY.NG1.CalcSharingInfoComponent.sendToEmployerBtn\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/personal/EmployerList.html\",`<div class=\"salaxy-component salaxy-employer-list\">\r\n  <div class=\"list-group avatar-list-group\">\r\n    <div ng-repeat=\"row in $ctrl.selectedItems\" class=\"list-group-item\">\r\n      <div class=\"list-group-item-content-wrapper d-flex flex-wrap align-items-center\">\r\n        <salaxy-avatar avatar=\"row.ownerInfo.avatar\" class=\"icon-wrapper\"></salaxy-avatar>\r\n        <div class=\"list-group-item-text-wrapper ms-3 d-flex flex-column\">\r\n          <div class=\"list-group-item-heading\">{{row.ownerInfo.avatar.displayName}}</div>\r\n          <div class=\"list-group-item-text\">{{row.ownerInfo.email}}</div>\r\n        </div>\r\n        <button ng-click=\"$ctrl.setEmployerSelected(row, false);\" class=\"btn btn-sm btn-default ms-auto\" sxy-text=\"SALAXY.UI_Terms.change\"></button>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div ng-if=\"!$ctrl.selectedItems.length\">\r\n\r\n    <div class=\"table-responsive\">\r\n      <table class=\"table table-striped\">\r\n        <thead>\r\n          <tr class=\"\">\r\n            <th colspan=\"2\">\r\n              <span class=\"clickable\" sxy-text=\"SALAXY.NG1_Other.Roles.employer\"></span>\r\n            </th>\r\n            <th>\r\n              <span sxy-text=\"SALAXY.NG1.WorkerListComponent.employment\"></span><br />\r\n              <span class=\"small\"><span sxy-text=\"SALAXY.UI_Terms.updated\"></span></span>\r\n            </th>\r\n            <!--th sxy-text=\"Palkkoja maksettu\"></th-->\r\n            <th class=\"right\"> </th>\r\n          </tr>\r\n        </thead>\r\n\r\n        <tbody>\r\n          <tr ng-repeat=\"row in $ctrl.employingRelations\">\r\n            <td class=\"td-avatar middle\">\r\n              <salaxy-avatar avatar=\"row.ownerInfo.avatar\"></salaxy-avatar>\r\n            </td>\r\n            <td class=\"td-name middle\">\r\n              <strong>{{row.ownerInfo.avatar.displayName}}</strong><br />\r\n              <span class=\"sm-description\">\r\n              {{row.ownerInfo.email}}\r\n            </span>\r\n            </td>\r\n            <td class=\"middle\">\r\n              {{ row.data | sxyDateRange }}<br /> <small>{{ row.updatedAt | date}}</small>\r\n            \r\n            </td>\r\n            <!--td class=\"middle\">\r\n            <span class=\"\">TODO: viimeisin palkka (pvm)</span><br>\r\n            <span class=\"\">TODO: tänä vuonna yht €</span>\r\n          </td-->\r\n            <td class=\"right middle\">\r\n              <button class=\"btn btn-sm btn-default\" sxy-text=\"SALAXY.UI_Terms.calculations\" ng-click=\"$ctrl.setEmployerSelected(row, true)\"></button>\r\n              <!-- TODO button class=\"btn btn-sm btn-default\" sxy-text=\"SALAXY.UI_Terms.newCalculation\"></button-->\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n\r\n  </div>\r\n\r\n\r\n\r\n  <salaxy-odata-table ng-if=\"$ctrl.selectedItems.length\" url=\"/v03/api/calculations/category/all\" crud-controller=\"CalculationCrudController as $crud\" options=\"{ $filter: 'otherId eq \\\\'' + $ctrl.employerId + '\\\\' and (status eq \\\\'paymentWorkerCopy\\\\' or status eq \\\\'workerRequested\\\\' or status eq \\\\'workerRequestAccepted\\\\' or status eq \\\\'workerRequestDeclined\\\\') ' }\"\r\n    template-url=\"salaxy-components/odata/lists/CalculationsEmployer.html\">\r\n  </salaxy-odata-table>\r\n\r\n</div>\r\n\r\n<div class=\"salaxy-component salaxy-employer-list d-none\">\r\n  <div ng-if=\"!$ctrl.employingRelations.length\" class=\"\">\r\n    <h2>Ei työnantajia</h2>\r\n  </div>\r\n  <div ng-if=\"$ctrl.employingRelations.length\" class=\"\">\r\n    <div class=\"list-group avatar-list-group\">\r\n      <div class=\"list-group-item list-group-header\">\r\n\r\n\r\n        <div class=\"list-group-item-content-wrapper one-third\">\r\n          <div class=\"list-group-item-text-wrapper\">\r\n            <p class=\"list-group-item-heading\">Työnantaja</p>\r\n          </div>\r\n        </div>\r\n        <div class=\"list-group-item-content-wrapper one-fifth\">\r\n          <div class=\"list-group-item-text-wrapper\">\r\n            <p class=\"list-group-item-heading\">Työsuhde alkanut<br>...päivitetty</p>\r\n\r\n          </div>\r\n        </div>\r\n        <div class=\"list-group-item-content-wrapper one-fifth\">\r\n          <div class=\"list-group-item-text-wrapper\">\r\n            <p class=\"list-group-item-heading\">Työsuhde alkanut<br> ...päivitetty\r\n            </p>\r\n\r\n          </div>\r\n        </div>\r\n      </div>\r\n\r\n\r\n\r\n      <div ng-repeat=\"row in $ctrl.employingRelations\" class=\"list-group-item\">\r\n\r\n        <div class=\"list-group-item-content-wrapper one-third\">\r\n          <salaxy-avatar avatar=\"row.ownerInfo.avatar\" class=\"float-start icon-wrapper\"></salaxy-avatar>\r\n          <div class=\"list-group-item-text-wrapper\">\r\n\r\n            <h4 class=\"list-group-item-heading\">{{row.ownerInfo.avatar.displayName}}</h4>\r\n            <p class=\"list-group-item-text\">{{row.ownerInfo.email}}</p>\r\n          </div>\r\n        </div>\r\n        <div class=\"list-group-item-content-wrapper one-fifth\">\r\n          <div class=\"list-group-item-text-wrapper\">\r\n            <h4 class=\"list-group-item-heading\">{{row.createdAt | date}}</h4>\r\n            <p class=\"list-group-item-text\">{{row.updatedAt | date}}</p>\r\n          </div>\r\n        </div>\r\n        <div class=\"list-group-item-content-wrapper one-fifth\">\r\n          <div class=\"list-group-item-text-wrapper\">\r\n            <h4 class=\"list-group-item-heading\">{{row.createdAt | date}}</h4>\r\n            <p class=\"list-group-item-text\">{{row.updatedAt | date}}</p>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <button ng-click=\"$ctrl.setEmployerSelected(row, true)\" class=\"btn btn-xs btn-default\" sxy-text=\"SALAXY.UI_Terms.select\"></button>\r\n    </div>\r\n  </div>\r\n</div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/personal/EmployerReport.html\",`<div class=\"salaxy-component salaxy-employer-report mt-3\">\r\n  <salaxy-spinner heading=\"SALAXY.UI_Terms.loading\" ng-if=\"!$ctrl.currentReport\"></salaxy-spinner>\r\n  <div class=\"d-flex align-items-center float-end\">\r\n    <label>Valitse vuosi: </label>\r\n    <select class=\"form-select ms-2\" ng-options=\"option.name for option in $ctrl.yearOptions track by option.value\" ng-model=\"$ctrl.selectedYear\" name=\"years\" id=\"years\"></select>\r\n  </div>\r\n  <div ng-if=\"$ctrl.currentReport.employerReports.length <= 0\">\r\n    <p>\r\n      Sinulla ei ole Palkkaus.fi-palvelussa vuonna {{ $ctrl.selectedYear.value }} maksettuja palkkoja.\r\n      Vetovalikosta voit vaihtaa raportointivuotta.\r\n    </p>\r\n    <hr />\r\n    <h2>Ei palkanmaksuja vuonna {{ $ctrl.selectedYear.value }}</h2>\r\n    <p>\r\n      Kun maksat palkkoja kauttamme, edellisten vuosien palkat ja niistä tehdyt raportit jäävät arkistoon tälle sivulle.\r\n      Muut raportit kohdassa voit esikatsella muutaman yleisen raportin\r\n      ja sivun alalaidasta löydät lisätietoja työntekijäkohtaisista raporteista.\r\n    </p>\r\n  </div>\r\n  <div ng-if=\"$ctrl.currentReport.employerReports.length > 0\">\r\n    <p>\r\n      Alla näet kaikki palkanmaksut, jotka olet tehnyt Palkkaus.fi-palvelun kautta vuonna {{ $ctrl.selectedYear.value }}.\r\n    </p>\r\n    <hr />\r\n    <h3>Raportit työntekijöittäin</h3>\r\n    <p>\r\n      Alla on listattu työntekijöittäin ja palkkalaskelmittain tärkeimmät tiedot ja raportit:\r\n      Työntekijän yhteenveto ja Verottajan vuosi-ilmoitus (7801)<span ng-if=\"$ctrl.selectedYear.value < 2021\"> sekä Kotitalousvähennyksen vuosi-ilmoitus (14B)</span>.\r\n      Lisätietoja raporteista löydät sivun alalaidasta.\r\n    </p>\r\n    <table class=\"table\" ng-controller=\"WorkerSummaryReportDisplayController as $displayCtrl\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\">Työntekijä</th>\r\n          <th class=\"right\">\r\n            Bruttopalkka<br />\r\n            Verotettava\r\n          </th>\r\n          <th>Yhteenveto</th>\r\n          <th>Vero (7801)</th>\r\n          <th ng-if=\"$ctrl.selectedYear.value < 2021\">KT-väh. (14B)</th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat-start=\"report in $ctrl.currentReport.employerReports\">\r\n          <td>\r\n            <div style=\"font-size: 64px; line-height: 1\" ng-init=\"avatar = $ctrl.avatarFrom(report.worker.avatar.url)\">\r\n              <i ng-if=\"!avatar.url\" class=\"salaxy-avatar bi\" ng-class=\"avatar.baseIcon\" ng-style=\"{color: avatar.color }\"><strong>{{ avatar.initials }}</strong></i>\r\n              <i ng-if=\"avatar.url\" class=\"salaxy-avatar bi\"><img ng-src=\"{{avatar.url}}\"></img></i>\r\n            </div>\r\n          </td>\r\n          <td>\r\n            {{ report.worker.fullName}}<br />\r\n            <a ng-href=\"mailto:{{ $ctrl.workerEmailFrom(report) }}\">{{ $ctrl.workerEmailFrom(report) }}</a><br />\r\n            {{ report.worker.identity.socialSecurityNumberValid }}\r\n          </td>\r\n          <td class=\"right\">\r\n            {{ report.grossSalary | currency : \"€\" : 2}}<br />\r\n            {{ report.totalTaxable | currency : \"€\" : 2}}\r\n          </td>\r\n          <td>\r\n            <a ng-click=\"$displayCtrl.display($ctrl.selectedYear.value + '-01-01', report.worker.identity.socialSecurityNumberValid , $ctrl.employerId )\"\r\n              >Yhteenveto&nbsp;&raquo;\r\n            </a>\r\n          </td>\r\n          <td>\r\n            <a ng-if=\"$ctrl.isSelectedYearBeforeIncomesRegistry\"\r\n              href=\"{{ $ctrl.apiServerAddress }}/ReportPdf/TaxYearly7801/{{ report.worker.identity.socialSecurityNumberValid }}?year={{ $ctrl.selectedYear.value }}&access_token={{ $ctrl.token }}\"\r\n              target=\"_blank\">Tuloste&nbsp;&raquo;\r\n            </a>\r\n          </td>\r\n          <td ng-if=\"$ctrl.selectedYear.value < 2021\">\r\n            <a ng-if=\"report.totalTaxableDeductible > 0\"\r\n              ng-href=\"{{ $ctrl.apiServerAddress }}/ReportPdf/TaxHouseholdDeduction14B/{{ report.worker.identity.socialSecurityNumberValid }}?year={{ $ctrl.selectedYear.value }}&access_token={{ $ctrl.token }}\"\r\n              target=\"_blank\" class=\"\">Tuloste&nbsp;&raquo;\r\n            </a>\r\n            <p ng-if=\"report.totalTaxableDeductible <= 0\">Ei merkitty koti&shy;talous&shy;vähen&shy;nykseen.</p>\r\n          </td>\r\n        </tr>\r\n        <tr ng-repeat-end=\"\" ng-repeat=\"calculation in report.underlyingCalculations\">\r\n          <td></td>\r\n          <td>\r\n            <b ng-if=\"!$ctrl.isSelectedYearBeforeIncomesRegistry\">\r\n              {{ calculation.salaryDate | date : \"dd.MM\" }}\r\n            </b>\r\n            <b ng-if=\"$ctrl.isSelectedYearBeforeIncomesRegistry\">\r\n              {{ calculation.paidAt | date : \"dd.MM\" }}\r\n            </b>\r\n          </td>\r\n          <td class=\"right\">\r\n            {{ calculation.totals.totalGrossSalary | currency : \"€\" : 2 }}<br />\r\n            {{ calculation.totals.totalTaxable | currency : \"€\" : 2 }}\r\n          </td>\r\n          <td ng-controller=\"CalcReportsDisplayController as $displayCtrl\">\r\n            <button  ng-click=\"$displayCtrl.displayForId('salarySlip', calculation.id)\"\r\n                    class=\"btn btn-primary btn-xs\">Tuloste&nbsp;&raquo;</button><br />\r\n          <td>\r\n            {{ calculation.workerCalc.tax > 0 ? \"Ennakonpidätys: \" + (calculation.workerCalc.tax | currency : \"€\" : 2) : \"Ei ennakonpidätystä\" }}\r\n          </td>\r\n          <td ng-if=\"$ctrl.selectedYear.value < 2021\">\r\n            {{ calculation.salary.isDeductible ? \"Kotitalousvähennys: \" + (calculation.employerCalc.householdDeduction | currency : \"€\" : 2) : \"Ei lasketa kotitalousväh.\" }}\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <hr />\r\n  <br />\r\n  <h3>Muut raportit</h3>\r\n  <p>Raportit, jotka eivät ole työntekijäkohtaisia.</p>\r\n  <div class=\"row\">\r\n    <div ng-if=\"$ctrl.isSelectedYearBeforeIncomesRegistry\" class=\"col-sm-4\">\r\n      <h4>TVR Palkka&shy;summa&shy;ilmoitus</h4>\r\n      <p>\r\n        Työttömyys&shy;vakuutus&shy;rahastolle (TVR) ilmoitetaan\r\n        yhteystiedot, palkkasumma sekä tilinumero mahdollisia takaisinmaksuja varten.\r\n      </p>\r\n      <p>\r\n        <strong>\r\n          Ilmoitettava palkkasumma on: {{ $ctrl.tvrSalaryAmount | currency : \"\" : 2 }} euroa.\r\n        </strong>\r\n      </p>\r\n      <p>\r\n        Avaa <a ng-href=\"{{ $ctrl.apiServerAddress }}/ReportPdf/Unemployment?year={{ $ctrl.selectedYear.value }}&access_token={{ $ctrl.token }}\" target=\"_blank\">PDF-dokumentti\r\n          tästä linkistä</a>.\r\n      </p>\r\n    </div>\r\n    <div class=\"col-sm-4\">\r\n      <h4>Vakuutusyhtiön vuosi-ilmoitus</h4>\r\n      <p>\r\n        Vakuutus- tai työeläkeyhtiö saattaa vaatia sinulta selvitystä maksetuista palkoista vuoden ajalta.\r\n        Tämä raportti on tarkoitettu sitä varten.\r\n      </p>\r\n      <p>\r\n        <strong>\r\n          Jos olet ostanut tapaturmavakuutuksen Palkkaus.fi-palvelusta ja\r\n          olet antanut Palkkaus.fi-palvelun hoitaa TyEL-vakuutuksen,\r\n          ei tämä raportti ole tarpeellinen.\r\n        </strong>\r\n      </p>\r\n      <p>\r\n        Avaa <a ng-href=\"{{ $ctrl.apiServerAddress }}/ReportHtml/Insurance?year={{ $ctrl.selectedYear.value }}&access_token={{ $ctrl.token }}\" target=\"_blank\">Raportti tästä</a>.\r\n      </p>\r\n    </div>\r\n    <div class=\"col-sm-4\">\r\n      <h4>Raportti kotitalous&shy;vähennyksistä</h4>\r\n      <p>\r\n        Yksityiskohtainen raportti näyttää yhdessä näkymässä kaikki\r\n        kotitalousvähennysta varten Palkkauksen verottajalle ilmoittamat tiedot.\r\n      </p>\r\n      <p>\r\n        Lisäksi tietoa miten ilmoitat Palkkaus.fi-palvelun ulkopuolella maksetut kotitalousvähennyksen alaiset kustannukset.\r\n      </p>\r\n      <p>\r\n        Avaa <a  ng-href=\"{{$ctrl.selectedYear.value < 2021 ? '#/archive/household-deduction-report' : '#/household-years/active'}}\">Raportti tästä</a>.\r\n      </p>\r\n    </div>\r\n  </div>\r\n  <hr />\r\n  <br />\r\n  <h3 id=\"more-info\">Lisätietoja raporteista</h3>\r\n  <p>\r\n    Lisätietoja yllä listatutuista työntekijäkohtaisista raporteista.\r\n  </p>\r\n  <div class=\"row\">\r\n    <div class=\"col-sm-4\">\r\n      <h4>Työntekijän yhteenveto</h4>\r\n      <p>\r\n        Lain mukaan työnantajan pitää toimittaa työntekijälle yhteenveto kaikista palkoista, joita on maksanut vuoden aikana.\r\n      </p>\r\n      <p>\r\n        <strong>Jos Palkkaus.fi-palvelussa on työntekijän sähköpostiosoite, lähetämme tähän linkin suoraan työntekijälle.</strong>\r\n        Jos sähköpostiosoite ei ole oikein, voit tulostaa tämän yhteenvedon ja lähettää työntekijälle.\r\n      </p>\r\n      <ul ng-controller=\"WorkerSummaryReportDisplayController as $displayCtrl\">\r\n        <li ng-repeat=\"employerReport in $ctrl.currentReport.employerReports\">\r\n          <a ng-click=\"$displayCtrl.display($ctrl.selectedYear.value + '-01-01', employerReport.worker.identity.socialSecurityNumberValid , $ctrl.employerId )\">{{\r\n            employerReport.worker.fullName }}</a>\r\n          {{ $ctrl.workerEmailFrom(employerReport) || 'Ei sähköpostia' }}\r\n        </li>\r\n      </ul>\r\n    </div>\r\n    <div ng-if=\"$ctrl.isSelectedYearBeforeIncomesRegistry\" class=\"col-sm-4\">\r\n      <h4>Vuosi-ilmoitus verottajalle (7801)</h4>\r\n      <p>\r\n        <i>Verottajan lomake 7801: Työnantajan tai suorituksen maksajan vuosi-ilmoitus</i>\r\n        Näitä lomakkeita tuotamme jokaista työntekijääsi kohden yhden.\r\n      </p>\r\n      <p>\r\n        Jokaisen vuoden tammikuussa luomme edellisen vuoden ilmoitukset ja voit vielä tarkistaa lomakkeen tiedot.\r\n        Tämän jälkeen <strong>lähetämme ilmoituksen verottajalle</strong> ja alkuperäinen ilmoitus jää Palkkaus.fi-arkistoon.\r\n      </p>\r\n      <ul>\r\n        <li ng-repeat=\"employerReport in $ctrl.currentReport.employerReports\">\r\n          <a href=\"{{ $ctrl.apiServerAddress }}/ReportPdf/TaxYearly7801/{{ employerReport.worker.identity.socialSecurityNumberValid }}?year={{ $ctrl.selectedYear.value }}&access_token={{ $ctrl.token }}\"\r\n            target=\"_blank\">{{\r\n            employerReport.worker.fullName }}</a>\r\n        </li>\r\n      </ul>\r\n    </div>\r\n    <div class=\"col-sm-4\" >\r\n      <h4>Kotitalous&shy;vähennyksen vuosi-ilmoitus (14B)</h4>\r\n      <p>\r\n        <i>Verottajan lomake 14B / 3026: Kotitalousvähennys työntekijälle maksetusta palkasta</i>\r\n        Yhteen lomakesivuun mahtuu tiedot kahdesta työntekijästä\r\n      </p>\r\n      <p>\r\n        <strong>\r\n          Lähetämme tiedot verottajalle tammikuun loppuun mennessä,\r\n        </strong> kun olet käynyt tarkistamassa tietosi\r\n      </p>\r\n      <p>\r\n        Huomaathan, että verottaja käsittelee kaikki lomakkeet 14B yhdellä kertaa veroilmoitusten kanssa kesäkuussa,\r\n        joten nämä tiedot eivät näy vielä esitäytetyssä veroilmoituksessa.\r\n      </p>\r\n\r\n      <ul ng-if=\"$ctrl.selectedYear.value < 2021\">\r\n        <li ng-repeat=\"employerGroup in $ctrl.employers14BGroups\">\r\n          <a href=\"{{ $ctrl.apiServerAddress }}/ReportPdf/TaxHouseholdDeduction14B/{{ employerGroup.id1 }}?id2={{ employerGroup.id2 }}&year={{ $ctrl.selectedYear.value }}&access_token={{ $ctrl.token }}\"\r\n            target=\"_blank\">\r\n            {{ employerGroup.names }}\r\n          </a>\r\n        </li>\r\n      </ul>\r\n      <span ng-if=\"$ctrl.selectedYear.value >= 2021\">Avaa <a href=\"#/household-years/active\">Raportti tästä</a>.</span>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/personal/EmployerSelect.html\",`<div class=\"salaxy-component salaxy-employer-select\">\r\n  <div ng-if=\"!$ctrl.employingRelations.length\" class=\"\">\r\n    <h2>Ei työnantajia</h2>\r\n  </div>\r\n\r\n\r\n  <div class=\"list-group avatar-list-group\">\r\n    <div ng-repeat=\"row in $ctrl.selectedItems\" class=\"list-group-item\">\r\n      <div class=\"list-group-item-content-wrapper\">\r\n        <salaxy-avatar avatar=\"row.ownerInfo.avatar\" class=\"float-start icon-wrapper\"></salaxy-avatar>\r\n        <div class=\"list-group-item-text-wrapper\">\r\n          <h4 class=\"list-group-item-heading\">{{row.ownerInfo.avatar.displayName}}</h4>\r\n          <p class=\"list-group-item-text\">{{row.owner | sxyIban}}</p>\r\n        </div>\r\n      </div>\r\n\r\n      <button ng-if=\"$ctrl.employingRelations.length > 1\" ng-click=\"$ctrl.setEmployerSelected(row, false);\" class=\"btn btn-xs btn-default\" sxy-text=\"SALAXY.UI_Terms.change\"></button>\r\n\r\n    </div>\r\n  </div>\r\n\r\n  <div ng-if=\"$ctrl.employingRelations.length > 1 && !$ctrl.selectedItems.length\">\r\n    <div class=\"list-group avatar-list-group\">\r\n      <div ng-repeat=\"row in $ctrl.employingRelations\" class=\"list-group-item\">\r\n        <div class=\"list-group-item-content-wrapper\">\r\n          <salaxy-avatar avatar=\"row.ownerInfo.avatar\" class=\"float-start icon-wrapper\"></salaxy-avatar>\r\n          <div class=\"list-group-item-text-wrapper\">\r\n            <h4 class=\"list-group-item-heading\">{{row.ownerInfo.avatar.displayName}}</h4>\r\n            <p class=\"list-group-item-text\">{{row.owner | sxyIban}}</p>\r\n          </div>\r\n        </div>\r\n        <button ng-click=\"$ctrl.setEmployerSelected(row, true)\" class=\"btn btn-xs btn-default\" sxy-text=\"SALAXY.UI_Terms.select\"></button>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/personal/HouseholdDeductionReport.html\",`<div style=\"max-width: calc(100% - 45px); margin-left: 15px\">\r\n  <salaxy-spinner heading=\"SALAXY.UI_Terms.loading\" ng-if=\"!$ctrl.currentReport\"></salaxy-spinner>\r\n  <div class=\"row\">\r\n    <div class=\"col-12 mb-2\">\r\n      <label>Valitse vuosi: </label>\r\n      <select class=\"form-select\" ng-options=\"option.name for option in $ctrl.yearOptions track by option.value\" ng-model=\"$ctrl.selectedYear\" name=\"years\" id=\"years\"></select>\r\n    </div>\r\n  </div>\r\n  <h2>Palkkaus.fi-palvelussa maksetut palkat</h2>\r\n  <h3 ng-repeat-start=\"yearlyReport in $ctrl.currentReport\" ng-if=\"$index == 0\">Nämä työt voit vähentää omassa verotuksessasi.</h3>\r\n  <p ng-if=\"$index == 0\">Kotitalousvähennys on enintään {{ $ctrl.deductionMaxAmount | currency : \"\" : 0 }} euroa vuodessa. Vähennyksen omavastuu on 100 euroa.</p>\r\n  <h3 ng-if=\"$index == 1\">Nämä työt voit vähentää mahdollisen puolisosi verotuksessa.</h3>\r\n  <p ng-if=\"$index == 1\">Kotitalousvähennys on henkilökohtainen, joten puolisot voivat saada yhteensä {{ (2 * $ctrl.deductionMaxAmount) | currency : \"\" : 0 }} euron vähennyksen. Jos {{ $ctrl.deductionMaxAmount | currency : \"\" : 0 }} euron raja ei ylity, vähennys kannattaa hakea\r\n    vain toiselle puolisolle. Silloin omavastuu vähennetään vain yhden kerran.</p>\r\n  <h3 ng-if=\"$index == 2\">Näitä töitä et voi vähentää verotuksessa</h3>\r\n  <p ng-if=\"$index == 2\">Kotitalousvähennyksen maksimimäärä on {{ $ctrl.deductionMaxAmount | currency : \"\" : 0 }} yhdessä puolison kanssa.</p>\r\n  <b>Työnantaja {{ yearlyReport.employer.fullName }}</b>\r\n  <table class=\"table table-sm\">\r\n    <thead>\r\n      <tr>\r\n        <th>Työntekijä</th>\r\n        <th>Työ: maksupäivä ja kuvaus</th>\r\n        <th class=\"right\" colspan=\"2\">Luvut 14B-lomakkeessa</th>\r\n        <th class=\"right\">KT-vähennys</th>\r\n      </tr>\r\n    </thead>\r\n    <tbody ng-repeat=\"employerReport in yearlyReport.employerReports\">\r\n      <tr ng-if-start=\"employerReport.isHouseholdDeductionWork\">\r\n        <td rowspan=\"4\">\r\n          {{ employerReport.worker.displayName }}<br /> {{ employerReport.worker.identity.socialSecurityNumberValid }}<br />\r\n        </td>\r\n        <td rowspan=\"4\">\r\n          {{ $ctrl.formatDateRange(employerReport.firstDeductiblePaymentDate, employerReport.lastDeductiblePaymentDate) }} {{ employerReport.deductionWorkDescription }}\r\n          <div class=\"form-group form-group-display\">\r\n            <label class=\"col-sm-10 control-label\">Kotitaloustyö</label>\r\n            <div class=\"col-sm-2\">\r\n              <input ng-checked=\"employerReport.hasHouseholdWork\" class=\"check-box\" disabled=\"disabled\" type=\"checkbox\">\r\n            </div>\r\n          </div>\r\n          <div class=\"form-group form-group-display\">\r\n            <label class=\"col-sm-10 control-label\">Hoiva- ja hoitotyö</label>\r\n            <div class=\"col-sm-2\">\r\n              <input ng-checked=\"employerReport.hasCareAndNurtureWork\" class=\"check-box\" disabled=\"disabled\" type=\"checkbox\">\r\n            </div>\r\n          </div>\r\n          <div class=\"form-group form-group-display\">\r\n            <label class=\"col-sm-10 control-label\">Asunnon kunnossapito- tai perusparannustyö</label>\r\n            <div class=\"col-sm-2\">\r\n              <input ng-checked=\"employerReport.hasConstructionWork\" class=\"check-box\" disabled=\"disabled\" type=\"checkbox\">\r\n            </div>\r\n          </div>\r\n        </td>\r\n        <td>Palkka</td>\r\n        <td class=\"right\">{{ $ctrl.formatNumber(employerReport.totalTaxableDeductible) }}</td>\r\n        <td class=\"right\">{{ $ctrl.formatNumber(employerReport.totalTaxableDeduction) }}</td>\r\n      </tr>\r\n\r\n      <tr>\r\n        <td>Sivukulut (TyEL+Sava+TVR)</td>\r\n        <td class=\"right\">{{ $ctrl.formatNumber(employerReport.totalMandatorySideCosts) }}</td>\r\n        <td class=\"right\">{{ $ctrl.formatNumber(employerReport.totalMandatorySideCosts) }}</td>\r\n      </tr>\r\n      <tr>\r\n        <td>Vakuutus</td>\r\n        <td class=\"right\">{{ $ctrl.formatNumber(employerReport.deductionInsuranceEtc) }}</td>\r\n        <td class=\"right\">{{ $ctrl.formatNumber(employerReport.deductionInsuranceEtc) }}</td>\r\n      </tr>\r\n      <tr ng-if-end class=\"total\">\r\n        <td>Yhteensä</td>\r\n        <td class=\"right\">{{ $ctrl.formatNumber(employerReport.deduction14BFormTotal) }}</td>\r\n        <td class=\"right\">{{ $ctrl.employerDeductionsTotalAmount(employerReport) }}</td>\r\n      </tr>\r\n      <tr ng-if=\"!employerReport.isHouseholdDeductionWork\">\r\n        <td>\r\n          {{ employerReport.worker.displayName }}<br /> {{ employerReport.worker.identity.socialSecurityNumberValid }}<br />\r\n        </td>\r\n        <td>\r\n          {{ $ctrl.formatDateRange(employerReport.firstPaymentDate, employerReport.lastPaymentDate) }} Ei töitä merkittynä kotitalousvähennykseen.\r\n        </td>\r\n        <td>Palkka</td>\r\n        <td class=\"right\">{{ $ctrl.formatNumber(employerReport.totalTaxableDeductible) }}</td>\r\n        <td class=\"right\">-</td>\r\n      </tr>\r\n    </tbody>\r\n    <tfoot>\r\n      <tr>\r\n        <td colspan=\"2\">&nbsp;</td>\r\n      </tr>\r\n      <tr class=\"total\">\r\n        <th colspan=\"2\">Yhteensä</th>\r\n        <th colspan=\"2\" class=\"right\">{{ $ctrl.yearlyForm14BTotalAmount(yearlyReport) }}</th>\r\n        <th class=\"right\">{{ $ctrl.yearlyDeductionsTotalAmount(yearlyReport) }}</th>\r\n      </tr>\r\n      <tr>\r\n        <td>Omavastuu</td>\r\n        <td>Max. {{ $ctrl.deductionMaxAmount | currency : \"\" : 0 }} euroa / henkilö (pariskunta {{ (2 * $ctrl.deductionMaxAmount) | currency : \"\" : 0 }})</td>\r\n        <td colspan=\"3\" class=\"right\">-100,00</td>\r\n      </tr>\r\n      <tr class=\"total\">\r\n        <th colspan=\"2\">Kotitalousvähennys yhteensä</th>\r\n        <th colspan=\"3\" class=\"right\">{{ $ctrl.yearlyDeductionTotal(yearlyReport) }}</th>\r\n      </tr>\r\n    </tfoot>\r\n  </table>\r\n  <p ng-repeat-end=\"\">&nbsp;</p>\r\n\r\n  <p>\r\n    Verottaja käsittelee kaikki lomakkeet 14B yhdellä kertaa veroilmoitusten kanssa kesäkuussa, joten nämä tiedot\r\n    <strong>eivät näy vielä esitäytetyssä veroilmoituksessa</strong>. Käymme aktiivista keskustelua verottajan kanssa, jotta ensi vuodeksi saisimme tiedot jo tähän esitäytettyyn veroilmoitukseen. Jos tämä on sinusta tärkeä juttu, lähetä meille palautetta\r\n    osoitteeseen aspa@palkkaus.fi. Viemme mielellämme tätä tietoa eteenpäin verottajalle.\r\n  </p>\r\n  <p>\r\n    Tulet saamaan <strong>elo-syyskuussa Verottajalta korjatun verotuspäätöksen</strong>, jossa kotitalousvähennys on huomioitu kokonaisuudessaan. Jos vielä silloin huomaat joitain puutteita, voit tehdä muutoksen lokakuun aikana. Lopullisesti verotus\r\n    vahvistetaan lokakuun viimeinen päivä.\r\n  </p>\r\n  <hr />\r\n  <h2 id=\"info14B\">Palkkaus.fi-palvelun ulkopuolella maksetut palkat</h2>\r\n  <p>\r\n    Jos olet teettänyt työtä, jonka palkan olet maksanut Palkkaus.fi-palvelun ulkopuolella, muistathan ilmoittaa siitä erikseen verottajalle.\r\n  </p>\r\n  <p>\r\n    Kotitalousvähennyksen alaisen työn voi ilmoittaa kahdella tavalla:\r\n  </p>\r\n  <ol>\r\n    <li>\r\n      Tulosta lomake\r\n      <a href=\"https://www.vero.fi/fi-FI/Syventavat_veroohjeet/Lomakkeet/Henkiloasiakkaiden_lomakkeet/14B_Kotitalousvahennys_tyontekijalle_mak(12921)\" target=\"_blank\">\r\n        14B tästä linkistä\r\n      </a> ja lähetä se verottajalle.\r\n    </li>\r\n    <li>Sähköisellä veroilmoituksella <a href=\"https://www.vero.fi/veroilmoitus\" target=\"_blank\">https://www.vero.fi/veroilmoitus</a></li>\r\n  </ol>\r\n  <hr />\r\n  <h2 id=\"info14A\">Yrityksen laskuttama työ kotitalousvähennykseen</h2>\r\n  <p>\r\n    Jos olet teettänyt yrityksellä työtä, joka kelpaa kotitalousvähennykseen, muistathan ilmoittaa myös sen verottajalle.\r\n  </p>\r\n  <p>\r\n    Laskulla teetetyn työn voi ilmoittaa kahdella tavalla:\r\n  </p>\r\n  <ol>\r\n    <li>\r\n      Tulosta lomake\r\n      <a href=\"http://www.vero.fi/fi-FI/Syventavat_veroohjeet/Lomakkeet/Henkiloasiakkaiden_lomakkeet/14A_Kotitalousvahennys_yritykselle_makse(12918)\" target=\"_blank\">\r\n        14A tästä linkistä\r\n      </a> ja lähetä se verottajalle.\r\n    </li>\r\n    <li>Sähköisellä veroilmoituksella <a href=\"https://www.vero.fi/veroilmoitus\" target=\"_blank\">https://www.vero.fi/veroilmoitus</a></li>\r\n  </ol>\r\n  <p>\r\n    Olemme suunnitelleet tähän myös työkalua Palkkaus.fi-sivustolle. Työkalulla voisi kirjata laskut jo etukäteen ja tallentaa kuitit arkistoon. Palkkaus.fi ilmoittaisi tiedot verottajalle vuoden lopussa. Jos tämä on sinusta tärkeä juttu, lähetä meille palautetta\r\n    osoitteeseen aspa@palkkaus.fi.\r\n  </p>\r\n  <hr />\r\n  <h2 id=\"info-kuuluuko\">Mistä tiedän kuuluuko työ kotitalousvähennykseen?</h2>\r\n  <p>Perusidea on, että työn pitää olla jotain seuraavista:</p>\r\n  <ul>\r\n    <li>kotitaloustyö</li>\r\n    <li>hoiva- tai hoitotyö</li>\r\n    <li>asunnon kunnossapito- tai perusparannustyö</li>\r\n  </ul>\r\n  <p>\r\n    Lisäksi työ pitää tehdä omassa käytössä olevassa asunnossa tai vapaa-ajan asunnnossa. (Erikoistapauksena myös joidenkin lähisukulaisten käytössä olevat asunnot)\r\n  </p>\r\n  <p>\r\n    Jos olet epävarma, niin <a href=\"http://www.vero.fi/fi-FI/Henkiloasiakkaat/Kotitalousvahennys\" target=\"_blank\">tällä verottajan sivulla on kuvattu</a> tarkemmin kotitalousvähennystä. Huomaa alalaidan linkit eri työtyyppeihin.\r\n    <a href=\"http://www.vero.fi/fi-FI/Henkiloasiakkaat/Kotitalousvahennys/Taulukko_kysytyimmista_kotitalousvahenny(9231)\" target=\"_blank\">Tällä toisella sivulla on pitkä lista</a> eri töistä.\r\n  </p>\r\n\r\n  <p>Jos et vieläkään ole varma, voit kysyä mielipidettä Suomen Palkanlaskenta Oy:n asiantuntijoilta (yhteystiedot sivun alalaidassa).</p>\r\n\r\n  <p>Me autamme mielellämme!</p>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/personal/HouseholdYearDetails.html\",`<div class=\"salaxy-component salaxy-household-year-details\">\r\n\r\n  <div class=\"btn-toolbar float-end\" role=\"toolbar\" salaxy-if-role=\"pro\">\r\n    <salaxy-workflow-buttons api-ctrl=\"$ctrl\" disabled=\"!$ctrl.current || $ctrl.isNew() || $ctrl.current.isReadOnly\"></salaxy-workflow-buttons>\r\n  </div>\r\n\r\n  <div class=\"table-responsive\">\r\n    <p class=\"lead\">\r\n      Palvelu tekee puolestasi kotitalousvähennysilmoitukset maksetuista palkoista, kun laskelmalla on kotitalousvähennysmerkintä. Tarkista valinnat ja täydennä tarvittavat tiedot.\r\n    </p>\r\n    <div ng-if=\"$ctrl.current && $ctrl.isOpen\">\r\n      <p>\r\n        Alla on listattu vuoden {{ $ctrl.current.year || \"\" }} aikana palvelun kautta maksamasi palkat.\r\n      </p>\r\n      <ol>\r\n        <li>Tarkista palkat</li>\r\n        <li>Lisää tai poista kotitalousvähennys</li>\r\n        <li>Hyväksy tarkistamasi tiedot</li>\r\n      </ol>\r\n      <p>\r\n        <big>Kotitalousvähennys:</big> laita rasti ruutuun niiden palkkalaskelmien kohdalle, joista haluat kotitalousvähennyksen.\r\n      </p>\r\n    </div>\r\n    <div ng-if=\"$ctrl.current && !$ctrl.isOpen\">\r\n      <h3>Tiedot on jo lähetetty</h3>\r\n      <p>\r\n        Olet lähettänyt alla olevat tiedot {{$ctrl.current.userFeedbackTime | date : 'dd.MM.yyyy HH:mm'}}\r\n      </p>\r\n      <p>\r\n        Jos haluat avata tarkistuksen, ole yhteydessä asiakaspalveluun.\r\n      </p>\r\n    </div>\r\n    <hr />\r\n  </div>\r\n  <form name=\"theForm\" ng-if=\"$ctrl.current\">\r\n    <div class=\"table-responsive\" ng-controller=\"WorkerSummaryReportDisplayController as $displayCtrl\">\r\n      <table class=\"table\">\r\n        <thead>\r\n          <tr>\r\n            <th colspan=\"7\">\r\n              <h3>Työntekijöiden palkkalaskelmat</h3>\r\n            </th>\r\n          </tr>\r\n          <tr>\r\n            <th colspan=\"2\">Työntekijä</th>\r\n            <th class=\"right\">Bruttopalkka</th>\r\n            <th class=\"right\">Työnantaja&shy;kulut</th>\r\n            <th colspan=\"3\">Kotitalousvähennys <br>(laita rasti ruutuun)</th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr ng-repeat-start=\"workerSummary in $ctrl.yearlyCalculations.workers\">\r\n            <td style=\"font-size: 64px; line-height: 1\">\r\n              <salaxy-avatar avatar=\"workerSummary.worker.avatar\"></salaxy-avatar>\r\n            </td>\r\n            <td>\r\n              {{ workerSummary.worker.avatar.displayName }}<br />\r\n              <a ng-href=\"mailto:{{ workerSummary.worker.paymentData.email }}\"> {{ workerSummary.worker.paymentData.email }}</a><br /> {{ workerSummary.worker.paymentData.socialSecurityNumberValid }}<br />\r\n            </td>\r\n            <td class=\"right\">\r\n              {{ workerSummary.totalTaxable | number : 2 }}€\r\n            </td>\r\n            <td class=\"right\">\r\n              {{ workerSummary.mandatorySideCosts | number : 2 }}€\r\n            </td>\r\n            <td></td>\r\n            <td></td>\r\n            <td>\r\n              Työntekijän raportit (esikatselu):\r\n              <div>\r\n                <a ng-click=\"$displayCtrl.display($ctrl.current.year + '-01-01', workerSummary.worker.paymentData.socialSecurityNumberValid , null)\">Yhteenveto</a>\r\n              </div>\r\n            </td>\r\n          </tr>\r\n          <tr ng-repeat=\"calc in workerSummary.calculations\">\r\n            <td></td>\r\n            <td class=\"valign-middle\" ng-controller=\"CalcReportsDisplayController as $displayCtrl\">\r\n              <a ng-click=\"$displayCtrl.displayForId('salarySlip', calc.id)\">Laskelma {{ calc.workflow.salaryDate | date : 'dd.MM.' }} &raquo;</a>\r\n            </td>\r\n            <td class=\"right valign-middle\">\r\n              {{ calc.result.totals.totalTaxable | number : 2 }}€\r\n            </td>\r\n            <td class=\"right valign-middle\">\r\n              {{ calc.result.employerCalc.mandatorySideCosts | number : 2 }}€\r\n            </td>\r\n            <td class=\"valign-middle\" style=\"min-width: 40px;\">\r\n              <input type=\"checkbox\" ng-disabled=\"!$ctrl.isOpen\" ng-model=\"calc.usecase.data.isHouseholdDeductible\" ng-change=\"$ctrl.calculationUpdated(calc)\" />\r\n            </td>\r\n            <td class=\"right valign-middle tax-deduction-item\" ng-class=\"{ 'text-disabled': !calc.usecase.data.isHouseholdDeductible }\">\r\n              {{ (calc.result.employerCalc.mandatorySideCosts + calc.result.totals.totalTaxable * $ctrl.getHouseholdDeduction(calc)) | number : 2 }}€\r\n            </td>\r\n            <td>\r\n              <span ng-if=\"!calc.usecase.data.isHouseholdDeductible\" class=\"text-danger\">Ei kotitalousvähennystä</span>\r\n              <div ng-if=\"calc.usecase.data.isHouseholdDeductible\">\r\n                <select class=\"form-select\" ng-disabled=\"!$ctrl.isOpen\" ng-model=\"calc.usecase.data.taxDeductionCategories\" ng-change=\"$ctrl.calculationUpdated(calc)\">\r\n                  <option hidden value=\"\">Valitse työn tyyppi...</option>\r\n                  <option value=\"none\">Ei valintaa</option>\r\n                  <option value=\"householdwork\">Kotitaloustyö</option>\r\n                  <option value=\"carework\">Hoiva- ja hoitotyö</option>\r\n                  <option value=\"homeImprovement\">Asunnon/loma-asunnon kunnossapito- tai korjaustyö</option>\r\n                  <option value=\"oilHeatingReplacementWork\">Öljylämmityksestä luopuminen</option>\r\n                </select>\r\n              </div>\r\n              <div ng-if=\"calc.usecase.data.isHouseholdDeductible\">\r\n                <select class=\"form-select\" ng-disabled=\"!$ctrl.isOpen\" ng-model=\"calc.usecase.data.taxDeductionProperty\" ng-change=\"$ctrl.calculationUpdated(calc)\">\r\n                  <option hidden value=\"\">Valitse työn sijainti</option>\r\n                  <option value=\"none\">Ei valintaa</option>\r\n                  <option value=\"ownProperty\">Omassa käytössä oleva asunto tai vapaa-ajan asunto</option>\r\n                  <option value=\"relativesProperty\">Vanhempien, isovanhempien yms. käytössä oleva asunto tai vapaa-ajan asunto.</option>\r\n                </select>\r\n              </div>\r\n            </td>\r\n          </tr>\r\n          <tr ng-repeat-end>\r\n            <td colspan=\"7\" style=\"border-top-color: rgb(145,210,20); line-height: 0; padding: 0;\"></td>\r\n          </tr>\r\n          <tr>\r\n            <th colspan=\"7\">\r\n              <h4>Tapaturmavakuutus kotitalousvähennykseen</h4>\r\n            </th>\r\n          </tr>\r\n          <tr>\r\n            <td></td>\r\n            <td colspan=\"5\">\r\n              <div>\r\n                Tapaturmavakuutus kelpaa kotitalousvähennykseen. Lisää maksamasi vakuutuksen summa tähän.\r\n              </div>\r\n            </td>\r\n            <td>\r\n              <salaxy-input-number name=\"insuranceAmount\" disabled=\"!$ctrl.isOpen\" label-type=\"plain\" unit=\"euro\" ng-model=\"$ctrl.current.insuranceAmount\" />\r\n            </td>\r\n          </tr>\r\n          <tr class=\"total\">\r\n            <th colspan=\"4\">\r\n              <h4>Kotitalousvähennys yhteensä</h4>\r\n            </th>\r\n            <th></th>\r\n            <th class=\"right valign-middle\">{{ $ctrl.getTaxDeductionTotal() + $ctrl.getTaxDeductionTotalExtended() + $ctrl.current.insuranceAmount  | number : 2 }}€</th>\r\n            <th class=\"valign-middle\">\r\n              <small style=\"font-weight: normal\">...josta vähennetään omavastuu.</small>\r\n            </th>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n      <p>\r\n        Huomioi: kotitalousvähennyksesi ei näy kevään esitäytetyssä veroilmoituksessasi, koska verottaja käsittelee ilmoitukset niin hitaasti. Lopulliseen verotukseesi ne tulevat kuitenkin oikein.\r\n      </p>\r\n    </div>\r\n    <div ng-show=\"$ctrl.canSplitWithSpouse()\">\r\n      <h3>Jaa kotitalousvähennys puolisosi kanssa</h3>\r\n      <p>\r\n        Kotitalousvähennystä voi saada {{ $ctrl.getGetSplittableMaxAmount() }}€ per henkilö ({{$ctrl.getHouseholdDeductionDeductible()}}€ omavastuun jälkeen).\r\n      </p>\r\n      <p>\r\n        Jos sinulla on puoliso, niin lisää tähän hänen tietonsa. Näin voimme lähettää {{ $ctrl.getGetSplittableMaxAmount() + $ctrl.getHouseholdDeductionDeductible()}}€ ylittävän osan kotitalousvähennyksestä hänen veroilmoitukseensa.\r\n      </p>\r\n      <div class=\"form-group\">\r\n        <label for=\"spouseName\" class=\"control-label\">Puolison nimi:</label>\r\n        <salaxy-input name=\"spouseName\" disabled=\"!$ctrl.isOpen\" placeholder=\"Koko nimi verottajalle\" label-type=\"plain\" ng-model=\"$ctrl.current.spouseName\"></salaxy-input>\r\n      </div>\r\n      <div class=\"form-group\">\r\n        <label for=\"spousePersonalId\" class=\"control-label\">Puolison henkilötunnus:</label>\r\n        <salaxy-input name=\"spousePersonalId\" disabled=\"!$ctrl.isOpen\" placeholder=\"ddmmyy-123X\" label-type=\"plain\" sxy-personal-id-fi ng-model=\"$ctrl.current.spousePersonalId\"></salaxy-input>\r\n      </div>\r\n    </div>\r\n    <div>\r\n      <h3>Tietojen lähettäminen</h3>\r\n      <p>Kun ole tarkistanut tiedot, valitse joku alla olevista vaihtoehdoista.</p>\r\n      <table>\r\n        <tr>\r\n          <td>\r\n            <label for=\"statusOk\">\r\n            <input id=\"statusOk\" type=\"radio\" ng-disabled=\"!$ctrl.isOpen\" ng-model=\"$ctrl.current.status\" value=\"ok\">\r\n            <span class=\"text-success\">Kyllä, tiedot tarkistettu / korjattu</span>\r\n            </label>\r\n          </td>\r\n          <td>\r\n            <p>Palvelu lähettää kotitalousvähennysilmoituksen 14B-lomakkeen verottajalle</p>\r\n          </td>\r\n        </tr>\r\n        <tr>\r\n          <td>\r\n            <label for=\"statusOkWithModifications\">\r\n            <input id=\"statusOkWithModifications\" type=\"radio\" ng-disabled=\"!$ctrl.isOpen\" ng-model=\"$ctrl.current.status\" value=\"okWithModifications\">\r\n            <span class=\"text-danger\">Tiedoissa on puutteita / virheitä<span>\r\n            </label>\r\n          </td>\r\n          <td>\r\n            <p>Jos tiedoissa on puutteita, joita et voinut korjata tällä sivulla itse, listaa puutteet tähän. Palvelu on sinuun tarvittaessa yhteydessä.</p>\r\n            <div ng-if=\"$ctrl.current.status == 'okWithModifications'\">\r\n              <textarea class=\"form-control\" ng-disabled=\"!$ctrl.isOpen\" ng-model=\"$ctrl.current.userFeedbackText\" rows=\"2\"></textarea>\r\n            </div>\r\n          </td>\r\n        </tr>\r\n        <tr>\r\n          <td>\r\n            <label for=\"statusWillHandleMyself\">\r\n            <input id=\"statusWillHandleMyself\" type=\"radio\" ng-disabled=\"!$ctrl.isOpen\" ng-model=\"$ctrl.current.status\" value=\"willHandleMyself\">\r\n            <span class=\"text-default\">Teen kotitalous&shy;vähennysilmoituksen itse</span>\r\n            </label>\r\n          </td>\r\n          <td>\r\n            <p>\r\n              Palvelu ei lähetä kotitalousvähennysilmoitusta (14B-lomake) verottajalle. Valitse tämä vaihtoehto, jos olet jo itse tehnyt kotitalousvähennysilmoitukset OmaVerossa tai et halua hakea kotitalousvähennystä.\r\n            </p>\r\n          </td>\r\n        </tr>\r\n      </table>\r\n    </div>\r\n\r\n    <div class=\"text-end\">\r\n      <button type=\"button\" class=\"btn btn-default\" ng-disabled=\"!$ctrl.current || !$ctrl.current.id\" ng-click=\"$ctrl.export()\">Lataa pdf(t)</button>\r\n      <button type=\"button\" class=\"btn btn-primary\" ng-disabled=\"!$ctrl.current || !theForm.$valid || $ctrl.current.isReadOnly || !$ctrl.isOpen\" ng-click=\"$ctrl.save()\">Tallenna</button>\r\n    </div>\r\n  </form>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/personal/HouseholdYearList.html\",`<div class=\"salaxy-component household-year-list\">\r\n  <salaxy-odata-table ng-ref=\"$odata\" crud-controller=\"HouseholdYearCrudController as $crud\">\r\n  </salaxy-odata-table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/personal/WorkerReport.html\",`<div class=\"salaxy-component salaxy-worker-report\">\r\n  <salaxy-spinner heading=\"SALAXY.UI_Terms.loading\" ng-if=\"!$ctrl.currentReport\"></salaxy-spinner>\r\n  <div class=\"d-flex align-items-center mb-3 d-flex\">\r\n    <label class=\"text-nowrap\" sxy-text=\"SALAXY.NG1.WorkerReportComponent.selectYearLabel\"></label>\r\n    <select class=\"form-select ms-2 w-auto\" ng-options=\"option.name for option in $ctrl.yearOptions track by option.value\" ng-model=\"$ctrl.selectedYear\" name=\"years\" id=\"years\"></select>\r\n  </div>\r\n  <div>\r\n    <h2 ng-if-start=\"$ctrl.currentReport.length <= 0\" sxy-text=\"SALAXY.NG1.WorkerReportComponent.noPaidSalaries.title\" params=\"{year: $ctrl.selectedYear.value}\"></h2>\r\n    <p sxy-text=\"SALAXY.NG1.WorkerReportComponent.noPaidSalaries.description\" params=\"{year: $ctrl.selectedYear.value}\"></p>\r\n    <p ng-if-end sxy-text=\"SALAXY.NG1.WorkerReportComponent.contactCustomerService\" params=\"{year: $ctrl.selectedYear.value}\"></p>\r\n    <p ng-if-start=\"$ctrl.currentReport.length > 0\" class=\"\" sxy-text=\"SALAXY.NG1.WorkerReportComponent.paidSalariesText\" params=\"{year: $ctrl.selectedYear.value}\"></p>\r\n    <div ng-if-end class=\"table-responsive light-bg\">\r\n      <table class=\"table table-striped table-sm\">\r\n        <thead>\r\n          <tr>\r\n            <th colspan=\"2\" sxy-text=\"SALAXY.NG1.WorkerReportComponent.table.employer\"></th>\r\n            <th class=\"right\">\r\n              <span sxy-text=\"SALAXY.NG1.WorkerReportComponent.table.grossSalary\"></span><br /><span sxy-text=\"SALAXY.NG1.WorkerReportComponent.table.totalTaxable\"></span>\r\n            </th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.WorkerReportComponent.table.compensation\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.WorkerReportComponent.table.summary\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.WorkerReportComponent.table.taxPercent\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.WorkerReportComponent.table.householdDeduction\"></th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr ng-repeat-start=\"report in $ctrl.currentReport\" ng-controller=\"WorkerSummaryReportDisplayController as $displayCtrl\">\r\n            <td>\r\n              <div style=\"font-size: 64px; line-height: 1\" ng-init=\"avatar = $ctrl.avatarFrom(report.employer.avatar.url)\">\r\n                <i ng-if=\"!avatar.url\" class=\"salaxy-avatar bi\" ng-class=\"avatar.baseIcon\" ng-style=\"{color: avatar.color}\"><strong>{{ avatar.initials }}</strong></i>\r\n                <i ng-if=\"avatar.url\" class=\"salaxy-avatar bi\"><img ng-src=\"{{ avatar.url }}\"></img></i>\r\n              </div>\r\n            </td>\r\n            <td>\r\n              {{ report.employer.fullName}}<br />\r\n              <a ng-href=\"mailto:{{ $ctrl.workerEmailFrom(report) }}\">{{ $ctrl.employerEmailFrom(report) }}</a><br /> {{ report.employer.identity.socialSecurityNumberValid }}\r\n            </td>\r\n            <td class=\"right\">\r\n              {{ report.grossSalary | currency : \"€\" : 2}}<br /> {{ report.totalTaxable | currency : \"€\" : 2}}\r\n            </td>\r\n            <td class=\"right\">\r\n              {{ report.totalExpenses | currency : \"€\" : 2}}\r\n            </td>\r\n            <td>\r\n              <a ng-click=\"$displayCtrl.display($ctrl.selectedYear.value, 'self', report.employer.id)\"\r\n                class=\"btn btn-primary btn-xs\"\r\n                sxy-text=\"SALAXY.NG1.WorkerReportComponent.table.yearlyReport\" post=\"&nbsp;&raquo;\"\r\n                ></a>\r\n            </td>\r\n            <td colspan=\"2\">\r\n              <p class=\"small\">\r\n                <strong sxy-text=\"SALAXY.NG1.WorkerReportComponent.table.workerYearlySummaryTitle\"></strong><br />\r\n                <a ng-click=\"$displayCtrl.display($ctrl.selectedYear.value, 'self', report.employer.id)\">\r\n                  <span sxy-text=\"SALAXY.NG1.WorkerReportComponent.table.workerYearlySummaryLink\"></span></a> <span\r\n                  sxy-text=\"SALAXY.NG1.WorkerReportComponent.table.workerYearlySummaryText\"></span>\r\n              </p>\r\n            </td>\r\n          </tr>\r\n          <tr ng-repeat-end=\"\" ng-repeat=\"calculation in report.underlyingCalculations\">\r\n            <td></td>\r\n            <td>\r\n              <b ng-if=\"!$ctrl.isSelectedYearBeforeIncomesRegistry\">\r\n                {{ calculation.salaryDate | date : \"dd.MM\" }}\r\n              </b>\r\n              <b ng-if=\"$ctrl.isSelectedYearBeforeIncomesRegistry\">\r\n                {{ calculation.paidAt | date : \"dd.MM\" }}\r\n              </b>\r\n            </td>\r\n            <td class=\"right\">\r\n              {{ calculation.totals.totalGrossSalary | currency : \"€\" : 2 }}<br /> {{ calculation.totals.totalTaxable | currency : \"€\" : 2 }}\r\n            </td>\r\n            <td class=\"right\">\r\n              {{ calculation.totals.totalExpenses | currency : \"€\" : 2 }}\r\n            </td>\r\n            <td ng-controller=\"CalcReportsDisplayController as $displayCtrl\">\r\n              <a ng-href=\"#/calc/details/{{ calculation.id }}\" class=\"btn btn-secondary btn-xs\"><span\r\n                  sxy-text=\"SALAXY.NG1.WorkerReportComponent.table.calculationBtn\"></span>&nbsp;&raquo;</a><br />\r\n              <button ng-click=\"$displayCtrl.displayForId('salarySlip', calculation.id)\" class=\"btn btn-primary btn-xs\"><span\r\n                  sxy-text=\"SALAXY.NG1.WorkerReportComponent.table.printBtn\"></span>&nbsp;&raquo;</button><br />\r\n            </td>\r\n            <td class=\"right\">\r\n              {{ calculation.workerCalc.tax > 0 ? (calculation.workerCalc.tax | currency : \"€\" : 2) : \"-\" }}\r\n            </td>\r\n            <td class=\"right\">\r\n              {{ calculation.salary.isDeductible ? (calculation.employerCalc.householdDeduction | currency : \"€\" : 2) : \"-\" }}\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n      <br />\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/records/Records.html\",`<div class=\"salaxy-component salaxy-records\">\r\n  <table class=\"table\">\r\n    <thead>\r\n      <tr>\r\n        <th>{{\"SALAXY.NG1.WorkerDetailsComponent.records.recordType\" | sxyTranslate}}</th>\r\n        <th>{{\"SALAXY.NG1.WorkerDetailsComponent.records.title\" | sxyTranslate}}</th>\r\n        <th>{{\"SALAXY.NG1.WorkerDetailsComponent.records.text\" | sxyTranslate}}</th>\r\n        <th>{{\"SALAXY.NG1.WorkerDetailsComponent.records.startDate\" | sxyTranslate}}</th>\r\n        <th>{{\"SALAXY.NG1.WorkerDetailsComponent.records.badge\" | sxyTranslate}}</th> \r\n        <th class=\"text-end\">\r\n          <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-if=\"!$ctrl.readOnly\" ng-click=\"$ctrl.showEditRecord({attachments: []})\" sxy-text=\"SALAXY.UI_Terms.add\"></button>\r\n        </th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat=\"item in $ctrl.records\">\r\n        <td>{{item.recordType}}</td>\r\n        <td>{{item.title}}</td>\r\n        <td>\r\n          <span ng-if=\"!('markdown' | sxyIsInRole)\">{{item.text}}</span>\r\n          <p  ng-if=\"'markdown' | sxyIsInRole\"  style=\"\r\n  display: -webkit-box;\r\n  -webkit-line-clamp: 3; /* Number of lines you want to display */\r\n  -webkit-box-orient: vertical;\r\n  overflow: hidden;\r\n  text-overflow: ellipsis;\r\n  white-space: normal;\r\n  word-break: break-word; /* For older browsers */\r\n  overflow-wrap: break-word; \">\r\n            <salaxy-input-markdown read-only=\"true\" ng-model=\"item.text\" name=\"{{ 'md-viewer' + $index }}\" label-type=\"plain\"></salaxy-input-markdown>\r\n          </p>\r\n          <div ng-repeat=\"attachment in item.attachments\">\r\n            <a target=\"_blank\" ng-href=\"{{$ctrl.getAttachmentDownloadUrl(attachment)}}\">\r\n              <i class=\"bi {{ $ctrl.getAttachmentIcon(attachment) }} text-primary me-1\"></i>{{attachment.fileName}}\r\n            </a>\r\n          </div>\r\n        </td>\r\n        <td>{{ item.startDate | date }}</td>\r\n        <td>\r\n          <div ng-repeat=\"wfEvent in $ctrl.getEvents(item)\">\r\n            <salaxy-workflow-badge ng-if=\"wfEvent.message\" model=\"{ workflowData:  { events: [wfEvent]}}\"  wf-types=\"'EmployerMessageRecord'\"></salaxy-workflow-badge>\r\n          </div>\r\n        </td>\r\n        <td class=\"text-end\" ng-if=\"!$ctrl.readOnly\">\r\n          <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-click=\"$ctrl.showEditRecord(item, $index)\">\r\n            <i class=\"bi bi-pencil-fill\" title=\"{{'SALAXY.UI_Terms.edit' | sxyTranslate}}\"></i>\r\n          </button>\r\n          <button type=\"button\" class=\"btn btn-danger btn-xs\" ng-click=\"$ctrl.deleteRecord(item, $index)\">\r\n            <i class=\"bi bi-trash\" title=\"{{'SALAXY.UI_Terms.deleteRow' | sxyTranslate}}\"></i>\r\n          </button>\r\n        </td>\r\n        <td class=\"text-end\" ng-if=\"$ctrl.readOnly\">\r\n          <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-click=\"$ctrl.showEditRecord(item, $index)\">\r\n            <i class=\"bi bi-info-circle\" title=\"{{'SALAXY.UI_Terms.show' | sxyTranslate}}\"></i>\r\n          </button>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/report/AccountingHolidayPayDebtReportQuery.html\",`<div class=\"salaxy-component salaxy-accounting-report-query\">\r\n  <form name=\"queryForm\" class=\"form-horizontal\">\r\n    <div ng-show=\"false\" ng-init=\"$ctrl.queryForm = queryForm\"></div>\r\n    <fieldset>\r\n      <div class=\"col col-md-6\">\r\n        <salaxy-datepicker-popup name=\"refDate\" ng-model=\"$ctrl.refDate\" label=\"Velan päivämäärä\" require=\"true\" ng-change=\"$ctrl.query()\"></salaxy-datepicker-popup>\r\n      </div>\r\n    </fieldset>\r\n  </form>\r\n  <div class=\"col col-md-12 text-right\">\r\n    <button class=\"btn btn-primary\" ng-disabled=\"!$ctrl.queryForm.$valid\" ng-click=\"$ctrl.queryData($reportTools.targetId)\" sxy-text=\"SALAXY.NG1.AccountingReportQueryComponent.queryRows\"></button>\r\n  </div>\r\n\r\n  <salaxy-accounting-report-tools ng-ref=\"$reportTools\" any-expanded=\"$reportRows.anyExpanded\" on-expand-change=\"$reportRows.expand(close)\" on-target-change=\"$ctrl.queryData(targetId)\" reader=\"$ctrl.dataReader\" view=\"$ctrl.view\"></salaxy-accounting-report-tools>\r\n  <salaxy-accounting-report-rows lang=\"$ctrl.lang\" ng-ref=\"$reportRows\" data=\"$ctrl.data\" view=\"$ctrl.view\"></salaxy-accounting-report-rows>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/report/AccountingReportList.html\",`<div class=\"salaxy-component salaxy-accounting-report-list\">\r\n  <salaxy-odata-table ng-if=\"$ctrl.mode != 'panel'\" crud-controller=\"AccountingReportCrudController as $crud\" template-url=\"salaxy-components/odata/lists/AccountingReports.html\" options=\"{ $filter: $ctrl.getODataFilter(), $orderby: 'logicalDate desc' }\">\r\n  </salaxy-odata-table>\r\n  <salaxy-odata-table ng-if=\"$ctrl.mode == 'panel'\" crud-controller=\"AccountingReportCrudController as $crud\" template-url=\"salaxy-components/odata/lists/AccountingReportsPanel.html\" options=\"$ctrl.panelQueryOptions\">\r\n  </salaxy-odata-table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/report/AccountingReportQuery.html\",`<div class=\"salaxy-component salaxy-accounting-report-query\">\r\n  <form name=\"queryForm\" ng-if=\"!$ctrl.calcs\" class=\"form-horizontal\">\r\n    <div ng-show=\"false\" ng-init=\"$ctrl.queryForm = queryForm\"></div>\r\n    <fieldset>\r\n      <div class=\"row\">\r\n        <div class=\"col col-6\">\r\n          <salaxy-input-enum name=\"queryType\" label=\"SALAXY.NG1.AccountingReportQueryComponent.reportCalcsLabel\" options=\"{periodQuery: ('SALAXY.NG1.AccountingReportQueryComponent.periodQueryEnum' | sxyTranslate), selectionQuery: ('SALAXY.NG1.AccountingReportQueryComponent.selectionQueryEnum' | sxyTranslate) }\"\r\n          ng-model=\"$ctrl.queryType\" type=\"radio\" required></salaxy-input-enum>\r\n        </div>\r\n        <div class=\"col col-6\" ng-if=\"$ctrl.queryType == 'selectionQuery'\">\r\n          <p>\r\n            <span class=\"label label-primary\" ng-if=\"$ctrl.calculations.length\"> <span sxy-text=\"SALAXY.UI_Terms.chosen\" ps=\":\"></span>{{ $ctrl.calculations.length }}</span>\r\n          </p>\r\n          <div class=\"btn-toolbar\" role=\"toolbar\">\r\n            <button class=\"btn btn-default\" ng-click=\"$ctrl.addCalcs('paid')\" sxy-text=\"SALAXY.NG1.AccountingReportQueryComponent.addPaidCalcs\"></button>\r\n            <button class=\"btn btn-default\" ng-click=\"$ctrl.addCalcs('draft')\" sxy-text=\"SALAXY.NG1.AccountingReportQueryComponent.addDraftCalcs\"></button>\r\n          </div>\r\n        </div>\r\n        <div class=\"col col-6\" ng-if=\"$ctrl.queryType == 'periodQuery'\">\r\n          <salaxy-input-enum name=\"periodDateKind\" label=\"SALAXY.NG1.AccountingReportQueryComponent.periodDateKindLabel\" enum=\"PeriodDateKind\"\r\n          ng-model=\"$ctrl.periodDateKind\" type=\"radio\" required></salaxy-input-enum>\r\n        </div>\r\n      </div>\r\n      <div class=\"row\">\r\n        <div class=\"col col-6\" ng-if=\"$ctrl.queryType == 'periodQuery'\">\r\n          <salaxy-input-enum name=\"period\" label=\"SALAXY.NG1.AccountingReportQueryComponent.period\" options=\"{month: ('SALAXY.NG1.AccountingReportQueryComponent.monthEnum' | sxyTranslate), custom: ('SALAXY.NG1.AccountingReportQueryComponent.customEnum' | sxyTranslate) }\"\r\n          ng-model=\"$ctrl.periodType\" type=\"radio\" required></salaxy-input-enum>\r\n        </div>\r\n        <div class=\"col col-6\" ng-if=\"$ctrl.queryType == 'periodQuery'\">\r\n          <salaxy-datepicker-popup name=\"refDateMonth\" placeholder=\"SALAXY.NG1.AccountingReportQueryComponent.monthPlaceHolder\" ng-if=\"$ctrl.periodType == 'month'\" format=\"month\" ng-model=\"$ctrl.refDate\"\r\n            label=\"SALAXY.NG1.AccountingReportQueryComponent.refDateMonthLabel\" require=\"true\"></salaxy-datepicker-popup>\r\n          <salaxy-datepicker-popup name=\"refDateQuarter\" placeholder=\"SALAXY.NG1.AccountingReportQueryComponent.monthPlaceHolder\" ng-if=\"$ctrl.periodType == 'quarter'\" format=\"month\" ng-model=\"$ctrl.refDate\"\r\n            label=\"SALAXY.NG1.AccountingReportQueryComponent.refDateQuarterLabel\" require=\"true\"></salaxy-datepicker-popup>\r\n          <salaxy-datepicker-popup name=\"refDateYear\" placeholder=\"SALAXY.NG1.AccountingReportQueryComponent.yearPlaceholder\" ng-if=\"$ctrl.periodType == 'year'\" format=\"year\" ng-model=\"$ctrl.refDate\"\r\n            label=\"SALAXY.NG1.AccountingReportQueryComponent.refDateYearLabel\" require=\"true\"></salaxy-datepicker-popup>\r\n          <salaxy-datepicker-popup name=\"refDateCustom\" ng-if=\"$ctrl.periodType == 'custom'\" ng-model=\"$ctrl.refDate\" label=\"SALAXY.NG1.AccountingReportQueryComponent.refDateCustomLabel\" require=\"true\"></salaxy-datepicker-popup>\r\n          <salaxy-datepicker-popup name=\"endDateCustom\" ng-if=\"$ctrl.periodType == 'custom'\" ng-model=\"$ctrl.endDate\" label=\"SALAXY.NG1.AccountingReportQueryComponent.endDateCustomLabel\"></salaxy-datepicker-popup>\r\n        </div>\r\n      </div>\r\n    </fieldset>\r\n    <div ng-if=\"$ctrl.queryType == 'selectionQuery'\" class=\"col col-md-12\">\r\n      <div ng-if=\"$ctrl.calculations.length\" class=\"table-responsive salaxy-odata-table\">\r\n        <table class=\"table table-striped\">\r\n          <thead>\r\n            <tr>\r\n              <th colspan=\"2\">\r\n                <span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span>\r\n              </th>\r\n              <th class=\"hidden-xxs\">\r\n                <span sxy-text=\"SALAXY.NG1.AccountingReportQueryComponent.status\"></span><br />\r\n                <span><span sxy-text=\"SALAXY.NG1.AccountingReportQueryComponent.date\"></span></span>\r\n              </th>\r\n              <th class=\"right hidden-xxs\">\r\n                <span sxy-text=\"SALAXY.NG1.AccountingReportQueryComponent.salary\"></span><br />\r\n                <span><span sxy-text=\"SALAXY.NG1.AccountingReportQueryComponent.payment\"></span></span>\r\n              </th>\r\n              <th class=\"hidden-xxs\"></th>\r\n            </tr>\r\n          </thead>\r\n          <tbody>\r\n            <tr ng-repeat=\"row in $ctrl.calculations\">\r\n              <td class=\"td-avatar visible-xxs middle\">\r\n                <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n              </td>\r\n              <td class=\"td-name visible-xxs middle\">\r\n                <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.AccountingReportQueryComponent.notSelected\"></span>\r\n                <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br /> {{ \"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate }}\r\n                <br /> {{ row.endAt | date }}\r\n              </td>\r\n              <td class=\"right visible-xxs bottom\">\r\n                <div>\r\n                  {{ row.grossSalary | currency }}<br /> {{ row.payment | currency }}\r\n                </div>\r\n              </td>\r\n              <td class=\"td-avatar hidden-xxs middle\">\r\n                <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n              </td>\r\n              <td class=\"td-name hidden-xxs middle\">\r\n                <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.AccountingReportQueryComponent.notSelected\"></span>\r\n                <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br />\r\n              </td>\r\n              <td class=\"hidden-xxs middle\">\r\n                {{ row.status ? (\"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate) : \"#ERR\" }}<br /> {{ row.endAt | date }}\r\n              </td>\r\n              <td class=\"right hidden-xxs middle\">\r\n                {{ row.grossSalary | currency }}<br /> {{ row.payment | currency }}\r\n              </td>\r\n              <td class=\"right middle\">\r\n                <button class=\"btn btn-sm  btn-danger\" type=\"button\" ng-click=\"$ctrl.removeCalc(row)\">\r\n                      {{ 'SALAXY.UI_Terms.unselect' | sxyTranslate }}\r\n                    </button>\r\n              </td>\r\n            </tr>\r\n          </tbody>\r\n        </table>\r\n      </div>\r\n    </div>\r\n  </form>\r\n  <div ng-if=\"!$ctrl.calcs\" class=\"col col-md-12 text-end\">\r\n    <button class=\"btn btn-primary\" ng-disabled=\"!$ctrl.queryForm.$valid\" ng-click=\"$ctrl.queryData($reportTools.targetId)\" sxy-text=\"SALAXY.NG1.AccountingReportQueryComponent.queryRows\"></button>\r\n  </div>\r\n\r\n  <salaxy-accounting-report-tools ng-ref=\"$reportTools\" any-expanded=\"$reportRows.anyExpanded\" on-expand-change=\"$reportRows.expand(close)\" on-target-change=\"$ctrl.queryData(targetId)\" reader=\"$ctrl.dataReader\" view=\"$ctrl.view\"></salaxy-accounting-report-tools>\r\n  <salaxy-accounting-report-rows lang=\"$ctrl.lang\" ng-ref=\"$reportRows\" data=\"$ctrl.data\" view=\"$ctrl.view\"></salaxy-accounting-report-rows>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/report/AccountingReportRows.html\",`<div class=\"salaxy-component salaxy-accounting-report-rows\">\r\n  <table ng-if=\"$ctrl.view != 'full'\" class=\"table table-sm\">\r\n    <thead style=\"display: table-header-group;\">\r\n      <tr>\r\n        <th class=\"col-md-3\" sxy-text=\"SALAXY.NG1.AccountingReportRowsComponent.accountNumber\"></th>\r\n        <th class=\"col-md-6\" sxy-text=\"SALAXY.NG1.AccountingReportRowsComponent.accountName\"></th>\r\n        <th class=\"col-md-3 right\" sxy-text=\"SALAXY.NG1.AccountingReportRowsComponent.saldo\"></th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat-start=\"ledgerAccount in ($ctrl.data || {}).ledgerAccounts\">\r\n        <td>{{ledgerAccount.accountNumber }}</td>\r\n        <td>{{ledgerAccount.accountName}}</td>\r\n        <td class=\"right\"><a ng-click=\"ledgerAccount.rowToggle = !ledgerAccount.rowToggle\">{{ledgerAccount.saldo | currency}}</a></td>\r\n      </tr>\r\n      <tr ng-if=\"ledgerAccount.rowToggle\" ng-repeat-end>\r\n        <td colspan=\"3\">\r\n          <table class=\"table table-sm\">\r\n            <thead>\r\n              <tr class=\"toggled-rows\">\r\n                <th class=\"col-md-3\" sxy-text=\"SALAXY.NG1.AccountingReportRowsComponent.calculation\"></th>\r\n                <th class=\"col-md-6\" sxy-text=\"SALAXY.NG1.AccountingReportRowsComponent.description\"></th>\r\n                <th class=\"col-md-1 right\" sxy-text=\"SALAXY.NG1.AccountingReportRowsComponent.vatPercent\"></th>\r\n                <th class=\"col-md-2 right\" sxy-text=\"SALAXY.NG1.AccountingReportRowsComponent.sum\"></th>\r\n              </tr>\r\n            </thead>\r\n            <tbody>\r\n              <tr ng-repeat=\"entry in ledgerAccount.entries\" class=\"toggled-rows\">\r\n                <td>\r\n                  <a ng-if=\"entry.dimension.calculationId\" ng-href=\"#/calc/details/{{entry.dimension.calculationId}}\">{{entry.dimension.calculationTitle}}</a>\r\n                  <a ng-if=\"!entry.dimension.calculationId && entry.dimension.employmentId\" ng-href=\"#/employments/details/{{entry.dimension.employmentId}}\">{{entry.dimension.workerName}}</a>\r\n                </td>\r\n                <td>{{entry.description}}\r\n                  <div ng-if=\"entry.dimension.projectNumber\">{{'SALAXY.NG1.AccountingReportRowsComponent.projectNumber' | sxyTranslate}}: {{entry.dimension.projectNumber}}</div>\r\n                  <div ng-if=\"entry.dimension.costCenter\">{{'SALAXY.NG1.AccountingReportRowsComponent.costCenter' | sxyTranslate}}: {{entry.dimension.costCenter}}</div>\r\n                  <div ng-if=\"entry.dimension.dimensions\" ng-repeat=\"(k,v) in entry.dimension.dimensions\">\r\n                    {{k}}: {{v}}\r\n                  </div>\r\n                </td>\r\n                <td class=\"right\"><span ng-if=\"entry.vatPercent >= 0\">{{ entry.vatPercent | sxyCount : 'percent'}}</span></td>\r\n                <td class=\"right\">{{!entry.isDebit ? -1 * entry.amount : entry.amount | currency}}</td>\r\n              </tr>\r\n            </tbody>\r\n          </table>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n  <div ng-if=\"$ctrl.view == 'full'\">\r\n    <div ng-bind-html=\"$ctrl.html\" class=\"report-binder table-responsive\"></div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/report/AccountingReportTools.html\",`<div class=\"salaxy-component salaxy-accounting-report-tools\">\r\n  <div class=\"btn-toolbar\" role=\"toolbar\" aria-label=\"Report options\">\r\n    <div class=\"btn-group btn-group-sm dropdown\">\r\n      <button id=\"reportOptionsTarget\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\">\r\n        {{'SALAXY.NG1.AccountingReportToolsComponent.target' | sxyTranslate}}: <img style=\"height: 15px;\" ng-if=\"$ctrl.getTarget($ctrl.targetId).avatar.url\" ng-src=\"{{$ctrl.getTarget($ctrl.targetId).avatar.url}}\">&nbsp;{{$ctrl.getTarget($ctrl.targetId).avatar.displayName}}\r\n      </button>\r\n      <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"reportOptionsTarget\">\r\n        <li ng-repeat=\"target in $ctrl.targets\" role=\"menuitem\">\r\n          <a href=\"\" ng-click=\"$ctrl.changeTarget(target.id)\" class=\"dropdown-item\"><img style=\"height: 20px;\" ng-if=\"$ctrl.getTarget(target.id).avatar.url\" ng-src=\"{{$ctrl.getTarget(target.id).avatar.url}}\">&nbsp;{{$ctrl.getTarget(target.id).avatar.displayName}}</a>\r\n        </li>\r\n        <li role=\"menuitem\"><button class=\"btn btn-link dropdown-item\" ng-click=\"$ctrl.navigate('/settings/accounting-target-settings')\" sxy-text=\"SALAXY.NG1.AccountingReportToolsComponent.settingsAddMoreTargets\" ps=\"...\"></button></li>\r\n      </ul>\r\n    </div>\r\n    <div class=\"btn-group btn-group-sm dropdown ms-1\" ng-if=\"$ctrl.getTarget($ctrl.targetId).schemes.length\">\r\n      <button id=\"reportOptionsScheme\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\">\r\n        {{$ctrl.getScheme($ctrl.schemeId).label}}\r\n      </button>\r\n      <ul class=\"dropdown-menu\"  role=\"menu\" aria-labelledby=\"reportOptionsScheme\">\r\n        <li ng-repeat=\"scheme in $ctrl.getTarget($ctrl.targetId).schemes\" role=\"menuitem\">\r\n          <a href=\"\" ng-click=\"$ctrl.schemeId = scheme.id\" class=\"dropdown-item\">{{$ctrl.getScheme(scheme.id).label}}</a>\r\n        </li>\r\n      </ul>\r\n    </div>\r\n    <div class=\"btn-group btn-group-sm dropdown ms-1\">\r\n      <button id=\"reportOptionsExportMethod\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\">\r\n        {{$ctrl.getExportMethod($ctrl.exportMethod).label}}\r\n      </button>\r\n      <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"reportOptionsExportMethod\">\r\n        <li role=\"menuitem\" ng-repeat=\"exportMethod in $ctrl.exportMethods\">\r\n          <a href=\"\" ng-click=\"$ctrl.exportMethod = exportMethod.id\" class=\"dropdown-item\">{{$ctrl.getExportMethod(exportMethod.id).label}}</a>\r\n        </li>\r\n      </ul>\r\n    </div>\r\n    <div class=\"btn-group btn-group-sm dropdown ms-1\">\r\n      <button id=\"reportOptionsCulture\" type=\"button\" class=\"btn btn-default dropdown-toggle\" ng-disabled=\"!$ctrl.getExportMethod($ctrl.exportMethod).hasLocales\" data-bs-toggle=\"dropdown\">\r\n        {{$ctrl.getLocale($ctrl.localeId).label}}\r\n      </button>\r\n      <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"reportOptionsCulture\">\r\n        <li role=\"menuitem\">\r\n          <a href=\"\" ng-click=\"$ctrl.localeId = 'fi'\" class=\"dropdown-item\">{{$ctrl.getLocale('fi').description}}</a>\r\n        </li>\r\n        <li role=\"menuitem\">\r\n          <a href=\"\" ng-click=\"$ctrl.localeId = 'en'\" class=\"dropdown-item\">{{$ctrl.getLocale('en').description}}</a>\r\n        </li>\r\n      </ul>\r\n    </div>\r\n    <div class=\"btn-group btn-group-sm ms-1\">\r\n      <button ng-disabled=\"$ctrl.reader.disabled()\" id=\"reportExport\" type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.export()\">\r\n        {{ $ctrl.reader.exportLabel || ('SALAXY.NG1.AccountingReportToolsComponent.createExport' | sxyTranslate) }}  \r\n      </button>\r\n    </div>\r\n    <div class=\"ms-auto\" ng-if=\"$ctrl.reader.showExpand && $ctrl.view == 'partial'\">\r\n      <button ng-if=\"!$ctrl.anyExpanded\" ng-disabled=\"$ctrl.reader.hasRows()\" class=\"btn btn-block btn-transparent p-0\" title=\"{{'SALAXY.NG1.AccountingReportToolsComponent.showRowsAndExports' | sxyTranslate}}\" ng-click=\"$ctrl.expand()\">\r\n        <i class=\"bi bi-arrows-angle-expand\"></i>\r\n      </button>\r\n      <button ng-if=\"$ctrl.anyExpanded\" ng-disabled=\"$ctrl.reader.hasRows()\" class=\"btn btn-block btn-transparent p-0\" title=\"{{'SALAXY.NG1.AccountingReportToolsComponent.showOnlyRows' | sxyTranslate}}\" ng-click=\"$ctrl.expand(true)\">\r\n        <i class=\"bi bi-arrows-angle-contract\"></i>\r\n      </button>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/report/AccountingReportViewer.html\",`<div class=\"btn-toolbar\" role=\"toolbar\" salaxy-if-role=\"test,pro\">\r\n  <salaxy-accounting-report-tools any-expanded=\"$reportRows.anyExpanded\" on-expand-change=\"$reportRows.expand(close)\" on-target-change=\"$ctrl.loadCurrentData(targetId)\" reader=\"$ctrl.currentDataReader\"></salaxy-accounting-report-tools>\r\n  <salaxy-workflow-buttons class=\"ms-auto\" disabled=\"!($ctrl.currentData && $ctrl.currentData.ledgerAccounts.length > 0)\" api-ctrl=\"$ctrl\"></salaxy-workflow-buttons>\r\n</div>\r\n<salaxy-accounting-report-rows ng-ref=\"$reportRows\" data=\"$ctrl.currentData\"></salaxy-accounting-report-rows>`);\n\n $templateCache.put(\"salaxy-components/report/AccountingRowReport.html\",`<div class=\"salaxy-component salaxy-accounting-row-report\" style=\"width:100%;height:100%;display:flex;flex-flow:column\">\r\n  <div class=\"btn-toolbar\" role=\"toolbar\">\r\n    <div class=\"btn-group\" role=\"group\" aria-label=\"{{'SALAXY.NG1.CumulativeReportComponent.chooseData' | sxyTranslate}}\">\r\n      <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.showPeriodSelection()\" sxy-text=\"SALAXY.NG1.CumulativeReportComponent.selectPeriod\" ps=\"...\"></button>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showCalcsSelection()\" sxy-text=\"SALAXY.NG1.CumulativeReportComponent.selectCalcs\" ps=\"...\"></button>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showPayrollSelection()\" sxy-text=\"SALAXY.NG1.CumulativeReportComponent.selectPayrolls\" ps=\"...\"></button>\r\n    </div>\r\n    <div class=\"btn-group ms-1\" role=\"group\" aria-label=\"{{'SALAXY.NG1.CumulativeReportComponent.reportTemplates' | sxyTranslate}}\">\r\n      <div class=\"btn-group btn-group dropdown\">\r\n        <button id=\"templateId\" type=\"button\" class=\"btn btn-default dropdown-toggle\" ng-disabled=\"!$ctrl.data\" data-bs-toggle=\"dropdown\">\r\n          <span ng-if=\"$ctrl.data\">\r\n            <salaxy-avatar style=\"font-size: 1.8em; margin: -2px 4px -2px -2px;\" avatar=\"$ctrl.getTemplate($ctrl.templateId).avatar\"></salaxy-avatar> {{$ctrl.getTemplate($ctrl.templateId).label}}\r\n          </span>\r\n          <span ng-if=\"!$ctrl.data\" sxy-text=\"SALAXY.NG1.CumulativeReportComponent.reportTemplates\"></span>\r\n        </button>\r\n        <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"templateId\">\r\n          <li role=\"menuitem\" ng-repeat=\"template in $ctrl.templates\">\r\n            <a href=\"\" ng-click=\"$ctrl.selectTemplate(template.id)\" class=\"dropdown-item\">\r\n               <salaxy-avatar style=\"font-size: 1.8em; margin: -2px 4px -2px -2px;\" avatar=\"$ctrl.getTemplate(template.id).avatar\"></salaxy-avatar> {{$ctrl.getTemplate(template.id).label}}\r\n            </a>\r\n          </li>\r\n        </ul>\r\n      </div>\r\n      <button type=\"button\" class=\"btn btn-default ms-1\"  ng-disabled=\"!$ctrl.data\" ng-click=\"$ctrl.showSaveTemplate()\">{{'SALAXY.UI_Terms.edit' | sxyTranslate}}...</button>\r\n    </div>\r\n  </div>\r\n  <div style=\"height:100%;flex-grow:1\">\r\n    <div id=\"dataGrid\" class=\"ag-theme-balham\" style=\"height:100%;overflow: hidden;\"></div>\r\n  </div>\r\n</div>\r\n`);\n\n $templateCache.put(\"salaxy-components/report/CalculationReport.html\",`<div class=\"salaxy-component salaxy-calculation-report\" style=\"width:100%;height:100%;display:flex;flex-flow:column\">\r\n  <div class=\"btn-toolbar\" role=\"toolbar\">\r\n    <div class=\"btn-group\" role=\"group\" aria-label=\"{{'SALAXY.NG1.CumulativeReportComponent.chooseData' | sxyTranslate}}\">\r\n      <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.showPeriodSelection()\" sxy-text=\"SALAXY.NG1.CumulativeReportComponent.selectPeriod\" ps=\"...\"></button>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showCalcsSelection()\" sxy-text=\"SALAXY.NG1.CumulativeReportComponent.selectCalcs\" ps=\"...\"></button>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showPayrollSelection()\" sxy-text=\"SALAXY.NG1.CumulativeReportComponent.selectPayrolls\" ps=\"...\"></button>\r\n    </div>\r\n    <div class=\"btn-group\" role=\"group\" aria-label=\"{{'SALAXY.NG1.CumulativeReportComponent.reportTemplates' | sxyTranslate}}\">\r\n      <div class=\"btn-group btn-group dropdown\">\r\n        <button id=\"templateId\" type=\"button\" class=\"btn btn-default dropdown-toggle\" ng-disabled=\"!$ctrl.data\" data-bs-toggle=\"dropdown\">\r\n          <span ng-if=\"$ctrl.data\">\r\n            <salaxy-avatar style=\"font-size: 1.8em; margin: -2px 4px -2px -2px;\" avatar=\"$ctrl.getTemplate($ctrl.templateId).avatar\"></salaxy-avatar> {{$ctrl.getTemplate($ctrl.templateId).label}}\r\n          </span>\r\n          <span ng-if=\"!$ctrl.data\" sxy-text=\"SALAXY.NG1.CumulativeReportComponent.reportTemplates\"></span>\r\n        </button>\r\n        <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"templateId\">\r\n          <li role=\"menuitem\" ng-repeat=\"template in $ctrl.templates\">\r\n            <a href=\"\" ng-click=\"$ctrl.selectTemplate(template.id)\" class=\"dropdown-item\">\r\n               <salaxy-avatar style=\"font-size: 1.8em; margin: -2px 4px -2px -2px;\" avatar=\"$ctrl.getTemplate(template.id).avatar\"></salaxy-avatar> {{$ctrl.getTemplate(template.id).label}}\r\n            </a>\r\n           </li>\r\n        </ul>\r\n      </div>\r\n      <button type=\"button\" class=\"btn btn-default ms-1\"  ng-disabled=\"!$ctrl.data\" ng-click=\"$ctrl.showSaveTemplate()\">{{'SALAXY.UI_Terms.edit' | sxyTranslate}}...</button>\r\n    </div>\r\n  </div>\r\n  <div style=\"height:100%;flex-grow:1\">\r\n    <div id=\"dataGrid\" class=\"ag-theme-balham\" style=\"height:100%;overflow: hidden;\"></div>\r\n  </div>\r\n</div>\r\n`);\n\n $templateCache.put(\"salaxy-components/report/HolidayPayReportQuery.html\",`<div class=\"salaxy-component salaxy-holiday-pay-report-query\">\r\n  <div ng-if=\"$ctrl.data.holidayYear.employmentId\" class=\"salaxy-calc-worker-info\" ng-controller=\"EmploymentCrudController as $employmentCtrl\" ng-init=\"$employmentCtrl.model=$ctrl.data.holidayYear.employmentId\">\r\n    <div class=\"row spacer-bottom\" ng-if=\"$employmentCtrl.current\">\r\n      <div class=\"col-xs-3 col-sm-2 col-xxs-3\">\r\n        <salaxy-avatar avatar=\"$employmentCtrl.current.personalInfo.avatar\"></salaxy-avatar>\r\n      </div>\r\n      <div class=\"col-xs-9 col-sm-10 col-xxs-9 worker-info-col\">\r\n        <h2>{{ $employmentCtrl.current.personalInfo.avatar.displayName || (\"SALAXY.NG1.WorkerInfo.noSelection\" | sxyTranslate) }}</h2>\r\n        <div class=\"row\" ng-if=\"$employmentCtrl.current\">\r\n          <div class=\"col-xs-12 col-sm-6 \">\r\n            <div ng-class=\"$employmentCtrl.current.personalInfo.officialId ? '' : 'text-danger'\">\r\n              {{ $employmentCtrl.current.personalInfo.officialId || ( \"SALAXY.NG1.PaymentDialogComponent.noSSNumber\" | sxyTranslate ) }}\r\n              &nbsp;\r\n              <div class=\"btn-group\" ng-if=\"$employmentCtrl.otherEmployments.length > 0\">\r\n                <button id=\"single-button\" type=\"button\" class=\"btn btn-default btn-xs dropdown-toggle\" \r\n                  data-bs-toggle=\"dropdown\" aria-expanded=\"false\">\r\n                  {{ $employmentCtrl.otherEmployments.length }} muuta työsuhdetta\r\n                </button>\r\n                <ul class=\"dropdown-menu\" aria-labelledby=\"single-button\">\r\n                  <li ng-repeat=\"item in $employmentCtrl.otherEmployments\">\r\n                    <a class=\"dropdown-item\" ng-href=\"{{$employmentCtrl.isModal ? '' : ('#/employments/details/' + item.id)}}\">\r\n                      {{ $employmentCtrl.getEmploymentDescription(item) }} \r\n                      ({{ $employmentCtrl.getActiveText(item) }})\r\n                    </a>\r\n                  </li>\r\n                </ul>\r\n              </div>\r\n              <span ng-if=\"!$employmentCtrl.otherEmployments\">Tarkistetaan muita työsuhteita...</span>\r\n            </div>\r\n            <div>{{ $employmentCtrl.getEmploymentDescription($employmentCtrl.current) }}</div>\r\n            <div>{{ $employmentCtrl.getActiveText($employmentCtrl.current) }}</div>\r\n            <div><small>{{ $employmentCtrl.current.id }}</small></div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"row\">\r\n      <div class=\"col-sm-6\">\r\n        <form class=\"form-horizontal\">\r\n            <salaxy-input-enum  name=\"year\"  ng-model=\"$ctrl.year\"   label=\"SALAXY.NG1.HolidayReportComponent.holidayYear\" options=\"$ctrl.years\" ng-change=\"$ctrl.query()\"></salaxy-input-enum>\r\n            <salaxy-input-enum ng-if=\"$ctrl.data.holidayYear.spec.code == 'permanent14Days' || $ctrl.data.holidayYear.spec.code == 'permanent35Hours' || $ctrl.data.holidayYear.spec.code == 'temporaryTimeOff' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script'\" name=\"holidayPayCalculation\" ng-model=\"$ctrl.data.holidayYear.spec.holidayPayCalculation\" disabled=\"true\" label=\"SALAXY.MODEL.HolidaySpecificationForYear.holidayPayCalculation.title\" enum=\"HolidayPayCalculation\"></salaxy-input-enum>\r\n            <salaxy-input-enum name=\"holidayCode\" ng-model=\"$ctrl.data.holidayYear.spec.code\" disabled=\"true\" label=\"SALAXY.MODEL.HolidaySpecificationForYear.code.title\" enum=\"HolidayCode\"></salaxy-input-enum>\r\n            <salaxy-input-enum name=\"wageBasis\" ng-model=\"$ctrl.data.holidayYear.spec.wageBasis\" disabled=\"true\" label=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.wageBasis\" enum=\"WageBasis\"></salaxy-input-enum>   \r\n        </form>\r\n      </div>\r\n      <div class=\"col-sm-6\">\r\n        <form class=\"form-horizontal\" ng-if=\"$ctrl.data.holidayYear.spec.code == 'permanent14Days' || $ctrl.data.holidayYear.spec.code == 'permanent35Hours' || $ctrl.data.holidayYear.spec.code == 'temporaryTimeOff' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script'\">\r\n\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.accrual.total\" name=\"accrualTotal\"   disabled=\"true\" label=\"Lomavuoden kertymä\" ></salaxy-input-number>\r\n\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.otherPay\" ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'otherPay'\" name=\"otherPay\"   disabled=\"true\"  label=\"SALAXY.MODEL.HolidayPay.otherPay.title\" ></salaxy-input-number>\r\n\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.scriptPay\" ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'scriptPay'\" name=\"scriptPay\"   disabled=\"true\"  label=\"SALAXY.MODEL.HolidayPay.scriptPay.title\" ></salaxy-input-number>\r\n\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.normalMonthlyPayDailySalary\" name=\"normalMonthlyPayDailySalary\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'permanent14Days' || $ctrl.data.holidayYear.spec.code == 'permanent35Hours' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && $ctrl.data.holidayYear.spec.wageBasis =='monthly' && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'normalMonthlyPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.normalMonthlyPayDailySalary.title\" ></salaxy-input-number>\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.normalMonthlyPayManual\" name=\"normalMonthlyPayManual\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'permanent14Days' || $ctrl.data.holidayYear.spec.code == 'permanent35Hours' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && $ctrl.data.holidayYear.spec.wageBasis =='monthly' && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'normalMonthlyPay'\"  disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.normalMonthlyPayManual.title\" ></salaxy-input-number>\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.normalMonthlyPay\" name=\"normalMonthlyPay\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'permanent14Days' || $ctrl.data.holidayYear.spec.code == 'permanent35Hours' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && $ctrl.data.holidayYear.spec.wageBasis =='monthly' && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'normalMonthlyPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.normalMonthlyPay.title\" ></salaxy-input-number>\r\n\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.averageDailyPayDailySalary\" name=\"averageDailyPayDailySalary\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'permanent14Days' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && ($ctrl.data.holidayYear.spec.wageBasis =='hourly' || $ctrl.data.holidayYear.spec.wageBasis =='performanceBased' || $ctrl.data.holidayYear.spec.wageBasis =='other') && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.averageDailyPayDailySalary.title\" ></salaxy-input-number>\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.averageDailyPayManual\" name=\"averageDailyPayManual\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'permanent14Days' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && ($ctrl.data.holidayYear.spec.wageBasis =='hourly' || $ctrl.data.holidayYear.spec.wageBasis =='performanceBased' || $ctrl.data.holidayYear.spec.wageBasis =='other') && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\"  disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.averageDailyPayManual.title\" ></salaxy-input-number>\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.averageDailyPay\" name=\"averageDailyPay\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'permanent14Days' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && ($ctrl.data.holidayYear.spec.wageBasis =='hourly' || $ctrl.data.holidayYear.spec.wageBasis =='performanceBased' || $ctrl.data.holidayYear.spec.wageBasis =='other') && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.averageDailyPay.title\" ></salaxy-input-number>\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.averageDailyPayBase\" name=\"averageDailyPayBase\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'permanent14Days' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && ($ctrl.data.holidayYear.spec.wageBasis =='hourly' || $ctrl.data.holidayYear.spec.wageBasis =='performanceBased' || $ctrl.data.holidayYear.spec.wageBasis =='other') && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\" disabled=\"true\"  label=\"SALAXY.MODEL.HolidayPay.averageDailyPayBase.title\" ></salaxy-input-number>\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.averageDailyPayDays\" name=\"averageDailyPayDays\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'permanent14Days' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && ($ctrl.data.holidayYear.spec.wageBasis =='hourly' || $ctrl.data.holidayYear.spec.wageBasis =='performanceBased' || $ctrl.data.holidayYear.spec.wageBasis =='other') && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.averageDailyPayDays.title\" ></salaxy-input-number>\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.averageDailyPayMultiplier\" name=\"averageDailyPayMultiplier\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'permanent14Days' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && ($ctrl.data.holidayYear.spec.wageBasis =='hourly' || $ctrl.data.holidayYear.spec.wageBasis =='performanceBased' || $ctrl.data.holidayYear.spec.wageBasis =='other') && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.averageDailyPayMultiplier.title\" ></salaxy-input-number>\r\n  \r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.averageHourlyPayDailySalary\" name=\"averageHourlyPayDailySalary\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'permanent14Days' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && ($ctrl.data.holidayYear.spec.wageBasis =='hourly' || $ctrl.data.holidayYear.spec.wageBasis =='performanceBased' || $ctrl.data.holidayYear.spec.wageBasis =='other') && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageHourlyPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.averageHourlyPayDailySalary.title\" ></salaxy-input-number>\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.averageHourlyPayManual\" name=\"averageHourlyPayManual\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'permanent14Days' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && ($ctrl.data.holidayYear.spec.wageBasis =='hourly' || $ctrl.data.holidayYear.spec.wageBasis =='performanceBased' || $ctrl.data.holidayYear.spec.wageBasis =='other') && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageHourlyPay'\"  disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.averageHourlyPayManual.title\" ></salaxy-input-number>\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.averageHourlyPay\" name=\"averageHourlyPay\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'permanent14Days' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && ($ctrl.data.holidayYear.spec.wageBasis =='hourly' || $ctrl.data.holidayYear.spec.wageBasis =='performanceBased' || $ctrl.data.holidayYear.spec.wageBasis =='other') && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageHourlyPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.averageHourlyPay.title\" ></salaxy-input-number>\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.averageHourlyPayBase\" name=\"averageHourlyPayBase\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'permanent14Days' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && ($ctrl.data.holidayYear.spec.wageBasis =='hourly' || $ctrl.data.holidayYear.spec.wageBasis =='performanceBased' || $ctrl.data.holidayYear.spec.wageBasis =='other') && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageHourlyPay'\" disabled=\"true\"  label=\"SALAXY.MODEL.HolidayPay.averageHourlyPayBase.title\" ></salaxy-input-number>\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.averageHourlyPayHours\" name=\"averageHourlyPayHours\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'permanent14Days' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && ($ctrl.data.holidayYear.spec.wageBasis =='hourly' || $ctrl.data.holidayYear.spec.wageBasis =='performanceBased' || $ctrl.data.holidayYear.spec.wageBasis =='other') && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageHourlyPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.averageHourlyPayHours.title\" ></salaxy-input-number>\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.averageHourlyPayMultiplier\" name=\"averageHourlyPayMultiplier\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'permanent14Days' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && ($ctrl.data.holidayYear.spec.wageBasis =='hourly' || $ctrl.data.holidayYear.spec.wageBasis =='performanceBased' || $ctrl.data.holidayYear.spec.wageBasis =='other') && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageHourlyPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.averageHourlyPayMultiplier.title\" ></salaxy-input-number>\r\n      \r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.percentageBasedPayDailySalary\" name=\"percentageBasedPayDailySalary\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'permanent35Hours' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'percentageBasedPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.percentageBasedPayDailySalary.title\" ></salaxy-input-number>\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.percentageBasedPayManual\" name=\"percentageBasedPayManual\" ng-if=\"$($ctrl.data.holidayYear.spec.code == 'permanent35Hours' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'percentageBasedPay'\"  disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.percentageBasedPayManual.title\" ></salaxy-input-number>\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.percentageBasedPay\" name=\"percentageBasedPay\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'permanent35Hours' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'percentageBasedPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.percentageBasedPay.title\" ></salaxy-input-number>\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.percentageBasedPayBase\" name=\"percentageBasedPayBase\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'permanent35Hours' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'percentageBasedPay'\"  disabled=\"true\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.percentageBasedPayBase.title\" ></salaxy-input-number>\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.spec.holidayPayPercent\" name=\"holidayPayPercent\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'permanent35Hours' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'percentageBasedPay'\" required unit=\"percent\"  disabled=\"true\" label=\"SALAXY.MODEL.HolidaySpecificationForYear.holidayPayPercent.title\" ></salaxy-input-number>\r\n\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.compensationPayDailySalary\" name=\"compensationPayDailySalary\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'temporaryTimeOff' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'holidayCompensation'\"  disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.compensationPayDailySalary.title\" ></salaxy-input-number>\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.compensationPayManual\" name=\"compensationPayManual\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'temporaryTimeOff' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'holidayCompensation'\"  disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.compensationPayManual.title\" ></salaxy-input-number>\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.compensationPay\" name=\"compensationPay\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'temporaryTimeOff' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'holidayCompensation'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.compensationPay.title\" ></salaxy-input-number>\r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.holidayPay.compensationPayBase\" name=\"compensationPayBase\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'temporaryTimeOff' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'holidayCompensation'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.compensationPayBase.title\" ></salaxy-input-number>        \r\n            <salaxy-input-number ng-model=\"$ctrl.data.holidayYear.spec.compensation\" name=\"compensation\" ng-if=\"($ctrl.data.holidayYear.spec.code == 'temporaryTimeOff' || $ctrl.data.holidayYear.spec.code == 'other' || $ctrl.data.holidayYear.spec.code == 'script') && $ctrl.data.holidayYear.spec.holidayPayCalculation == 'holidayCompensation'\" unit=\"percent\" required  disabled=\"true\" label=\"SALAXY.MODEL.HolidaySpecificationForYear.compensation.title\" ></salaxy-input-number>\r\n \r\n        </form>\r\n      </div>\r\n    </div>\r\n    <salaxy-tab-buttons\r\n      current-tab=\"$ctrl.currentTab\"\r\n      options=\"[\r\n        { 'value': 'calcs', 'text': 'SALAXY.NG1.HolidayPayReportQueryComponent.calculationsTab' },\r\n        { 'value': 'parameters', 'text': 'SALAXY.NG1.HolidayPayReportQueryComponent.parametersTab' }\r\n      ]\"\r\n      tabs-id=\"holidayPayReportQuery\">\r\n    </salaxy-tab-buttons>\r\n    <div class=\"tab-content\" id=\"tab-content-holidayPayReportQuery\" ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageHourlyPay' || $ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay' || $ctrl.data.holidayYear.spec.holidayPayCalculation == 'percentageBasedPay' || $ctrl.data.holidayYear.spec.holidayPayCalculation == 'holidayCompensation' || $ctrl.data.holidayYear.spec.holidayPayCalculation == 'normalMonthlyPay' || $ctrl.data.holidayYear.spec.holidayPayCalculation == 'scriptPay'\">\r\n      <div class=\"tab-pane\" id=\"calcs-tab\">\r\n        <table ng-if=\"$ctrl.currentTab == 'calcs'\" class=\"table table-striped\">\r\n          <thead>\r\n            <tr>\r\n              <th sxy-text=\"SALAXY.NG1.HolidayPayReportQueryComponent.calculation\"></th>\r\n              <th sxy-text=\"SALAXY.NG1.HolidayPayReportQueryComponent.description\"></th>\r\n              <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayPayReportQueryComponent.count\"></th>\r\n              <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayPayReportQueryComponent.price\"></th>\r\n              <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayPayReportQueryComponent.toHolidayPay\"></th>\r\n              <th class=\"right\" ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageHourlyPay'\" sxy-text=\"SALAXY.NG1.HolidayPayReportQueryComponent.toWorkingHours\"></th>\r\n              <th class=\"right\" ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\" sxy-text=\"SALAXY.NG1.HolidayPayReportQueryComponent.toOvertimeHours\"></th>\r\n              <th class=\"right\" ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\" sxy-text=\"SALAXY.NG1.HolidayPayReportQueryComponent.workingDays\"></th>\r\n              <th class=\"right\" ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\" sxy-text=\"SALAXY.NG1.HolidayPayReportQueryComponent.absenceDays\"></th>\r\n              <th sxy-text=\"SALAXY.NG1.HolidayPayReportQueryComponent.holidayPaySelection\"></th>\r\n              <th ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageHourlyPay'\" sxy-text=\"SALAXY.NG1.HolidayPayReportQueryComponent.workingHoursSelection\"></th>\r\n              <th ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\" sxy-text=\"SALAXY.NG1.HolidayPayReportQueryComponent.overtimeHoursSelection\"></th>\r\n            </tr>\r\n          </thead>\r\n          <tbody>\r\n            <tr ng-repeat-start=\"calc in $ctrl.data.calculations\">\r\n              <td><a ng-href=\"#/calc/details/{{calc.calculationId}}\">{{calc.calculationTitle}} {{calc.salaryDate | date}}</a></td>\r\n              <td>{{calc.workStartDate | date }} - {{calc.workEndDate | date}}</td>\r\n              <td class=\"right\"></td>\r\n              <td class=\"right\"></td>\r\n              <td class=\"right\"></td>\r\n              <td ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageHourlyPay'\" class=\"right\"></td>\r\n              <td ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\" class=\"right\"></td>\r\n              <td ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\" class=\"right\">{{calc.workingDays}}</td>\r\n              <td ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\" class=\"right\">{{calc.absenceDays}}</td>\r\n              <td></td>\r\n              <td ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageHourlyPay'\"></td>\r\n              <td ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\"></td>\r\n            </tr>\r\n            <tr ng-repeat-end ng-repeat=\"row in calc.rows\">\r\n              <td></td>\r\n              <td>{{$ctrl.getLabel(row.irRow)}}</td>\r\n              <td class=\"right\">{{row.irRow.count}}</td>\r\n              <td class=\"right\">{{row.irRow.price | currency}}</td>\r\n              <td class=\"right\">{{row.total | currency}}</td>\r\n              <td ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageHourlyPay'\" class=\"right\">{{row.hours}}</td>\r\n              <td ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\" class=\"right\">{{row.overtimeHours}}</td>\r\n              <td ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\" ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\" class=\"right\"></td>\r\n              <td ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\" class=\"right\"></td>\r\n              <td><salaxy-input-pay-stats-row-type name=\"salaryType\" label-type=\"no-label\" ng-model=\"row.salaryType\" read-only=\"true\"></salaxy-input-pay-stats-row-type></td>\r\n              <td ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageHourlyPay'\"><salaxy-input-pay-stats-row-type name=\"workingTimeType\" label-type=\"no-label\" ng-model=\"row.workingTimeType\" read-only=\"true\"></salaxy-input-pay-stats-row-type></td>\r\n              <td ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\"><salaxy-input-pay-stats-row-type name=\"overtimeType\" label-type=\"no-label\" ng-model=\"row.overtimeType\" read-only=\"true\"></salaxy-input-pay-stats-row-type></td>\r\n            </tr>\r\n          </tbody>\r\n          <tfoot>\r\n            <th sxy-text=\"SALAXY.NG1.HolidayPayReportQueryComponent.total\"></th>\r\n            <th></th>\r\n            <th class=\"right\"></th>\r\n            <th class=\"right\"></th>\r\n            <th class=\"right\">{{$ctrl.totals.total | currency}}</th>\r\n            <th ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageHourlyPay'\" class=\"right\">{{$ctrl.totals.hours}}</th>\r\n            <th ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\" class=\"right\">{{$ctrl.totals.overtimeHours}}</th>\r\n            <th ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\" class=\"right\">{{$ctrl.totals.workingDays}}</th>\r\n            <th ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\" class=\"right\">{{$ctrl.totals.absenceDays}}</th>\r\n            <th></th>\r\n            <th ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageHourlyPay'\"></th>\r\n            <th ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\"></th>\r\n          </tfoot>\r\n        </table>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"parameters-tab\">\r\n        <div ng-if=\"$ctrl.currentTab == 'parameters'\">\r\n          <div class=\"row\">\r\n            <div class=\"col-sm-6\">\r\n              <form class=\"form-horizontal\">\r\n                <salaxy-form-group ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageHourlyPay' || $ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay' || $ctrl.data.holidayYear.spec.holidayPayCalculation == 'percentageBasedPay' || $ctrl.data.holidayYear.spec.holidayPayCalculation == 'holidayCompensation' || $ctrl.data.holidayYear.spec.holidayPayCalculation == 'normalMonthlyPay'\" name=\"salaryTypes\" label=\"SALAXY.NG1.HolidayPayReportQueryComponent.holidayPayRowTypes\">\r\n                  <salaxy-input-pay-stats-row-type ng-repeat=\"rowType in $ctrl.data.holidayPaySettings.salaryTypes\" name=\"salaryType\" label-type=\"no-label\" ng-model=\"rowType\" read-only=\"true\"></salaxy-input-pay-stats-row-type>\r\n                </salaxy-form-group>\r\n              </form>\r\n            </div>\r\n            <div class=\"col-sm-6\">\r\n              <form class=\"form-horizontal\">\r\n                <salaxy-form-group  ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageHourlyPay'\" name=\"workingTimeTypes\" label=\"SALAXY.NG1.HolidayPayReportQueryComponent.workingHoursRowTypes\">\r\n                  <salaxy-input-pay-stats-row-type ng-repeat=\"rowType in $ctrl.data.holidayPaySettings.workingTimeTypes\" name=\"workingTimeType\" label-type=\"no-label\" ng-model=\"rowType\" read-only=\"true\"></salaxy-input-pay-stats-row-type>\r\n                </salaxy-form-group>\r\n                <salaxy-form-group  ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\" name=\"overtimeTypes\" label=\"SALAXY.NG1.HolidayPayReportQueryComponent.overtimeHoursRowTypes\">\r\n                  <salaxy-input-pay-stats-row-type ng-repeat=\"rowType in $ctrl.data.holidayPaySettings.overtimeTypes\" name=\"overtimeType\" label-type=\"no-label\" ng-model=\"rowType\" read-only=\"true\"></salaxy-input-pay-stats-row-type>\r\n                </salaxy-form-group>\r\n                <salaxy-form-group  ng-if=\"$ctrl.data.holidayYear.spec.code == 'permanent35Hours'\"  name=\"accrualWorkingTimeTypes\" label=\"SALAXY.NG1.HolidayPayReportQueryComponent.accrualWorkingTimeRowTypes\">\r\n                  <salaxy-input-pay-stats-row-type ng-repeat=\"rowType in $ctrl.data.holidayAccrualSettings.workingTimeTypes\" name=\"accrualWorkingTimeType\" label-type=\"no-label\" ng-model=\"rowType\" read-only=\"true\"></salaxy-input-pay-stats-row-type>\r\n                </salaxy-form-group>\r\n              </form>\r\n            </div>\r\n          </div>\r\n          <div class=\"row\">\r\n            <div class=\"col-sm-6\">\r\n              <form class=\"form-horizontal\">\r\n                <salaxy-input-holiday-multipliers ng-if=\"$ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageHourlyPay' || $ctrl.data.holidayYear.spec.holidayPayCalculation == 'averageDailyPay'\" name=\"multipliers\" label=\"SALAXY.MODEL.HolidayPaySettings.multipliers.title\" ng-model=\"$ctrl.data.holidayPaySettings.multipliers\" read-only=\"true\"></salaxy-input-holiday-multipliers>\r\n              </form>\r\n            <div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>\r\n`);\n\n $templateCache.put(\"salaxy-components/report/HolidayReport.html\",`<div class=\"salaxy-component salaxy-holiday-report\">\r\n  <salaxy-tab-buttons\r\n    current-tab=\"$ctrl.currentTab\"\r\n    options=\"[\r\n      { value: 'years', text: 'SALAXY.NG1.HolidayReportComponent.holidayYears' },\r\n      { value: 'debt', text: 'SALAXY.NG1.HolidayReportComponent.holidayPayDebt', hidden: ('hideHolidayDebt' | sxyIsInRole) }\r\n    ]\"\r\n    tabs-id=\"holidayReport\">\r\n  </salaxy-tab-buttons>\r\n  <div class=\"tab-content\" id=\"tab-content-holidayReport\">\r\n    <div class=\"tab-pane\" id=\"years-tab\">\r\n      <div class=\"row\">\r\n        <div class=\"form-horizontal col-sm-3\">\r\n          <salaxy-input-enum  name=\"year\"  ng-model=\"$ctrl.year\"   label=\"SALAXY.NG1.HolidayReportComponent.holidayYear\" options=\"$ctrl.years\"></salaxy-input-enum>\r\n        </div>\r\n        <div class=\"col-sm-3\">\r\n          <button type=\"button\" class=\"btn btn-secondary\" ng-click=\"$ctrl.exportToExcel()\">\r\n            <span class=\"hidden-sm hidden-xs\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.exportToExcel\"></span>\r\n            <i class=\"bi bi-file-earmark-pdf\" aria-hidden=\"true\"></i>\r\n          </button>\r\n        </div>\r\n      </div>\r\n      <table class=\"table table-striped\">\r\n        <thead>\r\n          <tr>\r\n            <th colspan=\"2\"><span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span></th>\r\n            <th sxy-text=\"SALAXY.NG1.HolidayReportComponent.table.startDate\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.HolidayReportComponent.table.endDate\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.HolidayReportComponent.table.employment\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.table.salary\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.HolidayReportComponent.table.holidayCode\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.table.periodDefaultAccrual\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.HolidayReportComponent.table.holidayPayCalculation\"></th>        \r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.startSaldo\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.total\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.paid\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.available\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.holidaySalary\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.holidayCompensation\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.paidBonus\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.availableBonus\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.holidayBonus\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.holidayPayDailySalary\"></th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr ng-repeat=\"row in $ctrl.resultRows | filter: { data : { holidayYear : { year: $ctrl.year } } } track by $index\">\r\n            <td class=\"align-middle td-avatar\">\r\n              <salaxy-avatar class=\"clickable\" ng-click=\"$ctrl.showEditEmploymentDialog(row)\" avatar=\"row.holidayYearReportRow.workerAvatar\"></salaxy-avatar>\r\n            </td>\r\n            <td>{{row.holidayYearReportRow.workerAvatar.displayName}}</td>\r\n            <td>{{row.holidayYearReportRow.startDate | sxyDate}}</td>\r\n            <td>{{row.holidayYearReportRow.endDate | sxyDate}}</td>\r\n            <td>{{row.holidayYearReportRow.employmentType}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.grossSalary| currency) || \"&nbsp;\"}}</td>\r\n            <td>{{row.holidayYearReportRow.holidayCode}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.periodDefaultAccrual | sxyCount : 'day') || \"&nbsp;\"}}</td>\r\n            <td>{{row.holidayYearReportRow.holidayPayCalculation}}</td>      \r\n            <td class=\"right\">{{(row.holidayYearReportRow.startSaldo | sxyCount : 'day') || \"&nbsp;\"}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.total| sxyCount : 'day') || \"&nbsp;\"}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.paid | sxyCount : 'day') || \"&nbsp;\"}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.available | sxyCount : 'day') || \"&nbsp;\"}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.holidaySalary | currency) || \"&nbsp;\"}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.holidayCompensation| currency) || \"&nbsp;\"}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.paidBonus | sxyCount : 'day') || \"&nbsp;\"}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.availableBonus | sxyCount : 'day') || \"&nbsp;\"}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.holidayBonus| currency) || \"&nbsp;\"}}</td>\r\n            <td class=\"right\"><a ng-href=\"#/reports/holiday-pay-report-query/{{row.data.holidayYear.year}}/{{row.employment.id}}\">{{(row.holidayYearReportRow.holidayPayDailySalary | currency) || \"&nbsp;\"}}</a></td>      \r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"debt-tab\">\r\n      <div class=\"row\">\r\n        <div class=\"form-horizontal col-sm-3\">\r\n          <salaxy-input-enum  name=\"year\"  ng-model=\"$ctrl.year\"   label=\"SALAXY.NG1.HolidayReportComponent.holidayYear\" options=\"$ctrl.years\"></salaxy-input-enum>\r\n        </div>\r\n        <div class=\"col-sm-3\">\r\n          <button type=\"button\" class=\"btn btn-secondary\" ng-click=\"$ctrl.exportToExcel()\">\r\n            <span class=\"hidden-sm hidden-xs\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.exportToExcel\"></span>\r\n            <i class=\"bi bi-file-earmark-pdf\" aria-hidden=\"true\"></i>\r\n          </button>\r\n        </div>\r\n        <div class=\"form-horizontal  col-sm-3\">\r\n          <salaxy-datepicker-popup name=\"refDate\" placeholder=\"\"  ng-model=\"$ctrl.refDate\"\r\n          label=\"SALAXY.NG1.HolidayReportComponent.holidayPayDebtDate\" require=\"true\" ng-change=\"$ctrl.query(true)\"></salaxy-datepicker-popup>\r\n        </div>\r\n        <div class=\"col-sm-3\">\r\n          <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.query(true)\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.calculateHolidayPayDebt\"></button>\r\n        </div>\r\n      </div>\r\n      <table class=\"table table-striped\" ng-if=\"$ctrl.hasQueryedDebt\">\r\n        <thead>\r\n          <tr>\r\n            <th colspan=\"2\"><span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span></th>\r\n            <th sxy-text=\"SALAXY.NG1.HolidayReportComponent.table.startDate\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.HolidayReportComponent.table.endDate\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.HolidayReportComponent.table.employment\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.table.salary\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.HolidayReportComponent.table.holidayCode\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.table.periodDefaultAccrual\"></th>\r\n            <th sxy-text=\"SALAXY.NG1.HolidayReportComponent.table.holidayPayCalculation\"></th>         \r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.startSaldo\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.total\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.paid\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.available\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.holidaySalary\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.holidayCompensation\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.paidBonus\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.availableBonus\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.holidayBonus\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.holidayPayDailySalary\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.totalAccruedHolidayPay\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.totalAccruedHolidayBonus\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.totalAccruedHolidaySocialSecurity\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.totalAccruedHolidayPension\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.totalAccruedHolidayUnemployment\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.totalAccruedHolidayAccidentInsurance\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.totalAccruedHolidayGroupLifeInsurance\"></th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.holidayYearReportRow.totalAccruedHolidayTotal\"></th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr ng-repeat=\"row in $ctrl.resultRows | filter: { data : { holidayYear : { year: $ctrl.year } } } track by $index\">\r\n            <td class=\"align-middle td-avatar\">\r\n              <salaxy-avatar class=\"clickable\" ng-click=\"$ctrl.showEditEmploymentDialog(row)\" avatar=\"row.holidayYearReportRow.workerAvatar\"></salaxy-avatar>\r\n            </td>\r\n            <td>{{row.holidayYearReportRow.workerAvatar.displayName}}</td>\r\n            <td>{{row.holidayYearReportRow.startDate | sxyDate}}</td>\r\n            <td>{{row.holidayYearReportRow.endDate | sxyDate}}</td>\r\n            <td>{{row.holidayYearReportRow.employmentType}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.grossSalary| currency) || \"&nbsp;\"}}</td>\r\n            <td>{{row.holidayYearReportRow.holidayCode}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.periodDefaultAccrual | sxyCount : 'day') || \"&nbsp;\"}}</td>\r\n            <td>{{row.holidayYearReportRow.holidayPayCalculation}}</td>       \r\n            <td class=\"right\">{{(row.holidayYearReportRow.startSaldo | sxyCount : 'day') || \"&nbsp;\"}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.total| sxyCount : 'day') || \"&nbsp;\"}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.paid | sxyCount : 'day') || \"&nbsp;\"}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.available | sxyCount : 'day') || \"&nbsp;\"}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.holidaySalary | currency) || \"&nbsp;\"}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.holidayCompensation| currency) || \"&nbsp;\"}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.paidBonus | sxyCount : 'day') || \"&nbsp;\"}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.availableBonus | sxyCount : 'day') || \"&nbsp;\"}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.holidayBonus| currency) || \"&nbsp;\"}}</td>\r\n            <td class=\"right\"><a ng-href=\"#/reports/holiday-pay-report-query/{{row.data.holidayYear.year}}/{{row.employment.id}}\">{{(row.holidayYearReportRow.holidayPayDailySalary | currency) || \"&nbsp;\"}}</a></td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.totalAccruedHolidayPay| currency) || \"&nbsp;\"}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.totalAccruedHolidayBonus| currency) || \"&nbsp;\"}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.totalAccruedHolidaySocialSecurity | currency) || \"&nbsp;\"}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.totalAccruedHolidayPension | currency) || \"&nbsp;\"}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.totalAccruedHolidayUnemployment | currency) || \"&nbsp;\"}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.totalAccruedHolidayAccidentInsurance| currency) || \"&nbsp;\"}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.totalAccruedHolidayGroupLifeInsurance| currency) || \"&nbsp;\"}}</td>\r\n            <td class=\"right\">{{(row.holidayYearReportRow.totalAccruedHolidayTotal| currency) || \"&nbsp;\"}}</td>       \r\n          </tr>\r\n        </tbody>\r\n        <tfoot>\r\n          <tr>&nbsp;</tr>\r\n          <tr>\r\n            <th colspan=\"19\">{{ \"SALAXY.NG1.HolidayReportComponent.yearAccruedDebt\" | sxyTranslate }} {{$ctrl.year}} </th>\r\n            <th class=\"right\">{{($ctrl.holidayCalc[$ctrl.year].totalAccruedHolidayPay| currency) || \"&nbsp;\"}}</th>\r\n            <th class=\"right\">{{($ctrl.holidayCalc[$ctrl.year].totalAccruedHolidayBonus| currency) || \"&nbsp;\"}}</th>\r\n            <th class=\"right\">{{($ctrl.holidayCalc[$ctrl.year].totalAccruedHolidaySocialSecurity | currency) || \"&nbsp;\"}}</th>\r\n            <th class=\"right\">{{($ctrl.holidayCalc[$ctrl.year].totalAccruedHolidayPension | currency) || \"&nbsp;\"}}</th>\r\n            <th class=\"right\">{{($ctrl.holidayCalc[$ctrl.year].totalAccruedHolidayUnemployment | currency) || \"&nbsp;\"}}</th>\r\n            <th class=\"right\">{{($ctrl.holidayCalc[$ctrl.year].totalAccruedHolidayAccidentInsurance| currency) || \"&nbsp;\"}}</th>\r\n            <th class=\"right\">{{($ctrl.holidayCalc[$ctrl.year].totalAccruedHolidayGroupLifeInsurance| currency) || \"&nbsp;\"}}</th>\r\n            <th class=\"right\">{{($ctrl.holidayCalcTotal[$ctrl.year] | currency) || \"&nbsp;\"}}</td>       \r\n          </tr>\r\n          <tr>\r\n            <th colspan=\"19\">{{ \"SALAXY.NG1.HolidayReportComponent.allAccruedDebt\" | sxyTranslate }}</th>\r\n            <th class=\"right\">{{($ctrl.holidayCalc['total'].totalAccruedHolidayPay| currency) || \"&nbsp;\"}}</th>\r\n            <th class=\"right\">{{($ctrl.holidayCalc['total'].totalAccruedHolidayBonus| currency) || \"&nbsp;\"}}</th>\r\n            <th class=\"right\">{{($ctrl.holidayCalc['total'].totalAccruedHolidaySocialSecurity | currency) || \"&nbsp;\"}}</th>\r\n            <th class=\"right\">{{($ctrl.holidayCalc['total'].totalAccruedHolidayPension | currency) || \"&nbsp;\"}}</th>\r\n            <th class=\"right\">{{($ctrl.holidayCalc['total'].totalAccruedHolidayUnemployment | currency) || \"&nbsp;\"}}</th>\r\n            <th class=\"right\">{{($ctrl.holidayCalc['total'].totalAccruedHolidayAccidentInsurance| currency) || \"&nbsp;\"}}</th>\r\n            <th class=\"right\">{{($ctrl.holidayCalc['total'].totalAccruedHolidayGroupLifeInsurance| currency) || \"&nbsp;\"}}</th>\r\n            <th class=\"right\">{{($ctrl.holidayCalcTotal['total'] | currency) || \"&nbsp;\"}}</td>       \r\n          </tr>\r\n        </tfoot>\r\n      </table>\r\n    </div>\r\n  </div> \r\n</div>\r\n`);\n\n $templateCache.put(\"salaxy-components/report/IrEarningsPayment.html\",`<div class=\"salaxy-component salaxy salaxy-ir-earnings-payment\">\r\n  <salaxy-spinner ng-if=\"$ctrl.isLoading\" full-screen=\"true\" heading=\"SALAXY.UI_Terms.loading\" text=\"SALAXY.UI_Terms.pleaseWait\"></salaxy-spinner>\r\n  <div ng-if=\"'test' | sxyIsInRole\">\r\n    <div ng-if=\"$ctrl.current.isReadOnly\" class=\"alert alert-info\" pre=\"VAIN TEST: \" sxy-text=\"SALAXY.NG1.EarningsPaymentComponent.common.readOnlyInfo\"></div>\r\n    <div class=\"btn-toolbar\" role=\"toolbar\" ng-if=\"$ctrl.current && $ctrl.isReadOnly && !$ctrl.current.isReadOnly\">\r\n      <div class=\"btn-group\" role=\"group\" aria-label=\"Muokkaa\">\r\n        <button ng-click=\"$ctrl.tempShowEditInNonAdminMode = true\" type=\"button\" role=\"group\" class=\"btn btn-primary\">VAIN TEST: Muokkaa</button>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div class=\"btn-toolbar\" role=\"toolbar\" ng-if=\"!$ctrl.isReadOnly\">\r\n    <div class=\"btn-group\" role=\"group\" aria-label=\"Tallenna\">\r\n      <button ng-click=\"$ctrl.saveChanges()\" type=\"button\" role=\"group\" class=\"btn btn-primary\" ng-disabled=\"!($ctrl.hasChanges || ( $ctrl.calcController && $ctrl.calcController.hasChanges)) || $ctrl.isReadOnly\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n    </div>\r\n    <div class=\"btn-group\" role=\"group\" aria-label=\"Lähetä/mitätöi\">\r\n      <button ng-click=\"$ctrl.sendToIncomesRegister()\" type=\"button\" role=\"group\" class=\"btn btn-default\" ng-disabled=\"$ctrl.isReadOnly\" sxy-text=\"SALAXY.UI_Terms.send\"></button>\r\n      <button ng-click=\"$ctrl.openSetScheduleDialog()\" type=\"button\" role=\"group\" class=\"btn btn-default\" ng-disabled=\"$ctrl.isReadOnly\" sxy-text=\"SALAXY.NG1.EarningsPaymentComponent.common.addScheduling\"></button>\r\n      <button ng-click=\"$ctrl.removeIrQueueItem()\" type=\"button\" role=\"group\" class=\"btn btn-danger\" ng-disabled=\"!$ctrl.current.scheduledFor || $ctrl.isReadOnly\" sxy-text=\"SALAXY.NG1.EarningsPaymentComponent.common.removeScheduling\"></button>\r\n      <button ng-click=\"$ctrl.cancelToIncomesRegister()\" type=\"button\" role=\"group\" class=\"btn btn-danger\" ng-disabled=\"!$ctrl.isCancellable || $ctrl.isReadOnly\" sxy-text=\"SALAXY.NG1.EarningsPaymentComponent.common.cancel\"></button>\r\n    </div>\r\n  </div>\r\n  <div ng-if=\"!$ctrl.isLoading && !$ctrl.current\">\r\n    <h3>Ei Palkkatietoilmoitusta</h3>\r\n    <p>Palkkatietoilmoitus luodaan vasta, kun laskelma on merkitty maksetuksi.</p>\r\n  </div>\r\n  <div class=\"form-horizontal form-condensed\" ng-if=\"$ctrl.current\">\r\n    <salaxy-tab-buttons\r\n      current-tab=\"$ctrl.currentTab\"\r\n      options=\"[\r\n        { value: 'default', text: 'SALAXY.NG1.EarningsPaymentComponent.common.basicInfo' },\r\n        { value: 'payer', text: 'SALAXY.MODEL.Payer.title' },\r\n        { value: 'incomeearner', text: 'SALAXY.MODEL.IncomeEarner.title' },\r\n        { value: 'insurances', text: 'SALAXY.NG1.EarningsPaymentComponent.common.insurances' },\r\n        { value: 'absenses', text: 'SALAXY.NG1.EarningsPaymentComponent.common.absences' },\r\n        { value: 'calcrows', text: 'SALAXY.NG1.EarningsPaymentComponent.common.rows' },\r\n        { value: 'history', text: 'SALAXY.NG1.EarningsPaymentComponent.common.history' },\r\n      ]\"\r\n      tabs-id=\"irEarningsPayment\">\r\n    </salaxy-tab-buttons>\r\n    <div class=\"tab-content\" id=\"tab-content-irEarningsPayment\"\">\r\n      <div class=\"tab-pane\" id=\"default-tab\">\r\n        <div>\r\n          <div class=\"label label-success float-end\" style=\"font-size: 1.5em\" ng-if=\"$ctrl.current.validation.isValid\">{{'SALAXY.NG1.EarningsPaymentComponent.common.noErrors' | sxyTranslate}}</div>\r\n          <!-- TODO: Check texts and add to language versioning. Consider could this be done with SXY-IPT infra. -->\r\n          <h3 ng-switch=\"$ctrl.current.status\">\r\n            <span ng-switch-when=\"new\">{{'SALAXY.NG1.EarningsPaymentComponent.statuses.new.text' | sxyTranslate}} <small sxy-text=\"SALAXY.NG1.EarningsPaymentComponent.statuses.new.smallText\"></small></span>\r\n            <span ng-switch-when=\"succeeded\">{{'SALAXY.NG1.EarningsPaymentComponent.statuses.succeeded.text' | sxyTranslate}} <small>{{ $ctrl.current.lastDeliveredAt | sxyDate }} {{'SALAXY.NG1.EarningsPaymentComponent.common.time' | sxyTranslate}} {{ $ctrl.current.lastDeliveredAt | date : \"hh:mm\" }}</small></span>\r\n            <span ng-switch-when=\"canceled\">{{'SALAXY.NG1.EarningsPaymentComponent.statuses.canceled.text' | sxyTranslate}} <small sxy-text=\"SALAXY.NG1.EarningsPaymentComponent.statuses.canceled.smallText\"></small> </span>\r\n            <span ng-switch-when=\"error\">{{'SALAXY.NG1.EarningsPaymentComponent.statuses.error.text' | sxyTranslate}} <small>{{'SALAXY.NG1.EarningsPaymentComponent.statuses.error.sending' | sxyTranslate}} {{ $ctrl.current.lastDeliveredAt | sxyDate }} {{'SALAXY.NG1.EarningsPaymentComponent.common.time' | sxyTranslate}} {{ $ctrl.current.lastDeliveredAt | date : \"hh:mm\" }} {{'SALAXY.NG1.EarningsPaymentComponent.statuses.error.gaveError' | sxyTranslate}}</small></span>\r\n            <span ng-switch-when=\"invalid\">{{'SALAXY.NG1.EarningsPaymentComponent.statuses.invalid.text' | sxyTranslate}} <small sxy-text=\"SALAXY.NG1.EarningsPaymentComponent.statuses.invalid.smallText\"></small></span>\r\n            <span ng-switch-when=\"scheduled\">{{'SALAXY.NG1.EarningsPaymentComponent.statuses.scheduled.text' | sxyTranslate}} <small>{{ $ctrl.current.scheduledFor | sxyDate }} {{'SALAXY.NG1.EarningsPaymentComponent.common.time' | sxyTranslate}} {{ $ctrl.current.scheduledFor | date : \"hh:mm\" }}</small></span>\r\n            <span ng-switch-default>{{'SALAXY.MODEL.EarningsPayment.status.title' | sxyTranslate}}: {{ \"EarningsPaymentReportStatus.\" + $ctrl.current.status | sxyEnum }}</span>\r\n          </h3>\r\n          <salaxy-validation-summary api-validation=\"$ctrl.current.validation\" ng-if=\"!$ctrl.current.validation.isValid\">\r\n          </salaxy-validation-summary>\r\n          <salaxy-validation-summary api-validation=\"$ctrl.current.irErrors\" ng-if=\"!$ctrl.current.irErrors.isValid\">\r\n          </salaxy-validation-summary>\r\n        </div>\r\n        <sxy-form open-api=\"salaxy-secure/schemas/irepr.json\" read-only=\"{{ $ctrl.isReadOnly }}\" model=\"$ctrl.current\" type=\"EarningsPayment\" debugger=\"false\" auto-gen=\"false\">\r\n          <div>\r\n            <div class=\"row\">\r\n              <div class=\"col-md-6\">\r\n                <fieldset>\r\n                  <legend sxy-text=\"SALAXY.MODEL.PaymentPeriod.title\"></legend>\r\n                  <sxy-input model=\"form.deliveryData.paymentPeriod.startDate\" format=\"date\"></sxy-input>\r\n                  <sxy-input model=\"form.deliveryData.paymentPeriod.endDate\" format=\"date\"></sxy-input>\r\n                  <sxy-input model=\"form.deliveryData.paymentPeriod.paymentDate\" format=\"date\"></sxy-input>\r\n                </fieldset>\r\n              </div>\r\n              <div class=\"col-md-6\">\r\n                <fieldset>\r\n                  <legend sxy-text=\"SALAXY.NG1.EarningsPaymentComponent.common.worker\"></legend>\r\n                  <salaxy-avatar class=\"float-start\" style=\"margin-right: 20px;font-size: 102px;\" avatar=\"$ctrl.current.info.worker\"></salaxy-avatar>\r\n                  <div>{{ $ctrl.current.info.worker.sortableName }}</div>\r\n                  <div>{{ $ctrl.current.deliveryData.reports[0].incomeEarner.incomeEarnerIds[0].code || \"Ei henkilötunnusta\" }}</div>\r\n                </fieldset>\r\n              </div>\r\n            </div>\r\n            <div class=\"row\">\r\n              <div class=\"col-md-6\">\r\n                <fieldset>\r\n                  <legend sxy-text=\"SALAXY.NG1.EarningsPaymentComponent.common.basicInfo\"></legend>\r\n                  <sxy-form open-api=\"salaxy-secure/schemas/irepr.json\" model=\"$ctrl.current.deliveryData.reports[0].reportData\" type=\"ReportData\" debugger=\"false\" auto-gen=\"false\">\r\n                    <div>\r\n                      <sxy-input model=\"form.reportId\" read-only=\"true\"></sxy-input>\r\n                      <!--sxy-input model=\"form.irReportId\" read-only=\"true\"></sxy-input-->\r\n                    </div>\r\n                  </sxy-form>\r\n                  <sxy-input model=\"form.createdAt\"></sxy-input>\r\n                  <sxy-input model=\"form.updatedAt\"></sxy-input>\r\n                  <sxy-input model=\"form.irStatus\" read-only=\"true\"></sxy-input>\r\n                  <sxy-input model=\"form.isModified\" read-only=\"true\"></sxy-input>\r\n                  <sxy-input model=\"form.scheduledFor\" read-only=\"true\"></sxy-input>\r\n                </fieldset>\r\n              </div>\r\n              <div class=\"col-md-6\">\r\n                <fieldset>\r\n                  <legend sxy-text=\"SALAXY.NG1.EarningsPaymentComponent.deliveryData.title\"></legend>\r\n                  <sxy-input model=\"form.deliveryData.deliveryDataType\" read-only=\"true\"></sxy-input>\r\n                  <sxy-input model=\"form.deliveryData.timestamp\" read-only=\"true\"></sxy-input>\r\n                  <sxy-input model=\"form.deliveryData.deliveryDataCreator.code\" label=\"SALAXY.NG1.EarningsPaymentComponent.deliveryData.deliveryDataCreator\" read-only=\"true\">\r\n                  </sxy-input>\r\n                  </sxy-input>\r\n                  <sxy-input model=\"form.deliveryData.deliveryDataSender.code\" label=\"SALAXY.NG1.EarningsPaymentComponent.deliveryData.deliveryDataSender\" read-only=\"true\">\r\n                  </sxy-input>\r\n                </fieldset>\r\n              </div>\r\n            </div>\r\n            <sxy-input model=\"form.deliveryData.contactPersons\" include=\"name,responsibilityCode\"></sxy-input>\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.NG1.EarningsPaymentComponent.deliveryData.deliveryDataOwner\"></legend>\r\n              <sxy-input model=\"form.deliveryData.deliveryDataOwner.code\"></sxy-input>\r\n              <sxy-input model=\"form.deliveryData.deliveryDataOwner.type\"></sxy-input>\r\n              <sxy-input model=\"form.deliveryData.deliveryDataOwner.countryCode\"></sxy-input>\r\n              <sxy-input model=\"form.deliveryData.deliveryDataOwner.countryName\"></sxy-input>\r\n            </fieldset>\r\n          </div>\r\n        </sxy-form>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"payer-tab\">\r\n        <sxy-form open-api=\"salaxy-secure/schemas/irepr.json\" read-only=\"{{ $ctrl.isReadOnly }}\" model=\"$ctrl.current.deliveryData.payer\" type=\"Payer\" debugger=\"false\" auto-gen=\"false\">\r\n          <div>\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.NG1.EarningsPaymentComponent.payer.title\"></legend>\r\n              <sxy-input model=\"form.payerBasic.companyName\"></sxy-input>\r\n              <sxy-input model=\"form.payerBasic.missingId\" format=\"checkbox\"></sxy-input>\r\n              <sxy-input model=\"form.payerIds\"></sxy-input>\r\n              <sxy-input model=\"form.payerOther.payerTypes\"></sxy-input>\r\n              <sxy-input model=\"form.subOrgs\"></sxy-input>\r\n            </fieldset>\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.NG1.EarningsPaymentComponent.address.title\"></legend>\r\n              <sxy-input model=\"form.address.co\"></sxy-input>\r\n              <sxy-input model=\"form.address.street\"></sxy-input>\r\n              <sxy-input model=\"form.address.poBox\"></sxy-input>\r\n              <sxy-input model=\"form.address.postalCode\"></sxy-input>\r\n              <sxy-input model=\"form.address.postOffice\"></sxy-input>\r\n              <sxy-input model=\"form.address.countryCode\"></sxy-input>\r\n              <sxy-input model=\"form.address.countryName\"></sxy-input>\r\n            </fieldset>\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.MODEL.SubstitutePayer.title\"></legend>\r\n              <sxy-input model=\"form.substitutePayer.acts\"></sxy-input>\r\n              <sxy-input model=\"form.substitutePayer.employerName\"></sxy-input>\r\n              <sxy-input model=\"form.substitutePayer.employerId.type\" label=\"SALAXY.NG1.EarningsPaymentComponent.substitutePayer.employerIdType.title\"></sxy-input>\r\n              <sxy-input model=\"form.substitutePayer.employerId.code\" label=\"SALAXY.NG1.EarningsPaymentComponent.substitutePayer.employerIdCode.title\"></sxy-input>\r\n              <sxy-input model=\"form.substitutePayer.employerId.countryCode\" label=\"SALAXY.NG1.EarningsPaymentComponent.substitutePayer.employerIdCountryCode.title\"></sxy-input>\r\n              <sxy-input model=\"form.substitutePayer.employerId.countryName\" label=\"SALAXY.NG1.EarningsPaymentComponent.substitutePayer.employerIdCountryName.title\"></sxy-input>\r\n              <sxy-input model=\"form.substitutePayer.wageSec\"></sxy-input>\r\n            </fieldset>\r\n          </div>\r\n        </sxy-form>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"incomeearner-tab\">\r\n        <sxy-form open-api=\"salaxy-secure/schemas/irepr.json\" read-only=\"{{ $ctrl.isReadOnly }}\" model=\"$ctrl.current.deliveryData.reports[0].incomeEarner\" type=\"IncomeEarner\" debugger=\"false\" auto-gen=\"false\">\r\n          <div>\r\n            <fieldset>\r\n              <sxy-input model=\"form.incomeEarnerIds\" include=\"code,type,countryCode\"></sxy-input>\r\n              <sxy-input model=\"form.incomeEarnerBasic.missingId\" format=\"checkbox\"></sxy-input>\r\n              <sxy-input model=\"form.incomeEarnerBasic.companyName\"></sxy-input>\r\n              <sxy-input model=\"form.incomeEarnerBasic.firstName\"></sxy-input>\r\n              <sxy-input model=\"form.incomeEarnerBasic.lastName\"></sxy-input>\r\n              <sxy-input model=\"form.incomeEarnerBasic.birthDate\" format=\"date\"></sxy-input>\r\n              <sxy-input model=\"form.incomeEarnerBasic.gender\"></sxy-input>\r\n              <sxy-input model=\"form.addresses\" include=\"street,postalCode,postOffice,countryCode\"></sxy-input>\r\n              <salaxy-custom-code>\r\n                <sxy-input model=\"form.professions\" template-url=\"epr-professions.html\"></sxy-input>\r\n              </salaxy-custom-code>\r\n              <sxy-input model=\"form.employmentRegs\"></sxy-input>\r\n              <sxy-input ng-if=\"$ctrl.current.deliveryData.reports[0].incomeEarner.incomeEarnerOther != null && $ctrl.current.deliveryData.reports[0].incomeEarner.incomeEarnerOther.incomeEarnerTypes != null\" model=\"form.incomeEarnerOther.incomeEarnerTypes\"></sxy-input>\r\n            </fieldset>\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.MODEL.Employment.title\"></legend>\r\n              <sxy-input model=\"form.employment.employed\"></sxy-input>\r\n              <sxy-input model=\"form.employment.employmentCode\"></sxy-input>\r\n              <sxy-input model=\"form.employment.termCode\"></sxy-input>\r\n              <sxy-input model=\"form.employment.partTime\"></sxy-input>\r\n              <sxy-input model=\"form.employment.hoursPerWeek\"></sxy-input>\r\n              <sxy-input model=\"form.employment.paymentTypes\"></sxy-input>\r\n              <sxy-input model=\"form.employment.employmentPeriods\" include=\"startDate,endDate\">\r\n                <form>\r\n                  <fieldset>\r\n                    <legend sxy-text=\"SALAXY.MODEL_IR.Period.title\"></legend>\r\n                    \r\n                    <sxy-input model=\"form.startDate\" format=\"date\"></sxy-input>\r\n                    <sxy-input model=\"form.endDate\" format=\"date\"></sxy-input>\r\n                  </fieldset>\r\n                </form>\r\n              </sxy-input>\r\n              <sxy-input model=\"form.employment.employmentEndings\"></sxy-input>\r\n            </fieldset>\r\n          </div>\r\n        </sxy-form>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"insurances-tab\">\r\n        <sxy-form open-api=\"salaxy-secure/schemas/irepr.json\" read-only=\"{{ $ctrl.isReadOnly }}\" model=\"$ctrl.current.deliveryData.reports[0].incomeEarner\" type=\"IncomeEarner\" debugger=\"false\" auto-gen=\"false\">\r\n          <div>\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.MODEL.PensionInsurance.title\"></legend>\r\n              <sxy-input model=\"form.pensionInsurance.pensionActCode\"></sxy-input>\r\n              <sxy-input model=\"form.pensionInsurance.pensionProvIdCode\"></sxy-input>\r\n              <sxy-input model=\"form.pensionInsurance.pensionPolicyNo\"></sxy-input>\r\n              <sxy-input ng-if=\"$ctrl.current.deliveryData.reports[0].incomeEarner.incomeEarnerOther != null && $ctrl.current.deliveryData.reports[0].incomeEarner.incomeEarnerOther.payments != null\" model=\"form.incomeEarnerOther.payments\" include=\"paymentRef,paymentSpecifier\"></sxy-input>\r\n            </fieldset>\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.MODEL.AccidentInsurance.title\"></legend>\r\n              <sxy-input model=\"form.accidentInsurance.accInsPolicyNo\"></sxy-input>\r\n              <sxy-input model=\"form.accidentInsurance.accInsProvId.type\"></sxy-input>\r\n              <sxy-input model=\"form.accidentInsurance.accInsProvId.code\"></sxy-input>\r\n              <sxy-input model=\"form.accidentInsurance.accInsProvId.countryCode\"></sxy-input>\r\n              <sxy-input model=\"form.accidentInsurance.accInsProvId.countryName\"></sxy-input>\r\n            </fieldset>\r\n          </div>\r\n        </sxy-form>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"absenses-tab\">\r\n        <salaxy-custom-code>\r\n          <div class=\"text-end\">\r\n            <button type=\"button\" class=\"btn btn-xs btn-primary\" ng-if=\"!$ctrl.isReadOnly\" ng-click=\"$ctrl.importAbsences()\" sxy-text=\"SALAXY.NG1.EarningsPaymentComponent.common.selectAbsences\"></button>\r\n          </div>\r\n        </salaxy-custom-code>\r\n        <sxy-form open-api=\"salaxy-secure/schemas/irepr.json\" read-only=\"{{ $ctrl.isReadOnly }}\" model=\"$ctrl.current.deliveryData.reports[0].absence\" type=\"Absence\" debugger=\"false\" auto-gen=\"false\">\r\n          <div>\r\n            <sxy-input model=\"form.absenceRepStartDate\" format=\"date\"></sxy-input>\r\n            <sxy-input model=\"form.absenceRepEndDate\" format=\"date\"></sxy-input>\r\n            <sxy-input model=\"form.unpaidAbsence.unpaidAbsencePeriods\" include=\"startDate,endDate,causeCode\">\r\n              <form>\r\n                <fieldset>\r\n                  <legend sxy-text=\"SALAXY.MODEL.UnpaidAbsencePeriod.title\"></legend>\r\n                  <sxy-input model=\"form.startDate\" format=\"date\"></sxy-input>\r\n                  <sxy-input model=\"form.endDate\" format=\"date\"></sxy-input>\r\n                  <sxy-input model=\"form.causeCode\"></sxy-input>\r\n                  <sxy-input model=\"form.absenceDays\"></sxy-input>\r\n                </fieldset>\r\n              </form>\r\n            </sxy-input>\r\n            <sxy-input model=\"form.paidAbsence.paidAbsencePeriods\" include=\"startDate,endDate,causeCode\">\r\n              <form>\r\n                <fieldset>\r\n                  <legend sxy-text=\"SALAXY.MODEL.PaidAbsencePeriod.title\"></legend>\r\n                  <sxy-input model=\"form.startDate\" format=\"date\"></sxy-input>\r\n                  <sxy-input model=\"form.endDate\" format=\"date\"></sxy-input>\r\n                  <sxy-input model=\"form.causeCode\"></sxy-input>\r\n                  <sxy-input model=\"form.absenceDays\"></sxy-input>\r\n                  <sxy-input model=\"form.absenceUntil\" format=\"date\"></sxy-input>\r\n                  <sxy-input model=\"form.amount\"></sxy-input>\r\n                  <sxy-input model=\"form.paidAbsencePeriodInfo\"></sxy-input>\r\n                  <sxy-input model=\"form.reimbApp\"></sxy-input>\r\n                </fieldset>\r\n              </form>\r\n            </sxy-input>\r\n          </div>\r\n        </sxy-form>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"calcrows-tab\">\r\n        <div ng-if=\"$ctrl.current.deliveryData.reports.length == 1\">\r\n\r\n          <fieldset>\r\n            <legend sxy-text=\"SALAXY.NG1.EarningsPaymentComponent.common.calcRows\"></legend>\r\n            <salaxy-calc-ir-rows model=\"$ctrl.calculation\" is-read-only-forced=\"true\" ng-ref=\"$ctrl.calcController\"></salaxy-calc-ir-rows>\r\n          </fieldset>\r\n          <hr/>\r\n\r\n          <fieldset>\r\n            <legend sxy-text=\"SALAXY.NG1.EarningsPaymentComponent.common.allRows\"></legend>\r\n            <sxy-form open-api=\"salaxy-secure/schemas/irepr.json\" read-only=\"{{ $ctrl.isReadOnly }}\" model=\"$ctrl.current.deliveryData.reports[0]\" type=\"Report\" debugger=\"false\" auto-gen=\"false\">\r\n              <div>\r\n                <fieldset>\r\n                  <sxy-input model=\"form.transactions\" read-only=\"true\" template-url=\"epr-transactions.html\"></sxy-input>\r\n                </fieldset>\r\n              </div>\r\n            </sxy-form>\r\n          </fieldset>\r\n        </div>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"history-tab\">\r\n        <sxy-form open-api=\"salaxy-secure/schemas/irepr.json\" read-only=\"{{ $ctrl.isReadOnly }}\" model=\"$ctrl.current\" type=\"EarningsPayment\" debugger=\"false\" auto-gen=\"false\">\r\n          <div>\r\n            <fieldset>\r\n              <sxy-input model=\"form.reportLog\" read-only=\"true\" include=\"irTimestamp,eventType,reportId,irReportId,irVersion\">\r\n              </sxy-input>\r\n            </fieldset>\r\n          </div>\r\n        </sxy-form>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>\r\n<script type=\"text/ng-template\" id=\"epr-professions.html\">\r\n  <table class=\"table\">\r\n    <caption sxy-text=\"SALAXY.NG1.EarningsPaymentComponent.professions.caption\"></caption>\r\n    <thead>\r\n      <tr>\r\n        <th sxy-text=\"SALAXY.NG1.EarningsPaymentComponent.professions.type\"></th>\r\n        <th sxy-text=\"SALAXY.NG1.EarningsPaymentComponent.professions.code\"></th>\r\n        <th sxy-text=\"SALAXY.NG1.EarningsPaymentComponent.professions.title\"></th>\r\n        <th class=\"text-end\">\r\n          <button type=\"button\" class=\"btn btn-xs btn-primary\" ng-if=\"!$ctrl.getReadOnly()\" ng-click=\"$ctrl.value.push({})\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n        </th>\r\n      </tr>\r\n    </thead>\r\n    <tbody class=\"form-horizontal\">\r\n      <tr ng-repeat=\"item in $ctrl.value\">\r\n        <td>\r\n          <salaxy-input-enum name=\"professionType\" label-type=\"plain\" type=\"select\" read-only=\"$ctrl.getReadOnly()\" enum=\"SALAXY.ENUM_IR.ProfessionType\" require=\"true\" ng-model=\"item.type\"></salaxy-input-enum>\r\n        </td>\r\n        <td>\r\n          <div ng-if=\"$ctrl.getReadOnly() && item.type == 'statisticsFinland'\">\r\n            <salaxy-input-occupation-type style=\"display: inline-block\" require=\"true\" name=\"statCode\" ng-model=\"item.code\" label-type=\"plain\" read-only=\"$ctrl.getReadOnly()\"></salaxy-input-occupation-type>\r\n            <span style=\"display: inline-block\" ng-if=\"$ctrl.getReadOnly()\">{{item.code}}</span>\r\n          </div>\r\n          <salaxy-input-occupation-type ng-if=\"!$ctrl.getReadOnly() && item.type == 'statisticsFinland'\" require=\"true\" name=\"statCode\" ng-model=\"item.code\" label-type=\"plain\" read-only=\"$ctrl.getReadOnly()\"></salaxy-input-occupation-type>\r\n          <salaxy-input ng-if=\"item.type != 'statisticsFinland'\" require=\"true\" name=\"code\" ng-model=\"item.code\" label-type=\"plain\" read-only=\"$ctrl.getReadOnly()\"></salaxy-input>\r\n        </td>\r\n        <td>\r\n          <salaxy-input name=\"title\" ng-model=\"item.title\" label-type=\"plain\" read-only=\"$ctrl.getReadOnly()\"></salaxy-input>\r\n        </td>\r\n        <td class=\"text-end\">\r\n          <button type=\"button\" class=\"btn btn-xs btn-danger\" ng-if=\"!$ctrl.getReadOnly()\" ng-click=\"$ctrl.delete(item, $index)\">\r\n            <i class=\"bi bi-trash\" title=\"Delete row\"></i>\r\n          </button>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n</script>\r\n<script type=\"text/ng-template\" id=\"epr-transactions.html\">\r\n  <table class=\"table\">\r\n    <thead>\r\n      <tr>\r\n        <th sxy-text=\"SALAXY.NG1.EarningsPaymentComponent.transactions.code\"></th>\r\n        <th class=\"text-end\" sxy-text=\"SALAXY.NG1.EarningsPaymentComponent.transactions.count\"></th>\r\n        <!--th class=\"text-end\">Ansaintakauden<br> alku ja loppu</th -->\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat=\"item in $ctrl.value\">\r\n        <td>\r\n          <salaxy-input-income-type name=\"code\" label-type=\"plain\" ng-model=\"item.transactionBasic.transactionCode\" read-only=\"true\"></salaxy-input-income-type>\r\n        </td>\r\n        <td class=\"text-end\">\r\n          <salaxy-input-number name=\"amount\" label-type=\"plain\" ng-model=\"item.transactionBasic.amount\" read-only=\"true\">\r\n        </td>\r\n        <!--td class=\"text-end\">\r\n          <span ng-repeat=\"earningPeriod in item.earningPeriods\">\r\n            {{earningPeriod.startDate | sxyDate}} - {{earningPeriod.endDate | sxyDate}}\r\n          </span>\r\n\r\n\r\n        </td-->\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n</script>`);\n\n $templateCache.put(\"salaxy-components/report/IrEarningsPaymentList.html\",`<div class=\"salaxy-component salaxy-ir-earnings-payment-list\">\r\n  <salaxy-odata-table crud-controller=\"IrEarningsPaymentCrudController as $crud\" template-url=\"salaxy-components/odata/lists/IrEpr.html\" options=\"$ctrl.queryOptions\">\r\n  </salaxy-odata-table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/report/IrPayerSummary.html\",`<div class=\"salaxy-component salaxy salaxy-ir-payer-summary\">\r\n  <salaxy-spinner ng-if=\"$ctrl.isLoading\" full-screen=\"true\" heading=\"SALAXY.UI_Terms.loading\" text=\"SALAXY.UI_Terms.pleaseWait\"></salaxy-spinner>\r\n  <div ng-if=\"'test' | sxyIsInRole\">\r\n    <div class=\"btn-toolbar\" role=\"toolbar\" ng-if=\"$ctrl.isReadOnly\">\r\n      <div class=\"btn-group\" role=\"group\" aria-label=\"Muokkaa\">\r\n        <button ng-click=\"$ctrl.tempShowEditInNonAdminMode = true\" type=\"button\" role=\"group\" class=\"btn btn-primary\">VAIN TEST: Muokkaa</button>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div class=\"btn-toolbar\" role=\"toolbar\" ng-if=\"!$ctrl.isReadOnly\">\r\n    <div class=\"btn-group\" role=\"group\" aria-label=\"Tallenna\">\r\n      <button ng-click=\"$ctrl.save()\" type=\"button\" role=\"group\" class=\"btn btn-primary\" ng-disabled=\"!$ctrl.hasChanges\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n    </div>\r\n    <div class=\"btn-group\" role=\"group\" aria-label=\"Lähetä/mitätöi\">\r\n      <button ng-click=\"$ctrl.sendToIncomesRegister()\" type=\"button\" role=\"group\" class=\"btn btn-default\" sxy-text=\"SALAXY.UI_Terms.send\"></button>\r\n      <button ng-click=\"$ctrl.openSetScheduleDialog()\" type=\"button\" role=\"group\" class=\"btn btn-default\" sxy-text=\"SALAXY.NG1.PayerSummaryComponent.common.addScheduling\"></button>\r\n      <button ng-click=\"$ctrl.removeIrQueueItem()\" type=\"button\" role=\"group\" class=\"btn btn-danger\" ng-disabled=\"!$ctrl.current.scheduledFor\" sxy-text=\"SALAXY.NG1.PayerSummaryComponent.common.removeScheduling\"></button>\r\n      <button ng-click=\"$ctrl.cancelToIncomesRegister()\" type=\"button\" role=\"group\" class=\"btn btn-danger\" ng-disabled=\"!$ctrl.isCancellable\" sxy-text=\"SALAXY.NG1.PayerSummaryComponent.common.cancel\"></button>\r\n    </div>\r\n  </div>\r\n  <div class=\"form-horizontal\">\r\n    <salaxy-tab-buttons\r\n      current-tab=\"$ctrl.currentTab\"\r\n      options=\"[\r\n        { value: 'default', text: 'SALAXY.NG1.PayerSummaryComponent.common.basicInfo' },\r\n        { value: 'payer', text: 'SALAXY.NG1.PayerSummaryComponent.common.payer' },\r\n        { value: 'paymentmonth', text: 'SALAXY.NG1.PayerSummaryComponent.common.payerInfo' },\r\n        { value: 'history', text: 'SALAXY.NG1.PayerSummaryComponent.common.historyTitle' },\r\n        { value: 'calculations', text: 'SALAXY.NG1.PayerSummaryComponent.common.calculationsTitle', hidden: !$ctrl.current.info.calculationIds.length }\r\n      ]\"\r\n      tabs-id=\"irPayerSummary\">\r\n    </salaxy-tab-buttons>\r\n    <div class=\"tab-content\" id=\"tab-content-irPayerSummary\">\r\n      <div class=\"tab-pane\" id=\"default-tab\">\r\n        <div>\r\n          <h3>\r\n            {{'SALAXY.MODEL.PayerSummary.status.title' | sxyTranslate}}: {{ \"SALAXY.ENUM_IR.PayerSummaryReportStatus.\" + $ctrl.current.status + \".label\" | sxyTranslate }}\r\n            <div class=\"label label-success float-end\" ng-if=\"$ctrl.current.validation.isValid\">{{SALAXY.NG1.PayerSummaryComponent.common.noErrors | sxyTranslate}}</div>\r\n          </h3>\r\n          <salaxy-validation-summary api-validation=\"$ctrl.current.validation\" ng-if=\"!$ctrl.current.validation.isValid\">\r\n          </salaxy-validation-summary>\r\n          <salaxy-validation-summary api-validation=\"$ctrl.current.irErrors\" ng-if=\"!$ctrl.current.irErrors.isValid\">\r\n          </salaxy-validation-summary>\r\n        </div>\r\n        <sxy-form open-api=\"salaxy-secure/schemas/irpsr.json\" model=\"$ctrl.current\" type=\"PayerSummary\" debugger=\"false\" auto-gen=\"false\" read-only=\"{{ $ctrl.isReadOnly }}\">\r\n          <div>\r\n            <div class=\"row\">\r\n              <div class=\"col-md-6\">\r\n                <fieldset>\r\n                  <legend sxy-text=\"SALAXY.NG1.PayerSummaryComponent.common.basicInfo\"></legend>\r\n                  <sxy-form open-api=\"salaxy-secure/schemas/irpsr.json\" model=\"$ctrl.current.deliveryData.reports[0].reportData\" type=\"ReportData\" debugger=\"false\" auto-gen=\"false\" read-only=\"{{ $ctrl.isReadOnly }}\">\r\n                    <div>\r\n                      <sxy-input model=\"form.reportId\" read-only=\"true\"></sxy-input>\r\n                      <!--sxy-input model=\"form.irReportId\" read-only=\"true\"></sxy-input-->\r\n                    </div>\r\n                  </sxy-form>\r\n                  <sxy-input model=\"form.createdAt\"></sxy-input>\r\n                  <sxy-input model=\"form.updatedAt\"></sxy-input>\r\n                  <sxy-input model=\"form.irStatus\" read-only=\"true\"></sxy-input>\r\n                  <sxy-input model=\"form.isModified\" read-only=\"true\"></sxy-input>\r\n                  <sxy-input model=\"form.scheduledFor\" read-only=\"true\"></sxy-input>\r\n                </fieldset>\r\n              </div>\r\n              <div class=\"col-md-6\">\r\n                <fieldset>\r\n                  <legend sxy-text=\"SALAXY.NG1.PayerSummaryComponent.common.deliveryDataTitle\"></legend>\r\n                  <sxy-input model=\"form.deliveryData.deliveryDataType\" read-only=\"true\"></sxy-input>\r\n                  <sxy-input model=\"form.deliveryData.timestamp\" read-only=\"true\"></sxy-input>\r\n                  <sxy-input model=\"form.deliveryData.reportDate\" format=\"date\" read-only=\"true\"></sxy-input>\r\n                  <sxy-input model=\"form.deliveryData.deliveryDataCreator.code\" label=\"SALAXY.NG1.PayerSummaryComponent.common.deliveryDataCreator\" read-only=\"true\"></sxy-input>\r\n                  <sxy-input model=\"form.deliveryData.deliveryDataSender.code\" label=\"SALAXY.NG1.PayerSummaryComponent.common.deliveryDataSender\" read-only=\"true\"></sxy-input>\r\n                </fieldset>\r\n              </div>\r\n            </div>\r\n            <sxy-input model=\"form.deliveryData.contactPersons\" include=\"name,responsibilityCode\"></sxy-input>\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.NG1.PayerSummaryComponent.common.deliveryDataOwner\"></legend>\r\n              <sxy-input model=\"form.deliveryData.deliveryDataOwner.code\"></sxy-input>\r\n              <sxy-input model=\"form.deliveryData.deliveryDataOwner.type\"></sxy-input>\r\n              <sxy-input model=\"form.deliveryData.deliveryDataOwner.countryCode\"></sxy-input>\r\n              <sxy-input model=\"form.deliveryData.deliveryDataOwner.countryName\"></sxy-input>\r\n            </fieldset>\r\n          </div>\r\n        </sxy-form>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"payer-tab\">\r\n        <sxy-form open-api=\"salaxy-secure/schemas/irpsr.json\" model=\"$ctrl.current.deliveryData.payer\" type=\"Payer\" debugger=\"false\" auto-gen=\"false\" read-only=\"{{ $ctrl.isReadOnly }}\">\r\n          <div>\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.NG1.PayerSummaryComponent.common.payerTitle\"></legend>\r\n              <sxy-input model=\"form.payerBasic.companyName\"></sxy-input>\r\n              <sxy-input model=\"form.payerBasic.missingId\"></sxy-input>\r\n              <sxy-input model=\"form.payerIds\"></sxy-input>\r\n              <sxy-input model=\"form.payerOther.payerTypes\"></sxy-input>\r\n              <sxy-input model=\"form.subOrgs\"></sxy-input>\r\n              <sxy-input model=\"form.pensionInsurances\"></sxy-input>\r\n              <sxy-input model=\"form.accidentInsurances\" include=\"accInsPolicyNo\">\r\n                <form>\r\n                  <fieldset>\r\n                    <legend sxy-text=\"SALAXY.MODEL.AccidentInsurance.title\"></legend>\r\n                    <sxy-input model=\"form.accInsPolicyNo\"></sxy-input>\r\n                    <sxy-input model=\"form.accInsProvId.code\"></sxy-input>\r\n                    <sxy-input model=\"form.accInsProvId.type\"></sxy-input>\r\n                    <sxy-input model=\"form.accInsProvId.countryCode\"></sxy-input>\r\n                    <sxy-input model=\"form.accInsProvId.countryName\"></sxy-input>\r\n                  </fieldset>\r\n                </form>\r\n              </sxy-input>\r\n            </fieldset>\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.NG1.PayerSummaryComponent.common.payerAddressTitle\"></legend>\r\n              <sxy-input model=\"form.address.co\"></sxy-input>\r\n              <sxy-input model=\"form.address.street\"></sxy-input>\r\n              <sxy-input model=\"form.address.poBox\"></sxy-input>\r\n              <sxy-input model=\"form.address.postalCode\"></sxy-input>\r\n              <sxy-input model=\"form.address.postOffice\"></sxy-input>\r\n              <sxy-input model=\"form.address.countryCode\"></sxy-input>\r\n              <sxy-input model=\"form.address.countryName\"></sxy-input>\r\n            </fieldset>\r\n          </div>\r\n        </sxy-form>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"paymentmonth-tab\">\r\n        <sxy-form open-api=\"salaxy-secure/schemas/irpsr.json\" model=\"$ctrl.current.deliveryData.reports[0]\" type=\"Report\" debugger=\"false\" auto-gen=\"false\" read-only=\"{{ $ctrl.isReadOnly }}\">\r\n          <div>\r\n            <fieldset>\r\n              <sxy-input model=\"form.paymentMonth.year\" read-only=\"true\"></sxy-input>\r\n              <sxy-input model=\"form.paymentMonth.month\" read-only=\"true\"></sxy-input>\r\n            </fieldset>\r\n            <fieldset>\r\n              <salaxy-custom-code>\r\n                <sxy-input model=\"form.transactions\" template-url=\"psr-transactions.html\"></sxy-input>\r\n              </salaxy-custom-code>\r\n            </fieldset>\r\n          </div>\r\n        </sxy-form>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"history-tab\">\r\n        <sxy-form open-api=\"salaxy-secure/schemas/irpsr.json\" model=\"$ctrl.current\" type=\"PayerSummary\" debugger=\"false\" auto-gen=\"false\" read-only=\"{{ $ctrl.isReadOnly }}\">\r\n          <div>\r\n            <fieldset>\r\n              <sxy-input model=\"form.reportLog\" read-only=\"true\" include=\"irTimestamp,eventType,reportId,irReportId,irVersion\"></sxy-input>\r\n            </fieldset>\r\n          </div>\r\n        </sxy-form>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"calculations-tab\">\r\n        <sxy-form ng-if=\"$ctrl.calculationsOpened || $ctrl.currentTab == 'calculations'\" ng-init=\"$ctrl.calculationsOpened=true\" open-api=\"salaxy-secure/schemas/irpsr.json\" model=\"$ctrl.current\" type=\"PayerSummary\" debugger=\"false\" auto-gen=\"false\" read-only=\"{{ $ctrl.isReadOnly }}\">\r\n          <div>\r\n            <fieldset>\r\n              <salaxy-custom-code>\r\n                <sxy-input model=\"form.info.calculationIds\" template-url=\"psr-calculations.html\"></sxy-input>\r\n              </salaxy-custom-code>\r\n            </fieldset>\r\n          </div>\r\n        </sxy-form>\r\n      </div>\r\n  </div>\r\n</div>\r\n<script type=\"text/ng-template\" id=\"psr-transactions.html\">\r\n  <table class=\"table\">\r\n    <caption sxy-text=\"SALAXY.NG1.PayerSummaryComponent.transactions.incomeTypes\"></caption>\r\n    <thead>\r\n      <tr>\r\n        <th sxy-text=\"SALAXY.NG1.PayerSummaryComponent.transactions.incomeType\"></th>\r\n        <th sxy-text=\"SALAXY.NG1.PayerSummaryComponent.transactions.count\"></th>\r\n        <th class=\"text-end\">\r\n          <button type=\"button\" class=\"btn btn-xs btn-primary\" ng-if=\"!$ctrl.getReadOnly()\" ng-click=\"$ctrl.value.push({})\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n        </th>\r\n      </tr>\r\n    </thead>\r\n    <tbody class=\"form-horizontal\">\r\n      <tr ng-repeat=\"item in $ctrl.value\">\r\n        <td>\r\n          <salaxy-input-enum name=\"transactionCode\" label-type=\"plain\" type=\"select\" read-only=\"$ctrl.getReadOnly()\" enum=\"SALAXY.ENUM_IR.SummaryTransactionCode\" require=\"true\" ng-model=\"item.transactionBasic.summaryTransactionCode\"></salaxy-input-enum>\r\n        </td>\r\n        <td>\r\n          <salaxy-input-number ng-if=\"item.transactionBasic.summaryTransactionCode != 'noWagesPayable'\" require=\"true\" name=\"transactionAmount\" label-type=\"plain\" read-only=\"$ctrl.getReadOnly()\" ng-model=\"item.transactionBasic.amount\"></salaxy-input-number>\r\n          <div ng-if=\"item.transactionBasic.summaryTransactionCode == 'noWagesPayable'\" class=\"form-control-plaintext\" ng-init=\"item.transactionBasic.amount = null\">-</div>\r\n        </td>\r\n        <td class=\"text-end\">\r\n          <button type=\"button\" class=\"btn btn-xs btn-danger\" ng-if=\"!$ctrl.getReadOnly()\" ng-click=\"$ctrl.delete(item, $index)\">\r\n            <i class=\"bi bi-trash\" title=\"Delete row\"></i>\r\n          </button>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n</script>\r\n<script type=\"text/ng-template\" id=\"psr-calculations.html\">\r\n    <div class=\"table-responsive\">\r\n      <table class=\"table table-striped\">\r\n        <thead>\r\n          <tr>\r\n            <th colspan=\"2\">\r\n              <span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span>\r\n            </th>\r\n            <th>\r\n              <span><span sxy-text=\"SALAXY.NG1.CalcListComponent.status.title\"></span></span><br />\r\n              <span><span sxy-text=\"SALAXY.NG1.CalcListComponent.payment\"></span></span>\r\n            </th>\r\n            <th class=\"right\">\r\n              <span><span sxy-text=\"SALAXY.NG1.CalcListComponent.salary\"></span></span><br />\r\n              <span><span sxy-text=\"SALAXY.NG1.CalcListComponent.payment\"></span></span>\r\n            </th>\r\n            <th class=\"right\" colspan=\"2\">\r\n            </th>\r\n          </tr>\r\n        </thead>\r\n        <tbody ng-controller=\"CalculationCrudController as $crud\">\r\n          <tr ng-repeat=\"id in $ctrl.value\" ng-controller=\"ODataQueryController as $odata\" ng-init=\"$odata.url='/v03/api/calculations/category/all?$filter=id eq \\\\'' + id + '\\\\'';$odata.reload()\">\r\n            <td ng-if=\"!$odata.items[0]\" colspan=\"6\"><span><i class=\"bi bi-arrow-repeat bi-spin\"></i></span></td>\r\n            <td ng-if=\"$odata.items[0]\" class=\"td-avatar middle\">\r\n              <salaxy-avatar avatar=\"$odata.items[0].otherPartyInfo.avatar\"></salaxy-avatar>\r\n            </td>\r\n            <td ng-if=\"$odata.items[0]\"class=\"td-name middle\">\r\n              <span ng-if=\"$odata.items[0].otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.CalcListComponent.notSelected\"></span>\r\n              <strong>{{$odata.items[0].otherPartyInfo.avatar.displayName}}</strong><br />\r\n            </td>\r\n            <td ng-if=\"$odata.items[0]\" class=\"middle\">\r\n              {{ \"SALAXY.ENUM.CalculationStatus.\" + $odata.items[0].status + \".label\" | sxyTranslate }}<br /> {{ $odata.items[0].endAt | date }}\r\n            </td>\r\n            <td ng-if=\"$odata.items[0]\" class=\"right middle\">\r\n              {{ $odata.items[0].grossSalary | currency }}<br /> {{ $odata.items[0].payment | currency }}\r\n            </td>\r\n            <td ng-if=\"$odata.items[0]\" class=\"middle\">\r\n              <a href=\"\" ng-click=\"$crud.showDetails($odata.items[0])\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\"><span sxy-text=\"SALAXY.UI_Terms.show\"></span>\r\n                </a>\r\n            </td>    \r\n            <td ng-if=\"$odata.items[0]\" class=\"middle\">\r\n              <a ng-href=\"{{$crud.getPdfUrl($odata.items[0])}}\" target=\"_blank\" title=\"{{ 'SALAXY.UI_Terms.printable' | sxyTranslate}}\" class=\"btn btn-sm btn-default btn-block\"><span sxy-text=\"SALAXY.UI_Terms.printable\"></span></a>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n</script>\r\n`);\n\n $templateCache.put(\"salaxy-components/report/IrPayerSummaryList.html\",`<div class=\"salaxy-component salaxy-ir-payer-summary-list\">\r\n  <salaxy-odata-table crud-controller=\"IrPayerSummaryCrudController as $crud\" template-url=\"salaxy-components/odata/lists/IrPsr.html\" options=\"$ctrl.queryOptions\">\r\n  </salaxy-odata-table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/report/modals/AccountNumbers.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.AccountNumbersComponent.title\"></h2>\r\n  <button type=\"button\" class=\"ms-auto btn-close\" ng-click=\"$close(null)\" aria-label=\"Close\"></button>\r\n</div>\r\n<div class=\"modal-body\" id=\"modal-body\">\r\n  <div class=\"table-responsive\" style=\"max-height: 40vh;\">\r\n    <table class=\"table table-sm\">\r\n      <thead>\r\n        <tr>\r\n          <th sxy-text=\"SALAXY.NG1.AccountNumbersComponent.accountNumber\"></th>\r\n          <th sxy-text=\"SALAXY.NG1.AccountNumbersComponent.description\"></th>\r\n          <th>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"account in $ctrl.data.accounts\">\r\n          <td>\r\n            {{account.account}}\r\n          </td>\r\n          <td>\r\n            {{account.text}}\r\n          </td>\r\n          <td class=\"right\">\r\n            <button ng-disabled=\"account.isSelected\" title=\"Valitse\" class=\"btn btn-success\" type=\"button\" ng-click=\"$close(account)\" sxy-text=\"SALAXY.NG1.AccountNumbersComponent.choose\"></button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n      <tfoot>\r\n      </tfoot>\r\n    </table>\r\n  </div>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button type=\"button\" class=\"btn btn-default float-end\" ng-click=\"$close(null)\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/report/modals/CalculationReportPeriodSelection.html\",`<form name=\"periodForm\" class=\"form-horizontal\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.CumulativeReportPeriodSelection.title\"></h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <salaxy-input-enum name=\"period\" label=\"SALAXY.NG1.CumulativeReportPeriodSelection.periodLabel\" options=\"{year: ('SALAXY.NG1.CumulativeReportPeriodSelection.enumOptionYear' | sxyTranslate), month: ('SALAXY.NG1.CumulativeReportPeriodSelection.enumOptionMonth' | sxyTranslate), all: ('SALAXY.NG1.CumulativeReportPeriodSelection.enumOptionAll' | sxyTranslate), custom: ('SALAXY.NG1.CumulativeReportPeriodSelection.enumOptionCustom' | sxyTranslate)}\"\r\n      ng-model=\"$ctrl.current.periodType\" type=\"radio\" required>\r\n    </salaxy-input-enum>\r\n    <salaxy-input-enum name=\"periodDateKind\" label=\"SALAXY.NG1.CumulativeReportPeriodSelection.periodDateKindLabel\" enum=\"PeriodDateKind\"\r\n      ng-model=\"$ctrl.current.periodDateKind\" type=\"radio\" required>\r\n    </salaxy-input-enum>\r\n    <salaxy-datepicker-popup name=\"refDateMonth\" placeholder=\"SALAXY.NG1.CumulativeReportPeriodSelection.month\" ng-if=\"$ctrl.current.periodType == 'month'\" format=\"month\" ng-model=\"$ctrl.current.refDate\"\r\n      label=\"SALAXY.NG1.CumulativeReportPeriodSelection.chooseMonthLabel\" require=\"true\"></salaxy-datepicker-popup>\r\n    <salaxy-datepicker-popup name=\"refDateYear\" placeholder=\"SALAXY.NG1.CumulativeReportPeriodSelection.year\" ng-if=\"$ctrl.current.periodType == 'year'\" format=\"year\" ng-model=\"$ctrl.current.refDate\"\r\n      label=\"SALAXY.NG1.CumulativeReportPeriodSelection.chooseYearLabel\" require=\"true\"></salaxy-datepicker-popup>\r\n    <salaxy-datepicker-popup name=\"refDateCustom\" ng-if=\"$ctrl.current.periodType == 'custom'\" ng-model=\"$ctrl.current.refDate\" label=\"SALAXY.NG1.CumulativeReportPeriodSelection.refDateCustomLabel\" require=\"true\">\r\n    </salaxy-datepicker-popup>\r\n    <salaxy-datepicker-popup name=\"endDateCustom\" ng-if=\"$ctrl.current.periodType == 'custom'\" ng-model=\"$ctrl.current.endDate\" label=\"SALAXY.NG1.CumulativeReportPeriodSelection.endDateCustomLabel\">\r\n    </salaxy-datepicker-popup>\r\n    <salaxy-form-group name=\"Workers\" label=\"SALAXY.NG1.CumulativeReportPeriodSelection.workersLabel\">\r\n      <span ng-if=\"$ctrl.current.selectedWorkers.length\"> {{'SALAXY.NG1.CumulativeReportPeriodSelection.chosen' | sxyTranslate}}: {{ $ctrl.current.selectedWorkers.length }} </span>\r\n      <span ng-if=\"!$ctrl.current.selectedWorkers.length\"> {{'SALAXY.NG1.CumulativeReportPeriodSelection.all' | sxyTranslate}} </span>\r\n      <button type=\"button\" class=\"btn btn-xs btn-default\" ng-click=\"$ctrl.logic.showWorkerSelection($ctrl.current)\" sxy-text=\"SALAXY.NG1.CumulativeReportPeriodSelection.more\" ps=\"...\"></button>\r\n    </salaxy-form-group>\r\n  </div>\r\n  <div class=\"modal-footer\">\r\n    <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n    <button type=\"submit\" class=\"btn btn-primary\" ng-disabled=\"!periodForm.$valid\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n  </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/report/modals/CalculationReportSaveTemplate.html\",`<form name=\"templateForm\" class=\"form-horizontal\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.CumulativeReportSaveTemplate.title\"></h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <salaxy-input-boolean disabled=\"!$ctrl.current.isEditable\" name=\"isNew\" label=\"SALAXY.NG1.CumulativeReportSaveTemplate.isNewLabel\" ng-model=\"$ctrl.current.isNew\" type=\"radio\" label-true=\"SALAXY.NG1.CumulativeReportSaveTemplate.isNewLabelTrue\" label-false=\"SALAXY.NG1.CumulativeReportSaveTemplate.isNewLabelFalse\" required>\r\n    </salaxy-input-boolean>\r\n    <salaxy-input name=\"label\" label=\"SALAXY.NG1.CumulativeReportSaveTemplate.currentLabel\" ng-model=\"$ctrl.current.label\" required></salaxy-input>\r\n  </div>\r\n  <div class=\"modal-footer\">\r\n    <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n    <button type=\"button\" ng-if=\"!$ctrl.current.isNew\" class=\"btn btn-danger\" ng-click=\"$close('delete')\" sxy-text=\"SALAXY.UI_Terms.delete\"></button>\r\n    <button type=\"submit\" class=\"btn btn-primary\" ng-disabled=\"!templateForm.$valid\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n  </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/report/modals/FivaldiPreview.html\",`<div class=\"table-responsive\">\r\n  <table class=\"table table-sm table-striped text-small\">\r\n    <tbody>\r\n      <tr>\r\n        <th>voucherTypeId</th>\r\n        <td>{{item.preview.voucherTypeId}}</td>\r\n        <td colspan=\"7\"></td>\r\n      </tr>\r\n      <tr>\r\n        <th>originalVoucherNumber</th>\r\n        <td>{{item.preview.originalVoucherNumber}}</td>\r\n        <td colspan=\"7\"></td>\r\n      </tr>\r\n      <tr>\r\n        <th>voucherDate</th>\r\n        <td>{{item.preview.voucherDate}}</td>\r\n        <td colspan=\"7\"></td>\r\n      </tr>\r\n      <tr>\r\n        <th>bookkeepingMonth</th>\r\n        <td>{{item.preview.bookkeepingMonth}}</td>\r\n        <td colspan=\"7\"></td>\r\n      </tr>\r\n      <tr>\r\n        <th>validateEntrySum</th>\r\n        <td>{{item.preview.validateEntrySum}}</td>\r\n        <td colspan=\"7\"></td>\r\n      </tr>\r\n      <tr>\r\n        <th>vatType</th>\r\n        <td>{{item.preview.vatType}}</td>\r\n        <td colspan=\"7\"></td>\r\n      </tr>\r\n      <tr>\r\n        <th>amount</th>\r\n        <th>accountNumber</th>\r\n        <th>balanceCode</th>\r\n        <th>dimensionValue1</th>\r\n        <th>description</th>\r\n        <th>vat.vatCode</th>\r\n        <th>vat.vatAmount</th>\r\n        <th>vat.account</th>\r\n        <th>vat.account2</th>\r\n      </tr>\r\n      <tr ng-repeat=\"entry in item.preview.voucherEntries\">\r\n        <td class=\"right\">{{ entry.amount }}</td>\r\n        <td class=\"right\">{{ entry.accountNumber}}</td>\r\n        <td class=\"right\">{{ entry.balanceCode }}</td>\r\n        <td>{{ entry.dimensionValue1 }}</td>\r\n        <td>{{ entry.description }}</td>      \r\n        <td>{{entry.vat.vatCode}}</td>\r\n        <td class=\"right\">{{entry.vat.vatAmount}}</td>\r\n        <td>{{entry.vat.account}}</td>\r\n        <td>{{entry.vat.account2}}</td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/report/modals/IncomeTypeCodeEditor.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.IncomeTypeCodeEditorComponent.title\"></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n</div>\r\n<div class=\"modal-body\" id=\"modal-body\">\r\n  <div class=\"row\">\r\n    <div class=\"col-6 form-horizontal\">\r\n      <salaxy-input-income-type name=\"Tulolaji\"  ng-model=\"$ctrl.data.row.transactionBasic.transactionCode\" ></salaxy-input-income-type>\r\n      <salaxy-input-number name=\"Summa\" ng-model=\"$ctrl.data.row.transactionBasic.amount\"></salaxy-input-number>\r\n\r\n      <salaxy-form-group name=\"carBenefit\" label=\"SALAXY.NG1.IncomeTypeCodeEditorComponent.carBenefitTypeLabel\" label-type=\"horizontal\">\r\n        <select class=\"form-select\" ng-model=\"$ctrl.data.carBenefit\" ng-model-options=\"{ getterSetter: true }\">\r\n          <option value=\"\" sxy-text=\"SALAXY.NG1.IncomeTypeCodeEditorComponent.noSelection\"></option>\r\n          <option value=\"limitedCarBenefit\" sxy-text=\"SALAXY.NG1.IncomeTypeCodeEditorComponent.carBenefitLimited\"></option>\r\n          <option value=\"fullCarBenefit\" sxy-text=\"SALAXY.NG1.IncomeTypeCodeEditorComponent.carBenefitFull\"></option>\r\n        </select>\r\n      </salaxy-form-group>\r\n\r\n      <salaxy-input-enum ng-if=\"$ctrl.data.row.carBenefit\" label=\"SALAXY.NG1.IncomeTypeCodeEditorComponent.carBenefitAgeGroupCodeLabel\" name=\"ageGroupCode\" ng-model=\"$ctrl.data.row.carBenefit.ageGroupCode\" options=\"{ '': ('SALAXY.NG1.IncomeTypeCodeEditorComponent.noSelection' | sxyTranslate), 'a': 'A', 'b': 'B', 'c': 'C', 'u': 'U' }\" type=\"select\"></salaxy-input-enum>\r\n\r\n      <salaxy-input-number ng-if=\"$ctrl.data.row.carBenefit\" label=\"SALAXY.NG1.IncomeTypeCodeEditorComponent.carBenefitEmissionsValueLabel\" name=\"emissionsValue\" ng-model=\"$ctrl.data.row.carBenefit.emissionsValue\" minimum=\"0\" maximum=\"100\" ></salaxy-input-number>\r\n\r\n      <salaxy-form-group name=\"kilometers\" label=\"SALAXY.NG1.IncomeTypeCodeEditorComponent.carBenefitKilometersLabel\" label-type=\"horizontal\">\r\n        <label>\r\n          {{ $ctrl.data.row.carBenefit.kilometers == null ? \"-\" : $ctrl.data.row.carBenefit.kilometers }}\r\n        </label>\r\n      </salaxy-form-group>\r\n\r\n      <salaxy-form-group name=\"mealBenefit\" label=\"SALAXY.NG1.IncomeTypeCodeEditorComponent.mealBenefitLabel\" label-type=\"horizontal\">\r\n        <select class=\"form-select\" ng-model=\"$ctrl.data.mealBenefit\" ng-model-options=\"{ getterSetter: true }\">\r\n          <option value=\"\" sxy-text=\"SALAXY.NG1.IncomeTypeCodeEditorComponent.noSelection\">Ei valintaa</option>\r\n          <option ng-value=\"true\" sxy-text=\"SALAXY.NG1.IncomeTypeCodeEditorComponent.mealBenefitTrue\">Kyllä</option>\r\n          <option ng-value=\"false\" sxy-text=\"SALAXY.NG1.IncomeTypeCodeEditorComponent.mealBenefitFalse\">Ei</option>\r\n        </select>\r\n      </salaxy-form-group>\r\n\r\n      <div class=\"form-group\" ng-if=\"!$ctrl.data.row.dailyAllowance || $ctrl.data.row.dailyAllowance.length != 1\">\r\n        <label for=\"addDailyAllowance\" class=\"col-sm-4 control-label\">\r\n              <span sxy-text=\"SALAXY.NG1.IncomeTypeCodeEditorComponent.dailyAllowanceTypeLabel\"></span>\r\n          </label>\r\n        <div class=\"col-sm-8\">\r\n          <button type=\"button\" class=\"btn btn-block btn-success\" ng-click=\"$ctrl.data.row.dailyAllowance = ['fullDailyAllowance']\"><i class=\"bi bi-plus-lg\"></i> {{'SALAXY.NG1.IncomeTypeCodeEditorComponent.add' | sxyTranslate}}</button>\r\n        </div>\r\n      </div>\r\n\r\n      <div ng-if=\"$ctrl.data.row.dailyAllowance && $ctrl.data.row.dailyAllowance.length == 1\">\r\n        <salaxy-input-enum label=\"SALAXY.NG1.IncomeTypeCodeEditorComponent.dailyAllowanceTypeLabel\" name=\"dailyAllowance\" ng-model=\"$ctrl.data.row.dailyAllowance[0]\" options=\"{ '': ('SALAXY.NG1.IncomeTypeCodeEditorComponent.noSelection' | sxyTranslate), 'partialDailyAllowance': ('SALAXY.NG1.IncomeTypeCodeEditorComponent.partialDailyAllowanceEnum' | sxyTranslate), 'fullDailyAllowance': ('SALAXY.NG1.IncomeTypeCodeEditorComponent.fullDailyAllowanceEnum' | sxyTranslate), 'internationalDailyAllowance': ('SALAXY.NG1.IncomeTypeCodeEditorComponent.internationalDailyAllowanceEnum' | sxyTranslate) }\"\r\n          type=\"select\"></salaxy-input-enum>\r\n        <div class=\"row\">\r\n          <div class=\"col-sm-4\"></div>\r\n          <div class=\"col-sm-8\">\r\n            <button type=\"button\" class=\"btn btn-block btn-danger\" ng-click=\"$ctrl.data.row.dailyAllowance = null\"><i class=\"bi bi-trash-fill\"></i> {{'SALAXY.UI_Terms.delete' | sxyTranslate}}</button>\r\n          </div>\r\n        </div>\r\n      </div>\r\n\r\n    </div>\r\n    <div class=\"col-6\">\r\n      <div style=\"width: 100%; overflow: auto\">\r\n        <pre>{{ $ctrl.data.row | json }}</pre>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button type=\"button\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/report/modals/IrImportAbsencesDialog.html\",`<div class=\"card panel-primary\">\r\n  <div class=\"card-header \">\r\n    <h2 sxy-text=\"SALAXY.NG1.IrImportAbsencesDialogComponent.heading\"></h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$dismiss()\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"card-body\">\r\n    <div class=\"table-responsive\">\r\n      <table class=\"table\">\r\n        <thead>\r\n          <tr>\r\n            <th>{{ \"SALAXY.NG1.IrImportAbsencesDialogComponent.absences\" | sxyTranslate }}</th>\r\n            <th class=\"right\" sxy-text=\"SALAXY.NG1.IrImportAbsencesDialogComponent.wholeAbsence\"></th>\r\n            <th class=\"right\" sxy-html=\"SALAXY.NG1.IrImportAbsencesDialogComponent.isHolidayAccrual.html\"></th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr ng-repeat=\"row in $ctrl.current.periods\">\r\n            <td>\r\n              <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" avatar=\"{ color: '#2b507c', initials: (row.period.daysCount + 'pv'), entityType: 'company' }\">\r\n              </salaxy-avatar>\r\n              <strong>{{ \"AbsenceCauseCode.\" + row.causeCode | sxyEnum }}</strong><br />\r\n              <div class=\"float-start\" style=\"padding: 0px;\">\r\n                {{ row.isPaid ? ('SALAXY.NG1.IrImportAbsencesDialogComponent.isPaid' | sxyTranslate) : ('SALAXY.NG1.IrImportAbsencesDialogComponent.notPaid' | sxyTranslate) }}\r\n                <span ng-if=\"row.isPaid != row.isHolidayAccrual\"> {{ row.isHolidayAccrual ? ('SALAXY.NG1.IrImportAbsencesDialogComponent.isAccrual' | sxyTranslate) :\r\n                  ('SALAXY.NG1.IrImportAbsencesDialogComponent.notAccrual' | sxyTranslate) }}</span>\r\n              </div>\r\n              <div class=\"truncate\" style=\"max-width: 250px; padding: 0px;\">\r\n                &nbsp;{{ row.notes }}\r\n              </div>\r\n            </td>\r\n            <td class=\"right\">\r\n              <strong>{{ row.period.daysCount | sxyCount : \"day\" }}</strong><br /> {{ row.period.start | date : 'dd.MM.' }}-{{ row.period.end | date : 'dd.MM.' }}\r\n            </td>\r\n            <td class=\"right\">\r\n              <strong>{{ (row.isPaid ? 0 : row.period.daysCount) | sxyCount : \"day\" }}</strong><br />\r\n              <strong>{{ (row.isHolidayAccrual ? 0 : row.period.daysCount) | sxyCount : \"day\" }}</strong><br />\r\n            </td>\r\n            <td class=\"middle right\">\r\n              <button class=\"btn btn-xs\" type=\"button\" ng-class=\"row.selected ? 'btn-danger' : 'btn-info'\" ng-click=\"row.selected = !row.selected\">\r\n                {{ row.selected ? (\"SALAXY.UI_Terms.unselect\" | sxyTranslate) : (\"SALAXY.UI_Terms.select\" | sxyTranslate) }}\r\n              </button>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n    <div>\r\n      <button type=\"submit\" class=\"btn btn-primary float-end\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n      <button type=\"reset\" class=\"btn btn-default float-end\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/report/modals/IrRowsEditorDialog.html\",`<div class=\"modal-calc-list\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{$ctrl.logic.title}}</h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n\r\n  </div>\r\n  <div class=\"card-body\">\r\n    <salaxy-calc-ir-rows model=\"$ctrl.current\"></salaxy-calc-ir-rows>\r\n    <div>\r\n      <button type=\"submit\" class=\"btn btn-primary float-end\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n      <button type=\"reset\" class=\"btn btn-default float-end\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/report/modals/IrScheduleSendDialog.html\",`  <div class=\"modal-header \">\r\n    <h2 sxy-text=\"SALAXY.NG1.IrScheduleSendDialogComponent.heading\"></h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$dismiss()\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <form class=\"form-horizontal\" name=\"schedulingDialog\">\r\n      <div class=\"col-12\">\r\n        <div class=\"salaxy-component salaxy-datepicker\">\r\n          <salaxy-datepicker ng-model=\"$ctrl.current.startAt\" label=\"SALAXY.NG1.IrScheduleSendDialogComponent.dateLabel\" name=\"date\" timepicker=\"true\"></salaxy-datepicker>\r\n        </div>\r\n      </div>\r\n      <div class=\"col-12\">\r\n        <salaxy-form-group label=\"SALAXY.NG1.IrScheduleSendDialogComponent.dateTimeLabel\" name=\"dateTime\">\r\n          <pre class=\"alert alert-danger d-inline-block\">{{$ctrl.current.startAt | sxyTime }}</pre>\r\n        </salaxy-form-group>\r\n      </div>\r\n      <div>\r\n        <button type=\"submit\" class=\"btn btn-primary float-end\" ng-disabled=\"schedulingDialog.$invalid\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.send\"></button>\r\n        <button type=\"reset\" class=\"btn btn-default float-end\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n      </div>\r\n    </form>\r\n  </div>\r\n  <div class=\"modal-footer\"></div>`);\n\n $templateCache.put(\"salaxy-components/report/modals/PostAccountingData.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" sxy-text=\"SALAXY.UI_Terms.send\"></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n</div>\r\n<div class=\"modal-body\" id=\"modal-body\"  style=\"max-height: calc(100vh - 300px); overflow-y: auto;\">\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table table-sm\">\r\n      <thead>\r\n        <tr>\r\n          <th><span sxy-text=\"SALAXY.NG1.AccountingReportToolsComponent.accountingData\"></span></th>\r\n          <th><span sxy-text=\"SALAXY.NG1.AccountingReportToolsComponent.status\"></span></th>\r\n          <th></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat-start=\"item in $ctrl.current\">\r\n          <td><a ng-click=\"item.rowToggle = !item.rowToggle\">{{item.accountingData.employer.displayName}}/{{item.accountingData.period.start}}</a></td>\r\n          <td>\r\n            <span ng-if=\"item.error\" class=\"text-danger\">{{item.error}}</span>\r\n            <span ng-if=\"item.result\" class=\"text-success\">{{item.result}}</span>\r\n          </td>\r\n          <td class=\"right\">\r\n            <button  class=\"btn btn-default\" ng-click=\"$ctrl.logic.postData(item)\" ng-disabled=\"item.isPosting\" type=\"button\">\r\n              <span ng-show=\"!item.isPosting\"><i class=\"bi bi-upload\"></i></span>\r\n              <span ng-show=\"item.isPosting\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span> <span sxy-text=\"SALAXY.UI_Terms.send\"></span>\r\n            </button>\r\n          </td>\r\n        </tr>\r\n        <tr ng-if=\"item.rowToggle\" ng-repeat-end>\r\n          <td colspan=\"3\">\r\n            <ng-include src=\"$ctrl.logic.previewTemplateUrl\" ></ng-include>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button type=\"button\" class=\"btn btn-default float-end\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/report/modals/SummaryReportPeriodSelection.html\",`<form name=\"periodForm\" class=\"form-horizontal\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.CumulativeReportPeriodSelection.title\"></h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <salaxy-input-enum name=\"period\" label=\"SALAXY.NG1.CumulativeReportPeriodSelection.periodLabel\" options=\"{year: ('SALAXY.NG1.CumulativeReportPeriodSelection.enumOptionYear' | sxyTranslate), month: ('SALAXY.NG1.CumulativeReportPeriodSelection.enumOptionMonth' | sxyTranslate), all: ('SALAXY.NG1.CumulativeReportPeriodSelection.enumOptionAll' | sxyTranslate), custom: ('SALAXY.NG1.CumulativeReportPeriodSelection.enumOptionCustom' | sxyTranslate)}\"\r\n      ng-model=\"$ctrl.current.periodType\" type=\"radio\" required>\r\n    </salaxy-input-enum>\r\n    <salaxy-input-enum name=\"periodDateKind\" label=\"SALAXY.NG1.CumulativeReportPeriodSelection.periodDateKindLabel\" enum=\"PeriodDateKind\"\r\n      ng-model=\"$ctrl.current.periodDateKind\" type=\"radio\" required>\r\n    </salaxy-input-enum>\r\n    <salaxy-datepicker-popup name=\"refDateMonth\" placeholder=\"SALAXY.NG1.CumulativeReportPeriodSelection.month\" ng-if=\"$ctrl.current.periodType == 'month'\" format=\"month\" ng-model=\"$ctrl.current.refDate\"\r\n      label=\"SALAXY.NG1.CumulativeReportPeriodSelection.chooseMonthLabel\" require=\"true\"></salaxy-datepicker-popup>\r\n    <salaxy-datepicker-popup name=\"refDateYear\" placeholder=\"SALAXY.NG1.CumulativeReportPeriodSelection.year\" ng-if=\"$ctrl.current.periodType == 'year'\" format=\"year\" ng-model=\"$ctrl.current.refDate\"\r\n      label=\"SALAXY.NG1.CumulativeReportPeriodSelection.chooseYearLabel\" require=\"true\"></salaxy-datepicker-popup>\r\n    <salaxy-datepicker-popup name=\"refDateCustom\" ng-if=\"$ctrl.current.periodType == 'custom'\" ng-model=\"$ctrl.current.refDate\" label=\"SALAXY.NG1.CumulativeReportPeriodSelection.refDateCustomLabel\" require=\"true\">\r\n    </salaxy-datepicker-popup>\r\n    <salaxy-datepicker-popup name=\"endDateCustom\" ng-if=\"$ctrl.current.periodType == 'custom'\" ng-model=\"$ctrl.current.endDate\" label=\"SALAXY.NG1.CumulativeReportPeriodSelection.endDateCustomLabel\">\r\n    </salaxy-datepicker-popup>\r\n  </div>\r\n  <div class=\"modal-footer\">\r\n    <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n    <button type=\"submit\" class=\"btn btn-primary\" ng-disabled=\"!periodForm.$valid\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.select\"></button>\r\n  </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/report/PayCertificate.html\",`<div class=\"salaxy-component salaxy-pay-certificate\">\r\n  <div class=\"d-block d-md-none\">\r\n    <h4><span sxy-text=\"SALAXY.NG1.PayCertificateComponent.step\"></span> {{$ctrl.currentStep.number}}/{{$ctrl.steps.length}}</h4>\r\n  </div>\r\n  <div class=\"salaxy-wizard\">\r\n    <div class=\"wizard-steps\">\r\n      <div class=\"wizard-step\" ng-repeat=\"step in $ctrl.steps\" ng-class=\"{'active': step.active, 'disabled': step.disabled}\">\r\n        <span class=\"salaxy-avatar\">\r\n          <div class=\"wizard-icons-wrapper\">\r\n            <i class=\"bi\" ng-class=\"step.active ? 'bi-circle-fill' : 'bi-circle'\"></i>\r\n            <i class=\"bi bi-circle-fill\"></i>\r\n          </div>\r\n          <strong class=\"number\">{{ step.number }}</strong>\r\n        </span>\r\n        <span class=\"step-text\">{{ step.title | sxyTranslate }}</span>\r\n      </div>\r\n    </div>\r\n    <div class=\"wizard-strikethrough\"></div>\r\n  </div>\r\n  <div class=\"wizard-content\" style=\"height: 600px; overflow-y: auto;\">\r\n    <ng-include src=\"$ctrl.currentStep.view\"></ng-include>\r\n  </div>\r\n  <div class=\"modal-footer\">\r\n    <button ng-if=\"$ctrl.step >= 2\" ng-click=\"$ctrl.goPrevious()\" ng-disabled=\"!$ctrl.canGoPrevious\" class=\"btn btn-default\" sxy-text=\"SALAXY.UI_Terms.previous\"></button>\r\n    <button ng-if=\"($ctrl.step < $ctrl.steps.length)\" ng-click=\"$ctrl.goNext()\" ng-disabled=\"!$ctrl.canGoNext\" class=\"btn btn-primary ms-auto\" sxy-text=\"SALAXY.UI_Terms.next\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/report/PayCertificateStep1.html\",`<div>\r\n  <salaxy-employment-list mode=\"select\" selected-items=\"$ctrl.selectedWorkers\" on-list-select=\"$ctrl.selectWorker(item, value)\"></salaxy-employment-list>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/report/PayCertificateStep2.html\",`<div>\r\n  <div class=\"btn-toolbar mb-2\" role=\"toolbar\">\r\n    <div class=\"btn-group\" role=\"group\">\r\n      <button type=\"button\" class=\"btn btn-sm btn-primary\" ng-click=\"$ctrl.selectCalculations($odata.items, 26)\" sxy-text=\"SALAXY.NG1.PayCertificateComponent.choose26Weeks\"></button>\r\n      <button type=\"button\" class=\"btn btn-sm btn-primary\" ng-click=\"$ctrl.selectCalculations($odata.items, 34)\" sxy-text=\"SALAXY.NG1.PayCertificateComponent.choose34Weeks\"></button>\r\n      <button type=\"button\" class=\"btn btn-sm btn-default\" ng-click=\"$ctrl.unselectCalculations()\" sxy-text=\"SALAXY.NG1.PayCertificateComponent.clear\"></button>\r\n    </div>\r\n  </div>\r\n  <salaxy-odata-table ng-ref=\"$odata\" selected-items=\"$ctrl.periodCalculations\" url=\"/v03/api/calculations/category/readonly\"\r\n    template-url=\"salaxy-components/odata/lists/CalculationsWithSalaryDate-select.html\" crud-controller=\"CalculationCrudController as $crud\"\r\n    options=\"{$orderby: 'salaryDate desc', $filter: 'otherId eq \\\\'' + $ctrl.worker.otherId + '\\\\' and ( status eq \\\\'paymentSucceeded\\\\' )' }\">\r\n  </salaxy-odata-table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/report/PayCertificateStep3.html\",`\r\n<salaxy-spinner ng-show=\"!$ctrl.validation\" heading=\"SALAXY.NG1.PayCertificateComponent.creatingPayCertificate\"></salaxy-spinner>\r\n<salaxy-validation-summary api-validation=\"$ctrl.validation\" template-url=\"pay-certificate-validation.html\">\r\n  <p class=\"text-center\">\r\n    <b sxy-text=\"SALAXY.NG1.PayCertificateComponent.payCertificateReadyForDownload\"></b>\r\n  </p>\r\n</salaxy-validation-summary>\r\n\r\n<p>&nbsp;</p>\r\n<p class=\"text-center\" ng-show=\"$ctrl.validation && $ctrl.worker && $ctrl.periodCalculations.length > 0\">{{'SALAXY.NG1.PayCertificateComponent.open' | sxyTranslate}} <a ng-href=\"{{$ctrl.getDownloadPdfUrl(true)}}\" target=\"_blank>\">{{'SALAXY.NG1.PayCertificateComponent.payCertificate' | sxyTranslate}}</a>. </p>\r\n\r\n\r\n<button class=\"btn btn-default float-end\" ng-click=\"$ctrl.startNew()\" sxy-text=\"SALAXY.NG1.PayCertificateComponent.createNewPayCertificate\"></button>\r\n\r\n\r\n\r\n<script type=\"text/ng-template\" id=\"pay-certificate-validation.html\">\r\n<div ng-if=\"!$ctrl.hasValidation\" ng-bind-html=\"$ctrl.loadingHtml\"></div>\r\n<div ng-if=\"$ctrl.hasValidation\">\r\n  <ng-transclude ng-if=\"$ctrl.isValid\"></ng-transclude>\r\n  <div ng-if=\"!$ctrl.isValid\" class=\"alert alert-danger\">\r\n      <h4 sxy-text=\"SALAXY.NG1.PayCertificateComponent.alertHeading\" ps=\":\"></h4>\r\n      <p style=\"display: block; font-family: monospace; white-space: pre;\" ng-repeat=\"error in $ctrl.getErrors()\">{{ error.msg }}</p>\r\n  </div>\r\n</div>\r\n</script>`);\n\n $templateCache.put(\"salaxy-components/report/PayStatsReportQuery.html\",`<style>\r\n  .tabulator-row {\r\n    border-bottom: 1px solid #ddd;\r\n  }\r\n  .tabulator-row.nested-odd {\r\n    background-color: #fff !important;\r\n  }\r\n  .tabulator-row.nested-even {\r\n    background-color: #efefef !important;\r\n  }\r\n  .tabulator-row.tabulator-tree-level-1 {\r\n    font-weight: bold;\r\n  }\r\n</style>\r\n<div class=\"salaxy-component salaxy-pay-stats-report-query\">\r\n  <div class=\"row\">\r\n    <div class=\"col-sm-6\">\r\n      <div ng-if=\"$ctrl.employmentId\" class=\"salaxy-calc-worker-info\" ng-controller=\"EmploymentCrudController as $employmentCtrl\"\r\n        ng-init=\"$employmentCtrl.model=$ctrl.employmentId\">\r\n        <div class=\"row spacer-bottom\" ng-if=\"$employmentCtrl.current\">\r\n          <div class=\"col-xs-3 col-sm-2 col-xxs-3\">\r\n            <salaxy-avatar avatar=\"$employmentCtrl.current.personalInfo.avatar\"></salaxy-avatar>\r\n          </div>\r\n          <div class=\"col-xs-9 col-sm-10 col-xxs-9 worker-info-col\">\r\n            <h2>{{ $employmentCtrl.current.personalInfo.avatar.displayName || (\"SALAXY.NG1.WorkerInfo.noSelection\" | sxyTranslate) }}</h2>\r\n            <div class=\"row\" ng-if=\"$employmentCtrl.current\">\r\n              <div class=\"col-xs-12 col-sm-6 \">\r\n                <div ng-class=\"$employmentCtrl.current.personalInfo.officialId ? '' : 'text-danger'\">\r\n                  {{ $employmentCtrl.current.personalInfo.officialId || ( \"SALAXY.NG1.PaymentDialogComponent.noSSNumber\" | sxyTranslate ) }}\r\n                  &nbsp;\r\n                  <div class=\"btn-group\" ng-if=\"$employmentCtrl.otherEmployments.length > 0\">\r\n                    <button id=\"single-button\" type=\"button\" class=\"btn btn-default btn-xs dropdown-toggle\" data-bs-toggle=\"dropdown\" aria-expanded=\"false\">\r\n                      {{ $employmentCtrl.otherEmployments.length }} muuta työsuhdetta\r\n                    </button>\r\n                    <ul class=\"dropdown-menu\" aria-labelledby=\"single-button\">\r\n                      <li ng-repeat=\"item in $employmentCtrl.otherEmployments\">\r\n                        <a class=\"dropdown-item\" ng-href=\"{{$employmentCtrl.isModal ? '' : ('#/employments/details/' + item.id)}}\">\r\n                          {{ $employmentCtrl.getEmploymentDescription(item) }}\r\n                          ({{ $employmentCtrl.getActiveText(item) }})\r\n                        </a>\r\n                      </li>\r\n                    </ul>\r\n                  </div>\r\n                  <span ng-if=\"!$employmentCtrl.otherEmployments\">Tarkistetaan muita työsuhteita...</span>\r\n                </div>\r\n                <div>{{ $employmentCtrl.getEmploymentDescription($employmentCtrl.current) }}</div>\r\n                <div>{{ $employmentCtrl.getActiveText($employmentCtrl.current) }}</div>\r\n                <div><small>{{ $employmentCtrl.current.id }}</small></div>\r\n              </div>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"col-sm-6\">\r\n      <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.query()\" ng-disabled=\"$ctrl.isQuerying\">\r\n      <span ng-if=\"$ctrl.isQuerying\"><i class=\"bi bi-arrow-repeat bi-spin me-1\"></i></span>\r\n      <span sxy-text=\"Laske ansiot\"></span>\r\n    </button>\r\n    </div>\r\n  </div>\r\n  <sxy-table class=\"report\" ng-if=\"$ctrl.reportData\" ng-ref=\"$ctrl.$sxyTable\" options=\"$ctrl.reportOptions\" include=\"$ctrl.reportInclude\" data=\"$ctrl.reportData\"></sxy-table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/report/ReportList.html\",`<div class=\"salaxy-component salaxy-report-list\">\r\n  <div ng-hide=\"$ctrl.getReports($ctrl.reportType).length > 0\">\r\n    <p sxy-text=\"SALAXY.NG1.ReportListComponent.noReportsToShow\" ps=\".\"></p>\r\n  </div>\r\n  <div class=\"table-responsive\" ng-show=\"$ctrl.getReports($ctrl.reportType).length > 0\">\r\n    <table class=\"table\">\r\n      <thead>\r\n        <tr>\r\n          <th style=\"width: 100px\"></th>\r\n          <th sxy-text=\"SALAXY.NG1.ReportListComponent.report\"></th>\r\n          <th sxy-text=\"SALAXY.NG1.ReportListComponent.links\"></th>\r\n          <th sxy-text=\"SALAXY.NG1.ReportListComponent.reportDate\"></th>\r\n          <th sxy-text=\"SALAXY.NG1.ReportListComponent.updated\"></th>\r\n          <th sxy-text=\"SALAXY.NG1.ReportListComponent.note\" ps=\".\"></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody ng-if=\"$ctrl.reportType !== 'monthlyDetails' && $ctrl.reportType !== 'yearlyDetails' && $ctrl.reportType !== 'monthlyLiikekirjuri'\" ng-controller=\"WorkerSummaryReportDisplayController as $displayCtrl\">\r\n        <tr ng-repeat=\"report in $ctrl.getReports($ctrl.reportType)\">\r\n          <td>\r\n            <a ng-if=\"!report.isPreview\" href=\"{{ report.pdfUrl || report.htmlUrl || report.jsonUrl }}\" target=\"_blank\">\r\n              <img ng-src=\"{{ report.thumbnail }}\" class=\"img-responsive img-thumbnail\" />\r\n            </a>\r\n            <a ng-if=\"report.isPreview\" ng-click=\"$displayCtrl.display(report.reportDate, $displayCtrl.parseWorkerID(report.htmlUrl), null)\">\r\n              <img ng-src=\"{{ report.thumbnail }}\" class=\"img-responsive img-thumbnail\" />\r\n            </a>\r\n          </td>\r\n          <td>\r\n            <a ng-if=\"!report.isPreview\" href=\"{{ report.pdfUrl || report.htmlUrl || report.jsonUrl }}\" target=\"_blank\">{{ report.title }}</a>\r\n            <a ng-if=\"report.isPreview\" ng-click=\"$displayCtrl.display(report.reportDate, $displayCtrl.parseWorkerID(report.htmlUrl), null)\">{{ report.title }} </a>\r\n          </td>\r\n          <td>\r\n            <a ng-if=\"!report.isPreview && report.pdfUrl\" href=\"{{ report.pdfUrl }}\" target=\"_blank\">PDF</a>\r\n            <a ng-if=\"report.isPreview\" ng-click=\"$displayCtrl.display(report.reportDate, $displayCtrl.parseWorkerID(report.htmlUrl), null)\">HTML</a>\r\n            <a ng-if=\"!report.isPreview && report.jsonUrl\" href=\"{{ report.jsonUrl }}\" target=\"_blank\">JSON</a>\r\n          </td>\r\n          <td>{{ report.reportDate | date }}</td>\r\n          <td>{{ report.updatedAt | date }}</td>\r\n          <td>\r\n            <span class=\"label label-info\" ng-if=\"report.isPreview\" sxy-text=\"SALAXY.NG1.ReportListComponent.preview\"></span>\r\n            <span class=\"label label-danger\" ng-if=\"report.isDemoData\">DEMO: demodataa</span>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n      <tbody ng-if=\"$ctrl.reportType === 'monthlyDetails' || $ctrl.reportType === 'yearlyDetails'\" ng-controller=\"SummaryReportDisplayController as $displayCtrl\">\r\n        <tr ng-repeat=\"report in $ctrl.getReports($ctrl.reportType)\">\r\n          <td>\r\n            <a ng-if=\"!report.isPreview\" href=\"{{ report.pdfUrl || report.htmlUrl || report.jsonUrl }}\" target=\"_blank\">\r\n              <img ng-src=\"{{ report.thumbnail }}\" class=\"img-responsive img-thumbnail\" />\r\n            </a>\r\n            <a ng-if=\"report.isPreview\" ng-click=\"$displayCtrl.display(report.reportDate,report.type)\">\r\n              <img ng-src=\"{{ report.thumbnail }}\" class=\"img-responsive img-thumbnail\" />\r\n            </a>\r\n          </td>\r\n          <td>\r\n            <a ng-if=\"!report.isPreview\" href=\"{{ report.pdfUrl || report.htmlUrl || report.jsonUrl }}\" target=\"_blank\">{{ report.title }}</a>\r\n            <a ng-if=\"report.isPreview\" ng-click=\"$displayCtrl.display(report.reportDate,report.type)\">{{ report.title }} </a>\r\n          </td>\r\n          <td>\r\n            <a ng-if=\"!report.isPreview && report.pdfUrl\" href=\"{{ report.pdfUrl }}\" target=\"_blank\">PDF</a>\r\n            <a ng-if=\"report.isPreview\" ng-click=\"$displayCtrl.display(report.reportDate,report.type)\">HTML</a>\r\n            <a ng-if=\"!report.isPreview && report.jsonUrl\" href=\"{{ report.jsonUrl }}\" target=\"_blank\">JSON</a>\r\n          </td>\r\n          <td>{{ report.reportDate | date }}</td>\r\n          <td>{{ report.updatedAt | date }}</td>\r\n          <td>\r\n            <span class=\"label label-info\" ng-if=\"report.isPreview\" sxy-text=\"SALAXY.NG1.ReportListComponent.preview\"></span>\r\n            <span class=\"label label-danger\" ng-if=\"report.isDemoData\">DEMO: demodataa</span>\r\n          </td>\r\n        </tr>\r\n      \r\n      </tbody>\r\n      <tbody ng-if=\"$ctrl.reportType === 'monthlyLiikekirjuri'\" ng-controller=\"AccountingReportDisplayController as $displayCtrl\">\r\n        <tr ng-repeat=\"report in $ctrl.getReports($ctrl.reportType)\">\r\n          <td>\r\n            <a ng-if=\"!report.isPreview\" href=\"{{ report.pdfUrl || report.htmlUrl || report.jsonUrl }}\" target=\"_blank\">\r\n              <img ng-src=\"{{ report.thumbnail }}\" class=\"img-responsive img-thumbnail\" />\r\n            </a>\r\n            <a ng-if=\"report.isPreview\" ng-click=\"$displayCtrl.display(report.reportDate,report.type, report)\">\r\n              <img ng-src=\"{{ report.thumbnail }}\" class=\"img-responsive img-thumbnail\" />\r\n            </a>\r\n          </td>\r\n          <td>\r\n            <a ng-if=\"!report.isPreview\" href=\"{{ report.pdfUrl || report.htmlUrl || report.jsonUrl }}\" target=\"_blank\">{{ report.title }}</a>\r\n            <a ng-if=\"report.isPreview\" ng-click=\"$displayCtrl.display(report.reportDate,report.type)\">{{ report.title }} </a>\r\n          </td>\r\n          <td>\r\n            <a ng-if=\"!report.isPreview && report.pdfUrl\" href=\"{{ report.pdfUrl }}\" target=\"_blank\">PDF</a>\r\n            <a ng-if=\"report.isPreview\" ng-click=\"$displayCtrl.display(report.reportDate)\">HTML</a>\r\n            <a ng-if=\"!report.isPreview && report.jsonUrl\" href=\"{{ report.jsonUrl }}\" target=\"_blank\">JSON</a>\r\n          </td>\r\n          <td>{{ report.reportDate | date }}</td>\r\n          <td>{{ report.updatedAt | date }}</td>\r\n          <td>\r\n            <span class=\"label label-info\" ng-if=\"report.isPreview\" sxy-text=\"SALAXY.NG1.ReportListComponent.preview\"></span>\r\n            <span class=\"label label-danger\" ng-if=\"report.isDemoData\">DEMO: demodataa</span>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/report/SalaryReportList.html\",`<div class=\"salaxy-component salaxy-salary-report-list\">\r\n  <salaxy-odata-table ng-if=\"$ctrl.mode != 'panel'\" crud-controller=\"SalaryReportCrudController as $crud\" template-url=\"salaxy-components/odata/lists/SalaryReports.html\" options=\"$ctrl.queryOptions\">\r\n  </salaxy-odata-table>\r\n  <salaxy-odata-table ng-if=\"$ctrl.mode == 'panel'\" crud-controller=\"SalaryReportCrudController as $crud\" template-url=\"salaxy-components/odata/lists/SalaryReportsPanel.html\" options=\"$ctrl.panelQueryOptions\">\r\n  </salaxy-odata-table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/report/SummaryReport.html\",`<div class=\"salaxy-component salaxy-summary-report\">\r\n  <div class=\"btn-toolbar\" role=\"toolbar\" aria-label=\"Report options\">\r\n\r\n    <div class=\"btn-group btn-group-sm dropdown\">\r\n      <button id=\"single-button2\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\" ng-disabled=\"disabled\">\r\n        <span sxy-text=\"SALAXY.NG1.CalcReportsComponent.reportLanguage\" ps=\":\"></span> {{$ctrl.languageText | sxyTranslate}}\r\n      </button>\r\n      <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"single-button2\">\r\n        <li ng-if=\"$ctrl.reportType === 'salarySlip'\" role=\"menuitem\">\r\n          <a href=\"\" ng-click=\"$ctrl.reportLang = 'default'\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.CalcReportsComponent.reportLanguageWorker\"></a>\r\n        </li>\r\n        <li ng-if=\"$ctrl.reportType !== 'salarySlip'\" role=\"menuitem\">\r\n          <a href=\"\" ng-click=\"$ctrl.reportLang = 'default'\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.CalcReportsComponent.reportLanguageCompany\"></a>\r\n        </li>\r\n        <li role=\"menuitem\">\r\n          <a href=\"\" ng-click=\"$ctrl.reportLang = 'fi'\" class=\"dropdown-item\" sxy-text=\"SALAXY.ENUM.Language.fi.label\"></a>\r\n        </li>\r\n        <li role=\"menuitem\">\r\n          <a href=\"\" ng-click=\"$ctrl.reportLang = 'en'\" class=\"dropdown-item\" sxy-text=\"SALAXY.ENUM.Language.en.label\"></a>\r\n        </li>\r\n        <li role=\"menuitem\">\r\n          <a href=\"\" ng-click=\"$ctrl.reportLang = 'sv'\" class=\"dropdown-item\" sxy-text=\"SALAXY.ENUM.Language.sv.label\"></a>\r\n        </li>\r\n      </ul>\r\n    </div>\r\n    <div class=\"btn-group btn-group-sm ms-sm-auto\" role=\"group\" aria-label=\"Pdf\">\r\n      <button sxy-if-role=\"!anon\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showDownloadDialog(true)\">\r\n        <span class=\"d-none d-md-inline-block\" sxy-text=\"SALAXY.UI_Terms.print\"></span>\r\n        <i class=\"bi bi-printer\" aria-hidden=\"true\"></i>\r\n      </button>\r\n      <button sxy-if-role=\"!anon\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showDownloadDialog(false)\">\r\n        <span class=\"d-none d-md-inline-block\" sxy-text=\"SALAXY.UI_Terms.downloadPdf\"></span>\r\n        <i class=\"bi bi-file-earmark-pdf\" aria-hidden=\"true\"></i>\r\n      </button>\r\n    </div>\r\n  </div>\r\n  <div class=\"\" ng-class=\"{'report-table-html': $ctrl.applySiteStyles}\">\r\n    <div ng-bind-html=\"$ctrl.html\" class=\"report-binder table-responsive\"></div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/report/SummaryReportQuery.html\",`<div class=\"salaxy-component salaxy-summary-report-query\">\r\n  <div class=\"btn-toolbar\" role=\"toolbar\">\r\n      <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.showPeriodSelection()\" sxy-text=\"SALAXY.NG1.CumulativeReportComponent.selectPeriod\" ps=\"...\"></button>\r\n      <button type=\"button\" class=\"btn btn-secondary\" ng-click=\"$ctrl.exportToExcel()\">\r\n        <span class=\"hidden-sm hidden-xs\" sxy-text=\"SALAXY.NG1.HolidayReportComponent.exportToExcel\"></span>\r\n        <i class=\"bi bi-file-earmark-pdf\" aria-hidden=\"true\"></i>\r\n      </button>\r\n  </div>\r\n  <p> {{ $ctrl.getQueryInfoText()}}</p>\r\n  <salaxy-tab-buttons\r\n    current-tab=\"$ctrl.currentTab\"\r\n    options=\"[\r\n      { value: 'incomereport', text: 'SALAXY.NG1.HolidayReportComponent.irIncomeTypeReport' },\r\n      { value: 'salarypaymentreport', text: 'SALAXY.NG1.HolidayReportComponent.salaryPaymentReport' },\r\n      { value: 'totalsreport', text: 'SALAXY.ENUM.ReportType.totalsReport.label', hidden: !('test' | sxyIsInRole) },\r\n      { value: 'irrowsreport', text: 'SALAXY.NG1.CalcReportsComponent.irRows', hidden: !('test' | sxyIsInRole) },\r\n      { value: 'rowsreport', text: 'SALAXY.NG1.CalcReportsComponent.rowsReport', hidden: !('test' | sxyIsInRole) },\r\n      { value: 'unionpaymentreport', text: 'SALAXY.NG1.CalcReportsComponent.unionPaymentReport' },\r\n      { value: 'costcenterreport', text: 'SALAXY.NG1.CalcReportsComponent.costCenterReport', hidden: !('test' | sxyIsInRole) }\r\n    ]\"\r\n    tabs-id=\"summaryReportQuery\">\r\n  </salaxy-tab-buttons>\r\n  <div class=\"tab-content\" id=\"tab-content-summaryReportQuery\">\r\n    <div class=\"tab-pane\" id=\"incomereport-tab\">\r\n      <div ng-if=\"$ctrl.currentTab == 'incomereport' && $ctrl.irReportRows.length > 0 && $ctrl.irReportRows[0].rows.length > 0\">\r\n        <table class=\"table table-striped\">\r\n          <thead>\r\n            <tr>\r\n              <th colspan=\"2\"><span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span></th>\r\n              <th ng-repeat=\"row in $ctrl.irReportRows[0].rows\" class=\"right\">{{row.label}}</th>             \r\n            </tr>\r\n          </thead>\r\n          <tbody>\r\n            <tr ng-repeat=\"row in $ctrl.irReportRows\">\r\n              <td class=\"align-middle td-avatar\">\r\n                <salaxy-avatar class=\"clickable\" ng-click=\"$ctrl.showEditEmploymentDialog(row)\" avatar=\"row.workerAvatar\"></salaxy-avatar>\r\n              </td>\r\n              <td>{{row.workerAvatar.displayName}}</td>\r\n              <td ng-repeat=\"r in row.rows\" class=\"right\">{{ r.isCount ?  r.total  : (r.total| currency) || \"&nbsp;\"}}</td>\r\n            </tr>\r\n          </tbody>\r\n        </table>\r\n      </div>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"salarypaymentreport-tab\">\r\n      <div ng-if=\"$ctrl.currentTab == 'salarypaymentreport' && $ctrl.resultRows.length > 0 && ($ctrl.entrepreneurSummaryReportResults.length > 0 || $ctrl.workerSummaryReportResults.length > 0)\">\r\n        <table class=\"table table-striped\">\r\n          <thead>\r\n            <tr>\r\n              <th></th>             \r\n              <th></th>             \r\n              <th class=\"right\">{{ \"SALAXY.REPORTS.summary.table.totalGrossSalary\" | sxyTranslate}}</th>\r\n              <th class=\"right\">{{ \"SALAXY.REPORTS.summary.table.totalRowCategory\" | sxyTranslate}}</th>\r\n              <th class=\"right\">{{ \"SALAXY.REPORTS.summary.table.benefits\" | sxyTranslate}}</th>\r\n              <th class=\"right\">{{ \"SALAXY.REPORTS.summary.table.irCode\" | sxyTranslate}}</th>\r\n              <th class=\"right\">{{ \"SALAXY.REPORTS.summary.table.totalTaxable\" | sxyTranslate}}</th>\r\n              <th class=\"right\">{{ \"SALAXY.REPORTS.summary.table.tax\" | sxyTranslate}}</th>\r\n              <th class=\"right\">{{ \"SALAXY.REPORTS.summary.table.pension\" | sxyTranslate}}</th>\r\n              <th class=\"right\">{{ \"SALAXY.REPORTS.summary.table.unemploymentInsurance\" | sxyTranslate}}</th>\r\n              <th class=\"right\">{{ \"SALAXY.REPORTS.summary.table.unionPayment\" | sxyTranslate}}</th>\r\n              <th class=\"right\">{{ \"SALAXY.REPORTS.summary.table.foreclosure\" | sxyTranslate}}</th>\r\n              <th class=\"right\">{{ \"SALAXY.REPORTS.summary.table.otherDeductions\" | sxyTranslate}}</th>\r\n              <th class=\"right\">{{ \"SALAXY.REPORTS.summary.table.totalExpenses\" | sxyTranslate}}</th>\r\n              <th class=\"right\" style=\"border-right: 1px solid #000\">{{ \"SALAXY.REPORTS.summary.table.totalWorkerPayment\" | sxyTranslate}}</th>\r\n              <th class=\"right\">{{ \"SALAXY.REPORTS.summary.table.totalPayment\" | sxyTranslate}}</th>\r\n              <th class=\"right\">{{ \"SALAXY.REPORTS.summary.table.palkkaus\" | sxyTranslate}}</th>\r\n              <th class=\"right\">{{ \"SALAXY.REPORTS.summary.table.service\" | sxyTranslate}}</th>\r\n              <th class=\"right\">{{ \"SALAXY.REPORTS.summary.table.socialSecurity\" | sxyTranslate}}</th>\r\n              <th class=\"right\">{{ \"SALAXY.REPORTS.summary.table.totalPensions\" | sxyTranslate}}</th>\r\n              <th class=\"right\">{{ \"SALAXY.REPORTS.summary.table.employerPension\" | sxyTranslate}}</th>\r\n              <th class=\"right\">{{ \"SALAXY.REPORTS.summary.table.unemployment\" | sxyTranslate}}</th>\r\n              <th class=\"right\">{{ \"SALAXY.REPORTS.summary.table.employerUnemployment\" | sxyTranslate}}</th>\r\n            </tr>\r\n          </thead>\r\n          <tbody ng-if=\"$ctrl.entrepreneurSummaryReportResults.length > 0\">\r\n            <tr >\r\n              <td colspan=\"15\" style=\"border-right: 1px solid #000\"><strong>{{\"SALAXY.REPORTS.summary.table.entrepreneurSalary\" | sxyTranslate}}</strong></td>\r\n              <td colspan=\"8\"></td>\r\n            </tr>\r\n            <tr ng-repeat=\"row in $ctrl.entrepreneurSummaryReportResults\">\r\n              <td class=\"align-middle td-avatar\">\r\n                <salaxy-avatar class=\"clickable\" ng-click=\"$ctrl.showEditEmploymentDialog(row)\" avatar=\"row.avatar\"></salaxy-avatar>\r\n              </td>     \r\n              <td>{{row.avatar.displayName}}</td>\r\n              <td class=\"right\">{{(row.totalGrossSalary | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.totalRowCategory | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.benefits | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.irCode | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.totalTaxable | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.tax | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.pension | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.unemploymentInsurance | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.unionPayment | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.foreclosure | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.otherDeductions | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.totalExpenses | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\" style=\"border-right: 1px solid #000\">{{(row.totalWorkerPayment | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.totalPayment | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.palkkaus | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.service | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.socialSecurity | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.totalPensions | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.employerPension | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.unemployment | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.employerUnemployment | currency) || \"&nbsp;\"}}</td>\r\n            </tr>\r\n          </tbody>\r\n          <tbody ng-if=\"$ctrl.workerSummaryReportResults.length > 0\">\r\n            <tr>\r\n              <td colspan=\"15\" style=\"border-right: 1px solid #000\"><strong>{{\"SALAXY.REPORTS.summary.table.workerSalary\" | sxyTranslate}}</strong></td>\r\n              <td colspan=\"8\"></td>\r\n            </tr>\r\n            <tr ng-repeat=\"row in $ctrl.workerSummaryReportResults\">\r\n              <td class=\"align-middle td-avatar\">\r\n                <salaxy-avatar class=\"clickable\" ng-click=\"$ctrl.showEditEmploymentDialog(row)\" avatar=\"row.avatar\"></salaxy-avatar>\r\n              </td>     \r\n              <td>{{row.avatar.displayName}}</td>\r\n              <td class=\"right\">{{(row.totalGrossSalary | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.totalRowCategory | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.benefits | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.irCode | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.totalTaxable | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.tax | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.pension | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.unemploymentInsurance | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.unionPayment | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.foreclosure | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.otherDeductions | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.totalExpenses | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\" style=\"border-right: 1px solid #000\">{{(row.totalWorkerPayment | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.totalPayment | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.palkkaus | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.service | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.socialSecurity | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.totalPensions | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.employerPension | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.unemployment | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.employerUnemployment | currency) || \"&nbsp;\"}}</td>\r\n            </tr>\r\n          </tbody>\r\n          <tbody ng-if=\"$ctrl.totalSummaryReportResults.length > 0\">           \r\n            <tr ng-repeat=\"row in $ctrl.totalSummaryReportResults\">\r\n              <td class=\"right\"><strong>{{\"SALAXY.REPORTS.summary.table.total\" | sxyTranslate }}:</strong></td>\r\n              <td></td>\r\n              <td class=\"right\">{{(row.totalGrossSalary | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.totalRowCategory | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.benefits | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.irCode | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.totalTaxable | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.tax | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.pension | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.unemploymentInsurance | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.unionPayment | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.foreclosure | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.otherDeductions | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.totalExpenses | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\" style=\"border-right: 1px solid #000\">{{(row.totalWorkerPayment | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.totalPayment | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.palkkaus | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.service | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.socialSecurity | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.totalPensions | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.employerPension | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.unemployment | currency) || \"&nbsp;\"}}</td>\r\n              <td class=\"right\">{{(row.employerUnemployment | currency) || \"&nbsp;\"}}</td>\r\n            </tr>\r\n          </tbody>\r\n        </table>\r\n        <small>\r\n          <small>\r\n            <div>\r\n              <span>{{\"SALAXY.REPORTS.summary.infoText.tt\" | sxyTranslate}}</span><br />\r\n              <span>{{\"SALAXY.REPORTS.summary.infoText.ta\" | sxyTranslate}}</span><br />\r\n              <span>{{\"SALAXY.REPORTS.summary.infoText.lo\" | sxyTranslate}}</span><br />\r\n            </div>\r\n          </small>\r\n        </small>\r\n      </div>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"totalsreport-tab\" ng-if=\"'test' | sxyIsInRole\">\r\n      <div class=\"report\">\r\n        <salaxy-calc-report ng-ref=\"$ctrl.$calcReports\" lang=\"$ctrl.reportLang\" calc=\"$ctrl.summaryReportData.calculations\"\r\n          apply-site-styles=\"$ctrl.view == 'partial'\" report-type=\"'totalsReport'\" preview=\"false\" template-name=\"'totalsTables'\">\r\n        </salaxy-calc-report>\r\n      </div>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"irrowsreport-tab\" ng-if=\"'test' | sxyIsInRole\">\r\n      <div class=\"report\" ng-if=\"$ctrl.currentTab == 'irrowsreport' && $ctrl.resultRows.length > 0\">\r\n        <salaxy-calcs-ir-rows ng-ref=\"$ctrl.$calcsIrRows\" calcs=\"$ctrl.summaryReportData.calculations\" lang=\"$ctrl.reportLang\"></salaxy-calcs-ir-rows>\r\n      </div>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"rowsreport-tab\" ng-if=\"'test' | sxyIsInRole\">\r\n      <div class=\"report\" ng-init=\"$reportsCtrl.calcs = $ctrl.summaryReportData.calculations; $reportsCtrl.reportType = 'rowsReport';\" ng-controller=\"CalcReportsController as $reportsCtrl\" ng-if=\"$ctrl.currentTab == 'rowsreport' && $ctrl.resultRows.length > 0\">\r\n        <sxy-table ng-ref=\"$reportsCtrl.$sxyTable\" options=\"$reportsCtrl.reportTableConfig.options\" include=\"$reportsCtrl.reportTableConfig.include\" data=\"$reportsCtrl.reportTableConfig.data\"></sxy-table>\r\n      </div>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"unionpaymentreport-tab\">\r\n      <sxy-table class=\"report\" ng-if=\"$ctrl.currentTab == 'unionpaymentreport' && $ctrl.reportConfig.unionPaymentTableConfig.data\" ng-ref=\"$ctrl.$sxyTable\" options=\"$ctrl.reportConfig.unionPaymentTableConfig.options\" include=\"$ctrl.reportConfig.unionPaymentTableConfig.include\" data=\"$ctrl.reportConfig.unionPaymentTableConfig.data\"></sxy-table>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"costcenterreport-tab\" ng-if=\"'test' | sxyIsInRole\">\r\n      <sxy-table class=\"report\" ng-if=\"$ctrl.currentTab == 'costcenterreport' && $ctrl.reportConfig.costCenterReportTableConfig.data\" ng-ref=\"$ctrl.$sxyTable\" options=\"$ctrl.reportConfig.costCenterReportTableConfig.options\" include=\"$ctrl.reportConfig.costCenterReportTableConfig.include\" data=\"$ctrl.reportConfig.costCenterReportTableConfig.data\"></sxy-table>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/report/WorkerSummaryReport.html\",`<div class=\"salaxy-component salaxy-summary-report\">\r\n  <div class=\"btn-toolbar\" role=\"toolbar\" aria-label=\"Report options\">\r\n\r\n    <div class=\"btn-group btn-group-sm dropdown\">\r\n      <button id=\"single-button2\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\" ng-disabled=\"disabled\">\r\n        <span sxy-text=\"SALAXY.NG1.CalcReportsComponent.reportLanguage\" ps=\":\"></span> {{$ctrl.languageText | sxyTranslate}}\r\n      </button>\r\n      <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"single-button2\">\r\n        <li ng-if=\"$ctrl.reportType === 'salarySlip'\" role=\"menuitem\">\r\n          <a href=\"\" ng-click=\"$ctrl.reportLang = 'default'\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.CalcReportsComponent.reportLanguageWorker\"></a>\r\n        </li>\r\n        <li ng-if=\"$ctrl.reportType !== 'salarySlip'\" role=\"menuitem\">\r\n          <a href=\"\" ng-click=\"$ctrl.reportLang = 'default'\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.CalcReportsComponent.reportLanguageCompany\"></a>\r\n        </li>\r\n        <li role=\"menuitem\">\r\n          <a href=\"\" ng-click=\"$ctrl.reportLang = 'fi'\" class=\"dropdown-item\" sxy-text=\"SALAXY.ENUM.Language.fi.label\"></a>\r\n        </li>\r\n        <li role=\"menuitem\">\r\n          <a href=\"\" ng-click=\"$ctrl.reportLang = 'en'\" class=\"dropdown-item\" sxy-text=\"SALAXY.ENUM.Language.en.label\"></a>\r\n        </li>\r\n        <li role=\"menuitem\">\r\n          <a href=\"\" ng-click=\"$ctrl.reportLang = 'sv'\" class=\"dropdown-item\" sxy-text=\"SALAXY.ENUM.Language.sv.label\"></a>\r\n        </li>\r\n      </ul>\r\n    </div>\r\n    <div class=\"btn-group btn-group-sm ms-sm-auto\" role=\"group\" aria-label=\"Pdf\">\r\n      <button sxy-if-role=\"!anon\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showDownloadDialog(true)\">\r\n        <span class=\"d-none d-md-inline-block\" sxy-text=\"SALAXY.UI_Terms.print\"></span>\r\n        <i class=\"bi bi-printer\" aria-hidden=\"true\"></i>\r\n      </button>\r\n      <button sxy-if-role=\"!anon\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showDownloadDialog(false)\">\r\n        <span class=\"d-none d-md-inline-block\" sxy-text=\"SALAXY.UI_Terms.downloadPdf\"></span>\r\n        <i class=\"bi bi-file-earmark-pdf\" aria-hidden=\"true\"></i>\r\n      </button>\r\n    </div>\r\n  </div>\r\n  <div class=\"\" ng-class=\"{'report-table-html': $ctrl.applySiteStyles}\">\r\n    <div ng-bind-html=\"$ctrl.html\" class=\"report-binder table-responsive\"></div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/settings/Accountant.html\",`<div class=\"content settings\">\r\n  <div class=\"card card-secondary accountant\" ng-if=\"$ctrl.accountant\">\r\n    <div class=\"card-header d-flex\">\r\n      <div class=\"flex-grow-1\">\r\n        <h2><span sxy-text=\"SALAXY.NG1.AccountantComponent.title\"></span>\r\n        </h2>\r\n        <p>\r\n          <small sxy-text=\"SALAXY.NG1.AccountantComponent.intro2\"></small>\r\n        </p>\r\n      </div>\r\n      <i class=\"bi bi-check-circle-fill text-success status-icon fs-1 d-block\"></i>\r\n    </div>\r\n    <div class=\"card-body\">\r\n      <div class=\"row\">\r\n        <div class=\"col-12 form-horizontal\">\r\n          <fieldset>\r\n            <div class=\"salaxy-component salaxy-accountant-info\">\r\n              <div>\r\n                <table>\r\n                  <tr ng-if=\"$ctrl.accountant.info.avatar.displayName\">\r\n                    <td sxy-text=\"SALAXY.NG1.AccountantComponent.name\" ps=\":\"></td>\r\n                    <td>\r\n                      <div class=\"d-flex align-items-center\">\r\n                        <salaxy-avatar class=\"me-2\" style=\"font-size: 25px;\" avatar=\"$ctrl.accountant.info.avatar\"></salaxy-avatar>\r\n                        <strong>{{ $ctrl.accountant.info.avatar.displayName}}<strong>\r\n                      </div>\r\n                    </td>\r\n                  </tr>\r\n                  <tr ng-if=\"$ctrl.accountant.info.officialId\">\r\n                    <td sxy-text=\"SALAXY.NG1.AccountantComponent.officialId\" ps=\":\"></td>\r\n                    <td>{{ $ctrl.accountant.info.officialId}}</td>\r\n                  </tr>\r\n                  <tr ng-if=\"$ctrl.accountant.info.email\">\r\n                    <td sxy-text=\"SALAXY.NG1.AccountantComponent.email\" ps=\":\"></td>\r\n                    <td>{{ $ctrl.accountant.info.email }}</td>\r\n                  </tr>\r\n                  <tr ng-if=\"$ctrl.accountant.info.telephone\">\r\n                    <td sxy-text=\"SALAXY.NG1.AccountantComponent.phone\" ps=\":\"></td>\r\n                    <td>{{ $ctrl.accountant.info.telephone }}</td>\r\n                  </tr>\r\n                  <tr ng-if=\"$ctrl.accountant.type == 'primaryPartner' || $ctrl.accountant.type == 'pendingPrimaryPartner' || $ctrl.accountant.type == 'unlinkedPrimaryPartner' || $ctrl.accountant.type == 'unlinkedAccountingOnly'\">\r\n                    <td sxy-text=\"SALAXY.NG1.AccountantComponent.accountantType\" ps=\":\"></td>\r\n                    <td>\r\n                      <span ng-if=\"$ctrl.accountant.type == 'primaryPartner'\" sxy-text=\"SALAXY.NG1.AccountantComponent.primaryPartner\"></span>\r\n                      <span ng-if=\"$ctrl.accountant.type == 'pendingPrimaryPartner'\" sxy-text=\"SALAXY.NG1.AccountantComponent.pendingPrimaryPartner\"></span>\r\n                      <span ng-if=\"$ctrl.accountant.type == 'unlinkedPrimaryPartner'\" sxy-text=\"SALAXY.NG1.AccountantComponent.unlinkedPrimaryPartner\"></span>\r\n                      <span ng-if=\"$ctrl.accountant.type == 'unlinkedAccountingOnly'\" sxy-text=\"SALAXY.NG1.AccountantComponent.unlinkedAccountingOnly\"></span>\r\n                    </td>\r\n                  </tr>\r\n                  <tr ng-if=\"$ctrl.accountantMainType == 'none' && !($ctrl.accountant.info.avatar.firstName || $ctrl.accountant.info.avatar.lastName || $ctrl.accountant.info.email || $ctrl.accountant.info.telephone)\">\r\n                    <td colspan=\"2\">\r\n                      <span sxy-text=\"SALAXY.NG1.AccountantSelectionComponent.noAccountantEnum\"></span>\r\n                    </td>\r\n                  </tr>\r\n                </table>\r\n              </div>\r\n            </div>\r\n\r\n          </fieldset>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"card-footer\">\r\n      <div class=\"row\">\r\n        <div class=\"col-12\">\r\n          <button class=\"btn btn-primary float-end\" ng-click=\"$ctrl.showEdit($ctrl.removalDisabled)\" sxy-text=\"SALAXY.UI_Terms.edit\"></button>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/settings/AccountantEmails.html\",`<div class=\"content settings\">\r\n  <div class=\"card card-secondary accountant\" ng-if=\"$ctrl.accountant\">\r\n    <div class=\"card-header\">\r\n      <h2><span sxy-text=\"SALAXY.NG1.AccountantComponent.title\"></span>\r\n      </h2>\r\n    </div>\r\n    <div class=\"card-body\">\r\n      <div class=\"row\">\r\n        <form name=\"companyAccountantForm\" class=\"form-horizontal\">\r\n          <div class=\"col\">\r\n            <fieldset ng-if=\"$ctrl.accountantMainType != 'none'\">\r\n              <div  class=\"container-fixed salaxy-component salaxy-accountant-info\">\r\n                <div class=\"table-responsive\">\r\n                  <table class=\"table\">\r\n                    <tr>\r\n                      <th sxy-text=\"SALAXY.NG1.AccountantComponent.name\" ps=\":\"></th>\r\n                      <td>\r\n                        <salaxy-avatar style=\"font-size: 20px; margin-right: 12px;\" avatar=\"$ctrl.accountant.info.avatar\"></salaxy-avatar><strong>{{ $ctrl.accountant.info.avatar.displayName}}<strong></td>\r\n                  </tr>\r\n                  <tr ng-if=\"$ctrl.accountant.info.officialId\">\r\n                    <th sxy-text=\"SALAXY.NG1.AccountantComponent.officialId\" ps=\":\"></th>\r\n                    <td>{{ $ctrl.accountant.info.officialId}}</td>\r\n                  </tr>\r\n                  <tr ng-if=\"$ctrl.accountant.type == 'primaryPartner' || $ctrl.accountant.type == 'pendingPrimaryPartner'\">\r\n                    <th sxy-text=\"SALAXY.NG1.AccountantSelectionComponent.companyAccountantForm.accountingDataEmail\" ps=\":\"></th>\r\n                    <td>\r\n                      <salaxy-input-boolean ng-model=\"$ctrl.accountant.info.accountantEmailsOrdered\" type=\"checkbox\" name=\"order\" label=\"\" label-type=\"plain\">\r\n                        </salaxy-input-boolean>\r\n                    </td>\r\n                  </tr>\r\n      \r\n                  <tr ng-if=\"$ctrl.accountant.type == 'unlinkedAccountingOnly' || !$ctrl.accountant.info.avatar.id || $ctrl.accountant.type == 'pendingPrimaryPartner' || $ctrl.accountant.type == 'primaryPartner'\">\r\n                    <th sxy-text=\"SALAXY.NG1.AccountantSelectionComponent.personAccountantForm.email\" ps=\":\"></th>\r\n                    <td>\r\n                      <salaxy-input name=\"email\" label=\"\" read-only=\"($ctrl.accountant.type == 'primaryPartner' || $ctrl.accountant.type == 'pendingPrimaryPartner') && !$ctrl.accountant.info.accountantEmailsOrdered\" require=\"!(($ctrl.accountant.type == 'primaryPartner' || $ctrl.accountant.type == 'pendingPrimaryPartner') && !$ctrl.accountant.info.accountantEmailsOrdered)\"\r\n                        label-type=\"plain\" sxy-email ng-model=\"$ctrl.accountant.info.email\"></salaxy-input>\r\n                    </td>\r\n                  </tr>\r\n                  <tr ng-if=\"$ctrl.accountant.type == 'unlinkedAccountingOnly' || !$ctrl.accountant.info.avatar.id || $ctrl.accountant.type == 'pendingPrimaryPartner' || $ctrl.accountant.type == 'primaryPartner'\">\r\n                    <th sxy-text=\"SALAXY.NG1.AccountantSelectionComponent.personAccountantForm.telephone\" ps=\":\"></th>\r\n                    <td>\r\n                      <salaxy-input name=\"telephone\" label=\"\" read-only=\"($ctrl.accountant.type == 'primaryPartner' || $ctrl.accountant.type == 'pendingPrimaryPartner') && !$ctrl.accountant.info.accountantEmailsOrdered\" require=\"!(($ctrl.accountant.type == 'primaryPartner' || $ctrl.accountant.type == 'pendingPrimaryPartner') && !$ctrl.accountant.info.accountantEmailsOrdered)\"\r\n                        label-type=\"plain\" sxy-mobile-phone ng-model=\"$ctrl.accountant.info.telephone\"></salaxy-input>\r\n                    </td>\r\n                  </tr>\r\n                  <tr ng-if=\"$ctrl.accountant.type == 'primaryPartner' || $ctrl.accountant.type == 'pendingPrimaryPartner' || $ctrl.accountant.type == 'unlinkedPrimaryPartner' || $ctrl.accountant.type == 'unlinkedAccountingOnly'\">\r\n                    <th sxy-text=\"SALAXY.NG1.AccountantComponent.accountantType\" ps=\":\"></th>\r\n                    <td>\r\n                      <span ng-if=\"$ctrl.accountant.type == 'primaryPartner'\" sxy-text=\"SALAXY.NG1.AccountantComponent.primaryPartner\"></span>\r\n                      <span ng-if=\"$ctrl.accountant.type == 'pendingPrimaryPartner'\" sxy-text=\"SALAXY.NG1.AccountantComponent.pendingPrimaryPartner\"></span>\r\n                      <span ng-if=\"$ctrl.accountant.type == 'unlinkedPrimaryPartner'\" sxy-text=\"SALAXY.NG1.AccountantComponent.unlinkedPrimaryPartner\"></span>\r\n                      <span ng-if=\"$ctrl.accountant.type == 'unlinkedAccountingOnly'\" sxy-text=\"SALAXY.NG1.AccountantComponent.unlinkedAccountingOnly\"></span>\r\n                    </td>\r\n                  </tr>\r\n                </table>\r\n              </div>\r\n            </div>\r\n          </fieldset>\r\n          <fieldset ng-if=\"$ctrl.accountantMainType == 'none'\">\r\n            <salaxy-input name=\"firstName\" label=\"SALAXY.NG1.AccountantSelectionComponent.personAccountantForm.firstName\" ng-model=\"$ctrl.accountant.info.avatar.firstName\"></salaxy-input>\r\n            <salaxy-input name=\"lastName\" label=\"SALAXY.NG1.AccountantSelectionComponent.personAccountantForm.lastName\"  ng-model=\"$ctrl.accountant.info.avatar.lastName\"></salaxy-input>\r\n            <salaxy-input name=\"email\" label=\"SALAXY.NG1.AccountantSelectionComponent.personAccountantForm.email\"  sxy-email ng-model=\"$ctrl.accountant.info.email\"></salaxy-input>\r\n            <salaxy-input name=\"telephone\" label=\"SALAXY.NG1.AccountantSelectionComponent.personAccountantForm.telephone\"  sxy-mobile-phone ng-model=\"$ctrl.accountant.info.telephone\"></salaxy-input>\r\n          </fieldset>\r\n        </div>\r\n      </form>\r\n      </div>\r\n    </div>\r\n    <div class=\"card-footer\">\r\n      <div class=\"row\">\r\n        <div class=\"col\">\r\n          <div class=\"text-end\">\r\n            <a ng-if=\"$ctrl.accountantMainType == 'none'\" class=\"btn btn-default\" href=\"#/settings/accountants\" sxy-text=\"SALAXY.NG1.AccountantComponent.addPrimaryPartner\"></a>\r\n            <button ng-disabled=\"!companyAccountantForm.$valid\" class=\"btn btn-primary\" ng-click=\"$ctrl.save()\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/settings/AccountantInfo.html\",`<div class=\"content settings\">\r\n  <div class=\"card mb-4 card-secondary accountant\" ng-if=\"$ctrl.accountant\">\r\n    <div class=\"card-header\">\r\n      <h2><span sxy-text=\"SALAXY.NG1.AccountantComponent.title\"></span>\r\n      </h2>\r\n    </div>\r\n    <div class=\"card-body\">\r\n      <div class=\"row\">\r\n        <div class=\"col-12 form-horizontal\">\r\n          <fieldset>\r\n            <div class=\"salaxy-component salaxy-accountant-info\">\r\n              <div >\r\n                <table>\r\n                  <tr ng-if=\"$ctrl.accountant.info.avatar.displayName\">\r\n                    <td sxy-text=\"SALAXY.NG1.AccountantComponent.name\" ps=\":\"></td>\r\n                    <td>\r\n                      <div class=\"d-flex align-items-center\">\r\n                        <salaxy-avatar class=\"me-2\" style=\"font-size: 25px;\" avatar=\"$ctrl.accountant.info.avatar\"></salaxy-avatar>\r\n                        <strong>{{ $ctrl.accountant.info.avatar.displayName}}<strong>\r\n                      </div>\r\n                    </td>\r\n                  </tr>\r\n                  <tr ng-if=\"$ctrl.accountant.info.officialId\">\r\n                    <td sxy-text=\"SALAXY.NG1.AccountantComponent.officialId\" ps=\":\"></td>\r\n                    <td>{{ $ctrl.accountant.info.officialId}}</td>\r\n                  </tr>\r\n                  <tr ng-if=\"$ctrl.accountant.info.email\">\r\n                    <td sxy-text=\"SALAXY.NG1.AccountantComponent.email\" ps=\":\"></td>\r\n                    <td>{{ $ctrl.accountant.info.email }}</td>\r\n                  </tr>\r\n                  <tr ng-if=\"$ctrl.accountant.info.telephone\">\r\n                    <td sxy-text=\"SALAXY.NG1.AccountantComponent.phone\" ps=\":\"></td>\r\n                    <td>{{ $ctrl.accountant.info.telephone }}</td>\r\n                  </tr>\r\n                  <tr ng-if=\"$ctrl.accountant.type == 'primaryPartner' || $ctrl.accountant.type == 'pendingPrimaryPartner' || $ctrl.accountant.type == 'unlinkedPrimaryPartner' || $ctrl.accountant.type == 'unlinkedAccountingOnly'\">\r\n                    <td sxy-text=\"SALAXY.NG1.AccountantComponent.accountantType\" ps=\":\"></td>\r\n                    <td>\r\n                      <span ng-if=\"$ctrl.accountant.type == 'primaryPartner'\" sxy-text=\"SALAXY.NG1.AccountantComponent.primaryPartner\"></span>\r\n                      <span ng-if=\"$ctrl.accountant.type == 'pendingPrimaryPartner'\" sxy-text=\"SALAXY.NG1.AccountantComponent.pendingPrimaryPartner\"></span>\r\n                      <span ng-if=\"$ctrl.accountant.type == 'unlinkedPrimaryPartner'\" sxy-text=\"SALAXY.NG1.AccountantComponent.unlinkedPrimaryPartner\"></span>\r\n                      <span ng-if=\"$ctrl.accountant.type == 'unlinkedAccountingOnly'\" sxy-text=\"SALAXY.NG1.AccountantComponent.unlinkedAccountingOnly\"></span>\r\n                    </td>\r\n                  </tr>\r\n                  <tr ng-if=\"$ctrl.accountantMainType == 'none' && !($ctrl.accountant.info.avatar.firstName || $ctrl.accountant.info.avatar.lastName || $ctrl.accountant.info.email || $ctrl.accountant.info.telephone)\">\r\n                    <td colspan=\"2\">\r\n                      <span sxy-text=\"SALAXY.NG1.AccountantSelectionComponent.noAccountantEnum\"></span>\r\n                    </td>\r\n                  </tr>\r\n                </table>\r\n              </div>\r\n            </div>\r\n\r\n          </fieldset>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"card-footer\" ng-if=\"$ctrl.accountantMainType == 'none'\">\r\n      <div class=\"row\">\r\n        <div class=\"col-12\">\r\n          <div class=\"text-end\">\r\n            <a class=\"btn btn-default\" href=\"#/settings/accountants\" sxy-text=\"SALAXY.NG1.AccountantComponent.addPrimaryPartner\"></a>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/settings/AccountingSettings.html\",`<div class=\"content settings\" ng-if=\"$ctrl.current\">\r\n  <div class=\"card mb-4 accounting card-secondary\">\r\n    <div>\r\n      <div class=\"card-header\">\r\n        <h2 sxy-text=\"SALAXY.MODEL.AccountingSettings.title\"></h2>\r\n        <p><small sxy-text=\"SALAXY.MODEL.AccountingSettings.descr\"></small></p>\r\n      </div>\r\n      <div class=\"card-body\">\r\n        <div class=\"row\">\r\n\r\n          <sxy-form ng-ref=\"$frm\" open-api=\"salaxy-secure/schemas/v02.json\" type=\"CompanyAccountSettings\" auto-gen=\"false\" debugger=\"false\" model=\"$ctrl.current\" read-only=\"{{!$ctrl.current.accounting.denyServiceModel  && $ctrl.current.partner.serviceModel.features.accounting}}\">\r\n            <div class=\"col-12 form-horizontal\">\r\n              <fieldset>\r\n                <salaxy-input-typeahead\r\n                  label=\"SALAXY.MODEL.AccountingSettings.defaultTargetId.title\"\r\n                  ng-model=\"$ctrl.current.accounting.defaultTargetId\"\r\n                  name=\"options_type\"\r\n                  disable-cache=\"true\"\r\n                  options=\"$ctrl.getSelectableAccountingTargets()\">\r\n                </salaxy-input-typeahead>\r\n                <salaxy-form-group name=\"targets\" label=\"SALAXY.MODEL.AccountingSettings.targets.title\">\r\n                  <div>\r\n                    <span>\r\n                        <i ng-click=\"$ctrl.showTargets = !$ctrl.showTargets\" class=\"clickable bi\" ng-class=\"$frm.readOnly == 'true' ? 'bi-info-circle-fill' : 'bi-pencil-fill'\"></i>\r\n                    </span>\r\n                  </div>\r\n                </salaxy-form-group>\r\n\r\n                  <sxy-input ng-if=\"$ctrl.showTargets\" template-url=\"salaxy-components/sxy-form/custom-templates/array-accounting-targets.html\" model=\"form.accounting.targets\">\r\n                    <form>\r\n                      <fieldset ng-show=\"!$ctrl.logic.showDelete\" ng-controller=\"CompanySettingsController as $companySettingsCtrl\" ng-init=\"$ctrl.logic.isReadOnly = true\">\r\n                        <salaxy-odata-table crud-controller=\"AccountingTargetCrudController as $crud\" template-url=\"salaxy-components/odata/lists/AccountingTargetSelect.html\" selected-items=\"$ctrl.selectedItems\" on-list-select=\"$companySettingsCtrl.onAccountingTargetSelect($ctrl.current, $ctrl.logic, value, item, allItems)\">\r\n                        </salaxy-odata-table>\r\n                      </fieldset>\r\n                      <fieldset ng-show=\"$ctrl.logic.showDelete\" ng-init=\"$ctrl.logic.isReadOnly = false\">\r\n                        <salaxy-input-enum disabled=\"false\" name=\"format\" label=\"SALAXY.NG1.AccountingTargetDetailsComponent.excelCsvFormat\" ng-model=\"$ctrl.current.format\"\r\n                          options=\"{\r\n                            '36dff2e2-e181-4f0d-9004-0e4aa92f5e17': 'Palkkaus.fi',\r\n                            '0db4e85f-93a8-46f1-b6d2-f7523d289d88': 'Fennoa',\r\n                            '8613f133-3fce-4611-b372-51f6a2e007dd': 'Procountor',\r\n                            'e62c10b0-222a-4170-b8b4-b1e02d9a7644': 'Passeli Merit',\r\n                            '53fd3863-b8f9-4909-86c9-cb4597595181': 'Heeros',\r\n                            '2fc7899c-7a3d-4d56-ad2f-05d52782bbbc': 'Asteri',\r\n                            '0a2bd312-06da-4862-aef5-75166e0bf461': 'Maestro',\r\n                            'c04e0757-63f3-420d-a183-3427710fc954': 'Visma Fivaldi',\r\n                            'ba271dac-dd63-4036-9d70-053a09ca4d9e' :'Visma Netvisor',\r\n                            '27e271d5-41f5-4319-ab29-4d5d9eb945c6': 'Lemonsoft',\r\n                            'd311f9d3-8c3a-4fd8-a665-8e3698e41e87': 'Tampuuri',\r\n                            'd58e95b7-d0b5-40ac-992b-6d3b29efc45e': 'Domus',\r\n                            '54e93c5f-bd74-4157-8a74-3515be7f585d': 'Oscar Software',\r\n                            '0e4f0a71-dcb9-43ba-9028-0239e674711f': 'Digia Enterprise',\r\n                            '2ccefa46-7992-46c5-9d87-b88336935916': 'Digia Enterprise - VILPE',\r\n                            'c36c24b9-5e2c-4f44-b67a-90d81aeea257': 'iScala'\r\n                          }\">\r\n                        </salaxy-input-enum>\r\n                        <sxy-input model=\"form.method\" read-only=\"false\"></sxy-input>\r\n                        <salaxy-input-enum disabled=\"false\" enum=\"ExportMethod\" label=\"SALAXY.MODEL.AccountingTargetSettings.availableMethods.title\" name=\"availableMethods\" type=\"multi-select\" ng-model=\"$ctrl.current.availableMethods\"></salaxy-input-enum>\r\n                      </fieldset>\r\n                    </form>\r\n                  </sxy-input>\r\n\r\n                <sxy-input model=\"form.accounting.defaultPeriodDateKind\"></sxy-input>\r\n                <salaxy-input-enum ng-if=\"$ctrl.defaultAccountingTarget\"\r\n                  read-only=\"$frm.readOnly == 'true'\" type=\"select\" name=\"method\"\r\n                  ng-model=\"$ctrl.defaultAccountingTarget.method\" enum=\"ExportMethod\" label=\"SALAXY.MODEL.AccountingTargetSettings.method.title\"></salaxy-input-enum>\r\n              </fieldset>\r\n              <fieldset>\r\n                <legend sxy-text=\"SALAXY.MODEL.AccountingSettings.reportDelivery.title\"></legend>\r\n                <sxy-input read-only=\"false\" format=\"checkbox\" model=\"form.accounting.reportDelivery.isEnabled\"></sxy-input>\r\n                <sxy-input read-only=\"false\"  format=\"email\" model=\"form.accounting.reportDelivery.address\" ng-if=\"$ctrl.current.accounting.reportDelivery.isEnabled\"></sxy-input>\r\n              </fieldset>\r\n              <fieldset>\r\n                <legend sxy-text=\"SALAXY.MODEL.AccountingSettings.accountantReportDelivery.title\"></legend>\r\n                <sxy-input read-only=\"false\" format=\"checkbox\" model=\"form.accounting.accountantReportDelivery.isEnabled\"></sxy-input>\r\n                <sxy-input read-only=\"false\"  format=\"email\" model=\"form.accounting.accountantReportDelivery.address\" ng-if=\"$ctrl.current.accounting.accountantReportDelivery.isEnabled\"></sxy-input>\r\n           \r\n              </fieldset>\r\n            </div>\r\n          </sxy-form>\r\n        </div>\r\n      </div>\r\n      <div class=\"card-footer\">\r\n        <div class=\"row\">\r\n          <div class=\"col-12\">\r\n            <button type=\"submit\" ng-disabled=\"!$frm.ngForm.$valid || $ctrl.isSaving('all')\" class=\"btn btn-primary float-end\" ng-click=\"$ctrl.save('all')\">\r\n              <span ng-if=\"$ctrl.isSaving('all')\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span>\r\n              <span sxy-text=\"SALAXY.UI_Terms.save\"></span>\r\n            </button>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/settings/AccountingTargetDetails.html\",`<div class=\"salaxy-component salaxy-accounting-target-editor\">\r\n  <div ng-if=\"!$ctrl.current\">\r\n    <salaxy-spinner heading=\"SALAXY.UI_Terms.loading\"></salaxy-spinner>\r\n  </div>\r\n  <div class=\"row\" ng-if=\"$ctrl.current\">\r\n    <div class=\"col-12 accounting-target-info-col\">\r\n      <div class=\"row mb-2\">\r\n        <div class=\"col-12\">\r\n          <div class=\"btn-toolbar float-end\" role=\"toolbar\" aria-label=\"Tilit\">\r\n            <div class=\"btn-group\" role=\"group\" aria-label=\"Save and load\">\r\n              <button class=\"btn btn-danger\" ng-disabled=\"$ctrl.isReadOnly\" ng-click=\"$ctrl.delete()\" sxy-text=\"SALAXY.UI_Terms.delete\"></button>\r\n              <button class=\"btn btn-default\" ng-click=\"$ctrl.showCopyAsNew($ctrl.current)\" sxy-text=\"SALAXY.UI_Terms.copyAsNew\"></button>\r\n              <button class=\"btn btn-primary\" ng-disabled=\"!$ctrl.hasChanges && !$ctrl.isNew()\" ng-click=\"$ctrl.save()\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n            </div>\r\n          </div>\r\n          <salaxy-avatar class=\"float-start\" style=\"font-size: 58px; margin-right: 15px; margin-top: -15px;\" avatar=\"$ctrl.current.info.target.avatar\"></salaxy-avatar>\r\n          <h2>{{ $ctrl.current.info.target.avatar.displayName}}</h2>\r\n\r\n          <fieldset class=\"form-horizontal\">\r\n            <legend sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.accountingTargetLegend\"></legend>\r\n            <div ng-if=\"$ctrl.template\">\r\n              <div class=\"row\">\r\n                <div class=\"col-sm-4\">\r\n                  <salaxy-input read-only=\"true\" name=\"template_name\" label=\"SALAXY.NG1.AccountingTargetDetailsComponent.name\"\r\n                    ng-model=\"$ctrl.template.info.target.avatar.displayName\"></salaxy-input>\r\n                  <salaxy-input read-only=\"true\" name=\"template_id\" label=\"SALAXY.NG1.AccountingTargetDetailsComponent.id\" ng-model=\"$ctrl.template.id\"></salaxy-input>\r\n                </div>\r\n                <div class=\"col-sm-4\">\r\n                  <salaxy-input-enum read-only=\"true\" name=\"format\" label=\"SALAXY.NG1.AccountingTargetDetailsComponent.excelCsv\" ng-model=\"$ctrl.template.info.format\" options=\"{\r\n                    '36dff2e2-e181-4f0d-9004-0e4aa92f5e17': 'Palkkaus.fi',\r\n                    '0db4e85f-93a8-46f1-b6d2-f7523d289d88': 'Fennoa',\r\n                    '8613f133-3fce-4611-b372-51f6a2e007dd': 'Procountor',\r\n                    'e62c10b0-222a-4170-b8b4-b1e02d9a7644': 'Passeli Merit',\r\n                    '53fd3863-b8f9-4909-86c9-cb4597595181': 'Heeros',\r\n                    '2fc7899c-7a3d-4d56-ad2f-05d52782bbbc': 'Asteri',\r\n                    '0a2bd312-06da-4862-aef5-75166e0bf461': 'Maestro',\r\n                    'c04e0757-63f3-420d-a183-3427710fc954': 'Visma Fivaldi',\r\n                    'ba271dac-dd63-4036-9d70-053a09ca4d9e': 'Visma Netvisor',\r\n                    '27e271d5-41f5-4319-ab29-4d5d9eb945c6': 'Lemonsoft',\r\n                    'd311f9d3-8c3a-4fd8-a665-8e3698e41e87': 'Tampuuri',\r\n                    'd58e95b7-d0b5-40ac-992b-6d3b29efc45e': 'Domus',\r\n                    '54e93c5f-bd74-4157-8a74-3515be7f585d': 'Oscar Software',\r\n                    '0e4f0a71-dcb9-43ba-9028-0239e674711f': 'Digia Enterprise',\r\n                    '2ccefa46-7992-46c5-9d87-b88336935916': 'Digia Enterprise - VILPE',\r\n                    'c36c24b9-5e2c-4f44-b67a-90d81aeea257': 'iScala'\r\n                  }\"></salaxy-input-enum>\r\n                </div>\r\n                <div class=\"col-sm-4\">\r\n                  <salaxy-datepicker read-only=\"true\" name=\"createdAt\" ng-model=\"$ctrl.template.createdAt\" label=\"SALAXY.UI_Terms.created\"></salaxy-datepicker>\r\n                  <salaxy-datepicker read-only=\"true\" name=\"updatedAt\" ng-model=\"$ctrl.template.updatedAt\" label=\"SALAXY.UI_Terms.updated\"></salaxy-datepicker>\r\n                </div>\r\n              </div>\r\n            </div>\r\n          </fieldset>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div ng-if=\"$ctrl.current\">\r\n    <salaxy-tab-buttons\r\n      current-tab=\"$ctrl.currentTab\"\r\n      options=\"[\r\n        { value: 'overview', text: 'SALAXY.NG1.AccountingTargetDetailsComponent.tabs.overview' },\r\n        { value: 'coa', text: 'SALAXY.NG1.AccountingTargetDetailsComponent.tabs.chartOfAccounts' },\r\n        { value: 'accounts', text: 'SALAXY.NG1.AccountingTargetDetailsComponent.tabs.usedAccounts', onClick: $ctrl.sortRulesetAccounts },\r\n        { value: 'guidelines', text: 'SALAXY.NG1.AccountingTargetDetailsComponent.tabs.guidelines' },\r\n        { value: 'rules', text: 'SALAXY.NG1.AccountingTargetDetailsComponent.tabs.rules' },\r\n        { value: 'accountingquery', text: 'SALAXY.NG1.AccountingTargetDetailsComponent.tabs.accountingQuery' },\r\n        { value: 'debugger', text: 'Debugger', hidden: !('test' | sxyIsInRole) }\r\n      ]\"\r\n      tabs-id=\"accountingTargetDetails\">\r\n    </salaxy-tab-buttons>\r\n    <div class=\"tab-content\" id=\"tab-content-accountingTargetDetails\">\r\n      <div class=\"tab-pane\" id=\"overview-tab\">\r\n        <form name=\"ruleSetForm\" class=\"form-horizontal\">\r\n          <div class=\"row\">\r\n            <div class=\"col-6\">\r\n              <fieldset>\r\n                <div ng-if=\"$ctrl.isReadOnly\" class=\"alert alert-danger\">\r\n                  <span class=\"text-danger\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.readOnly\"></span>\r\n                </div>\r\n                <salaxy-input disabled=\"$ctrl.isReadOnly\" name=\"ruleSetName\" label=\"SALAXY.NG1.AccountingTargetDetailsComponent.name\"\r\n                  ng-model=\"$ctrl.current.info.target.avatar.displayName\"></salaxy-input>\r\n                  <salaxy-input disabled=\"$ctrl.isReadOnly\" name=\"logoUrl\" label=\"SALAXY.NG1.AccountingTargetDetailsComponent.logoUrl\"\r\n                  ng-model=\"$ctrl.current.info.target.avatar.url\"></salaxy-input>\r\n                <salaxy-input-enum disabled=\"$ctrl.isReadOnly\" name=\"channel\" label=\"SALAXY.NG1.AccountingTargetDetailsComponent.channel\" ng-model=\"$ctrl.current.info.channel\" enum=\"AccountingChannel\">\r\n                </salaxy-input-enum>\r\n                <salaxy-input-enum disabled=\"$ctrl.isReadOnly\" name=\"format\" label=\"SALAXY.NG1.AccountingTargetDetailsComponent.excelCsvFormat\" ng-model=\"$ctrl.current.info.format\"\r\n                  options=\"{\r\n                    '36dff2e2-e181-4f0d-9004-0e4aa92f5e17': 'Palkkaus.fi',\r\n                    '0db4e85f-93a8-46f1-b6d2-f7523d289d88': 'Fennoa',\r\n                    '8613f133-3fce-4611-b372-51f6a2e007dd': 'Procountor',\r\n                    'e62c10b0-222a-4170-b8b4-b1e02d9a7644': 'Passeli Merit',\r\n                    '53fd3863-b8f9-4909-86c9-cb4597595181': 'Heeros',\r\n                    '2fc7899c-7a3d-4d56-ad2f-05d52782bbbc': 'Asteri',\r\n                    '0a2bd312-06da-4862-aef5-75166e0bf461': 'Maestro',\r\n                    'c04e0757-63f3-420d-a183-3427710fc954': 'Visma Fivaldi',\r\n                    'ba271dac-dd63-4036-9d70-053a09ca4d9e' :'Visma Netvisor',\r\n                    '27e271d5-41f5-4319-ab29-4d5d9eb945c6': 'Lemonsoft',\r\n                    'd311f9d3-8c3a-4fd8-a665-8e3698e41e87': 'Tampuuri',\r\n                    'd58e95b7-d0b5-40ac-992b-6d3b29efc45e': 'Domus',\r\n                    '54e93c5f-bd74-4157-8a74-3515be7f585d': 'Oscar Software',\r\n                    '0e4f0a71-dcb9-43ba-9028-0239e674711f': 'Digia Enterprise',\r\n                    '2ccefa46-7992-46c5-9d87-b88336935916': 'Digia Enterprise - VILPE',\r\n                    'c36c24b9-5e2c-4f44-b67a-90d81aeea257': 'iScala'\r\n                  }\">\r\n                </salaxy-input-enum>\r\n                <salaxy-form-group name=\"method\" label=\"SALAXY.NG1.AccountingTargetDetailsComponent.exportMethod\" label-type=\"horizontal\">\r\n                  <select class=\"form-select\" ng-model=\"$ctrl.current.info.method\">\r\n                    <option ng-repeat=\"method in $ctrl.current.info.availableMethods\"ng-value=\"method\">{{'SALAXY.ENUM.ExportMethod.' + method + \".label\" | sxyTranslate}}</option>\r\n                  </select>\r\n                </salaxy-form-group>\r\n                <salaxy-input-enum label=\"SALAXY.NG1.AccountingTargetDetailsComponent.exportMethods\" disabled=\"false\" enum=\"ExportMethod\"\r\n                  name=\"availableMethods\" type=\"multi-select\" ng-model=\"$ctrl.current.info.availableMethods\"></salaxy-input-enum>\r\n              </fieldset>\r\n            </div>\r\n          </div>\r\n        </form>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"coa-tab\">\r\n        <div class=\"btn-toolbar\" role=\"toolbar\" aria-label=\"Data options\">\r\n          <div class=\"btn-group\" role=\"group\">\r\n            <button ng-disabled=\"$ctrl.isReadOnly\" type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.pasteFromClipboard()\">\r\n              <span><span sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.pasteFromClipboard\"></span> <i class=\"bi bi-clipboard\"></i></span></button>\r\n            <button ng-disabled=\"$ctrl.isReadOnly\" type=\"button\" class=\"btn btn-default\" ngf-select=\"$ctrl.readFile($file)\" ngf-multiple=\"false\" ngf-max-size=\"10MB\">\r\n              <span><span sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.readFile\" ps=\"...\"></span><i class=\"bi bi-file-earmark-text\"></i></span>\r\n            </button>\r\n          </div>\r\n        </div>\r\n        <div class=\"table-responsive\" ng-if=\"$ctrl.hasTargetCoA\">\r\n          <table class=\"table table-sm\">\r\n            <thead>\r\n              <tr>\r\n                <th sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.accountNumber\"></th>\r\n                <th sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.name\"></th>\r\n                <th class=\"right\">\r\n                  <button title=\"{{'SALAXY.UI_Terms.addRow' | sxyTranslate}}\" class=\"btn btn-primary btn-sm\" type=\"button\" ng-click=\"$ctrl.addTargetCoaAccount(false)\"\r\n                    sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n                </th>\r\n              </tr>\r\n            </thead>\r\n            <tbody>\r\n              <tr ng-repeat=\"account in $ctrl.current.ruleSet.targetCoA\">\r\n                <td>\r\n                  <salaxy-input read-only=\"$ctrl.isReadOnly\" name=\"{{'accountAccount'+$index}}\" ng-change=\"$ctrl.updateRuleSetAccount(account)\" ng-model=\"account.account\" label-type=\"plain\"></salaxy-input>\r\n                </td>\r\n                <td>\r\n                  <salaxy-input read-only=\"$ctrl.isReadOnly\" name=\"{{'accountText'+$index}}\" ng-change=\"$ctrl.updateRuleSetAccount(account)\" ng-model=\"account.text\"\r\n                    label-type=\"plain\"></salaxy-input>\r\n                </td>\r\n                <td class=\"right\">\r\n                  <button title=\"{{'SALAXY.UI_Terms.deleteRow' | sxyTranslate}}\" class=\"btn btn-transparent\" type=\"button\" ng-if=\"!account.isReadOnly\"\r\n                    ng-click=\"$ctrl.removeAccount(account, true)\">\r\n                    <i class=\"bi bi-trash-fill\"></i>\r\n                  </button>\r\n                </td>\r\n              </tr>\r\n              <tr ng-if=\"$ctrl.hasTargetCoA\">\r\n                <td></td>\r\n                <td></td>\r\n                <td class=\"right\">\r\n                  <button title=\"{{'SALAXY.UI_Terms.addRow' | sxyTranslate}}\" class=\"btn btn-primary btn-sm\" type=\"button\" ng-click=\"$ctrl.addTargetCoaAccount(true)\"\r\n                    sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n                </td>\r\n              </tr>\r\n            </tbody>\r\n            <tfoot>\r\n            </tfoot>\r\n          </table>\r\n        </div>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"accounts-tab\">\r\n        <div class=\"btn-group btn-group-sm dropdown\">\r\n          <button id=\"single-button2\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\" ng-disabled=\"disabled\">\r\n            <span sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.filters.rowsToShow\" ps=\":\"></span> {{$ctrl.accountFilterText | sxyTranslate}}\r\n          </button>\r\n          <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"single-button2\">\r\n            <li role=\"menuitem\">\r\n              <a href=\"\" ng-click=\"$ctrl.accountFilter = 'all'\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.filters.all\"></a>\r\n            </li>\r\n            <li role=\"menuitem\">\r\n              <a href=\"\" ng-click=\"$ctrl.accountFilter = 'includedAndEnabled'\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.filters.includedAndEnabled\"></a>\r\n            </li>\r\n            <li role=\"menuitem\">\r\n              <a href=\"\" ng-click=\"$ctrl.accountFilter = 'error'\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.filters.error\"></a>\r\n            </li>\r\n          </ul>\r\n        </div>\r\n        <button class=\"btn btn-default btn-sm ms-1\" ng-click=\"$ctrl.showDistinct = !$ctrl.showDistinct\">{{$ctrl.showDistinct ?\r\n          ('SALAXY.NG1.AccountingTargetDetailsComponent.filters.showNormal' | sxyTranslate) : \"SALAXY.NG1.AccountingTargetDetailsComponent.filters.showDistinct\" |\r\n          sxyTranslate}}</button>\r\n        <div ng-if=\"$ctrl.showDistinct && !$ctrl.distinctAccounts.length || !$ctrl.showDistinct && !$ctrl.filteredAccounts.length\">\r\n            <p sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.filters.noRows\"></p>\r\n        </div>\r\n        <div class=\"table-responsive\" ng-if=\"!$ctrl.showDistinct && $ctrl.filteredAccounts.length\">\r\n          <table class=\"table table-sm\">\r\n            <thead>\r\n              <tr>\r\n                <th></th>\r\n                <th sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.accountNumber\"></th>\r\n                <th sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.name\"></th>\r\n                <th class=\"right\">\r\n                  <button ng-disabled=\"$ctrl.isReadOnly\" title=\"{{'SALAXY.UI_Terms.addRow' | sxyTranslate}}\" class=\"btn btn-primary btn-sm\" type=\"button\"\r\n                    ng-click=\"$ctrl.addAccount(false)\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n                </th>\r\n              </tr>\r\n            </thead>\r\n            <tbody>\r\n              <tr ng-repeat=\"account in $ctrl.filteredAccounts\">\r\n                <td class=\"middle\">\r\n                  <div class=\"text-center\" ng-if=\"!$ctrl.isValidAccount(account)\" data-toggle=\"tooltip\" data-placement=\"top\" data-bs-title=\"'SALAXY.NG1.AccountingTargetDetailsComponent.noAccountNumberFound' | sxyTranslate\" sxy-bs5-tooltip>\r\n                    <i class=\"bi bi-exclamation-circle-fill text-danger\"></i>\r\n                  </div>\r\n                </td>\r\n                <td>\r\n                  <salaxy-input read-only=\"$ctrl.isReadOnly\" name=\"{{'accountAccount'+$index}}\" ng-change=\"$ctrl.updateAccountToMatchTargetCoa(account)\" ng-model=\"account.account\" label-type=\"plain\"></salaxy-input>\r\n                </td>\r\n                <td>\r\n                  <salaxy-input read-only=\"true\" name=\"{{'accountText'+$index}}\" ng-model=\"account.text\" label-type=\"plain\"></salaxy-input>\r\n                </td>\r\n                <td class=\"right\">\r\n                  <button title=\"{{'SALAXY.UI_Terms.deleteRow' | sxyTranslate}}\" class=\"btn btn-transparent\" type=\"button\" ng-if=\"!account.isReadOnly\"\r\n                    ng-click=\"$ctrl.removeAccount(account)\">\r\n                    <i class=\"bi bi-trash-fill\"></i>\r\n                  </button>\r\n                  <button ng-disabled=\"$ctrl.isReadOnly\" title=\"{{'SALAXY.NG1.AccountingTargetDetailsComponent.changeAccount' | sxyTranslate}}\" class=\"btn btn-transparent\"\r\n                    type=\"button\" ng-click=\"$ctrl.selectTargetAccount(account)\" ng-if=\"$ctrl.hasTargetCoA\">\r\n                    <i class=\"bi bi-pencil-fill\"></i>\r\n                  </button>\r\n                </td>\r\n              </tr>\r\n              <tr ng-if=\"$ctrl.current.ruleSet.accounts.length\">\r\n                <td></td>\r\n                <td></td>\r\n                <td></td>\r\n                <td class=\"right\">\r\n                  <button ng-disabled=\"$ctrl.isReadOnly\" title=\"{{'SALAXY.UI_Terms.addRow' | sxyTranslate}}\" class=\"btn btn-primary btn-sm\" type=\"button\"\r\n                    ng-click=\"$ctrl.addAccount(true)\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n                </td>\r\n              </tr>\r\n            </tbody>\r\n            <tfoot>\r\n            </tfoot>\r\n          </table>\r\n        </div>\r\n        <div class=\"table-responsive\" ng-if=\"$ctrl.showDistinct && $ctrl.distinctAccounts.length\">\r\n          <table class=\"table table-sm\">\r\n            <thead>\r\n              <tr>\r\n                <th sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.accountNumber\"></th>\r\n                <th sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.name\"></th>\r\n                <th sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.ruleCount\"></th>\r\n              </tr>\r\n            </thead>\r\n            <tbody>\r\n              <tr ng-repeat=\"account in $ctrl.distinctAccounts\">\r\n                <td>\r\n                  <salaxy-input read-only=\"true\" name=\"{{'accountAccount'+$index}}\" ng-model=\"account.account\" label-type=\"plain\"></salaxy-input>\r\n                </td>\r\n                <td>\r\n                  <salaxy-input read-only=\"true\" name=\"{{'accountText'+$index}}\" ng-model=\"account.text\" label-type=\"plain\">\r\n                  </salaxy-input>\r\n                </td>\r\n                <td>{{$ctrl.getRulesCount(account.account)}}</td>\r\n              </tr>\r\n            </tbody>\r\n            <tfoot>\r\n            </tfoot>\r\n          </table>\r\n        </div>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"guidelines-tab\">\r\n        <div sxy-html=\"SALAXY.NG1.AccountingTargetDetailsComponent.guidelinesInfo.html\"></div>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"rules-tab\">\r\n        <div class=\"btn-toolbar\" role=\"toolbar\" aria-label=\"{{'SALAXY.NG1.AccountingTargetDetailsComponent.accounts' | sxyTranslate}}\">\r\n          <div class=\"btn-group\" role=\"group\" aria-label=\"{{'SALAXY.NG1.AccountingTargetDetailsComponent.sorting' | sxyTranslate}}\" ng-init=\"$ctrl.ruleViewSorting = 'default'\">\r\n            <salaxy-toggle-buttons ng-model=\"$ctrl.ruleViewSorting\" options=\"[\r\n              { value: 'default', label: 'SALAXY.NG1.AccountingTargetDetailsComponent.sortDefault' },\r\n              { value: 'byAccountPairs', label: 'SALAXY.NG1.AccountingTargetDetailsComponent.sortByAccountPairs' },\r\n              { value: 'byAccount', label: 'SALAXY.NG1.AccountingTargetDetailsComponent.sortByAccount' }\r\n              ]\" type=\"inline\"></salaxy-toggle-buttons>\r\n          </div>\r\n        </div>\r\n        <div ng-if=\"$ctrl.currentTab == 'rules'\">\r\n          <ng-include\r\n            src=\"'salaxy-components/settings/AccountingTargetEditorRulesTable' + ($ctrl.ruleViewSorting == 'byAccountPairs' ? 2 : $ctrl.ruleViewSorting == 'byAccount' ? 3 : 1) + '.html'\">\r\n          </ng-include>\r\n        </div>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"accountingquery-tab\">\r\n        <ng-include src=\"'salaxy-components/settings/AccountingTargetEditorQuery.html'\"></ng-include>\r\n      </div>\r\n      <div class=\"tab-pane\" id=\"debugger-tab\" ng-if=\"'test' | sxyIsInRole\">\r\n        <salaxy-json-formatter json=\"$ctrl.current\"></salaxy-json-formatter>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/settings/AccountingTargetEditorQuery.html\",`<div class=\"salaxy-component salaxy-accounting-report-query\" ng-controller=\"AccountingReportQueryController as $ctrlQuery\" ng-init=\"$ctrlQuery.queryType = 'selectionQuery'\">\r\n  <form name=\"queryForm\" class=\"form-horizontal\">\r\n    <fieldset>\r\n      <div class=\"col col-md-6\">\r\n        <p>\r\n          <span class=\"label label-primary\" ng-if=\"$ctrlQuery.calculations.length\">\r\n            <span sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.editorQuery.selectedAmount\" ps=\":\"></span>{{ $ctrlQuery.calculations.length }}\r\n          </span>\r\n        </p>\r\n        <div class=\"btn-toolbar\" role=\"toolbar\">\r\n          <button class=\"btn btn-default\" ng-click=\"$ctrlQuery.addCalcs('draft')\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.editorQuery.addDraftBtn\"></button>\r\n        </div>\r\n      </div>\r\n    </fieldset>\r\n    <div class=\"col col-md-12\">\r\n      <div ng-if=\"$ctrlQuery.calculations.length\" class=\"table-responsive salaxy-odata-table\">\r\n        <table class=\"table table-striped\">\r\n          <thead>\r\n            <tr>\r\n              <th colspan=\"2\">\r\n                <span sxy-text=\"SALAXY.NG1_Other.Roles.worker\"></span>\r\n              </th>\r\n              <th class=\"hidden-xxs\">\r\n                <span sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.editorQuery.status\"></span><br />\r\n                <span sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.editorQuery.date\"></span>\r\n              </th>\r\n              <th class=\"right hidden-xxs\">\r\n                <span sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.editorQuery.salary\"></span><br />\r\n                <span sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.editorQuery.payment\"></span>\r\n              </th>\r\n              <th class=\"hidden-xxs\"></th>\r\n            </tr>\r\n          </thead>\r\n          <tbody>\r\n            <tr ng-repeat=\"row in $ctrlQuery.calculations\">\r\n              <td class=\"td-avatar visible-xxs middle\">\r\n                <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n              </td>\r\n              <td class=\"td-name visible-xxs middle\">\r\n                <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.editorQuery.notSelected\"></span>\r\n                <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br /> {{ \"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate }}\r\n                <br /> {{ row.endAt | date }}\r\n              </td>\r\n              <td class=\"right visible-xxs bottom\">\r\n                <div>\r\n                  {{ row.grossSalary | currency }}<br /> {{ row.payment | currency }}\r\n                </div>\r\n              </td>\r\n              <td class=\"td-avatar hidden-xxs middle\">\r\n                <salaxy-avatar avatar=\"row.otherPartyInfo.avatar\"></salaxy-avatar>\r\n              </td>\r\n              <td class=\"td-name hidden-xxs middle\">\r\n                <span ng-if=\"row.otherPartyInfo.avatar.displayName == ''\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.editorQuery.notSelected\"></span>\r\n                <strong>{{row.otherPartyInfo.avatar.displayName}}</strong><br />\r\n              </td>\r\n              <td class=\"hidden-xxs middle\">\r\n                {{ row.status ? (\"SALAXY.ENUM.CalculationStatus.\" + row.status + \".label\" | sxyTranslate) : \"#ERR\" }}<br /> {{ row.endAt | date }}\r\n              </td>\r\n              <td class=\"right hidden-xxs middle\">\r\n                {{ row.grossSalary | currency }}<br /> {{ row.payment | currency }}\r\n              </td>\r\n              <td class=\"right middle\">\r\n                <button class=\"btn btn-sm  btn-danger\" type=\"button\" ng-click=\"$ctrlQuery.removeCalc(row)\">\r\n                        {{ 'SALAXY.NG1.AccountingTargetDetailsComponent.editorQuery.unselect' | sxyTranslate }}\r\n                      </button>\r\n              </td>\r\n            </tr>\r\n          </tbody>\r\n        </table>\r\n      </div>\r\n    </div>\r\n  </form>\r\n  <div class=\"col col-md-12 text-end\">\r\n    <button class=\"btn btn-primary\" ng-disabled=\"!queryForm.$valid || !$ctrlQuery.calculations.length\" ng-click=\"$ctrlQuery.queryData($ctrl.current.id)\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.editorQuery.fetchRowsBtn\"></button>\r\n  </div>\r\n  <salaxy-accounting-report-rows data=\"$ctrlQuery.data\"></salaxy-accounting-report-rows>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/settings/AccountingTargetEditorRulesTable1.html\",`<div class=\"table-responsive\">\r\n  <table class=\"table table-sm\">\r\n    <thead>\r\n      <tr>\r\n        <th sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.incomeTypeHead\"></th>\r\n        <th sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.additionalSelectionsHead\"></th>\r\n        <th>\r\n          <div sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.includeHead\"></div>\r\n          <div sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.enabledHead\"></div>\r\n        </th>\r\n        <th sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.debetHead\"></th>\r\n        <th sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.creditHead\"></th>\r\n        <th class=\"right\">\r\n          <button ng-disabled=\"$ctrl.isReadOnly\" title=\"{{'SALAXY.UI_Terms.addRow'| sxyTranslate}}\" class=\"btn btn-primary btn-sm\" type=\"button\" ng-click=\"$ctrl.addRow(null, true)\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n        </th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat-start=\"ruleSetRow in $ctrl.current.ruleSet.rows\">\r\n        <td>{{$ctrl.getEntryDescription(ruleSetRow)}}</td>\r\n        <td>\r\n          <div ng-repeat=\"flag in ruleSetRow.flags\">\r\n            <span class=\"badge\" ng-class=\"$ctrl.getFlagText(flag).found ? 'bg-success' : 'bg-warning'\">{{$ctrl.getFlagText(flag).text}}</span>\r\n          </div>\r\n        </td>\r\n        <td>\r\n          <div ng-class=\"{ 'text-danger': !ruleSetRow.isIncluded }\">{{ ruleSetRow.isIncluded ? ('SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.included'| sxyTranslate) : ('SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.excluded'| sxyTranslate) }}</div>\r\n          <div ng-class=\"{ 'text-danger': !ruleSetRow.enabled }\">{{ ruleSetRow.enabled ? ('SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.enabled'| sxyTranslate) : ('SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.disabled'| sxyTranslate) }}</div>\r\n        </td>\r\n        <td ng-if=\"ruleSetRow.isIncluded\">\r\n          <div>\r\n            {{ $ctrl.getAccount(ruleSetRow.debitId).account || ('SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.debitUndefined'| sxyTranslate) }}\r\n            <span ng-if=\"ruleSetRow.debitGrouping\">\r\n              <span>{{ ruleSetRow.debitGrouping }}</span>\r\n            <small style=\"text-decoration: line-through\">{{ $ctrl.getAccount(ruleSetRow.debitId).text }}</small>\r\n            </span>\r\n            <span ng-if=\"!ruleSetRow.debitGrouping\">\r\n              <span>{{ $ctrl.getAccount(ruleSetRow.debitId).text }}</span>\r\n            </span>\r\n          </div>\r\n        </td>\r\n        <td ng-if=\"ruleSetRow.isIncluded\">\r\n          <div>\r\n            {{ $ctrl.getAccount(ruleSetRow.creditId).account || ('SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.creditUndefined'| sxyTranslate) }}\r\n            <span ng-if=\"ruleSetRow.creditGrouping\">\r\n              <span>{{ ruleSetRow.creditGrouping }}</span>\r\n            <small style=\"text-decoration: line-through\">{{ $ctrl.getAccount(ruleSetRow.creditId).text }}</small>\r\n            </span>\r\n            <span ng-if=\"!ruleSetRow.creditGrouping\">\r\n              <span>{{ $ctrl.getAccount(ruleSetRow.creditId).text }}</span>\r\n            </span>\r\n          </div>\r\n        </td>\r\n        <td colspan=\"2\" ng-if=\"!ruleSetRow.isIncluded\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.notIncluded\"></td>\r\n        <td class=\"right\">\r\n          <div class=\"btn-group\">\r\n            <button ng-disabled=\"$ctrl.isReadOnly\" title=\"{{'SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.editRule' | sxyTranslate}}\" class=\"btn btn-sm\" ng-class=\"{ 'btn-primary': !ruleSetRow.isInEdit, 'btn-default': ruleSetRow.isInEdit }\" type=\"button\"\r\n              ng-click=\"ruleSetRow.isInEdit=!ruleSetRow.isInEdit\">\r\n              <i class=\"bi bi-pencil-square\"></i>\r\n            </button>\r\n            <button ng-disabled=\"$ctrl.isReadOnly\" title=\"{{'SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.copyAsNewRule' | sxyTranslate}}\" class=\"btn btn-default btn-sm\" type=\"button\" ng-click=\"$ctrl.addRow(ruleSetRow)\">\r\n              <i class=\"bi bi-copy\"></i>\r\n            </button>\r\n          </div>\r\n        </td>\r\n      </tr>\r\n      <tr ng-repeat-end ng-if=\"ruleSetRow.isInEdit\">\r\n        <td>\r\n          <button title=\"{{'SALAXY.UI_Terms.change' | sxyTranslate}}\" class=\"btn btn-sm btn-default\" type=\"button\" ng-click=\"$ctrl.selectEntry(ruleSetRow)\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.changeIncomeTypeBtn\"></button>\r\n        </td>\r\n        <td>\r\n          <button title=\"{{'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-sm btn-default\" type=\"button\" ng-click=\"$ctrl.selectFlags(ruleSetRow)\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.editAdditionalsBtn\"></button>\r\n        </td>\r\n        <td>\r\n          <salaxy-input-boolean type=\"checkbox\" name=\"{{'ruleSetIsIncluded'+$index}}\" ng-model=\"ruleSetRow.isIncluded\" label-type=\"plain\" label-true=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.includeHead\">\r\n          </salaxy-input-boolean>\r\n          <salaxy-input-boolean type=\"checkbox\" name=\"{{'ruleSetEnabled'+$index}}\" ng-model=\"ruleSetRow.enabled\" label-type=\"plain\" label-true=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.enabledHead\"></salaxy-input-boolean>\r\n        </td>\r\n        <td>\r\n          <div ng-if=\"ruleSetRow.isIncluded\">\r\n            <button title=\"{{'SALAXY.UI_Terms.change' | sxyTranslate}}\" ng-disabled=\"!ruleSetRow.isIncluded\" class=\"btn btn-default btn-sm btn-block\" type=\"button\" ng-click=\"$ctrl.selectAccount(ruleSetRow, false)\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.changeAccountBtn\"></button>\r\n            <salaxy-input name=\"{{'debitGrouping'+$index}}\" placeholder=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.grouping\" label-type=\"plain\" ng-model=\"ruleSetRow.debitGrouping\"></salaxy-input>\r\n          </div>\r\n        </td>\r\n        <td>\r\n          <div ng-if=\"ruleSetRow.isIncluded\">\r\n            <button title=\"{{'SALAXY.UI_Terms.change' | sxyTranslate}}\" ng-disabled=\"!ruleSetRow.isIncluded\" class=\"btn btn-default btn-sm btn-block\" type=\"button\" ng-click=\"$ctrl.selectAccount(ruleSetRow, true)\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.changeAccountBtn\"></button>\r\n            <salaxy-input name=\"{{'creditGrouping'+$index}}\" placeholder=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.grouping\" label-type=\"plain\" ng-model=\"ruleSetRow.creditGrouping\"></salaxy-input>\r\n          </div>\r\n        </td>\r\n        <td class=\"right\">\r\n          <button title=\"{{'SALAXY.UI_Terms.deleteRow' | sxyTranslate}}\" class=\"btn btn-danger btn-sm\" type=\"button\" ng-disabled=\"ruleSetRow.isReadOnly\" ng-click=\"$ctrl.removeRow(ruleSetRow)\" sxy-text=\"SALAXY.UI_Terms.deleteRow\"></button>\r\n        </td>\r\n      </tr>\r\n      <tr>\r\n        <td></td>\r\n        <td></td>\r\n        <td></td>\r\n        <td></td>\r\n        <td></td>\r\n        <td class=\"right\">\r\n          <button ng-disabled=\"$ctrl.isReadOnly\" title=\"{{'SALAXY.UI_Terms.addRow' | sxyTranslate}}\" class=\"btn btn-primary btn-sm\" type=\"button\" ng-click=\"$ctrl.addRow(null)\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/settings/AccountingTargetEditorRulesTable2.html\",`<div class=\"table-responsive\">\r\n  <table class=\"table table-sm\">\r\n    <thead>\r\n      <tr>\r\n        <th sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.debetHead\"></th>\r\n        <th sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.creditHead\"></th>\r\n        <th></th>\r\n        <th></th>\r\n        <th class=\"right\">\r\n          <button ng-disabled=\"true\" title=\"{{'SALAXY.UI_Terms.addRow'| sxyTranslate}}\" class=\"btn btn-primary btn-sm\" type=\"button\" ng-click=\"$ctrl.addRow(null, true)\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n        </th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat-start=\"(key, ruleSetGroup) in $ctrl.groupedRows\" class=\"primary\">\r\n        <td ng-if=\"ruleSetGroup[0].isIncluded\">\r\n          <div>\r\n            {{ $ctrl.getAccount(ruleSetGroup[0].debitId).account || ('SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.debitUndefined'| sxyTranslate) }}\r\n            <span ng-if=\"ruleSetGroup[0].debitGrouping\">\r\n              <span>{{ ruleSetGroup[0].debitGrouping }}</span>\r\n            <small style=\"text-decoration: line-through\">{{ $ctrl.getAccount(ruleSetGroup[0].debitId).text }}</small>\r\n            </span>\r\n            <span ng-if=\"!ruleSetGroup[0].debitGrouping\">\r\n              <span>{{ $ctrl.getAccount(ruleSetGroup[0].debitId).text }}</span>\r\n            </span>\r\n          </div>\r\n        </td>\r\n        <td ng-if=\"ruleSetGroup[0].isIncluded\">\r\n          <div>\r\n            {{ $ctrl.getAccount(ruleSetGroup[0].creditId).account || ('SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.creditUndefined'| sxyTranslate) }}\r\n            <span ng-if=\"ruleSetGroup[0].creditGrouping\">\r\n              <span>{{ ruleSetGroup[0].creditGrouping }}</span>\r\n            <small style=\"text-decoration: line-through\">{{ $ctrl.getAccount(ruleSetGroup[0].creditId).text }}</small>\r\n            </span>\r\n            <span ng-if=\"!ruleSetGroup[0].creditGrouping\">\r\n              <span>{{ $ctrl.getAccount(ruleSetGroup[0].creditId).text }}</span>\r\n            </span>\r\n          </div>\r\n        </td>\r\n        <td colspan=\"2\" ng-if=\"!ruleSetGroup[0].isIncluded\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.notIncluded\"></td>\r\n        <td colspan=\"4\"></td>\r\n      </tr>\r\n      <tr ng-repeat-start=\"ruleSetRow in ruleSetGroup\">\r\n        <td colspan=\"2\">{{$ctrl.getEntryDescription(ruleSetRow)}}</td>\r\n        <td>\r\n          <div ng-repeat=\"flag in ruleSetRow.flags\">\r\n            <span class=\"badge\" ng-class=\"$ctrl.getFlagText(flag).found ? 'bg-success' : 'bg-warning'\">{{$ctrl.getFlagText(flag).text}}</span>\r\n          </div>\r\n        </td>\r\n        <td>\r\n          <div ng-class=\"{ 'text-danger': !ruleSetRow.enabled }\">{{ ruleSetRow.enabled ? ('SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.enabled'| sxyTranslate) : ('SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.disabled'| sxyTranslate) }}</div>\r\n        </td>\r\n        <td class=\"right\">\r\n          <div class=\"btn-group\">\r\n            <button ng-disabled=\"$ctrl.isReadOnly\" title=\"{{'SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.editRule' | sxyTranslate}}\" class=\"btn btn-sm\" ng-class=\"{ 'btn-primary': !ruleSetRow.isInEdit, 'btn-default': ruleSetRow.isInEdit }\" type=\"button\"\r\n              ng-click=\"ruleSetRow.isInEdit=!ruleSetRow.isInEdit\">\r\n              <i class=\"bi bi-pencil-square\"></i>\r\n            </button>\r\n            <button ng-disabled=\"$ctrl.isReadOnly\" title=\"{{'SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.copyAsNewRule' | sxyTranslate}}\" class=\"btn btn-default btn-sm\" type=\"button\" ng-click=\"$ctrl.addRow(ruleSetRow)\">\r\n              <i class=\"bi bi-copy\"></i>\r\n            </button>\r\n          </div>\r\n        </td>\r\n      </tr>\r\n      <tr ng-repeat-end ng-if=\"ruleSetRow.isInEdit\" class=\"no-border\">\r\n        <td>\r\n          <div ng-if=\"!ruleSetRow.isIncluded\">\r\n            <small sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.notIncluded\"></small>\r\n          </div>\r\n          <div ng-if=\"ruleSetRow.isIncluded\">\r\n            <div class=\"input-group\">\r\n              <input type=\"text\" class=\"form-control\" ng-value=\"$ctrl.getAccount(ruleSetRow.debitId).account + ' ' + $ctrl.getAccount(ruleSetRow.debitId).text\" disabled=\"true\">\r\n              <span class=\"input-group-btn\">\r\n                <button class=\"btn btn-default fixed-width-addon\" type=\"button\" ng-click=\"$ctrl.selectAccount(ruleSetRow, false)\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.changeAccountBtn\"></button>\r\n              </span>\r\n            </div>\r\n            <div class=\"input-group\">\r\n              <input type=\"text\" class=\"form-control\" ng-init=\"ruleSetRow.debitGroupingTemp = ruleSetRow.debitGrouping\" ng-model=\"ruleSetRow.debitGroupingTemp\" placeholder=\"{{'SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.addGrouping' | sxyTranslate}}\">\r\n              <span class=\"input-group-btn\">\r\n                <button class=\"btn btn-default fixed-width-addon\" type=\"button\" ng-click=\"ruleSetRow.debitGrouping = ruleSetRow.debitGroupingTemp\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.changeGroupingBtn\"></button>\r\n              </span>\r\n            </div>\r\n          </div>\r\n        </td>\r\n        <td>\r\n          <div ng-if=\"!ruleSetRow.isIncluded\">\r\n            <small sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.notIncluded\"></small>\r\n          </div>\r\n          <div ng-if=\"ruleSetRow.isIncluded\">\r\n            <div class=\"input-group\">\r\n              <input type=\"text\" class=\"form-control\" ng-value=\"$ctrl.getAccount(ruleSetRow.creditId).account + ' ' + $ctrl.getAccount(ruleSetRow.creditId).text\" disabled=\"true\">\r\n              <span class=\"input-group-btn\">\r\n                <button class=\"btn btn-default fixed-width-addon\" type=\"button\" ng-click=\"$ctrl.selectAccount(ruleSetRow, true)\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.changeAccountBtn\"></button>\r\n              </span>\r\n            </div>\r\n            <div class=\"input-group\">\r\n              <input type=\"text\" class=\"form-control\" ng-init=\"ruleSetRow.creditGroupingTemp = ruleSetRow.creditGrouping\" ng-model=\"ruleSetRow.creditGroupingTemp\" placeholder=\"{{'SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.addGrouping' | sxyTranslate}}\">\r\n              <span class=\"input-group-btn\">\r\n                <button class=\"btn btn-default fixed-width-addon\" type=\"button\" ng-click=\"ruleSetRow.creditGrouping = ruleSetRow.creditGroupingTemp\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.changeGroupingBtn\"></button>\r\n              </span>\r\n            </div>\r\n          </div>\r\n        </td>\r\n        <td>\r\n          <button title=\"{{'SALAXY.UI_Terms.change' | sxyTranslate}}\" class=\"btn btn-default fixed-width-button\" type=\"button\" ng-click=\"$ctrl.selectEntry(ruleSetRow)\">\r\n            <span sxy-text=\"SALAXY.UI_Terms.change\"></span> {{ ruleSetRow.entryCodeGroup == 'incomeType' ? ('SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.incomeTypeBtnPS' | sxyTranslate) : ('SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.calcRowBtnPS' | sxyTranslate) }}\r\n          </button>\r\n          <button title=\"{{'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-default fixed-width-button\" type=\"button\" ng-click=\"$ctrl.selectFlags(ruleSetRow)\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.editAdditionalsBtn\"></button>\r\n        </td>\r\n        <td>\r\n          <salaxy-input-boolean type=\"checkbox\" name=\"{{'ruleSetIsIncluded'+$index}}\" ng-model=\"ruleSetRow.isIncluded\" label-type=\"plain\" label-true=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.includeHead\">\r\n          </salaxy-input-boolean>\r\n          <salaxy-input-boolean type=\"checkbox\" name=\"{{'ruleSetEnabled'+$index}}\" ng-model=\"ruleSetRow.enabled\" label-type=\"plain\" label-true=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.enabledHead\"></salaxy-input-boolean>\r\n        </td>\r\n        <td class=\"right\">\r\n          <button title=\"{{'SALAXY.UI_Terms.deleteRow' | sxyTranslate}}\" class=\"btn btn-danger btn-sm\" ng-disabled=\"ruleSetRow.isReadOnly\" type=\"button\" ng-disabled=\"ruleSetRow.isReadOnly\" ng-click=\"$ctrl.removeRow(ruleSetRow)\" sxy-text=\"SALAXY.UI_Terms.deleteRow\"></button>\r\n        </td>\r\n      </tr>\r\n      <tr ng-repeat-end></tr>\r\n      <tr>\r\n        <td></td>\r\n        <td></td>\r\n        <td></td>\r\n        <td></td>\r\n        <td class=\"right\">\r\n          <button ng-disabled=\"true\" title=\"{{'SALAXY.UI_Terms.addRow' | sxyTranslate}}\" class=\"btn btn-primary btn-sm\" type=\"button\" ng-click=\"$ctrl.addRow(null)\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/settings/AccountingTargetEditorRulesTable3.html\",`<div class=\"table-responsive\">\r\n  <table class=\"table table-sm\">\r\n    <thead>\r\n      <tr>\r\n        <th sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.accountsHead\"></th>\r\n        <th></th>\r\n        <th></th>\r\n      </tr>\r\n      <tr>\r\n        <th></th>\r\n        <th sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.debetHead\"></th>\r\n        <th sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.creditHead\"></th>\r\n        <th></th>\r\n        <th class=\"right\">\r\n          <button ng-disabled=\"true\" title=\"{{'SALAXY.UI_Terms.addRow'| sxyTranslate}}\" class=\"btn btn-primary btn-sm\" type=\"button\" ng-click=\"$ctrl.addRow(null, true)\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n        </th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat-start=\"account in $ctrl.current.ruleSet.accounts\" class=\"primary\">\r\n        <td>\r\n          {{account.account}} {{account.text}}\r\n        </td>\r\n        <td></td>\r\n        <td></td>\r\n        <td></td>\r\n      </tr>\r\n      <tr ng-repeat-start=\"ruleSetRow in $ctrl.getRulesetByAccount(account, true)\">\r\n        <td></td>\r\n        <td>\r\n          {{$ctrl.getEntryDescription(ruleSetRow)}}\r\n        </td>\r\n        <td></td>\r\n        <td></td>\r\n        <td class=\"right\">\r\n          <div class=\"btn-group\">\r\n            <button ng-disabled=\"$ctrl.isReadOnly\" title=\"{{'SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.editRule' | sxyTranslate}}\" class=\"btn btn-sm\" ng-class=\"{ 'btn-primary': !ruleSetRow.isInEdit, 'btn-default': ruleSetRow.isInEdit }\" type=\"button\"\r\n              ng-click=\"ruleSetRow.isInEdit=!ruleSetRow.isInEdit\">\r\n                <i class=\"bi bi-pencil-square\"></i>\r\n              </button>\r\n            <button ng-disabled=\"$ctrl.isReadOnly\" title=\"{{'SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.copyAsNewRule' | sxyTranslate}}\" class=\"btn btn-default btn-sm\" type=\"button\" ng-click=\"$ctrl.addRow(ruleSetRow)\">\r\n                <i class=\"bi bi-copy\"></i>\r\n              </button>\r\n          </div>\r\n        </td>\r\n      </tr>\r\n      <tr ng-if=\"ruleSetRow.isInEdit\">\r\n        <td>\r\n          <div ng-if=\"!ruleSetRow.isIncluded\">\r\n            <small sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.notIncluded\"></small>\r\n          </div>\r\n          <div ng-if=\"ruleSetRow.isIncluded\">\r\n            <div class=\"input-group\">\r\n              <input type=\"text\" class=\"form-control\" ng-value=\"$ctrl.getAccount(ruleSetRow.debitId).account + ' ' + $ctrl.getAccount(ruleSetRow.debitId).text\" disabled=\"true\">\r\n              <span class=\"input-group-btn\">\r\n                  <button class=\"btn btn-default fixed-width-addon\" type=\"button\" ng-click=\"$ctrl.selectAccount(ruleSetRow, false)\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.changeAccountBtn\"></button>\r\n                </span>\r\n            </div>\r\n            <div class=\"input-group\">\r\n              <input type=\"text\" class=\"form-control\" ng-init=\"ruleSetRow.debitGroupingTemp = ruleSetRow.debitGrouping\" ng-model=\"ruleSetRow.debitGroupingTemp\" placeholder=\"{{'SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.addGrouping' | sxyTranslate}}\">\r\n              <span class=\"input-group-btn\">\r\n                  <button class=\"btn btn-default fixed-width-addon\" type=\"button\" ng-click=\"ruleSetRow.debitGrouping = ruleSetRow.debitGroupingTemp\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.changeGroupingBtn\"></button>\r\n                </span>\r\n            </div>\r\n          </div>\r\n        </td>\r\n        <td>\r\n          <div ng-if=\"!ruleSetRow.isIncluded\">\r\n            <small sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.notIncluded\"></small>\r\n          </div>\r\n          <div ng-if=\"ruleSetRow.isIncluded\">\r\n            <div class=\"input-group\">\r\n              <input type=\"text\" class=\"form-control\" ng-value=\"$ctrl.getAccount(ruleSetRow.creditId).account + ' ' + $ctrl.getAccount(ruleSetRow.creditId).text\" disabled=\"true\">\r\n              <span class=\"input-group-btn\">\r\n                  <button class=\"btn btn-default fixed-width-addon\" type=\"button\" ng-click=\"$ctrl.selectAccount(ruleSetRow, true)\"  sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.changeAccountBtn\"></button>\r\n                </span>\r\n            </div>\r\n            <div class=\"input-group\">\r\n              <input type=\"text\" class=\"form-control\" ng-init=\"ruleSetRow.creditGroupingTemp = ruleSetRow.creditGrouping\" ng-model=\"ruleSetRow.creditGroupingTemp\" placeholder=\"{{'SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.addGrouping' | sxyTranslate}}\">\r\n              <span class=\"input-group-btn\">\r\n                  <button class=\"btn btn-default fixed-width-addon\" type=\"button\" ng-click=\"ruleSetRow.creditGrouping = ruleSetRow.creditGroupingTemp\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.changeGroupingBtn\"></button>\r\n                </span>\r\n            </div>\r\n          </div>\r\n        </td>\r\n        <td></td>\r\n        <td>\r\n          <button title=\"{{'SALAXY.UI_Terms.change' | sxyTranslate}}\" class=\"btn btn-default fixed-width-button\" type=\"button\" ng-click=\"$ctrl.selectEntry(ruleSetRow)\">\r\n            <span sxy-text=\"SALAXY.UI_Terms.change\"></span> {{ ruleSetRow.entryCodeGroup == 'incomeType' ? ('SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.incomeTypeBtnPS' | sxyTranslate) : ('SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.calcRowBtnPS' | sxyTranslate) }}\r\n            </button>\r\n          <button title=\"{{'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-default fixed-width-button\" type=\"button\" ng-click=\"$ctrl.selectFlags(ruleSetRow)\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.editAdditionalsBtn\"></button>\r\n        </td>\r\n        <td>\r\n          <salaxy-input-boolean type=\"checkbox\" name=\"{{'ruleSetIsIncluded'+$index}}\" ng-model=\"ruleSetRow.isIncluded\" label-type=\"plain\" label-true=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.includeHead\">\r\n          </salaxy-input-boolean>\r\n          <salaxy-input-boolean type=\"checkbox\" name=\"{{'ruleSetEnabled'+$index}}\" ng-model=\"ruleSetRow.enabled\" label-type=\"plain\" label-true=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.enabledHead\"></salaxy-input-boolean>\r\n          <button title=\"Poista rivi\" ng-disabled=\"ruleSetRow.isReadOnly\" class=\"btn btn-danger btn-sm\" type=\"button\" ng-click=\"$ctrl.removeRow(ruleSetRow)\" sxy-text=\"SALAXY.UI_Terms.deleteRow\"></button>\r\n        </td>\r\n      </tr>\r\n      <tr ng-repeat-end></tr>\r\n      <tr ng-repeat-start=\"ruleSetRow in $ctrl.getRulesetByAccount(account, false)\">\r\n        <td></td>\r\n        <td></td>\r\n        <td>\r\n          {{$ctrl.getEntryDescription(ruleSetRow)}}\r\n        </td>\r\n        <td></td>\r\n        <td class=\"right\">\r\n          <div class=\"btn-group\">\r\n            <button ng-disabled=\"$ctrl.isReadOnly\" ttitle=\"{{'SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.editRule' | sxyTranslate}}\" class=\"btn btn-sm\" ng-class=\"{ 'btn-primary': !ruleSetRow.isInEdit, 'btn-default': ruleSetRow.isInEdit }\" type=\"button\"\r\n              ng-click=\"ruleSetRow.isInEdit=!ruleSetRow.isInEdit\">\r\n              <i class=\"bi bi-pencil-square\"></i>\r\n            </button>\r\n            <button ng-disabled=\"$ctrl.isReadOnly\" title=\"{{'SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.copyAsNewRule' | sxyTranslate}}\" class=\"btn btn-default btn-sm\" type=\"button\" ng-click=\"$ctrl.addRow(ruleSetRow)\">\r\n              <i class=\"bi bi-copy\"></i>\r\n            </button>\r\n          </div>\r\n        </td>\r\n      </tr>\r\n      <tr ng-if=\"ruleSetRow.isInEdit\">\r\n        <td>\r\n          <div ng-if=\"!ruleSetRow.isIncluded\">\r\n            <small sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.notIncluded\"></small>\r\n          </div>\r\n          <div ng-if=\"ruleSetRow.isIncluded\">\r\n            <div class=\"input-group\">\r\n              <input type=\"text\" class=\"form-control\" ng-value=\"$ctrl.getAccount(ruleSetRow.debitId).account + ' ' + $ctrl.getAccount(ruleSetRow.debitId).text\" disabled=\"true\">\r\n              <span class=\"input-group-btn\">\r\n                  <button class=\"btn btn-default fixed-width-addon\" type=\"button\" ng-click=\"$ctrl.selectAccount(ruleSetRow, false)\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.changeAccountBtn\"></button>\r\n                </span>\r\n            </div>\r\n            <div class=\"input-group\">\r\n              <input type=\"text\" class=\"form-control\" ng-init=\"ruleSetRow.debitGroupingTemp = ruleSetRow.debitGrouping\" ng-model=\"ruleSetRow.debitGroupingTemp\" placeholder=\"{{'SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.addGrouping' | sxyTranslate}}\">\r\n              <span class=\"input-group-btn\">\r\n                  <button class=\"btn btn-default fixed-width-addon\" type=\"button\" ng-click=\"ruleSetRow.debitGrouping = ruleSetRow.debitGroupingTemp\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.changeGroupingBtn\"></button>\r\n                </span>\r\n            </div>\r\n          </div>\r\n        </td>\r\n        <td>\r\n          <div ng-if=\"!ruleSetRow.isIncluded\">\r\n            <small sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.notIncluded\"></small>\r\n          </div>\r\n          <div ng-if=\"ruleSetRow.isIncluded\">\r\n            <div class=\"input-group\">\r\n              <input type=\"text\" class=\"form-control\" ng-value=\"$ctrl.getAccount(ruleSetRow.creditId).account + ' ' + $ctrl.getAccount(ruleSetRow.creditId).text\" disabled=\"true\">\r\n              <span class=\"input-group-btn\">\r\n                  <button class=\"btn btn-default fixed-width-addon\" type=\"button\" ng-click=\"$ctrl.selectAccount(ruleSetRow, true)\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.changeAccountBtn\"></button>\r\n                </span>\r\n            </div>\r\n            <div class=\"input-group\">\r\n              <input type=\"text\" class=\"form-control\" ng-init=\"ruleSetRow.creditGroupingTemp = ruleSetRow.creditGrouping\" ng-model=\"ruleSetRow.creditGroupingTemp\" placeholder=\"{{'SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.addGrouping' | sxyTranslate}}\">\r\n              <span class=\"input-group-btn\">\r\n                  <button class=\"btn btn-default fixed-width-addon\" type=\"button\" ng-click=\"ruleSetRow.creditGrouping = ruleSetRow.creditGroupingTemp\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.changeGroupingBtn\"></button>\r\n                </span>\r\n            </div>\r\n          </div>\r\n        </td>\r\n        <td>\r\n          <button title=\"{{'SALAXY.UI_Terms.change' | sxyTranslate}}\" class=\"btn btn-default fixed-width-button\" type=\"button\" ng-click=\"$ctrl.selectEntry(ruleSetRow)\">\r\n            <span sxy-text=\"SALAXY.UI_Terms.change\"></span> {{ ruleSetRow.entryCodeGroup == 'incomeType' ? ('SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.incomeTypeBtnPS' | sxyTranslate) : ('SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.calcRowBtnPS' | sxyTranslate) }}\r\n            </button>\r\n          <button title=\"{{'SALAXY.UI_Terms.edit' | sxyTranslate}}\" class=\"btn btn-default fixed-width-button\" type=\"button\" ng-click=\"$ctrl.selectFlags(ruleSetRow)\" sxy-text=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.editAdditionalsBtn\"></button>\r\n        </td>\r\n        <td>\r\n          <salaxy-input-boolean type=\"checkbox\" name=\"{{'ruleSetIsIncluded'+$index}}\" ng-model=\"ruleSetRow.isIncluded\" label-type=\"plain\" label-true=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.includeHead\">\r\n          </salaxy-input-boolean>\r\n          <salaxy-input-boolean type=\"checkbox\" name=\"{{'ruleSetEnabled'+$index}}\" ng-model=\"ruleSetRow.enabled\" label-type=\"plain\" label-true=\"SALAXY.NG1.AccountingTargetDetailsComponent.rulesTables.enabledHead\"></salaxy-input-boolean>\r\n          <button title=\"{{'SALAXY.UI_Terms.deleteRow' | sxyTranslate}}\" ng-disabled=\"ruleSetRow.isReadOnly\" class=\"btn btn-danger btn-sm\" type=\"button\" ng-click=\"$ctrl.removeRow(ruleSetRow)\">\r\n              Poista rivi\r\n            </button>\r\n        </td>\r\n      </tr>\r\n      <tr ng-repeat-end>\r\n\r\n      </tr>\r\n      <tr ng-repeat-end></tr>\r\n      <tr>\r\n        <td></td>\r\n        <td></td>\r\n        <td></td>\r\n        <td></td>\r\n        <td class=\"right\">\r\n          <button ng-disabled=\"true\" title=\"{{'SALAXY.UI_Terms.addRow' | sxyTranslate}}\" class=\"btn btn-primary btn-sm\" type=\"button\" ng-click=\"$ctrl.addRow(null)\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/settings/AccountingTargetSettings.html\",`<div class=\"content settings\" ng-if=\"$ctrl.current\">\r\n  <div class=\"card accounting-target-settings card-default\">\r\n    <sxy-form open-api=\"salaxy-secure/schemas/v02.json\" type=\"CompanyAccountSettings\" auto-gen=\"false\" debugger=\"false\" model=\"$ctrl.current\">\r\n      <div class=\"card-header icon-card\">\r\n        <h2 sxy-text=\"SALAXY.NG1.AccountingTargetSettings.title\"></h2>\r\n        <p ng-if=\"!(!$ctrl.current.accounting.denyServiceModel  && $ctrl.current.partner.serviceModel.features.accounting)\"><small sxy-text=\"SALAXY.NG1.AccountingTargetSettings.intro\"></small></p>\r\n      </div>\r\n      <div class=\"card-body\">\r\n        <fieldset>\r\n          <legend><span sxy-text=\"SALAXY.NG1.AccountingTargetSettings.accountingLegend\"></span></legend>\r\n          <salaxy-input-typeahead name=\"options_type\" ng-model=\"$ctrl.current.accounting.defaultTargetId\" options=\"$ctrl.getSelectableAccountingTargets()\"\r\n            disable-cache=\"true\" label=\"SALAXY.NG1.AccountingTargetSettings.defaultTarget\"></salaxy-input-typeahead>\r\n          <sxy-input template-url=\"salaxy-components/sxy-form/custom-templates/array-accounting-targets.html\" model=\"form.accounting.targets\" read-only=\"{{!$ctrl.current.accounting.denyServiceModel && $ctrl.current.partner.serviceModel.features.accounting}}\">\r\n            <form>\r\n              <fieldset ng-show=\"!$ctrl.logic.showDelete\" ng-controller=\"CompanySettingsController as $companySettingsCtrl\" ng-init=\"$ctrl.logic.isReadOnly = true\">\r\n                <salaxy-odata-table  crud-controller=\"AccountingTargetCrudController as $crud\" template-url=\"salaxy-components/odata/lists/AccountingTargetSelect.html\" selected-items=\"$ctrl.selectedItems\" on-list-select=\"$companySettingsCtrl.onAccountingTargetSelect($ctrl.current, $ctrl.logic, value, item, allItems)\">\r\n                </salaxy-odata-table>\r\n              </fieldset>\r\n              <fieldset ng-show=\"$ctrl.logic.showDelete\" ng-init=\"$ctrl.logic.isReadOnly = false\">\r\n                <salaxy-input-enum disabled=\"false\" name=\"format\" label=\"SALAXY.NG1.AccountingTargetDetailsComponent.excelCsvFormat\" ng-model=\"$ctrl.current.format\"\r\n                options=\"{\r\n                  '36dff2e2-e181-4f0d-9004-0e4aa92f5e17': 'Palkkaus.fi',\r\n                  '0db4e85f-93a8-46f1-b6d2-f7523d289d88': 'Fennoa',\r\n                  '8613f133-3fce-4611-b372-51f6a2e007dd': 'Procountor',\r\n                  'e62c10b0-222a-4170-b8b4-b1e02d9a7644': 'Passeli Merit',\r\n                  '53fd3863-b8f9-4909-86c9-cb4597595181': 'Heeros',\r\n                  '2fc7899c-7a3d-4d56-ad2f-05d52782bbbc': 'Asteri',\r\n                  '0a2bd312-06da-4862-aef5-75166e0bf461': 'Maestro',\r\n                  'c04e0757-63f3-420d-a183-3427710fc954': 'Visma Fivaldi',\r\n                  'ba271dac-dd63-4036-9d70-053a09ca4d9e' :'Visma Netvisor',\r\n                  '27e271d5-41f5-4319-ab29-4d5d9eb945c6': 'Lemonsoft',\r\n                  'd311f9d3-8c3a-4fd8-a665-8e3698e41e87': 'Tampuuri',\r\n                  'd58e95b7-d0b5-40ac-992b-6d3b29efc45e': 'Domus',\r\n                  '54e93c5f-bd74-4157-8a74-3515be7f585d': 'Oscar Software',\r\n                  '0e4f0a71-dcb9-43ba-9028-0239e674711f': 'Digia Enterprise',\r\n                  '2ccefa46-7992-46c5-9d87-b88336935916': 'Digia Enterprise - VILPE',\r\n                  'c36c24b9-5e2c-4f44-b67a-90d81aeea257': 'iScala'\r\n                }\">\r\n                </salaxy-input-enum>\r\n                <sxy-input model=\"form.method\" read-only=\"false\"></sxy-input>\r\n                <salaxy-input-enum disabled=\"false\" enum=\"ExportMethod\" label=\"SALAXY.MODEL.AccountingTargetSettings.availableMethods.title\" name=\"availableMethods\" type=\"multi-select\" ng-model=\"$ctrl.current.availableMethods\"></salaxy-input-enum>\r\n              </fieldset>\r\n            </form>\r\n          </sxy-input>\r\n          <sxy-input model=\"form.accounting.defaultPeriodDateKind\" read-only=\"{{!$ctrl.current.accounting.denyServiceModel  && $ctrl.current.partner.serviceModel.features.accounting}}\"></sxy-input>\r\n        </fieldset>\r\n      </div>\r\n      <div class=\"card-footer\">\r\n        <div class=\"row\">\r\n          <div class=\"col-12 text-end\">\r\n            <button class=\"btn btn-primary\" ng-click=\"$ctrl.save('all')\" ng-disabled=\"$ctrl.isSaving('all')\"><span ng-if=\"$ctrl.isSaving('all')\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span> <span sxy-text=\"SALAXY.UI_Terms.save\"></span></button>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </sxy-form>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/settings/CostAccountingSettings.html\",`<div class=\"content settings\" ng-if=\"$ctrl.current\">\r\n  <div class=\"card mb-4 costAccounting card-secondary\">\r\n    <div>\r\n      <div class=\"card-header\">\r\n        <h2 sxy-text=\"SALAXY.MODEL.CostAccountingSettings.title\"></h2>\r\n        <p><small sxy-text=\"SALAXY.MODEL.CostAccountingSettings.descr\"></small></p>\r\n      </div>\r\n      <div class=\"card-body\">\r\n        <div class=\"row\">\r\n\r\n          <sxy-form open-api=\"salaxy-secure/schemas/v02.json\" type=\"CompanyAccountSettings\" auto-gen=\"false\" debugger=\"false\" model=\"$ctrl.current\"\r\n            read-only=\"{{(!$ctrl.current.costAccounting.denyServiceModel && $ctrl.current.partner.serviceModel.features.costAccounting) || $ctrl.isReadOnlyForced}}\">\r\n            \r\n            <div class=\"col form-horizontal\">\r\n              \r\n              <sxy-input model=\"form.costAccounting.dimensions\" include=\"id,label,scope\">\r\n                <form>\r\n                  <fieldset>\r\n                    <legend sxy-text=\"SALAXY.MODEL.CostAccountingDimensionDefinition.title\"></legend>\r\n                    <sxy-input model=\"form.id\" read-only=\"{{$ctrl.logic.showDelete}}\"></sxy-input>\r\n                    <sxy-input model=\"form.label\"></sxy-input>\r\n                    <sxy-input model=\"form.allowCostSharing\"></sxy-input>\r\n                    <sxy-input model=\"form.scope\"></sxy-input>\r\n                    <sxy-input model=\"form.options\" template-url=\"salaxy-components/sxy-form/custom-templates/cost-accounting-options.html\"></sxy-input>\r\n                  </fieldset>\r\n                </form>\r\n              </sxy-input> \r\n              \r\n            </div>\r\n          </sxy-form>\r\n        </div>\r\n      </div>\r\n      <div class=\"card-footer\">\r\n        <div class=\"row\">\r\n          <div class=\"col\">\r\n            <button type=\"submit\" ng-disabled=\"(!$ctrl.current.costAccounting.denyServiceModel && $ctrl.current.partner.serviceModel.features.costAccounting) ||$ctrl.isSaving('all')\" class=\"btn btn-primary float-end\" ng-click=\"$ctrl.save('all')\"><span ng-if=\"$ctrl.isSaving('all')\"><i\r\n                  class=\"bi bi-arrow-repeat bi-spin\"></i></span> <span sxy-text=\"SALAXY.UI_Terms.save\"></span></button>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/settings/HolidaySettings.html\",`<div class=\"content settings\" ng-if=\"$ctrl.current\">\r\n  <div class=\"card mb-4 accounting card-secondary\">\r\n    <div>\r\n      <div class=\"card-header icon-card\">\r\n        <h2 sxy-text=\"SALAXY.MODEL.HolidaySettings.title\"></h2>\r\n      </div>\r\n      <div class=\"card-body\">\r\n        <div class=\"row\">\r\n          <sxy-form ng-ref=\"$frm\" open-api=\"salaxy-secure/schemas/v02.json\" type=\"CompanyAccountSettings\" auto-gen=\"false\" debugger=\"false\" model=\"$ctrl.current\" read-only=\"{{!$ctrl.current.holiday.denyServiceModel  && $ctrl.current.partner.serviceModel.features.holiday}}\">\r\n            <div>\r\n              <sxy-input model=\"form.partner.serviceModel.features.holiday\" label=\"SALAXY.NG1.ProSettingsComponent.customHoliday\" read-only=\"true\"></sxy-input>\r\n              <salaxy-input-boolean label=\"SALAXY.NG1.ProSettingsComponent.overwriteServiceModel\" name=\"uc6\" ng-change=\"$ctrl.confirmServiceModelChange()\"\r\n                ng-if=\"$ctrl.current.partner.serviceModel.features.holiday\" ng-model=\"$ctrl.current.holiday.denyServiceModel\"></salaxy-input-boolean>\r\n              <sxy-input model=\"form.holiday.holidayPaySettings\"\r\n                read-only=\"{{!$ctrl.current.holiday.denyServiceModel  && $ctrl.current.partner.serviceModel.features.holiday }}\" include=\"holidayPayCalculation\">\r\n                <form>\r\n                  <fieldset>\r\n                    <legend sxy-text=\"SALAXY.MODEL.HolidayPaySettings.title\"></legend>\r\n                    <salaxy-input-enum ng-show=\"!('bizConfigs' | sxyIsInRole)\" enum=\"HolidayPayCalculation\" label=\"SALAXY.MODEL.HolidayPaySettings.holidayPayCalculation.title\" name=\"holidayPayCalculation\" filter=\"averageDailyPay,averageHourlyPay,percentageBasedPay,holidayCompensation\" require=\"true\" ng-model=\"$ctrl.current.holidayPayCalculation\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-enum>\r\n                    <salaxy-input-enum ng-show=\"'bizConfigs' | sxyIsInRole\" enum=\"HolidayPayCalculation\" label=\"SALAXY.MODEL.HolidayPaySettings.holidayPayCalculation.title\" name=\"holidayPayCalculation\" filter=\"averageDailyPay,averageHourlyPay,percentageBasedPay,holidayCompensation,scriptPay\" require=\"true\" ng-model=\"$ctrl.current.holidayPayCalculation\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-enum>\r\n                    <salaxy-input-collective-bargain-agreement ng-show=\"'bizConfigs' | sxyIsInRole\" name=\"cbaCode\" ng-model=\"$ctrl.current.cbaCode\" label=\"SALAXY.MODEL.HolidayPaySettings.cbaCode.title\"></salaxy-input-collective-bargain-agreement>\r\n                    <salaxy-input-employee-group ng-show=\"'bizConfigs' | sxyIsInRole\" name=\"employeeGroup\" ng-model=\"$ctrl.current.employeeGroup\" label=\"SALAXY.MODEL.HolidayPaySettings.employeeGroup.title\"></salaxy-input-employee-group>\r\n                    <sxy-input model=\"form.disabled\"></sxy-input>\r\n                    <sxy-input model=\"form.startYear\" label=\"SALAXY.MODEL.HolidayPaySettings.startYear.title\"></sxy-input>  \r\n                    <sxy-input model=\"form.endYear\" label=\"SALAXY.MODEL.HolidayPaySettings.endYear.title\"></sxy-input>                   \r\n                    <legend ng-show=\"$ctrl.current.holidayPayCalculation && $ctrl.current.holidayPayCalculation != 'scriptPay'\" sxy-text=\"SALAXY.MODEL.HolidayPaySettings.salaryTypes.title\"></legend>\r\n                    <sxy-input  ng-show=\"$ctrl.current.holidayPayCalculation && $ctrl.current.holidayPayCalculation != 'scriptPay'\" model=\"form.salaryTypes\" template-url=\"salaxy-components/sxy-form/custom-templates/pay-stats-row-types.html\"></sxy-input>\r\n                    <legend ng-show=\"$ctrl.current.holidayPayCalculation == 'averageHourlyPay'\" sxy-text=\"SALAXY.MODEL.HolidayPaySettings.workingTimeTypes.title\"></legend>\r\n                    <sxy-input ng-show=\"$ctrl.current.holidayPayCalculation == 'averageHourlyPay'\" model=\"form.workingTimeTypes\" template-url=\"salaxy-components/sxy-form/custom-templates/pay-stats-row-types.html\"></sxy-input>\r\n                    <legend ng-show=\"$ctrl.current.holidayPayCalculation == 'averageDailyPay'\" sxy-text=\"SALAXY.MODEL.HolidayPaySettings.overtimeTypes.title\"></legend>\r\n                    <sxy-input  ng-show=\"$ctrl.current.holidayPayCalculation == 'averageDailyPay'\" model=\"form.overtimeTypes\" template-url=\"salaxy-components/sxy-form/custom-templates/pay-stats-row-types.html\"></sxy-input>\r\n                    <legend ng-show=\"$ctrl.current.holidayPayCalculation == 'averageHourlyPay' || $ctrl.current.holidayPayCalculation == 'averageDailyPay'\" sxy-text=\"SALAXY.MODEL.HolidayPaySettings.multipliers.title\"></legend>\r\n                    <salaxy-input-holiday-multipliers ng-show=\"$ctrl.current.holidayPayCalculation == 'averageHourlyPay' || $ctrl.current.holidayPayCalculation == 'averageDailyPay'\" name=\"multipliers\" label=\"SALAXY.MODEL.HolidayPaySettings.multipliers.title\" ng-model=\"$ctrl.current.multipliers\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-holiday-multipliers>\r\n                    <sxy-code-editor ng-show=\"$ctrl.current.holidayPayCalculation == 'scriptPay'\" ng-model=\"$ctrl.current.script\"></sxy-code-editor>\r\n                  </fieldset>\r\n                </form>\r\n              </sxy-input>\r\n              <sxy-input model=\"form.holiday.holidayAccrualSettings\"\r\n                read-only=\"{{!$ctrl.current.holiday.denyServiceModel  && $ctrl.current.partner.serviceModel.features.holiday }}\" include=\"code\">\r\n                <form>\r\n                  <fieldset>\r\n                    <legend sxy-text=\"SALAXY.MODEL.HolidayAccrualSettings.title\"></legend>\r\n                    <salaxy-input-enum ng-show=\"!('bizConfigs' | sxyIsInRole)\" enum=\"HolidayCode\" label=\"SALAXY.MODEL.HolidayAccrualSettings.code.title\" name=\"code\" filter=\"permanent35Hours\" require=\"true\" ng-model=\"$ctrl.current.code\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-enum>\r\n                    <salaxy-input-enum  ng-show=\"'bizConfigs' | sxyIsInRole\" enum=\"HolidayCode\" label=\"SALAXY.MODEL.HolidayAccrualSettings.code.title\" name=\"code\" filter=\"permanent35Hours,script\" require=\"true\" ng-model=\"$ctrl.current.code\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-enum>\r\n                    <salaxy-input-collective-bargain-agreement ng-show=\"'bizConfigs' | sxyIsInRole\" name=\"cbaCode\" ng-model=\"$ctrl.current.cbaCode\" label=\"SALAXY.MODEL.HolidayAccrualSettings.cbaCode.title\"></salaxy-input-collective-bargain-agreement>\r\n                    <salaxy-input-employee-group ng-show=\"'bizConfigs' | sxyIsInRole\" name=\"employeeGroup\" ng-model=\"$ctrl.current.employeeGroup\" label=\"SALAXY.MODEL.HolidayAccrualSettings.employeeGroup.title\"></salaxy-input-employee-group>\r\n                    <sxy-input model=\"form.disabled\"></sxy-input>\r\n                    <sxy-input model=\"form.startYear\" label=\"SALAXY.MODEL.HolidayAccrualSettings.startYear.title\"></sxy-input>  \r\n                    <sxy-input model=\"form.endYear\" label=\"SALAXY.MODEL.HolidayAccrualSettings.endYear.title\"></sxy-input>  \r\n                    <legend ng-show=\"$ctrl.current.code == 'permanent35Hours'\" sxy-text=\"SALAXY.MODEL.HolidayAccrualSettings.workingTimeTypes.title\"></legend>\r\n                    <sxy-input ng-show=\"$ctrl.current.code == 'permanent35Hours'\" model=\"form.workingTimeTypes\" template-url=\"salaxy-components/sxy-form/custom-templates/pay-stats-row-types.html\"></sxy-input>\r\n                    <sxy-code-editor  ng-show=\"$ctrl.current.code == 'script'\" ng-model=\"$ctrl.current.script\"></sxy-code-editor>\r\n                  </fieldset>\r\n                </form>\r\n              </sxy-input>\r\n            </div>\r\n           \r\n          </sxy-form>\r\n        </div>\r\n      </div>\r\n      <div class=\"card-footer\">\r\n        <div class=\"row\">\r\n          <div class=\"col-xs-12\">\r\n            <button type=\"submit\" ng-disabled=\"(!$ctrl.current.holiday.denyServiceModel && $ctrl.current.partner.serviceModel.features.holiday) || !$frm.ngForm.$valid || $ctrl.isSaving('all')\" class=\"btn btn-primary pull-right\" ng-click=\"$ctrl.save('all')\">\r\n              <span ng-if=\"$ctrl.isSaving('all')\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span>\r\n              <span sxy-text=\"SALAXY.UI_Terms.save\"></span>\r\n            </button>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/settings/Insurances.html\",`<div class=\"content settings\" ng-if=\"$ctrl.current\" ng-controller=\"VarmaBannerController as $varma\">\r\n  <div class=\"card pension card-secondary my-4\" ng-repeat=\"item in $ctrl.pensionContracts\" ng-if=\"$ctrl.sections.indexOf('pensionContracts') >= 0 && $ctrl.isVisibleContract(item, $ctrl.pensionContracts)\">\r\n    <form name=\"pensionForm\" class=\"pension-form\" ng-readonly=\"$ctrl.isReadOnlyForced\">\r\n      <div class=\"card-header d-flex\">\r\n        <div class=\"flex-grow-1 pe-5\">\r\n          <h2 sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.pension.title\"></h2>\r\n          <p><small sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.pension.description\"></small></p>\r\n        </div>\r\n        <i class=\"bi bi-check-circle-fill text-success status-icon fs-1 d-block\"></i>\r\n      </div>\r\n      <div class=\"card-body\">\r\n        <div class=\"row\">\r\n          <div class=\"col-sm-6 col-12\">\r\n            <div class=\"form-horizontal\">\r\n              <fieldset>\r\n                <legend sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.pension.currentContractLegend\"></legend>\r\n                <salaxy-input-enum ng-model=\"item.company\" type=\"select\" label=\"SALAXY.MODEL.PensionContract.company.editLabel\" name=\"pensionCompany\" enum=\"PensionCompany\" filter=\"none,varma,elo,ilmarinen,veritas,apteekkien,verso,valio,kevaMunicipal,kevaAland,kevaChurch,kevaKela,kevaState\" require=\"true\" ng-change=\"item.contractNumber = null\"></salaxy-input-enum>\r\n                <main salaxy-if-role=\"test\" class=\"test-number\">\r\n                  <div class=\"form-group\" ng-if=\"item.company && item.company != 'none'\">\r\n                    <div class=\"col-sm-8 offset-sm-4 text-sm-end\">\r\n                      <span>Test only: <button class=\"btn btn-secondary btn-xs\" ng-click=\"$ctrl.setPensionNumberForTest(item)\"> Generoi numero </button></span>\r\n                    </div>\r\n                  </div>\r\n                </main>\r\n                <salaxy-input ng-if=\"item.company && item.company != 'none'\" require=\"true\" name=\"pensionContractNumber\" label=\"SALAXY.MODEL.PensionContract.contractNumber.title\" ng-model=\"item.contractNumber\" tooltip-html=\"{{'SALAXY.NG1.InsuranceSettingsComponent.pension.errors.sxyPensionContractNumber.html' | sxyTranslate}}\"\r\n                  tooltip-placement=\"right\" sxy-pension-contract-number=\"item.company\"></salaxy-input>\r\n                <div class=\"row\" ng-show=\"pensionForm.pensionContractNumber.$error.sxyTemporaryPensionContractNumber\">\r\n                  <div class=\"col-12 offset-sm-4 input-info text-danger\">\r\n                    <div class=\"input-info-icon\"><i class=\"bi bi-exclamation-triangle-fill\"></i></div>\r\n                    <p class=\"small input-info-text with-icon\" sxy-html=\"SALAXY.NG1.InsuranceSettingsComponent.pension.errors.sxyTemporaryPensionContractNumber.html\"></p>\r\n                  </div>\r\n                </div>\r\n                <salaxy-input-number disabled=\"true\" ng-if=\"(item.company && item.company != 'none')\" unit=\"percent\" ng-model=\"item.pensionDefaultPercent\" name=\"pensionDefaultPercent\" label=\"SALAXY.MODEL.PensionContract.pensionDefaultPercent.title\"></salaxy-input-number>\r\n                <salaxy-input-number disabled=\"!('admin,pro' | sxyIsInRole)\" ng-if=\"(item.company && item.company != 'none') && (('admin,pro' | sxyIsInRole) || item.pensionPercent)\" unit=\"percent\" ng-model=\"item.pensionPercent\" name=\"pensionPercent\" label=\"SALAXY.MODEL.PensionContract.pensionPercent.title\"></salaxy-input-number>\r\n              </fieldset>\r\n            </div>\r\n          </div>\r\n          <div class=\"col-sm-6 col-12\" ng-show=\"item.company && item.company != 'none' && item.company != 'varma'\">\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.pension.moveContractLegend\"></legend>\r\n              <p sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.pension.moveContractDescription\"></p>\r\n              <div>\r\n                <a ng-href=\"{{$varma.getVarmaShopLink()}}\" target=\"_blank\" class=\"btn btn-primary\" sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.pension.moveContractCta\"></a>\r\n              </div>\r\n            </fieldset>\r\n          </div>\r\n        </div>\r\n        <div class=\"row\">\r\n          <div class=\"col-sm-6 col-12\" ng-show=\"!item.company || item.company == 'none'\">\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.pension.varmaLegend\"></legend>\r\n              <p sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.pension.varmaDescription\"></p>\r\n              <div>\r\n                <a ng-href=\"{{$varma.getVarmaShopLink()}}\" target=\"_blank\" class=\"btn btn-primary\" sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.pension.varmaCta\"></a>\r\n              </div>\r\n            </fieldset>\r\n          </div>\r\n          <div class=\"col-sm-6 col-12\" ng-show=\"!item.company || item.company == 'none'\">\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.pension.temporaryLegend\"></legend>\r\n              <p sxy-html=\"SALAXY.NG1.InsuranceSettingsComponent.pension.temporaryDescription.html\"></p>\r\n            </fieldset>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div class=\"card-footer\">\r\n        <div class=\"row\">\r\n          <div class=\"col-12\">\r\n            <button ng-if=\"!$ctrl.isReadOnlyForced\" ng-disabled=\"!item.company || pensionForm.$invalid || $ctrl.isSaving('pensionContracts')\" class=\"btn btn-primary float-end\" ng-click=\"$ctrl.save('pensionContracts')\"><span ng-if=\"$ctrl.isSaving('pensionContracts')\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span> <span sxy-text=\"SALAXY.UI_Terms.save\"></span></button>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </form>\r\n  </div>\r\n  <div class=\"card pension yel-pension card-secondary mb-4\" ng-if=\"$ctrl.sections.indexOf('yelPensionContracts') >= 0\">\r\n    <div class=\"card-header\">\r\n      <h2 sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.yelPension.title\"></h2>\r\n    </div>\r\n    <div class=\"card-body\">\r\n      <p sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.yelPension.description\"></p>\r\n    </div>\r\n    <div class=\"card-footer text-end\">\r\n      <a class=\"btn btn-primary\" ng-href=\"{{$varma.getVarmaShopLink()}}\" target=\"_blank\" sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.yelPension.takeInsuranceBtn\"></a>\r\n    </div>\r\n  </div>\r\n  <div class=\"card insurance card-secondary mb-4\" ng-repeat=\"item in $ctrl.insuranceContracts\" ng-if=\"$ctrl.sections.indexOf('insuranceContracts') >= 0 && $ctrl.isVisibleContract(item, $ctrl.insuranceContracts)\">\r\n    <form ng-if=\"item.status != 'pending'\" name=\"insuranceForm\" class=\"insurance-form\" ng-readonly=\"$ctrl.isReadOnlyForced\">\r\n      <div class=\"card-header d-flex\">\r\n        <div class=\"flex-grow-1 pe-5\">\r\n          <h2 sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.insurance.title\"></h2>\r\n          <p><small sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.insurance.description\"></small></p>\r\n        </div>\r\n        <i class=\"bi bi-check-circle-fill text-success status-icon fs-1 d-block\"></i>\r\n      </div>\r\n      <div class=\"card-body\">\r\n        <div class=\"row\">\r\n          <div class=\"col-sm-6 col-12\">\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.insurance.currentContractLegend\"></legend>\r\n              <div class=\"form-horizontal\">\r\n                <salaxy-input-enum ng-model=\"item.company\" type=\"select\" enum=\"InsuranceCompany\" filter=\"none,fennia,if,lähiTapiola,pohjantähti,pohjola,turva,aVakuutus,folksam,alandia,ålands,protector\" label=\"SALAXY.MODEL.InsuranceContract.company.editLabel\" name=\"insurance-company\"\r\n                  require=\"true\"></salaxy-input-enum>\r\n              </div>\r\n              <div class=\"form-horizontal\" ng-if=\"item.company && item.company != 'none'\">\r\n                <salaxy-input ng-model=\"item.contractNumber\" require=\"true\" name=\"insuranceContractNumber\" label=\"SALAXY.MODEL.InsuranceContract.contractNumber.title\"></salaxy-input>\r\n              </div>\r\n              <div class=\"form-horizontal\" ng-if=\"item.company\">\r\n                <salaxy-input-number unit=\"percent\" tooltip-html=\"{{'SALAXY.MODEL.InsuranceContract.insurancePercent.descr' | sxyTranslate}}\" ng-model=\"item.insurancePercent\" name=\"insurancePercent\" label=\"SALAXY.MODEL.InsuranceContract.insurancePercent.title\"></salaxy-input-number>\r\n              </div>\r\n              <div class=\"form-horizontal\" ng-if=\"item.company\">\r\n                <salaxy-input-number unit=\"percent\" tooltip-html=\"{{'SALAXY.MODEL.InsuranceContract.groupLifeInsurancePercent.descr' | sxyTranslate}}\" ng-model=\"item.groupLifeInsurancePercent\" name=\"groupLifeInsurancePercent\" label=\"SALAXY.MODEL.InsuranceContract.groupLifeInsurancePercent.title\"></salaxy-input-number>\r\n              </div>\r\n            </fieldset>\r\n          </div>\r\n          <div class=\"col-sm-6 col-12\" ng-if=\"!$ctrl.isReadOnlyForced\">\r\n            <fieldset ng-show=\"item.company && item.company != 'lähiTapiola' && item.company != 'none' \">\r\n              <legend sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.insurance.moveToLocalTapiolaLegend\"></legend>\r\n              <div ng-controller=\"InsuranceWizardController as insuranceCtrl\">\r\n                <button class=\"btn btn-primary\" ng-click=\"insuranceCtrl.openModal();\" sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.insurance.moveToLocalTapiolaBtn\"></button>\r\n              </div>\r\n            </fieldset>\r\n            <fieldset ng-if=\"item.company == 'none' || !item.company\">\r\n              <legend sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.insurance.takeFromLocalTapiolaLegend\"></legend>\r\n              <div ng-controller=\"InsuranceWizardController as insuranceCtrl\">\r\n                <button class=\"btn btn-primary\" ng-click=\"insuranceCtrl.openModal();\" sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.insurance.takeFromLocalTapiolaBtn\"></button>\r\n              </div>\r\n            </fieldset>\r\n          </div>\r\n        </div>\r\n        <div class=\"row\" style=\"margin-top:10px;\">\r\n          <div class=\"col-12 settings-alert\">\r\n            <div ng-if=\"item.company && item.company != 'none'\">\r\n              <div class=\"float-start\">\r\n                <i class=\"bi bi-info-circle-fill alert-icon text-info icon-info\"></i>\r\n              </div>\r\n              <div class=\"alert-text\">\r\n                <p class=\"text-info \" sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.insurance.insuranceComment\"></p>\r\n              </div>\r\n            </div>\r\n            <div ng-if=\"item.company == 'none'\">\r\n              <div class=\"float-start\">\r\n                <i class=\"bi bi-exclamation-lg alert-icon d-flex align-items-center justify-content-center text-danger icon-danger\"></i>\r\n              </div>\r\n              <div class=\"alert-text\">\r\n                <p class=\"text-danger\" sxy-text=\"SALAXY.NG1.InsuranceSettingsComponent.insurance.warning\"></p>\r\n              </div>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div class=\"card-footer\">\r\n        <div class=\"row\">\r\n          <div class=\"col-12\">\r\n            <button ng-if=\"!$ctrl.isReadOnlyForced\" ng-disabled=\"!item.company || $ctrl.isSaving('insuranceContracts')\" class=\"btn btn-primary float-end\" ng-click=\"$ctrl.save('insuranceContracts')\"><span ng-if=\"$ctrl.isSaving('insuranceContracts')\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span> <span sxy-text=\"SALAXY.UI_Terms.save\"></span></button>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </form>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/settings/IrDeliverySettings.html\",`<div class=\"content settings\" ng-if=\"$ctrl.current\">\r\n  <div class=\"card ir-delivery card-secondary mb-4\">\r\n    <div class=\"card-header icon-card\">\r\n      <h2 sxy-text=\"Tulorekisteriraportoinnissa käytettävä varmenne\"></h2>\r\n    </div>\r\n    <div class=\"card-body\">\r\n      <div class=\"row\">\r\n        <ng-form name=\"$frmDelivery\" class=\"form-horizontal\">\r\n          <div>\r\n            <fieldset>\r\n              <legend>Tulorekisterivarmenteen omistaja</legend>\r\n              <p\r\n                sxy-text=\"Jos haluat käyttää tilitoimistovarmennetta Palkkaus.fi:n varmenteen sijasta, anna käytettävän varmenteen Y-tunnus.\">\r\n              </p>\r\n              <salaxy-input label=\"Tulorekisterivarmenteen omistajan Y-tunnus\" name=\"senderOfficialId\"\r\n                ng-model=\"$ctrl.current.calc.incomesRegister.irDelivery.senderOfficialId\"></salaxy-input>\r\n            </fieldset>\r\n            <fieldset>\r\n              <legend>Tulorekisteriraportin yhteyshenkilöt</legend>\r\n              <table class=\"table\">\r\n                <thead>\r\n                  <tr>\r\n                    <th>{{('Nimi') | sxyTranslate}}</th>\r\n                    <th>{{('Puhelin') | sxyTranslate}}</th>\r\n                    <th>{{('Sähköposti') | sxyTranslate}}</th>\r\n                    <th>{{('Vastuualue') | sxyTranslate}}</th>\r\n                    <th class=\"right\">\r\n                      <button type=\"button\" class=\"btn btn-primary btn-xs\"\r\n                        ng-click=\"$ctrl.current.calc.incomesRegister.irDelivery.contactPersons.push({})\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n                    </th>\r\n                  </tr>\r\n                </thead>\r\n                <tbody>\r\n                  <tr ng-repeat=\"item in $ctrl.current.calc.incomesRegister.irDelivery.contactPersons\">\r\n                    <td>\r\n                      <salaxy-input require=\"true\" ng-model=\"item.name\" name=\"{{ 'name' + $index }}\" label-type=\"plain\"></salaxy-input>\r\n                    </td>\r\n                    <td>\r\n                      <salaxy-input require=\"true\" ng-model=\"item.telephone\" name=\"{{ 'telephone' + $index }}\" label-type=\"plain\" sxy-mobile-phone></salaxy-input>\r\n                    </td>\r\n                    <td>\r\n                      <salaxy-input require=\"true\" ng-model=\"item.email\" name=\"{{ 'email' + $index }}\" label-type=\"plain\" sxy-email></salaxy-input>\r\n                    </td>\r\n                    <td>\r\n                      <salaxy-input-enum require=\"true\" ng-model=\"item.responsibilityCode\" name=\"{{ 'responsibilityCode' + $index }}\" label-type=\"plain\" type=\"select\"\r\n                        options=\"{ contentIssues: 'Raporttien sisältö', technicalIssues: 'Tekniset asiat' }\"></salaxy-input-enum>\r\n                    </td>\r\n                    <td class=\"text-right\">\r\n                      <button type=\"button\" class=\"btn btn-danger\" ng-click=\"$ctrl.current.calc.incomesRegister.irDelivery.contactPersons.splice($index, 1)\">\r\n                        <i class=\"bi bi-trash\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\"></i>\r\n                      </button>\r\n                    </td>\r\n                  </tr>\r\n                </tbody>\r\n              </table>\r\n            </fieldset>\r\n          </div>\r\n        </ng-form>\r\n      </div>\r\n    </div>\r\n    <div class=\"card-footer\">\r\n      <div class=\"row\">\r\n        <div class=\"col-xs-12 text-right\">\r\n          <button type=\"submit\" ng-disabled=\"!$frmDelivery.$valid || ($ctrl.current.calc.incomesRegister.irDelivery.senderOfficialId && !$ctrl.current.calc.incomesRegister.irDelivery.contactPersons[0].responsibilityCode ) || $ctrl.isSaving('all')\"\r\n            class=\"btn btn-primary\" ng-click=\"$ctrl.save('all')\">\r\n            <span ng-if=\"$ctrl.isSaving('all')\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span>\r\n            <span sxy-text=\"SALAXY.UI_Terms.save\"></span>\r\n          </button>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div class=\"card ir-certificate-actions card-secondary\" ng-if=\"$ctrl.hasOwnIrCertificate()\">\r\n    <div class=\"card-header icon-card\">\r\n      <h2 sxy-text=\"Tulorekisterivarmenteen luonti/uusinta\"></h2>\r\n    </div>\r\n    <div class=\"card-body\">\r\n      <div class=\"row\">\r\n        <ng-form name=\"$frmCert\" class=\"form-horizontal\">\r\n          <div>\r\n              <legend>Yrityksesi tulorekisterivarmenteen tila</legend>\r\n              <table class=\"table\">\r\n                <tr>\r\n                  <th>Luotu</th>\r\n                  <th>Voimassaolo päättyy</th>\r\n                </tr>\r\n                <tr ng-if=\"!$ctrl.irCertificate.id\">\r\n                  <td colspan=\"2\">Ei voimassa olevaa varmennetta</td>\r\n                </tr>\r\n                <tr ng-if=\"$ctrl.irCertificate.id\">\r\n                  <td>{{$ctrl.irCertificate.updatedAt | date}}</td>\r\n                  <td>{{$ctrl.irCertificate.expiresAt | date}}</td>\r\n                </tr>\r\n              </table>\r\n            </fieldset>\r\n            <fieldset>\r\n              <legend>Varmenteen luonti/uusinta</legend>\r\n              <salaxy-input-enum ng-if=\"$ctrl.irCertificate.id\" ng-init=\"$ctrl.irCertificateAction = 'renew'\" label=\"Toimenpide\" ng-model=\"$ctrl.irCertificateAction\" name=\"certAction\" type=\"radio\"\r\n                options=\"{ create: 'Luo uusi varmenne', renew: 'Uusi nykyinen varmenne' }\"></salaxy-input-enum>\r\n              <salaxy-input-enum ng-if=\"!$ctrl.irCertificate.id\" ng-init=\"$ctrl.irCertificateAction = 'create'\" label=\"Toimenpide\" ng-model=\"$ctrl.irCertificateAction\" name=\"certAction\" type=\"radio\"\r\n                options=\"{ create: 'Luo uusi varmenne'}\"></salaxy-input-enum>\r\n              <salaxy-input ng-if=\"$ctrl.irCertificateAction == 'create'\" require=\"true\" label=\"Siirtotunnus\" ng-model=\"$ctrl.irCertificateTransferId\"\r\n                name=\"transferId\"></salaxy-input>\r\n              <salaxy-input ng-if=\"$ctrl.irCertificateAction == 'create'\" require=\"true\" label=\"Kertakäyttösalasana\" ng-model=\"$ctrl.irCertificateTransferPassword\"\r\n                name=\"transferPassword\" type=\"password\"></salaxy-input>\r\n            </fieldset>\r\n          </div>\r\n        </ng-form>\r\n      </div>\r\n    </div>\r\n    <div class=\"card-footer\">\r\n      <div class=\"row\">\r\n        <div class=\"col-xs-12 text-right\">\r\n          <button type=\"button\" ng-if=\"$ctrl.irCertificateAction == 'create'\" class=\"btn btn-primary\" ng-disabled=\"$ctrl.isSaving('irCertificate') || !$frmCert.$valid\"\r\n            ng-click=\"$ctrl.createIrCertificate($ctrl.irCertificateTransferId, $ctrl.irCertificateTransferPassword)\"><span ng-if=\"$ctrl.isSaving('irCertificate')\"><i\r\n                class=\"bi bi-arrow-repeat bi-spin\"></i></span><span sxy-text=\"Luo uusi varmenne\"></span></button>\r\n          <button type=\"button\" ng-if=\"$ctrl.irCertificateAction == 'renew'\" class=\"btn btn-primary\" ng-disabled=\"$ctrl.isSaving('irCertificate')  || !$frmCert.$valid\"\r\n            ng-click=\"$ctrl.renewIrCertificate()\"><span ng-if=\"$ctrl.isSaving('irCertificate')\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span><span\r\n              sxy-text=\"Uusi nykyinen varmenne\"></span></button>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/settings/OwnerSettings.html\",`<div class=\"salaxy-component salaxy-owner-settings\">\r\n\r\n  <style>\r\n    @media print {\r\n      salaxy-tab {\r\n        display: none !important;\r\n      }\r\n    }\r\n  </style>\r\n  <salaxy-tab-buttons\r\n    current-tab=\"$ctrl.currentTab\"\r\n    options=\"[\r\n      { value: 'default', text: 'SALAXY.NG1.OwnerSettingsComponent.tabs.editing' },\r\n      { value: 'beneficiaries', text: 'SALAXY.NG1.OwnerSettingsComponent.tabs.beneficiaries' },\r\n      { value: 'printable', text: 'SALAXY.NG1.OwnerSettingsComponent.tabs.printable' }\r\n    ]\"\r\n    tabs-id=\"ownerSettings\">\r\n  </salaxy-tab-buttons>\r\n  <div class=\"tab-content\" id=\"tab-content-ownerSettings\">\r\n    <div class=\"tab-pane\" id=\"default-tab\">\r\n      <form class=\"form-horizontal\" ng-if=\"$ctrl.current\" ng-readonly=\"$ctrl.isReadOnlyForced\">\r\n        <div class=\"row\">\r\n          <div class=\"col-12\">\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.NG1.OwnerSettingsComponent.shareAmountTitle\"></legend>\r\n              <div class=\"row\">\r\n                <div class=\"col-md-6\">\r\n                  <salaxy-input-enum type=\"radio\" options=\"{ byPercent: ('SALAXY.NG1.OwnerSettingsComponent.byPercent' | sxyTranslate), byAmount: ('SALAXY.NG1.OwnerSettingsComponent.byAmount' | sxyTranslate)}\" ng-model=\"$ctrl.mode\" name=\"editMode\" label=\"SALAXY.NG1.OwnerSettingsComponent.sharesBy\"\r\n                    label-cols=\"col-md-6\"></salaxy-input-enum>\r\n                </div>\r\n                <div class=\"col-md-6\">\r\n                  <salaxy-input-number ng-model=\"$ctrl.current.ownedCompanyDetails.totalNumberOfShares\" name=\"numberOfShares\" label=\"SALAXY.NG1.OwnerSettingsComponent.shareAmount\" label-cols=\"col-md-6\" ng-change=\"$ctrl.recalculateShares()\"></salaxy-input-number>\r\n                </div>\r\n              </div>\r\n            </fieldset>\r\n          </div>\r\n        </div>\r\n        <fieldset>\r\n          <legend sxy-text=\"SALAXY.NG1.OwnerSettingsComponent.ownerInfoTitle\"></legend>\r\n          <div ng-if=\"!$ctrl.current.owners.length\" class=\"salaxy-placeholder-empty placeholder-md placeholder-default text-center\">\r\n            <h4 sxy-text=\"SALAXY.NG1.OwnerSettingsComponent.noOwnersTitle\"></h4>\r\n            <p></p>\r\n            <button class=\"btn btn-primary\" ng-click=\"$ctrl.current.owners.push({numberOfShares:0,percentOfShares:0, avatar:{}});\" ng-disabled=\"!$ctrl.mode\" sxy-text=\"SALAXY.NG1.OwnerSettingsComponent.addOwnerBtn\"></button>\r\n          </div>\r\n          <div class=\"row\" ng-repeat=\"owner in $ctrl.current.owners\">\r\n            <div class=\"col-md-6\">\r\n              <salaxy-input ng-model=\"owner.avatar.displayName\" name=\"ownerName{{$index}}\" label=\"SALAXY.NG1.OwnerSettingsComponent.ownerName\" label-type=\"basic\"></salaxy-input>\r\n            </div>\r\n            <div class=\"col-md-3\">\r\n              <salaxy-input ng-model=\"owner.officialId\" name=\"officialId{{$index}}\" label=\"SALAXY.NG1.OwnerSettingsComponent.ownerOfficialId\" label-type=\"basic\"></salaxy-input>\r\n            </div>\r\n            <div class=\"col-md-3\">\r\n              <salaxy-input ng-model=\"owner.email\" name=\"email{{$index}}\" label=\"SALAXY.NG1.OwnerSettingsComponent.ownerEmail\" label-type=\"basic\" sxy-email></salaxy-input>\r\n            </div>\r\n            <div class=\"col-md-6\">\r\n              <salaxy-input ng-model=\"owner.address\" name=\"address{{$index}}\" label=\"SALAXY.NG1.OwnerSettingsComponent.ownerAddress\" label-type=\"basic\"></salaxy-input>\r\n            </div>\r\n            <div class=\"col-md-3 col-5\">\r\n              <salaxy-input-number ng-model=\"owner.numberOfShares\" name=\"ownerShare{{$index}}\" label=\"SALAXY.NG1.OwnerSettingsComponent.ownerShareAmount\" label-type=\"basic\" read-only=\"$ctrl.mode == 'byPercent' || $ctrl.isReadOnlyForced\" ng-change=\"$ctrl.recalculateShares()\"></salaxy-input-number>\r\n            </div>\r\n            <div class=\"col-md-2 col-5\">\r\n              <salaxy-input-number ng-model=\"owner.percentOfShares\" name=\"ownerpercentOfShares{{$index}}\" label=\"SALAXY.NG1.OwnerSettingsComponent.ownerSharePercent\" label-type=\"basic\" read-only=\"$ctrl.mode == 'byAmount' || $ctrl.isReadOnlyForced\" ng-change=\"$ctrl.recalculateShares()\"></salaxy-input-number>\r\n            </div>\r\n            <div class=\"col-md-1 col-2 text-end\" style=\"padding-top:39px\">\r\n              <button ng-if=\"!$ctrl.isReadOnlyForced\" class=\"btn btn-danger btn-sm\" ng-click=\"$ctrl.current.owners.splice($index,1)\" title=\"{{'SALAXY.UI_Terms.deleteRow' | sxyTranslate}}\"><i class=\"bi bi-trash-fill\"></i></button>\r\n            </div>\r\n            <div class=\"col-12\">\r\n              <hr>\r\n            </div>\r\n          </div>\r\n          <div class=\"row total-row\" ng-if=\"$ctrl.current.owners.length\">\r\n            <div class=\"col-6\">\r\n              <strong sxy-text=\"SALAXY.NG1.OwnerSettingsComponent.totalShares\"></strong>\r\n            </div>\r\n            <div class=\"col-6 text-end\" ng-if=\"$ctrl.mode == 'byAmount'\" ng-class=\"{'text-danger' : $ctrl.getTotalAmount() > $ctrl.current.ownedCompanyDetails.totalNumberOfShares, 'text-warning' : $ctrl.getTotalAmount() < $ctrl.current.ownedCompanyDetails.totalNumberOfShares && $ctrl.getTotalAmount() > 0, 'text-success' : $ctrl.getTotalAmount() == $ctrl.current.ownedCompanyDetails.totalNumberOfShares}\">\r\n              <strong>{{$ctrl.getTotalAmount()}} / {{$ctrl.current.ownedCompanyDetails.totalNumberOfShares}} <span sxy-text=\"SALAXY.UI_Terms.units.pce\"></span></strong>\r\n            </div>\r\n            <div class=\"col-6 text-end\" ng-if=\"$ctrl.mode != 'byAmount'\" ng-class=\"{'text-danger' : $ctrl.getTotalPercent() > 100, 'text-warning' : $ctrl.getTotalPercent() < 100 && $ctrl.getTotalPercent() > 0, 'text-success' : $ctrl.getTotalPercent() == 100}\">\r\n              <strong>{{$ctrl.getTotalPercent()}} / 100 %</strong>\r\n            </div>\r\n            <div class=\"col-12\">\r\n              <hr>\r\n            </div>\r\n          </div>\r\n          <div class=\"row\" ng-if=\"$ctrl.current.owners.length && !$ctrl.isReadOnlyForced\">\r\n            <div class=\"col-6\">\r\n              <button class=\"btn btn-secondary btn-sm\" ng-click=\"$ctrl.current.owners.push({numberOfShares:0,percentOfShares:0, avatar: {}})\"><i class=\"bi bi-plus-lg\" style=\"margin-right:5px\"></i><span sxy-text=\"SALAXY.NG1.OwnerSettingsComponent.addOwnerBtn\"></span></button>\r\n            </div>\r\n            <div class=\"col-6 text-end\">\r\n              <button class=\"btn btn-primary btn-sm\" ng-click=\"$ctrl.save('owners')\" ng-disabled=\"$ctrl.isSaving('owners')\"><span ng-if=\"$ctrl.isSaving('owners')\"><i\r\n                class=\"bi bi-arrow-repeat bi-spin\"></i></span> <span sxy-text=\"SALAXY.UI_Terms.save\"></span></button>\r\n            </div>\r\n          </div>\r\n        </fieldset>\r\n      </form>\r\n    </div> \r\n    <div class=\"tab-pane\" id=\"beneficiaries-tab\">\r\n      <form class=\"form-horizontal\" ng-if=\"$ctrl.current\" ng-readonly=\"$ctrl.isReadOnlyForced\">\r\n        <fieldset>\r\n          <legend sxy-text=\"SALAXY.NG1.OwnerSettingsComponent.beneficiariesInfoTitle\"></legend>\r\n          <div ng-if=\"!$ctrl.current.beneficiaries.length\" class=\"salaxy-placeholder-empty placeholder-md placeholder-default text-center\">\r\n            <h4 sxy-title=\"SALAXY.NG1.OwnerSettingsComponent.noBeneficiariesTitle\">Edunsaajat</h4>\r\n            <p></p>\r\n            <button class=\"btn btn-primary\" ng-click=\"$ctrl.current.beneficiaries.push({ avatar:{}});\" sxy-text=\"SALAXY.NG1.OwnerSettingsComponent.addBeneficiaryBtn\"></button>\r\n          </div>\r\n          <div class=\"row\" ng-repeat=\"beneficiary in $ctrl.current.beneficiaries\">\r\n            <div class=\"col-md-5\">\r\n              <salaxy-input ng-model=\"beneficiary.avatar.displayName\" name=\"beneficiaryName\" label=\"SALAXY.NG1.OwnerSettingsComponent.beneficiaryName\" label-type=\"basic\"></salaxy-input>\r\n            </div>\r\n            <div class=\"col-md-3\">\r\n              <salaxy-input ng-model=\"beneficiary.officialId\" name=\"beneficiaryOfficialId\" label=\"SALAXY.NG1.OwnerSettingsComponent.beneficiaryOfficialId\" label-type=\"basic\"></salaxy-input>\r\n            </div>\r\n            <div class=\"col-md-3 col-10\">\r\n              <salaxy-input ng-model=\"beneficiary.nationality\" name=\"beneficiaryNationality\" label=\"SALAXY.NG1.OwnerSettingsComponent.beneficiaryNationality\" label-type=\"basic\"></salaxy-input>\r\n            </div>\r\n            <div class=\"col-md-1 col-2 text-end\" style=\"padding-top:39px\">\r\n              <button ng-if=\"!$ctrl.isReadOnlyForced\" class=\"btn btn-danger btn-sm\" ng-click=\"$ctrl.current.beneficiaries.splice($index,1)\" title=\"{{'SALAXY.UI_Terms.deleteRow' | sxyTranslate}}\"><i class=\"bi bi-trash-fill\"></i></button>\r\n            </div>\r\n            <div class=\"col-12\">\r\n              <hr>\r\n            </div>\r\n          </div>\r\n          <div class=\"row\" ng-if=\"$ctrl.current.beneficiaries.length && !$ctrl.isReadOnlyForced\">\r\n            <div class=\"col-6\">\r\n              <button class=\"btn btn-secondary btn-sm\" ng-click=\"$ctrl.current.beneficiaries.push({avatar:{}})\"><i class=\"bi bi-plus-lg\" style=\"margin-right:5px\"></i> <span sxy-text=\"SALAXY.NG1.OwnerSettingsComponent.addBeneficiaryBtn\"></span></button>\r\n            </div>\r\n            <div class=\"col-6 text-end\">\r\n              <button class=\"btn btn-primary btn-sm\" ng-click=\"$ctrl.save('beneficiaries')\" ng-disabled=\"$ctrl.isSaving('beneficiaries')\"><span ng-if=\"$ctrl.isSaving('beneficiaries')\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span> <span sxy-text=\"SALAXY.UI_Terms.save\"></span></button>\r\n            </div>\r\n          </div>\r\n        </fieldset>\r\n      </form>\r\n    </div> \r\n    <div class=\"tab-pane\" id=\"printable-tab\">\r\n      <div class=\"report-table-html\" ng-if=\"$ctrl.current\">\r\n        <div class=\"table-responsive\">\r\n\r\n          <h1 sxy-text=\"SALAXY.NG1.OwnerSettingsComponent.shareHoldersTitle\"></h1>\r\n          <table class=\"report-table columns-tree\">\r\n            <thead>\r\n              <tr style=\"border-bottom:1px solid black;\">\r\n                <th sxy-text=\"SALAXY.NG1.OwnerSettingsComponent.shareHolder\"></th>\r\n                <th class=\"right\" sxy-text=\"SALAXY.NG1.OwnerSettingsComponent.shares\"></th>\r\n                <th class=\"right\" sxy-text=\"SALAXY.NG1.OwnerSettingsComponent.sharesPercent\"></th>\r\n              </tr>\r\n            </thead>\r\n            <tbody>\r\n              <tr ng-repeat=\"owner in $ctrl.current.owners\">\r\n                <td>\r\n                  {{owner.avatar.displayName}}\r\n                </td>\r\n                <td class=\"right\">\r\n                  {{owner.numberOfShares}}\r\n                </td>\r\n                <td class=\"right\">\r\n                  {{owner.percentOfShares}}\r\n                </td>\r\n              </tr>\r\n              <tfoot class=\"\">\r\n                <tr class=\"total\">\r\n                  <td><strong sxy-text=\"SALAXY.NG1.OwnerSettingsComponent.totalShares\"></strong></td>\r\n                  <td class=\"right\">{{$ctrl.getTotalAmount()}}</td>\r\n                  <td class=\"right\">{{$ctrl.getTotalPercent()}}</td>\r\n                </tr>\r\n              </tfoot>\r\n            </tbody>\r\n          </table>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/settings/PaymentChannelSettings.html\",`<div class=\"salaxy-component salaxy-payment-channel-settings\">\r\n  <div class=\"row\">\r\n    <div class=\"col-sm-6 max-h-600px mb-4\">\r\n      <h4 sxy-text=\"SALAXY.NG1.PaymentChannelSettingsComponent.title\"></h4>\r\n      <table class=\"table\">\r\n        <tbody>\r\n          <tr ng-repeat=\"channel in $ctrl.getPaymentChannels('enabled')\">\r\n            <td>\r\n              <salaxy-avatar avatar=\"$ctrl.getAvatar(channel.channel)\" class=\"\" style=\"font-size: 64px; border-bottom: 32px;\"></salaxy-avatar>\r\n            </td>\r\n            <td>\r\n              <div>\r\n                <button class=\"btn btn-default float-end\" ng-click=\"$ctrl.openChannelSetupDialog(channel.channel)\" sxy-text=\"SALAXY.NG1.PaymentChannelSettingsComponent.settingsBtn\" ps=\"...\"></button>\r\n                <strong>{{$ctrl.getAvatar(channel.channel).displayName}}</strong>\r\n                <strong ng-if=\"channel.channel == $ctrl.defaultChannel\" class=\"text-primary\" sxy-text=\"SALAXY.NG1.PaymentChannelSettingsComponent.defaultChannel\"></strong>\r\n              </div>\r\n              <div>{{$ctrl.getAvatar(channel.channel).description}}</div>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n    <div class=\"col-sm-6 max-h-600px mb-4\">\r\n      <h4 sxy-text=\"SALAXY.NG1.PaymentChannelSettingsComponent.addNewTitle\" ps=\":\"></h4>\r\n      <table class=\"table\">\r\n        <tbody>\r\n          <tr ng-repeat=\"channel in $ctrl.getPaymentChannels('available')\">\r\n            <td>\r\n              <salaxy-avatar avatar=\"$ctrl.getAvatar(channel.channel)\" class=\"\" style=\"font-size: 64px; border-bottom: 32px;\"></salaxy-avatar>\r\n            </td>\r\n            <td>\r\n              <button class=\"btn btn-default float-end\" ng-click=\"$ctrl.openChannelSetupDialog(channel.channel)\" sxy-text=\"SALAXY.NG1.PaymentChannelSettingsComponent.addBtn\" ps=\"...\"></button>\r\n              <div><strong>{{$ctrl.getAvatar(channel.channel).displayName}}</strong></div>\r\n              <div>{{$ctrl.getAvatar(channel.channel).description}}</div>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n  </div>\r\n  <div class=\"row\" ng-if=\"'test' | sxyIsInRole\">\r\n    <div class=\"col-sm-12\">\r\n      <h4><span sxy-text=\"SALAXY.NG1.PaymentChannelSettingsComponent.notAvailableTitle\"></span> <span class=\"badge bg-primary\"><span class=\"small text-white\" sxy-text=\"SALAXY.NG1.PaymentChannelSettingsComponent.test\"></span></span>\r\n      </h4>\r\n      <p sxy-text=\"SALAXY.NG1.PaymentChannelSettingsComponent.notAvailableText\"></p>\r\n      <div class=\"table-wrapper\">\r\n        <table class=\"table table-sm\">\r\n          <tbody>\r\n            <tr ng-repeat=\"channel in $ctrl.getPaymentChannels('unavailable') | filter: { id: '!undefined' }\">\r\n              <td>\r\n                <salaxy-avatar avatar=\"$ctrl.getAvatar(channel.channel)\" class=\"\" style=\"font-size: 32px; border-bottom: 32px;\"></salaxy-avatar>\r\n              </td>\r\n              <td>\r\n                <div>\r\n                  <strong>{{$ctrl.getAvatar(channel.channel).displayName}}</strong>:\r\n                  <small>{{$ctrl.getAvatar(channel.channel).description}}</small>\r\n                </div>\r\n              </td>\r\n            </tr>\r\n          </tbody>\r\n        </table>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/settings/PaymentSettings.html\",`<div class=\"content settings\" ng-if=\"$ctrl.current\">\r\n  <div class=\"card tax card-secondary mb-4\" ng-if=\"$ctrl.sections.indexOf('incomesRegister') >= 0\">\r\n    <div class=\"card-header icon-card d-flex\">\r\n      <div>\r\n        <h2 sxy-text=\"SALAXY.NG1.PaymentSettingsComponent.tax.title\"></h2>\r\n        <p><small sxy-text=\"SALAXY.NG1.PaymentSettingsComponent.tax.intro\"></small></p>\r\n      </div>\r\n      <i class=\"bi bi-check-circle-fill text-success status-icon fs-1 d-block\"></i>\r\n    </div>\r\n    <div class=\"card-body\">\r\n      <div class=\"row\">\r\n        <div class=\"col-12 form-horizontal\">\r\n          <fieldset>\r\n            <salaxy-input-enum read-only=\"$ctrl.isReadOnlyForced\" type=\"radio\" ng-model=\"$ctrl.current.calc.incomesRegister.irReporting\" name=\"irReporting\" label=\"SALAXY.MODEL.IncomesRegisterSettings.irReporting.editLabel\" options=\"{ \r\n                                default: ('SALAXY.ENUM.TaxReportHandling.default.label' | sxyTranslate),\r\n                                noMonthlyReport: ('SALAXY.ENUM.TaxReportHandling.noMonthlyReport.label' | sxyTranslate),\r\n                                always: ('SALAXY.ENUM.TaxReportHandling.always.label' | sxyTranslate)\r\n                              }\">\r\n            </salaxy-input-enum>\r\n          </fieldset>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"card-footer\">\r\n      <div class=\"row\">\r\n        <div class=\"col-12\">\r\n          <button ng-if=\"!$ctrl.isReadOnlyForced\" ng-disabled=\"$ctrl.isSaving('incomesRegister')\" class=\"btn btn-primary float-end\" ng-click=\"$ctrl.save('incomesRegister')\"><span ng-if=\"$ctrl.isSaving('incomesRegister')\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span> <span sxy-text=\"SALAXY.UI_Terms.save\"></span></button>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div class=\"card einvoice card-secondary mb-4\" ng-if=\"$ctrl.sections.indexOf('eInvoice') >= 0\">\r\n    <div class=\"card-header\">\r\n      <h2 sxy-text=\"SALAXY.NG1.PaymentSettingsComponent.einvoice.title\"></h2>\r\n      <p><small sxy-text=\"SALAXY.NG1.PaymentSettingsComponent.einvoice.description\"></small></p>\r\n    </div>\r\n    <div class=\"card-body\">\r\n      <div class=\"row\">\r\n        <div class=\"col-12 form-horizontal\">\r\n          <form name=\"eInvoiceForm\" class=\"einvoice-form\" ng-readonly=\"$ctrl.isReadOnlyForced\">\r\n            <fieldset>\r\n              <salaxy-form-group name=\"eInvoiceReceiver\" label=\"SALAXY.NG1.PaymentSettingsComponent.einvoice.invoiceAddress\">\r\n                <div class=\"input-group\">\r\n                  <input class=\"form-control\" type=\"text\" autocomplete=\"off\" id=\"eInvoiceReceiver\" name=\"eInvoiceReceiver\" ng-disabled=\"true\" ng-model=\"$ctrl.current.payments.invoice.eInvoiceReceiver\">\r\n                  <span class=\"input-group-btn\">\r\n                    <button type=\"button\" class=\"btn btn-default\" ng-if=\"!$ctrl.isReadOnlyForced\" ng-click=\"$ctrl.selectEInvoiceAddress()\" sxy-text=\"SALAXY.UI_Terms.choose\"></button>\r\n                  </span>\r\n                </div>\r\n              </salaxy-form-group>\r\n              <salaxy-input disabled=\"true\" name=\"intermediator\" ng-model=\"$ctrl.current.payments.invoice.eInvoiceIntermediator\" label=\"SALAXY.NG1.NewPaymentComponent.einvoice.intermediatorLabel\"></salaxy-input>\r\n\r\n            </fieldset>\r\n          </form>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"card-footer\">\r\n      <div class=\"row\">\r\n        <div class=\"col-12\">\r\n          <button ng-if=\"!$ctrl.isReadOnlyForced\" ng-disabled=\"$ctrl.isSaving('eInvoice')\" class=\"btn btn-primary float-end\" ng-click=\"$ctrl.save('eInvoice')\"><span ng-if=\"$ctrl.isSaving('eInvoice')\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span> <span sxy-text=\"SALAXY.UI_Terms.save\"></span></button>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div class=\"card sepa card-secondary mb-4\" ng-if=\"$ctrl.sections.indexOf('sepa') >= 0\">\r\n    <form name=\"sepaForm\" ng-readonly=\"$ctrl.isReadOnlyForced\">\r\n      <div class=\"card-header\">\r\n        <h2 sxy-text=\"SALAXY.NG1.PaymentSettingsComponent.sepa.title\"></h2>\r\n        <p><small sxy-text=\"SALAXY.NG1.PaymentSettingsComponent.sepa.title\"></small></p>\r\n      </div>\r\n      <div class=\"card-body\">\r\n        <div class=\"row\">\r\n          <div class=\"col-12 form-horizontal\">\r\n            <fieldset>\r\n              <salaxy-input name=\"ibanNumber\" label=\"SALAXY.NG1.PaymentSettingsComponent.sepa.iban\" ng-model=\"$ctrl.current.payments.invoice.ibanNumber\" sxy-iban></salaxy-input>\r\n              <salaxy-input name=\"sepaBankPartyId\" label=\"SALAXY.NG1.PaymentSettingsComponent.sepa.sepaId\" ng-model=\"$ctrl.current.payments.invoice.sepaBankPartyId\"></salaxy-input>\r\n            </fieldset>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div class=\"card-footer\">\r\n        <div class=\"row\">\r\n          <div class=\"col-12\">\r\n            <button ng-if=\"!$ctrl.isReadOnlyForced\" ng-disabled=\"sepaForm.$invalid || $ctrl.isSaving('sepa')\" class=\"btn btn-primary float-end\" ng-click=\"$ctrl.save('sepa')\"><span ng-if=\"$ctrl.isSaving('sepa')\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span> <span sxy-text=\"SALAXY.UI_Terms.save\"></span></button>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </form>\r\n  </div>\r\n  <div class=\"card taxAndSocialSecuritySelfHandling card-secondary mb-4\" ng-if=\"$ctrl.sections.indexOf('taxAndSocialSecuritySelfHandling') >= 0\">\r\n    <div class=\"card-header\">\r\n      <h2 sxy-text=\"SALAXY.NG1.PaymentSettingsComponent.taxSelfHandling.title\"></h2>\r\n      <p><small sxy-text=\"SALAXY.NG1.PaymentSettingsComponent.taxSelfHandling.intro\"></small></p>\r\n      <p><small sxy-text=\"SALAXY.NG1.PaymentSettingsComponent.taxSelfHandling.intro2\"></small></p>\r\n    </div>\r\n    <div class=\"card-body\">\r\n      <div class=\"row\">\r\n        <div class=\"col-12 form-horizontal\">\r\n          <fieldset>\r\n            <salaxy-input-boolean read-only=\"$ctrl.isReadOnlyForced\" type=\"checkbox\" name=\"isTaxAndSocialSecuritySelfHandling\" label-type=\"plain\" label-true=\"SALAXY.NG1.PaymentSettingsComponent.taxSelfHandling.taxSelfHandlingTrue\" ng-model=\"$ctrl.current.payments.customerFunds.isTaxAndSocialSecuritySelfHandling\"></salaxy-input-boolean>\r\n          </fieldset>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"card-footer\">\r\n      <div class=\"row\">\r\n        <div class=\"col-12\">\r\n          <button ng-if=\"!$ctrl.isReadOnlyForced\" ng-disabled=\"$ctrl.isSaving('taxAndSocialSecuritySelfHandling')\" class=\"btn btn-primary float-end\" ng-click=\"$ctrl.save('taxAndSocialSecuritySelfHandling')\"><span ng-if=\"$ctrl.isSaving('taxAndSocialSecuritySelfHandling')\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span> <span sxy-text=\"SALAXY.UI_Terms.save\"></span></button>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div class=\"card workerSelfHandling card-secondary mb-4\" ng-if=\"$ctrl.sections.indexOf('workerSelfHandling') >= 0\">\r\n    <div class=\"card-header\">\r\n      <h2 sxy-text=\"SALAXY.NG1.PaymentSettingsComponent.workerSelfHandling.title\"></h2>\r\n      <p><small sxy-text=\"SALAXY.NG1.PaymentSettingsComponent.workerSelfHandling.intro\"></small></p>\r\n      <p><small sxy-text=\"SALAXY.NG1.PaymentSettingsComponent.workerSelfHandling.intro2\"></small></p>\r\n    </div>\r\n    <div class=\"card-body\">\r\n      <div class=\"row\">\r\n        <div class=\"col-12 form-horizontal\">\r\n          <fieldset>\r\n            <salaxy-input-boolean read-only=\"$ctrl.isReadOnlyForced\" type=\"checkbox\" name=\"isWorkerSelfHandling\" label-type=\"plain\" label-true=\"SALAXY.NG1.PaymentSettingsComponent.workerSelfHandling.workerSelfHandlingTrue\" ng-model=\"$ctrl.current.payments.customerFunds.isWorkerSelfHandling\"></salaxy-input-boolean>\r\n          </fieldset>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"card-footer\">\r\n      <div class=\"row\">\r\n        <div class=\"col-12\">\r\n          <button ng-if=\"!$ctrl.isReadOnlyForced\" ng-disabled=\"$ctrl.isSaving('workerSelfHandling')\" class=\"btn btn-primary float-end\" ng-click=\"$ctrl.save('workerSelfHandling')\"><span ng-if=\"$ctrl.isSaving('workerSelfHandling')\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span> <span sxy-text=\"SALAXY.UI_Terms.save\"></span></button>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div class=\"card unemployment card-secondary mb-4\" ng-if=\"$ctrl.sections.indexOf('unemploymentSelfHandling') >= 0\">\r\n    <div class=\"card-header\">\r\n      <h2 sxy-text=\"SALAXY.NG1.PaymentSettingsComponent.unemployment.title\"></h2>\r\n    </div>\r\n    <div class=\"card-body\">\r\n      <div class=\"row\">\r\n        <div class=\"col-12\">\r\n          <fieldset>\r\n            <p sxy-text=\"SALAXY.NG1.PaymentSettingsComponent.unemployment.intro\"></p>\r\n          </fieldset>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div class=\"card salarySlipDeliveryMethods card-secondary mb-4\" ng-if=\"$ctrl.sections.indexOf('payslip') >= 0  && ('payslip' | sxyIsInRole)\">\r\n    <div class=\"card-header\">\r\n      <h2 sxy-text=\"SALAXY.NG1.PaymentSettingsComponent.salarySlipDeliveryMethods.payslip.title\"></h2>\r\n    </div>\r\n    <div class=\"card-body\">\r\n      <div class=\"row\">\r\n        <div class=\"col-12 form-horizontal\">\r\n          <form name=\"salarySlipDeliveryMethodsForm\" class=\"salarySlipDeliveryMethods-form\">\r\n            <fieldset>\r\n              <p><small sxy-text=\"SALAXY.NG1.PaymentSettingsComponent.salarySlipDeliveryMethods.payslip.description\"></small></p>\r\n              <salaxy-input-boolean label=\"SALAXY.ENUM.WorkerSalarySlipDeliveryMethod.payslip.label\" name=\"payslip\" type=\"checkbox\" ng-model=\"$ctrl.payslip\" disabled=\"$ctrl.disableSwitchInput()\"></salaxy-input-boolean>\r\n            </fieldset>\r\n          </form>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div class=\"card omapalkka card-secondary mb-4\" ng-if=\"$ctrl.sections.indexOf('omapalkka') >= 0 && ('test,admin' | sxyIsInRole)\">\r\n    <div class=\"card-header\">\r\n      <h2 sxy-text=\"SALAXY.NG1.PaymentSettingsComponent.salarySlipDeliveryMethods.omapalkka.title\">\r\n      </h2>\r\n    </div>\r\n    <div class=\"card-body\">\r\n      <div class=\"row\">\r\n        <div class=\"col-12 form-horizontal\">\r\n          <form name=\"omapalkkaForm\" class=\"omapalkka-form\">\r\n            <fieldset>\r\n              <salaxy-input-boolean label=\"SALAXY.ENUM.WorkerSalarySlipDeliveryMethod.omapalkka.label\" name=\"omapalkka\" type=\"checkbox\" ng-model=\"$ctrl.omapalkka\" disabled=\"$ctrl.disableSwitchInput()\"></salaxy-input-boolean>\r\n            </fieldset>\r\n          </form>\r\n          <salaxy-form-group name=\"paidCalculationsToOmapalkka\" label=\"SALAXY.NG1.PaymentSettingsComponent.salarySlipDeliveryMethods.omapalkka.label\">\r\n            <div class=\"input-group\">\r\n              <button type=\"button\" class=\"btn btn-default float-end\" ng-click=\"$ctrl.sendPaidCalculationsToOmapalkka()\" sxy-text=\"SALAXY.NG1.PaymentSettingsComponent.salarySlipDeliveryMethods.omapalkka.sendToOmapalkkaButtonText\"></button>\r\n            </div>\r\n          </salaxy-form-group>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/settings/PayStatsSettings.html\",`<div class=\"content settings\" ng-if=\"$ctrl.current\">\r\n  <div class=\"card mb-4 accounting card-secondary\">\r\n    <div>\r\n      <div class=\"card-header icon-card\">\r\n        <h2 sxy-text=\"SALAXY.MODEL.PayStatsSettings.title\"></h2>\r\n      </div>\r\n      <div class=\"card-body\">\r\n        <div class=\"row\">\r\n          <sxy-form ng-ref=\"$frm\" open-api=\"salaxy-secure/schemas/v02.json\" type=\"CompanyAccountSettings\" auto-gen=\"false\" debugger=\"false\" model=\"$ctrl.current\" read-only=\"{{!$ctrl.current.payStats.denyServiceModel  && $ctrl.current.partner.serviceModel.features.payStats}}\">\r\n            <div>\r\n              <sxy-input model=\"form.partner.serviceModel.features.payStats\" label=\"SALAXY.NG1.ProSettingsComponent.customPayStats\" read-only=\"true\"></sxy-input>\r\n              <salaxy-input-boolean label=\"SALAXY.NG1.ProSettingsComponent.overwriteServiceModel\" name=\"serviceModelPayStats\" ng-change=\"$ctrl.confirmServiceModelChange()\"\r\n                ng-if=\"$ctrl.current.partner.serviceModel.features.payStats\" ng-model=\"$ctrl.current.payStats.denyServiceModel\"></salaxy-input-boolean>\r\n              <sxy-input model=\"form.payStats.types\"\r\n                read-only=\"{{!$ctrl.current.payStats.denyServiceModel  && $ctrl.current.partner.serviceModel.features.payStats }}\" include=\"id,kind,periodLength,employeeGroup,cbaCode\">\r\n                <form>\r\n                  <fieldset>\r\n                    <legend sxy-text=\"SALAXY.MODEL.PayStatsTypeDefinition.title\"></legend>\r\n                    <sxy-input model=\"form.id\" require=\"true\" read-only=\"{{$ctrl.logic.isReadOnly}}\"></sxy-input>\r\n                    <sxy-input model=\"form.description\"></sxy-input>\r\n                    <salaxy-input-enum enum=\"PayStatsKind\" label=\"SALAXY.MODEL.PayStatsTypeDefinition.kind.title\" name=\"kind\" require=\"true\" ng-model=\"$ctrl.current.kind\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-enum>\r\n                    <salaxy-input-enum enum=\"PayStatsPeriodLength\" label=\"SALAXY.MODEL.PayStatsTypeDefinition.periodLength.title\" name=\"periodLength\" require=\"true\" ng-model=\"$ctrl.current.periodLength\" filter=\"quarter,month,year\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-enum>\r\n                    <salaxy-input-enum enum=\"PeriodDateKind\" label=\"SALAXY.MODEL.PayStatsTypeDefinition.periodDateKind.title\" name=\"periodDateKind\" require=\"true\" ng-model=\"$ctrl.current.periodDateKind\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-enum>                   \r\n                    <salaxy-input-collective-bargain-agreement name=\"cbaCode\" ng-model=\"$ctrl.current.cbaCode\" label=\"SALAXY.MODEL.PayStatsTypeDefinition.cbaCode.title\"></salaxy-input-collective-bargain-agreement>\r\n                    <salaxy-input-employee-group name=\"employeeGroup\" ng-model=\"$ctrl.current.employeeGroup\" label=\"SALAXY.MODEL.PayStatsTypeDefinition.employeeGroup.title\"></salaxy-input-employee-group>\r\n                    <sxy-input model=\"form.disabled\"></sxy-input>\r\n                    <sxy-input model=\"form.startDate\"></sxy-input>\r\n                    <sxy-input model=\"form.endDate\"></sxy-input>\r\n                    <legend ng-show=\"$ctrl.current.kind == 'averageHourlyPay'\" sxy-text=\"SALAXY.MODEL.PayStatsTypeDefinition.salaryTypes.title\"></legend>\r\n                    <sxy-input ng-show=\"$ctrl.current.kind == 'averageHourlyPay'\" model=\"form.salaryTypes\" template-url=\"salaxy-components/sxy-form/custom-templates/pay-stats-row-types.html\"></sxy-input>\r\n                    <legend ng-show=\"$ctrl.current.kind == 'averageHourlyPay'\" sxy-text=\"SALAXY.MODEL.PayStatsTypeDefinition.workingTimeTypes.title\"></legend>\r\n                    <sxy-input ng-show=\"$ctrl.current.kind == 'averageHourlyPay'\" format=\"undefined\" model=\"form.minWorkingTime\"></sxy-input>\r\n                    <sxy-input ng-show=\"$ctrl.current.kind == 'averageHourlyPay'\" model=\"form.workingTimeTypes\" template-url=\"salaxy-components/sxy-form/custom-templates/pay-stats-row-types.html\"></sxy-input>\r\n                    <sxy-code-editor ng-show=\"$ctrl.current.kind == 'script'\" ng-model=\"$ctrl.current.script\"></sxy-code-editor>\r\n                  </fieldset>\r\n                </form>\r\n              </sxy-input>\r\n            </div>         \r\n          </sxy-form>\r\n        </div>\r\n      </div>\r\n      <div class=\"card-footer\">\r\n        <div class=\"row\">\r\n          <div class=\"col-xs-12\">\r\n            <button type=\"submit\" ng-disabled=\"(!$ctrl.current.payStats.denyServiceModel && $ctrl.current.partner.serviceModel.features.payStats) || !$frm.ngForm.$valid || $ctrl.isSaving('all')\" class=\"btn btn-primary pull-right\" ng-click=\"$ctrl.save('all')\">\r\n              <span ng-if=\"$ctrl.isSaving('all')\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span>\r\n              <span sxy-text=\"SALAXY.UI_Terms.save\"></span>\r\n            </button>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/settings/ProSettings.html\",`<div class=\"salaxy-component salaxy-pro-settings\">\r\n  <div class=\"btn-toolbar d-flex justify-content-end\">\r\n    <button class=\"btn btn-primary\" ng-click=\"$ctrl.save('all')\" ng-disabled=\"$ctrl.isSaving('all')\"><span ng-if=\"$ctrl.isSaving('all')\"><i\r\n      class=\"bi bi-arrow-repeat bi-spin\"></i></span> <span sxy-text=\"SALAXY.UI_Terms.save\"></span></button>\r\n  </div>\r\n  <div ng-if=\"$ctrl.current\">\r\n    <sxy-form open-api=\"salaxy-secure/schemas/v02.json\" type=\"CompanyAccountSettings\" auto-gen=\"false\" debugger=\"false\" model=\"$ctrl.current\">\r\n      <div>\r\n        <salaxy-tab-buttons\r\n          current-tab=\"$ctrl.currentTab\"\r\n          options=\"[\r\n            { value: 'insurances', text: 'SALAXY.NG1.ProSettingsComponent.insurances' },\r\n            { value: 'rows', text: 'SALAXY.NG1.ProSettingsComponent.tabs.defaultRows' },\r\n            { value: 'coms', text: 'SALAXY.NG1.ProSettingsComponent.tabs.messagingAndLayout' },\r\n            { value: 'paymentchannels', text: 'SALAXY.NG1.ProSettingsComponent.tabs.paymentChannels' },\r\n            { value: 'dimensions', text: 'SALAXY.NG1.ProSettingsComponent.tabs.dimensions' },\r\n            { value: 'accounting', text: 'SALAXY.NG1.ProSettingsComponent.tabs.accounting' },\r\n            { value: 'holidays', text: 'SALAXY.NG1.ProSettingsComponent.tabs.holidays' },\r\n            { value: 'other', text: 'SALAXY.NG1.ProSettingsComponent.tabs.other' },\r\n            { value: 'irdelivery', text: 'SALAXY.NG1.ProSettingsComponent.tabs.irdelivery' },\r\n            { value: 'paystats', text: 'SALAXY.NG1.ProSettingsComponent.tabs.paystats', hidden: !('bizConfigs' | sxyIsInRole) },\r\n            { value: 'employeeGroups', text: 'SALAXY.MODEL.CalculationSettings.employeeGroups.title', hidden: !('bizConfigs' | sxyIsInRole) },\r\n            { value: 'configs', text: 'SALAXY.MODEL.CompanyAccountSettings.configs.title', hidden: !('bizConfigs' | sxyIsInRole) },\r\n            { value: 'readonly', text: 'SALAXY.NG1.ProSettingsComponent.tabs.read-only' }\r\n          ]\"\r\n          tabs-id=\"proSettings\">\r\n        </salaxy-tab-buttons>\r\n        <div class=\"tab-content\" id=\"tab-content-proSettings\">\r\n          <div class=\"tab-pane\" id=\"insurances-tab\">\r\n            <fieldset>\r\n              <legend><span sxy-text=\"SALAXY.NG1.ProSettingsComponent.insurances\"></span> </legend>\r\n              <sxy-input model=\"form.calc.pensionContracts\" template-url=\"salaxy-components/sxy-form/custom-templates/array-pension.html\">\r\n                <form>\r\n                  <fieldset>\r\n                    <sxy-input model=\"form.company\"></sxy-input>\r\n                    <sxy-input model=\"form.contractNumber\" format=\"pension-contract-number\"></sxy-input>\r\n                    <sxy-input model=\"form.startDate\" format=\"date\"></sxy-input>\r\n                    <sxy-input model=\"form.endDate\" format=\"date\"></sxy-input>\r\n                    <sxy-input model=\"form.pensionDefaultPercent\"></sxy-input>\r\n                    <sxy-input model=\"form.pensionPercent\"></sxy-input>\r\n                    <sxy-input ng-show=\"['kevaMunicipal','kevaAland','kevaChurch','kevaKela','kevaState'].indexOf($ctrl.current.company) >= 0\" model=\"form.subOrgCode\"></sxy-input>\r\n                    <sxy-input ng-show=\"'admin' | sxyIsInRole\" model=\"form.pensionDiscountPercent\"></sxy-input>\r\n                    <sxy-input ng-show=\"'admin' | sxyIsInRole\" model=\"form.status\" read-only=\"false\"></sxy-input>\r\n                    <sxy-input ng-show=\"'!admin' | sxyIsInRole\" model=\"form.status\" read-only=\"true\"></sxy-input>\r\n                    <!--sxy-input model=\"form.id\" read-only=\"true\"></sxy-input-->\r\n                  </fieldset>\r\n                </form>\r\n              </sxy-input>\r\n              <sxy-input model=\"form.calc.insuranceContracts\" template-url=\"salaxy-components/sxy-form/custom-templates/array-insurance.html\">\r\n                <form>\r\n                  <fieldset>\r\n                    <legend><span sxy-text=\"SALAXY.NG1.ProSettingsComponent.insurance\"></span> </legend>\r\n                    <sxy-input model=\"form.company\"></sxy-input>\r\n                    <sxy-input model=\"form.contractNumber\"></sxy-input>\r\n                    <sxy-input model=\"form.startDate\" format=\"date\"></sxy-input>\r\n                    <sxy-input model=\"form.endDate\" format=\"date\"></sxy-input>\r\n                    <sxy-input model=\"form.insurancePercent\"></sxy-input>\r\n                    <sxy-input model=\"form.groupLifeInsurancePercent\"></sxy-input>\r\n                    <sxy-input model=\"form.isPartnerInsurance\"></sxy-input>\r\n                    <sxy-input ng-show=\"'admin' | sxyIsInRole\" model=\"form.status\" read-only=\"false\"></sxy-input>\r\n                    <sxy-input ng-show=\"'!admin' | sxyIsInRole\" model=\"form.status\" read-only=\"true\"></sxy-input>\r\n                    <!--sxy-input model=\"form.id\" read-only=\"true\"></sxy-input-->\r\n                  </fieldset>\r\n                </form>\r\n              </sxy-input>\r\n            </fieldset>\r\n            <fieldset>\r\n              <legend><span sxy-text=\"SALAXY.NG1.ProSettingsComponent.unemploymentInsurance\"></span> </legend>\r\n              <sxy-input model=\"form.calc.unemploymentInsurance.payrollLimitStatus\"></sxy-input>\r\n            </fieldset>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"rows-tab\">\r\n            <salaxy-calc-rows-editor ng-if=\"!$ctrl.isLoading\" rows=\"$ctrl.current.calc.salaryDefaults\"\r\n              title=\"{{ 'SALAXY.NG1.WorkerDetailsComponent.defaultCalcRows' | sxyTranslate }}\" type=\"salary-defaults\"></salaxy-calc-rows-editor>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"coms-tab\">\r\n            <fieldset>\r\n              <legend><span sxy-text=\"SALAXY.NG1.ProSettingsComponent.messaging\"></span> <span\r\n                  ng-if=\"!$ctrl.current.messaging.denyServiceModel && $ctrl.current.partner.serviceModel.features.messaging\" class=\"badge bg-danger float-end\"\r\n                  sxy-text=\"SALAXY.NG1.ProSettingsComponent.serviceModelBadge\"></span></legend>\r\n              <sxy-input model=\"form.partner.serviceModel.features.messaging\" label=\"SALAXY.NG1.ProSettingsComponent.customMessages\" read-only=\"true\"></sxy-input>\r\n              <salaxy-input-boolean label=\"SALAXY.NG1.ProSettingsComponent.overwriteServiceModel\" name=\"messagingDeny\" ng-change=\"$ctrl.confirmServiceModelChange()\"\r\n                ng-if=\"$ctrl.current.partner.serviceModel.features.messaging\" ng-model=\"$ctrl.current.messaging.denyServiceModel\"></salaxy-input-boolean>\r\n              <salaxy-input-boolean ng-if=\"$ctrl.current.partner.serviceModel.features.messaging\" read-only=\"!$ctrl.current.messaging.denyServiceModel\"\r\n                ng-model=\"$ctrl.current.messaging.partnerMessages\" name=\"partnerMessages\" label=\"SALAXY.NG1.ProSettingsComponent.messagesAccountant\"></salaxy-input-boolean>\r\n              <salaxy-input-enum read-only=\"!$ctrl.current.messaging.denyServiceModel && $ctrl.current.partner.serviceModel.features.messaging\" type=\"multi-select\"\r\n                enum=\"WorkerSalaryNotification\" ng-model=\"$ctrl.current.messaging.workerSalaryNotifications\" name=\"workerSalaryNotifications\"\r\n                label=\"SALAXY.NG1.ProSettingsComponent.messagesPayment\"></salaxy-input-enum>\r\n              <salaxy-input-enum read-only=\"!$ctrl.current.messaging.denyServiceModel && $ctrl.current.partner.serviceModel.features.messaging\" type=\"multi-select\"\r\n                enum=\"WorkerSalarySlipDeliveryMethod\" ng-model=\"$ctrl.current.messaging.workerSalarySlipDeliveryMethods\" name=\"workerSalarySlipDeliveryMethods\"\r\n                label=\"SALAXY.NG1.ProSettingsComponent.workerSalarySlipDeliveryMethods\"></salaxy-input-enum>\r\n            </fieldset>\r\n            <fieldset ng-init=\"$ctrl.isReportLogoManuallyUploaded = false\">\r\n              <legend><span sxy-text=\"SALAXY.NG1.ProSettingsComponent.reporting\"></span> <span\r\n                  ng-if=\"!$ctrl.current.reporting.denyServiceModel && $ctrl.current.partner.serviceModel.features.reporting\" class=\"badge bg-danger float-end\"\r\n                  sxy-text=\"SALAXY.NG1.ProSettingsComponent.serviceModelBadge\"></span></legend>\r\n              <sxy-input model=\"form.partner.serviceModel.features.reporting\" label=\"SALAXY.NG1.ProSettingsComponent.customReporting\" read-only=\"true\"></sxy-input>\r\n              <salaxy-input-boolean label=\"SALAXY.NG1.ProSettingsComponent.overwriteServiceModel\" name=\"uc4\" ng-change=\"$ctrl.confirmServiceModelChange()\"\r\n                ng-if=\"$ctrl.current.partner.serviceModel.features.reporting\" ng-model=\"$ctrl.current.reporting.denyServiceModel\"></salaxy-input-boolean>\r\n              <salaxy-input-enum read-only=\"!$ctrl.current.reporting.denyServiceModel && $ctrl.current.partner.serviceModel.features.reporting\"\r\n                ng-model=\"$ctrl.current.reporting.layoutTemplateId\" name=\"layputTemplateId\" label=\"SALAXY.NG1.ProSettingsComponent.layoutTemplateId\" options=\"{'palkkaus-report-options@FI53POYS0025543933': ('SALAXY.NG1.ProSettingsComponent.templateIdPalkkaus' | sxyTranslate),\r\n                'no-logo-report-options@FI53POYS0025543933': ('SALAXY.NG1.ProSettingsComponent.templateIdNoLogo' | sxyTranslate),\r\n                'logo-report-options@FI53POYS0025543933': ('SALAXY.NG1.ProSettingsComponent.templateIdLogo' | sxyTranslate)\r\n               }\"></salaxy-input-enum>\r\n               <salaxy-input-boolean ng-if=\"$ctrl.current.reporting.layoutTemplateId == 'logo-report-options@FI53POYS0025543933'\" type=\"radio\" name=\"reportLogoUploadType\" label=\"SALAXY.NG1.ProSettingsComponent.fileUpload.uploadMethod\" ng-model=\"$ctrl.isReportLogoManuallyUploaded\" label-true=\"SALAXY.NG1.ProSettingsComponent.fileUpload.manualUpload\" label-false=\"SALAXY.NG1.ProSettingsComponent.fileUpload.uploadFromDevice\"></salaxy-input-boolean>\r\n               <div class=\"form-group row\" ng-if=\"!$ctrl.isReportLogoManuallyUploaded && $ctrl.current.reporting.layoutTemplateId == 'logo-report-options@FI53POYS0025543933'\">\r\n                  <div class=\"col-xs-12 col-sm-4\">\r\n                    <label for=\"avatarImageUpload\" sxy-text=\"SALAXY.NG1.ProSettingsComponent.fileUpload.previewLabel\"></label>\r\n                  </div>\r\n                  <div class=\"col-xs-12 col-sm-8\">\r\n                    <div name=\"avatarImageUpload\" ng-model=\"avatarImage\" ngf-drop=\"$ctrl.createReportLogoDatauri($file)\" ngf-select=\"$ctrl.createReportLogoDatauri($file)\" class=\"salaxy-drop-box\" ngf-drag-over-class=\"'salaxy-drag-over'\" ngf-multiple=\"false\" ngf-min-size=\"1KB\" ngf-max-size=\"10MB\"\r\n                       ngf-model-invalid=\"invalidFile\" ng-class=\"invalidFile.$error != null ? 'error' : ''\">\r\n                      <span sxy-html=\"SALAXY.NG1.AccountAvatarEditPersonComponent.uploadImage.html\"></span>\r\n                      <p sxy-text=\"SALAXY.NG1.AccountAvatarEditPersonComponent.preferredImageSize\"></p>\r\n                    </div>\r\n                  </div>\r\n                  \r\n              </div>\r\n              <salaxy-textarea maxlength=\"\" read-only=\"!$ctrl.current.reporting.denyServiceModel && $ctrl.current.partner.serviceModel.features.reporting\"\r\n                label=\"SALAXY.NG1.ProSettingsComponent.customReportLogo\" name=\"logo\" ng-model=\"$ctrl.current.reporting.logo\" rows=\"3\"\r\n                ng-if=\"$ctrl.current.reporting.layoutTemplateId == 'logo-report-options@FI53POYS0025543933' && $ctrl.isReportLogoManuallyUploaded\">\r\n              </salaxy-textarea>\r\n              <div class=\"form-group row\" ng-if=\"$ctrl.current.reporting.logo && $ctrl.current.reporting.layoutTemplateId == 'logo-report-options@FI53POYS0025543933'\">\r\n                <div class=\"col-xs-12 col-sm-4\">\r\n                  <label for=\"avatarImageUpload\" sxy-text=\"Logo\"></label>\r\n                </div>\r\n                <div class=\"col-xs-12 col-sm-8\">\r\n                  <div class=\"salaxy-report-logo-preview\">\r\n                    <div ng-bind-html=\"$ctrl.getReportLogo()\" ></div>\r\n                  </div>\r\n                </div>\r\n              </div>\r\n            </fieldset>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"paymentchannels-tab\">\r\n            <fieldset>\r\n              <legend><span sxy-text=\"SALAXY.NG1.ProSettingsComponent.selfHandling\"></span> </legend>\r\n              <sxy-input model=\"form.payments.customerFunds.isWorkerSelfHandling\"></sxy-input>\r\n              <sxy-input model=\"form.payments.customerFunds.isPensionSelfHandling\"></sxy-input>\r\n              <sxy-input model=\"form.payments.customerFunds.isTaxAndSocialSecuritySelfHandling\"></sxy-input>\r\n            </fieldset>\r\n            <fieldset>\r\n              <legend><span sxy-text=\"SALAXY.NG1.ProSettingsComponent.invoices\"></span> </legend>\r\n              <sxy-input model=\"form.payments.invoice.eInvoiceReceiver\"></sxy-input>\r\n              <sxy-input model=\"form.payments.invoice.eInvoiceIntermediator\"></sxy-input>\r\n              <sxy-input model=\"form.payments.invoice.sepaBankPartyId\"></sxy-input>\r\n              <sxy-input model=\"form.payments.invoice.ibanNumber\"></sxy-input>\r\n            </fieldset>\r\n            <fieldset>\r\n              <legend><span sxy-text=\"SALAXY.NG1.ProSettingsComponent.paymentChannels\"></span> <span\r\n                  ng-if=\"!$ctrl.current.payments.denyServiceModel && $ctrl.current.partner.serviceModel.features.payments\" class=\"badge bg-danger float-end\"\r\n                  sxy-text=\"SALAXY.NG1.ProSettingsComponent.serviceModelBadge\"></span></legend>\r\n              <sxy-input model=\"form.partner.serviceModel.features.payments\" label=\"SALAXY.NG1.ProSettingsComponent.customPaymentChannels\" read-only=\"true\"></sxy-input>\r\n              <salaxy-input-boolean label=\"SALAXY.NG1.ProSettingsComponent.overwriteServiceModel\" name=\"uc1\" ng-change=\"$ctrl.confirmServiceModelChange()\"\r\n                ng-if=\"$ctrl.current.partner.serviceModel.features.payments\" ng-model=\"$ctrl.current.payments.denyServiceModel\"></salaxy-input-boolean>\r\n  \r\n              <salaxy-input-typeahead class=\"default-channel-input-enum\" disabled=\"!$ctrl.current.payments.denyServiceModel && $ctrl.current.partner.serviceModel.features.payments\"\r\n                name=\"options_type\" ng-model=\"$ctrl.current.payments.defaultChannel\" options=\"$ctrl.getSelectablePaymenMethods()\" disable-cache=\"true\"\r\n                label=\"SALAXY.NG1.ProSettingsComponent.defaultChannel\"></salaxy-input-typeahead>\r\n  \r\n              <sxy-input class=\"payment-channels\" template-url=\"salaxy-components/sxy-form/custom-templates/array-payment-channels.html\" model=\"form.payments.channels\"\r\n                read-only=\"{{!$ctrl.current.payments.denyServiceModel && $ctrl.current.partner.serviceModel.features.payments}}\">\r\n                <form>\r\n                  <fieldset ng-init=\"$ctrl.logic.showDelete = false\">\r\n                    <sxy-input model=\"form.channel\" read-only=\"true\"></sxy-input>\r\n                    <sxy-input model=\"form.isAvailable\" read-only=\"true\"></sxy-input>\r\n                    <sxy-input model=\"form.isEnabled\" read-only=\"{{!$ctrl.current.isAvailable}}\"></sxy-input>\r\n                  </fieldset>\r\n                </form>\r\n              </sxy-input>\r\n            </fieldset>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"dimensions-tab\">\r\n            <fieldset>\r\n              <legend><span sxy-text=\"SALAXY.MODEL.CostAccountingSettings.title\"></span> <span\r\n                  ng-if=\"!$ctrl.current.costAccounting.denyServiceModel && $ctrl.current.partner.serviceModel.features.costAccounting\" class=\"badge bg-danger float-end\"\r\n                  sxy-text=\"SALAXY.NG1.ProSettingsComponent.serviceModelBadge\"></span></legend>\r\n              <sxy-input model=\"form.partner.serviceModel.features.costAccounting\" label=\"SALAXY.NG1.ProSettingsComponent.customCostAccounting\" read-only=\"true\"></sxy-input>\r\n              <salaxy-input-boolean label=\"SALAXY.NG1.ProSettingsComponent.overwriteServiceModel\" name=\"uc5\" ng-change=\"$ctrl.confirmServiceModelChange()\"\r\n                ng-if=\"$ctrl.current.partner.serviceModel.features.costAccounting\" ng-model=\"$ctrl.current.costAccounting.denyServiceModel\"></salaxy-input-boolean>\r\n              <sxy-input model=\"form.costAccounting.dimensions\"\r\n                read-only=\"{{!$ctrl.current.costAccounting.denyServiceModel  && $ctrl.current.partner.serviceModel.features.costAccounting }}\" include=\"id,label,scope\">\r\n                <form>\r\n                  <fieldset>\r\n                    <legend sxy-text=\"SALAXY.MODEL.CostAccountingDimensionDefinition.title\"></legend>\r\n                    <sxy-input model=\"form.id\" read-only=\"{{$ctrl.logic.showDelete}}\"></sxy-input>\r\n                    <sxy-input model=\"form.label\"></sxy-input>\r\n                    <sxy-input model=\"form.allowCostSharing\"></sxy-input>\r\n                    <sxy-input model=\"form.scope\"></sxy-input>\r\n                    <sxy-input model=\"form.options\" template-url=\"salaxy-components/sxy-form/custom-templates/cost-accounting-options.html\"></sxy-input>\r\n                  </fieldset>\r\n                </form>\r\n              </sxy-input>\r\n            </fieldset>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"accounting-tab\">\r\n            <fieldset>\r\n              <legend><span sxy-text=\"SALAXY.NG1.ProSettingsComponent.accounting\"></span> <span\r\n                  ng-if=\"!$ctrl.current.accounting.denyServiceModel && $ctrl.current.partner.serviceModel.features.accounting\" class=\"badge bg-danger float-end\"\r\n                  sxy-text=\"SALAXY.NG1.ProSettingsComponent.serviceModelBadge\"></span></legend>\r\n              <sxy-input model=\"form.partner.serviceModel.features.accounting\" label=\"SALAXY.NG1.ProSettingsComponent.customAccounting\" read-only=\"true\"></sxy-input>\r\n              <salaxy-input-boolean label=\"SALAXY.NG1.ProSettingsComponent.overwriteServiceModel\" name=\"uc2\" ng-change=\"$ctrl.confirmServiceModelChange()\"\r\n                ng-if=\"$ctrl.current.partner.serviceModel.features.accounting\" ng-model=\"$ctrl.current.accounting.denyServiceModel\"></salaxy-input-boolean>\r\n              <salaxy-input-typeahead \r\n                name=\"options_type\" ng-model=\"$ctrl.current.accounting.defaultTargetId\" options=\"$ctrl.getSelectableAccountingTargets()\" disable-cache=\"true\"\r\n                label=\"SALAXY.NG1.ProSettingsComponent.defaultTarget\"></salaxy-input-typeahead>\r\n              <sxy-input template-url=\"salaxy-components/sxy-form/custom-templates/array-accounting-targets.html\" model=\"form.accounting.targets\"\r\n                read-only=\"{{!$ctrl.current.accounting.denyServiceModel  && $ctrl.current.partner.serviceModel.features.accounting}}\">\r\n                <form>\r\n                  <fieldset ng-show=\"!$ctrl.logic.showDelete\" ng-controller=\"CompanySettingsController as $companySettingsCtrl\" ng-init=\"$ctrl.logic.isReadOnly = true\">\r\n                    <salaxy-odata-table url=\"/v03/api/accounting-target\" template-url=\"salaxy-components/odata/lists/AccountingTargetSelect.html\"\r\n                      selected-items=\"$ctrl.selectedItems\" on-list-select=\"$companySettingsCtrl.onAccountingTargetSelect($ctrl.current, $ctrl.logic, value, item, allItems)\">\r\n                    </salaxy-odata-table>\r\n                  </fieldset>\r\n                  <fieldset ng-show=\"$ctrl.logic.showDelete\" ng-controller=\"AccountingChannelSettingsController as $settings\" ng-init=\"$ctrl.logic.isReadOnly = false\">\r\n                    <salaxy-input-enum disabled=\"false\" name=\"format\" label=\"SALAXY.NG1.AccountingTargetDetailsComponent.excelCsvFormat\" ng-model=\"$ctrl.current.format\"\r\n                      options=\"{\r\n                        '36dff2e2-e181-4f0d-9004-0e4aa92f5e17': 'Palkkaus.fi',\r\n                        '0db4e85f-93a8-46f1-b6d2-f7523d289d88': 'Fennoa',\r\n                        '8613f133-3fce-4611-b372-51f6a2e007dd': 'Procountor',\r\n                        'e62c10b0-222a-4170-b8b4-b1e02d9a7644': 'Passeli Merit',\r\n                        '53fd3863-b8f9-4909-86c9-cb4597595181': 'Heeros',\r\n                        '2fc7899c-7a3d-4d56-ad2f-05d52782bbbc': 'Asteri',\r\n                        '0a2bd312-06da-4862-aef5-75166e0bf461': 'Maestro',\r\n                        'c04e0757-63f3-420d-a183-3427710fc954': 'Visma Fivaldi',\r\n                        'ba271dac-dd63-4036-9d70-053a09ca4d9e' :'Visma Netvisor',\r\n                        '27e271d5-41f5-4319-ab29-4d5d9eb945c6': 'Lemonsoft',\r\n                        'd311f9d3-8c3a-4fd8-a665-8e3698e41e87': 'Tampuuri',\r\n                        'd58e95b7-d0b5-40ac-992b-6d3b29efc45e': 'Domus',\r\n                        '54e93c5f-bd74-4157-8a74-3515be7f585d': 'Oscar Software',\r\n                        '0e4f0a71-dcb9-43ba-9028-0239e674711f': 'Digia Enterprise',\r\n                        '2ccefa46-7992-46c5-9d87-b88336935916': 'Digia Enterprise - VILPE',\r\n                        'c36c24b9-5e2c-4f44-b67a-90d81aeea257': 'iScala'\r\n                      }\">\r\n                    </salaxy-input-enum>\r\n                    <sxy-input model=\"form.method\" read-only=\"false\"></sxy-input>\r\n                    <salaxy-input-enum disabled=\"false\" enum=\"ExportMethod\" label=\"SALAXY.MODEL.AccountingTargetSettings.availableMethods.title\" name=\"availableMethods\"\r\n                      type=\"multi-select\" ng-model=\"$ctrl.current.availableMethods\"></salaxy-input-enum>\r\n                    <button ng-show=\"$settings.isApiIntegration($ctrl.current)\" type=\"button\" class=\"btn btn-sm btn-default\"\r\n                      ng-click=\"$settings.openChannelSetupDialog($ctrl.current, $close)\">\r\n                      Siirry APIn konfigurointiin <i class=\"bi bi-box-arrow-up-right\"></i>\r\n                    </button>\r\n                    <button ng-show=\"$settings.isApiIntegration($ctrl.current)\" type=\"button\" class=\"btn btn-sm btn-default\"\r\n                      ng-click=\"$settings.configureCoa($ctrl.current, $close)\">\r\n                      Siirry tilikartan konfigurointiin <i class=\"bi bi-chevron-right\"></i>\r\n                    </button>\r\n                  </fieldset>\r\n                </form>\r\n              </sxy-input>\r\n              <sxy-input model=\"form.accounting.defaultPeriodDateKind\"\r\n                read-only=\"{{!$ctrl.current.accounting.denyServiceModel  && $ctrl.current.partner.serviceModel.features.accounting}}\"></sxy-input>\r\n              <salaxy-input-enum ng-if=\"$ctrl.defaultAccountingTarget\"\r\n                read-only=\"!$ctrl.current.accounting.denyServiceModel  && $ctrl.current.partner.serviceModel.features.accounting\" type=\"select\" name=\"method\"\r\n                ng-model=\"$ctrl.defaultAccountingTarget.method\" enum=\"ExportMethod\" label=\"SALAXY.MODEL.AccountingTargetSettings.method.title\"></salaxy-input-enum>\r\n              <legend sxy-text=\"SALAXY.MODEL.AccountingSettings.reportDelivery.title\"></legend>\r\n              <sxy-input model=\"form.accounting.reportDelivery.isEnabled\"></sxy-input>\r\n              <sxy-input model=\"form.accounting.reportDelivery.address\"></sxy-input>\r\n              <legend sxy-text=\"SALAXY.MODEL.AccountingSettings.accountantReportDelivery.title\"></legend>\r\n              <sxy-input model=\"form.accounting.accountantReportDelivery.isEnabled\"></sxy-input>\r\n              <sxy-input model=\"form.accounting.accountantReportDelivery.address\"></sxy-input>\r\n            </fieldset>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"holidays-tab\">\r\n            <fieldset>\r\n              <legend><span sxy-text=\"SALAXY.MODEL.HolidaySettings.title\"></span> <span\r\n                  ng-if=\"!$ctrl.current.holiday.denyServiceModel && $ctrl.current.partner.serviceModel.features.holiday\" class=\"badge bg-danger float-end\"\r\n                  sxy-text=\"SALAXY.NG1.ProSettingsComponent.serviceModelBadge\"></span></legend>\r\n              <sxy-input model=\"form.partner.serviceModel.features.holiday\" label=\"SALAXY.NG1.ProSettingsComponent.customHoliday\" read-only=\"true\"></sxy-input>\r\n              <salaxy-input-boolean label=\"SALAXY.NG1.ProSettingsComponent.overwriteServiceModel\" name=\"uc6\" ng-change=\"$ctrl.confirmServiceModelChange()\"\r\n                ng-if=\"$ctrl.current.partner.serviceModel.features.holiday\" ng-model=\"$ctrl.current.holiday.denyServiceModel\"></salaxy-input-boolean>\r\n              <!--div ng-if=\"('bizConfigs' | sxyIsInRole) && ($ctrl.current.holiday.denyServiceModel || !$ctrl.current.partner.serviceModel.features.holiday)\" ng-controller=\"TemplateCrudController as $templateCrudCtrl\">\r\n                <button type=\"button\" class=\"btn btn-sm btn-default\"\r\n                  ng-click=\"$templateCrudCtrl.selectTemplate()\">\r\n                  <i class=\"bi bi-plus\"></i> <span sxy-text=\"Lisää valmiista mallista...\"></span>\r\n                </button>\r\n              </div-->\r\n              <sxy-input model=\"form.holiday.holidayPaySettings\"\r\n                read-only=\"{{!$ctrl.current.holiday.denyServiceModel  && $ctrl.current.partner.serviceModel.features.holiday }}\" include=\"holidayPayCalculation\">\r\n                <form>\r\n                  <fieldset>\r\n                    <legend sxy-text=\"SALAXY.MODEL.HolidayPaySettings.title\"></legend>\r\n                    <salaxy-input-enum ng-show=\"!('bizConfigs' | sxyIsInRole)\" enum=\"HolidayPayCalculation\" label=\"SALAXY.MODEL.HolidayPaySettings.holidayPayCalculation.title\" name=\"holidayPayCalculation\" filter=\"averageDailyPay,averageHourlyPay,percentageBasedPay,holidayCompensation\" require=\"true\" ng-model=\"$ctrl.current.holidayPayCalculation\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-enum>\r\n                    <salaxy-input-enum ng-show=\"'bizConfigs' | sxyIsInRole\" enum=\"HolidayPayCalculation\" label=\"SALAXY.MODEL.HolidayPaySettings.holidayPayCalculation.title\" name=\"holidayPayCalculation\" filter=\"averageDailyPay,averageHourlyPay,percentageBasedPay,holidayCompensation,scriptPay\" require=\"true\" ng-model=\"$ctrl.current.holidayPayCalculation\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-enum>\r\n                    <salaxy-input-collective-bargain-agreement ng-show=\"'bizConfigs' | sxyIsInRole\" name=\"cbaCode\" ng-model=\"$ctrl.current.cbaCode\" label=\"SALAXY.MODEL.HolidayPaySettings.cbaCode.title\"></salaxy-input-collective-bargain-agreement>\r\n                    <salaxy-input-employee-group ng-show=\"'bizConfigs' | sxyIsInRole\" name=\"employeeGroup\" ng-model=\"$ctrl.current.employeeGroup\" label=\"SALAXY.MODEL.HolidayPaySettings.employeeGroup.title\"></salaxy-input-employee-group>\r\n                    <sxy-input model=\"form.disabled\"></sxy-input>\r\n                    <sxy-input model=\"form.startYear\" label=\"SALAXY.MODEL.HolidayPaySettings.startYear.title\"></sxy-input>  \r\n                    <sxy-input model=\"form.endYear\" label=\"SALAXY.MODEL.HolidayPaySettings.endYear.title\"></sxy-input> \r\n                    <legend  ng-show=\"$ctrl.current.holidayPayCalculation && $ctrl.current.holidayPayCalculation != 'scriptPay'\" sxy-text=\"SALAXY.MODEL.HolidayPaySettings.salaryTypes.title\"></legend>\r\n                    <sxy-input  ng-show=\"$ctrl.current.holidayPayCalculation && $ctrl.current.holidayPayCalculation != 'scriptPay'\" model=\"form.salaryTypes\" template-url=\"salaxy-components/sxy-form/custom-templates/pay-stats-row-types.html\"></sxy-input>\r\n                    <legend ng-show=\"$ctrl.current.holidayPayCalculation == 'averageHourlyPay'\" sxy-text=\"SALAXY.MODEL.HolidayPaySettings.workingTimeTypes.title\"></legend>\r\n                    <sxy-input ng-show=\"$ctrl.current.holidayPayCalculation == 'averageHourlyPay'\" model=\"form.workingTimeTypes\" template-url=\"salaxy-components/sxy-form/custom-templates/pay-stats-row-types.html\"></sxy-input>\r\n                    <legend ng-show=\"$ctrl.current.holidayPayCalculation == 'averageDailyPay'\" sxy-text=\"SALAXY.MODEL.HolidayPaySettings.overtimeTypes.title\"></legend>\r\n                    <sxy-input  ng-show=\"$ctrl.current.holidayPayCalculation == 'averageDailyPay'\" model=\"form.overtimeTypes\" template-url=\"salaxy-components/sxy-form/custom-templates/pay-stats-row-types.html\"></sxy-input>\r\n                    <legend ng-show=\"$ctrl.current.holidayPayCalculation == 'averageHourlyPay' || $ctrl.current.holidayPayCalculation == 'averageDailyPay'\" sxy-text=\"SALAXY.MODEL.HolidayPaySettings.multipliers.title\"></legend>\r\n                    <salaxy-input-holiday-multipliers ng-show=\"$ctrl.current.holidayPayCalculation == 'averageHourlyPay' || $ctrl.current.holidayPayCalculation == 'averageDailyPay'\" name=\"multipliers\" label=\"SALAXY.MODEL.HolidayPaySettings.multipliers.title\" ng-model=\"$ctrl.current.multipliers\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-holiday-multipliers>\r\n                    <sxy-code-editor ng-show=\"$ctrl.current.holidayPayCalculation == 'scriptPay'\" ng-model=\"$ctrl.current.script\"></sxy-code-editor>\r\n                  </fieldset>\r\n                </form>\r\n              </sxy-input>\r\n              <!--div ng-if=\"('bizConfigs' | sxyIsInRole) && ($ctrl.current.holiday.denyServiceModel || !$ctrl.current.partner.serviceModel.features.holiday)\" ng-controller=\"TemplateCrudController as $templateCrudCtrl\">\r\n                <button type=\"button\" class=\"btn btn-sm btn-default\"\r\n                  ng-click=\"$templateCrudCtrl.selectTemplate()\">\r\n                  <i class=\"bi bi-plus\"></i> <span sxy-text=\"Lisää valmiista mallista...\"></span>\r\n                </button>\r\n              </div-->\r\n              <sxy-input model=\"form.holiday.holidayAccrualSettings\"\r\n                read-only=\"{{!$ctrl.current.holiday.denyServiceModel  && $ctrl.current.partner.serviceModel.features.holiday }}\" include=\"code\">\r\n                <form>\r\n                  <fieldset>\r\n                    <legend sxy-text=\"SALAXY.MODEL.HolidayAccrualSettings.title\"></legend>\r\n                    <salaxy-input-enum ng-show=\"!('bizConfigs' | sxyIsInRole)\" enum=\"HolidayCode\" label=\"SALAXY.MODEL.HolidayAccrualSettings.code.title\" name=\"code\" filter=\"permanent35Hours\" require=\"true\" ng-model=\"$ctrl.current.code\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-enum>\r\n                    <salaxy-input-enum ng-show=\"'bizConfigs' | sxyIsInRole\" enum=\"HolidayCode\" label=\"SALAXY.MODEL.HolidayAccrualSettings.code.title\" name=\"code\" filter=\"permanent35Hours,script\" require=\"true\" ng-model=\"$ctrl.current.code\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-enum>\r\n                    <salaxy-input-collective-bargain-agreement ng-show=\"'bizConfigs' | sxyIsInRole\" name=\"cbaCode\" ng-model=\"$ctrl.current.cbaCode\" label=\"SALAXY.MODEL.HolidayAccrualSettings.cbaCode.title\"></salaxy-input-collective-bargain-agreement>\r\n                    <salaxy-input-employee-group ng-show=\"'bizConfigs' | sxyIsInRole\" name=\"employeeGroup\" ng-model=\"$ctrl.current.employeeGroup\" label=\"SALAXY.MODEL.HolidayAccrualSettings.employeeGroup.title\"></salaxy-input-employee-group>\r\n                    <sxy-input model=\"form.disabled\"></sxy-input>\r\n                    <sxy-input model=\"form.startYear\" label=\"SALAXY.MODEL.HolidayAccrualSettings.startYear.title\"></sxy-input>  \r\n                    <sxy-input model=\"form.endYear\" label=\"SALAXY.MODEL.HolidayAccrualSettings.endYear.title\"></sxy-input> \r\n                    <legend ng-show=\"$ctrl.current.code == 'permanent35Hours'\" sxy-text=\"SALAXY.MODEL.HolidayAccrualSettings.workingTimeTypes.title\"></legend>\r\n                    <sxy-input  ng-show=\"$ctrl.current.code == 'permanent35Hours'\" model=\"form.workingTimeTypes\" template-url=\"salaxy-components/sxy-form/custom-templates/pay-stats-row-types.html\"></sxy-input>\r\n                    <sxy-code-editor ng-show=\"$ctrl.current.code == 'script'\" ng-model=\"$ctrl.current.script\"></sxy-code-editor>\r\n                  </fieldset>\r\n                </form>\r\n              </sxy-input>\r\n            </fieldset>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"other-tab\">\r\n            <fieldset>\r\n              <legend><span sxy-text=\"SALAXY.NG1.ProSettingsComponent.incomesRegister\"></span> </legend>\r\n              <sxy-input model=\"form.calc.incomesRegister.irReporting\"></sxy-input>\r\n              <sxy-input model=\"form.calc.incomesRegister.taxReferenceNumber\"></sxy-input>\r\n            </fieldset>\r\n            <fieldset>\r\n              <legend><span sxy-text=\"SALAXY.NG1.ProSettingsComponent.usecases\"></span> <span\r\n                  ng-if=\"!$ctrl.current.usecase.denyServiceModel && $ctrl.current.partner.serviceModel.features.usecase\" class=\"badge bg-danger float-end\"\r\n                  sxy-text=\"SALAXY.NG1.ProSettingsComponent.serviceModelBadge\"></span></legend>\r\n              <sxy-input model=\"form.usecase.serverUrl\" label=\"Integration server (staging)\"></sxy-input>\r\n              <sxy-input model=\"form.partner.serviceModel.features.usecase\" label=\"SALAXY.NG1.ProSettingsComponent.customUsecases\" read-only=\"true\"></sxy-input>\r\n              <salaxy-input-boolean label=\"SALAXY.NG1.ProSettingsComponent.overwriteServiceModel\" name=\"uc3\" ng-change=\"$ctrl.confirmServiceModelChange()\"\r\n                ng-if=\"$ctrl.current.partner.serviceModel.features.usecase\" ng-model=\"$ctrl.current.usecase.denyServiceModel\"></salaxy-input-boolean>\r\n              <sxy-input template-url=\"salaxy-components/sxy-form/custom-templates/array-usecase.html\" model=\"form.usecase.usecases\"\r\n                read-only=\"{{!$ctrl.current.usecase.denyServiceModel  && $ctrl.current.partner.serviceModel.features.usecase}}\">\r\n                <form>\r\n                  <fieldset ng-show=\"!$ctrl.logic.showDelete\" ng-controller=\"CompanySettingsController as $companySettingsCtrl\">\r\n                    <salaxy-odata-table url=\"/v03/api/usecases\" template-url=\"salaxy-components/odata/lists/UsecaseSelect.html\" selected-items=\"$ctrl.selectedItems\"\r\n                      on-list-select=\"$companySettingsCtrl.onUsecaseSelect($ctrl.current, $ctrl.logic, value, item, allItems)\">\r\n                    </salaxy-odata-table>\r\n                  </fieldset>\r\n                  <fieldset ng-show=\"$ctrl.logic.showDelete\">\r\n                    <sxy-input model=\"form.uri\" read-only=\"true\"></sxy-input>\r\n                    <sxy-input model=\"form.label\" read-only=\"true\"></sxy-input>\r\n                    <sxy-input model=\"form.itemType\" read-only=\"true\"></sxy-input>\r\n                    <sxy-input model=\"form.status\"></sxy-input>\r\n                    <sxy-input model=\"form.order\"></sxy-input>\r\n                  </fieldset>\r\n                </form>\r\n              </sxy-input>\r\n            </fieldset>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"irdelivery-tab\">\r\n            <fieldset>\r\n              <legend>Tulorekisterivarmenteen omistaja</legend>\r\n              <p\r\n                sxy-text=\"Jos haluat käyttää tilitoimistovarmennetta Palkkaus.fi:n varmenteen sijasta, anna käytettävän varmenteen Y-tunnus.\">\r\n              </p>\r\n              <salaxy-input label=\"Tulorekisterivarmenteen omistajan Y-tunnus\" name=\"senderOfficialId\"\r\n                ng-model=\"$ctrl.current.calc.incomesRegister.irDelivery.senderOfficialId\"></salaxy-input>\r\n            </fieldset>\r\n            <fieldset>\r\n              <legend>Tulorekisteriraportin yhteyshenkilöt</legend>\r\n              <table class=\"table\">\r\n                <thead>\r\n                  <tr>\r\n                    <th>{{('Nimi') | sxyTranslate}}</th>\r\n                    <th>{{('Puhelin') | sxyTranslate}}</th>\r\n                    <th>{{('Sähköposti') | sxyTranslate}}</th>\r\n                    <th>{{('Vastuualue') | sxyTranslate}}</th>\r\n                    <th class=\"right\">\r\n                      <button type=\"button\" class=\"btn btn-primary btn-xs\"\r\n                        ng-click=\"$ctrl.current.calc.incomesRegister.irDelivery.contactPersons.push({})\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n                    </th>\r\n                  </tr>\r\n                </thead>\r\n                <tbody>\r\n                  <tr ng-repeat=\"item in $ctrl.current.calc.incomesRegister.irDelivery.contactPersons\">\r\n                    <td>\r\n                      <salaxy-input require=\"true\" ng-model=\"item.name\" name=\"{{ 'name' + $index }}\" label-type=\"plain\"></salaxy-input>\r\n                    </td>\r\n                    <td>\r\n                      <salaxy-input require=\"true\" ng-model=\"item.telephone\" name=\"{{ 'telephone' + $index }}\" label-type=\"plain\" sxy-mobile-phone></salaxy-input>\r\n                    </td>\r\n                    <td>\r\n                      <salaxy-input require=\"true\" ng-model=\"item.email\" name=\"{{ 'email' + $index }}\" label-type=\"plain\" sxy-email></salaxy-input>\r\n                    </td>\r\n                    <td>\r\n                      <salaxy-input-enum require=\"true\" ng-model=\"item.responsibilityCode\" name=\"{{ 'responsibilityCode' + $index }}\" label-type=\"plain\" type=\"select\"\r\n                        options=\"{ contentIssues: 'Raporttien sisältö', technicalIssues: 'Tekniset asiat' }\"></salaxy-input-enum>\r\n                    </td>\r\n                    <td class=\"text-right\">\r\n                      <button type=\"button\" class=\"btn btn-danger\" ng-click=\"$ctrl.current.calc.incomesRegister.irDelivery.contactPersons.splice($index, 1)\">\r\n                        <i class=\"bi bi-trash\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\"></i>\r\n                      </button>\r\n                    </td>\r\n                  </tr>\r\n                </tbody>\r\n              </table>\r\n            </fieldset>\r\n            <legend>Yrityksesi tulorekisterivarmenteen tila</legend>\r\n                <table class=\"table\">\r\n                  <tr>\r\n                    <th>Luotu</th>\r\n                    <th>Voimassaolo päättyy</th>\r\n                  </tr>\r\n                  <tr ng-if=\"!$ctrl.irCertificate.id\">\r\n                    <td colspan=\"2\">Ei voimassa olevaa varmennetta</td>\r\n                  </tr>\r\n                  <tr ng-if=\"$ctrl.irCertificate.id\">\r\n                    <td>{{$ctrl.irCertificate.updatedAt | date}}</td>\r\n                    <td>{{$ctrl.irCertificate.expiresAt | date}}</td>\r\n                  </tr>\r\n                </table>\r\n              </fieldset>\r\n              <fieldset>\r\n                <legend>Varmenteen luonti/uusinta</legend>\r\n                <salaxy-input-enum ng-if=\"$ctrl.irCertificate.id\" ng-init=\"$ctrl.irCertificateAction = 'renew'\" label=\"Toimenpide\" ng-model=\"$ctrl.irCertificateAction\" name=\"certAction\" type=\"radio\"\r\n                  options=\"{ create: 'Luo uusi varmenne', renew: 'Uusi nykyinen varmenne' }\"></salaxy-input-enum>\r\n                <salaxy-input-enum ng-if=\"!$ctrl.irCertificate.id\" ng-init=\"$ctrl.irCertificateAction = 'create'\" label=\"Toimenpide\" ng-model=\"$ctrl.irCertificateAction\" name=\"certAction\" type=\"radio\"\r\n                  options=\"{ create: 'Luo uusi varmenne'}\"></salaxy-input-enum>\r\n                <salaxy-input ng-if=\"$ctrl.irCertificateAction == 'create'\" require=\"true\" label=\"Siirtotunnus\" ng-model=\"$ctrl.irCertificateTransferId\"\r\n                  name=\"transferId\"></salaxy-input>\r\n                <salaxy-input ng-if=\"$ctrl.irCertificateAction == 'create'\" require=\"true\" label=\"Kertakäyttösalasana\" ng-model=\"$ctrl.irCertificateTransferPassword\"\r\n                  name=\"transferPassword\" type=\"password\"></salaxy-input>\r\n\r\n                  <div class=\"row\">\r\n                    <div class=\"col-xs-12 text-right\">\r\n                      <button type=\"button\" ng-if=\"$ctrl.irCertificateAction == 'create'\" class=\"btn btn-primary\" ng-disabled=\"$ctrl.isSaving('irCertificate')\"\r\n                        ng-click=\"$ctrl.createIrCertificate($ctrl.irCertificateTransferId, $ctrl.irCertificateTransferPassword)\"><span ng-if=\"$ctrl.isSaving('irCertificate')\"><i\r\n                            class=\"bi bi-arrow-repeat bi-spin\"></i></span><span sxy-text=\"Luo uusi varmenne\"></span></button>\r\n                      <button type=\"button\" ng-if=\"$ctrl.irCertificateAction == 'renew'\" class=\"btn btn-primary\" ng-disabled=\"$ctrl.isSaving('irCertificate')\"\r\n                        ng-click=\"$ctrl.renewIrCertificate()\"><span ng-if=\"$ctrl.isSaving('irCertificate')\"><i class=\"bi bi-arrow-repeat bi-spin\"></i></span><span\r\n                          sxy-text=\"Uusi nykyinen varmenne\"></span></button>\r\n                    </div>\r\n                  </div>\r\n              </fieldset>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"paystats-tab\">\r\n            <fieldset>\r\n              <legend><span sxy-text=\"SALAXY.MODEL.PayStatsSettings.title\"></span> <span\r\n                  ng-if=\"!$ctrl.current.payStats.denyServiceModel && $ctrl.current.partner.serviceModel.features.payStats\" class=\"badge bg-danger float-end\"\r\n                  sxy-text=\"SALAXY.NG1.ProSettingsComponent.serviceModelBadge\"></span></legend>\r\n              <sxy-input model=\"form.partner.serviceModel.features.payStats\" label=\"SALAXY.NG1.ProSettingsComponent.customPayStats\" read-only=\"true\"></sxy-input>\r\n              <salaxy-input-boolean label=\"SALAXY.NG1.ProSettingsComponent.overwriteServiceModel\" name=\"serviceModelPayStats\" ng-change=\"$ctrl.confirmServiceModelChange()\"\r\n                ng-if=\"$ctrl.current.partner.serviceModel.features.payStats\" ng-model=\"$ctrl.current.payStats.denyServiceModel\"></salaxy-input-boolean>\r\n              <!--div ng-if=\"('bizConfigs' | sxyIsInRole) && ($ctrl.current.payStats.denyServiceModel || !$ctrl.current.partner.serviceModel.features.payStats)\" ng-controller=\"TemplateCrudController as $templateCrudCtrl\">\r\n                <button type=\"button\" class=\"btn btn-sm btn-default\"\r\n                  ng-click=\"$templateCrudCtrl.selectTemplate()\">\r\n                  <i class=\"bi bi-plus\"></i> <span sxy-text=\"Lisää valmiista mallista...\"></span>\r\n                </button>\r\n              </div-->\r\n              <sxy-input model=\"form.payStats.types\"\r\n                read-only=\"{{!$ctrl.current.payStats.denyServiceModel  && $ctrl.current.partner.serviceModel.features.payStats }}\" include=\"id,kind,periodLength,cbaCode,employeeGroup\">\r\n                <form>\r\n                  <fieldset>\r\n                    <legend sxy-text=\"SALAXY.MODEL.PayStatsTypeDefinition.title\"></legend>\r\n                    <sxy-input model=\"form.id\" require=\"true\" read-only=\"{{$ctrl.logic.isReadOnly}}\"></sxy-input>\r\n                    <sxy-input model=\"form.description\"></sxy-input>\r\n                    <salaxy-input-enum enum=\"PayStatsKind\" label=\"SALAXY.MODEL.PayStatsTypeDefinition.kind.title\" name=\"kind\" require=\"true\" ng-model=\"$ctrl.current.kind\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-enum>\r\n                    <salaxy-input-enum enum=\"PayStatsPeriodLength\" label=\"SALAXY.MODEL.PayStatsTypeDefinition.periodLength.title\" name=\"periodLength\" require=\"true\" ng-model=\"$ctrl.current.periodLength\" filter=\"quarter,month,year\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-enum>\r\n                    <salaxy-input-enum enum=\"PeriodDateKind\" label=\"SALAXY.MODEL.PayStatsTypeDefinition.periodDateKind.title\" name=\"periodDateKind\" require=\"true\" ng-model=\"$ctrl.current.periodDateKind\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-enum>                   \r\n                    <salaxy-input-collective-bargain-agreement name=\"cbaCode\" ng-model=\"$ctrl.current.cbaCode\" label=\"SALAXY.MODEL.PayStatsTypeDefinition.cbaCode.title\"></salaxy-input-collective-bargain-agreement>\r\n                    <salaxy-input-employee-group name=\"employeeGroup\" ng-model=\"$ctrl.current.employeeGroup\" label=\"SALAXY.MODEL.PayStatsTypeDefinition.employeeGroup.title\"></salaxy-input-employee-group>\r\n                    <sxy-input model=\"form.disabled\"></sxy-input>\r\n                    <sxy-input model=\"form.startDate\"></sxy-input>\r\n                    <sxy-input model=\"form.endDate\"></sxy-input>\r\n                    <legend ng-show=\"$ctrl.current.kind == 'averageHourlyPay'\" sxy-text=\"SALAXY.MODEL.PayStatsTypeDefinition.salaryTypes.title\"></legend>\r\n                    <sxy-input ng-show=\"$ctrl.current.kind == 'averageHourlyPay'\" model=\"form.salaryTypes\" template-url=\"salaxy-components/sxy-form/custom-templates/pay-stats-row-types.html\"></sxy-input>\r\n                    <legend ng-show=\"$ctrl.current.kind == 'averageHourlyPay'\" sxy-text=\"SALAXY.MODEL.PayStatsTypeDefinition.workingTimeTypes.title\"></legend>\r\n                    <sxy-input ng-show=\"$ctrl.current.kind == 'averageHourlyPay'\" format=\"undefined\" model=\"form.minWorkingTime\"></sxy-input>\r\n                    <sxy-input ng-show=\"$ctrl.current.kind == 'averageHourlyPay'\" model=\"form.workingTimeTypes\" template-url=\"salaxy-components/sxy-form/custom-templates/pay-stats-row-types.html\"></sxy-input>\r\n                    <sxy-code-editor ng-show=\"$ctrl.current.kind == 'script'\" ng-model=\"$ctrl.current.script\"></sxy-code-editor>\r\n                  </fieldset>\r\n                </form>\r\n              </sxy-input>\r\n            </fieldset>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"employeeGroups-tab\">\r\n            <fieldset>\r\n              <legend><span sxy-text=\"SALAXY.MODEL.CalculationSettings.employeeGroups.title\"></span></legend>\r\n              <sxy-input model=\"form.calc.employeeGroups\">\r\n                <form>\r\n                  <fieldset>\r\n                    <legend sxy-text=\"SALAXY.MODEL.EmployeeGroupDefinition.title\"></legend>\r\n                    <sxy-input model=\"form.id\" require=\"true\" read-only=\"{{$ctrl.logic.isReadOnly}}\"></sxy-input>\r\n                    <sxy-input model=\"form.name\"></sxy-input>\r\n                  </fieldset>\r\n                </form>\r\n              </sxy-input>\r\n            </fieldset>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"configs-tab\">\r\n            <fieldset>\r\n              <legend><span sxy-text=\"SALAXY.MODEL.CompanyAccountSettings.configs.title\"></span></legend>\r\n              <sxy-input model=\"form.configs\" include=\"name,data\">\r\n                <form>\r\n                  <fieldset>\r\n                    <legend sxy-text=\"SALAXY.MODEL.BizConfig.title\"></legend>\r\n                    <sxy-input require=\"true\" model=\"form.name\"></sxy-input>\r\n                    <salaxy-input-collective-bargain-agreement name=\"cbaCode\" ng-model=\"$ctrl.current.cbaCode\" label=\"SALAXY.MODEL.BizConfig.cbaCode.title\"></salaxy-input-collective-bargain-agreement>\r\n                    <salaxy-input-employee-group name=\"employeeGroup\" ng-model=\"$ctrl.current.employeeGroup\" label=\"SALAXY.MODEL.BizConfig.employeeGroup.title\"></salaxy-input-employee-group>\r\n                    <sxy-input model=\"form.disabled\"></sxy-input>\r\n                    <sxy-input model=\"form.startDate\"></sxy-input>\r\n                    <sxy-input model=\"form.endDate\"></sxy-input>\r\n                    <salaxy-input-enum ng-model=\"$ctrl.current.dataType\" name=\"dataType\" label=\"SALAXY.MODEL.BizConfig.dataType.title\" options=\"{\r\n                      'string': 'Teksti',\r\n                      'number': 'Luku',\r\n                      'boolean': 'Kyllä/Ei'\r\n                     }\"></salaxy-input-enum>\r\n                     <salaxy-input ng-show=\"!$ctrl.current.dataType || $ctrl.current.dataType === 'string'\" ng-model=\"$ctrl.current.data\" name=\"dataString\" label=\"SALAXY.MODEL.BizConfig.data.title\"></salaxy-input>\r\n                     <salaxy-input-number ng-show=\"$ctrl.current.dataType == 'number'\" ng-model=\"$ctrl.current.data\"  name=\"dataNumber\" label=\"SALAXY.MODEL.BizConfig.data.title\"></salaxy-input-number>\r\n                     <salaxy-input-boolean ng-show=\"$ctrl.current.dataType == 'boolean'\" ng-model=\"$ctrl.current.data\" name=\"dataBoolean\" label=\"SALAXY.MODEL.BizConfig.data.title\"></salaxy-input-boolean>\r\n                    <sxy-input model=\"form.updatedAt\" read-only=\"true\"></sxy-input>\r\n                    <sxy-input model=\"form.updatedBy\" read-only=\"true\"></sxy-input>\r\n                  </fieldset>\r\n                </form>\r\n              </sxy-input>\r\n            </fieldset>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"readonly-tab\">\r\n            <fieldset>\r\n              <legend><span sxy-text=\"SALAXY.NG1.ProSettingsComponent.pricing\"></span> <span ng-if=\"$ctrl.current.partner.accountId\" class=\"badge bg-danger float-end\"\r\n                  sxy-text=\"SALAXY.NG1.ProSettingsComponent.serviceModelBadge\"></span></legend>\r\n              <sxy-input model=\"form.partner.serviceModel.pricing.pricingModel\" read-only=\"true\"></sxy-input>\r\n              <sxy-input model=\"form.partner.serviceModel.pricing.fixedFee\" read-only=\"true\"></sxy-input>\r\n            </fieldset>\r\n            <fieldset>\r\n              <legend><span sxy-text=\"SALAXY.NG1.ProSettingsComponent.webApp\"></span> <span class=\"badge bg-danger float-end\"\r\n                  sxy-text=\"SALAXY.NG1.ProSettingsComponent.serviceModelBadge\"></span></legend>\r\n              <sxy-input model=\"form.partner.serviceModel.site.webApp\" read-only=\"true\"></sxy-input>\r\n              <sxy-input model=\"form.partner.serviceModel.site.webAppUrl\" read-only=\"true\"></sxy-input>\r\n              <sxy-input model=\"form.partner.serviceModel.site.webAppName\" read-only=\"true\"></sxy-input>\r\n            </fieldset>\r\n            <fieldset>\r\n              <legend><span sxy-text=\"SALAXY.NG1.ProSettingsComponent.branding\"></span> <span class=\"badge bg-danger float-end\"\r\n                  sxy-text=\"SALAXY.NG1.ProSettingsComponent.serviceModelBadge\"></span></legend>\r\n              <sxy-input model=\"form.partner.serviceModel.branding.logo\" read-only=\"true\"></sxy-input>\r\n              <sxy-input model=\"form.partner.serviceModel.branding.skin\" read-only=\"true\"></sxy-input>\r\n            </fieldset>\r\n            <fieldset>\r\n              <legend><span sxy-text=\"SALAXY.MODEL.FormsSettings.title\"></span> <span\r\n                  ng-if=\"!$ctrl.current.forms.denyServiceModel && $ctrl.current.partner.serviceModel.features.forms\" class=\"badge bg-danger float-end\"\r\n                  sxy-text=\"SALAXY.NG1.ProSettingsComponent.serviceModelBadge\"></span></legend>\r\n              <sxy-input model=\"form.partner.serviceModel.features.forms\" label=\"SALAXY.NG1.ProSettingsComponent.customForms\" read-only=\"true\"></sxy-input>\r\n            </fieldset>\r\n            <fieldset>\r\n              <legend><span sxy-text=\"Tulorekisterin varmenne\"></span> <span\r\n                  ng-if=\"$ctrl.current.partner.serviceModel.features.irDelivery\" class=\"badge bg-danger float-end\"\r\n                  sxy-text=\"SALAXY.NG1.ProSettingsComponent.serviceModelBadge\"></span></legend>\r\n              <sxy-input model=\"form.partner.serviceModel.features.irDelivery\" label=\"Tilitoimiston asettama varmenne käytössä\" read-only=\"true\"></sxy-input>\r\n            </fieldset>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </sxy-form>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/settings/RowTypesSettings.html\",`<div class=\"salaxy-component salaxy-pro-settings\" ng-class=\"'salaxy-pro-settings-' + $ctrl.mode\"\r\n  ng-if=\"$ctrl.current\" ng-switch=\"$ctrl.mode\">\r\n  <div ng-switch-when=\"custom\">\r\n    <div class=\"d-flex mb-3 align-items-center\">\r\n      <div class=\"btn-group\">\r\n        <button id=\"categories\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\" aria-expanded=\"false\" ng-disabled=\"disabled\">\r\n          Kategoriat\r\n        </button>\r\n        <ul class=\"dropdown-menu\" aria-labelledby=\"categories\">\r\n          <li><a class=\"dropdown-item\" href=\"\" ng-click=\"$ctrl.categories = null\">All categories (no filter)</a></li>\r\n          <li><a class=\"dropdown-item\" href=\"\" ng-click=\"$ctrl.categories = ['salary', 'salaryCalc', 'holidays', 'salaryAdditions']\">Salaries and additions</a></li>\r\n          <li><a class=\"dropdown-item\" href=\"\" ng-click=\"$ctrl.categories = ['benefits']\">Benefits</a></li>\r\n          <li><a class=\"dropdown-item\" href=\"\" ng-click=\"$ctrl.categories = ['expenses']\">Expenses</a></li>\r\n          <li><a class=\"dropdown-item\" href=\"\" ng-click=\"$ctrl.categories = ['deductions']\">Deductions</a></li>\r\n          <li><a class=\"dropdown-item\" href=\"\" ng-click=\"$ctrl.categories = ['other']\">Other</a></li>\r\n        </ul>\r\n      </div>\r\n      <div class=\"form-horizontal ms-2 flex-grow-1\">\r\n        <salaxy-input name=\"calcRowTypeSearch\" ng-model=\"$ctrl.searchText\" label=\"Search name and description\"></salaxy-input>\r\n      </div>\r\n    </div>\r\n    <ng-include src=\"'salaxy-components/settings/RowTypesSettings_table.html'\"></ng-include>\r\n  </div>\r\n  <div ng-switch-when=\"prices\">\r\n    <table class=\"table table-condensed\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\">Palkkalajien hinnat</th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.DateRange.labelStartAndEndDate\"></th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.price\"></th>\r\n          <th></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.pricesList\">\r\n          <td style=\"width: 32px;\">\r\n            <salaxy-avatar ng-if=\"row.rowType\" class=\"salaxy-calc-row-type-avatar\"\r\n              avatar=\"{ color: $ctrl.getConfig(row).color, initials: $ctrl.getConfig(row).iconText, entityType: 'company' }\"></salaxy-avatar>\r\n          </td>\r\n          <td style=\"width: 40%;\">\r\n            <div>{{$ctrl.getMessagePlaceholderText(row)}}</div>\r\n            <div><small><code>{{ row.type }}{{ row.data.kind ? \"/\" + row.data.kind : \"\" }}</code></small>  &nbsp;</div>\r\n          </td>\r\n          <td class=\"right middle\">\r\n            <div>{{ row.period | sxyDateRange }}&nbsp;&nbsp;</div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <salaxy-input-number name=\"{{ 'iptPrice' + row.rowIndex }}\" ng-model=\"row.price\" label-type=\"plain\"  disabled=\"$ctrl.isDisabled(row, 'price')\" require=\"true\"></salaxy-input-number>\r\n          </td>\r\n          <td class=\"right\" style=\"width: 120px;\">\r\n            <button type=\"button\" class=\"edit btn btn-info\" ng-click=\"$ctrl.showEdit(row, 'auto')\"\r\n              title=\"{{'SALAXY.NG1.CalcRowsComponent.editor.buttons.infoIcon' | sxyTranslate}}\"><i class=\"bi bi-pencil-fill\"></i></button>\r\n            <button type=\"button\" class=\"btn btn-danger\" ng-click=\"$ctrl.delete(row)\"><i class=\"bi bi-trash-fill\"></i>\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n      <tfoot>\r\n        <tr>\r\n          <td></td>\r\n          <td class=\"middle\">\r\n            Lisää hinta:\r\n          </td>\r\n          <td>\r\n            <salaxy-calc-row-type name=\"newRowType\" model=\"$ctrl.newRow\" placeholder=\"SALAXY.NG1.CalcRowsComponent.editor.calcRowTypePlaceholder\"\r\n              on-row-changed=\"$ctrl.commitNewRow('price', false)\" categories=\"$ctrl.categories\" clear-on-select=\"true\"></salaxy-calc-row-type>\r\n          </td>\r\n          <td>\r\n            <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showRowTypeSelectionDialog()\"><i class=\"bi bi-info-circle-fill text-primary me-2\"></i> <span\r\n                sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.buttons.readMore\" ps=\"...\"></span></button>\r\n          </td>\r\n        </tr>\r\n      </tfoot>\r\n    </table>\r\n  </div>\r\n  <div ng-switch-when=\"copy\">\r\n    <table class=\"table table-condensed\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\">Laskelmalle kopioitavat rivit</th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.DateRange.labelStartAndEndDate\"></th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.price\"></th>\r\n          <th></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.copyRowsList\">\r\n          <td style=\"width: 32px;\">\r\n            <salaxy-avatar ng-if=\"row.rowType\" class=\"salaxy-calc-row-type-avatar\"\r\n              avatar=\"{ color: $ctrl.getConfig(row).color, initials: $ctrl.getConfig(row).iconText, entityType: 'company' }\"></salaxy-avatar>\r\n          </td>\r\n          <td style=\"width: 40%;\">\r\n            <div>{{$ctrl.getMessagePlaceholderText(row)}}</div>\r\n            <div><small><code>{{ row.type }}{{ row.data.kind ? \"/\" + row.data.kind : \"\" }}</code></small>  &nbsp;</div>\r\n          </td>\r\n          <td class=\"right middle\">\r\n            <div>{{ row.period | sxyDateRange }}&nbsp;&nbsp;</div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <salaxy-input-number name=\"{{ 'iptPrice' + row.rowIndex }}\" ng-model=\"row.price\" label-type=\"plain\"  disabled=\"$ctrl.isDisabled(row, 'price')\" require=\"true\"></salaxy-input-number>\r\n          </td>\r\n          <td class=\"right\">\r\n            <button type=\"button\" class=\"edit btn btn-info\" ng-click=\"$ctrl.showEdit(row, 'auto')\"\r\n              title=\"{{'SALAXY.NG1.CalcRowsComponent.editor.buttons.infoIcon' | sxyTranslate}}\"><i class=\"bi bi-pencil-square\"></i></button>\r\n            <button type=\"button\" class=\"btn btn-danger\" ng-click=\"$ctrl.delete(row)\"><i class=\"bi bi-trash-fill\"></i>\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n      <tfoot>\r\n        <tr>\r\n          <td></td>\r\n          <td class=\"middle\">\r\n            Lisää kopioitava rivi:\r\n          </td>\r\n          <td>\r\n            <salaxy-calc-row-type name=\"newRowType\" model=\"$ctrl.newRow\" placeholder=\"SALAXY.NG1.CalcRowsComponent.editor.calcRowTypePlaceholder\"\r\n              on-row-changed=\"$ctrl.commitNewRow('copy', false)\" categories=\"$ctrl.categories\"></salaxy-calc-row-type>\r\n          </td>\r\n          <td>\r\n            <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showRowTypeSelectionDialog()\"><i class=\"bi bi-info-lg text-primary\"></i> <span\r\n                sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.buttons.readMore\" ps=\"...\"></span></button>\r\n          </td>\r\n        </tr>\r\n      </tfoot>\r\n    </table>\r\n  </div>\r\n  <div ng-switch-when=\"defaults\">\r\n    <table class=\"table table-condensed\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\">Oletusrivit</th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.DateRange.labelStartAndEndDate\"></th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.totals.total\"></th>\r\n          <th></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.defaultsList\">\r\n          <td style=\"width: 32px;\">\r\n            <salaxy-avatar ng-if=\"row.rowType\" class=\"salaxy-calc-row-type-avatar\"\r\n              avatar=\"{ color: $ctrl.getConfig(row).color, initials: $ctrl.getConfig(row).iconText, entityType: 'company' }\"></salaxy-avatar>\r\n          </td>\r\n          <td style=\"width: 40%;\">\r\n            <div>{{row.message || ( \"CalculationRowType.\" + row.rowType | sxyEnum) }}</div>\r\n            <div>{{row.data.kind }}&nbsp;</div>\r\n          </td>\r\n          <td class=\"right middle\">\r\n            <div>{{ row.period | sxyDateRange }}&nbsp;&nbsp;</div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <salaxy-input-number name=\"{{ 'iptPrice' + row.rowIndex }}\" ng-model=\"row.price\" label-type=\"plain\"  disabled=\"$ctrl.isDisabled(row, 'price')\" require=\"true\"></salaxy-input-number>\r\n          </td>\r\n          <td class=\"right\">\r\n            <button type=\"button\" class=\"edit btn btn-info\" ng-click=\"$ctrl.showEdit(row, 'auto')\"\r\n              title=\"{{'SALAXY.NG1.CalcRowsComponent.editor.buttons.infoIcon' | sxyTranslate}}\">\r\n              <i class=\"bi bi-info-circle-fill\" ng-class=\"$ctrl.current == row ? 'bi-arrow-right-circle-fill' : 'bi-info-circle'\"></i></button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n      <tfoot>\r\n        <tr>\r\n          <td></td>\r\n          <td class=\"middle\">\r\n            Lisää oletusrivi:\r\n          </td>\r\n          <td>\r\n            <salaxy-calc-row-type name=\"newRowType\" model=\"$ctrl.newRow\" placeholder=\"SALAXY.NG1.CalcRowsComponent.editor.calcRowTypePlaceholder\"\r\n              on-row-changed=\"$ctrl.commitNewRow('manualRow', true)\" categories=\"$ctrl.categories\"></salaxy-calc-row-type>\r\n          </td>\r\n          <td>\r\n            <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showRowTypeSelectionDialog()\"><i class=\"bi bi-info-circle-fill text-primary me-2\"></i> <span\r\n                sxy-text=\"SALAXY.NG1.CalcRowsComponent.editor.buttons.readMore\" ps=\"...\"></span></button>\r\n          </td>\r\n        </tr>\r\n      </tfoot>\r\n    </table>\r\n  </div>\r\n  <div ng-switch-when=\"debugger\">\r\n    <salaxy-json-formatter key=\"'Rivit'\" json=\"$ctrl.list\" open=\"1\"></salaxy-json-formatter>\r\n    <hr />\r\n    <salaxy-calc-rows-editor ng-if=\"!$ctrl.isLoading\" rows=\"$ctrl.list\"\r\n      title=\"{{ 'SALAXY.NG1.WorkerDetailsComponent.defaultCalcRows' | sxyTranslate }}\" type=\"salary-defaults\"></salaxy-calc-rows-editor>\r\n  </div>\r\n  <div ng-switch-default>\r\n    <div class=\"d-flex mb-3 align-items-center\">\r\n      <div class=\"btn-group\">\r\n        <button id=\"categories\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\" aria-expanded=\"false\" ng-disabled=\"disabled\">\r\n          Kategoriat\r\n        </button>\r\n        <ul class=\"dropdown-menu\" aria-labelledby=\"categories\">\r\n          <li><a class=\"dropdown-item\" href=\"\" ng-click=\"$ctrl.categories = null\">All categories (no filter)</a></li>\r\n          <li><a class=\"dropdown-item\" href=\"\" ng-click=\"$ctrl.categories = ['salary', 'salaryCalc', 'holidays', 'salaryAdditions']\">Salaries and additions</a></li>\r\n          <li><a class=\"dropdown-item\" href=\"\" ng-click=\"$ctrl.categories = ['benefits']\">Benefits</a></li>\r\n          <li><a class=\"dropdown-item\" href=\"\" ng-click=\"$ctrl.categories = ['expenses']\">Expenses</a></li>\r\n          <li><a class=\"dropdown-item\" href=\"\" ng-click=\"$ctrl.categories = ['deductions']\">Deductions</a></li>\r\n          <li><a class=\"dropdown-item\" href=\"\" ng-click=\"$ctrl.categories = ['other']\">Other</a></li>\r\n        </ul>\r\n      </div>\r\n      <div class=\"form-horizontal ms-2 flex-grow-1\">\r\n        <salaxy-input name=\"calcRowTypeSearch\" ng-model=\"$ctrl.searchText\" label=\"Search name and description\"></salaxy-input>\r\n      </div>\r\n    </div>\r\n    <ng-include src=\"'salaxy-components/settings/RowTypesSettings_table.html'\"></ng-include>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/settings/RowTypesSettings_table.html\",`<div class=\"salaxy-calc-row-type-table\">\r\n  <div>\r\n    <div class=\"d-flex my-1 py-1 border-bottom ps-2\" style=\"background-color: #f5f5f5;\">\r\n      <salaxy-avatar class=\"salaxy-calc-row-type-avatar\" avatar=\"{ color: 'rgb(79, 205, 196)', initials: 'type', entityType: 'company' }\"></salaxy-avatar>\r\n      <div class=\"description w-100\">\r\n        <div class=\"flex-grow-1 row\">\r\n          <strong class=\"col-6\" sxy-text=\"SALAXY.NG1.CalcRowTypeComponent.rowType\" ps=\" (type)\"></strong>\r\n          <strong class=\"col-6\" sxy-text=\"SALAXY.NG1.CalcRowTypeComponent.rowTypeEn\"></strong>\r\n        </div>\r\n        <div sxy-text=\"SALAXY.NG1.CalcRowTypeComponent.rowDescription\" class=\"border-bottom py-1 mb-1\"></div>\r\n        <div class=\"flex-grow-1 row\">\r\n          <div class=\"col-6\" sxy-text=\"SALAXY.NG1.CalcRowTypeComponent.rowKind\" ps=\" (kind)\"></div>\r\n          <div class=\"col-6\" sxy-text=\"SALAXY.NG1.CalcRowTypeComponent.rowKindEn\"></div>\r\n        </div>\r\n      </div>\r\n      <div style=\"width: 140px;\"></div>\r\n  </div>\r\n  <div>\r\n    <div class=\"d-flex my-1 py-1 border-bottom ps-2\" ng-repeat=\"item in $ctrl.getCachedSearch($ctrl.searchText, true)\">\r\n      <salaxy-avatar ng-if=\"item.ui.iconText\" class=\"salaxy-calc-row-type-avatar me-2\" avatar=\"{ color: item.ui.color, initials: item.ui.iconText, entityType: 'company' }\"></salaxy-avatar>\r\n      <div class=\"description w-100\">\r\n        <div ng-if=\"item.ui.iconText\" class=\"row\">\r\n          <strong class=\"col-6 salaxy-highlight\" ng-bind-html=\"item.text | uibTypeaheadHighlight:$ctrl.searchText\"></strong>\r\n          <strong class=\"col-6 salaxy-highlight\" ng-bind-html=\"item.value | uibTypeaheadHighlight:$ctrl.searchText\"></strong>\r\n        </div>\r\n        <div ng-if=\"!item.ui.iconText\">\r\n          <div class=\"salaxy-highlight\" ng-bind-html=\"item.text | uibTypeaheadHighlight:$ctrl.searchText\"></div>\r\n          <div class=\"salaxy-highlight\" ng-bind-html=\"item.value.split('.')[1] | uibTypeaheadHighlight:$ctrl.searchText\"></div>\r\n        </div>\r\n        <div class=\"salaxy-highlight\" ng-bind-html=\"item.title | uibTypeaheadHighlight:$ctrl.searchText\"></div>\r\n      </div>\r\n      <div class=\"actions\" style=\"width: 140px;\">\r\n        <div class=\"btn-group\" ng-if=\"item.ui.group == 'builtIn'\">\r\n          <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.showRowTypeDetails(item)\" title=\"{{ 'SALAXY.UI_Terms.show' | sxyTranslate }}\">\r\n            <i class=\"bi bi-info-circle-fill\" aria-hidden=\"true\"></i>\r\n          </button>\r\n          <button type=\"button\" class=\"btn btn-info\" ng-click=\"$ctrl.createCustomRowType(item)\" title=\"Räätälöi\">\r\n            <i class=\"bi bi-plus-square-fill\" aria-hidden=\"true\"></i>\r\n          </button>\r\n          <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.copyToClipboard(item.ui.type)\" title=\"Kopioi ID leikepöydälle\">\r\n            <i class=\"bi bi-clipboard\" aria-hidden=\"true\"></i>\r\n          </button>\r\n        </div>\r\n        <div class=\"btn-group\" ng-if=\"item.ui.group != 'builtIn'\">\r\n          <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.showRowTypeDetails(item)\" title=\"{{ 'SALAXY.UI_Terms.edit' | sxyTranslate }}\">\r\n            <i class=\"bi bi-pencil-fill\" aria-hidden=\"true\"></i>\r\n          </button>\r\n          <button type=\"button\" class=\"btn btn-danger\" ng-click=\"$ctrl.deleteCustomRowType(item)\" title=\"Poista\">\r\n            <i class=\"bi bi-trash-fill\" aria-hidden=\"true\"></i>\r\n          </button>\r\n          <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.copyToClipboard(item.ui.type)\" title=\"Kopioi ID leikepöydälle\">\r\n            <i class=\"bi bi-clipboard\" aria-hidden=\"true\"></i>\r\n          </button>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/settings/ServiceModelDetails.html\",`<style>\r\n  /* TODO: Move to less */\r\n  \r\n  .salaxy-workspace {\r\n    display: flex;\r\n  }\r\n  \r\n  .salaxy-workspace-navi {\r\n    flex: 0 0 200px;\r\n  }\r\n  \r\n  .salaxy-workspace-content {\r\n    flex: 1 1 100%;\r\n    margin-left: -1px;\r\n    height: calc(100vh - 200px);\r\n    overflow-y: auto;\r\n    border: solid 1px #009fd8;\r\n    padding: 10px;\r\n  }\r\n  \r\n  .salaxy-workspace-content .container {\r\n    margin-left: 0px;\r\n  }\r\n</style>\r\n<!--\r\n\r\nTODO-lista:\r\n\r\nTyönkulut:\r\n\r\n- Itsepalvelu (Asiakas yksin)\r\n- Tilitoimisto tekee laskelman => Hyväksyntä => Tilitoimisto maksaa\r\n- Tilitoimisto tekee laskelman => Hyväksyntä => Asiakas maksaa\r\n- Asiakas tekee laskelman => PRO Tarkistaa => Asiakas maksaa\r\n- Asiakas tekee laskelman => PRO Tarkistaa => Tilitoimisto maksaa\r\n\r\nFlagit:\r\n\r\n- Aineiston lähetys: Näkyvissä / ei\r\n- Yritys: Maksaako vai hyväksyykö?\r\n\r\nMietittävä:\r\n\r\n- Entäs useita?\r\n- Saako muokata (osana hyväksyntää)?\r\n- Palkkalaskelman (Salary Slip) lähetys\r\n  - Notifikaatiot\r\n\r\n-->\r\n<div class=\"salaxy-component salaxy-service-model-details\">\r\n\r\n  <div class=\"btn-toolbar\" style=\"margin-left: 195px; margin-bottom: 2px;\">\r\n    <div class=\"btn-group\">\r\n      <button type=\"button\" class=\"btn btn-primary\" ng-disabled=\"!$ctrl.current || $ctrl.current.isReadOnly || $ctrl.isReadOnly\" ng-click=\"$ctrl.saveServiceModel()\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n      </button>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-disabled=\"$ctrl.isReadOnlyForced\" ng-click=\"$ctrl.showCopyAsNew($ctrl.current)\" sxy-text=\"SALAXY.UI_Terms.copyAsNew\"> </button>\r\n      <button class=\"btn btn-default\" ng-click=\"$ctrl.reload()\" title=\"{{ 'SALAXY.UI_Terms.refresh' | sxyTranslate}}\"><i class=\"bi bi-arrow-repeat\" aria-hidden=\"true\"></i></button>\r\n    </div>\r\n    \r\n    <div class=\"btn-group ms-1\">\r\n        <div class=\"d-flex\" style=\"line-height: 34px;\">\r\n          <strong><span sxy-text=\"SALAXY.NG1.ServiceModelDetailsComponent.name\" ps=\":\"></span></strong> {{$ctrl.current.name}}\r\n        </div>\r\n    </div>\r\n    <div class=\"btn-group ms-auto\">\r\n      <button type=\"button\" class=\"btn btn-danger\" ng-disabled=\"!$ctrl.current || $ctrl.current.isReadOnly || $ctrl.isReadOnly\" ng-click=\"$ctrl.delete($ctrl.current)\" sxy-text=\"Poista (test)\" ng-if=\"'test' | sxyIsInRole\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\"></button>\r\n    </div>\r\n  </div>\r\n  <div ng-if=\"$ctrl.current\">\r\n    <sxy-form open-api=\"salaxy-secure/schemas/v02.json\" type=\"ServiceModel\" auto-gen=\"false\" debugger=\"false\" model=\"$ctrl.current\" read-only=\"{{$ctrl.isReadOnly}}\">\r\n      <div ng-init=\"$ctrl.currentSection = 'basicInfo'\" class=\"salaxy-workspace\">\r\n        <div class=\"salaxy-workspace-navi\">\r\n          <salaxy-toggle-buttons ng-model=\"$ctrl.currentSection\" \r\n            options=\"[\r\n              { value: 'basicInfo', label: 'SALAXY.NG1.ServiceModelDetailsComponent.basicInfo' },\r\n              { value: 'exports', label: 'SALAXY.NG1.ServiceModelDetailsComponent.exports' },\r\n              { value: 'branding', label: 'SALAXY.NG1.ServiceModelDetailsComponent.branding' },\r\n              { value: 'sitemap', label: 'SALAXY.NG1.ServiceModelDetailsComponent.sitemap' },\r\n              { value: 'messaging', label: 'SALAXY.NG1.ServiceModelDetailsComponent.messaging' },\r\n              { value: 'i18n', label: 'SALAXY.NG1.ServiceModelDetailsComponent.i18n' },\r\n              { value: 'workflow', label: 'SALAXY.NG1.ServiceModelDetailsComponent.workflow' },\r\n              { value: 'usecases', label: 'SALAXY.NG1.ServiceModelDetailsComponent.usecases' },\r\n              { value: 'irdelivery', label: 'SALAXY.NG1.ServiceModelDetailsComponent.irdelivery' },\r\n              { value: 'advanced', label: 'Tech' }\r\n            ]\"\r\n            type=\"block\">\r\n          </salaxy-toggle-buttons>\r\n        </div>\r\n        <div class=\"salaxy-workspace-content\">\r\n          <div ng-if=\"$ctrl.currentSection == 'basicInfo'\" class=\"form-horizontal container\">\r\n            <div class=\"row\">\r\n              <div class=\"col-sm-8\">\r\n                <fieldset>\r\n                  <legend sxy-text=\"SALAXY.NG1.ServiceModelDetailsComponent.serviceModelTitle\"></legend>\r\n                  <p><strong sxy-text=\"SALAXY.NG1.ServiceModelDetailsComponent.serviceModelId\" ps=\":\"></strong> {{ $ctrl.current.id + \"@\" + $ctrl.current.owner }}</p>\r\n                  <sxy-input model=\"form.name\"></sxy-input>\r\n                  <sxy-input model=\"form.icon\" label=\"SALAXY.NG1.ServiceModelDetailsComponent.serviceModelIcon\"></sxy-input>\r\n                </fieldset>\r\n              </div>\r\n              <div class=\"col-sm-4 text-center\">\r\n                <img ng-if=\"$ctrl.current.icon\" ng-src=\"{{ $ctrl.current.icon }}\" style=\"width: 100px; margin-top: 60px;\" />\r\n              </div>\r\n            </div>\r\n            <div class=\"row\">\r\n              <div class=\"col-sm-8\">\r\n                <fieldset>\r\n                  <legend sxy-text=\"SALAXY.NG1.ServiceModelDetailsComponent.endUserPricing\"></legend>\r\n                  <sxy-input model=\"form.pricing.pricingModel\"></sxy-input>\r\n                  <sxy-input model=\"form.pricing.fixedFee\" ng-if=\"$ctrl.current.pricing.pricingModel == 'fixedFee'\"></sxy-input>\r\n                </fieldset>\r\n              </div>\r\n              <div class=\"col-sm-4\"></div>\r\n            </div>\r\n          </div>\r\n          <div ng-if=\"$ctrl.currentSection == 'exports'\" class=\"form-horizontal container\">\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.NG1.ServiceModelDetailsComponent.paymentChannelsTitle\"></legend>\r\n              <sxy-input model=\"form.features.payments\" format=\"switch\" label=\"SALAXY.NG1.ServiceModelDetailsComponent.customPaymentChannels\"></sxy-input>\r\n              <div ng-if=\"$ctrl.current.features.payments\">\r\n                <sxy-input template-url=\"salaxy-components/sxy-form/custom-templates/array-service-model-payment-channels.html\" model=\"form.payments.channels\">\r\n                  <form>\r\n                    <fieldset>\r\n                      <sxy-input model=\"form.channel\"></sxy-input>\r\n                      <sxy-input model=\"form.isAvailable\"></sxy-input>\r\n                      <sxy-input model=\"form.isEnabled\"></sxy-input>\r\n                    </fieldset>\r\n                  </form>\r\n                </sxy-input>\r\n                <salaxy-input-typeahead read-only=\"$ctrl.isReadOnly\" class=\"default-channel-input-enum\" name=\"options_type\" ng-model=\"$ctrl.current.payments.defaultChannel\" options=\"$ctrl.getSelectablePaymentChannels()\" ng-if=\"$ctrl.getSelectablePaymentChannels().length &gt; 1\"\r\n                  disable-cache=\"true\" label=\"SALAXY.NG1.ServiceModelDetailsComponent.defaultChannel\"></salaxy-input-typeahead>\r\n              </div>\r\n            </fieldset>\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.NG1.ServiceModelDetailsComponent.accountingTitle\"></legend>\r\n              <sxy-input model=\"form.features.accounting\" format=\"switch\" label=\"SALAXY.NG1.ServiceModelDetailsComponent.customAccounting\"></sxy-input>\r\n              <div ng-if=\"$ctrl.current.features.accounting\">\r\n                <sxy-input model=\"form.accounting.defaultPeriodDateKind\"></sxy-input>\r\n                <sxy-input template-url=\"salaxy-components/sxy-form/custom-templates/array-accounting-targets.html\" model=\"form.accounting.targets\">\r\n                  <form>\r\n                    <fieldset ng-show=\"!$ctrl.logic.showDelete\" ng-controller=\"ServiceModelCrudController as $serviceModelController\" ng-init=\"$ctrl.logic.isReadOnly = true\">\r\n                      <salaxy-odata-table crud-controller=\"AccountingTargetCrudController as $crud\" template-url=\"salaxy-components/odata/lists/AccountingTargetSelect.html\" selected-items=\"$ctrl.selectedItems\" on-list-select=\"$serviceModelController.onAccountingTargetSelect($ctrl.current, $ctrl.logic, value, item, allItems)\">\r\n                      </salaxy-odata-table>\r\n                    </fieldset>\r\n                    <fieldset ng-show=\"$ctrl.logic.showDelete\" ng-init=\"$ctrl.logic.isReadOnly = false\">\r\n                      <salaxy-input-enum disabled=\"false\" name=\"format\" label=\"SALAXY.NG1.AccountingTargetDetailsComponent.excelCsvFormat\" ng-model=\"$ctrl.current.format\"\r\n                        options=\"{\r\n                          '36dff2e2-e181-4f0d-9004-0e4aa92f5e17': 'Palkkaus.fi',\r\n                          '0db4e85f-93a8-46f1-b6d2-f7523d289d88': 'Fennoa',\r\n                          '8613f133-3fce-4611-b372-51f6a2e007dd': 'Procountor',\r\n                          'e62c10b0-222a-4170-b8b4-b1e02d9a7644': 'Passeli Merit',\r\n                          '53fd3863-b8f9-4909-86c9-cb4597595181': 'Heeros',\r\n                          '2fc7899c-7a3d-4d56-ad2f-05d52782bbbc': 'Asteri',\r\n                          '0a2bd312-06da-4862-aef5-75166e0bf461': 'Maestro',\r\n                          'c04e0757-63f3-420d-a183-3427710fc954': 'Visma Fivaldi',\r\n                          'ba271dac-dd63-4036-9d70-053a09ca4d9e' :'Visma Netvisor',\r\n                          '27e271d5-41f5-4319-ab29-4d5d9eb945c6': 'Lemonsoft',\r\n                          'd311f9d3-8c3a-4fd8-a665-8e3698e41e87': 'Tampuuri',\r\n                          'd58e95b7-d0b5-40ac-992b-6d3b29efc45e': 'Domus',\r\n                          '54e93c5f-bd74-4157-8a74-3515be7f585d': 'Oscar Software',\r\n                          '0e4f0a71-dcb9-43ba-9028-0239e674711f': 'Digia Enterprise',\r\n                          '2ccefa46-7992-46c5-9d87-b88336935916': 'Digia Enterprise - VILPE',\r\n                          'c36c24b9-5e2c-4f44-b67a-90d81aeea257': 'iScala'\r\n                        }\">\r\n                      </salaxy-input-enum>\r\n                      <sxy-input model=\"form.method\" read-only=\"false\"></sxy-input>\r\n                      <salaxy-input-enum disabled=\"false\" enum=\"ExportMethod\" label=\"SALAXY.MODEL.AccountingTargetSettings.availableMethods.title\" name=\"availableMethods\" type=\"multi-select\" ng-model=\"$ctrl.current.availableMethods\"></salaxy-input-enum>\r\n                    </fieldset>\r\n                  </form>\r\n                </sxy-input>\r\n                <salaxy-input-typeahead name=\"options_type\" ng-model=\"$ctrl.current.accounting.defaultTargetId\" options=\"$ctrl.getSelectableAccountingTargets()\" disable-cache=\"true\" ng-if=\"$ctrl.getSelectableAccountingTargets().length &gt; 1\" label=\"SALAXY.NG1.ServiceModelDetailsComponent.defaultTarget\"></salaxy-input-typeahead>\r\n              </div>\r\n            </fieldset>\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.MODEL.ServiceModelCostAccounting.title\"></legend>\r\n              <sxy-input model=\"form.features.costAccounting\" format=\"switch\" label=\"SALAXY.NG1.ServiceModelDetailsComponent.customCostAccounting\"></sxy-input>\r\n              <div ng-if=\"$ctrl.current.features.costAccounting\">\r\n                <sxy-input model=\"form.costAccounting.dimensions\" include=\"id,label,scope\">\r\n                  <form>\r\n                    <fieldset>\r\n                      <legend sxy-text=\"SALAXY.MODEL.CostAccountingDimensionDefinition.title\"></legend>\r\n                      <sxy-input model=\"form.id\" read-only=\"{{$ctrl.logic.showDelete}}\"></sxy-input>\r\n                      <sxy-input model=\"form.label\"></sxy-input>\r\n                      <sxy-input model=\"form.allowCostSharing\"></sxy-input>\r\n                      <sxy-input model=\"form.scope\"></sxy-input>\r\n                      <sxy-input model=\"form.options\" template-url=\"salaxy-components/sxy-form/custom-templates/cost-accounting-options.html\"></sxy-input>\r\n                    </fieldset>\r\n                  </form>\r\n                </sxy-input>\r\n              </div>\r\n            </fieldset>\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.MODEL.ServiceModelHoliday.title\"></legend>\r\n              <sxy-input model=\"form.features.holiday\" format=\"switch\" label=\"SALAXY.NG1.ServiceModelDetailsComponent.customHoliday\"></sxy-input>\r\n              <div ng-if=\"$ctrl.current.features.holiday\">\r\n                <sxy-input model=\"form.holiday.holidayPaySettings\" include=\"holidayPayCalculation\">\r\n                  <form>\r\n                    <fieldset>\r\n                      <legend sxy-text=\"SALAXY.MODEL.HolidayPaySettings.title\"></legend>\r\n                      <salaxy-input-enum ng-show=\"!('bizConfigs' | sxyIsInRole)\" enum=\"HolidayPayCalculation\" label=\"SALAXY.MODEL.HolidayPaySettings.holidayPayCalculation.title\" name=\"holidayPayCalculation\" filter=\"averageDailyPay,averageHourlyPay,percentageBasedPay,holidayCompensation\" require=\"true\" ng-model=\"$ctrl.current.holidayPayCalculation\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-enum>\r\n                      <salaxy-input-enum ng-show=\"'bizConfigs' | sxyIsInRole\" enum=\"HolidayPayCalculation\" label=\"SALAXY.MODEL.HolidayPaySettings.holidayPayCalculation.title\" name=\"holidayPayCalculation\" filter=\"averageDailyPay,averageHourlyPay,percentageBasedPay,holidayCompensation,scriptPay\" require=\"true\" ng-model=\"$ctrl.current.holidayPayCalculation\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-enum>                     \r\n                      <salaxy-input-collective-bargain-agreement ng-show=\"'bizConfigs' | sxyIsInRole\" name=\"cbaCode\" ng-model=\"$ctrl.current.cbaCode\" label=\"SALAXY.MODEL.HolidayPaySettings.cbaCode.title\"></salaxy-input-collective-bargain-agreement>\r\n                      <salaxy-input-employee-group ng-show=\"'bizConfigs' | sxyIsInRole\" name=\"employeeGroup\" ng-model=\"$ctrl.current.employeeGroup\" label=\"SALAXY.MODEL.HolidayPaySettings.employeeGroup.title\"></salaxy-input-employee-group>\r\n                      <sxy-input model=\"form.disabled\"></sxy-input>\r\n                      <sxy-input model=\"form.startYear\" label=\"SALAXY.MODEL.HolidayPaySettings.startYear.title\"></sxy-input>  \r\n                      <sxy-input model=\"form.endYear\" label=\"SALAXY.MODEL.HolidayPaySettings.endYear.title\"></sxy-input> \r\n                      <legend  ng-show=\"$ctrl.current.holidayPayCalculation && $ctrl.current.holidayPayCalculation != 'scriptPay'\" sxy-text=\"SALAXY.MODEL.HolidayPaySettings.salaryTypes.title\"></legend>\r\n                      <sxy-input  ng-show=\"$ctrl.current.holidayPayCalculation && $ctrl.current.holidayPayCalculation != 'scriptPay'\" model=\"form.salaryTypes\" template-url=\"salaxy-components/sxy-form/custom-templates/pay-stats-row-types.html\"></sxy-input>\r\n                      <legend ng-show=\"$ctrl.current.holidayPayCalculation == 'averageHourlyPay'\" sxy-text=\"SALAXY.MODEL.HolidayPaySettings.workingTimeTypes.title\"></legend>\r\n                      <sxy-input ng-show=\"$ctrl.current.holidayPayCalculation == 'averageHourlyPay'\" model=\"form.workingTimeTypes\" template-url=\"salaxy-components/sxy-form/custom-templates/pay-stats-row-types.html\"></sxy-input>\r\n                      <legend ng-show=\"$ctrl.current.holidayPayCalculation == 'averageDailyPay'\" sxy-text=\"SALAXY.MODEL.HolidayPaySettings.overtimeTypes.title\"></legend>\r\n                      <sxy-input  ng-show=\"$ctrl.current.holidayPayCalculation == 'averageDailyPay'\" model=\"form.overtimeTypes\" template-url=\"salaxy-components/sxy-form/custom-templates/pay-stats-row-types.html\"></sxy-input>\r\n                      <legend ng-show=\"$ctrl.current.holidayPayCalculation == 'averageHourlyPay' || $ctrl.current.holidayPayCalculation == 'averageDailyPay'\" sxy-text=\"SALAXY.MODEL.HolidayPaySettings.multipliers.title\"></legend>\r\n                      <salaxy-input-holiday-multipliers ng-show=\"$ctrl.current.holidayPayCalculation == 'averageHourlyPay' || $ctrl.current.holidayPayCalculation == 'averageDailyPay'\" name=\"multipliers\" label=\"SALAXY.MODEL.HolidayPaySettings.multipliers.title\" ng-model=\"$ctrl.current.multipliers\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-holiday-multipliers>\r\n                      <sxy-code-editor ng-show=\"$ctrl.current.holidayPayCalculation == 'scriptPay'\" ng-model=\"$ctrl.current.script\"></sxy-code-editor>\r\n                    </fieldset>\r\n                  </form>\r\n                </sxy-input>\r\n               <sxy-input model=\"form.holiday.holidayAccrualSettings\" include=\"code\">\r\n                  <form>\r\n                    <fieldset>\r\n                      <legend sxy-text=\"SALAXY.MODEL.HolidayAccrualSettings.title\"></legend>\r\n                      <salaxy-input-enum  ng-show=\"!('bizConfigs' | sxyIsInRole)\" enum=\"HolidayCode\" label=\"SALAXY.MODEL.HolidayAccrualSettings.code.title\" name=\"code\" filter=\"permanent35Hours\" require=\"true\" ng-model=\"$ctrl.current.code\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-enum>\r\n                      <salaxy-input-enum  ng-show=\"'bizConfigs' | sxyIsInRole\" enum=\"HolidayCode\" label=\"SALAXY.MODEL.HolidayAccrualSettings.code.title\" name=\"code\" filter=\"permanent35Hours,script\" require=\"true\" ng-model=\"$ctrl.current.code\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-enum>\r\n                      <salaxy-input-collective-bargain-agreement  ng-show=\"'bizConfigs' | sxyIsInRole\" name=\"cbaCode\" ng-model=\"$ctrl.current.cbaCode\" label=\"SALAXY.MODEL.HolidayAccrualSettings.cbaCode.title\"></salaxy-input-collective-bargain-agreement>\r\n                      <salaxy-input-employee-group  ng-show=\"'bizConfigs' | sxyIsInRole\" name=\"employeeGroup\" ng-model=\"$ctrl.current.employeeGroup\" label=\"SALAXY.MODEL.HolidayAccrualSettings.employeeGroup.title\"></salaxy-input-employee-group>\r\n                      <sxy-input model=\"form.disabled\"></sxy-input>\r\n                      <sxy-input model=\"form.startYear\" label=\"SALAXY.MODEL.HolidayAccrualSettings.startYear.title\"></sxy-input>  \r\n                      <sxy-input model=\"form.endYear\" label=\"SALAXY.MODEL.HolidayAccrualSettings.endYear.title\"></sxy-input> \r\n                      <legend ng-show=\"$ctrl.current.code == 'permanent35Hours'\" sxy-text=\"SALAXY.MODEL.HolidayAccrualSettings.workingTimeTypes.title\"></legend>\r\n                      <sxy-input  ng-show=\"$ctrl.current.code == 'permanent35Hours'\" model=\"form.workingTimeTypes\" template-url=\"salaxy-components/sxy-form/custom-templates/pay-stats-row-types.html\"></sxy-input>\r\n                      <sxy-code-editor ng-show=\"$ctrl.current.code == 'script'\" ng-model=\"$ctrl.current.script\"></sxy-code-editor>\r\n                    </fieldset>\r\n                  </form>\r\n                </sxy-input>\r\n              </div>\r\n            </fieldset>\r\n            <fieldset  ng-if=\"'bizConfigs' | sxyIsInRole\">\r\n              <legend sxy-text=\"SALAXY.MODEL.ServiceModelPayStats.title\"></legend>\r\n              <sxy-input model=\"form.features.payStats\" format=\"switch\" label=\"SALAXY.NG1.ServiceModelDetailsComponent.customPayStats\"></sxy-input>\r\n              <div ng-if=\"$ctrl.current.features.payStats\">\r\n                <sxy-input model=\"form.payStats.types\" include=\"id,kind,periodLength,cbaCode,employeeGroup\">\r\n                  <form>\r\n                    <fieldset>\r\n                      <legend sxy-text=\"SALAXY.MODEL.PayStatsTypeDefinition.title\"></legend>\r\n                      <sxy-input model=\"form.id\" require=\"true\" read-only=\"{{$ctrl.logic.isReadOnly}}\"></sxy-input>\r\n                      <sxy-input model=\"form.description\"></sxy-input>\r\n                      <salaxy-input-enum enum=\"PayStatsKind\" label=\"SALAXY.MODEL.PayStatsTypeDefinition.kind.title\" name=\"kind\" require=\"true\" ng-model=\"$ctrl.current.kind\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-enum>\r\n                      <salaxy-input-enum enum=\"PayStatsPeriodLength\" label=\"SALAXY.MODEL.PayStatsTypeDefinition.periodLength.title\" name=\"periodLength\" require=\"true\" ng-model=\"$ctrl.current.periodLength\" filter=\"quarter,month,year\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-enum>\r\n                      <salaxy-input-enum enum=\"PeriodDateKind\" label=\"SALAXY.MODEL.PayStatsTypeDefinition.periodDateKind.title\" name=\"periodDateKind\" require=\"true\" ng-model=\"$ctrl.current.periodDateKind\" read-only=\"$ctrl.logic.isReadOnly\"></salaxy-input-enum>                   \r\n                      <salaxy-input-collective-bargain-agreement name=\"cbaCode\" ng-model=\"$ctrl.current.cbaCode\" label=\"SALAXY.MODEL.PayStatsTypeDefinition.cbaCode.title\"></salaxy-input-collective-bargain-agreement>\r\n                      <salaxy-input-employee-group name=\"employeeGroup\" ng-model=\"$ctrl.current.employeeGroup\" label=\"SALAXY.MODEL.PayStatsTypeDefinition.employeeGroup.title\"></salaxy-input-employee-group>\r\n                      <sxy-input model=\"form.disabled\"></sxy-input>\r\n                      <sxy-input model=\"form.startDate\"></sxy-input>\r\n                      <sxy-input model=\"form.endDate\"></sxy-input>\r\n                      <legend ng-show=\"$ctrl.current.kind == 'averageHourlyPay'\" label=\"SALAXY.MODEL.PayStatsTypeDefinition.salaryTypes.title\"></legend>\r\n                      <sxy-input ng-show=\"$ctrl.current.kind == 'averageHourlyPay'\" model=\"form.salaryTypes\" template-url=\"salaxy-components/sxy-form/custom-templates/pay-stats-row-types.html\"></sxy-input>\r\n                      <legend ng-show=\"$ctrl.current.kind == 'averageHourlyPay'\" sxy-text=\"SALAXY.MODEL.PayStatsTypeDefinition.workingTimeTypes.title\"></legend>\r\n                      <sxy-input ng-show=\"$ctrl.current.kind == 'averageHourlyPay'\" format=\"undefined\" model=\"form.minWorkingTime\"></sxy-input>\r\n                      <sxy-input ng-show=\"$ctrl.current.kind == 'averageHourlyPay'\" model=\"form.workingTimeTypes\" template-url=\"salaxy-components/sxy-form/custom-templates/pay-stats-row-types.html\"></sxy-input>\r\n                      <sxy-code-editor ng-show=\"$ctrl.current.kind == 'script'\" ng-model=\"$ctrl.current.script\"></sxy-code-editor>\r\n                    </fieldset>\r\n                  </form>\r\n                </sxy-input>\r\n              </div>\r\n            </fieldset>\r\n          </div>\r\n          <div ng-if=\"$ctrl.currentSection == 'branding'\" class=\"form-horizontal container\">\r\n            <div class=\"row\">\r\n              <div class=\"col-sm-6\">\r\n                <fieldset>\r\n                  <legend sxy-text=\"SALAXY.NG1.ServiceModelDetailsComponent.webAppTitle\"></legend>\r\n                  <sxy-input model=\"form.site.webApp\"></sxy-input>\r\n                  <sxy-input model=\"form.site.webAppUrl\"></sxy-input>\r\n                  <sxy-input model=\"form.site.webAppName\"></sxy-input>\r\n                </fieldset>\r\n              </div>\r\n              <div class=\"col-sm-6\">\r\n                <fieldset>\r\n                  <legend sxy-text=\"SALAXY.NG1.ServiceModelDetailsComponent.reportingTitle\"></legend>\r\n                  <sxy-input model=\"form.features.reporting\" label=\"SALAXY.NG1.ServiceModelDetailsComponent.customReporting\"></sxy-input>\r\n                  <salaxy-input-enum ng-model=\"$ctrl.current.reporting.layoutTemplateId\" name=\"layputTemplateId\" label=\"SALAXY.NG1.ServiceModelDetailsComponent.layoutTemplateId\" options=\"{'palkkaus-report-options@FI53POYS0025543933': ('SALAXY.NG1.ServiceModelDetailsComponent.templateIdPalkkaus' | sxyTranslate),\r\n                      'no-logo-report-options@FI53POYS0025543933': ('SALAXY.NG1.ServiceModelDetailsComponent.templateIdNoLogo' | sxyTranslate),\r\n                      'logo-report-options@FI53POYS0025543933': ('SALAXY.NG1.ServiceModelDetailsComponent.templateIdLogo' | sxyTranslate),\r\n                      'kevytyrittaja-report-options@FI06POYT0009439335': ('SALAXY.NG1.ServiceModelDetailsComponent.templateIdTalenom' | sxyTranslate),\r\n                      'tilijaska-report-options@FI39POYT0025590211': ('SALAXY.NG1.ServiceModelDetailsComponent.templateIdTilijaska' | sxyTranslate),\r\n                      'treamer-report-options@FI86POYI0028244891': ('SALAXY.NG1.ServiceModelDetailsComponent.templateIdTreamer' | sxyTranslate)}\" read-only=\"$ctrl.isReadOnly\"></salaxy-input-enum>\r\n                  <salaxy-textarea maxlength=\"\" label=\"SALAXY.NG1.ServiceModelDetailsComponent.customReportLogo\" name=\"logo\" ng-model=\"$ctrl.current.reporting.logo\" rows=\"3\" ng-if=\"$ctrl.current.reporting.layoutTemplateId == 'logo-report-options@FI53POYS0025543933'\">\r\n                  </salaxy-textarea>\r\n                </fieldset>\r\n              </div>\r\n            </div>\r\n            <div class=\"row\">\r\n              <div class=\"col-sm-8\">\r\n                <fieldset>\r\n                  <legend sxy-text=\"SALAXY.NG1.ServiceModelDetailsComponent.brandingTitle\"></legend>\r\n                  <sxy-input model=\"form.branding.logo\"></sxy-input>\r\n                  <sxy-input model=\"form.branding.skin\"></sxy-input>\r\n                </fieldset>\r\n              </div>\r\n              <div class=\"col-sm-4 text-center\">\r\n                <img ng-if=\"$ctrl.current.branding.logo\" ng-src=\"{{ $ctrl.current.branding.logo }}\" style=\"width: 100px; margin-top: 35px;\" />\r\n              </div>\r\n            </div>\r\n          </div>\r\n          <div ng-if=\"$ctrl.currentSection == 'sitemap'\" class=\"form-horizontal height100\">\r\n            <div class=\"row height100\" style=\"width: 95%;\">\r\n              <div class=\"col-6 height100\" style=\"width: 45%; overflow-y: auto\">\r\n                <div class=\"btn-toolbar\">\r\n                  <div class=\"btn-group\">\r\n                    <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showHideAll(true)\">Avaa kaikki</button>\r\n                    <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showHideAll(false)\">Sulje kaikki</button>\r\n                  </div>\r\n                  <button type=\"button\" ng-disabled=\"$ctrl.isReadOnly\" class=\"btn btn-danger\" ng-click=\"$ctrl.resetSitemapChanges()\">Palauta kaikki</button>\r\n                </div>\r\n                <table class=\"table table-sm\">\r\n                  <thead>\r\n                    <tr>\r\n                      <th colspan=\"3\">Title</th>\r\n                      <th class=\"right\">Flags</th>\r\n                      <th class=\"right\">Roles</th>\r\n                      <th class=\"right\">Changes</th>\r\n                      <th colspan=\"2\"></th>\r\n                    </tr>\r\n                  </thead>\r\n                  <tbody>\r\n                    <tr ng-repeat-start=\"level1 in $ctrl.sitemap\" class=\"clickable\" ng-class=\"{ 'active': $ctrl.currentSitemapNode == level1 }\">\r\n                      <td colspan=\"3\" ng-click=\"$ctrl.currentSitemapNode = level1\">{{ $ctrl.translate(level1.title) }}</td>\r\n                      <td class=\"right\" ng-click=\"$ctrl.currentSitemapNode = level1\">\r\n                        <i ng-class=\"'bi ' + icon\" ng-repeat=\"icon in level1.$edit.$faIcons\" aria-hidden=\"true\"></i>\r\n                      </td>\r\n                      <td class=\"right\" ng-click=\"$ctrl.currentSitemapNode = level1\">\r\n                        <span ng-if=\"$ctrl.getIsTest(level1)\" class=\"badge bg-primary\"><span class=\"small\">test</span></span>\r\n                        <span>{{ $ctrl.getRoles(level1) }}</span>\r\n                      </td>\r\n                      <td class=\"right\" ng-click=\"$ctrl.currentSitemapNode = level1\">\r\n                        <i class=\"bi bi-translate text-primary\" ng-if=\"level1.$edit.$hasTextChanges\" aria-hidden=\"true\"></i>\r\n                        <i class=\"bi bi-pencil-square text-primary\" ng-if=\"level1.$edit.$hasChanges\" aria-hidden=\"true\"></i>\r\n                        <i class=\"bi bi-pencil-square\" ng-if=\"level1.$edit.$hasChildrenChanges\" aria-hidden=\"true\"></i>\r\n                      </td>\r\n                      <td colspan=\"2\" class=\"right\" ng-if=\"level1.children.length\" ng-click=\"level1.$edit.$isOpen = !level1.$edit.$isOpen\">\r\n                        <i class=\"bi\" ng-class=\"level1.$edit.$isOpen ? 'bi-chevron-up' : 'bi-chevron-down'\" aria-hidden=\"true\"></i>\r\n                      </td>\r\n                      <td colspan=\"2\" ng-if=\"!level1.children.length\"></td>\r\n                    </tr>\r\n                    <tr ng-if=\"level1.$edit.$isOpen\" ng-repeat-start=\"level2 in level1.children\" class=\"clickable\" ng-class=\"{ 'active': $ctrl.currentSitemapNode == level2 }\">\r\n                      <td style=\"width: 10px;\">-</td>\r\n                      <td colspan=\"2\" ng-click=\"$ctrl.currentSitemapNode = level2\">{{ $ctrl.translate(level2.title) }}</td>\r\n                      <td class=\"right\" ng-click=\"$ctrl.currentSitemapNode = level2\">\r\n                        <i ng-class=\"'bi ' + icon\" ng-repeat=\"icon in level2.$edit.$faIcons\" aria-hidden=\"true\"></i>\r\n                      </td>\r\n                      <td class=\"right\" ng-click=\"$ctrl.currentSitemapNode = level2\">\r\n                        <span ng-if=\"$ctrl.getIsTest(level2)\" class=\"badge bg-primary\"><span class=\"small\">test</span></span>\r\n                        <span>{{ $ctrl.getRoles(level2) }}</span>\r\n                      </td>\r\n                      <td class=\"right\" ng-click=\"$ctrl.currentSitemapNode = level2\">\r\n                        <i class=\"bi bi-translate text-primary\" ng-if=\"level2.$edit.$hasTextChanges\" aria-hidden=\"true\"></i>\r\n                        <i class=\"bi bi-pencil-square text-primary\" ng-if=\"level2.$edit.$hasChanges\" aria-hidden=\"true\"></i>\r\n                        <i class=\"bi bi-pencil-square\" ng-if=\"level2.$edit.$hasChildrenChanges\" aria-hidden=\"true\"></i>\r\n                      </td>\r\n                      <td ng-if=\"level2.children.length\" ng-click=\"level2.$edit.$isOpen = !level2.$edit.$isOpen\">\r\n                        <i class=\"bi\" ng-class=\"level2.$edit.$isOpen ? 'bi-chevron-up' : 'bi-chevron-down'\" aria-hidden=\"true\"></i>\r\n                      </td>\r\n                      <td ng-if=\"!level2.children.length\"></td>\r\n                      <td></td>\r\n                    </tr>\r\n                    <tr ng-if=\"level1.$edit.$isOpen && level2.$edit.$isOpen\" ng-repeat-end ng-repeat=\"level3 in level2.children\" class=\"clickable\" ng-click=\"$ctrl.currentSitemapNode = level3\" ng-class=\"{ 'active': $ctrl.currentSitemapNode == level3 }\">\r\n                      <td style=\"width: 10px;\">&nbsp;</td>\r\n                      <td style=\"width: 10px;\">-</td>\r\n                      <td>{{ $ctrl.translate(level3.title) }}</td>\r\n                      <td class=\"right\">\r\n                        <i ng-class=\"'bi ' + icon\" ng-repeat=\"icon in level3.$edit.$faIcons\" aria-hidden=\"true\"></i>\r\n                      </td>\r\n                      <td class=\"right\">\r\n                        <span ng-if=\"$ctrl.getIsTest(level3)\" class=\"badge bg-primary\"><span class=\"small\">test</span></span>\r\n                        <span>{{ $ctrl.getRoles(level3) }}</span>\r\n                      </td>\r\n                      <td class=\"right\">\r\n                        <i class=\"bi bi-translate text-primary\" ng-if=\"level3.$edit.$hasTextChanges\" aria-hidden=\"true\"></i>\r\n                        <i class=\"bi bi-pencil-square text-primary\" ng-if=\"level3.$edit.$hasChanges\" aria-hidden=\"true\"></i>\r\n                        <i class=\"bi bi-pencil-square\" ng-if=\"level3.$edit.$hasChildrenChanges\" aria-hidden=\"true\"></i>\r\n                      </td>\r\n                      <td colspan=\"2\"></td>\r\n                    </tr>\r\n                    <tr ng-repeat-end ng-if=0></tr>\r\n                  </tbody>\r\n                </table>\r\n              </div>\r\n              <div class=\"col-6\">\r\n                <div class=\"btn-toolbar\">\r\n                  <button type=\"button\" ng-disabled=\"$ctrl.isReadOnly\" class=\"btn btn-danger\" ng-click=\"$ctrl.resetSitemapNode(true)\">Palauta muutokset</button>\r\n                  <div class=\"btn-group ms-auto\">\r\n                    <button type=\"button\" ng-disabled=\"$ctrl.isReadOnly\" class=\"btn btn-default\" ng-click=\"$ctrl.resetSitemapNode()\">Peruuta</button>\r\n                    <button type=\"button\" ng-disabled=\"$ctrl.isReadOnly\" class=\"btn btn-primary\" ng-click=\"$ctrl.commitSitemapNode()\">OK</button>\r\n                  </div>\r\n                </div>\r\n\r\n                <h3>{{ $ctrl.translate($ctrl.currentSitemapNode.title) }} <small>({{ $ctrl.currentSitemapNode.$edit.$id }})</small></h3>\r\n                <salaxy-tab-buttons\r\n                  current-tab=\"$ctrl.SitemapActive\"\r\n                  options=\"[\r\n                    { value: 'general', text: 'Perustiedot' },\r\n                    { value: 'params', text: 'Parametrit' },\r\n                    { value: 'i18n', text: 'Tekstit' },\r\n                    { value: 'debug', text: 'Debug' }\r\n                  ]\"\r\n                  tabs-id=\"serviceModelDetails\">\r\n                </salaxy-tab-buttons>\r\n                <div class=\"tab-content\" id=\"tab-content-serviceModelDetails\">\r\n                  <div class=\"tab-pane\" id=\"general-tab\">\r\n                    <div class=\"form-horizontal\">\r\n                      <salaxy-input name=\"id\" read-only=\"true\" ng-model=\"$ctrl.currentSitemapNode.$edit.$id\" label=\"Id\"></salaxy-input>\r\n                      <salaxy-input name=\"url\" read-only=\"true\" ng-model=\"$ctrl.currentSitemapNode.url\" label=\"SALAXY.NG1.ServiceModelDetailsComponent.url\"></salaxy-input>\r\n                      <salaxy-input-enum name=\"visibility\" enum=\"SitemapVisibility\" label=\"Näkyvyys ({{ 'SitemapVisibility.' + ($ctrl.currentSitemapNode.visibility || 'visible') | sxyEnum }})\" ng-model=\"$ctrl.currentSitemapNode.$edit.visibility\" read-only=\"$ctrl.isReadOnly\"></salaxy-input-enum>\r\n                      <salaxy-input name=\"roles\" ng-model=\"$ctrl.currentSitemapNode.$edit.roles\" label=\"Roolit ({{ $ctrl.currentSitemapNode.roles || '-' }})\" read-only=\"$ctrl.isReadOnly\"></salaxy-input>\r\n                      <salaxy-input-boolean name=\"isFullWidth\" type=\"select\" label=\"Leveä näyttö ({{ $ctrl.currentSitemapNode.isFullWidth ? 'Kyllä' : 'Ei' }})\" ng-model=\"$ctrl.currentSitemapNode.$edit.isFullWidth\" read-only=\"$ctrl.isReadOnly\"></salaxy-input-boolean>\r\n                      <div class=\"row\">\r\n                        <div ng-if=\"$ctrl.currentSitemapNode.$edit.isFullWidth != null\" class=\"col-sm-6 offset-sm-4\">\r\n                          <button type=\"button\" class=\"btn btn-default btn-xs\" ng-click=\"$ctrl.currentSitemapNode.$edit.isFullWidth = null\">Palauta oletus</button>\r\n                        </div>\r\n                      </div>\r\n                      <fieldset>\r\n                        <legend>Sivun otsikko</legend>\r\n                        <small><p>Klikkaa muokataksesi kieliversioita. HUOM: Muutokset menevät suoraan kieliversiointiin, \"Peruuta\"/\"OK\"-nappuloila yllä ei ole vaikutusta. Käytä delete-nappia alla erikseen poistaaksesi muutokset.</p></small>\r\n                        <div style=\"padding-left: 10px;\">\r\n                          <salaxy-ui-translator mode=\"fieldset\" texts=\"$ctrl.current.site.texts\" filter=\"$ctrl.currentSitemapNode.$edit.$i18nKey\"></salaxy-ui-translator>\r\n                        </div>\r\n                      </fieldset>\r\n                    </div>\r\n                  </div>\r\n                  <div class=\"tab-pane\" id=\"params-tab\">\r\n                    <sxy-form open-api=\"SitemapParams\" open-api-doc=\"$ctrl.getSitemapParamsSchema()\" type=\"{{$ctrl.currentSitemapNode.$edit.$id}}\" auto-gen=\"true\" model=\"$ctrl.currentSitemapNode.$edit\" read-only=\"{{$ctrl.isReadOnly}}\"></sxy-form>\r\n                  </div>\r\n                  <div class=\"tab-pane\" id=\"i18n-tab\">\r\n                    <div class=\"alert alert-info\"><strong>HUOM!</strong> Suurin osa teksteistä on komponenttien tekstejä. Niiden muokkaaminen vaikuttaa kaikkiin sivuihin, joissa komponentti on käytössä: Ei pelkästään tähän sivuun.</div>\r\n                      <div ng-if=\"!$ctrl.currentSitemapNode.i18n.length\">Käännöstekstejä ei ole määritetty tälle sivulle.</div>\r\n                      <salaxy-ui-translator ng-if=\"$ctrl.currentSitemapNode.i18n.length\" texts=\"$ctrl.current.site.texts\" filter=\"$ctrl.currentSitemapNode.i18n\"></salaxy-ui-translator>\r\n                  </div>\r\n                  <div class=\"tab-pane\" id=\"debug-tab\">\r\n                    <salaxy-json-formatter json=\"$ctrl.currentSitemapNode\" key=\"'Node'\"></salaxy-json-formatter>\r\n                    <salaxy-json-formatter json=\"$ctrl.currentSitemapNode.$edit\" key=\"'$edit'\"></salaxy-json-formatter>\r\n                  </div>\r\n                </div>\r\n              </div>\r\n            </div>\r\n          </div>\r\n          <div ng-if=\"$ctrl.currentSection == 'messaging'\" class=\"form-horizontal container\">\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.NG1.ServiceModelDetailsComponent.messagingTitle\"></legend>\r\n              <sxy-input model=\"form.features.messaging\" label=\"SALAXY.NG1.ServiceModelDetailsComponent.messagingActive\"></sxy-input>\r\n              <sxy-input model=\"form.messaging.partnerMessages\"></sxy-input>\r\n              <sxy-input model=\"form.messaging.workerSalaryNotifications\"></sxy-input>\r\n              <sxy-input model=\"form.messaging.workerSalarySlipDeliveryMethods\"></sxy-input>\r\n            </fieldset>\r\n          </div>\r\n          <div ng-if=\"$ctrl.currentSection == 'i18n'\" class=\"form-horizontal\" ng-init=\"$ctrl.current.site.texts = $ctrl.current.site.texts ? $ctrl.current.site.texts : {}\">\r\n            <salaxy-ui-translator texts=\"$ctrl.current.site.texts\"></salaxy-ui-translator>\r\n          </div>\r\n          <div ng-if=\"$ctrl.currentSection == 'workflow'\" class=\"form-horizontal\">\r\n            <div class=\"container\">\r\n              <sxy-input model=\"form.features.forms\" legend=\"Aineiston lähetys käytössä\"></sxy-input>\r\n            </div>\r\n          </div>\r\n          <div ng-if=\"$ctrl.currentSection == 'usecases'\" class=\"form-horizontal container\">\r\n            <fieldset>\r\n              <sxy-input model=\"form.features.usecase\" label=\"SALAXY.NG1.ServiceModelDetailsComponent.customUsecases\"></sxy-input>\r\n              <sxy-input template-url=\"salaxy-components/sxy-form/custom-templates/array-usecase.html\" model=\"form.usecase.usecases\">\r\n                <form>\r\n                  <fieldset ng-show=\"!$ctrl.logic.showDelete\" ng-controller=\"ServiceModelCrudController as $serviceModelController\">\r\n                    <salaxy-odata-table url=\"/v03/api/usecases\" template-url=\"salaxy-components/odata/lists/UsecaseSelect.html\" selected-items=\"$ctrl.selectedItems\" on-list-select=\"$serviceModelController.onUsecaseSelect($ctrl.current, $ctrl.logic, value, item, allItems)\">\r\n                    </salaxy-odata-table>\r\n                  </fieldset>\r\n                  <fieldset ng-show=\"$ctrl.logic.showDelete\">\r\n                    <sxy-input model=\"form.uri\" read-only=\"true\"></sxy-input>\r\n                    <sxy-input model=\"form.label\"></sxy-input>\r\n                    <sxy-input model=\"form.itemType\"></sxy-input>\r\n                    <sxy-input model=\"form.status\"></sxy-input>\r\n                    <sxy-input model=\"form.order\"></sxy-input>\r\n                  </fieldset>\r\n                </form>\r\n              </sxy-input>\r\n            </fieldset>\r\n          </div>\r\n          <div ng-if=\"$ctrl.currentSection == 'irdelivery'\" class=\"form-horizontal container\">\r\n            <fieldset>\r\n              <legend>Tulorekisterin varmenne</legend>\r\n              <salaxy-input-boolean type=\"select\" name=\"irDelivery\" ng-model=\"$ctrl.current.features.irDelivery\" label=\"Käytä tätä varmennetta asiakkaille\"></salaxy-input-boolean>\r\n              \r\n              <salaxy-input label=\"Tulorekisterivarmenteen omistajan Y-tunnus\" name=\"senderOfficialId\"\r\n                        ng-model=\"$ctrl.current.calc.irDelivery.senderOfficialId\"></salaxy-input>\r\n              <legend>Tulorekisteriraportin yhteyshenkilöt</legend>\r\n              <table class=\"table\">\r\n                <thead>\r\n                  <tr>\r\n                    <th>{{('Nimi') | sxyTranslate}}</th>\r\n                    <th>{{('Puhelin') | sxyTranslate}}</th>\r\n                    <th>{{('Sähköposti') | sxyTranslate}}</th>\r\n                    <th>{{('Vastuualue') | sxyTranslate}}</th>\r\n                    <th class=\"right\">\r\n                      <button type=\"button\" class=\"btn btn-primary btn-xs\"\r\n                        ng-click=\"$ctrl.current.calc.irDelivery.contactPersons.push({})\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n                    </th>\r\n                  </tr>\r\n                </thead>\r\n                <tbody>\r\n                  <tr ng-repeat=\"item in $ctrl.current.calc.irDelivery.contactPersons\">\r\n                    <td>\r\n                      <salaxy-input require=\"true\" ng-model=\"item.name\" name=\"{{ 'name' + $index }}\" label-type=\"plain\"></salaxy-input>\r\n                    </td>\r\n                    <td>\r\n                      <salaxy-input require=\"true\" ng-model=\"item.telephone\" name=\"{{ 'telephone' + $index }}\" label-type=\"plain\" sxy-mobile-phone></salaxy-input>\r\n                    </td>\r\n                    <td>\r\n                      <salaxy-input require=\"true\" ng-model=\"item.email\" name=\"{{ 'email' + $index }}\" label-type=\"plain\" sxy-email></salaxy-input>\r\n                    </td>\r\n                    <td>\r\n                      <salaxy-input-enum require=\"true\" ng-model=\"item.responsibilityCode\" name=\"{{ 'responsibilityCode' + $index }}\" label-type=\"plain\" type=\"select\"\r\n                        options=\"{ contentIssues: 'Raporttien sisältö', technicalIssues: 'Tekniset asiat' }\"></salaxy-input-enum>\r\n                    </td>\r\n                    <td class=\"text-right\">\r\n                      <button type=\"button\" class=\"btn btn-danger\" ng-click=\"$ctrl.current.calc.irDelivery.contactPersons.splice($index, 1)\">\r\n                        <i class=\"bi bi-trash\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\"></i>\r\n                      </button>\r\n                    </td>\r\n                  </tr>\r\n                </tbody>\r\n              </table>\r\n            </fieldset>\r\n          </div>\r\n          <div ng-if=\"$ctrl.currentSection == 'advanced'\">\r\n            <div class=\"container\" ng-init=\"$ctrl.exportJson()\">\r\n              <h3>Tuonti ja vienti</h3>\r\n              <div class=\"btn-toolbar\">\r\n                <div class=\"btn-group\">\r\n                  <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.importJson()\">Import JSON to this service model</button>\r\n                </div>\r\n              </div>\r\n              <sxy-code-editor read-only=\"$ctrl.current.isReadOnly\" lang=\"json\" ng-model=\"$ctrl.json\"></sxy-code-editor>\r\n            </div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </sxy-form>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/array/default.html\",`<div ng-switch=\"$ctrl.schemaModel.items.type\">\r\n  <div ng-switch-when=\"object\">\r\n    <table class=\"table\">\r\n      <caption>{{ $ctrl.getLabel() }}</caption>\r\n      <thead>\r\n        <tr>\r\n          <th ng-repeat=\"itemInput in $ctrl.getChildInputs(3)\">{{ $ctrl.getLabel(itemInput.name) }}</th>\r\n          <th class=\"text-end\">\r\n            <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-if=\"!$ctrl.getReadOnly()\" ng-click=\"$ctrl.createNew()\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"item in $ctrl.value\">\r\n          <td ng-repeat=\"itemInput in $ctrl.getChildInputs(3)\">{{ $ctrl.formatValue(itemInput.name, $parent.$index) }}</td>\r\n          <td class=\"text-end\" ng-if=\"!$ctrl.getReadOnly()\">\r\n            <div class=\"btn-group\" role=\"group\" ng-if=\"$ctrl.value.length > 1\">\r\n              <button ng-if=\"$index < $ctrl.value.length - 1 && $index > 0\" id=\"move\" type=\"button\" class=\"btn btn-secondary dropdown-toggle btn-xs\" data-bs-toggle=\"dropdown\" aria-expanded=\"false\">\r\n                <i class=\"bi bi-arrow-down-up\" title=\"Move row\"></i>\r\n              </button>\r\n              <ul ng-if=\"$index < $ctrl.value.length - 1 && $index > 0\" class=\"dropdown-menu\" aria-labelledby=\"move\">\r\n                <li>\r\n                  <button class=\"btn btn-secondary dropdown-item btn-xs\" ng-click=\"$ctrl.moveUp($index)\"><i class=\"bi bi-arrow-up\" title=\"Move row up\"></i></button>\r\n                </li>\r\n                <li>\r\n                  <button class=\"btn btn-secondary dropdown-item btn-xs\" ng-click=\"$ctrl.moveDown($index)\"><i class=\"bi bi-arrow-down\" title=\"Move row down\"></i></button>\r\n                </li>\r\n              </ul>\r\n            </div>\r\n            <button ng-if=\"$ctrl.value.length > 1 && $index == 0\" class=\"btn btn-secondary btn-xs\" ng-click=\"$ctrl.moveDown($index)\"><i class=\"bi bi-arrow-down\" title=\"Move row down\"></i></button>\r\n            <button ng-if=\"$ctrl.value.length > 1 && $index == $ctrl.value.length - 1\" class=\"btn btn-secondary btn-xs\" ng-click=\"$ctrl.moveUp($index)\"><i class=\"bi bi-arrow-up\" title=\"Move row up\"></i></button>\r\n            <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-click=\"$ctrl.edit(item, $index)\">\r\n              <i class=\"bi bi-pencil-fill\" title=\"Edit row\"></i>\r\n            </button>\r\n            <button type=\"button\" class=\"btn btn-danger btn-xs\" ng-click=\"$ctrl.delete(item, $index)\">\r\n              <i class=\"bi bi-trash\" title=\"Delete row\"></i>\r\n            </button>\r\n          </td>\r\n          <td class=\"text-end\" ng-if=\"$ctrl.getReadOnly()\">\r\n            <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-click=\"$ctrl.edit(item, $index)\">\r\n              <i class=\"bi bi-info-circle\" title=\"Show row\"></i>\r\n            </button>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n  </div>\r\n  <div ng-switch-when=\"string\">\r\n    <salaxy-input-enum ng-if=\"$ctrl.schemaModel.items.enum.length\" ng-model=\"$ctrl.value\" name=\"{{ $ctrl.id }}\" label=\"{{ $ctrl.getLabel() }}\" tooltip-html=\"{{ $ctrl.getDescr() }}\" read-only=\"$ctrl.getReadOnly()\" disabled=\"$ctrl.getDisable()\" require=\"$ctrl.getRequire()\"\r\n      type=\"multi-select\" options=\"$ctrl.getEnumOptions()\"></salaxy-input-enum>\r\n    <salaxy-form-group ng-if=\"!$ctrl.schemaModel.items.enum.length\" name=\"{{ $ctrl.id }}\" label=\"{{ $ctrl.getLabel() }}\" tooltip-html=\"{{ $ctrl.getDescr() }}\" read-only=\"$ctrl.getReadOnly()\" disabled=\"$ctrl.getDisable()\" require=\"$ctrl.getRequire()\">\r\n      <div class=\"input-group\" ng-repeat=\"item in $ctrl.value track by $index\">\r\n        <input type=\"text\" class=\"form-control\" ng-model=\"$ctrl.value[$index]\" name=\"{{ $ctrl.id + '_' + $index }}\" id=\"{{ $ctrl.id + '_' + $index }}\" ng-readonly=\"$ctrl.getReadOnly()\" ng-disabled=\"$ctrl.getDisable()\">\r\n        <div class=\"input-group-btn\">\r\n          <button type=\"button\" class=\"btn btn-danger\" ng-click=\"$ctrl.delete(item, $index)\">\r\n            <i class=\"bi bi-trash\" title=\"Delete row\"></i>\r\n          </button>\r\n        </div>\r\n      </div>\r\n      <div class=\"text-end\">\r\n        <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.value.push('')\">Add new</button>\r\n      </div>\r\n    </salaxy-form-group>\r\n  </div>\r\n  <div ng-switch-default>\r\n    <salaxy-form-group name=\"{{ $ctrl.id }}\" label=\"{{ $ctrl.getLabel() }}\" tooltip-html=\"{{ $ctrl.getDescr() }}\" read-only=\"$ctrl.getReadOnly()\" disabled=\"$ctrl.getDisable()\" require=\"$ctrl.getRequire()\">\r\n      <p>Unhandled array type: {{ $ctrl.schemaModel.items.type }}</p>\r\n    </salaxy-form-group>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/array/PercentDimension.html\",`<table class=\"table\">\r\n  <caption>{{ $ctrl.getLabel() }}</caption>\r\n  <thead>\r\n    <tr>\r\n      <th>{{\"SALAXY.MODEL.PercentDimension.id.title\" | sxyTranslate}}</th>\r\n      <th class=\"right\">{{\"SALAXY.MODEL.PercentDimension.percent.title\" | sxyTranslate}}</th>\r\n      <th class=\"right\">\r\n        <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-if=\"!$ctrl.getReadOnly()\" ng-click=\"$ctrl.createNew({})\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n      </th>\r\n    </tr>\r\n  </thead>\r\n  <tbody>\r\n    <tr ng-repeat=\"item in $ctrl.value\">\r\n      <td>\r\n        <salaxy-input ng-model=\"item.id\" name=\"{{ 'id' + $index }}\" label-type=\"plain\" read-only=\"$ctrl.getReadOnly()\" disabled=\"$ctrl.getDisable()\"></salaxy-input>\r\n      </td>\r\n      <td>\r\n        <salaxy-input-number ng-model=\"item.percent\" name=\"{{ 'percent' + $index }}\" label-type=\"plain\" read-only=\"$ctrl.getReadOnly()\" disabled=\"$ctrl.getDisable()\" unit=\"percent\"></salaxy-input-number>\r\n      </td>\r\n      <td class=\"text-end\">\r\n        <button  ng-if=\"!$ctrl.getReadOnly()\" type=\"button\" class=\"btn btn-danger\" ng-click=\"$ctrl.delete(item, $index)\">\r\n          <i class=\"bi bi-trash\" title=\"Delete row\"></i>\r\n        </button>\r\n      </td>\r\n    </tr>\r\n  </tbody>\r\n  <tfoot>\r\n    <tr class=\"total\">\r\n      <td>{{\"SALAXY.UI_Terms.total\" | sxyTranslate}}</td>\r\n      <td class=\"right\">{{ ($ctrl.getTotal('percent') || ($ctrl.value.length == 1 ? 1 : \"-\")) | sxyCount : 'percent' }}</td>\r\n      <td></td>\r\n    </tr>\r\n  </tfoot>\r\n</table>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/boolean/checkbox.html\",`<salaxy-input-boolean ng-model=\"$ctrl.value\" name=\"{{ $ctrl.id }}\" label=\"{{ $ctrl.getLabel() }}\" tooltip-html=\"{{ $ctrl.getDescr() }}\" read-only=\"$ctrl.getReadOnly()\" disabled=\"$ctrl.getDisable()\" ng-require=\"$ctrl.getRequire()\" type=\"checkbox\">\r\n\r\n</salaxy-input-boolean>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/boolean/default.html\",`<salaxy-input-boolean ng-model=\"$ctrl.value\" name=\"{{ $ctrl.id }}\" label=\"{{ $ctrl.getLabel() }}\" tooltip-html=\"{{ $ctrl.getDescr() }}\" read-only=\"$ctrl.getReadOnly()\"\r\n  disabled=\"$ctrl.getDisable()\" require=\"$ctrl.getRequire()\" type=\"select\"></salaxy-input-boolean>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/boolean/radio.html\",`<salaxy-input-boolean ng-model=\"$ctrl.value\" name=\"{{ $ctrl.id }}\" label=\"{{ $ctrl.getLabel() }}\" tooltip-html=\"{{ $ctrl.getDescr() }}\" read-only=\"$ctrl.getReadOnly()\"\r\n  disabled=\"$ctrl.getDisable()\" require=\"$ctrl.getRequire()\" type=\"radio\"></salaxy-input-boolean>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/boolean/switch.html\",`<salaxy-input-boolean ng-model=\"$ctrl.value\" name=\"{{ $ctrl.id }}\" label=\"{{ $ctrl.getLabel() }}\" tooltip-html=\"{{ $ctrl.getDescr() }}\" read-only=\"$ctrl.getReadOnly()\"\r\n  disabled=\"$ctrl.getDisable()\" require=\"$ctrl.getRequire()\" type=\"switch\"></salaxy-input-boolean>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/custom-templates/array-accounting-targets.html\",`\r\n<table class=\"table\">\r\n  <thead>\r\n    <tr>\r\n      <th sxy-text=\"SALAXY.MODEL.AccountingSettings.targets.title\" colspan=\"2\"></th>\r\n      <th></th>\r\n      <th class=\"text-end\">\r\n        <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-if=\"!$ctrl.getReadOnly()\" ng-click=\"$ctrl.createNew()\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n      </th>\r\n    </tr>\r\n  </thead>\r\n  <tbody>\r\n    <tr ng-repeat=\"item in $ctrl.value\">\r\n      <td>\r\n        <salaxy-avatar avatar=\"item.avatar\"></salaxy-avatar>\r\n      </td>\r\n      <td>{{item.avatar.displayName}}</td>\r\n      <td></td>\r\n      <td class=\"text-end\" ng-if=\"!$ctrl.getReadOnly()\">\r\n        <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-click=\"$ctrl.edit(item, $index)\">\r\n          <i class=\"bi bi-pencil-fill\" title=\"Edit row\"></i>\r\n        </button>\r\n        <button type=\"button\" class=\"btn btn-danger btn-xs\" ng-click=\"$ctrl.delete(item, $index)\">\r\n            <i class=\"bi bi-trash\" title=\"Delete row\"></i>\r\n          </button>\r\n      </td>\r\n\r\n    </tr>\r\n  </tbody>\r\n</table>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/custom-templates/array-insurance.html\",`<p sxy-text=\"SALAXY.MODEL.CalculationSettings.insuranceContracts.title\" class=\"table-title\"></p>\r\n<table class=\"table\">\r\n\r\n  <thead>\r\n    <tr>\r\n      <th sxy-text=\"SALAXY.MODEL.InsuranceContract.company.title\"></th>\r\n      <th sxy-text=\"SALAXY.MODEL.InsuranceContract.contractNumber.title\"></th>\r\n      <th sxy-text=\"SALAXY.MODEL.InsuranceContract.status.title\"></th>\r\n      <th class=\"right\" sxy-text=\"SALAXY.MODEL.InsuranceContract.startDate.title\"></th>\r\n      <th class=\"text-end\">\r\n        <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-if=\"!$ctrl.getReadOnly()\" ng-click=\"$ctrl.createNew()\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n      </th>\r\n    </tr>\r\n  </thead>\r\n  <tbody>\r\n    <tr ng-repeat=\"item in $ctrl.value\">\r\n      <td>{{'SALAXY.ENUM.InsuranceCompany.' + item.company + '.label' | sxyTranslate}}</td>\r\n      <td>{{item.contractNumber}}</td>\r\n      <td>{{'SALAXY.ENUM.SettingsStatus.' + item.status + '.label' | sxyTranslate}}</td>\r\n      <td class=\"right\">{{item.startDate | date}}\r\n        <span class=\"\" ng-if=\"item.endDate\">\r\n          <br><small>(päättyy {{item.endDate | date}})</small>\r\n        </span>\r\n      </td>\r\n\r\n      <td class=\"text-end\" ng-if=\"!$ctrl.getReadOnly()\">\r\n        <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-click=\"$ctrl.edit(item, $index)\">\r\n            <i class=\"bi bi-pencil-fill\" title=\"Edit row\"></i>\r\n          </button>\r\n        <button type=\"button\" class=\"btn btn-danger btn-xs\" ng-click=\"$ctrl.delete(item, $index)\">\r\n            <i class=\"bi bi-trash\" title=\"Delete row\"></i>\r\n          </button>\r\n      </td>\r\n      <td class=\"text-end\" ng-if=\"$ctrl.getReadOnly()\">\r\n        <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-click=\"$ctrl.edit(item, $index)\">\r\n            <i class=\"bi bi-info-circle\" title=\"Show row\"></i>\r\n          </button>\r\n      </td>\r\n    </tr>\r\n  </tbody>\r\n</table>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/custom-templates/array-payment-channels.html\",`<table class=\"table\">\r\n  <thead>\r\n    <tr>\r\n      <th sxy-text=\"SALAXY.MODEL.PaymentSettings.channels.title\" colspan=\"2\"></th>\r\n      <th>Käytössä</th>\r\n      <th>Valittavissa</th>\r\n      <th class=\"text-end\"></th>\r\n\r\n    </tr>\r\n  </thead>\r\n  <tbody ng-controller=\"CompanySettingsController as $settingsCtrl\">\r\n    <tr ng-repeat=\"item in $ctrl.value\">\r\n      <td>\r\n        <salaxy-avatar avatar=\"$settingsCtrl.getPaymentChannelAvatar(item)\"></salaxy-avatar>\r\n      </td>\r\n      <td>\r\n        {{$settingsCtrl.getPaymentChannelAvatar(item).displayName}}\r\n      </td>\r\n      <td>\r\n        <span ng-if=\"item.isAvailable\">{{'SALAXY.UI_Terms.yes' | sxyTranslate}} </span>\r\n        <span ng-if=\"!item.isAvailable\">{{'SALAXY.UI_Terms.no' | sxyTranslate}} </span>\r\n      </td>\r\n      <td>\r\n        <span ng-if=\"item.isEnabled\">{{'SALAXY.UI_Terms.yes' | sxyTranslate}} </span>\r\n        <span ng-if=\"!item.isEnabled\">{{'SALAXY.UI_Terms.no' | sxyTranslate}} </span>\r\n      </td>\r\n      <td class=\"text-end\" ng-if=\"!$ctrl.getReadOnly()\">\r\n        <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-click=\"$ctrl.edit(item, $index)\">\r\n            <i class=\"bi bi-pencil-fill\" title=\"Edit row\"></i>\r\n          </button>\r\n      </td>\r\n    </tr>\r\n  </tbody>\r\n</table>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/custom-templates/array-pension.html\",`<p sxy-text=\"SALAXY.MODEL.CalculationSettings.pensionContracts.title\" class=\"table-title\"></p>\r\n<table class=\"table\">\r\n\r\n  <thead>\r\n    <tr>\r\n      <th sxy-text=\"SALAXY.MODEL.PensionContract.company.title\"></th>\r\n      <th sxy-text=\"SALAXY.MODEL.PensionContract.contractNumber.title\"></th>\r\n      <th sxy-text=\"SALAXY.MODEL.PensionContract.status.title\"></th>\r\n      <th class=\"right\" sxy-text=\"SALAXY.MODEL.PensionContract.startDate.title\"></th>\r\n      <th class=\"text-end\">\r\n        <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-if=\"!$ctrl.getReadOnly()\" ng-click=\"$ctrl.createNew()\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n      </th>\r\n    </tr>\r\n  </thead>\r\n  <tbody>\r\n    <tr ng-repeat=\"item in $ctrl.value\">\r\n      <td>{{'SALAXY.ENUM.PensionCompany.' + item.company + '.label' | sxyTranslate}}</td>\r\n      <td>{{ item.contractNumber}}</td>\r\n      <td>{{'SALAXY.ENUM.SettingsStatus.' + item.status + '.label' | sxyTranslate}}</td>\r\n      <td class=\"right\">{{item.startDate | date}}\r\n        <span class=\"\" ng-if=\"item.endDate\">\r\n          <br><small>(päättyy {{item.endDate | date}})</small>\r\n        </span>\r\n      </td>\r\n\r\n      <td class=\"text-end\" ng-if=\"!$ctrl.getReadOnly()\">\r\n        <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-click=\"$ctrl.edit(item, $index)\">\r\n            <i class=\"bi bi-pencil-fill\" title=\"Edit row\"></i>\r\n          </button>\r\n        <button type=\"button\" class=\"btn btn-danger btn-xs\" ng-click=\"$ctrl.delete(item, $index)\">\r\n            <i class=\"bi bi-trash\" title=\"Delete row\"></i>\r\n          </button>\r\n      </td>\r\n      <td class=\"text-end\" ng-if=\"$ctrl.getReadOnly()\">\r\n        <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-click=\"$ctrl.edit(item, $index)\">\r\n            <i class=\"bi bi-info-circle\" title=\"Show row\"></i>\r\n          </button>\r\n      </td>\r\n    </tr>\r\n  </tbody>\r\n</table>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/custom-templates/array-service-model-payment-channels.html\",`<table class=\"table\">\r\n  <thead>\r\n    <tr>\r\n      <th sxy-text=\"SALAXY.MODEL.PaymentSettings.channels.title\" colspan=\"2\"></th>\r\n      <th>Käytössä</th>\r\n      <th>Valittavissa</th>\r\n      <th class=\"text-end\">\r\n        <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-if=\"!$ctrl.getReadOnly()\" ng-click=\"$ctrl.createNew()\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n      </th>\r\n\r\n    </tr>\r\n  </thead>\r\n  <tbody ng-controller=\"CompanySettingsController as $settingsCtrl\">\r\n    <tr ng-repeat=\"item in $ctrl.value\">\r\n      <td>\r\n        <salaxy-avatar avatar=\"$settingsCtrl.getPaymentChannelAvatar(item)\"></salaxy-avatar>\r\n      </td>\r\n      <td>\r\n        {{$settingsCtrl.getPaymentChannelAvatar(item).displayName}}\r\n      </td>\r\n      <td>\r\n        <span ng-if=\"item.isAvailable\">{{'SALAXY.UI_Terms.yes' | sxyTranslate}} </span>\r\n        <span ng-if=\"!item.isAvailable\">{{'SALAXY.UI_Terms.no' | sxyTranslate}} </span>\r\n      </td>\r\n      <td>\r\n        <span ng-if=\"item.isEnabled\">{{'SALAXY.UI_Terms.yes' | sxyTranslate}} </span>\r\n        <span ng-if=\"!item.isEnabled\">{{'SALAXY.UI_Terms.no' | sxyTranslate}} </span>\r\n      </td>\r\n      <td class=\"text-end\" ng-if=\"!$ctrl.getReadOnly()\">\r\n        <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-click=\"$ctrl.edit(item, $index)\">\r\n            <i class=\"bi bi-pencil-fill\" title=\"Edit row\"></i>\r\n          </button>\r\n      </td>\r\n    </tr>\r\n  </tbody>\r\n</table>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/custom-templates/array-usecase.html\",`<table class=\"table\">\r\n  <thead>\r\n    <tr>\r\n      <th sxy-text=\"SALAXY.NG1.ArrayUsecase.table.usecaseLabel\" colspan=\"2\"></th>\r\n      <th></th>\r\n\r\n      <th class=\"text-end\">\r\n        <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-if=\"!$ctrl.getReadOnly()\" ng-click=\"$ctrl.createNew()\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n      </th>\r\n    </tr>\r\n  </thead>\r\n  <tbody>\r\n    <tr ng-repeat=\"item in $ctrl.value\">\r\n      <td>\r\n        {{item.label}}\r\n      </td>\r\n      <td>{{'SALAXY.NG1.CalcListComponent.' + item.itemType | sxyTranslate}}</td>\r\n      <td></td>\r\n      <td class=\"text-end\" ng-if=\"!$ctrl.getReadOnly()\">\r\n        <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-click=\"$ctrl.edit(item, $index)\">\r\n          <i class=\"bi bi-pencil-fill\" title=\"Edit row\"></i>\r\n        </button>\r\n      </td>\r\n    </tr>\r\n  </tbody>\r\n</table>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/custom-templates/cost-accounting-options.html\",`<table class=\"table\" ng-if=\"$ctrl.form\">\r\n  <thead>\r\n    <tr>\r\n      <th sxy-text=\"SALAXY.MODEL.CostAccountingDimensionOption.value.title\"></th>\r\n      <th sxy-text=\"SALAXY.MODEL.CostAccountingDimensionOption.text.title\"></th>\r\n      <th sxy-text=\"SALAXY.MODEL.CostAccountingDimensionOption.scope.title\"></th>\r\n      <th colspan=\"2\">\r\n        <div class=\"btn-group btn-xs float-end dropdown\">\r\n          <button id=\"single-button\" type=\"button\" class=\"btn btn-default btn-xs dropdown-toggle\" data-bs-toggle=\"dropdown\">\r\n            <i class=\"bi bi-three-dots\" aria-hidden=\"true\"></i>\r\n          </button>\r\n          <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"single-button\">\r\n            <li role=\"menuitem\">\r\n              <a href=\"\" ng-controller=\"ExportController as $export\" ng-click=\"$export.showExport($ctrl.getExportable())\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.ODataActionsComponent.export\"></a>\r\n            </li>\r\n            <!--\r\n              <li role=\"menuitem\">\r\n                <a href=\"\" ng-controller=\"ImportController as $import\" ng-click=\"$import.showImport($ctrl.getImportable())\" class=\"dropdown-item\" sxy-text=\"SALAXY.NG1.ODataActionsComponent.import\"></a>\r\n              </li> --> \r\n          </ul>\r\n        </div>\r\n        <button type=\"button\" class=\"btn btn-default btn-xs float-end\" ng-if=\"!$ctrl.getReadOnly()\" ng-click=\"$ctrl.createNew({})\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n      </th>\r\n    </tr>\r\n  </thead>\r\n  <tbody>\r\n    <tr ng-repeat=\"item in $ctrl.value\">\r\n      <td>\r\n        <salaxy-input ng-model=\"item.value\" name=\"{{ 'value' + $index }}\" label-type=\"plain\" read-only=\"$ctrl.getReadOnly()\" ></salaxy-input>\r\n      </td>\r\n      <td>\r\n        <salaxy-input ng-model=\"item.text\" name=\"{{ 'text' + $index }}\" label-type=\"plain\" read-only=\"$ctrl.getReadOnly()\" ></salaxy-input>\r\n      </td>\r\n      <td>\r\n        <salaxy-input-enum enum=\"CostAccountingDimensionScope\" ng-model=\"item.scope\" name=\"{{ 'scope' + $index }}\" label-type=\"plain\" read-only=\"$ctrl.getReadOnly()\" ></salaxy-input-enum>\r\n      </td>\r\n      <td colspan=\"2\" class=\"text-end\">\r\n        <button ng-if=\"!$ctrl.getReadOnly()\" type=\"button\" class=\"btn btn-danger\" ng-click=\"$ctrl.delete(item, $index)\">\r\n          <i class=\"bi bi-trash\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\"></i>\r\n        </button>\r\n      </td>\r\n    </tr>\r\n  </tbody>\r\n</table>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/custom-templates/pay-stats-row-types.html\",`<table class=\"table\" ng-if=\"$ctrl.form\">\r\n  <thead>\r\n    <tr>\r\n      <th sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.inputs.type\"></th>\r\n      <th class=\"text-right\">\r\n        <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-if=\"!$ctrl.getReadOnly()\" ng-click=\"$ctrl.value=($ctrl.value || []);$ctrl.value.push('')\" sxy-text=\"SALAXY.UI_Terms.addRow\"></button>\r\n      </th>\r\n    </tr>\r\n  </thead>\r\n  <tbody>\r\n    <tr ng-repeat=\"item in $ctrl.value track by $index\">\r\n      <td>\r\n        <salaxy-input-pay-stats-row-type ng-ref=\"$row\" ng-model=\"$ctrl.value[$index]\" name=\"{{ 'rowType' + $index }}\" label-type=\"plain\" read-only=\"$ctrl.getReadOnly()\" ></salaxy-input-pay-stats-row-type>\r\n      </td>\r\n      <td class=\"text-right\" ng-if=\"!$ctrl.getReadOnly()\">\r\n        <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-click=\"$row.edit()\">\r\n          <i class=\"bi bi-pencil-fill\" title=\"Edit row\"></i>\r\n        </button>\r\n        <button type=\"button\" class=\"btn btn-danger btn-xs\" ng-click=\"$ctrl.delete(item, $index)\">\r\n          <i class=\"bi bi-trash\" title=\"Delete row\"></i>\r\n        </button>\r\n      </td>\r\n      <td class=\"text-right\" ng-if=\"$ctrl.getReadOnly()\">\r\n        <button type=\"button\" class=\"btn btn-primary btn-xs\" ng-click=\"$row.edit()\">\r\n          <i class=\"bi bi-info-circle\" title=\"Show row\"></i>\r\n        </button>\r\n      </td>\r\n    </tr>\r\n  </tbody>\r\n</table>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/custom-templates/select-accounting-target-item.html\",`<a class=\"clickable salaxy-component salaxy-avatar-item\">\r\n  <salaxy-avatar style=\"font-size: 30px; vertical-align: middle;\"\r\n  avatar=\"match.model.otherPartyInfo.avatar\"></salaxy-avatar>\r\n  <b class=\"salaxy-highlight\" ng-bind-html=\"match.label | uibTypeaheadHighlight:query\"></b>\r\n</a>\r\n`);\n\n $templateCache.put(\"salaxy-components/sxy-form/error/default.html\",`<salaxy-form-group name=\"{{ $ctrl.id }}\" label=\"{{ $ctrl.getLabel() }}\" tooltip-html=\"{{ $ctrl.getDescr() }}\" read-only=\"$ctrl.getReadOnly()\" disabled=\"$ctrl.getDisable()\"\r\n  require=\"$ctrl.getRequire()\">\r\n  <sxy-alert type=\"error\">\r\n    <div ng-if=\"$ctrl.input.content\">{{ $ctrl.input.content }}</div>\r\n    <div ng-if=\"!$ctrl.input.content\">No UI for model \"{{ $ctrl.model }}\",  type \"{{ $ctrl.type }}\", format \"{{ $ctrl.format }}\".</div>\r\n    <div>\r\n      <salaxy-json-formatter key=\"'See input json'\" json=\"$ctrl.input\" type=\"dialog\"></salaxy-json-formatter>\r\n      <salaxy-json-formatter key=\"'See schema'\" json=\"$ctrl.schemaModel\" type=\"dialog\"></salaxy-json-formatter>\r\n    </div>\r\n  </sxy-alert>\r\n</salaxy-form-group>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/integer/default.html\",`<salaxy-input-number ng-model=\"$ctrl.value\" name=\"{{ $ctrl.id }}\" label=\"{{ $ctrl.getLabel() }}\" tooltip-html=\"{{ $ctrl.getDescr() }}\" read-only=\"$ctrl.getReadOnly()\" disabled=\"$ctrl.getDisable()\" require=\"$ctrl.getRequire()\" sxy-integer>\r\n</salaxy-input-number>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/number/default.html\",`<salaxy-input-number ng-model=\"$ctrl.value\" name=\"{{ $ctrl.id }}\" label=\"{{ $ctrl.getLabel() }}\" tooltip-html=\"{{ $ctrl.getDescr() }}\" read-only=\"$ctrl.getReadOnly()\" disabled=\"$ctrl.getDisable()\" require=\"$ctrl.getRequire()\" unit=\"{{ $ctrl.input.format }}\"\r\n  minimum=\"{{$ctrl.getMinimum()}}\" maximum=\"{{$ctrl.getMaximum()}}\" multiple-of=\"{{$ctrl.getMultipleOf()}}\">\r\n</salaxy-input-number>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/object/Avatar.html\",`<salaxy-form-group name=\"{{ $ctrl.id }}\" label=\"{{ $ctrl.getLabel() }}\" tooltip-html=\"{{ $ctrl.getDescr() }}\" read-only=\"$ctrl.getReadOnly()\" disabled=\"$ctrl.getDisable()\" require=\"$ctrl.getRequire()\">\r\n  <table>\r\n    <tr>\r\n      <td class=\"td-avatar middle\">\r\n        <salaxy-avatar avatar=\"$ctrl.value\"></salaxy-avatar>\r\n      </td>\r\n      <td class=\"td-name middle\">\r\n        <strong>{{$ctrl.value.displayName}}</strong><br />\r\n        <span class=\"\">{{ $ctrl.value.id | sxyIban }}</span>\r\n      </td>\r\n    </tr>\r\n  </table>\r\n</salaxy-form-group>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/object/DateRange.html\",`<salaxy-date-range ng-model=\"$ctrl.value\" name=\"{{ $ctrl.id }}\" label=\"{{ $ctrl.getLabel() }}\" tooltip-html=\"{{ $ctrl.getDescr() }}\" read-only=\"$ctrl.getReadOnly()\"\r\n  disabled=\"$ctrl.getDisable()\" require=\"$ctrl.getRequire()\">\r\n</salaxy-date-range>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/object/default.html\",`<salaxy-form-group name=\"{{ $ctrl.id }}\" label=\"{{ $ctrl.getLabel() }}\" tooltip-html=\"{{ $ctrl.getDescr() }}\" read-only=\"$ctrl.getReadOnly()\" disabled=\"$ctrl.getDisable()\"\r\n  require=\"$ctrl.getRequire()\">\r\n  <div>\r\n    <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.isInEdit[$ctrl.id] = !$ctrl.isInEdit[$ctrl.id]\">{{ $ctrl.isInEdit[$ctrl.id] ? \"Hide\" : \"Edit\" }}</button>\r\n  </div>\r\n</salaxy-form-group>\r\n<div ng-if=\"$ctrl.isInEdit[$ctrl.id]\" class=\"row\">\r\n  <div class=\"col-md-offset-1 col-11\">\r\n    <sxy-fieldset model=\"{{ $ctrl.model }}\"></sxy-fieldset>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/string/date-time.html\",`<salaxy-form-group name=\"{{$ctrl.id}}\" class=\"salaxy-component salaxy-read-only\" label=\"{{$ctrl.getLabel()}}\">\r\n  <div class=\"form-control-plaintext\">{{ $ctrl.value | date : \"dd.MM.yyyy HH:mm\" }}</div>\r\n</salaxy-form-group>\r\n`);\n\n $templateCache.put(\"salaxy-components/sxy-form/string/date.html\",`<salaxy-datepicker-popup ng-model=\"$ctrl.value\" name=\"{{ $ctrl.id }}\" label=\"{{ $ctrl.getLabel() }}\" tooltip-html=\"{{ $ctrl.getDescr() }}\" read-only=\"$ctrl.getReadOnly()\" disabled=\"$ctrl.getDisable()\" require=\"$ctrl.getRequire()\"></salaxy-datepicker-popup>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/string/default.html\",`<salaxy-input ng-model=\"$ctrl.value\" name=\"{{ $ctrl.id }}\" label=\"{{ $ctrl.getLabel() }}\" tooltip-html=\"{{ $ctrl.getDescr() }}\" read-only=\"$ctrl.getReadOnly()\" disabled=\"$ctrl.getDisable()\" require=\"$ctrl.getRequire()\" minlength=\"{{$ctrl.getMinLength()}}\"\r\n  maxlength=\"{{$ctrl.getMaxLength()}}\" pattern=\"{{$ctrl.getPattern()}}\">\r\n</salaxy-input>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/string/email.html\",`<salaxy-input ng-model=\"$ctrl.value\" name=\"{{ $ctrl.id }}\" label=\"{{ $ctrl.getLabel() }}\" tooltip-html=\"{{ $ctrl.getDescr() }}\" read-only=\"$ctrl.getReadOnly()\"\r\n  disabled=\"$ctrl.getDisable()\" require=\"$ctrl.getRequire()\" sxy-email>\r\n</salaxy-input>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/string/enum.html\",`<salaxy-input-enum ng-model=\"$ctrl.value\" name=\"{{ $ctrl.id }}\" label=\"{{ $ctrl.getLabel() }}\" tooltip-html=\"{{ $ctrl.getDescr() }}\" read-only=\"$ctrl.getReadOnly()\"\r\n  disabled=\"$ctrl.getDisable()\" require=\"$ctrl.getRequire()\" type=\"{{ $ctrl.getFormat() }}\" options=\"$ctrl.getEnumOptions()\"></salaxy-input-enum>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/string/multiline.html\",`<salaxy-textarea ng-model=\"$ctrl.value\" name=\"{{ $ctrl.id }}\" label=\"{{ $ctrl.getLabel() }}\" tooltip-html=\"{{ $ctrl.getDescr() }}\" read-only=\"$ctrl.getReadOnly()\"\r\n  disabled=\"$ctrl.getDisable()\" require=\"$ctrl.getRequire()\" maxlength=\"10000\">\r\n</salaxy-textarea>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/string/password.html\",`<salaxy-input ng-model=\"$ctrl.value\" name=\"{{ $ctrl.id }}\" label=\"{{ $ctrl.getLabel() }}\" tooltip-html=\"{{ $ctrl.getDescr() }}\" read-only=\"$ctrl.getReadOnly()\"\r\n  disabled=\"$ctrl.getDisable()\" require=\"$ctrl.getRequire()\" type=\"password\"></salaxy-input>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/string/pension-contract-number.html\",`<salaxy-input  ng-if=\"'!admin' | sxyIsInRole\" ng-model=\"$ctrl.value\" name=\"{{ $ctrl.id }}\" label=\"{{ $ctrl.getLabel() }}\" tooltip-html=\"{{ $ctrl.getDescr() }}\" read-only=\"$ctrl.getReadOnly()\" disabled=\"$ctrl.getDisable()\" require=\"$ctrl.getRequire()\" type=\"pension-contract-number\" sxy-pension-contract-number>\r\n</salaxy-input>\r\n<salaxy-input  ng-if=\"'admin' | sxyIsInRole\" ng-model=\"$ctrl.value\" name=\"{{ $ctrl.id }}\" label=\"{{ $ctrl.getLabel() }}\" tooltip-html=\"{{ $ctrl.getDescr() }}\" read-only=\"$ctrl.getReadOnly()\" disabled=\"$ctrl.getDisable()\" require=\"$ctrl.getRequire()\" type=\"pension-contract-number\">\r\n</salaxy-input>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/string/telephone.html\",`<salaxy-input ng-model=\"$ctrl.value\" name=\"{{ $ctrl.id }}\" label=\"{{ $ctrl.getLabel() }}\" tooltip-html=\"{{ $ctrl.getDescr() }}\" read-only=\"$ctrl.getReadOnly()\"\r\n  disabled=\"$ctrl.getDisable()\" require=\"$ctrl.getRequire()\" sxy-mobile-phone></salaxy-input>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/SxyAlert.html\",`<div class=\"salaxy-component salaxy-alert\">\r\n  <!-- TODO: Switch styling to \"sxy-component sxy-alert\" -->\r\n  <div ng-class=\"$ctrl.getAlertClasses()\">\r\n    <div>\r\n      <table style=\"width: 100%; border-collapse:separate;\">\r\n        <!-- TODO: Switch this to position:absolute & margins or flex-grid -->\r\n        <tr>\r\n          <td class=\"icon-container hidden-xxs\" ng-if=\"$ctrl.getAlertIcon()\">\r\n            <span class=\"icon\"><i class=\"bi {{ $ctrl.getAlertIcon() }}\"></i></span>\r\n          </td>\r\n          <td>\r\n            <div class=\"main\">\r\n              <ng-transclude>\r\n                <div sxy-html=\"{{$ctrl.msg}}\"></div>\r\n              </ng-transclude>\r\n            </div>\r\n          </td>\r\n          <td ng-if=\"$ctrl.aside\" class=\"text-end\">\r\n            <button class=\"btn btn-info btn-main\" ng-click=\"$ctrl.showMoreInfo = !$ctrl.showMoreInfo\" sxy-text=\"SALAXY.UI_Terms.learnMore\"></button>\r\n          </td>\r\n        </tr>\r\n      </table>\r\n      <div class=\"collapse\" ng-if=\"$ctrl.aside\" ng-class=\"{ show: $ctrl.showMoreInfo }\">\r\n        <div sxy-html=\"$ctrl.aside\"></div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/SxyCodeEditor.html\",`<div class=\"salaxy-component sxy-code-editor\">\r\n  <div ng-if=\"$ctrl.mode == 'basic'\">\r\n    <pre ng-if=\"$ctrl.readOnly\" style=\"padding: 10px; background-color: #1e1e1e; color: #d4d4d4\">{{ $ctrl.code }}</pre>\r\n    <textarea ng-if=\"!$ctrl.readOnly\"\r\n      style=\"font-family: 'Courier New', Courier, monospace; background-color: #1e1e1e; color: #d4d4d4; padding: 10px; width: 100%;\"\r\n      ng-model=\"$ctrl.value\" ng-model-options=\"{allowInvalid: true, debounce: 250, updateOn: 'default' }\" ng-change=\"$ctrl.onChange()\"\r\n      name=\"actionContent\" rows=\"10\"></textarea>\r\n  </div>\r\n  <div ng-if=\"$ctrl.mode != 'basic'\">\r\n    <iframe ng-src=\"{{ $ctrl.codeEditorUrl }}\" style=\"width: 100%;\" ng-style=\"{ height: $ctrl.height || '400px' }\"></iframe>\r\n  </div>\r\n</div>\r\n\r\n\r\n`);\n\n $templateCache.put(\"salaxy-components/sxy-form/SxyFieldset.html\",`<div ng-switch=\"$ctrl.format\" ng-if=\"$ctrl.form\">\r\n  <fieldset ng-switch-when=\"source\">\r\n    <legend>Form inputs source code (auto-gen)</legend>\r\n    <pre>&lt;fieldset&gt;\r\n  &lt;legend&gt;{{ $ctrl.label }}&lt;/legend&gt;\r\n<span ng-repeat=\"input in $ctrl.getChildInputs()\">  &lt;sxy-input model=\"{{ input.path }}\"&gt;&lt;/sxy-input&gt;<br /></span>&lt;/fieldset&gt;\r\n</pre>\r\n  </fieldset>\r\n  <fieldset ng-switch-default>\r\n    <legend>{{ $ctrl.getLabel() }}</legend>\r\n    <p>{{ $ctrl.getDescr() }}</p>\r\n    <sxy-input model=\"{{ input.path }}\" ng-repeat=\"input in $ctrl.getChildInputs()\"></sxy-input>\r\n  </fieldset>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/SxyForm.html\",`<div class=\"salaxy-component sxy-form form-horizontal\">\r\n  <h2 ng-if=\"$ctrl.legend\">{{ $ctrl.legend }}</h2>\r\n  <ng-form name=\"$ctrl.ngForm\">\r\n    <div ng-if=\"!$ctrl.isReady\">\r\n      <p>Ladataan...</p>\r\n    </div>\r\n    <div ng-if=\"$ctrl.isReady\">\r\n      <div ng-if=\"!$ctrl.autoGen\" ng-transclude=\"div\">\r\n        <div class=\"alert alert-info\">\r\n          Either set <code>auto-gen</code> attribute to true or add a\r\n          <code>DIV</code> element with your form sxy-input definitions.\r\n        </div>\r\n      </div>\r\n      <div ng-if=\"$ctrl.autoGen\">\r\n        <sxy-fieldset model=\"form\" label=\"{{ $ctrl.label }}\"></sxy-fieldset>\r\n      </div>\r\n      <div ng-if=\"$ctrl.debugger\">\r\n        <salaxy-tab-buttons\r\n          current-tab=\"$ctrl.currentTab\"\r\n          options=\"[\r\n            { value: 'data', text: 'Data' },\r\n            { value: 'schema', text: 'Auto-gen' },\r\n            { value: 'codegen', text: 'Code-gen' },\r\n            { value: 'registrations', text: 'Components' },\r\n            { value: 'validation', text: 'Validation' }\r\n          ]\"\r\n          tabs-id=\"sxyForm\">\r\n        </salaxy-tab-buttons>\r\n        <div class=\"tab-content\" id=\"tab-content-sxyForm\">\r\n          <div class=\"tab-pane\" id=\"data-tab\">\r\n            <salaxy-json-formatter key=\"'data'\" json=\"$ctrl.model\" open=\"2\"></salaxy-json-formatter>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"schema-tab\">\r\n            <salaxy-json-formatter key=\"$ctrl.type\" json=\"$ctrl.schemaModel\" open=\"2\"></salaxy-json-formatter>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"codegen-tab\">\r\n            <sxy-fieldset model=\"form\" format=\"source\" label=\"{{ $ctrl.label }}\"></sxy-fieldset>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"registrations-tab\">\r\n            <p>\r\n              This is a list of component registrations. Note that debugger \"Code-gen\" tab currently makes one registration for the form (with name \"[Parent][n1]_form[n2]\"). This might be removed later.\r\n            </p>\r\n            <ul>\r\n              <li ng-repeat=\"(key, value) in $ctrl.registeredInputs\">{{ key }}</li>\r\n            </ul>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"validation-tab\">\r\n            <salaxy-validation-summary api-validation=\"$ctrl.getValidation()\"></salaxy-validation-summary>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </ng-form>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/SxyGrid.html\",`<div class=\"salaxy-component sxy-grid height100\">\r\n  <div class=\"btn-toolbar\">\r\n    <div class=\"btn-group\">\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.addRow()\">Add row</button>\r\n      <button type=\"button\" class=\"btn btn-danger\" ng-disabled=\"!$ctrl.selection.length\" ng-click=\"$ctrl.deleteSelectedRows()\">Delete rows ({{ $ctrl.selection.length }})</button>\r\n    </div>\r\n    <div class=\"btn-group\" ng-if=\"$ctrl\">\r\n      <button type=\"button\" class=\"btn btn-default\" ng-controller=\"ExportController as $export\" ng-click=\"$export.showExport($ctrl.getExportable())\">Export</button>\r\n    </div>\r\n  </div>\r\n  <div id=\"dataGrid\" class=\"ag-theme-balham height100\" style=\"height: calc(100% - 34px);overflow: hidden;\"></div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/SxyInput-dialog-edit.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\">{{ $ctrl.logic.title }}</h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n</div>\r\n<div class=\"modal-body\">\r\n  <sxy-form open-api=\"{{ $ctrl.logic.openApi }}\" type=\"{{ $ctrl.logic.type }}\" auto-gen=\"true\" debugger=\"$ctrl.logic.debugger\" model=\"$ctrl.current\" read-only=\"{{$ctrl.logic.isReadOnly ? 'true' : ''}}\"></sxy-form>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button type=\"button\" ng-if=\"$ctrl.logic.showDelete\" class=\"btn btn-danger float-start\" ng-click=\"$close('delete-no-save')\" sxy-text=\"SALAXY.UI_Terms.delete\"></button>\r\n  <button type=\"reset\" ng-if=\"!$ctrl.logic.isReadOnly\" class=\"btn btn-default ms-auto\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n  <button type=\"button\" ng-if=\"!$ctrl.logic.isReadOnly\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.ok\"></button>\r\n  <button type=\"button\" ng-if=\"$ctrl.logic.isReadOnly\" class=\"btn btn-primary\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/SxyInput.html\",`<ng-include src=\"$ctrl.templateUrl\" ng-if=\"$ctrl.form\"></ng-include>`);\n\n $templateCache.put(\"salaxy-components/sxy-form/SxySchemaEditor.html\",`<div class=\"row\">\r\n  <div class=\"col-md-6\" ng-repeat=\"(key, value) in $ctrl.model\">\r\n    <fieldset>\r\n      <legend>\r\n        <button type=\"button\" class=\"btn btn-danger btn-xs float-end\" ng-click=\"$ctrl.deleteProperty(key)\">Poista</button>\r\n        {{ $index + 1 }}. {{ key }}\r\n      </legend>\r\n      <salaxy-input label=\"Teksti\" name=\"title\" ng-model=\"value.title\"></salaxy-input>\r\n      <salaxy-input label=\"Kuvaus\" name=\"description\" ng-model=\"value.description\"></salaxy-input>\r\n      <salaxy-input-enum label=\"Tietotyyppi\" name=\"type\" ng-model=\"value.type\"\r\n        options=\"$ctrl.types\"></salaxy-input-enum>\r\n      <salaxy-input-enum ng-if=\"value.type\" label=\"Käyttöliittymä\" name=\"type\" ng-model=\"value.format\"\r\n        disable-cache=\"true\" options=\"$ctrl.getFormats(value.type)\"></salaxy-input-enum>\r\n<!--\r\n- Lisää esikatselu\r\n- Lisää Array: Prosenttipohjainen jako, ehkä myös string ja number\r\n-->\r\n    </fieldset>\r\n  </div>\r\n  <div class=\"col-md-6\">\r\n    <button type=\"button\" class=\"btn btn-primary btn-block\" ng-click=\"$ctrl.addProperty()\">Lisää uusi</button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/sxy-table/SxyTable.html\",`<div style=\"margin-top: 10px; margin-bottom: 10px;\"></div>`);\n\n $templateCache.put(\"salaxy-components/test/AccountReset.html\",`<div class=\"salaxy-component salaxy-account-reset\">\r\n  <hr />\r\n  <h2>Vain testiympäristö</h2>\r\n  <p class=\"lead\">\r\n    Nämä toiminnallisuudet ovat näkyvissä vain testiympäristössä. Voit käyttää näitä toimintoja testataksesi työnantajan tiliä eri tiloissa.\r\n  </p>\r\n  <div class=\"table-responsive\">\r\n    <table class=\"table\">\r\n      <tr>\r\n        <td>Poista kaikki laskelmat.</td>\r\n        <td><button class=\"btn btn-danger btn-block\" ng-click=\"$ctrl.deleteCalculations()\">Poista laskelmat</button></td>\r\n      </tr>\r\n      <tr>\r\n        <td>Poista kaikki työntekijät. Tämä poistaa myös laskelmat, jos niitä on.</td>\r\n        <td><button class=\"btn btn-danger btn-block\" ng-click=\"$ctrl.deleteWorkers()\">Poista työntekijät</button></td>\r\n      </tr>\r\n      <tr>\r\n        <td>Poista loma- ja poissaolokirjanpito kaikilta työntekijöiltä.</td>\r\n        <td><button class=\"btn btn-danger btn-block\" ng-click=\"$ctrl.deleteHolidays()\">Poista lomat ja poissaolot</button></td>\r\n      </tr>\r\n      <tr>\r\n        <td>Poista kaikki data: Laskelmien ja työntekijöiden lisäksi myös mahd. työsopimukset, raportit jne. Asetukset ja allekirjoitus pysyvät ennallaan.</td>\r\n        <td><button class=\"btn btn-danger btn-block\" ng-click=\"$ctrl.deleteData()\">Poista kaikki data</button></td>\r\n      </tr>\r\n      <tr>\r\n        <td>Poista TyEL ja Tapavak: Käyttäjällä on puutteita palkanmaksun asetuksissa.</td>\r\n        <td><button class=\"btn btn-danger btn-block\" ng-click=\"$ctrl.deletePensionAndInsurance()\">Poista TyEL ja Tapavak</button></td>\r\n      </tr>\r\n      <tr>\r\n        <td>Poista Allekirjoitus: Käyttäjä keskeyttänyt Onboarding-wizardin ennen digitaalista allekirjoitusta.</td>\r\n        <td><button class=\"btn btn-danger btn-block\" ng-click=\"$ctrl.deleteSignature()\">Poista Allekirjoitus</button></td>\r\n      </tr>\r\n      <tr>\r\n        <td>Poista luodut tilit. Tämän tilin luomat uudet tilit, joilla ei ole maksettuja laskelmia tai allekirjoituksia, poistetaan.</td>\r\n        <td><button class=\"btn btn-danger btn-block\" ng-click=\"$ctrl.deleteAuthorizingAccounts()\">Poista luodut tilit</button></td>\r\n      </tr>\r\n      <tr>\r\n        <td>Tuhoa tili: Tuhoa koko tili. Voit aloittaa Onboarding-prosessin alusta.</td>\r\n        <td><button class=\"btn btn-danger btn-block\" ng-click=\"$ctrl.deleteCurrent()\">Tuhoa tili</button></td>\r\n      </tr>\r\n      <tr>\r\n        <td>{{$ctrl.isKycMissing() ? 'Aktivoi tilin KYC' : 'Poista tilin KYC'}}</td>\r\n        <td>\r\n          <button ng-class=\"$ctrl.isKycMissing() ? 'btn-info' : 'btn-danger'\" class=\"btn btn-block\" ng-click=\"$ctrl.handleKyc()\">{{$ctrl.isKycMissing() ? 'Aktivoi KYC' : 'Poista KYC'}}</button>\r\n        </td>\r\n      </tr>\r\n    </table>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/test/SmokeTest.html\",`<div ng-switch=\"$ctrl.mode\">\r\n  <fieldset ng-switch-when=\"reports\">\r\n    <legend><code>@salaxy/reports</code> functionality</legend>\r\n    <p>\r\n      Library loaded:\r\n      <span class=\"label\" ng-class=\"$ctrl.reportsTests.loaded ? 'label-success' : 'label-danger'\">{{ $ctrl.reportsTests.loaded ? \"OK\" : \"ERROR\" }}</span>\r\n    </p>\r\n    <p>\r\n      Basic functionality:\r\n      <span class=\"label\" ng-class=\"$ctrl.reportsTests.mapper ? 'label-success' : 'label-danger'\">{{ $ctrl.reportsTests.mapper ? \"OK\" : \"ERROR\" }}</span>\r\n    </p>\r\n    <p>\r\n      Report templates <small>(Handlebars)</small>:\r\n      <span class=\"label\" ng-class=\"$ctrl.reportsTests.handlebars ? 'label-success' : 'label-danger'\">{{ $ctrl.reportsTests.handlebars ? \"OK\" : \"ERROR\" }}</span>\r\n    </p>\r\n  </fieldset>\r\n  <fieldset ng-switch-default>\r\n    <legend><code>@salaxy/core</code> functionality</legend>\r\n    <p>\r\n      Basic functionality:\r\n      <span class=\"label\" ng-class=\"$ctrl.getNumber() ? 'label-success' : 'label-danger'\">{{ $ctrl.getNumber() ? \"OK\" : \"ERROR\" }}</span>\r\n    </p>\r\n    <p>\r\n      Dates <small>(MomentJS loaded)</small>:\r\n      <span class=\"label\" ng-class=\"$ctrl.getADate() == '20.02.2020' ? 'label-success' : 'label-danger'\">\r\n        {{ $ctrl.getADate() == '20.02.2020' ? \"OK\" : \"ERROR\" }}</span>\r\n    </p>\r\n    <p>\r\n      Token <small>(Base64)</small>:\r\n      <span class=\"label\" ng-class=\"$ctrl.readToken() ? 'label-success' : 'label-danger'\">{{ $ctrl.readToken() ? \"OK\" : \"ERROR\" }}</span>\r\n    </p>\r\n    <p>\r\n      Text from json: {{ $ctrl.getJson() }}\r\n      <span class=\"label\" ng-class=\"$ctrl.getJson() == 'This text is in json' ? 'label-success' : 'label-danger'\">{{ $ctrl.getJson() == 'This text is in json' ? \"OK\" : \"ERROR\" }}</span>\r\n    </p>\r\n  </fieldset>\r\n  <fieldset ng-switch-when=\"ng1\">\r\n    <legend><code>@salaxy/ng1</code> functionality</legend>\r\n    <p>\r\n      Library loaded:\r\n      <span class=\"label\" ng-class=\"$ctrl.sessionSrv ? 'label-success' : 'label-danger'\">{{ $ctrl.sessionSrv ? \"OK\" : \"ERROR\" }}</span>\r\n    </p>\r\n    <p>\r\n      Basic functionality:\r\n      <span class=\"label\" ng-class=\"$ctrl.sessionSrv.isInSomeRole('auth,anon,init') ? 'label-success' : 'label-danger'\">{{ $ctrl.sessionSrv.isInSomeRole('auth,anon,init') ? \"OK\" : \"ERROR\" }}</span>\r\n    </p>\r\n    <div>\r\n      <p>Component with template: You should see a drop-down menu with insurance companies below.</p>\r\n      <salaxy-input-enum enum=\"InsuranceCompany\" name=\"InsuranceCompany\" label=\"SALAXY.NG1.ProductDialogsComponent.company\" ng-model=\"$ctrl.temp.insuranceCompany\"></salaxy-input-enum>\r\n    </div>\r\n  </fieldset>\r\n  <fieldset ng-switch-when=\"ng1\">\r\n    <legend><code>@salaxy/ng1</code> AngularJS Modules</legend>\r\n    <div>\r\n      <b>angular-i18n (angular-locale_fi):</b><br /> The following sums should have the same euro currency format: {{ 1234 | currency }} == 1 234,00€<br /> Date should be in Finnish format: 20.12.2021 == {{ \"2021-12-20\" | date }}\r\n    </div>\r\n    <div>\r\n      <b>angular-route:</b>\r\n      <span class=\"label label-warning\">TODO</span>\r\n    </div>\r\n    <div>\r\n      <b>angular-sanitize:</b>\r\n      <div sxy-html=\"&lt;span class='label label-success'&gt;This text should be in GREEN background&lt;/span&gt;\"></div>\r\n    </div>\r\n    <div>\r\n      <b>angular-translate:</b><br />\r\n      <p>This text should be \"Kyllä\" / \"Yes\": <strong sxy-text=\"SALAXY.UI_Terms.yes\">ERROR</strong> <small>(ng1)</small></p>\r\n      <p>This text should be \"OK\": <strong sxy-text=\"SALAXY.UI_Terms.ok\">ERROR</strong> <small>(core)</small></p>\r\n    </div>\r\n    <div>\r\n      <b>angular-ui-bootstrap:</b> You should see a progress bar below:<br />\r\n      <div class=\"progress\">\r\n        <div class=\"progress-bar-striped bg-danger\" role=\"progressbar\" style=\"width: 83%\">83 %</div>\r\n      </div>\r\n    </div>\r\n    <!-- <div>\r\n      <b>Chart <small>Chart.js, angular-chart.js and chartjs-plugin-annotation</small>:</b> You should see a chart below with annotation.\r\n      <div class=\"salaxy-tax-card-chart chart-container\">\r\n        <canvas id=\"line\" class=\"chart chart-line\" chart-data=\"$ctrl.chartData.data\" chart-dataset-override=\"$ctrl.chartData.datasets\" chart-labels=\"$ctrl.chartData.labels\" chart-fill=\"$ctrl.chartData.fill\" chart-colors=\"$ctrl.chartData.colors\" chart-options=\"$ctrl.chartData.options\"></canvas>\r\n      </div>\r\n    </div> -->\r\n    <div>\r\n      <b>ng-file-upload:</b><br />\r\n      <button type=\"button\" class=\"btn btn-default\" ngf-select=\"upload($file)\">Click me to show Upload dialog</button> (Open/Cancel does nothing)\r\n    </div>\r\n    <hr />\r\n    <legend><code>@salaxy/ng1</code> Imported Modules</legend>\r\n    <div>\r\n      <b>file-saver:</b>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.saveAs()\">Click me to download a text file.</button>\r\n    </div>\r\n    <div>\r\n      <b>jszip:</b>\r\n      <span class=\"label label-warning\">TODO</span>\r\n    </div>\r\n    <div>\r\n      <b>marked: The following text should be formatted:</b>\r\n      <div ng-bind-html=\"'_italic_, **bold**, 'monospace', ~~strikethrough~~, [link](http://example.com)' | sxyMarkdown\"></div>\r\n    </div>\r\n    <div>\r\n      <b>rrule:</b>\r\n      <span class=\"label label-warning\">TODO</span>\r\n    </div>\r\n    <hr />\r\n    <legend>Removed</legend>\r\n    <p>The following dependencies have been dropped from this version:</p>\r\n    <ul>\r\n      <li>Babel (was in core): Babel was obsolete and we can target 2015. If necesssary, consider https://github.com/ryanelian/ts-polyfill or https://polyfill.io/v3/url-builder/ instead of js-core 3 (it has advertising issues).</li>\r\n      <li>js-base64: Moved from NG1 to Core (so not really removed)</li>\r\n      <li>angular-i18n: Not currently in use. Contains angular locales, e.g. </li>\r\n      <li>angular-animate: Removed as not used. Search for \"ngAnimate\" in projects.</li>\r\n      <li>angular-touch: Removed. Project marked as obsolete ages ago.</li>\r\n    </ul>\r\n  </fieldset>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/AbsencePeriods.html\",`<div class=\"salaxy-component salaxy-holiday-year-absences\">\r\n  <div ng-if=\"!$ctrl.list\" class=\"alert alert-info\">\r\n    <p sxy-text=\"SALAXY.NG1.AbsencePeriodsComponent.selectWorker\"></p>\r\n  </div>\r\n  <div ng-if=\"$ctrl.list && $ctrl.mode == 'calendar'\">\r\n    <salaxy-calendar data=\"$ctrl.parent\" on-list-select=\"$ctrl.calendarClick(type, date, calEvent)\"\r\n      start=\"$ctrl.filterStart\" end=\"$ctrl.filterEnd\" mapper=\"$ctrl.mapToCalendar\"></salaxy-calendar>\r\n    <div class=\"text-end\">\r\n      &nbsp;<br/>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showEditDialog('new')\" sxy-text=\"SALAXY.NG1.AbsencePeriodsComponent.addAbsenceButtonText\"></button>\r\n    </div>\r\n  </div>\r\n  <div ng-if=\"$ctrl.list && $ctrl.mode != 'calendar'\">\r\n    <table class=\"table table-striped {{ $ctrl.condensed ? 'table-sm' : '' }}\">\r\n      <thead>\r\n        <tr>\r\n          <th sxy-text=\"SALAXY.NG1.AbsencePeriodsComponent.headerAbsence\"></th>\r\n          <th class=\"right\" sxy-text=\"SALAXY.NG1.AbsencePeriodsComponent.headerDays\"></th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n        <tr ng-repeat=\"row in $ctrl.list | filter: $ctrl.filter\" ng-click=\"$ctrl.showEditDialog(row)\" class=\"clickable\">\r\n          <td>\r\n            <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" avatar=\"{ color: '#2b507c', initials: (row.period.daysCount + 'pv'), entityType: 'company' }\"></salaxy-avatar>\r\n            <strong>{{ \"AbsenceCauseCode.\" + row.causeCode | sxyEnum }}</strong><br />\r\n            <div class=\"float-start\" style=\"padding: 0px;\">\r\n              {{ row.isPaid ? ('SALAXY.NG1.AbsencePeriodsComponent.isPaid' | sxyTranslate) : ('SALAXY.NG1.AbsencePeriodsComponent.notPaid' |sxyTranslate) }}\r\n              <span ng-if=\"row.isPaid != row.isHolidayAccrual\"> {{ row.isHolidayAccrual ? ('SALAXY.NG1.AbsencePeriodsComponent.isAccrual' | sxyTranslate) : ('SALAXY.NG1.AbsencePeriodsComponent.notAccrual' | sxyTranslate) }}</span>\r\n            </div>\r\n            <div class=\"truncate\" style=\"max-width: 250px; padding: 0px;\">\r\n              &nbsp;{{ row.notes }}\r\n            </div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <strong>{{ row.period.daysCount | sxyCount : \"day\" }}</strong><br /> {{ row.period | sxyDateRange }}\r\n          </td>\r\n        </tr>\r\n        <tr ng-if=\"$ctrl.filteredList.length == 0\">\r\n          <td colspan=\"2\">\r\n            <h3 sxy-text=\"SALAXY.NG1.AbsencePeriodsComponent.noAbsences\"></h3>\r\n            <p sxy-text=\"SALAXY.NG1.AbsencePeriodsComponent.noAbsencesDescription\"></p>\r\n            <p sxy-text=\"SALAXY.NG1.AbsencePeriodsComponent.noAbsencesDescription2\"></p>\r\n          </td>\r\n        </tr>\r\n        <tr class=\"total\">\r\n          <td>\r\n            <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" style=\"margin-bottom: 20px\" avatar=\"{ color: '#2b507c', initials: 'sum', entityType: 'company' }\"></salaxy-avatar>\r\n            <strong>\r\n             <span sxy-text=\"SALAXY.NG1.AbsencePeriodsComponent.totalUnpaid\"></span><br />\r\n                         <span sxy-text=\"SALAXY.NG1.AbsencePeriodsComponent.totalNoHolidayAccrual\"></span><br />\r\n                           <span sxy-text=\"SALAXY.NG1.AbsencePeriodsComponent.totalAll\"></span><br />\r\n            </strong>\r\n          </td>\r\n          <td class=\"right\">\r\n            <strong>\r\n              {{ $ctrl.getTotalDays(\"absencesUnpaid\") | sxyCount : \"day\" }}<br />\r\n              {{ $ctrl.getTotalDays(\"absencesNoHolidayAccrual\") | sxyCount : \"day\" }}<br />\r\n              {{ $ctrl.getTotalDays(\"all\") | sxyCount : \"day\" }}<br />\r\n            </strong>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n    <div class=\"text-end\">\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showEditDialog('new')\" sxy-text=\"SALAXY.NG1.AbsencePeriodsComponent.addAbsenceButtonText\"></button>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/AbsencePeriodsEditDialog.html\",`  <div class=\"modal-header\">\r\n    <h1 class=\"modal-title\" sxy-text=\"SALAXY.NG1.AbsencePeriodsEditDialog.panelHeading\"></h1>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$dismiss()\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <form class=\"form-horizontal\" name=\"absencePeriodsForm\">\r\n      <salaxy-input-typeahead name=\"causeCode\" ng-model=\"$ctrl.current.causeCode\" enum=\"AbsenceCauseCode\" label=\"SALAXY.MODEL.WorkerAbsencePeriod.absencesId.title\" ng-change=\"$ctrl.logic.updateIsPaid($ctrl.current)\" require=\"true\" options=\"$ctrl.getCauseCodes()\"></salaxy-input-typeahead>\r\n      <salaxy-datepicker-popup name=\"start\" ng-model=\"$ctrl.current.period.start\" ng-change=\"$ctrl.logic.updatePeriodDays($ctrl.current)\" label=\"SALAXY.MODEL.DateRange.start.title\"></salaxy-datepicker-popup>\r\n      <salaxy-datepicker-popup name=\"end\" ng-model=\"$ctrl.current.period.end\" ng-change=\"$ctrl.logic.updatePeriodDays($ctrl.current)\" label=\"SALAXY.MODEL.DateRange.end.title\"></salaxy-datepicker-popup>\r\n      <salaxy-form-group name=\"daysCount\" label=\"SALAXY.MODEL.DateRange.daysCount.title\" ng-if=\"$ctrl.current.period.days == null\">\r\n        <div class=\"input-group\">\r\n          <input class=\"form-control\" type=\"text\" autocomplete=\"off\" id=\"daysCount\" name=\"daysCount\" ng-model=\"$ctrl.current.period.daysCount\" disabled>\r\n          <span class=\"input-group-btn\">\r\n            <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.logic.setDaysSelection($ctrl.current);\" sxy-text=\"SALAXY.NG1.AbsencePeriodsEditDialog.editDatesButtonText\"></button>\r\n          </span>\r\n        </div>\r\n      </salaxy-form-group>\r\n      <salaxy-datepicker ng-if=\"$ctrl.current.period.days != null\" name=\"days\" is-multiple=\"true\" ng-model=\"$ctrl.current.period\" label=\"SALAXY.MODEL.WorkerAbsencePeriod.period.title\" min-date=\"$ctrl.current.period.start\" max-date=\"$ctrl.current.period.end\"></salaxy-datepicker>\r\n      <salaxy-input-boolean type=\"checkbox\" name=\"isPaid\" label=\"SALAXY.MODEL.WorkerAbsencePeriod.isPaid.title\" label-true=\"SALAXY.NG1.AbsencePeriodsEditDialog.label.isPaidLabelTrue\" disabled=\"!$ctrl.logic.canSelectIsPaid($ctrl.current)\" ng-model=\"$ctrl.current.isPaid\"\r\n        ng-change=\"$ctrl.logic.updateIsHolidayAccrual($ctrl.current)\"></salaxy-input-boolean>\r\n      <salaxy-input-boolean type=\"checkbox\" name=\"isHolidayAccrual\" label=\"SALAXY.MODEL.WorkerAbsencePeriod.isHolidayAccrual.title\" label-true=\"SALAXY.NG1.AbsencePeriodsEditDialog.label.isAccrualLabelTrue\" ng-model=\"$ctrl.current.isHolidayAccrual\"></salaxy-input-boolean>\r\n    </form>\r\n  </div>\r\n  <div class=\"modal-footer\">\r\n    <button type=\"button\" class=\"btn btn-danger\" ng-click=\"$close('delete')\" sxy-text=\"SALAXY.NG1.AbsencePeriodsEditDialog.deleteButtonText\"></button>\r\n    <button type=\"reset\" class=\"btn btn-default ms-auto\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.NG1.AbsencePeriodsEditDialog.cancelButtonText\"></button>\r\n    <button type=\"submit\" ng-disabled=\"absencePeriodsForm.$invalid\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.ok\"></button>\r\n  </div>`);\n\n $templateCache.put(\"salaxy-components/worker/employment/Details.html\",`<ng-include src=\"'salaxy-components/worker/employment/Details_Header.html'\"></ng-include>\r\n<div ng-if=\"$ctrl.status == 'initialLoading'\">\r\n  <p sxy-text=\"SALAXY.UI_Terms.loading\"></p>\r\n</div>\r\n<div>\r\n  <salaxy-tab-buttons\r\n    ng-if=\"$ctrl.current\"\r\n    current-tab=\"$ctrl.currentTab\"\r\n    options=\"[\r\n      { value: 'default', text: 'SALAXY.NG1.WorkerDetailsComponent.workerInfo', isDefault: true },\r\n      { value: 'employment', text: 'SALAXY.NG1.WorkerDetailsComponent.employment' },\r\n      { value: 'calcrows', text: 'SALAXY.NG1.WorkerDetailsComponent.defaultCalcRows' },\r\n      { value: 'calculations', text: 'SALAXY.NG1.WorkerDetailsComponent.calculations' },\r\n      { value: 'taxcards', text: 'SALAXY.NG1.WorkerDetailsComponent.taxcards' },\r\n      { value: 'holidays', text: 'SALAXY.NG1.WorkerDetailsComponent.holidays', hidden: ('disableHolidays' | sxyIsInRole) },\r\n      { value: 'absences', text: 'SALAXY.NG1.WorkerDetailsComponent.absences', hidden: ('disableHolidays' | sxyIsInRole) },\r\n      { value: 'records', text: 'SALAXY.NG1.WorkerDetailsComponent.records.label', hidden: $ctrl.isModal && isHousehold },\r\n      { value: 'debugger', text: 'DEBUG', hidden: !('disabled-test' | sxyIsInRole) }\r\n    ]\"\r\n    tabs-id=\"employmentDetails\">\r\n  </salaxy-tab-buttons>\r\n  <div class=\"tab-content\" id=\"tab-content-employmentDetails\">\r\n    <div class=\"tab-pane\" id=\"default-tab\">\r\n      <ng-include src=\"'salaxy-components/worker/employment/Details_Basic.html'\" ng-if=\"$ctrl.currentTab == 'default'\"></ng-include>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"employment-tab\">\r\n      <ng-include src=\"'salaxy-components/worker/employment/Details_EmploymentRelation.html'\" ng-if=\"$ctrl.currentTab == 'employment'\"></ng-include>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"calcrows-tab\">\r\n      <ng-include src=\"'salaxy-components/worker/employment/Details_Calc.html'\" ng-if=\"$ctrl.currentTab == 'calcrows'\"></ng-include>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"calculations-tab\">\r\n      <salaxy-odata-table ng-if=\"$ctrl.current.personalInfo\" read-only=\"$ctrl.isReadOnlyForced\" crud-controller=\"CalculationCrudController as $crud\"\r\n        options=\"{ $filter: 'otherPartyInfo/officialId eq \\\\'' + $ctrl.current.personalInfo.officialId + '\\\\' and ( status ne \\\\'proDraft\\\\' and status ne \\\\'payrollDraft\\\\')' }\"\r\n        template-url=\"salaxy-components/odata/lists/CalculationsWorker.html\" logic=\"$ctrl.calcListLogic\" ng-if=\"$ctrl.currentTab == 'calculations'\">\r\n      </salaxy-odata-table>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"taxcards-tab\">\r\n      <ng-include src=\"'salaxy-components/worker/employment/Details_Tax.html'\" ng-if=\"$ctrl.currentTab == 'taxcards'\"></ng-include>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"holidays-tab\">\r\n      <salaxy-worker-holidays employment-id=\"$ctrl.current.id\" ng-if=\"$ctrl.currentTab == 'holidays'\"></salaxy-worker-holidays>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"absences-tab\">\r\n      <salaxy-worker-absences employment-id=\"$ctrl.current.id\" ng-if=\"$ctrl.currentTab == 'absences'\"></salaxy-worker-absences>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"records-tab\">\r\n      <salaxy-records read-only=\"$ctrl.isReadOnlyForced\" api-ctrl=\"$ctrl\" entity-type=\"'employment'\" ng-if=\"$ctrl.current && (!$ctrl.isModal || !isHousehold) && $ctrl.currentTab == 'records'\"></salaxy-records>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"debugger-tab\">\r\n      <div ng-if=\"('disabled-test' | sxyIsInRole) && $ctrl.currentTab == 'debugger'\">\r\n        <p><a ng-href=\"{{'#/workers/details/' + $ctrl.current.info.workerAccountId}}\">Old version (Worker ID {{ $ctrl.current.info.workerAccountId }})</a></p>\r\n        <salaxy-json-formatter json=\"$ctrl.current\" open=\"1\" key=\"'Employment'\"></salaxy-json-formatter>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>\r\n`);\n\n $templateCache.put(\"salaxy-components/worker/employment/Details_Accruals.html\",`<div ng-if=\"$ctrl.current\">\r\n  <sxy-form open-api=\"salaxy-secure/schemas/v02.json\" type=\"Employment\" auto-gen=\"false\" debugger=\"false\" model=\"$ctrl.current\">\r\n    <div>\r\n      <fieldset>\r\n        <legend><span sxy-text=\"SALAXY.MODEL.Employment.accruals.title\"></span></legend>\r\n        <sxy-input model=\"form.accruals\" include=\"type,startDate,endDate,amount,unit\">\r\n          <form>\r\n             <fieldset>\r\n                <legend sxy-text=\"SALAXY.MODEL.EmploymentAccrual.title\"></legend>\r\n                <sxy-input require=\"true\" model=\"form.type\"></sxy-input>\r\n                <sxy-input model=\"form.startDate\"></sxy-input>\r\n                <sxy-input model=\"form.endDate\"></sxy-input>\r\n                <sxy-input format=\"undefined\" model=\"form.amount\"></sxy-input>\r\n                <sxy-input model=\"form.unit\"></sxy-input>\r\n            </fieldset>\r\n          </form>\r\n        </sxy-input>\r\n      </fieldset>\r\n    </div>\r\n  </sxy-form>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/employment/Details_Basic.html\",`<div class=\"salaxy-component salaxy-worker-employment\">\r\n  <form name=\"basicForm\" class=\"form-horizontal\" ng-readonly=\"$ctrl.isReadOnlyForced\">\r\n    <div class=\"row\">\r\n      <div class=\"col-md-6\">\r\n        <fieldset ng-if=\"$ctrl.isNew()\">\r\n          <legend sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.details\"></legend>\r\n          <salaxy-input name=\"firstName\" label=\"SALAXY.NG1.WorkerDetailsComponent.firstName\" ng-required=\"true\" ng-model=\"$ctrl.current.identity.firstName\"></salaxy-input>\r\n          <salaxy-input name=\"lastName\" label=\"SALAXY.NG1.WorkerDetailsComponent.lastName\" ng-required=\"true\" ng-model=\"$ctrl.current.identity.lastName\"></salaxy-input>\r\n          <salaxy-input name=\"officialPersonId\" label=\"SALAXY.NG1.WorkerDetailsComponent.ssNumber\" sxy-personal-id-fi ng-required=\"true\" ng-model=\"$ctrl.current.identity.personalId\"></salaxy-input>\r\n          <salaxy-input-enum enum=\"Language\" ng-model=\"$ctrl.current.identity.language\" name=\"workerLanguage\" label=\"SALAXY.NG1.WorkerDetailsComponent.language\"></salaxy-input-enum>\r\n        </fieldset>\r\n        <fieldset ng-if=\"!$ctrl.isNew()\">\r\n          <legend sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.details\"></legend>\r\n          <salaxy-input read-only=\"$ctrl.current.isRegistered ? true : undefined\" name=\"firstName\" label=\"SALAXY.NG1.WorkerDetailsComponent.firstName\" ng-required=\"true\" ng-model=\"$ctrl.current.identity.firstName\"></salaxy-input>\r\n          <salaxy-input read-only=\"$ctrl.current.isRegistered ? true : undefined\" name=\"lastName\" label=\"SALAXY.NG1.WorkerDetailsComponent.lastName\" ng-required=\"true\" ng-model=\"$ctrl.current.identity.lastName\"></salaxy-input>\r\n          <salaxy-input name=\"officialPersonId\" label=\"SALAXY.NG1.WorkerDetailsComponent.ssNumber\" sxy-personal-id-fi read-only=\"true\" ng-required=\"true\" ng-model=\"$ctrl.current.identity.personalId\"></salaxy-input>\r\n          <salaxy-form-group ng-if=\"'workers.employments.employmentId' | sxyShow: 'workers.index'\" label=\"SALAXY.NG1.WorkerDetailsComponent.workerId\" name=\"workerId\">\r\n            <div class=\"salaxy-read-only-value\">\r\n              <small ng-if=\"!$ctrl.current.isRegistered\">{{ $ctrl.current.info.workerAccountId | sxyIban }}</small>\r\n              <code ng-if=\"$ctrl.current.isRegistered\">{{ $ctrl.current.info.workerAccountId | sxyIban }}</code><br/>\r\n              <small>({{ $ctrl.current.isRegistered ? \"Rekisteröitynyt, pysyvä ID\" : \"Ei rekisteröitynyt, tilapäinen ID\" }})</small>\r\n            </div>\r\n          </salaxy-form-group>\r\n          <salaxy-input-enum enum=\"Language\" ng-model=\"$ctrl.current.identity.language\" read-only=\"$ctrl.current.isRegistered\" name=\"workerLanguage\" label=\"SALAXY.NG1.WorkerDetailsComponent.language\"></salaxy-input-enum>\r\n        </fieldset>\r\n        <fieldset>\r\n          <legend sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.paymentDetails\"></legend>\r\n          <salaxy-input-enum ng-if=\"!('hideSalaryPaymentMethod' | sxyIsInRole)\" label=\"SALAXY.NG1.WorkerDetailsComponent.salaryPaymentMethod\" name=\"employmentRelationSalaryPaymentMethod\" ng-model=\"$ctrl.current.info.salaryPaymentMethod\" enum=\"EmploymentRelationSalaryPaymentMethod\" required placeholder=\"SALAXY.UI_Terms.selectAlt\"></salaxy-input-enum>\r\n          <salaxy-input ng-if=\"$ctrl.current.info.salaryPaymentMethod === 'bankAccount'\" name=\"ibanNumber\" label=\"SALAXY.NG1.WorkerDetailsComponent.ibanNumber\" sxy-iban\r\n            require=\"$ctrl.isRequired('ibanNumber')\" ng-model=\"$ctrl.current.info.ibanNumber\" tooltip-html=\"{{ $ctrl.getInputTooltip('ibanNumber') }}\"></salaxy-input>\r\n        </fieldset>\r\n      </div>\r\n      <div class=\"col-md-6\">\r\n        <fieldset>\r\n          <legend sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.contactInfo\"></legend>\r\n          <salaxy-input name=\"email\" label=\"SALAXY.NG1.WorkerDetailsComponent.email\" sxy-email ng-model=\"$ctrl.getContact().email\" tooltip-html=\"{{ $ctrl.getInputTooltip('email') }}\"></salaxy-input>\r\n          <salaxy-input name=\"telephone\" label=\"SALAXY.NG1.WorkerDetailsComponent.tel\" sxy-mobile-phone ng-model=\"$ctrl.getContact().telephone\" tooltip-html=\"{{ $ctrl.getInputTooltip('telephone') }}\"></salaxy-input>\r\n        </fieldset>\r\n        <fieldset>\r\n          <legend sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.address\"></legend>\r\n          <p ng-if=\"!$ctrl.isOtherIdentifier\" sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.addressInfo\"></p>\r\n          <p ng-if=\"$ctrl.isOtherIdentifier\" sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.addressInfoOtherIdentifier\"></p>\r\n          <salaxy-input name=\"street\" label=\"SALAXY.NG1.WorkerDetailsComponent.street\" require=\"$ctrl.isRequired('street')\" ng-model=\"$ctrl.getContact().street\" tooltip-html=\"{{ $ctrl.getInputTooltip('street') }}\">\r\n          </salaxy-input>\r\n          <salaxy-input name=\"postalCode\" label=\"SALAXY.NG1.WorkerDetailsComponent.postalCode\" require=\"$ctrl.isRequired('postalCode')\" ng-model=\"$ctrl.getContact().postalCode\" tooltip-html=\"{{ $ctrl.getInputTooltip('postalCode') }}\">\r\n          </salaxy-input>\r\n          <salaxy-input name=\"city\" label=\"SALAXY.NG1.WorkerDetailsComponent.city\" require=\"$ctrl.isRequired('city')\" ng-model=\"$ctrl.getContact().city\" tooltip-html=\"{{ $ctrl.getInputTooltip('city') }}\">\r\n          </salaxy-input>\r\n        </fieldset>\r\n      </div>\r\n    </div>\r\n    <div ng-if=\"!$ctrl.isModal\">\r\n      <button ng-click=\"$ctrl.deleteEmployment()\" type=\"button\" class=\"btn btn-danger\" sxy-text=\"SALAXY.UI_Terms.delete\"></button>\r\n      <button ng-click=\"$ctrl.save()\" ng-disabled=\"basicForm.$invalid\" class=\"btn btn-primary float-end\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n    </div>\r\n  </form>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/employment/Details_Calc.html\",`<div>\r\n  <div class=\"float-end\" ng-if=\"!$ctrl.isModal\">\r\n    <salaxy-json-formatter key=\"'Debug'\" sxy-if-role=\"test\" json=\"$ctrl.current.work.salaryDefaults\" open=\"1\" type=\"dialog\"></salaxy-json-formatter>\r\n    <button ng-click=\"$ctrl.save()\" ng-disabled=\"workerForm.$invalid\" class=\"btn btn-primary\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n  </div>\r\n  <p>Oletuspalkkarivit kopioidaan uudelle laskelmalle sellaisenaan. Päivämäärärajaukset huomioidaan vain tuntien sisääntuonnissa.</p>  \r\n  <salaxy-calc-rows-editor rows=\"$ctrl.current.work.salaryDefaults\" row-sources=\"thisproperty will be removed, just a marker until refactoring\"\r\n    title=\"{{ 'SALAXY.NG1.WorkerDetailsComponent.defaultCalcRows' | sxyTranslate }}\" type=\"salary-defaults-temp2\" mode=\"{{ $ctrl.isReadOnlyForced ? 'read-only' : 'edit'}}\"></salaxy-calc-rows-editor>\r\n  <hr>\r\n  <p>\r\n    Hintoja käytetään tällä hetkellä tuntien sisään tuonnissa. Myöhemmissä versioissa oletushintoja käytetään myös laskurissa.<br>\r\n    <span ng-if=\"'bizConfigs' | sxyIsInRole\">Jos hintoihin lasketaan keskituntiansioita, voit käyttää erillistä <a ng-href=\"#/reports/pay-stats-report-query/{{$ctrl.current.id}}\">ansioiden laskentaraporttia</a> tulosten tarkasteluun.</span>\r\n    <span ng-if=\"'bizConfigs' | sxyIsInRole\"><br>Jos haluat laskea uudelleen ja päivittää tälle työsuhteelle keskituntiansiot, voit käynnistää laskennan oheisesta painikkeesta. <button class=\"btn btn-xs btn-default\" ng-click=\"$ctrl.recalculatePayStats()\">Laske keskituntiansiot tälle työsuhteelle</button></span>\r\n    <span ng-if=\"'bizConfigs' | sxyIsInRole\"><br>Jos haluat laskea uudelleen ja päivittää kaikille työsuhteille keskituntiansiot, voit käynnistää laskennan oheisesta painikkeesta. <button class=\"btn btn-xs btn-danger\" ng-click=\"$ctrl.recalculateAllPayStats()\">Laske keskituntiansiot kaikille työsuhteille</button></span>\r\n  </p>\r\n  <salaxy-row-types-settings ng-ref=\"$ctrl.$prices\" mode=\"prices\" model=\"$ctrl.current\"></salaxy-row-types-settings>\r\n</div>\r\n\r\n<p>&nbsp;</p>\r\n\r\n<div class=\"row form-horizontal\" ng-if=\"!$ctrl.isHousehold && ('employments.defaultCalcRows.features' | sxyShow: 'workers.details')\">\r\n  <div class=\"col-sm-6\">\r\n    <fieldset>\r\n      <legend sxy-text=\"SALAXY.NG1.WorkerDetailsCalc.payrollDetails\"></legend>\r\n      <salaxy-input-enum label=\"SALAXY.NG1.WorkerDetailsCalc.wageBasis\" name=\"wageBases\" ng-model=\"$ctrl.current.work.wageBasis\" enum=\"WageBasis\" type=\"select\" read-only=\"$ctrl.isReadOnlyForced\"></salaxy-input-enum>\r\n      <salaxy-input-number label=\"SALAXY.NG1.WorkerDetailsCalc.monthlyHours\" name=\"monthlyHours\" unit=\"hour\" ng-model=\"$ctrl.current.work.monthlyHours\" read-only=\"$ctrl.isReadOnlyForced\"></salaxy-input-number>\r\n      <salaxy-input-enum label=\"SALAXY.NG1.WorkerDetailsCalc.irIncomeEarnerTypes\" label-type=\"basic\" name=\"wageBases\" ng-model=\"$ctrl.current.info.irIncomeEarnerTypes\" enum=\"IncomeEarnerType\" type=\"multi-select\" read-only=\"$ctrl.isReadOnlyForced\"></salaxy-input-enum>\r\n    </fieldset>\r\n  </div>\r\n  <div class=\"col-sm-6\">\r\n    <fieldset>\r\n      <legend sxy-text=\"SALAXY.NG1.WorkerDetailsCalc.integrations\"></legend>\r\n      <salaxy-input label=\"SALAXY.NG1.WorkerDetailsCalc.ssNumber\" name=\"sourceId\" ng-model=\"$ctrl.current.info.sourceId\" read-only=\"$ctrl.isReadOnlyForced\"></salaxy-input>\r\n    </fieldset>\r\n    <salaxy-cost-accounting read-only=\"$ctrl.isReadOnlyForced\" ng-init=\"$ctrl.current.work.accounting = $ctrl.current.work.accounting ? $ctrl.current.work.accounting : { dimensions: []}\" current=\"$ctrl.current.work.accounting.dimensions\"\r\n      scope=\"calculation\"></salaxy-cost-accounting>\r\n  </div>\r\n  <div class=\"col-sm-6\" ng-if=\"'bizConfigs' | sxyIsInRole\">\r\n    <ng-include src=\"'salaxy-components/worker/employment/Details_Configs.html'\"></ng-include>\r\n  </div>\r\n  <div class=\"col-sm-6\" ng-if=\"'bizConfigs' | sxyIsInRole\">\r\n    <ng-include src=\"'salaxy-components/worker/employment/Details_Accruals.html'\"></ng-include>\r\n  </div>\r\n</div>\r\n<div class=\"text-end\" ng-if=\"!$ctrl.isModal\">\r\n  <button ng-click=\"$ctrl.save()\" ng-disabled=\"workerForm.$invalid\" class=\"btn btn-primary\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/employment/Details_Configs.html\",`<div ng-if=\"$ctrl.current\">\r\n  <sxy-form open-api=\"salaxy-secure/schemas/v02.json\" type=\"Employment\" auto-gen=\"false\" debugger=\"false\" model=\"$ctrl.current\">\r\n    <div>\r\n      <fieldset>\r\n        <legend><span sxy-text=\"SALAXY.MODEL.Employment.configs.title\"></span></legend>\r\n        <sxy-input model=\"form.configs\" include=\"name,data,priority\">\r\n          <form>\r\n             <fieldset>\r\n                <legend sxy-text=\"SALAXY.MODEL.BizConfig.title\"></legend>\r\n                <sxy-input require=\"true\" model=\"form.name\"></sxy-input>\r\n                <salaxy-input-collective-bargain-agreement name=\"cbaCode\" ng-model=\"$ctrl.current.cbaCode\" label=\"SALAXY.MODEL.BizConfig.cbaCode.title\"></salaxy-input-collective-bargain-agreement>\r\n                <salaxy-input-employee-group name=\"employeeGroup\" ng-model=\"$ctrl.current.employeeGroup\" label=\"SALAXY.MODEL.BizConfig.employeeGroup.title\"></salaxy-input-employee-group>\r\n                <sxy-input model=\"form.disabled\"></sxy-input>\r\n                <sxy-input model=\"form.startDate\"></sxy-input>\r\n                <sxy-input model=\"form.endDate\"></sxy-input>\r\n                <salaxy-input-enum ng-model=\"$ctrl.current.dataType\" name=\"dataType\" label=\"SALAXY.MODEL.BizConfig.dataType.title\" options=\"{\r\n                      'string': 'Teksti',\r\n                      'number': 'Luku',\r\n                      'boolean': 'Kyllä/Ei'\r\n                     }\"></salaxy-input-enum>\r\n                <salaxy-input ng-show=\"!$ctrl.current.dataType || $ctrl.current.dataType === 'string'\" ng-model=\"$ctrl.current.data\" name=\"dataString\" label=\"SALAXY.MODEL.BizConfig.data.title\"></salaxy-input>\r\n                <salaxy-input-number ng-show=\"$ctrl.current.dataType == 'number'\" ng-model=\"$ctrl.current.data\"  name=\"dataNumber\" label=\"SALAXY.MODEL.BizConfig.data.title\"></salaxy-input-number>\r\n                <salaxy-input-boolean ng-show=\"$ctrl.current.dataType == 'boolean'\" ng-model=\"$ctrl.current.data\" name=\"dataBoolean\" label=\"SALAXY.MODEL.BizConfig.data.title\"></salaxy-input-boolean>       \r\n                <sxy-input model=\"form.updatedAt\" read-only=\"true\"></sxy-input>\r\n                <sxy-input model=\"form.updatedBy\" read-only=\"true\"></sxy-input>\r\n            </fieldset>\r\n          </form>\r\n        </sxy-input>\r\n      </fieldset>\r\n    </div>\r\n  </sxy-form>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/employment/Details_EmploymentRelation.html\",`﻿<div class=\"salaxy-component salaxy-worker-employment\">\r\n  <ng-form name=\"$ctrl.employmentForm\" class=\"form-horizontal\" ng-readonly=\"$ctrl.isReadOnlyForced\">\r\n    <ng-include src=\"'salaxy-components/worker/employment/shared-EmploymentRelation.html'\"></ng-include>\r\n    <div class=\"text-end\" ng-if=\"!$ctrl.isModal\">\r\n      <button ng-click=\"$ctrl.save()\" class=\"btn btn-primary\" ng-disabled=\"$ctrl.employmentForm.$invalid\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n    </div>\r\n  </ng-form>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/employment/Details_Header.html\",`<div class=\"salaxy-calc-worker-info\">\r\n  <div ng-if=\"$ctrl.status == 'initialLoading'\">\r\n    <div class=\"col-3 col-sm-2\">\r\n      <salaxy-spinner></salaxy-spinner>\r\n    </div>\r\n    <div class=\"col-9 col-sm-10 worker-info-col\">\r\n      <h2 sxy-text=\"SALAXY.UI_Terms.loading\"></h2>\r\n      <div class=\"row\">\r\n        <div class=\"col-12 col-sm-6\">\r\n          &nbsp;<br /> &nbsp;\r\n          <br /> &nbsp;\r\n        </div>\r\n        <div class=\"col-12 col-sm-6\">\r\n          &nbsp;<br />\r\n          <div>&nbsp;</div>\r\n          <div>&nbsp;</div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n  <div class=\"row\" ng-if=\"$ctrl.status !== 'initialLoading'\">\r\n    <div class=\"col-3 col-md-2 align-items-center justify-content-center d-flex\">\r\n      <salaxy-avatar avatar=\"$ctrl.current.personalInfo.avatar\"></salaxy-avatar>\r\n    </div>\r\n    <div class=\"col-9 col-md-10 worker-info-col\">\r\n      <div class=\"d-flex justify-content-between\">\r\n        <h2>{{ $ctrl.current.personalInfo.avatar.displayName || (\"SALAXY.NG1.WorkerInfo.noSelection\" | sxyTranslate) }}</h2>\r\n        <salaxy-action-button label=\"SALAXY.NG1.WorkerDetailsComponent.newCalculation\" action=\"'newCalcForEmployment'\" ng-if=\"!$ctrl.isModal\" options=\"{'id': $ctrl.currentId }\" button-class=\"btn-default float-start float-sm-end\"></salaxy-action-button>\r\n      </div>\r\n      <div class=\"row\" ng-if=\"$ctrl.current\">\r\n        <div class=\"col-12 col-md-6\">\r\n          <div ng-class=\"$ctrl.current.personalInfo.officialId ? '' : 'text-danger'\">\r\n            {{ $ctrl.current.personalInfo.officialId || ( \"SALAXY.NG1.PaymentDialogComponent.noSSNumber\" | sxyTranslate ) }}\r\n            &nbsp;\r\n            <div class=\"btn-group dropdown\" ng-if=\"$ctrl.otherEmployments.length > 0\">\r\n              <button id=\"single-button\" type=\"button\" class=\"btn btn-default btn-xs dropdown-toggle\" data-bs-toggle=\"dropdown\">\r\n                {{ $ctrl.otherEmployments.length }} muuta työsuhdetta\r\n              </button>\r\n              <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"single-button\">\r\n                <li role=\"menuitem\" ng-repeat=\"item in $ctrl.otherEmployments\">\r\n                  <a ng-href=\"{{$ctrl.isModal ? '' : ('#/employments/details/' + item.id)}}\" class=\"dropdown-item\">\r\n                    {{ $ctrl.getEmploymentDescription(item) }}\r\n                    ({{ $ctrl.getActiveText(item) }})\r\n                  </a>\r\n                </li>\r\n              </ul>\r\n            </div>\r\n            <span ng-if=\"!$ctrl.otherEmployments\">Tarkistetaan muita työsuhteita...</span>\r\n          </div>\r\n          <div>{{ $ctrl.getEmploymentDescription($ctrl.current) }}</div>\r\n          <div>{{ $ctrl.getActiveText($ctrl.current) }}</div>\r\n          <div><small>{{ $ctrl.current.id }}</small></div>\r\n        </div>\r\n        <div class=\"col-12 col-md-6 \">\r\n          \r\n          <div ng-if=\"$ctrl.readOnlyDefaultContact.email\">\r\n            <a href=\"{{ 'mailto:' + $ctrl.readOnlyDefaultContact.email }}\">{{ $ctrl.readOnlyDefaultContact.email }}</a>\r\n          </div>\r\n          <div ng-if=\"!$ctrl.readOnlyDefaultContact.email\">\r\n            <span sxy-text=\"SALAXY.NG1.PaymentDialogComponent.noEmail\"></span>\r\n            <span class=\"text-warning\" sxy-text=\"SALAXY.NG1.PaymentDialogComponent.noEmailInfo\"></span>\r\n          </div>\r\n          <div ng-if=\"!$ctrl.current.info.ibanNumber\" class=\"text-danger\" sxy-text=\"SALAXY.NG1.WorkerInfo.noIbanNumber\"></div>\r\n          <div ng-if=\"$ctrl.current.info.ibanNumber\">IBAN: {{ $ctrl.current.info.ibanNumber | sxyIban }}</div>\r\n          <div ng-class=\"{ 'text-danger': $ctrl.getTaxCardInfo().isMissing }\">\r\n            {{ $ctrl.getTaxCardInfo().text }}</div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/employment/Details_Tax.html\",`<form name=\"employmentTaxcardForm\" class=\"form-horizontal\" ng-readonly=\"$ctrl.isReadOnlyForced\">\r\n  <salaxy-input-enum label=\"SALAXY.NG1.WorkerDetailsComponent.employmentTaxcard\" name=\"employmentTaxcard\" ng-model=\"$ctrl.taxcardType\"\r\n    enum=\"EmploymentRelationTaxcard\" label-cols=\"col-sm-5\"></salaxy-input-enum>\r\n</form>\r\n<div ng-switch=\"$ctrl.current.info.taxcard\">\r\n  <div ng-switch-when=\"taxAtSource\">\r\n    <fieldset>\r\n      <legend>{{'SALAXY.NG1.EmploymentDetails.taxAtSource.title' | sxyTranslate}}</legend>\r\n      <div class=\"alert alert-danger\" ng-if=\"!$ctrl.socSec.isInternational\" sxy-html=\"SALAXY.NG1.EmploymentDetails.taxAtSource.info.html\"></div>\r\n      <salaxy-input-number name=\"percent\" unit=\"percent\" minimum=\"0\" maximum=\"100\" label=\"SALAXY.NG1.EmploymentDetails.percent\" label-cols=\"col-sm-8\" ng-model=\"$ctrl.current.international.taxAtSource.percent\" require=\"true\"></salaxy-input-number>\r\n      <salaxy-input-number name=\"deductionMonthly\" unit=\"eur\" label=\"SALAXY.NG1.EmploymentDetails.monthlyDeduction\" label-cols=\"col-sm-8\" ng-model=\"$ctrl.current.international.taxAtSource.deductionMonthly\"></salaxy-input-number>\r\n      <salaxy-input-number name=\"deductionDaily\" unit=\"eur\" label=\"SALAXY.NG1.EmploymentDetails.deductionDaily\" label-cols=\"col-sm-8\" ng-model=\"$ctrl.current.international.taxAtSource.deductionDaily\"></salaxy-input-number>\r\n    </fieldset>\r\n    <div class=\"text-right\">\r\n      <button ng-click=\"$ctrl.save()\" class=\"btn btn-primary\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n    </div>\r\n  </div>\r\n  <div ng-switch-when=\"noTaxCard\">\r\n    <fieldset>\r\n      <legend sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.taxCard.noTaxCard\"></legend>\r\n      <p sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.taxCard.noTaxCardText\"></p>\r\n    </fieldset>\r\n  </div>\r\n  <div ng-switch-default>\r\n    <salaxy-employment-taxcards employment-id=\"$ctrl.current.id\" on-save=\"$ctrl.reload()\" is-read-only-forced=\"$ctrl.isReadOnlyForced\" hide-buttons=\"$ctrl.isReadOnlyForced\"\r\n      ng-ref=\"$ctrl.taxcardsController\"></salaxy-employment-taxcards>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/employment/shared-EmploymentRelation.html\",`<div class=\"row\">\r\n  <div class=\"col-md-6\" ng-if=\"!$ctrl.isHousehold\">\r\n    <salaxy-input-enum ng-required=\"true\" hidden-options=\"undefined\" name=\"type\" ng-model=\"$ctrl.current.info.type\" ng-change=\"$ctrl.employmentTypeChange()\"\r\n      enum=\"EmploymentRelationType\" type=\"{{ $ctrl.socSec.isInternational ? 'select' : 'radio'}}\" label=\"Työsuhteen tyyppi\"\r\n      label-type=\"{{ $ctrl.current.info.type == 'foreignWorker' ? 'basic' : 'plain'}}\"\r\n      filter=\"entrepreneur,farmer,monthlySalary,hourlySalary,salary,employedByStateEmploymentFund,compensation,boardMember,athlete,performingArtist,foreignWorker\"></salaxy-input-enum>\r\n    <p>&nbsp;</p>\r\n    <div ng-if=\"( $ctrl.current.info.type == 'entrepreneur' ||  $ctrl.current.employment.type == 'farmer')\">\r\n      <div class=\"alert alert-danger\" ng-if=\"$ctrl.session.currentAccount.companyType =='fiTm'\" sxy-text=\"SALAXY.NG1.WorkerWizardComponent.workerType.entrepreneurTmiWarning\"></div>\r\n      <div class=\"alert alert-danger\" ng-if=\"$ctrl.session.currentAccount.companyType =='fiRy'\" sxy-text=\"SALAXY.NG1.WorkerWizardComponent.workerType.entrepreneurRyWarning\"></div>\r\n      <div class=\"alert alert-danger\" ng-if=\"$ctrl.session.currentAccount.entityType !='company'\" sxy-text=\"SALAXY.NG1.WorkerWizardComponent.workerType.entrepreneurPrivateWarning\"></div>\r\n    </div>\r\n    <fieldset ng-if=\"$ctrl.current.info.type == 'compensation'\">\r\n      <legend sxy-text=\"SALAXY.ENUM.EmploymentRelationType.compensation.label\"></legend>\r\n      <p>\r\n        <span sxy-text=\"SALAXY.NG1.WorkerWizardComponent.workerType.compensationDescription\"></span><br>\r\n        <a href=\"{{'SALAXY.NG1.WorkerWizardComponent.workerType.compensationLink' | sxyTranslate}}\" target=\"_blank\" sxy-text=\"SALAXY.NG1.WorkerWizardComponent.workerType.compensationCta\"></a>\r\n      </p>\r\n    </fieldset>\r\n    <fieldset ng-if=\"$ctrl.socSec.isInternational\">\r\n      <legend>{{'SALAXY.NG1.EmploymentRelation.isInternational.title' | sxyTranslate}}</legend>\r\n      <p sxy-html=\"SALAXY.NG1.EmploymentRelation.isInternational.info.html\"></p>\r\n      <salaxy-input-enum type=\"select\" ng-model=\"$ctrl.country\" label=\"SALAXY.MODEL.EmploymentRelationInternational.country.title\" name=\"country\" require=\"true\" enum=\"Country\"\r\n        hidden-options=\"fi\"></salaxy-input-enum>\r\n      <salaxy-input-enum type=\"select\" ng-model=\"$ctrl.current.international.idType\" label=\"SALAXY.MODEL.EmploymentRelationInternational.idType.title\" name=\"idType\" require=\"true\"\r\n        enum=\"InternationalIdentifier\"></salaxy-input-enum>\r\n      <salaxy-input ng-model=\"$ctrl.current.international.foreignId\" label=\"SALAXY.MODEL.EmploymentRelationInternational.foreignId.title\" name=\"foreignId\"\r\n        require=\"true\"></salaxy-input>\r\n      <salaxy-input name=\"street\" label=\"SALAXY.NG1.WorkerDetailsComponent.street\" ng-model=\"$ctrl.getContact('foreign').street\" require=\"true\"></salaxy-input>\r\n      <salaxy-input name=\"postalCode\" label=\"SALAXY.NG1.WorkerDetailsComponent.postalCode\" ng-model=\"$ctrl.getContact('foreign').postalCode\" require=\"true\"></salaxy-input>\r\n      <salaxy-input name=\"city\" label=\"SALAXY.NG1.WorkerDetailsComponent.city\" ng-model=\"$ctrl.getContact('foreign').city\" require=\"true\"></salaxy-input>\r\n      <salaxy-input-enum type=\"select\" ng-model=\"$ctrl.getContact('foreign').country\" label=\"SALAXY.MODEL.EmploymentRelationInternational.contactCountry.title\"\r\n        name=\"contactCountry\" read-only=\"true\" enum=\"Country\"></salaxy-input-enum>\r\n      <salaxy-input ng-if=\"$ctrl.getContact('foreign').country == 'other'\" ng-model=\"$ctrl.getContact('foreign').countryOtherName\"\r\n        label=\"SALAXY.MODEL.EmploymentRelationInternational.country.title\" name=\"countryOtherName\" require=\"true\"></salaxy-input>\r\n      <salaxy-input-enum type=\"select\" name=\"taxation\"\r\n        options=\"{ taxAtSource: ('SALAXY.NG1.EmploymentRelation.taxation.taxAtSource' | sxyTranslate), auto: ('SALAXY.NG1.EmploymentRelation.taxation.auto' | sxyTranslate), manual: ('SALAXY.NG1.EmploymentRelation.taxation.manual' | sxyTranslate) }\"\r\n        label=\"SALAXY.NG1.EmploymentRelation.taxation.label\" ng-model=\"$ctrl.current.info.taxcard\"></salaxy-input-enum>\r\n    </fieldset>\r\n    <fieldset ng-if=\"false && $ctrl.current.info.taxcard == 'taxAtSource'\">\r\n      <legend>{{'SALAXY.NG1.EmploymentRelation.taxAtSourceInfo' | sxyTranslate}}</legend>\r\n      <salaxy-input-number name=\"percent\" unit=\"percent\" minimum=\"0\" maximum=\"100\" label=\"SALAXY.NG1.EmploymentRelation.percent\" label-cols=\"col-sm-8\"\r\n        ng-model=\"$ctrl.current.international.taxAtSource.percent\" require=\"true\"></salaxy-input-number>\r\n      <salaxy-input-number name=\"deductionMonthly\" unit=\"eur\" label=\"SALAXY.NG1.EmploymentRelation.monthlyDeduction\" label-cols=\"col-sm-8\"\r\n        ng-model=\"$ctrl.current.international.taxAtSource.deductionMonthly\"></salaxy-input-number>\r\n      <salaxy-input-number name=\"deductionDaily\" unit=\"eur\" label=\"SALAXY.NG1.EmploymentRelation.deductionDaily\" label-cols=\"col-sm-8\"\r\n        ng-model=\"$ctrl.current.international.taxAtSource.deductionDaily\"></salaxy-input-number>\r\n    </fieldset>\r\n  </div>\r\n  <div class=\"col-md-6\">\r\n    <fieldset ng-if=\"!$ctrl.isHousehold\">\r\n      <legend>{{'SALAXY.NG1.EmploymentRelation.socSec'|sxyTranslate}}</legend>\r\n      <salaxy-input-enum type=\"select\" name=\"socialSecurity\" ng-if=\"$ctrl.socSec.isInternational\" enum=\"InternationalSocialSecurityType\"\r\n        label=\"SALAXY.MODEL.EmploymentRelationInternational.socialSecurity.title\" ng-model=\"$ctrl.current.international.socialSecurity\"></salaxy-input-enum>\r\n      <salaxy-input-enum ng-if=\"$ctrl.current.international.socialSecurity == 'mixed'\" type=\"multi-select\" name=\"irIncomeEarnerTypes\" disable-cache=\"true\"\r\n        enum=\"InternationalSocialSecurityException\" label=\"SALAXY.MODEL.EmploymentRelationInternational.socialSecurityExceptions.title\"\r\n        ng-model=\"$ctrl.current.international.socialSecurityExceptions\" label-type=\"basic\" hidden-options=\"voluntaryEarningsRelatedPensionInsurance\"></salaxy-input-enum>\r\n      <salaxy-input-enum ng-if=\"$ctrl.socSec.pensionCalculationOptions\" type=\"select\" name=\"pensionCalculation\" disable-cache=\"true\"\r\n        options=\"$ctrl.socSec.pensionCalculationOptions\" label=\"SALAXY.NG1.WorkerWizardComponent.employment.pension.title\" ng-model=\"$ctrl.current.info.pensionCalculation\"\r\n        ng-change=\"$ctrl.pensionCalculationChange()\"></salaxy-input-enum>\r\n      <salaxy-input-enum ng-if=\"$ctrl.socSec.showPensionCompanySelection\" type=\"select\" name=\"pensionCompany\" placeholder=\"SALAXY.UI_Terms.notChosen\" disable-cache=\"true\"\r\n        options=\"$ctrl.socSec.pensionCompanies\" label=\"SALAXY.MODEL.PensionContract.title\" ng-model=\"$ctrl.current.info.pensionCompany\"></salaxy-input-enum>\r\n      <salaxy-input-enum ng-if=\"$ctrl.socSec.pensionContractNumbers\" type=\"select\" name=\"pensionContractNumber\" placeholder=\"SALAXY.UI_Terms.notChosen\" disable-cache=\"true\"\r\n        options=\"$ctrl.socSec.pensionContractNumbers\" label=\"SALAXY.MODEL.PensionContract.contractNumber.title\"\r\n        ng-model=\"$ctrl.current.info.pensionContractNumber\"></salaxy-input-enum>\r\n      <salaxy-input-enum ng-if=\"$ctrl.socSec.showPension && ('test,admin,pro' | sxyIsInRole)\" type=\"select\" name=\"pensionRule\" enum=\"PensionRule\"\r\n        label=\"SALAXY.NG1.WorkerWizardComponent.employment.pensionRule\" ng-model=\"$ctrl.current.info.pensionRule\"></salaxy-input-enum>\r\n      <salaxy-input-enum ng-if=\"$ctrl.socSec.showInsuranceCompanySelection\" type=\"select\" name=\"insuranceCompany\" placeholder=\"SALAXY.UI_Terms.notChosen\" disable-cache=\"true\"\r\n        options=\"$ctrl.socSec.insuranceCompanies\" label=\"SALAXY.NG1.InsuranceSettingsComponent.insurance.title\" ng-model=\"$ctrl.current.info.insuranceCompany\"></salaxy-input-enum>\r\n      <salaxy-input-enum ng-if=\"$ctrl.socSec.insuranceContractNumbers\" type=\"select\" name=\"insuranceContractNumber\" placeholder=\"SALAXY.UI_Terms.notChosen\" disable-cache=\"true\"\r\n        options=\"$ctrl.socSec.insuranceContractNumbers\" label=\"SALAXY.MODEL.InsuranceContract.contractNumber.title\"\r\n        ng-model=\"$ctrl.current.info.insuranceContractNumber\"></salaxy-input-enum>\r\n    </fieldset>\r\n    <fieldset>\r\n      <legend ng-if=\"!$ctrl.isHousehold\">{{'SALAXY.NG1.EmploymentRelation.employmentRelation'|sxyTranslate}}</legend>\r\n      <salaxy-input ng-model=\"$ctrl.current.work.description\" label=\"SALAXY.NG1.WorkerWizardComponent.employment.work.description\" name=\"description\"></salaxy-input>\r\n      <salaxy-input-occupation-type  name=\"occupationType\" ng-model=\"$ctrl.current.work.occupationCode\"\r\n        label=\"SALAXY.NG1.WorkerWizardComponent.employment.work.occupationCode\"></salaxy-input-occupation-type>\r\n      <salaxy-input-collective-bargain-agreement name=\"collectiveBargainAgreement\" ng-model=\"$ctrl.current.info.cbaCode\" label=\"SALAXY.NG1.WorkerWizardComponent.employment.info.cbaCode\"></salaxy-input-collective-bargain-agreement>\r\n      <salaxy-input-employee-group ng-if=\"'bizConfigs' | sxyIsInRole\" name=\"employeeGroup\" ng-model=\"$ctrl.current.info.employeeGroup\" label=\"SALAXY.MODEL.EmploymentRelationInfo.employeeGroup.title\"></salaxy-input-employee-group>\r\n      <salaxy-input tooltip-html=\"&lt;a target=&#39;_blank&#39; href=&#39;https://www.keva.fi/tyonantajalle/elakemaksut/ammattinimikkeiden-haku/&#39;&gt;Info&lt;/a&gt;\" ng-if=\"$ctrl.current.info.pensionCalculation == 'publicSector'\" name=\"occupationCode2\" ng-model=\"$ctrl.current.work.occupationCode2\"\r\n        label=\"SALAXY.NG1.WorkerWizardComponent.employment.work.occupationCode2\"></salaxy-input>\r\n      <salaxy-form-group label=\"SALAXY.NG1.WorkerWizardComponent.employment.group.title\" name=\"contract\">\r\n        <salaxy-datepicker-popup name=\"startDate\" label=\"SALAXY.NG1.WorkerWizardComponent.employment.group.startDate\"\r\n          ng-model=\"$ctrl.current.info.startDate\"></salaxy-datepicker-popup>\r\n        <salaxy-datepicker-popup name=\"endDate\" label=\"SALAXY.NG1.WorkerWizardComponent.employment.group.endDate\"\r\n          disabled=\"!$ctrl.current.info.isFixedTerm && !$ctrl.current.info.isTerminated\" ng-model=\"$ctrl.current.info.endDate\"></salaxy-datepicker-popup>\r\n        <salaxy-input-boolean type=\"checkbox\" ng-model=\"$ctrl.current.info.isFixedTerm\" name=\"isFixedTerm\" id=\"isFixedTerm\" label-type=\"no-label\" label-true=\"SALAXY.NG1.WorkerWizardComponent.employment.isFixedTerm\"></salaxy-input-boolean>\r\n        <salaxy-input-boolean type=\"checkbox\" ng-model=\"$ctrl.current.info.isTerminated\" name=\"isTerminated\" id=\"isTerminated\" label-type=\"no-label\" label-true=\"SALAXY.NG1.WorkerWizardComponent.employment.isTerminated\"></salaxy-input-boolean>\r\n\r\n      </salaxy-form-group>\r\n      <salaxy-input-enum ng-if=\"$ctrl.current.info.pensionCalculation == 'publicSector'\" type=\"select\" name=\"employmentRegCodes\" disable-cache=\"true\"\r\n      options=\"$ctrl.socSec.employmentRegCodes\" label=\"SALAXY.NG1.WorkerWizardComponent.employment.employmentRegCode\" ng-model=\"$ctrl.current.info.employmentRegCode\"></salaxy-input-enum>\r\n      <salaxy-input-enum ng-if=\"$ctrl.current.isReadOnly\" label=\"SALAXY.NG1.WorkerDetailsComponent.salaryPaymentMethod\" name=\"employmentRelationSalaryPaymentMethod\"\r\n        ng-model=\"$ctrl.current.info.salaryPaymentMethod\" enum=\"EmploymentRelationSalaryPaymentMethod\" required placeholder=\"SALAXY.UI_Terms.selectAlt\"></salaxy-input-enum>\r\n    </fieldset>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/EmploymentEditModal.html\",`﻿<div class=\"modal-worker-edit\">\r\n  <div class=\"modal-header\">\r\n    <h2 class=\"modal-title\">{{$ctrl.logic.title}}</h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"modal-body\">\r\n    <salaxy-employment-details model=\"$ctrl.current\" current-tab=\"{{$ctrl.logic.initialTab}}\" is-read-only-forced=\"$ctrl.route.readOnly\" is-modal=\"true\" ng-ref=\"$ctrl.employmentDetails\"></salaxy-employment-details>\r\n  </div>\r\n  <div class=\"modal-footer text-end\">\r\n    <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.NG1.AbsencePeriodsEditDialog.cancelButtonText\"></button>\r\n    <button type=\"submit\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" ng-if=\"$ctrl.logic.buttonTypes != 'updateCalc'\" ng-disabled=\"$ctrl.employmentDetails.employmentForm.$invalid\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n    <button type=\"submit\" class=\"btn btn-default\" ng-click=\"$close('ok-no-rows')\" ng-if=\"$ctrl.logic.buttonTypes == 'updateCalc'\" ng-disabled=\"$ctrl.employmentDetails.employmentForm.$invalid\" sxy-text=\"SALAXY.NG1.EmploymentTaxcardsComponent.workerEdit.updateWorkerInfo\"></button>\r\n    <button type=\"submit\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" ng-if=\"$ctrl.logic.buttonTypes == 'updateCalc'\" ng-disabled=\"$ctrl.employmentDetails.employmentForm.$invalid\" sxy-text=\"SALAXY.NG1.EmploymentTaxcardsComponent.workerEdit.updateWorkerInfoAndSalaryRows\"></button>\r\n  </div>\r\n</div>\r\n`);\n\n $templateCache.put(\"salaxy-components/worker/EmploymentList.html\",`<div class=\"salaxy-component salaxy-worker-list\">\r\n  <salaxy-odata-table logic=\"{showToolbar: $ctrl.showToolbar}\" url=\"/v03/api/employments?activeDate=today\"\r\n    options=\"{$top: $ctrl.limitTo}\"\r\n    ng-if=\"($ctrl.mode || 'default') == 'default'\"\r\n    read-only=\"$ctrl.readOnly\" crud-controller=\"EmploymentCrudController as $crud\"\r\n    template-url=\"salaxy-components/odata/lists/Employments.html\"></salaxy-odata-table>\r\n  <salaxy-odata-table select-mode=\"$ctrl.mode\" url=\"/v03/api/employments?activeDate=today\"\r\n    options=\"{$top: $ctrl.limitTo }\"\r\n    ng-if=\"$ctrl.mode == 'select' || $ctrl.mode == 'multiselect'\"\r\n     template-url=\"salaxy-components/odata/lists/Employments-select.html\"\r\n    items=\"$ctrl.items\" selected-items=\"$ctrl.selectedItems\"\r\n    on-list-select=\"$ctrl.onListSelect({ value: value, item: item, allItems: allItems });\"\r\n    crud-controller=\"EmploymentCrudController as $crud\"></salaxy-odata-table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/EmploymentWizard/identity.html\",`<form name=\"currentForm\" class=\"form-horizontal\">\r\n  <span class=\"d-none\">{{ $ctrl.formDataValidity = currentForm.$valid  }}</span>\r\n  <div class=\"row\">\r\n    <div class=\"col-12 col-sm-6 margin-top-sm margin-xs\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.details\"></legend>\r\n        <salaxy-input name=\"officialPersonId\" label=\"SALAXY.NG1.WorkerDetailsComponent.ssNumber\" sxy-personal-id-fi ng-required=\"true\" ng-model=\"$ctrl.current.identity.personalId\">\r\n        </salaxy-input>\r\n        <salaxy-input name=\"firstName\" label=\"SALAXY.NG1.WorkerDetailsComponent.firstName\" ng-required=\"true\" ng-model=\"$ctrl.current.identity.firstName\"></salaxy-input>\r\n        <salaxy-input name=\"lastName\" label=\"SALAXY.NG1.WorkerDetailsComponent.lastName\" ng-required=\"true\" ng-model=\"$ctrl.current.identity.lastName\"></salaxy-input>\r\n      </fieldset>\r\n    </div>\r\n    <div class=\"col-12 col-sm-6 margin-top-sm margin-xs\">\r\n      <fieldset ng-if=\"$ctrl.otherEmployments.length > 0\">\r\n        <legend>Henkilötunnuksella on jo {{ $ctrl.otherEmployments.length }} työsuhdetta</legend>\r\n        <div class=\"list-group\">\r\n          <a ng-href=\"#/employments/details/{{ item.id }}\" ng-click=\"$close()\" class=\"list-group-item\" ng-repeat=\"item in $ctrl.otherEmployments\">\r\n            <strong>{{ $ctrl.getEmploymentDescription(item) }}</strong><br>\r\n            {{ $ctrl.getActiveText(item) }}\r\n          </a>\r\n        </div>\r\n      </fieldset>\r\n      <fieldset salaxy-if-role=\"test\">\r\n        <legend>Vain TESTI</legend>\r\n        <p>\r\n          <strong>Vain testiympäristö:</strong> Täytä loput tiedot nimen perusteella (syötä ensin etu- ja sukunimi).\r\n        </p>\r\n        <div class=\"text-end\">\r\n          <button ng-disabled=\"!$ctrl.current.identity.firstName || !$ctrl.current.identity.lastName\" ng-click=\"$ctrl.populateWithTestData(true)\" class=\"btn btn-danger\">\r\n            Täytä tiedot</button>\r\n          <button ng-disabled=\"!$ctrl.current.identity.firstName || !$ctrl.current.identity.lastName\" ng-click=\"$ctrl.populateWithTestData(false)\" class=\"btn btn-default\">...keinohetu</button>\r\n        </div>\r\n      </fieldset>\r\n    </div>\r\n  </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/worker/EmploymentWizard/index.html\",`<div class=\"modal-header\">\r\n  <h2 class=\"modal-title\" sxy-text=\"SALAXY.NG1.WorkerWizardComponent.wizard.title\"></h2>\r\n  <button type=\"button\" class=\"btn-close\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n</div>\r\n<div class=\"modal-body\">\r\n  <div class=\"d-block d-md-none\">\r\n    <h4><span sxy-text=\"SALAXY.NG1.WorkerWizardComponent.wizard.step\"></span> {{$ctrl.currentStep.number}}/{{$ctrl.steps.length}}</h4>\r\n  </div>\r\n  <div class=\"salaxy-wizard\">\r\n    <div class=\"wizard-steps\">\r\n      <div class=\"wizard-step\" ng-repeat=\"step in $ctrl.steps\" ng-class=\"{'active': step.active, 'disabled': step.disabled}\">\r\n        <span class=\"salaxy-avatar\">\r\n          <div class=\"wizard-icons-wrapper\">\r\n            <i class=\"bi\" ng-class=\"step.active ? 'bi-circle-fill' : 'bi-circle'\"></i>\r\n            <i class=\"bi bi-circle-fill\"></i>\r\n          </div>\r\n          <strong class=\"number\">{{ step.number }}</strong>\r\n        </span>\r\n        <span class=\"step-text\">{{ step.title | sxyTranslate }}</span>\r\n      </div>\r\n    </div>\r\n    <div class=\"wizard-strikethrough\"></div>\r\n  </div>\r\n  <div class=\"worker-wizard-content\">\r\n    <ng-include src=\"$ctrl.currentStep.view\"></ng-include>\r\n  </div>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <div>\r\n    <button ng-if=\"$ctrl.step &lt; 2\" ng-click=\"$close('cancel')\" class=\"btn btn-default\" sxy-text=\"SALAXY.UI_Terms.close\"></button>\r\n    <button ng-if=\"$ctrl.step >= 2\" ng-click=\"$ctrl.goPrevious()\" ng-disabled=\"!$ctrl.canGoPrevious\" class=\"btn btn-default\" sxy-text=\"SALAXY.UI_Terms.previous\"></button>\r\n  </div>\r\n  <div class=\"ms-auto\">\r\n    <button ng-if=\"$ctrl.step &lt; $ctrl.steps.length\" ng-click=\"$ctrl.goNext()\" ng-disabled=\"!$ctrl.canGoNext\" class=\"btn btn-primary\" sxy-text=\"SALAXY.UI_Terms.next\"></button>\r\n    <button ng-if=\"$ctrl.step == $ctrl.steps.length\" ng-click=\"$ctrl.saveAndClose($close)\" class=\"btn btn-primary\" ng-disabled=\"!$ctrl.formDataValidity\" sxy-text=\"SALAXY.UI_Terms.done\"></button>\r\n  </div>\r\n  \r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/EmploymentWizard/person.html\",`<form name=\"currentForm\" class=\"form-horizontal\">\r\n  <span class=\"d-none\">{{ $ctrl.formDataValidity = currentForm.$valid  }}</span>\r\n    <div class=\"row\">\r\n    <div class=\"col-12 col-sm-6 margin-top-sm margin-xs\">\r\n      <fieldset>\r\n        <legend>Yhteystiedot</legend>\r\n        <salaxy-input name=\"email\" label=\"SALAXY.NG1.WorkerDetailsComponent.email\" sxy-email ng-model=\"$ctrl.getContact().email\"></salaxy-input>\r\n        <salaxy-input name=\"telephone\" label=\"SALAXY.NG1.WorkerDetailsComponent.tel\" sxy-mobile-phone ng-model=\"$ctrl.getContact().telephone\"></salaxy-input>\r\n      </fieldset>\r\n      <fieldset ng-if=\"$ctrl.isOtherIdentifier\">\r\n        <legend sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.address\"></legend>\r\n        <p class=\"small\" sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.unRealPersonalIndenficationNumer\"></p>\r\n        <salaxy-input name=\"street\" label=\"SALAXY.NG1.WorkerDetailsComponent.street\" ng-required=\"true\" ng-model=\"$ctrl.getContact().street\">\r\n        </salaxy-input>\r\n        <salaxy-input name=\"postalCode\" label=\"SALAXY.NG1.WorkerDetailsComponent.postalCode\" ng-required=\"true\" ng-model=\"$ctrl.getContact().postalCode\">\r\n        </salaxy-input>\r\n        <salaxy-input name=\"city\" label=\"SALAXY.NG1.WorkerDetailsComponent.city\" ng-required=\"true\" ng-model=\"$ctrl.getContact().city\">\r\n        </salaxy-input>\r\n      </fieldset>\r\n    </div>\r\n    <div class=\"col-12 col-sm-6 margin-top-sm margin-xs\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.paymentDetails\"></legend>\r\n        <salaxy-input-enum label=\"SALAXY.NG1.WorkerDetailsComponent.salaryPaymentMethod\" name=\"employmentRelationSalaryPaymentMethod\" ng-model=\"$ctrl.current.info.salaryPaymentMethod\" enum=\"EmploymentRelationSalaryPaymentMethod\" required placeholder=\"SALAXY.UI_Terms.selectAlt\"></salaxy-input-enum>\r\n        <salaxy-input ng-if=\"$ctrl.current.info.salaryPaymentMethod === 'bankAccount'\" name=\"ibanNumber\" label=\"SALAXY.NG1.WorkerDetailsComponent.ibanNumber\" sxy-iban ng-required=\"true\" ng-model=\"$ctrl.current.info.ibanNumber\"></salaxy-input>\r\n      </fieldset>\r\n    </div>\r\n  </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/worker/EmploymentWizard/tax.html\",`<form name=\"currentForm\" class=\"form-horizontal\">\r\n  <span class=\"d-none\">{{ $ctrl.formDataValidity = currentForm.$valid }}</span>\r\n  <div class=\"row\">\r\n    <div class=\"col-6\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.employmentTaxcard\"></legend>\r\n        <salaxy-input-enum label=\"\" name=\"employmentTaxcard\" ng-model=\"$ctrl.current.info.taxcard\" enum=\"EmploymentRelationTaxcard\"\r\n          label-cols=\"col-sm-5\" label-type=\"plain\" type=\"radio\"></salaxy-input-enum>\r\n      </fieldset>\r\n    </div>\r\n    <div ng-switch=\"$ctrl.current.info.taxcard\" class=\"col-6\">\r\n      <fieldset ng-switch-when=\"taxAtSource\">\r\n        <legend>{{'SALAXY.NG1.EmploymentDetails.taxAtSource.title' | sxyTranslate}}</legend>\r\n        <div class=\"alert alert-danger\" ng-if=\"!$ctrl.socSec.isInternational\" sxy-html=\"SALAXY.NG1.EmploymentDetails.taxAtSource.info.html\"></div>\r\n        <salaxy-input-number name=\"percent\" unit=\"percent\" minimum=\"0\" maximum=\"100\" label=\"SALAXY.NG1.EmploymentDetails.percent\" label-cols=\"col-sm-8\"\r\n          ng-model=\"$ctrl.current.international.taxAtSource.percent\" require=\"true\"></salaxy-input-number>\r\n        <salaxy-input-number name=\"deductionMonthly\" unit=\"eur\" label=\"SALAXY.NG1.EmploymentDetails.monthlyDeduction\" label-cols=\"col-sm-8\"\r\n          ng-model=\"$ctrl.current.international.taxAtSource.deductionMonthly\"></salaxy-input-number>\r\n        <salaxy-input-number name=\"deductionDaily\" unit=\"eur\" label=\"SALAXY.NG1.EmploymentDetails.deductionDaily\" label-cols=\"col-sm-8\"\r\n          ng-model=\"$ctrl.current.international.taxAtSource.deductionDaily\"></salaxy-input-number>\r\n      </fieldset>\r\n      <fieldset ng-switch-when=\"noTaxCard\">\r\n        <legend>Ei verokorttia (60%)</legend>\r\n        <p class=\"lead\">Ennakonpidätys tehdään 60%:n mukaan.</p>\r\n      </fieldset>\r\n      <fieldset ng-switch-when=\"auto\">\r\n        <legend sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.taxCards.taxCardDetails.automaticTaxcard.legend\"></legend>\r\n        <!--\r\n        TODO: Consider implementing this\r\n        <button class=\"btn btn-default float-end\" ng-click=\"$ctrl.getTaxCard()\">Hae verokortti</button>\r\n        -->\r\n        <p sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.taxCards.taxCardDetails.automaticTaxcard.mainTaxPercentApi\"></p>\r\n        <span sxy-html=\"SALAXY.NG1.CurrentTaxCardComponent.taxCards.taxCardDetails.automaticTaxcard.taxPercentInfoText.html\"></span>\r\n      </fieldset>\r\n      <div ng-switch-default>\r\n        <span class=\"d-none\">{{ $ctrl.formDataValidity = $edit.isFormValid  }}</span>\r\n        <salaxy-taxcard-manual-edit ng-ref=\"$edit\" current=\"$ctrl.taxcard\"></salaxy-taxcard-manual-edit>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/worker/EmploymentWizard/type.html\",`<form name=\"currentForm\" class=\"form-horizontal\">\r\n  <span class=\"d-none\">{{ $ctrl.formDataValidity = currentForm.$valid }}</span>\r\n  <ng-include src=\"'salaxy-components/worker/employment/shared-EmploymentRelation.html'\"></ng-include>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/worker/EmploymentWizard/work.html\",`<form name=\"currentForm\" class=\"form-horizontal\">\r\n  <span class=\"d-none\">{{ $ctrl.formDataValidity = currentForm.$valid  }}</span>\r\n  <div class=\"row\">\r\n    <div class=\"col-12 margin-top-sm margin-xs\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.WorkerWizardComponent.employment.work.salaryDefaults.title\"></legend>\r\n        <div sxy-html=\"SALAXY.NG1.WorkerWizardComponent.employment.work.salaryDefaults.info.md\"></div>\r\n        <div class=\"table-responsive\">\r\n          <salaxy-calc-rows-2019-editor rows=\"$ctrl.current.work.salaryDefaults\" title=\"{{ 'SALAXY.NG1.WorkerDetailsComponent.defaultCalcRows' | sxyTranslate }}\" condensed=\"true\" mode=\"edit\"></salaxy-calc-rows-2019-editor>\r\n        </div>\r\n      </fieldset>\r\n    </div>\r\n  </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/worker/holidays/HolidayParametersForm.html\",`<form class=\"form-horizontal\" name=\"holidayForm\">\r\n  <div class=\"row form-horizontal\">\r\n    <div class=\"col-sm-4\">\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.legendSelectHolidayType\"></legend>\r\n        <div class=\"radio mb-1\">\r\n          <label class=\"d-flex align-items-start\">\r\n            <input type=\"radio\" ng-model=\"$ctrl.current.spec.code\" name=\"code\" id=\"permanent14Days\" value=\"permanent14Days\" class=\"mt-1 me-2\"> \r\n            <span sxy-html=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.permanent14Days.html\"></span>\r\n          </label>\r\n        </div>\r\n        <div class=\"radio mb-1\">\r\n          <label class=\"d-flex align-items-start\">\r\n            <input type=\"radio\" ng-model=\"$ctrl.current.spec.code\" name=\"code\" id=\"permanent35Hours\" value=\"permanent35Hours\" class=\"mt-1 me-2\">\r\n            <span sxy-html=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.permanent35Hours.html\"></span>\r\n          </label>\r\n        </div>\r\n        <div class=\"radio mb-1\">\r\n          <label class=\"d-flex align-items-start\">\r\n            <input type=\"radio\" ng-model=\"$ctrl.current.spec.code\" name=\"code\" id=\"holidayCompensation\" value=\"holidayCompensation\" class=\"mt-1 me-2\">\r\n            <span sxy-html=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.holidayCompensation.html\"></span>\r\n          </label>\r\n        </div>\r\n        <div class=\"radio mb-1\">\r\n          <label class=\"d-flex align-items-start\">\r\n            <input type=\"radio\" ng-model=\"$ctrl.current.spec.code\" name=\"code\" id=\"temporaryTimeOff\" value=\"temporaryTimeOff\" class=\"mt-1 me-2\">\r\n            <span sxy-html=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.temporaryTimeOff.html\"></span>\r\n          </label>\r\n        </div>\r\n        <div class=\"radio mb-1\">\r\n          <label class=\"d-flex align-items-start\">\r\n            <input type=\"radio\" ng-model=\"$ctrl.current.spec.code\" name=\"code\" id=\"other\" value=\"other\" class=\"mt-1 me-2\">\r\n            <span sxy-html=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.other.html\"></span>\r\n          </label>\r\n        </div>\r\n        <div class=\"radio mb-1\" ng-if=\"'bizConfigs' | sxyIsInRole\">\r\n          <label class=\"d-flex align-items-start\">\r\n            <input type=\"radio\" ng-model=\"$ctrl.current.spec.code\" name=\"code\" id=\"script\" value=\"script\" class=\"mt-1 me-2\">\r\n            <span sxy-html=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.script.html\"></span>\r\n          </label>\r\n        </div>\r\n        <div class=\"radio mb-1\">\r\n          <label class=\"d-flex align-items-start\">\r\n            <input type=\"radio\" ng-model=\"$ctrl.current.spec.code\" name=\"code\" id=\"noHolidays\" value=\"noHolidays\" class=\"mt-1 me-2\">\r\n            <span sxy-html=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.noHolidays.html\"></span>\r\n          </label>\r\n        </div>\r\n      </fieldset>\r\n    </div>\r\n    <div class=\"col-sm-8\">\r\n      <fieldset >\r\n        <legend sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.legendDetails\"></legend>\r\n        <div ng-if=\"$ctrl.getHolidayLogic($ctrl.current.spec).getVisibility($ctrl.current.spec, 'accrualFixed')\" ng-init=\"$holidayLogic = $ctrl.getHolidayLogic($ctrl.current.spec)\">\r\n          <salaxy-input-boolean type=\"checkbox\" name=\"accrualByLaw\" label=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.accrualByLaw\" label-true=\"{{ 'SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.accrualByLawLabelTrue' + ($ctrl.current.spec.code == 'temporaryTimeOff' ? '2' : '') }}\"\r\n            ng-change=\"$holidayLogic.accrualByLawChanged($ctrl.current.spec)\" ng-model=\"$holidayLogic.accrualByLaw\"></salaxy-input-boolean>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.spec.accrualFixed\" name=\"accrualFixed\" ng-if=\"$ctrl.current.spec.accrualFixed\" ng-change=\"$holidayLogic.accrualFixedChanged($ctrl.current.spec)\" label=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.accrualFixed\" unit=\"days\">\r\n          </salaxy-input-number>\r\n        </div>\r\n        <salaxy-input-number ng-model=\"$ctrl.current.spec.compensation\" name=\"compensation\" ng-if=\"$ctrl.getHolidayLogic($ctrl.current.spec).getVisibility($ctrl.current.spec, 'compensation')\" required label=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.compensation\" unit=\"percent\"></salaxy-input-number>\r\n        <salaxy-input-enum name=\"bonusMethod\" ng-model=\"$ctrl.current.spec.bonusMethod\" ng-if=\"$ctrl.getHolidayLogic($ctrl.current.spec).getVisibility($ctrl.current.spec, 'bonusMethod')\" label=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.bonusMethod\" filter=\"none,payForHolidaySalary,paySelectedDays\" enum=\"HolidayBonusPaymentMethod\"></salaxy-input-enum>\r\n        <salaxy-input-enum name=\"bonusMethod\" ng-model=\"$ctrl.current.spec.bonusMethod\" ng-if=\"$ctrl.getHolidayLogic($ctrl.current.spec).getVisibility($ctrl.current.spec, 'compensation')\" label=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.bonusMethod\" options=\"{ 'none': ('SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.bonusMethodNone' | sxyTranslate), 'payForHolidaySalary': ('SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.bonusMethodPayForHolidaySalary' | sxyTranslate)  }\">\r\n        </salaxy-input-enum>\r\n        <salaxy-input-number ng-model=\"$ctrl.current.spec.bonus\" name=\"bonus\" ng-if=\"$ctrl.getHolidayLogic($ctrl.current.spec).getVisibility($ctrl.current.spec, 'bonusPercent')\" label=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.bonusPercent\" unit=\"percent\"></salaxy-input-number>\r\n        <div ng-if=\"$ctrl.getHolidayLogic($ctrl.current.spec).getVisibility($ctrl.current.spec, 'accruesHolidays')\">\r\n          <salaxy-input-enum  required name=\"wageBasis\" ng-model=\"$ctrl.current.spec.wageBasis\" label=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.wageBasis\" enum=\"WageBasis\" hidden-options=\"undefined,other\"></salaxy-input-enum>\r\n          <salaxy-input-enum name=\"holidayPayCalculation\" ng-model=\"$ctrl.current.spec.holidayPayCalculation\" label=\"SALAXY.MODEL.HolidaySpecificationForYear.holidayPayCalculation.title\" options=\"$ctrl.getHolidayLogic($ctrl.current.spec).getholidayPayCalculationOptions($ctrl.current.spec)\" required disable-cache=\"true\"></salaxy-input-enum>\r\n          <salaxy-form-group name=\"holidayPayReport\" ng-if=\"$ctrl.current.spec.holidayPayCalculation && $ctrl.current.spec.holidayPayCalculation != 'undefined' && $ctrl.current.spec.holidayPayCalculation != 'otherPay'\" label=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.holidayPayCalculationReport\">\r\n            <a ng-href=\"#/reports/holiday-pay-report-query/{{$ctrl.current.year}}/{{$ctrl.current.employmentId}}\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.calculationReport\"></a>\r\n          </salaxy-form-group>\r\n          <salaxy-form-group name=\"holidayPayEmploymentRecalculate\" ng-if=\"('bizConfigs' | sxyIsInRole) && $ctrl.current.spec.holidayPayCalculation && $ctrl.current.spec.holidayPayCalculation != 'undefined' && $ctrl.current.spec.holidayPayCalculation != 'otherPay'\" label=\"Vuosilomapalkan laskenta\">\r\n            <button class=\"btn btn-xs btn-default\" ng-click=\"$ctrl.recalculateHolidayPay()\">Laske vuosilomapalkka tälle työsuhteelle</button></span>\r\n          </salaxy-form-group>\r\n          <salaxy-form-group name=\"holidayPayRecalculate\" ng-if=\"('bizConfigs' | sxyIsInRole) && $ctrl.current.spec.holidayPayCalculation && $ctrl.current.spec.holidayPayCalculation != 'undefined' && $ctrl.current.spec.holidayPayCalculation != 'otherPay'\" label=\"Vuosilomapalkan laskenta\">\r\n            <button class=\"btn btn-xs btn-danger\" ng-click=\"$ctrl.recalculateAllHolidayPay()\">Laske vuosilomapalkka kaikille työsuhteille</button></span>\r\n          </salaxy-form-group>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.otherPay\" ng-if=\"$ctrl.current.spec.holidayPayCalculation == 'otherPay'\" name=\"otherPay\"  label=\"SALAXY.MODEL.HolidayPay.otherPay.title\" ></salaxy-input-number>\r\n  \r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.normalMonthlyPayDailySalary\" name=\"normalMonthlyPayDailySalary\" ng-if=\"($ctrl.current.spec.code == 'permanent14Days' || $ctrl.current.spec.code == 'permanent35Hours' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && $ctrl.current.spec.wageBasis =='monthly' && $ctrl.current.spec.holidayPayCalculation == 'normalMonthlyPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.normalMonthlyPayDailySalary.title\" ></salaxy-input-number>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.normalMonthlyPayManual\" name=\"normalMonthlyPayManual\" ng-if=\"($ctrl.current.spec.code == 'permanent14Days' || $ctrl.current.spec.code == 'permanent35Hours' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && $ctrl.current.spec.wageBasis =='monthly' && $ctrl.current.spec.holidayPayCalculation == 'normalMonthlyPay'\" label=\"SALAXY.MODEL.HolidayPay.normalMonthlyPayManual.title\" ></salaxy-input-number>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.normalMonthlyPay\" name=\"normalMonthlyPay\" ng-if=\"($ctrl.current.spec.code == 'permanent14Days' || $ctrl.current.spec.code == 'permanent35Hours' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && $ctrl.current.spec.wageBasis =='monthly' && $ctrl.current.spec.holidayPayCalculation == 'normalMonthlyPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.normalMonthlyPay.title\" ></salaxy-input-number>\r\n\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.averageDailyPayDailySalary\" name=\"averageDailyPayDailySalary\" ng-if=\"($ctrl.current.spec.code == 'permanent14Days' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && ($ctrl.current.spec.wageBasis =='hourly' || $ctrl.current.spec.wageBasis =='performanceBased' || $ctrl.current.spec.wageBasis =='other') && $ctrl.current.spec.holidayPayCalculation == 'averageDailyPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.averageDailyPayDailySalary.title\" ></salaxy-input-number>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.averageDailyPayManual\" name=\"averageDailyPayManual\" ng-if=\"($ctrl.current.spec.code == 'permanent14Days' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && ($ctrl.current.spec.wageBasis =='hourly' || $ctrl.current.spec.wageBasis =='performanceBased' || $ctrl.current.spec.wageBasis =='other') && $ctrl.current.spec.holidayPayCalculation == 'averageDailyPay'\" label=\"SALAXY.MODEL.HolidayPay.averageDailyPayManual.title\" ></salaxy-input-number>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.averageDailyPay\" name=\"averageDailyPay\" ng-if=\"($ctrl.current.spec.code == 'permanent14Days' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && ($ctrl.current.spec.wageBasis =='hourly' || $ctrl.current.spec.wageBasis =='performanceBased' || $ctrl.current.spec.wageBasis =='other') && $ctrl.current.spec.holidayPayCalculation == 'averageDailyPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.averageDailyPay.title\" ></salaxy-input-number>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.averageDailyPayBase\" name=\"averageDailyPayBase\" ng-if=\"($ctrl.current.spec.code == 'permanent14Days' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && ($ctrl.current.spec.wageBasis =='hourly' || $ctrl.current.spec.wageBasis =='performanceBased' || $ctrl.current.spec.wageBasis =='other') && $ctrl.current.spec.holidayPayCalculation == 'averageDailyPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.averageDailyPayBase.title\" ></salaxy-input-number>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.averageDailyPayDays\" name=\"averageDailyPayDays\" ng-if=\"($ctrl.current.spec.code == 'permanent14Days' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && ($ctrl.current.spec.wageBasis =='hourly' || $ctrl.current.spec.wageBasis =='performanceBased' || $ctrl.current.spec.wageBasis =='other') && $ctrl.current.spec.holidayPayCalculation == 'averageDailyPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.averageDailyPayDays.title\" ></salaxy-input-number>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.averageDailyPayMultiplier\" name=\"averageDailyPayMultiplier\" ng-if=\"($ctrl.current.spec.code == 'permanent14Days' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && ($ctrl.current.spec.wageBasis =='hourly' || $ctrl.current.spec.wageBasis =='performanceBased' || $ctrl.current.spec.wageBasis =='other') && $ctrl.current.spec.holidayPayCalculation == 'averageDailyPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.averageDailyPayMultiplier.title\" ></salaxy-input-number>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.accrual\" name=\"averageDailyPayAccrual\" ng-if=\"($ctrl.current.spec.code == 'permanent14Days' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && ($ctrl.current.spec.wageBasis =='hourly' || $ctrl.current.spec.wageBasis =='performanceBased' || $ctrl.current.spec.wageBasis =='other') && $ctrl.current.spec.holidayPayCalculation == 'averageDailyPay'\"disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.accrual.title\" ></salaxy-input-number>\r\n\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.averageHourlyPayDailySalary\" name=\"averageHourlyPayDailySalary\" ng-if=\"($ctrl.current.spec.code == 'permanent14Days' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && ($ctrl.current.spec.wageBasis =='hourly' || $ctrl.current.spec.wageBasis =='performanceBased' || $ctrl.current.spec.wageBasis =='other') && $ctrl.current.spec.holidayPayCalculation == 'averageHourlyPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.averageHourlyPayDailySalary.title\" ></salaxy-input-number>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.averageHourlyPayManual\" name=\"averageHourlyPayManual\" ng-if=\"($ctrl.current.spec.code == 'permanent14Days' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && ($ctrl.current.spec.wageBasis =='hourly' || $ctrl.current.spec.wageBasis =='performanceBased' || $ctrl.current.spec.wageBasis =='other') && $ctrl.current.spec.holidayPayCalculation == 'averageHourlyPay'\" label=\"SALAXY.MODEL.HolidayPay.averageHourlyPayManual.title\" ></salaxy-input-number>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.averageHourlyPay\" name=\"averageHourlyPay\" ng-if=\"($ctrl.current.spec.code == 'permanent14Days' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && ($ctrl.current.spec.wageBasis =='hourly' || $ctrl.current.spec.wageBasis =='performanceBased' || $ctrl.current.spec.wageBasis =='other') && $ctrl.current.spec.holidayPayCalculation == 'averageHourlyPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.averageHourlyPay.title\" ></salaxy-input-number>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.averageHourlyPayBase\" name=\"averageHourlyPayBase\" ng-if=\"($ctrl.current.spec.code == 'permanent14Days' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && ($ctrl.current.spec.wageBasis =='hourly' || $ctrl.current.spec.wageBasis =='performanceBased' || $ctrl.current.spec.wageBasis =='other') && $ctrl.current.spec.holidayPayCalculation == 'averageHourlyPay'\" disabled=\"true\"  label=\"SALAXY.MODEL.HolidayPay.averageHourlyPayBase.title\" ></salaxy-input-number>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.averageHourlyPayHours\" name=\"averageHourlyPayHours\" ng-if=\"($ctrl.current.spec.code == 'permanent14Days' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && ($ctrl.current.spec.wageBasis =='hourly' || $ctrl.current.spec.wageBasis =='performanceBased' || $ctrl.current.spec.wageBasis =='other') && $ctrl.current.spec.holidayPayCalculation == 'averageHourlyPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.averageHourlyPayHours.title\" ></salaxy-input-number>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.averageHourlyPayMultiplier\" name=\"averageHourlyPayMultiplier\" ng-if=\"($ctrl.current.spec.code == 'permanent14Days' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && ($ctrl.current.spec.wageBasis =='hourly' || $ctrl.current.spec.wageBasis =='performanceBased' || $ctrl.current.spec.wageBasis =='other') && $ctrl.current.spec.holidayPayCalculation == 'averageHourlyPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.averageHourlyPayMultiplier.title\" ></salaxy-input-number>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.accrual\" name=\"averageHourlyPayAccrual\" ng-if=\"($ctrl.current.spec.code == 'permanent14Days' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && ($ctrl.current.spec.wageBasis =='hourly' || $ctrl.current.spec.wageBasis =='performanceBased' || $ctrl.current.spec.wageBasis =='other') && $ctrl.current.spec.holidayPayCalculation == 'averageHourlyPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.accrual.title\"></salaxy-input-number>\r\n\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.percentageBasedPayDailySalary\" name=\"percentageBasedPayDailySalary\" ng-if=\"($ctrl.current.spec.code == 'permanent35Hours' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && $ctrl.current.spec.holidayPayCalculation == 'percentageBasedPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.percentageBasedPayDailySalary.title\" ></salaxy-input-number>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.percentageBasedPayManual\" name=\"percentageBasedPayManual\" ng-if=\"($ctrl.current.spec.code == 'permanent35Hours' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && $ctrl.current.spec.holidayPayCalculation == 'percentageBasedPay'\" label=\"SALAXY.MODEL.HolidayPay.percentageBasedPayManual.title\" ></salaxy-input-number>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.percentageBasedPay\" name=\"percentageBasedPay\" ng-if=\"($ctrl.current.spec.code == 'permanent35Hours' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && $ctrl.current.spec.holidayPayCalculation == 'percentageBasedPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.percentageBasedPay.title\" ></salaxy-input-number>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.percentageBasedPayBase\" name=\"percentageBasedPayBase\" ng-if=\"($ctrl.current.spec.code == 'permanent35Hours' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && $ctrl.current.spec.holidayPayCalculation == 'percentageBasedPay'\"  disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.percentageBasedPayBase.title\" ></salaxy-input-number>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.spec.holidayPayPercent\" name=\"holidayPayPercent\" ng-if=\"($ctrl.current.spec.code == 'permanent35Hours' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && $ctrl.current.spec.holidayPayCalculation == 'percentageBasedPay'\" required unit=\"percent\" label=\"SALAXY.MODEL.HolidaySpecificationForYear.holidayPayPercent.title\" ></salaxy-input-number>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.accrual\" name=\"percentageBasedPayAccrual\" ng-if=\"($ctrl.current.spec.code == 'permanent35Hours' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && $ctrl.current.spec.holidayPayCalculation == 'percentageBasedPay'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.accrual.title\"></salaxy-input-number>\r\n\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.compensationPayDailySalary\" name=\"compensationPayDailySalary\" ng-if=\"($ctrl.current.spec.code == 'temporaryTimeOff'|| $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && $ctrl.current.spec.holidayPayCalculation == 'holidayCompensation'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.compensationPayDailySalary.title\" ></salaxy-input-number>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.compensationPayManual\" name=\"compensationPayManual\" ng-if=\"($ctrl.current.spec.code == 'temporaryTimeOff'|| $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && $ctrl.current.spec.holidayPayCalculation == 'holidayCompensation'\" label=\"SALAXY.MODEL.HolidayPay.compensationPayManual.title\" ></salaxy-input-number>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.compensationPay\" name=\"compensationPay\" ng-if=\"$($ctrl.current.spec.code == 'temporaryTimeOff'|| $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && $ctrl.current.spec.holidayPayCalculation == 'holidayCompensation'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.compensationPay.title\" ></salaxy-input-number>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.compensationPayBase\" name=\"compensationPayBase\" ng-if=\"($ctrl.current.spec.code == 'temporaryTimeOff'|| $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && $ctrl.current.spec.holidayPayCalculation == 'holidayCompensation'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.compensationPayBase.title\" ></salaxy-input-number>          \r\n          <salaxy-input-number ng-model=\"$ctrl.current.spec.compensation\" name=\"compensation\" ng-if=\"($ctrl.current.spec.code == 'temporaryTimeOff'|| $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && $ctrl.current.spec.holidayPayCalculation == 'holidayCompensation'\" unit=\"percent\" required label=\"SALAXY.MODEL.HolidaySpecificationForYear.compensation.title\" ></salaxy-input-number>\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.accrual\" name=\"compensationPayAccrual\" ng-if=\"($ctrl.current.spec.code == 'temporaryTimeOff'|| $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script') && $ctrl.current.spec.holidayPayCalculation == 'holidayCompensation'\" disabled=\"true\" label=\"SALAXY.MODEL.HolidayPay.accrual.title\"></salaxy-input-number>          \r\n\r\n          <salaxy-input-number ng-model=\"$ctrl.current.holidayPay.scriptPay\" ng-if=\"$ctrl.current.spec.holidayPayCalculation == 'scriptPay'\" name=\"scriptPay\"  label=\"SALAXY.MODEL.HolidayPay.scriptPay.title\" ></salaxy-input-number>\r\n \r\n          <salaxy-form-group label=\"SALAXY.MODEL.HolidaySpecificationForYear.employmentPeriod.title\" name=\"contract\">\r\n            <salaxy-datepicker-popup require=\"true\" name=\"startDate\" label=\"SALAXY.NG1.WorkerWizardComponent.employment.group.startDate\" ng-model=\"$ctrl.current.spec.employmentPeriod.start\"></salaxy-datepicker-popup>\r\n            <salaxy-datepicker-popup name=\"endDate\" label=\"SALAXY.NG1.WorkerWizardComponent.employment.group.endDate\" ng-model=\"$ctrl.current.spec.employmentPeriod.end\"></salaxy-datepicker-popup>\r\n          </salaxy-form-group>\r\n        </div>\r\n      </fieldset>\r\n    </div>\r\n  </div>\r\n  <div class=\"row\">\r\n    <div class=\"col-sm-12\">\r\n      <button class=\"btn btn-primary float-end\" ng-disabled=\"holidayForm.$invalid\" ng-click=\"$ctrl.saveYear($ctrl.current)\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n    </div>\r\n</form>`);\n\n $templateCache.put(\"salaxy-components/worker/holidays/HolidayYearAccrual.html\",`<salaxy-chart config=\"$ctrl.getChartConfig($ctrl.list)\"></salaxy-chart>\r\n<table class=\"table table-striped table-sm\">\r\n  <thead>\r\n    <tr>\r\n      <th sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearAccrual.tableHead.month\"></th>\r\n      <th class=\"right\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearAccrual.tableHead.daysCount\"></th>\r\n    </tr>\r\n  </thead>\r\n  <tbody>\r\n    <tr>\r\n      <td>\r\n        <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" avatar=\"{ color: $ctrl.getRowColor('start'), initials: 'saldo', entityType: 'company' }\"></salaxy-avatar>\r\n        <strong sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearAccrual.tableBody.startSaldo\"></strong>\r\n        <br />\r\n        <small>\r\n          <div class=\"truncate\" style=\"max-width: 300px;\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearAccrual.tableBody.startSaldoMore\"></div>\r\n        </small>\r\n      </td>\r\n      <td class=\"right\" style=\"width: 100px\">\r\n        <salaxy-input-number name=\"startSaldo\" label=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearAccrual.tableBody.startSaldo\" label-type=\"plain\" unit=\"days\" ng-model=\"$ctrl.parent.accrual.startSaldo\"></salaxy-input-number>\r\n      </td>\r\n    </tr>\r\n    <tr ng-repeat=\"row in $ctrl.list\">\r\n      <td>\r\n        <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" avatar=\"{ color: $ctrl.getRowColor(row), initials: (row.month | date : 'MM'), entityType: 'company' }\"></salaxy-avatar>\r\n        <strong>{{ \"SALAXY.ENUM.CalendarMonth.month\" + (row.month | date : 'M') + \".label\" | sxyTranslate }}</strong>\r\n        <br />\r\n        <small>\r\n          <div class=\"truncate\" style=\"max-width: 300px;\">{{ $ctrl.getAccrualNotes(row) }}</div>\r\n        </small>\r\n      </td>\r\n      <td class=\"right\" style=\"width: 100px\">\r\n        <salaxy-input-number name=\"{{ 'daysAccrued' + $index }}\" label=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearAccrual.tableBody.daysAccruedLabel\" label-type=\"plain\" unit=\"days\" ng-model=\"row.daysAccrued\" ng-change=\"row.daysAccrued == null ? row.source='initial': row.source = 'manual'\"></salaxy-input-number>\r\n      </td>\r\n    </tr>\r\n    <tr class=\"total\">\r\n      <td>\r\n        <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" avatar=\"{ color: $ctrl.getRowColor('total'), initials: 'Yht.', entityType: 'company' }\"></salaxy-avatar>\r\n        <strong sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearAccrual.tableBody.daysAccrued\"></strong><br />\r\n        <strong ng-if=\"$ctrl.getAccrualCalculations().totalToday != $ctrl.getAccrualCalculations().accrualToday\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearAccrual.tableBody.total\"></strong>\r\n        <div ng-if=\"$ctrl.getAccrualCalculations().total != $ctrl.getAccrualCalculations().totalToday\" class=\"truncate\" style=\"max-width: 300px;\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearAccrual.tableBody.estimatedHolidaysNexYear\"></div>\r\n      </td>\r\n      <td class=\"right\" style=\"width: 100px\">\r\n        <strong>{{ $ctrl.getAccrualCalculations().accrualToday | sxyCount : 'day' }}</strong><br />\r\n        <strong ng-if=\"$ctrl.getAccrualCalculations().totalToday != $ctrl.getAccrualCalculations().accrualToday\">{{ $ctrl.getAccrualCalculations().totalToday | sxyCount : 'day' }}</strong>\r\n        <div ng-if=\"$ctrl.getAccrualCalculations().total != $ctrl.getAccrualCalculations().totalToday\">{{ $ctrl.getAccrualCalculations().total | sxyCount : 'day' }}</div>\r\n      </td>\r\n    </tr>\r\n  </tbody>\r\n</table>\r\n<div class=\"text-end\">\r\n  <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.saveParent()\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/holidays/HolidayYearHolidays.html\",`<div class=\"salaxy-component salaxy-holiday-year-holidays\">\r\n  <table class=\"table table-striped {{ $ctrl.condensed ? 'table-sm' : ''}}\">\r\n    <thead>\r\n      <tr>\r\n        <th sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidays.tableHead.period\"></th>\r\n        <th class=\"right\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidays.tableHead.daysCount\"></th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-if=\"!$ctrl.condensed\">\r\n        <td>\r\n          <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" avatar=\"{ color: '#2b507c', initials: 'saldo', entityType: 'company' }\"></salaxy-avatar>\r\n          <strong sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidays.tableBody.availableHolidays\"></strong>\r\n          <br />\r\n          <small>\r\n            <div class=\"truncate\" style=\"max-width: 250px;\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidays.tableBody.availableHolidaysMore\"></div>\r\n          </small>\r\n        </td>\r\n        <td class=\"right\">\r\n          <strong>{{ $ctrl.getTotalDays(\"holidaysSaldoStart\") | sxyCount : \"day\" }}</strong>\r\n        </td>\r\n      </tr>\r\n      <tr ng-repeat=\"row in $ctrl.list | filter : $ctrl.filter\" ng-click=\"$ctrl.showEditDialog(row)\" class=\"clickable\">\r\n        <td>\r\n          <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" avatar=\"{ color: '#2b507c', initials: (row.period.daysCount + 'pv'), entityType: 'company' }\"></salaxy-avatar>\r\n          <strong>{{ row.period | sxyDateRange }}</strong>\r\n          <br />\r\n          <small>\r\n            <div class=\"truncate\" style=\"max-width: 250px;\">{{ $ctrl.getDescription(row) }}</div>\r\n          </small>\r\n        </td>\r\n        <td class=\"right\">\r\n          <strong>{{ row.period.daysCount | sxyCount : \"day\"  }}</strong>\r\n        </td>\r\n      </tr>\r\n      <tr class=\"total\" ng-if=\"$ctrl.condensed\">\r\n        <td>\r\n          <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" avatar=\"{ color: '#2b507c', initials: 'sum', entityType: 'company' }\"></salaxy-avatar>\r\n          <strong sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidays.tableBody.total\"></strong>\r\n        </td>\r\n        <td class=\"right\">\r\n          <strong>{{ $ctrl.getTotalDays(\"filtered\") | sxyCount : \"day\" }}</strong>\r\n        </td>\r\n      </tr>\r\n      <tr ng-if=\"$ctrl.list.length == 0 && !$ctrl.condensed\">\r\n        <td colspan=\"2\" style=\"padding-left: 48px\">\r\n          <h3 sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidays.tableBody.noHolidaysTitle\"></h3>\r\n          <p sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidays.tableBody.noHolidaysDescription\"></p>\r\n          <p sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidays.tableBody.noHolidaysDescription2\"></p>\r\n          <button type=\"button\" class=\"btn btn-primary btn-block\" ng-click=\"$ctrl.showEditDialog('new')\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidays.tableBody.addFirstHolidayButtonText\"></button>\r\n        </td>\r\n      </tr>\r\n      <tr class=\"total\" ng-if=\"!$ctrl.condensed\">\r\n        <td>\r\n          <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" avatar=\"{ color: '#2b507c', initials: 'sum', entityType: 'company' }\"></salaxy-avatar>\r\n          <strong sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidays.tableBody.total2\"></strong>\r\n          <br />\r\n          <small>\r\n            <div class=\"truncate\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidays.tableBody.total2More\"></div>\r\n          </small>\r\n        </td>\r\n        <td class=\"right\">\r\n          <strong>{{ $ctrl.getTotalDays(\"all\") | sxyCount : \"day\" }}</strong>\r\n        </td>\r\n      </tr>\r\n      <tr ng-if=\"!$ctrl.condensed\">\r\n        <td>\r\n          <salaxy-avatar class=\"salaxy-calc-row-type-avatar float-start\" avatar=\"{ color: '#2b507c', initials: 'saldo', entityType: 'company' }\"></salaxy-avatar>\r\n          <strong sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidays.tableBody.unusedHolidays\"></strong>\r\n          <br />\r\n          <small>\r\n            <div class=\"truncate\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidays.tableBody.unusedHolidaysMore\"></div>\r\n          </small>\r\n        </td>\r\n        <td class=\"right\">\r\n          <strong>{{ $ctrl.getTotalDays(\"holidaysSaldoEnd\") | sxyCount : \"day\" }}</strong>\r\n        </td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n  <div class=\"text-end\">\r\n    <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.showEditDialog('new')\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidays.addHolidayButtonText\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/holidays/HolidayYearHolidaysEditDialog.html\",`<div class=\"modal-header d-flex\">\r\n  <h1 sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidaysEditDialog.panelHeading\"></h1>\r\n  <button type=\"button\" class=\"btn-close btn-close ms-auto\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n</div>\r\n<div class=\"modal-body\">\r\n  <form class=\"form-horizontal\">\r\n    <salaxy-datepicker-popup name=\"start\" min-date=\"$ctrl.logic.minDate\" max-date=\"$ctrl.logic.maxDate\" ng-model=\"$ctrl.current.period.start\" ng-change=\"$ctrl.logic.updatePeriodDays($ctrl.current)\" label=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidaysEditDialog.labelStartDate\"></salaxy-datepicker-popup>\r\n    <salaxy-datepicker-popup name=\"end\" min-date=\"$ctrl.logic.minDate\" max-date=\"$ctrl.logic.maxDate\" ng-model=\"$ctrl.current.period.end\" ng-change=\"$ctrl.logic.updatePeriodDays($ctrl.current)\" label=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidaysEditDialog.labelEndDate\"></salaxy-datepicker-popup>\r\n    <salaxy-form-group name=\"daysCount\" label=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidaysEditDialog.labelHolidaysCount\" ng-if=\"!$ctrl.current.period.days || $ctrl.current.period.days.length == 0\">\r\n      <div class=\"input-group\">\r\n        <input class=\"form-control\" type=\"text\" autocomplete=\"off\" id=\"daysCount\" name=\"daysCount\" ng-model=\"$ctrl.current.period.daysCount\" disabled>\r\n        <span class=\"input-group-btn\">\r\n          <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.logic.setDaysSelection($ctrl.current)\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidaysEditDialog.editDatesButtonText\"></button>\r\n        </span>\r\n      </div>\r\n    </salaxy-form-group>\r\n    <salaxy-datepicker ng-model=\"$ctrl.current.period\" name=\"days\" is-multiple=\"true\" label=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidaysEditDialog.labelHolidaysCount\" min-date=\"$ctrl.current.period.start\" max-date=\"$ctrl.current.period.end\" ng-if=\"$ctrl.current.period.days.length > 0\"></salaxy-datepicker>\r\n    <salaxy-input name=\"notes\" label=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearHolidaysEditDialog.labelDescription\" ng-model=\"$ctrl.current.notes\"></salaxy-input>\r\n  </form>\r\n</div>\r\n<div class=\"modal-footer\">\r\n  <button type=\"button\" class=\"btn btn-danger\" ng-click=\"$close('delete')\" sxy-text=\"SALAXY.UI_Terms.delete\"></button>\r\n  <button type=\"reset\" class=\"btn btn-default ms-auto\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n  <button type=\"submit\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.ok\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/holidays/HolidayYearPaid.html\",`<div class=\"salaxy-component salaxy-holiday-year-paid\">\r\n  <div ng-if=\"!$ctrl.list\">\r\n    <salaxy-spinner></salaxy-spinner>\r\n  </div>\r\n  <div ng-if=\"$ctrl.list\">\r\n    <table class=\"table table-sm\">\r\n      <thead>\r\n        <tr>\r\n          <th colspan=\"2\">\r\n            &nbsp; <br />\r\n            <span class=\"uppercase\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaid.tableHead.paidHolidays\"></span>\r\n          </th>\r\n          <th class=\"right\">\r\n            <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaid.tableHead.holidaysCount\"></span>\r\n            <br />\r\n            <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaid.tableHead.holidaySalary\"></span>\r\n          </th>\r\n          <th class=\"right\">\r\n            <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaid.tableHead.compensation\"></span>\r\n            <br />\r\n            <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaid.tableHead.bonus\"></span>\r\n          </th>\r\n        </tr>\r\n      </thead>\r\n      <tbody>\r\n\r\n        <tr ng-repeat=\"row in $ctrl.list\" class=\"clickable\" ng-click=\"$ctrl.showEditDialog(row)\" ng-style=\"row.isDisabled ? {opacity: 0.5, 'text-decoration': 'line-through'}: ''\">\r\n          <td width=\"42px\">\r\n            <salaxy-avatar class=\"salaxy-calc-row-type-avatar\" avatar=\"row.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td>\r\n            <strong>{{ row.avatar.displayName }}</strong>\r\n            <span ng-if=\"row.kind =='manualSalary' || row.kind =='manualCompensation' || row.kind =='manualBonus'\" class=\"badge bg-primary\" sxy-text=\"Manual\"></span>\r\n            <div>{{ row.avatar.description }}</div>\r\n          </td>\r\n         \r\n          <td class=\"right\">\r\n            <div>{{ (row.holidayDays | sxyCount : 'day') || \"&nbsp;\" }}</div>\r\n            <div>{{ (row.holidaySalary | currency) || \"&nbsp;\" }}</div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <div>{{ (row.holidayCompensation | currency) || \"&nbsp;\" }}</div>\r\n            <div>{{ (row.holidayBonus | currency) || \"&nbsp;\" }}</div>\r\n          </td>\r\n        </tr>\r\n        \r\n        <tr>\r\n          <th colspan=\"4\">\r\n            &nbsp; <br />\r\n            <span class=\"uppercase\"> <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaid.tableHead.holidaySalary\"></span>, <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaid.tableHead.compensation\"></span></span>\r\n          </th>\r\n        </tr>\r\n        <tr>\r\n          <td width=\"42px\">\r\n            <salaxy-avatar class=\"salaxy-calc-row-type-avatar\" avatar=\"$ctrl.totals.startSaldo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td>\r\n            <strong>{{ $ctrl.totals.startSaldo.avatar.displayName }}</strong>\r\n            <div>{{ $ctrl.totals.startSaldo.avatar.description }}</div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <div>{{ ($ctrl.totals.startSaldo.holidayDays | sxyCount : 'day') || \"&nbsp;\" }}</div>\r\n            <div>{{ ($ctrl.totals.startSaldo.holidaySalary | currency) || \"&nbsp;\" }}</div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <div>{{ ($ctrl.totals.startSaldo.holidayCompensation | currency) || \"&nbsp;\" }}</div>\r\n            <div>{{ ($ctrl.totals.startSaldo.holidayBonus | currency) || \"&nbsp;\" }}</div>\r\n          </td>\r\n        </tr>\r\n        <tr class=\"total\">\r\n          <td width=\"42px\">\r\n            <salaxy-avatar class=\"salaxy-calc-row-type-avatar\" avatar=\"$ctrl.totals.total.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td>\r\n            <strong>{{ $ctrl.totals.total.avatar.displayName }}</strong>\r\n            <div>{{ $ctrl.totals.total.avatar.description }}</div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <div>{{ ($ctrl.totals.total.holidayDays | sxyCount : 'day') || \"&nbsp;\" }}</div>\r\n            <div>{{ ($ctrl.totals.total.holidaySalary | currency) || \"&nbsp;\" }}</div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <div>{{ ($ctrl.totals.total.holidayCompensation | currency) || \"&nbsp;\" }}</div>\r\n            <div>{{ ($ctrl.totals.total.holidayBonus | currency) || \"&nbsp;\" }}</div>\r\n          </td>\r\n        </tr>\r\n        <tr>\r\n          <td width=\"42px\">\r\n            <salaxy-avatar class=\"salaxy-calc-row-type-avatar\" avatar=\"$ctrl.totals.endSaldo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td>\r\n            <strong>{{ $ctrl.totals.endSaldo.avatar.displayName }}</strong>\r\n            <div>{{ $ctrl.totals.endSaldo.avatar.description }}</div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <div>{{ ($ctrl.totals.endSaldo.holidayDays | sxyCount : 'day') || \"&nbsp;\" }}</div>\r\n            <div>{{ ($ctrl.totals.endSaldo.holidaySalary | currency) || \"&nbsp;\" }}</div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <div>{{ ($ctrl.totals.endSaldo.holidayCompensation | currency) || \"&nbsp;\" }}</div>\r\n            <div>{{ ($ctrl.totals.endSaldo.holidayBonus | currency) || \"&nbsp;\" }}</div>\r\n          </td>\r\n        </tr>\r\n        <tr>\r\n          <th colspan=\"4\">\r\n            &nbsp; <br />\r\n            <span class=\"uppercase\"> <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaid.tableHead.bonus\"></span></span>\r\n          </th>\r\n        </tr>\r\n        <tr ng-if=\"$ctrl.shoudPayBonus\">\r\n          <td width=\"42px\">\r\n            <salaxy-avatar class=\"salaxy-calc-row-type-avatar\" avatar=\"$ctrl.bonusTotals.startSaldo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td>\r\n            <strong>{{ $ctrl.bonusTotals.startSaldo.avatar.displayName }}</strong>\r\n            <div>{{ $ctrl.bonusTotals.startSaldo.avatar.description }}</div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <div>{{ ($ctrl.bonusTotals.startSaldo.holidayDays | sxyCount : 'day') || \"&nbsp;\" }}</div>\r\n            <div>{{ ($ctrl.bonusTotals.startSaldo.holidaySalary | currency) || \"&nbsp;\" }}</div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <div>{{ ($ctrl.bonusTotals.startSaldo.holidayCompensation | currency) || \"&nbsp;\" }}</div>\r\n            <div>{{ ($ctrl.bonusTotals.startSaldo.holidayBonus | currency) || \"&nbsp;\" }}</div>\r\n          </td>\r\n        </tr>\r\n        <tr class=\"total\">\r\n          <td width=\"42px\">\r\n            <salaxy-avatar class=\"salaxy-calc-row-type-avatar\" avatar=\"$ctrl.bonusTotals.total.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td>\r\n            <strong>{{ $ctrl.bonusTotals.total.avatar.displayName }}</strong>\r\n            <div>{{ $ctrl.bonusTotals.total.avatar.description }}</div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <div>{{ ($ctrl.bonusTotals.total.holidayDays | sxyCount : 'day') || \"&nbsp;\" }}</div>\r\n            <div>{{ ($ctrl.bonusTotals.total.holidaySalary | currency) || \"&nbsp;\" }}</div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <div>{{ ($ctrl.bonusTotals.total.holidayCompensation | currency) || \"&nbsp;\" }}</div>\r\n            <div>{{ ($ctrl.bonusTotals.total.holidayBonus | currency) || \"&nbsp;\" }}</div>\r\n          </td>\r\n        </tr>\r\n        <tr ng-if=\"$ctrl.shoudPayBonus\">\r\n          <td width=\"42px\">\r\n            <salaxy-avatar class=\"salaxy-calc-row-type-avatar\" avatar=\"$ctrl.bonusTotals.endSaldo.avatar\"></salaxy-avatar>\r\n          </td>\r\n          <td>\r\n            <strong>{{ $ctrl.bonusTotals.endSaldo.avatar.displayName }}</strong>\r\n            <div>{{ $ctrl.bonusTotals.endSaldo.avatar.description }}</div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <div>{{ ($ctrl.bonusTotals.endSaldo.holidayDays | sxyCount : 'day') || \"&nbsp;\" }}</div>\r\n            <div>{{ ($ctrl.bonusTotals.endSaldo.holidaySalary | currency) || \"&nbsp;\" }}</div>\r\n          </td>\r\n          <td class=\"right\">\r\n            <div>{{ ($ctrl.bonusTotals.endSaldo.holidayCompensation | currency) || \"&nbsp;\" }}</div>\r\n            <div>{{ ($ctrl.bonusTotals.endSaldo.holidayBonus | currency) || \"&nbsp;\" }}</div>\r\n          </td>\r\n        </tr>\r\n      </tbody>\r\n    </table>\r\n    <button type=\"button\" class=\"btn btn-primary pull-right\" ng-click=\"$ctrl.showEditDialog('new', true)\" sxy-text=\"SALAXY.UI_Terms.add\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/holidays/HolidayYearPaidEditDialog.html\",`<div class=\"card card-primary\">\r\n  <div class=\"card-header \">\r\n    <h2 sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaidEditDialog.panelHeading\"></h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$dismiss()\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"card-body\">\r\n    <form class=\"form-horizontal\">      \r\n      <div ng-switch=\"$ctrl.current.kind\">\r\n        <div ng-switch-when=\"manualSalary\">\r\n          <h3 sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaidEditDialog.manualSalary.title\"></h3>\r\n          <p sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaidEditDialog.manualSalary.description\"></p>\r\n        </div>\r\n        <div ng-switch-when=\"manualCompensation\">\r\n          <h3 sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaidEditDialog.manualCompensation.title\"></h3>\r\n          <p sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaidEditDialog.manualCompensation.description\"></p>\r\n        </div>\r\n        <div ng-switch-when=\"manualBonus\">\r\n          <h3 sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaidEditDialog.manualBonus.title\"></h3>\r\n          <p sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaidEditDialog.manualBonus.description\"></p>\r\n        </div>\r\n        <div ng-switch-when=\"paidCalc\">\r\n          <h3 sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaidEditDialog.paidCalc.title\"></h3>\r\n          <p sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaidEditDialog.paidCalc.description\"></p>\r\n        </div>\r\n      </div>\r\n      <div ng-if=\"$ctrl.current.kind == 'undefined'\">\r\n        <p class=\"lead\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaidEditDialog.undefined.labelAnnualLeavePaymentKind\"></p>\r\n        <salaxy-input-enum ng-model=\"$ctrl.current.kind\" name=\"typeRadio\" enum=\"AnnualLeavePaymentKind\" type=\"radio\" filter=\"manualSalary,manualCompensation,manualBonus\" label-type=\"plain\"></salaxy-input-enum>\r\n        <p>&nbsp;</p>\r\n      </div>\r\n      <div ng-if=\"$ctrl.current.kind != 'undefined'\">\r\n        <salaxy-input-enum  disabled=\"true\" ng-if=\"$ctrl.current.kind == 'paidCalc'\" ng-model=\"$ctrl.current.kind\" enum=\"AnnualLeavePaymentKind\" label=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaidEditDialog.kind\" filter=\"paidCalc\" name=\"typeSelect\" type=\"select\"></salaxy-input-enum>\r\n        <salaxy-input-enum  ng-if=\"$ctrl.current.kind != 'paidCalc'\" ng-model=\"$ctrl.current.kind\" enum=\"AnnualLeavePaymentKind\" label=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaidEditDialog.kind\" filter=\"manualSalary,manualCompensation,manualBonus\" name=\"typeSelect\" type=\"select\"></salaxy-input-enum>\r\n \r\n        <salaxy-datepicker-popup disabled=\"$ctrl.current.kind =='paidCalc'\" name=\"date\" ng-model=\"$ctrl.current.date\" label=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaidEditDialog.manualSalary.labelPaidAt\" ></salaxy-datepicker-popup>\r\n        <salaxy-datepicker-popup disabled=\"$ctrl.current.kind =='paidCalc'\" name=\"myDatepickerPopup\" ng-model=\"$ctrl.current.period.start\" ng-change=\"$ctrl.logic.updatePeriodDays($ctrl.current)\" label=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaidEditDialog.manualSalary.labelStartDate\" >\r\n        </salaxy-datepicker-popup>\r\n        <salaxy-datepicker-popup disabled=\"$ctrl.current.kind =='paidCalc'\" name=\"myDatepickerPopup\" ng-model=\"$ctrl.current.period.end\" ng-change=\"$ctrl.logic.updatePeriodDays($ctrl.current)\" label=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaidEditDialog.manualSalary.labelEndDate\">\r\n        </salaxy-datepicker-popup>\r\n        <salaxy-input-number disabled=\"true\" name=\"days\" label=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaidEditDialog.manualSalary.labelDaysCount\" ng-model=\"$ctrl.current.period.daysCount\" ></salaxy-input-number>\r\n        <salaxy-input-number disabled=\"$ctrl.current.kind =='paidCalc'\" name=\"holidayDays\" label=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaidEditDialog.manualSalary.labelUsedHolidays\" ng-model=\"$ctrl.current.holidayDays\" ng-change=\"$ctrl.logic.updateDaysCount($ctrl.current)\"></salaxy-input-number>\r\n        <salaxy-input-number disabled=\"$ctrl.current.kind =='paidCalc'\" ng-if=\"$ctrl.current.kind =='paidCalc' || $ctrl.current.kind =='manualSalary'\" name=\"holidaySalary\" label=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaidEditDialog.manualSalary.labelHolidaySalary\" ng-model=\"$ctrl.current.holidaySalary\" ></salaxy-input-number>\r\n        <salaxy-input-number disabled=\"$ctrl.current.kind =='paidCalc'\" ng-if=\"$ctrl.current.kind =='paidCalc' || $ctrl.current.kind =='manualCompensation'\" name=\"holidayCompensation\" label=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaidEditDialog.manualCompensation.labelCompensation\" ng-model=\"$ctrl.current.holidayCompensation\"></salaxy-input-number>\r\n        <salaxy-input-number disabled=\"$ctrl.current.kind =='paidCalc'\" ng-if=\"$ctrl.current.kind =='paidCalc' || $ctrl.current.kind =='manualBonus'\" name=\"holidayBonus\" label=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaidEditDialog.manualSalary.labelBonus\" ng-model=\"$ctrl.current.holidayBonus\"></salaxy-input-number>\r\n        <salaxy-input-boolean ng-if=\"$ctrl.current.kind =='paidCalc'\" type=\"switch\" name=\"isDisabled\" ng-model=\"$ctrl.current.isDisabled\" label=\"Poista käytöstä\" label-true=\"on\"\r\n          label-false=\"off\"></salaxy-input-boolean>\r\n        <salaxy-form-group name=\"calc\" label=\"SALAXY.ENUM.AnnualLeavePaymentKind.paidCalc.label\" ng-if=\"$ctrl.current.calcId\">\r\n            <a ng-href=\"{{$ctrl.logic.getPdfUrl($ctrl.current.calcId)}}\" target=\"_blank\" title=\"{{ 'SALAXY.UI_Terms.printable' | sxyTranslate}}\" class=\"btn btn-sm btn-secondary\"><i class=\"bi bi-file-earmark-pdf\"></i></a>\r\n        </salaxy-form-group>\r\n        <salaxy-input disabled=\"$ctrl.current.kind =='paidCalc'\" name=\"notes\" label=\"SALAXY.NG1.WorkerHolidaysComponent.HolidayYearPaidEditDialog.manualSalary.labelDescription\" ng-model=\"$ctrl.current.notes\"></salaxy-input>\r\n      </div>\r\n      <div>\r\n        <button ng-disabled=\"$ctrl.current.kind == 'undefined'\" type=\"submit\" class=\"btn btn-primary float-end\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n        <button type=\"reset\" class=\"btn btn-default float-end\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n        <button ng-disabled=\"$ctrl.current.kind == 'paidCalc' || $ctrl.current.kind == 'undefined'\" type=\"button\" class=\"btn btn-danger\" ng-click=\"$close('delete')\" sxy-text=\"SALAXY.UI_Terms.delete\"></button>\r\n      </div>\r\n    </form>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/holidays/WorkerHolidays-accrual.html\",`<div class=\"row\">\r\n  <div class=\"col-sm-9\">\r\n    <fieldset ng-if=\"$ctrl.viewType == 'overview'\">\r\n      <legend><span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.accrual.overview.legend\"></span> {{ $ctrl.current.year }}</legend>\r\n      <table class=\"salaxy-holidays-overview-table\">\r\n        <thead>\r\n          <tr>\r\n            <th class=\"year bg-{{year.style}}\" ng-repeat=\"year in $ctrl.getYearVisualisation().years\" colspan=\"{{ year.months }}\">{{ year.text }}</th>\r\n          </tr>\r\n          <tr>\r\n            <th ng-class=\"{ 'month': true, 'bg-primary': month%2, 'bg-danger': $index == $ctrl.getYearVisualisation().currentMonthIx }\" ng-repeat=\"month in $ctrl.getYearVisualisation().months track by $index\" class=\"text-end\">{{ month }}</th>\r\n          </tr>\r\n        </thead>\r\n        <tr ng-repeat=\"item in $ctrl.getYearVisualisation().items\">\r\n          <td class=\"month-empty\" ng-repeat=\"x in [].constructor(item.start) track by $index\"></td>\r\n          <td colspan=\"{{ item.months }}\">\r\n            <button class=\"btn btn-{{ item.style }} btn-block btn-sm\" ng-click=\"$ctrl.viewType = item.view\">{{ item.text }}</button>\r\n          </td>\r\n          <td class=\"month-empty\" ng-repeat=\"x in [].constructor(25 - item.start - item.months) track by $index\"></td>\r\n        </tr>\r\n      </table>\r\n      <h3 sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.accrual.overview.introTitle\"></h3>\r\n      <ol class=\"lead\">\r\n        <li sxy-html=\"SALAXY.NG1.WorkerHolidaysComponent.accrual.overview.introList.html\"></li>\r\n        <li sxy-html=\"SALAXY.NG1.WorkerHolidaysComponent.accrual.overview.introList2.html\"></li>\r\n        <li ng-if=\"$ctrl.getVisibility('hourly')\" sxy-html=\"SALAXY.NG1.WorkerHolidaysComponent.accrual.overview.introList3.html\"></li>\r\n        <li sxy-html=\"SALAXY.NG1.WorkerHolidaysComponent.accrual.overview.introList4.html\"></li>\r\n      </ol>\r\n    </fieldset>\r\n    <fieldset ng-if=\"$ctrl.viewType == 'parameters'\">\r\n      <ng-include src=\"'salaxy-components/worker/holidays/HolidayParametersForm.html'\"></ng-include>\r\n    </fieldset>\r\n    <fieldset ng-if=\"$ctrl.viewType == 'holidays'\">\r\n      <legend>\r\n        <button class=\"btn btn-primary btn-sm float-end\" ng-click=\"$ctrl.viewType = 'holidays-summer'\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.buttonSummer\"></button>\r\n        <span class=\"float-end\">&nbsp;</span>\r\n        <button class=\"btn btn-primary btn-sm float-end\" ng-click=\"$ctrl.viewType = 'holidays-winter'\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.buttonWinter\"></button>\r\n        <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.calendarTitle\"></span> {{ $ctrl.current.year}}\r\n      </legend>\r\n      <salaxy-holiday-year-holidays on-commit=\"$ctrl.save()\" parent=\"$ctrl.current\"></salaxy-holiday-year-holidays>\r\n    </fieldset>\r\n    <fieldset ng-if=\"$ctrl.viewType == 'holidays-summer'\">\r\n      <legend>\r\n        <button class=\"btn btn-primary btn-sm float-end\" ng-click=\"$ctrl.viewType = 'holidays'\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.buttonAll\"></button>\r\n        <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.summerHolidaysTitle\"></span> {{ $ctrl.current.year}}\r\n      </legend>\r\n      <salaxy-calendar data=\"[$ctrl.current]\" mapper=\"$ctrl.mapToCalendar\" on-list-select=\"$ctrl.calendarClick(type, date, calEvent)\" start=\"$ctrl.current.year + '-05-01'\" end=\"$ctrl.current.year + '-09-01'\"></salaxy-calendar>\r\n    </fieldset>\r\n    <fieldset ng-if=\"$ctrl.viewType == 'holidays-winter'\">\r\n      <legend>\r\n        <button class=\"btn btn-primary btn-sm float-end\" ng-click=\"$ctrl.viewType = 'holidays'\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.buttonAll\"></button>\r\n        <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.winterHolidaysTitle\"></span> {{ $ctrl.current.year}}\r\n      </legend>\r\n      <salaxy-calendar data=\"[$ctrl.current]\" mapper=\"$ctrl.mapToCalendar\" on-list-select=\"$ctrl.calendarClick(type, date, calEvent)\" start=\"$ctrl.current.year + '-10-01'\" end=\"(1 * $ctrl.current.year + 1) + '-04-01'\"></salaxy-calendar>\r\n    </fieldset>\r\n\r\n    <fieldset ng-if=\"$ctrl.viewType == 'paidHolidays'\">\r\n      <legend>\r\n        <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.accrual.paidSalaries.legend\"></span> {{ $ctrl.current.period | sxyDateRange }}\r\n      </legend>\r\n      <p sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.accrual.paidSalaries.description\"></p>\r\n\r\n      <ul sxy-html=\"SALAXY.NG1.WorkerHolidaysComponent.accrual.paidSalaries.descriptionList.html\"></ul>\r\n      <salaxy-holiday-year-paid parent=\"$ctrl.current\" on-commit=\"$ctrl.save()\"></salaxy-holiday-year-paid>\r\n    </fieldset>\r\n    <fieldset ng-if=\"$ctrl.viewType == 'accrual'\">\r\n      <legend>\r\n        <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.accrual.accrualHolidays.legend\"></span> {{ $ctrl.current.accrual.period | sxyDateRange }}\r\n      </legend>\r\n      <p>\r\n        <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.accrual.accrualHolidays.description\"></span> {{ $ctrl.current.year - 1 }}.\r\n        <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.accrual.accrualHolidays.description2\"></span> {{ $ctrl.current.year }}.\r\n      </p>\r\n      <salaxy-holiday-year-accrual parent=\"$ctrl.current\"></salaxy-holiday-year-accrual>\r\n    </fieldset>\r\n    <fieldset ng-if=\"$ctrl.viewType == 'hourlySalaries'\">\r\n      <legend>\r\n        <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.accrual.hourlySalaries.legend\"></span> {{ $ctrl.current.period | sxyDateRange }}\r\n      </legend>\r\n      <p sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.accrual.hourlySalaries.description\"></p>\r\n      <ul sxy-html=\"SALAXY.NG1.WorkerHolidaysComponent.accrual.hourlySalaries.descriptionList.html\"></ul>\r\n      <p sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.accrual.hourlySalaries.description2\"></p>\r\n    </fieldset>\r\n  </div>\r\n  <div class=\"col-sm-3\">\r\n    <div class=\"btn-group btn-block dropdown mb-4\">\r\n      <button id=\"year-selection\" type=\"button\" class=\"btn btn-primary btn-block dropdown-toggle\" data-bs-toggle=\"dropdown\">\r\n        {{ $ctrl.current ? ('SALAXY.NG1.WorkerHolidaysComponent.UI.dropdown.selectedYear' | sxyTranslate) + \" \" + $ctrl.current.year : ('SALAXY.NG1.WorkerHolidaysComponent.UI.dropdown.selectYear' | sxyTranslate)  }}\r\n      </button>\r\n      <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"single-button\">\r\n        <li role=\"menuitem\" ng-repeat=\"year in $ctrl.employmentHolidayYears\">\r\n          <a href=\"\" ng-click=\"$ctrl.model = year\" class=\"dropdown-item\" >{{ year.year }}</a>\r\n        </li>\r\n        <li role=\"menuitem\">\r\n          <a ng-href=\"#{{ $ctrl.getDefaults().listUrl }}\" class=\"dropdown-item\" ng-if=\"!($ctrl.employmentHolidayYears.length > 0)\" sxy-text=\"SALAXY.UI_Terms.back\"></a>\r\n        </li>\r\n        <li class=\"divider\"></li>\r\n        <li role=\"menuitem\" ng-if=\"$ctrl.missingHolidayYear\">\r\n          <a href=\"\" ng-click=\"$ctrl.showInitHolidays()\" class=\"dropdown-item\">{{\"SALAXY.UI_Terms.add\" | sxyTranslate}} {{\"SALAXY.NG1.WorkerHolidaysComponent.holidayCompensation.overview.legendYear\" | sxyTranslate}} {{$ctrl.missingHolidayYear}}</a>\r\n        </li>\r\n      </ul>\r\n    </div>\r\n    <salaxy-toggle-buttons ng-model=\"$ctrl.viewType\" \r\n      options=\"[\r\n        { value: 'overview', label: 'SALAXY.NG1.WorkerHolidaysComponent.UI.sidebar.buttonOverview' },\r\n        { value: 'parameters', label: 'SALAXY.NG1.WorkerHolidaysComponent.UI.sidebar.buttonSettings' },\r\n        { value: 'accrual', label: 'SALAXY.NG1.WorkerHolidaysComponent.UI.sidebar.buttonAccrual' },\r\n        { value: 'holidays', label: 'SALAXY.NG1.WorkerHolidaysComponent.UI.sidebar.buttonHolidays' },\r\n        { value: 'paidHolidays', label: 'SALAXY.NG1.WorkerHolidaysComponent.UI.sidebar.buttonPaidHolidays' }\r\n        ]\" \r\n      type=\"block\">\r\n    </salaxy-toggle-buttons>\r\n    <p>&nbsp;</p>\r\n    <fieldset ng-if=\"$ctrl.current\">\r\n      <legend sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.sidebar.info\"></legend>\r\n      <div>{{ \"WageBasis.\" + $ctrl.current.spec.wageBasis | sxyEnum }}</div>\r\n      <div>{{ \"HolidayCode.\" + $ctrl.current.spec.code | sxyEnum }}</div>\r\n      <div ng-if=\"$ctrl.getVisibility('accrual')\">\r\n        {{'SALAXY.NG1.WorkerHolidaysComponent.UI.sidebar.periodAccrual' | sxyTranslate}}<br />{{ $ctrl.current.accrual.period | sxyDateRange }}</div>\r\n      <div><span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.sidebar.periodSelectedYear\"></span>\r\n        <br />{{ $ctrl.current.period | sxyDateRange }}\r\n      </div>\r\n      <div ng-if=\"$ctrl.getVisibility('accrual')\">\r\n        <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.sidebar.periodDefaultAccrual\"></span> {{ $ctrl.current.accrual.defaultAccrual | sxyCount : 'day' }}\r\n      </div>\r\n      <div ng-if=\"$ctrl.getVisibility('compensation')\">\r\n        <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.sidebar.compensation\"></span> {{ $ctrl.current.spec.compensation | sxyCount : 'percent' }}\r\n      </div>\r\n      <div ng-if=\"$ctrl.current.spec.bonusMethod != 'none'\">\r\n        <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.sidebar.bonus\"></span> {{ $ctrl.current.spec.bonus | sxyCount : 'percent' }}\r\n      </div>\r\n      <div ng-if=\"$ctrl.current.spec.bonusMethod == 'none'\">{{ \"HolidayBonusPaymentMethod.\" + $ctrl.current.spec.bonusMethod | sxyEnum }} </div>\r\n    </fieldset>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/holidays/WorkerHolidays-holidayCompensation.html\",`<div class=\"row\">\r\n  <div class=\"col-sm-9\">\r\n    <fieldset ng-if=\"$ctrl.viewType == 'overview'\">\r\n      <legend>\r\n        <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.holidayCompensation.overview.legend\"></span> (\r\n        <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.holidayCompensation.overview.legendYear\"></span> {{$ctrl.current.year}})\r\n      </legend>\r\n      <p class=\"lead\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.holidayCompensation.overview.intro\"></p>\r\n      <ul class=\"lead\">\r\n        <li>\r\n          <strong sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.holidayCompensation.overview.intro2\"></strong>\r\n          <ul>\r\n            <li> <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.holidayCompensation.overview.introCompensation\"></span>{{ $ctrl.current.spec.compensation | sxyCount : 'percent' }}</li>\r\n            <li ng-if=\"$ctrl.current.spec.bonusMethod != 'none'\"><span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.holidayCompensation.overview.introBonus\"></span> {{ $ctrl.current.spec.bonus | sxyCount : 'percent' }}</li>\r\n            <li ng-if=\"$ctrl.current.spec.bonusMethod == 'none'\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.holidayCompensation.overview.introNoBonus\"></li>\r\n          </ul>\r\n        </li>\r\n      </ul>\r\n    </fieldset>\r\n    <fieldset ng-if=\"$ctrl.viewType == 'parameters'\">\r\n      <ng-include src=\"'salaxy-components/worker/holidays/HolidayParametersForm.html'\"></ng-include>\r\n    </fieldset>\r\n    <fieldset ng-if=\"$ctrl.viewType == 'holidays'\">\r\n      <legend>\r\n        <button class=\"btn btn-primary btn-sm float-end\" ng-click=\"$ctrl.viewType = 'holidays-summer'\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.buttonSummer\"></button>\r\n        <span class=\"float-end\">&nbsp;</span>\r\n        <button class=\"btn btn-primary btn-sm float-end\" ng-click=\"$ctrl.viewType = 'holidays-winter'\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.buttonWinter\"></button>\r\n        <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.calendarTitle\"></span> {{ $ctrl.current.year}}\r\n      </legend>\r\n      <salaxy-holiday-year-holidays on-commit=\"$ctrl.save()\" parent=\"$ctrl.current\"></salaxy-holiday-year-holidays>\r\n    </fieldset>\r\n    <fieldset ng-if=\"$ctrl.viewType == 'holidays-summer'\">\r\n      <legend>\r\n        <button class=\"btn btn-primary btn-sm float-end\" ng-click=\"$ctrl.viewType = 'holidays'\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.buttonAll\"></button>\r\n        <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.summerHolidaysTitle\"></span> {{ $ctrl.current.year}}\r\n      </legend>\r\n      <salaxy-calendar data=\"[$ctrl.current]\" mapper=\"$ctrl.mapToCalendar\" on-list-select=\"$ctrl.calendarClick(type, date, calEvent)\" start=\"$ctrl.current + '-05-01'\" end=\"$ctrl.current + '-09-01'\"></salaxy-calendar>\r\n    </fieldset>\r\n    <fieldset ng-if=\"$ctrl.viewType == 'holidays-winter'\">\r\n      <legend>\r\n        <button class=\"btn btn-primary btn-sm float-end\" ng-click=\"$ctrl.viewType = 'holidays'\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.buttonAll\"></button>\r\n        <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.winterHolidaysTitle\"></span> {{ $ctrl.current.year}}\r\n      </legend>\r\n      <salaxy-calendar data=\"[$ctrl.current]\" mapper=\"$ctrl.mapToCalendar\" on-list-select=\"$ctrl.calendarClick(type, date, calEvent)\" start=\"$ctrl.current + '-10-01'\" end=\"(1 * $ctrl.current + 1) + '-04-01'\"></salaxy-calendar>\r\n    </fieldset>\r\n  </div>\r\n  <div class=\"col-sm-3\">\r\n    <div class=\"btn-group btn-block dropdown\">\r\n      <button id=\"year-selection\" type=\"button\" class=\"btn btn-primary btn-block dropdown-toggle\" data-bs-toggle=\"dropdown\">\r\n        {{ $ctrl.current ? ('SALAXY.NG1.WorkerHolidaysComponent.UI.dropdown.selectedYear' | sxyTranslate) + \" \" +  $ctrl.current.year : ('SALAXY.NG1.WorkerHolidaysComponent.UI.dropdown.selectYear' | sxyTranslate) }}\r\n      </button>\r\n      <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"single-button\">\r\n        <li role=\"menuitem\"  ng-repeat=\"year in $ctrl.employmentHolidayYears\" >\r\n          <a href=\"\" ng-click=\"$ctrl.model = year\" class=\"dropdown-item\">{{ year.year }}</a></li>\r\n        <li role=\"menuitem\">\r\n          <a ng-href=\"#{{ $ctrl.getDefaults().listUrl }}\" ng-if=\"!($ctrl.employmentHolidayYears.length > 0)\" class=\"dropdown-item\" sxy-text=\"SALAXY.UI_Terms.back\"></a></li>\r\n        <li class=\"divider\"></li>\r\n        <li role=\"menuitem\" ng-if=\"$ctrl.missingHolidayYear\">\r\n          <a href=\"\" ng-click=\"$ctrl.showInitHolidays()\" class=\"dropdown-item\">{{\"SALAXY.UI_Terms.add\" | sxyTranslate}} {{\"SALAXY.NG1.WorkerHolidaysComponent.holidayCompensation.overview.legendYear\" | sxyTranslate}} {{$ctrl.missingHolidayYear}}</a>\r\n        </li>\r\n      </ul>\r\n    </div>\r\n    <p>&nbsp;</p>\r\n    <salaxy-toggle-buttons ng-model=\"$ctrl.viewType\" options=\"[\r\n      { value: 'overview', label: 'SALAXY.NG1.WorkerHolidaysComponent.UI.sidebar.buttonOverview' },\r\n      { value: 'parameters', label: 'SALAXY.NG1.WorkerHolidaysComponent.UI.sidebar.buttonSettings' },\r\n      ]\" type=\"block\"></salaxy-toggle-buttons>\r\n    <p>&nbsp;</p>\r\n    <fieldset ng-if=\"$ctrl.current\">\r\n      <legend sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.sidebar.info\"></legend>\r\n      <div>{{ \"HolidayCode.\" + $ctrl.current.spec.code | sxyEnum }}</div>\r\n      <div><span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.sidebar.periodSelectedYear\"></span><br />{{ $ctrl.current.period | sxyDateRange }}</div>\r\n      <div><span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.sidebar.compensation\"></span> {{ $ctrl.current.spec.compensation | sxyCount : 'percent' }}</div>\r\n      <div ng-if=\"$ctrl.current.spec.bonusMethod != 'none'\">\r\n        <span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.sidebar.bonus\"></span> {{ $ctrl.current.spec.bonus | sxyCount : 'percent' }}\r\n      </div>\r\n      <div ng-if=\"$ctrl.current.spec.bonusMethod == 'none'\">{{ \"HolidayBonusPaymentMethod.\" + $ctrl.current.spec.bonusMethod | sxyEnum }} </div>\r\n    </fieldset>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/holidays/WorkerHolidays-noHolidays.html\",`<div class=\"row\">\r\n  <div class=\"col-sm-9\">\r\n    <fieldset ng-if=\"$ctrl.viewType == 'overview'\">\r\n      <legend><span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.noHolidays.legend\"></span>{{ $ctrl.current.year }}</legend>\r\n      <p class=\"lead\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.noHolidays.intro\"></p>\r\n    </fieldset>\r\n    <fieldset ng-if=\"$ctrl.viewType == 'parameters'\">\r\n      <ng-include src=\"'salaxy-components/worker/holidays/HolidayParametersForm.html'\"></ng-include>\r\n    </fieldset>\r\n  </div>\r\n  <div class=\"col-sm-3\">\r\n    <div class=\"btn-group btn-block dropdown\">\r\n      <button id=\"year-selection\" type=\"button\" class=\"btn btn-primary btn-block dropdown-toggle\" data-bs-toggle=\"dropdown\">\r\n        {{ $ctrl.current ? ('SALAXY.NG1.WorkerHolidaysComponent.UI.dropdown.selectedYear' | sxyTranslate) + \" \" + $ctrl.current.year : ('SALAXY.NG1.WorkerHolidaysComponent.UI.dropdown.selectYear' | sxyTranslate) }}\r\n      </button>\r\n      <ul class=\"dropdown-menu\"  role=\"menu\" aria-labelledby=\"single-button\">\r\n        <li role=\"menuitem\" ng-repeat=\"year in $ctrl.employmentHolidayYears\">\r\n          <a href=\"\" ng-click=\"$ctrl.model = year\" class=\"dropdown-item\">{{ year.year }}</a>\r\n        </li>\r\n        <li role=\"menuitem\">\r\n          <a ng-href=\"#{{ $ctrl.getDefaults().listUrl }}\" ng-if=\"!($ctrl.employmentHolidayYears.length > 0)\" class=\"dropdown-item\" sxy-text=\"SALAXY.UI_Terms.back\"></a>\r\n        </li>\r\n        <li class=\"divider\"></li>\r\n        <li role=\"menuitem\" ng-if=\"$ctrl.missingHolidayYear\">\r\n          <a href=\"\" ng-click=\"$ctrl.showInitHolidays()\" class=\"dropdown-item\">{{\"SALAXY.UI_Terms.add\" | sxyTranslate}} {{\"SALAXY.NG1.WorkerHolidaysComponent.holidayCompensation.overview.legendYear\" | sxyTranslate}} {{$ctrl.missingHolidayYear}}</a>\r\n        </li>\r\n      </ul>\r\n    </div>\r\n    <p>&nbsp;</p>\r\n    <salaxy-toggle-buttons ng-model=\"$ctrl.viewType\" options=\"[{ value: 'parameters', label: 'SALAXY.NG1.WorkerHolidaysComponent.UI.sidebar.buttonSettings' }]\" type=\"block\"></salaxy-toggle-buttons>\r\n    <fieldset ng-if=\"$ctrl.current\">\r\n      <legend sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.sidebar.info\"></legend>\r\n      <div>{{ \"HolidayCode.\" + $ctrl.current.spec.code | sxyEnum }}</div>\r\n      <div><span sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.UI.sidebar.periodSelectedYear\"></span><br />{{ $ctrl.current.period | sxyDateRange }}</div>\r\n    </fieldset>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/holidays/WorkerHolidays-undefined.html\",`<div class=\"salaxy-placeholder-empty placeholder-md\">\r\n  <h3 sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.undefined.title\"></h3>\r\n  <button class=\"btn btn-primary\" ng-click=\"$ctrl.showInitHolidays()\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.undefined.showInitHolidaysButtonText\"></button>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/holidays/WorkerHolidays.html\",`<div class=\"salaxy-component salaxy-worker-holidays\">\r\n  <ng-include ng-if=\"!$ctrl.current\" src=\"'salaxy-components/worker/holidays/WorkerHolidays-undefined.html'\"></ng-include>\r\n  <ng-include ng-if=\"$ctrl.current.spec.code == 'holidayCompensation'\" src=\"'salaxy-components/worker/holidays/WorkerHolidays-holidayCompensation.html'\"></ng-include>\r\n  <ng-include ng-if=\"($ctrl.current && !$ctrl.current.spec.code) || $ctrl.current.spec.code == 'undefined' || $ctrl.current.spec.code == 'permanent14Days' || $ctrl.current.spec.code == 'permanent35Hours' || $ctrl.current.spec.code == 'temporaryTimeOff' || $ctrl.current.spec.code == 'other' || $ctrl.current.spec.code == 'script'\" src=\"'salaxy-components/worker/holidays/WorkerHolidays-accrual.html'\"></ng-include>\r\n  <ng-include ng-if=\"$ctrl.current.spec.code == 'noHolidays'\" src=\"'salaxy-components/worker/holidays/WorkerHolidays-noHolidays.html'\"></ng-include>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/holidays/WorkerHolidaysInitDialog.html\",`<div class=\"salaxy-component salaxy-holidays-init-dialog\" ng-init=\"$ctrl.current.code = 'permanent14Days'\">\r\n  <form class=\"form-horizontal\" name=\"holidayForm\">\r\n    <div class=\"modal-content card-primary\">\r\n      <div class=\"modal-header d-flex\">\r\n        <div>\r\n          <h2 sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.panelHeading\"></h2>\r\n          <p sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.intro\"></p>\r\n        </div>\r\n        <button type=\"button\" class=\"btn-close ms-auto align-self-start\" data-dismiss=\"alert\" ng-click=\"$close('cancel')\" aria-label=\"Close\"></button>\r\n      </div>\r\n      <div class=\"modal-body\">\r\n        <div class=\"row form-horizontal\">\r\n          <div class=\"col-sm-6\">\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.legendSelectHolidayType\"></legend>\r\n              <div class=\"radio mb-1\">\r\n                <label class=\"d-flex align-items-start\">\r\n                  <input type=\"radio\"  ng-model=\"$ctrl.current.code\" name=\"code\" id=\"permanent14Days\" value=\"permanent14Days\" class=\"mt-1 me-2\"> \r\n                  <span sxy-html=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.permanent14Days.html\"></span>\r\n                </label>\r\n              </div>\r\n              <div class=\"radio mb-1\">\r\n                <label class=\"d-flex align-items-start\">\r\n                  <input type=\"radio\" ng-model=\"$ctrl.current.code\" name=\"code\" id=\"permanent35Hours\" value=\"permanent35Hours\" class=\"mt-1 me-2\">\r\n                  <span sxy-html=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.permanent35Hours.html\"></span>\r\n                </label>\r\n              </div>\r\n              <div class=\"radio mb-1\">\r\n                <label class=\"d-flex align-items-start\">\r\n                  <input type=\"radio\" ng-model=\"$ctrl.current.code\" name=\"code\" id=\"holidayCompensation\" value=\"holidayCompensation\" class=\"mt-1 me-2\">\r\n                  <span sxy-html=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.holidayCompensation.html\"></span>\r\n                </label>\r\n              </div>\r\n              <div class=\"radio mb-1\">\r\n                <label class=\"d-flex align-items-start\">\r\n                  <input type=\"radio\" ng-model=\"$ctrl.current.code\" name=\"code\" id=\"temporaryTimeOff\" value=\"temporaryTimeOff\" class=\"mt-1 me-2\">\r\n                  <span sxy-html=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.temporaryTimeOff.html\"></span>\r\n                </label>\r\n              </div>\r\n              <div class=\"radio mb-1\">\r\n                <label class=\"d-flex align-items-start\">\r\n                  <input type=\"radio\" ng-model=\"$ctrl.current.code\" name=\"code\" id=\"other\" value=\"other\" class=\"mt-1 me-2\">\r\n                  <span sxy-html=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.other.html\"></span>\r\n                </label>\r\n              </div>\r\n              <div class=\"radio mb-1\" ng-if=\"'bizConfigs' | sxyIsInRole\">\r\n                <label class=\"d-flex align-items-start\">\r\n                  <input type=\"radio\" ng-model=\"$ctrl.current.code\" name=\"code\" id=\"script\" value=\"script\" class=\"mt-1 me-2\">\r\n                  <span sxy-html=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.script.html\"></span>\r\n                </label>\r\n              </div>\r\n              <div class=\"radio mb-1\">\r\n                <label class=\"d-flex align-items-start\">\r\n                  <input type=\"radio\" ng-model=\"$ctrl.current.code\" name=\"code\" id=\"noHolidays\" value=\"noHolidays\" class=\"mt-1 me-2\">\r\n                  <span sxy-html=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.noHolidays.html\"></span>\r\n                </label>\r\n              </div>\r\n            </fieldset>\r\n          </div>\r\n          <div class=\"col-sm-6\">\r\n            <fieldset>\r\n              <legend sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.legendDetails\"></legend>\r\n              <div ng-if=\"$ctrl.logic.getVisibility($ctrl.current, 'accrualFixed')\">\r\n                <salaxy-input-boolean type=\"checkbox\" name=\"accrualByLaw\" label=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.accrualByLaw\" label-true=\"{{ 'SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.accrualByLawLabelTrue' + ($ctrl.current.code == 'temporaryTimeOff' ? '2' : '') }}\"\r\n                  ng-change=\"$ctrl.logic.accrualByLawChanged($ctrl.current)\" ng-model=\"$ctrl.logic.accrualByLaw\"></salaxy-input-boolean>\r\n                <salaxy-input-number ng-model=\"$ctrl.current.accrualFixed\" name=\"accrualFixed\" ng-if=\"$ctrl.current.accrualFixed\" ng-change=\"$ctrl.logic.accrualFixedChanged($ctrl.current)\" label=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.accrualFixed\" unit=\"days\">\r\n                </salaxy-input-number>\r\n              </div>\r\n              <salaxy-input-number ng-model=\"$ctrl.current.compensation\" name=\"compensation\" ng-if=\"$ctrl.logic.getVisibility($ctrl.current, 'compensation')\" required label=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.compensation\" unit=\"percent\"></salaxy-input-number>\r\n              <salaxy-input-enum name=\"bonusMethod\" ng-model=\"$ctrl.current.bonusMethod\" ng-if=\"$ctrl.logic.getVisibility($ctrl.current, 'bonusMethod')\" label=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.bonusMethod\" filter=\"none,payForHolidaySalary,paySelectedDays\" enum=\"HolidayBonusPaymentMethod\"></salaxy-input-enum>\r\n              <salaxy-input-enum name=\"bonusMethod\" ng-model=\"$ctrl.current.bonusMethod\" ng-if=\"$ctrl.logic.getVisibility($ctrl.current, 'compensation')\" label=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.bonusMethod\" options=\"{ 'none': ('SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.bonusMethodNone' | sxyTranslate), 'payForHolidaySalary': ('SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.bonusMethodPayForHolidaySalary' | sxyTranslate)  }\">\r\n              </salaxy-input-enum>\r\n              <salaxy-input-number ng-model=\"$ctrl.current.bonus\" name=\"bonus\" ng-if=\"$ctrl.logic.getVisibility($ctrl.current, 'bonusPercent')\" label=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.bonusPercent\" unit=\"percent\"></salaxy-input-number>\r\n              <div ng-if=\"$ctrl.logic.getVisibility($ctrl.current, 'accruesHolidays')\">\r\n                <salaxy-input-enum required name=\"wageBasis\" ng-model=\"$ctrl.current.wageBasis\" label=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.label.wageBasis\" enum=\"WageBasis\" hidden-options=\"undefined,other,script\"></salaxy-input-enum>\r\n                <salaxy-input-enum name=\"holidayPayCalculation\" ng-model=\"$ctrl.current.holidayPayCalculation\" label=\"SALAXY.MODEL.HolidaySpecificationForYear.holidayPayCalculation.title\" options=\"$ctrl.logic.getholidayPayCalculationOptions($ctrl.current)\" required disable-cache=\"true\"></salaxy-input-enum>\r\n\r\n                <salaxy-input-number ng-model=\"$ctrl.current.compensation\" name=\"compensation\" ng-if=\"($ctrl.current.code == 'temporaryTimeOff' || $ctrl.current.code == 'other' || $ctrl.current.code == 'script')  && $ctrl.current.holidayPayCalculation == 'holidayCompensation'\" unit=\"percent\" required label=\"SALAXY.MODEL.HolidaySpecificationForYear.compensation.title\" ></salaxy-input-number>\r\n                <salaxy-input-number ng-model=\"$ctrl.current.holidayPayPercent\" name=\"holidayPayPercent\" ng-if=\"($ctrl.current.code == 'permanent35Hours' || $ctrl.current.code == 'other' || $ctrl.current.code == 'script') && $ctrl.current.holidayPayCalculation == 'percentageBasedPay'\" required unit=\"percent\" label=\"SALAXY.MODEL.HolidaySpecificationForYear.holidayPayPercent.title\" ></salaxy-input-number>\r\n              \r\n                <salaxy-form-group label=\"SALAXY.MODEL.HolidaySpecificationForYear.employmentPeriod.title\" name=\"contract\">\r\n                  <salaxy-datepicker-popup require=\"true\" name=\"startDate\" label=\"SALAXY.NG1.WorkerWizardComponent.employment.group.startDate\" ng-model=\"$ctrl.current.employmentPeriod.start\"></salaxy-datepicker-popup>\r\n                  <salaxy-datepicker-popup name=\"endDate\" label=\"SALAXY.NG1.WorkerWizardComponent.employment.group.endDate\" ng-model=\"$ctrl.current.employmentPeriod.end\"></salaxy-datepicker-popup>\r\n                </salaxy-form-group>\r\n              </div>\r\n            </fieldset>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div class=\"modal-footer\">\r\n        <button type=\"submit\" class=\"btn btn-primary float-end\" ng-disabled=\"holidayForm.$invalid\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.NG1.WorkerHolidaysComponent.InitDialog.submitButtonText\"></button>\r\n        <button type=\"button\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.UI_Terms.cancel\"></button>\r\n      </div>\r\n    </div>\r\n  </form>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/HourlyReportEditDialog.html\",`<div class=\"salaxy-component salaxy-timer-dialog\">\r\n  <div>\r\n    <div class=\"modal-header\">\r\n      <h2 sxy-text=\"Muokkaa tuntikirjausta\"></h2>\r\n      <button type=\"button\" class=\"btn-close\" ng-click=\"$dismiss()\" aria-label=\"Close\"></button>\r\n    </div>\r\n    <div class=\"modal-body\">\r\n      <form class=\"form-horizontal\">\r\n        <div class=\"row\">\r\n          <div class=\"col-sm-6 col-12\">\r\n            <salaxy-input-typeahead ng-if=\"$ctrl.logic.costAccountingSettings\" label-format=\"text-value\" name=\"options_project\" ng-model=\"$ctrl.current.contentData.project\" options=\"$ctrl.logic.costAccountingSettings.options\" label=\"{{($ctrl.logic.costAccountingSettings.label || 'SALAXY.NG1.CalcCostAccountingComponent.defaultLabel') | sxyTranslate}}\" required=\"true\"></salaxy-input-typeahead>\r\n          </div>\r\n          <div class=\"col-sm-6 col-12\">\r\n            <salaxy-input name=\"message\" ng-model=\"$ctrl.current.contentData.projectText\" label=\"Kommentti\"></salaxy-input>\r\n          </div>\r\n          <div class=\"col-sm-6 col-12\">\r\n            <salaxy-input-time name=\"startTime\" label=\"Työaika\" type=\"minutes\" ng-model=\"$ctrl.current.contentData.totalTime\"></salaxy-input-time>\r\n          </div>\r\n          <div class=\"col-sm-6 col-12\">\r\n            <salaxy-input-number label=\"Työaika\" type=\"slider\" name=\"slider\" minimum=\"10\" maximum=\"720\" slider-step=\"5\" ng-model=\"$ctrl.current.contentData.totalTime\"></salaxy-input-number>\r\n          </div>\r\n        </div>\r\n      </form>\r\n    </div>\r\n    <div class=\"modal-footer\">\r\n      <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.NG1.AbsencePeriodsEditDialog.cancelButtonText\"></button>\r\n      <button type=\"submit\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.ok\"></button>\r\n\r\n      <button type=\"button\" class=\"btn btn-danger float-start\" ng-click=\"$close('delete')\" sxy-text=\"SALAXY.NG1.AbsencePeriodsEditDialog.deleteButtonText\"></button>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/taxcard/EmploymentTaxcards.html\",`﻿<div class=\"salaxy-component salaxy-employment-taxcards\">\r\n  <div ng-if=\"!$ctrl.current\">\r\n    <div class=\"alert alert-warning\" ng-if=\"!$ctrl.employmentId\">\r\n      <p sxy-text=\"SALAXY.NG1.WorkerTaxCardsComponent.instruction\"></p>\r\n    </div>\r\n    <salaxy-spinner ng-if=\"$ctrl.employmentId\"></salaxy-spinner>\r\n  </div>\r\n  <div ng-if=\"$ctrl.current\">\r\n    <div class=\"alert alert-warning\" ng-if=\"!$ctrl.current.personalId\">\r\n      <p sxy-text=\"SALAXY.NG1.WorkerTaxCardsComponent.error\"></p>\r\n    </div>\r\n    <div ng-if=\"$ctrl.mode != 'list'\">\r\n      <salaxy-tab-buttons\r\n        current-tab=\"$ctrl.currentTab\"\r\n        options=\"[\r\n          { value: 'taxcarddetails', text: 'SALAXY.NG1.WorkerDetailsComponent.currentTaxCard' },\r\n          { value: 'taxcardcalcs', text: 'SALAXY.NG1_PagesPersonal.taxcards.calcsPaidForCardTabHeading', hidden: !$ctrl.current.active },\r\n        ]\"\r\n        tabs-id=\"employmentTaxcards\">\r\n      </salaxy-tab-buttons>\r\n      <div class=\"tab-content\" id=\"tab-content-employmentTaxcards\">\r\n        <div class=\"tab-pane\" id=\"taxcarddetails-tab\">\r\n          <salaxy-taxcard-details model=\"$ctrl.current.active\" ng-ref=\"$ctrl.$active\" personal-id=\"$ctrl.current.personalId\" on-save=\"$ctrl.reload();$ctrl.onSave()\" hide-buttons=\"$ctrl.hideButtons\" employment-relation-taxcard-type=\"$ctrl.current.employmentTaxcard\"></salaxy-taxcard-details>\r\n        </div>\r\n        <div class=\"tab-pane\" id=\"taxcardcalcs-tab\" ng-if=\"$ctrl.current.active\">\r\n          <div class=\"alert alert-info\" ng-if=\"$ctrl.$incomeLog.hasDiff\">\r\n            <button type=\"button\" class=\"btn btn-primary float-end\" ng-click=\"$ctrl.$active.commitDiff()\" sxy-text=\"SALAXY.NG1.EmploymentTaxcardsComponent.taxCardIncomeLog.addSalaries\"></button>\r\n            <span sxy-text=\"SALAXY.NG1.EmploymentTaxcardsComponent.taxCardIncomeLog.addSalariesToTaxCard\" params=\"{validity: ($ctrl.current.active.card.validity | sxyDateRange)}\">\r\n            </span>\r\n          </div>\r\n          <salaxy-taxcard-income-log parent=\"$ctrl.current.active\" editable=\"false\" ng-ref=\"$ctrl.$incomeLog\"></salaxy-taxcard-income-log>\r\n          <div class=\"text-end\">\r\n            <button type=\"button\" class=\"btn btn-default btn-xs\" ng-click=\"$ctrl.editIncomeLog()\" sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.edit\"></button>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"row form-horizontal\" sxy-if-role=\"test\">\r\n      <div class=\"col-8\">\r\n        <salaxy-datepicker-popup name=\"today\" ng-model=\"$ctrl.today\" label=\"Maksupäivän testaus\" ng-change=\"\"></salaxy-datepicker-popup>\r\n      </div>\r\n      <div class=\"col-4\">\r\n        <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.reload()\">Vaihda (TEST)</button>\r\n      </div>\r\n    </div>\r\n    <div ng-if=\"$ctrl.mode != 'active' && $ctrl.list.length > 0\">\r\n      <h3 ng-if=\"$ctrl.mode != 'list'\" sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.historyTaxCard\"></h3>\r\n      <div class=\"table-responsive\">\r\n        <table class=\"table table-striped\">\r\n          <thead>\r\n            <tr>\r\n              <th class=\"th-xxs\">\r\n                <span sxy-text=\"SALAXY.NG1.WorkerTaxCardsComponent.type\"></span>\r\n                <span class=\"d-inline d-md-none\" sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.taxPercent\"></span>\r\n                <span class=\"d-inline d-md-none\" sxy-text=\"SALAXY.NG1.WorkerTaxCardsComponent.percentAfterIncomeLimit\"></span>\r\n              </th>\r\n              <th class=\"d-none d-md-table-cell\" sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.year\"></th>\r\n              <th class=\"d-none d-md-table-cell tax-percentage right\" sxy-text=\"SALAXY.NG1.WorkerDetailsComponent.taxPercent\"></th>\r\n              <th class=\"th-xxs salaries-paid right\">\r\n                <span sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.salariesPaid\"></span>\r\n                <span class=\"d-inline d-md-none\" sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.incomeLimit\"></span>\r\n              </th>\r\n              <th class=\"d-none d-md-table-cell income-limit right\">\r\n                <span sxy-text=\"SALAXY.NG1.WorkerTaxCardsComponent.incomeLimit\"></span><br /><span sxy-text=\"SALAXY.NG1.WorkerTaxCardsComponent.incomeLimitSpan\"></span>\r\n\r\n              </th>\r\n              <th class=\"th-xxs right\" sxy-html=\"SALAXY.NG1.WorkerDetailsComponent.validHtml\"></th>\r\n              <th></th>\r\n              <th sxy-if-role=\"test,admin\"></th>\r\n            </tr>\r\n          </thead>\r\n          <tbody>\r\n            <tr ng-repeat=\"taxCard in $ctrl.list\">\r\n              <td>\r\n                <span class=\"d-inline d-md-none\">\r\n                  <i>{{ \"TaxcardKind.\" + taxCard.data.kind | sxyEnum }} {{ taxCard.data.forYear }}</i>\r\n                  {{taxCard.data.taxPercent}} %\r\n                  <span ng-if=\"taxCard.data.taxPercent2 != null\">({{ taxCard.data.taxPercent2 }} %)</span>\r\n                </span>\r\n                <span class=\"d-none d-md-table-cell\">\r\n                  <b>{{ \"TaxcardKind.\" + taxCard.data.kind | sxyEnum }}</b>\r\n                </span>\r\n              </td>\r\n              <td class=\"d-none d-md-table-cell\">{{ taxCard.data.forYear }}</td>\r\n              <td class=\"d-none d-md-table-cell tax-percentage right\">{{taxCard.data.taxPercent}} %</td>\r\n              <td class=\"salaries-paid right\">\r\n                {{ taxCard.data.totalIncome | currency: ' €' : 0 }}\r\n                <span class=\"d-inline d-md-none\">{{(taxCard.data.incomeLimit | currency: ' €' : 0) || '-'}}</span>\r\n              </td>\r\n              <td class=\"d-none d-md-table-cell income-limit right\">\r\n                {{(taxCard.data.incomeLimit | currency: '€' : 0) || '-'}}<br />\r\n                <span>{{taxCard.data.taxPercent2 != null ? (taxCard.data.taxPercent2 + ' %') : '-'}}</span>\r\n              </td>\r\n              <td class=\"right\">\r\n                {{ taxCard.data | sxyDateRange }}<br /> {{ taxCard.createdAt | sxyDate }}\r\n              </td>\r\n              <td class=\"middle text-center\">\r\n                <span ng-if=\"!taxCard.isReadOnly && !$ctrl.hideButtons\">\r\n                  <button class=\"btn btn-danger btn-sm\" ng-click=\"$ctrl.deleteTaxCard(taxCard.id)\">\r\n                    <span class=\"d-none d-sm-inline\" sxy-text=\"SALAXY.UI_Terms.delete\"></span>\r\n                    <span class=\"d-inline d-sm-none\">&times;</span>\r\n                  </button>\r\n                </span>\r\n              </td>\r\n              <td class=\"middle text-center\" sxy-if-role=\"test,admin,pro\">\r\n                <a type=\"button\" class=\"edit btn btn-sm btn-default\" href=\"#/taxcards/details/{{taxCard.id}}\"><i class=\"bi bi-pencil-square\"></i></a>\r\n              </td>\r\n            </tr>\r\n          </tbody>\r\n        </table>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/taxcard/TaxcardDetails.html\",`<div class=\"salaxy-component salaxy-taxcard-details\">\r\n\r\n  <form name=\"editForm\">\r\n    <div ng-show=\"false\" ng-init=\"$ctrl.editForm = editForm\"></div>\r\n    <!-- TODO: See if this is in use in pro. It is probably in use in Admin. -->\r\n    <div ng-if=\"$ctrl.getMode() == 'pro'\" ng-include=\"'salaxy-components/worker/taxcard/TaxcardDetails_Pro.html'\"></div>\r\n    <div ng-if=\"$ctrl.getMode() == 'new'\" class=\"alert alert-danger\">\r\n      <h3>Error: Disabled</h3>\r\n      <p>Adding a new taxcard in details view is diabled.</p>\r\n    </div>\r\n    <div ng-if=\"$ctrl.getMode() == 'default'\" ng-include=\"'salaxy-components/worker/taxcard/TaxcardDetails_Info.html'\"></div>\r\n    <div ng-if=\"$ctrl.getMode() == 'null'\" class=\"salaxy-placeholder-empty placeholder-md text-center\">\r\n      <div ng-if=\"$ctrl.employmentRelationTaxcardType != 'auto'\">\r\n        <h4 sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.noTaxCardAddedWorker\" ng-if=\"$ctrl.employmentId == 'self'\"></h4>\r\n        <h4 sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.noTaxCardAdded\" ng-if=\"$ctrl.employmentId != 'self'\"></h4>\r\n        <button class=\"btn btn-primary\" ng-if=\"!$ctrl.hideButtons\" ng-disabled=\"$ctrl.loaders['showAddNew']\" ng-click=\"$ctrl.showAddNew()\" sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.addTaxCard\"></button>\r\n      </div>\r\n      <div ng-if=\"$ctrl.employmentRelationTaxcardType == 'auto'\">\r\n        <button class=\"btn btn-primary\" ng-if=\"!$ctrl.hideButtons\" ng-disabled=\"$ctrl.loaders['showSetAuto']\" ng-click=\"$ctrl.setAuto()\" sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.searchTaxCard\"></button>  \r\n      </div>\r\n    </div>\r\n    <div ng-if=\"$ctrl.getMode() == 'no-personal-id'\" class=\"alert alert-danger\" sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.noPersonalIdError\"></div>\r\n  </form>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/taxcard/TaxcardDetails_Info.html\",`<div>\r\n  <div ng-if=\"$ctrl.isTaxCardExpired($ctrl.current)\" class=\"salaxy-placeholder-empty placeholder-md placeholder-danger text-center\">\r\n    <h4 sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.taxCardExpired\"></h4>\r\n    <button class=\"btn btn-primary\" ng-if=\"!$ctrl.hideButtons\" ng-disabled=\"$ctrl.loaders['showAddNew']\" ng-click=\"$ctrl.showAddNew()\"\r\n      sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.newTaxCard\"></button>\r\n  </div>\r\n  <div class=\"row\">\r\n\r\n    <div class=\"col-md-7 col-lg-7\" ng-switch=\"$ctrl.chartType\">\r\n      <div ng-switch-when=\"full\" class=\"salaxy-tax-card-chart chart-container\">    \r\n          <salaxy-chart custom-height=\"400px\" config=\"$ctrl.getMainChartConfig($ctrl.current)\"></salaxy-chart>\r\n      </div>\r\n\r\n      <div ng-switch-when=\"pie\" class=\"salaxy-tax-card-chart chart-container text-center\">      \r\n          <salaxy-chart style=\"height: 400px; position: relative;\" config=\"$ctrl.getPieChartConfig($ctrl.current)\"></salaxy-chart>\r\n      </div>\r\n    </div>\r\n    <div class=\"col-md-5 col-lg-5\">\r\n      <div class=\"row current-taxcard-row table-row\">\r\n        <div class=\"col-12\">\r\n          <div class=\"btn-group float-end\">\r\n            <a ng-if=\"$ctrl.getTaxcardPreviewUrl($ctrl.current)\" ng-href=\"{{$ctrl.getTaxcardPreviewUrl($ctrl.current)}}\" target=\"_blank\" class=\"btn btn-xs btn-default\"\r\n              sxy-text=\"SALAXY.UI_Terms.open\"></a>\r\n            <a ng-if=\"$ctrl.getTaxcardDownloadUrl($ctrl.current)\" ng-href=\"{{$ctrl.getTaxcardDownloadUrl($ctrl.current)}}\" target=\"_blank\" class=\"btn btn-xs btn-default\"\r\n              sxy-text=\"SALAXY.UI_Terms.download\"></a>\r\n          </div>\r\n          <strong sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.taxCardKind\"></strong><br /> {{ 'TaxcardKind.' + $ctrl.current.card.kind | sxyEnum }}\r\n          ({{$ctrl.current.card.forYear}})\r\n        </div>\r\n      </div>\r\n      <div class=\"row current-taxcard-row table-row\">\r\n        <div class=\"col-8\">\r\n          <strong sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.validDate\"></strong><br /> {{$ctrl.current.card.validity.start | date}} - {{$ctrl.current.card.validity.end | date}}\r\n        </div>\r\n        <div class=\"col-4 text-end\">\r\n          <strong sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.taxCardAdded\"></strong><br />\r\n          <span title=\"{{ $ctrl.current.createdAt | date : 'short' }}\">{{ $ctrl.current.createdAt | sxyDate }}</span>\r\n        </div>\r\n      </div>\r\n      <table class=\"table table-sm\" style=\"margin-bottom: 0; margin-top: 6px\">\r\n        <thead>\r\n          <tr>\r\n            <th colspan=\"2\" style=\"padding-left: 0;\"><span sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.mainTaxPercent2\"></span></th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr>\r\n            <td sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.basicPercent\"></td>\r\n            <td class=\"right\">{{ $ctrl.current.card.taxPercent }} %</td>\r\n          </tr>\r\n          <tr ng-if=\"!$ctrl.current.card.incomeLimit\">\r\n            <td colspan=\"2\"><span sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.noIncomeLimit\"></span></td>\r\n          </tr>\r\n          <tr ng-if=\"$ctrl.current.card.incomeLimit\">\r\n            <td><span sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.taxPercent2.name\"></span> <small>(tulorajan {{ $ctrl.current.card.incomeLimit | currency : '€' : 0 }}\r\n                {{'SALAXY.NG1.CurrentTaxCardComponent.after' | sxyTranslate}})</small></td>\r\n            <td class=\"right\">{{ $ctrl.current.card.taxPercent2 || \"-\" }} %</td>\r\n          </tr>\r\n          <tr>\r\n            <td>\r\n              <span sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.taxPercentMin.title\"></span>\r\n              <button\r\n                ng-if=\"$ctrl.current.card.kind == 'auto' && ( $ctrl.current.card.state == 'shared' || $ctrl.current.card.state == 'employerAdded' || $ctrl.current.card.state == 'verifiedVero' || $ctrl.current.card.state == 'sharedApproved')\"\r\n                type=\"button\" class=\"btn btn-default btn-xs\" ng-click=\"$ctrl.editTaxPercentMin()\" sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.edit\"></button>\r\n            </td>\r\n            <td class=\"right\">\r\n              <span>{{ $ctrl.current.card.taxPercentMin || \"-\" }} %</span>\r\n            </td>\r\n          </tr>\r\n          <tr ng-if=\"$ctrl.current.card.kind == 'auto'\">\r\n            <td colspan=\"2\">\r\n              <span class=\"text-info\" ng-if=\"$ctrl.current.card.lastChecked != '2000-01-01T00:00:00Z'\"><small>{{'SALAXY.NG1.CurrentTaxCardComponent.taxCardChecked' | sxyTranslate}}\r\n                  {{$ctrl.current.card.lastChecked | date: \"dd.MM.yyyy HH:mm\"}}</small></span>\r\n              <br />\r\n              <button type=\"button\" ng-disabled=\"$ctrl.loaders['showRefreshAutoTaxcardDialog']\" ng-click=\"$ctrl.showRefreshAutoTaxcardDialog()\"\r\n                class=\"btn btn-info\">{{'SALAXY.NG1.CurrentTaxCardComponent.checkAutomaticTaxCard' | sxyTranslate}}</button>\r\n            </td>\r\n          </tr>\r\n          <tr ng-if=\"$ctrl.current.card.kind != 'auto'\">\r\n            <td colspan=\"2\">\r\n              <button class=\"btn btn-primary\" ng-if=\"!$ctrl.isTaxCardExpired($ctrl.current) && !$ctrl.hideButtons\" ng-disabled=\"$ctrl.loaders['showAddNew']\"\r\n                ng-click=\"$ctrl.showAddNew()\" sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.newTaxCard\"></button>\r\n            </td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n      <table class=\"table table-sm\" style=\"margin-top: 6px\" ng-if=\"$ctrl.current.card.incomeLimit\">\r\n        <thead>\r\n          <tr>\r\n            <th colspan=\"2\" style=\"padding-left: 0;\"><strong sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.incomeLimit\"></strong></th>\r\n            <th class=\"right\">{{ $ctrl.current.card.incomeLimit | currency : '€' : 0 }}</th>\r\n          </tr>\r\n        </thead>\r\n        <tbody>\r\n          <tr>\r\n            <td style=\"width: 20px;\" class=\"text-center\">-</td>\r\n            <td>\r\n              <span sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.salariesPaid\"></span>\r\n              <button type=\"button\" class=\"btn btn-default btn-xs\" ng-click=\"$ctrl.editIncomeLog()\" sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.edit\"></button>\r\n            </td>\r\n            <td class=\"right\">{{ $ctrl.current.result.totalIncome | currency }}</td>\r\n          </tr>\r\n          <tr ng-if=\"$ctrl.current.result.totalIncomeJanuary\">\r\n            <td></td>\r\n            <td>...<span sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.inJanuary\"></span></td>\r\n            <td class=\"right\">{{ $ctrl.current.result.totalIncomeJanuary | currency }}</td>\r\n          </tr>\r\n          <tr>\r\n            <td></td>\r\n            <td><span sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.inPalkkaus\"></span></td>\r\n            <td class=\"right\">{{ $ctrl.current.result.payment | currency }}</td>\r\n          </tr>\r\n          <tr ng-if=\"$ctrl.current.result.paymentJanuary\">\r\n            <td></td>\r\n            <td>...<span sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.inJanuary\"></span></td>\r\n            <td class=\"right\">{{ $ctrl.current.result.paymentJanuary | currency }}</td>\r\n          </tr>\r\n          <tr class=\"total\">\r\n            <td colspan=\"2\"><span sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.beforeIncomeLimit\"></span></td>\r\n            <td class=\"right\">{{ $ctrl.current.card.incomeLimit - $ctrl.current.result.totalIncome | currency }}</td>\r\n          </tr>\r\n        </tbody>\r\n      </table>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/taxcard/TaxcardDetails_Pro.html\",`<div class=\"salaxy-calc-worker-info row\" ng-if=\"$ctrl.status !== 'initialLoading'\">\r\n  <div class=\"col-3 col-sm-2 col-xxs-3 \">\r\n    <salaxy-avatar avatar=\"$ctrl.current.worker\"></salaxy-avatar>\r\n  </div>\r\n  <div class=\"col-9 col-sm-10 col-xxs-9 worker-info-col\">\r\n    <button class=\"btn btn-primary float-end\" ng-click=\"$ctrl.save()\" ng-disabled=\"!$ctrl.hasChanges\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n    <button class=\"btn btn-default float-end\" ng-disabled=\"$ctrl.loaders['showAddNew']\" ng-click=\"$ctrl.showAddNew()\" sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.newTaxCard\"></button>\r\n    <h2>{{ $ctrl.current.worker.displayName || ('SALAXY.NG1.WorkerInfo.noSelection'| sxyTranslate) }}</h2>\r\n    <div class=\"row\">\r\n      <div class=\"col-12 col-sm-6 \">\r\n        <span ng-if=\"!$ctrl.current.card.personalId\" sxy-text=\"SALAXY.NG1.PaymentDialogComponent.noSSNumber\" class=\"text-danger\"></span>\r\n        <span ng-if=\"$ctrl.current.card.personalId\">{{ $ctrl.current.card.personalId }}</span>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>\r\n<hr />\r\n<div ng-if=\"$ctrl.current\">\r\n  <div class=\"row\">\r\n    <div class=\"col-sm-6\">\r\n      <div class=\"form-horizontal\">\r\n        <salaxy-input-enum disabled=\"true\" label=\"SALAXY.NG1.WorkerDetailsComponent.taxCard.cardType\" ng-required=\"true\" name=\"kind\" enum=\"TaxcardKind\" ng-model=\"$ctrl.current.card.kind\">\r\n        </salaxy-input-enum>\r\n        <salaxy-input-number disabled=\"$ctrl.current.card.kind == 'auto'\" label=\"SALAXY.NG1.CurrentTaxCardComponent.taxCards.year\" name=\"year\" ng-model=\"$ctrl.current.card.forYear\" require=\"true\"></salaxy-input-number>\r\n        <salaxy-datepicker-popup disabled=\"$ctrl.current.card.kind == 'auto'\" name=\"validityStart\" ng-model=\"$ctrl.current.card.validity.start\" require=\"true\" label=\"SALAXY.NG1.CurrentTaxCardComponent.validFromDate2\">\r\n        </salaxy-datepicker-popup>\r\n        <salaxy-datepicker-popup disabled=\"$ctrl.current.card.kind == 'auto'\" name=\"validityEnd\" ng-model=\"$ctrl.current.card.validity.end\" require=\"true\" label=\"SALAXY.NG1.CurrentTaxCardComponent.validTillDate\"></salaxy-datepicker-popup>\r\n        <salaxy-input-number disabled=\"$ctrl.current.card.kind == 'auto'\" label=\"SALAXY.NG1.CurrentTaxCardComponent.mainTaxPercent\" name=\"taxPercent\" ng-model=\"$ctrl.current.card.taxPercent\" require=\"true\" sxy-tax-percent></salaxy-input-number>\r\n        <salaxy-input-number disabled=\"$ctrl.current.card.kind == 'auto'\" name=\"incomeLimit\" label=\"SALAXY.NG1.CurrentTaxCardComponent.incomeLimit2\" ng-model=\"$ctrl.current.card.incomeLimit\" sxy-currency></salaxy-input-number>\r\n        <salaxy-input-number disabled=\"$ctrl.current.card.kind == 'auto'\" name=\"taxPercent2\" label=\"SALAXY.NG1.CurrentTaxCardComponent.taxPercent2.name\" ng-model=\"$ctrl.current.card.taxPercent2\" sxy-tax-percent></salaxy-input-number>\r\n        <div class=\"row\" ng-if=\"$ctrl.current.card.kind != 'auto'\">\r\n          <div class=\"col-12\">\r\n            <div class=\"float-end\">\r\n              <a ng-href=\"{{ $ctrl.getTaxcardDownloadUrl($ctrl.current) }}\" ng-if=\"$ctrl.getTaxcardDownloadUrl($ctrl.current)\" target=\"_blank\" sxy-text=\"SALAXY.UI_Terms.download\"></a>\r\n            </div>\r\n            <legend style=\"text-align:left\" sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.taxCardAsFile\"></legend>\r\n            <div ng-include=\"'salaxy-components/worker/taxcard/TaxcardDetails_Upload.html'\"></div>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"col-sm-6\">\r\n      <div class=\"alert alert-info\" ng-if=\"$ctrl.$incomeLog.hasDiff\">\r\n        <button type=\"button\" class=\"btn btn-primary float-end\" ng-click=\"$ctrl.commitDiff()\" sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.commitDiffBtn\"></button>\r\n        <span sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.commitDiffNote\"></span>\r\n      </div>\r\n      <salaxy-taxcard-income-log parent=\"$ctrl.current\" editable=\"false\" ng-ref=\"$ctrl.$incomeLog\"></salaxy-taxcard-income-log>\r\n      <div class=\"text-end\">\r\n        <button type=\"button\" class=\"btn btn-default btn-xs\" ng-click=\"$ctrl.editIncomeLog()\" sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.edit\"></button>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/taxcard/TaxcardDetails_Upload.html\",`<div name=\"taxCardFile\" ng-model=\"taxCardFile\" ngf-drop=\"$ctrl.uploadTaxCard($file)\" \r\n  ngf-select=\"$ctrl.uploadTaxCard($file)\" class=\"salaxy-drop-box\" ngf-drag-over-class=\"'salaxy-drag-over'\" \r\n  ngf-multiple=\"false\" ngf-min-size=\"5KB\" ngf-max-size=\"10MB\"\r\n  ngf-pattern=\"'image/*,application/pdf'\" ngf-model-invalid=\"invalidFile\" ng-class=\"invalidFile.$error != null ? 'error' : ''\"\r\n  ng-required=\"$ctrl.addNewUi.upload == 'required'\">\r\n  <span ng-if=\"$ctrl.uploadProgress && $ctrl.uploadProgress != 100\">\r\n    <span sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.loading\"></span> {{ $ctrl.uploadProgress }}% {{'SALAXY.NG1.CurrentTaxCardComponent.taxCards.taxCardDetails.downloaded' | sxyTranslate}}\r\n  </span>\r\n  <span ng-if=\"$ctrl.uploadProgress == 100\" sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.progressPreview\"></span>\r\n  <span class=\"text-danger\" ng-if=\"$ctrl.getInvalidFileDescription(invalidFile)\">{{$ctrl.getInvalidFileDescription(invalidFile)}}</span>\r\n  <span ng-if=\"!$ctrl.uploadProgress && !$ctrl.current.card.fileUri\" sxy-html=\"SALAXY.NG1.CurrentTaxCardComponent.uploadTaxCard.html\"></span>\r\n  <span ng-if=\"!$ctrl.uploadProgress && $ctrl.current.card.fileUri\">\r\n    <img class=\"img-responsive\" ng-src=\"{{$ctrl.getUploadPreviewUrl($ctrl.current)}}\" />\r\n  </span>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/taxcard/TaxcardIncomeLog.html\",`<div class=\"salaxy-component salaxy-taxcard-income-log\">\r\n  <table class=\"table table-sm\">\r\n    <thead>\r\n      <tr>\r\n        <th>\r\n          <strong sxy-text=\"SALAXY.NG1.TaxCardIncomeLogComponent.addedForTaxCard\"></strong><br />\r\n          <span sxy-text=\"SALAXY.NG1.TaxCardIncomeLogComponent.salaryPeriod\"></span>\r\n        </th>\r\n        <th class=\"right\">\r\n          <strong sxy-text=\"SALAXY.NG1.TaxCardIncomeLogComponent.mainTaxPercent\"></strong><br />\r\n          <span sxy-text=\"SALAXY.NG1.TaxCardIncomeLogComponent.salaryAmount\"></span>\r\n        </th>\r\n        <th ng-if=\"$ctrl.editable\" style=\"width: 20px;\"></th>\r\n      </tr>\r\n    </thead>\r\n    <tbody>\r\n      <tr ng-repeat=\"row in $ctrl.list\" class=\"\" ng-style=\"row.diff == 'removed' ? 'text-decoration: line-through' : ''\" ng-class=\"{ 'success': row.diff == 'new', 'text-primary': row.diff == 'changed', 'text-danger': row.diff == 'removed' }\">\r\n        <td>\r\n          <strong>\r\n            <span ng-if=\"row.id && row.diff != 'removed'\" sxy-text=\"SALAXY.NG1.TaxCardIncomeLogComponent.calculation\"></span>\r\n            <span ng-if=\"row.id && row.diff == 'removed'\" sxy-text=\"SALAXY.NG1.TaxCardIncomeLogComponent.removedCalc\"></span>\r\n            <span ng-if=\"!row.id\">{{ \"TaxCardIncomeType.\" + row.type | sxyEnum }}</span ng-if=\"row.id\">\r\n            {{ row.paidAt | sxyDate }}\r\n            <button ng-if=\"row.diff == 'new'\"\r\n              type=\"button\" \r\n              class=\"btn btn-xs btn-success\" \r\n              data-bs-toggle=\"popover\" \r\n              data-bs-html=\"true\" \r\n              data-bs-title=\"Info\" \r\n              data-bs-content=\"'SALAXY.NG1.TaxCardIncomeLogComponent.newCalcPopover'| sxyTranslate\" \r\n              data-bs-trigger=\"hover\"\r\n              sxy-text=\"SALAXY.NG1.TaxCardIncomeLogComponent.newCalcBtn\" \r\n              sxy-bs5-popover></button>\r\n\r\n            <button ng-if=\"row.diff == 'changed' && row.type != 'diff'\" \r\n              type=\"button\" \r\n              class=\"btn btn-xs btn-primary\"\r\n              data-bs-toggle=\"popover\" \r\n              data-bs-html=\"true\" \r\n              data-bs-title=\"Info\"\r\n              data-bs-content=\"'SALAXY.NG1.TaxCardIncomeLogComponent.taxCardChangedPopover'| sxyTranslate\" \r\n              data-bs-trigger=\"hover\" \r\n              sxy-text=\"SALAXY.NG1.TaxCardIncomeLogComponent.taxCardChangedBtn\" \r\n              sxy-bs5-popover></button>\r\n\r\n            <button ng-if=\"row.diff == 'changed' && row.type == 'diff'\" \r\n              type=\"button\" \r\n              class=\"btn btn-xs btn-primary\"\r\n              data-bs-toggle=\"popover\" \r\n              data-bs-html=\"true\" \r\n              data-bs-title=\"'Info'\"  \r\n              data-bs-content=\"'SALAXY.NG1.TaxCardIncomeLogComponent.calcChangedPopover'| sxyTranslate\"\r\n              data-bs-trigger=\"hover\" \r\n              sxy-text=\"SALAXY.NG1.TaxCardIncomeLogComponent.calcChangedBtn\"\r\n              sxy-bs5-popover></button>\r\n\r\n            <button ng-if=\"row.diff == 'removed'\" \r\n              type=\"button\" \r\n              class=\"btn btn-xs btn-danger\" \r\n              data-bs-toggle=\"popover\" \r\n              data-bs-html=\"true\" \r\n              data-bs-title=\"'Info'\" \r\n              data-bs-content=\"'SALAXY.NG1.TaxCardIncomeLogComponent.calcRemovedPopover'| sxyTranslate\" \r\n              data-bs-trigger=\"hover\" \r\n              sxy-text=\"SALAXY.NG1.TaxCardIncomeLogComponent.calcRemovedBtn\"\r\n              sxy-bs5-popover></button>\r\n          </strong><br />\r\n          <div class=\"float-start\" style=\"padding: 0px;\">\r\n            {{ { start: row.startDate, end: row.endDate } | sxyDateRange }}\r\n          </div>\r\n          <div class=\"truncate\" style=\"max-width: 250px; padding: 0px;\">\r\n            &nbsp;{{ row.description }}\r\n          </div>\r\n        </td>\r\n        <td class=\"right\">\r\n          <strong>{{ row.tax ? (row.tax | currency) : \"-\" }}</strong><br /> {{ row.income | currency }}\r\n        </td>\r\n        <td ng-if=\"$ctrl.editable\" style=\"width: 20px;\">\r\n          <button type=\"button\" class=\"btn btn-default\" ng-if=\"!$ctrl.isReadOnly(row)\" ng-click=\"$ctrl.showEditDialog(row)\"><i class=\"bi bi-pencil-square\"></i></button>\r\n        </td>\r\n      </tr>\r\n      <tr ng-if=\"!($ctrl.list.length > 0)\">\r\n        <td colspan=\"2\">\r\n          <h3 sxy-text=\"SALAXY.NG1.TaxCardIncomeLogComponent.noCalcsTitle\"></h3>\r\n          <p sxy-text=\"SALAXY.NG1.TaxCardIncomeLogComponent.noCalcsDescription\"></p>\r\n        </td>\r\n      </tr>\r\n      <tr class=\"total\">\r\n        <td>\r\n          <strong>\r\n         <span sxy-text=\"SALAXY.NG1.TaxCardIncomeLogComponent.totalTaxes\"></span> <br />\r\n            <span sxy-text=\"SALAXY.NG1.TaxCardIncomeLogComponent.totalIncome\"></span>\r\n          </strong>\r\n        </td>\r\n        <td class=\"right\">\r\n          <strong>\r\n            {{ $ctrl.getSum(\"tax\") | currency }}<br />\r\n            {{ $ctrl.getSum(\"income\") | currency }}\r\n          </strong>\r\n        </td>\r\n        <td ng-if=\"$ctrl.editable\" style=\"width: 20px;\"></td>\r\n      </tr>\r\n    </tbody>\r\n  </table>\r\n  <div class=\"text-end\" ng-if=\"$ctrl.editable\">\r\n    <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showEditDialog('new')\" sxy-text=\"SALAXY.NG1.EmploymentTaxcardsComponent.taxCardIncomeLog.addElseWherePaidSalary\"></button>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/taxcard/TaxcardIncomeLogEditDialog.html\",`<div class=\"card card-primary\">\r\n  <div class=\"card-header \">\r\n    <h2 sxy-text=\"SALAXY.NG1.TaxCardIncomeLogEditDialogComponent.title\"></h2>\r\n    <button type=\"button\" class=\"btn-close\" ng-click=\"$dismiss()\" aria-label=\"Close\"></button>\r\n  </div>\r\n  <div class=\"card-body\">\r\n    <form class=\"form-horizontal\">\r\n      <fieldset>\r\n        <legend>Tulorajaan vaikuttavat tiedot</legend>\r\n        <salaxy-input-enum name=\"causeCode\" ng-model=\"$ctrl.current.type\" read-only=\"true\" enum=\"TaxCardIncomeType\" filter=\"externalSalaries\" label=\"SALAXY.NG1.TaxCardIncomeLogEditDialogComponent.incomeType\" type=\"select\"></salaxy-input-enum>\r\n        <salaxy-datepicker-popup name=\"paidAt\" ng-model=\"$ctrl.current.paidAt\" label=\"SALAXY.NG1.TaxCardIncomeLogEditDialogComponent.paymentDate\"></salaxy-datepicker-popup>\r\n        <salaxy-input-number name=\"income\" label=\"SALAXY.NG1.TaxCardIncomeLogEditDialogComponent.taxableIncome\" ng-model=\"$ctrl.current.income\"></salaxy-input-number>\r\n      </fieldset>\r\n      <fieldset>\r\n        <legend>Lisätiedot</legend>\r\n        <salaxy-datepicker-popup name=\"startDate\" ng-model=\"$ctrl.current.startDate\" label=\"SALAXY.NG1.TaxCardIncomeLogEditDialogComponent.periodStart\"></salaxy-datepicker-popup>\r\n        <salaxy-datepicker-popup name=\"endDate\" ng-model=\"$ctrl.current.endDate\" label=\"SALAXY.NG1.TaxCardIncomeLogEditDialogComponent.periodEnd\"></salaxy-datepicker-popup>\r\n        <salaxy-input-number name=\"tax\" label=\"SALAXY.NG1.TaxCardIncomeLogEditDialogComponent.tax\" ng-model=\"$ctrl.current.tax\"></salaxy-input-number>\r\n        <salaxy-input name=\"description\" label=\"SALAXY.NG1.TaxCardIncomeLogEditDialogComponent.notes\" ng-model=\"$ctrl.current.description\"></salaxy-input>\r\n        <salaxy-input name=\"id\" read-only=\"true\" label=\"SALAXY.NG1.TaxCardIncomeLogEditDialogComponent.calcId\" ng-model=\"$ctrl.current.id\"></salaxy-input>\r\n      </fieldset>\r\n      <div>\r\n        <button type=\"submit\" class=\"btn btn-primary float-end\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.ok\"></button>\r\n        <button type=\"reset\" class=\"btn btn-default float-end\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.NG1.AbsencePeriodsEditDialog.cancelButtonText\"></button>\r\n        <button type=\"button\" class=\"btn btn-danger\" ng-click=\"$close('delete')\" sxy-text=\"SALAXY.NG1.AbsencePeriodsEditDialog.deleteButtonText\"></button>\r\n      </div>\r\n    </form>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/taxcard/TaxcardList.html\",`<div class=\"salaxy-component salaxy-taxcard-list\">\r\n  <salaxy-odata-table select-mode=\"$ctrl.mode\" url=\"/v03/api/taxcards\"\r\n    options=\"$ctrl.options\"\r\n    ng-if=\"$ctrl.mode == 'select' || $ctrl.mode == 'multiselect'\"\r\n    template-url=\"salaxy-components/odata/lists/Taxcards-select.html\"\r\n    items=\"$ctrl.items\" selected-items=\"$ctrl.selectedItems\"\r\n    on-list-select=\"$ctrl.onListSelect({ value: value, item: item, allItems: allItems });\"\r\n    crud-controller=\"TaxcardCrudController as $crud\"></salaxy-odata-table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/taxcard/TaxcardManualEdit.html\",`<div class=\"salaxy-component salaxy-manual-edit\">\r\n  <form name=\"editForm\">\r\n    <div ng-show=\"false\" ng-init=\"$ctrl.editForm = editForm\"></div>\r\n    <div class=\"form-horizontal\">\r\n      <legend>\r\n        <span sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.newTaxCardTitle\"></span>\r\n        <button class=\"btn btn-primary btn-xs float-end\" sxy-if-role=\"test\" ng-click=\"$ctrl.showToday=!$ctrl.showToday\">test</button>\r\n      </legend>\r\n      <salaxy-datepicker-popup ng-if=\"$ctrl.showToday\" name=\"todayTest\" ng-model=\"$ctrl.today\" ng-change=\"$ctrl.current.card.forYear = null;$ctrl.resetAsNew()\" label-cols=\"col-sm-7\"\r\n        label=\"SALAXY.NG1.CurrentTaxCardComponent.taxCards.taxCardDetails.changeThisDate\"></salaxy-datepicker-popup>\r\n      <salaxy-input-enum label=\"SALAXY.NG1.CurrentTaxCardComponent.taxCardKind\" label-cols=\"col-sm-7\" require=\"true\" name=\"verokortinTyyppi\" enum=\"TaxcardKind\"\r\n        type=\"{{ (!$ctrl.current.card.kind || $ctrl.current.card.kind == 'undefined' || $ctrl.current.card.kind == 'auto') ? 'radio' : 'select' }}\"\r\n        ng-model=\"$ctrl.current.card.kind\" ng-change=\"$ctrl.resetAsNew($ctrl.current.card.kind)\" options=\"$ctrl.taxcardKindOptions\"\r\n        placeholder=\"SALAXY.NG1.CurrentTaxCardComponent.selectCardKind\">\r\n      </salaxy-input-enum>\r\n      <p ng-if=\"$ctrl.current.card.kind == 'noTaxCard'\" class=\"text-danger\" style=\"margin-top:5px; margin-bottom:0;\"\r\n        sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.noTaxCard.description\"></p>\r\n      <p ng-if=\"$ctrl.current.card.kind == 'noWithholdingHousehold'\" class=\"text-danger\" style=\"margin-top:5px; margin-bottom:0;\"\r\n        sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.noWithholdingHousehold.description\"></p>\r\n      <salaxy-form-group label=\"SALAXY.NG1.CurrentTaxCardComponent.year\" require=\"true\" name=\"year\" label-cols=\"col-sm-7\" ng-if=\"$ctrl.addNewUi.yearsAllowed\">\r\n        <select class=\"form-select\" ng-model=\"$ctrl.current.card.forYear\" ng-options=\"i for i in $ctrl.addNewUi.yearsAllowed\" ng-change=\"$ctrl.yearChanged()\"></select>\r\n      </salaxy-form-group>\r\n      <salaxy-input label=\"SALAXY.NG1.CurrentTaxCardComponent.mainTaxPercent3\" name=\"veroprosentti\" label-cols=\"col-sm-7\" ng-model=\"$ctrl.current.card.taxPercent\"\r\n        disabled=\"$ctrl.addNewUi.readonly\" require=\"true\" sxy-tax-percent ng-if=\"$ctrl.addNewUi.showTaxPercent\"></salaxy-input>\r\n      <salaxy-input name=\"tuloraja\" label=\"SALAXY.NG1.CurrentTaxCardComponent.incomeLimit2\" ng-model=\"$ctrl.current.card.incomeLimit\" maxlength=\"10\"\r\n        ng-if=\"$ctrl.addNewUi.showIncomeLimit\" label-cols=\"col-sm-7\" require=\"$ctrl.addNewUi.requireIncomeLimit || $ctrl.current.card.taxPercent2\" sxy-currency></salaxy-input>\r\n      <salaxy-input name=\"lisaveroprosentti\" label=\"SALAXY.NG1.CurrentTaxCardComponent.taxPercent2.name\" label-cols=\"col-sm-7\" ng-model=\"$ctrl.current.card.taxPercent2\"\r\n        ng-if=\"$ctrl.addNewUi.showIncomeLimit\" require=\"$ctrl.addNewUi.requireIncomeLimit || $ctrl.current.card.incomeLimit\" sxy-tax-percent></salaxy-input>\r\n      <salaxy-form-group label-cols=\"col-sm-5\" label=\"SALAXY.NG1.CurrentTaxCardComponent.validDate\" name=\"validityStart\" class=\"salaxy-read-only\"\r\n        ng-if=\"$ctrl.current.card.kind =='defaultYearly' || $ctrl.current.card.kind == 'replacement'\">\r\n        <div class=\"form-control-plaintext text-end\">{{ $ctrl.current.card.validity.start | date : \"dd.MM.yyyy\" }} – {{ $ctrl.current.card.validity.end | date :\r\n          \"dd.MM.yyyy\" }}</div>\r\n      </salaxy-form-group>\r\n      <salaxy-datepicker-popup name=\"voimaantuloPvm\" ng-model=\"$ctrl.current.card.validity.start\" ng-if=\"$ctrl.addNewUi.startDateOptions\"\r\n        min-date=\"$ctrl.addNewUi.startDateOptions.minDate\" max-date=\"$ctrl.addNewUi.startDateOptions.maxDate\" label-cols=\"col-sm-7\" require=\"true\"\r\n        label=\"SALAXY.NG1.CurrentTaxCardComponent.validFromDate2\"></salaxy-datepicker-popup>\r\n      <salaxy-input name=\"previousSalariesRow\" label=\"SALAXY.NG1.CurrentTaxCardComponent.previousSalariesForTaxCard.label\" ng-model=\"$ctrl.previousSalariesRow.income\"\r\n        ng-if=\"$ctrl.addNewUi.showPreviousSalariesPaid\" tooltip-html=\"{{'SALAXY.NG1.CurrentTaxCardComponent.previousSalariesForTaxCard.tooltip' | sxyTranslate}}\"\r\n        tooltip-placement=\"right\" label-cols=\"col-sm-7\" sxy-currency></salaxy-input>\r\n    </div>\r\n  </form>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/taxcard/TaxCardsList.html\",`<div class=\"salaxy-component salaxy-tax-cards-list\">\r\n  <div class=\"row form-horizontal\" sxy-if-role=\"test\" ng-init=\"$ctrl.today = 'today'\">\r\n    <div class=\"col-6\">\r\n      <salaxy-datepicker-popup name=\"today\" ng-model=\"$ctrl.today\" label=\"SALAXY.NG1.CurrentTaxCardComponent.salaryDate\"\r\n        ng-change=\"\"></salaxy-datepicker-popup>\r\n    </div>\r\n    <div class=\"col-6\">\r\n      <button type=\"button\" class=\"btn btn-primary\" \r\n        ng-click=\"$ctrl.$odata.setUrl('/v03/api/taxcards/current/' + $ctrl.today || 'null')\" sxy-text=\"SALAXY.NG1.CurrentTaxCardComponent.changePaymentDate\"></button>\r\n    </div>\r\n  </div>\r\n  <salaxy-odata-table url=\"/v03/api/taxcards/current/null\" crud-controller=\"TaxcardCrudController as $crud\"\r\n    ng-ref=\"$ctrl.$odata\"\r\n    template-url=\"salaxy-components/odata/lists/Taxcards.html\"></salaxy-odata-table>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/TimerEditDialog.html\",`<div class=\"salaxy-component salaxy-timer-dialog\">\r\n  <div>\r\n    <div class=\"modal-header\">\r\n      <h2 sxy-text=\"Muokkaa kellokorttimerkintää\"></h2>\r\n      <button type=\"button\" class=\"btn-close\" ng-click=\"$dismiss()\" aria-label=\"Close\"></button>\r\n    </div>\r\n    <div class=\"modal-body\">\r\n      <form class=\"form-horizontal\">\r\n        <div class=\"row\">\r\n          <div class=\"col-sm-6 col-12\">\r\n            <salaxy-datepicker-popup name=\"start\" ng-model=\"$ctrl.current.contentData.period.start\" label=\"Aloituspäivä\"></salaxy-datepicker-popup>\r\n          </div>\r\n          <div class=\"col-sm-6  col-12\">\r\n            <salaxy-input-time name=\"startTime\" label=\"Alkoi\" type=\"time\" ng-model=\"$ctrl.current.contentData.startTime\"></salaxy-input-time>\r\n          </div>\r\n        </div>\r\n        <div class=\"row\">\r\n          <div class=\"col-sm-6  col-12\">\r\n            <salaxy-datepicker-popup name=\"start\" ng-model=\"$ctrl.current.contentData.period.end\" label=\"Lopetuspäivä\"></salaxy-datepicker-popup>\r\n          </div>\r\n          <div class=\"col-sm-6  col-12\">\r\n            <salaxy-input-time name=\"endTime\" label=\"Loppui\" type=\"time\" ng-model=\"$ctrl.current.contentData.endTime\"></salaxy-input-time>\r\n          </div>\r\n        </div>\r\n        <div class=\"row\">\r\n          <div class=\"col-sm-6 col-12\">\r\n            <salaxy-input-typeahead ng-if=\"$ctrl.logic.costAccountingSettings\" label-format=\"text-value\"\r\n              name=\"options_project\" ng-model=\"$ctrl.current.contentData.project\" options=\"$ctrl.logic.costAccountingSettings.options\"\r\n              label=\"{{($ctrl.logic.costAccountingSettings.label || 'SALAXY.NG1.CalcCostAccountingComponent.defaultLabel') | sxyTranslate}}\" required=\"true\"></salaxy-input-typeahead>\r\n          </div>\r\n          <div class=\"col-sm-6 col-12\">\r\n            <salaxy-input label=\"Kommentti\" placeholder=\"Kommentti\"  name=\"comment\" ng-model=\"$ctrl.current.contentData.projectText\">\r\n            </salaxy-input>\r\n          </div>\r\n        </div>\r\n    </div>\r\n    </form>\r\n  </div>\r\n  <div class=\"modal-footer\">\r\n    <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.NG1.AbsencePeriodsEditDialog.cancelButtonText\"></button>\r\n    <button type=\"submit\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.ok\"></button>\r\n\r\n    <button type=\"button\" class=\"btn btn-danger float-start\" ng-click=\"$close('delete')\" sxy-text=\"SALAXY.NG1.AbsencePeriodsEditDialog.deleteButtonText\"></button>\r\n  </div>\r\n</div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/TimeReportEditDialog.html\",`<div class=\"salaxy-component salaxy-timer-dialog\">\r\n  <div>\r\n    <div class=\"modal-header\">\r\n      <h2 sxy-text=\"Muokkaa aikakirjausta\"></h2>\r\n      <button type=\"button\" class=\"btn-close\" ng-click=\"$dismiss()\" aria-label=\"Close\"></button>\r\n    </div>\r\n    <div class=\"modal-body\">\r\n      <form class=\"form-horizontal\">\r\n        <div class=\"row\">\r\n          <div class=\"col-sm-6 col-12\">\r\n            <salaxy-input-typeahead ng-if=\"$ctrl.logic.costAccountingSettings\" label-format=\"text-value\" name=\"options_project\" ng-model=\"$ctrl.current.contentData.project\" options=\"$ctrl.logic.costAccountingSettings.options\" label=\"{{($ctrl.logic.costAccountingSettings.label || 'SALAXY.NG1.CalcCostAccountingComponent.defaultLabel') | sxyTranslate}}\" required=\"true\"></salaxy-input-typeahead>\r\n          </div>\r\n          <div class=\"col-sm-6 col-12\">\r\n            <salaxy-input name=\"message\" ng-model=\"$ctrl.current.contentData.projectText\" label=\"Kommentti\"></salaxy-input>\r\n          </div>\r\n          <div class=\"col-sm-6 col-12\">\r\n            <salaxy-input-time name=\"startTime\" label=\"Aloitusaika\" type=\"time\" ng-model=\"$ctrl.current.contentData.startTime\"></salaxy-input-time>\r\n          </div>\r\n          <div class=\"col-sm-6 col-12\">\r\n            <salaxy-input-time name=\"endTime\" label=\"Lopetusaika\" type=\"time\" ng-model=\"$ctrl.current.contentData.endTime\"></salaxy-input-time>\r\n          </div>\r\n        </div>\r\n      </form>\r\n    </div>\r\n    <div class=\"modal-footer\">\r\n      <button type=\"reset\" class=\"btn btn-default\" ng-click=\"$close('cancel')\" sxy-text=\"SALAXY.NG1.AbsencePeriodsEditDialog.cancelButtonText\"></button>\r\n      <button type=\"submit\" class=\"btn btn-primary\" ng-click=\"$close('ok')\" sxy-text=\"SALAXY.UI_Terms.ok\"></button>\r\n\r\n      <button type=\"button\" class=\"btn btn-danger float-start\" ng-click=\"$close('delete')\" sxy-text=\"SALAXY.NG1.AbsencePeriodsEditDialog.deleteButtonText\"></button>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/WorkerAbsences.html\",`<div class=\"salaxy-component salaxy-worker-absences\">\r\n  <salaxy-spinner ng-if=\"$ctrl.isLoading\"></salaxy-spinner>\r\n  <div class=\"row\">\r\n    <div class=\"col-sm-8\">\r\n      <fieldset ng-if=\"$ctrl.viewType == 'overview'\">\r\n        <salaxy-absence-periods on-commit=\"$ctrl.save()\" parent=\"$ctrl.current\" mode=\"calendar\"\r\n          filter-start=\"$ctrl.currentYear + '-01-01'\" filter-end=\"$ctrl.currentYear + '-12-31'\"\r\n          ></salaxy-absence-periods>\r\n      </fieldset>\r\n      <fieldset ng-if=\"$ctrl.viewType == 'list'\">\r\n        <salaxy-absence-periods on-commit=\"$ctrl.save()\" parent=\"$ctrl.current\"></salaxy-absence-periods>\r\n      </fieldset>\r\n    </div>\r\n    <div class=\"col-sm-4\">\r\n      <div class=\"btn-group btn-block dropdown mb-4\">\r\n        <button id=\"year-selection\" type=\"button\" class=\"btn btn-primary btn-block dropdown-toggle\" data-bs-toggle=\"dropdown\">\r\n          {{ $ctrl.currentYear  }}\r\n        </button>\r\n        <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"single-button\">\r\n          <li role=\"menuitem\"  ng-repeat=\"year in $ctrl.years\">\r\n            <a href=\"\" ng-click=\"$ctrl.currentYear = year\" class=\"dropdown-item\">{{ year }}</a>\r\n          </li>\r\n        </ul>\r\n      </div>\r\n      <salaxy-toggle-buttons ng-model=\"$ctrl.viewType\" options=\"[\r\n        { value: 'overview', label: 'SALAXY.NG1.WorkerAbsencesComponent.calendarButtonText' },\r\n        { value: 'list', label: 'SALAXY.NG1.WorkerAbsencesComponent.listButtonText' }\r\n      ]\" type=\"block\"></salaxy-toggle-buttons>\r\n      <p>&nbsp;</p>\r\n      <fieldset>\r\n        <legend sxy-text=\"SALAXY.NG1.WorkerAbsencesComponent.legendInstructions\"></legend>\r\n        <div sxy-html=\"SALAXY.NG1.WorkerAbsencesComponent.instructions.html\"></div>\r\n      </fieldset>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/WorkerAssure.html\",`<div class=\"salaxy-component salaxy-worker-assure\">\r\n  <div class=\"col\">\r\n    <form name=\"assureWorkerForm\" class=\"form-horizontal\">\r\n      <h3>Luo uusi työntekijä (Partner, BETA)</h3>\r\n      <salaxy-input sxy-personal-id-fi ng-model=\"$ctrl.assureWorkerAccountReq.officialId\" label=\"Henkilötunnus\" name=\"officialId\" require=\"true\"></salaxy-input>\r\n      <salaxy-input ng-model=\"$ctrl.assureWorkerAccountReq.firstName\" label=\"Etunimi\" name=\"firstName\" require=\"true\"></salaxy-input>\r\n      <salaxy-input ng-model=\"$ctrl.assureWorkerAccountReq.lastName\" label=\"Sukunimi\" name=\"lastName\" require=\"true\"></salaxy-input>\r\n      <salaxy-input sxy-email ng-model=\"$ctrl.assureWorkerAccountReq.email\" label=\"Sähköposti\" name=\"email\" require=\"true\"></salaxy-input>\r\n      <salaxy-input sxy-mobile-phone ng-model=\"$ctrl.assureWorkerAccountReq.telephone\" label=\"Puhelin\" name=\"telephone\" require=\"true\"></salaxy-input>\r\n      <salaxy-input sxy-iban ng-model=\"$ctrl.assureWorkerAccountReq.bankAccountIban\" label=\"Pankkitili\" name=\"bankAccountIban\" require=\"true\"></salaxy-input>\r\n      <salaxy-datepicker-popup name=\"startDate\" label=\"Työsuhteen alkamispäivä\" ng-model=\"$ctrl.assureWorkerAccountReq.startDate\"></salaxy-datepicker-popup>\r\n      <salaxy-datepicker-popup name=\"endDate\" label=\"Työsuhteen päättymispäivä\" ng-model=\"$ctrl.assureWorkerAccountReq.endDate\"></salaxy-datepicker-popup>\r\n\r\n      <div class=\"text-end\">\r\n        <button type=\"reset\" ng-click=\"assureWorkerForm.$setPristine(); $ctrl.resetAssureWorkerAccount()\" class=\"btn btn-default\">Tyhjennä</button>\r\n        <button ng-click=\"assureWorkerForm.$setPristine(); $ctrl.submitAssureWorkerAccount($employmentDetails, $employmentsList);\" ng-disabled=\"assureWorkerForm.$invalid\" class=\"btn btn-primary\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n      </div>\r\n    </form>\r\n  </div>\r\n\r\n  <div class=\"col col-md-5 col-lg-5\">\r\n    <hr />\r\n    <salaxy-employment-list limit-to=\"10\" ng-ref=\"$employmentsList\" mode=\"select\" on-list-select=\"$employmentDetails.model = (value == true ? item.id : null); $employmentsList.selectedItems = []\"></salaxy-employment-list>\r\n  </div>\r\n  <div class=\"col-md-7 col-lg-7\">\r\n    <hr />\r\n    <salaxy-employment-details ng-ref=\"$employmentDetails\"></salaxy-employment-details>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/worker/WorkerDetails.html\",`<div ng-if=\"$ctrl.status == 'initialLoading'\">\r\n  <p sxy-text=\"SALAXY.UI_Terms.loading\"></p>\r\n</div>\r\n<div ng-if=\"$ctrl.current\">\r\n  <div class=\"alert alert-warning\">\r\n    <div><strong>WARNING: This page is depricated!</strong></div>\r\n    <div>Tämä on vanha sivu, joka ei pitäisi enää olle näkyvissä. \r\n      <strong>Ilmoita asiakaspalvelulle</strong>, jos tämä sivu on vielä näkyvissä sivustollasi.</div>\r\n  </div>\r\n  <salaxy-employment-details model=\"$ctrl.current.employmentId\"></salaxy-employment-details>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/workflow/CalendarEventDetails.html\",`<div class=\"salaxy-component salaxy-calendar-event-details\">\r\n  <salaxy-tab-buttons\r\n    current-tab=\"$ctrl.currentTab\"\r\n    options=\"$ctrl.tabOptions\"\r\n    tabs-id=\"calendarEventDetails\">\r\n  </salaxy-tab-buttons>\r\n  <div class=\"tab-content\" id=\"tab-content-calendarEventDetails\" style=\"min-height: 360px\">\r\n    <div class=\"tab-pane\" id=\"basic-tab\">\r\n      <div class=\"row\">\r\n        <div class=\"col-sm-6 form-horizontal\">\r\n          <fieldset>\r\n            <legend>Tapahtuma-aika</legend>\r\n            <salaxy-datepicker-popup ng-model=\"$ctrl.current.event.start\" name=\"start\" label=\"Alku\" require=\"true\" ng-change=\"$ctrl.current.event.end = $ctrl.current.event.start\">\r\n            </salaxy-datepicker-popup>\r\n            <salaxy-datepicker-popup ng-model=\"$ctrl.current.event.end\" name=\"end\" label=\"Loppu\" ng-change=\"$ctrl.current.event.duration = null\" min-date=\"$ctrl.current.event.start\"></salaxy-datepicker-popup>\r\n            <salaxy-form-group name=\"duration\" class=\"salaxy-component salaxy-read-only\" label=\"Kesto\">\r\n              <div class=\"form-control-plaintext\">{{ $ctrl.getEventDuration() }}</div>\r\n            </salaxy-form-group>\r\n            <div class=\"alert alert-warning\" ng-if=\"!$ctrl.current.event.isAllDay\">\r\n              Kalenteritapahtuma määrittää kellonaikoja. Tämä käyttöliittymä on suunniteltu vain koko päivän kestäviin tapahtumiin ja muokkaukset saattavat johtaa virheellisiin tuloksiin.\r\n            </div>\r\n          </fieldset>\r\n          <fieldset>\r\n            <legend>Lisätietoja</legend>\r\n            <salaxy-input-enum name=\"status\" enum=\"CalendarEventStatus\" ng-model=\"$ctrl.current.event.status\" label=\"Status\" read-only=\"true\"></salaxy-input-enum>\r\n            <salaxy-form-group name=\"categories\" class=\"salaxy-component salaxy-read-only\" label=\"Kategoriat\">\r\n              <div class=\"form-control-plaintext\">\r\n                <div ng-repeat=\"cat in $ctrl.current.event.categories\"><span>{{ cat + ($last ? \"\" : \", \") }}</span></div>\r\n                <div ng-if=\"!$ctrl.current.event.categories.length\">-</div>\r\n              </div>\r\n            </salaxy-form-group>\r\n            <salaxy-input-number name=\"priority\" ng-model=\"$ctrl.current.event.priority\" label=\"Prioriteetti\" read-only=\"true\"></salaxy-input-number>\r\n          </fieldset>\r\n        </div>\r\n        <div class=\"col-sm-6\">\r\n          <fieldset class=\"form-horizontal\">\r\n            <legend>Kuvaus</legend>\r\n            <salaxy-input ng-model=\"$ctrl.current.event.summary\" name=\"summary\" required=\"true\" label=\"Lyhyt kuvaus\"></salaxy-input>\r\n            <salaxy-textarea ng-model=\"$ctrl.current.event.description\" name=\"description\" label=\"Kuvaus\" rows=\"5\" label-type=\"basic\"></salaxy-textarea>\r\n          </fieldset>\r\n        </div>\r\n      </div>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"recurrence-tab\">\r\n      <p class=\"lead\">\r\n        <button type=\"button\" class=\"btn btn-primary float-end\" ng-click=\"$ctrl.addRecurrenceRule()\">Lisää sääntö</button> Voit määrittää tapahtumalle toistuvuussääntöjä: Esim. kuukausittain, viikottain jne. Toistuvuus perustuu alkupäivämäärään <strong>{{ $ctrl.current.event.start | sxyDate }}</strong>        aivan kuten Outlookissa tai Google kalenterissa.\r\n      </p>\r\n      <fieldset ng-repeat=\"rule in $ctrl.current.event.recurrenceRules track by $index\">\r\n        <legend>\r\n          <button ng-click=\"$ctrl.deleteRecurrence($index)\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\" class=\"btn btn-danger btn-sm float-end\">\r\n            <i class=\"bi bi-trash-fill\"></i>\r\n          </button> Toistuvuus {{ $index + 1 }}\r\n        </legend>\r\n        <salaxy-input ng-model=\"$ctrl.current.event.recurrenceRules[$index]\" name=\"rule{{$index}}\" required=\"true\" label=\"iCalendar sääntö (rrule)\"></salaxy-input>\r\n      </fieldset>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"actions-tab\">\r\n      <p class=\"lead\">\r\n        <button type=\"button\" class=\"btn btn-primary float-end\" ng-click=\"$ctrl.addAction()\">Lisää tehtävä</button> Säännöt määritetään päivinä ennen tai jälkeen alkupäivän <strong>{{ $ctrl.current.event.start | sxyDate }}</strong> (+ mahd. toistuvuus).\r\n      </p>\r\n      <fieldset ng-repeat=\"action in $ctrl.current.event.actions | orderBy: 'triggerDuration'\" class=\"form-horizontal\" ng-switch=\"action.type\">\r\n        <legend>\r\n          <button ng-click=\"$ctrl.deleteAction($index)\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\" class=\"btn btn-danger btn-sm float-end\">\r\n            <i class=\"bi bi-trash-fill\"></i>\r\n          </button> Skripti {{ $index + 1 }}\r\n        </legend>\r\n        <div class=\"alert alert-danger\">\r\n          <strong>HUOM: </strong> Skriptit ovat rajatussa testikäytössä. Ota yhteyttä asiakaspalveluun, jos tarvitse skriptejä.\r\n        </div>\r\n      </fieldset>\r\n    </div>\r\n    <div class=\"tab-pane\" id=\"debug-tab\">\r\n      <salaxy-json-formatter key=\"'Event'\" json=\"$ctrl.current\" open=\"1\"></salaxy-json-formatter>\r\n    </div>\r\n  </div>\r\n\r\n  <div class=\"row\">\r\n    <div class=\"col-12 text-end\">\r\n      <button class=\"btn btn-danger\" ng-click=\"$ctrl.delete($ctrl.current)\">Poista</button>\r\n      <button class=\"btn btn-primary\" ng-click=\"$ctrl.save()\">Tallenna</button>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/workflow/dataset/DatasetDetails.html\",`<div class=\"salaxy-component salaxy-dataset-details\" ng-switch=\"$ctrl.getMode()\">\r\n  <salaxy-spinner ng-switch-when=\"loading\"></salaxy-spinner>\r\n  <div ng-switch-when=\"usecase\">\r\n    <div ng-if=\"$ctrl.usecase && !$ctrl.usecase.defaultView\" class=\"alert alert-danger\">\r\n      ERROR: This usecase {{ $ctrl.usecase.uri }} does not have user interface (view) defined.\r\n    </div>\r\n    <div ng-if=\"$ctrl.usecase.defaultView\">\r\n      <ng-include src=\"$ctrl.usecase.defaultView\"></ng-include>\r\n    </div>\r\n  </div>\r\n  <div ng-switch-when=\"data-edit\">\r\n    <ng-include src=\"'salaxy-components/workflow/dataset/DatasetDetails_data.html'\"></ng-include>\r\n  </div>\r\n  <div ng-switch-when=\"full-edit\">\r\n    <ng-include src=\"'salaxy-components/workflow/dataset/DatasetDetails_full.html'\"></ng-include>\r\n  </div>\r\n  <div ng-switch-default class=\"alert alert-danger\">ERROR: Unable to load Dataset</div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/workflow/dataset/DatasetDetails_data.html\",`<div>\r\n  <div class=\"btn-toolbar\">\r\n    <div class=\"btn-group\">\r\n      <button type=\"button\" class=\"btn btn-primary\" ng-disabled=\"!$ctrl.current || $ctrl.current.isReadOnly\" ng-click=\"$ctrl.save()\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n      </button>\r\n    </div>\r\n    <div class=\"btn-group\">\r\n      \r\n        <div class=\"form-group\" style=\"line-height: 34px;\">\r\n          <strong> &nbsp; Nimi:</strong> {{$ctrl.current.info.label}}\r\n        </div>\r\n     \r\n    </div>\r\n    <div class=\"btn-group ms-1\">\r\n      <button type=\"button\" class=\"btn\" ng-class=\"'btn-' + (action.uiColor || 'default')\" ng-repeat=\"action in $ctrl.usecase.actions\" ng-click=\"$ctrl.executeAction(action)\">{{\r\n        action.uiText }}</button>\r\n    </div>\r\n  </div>\r\n  <div style=\"height: calc(100vh - 200px);\" class=\"form-horizontal\">\r\n    <style>\r\n      /* TODO: Move to less */\r\n      .salaxy-tab-height100 {\r\n        height: 100%;\r\n      }\r\n\r\n      .salaxy-tab-height100 .tab-content {\r\n        height: calc(100% - 43px);\r\n      }\r\n\r\n      .salaxy-tab-height100 .height100 {\r\n        height: 100%;\r\n      }\r\n    </style>\r\n    <salaxy-tab-buttons\r\n      currentTab=\"$ctrl.currentTab\"\r\n      options=\"$ctrl.generateTabOptions()\"\r\n      tabs-id=\"datasetDetailsData\">\r\n    </salaxy-tab-buttons>\r\n\r\n    <div class=\"tab-content\" id=\"tab-content-datasetDetailsData\">\r\n      <div class=\"tab-pane\" ng-repeat=\"table in $ctrl.current.data\" id=\"{{ $ctrl.generateTabOptions()[$index].value }}\">\r\n        <div class=\"height100\">\r\n          <sxy-grid\r\n            ng-if=\"$ctrl.getSchamaDef($index)\"\r\n            data=\"table.content\"\r\n            schema-def=\"$ctrl.getSchamaDef($index)\"\r\n            schema=\"table.schema\"\r\n            ng-ref=\"grid\">\r\n          </sxy-grid>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/workflow/dataset/DatasetDetails_full.html\",`<div>\r\n  <div class=\"btn-toolbar\" style=\"margin-left: 195px; margin-bottom: 2px;\">\r\n    <div class=\"btn-group\">\r\n      <button type=\"button\" class=\"btn btn-primary\" ng-disabled=\"!$ctrl.current || $ctrl.current.isReadOnly\" ng-click=\"$ctrl.save()\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n      </button>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showCopyAsNew($ctrl.current)\" sxy-text=\"SALAXY.UI_Terms.copyAsNew\"></button>\r\n      <button class=\"btn btn-default\" ng-click=\"$ctrl.reload()\"><i class=\"bi bi-arrow-repeat\" aria-hidden=\"true\"></i></button>\r\n    </div>\r\n    <div class=\"btn-group ms-1\">\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.addDataObject()\" sxy-text=\"Lisää dataobjekti\"></button>\r\n    </div>\r\n    <div class=\"btn-group ms-1\">\r\n      \r\n        <div class=\"form-group\" style=\"line-height: 34px;\">\r\n          <strong> &nbsp; Nimi:</strong> {{$ctrl.current.info.label}}\r\n        </div>\r\n      \r\n    </div>\r\n    <div class=\"btn-group ms-1\">\r\n      <button type=\"button\" class=\"btn\" ng-class=\"'btn-' + (action.uiColor || 'default')\" ng-repeat=\"action in $ctrl.usecase.actions\" ng-click=\"$ctrl.executeAction(action)\">{{ action.uiText }}</button>\r\n    </div>\r\n    <div class=\"btn-group ms-auto\">\r\n      <button type=\"button\" class=\"btn btn-danger\" ng-disabled=\"!$ctrl.current || $ctrl.current.isReadOnly\" ng-click=\"$ctrl.delete($ctrl.current)\"\r\n        sxy-text=\"SALAXY.UI_Terms.delete\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\">\r\n    </div>\r\n  </div>\r\n  <div ng-init=\"$ctrl.currentSection = 'basicInfo'\" style=\"display: flex\">\r\n    <div style=\"flex: 0 0 200px;\">\r\n      <salaxy-toggle-buttons ng-model=\"$ctrl.currentSection\" options=\"[{ value: 'basicInfo', label: 'Perustiedot' }]\" type=\"block\"></salaxy-toggle-buttons>\r\n      <div style=\"margin-top: 8px;\">Dataobjektit:</div>\r\n      <salaxy-toggle-buttons ng-repeat=\"table in $ctrl.current.data\" ng-model=\"$ctrl.currentSection\" options=\"[{ value: 'table' + $index, label: table.label }]\" type=\"block\"></salaxy-toggle-buttons>\r\n      <div>&nbsp;</div>\r\n      <salaxy-toggle-buttons ng-model=\"$ctrl.currentSection\" options=\"[{ value: 'debugger', label: 'Debugger' }]\" type=\"block\"></salaxy-toggle-buttons>\r\n    </div>\r\n    <div ng-if=\"$ctrl.current\" style=\"flex: 1 1 100%;margin-left: -1px; height: calc(100vh - 200px); overflow-y: auto; border: solid 1px #009fd8; padding: 10px;\">\r\n      <div ng-if=\"$ctrl.currentSection == 'basicInfo'\" class=\"form-horizontal\">\r\n        <sxy-form open-api=\"salaxy-secure/schemas/v02.json\" type=\"Dataset\" auto-gen=\"false\" debugger=\"false\" model=\"$ctrl.current\">\r\n          <div class=\"row\">\r\n            <div class=\"col-sm-6\">\r\n              <fieldset>\r\n                <legend>Perustiedot</legend>\r\n                <sxy-input label=\"Id\" model=\"form.id\"></sxy-input>\r\n                <sxy-input label=\"Nimi\" model=\"form.info.label\"></sxy-input>\r\n                <sxy-input label=\"Status\" model=\"form.info.status\"></sxy-input>\r\n                <sxy-input label=\"Tyyppi\" model=\"form.info.type\"></sxy-input>\r\n              </fieldset>\r\n            </div>\r\n            <div class=\"col-sm-6\">\r\n              <fieldset>\r\n                <legend>Räätälöinti</legend>\r\n                <div ng-if=\"$ctrl.usecase == 'none'\">\r\n                  <salaxy-input-enum label=\"Valitse räätälöinti\" ng-if=\"$ctrl.usecases\" name=\"uri\" ng-model=\"$ctrl.current.usecase.uri\" options=\"$ctrl.usecases\"></salaxy-input-enum>\r\n                  <div ng-if=\"!$ctrl.current.usecase.uri\" class=\"alert alert-danger\">\r\n                    Tälle datasetille ei ole määritetty räätälöintiä (datamalli ja toiminnallisuudet).\r\n                  </div>\r\n                  <div ng-if=\"$ctrl.current.usecase.uri\" class=\"alert alert-info\">\r\n                    <p>\r\n                      Räätälöintiä ei löytynyt tai ei vielä ladattu (tallenna ladataksesi): {{ $ctrl.current.usecase.uri }}\r\n                    </p>\r\n                  </div>\r\n                </div>\r\n                <div ng-if=\"$ctrl.usecase != 'none'\">\r\n                  <p><strong>URI:</strong> <code>{{ $ctrl.current.usecase.uri }}</code></p>\r\n                  <sxy-input label=\"Nimi\" model=\"form.usecase.label\" read-only=\"true\"></sxy-input>\r\n                  <sxy-input label=\"Kuvaus\" model=\"form.usecase.description\" read-only=\"true\"></sxy-input>\r\n                  <salaxy-form-group name=\"btnEdit\" label=\"Muokkaa\">\r\n                    <a ng-href=\"#/usecases/details/{{ $ctrl.usecase.id }}@{{ $ctrl.usecase.owner }}\" target=\"_blank\" ng-disabled=\"!$ctrl.usecase || $ctrl.usecase.isReadOnly\"\r\n                      class=\"btn btn-default btn-sm\">Muokkaa (uuteen ikkunaan)...</a>\r\n                  </salaxy-form-group>\r\n                  <salaxy-json-formatter json=\"$ctrl.usecase\" key=\"'Yksityiskohdat...'\" open=\"0\"></salaxy-json-formatter>\r\n                </div>\r\n              </fieldset>\r\n            </div>\r\n          </div>\r\n        </sxy-form>\r\n      </div>\r\n      <div ng-repeat=\"dataObj in $ctrl.current.data\" ng-if=\"$ctrl.currentSection == ('table' + $index)\" class=\"height100 form-horizontal\">\r\n        <style>\r\n          /* TODO: Move to less */\r\n          .salaxy-tab-height100 {\r\n            height: 100%;\r\n          }\r\n\r\n          .salaxy-tab-height100 .tab-content {\r\n            height: calc(100% - 43px);\r\n          }\r\n\r\n          .salaxy-tab-height100 .tab-pane {\r\n            height: 100%;\r\n          }\r\n        </style>\r\n        <salaxy-tab-buttons\r\n          current-tab=\"$ctrl.currentTab\"\r\n          options=\"[\r\n            { value: 'grid', text: 'Grid' },\r\n            { value: 'properties', text: 'Ominaisuudet' },\r\n            { value: 'validation', text: 'Validation' }\r\n          ]\"\r\n          tabs-id=\"datasetDetailsFull\">\r\n        </salaxy-tab-buttons>\r\n        <div class=\"tab-content\" id=\"tab-content-datasetDetailsFull\">\r\n          <div class=\"tab-pane\" id=\"grid-tab\">\r\n            <div style=\"height: 100%\">\r\n              <sxy-grid data=\"dataObj.content\" schema-def=\"$ctrl.getSchamaDef($index)\"\r\n                schema=\"{{$ctrl.current.data[$index].schema}}\"\r\n                include=\"dataObj.views[0].include\"\r\n                exclude=\"dataObj.views[0].exclude\"></sxy-grid>\r\n            </div>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"properties-tab\">\r\n            <div class=\"row\">\r\n              <div class=\"col-sm-6\">\r\n                <salaxy-input label=\"Label\" name=\"label\" ng-model=\"dataObj.label\"></salaxy-input>\r\n                <salaxy-input label=\"Technical name\" name=\"name\" ng-model=\"dataObj.name\"></salaxy-input>\r\n                <salaxy-form-group name=\"btnDeleteIndex\" label=\"Remove\">\r\n                  <button type=\"button\" ng-click=\"$ctrl.deleteObject($index)\" class=\"btn btn-danger btn-sm\" ng-disabled=\"$ctrl.usecase.isReadOnly\">Remove object</button>\r\n                </salaxy-form-group>\r\n              </div>\r\n              <div class=\"col-sm-6\">\r\n                <salaxy-input-enum label=\"Schema document\" name=\"schemaDoc\" ng-model=\"dataObj.schemaDoc\" disable-cache=\"true\"\r\n                  options=\"$ctrl.getSchemaDocs()\"></salaxy-input-enum>\r\n                <salaxy-input-typeahead label=\"Schema\" name=\"schema\" ng-model=\"dataObj.schema\" disable-cache=\"true\"\r\n                  options=\"$ctrl.getSchemas(dataObj.schemaDoc)\" disabled=\"(dataObj.schemaDoc || 'any') == 'any'\"></salaxy-input-typeahead>\r\n                <!-- TODO: isArray -->\r\n              </div>\r\n            </div>\r\n            <div class=\"row\">\r\n              <div class=\"col-sm-6\">\r\n                <fieldset>\r\n                  <legend>Include fields (default view)</legend>\r\n                  <ul class=\"list-group\">\r\n                    <li class=\"list-group-item\" ng-repeat=\"incl in dataObj.views[0].include track by $index\">\r\n                      {{ incl }}\r\n                      <div class=\"float-end\">\r\n                        <button class=\"btn btn-primary btn-xs\" title=\"Move up\" ng-click=\"$ctrl.arraymove($ctrl.current.data[$parent.$index].views[0].include, $index, -1)\">&#9650;</button>\r\n                        <button class=\"btn btn-primary btn-xs\" title=\"Move down\" ng-click=\"$ctrl.arraymove($ctrl.current.data[$parent.$index].views[0].include, $index, +1)\">&#9660;</button>\r\n                        <button class=\"btn btn-default btn-xs\" title=\"Delete\" ng-click=\"$ctrl.current.data[$parent.$index].views[0].include.splice($index, 1)\">&#10060;</button>\r\n                      </div>\r\n                    </li>\r\n                    <li class=\"list-group-item\" ng-if=\"!dataObj.views[0].include.length\">No rows selected: All columns</li>\r\n                  </ul>\r\n                  <div style=\"display: inline-block;\">\r\n                    <salaxy-input-typeahead label=\"Add new property\" name=\"addProp\" label-type=\"plain\"\r\n                      ng-model=\"$ctrl.tempNewProperty\" disable-cache=\"true\"\r\n                      ng-change=\"$ctrl.addViewItem($index, 'include', $ctrl.tempNewProperty);$ctrl.tempNewProperty=null\"\r\n                      options=\"$ctrl.getAllPropertiesOfSchema($index)\"></salaxy-input-typeahead>\r\n                  </div>\r\n                  <button type=\"button\" class=\"btn btn-default btn-sm\" ng-click=\"$ctrl.addViewItem($index, 'include', $ctrl.tempNewProperty);$ctrl.tempNewProperty=null\">Add</button>\r\n                </fieldset>\r\n              </div>\r\n              <div class=\"col-sm-6\">\r\n                <fieldset>\r\n                  <legend>Exclude fields (default view)</legend>\r\n                  <ul class=\"list-group\">\r\n                    <li class=\"list-group-item\" ng-repeat=\"incl in dataObj.views[0].exclude track by $index\">\r\n                      {{ incl }}\r\n                      <div class=\"float-end\">\r\n                        <button class=\"btn btn-primary btn-xs\" title=\"Move up\" ng-click=\"$ctrl.arraymove($ctrl.current.data[$parent.$index].views[0].exclude, $index, -1)\">&#9650;</button>\r\n                        <button class=\"btn btn-primary btn-xs\" title=\"Move down\" ng-click=\"$ctrl.arraymove($ctrl.current.data[$parent.$index].views[0].exclude, $index, +1)\">&#9660;</button>\r\n                        <button class=\"btn btn-default btn-xs\" title=\"Delete\" ng-click=\"$ctrl.current.data[$parent.$index].views[0].exclude.splice($index, 1)\">&#10060;</button>\r\n                      </div>\r\n                    </li>\r\n                    <li class=\"list-group-item\" ng-if=\"!dataObj.views[0].exclude.length\">No rows selected: All columns</li>\r\n                  </ul>\r\n                  <div style=\"display: inline-block;\">\r\n                    <salaxy-input-typeahead label=\"Add new property\" name=\"addProp\" label-type=\"plain\"\r\n                      ng-model=\"$ctrl.tempNewProperty\" disable-cache=\"true\"\r\n                      ng-change=\"$ctrl.addViewItem($index, 'exclude', $ctrl.tempNewProperty);$ctrl.tempNewProperty=null\"\r\n                      options=\"$ctrl.getAllPropertiesOfSchema($index)\"></salaxy-input-typeahead>\r\n                  </div>\r\n                  <button type=\"button\" class=\"btn btn-default btn-sm\" ng-click=\"$ctrl.addViewItem($index, 'exclude', $ctrl.tempNewProperty);$ctrl.tempNewProperty=null\">Add</button>\r\n                </fieldset>\r\n              </div>\r\n            </div>\r\n          </div>\r\n          <div class=\"tab-pane\" id=\"validation-tab\">\r\n            <p>TODO: Validation</p>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <div ng-if=\"$ctrl.currentSection == 'debugger'\">\r\n        <salaxy-json-formatter json=\"$ctrl.current\" key=\"'Data'\" open=\"1\"></salaxy-json-formatter>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/workflow/usecases/UsecaseDetails.html\",`<main class=\"salaxy-content sxytpl-usecases-details\">\r\n  <div class=\"btn-toolbar\" style=\"margin-left: 195px; margin-bottom: 2px;\">\r\n    <div class=\"btn-group\">\r\n      <button type=\"button\" class=\"btn btn-primary\" ng-disabled=\"!$ctrl.current || $ctrl.current.isReadOnly\" ng-click=\"$ctrl.save()\" sxy-text=\"SALAXY.UI_Terms.save\"></button>\r\n      </button>\r\n      <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.showCopyAsNew($ctrl.current)\" sxy-text=\"SALAXY.UI_Terms.copyAsNew\"></button>\r\n      <button class=\"btn btn-default\" ng-click=\"$ctrl.reload()\"><i class=\"bi bi-arrow-repeat\" aria-hidden=\"true\"></i></button>\r\n    </div>\r\n   \r\n    <div class=\"btn-group ms-1\">\r\n      <div class=\"form-group\" style=\"line-height: 34px;\">\r\n        <strong> &nbsp; Nimi:</strong> {{$ctrl.current.label}}\r\n      </div>\r\n    </div>\r\n    <div class=\"btn-group ms-auto\">\r\n      <button type=\"button\" class=\"btn btn-danger\" ng-disabled=\"!$ctrl.current || $ctrl.current.isReadOnly\" ng-click=\"$ctrl.delete($ctrl.current)\" sxy-text=\"SALAXY.UI_Terms.delete\" title=\"{{ 'SALAXY.UI_Terms.delete' | sxyTranslate}}\"></button>\r\n    </div>\r\n  </div>\r\n  <div ng-init=\"$ctrl.currentSection = 'basicInfo'\" style=\"display: flex\">\r\n    <div style=\"flex: 0 0 200px;\">\r\n      <salaxy-toggle-buttons ng-model=\"$ctrl.currentSection\" \r\n        options=\"[\r\n            { value: 'basicInfo', label: 'Perustiedot' },\r\n            { value: 'schemas', label: 'Datamalli' },\r\n            { value: 'scripts', label: 'Skriptit' },\r\n            { value: 'schema', label: 'Schema' },\r\n            { value: 'views', label: 'Käyttöliittymä' },\r\n            { value: 'tester', label: 'Testaa' },\r\n            { value: 'debugger', label: 'Debugger' }\r\n        ]\" \r\n        type=\"block\">\r\n      </salaxy-toggle-buttons>\r\n    </div>\r\n    <div ng-if=\"$ctrl.current\" style=\"flex: 1 1 100%;margin-left: -1px; height: calc(100vh - 200px); overflow-y: auto; border: solid 1px #009fd8; padding: 10px;\">\r\n      <div ng-if=\"$ctrl.currentSection == 'basicInfo'\" class=\"form-horizontal\">\r\n        <div class=\"row\">\r\n          <div class=\"col-sm-6\">\r\n            <sxy-form open-api=\"salaxy-secure/schemas/v02.json\" type=\"Usecase\" auto-gen=\"false\" debugger=\"false\" model=\"$ctrl.current\">\r\n              <div>\r\n                <fieldset>\r\n                  <legend>Perustiedot</legend>\r\n                  <p ng-if=\"$ctrl.current.id\"><strong>URI:</strong> <code>{{ $ctrl.current.uri }}</code></p>\r\n                  <sxy-input label=\"Id\" model=\"form.id\"></sxy-input>\r\n                  <sxy-input label=\"Nimi\" model=\"form.label\"></sxy-input>\r\n                  <sxy-input label=\"Kuvaus\" model=\"form.description\"></sxy-input>\r\n                  <sxy-input label=\"Ikoni / kuva\" model=\"form.icon\"></sxy-input>\r\n                  <sxy-input label=\"Objektin tyyppi\" model=\"form.itemType\"></sxy-input>\r\n                  <sxy-input label=\"Tila\" model=\"form.status\"></sxy-input>\r\n                  <sxy-input label=\"Järjestysnumero\" model=\"form.order\"></sxy-input>\r\n                </fieldset>\r\n              </div>\r\n            </sxy-form>\r\n          </div>\r\n          <div class=\"col-sm-6 col-md-4\">\r\n            <fieldset>\r\n              <legend>Perustietojen esikatselu</legend>\r\n              <div class=\"card\">\r\n                <div class=\"text-center card-pic-fixed\" style=\"height: 150px;\">\r\n                  <img ng-if=\"$ctrl.current.icon[0] == 'h'\" ng-src=\"{{$ctrl.current.icon}}\">\r\n                  <div ng-if=\"$ctrl.current.icon[0] != 'h'\" class=\"bg-primary card-pic-icon\">\r\n                    <i class=\"bi\" ng-class=\"($ctrl.current.icon || 'bi') == 'bi' ? 'bi-currency-euro' : $ctrl.current.icon\" aria-hidden=\"true\"></i>\r\n                  </div>\r\n                  <span class=\"badge float-end\" ng-class=\"$ctrl.getStatusBgColor($ctrl.current.status)\">{{ \"UsecaseStatus.\" + $ctrl.current.status | sxyEnum }}</span>\r\n                </div>\r\n                <div class=\"card-body\">\r\n                  <h3 class=\"truncate\">{{ $ctrl.current.label }}</h3>\r\n                  <p style=\"height: 80px;overflow: hidden\">{{ $ctrl.current.description }}</p>\r\n                  <p>\r\n                    <a ng-href=\"#/calc/usecase/new?usecase=%2FUsecaseDefinition%2F{{ $ctrl.current.owner }}%2F{{ $ctrl.current.id }}\" class=\"btn btn-primary\" role=\"button\" style=\"color: white\" sxy-text=\"SALAXY.UI_Terms.createNew\" ps=\"...\"></a>\r\n                  </p>\r\n                </div>\r\n              </div>\r\n            </fieldset>\r\n          </div>\r\n        </div>\r\n      </div>\r\n      <ng-include src=\"'salaxy-components/workflow/usecases/UsecaseDetails_schemas.html'\"></ng-include>\r\n      <ng-include src=\"'salaxy-components/workflow/usecases/UsecaseDetails_scripts.html'\"></ng-include>\r\n      <ng-include src=\"'salaxy-components/workflow/usecases/UsecaseDetails_views.html'\"></ng-include>\r\n      <div ng-if=\"$ctrl.currentSection == 'schema'\" class=\"height100\">\r\n        <sxy-code-editor read-only=\"$ctrl.current.isReadOnly\" lang=\"json\" ng-model=\"$ctrl.editableSchema\"></sxy-code-editor>\r\n      </div>\r\n      <ng-include src=\"'salaxy-components/workflow/usecases/UsecaseDetails_tester.html'\"></ng-include>\r\n      <div ng-if=\"$ctrl.currentSection == 'debugger'\">\r\n        <div class=\"row\">\r\n          <div class=\"col-sm-6\">\r\n            <salaxy-json-formatter json=\"$ctrl.current\" key=\"'Usecase'\" open=\"1\"></salaxy-json-formatter>\r\n          </div>\r\n          <div class=\"col-sm-6\">\r\n            <salaxy-json-formatter json=\"$ctrl.currentItem\" key=\"'Current item'\" open=\"1\"></salaxy-json-formatter>\r\n          </div>\r\n        </div>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</main>`);\n\n $templateCache.put(\"salaxy-components/workflow/usecases/UsecaseDetails_schemas.html\",`<div ng-if=\"$ctrl.currentSection == 'schemas'\">\r\n  <div class=\"btn-toolbar\" role=\"toolbar\">\r\n    <button type=\"button\" ng-click=\"$ctrl.createSchema()\" class=\"btn btn-primary\">Lisää uusi</button>\r\n    <div class=\"btn-group dropdown\">\r\n      <button id=\"selectAction\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\">\r\n        <span ng-if=\"!$ctrl.currentSchema\">Valitse datamalli...</span>\r\n        <span ng-if=\"$ctrl.currentSchema\">{{ $ctrl.currentSchema.title || (\"Ei nimeä \" + ($index + 1)) }}</span>\r\n      </button>\r\n      <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"selectAction\">\r\n        <li ng-repeat=\"(key, schema) in $ctrl.current.schema.components.schemas\" ng-click=\"$ctrl.setCurrentSchema(key)\" role=\"menuitem\">\r\n          <a href=\"\" class=\"dropdown-item\">{{ schema.title || (\"Ei nimeä \" + ($index + 1)) }} ({{ key }})</a>\r\n        </li>\r\n      </ul>\r\n    </div>\r\n    <button type=\"button\" ng-click=\"$ctrl.deleteSchema($ctrl.currentSchemaKey)\" ng-disabled=\"!$ctrl.currentSchema\" class=\"btn btn-danger\">Poista</button>\r\n  </div>\r\n  <hr />\r\n  <div ng-if=\"!$ctrl.currentSchema\" class=\"alert alert-info\">\r\n    Lisää uusi datamalli tai valitse yksi muokattavista.\r\n  </div>\r\n  <div class=\"row form-horizontal\" ng-if=\"$ctrl.currentSchema\">\r\n    <div class=\"col-sm-6\">\r\n      <salaxy-input label=\"Nimi\" name=\"{{ 'schemaTitle' + $index }}\" ng-model=\"$ctrl.currentSchema.title\"></salaxy-input>\r\n    </div>\r\n    <div class=\"col-sm-6\">\r\n      <salaxy-input label=\"Tekninen nimi\" name=\"{{ 'schemaKey' + $index }}\" ng-model=\"$ctrl.currentSchemaKey\" readonly=\"true\"></salaxy-input>\r\n    </div>\r\n    <div class=\"col-12\">\r\n      <h4>Datamallin muokkaus</h4>\r\n      <sxy-schema-editor model=\"$ctrl.currentSchema.properties\"></sxy-schema-editor>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/workflow/usecases/UsecaseDetails_scripts.html\",`<div ng-if=\"$ctrl.currentSection == 'scripts'\">\r\n  <div class=\"btn-toolbar\" role=\"toolbar\">\r\n    <button type=\"button\" ng-click=\"$ctrl.createAction()\" class=\"btn btn-primary\">Lisää uusi</button>\r\n    <div class=\"btn-group dropdown\">\r\n      <button id=\"selectAction\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\" ng-disabled=\"$ctrl.current.actions.length == 0\">\r\n        <span ng-if=\"!$ctrl.currentAction\">Valitse skripti...</span>\r\n        <span ng-if=\"$ctrl.currentAction\">{{ $ctrl.currentAction.label || (\"Ei nimeä \" + ($index + 1)) }}</span>\r\n      </button>\r\n      <ul class=\"dropdown-menu\" role=\"menu\" aria-labelledby=\"selectAction\">\r\n        <li ng-repeat=\"action in $ctrl.current.actions\" ng-click=\"$ctrl.currentAction = action\" role=\"menuitem\">\r\n          <a href=\"\" class=\"dropdown-item\">{{ action.label || (\"Ei nimeä \" + ($index + 1)) }}</a>\r\n        </li>\r\n      </ul>\r\n    </div>\r\n    <button type=\"button\" ng-click=\"$ctrl.deleteAction($ctrl.currentAction)\" ng-disabled=\"!$ctrl.currentAction\" class=\"btn btn-danger\">Poista</button>\r\n    <button type=\"button\" ng-click=\"$ctrl.executeAction()\" class=\"btn float-end\" ng-class=\"'btn-' + ($ctrl.currentAction.uiColor || 'default')\"\r\n      ng-disabled=\"!$ctrl.currentAction.content\">\r\n      {{ $ctrl.currentAction.uiText || \"Käynnistä\" }}\r\n    </button>\r\n  </div>\r\n  <hr />\r\n  <div ng-if=\"!$ctrl.currentAction\" class=\"alert alert-info\">\r\n    Lisää uusi skripti tai valitse yksi muokattavista.\r\n  </div>\r\n  <div class=\"row\" ng-if=\"$ctrl.currentAction\">\r\n    <div class=\"col-sm-6\">\r\n      <salaxy-input label=\"Nimi\" name=\"actionTitle\" ng-model=\"$ctrl.currentAction.label\"></salaxy-input>\r\n      <salaxy-input label=\"Kuvaus\" name=\"actionDescription\" ng-model=\"$ctrl.currentAction.description\"></salaxy-input>\r\n      <salaxy-input-enum label=\"Tyyppi\" name=\"actionType\" ng-model=\"$ctrl.currentAction.actionType\" enum=\"UsecaseActionType\"></salaxy-input-enum>\r\n    </div>\r\n    <div class=\"col-sm-6\">\r\n      <salaxy-input label=\"Napin teksti\" name=\"actionUiText\" ng-model=\"$ctrl.currentAction.uiText\"></salaxy-input>\r\n      <salaxy-input-enum label=\"Napin väri\" name=\"actionUiColor\" ng-model=\"$ctrl.currentAction.uiColor\" enum=\"WorkflowEventUi\"></salaxy-input-enum>\r\n    </div>\r\n    <div class=\"col-12\">\r\n      <div><small>Globals in this script:\r\n          <code>item: <span>{{ $ctrl.itemType || 'any / unknown' }}</span></code>,\r\n          <code>session: UserSession</code>, <code>core: @salaxy/core</code>\r\n          <span ng-if=\"$ctrl.currentExecutor.isAsync\">, <code>ajax: Ajax</code></span>\r\n        </small></div>\r\n      <sxy-code-editor read-only=\"$ctrl.current.isReadOnly\" item-type=\"$ctrl.itemType || 'any'\" ng-model=\"$ctrl.currentAction.content\"></sxy-code-editor>\r\n      <pre class=\"alert\" ng-class=\"'alert-' + ($ctrl.currentExecutor.status || 'default')\">{{ $ctrl.currentExecutor.result | json }}</pre>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/workflow/usecases/UsecaseDetails_tester.html\",`<div ng-if=\"$ctrl.currentSection == 'tester'\" ng-init=\"$ctrl.refreshCurrentInCache();$ctrl.currentView=$ctrl.currentView\">\r\n  <div>\r\n    <div class=\"btn-toolbar\">\r\n      <div class=\"btn-group\">\r\n        <button type=\"button\" class=\"btn btn-primary\" ng-click=\"$ctrl.selectItem('new')\">Luo uusi</button>\r\n        <button type=\"button\" class=\"btn btn-default\" ng-click=\"$ctrl.selectItem('select')\">Valitse testitietue..</button>\r\n        <button type=\"button\" class=\"btn btn-default float-end\" ng-click=\"$ctrl.selectItem(null)\">Tyhjennä</button>\r\n      </div>\r\n      <div class=\"btn-group dropdown\">\r\n        <button id=\"selectView\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\" ng-disabled=\"$ctrl.current.views.length == 0\">\r\n          <span ng-if=\"!$ctrl.currentView\">Oletusnäkymä</span>\r\n          <span ng-if=\"$ctrl.currentView\">{{ $ctrl.currentView.label || (\"Ei nimeä \" + ($index + 1)) }}</span>\r\n        </button>\r\n        <ul class=\"dropdown-menu\"  role=\"menu\" aria-labelledby=\"selectView\">\r\n          <li ng-click=\"$ctrl.currentView = null\" role=\"menuitem\">\r\n            <a href=\"\"  class=\"dropdown-item\">Oletusnäkymä</a>\r\n          </li>\r\n          <li ng-repeat=\"view in $ctrl.current.views\" ng-click=\"$ctrl.currentView = view\" role=\"menuitem\">\r\n            <a href=\"\" class=\"dropdown-item\">{{ view.label || (\"Ei nimeä \" + ($index + 1)) }}</a>\r\n          </li>\r\n        </ul>\r\n      </div>\r\n    </div>\r\n    <div ng-if=\"!$ctrl.currentItem\" class=\"container alert alert-info\">\r\n      <p>Valitse testitietue ja näkymä, jota haluat testata.</p>\r\n    </div>\r\n    <div class=\"container\" ng-if=\"$ctrl.currentItem\" ng-switch=\"$ctrl.current.itemType\" ng-init=\"temp = $ctrl.currentItem\">\r\n      <div ng-switch-when=\"calculation\">\r\n        <div ng-if=\"$ctrl.currentView\">\r\n          <div ng-controller=\"Calculator2022Controller as $ctrl\" ng-init=\"$ctrl.model = temp\">\r\n            <ng-include src=\"'salaxy-dynamic-templates/usecase-custom-view.html'\"></ng-include>\r\n          </div>\r\n        </div>\r\n        <div ng-if=\"!$ctrl.currentView\">\r\n          <salaxy-calc model=\"$ctrl.currentItem\"></salaxy-calc>\r\n        </div>\r\n      </div>\r\n      <div ng-switch-when=\"dataset\">\r\n        <div ng-if=\"$ctrl.currentView\">\r\n          <div ng-controller=\"DatasetsCrudController as $ctrl\" ng-init=\"$ctrl.model = temp\">\r\n            <ng-include src=\"'salaxy-dynamic-templates/usecase-custom-view.html'\"></ng-include>\r\n          </div>\r\n        </div>\r\n        <div ng-if=\"!$ctrl.currentView\">\r\n          <salaxy-dataset-details mode=\"data-edit\" model=\"$ctrl.currentItem\"></salaxy-dataset-details>\r\n        </div>\r\n      </div>\r\n      <div ng-switch-default>\r\n        <p>\r\n          TODO: Testinäkymää ei ole toteutettu datatyypille\r\n          <strong>{{$ctrl.current.itemType}}</strong>.\r\n        </p>\r\n      </div>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/workflow/usecases/UsecaseDetails_views.html\",`<div ng-if=\"$ctrl.currentSection == 'views'\">\r\n  <div class=\"btn-toolbar\" role=\"toolbar\">\r\n    <button type=\"button\" ng-click=\"$ctrl.createView()\" class=\"btn btn-primary\">Lisää uusi</button>\r\n    <div class=\"btn-group dropdown\">\r\n      <button id=\"selectView\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\" ng-disabled=\"$ctrl.current.views.length == 0\">\r\n        <span ng-if=\"!$ctrl.currentView\">Valitse käyttöliittymä...</span>\r\n        <span ng-if=\"$ctrl.currentView\">{{ $ctrl.currentView.label || (\"Ei nimeä \" + ($index + 1)) }}</span>\r\n      </button>\r\n      <ul class=\"dropdown-menu\"role=\"menu\" aria-labelledby=\"selectView\">\r\n        <li ng-repeat=\"view in $ctrl.current.views\" ng-click=\"$ctrl.currentView = view\" role=\"menuitem\">\r\n          <a href=\"\" class=\"dropdown-item\">{{ view.label || (\"Ei nimeä \" + ($index + 1)) }}</a>\r\n        </li>\r\n      </ul>\r\n    </div>\r\n    <button type=\"button\" ng-click=\"$ctrl.deleteView($ctrl.currentView)\" ng-disabled=\"!$ctrl.currentView\" class=\"btn btn-danger\">Poista</button>\r\n  </div>\r\n  <hr />\r\n  <div ng-if=\"!$ctrl.currentView\" class=\"alert alert-info\">\r\n    Lisää uusi näkymä tai valitse yksi muokattavista.\r\n  </div>\r\n  <div class=\"row\" ng-if=\"$ctrl.currentView\">\r\n    <div class=\"col-sm-6\">\r\n      <salaxy-input label=\"Nimi\" name=\"viewTitle\" ng-model=\"$ctrl.currentView.label\"></salaxy-input>\r\n      <salaxy-input label=\"Kuvaus\" name=\"viewDescription\" ng-model=\"$ctrl.currentView.description\"></salaxy-input>\r\n    </div>\r\n    <div class=\"col-sm-6\"></div>\r\n    <div class=\"col-12\">\r\n      <sxy-code-editor read-only=\"$ctrl.current.isReadOnly\" lang=\"html\" ng-model=\"$ctrl.currentView.content\"></sxy-code-editor>\r\n    </div>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/workflow/WorkflowBadge.html\",`<div ng-if=\"$ctrl.mode != 'horizontal'\" class=\"salaxy-component salaxy-workflow-badge\">\r\n  <div ng-repeat=\"event in $ctrl.events\">\r\n    <span ng-click=\"$ctrl.showEventDetails(event)\" class=\"clickable\" ng-class=\"'badge bg-' + event.ui\" title=\"{{ event.message + ' (' + (event.time | sxyTime)  + ')' }}\">\r\n      {{event.message}}\r\n    </span>\r\n  </div>\r\n</div>\r\n<span ng-if=\"$ctrl.mode == 'horizontal' && $ctrl.events.length\" class=\"salaxy-component salaxy-workflow-badge\">\r\n  <span ng-repeat=\"event in $ctrl.events\" ng-click=\"$ctrl.showEventDetails(event)\" class=\"clickable\" ng-class=\"'badge bg-' + event.ui\"\r\n    title=\"{{ event.message + ' (' + (event.time | sxyTime)  + ')' }}\" style=\"margin-right: 4px;\">{{event.message}}</span>\r\n</span>`);\n\n $templateCache.put(\"salaxy-components/workflow/WorkflowButtons.html\",`<div class=\"btn-group salaxy-workflow-buttons\">\r\n  <button class=\"btn btn-icon btn-transparent\" ng-class=\"$ctrl.hasWorkflowEvent('PartnerMessageClosed') ? 'text-success' : 'text-muted'\" ng-disabled=\"$ctrl.disabled\"\r\n    ng-click=\"$ctrl.buttonClick('close')\" title=\"{{ $ctrl.getWorkflowEvent('PartnerMessageClosed').message || ('SALAXY.UI_Terms.markChecked' | sxyTranslate)}}\">\r\n    <span ng-if=\"$ctrl.getWorkflowEvent('PartnerMessageClosed').message\" class=\"badge bg-success\">{{$ctrl.getWorkflowEvent('PartnerMessageClosed').message}}</span>\r\n    <i ng-if=\"!$ctrl.getWorkflowEvent('PartnerMessageClosed').message\" class=\"bi bi-check-circle-fill bi-2x\" ng-class=\"{ 'text-muted': $ctrl.isUpdating }\"></i>\r\n  </button>\r\n  <button ng-disabled=\"$ctrl.disabled\"\r\n    title=\"{{ $ctrl.getWorkflowEvent('PartnerMessageIssue').message || ('SALAXY.NG1.WorkFlowIssueComponent.buttons.showEditor' | sxyTranslate) }}\"\r\n    ng-click=\"$ctrl.buttonClick('issue')\" class=\"btn btn-icon btn-transparent\" ng-class=\"$ctrl.hasWorkflowEvent('PartnerMessageIssue') ? 'text-danger' : 'text-muted'\">\r\n    <span ng-if=\"$ctrl.getWorkflowEvent('PartnerMessageIssue').message\" class=\"badge bg-danger\">{{$ctrl.getWorkflowEvent('PartnerMessageIssue').message}}</span>\r\n    <i ng-if=\"!$ctrl.getWorkflowEvent('PartnerMessageIssue').message\" class=\"bi bi-exclamation-circle-fill bi-2x\" ng-class=\"{ 'text-muted': $ctrl.isUpdating }\"></i>\r\n  </button>\r\n  <div ng-if=\"$ctrl.showWorkflowAssign\" class=\"btn-group workflow-assign dropdown d-flex align-items-center\">\r\n    <button id=\"workflowAssign\" type=\"button\" class=\"btn btn-default dropdown-toggle\" data-bs-toggle=\"dropdown\" ng-disabled=\"$ctrl.disabled\">\r\n      <salaxy-avatar ng-if=\"$ctrl.getAssignedTo().id\" avatar=\"$ctrl.getAssignedTo().avatar\"></salaxy-avatar>\r\n      <span class=\"workflow-assign-title\">{{ $ctrl.getAssignedTo().email ||\r\n        $ctrl.getAssignedTo().avatar.displayName || ('SALAXY.UI_Terms.assignToPerson' | sxyTranslate) }}</span>\r\n    </button>\r\n    <ul class=\"dropdown-menu\"  role=\"menu\" aria-labelledby=\"workflowAssign\">\r\n      <li role=\"menuitem\" ng-if=\"$ctrl.getAssignedTo().id\">\r\n        <a href=\"\"ng-click=\"$ctrl.buttonClick('assign', undefined)\" class=\"dropdown-item\">Poista valinta</a>\r\n      </li>\r\n      <li role=\"menuitem\" ng-repeat=\"credential in $ctrl.credentials\" ng-class=\"{ active: credential == $ctrl.getAssignedTo() }\">\r\n        <a href=\"\" ng-click=\"$ctrl.buttonClick('assign', credential)\" class=\"dropdown-item d-flex align-items-center\">\r\n          <salaxy-avatar avatar=\"credential.avatar\"></salaxy-avatar>\r\n          <span>&nbsp; {{ credential.email || credential.avatar.displayName }}</span>\r\n        </a>\r\n      </li>\r\n    </ul>\r\n  </div>\r\n</div>`);\n\n $templateCache.put(\"salaxy-components/workflow/WorkflowReopen.html\",`<button class=\"btn btn-sm btn-secondary\" ng-disabled=\"$ctrl.disabled\" ng-class=\"{muted : $ctrl.isUpdating}\" ng-if=\"$ctrl.hasWorkflowEvent('PartnerMessageClosed') && $ctrl.apiCtrl.role === 'owner'\" ng-click=\"$ctrl.deleteWorkflowEvent('PartnerMessageClosed')\">\r\n  Avaa keskustelu\r\n</button>`);\n\n      }\n    }]);\n    ","import angular from \"angular\";\r\n\r\nimport { Ajax } from \"@salaxy/core\";\r\nimport { SessionService } from \"../services\";\r\n\r\n/**\r\n * Declaration of salaxy global variable.\r\n * @ignore\r\n */\r\ndeclare let salaxy;\r\n\r\n/**\r\n * User interaction with the current session: UserCredentials, Current Account(s) and Login/Logout.\r\n */\r\nexport class PersonalWebLegacyController implements angular.IController {\r\n\r\n  /**\r\n   * For NG-dependency injection\r\n   * @ignore\r\n   */\r\n  public static $inject = [\r\n    \"AjaxNg1\",\r\n    \"$sce\",\r\n    \"$window\",\r\n    \"$location\",\r\n    \"$timeout\",\r\n    \"SessionService\"\r\n  ];\r\n\r\n  constructor(\r\n    private ajax: Ajax,\r\n\r\n    private $sce: angular.ISCEService,\r\n    private $window: angular.IWindowService,\r\n    private $location: angular.ILocationService,\r\n    private $timeout: angular.ITimeoutService,\r\n\r\n    private sessionService: SessionService,\r\n  ) {\r\n\r\n  }\r\n\r\n  /**\r\n   * Implement IController\r\n   */\r\n  public $onInit() {\r\n    //\r\n    this.$window.addEventListener(\"message\", (event) => this.receiveUrl(event), false);\r\n  }\r\n\r\n  /** Get Archive page (in iframe) */\r\n  public getArchivePage() {\r\n    const url = `${salaxy.config.wwwServer}/YearlyLegacy/Open?access_token=${this.ajax.getCurrentToken()}`;\r\n    return this.$sce.trustAsResourceUrl(url);\r\n  }\r\n\r\n  /** TODO */\r\n  public receiveUrl(event) {\r\n    if (event && event.data && event.data.eventType === \"legacyRedirect\" && event.data.calcId) {\r\n      this.$timeout(() => { this.$location.path(\"/calc/details/\" + event.data.calcId); });\r\n    }\r\n  }\r\n\r\n  /** Get logout url */\r\n  public signOut() {\r\n    const url = `${salaxy.config.wwwServer}`;\r\n    this.sessionService.signOut(url);\r\n  }\r\n}\r\n","import { SitemapNode } from \"@salaxy/core\";\r\n\r\n/** Sitemap for the Palkkaus.fi personal web site (Household and Worker) */\r\nexport class PersonalWebSiteMap {\r\n  /** The sitemap */\r\n  public static sitemap: SitemapNode[] = [\r\n    {\r\n      title: \"SALAXY.NG1_Sitemap.personalWeb.home\",\r\n      url: \"#/\",\r\n      id: \"home\",\r\n      isFullWidth: true,\r\n      cssClass: \"double-sidebar\",\r\n    },\r\n    {\r\n      title: \"SALAXY.NG1_Sitemap.personalWeb.taxcards\",\r\n      url: \"#/taxcards\",\r\n      id: \"taxcards\",\r\n    },\r\n    {\r\n      title: \"SALAXY.NG1_Sitemap.personalWeb.calculations.main\",\r\n      url: \"#/calc\",\r\n      id: \"calc\",\r\n      children: [\r\n        {\r\n          title: \"SALAXY.NG1_Sitemap.personalWeb.calculations.paid\",\r\n          url: \"#/calc/paid\",\r\n        },\r\n        {\r\n          title: \"SALAXY.NG1_Sitemap.personalWeb.calculations.sent\",\r\n          url: \"#/calc/sent\",\r\n        },\r\n        {\r\n          title: \"SALAXY.NG1_Sitemap.personalWeb.calculations.draft\",\r\n          url: \"#/calc/draft\",\r\n        },\r\n        {\r\n          title: \"SALAXY.NG1_Sitemap.personalWeb.calculations.error\",\r\n          url: \"#/calc/error\",\r\n          id: \"error\",\r\n        },\r\n        {\r\n          title: \"SALAXY.NG1_Sitemap.personalWeb.calculations.new\",\r\n          url: \"#/calc/details/new\",\r\n          id: \"new\",\r\n          visibility: \"hidden\",\r\n        },\r\n        {\r\n          title: \"SALAXY.NG1_Sitemap.personalWeb.calculations.calc\",\r\n          url: \"#/calc/details/*\",\r\n          id: \"calc\",\r\n          visibility: \"hidden\",\r\n        },\r\n        {\r\n          title: \"SALAXY.NG1_Sitemap.personalWeb.calculations.share\",\r\n          url: \"#/calc/sharing/*\",\r\n          id: \"calcSharing\",\r\n          visibility: \"hidden\",\r\n        },\r\n      ],\r\n    },\r\n    {\r\n      title:\"Työnantajat\",\r\n      url:\"#/employers\",\r\n      id:\"employers\",\r\n      roles:\"test\"\r\n    },\r\n    {\r\n      title: \"SALAXY.NG1_Sitemap.personalWeb.archive.main\",\r\n      url: \"#/archive/worker-report\",\r\n      id: \"archive\",\r\n      children: [\r\n        {\r\n          title: \"SALAXY.NG1_Sitemap.personalWeb.archive.workerReport\",\r\n          url: \"#/archive/worker-report\",\r\n        },\r\n        {\r\n          title: \"SALAXY.NG1_Sitemap.personalWeb.employerArchive.main\",\r\n          url: \"#/archive/employer-archive\",\r\n          id: \"employer-archive\",\r\n          children: [\r\n            {\r\n              title: \"SALAXY.NG1_Sitemap.personalWeb.employerArchive.employerPaid\",\r\n              url: \"#/archive/employer-paid\",\r\n            },\r\n            {\r\n              title: \"SALAXY.NG1_Sitemap.personalWeb.employerArchive.employerReport\",\r\n              url: \"#/archive/employer-report\",\r\n            },\r\n            {\r\n              title: \"SALAXY.NG1_Sitemap.personalWeb.employerArchive.householdYears.main\",\r\n              url: \"#/household-years/active\",\r\n              id: \"householdYears\",\r\n              children: [\r\n                {\r\n                  title: \"SALAXY.NG1_Sitemap.personalWeb.employerArchive.householdYears.details\",\r\n                  url: \"#/household-years/details/*\",\r\n                  visibility: \"hidden\",\r\n                  id: \"details\",\r\n                },\r\n              ],\r\n            },\r\n            {\r\n              title: \"SALAXY.NG1_Sitemap.personalWeb.archive.householdDeductionReport\",\r\n              url: \"#/archive/household-deduction-report\",\r\n              id: \"householdDeductionReport\",\r\n              visibility: \"hidden\",\r\n            },\r\n          ]\r\n        },\r\n      ]\r\n    },\r\n    {\r\n      title: \"SALAXY.NG1_Sitemap.personalWeb.account\",\r\n      url: \"#/account\",\r\n      id: \"account\",\r\n    },\r\n    {\r\n      title: \"SALAXY.NG1_Sitemap.personalWeb.abc\",\r\n      url: \"https://help.palkkaus.fi/hc/fi\",\r\n      id: \"abc\",\r\n      isFullWidth: true,\r\n    },\r\n  ];\r\n}\r\n","import angular from \"angular\";\r\n\r\nimport { Translations, WebSiteUserRole } from \"@salaxy/core\";\r\n\r\nimport { AppInsightExceptionTracking, RouteHelperProvider } from \"../helpers\";\r\nimport { TemplateInterceptor } from \"../interceptors\";\r\nimport { SessionService, UiHelpers } from \"../services\";\r\nimport { PersonalWebLegacyController } from \"./PersonalWebLegacyController\";\r\nimport { PersonalWebSiteMap } from \"./PersonalWebSiteMap\";\r\n\r\n/** The main angular module configuration. */\r\nangular.module(\"palkkaus.web.personal\", [\"ngRoute\", \"salaxy.ng1.components.all\"])\r\n\r\n  // Set sitemap for navigation\r\n  .constant(\"SITEMAP\", PersonalWebSiteMap.sitemap)\r\n  // Set routes to pages\r\n  .config([\"RouteHelperProvider\", (routeHelperProvider: RouteHelperProvider) => {\r\n    const personalRoot = \"salaxy-components/pages-personal/\";\r\n    routeHelperProvider\r\n      .setCustomSectionRoot(\"salaxy-components/pages-personal\")\r\n      .homeDefault(\"home\")\r\n      .defaultSection(\"home\", [\"timeline-tester\"], \"./app/views/ng1/pages-undercon\", personalRoot + \"home\")\r\n\r\n      // [], \"./app/views/ng1/pages-undercon\" is a method for temporarily moving some pages to web where view changes require no build.\r\n      .defaultSection(\"calc\", [], \"./app/views/ng1/pages-undercon\", personalRoot + \"calc\")\r\n      .defaultSection(\"workers\", [], \"./app/views/ng1/pages-undercon\", personalRoot + \"workers\")\r\n      .defaultSection(\"account\", [], \"./app/views/ng1/pages-undercon\", personalRoot + \"account\")\r\n      .defaultSection(\"archive\", [], \"./app/views/ng1/pages-undercon\", personalRoot + \"archive\")\r\n      .defaultSection(\"taxcards\", [], \"./app/views/ng1/pages-undercon\", personalRoot + \"taxcards\")\r\n      .defaultSection(\"employers\", [], \"./app/views/ng1/pages-undercon\", personalRoot + \"employers\")\r\n      /** Temporary until the household site is shut down (02/2021) */\r\n      .defaultSection(\"employment\", [], \"./app/views/ng1/pages-undercon\", personalRoot + \"employment\")\r\n      .defaultSection(\"calc-household\", [], \"./app/views/ng1/pages-undercon\", personalRoot + \"calc\")\r\n      .defaultSection(\"workers-household\", [], \"./app/views/ng1/pages-undercon\", personalRoot + \"workers\")\r\n      .defaultSection(\"account-household\", [], \"./app/views/ng1/pages-undercon\", personalRoot + \"account\")\r\n      .defaultSection(\"taxcards-household\", [], \"./app/views/ng1/pages-undercon\", personalRoot + \"taxcards\")\r\n\r\n      // Not currenlty in use\r\n      .defaultSection(\"payroll\")\r\n      .customSection(\"messages\")\r\n      .defaultSection(\"reports\")\r\n\r\n      .otherwiseDefault();\r\n  }])\r\n  .config(AppInsightExceptionTracking)\r\n  .config([\"$httpProvider\", ($httpProvider: angular.IHttpProvider) => {\r\n    // Clear cached templates in browser every hour\r\n    $httpProvider.interceptors.push(TemplateInterceptor.factory(/views\\//, \"YYYYMMDDHH\"));\r\n  }])\r\n  .controller({PersonalWebLegacyController})\r\n  // eslint-disable-next-line @typescript-eslint/no-unused-vars\r\n  .run([\"UiHelpers\", (uiHelpers: UiHelpers) => {\r\n    // UiHelpers is required for url detection (access token & return url)\r\n  }])\r\n  .run([\"SessionService\", \"$rootScope\", (sessionService: SessionService, $rootScope: angular.IRootScopeService) => {\r\n    Translations.setLocalesPath(\"/locales\");\r\n    sessionService.onAuthenticatedSession($rootScope, () => {\r\n      if (sessionService.isInRole(\"household\")) {\r\n        // Override household => worker role.\r\n        (sessionService.personAccount as any).lastLoginAsServer = sessionService.personAccount.lastLoginAs;\r\n        sessionService.personAccount.lastLoginAs = WebSiteUserRole.Worker;\r\n      }\r\n    });\r\n  }])\r\n  ;\r\n"],"names":["_AjaxNg1","$http","$q","config","globalConfig","Configs","apiServer","useCredentials","useCookie","method","request","token","response","error","headers","headersObject","key","data","Cookies","Token","isStronglyAuthorizedPayer","errorThrown","msg","AjaxNg1","_WizardController","$scope","wizardService","stepNumber","WizardController","_CustomerOnboardingController","onboardingService","sessionService","authorizedAccountService","ajax","$location","steps","reason","link","body","currentAccountId","PensionCompany","pensionCompany","SettingsLogic","accountId","CustomerOnboardingController","_WorkerOnboardingController","uiHelpers","signatureService","checkFunction","x","ssn","id","signatureMethods","WorkerOnboardingController","_HouseholdOnboardingController","HouseholdOnboardingController","_CompanyOnboardingController","r","Role","rawUrl","baseUrl","accessToken","urlParam","cancelUrl","successUrl","Translations","businessId","searchType","onBoardingId","skin","origin","url","result","start","end","CompanyOnboardingController","_SigningController","$sce","$timeout","onboarding","authMethod","value","arr","AuthorizationType","loading","WebSiteUserRole","SigningController","_SignatureController","methodGroup","SignatureController","_CrudControllerBase","crudService","$attrs","copySourceId","copySource","selectedItem","selectedItemId","confirmMessage","newItem","copy","item","CrudControllerBase","_AccountAuthorizationController","partnerSite","authorizedAccount","callback","avatar","role","AccountAuthorizationController","_CertificateController","certificateService","certificateApi","f","certificate","CertificateController","window","minErrConfig","errorHandlingConfig","isObject","isDefined","isValidObjectMaxDepth","isBoolean","maxDepth","isNumber","minErr","module","ErrorConstructor","regex","errRegExp","code","template","message","templateArgs","sliceArgs","arg","toDebugString","paramPrefix","i","match","index","REGEX_STRING_REGEXP","VALIDITY_STATE_PROPERTY","hasOwnProperty","lowercase","string","isString","uppercase","msie","jqLite","jQuery","slice","splice","push","toString","getPrototypeOf","ngMinErr","angular","angularModule","uid","isArrayLike","obj","isWindow","isArray","length","forEach","iterator","context","isFunction","isPrimitive","isBlankObject","forEachSorted","keys","reverseParams","iteratorFn","nextUid","setHashKey","h","baseExtend","dst","objs","deep","ii","j","jj","src","isDate","isRegExp","isElement","extend","merge","toInt","str","isNumberNaN","num","inherit","parent","extra","noop","identity","$","valueFn","hasCustomToString","isUndefined","isError","tag","isScope","isFile","isFormData","isBlob","isPromiseLike","TYPED_ARRAY_REGEXP","isTypedArray","isArrayBuffer","trim","escapeForRegexp","s","node","makeMap","items","nodeName_","element","includes","array","arrayRemove","source","destination","stackSource","stackDest","copyRecurse","copyElement","needsRecurse","copyType","copied","re","simpleCompare","a","b","equals","o1","o2","t1","t2","keySet","createMap","csp","ngCspElement","ngCspAttribute","noUnsafeEval","jq","el","ngAttrPrefixes","prefix","name","concat","array1","array2","args","startIndex","bind","self","fn","curryArgs","toJsonReplacer","val","toJson","pretty","fromJson","json","ALL_COLONS","timezoneToOffset","timezone","fallback","requestedTimezoneOffset","addDateMinutes","date","minutes","convertTimezoneToLocal","reverse","dateTimezoneOffset","timezoneOffset","startingTag","elemHtml","NODE_TYPE_TEXT","nodeName","tryDecodeURIComponent","parseKeyValue","keyValue","splitPoint","toKeyValue","parts","arrayValue","encodeUriQuery","encodeUriSegment","pctEncodeSpaces","getNgAttribute","ngAttr","attr","allowAutoBootstrap","document","script","attributes","srcs","isAutoBootstrapAllowed","angularInit","bootstrap","appElement","candidate","modules","defaultConfig","doBootstrap","$provide","$compileProvider","injector","createInjector","scope","compile","NG_ENABLE_DEBUG_INFO","NG_DEFER_BOOTSTRAP","extraModules","reloadWithDebugInfo","getTestability","rootElement","SNAKE_CASE_REGEXP","snake_case","separator","letter","pos","bindJQueryFired","bindJQuery","originalCleanData","jqName","JQLitePrototype","JQLite","elems","events","elem","UNSAFE_restoreLegacyJqLiteXHTMLReplacement","assertArg","assertArgFn","acceptArrayAnnotation","assertNotHasOwnProperty","getter","path","bindFnToScope","len","getBlockNodes","nodes","endNode","blockNodes","stringify","NODE_TYPE_ELEMENT","NODE_TYPE_ATTRIBUTE","NODE_TYPE_COMMENT","NODE_TYPE_DOCUMENT","NODE_TYPE_DOCUMENT_FRAGMENT","setupModuleLoader","$injectorMinErr","ensure","factory","requires","configFn","info","invokeQueue","configBlocks","runBlocks","invokeLater","moduleInstance","invokeLaterAndSetModuleName","block","provider","insertMethod","queue","recipeName","factoryFunction","shallowCopy","serializeObject","seen","version","publishExternalAPI","$$SanitizeUriProvider","$CompileProvider","htmlAnchorDirective","inputDirective","formDirective","scriptDirective","selectDirective","optionDirective","ngBindDirective","ngBindHtmlDirective","ngBindTemplateDirective","ngClassDirective","ngClassEvenDirective","ngClassOddDirective","ngCloakDirective","ngControllerDirective","ngFormDirective","ngHideDirective","ngIfDirective","ngIncludeDirective","ngInitDirective","ngNonBindableDirective","ngPluralizeDirective","ngRefDirective","ngRepeatDirective","ngShowDirective","ngStyleDirective","ngSwitchDirective","ngSwitchWhenDirective","ngSwitchDefaultDirective","ngOptionsDirective","ngTranscludeDirective","ngModelDirective","ngListDirective","ngChangeDirective","patternDirective","requiredDirective","minlengthDirective","maxlengthDirective","ngValueDirective","ngModelOptionsDirective","ngIncludeFillContentDirective","hiddenInputBrowserCacheDirective","ngAttributeAliasDirectives","ngEventDirectives","$AnchorScrollProvider","$AnimateProvider","$CoreAnimateCssProvider","$$CoreAnimateJsProvider","$$CoreAnimateQueueProvider","$$AnimateRunnerFactoryProvider","$$AnimateAsyncRunFactoryProvider","$BrowserProvider","$CacheFactoryProvider","$ControllerProvider","$DocumentProvider","$$IsDocumentHiddenProvider","$ExceptionHandlerProvider","$FilterProvider","$$ForceReflowProvider","$InterpolateProvider","$IntervalProvider","$$IntervalFactoryProvider","$HttpProvider","$HttpParamSerializerProvider","$HttpParamSerializerJQLikeProvider","$HttpBackendProvider","$xhrFactoryProvider","$jsonpCallbacksProvider","$LocationProvider","$LogProvider","$ParseProvider","$RootScopeProvider","$QProvider","$$QProvider","$SceProvider","$SceDelegateProvider","$SnifferProvider","$$TaskTrackerFactoryProvider","$TemplateCacheProvider","$TemplateRequestProvider","$$TestabilityProvider","$TimeoutProvider","$WindowProvider","$$RAFProvider","$$jqLiteProvider","$$MapProvider","$$CookieReaderProvider","jqCache","jqId","jqNextId","DASH_LOWERCASE_REGEXP","MS_HACK_REGEXP","MOUSE_EVENT_MAP","jqLiteMinErr","cssKebabToCamel","kebabToCamel","fnCamelCaseReplace","all","SINGLE_TAG_REGEXP","HTML_REGEXP","TAG_NAME_REGEXP","XHTML_TAG_REGEXP","wrapMap","wrapMapIE9","wrapMapValueClosing","wrapMapValue","jqLiteIsTextNode","html","jqLiteAcceptsData","nodeType","jqLiteHasData","jqLiteBuildFragment","tmp","wrap","finalHtml","fragment","jqLiteParseHTML","parsed","jqLiteWrapNode","wrapper","jqLiteContains","argIsString","jqLiteAddNodes","jqLiteReady","jqLiteClone","jqLiteDealoc","onlyDescendants","isEmptyObject","removeIfEmptyData","expandoId","expandoStore","jqLiteOff","type","unsupported","jqLiteExpandoStore","handle","removeHandler","listenerFns","jqLiteRemoveData","createIfNecessary","jqLiteData","prop","isSimpleSetter","isSimpleGetter","massGetter","jqLiteHasClass","selector","jqLiteRemoveClass","cssClasses","existingClasses","newClasses","cssClass","jqLiteAddClass","root","elements","jqLiteController","jqLiteInheritedData","names","jqLiteEmpty","jqLiteRemove","keepData","jqLiteDocumentLoaded","action","win","trigger","e","BOOLEAN_ATTR","BOOLEAN_ELEMENTS","ALIASED_ATTR","getBooleanAttrName","booleanAttr","getAliasedAttrName","ret","lowercasedName","isBooleanAttr","getText","option","arg1","arg2","nodeCount","nodeValue","createEventHandler","eventHandler","event","eventFns","eventFnsLength","originalStopImmediatePropagation","handlerWrapper","defaultHandlerWrapper","handler","specialMouseHandlerWrapper","target","related","types","addHandler","specialHandlerWrapper","noEventListener","onFn","replaceNode","children","child","wrapNode","newElement","condition","className","classCondition","extraParameters","dummyEvent","eventFnsCopy","handlerArgs","eventName","arg3","classes","hashKey","nextUidFn","objType","nanKey","NgMapShim","idx","NgMap","ARROW_ARG","FN_ARGS","FN_ARG_SPLIT","FN_ARG","STRIP_COMMENTS","stringifyFn","extractArgs","fnText","anonFn","annotate","strictDi","$inject","argDecl","last","underscore","modulesToLoad","INSTANTIATING","providerSuffix","loadedModules","providerCache","supportObject","service","constant","decorator","providerInjector","createInternalInjector","serviceName","caller","instanceCache","protoInstanceInjector","instanceInjector","loadModules","mods","delegate","provider_","enforceReturnValue","factoryFn","enforce","constructor","$injector","decorFn","origProvider","orig$get","origInstance","moduleFn","runInvokeQueue","invokeArgs","cache","getService","err","injectionArgs","locals","isClass","func","invoke","instantiate","Type","ctor","autoScrollingEnabled","$window","$rootScope","getFirstAnchor","list","getYOffset","offset","scroll","style","scrollTo","elemTop","hash","elm","newVal","oldVal","$animateMinErr","ELEMENT_NODE","NG_ANIMATE_CLASSNAME","mergeClasses","extractElementNode","splitClasses","klass","prepareAnimateOptions","options","postDigestQueue","postDigestElements","$$AnimateRunner","domOperation","addRemoveClassesPostDigest","runner","updateData","changed","handleCSSClassChanges","existing","toAdd","toRemove","status","hasClass","add","remove","classesAdded","classesRemoved","classNameFilter","customFilter","filterFn","expression","reservedRegex","$$animateQueue","domInsert","parentElement","afterElement","afterNode","after","from","to","$$rAF","waitQueue","waitForTick","passed","$sniffer","$$animateAsyncRun","$$isDocumentHidden","INITIAL_STATE","DONE_PENDING_STATE","DONE_COMPLETE_STATE","AnimateRunner","chain","next","runners","count","onProgress","host","rafTick","timeoutTick","resolve","reject","resolveHandler","rejectHandler","initialOptions","closed","run","applyAnimationContents","getHash","trimEmptyHash","Browser","$log","$$taskTrackerFactory","location","history","setTimeout","clearTimeout","pendingDeferIds","taskTracker","cachedState","lastHistoryState","lastBrowserUrl","baseElement","pendingLocation","getCurrentState","cacheState","replace","state","sameState","urlResolve","sameBase","stripHash","urlChangeListeners","urlChangeInit","cacheStateAndFireUrlChange","fireStateOrUrlChange","lastCachedState","prevLastHistoryState","listener","href","delay","taskType","timeoutId","deferId","$document","caches","cacheFactory","cacheId","size","stats","capacity","lruHash","freshEnd","staleEnd","lruEntry","refresh","entry","nextEntry","prevEntry","$cacheFactory","$compileMinErr","UNINITIALIZED_VALUE","_UNINITIALIZED_VALUE","$$sanitizeUriProvider","hasDirectives","Suffix","COMMENT_DIRECTIVE_REGEXP","CLASS_DIRECTIVE_REGEXP","ALL_OR_NOTHING_ATTRS","REQUIRE_PREFIX_REGEXP","EVENT_HANDLER_ATTR_REGEXP","bindingCache","parseIsolateBindings","directiveName","isController","LOCAL_REGEXP","bindings","definition","scopeName","parseDirectiveBindings","directive","assertValidDirectiveName","getDirectiveRequire","require","getDirectiveRestrict","restrict","registerDirective","directiveFactory","$exceptionHandler","directives","registerComponent","controller","makeInjectable","tElement","tAttrs","ddo","identifierForController","regexp","debugInfoEnabled","enabled","strictComponentBindingsEnabled","TTL","commentDirectivesEnabledConfig","cssClassDirectivesEnabledConfig","PROP_CONTEXTS","elementName","propertyName","ctx","registerContext","values","v","SCE_CONTEXTS","$interpolate","$templateRequest","$parse","$controller","$animate","SIMPLE_ATTR_NAME","specialAttrHolder","commentDirectivesEnabled","cssClassDirectivesEnabled","onChangesTtl","onChangesQueue","flushOnChangesQueue","sanitizeSrcset","invokeType","trimmedSrcset","srcPattern","pattern","rawUris","nbrUrisWith2parts","innerIdx","lastTuple","Attributes","attributesToCopy","l","directiveNormalize","classVal","oldClasses","tokenDifference","writeAttr","attrName","booleanKey","aliasedKey","observer","setSpecialAttr","$$observers","attrs","listeners","attribute","safeAddClass","$element","startSymbol","endSymbol","denormalizeTemplate","NG_PREFIX_BINDING","MULTI_ELEMENT_DIR_RE","binding","isolated","noTemplate","dataName","comment","content","$compileNodes","transcludeFn","maxPriority","ignoreDirective","previousCompileContext","compositeLinkFn","compileNodes","namespace","cloneConnectFn","parentBoundTranscludeFn","transcludeControllers","futureParentElement","detectNamespaceForChildElements","$linkNode","wrapTemplate","controllerName","nodeList","$rootElement","linkFns","notLiveList","nodeLinkFn","childNodes","childLinkFn","linkFnFound","nodeLinkFnFound","mergeConsecutiveTextNodes","collectDirectives","applyDirectivesToNode","childScope","childBoundTranscludeFn","stableNodeList","nodeListLength","createBoundTranscludeFn","sibling","previousBoundTranscludeFn","boundTranscludeFn","transcludedScope","cloneFn","controllers","containingScope","boundSlots","slotName","attrsMap","addDirective","nName","ngPrefixMatch","nAttrs","attrStartName","attrEndName","isNgAttr","isNgProp","isNgEvent","multiElementMatch","PREFIX_REGEXP","directiveIsMultiElement","addPropertyDirective","addEventDirective","addAttrInterpolateDirective","addTextInterpolateDirective","collectCommentDirectives","byPriority","groupScan","attrStart","attrEnd","depth","groupElementsLinkFnWrapper","linkFn","compilationGenerator","eager","compiled","compileNode","templateAttrs","jqCollection","originalReplaceDirective","preLinkFns","postLinkFns","terminalPriority","newScopeDirective","controllerDirectives","newIsolateScopeDirective","templateDirective","nonTlbTranscludeDirective","hasTranscludeDirective","hasTemplate","hasElementTranscludeDirective","$compileNode","$template","replaceDirective","childTranscludeFn","didScanForMultipleTransclusion","mightHaveMultipleTransclusionError","directiveValue","assertNoDuplicate","candidateDirective","scanningIndex","replaceWith","slots","slotMap","filledSlots","elementSelector","optional","filled","slotCompileNodes","removeComments","newTemplateAttrs","templateDirectives","unprocessedDirectives","markDirectiveScope","mergeTemplateAttributes","compileTemplateUrl","addLinkFns","pre","post","cloneAndAnnotateFn","linkNode","isolateScope","controllerScope","elementControllers","scopeBindingInfo","controllersBoundTransclude","setupControllers","initializeDirectiveBindings","controllerDirective","getControllers","controllerInstance","invokeLinkFn","scopeToChild","cloneAttachFn","slotTranscludeFn","inheritType","property","controllerKey","newScope","tDirectives","startAttrName","endAttrName","srcAttr","dstAttr","linkQueue","afterTemplateNodeLinkFn","afterTemplateChildLinkFn","beforeTemplateCompileNode","origAsyncDirective","derivedSyncDirective","templateUrl","templateNamespace","tempTemplateAttrs","beforeTemplateLinkNode","linkRootElement","ignoreChildLinkFn","diff","what","previousDirective","wrapModuleNameIfDefined","moduleName","text","interpolateFn","templateNode","templateNodeParent","hasCompileParent","getTrustedAttrContext","attrNormalizedName","getTrustedPropContext","propNormalizedName","sanitizeSrcsetPropertyValue","propName","trustedContext","sanitizer","_","ngPropGetter","ngPropWatch","applyPropValue","propValue","createEventDirective","mustHaveExpression","allOrNothing","newValue","oldValue","elementsToRemove","newNode","firstElementToRemove","removeCount","j2","annotation","strictBindingsCheck","removeWatchCollection","initialChanges","changes","mode","lastValue","parentGet","parentSet","compare","removeWatch","recordChanges","SimpleChange","parentValueWatch","parentValue","isLiteral","initialValue","currentValue","previousValue","triggerOnChangesHook","previous","current","SPECIAL_CHARS_REGEXP","str1","str2","tokens1","tokens2","outer","jqNodes","$controllerMinErr","CNTRL_REG","ident","later","instance","identifier","controllerPrototype","addIdentifier","doc","hidden","changeListener","exception","cause","domNode","APPLICATION_JSON","CONTENT_TYPE_APPLICATION_JSON","JSON_START","JSON_ENDS","JSON_PROTECTION_PREFIX","$httpMinErr","serializeValue","params","serialize","toSerialize","topLevel","defaultHttpResponseTransform","tempData","contentType","hasJsonContentType","isJsonLike","jsonStart","parseHeaders","fillInParsed","line","headerVal","headerKey","headersGetter","headersObj","transformData","fns","isSuccess","defaults","d","useApplyAsync","interceptorFactories","xsrfTrustedOrigins","origins","$browser","$httpBackend","$$cookieReader","defaultCache","reversedInterceptors","interceptorFactory","urlIsAllowedOrigin","urlIsAllowedOriginFactory","requestConfig","mergeHeaders","requestInterceptors","responseInterceptors","promise","interceptor","chainInterceptors","serverRequest","completeOutstandingRequest","interceptors","thenFn","rejectFn","executeHeaderFns","headerContent","processedHeaders","headerFn","header","defHeaders","reqHeaders","defHeaderName","lowercaseDefHeaderName","reqHeaderName","defaultHeadersIteration","reqData","sendReq","transformResponse","resp","createShortMethods","createShortMethodsWithData","deferred","cachedResp","isJsonp","buildUrl","sanitizeJsonpCallbackParam","removePendingReq","resolvePromiseWithResult","resolvePromise","xsrfValue","done","createApplyHandlers","eventHandlers","applyHandlers","callEventHandler","headersString","statusText","xhrStatus","resolveHttpPromise","serializedParams","cbKey","$jsonpCallbacks","$xhrFactory","createHttpBackend","createXhr","$browserDefer","callbacks","rawDocument","timeout","withCredentials","responseType","uploadEventHandlers","callbackPath","jsonpDone","jsonpReq","completeRequest","xhr","abortedByTimeout","requestError","requestAborted","requestTimeout","timeoutRequest","$interpolateMinErr","startSymbolLength","endSymbolLength","escapedStartRegexp","escape","escapedEndRegexp","ch","unescapeText","constantWatchDelegate","objectEquality","constantInterp","unwatch","contextAllowsConcatenation","unescapedText","endIndex","expressions","parseFns","textLength","exp","expressionPositions","singleExpression","parseStringifyInterceptor","compute","oldValues","currValue","$intervalMinErr","$$intervalFactory","intervals","setIntervalFn","tick","clearIntervalFn","interval","markQExceptionHandled","$$q","invokeApply","hasParams","iteration","skipApply","callbackMap","createCallback","callbackId","PATH_MATCH","DEFAULT_PORTS","$locationMinErr","encodePath","segments","decodePath","html5Mode","normalizePath","pathValue","searchValue","hashValue","search","parseAbsoluteUrl","absoluteUrl","locationObj","parsedUrl","DOUBLE_SLASH_REGEX","parseAppUrl","prefixed","startsWith","stripBaseUrl","base","stripFile","serverBase","LocationHtml5Url","appBase","appBaseNoFile","basePrefix","pathUrl","relHref","appUrl","prevAppUrl","rewrittenUrl","LocationHashbangUrl","hashPrefix","withoutBaseUrl","withoutHashUrl","removeWindowsDriveName","windowsFilePathExp","firstPathSegmentMatch","LocationHashbangInHtml5Url","locationPrototype","locationGetter","locationGetterSetter","paramValue","Location","preprocess","LocationMode","baseHref","initialUrl","IGNORE_URI_REGEXP","urlsEqual","setBrowserUrlWithFallback","oldUrl","oldState","rewriteLinks","absHref","initializing","newUrl","newState","defaultPrevented","afterLocationChange","currentReplace","urlOrStateChanged","debug","flag","formatStackTrace","consoleLog","formatError","console","logFn","$parseMinErr","objectValueOf","getStringValue","OPERATORS","operator","ESCAPE","Lexer","ch2","ch3","op1","op2","op3","chars","cp","peek","cp1","cp2","colStr","number","peekCh","quote","rawString","hex","rep","AST","lexer","left","isAssignable","test","alternate","consequent","primary","baseExpression","properties","e1","e2","e3","e4","t","ifDefined","plusFn","isStateless","$filter","filterName","PURITY_ABSOLUTE","PURITY_RELATIVE","isPure","parentIsPure","findConstantAndWatchExpressions","ast","allConstants","argsToWatch","isStatelessFilter","astIsPure","expr","getInputs","lastExpression","assignableAST","isConstant","ASTCompiler","assignable","toWatch","watch","fnKey","intoId","fnString","inputs","input","filter","section","nameId","recursionFn","create","skipWatchIdCheck","right","computed","argument","own","defaultValue","SAFE_IDENTIFIER","UNSAFE_CHARACTERS","c","skip","init","ASTInterpreter","assign","rhs","lhs","watchId","Parser","oneTime","getValueOf","literals","identStart","identContinue","literalName","literalValue","identifierStart","identifierContinue","$parseOptions","$$getAst","interceptorFn","parsedExpression","cacheKey","parser","addWatchDelegate","addInterceptor","expressionInputDirtyCheck","oldValueOfValue","compareObjectIdentity","inputsWatchDelegate","prettyPrintExpression","inputExpressions","lastResult","oldInputValueOf","newInputValue","oldInputValueOfValues","oldInputValues","oneTimeWatchDelegate","isDone","isAllDefined","useInputs","oneTimeWatch","unwatchIfDone","allDefined","first","second","chainedInterceptor","errorOnUnhandledRejections","qFactory","nextTick","exceptionHandler","$qMinErr","queueSize","checkQueue","defer","Deferred","Promise","rejectPromise","progress","notifyPromise","onFulfilled","onRejected","progressBack","scheduleProcessQueue","handleCallback","processQueue","pending","markQStateExceptionHandled","processChecks","toCheck","isStateExceptionHandled","errorMessage","$$reject","$$resolve","then","doResolve","doReject","doNotify","resolver","callbackOutput","when","errback","promises","counter","results","race","$Q","resolveFn","q","requestAnimationFrame","cancelAnimationFrame","rafSupported","raf","timer","$rootScopeMinErr","lastDirtyWatch","applyAsyncId","createChildScopeClass","ChildScope","destroyChildScope","$event","cleanUpScope","Scope","isolate","watchExp","get","watcher","initWatchVal","incrementWatchersCount","watchExpressions","newValues","deregisterFns","changeReactionScheduled","firstRun","shouldCall","unwatchFn","watchGroupAction","$watchCollectionInterceptor","veryOldValue","trackVeryOldValue","changeDetected","changeDetector","internalArray","internalObject","initRun","oldLength","_value","newLength","bothNaN","oldItem","$watchCollectionAction","watchers","dirty","ttl","asyncQueue","watchLog","logIdx","asyncTask","beginPhase","flushApplyAsync","asyncQueuePosition","traverseScopesLoop","clearPhase","postDigestQueuePosition","decrementListenerCount","applyAsyncQueue","$applyAsyncExpression","scheduleApplyAsync","namedListeners","indexOfListener","empty","stopPropagation","listenerArgs","phase","aHrefSanitizationTrustedUrlList","imgSrcSanitizationTrustedUrlList","uri","isMediaUrl","normalizedVal","$sceMinErr","UNDERSCORE_LOWERCASE_REGEXP","snakeToCamel","adjustMatcher","matcher","adjustMatchers","matchers","adjustedMatchers","trustedResourceUrlList","bannedResourceUrlList","$$sanitizeUri","htmlSanitizer","matchUrl","urlIsSameOrigin","urlIsSameOriginAsBaseUrl","isResourceUrlAllowedByPolicy","n","allowed","generateHolderType","Base","holderType","trustedValue","trustedValueHolderBase","byType","trustAs","Constructor","valueOf","maybeTrusted","getTrusted","$sceDelegate","sce","parse","enumValue","lName","eventSupport","isNw","isChromePackagedApp","hasHistoryPushState","android","boxee","bodyStyle","transitions","animations","divElm","log","TaskTracker","taskCounts","taskCallbacks","ALL_TASKS_TYPE","DEFAULT_TASK_TYPE","completeTask","incTaskCount","notifyWhenNoPendingTasks","decTaskCount","countForType","countForAll","getNextCallback","getLastCallbackForType","getLastCallback","nextCb","cbInfo","$templateRequestMinErr","httpOptions","$templateCache","handleRequestFn","tpl","ignoreRequestError","transformer","handleError","testability","opt_exactMatch","matches","dataBinding","bindingName","prefixes","p","attributeEquals","$timeoutMinErr","deferreds","urlParsingNode","originUrl","baseUrlParsingNode","ipv6InBrackets","hostname","requestUrl","urlsAreSameOrigin","getBaseUrl","trustedOriginUrls","parsedAllowedOriginUrls","url1","url2","$$CookieReader","lastCookies","lastCookieString","safeGetCookie","safeDecodeURIComponent","cookieArray","cookie","currentCookieString","suffix","register","filters","currencyFilter","dateFilter","filterFilter","jsonFilter","limitToFilter","lowercaseFilter","numberFilter","orderByFilter","uppercaseFilter","comparator","anyPropertyKey","expressionType","getTypeForFilter","predicateFn","matchAgainstAnyProp","createPredicateFn","shouldMatchPrimitives","actual","expected","deepCompare","dontMatchWholeObject","actualType","expectedType","expectedVal","matchAnyProperty","actualVal","MAX_DIGITS","DECIMAL_SEP","ZERO_CHAR","$locale","formats","amount","currencySymbol","fractionSize","currencySymbolRe","formatNumber","numStr","exponent","digits","numberOfIntegerDigits","zeros","roundNumber","parsedNumber","minFrac","maxFrac","fractionLen","roundAt","digit","k","carry","groupSep","decimalSep","isInfinity","isZero","formattedText","integerLen","decimals","groups","padNumber","negWrap","neg","dateGetter","dateStrGetter","shortForm","standAlone","propPrefix","timeZoneGetter","zone","paddedZone","getFirstThursdayOfYear","year","dayOfWeekOnFirst","getThursdayThisWeek","datetime","weekGetter","firstThurs","thisThurs","ampmGetter","eraGetter","longEraGetter","DATE_FORMATS","DATE_FORMATS_SPLIT","NUMBER_STRING","R_ISO8601_STR","jsonStringToDate","tzHour","tzMin","dateSetter","timeSetter","m","ms","format","object","spacing","limit","begin","sliceFn","sortPredicate","reverseOrder","compareFn","predicates","processPredicates","descending","defaultCompare","compareValues","getComparisonObject","doComparison","predicate","getPredicateValue","v1","v2","sortPredicates","objectValue","type1","type2","value1","value2","ngDirective","defaultLinkFn","normalized","htmlAttr","nullFormCtrl","nullFormRenameControl","PENDING_CLASS","SUBMITTED_CLASS","control","FormController","setupValidity","newName","oldName","PRISTINE_CLASS","DIRTY_CLASS","rootForm","addSetValidityMethod","formDirectiveFactory","isNgForm","formElement","VALID_CLASS","nameAttr","ctrls","handleFormSubmission","parentFormCtrl","setter","getSetter","INVALID_CLASS","clazz","set","unset","validationErrorKey","createAndSet","unsetAndCleanup","cachedToggleClass","toggleValidationCss","isObjectEmpty","combinedState","ctrl","switchValue","isValid","ISO_DATE_REGEXP","URL_REGEXP","EMAIL_REGEXP","NUMBER_REGEXP","DATE_REGEXP","DATETIMELOCAL_REGEXP","WEEK_REGEXP","MONTH_REGEXP","TIME_REGEXP","PARTIAL_VALIDATION_EVENTS","PARTIAL_VALIDATION_TYPES","inputType","textInputType","createDateInputType","createDateParser","weekParser","numberInputType","urlInputType","emailInputType","radioInputType","rangeInputType","checkboxInputType","stringBasedInputType","baseInputType","composing","ev","deferListener","origValue","validity","origBadInput","origTypeMismatch","isoWeek","existingDate","week","hours","seconds","milliseconds","addDays","mapping","iso","previousDate","map","part","parseDate","badInputChecker","isTimeType","previousTimezone","parseDateAndConvertTimeZoneToLocal","ngModelMinErr","isValidDate","formatter","minVal","parsedMinVal","parseObservedDateValue","maxVal","parsedMaxVal","parsedDate","targetFormat","formatted","parserName","nativeValidation","numberFormatterParser","parseNumberAttrVal","isNumberInteger","countDecimals","numString","decimalSymbolIndex","isValidForStep","viewValue","stepBase","step","isNonIntegerValue","isNonIntegerStepBase","isNonIntegerStep","valueDecimals","stepBaseDecimals","stepDecimals","decimalCount","multiplier","modelValue","stepVal","parsedStepVal","supportsRange","hasMinAttr","hasMaxAttr","hasStepAttr","originalRender","setInitialValueAndObserver","minChange","maxChange","stepChange","htmlAttrName","changeFn","elVal","doTrim","parseConstantExpr","parseFn","trueValue","falseValue","valueProperty","CONSTANT_VALUE_REGEXP","updateElementValue","tplAttr","$compile","templateElement","ngBindHtmlGetter","ngBindHtmlWatch","classDirective","indexWatchExpression","classCounts","oldModulo","oldClassString","$index","ngClassIndexWatchAction","toClassString","ngClassWatchAction","addClasses","classString","digestClassCounts","split","removeClasses","updateClasses","newClassString","oldClassArray","newClassArray","toRemoveArray","arrayDifference","toAddArray","toRemoveString","toAddString","classArray","classesToUpdate","newModulo","classValue","forceAsyncEvents","forceAsync","$attr","$transclude","previousElements","clone","$anchorScroll","srcExp","onloadExp","autoScrollExp","changeCounter","currentScope","previousElement","currentElement","cleanupLastIncludeContent","afterAnimation","thisChangeId","ngList","trimValues","UNTOUCHED_CLASS","TOUCHED_CLASS","EMPTY_CLASS","NOT_EMPTY_CLASS","NgModelController","defaultModelOptions","setupModelWatcher","invokeModelGetter","invokeModelSetter","prevValid","prevModelValue","allowInvalid","that","allValid","doneCallback","localValidationRunId","processParseErrors","validationDone","processSyncValidators","processAsyncValidators","errorKey","setValidity","syncValidatorsValid","validator","validatorPromises","writeToModelIfNeeded","debounceDelay","formatters","modelCtrl","formCtrl","optionsCtrl","setTouched","DEFAULT_REGEXP","ModelOptions","inheritAll","NgModelOptionsController","parentOptions","modelOptionsDefinition","ngOptionsMinErr","NG_OPTIONS_REGEXP","parseOptionsExpression","optionsExp","selectElement","valueName","keyName","selectAs","trackBy","selectAsFn","viewValueFn","trackByFn","getTrackByValueFn","getTrackByValue","getLocals","displayFn","groupByFn","disableWhenFn","valuesFn","Option","selectValue","label","group","disabled","getOptionValuesKeys","optionValues","optionValuesKeys","itemKey","watchedArray","optionValuesLength","disableWhen","optionItems","selectValueMap","optionItem","optionTemplate","optGroupTemplate","ngOptionsPostLink","selectCtrl","ngModelCtrl","multiple","providedEmptyOption","unknownOption","ngOptions","listFragment","selectedOptions","getAndUpdateSelectedOption","selectedValues","selections","selectedOption","optionScope","optionEl","needsRerender","updateOptions","addOptionElement","optionElement","updateOptionElement","groupElementMap","groupElement","nextValue","isNotPrimitive","BRACE","IS_WHEN","numberExp","whenExp","whens","whensExpFns","braceReplacement","watchRemover","lastCount","attributeName","tmpMatch","whenKey","countIsNaN","whenExpFn","updateElementText","newText","ngRefMinErr","refValue","NG_REMOVED","ngRepeatMinErr","updateScope","valueIdentifier","keyIdentifier","arrayLength","getBlockStart","getBlockEnd","trackByIdArrayFn","trackByIdObjFn","ngRepeatEndComment","aliasAs","trackByExp","trackByIdExpFn","hashFnLocals","trackByExpGetter","lastBlockMap","collection","previousNode","nextNode","nextBlockMap","collectionLength","trackById","trackByIdFn","collectionKeys","nextBlockOrder","blockKey","NG_HIDE_CLASS","NG_HIDE_IN_PROGRESS_CLASS","newStyles","oldStyles","ngSwitchController","watchExpr","selectedTranscludes","selectedElements","previousLeaveAnimations","selectedScopes","spliceFactory","selected","selectedTransclude","caseElement","selectedScope","anchor","cases","whenCase","ngTranscludeMinErr","fallbackLinkFn","ngTranscludeCloneAttachFn","useFallbackContent","notWhitespace","noopNgModelController","setOptionSelectedStatus","SelectController","optionsMap","unknownVal","realVal","currentlySelectedOption","hashedVal","scheduleRender","renderScheduled","updateScheduled","scheduleViewValueUpdate","renderAfter","optionAttrs","interpolateValueFn","interpolateTextFn","removal","previouslySelected","removeValue","selectPreLink","selectPostLink","shouldBeSelected","currentlySelected","lastView","lastViewRef","selectCtrlName","tElm","tAttr","patternExp","attrVal","parsePatternAttr","oldRegexp","maxlength","maxlengthParsed","parseLength","minlength","minlengthParsed","intVal","PLURAL_CATEGORY","getDecimals","getVF","opt_precision","vf","angular_1","ApiCrudObjectController","api","$routeParams","crudItemIdArr","wasNew","loader","resetOriginal","keepOriginalAsIs","loadAction","wfEvent","wfIdOrType","wfId","ApiCrudObjectControllerBindings","ListControllerBase","isNew","ListControllerBaseBindings","_ODataHelperController","ODataHelperController","_ODataQueryController","cacheService","queryOptions","column","direction","operation","andFilters","valueType","unit","ix","exists","columnName","columns","colSpec","colArr","append","queryString","searchParams","OData","maxCount","notify","ODataQueryController","_CertificateCrudController","fullApi","CertificateCrudController","EditDialogKnownActions","EditDialogParameters","EditDialogResult","_AlertService","alertType","alert","container","hiddenAlerts","currentList","alertElementId","AlertService","Z_NO_FLUSH","Z_PARTIAL_FLUSH","Z_SYNC_FLUSH","Z_FULL_FLUSH","Z_FINISH","Z_BLOCK","Z_OK","Z_STREAM_END","Z_NEED_DICT","Z_STREAM_ERROR","Z_DATA_ERROR","Z_BUF_ERROR","Z_DEFAULT_COMPRESSION","Z_FILTERED","Z_HUFFMAN_ONLY","Z_RLE","Z_FIXED","Z_DEFAULT_STRATEGY","Z_BINARY","Z_TEXT","Z_UNKNOWN","Z_DEFLATED","_has","sources","shrinkBuf","buf","fnTyped","dest","src_offs","dest_offs","chunks","chunk","fnUntyped","typedOK","supported","arraySet","flattenChunks","Buf8","Buf16","Buf32","strApplyOK","strApplyUintOK","utf8len","table","string2buf","c2","m_pos","str_len","buf_len","_buf2binstring","buf2binstring","binstring2buf","buf2string","max","out","c_len","utf16buf","utf8border","adler32","adler","s1","s2","makeTable","crcTable","crc32","crc","BAD","TYPE","inflate_fast","strm","_in","_out","beg","dmax","wsize","whave","wnext","s_window","hold","bits","lcode","dcode","lmask","dmask","here","op","dist","from_source","output","top","dolen","dodist","MAXBITS","ENOUGH_LENS","ENOUGH_DISTS","CODES","LENS","DISTS","lbase","lext","dbase","dext","inflate_table","lens","lens_index","codes","table_index","work","opts","sym","min","curr","drop","used","huff","incr","fill","low","mask","base_index","offs","extra_index","here_bits","here_op","here_val","CODES$1","LENS$1","DISTS$1","Z_FINISH$1","Z_OK$1","Z_STREAM_END$1","Z_NEED_DICT$1","Z_STREAM_ERROR$1","Z_DATA_ERROR$1","Z_MEM_ERROR","Z_BUF_ERROR$1","Z_DEFLATED$1","HEAD","FLAGS","TIME","OS","EXLEN","EXTRA","NAME","COMMENT","HCRC","DICTID","DICT","TYPE$1","TYPEDO","STORED","COPY_","COPY","TABLE","LENLENS","CODELENS","LEN_","LEN","LENEXT","DIST","DISTEXT","MATCH","LIT","CHECK","LENGTH","DONE","BAD$1","MEM","SYNC","ENOUGH_LENS$1","ENOUGH_DISTS$1","zswap32","InflateState","inflateResetKeep","inflateReset","inflateReset2","windowBits","inflateInit2","virgin","lenfix","distfix","fixedtables","updatewindow","inflate","flush","put","have","last_bits","last_op","last_val","hbuf","order","inf_leave","inflateEnd","inflateGetHeader","head","inflateSetDictionary","dictionary","dictLength","dictid","ZStream","GZheader","Inflate","opt","chunkSize","_mode","next_out_utf8","tail","utf8str","dict","allowBufError","zero","STORED_BLOCK","STATIC_TREES","DYN_TREES","MIN_MATCH","MAX_MATCH","LENGTH_CODES","LITERALS","L_CODES","D_CODES","BL_CODES","HEAP_SIZE","MAX_BITS","Buf_size","MAX_BL_BITS","END_BLOCK","REP_3_6","REPZ_3_10","REPZ_11_138","extra_lbits","extra_dbits","extra_blbits","bl_order","DIST_CODE_LEN","static_ltree","static_dtree","_dist_code","_length_code","base_length","base_dist","StaticTreeDesc","static_tree","extra_bits","extra_base","max_length","static_l_desc","static_d_desc","static_bl_desc","TreeDesc","dyn_tree","stat_desc","d_code","put_short","w","send_bits","send_code","tree","bi_reverse","res","bi_flush","gen_bitlen","desc","max_code","stree","has_stree","xbits","overflow","gen_codes","bl_count","next_code","tr_static_init","init_block","bi_windup","copy_block","smaller","_n2","_m2","pqdownheap","compress_block","ltree","dtree","lc","lx","build_tree","scan_tree","prevlen","curlen","nextlen","max_count","min_count","send_tree","build_bl_tree","max_blindex","send_all_trees","lcodes","dcodes","blcodes","rank","detect_data_type","black_mask","static_init_done","_tr_init","_tr_stored_block","stored_len","_tr_align","_tr_flush_block","opt_lenb","static_lenb","_tr_tally","MAX_MEM_LEVEL","LENGTH_CODES$1","LITERALS$1","L_CODES$1","D_CODES$1","BL_CODES$1","HEAP_SIZE$1","MAX_BITS$1","MIN_MATCH$1","MAX_MATCH$1","MIN_LOOKAHEAD","PRESET_DICT","INIT_STATE","EXTRA_STATE","NAME_STATE","COMMENT_STATE","HCRC_STATE","BUSY_STATE","FINISH_STATE","BS_NEED_MORE","BS_BLOCK_DONE","BS_FINISH_STARTED","BS_FINISH_DONE","OS_CODE","errorCode","zero$1","flush_pending","flush_block_only","put_byte","putShortMSB","read_buf","longest_match","cur_match","chain_length","scan","best_len","nice_match","_win","wmask","prev","strend","scan_end1","scan_end","fill_window","_w_size","more","deflate_stored","max_block_size","max_start","deflate_fast","hash_head","bflush","deflate_slow","max_insert","deflate_rle","deflate_huff","Config","good_length","max_lazy","nice_length","max_chain","configurationTable","lm_init","DeflateState","deflateResetKeep","deflateReset","deflateSetHeader","deflateInit2","level","memLevel","strategy","deflate","old_flush","level_flags","bstate","deflateEnd","deflateSetDictionary","avail","tmpDict","toString$1","Deflate","external","support","blob","buffer","_keyStr","encode","chr1","chr2","chr3","enc1","enc2","enc3","enc4","remainingBytes","decode","resultIndex","dataUrlPrefix","totalLength","string2binary","stringToArrayLike","newBlob","checkSupport","stringifyByChunk","stringifyByChar","resultStr","fromCharCodeSupportsTypedArrays","arrayLikeToString","getTypeOf","canUseApply","applyFromCharCode","arrayLikeToArrayLike","arrayFrom","arrayTo","transform","transformTo","outputType","MAX_VALUE_16BITS","MAX_VALUE_32BITS","arguments$1","prepareContent","inputData","isBinary","isOptimizedBinaryString","isBase64","reader","dataType","GenericWorker","withError","me","_utf8len","utf8encode","utf8decode","Utf8DecodeWorker","previousData","nextBoundary","usableData","Utf8EncodeWorker","ConvertWorker","destType","transformZipOutput","mimeType","dataArray","accumulate","helper","updateCallback","chunkType","resultType","meta","StreamHelper","worker","internalType","updateCb","evt","base64","binary","dir","createFolders","compression","compressionOptions","unixPermissions","dosPermissions","DEFAULT_BLOCK_SIZE","DataWorker","dataP","nextIndex","DataLengthProbe","crc32str","crc32wrapper","Crc32Probe","CompressedObject","compressedSize","uncompressedSize","uncompressedWorker","ZipObject","askUnicodeString","isUnicodeString","onUpdate","arrayType","useTypedArray","resolved","FlateWorker","this$1$1","DEFLATE","STORE","compressions","LOCAL_FILE_HEADER","CENTRAL_FILE_HEADER","CENTRAL_DIRECTORY_END","ZIP64_CENTRAL_DIRECTORY_LOCATOR","ZIP64_CENTRAL_DIRECTORY_END","DATA_DESCRIPTOR","decToHex","dec","bytes","generateUnixExternalFileAttr","isDir","generateDosExternalFileAttr","generateZipParts","streamInfo","streamedContent","streamingEnded","platform","encodeFileName","file","useCustomEncoding","encodedFileName","utfEncodedFileName","encodedComment","utfEncodedComment","useUTF8ForFileName","useUTF8ForComment","dosTime","dosDate","extraFields","unicodePathExtraField","unicodeCommentExtraField","dataInfo","bitflag","extFileAttr","versionMadeBy","fileRecord","dirRecord","generateCentralDirectoryEnd","entriesCount","centralDirLength","localDirLength","dirEnd","generateDataDescriptors","descriptor","ZipFileWorker","streamFiles","currentFilePercent","remainingFiles","record","getCompression","fileCompression","zipCompression","compressionName","generateWorker","zip","zipFileWorker","relativePath","DataReader","newIndex","sig","dostime","ArrayReader","sig0","sig1","sig2","sig3","StringReader","Uint8ArrayReader","readerFor","MADE_BY_DOS","MADE_BY_UNIX","findCompression","compressionMethod","ZipEntry","loadOptions","localExtraFieldsLength","fileNameLength","madeBy","extraReader","extraFieldId","extraFieldLength","extraFieldValue","decodeParamType","upath","fileNameByteArray","ucomment","commentByteArray","upathField","ucommentField","ZipEntries","expectedSignature","signature","askedIndex","currentIndex","zipComment","decodeContent","extraDataSize","isGarbage","endOfCentralDirOffset","expectedEndOfCentralDirOffset","extraBytes","checkEntryCRC32","zipEntry","load","zipEntries","files","fileAdd","originalOptions","o","forceTrailingSlash","parentFolder","folderAdd","isCompressedEmpty","zipObjectContent","lastSlash","createFolders$1","JSZip","newObj","staticAccessors","cb","filename","newFolder","kids","this","g","global","Zipcelx","xl","worksheet","colIndex","rowNumber","rowIndex","Texts","cell","row","rowCells","cellIndex","rows","col","cols","xmlCols","xmlRows","_ExcelHelpers","tableData","fileName","rowMapper","saveAs","tablesData","zipName","fieldMapper","Dates","ExcelHelpers","_FileService","alertService","ExportMethod","locale","tabbedData","Tables","TableFormat","csvData","csvFileData","FileService","GravatarHelpers","email","rotateLeft","lValue","iShiftBits","addUnsigned","lX","lY","lX8","lY8","lX4","lY4","lResult","y","z","ff","ac","gg","hh","convertToWordArray","lWordCount","lMessageLength","lNumberOfWordsTemp1","lNumberOfWords","lWordArray","lBytePosition","lByteCount","wordToHex","wordToHexValue","wordToHexValueTemp","lByte","lCount","utf8Encode","utftext","aa","bb","cc","dd","_JsonSchemaService","JsonSchemaCache","openApiUrl","throwIfNotFound","schemaName","schema","JsonSchemaUtils","JsonSchemaService","_AppInsightExceptionTracking","$delegate","appInsights","AppInsightExceptionTracking","CalendarHelper","description","p1","sitemap_PersonLeafs","sitemap_Company","SitemapHelper","evaluateFor","SitemapVisibility","site","parentId","i18Prefix","hasChildrenChanges","isOpen","sectionPostFix","Arrays","session","sitemapProps","sitemap","currentPath","newPath","sectionId","nodeId","CurrentRoute","visibility","Objects","flagValue","_PromisePolyfill","PromisePolyfill","_RouteHelperProvider","$routeProvider","defaultViews","defaultViewsFolder","customViewsFolder","view","customViews","customSectionRoot","homePage","route","skipDefaults","RouteHelperProvider","RRuleFinnish","_NaviService","newSitemap","siteMapNode","targetNode","targetNodePath","main","appStatus","RoleLogic","urlFromPath","checkSession","nodeUrl","newNodeUrl","rule","childMatch","isInSomeRole","roles","filteredNodes","rolesWithoutTest","childNode","childParent","NaviService","_UiCrudHelpers","taxcards","employments","employmentId","buttonTypes","initialTab","employment","savedEmployment","innerResult","personalId","EmploymentRelationTaxcard","TaxCard2019Logic","TaxcardKind","kind","savedTaxcard","incomeLogResult","commitResult","taxcardId","salaryDate","UiCrudHelpers","_UiHelpers","$uibModal","$uibModalStack","logic","modalOptions","modal","modalResult","hasChanges","hideExternalDialogLoader","browserWindow","width","height","windowFeatures","hostUrl","popupBaseUrl","windowTemplateUrl","backdrop","heading","staticBackdrop","okText","cancelText","title","dateRange","calc","dialogResult","EmploymentLogic","taxcard","calEvent","isSimplified","category","calculations","workerList","dataMethod","dataDiffMethod","batchParamsTemplateUrl","autoStart","autoClose","silent","itemToProcess","byteArray","char","returnUrlParameters","dialog","returnUrl","UiHelpers","_WizardService","newSteps","skipNotify","Numeric","WizardService","BaseService","owner","_AuthorizedAccountService","authorizedAccountsApi","sites","AuthorizedAccountService","CacheService","cacheItem","expiresSeconds","_CertificateService","CertificateService","_CredentialService","credentialsApi","credentialId","CredentialService","PayrollLogic","payroll","calcs","Payrolls","CalculatorLogic","_InvoicesService","invoicesApi","settingsService","PaymentChannel","defaultChannel","channelsForRole","InvoicesLogic","paymentObject","channel","saveForPreview","CalculationStatus","savedCalculation","paymentObjectForCfa","Payrolls4","listItemResult","paramsTemplate","itemIds","payrollCalcs","newPaymentObject","reportingPaymentObject","pObj","InvoiceStatus","calculation","ok","LegalEntityType","isPaid","PayrollStatus","SalaryDateKind","SalaryDateLogic","officialDate","expiresAt","previewInvoices","coll","createNewInvoice","createInvoice","previews","grossInvoicePreview","InvoiceType","invoices","navigateToPaymentObject","businessObjectId","invoice","grossInvoice","settingsReceiver","settingsIntermediator","showAddressSelection","sendEInvoice","address","sendLoader","settings","freeText","ft","eInvoiceLogic","itemRef","cfaReferenceCalculations","cfaReferenceTotalResultCalculation","CalculationResultLogic","referenceLogic","pcls","paytrailUrl","updateInvoiceStatus","newStatus","netAndTaxInvoices","netInvoicePreview","taxInvoicePreview","getNetInvoice","netInvoice","getTaxInvoice","taxInvoice","rowLength","remaining","InvoicesService","_OnboardingService","onboardingsApi","authService","signerPersonalId","testSignerPersonalId","asUntrusted","isModelLoaded","close","onboardingType","OnboardingService","_PartnerService","PartnerService","_ReportsService","reportsApi","id2","ReportsLogic","reportType","calcId","inline","ids","preview","refDate","tableType","AccountingReportTableType","periodType","PeriodType","endDate","calculationIds","calculationId","ReportsService","_RowTypeService","CalcRowsLogic","categories","obsolete","CalculationRowType","CalculationRowSource","specialKnownRowTypes","customRow","yearlyNumbers","Years","RowTypeService","_SessionService","sessionApi","accountApi","workers","commaSeparatedRolesList","accountRoles","cssUrl","isDev","entityType","redirectUrl","urlPostfix","OAuthSalaxyAuthorizeMode","getOrigin","regEx","isTestData","clientRoles","useDevelopmentFolder","urlParams","workerId","lang","Language","langParam","workerLang","channelAccounts","splits","kycUpdatedAt","roleList","scopes","partner","removeTokensFromPath","tt","rg","cleanPath","errorDescription","errorUri","SessionService","_SettingsService","accountSettings","transferId","transferPassword","reportOptions","reporting","logoMarkup","check","SettingsService","SignatureMethod","_SignatureService","OnboardingLogic","SignatureService","UiTranslatorService","_UploadService","angularUpload","fileId","invalidFile","UploadService","_UsecasesService","usecases","defaultOnly","filteredList","UsecaseStatus","defaultUri","usecase","ApiItemType","considerEmpty","newVersion","sessionUsecase","StorageLogic","UsecasesService","UserSettingsService","_VarmaPensionService","partnerServicesApi","getEmptyOrder","VarmaPensionService","_WorkflowService","credentialService","apiCtrl","WorkflowService","_CredentialController","uploadService","AvatarPictureType","credential","CredentialController","_EmbeddedUiController","userSettingsService","EmbeddedUiController","_PartnerController","partnerService","PartnerController","_SessionController","resultRole","SessionController","_CompanyAccountController","accounts","company","originalAvatar","editType","CompanyAccountController","_CalcEmploymentController","uiCrudHelpers","CalcEmploymentController","_CalculationCrudController","calculationsApi","reportsService","invoicesService","newCalc","reloaded","updateRows","eprWarningMessage","eprText","onAfterAction","SystemRole","epr","CalculationCrudController","_Calculator2022Controller","calcApi","usecasesService","usecaseUri","uc","Calculator2022Controller","_SalaryBasesController","employmentsApi","jsonSchemaService","datasetsApi","datasetToLoad","HrSuuntiImportLogic","payrollEmployments","mapper","DataMapper","FileParser","validation","ValidationHelper","SalaryBasesController","round","lim","p2b","n2b","b2n","n2p","map$1","h1","h2","eq","isShort","hexParse","alpha","hexString","HUE_RE","hsl2rgbn","hsv2rgbn","hwb2rgbn","rgb","hueValue","rgb2hsl","calln","hsl2rgb","hwb2rgb","hsv2rgb","hue","hueParse","p2","rotate","deg","hslString","names$1","unpack","unpacked","tkeys","nk","nameParse","RGB_RE","rgbParse","rgbString","interpolate","rgb1","rgb2","modHSL","ratio","proto","fromObject","functionParse","Color","color","weight","c1","w2","w1","isNullOrUndef","isNumberFinite","finiteOrDefault","valueOrDefault","toPercentage","dimension","toDimension","thisArg","each","loopable","_elementsEqual","a0","a1","ilen","v0","klen","isValidKey","_merger","tval","sval","merger","mergeIf","_mergerIf","keyResolvers","_splitKey","_getKeyResolver","resolveObjectKey","_capitalize","defined","setsEqual","_isClickEvent","PI","TAU","PITAU","INFINITY","RAD_PER_DEG","HALF_PI","QUARTER_PI","TWO_THIRDS_PI","log10","sign","almostEquals","epsilon","niceNum","range","roundedRange","niceRange","fraction","_factorize","sqrt","almostWhole","rounded","_setMinAndMaxByKey","toRadians","degrees","toDegrees","radians","_decimalPlaces","getAngleFromPoint","centrePoint","anglePoint","distanceFromXCenter","distanceFromYCenter","radialDistanceFromCenter","angle","distanceBetweenPoints","pt1","pt2","_angleDiff","_normalizeAngle","_angleBetween","sameAngleIsFullCircle","angleToStart","angleToEnd","startToAngle","endToAngle","_limitValue","_int16Range","_isBetween","_lookup","cmp","hi","lo","mid","_lookupByKey","ti","_rlookupByKey","_filterBetween","arrayEvents","listenArrayEvents","unlistenArrayEvents","stub","_arrayUnique","requestAnimFrame","throttled","argsToUse","ticking","debounce","_toLeftRightCenter","align","_alignStartEnd","_textX","rtl","_getStartAndCountOfVisiblePoints","points","animationsDisabled","pointCount","iScale","_parsed","axis","minDefined","maxDefined","_scaleRangesChanged","xScale","yScale","_scaleRanges","newRanges","atEdge","elasticIn","elasticOut","effects","isPatternOrGradient","getHoverColor","numbers","colors","applyAnimationsDefaults","applyLayoutsDefaults","intlCache","getNumberFormat","tickValue","ticks","notation","delta","maxTick","calculateDelta","logDelta","numDecimal","remain","Ticks","applyScaleDefaults","_ctx","overrides","descriptors","getScope$1","Defaults","_descriptors","_appliers","targetScope","targetName","scopeObject","targetScopeObject","privateName","local","appliers","apply","toFontString","font","_measureText","gc","longest","textWidth","_longestText","arrayOfThings","jlen","thing","nestedThing","gcLen","_alignPixel","chart","pixel","devicePixelRatio","halfWidth","clearCanvas","canvas","drawPoint","drawPointLegend","xOffset","yOffset","cornerRadius","xOffsetW","yOffsetW","rotation","radius","rad","_isPointInArea","point","area","margin","clipArea","unclipArea","_steppedLineTo","flip","midpoint","_bezierCurveTo","setRenderOpts","decorateText","metrics","bottom","yDecoration","drawBackdrop","oldColor","renderText","lines","stroke","addRoundedRectPath","rect","LINE_HEIGHT","FONT_STYLE","toLineHeight","numberOrZero","_readValueToProps","props","objProps","read","toTRBL","toTRBLCorners","toPadding","toFont","_addGrace","minmax","grace","beginAtZero","change","keepZero","createContext","parentContext","_createResolver","rootScopes","getTarget","finalRootScopes","_resolve","_cached","_resolveWithPrefixes","getKeysFromAllScopes","storage","_attachContext","proxy","subProxy","descriptorDefaults","receiver","_resolveWithContext","_scriptable","_indexable","_allKeys","readKey","needsSubResolver","_proxy","_context","_subProxy","_resolveScriptable","_resolveArray","getValue","_stack","createSubResolver","isIndexable","resolveFallback","getScope","addScopes","parentScopes","parentFallback","allScopes","addScopesFromKey","subGetTarget","resolveKeysFromAllScopes","_parseObjectDataRadialScale","EPSILON","getPoint","getValueAxis","indexAxis","splineCurve","firstPoint","middlePoint","afterPoint","d01","d12","s01","s12","fa","fb","monotoneAdjust","deltaK","mK","pointsLen","alphaK","betaK","tauK","squaredMagnitude","pointCurrent","pointAfter","monotoneCompute","valueAxis","pointBefore","iPixel","vPixel","splineCurveMonotone","slopeDelta","capControlPoint","pt","capBezierPoints","inArea","inAreaPrev","inAreaNext","_updateBezierControlPoints","loop","controlPoints","_isDomSupported","_getParentNode","parseMaxStyle","styleValue","parentProperty","valueInPixels","getComputedStyle","getStyle","positions","getPositionedStyle","styles","useOffsetPos","getCanvasPosition","touches","offsetX","offsetY","box","getRelativePosition","currentDevicePixelRatio","borderBox","paddings","borders","getContainerSize","maxWidth","maxHeight","containerStyle","containerBorder","containerPadding","round1","getMaximumSize","bbWidth","bbHeight","aspectRatio","margins","containerSize","retinaScale","forceRatio","forceStyle","pixelRatio","deviceHeight","deviceWidth","supportsEventListenerOptions","passiveSupported","readUsedSize","_pointInLine","_steppedInterpolation","_bezierInterpolation","getRightToLeftAdapter","rectX","itemWidth","getLeftToRightAdapter","_itemWidth","getRtlAdapter","overrideTextDirection","original","restoreTextDirection","propertyFn","normalizeSegment","getSegment","segment","bounds","startBound","endBound","between","normalize","_boundSegment","inside","subStart","prevValue","startIsBefore","endIsBefore","shouldStart","shouldStop","_boundSegments","sub","findStartAndEnd","spanGaps","solidSegments","cur","_computeSegments","segmentOptions","splitByStyles","completeLoop","doSplitByStyles","chartContext","baseStyle","readStyle","datasetIndex","prevStyle","addStyle","st","styleChanged","replacer","Animator","anims","numSteps","draw","charts","acc","animator","transparent","interpolators","factor","c0","Animation","cfg","elapsed","duration","rej","Animations","animationOptions","animatedProps","newOptions","resolveTargetOptions","awaitAll","running","animation","anim","scaleClip","scale","allowedOverflow","defaultClip","toClip","getSortedDatasetIndices","filterVisible","metasets","applyStack","stack","dsIndex","singleMode","otherValue","convertObjectDataToArray","adata","isStacked","stacked","getStackKey","indexScale","valueScale","getUserBounds","getOrCreateStack","stacks","stackKey","indexValue","subStack","getLastIndexInStack","vScale","positive","updateStacks","iAxis","vAxis","itemStacks","visualValues","getFirstScaleId","scales","createDatasetContext","createDataContext","clearStacks","isDirectUpdateMode","cloneIfNotShared","cached","shared","createStack","canStack","DatasetController","dataset","chooseId","xid","yid","rid","iid","vid","scaleID","_data","resetNewElements","stackChanged","oldStacked","scopeKeys","_stacked","sorted","isNotInOrderComparedToPrev","labels","singleScale","xAxisKey","yAxisKey","parsedValue","otherScale","otherMin","otherMax","_skip","active","drawActiveElementsOnTop","elementType","sharing","transition","sharedOptions","firstOpts","previouslySharedOptions","includeOptions","numMeta","numData","move","removed","newCount","__publicField","getAllScaleValues","visibleMetas","computeMinSampleSize","updateMinAndPrev","computeFitCategoryTraits","ruler","stackCount","thickness","computeFlexCategoryTraits","pixels","percent","parseFloatBar","startValue","endValue","barStart","barEnd","parseValue","parseArrayOrPrimitive","isFloatBar","custom","barSign","actualBase","borderProps","setBorderSkipped","edge","parseEdge","swap","startEnd","orig","setInflateAmount","inflateAmount","BarController","iAxisKey","vAxisKey","bars","reset","horizontal","vpixels","ipixels","dataIndex","skipNull","barThickness","baseValue","minBarLength","floating","startPixel","endPixel","halfGrid","maxBarThickness","center","stackIndex","rects","BubbleController","getRatioAndOffset","circumference","cutout","ratioX","ratioY","startAngle","endAngle","startX","startY","endX","endY","calcMax","calcMin","maxX","maxY","minX","minY","DoughnutController","chartArea","arcs","maxSize","chartWeight","maxRadius","outerRadius","innerRadius","radiusLength","animationOpts","centerX","centerY","animateScale","arc","metaData","total","ringWeightOffset","pointStyle","legendItem","legend","LineController","_dataset","maxGapLength","directUpdate","pointsCount","prevParsed","nullData","border","lastPoint","PolarAreaController","minSize","datasetStartAngle","defaultAngle","PieController","RadarController","pointPosition","ScatterController","showLine","abstract","DateAdapterBase","members","adapters","binarySearch","metaset","intersect","_sorted","lookupMethod","evaluateInteractionItems","position","getDistanceMetricForAxis","useX","useY","deltaX","deltaY","getIntersectItems","useFinalPosition","includeInvisible","getNearestRadialItems","evaluationFunc","getNearestCartesianItems","distanceMetric","minDistance","inRange","distance","getNearestItems","getAxisItems","rangeMethod","intersectsItem","Interaction","STATIC_POSITIONS","filterByPosition","filterDynamicPositionByAxis","sortByWeight","wrapBoxes","boxes","layoutBoxes","stackWeight","buildStacks","layouts","setLayoutDims","vBoxMaxWidth","hBoxMaxHeight","layout","fullSize","buildLayoutBoxes","centerHorizontal","centerVertical","getCombinedMax","maxPadding","updateMaxPadding","boxPadding","updateDims","newWidth","newHeight","widthChanged","heightChanged","handleMaxPadding","updatePos","getMargins","marginForPositions","fitBoxes","refitBoxes","refit","same","other","setBoxDims","placeBoxes","userPadding","layoutItem","minPadding","padding","availableWidth","availableHeight","verticalBoxes","horizontalBoxes","visibleVerticalBoxCount","BasePlatform","BasicPlatform","EXPANDO_KEY","EVENT_TYPES","isNullOrEmpty","initCanvas","renderHeight","renderWidth","displayWidth","displayHeight","eventListenerOptions","addListener","removeListener","fromNativeEvent","nodeListContains","createAttachObserver","entries","createDetachObserver","drpListeningCharts","oldDevicePixelRatio","onWindowResize","dpr","resize","listenDevicePixelRatioChanges","unlistenDevicePixelRatioChanges","createResizeObserver","releaseObserver","createProxyAndListen","DomPlatform","initial","proxies","_detectPlatform","Element$1","_a","final","autoSkip","tickOpts","determinedMaxTicks","determineMaxTicks","ticksLimit","majorIndices","getMajorIndices","numMajorIndices","newTicks","skipMajors","calculateSpacing","avgMajorSpacing","tickLength","maxScale","maxChart","evenMajorSpacing","getEvenSpacing","factors","majorStart","majorEnd","reverseAlign","offsetFromEdge","getTicksLimit","ticksLength","maxTicksLimit","sample","numItems","increment","getPixelForGridLine","offsetGridLines","validIndex","lineValue","garbageCollect","getTickMarkLength","getTitleHeight","createScaleContext","createTickContext","titleAlign","titleArgs","titleX","titleY","positionAxisID","Scale","Element","raw","_userMin","_userMax","_suggestedMin","_suggestedMax","metas","sampleSize","samplingEnabled","reversePixels","numTicks","minRotation","maxRotation","labelRotation","tickWidth","maxLabelDiagonal","labelSizes","maxLabelWidth","maxLabelHeight","titleOpts","gridOpts","display","isHorizontal","titleHeight","widest","highest","tickPadding","angleRadians","cos","sin","labelHeight","labelWidth","isRotated","labelsBelowTicks","offsetLeft","offsetRight","paddingLeft","paddingRight","paddingTop","paddingBottom","widths","heights","widestLabelSize","highestLabelSize","tickFont","fontString","lineHeight","nestedLabel","valueAt","decimal","optionTicks","rot","grid","tl","borderOpts","axisWidth","axisHalfWidth","alignBorderValue","borderValue","alignedLineValue","tx1","ty1","tx2","ty2","x1","y1","x2","y2","optsAtIndex","optsAtIndexBorder","lineWidth","lineColor","borderDash","borderDashOffset","tickColor","tickBorderDash","tickBorderDashOffset","crossAlign","mirror","tickAndPadding","hTickAndPadding","textAlign","lineCount","textOffset","textBaseline","halfCount","strokeColor","strokeWidth","tickTextAlign","labelPadding","backgroundColor","drawLine","lastLineWidth","renderTextOptions","tz","gz","bz","axisID","fontSize","TypedRegistry","override","parentScope","isIChartComponent","registerDefaults","itemDefaults","routeDefaults","routes","propertyParts","sourceName","sourceScope","Registry","typedRegistry","reg","itemReg","registry","component","camelMethod","PluginService","hook","plugin","plugins","allPlugins","createDescriptors","previousDescriptors","localIds","getOpts","pluginOpts","getIndexAxis","datasetDefaults","getAxisFromDefaultScaleID","getDefaultScaleIDFromAxis","idMatchesAxis","axisFromPosition","determineAxis","scaleOptions","getAxisFromDataset","retrieveAxisFromDatasets","boundDs","mergeScaleConfig","chartDefaults","configScales","chartIndexAxis","scaleConf","defaultId","defaultScaleOptions","defaultID","initOptions","initData","initConfig","keyCache","keysCached","cachedKeys","generate","addIfFound","Config$1","datasetType","mainScope","resetCache","_scopeCache","keyLists","subPrefixes","getResolver","needContext","subResolver","resolverCache","hasFunction","isScriptable","scriptable","indexable","KNOWN_POSITIONS","positionIsHorizontal","compare2Level","l1","l2","onAnimationsComplete","onAnimationProgress","getCanvas","instances","getChart","moveNumericKeys","intKey","determineLastEvent","lastEvent","inChartArea","isClick","getSizeForArea","field","getDatasetArea","Chart$1","_b","invalidatePlugins","userConfig","initialCanvas","existingChart","maintainAspectRatio","_aspectRatio","newSize","newRatio","scalesOptions","axisOptions","scaleOpts","updated","isRadial","scaleType","scaleClass","hasUpdated","datasets","newControllers","ControllerClass","datasetElementType","dataElementType","animsDisabled","_active","_lastEvent","existingEvents","newEvents","_hiddenIndices","_dataChanges","datasetCount","makeSet","changeSet","noArea","layers","clip","useClip","visible","_add","_remove","detached","attached","activeElements","lastActive","pluginId","replay","hoverOptions","deactivated","activated","eventFilter","Chart","clipArc","pixelMargin","angleMargin","toRadiusCorners","parseBorderRadius$1","angleDelta","halfThickness","innerLimit","computeOuterLimit","outerArcLimit","rThetaToXY","theta","pathArc","circular","innerR","spacingOffset","noSpacingInnerRadius","noSpacingOuterRadius","avNogSpacingRadius","adjustedAngle","beta","angleOffset","outerStart","outerEnd","innerStart","innerEnd","outerStartAdjustedRadius","outerEndAdjustedRadius","outerStartAdjustedAngle","outerEndAdjustedAngle","innerStartAdjustedRadius","innerEndAdjustedRadius","innerStartAdjustedAngle","innerEndAdjustedAngle","outerMidAdjustedAngle","pCenter","p4","innerMidAdjustedAngle","p8","outerStartX","outerStartY","outerEndX","outerEndY","drawArc","fullCircles","drawBorder","borderWidth","borderJoinStyle","inner","ArcElement","chartX","chartY","rAdjust","betweenAngles","withinRadius","halfAngle","halfRadius","fix","radiusOffset","setStyle","lineTo","getLineMethod","pathVars","paramsStart","paramsEnd","segmentStart","segmentEnd","outside","pathSegment","lineMethod","fastPathSegment","avgX","countX","prevX","lastY","pointIndex","drawX","truncX","_getSegmentMethod","_getInterpolationMethod","strokePathWithCache","strokePathDirect","segmentMethod","usePath2D","LineElement","_interpolate","interpolated","inRange$1","PointElement","mouseX","mouseY","getBarBounds","bar","half","skipOrLimit","parseBorderWidth","maxW","maxH","parseBorderRadius","enableBorderRadius","maxR","enableBorder","boundingRects","skipX","skipY","hasRadius","addNormalRectPath","inflateRect","refRect","BarElement","borderColor","addRectPath","BORDER_COLORS","BACKGROUND_COLORS","getBorderColor","getBackgroundColor","colorizeDefaultDataset","colorizeDoughnutDataset","colorizePolarAreaDataset","getColorizer","containsColorsDefinitions","containsColorsDefinition","plugin_colors","_args","chartOptions","colorizer","lttbDecimation","samples","decimated","bucketWidth","sampledIndex","maxAreaPoint","maxArea","nextA","avgY","avgRangeStart","avgRangeEnd","avgRangeLength","rangeOffs","rangeTo","pointAx","pointAy","minMaxDecimation","minIndex","maxIndex","xMin","dx","lastIndex","intermediateIndex1","intermediateIndex2","cleanDecimatedDataset","cleanDecimatedData","getStartAndCountOfVisiblePointsSimplified","plugin_decimation","xAxis","threshold","_segments","tpoints","_findSegmentEnd","_getBounds","targetSegments","tgt","subBounds","fillSources","fillSource","_getEdge","_pointsFromSegments","boundary","linePoints","_createBoundaryLine","_loop","_shouldApplyFill","_resolveTarget","propagate","visited","_decodeFill","parseFillOption","decodeTargetIndex","firstCh","_getTargetPixel","_getTargetValue","fillOption","_buildStackLine","sourcePoints","linesBelow","getLinesBelow","addPointsBelow","below","sourcePoint","postponed","findPoint","pointValue","firstValue","simpleArc","_getTarget","getLineByIndex","computeBoundary","computeCircularBoundary","computeLinearBoundary","_drawfill","lineOpts","above","doFill","clipVertical","clipY","lineLoop","notShape","clipBounds","interpolatedLineTo","targetLoop","interpolatedPoint","getBoxSize","labelOpts","boxHeight","boxWidth","itemsEqual","Legend","legendItems","labelFont","itemHeight","hitboxes","lineWidths","totalHeight","_itemHeight","columnSizes","heightLimit","totalWidth","currentColWidth","currentColHeight","calculateItemSize","rtlHelper","hitbox","defaultColor","halfFontSize","cursor","drawLegendBox","drawOptions","yBoxTop","xBoxLeft","borderRadius","fillText","realX","fontLineHeight","calculateLegendItemHeight","titleFont","titlePadding","topPaddingPlusHalfFontSize","hitBox","lh","isListened","hoveredItem","sameItem","calculateItemWidth","calculateItemHeight","legendItemText","plugin_legend","ci","usePointStyle","useBorderRadius","Title","textSize","fontOpts","createTitle","plugin_title","titleBlock","plugin_subtitle","positioners","xSet","eventPosition","nearestElement","tp","pushOrConcat","toPush","splitNewlines","createTooltipItem","getTooltipSize","tooltip","footer","bodyFont","footerFont","titleLineCount","footerLineCount","bodyLineItemCount","combinedBodyLength","bodyItem","bodyLineHeight","widthPadding","maxLineWidth","determineYAlign","doesNotFitWithAlign","xAlign","caret","determineXAlign","yAlign","chartWidth","determineAlignment","alignX","alignY","paddingAndSize","getBackgroundPoint","alignment","caretSize","caretPadding","topLeft","topRight","bottomLeft","bottomRight","getAlignedX","getBeforeAfterBodyLines","createTooltipContext","tooltipItems","overrideCallbacks","defaultCallbacks","labelCount","tooltipItem","invokeCallbackWithFallback","_c","beforeTitle","afterTitle","bodyItems","scoped","beforeFooter","afterFooter","labelColors","labelPointStyles","labelTextColors","positionAndSize","backgroundPoint","tooltipPoint","caretPosition","ptX","ptY","x3","y3","titleSpacing","labelColor","labelPointStyle","colorX","rtlColorX","yOffSet","colorY","outerX","innerX","bodySpacing","bodyAlign","displayColors","xLinePadding","fillLineOfText","bodyAlignForCalculation","textColor","tooltipSize","animX","animY","opacity","hasTooltipContent","positionChanged","caretX","caretY","plugin_tooltip","Tooltip","addIfString","addedLabels","findOrAddLabel","_getLabelForValue","CategoryScale","added","generateTicks$1","generationOptions","dataRange","precision","maxTicks","maxDigits","includeBounds","maxSpaces","rmin","rmax","countDefined","minSpacing","niceMin","niceMax","numSpaces","decimalPlaces","relativeLabelSize","LinearScaleBase","setMin","setMax","minSign","maxSign","stepSize","numericGeneratorOptions","LinearScale","log10Floor","changeExponent","isMajor","tickVal","rangeExp","rangeStep","startExp","generateTicks","minExp","significand","lastTick","LogarithmicScale","getTickBackdropHeight","measureLabelSize","determineLimits","fitWithPointLabels","limits","valueCount","pointLabelOpts","additionalAngle","plFont","hLimits","vLimits","updateLimits","buildPointLabelItems","createPointLabelItem","itemOpts","outerDistance","pointLabelPosition","yForAngle","getTextAlignForAngle","leftForTextAlign","isNotOverlapped","centerPointLabels","drawPointLabelBox","backdropColor","backdropLeft","backdropTop","backdropWidth","backdropHeight","drawPointLabels","pointLabels","pathRadiusLine","drawRadiusLine","gridLineOpts","createPointLabelContext","RadialLinearScale","leftMovement","rightMovement","topMovement","bottomMovement","angleMultiplier","scalingFactor","scaledDistance","pointLabel","distanceFromCenter","angleLines","INTERVALS","UNITS","sorter","adapter","isoWeekday","determineUnitForAutoTicks","minUnit","determineUnitForFormatting","determineMajorUnit","addTick","time","timestamps","timestamp","setMajorTicks","majorUnit","major","ticksFromTimestamps","TimeScale","_applyBounds","timeOpts","minor","weekday","hasWeekday","fmt","minorFormat","majorFormat","offsets","ticksOpts","tickLabelWidth","cosRotation","sinRotation","tickFontSize","exampleTime","displayFormats","exampleLabel","prevSource","nextSource","prevTarget","nextTarget","span","TimeSeriesScale","registerables","_CalcChartController","times","getColorSet","Brand","CalcChartController","_CalcHouseholdUsecaseController","workersApi","HouseholdUsecasesLogic","calcResult","CalculationRowUnit","framework","noPeriodStartDateUpdate","currentMonth","CalcHouseholdUsecaseController","CalculatorSection","isActive","isSelectionDone","CalculatorSections","expenses","benefits","deductions","isHouseholdDeductible","unionPaymentType","UnionPaymentType","allSalary","salaryAdditions","isResultsActive","Calculator2019ControllerCrudBindings","_Calculator2019Controller","workerCalc","isOverview","BootstrapStyle","AbsenceCauseCode","Calculator2019Controller","_CalcIrRowsController","IncomeTypesLogic","IrRowSourceType","Unit","CalcIrRowsController","_CalcReportController","templates","ReportType","renderingLang","TotalsReportConfigGenerator","xml","ESalaryMapper","xsltProcessor","xslDoc","xmlDoc","resultDocument","cumulativeCalc","CalculationMapper","Templates","optionsInput","CalcReportController","_CalcReportsController","getExportData","RowsReportConfigGenerator","IrRowsReportConfigGenerator","fileNames","getFileName","CostCenterReportConfigGenerator","CalcReportsController","_CalcReportsDisplayController","CalcReportsDisplayController","_CalcRowTypeController","rowTypeService","searchText","ignoreTop","showChildren","toOption","rowConfig","isParentAdded","isParentAddedAsSelf","listRowType","valueArr","rowTypeKey","rowTypeName","kindName","rowType","_result","rowsLogic","rowConfigsByCategory","irIncomeType","CalcRowTypeController","_CalcRowFormulaController","scriptName","HelpersRoot","returnedCalculation","CalcRowFormulaController","_CalcWorktimeController","anonCalcApi","HolidaysLogic","holidaysCtrl","absencesCtrl","HolidayCode","WageBasis","HolidayPayCalculation","detailsModel","month","monthlyAccrual","holiday","absenceDay","workdays","tabId","tabButton","CalcWorktimeController","_CalcRowDimensionInputController","dimensionIds","truncate","singleValue","CostAccountingDimensionScope","dimensions","CalcRowDimensionInputController","_CalcRowDocumentationController","examplesCdnUrl","hasKind","example","newSample","filteredSamples","RowsUsecaseLogic","dataWithoutKind","dataString","CalcRowDocumentationController","CalcRows2019ControllerBindings","_CalcRows2019Controller","editDialogParams","accountingTargets","currentYear","previousYear","typesToShow","statuses","rowSources","cat","UserDefinedRowLogic","isDebit","targetOdata","currentRow","compRow","price","showEdit","vehicleTypes","vehicleAdditions","irCode","$close","EnumerationsLogic","defaultDimension","ordered","CalcRows2019Controller","_CalcSharingReceiptActionController","CalcSharingReceiptActionController","_CalcsIrRowsController","CalcsIrRowsController","CalculatorPanels","calcAsAny","panels","positionOfLastPanel","panel","_CreditTransferController","qrCode","getDocumentAndSvgNode","Barcodes","QrCodes","iban","BicHelper","Iban","CreditTransferController","_PayrollCrudController","payrollsApi","calcsApi","calendarEvents","taxcardsApi","oldCalc","originalCalc","actions","recalcs","apiCalc","worktime","resultCalc","oldId","empl","ui","noReloadValidation","forceSave","result2","resultInner","unlink","savedPayroll","removeImportedRows","payrolls","targetEmployments","newEmployments","calcsToSave","srcCalc","targetCalc","newRows","$msg","model","MessageThreadStatus","MessageFrom","ThreadedMessageType","calcsEmploymentIds","fetchedEmploymenIds","missingIds","calls","callIds","PayrollCrudController","_Payroll4CrudController","_event","tabToSelect","tab","calcIds","odataResult","removeAllRows","headerChangeInfo","doChangePeriod","apiCalcs","calcsResult","listItem","currentPage","loadedCalc","preCalc","page","truly","showCanvas","launcher","ContactType","calcToSave","applyWorktime","applyEmploymentDefaultRows","totalCalcCount","pageTotal","calcRange","preOriginalCalc","changedCalcs","isMerge","payrollItems","calcPromises","payrollItem","calcPromise","excludePeriodic","infoCalcs","hasException","period","r1","r2","status1","status2","Payroll4CrudController","_PaymentController","newChannel","PaymentController","_CalculationEditorController","ruleSet","ApiValidationErrorType","targetId","accountingReports","confirmationDescription","payload","kevaEmploymentRegCodes","regCode","originalAccountingData","modifiedAccountingData","modified","removedAccount","CalculationEditorController","_CostAccountingController","dimensionForOptions","CostAccountingController","_CalcCostAccountingController","CalcCostAccountingController","_CalcRowCostAccountingController","CalcRowCostAccountingController","_PalkkausPersonalPaymentOverviewController","editDialogParameters","PalkkausPersonalPaymentOverviewController","_SalaryDateKindController","newSalaryDateKind","isCfa","SalaryDateKindController","_CalcLeavesController","periodStart","holidayYear","leave","absence","HolidayBonusPaymentMethod","dt","CalcLeavesController","_CalcRepairController","repairApi","uiHelpersApi","saved","CalcRepairController","current_ansi","VALID_ANSI","CS2CP","set_ansi","reset_ansi","set_cp","reset_cp","char_codes","utf16leread","utf16beread","debom","_getchar","_getansi","$cptable","Base64_map","Base64_encode","c3","Base64_decode","has_buf","Buffer_from","nbfs","enc","new_raw_buf","new_unsafe_buf","s2a","a2s","ab2a","bconcat","bufs","maxlen","widx","L","ridx","chr0","_strrev","pad0","pad_","rpad_","pad0r1","pad0r2","p2_32","pad0r","SSF_isgeneral","days","months","SSF_init_table","table_fmt","SSF_default_map","SSF_default_str","SSF_frac","D","mixed","sgn","B","P_2","P_1","P","Q_2","Q_1","Q","A","SSF_parse_date_code","b2","dow","dout","SSF_fix_hijri","SSFbasedate","SSFdnthresh","SSFbase1904","datenum_local","date1904","epoch","SSF_strip_decimal","SSF_normalize_exp","SSF_small_exp","SSF_large_exp","SSF_general_num","V","SSF_general","SSF_format","SSF_write_date","ss0","ss","outl","outstr","commaify","pct1","write_num_pct","sfmt","mul","write_num","write_num_cm","write_num_exp","ee","fakee","$$","$1","$2","$3","frac1","write_num_f1","aval","den","rr","myn","myd","write_num_f2","dec1","closeparen","phone","hashq","rnd","_frac","flr","write_num_flt","ffmt","ri","oa","lres","rres","write_num_cm2","write_num_pct2","write_num_exp2","write_num_int","SSF_split_fmt","in_str","SSF_abstime","fmt_is_date","eval_fmt","flen","lst","hr","bt","ssm","nstr","vv","myv","ostr","decpt","lasti","retval","cfregex2","chkcond","thresh","choose_fmt","lat","m1","m2","SSF_load","make_ssf","SSFImplicit","dateNFregex","dateNF_regex","dateNF","dateNF_fix","Y","H","M","S","datestr","timestr","CRC32","signed_crc_table","T0","slice_by_16_tables","TT","T1","T2","T3","T4","T5","T6","T7","T8","T9","Ta","Tb","Tc","Td","Te","Tf","crc32_bstr","bstr","seed","C","crc32_buf","crc32_str","CFB","exports","namecmp","R","Z","dirname","write_dos_date","hms","ymd","parse_dos_date","parse_extra_field","prep_blob","flags","sz","fs","get_fs","parse_zip","parse_mad","mver","ssz","nmfs","difat_sec_cnt","dir_start","minifat_start","difat_start","fat_addrs","mv","check_get_mver","check_shifts","dir_cnt","sectors","sectorify","sleuth_fat","sector_list","make_sector_list","ENDOFCHAIN","Paths","FileIndex","FullPaths","read_directory","build_full_paths","HEADER_SIGNATURE","shift","nsectors","FI","FP","pl","dad","get_mfat_entry","mini","MSSZ","__readInt32LE","new_buf","cnt","sector","get_sector_list","chkd","buf_chain","modulus","addr","__toBuffer","sl","minifat_store","namelen","__utf16le","ctime","read_date","mtime","__readUInt32LE","read_file","init_cfb","cfb","seed_cfb","nm","rebuild_cfb","_file","now","fullPaths","HEADER_CLSID","elt","_write","_opts","write_mad","write_zip","mini_size","fat_size","mini_cnt","mfat_cnt","fat_base","fat_cnt","difat_cnt","T","HEADER_SIG","chainit","consts","_nm","find","UCFullPaths","UCPaths","UCPath","write_file","write","_zlib","use_zlib","zlib","InflateRaw","InflRaw","_inflateRawSync","usz","_inflate","_deflateRawSync","_deflate","CLEN_ORDER","LEN_LN","DST_LN","bit_swap_8","use_typed_arrays","bitswap8","bit_swap_n","rev","read_bits_2","bl","read_bits_3","read_bits_4","read_bits_5","read_bits_7","read_bits_n","write_bits_3","write_bits_1","write_bits_8","write_bits_16","realloc","zero_fill_array","clens","cmap","MAX","ccode","ctree","cleni","fix_lmap","fix_dmap","dlens","_deflateRaw","DST_LN_RE","LEN_LN_RE","write_stored","boff","write_huff_fixed","addrs","mlen","len_eb","dst_eb","off","dyn_lmap","dyn_dmap","dyn_cmap","dyn_len_1","dyn_len_2","dyn","_HLIT","_HDIST","_HCLEN","hcodes","outbuf","woff","OL","max_len_1","max_len_2","warn_or_throw","wrn","fcnt","start_cd","csz","efsz","fcsz","EF","parse_local_file","meth","_csz","_usz","ef","cfb_add","cdirs","fp","fi","crcs","sz_cd","namebuf","ContentTypeMap","get_content_type","ext","write_base64_76","write_quoted_printable","encoded","si","parse_quoted_printable","di","oi","parse_mime","fname","cte","ctype","fdata","mboundary","start_di","u","ca","cstr","dispcnt","csl","qp","cfb_new","unsafe","fpath","cfb_del","cfb_mov","old_name","new_name","cfb_gc","ReadShift","CheckField","read_binary","infile","ks","evert","K","basedate","datenum","dnthresh","refdate","refoffset","numdate","parse_isodur","sec","mt","good_pd_date_1","good_pd_date","good_pd","fixdate","cc2str","debomit","utf8write","dup","fuzzynum","wt","lower_months","fuzzydate","lower","split_regex","safe_split_regex","def","getdatastr","getdatabin","getdata","safegetzipfile","getzipfile","getzipdata","safe","getzipstr","getzipbin","zipentries","zip_add_file","zip_read","resolve_path","XML_HEADER","attregexg","tagregex1","tagregex2","tagregex","nsregex","nsregex2","parsexmltag","skip_root","skip_LC","quot","strip_ns","encodings","rencoding","unescapexml","encregex","coderegex","decregex","htmlcharegex","escapehtml","xlml_fixstr","entregex","entrepl","parsexmlbool","utf8reada","utf8readb","ww","utf8readc","utf8corpus","utf8read","matchtag","mtcache","htmldecode","entities","vtregex","vt_cache","vtvregex","vtmregex","parseVector","wtregex","wxt_helper","writextag","xlml_normalize","xlmlregex","XMLNS","XMLNS_main","read_double_le","write_double_le","bs","av","___toBuffer","___utf16le","__readUInt16LE","___hexlify","__hexlify","___utf8","__readUInt8","__utf8","___lpstr","__lpstr","___cpstr","__cpstr","___lpwstr","__lpwstr","___lpp4","__lpp4","___8lpp4","__8lpp4","___double","__double","is_buf","__readInt16LE","__readInt32BE","oI","oR","oo","loc","__writeUInt32LE","__writeInt32LE","__writeUInt16LE","WriteShift","hexstr","fld","parsenoop","recordhopper","tmpbyte","cntbyte","RT","XLSBRecordEnum","buf_array","blksz","newblk","curbuf","endbuf","shift_cell_xls","shift_range_xls","encode_cell_xls","biff","encode_cell","fix_col","fix_row","encode_range_xls","encode_col","encode_row","decode_row","rowstr","unfix_row","decode_col","colstr","unfix_col","split_cell","decode_cell","decode_range","encode_range","cs","ce","safe_decode_range","safe_format_cell","format_cell","BErr","sheet_to_workbook","sheet","sheets","sheet_add_aoa","_ws","dense","ws","_R","_C","_origin","_range","__R","__C","cell_ref","aoa_to_sheet","parse_Int32LE","parse_XLWideString","cchCharacters","parse_StrRun","parse_RichStr","rgsStrRun","dwSizeStrRun","parse_BrtCommentText","parse_XLSBCell","iStyleRef","parse_XLSBShortCell","parse_XLSBCodeName","parse_XLNullableWideString","parse_XLNameWideString","parse_RelID","parse_RkNumber","fX100","fInt","RK","parse_RfX","parse_UncheckedRfX","parse_Xnum","parse_BrtColor","xColorType","nTS","bR","bG","bB","icv","XLSIcv","rgb2Hex","parse_FontFlags","parse_ClipboardFormatOrString","ClipFmt","parse_ClipboardFormatOrAnsiString","parse_ClipboardFormatOrUnicodeString","VT_I2","VT_I4","VT_BOOL","VT_VARIANT","VT_UI4","VT_FILETIME","VT_BLOB","VT_CF","VT_VECTOR_VARIANT","VT_VECTOR_LPSTR","VT_STRING","VT_USTR","VT_CUSTOM","DocSummaryPIDDSI","SummaryPIDSI","CountryEnum","XLSFillPattern","rgbify","_XLSIcv","RBErr","ct2type","new_ct","parse_ct","ct","ctext","RELS","get_rels_path","parse_rels","currentFilePath","rels","rel","canonictarget","CT_ODS","parse_manifest","Rn","FEtag","CORE_PROPS","CORE_PROPS_REGEX","parse_core_props","EXT_PROPS","load_props_pairs","HP","TOP","hp","parse_ext_props","custregex","parse_cust_props","toks","XLMLDocPropsMap","evert_XLMLDPM","xlml_set_prop","Props","parse_FILETIME","dwLowDateTime","dwHighDateTime","parse_lpstr","pad","parse_lpwstr","parse_VtStringBase","stringType","parse_VtString","parse_VtUnalignedString","parse_VtVecLpwstrValue","parse_VtVecUnalignedLpstrValue","parse_VtHeadingPair","headingString","parse_TypedPropertyValue","headerParts","parse_VtVecHeadingPairValue","cElements","parse_dictionary","CodePage","pid","parse_BLOB","parse_ClipboardData","parse_PropertySet","PIDSI","start_addr","NumProps","Dictionary","DictObj","PropID","Offset","PropH","fail","piddsi","oldpos","parsebool","parse_PropertySetStream","clsid","NumSets","FMTID0","FMTID1","Offset0","Offset1","SystemIdentifier","CLSID","PSet0","rval","PSet1","parsenoop2","parslurp","parseuint16","parseuint16a","parse_Bes","parse_ShortXLUnicodeString","cch","encoding","fHighByte","parse_XLUnicodeRichExtendedString","fExtSt","fRichSt","cRun","cbExtRst","parse_XLUnicodeStringNoCch","parse_XLUnicodeString","parse_XLUnicodeString2","parse_ControlInfo","accel","parse_URLMoniker","parse_FileMoniker","cAnti","preamble","ansiPath","unicodePath","parse_HyperlinkMoniker","parse_HyperlinkString","parse_Hyperlink","sVer","displayName","targetFrameName","moniker","oleMoniker","Loc","guid","fileTime","parse_LongRGBA","parse_LongRGB","parse_XLSCell","rw","ixfe","parse_frtHeader","rt","parse_OptXLUnicodeString","parse_XTI","iSupBook","itabFirst","itabLast","parse_RkRec","parse_AddinUdf","udfName","parse_Ref8U","rwFirst","rwLast","colFirst","colLast","parse_RefU","parse_Ref","parse_FtCmo","ot","parse_FtNts","parse_FtCf","parse_FtSkip","FtTab","parse_FtArray","fts","parse_BOF","parse_InterfaceHdr","parse_WriteAccess","UserName","parse_WsBool","parse_BoundSheet8","parse_SST","ucnt","strs","parse_ExtSST","extsst","parse_Row","miyRw","parse_ForceFullCalculation","fullcalc","parse_RecalcId","parse_DefaultRowHeight","fl","parse_Window1","xWn","yWn","dxWn","dyWn","iTabCur","iTabFirst","ctabSel","wTabRatio","parse_Window2","parse_Pane","parse_Font","parse_LabelSst","parse_Label","parse_Format","numFmtId","fmtstr","parse_BIFF2Format","parse_Dimensions","parse_RK","rkrec","parse_MulRk","rkrecs","lastcol","parse_MulBlank","ixfes","parse_CellStyleXF","parse_XF","parse_Guts","parse_BoolErr","parse_Number","xnum","parse_XLHeaderFooter","parse_SupBook","ctab","virtPath","rgst","parse_ExternName","XLSLblBuiltIn","parse_Lbl","chKey","cce","itab","npflen","rgce","parse_NameParsedFormula","parse_ExternSheet","parse_BIFF5ExternSheet","parse_NameCmt","cchName","cchComment","parse_ShrFmla","ref","cUse","parse_SharedParsedFormula","parse_Array","parse_ArrayParsedFormula","parse_MTRSettings","fMTREnabled","fUserSetThreadCount","cUserThreadCount","parse_NoteSh","idObj","stAuthor","parse_Note","parse_MergeCells","merges","cmcs","parse_Obj","parse_BIFF5Obj","cmo","parse_BIFF5OT","cf","grbit","parse_TxO","texts","controlInfo","cchText","hdr","parse_HLink","hlink","parse_HLinkTooltip","wzTooltip","parse_Country","parse_ClrtClient","ccv","parse_Palette","parse_XFCRC","parse_ColInfo","coldx","parse_Setup","parse_ShtProps","parse_Blank","parse_Scl","parse_String","parse_ImData","env","lcb","parse_BIFF2STR","parse_BIFF2NUM","parse_BIFF2INT","parse_BIFF2STRING","parse_BIFF2FONTXTRA","parse_RString","DBF_SUPPORTED_VERSIONS","DBF","dbf_codepage_map","dbf_reverse_map","dbf_to_aoa","memo","vfp","l7","nrow","fpos","rlen","current_cp","fields","hend","dbf_to_sheet","dbf_to_workbook","_RLEN","sheet_to_dbf","ba","aoa","sheet_to_json","hcnt","coltypes","colwidths","coldecimals","guess","_guess","hf","_f","hb","rout","_n","_s","SYLK","sylk_escapes","sylk_char_regex","sylk_char_fn","decode_sylk_char","newcc","sylk_to_aoa","sylk_to_aoa_str","records","rj","next_cell_format","sht","rowinfo","colinfo","cw","Mval","rstr","C_seen_K","C_seen_X","C_seen_S","C_seen_E","formula","rc_to_a1","shrbase","shift_formula_str","F_seen","process_col","pt2px","sylk_to_sheet","aoasht","sylk_to_workbook","write_ws_cell_sylk","a1_to_rc","write_ws_cols_sylk","rec","width2px","px2char","write_ws_rows_sylk","px2pt","sheet_to_sylk","RS","coord","DIF","dif_to_aoa","dif_to_aoa_str","metadata","dif_to_sheet","dif_to_workbook","sheet_to_dif","push_field","topic","push_value","ETH","eth_to_aoa","eth_to_sheet","eth_to_workbook","sep","sheet_to_eth_data","sheet_to_eth","PRN","set_text_arr","prn_to_aoa_str","guess_seps","guess_sep_weights","guess_sep","instr","dsv_to_sheet_str","sepcc","startcc","_re","finish_cell","fuzzyfmla","prn_to_sheet_str","prn_to_sheet","firstbyte","prn_to_workbook","sheet_to_prn","read_wb_ID","OLD_WTF","WK_","lotushopper","Enum","WK1Enum","lotus_to_workbook","lotus_to_workbook_buf","next_n","sidx","snames","realnames","refguess","sheetRows","tmpcell","WK3Enum","osheets","rnames","sheet_to_wk1","write_biff_rec","write_BOF_WK1","write_RANGE","max_R","write_INTEGER","write_NUMBER","write_LABEL","book_to_wk3","wb","write_BOF_WK3","write_XFORMAT_SHEETNAME","wsidx","write_NUMBER_17","write_LABEL_16","wscnt","parse_RANGE","parse_cell","parse_LABEL","parse_INTEGER","parse_NUMBER","parse_FORMULA","wk1_fmla_to_csf","wk1_parse_rc","FuncTab","BinOpTab","argc","argL","argR","parse_cell_3","parse_LABEL_16","parse_NUMBER_18","parse_NUMBER_17","parse_FORMULA_19","parse_NUMBER_25","parse_NUMBER_27","parse_FORMULA_28","parse_SHEETNAMECS","parse_SHEETNAMELP","parse_SHEETINFOQP","parse_XFORMAT","parse_rpr","rpr","pass","parse_rs","tregex","rpregex","parse_r","rregex","rend","rs","rs_to_html","nlregex","parse_rpr2","intro","outro","r_to_html","terms","sitregex","sirregex","sirphregex","parse_si","sstr0","sstr1","sstr2","parse_sst_xml","sst","parse_BrtBeginSst","parse_sst_bin","_JS2ANSI","parse_CRYPTOVersion","parse_DataSpaceVersionInfo","parse_DataSpaceMapEntry","comps","parse_DataSpaceMap","parse_DataSpaceDefinition","parse_TransformInfoHeader","parse_Primary","parse_EncryptionHeader","valid","parse_EncryptionVerifier","parse_EncryptionInfo","vers","parse_EncInfoStd","parse_EncInfoExt","parse_EncInfoAgl","verifier","KeyData","parse_RC4CryptoHeader","parse_RC4Header","crypto_CreatePasswordVerifier_Method1","Password","Verifier","PasswordArray","PasswordDecoded","PasswordByte","Intermediate1","Intermediate2","Intermediate3","crypto_CreateXorArray_Method1","PadArray","InitialCode","XorMatrix","Ror","Byte","XorRor","byte1","byte2","CreateXorKey_Method1","XorKey","CurrentElement","Char","password","Index","ObfuscationArray","Temp","PasswordLastChar","PadIndex","crypto_DecryptData_Method1","Data","XorArrayIndex","XorArray","O","Value","crypto_MakeXorDecryptor","parse_XORObfuscation","parse_FilePassHeader","parse_FilePass","RTF","rtf_to_sheet","rtf_to_sheet_str","rowtf","rtfre","last_index","rtf_to_workbook","sheet_to_rtf","hex2RGB","rgb2HSL","G","H6","L2","hsl2RGB","hsl","h6","X","rgb_tint","tint","DEF_MDW","MAX_MDW","MIN_MDW","MDW","px","char2width","chr","cycle_width","collw","find_mdw_colw","_MDW","DEF_PPI","PPI","XLMLPatternTypeMap","parse_borders","themes","parse_fills","parse_fonts","parse_numFmts","cellXF_uint","cellXF_bool","parse_cellXfs","xf","parse_sty_xml","numFmtRegex","cellXfRegex","fillsRegex","fontsRegex","bordersRegex","parse_BrtFmt","stFmtCode","parse_BrtFont","bls","underline","family","bCharSet","parse_BrtFill","parse_BrtXF","ixfeParent","ifmt","parse_BrtBorder","parse_sty_bin","XLSXThemeClrScheme","parse_clrScheme","parse_fontScheme","parse_fmtScheme","clrsregex","fntsregex","fmtsregex","parse_themeElements","themeltregex","parse_theme_xml","write_theme","Themes","parse_Theme","dwThemeVersion","themeXML","parse_ColorTheme","parse_FullColorExt","parse_IcvXF","parse_XFExtGradient","parse_ExtProp","extType","parse_XFExt","cexts","update_xfext","xfext","xfe","parse_BrtMdtinfo","parse_BrtMdb","parse_BrtBeginEsmdb","parse_xlmeta_bin","metatype","parse_xlmeta_xml","lastmeta","parse_cc_xml","parse_BrtCalcChainItem$","parse_cc_bin","parse_xlink_xml","parse_xlink_bin","parse_drawing","sheet_insert_comments","comments","threaded","people","parse_comments_xml","authors","commentList","authtag","cmnttag","cm","textMatch","parse_tcmnt_xml","tidx","parse_people_xml","parse_BrtBeginComment","rfx","parse_BrtCommentAuthor","parse_comments_bin","CT_VBA","make_vba_xls","newcfb","newpath","parse_ds_bin","parse_ds_xml","parse_ms_bin","parse_ms_xml","rcregex","rcbase","rcfunc","cRel","rRel","fstr","crefregex","$0","$4","$5","shift_formula_xlsx","_xlfn","parseread1","parse_ColRelU","parse_RgceArea","parse_RgceArea_BIFF2","parse_RgceAreaRel","parse_RgceLoc","parse_RgceLoc_BIFF2","parse_RgceElfLoc","parse_RgceLocRel","parse_RgceLocRel_BIFF2","cl","rl","parse_PtgArea","parse_PtgArea3d","ixti","parse_PtgAreaErr","parse_PtgAreaErr3d","parse_PtgAreaN","parse_PtgArray","parse_PtgAttrBaxcel","bitSemi","bitBaxcel","parse_PtgAttrChoose","parse_PtgAttrGoto","bitGoto","parse_PtgAttrIf","bitIf","parse_PtgAttrIfError","parse_PtgAttrSemi","parse_PtgAttrSpaceType","parse_PtgAttrSpace","parse_PtgAttrSpaceSemi","parse_PtgRef","parse_PtgRefN","parse_PtgRef3d","parse_PtgFunc","iftab","FtabArgc","Ftab","parse_PtgFuncVar","cparams","parsetab","Cetab","parse_PtgAttrSum","parse_PtgExp","parse_PtgErr","parse_PtgInt","parse_PtgBool","parse_PtgNum","parse_PtgStr","parse_SerAr","parse_PtgExtraMem","parse_PtgExtraArray","parse_PtgName","nameindex","parse_PtgNameX","parse_PtgNameX_BIFF5","parse_PtgMemArea","parse_PtgMemFunc","parse_PtgRefErr","parse_PtgRefErr3d","parse_PtgMemErr","parse_PtgMemNoMem","parse_PtgTbl","parse_PtgElfLoc","parse_PtgElfNoop","parse_PtgElfCol","parse_PtgElfColS","parse_PtgElfColSV","parse_PtgElfColV","parse_PtgElfLel","parse_PtgElfRadical","parse_PtgElfRadicalLel","parse_PtgElfRadicalS","parse_PtgElfRw","parse_PtgElfRwV","PtgListRT","parse_PtgList","parse_PtgSxName","parse_PtgSheet","parse_PtgEndSheet","parse_PtgMemAreaN","parse_PtgMemNoMemN","parse_PtgAttrNoop","PtgTypes","PtgDupes","Ptg18","Ptg19","parse_RgbExtra","parse_Rgce","ptgs","stringify_array","PtgBinOp","formula_quote_sheet_name","sname","get_ixti_raw","supbooks","XTI","get_ixti","ixtiraw","stringify_formula","nameidx","last_sp","sp","fflen","lbl","bookidx","externbook","ixtidata","lp","rp","parsedf","fnd","PtgNonDisp","_left","rgcb","parse_XLSCellParsedFormula","parse_FormulaValue","parse_Formula","cbf","parse_XLSBParsedFormula","parse_XLSBArrayParsedFormula","parse_XLSBCellParsedFormula","parse_XLSBNameParsedFormula","parse_XLSBSharedParsedFormula","ods_to_csf_formula","ods_to_csf_3D","_ssfopts","default_margins","defs","safe_format","fmtid","fillid","parse_ws_xml_dim","mergecregex","sheetdataregex","hlinkregex","dimregex","colregex","afregex","marginregex","sheetprregex","sheetprregex2","svsregex","parse_ws_xml","data1","data2","mtch","sheetPr","parse_ws_xml_sheetpr","parse_ws_xml_sheetpr2","svs","parse_ws_xml_sheetviews","parse_ws_xml_cols","parse_ws_xml_data","afilter","parse_ws_xml_autofilter","_merge","parse_ws_xml_hlinks","parse_ws_xml_margins","tmpref","rng","seencol","coli","colm","colM","sviewregex","cellregex","rowregex","isregex","refregex","match_v","match_f","sdata","cells","cref","tagr","tagc","sstr","ftag","do_format","arrayf","sharedf","rowobj","rowrite","sheetStubs","marr","marrlen","xlen","rstarti","outa","rslice","___f","_tag","_r","parse_BrtRowHdr","parse_BrtWsDim","parse_BrtWsFmtInfo","parse_BrtWsProp","parse_BrtCellBlank","parse_BrtShortBlank","parse_BrtCellBool","fBool","parse_BrtShortBool","parse_BrtCellError","bError","parse_BrtShortError","parse_BrtCellIsst","isst","parse_BrtShortIsst","parse_BrtCellReal","parse_BrtShortReal","parse_BrtCellRk","parse_BrtShortRk","parse_BrtCellRString","parse_BrtCellSt","parse_BrtShortSt","parse_BrtFmlaBool","parse_BrtFmlaError","parse_BrtFmlaNum","parse_BrtFmlaString","parse_BrtMergeCell","parse_BrtHLink","relId","parse_BrtPane","parse_BrtArrFmla","fAlwaysCalc","parse_BrtShrFmla","BrtMarginKeys","parse_BrtMargins","parse_BrtBeginWsView","parse_BrtDVal","parse_BrtDVal14","parse_ws_bin","ai","af","RR","aii","_d","parse_Cache","nf","F","parse_chart","csheet","nc","parse_cs_xml","parse_BrtCsProp","parse_cs_bin","WBPropsDef","WBViewDef","SheetDef","CalcPrDef","push_defaults_array","push_defaults","parse_wb_defaults","badchars","check_ws_name","_good","wbnsregex","parse_wb_xml","xmlns","dname","dnstart","parse_BrtBundleSh","parse_BrtWbProp","strName","parse_BrtFRTArchID$","parse_BrtName","parse_wb_bin","Names","parse_wb","parse_ws","parse_cs","parse_ms","parse_ds","parse_sty","parse_theme","parse_sst","parse_cmnt","parse_cc","parse_xlink","parse_xlmeta","attregexg2","attregex2","xlml_parsexmltag","words","xlml_parsexmltagobj","XLMLFormatMap","xlml_format","xlml_set_custprop","Custprops","oval","safe_format_xlml","process_style_xlml","stag","I","parse_xlml_data","csty","sid","interiors","xlml_clean_comment","parse_xlml_xml","opening","ishtml","_o","html_to_workbook","sheetnames","cursheet","sheetname","dtag","didx","fidx","pidx","cstys","Workbook","wsprops","raw_Rn3","cma","cmd","ssfidx","_col","_NamedRange","_DefinedName","AutoFilter","parse_fods","pagemargins","parse_xlml","fix_read_opts","parse_compobj","CONTINUE_RT","slurp","RecordType","nextrt","XLSRecordEnum","ll","safe_format_xf","make_cell","parse_workbook","Sheets","Directory","last_formula","cur_sheet","Preamble","lastcell","last_cell","cmnt","rngC","rngR","temp_val","country","XFs","palette","get_rgb","process_cell_style","xfd","addcell","file_depth","afi","objects","last_RT","BIFF2Fmt","BIFF2FmtTable","FilterDatabases","last_lbl","seen_codepage","cpval","tmpri","fakebs8","_fr","_fc","_fe","_arraystart","_j","_ixfe","b4idx","b2idx","noteobj","PSCLSID","parse_xls_props","DSI","DocSummary","SI","Summary","parse_xlscfb","CompObj","WB","WorkbookP","html_to_sheet","mtch2","CS","hd","midx","_t","make_html_row","HTML_BEGIN","HTML_END","book_new","book_append_sheet","make_html_preamble","sheet_to_html","sheet_add_dom","or_R","or_C","is_dom_element_hidden","elts","Aelts","Aelti","parse_dom_table","table_to_book","get_computed_style","get_get_computed_style_function","parse_text_p","fixed","number_formats_ods","parse_content_xml","NFtag","NF","sheetag","rowtag","SheetNames","ctag","textp","textpidx","textR","row_ol","number_format_map","mrange","mR","mC","rowpeat","colpeat","atag","_Ref","creator","creatoridx","isstub","intable","rptR","rpt","nrange","ptp","parse_ods","u8_to_dataview","u8str","u8","u8concat","u8a","popcnt","readDecimal128LE","mantissa","parse_varint49","ptr","varint","varint_to_i32","i32","parse_shallow","mappa","parse_iwa_file","mi","parse_snappy_chunk","decompress_iwa_file","parse_old_storage","rsst","dv","data_offset","ieee","parse_new_storage","d128","parse_cell_storage","parse_TSP_Reference","pb","parse_TST_TableDataList","le","rtp","rtpref","mtype","tswpsa","parse_TST_TileRowInfo","_e","_g","_h","_i","_k","_l","_m","wide_offsets","used_storage_u8","used_storage","used_storage_offsets","parse_TST_Tile","parse_TST_TableModelArchive","store","tile","_tile","parse_TST_TableInfoArchive","tableref","parse_TN_SheetArchive","shapeoffs","parse_TN_DocumentArchive","sheetoffs","root2","parse_numbers_iwa","indices","packets","packet","docroot","iwam","fix_opts_func","get_sheet_type","safe_parse_wbrels","wbrels","safe_parse_sheet","relsPath","sheetRels","stype","dfile","drelsp","chartp","crelsp","tcomments","strip_front_slash","_zip","xlsb","binname","propdata","custprops","deps","wbsheets","wbext","wbrelsi","wbrelsfile","nmode","wsloop","snjseen","snj","parse_xlsxcfb","dsm","seds","einfo","read_cfb","read_zip","read_plaintext","read_plaintext_raw","read_utf16","bstrify","read_prn","readSync","ab","vu","make_json_row","defval","isempty","outi","header_cnt","qreg","make_csv_row","FS","txt","sheet_to_csv","endregex","sheet_to_txt","sheet_to_formulae","cmds","sheet_add_json","js","JS","ws_get_cell_stub","json_to_sheet","RC","wb_sheet_idx","sh","roll","book_set_sheet_visibility","vis","cell_set_number_format","cell_set_hyperlink","cell_set_internal_link","cell_add_comment","author","sheet_set_array_formula","dynamic","rngstr","utils","default_format","RFC1738","is_array","hex_table","_defaultEncoder","charset","_kind","is_buffer","maybe_map","mapped","has","array_prefix_generators","push_to_array","value_or_array","to_ISO","is_non_nullish_primitive","sentinel","inner_stringify","generateArrayPrefix","commaRoundTrip","allowEmptyArrays","strictNullHandling","skipNulls","encodeDotInKeys","encoder","sort","allowDots","serializeDate","encodeValuesOnly","sideChannel","tmp_sc","find_flag","key_value","obj_keys","encoded_prefix","adjusted_prefix","encoded_key","key_prefix","valueSideChannel","normalize_stringify_options","arrayFormat","joined","VERSION","auto","fetch","FormData","File","ReadableStream","getMultipartRequestOptions","getDefaultAgent","fileFromPath","isFsReadStream","setShims","shims","MultipartBody","getRuntime","manuallyImported","recommendation","_fetch","_Request","_Response","_Headers","form","shims.kind","shims.setShims","auto.getRuntime","OpenAIError","APIError","errorResponse","APIConnectionError","castToError","BadRequestError","AuthenticationError","PermissionDeniedError","NotFoundError","ConflictError","UnprocessableEntityError","RateLimitError","InternalServerError","APIUserAbortError","APIConnectionTimeoutError","LengthFinishReasonError","ContentFilterFinishReasonError","__classPrivateFieldSet","__classPrivateFieldGet","_LineDecoder_carriageReturnIndex","LineDecoder","binaryChunk","newData","patternIndex","findNewlineIndex","findDoubleNewlineIndex","ReadableStreamToAsyncIterable","stream","cancelPromise","Stream","consumed","sse","_iterSSEMessages","readableStream","iterLines","lineDecoder","iter","teeIterator","sseDecoder","SSEDecoder","sseChunk","iterSSEChunks","fieldname","partition","delimiter","isResponseLike","isFileLike","isBlobLike","isUploadable","toFile","getBytes","getName","isAsyncIterableIterator","propsForError","getStringFromMaybeBuffer","isMultipartBody","multipartFormRequestOptions","createForm","addFormValue","_AbstractPage_client","defaultParseResponse","_addRequestID","APIPromise","responsePromise","parseResponse","onfulfilled","onrejected","onfinally","APIClient","baseURL","maxRetries","httpAgent","overriddenFetch","validatePositiveInteger","getPlatformHeaders","customHeaders","uuid4","Page","retryCount","query","contentLength","minAgentTimeout","defaultHeaders","applyHeadersMut","shimsKind","getHeader","remainingRetries","retriesRemaining","req","responseHeaders","createResponseHeaders","retryMessage","errText","errJSON","safeJSON","errMessage","PagePromise","isAbsoluteURL","defaultQuery","isEmptyObj","signal","fetchOptions","shouldRetryHeader","timeoutMillis","retryAfterMillisHeader","timeoutMs","retryAfterHeader","timeoutSeconds","sleep","numRetries","sleepSeconds","jitter","AbstractPage","client","nextInfo","nextOptions","requestOptionsKeys","isRequestOptions","hasOwn","getPlatformProperties","normalizePlatform","normalizeArch","browserInfo","getBrowserInfo","browserPatterns","patch","arch","_platformHeaders","startsWithSchemeRegexp","readEnv","targetHeaders","newHeaders","lowerKey","SENSITIVE_HEADERS","modifiedArgs","modifiedArg","isRunningInBrowser","isHeadersProtocol","lowerCasedHeader","intercapsHeader","g1","g2","isObj","CursorPage","APIResource","completionId","ChatCompletionStoreMessagesPage","MessagesAPI.Messages","ChatCompletionsPage","Completions","Messages","CompletionsAPI.Completions","Chat","Speech","Transcriptions","Core.multipartFormRequestOptions","Audio","TranscriptionsAPI.Transcriptions","TranslationsAPI.Translations","SpeechAPI.Speech","Batches","batchId","BatchesPage","Assistants","assistantId","AssistantsPage","isRunnableFunctionWithParse","isAssistantMessage","isFunctionMessage","isToolMessage","_EventStream_instances","_EventStream_connectedPromise","_EventStream_resolveConnectedPromise","_EventStream_rejectConnectedPromise","_EventStream_endPromise","_EventStream_resolveEndPromise","_EventStream_rejectEndPromise","_EventStream_listeners","_EventStream_ended","_EventStream_errored","_EventStream_aborted","_EventStream_catchingPromiseCreated","_EventStream_handleError","EventStream","executor","openAIError","isAutoParsableResponseFormat","response_format","isAutoParsableTool","tool","maybeParseChatCompletion","completion","hasAutoParseableInput","choice","parseChatCompletion","choices","toolCall","parseToolCall","parseResponseFormat","inputTool","shouldParseToolCall","validateInputTools","tools","_AbstractChatCompletionRunner_instances","_AbstractChatCompletionRunner_getFinalContent","_AbstractChatCompletionRunner_getFinalMessage","_AbstractChatCompletionRunner_getFinalFunctionCall","_AbstractChatCompletionRunner_getFinalFunctionCallResult","_AbstractChatCompletionRunner_calculateTotalUsage","_AbstractChatCompletionRunner_validateParams","_AbstractChatCompletionRunner_stringifyFunctionCallResult","DEFAULT_MAX_CHAT_COMPLETIONS","AbstractChatCompletionRunner","chatCompletion","emit","tool_call","finalMessage","finalContent","finalFunctionCall","finalFunctionCallResult","function_call","restParams","singleFunctionToCall","maxChatCompletions","functionsByName","functions","rawContent","tool_choice","inputTools","tool_call_id","rest","usage","ChatCompletionRunner","STR","NUM","ARR","OBJ","NULL","BOOL","NAN","MINUS_INFINITY","INF","SPECIAL","ATOM","COLLECTION","ALL","Allow","PartialJSON","MalformedJSON","parseJSON","jsonString","allowPartial","_parseJSON","allow","markPartialJSON","throwMalformedError","parseAny","skipBlank","parseStr","parseObj","parseArr","parseNum","partialParse","_ChatCompletionStream_instances","_ChatCompletionStream_params","_ChatCompletionStream_choiceEventStates","_ChatCompletionStream_currentChatCompletionSnapshot","_ChatCompletionStream_beginRequest","_ChatCompletionStream_getChoiceEventState","_ChatCompletionStream_addChunk","_ChatCompletionStream_emitToolCallDoneEvent","_ChatCompletionStream_emitContentDoneEvents","_ChatCompletionStream_endRequest","_ChatCompletionStream_getAutoParseableResponseFormat","_ChatCompletionStream_accumulateChatCompletion","ChatCompletionStream","chatId","choiceSnapshot","toolCallDelta","toolCallSnapshot","toolCallIndex","responseFormat","snapshot","finalizeChatCompletion","finish_reason","logprobs","refusal","tool_calls","pushQueue","readQueue","created","system_fingerprint","choiceRest","messageRest","toolRest","fnRest","assertNever","_x","ChatCompletionStreamingRunner","Sessions","Realtime","SessionsAPI.Sessions","_AssistantStream_instances","_AssistantStream_events","_AssistantStream_runStepSnapshots","_AssistantStream_messageSnapshots","_AssistantStream_messageSnapshot","_AssistantStream_finalRun","_AssistantStream_currentContentIndex","_AssistantStream_currentContent","_AssistantStream_currentToolCallIndex","_AssistantStream_currentToolCall","_AssistantStream_currentEvent","_AssistantStream_currentRunSnapshot","_AssistantStream_currentRunStepSnapshot","_AssistantStream_addEvent","_AssistantStream_endRequest","_AssistantStream_handleMessage","_AssistantStream_handleRunStep","_AssistantStream_handleEvent","_AssistantStream_accumulateRunStep","_AssistantStream_accumulateMessage","_AssistantStream_accumulateContent","_AssistantStream_handleRun","AssistantStream","threadId","runId","runs","thread","deltaValue","accValue","Core.isObj","deltaEntry","accEntry","accumulatedMessage","newContent","snapshotContent","textDelta","currentContent","accumulatedRunStep","accumulated","contentElement","messageId","MessagesPage","Steps","stepId","RunStepsPage","Runs","StepsAPI.Steps","include","RunsPage","sleepInterval","headerInterval","headerIntervalMs","Threads","RunsAPI.Runs","allSettledWithThrow","rejected","vectorStoreId","VectorStoreFilesPage","fileResponse","fileInfo","Files","FileBatches","batch","fileIds","configuredConcurrency","concurrencyLimit","fileIterator","allFileIds","processFiles","fileObj","VectorStores","FilesAPI.Files","FileBatchesAPI.FileBatches","VectorStoresPage","Beta","RealtimeAPI.Realtime","VectorStoresAPI.VectorStores","ChatAPI.Chat","AssistantsAPI.Assistants","ThreadsAPI.Threads","Embeddings","FileObjectsPage","pollInterval","maxWait","TERMINAL_STATES","Checkpoints","fineTuningJobId","FineTuningJobCheckpointsPage","Jobs","CheckpointsAPI.Checkpoints","FineTuningJobsPage","FineTuningJobEventsPage","FineTuning","JobsAPI.Jobs","Images","Models","ModelsPage","Moderations","Parts","uploadId","Uploads","PartsAPI.Parts","OpenAI","Core.APIClient","Core.readEnv","apiKey","organization","project","Errors.OpenAIError","Core.isRunningInBrowser","API.Completions","API.Chat","API.Embeddings","API.Files","API.Images","API.Audio","API.Moderations","API.Models","API.FineTuning","API.Beta","API.Batches","API.Uploads","qs.stringify","Errors.APIError","Errors.APIConnectionError","Errors.APIConnectionTimeoutError","Errors.APIUserAbortError","Errors.NotFoundError","Errors.ConflictError","Errors.RateLimitError","Errors.BadRequestError","Errors.AuthenticationError","Errors.InternalServerError","Errors.PermissionDeniedError","Errors.UnprocessableEntityError","Uploads.toFile","Uploads.fileFromPath","UploadsAPIUploads","_Payroll4AssistantController","payrollContent","objDiv","openaiStream","responseMessage","finishReason","htmlContentMatch","workbook","XLSX.read","firstSheet","XLSX.utils","userDefinedRow","employees","rowTypes","yearlyChangingNumbers","extRows","Payroll4AssistantController","_CalcRepairInfoController","repaired","CalcRepairInfoController","_NewPaymentController","businessObjectType","NewPaymentController","ContactInfoController","_MessageThreadCrudController","messageApi","endUserService","subject","totalMinutes","newMessage","calculationListItem","payrollListItem","readBy","readByValue","flagFor","startFrom","relevantMessages","messages","defaultMessageDetailsUrl","messageThread","MessageThreadCrudController","_OmapalkkaController","embeddedUrl","OmapalkkaController","_VarmaBannerController","dialogData","pension","PensionCalculation","VarmaBannerController","_WelcomeController","overview","searchString","searchResult","avatarId","taxCard","userSession","WelcomeController","_InputBase","hasRequiredValidator","readOnlyValue","validationErrors","InputBase","E","N","en","default_1","_default","sv","basePlacements","clippingParents","viewport","popper","reference","variationPlacements","placement","placements","beforeRead","afterRead","beforeMain","afterMain","beforeWrite","afterWrite","modifierPhases","getNodeName","getWindow","ownerDocument","OwnElement","isHTMLElement","isShadowRoot","applyStyles","_ref","effect","_ref2","initialStyles","styleProperties","applyStyles$1","getBasePlacement","getUAString","uaData","isLayoutViewport","getBoundingClientRect","includeScale","isFixedStrategy","clientRect","scaleX","scaleY","visualViewport","addVisualOffsets","getLayoutRect","contains","rootNode","isTableElement","getDocumentElement","getParentNode","getTrueOffsetParent","getContainingBlock","isFirefox","isIE","elementCss","currentNode","css","getOffsetParent","offsetParent","getMainAxisFromPlacement","within","mathMax","mathMin","withinMaxClamp","getFreshSideObject","mergePaddingObject","paddingObject","expandToHashMap","hashMap","toPaddingObject","arrow","_state$modifiersData$","arrowElement","popperOffsets","basePlacement","isVertical","arrowRect","minProp","maxProp","endDiff","startDiff","arrowOffsetParent","clientSize","centerToReference","axisProp","_options$element","arrow$1","getVariation","unsetSides","roundOffsetsByDPR","mapToStyles","_Object$assign2","popperRect","variation","gpuAcceleration","adaptive","roundOffsets","isFixed","_offsets$x","_offsets$y","_ref3","hasX","hasY","sideX","sideY","heightProp","widthProp","commonStyles","_ref4","_Object$assign","computeStyles","_ref5","_options$gpuAccelerat","_options$adaptive","_options$roundOffsets","computeStyles$1","passive","_options$scroll","_options$resize","scrollParents","scrollParent","eventListeners","getOppositePlacement","matched","getOppositeVariationPlacement","getWindowScroll","scrollLeft","scrollTop","getWindowScrollBarX","getViewportRect","layoutViewport","getDocumentRect","_element$ownerDocumen","winScroll","isScrollParent","_getComputedStyle","overflowX","overflowY","getScrollParent","listScrollParents","isBody","updatedList","rectToClientRect","getInnerBoundingClientRect","getClientRectFromMixedType","clippingParent","getClippingParents","canEscapeClipping","clipperElement","getClippingRect","rootBoundary","mainClippingParents","firstClippingParent","clippingRect","accRect","computeOffsets","commonX","commonY","mainAxis","detectOverflow","_options","_options$placement","_options$strategy","_options$boundary","_options$rootBoundary","_options$elementConte","elementContext","_options$altBoundary","altBoundary","_options$padding","altContext","clippingClientRect","referenceClientRect","popperClientRect","elementClientRect","overflowOffsets","offsetData","multiply","computeAutoPlacement","flipVariations","_options$allowedAutoP","allowedAutoPlacements","allPlacements","allowedPlacements","overflows","getExpandedFallbackPlacements","oppositePlacement","_options$mainAxis","checkMainAxis","_options$altAxis","checkAltAxis","specifiedFallbackPlacements","_options$flipVariatio","preferredPlacement","isBasePlacement","fallbackPlacements","referenceRect","checksMap","makeFallbackChecks","firstFittingPlacement","_basePlacement","isStartVariation","mainVariationSide","altVariationSide","checks","numberOfChecks","fittingPlacement","_ret","flip$1","getSideOffsets","preventedOffsets","isAnySideFullyClipped","side","hide","referenceOverflow","popperAltOverflow","referenceClippingOffsets","popperEscapeOffsets","isReferenceHidden","hasPopperEscaped","hide$1","distanceAndSkiddingToXY","invertDistance","skidding","_options$offset","_data$state$placement","offset$1","popperOffsets$1","getAltAxis","preventOverflow","_options$tether","tether","_options$tetherOffset","tetherOffset","altAxis","tetherOffsetValue","normalizedTetherOffsetValue","offsetModifierState","_offsetModifierState$","mainSide","altSide","additive","minLen","maxLen","arrowPaddingObject","arrowPaddingMin","arrowPaddingMax","arrowLen","minOffset","maxOffset","clientOffset","offsetModifierValue","tetherMin","tetherMax","preventedOffset","_offsetModifierState$2","_mainSide","_altSide","_offset","_len","_min","_max","isOriginSide","_offsetModifierValue","_tetherMin","_tetherMax","_preventedOffset","preventOverflow$1","getHTMLElementScroll","getNodeScroll","isElementScaled","getCompositeRect","elementOrVirtualElement","isOffsetParentAnElement","offsetParentIsScaled","documentElement","modifiers","modifier","dep","depModifier","orderModifiers","orderedModifiers","mergeByName","merged","DEFAULT_OPTIONS","areValidElements","_key","popperGenerator","generatorOptions","_generatorOptions","_generatorOptions$def","defaultModifiers","_generatorOptions$def2","defaultOptions","effectCleanupFns","isDestroyed","setOptionsAction","cleanupModifierEffects","runModifierEffects","_state$elements","_state$orderedModifie","_state$orderedModifie2","_ref$options","cleanupFn","noopFn","createPopper","_DatepickerController","jsDate","isManualInputInit","datepickerElem","viewLevel","minView","multipleDates","dateFormat","minDate","maxDate","clearButton","buttons","localeMap","localeFi","localeEn","localeSv","createPopperPlacement","AirDatepicker","$datepicker","$target","$pointer","viewDates","disabledDates","dpValue","viewDate","dateVal","trySetValidator","typedValue","DatepickerController","_DatepickerPopupController","DatepickerPopupController","_DateRangeController","dateRangeElem","dateRangeVals","updateDatepickerElemValues","dateObj","typedValueStart","typedValueEnd","normalizedStart","normalizedEnd","parsedStart","parsedEnd","DateRangeController","_FormGroupController","legacyRequiredValue","forElement","colsCount","FormGroupController","_InputController","InputController","_InputAccountingTargetController","accountingTargetId","refresher","InputAccountingTargetController","_InputBooleanController","InputBooleanController","_InputCollectiveBargainAgreementController","currentLanguage","cbaCodes","InputCollectiveBargainAgreementController","InputEnumController","allValues","selectedValue","enums","matchingHiddenValue","hiddenValue","filterArr","inputName","storageKey","_InputCredentialController","workflowService","newCredentials","InputCredentialController","_InputDurationController","InputDurationController","_InputIncomeTypeController","incomeType","InputIncomeTypeController","InputNumberController","valueNum","_InputOccupationTypeController","occupations","defaultList","Occupations","occupationId","occupation","InputOccupationTypeController","ALL_WEEKDAYS","Weekday","isPresent","isWeekdayStr","rang","repeat","toArray","padStart","targetLength","padString","pymod","divmod","notEmpty","MONTH_DAYS","ONE_DAY","MAXYEAR","ORDINAL_BASE","PY_WEEKDAYS","isLeapYear","daysBetween","date1","date2","date1ms","date2ms","differencems","toOrdinal","fromOrdinal","ordinal","getMonthDays","getWeekday","monthRange","combine","dolly","cloneDates","dates","clones","timeToUntilString","utc","untilStringToDate","until","dateTZtoISO8601","timeZone","dateStr","dateInTimeZone","localTimeZone","dateInLocalTZ","dateInTargetTZ","tzOffset","IterResult","tooEarly","tooLate","extendStatics","__extends","__","__assign","__spreadArray","pack","ar","CallbackIterResult","_super","_this","ENGLISH","defaultGetText","defaultDateFormatter","day","ToText","rrule","gettext","language","dateFormatter","bymonthday","bynmonthday","byweekday","sortWeekDays","canConvert","RRule","nth","npos","wday","finalDelim","delim","delimJoin","finalDelimiter","realCallback","rules","best","bestSymbol","name_1","parseText","ttr","AT","ON","wkd","decodeWKD","MDAYs","decodeM","on","the","decodeNTH","at","Frequency","freqIsDailyOrGreater","freq","fromText","common","toText","isFullyConvertible","Time","hour","minute","millisecond","DateTime","years","yearDiv","monthMod","wkst","filtered","byhour","dayDiv","hourMod","byminute","hourDiv","minuteMod","bysecond","minuteDiv","secondMod","daysinmonth","initializeOptions","invalid","keys_1","defaultKeys","parseOptions","bynweekday","buildTimeset","millisecondModulo","timeset","parseString","rfcString","parseLine","parseDtstart","dtstartWithZone","tzid","dtstart","parseRrule","strippedLine","Days","parseNumber","optionKey","parseWeekday","parseIndividualNumber","wdaypart","DateWithZone","optionsToString","outValue","buildDtstart","strValues","ruleString","argsMatch","Cache","argsKeys","findCacheDiff","cachedObject","iterResult","M365MASK","M366MASK","M28","M29","M30","M31","MDAY366MASK","MDAY365MASK","NM28","NM29","NM30","NM31","NMDAY366MASK","NMDAY365MASK","M366RANGE","M365RANGE","WDAYMASK","wdaymask","rebuildYear","firstyday","yearlen","nextyearlen","yearordinal","yearweekday","baseYearMasks","firstwkst","wyearlen","no1wkst","div","mod","numweeks","lnumweeks","lyearweekday","lno1wkst","lyearlen","weekst","rebuildMonth","ranges","easter","yearStart","Iterinfo","buildPoslist","bysetpos","dayset","poslist","daypos","timepos","emitResult","counterDate","makeTimeset","removeFilteredDays","rezonedDate","rezoneIfNeeded","currentDay","isFiltered","bymonth","byweekno","byeaster","byyearday","dayCounter","noCache","parsedOptions","before","inc","iterSet","_rrule","_exrule","_rdate","_exdate","_exdateHash","_accept","evalExdate","zonedDate","parseInput","rrulevals","rdatevals","exrulevals","exdatevals","parsedDtstart","splitIntoLines","breakDownLine","parms","rdateTzid","parseRDate","buildRule","rset_1","RRuleSet","groomRruleOptions","rrulestr","extractName","unfold","validateDateParm","parm","rdateval","createGetterSetter","fieldName","field_1","_addRule","_addDate","exrule","rdatesToString","rrs","param","rdates","isUTC","dateString","rdate","_InputRruleController","InputRruleController","InputTimeController","DateTimes","_InputTypeaheadController","currentSelected","rawValue","valObj","onClick","available","clamped","showAll","allItems","updateModel","InputTypeaheadController","ToggleButtonsController","_ValidationSummaryController","errors","labelKey","descriptionKey","ValidationSummaryController","InputHolidayMultipliersController","newKey","_InputPayStatsRowTypeController","isExclusive","baseType","dotParts","nameParts","wageType","InputPayStatsRowTypeController","_InputEmployeeGroupController","newEmployeeGroups","InputEmployeeGroupController","_MarkdownEditorController","MarkdownEditorController","_MarkdownViewerController","MarkdownViewerController","_ActionButtonController","ActionButtonController","_AlertController","AlertController","_AvatarController","AvatarController","_BatchProcessController","$uibModalInstance","openApiDoc","remainingItems","itemsToProcess","defaultCols","statusEnum","party","infoProp","CellRenderingLogic","enumType","BatchProcessController","_CalendarController","dayEventsCount","series","startDay","endDay","currentMonthDay","daysInMonth","firstDayDayOfWeek","periods","singleDays","allEvents","dataRows","finalResult","isEventOnDay","defaultSeries","CalendarController","interaction","filterElements","getNearestItem","getElements","inRangeByAxis","getPointByAxis","nearestItems","evenPoint","isOlderPart","act","clamp","clampAll","inPointRange","hBorderWidth","inBoxRange","inRangeX","inRangeY","getElementCenterPoint","requireVersion","pkg","ver","strict","isPercentString","toPercent","toPositivePercent","boxAppering","defaultInitAnimation","getSize","positivePercent","calculateTextAlignment","toPosition","isBoundToPoint","initAnimationProperties","initAnim","applyDefault","execCallback","loadHooks","hooks","hooksContainer","widthCache","notRadius","fontsKey","fonts","isImageOrCanvas","translate","setBorderStyle","setShadowStyle","optFont","mapKey","calculateLabelSize","drawBox","drawLabel","getOpacity","optColor","setTextStrokeStyle","applyLabelDecoration","applyLabelContent","drawPointStyle","elementValue","limitedLineScale","scaleValue","isFinite","retrieveScaleID","axes","getDimensionByScale","getChartPoint","resolveBoxProperties","xDim","getChartDimensionByScale","yDim","resolvePointProperties","adjustCenterX","adjustCenterY","getChartCircle","resolveLineProperties","resolveFullLineProperties","resolveLimitedLineProperties","resolveBoxAndLabelProperties","resolveLabelElementProperties$1","scaleId","startProp","endProp","dim","calculateX","labelSize","calculatePosition$1","calculateY","boxOpts","padEnd","adjust","availableSize","rotated","cx","cy","moveHooks","eventHooks","updateListeners","handleEvent","handleMoveEvents","handleClickEvents","dispatchMoveEvents","checkElements","dispatchEvent","elementHooks","updateHooks","visibleElements","invokeHook","callbackHook","adjustScaleRange","annotations","getScaleLimits","changeScaleLimit","verifyScaleOptions","verifyScaleIDs","suggestedLimit","scaleLimitDefined","verifyProperties","scaleIDOption","BoxAnnotation","LabelAnnotation","drawCallout","getLabelSize","boxSize","measureRect","calculatePosition","pointX","pointY","callout","calloutPosition","resolveCalloutPosition","isPointInRange","separatorStart","separatorEnd","getCalloutSeparatorCoord","sideStart","sideEnd","getCalloutSideCoord","rotatedPoint","getCalloutSeparatorAdjust","getCalloutSideAdjust","resolveCalloutAutoPosition","xAdjust","yAdjust","xPoints","yPoints","pointInLine","interpolateX","interpolateY","sqr","rangeLimit","coordInCurve","pointInCurve","coordAngleInCurve","angleInCurve","LineAnnotation","mx","my","isOnLabel","intersects","inAxisRange","drawCurve","startOpts","endOpts","startAdjust","endAdjust","getArrowHeads","drawArrowHead","isLineInArea","limitLineToArea","getControlPoint","labelProperties","resolveLabelElementProperties","arrowHeadsDefaults","limitPointToArea","dy","lenSq","xx","yy","calculateLabelPosition","calculateAutoRotation","sizes","rotatedSize","calculateT","xCoordinateSizes","yCoordinateSizes","adjustLabelCoordinate","space","spaceAround","calculateTAdjust","lineSize","lineW","lineH","coordinate","halfSize","arrowStartOpts","arrowEndOpts","getLineAdjust","arrowOpts","arrowOffsetX","drawArrowHeadOnCurve","ps","pe","EllipseAnnotation","pointInEllipse","ellipse","xRadius","yRadius","cosAngle","sinAngle","PointAnnotation","PolygonAnnotation","pointIsInPolygon","axisPoints","sides","elProps","buildPointElement","halfBorder","isInside","annotationTypes","directUpdater","hooks$1","optDefs","resolveObj","resolveType","updateElements","resolveAnimations","resyncElements","annotationOptions","getOrCreateElement","getContext","toSkip","updateSubElements","resolveAnnotationOptions","animOpts","mainElement","subElements","subElement","initProperties","elementClass","chartStates","drawableElements","getDrawableElements","drawElement","dayjs","AdvancedFormat","QuarterOfYear","LocalizedFormat","CustomParseFormat","FORMATS","_adapters","_format","validatedWeekday","annotationPlugin","_ChartController","ChartController","_JsonFormatterController","isUrl","kvs","ellipsis","currentKeys","ck","icon","JsonFormatterController","secondSet","arrayIntersection","keyBy","getKey2","oldObj","embeddedObjKeys","keysToSkip","treatTypeChangeAsReplace","atomizeChangeset","embeddedKey","handleArray","updatedPath","atomicChange","handleEmbeddedKey","getTypeOfObj","finalPath","endsWithFilterValue","filterEndIdx","filterStartIdx","filterExpression","getKey","keyPath","skipPath","skipParts","currentParts","typeOfOldObj","typeOfNewObj","comparePrimitives","diffs","compareObject","compareArray","newKeyPath","oldObjKeys","newObjKeys","intersectionKeys","addedKeys","skipPath2","deletedKeys","getObjectKey","uniqKey","indexedOldObj","convertArrayToObj","indexedNewObj","key2","basePath","nextSegment","filterKey","filterValue","_JsonDiffController","jsonCopy","compareToCopy","changeset","normalizedPath","schemaProp","arrayPropertyName","arraySchemaProp","remainingPath","trimmed","JsonDiffController","_NaviController","naviService","NaviController","_SpinnerController","knownTerms","defaultText","SpinnerController","_TabController","slot","found","salaxyTabNode","salaxyTabsNode","salaxyTabNodes","tagName","TabController","_TabsController","newActiveTabIndex","selectedTab","newTab","resort","TabsController","_TabButtonsController","chosenTab","paramTab","tabs","tabValue","tabContentElement","tabPaneElement","pane","tabText","TabButtonsController","_UiTranslatorController","uiTranslatorService","fullkey","fullKey","baseDictionary","serviceModelTranslation","newFullKey","fullPath","allKeyValues","splitKeys","diffBase","subKeys","UiTranslatorController","_ODataActionsController","fileService","Calculations","DataMappersLogic","ODataActionsController","_ImportController","Culture","ImportBatch","parserGuess","isDebug","ImportController","_ExportController","exporterId","ExportLogic","newMapper","ExportController","CoreFeature","columnsChanged","force","oldOption","newOption","convert","Helpers","structure","objectProto","arrayProto","Popup","touch","parentOffset","containerOffset","parentEl","coords","Module","priority","lookupIndex","renderInPosition","menuEl","menuContainer","defaultAccessors","Accessor","accessor","rowComponent","colComponent","generateParamsList","serializeParams","urlBuilder","defaultLoaderPromise","generateParamsList$1","defaultContentTypeFormatters","Ajax","ajaxParams","ajaxConfig","defaultPasteActions","singleCell","startCell","startRow","rowWidth","dataLength","defaultPasteParsers","clipboard","headerFindSuccess","columnMap","colWidth","startCol","itemLength","Clipboard","plain","rowData","internal","sel","textRange","blocked","CalcComponent","CellComponent","mutate","Cell","vertAligns","hozAligns","classNames","containerOnly","ColumnComponent","Column","ifVisible","toColumn","nextCol","prevCol","updates","defaultColumnOptions","newCol","titleHolderElement","titleElement","contents","dataObj","parentHeight","traverse","updateBranches","colDefs","responsiveToggle","childWidth","minWidth","cellCount","setTo","RowComponent","Row","inFragment","minHeight","updatedData","newRowData","attrname","findCell","toRow","blockRedraw","defaultCalculations","calcParams","sum","unique","ColumnCalcs","viewable","paramKey","groupObj","subGroups","subGroupResults","subgroup","DataTree","dummyEl","firstCol","childArray","oldControl","allChildren","subChildren","childData","childRow","childIndex","recurse","csv","setFileContents","fileContents","pdf","autoTableParams","rowGroupStyles","rowCalcStyles","jsPDFParams","parseRow","xlsx","sheetName","tableFeatures","writeOptions","generateSheet","s2ab","jsonLines","defaultDownloaders","Download","interceptCallback","downloadFunc","buildLink","mime","groupHeader","maskInput","maskLetter","maskNumber","maskWildcard","fillSymbols","symbol","onRendered","success","cancel","editorParams","cellValue","onChange","textarea","vertNav","scrollHeight","heightNow","blurFunc","inputFormat","DT","convertDate","newDatetime","luxDate","luxTime","luxDateTime","Edit","editor","cellEl","clickStop","listEl","attribs","valueKeys","valueCheck","character","responseValues","placeholder","term","inputValues","as","b1","rx","rd","emptyAlign","filterFunc","startVis","blur","select","autocomplete","star","maxStars","stars","starsHolder","starChange","buildStar","starHolder","nextStar","changeValue","mouseDrag","mouseDragWidth","updateValue","calcVal","tickCross","tristate","indetermValue","indetermState","trueValueSet","falseValueSet","setValue","checkedValue","defaultEditors","Edit$1","newRow","nextCell","prevRow","nextRow","prevCell","forceEdit","topEdge","bottomEdge","rowEl","leftEdge","rightEdge","allowEdit","rendered","editFinished","cellEditor","editIndex","ExportRow","indent","ExportColumn","Export","colVisProp","colData","groupData","subGroup","subGroupData","visProp","headerDepth","exportRows","parseColumnGroup","exportCols","headerEl","bodyEl","rowFormatter","setup","cellStyle","cellWrapper","formatComponent","holder","lookup","fromStyle","defaultFilters","filterVal","rowVal","filterParams","keywords","keyword","Filter","filterType","filterChangeCheck","fieldVal","colVal","reinitialize","filterElement","editorElement","typingTimer","searchTrigger","onRenderedCallback","headerPos","filterList","activeRows","rowList","activeRowComponents","subFilter","plaintext","formatterParams","html$1","textarea$1","money","floatVal","integer","rgx","decimalSym","thousandSym","negativeSign","urlPrefix","download","labelTraverse","image","tickCross$1","truthy","cross","datetime$1","outputFormat","datetimediff","humanize","star$1","starActive","starInactive","traffic","percentValue","progress$1","legendAlign","legendColor","barEl","barContainer","legendEl","holderEl","buttonTick","buttonCross","rownum","responsiveCollapse","toggleList","collapseEl","rowSelection","checkbox","defaultFormatters","Format","mockCell","entityMap","FrozenColumns","allCells","leftParents","leftMargin","rightMargin","visibleRows","otherRows","FrozenRows","frozenRows","GroupComponent","Group","groupManager","generator","oldGroup","elementsOnly","toggleElement","groupID","groupKey","toIndex","includeChildren","GroupRows","groupBy","startOpen","langValue","lookupFunc","groupRows","groupValues","toGroup","fromGroup","groupComponents","groupList","groupListData","oldGroups","newGroupNeeded","oldRowGroup","oldGroupPath","newGroupPath","samePath","groupPath","groupId","onlyGroupHeaders","defaultUndoers","defaultRedoers","History","oldRow","HtmlTableImport","optionsArr","optionsList","attrib","csvImporter","inQuote","nextChar","json$1","arrayImporter","defaultImporters","Import","importFormat","importer","extension","extensions","parsedData","noTouch","componentObj","defaultBindings","defaultActions","rowManager","newPos","scrollMax","Keybindings","mergedBindings","bindingList","symbolsList","symbols","Menu","headerMenuEl","menu","parentPopup","popup","itemEl","MoveColumns","colEl","startXMove","nextColWidth","prevColWidth","nextColWidthLast","prevColWidthLast","moveToCol","headerElement","headersElement","movingCells","columnHolder","xPos","scrollPos","MoveRows","startYMove","nextRowHeight","prevRowHeight","nextRowHeightLast","prevRowHeightLast","moveToRow","pageX","pageY","rowHolder","yPos","connectionTables","dropEvent","sender","fromRow","fromTable","toTable","defaultMutators","Mutator","mutator","links","linkCell","pageSize","totalRows","totalPages","showingEl","valueEl","ofEl","totalEl","rowsEl","pages","defaultPageCounters","displayRows","testElRow","testElCell","button","pageSizes","pageCounter","pageSelectLabel","paginationCounterHolder","rowCount","leftSize","rightSize","actualRowPageSize","actualStartRow","actualRows","defaultReaders","cookiePos","defaultWriters","expireDate","Persistence","testKey","retrievedData","sorters","headerFilters","oldCols","newCols","mergeAllNew","definitions","excludedKeys","defStore","colDef","Popup$1","headerPopupEl","renderedCallback","contentsEl","Print","scrollX","scrollY","footerEl","tableEl","footerContent","ReactiveData","oldRows","childField","origFuncs","update","ResizeColumns","frozenOffset","variableHeight","nearestColumn","handleDown","oldWidth","handleEl","mouseMove","moveDiff","blockedBefore","blockedAfter","mouseUp","ResizeRows","prevHandle","prevHandleDown","ResizeTable","tableStyle","nodeHeight","nodeWidth","ResponsiveLayout","colCount","working","mockCellComponent","titleData","valueData","node_content","titleHighlight","SelectRow","prevSelected","selectable","endSelect","lastClickedRowIdx","rowIdx","fromRowIdx","toRowIdx","toggledRows","toggledRow","rowMatch","rowInfo","selectedRow","deselected","number$1","aRow","bRow","alignEmptyValues","thousand","datetime$2","date$1","time$1","boolean","el1","el2","alphanum","defaultSorters","Sort","sortList","arrowEl","newSortList","sortListActual","rowComponents","sortObj","sortEl","sorterCount","sortItem","el1Comp","el2Comp","RangeComponent","Range","rangeManager","rowsCount","isRowHeader","_vDomTop","_vDomBottom","_vDomLeft","_vDomRight","topLeftCell","bottomRightCell","structured","clearValue","SelectRange","selectedColumns","selectedColumn","rangeIdx","jump","expand","moved","rangeEdge","emptyStart","emptySide","currentCell","rowPos","colPos","isStartingCellEmpty","isLeftOfStartingCellEmpty","jumpCol","targetCells","isRightOfStartingCellEmpty","isTopOfStartingCellEmpty","jumpRow","isBottomOfStartingCellEmpty","tableHolder","rowHeader","withinHorizontalView","withinVerticalView","occupied","activeCell","colIdx","defaultValidators","parameters","cellData","Validate","cancelled","validators","failedValidators","invalidIndex","OptionsList","msgType","userOptions","warn","Renderer","includingBuffer","BasicHorizontal","rowFrag","VirtualDomHorizontal","old","colEnd","ex","widthDiff","ColumnManager","renderClass","renderers","nextToColumn","topColumn","parentIndex","nextEl","fieldRoot","fromIndex","fixedWidth","BasicVertical","tableFrag","rowTop","VirtualDomVertical","topRow","topOffset","topDiff","bottomDiff","topFound","bottomRow","forceMove","topPad","rowsHeight","rowHeight","heightOccupied","topPadHeight","rowFragment","renderedRows","totalRowsRendered","rowsToRender","fixedHeight","containerHeight","avgRowHeight","resized","fillableSpace","addedRows","paddingAdjust","initialized","removableRows","RowManager","leftDir","topDir","allIndex","activeIndex","displayIndex","refreshDisplayOnly","chainResult","rowOnly","skipStage","stage","cascadeOrder","scrollbarWidth","initialHeight","otherHeight","FooterManager","InteractionManager","listenerMap","leaveList","linkedKeys","components","comp","targets","componentMap","classList","elTargets","targetMatches","previousTarget","ComponentFunctionBinder","funcName","DataLoader","requestNo","shouldLoad","ExternalEventBus","subscribed","notifiers","callResult","InternalEventBus","subscriber","confirmed","DeprecationAdvisor","TableRegistry","Tabulator","fitData","forced","fitDataGeneral","fitDataStretch","colsWidth","tableWidth","gap","lastCol","fitColumns","flexWidth","flexGrowUnits","flexColWidth","flexColumns","fixedShrinkColumns","flexShrinkUnits","overflowWidth","gapFill","calcWidth","scaleColumns","freeSpace","shrinkCols","oversizeCols","oversizeSpace","remainingSpace","remainingFlexGrowUnits","changeUnits","undersizeCols","calcGrow","calcShrink","defaultModes","Layout","dataChanged","defaultLangs","Localize","desiredLocale","traverseLang","trans","fillPath","pathArray","rootPath","Comms","selectors","connections","connection","con","coreModules","ModuleBinder","tabulator","orderedStartMods","orderedEndMods","unOrderedMods","core","Alert","ua","responses","foundRows","fromColumn","required","TabulatorFull","XLSX","DataImportControllerBase","helpData","emptyRow","helpSheet","fileData","sheetData","sheetRow","setData","isValidRow","ApiImportStatus","fieldSchema","enumMetadata","y1900","lowerValue","dataOk","_CompanyImportController","importsApi","sourceRow","getTargetKey","getSourceKey","importObj","sourceRows","addresses","selectionDialog","CompanyImportController","_CalcImportController","RowMergeOption","imports","groupCalcs","firstCalc","rowMap","rowSelector","DataMapperSelector","workerGroups","workerChecks","workerGroupKey","checkObj","ApiCheckStatus","CalcImportController","_ImportStagingController","WorktimeApiConnector","commitSingle","payrollId","totals","committedCalc","ipt","ImportStagingController","_WorkerImportController","salaryDefaultSelector","WorkerImportController","_CustomerInvoiceCrudController","CustomerInvoiceCrudController","_InvoiceCrudController","InvoiceCrudController","_InvoicePaymentListController","invoicesFullApi","invService","sepaAjax","fileTypeId","warning","showLoading","idsToUpdate","changeInvoiceStatus","invoiceIds","confirmHeading","loaderHeading","markAsPaidStatuses","markAsCancelledStatuses","invoiceMarkAsPaidAllowed","invoiceCancellingAllowed","updateStatus","handlePsdPayment","bank","externalDialogLoader","sortByDate","updateSpecificInvoices","updatedInvoicesMap","loadItems","nextPageLink","readInvoice","updatedInvoice","blobs","payerIbanNumber","isDelayed","InvoicePaymentListController","_InvoicesCreateController","inProgress","exceptions","paid","payrolls4Api","salaryDateKind","closeFunc","idsToPay","refreshCurrentCalculation","InvoicePaymentType","calcController","payrollController","invoiceCreate","InvoicesCreateController","_PaymentChannelController","PaymentChannelApi","setChannel","PaymentChannelController","_InvoiceToolsController","fileTypes","hideLoading","withoutContent","preferZip","pdfArr","sepaData","finvoiceArr","invoiceType","fileType","InvoiceToolsController","_InvoiceSepaController","Promises","allInvoices","groupInvoice","invoicesWithSameId","InvoiceSepaController","_InvoiceReportController","InvoiceMapper","InvoiceReportController","_CompanyInvoicesController","invoiceService","companyAjax","updatePeriodicInvoices","getConfirmText","_arr","oldDateFilterQueryOption","filterInvoices","netInvoices","taxInvoices","unionInvoices","foreclosureInvoices","periodicInvoices","toBeRemoved","periodicInvoice","CompanyInvoicesController","_InvoiceAlertsController","paymentChannels","paymentChannel","paymentChannelItems","getInstructionText","getLinks","urls","InvoiceAlertsController","_EditDialogController","EditDialogController","_ModalGenericDialogController","ModalGenericDialogController","_CalcSharingController","sharingCalculationsApi","SharingUriType","employer","createSharingMessageForEmployer","distinctItems","CalcSharingController","_EmployerListController","employerId","EmployerListController","_EmployerReportController","report","iconComponents","initials","indx","id1","EmployerReportController","_EmployerSelectController","EmployerSelectController","_HouseholdDeductionReportController","employerReport","yearlyReport","deductibleAmount","HouseholdDeductionReportController","_HouseholdYearCrudController","householdYearsApi","updatedCalc","HouseholdYearProcessingStatus","deductibleTotal","maxAmount","sideCosts","odata","logicalDate","yearReport","newModel","pdfs","TaxDeductionWorkCategories","HouseholdYearCrudController","_PersonAccountController","person","supportedHashes","PersonAccountController","_WorkerReportController","endYear","WorkerReportController","_TimesheetWorkerDemoController","msgApi","$interval","newUsecase","TimesheetWorkerDemoController","_WorkerTimerController","timerMessage","messageIndex","contentData","TimesheetInputModification","padTo2Digits","lk1","costAccountingSettings","endTime","startTime","entryStartTime","entryEndTime","xStartTime","xEndTime","WorkerTimerController","WorkerHourlyReportControllerBindings","_WorkerHourlyReportController","targetDate","WorkerHourlyReportController","WorkerExpenseReportControllerBindings","_WorkerExpenseReportController","WorkerExpenseReportController","_AccountantWizardController","AccountantWizardController","_RecordsController","wfEvents","attachment","attachments","recordAndEvent","serverRecordTypes","wfItem","uploadUrl","orphans","orphan","eventsOfType","RecordsController","_AccountingReportCrudController","filesApi","logicalDateExcluding","currentLoadingId","AccountingReportCrudController","_AccountingReportQueryController","PeriodDateKind","selectedCalculations","selectedCalculation","AccountingReportQueryController","_AccountingReportRowsController","AccountingMapper","ledgerAccount","AccountingReportRowsController","_AccountingReportToolsController","AccountingTargetLogic","accountingData","schemeId","targetOption","tabbed","availableMethods","exportMethodId","localeId","exportMethod","isFinnish","addPrefix","addQuotes","formatAsText","AccountingChannel","AccountingReportToolsController","_IrEarningsPaymentCrudController","absencesApi","irepr","startAt","aso","nonErrorEntries","startAtDate","workerAbsences","selectedAbsences","absencesStartDate","absencesEndDate","causeCode","IrEarningsPaymentCrudController","_IrPayerSummaryCrudController","irpsr","psr","IrPayerSummaryCrudController","_ReportsController","ReportsController","_SalaryReportCrudController","SalaryReportCrudController","_PayCertificateController","reports","isSelected","weeks","PayCertificateController","ConfigurableGridReportControllerBase","agGridModule","agGrid","eGridDiv","templateId","currentTemplate","saveTemplate","DatasetStatus","DatasetType","saveResult","editedTemplate","newTemplate","savedTemplate","workerPeriod","selectionResult","periodResult","workerIds","dataResult","customerTemplates","_CalculationReportController","sortingDateComparator","mA","mB","filterDateComparator","columnDefs","irGroupDef","typeGroupDef","employerCalcDef","workerCalcDef","totalsDef","totalGroupDef","incomeTypes","filterModel","periodDateKind","preset","calculationDef","dimensionDef","incomeTypeDef","rowTypeDef","workerTotalsDef","employerTotalsDef","totalFields","colId","rowGroup","aggFunc","CalculationReportController","_AccountingRowReportController","holidays","pivot","pivotIndex","AccountingRowReportController","_SummaryReportDisplayController","summaryReportData","SummaryReportDisplayController","_SummaryReportController","SummaryMapper","SummaryReportController","_AccountingReportDisplayController","getAccountingData","AccountingReportDisplayController","_WorkerSummaryReportController","workerSummaryReportData","WorkerSummaryMapper","WorkerSummaryReportController","_WorkerSummaryReportDisplayController","reportUrl","WorkerSummaryReportDisplayController","_HolidayReportController","holidayYears","queryDebt","yearData","resultRow","yearCalc","HolidayReportController","_SalarySlipDownloadController","zipBlob","SalarySlipDownloadController","_AccountingHolidayPayDebtReportQueryController","AccountingHolidayPayDebtReportQueryController","_HolidayPayReportQueryController","holidayYearsApi","crudItemId","irRow","HolidayPayReportQueryController","_SummaryReportQueryController","reportName","irReportRows","findAvatar","unionPaymentRows","workerName","periodEnd","unionName","payment","refNumber","UnionPaymentReportConfigGenerator","systemDimensions","hourlySalaryRowIndex","monthlySalaryRowIndex","salaryPaymentHoursRow","hourlySalariesRows","salaryPaymentMonthsRow","monthlySalariesCals","AllowanceCode","DailyAllowanceKind","EmploymentTerminationKind","WorkingTimeCompensationKind","RemunerationKind","OtherCompensationKind","NonProfitOrgKind","TrainingKind","PaidSickLeaveKind","SummaryReportQueryController","_PayStatsReportQueryController","applyClassRecursive","payStatsCalc","PayStatsReportQueryController","_AccountantController","removalDisabled","accountant","AccountantType","AccountantController","_AccountingChannelSettingsController","closeFn","coa","ownerId","AccountingTargets","targetToSave","AccountingChannelSettingsController","_AccountingTargetCrudController","isCredit","account","selectedAccount","sortKeys","debit","credit","isDebet","addToEnd","copyRow","removeFromTargetCoa","addToStart","newFlag","addFlagResult","FileLogic","fileDelimeter","FileDelimiter","firstRow","mappingResult","targetCoaAccount","rulesetAccount","legacyFlagDescription","flagParts","accountCandidate","digitsArr","firstKey","secondKey","AccountingTargetCrudController","_CompanySettingsController","contract","allContracts","SettingsStatus","methods","WorkerSalarySlipDeliveryMethod","logo","dataUri","contracts","today","CompanySettingsController","_InsuranceWizardController","partnerServices","insuranceAction","LocalTapiolaInsuranceOrderType","asap","firstDate","secondDate","thirdDate","fourthDate","orderTypes","InsuranceWizardController","_OwnerSettingsController","beneficialOwnersApi","$timoeut","numberOfShares","percentOfShares","singleOwner","OwnerSettingsController","_PaymentChannelSettingsController","isExternal","channelInEdit","supportedCompanies","isPensionIncludedSupported","channelSettings","saveSettings","channelToSave","PaymentChannelSettingsController","_RowTypesSettingsController","nextId","settingsRow","editableType","CalcRowConfigTypeGroup","RowTypesSettingsController","_ServiceModelCrudController","open","level1","level2","objToStore","TranslationsInstance","resetCommitted","schemas","ServiceModelCrudController","_SxyCodeEditorController","iFrame","clonedElement","SxyCodeEditorController","_SxyFormController","FormHelpers","propPath","rawErrors","SxyFormController","_SxyFormElementController","SxyFormElementController","_SxyGridController","selectedRows","fullMapper","exptMapper","mappers","itemToValidate","schemaDoc","excludeArr","headerName","enumValues","salaxyGridModule","gridWrapper","SxyGridController","_SxyInputController","childName","arrayItemsType","childType","childvalue","defaultLabel","readOnlyFormValue","requireValue","disableValue","defaultTop","includeArr","transEl","transScope","textOrElem","enumArr","enumName","enumFormat","SxyInputController","_SxySchemaEditorController","SxySchemaEditorController","_SxyTableController","colDefOrKey","tableOptions","keyString","arrayCandidate","_formatterParams","_onRendered","SxyTableController","_AccountResetController","testApi","AccountResetController","_SmokeTestController","sessionSrv","jsonTest","calcReport","SmokeTestController","_ReferenceObjectCrudController","ReferenceObjectCrudController","AbsencePeriodsControllerBindings","_AbsencePeriodsController","abs","AbsencePeriodsController","_EmploymentCrudController","$route","taxcardData","createIfNotExists","contact","cardType","employmentList","fullEmployment","Country","socialSecurity","pensionCalculation","insuranceCompany","socSecExceptions","workerAccount","workerAccountValue","EmploymentRelationSalaryPaymentMethod","EmploymentCrudController","_EmploymentTaxcardsController","EmploymentTaxcardsController","_EmploymentWizardController","useRealPersonaIdRange","commonSteps","closeFunction","card","Validation","EmploymentWizardController","_HolidayYearAccrualController","cumulative","startOfMonth","HolidayAccrualSource","startSaldo","HolidayYearAccrualController","_HolidayYearCrudController","hy","thisYear","spec","itemData","missingYear","itemToSave","savedValue","keepView","obj1","obj2","isAccrualView","HolidayYearCrudController","HolidayYearHolidaysControllerBindings","_HolidayYearHolidaysController","handleResult","confirmResult","HolidayYearHolidaysController","_HolidayYearPaidController","paidLeave","AnnualLeavePaymentKind","HolidayYearPaidController","_MyTaxcardsController","_taxcards","MyTaxcardsController","_TaxcardManualEditController","TaxCardIncomeType","todayYear","yearsAllowed","forYear","TaxcardManualEditController","_TaxcardCrudController","savedCard","TaxcardCrudController","_TaxcardIncomeLogController","TaxcardIncomeLogController","_WorkerAbsencesCrudController","todayDay","monthStart","monthEnd","previousMonthStart","previousMonthEnd","absences","WorkerAbsencesCrudController","_WorkerAccountCrudController","WorkerAccountCrudController","_WorkerAssureController","detailsCtrl","listCtrl","WorkerAssureController","_CalendarEventsCrudController","CalendarActionType","CalendarEventsCrudController","_DatasetsCrudController","ActionExecutor","dataObjectIndex","docUrl","schemaKey","DatasetsCrudController","_UsecasesCrudController","schemaNames","UsecaseActionType","calcType","UsecasesCrudController","_WorkflowController","wfType","assignedTo","workflowData","WorkflowController","isWorkflowPayload","isMessagesListItem","_WorkflowBadgeController","eventsOfTypes","eventOfType","ensureItem","messageString","uiStartX","uiEndX","messageEndX","aIdx","tIdx","WorkflowBadgeController","_TemplateCrudController","TemplateCrudController","ComponentBase","AccountInfo","AssurePartner","AuthCard","AuthorizedAccounts","AuthorizingAccounts","Certificates","Credentials","LanguageSelector","LoginButton","Signing","UserInfo","AccountAvatarEdit","AccountContactEdit","CalcEmployment","CalcRowsEditor","CalcUsecase","PayrollDetails","PayrollDetailsList","PayrollEdit","PayrollList","PayrollSelectList","PayrollDetailsSelectList","PayrollAssistant","CalcIrRows","CalcRows2019Editor","CalcRowCostAccounting","CalcRowDimensionInput","CalcsIrRows","CalcRowDocumentation","CalcRowFormula","Calc","CalcChart","CalcDashboard","CalcList","CalcNewIntro","CalcReport","CalcReports","CalcResults","CalcRowType","CalcSharingReceiptAction","CalcLeaves","CalcWorkerInfo","CalcWorktime","PayButton","CalcEditor","CalcCostAccounting","CostAccounting","SalaryDateKindButton","CalcRepair","CalcRepairInfo","ContactInfo","MessageThread","VarmaBanner","Welcome","HourlyReport","TimerBindings","Timer","ExpenseReport","MessageThreadList","Datepicker","DatepickerPopup","DateRange","FormGroup","Input","InputAccountingTarget","InputBoolean","InputCollectiveBargainAgreement","InputEnum","InputCredential","InputDuration","InputIncomeType","InputNumber","InputOccupationType","InputRrule","InputTime","ToggleButtons","Textarea","ValidationSummary","InputTypeahead","InputPayStatsRowType","InputHolidayMultipliers","InputEmployeeGroup","InputMarkdown","MarkdownEditor","MarkdownViewer","ActionButton","Avatar","Calendar","JsonFormatter","NaviSitemap","NaviStarterLayout","Spinner","Tabs","TabButtons","UiTranslator","DataImportComponentBase","CalcImport","CompanyImport","ImportStaging","WorkerImport","JsonDiff","CreditTransfer","InvoiceEdit","InvoiceList","InvoicePaymentList","InvoicePreview","InvoicesCreate","PaymentChannelInvoicePreview","InvoiceTools","InvoiceReport","CompanyInvoices","InvoiceAlerts","WorkerAssure","OdataFooter","OdataTable","OdataActions","AccountAuthorizationPerson","AccountAvatarEditPerson","AccountContactEditPerson","AccountDetailsPerson","AccountDetailsEditPerson","AccountInfoPerson","AccountInsuranceEditPerson","EmployerList","EmployerReport","EmployerSelect","CalcHouseholdUsecase","CalcSharing","CalcSharingInfo","HouseholdDeductionReport","WorkerReport","HouseholdYearList","HouseholdYearDetails","AccountingReportList","AccountingReportQuery","AccountingReportRows","AccountingReportTools","AccountingReportViewer","CalculationReport","HolidayReport","IrEarningsPayment","IrEarningsPaymentList","IrPayerSummary","IrPayerSummaryList","PayCertificate","ReportList","SalaryReportList","AccountingRowReport","SummaryReport","WorkerSummaryReport","AccountingHolidayPayDebtReportQuery","HolidayPayReportQuery","SummaryReportQuery","PayStatsReportQuery","Accountant","AccountingSettings","AccountingTargetDetails","AccountingTargetSettings","CostAccountingSettings","HolidaySettings","Insurance","InsuranceSettings","OwnerSettings","PaymentChannelSettings","PaymentSettings","ProSettings","RowTypesSettings","ServiceModelDetails","IrDeliverySettings","PayStatsSettings","SxyAlert","SxyCodeEditor","SxyFieldset","SxyForm","SxyGrid","SxyInput","SxySchemaEditor","SxyTable","AccountReset","SmokeTest","HolidayYearAccrual","HolidayYearHolidays","HolidayYearPaid","WorkerHolidays","EmploymentTaxcards","TaxcardDetails","TaxcardIncomeLogBindings","TaxcardIncomeLog","TaxcardManualEdit","TaxCardsList","TaxcardList","AbsencePeriods","EmploymentDetails","WorkerAbsences","WorkerDetails","EmploymentList","CalendarEventDetails","DatasetDetails","UsecaseDetails","Records","WorkflowButtons","WorkflowReopen","WorkflowBadge","ComponentsRegistration","Tab","routeToRegExp","slash","ngRouteModule","$RouteProvider","instantiateRoute","$routeMinErr","isEagerInstantiationEnabled","routeCopy","redirectPath","forceReload","preparedRoute","preparedRouteIsUpdateOnly","fakeLocationEvent","prepareRoute","commitRoute","newParams","switchRouteMatcher","$locationEvent","lastRoute","parseRoute","isNavigationUpdateOnly","nextRoute","nextRoutePromise","getRedirectionData","handlePossibleRedirection","keepProcessingRoute","resolveLocals","oldPath","oldSearch","getTemplateFor","newRoute","oldRoute","segmentMatch","$RouteParamsProvider","ngViewFactory","ngViewFillContentFactory","previousLeaveAnimation","cleanupLastView","angularRoute","$animateCss","expandingExpr","expandedExpr","collapsingExpr","collapsedExpr","cssTo","getScrollFromElement","expandDone","collapse","collapseDone","shouldCollapse","accordionConfig","openGroup","closeOthers","groupScope","accordionCtrl","accordionGroupCtrl","transclude","getHeaderSelectors","dismissOnTimeout","buttonConfig","buttonsCtrl","uncheckableExpr","uncheckable","getTrueValue","getCheckboxValue","getFalseValue","slides","SLIDE_DIRECTION","currentInterval","isPlaying","destroyed","slide","setActive","findSlideIndex","nextSlide","goNext","resetTimer","restartTimer","noTransition","resetTransition","currentIdx","timerFn","carouselCtrl","removeClass","directionClass","removeClassFn","SPECIAL_CHARACTERS_REGEXP","formatCodeToRegex","_date","getFormatCodeToRegex","createParser","quoteIndex","inLiteral","createFormatter","literalIdx","constructLiteralFormatter","constructFormatterFromIdx","endIdx","currentPosStr","baseDate","datesetter","timesetter","toTimezone","fromTimezone","ON_REGEXP","IS_REGEXP","linkedScopes","expToData","onExpMatches","onExp","expsStr","exps","addForExp","removeScope","compareWithExp","watchFn","compareWithVal","newActivated","thisVal","removedScope","newWatchScope","datepickerConfig","$datepickerLiteralWarning","$datepickerSuppressError","dateParser","ngModelOptions","watchListeners","dateObject","ngModelCtrl_","extractOptions","initDate","arrays","setMode","focusElement","DAYS_IN_MONTH","getDaysInMonth","startDate","firstDayOfMonth","difference","numDisplayedFromPreviousMonth","thursdayIndex","numWeeks","curWeek","getISO8601WeekNumber","_date1","_date2","checkDate","getStartingYear","datepickerCtrl","daypickerCtrl","monthpickerCtrl","SCROLLBAR_WIDTH","BODY_SCROLLBAR_WIDTH","OVERFLOW_REGEX","PLACEMENT_REGEX","BODY_REGEX","isStaticPositioned","bodyElem","scrollElem","elemStyle","includeHidden","overflowRegex","includeSelf","documentEl","excludeStatic","spStyle","includeMagins","elemOffset","elemBCR","useDocument","includePadding","offsetBCR","offsetParentBCR","offsetParentStyle","autoPlace","hostElem","targetElem","appendToBody","targetWidth","targetHeight","hostElemPos","targetElemPos","viewportOffset","targetElemStyle","adjustedSize","xOverflow","yOverflow","placementClasses","containerPosition","currentHeight","innerElem","isTooltip","arrowElem","arrowCss","borderProp","borderRadiusProp","$position","datepickerPopupConfig","$datepickerPopupLiteralWarning","isHtml5DateInput","closeOnDateSelection","onOpenFocus","datepickerPopupTemplateUrl","datepickerTemplateUrl","popupEl","datepickerEl","scrollParentEl","ngModel","$popup","altInputFormats","_ngModel_","newDateFormat","parseDateString","inputKeydownBind","documentClickBind","positionPopup","dpContainsTarget","popupContainsTarget","dpElement","debounceTime","timeoutPromise","$$multiMap","openScope","openedContainers","dropdownScope","appendTo","openedDropdowns","openDropdown","toClose","dropdown","closeDropdown","openedScopes","dropdownToClose","dropdownElement","dropdownElementTargeted","toggleElementTargeted","dropdownConfig","uibDropdownService","templateScope","appendToOpenClass","openClass","getIsOpen","setIsOpen","toggleInvoker","keynavEnabled","keyCode","removeDropdownMenu","wasOpen","appendToEl","appendToBodyValue","rightalign","scrollbarPadding","appendOffset","openContainer","dropdownOpenClass","hasOpenClass","isOnlyOpen","toggleClass","tplContent","newEl","dropdownCtrl","tplUrl","toggleDropdown","invocables","resolves","resolveIter","$modalStack","setIsAsync","modalRenderDeferObj","animationPromise","inputWithAutofocus","$$stackedMap","$uibPosition","OPENED_MODAL_CLASS","backdropDomEl","backdropScope","openedWindows","openedClasses","topModalIndex","previousTopOpenedModal","ARIA_HIDDEN_ATTRIBUTE_NAME","tabbableSelector","isVisible","backdropIndex","topBackdropIndex","opened","newBackdropIndex","removeModalWindow","modalInstance","elementToReceiveFocus","modalWindow","appendToElement","removeAfterAnimate","modalBodyClass","areAnyOpen","toggleTopWindowClass","checkRemoveBackdrop","toggleSwitch","domEl","closedDeferred","asyncDeferred","asyncPromise","afterAnimating","keydownListener","focusChanged","modalOpener","currBackdropIndex","angularDomEl","applyAriaHidden","getSiblings","elemIsAlreadyHidden","ariaHiddenCount","broadcastClosing","resultOrReason","closing","unhideBackgroundElements","hiddenEl","newHiddenCount","topModal","modalDomEl","modalDomE1","$modalProvider","$uibResolve","$modal","getTemplatePromise","promiseChain","modalResultDeferred","modalOpenedDeferred","modalClosedDeferred","modalRenderDeferred","templateAndResolvePromise","resolveWithTemplate","samePromise","tplAndVars","providedScope","modalScope","ctrlInstance","ctrlInstantiate","ctrlLocals","constructLocals","instanceOnScope","injectable","newTotal","oldTotal","clickAllowed","uibPaging","uibPagerConfig","paginationCtrl","uibPaginationConfig","forceEllipses","boundaryLinkNumbers","pageLabel","makePage","getPages","startPage","endPage","isMaxSized","previousPageSet","secondPageLink","firstPageLink","nextPageSet","secondToLastPageLink","lastPageLink","triggerMap","globalOptions","triggers","openedTooltips","keypressListener","ttType","defaultTriggerShow","getTriggers","show","startSym","endSym","tElem","tooltipLinker","tooltipCtrl","tooltipLinkedScope","transitionTimeout","showTimeout","hideTimeout","positionTimeout","adjustmentTimeout","hasEnableExp","ttScope","repositionScheduled","isOpenParse","contentParse","observers","lastPlacement","positionTooltip","ttPosition","elementPos","adjustment","toggleTooltipBind","hideTooltipBind","showTooltipBind","cancelHide","prepareTooltip","cancelShow","createTooltip","assignIsOpen","removeTooltip","prepObservers","unregisterObservers","closeDelay","bodyHideTooltipBind","hideOnEscapeKey","unregisterTriggers","prepTriggers","showTriggers","hideTriggers","appendToBodyVal","appendKey","origScope","$uibTooltip","progressConfig","animate","getMaxOrDefault","totalPercentage","maxParam","progressCtrl","ratingConfig","tmpTitles","ratingStates","states","newViewValue","ratingCtrl","oldIndex","previousIndex","findTabIndex","previousSelected","newActiveIndex","tabsetCtrl","isTabHeading","timepickerConfig","hoursModelCtrl","minutesModelCtrl","secondsModelCtrl","meridians","padHours","hoursInputEl","minutesInputEl","secondsInputEl","mousewheel","arrowkeys","hourStep","minuteStep","incrementedSelected","addMinutes","decrementedSelected","addSeconds","secondStep","getHoursFromTemplate","getMinutesFromTemplate","updateTemplate","getSecondsFromTemplate","noPad","isScrollingUp","invalidate","invalidHours","invalidMinutes","invalidSeconds","modelIsEmpty","makeValid","keyboardChange","addSecondsToSelected","newDate","uibTimepickerConfig","timepickerCtrl","TYPEAHEAD_REGEXP","originalScope","$$debounce","typeaheadParser","HOT_KEYS","eventDebounceTime","minLength","waitTime","isEditable","isLoadingSetter","isSelectEvent","vals","onSelectCallback","isSelectOnBlur","isNoResultsSetter","inputFormatter","focusFirst","selectOnExact","isOpenSetter","showHint","parsedModel","$setModelValue","parserResult","hasFocus","offDestroy","popupId","inputsContainer","hintInputElem","popUpEl","resetHint","resetMatches","getMatchId","inputIsExactMatch","inputValue","getMatchesAsync","onCurrentRequest","recalculatePosition","firstLabel","fireRecalculating","debouncedRecalculate","scheduleSearchWithTimeout","cancelPreviousTimeout","activeIdx","shouldSelect","dismissClickHandler","_modelCtrl","candidateViewValue","emptyViewValue","isDropdownOpen","matchIdx","tplEl","isSanitizePresent","escapeRegexp","queryToEscape","containsHtml","matchItem","angularUiBootstrap","$sanitizeMinErr","nodeContains","htmlParser","htmlSanitizeWriter","$SanitizeProvider","hasBeenInstantiated","svgEnabled","validElements","svgElements","isImage","enableSvg","addElementsTo","voidElements","validAttrs","arrayToMap","htmlParserImpl","htmlSanitizeWriterImpl","SURROGATE_PAIR_REGEXP","NON_ALPHANUMERIC_REGEXP","stringToMap","optionalEndTagBlockElements","optionalEndTagInlineElements","optionalEndTagElements","blockElements","inlineElements","blockedElements","uriAttrs","htmlAttrs","svgAttrs","lowercaseKeys","elementsMap","newElements","getInertBodyElement","isDOMParserAvailable","getInertBodyElement_DOMParser","inertDocument","inertBodyElement","getInertBodyElement_InertDocument","stripCustomNsAttrs","mXSSAttempts","attrToMap","getNonDescendant","encodeEntities","uriValidator","ignoreCurrentElement","lkey","attrNode","sanitizeText","writer","$sanitize","LINKY_URL_REGEXP","MAILTO_REGEXP","linkyMinErr","attributesFn","addText","addLink","linkAttributes","angularSanitize","patchXHR","fnName","newFn","redefineProp","initializeUploadListener","origAddEventListener","formData","fileApiXHR","isInputTypeFile","hasFlash","fo","getOffset","jsUrl","allScripts","fileElem","fixInputStyle","fileApiChangeFn","disable","loadStarted","constructEvent","ngFileUpload","upload","resumeSupported","sendHttp","notifyProgress","getNotifyEvent","uploadWithAngular","fileSize","origXhrFn","toResumeFile","addFieldToFormData","objectKey","digestConfig","arrayBufferView","UploadExif","modelOptions","applyExifRotations","fixedFile","resizeFile","resizeVal","resizeWithParams","handleFile","resizedFile","fileChange","noDelay","invalidFiles","newFiles","dupFiles","isSingleModel","invalidModel","allNewFiles","prevValidFiles","prevInvalidFiles","invalids","valids","removeDuplicates","f1","f2","isInPrevFiles","resizeAndUpdate","keep","resizingFiles","validateAfterResize","validationResult","Upload","generatedElems","isDelayedClickSupported","linkFileSelect","attrGetter","fileChangeAttr","fileList","unwatches","bindAttrToFileInput","updateId","createFileInput","clickHandler","detectSwipe","resetModel","initialTouchStartY","initialTouchStartX","currentX","currentY","ie10SameFileSelectFix","UploadBase","disallowObjectUrl","URL","maxMemory","maxLength","fileReader","getTagType","linkFileDirective","resizeParams","isBackground","constructDataUrl","UploadDataUrl","trustedUrl","globStringToRegex","excludes","exclude","xIndex","filesArray","markModelAsDirty","validationName","dName","prevLength","ignoredErrors","runAllValidation","validateSync","totalSize","validateAsync","asyncFn","resolveResult","resolveInternal","deffer","dataUrl","img","secondsCounter","checkLoadErrorInCaseOfNoCallback","checkLoadError","UploadValidate","calculateAspectRatioFit","srcWidth","srcHeight","centerCrop","imagen","quality","resizeIf","canvasElement","imageElement","imgWidth","imgHeight","ratioFloat","imgRatio","dataurl","origSize","u8arr","linkDrop","dropAvailable","isDisabled","leaveTimeout","dragOverDelay","actualDragOverClass","calculateDragOverClass","extractFilesAndUpdateModel","updateOnType","extractFiles","extractFilesFromHtml","updateOn","dClass","allowDir","maxFiles","maxTotalSize","includeDir","traverseFileTree","dirReader","readEntries","UploadResize","applyTransform","orientation","slicedFile","marker","little","tags","arrayBufferToBase64","ExifRestorer","origFileBase64","resizedFileBase64","rawImage","exifArray","newImageArray","seg","imageData","separatePoint","mae","ato","rawImageArray","endPoint","base64test","runTranslate","$translate","$translateDefaultInterpolation","translateDirective","translateAttrDirective","translateCloakDirective","translateFilterFactory","$translationCache","fallbackFromIncorrectStorageValue","preferred","$translateSanitizationProvider","currentStrategy","hasConfiguredStrategy","hasShownNoStrategyConfiguredWarning","strategies","htmlSanitizeValue","htmlEscapeValue","mapInterpolationParameters","htmlTrustValue","strategyName","strategyFunction","cachedStrategyMap","applyStrategies","selectedStrategies","selectedStrategy","showNoStrategyConfiguredWarning","iteratee","propertyValue","propertyKey","$STORAGE_KEY","$windowProvider","pascalprechtTranslateOverrider","$translationTable","$preferredLanguage","$availableLanguageKeys","$languageKeyAliases","$fallbackLanguage","$fallbackWasString","$uses","$nextLang","$storageFactory","$storageKey","$storagePrefix","$missingTranslationHandlerFactory","$interpolationFactory","$interpolatorFactories","$loaderFactory","$cloakClassName","$loaderOptions","$notFoundIndicatorLeft","$notFoundIndicatorRight","$postCompilingEnabled","$forceAsyncReloadEnabled","$allowNamespaces","$nestedObjectDelimeter","$isReady","$keepContent","loaderCache","directivePriority","statefulFilter","postProcessFn","uniformLanguageTagResolver","languageTagResolver","temp","getFirstBrowserLanguage","nav","browserLanguagePropertyKeys","getLocale","indexOf","searchElement","negotiateLocale","alias","langKeyAlias","hasWildcardKey","hasExactKey","translations","langKey","translationTable","flatObject","namespacesEnabled","prevKey","keyWithPath","keyWithShortPath","setupPreferredLanguage","indicator","fallbackStack","loaderFactory","storageFactory","languageKeys","aliases","Storage","defaultInterpolator","pendingLoader","interpolatorHashMap","langPromises","fallbackIndex","startFallbackIteration","translationId","interpolateParams","interpolationId","defaultTranslationText","forceLanguage","sanitizeStrategy","uses","loadTranslationsIfMissing","translateAll","translationIds","regardless","promiseToWaitFor","determineTranslation","promiseResolved","applyNotFoundIndicators","useLanguage","eachInterpolator","interpolator","loadAsync","loaderOptions","onLoaderSuccess","onLoaderError","eachInterpolationFactory","interpolatorFactory","getTranslationTable","onResolve","getFallbackTranslation","Interpolator","translation","interpolatedValue","applyPostProcessing","getFallbackTranslationInstant","translateByHandler","resolveForFallbackLanguage","fallbackLanguageIndex","missingTranslationHandlerTranslation","resolveForFallbackLanguageInstant","fallbackTranslation","fallbackTranslationInstant","resolvedTranslation","_translationId","determineTranslationInstant","clearNextLangAndPromise","langKeyPosition","updatedLanguages","loadNewData","languageKey","languagesToReload","possibleLangKeys","possibleLangKey","$onReadyDeferred","globalOnReadyListener","globalOnChangeListener","processAsyncResult","fallbackLanguageId","$translateSanitization","$translateInterpolator","$identifier","interpolationParams","interpolatedText","translateValuesExist","translateInterpolation","translateSanitizeStrategyExist","translateValueExist","interpolateRegExp","watcherRegExp","iElement","iAttr","getTranslateNamespace","initInterpolationParams","observeElementTranslation","iElementText","interpolateMatches","watcherMatches","updateTranslations","observeAttributeTranslation","translateAttr","firstAttributeChangedEvent","observeValueAttribute","updateTranslation","translateNamespace","applyTranslation","successful","globallyEnabled","locallyDefined","locallyEnabled","unbind","translateValues","translateSanitizeStrategy","previousAttributes","watchAttribute","valueCallback","changeCallback","applyCloak","removeCloak","iRemoveCloak","iApplyCloak","translateNamespaceDirective","iAttrs","_getTranslateNamespace","translateLanguageDirective","newTranslateLanguage","translateFilter","interpolation","ControllersRegistration","AppendNodeDirective","elementMap","instanceMap","MAX_UID","MILLISECONDS_MULTIPLIER","TRANSITION_END","parseSelector","toType","getUID","getTransitionDurationFromElement","transitionDuration","transitionDelay","floatTransitionDuration","floatTransitionDelay","triggerTransitionEnd","getElement","elementIsVisible","closedDetails","summary","findShadowRoot","reflow","getjQuery","DOMContentLoadedCallbacks","onDOMContentLoaded","isRTL","defineJQueryPlugin","JQUERY_NO_CONFLICT","execute","possibleCallback","executeAfterTransition","transitionElement","waitForTransition","emulatedDuration","called","getNextActiveElement","activeElement","shouldGetNext","isCycleAllowed","listLength","namespaceRegex","stripNameRegex","stripUidRegex","eventRegistry","uidEvent","customEvents","nativeEvents","makeEventUid","getElementEvents","bootstrapHandler","hydrateObj","EventHandler","bootstrapDelegationHandler","domElements","domElement","findHandler","callable","delegationSelector","normalizeParameters","originalTypeEvent","delegationFunction","isDelegated","typeEvent","getTypeEvent","oneOff","handlers","previousFunction","removeNamespacedHandlers","storeElementEvent","handlerKey","inNamespace","isNamespace","elementEvent","keyHandlers","jQueryEvent","bubbles","nativeDispatch","normalizeData","normalizeDataKey","Manipulator","bsKeys","pureKey","jsonConfig","configTypes","expectedTypes","BaseComponent","isAnimated","getSelector","hrefAttribute","SelectorEngine","parents","ancestor","focusables","enableDismissTrigger","clickEvent","NAME$f","EVENT_KEY$b","EVENT_CLOSE","EVENT_CLOSED","CLASS_NAME_FADE$5","CLASS_NAME_SHOW$8","NAME$e","EVENT_KEY$a","DATA_API_KEY$6","CLASS_NAME_ACTIVE$3","SELECTOR_DATA_TOGGLE$5","EVENT_CLICK_DATA_API$6","Button","NAME$d","EVENT_KEY$9","EVENT_TOUCHSTART","EVENT_TOUCHMOVE","EVENT_TOUCHEND","EVENT_POINTERDOWN","EVENT_POINTERUP","POINTER_TYPE_TOUCH","POINTER_TYPE_PEN","CLASS_NAME_POINTER_EVENT","SWIPE_THRESHOLD","Default$c","DefaultType$c","Swipe","absDeltaX","NAME$c","EVENT_KEY$8","DATA_API_KEY$5","ARROW_LEFT_KEY$1","ARROW_RIGHT_KEY$1","TOUCHEVENT_COMPAT_WAIT","ORDER_NEXT","ORDER_PREV","DIRECTION_LEFT","DIRECTION_RIGHT","EVENT_SLIDE","EVENT_SLID","EVENT_KEYDOWN$1","EVENT_MOUSEENTER$1","EVENT_MOUSELEAVE$1","EVENT_DRAG_START","EVENT_LOAD_DATA_API$3","EVENT_CLICK_DATA_API$5","CLASS_NAME_CAROUSEL","CLASS_NAME_ACTIVE$2","CLASS_NAME_SLIDE","CLASS_NAME_END","CLASS_NAME_START","CLASS_NAME_NEXT","CLASS_NAME_PREV","SELECTOR_ACTIVE","SELECTOR_ITEM","SELECTOR_ACTIVE_ITEM","SELECTOR_ITEM_IMG","SELECTOR_INDICATORS","SELECTOR_DATA_SLIDE","SELECTOR_DATA_RIDE","KEY_TO_DIRECTION","Default$b","DefaultType$b","Carousel","swipeConfig","activeIndicator","newActiveIndicator","elementInterval","isNext","nextElement","nextElementIndex","triggerEvent","isCycling","directionalClassName","orderClassName","completeCallBack","carousel","slideIndex","carousels","NAME$b","EVENT_KEY$7","DATA_API_KEY$4","EVENT_SHOW$6","EVENT_SHOWN$6","EVENT_HIDE$6","EVENT_HIDDEN$6","EVENT_CLICK_DATA_API$4","CLASS_NAME_SHOW$7","CLASS_NAME_COLLAPSE","CLASS_NAME_COLLAPSING","CLASS_NAME_COLLAPSED","CLASS_NAME_DEEPER_CHILDREN","CLASS_NAME_HORIZONTAL","WIDTH","HEIGHT","SELECTOR_ACTIVES","SELECTOR_DATA_TOGGLE$4","Default$a","DefaultType$a","Collapse","foundElement","activeChildren","activeInstance","complete","scrollSize","triggerArray","_config","NAME$a","EVENT_KEY$6","DATA_API_KEY$3","ESCAPE_KEY$2","TAB_KEY$1","ARROW_UP_KEY$1","ARROW_DOWN_KEY$1","RIGHT_MOUSE_BUTTON","EVENT_HIDE$5","EVENT_HIDDEN$5","EVENT_SHOW$5","EVENT_SHOWN$5","EVENT_CLICK_DATA_API$3","EVENT_KEYDOWN_DATA_API","EVENT_KEYUP_DATA_API","CLASS_NAME_SHOW$6","CLASS_NAME_DROPUP","CLASS_NAME_DROPEND","CLASS_NAME_DROPSTART","CLASS_NAME_DROPUP_CENTER","CLASS_NAME_DROPDOWN_CENTER","SELECTOR_DATA_TOGGLE$3","SELECTOR_DATA_TOGGLE_SHOWN","SELECTOR_MENU","SELECTOR_NAVBAR","SELECTOR_NAVBAR_NAV","SELECTOR_VISIBLE_ITEMS","PLACEMENT_TOP","PLACEMENT_TOPEND","PLACEMENT_BOTTOM","PLACEMENT_BOTTOMEND","PLACEMENT_RIGHT","PLACEMENT_LEFT","PLACEMENT_TOPCENTER","PLACEMENT_BOTTOMCENTER","Default$9","DefaultType$9","Dropdown","relatedTarget","Popper","referenceElement","popperConfig","Popper.createPopper","parentDropdown","isEnd","popperData","defaultBsPopperConfig","openToggles","toggle","composedPath","isMenuTarget","isInput","isEscapeEvent","isUpOrDownEvent","getToggleButton","NAME$9","CLASS_NAME_FADE$4","CLASS_NAME_SHOW$5","EVENT_MOUSEDOWN","Default$8","DefaultType$8","Backdrop","NAME$8","EVENT_KEY$5","EVENT_FOCUSIN$2","EVENT_KEYDOWN_TAB","TAB_KEY","TAB_NAV_FORWARD","TAB_NAV_BACKWARD","Default$7","DefaultType$7","FocusTrap","trapElement","SELECTOR_FIXED_CONTENT","SELECTOR_STICKY_CONTENT","PROPERTY_PADDING","PROPERTY_MARGIN","ScrollBarHelper","documentWidth","calculatedValue","styleProperty","manipulationCallBack","actualValue","callBack","NAME$7","EVENT_KEY$4","DATA_API_KEY$2","ESCAPE_KEY$1","EVENT_HIDE$4","EVENT_HIDE_PREVENTED$1","EVENT_HIDDEN$4","EVENT_SHOW$4","EVENT_SHOWN$4","EVENT_RESIZE$1","EVENT_CLICK_DISMISS","EVENT_MOUSEDOWN_DISMISS","EVENT_KEYDOWN_DISMISS$1","EVENT_CLICK_DATA_API$2","CLASS_NAME_OPEN","CLASS_NAME_FADE$3","CLASS_NAME_SHOW$4","CLASS_NAME_STATIC","OPEN_SELECTOR$1","SELECTOR_DIALOG","SELECTOR_MODAL_BODY","SELECTOR_DATA_TOGGLE$2","Default$6","DefaultType$6","Modal","modalBody","transitionComplete","event2","isModalOverflowing","initialOverflowY","isBodyOverflowing","showEvent","alreadyOpen","NAME$6","EVENT_KEY$3","DATA_API_KEY$1","EVENT_LOAD_DATA_API$2","ESCAPE_KEY","CLASS_NAME_SHOW$3","CLASS_NAME_SHOWING$1","CLASS_NAME_HIDING","CLASS_NAME_BACKDROP","OPEN_SELECTOR","EVENT_SHOW$3","EVENT_SHOWN$3","EVENT_HIDE$3","EVENT_HIDE_PREVENTED","EVENT_HIDDEN$3","EVENT_RESIZE","EVENT_CLICK_DATA_API$1","EVENT_KEYDOWN_DISMISS","SELECTOR_DATA_TOGGLE$1","Default$5","DefaultType$5","Offcanvas","completeCallback","clickCallback","DefaultAllowlist","uriAttributes","SAFE_URL_PATTERN","allowedAttribute","allowedAttributeList","attributeRegex","sanitizeHtml","unsafeHtml","allowList","sanitizeFunction","createdDocument","attributeList","allowedAttributes","NAME$5","Default$4","DefaultType$4","DefaultContentType","TemplateFactory","templateWrapper","extraClass","NAME$4","DISALLOWED_ATTRIBUTES","CLASS_NAME_FADE$2","CLASS_NAME_MODAL","CLASS_NAME_SHOW$2","SELECTOR_TOOLTIP_INNER","SELECTOR_MODAL","EVENT_MODAL_HIDE","TRIGGER_HOVER","TRIGGER_FOCUS","TRIGGER_CLICK","TRIGGER_MANUAL","EVENT_HIDE$2","EVENT_HIDDEN$2","EVENT_SHOW$2","EVENT_SHOWN$2","EVENT_INSERTED","EVENT_CLICK$1","EVENT_FOCUSIN$1","EVENT_FOCUSOUT$1","EVENT_MOUSEENTER","EVENT_MOUSELEAVE","AttachmentMap","Default$3","DefaultType$3","isInTheDom","tip","tipId","eventIn","eventOut","dataAttributes","dataAttribute","NAME$3","SELECTOR_TITLE","SELECTOR_CONTENT","Default$2","DefaultType$2","Popover","NAME$2","EVENT_KEY$2","DATA_API_KEY","EVENT_ACTIVATE","EVENT_CLICK","EVENT_LOAD_DATA_API$1","CLASS_NAME_DROPDOWN_ITEM","CLASS_NAME_ACTIVE$1","SELECTOR_DATA_SPY","SELECTOR_TARGET_LINKS","SELECTOR_NAV_LIST_GROUP","SELECTOR_NAV_LINKS","SELECTOR_LINK_ITEMS","SELECTOR_DROPDOWN","SELECTOR_DROPDOWN_TOGGLE$1","Default$1","DefaultType$1","ScrollSpy","observableSection","targetElement","activate","parentScrollTop","userScrollsDown","entryIsLowerThanPrevious","targetLinks","listGroup","activeNodes","spy","NAME$1","EVENT_KEY$1","EVENT_HIDE$1","EVENT_HIDDEN$1","EVENT_SHOW$1","EVENT_SHOWN$1","EVENT_CLICK_DATA_API","EVENT_KEYDOWN","EVENT_LOAD_DATA_API","ARROW_LEFT_KEY","ARROW_RIGHT_KEY","ARROW_UP_KEY","ARROW_DOWN_KEY","HOME_KEY","END_KEY","CLASS_NAME_ACTIVE","CLASS_NAME_FADE$1","CLASS_NAME_SHOW$1","CLASS_DROPDOWN","SELECTOR_DROPDOWN_TOGGLE","SELECTOR_DROPDOWN_MENU","NOT_SELECTOR_DROPDOWN_TOGGLE","SELECTOR_TAB_PANEL","SELECTOR_OUTER","SELECTOR_INNER","SELECTOR_DATA_TOGGLE","SELECTOR_INNER_ELEM","SELECTOR_DATA_TOGGLE_ACTIVE","hideEvent","relatedElem","nextActiveElement","outerElem","EVENT_KEY","EVENT_MOUSEOVER","EVENT_MOUSEOUT","EVENT_FOCUSIN","EVENT_FOCUSOUT","EVENT_HIDE","EVENT_HIDDEN","EVENT_SHOW","EVENT_SHOWN","CLASS_NAME_FADE","CLASS_NAME_HIDE","CLASS_NAME_SHOW","CLASS_NAME_SHOWING","DefaultType","Default","Toast","isInteracting","Bs5Tooltip","Bs5Popover","EnumParserFunctions","IfRoleDirective","IfSitemapDirective","compareTo","LoaderDirective","OrderbyDirective","ValidatorFunctions","attrValue","validationFunction","validationFunctions","DatepickerInputValidationDirective","datepickerOptions","modelValueDay","minDateDay","maxDateDay","_getDefaults","_defaults","changeDefaults","newDefaults","escapeTest","escapeReplace","escapeTestNoEncode","escapeReplaceNoEncode","escapeReplacements","getEscapeReplacement","escape$1","unescapeTest","unescape","edit","valSource","cleanUrl","noopTest","splitCells","tableRow","escaped","rtrim","invert","suffLen","findClosingBracket","outputLink","cap","indentCodeCompensation","matchIndentToCode","indentToCode","matchIndentInNode","indentInNode","_Tokenizer","tokens","bull","isordered","itemRegex","itemContents","endsWithBlankLine","endEarly","nextLine","blankLine","nextBulletRegex","hrRegex","fencesBeginRegex","headingBeginRegex","rawLine","istask","ischecked","spacers","hasMultipleLineBreaks","aligns","trimmedUrl","rtrimSlash","lastParenIndex","linkLen","linkString","maskedSrc","prevChar","lLength","rDelim","rLength","delimTotal","midDelimTotal","endReg","lastCharLength","hasNonSpaceChars","hasSpaceCharsOnBothEnds","prevCapZero","newline","blockCode","fences","bullet","lheading","_paragraph","blockText","_blockLabel","_comment","paragraph","blockNormal","gfmTable","blockGfm","blockPedantic","inlineCode","br","inlineText","_punctuation","punctuation","blockSkip","emStrongLDelim","emStrongRDelimAst","emStrongRDelimUnd","anyPunctuation","autolink","_inlineComment","_inlineLabel","reflink","nolink","reflinkSearch","inlineNormal","inlinePedantic","inlineGfm","inlineBreaks","_Lexer","leading","lastToken","cutSrc","lastParagraphClipped","extTokenizer","tempSrc","tempStart","getStartIndex","errMsg","keepPrevChar","_Renderer","infostring","startatt","task","checked","cleanHref","_TextRenderer","_Parser","genericToken","headingToken","codeToken","tableToken","blockquoteToken","listToken","loose","itemBody","htmlToken","paragraphToken","textToken","renderer","escapeToken","tagToken","linkToken","imageToken","strongToken","emToken","codespanToken","delToken","_Hooks","markdown","Marked","__privateAdd","_parseMarkdown","_onError","__privateMethod","parseMarkdown_fn","childTokens","prevRenderer","extLevel","rendererProp","rendererFunc","tokenizer","tokenizerProp","tokenizerFunc","prevTokenizer","hooksProp","hooksFunc","prevHook","walkTokens","packWalktokens","origOpt","throwError","onError_fn","async","markedInstance","marked","HtmlDirective","cElement","cAttr","endsWith","sxyHtml","TextDirective","wsTranslate","getUntrimmedAttributeValue","DirectivesRegistration","_FilterFunctions","splitValues","employmentData","nullText","zeroText","addWorkDays","messageTypes","uiClassMarker","uiClassEndMarker","shortMessage","fullMessage","uiClass","dtReg","sectionToCheck","sitemapPath","splitPaths","companySite","resultSitemapNode","currentSection","visibilityToEvaluate","FilterFunctions","FiltersRegistration","LoaderInterceptor","rejection","TemplateInterceptor","views","ServicesRegistration","CustomerInvoices","Absences","Accounts","AccountSettings","BeneficialOwnersApi","BusinessTemplates","Calculator","CalendarEvents","Client","Datasets","Employments","HolidayYears","Imports","Invoices","IrEarningsPayments","IrPayerSummaries","MessageThreads","OAuth2","Onboardings","Overview","PartnerServices","ProApi","ReferenceObjects","Reports","Session","Taxcards","Test","Usecases","Workers","ServiceModels","HouseholdYears","SalaxyNg1ComponentsModule","ngBs","sco","tx","$httpProvider","$translateProvider","$locationProvider","SalaxyNg1BootstrapTemplatesModule","_PersonalWebLegacyController","PersonalWebLegacyController","_PersonalWebSiteMap","PersonalWebSiteMap","routeHelperProvider","personalRoot"],"mappings":"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AU,EAAGG,EAAM,EAC3C,WAAmB,CAAE,EAAG,WAAY,EAAGA,EAAM,EAC7C,WAAmB,CAAA,CAC3B,EAGIW,GAAc,CACV,EAAe,KACf,EAAe,KACf,EAAe,GACf,EAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,GAAe,KACf,IAAe,KACf,IAAe,KACf,IAAe,KACf,IAAe,KACf,IAAe,KACf,IAAe,KACf,IAAe,KACf,IAAe,KACf,IAAe,KACf,IAAe,KACf,IAAe,KACf,IAAe,KACf,IAAe,KACf,IAAe,KACf,IAAe,KACf,IAAe,KACf,IAAe,KACf,IAAe,KACf,IAAe,KACf,MAAe,IACvB,EAGIC,GAAiB,CACpB,KACA,QACA,aACA,WACA,YACA,iBACA,eACA,WACA,SACA,WACA,cACA,kBACA,gBACA,YACA,UACA,YACA,eACA,UACA,UACD,EAEA,SAASC,GAAO5oL,EAA2D,CAAE,OAAOA,EAAI,IAAI,SAASjC,EAAG,CAAE,MAAO,CAAEA,GAAG,GAAI,IAAKA,GAAG,EAAG,IAAIA,EAAE,GAAG,CAAG,CAAC,CAAG,CAIrJ,IAAI8qL,GAAwBD,GAAO,CAElC,EACA,SACA,SACA,MACA,IACA,SACA,SACA,MAGA,EACA,SACA,SACA,MACA,IACA,SACA,SACA,MAEA,QACA,MACA,IACA,QACA,QACA,MACA,SACA,QACA,SACA,SACA,SACA,SACA,QACA,SACA,MACA,SAEA,IACA,SACA,SACA,MACA,QACA,QACA,MACA,IACA,MACA,SACA,SACA,SACA,SACA,SACA,SACA,SAEA,QACA,QACA,SACA,SACA,SACA,SACA,QACA,QACA,MACA,QACA,MACA,QACA,SACA,SACA,QACA,QAGA,SACA,EACA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cACL,IAAK,UACL,IAAK,YACL,IAAK,iBACL,IAAK,cACL,IAAK,oBACL,IAAK,gBACL,IAAK,eACL,IAAK,iBACL,IAAK,kBACL,IAAK,cACL,IAAK,qBACL,IAAK,SACL,IAAK,cACL,IAAK,WACL,IAAK,WACL,IAAK,eACL,IAAK,eACL,IAAK,iBACL,IAAK,eACL,IAAK,kBACL,IAAK,qBACL,IAAK,aACL,IAAK,YACL,IAAK,YACL,IAAK,gBACL,IAAK,cACL,IAAK,eACL,IAAK,kBACL,IAAK,oBACL,IAAK,kBACL,IAAK,iBACL,IAAK,UACL,IAAK,YACL,IAAK,YACL,IAAK,aACL,IAAK,cACL,IAAK,UACL,IAAK,SACL,IAAK,cACL,IAAK,UACL,IAAK,oBACL,IAAK,kBACL,IAAK,QACL,IAAK,aACL,IAAK,YACL,IAAK,cACL,IAAK,mBACL,IAAK,oBACL,IAAK,cACL,IAAK,cACL,IAAK,mBACL,IAAK,eACL,IAAK,aACL,IAAK,eACL,IAAK,gBACL,IAAK,aACL,IAAK,cACL,IAAK,cACL,IAAK,iBACL,IAAK,YACL,IAAK,cACL,IAAK,eACL,IAAK,aACL,IAAK,aACL,IAAK,gBACL,IAAK,eACL,IAAK,kBACL,IAAK,gBACL,IAAK,qBACL,IAAK,WACL,IAAK,OACL,IAAK,gBACL,IAAK,kBACL,IAAK,aACL,IAAK,aACL,IAAK,eACL,IAAK,iBACL,IAAK,cACL,IAAK,iBACL,IAAK,qBACL,IAAK,YACL,IAAK,oBACL,IAAK,WACL,IAAK,cACL,IAAK,iBACL,IAAK,WACL,IAAK,eACL,IAAK,gBACL,IAAK,gBACL,IAAK,mBACL,IAAK,iBACL,IAAK,eACL,IAAK,cACL,IAAK,YACL,IAAK,kBACL,IAAK,oBACL,IAAK,iBACL,IAAK,YACL,IAAK,aACL,IAAK,oBACL,IAAK,aACL,IAAK,eACL,IAAK,iBACL,IAAK,kBACL,IAAK,eACL,IAAK,gBACL,IAAK,gBACL,IAAK,qBACL,IAAK,mBACL,IAAK,qBACL,IAAK,yBACL,IAAK,cACL,IAAK,aACL,IAAK,mBACL,IAAK,sBACL,IAAK,eACL,IAAK,eACL,IAAK,gBACL,IAAK,cACL,IAAK,kBACL,IAAK,cACL,IAAK,gBACL,IAAK,kBACL,IAAK,2BACL,IAAK,eACL,IAAK,iBACL,IAAK,aACL,IAAK,iBACL,IAAK,YACL,IAAK,mBACL,IAAK,cACL,IAAK,wBACL,IAAK,kBACL,IAAK,qBACL,IAAK,kBACL,IAAK,kBACL,IAAK,kBACL,IAAK,qBACL,IAAK,aACL,IAAK,iBACL,IAAK,eACL,IAAK,mBACL,IAAK,aACL,IAAK,eACL,IAAK,kBACL,IAAK,gBACL,IAAK,gBACL,IAAK,kBACL,IAAK,kBACL,IAAK,gBACL,IAAK,iBACL,IAAK,uBACL,IAAK,0BACL,IAAK,iBACL,IAAK,eACL,IAAK,YACL,IAAK,cACL,IAAK,aACL,IAAK,iBACL,IAAK,kBACL,IAAK,kBACL,IAAK,gBACL,IAAK,kBACL,IAAK,gBACL,IAAK,gBACL,IAAK,qBACL,IAAK,cACL,IAAK,mBACL,IAAK,uBACL,IAAK,mBACL,IAAK,kBACL,IAAK,mBACL,IAAK,cACL,IAAK,iBACL,IAAK,kBACL,IAAK,eACL,IAAK,eACL,IAAK,oBACL,IAAK,sBACL,IAAK,sBACL,IAAK,mBACL,IAAK,qBACL,IAAK,qBACL,IAAK,gBACL,IAAK,aACL,IAAK,YACL,IAAK,cACL,IAAK,mBACL,IAAK,gBACL,IAAK,wBACL,IAAK,qBACL,IAAK,SACL,IAAK,kBACL,IAAK,gBACL,IAAK,kBACL,IAAK,gBACL,IAAK,gBACL,IAAK,mBACL,IAAK,mBACL,IAAK,oBACL,IAAK,eACL,IAAK,oBACL,IAAK,uBACL,IAAK,cACL,IAAK,WACL,IAAK,WACL,IAAK,aACL,IAAK,aACL,IAAK,eACL,IAAK,eACL,IAAK,cACL,IAAK,qBACL,IAAK,yBACL,IAAK,mBACL,IAAK,WACL,IAAK,iBACL,IAAK,iBACL,IAAK,eACL,IAAK,YACL,IAAK,mBACL,IAAK,mBACL,IAAK,iBACL,IAAK,kBACL,IAAK,oBACL,IAAK,mBACL,IAAK,cACL,IAAK,gBACL,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K,OACL,IAAK,OACL,IAAK,UACL,IAAK,YACL,IAAK,MACL,IAAK,OACL,IAAK,OACL,IAAK,UACL,IAAK,UACL,IAAK,QACL,IAAK,MACL,IAAK,OACL,IAAK,UACL,IAAK,SACL,IAAK,WACL,IAAK,SACL,IAAK,aACL,IAAK,OACL,IAAK,OACL,IAAK,OACL,IAAK,QACL,IAAK,QACL,IAAK,QACL,IAAK,OACL,IAAK,gBACL,IAAK,WACL,IAAK,aACL,IAAK,cACL,IAAK,gBACL,IAAK,kBACL,IAAK,gBACL,IAAK,WACL,IAAK,OACL,IAAK,QACL,IAAK,aACL,IAAK,KACL,IAAK,QACL,IAAK,SACL,IAAK,YACL,IAAK,cACL,IAAK,iBACL,IAAK,OACL,IAAK,gBACL,IAAK,WACL,IAAK,cACL,IAAK,WACL,IAAK,iBACL,IAAK,aACL,IAAK,YACL,IAAK,eACL,IAAK,eACL,IAAK,cACL,IAAK,aACL,IAAK,cACL,IAAK,eACL,IAAK,SACL,IAAK,WACL,IAAK,UACL,IAAK,UACL,IAAK,YACL,IAAK,UACL,IAAK,SACL,IAAK,SACL,IAAK,aACL,IAAK,YACL,IAAK,OACL,IAAK,YACL,IAAK,QACL,IAAK,OACL,IAAK,SACL,IAAK,YACL,IAAK,QACL,IAAK,YACL,IAAK,WACL,IAAK,UACL,IAAK,cACL,IAAK,cACL,IAAK,SACL,IAAK,eACL,IAAK,WACL,IAAK,YACL,IAAK,UACL,IAAK,WACL,IAAK,cACL,IAAK,MACL,IAAK,SACL,IAAK,UACL,IAAK,QACL,IAAK,UACL,IAAK,UACL,IAAK,WACL,IAAK,WACL,IAAK,UACL,IAAK,SACL,IAAK,QACL,IAAK,WACL,IAAK,QACL,IAAK,YACL,IAAK,UACL,IAAK,MACL,IAAK,QACL,IAAK,QACL,IAAK,QACL,IAAK,OACL,IAAK,QACL,IAAK,UACL,IAAK,UACL,IAAK,QACL,IAAK,OACL,IAAK,OACL,IAAK,QACL,IAAK,QACL,IAAK,QACL,IAAK,WACL,IAAK,aACL,IAAK,cACL,IAAK,OACL,IAAK,WACL,IAAK,OACL,IAAK,gBACL,IAAK,YACL,IAAK,cACL,IAAK,QACL,IAAK,iBACL,IAAK,kBACL,IAAK,kBACL,IAAK,iBACL,IAAK,UACL,IAAK,UACL,IAAK,WACL,IAAK,QACL,IAAK,UACL,IAAK,aACL,IAAK,eACL,IAAK,oBACL,IAAK,QACL,IAAK,UACL,IAAK,aACL,IAAK,eACL,IAAK,QACL,IAAK,cACL,IAAK,cACL,IAAK,WACL,IAAK,eACL,IAAK,YACL,IAAK,WACL,IAAK,WACL,IAAK,OACL,IAAK,OACL,IAAK,UACL,IAAK,QACL,IAAK,SACL,IAAK,OACL,IAAK,WACL,IAAK,gBACL,IAAK,YACL,IAAK,kBACL,IAAK,eACL,IAAK,gBACL,IAAK,mBACL,IAAK,cACL,IAAK,gBACL,IAAK,cACL,IAAK,WACL,IAAK,MACL,IAAK,YACL,IAAK,aACL,IAAK,qBACL,IAAK,mBACL,IAAK,UACL,IAAK,UACL,IAAK,UACL,IAAK,UACL,IAAK,UACL,IAAK,UACL,IAAK,UACL,IAAK,UACL,IAAK,UACL,IAAK,UACL,IAAK,UACL,IAAK,UACL,IAAK,QACL,IAAK,QACL,IAAK,UACL,IAAK,QACL,IAAK,SACL,IAAK,OACL,IAAK,SACL,IAAK,UACL,IAAK,QACL,IAAK,QACL,IAAK,QACL,IAAK,aACL,IAAK,cACL,IAAK,YACL,IAAK,SACL,IAAK,UACL,IAAK,QACL,IAAK,YACL,IAAK,YACL,IAAK,aACL,IAAK,SACL,IAAK,WACL,IAAK,QACL,IAAK,SACL,IAAK,SACL,IAAK,QACL,IAAK,SACL,IAAK,MACL,IAAK,OACL,IAAK,UACL,IAAK,UACL,IAAK,UACL,IAAK,UACL,IAAK,OACL,IAAK,OACL,IAAK,WACL,IAAK,WACL,IAAK,UACL,IAAK,WACL,IAAK,OACL,IAAK,YACL,IAAK,YACL,IAAK,UACL,IAAK,aACL,IAAK,aACL,IAAK,QACL,IAAK,QACL,IAAK,WACL,IAAK,WACL,IAAK,UACL,IAAK,SACL,IAAK,WACL,IAAK,UACL,IAAK,QACL,IAAK,UACL,IAAK,WACL,IAAK,YACL,IAAK,WACL,IAAK,aACL,IAAK,UACL,IAAK,UACL,IAAK,UACL,IAAK,WACL,IAAK,YACL,IAAK,YACL,IAAK,YACL,IAAK,YACL,IAAK,YACL,IAAK,cACL,IAAK,UACL,IAAK,YACL,IAAK,WACL,IAAK,UACL,IAAK,UACL,IAAK,UACL,IAAK,WACL,IAAK,UACL,IAAK,cACL,IAAK,MACL,IAAK,cACL,IAAK,MACL,IAAK,aACL,IAAK,gBACL,IAAK,UACL,IAAK,eACL,IAAK,UACL,IAAK,WACL,IAAK,SACL,IAAK,YACL,IAAK,YACP,EACID,GAAW,CACb,EAAG,EACH,EAAG,EACH,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,GAAI,EACJ,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,EACL,IAAK,E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;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAqW/D,EAENA,EAAe,IAAI,+CAA+C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAgH5D,EAENA,EAAe,IAAI,mCAAmC;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAqNhD,EAENA,EAAe,IAAI,wCAAwC;AAAA;AAAA;AAAA,OAGrD,EAENA,EAAe,IAAI,iDAAiD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAkD9D,EAENA,EAAe,IAAI,4CAA4C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAYzD,EAENA,EAAe,IAAI,yCAAyC;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAoYtD,EAENA,EAAe,IAAI,yCAAyC;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAgKtD,EAENA,EAAe,IAAI,uCAAuC;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAmDpD,EAENA,EAAe,IAAI,2CAA2C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAoCxD,EAENA,EAAe,IAAI,yCAAyC;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA0WtD,EAENA,EAAe,IAAI,6CAA6C;AAAA;AAAA;AAAA;AAAA,QAIzD,EAEPA,EAAe,IAAI,yCAAyC;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAQtD,EAENA,EAAe,IAAI,0CAA0C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAqIvD,EAENA,EAAe,IAAI,0CAA0C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAsJvD,EAENA,EAAe,IAAI,0CAA0C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA2FvD,EAENA,EAAe,IAAI,8CAA8C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,KAY7D,EAEJA,EAAe,IAAI,uDAAuD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,QAanE,EAEPA,EAAe,IAAI,6CAA6C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAiC1D,EAENA,EAAe,IAAI,2CAA2C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA8OxD,EAENA,EAAe,IAAI,6CAA6C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA6I1D,EAENA,EAAe,IAAI,+CAA+C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,QAgB3D,EAEPA,EAAe,IAAI,6CAA6C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,QAWzD,EAEPA,EAAe,IAAI,6CAA6C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,QAoEzD,EAEPA,EAAe,IAAI,mDAAmD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,iCA8JtC,EAEhCA,EAAe,IAAI,wCAAwC;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA+BrD,EAENA,EAAe,IAAI,mDAAmD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA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;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAsHzE,EAENA,EAAe,IAAI,6DAA6D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA2E1E,EAENA,EAAe,IAAI,mEAAmE;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA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AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAsN3D,EAENA,EAAe,IAAI,yDAAyD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA8CtE,EAENA,EAAe,IAAI,yDAAyD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,CAsD5E,EAEAA,EAAe,IAAI,wDAAwD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAuBrE,EAENA,EAAe,IAAI,kDAAkD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA2G/D,EAENA,EAAe,IAAI,uEAAuE;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA8JpF,EAENA,EAAe,IAAI,0DAA0D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAmyBvE,EAENA,EAAe,IAAI,sDAAsD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAqNnE,EAENA,EAAe,IAAI,+CAA+C;AAAA;AAAA,OAE5D,EAENA,EAAe,IAAI,qDAAqD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;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AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAsDzF,EAENA,EAAe,IAAI,qEAAqE;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAqGlF,EAENA,EAAe,IAAI,gEAAgE;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;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;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA0HvD,EAENA,EAAe,IAAI,uCAAuC;AAAA;AAAA;AAAA,OAGpD,EAENA,EAAe,IAAI,4CAA4C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;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AA,OAkB1F,EAENA,EAAe,IAAI,wDAAwD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA6GrE,EAENA,EAAe,IAAI,8DAA8D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AA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;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,QA8OvE,EAEPA,EAAe,IAAI,4DAA4D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA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AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAsFnE,EAENA,EAAe,IAAI,wDAAwD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,CAkG3E,EAEAA,EAAe,IAAI,uDAAuD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAwLpE,EAENA,EAAe,IAAI,qEAAqE;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAiClF,EAENA,EAAe,IAAI,0DAA0D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;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AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,SAyJxE,EAERA,EAAe,IAAI,8CAA8C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAyE3D,EAENA,EAAe,IAAI,qDAAqD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAkNlE,EAENA,EAAe,IAAI,mDAAmD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA4ChE,EAENA,EAAe,IAAI,4DAA4D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAoGzE,EAENA,EAAe,IAAI,oDAAoD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAmHjE,EAENA,EAAe,IAAI,kDAAkD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAsK/D,EAENA,EAAe,IAAI,2CAA2C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA4DxD,EAENA,EAAe,IAAI,2CAA2C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;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AA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,QA8EjE,EAEPA,EAAe,IAAI,+CAA+C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,QAc3D,EAEPA,EAAe,IAAI,8CAA8C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAA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AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAkKhE,EAENA,EAAe,IAAI,2DAA2D;AAAA;AAAA,OAExE,EAENA,EAAe,IAAI,uDAAuD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAoJpE,EAENA,EAAe,IAAI,yEAAyE;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA2FtF,EAENA,EAAe,IAAI,+DAA+D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;A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AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAmFpE,EAENA,EAAe,IAAI,8CAA8C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA8C3D,EAENA,EAAe,IAAI,kDAAkD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAqJ/D,EAENA,EAAe,IAAI,+CAA+C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA+H5D,EAENA,EAAe,IAAI,iDAAiD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAmO9D,EAENA,EAAe,IAAI,iDAAiD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAmC9D,EAENA,EAAe,IAAI,2DAA2D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA4KxE,EAENA,EAAe,IAAI,uDAAuD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAuNpE,EAENA,EAAe,IAAI,oDAAoD;AAAA;AAAA;AAAA,OAGjE,EAENA,EAAe,IAAI,+CAA+C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA4F5D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AA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,CAoMzE,EAEAA,EAAe,IAAI,8CAA8C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,CAwLjE,EAEAA,EAAe,IAAI,kDAAkD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,WAiW5D,EAETA,EAAe,IAAI,sDAAsD;AAAA;AAAA;AAAA,OAGnE,EAENA,EAAe,IAAI,+CAA+C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,CA6OlE,EAEAA,EAAe,IAAI,mDAAmD;AAAA;AAAA;AAAA,OAGhE,EAENA,EAAe,IAAI,sDAAsD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAmCnE,EAENA,EAAe,IAAI,wEAAwE;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,QA8BpF,EAEPA,EAAe,IAAI,qEAAqE;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,QAejF,EAEPA,EAAe,IAAI,sDAAsD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAyDnE,EAENA,EAAe,IAAI,4DAA4D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAkEzE,EAENA,EAAe,IAAI,8DAA8D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAmD3E,EAENA,EAAe,IAAI,0DAA0D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAavE,EAENA,EAAe,IAAI,4DAA4D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,mCAsB7C,EAElCA,EAAe,IAAI,0DAA0D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAuCvE,EAENA,EAAe,IAAI,oEAAoE;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,QAyBhF,EAEPA,EAAe,IAAI,+CAA+C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA0B5D,EAENA,EAAe,IAAI,oDAAoD;AAAA;AAAA,OAEjE,EAENA,EAAe,IAAI,oDAAoD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAYjE,EAENA,EAAe,IAAI,oDAAoD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,WAyB9D,EAETA,EAAe,IAAI,oDAAoD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA8DjE,EAENA,EAAe,IAAI,2CAA2C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAoGxD,EAENA,EAAe,IAAI,iDAAiD;AAAA;AAAA;AAAA;AAAA;AAAA,OAK9D,EAENA,EAAe,IAAI,8CAA8C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAuC3D,EAENA,EAAe,IAAI,mDAAmD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA2MhE,EAENA,EAAe,IAAI,oDAAoD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAuCjE,EAENA,EAAe,IAAI,6CAA6C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAsE1D,EAENA,EAAe,IAAI,mDAAmD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA+EhE,EAENA,EAAe,IAAI,iDAAiD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAkE9D,EAENA,EAAe,IAAI,qDAAqD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA6FlE,EAENA,EAAe,IAAI,0DAA0D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA0SvE,EAENA,EAAe,IAAI,8DAA8D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA4E3E,EAENA,EAAe,IAAI,oEAAoE;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA0GjF,EAENA,EAAe,IAAI,oEAAoE;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAkIjF,EAENA,EAAe,IAAI,oEAAoE;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA4LjF,EAENA,EAAe,IAAI,2DAA2D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAwDxE,EAENA,EAAe,IAAI,yDAAyD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA0CtE,EAENA,EAAe,IAAI,kDAAkD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAwE/D,EAENA,EAAe,IAAI,6CAA6C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA+J1D,EAENA,EAAe,IAAI,qDAAqD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA2HlE,EAENA,EAAe,IAAI,gDAAgD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA2K7D,EAENA,EAAe,IAAI,yDAAyD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAgEtE,EAENA,EAAe,IAAI,kDAAkD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA4L/D,EAENA,EAAe,IAAI,mDAAmD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAqDhE,EAENA,EAAe,IAAI,8CAA8C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAojB3D,EAENA,EAAe,IAAI,mDAAmD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA6MhE,EAENA,EAAe,IAAI,yDAAyD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAyDtE,EAENA,EAAe,IAAI,sDAAsD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA+hBnE,EAENA,EAAe,IAAI,gDAAgD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAqE7D,EAENA,EAAe,IAAI,yDAAyD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,SAiCpE,EAERA,EAAe,IAAI,mDAAmD;AAAA;AAAA,wBAE/C,EAEvBA,EAAe,IAAI,kDAAkD;AAAA,mGAC6B,EAElGA,EAAe,IAAI,gDAAgD;AAAA,kGAC8B,EAEjGA,EAAe,IAAI,iDAAiD;AAAA,mGAC8B,EAElGA,EAAe,IAAI,4EAA4E;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,SA6BvF,EAERA,EAAe,IAAI,mEAAmE;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,SAwC9E,EAERA,EAAe,IAAI,0EAA0E;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,SAiCrF,EAERA,EAAe,IAAI,iEAAiE;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,SAwC5E,EAERA,EAAe,IAAI,wFAAwF;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,SAmCnG,EAERA,EAAe,IAAI,iEAAiE;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,SAyB5E,EAERA,EAAe,IAAI,2EAA2E;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,SA2CtF,EAERA,EAAe,IAAI,uEAAuE;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,SA6BlF,EAERA,EAAe,IAAI,iFAAiF;AAAA;AAAA;AAAA;AAAA;AAAA,CAKpG,EAEAA,EAAe,IAAI,gDAAgD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,qBAU/C,EAEpBA,EAAe,IAAI,kDAAkD;AAAA,uBAC/C,EAEtBA,EAAe,IAAI,iDAAiD;AAAA;AAAA,uBAE9C,EAEtBA,EAAe,IAAI,gDAAgD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,qBAY/C,EAEpBA,EAAe,IAAI,mDAAmD;AAAA;AAAA,qBAElD,EAEpBA,EAAe,IAAI,iDAAiD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAU9D,EAENA,EAAe,IAAI,mDAAmD;AAAA;AAAA;AAAA,CAGtE,EAEAA,EAAe,IAAI,8CAA8C,kQAAkQ,EAEnUA,EAAe,IAAI,iDAAiD;AAAA;AAAA,gBAErD,EAEfA,EAAe,IAAI,+CAA+C;AAAA;AAAA,gBAEnD,EAEfA,EAAe,IAAI,8CAA8C;AAAA,kJACgF,EAEjJA,EAAe,IAAI,mDAAmD;AAAA;AAAA,mBAEpD,EAElBA,EAAe,IAAI,kDAAkD;AAAA,6FACuB,EAE5FA,EAAe,IAAI,iEAAiE;AAAA;AAAA;AAAA,gBAGrE,EAEfA,EAAe,IAAI,mDAAmD;AAAA,8FACuB,EAE7FA,EAAe,IAAI,2CAA2C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA2BxD,EAENA,EAAe,IAAI,gDAAgD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,CAcnE,EAEAA,EAAe,IAAI,8CAA8C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAa3D,EAENA,EAAe,IAAI,0CAA0C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAqDvD,EAENA,EAAe,IAAI,0CAA0C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAWvD,EAENA,EAAe,IAAI,uDAAuD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAYpE,EAENA,EAAe,IAAI,2CAA2C,sEAAsE,EAEpIA,EAAe,IAAI,kDAAkD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAsB/D,EAENA,EAAe,IAAI,4CAA4C,4DAA4D,EAE3HA,EAAe,IAAI,2CAA2C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAgDxD,EAENA,EAAe,IAAI,wCAAwC;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAkHrD,EAENA,EAAe,IAAI,+CAA+C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAmE5D,EAENA,EAAe,IAAI,yDAAyD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,SA2BpE,EAERA,EAAe,IAAI,mDAAmD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,CAyDtE,EAEAA,EAAe,IAAI,4DAA4D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAoBzE,EAENA,EAAe,IAAI,yDAAyD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAwDtE,EAENA,EAAe,IAAI,wDAAwD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA8CrE,EAENA,EAAe,IAAI,2DAA2D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA+BxE,EAENA,EAAe,IAAI,sEAAsE;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAOnF,EAENA,EAAe,IAAI,0DAA0D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAsEvE,EAENA,EAAe,IAAI,uDAAuD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA2BpE,EAENA,EAAe,IAAI,qEAAqE;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAiGlF,EAENA,EAAe,IAAI,oDAAoD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,CAevE,EAEAA,EAAe,IAAI,+CAA+C;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAa5D,EAENA,EAAe,IAAI,0DAA0D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,QAmCtE,EAEPA,EAAe,IAAI,uDAAuD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAqCpE,EAENA,EAAe,IAAI,wDAAwD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,QA4BpE,EAEPA,EAAe,IAAI,qDAAqD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,QAwCjE,EAEPA,EAAe,IAAI,sDAAsD;AAAA;AAAA;AAAA,QAGlE,EAEPA,EAAe,IAAI,sDAAsD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,QAalE,EAEPA,EAAe,IAAI,+DAA+D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,QA6H3E,EAEPA,EAAe,IAAI,4DAA4D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAoDzE,EAENA,EAAe,IAAI,6DAA6D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAmF1E,EAENA,EAAe,IAAI,uEAAuE;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAwBpF,EAENA,EAAe,IAAI,yDAAyD;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAoKtE,EAENA,EAAe,IAAI,mEAAmE;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OA0DhF,EAENA,EAAe,IAAI,gEAAgE;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;A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AA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAqD3E,EAENA,EAAe,IAAI,8DAA8D;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,OAyL3E,EAENA,EAAe,IAAI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","x_google_ignoreList":[11,12,24,25,26,73,74,75,106,107,108,109,110,111,112,113,114,115,116,117,118,119,120,121,122,123,124,125,126,127,128,129,130,131,132,133,134,135,136,137,138,139,140,141,142,143,144,145,146,147,148,149,150,151,152,153,154,155,156,157,158,159,160,161,162,163,164,165,166,176,177,178,179,180,181,182,183,184,185,186,187,188,189,190,191,192,193,194,195,196,197,198,199,200,201,202,203,204,205,206,207,208,209,210,211,212,213,214,215,216,217,218,219,220,221,222,223,224,225,226,227,228,229,230,231,232,233,234,249,250,251,252,253,254,255,256,257,258,259,260,261,262,263,264,265,266,267,268,269,270,271,272,273,274,275,276,292,293,294,295,296,297,298,299,302,313,615,616,617,618,619,620,621,622,623,624,627,637]}